Beispiel #1
0
 /**
  * Adjusts the visualization to reflect the fisheye state of the node. If the node is in fisheye
  * state, its label will be reduced to the first letter.
  *
  * @param visual The visual of this {@link NodeContentPart}.
  * @param attrs The attributes map that stores the fisheye state of this {@link NodeContentPart}.
  * @param str The label of this {@link NodeContentPart}.
  * @return The adjusted label for this {@link NodeContentPart}.
  */
 protected String refreshFisheye(Group visual, Map<String, Object> attrs, String str) {
   // limit label to first letter when in fisheye mode (and not hovered)
   Object fisheye = attrs.get(ZestProperties.NODE_FISHEYE);
   if (fisheye instanceof Boolean && (Boolean) fisheye) {
     // register mouse event listeners
     visual.addEventHandler(MouseEvent.ANY, mouseHandler);
     if (!visual.isHover()) {
       // limit label to first letter
       // TODO: hide image, hide children/graph icon
       str = str.substring(0, 1);
       restoreZOrder();
     } else {
       if (originalBounds == null) {
         originalBounds = visual.localToScene(visual.getLayoutBounds());
       }
       // TODO: show image, show children/graph icon
       // highlight this node by moving it to the front
       List<IVisualPart<Node, ? extends Node>> children = getParent().getChildren();
       originalIndex = children.indexOf(this); // restore later
       getParent().reorderChild(this, children.size() - 1);
       visual.toFront();
     }
   } else {
     // TODO: show image, show children/graph icon
     restoreZOrder();
     visual.removeEventHandler(MouseEvent.ANY, mouseHandler);
   }
   return str;
 }
  public void load() {

    age = 1;
    turn = 1;
    Manager.getKernel().startAge(1);
    boards = Manager.getKernel().getBoards();
    hands = Manager.getKernel().getHands();
    screenX = GUIManager.width; // get the width of the screen
    screenY = GUIManager.height; // get the height of the screen
    // root = new Group();
    scene = new Scene(root, screenX, screenY, GUIManager.bgColor);
    root.setCursor(new ImageCursor(GUIManager.cursor));
    R = screenX / 2.8; //
    r = screenY / 3.1; //
    Ox = screenX / 2 - 140; //
    Oy = screenY / 2 - 98; //
    numOfPlayers = boards.length; // get the amount of players
    moveable = false;
    isDragging = false;
    resList = new SimpleResList[numOfPlayers];
    isIncard = false;
    orListNum = new int[numOfPlayers];
    coins = new int[numOfPlayers];
    for (int i = 0; i < numOfPlayers; i++) coins[i] = 3;
    judgeStateTimeline = new Timeline[numOfPlayers];
    buyStateCircle = new Circle[numOfPlayers];
    // wonderBorderEffect = false;
    // wonderReflectEffect = false;
    if (!GUIManager.enableReflectionEffect) {
      Ox = screenX / 2 - 140; //
      Oy = screenY / 2 - 68;
      r = screenY / 3.5;
    }
    observeIndex = 0;
    isTwice = new boolean[numOfPlayers];
    // primaryStage.setResizable(false);
    for (int i = 0; i < numOfPlayers; i++) isTwice[i] = false;
    handlerEnable = true;
    player = new Circle[numOfPlayers];
    wait = new Circle[numOfPlayers];
    // shop = new Circle[numOfPlayers];
    // look = new Circle[numOfPlayers];
    numOfCardGivenup = new Label();
    numOfCardGivenup.setVisible(true);
    CardsGivenup = 0;
    String s = String.valueOf(CardsGivenup);
    numOfCardGivenup.setText(s);
    numOfCardGivenup.setFont(Font.font("Arial", 45));

    if (GUIManager.enableGlowEffect) numOfCardGivenup.setEffect(new Glow());
    numOfCardGivenup.setTextFill(Color.web("#c88d15"));
    b = new Block(screenX, screenY);
    b.setVisible(false);
    root.getChildren().add(b);
    TPABoard.initialize();
    tpa = new TPABoard[numOfPlayers];

    final Paint[] color = new Paint[7];
    color[0] = Color.RED;
    color[1] = Color.ORANGE;
    color[2] = Color.YELLOW;
    color[3] = Color.YELLOWGREEN;
    color[4] = Color.GREEN;
    color[5] = Color.BLUE;
    color[6] = Color.PURPLE;
    for (int i = 0; i < 7; i++) {
      Paint temp = color[i];
      int newIndex = (int) (Math.random() * 7);
      color[i] = color[newIndex];
      color[newIndex] = temp;
    }

    playerBoard = new Group();
    // primaryStage.setFullScreen(true);
    // primaryStage.initStyle(StageStyle.UNDECORATED);
    Image bg = ResManager.getImage("bg.jpg");
    background = new ImageView(bg);
    if (!GUIManager.isFullScreen && !Manager.isApplet) this.setDragBackground(background);
    xrate = screenX / 1220.0;
    yrate = screenY / 784.0;
    background.setScaleX(xrate);
    background.setScaleY(yrate);
    numOfCardGivenup.setLayoutX(1106 * xrate);
    numOfCardGivenup.setLayoutY(94 * yrate);
    background.setTranslateX((scene.getWidth() - 1220.0) / 2.0);
    background.setTranslateY((scene.getHeight() - 784.0) / 2.0);
    // Rectangle clip = new Rectangle(0,0,1220,784);
    // clip.setArcHeight(50);
    // clip.setArcWidth(50);
    // background.setClip(clip);
    theta = Math.PI / 2;
    root.getChildren().add(background);
    root.getChildren().add(numOfCardGivenup);
    updateAge(1);

    Image im1 = ResManager.getImage("dir0.jpg");
    counterClockwise0 = new ImageView(im1);
    counterClockwise0.setScaleX(xrate);
    counterClockwise0.setScaleY(yrate);
    counterClockwise0.setTranslateX((im1.getWidth() * xrate - 107.0) / 2 + 271.23 * xrate);
    counterClockwise0.setTranslateY((im1.getHeight() * yrate - 86.0) / 2 + 560 * yrate);
    counterClockwise0.setVisible(false);

    Image im2 = ResManager.getImage("dir1.jpg");
    counterClockwise1 = new ImageView(im2);
    counterClockwise1.setScaleX(xrate);
    counterClockwise1.setScaleY(yrate);
    counterClockwise1.setTranslateX((im2.getWidth() * xrate - 112.0) / 2 + 826 * xrate);
    counterClockwise1.setTranslateY((im2.getHeight() * yrate - 86.0) / 2 + 560 * yrate);
    counterClockwise1.setVisible(false);

    Image im3 = ResManager.getImage("dir2.jpg");
    counterClockwise2 = new ImageView(im3);
    counterClockwise2.setScaleX(xrate);
    counterClockwise2.setScaleY(yrate);
    counterClockwise2.setTranslateX((im3.getWidth() * xrate - 52.0) / 2 + 846.4 * xrate);
    counterClockwise2.setTranslateY((im3.getHeight() * yrate - 39.0) / 2 + 223 * yrate);
    counterClockwise2.setVisible(false);

    Image im4 = ResManager.getImage("dir3.jpg");
    counterClockwise3 = new ImageView(im4);
    counterClockwise3.setScaleX(xrate);
    counterClockwise3.setScaleY(yrate);
    counterClockwise3.setTranslateX((im4.getWidth() * xrate - 52.0) / 2 + 302.6 * xrate);
    counterClockwise3.setTranslateY((im4.getHeight() * yrate - 39.0) / 2 + 222.8 * yrate);
    counterClockwise3.setVisible(false);
    root.getChildren().add(counterClockwise0);
    root.getChildren().add(counterClockwise1);
    root.getChildren().add(counterClockwise2);
    root.getChildren().add(counterClockwise3);

    Image[] image = new Image[numOfPlayers];
    wonder = new Wonders[numOfPlayers];
    Rectangle[] rec = new Rectangle[numOfPlayers];

    TreeMap<String, Integer> boardNameMap = new TreeMap<String, Integer>();
    boardNameMap.put("Rhodes", 0);
    boardNameMap.put("Alexandria", 1);
    boardNameMap.put("Ephesus", 2);
    boardNameMap.put("Babylon", 3);
    boardNameMap.put("Olympia", 4);
    boardNameMap.put("Halicarnassus", 5);
    boardNameMap.put("Giza", 6);

    TreeMap<String, Integer> resNameMap = new TreeMap<String, Integer>();
    // resNameMap.put("", value)

    for (int i = 0; i < numOfPlayers; i++) {
      // Manager.debug(boards[i].getResourceList());
      int ii = boardNameMap.get(boards[i].getName());
      if (boards[i].isBSide()) ii += 7;
      // Manager.debug("" + ii + boards[i].isBSide());
      image[i] = ResManager.getImage("board" + ii + ".jpg");
      // }
      rec[i] = new Rectangle(image[i].getWidth(), image[i].getHeight(), Color.TRANSPARENT);
      rec[i].setX(0);
      rec[i].setY(0);
      rec[i].setArcWidth(20);
      rec[i].setArcHeight(20);
      // if (i > 0) {
      rec[i].setStroke(color[i]);
      rec[i].setStrokeWidth(8);
      // } else {
      // MovingStroke.set(rec[i], (Color) color[i], 8.0, 20.0, 15.0, 0);
      // rec[i].setStroke(color[i]);
      // rec[i].setStrokeWidth(14);
      // }
      // tpa[i] = new TPABoard();
      if (GUIManager.enableLightingEffect) rec[i].setEffect(new Lighting());
      tpa[i] = new TPABoard();
      wonder[i] =
          new Wonders(
              image[i], screenX, screenY, GUIManager.enableReflectionEffect, ii, tpa[i], root);

      SimpleResList list = boards[i].getResourceList();
      for (int index = 1; index <= 7; index++) {
        for (int am = 0; am < list.numAt(index); am++) wonder[i].addResource(index);
        // Manager.debug(i + "Adding Res..." +
        // SimpleResList.resourceAt(index).toString());
      }
      wonder[i].addGoldSign(3);
      double percent = (workoutY1(Ox, Oy + r, i, numOfPlayers) - Oy + r) / (2 * r);
      wonder[i].setLayoutX(workoutX1(Ox, Oy + r, i, numOfPlayers) - (0.6 * percent + 0.4) * 160);
      wonder[i].setLayoutY(workoutY1(Ox, Oy + r, i, numOfPlayers) - (0.6 * percent + 0.4) * 90);
      wonder[i].setScaleX(0.6 * percent + 0.4);
      wonder[i].setScaleY(0.6 * percent + 0.4);
      wonder[i].getChildren().add(rec[i]);
      final int index = i;
      wonder[i].addEventHandler(
          MouseEvent.MOUSE_ENTERED,
          new EventHandler<MouseEvent>() {
            public void handle(MouseEvent event) {
              moveable = true;
              targetWonderIndex = index;
              for (int i = 0; i < numOfPlayers; i++) {
                Timeline tl =
                    new Timeline(
                        new KeyFrame(
                            Duration.seconds(0.3), new KeyValue(wonder[i].opacityProperty(), 1)));
                tl.play();
              }
            }
          });
      wonder[i].addEventHandler(
          MouseEvent.MOUSE_EXITED,
          new EventHandler<MouseEvent>() {
            public void handle(MouseEvent event) {
              if (!isDragging) moveable = false;
            }
          });

      wonder[i].getChildren().add(tpa[i]);
      tpa[i].setLayoutY(-80);
      tpa[i].setLayoutX(65);
      tpa[i].setScaleX(1 / (0.6 * percent + 0.4));
      tpa[i].setScaleY(1 / (0.6 * percent + 0.4));
    }

    dicClockwise();
    bigCircle = new Group();
    bigCircle
        .getChildren()
        .add(
            MovingStroke.set(
                new Circle(29, Color.web("white", 0)),
                Color.web("white", 0.7),
                6,
                5,
                10,
                0.3 * (age != 2 ? -1 : 1)));

    // bigCircle.setStroke(Color.web("white", 0.3));
    if (GUIManager.enableLightingEffect) bigCircle.setEffect(new Lighting());
    // bigCircle.setStrokeWidth(4);
    playerBoard.getChildren().add(bigCircle);

    for (int i = 0; i < numOfPlayers; i++) {
      wait[i] = new Circle(8);
      wait[i].setFill(color[i]);
      // look[i] = new Circle(4);
      // look[i].setFill(color[i]);
      // shop[i] = new Circle(5, Color.web("white", 0));
      // shop[i].setStroke(color[i]);
      // shop[i].setStrokeWidth(4);
      player[i] = wait[i];
      player[i].setVisible(true);
      if (GUIManager.enableLightingEffect) player[i].setEffect(new Lighting());
      player[i].setLayoutX(xForPlayer(i));
      player[i].setLayoutY(yForPlayer(i));
      player[i].addEventHandler(
          MouseEvent.MOUSE_ENTERED,
          new EventHandler<MouseEvent>() {
            public void handle(MouseEvent e) {
              // show the information of the players
            }
          });
      final int i1 = i;
      player[i].addEventHandler(
          MouseEvent.MOUSE_CLICKED,
          new EventHandler<MouseEvent>() {
            public void handle(MouseEvent e) {
              if (!isTwice[i1]) {
                if (remable) {
                  remable = false;
                }
                isTwice[i1] = true;
                for (int i = 0; i < numOfPlayers; i++) if (i != i1) isTwice[i] = false;
                handlerEnable = true;
                EventHandler<ActionEvent> act1 =
                    new EventHandler<ActionEvent>() {
                      public void handle(ActionEvent event) {
                        wonder[signrec].hideInfo();
                      }
                    };
                EventHandler<ActionEvent> act2 =
                    new EventHandler<ActionEvent>() {
                      public void handle(ActionEvent event) {
                        b.setVisible(false);
                        // cardBoard.toFront();
                        player[i1].setDisable(false);
                      }
                    };
                Timeline pre_tl =
                    new Timeline(
                        new KeyFrame(Duration.ZERO, act1),
                        new KeyFrame(
                            Duration.seconds(0.3),
                            new KeyValue(b.opacityProperty(), 0.7),
                            new KeyValue(cardBoard.layoutYProperty(), screenY - 105)),
                        new KeyFrame(Duration.seconds(0.6), new KeyValue(b.opacityProperty(), 0)),
                        new KeyFrame(Duration.seconds(0.6), act2));
                if (b.isVisible()) {
                  player[i1].setDisable(true);
                  pre_tl.play();
                }
                double[] forsort = new double[numOfPlayers];
                int[] sign = new int[numOfPlayers];
                for (int j = 0; j < numOfPlayers; j++) {
                  double percent = (workoutY1(Ox, Oy + r, j - i1, numOfPlayers) - Oy + r) / (2 * r);
                  Timeline tl =
                      new Timeline(
                          new KeyFrame(
                              Duration.seconds(0.3),
                              new KeyValue(
                                  wonder[j].layoutXProperty(),
                                  workoutX1(Ox, Oy + r, j - i1, numOfPlayers)
                                      - (0.6 * percent + 0.4) * 160),
                              new KeyValue(
                                  wonder[j].layoutYProperty(),
                                  workoutY1(Ox, Oy + r, j - i1, numOfPlayers)
                                      - (0.6 * percent + 0.4) * 90),
                              new KeyValue(tpa[j].scaleXProperty(), 1 / (0.6 * percent + 0.4)),
                              new KeyValue(tpa[j].scaleYProperty(), 1 / (0.6 * percent + 0.4)),
                              new KeyValue(wonder[j].scaleXProperty(), (0.6 * percent + 0.4)),
                              new KeyValue(wonder[j].scaleYProperty(), (0.6 * percent + 0.4))));
                  // wonder[j].setLayoutX();
                  // wonder[j].setLayoutY();
                  // tpa[j].setScaleX();
                  // tpa[j].setScaleY();
                  // wonder[j].setScaleX();
                  // wonder[j].setScaleY();
                  // Path path = new Path();
                  // Manager.debug(wonder[j].getLayoutX() +
                  // ":" +
                  // wonder[j].getLayoutY() + " " +
                  // wonder[j].getTranslateX() + ":" +
                  // wonder[j].getTranslateY());
                  // double x = wonder[j].getLayoutX();
                  // double y = wonder[j].getLayoutY();
                  // path.getElements().addAll(new
                  // MoveTo(screenX/2,screenY/2),
                  // new ArcTo(R/2,r/2,0,workoutX1(Ox, Oy + r,
                  // j - i1,
                  // numOfPlayers) - x, workoutY1(Ox, Oy + r,
                  // j - i1,
                  // numOfPlayers) - y,true,true)
                  // );
                  // path.setStroke(color[j]);
                  // path.setStrokeWidth(10);
                  // root.getChildren().add(path);
                  // PathTransition pt = new
                  // PathTransition(Duration.seconds(8),path,wonder[j]);
                  //
                  // pt.setCycleCount(PathTransition.INDEFINITE);
                  // pt.setAutoReverse(true);
                  // pt.play();

                  tl.play();
                  forsort[j] = wonder[j].getLayoutY();
                  sign[j] = j;
                }
                // wonder[i1].toFront();
                for (int i = 0; i < numOfPlayers - 1; i++) {
                  for (int j = 0; j < numOfPlayers - i - 1; j++) {
                    if (forsort[j] > forsort[j + 1]) {
                      double temp = forsort[j + 1];
                      forsort[j + 1] = forsort[j];
                      forsort[j] = temp;
                      int temp1 = sign[j + 1];
                      sign[j + 1] = sign[j];
                      sign[j] = temp1;
                    }
                  }
                }
                for (int i = 0; i < numOfPlayers; i++) {
                  if (sign[i] == i1) {

                    b.toFront();
                  }
                  wonder[sign[i]].toFront();
                }
                // if(!b.isVisible())
                cardBoard.toFront();
                playerBoard.toFront();
                // turn the wonderBoard
                if (Manager.getKernel().isReplayMode()) {
                  int index = 0;
                  if (age == 2) index = (2 * numOfPlayers - turn + i1 + 1) % numOfPlayers;
                  else index = (turn + i1 - 1) % numOfPlayers;
                  handCard.changeRole(boards[i1], hands[index]);
                  observeIndex = i1;
                }
              } else {
                EventHandler<ActionEvent> act =
                    new EventHandler<ActionEvent>() {
                      public void handle(ActionEvent event) {
                        wonder[i1].showInfo();
                        remable = true;
                        signrec = i1;
                        playerBoard.toFront();
                        // show the game information of player
                      }
                    };
                for (int i = 0; i < numOfPlayers; i++) isTwice[i] = false;
                b.setOpacity(0);
                b.toFront();
                playerBoard.toFront();
                wonder[i1].toFront();
                b.setVisible(true);

                handlerEnable = false;
                Timeline tl =
                    new Timeline(
                        new KeyFrame(
                            Duration.seconds(0.3),
                            new KeyValue(b.opacityProperty(), 0.7),
                            new KeyValue(cardBoard.layoutYProperty(), screenY)),
                        new KeyFrame(Duration.seconds(0.3), act));
                tl.play();
              }
              theta = Math.PI / 2 - 2 * Math.PI / numOfPlayers * i1;
            }
          });
      playerBoard.getChildren().add(player[i]);
      judgeStateTimeline[i] =
          new Timeline(
              new KeyFrame(Duration.seconds(0.3), new KeyValue(player[i].opacityProperty(), 0)));
      judgeStateTimeline[i].setCycleCount(Timeline.INDEFINITE);
      judgeStateTimeline[i].setAutoReverse(true);
      buyStateCircle[i] =
          (Circle)
              MovingStroke.set(
                  new Circle(xForPlayer(i), yForPlayer(i), 11, Color.TRANSPARENT),
                  Color.GOLDENROD,
                  3,
                  3,
                  4,
                  0.3);
      playerBoard.getChildren().add(buyStateCircle[i]);
      buyStateCircle[i].setVisible(false);
    }
    buy = new BuyBoard();
    buy.setScaleX(0.7);
    buy.setScaleY(0.7);
    buy.setLayoutY(0);
    buy.setVisible(false);
    root.getChildren().add(buy);
    CardGroup.initializeData(screenX, buy, boards[0]);
    handCard = new CardGroup();
    handCard.setplayer(wonder[0]);
    for (int i = 0; i < numOfPlayers; i++) {
      resList[i] = new SimpleResList(boards[i].getResourceList());
    }
    /*
     * primaryStage.addEventHandler(WindowEvent.RESIZE, new
     * EventHandler<MouseEvent>(){
     *
     * @Override public void handle(MouseEvent event) {
     * System.out.println("OK");
     *
     * }
     *
     * }); primaryStage.
     */

    scene.addEventHandler(
        MouseEvent.MOUSE_PRESSED,
        new EventHandler<MouseEvent>() {
          public void handle(MouseEvent e) {
            if (handlerEnable && moveable) {
              double x = e.getX(), y = e.getY();
              double tana = (y - Oy) / (x - Ox) * R / r;
              beta = Math.atan(tana);
              if (x <= Ox) beta = beta + Math.PI;
            }
          }
        });

    scene.addEventHandler(
        MouseEvent.MOUSE_RELEASED,
        new EventHandler<MouseEvent>() {
          public void handle(MouseEvent e) {
            isDragging = false;
            if (handlerEnable && moveable) theta = alpha - beta + theta;
          }
        });

    scene.addEventHandler(
        MouseEvent.MOUSE_DRAGGED,
        new EventHandler<MouseEvent>() {
          public void handle(MouseEvent e) {
            isDragging = true;
            if (handlerEnable && moveable) {
              for (int i = 0; i < numOfPlayers; i++) isTwice[i] = false;
              double x = e.getX() - 70, y = e.getY();
              double[] forsort = new double[numOfPlayers];
              int[] sign = new int[numOfPlayers];
              for (int i = 0; i < numOfPlayers; i++) {
                // int index = (i +
                // numOfPlayers+targetWonderIndex+1) %
                // numOfPlayers;
                int index = i;
                double percent = (workoutY(x, y, i, numOfPlayers) - Oy + r) / (2 * r);
                tpa[index].setScaleX(1 / (0.6 * percent + 0.4));
                tpa[index].setScaleY(1 / (0.6 * percent + 0.4));
                wonder[index].setScaleX((0.6 * percent + 0.4));
                wonder[index].setScaleY((0.6 * percent + 0.4));
                wonder[index].setLayoutX(
                    workoutX(x, y, i, numOfPlayers) - (0.6 * percent + 0.4) * 160);
                wonder[index].setLayoutY(
                    workoutY(x, y, i, numOfPlayers) - (0.6 * percent + 0.4) * 90);
                forsort[i] = wonder[i].getLayoutY();
                sign[i] = i;
              }
              for (int i = 0; i < numOfPlayers - 1; i++) {
                for (int j = 0; j < numOfPlayers - i - 1; j++) {
                  if (forsort[j] > forsort[j + 1]) {
                    double temp = forsort[j + 1];
                    forsort[j + 1] = forsort[j];
                    forsort[j] = temp;
                    int temp1 = sign[j + 1];
                    sign[j + 1] = sign[j];
                    sign[j] = temp1;
                  }
                }
              }
              for (int i = 0; i < numOfPlayers; i++) wonder[sign[i]].toFront();
              playerBoard.toFront();
              cardBoard.toFront();
            }
          }
        });

    scene.addEventHandler(
        MouseEvent.MOUSE_ENTERED,
        new EventHandler<MouseEvent>() {
          public void handle(MouseEvent e) {
            if (handlerEnable) {
              double y = e.getX();
              // if( y > screenY - 牌宽)
              // 牌.show();
            }
          }
        });
    switch (numOfPlayers) {
      case 3:
        root.getChildren().add(wonder[2]);
        break;
      case 4:
        root.getChildren().add(wonder[3]);
        root.getChildren().add(wonder[2]);
        break;
      case 5:
        root.getChildren().add(wonder[3]);
        root.getChildren().add(wonder[2]);
        root.getChildren().add(wonder[4]);
        break;
      case 6:
        root.getChildren().add(wonder[3]);
        root.getChildren().add(wonder[2]);
        root.getChildren().add(wonder[4]);
        root.getChildren().add(wonder[5]);
        break;
      case 7:
        root.getChildren().add(wonder[3]);
        root.getChildren().add(wonder[2]);
        root.getChildren().add(wonder[4]);
        root.getChildren().add(wonder[5]);
        root.getChildren().add(wonder[6]);
    }

    root.getChildren().add(wonder[1]);
    root.getChildren().add(wonder[0]);

    playerBoard.setLayoutX(scene.getWidth() - 60);
    playerBoard.setLayoutY(50);
    root.getChildren().add(playerBoard);
    handCard.nextHand(hands[0], true);
    cardBoard = new Group();
    cardBoard.getChildren().add(handCard);
    root.getChildren().add(cardBoard);
    cardBoard.setLayoutX(0);
    cardBoard.setLayoutY(screenY - 105);
    cardBoard.addEventHandler(
        MouseEvent.MOUSE_ENTERED,
        new EventHandler<MouseEvent>() {

          public void handle(MouseEvent e) {
            if (wonderFadeTimeline != null)
              for (Timeline tl : wonderFadeTimeline) if (tl != null) tl.stop();
            wonderFadeTimeline = new Timeline[numOfPlayers];
            wonderFadeTimeline[observeIndex] =
                new Timeline(
                    new KeyFrame(
                        Duration.seconds(0.1),
                        new KeyValue(cardBoard.layoutYProperty(), screenY - 270)));
            for (int i = 0; i < numOfPlayers; i++) {
              if (i == observeIndex) continue;
              if (wonder[i].getOpacity() > 0.99)
                wonderFadeTimeline[i] =
                    new Timeline(
                        new KeyFrame(
                            Duration.seconds(0), new KeyValue(wonder[i].opacityProperty(), 1)),
                        new KeyFrame(
                            Duration.seconds(1.5), new KeyValue(wonder[i].opacityProperty(), 1)),
                        new KeyFrame(
                            Duration.seconds(2),
                            new KeyValue(
                                wonder[i].opacityProperty(),
                                i == (1 + observeIndex) % numOfPlayers
                                        || i == (numOfPlayers - 1 + observeIndex) % numOfPlayers
                                    ? 0.65
                                    : 0.35,
                                Interpolator.EASE_IN)));
            }
            for (Timeline tl : wonderFadeTimeline) if (tl != null) tl.play();

            cardBoard.toFront();
            isIncard = true;
          }
        });
    cardBoard.addEventHandler(
        MouseEvent.MOUSE_EXITED,
        new EventHandler<MouseEvent>() {
          public void handle(MouseEvent e) {
            if (wonderFadeTimeline != null)
              for (Timeline tl : wonderFadeTimeline) if (tl != null) tl.stop();
            wonderFadeTimeline = new Timeline[numOfPlayers];
            wonderFadeTimeline[0] =
                new Timeline(
                    new KeyFrame(
                        Duration.seconds(0.15),
                        new KeyValue(cardBoard.layoutYProperty(), screenY - 105)));
            for (int i = 1; i < numOfPlayers; i++) {
              if (wonder[i].getOpacity() < 0.99)
                wonderFadeTimeline[i] =
                    new Timeline(
                        new KeyFrame(
                            Duration.seconds(0), new KeyValue(wonder[i].opacityProperty(), 0.5)),
                        new KeyFrame(
                            Duration.seconds(0.3), new KeyValue(wonder[i].opacityProperty(), 1)));
            }
            for (Timeline tl : wonderFadeTimeline) if (tl != null) tl.play();
            isIncard = true;
          }
        });
    this.exitDialog = Index.loadExitGameDialog(root);
    root.getChildren().add(new GameMenu());

    // For Test
    for (int i = 0; i < numOfPlayers; i++) {
      updatePlayerState(i, 1);
    }
    // ScoreBoard sb = new ScoreBoard(boards);
    // root.getChildren().add(sb);
    // JOptionPane.showMessageDialog(null,
    // boards[0].getLeftNeighbor().getName() + ""
    // +boards[0].getRightNeighbor().getName());
    if (Manager.getKernel().isReplayMode()) {
      // Button nextBtn = new Button("Next!");
      // nextBtn.setOnMouseClicked(new EventHandler<MouseEvent>() {
      // @Override
      // public void handle(MouseEvent event) {
      // nextTurn();
      // }
      // });
      // root.getChildren().add(nextBtn);
      root.getChildren().add(replayControl = new ReplayControl());
    }
  }
  private Scene createScene() {
    final Group group = new Group();
    Scene scene = new Scene(group);

    final TestNode node1 = new TestNode(300, 300, "node1");
    final TestNode node2 = new TestNode(500, 200, "node2");
    final TestNode node3 = new TestNode(80, 100, "node3");
    final TestNode node4 = new TestNode(650, 500, "node4");
    connectNodes(node1, node2);
    connectNodes(node1, node3);
    connectNodes(node2, node3);
    connectNodes(node1, node4);

    ArrayList<Node> array = new ArrayList<Node>();
    for (Edge n : node1.lines) array.add(n.line);
    for (Edge n : node2.lines) array.add(n.line);
    for (Edge n : node3.lines) array.add(n.line);
    for (Edge n : node4.lines) array.add(n.line);
    LinkedHashSet<Node> lhs = new LinkedHashSet<Node>();
    lhs.addAll(array); // Remove duplicates
    array.clear();
    array.addAll(lhs);

    array.add(node1.circle);
    array.add(node1.text);
    array.add(node2.circle);
    array.add(node2.text);
    array.add(node3.circle);
    array.add(node3.text);
    array.add(node4.circle);
    array.add(node4.text);

    Collection<Node> c = array;

    // Won't work with JavaFX 2.2 ->
    // group.getChildren().add(new Group(c));

    group
        .getChildren()
        .add(
            new Group(
                // edge1.line, edge2.line, edge3.line, edge4.line,
                node1.circle, node1.text,
                node2.circle, node2.text,
                node3.circle, node3.text,
                node4.circle, node4.text));

    group.setOnMousePressed(
        new EventHandler<MouseEvent>() {
          @Override
          public void handle(MouseEvent event) {
            lastX = event.getX();
            lastY = event.getY();
            if (ITERATION == 0) changePosition(node1, 100, 500); // TEMPORARY; FOR TESTING
            if (ITERATION == 1) changePosition(node2, 300, 200); // TEMPORARY; FOR TESTING
            if (ITERATION == 2) changePosition(node3, 600, 300); // TEMPORARY; FOR TESTING
            if (ITERATION == 3) changePosition(node4, 300, 530); // TEMPORARY; FOR TESTING
            if (ITERATION == 4) changePosition(node1, 500, 100); // TEMPORARY; FOR TESTING
            if (ITERATION == 5) changePosition(node1, 400, 350); // TEMPORARY; FOR TESTING
            if (ITERATION == 6) changePosition(node2, 200, 150); // TEMPORARY; FOR TESTING
            if (ITERATION == 6) changePosition(node3, 700, 200); // TEMPORARY; FOR TESTING
            ++ITERATION; // TEMPORARY; FOR TESTING
          }
        });

    group.addEventHandler(
        ZoomEvent.ZOOM_STARTED,
        new EventHandler<ZoomEvent>() {
          @Override
          public void handle(ZoomEvent event) {
            startScale = group.getScaleX();
            group.setScaleX(startScale);
            // group.setScaleY(startScale); // Is this necessary? Apparently not.
          }
        });
    group.addEventHandler(
        ZoomEvent.ZOOM,
        new EventHandler<ZoomEvent>() {
          @Override
          public void handle(ZoomEvent event) {
            group.setScaleX(startScale * event.getTotalZoomFactor());
            group.setScaleY(startScale * event.getTotalZoomFactor());
          }
        });

    // TODO: Adjust the text after rotation?

    group.addEventHandler(
        RotateEvent.ROTATION_STARTED,
        new EventHandler<RotateEvent>() {
          @Override
          public void handle(RotateEvent event) {
            startRotate = group.getRotate();
            group.setRotate(startRotate);
          }
        });
    group.addEventHandler(
        RotateEvent.ROTATE,
        new EventHandler<RotateEvent>() {
          @Override
          public void handle(RotateEvent event) {
            group.setRotate(startRotate + event.getTotalAngle());
          }
        });

    return scene;
  }