001    /*
002     * Copyright 2011 The Kuali Foundation.
003     * 
004     * Licensed under the Educational Community License, Version 2.0 (the "License");
005     * you may not use this file except in compliance with the License.
006     * You may obtain a copy of the License at
007     * 
008     * http://www.opensource.org/licenses/ecl2.php
009     * 
010     * Unless required by applicable law or agreed to in writing, software
011     * distributed under the License is distributed on an "AS IS" BASIS,
012     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013     * See the License for the specific language governing permissions and
014     * limitations under the License.
015     */
016    package org.kuali.kfs.sys.document.web;
017    
018    import java.lang.reflect.InvocationTargetException;
019    import java.util.List;
020    import java.util.Map;
021    
022    import javax.servlet.jsp.JspException;
023    import javax.servlet.jsp.PageContext;
024    import javax.servlet.jsp.tagext.Tag;
025    
026    import org.apache.commons.beanutils.PropertyUtils;
027    import org.apache.commons.lang.StringUtils;
028    import org.kuali.kfs.sys.KFSConstants;
029    import org.kuali.kfs.sys.businessobject.AccountingLine;
030    import org.kuali.kfs.sys.context.SpringContext;
031    import org.kuali.kfs.sys.document.datadictionary.AccountingLineViewMultipleReadOnlyFieldsDefinition;
032    import org.kuali.kfs.sys.document.service.AccountingLineFieldRenderingTransformation;
033    import org.kuali.kfs.sys.document.web.renderers.MultipleReadOnlyFieldsRenderer;
034    import org.kuali.rice.kns.datadictionary.AttributeDefinition;
035    import org.kuali.rice.kns.datadictionary.BusinessObjectEntry;
036    import org.kuali.rice.kns.service.DataDictionaryService;
037    import org.kuali.rice.kns.util.FieldUtils;
038    import org.kuali.rice.kns.util.ObjectUtils;
039    import org.kuali.rice.kns.web.ui.Field;
040    
041    /**
042     * Represents multiple fields displaying with their values in a single cell
043     */
044    public class AccountingLineViewMultipleReadOnlyFields extends FieldTableJoiningWithHeader {
045        private AccountingLineViewMultipleReadOnlyFieldsDefinition definition;
046        private List<Field> fields;
047        private static DataDictionaryService dataDictionaryService;
048        
049        /**
050         * Constructs a AccountingLineViewMultipleReadOnlyFields
051         * @param definition data dictionary definition which created this
052         * @param fields the fields to render as read only 
053         */
054        public AccountingLineViewMultipleReadOnlyFields(AccountingLineViewMultipleReadOnlyFieldsDefinition definition, List<Field> fields) {
055            this.definition = definition;
056            this.fields = fields;
057        }
058    
059        /**
060         * 
061         * @see org.kuali.kfs.sys.document.web.TableJoiningWithHeader#createHeaderLabel()
062         */
063        public HeaderLabel createHeaderLabel() {
064            return new LiteralHeaderLabel(KFSConstants.BLANK_SPACE);
065        }
066    
067        /**
068         * Returns the top field name given in the definition
069         * @see org.kuali.kfs.sys.document.web.ElementNamable#getName()
070         */
071        public String getName() {
072            return definition.getFieldNames().get(0);
073        }
074    
075        /**
076         * None of the read only fields will be associated with quickfinders, so this method does nothing
077         * @see org.kuali.kfs.sys.document.web.RenderableElement#appendFields(java.util.List)
078         */
079        public void appendFields(List<Field> fields) {}
080    
081        /**
082         * There are no input fields here, so no need to set tab indices
083         * @see org.kuali.kfs.sys.document.web.RenderableElement#populateWithTabIndexIfRequested(int)
084         */
085        public void populateWithTabIndexIfRequested(int reallyHighIndex) {}
086    
087        /**
088         * @return the fields associated with this Multiple read only fields
089         */
090        public List<Field> getFields() {
091            return fields;
092        }
093    
094        /**
095         * 
096         * @see org.kuali.kfs.sys.document.web.RenderableElement#renderElement(javax.servlet.jsp.PageContext, javax.servlet.jsp.tagext.Tag, org.kuali.kfs.sys.document.web.AccountingLineRenderingContext)
097         */
098        public void renderElement(PageContext pageContext, Tag parentTag, AccountingLineRenderingContext renderingContext) throws JspException {
099            final BusinessObjectEntry boEntry = getDataDictionaryService().getDataDictionary().getBusinessObjectEntry(renderingContext.getAccountingLine().getClass().getName());
100            if (fields != null && !fields.isEmpty()) {
101                for (Field field : fields) {
102                    setShortLabelsForFields(field, boEntry);
103                    setValueForField(field, renderingContext.getAccountingLine());
104                    setInquiryUrlForField(field, renderingContext.getAccountingLine());
105                }
106            }
107            
108            MultipleReadOnlyFieldsRenderer renderer = new MultipleReadOnlyFieldsRenderer();
109            renderer.setFields(getFields());
110            renderer.render(pageContext, parentTag);
111            renderer.clear();
112        }
113        
114        /**
115         * For each field, set the short label, or, failing that, set the label
116         * @param boEntry the business object entry for the accounting line
117         */
118        protected void setShortLabelsForFields(Field field, BusinessObjectEntry boEntry) {
119            final AttributeDefinition propertyDefinition = boEntry.getAttributeDefinition(field.getPropertyName());
120            final String label = (propertyDefinition == null) ? "" : (!StringUtils.isBlank(propertyDefinition.getShortLabel()) ? propertyDefinition.getShortLabel() : propertyDefinition.getLabel());
121            field.setFieldLabel(label);
122        }
123        
124        /**
125         * Sets the value for the field before rendering
126         * @param field the field to set the value of
127         * @param accountingLine the accounting line the field is associated with, which holds the value
128         */
129        protected void setValueForField(Field field, AccountingLine accountingLine) {
130            field.setPropertyValue(ObjectUtils.getPropertyValue(accountingLine, field.getPropertyName()));
131        }
132        
133        /**
134         * Populates the inquiry url on the field if possible
135         * @param field the field to set the inquiry url on
136         * @param accountingLine the accounting line holding values for the field
137         */
138        protected void setInquiryUrlForField(Field field, AccountingLine accountingLine) {
139            if (!StringUtils.isBlank(field.getPropertyValue())) {
140                FieldUtils.setInquiryURL(field, accountingLine, field.getPropertyName());
141            }
142        }
143        
144        /**
145         * @return the implementation of the DataDictionaryService
146         */
147        protected DataDictionaryService getDataDictionaryService() {
148            if (dataDictionaryService == null) {
149                dataDictionaryService = SpringContext.getBean(DataDictionaryService.class);
150            }
151            return dataDictionaryService;
152        }
153    
154    }