1 /*
2 * Copyright (c) 2011, 2013, 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
3220
3221 if (e.getSource() == scrollForwardButton) {
3222 actionKey = "scrollTabsForwardAction";
3223 } else {
3224 actionKey = "scrollTabsBackwardAction";
3225 }
3226 final Action action = map.get(actionKey);
3227
3228 if (action != null && action.isEnabled()) {
3229 action.actionPerformed(new ActionEvent(tabPane, ActionEvent.ACTION_PERFORMED, null, e.getWhen(), e.getModifiers()));
3230 }
3231 }
3232 }
3233
3234 public String toString() {
3235 return new String("viewport.viewSize=" + viewport.getViewSize() + "\n" + "viewport.viewRectangle=" + viewport.getViewRect() + "\n" + "leadingTabIndex=" + leadingTabIndex + "\n" + "tabViewPosition=" + tabViewPosition);
3236 }
3237
3238 }
3239
3240 private class ScrollableTabViewport extends JViewport implements UIResource {
3241 public ScrollableTabViewport() {
3242 super();
3243 setName("TabbedPane.scrollableViewport");
3244 setScrollMode(SIMPLE_SCROLL_MODE);
3245 setOpaque(tabPane.isOpaque());
3246 Color bgColor = UIManager.getColor("TabbedPane.tabAreaBackground");
3247 if (bgColor == null) {
3248 bgColor = tabPane.getBackground();
3249 }
3250 setBackground(bgColor);
3251 }
3252 }
3253
3254 private class ScrollableTabPanel extends JPanel implements UIResource {
3255 public ScrollableTabPanel() {
3256 super(null);
3257 setOpaque(tabPane.isOpaque());
3258 Color bgColor = UIManager.getColor("TabbedPane.tabAreaBackground");
3259 if (bgColor == null) {
3260 bgColor = tabPane.getBackground();
3261 }
3262 setBackground(bgColor);
3263 }
3264
3265 public void paintComponent(final Graphics g) {
3266 super.paintComponent(g);
3267 AquaTabbedPaneCopyFromBasicUI.this.paintTabArea(g, tabPane.getTabPlacement(), tabPane.getSelectedIndex());
3268 if (tabScroller.croppedEdge.isParamsSet() && tabContainer == null) {
3269 final Rectangle croppedRect = rects[tabScroller.croppedEdge.getTabIndex()];
3270 g.translate(croppedRect.x, croppedRect.y);
3271 tabScroller.croppedEdge.paintComponent(g);
3272 g.translate(-croppedRect.x, -croppedRect.y);
3273 }
3274 }
3275
3276 public void doLayout() {
3277 if (getComponentCount() > 0) {
3278 final Component child = getComponent(0);
3279 child.setBounds(0, 0, getWidth(), getHeight());
3280 }
3281 }
3282 }
3283
3284 private class ScrollableTabButton extends javax.swing.plaf.basic.BasicArrowButton implements UIResource, SwingConstants {
3285 public ScrollableTabButton(final int direction) {
3286 super(direction, UIManager.getColor("TabbedPane.selected"), UIManager.getColor("TabbedPane.shadow"), UIManager.getColor("TabbedPane.darkShadow"), UIManager.getColor("TabbedPane.highlight"));
3287 }
3288 }
3289
3290 // Controller: event listeners
3291
3292 private class Handler implements ChangeListener, ContainerListener, FocusListener, MouseListener, MouseMotionListener, PropertyChangeListener {
3293 //
3294 // PropertyChangeListener
3295 //
3296 public void propertyChange(final PropertyChangeEvent e) {
3297 final JTabbedPane pane = (JTabbedPane)e.getSource();
3298 final String name = e.getPropertyName();
3299 final boolean isScrollLayout = scrollableTabLayoutEnabled();
3300 if (name == "mnemonicAt") {
3301 updateMnemonics();
3302 pane.repaint();
3303 } else if (name == "displayedMnemonicIndexAt") {
3568 getHandler().focusLost(e);
3569 }
3570 }
3571
3572 private Vector<View> createHTMLVector() {
3573 final Vector<View> htmlViews = new Vector<View>();
3574 final int count = tabPane.getTabCount();
3575 if (count > 0) {
3576 for (int i = 0; i < count; i++) {
3577 final String title = tabPane.getTitleAt(i);
3578 if (BasicHTML.isHTMLString(title)) {
3579 htmlViews.addElement(BasicHTML.createHTMLView(tabPane, title));
3580 } else {
3581 htmlViews.addElement(null);
3582 }
3583 }
3584 }
3585 return htmlViews;
3586 }
3587
3588 private class TabContainer extends JPanel implements UIResource {
3589 private boolean notifyTabbedPane = true;
3590
3591 public TabContainer() {
3592 super(null);
3593 setOpaque(false);
3594 }
3595
3596 public void remove(final Component comp) {
3597 final int index = tabPane.indexOfTabComponent(comp);
3598 super.remove(comp);
3599 if (notifyTabbedPane && index != -1) {
3600 tabPane.setTabComponentAt(index, null);
3601 }
3602 }
3603
3604 private void removeUnusedTabComponents() {
3605 for (final Component c : getComponents()) {
3606 if (!(c instanceof UIResource)) {
3607 final int index = tabPane.indexOfTabComponent(c);
3612 }
3613 }
3614
3615 public boolean isOptimizedDrawingEnabled() {
3616 return tabScroller != null && !tabScroller.croppedEdge.isParamsSet();
3617 }
3618
3619 public void doLayout() {
3620 // We layout tabComponents in JTabbedPane's layout manager
3621 // and use this method as a hook for repainting tabs
3622 // to update tabs area e.g. when the size of tabComponent was changed
3623 if (scrollableTabLayoutEnabled()) {
3624 tabScroller.tabPanel.repaint();
3625 tabScroller.updateView();
3626 } else {
3627 tabPane.repaint(getBounds());
3628 }
3629 }
3630 }
3631
3632 private class CroppedEdge extends JPanel implements UIResource {
3633 private Shape shape;
3634 private int tabIndex;
3635 private int cropline;
3636 private int cropx, cropy;
3637
3638 public CroppedEdge() {
3639 setOpaque(false);
3640 }
3641
3642 public void setParams(final int tabIndex, final int cropline, final int cropx, final int cropy) {
3643 this.tabIndex = tabIndex;
3644 this.cropline = cropline;
3645 this.cropx = cropx;
3646 this.cropy = cropy;
3647 final Rectangle tabRect = rects[tabIndex];
3648 setBounds(tabRect);
3649 shape = createCroppedTabShape(tabPane.getTabPlacement(), tabRect, cropline);
3650 if (getParent() == null && tabContainer != null) {
3651 tabContainer.add(this, 0);
3691 if (isParamsSet() && g instanceof Graphics2D) {
3692 final Graphics2D g2 = (Graphics2D)g;
3693 g2.clipRect(0, 0, getWidth(), getHeight());
3694 g2.setColor(getBgColor());
3695 g2.translate(cropx, cropy);
3696 g2.fill(shape);
3697 paintCroppedTabEdge(g);
3698 g2.translate(-cropx, -cropy);
3699 }
3700 }
3701 }
3702
3703 /**
3704 * An ActionMap that populates its contents as necessary. The
3705 * contents are populated by invoking the <code>loadActionMap</code>
3706 * method on the passed in Object.
3707 *
3708 * @version 1.6, 11/17/05
3709 * @author Scott Violet
3710 */
3711 static class LazyActionMap extends ActionMapUIResource {
3712 /**
3713 * Object to invoke <code>loadActionMap</code> on. This may be
3714 * a Class object.
3715 */
3716 private transient Object _loader;
3717
3718 /**
3719 * Installs an ActionMap that will be populated by invoking the
3720 * <code>loadActionMap</code> method on the specified Class
3721 * when necessary.
3722 * <p>
3723 * This should be used if the ActionMap can be shared.
3724 *
3725 * @param c JComponent to install the ActionMap on.
3726 * @param loaderClass Class object that gets loadActionMap invoked
3727 * on.
3728 * @param defaultsKey Key to use to defaults table to check for
3729 * existing map and what resulting Map will be registered on.
3730 */
|
1 /*
2 * Copyright (c) 2011, 2014, 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
3220
3221 if (e.getSource() == scrollForwardButton) {
3222 actionKey = "scrollTabsForwardAction";
3223 } else {
3224 actionKey = "scrollTabsBackwardAction";
3225 }
3226 final Action action = map.get(actionKey);
3227
3228 if (action != null && action.isEnabled()) {
3229 action.actionPerformed(new ActionEvent(tabPane, ActionEvent.ACTION_PERFORMED, null, e.getWhen(), e.getModifiers()));
3230 }
3231 }
3232 }
3233
3234 public String toString() {
3235 return new String("viewport.viewSize=" + viewport.getViewSize() + "\n" + "viewport.viewRectangle=" + viewport.getViewRect() + "\n" + "leadingTabIndex=" + leadingTabIndex + "\n" + "tabViewPosition=" + tabViewPosition);
3236 }
3237
3238 }
3239
3240 @SuppressWarnings("serial") // Superclass is not serializable across versions
3241 private class ScrollableTabViewport extends JViewport implements UIResource {
3242 public ScrollableTabViewport() {
3243 super();
3244 setName("TabbedPane.scrollableViewport");
3245 setScrollMode(SIMPLE_SCROLL_MODE);
3246 setOpaque(tabPane.isOpaque());
3247 Color bgColor = UIManager.getColor("TabbedPane.tabAreaBackground");
3248 if (bgColor == null) {
3249 bgColor = tabPane.getBackground();
3250 }
3251 setBackground(bgColor);
3252 }
3253 }
3254
3255 @SuppressWarnings("serial") // Superclass is not serializable across versions
3256 private class ScrollableTabPanel extends JPanel implements UIResource {
3257 public ScrollableTabPanel() {
3258 super(null);
3259 setOpaque(tabPane.isOpaque());
3260 Color bgColor = UIManager.getColor("TabbedPane.tabAreaBackground");
3261 if (bgColor == null) {
3262 bgColor = tabPane.getBackground();
3263 }
3264 setBackground(bgColor);
3265 }
3266
3267 public void paintComponent(final Graphics g) {
3268 super.paintComponent(g);
3269 AquaTabbedPaneCopyFromBasicUI.this.paintTabArea(g, tabPane.getTabPlacement(), tabPane.getSelectedIndex());
3270 if (tabScroller.croppedEdge.isParamsSet() && tabContainer == null) {
3271 final Rectangle croppedRect = rects[tabScroller.croppedEdge.getTabIndex()];
3272 g.translate(croppedRect.x, croppedRect.y);
3273 tabScroller.croppedEdge.paintComponent(g);
3274 g.translate(-croppedRect.x, -croppedRect.y);
3275 }
3276 }
3277
3278 public void doLayout() {
3279 if (getComponentCount() > 0) {
3280 final Component child = getComponent(0);
3281 child.setBounds(0, 0, getWidth(), getHeight());
3282 }
3283 }
3284 }
3285
3286 @SuppressWarnings("serial") // Superclass is not serializable across versions
3287 private class ScrollableTabButton extends javax.swing.plaf.basic.BasicArrowButton implements UIResource, SwingConstants {
3288 public ScrollableTabButton(final int direction) {
3289 super(direction, UIManager.getColor("TabbedPane.selected"), UIManager.getColor("TabbedPane.shadow"), UIManager.getColor("TabbedPane.darkShadow"), UIManager.getColor("TabbedPane.highlight"));
3290 }
3291 }
3292
3293 // Controller: event listeners
3294
3295 private class Handler implements ChangeListener, ContainerListener, FocusListener, MouseListener, MouseMotionListener, PropertyChangeListener {
3296 //
3297 // PropertyChangeListener
3298 //
3299 public void propertyChange(final PropertyChangeEvent e) {
3300 final JTabbedPane pane = (JTabbedPane)e.getSource();
3301 final String name = e.getPropertyName();
3302 final boolean isScrollLayout = scrollableTabLayoutEnabled();
3303 if (name == "mnemonicAt") {
3304 updateMnemonics();
3305 pane.repaint();
3306 } else if (name == "displayedMnemonicIndexAt") {
3571 getHandler().focusLost(e);
3572 }
3573 }
3574
3575 private Vector<View> createHTMLVector() {
3576 final Vector<View> htmlViews = new Vector<View>();
3577 final int count = tabPane.getTabCount();
3578 if (count > 0) {
3579 for (int i = 0; i < count; i++) {
3580 final String title = tabPane.getTitleAt(i);
3581 if (BasicHTML.isHTMLString(title)) {
3582 htmlViews.addElement(BasicHTML.createHTMLView(tabPane, title));
3583 } else {
3584 htmlViews.addElement(null);
3585 }
3586 }
3587 }
3588 return htmlViews;
3589 }
3590
3591 @SuppressWarnings("serial") // Superclass is not serializable across versions
3592 private class TabContainer extends JPanel implements UIResource {
3593 private boolean notifyTabbedPane = true;
3594
3595 public TabContainer() {
3596 super(null);
3597 setOpaque(false);
3598 }
3599
3600 public void remove(final Component comp) {
3601 final int index = tabPane.indexOfTabComponent(comp);
3602 super.remove(comp);
3603 if (notifyTabbedPane && index != -1) {
3604 tabPane.setTabComponentAt(index, null);
3605 }
3606 }
3607
3608 private void removeUnusedTabComponents() {
3609 for (final Component c : getComponents()) {
3610 if (!(c instanceof UIResource)) {
3611 final int index = tabPane.indexOfTabComponent(c);
3616 }
3617 }
3618
3619 public boolean isOptimizedDrawingEnabled() {
3620 return tabScroller != null && !tabScroller.croppedEdge.isParamsSet();
3621 }
3622
3623 public void doLayout() {
3624 // We layout tabComponents in JTabbedPane's layout manager
3625 // and use this method as a hook for repainting tabs
3626 // to update tabs area e.g. when the size of tabComponent was changed
3627 if (scrollableTabLayoutEnabled()) {
3628 tabScroller.tabPanel.repaint();
3629 tabScroller.updateView();
3630 } else {
3631 tabPane.repaint(getBounds());
3632 }
3633 }
3634 }
3635
3636 @SuppressWarnings("serial") // Superclass is not serializable across versions
3637 private class CroppedEdge extends JPanel implements UIResource {
3638 private Shape shape;
3639 private int tabIndex;
3640 private int cropline;
3641 private int cropx, cropy;
3642
3643 public CroppedEdge() {
3644 setOpaque(false);
3645 }
3646
3647 public void setParams(final int tabIndex, final int cropline, final int cropx, final int cropy) {
3648 this.tabIndex = tabIndex;
3649 this.cropline = cropline;
3650 this.cropx = cropx;
3651 this.cropy = cropy;
3652 final Rectangle tabRect = rects[tabIndex];
3653 setBounds(tabRect);
3654 shape = createCroppedTabShape(tabPane.getTabPlacement(), tabRect, cropline);
3655 if (getParent() == null && tabContainer != null) {
3656 tabContainer.add(this, 0);
3696 if (isParamsSet() && g instanceof Graphics2D) {
3697 final Graphics2D g2 = (Graphics2D)g;
3698 g2.clipRect(0, 0, getWidth(), getHeight());
3699 g2.setColor(getBgColor());
3700 g2.translate(cropx, cropy);
3701 g2.fill(shape);
3702 paintCroppedTabEdge(g);
3703 g2.translate(-cropx, -cropy);
3704 }
3705 }
3706 }
3707
3708 /**
3709 * An ActionMap that populates its contents as necessary. The
3710 * contents are populated by invoking the <code>loadActionMap</code>
3711 * method on the passed in Object.
3712 *
3713 * @version 1.6, 11/17/05
3714 * @author Scott Violet
3715 */
3716 @SuppressWarnings("serial") // Superclass is not serializable across versions
3717 static class LazyActionMap extends ActionMapUIResource {
3718 /**
3719 * Object to invoke <code>loadActionMap</code> on. This may be
3720 * a Class object.
3721 */
3722 private transient Object _loader;
3723
3724 /**
3725 * Installs an ActionMap that will be populated by invoking the
3726 * <code>loadActionMap</code> method on the specified Class
3727 * when necessary.
3728 * <p>
3729 * This should be used if the ActionMap can be shared.
3730 *
3731 * @param c JComponent to install the ActionMap on.
3732 * @param loaderClass Class object that gets loadActionMap invoked
3733 * on.
3734 * @param defaultsKey Key to use to defaults table to check for
3735 * existing map and what resulting Map will be registered on.
3736 */
|