001 /* MultiTabbedPaneUI.java --
002 Copyright (C) 2005 Free Software Foundation, Inc.
003
004 This file is part of GNU Classpath.
005
006 GNU Classpath is free software; you can redistribute it and/or modify
007 it under the terms of the GNU General Public License as published by
008 the Free Software Foundation; either version 2, or (at your option)
009 any later version.
010
011 GNU Classpath is distributed in the hope that it will be useful, but
012 WITHOUT ANY WARRANTY; without even the implied warranty of
013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
014 General Public License for more details.
015
016 You should have received a copy of the GNU General Public License
017 along with GNU Classpath; see the file COPYING. If not, write to the
018 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
019 02110-1301 USA.
020
021 Linking this library statically or dynamically with other modules is
022 making a combined work based on this library. Thus, the terms and
023 conditions of the GNU General Public License cover the whole
024 combination.
025
026 As a special exception, the copyright holders of this library give you
027 permission to link this library with independent modules to produce an
028 executable, regardless of the license terms of these independent
029 modules, and to copy and distribute the resulting executable under
030 terms of your choice, provided that you also meet, for each linked
031 independent module, the terms and conditions of the license of that
032 module. An independent module is a module which is not derived from
033 or based on this library. If you modify this library, you may extend
034 this exception to your version of the library, but you are not
035 obligated to do so. If you do not wish to do so, delete this
036 exception statement from your version. */
037
038 package javax.swing.plaf.multi;
039
040 import java.awt.Dimension;
041 import java.awt.Graphics;
042 import java.awt.Rectangle;
043 import java.util.Iterator;
044 import java.util.Vector;
045
046 import javax.accessibility.Accessible;
047 import javax.swing.JComponent;
048 import javax.swing.JTabbedPane;
049 import javax.swing.LookAndFeel;
050 import javax.swing.UIManager;
051 import javax.swing.plaf.ComponentUI;
052 import javax.swing.plaf.TabbedPaneUI;
053
054 /**
055 * A UI delegate that that coordinates multiple {@link TabbedPaneUI}
056 * instances, one from the primary look and feel, and one or more from the
057 * auxiliary look and feel(s).
058 *
059 * @see UIManager#addAuxiliaryLookAndFeel(LookAndFeel)
060 */
061 public class MultiTabbedPaneUI extends TabbedPaneUI
062 {
063
064 /** A list of references to the actual component UIs. */
065 protected Vector uis;
066
067 /**
068 * Creates a new <code>MultiTabbedPaneUI</code> instance.
069 *
070 * @see #createUI(JComponent)
071 */
072 public MultiTabbedPaneUI()
073 {
074 uis = new Vector();
075 }
076
077 /**
078 * Creates a delegate object for the specified component. If any auxiliary
079 * look and feels support this component, a <code>MultiTabbedPaneUI</code> is
080 * returned, otherwise the UI from the default look and feel is returned.
081 *
082 * @param target the component.
083 *
084 * @see MultiLookAndFeel#createUIs(ComponentUI, Vector, JComponent)
085 */
086 public static ComponentUI createUI(JComponent target)
087 {
088 MultiTabbedPaneUI mui = new MultiTabbedPaneUI();
089 return MultiLookAndFeel.createUIs(mui, mui.uis, target);
090 }
091
092 /**
093 * Calls the {@link ComponentUI#installUI(JComponent)} method for all
094 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>.
095 *
096 * @param c the component.
097 */
098 public void installUI(JComponent c)
099 {
100 Iterator iterator = uis.iterator();
101 while (iterator.hasNext())
102 {
103 ComponentUI ui = (ComponentUI) iterator.next();
104 ui.installUI(c);
105 }
106 }
107
108 /**
109 * Calls the {@link ComponentUI#uninstallUI(JComponent)} method for all
110 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>.
111 *
112 * @param c the component.
113 */
114 public void uninstallUI(JComponent c)
115 {
116 Iterator iterator = uis.iterator();
117 while (iterator.hasNext())
118 {
119 ComponentUI ui = (ComponentUI) iterator.next();
120 ui.uninstallUI(c);
121 }
122 }
123
124 /**
125 * Returns an array containing the UI delegates managed by this
126 * <code>MultiTabbedPaneUI</code>. The first item in the array is always
127 * the UI delegate from the installed default look and feel.
128 *
129 * @return An array of UI delegates.
130 */
131 public ComponentUI[] getUIs()
132 {
133 return MultiLookAndFeel.uisToArray(uis);
134 }
135
136 /**
137 * Calls the {@link ComponentUI#contains(JComponent, int, int)} method for all
138 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>,
139 * returning the result for the UI delegate from the primary look and
140 * feel.
141 *
142 * @param c the component.
143 * @param x the x-coordinate.
144 * @param y the y-coordinate.
145 *
146 * @return <code>true</code> if the specified (x, y) coordinate falls within
147 * the bounds of the component as rendered by the UI delegate in the
148 * primary look and feel, and <code>false</code> otherwise.
149 */
150 public boolean contains(JComponent c, int x, int y)
151 {
152 boolean result = false;
153 Iterator iterator = uis.iterator();
154 // first UI delegate provides the return value
155 if (iterator.hasNext())
156 {
157 ComponentUI ui = (ComponentUI) iterator.next();
158 result = ui.contains(c, x, y);
159 }
160 // return values from auxiliary UI delegates are ignored
161 while (iterator.hasNext())
162 {
163 ComponentUI ui = (ComponentUI) iterator.next();
164 /* boolean ignored = */ ui.contains(c, x, y);
165 }
166 return result;
167 }
168
169 /**
170 * Calls the {@link ComponentUI#update(Graphics, JComponent)} method for all
171 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>.
172 *
173 * @param g the graphics device.
174 * @param c the component.
175 */
176 public void update(Graphics g, JComponent c)
177 {
178 Iterator iterator = uis.iterator();
179 while (iterator.hasNext())
180 {
181 ComponentUI ui = (ComponentUI) iterator.next();
182 ui.update(g, c);
183 }
184 }
185
186 /**
187 * Calls the <code>paint(Graphics, JComponent)</code> method for all the UI
188 * delegates managed by this <code>MultiTabbedPaneUI</code>.
189 *
190 * @param g the graphics device.
191 * @param c the component.
192 */
193 public void paint(Graphics g, JComponent c)
194 {
195 Iterator iterator = uis.iterator();
196 while (iterator.hasNext())
197 {
198 ComponentUI ui = (ComponentUI) iterator.next();
199 ui.paint(g, c);
200 }
201 }
202
203 /**
204 * Calls the {@link ComponentUI#getPreferredSize(JComponent)} method for all
205 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>,
206 * returning the preferred size for the UI delegate from the primary look and
207 * feel.
208 *
209 * @param c the component.
210 *
211 * @return The preferred size returned by the UI delegate from the primary
212 * look and feel.
213 */
214 public Dimension getPreferredSize(JComponent c)
215 {
216 Dimension result = null;
217 Iterator iterator = uis.iterator();
218 // first UI delegate provides the return value
219 if (iterator.hasNext())
220 {
221 ComponentUI ui = (ComponentUI) iterator.next();
222 result = ui.getPreferredSize(c);
223 }
224 // return values from auxiliary UI delegates are ignored
225 while (iterator.hasNext())
226 {
227 ComponentUI ui = (ComponentUI) iterator.next();
228 /* Dimension ignored = */ ui.getPreferredSize(c);
229 }
230 return result;
231 }
232
233 /**
234 * Calls the {@link ComponentUI#getMinimumSize(JComponent)} method for all
235 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>,
236 * returning the minimum size for the UI delegate from the primary look and
237 * feel.
238 *
239 * @param c the component.
240 *
241 * @return The minimum size returned by the UI delegate from the primary
242 * look and feel.
243 */
244 public Dimension getMinimumSize(JComponent c)
245 {
246 Dimension result = null;
247 Iterator iterator = uis.iterator();
248 // first UI delegate provides the return value
249 if (iterator.hasNext())
250 {
251 ComponentUI ui = (ComponentUI) iterator.next();
252 result = ui.getMinimumSize(c);
253 }
254 // return values from auxiliary UI delegates are ignored
255 while (iterator.hasNext())
256 {
257 ComponentUI ui = (ComponentUI) iterator.next();
258 /* Dimension ignored = */ ui.getMinimumSize(c);
259 }
260 return result;
261 }
262
263 /**
264 * Calls the {@link ComponentUI#getMaximumSize(JComponent)} method for all
265 * the UI delegates managed by this <code>MultiTabbedPaneUI</code>,
266 * returning the maximum size for the UI delegate from the primary look and
267 * feel.
268 *
269 * @param c the component.
270 *
271 * @return The maximum size returned by the UI delegate from the primary
272 * look and feel.
273 */
274 public Dimension getMaximumSize(JComponent c)
275 {
276 Dimension result = null;
277 Iterator iterator = uis.iterator();
278 // first UI delegate provides the return value
279 if (iterator.hasNext())
280 {
281 ComponentUI ui = (ComponentUI) iterator.next();
282 result = ui.getMaximumSize(c);
283 }
284 // return values from auxiliary UI delegates are ignored
285 while (iterator.hasNext())
286 {
287 ComponentUI ui = (ComponentUI) iterator.next();
288 /* Dimension ignored = */ ui.getMaximumSize(c);
289 }
290 return result;
291 }
292
293 /**
294 * Calls the {@link ComponentUI#getAccessibleChildrenCount(JComponent)} method
295 * for all the UI delegates managed by this <code>MultiTabbedPaneUI</code>,
296 * returning the count for the UI delegate from the primary look and
297 * feel.
298 *
299 * @param c the component.
300 *
301 * @return The count returned by the UI delegate from the primary
302 * look and feel.
303 */
304 public int getAccessibleChildrenCount(JComponent c)
305 {
306 int result = 0;
307 Iterator iterator = uis.iterator();
308 // first UI delegate provides the return value
309 if (iterator.hasNext())
310 {
311 ComponentUI ui = (ComponentUI) iterator.next();
312 result = ui.getAccessibleChildrenCount(c);
313 }
314 // return values from auxiliary UI delegates are ignored
315 while (iterator.hasNext())
316 {
317 ComponentUI ui = (ComponentUI) iterator.next();
318 /* int ignored = */ ui.getAccessibleChildrenCount(c);
319 }
320 return result;
321 }
322
323 /**
324 * Calls the {@link ComponentUI#getAccessibleChild(JComponent, int)} method
325 * for all the UI delegates managed by this <code>MultiTabbedPaneUI</code>,
326 * returning the child for the UI delegate from the primary look and
327 * feel.
328 *
329 * @param c the component
330 * @param i the child index.
331 *
332 * @return The child returned by the UI delegate from the primary
333 * look and feel.
334 */
335 public Accessible getAccessibleChild(JComponent c, int i)
336 {
337 Accessible result = null;
338 Iterator iterator = uis.iterator();
339 // first UI delegate provides the return value
340 if (iterator.hasNext())
341 {
342 ComponentUI ui = (ComponentUI) iterator.next();
343 result = ui.getAccessibleChild(c, i);
344 }
345 // return values from auxiliary UI delegates are ignored
346 while (iterator.hasNext())
347 {
348 ComponentUI ui = (ComponentUI) iterator.next();
349 /* Accessible ignored = */ ui.getAccessibleChild(c, i);
350 }
351 return result;
352 }
353
354 /**
355 * Calls the {@link TabbedPaneUI#tabForCoordinate(JTabbedPane, int, int)}
356 * method for all the UI delegates managed by this
357 * <code>MultiTabbedPaneUI</code>, returning the tab index for the UI
358 * delegate from the primary look and feel.
359 *
360 * @param pane the tabbed pane.
361 * @param x the x-coordinate.
362 * @param y the y-coordinate.
363 *
364 * @return The tab index returned by the UI delegate from the primary
365 * look and feel.
366 */
367 public int tabForCoordinate(JTabbedPane pane, int x, int y)
368 {
369 int result = 0;
370 Iterator iterator = uis.iterator();
371 // first UI delegate provides the return value
372 if (iterator.hasNext())
373 {
374 TabbedPaneUI ui = (TabbedPaneUI) iterator.next();
375 result = ui.tabForCoordinate(pane, x, y);
376 }
377 // return values from auxiliary UI delegates are ignored
378 while (iterator.hasNext())
379 {
380 TabbedPaneUI ui = (TabbedPaneUI) iterator.next();
381 /* int ignored = */ ui.tabForCoordinate(pane, x, y);
382 }
383 return result;
384 }
385
386 /**
387 * Calls the {@link TabbedPaneUI#getTabBounds(JTabbedPane, int)}
388 * method for all the UI delegates managed by this
389 * <code>MultiTabbedPaneUI</code>, returning the bounds for the UI
390 * delegate from the primary look and feel.
391 *
392 * @param pane the tabbed pane.
393 * @param index the index.
394 *
395 * @return The bounds returned by the UI delegate from the primary
396 * look and feel.
397 */
398 public Rectangle getTabBounds(JTabbedPane pane, int index)
399 {
400 Rectangle result = null;
401 Iterator iterator = uis.iterator();
402 // first UI delegate provides the return value
403 if (iterator.hasNext())
404 {
405 TabbedPaneUI ui = (TabbedPaneUI) iterator.next();
406 result = ui.getTabBounds(pane, index);
407 }
408 // return values from auxiliary UI delegates are ignored
409 while (iterator.hasNext())
410 {
411 TabbedPaneUI ui = (TabbedPaneUI) iterator.next();
412 /* int ignored = */ ui.getTabRunCount(pane);
413 }
414 return result;
415 }
416
417 /**
418 * Calls the {@link TabbedPaneUI#getTabRunCount(JTabbedPane)}
419 * method for all the UI delegates managed by this
420 * <code>MultiTabbedPaneUI</code>, returning the nt for the UI
421 * delegate from the primary look and feel.
422 *
423 * @param pane the tabbed pane.
424 *
425 * @return The count returned by the UI delegate from the primary
426 * look and feel.
427 */
428 public int getTabRunCount(JTabbedPane pane)
429 {
430 int result = 0;
431 Iterator iterator = uis.iterator();
432 // first UI delegate provides the return value
433 if (iterator.hasNext())
434 {
435 TabbedPaneUI ui = (TabbedPaneUI) iterator.next();
436 result = ui.getTabRunCount(pane);
437 }
438 // return values from auxiliary UI delegates are ignored
439 while (iterator.hasNext())
440 {
441 TabbedPaneUI ui = (TabbedPaneUI) iterator.next();
442 /* int ignored = */ ui.getTabRunCount(pane);
443 }
444 return result;
445 }
446
447 }