xref: /trunk/main/xmloff/source/transform/EventOOoTContext.cxx (revision cdf0e10c4e3984b49a9502b011690b615761d4a3)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_xmloff.hxx"
30 #include "EventOOoTContext.hxx"
31 #include "EventMap.hxx"
32 #include "MutableAttrList.hxx"
33 #include "xmloff/xmlnmspe.hxx"
34 #ifndef _XMLOFF_ACTIONMAPTYPESOOo_HXX
35 #include "ActionMapTypesOOo.hxx"
36 #endif
37 #include "AttrTransformerAction.hxx"
38 #include "TransformerActions.hxx"
39 #ifndef _XMLOFF_TRANSFORMERBASE_HXX
40 #include "TransformerBase.hxx"
41 #endif
42 #include <comphelper/stl_types.hxx>
43 #include <rtl/ustrbuf.hxx>
44 
45 #include <hash_map>
46 
47 using ::rtl::OUString;
48 using ::rtl::OUStringBuffer;
49 using namespace ::com::sun::star::uno;
50 using namespace ::com::sun::star::xml::sax;
51 using namespace ::xmloff::token;
52 
53 class XMLTransformerOOoEventMap_Impl:
54     public ::std::hash_map< ::rtl::OUString, NameKey_Impl,
55                             ::rtl::OUStringHash, ::comphelper::UStringEqual >
56 {
57 public:
58 
59     void AddMap( XMLTransformerEventMapEntry *pInit );
60 
61     XMLTransformerOOoEventMap_Impl( XMLTransformerEventMapEntry *pInit,
62                                     XMLTransformerEventMapEntry *pInit2 );
63     ~XMLTransformerOOoEventMap_Impl();
64 };
65 
66 void XMLTransformerOOoEventMap_Impl::AddMap( XMLTransformerEventMapEntry *pInit )
67 {
68     XMLTransformerOOoEventMap_Impl::key_type aKey;
69     XMLTransformerOOoEventMap_Impl::data_type aData;
70     while( pInit->m_pOOoName )
71     {
72         aKey = OUString::createFromAscii(pInit->m_pOOoName);
73 
74         OSL_ENSURE( find( aKey ) == end(), "duplicate event map entry" );
75 
76         aData.m_nPrefix = pInit->m_nOASISPrefix;
77         aData.m_aLocalName = OUString::createFromAscii(pInit->m_pOASISName);
78 
79         XMLTransformerOOoEventMap_Impl::value_type aVal( aKey, aData );
80 
81         if( !insert( aVal ).second )
82         {
83             OSL_ENSURE( false, "duplicate OOo event name extry" );
84         }
85 
86         ++pInit;
87     }
88 }
89 
90 XMLTransformerOOoEventMap_Impl::XMLTransformerOOoEventMap_Impl(
91         XMLTransformerEventMapEntry *pInit,
92         XMLTransformerEventMapEntry *pInit2 )
93 {
94     if( pInit )
95         AddMap( pInit );
96     if( pInit )
97         AddMap( pInit2 );
98 }
99 
100 XMLTransformerOOoEventMap_Impl::~XMLTransformerOOoEventMap_Impl()
101 {
102 }
103 
104 // -----------------------------------------------------------------------------
105 
106 TYPEINIT1( XMLEventOOoTransformerContext, XMLPersElemContentTContext );
107 
108 XMLEventOOoTransformerContext::XMLEventOOoTransformerContext(
109         XMLTransformerBase& rImp,
110         const OUString& rQName,
111         sal_Bool bPersistent ) :
112     XMLPersElemContentTContext( rImp, rQName,
113         rImp.GetNamespaceMap().GetKeyByAttrName( rQName ), XML_EVENT_LISTENER ),
114     m_bPersistent( bPersistent )
115 {
116 }
117 
118 XMLEventOOoTransformerContext::~XMLEventOOoTransformerContext()
119 {
120 }
121 
122 XMLTransformerOOoEventMap_Impl
123     *XMLEventOOoTransformerContext::CreateEventMap()
124 {
125     return new XMLTransformerOOoEventMap_Impl( aTransformerEventMap,
126                                                aFormTransformerEventMap );
127 }
128 
129 void XMLEventOOoTransformerContext::FlushEventMap(
130         XMLTransformerOOoEventMap_Impl *p )
131 {
132     delete p;
133 }
134 
135 sal_uInt16 XMLEventOOoTransformerContext::GetEventName(
136         const OUString& rName,
137         OUString& rNewName,
138         XMLTransformerOOoEventMap_Impl& rMap )
139 {
140     XMLTransformerOOoEventMap_Impl::key_type aKey( rName );
141     XMLTransformerOOoEventMap_Impl::const_iterator aIter = rMap.find( aKey );
142     if( aIter == rMap.end() )
143     {
144         rNewName = rName;
145         return XML_NAMESPACE_UNKNOWN;
146     }
147     else
148     {
149         rNewName = (*aIter).second.m_aLocalName;
150         return (*aIter).second.m_nPrefix;
151     }
152 }
153 
154 
155 void XMLEventOOoTransformerContext::StartElement(
156     const Reference< XAttributeList >& rAttrList )
157 {
158     XMLTransformerActions *pActions =
159         GetTransformer().GetUserDefinedActions( OOO_EVENT_ACTIONS );
160     OSL_ENSURE( pActions, "go no actions" );
161 
162     OUString aLocation, aMacroName;
163     sal_Int16 nMacroName = -1;
164     Reference< XAttributeList > xAttrList( rAttrList );
165     XMLMutableAttributeList *pMutableAttrList = 0;
166     sal_Int16 nAttrCount = xAttrList.is() ? xAttrList->getLength() : 0;
167     for( sal_Int16 i=0; i < nAttrCount; i++ )
168     {
169         const OUString& rAttrName = xAttrList->getNameByIndex( i );
170         OUString aLocalName;
171         sal_uInt16 nPrefix =
172             GetTransformer().GetNamespaceMap().GetKeyByAttrName( rAttrName,
173                                                                  &aLocalName );
174         XMLTransformerActions::key_type aKey( nPrefix, aLocalName );
175         XMLTransformerActions::const_iterator aIter =
176             pActions->find( aKey );
177         if( !(aIter == pActions->end() ) )
178         {
179             if( !pMutableAttrList )
180             {
181                 pMutableAttrList =
182                         new XMLMutableAttributeList( xAttrList );
183                 xAttrList = pMutableAttrList;
184             }
185             const OUString& rAttrValue = xAttrList->getValueByIndex( i );
186             switch( (*aIter).second.m_nActionType )
187             {
188             case XML_ATACTION_HREF:
189                 // TODO
190                 break;
191             case XML_ATACTION_EVENT_NAME:
192                 pMutableAttrList->SetValueByIndex( i,
193                                GetTransformer().GetEventName( rAttrValue ) );
194                 break;
195             case XML_ATACTION_ADD_NAMESPACE_PREFIX:
196                 {
197                     OUString aAttrValue( rAttrValue );
198                     sal_uInt16 nValPrefix =
199                         static_cast<sal_uInt16>((*aIter).second.m_nParam1);
200                     if( GetTransformer().AddNamespacePrefix( aAttrValue,
201                                                              nValPrefix ) )
202                         pMutableAttrList->SetValueByIndex( i, aAttrValue );
203                 }
204                 break;
205             case XML_ATACTION_MACRO_LOCATION:
206                 aLocation = rAttrValue;
207                 pMutableAttrList->RemoveAttributeByIndex( i );
208                 --i;
209                 --nAttrCount;
210                 break;
211             case XML_ATACTION_MACRO_NAME:
212                 aMacroName = rAttrValue;
213                 nMacroName = i;
214                 break;
215             case XML_ATACTION_COPY:
216                 break;
217             default:
218                 OSL_ENSURE( !this, "unknown action" );
219                 break;
220             }
221         }
222     }
223 
224     if( nMacroName != -1 && aLocation.getLength() > 0 )
225     {
226         if( !IsXMLToken( aLocation, XML_APPLICATION ) )
227             aLocation = GetXMLToken( XML_DOCUMENT );
228         OUStringBuffer sTmp( aLocation.getLength() + aMacroName.getLength() + 1 );
229         sTmp = aLocation;
230         sTmp.append( sal_Unicode( ':' ) );
231         sTmp.append( aMacroName );
232         pMutableAttrList->SetValueByIndex( nMacroName,
233                                            sTmp.makeStringAndClear() );
234     }
235 
236     if( m_bPersistent )
237         XMLPersElemContentTContext::StartElement( xAttrList );
238     else
239         GetTransformer().GetDocHandler()->startElement( GetExportQName(),
240                                                         xAttrList );
241 }
242 
243 void XMLEventOOoTransformerContext::EndElement()
244 {
245     if( m_bPersistent )
246         XMLPersElemContentTContext::EndElement();
247     else
248         GetTransformer().GetDocHandler()->endElement( GetExportQName() );
249 }
250 
251 XMLTransformerContext * XMLEventOOoTransformerContext::CreateChildContext(
252                             sal_uInt16 nPrefix,
253                             const OUString& rLocalName,
254                             const OUString& rQName,
255                             const Reference< XAttributeList >& xAttrList )
256 {
257     if( m_bPersistent )
258         return XMLPersElemContentTContext::CreateChildContext(nPrefix, rLocalName, rQName, xAttrList);
259     else
260         return XMLTransformerContext::CreateChildContext(nPrefix, rLocalName, rQName, xAttrList);
261 }
262 
263 sal_Bool XMLEventOOoTransformerContext::IsPersistent() const
264 {
265     return m_bPersistent;
266 }
267