Update ooo320-m1
[ooovba.git] / basic / source / sbx / sbxstr.cxx
blobfe8ebd5b0b416c693e0467ffd35e0ceb11650876
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: sbxstr.cxx,v $
10 * $Revision: 1.10 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_basic.hxx"
33 #include <tools/errcode.hxx>
34 #include <basic/sbx.hxx>
35 #include "sbxconv.hxx"
36 #include "sbxres.hxx"
37 #include "runtime.hxx"
38 #ifndef _RTL_USTRBUF_HXX_
39 #include <rtl/ustrbuf.hxx>
40 #endif
41 // AB 29.10.99 Unicode
42 #ifndef _USE_NO_NAMESPACE
43 using namespace rtl;
44 #endif
47 // Die Konversion eines Items auf String wird ueber die Put-Methoden
48 // der einzelnen Datentypen abgewickelt, um doppelten Code zu vermeiden.
50 XubString ImpGetString( const SbxValues* p )
52 SbxValues aTmp;
53 XubString aRes;
54 aTmp.eType = SbxSTRING;
55 aTmp.pString = &aRes;
56 switch( +p->eType )
58 case SbxNULL:
59 SbxBase::SetError( SbxERR_CONVERSION );
60 case SbxEMPTY:
61 break;
62 case SbxCHAR:
63 ImpPutChar( &aTmp, p->nChar ); break;
64 case SbxBYTE:
65 ImpPutByte( &aTmp, p->nByte ); break;
66 case SbxINTEGER:
67 ImpPutInteger( &aTmp, p->nInteger ); break;
68 case SbxBOOL:
69 ImpPutBool( &aTmp, p->nUShort ); break;
70 case SbxUSHORT:
71 ImpPutUShort( &aTmp, p->nUShort ); break;
72 case SbxLONG:
73 ImpPutLong( &aTmp, p->nLong ); break;
74 case SbxULONG:
75 ImpPutULong( &aTmp, p->nULong ); break;
76 case SbxSINGLE:
77 ImpPutSingle( &aTmp, p->nSingle ); break;
78 case SbxDOUBLE:
79 ImpPutDouble( &aTmp, p->nDouble ); break;
80 case SbxCURRENCY:
81 ImpPutCurrency( &aTmp, p->nLong64 ); break;
82 case SbxDECIMAL:
83 case SbxBYREF | SbxDECIMAL:
84 ImpPutDecimal( &aTmp, p->pDecimal ); break;
85 case SbxSALINT64:
86 ImpPutInt64( &aTmp, p->nInt64 ); break;
87 case SbxSALUINT64:
88 ImpPutUInt64( &aTmp, p->uInt64 ); break;
89 case SbxBYREF | SbxSTRING:
90 case SbxSTRING:
91 case SbxLPSTR:
92 if( p->pString )
93 aRes = *p->pString;
94 break;
95 case SbxOBJECT:
97 SbxValue* pVal = PTR_CAST(SbxValue,p->pObj);
98 if( pVal )
99 aRes = pVal->GetString();
100 else if( p->pObj && p->pObj->IsFixed()
101 && (p->pObj->GetType() == (SbxARRAY | SbxBYTE )) )
103 // convert byte array to string
104 SbxArray* pArr = PTR_CAST(SbxArray, p->pObj);
105 if( pArr )
106 aRes = ByteArrayToString( pArr );
108 else
109 SbxBase::SetError( SbxERR_NO_OBJECT );
110 break;
112 case SbxERROR:
113 // Hier wird der String "Error n" erzeugt
114 aRes = SbxRes( STRING_ERRORMSG );
115 aRes += p->nUShort; break;
116 case SbxDATE:
117 ImpPutDate( &aTmp, p->nDouble ); break;
119 case SbxBYREF | SbxCHAR:
120 ImpPutChar( &aTmp, *p->pChar ); break;
121 case SbxBYREF | SbxBYTE:
122 ImpPutByte( &aTmp, *p->pByte ); break;
123 case SbxBYREF | SbxINTEGER:
124 case SbxBYREF | SbxBOOL:
125 ImpPutInteger( &aTmp, *p->pInteger ); break;
126 case SbxBYREF | SbxLONG:
127 ImpPutLong( &aTmp, *p->pLong ); break;
128 case SbxBYREF | SbxULONG:
129 ImpPutULong( &aTmp, *p->pULong ); break;
130 case SbxBYREF | SbxERROR:
131 case SbxBYREF | SbxUSHORT:
132 ImpPutUShort( &aTmp, *p->pUShort ); break;
133 case SbxBYREF | SbxSINGLE:
134 ImpPutSingle( &aTmp, *p->pSingle ); break;
135 case SbxBYREF | SbxDATE:
136 case SbxBYREF | SbxDOUBLE:
137 ImpPutDouble( &aTmp, *p->pDouble ); break;
138 case SbxBYREF | SbxCURRENCY:
139 ImpPutCurrency( &aTmp, *p->pLong64 ); break;
140 case SbxBYREF | SbxSALINT64:
141 ImpPutInt64( &aTmp, *p->pnInt64 ); break;
142 case SbxBYREF | SbxSALUINT64:
143 ImpPutUInt64( &aTmp, *p->puInt64 ); break;
144 default:
145 SbxBase::SetError( SbxERR_CONVERSION );
147 return aRes;
150 // AB 10.4.97, neue Funktion fuer SbxValue::GetCoreString()
151 XubString ImpGetCoreString( const SbxValues* p )
153 // Vorerst nur fuer double
154 if( ( p->eType & (~SbxBYREF) ) == SbxDOUBLE )
156 SbxValues aTmp;
157 XubString aRes;
158 aTmp.eType = SbxSTRING;
159 aTmp.pString = &aRes;
160 if( p->eType == SbxDOUBLE )
161 ImpPutDouble( &aTmp, p->nDouble, /*bCoreString=*/TRUE );
162 else
163 ImpPutDouble( &aTmp, *p->pDouble, /*bCoreString=*/TRUE );
164 return aRes;
166 else
167 return ImpGetString( p );
170 void ImpPutString( SbxValues* p, const XubString* n )
172 SbxValues aTmp;
173 aTmp.eType = SbxSTRING;
174 XubString* pTmp = NULL;
175 // Sicherheitshalber, falls ein NULL-Ptr kommt
176 if( !n )
177 n = pTmp = new XubString;
178 aTmp.pString = (XubString*) n;
179 switch( +p->eType )
181 case SbxCHAR:
182 p->nChar = ImpGetChar( &aTmp ); break;
183 case SbxBYTE:
184 p->nByte = ImpGetByte( &aTmp ); break;
185 case SbxINTEGER:
186 case SbxBOOL:
187 p->nInteger = ImpGetInteger( &aTmp ); break;
188 case SbxLONG:
189 p->nLong = ImpGetLong( &aTmp ); break;
190 case SbxULONG:
191 p->nULong = ImpGetULong( &aTmp ); break;
192 case SbxERROR:
193 case SbxUSHORT:
194 p->nUShort = ImpGetUShort( &aTmp ); break;
195 case SbxSINGLE:
196 p->nSingle = ImpGetSingle( &aTmp ); break;
197 case SbxDATE:
198 p->nDouble = ImpGetDate( &aTmp ); break;
199 case SbxDOUBLE:
200 p->nDouble = ImpGetDouble( &aTmp ); break;
201 case SbxULONG64:
202 p->nLong64 = ImpGetCurrency( &aTmp ); break;
203 case SbxDECIMAL:
204 case SbxBYREF | SbxDECIMAL:
205 releaseDecimalPtr( p->pDecimal );
206 p->pDecimal = ImpGetDecimal( &aTmp ); break;
207 case SbxSALINT64:
208 p->nInt64 = ImpGetInt64( &aTmp ); break;
209 case SbxSALUINT64:
210 p->uInt64 = ImpGetUInt64( &aTmp ); break;
212 case SbxBYREF | SbxSTRING:
213 case SbxSTRING:
214 case SbxLPSTR:
215 if( n->Len() )
217 if( !p->pString )
218 p->pString = new XubString;
219 *p->pString = *n;
221 else
222 delete p->pString, p->pString = NULL;
223 break;
224 case SbxOBJECT:
226 SbxValue* pVal = PTR_CAST(SbxValue,p->pObj);
227 if( pVal )
228 pVal->PutString( *n );
229 else
230 SbxBase::SetError( SbxERR_NO_OBJECT );
231 break;
233 case SbxBYREF | SbxCHAR:
234 *p->pChar = ImpGetChar( p ); break;
235 case SbxBYREF | SbxBYTE:
236 *p->pByte = ImpGetByte( p ); break;
237 case SbxBYREF | SbxINTEGER:
238 *p->pInteger = ImpGetInteger( p ); break;
239 case SbxBYREF | SbxBOOL:
240 *p->pUShort = sal::static_int_cast< UINT16 >( ImpGetBool( p ) );
241 break;
242 case SbxBYREF | SbxERROR:
243 case SbxBYREF | SbxUSHORT:
244 *p->pUShort = ImpGetUShort( p ); break;
245 case SbxBYREF | SbxLONG:
246 *p->pLong = ImpGetLong( p ); break;
247 case SbxBYREF | SbxULONG:
248 *p->pULong = ImpGetULong( p ); break;
249 case SbxBYREF | SbxSINGLE:
250 *p->pSingle = ImpGetSingle( p ); break;
251 case SbxBYREF | SbxDATE:
252 *p->pDouble = ImpGetDate( p ); break;
253 case SbxBYREF | SbxDOUBLE:
254 *p->pDouble = ImpGetDouble( p ); break;
255 case SbxBYREF | SbxCURRENCY:
256 *p->pLong64 = ImpGetCurrency( p ); break;
257 default:
258 SbxBase::SetError( SbxERR_CONVERSION );
260 delete pTmp;
263 // Convert string to an array of bytes, preserving unicode (2bytes per character)
264 SbxArray* StringToByteArray(const String& rStr)
266 USHORT nArraySize = rStr.Len() * 2;
267 const sal_Unicode* pSrc = rStr.GetBuffer();
268 SbxDimArray* pArray = new SbxDimArray(SbxBYTE);
269 bool bIncIndex = ( IsBaseIndexOne() && SbiRuntime::isVBAEnabled() );
270 if( nArraySize )
272 if( bIncIndex )
273 pArray->AddDim( 1, nArraySize );
274 else
275 pArray->AddDim( 0, nArraySize-1 );
277 else
279 pArray->unoAddDim( 0, -1 );
282 for( USHORT i=0; i< nArraySize; i++)
284 SbxVariable* pNew = new SbxVariable( SbxBYTE );
285 BYTE aByte = static_cast< BYTE >( i%2 ? ((*pSrc) >> 8) & 0xff : (*pSrc) & 0xff );
286 pNew->PutByte( aByte );
287 pNew->SetFlag( SBX_WRITE );
288 pArray->Put( pNew, i );
289 if( i%2 )
290 pSrc++;
292 return pArray;
295 // Convert an array of bytes to string (2bytes per character)
296 String ByteArrayToString(SbxArray* pArr)
298 USHORT nCount = pArr->Count();
299 OUStringBuffer aStrBuf;
300 sal_Unicode aChar = 0;
301 for( USHORT i = 0 ; i < nCount ; i++ )
303 sal_Unicode aTempChar = pArr->Get(i)->GetByte();
304 if( i%2 )
306 aChar = (aTempChar << 8 ) | aChar;
307 aStrBuf.append(aChar);
308 aChar = 0;
310 else
312 aChar = aTempChar;
316 if( nCount%2 )
318 aStrBuf.append(aChar);
321 String aStr(aStrBuf.makeStringAndClear());
323 return aStr;