0

I want to display my images randomly one by one. The code below displays images one by one only if i put the duration time in seconds like:

 new KeyFrame(Duration.seconds(1), new KeyValue(imageView.imageProperty(), image1)),
 new KeyFrame(Duration.seconds(2), new KeyValue(imageView.imageProperty(), image2)),
 new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image3)),
 new KeyFrame(Duration.seconds(4), new KeyValue(imageView.imageProperty(), image4)),

So, my code will display image1 firstn image 2 second, image3 thirds and so on.

1) I want it to display random images every time.
2) Not to depend on duration time . Because if i put Duration.seconds(3) to all of them it will display just the first one.

Code looks like this:

package imagedisplayy;

import javafx.animation.KeyFrame;
import javafx.animation.KeyValue;
import javafx.animation.Timeline;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;
import javafx.util.Duration;
/**
 *
 * @author D
 */
public class ImageDisplayy extends Application {

    @Override
    public void start(Stage primaryStage) {
        Image image1 = new Image("file:lib/1.jpg");
        Image image2 = new Image("file:lib/2.jpg");
        Image image3 = new Image("file:lib/3.jpg");
        Image image4 = new Image("file:lib/4.jpg");
        ImageView imageView = new ImageView();
        Timeline timeline = new Timeline(

                new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image1)),
                new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image2)),  
                new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image3)),
                new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image4)),   
                new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), null))
                );
        timeline.play();
        StackPane root = new StackPane();
        root.getChildren().add(imageView);
        primaryStage.setScene(new Scene(root, 800, 600));
        primaryStage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }
}
jewelsea
  • 150,031
  • 14
  • 366
  • 406
dailyadd
  • 91
  • 10

2 Answers2

3

Here is an array based solution that cycles displaying a random choice of images. All images in the array will be displayed once in random order, then the array will be shuffled, allowing all images to be displayed again in a different random order.

import javafx.animation.*;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.image.*;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;
import javafx.util.Duration;

import java.util.*;
import java.util.stream.Collectors;

public class ImageDisplay extends Application {

    private List<Image> images;
    private Iterator<Image> imageIterator;

    @Override
    public void start(Stage stage) {
        images = Arrays.stream(IMAGE_LOCS)
                .map(Image::new)
                .collect(Collectors.toList());
        Collections.shuffle(images);
        imageIterator = images.iterator();
        ImageView imageView = new ImageView();

        Timeline timeline = new Timeline(
                new KeyFrame(
                        Duration.ZERO,
                        e -> {
                            imageView.setImage(imageIterator.next());
                            System.out.println(
                                 "Displaying " + imageView.getImage().impl_getUrl()
                            );
                        }
                ),
                new KeyFrame(Duration.seconds(1))
        );
        timeline.setCycleCount(images.size());
        timeline.setOnFinished(event -> {
            Collections.shuffle(images);
            imageIterator = images.iterator();
            timeline.playFromStart();
        });
        timeline.play();

        StackPane layout = new StackPane(imageView);
        stage.setScene(new Scene(layout));
        stage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }

    // image license: linkware - backlink to http://www.fasticon.com
    private static final String[] IMAGE_LOCS = {
        "http://icons.iconarchive.com/icons/fasticon/fish-toys/128/Blue-Fish-icon.png",
        "http://icons.iconarchive.com/icons/fasticon/fish-toys/128/Red-Fish-icon.png",
        "http://icons.iconarchive.com/icons/fasticon/fish-toys/128/Yellow-Fish-icon.png",
        "http://icons.iconarchive.com/icons/fasticon/fish-toys/128/Green-Fish-icon.png"
    };
}

Because we shuffle each time, it is possible for the last image displayed to be shuffled to be the first image on the next cycle (displaying it twice in a row). If you don't want the order to change between cycles, just remove the shuffle command executed when the time completes playing.

Note, for simplicity, the code uses impl_getUrl() to output a log of displayed image urls to the console - use of impl methods is not recommended in production code.

jewelsea
  • 150,031
  • 14
  • 366
  • 406
  • Basically, what i asked was to put my images in an array so I can shuffle them and this procedure should happen being based on my code. Not to give me an example which contributes only 10% in the solution of my problem because i can find those in google. – dailyadd Mar 08 '16 at 23:42
  • No, your question is to "display random images one by one", which is what this answer does. I do not believe this to be a 10% solution, it seems to solve the complete problem to me. Note that this solution does put images in an array list and shuffle them as part of solving the question. If I was mistaken in my understanding of the question or the answer is unacceptable for you, it's probably best just to ignore the answer. – jewelsea Mar 08 '16 at 23:53
  • yes u can see my code overthere that i have pasted if you didnt notice. You seem old here but u might have missed the point of this page. Let me tell you. stackoverflow.com is not about giving hints but its about giving solutions. – dailyadd Mar 09 '16 at 00:03
  • I'm not going to argue this anymore, but this is a solution and not a hint. – jewelsea Mar 09 '16 at 00:06
  • Sorry @dailyadd but this answer is more complete, since it answers to your both questions (see "1)" and "2)" above in your question). Additionally you didn't mention that the solution should be based on your code snippet. Moreover this is a Q&A site where the other users can/should benefit from. So please bear in mind that users having the same use case as yours can refer to this answer as an alternative approach to their app requirement. – Uluk Biy Mar 09 '16 at 06:28
2

In your stack pane it says for a duration of three seconds show all four images, you need them to show one by one. Change

 new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image1)),
            new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image2)),  
            new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image3)),
            new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image4)),   
            new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), null))
            );

to

     new KeyFrame(Duration.ZERO, new KeyValue(imageView.imageProperty(), image1)),
            new KeyFrame(Duration.seconds(1), new KeyValue(imageView.imageProperty(), image2)),  
            new KeyFrame(Duration.seconds(2), new KeyValue(imageView.imageProperty(), image3)),
            new KeyFrame(Duration.seconds(3), new KeyValue(imageView.imageProperty(), image4)),   
            new KeyFrame(Duration.seconds(4), new KeyValue(imageView.imageProperty(), null))
            );
Juice
  • 21
  • 4