xref: /aoo41x/main/sfx2/source/doc/oleprops.cxx (revision d119d52d)
1*d119d52dSAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3*d119d52dSAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*d119d52dSAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*d119d52dSAndrew Rist  * distributed with this work for additional information
6*d119d52dSAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*d119d52dSAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*d119d52dSAndrew Rist  * "License"); you may not use this file except in compliance
9*d119d52dSAndrew Rist  * with the License.  You may obtain a copy of the License at
10*d119d52dSAndrew Rist  *
11*d119d52dSAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12*d119d52dSAndrew Rist  *
13*d119d52dSAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*d119d52dSAndrew Rist  * software distributed under the License is distributed on an
15*d119d52dSAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*d119d52dSAndrew Rist  * KIND, either express or implied.  See the License for the
17*d119d52dSAndrew Rist  * specific language governing permissions and limitations
18*d119d52dSAndrew Rist  * under the License.
19*d119d52dSAndrew Rist  *
20*d119d52dSAndrew Rist  *************************************************************/
21*d119d52dSAndrew Rist 
22*d119d52dSAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_sfx2.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir #include "oleprops.hxx"
28cdf0e10cSrcweir 
29cdf0e10cSrcweir #include <comphelper/types.hxx>
30cdf0e10cSrcweir #include <tools/debug.hxx>
31cdf0e10cSrcweir #include <tools/datetime.hxx>
32cdf0e10cSrcweir #include <rtl/tencinfo.h>
33cdf0e10cSrcweir 
34cdf0e10cSrcweir // ============================================================================
35cdf0e10cSrcweir 
36cdf0e10cSrcweir 
37cdf0e10cSrcweir // ============================================================================
38cdf0e10cSrcweir 
39cdf0e10cSrcweir #define VERSION 11
40cdf0e10cSrcweir #define STREAM_BUFFER_SIZE 2048
41cdf0e10cSrcweir 
42cdf0e10cSrcweir // usings
43cdf0e10cSrcweir using ::rtl::OUString;
44cdf0e10cSrcweir using ::com::sun::star::uno::Any;
45cdf0e10cSrcweir using ::com::sun::star::uno::makeAny;
46cdf0e10cSrcweir 
47cdf0e10cSrcweir using namespace ::com::sun::star;
48cdf0e10cSrcweir 
49cdf0e10cSrcweir #define TIMESTAMP_INVALID_DATETIME    	( DateTime ( Date ( 1, 1, 1601 ), Time ( 0, 0, 0 ) ) )	/// Invalid value for date and time to create invalid instance of TimeStamp.
50cdf0e10cSrcweir #define TIMESTAMP_INVALID_UTILDATETIME  ( util::DateTime ( 0, 0, 0, 0, 1, 1, 1601 ) )	/// Invalid value for date and time to create invalid instance of TimeStamp.
51cdf0e10cSrcweir 
52cdf0e10cSrcweir static
53cdf0e10cSrcweir bool operator==(const util::DateTime &i_rLeft, const util::DateTime &i_rRight)
54cdf0e10cSrcweir {
55cdf0e10cSrcweir     return i_rLeft.Year             == i_rRight.Year
56cdf0e10cSrcweir         && i_rLeft.Month            == i_rRight.Month
57cdf0e10cSrcweir         && i_rLeft.Day              == i_rRight.Day
58cdf0e10cSrcweir         && i_rLeft.Hours            == i_rRight.Hours
59cdf0e10cSrcweir         && i_rLeft.Minutes          == i_rRight.Minutes
60cdf0e10cSrcweir         && i_rLeft.Seconds          == i_rRight.Seconds
61cdf0e10cSrcweir         && i_rLeft.HundredthSeconds == i_rRight.HundredthSeconds;
62cdf0e10cSrcweir }
63cdf0e10cSrcweir 
64cdf0e10cSrcweir // ============================================================================
65cdf0e10cSrcweir 
66cdf0e10cSrcweir /** Property representing a signed 32-bit integer value. */
67cdf0e10cSrcweir class SfxOleInt32Property : public SfxOlePropertyBase
68cdf0e10cSrcweir {
69cdf0e10cSrcweir public:
70cdf0e10cSrcweir     explicit            SfxOleInt32Property( sal_Int32 nPropId, sal_Int32 nValue = 0 );
71cdf0e10cSrcweir 
72cdf0e10cSrcweir     inline sal_Int32    GetValue() const { return mnValue; }
73cdf0e10cSrcweir     inline void         SetValue( sal_Int32 nValue ) { mnValue = nValue; }
74cdf0e10cSrcweir 
75cdf0e10cSrcweir private:
76cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
77cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
78cdf0e10cSrcweir 
79cdf0e10cSrcweir private:
80cdf0e10cSrcweir     sal_Int32           mnValue;
81cdf0e10cSrcweir };
82cdf0e10cSrcweir 
83cdf0e10cSrcweir // ============================================================================
84cdf0e10cSrcweir 
85cdf0e10cSrcweir /** Property representing a floating-point value. */
86cdf0e10cSrcweir class SfxOleDoubleProperty : public SfxOlePropertyBase
87cdf0e10cSrcweir {
88cdf0e10cSrcweir public:
89cdf0e10cSrcweir     explicit            SfxOleDoubleProperty( sal_Int32 nPropId, double fValue = 0.0 );
90cdf0e10cSrcweir 
91cdf0e10cSrcweir     inline double       GetValue() const { return mfValue; }
92cdf0e10cSrcweir     inline void         SetValue( double fValue ) { mfValue = fValue; }
93cdf0e10cSrcweir 
94cdf0e10cSrcweir private:
95cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
96cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
97cdf0e10cSrcweir 
98cdf0e10cSrcweir private:
99cdf0e10cSrcweir     double              mfValue;
100cdf0e10cSrcweir };
101cdf0e10cSrcweir 
102cdf0e10cSrcweir // ============================================================================
103cdf0e10cSrcweir 
104cdf0e10cSrcweir /** Property representing a boolean value. */
105cdf0e10cSrcweir class SfxOleBoolProperty : public SfxOlePropertyBase
106cdf0e10cSrcweir {
107cdf0e10cSrcweir public:
108cdf0e10cSrcweir     explicit            SfxOleBoolProperty( sal_Int32 nPropId, bool bValue = false );
109cdf0e10cSrcweir 
110cdf0e10cSrcweir     inline bool         GetValue() const { return mbValue; }
111cdf0e10cSrcweir     inline void         SetValue( bool bValue ) { mbValue = bValue; }
112cdf0e10cSrcweir 
113cdf0e10cSrcweir private:
114cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
115cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
116cdf0e10cSrcweir 
117cdf0e10cSrcweir private:
118cdf0e10cSrcweir     bool                mbValue;
119cdf0e10cSrcweir };
120cdf0e10cSrcweir 
121cdf0e10cSrcweir // ============================================================================
122cdf0e10cSrcweir 
123cdf0e10cSrcweir /** Base class for properties that contain a single string value. */
124cdf0e10cSrcweir class SfxOleStringPropertyBase : public SfxOlePropertyBase, public SfxOleStringHelper
125cdf0e10cSrcweir {
126cdf0e10cSrcweir public:
127cdf0e10cSrcweir     explicit            SfxOleStringPropertyBase(
128cdf0e10cSrcweir                             sal_Int32 nPropId, sal_Int32 nPropType,
129cdf0e10cSrcweir                             const SfxOleTextEncoding& rTextEnc );
130cdf0e10cSrcweir     explicit            SfxOleStringPropertyBase(
131cdf0e10cSrcweir                             sal_Int32 nPropId, sal_Int32 nPropType,
132cdf0e10cSrcweir                             const SfxOleTextEncoding& rTextEnc, const String& rValue );
133cdf0e10cSrcweir     explicit            SfxOleStringPropertyBase(
134cdf0e10cSrcweir                             sal_Int32 nPropId, sal_Int32 nPropType,
135cdf0e10cSrcweir                             rtl_TextEncoding eTextEnc );
136cdf0e10cSrcweir     explicit            SfxOleStringPropertyBase(
137cdf0e10cSrcweir                             sal_Int32 nPropId, sal_Int32 nPropType,
138cdf0e10cSrcweir                             rtl_TextEncoding eTextEnc, const String& rValue );
139cdf0e10cSrcweir 
140cdf0e10cSrcweir     inline const String& GetValue() const { return maValue; }
141cdf0e10cSrcweir     inline void         SetValue( const String& rValue ) { maValue = rValue; }
142cdf0e10cSrcweir 
143cdf0e10cSrcweir private:
144cdf0e10cSrcweir     String              maValue;
145cdf0e10cSrcweir };
146cdf0e10cSrcweir 
147cdf0e10cSrcweir // ============================================================================
148cdf0e10cSrcweir 
149cdf0e10cSrcweir /** Property representing a bytestring value. */
150cdf0e10cSrcweir class SfxOleString8Property : public SfxOleStringPropertyBase
151cdf0e10cSrcweir {
152cdf0e10cSrcweir public:
153cdf0e10cSrcweir     explicit            SfxOleString8Property(
154cdf0e10cSrcweir                             sal_Int32 nPropId, const SfxOleTextEncoding& rTextEnc );
155cdf0e10cSrcweir     explicit            SfxOleString8Property(
156cdf0e10cSrcweir                             sal_Int32 nPropId, const SfxOleTextEncoding& rTextEnc,
157cdf0e10cSrcweir                             const String& rValue );
158cdf0e10cSrcweir 
159cdf0e10cSrcweir private:
160cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
161cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
162cdf0e10cSrcweir };
163cdf0e10cSrcweir 
164cdf0e10cSrcweir // ============================================================================
165cdf0e10cSrcweir 
166cdf0e10cSrcweir /** Property representing a Unicode string value. */
167cdf0e10cSrcweir class SfxOleString16Property : public SfxOleStringPropertyBase
168cdf0e10cSrcweir {
169cdf0e10cSrcweir public:
170cdf0e10cSrcweir     explicit            SfxOleString16Property( sal_Int32 nPropId );
171cdf0e10cSrcweir     explicit            SfxOleString16Property( sal_Int32 nPropId, const String& rValue );
172cdf0e10cSrcweir 
173cdf0e10cSrcweir private:
174cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
175cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
176cdf0e10cSrcweir };
177cdf0e10cSrcweir 
178cdf0e10cSrcweir // ============================================================================
179cdf0e10cSrcweir 
180cdf0e10cSrcweir /** Property representing a filetime value as defined by the Windows API. */
181cdf0e10cSrcweir class SfxOleFileTimeProperty : public SfxOlePropertyBase
182cdf0e10cSrcweir {
183cdf0e10cSrcweir public:
184cdf0e10cSrcweir     explicit            SfxOleFileTimeProperty( sal_Int32 nPropId );
185cdf0e10cSrcweir     /** @param rDateTime  Date and time as LOCAL time. */
186cdf0e10cSrcweir     explicit            SfxOleFileTimeProperty( sal_Int32 nPropId, const util::DateTime& rDateTime );
187cdf0e10cSrcweir 
188cdf0e10cSrcweir     /** Returns the time value as LOCAL time. */
189cdf0e10cSrcweir     inline const util::DateTime& GetValue() const { return maDateTime; }
190cdf0e10cSrcweir     /** @param rDateTime  Date and time as LOCAL time. */
191cdf0e10cSrcweir     inline void         SetValue( const util::DateTime& rDateTime ) { maDateTime = rDateTime; }
192cdf0e10cSrcweir 
193cdf0e10cSrcweir private:
194cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
195cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
196cdf0e10cSrcweir 
197cdf0e10cSrcweir private:
198cdf0e10cSrcweir     util::DateTime      maDateTime;
199cdf0e10cSrcweir };
200cdf0e10cSrcweir 
201cdf0e10cSrcweir // ============================================================================
202cdf0e10cSrcweir 
203cdf0e10cSrcweir /** Property representing a thumbnail picture.
204cdf0e10cSrcweir 
205cdf0e10cSrcweir     Currently, only saving this property is implemented.
206cdf0e10cSrcweir  */
207cdf0e10cSrcweir class SfxOleThumbnailProperty : public SfxOlePropertyBase
208cdf0e10cSrcweir {
209cdf0e10cSrcweir public:
210cdf0e10cSrcweir     explicit            SfxOleThumbnailProperty( sal_Int32 nPropId,
211cdf0e10cSrcweir                             const uno::Sequence<sal_uInt8> & i_rData);
212cdf0e10cSrcweir 
213cdf0e10cSrcweir     inline bool         IsValid() const { return mData.getLength() > 0; }
214cdf0e10cSrcweir 
215cdf0e10cSrcweir private:
216cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
217cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
218cdf0e10cSrcweir 
219cdf0e10cSrcweir private:
220cdf0e10cSrcweir     uno::Sequence<sal_uInt8>    mData;
221cdf0e10cSrcweir };
222cdf0e10cSrcweir 
223cdf0e10cSrcweir // ============================================================================
224cdf0e10cSrcweir 
225cdf0e10cSrcweir /** Property representing a BLOB (which presumably stands for binary large
226cdf0e10cSrcweir     object).
227cdf0e10cSrcweir 
228cdf0e10cSrcweir     Currently, only saving this property is implemented.
229cdf0e10cSrcweir  */
230cdf0e10cSrcweir class SfxOleBlobProperty : public SfxOlePropertyBase
231cdf0e10cSrcweir {
232cdf0e10cSrcweir public:
233cdf0e10cSrcweir     explicit            SfxOleBlobProperty( sal_Int32 nPropId,
234cdf0e10cSrcweir                             const uno::Sequence<sal_uInt8> & i_rData);
235cdf0e10cSrcweir     inline bool         IsValid() const { return mData.getLength() > 0; }
236cdf0e10cSrcweir 
237cdf0e10cSrcweir private:
238cdf0e10cSrcweir     virtual void        ImplLoad( SvStream& rStrm );
239cdf0e10cSrcweir     virtual void        ImplSave( SvStream& rStrm );
240cdf0e10cSrcweir 
241cdf0e10cSrcweir private:
242cdf0e10cSrcweir     uno::Sequence<sal_uInt8>    mData;
243cdf0e10cSrcweir };
244cdf0e10cSrcweir 
245cdf0e10cSrcweir // ============================================================================
246cdf0e10cSrcweir 
247cdf0e10cSrcweir sal_uInt16 SfxOleTextEncoding::GetCodePage() const
248cdf0e10cSrcweir {
249cdf0e10cSrcweir     sal_uInt16 nCodePage = IsUnicode() ? CODEPAGE_UNICODE :
250cdf0e10cSrcweir         static_cast< sal_uInt16 >( rtl_getWindowsCodePageFromTextEncoding( *mxTextEnc ) );
251cdf0e10cSrcweir     return (nCodePage == CODEPAGE_UNKNOWN) ? CODEPAGE_UTF8 : nCodePage;
252cdf0e10cSrcweir }
253cdf0e10cSrcweir 
254cdf0e10cSrcweir void SfxOleTextEncoding::SetCodePage( sal_uInt16 nCodePage )
255cdf0e10cSrcweir {
256cdf0e10cSrcweir     if( nCodePage == CODEPAGE_UNICODE )
257cdf0e10cSrcweir         SetUnicode();
258cdf0e10cSrcweir     else
259cdf0e10cSrcweir     {
260cdf0e10cSrcweir         rtl_TextEncoding eTextEnc = rtl_getTextEncodingFromWindowsCodePage( nCodePage );
261cdf0e10cSrcweir         if( eTextEnc != RTL_TEXTENCODING_DONTKNOW )
262cdf0e10cSrcweir             *mxTextEnc = eTextEnc;
263cdf0e10cSrcweir     }
264cdf0e10cSrcweir }
265cdf0e10cSrcweir 
266cdf0e10cSrcweir // ----------------------------------------------------------------------------
267cdf0e10cSrcweir 
268cdf0e10cSrcweir String SfxOleStringHelper::LoadString8( SvStream& rStrm ) const
269cdf0e10cSrcweir {
270cdf0e10cSrcweir     return IsUnicode() ? ImplLoadString16( rStrm ) : ImplLoadString8( rStrm );
271cdf0e10cSrcweir }
272cdf0e10cSrcweir 
273cdf0e10cSrcweir void SfxOleStringHelper::SaveString8( SvStream& rStrm, const String& rValue ) const
274cdf0e10cSrcweir {
275cdf0e10cSrcweir     if( IsUnicode() )
276cdf0e10cSrcweir         ImplSaveString16( rStrm, rValue );
277cdf0e10cSrcweir     else
278cdf0e10cSrcweir         ImplSaveString8( rStrm, rValue );
279cdf0e10cSrcweir }
280cdf0e10cSrcweir 
281cdf0e10cSrcweir String SfxOleStringHelper::LoadString16( SvStream& rStrm ) const
282cdf0e10cSrcweir {
283cdf0e10cSrcweir     return ImplLoadString16( rStrm );
284cdf0e10cSrcweir }
285cdf0e10cSrcweir 
286cdf0e10cSrcweir void SfxOleStringHelper::SaveString16( SvStream& rStrm, const String& rValue ) const
287cdf0e10cSrcweir {
288cdf0e10cSrcweir     ImplSaveString16( rStrm, rValue );
289cdf0e10cSrcweir }
290cdf0e10cSrcweir 
291cdf0e10cSrcweir String SfxOleStringHelper::ImplLoadString8( SvStream& rStrm ) const
292cdf0e10cSrcweir {
293cdf0e10cSrcweir     String aValue;
294cdf0e10cSrcweir     // read size field (signed 32-bit)
295cdf0e10cSrcweir     sal_Int32 nSize;
296cdf0e10cSrcweir     rStrm >> nSize;
297cdf0e10cSrcweir     // size field includes trailing NUL character
298cdf0e10cSrcweir     DBG_ASSERT( (0 < nSize) && (nSize <= 0xFFFF), "SfxOleStringHelper::ImplLoadString8 - invalid string" );
299cdf0e10cSrcweir     if( (0 < nSize) && (nSize <= 0xFFFF) )
300cdf0e10cSrcweir     {
301cdf0e10cSrcweir         // load character buffer
302cdf0e10cSrcweir         ::std::vector< sal_Char > aBuffer( static_cast< size_t >( nSize + 1 ), 0 );
303cdf0e10cSrcweir         rStrm.Read( &aBuffer.front(), static_cast< sal_Size >( nSize ) );
304cdf0e10cSrcweir         // create string from encoded character array
305cdf0e10cSrcweir         aValue = String( &aBuffer.front(), GetTextEncoding() );
306cdf0e10cSrcweir     }
307cdf0e10cSrcweir     return aValue;
308cdf0e10cSrcweir }
309cdf0e10cSrcweir 
310cdf0e10cSrcweir String SfxOleStringHelper::ImplLoadString16( SvStream& rStrm ) const
311cdf0e10cSrcweir {
312cdf0e10cSrcweir     String aValue;
313cdf0e10cSrcweir     // read size field (signed 32-bit), may be buffer size or character count
314cdf0e10cSrcweir     sal_Int32 nSize;
315cdf0e10cSrcweir     rStrm >> nSize;
316cdf0e10cSrcweir     DBG_ASSERT( (0 < nSize) && (nSize <= 0xFFFF), "SfxOleStringHelper::ImplLoadString16 - invalid string" );
317cdf0e10cSrcweir     // size field includes trailing NUL character
318cdf0e10cSrcweir     if( (0 < nSize) && (nSize <= 0xFFFF) )
319cdf0e10cSrcweir     {
320cdf0e10cSrcweir         // load character buffer
321cdf0e10cSrcweir         ::std::vector< sal_Unicode > aBuffer;
322cdf0e10cSrcweir         aBuffer.reserve( static_cast< size_t >( nSize + 1 ) );
323cdf0e10cSrcweir         sal_uInt16 cChar;
324cdf0e10cSrcweir         for( sal_Int32 nIdx = 0; nIdx < nSize; ++nIdx )
325cdf0e10cSrcweir         {
326cdf0e10cSrcweir             rStrm >> cChar;
327cdf0e10cSrcweir             aBuffer.push_back( static_cast< sal_Unicode >( cChar ) );
328cdf0e10cSrcweir         }
329cdf0e10cSrcweir         // stream is always padded to 32-bit boundary, skip 2 bytes on odd character count
330cdf0e10cSrcweir         if( (nSize & 1) == 1 )
331cdf0e10cSrcweir             rStrm.SeekRel( 2 );
332cdf0e10cSrcweir         // create string from character array
333cdf0e10cSrcweir         aBuffer.push_back( 0 );
334cdf0e10cSrcweir         aValue = String( &aBuffer.front() );
335cdf0e10cSrcweir     }
336cdf0e10cSrcweir     return aValue;
337cdf0e10cSrcweir }
338cdf0e10cSrcweir 
339cdf0e10cSrcweir void SfxOleStringHelper::ImplSaveString8( SvStream& rStrm, const String& rValue ) const
340cdf0e10cSrcweir {
341cdf0e10cSrcweir     // encode to byte string
342cdf0e10cSrcweir     ByteString aEncoded( rValue, GetTextEncoding() );
343cdf0e10cSrcweir     // write size field (including trailing NUL character)
344cdf0e10cSrcweir     sal_Int32 nSize = static_cast< sal_Int32 >( aEncoded.Len() + 1 );
345cdf0e10cSrcweir     rStrm << nSize;
346cdf0e10cSrcweir     // write character array with trailing NUL character
347cdf0e10cSrcweir     rStrm.Write( aEncoded.GetBuffer(), aEncoded.Len() );
348cdf0e10cSrcweir     rStrm << sal_uInt8( 0 );
349cdf0e10cSrcweir }
350cdf0e10cSrcweir 
351cdf0e10cSrcweir void SfxOleStringHelper::ImplSaveString16( SvStream& rStrm, const String& rValue ) const
352cdf0e10cSrcweir {
353cdf0e10cSrcweir     // write size field (including trailing NUL character)
354cdf0e10cSrcweir     sal_Int32 nSize = static_cast< sal_Int32 >( rValue.Len() + 1 );
355cdf0e10cSrcweir     rStrm << nSize;
356cdf0e10cSrcweir     // write character array with trailing NUL character
357cdf0e10cSrcweir     for( xub_StrLen nIdx = 0; nIdx < rValue.Len(); ++nIdx )
358cdf0e10cSrcweir         rStrm << static_cast< sal_uInt16 >( rValue.GetChar( nIdx ) );
359cdf0e10cSrcweir     rStrm << sal_uInt16( 0 );
360cdf0e10cSrcweir     // stream is always padded to 32-bit boundary, add 2 bytes on odd character count
361cdf0e10cSrcweir     if( (nSize & 1) == 1 )
362cdf0e10cSrcweir         rStrm << sal_uInt16( 0 );
363cdf0e10cSrcweir }
364cdf0e10cSrcweir 
365cdf0e10cSrcweir // ----------------------------------------------------------------------------
366cdf0e10cSrcweir 
367cdf0e10cSrcweir SfxOleObjectBase::~SfxOleObjectBase()
368cdf0e10cSrcweir {
369cdf0e10cSrcweir }
370cdf0e10cSrcweir 
371cdf0e10cSrcweir ErrCode SfxOleObjectBase::Load( SvStream& rStrm )
372cdf0e10cSrcweir {
373cdf0e10cSrcweir     mnErrCode = ERRCODE_NONE;
374cdf0e10cSrcweir     ImplLoad( rStrm );
375cdf0e10cSrcweir     SetError( rStrm.GetErrorCode() );
376cdf0e10cSrcweir     return GetError();
377cdf0e10cSrcweir }
378cdf0e10cSrcweir 
379cdf0e10cSrcweir ErrCode SfxOleObjectBase::Save( SvStream& rStrm )
380cdf0e10cSrcweir {
381cdf0e10cSrcweir     mnErrCode = ERRCODE_NONE;
382cdf0e10cSrcweir     ImplSave( rStrm );
383cdf0e10cSrcweir     SetError( rStrm.GetErrorCode() );
384cdf0e10cSrcweir     return GetError();
385cdf0e10cSrcweir }
386cdf0e10cSrcweir 
387cdf0e10cSrcweir void SfxOleObjectBase::LoadObject( SvStream& rStrm, SfxOleObjectBase& rObj )
388cdf0e10cSrcweir {
389cdf0e10cSrcweir     SetError( rObj.Load( rStrm ) );
390cdf0e10cSrcweir }
391cdf0e10cSrcweir 
392cdf0e10cSrcweir void SfxOleObjectBase::SaveObject( SvStream& rStrm, SfxOleObjectBase& rObj )
393cdf0e10cSrcweir {
394cdf0e10cSrcweir     SetError( rObj.Save( rStrm ) );
395cdf0e10cSrcweir }
396cdf0e10cSrcweir 
397cdf0e10cSrcweir // ----------------------------------------------------------------------------
398cdf0e10cSrcweir 
399cdf0e10cSrcweir SfxOleCodePageProperty::SfxOleCodePageProperty() :
400cdf0e10cSrcweir     SfxOlePropertyBase( PROPID_CODEPAGE, PROPTYPE_INT16 )
401cdf0e10cSrcweir {
402cdf0e10cSrcweir }
403cdf0e10cSrcweir 
404cdf0e10cSrcweir void SfxOleCodePageProperty::ImplLoad( SvStream& rStrm )
405cdf0e10cSrcweir {
406cdf0e10cSrcweir     // property type is signed int16, but we use always unsigned int16 for codepages
407cdf0e10cSrcweir     sal_uInt16 nCodePage;
408cdf0e10cSrcweir     rStrm >> nCodePage;
409cdf0e10cSrcweir     SetCodePage( nCodePage );
410cdf0e10cSrcweir }
411cdf0e10cSrcweir 
412cdf0e10cSrcweir void SfxOleCodePageProperty::ImplSave( SvStream& rStrm )
413cdf0e10cSrcweir {
414cdf0e10cSrcweir     // property type is signed int16, but we use always unsigned int16 for codepages
415cdf0e10cSrcweir     rStrm << GetCodePage();
416cdf0e10cSrcweir }
417cdf0e10cSrcweir 
418cdf0e10cSrcweir // ----------------------------------------------------------------------------
419cdf0e10cSrcweir 
420cdf0e10cSrcweir SfxOleInt32Property::SfxOleInt32Property( sal_Int32 nPropId, sal_Int32 nValue ) :
421cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_INT32 ),
422cdf0e10cSrcweir     mnValue( nValue )
423cdf0e10cSrcweir {
424cdf0e10cSrcweir }
425cdf0e10cSrcweir 
426cdf0e10cSrcweir void SfxOleInt32Property::ImplLoad( SvStream& rStrm )
427cdf0e10cSrcweir {
428cdf0e10cSrcweir     rStrm >> mnValue;
429cdf0e10cSrcweir }
430cdf0e10cSrcweir 
431cdf0e10cSrcweir void SfxOleInt32Property::ImplSave( SvStream& rStrm )
432cdf0e10cSrcweir {
433cdf0e10cSrcweir     rStrm << mnValue;
434cdf0e10cSrcweir }
435cdf0e10cSrcweir 
436cdf0e10cSrcweir // ----------------------------------------------------------------------------
437cdf0e10cSrcweir 
438cdf0e10cSrcweir SfxOleDoubleProperty::SfxOleDoubleProperty( sal_Int32 nPropId, double fValue ) :
439cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_DOUBLE ),
440cdf0e10cSrcweir     mfValue( fValue )
441cdf0e10cSrcweir {
442cdf0e10cSrcweir }
443cdf0e10cSrcweir 
444cdf0e10cSrcweir void SfxOleDoubleProperty::ImplLoad( SvStream& rStrm )
445cdf0e10cSrcweir {
446cdf0e10cSrcweir     rStrm >> mfValue;
447cdf0e10cSrcweir }
448cdf0e10cSrcweir 
449cdf0e10cSrcweir void SfxOleDoubleProperty::ImplSave( SvStream& rStrm )
450cdf0e10cSrcweir {
451cdf0e10cSrcweir     rStrm << mfValue;
452cdf0e10cSrcweir }
453cdf0e10cSrcweir 
454cdf0e10cSrcweir // ----------------------------------------------------------------------------
455cdf0e10cSrcweir 
456cdf0e10cSrcweir SfxOleBoolProperty::SfxOleBoolProperty( sal_Int32 nPropId, bool bValue ) :
457cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_BOOL ),
458cdf0e10cSrcweir     mbValue( bValue )
459cdf0e10cSrcweir {
460cdf0e10cSrcweir }
461cdf0e10cSrcweir 
462cdf0e10cSrcweir void SfxOleBoolProperty::ImplLoad( SvStream& rStrm )
463cdf0e10cSrcweir {
464cdf0e10cSrcweir     sal_Int16 nValue;
465cdf0e10cSrcweir     rStrm >> nValue;
466cdf0e10cSrcweir     mbValue = nValue != 0;
467cdf0e10cSrcweir }
468cdf0e10cSrcweir 
469cdf0e10cSrcweir void SfxOleBoolProperty::ImplSave( SvStream& rStrm )
470cdf0e10cSrcweir {
471cdf0e10cSrcweir     rStrm << static_cast< sal_Int16 >( mbValue ? -1 : 0 );
472cdf0e10cSrcweir }
473cdf0e10cSrcweir 
474cdf0e10cSrcweir // ----------------------------------------------------------------------------
475cdf0e10cSrcweir 
476cdf0e10cSrcweir SfxOleStringPropertyBase::SfxOleStringPropertyBase(
477cdf0e10cSrcweir         sal_Int32 nPropId, sal_Int32 nPropType, const SfxOleTextEncoding& rTextEnc ) :
478cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, nPropType ),
479cdf0e10cSrcweir     SfxOleStringHelper( rTextEnc )
480cdf0e10cSrcweir {
481cdf0e10cSrcweir }
482cdf0e10cSrcweir 
483cdf0e10cSrcweir SfxOleStringPropertyBase::SfxOleStringPropertyBase(
484cdf0e10cSrcweir         sal_Int32 nPropId, sal_Int32 nPropType, const SfxOleTextEncoding& rTextEnc, const String& rValue ) :
485cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, nPropType ),
486cdf0e10cSrcweir     SfxOleStringHelper( rTextEnc ),
487cdf0e10cSrcweir     maValue( rValue )
488cdf0e10cSrcweir {
489cdf0e10cSrcweir }
490cdf0e10cSrcweir 
491cdf0e10cSrcweir SfxOleStringPropertyBase::SfxOleStringPropertyBase(
492cdf0e10cSrcweir         sal_Int32 nPropId, sal_Int32 nPropType, rtl_TextEncoding eTextEnc ) :
493cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, nPropType ),
494cdf0e10cSrcweir     SfxOleStringHelper( eTextEnc )
495cdf0e10cSrcweir {
496cdf0e10cSrcweir }
497cdf0e10cSrcweir 
498cdf0e10cSrcweir SfxOleStringPropertyBase::SfxOleStringPropertyBase(
499cdf0e10cSrcweir         sal_Int32 nPropId, sal_Int32 nPropType, rtl_TextEncoding eTextEnc, const String& rValue ) :
500cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, nPropType ),
501cdf0e10cSrcweir     SfxOleStringHelper( eTextEnc ),
502cdf0e10cSrcweir     maValue( rValue )
503cdf0e10cSrcweir {
504cdf0e10cSrcweir }
505cdf0e10cSrcweir 
506cdf0e10cSrcweir // ----------------------------------------------------------------------------
507cdf0e10cSrcweir 
508cdf0e10cSrcweir SfxOleString8Property::SfxOleString8Property(
509cdf0e10cSrcweir         sal_Int32 nPropId, const SfxOleTextEncoding& rTextEnc ) :
510cdf0e10cSrcweir     SfxOleStringPropertyBase( nPropId, PROPTYPE_STRING8, rTextEnc )
511cdf0e10cSrcweir {
512cdf0e10cSrcweir }
513cdf0e10cSrcweir 
514cdf0e10cSrcweir SfxOleString8Property::SfxOleString8Property(
515cdf0e10cSrcweir         sal_Int32 nPropId, const SfxOleTextEncoding& rTextEnc, const String& rValue ) :
516cdf0e10cSrcweir     SfxOleStringPropertyBase( nPropId, PROPTYPE_STRING8, rTextEnc, rValue )
517cdf0e10cSrcweir {
518cdf0e10cSrcweir }
519cdf0e10cSrcweir 
520cdf0e10cSrcweir void SfxOleString8Property::ImplLoad( SvStream& rStrm )
521cdf0e10cSrcweir {
522cdf0e10cSrcweir     SetValue( LoadString8( rStrm ) );
523cdf0e10cSrcweir }
524cdf0e10cSrcweir 
525cdf0e10cSrcweir void SfxOleString8Property::ImplSave( SvStream& rStrm )
526cdf0e10cSrcweir {
527cdf0e10cSrcweir     SaveString8( rStrm, GetValue() );
528cdf0e10cSrcweir }
529cdf0e10cSrcweir 
530cdf0e10cSrcweir // ----------------------------------------------------------------------------
531cdf0e10cSrcweir 
532cdf0e10cSrcweir SfxOleString16Property::SfxOleString16Property( sal_Int32 nPropId ) :
533cdf0e10cSrcweir     SfxOleStringPropertyBase( nPropId, PROPTYPE_STRING16, RTL_TEXTENCODING_UCS2 )
534cdf0e10cSrcweir {
535cdf0e10cSrcweir }
536cdf0e10cSrcweir 
537cdf0e10cSrcweir SfxOleString16Property::SfxOleString16Property( sal_Int32 nPropId, const String& rValue ) :
538cdf0e10cSrcweir     SfxOleStringPropertyBase( nPropId, PROPTYPE_STRING16, RTL_TEXTENCODING_UCS2, rValue )
539cdf0e10cSrcweir {
540cdf0e10cSrcweir }
541cdf0e10cSrcweir 
542cdf0e10cSrcweir void SfxOleString16Property::ImplLoad( SvStream& rStrm )
543cdf0e10cSrcweir {
544cdf0e10cSrcweir     SetValue( LoadString16( rStrm ) );
545cdf0e10cSrcweir }
546cdf0e10cSrcweir 
547cdf0e10cSrcweir void SfxOleString16Property::ImplSave( SvStream& rStrm )
548cdf0e10cSrcweir {
549cdf0e10cSrcweir     SaveString16( rStrm, GetValue() );
550cdf0e10cSrcweir }
551cdf0e10cSrcweir 
552cdf0e10cSrcweir // ----------------------------------------------------------------------------
553cdf0e10cSrcweir 
554cdf0e10cSrcweir SfxOleFileTimeProperty::SfxOleFileTimeProperty( sal_Int32 nPropId ) :
555cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_FILETIME )
556cdf0e10cSrcweir {
557cdf0e10cSrcweir }
558cdf0e10cSrcweir 
559cdf0e10cSrcweir SfxOleFileTimeProperty::SfxOleFileTimeProperty( sal_Int32 nPropId, const util::DateTime& rDateTime ) :
560cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_FILETIME ),
561cdf0e10cSrcweir     maDateTime( rDateTime )
562cdf0e10cSrcweir {
563cdf0e10cSrcweir }
564cdf0e10cSrcweir 
565cdf0e10cSrcweir void SfxOleFileTimeProperty::ImplLoad( SvStream& rStrm )
566cdf0e10cSrcweir {
567cdf0e10cSrcweir     sal_uInt32 nLower, nUpper;
568cdf0e10cSrcweir     rStrm >> nLower >> nUpper;
569cdf0e10cSrcweir     ::DateTime aDateTime = DateTime::CreateFromWin32FileDateTime( nLower, nUpper );
570cdf0e10cSrcweir     // note: editing duration is stored as offset to TIMESTAMP_INVALID_DATETIME
571cdf0e10cSrcweir     //       of course we should not convert the time zone of a duration!
572cdf0e10cSrcweir     // heuristic to detect editing durations (which we assume to be < 1 year):
573cdf0e10cSrcweir     // check only the year, not the entire date
574cdf0e10cSrcweir 	if ( aDateTime.GetYear() != TIMESTAMP_INVALID_DATETIME.GetYear() )
575cdf0e10cSrcweir 		aDateTime.ConvertToLocalTime();
576cdf0e10cSrcweir     maDateTime.Year    = aDateTime.GetYear();
577cdf0e10cSrcweir     maDateTime.Month   = aDateTime.GetMonth();
578cdf0e10cSrcweir     maDateTime.Day     = aDateTime.GetDay();
579cdf0e10cSrcweir     maDateTime.Hours   = aDateTime.GetHour();
580cdf0e10cSrcweir     maDateTime.Minutes = aDateTime.GetMin();
581cdf0e10cSrcweir     maDateTime.Seconds = aDateTime.GetSec();
582cdf0e10cSrcweir     maDateTime.HundredthSeconds = aDateTime.Get100Sec();
583cdf0e10cSrcweir }
584cdf0e10cSrcweir 
585cdf0e10cSrcweir void SfxOleFileTimeProperty::ImplSave( SvStream& rStrm )
586cdf0e10cSrcweir {
587cdf0e10cSrcweir     DateTime aDateTimeUtc(
588cdf0e10cSrcweir             Date(
589cdf0e10cSrcweir                 static_cast< sal_uInt16 >( maDateTime.Day ),
590cdf0e10cSrcweir                 static_cast< sal_uInt16 >( maDateTime.Month ),
591cdf0e10cSrcweir                 static_cast< sal_uInt16 >( maDateTime.Year ) ),
592cdf0e10cSrcweir             Time(
593cdf0e10cSrcweir                 static_cast< sal_uIntPtr >( maDateTime.Hours ),
594cdf0e10cSrcweir                 static_cast< sal_uIntPtr >( maDateTime.Minutes ),
595cdf0e10cSrcweir                 static_cast< sal_uIntPtr >( maDateTime.Seconds ),
596cdf0e10cSrcweir                 static_cast< sal_uIntPtr >( maDateTime.HundredthSeconds ) ) );
597cdf0e10cSrcweir     // invalid time stamp is not converted to UTC
598cdf0e10cSrcweir     // heuristic to detect editing durations (which we assume to be < 1 year):
599cdf0e10cSrcweir     // check only the year, not the entire date
600cdf0e10cSrcweir     if( aDateTimeUtc.IsValid()
601cdf0e10cSrcweir         && aDateTimeUtc.GetYear() != TIMESTAMP_INVALID_DATETIME.GetYear() ) {
602cdf0e10cSrcweir             aDateTimeUtc.ConvertToUTC();
603cdf0e10cSrcweir     }
604cdf0e10cSrcweir     sal_uInt32 nLower, nUpper;
605cdf0e10cSrcweir     aDateTimeUtc.GetWin32FileDateTime( nLower, nUpper );
606cdf0e10cSrcweir     rStrm << nLower << nUpper;
607cdf0e10cSrcweir }
608cdf0e10cSrcweir 
609cdf0e10cSrcweir // ----------------------------------------------------------------------------
610cdf0e10cSrcweir 
611cdf0e10cSrcweir SfxOleThumbnailProperty::SfxOleThumbnailProperty(
612cdf0e10cSrcweir         sal_Int32 nPropId, const uno::Sequence<sal_uInt8> & i_rData) :
613cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_CLIPFMT ),
614cdf0e10cSrcweir     mData(i_rData)
615cdf0e10cSrcweir {
616cdf0e10cSrcweir }
617cdf0e10cSrcweir 
618cdf0e10cSrcweir void SfxOleThumbnailProperty::ImplLoad( SvStream& )
619cdf0e10cSrcweir {
620cdf0e10cSrcweir     DBG_ERRORFILE( "SfxOleThumbnailProperty::ImplLoad - not implemented" );
621cdf0e10cSrcweir     SetError( SVSTREAM_INVALID_ACCESS );
622cdf0e10cSrcweir }
623cdf0e10cSrcweir 
624cdf0e10cSrcweir void SfxOleThumbnailProperty::ImplSave( SvStream& rStrm )
625cdf0e10cSrcweir {
626cdf0e10cSrcweir     /*  Type        Contents
627cdf0e10cSrcweir         -----------------------------------------------------------------------
628cdf0e10cSrcweir         int32       size of following data
629cdf0e10cSrcweir         int32       clipboard format tag (see below)
630cdf0e10cSrcweir         byte[]      clipboard data (see below)
631cdf0e10cSrcweir 
632cdf0e10cSrcweir         Clipboard format tag:
633cdf0e10cSrcweir             -1 = Windows clipboard format
634cdf0e10cSrcweir             -2 = Macintosh clipboard format
635cdf0e10cSrcweir             -3 = GUID that contains a format identifier (FMTID)
636cdf0e10cSrcweir             >0 = custom clipboard format name plus data (see msdn site below)
637cdf0e10cSrcweir             0  = no data
638cdf0e10cSrcweir 
639cdf0e10cSrcweir         References:
640cdf0e10cSrcweir         http://msdn.microsoft.com/library/default.asp?url=/library/en-us/stg/stg/propvariant.asp
641cdf0e10cSrcweir         http://jakarta.apache.org/poi/hpsf/thumbnails.html
642cdf0e10cSrcweir         http://linux.com.hk/docs/poi/org/apache/poi/hpsf/Thumbnail.html
643cdf0e10cSrcweir         http://sparks.discreet.com/knowledgebase/public/solutions/ExtractThumbnailImg.htm
644cdf0e10cSrcweir      */
645cdf0e10cSrcweir     if( IsValid() )
646cdf0e10cSrcweir     {
647cdf0e10cSrcweir         // clipboard size: clip_format_tag + data_format_tag + bitmap_len
648cdf0e10cSrcweir         sal_Int32 nClipSize = static_cast< sal_Int32 >( 4 + 4 + mData.getLength() );
649cdf0e10cSrcweir         rStrm << nClipSize << CLIPFMT_WIN << CLIPDATAFMT_DIB;
650cdf0e10cSrcweir         rStrm.Write( mData.getConstArray(), mData.getLength() );
651cdf0e10cSrcweir     }
652cdf0e10cSrcweir     else
653cdf0e10cSrcweir     {
654cdf0e10cSrcweir         DBG_ERRORFILE( "SfxOleThumbnailProperty::ImplSave - invalid thumbnail property" );
655cdf0e10cSrcweir         SetError( SVSTREAM_INVALID_ACCESS );
656cdf0e10cSrcweir     }
657cdf0e10cSrcweir }
658cdf0e10cSrcweir 
659cdf0e10cSrcweir // ----------------------------------------------------------------------------
660cdf0e10cSrcweir 
661cdf0e10cSrcweir SfxOleBlobProperty::SfxOleBlobProperty( sal_Int32 nPropId,
662cdf0e10cSrcweir         const uno::Sequence<sal_uInt8> & i_rData) :
663cdf0e10cSrcweir     SfxOlePropertyBase( nPropId, PROPTYPE_BLOB ),
664cdf0e10cSrcweir     mData(i_rData)
665cdf0e10cSrcweir {
666cdf0e10cSrcweir }
667cdf0e10cSrcweir 
668cdf0e10cSrcweir void SfxOleBlobProperty::ImplLoad( SvStream& )
669cdf0e10cSrcweir {
670cdf0e10cSrcweir     DBG_ERRORFILE( "SfxOleBlobProperty::ImplLoad - not implemented" );
671cdf0e10cSrcweir     SetError( SVSTREAM_INVALID_ACCESS );
672cdf0e10cSrcweir }
673cdf0e10cSrcweir 
674cdf0e10cSrcweir void SfxOleBlobProperty::ImplSave( SvStream& rStrm )
675cdf0e10cSrcweir {
676cdf0e10cSrcweir     if (IsValid()) {
677cdf0e10cSrcweir         rStrm.Write( mData.getConstArray(), mData.getLength() );
678cdf0e10cSrcweir     } else {
679cdf0e10cSrcweir         DBG_ERRORFILE( "SfxOleBlobProperty::ImplSave - invalid BLOB property" );
680cdf0e10cSrcweir         SetError( SVSTREAM_INVALID_ACCESS );
681cdf0e10cSrcweir     }
682cdf0e10cSrcweir }
683cdf0e10cSrcweir 
684cdf0e10cSrcweir // ----------------------------------------------------------------------------
685cdf0e10cSrcweir 
686cdf0e10cSrcweir SfxOleDictionaryProperty::SfxOleDictionaryProperty( const SfxOleTextEncoding& rTextEnc ) :
687cdf0e10cSrcweir     SfxOlePropertyBase( PROPID_DICTIONARY, 0 ),
688cdf0e10cSrcweir     SfxOleStringHelper( rTextEnc )
689cdf0e10cSrcweir {
690cdf0e10cSrcweir }
691cdf0e10cSrcweir 
692cdf0e10cSrcweir const String& SfxOleDictionaryProperty::GetPropertyName( sal_Int32 nPropId ) const
693cdf0e10cSrcweir {
694cdf0e10cSrcweir     SfxOlePropNameMap::const_iterator aIt = maPropNameMap.find( nPropId );
695cdf0e10cSrcweir     return (aIt == maPropNameMap.end()) ? String::EmptyString() : aIt->second;
696cdf0e10cSrcweir }
697cdf0e10cSrcweir 
698cdf0e10cSrcweir void SfxOleDictionaryProperty::SetPropertyName( sal_Int32 nPropId, const String& rPropName )
699cdf0e10cSrcweir {
700cdf0e10cSrcweir     maPropNameMap[ nPropId ] = rPropName;
701cdf0e10cSrcweir     // dictionary property contains number of pairs in property type field
702cdf0e10cSrcweir     SetPropType( static_cast< sal_Int32 >( maPropNameMap.size() ) );
703cdf0e10cSrcweir }
704cdf0e10cSrcweir 
705cdf0e10cSrcweir void SfxOleDictionaryProperty::ImplLoad( SvStream& rStrm )
706cdf0e10cSrcweir {
707cdf0e10cSrcweir     // dictionary property contains number of pairs in property type field
708cdf0e10cSrcweir     sal_Int32 nNameCount = GetPropType();
709cdf0e10cSrcweir     // read property ID/name pairs
710cdf0e10cSrcweir     maPropNameMap.clear();
711cdf0e10cSrcweir     for( sal_Int32 nIdx = 0; (nIdx < nNameCount) && (rStrm.GetErrorCode() == SVSTREAM_OK) && !rStrm.IsEof(); ++nIdx )
712cdf0e10cSrcweir     {
713cdf0e10cSrcweir         sal_Int32 nPropId;
714cdf0e10cSrcweir         rStrm >> nPropId;
715cdf0e10cSrcweir         // name always stored as byte string
716cdf0e10cSrcweir         maPropNameMap[ nPropId ] = LoadString8( rStrm );
717cdf0e10cSrcweir     }
718cdf0e10cSrcweir }
719cdf0e10cSrcweir 
720cdf0e10cSrcweir void SfxOleDictionaryProperty::ImplSave( SvStream& rStrm )
721cdf0e10cSrcweir {
722cdf0e10cSrcweir     // write property ID/name pairs
723cdf0e10cSrcweir     for( SfxOlePropNameMap::const_iterator aIt = maPropNameMap.begin(), aEnd = maPropNameMap.end(); aIt != aEnd; ++aIt )
724cdf0e10cSrcweir     {
725cdf0e10cSrcweir         rStrm << aIt->first;
726cdf0e10cSrcweir         // name always stored as byte string
727cdf0e10cSrcweir         SaveString8( rStrm, aIt->second );
728cdf0e10cSrcweir     }
729cdf0e10cSrcweir }
730cdf0e10cSrcweir 
731cdf0e10cSrcweir // ----------------------------------------------------------------------------
732cdf0e10cSrcweir 
733cdf0e10cSrcweir SfxOleSection::SfxOleSection( bool bSupportsDict ) :
734cdf0e10cSrcweir     maDictProp( maCodePageProp ),
735cdf0e10cSrcweir     mnStartPos( 0 ),
736cdf0e10cSrcweir     mbSupportsDict( bSupportsDict )
737cdf0e10cSrcweir {
738cdf0e10cSrcweir }
739cdf0e10cSrcweir 
740cdf0e10cSrcweir SfxOlePropertyRef SfxOleSection::GetProperty( sal_Int32 nPropId ) const
741cdf0e10cSrcweir {
742cdf0e10cSrcweir     SfxOlePropertyRef xProp;
743cdf0e10cSrcweir     SfxOlePropMap::const_iterator aIt = maPropMap.find( nPropId );
744cdf0e10cSrcweir     if( aIt != maPropMap.end() )
745cdf0e10cSrcweir         xProp = aIt->second;
746cdf0e10cSrcweir     return xProp;
747cdf0e10cSrcweir }
748cdf0e10cSrcweir 
749cdf0e10cSrcweir bool SfxOleSection::GetInt32Value( sal_Int32& rnValue, sal_Int32 nPropId ) const
750cdf0e10cSrcweir {
751cdf0e10cSrcweir     SfxOlePropertyRef xProp = GetProperty( nPropId );
752cdf0e10cSrcweir     const SfxOleInt32Property* pProp =
753cdf0e10cSrcweir         dynamic_cast< const SfxOleInt32Property* >( xProp.get() );
754cdf0e10cSrcweir     if( pProp )
755cdf0e10cSrcweir         rnValue = pProp->GetValue();
756cdf0e10cSrcweir     return pProp != 0;
757cdf0e10cSrcweir }
758cdf0e10cSrcweir 
759cdf0e10cSrcweir bool SfxOleSection::GetDoubleValue( double& rfValue, sal_Int32 nPropId ) const
760cdf0e10cSrcweir {
761cdf0e10cSrcweir     SfxOlePropertyRef xProp = GetProperty( nPropId );
762cdf0e10cSrcweir     const SfxOleDoubleProperty* pProp =
763cdf0e10cSrcweir         dynamic_cast< const SfxOleDoubleProperty* >( xProp.get() );
764cdf0e10cSrcweir     if( pProp )
765cdf0e10cSrcweir         rfValue = pProp->GetValue();
766cdf0e10cSrcweir     return pProp != 0;
767cdf0e10cSrcweir }
768cdf0e10cSrcweir 
769cdf0e10cSrcweir bool SfxOleSection::GetBoolValue( bool& rbValue, sal_Int32 nPropId ) const
770cdf0e10cSrcweir {
771cdf0e10cSrcweir     SfxOlePropertyRef xProp = GetProperty( nPropId );
772cdf0e10cSrcweir     const SfxOleBoolProperty* pProp =
773cdf0e10cSrcweir         dynamic_cast< const SfxOleBoolProperty* >( xProp.get() );
774cdf0e10cSrcweir     if( pProp )
775cdf0e10cSrcweir         rbValue = pProp->GetValue();
776cdf0e10cSrcweir     return pProp != 0;
777cdf0e10cSrcweir }
778cdf0e10cSrcweir 
779cdf0e10cSrcweir bool SfxOleSection::GetStringValue( String& rValue, sal_Int32 nPropId ) const
780cdf0e10cSrcweir {
781cdf0e10cSrcweir     SfxOlePropertyRef xProp = GetProperty( nPropId );
782cdf0e10cSrcweir     const SfxOleStringPropertyBase* pProp =
783cdf0e10cSrcweir         dynamic_cast< const SfxOleStringPropertyBase* >( xProp.get() );
784cdf0e10cSrcweir     if( pProp )
785cdf0e10cSrcweir         rValue = pProp->GetValue();
786cdf0e10cSrcweir     return pProp != 0;
787cdf0e10cSrcweir }
788cdf0e10cSrcweir 
789cdf0e10cSrcweir bool SfxOleSection::GetFileTimeValue( util::DateTime& rValue, sal_Int32 nPropId ) const
790cdf0e10cSrcweir {
791cdf0e10cSrcweir     SfxOlePropertyRef xProp = GetProperty( nPropId );
792cdf0e10cSrcweir     const SfxOleFileTimeProperty* pProp =
793cdf0e10cSrcweir         dynamic_cast< const SfxOleFileTimeProperty* >( xProp.get() );
794cdf0e10cSrcweir     if( pProp )
795cdf0e10cSrcweir 	{
796cdf0e10cSrcweir 		if ( pProp->GetValue() == TIMESTAMP_INVALID_UTILDATETIME )
797cdf0e10cSrcweir 			rValue = util::DateTime();
798cdf0e10cSrcweir 		else
799cdf0e10cSrcweir 			rValue = pProp->GetValue();
800cdf0e10cSrcweir 	}
801cdf0e10cSrcweir     return pProp != 0;
802cdf0e10cSrcweir }
803cdf0e10cSrcweir 
804cdf0e10cSrcweir void SfxOleSection::SetProperty( SfxOlePropertyRef xProp )
805cdf0e10cSrcweir {
806cdf0e10cSrcweir     if( xProp.get() )
807cdf0e10cSrcweir         maPropMap[ xProp->GetPropId() ] = xProp;
808cdf0e10cSrcweir }
809cdf0e10cSrcweir 
810cdf0e10cSrcweir void SfxOleSection::SetInt32Value( sal_Int32 nPropId, sal_Int32 nValue )
811cdf0e10cSrcweir {
812cdf0e10cSrcweir     SetProperty( SfxOlePropertyRef( new SfxOleInt32Property( nPropId, nValue ) ) );
813cdf0e10cSrcweir }
814cdf0e10cSrcweir 
815cdf0e10cSrcweir void SfxOleSection::SetDoubleValue( sal_Int32 nPropId, double fValue )
816cdf0e10cSrcweir {
817cdf0e10cSrcweir     SetProperty( SfxOlePropertyRef( new SfxOleDoubleProperty( nPropId, fValue ) ) );
818cdf0e10cSrcweir }
819cdf0e10cSrcweir 
820cdf0e10cSrcweir void SfxOleSection::SetBoolValue( sal_Int32 nPropId, bool bValue )
821cdf0e10cSrcweir {
822cdf0e10cSrcweir     SetProperty( SfxOlePropertyRef( new SfxOleBoolProperty( nPropId, bValue ) ) );
823cdf0e10cSrcweir }
824cdf0e10cSrcweir 
825cdf0e10cSrcweir bool SfxOleSection::SetStringValue( sal_Int32 nPropId, const String& rValue, bool bSkipEmpty )
826cdf0e10cSrcweir {
827cdf0e10cSrcweir     bool bInserted = !bSkipEmpty || (rValue.Len() > 0);
828cdf0e10cSrcweir     if( bInserted )
829cdf0e10cSrcweir         SetProperty( SfxOlePropertyRef( new SfxOleString8Property( nPropId, maCodePageProp, rValue ) ) );
830cdf0e10cSrcweir     return bInserted;
831cdf0e10cSrcweir }
832cdf0e10cSrcweir 
833cdf0e10cSrcweir void SfxOleSection::SetFileTimeValue( sal_Int32 nPropId, const util::DateTime& rValue )
834cdf0e10cSrcweir {
835cdf0e10cSrcweir 	if ( rValue.Year == 0 || rValue.Month == 0 || rValue.Day == 0 )
836cdf0e10cSrcweir 	    SetProperty( SfxOlePropertyRef( new SfxOleFileTimeProperty( nPropId, TIMESTAMP_INVALID_UTILDATETIME ) ) );
837cdf0e10cSrcweir 	else
838cdf0e10cSrcweir 	    SetProperty( SfxOlePropertyRef( new SfxOleFileTimeProperty( nPropId, rValue ) ) );
839cdf0e10cSrcweir }
840cdf0e10cSrcweir 
841cdf0e10cSrcweir void SfxOleSection::SetThumbnailValue( sal_Int32 nPropId,
842cdf0e10cSrcweir     const uno::Sequence<sal_uInt8> & i_rData)
843cdf0e10cSrcweir {
844cdf0e10cSrcweir     SfxOleThumbnailProperty* pThumbnail = new SfxOleThumbnailProperty( nPropId, i_rData );
845cdf0e10cSrcweir     SfxOlePropertyRef xProp( pThumbnail );  // take ownership
846cdf0e10cSrcweir     if( pThumbnail->IsValid() )
847cdf0e10cSrcweir         SetProperty( xProp );
848cdf0e10cSrcweir }
849cdf0e10cSrcweir 
850cdf0e10cSrcweir void SfxOleSection::SetBlobValue( sal_Int32 nPropId,
851cdf0e10cSrcweir     const uno::Sequence<sal_uInt8> & i_rData)
852cdf0e10cSrcweir {
853cdf0e10cSrcweir     SfxOleBlobProperty* pBlob( new SfxOleBlobProperty( nPropId, i_rData ) );
854cdf0e10cSrcweir     SfxOlePropertyRef xProp( pBlob );
855cdf0e10cSrcweir     if( pBlob->IsValid() ) {
856cdf0e10cSrcweir         SetProperty( xProp );
857cdf0e10cSrcweir     }
858cdf0e10cSrcweir }
859cdf0e10cSrcweir 
860cdf0e10cSrcweir Any SfxOleSection::GetAnyValue( sal_Int32 nPropId ) const
861cdf0e10cSrcweir {
862cdf0e10cSrcweir     Any aValue;
863cdf0e10cSrcweir     sal_Int32 nInt32 = 0;
864cdf0e10cSrcweir     double fDouble = 0.0;
865cdf0e10cSrcweir     bool bBool = false;
866cdf0e10cSrcweir     String aString;
867cdf0e10cSrcweir     ::com::sun::star::util::DateTime aApiDateTime;
868cdf0e10cSrcweir 
869cdf0e10cSrcweir     if( GetInt32Value( nInt32, nPropId ) )
870cdf0e10cSrcweir         aValue <<= nInt32;
871cdf0e10cSrcweir     else if( GetDoubleValue( fDouble, nPropId ) )
872cdf0e10cSrcweir         aValue <<= fDouble;
873cdf0e10cSrcweir     else if( GetBoolValue( bBool, nPropId ) )
874cdf0e10cSrcweir         ::comphelper::setBOOL( aValue, bBool ? sal_True : sal_False );
875cdf0e10cSrcweir     else if( GetStringValue( aString, nPropId ) )
876cdf0e10cSrcweir         aValue <<= OUString( aString );
877cdf0e10cSrcweir     else if( GetFileTimeValue( aApiDateTime, nPropId ) )
878cdf0e10cSrcweir     {
879cdf0e10cSrcweir         aValue <<= aApiDateTime;
880cdf0e10cSrcweir     }
881cdf0e10cSrcweir     return aValue;
882cdf0e10cSrcweir }
883cdf0e10cSrcweir 
884cdf0e10cSrcweir bool SfxOleSection::SetAnyValue( sal_Int32 nPropId, const Any& rValue )
885cdf0e10cSrcweir {
886cdf0e10cSrcweir     bool bInserted = true;
887cdf0e10cSrcweir     sal_Int32 nInt32 = 0;
888cdf0e10cSrcweir     double fDouble = 0.0;
889cdf0e10cSrcweir     OUString aString;
890cdf0e10cSrcweir     ::com::sun::star::util::DateTime aApiDateTime;
891cdf0e10cSrcweir 
892cdf0e10cSrcweir     if( rValue.getValueType() == ::getBooleanCppuType() )
893cdf0e10cSrcweir         SetBoolValue( nPropId, ::comphelper::getBOOL( rValue ) == sal_True );
894cdf0e10cSrcweir     else if( rValue >>= nInt32 )
895cdf0e10cSrcweir         SetInt32Value( nPropId, nInt32 );
896cdf0e10cSrcweir     else if( rValue >>= fDouble )
897cdf0e10cSrcweir         SetDoubleValue( nPropId, fDouble );
898cdf0e10cSrcweir     else if( rValue >>= aString )
899cdf0e10cSrcweir         bInserted = SetStringValue( nPropId, aString );
900cdf0e10cSrcweir     else if( rValue >>= aApiDateTime )
901cdf0e10cSrcweir     {
902cdf0e10cSrcweir         SetFileTimeValue( nPropId, aApiDateTime );
903cdf0e10cSrcweir     }
904cdf0e10cSrcweir     else
905cdf0e10cSrcweir         bInserted = false;
906cdf0e10cSrcweir     return bInserted;
907cdf0e10cSrcweir }
908cdf0e10cSrcweir 
909cdf0e10cSrcweir const String& SfxOleSection::GetPropertyName( sal_Int32 nPropId ) const
910cdf0e10cSrcweir {
911cdf0e10cSrcweir     return maDictProp.GetPropertyName( nPropId );
912cdf0e10cSrcweir }
913cdf0e10cSrcweir 
914cdf0e10cSrcweir void SfxOleSection::SetPropertyName( sal_Int32 nPropId, const String& rPropName )
915cdf0e10cSrcweir {
916cdf0e10cSrcweir     maDictProp.SetPropertyName( nPropId, rPropName );
917cdf0e10cSrcweir }
918cdf0e10cSrcweir 
919cdf0e10cSrcweir void SfxOleSection::GetPropertyIds( ::std::vector< sal_Int32 >& rPropIds ) const
920cdf0e10cSrcweir {
921cdf0e10cSrcweir     rPropIds.clear();
922cdf0e10cSrcweir     for( SfxOlePropMap::const_iterator aIt = maPropMap.begin(), aEnd = maPropMap.end(); aIt != aEnd; ++aIt )
923cdf0e10cSrcweir         rPropIds.push_back( aIt->first );
924cdf0e10cSrcweir }
925cdf0e10cSrcweir 
926cdf0e10cSrcweir sal_Int32 SfxOleSection::GetFreePropertyId() const
927cdf0e10cSrcweir {
928cdf0e10cSrcweir     return maPropMap.empty() ? PROPID_FIRSTCUSTOM : (maPropMap.rbegin()->first + 1);
929cdf0e10cSrcweir }
930cdf0e10cSrcweir 
931cdf0e10cSrcweir void SfxOleSection::ImplLoad( SvStream& rStrm )
932cdf0e10cSrcweir {
933cdf0e10cSrcweir     // read section header
934cdf0e10cSrcweir     mnStartPos = rStrm.Tell();
935cdf0e10cSrcweir     sal_uInt32 nSize;
936cdf0e10cSrcweir     sal_Int32 nPropCount;
937cdf0e10cSrcweir     rStrm >> nSize >> nPropCount;
938cdf0e10cSrcweir 
939cdf0e10cSrcweir     // read property ID/position pairs
940cdf0e10cSrcweir     typedef ::std::map< sal_Int32, sal_uInt32 > SfxOlePropPosMap;
941cdf0e10cSrcweir     SfxOlePropPosMap aPropPosMap;
942cdf0e10cSrcweir     for( sal_Int32 nPropIdx = 0; (nPropIdx < nPropCount) && (rStrm.GetErrorCode() == SVSTREAM_OK) && !rStrm.IsEof(); ++nPropIdx )
943cdf0e10cSrcweir     {
944cdf0e10cSrcweir         sal_Int32 nPropId;
945cdf0e10cSrcweir         sal_uInt32 nPropPos;
946cdf0e10cSrcweir         rStrm >> nPropId >> nPropPos;
947cdf0e10cSrcweir         aPropPosMap[ nPropId ] = nPropPos;
948cdf0e10cSrcweir     }
949cdf0e10cSrcweir 
950cdf0e10cSrcweir     // read codepage property
951cdf0e10cSrcweir     SfxOlePropPosMap::iterator aCodePageIt = aPropPosMap.find( PROPID_CODEPAGE );
952cdf0e10cSrcweir     if( (aCodePageIt != aPropPosMap.end()) && SeekToPropertyPos( rStrm, aCodePageIt->second ) )
953cdf0e10cSrcweir     {
954cdf0e10cSrcweir         // codepage property must be of type signed int-16
955cdf0e10cSrcweir         sal_Int32 nPropType;
956cdf0e10cSrcweir         rStrm >> nPropType;
957cdf0e10cSrcweir         if( nPropType == PROPTYPE_INT16 )
958cdf0e10cSrcweir             LoadObject( rStrm, maCodePageProp );
959cdf0e10cSrcweir         // remove property position
960cdf0e10cSrcweir         aPropPosMap.erase( aCodePageIt );
961cdf0e10cSrcweir     }
962cdf0e10cSrcweir 
963cdf0e10cSrcweir     // read dictionary property
964cdf0e10cSrcweir     SfxOlePropPosMap::iterator aDictIt = aPropPosMap.find( PROPID_DICTIONARY );
965cdf0e10cSrcweir     if( (aDictIt != aPropPosMap.end()) && SeekToPropertyPos( rStrm, aDictIt->second ) )
966cdf0e10cSrcweir     {
967cdf0e10cSrcweir         // #i66214# #i66428# applications may write broken dictionary properties in wrong sections
968cdf0e10cSrcweir         if( mbSupportsDict )
969cdf0e10cSrcweir         {
970cdf0e10cSrcweir             // dictionary property contains number of pairs in property type field
971cdf0e10cSrcweir             sal_Int32 nNameCount;
972cdf0e10cSrcweir             rStrm >> nNameCount;
973cdf0e10cSrcweir             maDictProp.SetNameCount( nNameCount );
974cdf0e10cSrcweir             LoadObject( rStrm, maDictProp );
975cdf0e10cSrcweir         }
976cdf0e10cSrcweir         // always remove position of dictionary property (do not try to read it again below)
977cdf0e10cSrcweir         aPropPosMap.erase( aDictIt );
978cdf0e10cSrcweir     }
979cdf0e10cSrcweir 
980cdf0e10cSrcweir     // read other properties
981cdf0e10cSrcweir     maPropMap.clear();
982cdf0e10cSrcweir     for( SfxOlePropPosMap::const_iterator aIt = aPropPosMap.begin(), aEnd = aPropPosMap.end(); aIt != aEnd; ++aIt )
983cdf0e10cSrcweir         if( SeekToPropertyPos( rStrm, aIt->second ) )
984cdf0e10cSrcweir             LoadProperty( rStrm, aIt->first );
985cdf0e10cSrcweir }
986cdf0e10cSrcweir 
987cdf0e10cSrcweir void SfxOleSection::ImplSave( SvStream& rStrm )
988cdf0e10cSrcweir {
989cdf0e10cSrcweir     /*  Always export with UTF-8 encoding. All dependent properties (bytestring
990cdf0e10cSrcweir         and dictionary) will be updated automatically. */
991cdf0e10cSrcweir     maCodePageProp.SetTextEncoding( RTL_TEXTENCODING_UTF8 );
992cdf0e10cSrcweir 
993cdf0e10cSrcweir     // write section header
994cdf0e10cSrcweir     mnStartPos = rStrm.Tell();
995cdf0e10cSrcweir     sal_Int32 nPropCount = static_cast< sal_Int32 >( maPropMap.size() + 1 );
996cdf0e10cSrcweir     if( maDictProp.HasPropertyNames() )
997cdf0e10cSrcweir         ++nPropCount;
998cdf0e10cSrcweir     rStrm << sal_uInt32( 0 ) << nPropCount;
999cdf0e10cSrcweir 
1000cdf0e10cSrcweir     // write placeholders for property ID/position pairs
1001cdf0e10cSrcweir     sal_Size nPropPosPos = rStrm.Tell();
1002cdf0e10cSrcweir     rStrm.SeekRel( static_cast< sal_sSize >( 8 * nPropCount ) );
1003cdf0e10cSrcweir 
1004cdf0e10cSrcweir     // write dictionary property
1005cdf0e10cSrcweir     if( maDictProp.HasPropertyNames() )
1006cdf0e10cSrcweir         SaveProperty( rStrm, maDictProp, nPropPosPos );
1007cdf0e10cSrcweir     // write codepage property
1008cdf0e10cSrcweir     SaveProperty( rStrm, maCodePageProp, nPropPosPos );
1009cdf0e10cSrcweir     // write other properties
1010cdf0e10cSrcweir     for( SfxOlePropMap::const_iterator aIt = maPropMap.begin(), aEnd = maPropMap.end(); aIt != aEnd; ++aIt )
1011cdf0e10cSrcweir         SaveProperty( rStrm, *aIt->second, nPropPosPos );
1012cdf0e10cSrcweir 
1013cdf0e10cSrcweir     // write section size (first field in section header)
1014cdf0e10cSrcweir     rStrm.Seek( STREAM_SEEK_TO_END );
1015cdf0e10cSrcweir     sal_uInt32 nSectSize = static_cast< sal_uInt32 >( rStrm.Tell() - mnStartPos );
1016cdf0e10cSrcweir     rStrm.Seek( mnStartPos );
1017cdf0e10cSrcweir     rStrm << nSectSize;
1018cdf0e10cSrcweir }
1019cdf0e10cSrcweir 
1020cdf0e10cSrcweir bool SfxOleSection::SeekToPropertyPos( SvStream& rStrm, sal_uInt32 nPropPos ) const
1021cdf0e10cSrcweir {
1022cdf0e10cSrcweir     rStrm.Seek( static_cast< sal_Size >( mnStartPos + nPropPos ) );
1023cdf0e10cSrcweir     return rStrm.GetErrorCode() == SVSTREAM_OK;
1024cdf0e10cSrcweir }
1025cdf0e10cSrcweir 
1026cdf0e10cSrcweir void SfxOleSection::LoadProperty( SvStream& rStrm, sal_Int32 nPropId )
1027cdf0e10cSrcweir {
1028cdf0e10cSrcweir     // property data type
1029cdf0e10cSrcweir     sal_Int32 nPropType;
1030cdf0e10cSrcweir     rStrm >> nPropType;
1031cdf0e10cSrcweir     // create empty property object
1032cdf0e10cSrcweir     SfxOlePropertyRef xProp;
1033cdf0e10cSrcweir     switch( nPropType )
1034cdf0e10cSrcweir     {
1035cdf0e10cSrcweir         case PROPTYPE_INT32:
1036cdf0e10cSrcweir             xProp.reset( new SfxOleInt32Property( nPropId ) );
1037cdf0e10cSrcweir         break;
1038cdf0e10cSrcweir         case PROPTYPE_DOUBLE:
1039cdf0e10cSrcweir             xProp.reset( new SfxOleDoubleProperty( nPropId ) );
1040cdf0e10cSrcweir         break;
1041cdf0e10cSrcweir         case PROPTYPE_BOOL:
1042cdf0e10cSrcweir             xProp.reset( new SfxOleBoolProperty( nPropId ) );
1043cdf0e10cSrcweir         break;
1044cdf0e10cSrcweir         case PROPTYPE_STRING8:
1045cdf0e10cSrcweir             xProp.reset( new SfxOleString8Property( nPropId, maCodePageProp ) );
1046cdf0e10cSrcweir         break;
1047cdf0e10cSrcweir         case PROPTYPE_STRING16:
1048cdf0e10cSrcweir             xProp.reset( new SfxOleString16Property( nPropId ) );
1049cdf0e10cSrcweir         break;
1050cdf0e10cSrcweir         case PROPTYPE_FILETIME:
1051cdf0e10cSrcweir             xProp.reset( new SfxOleFileTimeProperty( nPropId ) );
1052cdf0e10cSrcweir         break;
1053cdf0e10cSrcweir     }
1054cdf0e10cSrcweir     // load property contents
1055cdf0e10cSrcweir     if( xProp.get() )
1056cdf0e10cSrcweir     {
1057cdf0e10cSrcweir         SetError( xProp->Load( rStrm ) );
1058cdf0e10cSrcweir         maPropMap[ nPropId ] = xProp;
1059cdf0e10cSrcweir     }
1060cdf0e10cSrcweir }
1061cdf0e10cSrcweir 
1062cdf0e10cSrcweir void SfxOleSection::SaveProperty( SvStream& rStrm, SfxOlePropertyBase& rProp, sal_Size& rnPropPosPos )
1063cdf0e10cSrcweir {
1064cdf0e10cSrcweir     rStrm.Seek( STREAM_SEEK_TO_END );
1065cdf0e10cSrcweir     sal_uInt32 nPropPos = static_cast< sal_uInt32 >( rStrm.Tell() - mnStartPos );
1066cdf0e10cSrcweir     // property data type
1067cdf0e10cSrcweir     rStrm << rProp.GetPropType();
1068cdf0e10cSrcweir     // write property contents
1069cdf0e10cSrcweir     SaveObject( rStrm, rProp );
1070cdf0e10cSrcweir     // align to 32-bit
1071cdf0e10cSrcweir     while( (rStrm.Tell() & 3) != 0 )
1072cdf0e10cSrcweir         rStrm << sal_uInt8( 0 );
1073cdf0e10cSrcweir     // write property ID/position pair
1074cdf0e10cSrcweir     rStrm.Seek( rnPropPosPos );
1075cdf0e10cSrcweir     rStrm << rProp.GetPropId() << nPropPos;
1076cdf0e10cSrcweir     rnPropPosPos = rStrm.Tell();
1077cdf0e10cSrcweir }
1078cdf0e10cSrcweir 
1079cdf0e10cSrcweir // ----------------------------------------------------------------------------
1080cdf0e10cSrcweir 
1081cdf0e10cSrcweir ErrCode SfxOlePropertySet::LoadPropertySet( SotStorage* pStrg, const String& rStrmName )
1082cdf0e10cSrcweir {
1083cdf0e10cSrcweir     if( pStrg )
1084cdf0e10cSrcweir     {
1085cdf0e10cSrcweir         SotStorageStreamRef xStrm = pStrg->OpenSotStream( rStrmName, STREAM_STD_READ );
1086cdf0e10cSrcweir         if( xStrm.Is() && (xStrm->GetError() == SVSTREAM_OK) )
1087cdf0e10cSrcweir         {
1088cdf0e10cSrcweir             xStrm->SetBufferSize( STREAM_BUFFER_SIZE );
1089cdf0e10cSrcweir             Load( *xStrm );
1090cdf0e10cSrcweir         }
1091cdf0e10cSrcweir         else
1092cdf0e10cSrcweir             SetError( ERRCODE_IO_ACCESSDENIED );
1093cdf0e10cSrcweir     }
1094cdf0e10cSrcweir     else
1095cdf0e10cSrcweir         SetError( ERRCODE_IO_ACCESSDENIED );
1096cdf0e10cSrcweir     return GetError();
1097cdf0e10cSrcweir }
1098cdf0e10cSrcweir 
1099cdf0e10cSrcweir ErrCode SfxOlePropertySet::SavePropertySet( SotStorage* pStrg, const String& rStrmName )
1100cdf0e10cSrcweir {
1101cdf0e10cSrcweir     if( pStrg )
1102cdf0e10cSrcweir     {
1103cdf0e10cSrcweir         SotStorageStreamRef xStrm = pStrg->OpenSotStream( rStrmName, STREAM_TRUNC | STREAM_STD_WRITE );
1104cdf0e10cSrcweir         if( xStrm.Is() )
1105cdf0e10cSrcweir             Save( *xStrm );
1106cdf0e10cSrcweir         else
1107cdf0e10cSrcweir             SetError( ERRCODE_IO_ACCESSDENIED );
1108cdf0e10cSrcweir     }
1109cdf0e10cSrcweir     else
1110cdf0e10cSrcweir         SetError( ERRCODE_IO_ACCESSDENIED );
1111cdf0e10cSrcweir     return GetError();
1112cdf0e10cSrcweir }
1113cdf0e10cSrcweir 
1114cdf0e10cSrcweir SfxOleSectionRef SfxOlePropertySet::GetSection( SfxOleSectionType eSection ) const
1115cdf0e10cSrcweir {
1116cdf0e10cSrcweir     return GetSection( GetSectionGuid( eSection ) );
1117cdf0e10cSrcweir }
1118cdf0e10cSrcweir 
1119cdf0e10cSrcweir SfxOleSectionRef SfxOlePropertySet::GetSection( const SvGlobalName& rSectionGuid ) const
1120cdf0e10cSrcweir {
1121cdf0e10cSrcweir     SfxOleSectionRef xSection;
1122cdf0e10cSrcweir     SfxOleSectionMap::const_iterator aIt = maSectionMap.find( rSectionGuid );
1123cdf0e10cSrcweir     if( aIt != maSectionMap.end() )
1124cdf0e10cSrcweir         xSection = aIt->second;
1125cdf0e10cSrcweir     return xSection;
1126cdf0e10cSrcweir }
1127cdf0e10cSrcweir 
1128cdf0e10cSrcweir SfxOleSection& SfxOlePropertySet::AddSection( SfxOleSectionType eSection )
1129cdf0e10cSrcweir {
1130cdf0e10cSrcweir     return AddSection( GetSectionGuid( eSection ) );
1131cdf0e10cSrcweir }
1132cdf0e10cSrcweir 
1133cdf0e10cSrcweir SfxOleSection& SfxOlePropertySet::AddSection( const SvGlobalName& rSectionGuid )
1134cdf0e10cSrcweir {
1135cdf0e10cSrcweir     SfxOleSectionRef xSection = GetSection( rSectionGuid );
1136cdf0e10cSrcweir     if( !xSection )
1137cdf0e10cSrcweir     {
1138cdf0e10cSrcweir         // #i66214# #i66428# applications may write broken dictionary properties in wrong sections
1139cdf0e10cSrcweir         bool bSupportsDict = rSectionGuid == GetSectionGuid( SECTION_CUSTOM );
1140cdf0e10cSrcweir         xSection.reset( new SfxOleSection( bSupportsDict ) );
1141cdf0e10cSrcweir         maSectionMap[ rSectionGuid ] = xSection;
1142cdf0e10cSrcweir     }
1143cdf0e10cSrcweir     return *xSection;
1144cdf0e10cSrcweir }
1145cdf0e10cSrcweir 
1146cdf0e10cSrcweir void SfxOlePropertySet::ImplLoad( SvStream& rStrm )
1147cdf0e10cSrcweir {
1148cdf0e10cSrcweir     // read property set header
1149cdf0e10cSrcweir     sal_uInt16 nByteOrder;
1150cdf0e10cSrcweir     sal_uInt16 nVersion;
1151cdf0e10cSrcweir     sal_uInt16 nOsMinor;
1152cdf0e10cSrcweir     sal_uInt16 nOsType;
1153cdf0e10cSrcweir     SvGlobalName aGuid;
1154cdf0e10cSrcweir     sal_Int32 nSectCount;
1155cdf0e10cSrcweir     rStrm >> nByteOrder >> nVersion >> nOsMinor >> nOsType >> aGuid >> nSectCount;
1156cdf0e10cSrcweir 
1157cdf0e10cSrcweir     // read sections
1158cdf0e10cSrcweir     sal_Size nSectPosPos = rStrm.Tell();
1159cdf0e10cSrcweir     for( sal_Int32 nSectIdx = 0; (nSectIdx < nSectCount) && (rStrm.GetErrorCode() == SVSTREAM_OK) && !rStrm.IsEof(); ++nSectIdx )
1160cdf0e10cSrcweir     {
1161cdf0e10cSrcweir         // read section guid/position pair
1162cdf0e10cSrcweir         rStrm.Seek( nSectPosPos );
1163cdf0e10cSrcweir         SvGlobalName aSectGuid;
1164cdf0e10cSrcweir         sal_uInt32 nSectPos;
1165cdf0e10cSrcweir         rStrm >> aSectGuid >> nSectPos;
1166cdf0e10cSrcweir         nSectPosPos = rStrm.Tell();
1167cdf0e10cSrcweir         // read section
1168cdf0e10cSrcweir         rStrm.Seek( static_cast< sal_Size >( nSectPos ) );
1169cdf0e10cSrcweir         if( rStrm.GetErrorCode() == SVSTREAM_OK )
1170cdf0e10cSrcweir             LoadObject( rStrm, AddSection( aSectGuid ) );
1171cdf0e10cSrcweir     }
1172cdf0e10cSrcweir }
1173cdf0e10cSrcweir 
1174cdf0e10cSrcweir void SfxOlePropertySet::ImplSave( SvStream& rStrm )
1175cdf0e10cSrcweir {
1176cdf0e10cSrcweir     // write property set header
1177cdf0e10cSrcweir     SvGlobalName aGuid;
1178cdf0e10cSrcweir     sal_Int32 nSectCount = static_cast< sal_Int32 >( maSectionMap.size() );
1179cdf0e10cSrcweir     rStrm   << sal_uInt16( 0xFFFE )     // byte order
1180cdf0e10cSrcweir             << sal_uInt16( 0 )          // version
1181cdf0e10cSrcweir             << sal_uInt16( 1 )          // OS minor version
1182cdf0e10cSrcweir             << sal_uInt16( 2 )          // OS type always windows for text encoding
1183cdf0e10cSrcweir             << aGuid                    // unused guid
1184cdf0e10cSrcweir             << nSectCount;              // number of sections
1185cdf0e10cSrcweir 
1186cdf0e10cSrcweir     // write placeholders for section guid/position pairs
1187cdf0e10cSrcweir     sal_Size nSectPosPos = rStrm.Tell();
1188cdf0e10cSrcweir     rStrm.SeekRel( static_cast< sal_sSize >( 20 * nSectCount ) );
1189cdf0e10cSrcweir 
1190cdf0e10cSrcweir     // write sections
1191cdf0e10cSrcweir     for( SfxOleSectionMap::const_iterator aIt = maSectionMap.begin(), aEnd = maSectionMap.end(); aIt != aEnd; ++aIt )
1192cdf0e10cSrcweir     {
1193cdf0e10cSrcweir         SfxOleSection& rSection = *aIt->second;
1194cdf0e10cSrcweir         rStrm.Seek( STREAM_SEEK_TO_END );
1195cdf0e10cSrcweir         sal_uInt32 nSectPos = static_cast< sal_uInt32 >( rStrm.Tell() );
1196cdf0e10cSrcweir         // write the section
1197cdf0e10cSrcweir         SaveObject( rStrm, rSection );
1198cdf0e10cSrcweir         // write section guid/position pair
1199cdf0e10cSrcweir         rStrm.Seek( nSectPosPos );
1200cdf0e10cSrcweir         rStrm << aIt->first << nSectPos;
1201cdf0e10cSrcweir         nSectPosPos = rStrm.Tell();
1202cdf0e10cSrcweir     }
1203cdf0e10cSrcweir }
1204cdf0e10cSrcweir 
1205cdf0e10cSrcweir const SvGlobalName& SfxOlePropertySet::GetSectionGuid( SfxOleSectionType eSection )
1206cdf0e10cSrcweir {
1207cdf0e10cSrcweir     static const SvGlobalName saGlobalGuid(  0xF29F85E0, 0x4FF9, 0x1068, 0xAB, 0x91, 0x08, 0x00, 0x2B, 0x27, 0xB3, 0xD9 );
1208cdf0e10cSrcweir     static const SvGlobalName saBuiltInGuid( 0xD5CDD502, 0x2E9C, 0x101B, 0x93, 0x97, 0x08, 0x00, 0x2B, 0x2C, 0xF9, 0xAE );
1209cdf0e10cSrcweir     static const SvGlobalName saCustomGuid(  0xD5CDD505, 0x2E9C, 0x101B, 0x93, 0x97, 0x08, 0x00, 0x2B, 0x2C, 0xF9, 0xAE );
1210cdf0e10cSrcweir     static const SvGlobalName saEmptyGuid;
1211cdf0e10cSrcweir     switch( eSection )
1212cdf0e10cSrcweir     {
1213cdf0e10cSrcweir         case SECTION_GLOBAL:    return saGlobalGuid;
1214cdf0e10cSrcweir         case SECTION_BUILTIN:   return saBuiltInGuid;
1215cdf0e10cSrcweir         case SECTION_CUSTOM:    return saCustomGuid;
1216cdf0e10cSrcweir         default:    DBG_ERRORFILE( "SfxOlePropertySet::GetSectionGuid - unknown section type" );
1217cdf0e10cSrcweir     }
1218cdf0e10cSrcweir     return saEmptyGuid;
1219cdf0e10cSrcweir }
1220cdf0e10cSrcweir 
1221cdf0e10cSrcweir // ============================================================================
1222cdf0e10cSrcweir 
1223cdf0e10cSrcweir //} // namespace
1224