1*b1cdbd2cSJim Jagielski /**************************************************************
2*b1cdbd2cSJim Jagielski  *
3*b1cdbd2cSJim Jagielski  * Licensed to the Apache Software Foundation (ASF) under one
4*b1cdbd2cSJim Jagielski  * or more contributor license agreements.  See the NOTICE file
5*b1cdbd2cSJim Jagielski  * distributed with this work for additional information
6*b1cdbd2cSJim Jagielski  * regarding copyright ownership.  The ASF licenses this file
7*b1cdbd2cSJim Jagielski  * to you under the Apache License, Version 2.0 (the
8*b1cdbd2cSJim Jagielski  * "License"); you may not use this file except in compliance
9*b1cdbd2cSJim Jagielski  * with the License.  You may obtain a copy of the License at
10*b1cdbd2cSJim Jagielski  *
11*b1cdbd2cSJim Jagielski  *   http://www.apache.org/licenses/LICENSE-2.0
12*b1cdbd2cSJim Jagielski  *
13*b1cdbd2cSJim Jagielski  * Unless required by applicable law or agreed to in writing,
14*b1cdbd2cSJim Jagielski  * software distributed under the License is distributed on an
15*b1cdbd2cSJim Jagielski  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*b1cdbd2cSJim Jagielski  * KIND, either express or implied.  See the License for the
17*b1cdbd2cSJim Jagielski  * specific language governing permissions and limitations
18*b1cdbd2cSJim Jagielski  * under the License.
19*b1cdbd2cSJim Jagielski  *
20*b1cdbd2cSJim Jagielski  *************************************************************/
21*b1cdbd2cSJim Jagielski 
22*b1cdbd2cSJim Jagielski 
23*b1cdbd2cSJim Jagielski 
24*b1cdbd2cSJim Jagielski // MARKER(update_precomp.py): autogen include statement, do not remove
25*b1cdbd2cSJim Jagielski #include "precompiled_xmloff.hxx"
26*b1cdbd2cSJim Jagielski #include <xmloff/XMLEventsImportContext.hxx>
27*b1cdbd2cSJim Jagielski 
28*b1cdbd2cSJim Jagielski #ifndef _XMLOFF_XMLEVENTIMPORTHELPER_HXX
29*b1cdbd2cSJim Jagielski #include "XMLEventImportHelper.hxx"
30*b1cdbd2cSJim Jagielski #endif
31*b1cdbd2cSJim Jagielski 
32*b1cdbd2cSJim Jagielski #ifndef _COM_SUN_STAR_DOCUMENT_XEVENTSSUPPLIER_HPP
33*b1cdbd2cSJim Jagielski #include <com/sun/star/document/XEventsSupplier.hpp>
34*b1cdbd2cSJim Jagielski #endif
35*b1cdbd2cSJim Jagielski #include <tools/debug.hxx>
36*b1cdbd2cSJim Jagielski #include <xmloff/xmlimp.hxx>
37*b1cdbd2cSJim Jagielski #include <xmloff/nmspmap.hxx>
38*b1cdbd2cSJim Jagielski #include "xmloff/xmlnmspe.hxx"
39*b1cdbd2cSJim Jagielski #include <xmloff/xmltoken.hxx>
40*b1cdbd2cSJim Jagielski #include "xmloff/xmlerror.hxx"
41*b1cdbd2cSJim Jagielski 
42*b1cdbd2cSJim Jagielski using namespace ::com::sun::star::uno;
43*b1cdbd2cSJim Jagielski using namespace ::xmloff::token;
44*b1cdbd2cSJim Jagielski 
45*b1cdbd2cSJim Jagielski using ::rtl::OUString;
46*b1cdbd2cSJim Jagielski using ::com::sun::star::xml::sax::XAttributeList;
47*b1cdbd2cSJim Jagielski using ::com::sun::star::beans::PropertyValue;
48*b1cdbd2cSJim Jagielski using ::com::sun::star::container::XNameReplace;
49*b1cdbd2cSJim Jagielski using ::com::sun::star::document::XEventsSupplier;
50*b1cdbd2cSJim Jagielski using ::com::sun::star::lang::IllegalArgumentException;
51*b1cdbd2cSJim Jagielski 
52*b1cdbd2cSJim Jagielski TYPEINIT1(XMLEventsImportContext,  SvXMLImportContext);
53*b1cdbd2cSJim Jagielski 
54*b1cdbd2cSJim Jagielski 
XMLEventsImportContext(SvXMLImport & rImport,sal_uInt16 nPrfx,const OUString & rLocalName)55*b1cdbd2cSJim Jagielski XMLEventsImportContext::XMLEventsImportContext(
56*b1cdbd2cSJim Jagielski 	SvXMLImport& rImport,
57*b1cdbd2cSJim Jagielski 	sal_uInt16 nPrfx,
58*b1cdbd2cSJim Jagielski 	const OUString& rLocalName) :
59*b1cdbd2cSJim Jagielski 		SvXMLImportContext(rImport, nPrfx, rLocalName)
60*b1cdbd2cSJim Jagielski {
61*b1cdbd2cSJim Jagielski }
62*b1cdbd2cSJim Jagielski 
63*b1cdbd2cSJim Jagielski 
XMLEventsImportContext(SvXMLImport & rImport,sal_uInt16 nPrfx,const OUString & rLocalName,const Reference<XEventsSupplier> & xEventsSupplier)64*b1cdbd2cSJim Jagielski XMLEventsImportContext::XMLEventsImportContext(
65*b1cdbd2cSJim Jagielski 	SvXMLImport& rImport,
66*b1cdbd2cSJim Jagielski 	sal_uInt16 nPrfx,
67*b1cdbd2cSJim Jagielski 	const OUString& rLocalName,
68*b1cdbd2cSJim Jagielski 	const Reference<XEventsSupplier> & xEventsSupplier) :
69*b1cdbd2cSJim Jagielski 		SvXMLImportContext(rImport, nPrfx, rLocalName),
70*b1cdbd2cSJim Jagielski 		xEvents(xEventsSupplier->getEvents())
71*b1cdbd2cSJim Jagielski {
72*b1cdbd2cSJim Jagielski }
73*b1cdbd2cSJim Jagielski 
74*b1cdbd2cSJim Jagielski 
XMLEventsImportContext(SvXMLImport & rImport,sal_uInt16 nPrfx,const OUString & rLocalName,const Reference<XNameReplace> & xNameReplace)75*b1cdbd2cSJim Jagielski XMLEventsImportContext::XMLEventsImportContext(
76*b1cdbd2cSJim Jagielski 	SvXMLImport& rImport,
77*b1cdbd2cSJim Jagielski 	sal_uInt16 nPrfx,
78*b1cdbd2cSJim Jagielski 	const OUString& rLocalName,
79*b1cdbd2cSJim Jagielski 	const Reference<XNameReplace> & xNameReplace) :
80*b1cdbd2cSJim Jagielski 		SvXMLImportContext(rImport, nPrfx, rLocalName),
81*b1cdbd2cSJim Jagielski 		xEvents(xNameReplace)
82*b1cdbd2cSJim Jagielski {
83*b1cdbd2cSJim Jagielski }
84*b1cdbd2cSJim Jagielski 
~XMLEventsImportContext()85*b1cdbd2cSJim Jagielski XMLEventsImportContext::~XMLEventsImportContext()
86*b1cdbd2cSJim Jagielski {
87*b1cdbd2cSJim Jagielski // 	// if, for whatever reason, the object gets destroyed prematurely,
88*b1cdbd2cSJim Jagielski // 	// we need to delete the collected events
89*b1cdbd2cSJim Jagielski // 	EventsVector::iterator aEnd = aCollectEvents.end();
90*b1cdbd2cSJim Jagielski // 	for(EventsVector::iterator aIter = aCollectEvents.begin();
91*b1cdbd2cSJim Jagielski // 		aIter != aEnd;
92*b1cdbd2cSJim Jagielski // 		aIter++)
93*b1cdbd2cSJim Jagielski // 	{
94*b1cdbd2cSJim Jagielski // 		EventNameValuesPair* pPair = &(*aIter);
95*b1cdbd2cSJim Jagielski // 		delete pPair;
96*b1cdbd2cSJim Jagielski // 	}
97*b1cdbd2cSJim Jagielski // 	aCollectEvents.clear();
98*b1cdbd2cSJim Jagielski }
99*b1cdbd2cSJim Jagielski 
100*b1cdbd2cSJim Jagielski 
StartElement(const Reference<XAttributeList> &)101*b1cdbd2cSJim Jagielski void XMLEventsImportContext::StartElement(
102*b1cdbd2cSJim Jagielski 	const Reference<XAttributeList> &)
103*b1cdbd2cSJim Jagielski {
104*b1cdbd2cSJim Jagielski 	// nothing to be done
105*b1cdbd2cSJim Jagielski }
106*b1cdbd2cSJim Jagielski 
EndElement()107*b1cdbd2cSJim Jagielski void XMLEventsImportContext::EndElement()
108*b1cdbd2cSJim Jagielski {
109*b1cdbd2cSJim Jagielski 	// nothing to be done
110*b1cdbd2cSJim Jagielski }
111*b1cdbd2cSJim Jagielski 
CreateChildContext(sal_uInt16 p_nPrefix,const OUString & rLocalName,const Reference<XAttributeList> & xAttrList)112*b1cdbd2cSJim Jagielski SvXMLImportContext* XMLEventsImportContext::CreateChildContext(
113*b1cdbd2cSJim Jagielski 	sal_uInt16 p_nPrefix,
114*b1cdbd2cSJim Jagielski 	const OUString& rLocalName,
115*b1cdbd2cSJim Jagielski 	const Reference<XAttributeList> & xAttrList )
116*b1cdbd2cSJim Jagielski {
117*b1cdbd2cSJim Jagielski 	// a) search for script:language and script:event-name attribute
118*b1cdbd2cSJim Jagielski 	// b) delegate to factory. The factory will:
119*b1cdbd2cSJim Jagielski 	//    1) translate XML event name into API event name
120*b1cdbd2cSJim Jagielski 	//    2) get proper event context factory from import
121*b1cdbd2cSJim Jagielski 	//    3) instantiate context
122*b1cdbd2cSJim Jagielski 
123*b1cdbd2cSJim Jagielski 	// a) search for script:language and script:event-name attribute
124*b1cdbd2cSJim Jagielski 	OUString sLanguage;
125*b1cdbd2cSJim Jagielski 	OUString sEventName;
126*b1cdbd2cSJim Jagielski 	sal_Int16 nCount = xAttrList->getLength();
127*b1cdbd2cSJim Jagielski 	for (sal_Int16 nAttr = 0; nAttr < nCount; nAttr++)
128*b1cdbd2cSJim Jagielski 	{
129*b1cdbd2cSJim Jagielski 		OUString sLocalName;
130*b1cdbd2cSJim Jagielski 		sal_uInt16 nPrefix = GetImport().GetNamespaceMap().
131*b1cdbd2cSJim Jagielski 			GetKeyByAttrName( xAttrList->getNameByIndex(nAttr), &sLocalName );
132*b1cdbd2cSJim Jagielski 
133*b1cdbd2cSJim Jagielski 		if (XML_NAMESPACE_SCRIPT == nPrefix)
134*b1cdbd2cSJim Jagielski 		{
135*b1cdbd2cSJim Jagielski 			if (IsXMLToken(sLocalName, XML_EVENT_NAME))
136*b1cdbd2cSJim Jagielski 			{
137*b1cdbd2cSJim Jagielski 				sEventName = xAttrList->getValueByIndex(nAttr);
138*b1cdbd2cSJim Jagielski 			}
139*b1cdbd2cSJim Jagielski 			else if (IsXMLToken(sLocalName, XML_LANGUAGE))
140*b1cdbd2cSJim Jagielski 			{
141*b1cdbd2cSJim Jagielski 				sLanguage = xAttrList->getValueByIndex(nAttr);
142*b1cdbd2cSJim Jagielski 			}
143*b1cdbd2cSJim Jagielski 			// else: ignore -> let child context handle this
144*b1cdbd2cSJim Jagielski 		}
145*b1cdbd2cSJim Jagielski 		// else: ignore -> let child context handle this
146*b1cdbd2cSJim Jagielski 	}
147*b1cdbd2cSJim Jagielski 
148*b1cdbd2cSJim Jagielski 	// b) delegate to factory
149*b1cdbd2cSJim Jagielski 	return GetImport().GetEventImport().CreateContext(
150*b1cdbd2cSJim Jagielski 		GetImport(), p_nPrefix, rLocalName, xAttrList,
151*b1cdbd2cSJim Jagielski 		this, sEventName, sLanguage);
152*b1cdbd2cSJim Jagielski }
153*b1cdbd2cSJim Jagielski 
SetEvents(const Reference<XEventsSupplier> & xEventsSupplier)154*b1cdbd2cSJim Jagielski void XMLEventsImportContext::SetEvents(
155*b1cdbd2cSJim Jagielski 	const Reference<XEventsSupplier> & xEventsSupplier)
156*b1cdbd2cSJim Jagielski {
157*b1cdbd2cSJim Jagielski 	if (xEventsSupplier.is())
158*b1cdbd2cSJim Jagielski 	{
159*b1cdbd2cSJim Jagielski 		SetEvents(xEventsSupplier->getEvents());
160*b1cdbd2cSJim Jagielski 	}
161*b1cdbd2cSJim Jagielski }
162*b1cdbd2cSJim Jagielski 
SetEvents(const Reference<XNameReplace> & xNameRepl)163*b1cdbd2cSJim Jagielski void XMLEventsImportContext::SetEvents(
164*b1cdbd2cSJim Jagielski 	const Reference<XNameReplace> & xNameRepl)
165*b1cdbd2cSJim Jagielski {
166*b1cdbd2cSJim Jagielski 	if (xNameRepl.is())
167*b1cdbd2cSJim Jagielski 	{
168*b1cdbd2cSJim Jagielski 		xEvents = xNameRepl;
169*b1cdbd2cSJim Jagielski 
170*b1cdbd2cSJim Jagielski 		// now iterate over vector and a) insert b) delete all elements
171*b1cdbd2cSJim Jagielski 		EventsVector::iterator aEnd = aCollectEvents.end();
172*b1cdbd2cSJim Jagielski 		for(EventsVector::iterator aIter = aCollectEvents.begin();
173*b1cdbd2cSJim Jagielski 			aIter != aEnd;
174*b1cdbd2cSJim Jagielski 			aIter++)
175*b1cdbd2cSJim Jagielski 		{
176*b1cdbd2cSJim Jagielski 			AddEventValues(aIter->first, aIter->second);
177*b1cdbd2cSJim Jagielski // 			EventNameValuesPair* pPair = &(*aIter);
178*b1cdbd2cSJim Jagielski // 			delete pPair;
179*b1cdbd2cSJim Jagielski 		}
180*b1cdbd2cSJim Jagielski 		aCollectEvents.clear();
181*b1cdbd2cSJim Jagielski 	}
182*b1cdbd2cSJim Jagielski }
183*b1cdbd2cSJim Jagielski 
GetEventSequence(const OUString & rName,Sequence<PropertyValue> & rSequence)184*b1cdbd2cSJim Jagielski sal_Bool XMLEventsImportContext::GetEventSequence(
185*b1cdbd2cSJim Jagielski     const OUString& rName,
186*b1cdbd2cSJim Jagielski     Sequence<PropertyValue> & rSequence )
187*b1cdbd2cSJim Jagielski {
188*b1cdbd2cSJim Jagielski     // search through the vector
189*b1cdbd2cSJim Jagielski     // (This shouldn't take a lot of time, since this method should only get
190*b1cdbd2cSJim Jagielski     //  called if only one (or few) events are being expected)
191*b1cdbd2cSJim Jagielski 
192*b1cdbd2cSJim Jagielski     // iterate over vector until end or rName is found;
193*b1cdbd2cSJim Jagielski     EventsVector::iterator aIter = aCollectEvents.begin();
194*b1cdbd2cSJim Jagielski     while( (aIter != aCollectEvents.end()) && (aIter->first != rName) )
195*b1cdbd2cSJim Jagielski     {
196*b1cdbd2cSJim Jagielski         aIter++;
197*b1cdbd2cSJim Jagielski     }
198*b1cdbd2cSJim Jagielski 
199*b1cdbd2cSJim Jagielski     // if we're not at the end, set the sequence
200*b1cdbd2cSJim Jagielski     sal_Bool bRet = (aIter != aCollectEvents.end());
201*b1cdbd2cSJim Jagielski     if (bRet)
202*b1cdbd2cSJim Jagielski         rSequence = aIter->second;
203*b1cdbd2cSJim Jagielski 
204*b1cdbd2cSJim Jagielski     return bRet;
205*b1cdbd2cSJim Jagielski }
206*b1cdbd2cSJim Jagielski 
AddEventValues(const OUString & rEventName,const Sequence<PropertyValue> & rValues)207*b1cdbd2cSJim Jagielski void XMLEventsImportContext::AddEventValues(
208*b1cdbd2cSJim Jagielski 	const OUString& rEventName,
209*b1cdbd2cSJim Jagielski 	const Sequence<PropertyValue> & rValues )
210*b1cdbd2cSJim Jagielski {
211*b1cdbd2cSJim Jagielski 	// if we already have the events, set them; else just collect
212*b1cdbd2cSJim Jagielski 	if (xEvents.is())
213*b1cdbd2cSJim Jagielski 	{
214*b1cdbd2cSJim Jagielski 		// set event (if name is known)
215*b1cdbd2cSJim Jagielski 		if (xEvents->hasByName(rEventName))
216*b1cdbd2cSJim Jagielski 		{
217*b1cdbd2cSJim Jagielski 			Any aAny;
218*b1cdbd2cSJim Jagielski 			aAny <<= rValues;
219*b1cdbd2cSJim Jagielski 
220*b1cdbd2cSJim Jagielski             try
221*b1cdbd2cSJim Jagielski             {
222*b1cdbd2cSJim Jagielski                 xEvents->replaceByName(rEventName, aAny);
223*b1cdbd2cSJim Jagielski             } catch ( const IllegalArgumentException & rException )
224*b1cdbd2cSJim Jagielski             {
225*b1cdbd2cSJim Jagielski                 Sequence<OUString> aMsgParams(1);
226*b1cdbd2cSJim Jagielski 
227*b1cdbd2cSJim Jagielski                 aMsgParams[0] = rEventName;
228*b1cdbd2cSJim Jagielski 
229*b1cdbd2cSJim Jagielski                 GetImport().SetError(XMLERROR_FLAG_ERROR |
230*b1cdbd2cSJim Jagielski                                      XMLERROR_ILLEGAL_EVENT,
231*b1cdbd2cSJim Jagielski                                      aMsgParams, rException.Message, 0);
232*b1cdbd2cSJim Jagielski             }
233*b1cdbd2cSJim Jagielski 		}
234*b1cdbd2cSJim Jagielski 	}
235*b1cdbd2cSJim Jagielski 	else
236*b1cdbd2cSJim Jagielski 	{
237*b1cdbd2cSJim Jagielski // 		EventNameValuesPair* aPair = new EventNameValuesPair(rEventName,
238*b1cdbd2cSJim Jagielski // 															rValues);
239*b1cdbd2cSJim Jagielski // 		aCollectEvents.push_back(*aPair);
240*b1cdbd2cSJim Jagielski 		EventNameValuesPair aPair(rEventName, rValues);
241*b1cdbd2cSJim Jagielski 		aCollectEvents.push_back(aPair);
242*b1cdbd2cSJim Jagielski 	}
243*b1cdbd2cSJim Jagielski }
244