Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include <precomp.h>
21 : #include <udm/xml/xmlitem.hxx>
22 :
23 : // NOT FULLY DECLARED SERVICES
24 : #include <cosv/file.hxx>
25 :
26 :
27 : namespace csi
28 : {
29 : namespace xml
30 : {
31 :
32 : char cReplacable[256] =
33 : {
34 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0 - 49
35 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
36 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
37 : 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, // ", &
38 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
39 :
40 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 50 - 99
41 : 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, // <, >
42 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
43 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
44 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
45 :
46 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 100 - 149
47 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
48 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
49 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
50 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
51 :
52 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
53 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
54 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
55 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
56 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
57 :
58 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
59 : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
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 :
64 : 0, 0, 0, 0, 0, 1 //
65 : };
66 :
67 :
68 : class MultiItem : public Item
69 : {
70 : public:
71 : MultiItem();
72 : ~MultiItem();
73 :
74 3211884 : void Add(
75 : DYN Item * let_dpDatum )
76 : { csv_assert( let_dpDatum != 0 );
77 3211884 : aItems.push_back(let_dpDatum); }
78 : void Erase() { aItems.erase_all(); }
79 :
80 : private:
81 : virtual void do_WriteOut(
82 : csv::bostream & io_aFile ) const;
83 : // DATA
84 : ItemList aItems;
85 : };
86 :
87 :
88 : void StreamOut(
89 : Dyn< Item > & o_rContent,
90 : DYN Item * let_dpItem );
91 : inline void
92 824649 : StreamOut( AttrList & o_rAttrs,
93 : DYN Attribute * let_dpAttr )
94 : {
95 : csv_assert( let_dpAttr != 0 );
96 824649 : o_rAttrs.push_back( let_dpAttr );
97 824649 : }
98 :
99 :
100 : inline void
101 7831 : Impl_SetContent( Dyn< Item > & o_rContent,
102 : DYN Item * let_dpItem )
103 : {
104 7831 : o_rContent = let_dpItem;
105 7831 : }
106 :
107 :
108 : //********************* Attribute ****************************//
109 :
110 1 : const String attrValueBegin("=\"");
111 1 : const String attrValueEnd("\"");
112 :
113 : void
114 824649 : Attribute::WriteOut( csv::bostream & io_aFile ) const
115 : {
116 824649 : io_aFile.write( Name() );
117 824649 : if ( Value().length() > 0 )
118 : {
119 824084 : io_aFile.write( attrValueBegin );
120 824084 : io_aFile.write( Value() );
121 824084 : io_aFile.write( attrValueEnd );
122 : }
123 824649 : }
124 :
125 :
126 :
127 : //************************ Element ****************************//
128 :
129 1 : const String newline("\n");
130 1 : const String space(" ");
131 1 : const String beginTagBegin("<");
132 1 : const String endTagBegin("</");
133 1 : const String tagEnd(">");
134 1 : const String emptyTagEnd("/>");
135 :
136 : void
137 869553 : Element::do_WriteOut( csv::bostream & io_aFile ) const
138 : {
139 869553 : io_aFile.write( beginTagBegin );
140 869553 : io_aFile.write( inq_TagName() );
141 :
142 869553 : const AttrList * pAttrs = inq_Attrs();
143 869553 : if ( pAttrs != 0 )
144 : {
145 4867839 : for ( AttrList::iterator it = pAttrs->begin();
146 3245226 : it != pAttrs->end();
147 : ++it )
148 : {
149 :
150 824649 : io_aFile.write( space );
151 824649 : (*it)->WriteOut( io_aFile );
152 : }
153 : }
154 :
155 869553 : const Item * pContent = inq_Content();
156 869553 : if ( pContent != 0 )
157 818948 : io_aFile.write( tagEnd );
158 : else
159 : {
160 50605 : if (FinishEmptyTag_XmlStyle())
161 47374 : io_aFile.write( emptyTagEnd );
162 : else
163 : {
164 3231 : io_aFile.write( tagEnd );
165 3231 : io_aFile.write( endTagBegin );
166 3231 : io_aFile.write( inq_TagName() );
167 3231 : io_aFile.write( tagEnd );
168 : }
169 : }
170 869553 : if ( LineBreakAfterBeginTag() )
171 216723 : io_aFile.write( newline );
172 869553 : if ( pContent == 0 )
173 920158 : return;
174 :
175 818948 : pContent->WriteOut( io_aFile );
176 818948 : io_aFile.write( endTagBegin );
177 818948 : io_aFile.write( inq_TagName() );
178 818948 : io_aFile.write( tagEnd );
179 818948 : if ( LineBreakAfterEndTag() )
180 505566 : io_aFile.write( newline );
181 : }
182 :
183 : bool
184 47374 : Element::FinishEmptyTag_XmlStyle() const
185 : {
186 47374 : return true;
187 : }
188 :
189 : bool
190 966212 : Element::LineBreakAfterBeginTag() const
191 : {
192 966212 : return false;
193 : }
194 :
195 : bool
196 524111 : Element::LineBreakAfterEndTag() const
197 : {
198 524111 : return LineBreakAfterBeginTag();
199 : }
200 :
201 :
202 : //************************ EmptyElement ****************************//
203 :
204 : void
205 0 : EmptyElement::op_streamout( DYN Item * )
206 : {
207 : // Does nothing.
208 0 : }
209 :
210 : void
211 0 : EmptyElement::op_streamout( DYN Attribute * let_dpAttr )
212 : {
213 0 : StreamOut( inq_RefAttrs(), let_dpAttr );
214 0 : }
215 :
216 : void
217 0 : EmptyElement::do_SetContent( DYN Item * )
218 : {
219 : // Does nothing.
220 0 : }
221 :
222 : const Item *
223 0 : EmptyElement::inq_Content() const
224 : {
225 0 : return 0;
226 : }
227 :
228 : const AttrList *
229 0 : EmptyElement::inq_Attrs() const
230 : {
231 0 : return & const_cast< EmptyElement* >(this)->inq_RefAttrs();
232 : }
233 :
234 :
235 : //************************ PureElement ****************************//
236 :
237 : void
238 83376 : PureElement::op_streamout( DYN Item * let_dpItem )
239 : {
240 83376 : StreamOut( inq_RefContent(), let_dpItem );
241 83376 : }
242 :
243 : void
244 0 : PureElement::op_streamout( DYN Attribute * )
245 : {
246 : // Does nothing.
247 0 : }
248 :
249 : void
250 0 : PureElement::do_SetContent( DYN Item * let_dpItem )
251 : {
252 0 : Impl_SetContent( inq_RefContent(), let_dpItem );
253 0 : }
254 :
255 : const Item *
256 71589 : PureElement::inq_Content() const
257 : {
258 71589 : return const_cast< PureElement* >(this)->inq_RefContent().Ptr();
259 : }
260 :
261 : const AttrList *
262 71589 : PureElement::inq_Attrs() const
263 : {
264 71589 : return 0;
265 : }
266 :
267 :
268 : //*************************** SglTag **************************//
269 :
270 : void
271 0 : SglTag::op_streamout( DYN Item * )
272 : {
273 : // Does nothing.
274 0 : }
275 :
276 : void
277 0 : SglTag::op_streamout( DYN Attribute * )
278 : {
279 : // Does nothing.
280 0 : }
281 :
282 : void
283 0 : SglTag::do_SetContent( DYN Item *)
284 : {
285 : // Does nothing.
286 0 : }
287 :
288 : const Item *
289 0 : SglTag::inq_Content() const
290 : {
291 0 : return 0;
292 : }
293 :
294 : const AttrList *
295 0 : SglTag::inq_Attrs() const
296 : {
297 0 : return 0;
298 : }
299 :
300 :
301 : //*************************** AnElement **************************//
302 :
303 790134 : AnElement::AnElement( const char * i_sTagName )
304 790134 : : sTagName( i_sTagName )
305 : // pContent,
306 : // aAttrs
307 : {
308 790134 : }
309 :
310 791399 : AnElement::~AnElement()
311 : {
312 791399 : }
313 :
314 : void
315 3128508 : AnElement::op_streamout( DYN Item * let_dpItem )
316 : {
317 3128508 : StreamOut( pContent, let_dpItem );
318 3128508 : }
319 :
320 : void
321 824649 : AnElement::op_streamout( DYN Attribute * let_dpAttr )
322 : {
323 824649 : StreamOut( aAttrs, let_dpAttr );
324 824649 : }
325 :
326 : void
327 7831 : AnElement::do_SetContent( DYN Item * let_dpItem )
328 : {
329 7831 : Impl_SetContent( pContent, let_dpItem );
330 7831 : }
331 :
332 : const String &
333 1548555 : AnElement::inq_TagName() const
334 : {
335 1548555 : return sTagName;
336 : }
337 :
338 : const Item *
339 797964 : AnElement::inq_Content() const
340 : {
341 797964 : return pContent.Ptr();
342 : }
343 :
344 : const AttrList *
345 797964 : AnElement::inq_Attrs() const
346 : {
347 797964 : return &aAttrs;
348 : }
349 :
350 : //*************************** APureElement **************************//
351 :
352 71589 : APureElement::APureElement( const char * i_sTagName )
353 71589 : : sTagName( i_sTagName )
354 : // pContent
355 : {
356 71589 : }
357 :
358 71589 : APureElement::~APureElement()
359 : {
360 71589 : }
361 :
362 : const String &
363 143177 : APureElement::inq_TagName() const
364 : {
365 143177 : return sTagName;
366 : }
367 :
368 : Dyn< Item > &
369 154965 : APureElement::inq_RefContent()
370 : {
371 154965 : return pContent;
372 : }
373 :
374 : //*************************** AnAttribute **************************//
375 777492 : AnAttribute::AnAttribute( const String & i_sName,
376 : const String & i_sValue )
377 : : sName(i_sName),
378 777492 : sValue(i_sValue)
379 : {
380 777492 : }
381 :
382 47157 : AnAttribute::AnAttribute( const char * i_sName,
383 : const char * i_sValue )
384 : : sName(i_sName),
385 47157 : sValue(i_sValue)
386 : {
387 47157 : }
388 :
389 1290597 : AnAttribute::~AnAttribute()
390 : {
391 1290597 : }
392 :
393 : const String &
394 824649 : AnAttribute::inq_Name() const
395 : {
396 824649 : return sName;
397 : }
398 :
399 : const String &
400 1648733 : AnAttribute::inq_Value() const
401 : {
402 1648733 : return sValue;
403 : }
404 :
405 :
406 :
407 : //*************************** Text **************************//
408 :
409 441907 : Text::Text( const String & i_sText )
410 441907 : : sText(i_sText)
411 : {
412 441907 : }
413 :
414 1165408 : Text::Text( const char * i_sText )
415 1165408 : : sText(i_sText)
416 : {
417 1165408 : }
418 :
419 3214630 : Text::~Text()
420 : {
421 3214630 : }
422 :
423 : void
424 1607315 : Text::do_WriteOut( csv::bostream & io_aFile ) const
425 : {
426 : const unsigned char *
427 1607315 : pStart = reinterpret_cast< const unsigned char* >(sText.c_str());
428 : const unsigned char *
429 1607315 : pOut = pStart;
430 :
431 8637535 : for ( ; *pOut != '\0'; ++pOut )
432 : {
433 7030220 : if ( cReplacable[*pOut] )
434 : {
435 2439 : if ( pOut != pStart )
436 : {
437 2419 : io_aFile.write( pStart, pOut-pStart );
438 : }
439 :
440 2439 : switch (*pOut)
441 : {
442 1217 : case '<': io_aFile.write("<"); break;
443 1217 : case '>': io_aFile.write(">"); break;
444 1 : case '"': io_aFile.write("""); break;
445 4 : case '&': io_aFile.write("&"); break;
446 0 : case 255: io_aFile.write(" "); break;
447 : }
448 :
449 2439 : pStart = pOut+1;
450 : } // endif (cReplacable[*pOut])
451 : } // end for
452 :
453 1607315 : if ( pOut != pStart )
454 : {
455 1605942 : io_aFile.write( pStart, pOut-pStart );
456 : }
457 1607315 : }
458 :
459 :
460 : //*************************** XmlCode **************************//
461 :
462 26743 : XmlCode::XmlCode( const String & i_sText )
463 26743 : : sText(i_sText)
464 : {
465 26743 : }
466 :
467 716104 : XmlCode::XmlCode( const char * i_sText )
468 716104 : : sText(i_sText)
469 : {
470 716104 : }
471 :
472 1403288 : XmlCode::~XmlCode()
473 : {
474 1403288 : }
475 :
476 : void
477 742847 : XmlCode::do_WriteOut( csv::bostream & io_aFile ) const
478 : {
479 742847 : io_aFile.write(sText);
480 742847 : }
481 :
482 :
483 : //*************************** MultiItem **************************//
484 :
485 818948 : MultiItem::MultiItem()
486 : {
487 818948 : }
488 :
489 1637896 : MultiItem::~MultiItem()
490 : {
491 1637896 : }
492 :
493 : void
494 818948 : MultiItem::do_WriteOut( csv::bostream & io_aFile ) const
495 : {
496 818948 : ItemList::iterator itEnd = aItems.end();
497 :
498 4030832 : for ( ItemList::iterator it = aItems.begin();
499 : it != itEnd;
500 : ++it )
501 : {
502 3211884 : (*it)->WriteOut( io_aFile );
503 : }
504 :
505 818948 : }
506 :
507 :
508 :
509 : //*************************** Helpers **************************//
510 :
511 : void
512 3211884 : StreamOut( Dyn< Item > & o_rContent,
513 : DYN Item * let_dpItem )
514 : {
515 3211884 : MultiItem * pContent = 0;
516 3211884 : if ( bool(o_rContent) )
517 : {
518 2392936 : pContent = static_cast< MultiItem* >( o_rContent.MutablePtr() );
519 : csv_assert( dynamic_cast< MultiItem* >( o_rContent.MutablePtr() ) != 0 );
520 : }
521 : else
522 : {
523 818948 : pContent = new MultiItem;
524 818948 : o_rContent = pContent;
525 : }
526 :
527 : csv_assert( let_dpItem != 0 );
528 3211884 : pContent->Add( let_dpItem );
529 3211884 : }
530 :
531 :
532 :
533 :
534 : } // namespace xml
535 3 : } // namespace csi
536 :
537 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|