fix baseline build (old cairo) - 'cairo_rectangle_int_t' does not name a type
[LibreOffice.git] / sc / source / filter / lotus / op.cxx
blobbc5b6901db91fb187d617ac06f63c55049f4e3c6
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include <rtl/math.hxx>
22 #include <stdio.h>
23 #include <string.h>
24 #include <math.h>
25 #include <ctype.h>
26 #include <stdlib.h>
28 #include "scitems.hxx"
29 #include "patattr.hxx"
30 #include "docpool.hxx"
31 #include <svx/algitem.hxx>
32 #include <editeng/postitem.hxx>
33 #include <editeng/udlnitem.hxx>
34 #include <editeng/wghtitem.hxx>
35 #include <editeng/justifyitem.hxx>
37 #include "formulacell.hxx"
38 #include "rangenam.hxx"
39 #include "document.hxx"
40 #include "postit.hxx"
42 #include "op.h"
43 #include "optab.h"
44 #include "tool.h"
45 #include "decl.h"
46 #include "lotfilter.hxx"
47 #include "lotform.hxx"
48 #include "lotrange.hxx"
49 #include "root.hxx"
50 #include "ftools.hxx"
52 #include <vector>
53 #include <map>
54 #include <boost/scoped_array.hpp>
56 static sal_uInt16 nDefWidth = ( sal_uInt16 ) ( TWIPS_PER_CHAR * 10 );
58 void NI(LotusContext& /*rContext*/, SvStream& r, sal_uInt16 n)
60 r.SeekRel( n );
63 void OP_BOF(LotusContext& /*rContext*/, SvStream& r, sal_uInt16 /*n*/)
65 r.SeekRel( 2 ); // skip version number
68 void OP_EOF(LotusContext& rContext, SvStream& /*r*/, sal_uInt16 /*n*/)
70 rContext.bEOF = true;
73 void OP_Integer(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
75 sal_uInt8 nFormat(0);
76 sal_uInt16 nTmpCol(0), nTmpRow(0);
77 sal_Int16 nValue(0);
78 r.ReadUChar(nFormat).ReadUInt16(nTmpCol).ReadUInt16(nTmpRow).ReadInt16(nValue);
79 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
80 SCROW nRow(static_cast<SCROW>(nTmpRow));
82 if (ValidColRow(nCol, nRow))
84 rContext.pDoc->EnsureTable(0);
85 rContext.pDoc->SetValue(ScAddress(nCol, nRow, 0), static_cast<double>(nValue));
87 // 0 decimal places!
88 SetFormat(rContext, nCol, nRow, 0, nFormat, 0);
92 void OP_Number(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
94 sal_uInt8 nFormat(0);
95 sal_uInt16 nTmpCol(0), nTmpRow(0);
96 double fValue(0.0);
97 r.ReadUChar( nFormat ).ReadUInt16(nTmpCol).ReadUInt16(nTmpRow).ReadDouble(fValue);
98 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
99 SCROW nRow(static_cast<SCROW>(nTmpRow));
101 if (ValidColRow(nCol, nRow))
103 fValue = ::rtl::math::round( fValue, 15 );
104 rContext.pDoc->EnsureTable(0);
105 rContext.pDoc->SetValue(ScAddress(nCol, nRow, 0), fValue);
107 SetFormat(rContext, nCol, nRow, 0, nFormat, nDezFloat);
111 void OP_Label(LotusContext& rContext, SvStream& r, sal_uInt16 n)
113 sal_uInt8 nFormat(0);
114 sal_uInt16 nTmpCol(0), nTmpRow(0);
115 r.ReadUChar(nFormat).ReadUInt16(nTmpCol).ReadUInt16(nTmpRow);
116 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
117 SCROW nRow(static_cast<SCROW>(nTmpRow));
119 n -= (n > 5) ? 5 : n;
121 boost::scoped_array<sal_Char> pText(new sal_Char[n + 1]);
122 r.Read( pText.get(), n );
123 pText[n] = 0;
125 if (ValidColRow(nCol, nRow))
127 nFormat &= 0x80; // don't change Bit 7
128 nFormat |= 0x75; // protected does not matter, special-text is set
130 PutFormString(rContext, nCol, nRow, 0, pText.get());
132 SetFormat(rContext, nCol, nRow, 0, nFormat, nDezStd);
136 void OP_Formula(LotusContext &rContext, SvStream& r, sal_uInt16 /*n*/)
138 sal_uInt8 nFormat(0);
139 sal_uInt16 nTmpCol(0), nTmpRow(0);
140 r.ReadUChar(nFormat).ReadUInt16(nTmpCol).ReadUInt16(nTmpRow);
141 r.SeekRel(8); // skip result
142 sal_uInt16 nFormulaSize(0);
143 r.ReadUInt16(nFormulaSize);
145 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
146 SCROW nRow(static_cast<SCROW>(nTmpRow));
148 const ScTokenArray* pErg;
149 sal_Int32 nBytesLeft = nFormulaSize;
150 ScAddress aAddress(nCol, nRow, 0);
152 svl::SharedStringPool& rSPool = rContext.pLotusRoot->pDoc->GetSharedStringPool();
153 LotusToSc aConv(rContext, r, rSPool, rContext.pLotusRoot->eCharsetQ, false);
154 aConv.Reset( aAddress );
155 aConv.Convert( pErg, nBytesLeft );
157 if (ValidColRow(nCol, nRow))
159 ScFormulaCell* pCell = new ScFormulaCell(rContext.pLotusRoot->pDoc, aAddress, *pErg);
160 pCell->AddRecalcMode( ScRecalcMode::ONLOAD_ONCE );
161 rContext.pDoc->EnsureTable(0);
162 rContext.pDoc->SetFormulaCell(ScAddress(nCol, nRow, 0), pCell);
164 // nFormat = Default -> decimal places like Float
165 SetFormat(rContext, nCol, nRow, 0, nFormat, nDezFloat);
169 void OP_ColumnWidth(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
171 sal_uInt16 nTmpCol(0);
172 sal_uInt8 nWidthSpaces(0);
173 r.ReadUInt16(nTmpCol).ReadUChar(nWidthSpaces);
174 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
176 if (ValidCol(nCol))
178 nCol = SanitizeCol(nCol);
180 sal_uInt16 nBreite;
181 if( nWidthSpaces )
182 // assuming 10cpi character set
183 nBreite = ( sal_uInt16 ) ( TWIPS_PER_CHAR * nWidthSpaces );
184 else
186 rContext.pDoc->SetColHidden(nCol, nCol, 0, true);
187 nBreite = nDefWidth;
190 rContext.pDoc->SetColWidth(nCol, 0, nBreite);
194 void OP_NamedRange(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
196 // POST: don't save for invalid coordinates
197 sal_uInt16 nColSt, nRowSt, nColEnd, nRowEnd;
199 sal_Char cPuffer[ 16+1 ];
200 r.Read( cPuffer, 16 );
201 cPuffer[ 16 ] = 0;
203 r.ReadUInt16( nColSt ).ReadUInt16( nRowSt ).ReadUInt16( nColEnd ).ReadUInt16( nRowEnd );
205 if (ValidColRow( static_cast<SCCOL>(nColSt), nRowSt) && ValidColRow( static_cast<SCCOL>(nColEnd), nRowEnd))
207 LotusRange* pRange;
209 if( nColSt == nColEnd && nRowSt == nRowEnd )
210 pRange = new LotusRange( static_cast<SCCOL> (nColSt), static_cast<SCROW> (nRowSt) );
211 else
212 pRange = new LotusRange( static_cast<SCCOL> (nColSt), static_cast<SCROW> (nRowSt),
213 static_cast<SCCOL> (nColEnd), static_cast<SCROW> (nRowEnd) );
215 sal_Char cBuf[sizeof(cPuffer)+1];
216 if( isdigit( *cPuffer ) )
217 { // first char in name is a number -> prepend 'A'
218 cBuf[0] = 'A';
219 strcpy( cBuf + 1, cPuffer ); // #100211# - checked
221 else
222 strcpy( cBuf, cPuffer ); // #100211# - checked
224 OUString aTmp( cBuf, strlen(cBuf), rContext.pLotusRoot->eCharsetQ );
226 aTmp = ScfTools::ConvertToScDefinedName( aTmp );
228 rContext.pLotusRoot->pRangeNames->Append( pRange, aTmp );
232 void OP_SymphNamedRange(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
234 // POST:don't save for invalid coordinates
235 sal_uInt16 nColSt, nRowSt, nColEnd, nRowEnd;
236 sal_uInt8 nType;
238 sal_Char cPuffer[ 16+1 ];
239 r.Read( cPuffer, 16 );
240 cPuffer[ 16 ] = 0;
242 r.ReadUInt16( nColSt ).ReadUInt16( nRowSt ).ReadUInt16( nColEnd ).ReadUInt16( nRowEnd ).ReadUChar( nType );
244 if (ValidColRow( static_cast<SCCOL>(nColSt), nRowSt) && ValidColRow( static_cast<SCCOL>(nColEnd), nRowEnd))
246 LotusRange* pRange;
248 if( nType )
249 pRange = new LotusRange( static_cast<SCCOL> (nColSt), static_cast<SCROW> (nRowSt) );
250 else
251 pRange = new LotusRange( static_cast<SCCOL> (nColSt), static_cast<SCROW> (nRowSt),
252 static_cast<SCCOL> (nColEnd), static_cast<SCROW> (nRowEnd) );
254 sal_Char cBuf[sizeof(cPuffer)+1];
255 if( isdigit( *cPuffer ) )
256 { // first char in name is a number -> prepend 'A'
257 cBuf[0] = 'A';
258 strcpy( cBuf + 1, cPuffer ); // #100211# - checked
260 else
261 strcpy( cBuf, cPuffer ); // #100211# - checked
263 OUString aTmp( cBuf, strlen(cBuf), rContext.pLotusRoot->eCharsetQ );
264 aTmp = ScfTools::ConvertToScDefinedName( aTmp );
266 rContext.pLotusRoot->pRangeNames->Append( pRange, aTmp );
270 void OP_Footer(LotusContext& /*rContext*/, SvStream& r, sal_uInt16 n)
272 r.SeekRel( n );
275 void OP_Header(LotusContext& /*rContext*/, SvStream& r, sal_uInt16 n)
277 r.SeekRel( n );
280 void OP_Margins(LotusContext& /*rContext*/, SvStream& r, sal_uInt16 n)
282 r.SeekRel( n );
285 void OP_HiddenCols(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
287 sal_uInt16 nByte, nBit;
288 SCCOL nCount;
289 sal_uInt8 nAkt;
290 nCount = 0;
292 for( nByte = 0 ; nByte < 32 ; nByte++ ) // 32 Bytes with ...
294 r.ReadUChar( nAkt );
295 for( nBit = 0 ; nBit < 8 ; nBit++ ) // ...each 8 Bits = 256 Bits
297 if( nAkt & 0x01 ) // is lowest Bit set?
299 // -> Hidden Col
300 rContext.pDoc->SetColHidden(nCount, nCount, 0, true);
303 nCount++;
304 nAkt = nAkt / 2; // the next please...
309 void OP_Window1(LotusContext& rContext, SvStream& r, sal_uInt16 n)
311 r.SeekRel( 4 ); // skip Cursor Pos
313 r.ReadUChar(rContext.nDefaultFormat);
315 r.SeekRel( 1 ); // skip 'unused'
317 r.ReadUInt16( nDefWidth );
319 r.SeekRel( n - 8 ); // skip the rest
321 nDefWidth = ( sal_uInt16 ) ( TWIPS_PER_CHAR * nDefWidth );
323 // instead of default, set all Cols in SC by hand
324 for( SCCOL nCol = 0 ; nCol <= MAXCOL ; nCol++ )
325 rContext.pDoc->SetColWidth( nCol, 0, nDefWidth );
328 void OP_Blank(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
330 sal_uInt8 nFormat(0);
331 sal_uInt16 nTmpCol(0), nTmpRow(0);
332 r.ReadUChar( nFormat ).ReadUInt16(nTmpCol).ReadUInt16(nTmpRow);
333 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
334 SCROW nRow(static_cast<SCROW>(nTmpRow));
336 SetFormat(rContext, nCol, nRow, 0, nFormat, nDezFloat);
339 void OP_BOF123(LotusContext& /*rContext*/, SvStream& r, sal_uInt16 /*n*/)
341 r.SeekRel( 26 );
344 void OP_EOF123(LotusContext& rContext, SvStream& /*r*/, sal_uInt16 /*n*/)
346 rContext.bEOF = true;
349 void OP_Label123(LotusContext& rContext, SvStream& r, sal_uInt16 n)
351 sal_uInt8 nTmpTab(0), nTmpCol(0);
352 sal_uInt16 nTmpRow(0);
353 r.ReadUInt16(nTmpRow).ReadUChar(nTmpTab).ReadUChar(nTmpCol);
354 SCTAB nTab(static_cast<SCTAB>(nTmpTab));
355 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
356 SCROW nRow(static_cast<SCROW>(nTmpRow));
358 n -= (n > 4) ? 4 : n;
360 boost::scoped_array<sal_Char> pText(new sal_Char[n + 1]);
361 r.Read( pText.get(), n );
362 pText[ n ] = 0;
364 PutFormString(rContext, nCol, nRow, nTab, pText.get());
367 void OP_Number123(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
369 sal_uInt16 nTmpRow(0);
370 sal_uInt8 nTmpCol(0), nTmpTab(0);
371 sal_uInt32 nValue(0);
372 r.ReadUInt16(nTmpRow).ReadUChar(nTmpTab).ReadUChar(nTmpCol).ReadUInt32(nValue);
373 SCTAB nTab(static_cast<SCTAB>(nTmpTab));
374 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
375 SCROW nRow(static_cast<SCROW>(nTmpRow));
377 if (ValidColRow(nCol, nRow) && nTab <= rContext.pDoc->GetMaxTableNumber())
379 double fValue = Snum32ToDouble( nValue );
380 rContext.pDoc->EnsureTable(nTab);
381 rContext.pDoc->SetValue(ScAddress(nCol,nRow,nTab), fValue);
385 void OP_Formula123(LotusContext& rContext, SvStream& r, sal_uInt16 n)
387 sal_uInt16 nTmpRow(0);
388 sal_uInt8 nTmpCol(0), nTmpTab(0);
389 r.ReadUInt16(nTmpRow).ReadUChar(nTmpTab).ReadUChar(nTmpCol);
390 SCTAB nTab(static_cast<SCTAB>(nTmpTab));
391 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
392 SCROW nRow(static_cast<SCROW>(nTmpRow));
393 r.SeekRel( 8 ); // skip Result
395 const ScTokenArray* pErg;
396 sal_Int32 nBytesLeft = (n > 12) ? n - 12 : 0;
397 ScAddress aAddress( nCol, nRow, nTab );
399 svl::SharedStringPool& rSPool = rContext.pLotusRoot->pDoc->GetSharedStringPool();
400 LotusToSc aConv(rContext, r, rSPool, rContext.pLotusRoot->eCharsetQ, true);
401 aConv.Reset( aAddress );
402 aConv.Convert( pErg, nBytesLeft );
404 if (ValidColRow(nCol, nRow) && nTab <= rContext.pDoc->GetMaxTableNumber())
406 ScFormulaCell* pCell = new ScFormulaCell(rContext.pLotusRoot->pDoc, aAddress, *pErg);
407 pCell->AddRecalcMode( ScRecalcMode::ONLOAD_ONCE );
408 rContext.pDoc->EnsureTable(nTab);
409 rContext.pDoc->SetFormulaCell(ScAddress(nCol,nRow,nTab), pCell);
413 void OP_IEEENumber123(LotusContext& rContext, SvStream& r, sal_uInt16 /*n*/)
415 sal_uInt16 nTmpRow(0);
416 sal_uInt8 nTmpCol(0), nTmpTab(0);
417 double dValue(0.0);
418 r.ReadUInt16(nTmpRow).ReadUChar(nTmpTab).ReadUChar(nTmpCol).ReadDouble(dValue);
419 SCTAB nTab(static_cast<SCTAB>(nTmpTab));
420 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
421 SCROW nRow(static_cast<SCROW>(nTmpRow));
423 if (ValidColRow(nCol, nRow) && nTab <= rContext.pDoc->GetMaxTableNumber())
425 rContext.pDoc->EnsureTable(nTab);
426 rContext.pDoc->SetValue(ScAddress(nCol,nRow,nTab), dValue);
430 void OP_Note123(LotusContext& rContext, SvStream& r, sal_uInt16 n)
432 sal_uInt16 nTmpRow(0);
433 sal_uInt8 nTmpTab(0), nTmpCol(0);
434 r.ReadUInt16(nTmpRow).ReadUChar(nTmpTab).ReadUChar(nTmpCol);
435 SCTAB nTab(static_cast<SCTAB>(nTmpTab));
436 SCCOL nCol(static_cast<SCCOL>(nTmpCol));
437 SCROW nRow(static_cast<SCROW>(nTmpRow));
439 n -= (n > 4) ? 4 : n;
441 boost::scoped_array<sal_Char> pText(new sal_Char[n + 1]);
442 r.Read( pText.get(), n );
443 pText[ n ] = 0;
445 OUString aNoteText(pText.get(), strlen(pText.get()), rContext.pLotusRoot->eCharsetQ);
446 pText.reset();
448 ScAddress aPos(nCol, nRow, nTab);
449 ScNoteUtil::CreateNoteFromString( *rContext.pDoc, aPos, aNoteText, false, false );
452 void OP_HorAlign123(LotusContext& /*rContext*/, sal_uInt8 nAlignPattern, SfxItemSet& rPatternItemSet)
454 // pre: Pattern is stored in the last 3 bites of the 21st byte
455 // post: Appropriate Horizontal Alignement is set in rPattern according to the bit pattern.
457 // LEFT:001, RIGHT:010, CENTER:011, JUSTIFY:110,
458 // LEFT-Text/RIGHT-NUMBER:100, DEFAULT:000
460 nAlignPattern = ( nAlignPattern & 0x07);
462 switch (nAlignPattern)
464 case 1:
465 rPatternItemSet.Put( SvxHorJustifyItem( SVX_HOR_JUSTIFY_LEFT, ATTR_HOR_JUSTIFY ) );
466 break;
467 case 2:
468 rPatternItemSet.Put( SvxHorJustifyItem( SVX_HOR_JUSTIFY_RIGHT, ATTR_HOR_JUSTIFY ) );
469 break;
470 case 3:
471 rPatternItemSet.Put( SvxHorJustifyItem( SVX_HOR_JUSTIFY_CENTER, ATTR_HOR_JUSTIFY) );
472 break;
473 case 4:
474 rPatternItemSet.Put( SvxHorJustifyItem( SVX_HOR_JUSTIFY_STANDARD, ATTR_HOR_JUSTIFY ) );
475 break;
476 case 6:
477 rPatternItemSet.Put( SvxHorJustifyItem( SVX_HOR_JUSTIFY_BLOCK, ATTR_HOR_JUSTIFY ) );
478 break;
479 default:
480 rPatternItemSet.Put( SvxHorJustifyItem( SVX_HOR_JUSTIFY_STANDARD, ATTR_HOR_JUSTIFY ) );
481 break;
485 void OP_VerAlign123(LotusContext& /*rContext*/, sal_uInt8 nAlignPattern, SfxItemSet& rPatternItemSet)
487 // pre: Pattern is stored in the last 3 bites of the 22nd byte
488 // post: Appropriate Verticle Alignement is set in rPattern according to the bit pattern.
490 // TOP:001, MIDDLE:010, DOWN:100, DEFAULT:000
492 nAlignPattern = ( nAlignPattern & 0x07);
494 switch (nAlignPattern)
496 case 0:
497 rPatternItemSet.Put( SvxVerJustifyItem(SVX_VER_JUSTIFY_STANDARD, ATTR_VER_JUSTIFY) );
498 break;
499 case 1:
500 rPatternItemSet.Put( SvxVerJustifyItem(SVX_VER_JUSTIFY_TOP, ATTR_VER_JUSTIFY) );
501 break;
502 case 2:
503 rPatternItemSet.Put( SvxVerJustifyItem(SVX_VER_JUSTIFY_CENTER, ATTR_VER_JUSTIFY) );
504 break;
505 case 4:
506 rPatternItemSet.Put( SvxVerJustifyItem(SVX_VER_JUSTIFY_BOTTOM, ATTR_VER_JUSTIFY) );
507 break;
508 default:
509 rPatternItemSet.Put( SvxVerJustifyItem(SVX_VER_JUSTIFY_STANDARD, ATTR_VER_JUSTIFY) );
510 break;
514 void OP_CreatePattern123(LotusContext& rContext, SvStream& r, sal_uInt16 n)
516 sal_uInt16 nCode,nPatternId;
518 ScPatternAttr aPattern(rContext.pDoc->GetPool());
519 SfxItemSet& rItemSet = aPattern.GetItemSet();
521 r.ReadUInt16( nCode );
522 n -= (n > 2) ? 2 : n;
524 if ( nCode == 0x0fd2 )
526 r.ReadUInt16( nPatternId );
528 sal_uInt8 Hor_Align, Ver_Align, temp;
529 bool bIsBold,bIsUnderLine,bIsItalics;
531 r.SeekRel(12);
533 // Read 17th Byte
534 r.ReadUChar( temp );
536 bIsBold = (temp & 0x01);
537 bIsItalics = (temp & 0x02);
538 bIsUnderLine = (temp & 0x04);
540 if ( bIsBold )
541 rItemSet.Put( SvxWeightItem(WEIGHT_BOLD,ATTR_FONT_WEIGHT) );
542 if ( bIsItalics )
543 rItemSet.Put( SvxPostureItem(ITALIC_NORMAL, ATTR_FONT_POSTURE ) );
544 if ( bIsUnderLine )
545 rItemSet.Put( SvxUnderlineItem( UNDERLINE_SINGLE, ATTR_FONT_UNDERLINE ) );
547 r.SeekRel(3);
549 // Read 21st Byte
550 r.ReadUChar( Hor_Align );
551 OP_HorAlign123(rContext, Hor_Align, rItemSet );
553 r.ReadUChar( Ver_Align );
554 OP_VerAlign123(rContext, Ver_Align, rItemSet );
556 rContext.aLotusPatternPool.insert( std::map<sal_uInt16, ScPatternAttr>::value_type( nPatternId, aPattern ) );
557 n -= (n > 20) ? 20 : n;
559 r.SeekRel(n);
562 void OP_SheetName123(LotusContext& rContext, SvStream& rStream, sal_uInt16 nLength)
564 if (nLength <= 4)
566 rStream.SeekRel(nLength);
567 return;
570 // B0 36 [sheet number (2 bytes?)] [sheet name (null terminated char array)]
572 sal_uInt16 nDummy;
573 rStream.ReadUInt16( nDummy ); // ignore the first 2 bytes (B0 36).
574 rStream.ReadUInt16( nDummy );
575 SCTAB nSheetNum = static_cast<SCTAB>(nDummy);
576 rContext.pDoc->MakeTable(nSheetNum);
578 ::std::vector<sal_Char> sSheetName;
579 sSheetName.reserve(nLength-4);
580 for (sal_uInt16 i = 4; i < nLength; ++i)
582 sal_Char c;
583 rStream.ReadChar( c );
584 sSheetName.push_back(c);
587 if (!sSheetName.empty())
589 OUString aName(&sSheetName[0], strlen(&sSheetName[0]), rContext.eCharVon);
590 rContext.pDoc->RenameTab(nSheetNum, aName);
594 void OP_ApplyPatternArea123(LotusContext& rContext, SvStream& rStream)
596 sal_uInt16 nOpcode, nLength;
597 sal_uInt16 nCol = 0, nColCount = 0, nRow = 0, nRowCount = 0, nTab = 0, nData, nTabCount = 0, nLevel = 0;
601 rStream.ReadUInt16( nOpcode ).ReadUInt16( nLength );
602 switch ( nOpcode )
604 case ROW_FORMAT_MARKER:
605 nLevel++;
606 break;
607 case COL_FORMAT_MARKER:
608 nLevel--;
609 if( nLevel == 1 )
611 nTab = nTab + nTabCount;
612 nCol = 0; nColCount = 0;
613 nRow = 0; nRowCount = 0;
615 break;
616 case LOTUS_FORMAT_INDEX:
617 if( nLength >= 2 )
619 rStream.ReadUInt16( nData );
620 rStream.SeekRel( nLength - 2 );
621 if( nLevel == 1 )
622 nTabCount = nData;
623 else if( nLevel == 2 )
625 nCol = nCol + nColCount;
626 nColCount = nData;
627 if ( nCol > 0xff ) // 256 is the max col size supported by 123
628 nCol = 0;
630 else if( nLevel == 3 )
632 nRow = nRow + nRowCount;
633 nRowCount = nData;
634 if ( nRow > 0x1fff ) // 8192 is the max row size supported by 123
635 nRow = 0;
638 else
639 rStream.SeekRel( nLength );
640 break;
641 case LOTUS_FORMAT_INFO:
642 if( nLength >= 2 )
644 rStream.ReadUInt16( nData );
645 rStream.SeekRel( nLength - 2 );
646 std::map<sal_uInt16, ScPatternAttr>::iterator loc = rContext.aLotusPatternPool.find( nData );
647 // #126338# apparently, files with invalid index occur in the wild -> don't crash then
648 if ( loc != rContext.aLotusPatternPool.end() )
649 for( int i = 0; i < nTabCount; i++)
651 rContext.pDoc->ApplyPatternAreaTab( nCol, nRow, nCol + nColCount - 1, nRow + nRowCount - 1, static_cast< SCTAB >( nTab + i ), loc->second );
654 else
655 rStream.SeekRel( nLength );
656 break;
657 default:
658 rStream.SeekRel( nLength );
659 break;
662 while( nLevel && !rStream.IsEof() );
664 rContext.aLotusPatternPool.clear();
667 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */