KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > blandware > atleap > webapp > taglib > core > content > ContentTag


1 /*
2  * Copyright 2004 Blandware (http://www.blandware.com)
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package com.blandware.atleap.webapp.taglib.core.content;
17
18 import com.blandware.atleap.common.Constants;
19 import com.blandware.atleap.common.util.ConvertUtil;
20 import com.blandware.atleap.common.util.StringUtil;
21 import com.blandware.atleap.model.core.ContentField;
22 import com.blandware.atleap.model.core.ContentFieldValue;
23 import com.blandware.atleap.model.core.Page;
24 import com.blandware.atleap.service.core.ContentFieldManager;
25 import com.blandware.atleap.service.core.PageManager;
26 import com.blandware.atleap.webapp.struts.ContentTilesRequestProcessor;
27 import com.blandware.atleap.webapp.struts.HeritableComponentDefinition;
28 import com.blandware.atleap.webapp.taglib.core.util.ContextMenuItem;
29 import com.blandware.atleap.webapp.taglib.core.util.JavaScriptUtil;
30 import com.blandware.atleap.webapp.util.core.ApplicationResources;
31 import com.blandware.atleap.webapp.util.core.CacheUtil;
32 import com.blandware.atleap.webapp.util.core.WebappConstants;
33 import com.blandware.atleap.webapp.util.core.WebappUtil;
34 import org.apache.commons.logging.Log;
35 import org.apache.commons.logging.LogFactory;
36 import org.apache.commons.validator.GenericValidator;
37 import org.apache.struts.Globals;
38 import org.apache.struts.taglib.TagUtils;
39 import org.apache.struts.tiles.ComponentDefinition;
40 import org.apache.struts.tiles.TilesUtil;
41 import org.springframework.context.ApplicationContext;
42 import org.springframework.web.context.support.WebApplicationContextUtils;
43
44 import javax.servlet.ServletContext JavaDoc;
45 import javax.servlet.http.HttpServletRequest JavaDoc;
46 import javax.servlet.jsp.JspTagException JavaDoc;
47 import javax.servlet.jsp.PageContext JavaDoc;
48 import javax.servlet.jsp.tagext.SimpleTagSupport JavaDoc;
49 import java.util.Arrays JavaDoc;
50 import java.util.Locale JavaDoc;
51
52 // TODO: get/put localizable field value from/in cache
53

54 /**
55  * <p>Tag used to include content field value from database by identifier. It may
56  * also be highlighted in edit mode when a mouse is over it and may be edited
57  * through context menu or double click. Context menu gives ability to edit
58  * content field value for current locale (this is what user gets when he
59  * double-clicks on content), for all locales or for selected locales only.</p>
60  * <p>
61  * If edit mode is on, <b>editable</b> is "true" (or omitted) and CFV couldn't
62  * be found or empty, then message like "The field value is empty, please insert
63  * the text" will be treated as result.
64  * </p>
65  * <p>
66  * Note, that when this tag looks for a field through definitions, it ALWAYS
67  * skips starting definition. So, if you have a parent_definition and
68  * child_definition and <b>definition</b> attribute is set to be
69  * 'child_definition' (or this is definition on which current page is based),
70  * then only fields from parent_definition and its parents will be considered
71  * when obtaining content.
72  * </p>
73  * <p>
74  * Allowed attributes are:
75  * <ul>
76  * <li>
77  * <b>identifier</b> - mandatory identifier of the content field
78  * </li>
79  * <li>
80  * <b>uri</b> - URI of the page in database. By default it is URI of currently processed page.
81  * </li>
82  * <li>
83  * <b>definition</b> - Definition name of some layout. By default it is definition of currently processed page.
84  * </li>
85  * <li>
86  * <b>locale</b> - By default locale is taken from session
87  * </li>
88  * <li>
89  * <b>ignore</b> - "true" if you do not want to issue an error message when content was not found,
90  * default is "false"
91  * </li>
92  * <li>
93  * <b>filter</b> - whether or not to replace characters, which are sensitive in
94  * HTML, with their entity equivalents. If not specified, then data will be
95  * filtered only if field type is not <code>ContentField.HTML_TYPE</code>.
96  * </li>
97  * <li>
98  * <b>contextMenuJsp</b> - optional - path to JSP which will render a context menu. If not
99  * given, <code>WebappConstants.DEFAULT_CONTEXT_MENU_JSP</code> is used.
100  * </li>
101  * <li>
102  * <b>showEmpty</b> - If "true", empty content will be shown, otherwise it will be
103  * searched further in sequence of layouts (from child to parent). If not
104  * specified, then this is treated as "true" if and only if field type is not
105  * <code>ContentField.LINE_TYPE</code>.
106  * </li>
107  * <li>
108  * <b>var</b> - name of variable that will accept the result
109  * </li>
110  * <li>
111  * <b>scope</b> - scope of variable that will accept the result
112  * </li>
113  * <li>
114  * <b>index</b> - field index if this tag is used used inside
115  * <em>contentIterator</em> tag.
116  * </li>
117  * <li>
118  * <b>editable</b> - whether this content field value is editable by user in
119  * edit mode, default is "true"
120  * </li>
121  * </ul>
122  * <p>This can be used only on pages processed by action using tile definition.</p>
123  * <p>
124  * Here's an example:
125  * <pre>
126  * &lt;atleap:contentIterator identifier="leftBlock" index="index"&gt;
127  * &lt;div class="block"&gt;
128  * &lt;atleap:content identifier="leftBlock" index="${index}"/&gt;
129  * &lt;/div&gt;
130  * &lt;/atleap:contentIterator&gt;
131  * </pre>
132  * It will render content field values that belong to indexed field with
133  * identifier "leftBlock", which is owned by current page or its layout for
134  * current content locale.
135  * </p>
136  * <p><a HREF="ContentTag.java.htm"><i>View Source</i></a></p>
137  * <p/>
138  *
139  * @author Andrey Grebnev <a HREF="mailto:andrey.grebnev@blandware.com">&lt;andrey.grebnev@blandware.com&gt;</a>
140  * @author Sergey Zubtcovskii <a HREF="mailto:sergey.zubtcovskii@blandware.com">&lt;sergey.zubtcovskii@blandware.com&gt;</a>
141  * @version $Revision: 1.45 $ $Date: 2006/03/17 16:13:33 $
142  * @jsp.tag name="content"
143  * body-content="empty"
144  */

