/*
* Copyright 2003-2010 Tufts University Licensed under the
* Educational Community License, Version 2.0 (the "License"); you may
* not use this file except in compliance with the License. You may
* obtain a copy of the License at
*
* http://www.osedu.org/licenses/ECL-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an "AS IS"
* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
* or implied. See the License for the specific language governing
* permissions and limitations under the License.
*/
package tufts.vue.gui;
import java.awt.BorderLayout;
import java.awt.event.ActionListener;
import java.awt.event.MouseListener;
import tufts.vue.DEBUG;
import tufts.vue.DRBrowser;
import tufts.vue.VUE;
import javax.swing.Icon;
import javax.swing.JComponent;
//import com.sun.xml.rpc.processor.modeler.j2ee.xml.javaXmlTypeMappingType;
/**
* A convenience class for providing a wrapper for JComponents to go in
* WidgetStack's or DockWindow's.
* Most usefully this actually provides static methods so that any
* existing JComponent can be treated as a Widget (it just needs to be
* parented to a WidgetStack or DockWindow) without having to wrap it
* in a Widget / make it a subclass. This is doable because we need
* only add a few properties to the JComponent (e.g., a title,
* title-suffix) and change events can be issued to the parent via AWT
* PropertyChangeEvents (e.g., expand/collapse, hide/show).
*
* @version $Revision: 1.23 $ / $Date: 2010-02-03 19:15:47 $ / $Author: mike $
* @author Scott Fraize
*/
public class Widget extends javax.swing.JPanel
{
static final String EXPANSION_KEY = "widget.expand";
static final String HIDDEN_KEY = "widget.hide";
static final String MENU_ACTIONS_KEY = "widget.menuActions";
static final String MISC_ACTION_KEY = "widget.miscAction";
static final String MISC_ICON_KEY = "widget.miscIcon";
static final String HELP_ACTION_KEY = "widget.helpAction";
static final String REFRESH_ACTION_KEY = "widget.refreshAction";
static final String WANTS_SCROLLER_KEY = "widget.wantsScroller";
static final String WANTS_SCROLLERALWAYS_KEY = "widget.wantsScrollerAlways";
static final String TITLE_HIDDEN_KEY = "widget.titleHidden";
static final String LOADING_KEY = "widget.loading";
public static void setTitle(JComponent c, String title) {
c.setName(title);
}
public static void setTitleHidden(JComponent c, boolean hidden) {
setBoolean(c, TITLE_HIDDEN_KEY, hidden);
}
public static boolean isHidden(JComponent c)
{
Boolean currentProp = (Boolean)c.getClientProperty(HIDDEN_KEY);
boolean current = currentProp == null ? false : currentProp.booleanValue();
return current;
}
/** Hide the entire widget, including it's title. Do not affect expansion state. */
public static void setHidden(JComponent c, boolean hidden) {
// make sure instance method called in case it was overridden
if (c instanceof Widget)
((Widget)c).setHidden(hidden);
else
setHiddenImpl(c, hidden);
}
public static void show(JComponent c) {
setHidden(c, false);
}
public static void hide(JComponent c) {
setHidden(c, true);
}
protected static void setHiddenImpl(JComponent c, boolean hidden) {
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setHidden " + hidden);
setBoolean(c, HIDDEN_KEY, hidden);
}
public static void setWantsScroller(JComponent c, boolean scroller) {
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setWantsScroller " + scroller);
setBoolean(c, WANTS_SCROLLER_KEY, scroller);
}
public static void setWantsScrollerAlways(JComponent c, boolean scroller) {
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setWantsScrollerAlways " + scroller);
setBoolean(c, WANTS_SCROLLERALWAYS_KEY, scroller);
}
/** Make sure the Widget is expanded (visible). Containing java.awt.Window
* will be made visible if it's not */
public static void setExpanded(JComponent c, boolean expanded) {
// make sure instance method called in case it was overridden
if (c instanceof Widget)
((Widget)c).setExpanded(expanded);
else
setExpandedImpl(c, expanded);
}
public static boolean isExpanded(JComponent c)
{
Boolean currentProp = (Boolean)c.getClientProperty(EXPANSION_KEY);
boolean current = currentProp == null ? false : currentProp.booleanValue();
return current;
}
protected static void setExpandedImpl(JComponent c, boolean expand) {
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setExpanded " + expand);
//c.putClientProperty(EXPANSION_KEY, expanded ? Boolean.TRUE : Boolean.FALSE);
setBoolean(c, EXPANSION_KEY, expand);
// We do NOT auto-display the containing window if startup is
// underway, otherwise all sorts of stuff will show while the
// windows are being pre-configured.
if (expand && !tufts.vue.VUE.isStartupUnderway()) {
if (isBooleanTrue(c, HIDDEN_KEY) || !c.isVisible())
setHidden(c, false);
if (!DockWindow.AllWindowsHidden() && !tufts.vue.VUE.inNativeFullScreen() &&
!isBooleanTrue(c, LOADING_KEY)) {
// make sure the parent window containing us is visible:
GUI.makeVisibleOnScreen(c);
}
}
//c.firePropertyChange("TESTPROPERTY", false, true);
}
public static void setHelpAction(JComponent c, String action)
{
// if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setMenuAction " + action.toString());
c.putClientProperty(HELP_ACTION_KEY, action);
}
public static void setRefreshAction(JComponent c, MouseListener action)
{
// if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setMenuAction " + action.toString());
c.putClientProperty(REFRESH_ACTION_KEY, action);
}
public static void setMiscAction(JComponent c, MouseListener action, String icon)
{
// if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setMenuAction " + action.toString());
c.putClientProperty(MISC_ACTION_KEY, action);
c.putClientProperty(MISC_ICON_KEY, icon);
}
public static void setMenuActions(JComponent c, javax.swing.Action[] actions)
{
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setMenuActions " + java.util.Arrays.asList(actions));
c.putClientProperty(MENU_ACTIONS_KEY, actions);
}
public static boolean isWidget(JComponent c) {
return c != null && (c instanceof Widget || c.getClientProperty(EXPANSION_KEY) != null);
}
public static boolean wantsScroller(JComponent c) {
return isBooleanTrue(c, WANTS_SCROLLER_KEY);
}
public static boolean wantsScrollerAlways(JComponent c) {
return isBooleanTrue(c, WANTS_SCROLLERALWAYS_KEY);
}
/** only set property if not already set
* @return true if the value changed
*/
protected static boolean setBoolean(JComponent c, String key, boolean newValue) {
Boolean currentProp = (Boolean) c.getClientProperty(key);
// default for property value not there is false:
boolean current = currentProp == null ? false : currentProp.booleanValue();
if (current != newValue) {
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " WIDGET-CHANGE " + key + "=" + newValue);
c.putClientProperty(key, newValue ? Boolean.TRUE : Boolean.FALSE);
return true;
} else
return false;
}
protected static boolean isBooleanTrue(JComponent c, Object key) {
Boolean boolProp = (Boolean) c.getClientProperty(key);
return boolProp != null && boolProp.booleanValue();
}
// instance methods for when used as a subclassed wrapper of JPanel:
/** Create a new empty Widget JPanel, with a default layout of BorderLayout, with the given content in center */
public Widget(String title, JComponent content) {
super(new java.awt.BorderLayout());
setName(title);
if (content != null)
add(content);
if (DEBUG.BOXES) setBorder(new javax.swing.border.LineBorder(java.awt.Color.blue, 4));
}
/** Create a new empty Widget JPanel, with a default layout of BorderLayout */
public Widget(String title) {
this(title, null);
}
public Widget(String title, javax.swing.JButton blah) {
super(new java.awt.BorderLayout());
setName(title);
if (DEBUG.BOXES) setBorder(new javax.swing.border.LineBorder(java.awt.Color.blue, 4));
}
public final void setTitle(String title) {
setTitle(this, title);
}
public void setExpanded(boolean expanded) {
setExpandedImpl(this, expanded);
}
public void setHidden(boolean hidden) {
setHiddenImpl(this, hidden);
}
public final void setTitleHidden(boolean hidden) {
setTitleHidden(this, hidden);
}
public final void setMenuActions(javax.swing.Action[] actions) {
setMenuActions(this, actions);
}
public final void setWantsScroller(boolean scroller) {
setWantsScroller(this, scroller);
}
public static boolean isLoading(JComponent c)
{
Boolean currentProp = (Boolean)c.getClientProperty(LOADING_KEY);
boolean current = currentProp == null ? false : currentProp.booleanValue();
return current;
}
public static void setLoading(JComponent c, boolean loading) {
// make sure instance method called in case it was overridden
if (c instanceof Widget)
((Widget)c).setLoading(loading);
else
setLoadingImpl(c, loading);
}
protected static void setLoadingImpl(JComponent c, boolean loading) {
if (DEBUG.WIDGET) System.out.println(GUI.name(c) + " Widget.setLoading " + loading);
setBoolean(c, LOADING_KEY, loading);
}
public void setLoading(boolean loading) {
setLoadingImpl(this, loading);
}
}