web-dev-qa-db-fra.com

JavaFX tableview redimensionner pour s'adapter à la fenêtre

Je suis juste en train d'essayer JavaFX et je m'y fraye un chemin parce que c'est supposé être le futur. J'essaie de créer un tableau avec 4 colonnes. Les colonnes ET LA TABLE doivent être redimensionnées pour remplir le volet parent. Je ne peux pas pour la vie de moi faire fonctionner cela. J'essaie depuis plus de 4 heures maintenant et la table ne redimensionne pas.

Voici mon fichier FXML.

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

<?import Java.lang.*?>
<?import Java.util.*?>
<?import javafx.scene.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>
<?import Java.net.*?>
<?import javafx.geometry.*?>
<?import javafx.geometry.Insets?>
<?import javafx.scene.control.*?>
<?import javafx.scene.control.cell.*?>
<?import javafx.scene.layout.*?>
<?import javafx.scene.text.*?>
<?import javafx.collections.*?>
<?import t.cubed.fxml.*?>


<BorderPane styleClass="root" xmlns:fx="http://javafx.com/fxml/1" xmlns="http://javafx.com/javafx/8" fx:controller="t.cubed.fxml.FXMLDocumentController">
    <top>
        <MenuBar fx:id="menuBar" styleClass="menu-bar">
        <menus>
            <Menu text="File">
                <items>
                    <MenuItem onAction="#handleOpenAction" text="Open" />
                    <MenuItem onAction="#handleExitAction" text="Exit" />
                </items>
            </Menu>
            <Menu text="Edit">
                <items>
                    <MenuItem onAction="#handleWeightAction" text="Edit Weights" />  
                    <MenuItem onAction="#handleFilterAction" text="Edit Filters" />
                    <MenuItem onAction="#handleOptionsAction" text="Options" />
                </items>
            </Menu>
        </menus>
    </MenuBar>
    </top>
    <center>
        <GridPane>
               <!--
               <padding>
                   <Insets bottom="10.0" left="10.0" right="10.0" top="10.0"/> 
               </padding>
               -->
               <TableView fx:id="testTable" GridPane.columnIndex="0" GridPane.rowIndex="0" GridPane.columnSpan="1">
                   <columnResizePolicy>
                       <TableView fx:constant="CONSTRAINED_RESIZE_POLICY" />
                   </columnResizePolicy>
                   <columns>
                       <TableColumn text="TEST NUMBER">
                       <cellValueFactory>
                           <PropertyValueFactory property="testNumber" />
                       </cellValueFactory>
                       </TableColumn>
                       <TableColumn text="TEST NAME">
                           <cellValueFactory>
                           <PropertyValueFactory property="testName" />
                       </cellValueFactory>
                       </TableColumn>
                       <TableColumn text="TEST TIME(ms)">
                           <cellValueFactory>
                           <PropertyValueFactory property="testTime" />
                       </cellValueFactory>
                       </TableColumn>
                       <TableColumn text="BEST MATCH">
                           <cellValueFactory>
                           <PropertyValueFactory property="bestMatch" />
                       </cellValueFactory>
                       </TableColumn>
                   </columns>
                   <items>
                    <!--
                    <FXCollections fx:factory="observableArrayList">
                        <TestTableModel testNumber="100" testName="Test1234" testTime="0.34" bestMatch="99"/>
                    </FXCollections>
                    -->
                </items>
               </TableView>
        </GridPane>
    </center>
<stylesheets>
    <URL value="@t-cubed.css" />
</stylesheets>
</BorderPane>
12
bzanchi

Fonctionnement de la mise en page redimensionnable

La taille des éléments redimensionnables dans JavaFX est gérée par les gestionnaires de disposition dans lesquels les éléments sont placés.

Ce que vous devez faire

Pour votre problème particulier, vous devez définir les contraintes de dimensionnement de GridPane pour gérer le TableView que vous avez placé dans la grille.

Voir les contraintes GridPane.hgrow Et GridPane.vgrow Que j'ai ajoutées sur TableView:

<TableView fx:id="testTable" 
           GridPane.columnIndex="0" 
           GridPane.columnSpan="1" 
           GridPane.hgrow="ALWAYS" 
           GridPane.vgrow="ALWAYS"
           GridPane.rowIndex="0">

FXML reflète simplement l'API Java, vous pouvez donc également faire la même chose dans Java source également; c'est-à-dire GridPane.setHGrow(node, priority) Cependant, si vous utilisez FXML pour votre mise en page, il est recommandé de définir les contraintes de mise en page dans FXML.

grid

Échantillon refactorisé

J'ai chargé votre FXML dans Scene Builder 2 et défini les contraintes appropriées et il semble se redimensionner automatiquement correctement lorsque j'utilise la fonctionnalité de prévisualisation de Scene Builder.

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

<?import Java.lang.*?>
<?import Java.util.*?>
<?import javafx.scene.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>
<?import Java.net.*?>
<?import javafx.geometry.*?>
<?import javafx.geometry.Insets?>
<?import javafx.scene.control.*?>
<?import javafx.scene.control.cell.*?>
<?import javafx.scene.layout.*?>
<?import javafx.scene.text.*?>
<?import javafx.collections.*?>
<?import t.cubed.fxml.*?>

