001: /*
002: ItsNat Java Web Application Framework
003: Copyright (C) 2007 Innowhere Software Services S.L., Spanish Company
004: Author: Jose Maria Arranz Santamaria
005:
006: This program is free software: you can redistribute it and/or modify
007: it under the terms of the GNU Affero General Public License as published by
008: the Free Software Foundation, either version 3 of the License, or
009: (at your option) any later version. See the GNU Affero General Public
010: License for more details. See the copy of the GNU Affero General Public License
011: included in this program. If not, see <http://www.gnu.org/licenses/>.
012: */
013:
014: package org.itsnat.impl.core.domutil;
015:
016: import org.itsnat.core.ItsNatException;
017: import org.itsnat.core.domutil.ElementLabel;
018: import org.itsnat.core.domutil.ElementLabelRenderer;
019: import org.itsnat.core.domutil.ItsNatDOMUtil;
020: import org.itsnat.impl.core.ItsNatDocumentImpl;
021: import org.w3c.dom.DocumentFragment;
022: import org.w3c.dom.Element;
023:
024: /**
025: *
026: * @author jmarranz
027: */
028: public class ElementLabelImpl extends ElementGroupImpl implements
029: ElementLabel {
030: protected Element parentElement;
031: protected ElementLabelRenderer renderer;
032: protected DocumentFragment contentPatternFragment; // Será recordado como patrón, nunca es null pero puede estar vacío
033: protected boolean usePatternMarkupToRender;
034: protected boolean hasLabel = false;
035:
036: /** Creates a new instance of ElementLabelImpl */
037: public ElementLabelImpl(ItsNatDocumentImpl itsNatDoc,
038: Element parentElement, boolean removePattern,
039: ElementLabelRenderer renderer) {
040: super (itsNatDoc);
041:
042: this .parentElement = parentElement;
043: this .renderer = renderer;
044: this .usePatternMarkupToRender = itsNatDoc
045: .isUsePatternMarkupToRender();
046:
047: if (removePattern) {
048: this .contentPatternFragment = ItsNatDOMUtilInternal
049: .extractChildrenToDocFragment(parentElement);
050: // Hasta que no se defina un value explícitamente el label está vacío
051: } else {
052: Element clonedParentElem = (Element) parentElement
053: .cloneNode(true);
054: this .contentPatternFragment = ItsNatDOMUtilInternal
055: .extractChildrenToDocFragment(clonedParentElem);
056: this .hasLabel = true; // De esta manera evitamos que se use el patrón para llenar el contenido la primera vez, pues el contenido original ya está ahí
057: // El contenido original queda como está, el patrón está clonado del original
058: // y se usará si usePatternMarkupToRender es true
059: }
060: }
061:
062: public Element getParentElement() {
063: return parentElement;
064: }
065:
066: public ElementLabelRenderer getElementLabelRenderer() {
067: return renderer;
068: }
069:
070: public void setElementLabelRenderer(ElementLabelRenderer renderer) {
071: this .renderer = renderer;
072: }
073:
074: public DocumentFragment getContentPatternFragment() {
075: return contentPatternFragment;
076: }
077:
078: public boolean hasLabelMarkup() {
079: return hasLabel;
080: }
081:
082: public void setLabelValue(Object value) {
083: if (!hasLabel) {
084: // Definido por vez primera explícitamente, en este caso
085: // inicialmente el contenido del label está vacío, lo llenamos con el pattern
086: addLabelMarkup(value);
087: } else {
088: setElementValue(value, false);
089: }
090: }
091:
092: public void setElementValue(Object value, boolean isNew) {
093: prepareRendering(isNew);
094:
095: Element parent = getParentElement();
096: ElementLabelRenderer renderer = getElementLabelRenderer();
097: if (renderer != null)
098: renderer.renderLabel(this , value, parent, isNew);
099: }
100:
101: public void addLabelMarkup() {
102: if (hasLabel)
103: throw new ItsNatException("Label already has markup");
104:
105: Element parent = getParentElement();
106: parent.appendChild(contentPatternFragment.cloneNode(true));
107: this .hasLabel = true;
108: }
109:
110: public void addLabelMarkup(Object value) {
111: addLabelMarkup();
112: setElementValue(value, true);
113: }
114:
115: public void removeLabelMarkup() {
116: Element parent = getParentElement();
117: ElementLabelRenderer renderer = getElementLabelRenderer();
118: if (renderer != null) // If null rendering disabled
119: renderer.unrenderLabel(this , parent);
120:
121: ItsNatDOMUtil.removeAllChildren(parent); // Si está ya vacío no hace nada obviamente
122: this .hasLabel = false;
123: }
124:
125: public void prepareRendering(boolean isNew) {
126: if (!isNew && isUsePatternMarkupToRender()) {
127: // Es una actualización en donde tenemos que usar el markup pattern en vez del contenido actual
128: Element parent = getParentElement();
129: restorePatternMarkupWhenRendering(parent,
130: getContentPatternFragment());
131: }
132: }
133:
134: public boolean isUsePatternMarkupToRender() {
135: return usePatternMarkupToRender;
136: }
137:
138: public void setUsePatternMarkupToRender(
139: boolean usePatternMarkupToRender) {
140: this.usePatternMarkupToRender = usePatternMarkupToRender;
141: }
142: }
|