001: /*
002: * @(#)PnutsLayoutMapping.java 1.2 04/12/06
003: *
004: * Copyright (c) 1997-2003 Sun Microsystems, Inc. All Rights Reserved.
005: *
006: * See the file "LICENSE.txt" for information on usage and redistribution of this file, and for a DISCLAIMER OF ALL WARRANTIES.
007: */
008:
009: package pnuts.awt;
010:
011: import java.lang.reflect.Constructor;
012: import java.lang.reflect.Method;
013: import java.awt.*;
014: import java.io.*;
015: import java.util.Stack;
016:
017: /**
018: * <a href="/pnuts/doc/PnutsLayout.html">PnutsLayout</a> mapping of <a href="/pnuts/doc/hierarchicalLayout.html">Hierarchical
019: * Layout</a>.
020: *
021: * @version 1.1
022: * @author Toyokazu Tomatsu
023: */
024: public class PnutsLayoutMapping extends Layout {
025:
026: static Class[] paramType = new Class[] { String.class };
027: Stack prototypeOfLabel = new Stack();
028:
029: private static Class jlabelClass = null;
030: private static boolean jLabelFlg = false;
031: private final static String swingPkgNames[] = {
032: "com.sun.java.swing", "javax.swing" };
033:
034: private static Class findJLabelClass(String pkgName) {
035: if (!jLabelFlg) {
036: jLabelFlg = true;
037: try {
038: jlabelClass = Class.forName(pkgName + ".JLabel");
039: return jlabelClass;
040: } catch (ClassNotFoundException e) { /* ignore */
041: }
042: }
043: return jlabelClass;
044: }
045:
046: Component getPrototypeOfLabel() {
047: if (prototypeOfLabel.size() > 0) {
048: return (Component) prototypeOfLabel.peek();
049: }
050: return null;
051: }
052:
053: Component makeLabel(String str, Container hint) {
054: try {
055: Container prototypeOfPanel = null;
056: Component prototype = getPrototypeOfLabel();
057: if (prototype != null) {
058: ByteArrayOutputStream bout = new ByteArrayOutputStream();
059: ObjectOutputStream out = new ObjectOutputStream(bout);
060: out.writeObject(prototype);
061: ByteArrayInputStream bin = new ByteArrayInputStream(
062: bout.toByteArray());
063: ObjectInputStream in = new ObjectInputStream(bin);
064: Component c = (Component) in.readObject();
065: Method m = c.getClass().getMethod("setText", paramType);
066: m.invoke(c, new Object[] { str });
067: return c;
068: } else if (hint != null) {
069: return createLabel(str, hint);
070: } else {
071: return new Label(str);
072: }
073: } catch (Exception e) {
074: throw new LayoutException("can't create Label");
075: }
076: }
077:
078: Component createLabel(String str, Component hint) {
079: String name = hint.getClass().getName();
080: Object[] params = new Object[] { str };
081: Class cl = null;
082: try {
083: int type = -1;
084: if (name.startsWith(swingPkgNames[0])) {
085: type = 0;
086: } else if (name.startsWith(swingPkgNames[1])) {
087: type = 1;
088: }
089: if (type == 0 || type == 1) {
090: cl = findJLabelClass(swingPkgNames[type]);
091: if (cl == null) {
092: cl = Label.class;
093: }
094: } else {
095: cl = Label.class;
096: }
097: Constructor con = cl.getConstructor(paramType);
098: return (Component) con.newInstance(params);
099: } catch (Exception e) {
100: throw new LayoutException("can't create Label object");
101: }
102: }
103:
104: void markLabel(Component label) {
105: if (label instanceof Label) {
106: prototypeOfLabel.setElementAt(label, prototypeOfLabel
107: .size() - 1);
108: } else {
109: try {
110: String name = label.getClass().getName();
111: Class cl = null;
112: int type = -1;
113: if (name.startsWith(swingPkgNames[0])) {
114: type = 0;
115: } else if (name.startsWith(swingPkgNames[1])) {
116: type = 1;
117: }
118: if (type == 0 || type == 1) {
119: cl = findJLabelClass(swingPkgNames[type]);
120: }
121: if (cl != null && cl.isInstance(label)) {
122: prototypeOfLabel.setElementAt(label,
123: prototypeOfLabel.size() - 1);
124: }
125: } catch (Exception e) {
126: throw new LayoutException("can't create Label");
127: }
128: }
129: }
130:
131: void initLabel(Container container) {
132: if (prototypeOfLabel.size() == 0) {
133: prototypeOfLabel.push(createLabel("", container));
134: } else {
135: prototypeOfLabel.push(prototypeOfLabel.peek());
136: }
137: }
138:
139: public Container createContainer(Container container,
140: Object[] format) {
141: initLabel(container);
142: if (!(format[1] instanceof String)) {
143: throw new LayoutException(
144: "Element after the PnutsLayout class must be a String.");
145: }
146: container.setLayout(new PnutsLayout((String) format[1]));
147: for (int i = 2; i < format.length; i++) {
148: if (format[i] == null) {
149: container.add(makePanel(container), "");
150: } else if (format[i] instanceof String) {
151: container.add(makeLabel((String) format[i], container),
152: "");
153: } else if (isArray(format[i])) {
154: Component compToAdd;
155: Object addParam;
156: Object a[] = (Object[]) format[i];
157: if (a[0] == null) {
158: compToAdd = makePanel(container);
159: addParam = a[1];
160: } else if (isArray(a[0])) {
161: compToAdd = Layout.layout(makePanel(container),
162: (Object[]) a[0]);
163: addParam = a[1];
164: } else if (a[0] instanceof Class) {
165: compToAdd = Layout.layout(makePanel(container), a);
166: addParam = "";
167: } else if (a[0] instanceof String) {
168: compToAdd = makeLabel((String) a[0], container);
169: addParam = a[1];
170: } else if (a[0] instanceof Component) {
171: compToAdd = (Component) a[0];
172: addParam = a[1];
173: markLabel(compToAdd);
174: } else {
175: throw new LayoutException(
176: "PnutsLayout requires array elements to contain a class, String, Component, array, or null.");
177: }
178:
179: container.add(compToAdd, addParam);
180:
181: if (!(a[0] instanceof Class) && a.length > 2) {
182: if (!(compToAdd instanceof Container))
183: throw new LayoutException(
184: "Component must be a Container when a third element is used: "
185: + a[0]);
186: if (!(a[2] instanceof Object[]))
187: throw new LayoutException(
188: "Third element must be an array: "
189: + a[2]);
190: Layout.layout((Container) compToAdd,
191: (Object[]) a[2]);
192: }
193:
194: } else if (format[i] instanceof Component) {
195: markLabel((Component) (format[i]));
196: container.add((Component) format[i], "");
197: } else {
198: throw new LayoutException(
199: "PnutsLayout requires elements to be a String, Component, array, or null.");
200: }
201: }
202: prototypeOfLabel.pop();
203: return container;
204: }
205: }
|