<BorderPane styleClass="root" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="t.cubed.fxml.FXMLDocumentController">
  <top>
    <MenuBar fx:id="menuBar" styleClass="menu-bar">
      <menus>
        <Menu text="File">
          <items>
            <MenuItem onAction="#handleOpenAction" text="Open" />
            <MenuItem onAction="#handleExitAction" text="Exit" />
          </items>
        </Menu>
        <Menu text="Edit">
          <items>
            <MenuItem onAction="#handleWeightAction" text="Edit Weights" />
            <MenuItem onAction="#handleFilterAction" text="Edit Filters" />
            <MenuItem onAction="#handleOptionsAction" text="Options" />
          </items>
        </Menu>
      </menus>
    </MenuBar>
  </top>
  <center>
    <GridPane>
       <children>
         <!--
         <padding>
             <Insets bottom="10.0" left="10.0" right="10.0" top="10.0"/>
         </padding>
         -->
         <TableView fx:id="testTable" GridPane.columnIndex="0" GridPane.columnSpan="1" GridPane.hgrow="ALWAYS" GridPane.rowIndex="0" GridPane.vgrow="ALWAYS">
           <columnResizePolicy>
             <TableView fx:constant="CONSTRAINED_RESIZE_POLICY" />
           </columnResizePolicy>
           <columns>
             <TableColumn text="TEST NUMBER">
               <cellValueFactory>
                 <PropertyValueFactory property="testNumber" />
               </cellValueFactory>
             </TableColumn>
             <TableColumn text="TEST NAME">
               <cellValueFactory>
                 <PropertyValueFactory property="testName" />
               </cellValueFactory>
             </TableColumn>
             <TableColumn text="TEST TIME(ms)">
               <cellValueFactory>
                 <PropertyValueFactory property="testTime" />
               </cellValueFactory>
             </TableColumn>
             <TableColumn text="BEST MATCH">
               <cellValueFactory>
                 <PropertyValueFactory property="bestMatch" />
               </cellValueFactory>
             </TableColumn>
           </columns>
           <items>
          <!--
          <FXCollections fx:factory="observableArrayList">
              <TestTableModel testNumber="100" testName="Test1234" testTime="0.34" bestMatch="99"/>
          </FXCollections>
          -->
        </items>
         </TableView>
       </children>
         <columnConstraints>
            <ColumnConstraints />
         </columnConstraints>
         <rowConstraints>
            <RowConstraints />
         </rowConstraints>
    </GridPane>
  </center>
  <stylesheets>
    <URL value="@t-cubed.css" />
  </stylesheets>
</BorderPane>

Quelques conseils

Vous placez le TableView à l'intérieur d'un GridPane. L'utilisation d'un GridPane dans votre cas est un peu étrange car le GridPane vous place seulement un nœud dans le GridPane. Placer le TableView directement au centre de votre BorderPane ou utiliser un parent de disposition plus simple tel qu'un StackPane aurait très bien fonctionné. Mais peut-être que ce n'est qu'une version réduite d'une interface utilisateur plus complexe, c'est peut-être pourquoi vous avez utilisé un GridPane.

Lectures complémentaires

Si vous avez le temps, lisez la mise en page dans JavaFX dans le Node , Pane , Group and GridPane javadoc and essayez ce petit démo des limites de mise en page aussi.

Questions supplémentaires pour les commentaires

mentionner qu'un StackPane fonctionnerait, mais StackPanes ne semble pas avoir Hgrow et Vgrow?

StackPanes n'a pas besoin de contraintes Hgrow ou Vgrow. Ces contraintes définissent Priorités , qui sont définies comme:

Énumération utilisée pour déterminer la priorité de croissance (ou de rétrécissement) d'une zone de disposition d'un nœud donné lorsque sa région dispose de plus (ou moins) d'espace disponible et que plusieurs nœuds sont en concurrence pour cet espace.

Avec un StackPane, tous les enfants sont superposés, ils ne rivalisent pas pour l'espace, donc ces paramètres de priorité de croissance pour les nœuds enfants ne sont pas applicables.

22
jewelsea

Après quelques devoirs, nous avons trouvé des informations qualificatives sur les conteneurs FXML. À peu près pour la même raison donnée ci-dessus par @ user3403469. Dans le Scene Builder, il y a une longue liste de ' conteneurs'. À mon humble avis, seuls ces 9 éléments et volet se qualifient comme conteneur de disposition, car ils héritent de

< volet > ... parent pour tous classes de volet . Alors que les deux, Pane et Control héritent de Region, seules les classes enfants Pane ont des propriétés de mise en page.

* <AnchorPane>
* <BorderPane>
* <FlowPane>
* <GridPane>
* <StackPane>
* <TextFlow>
* <TilePane>
* <HBox>
* <VBox> 

Vous pouvez considérer que les classes enfants Control héritent plus ou moins des événements et des actions. La mise en page comme si les choses devaient provenir de la région d'encapsulation, et la seule chose avec des éléments de mise en page disponibles pour envelopper un "contrôle" est un "volet".

Ces éléments FXML seraient les "gestionnaires de mise en page" sur mesure décrits dans la réponse de @ jewelsea et ailleurs.

Je suppose que les conteneurs "Control" sont toujours des conteneurs en FXML. Il semble qu'ils doivent être "à l'intérieur" d'un panneau pour faire le bien ;-)

Corrections et commentaires bienvenus.

lié:

0
will