| /* BasicScrollPaneUI.java |
| Copyright (C) 2002, 2004, 2005, 2006, Free Software Foundation, Inc. |
| |
| This file is part of GNU Classpath. |
| |
| GNU Classpath is free software; you can redistribute it and/or modify |
| it under the terms of the GNU General Public License as published by |
| the Free Software Foundation; either version 2, or (at your option) |
| any later version. |
| |
| GNU Classpath is distributed in the hope that it will be useful, but |
| WITHOUT ANY WARRANTY; without even the implied warranty of |
| MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
| General Public License for more details. |
| |
| You should have received a copy of the GNU General Public License |
| along with GNU Classpath; see the file COPYING. If not, write to the |
| Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA |
| 02110-1301 USA. |
| |
| Linking this library statically or dynamically with other modules is |
| making a combined work based on this library. Thus, the terms and |
| conditions of the GNU General Public License cover the whole |
| combination. |
| |
| As a special exception, the copyright holders of this library give you |
| permission to link this library with independent modules to produce an |
| executable, regardless of the license terms of these independent |
| modules, and to copy and distribute the resulting executable under |
| terms of your choice, provided that you also meet, for each linked |
| independent module, the terms and conditions of the license of that |
| module. An independent module is a module which is not derived from |
| or based on this library. If you modify this library, you may extend |
| this exception to your version of the library, but you are not |
| obligated to do so. If you do not wish to do so, delete this |
| exception statement from your version. */ |
| |
| |
| package javax.swing.plaf.basic; |
| |
| import java.awt.Dimension; |
| import java.awt.Graphics; |
| import java.awt.Point; |
| import java.awt.Rectangle; |
| import java.awt.event.ActionEvent; |
| import java.awt.event.ContainerEvent; |
| import java.awt.event.ContainerListener; |
| import java.awt.event.MouseWheelEvent; |
| import java.awt.event.MouseWheelListener; |
| import java.beans.PropertyChangeEvent; |
| import java.beans.PropertyChangeListener; |
| |
| import javax.swing.AbstractAction; |
| import javax.swing.ActionMap; |
| import javax.swing.InputMap; |
| import javax.swing.JComponent; |
| import javax.swing.JScrollBar; |
| import javax.swing.JScrollPane; |
| import javax.swing.JSlider; |
| import javax.swing.JViewport; |
| import javax.swing.LookAndFeel; |
| import javax.swing.ScrollPaneConstants; |
| import javax.swing.ScrollPaneLayout; |
| import javax.swing.SwingUtilities; |
| import javax.swing.UIManager; |
| import javax.swing.border.Border; |
| import javax.swing.event.ChangeEvent; |
| import javax.swing.event.ChangeListener; |
| import javax.swing.plaf.ActionMapUIResource; |
| import javax.swing.plaf.ComponentUI; |
| import javax.swing.plaf.ScrollPaneUI; |
| import javax.swing.plaf.UIResource; |
| |
| /** |
| * A UI delegate for the {@link JScrollPane} component. |
| */ |
| public class BasicScrollPaneUI extends ScrollPaneUI |
| implements ScrollPaneConstants |
| { |
| |
| /** |
| * Listens for changes in the state of the horizontal scrollbar's model and |
| * updates the scrollpane accordingly. |
| * |
| * @author Roman Kennke (kennke@aicas.com) |
| */ |
| public class HSBChangeListener implements ChangeListener |
| { |
| |
| /** |
| * Receives notification when the state of the horizontal scrollbar |
| * model has changed. |
| * |
| * @param event the change event |
| */ |
| public void stateChanged(ChangeEvent event) |
| { |
| JScrollBar hsb = scrollpane.getHorizontalScrollBar(); |
| JViewport vp = scrollpane.getViewport(); |
| Point viewPosition = vp.getViewPosition(); |
| viewPosition.x = hsb.getValue(); |
| vp.setViewPosition(viewPosition); |
| } |
| |
| } |
| |
| /** |
| * Listens for changes in the state of the vertical scrollbar's model and |
| * updates the scrollpane accordingly. |
| * |
| * @author Roman Kennke (kennke@aicas.com) |
| */ |
| public class VSBChangeListener implements ChangeListener |
| { |
| |
| /** |
| * Receives notification when the state of the vertical scrollbar |
| * model has changed. |
| * |
| * @param event the change event |
| */ |
| public void stateChanged(ChangeEvent event) |
| { |
| JScrollBar vsb = scrollpane.getVerticalScrollBar(); |
| JViewport vp = scrollpane.getViewport(); |
| Point viewPosition = vp.getViewPosition(); |
| viewPosition.y = vsb.getValue(); |
| vp.setViewPosition(viewPosition); |
| } |
| |
| } |
| |
| /** |
| * Listens for changes of the viewport's extent size and updates the |
| * scrollpane accordingly. |
| * |
| * @author Roman Kennke (kennke@aicas.com) |
| */ |
| public class ViewportChangeHandler implements ChangeListener |
| { |
| |
| /** |
| * Receives notification when the view's size, position or extent size |
| * changes. When the extents size has changed, this method calls |
| * {@link BasicScrollPaneUI#syncScrollPaneWithViewport()} to adjust the |
| * scrollbars extents as well. |
| * |
| * @param event the change event |
| */ |
| public void stateChanged(ChangeEvent event) |
| { |
| syncScrollPaneWithViewport(); |
| } |
| |
| } |
| |
| /** |
| * Listens for property changes on the scrollpane and update the view |
| * accordingly. |
| * |
| * @author Roman Kennke (kennke@aicas.com) |
| */ |
| public class PropertyChangeHandler implements PropertyChangeListener |
| { |
| |
| /** |
| * Receives notification when any of the scrollpane's bound property |
| * changes. This method calls the appropriate update method on the |
| * <code>ScrollBarUI</code>. |
| * |
| * @param e the property change event |
| * |
| * @see BasicScrollPaneUI#updateColumnHeader(PropertyChangeEvent) |
| * @see BasicScrollPaneUI#updateRowHeader(PropertyChangeEvent) |
| * @see BasicScrollPaneUI#updateScrollBarDisplayPolicy(PropertyChangeEvent) |
| * @see BasicScrollPaneUI#updateViewport(PropertyChangeEvent) |
| */ |
| public void propertyChange(PropertyChangeEvent e) |
| { |
| String propName = e.getPropertyName(); |
| if (propName.equals("viewport")) |
| updateViewport(e); |
| else if (propName.equals("rowHeader")) |
| updateRowHeader(e); |
| else if (propName.equals("columnHeader")) |
| updateColumnHeader(e); |
| else if (propName.equals("horizontalScrollBarPolicy") |
| || e.getPropertyName().equals("verticalScrollBarPolicy")) |
| updateScrollBarDisplayPolicy(e); |
| else if (propName.equals("verticalScrollBar")) |
| { |
| JScrollBar oldSb = (JScrollBar) e.getOldValue(); |
| oldSb.getModel().removeChangeListener(vsbChangeListener); |
| JScrollBar newSb = (JScrollBar) e.getNewValue(); |
| newSb.getModel().addChangeListener(vsbChangeListener); |
| } |
| else if (propName.equals("horizontalScrollBar")) |
| { |
| JScrollBar oldSb = (JScrollBar) e.getOldValue(); |
| oldSb.getModel().removeChangeListener(hsbChangeListener); |
| JScrollBar newSb = (JScrollBar) e.getNewValue(); |
| newSb.getModel().addChangeListener(hsbChangeListener); |
| } |
| } |
| |
| } |
| |
| /** |
| * Listens for mouse wheel events and update the scrollpane accordingly. |
| * |
| * @author Roman Kennke (kennke@aicas.com) |
| * |
| * @since 1.4 |
| */ |
| protected class MouseWheelHandler implements MouseWheelListener |
| { |
| /** |
| * Use to compute the visible rectangle. |
| */ |
| final Rectangle rect = new Rectangle(); |
| |
| /** |
| * Scroll with the mouse wheel. |
| * |
| * @author Audrius Meskauskas (audriusa@Bioinformatics.org) |
| */ |
| public void mouseWheelMoved(MouseWheelEvent e) |
| { |
| if (scrollpane.isWheelScrollingEnabled() && e.getScrollAmount() != 0) |
| { |
| // Try to scroll vertically first. |
| JScrollBar scrollBar = scrollpane.getVerticalScrollBar(); |
| if (scrollBar == null || ! scrollBar.isVisible()) |
| scrollBar = scrollpane.getHorizontalScrollBar(); |
| if (scrollBar != null && scrollBar.isVisible()) |
| { |
| int direction = e.getWheelRotation() < 0 ? -1 : 1; |
| int scrollType = e.getScrollType(); |
| if (scrollType == MouseWheelEvent.WHEEL_UNIT_SCROLL) |
| BasicScrollBarUI.scrollByUnits(scrollBar, direction, |
| e.getScrollAmount()); |
| else if (scrollType == MouseWheelEvent.WHEEL_BLOCK_SCROLL) |
| BasicScrollBarUI.scrollByBlock(scrollBar, direction); |
| } |
| } |
| } |
| } |
| |
| /** |
| * Adds/removes the mouse wheel listener when the component is added/removed |
| * to/from the scroll pane view port. |
| * |
| * @author Audrius Meskauskas (audriusa@bioinformatics.org) |
| */ |
| class ViewportContainerListener implements ContainerListener |
| { |
| /** |
| * Add the mouse wheel listener, allowing to scroll with the mouse. |
| */ |
| public void componentAdded(ContainerEvent e) |
| { |
| e.getChild().addMouseWheelListener(mouseWheelListener); |
| } |
| |
| /** |
| * Remove the mouse wheel listener. |
| */ |
| public void componentRemoved(ContainerEvent e) |
| { |
| e.getChild().removeMouseWheelListener(mouseWheelListener); |
| } |
| } |
| |
| /** |
| * The number of pixels by that we should scroll the content that does |
| * not implement Scrollable. |
| */ |
| static int SCROLL_NON_SCROLLABLES = 10; |
| |
| /** |
| * The number of rows to scroll per mouse wheel click. From impression, |
| * Sun seems using the value 3. |
| */ |
| static int ROWS_PER_WHEEL_CLICK = 3; |
| |
| /** The Scrollpane for which the UI is provided by this class. */ |
| protected JScrollPane scrollpane; |
| |
| /** |
| * The horizontal scrollbar listener. |
| */ |
| protected ChangeListener hsbChangeListener; |
| |
| /** |
| * The vertical scrollbar listener. |
| */ |
| protected ChangeListener vsbChangeListener; |
| |
| /** |
| * The viewport listener. |
| */ |
| protected ChangeListener viewportChangeListener; |
| |
| /** |
| * The scrollpane property change listener. |
| */ |
| protected PropertyChangeListener spPropertyChangeListener; |
| |
| /** |
| * The mousewheel listener for the scrollpane. |
| */ |
| MouseWheelListener mouseWheelListener; |
| |
| /** |
| * The listener to add and remove the mouse wheel listener to/from |
| * the component container. |
| */ |
| ContainerListener containerListener; |
| |
| public static ComponentUI createUI(final JComponent c) |
| { |
| return new BasicScrollPaneUI(); |
| } |
| |
| protected void installDefaults(JScrollPane p) |
| { |
| scrollpane = p; |
| LookAndFeel.installColorsAndFont(p, "ScrollPane.background", |
| "ScrollPane.foreground", |
| "ScrollPane.font"); |
| LookAndFeel.installBorder(p, "ScrollPane.border"); |
| |
| // Install Viewport border. |
| Border vpBorder = p.getViewportBorder(); |
| if (vpBorder == null || vpBorder instanceof UIResource) |
| { |
| vpBorder = UIManager.getBorder("ScrollPane.viewportBorder"); |
| p.setViewportBorder(vpBorder); |
| } |
| |
| p.setOpaque(true); |
| } |
| |
| protected void uninstallDefaults(JScrollPane p) |
| { |
| LookAndFeel.uninstallBorder(p); |
| Border vpBorder = p.getViewportBorder(); |
| if (vpBorder != null && vpBorder instanceof UIResource) |
| p.setViewportBorder(null); |
| } |
| |
| public void installUI(final JComponent c) |
| { |
| super.installUI(c); |
| installDefaults((JScrollPane) c); |
| installListeners((JScrollPane) c); |
| installKeyboardActions((JScrollPane) c); |
| } |
| |
| /** |
| * Installs the listeners on the scrollbars, the viewport and the scrollpane. |
| * |
| * @param sp the scrollpane on which to install the listeners |
| */ |
| protected void installListeners(JScrollPane sp) |
| { |
| if (spPropertyChangeListener == null) |
| spPropertyChangeListener = createPropertyChangeListener(); |
| sp.addPropertyChangeListener(spPropertyChangeListener); |
| |
| if (hsbChangeListener == null) |
| hsbChangeListener = createHSBChangeListener(); |
| sp.getHorizontalScrollBar().getModel().addChangeListener(hsbChangeListener); |
| |
| if (vsbChangeListener == null) |
| vsbChangeListener = createVSBChangeListener(); |
| sp.getVerticalScrollBar().getModel().addChangeListener(vsbChangeListener); |
| |
| if (viewportChangeListener == null) |
| viewportChangeListener = createViewportChangeListener(); |
| |
| if (mouseWheelListener == null) |
| mouseWheelListener = createMouseWheelListener(); |
| |
| if (containerListener == null) |
| containerListener = new ViewportContainerListener(); |
| |
| JViewport v = sp.getViewport(); |
| v.addChangeListener(viewportChangeListener); |
| v.addContainerListener(containerListener); |
| |
| // Add mouse wheel listeners to the componets that are probably already |
| // in the view port. |
| for (int i = 0; i < v.getComponentCount(); i++) |
| v.getComponent(i).addMouseWheelListener(mouseWheelListener); |
| } |
| |
| InputMap getInputMap(int condition) |
| { |
| if (condition == JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT) |
| return (InputMap) UIManager.get("ScrollPane.ancestorInputMap"); |
| return null; |
| } |
| |
| /** |
| * Returns the action map for the {@link JScrollPane}. All scroll panes |
| * share a single action map which is created the first time this method is |
| * called, then stored in the UIDefaults table for subsequent access. |
| * |
| * @return The shared action map. |
| */ |
| ActionMap getActionMap() |
| { |
| ActionMap map = (ActionMap) UIManager.get("ScrollPane.actionMap"); |
| |
| if (map == null) // first time here |
| { |
| map = createActionMap(); |
| if (map != null) |
| UIManager.put("ScrollPane.actionMap", map); |
| } |
| return map; |
| } |
| |
| /** |
| * Creates the action map shared by all {@link JSlider} instances. |
| * This method is called once by {@link #getActionMap()} when it |
| * finds no action map in the UIDefaults table...after the map is |
| * created, it gets added to the defaults table so that subsequent |
| * calls to {@link #getActionMap()} will return the same shared |
| * instance. |
| * |
| * @return The action map. |
| */ |
| ActionMap createActionMap() |
| { |
| ActionMap map = new ActionMapUIResource(); |
| map.put("scrollLeft", |
| new AbstractAction("scrollLeft") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getHorizontalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getBlockIncrement(-1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("scrollEnd", |
| new AbstractAction("scrollEnd") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb1 = sp.getHorizontalScrollBar(); |
| if (sb1.isVisible()) |
| { |
| sb1.setValue(sb1.getMaximum()); |
| } |
| JScrollBar sb2 = sp.getVerticalScrollBar(); |
| if (sb2.isVisible()) |
| { |
| sb2.setValue(sb2.getMaximum()); |
| } |
| } |
| } |
| ); |
| map.put("unitScrollUp", |
| new AbstractAction("unitScrollUp") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getVerticalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getUnitIncrement(-1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("unitScrollLeft", |
| new AbstractAction("unitScrollLeft") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getHorizontalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getUnitIncrement(-1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("scrollUp", |
| new AbstractAction("scrollUp") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getVerticalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getBlockIncrement(-1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("scrollRight", |
| new AbstractAction("scrollRight") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getHorizontalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getBlockIncrement(1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("scrollHome", |
| new AbstractAction("scrollHome") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb1 = sp.getHorizontalScrollBar(); |
| if (sb1.isVisible()) |
| { |
| sb1.setValue(sb1.getMinimum()); |
| } |
| JScrollBar sb2 = sp.getVerticalScrollBar(); |
| if (sb2.isVisible()) |
| { |
| sb2.setValue(sb2.getMinimum()); |
| } |
| } |
| } |
| ); |
| map.put("scrollDown", |
| new AbstractAction("scrollDown") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getVerticalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getBlockIncrement(1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("unitScrollDown", |
| new AbstractAction("unitScrollDown") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getVerticalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getUnitIncrement(1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| map.put("unitScrollRight", |
| new AbstractAction("unitScrollRight") { |
| public void actionPerformed(ActionEvent event) |
| { |
| JScrollPane sp = (JScrollPane) event.getSource(); |
| JScrollBar sb = sp.getHorizontalScrollBar(); |
| if (sb.isVisible()) |
| { |
| int delta = sb.getUnitIncrement(1); |
| sb.setValue(sb.getValue() + delta); |
| } |
| } |
| } |
| ); |
| return map; |
| } |
| |
| /** |
| * Installs additional keyboard actions on the scrollpane. This is a hook |
| * method provided to subclasses in order to install their own keyboard |
| * actions. |
| * |
| * @param sp the scrollpane to install keyboard actions on |
| */ |
| protected void installKeyboardActions(JScrollPane sp) |
| { |
| InputMap keyMap = getInputMap( |
| JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT); |
| SwingUtilities.replaceUIInputMap(sp, |
| JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT, keyMap); |
| ActionMap map = getActionMap(); |
| SwingUtilities.replaceUIActionMap(sp, map); |
| } |
| |
| /** |
| * Uninstalls all keyboard actions from the JScrollPane that have been |
| * installed by {@link #installKeyboardActions}. This is a hook method |
| * provided to subclasses to add their own keyboard actions. |
| * |
| * @param sp the scrollpane to uninstall keyboard actions from |
| */ |
| protected void uninstallKeyboardActions(JScrollPane sp) |
| { |
| SwingUtilities.replaceUIActionMap(sp, null); |
| SwingUtilities.replaceUIInputMap(sp, |
| JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT, null); |
| } |
| |
| /** |
| * Creates and returns the change listener for the horizontal scrollbar. |
| * |
| * @return the change listener for the horizontal scrollbar |
| */ |
| protected ChangeListener createHSBChangeListener() |
| { |
| return new HSBChangeListener(); |
| } |
| |
| /** |
| * Creates and returns the change listener for the vertical scrollbar. |
| * |
| * @return the change listener for the vertical scrollbar |
| */ |
| protected ChangeListener createVSBChangeListener() |
| { |
| return new VSBChangeListener(); |
| } |
| |
| /** |
| * Creates and returns the change listener for the viewport. |
| * |
| * @return the change listener for the viewport |
| */ |
| protected ChangeListener createViewportChangeListener() |
| { |
| return new ViewportChangeHandler(); |
| } |
| |
| /** |
| * Creates and returns the property change listener for the scrollpane. |
| * |
| * @return the property change listener for the scrollpane |
| */ |
| protected PropertyChangeListener createPropertyChangeListener() |
| { |
| return new PropertyChangeHandler(); |
| } |
| |
| /** |
| * Creates and returns the mouse wheel listener for the scrollpane. |
| * |
| * @return the mouse wheel listener for the scrollpane |
| * |
| * @since 1.4 |
| */ |
| protected MouseWheelListener createMouseWheelListener() |
| { |
| return new MouseWheelHandler(); |
| } |
| |
| public void uninstallUI(final JComponent c) |
| { |
| uninstallDefaults((JScrollPane) c); |
| uninstallListeners(c); |
| installKeyboardActions((JScrollPane) c); |
| } |
| |
| /** |
| * Uninstalls all the listeners that have been installed in |
| * {@link #installListeners(JScrollPane)}. |
| * |
| * @param c the scrollpane from which to uninstall the listeners |
| */ |
| protected void uninstallListeners(JComponent c) |
| { |
| JScrollPane sp = (JScrollPane) c; |
| sp.removePropertyChangeListener(spPropertyChangeListener); |
| sp.getHorizontalScrollBar().getModel() |
| .removeChangeListener(hsbChangeListener); |
| sp.getVerticalScrollBar().getModel() |
| .removeChangeListener(vsbChangeListener); |
| |
| JViewport v = sp.getViewport(); |
| v.removeChangeListener(viewportChangeListener); |
| v.removeContainerListener(containerListener); |
| |
| for (int i = 0; i < v.getComponentCount(); i++) |
| v.getComponent(i).removeMouseWheelListener(mouseWheelListener); |
| |
| } |
| |
| public Dimension getMinimumSize(JComponent c) |
| { |
| JScrollPane p = (JScrollPane) c; |
| ScrollPaneLayout sl = (ScrollPaneLayout) p.getLayout(); |
| return sl.minimumLayoutSize(c); |
| } |
| |
| public void paint(Graphics g, JComponent c) |
| { |
| Border vpBorder = scrollpane.getViewportBorder(); |
| if (vpBorder != null) |
| { |
| Rectangle r = scrollpane.getViewportBorderBounds(); |
| vpBorder.paintBorder(scrollpane, g, r.x, r.y, r.width, r.height); |
| } |
| } |
| |
| /** |
| * Synchronizes the scrollbar and header settings positions and extent |
| * with the viewport's view position and extent. |
| */ |
| protected void syncScrollPaneWithViewport() |
| { |
| JViewport vp = scrollpane.getViewport(); |
| |
| if (vp != null) |
| { |
| Dimension extentSize = vp.getExtentSize(); |
| Point viewPos = vp.getViewPosition(); |
| Dimension viewSize = vp.getViewSize(); |
| |
| // Update the vertical scrollbar. |
| JScrollBar vsb = scrollpane.getVerticalScrollBar(); |
| if (vsb != null) |
| { |
| int extent = extentSize.height; |
| int max = viewSize.height; |
| int val = Math.max(0, Math.min(viewPos.y, max - extent)); |
| vsb.setValues(val, extent, 0, max); |
| } |
| |
| // Update the horizontal scrollbar. |
| JScrollBar hsb = scrollpane.getHorizontalScrollBar(); |
| if (hsb != null) |
| { |
| int extent = extentSize.width; |
| int max = viewSize.width; |
| int val = Math.max(0, Math.min(viewPos.x, max - extent)); |
| hsb.setValues(val, extent, 0, max); |
| } |
| |
| // Update the row header. |
| JViewport rowHeader = scrollpane.getRowHeader(); |
| if (rowHeader != null) |
| { |
| Point p = new Point(0, viewPos.y); |
| rowHeader.setViewPosition(p); |
| } |
| |
| // Update the column header. |
| JViewport colHeader = scrollpane.getColumnHeader(); |
| if (colHeader != null) |
| { |
| Point p = new Point(viewPos.x, 0); |
| colHeader.setViewPosition(p); |
| } |
| } |
| } |
| |
| /** |
| * Receives notification when the <code>columnHeader</code> property has |
| * changed on the scrollpane. |
| * |
| * @param ev the property change event |
| */ |
| protected void updateColumnHeader(PropertyChangeEvent ev) |
| { |
| // TODO: Find out what should be done here. Or is this only a hook? |
| } |
| |
| /** |
| * Receives notification when the <code>rowHeader</code> property has changed |
| * on the scrollpane. |
| * |
| * @param ev the property change event |
| */ |
| protected void updateRowHeader(PropertyChangeEvent ev) |
| { |
| // TODO: Find out what should be done here. Or is this only a hook? |
| } |
| |
| /** |
| * Receives notification when the <code>scrollBarDisplayPolicy</code> |
| * property has changed on the scrollpane. |
| * |
| * @param ev the property change event |
| */ |
| protected void updateScrollBarDisplayPolicy(PropertyChangeEvent ev) |
| { |
| scrollpane.revalidate(); |
| scrollpane.repaint(); |
| } |
| |
| /** |
| * Receives notification when the <code>viewport</code> property has changed |
| * on the scrollpane. |
| * |
| * This method sets removes the viewportChangeListener from the old viewport |
| * and adds it to the new viewport. |
| * |
| * @param ev the property change event |
| */ |
| protected void updateViewport(PropertyChangeEvent ev) |
| { |
| JViewport oldViewport = (JViewport) ev.getOldValue(); |
| oldViewport.removeChangeListener(viewportChangeListener); |
| JViewport newViewport = (JViewport) ev.getNewValue(); |
| newViewport.addChangeListener(viewportChangeListener); |
| syncScrollPaneWithViewport(); |
| } |
| } |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |