我正在使用javafx构建桌面应用程序,我使用ftp下载大约500 MB的文件。我需要在下载过程中显示%栏的进度条。我还需要提供取消正在进行的下载过程的选项。 单击下载按钮时我想要进度条,它显示下载进度,如果我取消下载应停止。
这是我下载文件的代码。
downloadButton.setOnMouseClicked(new EventHandler<MouseEvent>() {
@Override
public void handle(MouseEvent event) {
// TODO Auto-generated method stub
FTPClient ftpClient = new FTPConnection().makeConnection();
try {
ftpClient.setFileType(FTP.BINARY_FILE_TYPE);
success = ftpClient.changeWorkingDirectory(PATH + preset + "/" + file_to_download + offset);
System.out.println("Download Path:-" + PATH + preset + "/" + file_to_download + offset);
if (!success) {
System.out.println("Could not changed the directory to RIBS");
return;
} else {
System.out.println("Directory changed to RIBS");
}
FTPFile[] files = ftpClient.listFiles();
for (FTPFile file : files) {
if (file.getName().contains(".zip")) {
dfile = file.getName();
}
}
DirectoryChooser dirChooser = new DirectoryChooser();
primaryStage = (Stage) tableView.getScene().getWindow();
primaryStage.setTitle("Background Processes");
File chosenDir = dirChooser.showDialog(primaryStage);
System.out.println(chosenDir.getAbsolutePath());
Task task = new Task<Void>() {
@Override
public Void call() throws IOException {
try {
output = new FileOutputStream(chosenDir.getAbsolutePath() + "/" + dfile);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
ftpClient.sendNoOp();
ftpClient.setConnectTimeout(1000);
int filesize = 0;
if (ftpClient.retrieveFile(dfile, output) == true) {
downloadButton.setDisable(true);
dfile.length();
System.out.println("FILE:LENGTH" + dfile.length());
}
// updateProgress(outByte, inputByte);
return null;
}
};
final Stage dialog = new Stage();
dialog.initModality(Modality.WINDOW_MODAL);
dialog.initOwner(primaryStage);
final ProgressBar progressBar = new ProgressBar(0);
final Button cancelButton = new Button("Cancel");
cancelButton.setOnAction(new EventHandler<ActionEvent>() {
public void handle(ActionEvent event) {
copyWorker.cancel(true);
progressBar.progressProperty().unbind();
progressBar.setProgress(0);
System.out.println("cancelled.");
dialog.close();
}
});
final Button closeButton = new Button("Close");
closeButton.setOnAction(new EventHandler<ActionEvent>() {
public void handle(ActionEvent event) {
progressBar.progressProperty().unbind();
progressBar.setProgress(0);
dialog.close();
}
});
cancelButton.setDisable(false);
closeButton.setDisable(true);
VBox dialogVbox = new VBox();
VBox.setMargin(progressBar, new Insets(10, 10, 10, 10));
VBox.setMargin(cancelButton, new Insets(10, 10, 10, 10));
dialogVbox.setAlignment(Pos.CENTER);
HBox hBox = new HBox();
hBox.setAlignment(Pos.CENTER);
hBox.getChildren().addAll(cancelButton, closeButton);
dialogVbox.getChildren().addAll(progressBar, hBox);
Scene dialogScene = new Scene(dialogVbox, 160, 100);
dialog.initStyle(StageStyle.UNDECORATED);
dialog.setResizable(false);
dialog.setScene(dialogScene);
dialog.setOnShown(e -> {
progressBar.setProgress(0);
copyWorker = createWorker();
progressBar.progressProperty().unbind();
progressBar.progressProperty().bind(copyWorker.progressProperty());
copyWorker.messageProperty().addListener(new ChangeListener<String>() {
public void changed(ObservableValue<? extends String> observable, String oldValue, String newValue) {
System.out.println(newValue);
}
});
// TODO: handle succeeded & failed depending on your needs
EventHandler doneHandler = new EventHandler() {
@Override
public void handle(Event event) {
cancelButton.setDisable(true);
closeButton.setDisable(false);
}
};
copyWorker.setOnSucceeded(doneHandler);
copyWorker.setOnFailed(doneHandler);
new Thread(copyWorker).start();
});
dialog.show();
// end
new Thread(task).start();
if (output != null) {
output.close();
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
参考我的问题How to show a progress bar while downloading in javafx 我已将下载代码移到另一个后台线程中,但我无法弄清楚如何显示进度条。
答案 0 :(得分:2)
示例代码已经为您提供了进度条。它就像任何其他节点一样。你可以把它放在任何你想要的地方。以下是将其放入对话框的示例:
import javafx.application.Application;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.concurrent.Task;
import javafx.event.ActionEvent;
import javafx.event.Event;
import javafx.event.EventHandler;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.ProgressBar;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.HBox;
import javafx.scene.layout.VBox;
import javafx.scene.paint.Color;
import javafx.stage.Modality;
import javafx.stage.Stage;
import javafx.stage.StageStyle;
// source: http://www.java2s.com/Code/Java/JavaFX/ProgressBarandBackgroundProcesses.htm
// http://stackoverflow.com/questions/22166610/how-to-create-a-popup-windows-in-javafx
public class ProgressTask extends Application {
Task copyWorker;
public static void main(String[] args) {
Application.launch(args);
}
@Override
public void start(Stage primaryStage) {
primaryStage.setTitle("Background Processes");
Group root = new Group();
Scene scene = new Scene(root, 330, 120, Color.WHITE);
BorderPane mainPane = new BorderPane();
root.getChildren().add(mainPane);
final Label label = new Label("Files Transfer:");
final HBox hb = new HBox();
hb.setSpacing(5);
hb.setAlignment(Pos.CENTER);
hb.getChildren().addAll(label);
mainPane.setTop(hb);
final Button startButton = new Button("Start");
startButton.setText("Start");
startButton.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
final Stage dialog = new Stage();
dialog.initModality(Modality.WINDOW_MODAL);
dialog.initOwner(primaryStage);
final ProgressBar progressBar = new ProgressBar(0);
final Button cancelButton = new Button("Cancel");
cancelButton.setOnAction(new EventHandler<ActionEvent>() {
public void handle(ActionEvent event) {
copyWorker.cancel(true);
progressBar.progressProperty().unbind();
progressBar.setProgress(0);
System.out.println("cancelled.");
dialog.close();
}
});
final Button closeButton = new Button("Close");
closeButton.setOnAction(new EventHandler<ActionEvent>() {
public void handle(ActionEvent event) {
progressBar.progressProperty().unbind();
progressBar.setProgress(0);
dialog.close();
}
});
cancelButton.setDisable(false);
closeButton.setDisable(true);
VBox dialogVbox = new VBox();
VBox.setMargin(progressBar, new Insets(10, 10, 10, 10));
VBox.setMargin(cancelButton, new Insets(10, 10, 10, 10));
dialogVbox.setAlignment(Pos.CENTER);
HBox hBox = new HBox();
hBox.setAlignment(Pos.CENTER);
hBox.getChildren().addAll(cancelButton, closeButton);
dialogVbox.getChildren().addAll(progressBar, hBox);
Scene dialogScene = new Scene(dialogVbox, 160, 100);
dialog.initStyle(StageStyle.UNDECORATED);
dialog.setResizable(false);
dialog.setScene(dialogScene);
dialog.setOnShown(e -> {
progressBar.setProgress(0);
copyWorker = createWorker();
progressBar.progressProperty().unbind();
progressBar.progressProperty().bind(copyWorker.progressProperty());
copyWorker.messageProperty().addListener(new ChangeListener<String>() {
public void changed(ObservableValue<? extends String> observable, String oldValue, String newValue) {
System.out.println(newValue);
}
});
// TODO: handle succeeded & failed depending on your needs
EventHandler doneHandler = new EventHandler() {
@Override
public void handle(Event event) {
cancelButton.setDisable(true);
closeButton.setDisable(false);
}
};
copyWorker.setOnSucceeded(doneHandler);
copyWorker.setOnFailed(doneHandler);
new Thread(copyWorker).start();
});
dialog.show();
}
});
final HBox hb2 = new HBox();
hb2.setSpacing(5);
hb2.setAlignment(Pos.CENTER);
hb2.getChildren().addAll(startButton);
mainPane.setBottom(hb2);
primaryStage.setScene(scene);
primaryStage.show();
}
public Task createWorker() {
return new Task() {
@Override
protected Object call() throws Exception {
for (int i = 0; i < 10; i++) {
Thread.sleep(1000);
updateMessage(((i + 1) * 1000) + " milliseconds");
updateProgress(i + 1, 10);
}
return true;
}
};
}
}