java fx使用淡入淡出和时间轴过渡

时间:2015-08-03 23:43:11

标签: java javafx

我想用淡入淡出和时间线过渡制作图像幻灯片,所以当我按下按钮时,一个图像消失(通过淡入淡出动画)而另一个将出现(通过淡入淡出和时间线过渡)。现在我有一个代码像这只会使第一张图像消失,然后只有时间轴才能工作...(我使用并行转换,我也尝试过顺序,但它不起作用)。

public class MainPaneController implements Initializable {

@FXML
private BorderPane borderPane;

@FXML
private MenuBar menuBar;

@FXML
private AnchorPane anchorPaneTop;

@FXML
private HBox hBox;

@FXML
private MenuItem openFolder;

@FXML
private AnchorPane anchorPaneCenter;

@FXML
private ImageView imageView;

@FXML
private Button slideShowButton;

@FXML
private Menu menu;

private Image image;

private ImageParser parser;

private ObservableList<Image> imagesList;
private int indexPrev = 0;
private int indexNext = 0;
private Timeline timeline;
private AnimationTimer timer;
int i = 0;

@Override
public void initialize(URL location, ResourceBundle resources)
        throws IndexOutOfBoundsException {
    parser = new ImageParser();
    imagesList = FXCollections.observableArrayList();
    DirectoryChooser dc = new DirectoryChooser();

    openFolder.setOnAction(new EventHandler<ActionEvent>() {

        @Override
        public void handle(ActionEvent event) {
            File dir = dc.showDialog(new Stage());
            imagesList = parser.createImagesListFromFileList(dir);
            imageView.setImage(imagesList.get(0));

        }
    });
    slideShowButton.setOnAction(new EventHandler<ActionEvent>() {

        @Override
        public void handle(ActionEvent event) {
            FadeTransition ft = new FadeTransition();

            ft.setNode(imageView);
            ft.setDuration(new Duration(2000));
            ft.setFromValue(1.0);
            ft.setToValue(0.0);
            ft.setCycleCount(imagesList.size());
            ft.setAutoReverse(true);

            imageView.setImage(imagesList.get(0));

            timeline = new Timeline();
            timeline.setCycleCount(Timeline.INDEFINITE);
            timeline.setAutoReverse(true);

            KeyFrame key = new KeyFrame(Duration.seconds(1),
                    new EventHandler<ActionEvent>() {

                        @Override
                        public void handle(ActionEvent event) {

                            if (i < imagesList.size()) {
                                imageView.setImage(imagesList.get(i));
                                i++;
                            }

                        }

                    });
            timeline.getKeyFrames().add(key);

            ParallelTransition parallelTransition = new ParallelTransition();
            parallelTransition.getChildren().addAll(
                    ft,
                   timeline
            );
            parallelTransition.setCycleCount(Timeline.INDEFINITE);
            parallelTransition.play();


        }
    });
}



}

2 个答案:

答案 0 :(得分:1)

我只想使用一个Timeline。例如,对于250毫秒淡入,250毫秒淡出和每秒新图像,您需要以下KeyFrame s:

  • 时间0:不透明度0.0
  • 时间0.25秒:不透明度1.0
  • 时间0.75秒:不透明度1.0
  • 时间1.0秒不透明度0.0并加载新图像。

您可以使用

执行此操作
timeline = new Timeline();

KeyValue transparent = new KeyValue(imageView.opacityProperty(), 0.0);
KeyValue opaque = new KeyValue(imageView.opacityProperty(), 1.0);

KeyFrame startFadeIn = new KeyFrame(Duration.ZERO, transparent);
KeyFrame endFadeIn = new KeyFrame(Duration.millis(250), opaque);
KeyFrame startFadeOut = new KeyFrame(Duration.millis(750), opaque);
KeyFrame endFadeOut = new KeyFrame(Duration.millis(1000), e -> {
    if (i < images.size()) {
        imageView.setImage(images.get(i));
        i++ ;
    }
}, transparent);

timeline.getKeyFrames().addAll(startFadeIn, endFadeIn, startFadeOut, endFadeOut);

timeline.setCycleCount(Animation.INDEFINITE);
timeline.play();

答案 1 :(得分:0)

以上答案的变体解决了上一个答案评论中提出的问题。

以下在第一张图像中消失超过250毫秒,然后在接下来的500毫秒内以100%不透明度显示,在接下来的250毫秒内淡出它。第一个helpers.php加载初始图像,最后一个KeyFrame删除图像(通过将其设置为null)。当动画结束时,会调用KeyFrame的{​​{1}}方法来检查是否有更多图像,如果有,则调用Timeline,这会启动再一次处理。请注意,从OnFinished() displayNextMedia()事件处理程序中调用displayNextImage()不会导致递归到Timeline

OnFinished()