001: package org.enhydra.shark.xpdl;
002:
003: import java.util.ArrayList;
004: import java.util.Iterator;
005:
006: /**
007: * Class that represents choice of complex elements from XML schema.
008: *
009: * @author Sasa Bojanic
010: */
011: public abstract class XMLComplexChoice extends XMLElement {
012:
013: protected ArrayList choices;
014:
015: protected XMLElement choosen;
016:
017: protected transient boolean cachesInitialized = false;
018:
019: public XMLComplexChoice(XMLComplexElement parent, String name,
020: boolean isRequired) {
021: super (parent, name, isRequired);
022: fillChoices();
023: }
024:
025: public void setValue(String v) {
026: // throw new RuntimeException("Can't set value for this type of element!");
027: }
028:
029: public void makeAs(XMLElement el) {
030: super .makeAs(el);
031:
032: XMLComplexChoice cce = (XMLComplexChoice) el;
033: int chsnind = cce.choices.indexOf(cce.getChoosen());
034: XMLElement newChsn = (XMLElement) choices.get(chsnind);
035: newChsn.makeAs(cce.getChoosen());
036: this .setChoosen(newChsn);
037: // Iterator it1=this.choices.iterator();
038: // Iterator it2=cce.choices.iterator();
039: // int chsnind=cce.choices.indexOf(cce.getChoosen());
040: //
041: // while (it1.hasNext() && it2.hasNext()) {
042: // XMLElement e1=(XMLElement)it1.next();
043: // XMLElement e2=(XMLElement)it2.next();
044: // e1.makeAs(e2);
045: // }
046: // this.setChoosen((XMLElement)choices.get(chsnind));
047:
048: }
049:
050: /**
051: * Overrides super-method to set this element and all of its
052: * choice elements read only value to the one specified.
053: */
054: public void setReadOnly(boolean ro) {
055: super .setReadOnly(ro);
056: for (int i = 0; i < choices.size(); i++) {
057: ((XMLElement) choices.get(i)).setReadOnly(ro);
058: }
059: }
060:
061: public void setNotifyListeners(boolean notify) {
062: super .setNotifyListeners(notify);
063: for (int i = 0; i < choices.size(); i++) {
064: ((XMLElement) choices.get(i)).setNotifyListeners(notify);
065: }
066: }
067:
068: public void setNotifyMainListeners(boolean notify) {
069: super .setNotifyMainListeners(notify);
070: for (int i = 0; i < choices.size(); i++) {
071: ((XMLElement) choices.get(i))
072: .setNotifyMainListeners(notify);
073: }
074: }
075:
076: /**
077: * Initializes caches in read-only mode. If mode is not read-only,
078: * throws RuntimeException.
079: */
080: public void initCaches() {
081: if (!isReadOnly) {
082: throw new RuntimeException(
083: "Caches can be initialized only in read-only mode!");
084: }
085: clearCaches();
086: Iterator it = choices.iterator();
087: while (it.hasNext()) {
088: XMLElement el = (XMLElement) it.next();
089: if (el instanceof XMLBaseForCollectionAndComplex) {
090: ((XMLBaseForCollectionAndComplex) el).initCaches();
091: } else if (el instanceof XMLComplexChoice) {
092: ((XMLComplexChoice) el).initCaches();
093: }
094: }
095: cachesInitialized = true;
096: }
097:
098: public void clearCaches() {
099: Iterator it = choices.iterator();
100: while (it.hasNext()) {
101: XMLElement el = (XMLElement) it.next();
102: if (el instanceof XMLBaseForCollectionAndComplex) {
103: ((XMLBaseForCollectionAndComplex) el).clearCaches();
104: } else if (el instanceof XMLComplexChoice) {
105: ((XMLComplexChoice) el).clearCaches();
106: }
107: }
108: cachesInitialized = false;
109: }
110:
111: public boolean isEmpty() {
112: return (choosen instanceof XMLEmptyChoiceElement);
113: }
114:
115: /**
116: * The possible choices - instances of XMLElement class.
117: *
118: * @return the possible choices for this element.
119: */
120: public ArrayList getChoices() {
121: return choices;
122: }
123:
124: public XMLElement getChoosen() {
125: return choosen;
126: }
127:
128: public void setChoosen(XMLElement ch) {
129: if (isReadOnly) {
130: throw new RuntimeException(
131: "Can't set the value of read only element!");
132: }
133: if (!choices.contains(ch)) {
134: throw new RuntimeException(
135: "Incorrect value! The possible values are: "
136: + choices);
137: }
138: boolean notify = false;
139: XMLElement oldChoosen = choosen;
140: if (this .choosen == null || !this .choosen.equals(ch)) {
141: notify = true;
142: }
143:
144: this .choosen = ch;
145:
146: if (notify && (notifyMainListeners || notifyListeners)) {
147: XMLElementChangeInfo info = createInfo(oldChoosen, choosen,
148: null, XMLElementChangeInfo.UPDATED);
149: if (notifyListeners) {
150: notifyListeners(info);
151: }
152: if (notifyMainListeners) {
153: notifyMainListeners(info);
154: }
155: }
156: }
157:
158: protected abstract void fillChoices();
159:
160: public Object clone() {
161: XMLComplexChoice d = (XMLComplexChoice) super .clone();
162:
163: d.choices = new ArrayList();
164: d.choosen = null;
165: d.cachesInitialized = false;
166: Iterator it = choices.iterator();
167: while (it.hasNext()) {
168: XMLElement c = (XMLElement) it.next();
169: XMLElement cloned = (XMLElement) c.clone();
170: d.choices.add(cloned);
171: cloned.setParent(d);
172: if (d.choosen == null && this .choosen != null
173: && this .choosen.equals(c)) {
174: d.choosen = cloned;
175: }
176: }
177: return d;
178: }
179:
180: public boolean equals(Object e) {
181: boolean equals = super .equals(e);
182: if (equals) {
183: XMLComplexChoice el = (XMLComplexChoice) e;
184: equals = (this .choices.equals(el.choices));
185: // System.out.println(" XMLComplexChoice choices equal - "+equals);
186: equals = equals
187: && !((choices == null && el.choices != null) || (choices != null && el.choices == null));
188: // System.out.println(" XMLComplexChoice choosen equal - "+equals);
189: }
190: return equals;
191: }
192:
193: }
|