001: package org.enhydra.shark.xpdl;
002:
003: import java.util.ArrayList;
004: import java.util.Iterator;
005:
006: import org.enhydra.shark.utilities.SequencedHashMap;
007:
008: /**
009: * Class that represents complex element from XML schema.
010: *
011: * @author Sasa Bojanic
012: */
013: public abstract class XMLComplexElement extends
014: XMLBaseForCollectionAndComplex {
015:
016: public XMLComplexElement(XMLElement parent, boolean isRequired) {
017: super (parent, isRequired);
018: fillStructure();
019: }
020:
021: public XMLComplexElement(XMLElement parent, String name,
022: boolean isRequired) {
023: super (parent, name, isRequired);
024: fillStructure();
025: }
026:
027: public void makeAs(XMLElement el) {
028: if (!(el != null && el.getClass().equals(this .getClass()) && el
029: .toName().equals(this .toName()))) {
030: throw new RuntimeException("Can't perform makeAs!");
031: }
032: //System.err.println("Performing make as for element "+el.toName()+", pkg="+getMainElement().hashCode()+", mapkg="+el.getMainElement().hashCode()+", notifml="+notifyMainListeners);
033: XMLComplexElement ce = (XMLComplexElement) el;
034: Iterator it1 = this .elements.iterator();
035: Iterator it2 = ce.elements.iterator();
036: while (it1.hasNext() && it2.hasNext()) {
037: XMLElement e1 = (XMLElement) it1.next();
038: XMLElement e2 = (XMLElement) it2.next();
039: e1.makeAs(e2);
040: }
041:
042: }
043:
044: protected void add(XMLElement el) {
045: elements.add(el);
046: elementMap.put(el.toName(), el);
047: }
048:
049: protected boolean add(int no, XMLElement el) {
050: if (no < 0 || no > size())
051: return false;
052: elements.add(no, el);
053: // here, we don't care about position
054: elementMap.put(el.toName(), el);
055: return true;
056: }
057:
058: /**
059: * It is empty if its value is not set, and if
060: * all elements in the structure are empty.
061: */
062: public boolean isEmpty() {
063: boolean isEmpty = true;
064: Iterator it = elements.iterator();
065: while (it.hasNext()) {
066: XMLElement el = (XMLElement) it.next();
067: isEmpty = isEmpty && el.isEmpty();
068: }
069: isEmpty = isEmpty && value.trim().length() == 0;
070: return isEmpty;
071: }
072:
073: /**
074: * Returns the collection of XML elements this element is made of.
075: */
076: public ArrayList getXMLElements() {
077: ArrayList els = new ArrayList();
078: Iterator it = elements.iterator();
079: while (it.hasNext()) {
080: Object el = it.next();
081: if (!(el instanceof XMLAttribute)) {
082: els.add(el);
083: }
084: }
085: return els;
086: }
087:
088: /**
089: * Returns the collection of XML attributes this element is made of.
090: */
091: public ArrayList getXMLAttributes() {
092: ArrayList attribs = new ArrayList();
093: Iterator it = elements.iterator();
094: while (it.hasNext()) {
095: Object el = it.next();
096: if (el instanceof XMLAttribute) {
097: attribs.add(el);
098: }
099: }
100: return attribs;
101: }
102:
103: /**
104: * Sets the element from structure with specified name to
105: * the specified value.
106: */
107: public void set(String name, String value) {
108: if (isReadOnly) {
109: throw new RuntimeException(
110: "Can't change element from read only structure!");
111: }
112: XMLElement el = get(name);
113: if (el != null) {
114: el.setValue(value);
115: } else {
116: throw new RuntimeException("No such element!");
117: }
118: }
119:
120: /**
121: * Sets the element that is placed at specified location within structure
122: * to the specified value.
123: */
124: public boolean set(int no, String value) {
125: if (no < 0 || no >= size())
126: return false;
127: if (isReadOnly) {
128: throw new RuntimeException(
129: "Can't change element from read only structure!");
130: }
131:
132: XMLElement el = get(no);
133: el.setValue(value);
134: return true;
135: }
136:
137: /** Gets the element with specified name from stucture. */
138: public XMLElement get(String name) {
139: return (XMLElement) elementMap.get(name);
140: }
141:
142: /** Returns true if there is an element with such element in structure. */
143: public boolean containsName(String name) {
144: return elementMap.containsKey(name);
145: }
146:
147: /**
148: * The classes that are derived from this class has to give its
149: * definition for this method. It is used to insert all members
150: * of those classes that are derived from XMLElement.
151: * <p>NOTE: The order of inserted elements is relevant for XML to be
152: * valid (members of classes derived from this class must be
153: * inserted into first mentioned list in the same order that
154: * they are within a corresponding tag for those classes
155: * within WfMC XML).
156: */
157: protected abstract void fillStructure();
158:
159: public Object clone() {
160: XMLComplexElement d = (XMLComplexElement) super .clone();
161: d.elements = new ArrayList();
162: d.elementMap = new SequencedHashMap();
163: d.cachesInitialized = false;
164: Iterator it = elements.iterator();
165: while (it.hasNext()) {
166: XMLElement el = (XMLElement) it.next();
167: XMLElement cl = (XMLElement) el.clone();
168: cl.setParent(d);
169: d.elements.add(cl);
170: d.elementMap.put(cl.toName(), cl);
171: }
172: return d;
173: }
174:
175: }
|