xref: /AOO41X/main/udm/source/xml/xmlitem.cxx (revision 1ecadb572e7010ff3b3382ad9bf179dbc6efadbb)
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 #include <precomp.h>
29 #include <udm/xml/xmlitem.hxx>
30 
31 // NOT FULLY DECLARED SERVICES
32 #include <cosv/file.hxx>
33 
34 
35 namespace csi
36 {
37 namespace xml
38 {
39 
40 char cReplacable[256] =
41 	{
42 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,	// 0 - 49
43 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
44 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
45 	  0,  0,  0,  0,  1,  	0,  0,  0,  1,  0,    	// ", &
46 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
47 
48 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,	// 50 - 99
49 	  1,  0,  1,  0,  0,  	0,  0,  0,  0,  0,	  	// <, >
50 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
51 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
52 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
53 
54 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,  // 100 - 149
55 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
56 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
57 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
58 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
59 
60 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
61 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
62 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
63 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
64 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
65 
66 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
67 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
68 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
69 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
70 	  0,  0,  0,  0,  0,  	0,  0,  0,  0,  0,
71 
72 	  0,  0,  0,  0,  0,  	1					// &nbsp;
73 	};
74 
75 
76 class MultiItem : public Item
77 {
78   public:
79 						MultiItem();
80 						~MultiItem();
81 
82 	void				Add(
83 							DYN Item *			let_dpDatum )
84 													{ csv_assert( let_dpDatum != 0 );
85 													  aItems.push_back(let_dpDatum); }
86 	void				Erase()						{ aItems.erase_all(); }
87 
88   private:
89 	virtual void		do_WriteOut(
90 							csv::bostream &			io_aFile ) const;
91 	// DATA
92 	ItemList			aItems;
93 };
94 
95 
96 void					StreamOut(
97 							Dyn< Item >  &			o_rContent,
98 							DYN Item *				let_dpItem );
99 inline void
100 StreamOut( AttrList &				o_rAttrs,
101 		   DYN Attribute *			let_dpAttr )
102 {
103 	csv_assert( let_dpAttr != 0 );
104 	o_rAttrs.push_back( let_dpAttr );
105 }
106 
107 
108 inline void
109 Impl_SetContent( Dyn< Item >  &			o_rContent,
110 				 DYN Item *				let_dpItem )
111 {
112 	o_rContent = let_dpItem;
113 }
114 
115 
116 //*********************		Attribute		****************************//
117 
118 const String   attrValueBegin("=\"");
119 const String   attrValueEnd("\"");
120 
121 void
122 Attribute::WriteOut( csv::bostream & io_aFile ) const
123 {
124 	io_aFile.write( Name() );
125     if ( Value().length() > 0 )
126     {
127 	    io_aFile.write( attrValueBegin );
128 	    io_aFile.write( Value() );
129 	    io_aFile.write( attrValueEnd );
130     }
131 }
132 
133 
134 
135 //************************		Element		****************************//
136 
137 const String    newline("\n");
138 const String    space(" ");
139 const String    beginTagBegin("<");
140 const String    endTagBegin("</");
141 const String    tagEnd(">");
142 const String    emptyTagEnd("/>");
143 
144 void
145 Element::do_WriteOut( csv::bostream & io_aFile ) const
146 {
147 	io_aFile.write( beginTagBegin );
148 	io_aFile.write( inq_TagName() );
149 
150 	const AttrList * pAttrs = inq_Attrs();
151 	if ( pAttrs != 0 )
152 	{
153 		for ( AttrList::iterator it = pAttrs->begin();
154 			  it != pAttrs->end();
155 			  ++it )
156 		{
157 
158 			io_aFile.write( space );
159 			(*it)->WriteOut( io_aFile );
160 		}
161 	}
162 
163 	const Item * pContent = inq_Content();
164 	if ( pContent != 0 )
165 		io_aFile.write( tagEnd );
166 	else
167     {
168      	if (FinishEmptyTag_XmlStyle())
169     		io_aFile.write( emptyTagEnd );
170         else
171         {
172     		io_aFile.write( tagEnd );
173     		io_aFile.write( endTagBegin );
174         	io_aFile.write( inq_TagName() );
175     		io_aFile.write( tagEnd );
176         }
177     }
178 	if ( LineBreakAfterBeginTag() )
179 		io_aFile.write( newline );
180 	if ( pContent == 0 )
181 		return;
182 
183 	pContent->WriteOut( io_aFile );
184 	io_aFile.write( endTagBegin );
185 	io_aFile.write( inq_TagName() );
186 	io_aFile.write( tagEnd );
187 	if ( LineBreakAfterEndTag() )
188 		io_aFile.write( newline );
189 }
190 
191 bool
192 Element::FinishEmptyTag_XmlStyle() const
193 {
194  	return true;
195 }
196 
197 bool
198 Element::LineBreakAfterBeginTag() const
199 {
200 	return false;
201 }
202 
203 bool
204 Element::LineBreakAfterEndTag() const
205 {
206 	return LineBreakAfterBeginTag();
207 }
208 
209 
210 //************************		EmptyElement		****************************//
211 
212 void
213 EmptyElement::op_streamout( DYN Item *	)
214 {
215 	// Does nothing.
216 }
217 
218 void
219 EmptyElement::op_streamout( DYN Attribute * let_dpAttr )
220 {
221 	StreamOut( inq_RefAttrs(), let_dpAttr );
222 }
223 
224 void
225 EmptyElement::do_SetContent( DYN Item *	)
226 {
227 	// Does nothing.
228 }
229 
230 const Item *
231 EmptyElement::inq_Content() const
232 {
233 	return 0;
234 }
235 
236 const AttrList *
237 EmptyElement::inq_Attrs() const
238 {
239     return & const_cast< EmptyElement* >(this)->inq_RefAttrs();
240 }
241 
242 
243 //************************		PureElement		****************************//
244 
245 void
246 PureElement::op_streamout( DYN Item * let_dpItem )
247 {
248 	StreamOut( inq_RefContent(), let_dpItem );
249 }
250 
251 void
252 PureElement::op_streamout( DYN Attribute * )
253 {
254 	// Does nothing.
255 }
256 
257 void
258 PureElement::do_SetContent( DYN Item *	let_dpItem )
259 {
260 	Impl_SetContent( inq_RefContent(), let_dpItem );
261 }
262 
263 const Item *
264 PureElement::inq_Content() const
265 {
266     return const_cast< PureElement* >(this)->inq_RefContent().Ptr();
267 }
268 
269 const AttrList *
270 PureElement::inq_Attrs() const
271 {
272 	return 0;
273 }
274 
275 
276 //***************************		SglTag		**************************//
277 
278 void
279 SglTag::op_streamout( DYN Item * )
280 {
281 	// Does nothing.
282 }
283 
284 void
285 SglTag::op_streamout( DYN Attribute * )
286 {
287 	// Does nothing.
288 }
289 
290 void
291 SglTag::do_SetContent( DYN Item *)
292 {
293 	// Does nothing.
294 }
295 
296 const Item *
297 SglTag::inq_Content() const
298 {
299 	return 0;
300 }
301 
302 const AttrList *
303 SglTag::inq_Attrs() const
304 {
305 	return 0;
306 }
307 
308 
309 //***************************		AnElement		**************************//
310 
311 AnElement::AnElement( const String &   i_sTagName )
312 	:	sTagName( i_sTagName )
313 		// pContent,
314 		// aAttrs
315 {
316 }
317 
318 AnElement::AnElement( const char * i_sTagName )
319 	:	sTagName( i_sTagName )
320 		// pContent,
321 		// aAttrs
322 {
323 }
324 
325 AnElement::~AnElement()
326 {
327 }
328 
329 void
330 AnElement::op_streamout( DYN Item *	let_dpItem )
331 {
332 	StreamOut( pContent, let_dpItem );
333 }
334 
335 void
336 AnElement::op_streamout( DYN Attribute * let_dpAttr )
337 {
338 	StreamOut( aAttrs, let_dpAttr );
339 }
340 
341 void
342 AnElement::do_SetContent( DYN Item * let_dpItem )
343 {
344 	Impl_SetContent( pContent, let_dpItem );
345 }
346 
347 const String &
348 AnElement::inq_TagName() const
349 {
350 	return sTagName;
351 }
352 
353 const Item *
354 AnElement::inq_Content() const
355 {
356 	return pContent.Ptr();
357 }
358 
359 const AttrList *
360 AnElement::inq_Attrs() const
361 {
362 	return &aAttrs;
363 }
364 
365 
366 //***************************     AnEmptyElement	**************************//
367 
368 AnEmptyElement::AnEmptyElement( const String &   i_sTagName )
369 	:	sTagName( i_sTagName )
370 		// aAttrs
371 {
372 }
373 
374 AnEmptyElement::AnEmptyElement( const char * i_sTagName )
375 	:	sTagName( i_sTagName )
376 		// aAttrs
377 {
378 }
379 
380 AnEmptyElement::~AnEmptyElement()
381 {
382 
383 }
384 
385 const String &
386 AnEmptyElement::inq_TagName() const
387 {
388 	return sTagName;
389 }
390 
391 AttrList &
392 AnEmptyElement::inq_RefAttrs()
393 {
394 	return aAttrs;
395 }
396 
397 
398 //***************************     APureElement	 	**************************//
399 
400 APureElement::APureElement( const String &   i_sTagName )
401 	:	sTagName( i_sTagName )
402 		// pContent
403 {
404 }
405 
406 APureElement::APureElement( const char * i_sTagName )
407 	:	sTagName( i_sTagName )
408 		// pContent
409 {
410 }
411 
412 APureElement::~APureElement()
413 {
414 }
415 
416 const String &
417 APureElement::inq_TagName() const
418 {
419 	return sTagName;
420 }
421 
422 Dyn< Item > &
423 APureElement::inq_RefContent()
424 {
425 	return pContent;
426 }
427 
428 
429 
430 //***************************     ASglTag	 		**************************//
431 
432 ASglTag::ASglTag( const String &   i_sTagName )
433 	:	sTagName( i_sTagName )
434 {
435 }
436 
437 ASglTag::ASglTag( const char *  i_sTagName )
438 	:	sTagName( i_sTagName )
439 {
440 }
441 
442 ASglTag::~ASglTag()
443 {
444 }
445 
446 const String &
447 ASglTag::inq_TagName() const
448 {
449 	return sTagName;
450 }
451 
452 
453 //***************************		AnAttribute		**************************//
454 AnAttribute::AnAttribute( const String &   i_sName,
455 						  const String &   i_sValue )
456 	:	sName(i_sName),
457 	    sValue(i_sValue)
458 {
459 }
460 
461 AnAttribute::AnAttribute( const char * i_sName,
462 						  const char * i_sValue )
463 	:	sName(i_sName),
464 	    sValue(i_sValue)
465 {
466 }
467 
468 AnAttribute::~AnAttribute()
469 {
470 }
471 
472 const String &
473 AnAttribute::inq_Name() const
474 {
475 	return sName;
476 }
477 
478 const String &
479 AnAttribute::inq_Value() const
480 {
481 	return sValue;
482 }
483 
484 
485 
486 //***************************		Text		**************************//
487 
488 Text::Text( const String &   i_sText )
489 	:	sText(i_sText)
490 {
491 }
492 
493 Text::Text( const char * i_sText )
494 	:	sText(i_sText)
495 {
496 }
497 
498 Text::~Text()
499 {
500 }
501 
502 void
503 Text::do_WriteOut( csv::bostream & io_aFile ) const
504 {
505 	const unsigned char *
506 	    pStart = reinterpret_cast< const unsigned char* >(sText.c_str());
507 	const unsigned char *
508 	    pOut = pStart;
509 
510 	for ( ; *pOut != '\0'; ++pOut )
511 	{
512 		if ( cReplacable[*pOut] )
513 		{
514 			if ( pOut != pStart )
515 			{
516 				io_aFile.write( pStart, pOut-pStart );
517 			}
518 
519 			switch (*pOut)
520 			{
521 				case '<': 	io_aFile.write("&lt;");		break;
522 				case '>':   io_aFile.write("&gt;");		break;
523 				case '"':   io_aFile.write("&quot;");	break;
524 				case '&':   io_aFile.write("&amp;");	break;
525 				case 255:   io_aFile.write("&nbsp;");	break;
526 			}
527 
528 			pStart = pOut+1;
529 		}	// endif (cReplacable[*pOut])
530 	}	// end for
531 
532 	if ( pOut != pStart )
533 	{
534 		io_aFile.write( pStart, pOut-pStart );
535 	}
536 }
537 
538 
539 //***************************		XmlCode		**************************//
540 
541 XmlCode::XmlCode( const String &   i_sText )
542 	:	sText(i_sText)
543 {
544 }
545 
546 XmlCode::XmlCode( const char *     i_sText )
547 	:	sText(i_sText)
548 {
549 }
550 
551 XmlCode::~XmlCode()
552 {
553 }
554 
555 void
556 XmlCode::do_WriteOut( csv::bostream & io_aFile ) const
557 {
558 	io_aFile.write(sText);
559 }
560 
561 
562 //***************************		MultiItem		**************************//
563 
564 MultiItem::MultiItem()
565 {
566 }
567 
568 MultiItem::~MultiItem()
569 {
570 }
571 
572 void
573 MultiItem::do_WriteOut( csv::bostream &	io_aFile ) const
574 {
575 	ItemList::iterator itEnd = aItems.end();
576 
577 	for ( ItemList::iterator it = aItems.begin();
578 		  it != itEnd;
579 		  ++it )
580 	{
581 		(*it)->WriteOut( io_aFile );
582 	}
583 
584 }
585 
586 
587 
588 //***************************		Helpers		**************************//
589 
590 void
591 StreamOut( Dyn< Item >  &			o_rContent,
592 		   DYN Item *				let_dpItem )
593 {
594 	MultiItem * pContent = 0;
595 	if ( bool(o_rContent) )
596 	{
597 		pContent = static_cast< MultiItem* >( o_rContent.MutablePtr() );
598 		csv_assert( dynamic_cast< MultiItem* >( o_rContent.MutablePtr() ) != 0 );
599 	}
600 	else
601 	{
602 		pContent = new MultiItem;
603 		o_rContent = pContent;
604 	}
605 
606 	csv_assert( let_dpItem != 0 );
607 	pContent->Add( let_dpItem );
608 }
609 
610 
611 
612 
613 }   // namespace xml
614 }   // namespace csi
615