LCOV - code coverage report
Current view: top level - libreoffice/sc/source/filter/excel - xihelper.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 255 432 59.0 %
Date: 2012-12-27 Functions: 26 40 65.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 "xihelper.hxx"
      21             : #include <svl/itemset.hxx>
      22             : #include <editeng/editobj.hxx>
      23             : #include <tools/urlobj.hxx>
      24             : #include "scitems.hxx"
      25             : #include <editeng/eeitem.hxx>
      26             : #include <editeng/flditem.hxx>
      27             : #include "document.hxx"
      28             : #include "cell.hxx"
      29             : #include "rangelst.hxx"
      30             : #include "editutil.hxx"
      31             : #include "attrib.hxx"
      32             : #include "xltracer.hxx"
      33             : #include "xistream.hxx"
      34             : #include "xistyle.hxx"
      35             : 
      36             : #include "excform.hxx"
      37             : 
      38             : // Excel->Calc cell address/range conversion ==================================
      39             : 
      40             : namespace {
      41             : 
      42             : /** Fills the passed Calc address with the passed Excel cell coordinates without checking any limits. */
      43       48399 : inline void lclFillAddress( ScAddress& rScPos, sal_uInt16 nXclCol, sal_uInt32 nXclRow, SCTAB nScTab )
      44             : {
      45       48399 :     rScPos.SetCol( static_cast< SCCOL >( nXclCol ) );
      46       48399 :     rScPos.SetRow( static_cast< SCROW >( nXclRow ) );
      47       48399 :     rScPos.SetTab( nScTab );
      48       48399 : }
      49             : 
      50             : } // namespace
      51             : 
      52             : // ----------------------------------------------------------------------------
      53             : 
      54          20 : XclImpAddressConverter::XclImpAddressConverter( const XclImpRoot& rRoot ) :
      55          20 :     XclAddressConverterBase( rRoot.GetTracer(), rRoot.GetScMaxPos() )
      56             : {
      57          20 : }
      58             : 
      59             : // cell address ---------------------------------------------------------------
      60             : 
      61       54299 : bool XclImpAddressConverter::CheckAddress( const XclAddress& rXclPos, bool bWarn )
      62             : {
      63       54299 :     bool bValidCol = rXclPos.mnCol <= mnMaxCol;
      64       54299 :     bool bValidRow = rXclPos.mnRow <= mnMaxRow;
      65       54299 :     bool bValid = bValidCol && bValidRow;
      66       54299 :     if( !bValid && bWarn )
      67             :     {
      68        5899 :         mbColTrunc |= !bValidCol;
      69        5899 :         mbRowTrunc |= !bValidRow;
      70             :         mrTracer.TraceInvalidAddress( ScAddress(
      71        5899 :             static_cast< SCCOL >( rXclPos.mnCol ), static_cast< SCROW >( rXclPos.mnRow ), 0 ), maMaxPos );
      72             :     }
      73       54299 :     return bValid;
      74             : }
      75             : 
      76       53020 : bool XclImpAddressConverter::ConvertAddress( ScAddress& rScPos,
      77             :         const XclAddress& rXclPos, SCTAB nScTab, bool bWarn )
      78             : {
      79       53020 :     bool bValid = CheckAddress( rXclPos, bWarn );
      80       53020 :     if( bValid )
      81       47121 :         lclFillAddress( rScPos, rXclPos.mnCol, rXclPos.mnRow, nScTab );
      82       53020 :     return bValid;
      83             : }
      84             : 
      85         221 : ScAddress XclImpAddressConverter::CreateValidAddress(
      86             :         const XclAddress& rXclPos, SCTAB nScTab, bool bWarn )
      87             : {
      88         221 :     ScAddress aScPos( ScAddress::UNINITIALIZED );
      89         221 :     if( !ConvertAddress( aScPos, rXclPos, nScTab, bWarn ) )
      90             :     {
      91           0 :         aScPos.SetCol( static_cast< SCCOL >( ::std::min( rXclPos.mnCol, mnMaxCol ) ) );
      92           0 :         aScPos.SetRow( static_cast< SCROW >( ::std::min( rXclPos.mnRow, mnMaxRow ) ) );
      93           0 :         aScPos.SetTab( limit_cast< SCTAB >( nScTab, 0, maMaxPos.Tab() ) );
      94             :     }
      95         221 :     return aScPos;
      96             : }
      97             : 
      98             : // cell range -----------------------------------------------------------------
      99             : 
     100         640 : bool XclImpAddressConverter::ConvertRange( ScRange& rScRange,
     101             :         const XclRange& rXclRange, SCTAB nScTab1, SCTAB nScTab2, bool bWarn )
     102             : {
     103             :     // check start position
     104         640 :     bool bValidStart = CheckAddress( rXclRange.maFirst, bWarn );
     105         640 :     if( bValidStart )
     106             :     {
     107         639 :         lclFillAddress( rScRange.aStart, rXclRange.maFirst.mnCol, rXclRange.maFirst.mnRow, nScTab1 );
     108             : 
     109             :         // check & correct end position
     110         639 :         sal_uInt16 nXclCol2 = rXclRange.maLast.mnCol;
     111         639 :         sal_uInt32 nXclRow2 = rXclRange.maLast.mnRow;
     112         639 :         if( !CheckAddress( rXclRange.maLast, bWarn ) )
     113             :         {
     114           0 :             nXclCol2 = ::std::min( nXclCol2, mnMaxCol );
     115           0 :             nXclRow2 = ::std::min( nXclRow2, mnMaxRow );
     116             :         }
     117         639 :         lclFillAddress( rScRange.aEnd, nXclCol2, nXclRow2, nScTab2 );
     118             :     }
     119         640 :     return bValidStart;
     120             : }
     121             : 
     122             : // cell range list ------------------------------------------------------------
     123             : 
     124          75 : void XclImpAddressConverter::ConvertRangeList( ScRangeList& rScRanges,
     125             :         const XclRangeList& rXclRanges, SCTAB nScTab, bool bWarn )
     126             : {
     127          75 :     rScRanges.RemoveAll();
     128         150 :     for( XclRangeList::const_iterator aIt = rXclRanges.begin(), aEnd = rXclRanges.end(); aIt != aEnd; ++aIt )
     129             :     {
     130          75 :         ScRange aScRange( ScAddress::UNINITIALIZED );
     131          75 :         if( ConvertRange( aScRange, *aIt, nScTab, nScTab, bWarn ) )
     132          75 :             rScRanges.Append( aScRange );
     133             :     }
     134          75 : }
     135             : 
     136             : // String->EditEngine conversion ==============================================
     137             : 
     138             : namespace {
     139             : 
     140       10481 : EditTextObject* lclCreateTextObject( const XclImpRoot& rRoot,
     141             :         const XclImpString& rString, XclFontItemType eType, sal_uInt16 nXFIndex )
     142             : {
     143       10481 :     EditTextObject* pTextObj = 0;
     144             : 
     145       10481 :     const XclImpXFBuffer& rXFBuffer = rRoot.GetXFBuffer();
     146       10481 :     const XclImpFont* pFirstFont = rXFBuffer.GetFont( nXFIndex );
     147       10481 :     bool bFirstEscaped = pFirstFont && pFirstFont->HasEscapement();
     148             : 
     149       10481 :     if( rString.IsRich() || bFirstEscaped )
     150             :     {
     151          48 :         const XclImpFontBuffer& rFontBuffer = rRoot.GetFontBuffer();
     152          48 :         const XclFormatRunVec& rFormats = rString.GetFormats();
     153             : 
     154             :         ScEditEngineDefaulter& rEE = (eType == EXC_FONTITEM_NOTE) ?
     155          48 :             static_cast< ScEditEngineDefaulter& >( rRoot.GetDoc().GetNoteEngine() ) : rRoot.GetEditEngine();
     156          48 :         rEE.SetText( rString.GetText() );
     157             : 
     158          48 :         SfxItemSet aItemSet( rEE.GetEmptyItemSet() );
     159          48 :         if( bFirstEscaped )
     160           0 :             rFontBuffer.FillToItemSet( aItemSet, eType, rXFBuffer.GetFontIndex( nXFIndex ) );
     161          48 :         ESelection aSelection;
     162             : 
     163          48 :         XclFormatRun aNextRun;
     164          48 :         XclFormatRunVec::const_iterator aIt = rFormats.begin();
     165          48 :         XclFormatRunVec::const_iterator aEnd = rFormats.end();
     166             : 
     167          48 :         if( aIt != aEnd )
     168          48 :             aNextRun = *aIt++;
     169             :         else
     170           0 :             aNextRun.mnChar = 0xFFFF;
     171             : 
     172          48 :         xub_StrLen nLen = rString.GetText().Len();
     173        2722 :         for( sal_uInt16 nChar = 0; nChar < nLen; ++nChar )
     174             :         {
     175             :             // reached new different formatted text portion
     176        2674 :             if( nChar >= aNextRun.mnChar )
     177             :             {
     178             :                 // send items to edit engine
     179          87 :                 rEE.QuickSetAttribs( aItemSet, aSelection );
     180             : 
     181             :                 // start new item set
     182          87 :                 aItemSet.ClearItem();
     183          87 :                 rFontBuffer.FillToItemSet( aItemSet, eType, aNextRun.mnFontIdx );
     184             : 
     185             :                 // read new formatting information
     186          87 :                 if( aIt != aEnd )
     187          50 :                     aNextRun = *aIt++;
     188             :                 else
     189          37 :                     aNextRun.mnChar = 0xFFFF;
     190             : 
     191             :                 // reset selection start to current position
     192          87 :                 aSelection.nStartPara = aSelection.nEndPara;
     193          87 :                 aSelection.nStartPos = aSelection.nEndPos;
     194             :             }
     195             : 
     196             :             // set end of selection to current position
     197        2674 :             if( rString.GetText().GetChar( nChar ) == '\n' )
     198             :             {
     199           1 :                 ++aSelection.nEndPara;
     200           1 :                 aSelection.nEndPos = 0;
     201             :             }
     202             :             else
     203        2673 :                 ++aSelection.nEndPos;
     204             :         }
     205             : 
     206             :         // send items of last text portion to edit engine
     207          48 :         rEE.QuickSetAttribs( aItemSet, aSelection );
     208             : 
     209          48 :         pTextObj = rEE.CreateTextObject();
     210             :     }
     211             : 
     212       10481 :     return pTextObj;
     213             : }
     214             : 
     215             : } // namespace
     216             : 
     217          11 : EditTextObject* XclImpStringHelper::CreateTextObject(
     218             :         const XclImpRoot& rRoot, const XclImpString& rString )
     219             : {
     220          11 :     return lclCreateTextObject( rRoot, rString, EXC_FONTITEM_EDITENG, 0 );
     221             : }
     222             : 
     223       10470 : ScBaseCell* XclImpStringHelper::CreateCell(
     224             :         const XclImpRoot& rRoot, const XclImpString& rString, sal_uInt16 nXFIndex )
     225             : {
     226       10470 :     ScBaseCell* pCell = 0;
     227             : 
     228       10470 :     if( rString.GetText().Len() )
     229             :     {
     230       10470 :         ::std::auto_ptr< EditTextObject > pTextObj( lclCreateTextObject( rRoot, rString, EXC_FONTITEM_EDITENG, nXFIndex ) );
     231       10470 :         ScDocument& rDoc = rRoot.GetDoc();
     232             : 
     233       10470 :         if( pTextObj.get() )
     234             :             // ScEditCell creates own copy of text object
     235          37 :             pCell = new ScEditCell( pTextObj.get(), &rDoc, rRoot.GetEditEngine().GetEditTextObjectPool() );
     236             :         else
     237       10433 :             pCell = ScBaseCell::CreateTextCell( rString.GetText(), &rDoc );
     238             :     }
     239             : 
     240       10470 :     return pCell;
     241             : }
     242             : 
     243             : // Header/footer conversion ===================================================
     244             : 
     245          96 : XclImpHFConverter::XclImpHFPortionInfo::XclImpHFPortionInfo() :
     246             :     mnHeight( 0 ),
     247          96 :     mnMaxLineHt( 0 )
     248             : {
     249          96 :     maSel.nStartPara = maSel.nEndPara = 0;
     250          96 :     maSel.nStartPos = maSel.nEndPos = 0;
     251          96 : }
     252             : 
     253             : // ----------------------------------------------------------------------------
     254             : 
     255          75 : XclImpHFConverter::XclImpHFConverter( const XclImpRoot& rRoot ) :
     256             :     XclImpRoot( rRoot ),
     257          75 :     mrEE( rRoot.GetHFEditEngine() ),
     258          75 :     mxFontData( new XclFontData ),
     259         225 :     meCurrObj( EXC_HF_CENTER )
     260             : {
     261          75 : }
     262             : 
     263          75 : XclImpHFConverter::~XclImpHFConverter()
     264             : {
     265          75 : }
     266             : 
     267          32 : void XclImpHFConverter::ParseString( const String& rHFString )
     268             : {
     269             :     // edit engine objects
     270          32 :     mrEE.SetText( EMPTY_STRING );
     271          32 :     maInfos.clear();
     272          32 :     maInfos.resize( EXC_HF_PORTION_COUNT );
     273          32 :     meCurrObj = EXC_HF_CENTER;
     274             : 
     275             :     // parser temporaries
     276          32 :     maCurrText.Erase();
     277          32 :     String aReadFont;           // current font name
     278          32 :     String aReadStyle;          // current font style
     279          32 :     sal_uInt16 nReadHeight = 0; // current font height
     280          32 :     ResetFontData();
     281             : 
     282             :     /** State of the parser. */
     283             :     enum XclHFParserState
     284             :     {
     285             :         xlPSText,           /// Read text, search for functions.
     286             :         xlPSFunc,           /// Read function (token following a '&').
     287             :         xlPSFont,           /// Read font name ('&' is followed by '"', reads until next '"' or ',').
     288             :         xlPSFontStyle,      /// Read font style name (font part after ',', reads until next '"').
     289             :         xlPSHeight          /// Read font height ('&' is followed by num. digits, reads until non-digit).
     290          32 :     } eState = xlPSText;
     291             : 
     292          32 :     const sal_Unicode* pChar = rHFString.GetBuffer();
     293          32 :     const sal_Unicode* pNull = pChar + rHFString.Len(); // pointer to teminating null char
     294         377 :     while( *pChar )
     295             :     {
     296         313 :         switch( eState )
     297             :         {
     298             : 
     299             : // --- read text character ---
     300             : 
     301             :             case xlPSText:
     302             :             {
     303         195 :                 switch( *pChar )
     304             :                 {
     305             :                     case '&':           // new command
     306          66 :                         InsertText();
     307          66 :                         eState = xlPSFunc;
     308          66 :                     break;
     309             :                     case '\n':          // line break
     310           0 :                         InsertText();
     311           0 :                         InsertLineBreak();
     312           0 :                     break;
     313             :                     default:
     314         129 :                         maCurrText += *pChar;
     315             :                 }
     316             :             }
     317         195 :             break;
     318             : 
     319             : // --- read control sequence ---
     320             : 
     321             :             case xlPSFunc:
     322             :             {
     323          66 :                 eState = xlPSText;
     324          66 :                 switch( *pChar )
     325             :                 {
     326           0 :                     case '&':   maCurrText += '&';  break;  // the '&' character
     327             : 
     328           2 :                     case 'L':   SetNewPortion( EXC_HF_LEFT );   break;  // Left portion
     329          28 :                     case 'C':   SetNewPortion( EXC_HF_CENTER ); break;  // Center portion
     330           1 :                     case 'R':   SetNewPortion( EXC_HF_RIGHT );  break;  // Right portion
     331             : 
     332          15 :                     case 'P':   InsertField( SvxFieldItem( SvxPageField(), EE_FEATURE_FIELD ) );      break;  // page
     333           0 :                     case 'N':   InsertField( SvxFieldItem( SvxPagesField(), EE_FEATURE_FIELD ) );     break;  // page count
     334           1 :                     case 'D':   InsertField( SvxFieldItem( SvxDateField(), EE_FEATURE_FIELD ) );      break;  // date
     335           0 :                     case 'T':   InsertField( SvxFieldItem( SvxTimeField(), EE_FEATURE_FIELD ) );      break;  // time
     336          14 :                     case 'A':   InsertField( SvxFieldItem( SvxTableField(), EE_FEATURE_FIELD ) );     break;  // table name
     337             : 
     338             :                     case 'Z':           // file path
     339           0 :                         InsertField( SvxFieldItem( SvxExtFileField(), EE_FEATURE_FIELD ) );   // convert to full name
     340           0 :                         if( (pNull - pChar >= 2) && (*(pChar + 1) == '&') && (*(pChar + 2) == 'F') )
     341             :                         {
     342             :                             // &Z&F found - ignore the &F part
     343           0 :                             pChar += 2;
     344             :                         }
     345           0 :                     break;
     346             :                     case 'F':           // file name
     347           1 :                         InsertField( SvxFieldItem( SvxExtFileField( EMPTY_STRING, SVXFILETYPE_VAR, SVXFILEFORMAT_NAME_EXT ), EE_FEATURE_FIELD ) );
     348           1 :                     break;
     349             : 
     350             :                     case 'U':           // underline
     351           0 :                         SetAttribs();
     352           0 :                         mxFontData->mnUnderline = (mxFontData->mnUnderline == EXC_FONTUNDERL_SINGLE) ?
     353           0 :                             EXC_FONTUNDERL_NONE : EXC_FONTUNDERL_SINGLE;
     354           0 :                     break;
     355             :                     case 'E':           // double underline
     356           0 :                         SetAttribs();
     357           0 :                         mxFontData->mnUnderline = (mxFontData->mnUnderline == EXC_FONTUNDERL_DOUBLE) ?
     358           0 :                             EXC_FONTUNDERL_NONE : EXC_FONTUNDERL_DOUBLE;
     359           0 :                     break;
     360             :                     case 'S':           // strikeout
     361           0 :                         SetAttribs();
     362           0 :                         mxFontData->mbStrikeout = !mxFontData->mbStrikeout;
     363           0 :                     break;
     364             :                     case 'X':           // superscript
     365           0 :                         SetAttribs();
     366           0 :                         mxFontData->mnEscapem = (mxFontData->mnEscapem == EXC_FONTESC_SUPER) ?
     367           0 :                             EXC_FONTESC_NONE : EXC_FONTESC_SUPER;
     368           0 :                     break;
     369             :                     case 'Y':           // subsrcipt
     370           0 :                         SetAttribs();
     371           0 :                         mxFontData->mnEscapem = (mxFontData->mnEscapem == EXC_FONTESC_SUB) ?
     372           0 :                             EXC_FONTESC_NONE : EXC_FONTESC_SUB;
     373           0 :                     break;
     374             : 
     375             :                     case '\"':          // font name
     376           2 :                         aReadFont.Erase();
     377           2 :                         aReadStyle.Erase();
     378           2 :                         eState = xlPSFont;
     379           2 :                     break;
     380             :                     default:
     381           2 :                         if( ('0' <= *pChar) && (*pChar <= '9') )    // font size
     382             :                         {
     383           2 :                             nReadHeight = *pChar - '0';
     384           2 :                             eState = xlPSHeight;
     385             :                         }
     386             :                 }
     387             :             }
     388          66 :             break;
     389             : 
     390             : // --- read font name ---
     391             : 
     392             :             case xlPSFont:
     393             :             {
     394          32 :                 switch( *pChar )
     395             :                 {
     396             :                     case '\"':
     397           0 :                         --pChar;
     398             :                         // run through
     399             :                     case ',':
     400           2 :                         eState = xlPSFontStyle;
     401           2 :                     break;
     402             :                     default:
     403          30 :                         aReadFont += *pChar;
     404             :                 }
     405             :             }
     406          32 :             break;
     407             : 
     408             : // --- read font style ---
     409             : 
     410             :             case xlPSFontStyle:
     411             :             {
     412          16 :                 switch( *pChar )
     413             :                 {
     414             :                     case '\"':
     415           2 :                         SetAttribs();
     416           2 :                         if( aReadFont.Len() )
     417           2 :                             mxFontData->maName = aReadFont;
     418           2 :                         mxFontData->maStyle = aReadStyle;
     419           2 :                         eState = xlPSText;
     420           2 :                     break;
     421             :                     default:
     422          14 :                         aReadStyle += *pChar;
     423             :                 }
     424             :             }
     425          16 :             break;
     426             : 
     427             : // --- read font height ---
     428             : 
     429             :             case xlPSHeight:
     430             :             {
     431           4 :                 if( ('0' <= *pChar) && (*pChar <= '9') )
     432             :                 {
     433           4 :                     if( nReadHeight != 0xFFFF )
     434             :                     {
     435           2 :                         nReadHeight *= 10;
     436           2 :                         nReadHeight += (*pChar - '0');
     437           2 :                         if( nReadHeight > 1600 )    // max 1600pt = 32000twips
     438           0 :                             nReadHeight = 0xFFFF;
     439             :                     }
     440             :                 }
     441             :                 else
     442             :                 {
     443           2 :                     if( (nReadHeight != 0) && (nReadHeight != 0xFFFF) )
     444             :                     {
     445           2 :                         SetAttribs();
     446           2 :                         mxFontData->mnHeight = nReadHeight * 20;
     447             :                     }
     448           2 :                     --pChar;
     449           2 :                     eState = xlPSText;
     450             :                 }
     451             :             }
     452           4 :             break;
     453             :         }
     454         313 :         ++pChar;
     455             :     }
     456             : 
     457             :     // finalize
     458          32 :     CreateCurrObject();
     459          32 :     maInfos[ EXC_HF_LEFT   ].mnHeight += GetMaxLineHeight( EXC_HF_LEFT );
     460          32 :     maInfos[ EXC_HF_CENTER ].mnHeight += GetMaxLineHeight( EXC_HF_CENTER );
     461          32 :     maInfos[ EXC_HF_RIGHT  ].mnHeight += GetMaxLineHeight( EXC_HF_RIGHT );
     462          32 : }
     463             : 
     464          64 : void XclImpHFConverter::FillToItemSet( SfxItemSet& rItemSet, sal_uInt16 nWhichId ) const
     465             : {
     466          64 :     ScPageHFItem aHFItem( nWhichId );
     467          64 :     if( maInfos[ EXC_HF_LEFT ].mxObj.get() )
     468           4 :         aHFItem.SetLeftArea( *maInfos[ EXC_HF_LEFT ].mxObj );
     469          64 :     if( maInfos[ EXC_HF_CENTER ].mxObj.get() )
     470          64 :         aHFItem.SetCenterArea( *maInfos[ EXC_HF_CENTER ].mxObj );
     471          64 :     if( maInfos[ EXC_HF_RIGHT ].mxObj.get() )
     472           2 :         aHFItem.SetRightArea( *maInfos[ EXC_HF_RIGHT ].mxObj );
     473          64 :     rItemSet.Put( aHFItem );
     474          64 : }
     475             : 
     476          32 : sal_Int32 XclImpHFConverter::GetTotalHeight() const
     477             : {
     478          32 :     return ::std::max( maInfos[ EXC_HF_LEFT ].mnHeight,
     479          64 :         ::std::max( maInfos[ EXC_HF_CENTER ].mnHeight, maInfos[ EXC_HF_RIGHT ].mnHeight ) );
     480             : }
     481             : 
     482             : // private --------------------------------------------------------------------
     483             : 
     484          96 : sal_uInt16 XclImpHFConverter::GetMaxLineHeight( XclImpHFPortion ePortion ) const
     485             : {
     486          96 :     sal_uInt16 nMaxHt = maInfos[ ePortion ].mnMaxLineHt;
     487          96 :     return (nMaxHt == 0) ? mxFontData->mnHeight : nMaxHt;
     488             : }
     489             : 
     490           0 : sal_uInt16 XclImpHFConverter::GetCurrMaxLineHeight() const
     491             : {
     492           0 :     return GetMaxLineHeight( meCurrObj );
     493             : }
     494             : 
     495          47 : void XclImpHFConverter::UpdateMaxLineHeight( XclImpHFPortion ePortion )
     496             : {
     497          47 :     sal_uInt16& rnMaxHt = maInfos[ ePortion ].mnMaxLineHt;
     498          47 :     rnMaxHt = ::std::max( rnMaxHt, mxFontData->mnHeight );
     499          47 : }
     500             : 
     501          47 : void XclImpHFConverter::UpdateCurrMaxLineHeight()
     502             : {
     503          47 :     UpdateMaxLineHeight( meCurrObj );
     504          47 : }
     505             : 
     506          39 : void XclImpHFConverter::SetAttribs()
     507             : {
     508          39 :     ESelection& rSel = GetCurrSel();
     509          39 :     if( (rSel.nStartPara != rSel.nEndPara) || (rSel.nStartPos != rSel.nEndPos) )
     510             :     {
     511          33 :         SfxItemSet aItemSet( mrEE.GetEmptyItemSet() );
     512          33 :         XclImpFont aFont( GetRoot(), *mxFontData );
     513          33 :         aFont.FillToItemSet( aItemSet, EXC_FONTITEM_HF );
     514          33 :         mrEE.QuickSetAttribs( aItemSet, rSel );
     515          33 :         rSel.nStartPara = rSel.nEndPara;
     516          33 :         rSel.nStartPos = rSel.nEndPos;
     517             :     }
     518          39 : }
     519             : 
     520          35 : void XclImpHFConverter::ResetFontData()
     521             : {
     522          35 :     if( const XclImpFont* pFirstFont = GetFontBuffer().GetFont( EXC_FONT_APP ) )
     523          35 :         *mxFontData = pFirstFont->GetFontData();
     524             :     else
     525             :     {
     526           0 :         mxFontData->Clear();
     527           0 :         mxFontData->mnHeight = 200;
     528             :     }
     529          35 : }
     530             : 
     531         101 : void XclImpHFConverter::InsertText()
     532             : {
     533         101 :     if( maCurrText.Len() )
     534             :     {
     535          16 :         ESelection& rSel = GetCurrSel();
     536          16 :         mrEE.QuickInsertText( maCurrText, ESelection( rSel.nEndPara, rSel.nEndPos, rSel.nEndPara, rSel.nEndPos ) );
     537          16 :         rSel.nEndPos = rSel.nEndPos + maCurrText.Len();
     538          16 :         maCurrText.Erase();
     539          16 :         UpdateCurrMaxLineHeight();
     540             :     }
     541         101 : }
     542             : 
     543          31 : void XclImpHFConverter::InsertField( const SvxFieldItem& rFieldItem )
     544             : {
     545          31 :     ESelection& rSel = GetCurrSel();
     546          31 :     mrEE.QuickInsertField( rFieldItem, ESelection( rSel.nEndPara, rSel.nEndPos, rSel.nEndPara, rSel.nEndPos ) );
     547          31 :     ++rSel.nEndPos;
     548          31 :     UpdateCurrMaxLineHeight();
     549          31 : }
     550             : 
     551           0 : void XclImpHFConverter::InsertLineBreak()
     552             : {
     553           0 :     ESelection& rSel = GetCurrSel();
     554           0 :     mrEE.QuickInsertText( rtl::OUString('\n'), ESelection( rSel.nEndPara, rSel.nEndPos, rSel.nEndPara, rSel.nEndPos ) );
     555           0 :     ++rSel.nEndPara;
     556           0 :     rSel.nEndPos = 0;
     557           0 :     GetCurrInfo().mnHeight += GetCurrMaxLineHeight();
     558           0 :     GetCurrInfo().mnMaxLineHt = 0;
     559           0 : }
     560             : 
     561          35 : void XclImpHFConverter::CreateCurrObject()
     562             : {
     563          35 :     InsertText();
     564          35 :     SetAttribs();
     565          35 :     GetCurrObj().reset( mrEE.CreateTextObject() );
     566          35 : }
     567             : 
     568          31 : void XclImpHFConverter::SetNewPortion( XclImpHFPortion eNew )
     569             : {
     570          31 :     if( eNew != meCurrObj )
     571             :     {
     572           3 :         CreateCurrObject();
     573           3 :         meCurrObj = eNew;
     574           3 :         if( GetCurrObj().get() )
     575           0 :             mrEE.SetText( *GetCurrObj() );
     576             :         else
     577           3 :             mrEE.SetText( EMPTY_STRING );
     578           3 :         ResetFontData();
     579             :     }
     580          31 : }
     581             : 
     582             : // URL conversion =============================================================
     583             : 
     584             : namespace {
     585             : 
     586           0 : void lclAppendUrlChar( String& rUrl, sal_Unicode cChar )
     587             : {
     588             :     // encode special characters
     589           0 :     switch( cChar )
     590             :     {
     591           0 :         case '#':   rUrl.AppendAscii( "%23" );  break;
     592           0 :         case '%':   rUrl.AppendAscii( "%25" );  break;
     593           0 :         default:    rUrl.Append( cChar );
     594             :     }
     595           0 : }
     596             : 
     597             : } // namespace
     598             : 
     599           1 : void XclImpUrlHelper::DecodeUrl(
     600             :         String& rUrl, String& rTabName, bool& rbSameWb,
     601             :         const XclImpRoot& rRoot, const String& rEncodedUrl )
     602             : {
     603             :     enum
     604             :     {
     605             :         xlUrlInit,              /// Initial state, read string mode character.
     606             :         xlUrlPath,              /// Read URL path.
     607             :         xlUrlFileName,          /// Read file name.
     608             :         xlUrlSheetName,         /// Read sheet name.
     609             :         xlUrlRaw                /// Raw mode. No control characters will occur.
     610           1 :     } eState = xlUrlInit;
     611             : 
     612           1 :     bool bEncoded = true;
     613           1 :     rbSameWb = false;
     614             : 
     615           1 :     sal_Unicode cCurrDrive = 0;
     616           1 :     String aDosBase( INetURLObject( rRoot.GetBasePath() ).getFSysPath( INetURLObject::FSYS_DOS ) );
     617           1 :     if( (aDosBase.Len() > 2) && aDosBase.EqualsAscii( ":\\", 1, 2 ) )
     618           0 :         cCurrDrive = aDosBase.GetChar( 0 );
     619             : 
     620           1 :     const sal_Unicode* pChar = rEncodedUrl.GetBuffer();
     621           9 :     while( *pChar )
     622             :     {
     623           7 :         switch( eState )
     624             :         {
     625             : 
     626             : // --- first character ---
     627             : 
     628             :             case xlUrlInit:
     629             :             {
     630           1 :                 switch( *pChar )
     631             :                 {
     632             :                     case EXC_URLSTART_ENCODED:
     633           0 :                         eState = xlUrlPath;
     634           0 :                     break;
     635             :                     case EXC_URLSTART_SELF:
     636             :                     case EXC_URLSTART_SELFENCODED:
     637           1 :                         rbSameWb = true;
     638           1 :                         eState = xlUrlSheetName;
     639           1 :                     break;
     640             :                     case '[':
     641           0 :                         bEncoded = false;
     642           0 :                         eState = xlUrlFileName;
     643           0 :                     break;
     644             :                     default:
     645           0 :                         bEncoded = false;
     646           0 :                         lclAppendUrlChar( rUrl, *pChar );
     647           0 :                         eState = xlUrlPath;
     648             :                 }
     649             :             }
     650           1 :             break;
     651             : 
     652             : // --- URL path ---
     653             : 
     654             :             case xlUrlPath:
     655             :             {
     656           0 :                 switch( *pChar )
     657             :                 {
     658             :                     case EXC_URL_DOSDRIVE:
     659             :                     {
     660           0 :                         if( *(pChar + 1) )
     661             :                         {
     662           0 :                             ++pChar;
     663           0 :                             if( *pChar == '@' )
     664           0 :                                 rUrl.AppendAscii( "\\\\" );
     665             :                             else
     666             :                             {
     667           0 :                                 lclAppendUrlChar( rUrl, *pChar );
     668           0 :                                 rUrl.AppendAscii( ":\\" );
     669             :                             }
     670             :                         }
     671             :                         else
     672           0 :                             rUrl.AppendAscii( "<NULL-DRIVE!>" );
     673             :                     }
     674           0 :                     break;
     675             :                     case EXC_URL_DRIVEROOT:
     676           0 :                         if( cCurrDrive )
     677             :                         {
     678           0 :                             lclAppendUrlChar( rUrl, cCurrDrive );
     679           0 :                             rUrl.Append( ':' );
     680             :                         }
     681             :                         // run through
     682             :                     case EXC_URL_SUBDIR:
     683           0 :                         if( bEncoded )
     684           0 :                             rUrl.Append( '\\' );
     685             :                         else    // control character in raw name -> DDE link
     686             :                         {
     687           0 :                             rUrl.Append( EXC_DDE_DELIM );
     688           0 :                             eState = xlUrlRaw;
     689             :                         }
     690           0 :                     break;
     691             :                     case EXC_URL_PARENTDIR:
     692           0 :                         rUrl.AppendAscii( "..\\" );
     693           0 :                     break;
     694             :                     case EXC_URL_RAW:
     695             :                     {
     696           0 :                         if( *(pChar + 1) )
     697             :                         {
     698           0 :                             xub_StrLen nLen = *++pChar;
     699           0 :                             for( xub_StrLen nChar = 0; (nChar < nLen) && *(pChar + 1); ++nChar )
     700           0 :                                 lclAppendUrlChar( rUrl, *++pChar );
     701             : //                            rUrl.Append( ':' );
     702             :                         }
     703             :                     }
     704           0 :                     break;
     705             :                     case '[':
     706           0 :                         eState = xlUrlFileName;
     707           0 :                     break;
     708             :                     default:
     709           0 :                         lclAppendUrlChar( rUrl, *pChar );
     710             :                 }
     711             :             }
     712           0 :             break;
     713             : 
     714             : // --- file name ---
     715             : 
     716             :             case xlUrlFileName:
     717             :             {
     718           0 :                 switch( *pChar )
     719             :                 {
     720           0 :                     case ']':   eState = xlUrlSheetName;    break;
     721           0 :                     default:    lclAppendUrlChar( rUrl, *pChar );
     722             :                 }
     723             :             }
     724           0 :             break;
     725             : 
     726             : // --- sheet name ---
     727             : 
     728             :             case xlUrlSheetName:
     729           6 :                 rTabName.Append( *pChar );
     730           6 :             break;
     731             : 
     732             : // --- raw read mode ---
     733             : 
     734             :             case xlUrlRaw:
     735           0 :                 lclAppendUrlChar( rUrl, *pChar );
     736           0 :             break;
     737             :         }
     738             : 
     739           7 :         ++pChar;
     740           1 :     }
     741           1 : }
     742             : 
     743           0 : void XclImpUrlHelper::DecodeUrl(
     744             :         String& rUrl, bool& rbSameWb, const XclImpRoot& rRoot, const String& rEncodedUrl )
     745             : {
     746           0 :     String aTabName;
     747           0 :     DecodeUrl( rUrl, aTabName, rbSameWb, rRoot, rEncodedUrl );
     748           0 :     OSL_ENSURE( !aTabName.Len(), "XclImpUrlHelper::DecodeUrl - sheet name ignored" );
     749           0 : }
     750             : 
     751           0 : void XclImpUrlHelper::DecodeUrl(
     752             :     ::rtl::OUString& rUrl, bool& rbSameWb, const XclImpRoot& rRoot, const ::rtl::OUString& rEncodedUrl )
     753             : {
     754           0 :     String aTabName;
     755           0 :     String aUrl;
     756           0 :     DecodeUrl( aUrl, aTabName, rbSameWb, rRoot, rEncodedUrl );
     757           0 :     rUrl = aUrl;
     758           0 :     OSL_ENSURE( !aTabName.Len(), "XclImpUrlHelper::DecodeUrl - sheet name ignored" );
     759           0 : }
     760             : 
     761           0 : bool XclImpUrlHelper::DecodeLink( String& rApplic, String& rTopic, const String rEncUrl )
     762             : {
     763           0 :     xub_StrLen nPos = rEncUrl.Search( EXC_DDE_DELIM );
     764           0 :     if( (nPos != STRING_NOTFOUND) && (0 < nPos) && (nPos + 1 < rEncUrl.Len()) )
     765             :     {
     766           0 :         rApplic = rEncUrl.Copy( 0, nPos );
     767           0 :         rTopic = rEncUrl.Copy( nPos + 1 );
     768           0 :         return true;
     769             :     }
     770           0 :     return false;
     771             : }
     772             : 
     773             : // Cached Values ==============================================================
     774             : 
     775           0 : XclImpCachedValue::XclImpCachedValue( XclImpStream& rStrm ) :
     776             :     mfValue( 0.0 ),
     777           0 :     mnBoolErr( 0 )
     778             : {
     779           0 :     rStrm >> mnType;
     780           0 :     switch( mnType )
     781             :     {
     782             :         case EXC_CACHEDVAL_EMPTY:
     783           0 :             rStrm.Ignore( 8 );
     784           0 :         break;
     785             :         case EXC_CACHEDVAL_DOUBLE:
     786           0 :             rStrm >> mfValue;
     787           0 :         break;
     788             :         case EXC_CACHEDVAL_STRING:
     789           0 :             mxStr.reset( new String( rStrm.ReadUniString() ) );
     790           0 :         break;
     791             :         case EXC_CACHEDVAL_BOOL:
     792             :         case EXC_CACHEDVAL_ERROR:
     793             :         {
     794             :             double fVal;
     795           0 :             rStrm >> mnBoolErr;
     796           0 :             rStrm.Ignore( 7 );
     797             : 
     798           0 :             const ScTokenArray* pScTokArr = rStrm.GetRoot().GetOldFmlaConverter().GetBoolErr(
     799           0 :                 XclTools::ErrorToEnum( fVal, mnType == EXC_CACHEDVAL_ERROR, mnBoolErr ) );
     800           0 :             if( pScTokArr )
     801           0 :                 mxTokArr.reset( pScTokArr->Clone() );
     802             :         }
     803           0 :         break;
     804             :         default:
     805             :             OSL_FAIL( "XclImpCachedValue::XclImpCachedValue - unknown data type" );
     806             :     }
     807           0 : }
     808             : 
     809           0 : XclImpCachedValue::~XclImpCachedValue()
     810             : {
     811           0 : }
     812             : 
     813           0 : sal_uInt16 XclImpCachedValue::GetScError() const
     814             : {
     815           0 :     return (mnType == EXC_CACHEDVAL_ERROR) ? XclTools::GetScErrorCode( mnBoolErr ) : 0;
     816             : }
     817             : 
     818             : // Matrix Cached Values ==============================================================
     819             : 
     820           0 : XclImpCachedMatrix::XclImpCachedMatrix( XclImpStream& rStrm ) :
     821             :     mnScCols( 0 ),
     822           0 :     mnScRows( 0 )
     823             : {
     824           0 :     mnScCols = rStrm.ReaduInt8();
     825           0 :     mnScRows = rStrm.ReaduInt16();
     826             : 
     827           0 :     if( rStrm.GetRoot().GetBiff() <= EXC_BIFF5 )
     828             :     {
     829             :         // in BIFF2-BIFF7: 256 columns represented by 0 columns
     830           0 :         if( mnScCols == 0 )
     831           0 :             mnScCols = 256;
     832             :     }
     833             :     else
     834             :     {
     835             :         // in BIFF8: columns and rows decreaed by 1
     836           0 :         ++mnScCols;
     837           0 :         ++mnScRows;
     838             :     }
     839             : 
     840           0 :     for( SCSIZE nScRow = 0; nScRow < mnScRows; ++nScRow )
     841           0 :         for( SCSIZE nScCol = 0; nScCol < mnScCols; ++nScCol )
     842           0 :             maValueList.push_back( new XclImpCachedValue( rStrm ) );
     843           0 : }
     844             : 
     845           0 : XclImpCachedMatrix::~XclImpCachedMatrix()
     846             : {
     847           0 : }
     848             : 
     849           0 : ScMatrixRef XclImpCachedMatrix::CreateScMatrix() const
     850             : {
     851           0 :     ScMatrixRef xScMatrix;
     852             :     OSL_ENSURE( mnScCols * mnScRows == maValueList.size(), "XclImpCachedMatrix::CreateScMatrix - element count mismatch" );
     853           0 :     if( mnScCols && mnScRows && static_cast< sal_uLong >( mnScCols * mnScRows ) <= maValueList.size() )
     854             :     {
     855           0 :         xScMatrix = new ScMatrix(mnScCols, mnScRows, 0.0);
     856           0 :         XclImpValueList::const_iterator itValue = maValueList.begin();
     857           0 :         for( SCSIZE nScRow = 0; nScRow < mnScRows; ++nScRow )
     858             :         {
     859           0 :             for( SCSIZE nScCol = 0; nScCol < mnScCols; ++nScCol )
     860             :             {
     861           0 :                 switch( itValue->GetType() )
     862             :                 {
     863             :                     case EXC_CACHEDVAL_EMPTY:
     864             :                         // Excel shows 0.0 here, not an empty cell
     865           0 :                         xScMatrix->PutEmpty( nScCol, nScRow );
     866           0 :                     break;
     867             :                     case EXC_CACHEDVAL_DOUBLE:
     868           0 :                         xScMatrix->PutDouble( itValue->GetValue(), nScCol, nScRow );
     869           0 :                     break;
     870             :                     case EXC_CACHEDVAL_STRING:
     871           0 :                         xScMatrix->PutString( itValue->GetString(), nScCol, nScRow );
     872           0 :                     break;
     873             :                     case EXC_CACHEDVAL_BOOL:
     874           0 :                         xScMatrix->PutBoolean( itValue->GetBool(), nScCol, nScRow );
     875           0 :                     break;
     876             :                     case EXC_CACHEDVAL_ERROR:
     877           0 :                         xScMatrix->PutError( itValue->GetScError(), nScCol, nScRow );
     878           0 :                     break;
     879             :                     default:
     880             :                         OSL_FAIL( "XclImpCachedMatrix::CreateScMatrix - unknown value type" );
     881           0 :                         xScMatrix->PutEmpty( nScCol, nScRow );
     882             :                 }
     883           0 :                 ++itValue;
     884             :             }
     885             :         }
     886             :     }
     887           0 :     return xScMatrix;
     888             : }
     889             : 
     890             : // ============================================================================
     891             : 
     892             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10