LanguageTool: don't crash if REST protocol isn't set
[LibreOffice.git] / sc / source / filter / excel / xistring.cxx
blobf0878a6171fd74de8d24ee0c2f8410101b339ba9
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 <xistring.hxx>
21 #include <xlstyle.hxx>
22 #include <xistream.hxx>
23 #include <xiroot.hxx>
24 #include <xltools.hxx>
25 #include <sal/log.hxx>
27 // Byte/Unicode strings =======================================================
29 /** All allowed flags for import. */
30 const XclStrFlags nAllowedFlags = XclStrFlags::EightBitLength | XclStrFlags::SmartFlags | XclStrFlags::SeparateFormats;
32 XclImpString::XclImpString()
36 XclImpString::XclImpString( const OUString& rString ) :
37 maString( rString )
41 void XclImpString::Read( XclImpStream& rStrm, XclStrFlags nFlags )
43 if( !( nFlags & XclStrFlags::SeparateFormats ) )
44 maFormats.clear();
46 SAL_WARN_IF(
47 nFlags & ~nAllowedFlags, "sc.filter",
48 "XclImpString::Read - unknown flag");
49 bool b16BitLen = !( nFlags & XclStrFlags::EightBitLength );
51 switch( rStrm.GetRoot().GetBiff() )
53 case EXC_BIFF2:
54 case EXC_BIFF3:
55 case EXC_BIFF4:
56 case EXC_BIFF5:
57 // no integrated formatting in BIFF2-BIFF7
58 maString = rStrm.ReadByteString( b16BitLen );
59 break;
61 case EXC_BIFF8:
63 // --- string header ---
64 sal_uInt16 nChars = b16BitLen ? rStrm.ReaduInt16() : rStrm.ReaduInt8();
65 sal_uInt8 nFlagField = 0;
66 if( nChars || !( nFlags & XclStrFlags::SmartFlags ) )
67 nFlagField = rStrm.ReaduInt8();
69 bool b16Bit, bRich, bFarEast;
70 sal_uInt16 nRunCount;
71 sal_uInt32 nExtInf;
72 rStrm.ReadUniStringExtHeader( b16Bit, bRich, bFarEast, nRunCount, nExtInf, nFlagField );
73 // ignore the flags, they may be wrong
75 // --- character array ---
76 maString = rStrm.ReadRawUniString( nChars, b16Bit );
78 // --- formatting ---
79 if (nRunCount)
80 ReadFormats( rStrm, maFormats, nRunCount );
82 // --- extended (FarEast) information ---
83 rStrm.Ignore( nExtInf );
85 break;
87 default:
88 DBG_ERROR_BIFF();
92 void XclImpString::AppendFormat( XclFormatRunVec& rFormats, sal_uInt16 nChar, sal_uInt16 nFontIdx )
94 // #i33341# real life -- same character index may occur several times
95 OSL_ENSURE( rFormats.empty() || (rFormats.back().mnChar <= nChar), "XclImpString::AppendFormat - wrong char order" );
96 if( rFormats.empty() || (rFormats.back().mnChar < nChar) )
97 rFormats.emplace_back( nChar, nFontIdx );
98 else
99 rFormats.back().mnFontIdx = nFontIdx;
102 void XclImpString::ReadFormats( XclImpStream& rStrm, XclFormatRunVec& rFormats )
104 bool bBiff8 = rStrm.GetRoot().GetBiff() == EXC_BIFF8;
105 sal_uInt16 nRunCount = bBiff8 ? rStrm.ReaduInt16() : rStrm.ReaduInt8();
106 ReadFormats( rStrm, rFormats, nRunCount );
109 void XclImpString::ReadFormats( XclImpStream& rStrm, XclFormatRunVec& rFormats, sal_uInt16 nRunCount )
111 rFormats.clear();
113 size_t nElementSize = rStrm.GetRoot().GetBiff() == EXC_BIFF8 ? 4 : 2;
114 size_t nAvailableBytes = rStrm.GetRecLeft();
115 size_t nMaxElements = nAvailableBytes / nElementSize;
116 if (nRunCount > nMaxElements)
118 SAL_WARN("sc.filter", "XclImpString::ReadFormats - more formats claimed than stream could contain");
119 rStrm.SetSvStreamError(SVSTREAM_FILEFORMAT_ERROR);
120 return;
123 rFormats.reserve( nRunCount );
124 /* #i33341# real life -- same character index may occur several times
125 -> use AppendFormat() to validate formats */
126 if( rStrm.GetRoot().GetBiff() == EXC_BIFF8 )
128 for( sal_uInt16 nIdx = 0; nIdx < nRunCount; ++nIdx )
130 sal_uInt16 nChar = rStrm.ReaduInt16();
131 sal_uInt16 nFontIdx = rStrm.ReaduInt16();
132 AppendFormat( rFormats, nChar, nFontIdx );
135 else
137 for( sal_uInt16 nIdx = 0; nIdx < nRunCount; ++nIdx )
139 sal_uInt8 nChar = rStrm.ReaduInt8();
140 sal_uInt8 nFontIdx = rStrm.ReaduInt8();
141 AppendFormat( rFormats, nChar, nFontIdx );
146 void XclImpString::ReadObjFormats( XclImpStream& rStrm, XclFormatRunVec& rFormats, sal_uInt16 nFormatSize )
148 // number of formatting runs, each takes 8 bytes
149 sal_uInt16 nRunCount = nFormatSize / 8;
150 rFormats.clear();
151 rFormats.reserve( nRunCount );
152 for( sal_uInt16 nIdx = 0; nIdx < nRunCount; ++nIdx )
154 sal_uInt16 nChar = rStrm.ReaduInt16();
155 sal_uInt16 nFontIdx = rStrm.ReaduInt16();
156 rStrm.Ignore( 4 );
157 AppendFormat( rFormats, nChar, nFontIdx );
161 // String iterator ============================================================
163 XclImpStringIterator::XclImpStringIterator( const XclImpString& rString ) :
164 mrText( rString.GetText() ),
165 mrFormats( rString.GetFormats() ),
166 mnPortion( 0 ),
167 mnTextBeg( 0 ),
168 mnTextEnd( 0 ),
169 mnFormatsBeg( 0 ),
170 mnFormatsEnd( 0 )
172 // first portion is formatted, adjust vector index to next portion
173 if( !mrFormats.empty() && (mrFormats.front().mnChar == 0) )
174 ++mnFormatsEnd;
175 // find end position of the first portion
176 mnTextEnd = (mnFormatsEnd < mrFormats.size() ?
177 mrFormats[ mnFormatsEnd ].mnChar : mrText.getLength() );
180 OUString XclImpStringIterator::GetPortionText() const
182 return mrText.copy( mnTextBeg, mnTextEnd - mnTextBeg );
185 sal_uInt16 XclImpStringIterator::GetPortionFont() const
187 return (mnFormatsBeg < mnFormatsEnd) ? mrFormats[ mnFormatsBeg ].mnFontIdx : EXC_FONT_NOTFOUND;
190 XclImpStringIterator& XclImpStringIterator::operator++()
192 if( Is() )
194 ++mnPortion;
197 // indexes into vector of formatting runs
198 if( mnFormatsBeg < mnFormatsEnd )
199 ++mnFormatsBeg;
200 if( mnFormatsEnd < mrFormats.size() )
201 ++mnFormatsEnd;
202 // character positions of next portion
203 mnTextBeg = mnTextEnd;
204 mnTextEnd = (mnFormatsEnd < mrFormats.size()) ?
205 mrFormats[ mnFormatsEnd ].mnChar : mrText.getLength();
207 while( Is() && (mnTextBeg == mnTextEnd) );
209 return *this;
212 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */