[SOLVED] Any easy way to do screen fade in and out?

This is an very basic functionality in any game, any easy way to do it ?
There is no function to do it in the screen class and I could not find anything.
For who that dont know what it is, its one effect to make the screen darker to black or inverse, in order to smooth show the next screen.

You can fake it with gradually updating (alpha) a quad in GUI node or using Nifty effects / panels. This is easy, and you could do an Appstate for it.

Or if I remember correctly, there are such effects in the ShaderBlow library as well.

Create a 1x1 quad, scale it to the full screen, place it on gui node or on root node (but you need to move and rotate it every time you rotate the camera). Set it’s material to Gui.j3md. Set “Color” parameter to (0, 0, 0, A) where a means alpha. Play with A value.

That seens to be easy enouth :smile:
Thanks @FrozenShade !
I wander why there is any native function for this, maybe using shaders…

This IS the shader’s way…

http://wiki.jmonkeyengine.org/doku.php/jme3:advanced:fade

I tried that, didn’t work for me. It simple do nothing in my screen.

Well, I just wrote that, please fell free to comment if there is any mistake.
Thanks friend !

package mygame;

import com.jme3.asset.AssetManager;
import com.jme3.material.Material;
import com.jme3.material.RenderState;
import com.jme3.math.ColorRGBA;
import com.jme3.renderer.RenderManager;
import com.jme3.renderer.Renderer;
import com.jme3.renderer.ViewPort;
import com.jme3.renderer.queue.RenderQueue;
import com.jme3.scene.Geometry;
import com.jme3.scene.Node;
import com.jme3.scene.control.AbstractControl;
import com.jme3.scene.shape.Quad;
import com.jme3.system.AppSettings;

public class ScreenController extends AbstractControl {

    private Geometry quad;
    private float duration;
    private float speedR,speedB,speedG,speedA;
    private long starterTimer;

    private ColorRGBA color = new ColorRGBA(0, 0, 0, 0);
    private ColorRGBA colorToFade = new ColorRGBA(0, 0, 0, 0);
    private boolean startFadeEffect = false;

    public ScreenController(Node p_guiNode,  AppSettings settings, AssetManager assetManager) {
        Quad mesh = new Quad(settings.getWidth(), settings.getHeight());
        quad = new Geometry("",mesh);            
        quad.getLocalScale().set(1.0f, 1.0f, 1.0f);
        quad.setQueueBucket(RenderQueue.Bucket.Gui);

        Material screenMaterial = new Material(assetManager, "Common/MatDefs/Gui/Gui.j3md");
        screenMaterial.getAdditionalRenderState().setBlendMode(RenderState.BlendMode.Alpha);
        quad.setMaterial(screenMaterial);
        screenMaterial.setColor("Color",color); // total transparent

        spatial = quad;
        p_guiNode.attachChild(spatial);
        spatial.addControl(this);
    }

    public void setScreenColor( ColorRGBA color) {
        this.color = color;
        quad.getMaterial().setColor("Color",color);
    }

    public void startFadeEffect(ColorRGBA colorToFade , float duration) {
        this.colorToFade=colorToFade;
        this.duration=duration;
        speedR = (colorToFade.r - color.r)/duration;
        speedB = (colorToFade.b - color.b)/duration;
        speedG = (colorToFade.g - color.g)/duration;
        speedA = (colorToFade.a - color.a)/duration;
        starterTimer=System.currentTimeMillis();
        if(speedR!=0||speedB!=0||speedG!=0||speedA!=0) startFadeEffect = true;
    }

    @Override protected void controlUpdate(float tpf) {
        if( startFadeEffect ) {
            color.r = color.r + speedR/tpf;
            color.b = color.b + speedB/tpf;
            color.g = color.g + speedG/tpf;
            color.a = color.a + speedA/tpf;
            quad.getMaterial().setColor("Color", color);

            if(System.currentTimeMillis()-starterTimer>=duration) {
                color=colorToFade;
                startFadeEffect=false;                    
            }
        }
    }

    @Override protected void controlRender(RenderManager rm, ViewPort vp) { }

}

When do you call fadeOut()?

Test case :

package mygame;

import com.jme3.app.SimpleApplication;
import com.jme3.effect.ParticleEmitter;
import com.jme3.material.Material;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Vector3f;
import com.jme3.post.FilterPostProcessor;
import com.jme3.post.filters.FadeFilter;
import com.jme3.renderer.RenderManager;
import com.jme3.scene.Geometry;
import com.jme3.scene.Node;
import com.jme3.scene.Spatial;
import com.jme3.scene.shape.Box;

public class Main extends SimpleApplication {

    public Main() {super(null);}

    float counter=10;
    private FilterPostProcessor fpp;
    private FadeFilter fade;

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

    @Override public void simpleInitApp() {
        Box b = new Box(0.5f, 0.5f, 0.5f);
        Geometry geom = new Geometry("Box", b);
        Material mat = new Material(assetManager, "Common/MatDefs/Misc/Unshaded.j3md");
        mat.setColor("Color", ColorRGBA.Blue);
        geom.setMaterial(mat);
        rootNode.attachChild(geom);

        fpp = new FilterPostProcessor(assetManager);
        fade = new FadeFilter(2); // e.g. 2 seconds
        fpp.addFilter(fade);
        viewPort.addProcessor(fpp);
    }

    @Override public void simpleUpdate(float tpf) {
        if(counter<=200) counter=counter+1;

        if(counter==200)
            fade.fadeIn();
    }

    @Override public void simpleRender(RenderManager rm) {
    }
}

Just to add, I was expecting the screen to get write on fadeIn…
It seens FadeOut is working thought.
It may be just an misunderstanding on what fade means here, so you can ignore it :slight_smile: