Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-8228458

Window content is shrunk when run on 125% DPI

XMLWordPrintable

    • Icon: Bug Bug
    • Resolution: Unresolved
    • Icon: P4 P4
    • tbd
    • jfx11
    • javafx
    • x86_64
    • windows_10

      ADDITIONAL SYSTEM INFORMATION :
      Microsoft Windows [Version 10.0.17134.765]
      openjdk version "11.0.3" 2019-04-16
      OpenJDK Runtime Environment AdoptOpenJDK (build 11.0.3+7)
      OpenJDK 64-Bit Server VM AdoptOpenJDK (build 11.0.3+7, mixed mode)

      A DESCRIPTION OF THE PROBLEM :
      Window content is shrunk when run on 125% DPI. Due to size caching done in Region class, methods like prefHeight( -1 ) previously cached sizes, not snapped with actual output scale. This result in scroll pane's shrunk content issues.

      STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
      Preconditions:
      Two screens environment:
      - left side monitor 125% DPI,
      - right side monitor 100% DPI.
      Application starts on left monitor by default.


      Startup application from given source code and observe scrollbars visibility.

      EXPECTED VERSUS ACTUAL BEHAVIOR :
      EXPECTED -
      scrollbars should not be visible because scroll pane has fitToWidth and fitToHeight properties and they are not visible on 100% DPI screen
      ACTUAL -
      scroll bars are visible, content is shrunk

      ---------- BEGIN SOURCE ----------
      package com.example;

      import javafx.application.Application;
      import javafx.geometry.Insets;
      import javafx.geometry.Orientation;
      import javafx.geometry.Pos;
      import javafx.scene.Node;
      import javafx.scene.Parent;
      import javafx.scene.Scene;
      import javafx.scene.control.Button;
      import javafx.scene.control.Label;
      import javafx.scene.control.ScrollPane;
      import javafx.scene.layout.BorderPane;
      import javafx.scene.layout.FlowPane;
      import javafx.scene.layout.Region;
      import javafx.stage.Stage;

      public class HiDpiIssue2Sample
      {

          public static void main( String[] args )
          {
              System.err.println( Runtime.version().toString() );
              Application.launch( MainFx.class, args );
          }

          public static class MainFx extends Application
          {

              @Override
              public void start( final Stage primaryStage ) throws Exception
              {
                  final BorderPane borderPane = new BorderPane();
                  final BorderPane topContentPanel_layeredPane = new BorderPane();
                  topContentPanel_layeredPane.setId( "TopContentPanel.layeredPane" );
                  borderPane.setCenter( topContentPanel_layeredPane );

                  //region bottom
                  final BorderPane buttonBar = new BorderPane();
                  borderPane.setBottom( buttonBar );
                  final Button ok = new Button( "Fix issues" );
                  ok.setOnAction( event -> {
                      relayoutAll( primaryStage );
                      primaryStage.sizeToScene();
                  } );
                  final FlowPane flowPane = new FlowPane( Orientation.HORIZONTAL, 10, 10, ok );
                  flowPane.setAlignment( Pos.BASELINE_RIGHT );
                  flowPane.setPadding( new Insets( 10 ) );
                  buttonBar.setCenter( flowPane );

                  final BorderPane topContentPanel_container = new BorderPane();
                  topContentPanel_layeredPane.setCenter( topContentPanel_container );

                  final var sp = new ScrollPane();
                  sp.setFitToHeight( true );
                  sp.setFitToWidth( true );
                  sp.setPadding( Insets.EMPTY );
                  topContentPanel_container.setCenter( sp );
                  final BorderPane inputViewBp = new BorderPane();
                  inputViewBp.setPadding( new Insets( 0, 0, 5, 0 ) );
                  sp.setContent( inputViewBp );

                  // This part is causing issues, because it is not relayouted on output scale change
                  final BorderPane headerBp = new BorderPane();
                  headerBp.setLeft( createLabel( 133, 50 ) );
                  headerBp.setRight( createLabel( 351, 100 ) );
                  inputViewBp.setTop( headerBp );

                  final Scene aScene = new Scene( borderPane );
                  primaryStage.setScene( aScene );
                  primaryStage.sizeToScene();
                  primaryStage.show();
              }

              private void relayoutAll( final Stage aPrimaryStage )
              {
                  relayoutImpl( aPrimaryStage.getScene().getRoot() );
                  aPrimaryStage.sizeToScene();
              }

              private void relayoutImpl( final Parent aRoot )
              {
                  for( final Node node : aRoot.getChildrenUnmodifiable() )
                  {
                      if( node instanceof Parent )
                      {
                          relayoutImpl( ( (Parent)node ) );
                      }
                      if( node instanceof Region )
                      {
                          ( (Region)node ).requestLayout();
                      }
                  }
              }

              private static Label createLabel( final int width, final int height )
              {
                  return new Label( width + "/" + height + "px width/height" )
                  {

                      @Override
                      protected double computeMinWidth( final double height )
                      {
                          return snapSizeX( width );
                      }

                      @Override
                      protected double computeMinHeight( final double width )
                      {
                          return snapSizeY( height );
                      }

                      @Override
                      protected double computePrefHeight( final double width )
                      {
                          return snapSizeY( height );
                      }

                      @Override
                      protected double computePrefWidth( final double height )
                      {
                          return snapSizeX( width );
                      }
                  };
              }

          }
      }

      ---------- END SOURCE ----------

      CUSTOMER SUBMITTED WORKAROUND :
      Please press "Fix issues" button

      FREQUENCY : always


            arapte Ambarish Rapte
            webbuggrp Webbug Group
            Votes:
            0 Vote for this issue
            Watchers:
            3 Start watching this issue

              Created:
              Updated: