View Javadoc

1   /*
2    * Copyright (c) 2001 - 2005 ivata limited.
3    * All rights reserved.
4    * -----------------------------------------------------------------------------
5    * ivata masks may be redistributed under the GNU General Public
6    * License as published by the Free Software Foundation;
7    * version 2 of the License.
8    *
9    * These programs are free software; you can redistribute them and/or
10   * modify them under the terms of the GNU General Public License
11   * as published by the Free Software Foundation; version 2 of the License.
12   *
13   * These programs are distributed in the hope that they will be useful,
14   * but WITHOUT ANY WARRANTY; without even the implied warranty of
15   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
16   *
17   * See the GNU General Public License in the file LICENSE.txt for more
18   * details.
19   *
20   * If you would like a copy of the GNU General Public License write to
21   *
22   * Free Software Foundation, Inc.
23   * 59 Temple Place - Suite 330
24   * Boston, MA 02111-1307, USA.
25   *
26   *
27   * To arrange commercial support and licensing, contact ivata at
28   *                  http://www.ivata.com/contact.jsp
29   * -----------------------------------------------------------------------------
30   * $Log: FieldImpl.java,v $
31   * Revision 1.6  2005/04/11 12:27:02  colinmacleod
32   * Added preliminary support for filters.
33   * Added FieldValueConvertor factor interface
34   * to split off value convertors for reuse.
35   *
36   * Revision 1.5  2005/04/09 18:04:15  colinmacleod
37   * Changed copyright text to GPL v2 explicitly.
38   *
39   * Revision 1.4  2005/03/10 10:19:24  colinmacleod
40   * Added getLabelKey().
41   *
42   * Revision 1.3  2005/01/19 12:35:04  colinmacleod
43   * Added hidden fields.
44   *
45   * Revision 1.2  2005/01/06 22:13:21  colinmacleod
46   * Moved up a version number.
47   * Changed copyright notices to 2005.
48   * Updated the documentation:
49   *   - started working on multiproject:site docu.
50   *   - changed the logo.
51   * Added checkstyle and fixed LOADS of style issues.
52   * Added separate thirdparty subproject.
53   * Added struts (in web), util and webgui (in webtheme) from ivata op.
54   *
55   * Revision 1.1  2004/12/29 20:07:07  colinmacleod
56   * Renamed subproject masks to mask.
57   *
58   * Revision 1.2  2004/11/11 13:31:02  colinmacleod
59   * Added MaskFactory.
60   *
61   * Revision 1.1.1.1  2004/05/16 20:40:31  colinmacleod
62   * Ready for 0.1 release
63   * -----------------------------------------------------------------------------
64   */
65  package com.ivata.mask.field;
66  
67  import org.apache.log4j.Logger;
68  
69  import java.io.Serializable;
70  import java.util.List;
71  import java.util.Properties;
72  import com.ivata.mask.Mask;
73  import com.ivata.mask.MaskFactory;
74  /***
75   * This is the default implementation of an <strong>ivata masks </strong> field.
76   * Don't use this class directly, use the {@link Field}interface.
77   *
78   * @author Colin MacLeod
79   * @since ivata masks 0.1 (2004-05-15) <a
80   *        href='mailto:colin.macleod@ivata.com'>colin.macleod@ivata.com </a>
81   * @see Field
82   */
83  public class FieldImpl implements Field, Serializable {
84      /***
85       * Logger for this class.
86       */
87      private static final Logger logger = Logger.getLogger(FieldImpl.class);
88  
89      /***
90       * If this field represents a combo (select) type, stores the choices as a
91       * <code>Properties</code> instance.
92       */
93      private Properties choiceProperties;
94      /***
95       * If this field represents a combo (select) type, stores the choice keys as
96       * a <code>List</code> of <code>String</code> instances.
97       */
98      private List choicePropertyKeys;
99      /***
100      * The default value for this field. If no default has been defined for this
101      * field, it is <code>null</code>.
102      */
103     private String defaultValue = null;
104     /***
105      * Refer to {@link #isDisplayOnly}.
106      */
107     boolean displayOnly;
108     /***
109      * The data object class for this field, if appropriate, otherwise
110      * <code>null</code>.
111      */
112     private Class dOClass;
113     /***
114      * <p>
115      * Each field may inherit attributes from one other field. This could either
116      * be as a result of an explicit "extends", or it could be a field with the
117      * same name in a super group.
118      * </p>
119      */
120     private Field extendedField;
121     /***
122      * <code>true</code> if this field is hidden. Otherwise, <code>false</code>.
123      */
124     private boolean hidden = false;
125     /***
126      * <p>
127      * The label key is used to identify a clear text description of the field.
128      * </p>
129      */
130     private String labelKey;
131     /***
132      * <code>true</code> if this field is required and must have a non-
133      * <code>null</code>, non-empty value. Otherwise, <code>false</code>
134      * denotes an optional field.
135      */
136     private boolean mandatory = false;
137     /***
138      * <p>
139      * This mask factory is used to retrieve the mask for this field, if the
140      * field represents a value object.
141      * </p>
142      */
143     private MaskFactory maskFactory;
144     /***
145      * Identifier of this field.
146      */
147     private String name;
148     /***
149      * Refer to {@link #isOneToOne}.
150      */
151     private boolean oneToOne;
152     /***
153      * Field which contains this one.
154      */
155     private Field parent;
156     /***
157      * Type of the field, from one of the <code>TYPE_</code> values in the
158      * {@link Field}interface.
159      */
160     private String type;
161     /***
162      * Construct a field with the given parent or inherited field.
163      *
164      * @param parentParam
165      *            The field whose characteristics this one inherits, if they
166      *            have not been set directly.
167      * @param extendedFieldParam
168      *            field defined by an explicit "extends" attribute in the
169      *            configuration.
170      * @param maskFactoryParam
171      *            This mask factory is used to retrieve the mask for this field,
172      *            if the field represents a value object.
173      * @param resouceFieldPathParam
174      * Refer to {@link #getResourceFieldPath}.
175      */
176     public FieldImpl(final Field parentParam,
177             final Field extendedFieldParam,
178             final MaskFactory maskFactoryParam) {
179         this.parent = parentParam;
180         this.extendedField = extendedFieldParam;
181         this.maskFactory = maskFactoryParam;
182     }
183     /***
184      * If this field represents a combo (select) type, returns the choices as a
185      * <code>Properties</code> instance.
186      *
187      * @return <code>Properties</code> instance representing the possible
188      *         values.
189      */
190     public final Properties getChoiceProperties() {
191         if ((choiceProperties == null) && (extendedField != null)) {
192             return extendedField.getChoiceProperties();
193         }
194         return choiceProperties;
195     }
196     /***
197      * If this field represents a combo (select) type, returns the choice keys
198      * as a <code>List</code> of <code>String</code> instances.
199      *
200      * @return <code>List</code> of <code>String</code> instances
201      *         representing the key values of all choice options.
202      */
203     public final List getChoicePropertyKeys() {
204         if ((choicePropertyKeys == null) && (extendedField != null)) {
205             return extendedField.getChoicePropertyKeys();
206         }
207         return choicePropertyKeys;
208     }
209     /***
210      * Get the default value for this field. If no default has been defined for
211      * this field, is <code>null</code>.
212      *
213      * @return default value for this field, or <code>null</code> if none is
214      *         defined.
215      */
216     public final String getDefaultValue() {
217         if ((defaultValue == null) && (extendedField != null)) {
218             return extendedField.getDefaultValue();
219         }
220         return defaultValue;
221     }
222     /***
223      * Get the data object class for this field, if appropriate.
224      *
225      * @return data object class if this field links to a data object, otherwise
226      *         <code>null</code>.
227      */
228     public final Class getDOClass() {
229         if ((dOClass == null) && (extendedField != null)) {
230             return extendedField.getDOClass();
231         }
232         return dOClass;
233     }
234     /***
235      * @return Returns the labelKey.
236      */
237     public String getLabelKey() {
238         return labelKey;
239     }
240     /***
241      * Id of just this field - equivalent to the field name.
242      *
243      * @return Id of just this field - equivalent to the field name.
244      */
245     public final String getName() {
246         return name;
247     }
248     /***
249      * <p>
250      * Get the field which contains this one.
251      * </p>
252      *
253      * @return Field which contains this field, or <code>null</code> if this
254      *         is a top-level field.
255      */
256     public final Field getParent() {
257         return parent;
258     }
259     /***
260      * <p>
261      * Return the full path to this field, including the ids of parent fields
262      * separated by '.' characters.
263      * </p>
264      *
265      * @return Full path to this field, to uniquely identify it within the
266      *         system.
267      */
268     public final String getPath() {
269         if (parent != null) {
270             return parent.getPath() + "." + name;
271         }
272         return name;
273     }
274     /***
275      * Indicates what sort of data this field should hold.
276      *
277      * @return type of the field, from one of the <code>TYPE_</code> values in
278      *         the {@link Field}interface.
279      */
280     public final String getType() {
281         if ((type == null) && (extendedField != null)) {
282             return extendedField.getType();
283         }
284         return type;
285     }
286     /***
287      * <p>
288      * If this field represents a value object, get the mask associated with
289      * this value object.
290      * </p>
291      *
292      * @return Mask associated with this value object or <code>null</code> if
293      *         this field is not a value object.
294      * @see com.ivata.mask.field.Field#getMask
295      */
296     public final Mask getValueObjectMask() {
297         if (dOClass == null) {
298             return null;
299         }
300         return maskFactory.getMask(this, dOClass);
301     }
302 
303     /***
304      * Get whether or not this field can be amended. Useful for automatically
305      * generated fields such as timestamps.
306      * @return <code>true</code> if the field <u>cannot</u> be manually changed.
307      */
308     public boolean isDisplayOnly() {
309         return displayOnly;
310     }
311     /***
312      * <code>true</code> if this field is hidden. Otherwise, <code>false</code>.
313      *
314      * @return Returns whether or not the field is hidden.
315      */
316     public boolean isHidden() {
317         return hidden;
318     }
319     /***
320      * <p>
321      * Is this field is required or optional?
322      * </p>
323      *
324      * @return <code>true</code> if this field is required and must have a
325      *         non- <code>null</code>, non-empty value. Otherwise,
326      *         <code>false</code> for an optional field.
327      */
328     public final boolean isMandatory() {
329         return mandatory;
330     }
331     /***
332      * If this field represents another value object, but the relationship with
333      * its container is one-to-one, then it can be included in the parent's
334      * mask directly.
335      *
336      * @return <code>true</code> if this field should be displayed directly
337      * in the mask of the parent field.
338      */
339     public boolean isOneToOne() {
340         return oneToOne;
341     }
342     /***
343      * Refer to {@link #getChoiceProperties}.
344      * @param choicePropertiesParam Refer to {@link #getChoiceProperties}.
345      */
346     public void setChoiceProperties(Properties choicePropertiesParam) {
347         if (logger.isDebugEnabled()) {
348             logger.debug("Setting choiceProperties. Before '"
349                     + choiceProperties + "', after '" + choicePropertiesParam
350                     + "'");
351         }
352         choiceProperties = choicePropertiesParam;
353     }
354     /***
355      * Refer to {@link #getChoicePropertyKeys}.
356      * @param choicePropertyKeysParam Refer to {@link #getChoicePropertyKeys}.
357      */
358     public void setChoicePropertyKeys(List choicePropertyKeysParam) {
359         if (logger.isDebugEnabled()) {
360             logger.debug("Setting choicePropertyKeys. Before '"
361                     + choicePropertyKeys + "', after '"
362                     + choicePropertyKeysParam + "'");
363         }
364         choicePropertyKeys = choicePropertyKeysParam;
365     }
366     /***
367      * Refer to {@link #getDefaultValue}.
368      * @param defaultValueParam Refer to {@link #getDefaultValue}.
369      */
370     public void setDefaultValue(String defaultValueParam) {
371         if (logger.isDebugEnabled()) {
372             logger.debug("Setting defaultValue. Before '" + defaultValue
373                     + "', after '" + defaultValueParam + "'");
374         }
375         defaultValue = defaultValueParam;
376     }
377     /***
378      * Refer to {@link #isDisplayOnly}.
379      * @param displayOnlyParam Refer to {@link #isDisplayOnly}.
380      */
381     public void setDisplayOnly(boolean displayOnlyParam) {
382         if (logger.isDebugEnabled()) {
383             logger.debug("Setting displayOnly. Before '" + displayOnly
384                     + "', after '" + displayOnlyParam + "'");
385         }
386         displayOnly = displayOnlyParam;
387     }
388     /***
389      * Refer to {@link #getDOClass}.
390      * @param classParam Refer to {@link #getDOClass}.
391      */
392     public void setDOClass(Class classParam) {
393         if (logger.isDebugEnabled()) {
394             logger.debug("Setting dOClass. Before '" + dOClass + "', after '"
395                     + classParam + "'");
396         }
397         dOClass = classParam;
398     }
399     /***
400      * Refer to {@link #getHidden}.
401      * @param hiddenParam Refer to {@link #getHidden}.
402      */
403     public void setHidden(boolean hiddenParam) {
404         if (logger.isDebugEnabled()) {
405             logger.debug("Setting hidden. Before '" + hidden + "', after '"
406                     + hiddenParam + "'");
407         }
408         hidden = hiddenParam;
409     }
410     /***
411      * Refer to {@link #getLabelKey}.
412      * @param labelKeyParam Refer to {@link #getLabelKey}.
413      */
414     public void setLabelKey(String labelKeyParam) {
415         if (logger.isDebugEnabled()) {
416             logger.debug("Setting labelKey. Before '" + labelKey + "', after '"
417                     + labelKeyParam + "'");
418         }
419         labelKey = labelKeyParam;
420     }
421     /***
422      * Refer to {@link #getMandatory}.
423      * @param mandatoryParam Refer to {@link #getMandatory}.
424      */
425     public void setMandatory(boolean mandatoryParam) {
426         if (logger.isDebugEnabled()) {
427             logger.debug("Setting mandatory. Before '" + mandatory
428                     + "', after '" + mandatoryParam + "'");
429         }
430         mandatory = mandatoryParam;
431     }
432     /***
433      * Refer to {@link #getName}.
434      * @param nameParam Refer to {@link #getName}.
435      */
436     public void setName(String nameParam) {
437         if (logger.isDebugEnabled()) {
438             logger.debug("Setting name. Before '" + name + "', after '"
439                     + nameParam + "'");
440         }
441         name = nameParam;
442     }
443     /***
444      * Refer to {@link #isOneToOne}.
445      * @param oneToOneParam Refer to {@link #isOneToOne}.
446      */
447     public void setOneToOne(boolean oneToOneParam) {
448         if (logger.isDebugEnabled()) {
449             logger.debug("Setting oneToOne. Before '" + oneToOne + "', after '"
450                     + oneToOneParam + "'");
451         }
452         oneToOne = oneToOneParam;
453     }
454     /***
455      * Refer to {@link #getParent}.
456      * @param parentParam Refer to {@link #getParent}.
457      */
458     public void setParent(Field parentParam) {
459         if (logger.isDebugEnabled()) {
460             logger.debug("Setting parent. Before '" + parent + "', after '"
461                     + parentParam + "'");
462         }
463         parent = parentParam;
464     }
465     /***
466      * Refer to {@link #getType}.
467      * @param typeParam Refer to {@link #getType}.
468      */
469     public void setType(String typeParam) {
470         if (logger.isDebugEnabled()) {
471             logger.debug("Setting type. Before '" + type + "', after '"
472                     + typeParam + "'");
473         }
474         type = typeParam;
475     }
476     /***
477      * Overridden to return the field name.
478      *
479      * @return the field name.
480      */
481     public final String toString() {
482         return getName();
483     }
484 }