145 public class ContentTag extends SimpleTagSupport JavaDoc {
146
147     protected transient final Log log = LogFactory.getLog(ContentTag.class);
148     protected ApplicationContext applicationCtx = null;
149     protected static final String JavaDoc NUMBER_KEY = "com.blandware.atleap.taglib.content.CONTENT_TAG_NUMBER";
150
151     /**
152      * Name of variable to export field value
153      */

154     protected String JavaDoc var;
155
156     /**
157      * Scope to export variable to
158      */

159     protected String JavaDoc scope;
160     /**
161      * Mandatory identifier of the content field
162      */

163     protected String JavaDoc identifier = null;
164     /**
165      * Definition name of some layout. By default it is definition of currently processed page.
166      */

167     protected String JavaDoc definition = null;
168     /**
169      * URI of the page in database. By default it is URI of currently processed page.
170      */

171     protected String JavaDoc uri = null;
172     /**
173      * By default locale is taken from session
174      */

175     protected String JavaDoc locale = null;
176     /**
177      * Field index if this tag is used used inside <em>contentIterator</em> tag.
178      */

179     protected String JavaDoc index = null;
180     /**
181      * "true" if you do not want to issue an error message when content was not found,
182      * default is "false"
183      */

184     protected Boolean JavaDoc ignore = Boolean.FALSE;
185     /**
186      * Path to JSP which will render a context menu. If not
187      * given, <code>WebappConstants.DEFAULT_CONTEXT_MENU_JSP</code> is used.
188      */

189     protected String JavaDoc contextMenuJsp = null;
190
191
192     /**
193      * If <code>true</code> empty content will be shown, otherwise it will be searched in sequence of layouts
194      */

195     protected Boolean JavaDoc showEmpty;
196
197     /**
198      * Whether or not to replace characters, which are sensitive in HTML, with their entity equivalents.<br />
199      */

200     protected Boolean JavaDoc filter = null;
201
202     /**
203      * If this value is <code>Boolean.TRUE</code> content will be wrapped in &lt;span&gt;&lt;/span&gt; tags
204      * to provide access to editing content while in edit mode.
205      */

206     protected Boolean JavaDoc editable = Boolean.TRUE;
207
208     /**
209      * Returns identifier of the field
210      *
211      * @return identifier of the field
212      * @jsp.attribute required="true"
213      * rtexprvalue="true"
214      * type="java.lang.String"
215      * description="Identifier of the field"
216      */

217     public String JavaDoc getIdentifier() {
218         return identifier;
219     }
220
221     /**
222      * Sets identifier of the field
223      *
224      * @param identifier identifier of the field to set
225      */

226     public void setIdentifier(String JavaDoc identifier) {
227         this.identifier = identifier;
228     }
229
230     /**
231      * Returns URI of page to which the field belongs
232      *
233      * @return URI of page
234      * @jsp.attribute required="false"
235      * rtexprvalue="true"
236      * type="java.lang.String"
237      * description="URI of the page in database. By default it is uri of current processed page."
238      */

239     public String JavaDoc getUri() {
240         return uri;
241     }
242
243     /**
244      * Sets URI of page to which the field belongs
245      *
246      * @param uri URI of page to set
247      */

248     public void setUri(String JavaDoc uri) {
249         this.uri = uri;
250     }
251
252     /**
253      * Returns tiles definition name to which the field belongs
254      *
255      * @return tiles definition name to which the field belongs
256      * @jsp.attribute required="false"
257      * rtexprvalue="true"
258      * type="java.lang.String"
259      * description="Definition name in database. By default it is definition of current processed page."
260      */

261     public String JavaDoc getDefinition() {
262         return definition;
263     }
264
265     /**
266      * Sets tiles definition name to which the field belongs
267      *
268      * @param definition tiles definition name to set
269      */

270     public void setDefinition(String JavaDoc definition) {
271         this.definition = definition;
272     }
273
274     /**
275      * Returns whether to ignore search errors
276      *
277      * @return whether to ignore search errors
278      * @jsp.attribute required="false"
279      * rtexprvalue="true"
280      * type="java.lang.Boolean"
281      * description="If it is true then search errors will be ignored"
282      */

283     public Boolean JavaDoc getIgnore() {
284         return ignore;
285     }
286
287     /**
288      * Sets whether to ignore search errors
289      *
290      * @param ignore whether to ignore search errors
291      */

292     public void setIgnore(Boolean JavaDoc ignore) {
293         this.ignore = ignore;
294     }
295
296     /**
297      * Returns whether to show empty value
298      *
299      * @return whether to show empty value
300      * @see #showEmpty
301      * @jsp.attribute required="false"
302      * rtexprvalue="true"
303      * type="java.lang.Boolean"
304      * description="If true empty content will be shown, otherwise it will be searched in sequence of layouts "
305      */

306     public Boolean JavaDoc getShowEmpty() {
307         return showEmpty;
308     }
309
310     /**
311      * Sets whether to show empty value
312      *
313      * @param showEmpty whether to show empty value
314      * @see #showEmpty
315      */

316     public void setShowEmpty(Boolean JavaDoc showEmpty) {
317         this.showEmpty = showEmpty;
318     }
319
320     /**
321      * Returns whether or not to replace characters, which are sensitive in
322      * HTML, with their entity equivalents.
323      *
324      * @return whether or not to replace characters, which are sensitive in HTML
325      * @jsp.attribute required="false"
326      * rtexprvalue="true"
327      * type="java.lang.Boolean"
328      * description="Whether or not to replace characters, which are sensitive in HTML, with their entity equivalents"
329      */

330     public Boolean JavaDoc getFilter() {
331         return filter;
332     }
333
334     /**
335      * Sets whether or not to replace characters, which are sensitive in HTML,
336      * with their entity equivalents.
337      *
338      * @param filter whether or not to replace characters, which are sensitive in HTML
339      */

340     public void setFilter(Boolean JavaDoc filter) {
341         this.filter = filter;
342     }
343
344     /**
345      * Returns locale for which to obtain CFV
346      *
347      * @return locale
348      * @jsp.attribute required="false"
349      * rtexprvalue="true"
350      * type="java.lang.Boolean"
351      * description="By default locale is used form session"
352      */

353     public String JavaDoc getLocale() {
354         return locale;
355     }
356
357     /**
358      * Sets locale for which to obtain CFV
359      *
360      * @param locale locale to set
361      */

362     public void setLocale(String JavaDoc locale) {
363         this.locale = locale;
364     }
365
366     /**
367      * Returns name of variable that will accept the result
368      *
369      * @return name of variable
370      * @jsp.attribute required="false"
371      * rtexprvalue="true"
372      * type="java.lang.String"
373      * description="Name of variable to export message"
374      */

375     public String JavaDoc getVar() {
376         return var;
377     }
378
379     /**
380      * Sets name of variable that will accept the result
381      *
382      * @param var name of variable to set
383      */

384     public void setVar(String JavaDoc var) {
385         this.var = var;
386     }
387
388     /**
389      * Returns variable scope
390      *
391      * @return variable scope
392      * @jsp.attribute required="false"
393      * rtexprvalue="true"
394      * type="java.lang.String"
395      * description="Scope to export variable to"
396      */

397     public String JavaDoc getScope() {
398         return scope;
399     }
400
401     /**
402      * Sets variable scope
403      *
404      * @param scope variable scope to set
405      */

406     public void setScope(String JavaDoc scope) {
407         this.scope = scope;
408     }
409
410     /**
411      * Returns field index
412      *
413      * @return field index
414      * @jsp.attribute required="false"
415      * rtexprvalue="true"
416      * type="java.lang.String"
417      * description="Index if this tag is used used inside ContentIterator"
418      */

419     public String JavaDoc getIndex() {
420         return index;
421     }
422
423     /**
424      * Sets field index
425      *
426      * @param index field index to set
427      */

428     public void setIndex(String JavaDoc index) {
429         this.index = index;
430     }
431
432     /**
433      * Returns whether this value will be editable by user
434      *
435      * @return whether this value will be editable by user
436      * @see #editable
437      * @jsp.attribute required="false"
438      * rtexprvalue="true"
439      * type="java.lang.Boolean"
440      * description="Is content editable or not"
441      */

442     public Boolean JavaDoc getEditable() {
443         return editable;
444     }
445
446     /**
447      * Sets whether this value will be editable by user
448      *
449      * @param editable whether this value will be editable by user
450      * @see #editable
451      */

452     public void setEditable(Boolean JavaDoc editable) {
453         this.editable = editable;
454     }
455
456     /**
457      * Returns address of JSP that will be used to render a context menu
458      *
459      * @return address of JSP for context menu
460      * @jsp.attribute required="false"
461      * rtexprvalue="true"
462      * type="java.lang.String"
463      * description="Path to JSP which will render a context menu"
464      */

465     public String JavaDoc getContextMenuJsp() {
466         return contextMenuJsp;
467     }
468
469     /**
470      * Sets address of JSP that will be used to render a context menu
471      *
472      * @param contextMenuJsp address of JSP for context menu to set
473      */

474     public void setContextMenuJsp(String JavaDoc contextMenuJsp) {
475         this.contextMenuJsp = contextMenuJsp;
476     }
477
478     /**
479      * Processes the tag
480      *
481      * @throws JspTagException
482      */

483     public void doTag() throws JspTagException JavaDoc {
484
485         PageContext JavaDoc pageContext = (PageContext JavaDoc) getJspContext();
486
487         HttpServletRequest JavaDoc request = (HttpServletRequest JavaDoc) pageContext.getRequest();
488         ApplicationResources applicationResources = ApplicationResources.getInstance(pageContext.getServletContext());
489         ServletContext JavaDoc servletContext = pageContext.getServletContext();
490
491         if ( ignore == null ) {
492             ignore = Boolean.FALSE;
493         }
494
495         if ( applicationCtx == null ) {
496             applicationCtx = WebApplicationContextUtils.getRequiredWebApplicationContext(pageContext.getServletContext());
497         }
498
499         if ( index != null && index.trim().length() > 0 ) {
500             identifier = identifier + "[" + index + "]";
501         }
502
503         // calculate tag number
504
Integer JavaDoc tagNumber = (Integer JavaDoc) pageContext.getAttribute(NUMBER_KEY, PageContext.REQUEST_SCOPE);
505         if ( tagNumber == null ) {
506             tagNumber = new Integer JavaDoc(0);
507         } else {
508             tagNumber = new Integer JavaDoc(tagNumber.intValue() + 1);
509         }
510
511         pageContext.setAttribute(NUMBER_KEY, tagNumber, PageContext.REQUEST_SCOPE);
512
513         //get locale
514
if ( locale == null ) {
515             Locale JavaDoc l = (Locale JavaDoc) pageContext.getAttribute(Globals.LOCALE_KEY, PageContext.SESSION_SCOPE);
516             if ( l != null ) {
517                 locale = l.getLanguage();
518             }
519         }
520         if ( locale == null ) {
521             locale = Locale.getDefault().getLanguage();
522         }
523
524         // get definition
525
if ( definition != null ) {
526             ComponentDefinition tmpDef = null;
527             try {
528                 tmpDef = TilesUtil.getDefinition(definition, request, servletContext);
529             } catch ( Exception JavaDoc ex ) {
530                 //do nothing
531
}
532             if ( tmpDef == null ) {
533                 if ( ignore.booleanValue() ) {
534                     return;
535                 }
536                 String JavaDoc errorMessage = "Specified definition '" + definition + "' has not been found";
537                 JspTagException JavaDoc e = new JspTagException JavaDoc(errorMessage);
538                 throw e;
539             }
540         } else {
541             definition = (String JavaDoc) pageContext.getAttribute(ContentTilesRequestProcessor.DEFINITION_NAME, PageContext.REQUEST_SCOPE);
542         }
543         if ( definition == null ) {
544             if ( ignore.booleanValue() ) {
545                 return;
546             }
547             String JavaDoc errorMessage = "DEFINITION_NAME attribute has not been found in request. This can be used only on pages processed by action using tile definition.";
548             JspTagException JavaDoc e = new JspTagException JavaDoc(errorMessage);
549             throw e;
550         }
551
552         //get uri
553
if ( uri != null ) {
554             PageManager pageManager = (PageManager) applicationCtx.getBean(Constants.PAGE_MANAGER_BEAN);
555             Page page = pageManager.findPageByUri(uri);
556             if ( page == null ) {
557                 if ( ignore.booleanValue() ) {
558                     return;
559                 }
560                 String JavaDoc errorMessage = "Specified page uri '" + uri + "' has not been found";
561                 JspTagException JavaDoc e = new JspTagException JavaDoc(errorMessage);
562                 throw e;
563             }
564         } else {
565             uri = (String JavaDoc) pageContext.getAttribute(ContentTilesRequestProcessor.PROCESSED_URI, PageContext.REQUEST_SCOPE);
566         }
567
568         if ( uri == null ) {
569             if ( ignore.booleanValue() ) {
570                 return;
571             }
572             String JavaDoc errorMessage = "PROCESSED_URI attribute has not been found in request. This can be used only on pages processed by action using tile definition.";
573             JspTagException JavaDoc e = new JspTagException JavaDoc(errorMessage);
574             throw e;
575         }
576
577         // save definition and uri for later usage
578
String JavaDoc savedDefinition = new String JavaDoc(definition);
579         String JavaDoc savedUri = new String JavaDoc(uri);
580
581         TagUtils tagUtils = TagUtils.getInstance();
582         if ( GenericValidator.isBlankOrNull(contextMenuJsp) ) {
583             contextMenuJsp = WebappConstants.DEFAULT_CONTEXT_MENU_JSP;
584         }
585         try {
586             if ( log.isDebugEnabled() ) {
587                 log.debug("Processing content; definition name: " + definition + ", locale: " + locale + ", uri: " + uri + ", identifier: " + identifier);
588             }
589             String JavaDoc content = null;
590             Long JavaDoc fieldId = null;
591             Long JavaDoc fieldValueId = null;
592             byte fieldType = 0;
593
594             CacheUtil cacheUtil = CacheUtil.getInstance(request);
595             CacheUtil.CFVData cfvData = null;
596
597             //try to search in cache by uri
598
cfvData = cacheUtil.getPageFieldValueFromCache(uri, identifier, locale);
599
600             if ( cfvData != null ) {
601                 content = cfvData.getData();
602                 fieldId = cfvData.getContentFieldId();
603                 fieldType = cfvData.getContentFieldType();
604             }
605
606             // rules to determine, whether or not to show empty content
607
// 1. if this.showEmpty is specified, get its value
608
// 2. else check field's type
609
// 3. if field's type is LINE_TYPE, set local showEmpty to true, otherwise, set it to false
610
boolean showEmpty = this.showEmpty == null ? fieldType != ContentField.LINE_TYPE : this.showEmpty.booleanValue();
611
612             // not found in cache, search in persistence layer
613
if ( content == null || (content.trim().length() == 0 && !showEmpty) ) {
614                 // try to search content by uri
615
if ( log.isDebugEnabled() ) {
616                     log.debug("Trying to search in persistent storage by uri: " + uri);
617                 }
618                 ContentFieldManager contentFieldManager = (ContentFieldManager) applicationCtx.getBean(Constants.CONTENT_FIELD_MANAGER_BEAN);
619
620                 // search content field by page uri
621
boolean continueSearch = true;
622                 ContentField field = contentFieldManager.findContentFieldByPageUri(identifier, uri);
623                 content = null;
624                 if ( field != null ) {
625                     ContentFieldValue fieldValue = contentFieldManager.findContentFieldValueByUriAndIdentifierAndLocale(uri, identifier, locale);
626                     if ( fieldValue == null ) {
627                         continueSearch = false;
628                     } else {
629                         fieldValueId = fieldValue.getId();
630                         content = retrieveContent(fieldValue, field.getType());
631                         showEmpty = this.showEmpty == null ? field.getType() != ContentField.LINE_TYPE : this.showEmpty.booleanValue();
632                         continueSearch = (content == null || content.trim().length() == 0) && !showEmpty;
633                     }
634                 }
635
636                 if ( continueSearch ) {
637                     // not found - search by layout definition
638
String JavaDoc tmpDefinition = null;
639                     do {
640                         tmpDefinition = new String JavaDoc(definition);
641                         definition = ((HeritableComponentDefinition) TilesUtil.getDefinition(definition, request, servletContext)).getExtends();
642                         if ( definition != null ) {
643                             if ( log.isDebugEnabled() ) {
644                                 log.debug("Trying to search in persistent storage by definition: " + definition);
645                             }
646                             field = contentFieldManager.findContentFieldByLayoutDefinition(identifier, definition);
647                             if ( field != null ) {
648                                 // field has been found, search for CFV
649
ContentFieldValue fieldValue = contentFieldManager.findContentFieldValueByDefinitionAndIdentifierAndLocale(definition, identifier, locale);
650                                 if ( fieldValue == null ) {
651                                     continueSearch = false;
652                                 } else {
653                                     fieldValueId = fieldValue.getId();
654                                     content = retrieveContent(fieldValue, field.getType());
655                                     showEmpty = this.showEmpty == null ? field.getType() != ContentField.LINE_TYPE : this.showEmpty.booleanValue();
656                                     continueSearch = (content == null || content.trim().length() == 0) && !showEmpty;
657                                 }
658                             } else {
659                                 continueSearch = true;
660                             }
661                         }
662                     } while ( definition != null && continueSearch );
663
664                     if ( field != null ) {
665                         fieldId = field.getId();
666                         fieldType = field.getType();
667
668                         // put in cache
669
if ( content != null ) {
670                             cfvData = new CacheUtil.CFVData(content, fieldId, fieldType, fieldValueId);
671                             if ( definition == null ) {
672                                 cacheUtil.putLayoutFieldValueInCache(cfvData, tmpDefinition, uri, identifier, locale);
673                             } else {
674                                 cacheUtil.putLayoutFieldValueInCache(cfvData, definition, uri, identifier, locale);
675                             }
676                         }
677                     }
678                 } else if ( field != null ) {
679                     fieldId = field.getId();
680                     fieldType = field.getType();
681
682                     if ( content != null ) {
683                         // put content in cache
684
cfvData = new CacheUtil.CFVData(content, fieldId, fieldType, fieldValueId);
685                         cacheUtil.putPageFieldValueInCache(cfvData, uri, identifier, locale);
686                     }
687                 }
688                 if ( field == null ) {
689                     if ( !ignore.booleanValue() ) {
690                         String JavaDoc errorMessage = applicationResources.getMessage(request, "core.commons.contentTag.fieldNotFound", new Object JavaDoc[]{identifier, savedUri, savedDefinition});
691                         tagUtils.write(pageContext, errorMessage);
692                     }
693                     return;
694                 }
695             }
696
697             boolean contentIsEmpty = content == null || content.trim().length() == 0;
698
699             if ( !contentIsEmpty ) {
700                 boolean encode = filter == null ? fieldType != ContentField.HTML_TYPE : filter.booleanValue();
701
702                 if ( encode ) {
703                     content = StringUtil.htmlEncode(content);
704                 }
705             }
706
707             if ( var != null ) {
708                 if ( content != null ) {
709                     // save message in specified scope
710
int varScope = PageContext.PAGE_SCOPE;
711                     if ( scope != null ) {
712                         varScope = tagUtils.getScope(scope);
713                     }
714                     pageContext.setAttribute(var, content, varScope);
715                 }
716             } else {
717                 // write message directly to page
718
Object JavaDoc editModeEnabledAttr = request.getSession().getAttribute(WebappConstants.SITE_EDIT_MODE_ENABLED_KEY);
719                 boolean editModeEnabled = editModeEnabledAttr != null && Boolean.TRUE.equals(editModeEnabledAttr);
720                 if ( editModeEnabled && editable != null && editable.booleanValue() ) {
721                     if ( contentIsEmpty ) {
722                         content = applicationResources.getMessage(request, "core.commons.contentTag.insertText");
723                     }
724                     // wrap content with <div></div> tags
725
StringBuffer JavaDoc divId = new StringBuffer JavaDoc("__field__value__").append(fieldId).append("__wrapper__").append(tagNumber);
726                     String JavaDoc requestUrl = (String JavaDoc) request.getAttribute(ContentTilesRequestProcessor.PROCESSED_URL);
727                     if ( requestUrl == null ) {
728                         requestUrl = WebappUtil.findGlobalForwardConfig("index", null, request).getPath();
729                     }
730
731                     // Make context menu ID
732
StringBuffer JavaDoc contextMenuId = new StringBuffer JavaDoc("__contextMenu__content__").append(tagNumber);
733
734                     /*
735                        That's a name of JS variable that will hold this
736                        context menu (that variable is used to refer to this context
737                        menu from showContextMenu(), for instance)
738                     */

739                     StringBuffer JavaDoc contextMenuLayerVar = new StringBuffer JavaDoc(contextMenuId.toString());
740
741                     StringBuffer JavaDoc onmouseover = new StringBuffer JavaDoc("doSelectLayer(this.id);");
742                     StringBuffer JavaDoc onmouseout = new StringBuffer JavaDoc("doUnselectLayer(this.id);");
743                     StringBuffer JavaDoc ondblclick = new StringBuffer JavaDoc("doCallFieldUpdateInCurrentLocale('").append(locale).append("', ").append(fieldId).append(", '").append(requestUrl).append("');");
744                     StringBuffer JavaDoc oncontextmenu = new StringBuffer JavaDoc("return showContextMenu(").append(contextMenuLayerVar).append(", event);");
745
746                     String JavaDoc divDisplay = "inline";
747                     if ( fieldType == ContentField.HTML_TYPE ) {
748                         divDisplay = "block";
749                     }
750                     content = new StringBuffer JavaDoc("<div id=\"").append(divId).append("\" name=\"").append(divId).append("\" class=\"fieldValueWrapper\" style=\"display: ").append(divDisplay).append(";\" ").append("onmouseover=\"").append(onmouseover).append("\" onmouseout=\"").append(onmouseout).append("\" ondblclick=\"").append(ondblclick).append("\" oncontextmenu=\"").append(oncontextmenu).append("\">").append(content).append("</div>").toString();
751                     tagUtils.write(pageContext, content);
752
753                     // Insert context menu
754
// Obtain titles
755
String JavaDoc editInCurrentLocaleTitle = applicationResources.getMessage(request, "core.editMode.menu.context.editInCurrentLocale");
756                     String JavaDoc editInAllLocalesTitle = applicationResources.getMessage(request, "core.editMode.menu.context.editInAllLocales");
757                     String JavaDoc editInChosenLocalesTitle = applicationResources.getMessage(request, "core.editMode.menu.context.editInChosenLocales");
758
759                     // Create and populate list of items
760
ContextMenuItem menu = new ContextMenuItem();
761                     menu.setId(contextMenuId.toString());
762                     menu.addChildItem(new ContextMenuItem(JavaScriptUtil.createLinkAsLayer("javascript:" + ondblclick,
763                             editInCurrentLocaleTitle, WebappConstants.CONTEXT_MENU_ITEM_STYLE_CLASS, WebappConstants.HIGHLIGHTED_CONTEXT_MENU_ITEM_STYLE_CLASS)));
764                     menu.addChildItem(new ContextMenuItem(JavaScriptUtil.createLinkAsLayer("javascript:doCallFieldUpdate(" + fieldId + ", '" + requestUrl + "');",
765                             editInAllLocalesTitle, WebappConstants.CONTEXT_MENU_ITEM_STYLE_CLASS, WebappConstants.HIGHLIGHTED_CONTEXT_MENU_ITEM_STYLE_CLASS)));
766                     menu.addChildItem(new ContextMenuItem(JavaScriptUtil.createLinkAsLayer("javascript:doChooseLocalesForFieldUpdate(" + fieldId + ", '" + requestUrl + "');",
767                             editInChosenLocalesTitle, WebappConstants.CONTEXT_MENU_ITEM_STYLE_CLASS, WebappConstants.HIGHLIGHTED_CONTEXT_MENU_ITEM_STYLE_CLASS)));
768
769                     // Store menu in request
770
pageContext.setAttribute(WebappConstants.CONTEXT_MENUS_KEY, Arrays.asList(new ContextMenuItem[]{menu}), PageContext.REQUEST_SCOPE);
771
772                     // include page that renders menu
773
pageContext.include(contextMenuJsp);
774                 } else {
775                     // edit mode disabled or content is not editable
776
showEmpty = this.showEmpty == null ? fieldType != ContentField.LINE_TYPE : this.showEmpty.booleanValue();
777                     if ( content == null ) {
778                         content = "";
779                     }
780                     if ( !contentIsEmpty || showEmpty ) {
781                         tagUtils.write(pageContext, content);
782                     }
783                 }
784             }
785         } catch ( Exception JavaDoc ex ) {
786             JspTagException JavaDoc e = new JspTagException JavaDoc(ex);
787             throw e;
788         }
789
790     }
791
792
793     /**
794      * Searches for content in given field value according to field type
795      *
796      * @param fieldValue Content field value to search content in
797      * @param fieldType Type of field which is owner of given field value
798      * @return Content or
799      */

800     protected String JavaDoc retrieveContent(ContentFieldValue fieldValue, byte fieldType) {
801         String JavaDoc content = null;
802         if ( fieldType == ContentField.LINE_TYPE ) {
803             content = fieldValue.getSimpleValue();
804         } else {
805             content = ConvertUtil.convertToString(fieldValue.getValue());
806         }
807         return content;
808     }
809
810 }
811
Popular Tags