2016-10-06 6 views
1

Я нашел способ открыть ссылку на браузер по умолчанию с помощью HostServices.Открытое внешнее приложение из JavaFX

getHostServices().showDocument("http://www.google.com"); 
  • Есть ли способ, чтобы открыть СМИ в медиа-плеер по умолчанию?
  • Есть ли способ для запуска определенного файла или Заявление?
+1

Всякий раз, когда я пробовал это с URL-адресом (включая файл: // URL), который сопоставляется с определенным документом, он открывает документ по умолчанию для этого типа документа. Не работает ли это так же для СМИ и т. Д.? Вероятно, лучше избегать смешивания AWT и JavaFX (что принято в этом случае), если вы можете это сделать разумно. –

+0

Да, если он содержит 'файл: //' Я столкнулся с 'IllegalArgumentException'. Я не заметил, прежде чем читать ваши комментарии, что это от AWT. Я был бы очень признателен, если бы вы поделились своим ответом, как я могу это сделать с помощью JavaFX, который также обогатит мои знания и опыт. –

+0

Ну, я просто проверил снова, и он работает с файлами: // URL, но не будет работать с другими типами документов с http: URL (он открывает браузер, который загружает файл). Я добавлю ответ, но если вы хотите открыть носитель, который загружается с веб-сервера, я не уверен, что есть способ сделать это. –

ответ

2

Если вы хотите, чтобы либо открыть URL, который имеет http: схему в браузере или открыть файл с помощью приложения по умолчанию для этого типа файла, метод HostServices.showDocument(...) вы ссылка обеспечивает «чистый JavaFX» способ сделать это. Обратите внимание: вы не можете использовать это (насколько я могу судить), чтобы загрузить файл с веб-сервера и открыть его с помощью приложения по умолчанию.

Чтобы открыть файл с использованием приложения по умолчанию, вы должны преобразовать файл в строковое представление URL-адреса file:. Вот простой пример:

import java.io.File; 

import javafx.application.Application; 
import javafx.event.ActionEvent; 
import javafx.event.EventHandler; 
import javafx.geometry.Insets; 
import javafx.scene.Scene; 
import javafx.scene.control.Button; 
import javafx.scene.control.Label; 
import javafx.scene.control.TextField; 
import javafx.scene.layout.HBox; 
import javafx.scene.layout.VBox; 
import javafx.stage.FileChooser; 
import javafx.stage.Stage; 

public class OpenResourceNatively extends Application { 

    @Override 
    public void start(Stage primaryStage) { 
     TextField textField = new TextField("http://stackoverflow.com/questions/39898704"); 
     Button openURLButton = new Button("Open URL"); 
     EventHandler<ActionEvent> handler = e -> open(textField.getText()); 
     textField.setOnAction(handler); 
     openURLButton.setOnAction(handler); 

     FileChooser fileChooser = new FileChooser(); 
     Button openFileButton = new Button("Open File..."); 
     openFileButton.setOnAction(e -> { 
      File file = fileChooser.showOpenDialog(primaryStage); 
      if (file != null) { 
       open(file.toURI().toString()); 
      } 
     }); 

     VBox root = new VBox(5, 
       new HBox(new Label("URL:"), textField, openURLButton), 
       new HBox(openFileButton) 
     ); 

     root.setPadding(new Insets(20)); 
     primaryStage.setScene(new Scene(root)); 
     primaryStage.show(); 
    } 

    private void open(String resource) { 
     getHostServices().showDocument(resource); 
    } 

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

Хорошо, теперь я понял. Метод HostServices.showDocument (...) 'может не только открыть только браузер, но и открыть любой файл с установленными приложениями по умолчанию. Большое спасибо :) –

+0

В AWT появился способ открыть каталог в System Explorer. В JavaFX как открыть каталог в System Explorer? –

+0

@ RanaDepto То же самое работает, не так ли? Если 'file' ссылается на каталог, getHostServices(). ShowDocument (file.toURI(). ToString())' откроет каталог в обозревателе системных файлов. –

4

Вообще говоря, вы можете использовать Desktop#open(file) открыть файл нативно в следующем:

final Desktop desktop = Desktop.isDesktopSupported() ? Desktop.getDesktop() : null; 
if (desktop != null && desktop.isSupported(Desktop.Action.OPEN)) { 
    desktop.open(file); 
} else { 
    throw new UnsupportedOperationException("Open action not supported"); 
} 

запускает соответствующее приложение, чтобы открыть файл. Если указанный файл является каталогом, диспетчер файлов текущей платформы - , запущенный для его открытия.

Более конкретно, в случае браузера вы можете использовать непосредственно Desktop#browse(uri), в следующем:

final Desktop desktop = Desktop.isDesktopSupported() ? Desktop.getDesktop() : null; 
if (desktop != null && desktop.isSupported(Desktop.Action.BROWSE)) { 
    desktop.browse(uri); 
} else { 
    throw new UnsupportedOperationException("Browse action not supported"); 
} 

запускает браузер по умолчанию для отображения URI. Если браузер по умолчанию не может обрабатывать указанные URI, приложение, зарегистрированное для обработки URIs указанного типа, вызывается. Заявка определяется по протоколу и адресу URI, как определено классом URI. Если вызывающий поток не имеет необходимых разрешений , и это вызвано из апплета, используется AppletContext.showDocument(). Аналогично, если вызывающий код не имеет необходимых разрешений, и он вызывается из приложения Java Web Started, используется BasicService.showDocument().

+1

Большое спасибо. Этот ответ полностью отвечает всем моим требованиям :) –

0

Только решение с java.awt.Desktop работал для меня, чтобы открыть файл с JavaFX.

Однако сначала мое приложение застряло, и мне пришлось выяснить, что необходимо позвонить Desktop#open(File file) из новой темы. Вызов метода из текущего потока или потока приложений JavaFX Platform#runLater(Runnable runnable) привел к тому, что приложение зависало бесконечно без исключения исключения.

Это небольшой пример JavaFX приложения с рабочего открытия файла решения:

import java.awt.Desktop; 
import java.io.File; 
import java.io.IOException; 

import javafx.application.Application; 
import javafx.concurrent.Task; 
import javafx.scene.Scene; 
import javafx.scene.control.Button; 
import javafx.stage.FileChooser; 
import javafx.stage.Stage; 

public class FileOpenDemo extends Application { 

    @Override 
    public void start(Stage primaryStage) { 
     final Button button = new Button("Open file"); 

     button.setOnAction(event -> { 
      final FileChooser fileChooser = new FileChooser(); 
      final File file = fileChooser.showOpenDialog(primaryStage.getOwner()); 

      if (file == null) 
       return; 

      System.out.println("File selected: " + file.getName()); 

      if (!Desktop.isDesktopSupported()) { 
       System.out.println("Desktop not supported"); 
       return; 
      } 

      if (!Desktop.getDesktop().isSupported(Desktop.Action.OPEN)) { 
       System.out.println("File opening not supported"); 
       return; 
      } 

      final Task<Void> task = new Task<Void>() { 
       @Override 
       public Void call() throws Exception { 
        try { 
         Desktop.getDesktop().open(file); 
        } catch (IOException e) { 
         System.err.println(e.toString()); 
        } 
        return null; 
       } 
      }; 

      final Thread thread = new Thread(task); 
      thread.setDaemon(true); 
      thread.start(); 
     }); 

     primaryStage.setScene(new Scene(button)); 
     primaryStage.show(); 
    } 

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

Другой Предлагаемое решение с javafx.application.HostServices не работает. Я использую OpenJFX 8u141 на Ubuntu 17.10 amd64, и я получил следующее исключение при вызове HostServices#showDocument(String uri):

java.lang.ClassNotFoundException: com.sun.deploy.uitoolkit.impl.fx.HostServicesFactory

Очевидно, что JavaFX HostServices еще не реализована должным образом на всех платформах. По этой теме смотрите также: https://github.com/Qabel/qabel-desktop/issues/420

Смежные вопросы