home *** CD-ROM | disk | FTP | other *** search
/ Chip 1998 November / Chip_1998-11_cd.bin / tema / Cafe / main.bin / CardLayout.java < prev    next >
Text File  |  1997-10-01  |  15KB  |  443 lines

  1. /*
  2.  * @(#)CardLayout.java    1.20 97/06/12
  3.  * 
  4.  * Copyright (c) 1995, 1996 Sun Microsystems, Inc. All Rights Reserved.
  5.  * 
  6.  * This software is the confidential and proprietary information of Sun
  7.  * Microsystems, Inc. ("Confidential Information").  You shall not
  8.  * disclose such Confidential Information and shall use it only in
  9.  * accordance with the terms of the license agreement you entered into
  10.  * with Sun.
  11.  * 
  12.  * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF THE
  13.  * SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
  14.  * IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
  15.  * PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR ANY DAMAGES
  16.  * SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR DISTRIBUTING
  17.  * THIS SOFTWARE OR ITS DERIVATIVES.
  18.  * 
  19.  * CopyrightVersion 1.1_beta
  20.  * 
  21.  */
  22.  
  23. package java.awt;
  24.  
  25. import java.util.Hashtable;
  26. import java.util.Enumeration;
  27.  
  28. /**
  29.  * A <code>CardLayout</code> object is a layout manager for a 
  30.  * container. It treats each component in the container as a card.
  31.  * Only one card is visible at a time, and the container acts as
  32.  * a stack of cards.  
  33.  * <p>
  34.  * The ordering of cards is determined by the container's own internal
  35.  * ordering of its component objects. <code>CardLayout</code> 
  36.  * defines a set of methods that allow an application to flip 
  37.  * through these cards sequentially, or to show a specified card.
  38.  * The <A HREF="#addLayoutComponent"><code>addLayoutComponent</code></A> 
  39.  * method can be used to associate a string identifier with a given card
  40.  * for fast random access.
  41.  *
  42.  * @version     1.20 06/12/97
  43.  * @author     Arthur van Hoff
  44.  * @see         java.awt.Container
  45.  * @since       JDK1.0
  46.  */
  47.  
  48. public class CardLayout implements LayoutManager2,
  49.                    java.io.Serializable {
  50.     Hashtable tab = new Hashtable();
  51.     int hgap;
  52.     int vgap;
  53.  
  54.     /**
  55.      * Creates a new card layout with gaps of size zero.
  56.      * @since  JDK1.0
  57.      */
  58.     public CardLayout() {
  59.     this(0, 0);
  60.     }
  61.  
  62.     /**
  63.      * Creates a new card layout with the specified horizontal and 
  64.      * vertical gaps. The horizontal gaps are placed at the left and 
  65.      * right edges. The vertical gaps are placed at the top and bottom 
  66.      * edges. 
  67.      * @param     hgap   the horizontal gap.
  68.      * @param     vgap   the vertical gap.
  69.      * @since     JDK1.0
  70.      */
  71.     public CardLayout(int hgap, int vgap) {
  72.     this.hgap = hgap;
  73.     this.vgap = vgap;
  74.     }
  75.  
  76.     /**
  77.      * Gets the horizontal gap between components.
  78.      * @return    the horizontal gap between components.
  79.      * @see       java.awt.CardLayout#setHgap(int)
  80.      * @see       java.awt.CardLayout#getVgap()
  81.      * @since     JDK1.1
  82.      */
  83.     public int getHgap() {
  84.     return hgap;
  85.     }
  86.     
  87.     /**
  88.      * Sets the horizontal gap between components.
  89.      * @param hgap the horizontal gap between components.
  90.      * @see       java.awt.CardLayout#getHgap()
  91.      * @see       java.awt.CardLayout#setVgap(int)
  92.      * @since     JDK1.1
  93.      */
  94.     public void setHgap(int hgap) {
  95.     this.hgap = hgap;
  96.     }
  97.     
  98.     /**
  99.      * Gets the vertical gap between components.
  100.      * @return the vertical gap between components.
  101.      * @see       java.awt.CardLayout#setVgap(int)
  102.      * @see       java.awt.CardLayout#getHgap()
  103.      */
  104.     public int getVgap() {
  105.     return vgap;
  106.     }
  107.     
  108.     /**
  109.      * Sets the vertical gap between components.
  110.      * @param     vgap the vertical gap between components.
  111.      * @see       java.awt.CardLayout#getVgap()
  112.      * @see       java.awt.CardLayout#setHgap(int)
  113.      * @since     JDK1.1
  114.      */
  115.     public void setVgap(int vgap) {
  116.     this.vgap = vgap;
  117.     }
  118.  
  119.     /**
  120.      * Adds the specified component to this card layout's internal
  121.      * table of names. The object specified by <code>constraints</code>  
  122.      * must be a string. The card layout stores this string as a key-value
  123.      * pair that can be used for random access to a particular card.
  124.      * By calling the <code>show</code> method, an application can  
  125.      * display the component with the specified name. 
  126.      * @param     comp          the component to be added.
  127.      * @param     constraints   a tag that identifies a particular 
  128.      *                                        card in the layout.
  129.      * @see       java.awt.CardLayout#show(java.awt.Container, java.lang.String)
  130.      * @exception  IllegalArgumentException  if the constraint is not a string.
  131.      * @since     JDK1.0
  132.      */
  133.     public void addLayoutComponent(Component comp, Object constraints) {
  134.     if (constraints instanceof String) {
  135.         addLayoutComponent((String)constraints, comp);
  136.     } else {
  137.         throw new IllegalArgumentException("cannot add to layout: constraint must be a string");
  138.     }
  139.     }
  140.  
  141.     /**
  142.      * @deprecated   replaced by 
  143.      *      <code>addLayoutComponent(Component, Object)</code>.
  144.      */
  145.     public void addLayoutComponent(String name, Component comp) {
  146.     if (tab.size() > 0) {
  147.         comp.hide();
  148.     }
  149.     tab.put(name, comp);
  150.     }
  151.  
  152.     /**
  153.      * Removes the specified component from the layout.
  154.      * @param   comp   the component to be removed.
  155.      * @see     java.awt.Container#remove(java.awt.Component)
  156.      * @see     java.awt.Container#removeAll()
  157.      * @since   JDK1.0
  158.      */
  159.     public void removeLayoutComponent(Component comp) {
  160.     for (Enumeration e = tab.keys() ; e.hasMoreElements() ; ) {
  161.         String key = (String)e.nextElement();
  162.         if (tab.get(key) == comp) {
  163.         tab.remove(key);
  164.         return;
  165.         }
  166.     }
  167.     }
  168.  
  169.     /** 
  170.      * Determines the preferred size of the container argument using 
  171.      * this card layout.
  172.      * @param   parent the name of the parent container.
  173.      * @return  the preferred dimensions to lay out the subcomponents 
  174.      *                of the specified container.
  175.      * @see     java.awt.Container#getPreferredSize
  176.      * @see     java.awt.CardLayout#minimumLayoutSize
  177.      * @since   JDK1.0
  178.      */
  179.     public Dimension preferredLayoutSize(Container parent) {
  180.     Insets insets = parent.getInsets();
  181.     int ncomponents = parent.getComponentCount();
  182.     int w = 0;
  183.     int h = 0;
  184.  
  185.     for (int i = 0 ; i < ncomponents ; i++) {
  186.         Component comp = parent.getComponent(i);
  187.         Dimension d = comp.getPreferredSize();
  188.         if (d.width > w) {
  189.         w = d.width;
  190.         }
  191.         if (d.height > h) {
  192.         h = d.height;
  193.         }
  194.     }
  195.     return new Dimension(insets.left + insets.right + w + hgap*2, 
  196.                  insets.top + insets.bottom + h + vgap*2);
  197.     }
  198.  
  199.     /** 
  200.      * Calculates the minimum size for the specified panel.
  201.      * @param     parent the name of the parent container 
  202.      *                in which to do the layout.
  203.      * @return    the minimum dimensions required to lay out the 
  204.      *                subcomponents of the specified container.
  205.      * @see       java.awt.Container#doLayout
  206.      * @see       java.awt.CardLayout#preferredLayoutSize 
  207.      * @since     JDK1.0
  208.      */
  209.     public Dimension minimumLayoutSize(Container parent) {
  210.     Insets insets = parent.getInsets();
  211.     int ncomponents = parent.getComponentCount();
  212.     int w = 0;
  213.     int h = 0;
  214.  
  215.     for (int i = 0 ; i < ncomponents ; i++) {
  216.         Component comp = parent.getComponent(i);
  217.         Dimension d = comp.getMinimumSize();
  218.         if (d.width > w) {
  219.         w = d.width;
  220.         }
  221.         if (d.height > h) {
  222.         h = d.height;
  223.         }
  224.     }
  225.     return new Dimension(insets.left + insets.right + w + hgap*2, 
  226.                  insets.top + insets.bottom + h + vgap*2);
  227.     }
  228.  
  229.     /**
  230.      * Returns the maximum dimensions for this layout given the components
  231.      * in the specified target container.
  232.      * @param target the component which needs to be laid out
  233.      * @see Container
  234.      * @see #minimumLayoutSize
  235.      * @see #preferredLayoutSize
  236.      */
  237.     public Dimension maximumLayoutSize(Container target) {
  238.     return new Dimension(Integer.MAX_VALUE, Integer.MAX_VALUE);
  239.     }
  240.  
  241.     /**
  242.      * Returns the alignment along the x axis.  This specifies how
  243.      * the component would like to be aligned relative to other 
  244.      * components.  The value should be a number between 0 and 1
  245.      * where 0 represents alignment along the origin, 1 is aligned
  246.      * the furthest away from the origin, 0.5 is centered, etc.
  247.      */
  248.     public float getLayoutAlignmentX(Container parent) {
  249.     return 0.5f;
  250.     }
  251.  
  252.     /**
  253.      * Returns the alignment along the y axis.  This specifies how
  254.      * the component would like to be aligned relative to other 
  255.      * components.  The value should be a number between 0 and 1
  256.      * where 0 represents alignment along the origin, 1 is aligned
  257.      * the furthest away from the origin, 0.5 is centered, etc.
  258.      */
  259.     public float getLayoutAlignmentY(Container parent) {
  260.     return 0.5f;
  261.     }
  262.  
  263.     /**
  264.      * Invalidates the layout, indicating that if the layout manager
  265.      * has cached information it should be discarded.
  266.      */
  267.     public void invalidateLayout(Container target) {
  268.     }
  269.                       
  270.     /** 
  271.      * Lays out the specified container using this card layout. 
  272.      * <p>
  273.      * Each component in the <code>parent</code> container is reshaped 
  274.      * to be the size of the container, minus space for surrounding 
  275.      * insets, horizontal gaps, and vertical gaps. 
  276.      * 
  277.      * @param     parent the name of the parent container 
  278.      *                             in which to do the layout. 
  279.      * @see       java.awt.Container#doLayout
  280.      * @since     JDK1.0 
  281.      */
  282.     public void layoutContainer(Container parent) {
  283.     Insets insets = parent.getInsets();
  284.     int ncomponents = parent.getComponentCount();
  285.     for (int i = 0 ; i < ncomponents ; i++) {
  286.         Component comp = parent.getComponent(i);
  287.         if (comp.visible) {
  288.         comp.setBounds(hgap + insets.left, vgap + insets.top, 
  289.                    parent.width - (hgap*2 + insets.left + insets.right), 
  290.                    parent.height - (vgap*2 + insets.top + insets.bottom));
  291.         }
  292.     }
  293.     }
  294.  
  295.     /**
  296.      * Make sure that the Container really has a CardLayout installed.
  297.      * Otherwise havoc can ensue!
  298.      */
  299.     void checkLayout(Container parent) {
  300.     if (parent.getLayout() != this) {
  301.         throw new IllegalArgumentException("wrong parent for CardLayout");
  302.     }
  303.     }
  304.  
  305.     /**
  306.      * Flips to the first card of the container. 
  307.      * @param     parent   the name of the parent container 
  308.      *                          in which to do the layout.
  309.      * @see       java.awt.CardLayout#last
  310.      * @since     JDK1.0
  311.      */
  312.     public void first(Container parent) {
  313.     synchronized (Component.LOCK) {
  314.         checkLayout(parent);
  315.         int ncomponents = parent.getComponentCount();
  316.         for (int i = 0 ; i < ncomponents ; i++) {
  317.         Component comp = parent.getComponent(i);
  318.         if (comp.visible) {
  319.             comp.hide();
  320.             comp = parent.getComponent(0);
  321.             comp.show();
  322.             parent.validate();
  323.             return;
  324.         }
  325.         }
  326.     }
  327.     }
  328.  
  329.     /**
  330.      * Flips to the next card of the specified container. If the 
  331.      * currently visible card is the last one, this method flips to the 
  332.      * first card in the layout. 
  333.      * @param     parent   the name of the parent container 
  334.      *                          in which to do the layout.
  335.      * @see       java.awt.CardLayout#previous
  336.      * @since     JDK1.0
  337.      */
  338.     public void next(Container parent) {
  339.     synchronized (Component.LOCK) {
  340.         checkLayout(parent);
  341.         int ncomponents = parent.getComponentCount();
  342.         for (int i = 0 ; i < ncomponents ; i++) {
  343.         Component comp = parent.getComponent(i);
  344.         if (comp.visible) {
  345.             comp.hide();
  346.             comp = parent.getComponent((i + 1 < ncomponents) ? i+1 : 0);
  347.             comp.show();
  348.             parent.validate();
  349.             return;
  350.         }
  351.         }
  352.     }
  353.     }
  354.  
  355.     /**
  356.      * Flips to the previous card of the specified container. If the 
  357.      * currently visible card is the first one, this method flips to the 
  358.      * last card in the layout. 
  359.      * @param     parent   the name of the parent container 
  360.      *                          in which to do the layout.
  361.      * @see       java.awt.CardLayout#next
  362.      * @since     JDK1.0
  363.      */
  364.     public void previous(Container parent) {
  365.     synchronized (Component.LOCK) {
  366.         checkLayout(parent);
  367.         int ncomponents = parent.getComponentCount();
  368.         for (int i = 0 ; i < ncomponents ; i++) {
  369.         Component comp = parent.getComponent(i);
  370.         if (comp.visible) {
  371.             comp.hide();
  372.             comp = parent.getComponent((i > 0) ? i-1 : ncomponents-1);
  373.             comp.show();
  374.             parent.validate();
  375.             return;
  376.         }
  377.         }
  378.     }
  379.     }
  380.  
  381.     /**
  382.      * Flips to the last card of the container. 
  383.      * @param     parent   the name of the parent container 
  384.      *                          in which to do the layout.
  385.      * @see       java.awt.CardLayout#first
  386.      * @since     JDK1.0
  387.      */
  388.     public void last(Container parent) {
  389.     synchronized (Component.LOCK) {
  390.         checkLayout(parent);
  391.         int ncomponents = parent.getComponentCount();
  392.         for (int i = 0 ; i < ncomponents ; i++) {
  393.         Component comp = parent.getComponent(i);
  394.         if (comp.visible) {
  395.             comp.hide();
  396.             comp = parent.getComponent(ncomponents - 1);
  397.             comp.show();
  398.             parent.validate();
  399.             return;
  400.         }
  401.         }
  402.     }
  403.     }
  404.  
  405.     /**
  406.      * Flips to the component that was added to this layout with the  
  407.      * specified <code>name</code>, using <code>addLayoutComponent</code>.  
  408.      * If no such component exists, then nothing happens. 
  409.      * @param     parent   the name of the parent container 
  410.      *                     in which to do the layout.
  411.      * @param     name     the component name.
  412.      * @see       java.awt.CardLayout#addLayoutComponent(java.awt.Component, java.lang.Object)
  413.      * @since     JDK1.0
  414.      */
  415.     public void show(Container parent, String name) {
  416.     synchronized (Component.LOCK) {
  417.         checkLayout(parent);
  418.         Component next = (Component)tab.get(name);
  419.         if ((next != null) && !next.visible){
  420.         int ncomponents = parent.getComponentCount();
  421.         for (int i = 0 ; i < ncomponents ; i++) {
  422.             Component comp = parent.getComponent(i);
  423.             if (comp.visible) {
  424.             comp.hide();
  425.             break;
  426.             }
  427.         }
  428.         next.show();
  429.         parent.validate();
  430.         }
  431.     }
  432.     }
  433.     
  434.     /**
  435.      * Returns a string representation of the state of this card layout.
  436.      * @return    a string representation of this card layout.
  437.      * @since     JDK1.0
  438.      */
  439.     public String toString() {
  440.     return getClass().getName() + "[hgap=" + hgap + ",vgap=" + vgap + "]";
  441.     }
  442. }
  443.