如何使用多线程在java中切换交通灯,使每个灯只亮3秒钟?

如何使用多线程在java中切换交通灯,使每个灯只亮3秒钟?,java,multithreading,Java,Multithreading,我制作了一个交通灯刺激系统,其中每个交通灯,即绿色、红色、黄色,将分别亮3秒钟。 我成功地创建了这个系统的GUI public class TrafficLightSimulator extends Application implements Runnable{ Circle red = new Circle(); Circle green = new Circle(); Circle yellow = new Circle(); Button b1 = new

我制作了一个交通灯刺激系统,其中每个交通灯,即绿色、红色、黄色,将分别亮3秒钟。 我成功地创建了这个系统的GUI

public class TrafficLightSimulator extends Application implements Runnable{
    Circle red = new Circle();
    Circle green = new Circle();
    Circle yellow = new Circle();
    Button b1 = new Button();
@Override
public void start(Stage stage) {
    //Drawing a Rectangle 
    Rectangle rectangle = new Rectangle();


    //grid layout
    GridPane grid = new GridPane();
    grid.setHgap(20);
    grid.setVgap(5);
//buttons
    HBox hbButtons = new HBox();

    Button buttonStart = new Button("Start");
    Button buttonStop = new Button("Stop");
  buttonStart.setOnAction(new EventHandler<ActionEvent>() {
        public void handle(ActionEvent event) {
        green.setFill(Color.YELLOW);
}
    });
   buttonStop.setOnAction(new EventHandler<ActionEvent>() {
        public void handle(ActionEvent event) {
   TrafficLightSimulator tl=new TrafficLightSimulator();
   Thread t1=new Thread(tl);
   t1.start();
        }
    });
    //labels and textfeilds
    Label lblGreen = new Label("Green");
    TextField tfGreen = new TextField("3");
    Label lblYellow = new Label("Yellow");
    TextField tfYellow = new TextField("3");
    Label lblRed = new Label("Red");
    TextField tfRed = new TextField("3");

    grid.add(lblGreen, 0, 0);
    grid.add(tfGreen, 1, 0);
    grid.add(lblYellow, 0, 1);
    grid.add(tfYellow, 1, 1);
    grid.add(lblRed, 0, 2);
    grid.add(tfRed, 1, 2);
    grid.setPadding(new Insets(320, 5, 30, 40));


    hbButtons.getChildren().addAll(buttonStart, buttonStop);
    hbButtons.setAlignment(Pos.BOTTOM_CENTER);
    //Setting the properties of the rectangle 
    rectangle.setX(150);
    rectangle.setY(75);
    rectangle.setWidth(400);
    rectangle.setHeight(200);

    rectangle.setArcHeight(50);
    rectangle.setArcWidth(50);
    Color c = Color.web("#404040");
    Color color1 = Color.web("#404040");
    Color color2 = Color.web("#808080");
    Color greenColor = Color.web("#00FF00");

    rectangle.setFill(c);
    //setting circle properties

    green.setCenterX(230);
    green.setCenterY(170);
    green.setRadius(50);
    green.setFill(greenColor);

    yellow.setCenterX(345);
    yellow.setCenterY(170);
    yellow.setRadius(50);
    yellow.setFill(color2);
    red.setCenterX(465);
    red.setCenterY(170);
    red.setRadius(50);
    red.setFill(color2);
    hbButtons.setPadding(new Insets(15, 12, 15, 12));
    hbButtons.setSpacing(10);   // Gap between nodes
    //Creating a Group object  
    StackPane rootPane = new StackPane();
    Pane p1 = new Pane(red, green, yellow);
    Pane p2 = new Pane(rectangle);
    grid.add(hbButtons, 2, 2, 2, 1);
    //  grid.add(grid, 2, 0, 0, 0);

    rootPane.getChildren().addAll(p2, p1, grid);
    //Creating a scene object 
    Scene scene = new Scene(rootPane, 600, 500);

    //Setting title to the Stage 
    stage.setTitle("Drawing a Rectangle");

    //Adding scene to the stage 
    stage.setScene(scene);

    //Displaying the contents of the stage 
    stage.show();
}

将“开始”按钮的事件处理程序更改为:

buttonStart.setOnAction(new EventHandler<ActionEvent>() {
    public void handle(ActionEvent event) {
        Thread t = new Thread() {
            @Override
            public void run() {
                try {
                    green.setFill(Color.GREEN);

                    Thread.sleep(3000L);
                    green.setFill(Color.GRAY);
                    yellow.setFill(Color.YELLOW);

                    Thread.sleep(3000L);
                    yellow.setFill(Color.GRAY);
                    red.setFill(Color.RED);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        };
        t.start();
    }
});
buttonStart.setOnAction(新的EventHandler(){
公共无效句柄(ActionEvent事件){
线程t=新线程(){
@凌驾
公开募捐{
试一试{
绿色。设置填充(颜色。绿色);
线程。睡眠(3000L);
绿色。刚毛填充(颜色。灰色);
黄色。设置填充(颜色。黄色);
线程。睡眠(3000L);
黄色。刚毛填充(颜色。灰色);
红色。设置填充(颜色。红色);
}捕捉(中断异常e){
e、 printStackTrace();
}
}
};
t、 start();
}
});
请注意,圆的颜色在新线程中更新


在JavaFX中,事件和UI更新都由同一个JavaFX应用程序线程处理。如果我们不在其他线程中运行这些UI更新,渲染将一直阻止,直到事件处理程序完成。

谢谢!!!它工作得很好,但我认为我们必须在代码中稍加修改,才能从定时器的文本框中获取文本值。我们还需要添加一个按钮停止操作侦听器来停止线程

buttonStart.setOnAction(new EventHandler<ActionEvent>() {
            public void handle(ActionEvent event) {
                Thread t = new Thread() {
                    @Override
                    public void run() {
                        try {

                            green.setFill(Color.GREEN);
                            System.out.println(Long.parseLong(tfGreen.getText()));
                            Thread.sleep(Long.parseLong(tfGreen.getText()) * 1000);
                            green.setFill(Color.GRAY);

                            yellow.setFill(Color.YELLOW);
                            Thread.sleep(Long.parseLong(tfYellow.getText()) * 1000);
                            yellow.setFill(Color.GRAY);

                            red.setFill(Color.RED);
                            Thread.sleep(Long.parseLong(tfRed.getText()) * 1000);
                            red.setFill(Color.GRAY);

                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                    }
                };
                t.start();

                buttonStop.setOnAction(new EventHandler<ActionEvent>() {
                    public void handle(ActionEvent event) {
                        green.setFill(Color.GRAY);
                        yellow.setFill(Color.GRAY);
                        red.setFill(Color.GRAY);
                        t.stop();
                    }
                });
            }
        });
buttonStart.setOnAction(新的EventHandler(){
公共无效句柄(ActionEvent事件){
线程t=新线程(){
@凌驾
公开募捐{
试一试{
绿色。设置填充(颜色。绿色);
System.out.println(Long.parseLong(tfGreen.getText());
sleep(Long.parseLong(tfGreen.getText())*1000);
绿色。刚毛填充(颜色。灰色);
黄色。设置填充(颜色。黄色);
sleep(Long.parseLong(tfYellow.getText())*1000);
黄色。刚毛填充(颜色。灰色);
红色。设置填充(颜色。红色);
sleep(Long.parseLong(tfRed.getText())*1000);
红色。刚毛填充(颜色。灰色);
}捕捉(中断异常e){
e、 printStackTrace();
}
}
};
t、 start();
setOnAction(新的EventHandler(){
公共无效句柄(ActionEvent事件){
绿色。刚毛填充(颜色。灰色);
黄色。刚毛填充(颜色。灰色);
红色。刚毛填充(颜色。灰色);
t、 停止();
}
});
}
});

看看java.util.Timer,这里有一个例子:非常感谢您提供的解决方案。它对我非常有用。
buttonStart.setOnAction(new EventHandler<ActionEvent>() {
            public void handle(ActionEvent event) {
                Thread t = new Thread() {
                    @Override
                    public void run() {
                        try {

                            green.setFill(Color.GREEN);
                            System.out.println(Long.parseLong(tfGreen.getText()));
                            Thread.sleep(Long.parseLong(tfGreen.getText()) * 1000);
                            green.setFill(Color.GRAY);

                            yellow.setFill(Color.YELLOW);
                            Thread.sleep(Long.parseLong(tfYellow.getText()) * 1000);
                            yellow.setFill(Color.GRAY);

                            red.setFill(Color.RED);
                            Thread.sleep(Long.parseLong(tfRed.getText()) * 1000);
                            red.setFill(Color.GRAY);

                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                    }
                };
                t.start();

                buttonStop.setOnAction(new EventHandler<ActionEvent>() {
                    public void handle(ActionEvent event) {
                        green.setFill(Color.GRAY);
                        yellow.setFill(Color.GRAY);
                        red.setFill(Color.GRAY);
                        t.stop();
                    }
                });
            }
        });