应用
我试图在我的JavaFX应用程序中创建幻灯片放映。为此,我创建了一个线程并处理该线程内的图像更改。我在线程中使用Thread.sleep(int)
来暂停图像之间的转换。
实施
我在Scene Builder中创建了应用程序,因此它在FXML中。 imageview以图像开始,我给了imageview一个id。以下是imageview所在的FXML的一部分:
<Tab>
<content>
<AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="376.0" prefWidth="981.0">
<children>
<ImageView fx:id="myImage" fitHeight="197.0" fitWidth="294.0" layoutX="20.0" layoutY="151.0" pickOnBounds="true" preserveRatio="true">
<image>
<Image url="@../Pictures/NevadaDesert.jpg" />
</image>
<effect>
<Glow />
</effect>
</ImageView>
我在我的Java代码中获取了imageview:
@FXML
private ImageView myImage;
然后我处理加载FXML后调用的新runnable线程内的所有图像更改:
@Override
public void start(Stage stage) throws Exception {
Parent root = FXMLLoader.load(getClass().getResource("MyResume.fxml"));
Scene scene = new Scene(root);
stage.setScene(scene);
stage.show();
(new Thread(new PictureRunnable())).start();
}
PictureRunnable的run方法如下所示:
public void run() {
try {
File file1 = new File("C:/Users/Kyle/Documents/NetBeansProjects/MyResume/src/Pictures/activities.jpg");
File file2 = new File("C:/Users/Kyle/Documents/NetBeansProjects/MyResume/src/Pictures/foodService2.png");
File file3 = new File("C:/Users/Kyle/Documents/NetBeansProjects/MyResume/src/Pictures/NevadaDesert.jpg");
Image a = new Image(file1.toURI().toURL().toExternalForm());
Image b = new Image(file2.toURI().toURL().toExternalForm());
Image c = new Image(file3.toURI().toURL().toExternalForm());
for(int i=0; true; i++) {
//Pause for 5 seconds
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
if( i%2 == 0 )
myImage.setImage(a);
else if( i%3 == 0 )
myImage.setImage(b);
else
myImage.setImage(c);
}
}
catch(MalformedURLException e) {
e.printStackTrace();
}
}
问题:
我在设置图片myImage.setImage(abc)
的行上得到NullPointerException。
我的代码中是否存在我如何更改图片的问题?
或者问题是线程,也许我无法打开新线程并对舞台进行更改?
答案 0 :(得分:0)
如果你想在imageView上设置一个图像,它必须在javafx线程上:使用你的线程或其他机制中的Platform.runLater()。
我刚注意到我的简单幻灯片帖子在其历史记录中有一些点击 - 抱歉它有一些错误,java8的最终版本改变了它在动画中处理空指针的方式。我修复了这些错误并更新了帖子。
(我注意到了)
答案 1 :(得分:0)
仅使用Java
package sample;
import java.util.ArrayList;
import java.util.List;
import javafx.application.*;
import javafx.event.EventHandler;
import javafx.geometry.Pos;
import javafx.geometry.Insets;
import javafx.scene.control.Label;
import javafx.stage.*;
import javafx.scene.*;
import javafx.scene.Cursor;
import java.lang.String;
import javafx.scene.layout.*;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.geometry.*;
import javafx.scene.paint.ImagePattern;
import javafx.scene.effect.DropShadow;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.GridPane;
import com.jfoenix.controls.JFXButton;
public class Main extends Application {
public static void main(String[] args) {
launch(args);
}
private List<String> list = new ArrayList<String>();
int j = 0;
JFXButton lbutton, rButton;
ImageView imageView;
@Override
public void start(Stage primaryStage) {
// images in src folder.
try {
list.add("/image/1.jpg");
list.add("/image/2.jpg");
list.add("/image/3.jpg");
list.add("/image/4.jpg");
list.add("/image/5.jpg");
list.add("/image/6.jpg");
list.add("/image/7.jpg");
list.add("/image/8.jpg");
GridPane root = new GridPane();
root.setAlignment(Pos.CENTER);
lbutton = new JFXButton("<");
rButton = new JFXButton(">");
Image images[] = new Image[list.size()];
for (int i = 0; i < list.size(); i++) {
images[i] = new Image(list.get(i));
}
imageView = new ImageView(images[j]);
imageView.setCursor(Cursor.CLOSED_HAND);
rButton.setOnAction(e -> {
System.out.print("hello");
j++;
if (j > list.size()-1)
{
j = list.size()-1;
imageView.setImage(images[j]);
}
else
{
imageView.setImage(images[j]);
}
});
lbutton.setOnAction(e -> {
System.out.print("hello");
j--;
if (j < 0)
{
j = 0;
imageView.setImage(images[j]);
}
else
{
imageView.setImage(images[j]);
}
});
imageView.setFitHeight(350);
//main controls
AnchorPane pane = new AnchorPane(imageView, rButton, lbutton);
AnchorPane.setTopAnchor(lbutton, 300.0);
AnchorPane.setLeftAnchor(lbutton, 210.0);
AnchorPane.setTopAnchor(rButton, 300.0);
AnchorPane.setRightAnchor(rButton, 210.0);
// Set the stage
Scene scene = new Scene(pane, 600, 600);
imageView.fitWidthProperty().bind(scene.widthProperty());
primaryStage.setScene(scene);
primaryStage.setResizable(false);
primaryStage.setTitle("Sample");
primaryStage.show();
} catch (Exception e) {
e.printStackTrace();
}
}
}