JavaFX: поддержка разных разрешений - PullRequest
2 голосов
/ 01 октября 2019

Я пытаюсь понять, как поддерживать различные разрешения в JavaFX. Я ищу своего рода руководство о том, как этого добиться.

Я хочу создать приложение, для которого требуется минимальное разрешение, например, 1280 × 720. И я хочу, чтобы мои приложения выглядели хорошо и на любом более высоком разрешении (например, 1920 × 1080). Кроме того, приложение должно хорошо выглядеть при различных значениях DPI. Как я могу это сделать?

Позволяет установить минимальные требования JDK 11.0.2+ и JavaFX 11.0.2+, чтобы быть более конкретными.

Что я (кажется) понимаю сейчас:

  1. Необходимо установить минимальную ширину и высоту сцены.
  2. Не могу беспокоиться о поддержке DPI, так как похоже, что она реализована .

Что я до сих пор не понимаю:

  1. Как установить размеры элементов, отступов и т. Д.
    • Следует ли устанавливать значения в пикселях для минимумаподдерживаемое разрешение, а затем умножить их на коэффициент в соответствии с текущим разрешением?
    • Или я должен увеличить размер в процентах от ширины / высоты экрана?
    • Или я должен сделатьвсе это совсем по-другому?
  2. Должен ли я избегать каких-либо элементов управления / макетов?

Надеюсь, я был достаточно ясен.

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

Заранее благодарю за помощь.

Ответы [ 4 ]

5 голосов
/ 01 октября 2019

Хорошо, что это очень хороший вопрос, так как JavaFX не поддерживает адаптивное разрешение на лету, поэтому вы сделаете это самостоятельно

  1. Сначала попробуйте положиться на различные макеты для распространения пользовательского интерфейса. компоненты в соответствии с вычисленным местоположением, шириной и высотой, как в BorderPane, которые имеют 5 секций, чтобы легко настроить компоненты
  2. После выполнения первого шага у вас все еще есть некоторые компоненты, которые требуют пользовательской модификации с точки зрения шириныи height задайте желаемую ширину и высоту и умножьте эти значения на коэффициент, который вы можете рассчитать с помощью этого соотношения. Получив разрешение экрана, при следующем запуске приложения на другом экране с другим разрешением оно получит другую ширину или высоту дляэтот компонент
  3. Вы также можете предоставить свой файл FXML для каждого поддерживаемого разрешения вашим приложением, чтобы вы могли запустить соответствующий дизайн, а также для случаев с альбомной и портретной ориентацией
  4. Конечно, вы можете посмотретьдля третьей стороны library, который может предоставить отзывчивый компонент, такой как BootstrapFX, который аналогичен таковому для веб-дизайна, а также есть ResponsiveFX, но я не пробовал их раньше

Надеюсь, мой ответ поможет вам илипоставить вас на правильный путь, чтобы сделать несколько крутых приложений

3 голосов
/ 02 октября 2019

Каждый компонент (кнопка, текстовое поле и т. Д.) Рассчитывает свой собственный предпочтительный размер на основе разрешения, размеров шрифта, выбранной пользователем темы и т. Д. Все, что вам нужно, это убедиться, что вы не мешаете этому. Поэтому не устанавливайте никаких размеров.

Когда вы размещаете компоненты в макете (любой подкласс Pane, кроме AnchorPane), макет будет стараться соответствовать предпочтительному размеру каждого дочернего элемента. В большинстве приложений вам никогда не придется явно указывать одну ширину или высоту.

0 голосов
/ 11 октября 2019

Я сейчас создаю настольное приложение с почти такими же ограничениями. Я столкнулся с этим вопросом месяц назад, но позже узнал, что мне ничего не нужно делать. Pane автоматически изменит размеры внутренних элементов в соответствии с разрешением экрана. Как правильно упомянуто VGR, Anchorpane не будет делать это изменение размера дочерних элементов, и мне нужно заменить всю Anchorpane на Pane.

На одном из тестовых компьютеров возникла другая проблема, из-за которой сцена отображалась слишком большой длядисплей с низким разрешением и не менялся автоматически. Чтобы решить эту проблему, я установил разрешение экрана на другое значение, а затем переключил его обратно на исходное значение, и оно было исправлено.

Вам нужно установить минимальный и (или) максимальный размер сцены и (возможно) установить его неизменяемым, и это должно работать.

0 голосов
/ 11 октября 2019

Привет, попробуйте использовать разные fxml-файлы:

MaximizedPane.fxml: -> см. PrefWidth / perfHight

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.layout.StackPane?>
<?import javafx.scene.control.Label?>
<?import javafx.stage.Screen?>

<StackPane xmlns:fx="http://javafx.com/fxml/1"
           prefWidth="${screen.visualBounds.width}" 
           prefHeight="${screen.visualBounds.height}" >
    <fx:define>
        <Screen fx:factory="getPrimary" fx:id="screen"/>
    </fx:define>
    <Label text="A maximized pane"/>    
</StackPane>

Загрузка fxml-файлов динамически:

import java.io.IOException;

import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.stage.Stage;

public class MaximizedFXMLPane extends Application {

    @Override
    public void start(Stage primaryStage) throws IOException {
        Scene scene = new Scene(FXMLLoader.load(getClass().getResource("MaximizedPane.fxml")));
        primaryStage.setScene(scene);
        primaryStage.show();
    }

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

Пример из моего архива git: https://github.com/src-mgra/my-calendar/blob/master/MyCalendar/src/sample/Main.java


Другой способ - использовать сцены:

import java.awt.Dimension;

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.layout.AnchorPane;
import javafx.stage.Stage;

public class ScreenResolutionDemo extends Application {


    @Override
    public void start(Stage primaryStage) throws Exception {
        Dimension screenSize = java.awt.Toolkit.getDefaultToolkit().getScreenSize();
        double width = screenSize.getWidth() / 3;
        double height = screenSize.getHeight() / 2;

        try {
            **primaryStage.setScene**(new Scene(new AnchorPane(), *width*, **height**));
            primaryStage.show();
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

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

}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...