< prev index next >

modules/javafx.controls/src/main/java/javafx/scene/control/skin/TabPaneSkin.java

Print this page


   1 /*
   2  * Copyright (c) 2011, 2017, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any


 809                         if (tabHeaderSkin.isVisible() && (measureClosingTabs || ! tabHeaderSkin.isClosing)) {
 810                             width += tabHeaderSkin.prefWidth(height);
 811                         }
 812                     }
 813                     return snapSize(width) + snappedLeftInset() + snappedRightInset();
 814                 }
 815 
 816                 @Override protected double computePrefHeight(double width) {
 817                     double height = 0.0F;
 818                     for (Node child : getChildren()) {
 819                         TabHeaderSkin tabHeaderSkin = (TabHeaderSkin)child;
 820                         height = Math.max(height, tabHeaderSkin.prefHeight(width));
 821                     }
 822                     return snapSize(height) + snappedTopInset() + snappedBottomInset();
 823                 }
 824 
 825                 @Override protected void layoutChildren() {
 826                     if (tabsFit()) {
 827                         setScrollOffset(0.0);
 828                     } else {
 829                         if (!removeTab.isEmpty()) {
 830                             double offset = 0;
 831                             double w = tabHeaderArea.getWidth() - snapSize(controlButtons.prefWidth(-1)) - firstTabIndent() - SPACER;
 832                             Iterator<Node> i = getChildren().iterator();
 833                             while (i.hasNext()) {
 834                                 TabHeaderSkin tabHeader = (TabHeaderSkin)i.next();
 835                                 double tabHeaderPrefWidth = snapSize(tabHeader.prefWidth(-1));
 836                                 if (removeTab.contains(tabHeader)) {
 837                                     if (offset < w) {
 838                                         isSelectingTab = true;
 839                                     }
 840                                     i.remove();
 841                                     removeTab.remove(tabHeader);
 842                                     if (removeTab.isEmpty()) {
 843                                         break;
 844                                     }
 845                                 }
 846                                 offset += tabHeaderPrefWidth;
 847                             }
 848 //                        } else {
 849 //                            isSelectingTab = true;
 850                         }
 851                     }
 852 
 853                     if (isSelectingTab) {
 854                         ensureSelectedTabIsVisible();
 855                         isSelectingTab = false;
 856                     } else {
 857                         validateScrollOffset();
 858                     }


 859 
 860                     Side tabPosition = getSkinnable().getSide();
 861                     double tabBackgroundHeight = snapSize(prefHeight(-1));
 862                     double tabX = (tabPosition.equals(Side.LEFT) || tabPosition.equals(Side.BOTTOM)) ?
 863                         snapSize(getWidth()) - getScrollOffset() : getScrollOffset();
 864 
 865                     updateHeaderClip();
 866                     for (Node node : getChildren()) {
 867                         TabHeaderSkin tabHeader = (TabHeaderSkin)node;
 868 
 869                         // size and position the header relative to the other headers
 870                         double tabHeaderPrefWidth = snapSize(tabHeader.prefWidth(-1) * tabHeader.animationTransition.get());
 871                         double tabHeaderPrefHeight = snapSize(tabHeader.prefHeight(-1));
 872                         tabHeader.resize(tabHeaderPrefWidth, tabHeaderPrefHeight);
 873 
 874                         // This ensures that the tabs are located in the correct position
 875                         // when there are tabs of differing heights.
 876                         double startY = tabPosition.equals(Side.BOTTOM) ?
 877                             0 : tabBackgroundHeight - tabHeaderPrefHeight - snappedBottomInset();
 878                         if (tabPosition.equals(Side.LEFT) || tabPosition.equals(Side.BOTTOM)) {


 973                 }
 974                 clipHeight = headersPrefHeight;
 975             } else {
 976                 // If x = 0 the header region's drop shadow is clipped.
 977                 x = -shadowRadius;
 978                 clipWidth = (headersPrefWidth < maxWidth ? headersPrefWidth : maxWidth) + shadowRadius;
 979                 clipHeight = headersPrefHeight;
 980             }
 981 
 982             headerClip.setX(x);
 983             headerClip.setY(y);
 984             headerClip.setWidth(clipWidth);
 985             headerClip.setHeight(clipHeight);
 986         }
 987 
 988         private void addTab(Tab tab, int addToIndex) {
 989             TabHeaderSkin tabHeaderSkin = new TabHeaderSkin(tab);
 990             headersRegion.getChildren().add(addToIndex, tabHeaderSkin);
 991         }
 992 
 993         private List<TabHeaderSkin> removeTab = new ArrayList<>();
 994         private void removeTab(Tab tab) {
 995             TabHeaderSkin tabHeaderSkin = getTabHeaderSkin(tab);
 996             if (tabHeaderSkin != null) {
 997                 if (tabsFit()) {
 998                     headersRegion.getChildren().remove(tabHeaderSkin);
 999                 } else {
1000                     // The tab will be removed during layout because
1001                     // we need its width to compute the scroll offset.
1002                     removeTab.add(tabHeaderSkin);
1003                     tabHeaderSkin.removeListeners(tab);
1004                 }
1005             }
1006         }
1007 
1008         private TabHeaderSkin getTabHeaderSkin(Tab tab) {
1009             for (Node child: headersRegion.getChildren()) {
1010                 TabHeaderSkin tabHeaderSkin = (TabHeaderSkin)child;
1011                 if (tabHeaderSkin.getTab().equals(tab)) {
1012                     return tabHeaderSkin;
1013                 }
1014             }
1015             return null;
1016         }
1017 
1018         private boolean tabsFit() {
1019             double headerPrefWidth = snapSize(headersRegion.prefWidth(-1));
1020             double controlTabWidth = snapSize(controlButtons.prefWidth(-1));
1021             double visibleWidth = headerPrefWidth + controlTabWidth + firstTabIndent() + SPACER;
1022             return visibleWidth < getWidth();
1023         }
1024 


   1 /*
   2  * Copyright (c) 2011, 2018, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any


 809                         if (tabHeaderSkin.isVisible() && (measureClosingTabs || ! tabHeaderSkin.isClosing)) {
 810                             width += tabHeaderSkin.prefWidth(height);
 811                         }
 812                     }
 813                     return snapSize(width) + snappedLeftInset() + snappedRightInset();
 814                 }
 815 
 816                 @Override protected double computePrefHeight(double width) {
 817                     double height = 0.0F;
 818                     for (Node child : getChildren()) {
 819                         TabHeaderSkin tabHeaderSkin = (TabHeaderSkin)child;
 820                         height = Math.max(height, tabHeaderSkin.prefHeight(width));
 821                     }
 822                     return snapSize(height) + snappedTopInset() + snappedBottomInset();
 823                 }
 824 
 825                 @Override protected void layoutChildren() {
 826                     if (tabsFit()) {
 827                         setScrollOffset(0.0);
 828                     } else {
























 829                         if (isSelectingTab) {
 830                             ensureSelectedTabIsVisible();

 831                         } else {
 832                             validateScrollOffset();
 833                         }
 834                     }
 835                     isSelectingTab = false;
 836 
 837                     Side tabPosition = getSkinnable().getSide();
 838                     double tabBackgroundHeight = snapSize(prefHeight(-1));
 839                     double tabX = (tabPosition.equals(Side.LEFT) || tabPosition.equals(Side.BOTTOM)) ?
 840                         snapSize(getWidth()) - getScrollOffset() : getScrollOffset();
 841 
 842                     updateHeaderClip();
 843                     for (Node node : getChildren()) {
 844                         TabHeaderSkin tabHeader = (TabHeaderSkin)node;
 845 
 846                         // size and position the header relative to the other headers
 847                         double tabHeaderPrefWidth = snapSize(tabHeader.prefWidth(-1) * tabHeader.animationTransition.get());
 848                         double tabHeaderPrefHeight = snapSize(tabHeader.prefHeight(-1));
 849                         tabHeader.resize(tabHeaderPrefWidth, tabHeaderPrefHeight);
 850 
 851                         // This ensures that the tabs are located in the correct position
 852                         // when there are tabs of differing heights.
 853                         double startY = tabPosition.equals(Side.BOTTOM) ?
 854                             0 : tabBackgroundHeight - tabHeaderPrefHeight - snappedBottomInset();
 855                         if (tabPosition.equals(Side.LEFT) || tabPosition.equals(Side.BOTTOM)) {


 950                 }
 951                 clipHeight = headersPrefHeight;
 952             } else {
 953                 // If x = 0 the header region's drop shadow is clipped.
 954                 x = -shadowRadius;
 955                 clipWidth = (headersPrefWidth < maxWidth ? headersPrefWidth : maxWidth) + shadowRadius;
 956                 clipHeight = headersPrefHeight;
 957             }
 958 
 959             headerClip.setX(x);
 960             headerClip.setY(y);
 961             headerClip.setWidth(clipWidth);
 962             headerClip.setHeight(clipHeight);
 963         }
 964 
 965         private void addTab(Tab tab, int addToIndex) {
 966             TabHeaderSkin tabHeaderSkin = new TabHeaderSkin(tab);
 967             headersRegion.getChildren().add(addToIndex, tabHeaderSkin);
 968         }
 969 

 970         private void removeTab(Tab tab) {
 971             TabHeaderSkin tabHeaderSkin = getTabHeaderSkin(tab);
 972             if (tabHeaderSkin != null) {

 973                 headersRegion.getChildren().remove(tabHeaderSkin);






 974             }
 975         }
 976 
 977         private TabHeaderSkin getTabHeaderSkin(Tab tab) {
 978             for (Node child: headersRegion.getChildren()) {
 979                 TabHeaderSkin tabHeaderSkin = (TabHeaderSkin)child;
 980                 if (tabHeaderSkin.getTab().equals(tab)) {
 981                     return tabHeaderSkin;
 982                 }
 983             }
 984             return null;
 985         }
 986 
 987         private boolean tabsFit() {
 988             double headerPrefWidth = snapSize(headersRegion.prefWidth(-1));
 989             double controlTabWidth = snapSize(controlButtons.prefWidth(-1));
 990             double visibleWidth = headerPrefWidth + controlTabWidth + firstTabIndent() + SPACER;
 991             return visibleWidth < getWidth();
 992         }
 993 


< prev index next >