LCOV - code coverage report
Current view: top level - usr/local/src/libreoffice/sc/source/core/data - table4.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 372 1096 33.9 %
Date: 2013-07-09 Functions: 15 27 55.6 %
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 "scitems.hxx"
      21             : #include <comphelper/string.hxx>
      22             : #include <svx/algitem.hxx>
      23             : #include <editeng/boxitem.hxx>
      24             : #include <editeng/brushitem.hxx>
      25             : #include <editeng/contouritem.hxx>
      26             : #include <editeng/colritem.hxx>
      27             : #include <editeng/crossedoutitem.hxx>
      28             : #include <editeng/fhgtitem.hxx>
      29             : #include <editeng/fontitem.hxx>
      30             : #include <editeng/langitem.hxx>
      31             : #include <editeng/postitem.hxx>
      32             : #include <editeng/shdditem.hxx>
      33             : #include <editeng/udlnitem.hxx>
      34             : #include <editeng/wghtitem.hxx>
      35             : #include <svx/rotmodit.hxx>
      36             : #include <editeng/editobj.hxx>
      37             : #include <editeng/editeng.hxx>
      38             : #include <editeng/eeitem.hxx>
      39             : #include <editeng/escapementitem.hxx>
      40             : #include <svl/zforlist.hxx>
      41             : #include <vcl/keycodes.hxx>
      42             : #include <rtl/math.hxx>
      43             : #include <unotools/charclass.hxx>
      44             : 
      45             : #include "attrib.hxx"
      46             : #include "patattr.hxx"
      47             : #include "formulacell.hxx"
      48             : #include "table.hxx"
      49             : #include "globstr.hrc"
      50             : #include "global.hxx"
      51             : #include "document.hxx"
      52             : #include "autoform.hxx"
      53             : #include "userlist.hxx"
      54             : #include "zforauto.hxx"
      55             : #include "subtotal.hxx"
      56             : #include "formula/errorcodes.hxx"
      57             : #include "rangenam.hxx"
      58             : #include "docpool.hxx"
      59             : #include "progress.hxx"
      60             : #include "segmenttree.hxx"
      61             : #include "conditio.hxx"
      62             : #include "editutil.hxx"
      63             : 
      64             : #include <math.h>
      65             : #include <boost/scoped_ptr.hpp>
      66             : 
      67             : // STATIC DATA -----------------------------------------------------------
      68             : 
      69             : #define _D_MAX_LONG_  (double) 0x7fffffff
      70             : 
      71             : extern sal_uInt16 nScFillModeMouseModifier;     // global.cxx
      72             : 
      73             : namespace {
      74             : 
      75           2 : short lcl_DecompValueString( String& aValue, sal_Int32& nVal, sal_uInt16* pMinDigits = NULL )
      76             : {
      77           2 :     if ( !aValue.Len() )
      78             :     {
      79           0 :         nVal = 0;
      80           0 :         return 0;
      81             :     }
      82           2 :     const sal_Unicode* p = aValue.GetBuffer();
      83           2 :     xub_StrLen nNeg = 0;
      84           2 :     xub_StrLen nNum = 0;
      85           2 :     if ( p[nNum] == '-' )
      86           0 :         nNum = nNeg = 1;
      87           4 :     while ( p[nNum] && CharClass::isAsciiNumeric( OUString(p[nNum]) ) )
      88           0 :         nNum++;
      89             : 
      90           2 :     sal_Unicode cNext = p[nNum];            // 0 if at the end
      91           2 :     sal_Unicode cLast = p[aValue.Len()-1];
      92             : 
      93             :     // #i5550# If there are numbers at the beginning and the end,
      94             :     // prefer the one at the beginning only if it's followed by a space.
      95             :     // Otherwise, use the number at the end, to enable things like IP addresses.
      96           2 :     if ( nNum > nNeg && ( cNext == 0 || cNext == ' ' || !CharClass::isAsciiNumeric(OUString(cLast)) ) )
      97             :     {   // number at the beginning
      98           0 :         nVal = aValue.Copy( 0, nNum ).ToInt32();
      99             :         //  any number with a leading zero sets the minimum number of digits
     100           0 :         if ( p[nNeg] == '0' && pMinDigits && ( nNum - nNeg > *pMinDigits ) )
     101           0 :             *pMinDigits = nNum - nNeg;
     102           0 :         aValue.Erase( 0, nNum );
     103           0 :         return -1;
     104             :     }
     105             :     else
     106             :     {
     107           2 :         nNeg = 0;
     108           2 :         xub_StrLen nEnd = nNum = aValue.Len() - 1;
     109           4 :         while ( nNum && CharClass::isAsciiNumeric( OUString(p[nNum]) ) )
     110           0 :             nNum--;
     111           2 :         if ( p[nNum] == '-' )
     112             :         {
     113           0 :             nNum--;
     114           0 :             nNeg = 1;
     115             :         }
     116           2 :         if ( nNum < nEnd - nNeg )
     117             :         {   // number at the end
     118           0 :             nVal = aValue.Copy( nNum + 1 ).ToInt32();
     119             :             //  any number with a leading zero sets the minimum number of digits
     120           0 :             if ( p[nNum+1+nNeg] == '0' && pMinDigits && ( nEnd - nNum - nNeg > *pMinDigits ) )
     121           0 :                 *pMinDigits = nEnd - nNum - nNeg;
     122           0 :             aValue.Erase( nNum + 1 );
     123           0 :             return 1;
     124             :         }
     125             :     }
     126           2 :     nVal = 0;
     127           2 :     return 0;
     128             : }
     129             : 
     130           0 : OUString lcl_ValueString( sal_Int32 nValue, sal_uInt16 nMinDigits )
     131             : {
     132           0 :     if ( nMinDigits <= 1 )
     133           0 :         return OUString::number( nValue );           // simple case...
     134             :     else
     135             :     {
     136           0 :         OUString aStr = OUString::number( std::abs( nValue ) );
     137           0 :         if ( aStr.getLength() < nMinDigits )
     138             :         {
     139           0 :             OUStringBuffer aZero;
     140           0 :             comphelper::string::padToLength(aZero, nMinDigits - aStr.getLength(), '0');
     141           0 :             aStr = aZero.makeStringAndClear() + aStr;
     142             :         }
     143             :         //  nMinDigits doesn't include the '-' sign -> add after inserting zeros
     144           0 :         if ( nValue < 0 )
     145           0 :             aStr = "-" + aStr;
     146           0 :         return aStr;
     147             :     }
     148             : }
     149             : 
     150           0 : void setSuffixCell(
     151             :     ScColumn& rColumn, SCROW nRow, sal_Int32 nValue, sal_uInt16 nDigits, const OUString& rSuffix,
     152             :     CellType eCellType, bool bIsOrdinalSuffix )
     153             : {
     154           0 :     ScDocument& rDoc = rColumn.GetDoc();
     155           0 :     OUString aValue = lcl_ValueString(nValue, nDigits);
     156           0 :     if (!bIsOrdinalSuffix)
     157             :     {
     158           0 :         rColumn.SetRawString(nRow, aValue += rSuffix);
     159           0 :         return;
     160             :     }
     161             : 
     162           0 :     OUString aOrdinalSuffix = ScGlobal::GetOrdinalSuffix(nValue);
     163           0 :     if (eCellType != CELLTYPE_EDIT)
     164             :     {
     165           0 :         rColumn.SetRawString(nRow, aValue += aOrdinalSuffix);
     166           0 :         return;
     167             :     }
     168             : 
     169           0 :     EditEngine aEngine(rDoc.GetEnginePool());
     170           0 :     aEngine.SetEditTextObjectPool(rDoc.GetEditPool());
     171             : 
     172           0 :     SfxItemSet aAttr = aEngine.GetEmptyItemSet();
     173           0 :     aAttr.Put( SvxEscapementItem( SVX_ESCAPEMENT_SUPERSCRIPT, EE_CHAR_ESCAPEMENT));
     174           0 :     aEngine.SetText( aValue );
     175             :     aEngine.QuickInsertText(
     176             :         aOrdinalSuffix,
     177           0 :         ESelection(0, aValue.getLength(), 0, aValue.getLength() + aOrdinalSuffix.getLength()));
     178             : 
     179             :     aEngine.QuickSetAttribs(
     180             :         aAttr,
     181           0 :         ESelection(0, aValue.getLength(), 0, aValue.getLength() + aOrdinalSuffix.getLength()));
     182             : 
     183             :     // Text object instance will be owned by the cell.
     184           0 :     rColumn.SetEditText(nRow, aEngine.CreateTextObject());
     185             : }
     186             : 
     187             : }
     188             : 
     189          11 : void ScTable::FillAnalyse( SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
     190             :                             FillCmd& rCmd, FillDateCmd& rDateCmd,
     191             :                             double& rInc, sal_uInt16& rMinDigits,
     192             :                             ScUserListData*& rListData, sal_uInt16& rListIndex)
     193             : {
     194             :     OSL_ENSURE( nCol1==nCol2 || nRow1==nRow2, "FillAnalyse: invalid range" );
     195             : 
     196          11 :     rInc = 0.0;
     197          11 :     rMinDigits = 0;
     198          11 :     rListData = NULL;
     199          11 :     rCmd = FILL_SIMPLE;
     200          11 :     if ( (nScFillModeMouseModifier & KEY_MOD1) )
     201           1 :         return ;        // Ctrl-key: Copy
     202             : 
     203             :     SCCOL nAddX;
     204             :     SCROW nAddY;
     205             :     SCSIZE nCount;
     206          11 :     if (nCol1 == nCol2)
     207             :     {
     208          11 :         nAddX = 0;
     209          11 :         nAddY = 1;
     210          11 :         nCount = static_cast<SCSIZE>(nRow2 - nRow1 + 1);
     211             :     }
     212             :     else
     213             :     {
     214           0 :         nAddX = 1;
     215           0 :         nAddY = 0;
     216           0 :         nCount = static_cast<SCSIZE>(nCol2 - nCol1 + 1);
     217             :     }
     218             : 
     219          11 :     SCCOL nCol = nCol1;
     220          11 :     SCROW nRow = nRow1;
     221             : 
     222          11 :     ScRefCellValue aFirstCell = GetCellValue(nCol, nRow);
     223          11 :     CellType eCellType = aFirstCell.meType;
     224             : 
     225          11 :     if (eCellType == CELLTYPE_VALUE)
     226             :     {
     227           8 :         sal_uInt32 nFormat = ((const SfxUInt32Item*)GetAttr(nCol,nRow,ATTR_VALUE_FORMAT))->GetValue();
     228           8 :         bool bDate = ( pDocument->GetFormatTable()->GetType(nFormat) == NUMBERFORMAT_DATE );
     229           8 :         if (bDate)
     230             :         {
     231           0 :             if (nCount > 1)
     232             :             {
     233             :                 double nVal;
     234           0 :                 Date aNullDate = *pDocument->GetFormatTable()->GetNullDate();
     235           0 :                 Date aDate1 = aNullDate;
     236           0 :                 nVal = aFirstCell.mfValue;
     237           0 :                 aDate1 += (long)nVal;
     238           0 :                 Date aDate2 = aNullDate;
     239           0 :                 nVal = GetValue(nCol+nAddX, nRow+nAddY);
     240           0 :                 aDate2 += (long)nVal;
     241           0 :                 if ( aDate1 != aDate2 )
     242             :                 {
     243           0 :                     long nCmpInc = 0;
     244             :                     FillDateCmd eType;
     245           0 :                     long nDDiff = aDate2.GetDay()   - (long) aDate1.GetDay();
     246           0 :                     long nMDiff = aDate2.GetMonth() - (long) aDate1.GetMonth();
     247           0 :                     long nYDiff = aDate2.GetYear()  - (long) aDate1.GetYear();
     248           0 :                     if ( nDDiff )
     249             :                     {
     250           0 :                         eType = FILL_DAY;
     251           0 :                         nCmpInc = aDate2 - aDate1;
     252             :                     }
     253             :                     else
     254             :                     {
     255           0 :                         eType = FILL_MONTH;
     256           0 :                         nCmpInc = nMDiff + 12 * nYDiff;
     257             :                     }
     258             : 
     259           0 :                     nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     260           0 :                     nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     261           0 :                     bool bVal = true;
     262           0 :                     for (sal_uInt16 i=1; i<nCount && bVal; i++)
     263             :                     {
     264           0 :                         ScRefCellValue aCell = GetCellValue(nCol,nRow);
     265           0 :                         if (aCell.meType == CELLTYPE_VALUE)
     266             :                         {
     267           0 :                             nVal = aCell.mfValue;
     268           0 :                             aDate2 = aNullDate + (long) nVal;
     269           0 :                             if ( eType == FILL_DAY )
     270             :                             {
     271           0 :                                 if ( aDate2-aDate1 != nCmpInc )
     272           0 :                                     bVal = false;
     273             :                             }
     274             :                             else
     275             :                             {
     276           0 :                                 nDDiff = aDate2.GetDay()   - (long) aDate1.GetDay();
     277           0 :                                 nMDiff = aDate2.GetMonth() - (long) aDate1.GetMonth();
     278           0 :                                 nYDiff = aDate2.GetYear()  - (long) aDate1.GetYear();
     279           0 :                                 if (nDDiff || ( nMDiff + 12 * nYDiff != nCmpInc ))
     280           0 :                                     bVal = false;
     281             :                             }
     282           0 :                             aDate1 = aDate2;
     283           0 :                             nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     284           0 :                             nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     285             :                         }
     286             :                         else
     287           0 :                             bVal = false;   // kein Datum passt auch nicht
     288           0 :                     }
     289           0 :                     if (bVal)
     290             :                     {
     291           0 :                         if ( eType == FILL_MONTH && ( nCmpInc % 12 == 0 ) )
     292             :                         {
     293           0 :                             eType = FILL_YEAR;
     294           0 :                             nCmpInc /= 12;
     295             :                         }
     296           0 :                         rCmd = FILL_DATE;
     297           0 :                         rDateCmd = eType;
     298           0 :                         rInc = nCmpInc;
     299             :                     }
     300             :                 }
     301             :             }
     302             :             else                            // single date -> increment by days
     303             :             {
     304           0 :                 rCmd = FILL_DATE;
     305           0 :                 rDateCmd = FILL_DAY;
     306           0 :                 rInc = 1.0;
     307             :             }
     308             :         }
     309             :         else
     310             :         {
     311           8 :             if (nCount > 1)
     312             :             {
     313           0 :                 double nVal1 = aFirstCell.mfValue;
     314           0 :                 double nVal2 = GetValue(nCol+nAddX, nRow+nAddY);
     315           0 :                 rInc = nVal2 - nVal1;
     316           0 :                 nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     317           0 :                 nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     318           0 :                 bool bVal = true;
     319           0 :                 for (sal_uInt16 i=1; i<nCount && bVal; i++)
     320             :                 {
     321           0 :                     ScRefCellValue aCell = GetCellValue(nCol,nRow);
     322           0 :                     if (aCell.meType == CELLTYPE_VALUE)
     323             :                     {
     324           0 :                         nVal2 = aCell.mfValue;
     325           0 :                         double nDiff = nVal2 - nVal1;
     326           0 :                         if ( !::rtl::math::approxEqual( nDiff, rInc, 13 ) )
     327           0 :                             bVal = false;
     328           0 :                         nVal1 = nVal2;
     329             :                     }
     330             :                     else
     331           0 :                         bVal = false;
     332           0 :                     nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     333           0 :                     nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     334           0 :                 }
     335           0 :                 if (bVal)
     336           0 :                     rCmd = FILL_LINEAR;
     337             :             }
     338             :         }
     339             :     }
     340           3 :     else if (eCellType == CELLTYPE_STRING || eCellType == CELLTYPE_EDIT)
     341             :     {
     342           2 :         OUString aStr;
     343           2 :         GetString(nCol, nRow, aStr);
     344             : 
     345             :         // fdo#39500 don't deduce increment from multiple equal list entries
     346           2 :         bool bAllSame = true;
     347           5 :         for (sal_uInt16 i = 0; i < nCount; ++i)
     348             :         {
     349           3 :             OUString aTestStr;
     350           3 :             GetString(static_cast<SCCOL>(nCol + i* nAddX), static_cast<SCROW>(nRow + i * nAddY), aTestStr);
     351           3 :             if(aStr != aTestStr)
     352             :             {
     353           0 :                 bAllSame = false;
     354           0 :                 break;
     355             :             }
     356           3 :         }
     357           2 :         if(bAllSame && nCount > 1)
     358           1 :             return;
     359             : 
     360           1 :         rListData = (ScUserListData*)(ScGlobal::GetUserList()->GetData(aStr));
     361           1 :         if (rListData)
     362             :         {
     363           1 :             rListData->GetSubIndex(aStr, rListIndex);
     364           1 :             nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     365           1 :             nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     366           1 :             for (sal_uInt16 i=1; i<nCount && rListData; i++)
     367             :             {
     368           0 :                 GetString(nCol, nRow, aStr);
     369           0 :                 if (!rListData->GetSubIndex(aStr, rListIndex))
     370           0 :                     rListData = NULL;
     371           0 :                 nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     372           0 :                 nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     373             :             }
     374             :         }
     375           0 :         else if ( nCount > 1 )
     376             :         {
     377             :             //  pass rMinDigits to all DecompValueString calls
     378             :             //  -> longest number defines rMinDigits
     379             : 
     380             :             sal_Int32 nVal1;
     381           0 :             String aString = aStr;
     382           0 :             short nFlag1 = lcl_DecompValueString( aString, nVal1, &rMinDigits );
     383           0 :             aStr = aString;
     384           0 :             if ( nFlag1 )
     385             :             {
     386             :                 sal_Int32 nVal2;
     387           0 :                 GetString( nCol+nAddX, nRow+nAddY, aStr );
     388           0 :                 aString = aStr;
     389           0 :                 short nFlag2 = lcl_DecompValueString( aString, nVal2, &rMinDigits );
     390           0 :                 aStr = aString;
     391           0 :                 if ( nFlag1 == nFlag2 )
     392             :                 {
     393           0 :                     rInc = (double)nVal2 - (double)nVal1;
     394           0 :                     nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     395           0 :                     nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     396           0 :                     bool bVal = true;
     397           0 :                     for (sal_uInt16 i=1; i<nCount && bVal; i++)
     398             :                     {
     399           0 :                         ScRefCellValue aCell = GetCellValue(nCol, nRow);
     400           0 :                         CellType eType = aCell.meType;
     401           0 :                         if ( eType == CELLTYPE_STRING || eType == CELLTYPE_EDIT )
     402             :                         {
     403           0 :                             aStr = aCell.getString();
     404           0 :                             aString = aStr;
     405           0 :                             nFlag2 = lcl_DecompValueString( aString, nVal2, &rMinDigits );
     406           0 :                             aStr = aString;
     407           0 :                             if ( nFlag1 == nFlag2 )
     408             :                             {
     409           0 :                                 double nDiff = (double)nVal2 - (double)nVal1;
     410           0 :                                 if ( !::rtl::math::approxEqual( nDiff, rInc, 13 ) )
     411           0 :                                     bVal = false;
     412           0 :                                 nVal1 = nVal2;
     413             :                             }
     414             :                             else
     415           0 :                                 bVal = false;
     416             :                         }
     417             :                         else
     418           0 :                             bVal = false;
     419           0 :                         nCol = sal::static_int_cast<SCCOL>( nCol + nAddX );
     420           0 :                         nRow = sal::static_int_cast<SCROW>( nRow + nAddY );
     421           0 :                     }
     422           0 :                     if (bVal)
     423           0 :                         rCmd = FILL_LINEAR;
     424             :                 }
     425           0 :             }
     426             :         }
     427             :         else
     428             :         {
     429             :             //  call DecompValueString to set rMinDigits
     430             :             sal_Int32 nDummy;
     431           0 :             String aString = aStr;
     432           0 :             lcl_DecompValueString( aString, nDummy, &rMinDigits );
     433           1 :         }
     434          10 :     }
     435             : }
     436             : 
     437           3 : void ScTable::FillFormula(sal_uLong& /* nFormulaCounter */, bool /* bFirst */, ScFormulaCell* pSrcCell,
     438             :                           SCCOL nDestCol, SCROW nDestRow, bool bLast )
     439             : {
     440             : 
     441           3 :     pDocument->SetNoListening( true );  // still the wrong reference
     442           3 :     ScAddress aAddr( nDestCol, nDestRow, nTab );
     443           3 :     ScFormulaCell* pDestCell = new ScFormulaCell( *pSrcCell, *pDocument, aAddr );
     444           3 :     aCol[nDestCol].SetFormulaCell(nDestRow, pDestCell);
     445             : 
     446           3 :     if ( bLast && pDestCell->GetMatrixFlag() )
     447             :     {
     448           0 :         ScAddress aOrg;
     449           0 :         if ( pDestCell->GetMatrixOrigin( aOrg ) )
     450             :         {
     451           0 :             if ( nDestCol >= aOrg.Col() && nDestRow >= aOrg.Row() )
     452             :             {
     453           0 :                 ScFormulaCell* pOrgCell = pDocument->GetFormulaCell(aOrg);
     454           0 :                 if (pOrgCell && pOrgCell->GetMatrixFlag() == MM_FORMULA)
     455             :                 {
     456             :                     ((ScFormulaCell*)pOrgCell)->SetMatColsRows(
     457           0 :                         nDestCol - aOrg.Col() + 1,
     458           0 :                         nDestRow - aOrg.Row() + 1 );
     459             :                 }
     460             :                 else
     461             :                 {
     462             :                     OSL_FAIL( "FillFormula: MatrixOrigin no forumla cell with MM_FORMULA" );
     463             :                 }
     464             :             }
     465             :             else
     466             :             {
     467             :                 OSL_FAIL( "FillFormula: MatrixOrigin bottom right" );
     468             :             }
     469             :         }
     470             :         else
     471             :         {
     472             :             OSL_FAIL( "FillFormula: no MatrixOrigin" );
     473             :         }
     474             :     }
     475           3 :     pDocument->SetNoListening( false );
     476           3 :     pDestCell->StartListeningTo( pDocument );
     477             : 
     478           3 : }
     479             : 
     480           4 : void ScTable::FillAuto( SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
     481             :                         sal_uLong nFillCount, FillDir eFillDir, ScProgress* pProgress )
     482             : {
     483           4 :     if ( (nFillCount == 0) || !ValidColRow(nCol1, nRow1) || !ValidColRow(nCol2, nRow2) )
     484           4 :         return;
     485             : 
     486             :     //
     487             :     //  Detect direction
     488             :     //
     489             : 
     490           4 :     bool bVertical = (eFillDir == FILL_TO_BOTTOM || eFillDir == FILL_TO_TOP);
     491           4 :     bool bPositive = (eFillDir == FILL_TO_BOTTOM || eFillDir == FILL_TO_RIGHT);
     492             : 
     493           4 :     sal_uLong nCol = 0;
     494           4 :     sal_uLong nRow = 0;
     495           4 :     sal_uLong& rInner = bVertical ? nRow : nCol;        // loop variables
     496           4 :     sal_uLong& rOuter = bVertical ? nCol : nRow;
     497             :     sal_uLong nOStart;
     498             :     sal_uLong nOEnd;
     499             :     sal_uLong nIStart;
     500             :     sal_uLong nIEnd;
     501             :     sal_uLong nISrcStart;
     502             :     sal_uLong nISrcEnd;
     503           4 :     ScRange aFillRange;
     504             : 
     505           4 :     if (bVertical)
     506             :     {
     507           3 :         nOStart = nCol1;
     508           3 :         nOEnd = nCol2;
     509           3 :         if (bPositive)
     510             :         {
     511           3 :             nISrcStart = nRow1;
     512           3 :             nISrcEnd = nRow2;
     513           3 :             nIStart = nRow2 + 1;
     514           3 :             nIEnd = nRow2 + nFillCount;
     515           3 :             aFillRange = ScRange(nCol1, nRow2+1, 0, nCol2, nRow2 + nFillCount, 0);
     516             :         }
     517             :         else
     518             :         {
     519           0 :             nISrcStart = nRow2;
     520           0 :             nISrcEnd = nRow1;
     521           0 :             nIStart = nRow1 - 1;
     522           0 :             nIEnd = nRow1 - nFillCount;
     523           0 :             aFillRange = ScRange(nCol1, nRow1-1, 0, nCol2, nRow2 - nFillCount, 0);
     524             :         }
     525             :     }
     526             :     else
     527             :     {
     528           1 :         nOStart = nRow1;
     529           1 :         nOEnd = nRow2;
     530           1 :         if (bPositive)
     531             :         {
     532           1 :             nISrcStart = nCol1;
     533           1 :             nISrcEnd = nCol2;
     534           1 :             nIStart = nCol2 + 1;
     535           1 :             nIEnd = nCol2 + nFillCount;
     536           1 :             aFillRange = ScRange(nCol2 + 1, nRow1, 0, nCol2 + nFillCount, nRow2, 0);
     537             :         }
     538             :         else
     539             :         {
     540           0 :             nISrcStart = nCol2;
     541           0 :             nISrcEnd = nCol1;
     542           0 :             nIStart = nCol1 - 1;
     543           0 :             nIEnd = nCol1 - nFillCount;
     544           0 :             aFillRange = ScRange(nCol1 - 1, nRow1, 0, nCol1 - nFillCount, nRow2, 0);
     545             :         }
     546             :     }
     547           4 :     sal_uLong nIMin = nIStart;
     548           4 :     sal_uLong nIMax = nIEnd;
     549           4 :     PutInOrder(nIMin,nIMax);
     550           4 :     bool bHasFiltered = IsDataFiltered(aFillRange);
     551             : 
     552           4 :     if (!bHasFiltered)
     553             :     {
     554           4 :         if (bVertical)
     555           3 :             DeleteArea(nCol1, static_cast<SCROW>(nIMin), nCol2, static_cast<SCROW>(nIMax), IDF_AUTOFILL);
     556             :         else
     557           1 :             DeleteArea(static_cast<SCCOL>(nIMin), nRow1, static_cast<SCCOL>(nIMax), nRow2, IDF_AUTOFILL);
     558             :     }
     559             : 
     560           4 :     sal_uLong nProgress = 0;
     561           4 :     if (pProgress)
     562           2 :         nProgress = pProgress->GetState();
     563             : 
     564             :     //
     565             :     //  execute
     566             :     //
     567             : 
     568           4 :     sal_uLong nActFormCnt = 0;
     569          15 :     for (rOuter = nOStart; rOuter <= nOEnd; rOuter++)
     570             :     {
     571          11 :         sal_uLong nMaxFormCnt = 0;                      // for formulas
     572             : 
     573             :         //  transfer attributes
     574             : 
     575          11 :         const ScPatternAttr* pSrcPattern = NULL;
     576          11 :         const ScStyleSheet* pStyleSheet = NULL;
     577          11 :         sal_uLong nAtSrc = nISrcStart;
     578          11 :         ScPatternAttr* pNewPattern = NULL;
     579          11 :         bool bGetPattern = true;
     580          11 :         rInner = nIStart;
     581             :         while (true)        // #i53728# with "for (;;)" old solaris/x86 compiler mis-optimizes
     582             :         {
     583          22 :             if (!ColHidden(nCol) && !RowHidden(nRow))
     584             :             {
     585          22 :                 if ( bGetPattern )
     586             :                 {
     587          12 :                     delete pNewPattern;
     588          12 :                     if (bVertical)      // rInner&:=nRow, rOuter&:=nCol
     589           7 :                         pSrcPattern = aCol[nCol].GetPattern(static_cast<SCROW>(nAtSrc));
     590             :                     else                // rInner&:=nCol, rOuter&:=nRow
     591           5 :                         pSrcPattern = aCol[nAtSrc].GetPattern(static_cast<SCROW>(nRow));
     592          12 :                     bGetPattern = false;
     593          12 :                     pStyleSheet = pSrcPattern->GetStyleSheet();
     594             :                     //  do not transfer ATTR_MERGE / ATTR_MERGE_FLAG
     595          12 :                     const SfxItemSet& rSet = pSrcPattern->GetItemSet();
     596          24 :                     if ( rSet.GetItemState(ATTR_MERGE, false) == SFX_ITEM_SET
     597          12 :                             || rSet.GetItemState(ATTR_MERGE_FLAG, false) == SFX_ITEM_SET )
     598             :                     {
     599           0 :                         pNewPattern = new ScPatternAttr( *pSrcPattern );
     600           0 :                         SfxItemSet& rNewSet = pNewPattern->GetItemSet();
     601           0 :                         rNewSet.ClearItem(ATTR_MERGE);
     602           0 :                         rNewSet.ClearItem(ATTR_MERGE_FLAG);
     603             :                     }
     604             :                     else
     605          12 :                         pNewPattern = NULL;
     606             :                 }
     607             : 
     608          22 :                 const ScCondFormatItem& rCondFormatItem = static_cast<const ScCondFormatItem&>(pSrcPattern->GetItem(ATTR_CONDITIONAL));
     609          22 :                 const std::vector<sal_uInt32>& rCondFormatIndex = rCondFormatItem.GetCondFormatData();
     610             : 
     611          22 :                 if ( bVertical && nISrcStart == nISrcEnd && !bHasFiltered )
     612             :                 {
     613             :                     //  set all attributes at once (en bloc)
     614           5 :                     if (pNewPattern || pSrcPattern != pDocument->GetDefPattern())
     615             :                     {
     616             :                         //  Default is already present (DeleteArea)
     617           0 :                         SCROW nY1 = static_cast<SCROW>(std::min( nIStart, nIEnd ));
     618           0 :                         SCROW nY2 = static_cast<SCROW>(std::max( nIStart, nIEnd ));
     619           0 :                         if ( pStyleSheet )
     620           0 :                             aCol[nCol].ApplyStyleArea( nY1, nY2, *pStyleSheet );
     621           0 :                         if ( pNewPattern )
     622           0 :                             aCol[nCol].ApplyPatternArea( nY1, nY2, *pNewPattern );
     623             :                         else
     624           0 :                             aCol[nCol].ApplyPatternArea( nY1, nY2, *pSrcPattern );
     625             : 
     626           0 :                         for(std::vector<sal_uInt32>::const_iterator itr = rCondFormatIndex.begin(), itrEnd = rCondFormatIndex.end();
     627             :                                                         itr != itrEnd; ++itr)
     628             :                         {
     629           0 :                             ScConditionalFormat* pCondFormat = mpCondFormatList->GetFormat(*itr);
     630           0 :                             ScRangeList aRange = pCondFormat->GetRange();
     631           0 :                             aRange.Join(ScRange(nCol, nY1, nTab, nCol, nY2, nTab));
     632           0 :                             pCondFormat->AddRange(aRange);
     633           0 :                         }
     634             :                     }
     635             : 
     636             : 
     637           5 :                     break;
     638             :                 }
     639             : 
     640          17 :                 if ( bHasFiltered )
     641             :                     DeleteArea(static_cast<SCCOL>(nCol), static_cast<SCROW>(nRow),
     642           0 :                             static_cast<SCCOL>(nCol), static_cast<SCROW>(nRow), IDF_AUTOFILL);
     643             : 
     644          17 :                 if ( pSrcPattern != aCol[nCol].GetPattern( static_cast<SCROW>(nRow) ) )
     645             :                 {
     646             :                     // Transfer template too
     647             :                     //! Merge ApplyPattern to AttrArray ??
     648           0 :                     if ( pStyleSheet )
     649           0 :                         aCol[nCol].ApplyStyle( static_cast<SCROW>(nRow), *pStyleSheet );
     650             : 
     651             :                     //  Use ApplyPattern instead of SetPattern to keep old MergeFlags
     652           0 :                     if ( pNewPattern )
     653           0 :                         aCol[nCol].ApplyPattern( static_cast<SCROW>(nRow), *pNewPattern );
     654             :                     else
     655           0 :                         aCol[nCol].ApplyPattern( static_cast<SCROW>(nRow), *pSrcPattern );
     656             : 
     657           0 :                     for(std::vector<sal_uInt32>::const_iterator itr = rCondFormatIndex.begin(), itrEnd = rCondFormatIndex.end();
     658             :                             itr != itrEnd; ++itr)
     659             :                     {
     660           0 :                         ScConditionalFormat* pCondFormat = mpCondFormatList->GetFormat(*itr);
     661           0 :                         ScRangeList aRange = pCondFormat->GetRange();
     662           0 :                         aRange.Join(ScRange(nCol, nRow, nTab, nCol, nRow, nTab));
     663           0 :                         pCondFormat->AddRange(aRange);
     664           0 :                     }
     665             :                 }
     666             : 
     667          17 :                 if (nAtSrc==nISrcEnd)
     668             :                 {
     669          16 :                     if ( nAtSrc != nISrcStart )
     670             :                     {    // More than one source cell
     671           1 :                         nAtSrc = nISrcStart;
     672           1 :                         bGetPattern = true;
     673             :                     }
     674             :                 }
     675           1 :                 else if (bPositive)
     676             :                 {
     677           1 :                     ++nAtSrc;
     678           1 :                     bGetPattern = true;
     679             :                 }
     680             :                 else
     681             :                 {
     682           0 :                     --nAtSrc;
     683           0 :                     bGetPattern = true;
     684             :                 }
     685             :             }
     686             : 
     687          17 :             if (rInner == nIEnd) break;
     688          11 :             if (bPositive) ++rInner; else --rInner;
     689             :         }
     690          11 :         if ( pNewPattern )
     691           0 :             delete pNewPattern;
     692             : 
     693             :         //  Analyse
     694             : 
     695             :         FillCmd eFillCmd;
     696             :         FillDateCmd eDateCmd;
     697             :         double nInc;
     698             :         sal_uInt16 nMinDigits;
     699          11 :         ScUserListData* pListData = NULL;
     700             :         sal_uInt16 nListIndex;
     701          11 :         if (bVertical)
     702             :             FillAnalyse(static_cast<SCCOL>(nCol),nRow1,
     703             :                     static_cast<SCCOL>(nCol),nRow2, eFillCmd,eDateCmd,
     704           6 :                     nInc,nMinDigits, pListData,nListIndex);
     705             :         else
     706             :             FillAnalyse(nCol1,static_cast<SCROW>(nRow),
     707             :                     nCol2,static_cast<SCROW>(nRow), eFillCmd,eDateCmd,
     708           5 :                     nInc,nMinDigits, pListData,nListIndex);
     709             : 
     710          11 :         if (pListData)
     711             :         {
     712           1 :             sal_uInt16 nListCount = pListData->GetSubCount();
     713           1 :             if ( !bPositive )
     714             :             {
     715             :                 //  nListIndex of FillAnalyse points to the last entry -> adjust
     716           0 :                 sal_uLong nSub = nISrcStart - nISrcEnd;
     717           0 :                 for (sal_uLong i=0; i<nSub; i++)
     718             :                 {
     719           0 :                     if (nListIndex == 0) nListIndex = nListCount;
     720           0 :                     --nListIndex;
     721             :                 }
     722             :             }
     723             : 
     724           1 :             rInner = nIStart;
     725             :             while (true)        // #i53728# with "for (;;)" old solaris/x86 compiler mis-optimizes
     726             :             {
     727           2 :                 if(!ColHidden(nCol) && !RowHidden(nRow))
     728             :                 {
     729           2 :                     if (bPositive)
     730             :                     {
     731           2 :                         ++nListIndex;
     732           2 :                         if (nListIndex >= nListCount) nListIndex = 0;
     733             :                     }
     734             :                     else
     735             :                     {
     736           0 :                         if (nListIndex == 0) nListIndex = nListCount;
     737           0 :                         --nListIndex;
     738             :                     }
     739           2 :                     aCol[nCol].SetRawString(static_cast<SCROW>(nRow), pListData->GetSubStr(nListIndex));
     740             :                 }
     741             : 
     742           2 :                 if (rInner == nIEnd) break;
     743           1 :                 if (bPositive) ++rInner; else --rInner;
     744             :             }
     745           1 :             if(pProgress)
     746             :             {
     747           0 :                 nProgress += nIMax - nIMin + 1;
     748           0 :                 pProgress->SetStateOnPercent( nProgress );
     749           1 :             }
     750             :         }
     751          10 :         else if (eFillCmd == FILL_SIMPLE)           // fill with pattern/sample
     752             :         {
     753          10 :             sal_uLong nSource = nISrcStart;
     754             :             double nDelta;
     755          10 :             if ( (nScFillModeMouseModifier & KEY_MOD1) )
     756           0 :                 nDelta = 0.0;
     757          10 :             else if ( bPositive )
     758          10 :                 nDelta = 1.0;
     759             :             else
     760           0 :                 nDelta = -1.0;
     761          10 :             double nVal = 0.0;
     762          10 :             sal_uLong nFormulaCounter = nActFormCnt;
     763          10 :             bool bFirst = true;
     764          10 :             bool bGetCell = true;
     765          10 :             sal_uInt16 nCellDigits = 0;
     766          10 :             short nHeadNoneTail = 0;
     767          10 :             sal_Int32 nStringValue = 0;
     768          10 :             String aValue;
     769          20 :             ScCellValue aSrcCell;
     770          10 :             CellType eCellType = CELLTYPE_NONE;
     771          10 :             bool bIsOrdinalSuffix = false;
     772             : 
     773          10 :             rInner = nIStart;
     774             :             while (true)        // #i53728# with "for (;;)" old solaris/x86 compiler mis-optimizes
     775             :             {
     776          33 :                 if(!ColHidden(nCol) && !RowHidden(nRow))
     777             :                 {
     778          33 :                     if ( bGetCell )
     779             :                     {
     780          11 :                         if (bVertical)      // rInner&:=nRow, rOuter&:=nCol
     781           6 :                             aSrcCell = aCol[nCol].GetCellValue(static_cast<SCROW>(nSource));
     782             :                         else                // rInner&:=nCol, rOuter&:=nRow
     783           5 :                             aSrcCell = aCol[nSource].GetCellValue(static_cast<SCROW>(nRow));
     784             : 
     785          11 :                         bGetCell = false;
     786          11 :                         if (!aSrcCell.isEmpty())
     787             :                         {
     788          11 :                             eCellType = aSrcCell.meType;
     789          11 :                             switch (eCellType)
     790             :                             {
     791             :                                 case CELLTYPE_VALUE:
     792           8 :                                     nVal = aSrcCell.mfValue;
     793           8 :                                     break;
     794             :                                 case CELLTYPE_STRING:
     795             :                                 case CELLTYPE_EDIT:
     796           2 :                                     if ( eCellType == CELLTYPE_STRING )
     797           2 :                                         aValue = *aSrcCell.mpString;
     798             :                                     else
     799           0 :                                         aValue = ScEditUtil::GetString(*aSrcCell.mpEditText);
     800           2 :                                     if ( !(nScFillModeMouseModifier & KEY_MOD1) && !bHasFiltered )
     801             :                                     {
     802           2 :                                         nCellDigits = 0;    // look at each source cell individually
     803             :                                         nHeadNoneTail = lcl_DecompValueString(
     804           2 :                                                 aValue, nStringValue, &nCellDigits );
     805             : 
     806             :                                         bIsOrdinalSuffix = aValue.Equals(
     807           2 :                                                 ScGlobal::GetOrdinalSuffix( nStringValue));
     808             :                                     }
     809           2 :                                     break;
     810             :                                 default:
     811             :                                     {
     812             :                                         // added to avoid warnings
     813             :                                     }
     814             :                             }
     815             :                         }
     816             :                         else
     817           0 :                             eCellType = CELLTYPE_NONE;
     818             :                     }
     819             : 
     820          33 :                     switch (eCellType)
     821             :                     {
     822             :                         case CELLTYPE_VALUE:
     823          28 :                             aCol[nCol].SetValue(static_cast<SCROW>(nRow), nVal + nDelta);
     824          28 :                             break;
     825             :                         case CELLTYPE_STRING:
     826             :                         case CELLTYPE_EDIT:
     827           2 :                             if ( nHeadNoneTail )
     828             :                             {
     829             :                                 // #i48009# with the "nStringValue+(long)nDelta" expression within the
     830             :                                 // lcl_ValueString calls, gcc 3.4.1 makes wrong optimizations (ok in 3.4.3),
     831             :                                 // so nNextValue is now calculated ahead.
     832           0 :                                 sal_Int32 nNextValue = nStringValue+(sal_Int32)nDelta;
     833             : 
     834           0 :                                 OUString aStr;
     835           0 :                                 if ( nHeadNoneTail < 0 )
     836             :                                 {
     837             :                                     setSuffixCell(
     838           0 :                                         aCol[nCol], static_cast<SCROW>(nRow),
     839             :                                         nNextValue, nCellDigits, aValue,
     840           0 :                                         eCellType, bIsOrdinalSuffix);
     841             :                                 }
     842             :                                 else
     843             :                                 {
     844           0 :                                     aStr = aValue + lcl_ValueString( nNextValue, nCellDigits );
     845           0 :                                     aCol[nCol].SetRawString(static_cast<SCROW>(nRow), aStr);
     846           0 :                                 }
     847             :                             }
     848             :                             else
     849           2 :                                 aSrcCell.commit(aCol[nCol], nRow);
     850             : 
     851           2 :                             break;
     852             :                         case CELLTYPE_FORMULA :
     853             :                             FillFormula( nFormulaCounter, bFirst, aSrcCell.mpFormula,
     854             :                                     static_cast<SCCOL>(nCol),
     855           3 :                                     static_cast<SCROW>(nRow), (rInner == nIEnd) );
     856           3 :                             if (nFormulaCounter - nActFormCnt > nMaxFormCnt)
     857           0 :                                 nMaxFormCnt = nFormulaCounter - nActFormCnt;
     858           3 :                             break;
     859             :                         default:
     860             :                             {
     861             :                                 // added to avoid warnings
     862             :                             }
     863             :                     }
     864             : 
     865          33 :                     if (nSource==nISrcEnd)
     866             :                     {
     867          32 :                         if ( nSource != nISrcStart )
     868             :                         {   // More than one source cell
     869           1 :                             nSource = nISrcStart;
     870           1 :                             bGetCell = true;
     871             :                         }
     872          32 :                         if ( !(nScFillModeMouseModifier & KEY_MOD1) )
     873             :                         {
     874          32 :                             if ( bPositive )
     875          32 :                                 nDelta += 1.0;
     876             :                             else
     877           0 :                                 nDelta -= 1.0;
     878             :                         }
     879          32 :                         nFormulaCounter = nActFormCnt;
     880          32 :                         bFirst = false;
     881             :                     }
     882           1 :                     else if (bPositive)
     883             :                     {
     884           1 :                         ++nSource;
     885           1 :                         bGetCell = true;
     886             :                     }
     887             :                     else
     888             :                     {
     889           0 :                         --nSource;
     890           0 :                         bGetCell = true;
     891             :                     }
     892             :                 }
     893             : 
     894          33 :                 if (rInner == nIEnd) break;
     895          23 :                 if (bPositive) ++rInner; else --rInner;
     896             : 
     897             :                 //  Progress in inner loop only for expensive cells,
     898             :                 //  and even then not individually for each one
     899             : 
     900          23 :                 ++nProgress;
     901          23 :                 if ( pProgress && (eCellType == CELLTYPE_FORMULA || eCellType == CELLTYPE_EDIT) )
     902           2 :                     pProgress->SetStateOnPercent( nProgress );
     903             : 
     904             :             }
     905          10 :             if (pProgress)
     906          19 :                 pProgress->SetStateOnPercent( nProgress );
     907             :         }
     908             :         else
     909             :         {
     910           0 :             if (!bPositive)
     911           0 :                 nInc = -nInc;
     912           0 :             double nEndVal = (nInc>=0.0) ? MAXDOUBLE : -MAXDOUBLE;
     913           0 :             if (bVertical)
     914             :                 FillSeries( static_cast<SCCOL>(nCol), nRow1,
     915             :                         static_cast<SCCOL>(nCol), nRow2, nFillCount, eFillDir,
     916             :                         eFillCmd, eDateCmd, nInc, nEndVal, nMinDigits, false,
     917           0 :                         pProgress );
     918             :             else
     919             :                 FillSeries( nCol1, static_cast<SCROW>(nRow), nCol2,
     920             :                         static_cast<SCROW>(nRow), nFillCount, eFillDir,
     921             :                         eFillCmd, eDateCmd, nInc, nEndVal, nMinDigits, false,
     922           0 :                         pProgress );
     923           0 :             if (pProgress)
     924           0 :                 nProgress = pProgress->GetState();
     925             :         }
     926             : 
     927          11 :         nActFormCnt += nMaxFormCnt;
     928          11 :     }
     929             : }
     930             : 
     931           0 : String ScTable::GetAutoFillPreview( const ScRange& rSource, SCCOL nEndX, SCROW nEndY )
     932             : {
     933           0 :     String aValue;
     934             : 
     935           0 :     SCCOL nCol1 = rSource.aStart.Col();
     936           0 :     SCROW nRow1 = rSource.aStart.Row();
     937           0 :     SCCOL nCol2 = rSource.aEnd.Col();
     938           0 :     SCROW nRow2 = rSource.aEnd.Row();
     939           0 :     bool bOk = true;
     940           0 :     long nIndex = 0;
     941           0 :     sal_uLong nSrcCount = 0;
     942           0 :     FillDir eFillDir = FILL_TO_BOTTOM;
     943           0 :     if ( nEndX == nCol2 && nEndY == nRow2 )     // empty
     944           0 :         bOk = false;
     945           0 :     else if ( nEndX == nCol2 )                  // to up / down
     946             :     {
     947           0 :         nEndX = nCol2 = nCol1;                  // use only first column
     948           0 :         nSrcCount = nRow2 - nRow1 + 1;
     949           0 :         nIndex = ((long)nEndY) - nRow1;         // can be negative
     950           0 :         if ( nEndY >= nRow1 )
     951           0 :             eFillDir = FILL_TO_BOTTOM;
     952             :         else
     953           0 :             eFillDir = FILL_TO_TOP;
     954             :     }
     955           0 :     else if ( nEndY == nRow2 )                  // to left / right
     956             :     {
     957           0 :         nEndY = nRow2 = nRow1;                  // use only first row
     958           0 :         nSrcCount = nCol2 - nCol1 + 1;
     959           0 :         nIndex = ((long)nEndX) - nCol1;         // can be negative
     960           0 :         if ( nEndX >= nCol1 )
     961           0 :             eFillDir = FILL_TO_RIGHT;
     962             :         else
     963           0 :             eFillDir = FILL_TO_LEFT;
     964             :     }
     965             :     else                                        // direction not clear
     966           0 :         bOk = false;
     967             : 
     968           0 :     if ( bOk )
     969             :     {
     970             :         FillCmd eFillCmd;
     971             :         FillDateCmd eDateCmd;
     972             :         double nInc;
     973             :         sal_uInt16 nMinDigits;
     974           0 :         ScUserListData* pListData = NULL;
     975             :         sal_uInt16 nListIndex;
     976             : 
     977           0 :         FillAnalyse(nCol1,nRow1, nCol2,nRow2, eFillCmd,eDateCmd, nInc,nMinDigits, pListData,nListIndex);
     978             : 
     979           0 :         if ( pListData )                            // user defined list
     980             :         {
     981           0 :             sal_uInt16 nListCount = pListData->GetSubCount();
     982           0 :             if ( nListCount )
     983             :             {
     984           0 :                 sal_uLong nSub = nSrcCount - 1; //  nListIndex is from last source entry
     985           0 :                 while ( nIndex < sal::static_int_cast<long>(nSub) )
     986           0 :                     nIndex += nListCount;
     987           0 :                 sal_uLong nPos = ( nListIndex + nIndex - nSub ) % nListCount;
     988           0 :                 aValue = pListData->GetSubStr(sal::static_int_cast<sal_uInt16>(nPos));
     989             :             }
     990             :         }
     991           0 :         else if ( eFillCmd == FILL_SIMPLE )         // fill with pattern/sample
     992             :         {
     993           0 :             if ((eFillDir == FILL_TO_BOTTOM)||(eFillDir == FILL_TO_TOP))
     994             :             {
     995           0 :                 long nBegin = 0;
     996           0 :                 long nEnd = 0;
     997           0 :                 if (nEndY > nRow1)
     998             :                 {
     999           0 :                     nBegin = nRow2+1;
    1000           0 :                     nEnd = nEndY;
    1001             :                 }
    1002             :                 else
    1003             :                 {
    1004           0 :                     nBegin = nEndY;
    1005           0 :                     nEnd = nRow1 -1;
    1006             :                 }
    1007             : 
    1008           0 :                 long nNonFiltered = CountNonFilteredRows(nBegin, nEnd);
    1009           0 :                 long nFiltered = nEnd + 1 - nBegin - nNonFiltered;
    1010             : 
    1011           0 :                 if (nIndex > 0)
    1012           0 :                     nIndex = nIndex - nFiltered;
    1013             :                 else
    1014           0 :                     nIndex = nIndex + nFiltered;
    1015             :             }
    1016             : 
    1017           0 :             long nPosIndex = nIndex;
    1018           0 :             while ( nPosIndex < 0 )
    1019           0 :                 nPosIndex += nSrcCount;
    1020           0 :             sal_uLong nPos = nPosIndex % nSrcCount;
    1021           0 :             SCCOL nSrcX = nCol1;
    1022           0 :             SCROW nSrcY = nRow1;
    1023           0 :             if ( eFillDir == FILL_TO_TOP || eFillDir == FILL_TO_BOTTOM )
    1024           0 :                 nSrcY = sal::static_int_cast<SCROW>( nSrcY + static_cast<SCROW>(nPos) );
    1025             :             else
    1026           0 :                 nSrcX = sal::static_int_cast<SCCOL>( nSrcX + static_cast<SCCOL>(nPos) );
    1027             : 
    1028           0 :             ScRefCellValue aCell = GetCellValue(nSrcX, nSrcY);
    1029           0 :             if (!aCell.isEmpty())
    1030             :             {
    1031             :                 sal_Int32 nDelta;
    1032           0 :                 if (nIndex >= 0)
    1033           0 :                     nDelta = nIndex / nSrcCount;
    1034             :                 else
    1035           0 :                     nDelta = ( nIndex - nSrcCount + 1 ) / nSrcCount;    // -1 -> -1
    1036             : 
    1037           0 :                 CellType eType = aCell.meType;
    1038           0 :                 switch ( eType )
    1039             :                 {
    1040             :                     case CELLTYPE_STRING:
    1041             :                     case CELLTYPE_EDIT:
    1042             :                     {
    1043           0 :                         aValue = aCell.getString();
    1044             : 
    1045           0 :                         if ( !(nScFillModeMouseModifier & KEY_MOD1) )
    1046             :                         {
    1047             :                             sal_Int32 nVal;
    1048           0 :                             sal_uInt16 nCellDigits = 0; // look at each source cell individually
    1049           0 :                             short nFlag = lcl_DecompValueString( aValue, nVal, &nCellDigits );
    1050           0 :                             if ( nFlag < 0 )
    1051             :                             {
    1052           0 :                                 if (aValue.Equals( ScGlobal::GetOrdinalSuffix( nVal)))
    1053           0 :                                     aValue = ScGlobal::GetOrdinalSuffix( nVal + nDelta);
    1054             : 
    1055           0 :                                 aValue.Insert( lcl_ValueString( nVal + nDelta, nCellDigits ), 0 );
    1056             :                             }
    1057           0 :                             else if ( nFlag > 0 )
    1058           0 :                                 aValue += lcl_ValueString( nVal + nDelta, nCellDigits );
    1059             :                         }
    1060             :                     }
    1061           0 :                     break;
    1062             :                     case CELLTYPE_VALUE:
    1063             :                     {
    1064             :                         //  overflow is possible...
    1065           0 :                         double nVal = aCell.mfValue;
    1066           0 :                         if ( !(nScFillModeMouseModifier & KEY_MOD1) )
    1067           0 :                             nVal += (double) nDelta;
    1068             : 
    1069             :                         Color* pColor;
    1070           0 :                         sal_uLong nNumFmt = GetNumberFormat( nSrcX, nSrcY );
    1071           0 :                         OUString sTmp(aValue);
    1072           0 :                         pDocument->GetFormatTable()->GetOutputString( nVal, nNumFmt, sTmp, &pColor );
    1073           0 :                         aValue = sTmp;
    1074             :                     }
    1075           0 :                     break;
    1076             :                     //  not for formulas
    1077             :                     default:
    1078             :                     {
    1079             :                         // added to avoid warnings
    1080             :                     }
    1081             :                 }
    1082           0 :             }
    1083             :         }
    1084           0 :         else if ( eFillCmd == FILL_LINEAR || eFillCmd == FILL_DATE )        // values
    1085             :         {
    1086             :             bool bValueOk;
    1087             :             double nStart;
    1088           0 :             sal_Int32 nVal = 0;
    1089           0 :             short nHeadNoneTail = 0;
    1090           0 :             ScRefCellValue aCell = GetCellValue(nCol1, nRow1);
    1091           0 :             if (!aCell.isEmpty())
    1092             :             {
    1093           0 :                 CellType eType = aCell.meType;
    1094           0 :                 switch ( eType )
    1095             :                 {
    1096             :                     case CELLTYPE_STRING:
    1097             :                     case CELLTYPE_EDIT:
    1098             :                     {
    1099           0 :                         aValue = aCell.getString();
    1100           0 :                         nHeadNoneTail = lcl_DecompValueString( aValue, nVal );
    1101           0 :                         if ( nHeadNoneTail )
    1102           0 :                             nStart = (double)nVal;
    1103             :                         else
    1104           0 :                             nStart = 0.0;
    1105             :                     }
    1106           0 :                     break;
    1107             :                     case CELLTYPE_VALUE:
    1108           0 :                         nStart = aCell.mfValue;
    1109           0 :                     break;
    1110             :                     case CELLTYPE_FORMULA:
    1111           0 :                         nStart = aCell.mpFormula->GetValue();
    1112           0 :                     break;
    1113             :                     default:
    1114           0 :                         nStart = 0.0;
    1115             :                 }
    1116             :             }
    1117             :             else
    1118           0 :                 nStart = 0.0;
    1119           0 :             if ( eFillCmd == FILL_LINEAR )
    1120             :             {
    1121           0 :                 double nAdd = nInc;
    1122           0 :                 bValueOk = ( SubTotal::SafeMult( nAdd, (double) nIndex ) &&
    1123           0 :                              SubTotal::SafePlus( nStart, nAdd ) );
    1124             :             }
    1125             :             else        // date
    1126             :             {
    1127           0 :                 bValueOk = true;
    1128           0 :                 sal_uInt16 nDayOfMonth = 0;
    1129           0 :                 if ( nIndex < 0 )
    1130             :                 {
    1131           0 :                     nIndex = -nIndex;
    1132           0 :                     nInc = -nInc;
    1133             :                 }
    1134           0 :                 for (long i=0; i<nIndex; i++)
    1135           0 :                     IncDate( nStart, nDayOfMonth, nInc, eDateCmd );
    1136             :             }
    1137             : 
    1138           0 :             if (bValueOk)
    1139             :             {
    1140           0 :                 if ( nHeadNoneTail )
    1141             :                 {
    1142           0 :                     if ( nHeadNoneTail < 0 )
    1143             :                     {
    1144           0 :                         if (aValue.Equals( ScGlobal::GetOrdinalSuffix( nVal)))
    1145           0 :                             aValue = ScGlobal::GetOrdinalSuffix( (sal_Int32)nStart );
    1146             : 
    1147           0 :                         aValue.Insert( lcl_ValueString( (sal_Int32)nStart, nMinDigits ), 0 );
    1148             :                     }
    1149             :                     else
    1150           0 :                         aValue += lcl_ValueString( (sal_Int32)nStart, nMinDigits );
    1151             :                 }
    1152             :                 else
    1153             :                 {
    1154             :                     //! Zahlformat je nach Index holen?
    1155             :                     Color* pColor;
    1156           0 :                     sal_uLong nNumFmt = GetNumberFormat( nCol1, nRow1 );
    1157           0 :                     OUString sTmp(aValue);
    1158           0 :                     pDocument->GetFormatTable()->GetOutputString( nStart, nNumFmt, sTmp, &pColor );
    1159           0 :                     aValue = sTmp;
    1160             :                 }
    1161           0 :             }
    1162             :         }
    1163             :         else
    1164             :         {
    1165             :             OSL_FAIL("GetAutoFillPreview: invalid mode");
    1166             :         }
    1167             :     }
    1168             : 
    1169           0 :     return aValue;
    1170             : }
    1171             : 
    1172           0 : void ScTable::IncDate(double& rVal, sal_uInt16& nDayOfMonth, double nStep, FillDateCmd eCmd)
    1173             : {
    1174           0 :     if (eCmd == FILL_DAY)
    1175             :     {
    1176           0 :         rVal += nStep;
    1177           0 :         return;
    1178             :     }
    1179             : 
    1180             :     // class Date limits
    1181           0 :     const sal_uInt16 nMinYear = 1583;
    1182           0 :     const sal_uInt16 nMaxYear = 9956;
    1183             : 
    1184           0 :     long nInc = (long) nStep;       // upper/lower limits ?
    1185           0 :     Date aNullDate = *pDocument->GetFormatTable()->GetNullDate();
    1186           0 :     Date aDate = aNullDate;
    1187           0 :     aDate += (long)rVal;
    1188           0 :     switch (eCmd)
    1189             :     {
    1190             :         case FILL_WEEKDAY:
    1191             :             {
    1192           0 :                 aDate += nInc;
    1193           0 :                 DayOfWeek eWeekDay = aDate.GetDayOfWeek();
    1194           0 :                 if (nInc >= 0)
    1195             :                 {
    1196           0 :                     if (eWeekDay == SATURDAY)
    1197           0 :                         aDate += 2;
    1198           0 :                     else if (eWeekDay == SUNDAY)
    1199           0 :                         aDate += 1;
    1200             :                 }
    1201             :                 else
    1202             :                 {
    1203           0 :                     if (eWeekDay == SATURDAY)
    1204           0 :                         aDate -= 1;
    1205           0 :                     else if (eWeekDay == SUNDAY)
    1206           0 :                         aDate -= 2;
    1207             :                 }
    1208             :             }
    1209           0 :             break;
    1210             :         case FILL_MONTH:
    1211             :             {
    1212           0 :                 if ( nDayOfMonth == 0 )
    1213           0 :                     nDayOfMonth = aDate.GetDay();       // init
    1214           0 :                 long nMonth = aDate.GetMonth();
    1215           0 :                 long nYear = aDate.GetYear();
    1216             : 
    1217           0 :                 nMonth += nInc;
    1218             : 
    1219           0 :                 if (nInc >= 0)
    1220             :                 {
    1221           0 :                     if (nMonth > 12)
    1222             :                     {
    1223           0 :                         long nYAdd = (nMonth-1) / 12;
    1224           0 :                         nMonth -= nYAdd * 12;
    1225           0 :                         nYear += nYAdd;
    1226             :                     }
    1227             :                 }
    1228             :                 else
    1229             :                 {
    1230           0 :                     if (nMonth < 1)
    1231             :                     {
    1232           0 :                         long nYAdd = 1 - nMonth / 12;       // positive
    1233           0 :                         nMonth += nYAdd * 12;
    1234           0 :                         nYear -= nYAdd;
    1235             :                     }
    1236             :                 }
    1237             : 
    1238           0 :                 if ( nYear < nMinYear )
    1239           0 :                     aDate = Date( 1,1, nMinYear );
    1240           0 :                 else if ( nYear > nMaxYear )
    1241           0 :                     aDate = Date( 31,12, nMaxYear );
    1242             :                 else
    1243             :                 {
    1244           0 :                     aDate.SetMonth((sal_uInt16) nMonth);
    1245           0 :                     aDate.SetYear((sal_uInt16) nYear);
    1246           0 :                     aDate.SetDay( std::min( Date::GetDaysInMonth( nMonth, nYear), nDayOfMonth ) );
    1247             :                 }
    1248             :             }
    1249           0 :             break;
    1250             :         case FILL_YEAR:
    1251             :             {
    1252           0 :                 long nYear = aDate.GetYear();
    1253           0 :                 nYear += nInc;
    1254           0 :                 if ( nYear < nMinYear )
    1255           0 :                     aDate = Date( 1,1, nMinYear );
    1256           0 :                 else if ( nYear > nMaxYear )
    1257           0 :                     aDate = Date( 31,12, nMaxYear );
    1258             :                 else
    1259           0 :                     aDate.SetYear((sal_uInt16) nYear);
    1260             :             }
    1261           0 :             break;
    1262             :         default:
    1263             :         {
    1264             :             // added to avoid warnings
    1265             :         }
    1266             :     }
    1267             : 
    1268           0 :     rVal = aDate - aNullDate;
    1269             : }
    1270             : 
    1271             : namespace
    1272             : {
    1273             : 
    1274         146 : bool HiddenRowColumn(sal_uLong nRowColumn, bool bVertical, ScTable* pTable)
    1275             : {
    1276         146 :     if(bVertical)
    1277             :     {
    1278          66 :         return pTable->RowHidden(static_cast<SCROW>(nRowColumn));
    1279             :     }
    1280             :     else
    1281             :     {
    1282          80 :         return pTable->ColHidden(static_cast<SCCOL>(nRowColumn));
    1283             :     }
    1284             : }
    1285             : 
    1286             : }
    1287             : 
    1288          16 : void ScTable::FillSeries( SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
    1289             :                     sal_uLong nFillCount, FillDir eFillDir, FillCmd eFillCmd, FillDateCmd eFillDateCmd,
    1290             :                     double nStepValue, double nMaxValue, sal_uInt16 nArgMinDigits,
    1291             :                     bool bAttribs, ScProgress* pProgress )
    1292             : {
    1293             :     //
    1294             :     //  Detect direction
    1295             :     //
    1296             : 
    1297          16 :     bool bVertical = (eFillDir == FILL_TO_BOTTOM || eFillDir == FILL_TO_TOP);
    1298          16 :     bool bPositive = (eFillDir == FILL_TO_BOTTOM || eFillDir == FILL_TO_RIGHT);
    1299             : 
    1300          16 :     sal_uLong nCol = 0;
    1301          16 :     sal_uLong nRow = 0;
    1302          16 :     sal_uLong& rInner = bVertical ? nRow : nCol;        // loop variables
    1303          16 :     sal_uLong& rOuter = bVertical ? nCol : nRow;
    1304             :     sal_uLong nOStart;
    1305             :     sal_uLong nOEnd;
    1306             :     sal_uLong nIStart;
    1307             :     sal_uLong nIEnd;
    1308             :     sal_uLong nISource;
    1309          16 :     ScRange aFillRange;
    1310             : 
    1311          16 :     if (bVertical)
    1312             :     {
    1313           8 :         nFillCount += (nRow2 - nRow1);
    1314           8 :         if (nFillCount == 0)
    1315           0 :             return;
    1316           8 :         nOStart = nCol1;
    1317           8 :         nOEnd = nCol2;
    1318           8 :         if (bPositive)
    1319             :         {
    1320           6 :             nISource = nRow1;
    1321           6 :             nIStart = nRow1 + 1;
    1322           6 :             nIEnd = nRow1 + nFillCount;
    1323           6 :             aFillRange = ScRange(nCol1, nRow1 + 1, nTab, nCol2, nRow1 + nFillCount, nTab);
    1324             :         }
    1325             :         else
    1326             :         {
    1327           2 :             nISource = nRow2;
    1328           2 :             nIStart = nRow2 - 1;
    1329           2 :             nIEnd = nRow2 - nFillCount;
    1330           2 :             aFillRange = ScRange(nCol1, nRow2 -1, nTab, nCol2, nRow2 - nFillCount, nTab);
    1331             :         }
    1332             :     }
    1333             :     else
    1334             :     {
    1335           8 :         nFillCount += (nCol2 - nCol1);
    1336           8 :         if (nFillCount == 0)
    1337           0 :             return;
    1338           8 :         nOStart = nRow1;
    1339           8 :         nOEnd = nRow2;
    1340           8 :         if (bPositive)
    1341             :         {
    1342           6 :             nISource = nCol1;
    1343           6 :             nIStart = nCol1 + 1;
    1344           6 :             nIEnd = nCol1 + nFillCount;
    1345           6 :             aFillRange = ScRange(nCol1 + 1, nRow1, nTab, nCol1 + nFillCount, nRow2, nTab);
    1346             :         }
    1347             :         else
    1348             :         {
    1349           2 :             nISource = nCol2;
    1350           2 :             nIStart = nCol2 - 1;
    1351           2 :             nIEnd = nCol2 - nFillCount;
    1352           2 :             aFillRange = ScRange(nCol2 - 1, nRow1, nTab, nCol2 - nFillCount, nRow2, nTab);
    1353             :         }
    1354             :     }
    1355             : 
    1356          16 :     sal_uLong nIMin = nIStart;
    1357          16 :     sal_uLong nIMax = nIEnd;
    1358          16 :     PutInOrder(nIMin,nIMax);
    1359          16 :     sal_uInt16 nDel = bAttribs ? IDF_AUTOFILL : (IDF_AUTOFILL & IDF_CONTENTS);
    1360             : 
    1361          16 :     bool bIsFiltered = IsDataFiltered(aFillRange);
    1362          16 :     if (!bIsFiltered)
    1363             :     {
    1364          14 :         if (bVertical)
    1365           7 :             DeleteArea(nCol1, static_cast<SCROW>(nIMin), nCol2, static_cast<SCROW>(nIMax), nDel);
    1366             :         else
    1367           7 :             DeleteArea(static_cast<SCCOL>(nIMin), nRow1, static_cast<SCCOL>(nIMax), nRow2, nDel);
    1368             :     }
    1369             : 
    1370          16 :     sal_uLong nProgress = 0;
    1371          16 :     if (pProgress)
    1372          13 :         nProgress = pProgress->GetState();
    1373             : 
    1374             :     //
    1375             :     //  execute
    1376             :     //
    1377             : 
    1378          16 :     sal_uLong nActFormCnt = 0;
    1379          88 :     for (rOuter = nOStart; rOuter <= nOEnd; rOuter++)
    1380             :     {
    1381          72 :         rInner = nISource;
    1382             : 
    1383             :         // Source cell value. We need to clone the value since it may be inserted repeatedly.
    1384          72 :         ScCellValue aSrcCell = aCol[nCol].GetCellValue(static_cast<SCROW>(nRow));
    1385             : 
    1386          72 :         if (bAttribs)
    1387             :         {
    1388          72 :             const ScPatternAttr* pSrcPattern = aCol[nCol].GetPattern(static_cast<SCROW>(nRow));
    1389             : 
    1390          72 :             const ScCondFormatItem& rCondFormatItem = static_cast<const ScCondFormatItem&>(pSrcPattern->GetItem(ATTR_CONDITIONAL));
    1391          72 :             const std::vector<sal_uInt32>& rCondFormatIndex = rCondFormatItem.GetCondFormatData();
    1392             : 
    1393          72 :             if (bVertical)
    1394             :             {
    1395             :                 // if not filtered use the faster method
    1396             :                 // hidden cols/rows should be skiped
    1397          26 :                 if(!bIsFiltered)
    1398             :                 {
    1399          25 :                     aCol[nCol].SetPatternArea( static_cast<SCROW>(nIMin),
    1400          50 :                             static_cast<SCROW>(nIMax), *pSrcPattern, true );
    1401             : 
    1402          25 :                     for(std::vector<sal_uInt32>::const_iterator itr = rCondFormatIndex.begin(), itrEnd = rCondFormatIndex.end();
    1403             :                             itr != itrEnd; ++itr)
    1404             :                     {
    1405           0 :                         ScConditionalFormat* pCondFormat = mpCondFormatList->GetFormat(*itr);
    1406           0 :                         ScRangeList aRange = pCondFormat->GetRange();
    1407           0 :                         aRange.Join(ScRange(nCol, nIMin, nTab, nCol, nIMax, nTab));
    1408           0 :                         pCondFormat->AddRange(aRange);
    1409           0 :                     }
    1410             :                 }
    1411             :                 else
    1412             :                 {
    1413           9 :                     for(SCROW nAtRow = static_cast<SCROW>(nIMin); nAtRow <= static_cast<SCROW>(nIMax); ++nAtRow)
    1414             :                     {
    1415           8 :                         if(!RowHidden(nAtRow))
    1416             :                         {
    1417           6 :                             aCol[nCol].SetPatternArea( static_cast<SCROW>(nAtRow),
    1418           6 :                                     static_cast<SCROW>(nAtRow), *pSrcPattern, true);
    1419           6 :                             for(std::vector<sal_uInt32>::const_iterator itr = rCondFormatIndex.begin(), itrEnd = rCondFormatIndex.end();
    1420             :                                     itr != itrEnd; ++itr)
    1421             :                             {
    1422           0 :                                 ScConditionalFormat* pCondFormat = mpCondFormatList->GetFormat(*itr);
    1423           0 :                                 ScRangeList aRange = pCondFormat->GetRange();
    1424           0 :                                 aRange.Join(ScRange(nCol, nAtRow, nTab, nCol, nAtRow, nTab));
    1425           0 :                                 pCondFormat->AddRange(aRange);
    1426           0 :                             }
    1427             :                         }
    1428             :                     }
    1429             : 
    1430             :                 }
    1431             :             }
    1432             :             else
    1433         203 :                 for (SCCOL nAtCol = static_cast<SCCOL>(nIMin); nAtCol <= sal::static_int_cast<SCCOL>(nIMax); nAtCol++)
    1434         157 :                     if(!ColHidden(nAtCol))
    1435             :                     {
    1436         157 :                         aCol[nAtCol].SetPattern(static_cast<SCROW>(nRow), *pSrcPattern, true);
    1437         157 :                         for(std::vector<sal_uInt32>::const_iterator itr = rCondFormatIndex.begin(), itrEnd = rCondFormatIndex.end();
    1438             :                                 itr != itrEnd; ++itr)
    1439             :                         {
    1440           0 :                             ScConditionalFormat* pCondFormat = mpCondFormatList->GetFormat(*itr);
    1441           0 :                             ScRangeList aRange = pCondFormat->GetRange();
    1442           0 :                             aRange.Join(ScRange(nAtCol, static_cast<SCROW>(nRow), nTab, nAtCol, static_cast<SCROW>(nRow), nTab));
    1443           0 :                             pCondFormat->AddRange(aRange);
    1444           0 :                         }
    1445             :                     }
    1446             :         }
    1447             : 
    1448          72 :         if (!aSrcCell.isEmpty())
    1449             :         {
    1450          60 :             CellType eCellType = aSrcCell.meType;
    1451             : 
    1452          60 :             if (eFillCmd == FILL_SIMPLE)                // copy
    1453             :             {
    1454          38 :                 if (eCellType == CELLTYPE_FORMULA)
    1455             :                 {
    1456           0 :                     bool bFirst = true;
    1457           0 :                     for (rInner = nIMin; rInner <= nIMax; rInner++)
    1458             :                     {
    1459           0 :                         if(HiddenRowColumn(rInner, bVertical, this))
    1460           0 :                             continue;
    1461           0 :                         sal_uLong nInd = nActFormCnt;
    1462             :                         FillFormula(nInd, bFirst, aSrcCell.mpFormula,
    1463           0 :                             static_cast<SCCOL>(nCol), nRow, (rInner == nIEnd) );
    1464           0 :                         bFirst = false;
    1465           0 :                         if(pProgress)
    1466           0 :                             pProgress->SetStateOnPercent( ++nProgress );
    1467             :                     }
    1468             :                 }
    1469             :                 else
    1470             :                 {
    1471         184 :                     for (rInner = nIMin; rInner <= nIMax; rInner++)
    1472             :                     {
    1473         146 :                         if(HiddenRowColumn(rInner, bVertical, this))
    1474           0 :                             continue;
    1475         146 :                         ScAddress aDestPos( static_cast<SCCOL>(nCol), static_cast<SCROW>(nRow), nTab );
    1476         146 :                         aSrcCell.commit(aCol[nCol], aDestPos.Row());
    1477             :                     }
    1478          38 :                     nProgress += nIMax - nIMin + 1;
    1479          38 :                     if(pProgress)
    1480          38 :                         pProgress->SetStateOnPercent( nProgress );
    1481             :                 }
    1482             :             }
    1483          22 :             else if (eCellType == CELLTYPE_VALUE || eCellType == CELLTYPE_FORMULA)
    1484             :             {
    1485             :                 double nStartVal;
    1486          22 :                 if (eCellType == CELLTYPE_VALUE)
    1487          21 :                     nStartVal = aSrcCell.mfValue;
    1488             :                 else
    1489           1 :                     nStartVal = aSrcCell.mpFormula->GetValue();
    1490          22 :                 double nVal = nStartVal;
    1491          22 :                 long nIndex = 0;
    1492             : 
    1493          22 :                 bool bError = false;
    1494          22 :                 bool bOverflow = false;
    1495             : 
    1496          22 :                 sal_uInt16 nDayOfMonth = 0;
    1497          22 :                 rInner = nIStart;
    1498             :                 while (true)        // #i53728# with "for (;;)" old solaris/x86 compiler mis-optimizes
    1499             :                 {
    1500          99 :                     if(!ColHidden(nCol) && !RowHidden(nRow))
    1501             :                     {
    1502          87 :                         if (!bError && !bOverflow)
    1503             :                         {
    1504          72 :                             switch (eFillCmd)
    1505             :                             {
    1506             :                                 case FILL_LINEAR:
    1507             :                                     {
    1508             :                                         //  use multiplication instead of repeated addition
    1509             :                                         //  to avoid accumulating rounding errors
    1510          58 :                                         nVal = nStartVal;
    1511          58 :                                         double nAdd = nStepValue;
    1512         116 :                                         if ( !SubTotal::SafeMult( nAdd, (double) ++nIndex ) ||
    1513          58 :                                                 !SubTotal::SafePlus( nVal, nAdd ) )
    1514           0 :                                             bError = true;
    1515             :                                     }
    1516          58 :                                     break;
    1517             :                                 case FILL_GROWTH:
    1518          14 :                                     if (!SubTotal::SafeMult(nVal, nStepValue))
    1519           0 :                                         bError = true;
    1520          14 :                                     break;
    1521             :                                 case FILL_DATE:
    1522           0 :                                     if (fabs(nVal) > _D_MAX_LONG_)
    1523           0 :                                         bError = true;
    1524             :                                     else
    1525           0 :                                         IncDate(nVal, nDayOfMonth, nStepValue, eFillDateCmd);
    1526           0 :                                     break;
    1527             :                                 default:
    1528             :                                     {
    1529             :                                         // added to avoid warnings
    1530             :                                     }
    1531             :                             }
    1532             : 
    1533          72 :                             if (nStepValue >= 0)
    1534             :                             {
    1535          72 :                                 if (nVal > nMaxValue)           // target value reached ?
    1536             :                                 {
    1537           9 :                                     nVal = nMaxValue;
    1538           9 :                                     bOverflow = true;
    1539             :                                 }
    1540             :                             }
    1541             :                             else
    1542             :                             {
    1543           0 :                                 if (nVal < nMaxValue)
    1544             :                                 {
    1545           0 :                                     nVal = nMaxValue;
    1546           0 :                                     bOverflow = true;
    1547             :                                 }
    1548             :                             }
    1549             :                         }
    1550             : 
    1551          87 :                         if (bError)
    1552           0 :                             aCol[nCol].SetError(static_cast<SCROW>(nRow), errNoValue);
    1553          87 :                         else if (bOverflow)
    1554          24 :                             aCol[nCol].SetError(static_cast<SCROW>(nRow), errIllegalFPOperation);
    1555             :                         else
    1556          63 :                             aCol[nCol].SetValue(static_cast<SCROW>(nRow), nVal);
    1557             :                     }
    1558             : 
    1559          99 :                     if (rInner == nIEnd)
    1560          22 :                         break;
    1561          77 :                     if (bPositive)
    1562             :                     {
    1563          77 :                         ++rInner;
    1564             :                     }
    1565             :                     else
    1566             :                     {
    1567           0 :                         --rInner;
    1568             :                     }
    1569             :                 }
    1570          22 :                 nProgress += nIMax - nIMin + 1;
    1571          22 :                 if(pProgress)
    1572          88 :                     pProgress->SetStateOnPercent( nProgress );
    1573             :             }
    1574           0 :             else if (eCellType == CELLTYPE_STRING || eCellType == CELLTYPE_EDIT)
    1575             :             {
    1576           0 :                 if ( nStepValue >= 0 )
    1577             :                 {
    1578           0 :                     if ( nMaxValue >= (double)LONG_MAX )
    1579           0 :                         nMaxValue = (double)LONG_MAX - 1;
    1580             :                 }
    1581             :                 else
    1582             :                 {
    1583           0 :                     if ( nMaxValue <= (double)LONG_MIN )
    1584           0 :                         nMaxValue = (double)LONG_MIN + 1;
    1585             :                 }
    1586           0 :                 String aValue;
    1587           0 :                 if (eCellType == CELLTYPE_STRING)
    1588           0 :                     aValue = *aSrcCell.mpString;
    1589             :                 else
    1590           0 :                     aValue = ScEditUtil::GetString(*aSrcCell.mpEditText);
    1591             :                 sal_Int32 nStringValue;
    1592           0 :                 sal_uInt16 nMinDigits = nArgMinDigits;
    1593           0 :                 short nHeadNoneTail = lcl_DecompValueString( aValue, nStringValue, &nMinDigits );
    1594           0 :                 if ( nHeadNoneTail )
    1595             :                 {
    1596           0 :                     double nStartVal = (double)nStringValue;
    1597           0 :                     double nVal = nStartVal;
    1598           0 :                     long nIndex = 0;
    1599           0 :                     bool bError = false;
    1600           0 :                     bool bOverflow = false;
    1601             : 
    1602             :                     bool bIsOrdinalSuffix = aValue.Equals( ScGlobal::GetOrdinalSuffix(
    1603           0 :                                 (sal_Int32)nStartVal));
    1604             : 
    1605           0 :                     rInner = nIStart;
    1606             :                     while (true)        // #i53728# with "for (;;)" old solaris/x86 compiler mis-optimizes
    1607             :                     {
    1608           0 :                         if(!ColHidden(nCol) && !RowHidden(nRow))
    1609             :                         {
    1610           0 :                             if (!bError && !bOverflow)
    1611             :                             {
    1612           0 :                                 switch (eFillCmd)
    1613             :                                 {
    1614             :                                     case FILL_LINEAR:
    1615             :                                         {
    1616             :                                             //  use multiplication instead of repeated addition
    1617             :                                             //  to avoid accumulating rounding errors
    1618           0 :                                             nVal = nStartVal;
    1619           0 :                                             double nAdd = nStepValue;
    1620           0 :                                             if ( !SubTotal::SafeMult( nAdd, (double) ++nIndex ) ||
    1621           0 :                                                     !SubTotal::SafePlus( nVal, nAdd ) )
    1622           0 :                                                 bError = true;
    1623             :                                         }
    1624           0 :                                         break;
    1625             :                                     case FILL_GROWTH:
    1626           0 :                                         if (!SubTotal::SafeMult(nVal, nStepValue))
    1627           0 :                                             bError = true;
    1628           0 :                                         break;
    1629             :                                     default:
    1630             :                                         {
    1631             :                                             // added to avoid warnings
    1632             :                                         }
    1633             :                                 }
    1634             : 
    1635           0 :                                 if (nStepValue >= 0)
    1636             :                                 {
    1637           0 :                                     if (nVal > nMaxValue)           // target value reached ?
    1638             :                                     {
    1639           0 :                                         nVal = nMaxValue;
    1640           0 :                                         bOverflow = true;
    1641             :                                     }
    1642             :                                 }
    1643             :                                 else
    1644             :                                 {
    1645           0 :                                     if (nVal < nMaxValue)
    1646             :                                     {
    1647           0 :                                         nVal = nMaxValue;
    1648           0 :                                         bOverflow = true;
    1649             :                                     }
    1650             :                                 }
    1651             :                             }
    1652             : 
    1653           0 :                             if (bError)
    1654           0 :                                 aCol[nCol].SetError(static_cast<SCROW>(nRow), errNoValue);
    1655           0 :                             else if (bOverflow)
    1656           0 :                                 aCol[nCol].SetError(static_cast<SCROW>(nRow), errIllegalFPOperation);
    1657             :                             else
    1658             :                             {
    1659           0 :                                 nStringValue = (sal_Int32)nVal;
    1660           0 :                                 String aStr;
    1661           0 :                                 if ( nHeadNoneTail < 0 )
    1662             :                                 {
    1663             :                                     setSuffixCell(
    1664           0 :                                         aCol[nCol], static_cast<SCROW>(nRow),
    1665             :                                         nStringValue, nMinDigits, aValue,
    1666           0 :                                         eCellType, bIsOrdinalSuffix);
    1667             :                                 }
    1668             :                                 else
    1669             :                                 {
    1670           0 :                                     aStr = aValue;
    1671           0 :                                     aStr += lcl_ValueString( nStringValue, nMinDigits );
    1672           0 :                                     aCol[nCol].SetRawString(static_cast<SCROW>(nRow), aStr);
    1673           0 :                                 }
    1674             :                             }
    1675             :                         }
    1676             : 
    1677           0 :                         if (rInner == nIEnd) break;
    1678           0 :                         if (bPositive) ++rInner; else --rInner;
    1679           0 :                     }
    1680             :                 }
    1681           0 :                 if(pProgress)
    1682             :                 {
    1683           0 :                     nProgress += nIMax - nIMin + 1;
    1684           0 :                     pProgress->SetStateOnPercent( nProgress );
    1685           0 :                 }
    1686             :             }
    1687             :         }
    1688          12 :         else if(pProgress)
    1689             :         {
    1690          12 :             nProgress += nIMax - nIMin + 1;
    1691          12 :             pProgress->SetStateOnPercent( nProgress );
    1692             :         }
    1693          72 :         ++nActFormCnt;
    1694          72 :     }
    1695             : }
    1696             : 
    1697          20 : void ScTable::Fill( SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
    1698             :                     sal_uLong nFillCount, FillDir eFillDir, FillCmd eFillCmd, FillDateCmd eFillDateCmd,
    1699             :                     double nStepValue, double nMaxValue, ScProgress* pProgress)
    1700             : {
    1701          20 :     if (eFillCmd == FILL_AUTO)
    1702           4 :         FillAuto(nCol1, nRow1, nCol2, nRow2, nFillCount, eFillDir, pProgress);
    1703             :     else
    1704             :         FillSeries(nCol1, nRow1, nCol2, nRow2, nFillCount, eFillDir,
    1705          16 :                     eFillCmd, eFillDateCmd, nStepValue, nMaxValue, 0, true, pProgress);
    1706          20 : }
    1707             : 
    1708             : 
    1709           0 : void ScTable::AutoFormatArea(SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
    1710             :                                 const ScPatternAttr& rAttr, sal_uInt16 nFormatNo)
    1711             : {
    1712           0 :     ScAutoFormat& rFormat = *ScGlobal::GetOrCreateAutoFormat();
    1713           0 :     ScAutoFormatData* pData = rFormat.findByIndex(nFormatNo);
    1714           0 :     if (pData)
    1715             :     {
    1716           0 :         ApplyPatternArea(nStartCol, nStartRow, nEndCol, nEndRow, rAttr);
    1717             :     }
    1718           0 : }
    1719             : 
    1720           0 : void ScTable::AutoFormat( SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow,
    1721             :                             sal_uInt16 nFormatNo )
    1722             : {
    1723           0 :     if (ValidColRow(nStartCol, nStartRow) && ValidColRow(nEndCol, nEndRow))
    1724             :     {
    1725           0 :         ScAutoFormat& rFormat = *ScGlobal::GetOrCreateAutoFormat();
    1726           0 :         ScAutoFormatData* pData = rFormat.findByIndex(nFormatNo);
    1727           0 :         if (pData)
    1728             :         {
    1729             :             ScPatternAttr* pPatternAttrs[16];
    1730           0 :             for (sal_uInt8 i = 0; i < 16; ++i)
    1731             :             {
    1732           0 :                 pPatternAttrs[i] = new ScPatternAttr(pDocument->GetPool());
    1733           0 :                 pData->FillToItemSet(i, pPatternAttrs[i]->GetItemSet(), *pDocument);
    1734             :             }
    1735             : 
    1736           0 :             SCCOL nCol = nStartCol;
    1737           0 :             SCROW nRow = nStartRow;
    1738           0 :             sal_uInt16 nIndex = 0;
    1739             :             // Left top corner
    1740           0 :             AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1741             :             // Left column
    1742           0 :             if (pData->IsEqualData(4, 8))
    1743           0 :                 AutoFormatArea(nStartCol, nStartRow + 1, nStartCol, nEndRow - 1, *pPatternAttrs[4], nFormatNo);
    1744             :             else
    1745             :             {
    1746           0 :                 nIndex = 4;
    1747           0 :                 for (nRow = nStartRow + 1; nRow < nEndRow; nRow++)
    1748             :                 {
    1749           0 :                     AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1750           0 :                     if (nIndex == 4)
    1751           0 :                         nIndex = 8;
    1752             :                     else
    1753           0 :                         nIndex = 4;
    1754             :                 }
    1755             :             }
    1756             :             // Left bottom corner
    1757           0 :             nRow = nEndRow;
    1758           0 :             nIndex = 12;
    1759           0 :             AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1760             :             // Right top corner
    1761           0 :             nCol = nEndCol;
    1762           0 :             nRow = nStartRow;
    1763           0 :             nIndex = 3;
    1764           0 :             AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1765             :             // Right column
    1766           0 :             if (pData->IsEqualData(7, 11))
    1767           0 :                 AutoFormatArea(nEndCol, nStartRow + 1, nEndCol, nEndRow - 1, *pPatternAttrs[7], nFormatNo);
    1768             :             else
    1769             :             {
    1770           0 :                 nIndex = 7;
    1771           0 :                 for (nRow = nStartRow + 1; nRow < nEndRow; nRow++)
    1772             :                 {
    1773           0 :                     AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1774           0 :                     if (nIndex == 7)
    1775           0 :                         nIndex = 11;
    1776             :                     else
    1777           0 :                         nIndex = 7;
    1778             :                 }
    1779             :             }
    1780             :             // Right bottom corner
    1781           0 :             nRow = nEndRow;
    1782           0 :             nIndex = 15;
    1783           0 :             AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1784           0 :             nRow = nStartRow;
    1785           0 :             nIndex = 1;
    1786           0 :             for (nCol = nStartCol + 1; nCol < nEndCol; nCol++)
    1787             :             {
    1788           0 :                 AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1789           0 :                 if (nIndex == 1)
    1790           0 :                     nIndex = 2;
    1791             :                 else
    1792           0 :                     nIndex = 1;
    1793             :             }
    1794             :             // Bottom row
    1795           0 :             nRow = nEndRow;
    1796           0 :             nIndex = 13;
    1797           0 :             for (nCol = nStartCol + 1; nCol < nEndCol; nCol++)
    1798             :             {
    1799           0 :                 AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1800           0 :                 if (nIndex == 13)
    1801           0 :                     nIndex = 14;
    1802             :                 else
    1803           0 :                     nIndex = 13;
    1804             :             }
    1805             :             // Boddy
    1806           0 :             if ((pData->IsEqualData(5, 6)) && (pData->IsEqualData(9, 10)) && (pData->IsEqualData(5, 9)))
    1807           0 :                 AutoFormatArea(nStartCol + 1, nStartRow + 1, nEndCol-1, nEndRow - 1, *pPatternAttrs[5], nFormatNo);
    1808             :             else
    1809             :             {
    1810           0 :                 if ((pData->IsEqualData(5, 9)) && (pData->IsEqualData(6, 10)))
    1811             :                 {
    1812           0 :                     nIndex = 5;
    1813           0 :                     for (nCol = nStartCol + 1; nCol < nEndCol; nCol++)
    1814             :                     {
    1815           0 :                         AutoFormatArea(nCol, nStartRow + 1, nCol, nEndRow - 1, *pPatternAttrs[nIndex], nFormatNo);
    1816           0 :                         if (nIndex == 5)
    1817           0 :                             nIndex = 6;
    1818             :                         else
    1819           0 :                             nIndex = 5;
    1820             :                     }
    1821             :                 }
    1822             :                 else
    1823             :                 {
    1824           0 :                     nIndex = 5;
    1825           0 :                     for (nCol = nStartCol + 1; nCol < nEndCol; nCol++)
    1826             :                     {
    1827           0 :                         for (nRow = nStartRow + 1; nRow < nEndRow; nRow++)
    1828             :                         {
    1829           0 :                             AutoFormatArea(nCol, nRow, nCol, nRow, *pPatternAttrs[nIndex], nFormatNo);
    1830           0 :                             if ((nIndex == 5) || (nIndex == 9))
    1831             :                             {
    1832           0 :                                 if (nIndex == 5)
    1833           0 :                                     nIndex = 9;
    1834             :                                 else
    1835           0 :                                     nIndex = 5;
    1836             :                             }
    1837             :                             else
    1838             :                             {
    1839           0 :                                 if (nIndex == 6)
    1840           0 :                                     nIndex = 10;
    1841             :                                 else
    1842           0 :                                     nIndex = 6;
    1843             :                             }
    1844             :                         } // for nRow
    1845           0 :                         if ((nIndex == 5) || (nIndex == 9))
    1846           0 :                             nIndex = 6;
    1847             :                         else
    1848           0 :                             nIndex = 5;
    1849             :                     } // for nCol
    1850             :                 } // if not equal Column
    1851             :             } // if not all equal
    1852             : 
    1853           0 :             for (sal_uInt8 j = 0; j < 16; ++j)
    1854           0 :                 delete pPatternAttrs[j];
    1855             :         } // if AutoFormatData != NULL
    1856             :     } // if ValidColRow
    1857           0 : }
    1858             : 
    1859           0 : void ScTable::GetAutoFormatAttr(SCCOL nCol, SCROW nRow, sal_uInt16 nIndex, ScAutoFormatData& rData)
    1860             : {
    1861           0 :     sal_uInt32 nFormatIndex = GetNumberFormat( nCol, nRow );
    1862           0 :     ScNumFormatAbbrev   aNumFormat( nFormatIndex, *pDocument->GetFormatTable() );
    1863           0 :     rData.GetFromItemSet( nIndex, GetPattern( nCol, nRow )->GetItemSet(), aNumFormat );
    1864           0 : }
    1865             : 
    1866             : #define LF_LEFT         1
    1867             : #define LF_TOP          2
    1868             : #define LF_RIGHT        4
    1869             : #define LF_BOTTOM       8
    1870             : #define LF_ALL          (LF_LEFT | LF_TOP | LF_RIGHT | LF_BOTTOM)
    1871             : 
    1872           0 : void ScTable::GetAutoFormatFrame(SCCOL nCol, SCROW nRow, sal_uInt16 nFlags, sal_uInt16 nIndex, ScAutoFormatData& rData)
    1873             : {
    1874           0 :     const SvxBoxItem* pTheBox = (SvxBoxItem*)GetAttr(nCol, nRow, ATTR_BORDER);
    1875           0 :     const SvxBoxItem* pLeftBox = (SvxBoxItem*)GetAttr(nCol - 1, nRow, ATTR_BORDER);
    1876           0 :     const SvxBoxItem* pTopBox = (SvxBoxItem*)GetAttr(nCol, nRow - 1, ATTR_BORDER);
    1877           0 :     const SvxBoxItem* pRightBox = (SvxBoxItem*)GetAttr(nCol + 1, nRow, ATTR_BORDER);
    1878           0 :     const SvxBoxItem* pBottomBox = (SvxBoxItem*)GetAttr(nCol, nRow + 1, ATTR_BORDER);
    1879             : 
    1880           0 :     SvxBoxItem aBox( ATTR_BORDER );
    1881           0 :     if (nFlags & LF_LEFT)
    1882             :     {
    1883           0 :         if (pLeftBox)
    1884             :         {
    1885           0 :             if (ScHasPriority(pTheBox->GetLeft(), pLeftBox->GetRight()))
    1886           0 :                 aBox.SetLine(pTheBox->GetLeft(), BOX_LINE_LEFT);
    1887             :             else
    1888           0 :                 aBox.SetLine(pLeftBox->GetRight(), BOX_LINE_LEFT);
    1889             :         }
    1890             :         else
    1891           0 :             aBox.SetLine(pTheBox->GetLeft(), BOX_LINE_LEFT);
    1892             :     }
    1893           0 :     if (nFlags & LF_TOP)
    1894             :     {
    1895           0 :         if (pTopBox)
    1896             :         {
    1897           0 :             if (ScHasPriority(pTheBox->GetTop(), pTopBox->GetBottom()))
    1898           0 :                 aBox.SetLine(pTheBox->GetTop(), BOX_LINE_TOP);
    1899             :             else
    1900           0 :                 aBox.SetLine(pTopBox->GetBottom(), BOX_LINE_TOP);
    1901             :         }
    1902             :         else
    1903           0 :             aBox.SetLine(pTheBox->GetTop(), BOX_LINE_TOP);
    1904             :     }
    1905           0 :     if (nFlags & LF_RIGHT)
    1906             :     {
    1907           0 :         if (pRightBox)
    1908             :         {
    1909           0 :             if (ScHasPriority(pTheBox->GetRight(), pRightBox->GetLeft()))
    1910           0 :                 aBox.SetLine(pTheBox->GetRight(), BOX_LINE_RIGHT);
    1911             :             else
    1912           0 :                 aBox.SetLine(pRightBox->GetLeft(), BOX_LINE_RIGHT);
    1913             :         }
    1914             :         else
    1915           0 :             aBox.SetLine(pTheBox->GetRight(), BOX_LINE_RIGHT);
    1916             :     }
    1917           0 :     if (nFlags & LF_BOTTOM)
    1918             :     {
    1919           0 :         if (pBottomBox)
    1920             :         {
    1921           0 :             if (ScHasPriority(pTheBox->GetBottom(), pBottomBox->GetTop()))
    1922           0 :                 aBox.SetLine(pTheBox->GetBottom(), BOX_LINE_BOTTOM);
    1923             :             else
    1924           0 :                 aBox.SetLine(pBottomBox->GetTop(), BOX_LINE_BOTTOM);
    1925             :         }
    1926             :         else
    1927           0 :             aBox.SetLine(pTheBox->GetBottom(), BOX_LINE_BOTTOM);
    1928             :     }
    1929           0 :     rData.PutItem( nIndex, aBox );
    1930           0 : }
    1931             : 
    1932           0 : void ScTable::GetAutoFormatData(SCCOL nStartCol, SCROW nStartRow, SCCOL nEndCol, SCROW nEndRow, ScAutoFormatData& rData)
    1933             : {
    1934           0 :     if (ValidColRow(nStartCol, nStartRow) && ValidColRow(nEndCol, nEndRow))
    1935             :     {
    1936           0 :         if ((nEndCol - nStartCol >= 3) && (nEndRow - nStartRow >= 3))
    1937             :         {
    1938             :             // Left top corner
    1939           0 :             GetAutoFormatAttr(nStartCol, nStartRow, 0, rData);
    1940           0 :             GetAutoFormatFrame(nStartCol, nStartRow, LF_ALL, 0, rData);
    1941             :             // Left column
    1942           0 :             GetAutoFormatAttr(nStartCol, nStartRow + 1, 4, rData);
    1943           0 :             GetAutoFormatAttr(nStartCol, nStartRow + 2, 8, rData);
    1944           0 :             GetAutoFormatFrame(nStartCol, nStartRow + 1, LF_LEFT | LF_RIGHT | LF_BOTTOM, 4, rData);
    1945           0 :             if (nEndRow - nStartRow >= 4)
    1946           0 :                 GetAutoFormatFrame(nStartCol, nStartRow + 2, LF_LEFT | LF_RIGHT | LF_BOTTOM, 8, rData);
    1947             :             else
    1948           0 :                 rData.CopyItem( 8, 4, ATTR_BORDER );
    1949             :             // Left bottom corner
    1950           0 :             GetAutoFormatAttr(nStartCol, nEndRow, 12, rData);
    1951           0 :             GetAutoFormatFrame(nStartCol, nEndRow, LF_ALL, 12, rData);
    1952             :             // Right top corner
    1953           0 :             GetAutoFormatAttr(nEndCol, nStartRow, 3, rData);
    1954           0 :             GetAutoFormatFrame(nEndCol, nStartRow, LF_ALL, 3, rData);
    1955             :             // Right column
    1956           0 :             GetAutoFormatAttr(nEndCol, nStartRow + 1, 7, rData);
    1957           0 :             GetAutoFormatAttr(nEndCol, nStartRow + 2, 11, rData);
    1958           0 :             GetAutoFormatFrame(nEndCol, nStartRow + 1, LF_LEFT | LF_RIGHT | LF_BOTTOM, 7, rData);
    1959           0 :             if (nEndRow - nStartRow >= 4)
    1960           0 :                 GetAutoFormatFrame(nEndCol, nStartRow + 2, LF_LEFT | LF_RIGHT | LF_BOTTOM, 11, rData);
    1961             :             else
    1962           0 :                 rData.CopyItem( 11, 7, ATTR_BORDER );
    1963             :             // Right bottom corner
    1964           0 :             GetAutoFormatAttr(nEndCol, nEndRow, 15, rData);
    1965           0 :             GetAutoFormatFrame(nEndCol, nEndRow, LF_ALL, 15, rData);
    1966             :             // Top row
    1967           0 :             GetAutoFormatAttr(nStartCol + 1, nStartRow, 1, rData);
    1968           0 :             GetAutoFormatAttr(nStartCol + 2, nStartRow, 2, rData);
    1969           0 :             GetAutoFormatFrame(nStartCol + 1, nStartRow, LF_TOP | LF_BOTTOM | LF_RIGHT, 1, rData);
    1970           0 :             if (nEndCol - nStartCol >= 4)
    1971           0 :                 GetAutoFormatFrame(nStartCol + 2, nStartRow, LF_TOP | LF_BOTTOM | LF_RIGHT, 2, rData);
    1972             :             else
    1973           0 :                 rData.CopyItem( 2, 1, ATTR_BORDER );
    1974             :             // Bottom row
    1975           0 :             GetAutoFormatAttr(nStartCol + 1, nEndRow, 13, rData);
    1976           0 :             GetAutoFormatAttr(nStartCol + 2, nEndRow, 14, rData);
    1977           0 :             GetAutoFormatFrame(nStartCol + 1, nEndRow, LF_TOP | LF_BOTTOM | LF_RIGHT, 13, rData);
    1978           0 :             if (nEndCol - nStartCol >= 4)
    1979           0 :                 GetAutoFormatFrame(nStartCol + 2, nEndRow, LF_TOP | LF_BOTTOM | LF_RIGHT, 14, rData);
    1980             :             else
    1981           0 :                 rData.CopyItem( 14, 13, ATTR_BORDER );
    1982             :             // Body
    1983           0 :             GetAutoFormatAttr(nStartCol + 1, nStartRow + 1, 5, rData);
    1984           0 :             GetAutoFormatAttr(nStartCol + 2, nStartRow + 1, 6, rData);
    1985           0 :             GetAutoFormatAttr(nStartCol + 1, nStartRow + 2, 9, rData);
    1986           0 :             GetAutoFormatAttr(nStartCol + 2, nStartRow + 2, 10, rData);
    1987           0 :             GetAutoFormatFrame(nStartCol + 1, nStartRow + 1, LF_RIGHT | LF_BOTTOM, 5, rData);
    1988           0 :             if ((nEndCol - nStartCol >= 4) && (nEndRow - nStartRow >= 4))
    1989             :             {
    1990           0 :                 GetAutoFormatFrame(nStartCol + 2, nStartRow + 1, LF_RIGHT | LF_BOTTOM, 6, rData);
    1991           0 :                 GetAutoFormatFrame(nStartCol + 1, nStartRow + 2, LF_RIGHT | LF_BOTTOM, 9, rData);
    1992           0 :                 GetAutoFormatFrame(nStartCol + 2, nStartRow + 2, LF_RIGHT | LF_BOTTOM, 10, rData);
    1993             :             }
    1994             :             else
    1995             :             {
    1996           0 :                 rData.CopyItem( 6, 5, ATTR_BORDER );
    1997           0 :                 rData.CopyItem( 9, 5, ATTR_BORDER );
    1998           0 :                 rData.CopyItem( 10, 5, ATTR_BORDER );
    1999             :             }
    2000             :         }
    2001             :     }
    2002           0 : }
    2003             : 
    2004           0 : void ScTable::SetError( SCCOL nCol, SCROW nRow, sal_uInt16 nError)
    2005             : {
    2006           0 :     if (ValidColRow(nCol, nRow))
    2007           0 :         aCol[nCol].SetError( nRow, nError );
    2008           0 : }
    2009             : 
    2010           4 : void ScTable::UpdateInsertTabAbs(SCTAB nTable)
    2011             : {
    2012        4100 :     for (SCCOL i=0; i <= MAXCOL; i++)
    2013        4096 :         aCol[i].UpdateInsertTabAbs(nTable);
    2014           4 : }
    2015             : 
    2016           0 : bool ScTable::GetNextSpellingCell(SCCOL& rCol, SCROW& rRow, bool bInSel,
    2017             :                                     const ScMarkData& rMark) const
    2018             : {
    2019           0 :     if (rRow == MAXROW+2)                       // end of table
    2020             :     {
    2021           0 :         rRow = 0;
    2022           0 :         rCol = 0;
    2023             :     }
    2024             :     else
    2025             :     {
    2026           0 :         rRow++;
    2027           0 :         if (rRow == MAXROW+1)
    2028             :         {
    2029           0 :             rCol++;
    2030           0 :             rRow = 0;
    2031             :         }
    2032             :     }
    2033           0 :     if (rCol == MAXCOL+1)
    2034           0 :         return true;
    2035             :     else
    2036             :     {
    2037           0 :         bool bStop = false;
    2038           0 :         while (!bStop)
    2039             :         {
    2040           0 :             if (ValidCol(rCol))
    2041             :             {
    2042           0 :                 bStop = aCol[rCol].GetNextSpellingCell(rRow, bInSel, rMark);
    2043           0 :                 if (bStop)
    2044           0 :                     return true;
    2045             :                 else /*if (rRow == MAXROW+1) */
    2046             :                 {
    2047           0 :                     rCol++;
    2048           0 :                     rRow = 0;
    2049             :                 }
    2050             :             }
    2051             :             else
    2052           0 :                 return true;
    2053             :         }
    2054             :     }
    2055           0 :     return false;
    2056             : }
    2057             : 
    2058           0 : void ScTable::RemoveAutoSpellObj()
    2059             : {
    2060           0 :     for (SCCOL i=0; i <= MAXCOL; i++)
    2061           0 :         aCol[i].RemoveAutoSpellObj();
    2062           0 : }
    2063             : 
    2064           1 : bool ScTable::TestTabRefAbs(SCTAB nTable) const
    2065             : {
    2066           4 :     for (SCCOL i=0; i <= MAXCOL; i++)
    2067           4 :         if (aCol[i].TestTabRefAbs(nTable))
    2068           1 :             return true;
    2069           0 :     return false;
    2070             : }
    2071             : 
    2072           9 : void ScTable::CompileDBFormula()
    2073             : {
    2074           9 :     for (SCCOL i=0; i<=MAXCOL; i++) aCol[i].CompileDBFormula();
    2075           9 : }
    2076             : 
    2077          16 : void ScTable::CompileDBFormula( bool bCreateFormulaString )
    2078             : {
    2079          16 :     for (SCCOL i=0; i<=MAXCOL; i++) aCol[i].CompileDBFormula( bCreateFormulaString );
    2080          16 : }
    2081             : 
    2082         202 : void ScTable::CompileNameFormula( bool bCreateFormulaString )
    2083             : {
    2084         202 :     for (SCCOL i=0; i<=MAXCOL; i++) aCol[i].CompileNameFormula( bCreateFormulaString );
    2085         202 : }
    2086             : 
    2087           7 : void ScTable::CompileColRowNameFormula()
    2088             : {
    2089           7 :     for (SCCOL i=0; i<=MAXCOL; i++) aCol[i].CompileColRowNameFormula();
    2090         100 : }
    2091             : 
    2092             : 
    2093             : 
    2094             : 
    2095             : 
    2096             : 
    2097             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10