LCOV - code coverage report
Current view: top level - libreoffice/sw/source/filter/html - htmldraw.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 0 385 0.0 %
Date: 2012-12-27 Functions: 0 9 0.0 %
Legend: Lines: hit not hit

          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 "hintids.hxx"
      21             : #include <vcl/svapp.hxx>
      22             : #include <vcl/wrkwin.hxx>
      23             : #include <svx/svdmodel.hxx>
      24             : #include <svx/svdpage.hxx>
      25             : #include <svx/svdobj.hxx>
      26             : #include <svx/svdotext.hxx>
      27             : #include <editeng/eeitem.hxx>
      28             : 
      29             : #ifndef _OUTLINER_HXX //autogen
      30             : #define _EEITEMID_HXX
      31             : #include <editeng/outliner.hxx>
      32             : #endif
      33             : #include <svx/xfillit.hxx>
      34             : #include <editeng/colritem.hxx>
      35             : #include <editeng/brshitem.hxx>
      36             : #include <editeng/lrspitem.hxx>
      37             : #include <editeng/ulspitem.hxx>
      38             : #include <svl/itemiter.hxx>
      39             : #include <svl/whiter.hxx>
      40             : #include <svtools/htmlout.hxx>
      41             : #include <svtools/htmltokn.h>
      42             : #include <svtools/htmlkywd.hxx>
      43             : #include <svx/svdpool.hxx>
      44             : 
      45             : 
      46             : #include "charatr.hxx"
      47             : #include <frmfmt.hxx>
      48             : #include <fmtanchr.hxx>
      49             : #include <fmtsrnd.hxx>
      50             : #include "ndtxt.hxx"
      51             : #include "doc.hxx"
      52             : #include "dcontact.hxx"
      53             : #include "poolfmt.hxx"
      54             : #include "swcss1.hxx"
      55             : #include "swhtml.hxx"
      56             : #include "wrthtml.hxx"
      57             : #include <rtl/strbuf.hxx>
      58             : 
      59             : using namespace ::com::sun::star;
      60             : 
      61             : 
      62             : const sal_uInt32 HTML_FRMOPTS_MARQUEE   =
      63             :     HTML_FRMOPT_ALIGN |
      64             :     HTML_FRMOPT_SPACE;
      65             : 
      66             : const sal_uInt32 HTML_FRMOPTS_MARQUEE_CSS1  =
      67             :     HTML_FRMOPT_S_ALIGN |
      68             :     HTML_FRMOPT_S_SPACE;
      69             : 
      70             : static HTMLOptionEnum aHTMLMarqBehaviorTable[] =
      71             : {
      72             :     { OOO_STRING_SVTOOLS_HTML_BEHAV_scroll,     SDRTEXTANI_SCROLL       },
      73             :     { OOO_STRING_SVTOOLS_HTML_BEHAV_alternate,  SDRTEXTANI_ALTERNATE    },
      74             :     { OOO_STRING_SVTOOLS_HTML_BEHAV_slide,      SDRTEXTANI_SLIDE        },
      75             :     { 0,                        0                       }
      76             : };
      77             : 
      78             : static HTMLOptionEnum aHTMLMarqDirectionTable[] =
      79             : {
      80             :     { OOO_STRING_SVTOOLS_HTML_AL_left,          SDRTEXTANI_LEFT         },
      81             :     { OOO_STRING_SVTOOLS_HTML_AL_right,         SDRTEXTANI_RIGHT        },
      82             :     { 0,                        0                       }
      83             : };
      84             : 
      85           0 : void SwHTMLParser::InsertDrawObject( SdrObject* pNewDrawObj,
      86             :                                      const Size& rPixSpace,
      87             :                                      sal_Int16 eVertOri,
      88             :                                      sal_Int16 eHoriOri,
      89             :                                      SfxItemSet& rCSS1ItemSet,
      90             :                                      SvxCSS1PropertyInfo& rCSS1PropInfo,
      91             :                                      sal_Bool bHidden )
      92             : {
      93             :     // always on top of text.
      94             :     // but in invisible layer. <ConnectToLayout> will move the object
      95             :     // to the visible layer.
      96           0 :     pNewDrawObj->SetLayer( pDoc->GetInvisibleHeavenId() );
      97             : 
      98           0 :     SfxItemSet aFrmSet( pDoc->GetAttrPool(),
      99           0 :                         RES_FRMATR_BEGIN, RES_FRMATR_END-1 );
     100           0 :     if( !IsNewDoc() )
     101           0 :         Reader::ResetFrmFmtAttrs( aFrmSet );
     102             : 
     103           0 :     sal_uInt16 nLeftSpace = 0, nRightSpace = 0, nUpperSpace = 0, nLowerSpace = 0;
     104           0 :     if( (rPixSpace.Width() || rPixSpace.Height()) && Application::GetDefaultDevice() )
     105             :     {
     106           0 :         Size aTwipSpc( rPixSpace.Width(), rPixSpace.Height() );
     107             :         aTwipSpc =
     108             :             Application::GetDefaultDevice()->PixelToLogic( aTwipSpc,
     109           0 :                                                 MapMode(MAP_TWIP) );
     110           0 :         nLeftSpace = nRightSpace = (sal_uInt16)aTwipSpc.Width();
     111           0 :         nUpperSpace = nLowerSpace = (sal_uInt16)aTwipSpc.Height();
     112             :     }
     113             : 
     114             :     // linken/rechten Rand setzen
     115             :     const SfxPoolItem *pItem;
     116           0 :     if( SFX_ITEM_SET==rCSS1ItemSet.GetItemState( RES_LR_SPACE, sal_True, &pItem ) )
     117             :     {
     118             :         // Ggf. den Erstzeilen-Einzug noch plaetten
     119           0 :         const SvxLRSpaceItem *pLRItem = (const SvxLRSpaceItem *)pItem;
     120           0 :         SvxLRSpaceItem aLRItem( *pLRItem );
     121           0 :         aLRItem.SetTxtFirstLineOfst( 0 );
     122           0 :         if( rCSS1PropInfo.bLeftMargin )
     123             :         {
     124           0 :             nLeftSpace = static_cast< sal_uInt16 >(aLRItem.GetLeft());
     125           0 :             rCSS1PropInfo.bLeftMargin = sal_False;
     126             :         }
     127           0 :         if( rCSS1PropInfo.bRightMargin )
     128             :         {
     129           0 :             nRightSpace = static_cast< sal_uInt16 >(aLRItem.GetRight());
     130           0 :             rCSS1PropInfo.bRightMargin = sal_False;
     131             :         }
     132           0 :         rCSS1ItemSet.ClearItem( RES_LR_SPACE );
     133             :     }
     134           0 :     if( nLeftSpace || nRightSpace )
     135             :     {
     136           0 :         SvxLRSpaceItem aLRItem( RES_LR_SPACE );
     137           0 :         aLRItem.SetLeft( nLeftSpace );
     138           0 :         aLRItem.SetRight( nRightSpace );
     139           0 :         aFrmSet.Put( aLRItem );
     140             :     }
     141             : 
     142             :     // oberen/unteren Rand setzen
     143           0 :     if( SFX_ITEM_SET==rCSS1ItemSet.GetItemState( RES_UL_SPACE, sal_True, &pItem ) )
     144             :     {
     145             :         // Ggf. den Erstzeilen-Einzug noch plaetten
     146           0 :         const SvxULSpaceItem *pULItem = (const SvxULSpaceItem *)pItem;
     147           0 :         if( rCSS1PropInfo.bTopMargin )
     148             :         {
     149           0 :             nUpperSpace = pULItem->GetUpper();
     150           0 :             rCSS1PropInfo.bTopMargin = sal_False;
     151             :         }
     152           0 :         if( rCSS1PropInfo.bBottomMargin )
     153             :         {
     154           0 :             nLowerSpace = pULItem->GetLower();
     155           0 :             rCSS1PropInfo.bBottomMargin = sal_False;
     156             :         }
     157             : 
     158           0 :         rCSS1ItemSet.ClearItem( RES_UL_SPACE );
     159             :     }
     160           0 :     if( nUpperSpace || nLowerSpace )
     161             :     {
     162           0 :         SvxULSpaceItem aULItem( RES_UL_SPACE );
     163           0 :         aULItem.SetUpper( nUpperSpace );
     164           0 :         aULItem.SetLower( nLowerSpace );
     165           0 :         aFrmSet.Put( aULItem );
     166             :     }
     167             : 
     168           0 :     SwFmtAnchor aAnchor( FLY_AS_CHAR );
     169           0 :     if( SVX_CSS1_POS_ABSOLUTE == rCSS1PropInfo.ePosition &&
     170             :         SVX_CSS1_LTYPE_TWIP == rCSS1PropInfo.eLeftType &&
     171             :         SVX_CSS1_LTYPE_TWIP == rCSS1PropInfo.eTopType )
     172             :     {
     173             :         const SwStartNode *pFlySttNd =
     174           0 :             pPam->GetPoint()->nNode.GetNode().FindFlyStartNode();
     175             : 
     176           0 :         if( pFlySttNd )
     177             :         {
     178           0 :             aAnchor.SetType( FLY_AT_FLY );
     179           0 :             SwPosition aPos( *pFlySttNd );
     180           0 :             aAnchor.SetAnchor( &aPos );
     181             :         }
     182             :         else
     183             :         {
     184           0 :             aAnchor.SetType( FLY_AT_PAGE );
     185             :         }
     186             :         // #i26791# - direct positioning for <SwDoc::Insert(..)>
     187             :         pNewDrawObj->SetRelativePos( Point(rCSS1PropInfo.nLeft + nLeftSpace,
     188           0 :                                            rCSS1PropInfo.nTop + nUpperSpace) );
     189           0 :         aFrmSet.Put( SwFmtSurround(SURROUND_THROUGHT) );
     190             :     }
     191           0 :     else if( SVX_ADJUST_LEFT == rCSS1PropInfo.eFloat ||
     192             :              text::HoriOrientation::LEFT == eHoriOri )
     193             :     {
     194           0 :         aAnchor.SetType( FLY_AT_PARA );
     195             :         aFrmSet.Put( SwFmtSurround(bHidden ? SURROUND_THROUGHT
     196           0 :                                              : SURROUND_RIGHT) );
     197             :         // #i26791# - direct positioning for <SwDoc::Insert(..)>
     198           0 :         pNewDrawObj->SetRelativePos( Point(nLeftSpace, nUpperSpace) );
     199             :     }
     200           0 :     else if( text::VertOrientation::NONE != eVertOri )
     201             :     {
     202           0 :         aFrmSet.Put( SwFmtVertOrient( 0, eVertOri ) );
     203             :     }
     204             : 
     205           0 :     if (FLY_AT_PAGE == aAnchor.GetAnchorId())
     206             :     {
     207           0 :         aAnchor.SetPageNum( 1 );
     208             :     }
     209           0 :     else if( FLY_AT_FLY != aAnchor.GetAnchorId() )
     210             :     {
     211           0 :         aAnchor.SetAnchor( pPam->GetPoint() );
     212             :     }
     213           0 :     aFrmSet.Put( aAnchor );
     214             : 
     215           0 :     pDoc->Insert( *pPam, *pNewDrawObj, &aFrmSet, NULL );
     216           0 : }
     217             : 
     218             : 
     219           0 : static void PutEEPoolItem( SfxItemSet &rEEItemSet,
     220             :                            const SfxPoolItem& rSwItem )
     221             : {
     222             : 
     223           0 :     sal_uInt16 nEEWhich = 0;
     224             : 
     225           0 :     switch( rSwItem.Which() )
     226             :     {
     227           0 :     case RES_CHRATR_COLOR:          nEEWhich = EE_CHAR_COLOR; break;
     228           0 :     case RES_CHRATR_CROSSEDOUT:     nEEWhich = EE_CHAR_STRIKEOUT; break;
     229           0 :     case RES_CHRATR_ESCAPEMENT:     nEEWhich = EE_CHAR_ESCAPEMENT; break;
     230           0 :     case RES_CHRATR_FONT:           nEEWhich = EE_CHAR_FONTINFO; break;
     231           0 :     case RES_CHRATR_CJK_FONT:       nEEWhich = EE_CHAR_FONTINFO_CJK; break;
     232           0 :     case RES_CHRATR_CTL_FONT:       nEEWhich = EE_CHAR_FONTINFO_CTL; break;
     233           0 :     case RES_CHRATR_FONTSIZE:       nEEWhich = EE_CHAR_FONTHEIGHT; break;
     234           0 :     case RES_CHRATR_CJK_FONTSIZE:   nEEWhich = EE_CHAR_FONTHEIGHT_CJK; break;
     235           0 :     case RES_CHRATR_CTL_FONTSIZE:   nEEWhich = EE_CHAR_FONTHEIGHT_CTL; break;
     236           0 :     case RES_CHRATR_KERNING:        nEEWhich = EE_CHAR_KERNING; break;
     237           0 :     case RES_CHRATR_POSTURE:        nEEWhich = EE_CHAR_ITALIC; break;
     238           0 :     case RES_CHRATR_CJK_POSTURE:    nEEWhich = EE_CHAR_ITALIC_CJK; break;
     239           0 :     case RES_CHRATR_CTL_POSTURE:    nEEWhich = EE_CHAR_ITALIC_CTL; break;
     240           0 :     case RES_CHRATR_UNDERLINE:      nEEWhich = EE_CHAR_UNDERLINE; break;
     241           0 :     case RES_CHRATR_WEIGHT:         nEEWhich = EE_CHAR_WEIGHT; break;
     242           0 :     case RES_CHRATR_CJK_WEIGHT:     nEEWhich = EE_CHAR_WEIGHT_CJK; break;
     243           0 :     case RES_CHRATR_CTL_WEIGHT:     nEEWhich = EE_CHAR_WEIGHT_CTL; break;
     244             :     case RES_BACKGROUND:
     245             :     case RES_CHRATR_BACKGROUND:
     246             :         {
     247           0 :             const SvxBrushItem& rBrushItem = (const SvxBrushItem&)rSwItem;
     248           0 :             rEEItemSet.Put( XFillStyleItem(XFILL_SOLID) );
     249             :             rEEItemSet.Put( XFillColorItem(aEmptyStr,
     250           0 :                             rBrushItem.GetColor()) );
     251             :         }
     252           0 :         break;
     253             :     }
     254             : 
     255           0 :     if( nEEWhich )
     256             :     {
     257           0 :         SfxPoolItem *pEEItem = rSwItem.Clone();
     258           0 :         pEEItem->SetWhich( nEEWhich );
     259           0 :         rEEItemSet.Put( *pEEItem );
     260           0 :         delete pEEItem;
     261             :     }
     262           0 : }
     263             : 
     264           0 : void SwHTMLParser::NewMarquee( HTMLTable *pCurTable )
     265             : {
     266             : 
     267             :     OSL_ENSURE( !pMarquee, "Marquee in Marquee???" );
     268           0 :     aContents.Erase();
     269             : 
     270           0 :     String aId, aStyle, aClass;
     271             : 
     272           0 :     long nWidth=0, nHeight=0;
     273           0 :     sal_Bool bPrcWidth = sal_False, bDirection = sal_False, bBGColor = sal_False;
     274           0 :     Size aSpace( 0, 0 );
     275           0 :     sal_Int16 eVertOri = text::VertOrientation::TOP;
     276           0 :     sal_Int16 eHoriOri = text::HoriOrientation::NONE;
     277           0 :     SdrTextAniKind eAniKind = SDRTEXTANI_SCROLL;
     278           0 :     SdrTextAniDirection eAniDir = SDRTEXTANI_LEFT;
     279           0 :     sal_uInt16 nCount = 0, nDelay = 60;
     280           0 :     sal_Int16 nAmount = -6;
     281           0 :     Color aBGColor;
     282             : 
     283           0 :     const HTMLOptions& rHTMLOptions = GetOptions();
     284           0 :     for (size_t i = 0, n = rHTMLOptions.size(); i < n; ++i)
     285             :     {
     286           0 :         const HTMLOption& rOption = rHTMLOptions[i];
     287           0 :         switch( rOption.GetToken() )
     288             :         {
     289             :             case HTML_O_ID:
     290           0 :                 aId = rOption.GetString();
     291           0 :                 break;
     292             :             case HTML_O_STYLE:
     293           0 :                 aStyle = rOption.GetString();
     294           0 :                 break;
     295             :             case HTML_O_CLASS:
     296           0 :                 aClass = rOption.GetString();
     297           0 :                 break;
     298             : 
     299             :             case HTML_O_BEHAVIOR:
     300             :                 eAniKind =
     301             :                     (SdrTextAniKind)rOption.GetEnum( aHTMLMarqBehaviorTable,
     302           0 :                                                       static_cast< sal_uInt16 >(eAniKind) );
     303           0 :                 break;
     304             : 
     305             :             case HTML_O_BGCOLOR:
     306           0 :                 rOption.GetColor( aBGColor );
     307           0 :                 bBGColor = sal_True;
     308           0 :                 break;
     309             : 
     310             :             case HTML_O_DIRECTION:
     311             :                 eAniDir =
     312             :                     (SdrTextAniDirection)rOption.GetEnum( aHTMLMarqDirectionTable,
     313           0 :                                                       static_cast< sal_uInt16 >(eAniDir) );
     314           0 :                 bDirection = sal_True;
     315           0 :                 break;
     316             : 
     317             :             case HTML_O_LOOP:
     318           0 :                 if( rOption.GetString().
     319           0 :                         EqualsIgnoreCaseAscii(OOO_STRING_SVTOOLS_HTML_LOOP_infinite) )
     320             :                 {
     321           0 :                     nCount = 0;
     322             :                 }
     323             :                 else
     324             :                 {
     325           0 :                     sal_uInt32 nLoop = rOption.GetSNumber();
     326           0 :                     nCount = (sal_uInt16)(nLoop>0 ? nLoop : 0 );
     327             :                 }
     328           0 :                 break;
     329             : 
     330             :             case HTML_O_SCROLLAMOUNT:
     331           0 :                 nAmount = -((sal_Int16)rOption.GetNumber());
     332           0 :                 break;
     333             : 
     334             :             case HTML_O_SCROLLDELAY:
     335           0 :                 nDelay = (sal_uInt16)rOption.GetNumber();
     336           0 :                 break;
     337             : 
     338             :             case HTML_O_WIDTH:
     339             :                 // erstmal nur als Pixelwerte merken!
     340           0 :                 nWidth = rOption.GetNumber();
     341           0 :                 bPrcWidth = rOption.GetString().Search('%') != STRING_NOTFOUND;
     342           0 :                 if( bPrcWidth && nWidth>100 )
     343           0 :                     nWidth = 100;
     344           0 :                 break;
     345             : 
     346             :             case HTML_O_HEIGHT:
     347             :                 // erstmal nur als Pixelwerte merken!
     348           0 :                 nHeight = rOption.GetNumber();
     349           0 :                 if( rOption.GetString().Search('%') != STRING_NOTFOUND )
     350           0 :                     nHeight = 0;
     351           0 :                 break;
     352             : 
     353             :             case HTML_O_HSPACE:
     354             :                 // erstmal nur als Pixelwerte merken!
     355           0 :                 aSpace.Height() = rOption.GetNumber();
     356           0 :                 break;
     357             : 
     358             :             case HTML_O_VSPACE:
     359             :                 // erstmal nur als Pixelwerte merken!
     360           0 :                 aSpace.Width() = rOption.GetNumber();
     361           0 :                 break;
     362             : 
     363             :             case HTML_O_ALIGN:
     364             :                 eVertOri =
     365             :                     rOption.GetEnum( aHTMLImgVAlignTable,
     366           0 :                                                     text::VertOrientation::TOP );
     367             :                 eHoriOri =
     368             :                     rOption.GetEnum( aHTMLImgHAlignTable,
     369           0 :                                                     text::HoriOrientation::NONE );
     370           0 :                 break;
     371             :         }
     372             :     }
     373             : 
     374             :     // Ein DrawTxtobj anlegen
     375             :     // #i52858# - method name changed
     376           0 :     SdrModel* pModel = pDoc->GetOrCreateDrawModel();
     377             : 
     378           0 :     SdrPage* pPg = pModel->GetPage( 0 );
     379             :     pMarquee = SdrObjFactory::MakeNewObject( SdrInventor,
     380           0 :                                              OBJ_TEXT, pPg, pModel );
     381           0 :     if( !pMarquee )
     382           0 :         return;
     383             : 
     384           0 :     pPg->InsertObject( pMarquee );
     385             : 
     386           0 :     if( aId.Len() )
     387           0 :         InsertBookmark( aId );
     388             : 
     389             :     // (Nur) Alternate leueft per Default von links nach rechts
     390           0 :     if( SDRTEXTANI_ALTERNATE==eAniKind && !bDirection )
     391           0 :         eAniDir = SDRTEXTANI_RIGHT;
     392             : 
     393             :     // die fuer das Scrollen benoetigten Attribute umsetzen
     394             :     sal_uInt16 aWhichMap[7] =   { XATTR_FILL_FIRST,   XATTR_FILL_LAST,
     395             :                               SDRATTR_MISC_FIRST, SDRATTR_MISC_LAST,
     396             :                               EE_CHAR_START,      EE_CHAR_END,
     397           0 :                               0 };
     398           0 :     SfxItemSet aItemSet( pModel->GetItemPool(), aWhichMap );
     399           0 :     aItemSet.Put( SdrTextAutoGrowWidthItem( sal_False ) );
     400           0 :     aItemSet.Put( SdrTextAutoGrowHeightItem( sal_True ) );
     401           0 :     aItemSet.Put( SdrTextAniKindItem( eAniKind ) );
     402           0 :     aItemSet.Put( SdrTextAniDirectionItem( eAniDir ) );
     403           0 :     aItemSet.Put( SdrTextAniCountItem( nCount ) );
     404           0 :     aItemSet.Put( SdrTextAniDelayItem( nDelay ) );
     405           0 :     aItemSet.Put( SdrTextAniAmountItem( nAmount ) );
     406           0 :     if( SDRTEXTANI_ALTERNATE==eAniKind )
     407             :     {
     408             :         // (Nur) Alternate startet und stoppt per default Inside
     409           0 :         aItemSet.Put( SdrTextAniStartInsideItem(sal_True) );
     410           0 :         aItemSet.Put( SdrTextAniStopInsideItem(sal_True) );
     411           0 :         if( SDRTEXTANI_LEFT==eAniDir )
     412           0 :             aItemSet.Put( SdrTextHorzAdjustItem(SDRTEXTHORZADJUST_RIGHT) );
     413             :     }
     414             : 
     415             :     // die Default-Farbe (aus der Standard-Vorlage) setzen, damit ueberhaupt
     416             :     // eine sinnvolle Farbe gesetzt ist.
     417             :     const Color& rDfltColor =
     418           0 :         pCSS1Parser->GetTxtCollFromPool( RES_POOLCOLL_STANDARD )
     419           0 :             ->GetColor().GetValue();
     420           0 :     aItemSet.Put( SvxColorItem( rDfltColor, EE_CHAR_COLOR ) );
     421             : 
     422             :     // Die Attribute der aktuellen Absatzvorlage setzen
     423             :     sal_uInt16 nWhichIds[] =
     424             :     {
     425             :         RES_CHRATR_COLOR,   RES_CHRATR_CROSSEDOUT, RES_CHRATR_ESCAPEMENT,
     426             :         RES_CHRATR_FONT,    RES_CHRATR_FONTSIZE,   RES_CHRATR_KERNING,
     427             :         RES_CHRATR_POSTURE, RES_CHRATR_UNDERLINE,  RES_CHRATR_WEIGHT,
     428             :         RES_CHRATR_BACKGROUND,
     429             :         RES_CHRATR_CJK_FONT, RES_CHRATR_CJK_FONTSIZE,
     430             :         RES_CHRATR_CJK_POSTURE, RES_CHRATR_CJK_WEIGHT,
     431             :         RES_CHRATR_CTL_FONT, RES_CHRATR_CTL_FONTSIZE,
     432             :         RES_CHRATR_CTL_POSTURE, RES_CHRATR_CTL_WEIGHT,
     433             :         0
     434           0 :     };
     435             :     SwTxtNode const*const pTxtNd =
     436           0 :         pPam->GetPoint()->nNode.GetNode().GetTxtNode();
     437           0 :     if( pTxtNd )
     438             :     {
     439           0 :         const SfxItemSet& rItemSet = pTxtNd->GetAnyFmtColl().GetAttrSet();
     440             :         const SfxPoolItem *pItem;
     441           0 :         for( sal_uInt16 i=0; nWhichIds[i]; i++ )
     442             :         {
     443           0 :             if( SFX_ITEM_SET == rItemSet.GetItemState( nWhichIds[i], sal_True, &pItem ) )
     444           0 :                 PutEEPoolItem( aItemSet, *pItem );
     445             :         }
     446             :     }
     447             : 
     448             :     // die Attribute der Umgebung am Draw-Objekt setzen
     449           0 :     _HTMLAttr** pTbl = (_HTMLAttr**)&aAttrTab;
     450           0 :     for( sal_uInt16 nCnt = sizeof( _HTMLAttrTable ) / sizeof( _HTMLAttr* );
     451             :          nCnt--; ++pTbl )
     452             :     {
     453           0 :         _HTMLAttr *pAttr = *pTbl;
     454           0 :         if( pAttr )
     455           0 :             PutEEPoolItem( aItemSet, pAttr->GetItem() );
     456             :     }
     457             : 
     458           0 :     if( bBGColor )
     459             :     {
     460           0 :         aItemSet.Put( XFillStyleItem(XFILL_SOLID) );
     461           0 :         aItemSet.Put( XFillColorItem(aEmptyStr, aBGColor) );
     462             :     }
     463             : 
     464             :     // Styles parsen (funktioniert hier nur fuer Attribute, die auch
     465             :     // am Zeichen-Objekt gesetzt werden koennen)
     466           0 :     SfxItemSet aStyleItemSet( pDoc->GetAttrPool(),
     467           0 :                               pCSS1Parser->GetWhichMap() );
     468           0 :     SvxCSS1PropertyInfo aPropInfo;
     469           0 :     if( HasStyleOptions( aStyle, aId, aClass )  &&
     470           0 :         ParseStyleOptions( aStyle, aId, aClass, aStyleItemSet, aPropInfo ) )
     471             :     {
     472           0 :         SfxItemIter aIter( aStyleItemSet );
     473             : 
     474           0 :         const SfxPoolItem *pItem = aIter.FirstItem();
     475           0 :         while( pItem )
     476             :         {
     477           0 :             PutEEPoolItem( aItemSet, *pItem );
     478           0 :             pItem = aIter.NextItem();
     479           0 :         }
     480             :     }
     481             : 
     482             :     // jetzt noch die Groesse setzen
     483           0 :     Size aTwipSz( bPrcWidth ? 0 : nWidth, nHeight );
     484           0 :     if( (aTwipSz.Width() || aTwipSz.Height()) && Application::GetDefaultDevice() )
     485             :     {
     486             :         aTwipSz = Application::GetDefaultDevice()
     487           0 :                     ->PixelToLogic( aTwipSz, MapMode( MAP_TWIP ) );
     488             :     }
     489             : 
     490           0 :     if( SVX_CSS1_LTYPE_TWIP== aPropInfo.eWidthType )
     491             :     {
     492           0 :         aTwipSz.Width() = aPropInfo.nWidth;
     493           0 :         nWidth = 1; // != 0;
     494           0 :         bPrcWidth = sal_False;
     495             :     }
     496           0 :     if( SVX_CSS1_LTYPE_TWIP== aPropInfo.eHeightType )
     497           0 :         aTwipSz.Height() = aPropInfo.nHeight;
     498             : 
     499           0 :     bFixMarqueeWidth = sal_False;
     500           0 :     if( !nWidth || bPrcWidth )
     501             :     {
     502           0 :         if( pTable )
     503             :         {
     504           0 :             if( !pCurTable )
     505             :             {
     506             :                 // Die Laufschrift steht in einer Tabelle, aber nicht
     507             :                 // in einer Zelle. Da jetzt keine vernuenftige Zuordung
     508             :                 // zu einer Zelle moeglich ist, passen wir hir die
     509             :                 // Breite dem Inhalt der Laufschrift an.
     510           0 :                 bFixMarqueeWidth = sal_True;
     511             :             }
     512           0 :             else if( !nWidth )
     513             :             {
     514             :                 // Da wir wissen, in welcher Zelle die Laufschrift ist,
     515             :                 // koennen wir die Breite auch anpassen. Keine Breitenangabe
     516             :                 // wird wie 100% behandelt.
     517           0 :                 nWidth = 100;
     518           0 :                 bPrcWidth = sal_True;
     519             :             }
     520           0 :             aTwipSz.Width() = MINLAY;
     521             :         }
     522             :         else
     523             :         {
     524           0 :             long nBrowseWidth = GetCurrentBrowseWidth();
     525           0 :             aTwipSz.Width() = !nWidth ? nBrowseWidth
     526           0 :                                       : (nWidth*nBrowseWidth) / 100;
     527             :         }
     528             :     }
     529             : 
     530             :     // Die Hoehe ist nur eine Mindest-Hoehe
     531           0 :     if( aTwipSz.Height() < MINFLY )
     532           0 :         aTwipSz.Height() = MINFLY;
     533           0 :     aItemSet.Put( SdrTextMinFrameHeightItem( aTwipSz.Height() ) );
     534             : 
     535           0 :     pMarquee->SetMergedItemSetAndBroadcast(aItemSet);
     536             : 
     537           0 :     if( aTwipSz.Width() < MINFLY )
     538           0 :         aTwipSz.Width() = MINFLY;
     539           0 :     pMarquee->SetLogicRect( Rectangle( 0, 0, aTwipSz.Width(), aTwipSz.Height() ) );
     540             : 
     541             :     // und das Objekt in das Dok einfuegen
     542             :     InsertDrawObject( pMarquee, aSpace, eVertOri, eHoriOri, aStyleItemSet,
     543           0 :                       aPropInfo );
     544             : 
     545             :     // Das Zeichen-Objekt der Tabelle bekanntmachen. Ist ein bisserl
     546             :     // umstaendlich, weil noch ueber den Parser gegangen wird, obwohl die
     547             :     // Tabelle bekannt ist, aber anderenfalls muesste man die Tabelle
     548             :     // oeffentlich machen, und das ist auch nicht schoen. Das globale
     549             :     // pTable kann uebrigens auch nicht verwendet werden, denn die
     550             :     // Laufschrift kann sich auch mal in einer Sub-Tabelle befinden.
     551           0 :     if( pCurTable && bPrcWidth)
     552           0 :         RegisterDrawObjectToTable( pCurTable, pMarquee, (sal_uInt8)nWidth );
     553             : }
     554             : 
     555           0 : void SwHTMLParser::EndMarquee()
     556             : {
     557             :     OSL_ENSURE( pMarquee && OBJ_TEXT==pMarquee->GetObjIdentifier(),
     558             :             "kein Marquee oder falscher Typ" );
     559             : 
     560           0 :     if( bFixMarqueeWidth )
     561             :     {
     562             :         // Da es keine fixe Hoehe gibt, das Text-Objekt erstmal breiter
     563             :         // als den Text machen, damit nicht umgebrochen wird.
     564           0 :         const Rectangle& rOldRect = pMarquee->GetLogicRect();
     565             :         pMarquee->SetLogicRect( Rectangle( rOldRect.TopLeft(),
     566           0 :                                            Size( USHRT_MAX, 240 ) ) );
     567             :     }
     568             : 
     569             :     // den gesammelten Text einfuegen
     570           0 :     ((SdrTextObj*)pMarquee)->SetText( aContents );
     571           0 :     pMarquee->SetMergedItemSetAndBroadcast( pMarquee->GetMergedItemSet() );
     572             : 
     573           0 :     if( bFixMarqueeWidth )
     574             :     {
     575             :         // die Groesse dem Text anpassen.
     576           0 :         ((SdrTextObj*)pMarquee)->FitFrameToTextSize();
     577             :     }
     578             : 
     579           0 :     aContents.Erase();
     580           0 :     pMarquee = 0;
     581           0 : }
     582             : 
     583           0 : void SwHTMLParser::InsertMarqueeText()
     584             : {
     585             :     OSL_ENSURE( pMarquee && OBJ_TEXT==pMarquee->GetObjIdentifier(),
     586             :             "kein Marquee oder falscher Typ" );
     587             : 
     588             :     // das akteulle Textstueck an den Text anhaengen
     589           0 :     aContents += aToken;
     590           0 : }
     591             : 
     592           0 : void SwHTMLParser::ResizeDrawObject( SdrObject* pObj, SwTwips nWidth )
     593             : {
     594             :     OSL_ENSURE( OBJ_TEXT==pObj->GetObjIdentifier(),
     595             :             "kein Marquee oder falscher Typ" );
     596             : 
     597           0 :     if( OBJ_TEXT!=pObj->GetObjIdentifier() )
     598           0 :         return;
     599             : 
     600             :     // die alte Groesse
     601           0 :     const Rectangle& rOldRect = pObj->GetLogicRect();
     602           0 :     Size aNewSz( nWidth, rOldRect.GetSize().Height() );
     603           0 :     pObj->SetLogicRect( Rectangle( rOldRect.TopLeft(), aNewSz ) );
     604             : }
     605             : 
     606             : 
     607           0 : const SdrObject *SwHTMLWriter::GetMarqueeTextObj( const SwDrawFrmFmt& rFmt )
     608             : {
     609           0 :     const SdrObject* pObj = rFmt.FindSdrObject();
     610           0 :     return (pObj && ::IsMarqueeTextObj( *pObj )) ? pObj : 0;
     611             : }
     612             : 
     613           0 : void SwHTMLWriter::GetEEAttrsFromDrwObj( SfxItemSet& rItemSet,
     614             :                                          const SdrObject *pObj,
     615             :                                          sal_Bool bSetDefaults )
     616             : {
     617             :     // die Edit script::Engine-Attribute aus dem Objekt holen
     618           0 :     SfxItemSet rObjItemSet = pObj->GetMergedItemSet();
     619             : 
     620             :     // ueber die Edit script::Engine-Attribute iterieren und die Attribute
     621             :     // in SW-Attrs wandeln bzw. default setzen
     622           0 :     SfxWhichIter aIter( rObjItemSet );
     623           0 :     sal_uInt16 nEEWhich = aIter.FirstWhich();
     624           0 :     while( nEEWhich )
     625             :     {
     626             :         const SfxPoolItem *pEEItem;
     627             :         sal_Bool bSet = SFX_ITEM_SET == rObjItemSet.GetItemState( nEEWhich, sal_False,
     628           0 :                                                               &pEEItem );
     629             : 
     630           0 :         if( bSet || bSetDefaults )
     631             :         {
     632           0 :             sal_uInt16 nSwWhich = 0;
     633           0 :             switch( nEEWhich )
     634             :             {
     635           0 :             case EE_CHAR_COLOR:         nSwWhich = RES_CHRATR_COLOR;        break;
     636           0 :             case EE_CHAR_STRIKEOUT:     nSwWhich = RES_CHRATR_CROSSEDOUT;   break;
     637           0 :             case EE_CHAR_ESCAPEMENT:    nSwWhich = RES_CHRATR_ESCAPEMENT;   break;
     638           0 :             case EE_CHAR_FONTINFO:      nSwWhich = RES_CHRATR_FONT;         break;
     639           0 :             case EE_CHAR_FONTINFO_CJK:  nSwWhich = RES_CHRATR_CJK_FONT;     break;
     640           0 :             case EE_CHAR_FONTINFO_CTL:  nSwWhich = RES_CHRATR_CTL_FONT;     break;
     641           0 :             case EE_CHAR_FONTHEIGHT:    nSwWhich = RES_CHRATR_FONTSIZE;     break;
     642           0 :             case EE_CHAR_FONTHEIGHT_CJK:nSwWhich = RES_CHRATR_CJK_FONTSIZE; break;
     643           0 :             case EE_CHAR_FONTHEIGHT_CTL:nSwWhich = RES_CHRATR_CTL_FONTSIZE; break;
     644           0 :             case EE_CHAR_KERNING:       nSwWhich = RES_CHRATR_KERNING;      break;
     645           0 :             case EE_CHAR_ITALIC:        nSwWhich = RES_CHRATR_POSTURE;      break;
     646           0 :             case EE_CHAR_ITALIC_CJK:    nSwWhich = RES_CHRATR_CJK_POSTURE;  break;
     647           0 :             case EE_CHAR_ITALIC_CTL:    nSwWhich = RES_CHRATR_CTL_POSTURE;  break;
     648           0 :             case EE_CHAR_UNDERLINE:     nSwWhich = RES_CHRATR_UNDERLINE;    break;
     649           0 :             case EE_CHAR_WEIGHT:        nSwWhich = RES_CHRATR_WEIGHT;       break;
     650           0 :             case EE_CHAR_WEIGHT_CJK:    nSwWhich = RES_CHRATR_CJK_WEIGHT;   break;
     651           0 :             case EE_CHAR_WEIGHT_CTL:    nSwWhich = RES_CHRATR_CTL_WEIGHT;   break;
     652             :             }
     653             : 
     654           0 :             if( nSwWhich )
     655             :             {
     656             :                 // wenn das Item nicht gesetzt ist nehmen wir ggf. das
     657             :                 // Default-Item
     658           0 :                 if( !bSet )
     659           0 :                     pEEItem = &rObjItemSet.GetPool()->GetDefaultItem(nEEWhich);
     660             : 
     661             :                 // jetzt Clonen wir das Item mit der Which-Id des Writers
     662           0 :                 SfxPoolItem *pSwItem = pEEItem->Clone();
     663           0 :                 pSwItem->SetWhich( nSwWhich );
     664           0 :                 rItemSet.Put( *pSwItem );
     665           0 :                 delete pSwItem;
     666             :             }
     667             :         }
     668             : 
     669           0 :         nEEWhich = aIter.NextWhich();
     670           0 :     }
     671           0 : }
     672             : 
     673             : 
     674           0 : Writer& OutHTML_DrawFrmFmtAsMarquee( Writer& rWrt,
     675             :                                      const SwDrawFrmFmt& rFmt,
     676             :                                      const SdrObject& rSdrObject )
     677             : {
     678           0 :     SwHTMLWriter & rHTMLWrt = (SwHTMLWriter&)rWrt;
     679             : 
     680             :     OSL_ENSURE( rWrt.pDoc->GetDrawModel(), "Da gibt's ein Draw-Obj ohne ein Draw-Model zu haben?" );
     681           0 :     const SdrTextObj *pTextObj = (const SdrTextObj *)&rSdrObject;
     682             : 
     683             :     // Gibt es ueberhaupt auszugebenden Text
     684             :     const OutlinerParaObject *pOutlinerParaObj =
     685           0 :         pTextObj->GetOutlinerParaObject();
     686           0 :     if( !pOutlinerParaObj )
     687           0 :         return rWrt;
     688             : 
     689           0 :     rtl::OStringBuffer sOut;
     690           0 :     sOut.append('<').append(OOO_STRING_SVTOOLS_HTML_marquee);
     691             : 
     692             :     // Die Attribute des Objektd holen
     693           0 :     const SfxItemSet& rItemSet = pTextObj->GetMergedItemSet();
     694             : 
     695             :     // BEHAVIOUR
     696           0 :     SdrTextAniKind eAniKind = pTextObj->GetTextAniKind();
     697             :     OSL_ENSURE( SDRTEXTANI_SCROLL==eAniKind ||
     698             :             SDRTEXTANI_ALTERNATE==eAniKind ||
     699             :             SDRTEXTANI_SLIDE==eAniKind,
     700             :             "Text-Draw-Objekt nicht fuer Marquee geeignet" );
     701             : 
     702           0 :     const sal_Char *pStr = 0;
     703           0 :     switch( eAniKind )
     704             :     {
     705           0 :     case SDRTEXTANI_SCROLL:     pStr = OOO_STRING_SVTOOLS_HTML_BEHAV_scroll;        break;
     706           0 :     case SDRTEXTANI_SLIDE:      pStr = OOO_STRING_SVTOOLS_HTML_BEHAV_slide;     break;
     707           0 :     case SDRTEXTANI_ALTERNATE:  pStr = OOO_STRING_SVTOOLS_HTML_BEHAV_alternate; break;
     708             :     default:
     709             :         ;
     710             :     }
     711             : 
     712           0 :     if( pStr )
     713             :     {
     714           0 :         sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_behavior).
     715           0 :             append('=').append(pStr);
     716             :     }
     717             : 
     718             :     // DIRECTION
     719           0 :     pStr = 0;
     720           0 :     SdrTextAniDirection eAniDir = pTextObj->GetTextAniDirection();
     721           0 :     switch( eAniDir )
     722             :     {
     723           0 :     case SDRTEXTANI_LEFT:       pStr = OOO_STRING_SVTOOLS_HTML_AL_left;     break;
     724           0 :     case SDRTEXTANI_RIGHT:      pStr = OOO_STRING_SVTOOLS_HTML_AL_right;        break;
     725             :     default:
     726             :         ;
     727             :     }
     728             : 
     729           0 :     if( pStr )
     730             :     {
     731           0 :         sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_direction).
     732           0 :             append('=').append(pStr);
     733             :     }
     734             : 
     735             :     // LOOP
     736             :     sal_Int32 nCount =
     737           0 :         ((const SdrTextAniCountItem&)rItemSet.Get( SDRATTR_TEXT_ANICOUNT ))
     738           0 :                                              .GetValue();
     739           0 :     if( 0==nCount )
     740           0 :         nCount = SDRTEXTANI_SLIDE==eAniKind ? 1 : -1;
     741           0 :     sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_loop).append('=').
     742           0 :         append(nCount);
     743             : 
     744             :     // SCROLLDELAY
     745             :     sal_uInt16 nDelay =
     746           0 :         ((const SdrTextAniDelayItem&)rItemSet.Get( SDRATTR_TEXT_ANIDELAY ))
     747           0 :                                             .GetValue();
     748           0 :     sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_scrolldelay).
     749           0 :         append('=').append(static_cast<sal_Int32>(nDelay));
     750             : 
     751             :     // SCROLLAMOUNT
     752             :     sal_Int16 nAmount =
     753           0 :         ((const SdrTextAniAmountItem&)rItemSet.Get( SDRATTR_TEXT_ANIAMOUNT ))
     754           0 :                                              .GetValue();
     755           0 :     if( nAmount < 0 )
     756             :     {
     757           0 :         nAmount = -nAmount;
     758             :     }
     759           0 :     else if( nAmount && Application::GetDefaultDevice() )
     760             :     {
     761             :         nAmount = (sal_uInt16)(Application::GetDefaultDevice()
     762             :                             ->LogicToPixel( Size(nAmount,0),
     763           0 :                                             MapMode(MAP_TWIP) ).Width());
     764             :     }
     765           0 :     if( nAmount )
     766             :     {
     767           0 :         sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_scrollamount).
     768           0 :             append('=').append(static_cast<sal_Int32>(nAmount));
     769             :     }
     770             : 
     771           0 :     Size aTwipSz( pTextObj->GetLogicRect().GetSize() );
     772           0 :     if( pTextObj->IsAutoGrowWidth() )
     773           0 :         aTwipSz.Width() = 0;
     774             :     // Die Hoehe ist bei MS eine Mindesthoehe, also geben wir auch die
     775             :     // Mindestheoehe aus, wenn es sie gibt. Da eine Mindesthoehe MINFLY
     776             :     // mit hoher Wahrscheinlichkeit vom Import kommt, wird sie nicht mit
     777             :     // ausgegeben. Falsch machen kann man da nichst, denn jeder Font ist
     778             :     // hoeher.
     779           0 :     if( pTextObj->IsAutoGrowHeight() )
     780             :     {
     781           0 :         aTwipSz.Height() = pTextObj->GetMinTextFrameHeight();
     782           0 :         if( MINFLY==aTwipSz.Height() )
     783           0 :             aTwipSz.Height() = 0;
     784             :     }
     785             : 
     786           0 :     if( (aTwipSz.Width() || aTwipSz.Height()) &&
     787           0 :         Application::GetDefaultDevice() )
     788             :     {
     789             :         Size aPixelSz =
     790             :             Application::GetDefaultDevice()->LogicToPixel( aTwipSz,
     791           0 :                                                 MapMode(MAP_TWIP) );
     792           0 :         if( !aPixelSz.Width() && aTwipSz.Width() )
     793           0 :             aPixelSz.Width() = 1;
     794           0 :         if( !aPixelSz.Height() && aTwipSz.Height() )
     795           0 :             aPixelSz.Height() = 1;
     796             : 
     797           0 :         if( aPixelSz.Width() )
     798             :         {
     799           0 :             sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_width).
     800           0 :                 append('=').append(static_cast<sal_Int32>(aPixelSz.Width()));
     801             :         }
     802             : 
     803           0 :         if( aPixelSz.Height() )
     804             :         {
     805           0 :             sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_height).
     806           0 :                 append('=').append(static_cast<sal_Int32>(aPixelSz.Height()));
     807             :         }
     808             :     }
     809             : 
     810             :     // BGCOLOR
     811             :     XFillStyle eFillStyle =
     812           0 :         ((const XFillStyleItem&)rItemSet.Get(XATTR_FILLSTYLE)).GetValue();
     813           0 :     if( XFILL_SOLID==eFillStyle )
     814             :     {
     815             :         const Color& rFillColor =
     816           0 :             ((const XFillColorItem&)rItemSet.Get(XATTR_FILLCOLOR)).GetColorValue();
     817             : 
     818           0 :         sOut.append(' ').append(OOO_STRING_SVTOOLS_HTML_O_bgcolor).append('=');
     819           0 :         rWrt.Strm() << sOut.makeStringAndClear().getStr();
     820           0 :         HTMLOutFuncs::Out_Color( rWrt.Strm(), rFillColor, rHTMLWrt.eDestEnc );
     821             :     }
     822             : 
     823           0 :     if (sOut.getLength())
     824           0 :         rWrt.Strm() << sOut.makeStringAndClear().getStr();
     825             : 
     826             :     // und nun noch ALIGN, HSPACE und VSPACE
     827           0 :     sal_uInt32 nFrmFlags = HTML_FRMOPTS_MARQUEE;
     828           0 :     if( rHTMLWrt.IsHTMLMode( HTMLMODE_ABS_POS_DRAW ) )
     829           0 :         nFrmFlags |= HTML_FRMOPTS_MARQUEE_CSS1;
     830           0 :     rtl::OString aEndTags = rHTMLWrt.OutFrmFmtOptions( rFmt, aEmptyStr, nFrmFlags );
     831           0 :     if( rHTMLWrt.IsHTMLMode( HTMLMODE_ABS_POS_DRAW ) )
     832           0 :         rHTMLWrt.OutCSS1_FrmFmtOptions( rFmt, nFrmFlags, &rSdrObject );
     833             : 
     834             : 
     835           0 :     rWrt.Strm() << '>';
     836             : 
     837             :     // Was jetzt kommt ist das Gegenstueck zu SdrTextObjectt::SetText()
     838           0 :     Outliner aOutliner(0, OUTLINERMODE_TEXTOBJECT);
     839           0 :     aOutliner.SetUpdateMode( sal_False );
     840           0 :     aOutliner.SetText( *pOutlinerParaObj );
     841             :     String aText( aOutliner.GetText( aOutliner.GetParagraph(0),
     842           0 :                                      aOutliner.GetParagraphCount() ) );
     843           0 :     HTMLOutFuncs::Out_String( rWrt.Strm(), aText,
     844           0 :                                 rHTMLWrt.eDestEnc, &rHTMLWrt.aNonConvertableCharacters );
     845             : 
     846           0 :     HTMLOutFuncs::Out_AsciiTag( rWrt.Strm(), OOO_STRING_SVTOOLS_HTML_marquee, sal_False );
     847             : 
     848           0 :     if( !aEndTags.isEmpty() )
     849           0 :         rWrt.Strm() << aEndTags.getStr();
     850             : 
     851           0 :     return rWrt;
     852             : }
     853             : 
     854             : 
     855             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10