[SOLVED] NiftyGUI sounds are not played in popups

Hi,

I’ve noticed that sounds are not reproduced if the effect is defined in an element inside a popup. The sound is properly played in the screen and also other effects in elements inside the popup are rendered.

I’ve implemented a simple test for this:

Main.java:

package mygame;

import com.jme3.app.SimpleApplication;
import com.jme3.niftygui.NiftyJmeDisplay;
import de.lessvoid.nifty.Nifty;
import de.lessvoid.nifty.elements.Element;
import de.lessvoid.nifty.screen.Screen;
import de.lessvoid.nifty.screen.ScreenController;

public class Main extends SimpleApplication implements ScreenController {
    
    NiftyJmeDisplay niftyGui;
    Element popup;

    public static void main(String[] args) {
        Main app = new Main();
        app.start();
    }

    @Override
    public void simpleInitApp() {
        flyCam.setDragToRotate(true);
        
        niftyGui = new NiftyJmeDisplay(getAssetManager(), getInputManager(), getAudioRenderer(), guiViewPort);
        niftyGui.getNifty().fromXml("Interface/test.xml", "empty", this);
        guiViewPort.addProcessor(niftyGui);
    }

    public void showTestPopup() {
        popup=niftyGui.getNifty().findPopupByName("testPopup");
        if(popup==null)
        {
            popup=niftyGui.getNifty().createPopupWithId("testPopup", "testPopup");
        }
        niftyGui.getNifty().showPopup(niftyGui.getNifty().getCurrentScreen(), "testPopup", null);
    }
    
    public void hideTestPopup() {
        if(popup!=null)
        {
            niftyGui.getNifty().getCurrentScreen().closePopup(popup, null);
            popup=null;
        }
    }
    
    @Override
    public void bind(Nifty nifty, Screen screen) {
    }

    @Override
    public void onStartScreen() {
    }

    @Override
    public void onEndScreen() {
    }
}

test.xml:

<?xml version="1.0" encoding="UTF-8"?>
<nifty xmlns="http://nifty-gui.lessvoid.com/nifty-gui" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="https://raw.githubusercontent.com/void256/nifty-gui/1.4/nifty-core/src/main/resources/nifty.xsd https://raw.githubusercontent.com/void256/nifty-gui/1.4/nifty-core/src/main/resources/nifty.xsd">

    <useStyles filename="nifty-default-styles.xml" />
    <useControls filename="nifty-default-controls.xml" />
    <registerSound id="menuSelect" filename="Sounds/MenuSelect.ogg" />
    <registerSound id="menuBack" filename="Sounds/MenuBack.ogg" />
  
    <screen id="empty" controller="mygame.Main">
        <layer id="GLayer0" childLayout="center">
            <panel style="nifty-panel-red" childLayout="center" padding="18px,28px,40px,16px" width="100%" height="100%" align="center" valign="center">
                <interact onClick="showTestPopup()" />
                <effect>
                  <onHover name="colorPulsate" startColor="#f00f" endColor="#0f0f" startDelay="0" />
                  <onClick name="playSound" sound="menuSelect" />
                </effect>
            </panel>
        </layer>
    </screen>
    
    <popup id="testPopup" childLayout="center" backgroundColor="#000a">
      <panel style="nifty-panel-red" childLayout="center" padding="18px,28px,40px,16px" width="440px" height="250px" align="center" valign="center">
        <panel childLayout="vertical" align="center" valign="center">
          <panel childLayout="vertical" height="70%" width="100%">
            <text text="Popup text" style="base-font" align="center" valign="center" color="#000f" wrap="true"/>
          </panel>
          <panel childLayout="horizontal" align="center" height="30%" width="100%" backgroundColor="#fd0f" >
            <interact onClick="hideTestPopup()" />
            <effect>
              <onHover name="colorPulsate" startColor="#f00f" endColor="#0f0f" startDelay="0" />
              <onClick name="playSound" sound="menuSelect" />
            </effect>
          </panel>
        </panel>
      </panel>
    </popup>
      
</nifty>

Maybe a nifty issue?

Thanks

EDIT: I forgot to mention I’m using jme 3.2.1 SDK which includes nifty-1.4.3

1 Like

I’ve been investigating a little more, it’s not the play sound effect but the onclick event, if you change the effect to any other event it works as expected.

I’ve been debugging a while I found out that the EffectProcessorImpl has active=false when trying to execute the event. The method internalSetActive is being called setting it to true same as for the scene elements.

  .....
  private void renderActive(@Nonnull final NiftyRenderEngine renderDevice, @Nonnull final List<Effect> effects) {
    if (isInactive()) {
      return;
    }
    ....
  private void internalSetActive(final boolean newActive) {
    boolean oldActive = active;
    this.active = newActive;
    if (newActive != oldActive) {
      notify.effectProcessorStateChanged(newActive);
    }
  }

EDIT:

The problem is that, if you close the popup in the interact method, the effect is not run because the element is not rendered in the next frame and the play sound effect is rendered in the pre-frame phase of niftygui.

To bypass it, it’s enough to change the callback code as follows:

public void callback() {
    app.enqueue(new Callable () 
    {
        @Override
        public Object call() throws Exception
        {
            // Real callback code including popup hiding code
            return null;
        }
    });
}

This way the element is rendered once more and the sound is played properly

4 Likes