001/*
002 * This library is part of OpenCms -
003 * the Open Source Content Management System
004 *
005 * Copyright (c) Alkacon Software GmbH & Co. KG (http://www.alkacon.com)
006 *
007 * This library is free software; you can redistribute it and/or
008 * modify it under the terms of the GNU Lesser General Public
009 * License as published by the Free Software Foundation; either
010 * version 2.1 of the License, or (at your option) any later version.
011 *
012 * This library is distributed in the hope that it will be useful,
013 * but WITHOUT ANY WARRANTY; without even the implied warranty of
014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015 * Lesser General Public License for more details.
016 *
017 * For further information about Alkacon Software GmbH & Co. KG, please see the
018 * company website: http://www.alkacon.com
019 *
020 * For further information about OpenCms, please see the
021 * project website: http://www.opencms.org
022 *
023 * You should have received a copy of the GNU Lesser General Public
024 * License along with this library; if not, write to the Free Software
025 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
026 */
027
028package org.opencms.workplace.editors;
029
030import org.opencms.ade.contenteditor.CmsWidgetUtil;
031import org.opencms.main.CmsLog;
032import org.opencms.widgets.I_CmsWidget;
033import org.opencms.widgets.Messages;
034import org.opencms.xml.content.I_CmsXmlContentValueVisitor;
035import org.opencms.xml.types.I_CmsXmlContentValue;
036
037import java.util.ArrayList;
038import java.util.HashMap;
039import java.util.List;
040import java.util.Locale;
041import java.util.Map;
042
043import org.apache.commons.logging.Log;
044
045/**
046 * Visitor implementation that collects the different widgets for all visited values and all widgets for the found values.<p>
047 *
048 * This implementation is needed when creating the html output of the xmlcontent editor
049 * {@link org.opencms.workplace.editors.CmsXmlContentEditor}.<p>
050 *
051 * @since 6.0.0
052 */
053public class CmsXmlContentWidgetVisitor implements I_CmsXmlContentValueVisitor {
054
055    /** Static reference to the log. */
056    private static final Log LOG = CmsLog.getLog(CmsXmlContentWidgetVisitor.class);
057
058    /** The locale to get the values from. */
059    private Locale m_locale;
060
061    /** The unique widgets found in the XML content.  */
062    private List<I_CmsWidget> m_uniqueWidgets;
063
064    /** The values corresponding to the found widgets. */
065    private Map<String, I_CmsXmlContentValue> m_values;
066
067    /** The widgets found in the XML content. */
068    private Map<String, I_CmsWidget> m_widgets;
069
070    /**
071     * Creates a new widget collector node visitor.<p>
072     */
073    public CmsXmlContentWidgetVisitor() {
074
075        initialize(null);
076    }
077
078    /**
079     * Creates a new widget collector node visitor.<p>
080     *
081     * @param locale the Locale to get the widgets from
082     */
083    public CmsXmlContentWidgetVisitor(Locale locale) {
084
085        initialize(locale);
086    }
087
088    /**
089     * Returns the locale to get the widgets from.<p>
090     *
091     * @return the locale to get the widgets from
092     */
093    public Locale getLocale() {
094
095        return m_locale;
096    }
097
098    /**
099     * Returns the unique widgets that were found in the content.<p>
100     *
101     * @return the unique widgets that were found in the content
102     */
103    public List<I_CmsWidget> getUniqueWidgets() {
104
105        return m_uniqueWidgets;
106    }
107
108    /**
109     * Returns all simple values that were found in the content.<p>
110     *
111     * The map key is the complete xpath of the value.<p>
112     *
113     * @return all simple values that were found in the content
114     */
115    public Map<String, I_CmsXmlContentValue> getValues() {
116
117        return m_values;
118    }
119
120    /**
121     * Returns all widgets that were found in the content.<p>
122     *
123     * The map key is the complete xpath of the corresponding value.<p>
124     *
125     * @return all widgets that were found in the content
126     */
127    public Map<String, I_CmsWidget> getWidgets() {
128
129        return m_widgets;
130    }
131
132    /**
133     * @see org.opencms.xml.content.I_CmsXmlContentValueVisitor#visit(org.opencms.xml.types.I_CmsXmlContentValue)
134     */
135    public void visit(I_CmsXmlContentValue value) {
136
137        if (LOG.isDebugEnabled()) {
138            LOG.debug(
139                org.opencms.workplace.editors.Messages.get().getBundle().key(
140                    org.opencms.workplace.editors.Messages.LOG_VISITING_1,
141                    value.getPath()));
142        }
143
144        if (value.isSimpleType()) {
145            // only visit simple values
146            boolean useLocale = m_locale != null;
147            if ((useLocale && (value.getLocale().equals(getLocale()))) || (!useLocale)) {
148                try {
149                    // get widget for value
150                    I_CmsWidget widget = CmsWidgetUtil.collectWidgetInfo(value).getWidget();
151                    if (!m_uniqueWidgets.contains(widget)) {
152                        m_uniqueWidgets.add(widget);
153                    }
154                    m_widgets.put(value.getPath(), widget);
155                    m_values.put(value.getPath(), value);
156                    if (LOG.isDebugEnabled()) {
157                        LOG.debug(
158                            Messages.get().getBundle().key(Messages.LOG_DEBUG_WIDGETCOLLECTOR_ADD_1, value.getPath()));
159                    }
160                } catch (Exception e) {
161                    // should usually not happen
162                    if (LOG.isErrorEnabled()) {
163                        LOG.error(Messages.get().getBundle().key(Messages.ERR_WIDGETCOLLECTOR_ADD_1, value), e);
164                    }
165                }
166            }
167        }
168    }
169
170    /**
171     * Initializes the necessary members of the collector.<p>
172     *
173     * @param locale the Locale to get the widgets from
174     */
175    private void initialize(Locale locale) {
176
177        // start with a new instance of the widgets and unique widgets
178        m_widgets = new HashMap<String, I_CmsWidget>(25);
179        m_uniqueWidgets = new ArrayList<I_CmsWidget>(12);
180        m_values = new HashMap<String, I_CmsXmlContentValue>(25);
181        // store Locale to use when collecting the widgets
182        m_locale = locale;
183    }
184}