1c82f2877SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3c82f2877SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4c82f2877SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5c82f2877SAndrew Rist  * distributed with this work for additional information
6c82f2877SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7c82f2877SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8c82f2877SAndrew Rist  * "License"); you may not use this file except in compliance
9c82f2877SAndrew Rist  * with the License.  You may obtain a copy of the License at
10c82f2877SAndrew Rist  *
11c82f2877SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12c82f2877SAndrew Rist  *
13c82f2877SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14c82f2877SAndrew Rist  * software distributed under the License is distributed on an
15c82f2877SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16c82f2877SAndrew Rist  * KIND, either express or implied.  See the License for the
17c82f2877SAndrew Rist  * specific language governing permissions and limitations
18c82f2877SAndrew Rist  * under the License.
19c82f2877SAndrew Rist  *
20c82f2877SAndrew Rist  *************************************************************/
21c82f2877SAndrew Rist 
22c82f2877SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_vcl.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir #include <string.h>
28cdf0e10cSrcweir 
29cdf0e10cSrcweir #include "psputil.hxx"
30cdf0e10cSrcweir 
31cdf0e10cSrcweir #include "tools/debug.hxx"
32cdf0e10cSrcweir 
33cdf0e10cSrcweir namespace psp {
34cdf0e10cSrcweir 
35cdf0e10cSrcweir /*
36cdf0e10cSrcweir  * string convenience routines
37cdf0e10cSrcweir  */
38cdf0e10cSrcweir 
39cdf0e10cSrcweir sal_Int32
getHexValueOf(sal_Int32 nValue,sal_Char * pBuffer)40cdf0e10cSrcweir getHexValueOf (sal_Int32 nValue, sal_Char* pBuffer)
41cdf0e10cSrcweir {
42cdf0e10cSrcweir     const static sal_Char pHex [0x10] = {
43cdf0e10cSrcweir         '0', '1', '2', '3', '4', '5', '6', '7',
44cdf0e10cSrcweir         '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
45cdf0e10cSrcweir 
46cdf0e10cSrcweir     pBuffer[0] = pHex [(nValue & 0xF0) >> 4];
47cdf0e10cSrcweir     pBuffer[1] = pHex [(nValue & 0x0F)     ];
48cdf0e10cSrcweir 
49cdf0e10cSrcweir     return 2;
50cdf0e10cSrcweir }
51cdf0e10cSrcweir 
52cdf0e10cSrcweir sal_Int32
getAlignedHexValueOf(sal_Int32 nValue,sal_Char * pBuffer)53cdf0e10cSrcweir getAlignedHexValueOf (sal_Int32 nValue, sal_Char* pBuffer)
54cdf0e10cSrcweir {
55cdf0e10cSrcweir     // get sign
56cdf0e10cSrcweir     sal_Bool bNegative = nValue < 0;
57cdf0e10cSrcweir     nValue = bNegative ? -nValue : nValue;
58cdf0e10cSrcweir 
59cdf0e10cSrcweir     // get required buffer size, must be a multiple of two
60cdf0e10cSrcweir     sal_Int32 nPrecision;
61cdf0e10cSrcweir     if (nValue < 0x80)
62cdf0e10cSrcweir         nPrecision = 2;
63cdf0e10cSrcweir     else
64cdf0e10cSrcweir         if (nValue < 0x8000)
65cdf0e10cSrcweir             nPrecision = 4;
66cdf0e10cSrcweir         else
67cdf0e10cSrcweir             if (nValue < 0x800000)
68cdf0e10cSrcweir                 nPrecision = 6;
69cdf0e10cSrcweir             else
70cdf0e10cSrcweir                 nPrecision = 8;
71cdf0e10cSrcweir 
72cdf0e10cSrcweir     // convert the int into its hex representation, write it into the buffer
73cdf0e10cSrcweir     sal_Int32 nRet = nPrecision;
74cdf0e10cSrcweir     while (nPrecision)
75cdf0e10cSrcweir     {
76cdf0e10cSrcweir         nPrecision -= getHexValueOf (nValue % 256, pBuffer + nPrecision - 2 );
77cdf0e10cSrcweir         nValue /= 256;
78cdf0e10cSrcweir     }
79cdf0e10cSrcweir 
80cdf0e10cSrcweir     // set sign bit
81cdf0e10cSrcweir     if (bNegative)
82cdf0e10cSrcweir     {
83cdf0e10cSrcweir         switch (pBuffer[0])
84cdf0e10cSrcweir         {
85cdf0e10cSrcweir             case '0' : pBuffer[0] = '8'; break;
86cdf0e10cSrcweir             case '1' : pBuffer[0] = '9'; break;
87cdf0e10cSrcweir             case '2' : pBuffer[0] = 'A'; break;
88cdf0e10cSrcweir             case '3' : pBuffer[0] = 'B'; break;
89cdf0e10cSrcweir             case '4' : pBuffer[0] = 'C'; break;
90cdf0e10cSrcweir             case '5' : pBuffer[0] = 'D'; break;
91cdf0e10cSrcweir             case '6' : pBuffer[0] = 'E'; break;
92cdf0e10cSrcweir             case '7' : pBuffer[0] = 'F'; break;
93cdf0e10cSrcweir             default: DBG_ERROR("Already a signed value");
94cdf0e10cSrcweir         }
95cdf0e10cSrcweir     }
96cdf0e10cSrcweir 
97cdf0e10cSrcweir     // report precision
98cdf0e10cSrcweir     return nRet;
99cdf0e10cSrcweir }
100cdf0e10cSrcweir 
101cdf0e10cSrcweir 
102cdf0e10cSrcweir sal_Int32
getValueOf(sal_Int32 nValue,sal_Char * pBuffer)103cdf0e10cSrcweir getValueOf (sal_Int32 nValue, sal_Char* pBuffer)
104cdf0e10cSrcweir {
105cdf0e10cSrcweir     sal_Int32 nChar = 0;
106cdf0e10cSrcweir     if (nValue < 0)
107cdf0e10cSrcweir     {
108cdf0e10cSrcweir         pBuffer [nChar++] = '-';
109cdf0e10cSrcweir         nValue *= -1;
110cdf0e10cSrcweir     }
111cdf0e10cSrcweir     else
112cdf0e10cSrcweir         if (nValue == 0)
113cdf0e10cSrcweir         {
114cdf0e10cSrcweir             pBuffer [nChar++] = '0';
115cdf0e10cSrcweir             return nChar;
116cdf0e10cSrcweir         }
117cdf0e10cSrcweir 
118cdf0e10cSrcweir     sal_Char  pInvBuffer [32];
119cdf0e10cSrcweir     sal_Int32 nInvChar = 0;
120cdf0e10cSrcweir     while (nValue > 0)
121cdf0e10cSrcweir     {
122cdf0e10cSrcweir         pInvBuffer [nInvChar++] = '0' + nValue % 10;
123cdf0e10cSrcweir         nValue /= 10;
124cdf0e10cSrcweir     }
125cdf0e10cSrcweir     while (nInvChar > 0)
126cdf0e10cSrcweir     {
127cdf0e10cSrcweir         pBuffer [nChar++] = pInvBuffer [--nInvChar];
128cdf0e10cSrcweir     }
129cdf0e10cSrcweir 
130cdf0e10cSrcweir     return nChar;
131cdf0e10cSrcweir }
132cdf0e10cSrcweir 
133cdf0e10cSrcweir sal_Int32
appendStr(const sal_Char * pSrc,sal_Char * pDst)134cdf0e10cSrcweir appendStr (const sal_Char* pSrc, sal_Char* pDst)
135cdf0e10cSrcweir {
136cdf0e10cSrcweir     sal_Int32 nBytes = strlen (pSrc);
137cdf0e10cSrcweir     strncpy (pDst, pSrc, nBytes + 1);
138cdf0e10cSrcweir 
139cdf0e10cSrcweir     return nBytes;
140cdf0e10cSrcweir }
141cdf0e10cSrcweir 
142cdf0e10cSrcweir sal_Int32
appendStr(const sal_Char * pSrc,sal_Char * pDst,sal_Int32 nBytes)143cdf0e10cSrcweir appendStr (const sal_Char* pSrc, sal_Char* pDst, sal_Int32 nBytes)
144cdf0e10cSrcweir {
145cdf0e10cSrcweir     strncpy (pDst, pSrc, nBytes);
146cdf0e10cSrcweir     pDst [nBytes] = '\0';
147cdf0e10cSrcweir     return nBytes;
148cdf0e10cSrcweir }
149cdf0e10cSrcweir 
150cdf0e10cSrcweir /*
151cdf0e10cSrcweir  * copy strings to file
152cdf0e10cSrcweir  */
153cdf0e10cSrcweir 
154cdf0e10cSrcweir sal_Bool
WritePS(osl::File * pFile,const sal_Char * pString)155cdf0e10cSrcweir WritePS (osl::File* pFile, const sal_Char* pString)
156cdf0e10cSrcweir {
157cdf0e10cSrcweir     sal_uInt64 nInLength = rtl_str_getLength (pString);
158cdf0e10cSrcweir     sal_uInt64 nOutLength = 0;
159cdf0e10cSrcweir 
160cdf0e10cSrcweir     if (nInLength > 0 && pFile)
161cdf0e10cSrcweir         pFile->write (pString, nInLength, nOutLength);
162cdf0e10cSrcweir 
163cdf0e10cSrcweir     return nInLength == nOutLength;
164cdf0e10cSrcweir }
165cdf0e10cSrcweir 
166cdf0e10cSrcweir sal_Bool
WritePS(osl::File * pFile,const sal_Char * pString,sal_uInt64 nInLength)167cdf0e10cSrcweir WritePS (osl::File* pFile, const sal_Char* pString, sal_uInt64 nInLength)
168cdf0e10cSrcweir {
169cdf0e10cSrcweir     sal_uInt64 nOutLength = 0;
170cdf0e10cSrcweir 
171cdf0e10cSrcweir     if (nInLength > 0 && pFile)
172cdf0e10cSrcweir         pFile->write (pString, nInLength, nOutLength);
173cdf0e10cSrcweir 
174cdf0e10cSrcweir     return nInLength == nOutLength;
175cdf0e10cSrcweir }
176cdf0e10cSrcweir 
177cdf0e10cSrcweir sal_Bool
WritePS(osl::File * pFile,const rtl::OString & rString)178cdf0e10cSrcweir WritePS (osl::File* pFile, const rtl::OString &rString)
179cdf0e10cSrcweir {
180cdf0e10cSrcweir     sal_uInt64 nInLength = rString.getLength();
181cdf0e10cSrcweir     sal_uInt64 nOutLength = 0;
182cdf0e10cSrcweir 
183cdf0e10cSrcweir     if (nInLength > 0 && pFile)
184*24c56ab9SHerbert Dürr         pFile->write( rString.getStr(), nInLength, nOutLength);
185cdf0e10cSrcweir 
186cdf0e10cSrcweir     return nInLength == nOutLength;
187cdf0e10cSrcweir }
188cdf0e10cSrcweir 
189cdf0e10cSrcweir sal_Bool
WritePS(osl::File * pFile,const rtl::OUString & rString)190cdf0e10cSrcweir WritePS (osl::File* pFile, const rtl::OUString &rString)
191cdf0e10cSrcweir {
192cdf0e10cSrcweir     return WritePS (pFile, rtl::OUStringToOString(rString, RTL_TEXTENCODING_ASCII_US));
193cdf0e10cSrcweir }
194cdf0e10cSrcweir 
195cdf0e10cSrcweir /*
196cdf0e10cSrcweir  * cache converter for use in postscript drawing routines
197cdf0e10cSrcweir  */
198cdf0e10cSrcweir 
ConverterFactory()199cdf0e10cSrcweir ConverterFactory::ConverterFactory()
200cdf0e10cSrcweir {
201cdf0e10cSrcweir }
202cdf0e10cSrcweir 
~ConverterFactory()203cdf0e10cSrcweir ConverterFactory::~ConverterFactory ()
204cdf0e10cSrcweir {
205cdf0e10cSrcweir     for( std::map< rtl_TextEncoding, rtl_UnicodeToTextConverter >::const_iterator it = m_aConverters.begin(); it != m_aConverters.end(); ++it )
206cdf0e10cSrcweir             rtl_destroyUnicodeToTextConverter (it->second);
207cdf0e10cSrcweir }
208cdf0e10cSrcweir 
209cdf0e10cSrcweir rtl_UnicodeToTextConverter
Get(rtl_TextEncoding nEncoding)210cdf0e10cSrcweir ConverterFactory::Get (rtl_TextEncoding nEncoding)
211cdf0e10cSrcweir {
212cdf0e10cSrcweir     if (rtl_isOctetTextEncoding( nEncoding ))
213cdf0e10cSrcweir     {
214cdf0e10cSrcweir         std::map< rtl_TextEncoding, rtl_UnicodeToTextConverter >::const_iterator it =
215cdf0e10cSrcweir             m_aConverters.find( nEncoding );
216cdf0e10cSrcweir         rtl_UnicodeToTextConverter aConverter;
217cdf0e10cSrcweir         if (it == m_aConverters.end())
218cdf0e10cSrcweir         {
219cdf0e10cSrcweir             aConverter = rtl_createUnicodeToTextConverter (nEncoding);
220cdf0e10cSrcweir             m_aConverters[nEncoding] = aConverter;
221cdf0e10cSrcweir         }
222cdf0e10cSrcweir         else
223cdf0e10cSrcweir             aConverter = it->second;
224cdf0e10cSrcweir         return aConverter;
225cdf0e10cSrcweir     }
226cdf0e10cSrcweir     return NULL;
227cdf0e10cSrcweir }
228cdf0e10cSrcweir 
229cdf0e10cSrcweir // wrapper for rtl_convertUnicodeToText that handles the usual cases for
230cdf0e10cSrcweir // textconversion in drawtext
231cdf0e10cSrcweir sal_Size
Convert(const sal_Unicode * pText,int nTextLen,sal_uChar * pBuffer,sal_Size nBufferSize,rtl_TextEncoding nEncoding)232cdf0e10cSrcweir ConverterFactory::Convert (const sal_Unicode *pText, int nTextLen,
233cdf0e10cSrcweir                            sal_uChar *pBuffer, sal_Size nBufferSize, rtl_TextEncoding nEncoding)
234cdf0e10cSrcweir {
235cdf0e10cSrcweir     const sal_uInt32 nCvtFlags =  RTL_UNICODETOTEXT_FLAGS_UNDEFINED_QUESTIONMARK
236cdf0e10cSrcweir         | RTL_UNICODETOTEXT_FLAGS_INVALID_QUESTIONMARK ;
237cdf0e10cSrcweir     sal_uInt32  nCvtInfo;
238cdf0e10cSrcweir     sal_Size    nCvtChars;
239cdf0e10cSrcweir 
240cdf0e10cSrcweir     rtl_UnicodeToTextConverter aConverter = Get (nEncoding);
241cdf0e10cSrcweir     rtl_UnicodeToTextContext   aContext   = rtl_createUnicodeToTextContext (aConverter);
242cdf0e10cSrcweir 
243cdf0e10cSrcweir     sal_Size nSize = rtl_convertUnicodeToText (aConverter, aContext,
244cdf0e10cSrcweir                                                pText, nTextLen, (sal_Char*)pBuffer, nBufferSize,
245cdf0e10cSrcweir                                                nCvtFlags, &nCvtInfo, &nCvtChars);
246cdf0e10cSrcweir 
247cdf0e10cSrcweir     rtl_destroyUnicodeToTextContext (aConverter, aContext);
248cdf0e10cSrcweir 
249cdf0e10cSrcweir     return nSize;
250cdf0e10cSrcweir }
251cdf0e10cSrcweir 
252cdf0e10cSrcweir ConverterFactory*
GetConverterFactory()253cdf0e10cSrcweir GetConverterFactory ()
254cdf0e10cSrcweir {
255cdf0e10cSrcweir     static ConverterFactory* pCvt = NULL;
256cdf0e10cSrcweir 
257cdf0e10cSrcweir     if (pCvt == NULL)
258cdf0e10cSrcweir         pCvt = new ConverterFactory;
259cdf0e10cSrcweir 
260cdf0e10cSrcweir     return pCvt;
261cdf0e10cSrcweir }
262cdf0e10cSrcweir 
263cdf0e10cSrcweir 
264cdf0e10cSrcweir } /* namespace psp */
265