Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*************************************************************************
3 : : *
4 : : * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 : : *
6 : : * Copyright 2000, 2010 Oracle and/or its affiliates.
7 : : *
8 : : * OpenOffice.org - a multi-platform office productivity suite
9 : : *
10 : : * This file is part of OpenOffice.org.
11 : : *
12 : : * OpenOffice.org is free software: you can redistribute it and/or modify
13 : : * it under the terms of the GNU Lesser General Public License version 3
14 : : * only, as published by the Free Software Foundation.
15 : : *
16 : : * OpenOffice.org is distributed in the hope that it will be useful,
17 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 : : * GNU Lesser General Public License version 3 for more details
20 : : * (a copy is included in the LICENSE file that accompanied this code).
21 : : *
22 : : * You should have received a copy of the GNU Lesser General Public License
23 : : * version 3 along with OpenOffice.org. If not, see
24 : : * <http://www.openoffice.org/license.html>
25 : : * for a copy of the LGPLv3 License.
26 : : *
27 : : ************************************************************************/
28 : :
29 : :
30 : : #include "model.hxx"
31 : : #include "model_helper.hxx"
32 : : #include "mip.hxx"
33 : : #include "evaluationcontext.hxx"
34 : : #include "unohelper.hxx"
35 : : #include "submission/serialization_app_xml.hxx"
36 : : #include "resourcehelper.hxx"
37 : : #include "xmlhelper.hxx"
38 : : #include "convert.hxx"
39 : :
40 : : #include <rtl/ustring.hxx>
41 : : #include <rtl/ustrbuf.hxx>
42 : : #include <tools/debug.hxx>
43 : :
44 : : // UNO classes
45 : : #include <com/sun/star/xml/dom/XNode.hpp>
46 : : #include <com/sun/star/xml/dom/XDocumentBuilder.hpp>
47 : : #include <com/sun/star/xml/dom/XDocumentFragment.hpp>
48 : : #include <com/sun/star/xml/dom/XNamedNodeMap.hpp>
49 : : #include <com/sun/star/xml/xpath/XXPathObject.hpp>
50 : : #include <com/sun/star/xml/xpath/XPathObjectType.hpp>
51 : : #include <com/sun/star/beans/PropertyValue.hpp>
52 : : #include <com/sun/star/io/XInputStream.hpp>
53 : : #include <com/sun/star/io/XActiveDataSink.hpp>
54 : : #include <com/sun/star/io/XTextInputStream.hpp>
55 : : #include <com/sun/star/container/XEnumeration.hpp>
56 : : #include <com/sun/star/container/XNameContainer.hpp>
57 : : #include <com/sun/star/frame/XModel.hpp>
58 : : #include <com/sun/star/xforms/XFormsSupplier.hpp>
59 : : #include <com/sun/star/xforms/XDataTypeRepository.hpp>
60 : : #include <com/sun/star/xsd/XDataType.hpp>
61 : : #include <com/sun/star/xsd/DataTypeClass.hpp>
62 : :
63 : :
64 : : using rtl::OUString;
65 : : using rtl::OUStringBuffer;
66 : : using com::sun::star::beans::PropertyValue;
67 : : using com::sun::star::io::XInputStream;
68 : : using com::sun::star::io::XActiveDataSink;
69 : : using com::sun::star::io::XTextInputStream;
70 : : using com::sun::star::container::XEnumeration;
71 : : using com::sun::star::container::XNameContainer;
72 : : using com::sun::star::xforms::XFormsSupplier;
73 : :
74 : : using namespace xforms;
75 : : using namespace com::sun::star::uno;
76 : : using namespace com::sun::star::xml::dom;
77 : : using namespace com::sun::star::xml::xpath;
78 : :
79 : :
80 : :
81 : : //
82 : : // implement XFormsUIHelper1
83 : : //
84 : :
85 : 0 : OUString Model::getDefaultServiceNameForNode( const XNode_t& xNode )
86 : : throw( RuntimeException )
87 : : {
88 : : // determine service for control. string/text field is default.
89 [ # # ]: 0 : OUString sService = OUSTRING("com.sun.star.form.component.TextField");
90 : :
91 : : // query repository for suitable type
92 : : OSL_ENSURE( mxDataTypes.is(), "no type repository?" );
93 [ # # ][ # # ]: 0 : OUString sTypeName = queryMIP( xNode ).getTypeName();
[ # # ]
94 [ # # ][ # # ]: 0 : if( mxDataTypes->hasByName( sTypeName ) )
[ # # ]
95 : : {
96 : : OSL_ENSURE( mxDataTypes->getDataType( sTypeName ).is(),
97 : : "has or has not?" );
98 : :
99 [ # # ][ # # ]: 0 : switch( mxDataTypes->getDataType( sTypeName )->getTypeClass() )
[ # # ][ # # ]
[ # # # ]
100 : : {
101 : : case com::sun::star::xsd::DataTypeClass::BOOLEAN:
102 [ # # ]: 0 : sService = OUSTRING("com.sun.star.form.component.CheckBox");
103 : 0 : break;
104 : : case com::sun::star::xsd::DataTypeClass::DOUBLE:
105 : : case com::sun::star::xsd::DataTypeClass::DECIMAL:
106 : : case com::sun::star::xsd::DataTypeClass::FLOAT:
107 [ # # ]: 0 : sService = OUSTRING("com.sun.star.form.component.NumericField");
108 : 0 : break;
109 : :
110 : : case com::sun::star::xsd::DataTypeClass::STRING:
111 : : case com::sun::star::xsd::DataTypeClass::DURATION:
112 : : case com::sun::star::xsd::DataTypeClass::DATETIME:
113 : : case com::sun::star::xsd::DataTypeClass::TIME:
114 : : case com::sun::star::xsd::DataTypeClass::DATE:
115 : : case com::sun::star::xsd::DataTypeClass::gYearMonth:
116 : : case com::sun::star::xsd::DataTypeClass::gYear:
117 : : case com::sun::star::xsd::DataTypeClass::gMonthDay:
118 : : case com::sun::star::xsd::DataTypeClass::gDay:
119 : : case com::sun::star::xsd::DataTypeClass::gMonth:
120 : : case com::sun::star::xsd::DataTypeClass::hexBinary:
121 : : case com::sun::star::xsd::DataTypeClass::base64Binary:
122 : : case com::sun::star::xsd::DataTypeClass::anyURI:
123 : : case com::sun::star::xsd::DataTypeClass::QName:
124 : : case com::sun::star::xsd::DataTypeClass::NOTATION:
125 : : default:
126 : : // keep default
127 : 0 : break;
128 : : }
129 : : }
130 : :
131 : 0 : return sService;
132 : : }
133 : :
134 : :
135 : 0 : void lcl_OutPosition( OUStringBuffer& rBuffer,
136 : : const Reference<XNode>& xNode )
137 : : {
138 : : OSL_ENSURE( xNode->getParentNode().is(), "need parent" );
139 : :
140 : : // count # of occurrences of this node
141 : 0 : sal_Int32 nFound = 0;
142 : 0 : sal_Int32 nPosition = -1;
143 [ # # ]: 0 : if( xNode->getParentNode().is() )
144 : : {
145 [ # # ][ # # ]: 0 : for( Reference<XNode> xIter = xNode->getParentNode()->getFirstChild();
[ # # ][ # # ]
[ # # ][ # # ]
146 [ # # ]: 0 : xIter != NULL;
147 [ # # ][ # # ]: 0 : xIter = xIter->getNextSibling() )
148 : : {
149 [ # # ][ # # ]: 0 : if( xIter->getNodeType() == xNode->getNodeType() &&
[ # # ][ # # ]
[ # # # #
# # ][ # # ]
150 [ # # ][ # # ]: 0 : xIter->getNodeName() == xNode->getNodeName() &&
[ # # ][ # # ]
[ # # ][ # # ]
[ # # # # ]
151 [ # # ][ # # ]: 0 : xIter->getNamespaceURI() == xNode->getNamespaceURI() )
[ # # ][ # # ]
[ # # ][ # # ]
[ # # # # ]
152 : : {
153 : 0 : nFound++;
154 [ # # ][ # # ]: 0 : if( xIter == xNode )
155 : 0 : nPosition = nFound;
156 : : }
157 : 0 : }
158 : : }
159 : : OSL_ENSURE( nFound > 0 && nPosition > 0, "node not found???" );
160 : :
161 : : // output position (if necessary)
162 [ # # ]: 0 : if( nFound > 1 )
163 : : {
164 : 0 : rBuffer.insert( 0, sal_Unicode(']') );
165 : 0 : rBuffer.insert( 0, nPosition );
166 : 0 : rBuffer.insert( 0, sal_Unicode('[') );
167 : : }
168 : 0 : }
169 : :
170 : 0 : void lcl_OutName( OUStringBuffer& rBuffer,
171 : : const Reference<XNode>& xNode )
172 : : {
173 [ # # ][ # # ]: 0 : rBuffer.insert( 0, xNode->getNodeName() );
[ # # ]
174 [ # # ][ # # ]: 0 : OUString sPrefix = xNode->getPrefix();
175 [ # # ]: 0 : if( !sPrefix.isEmpty() )
176 : : {
177 [ # # ]: 0 : rBuffer.insert( 0, sal_Unicode(':') );
178 [ # # ]: 0 : rBuffer.insert( 0, sPrefix );
179 : 0 : }
180 : 0 : }
181 : :
182 : 0 : void lcl_OutInstance( OUStringBuffer& rBuffer,
183 : : const Reference<XNode>& xNode,
184 : : Model* pModel )
185 : : {
186 [ # # ][ # # ]: 0 : Reference<XDocument> xDoc = xNode->getOwnerDocument();
187 : :
188 [ # # ][ # # ]: 0 : if( xDoc != pModel->getDefaultInstance() )
[ # # ]
189 : : {
190 [ # # ][ # # ]: 0 : rBuffer.insert( 0, OUSTRING("')") );
191 : :
192 : : // iterate over instances, and find the right one
193 : 0 : OUString sInstanceName;
194 : : Reference<XEnumeration> xEnum =
195 [ # # ][ # # ]: 0 : pModel->getInstances()->createEnumeration();
[ # # ]
196 [ # # ][ # # ]: 0 : while( sInstanceName.isEmpty() && xEnum->hasMoreElements() )
[ # # ][ # # ]
[ # # ]
197 : : {
198 [ # # ]: 0 : Sequence<PropertyValue> aValues;
199 [ # # ][ # # ]: 0 : xEnum->nextElement() >>= aValues;
[ # # ]
200 : :
201 : : // get ID and instance
202 : 0 : OUString sId;
203 : 0 : Reference<XDocument> xInstance;
204 [ # # ]: 0 : getInstanceData( aValues, &sId, &xInstance, NULL, NULL );
205 : :
206 : : // now check whether this was our instance:
207 [ # # ][ # # ]: 0 : if( xInstance == xDoc )
208 : 0 : sInstanceName = sId;
209 [ # # ]: 0 : }
210 : :
211 [ # # ]: 0 : rBuffer.insert( 0, sInstanceName );
212 [ # # ][ # # ]: 0 : rBuffer.insert( 0, OUSTRING("instance('") );
213 : 0 : }
214 : 0 : }
215 : :
216 : 0 : OUString Model::getDefaultBindingExpressionForNode(
217 : : const XNode_t& xNode,
218 : : const EvaluationContext& rContext)
219 : : {
220 : : OSL_ENSURE( xNode.is(), "need node" );
221 : :
222 : : // iterate upwards and put sections into the expression buffer.
223 : : // Stop iteration either at context node (relative expression) or
224 : : // at document root, whichever occurs first.
225 : 0 : OUStringBuffer aBuffer;
226 [ # # # # ]: 0 : for( Reference<XNode> xCurrent = xNode;
[ # # ][ # # ]
227 [ # # ]: 0 : xCurrent.is() && xCurrent != rContext.mxContextNode;
228 [ # # ][ # # ]: 0 : xCurrent = xCurrent->getParentNode() )
229 : : {
230 : : // insert a '/' for every step except the first
231 [ # # ]: 0 : if( aBuffer.getLength() > 0 )
232 [ # # ]: 0 : aBuffer.insert( 0, sal_Unicode('/') );
233 : :
234 [ # # ][ # # ]: 0 : switch( xCurrent->getNodeType() )
[ # # # #
# ]
235 : : {
236 : : case NodeType_ELEMENT_NODE:
237 [ # # ]: 0 : lcl_OutPosition( aBuffer, xCurrent );
238 [ # # ]: 0 : lcl_OutName( aBuffer, xCurrent );
239 : 0 : break;
240 : :
241 : : case NodeType_TEXT_NODE:
242 [ # # ]: 0 : lcl_OutPosition( aBuffer, xCurrent );
243 [ # # ][ # # ]: 0 : aBuffer.insert( 0, OUSTRING("text()") );
244 : 0 : break;
245 : :
246 : : case NodeType_ATTRIBUTE_NODE:
247 [ # # ]: 0 : lcl_OutName( aBuffer, xCurrent );
248 [ # # ]: 0 : aBuffer.insert( 0, sal_Unicode('@') );
249 : 0 : break;
250 : :
251 : : case NodeType_DOCUMENT_NODE:
252 : : // check for which instance we have
253 [ # # ]: 0 : lcl_OutInstance( aBuffer, xCurrent, this );
254 : 0 : break;
255 : :
256 : : default:
257 : : // unknown type? fail!
258 : : OSL_FAIL( "unknown node type!" );
259 [ # # ]: 0 : xCurrent.set( NULL );
260 [ # # ]: 0 : aBuffer.makeStringAndClear();
261 : : // we'll remove the slash below
262 [ # # ]: 0 : aBuffer.insert( 0, sal_Unicode('/') );
263 : 0 : break;
264 : : }
265 : 0 : }
266 : :
267 [ # # ]: 0 : return aBuffer.makeStringAndClear();
268 : : }
269 : :
270 : :
271 : :
272 : 0 : OUString Model::getDefaultBindingExpressionForNode( const XNode_t& xNode )
273 : : throw( RuntimeException )
274 : : {
275 [ # # ]: 0 : return getDefaultBindingExpressionForNode( xNode, getEvaluationContext() );
276 : : }
277 : :
278 : 0 : bool lcl_isWhitespace( const OUString& rString )
279 : : {
280 : 0 : sal_Int32 nLength = rString.getLength();
281 : 0 : const sal_Unicode* pStr = rString.getStr();
282 : :
283 : 0 : bool bWhitespace = true;
284 [ # # ][ # # ]: 0 : for( sal_Int32 i = 0; bWhitespace && ( i < nLength ); i++ )
[ # # ]
285 : : {
286 : 0 : sal_Unicode c = pStr[i];
287 : : bWhitespace = ( c == sal_Unicode(0x09) ||
288 : : c == sal_Unicode(0x0A) ||
289 : : c == sal_Unicode(0x0D) ||
290 [ # # ][ # # ]: 0 : c == sal_Unicode(0x20) );
[ # # ][ # # ]
291 : : }
292 : 0 : return bWhitespace;
293 : : }
294 : :
295 : 0 : OUString Model::getNodeDisplayName( const XNode_t& xNode,
296 : : sal_Bool bDetail )
297 : : throw( RuntimeException )
298 : : {
299 : 0 : OUStringBuffer aBuffer;
300 : :
301 [ # # ][ # # : 0 : switch( xNode->getNodeType() )
# # # ]
[ # # ]
302 : : {
303 : : case NodeType_ELEMENT_NODE:
304 [ # # ]: 0 : lcl_OutName( aBuffer, xNode );
305 : 0 : break;
306 : :
307 : : case NodeType_TEXT_NODE:
308 : : {
309 [ # # ][ # # ]: 0 : OUString sContent = xNode->getNodeValue();
310 [ # # ][ # # ]: 0 : if( bDetail || ! lcl_isWhitespace( sContent ) )
[ # # ]
311 : : {
312 [ # # ]: 0 : aBuffer.append( sal_Unicode('"') );
313 [ # # ][ # # ]: 0 : aBuffer.append( Convert::collapseWhitespace( sContent ) );
314 [ # # ]: 0 : aBuffer.append( sal_Unicode('"') );
315 : 0 : }
316 : : }
317 : 0 : break;
318 : :
319 : : case NodeType_ATTRIBUTE_NODE:
320 [ # # ]: 0 : lcl_OutName( aBuffer, xNode );
321 [ # # ]: 0 : aBuffer.insert( 0, sal_Unicode('@') );
322 : 0 : break;
323 : :
324 : : case NodeType_DOCUMENT_NODE:
325 [ # # ][ # # ]: 0 : if( xNode == getDefaultInstance() )
[ # # ]
326 [ # # ]: 0 : aBuffer.append( sal_Unicode('/') );
327 : : else
328 [ # # ]: 0 : lcl_OutInstance( aBuffer, xNode, this );
329 : 0 : break;
330 : :
331 : : default:
332 : : // unknown type? fail!
333 : : OSL_FAIL( "unknown node type!" );
334 : 0 : break;
335 : : }
336 : :
337 [ # # ]: 0 : return aBuffer.makeStringAndClear();
338 : : }
339 : :
340 : 0 : OUString Model::getNodeName( const XNode_t& xNode )
341 : : throw( RuntimeException )
342 : : {
343 : 0 : OUStringBuffer aBuffer;
344 : :
345 [ # # ][ # # ]: 0 : switch( xNode->getNodeType() )
[ # # ]
346 : : {
347 : : case NodeType_ELEMENT_NODE:
348 : : case NodeType_ATTRIBUTE_NODE:
349 [ # # ]: 0 : lcl_OutName( aBuffer, xNode );
350 : 0 : break;
351 : :
352 : : case NodeType_TEXT_NODE:
353 : : case NodeType_DOCUMENT_NODE:
354 : : default:
355 : : // unknown type? fail!
356 : : OSL_FAIL( "no name for this node type!" );
357 : 0 : break;
358 : : }
359 : :
360 [ # # ]: 0 : return aBuffer.makeStringAndClear();
361 : : }
362 : :
363 : 0 : OUString Model::getBindingName( const XPropertySet_t& xBinding,
364 : : sal_Bool /*bDetail*/ )
365 : : throw( RuntimeException )
366 : : {
367 : 0 : OUString sID;
368 [ # # ][ # # ]: 0 : xBinding->getPropertyValue( OUSTRING("BindingID" ) ) >>= sID;
[ # # ]
369 : 0 : OUString sExpression;
370 [ # # ][ # # ]: 0 : xBinding->getPropertyValue( OUSTRING("BindingExpression" ) ) >>= sExpression;
[ # # ]
371 : :
372 : 0 : OUStringBuffer aBuffer;
373 [ # # ]: 0 : if( !sID.isEmpty() )
374 : : {
375 [ # # ]: 0 : aBuffer.append( sID );
376 [ # # ][ # # ]: 0 : aBuffer.append( OUSTRING(" (" ));
377 [ # # ]: 0 : aBuffer.append( sExpression );
378 [ # # ][ # # ]: 0 : aBuffer.append( OUSTRING(")" ));
379 : : }
380 : : else
381 [ # # ]: 0 : aBuffer.append( sExpression );
382 : :
383 [ # # ]: 0 : return aBuffer.makeStringAndClear();
384 : : }
385 : :
386 : 0 : OUString Model::getSubmissionName( const XPropertySet_t& xSubmission,
387 : : sal_Bool /*bDetail*/ )
388 : : throw( RuntimeException )
389 : : {
390 : 0 : OUString sID;
391 [ # # ][ # # ]: 0 : xSubmission->getPropertyValue( OUSTRING("ID") ) >>= sID;
[ # # ]
392 : 0 : return sID;
393 : : }
394 : :
395 : 0 : Model::XPropertySet_t Model::cloneBindingAsGhost( const XPropertySet_t &xBinding )
396 : : throw( RuntimeException )
397 : : {
398 : : // Create a new binding instance first...
399 [ # # ]: 0 : Binding *pBinding = new Binding();
400 : :
401 : : // ...and bump up the "defered notification counter"
402 : : // to prevent this binding from contributing to the
403 : : // MIPs table...
404 : 0 : pBinding->deferNotifications(true);
405 : :
406 : : // Copy the propertyset and return result...
407 [ # # ]: 0 : XPropertySet_t xNewBinding(pBinding);
408 [ # # ]: 0 : copy( xBinding, xNewBinding );
409 : 0 : return xNewBinding;
410 : : }
411 : :
412 : 0 : void Model::removeBindingIfUseless( const XPropertySet_t& xBinding )
413 : : throw( RuntimeException )
414 : : {
415 : 0 : Binding* pBinding = Binding::getBinding( xBinding );
416 [ # # ]: 0 : if( pBinding != NULL )
417 : : {
418 [ # # ]: 0 : if( ! pBinding->isUseful() )
419 [ # # ][ # # ]: 0 : mpBindings->removeItem( pBinding );
420 : : }
421 : 0 : }
422 : :
423 : 0 : Model::XDocument_t Model::newInstance( const rtl::OUString& sName,
424 : : const rtl::OUString& sURL,
425 : : sal_Bool bURLOnce )
426 : : throw( RuntimeException )
427 : : {
428 : : // create a default instance with <instanceData> element
429 [ # # ][ # # ]: 0 : XDocument_t xInstance = getDocumentBuilder()->newDocument();
[ # # ]
430 : : DBG_ASSERT( xInstance.is(), "failed to create DOM instance" );
431 : :
432 [ # # ][ # # ]: 0 : Reference<XNode>( xInstance, UNO_QUERY_THROW )->appendChild(
433 [ # # ]: 0 : Reference<XNode>( xInstance->createElement( OUSTRING("instanceData") ),
434 [ # # ][ # # ]: 0 : UNO_QUERY_THROW ) );
[ # # ][ # # ]
435 : :
436 [ # # ]: 0 : Sequence<PropertyValue> aSequence;
437 : 0 : bool bOnce = bURLOnce; // bool, so we can take address in setInstanceData
438 [ # # ]: 0 : setInstanceData( aSequence, &sName, &xInstance, &sURL, &bOnce );
439 [ # # ]: 0 : sal_Int32 nInstance = mpInstances->addItem( aSequence );
440 [ # # ]: 0 : loadInstance( nInstance );
441 : :
442 [ # # ]: 0 : return xInstance;
443 : : }
444 : :
445 : 0 : sal_Int32 lcl_findProp( const PropertyValue* pValues,
446 : : sal_Int32 nLength,
447 : : const rtl::OUString& rName )
448 : : {
449 : 0 : bool bFound = false;
450 : 0 : sal_Int32 n = 0;
451 [ # # ][ # # ]: 0 : for( ; !bFound && n < nLength; n++ )
[ # # ]
452 : : {
453 : 0 : bFound = ( pValues[n].Name == rName );
454 : : }
455 [ # # ]: 0 : return bFound ? ( n - 1) : -1;
456 : : }
457 : :
458 : 0 : sal_Int32 xforms::lcl_findInstance( const InstanceCollection* pInstances,
459 : : const rtl::OUString& rName )
460 : : {
461 : 0 : sal_Int32 nLength = pInstances->countItems();
462 : 0 : sal_Int32 n = 0;
463 : 0 : bool bFound = false;
464 [ # # ][ # # ]: 0 : for( ; !bFound && n < nLength; n++ )
[ # # ]
465 : : {
466 : 0 : OUString sName;
467 [ # # ][ # # ]: 0 : getInstanceData( pInstances->getItem( n ), &sName, NULL, NULL, NULL );
468 : 0 : bFound = ( sName == rName );
469 : 0 : }
470 [ # # ]: 0 : return bFound ? ( n - 1 ) : -1;
471 : : }
472 : :
473 : 0 : void Model::renameInstance( const rtl::OUString& sFrom,
474 : : const rtl::OUString& sTo,
475 : : const rtl::OUString& sURL,
476 : : sal_Bool bURLOnce )
477 : : throw( RuntimeException )
478 : : {
479 : 0 : sal_Int32 nPos = lcl_findInstance( mpInstances, sFrom );
480 [ # # ]: 0 : if( nPos != -1 )
481 : : {
482 [ # # ][ # # ]: 0 : Sequence<PropertyValue> aSeq = mpInstances->getItem( nPos );
483 [ # # ]: 0 : PropertyValue* pSeq = aSeq.getArray();
484 : 0 : sal_Int32 nLength = aSeq.getLength();
485 : :
486 [ # # ]: 0 : sal_Int32 nProp = lcl_findProp( pSeq, nLength, OUSTRING("ID") );
487 [ # # ]: 0 : if( nProp == -1 )
488 : : {
489 : : // add name property
490 [ # # ]: 0 : aSeq.realloc( nLength + 1 );
491 [ # # ]: 0 : pSeq = aSeq.getArray();
492 [ # # ]: 0 : pSeq[ nLength ].Name = OUSTRING("ID");
493 : 0 : nProp = nLength;
494 : : }
495 : :
496 : : // change name
497 [ # # ]: 0 : pSeq[ nProp ].Value <<= sTo;
498 : :
499 : : // change url
500 [ # # ]: 0 : nProp = lcl_findProp( pSeq, nLength, OUSTRING("URL") );
501 [ # # ]: 0 : if(nProp != -1)
502 [ # # ]: 0 : pSeq[ nProp ].Value <<= sURL;
503 : :
504 : : // change urlonce
505 [ # # ]: 0 : nProp = lcl_findProp( pSeq, nLength, OUSTRING("URLOnce") );
506 [ # # ]: 0 : if(nProp != -1)
507 [ # # ]: 0 : pSeq[ nProp ].Value <<= bURLOnce;
508 : :
509 : : // set instance
510 [ # # ][ # # ]: 0 : mpInstances->setItem( nPos, aSeq );
511 : : }
512 : 0 : }
513 : :
514 : 0 : void Model::removeInstance( const rtl::OUString& sName )
515 : : throw( RuntimeException )
516 : : {
517 : 0 : sal_Int32 nPos = lcl_findInstance( mpInstances, sName );
518 [ # # ]: 0 : if( nPos != -1 )
519 : 0 : mpInstances->removeItem( mpInstances->getItem( nPos ) );
520 : 0 : }
521 : :
522 : 0 : Reference<XNameContainer> lcl_getModels(
523 : : const Reference<com::sun::star::frame::XModel>& xComponent )
524 : : {
525 : 0 : Reference<XNameContainer> xRet;
526 [ # # ]: 0 : Reference<XFormsSupplier> xSupplier( xComponent, UNO_QUERY );
527 [ # # ]: 0 : if( xSupplier.is() )
528 : : {
529 [ # # ][ # # ]: 0 : xRet = xSupplier->getXForms();
[ # # ]
530 : : }
531 : 0 : return xRet;
532 : : }
533 : :
534 : 0 : Model::XModel_t Model::newModel( const Reference<com::sun::star::frame::XModel>& xCmp,
535 : : const OUString& sName )
536 : : throw( RuntimeException )
537 : : {
538 : 0 : Model::XModel_t xModel;
539 [ # # ]: 0 : Reference<XNameContainer> xModels = lcl_getModels( xCmp );
540 [ # # ][ # # ]: 0 : if( xModels.is()
[ # # ]
541 [ # # ][ # # ]: 0 : && ! xModels->hasByName( sName ) )
542 : : {
543 [ # # ]: 0 : Model* pModel = new Model();
544 [ # # ][ # # ]: 0 : xModel.set( pModel );
545 : :
546 [ # # ]: 0 : pModel->setID( sName );
547 [ # # ]: 0 : pModel->newInstance( OUString(), OUString(), sal_False );
548 [ # # ]: 0 : pModel->initialize();
549 [ # # ][ # # ]: 0 : xModels->insertByName( sName, makeAny( xModel ) );
[ # # ]
550 : : }
551 : :
552 : 0 : return xModel;
553 : : }
554 : :
555 : 0 : void Model::renameModel( const Reference<com::sun::star::frame::XModel>& xCmp,
556 : : const OUString& sFrom,
557 : : const OUString& sTo )
558 : : throw( RuntimeException )
559 : : {
560 [ # # ]: 0 : Reference<XNameContainer> xModels = lcl_getModels( xCmp );
561 [ # # ][ # # ]: 0 : if( xModels.is()
[ # # ][ # # ]
562 [ # # ][ # # ]: 0 : && xModels->hasByName( sFrom )
563 [ # # ][ # # ]: 0 : && ! xModels->hasByName( sTo ) )
564 : : {
565 [ # # ][ # # ]: 0 : Reference<XModel> xModel( xModels->getByName( sFrom ), UNO_QUERY );
[ # # ]
566 [ # # ][ # # ]: 0 : xModel->setID( sTo );
567 [ # # ][ # # ]: 0 : xModels->insertByName( sTo, makeAny( xModel ) );
[ # # ]
568 [ # # ][ # # ]: 0 : xModels->removeByName( sFrom );
569 : 0 : }
570 : 0 : }
571 : :
572 : 0 : void Model::removeModel( const Reference<com::sun::star::frame::XModel>& xCmp,
573 : : const OUString& sName )
574 : : throw( RuntimeException )
575 : : {
576 [ # # ]: 0 : Reference<XNameContainer> xModels = lcl_getModels( xCmp );
577 [ # # ][ # # ]: 0 : if( xModels.is()
[ # # ]
578 [ # # ][ # # ]: 0 : && xModels->hasByName( sName ) )
579 : : {
580 [ # # ][ # # ]: 0 : xModels->removeByName( sName );
581 : 0 : }
582 : 0 : }
583 : :
584 : 0 : Model::XNode_t Model::createElement( const XNode_t& xParent,
585 : : const OUString& sName )
586 : : throw( RuntimeException )
587 : : {
588 : 0 : Reference<XNode> xNode;
589 [ # # ][ # # ]: 0 : if( xParent.is()
[ # # ]
590 [ # # ]: 0 : && isValidXMLName( sName ) )
591 : : {
592 : : // TODO: implement proper namespace handling
593 [ # # ][ # # ]: 0 : xNode.set( xParent->getOwnerDocument()->createElement( sName ),
[ # # ]
594 [ # # ][ # # ]: 0 : UNO_QUERY );
595 : : }
596 : 0 : return xNode;
597 : : }
598 : :
599 : 0 : Model::XNode_t Model::createAttribute( const XNode_t& xParent,
600 : : const OUString& sName )
601 : : throw( RuntimeException )
602 : : {
603 : 0 : Reference<XNode> xNode;
604 [ # # ]: 0 : Reference<XElement> xElement( xParent, UNO_QUERY );
605 [ # # # # ]: 0 : if( xParent.is()
[ # # ][ # # ]
606 : 0 : && xElement.is()
607 [ # # ]: 0 : && isValidXMLName( sName ) )
608 : : {
609 : : // handle case where attribute already exists
610 : 0 : sal_Int32 nCount = 0;
611 : 0 : OUString sUniqueName = sName;
612 [ # # ][ # # ]: 0 : while( xElement->hasAttribute( sUniqueName ) )
[ # # ]
613 : : {
614 : 0 : nCount++;
615 : 0 : sUniqueName = sName + OUString::valueOf( nCount );
616 : : }
617 : :
618 : : // TODO: implement proper namespace handling
619 [ # # ][ # # ]: 0 : xNode.set( xParent->getOwnerDocument()->createAttribute( sUniqueName ),
[ # # ]
620 [ # # ][ # # ]: 0 : UNO_QUERY );
621 : : }
622 : 0 : return xNode;
623 : : }
624 : :
625 : 0 : Model::XNode_t Model::renameNode( const XNode_t& xNode,
626 : : const rtl::OUString& sName )
627 : : throw( RuntimeException )
628 : : {
629 : : // early out if we don't have to change the name
630 [ # # ][ # # ]: 0 : if( xNode->getNodeName() == sName )
[ # # ]
631 : 0 : return xNode;
632 : :
633 : : // refuse to change name if its an attribute, and the name is already used
634 [ # # ][ # # ]: 0 : if( xNode->getNodeType() == NodeType_ATTRIBUTE_NODE
[ # # # # ]
[ # # ][ # # ]
635 [ # # ][ # # ]: 0 : && xNode->getParentNode().is()
[ # # ][ # # ]
636 [ # # ][ # # ]: 0 : && Reference<XElement>(xNode->getParentNode(), UNO_QUERY_THROW)->hasAttribute( sName ) )
[ # # ][ # # ]
[ # # ][ # # ]
[ # # ]
[ # # # # ]
637 : 0 : return xNode;
638 : :
639 : : // note old binding expression so we can adjust bindings below
640 : : OUString sOldDefaultBindingExpression =
641 [ # # ]: 0 : getDefaultBindingExpressionForNode( xNode );
642 : :
643 [ # # ][ # # ]: 0 : Reference<XDocument> xDoc = xNode->getOwnerDocument();
644 : 0 : Reference<XNode> xNew;
645 [ # # ][ # # ]: 0 : if( xNode->getNodeType() == NodeType_ELEMENT_NODE )
[ # # ]
646 : : {
647 [ # # ][ # # ]: 0 : Reference<XElement> xElem = xDoc->createElement( sName );
648 [ # # ]: 0 : xNew.set( xElem, UNO_QUERY );
649 : :
650 : : // iterate over all attributes and append them to the new element
651 [ # # ]: 0 : Reference<XElement> xOldElem( xNode, UNO_QUERY );
652 : : OSL_ENSURE( xNode.is(), "no element?" );
653 : :
654 [ # # ][ # # ]: 0 : Reference<XNamedNodeMap> xMap = xNode->getAttributes();
655 [ # # ][ # # ]: 0 : sal_Int32 nLength = xMap.is() ? xMap->getLength() : 0;
[ # # ]
656 [ # # ]: 0 : for( sal_Int32 n = 0; n < nLength; n++ )
657 : : {
658 [ # # ][ # # ]: 0 : Reference<XAttr> xAttr( xMap->item(n), UNO_QUERY );
[ # # ]
659 [ # # ][ # # ]: 0 : xElem->setAttributeNode( xOldElem->removeAttributeNode( xAttr ) );
[ # # ][ # # ]
660 : 0 : }
661 : :
662 : : // iterate over all children and append them to the new element
663 [ # # ][ # # ]: 0 : for( Reference<XNode> xCurrent = xNode->getFirstChild();
[ # # # # ]
664 : 0 : xCurrent.is();
665 [ # # ][ # # ]: 0 : xCurrent = xNode->getFirstChild() )
666 : : {
667 [ # # ][ # # ]: 0 : xNew->appendChild( xNode->removeChild( xCurrent ) );
[ # # ][ # # ]
668 : 0 : }
669 : :
670 [ # # ][ # # ]: 0 : xNode->getParentNode()->replaceChild( xNew, xNode );
[ # # ][ # # ]
671 : : }
672 [ # # ][ # # ]: 0 : else if( xNode->getNodeType() == NodeType_ATTRIBUTE_NODE )
[ # # ]
673 : : {
674 : : // create new attribute
675 [ # # ][ # # ]: 0 : Reference<XAttr> xAttr = xDoc->createAttribute( sName );
676 [ # # ][ # # ]: 0 : xAttr->setValue( xNode->getNodeValue() );
[ # # ][ # # ]
677 : :
678 : : // replace node
679 [ # # ][ # # ]: 0 : Reference<XNode> xParent = xNode->getParentNode();
680 [ # # ][ # # ]: 0 : xParent->removeChild( xNode );
681 [ # # ][ # # ]: 0 : xNew = xParent->appendChild( Reference<XNode>( xAttr, UNO_QUERY ) );
[ # # ][ # # ]
682 : : }
683 : : else
684 : : {
685 : : OSL_FAIL( "can't rename this node type" );
686 : : }
687 : :
688 : : // adjust bindings (if necessary):
689 [ # # ]: 0 : if( xNew.is() )
690 : : {
691 : : // iterate over bindings and replace default expressions
692 : : OUString sNewDefaultBindingExpression =
693 [ # # ]: 0 : getDefaultBindingExpressionForNode( xNew );
694 [ # # ]: 0 : for( sal_Int32 n = 0; n < mpBindings->countItems(); n++ )
695 : : {
696 : : Binding* pBinding = Binding::getBinding(
697 [ # # ][ # # ]: 0 : mpBindings->Collection<XPropertySet_t>::getItem( n ) );
698 : :
699 [ # # ]: 0 : if( pBinding->getBindingExpression()
700 [ # # ]: 0 : == sOldDefaultBindingExpression )
701 [ # # ]: 0 : pBinding->setBindingExpression( sNewDefaultBindingExpression );
702 : 0 : }
703 : : }
704 : :
705 : : // return node; return old node if renaming failed
706 [ # # ]: 0 : return xNew.is() ? xNew : xNode;
707 : : }
708 : :
709 : 0 : Model::XPropertySet_t Model::getBindingForNode( const XNode_t& xNode,
710 : : sal_Bool bCreate )
711 : : throw( RuntimeException )
712 : : {
713 : : OSL_ENSURE( xNode.is(), "no node?" );
714 : :
715 : : // We will iterate over all bindings and determine the
716 : : // appropriateness of the respective binding for this node. The
717 : : // best one will be used. If we don't find any and bCreate is set,
718 : : // then we will create a suitable binding.
719 : 0 : Binding* pBestBinding = NULL;
720 : 0 : sal_Int32 nBestScore = 0;
721 : :
722 [ # # ]: 0 : for( sal_Int32 n = 0; n < mpBindings->countItems(); n++ )
723 : : {
724 : : Binding* pBinding = Binding::getBinding(
725 [ # # ][ # # ]: 0 : mpBindings->Collection<XPropertySet_t>::getItem( n ) );
726 : :
727 : : OSL_ENSURE( pBinding != NULL, "no binding?" );
728 [ # # ]: 0 : Reference<XNodeList> xNodeList = pBinding->getXNodeList();
729 : :
730 [ # # ][ # # ]: 0 : sal_Int32 nNodes = xNodeList.is() ? xNodeList->getLength() : 0;
[ # # ]
731 [ # # ][ # # ]: 0 : if( nNodes > 0 && xNodeList->item( 0 ) == xNode )
[ # # ][ # # ]
[ # # ][ # # ]
[ # # # # ]
732 : : {
733 : : // allright, we found a suitable node. Let's determine how
734 : : // well it fits. Score:
735 : : // - bind to exactly this node is better than whole nodeset
736 : : // - simple binding expressions is better than complex ones
737 : 0 : sal_Int32 nScore = 0;
738 [ # # ]: 0 : if( nNodes == 1 )
739 : 0 : nScore ++;
740 [ # # ][ # # ]: 0 : if( pBinding->isSimpleBindingExpression() )
741 : 0 : nScore ++;
742 : :
743 : : // if we found a better binding, remember it
744 [ # # ]: 0 : if( nScore > nBestScore )
745 : : {
746 : 0 : pBestBinding = pBinding;
747 : 0 : nBestScore = nScore;
748 : : }
749 : : }
750 : 0 : }
751 : :
752 : : // create binding, if none was found and bCreate is set
753 : : OSL_ENSURE( ( nBestScore == 0 ) == ( pBestBinding == NULL ),
754 : : "score != binding?" );
755 [ # # ][ # # ]: 0 : if( bCreate && pBestBinding == NULL )
756 : : {
757 [ # # ]: 0 : pBestBinding = new Binding();
758 : : pBestBinding->setBindingExpression(
759 [ # # ]: 0 : getDefaultBindingExpressionForNode( xNode ) );
760 [ # # ][ # # ]: 0 : mpBindings->addItem( pBestBinding );
761 : : }
762 : :
763 [ # # ]: 0 : return pBestBinding;
764 : : }
765 : :
766 : 0 : void Model::removeBindingForNode( const XNode_t& )
767 : : throw( RuntimeException )
768 : : {
769 : : // determine whether suitable binding is still used
770 : 0 : }
771 : :
772 : 0 : OUString lcl_serializeForDisplay( const Reference< XAttr >& _rxAttrNode )
773 : : {
774 : 0 : ::rtl::OUString sResult;
775 : : OSL_ENSURE( _rxAttrNode.is(), "lcl_serializeForDisplay( attr ): invalid argument!" );
776 [ # # ]: 0 : if ( _rxAttrNode.is() )
777 : : {
778 : 0 : ::rtl::OUStringBuffer aBuffer;
779 [ # # ][ # # ]: 0 : aBuffer.append( _rxAttrNode->getName() );
[ # # ]
780 [ # # ]: 0 : aBuffer.appendAscii( "=" );
781 [ # # ][ # # ]: 0 : ::rtl::OUString sValue = _rxAttrNode->getValue();
782 : 0 : sal_Unicode nQuote = '"';
783 [ # # ]: 0 : if ( sValue.indexOf( nQuote ) >= 0 )
784 : 0 : nQuote = '\'';
785 [ # # ]: 0 : aBuffer.append( nQuote );
786 [ # # ]: 0 : aBuffer.append( sValue );
787 [ # # ]: 0 : aBuffer.append( nQuote );
788 [ # # ]: 0 : aBuffer.append( (sal_Unicode)' ' );
789 [ # # ]: 0 : sResult = aBuffer.makeStringAndClear();
790 : : }
791 : 0 : return sResult;
792 : : }
793 : :
794 : 0 : OUString lcl_serializeForDisplay( const Reference<XNodeList>& xNodes )
795 : : {
796 : 0 : ::rtl::OUString sResult;
797 : :
798 : : // create document fragment
799 [ # # ][ # # ]: 0 : Reference<XDocument> xDocument( getDocumentBuilder()->newDocument() );
[ # # ]
800 : : Reference<XDocumentFragment> xFragment(
801 [ # # ][ # # ]: 0 : xDocument->createDocumentFragment() );
802 [ # # ]: 0 : Reference<XNode> xNode( xFragment, UNO_QUERY );
803 : : OSL_ENSURE( xFragment.is(), "xFragment" );
804 : : OSL_ENSURE( xNode.is(), "xNode" );
805 : :
806 : 0 : sal_Int32 nAttributeNodes = 0;
807 : :
808 : : // attach nodelist to fragment
809 [ # # ][ # # ]: 0 : sal_Int32 nLength = xNodes->getLength();
810 [ # # ]: 0 : for( sal_Int32 i = 0; i < nLength; i++ )
811 : : {
812 [ # # ][ # # ]: 0 : Reference<XNode> xCurrent = xNodes->item( i );
813 : :
814 [ # # ][ # # ]: 0 : switch ( xCurrent->getNodeType() )
[ # # # ]
815 : : {
816 : : case NodeType_DOCUMENT_NODE:
817 : : // special-case documents: use top-level element instead
818 [ # # ][ # # ]: 0 : xCurrent = xCurrent->getFirstChild();
[ # # ]
819 : 0 : break;
820 : : case NodeType_ATTRIBUTE_NODE:
821 : : {
822 [ # # ]: 0 : Reference< XAttr > xAttr( xCurrent, UNO_QUERY );
823 [ # # ]: 0 : if ( xAttr.is() )
824 : : {
825 [ # # ]: 0 : sResult += lcl_serializeForDisplay( xAttr );
826 : 0 : ++nAttributeNodes;
827 : 0 : }
828 : : }
829 : 0 : continue;
830 : :
831 : : default:
832 : 0 : break;
833 : : }
834 : :
835 : : // append node
836 [ # # ][ # # ]: 0 : xNode->appendChild( xDocument->importNode( xCurrent, sal_True ) );
[ # # ][ # # ]
[ # # ]
837 : 0 : }
838 : : OSL_ENSURE( ( nAttributeNodes == 0 ) || ( nAttributeNodes == nLength ),
839 : : "lcl_serializeForDisplay: mixed attribute and non-attribute nodes?" );
840 [ # # ]: 0 : if ( nAttributeNodes )
841 : : // had only attribute nodes
842 : : return sResult;
843 : :
844 : : // serialize fragment
845 [ # # ]: 0 : CSerializationAppXML aSerialization;
846 [ # # ]: 0 : aSerialization.setSource( xFragment );
847 [ # # ]: 0 : aSerialization.serialize();
848 : :
849 : : // copy stream into buffer
850 : : Reference<XTextInputStream> xTextInputStream(
851 : : createInstance( OUSTRING("com.sun.star.io.TextInputStream") ),
852 [ # # ][ # # ]: 0 : UNO_QUERY );
[ # # ]
853 : : Reference<XActiveDataSink>( xTextInputStream, UNO_QUERY_THROW )
854 [ # # ][ # # ]: 0 : ->setInputStream( aSerialization.getInputStream() );
[ # # ][ # # ]
855 : :
856 : : /* WORK AROUND for problem in serialization: currently, multiple
857 : : XML delarations (<?xml...?>) are being written out and we don't
858 : : want them. When this is fixed, the code below is nice and
859 : : simple. The current code filters out the declarations.
860 : : OUString sResult = xTextInputStream->readString( Sequence<sal_Unicode>(),
861 : : sal_True );
862 : : */
863 : :
864 : : // well, the serialization prepends XML header(s) that we need to
865 : : // remove first.
866 : 0 : OUStringBuffer aBuffer;
867 [ # # ][ # # ]: 0 : while( ! xTextInputStream->isEOF() )
[ # # ]
868 : : {
869 [ # # ][ # # ]: 0 : OUString sLine = xTextInputStream->readLine();
870 [ # # # # ]: 0 : if( !sLine.isEmpty()
[ # # ]
871 : 0 : && sLine.compareToAscii( "<?xml", 5 ) != 0 )
872 : : {
873 [ # # ]: 0 : aBuffer.append( sLine );
874 [ # # ]: 0 : aBuffer.append( sal_Unicode('\n') );
875 : : }
876 : 0 : }
877 [ # # ]: 0 : sResult = aBuffer.makeStringAndClear();
878 : :
879 [ # # ]: 0 : return sResult;
880 : : }
881 : :
882 : 0 : OUString lcl_serializeForDisplay( const Reference<XXPathObject>& xResult )
883 : : {
884 : : // error handling first
885 [ # # ]: 0 : if( ! xResult.is() )
886 [ # # ]: 0 : return getResource( RID_STR_XFORMS_CANT_EVALUATE );
887 : :
888 : :
889 : : // TODO: localize
890 : 0 : OUStringBuffer aBuffer;
891 : :
892 [ # # ][ # # : 0 : switch( xResult->getObjectType() )
# # # ]
[ # # ]
893 : : {
894 : : case XPathObjectType_XPATH_BOOLEAN:
895 [ # # ][ # # ]: 0 : aBuffer.append( xResult->getBoolean()
896 : : ? OUSTRING("true")
897 [ # # ][ # # ]: 0 : : OUSTRING("false") );
[ # # ][ # # ]
898 : 0 : break;
899 : :
900 : : case XPathObjectType_XPATH_STRING:
901 [ # # ]: 0 : aBuffer.append( sal_Unicode('"') );
902 [ # # ][ # # ]: 0 : aBuffer.append( xResult->getString() );
[ # # ]
903 [ # # ]: 0 : aBuffer.append( sal_Unicode('"') );
904 : 0 : break;
905 : :
906 : : case XPathObjectType_XPATH_NODESET:
907 [ # # ][ # # ]: 0 : aBuffer.append( lcl_serializeForDisplay( xResult->getNodeList() ) );
[ # # ][ # # ]
908 : 0 : break;
909 : :
910 : : case XPathObjectType_XPATH_NUMBER:
911 [ # # ][ # # ]: 0 : aBuffer.append( xResult->getDouble() );
[ # # ]
912 : 0 : break;
913 : :
914 : : case XPathObjectType_XPATH_UNDEFINED:
915 : : case XPathObjectType_XPATH_POINT:
916 : : case XPathObjectType_XPATH_RANGE:
917 : : case XPathObjectType_XPATH_LOCATIONSET:
918 : : case XPathObjectType_XPATH_USERS:
919 : : case XPathObjectType_XPATH_XSLT_TREE:
920 : : default:
921 : : // TODO: localized error message?
922 : 0 : break;
923 : : }
924 : :
925 [ # # ]: 0 : return aBuffer.makeStringAndClear();
926 : : }
927 : :
928 : 0 : OUString Model::getResultForExpression(
929 : : const XPropertySet_t& xBinding,
930 : : sal_Bool bIsBindingExpression,
931 : : const OUString& sExpression )
932 : : throw( RuntimeException )
933 : : {
934 [ # # ]: 0 : Binding* pBinding = Binding::getBinding( xBinding );
935 [ # # ]: 0 : if( pBinding == NULL )
936 [ # # ]: 0 : throw RuntimeException();
937 : :
938 : : // prepare & evaluate expression
939 : 0 : OUStringBuffer aBuffer;
940 [ # # ]: 0 : ComputedExpression aExpression;
941 [ # # ]: 0 : aExpression.setExpression( sExpression );
942 [ # # ]: 0 : if( bIsBindingExpression )
943 : : {
944 : : // binding: use binding context and evaluation
945 [ # # ][ # # ]: 0 : aExpression.evaluate( pBinding->getEvaluationContext() );
[ # # ]
946 [ # # ][ # # ]: 0 : aBuffer.append( lcl_serializeForDisplay( aExpression.getXPath() ) );
[ # # ]
947 : : }
948 : : else
949 : : {
950 : : // MIP (not binding): iterate over bindings contexts
951 : : std::vector<EvaluationContext> aContext =
952 [ # # ]: 0 : pBinding->getMIPEvaluationContexts();
953 [ # # ][ # # ]: 0 : for( std::vector<EvaluationContext>::iterator aIter = aContext.begin();
954 : 0 : aIter != aContext.end();
955 : : ++aIter )
956 : : {
957 [ # # ]: 0 : aExpression.evaluate( *aIter );
958 [ # # ][ # # ]: 0 : aBuffer.append( lcl_serializeForDisplay(aExpression.getXPath()) );
[ # # ]
959 [ # # ]: 0 : aBuffer.append( sal_Unicode('\n') );
960 : 0 : }
961 : : }
962 [ # # ][ # # ]: 0 : return aBuffer.makeStringAndClear();
963 : : }
964 : :
965 : 0 : sal_Bool Model::isValidXMLName( const OUString& sName )
966 : : throw( RuntimeException )
967 : : {
968 [ # # ]: 0 : return isValidQName( sName, NULL );
969 : : }
970 : :
971 : 0 : sal_Bool Model::isValidPrefixName( const OUString& sName )
972 : : throw( RuntimeException )
973 : : {
974 [ # # ]: 0 : return ::isValidPrefixName( sName, NULL );
975 : : }
976 : :
977 : 0 : void Model::setNodeValue(
978 : : const XNode_t& xNode,
979 : : const rtl::OUString& sValue )
980 : : throw( RuntimeException )
981 : : {
982 : 0 : setSimpleContent( xNode, sValue );
983 : 0 : }
984 : :
985 : :
986 : : //
987 : : // helper functions from model_helper.hxx
988 : : //
989 : :
990 : 0 : void xforms::getInstanceData(
991 : : const Sequence<PropertyValue>& aValues,
992 : : OUString* pID,
993 : : Reference<XDocument>* pInstance,
994 : : OUString* pURL,
995 : : bool* pURLOnce )
996 : : {
997 : 0 : sal_Int32 nValues = aValues.getLength();
998 : 0 : const PropertyValue* pValues = aValues.getConstArray();
999 [ # # ]: 0 : for( sal_Int32 n = 0; n < nValues; n++ )
1000 : : {
1001 : 0 : const PropertyValue& rValue = pValues[n];
1002 : : #define PROP(NAME) \
1003 : : if( p##NAME != NULL && \
1004 : : rValue.Name == #NAME ) \
1005 : : rValue.Value >>= (*p##NAME)
1006 [ # # ][ # # ]: 0 : PROP(ID);
[ # # ]
1007 [ # # ][ # # ]: 0 : PROP(Instance);
[ # # ]
1008 [ # # ][ # # ]: 0 : PROP(URL);
[ # # ]
1009 [ # # ][ # # ]: 0 : PROP(URLOnce);
[ # # ]
1010 : : #undef PROP
1011 : : }
1012 : 0 : }
1013 : :
1014 : 0 : void xforms::setInstanceData(
1015 : : Sequence<PropertyValue>& aSequence,
1016 : : const OUString* _pID,
1017 : : const Reference<XDocument>* _pInstance,
1018 : : const OUString* _pURL,
1019 : : const bool* _pURLOnce )
1020 : : {
1021 : : // get old instance data
1022 : 0 : OUString sID;
1023 : 0 : Reference<XDocument> xInstance;
1024 : 0 : OUString sURL;
1025 : 0 : bool bURLOnce = false;
1026 [ # # ]: 0 : getInstanceData( aSequence, &sID, &xInstance, &sURL, &bURLOnce );
1027 [ # # ]: 0 : const OUString* pID = !sID.isEmpty() ? &sID : NULL;
1028 [ # # ]: 0 : const Reference<XDocument>* pInstance = xInstance.is() ? &xInstance : NULL;
1029 [ # # ]: 0 : const OUString* pURL = !sURL.isEmpty() ? &sURL : NULL;
1030 [ # # ][ # # ]: 0 : const bool* pURLOnce = ( bURLOnce && pURL != NULL ) ? &bURLOnce : NULL;
1031 : :
1032 : : // determine new instance data
1033 : : #define PROP(NAME) if( _p##NAME != NULL ) p##NAME = _p##NAME
1034 [ # # ]: 0 : PROP(ID);
1035 [ # # ]: 0 : PROP(Instance);
1036 [ # # ]: 0 : PROP(URL);
1037 [ # # ]: 0 : PROP(URLOnce);
1038 : : #undef PROP
1039 : :
1040 : : // count # of values we want to set
1041 : 0 : sal_Int32 nCount = 0;
1042 : : #define PROP(NAME) if( p##NAME != NULL ) nCount++
1043 [ # # ]: 0 : PROP(ID);
1044 [ # # ]: 0 : PROP(Instance);
1045 [ # # ]: 0 : PROP(URL);
1046 [ # # ]: 0 : PROP(URLOnce);
1047 : : #undef PROP
1048 : :
1049 : : // realloc sequence and enter values;
1050 [ # # ]: 0 : aSequence.realloc( nCount );
1051 [ # # ]: 0 : PropertyValue* pSequence = aSequence.getArray();
1052 : 0 : sal_Int32 nIndex = 0;
1053 : : #define PROP(NAME) \
1054 : : if( p##NAME != NULL ) \
1055 : : { \
1056 : : pSequence[ nIndex ].Name = OUSTRING(#NAME); \
1057 : : pSequence[ nIndex ].Value <<= *p##NAME; \
1058 : : nIndex++; \
1059 : : }
1060 [ # # ][ # # ]: 0 : PROP(ID);
[ # # ]
1061 [ # # ][ # # ]: 0 : PROP(Instance);
[ # # ]
1062 [ # # ][ # # ]: 0 : PROP(URL);
[ # # ]
1063 [ # # ][ # # ]: 0 : PROP(URLOnce);
[ # # ]
1064 : : #undef PROP
1065 : 0 : }
1066 : :
1067 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|