J'ai des problèmes pour fermer mon application javaFX, lorsque je clique sur le bouton de fermeture de mon étape, mon application disparaît mais si je le cherche dans mon gestionnaire de tâches, mon application est toujours là sans fermer .. J'ai essayé d'utiliser ce code ci-dessous pour le forcer à fermer le thread principal et tous les threads des enfants, mais le problème persiste.
primaryStage.setOnCloseRequest(new EventHandler<WindowEvent>() {
@Override
public void handle(WindowEvent t) {
Platform.exit();
}
});
Votre application génère-t-elle des threads enfants? Si c'est le cas, vous êtes-vous assuré de les terminer (en supposant qu'il ne s'agisse pas de threads démon)?
Si votre application génère des threads non-démons, ils (et donc votre application) continueront à vivre jusqu'à ce que vous interrompiez le processus.
Le seul moyen était d'appeler System.exit (0);
primaryStage.setOnCloseRequest(new EventHandler<WindowEvent>() {
@Override
public void handle(WindowEvent t) {
Platform.exit();
System.exit(0);
}
});
[MODIFIÉ]
System.exit masquera simplement votre application. Si vous ouvrez la tâche du responsable de SO, votre application sera là. La bonne façon est de vérifier vos threads, un par un et de tout fermer avant de fermer l’application.
public void start(Stage stage) {
Platform.setImplicitExit(true);
stage.setOnCloseRequest((ae) -> {
Platform.exit();
System.exit(0);
});
}
Je rencontrais actuellement ce problème lorsque j'utilisais un ThreadExecutor dans le contrôleur . L'application ne se ferme pas si ThreadExecutor n'est pas arrêté . Voir ici: comment lorsque vous quittez une application
Comme il peut être problématique de reconnaître une sortie d’application dans le contrôleur, vous pouvez obtenir une référence au contrôleur à partir de votre classe d’application comme suit (en utilisant l’exemple d’application d’Eclipse):
public class Main extends Application {
private SampleController controller;
@Override
public void start(Stage primaryStage) {
try {
FXMLLoader loader = new FXMLLoader(getClass().getResource("MyFXML.fxml"));
BorderPane root = (BorderPane)loader.load(getClass().getResource("Sample.fxml").openStream());
Scene scene = new Scene(root,400,400);
scene.getStylesheets().add(getClass().getResource("application.css").toExternalForm());
primaryStage.setScene(scene);
primaryStage.show();
controller = loader.<SampleController>getController();
}
catch(Exception e)
{
e.printStackTrace();
}
}
Votre application annule la méthode d'arrêt, où vous pouvez appeler une méthode de ménage du contrôleur (j'utilise une méthode appelée startHousekeeping):
/**
* This method is called when the application should stop,
* and provides a convenient place to prepare for application exit and destroy resources.
*/
@Override
public void stop() throws Exception
{
super.stop();
if(controller != null)
{
controller.startHousekeeping();
}
Platform.exit();
System.exit(0);
}
J'ai pu résoudre ce problème en appelant com.Sun.javafx.application.tkExit()
. Vous pouvez lire plus dans mon autre réponse ici: https://stackoverflow.com/a/22997736/1768232 (ces deux questions sont vraiment des doubles).
Juste une note: Essayez de vérifier si vous utilisez
Platform.setImplicitExit(false);
Avait un problème similaire et débordant mes tâches. La ligne ci-dessus ne fera pas fermer la scène, elle la cachera.
Pour imiter en appuyant sur 'x' on peut faire:
stage.fireEvent(new WindowEvent(stage, WindowEvent.WINDOW_CLOSE_REQUEST))
Vous pouvez fermer votre application en cliquant sur le bouton fermer Button, avec du code.
stage.setOnCloseRequest(
event -> closeMyApp()
);
private void closeMyApp()
{
try
{
Stage stage = (Stage) closeButton.getScene().getWindow();
stage.close();
}
catch(Exception ee)
{
ex.printStackTrace();
}
}
// where closeButton is button having similar controller class initialization.
@FXML
private Button closeButton;