tags:

views:

1260

answers:

3

I'm writing a very simple application in Javafx where there is a single button with a textbox on the stage as one scene.Now,the behavior I want is that when I click the button I can load another scene with another button and a textbox on the stage and remove the button i clicked alongwith the previous textbox. So the click of a button should load a new scene on the stage. any hints on how i can do this ?

Following Eric's advice:i have this code,and its working the way I want.

var showScene1 = true;
var showScene2 = false;
var showScene3 = false;

def stage = Stage
{
  title: "Hello World"

    var scene1 =Scene
    {
          content:
          [

                                  Text {
                          font : Font {
                                  size: 24
                          }
                          x: 10, y: 30
                          content: "HelloWorld from Scene1"
                  },
                  Button
                      {
                          text: "Click Me to change to Scene2 "
                          onMouseClicked: function( e: MouseEvent ):Void
                          {

                                  showScene2 = true;

                                  println("In scene 2");

                          }

                        }


          ]
     }



     var scene2 =Scene
        {
              content:
              [

                                      Text {
                              font : Font {
                                      size: 24
                              }
                              x: 10, y: 30
                              content: "HelloWorld from Scene2"
                      },
                      Button
                          {
                              text: "Click Me to change to Scene3 "
                              onMouseClicked: function( e: MouseEvent ):Void
                              {
                                      showScene1 = false;
                                      showScene2 = false;
                                      showScene3 = true;
                                      println("In scene 3");

                              }

                            }


              ]
         }

     var scene3 =Scene
        {
              content:
              [

                                      Text {
                              font : Font {
                                      size: 24
                              }
                              x: 10, y: 30
                              content: "HelloWorld from Scene3"
                      }


              ]
         }


scene: bind if (showScene2) then scene2
    else if (showScene1) then scene1
    else scene3

}
+1  A: 

If you are sure you will only have 2 different scenes, you can just bind the scene property of the Stage like so:

var showSecondScene = false;
var myButton = Button {
    onMouseClicked: function(e) { showSecondScene = true; }
}
def stage = Stage {
    scene: bind if (showSecondScene) then secondScene else firstScene
}

UPDATE: This actually works if you have any number of scenes like so:

scene: bind if (showScene1) then scene1
    else if (showScene2) then scene2
    else scene3

You might consider why you'd have more than 2 scenes, instead opting for setting 'visible: false' on overlapping Group nodes instead.

Eric Wendelin
I have more than 2 scenes and this technique is just fine for 2 scenes because Javafx doesn't allow if-else or switch case after scene bind. Is there any other way i can try ?
iceman
I've updated my answer. Definitely consider if you want multiple scenes or just multiple CustomNodes setting visibility as appropriate.
Eric Wendelin
Is it possible to enter debug print statements inside a scene declaration to know if its loading or being called? I can't call any method inside a scene.
iceman
Yes just use println("message"), but you must NOT be in WebStart application mode or you must configure your Java Web Start settings. I would recommend running this in NetBeans using "Standard" execution mode.
Eric Wendelin
You're right , I could insert println in a scene, but cannot call any other methods inside a scene declaration. For example I want to call a java text to speech method after a scene loads, but I'm not able to do that. I can do that inside a mouse click listener(for a button) which is inside a scene.I also tried replacing the if-else ladder after 'bind' with switch-case,but that doesn't work either.
iceman
@Eric why use visibility settings? Doesn't that make the scene graph unnecessarily large? If certain things like resizing happen, wouldn't that cause calculations to happen on the graph that don't need to be done?
Mike Caron
+1  A: 

Eliminate all the if-else statements. Bind directly to a variable that contains the current scene.

import javafx.stage.Stage;
import javafx.scene.Scene;
import javafx.scene.text.Text;
import javafx.scene.text.Font;

var currentScene: Scene;


def scene1: Scene = Scene {
    content: Text {
        font : Font {
            size : 24
        }
        x: 10, y: 30
        content: "Scene 1"
        onMouseClicked: function( e ):Void {
         currentScene = scene2;
       }
    }
}

def scene2: Scene = Scene {
    content: Text {
        font : Font {
            size : 24
        }
        x: 10, y: 30
        content: "Scene 2"
        onMouseClicked: function( e ):Void {
         currentScene = scene1;
       }
    }
}

Stage {
    title: "Multi-Scene"
    width: 250
    height: 80
    scene: bind currentScene
}

currentScene = scene1;   
Abie
A: 

Following good old OO Principle, is there a way to capsule the contents scenes into separate classes and switch them? similar as with what is possible in flex or silverlight? this would make an application much more cleaner.

Thorsten Treffer