1 16 package org.apache.cocoon.forms.formmodel; 17 18 import java.util.ArrayList ; 19 import java.util.HashMap ; 20 import java.util.Iterator ; 21 import java.util.List ; 22 import java.util.Locale ; 23 import java.util.Map ; 24 25 import org.apache.cocoon.forms.FormsConstants; 26 import org.apache.cocoon.forms.event.CreateEvent; 27 import org.apache.cocoon.forms.event.ValueChangedListenerEnabled; 28 import org.apache.cocoon.forms.event.WidgetEvent; 29 import org.apache.cocoon.forms.validation.ValidationErrorAware; 30 import org.apache.cocoon.forms.validation.WidgetValidator; 31 import org.apache.cocoon.util.location.Location; 32 import org.apache.cocoon.xml.AttributesImpl; 33 import org.xml.sax.ContentHandler ; 34 import org.xml.sax.SAXException ; 35 36 42 public abstract class AbstractWidget implements Widget { 43 44 49 private Widget parent; 50 51 54 private WidgetState state = WidgetState.ACTIVE; 55 56 59 private Form form; 60 61 64 private List validators; 65 66 69 private Map attributes; 70 71 74 protected boolean wasValid = true; 75 76 77 protected AbstractWidget(AbstractWidgetDefinition definition) { 78 this.state = definition.getState(); 79 } 80 81 86 public void initialize() { 87 ((AbstractWidgetDefinition)getDefinition()).widgetCreated(this); 88 } 89 90 93 public String getId() { 94 return getDefinition().getId(); 95 } 96 97 public String getName() { 98 return getId(); 99 } 100 101 113 public abstract WidgetDefinition getDefinition(); 114 115 119 public Location getLocation() { 120 return getDefinition().getLocation(); 121 } 122 123 126 public final Widget getParent() { 128 return this.parent; 129 } 130 131 138 public void setParent(Widget widget) { 139 if (this.parent != null) { 140 throw new IllegalStateException ("The parent of widget " + getRequestParameterName() + " should only be set once."); 141 } 142 this.parent = widget; 143 } 144 145 148 public Form getForm() { 149 if (this.form == null) { 150 Widget myParent = getParent(); 151 if (myParent == null) { 152 this.form = (Form)this; 153 } else { 154 this.form = myParent.getForm(); 155 } 156 } 157 return this.form; 158 } 159 160 public WidgetState getState() { 161 return this.state; 162 } 163 164 public void setState(WidgetState state) { 165 if (state == null) { 166 throw new IllegalArgumentException ("A widget state cannot be set to null"); 167 } 168 this.state = state; 169 170 getForm().addWidgetUpdate(this); 172 } 173 174 public WidgetState getCombinedState() { 175 if (this.parent == null) { 176 return this.state; 177 } 178 return WidgetState.strictest(this.state, this.parent.getCombinedState()); 179 } 180 181 private String cachedParentParamName; 184 private String cachedParamName; 185 186 190 protected void widgetNameChanged() { 191 this.cachedParentParamName = null; 192 this.cachedParamName = null; 193 } 194 195 public String getFullName() { 196 return getRequestParameterName(); 197 } 198 199 public String getRequestParameterName() { 200 201 if (this.parent == null) { 202 return getId(); 203 } 204 205 String parentParamName = parent.getRequestParameterName(); 206 if (parentParamName == this.cachedParentParamName) { 207 return this.cachedParamName; 209 } 210 211 this.cachedParentParamName = parentParamName; 213 if (this.cachedParentParamName.length() == 0) { 214 this.cachedParamName = getId(); 216 } else { 217 this.cachedParamName = this.cachedParentParamName + "." + getId(); 218 } 219 220 return this.cachedParamName; 221 } 222 223 public Widget lookupWidget(String path) { 224 225 if (path == null || path.equals("")) { 226 return this; 227 } 228 229 Widget relativeWidget; 230 String relativePath = null; 231 int sepPosition = path.indexOf("" + Widget.PATH_SEPARATOR); 232 233 if (sepPosition < 0) { 234 if (path.startsWith("..")) return getParent(); 236 return getChild(path); 237 } else if (sepPosition == 0) { 238 relativeWidget = getForm(); 240 relativePath = path.substring(1); 241 } else { 242 if (path.startsWith(".." + Widget.PATH_SEPARATOR)) { 243 relativeWidget = getParent(); 244 relativePath = path.substring(3); 245 } else { 246 String childId = path.substring(0, sepPosition ); 247 relativeWidget = getChild(childId); 248 relativePath = path.substring(sepPosition+1); 249 } 250 } 251 252 if (relativeWidget == null) return null; 253 return relativeWidget.lookupWidget(relativePath); 254 } 255 256 263 protected Widget getChild(String id) { 264 return null; 265 } 266 267 public Widget getWidget(String id) { 268 throw new UnsupportedOperationException ("getWidget(id) got deprecated from the API. \n" + 269 "Consider using getChild(id) or even lookupWidget(path) instead."); 270 } 271 272 public Object getValue() { 273 throw new UnsupportedOperationException ("Widget " + toString() + " has no value, at " + getLocation()); 274 } 275 276 public void setValue(Object object) { 277 throw new UnsupportedOperationException ("Widget " + toString() + " has no value, at " + getLocation()); 278 } 279 280 public boolean isRequired() { 281 return false; 282 } 283 284 290 public void broadcastEvent(WidgetEvent event) { 291 if (event instanceof CreateEvent) { 292 ((AbstractWidgetDefinition)getDefinition()).fireCreateEvent((CreateEvent)event); 293 } else { 294 throw new UnsupportedOperationException ("Widget " + this.getRequestParameterName() + " doesn't handle events."); 295 } 296 } 297 298 303 public void addValidator(WidgetValidator validator) { 304 if (this.validators == null) { 305 this.validators = new ArrayList (); 306 } 307 this.validators.add(validator); 308 } 309 310 316 public boolean removeValidator(WidgetValidator validator) { 317 if (this.validators != null) { 318 return this.validators.remove(validator); 319 } 320 return false; 321 } 322 323 326 public boolean validate() { 327 if (!getCombinedState().isValidatingValues()) { 329 this.wasValid = true; 330 return true; 331 } 332 333 if (!getDefinition().validate(this)) { 335 this.wasValid = false; 337 return false; 338 } 339 if (this.validators != null) { 341 Iterator iter = this.validators.iterator(); 342 while(iter.hasNext()) { 343 WidgetValidator validator = (WidgetValidator)iter.next(); 344 if (!validator.validate(this)) { 345 this.wasValid = false; 346 return false; 347 } 348 } 349 } 350 351 353 if (this instanceof ValidationErrorAware) { 354 ((ValidationErrorAware)this).setValidationError(null); 356 } 357 358 this.wasValid = true; 359 return true; 360 } 361 362 365 public boolean isValid() { 366 return this.wasValid; 367 } 368 369 381 public void generateLabel(ContentHandler contentHandler) throws SAXException { 382 if (getCombinedState().isDisplayingValues()) { 383 getDefinition().generateDisplayData("label", contentHandler); 384 } 385 } 386 387 398 protected void generateItemSaxFragment(ContentHandler contentHandler, Locale locale) throws SAXException { 399 } 401 402 408 protected abstract String getXMLElementName(); 409 410 424 protected AttributesImpl getXMLElementAttributes() { 425 AttributesImpl attrs = new AttributesImpl(); 426 if (getId().length() != 0) { 429 attrs.addCDATAAttribute("id", getRequestParameterName()); 430 } 431 432 WidgetState state = getCombinedState(); 434 if (state != WidgetState.ACTIVE) { 435 attrs.addCDATAAttribute("state", getCombinedState().getName()); 436 } 437 438 if (this instanceof ValueChangedListenerEnabled && 440 ((ValueChangedListenerEnabled)this).hasValueChangedListeners()) { 441 attrs.addCDATAAttribute("listening", "true"); 442 } 443 return attrs; 444 } 445 446 458 protected void generateDisplayData(ContentHandler contentHandler) throws SAXException { 459 getDefinition().generateDisplayData(contentHandler); 460 } 461 462 483 public void generateSaxFragment(ContentHandler contentHandler, Locale locale) 484 throws SAXException { 485 486 if (getCombinedState().isDisplayingValues()) { 487 String element = this.getXMLElementName(); 489 AttributesImpl attrs = getXMLElementAttributes(); 490 contentHandler.startElement(FormsConstants.INSTANCE_NS, element, FormsConstants.INSTANCE_PREFIX_COLON + element, attrs); 491 492 generateDisplayData(contentHandler); 493 494 if (locale == null) { 495 locale = getForm().getLocale(); 496 } 497 498 generateItemSaxFragment(contentHandler, locale); 499 500 contentHandler.endElement(FormsConstants.INSTANCE_NS, element, FormsConstants.INSTANCE_PREFIX_COLON + element); 501 502 } else { 503 AttributesImpl attrs = new AttributesImpl(); 505 attrs.addCDATAAttribute("id", getRequestParameterName()); 506 contentHandler.startElement(FormsConstants.INSTANCE_NS, "placeholder", FormsConstants.INSTANCE_PREFIX_COLON + "placeholder", attrs); 507 contentHandler.endElement(FormsConstants.INSTANCE_NS, "placeholder", FormsConstants.INSTANCE_PREFIX_COLON + "placeholder"); 508 } 509 } 510 511 public Object getAttribute(String name) { 512 Object result = null; 513 514 if (this.attributes != null) { 516 result = this.attributes.get(name); 517 } 518 519 if (result == null) { 521 result = getDefinition().getAttribute(name); 522 } 523 524 return result; 525 } 526 527 public void setAttribute(String name, Object value) { 528 if (this.attributes == null) { 529 this.attributes = new HashMap (); 530 } 531 this.attributes.put(name, value); 532 } 533 534 public void removeAttribute(String name) { 535 if (this.attributes != null) { 536 this.attributes.remove(name); 537 } 538 } 539 540 public String toString() { 541 String className = this.getClass().getName(); 542 int last = className.lastIndexOf('.'); 543 if (last != -1) { 544 className = className.substring(last+1); 545 } 546 547 String name = getRequestParameterName(); 548 return name.length() == 0 ? className : className + " '" + getRequestParameterName() + "'"; 549 } 550 } 551 | Popular Tags |