xref: /trunk/main/vcl/os2/source/gdi/salgdi.cxx (revision 20a25b3e8c80084a1353857ae72ef95bdab19d12)
19f62ea84SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
39f62ea84SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
49f62ea84SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
59f62ea84SAndrew Rist  * distributed with this work for additional information
69f62ea84SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
79f62ea84SAndrew Rist  * to you under the Apache License, Version 2.0 (the
89f62ea84SAndrew Rist  * "License"); you may not use this file except in compliance
99f62ea84SAndrew Rist  * with the License.  You may obtain a copy of the License at
10cdf0e10cSrcweir  *
119f62ea84SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12cdf0e10cSrcweir  *
139f62ea84SAndrew Rist  * Unless required by applicable law or agreed to in writing,
149f62ea84SAndrew Rist  * software distributed under the License is distributed on an
159f62ea84SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
169f62ea84SAndrew Rist  * KIND, either express or implied.  See the License for the
179f62ea84SAndrew Rist  * specific language governing permissions and limitations
189f62ea84SAndrew Rist  * under the License.
19cdf0e10cSrcweir  *
209f62ea84SAndrew Rist  *************************************************************/
219f62ea84SAndrew Rist 
229f62ea84SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir #include <string.h>
25cdf0e10cSrcweir #include <svpm.h>
26cdf0e10cSrcweir 
27cdf0e10cSrcweir #define _SV_SALGDI_CXX
28cdf0e10cSrcweir #include <tools/debug.hxx>
29fc9fd3f1SPedro Giffuni #include <os2/saldata.hxx>
30fc9fd3f1SPedro Giffuni #include <os2/salgdi.h>
31cdf0e10cSrcweir #include <tools/debug.hxx>
32fc9fd3f1SPedro Giffuni #include <os2/salframe.h>
33cdf0e10cSrcweir #include <tools/poly.hxx>
34cdf0e10cSrcweir #ifndef _RTL_STRINGBUF_HXX
35cdf0e10cSrcweir #include <rtl/strbuf.hxx>
36cdf0e10cSrcweir #endif
37fc9fd3f1SPedro Giffuni 
38fc9fd3f1SPedro Giffuni #include <region.h>
39cdf0e10cSrcweir 
40cdf0e10cSrcweir #ifndef __H_FT2LIB
41fc9fd3f1SPedro Giffuni #include <os2/wingdi.h>
42cdf0e10cSrcweir #include <ft2lib.h>
43cdf0e10cSrcweir #endif
44cdf0e10cSrcweir 
45cdf0e10cSrcweir // -----------
46cdf0e10cSrcweir // - Defines -
47cdf0e10cSrcweir // -----------
48cdf0e10cSrcweir 
49cdf0e10cSrcweir // ClipRegions funktionieren immer noch nicht auf allen getesteten Druckern
50cdf0e10cSrcweir #define SAL_PRINTER_CLIPPATH    1
51cdf0e10cSrcweir // #define SAL_PRINTER_POLYPATH 1
52cdf0e10cSrcweir 
53cdf0e10cSrcweir // =======================================================================
54cdf0e10cSrcweir 
55cdf0e10cSrcweir void ImplInitSalGDI()
56cdf0e10cSrcweir {
57cdf0e10cSrcweir }
58cdf0e10cSrcweir 
59cdf0e10cSrcweir // -----------------------------------------------------------------------
60cdf0e10cSrcweir 
61cdf0e10cSrcweir void ImplFreeSalGDI()
62cdf0e10cSrcweir {
63cdf0e10cSrcweir     SalData*    pSalData = GetSalData();
64cdf0e10cSrcweir 
65cdf0e10cSrcweir     // delete icon cache
66cdf0e10cSrcweir     SalIcon* pIcon = pSalData->mpFirstIcon;
67cdf0e10cSrcweir     while( pIcon )
68cdf0e10cSrcweir     {
69cdf0e10cSrcweir         SalIcon* pTmp = pIcon->pNext;
70cdf0e10cSrcweir         WinDestroyPointer( pIcon->hIcon );
71cdf0e10cSrcweir         delete pIcon;
72cdf0e10cSrcweir         pIcon = pTmp;
73cdf0e10cSrcweir     }
74cdf0e10cSrcweir 
75cdf0e10cSrcweir }
76cdf0e10cSrcweir 
77cdf0e10cSrcweir // =======================================================================
78cdf0e10cSrcweir 
79cdf0e10cSrcweir void ImplSalInitGraphics( Os2SalGraphics* pData )
80cdf0e10cSrcweir {
81cdf0e10cSrcweir     GpiCreateLogColorTable( pData->mhPS, LCOL_RESET, LCOLF_RGB, 0, 0, NULL );
82cdf0e10cSrcweir }
83cdf0e10cSrcweir 
84cdf0e10cSrcweir // -----------------------------------------------------------------------
85cdf0e10cSrcweir 
86cdf0e10cSrcweir void ImplSalDeInitGraphics( Os2SalGraphics* pData )
87cdf0e10cSrcweir {
88cdf0e10cSrcweir }
89cdf0e10cSrcweir 
90cdf0e10cSrcweir // =======================================================================
91cdf0e10cSrcweir 
92cdf0e10cSrcweir Os2SalGraphics::Os2SalGraphics()
93cdf0e10cSrcweir {
94cdf0e10cSrcweir     for( int i = 0; i < MAX_FALLBACK; ++i )
95cdf0e10cSrcweir     {
96cdf0e10cSrcweir         mhFonts[ i ] = 0;
97cdf0e10cSrcweir         mpOs2FontData[ i ]  = NULL;
98cdf0e10cSrcweir         mpOs2FontEntry[ i ] = NULL;
99cdf0e10cSrcweir     }
100cdf0e10cSrcweir 
101cdf0e10cSrcweir     mfFontScale = 1.0;
102cdf0e10cSrcweir 
103cdf0e10cSrcweir     mhPS            = 0;
104cdf0e10cSrcweir     mhDC            = 0;
105cdf0e10cSrcweir     mbLine              = FALSE;
106cdf0e10cSrcweir     mbFill              = FALSE;
107cdf0e10cSrcweir     mbXORMode           = FALSE;
108cdf0e10cSrcweir     mnFontMetricCount   = 0;
109cdf0e10cSrcweir     mpFontMetrics       = NULL;
110cdf0e10cSrcweir     mpClipRectlAry      = NULL;
111cdf0e10cSrcweir 
112cdf0e10cSrcweir     mhDefFont           = 0;
113cdf0e10cSrcweir     mpFontKernPairs     = NULL;
114cdf0e10cSrcweir     mnFontKernPairCount = 0;
115cdf0e10cSrcweir     mbFontKernInit      = FALSE;
116cdf0e10cSrcweir 
117cdf0e10cSrcweir }
118cdf0e10cSrcweir 
119cdf0e10cSrcweir // -----------------------------------------------------------------------
120cdf0e10cSrcweir 
121cdf0e10cSrcweir Os2SalGraphics::~Os2SalGraphics()
122cdf0e10cSrcweir {
123cdf0e10cSrcweir     Ft2DeleteSetId( mhPS, LCID_BASE);
124cdf0e10cSrcweir 
125cdf0e10cSrcweir     if ( mpFontMetrics )
126cdf0e10cSrcweir         delete mpFontMetrics;
127cdf0e10cSrcweir 
128cdf0e10cSrcweir     if ( mpFontKernPairs )
129cdf0e10cSrcweir         delete mpFontKernPairs;
130cdf0e10cSrcweir 
131cdf0e10cSrcweir }
132cdf0e10cSrcweir 
133cdf0e10cSrcweir // -----------------------------------------------------------------------
134cdf0e10cSrcweir 
135cdf0e10cSrcweir static SalColor ImplGetROPSalColor( SalROPColor nROPColor )
136cdf0e10cSrcweir {
137cdf0e10cSrcweir     SalColor nSalColor;
138cdf0e10cSrcweir 
139cdf0e10cSrcweir     switch( nROPColor )
140cdf0e10cSrcweir     {
141cdf0e10cSrcweir         case SAL_ROP_0:
142cdf0e10cSrcweir             nSalColor = MAKE_SALCOLOR( 0, 0, 0 );
143cdf0e10cSrcweir         break;
144cdf0e10cSrcweir 
145cdf0e10cSrcweir         case SAL_ROP_1:
146cdf0e10cSrcweir         case SAL_ROP_INVERT:
147cdf0e10cSrcweir             nSalColor = MAKE_SALCOLOR( 255, 255, 255 );
148cdf0e10cSrcweir         break;
149cdf0e10cSrcweir     }
150cdf0e10cSrcweir 
151cdf0e10cSrcweir     return nSalColor;
152cdf0e10cSrcweir }
153cdf0e10cSrcweir 
154cdf0e10cSrcweir // -----------------------------------------------------------------------
155cdf0e10cSrcweir 
156cdf0e10cSrcweir void Os2SalGraphics::GetResolution( long& rDPIX, long& rDPIY )
157cdf0e10cSrcweir {
158cdf0e10cSrcweir     // since OOo asks for DPI, I will query FONT_RES, which seems to be
159cdf0e10cSrcweir     // more correct than _RESOLUTION fields (on my wide screen lcd)
160cdf0e10cSrcweir     // and does not require conversion
161cdf0e10cSrcweir     DevQueryCaps( mhDC, CAPS_HORIZONTAL_FONT_RES, 1, &rDPIX );
162cdf0e10cSrcweir     DevQueryCaps( mhDC, CAPS_VERTICAL_FONT_RES, 1, &rDPIY );
163cdf0e10cSrcweir }
164cdf0e10cSrcweir 
165cdf0e10cSrcweir // -----------------------------------------------------------------------
166cdf0e10cSrcweir 
167cdf0e10cSrcweir USHORT Os2SalGraphics::GetBitCount()
168cdf0e10cSrcweir {
169cdf0e10cSrcweir     LONG nBitCount;
170cdf0e10cSrcweir     DevQueryCaps( mhDC, CAPS_COLOR_BITCOUNT, 1, &nBitCount );
171cdf0e10cSrcweir     return (USHORT)nBitCount;
172cdf0e10cSrcweir }
173cdf0e10cSrcweir 
174cdf0e10cSrcweir // -----------------------------------------------------------------------
175cdf0e10cSrcweir 
176cdf0e10cSrcweir long Os2SalGraphics::GetGraphicsWidth() const
177cdf0e10cSrcweir {
178cdf0e10cSrcweir     if( mhWnd )
179cdf0e10cSrcweir     {
180cdf0e10cSrcweir         Os2SalFrame* pFrame = (Os2SalFrame*)GetWindowPtr( mhWnd );
181cdf0e10cSrcweir         if( pFrame )
182cdf0e10cSrcweir         {
183cdf0e10cSrcweir             if( pFrame->maGeometry.nWidth )
184cdf0e10cSrcweir                 return pFrame->maGeometry.nWidth;
185cdf0e10cSrcweir             else
186cdf0e10cSrcweir             {
187cdf0e10cSrcweir                 // TODO: perhaps not needed, maGeometry should always be up-to-date
188cdf0e10cSrcweir                 RECTL aRect;
189cdf0e10cSrcweir                 WinQueryWindowRect( mhWnd, &aRect );
190cdf0e10cSrcweir                 return aRect.xRight;
191cdf0e10cSrcweir             }
192cdf0e10cSrcweir         }
193cdf0e10cSrcweir     }
194cdf0e10cSrcweir 
195cdf0e10cSrcweir     return 0;
196cdf0e10cSrcweir }
197cdf0e10cSrcweir 
198cdf0e10cSrcweir // -----------------------------------------------------------------------
199cdf0e10cSrcweir 
200cdf0e10cSrcweir void Os2SalGraphics::ResetClipRegion()
201cdf0e10cSrcweir {
202cdf0e10cSrcweir #ifdef SAL_PRINTER_CLIPPATH
203cdf0e10cSrcweir     if ( mbPrinter )
204cdf0e10cSrcweir         GpiSetClipPath( mhPS, 0, SCP_RESET );
205cdf0e10cSrcweir     else
206cdf0e10cSrcweir #endif
207cdf0e10cSrcweir     {
208cdf0e10cSrcweir         HRGN hOldRegion;
209cdf0e10cSrcweir 
210cdf0e10cSrcweir         GpiSetClipRegion( mhPS, NULL, &hOldRegion );
211cdf0e10cSrcweir         if ( hOldRegion )
212cdf0e10cSrcweir             GpiDestroyRegion( mhPS, hOldRegion );
213cdf0e10cSrcweir     }
214cdf0e10cSrcweir }
215cdf0e10cSrcweir 
216cdf0e10cSrcweir // -----------------------------------------------------------------------
217cdf0e10cSrcweir 
218cdf0e10cSrcweir bool Os2SalGraphics::setClipRegion( const Region& i_rClip )
219cdf0e10cSrcweir {
220cdf0e10cSrcweir     ULONG nCount = i_rClip.GetRectCount();
221cdf0e10cSrcweir 
222cdf0e10cSrcweir     mpClipRectlAry    = new RECTL[ nCount ];
223cdf0e10cSrcweir     mnClipElementCount = 0;
224cdf0e10cSrcweir 
225cdf0e10cSrcweir     ImplRegionInfo aInfo;
226cdf0e10cSrcweir     long nX, nY, nW, nH;
227cdf0e10cSrcweir     bool bRegionRect = i_rClip.ImplGetFirstRect(aInfo, nX, nY, nW, nH );
228cdf0e10cSrcweir     while( bRegionRect )
229cdf0e10cSrcweir     {
230cdf0e10cSrcweir         if ( nW && nH )
231cdf0e10cSrcweir         {
232cdf0e10cSrcweir             RECTL* pClipRect = &mpClipRectlAry[ mnClipElementCount ];
233cdf0e10cSrcweir             pClipRect->xLeft   = nX;
234cdf0e10cSrcweir             pClipRect->yTop    = mnHeight - nY;
235cdf0e10cSrcweir             pClipRect->xRight  = nX + nW;
236cdf0e10cSrcweir             pClipRect->yBottom = mnHeight - (nY + nH);
237cdf0e10cSrcweir             mnClipElementCount++;
238cdf0e10cSrcweir         }
239cdf0e10cSrcweir         bRegionRect = i_rClip.ImplGetNextRect( aInfo, nX, nY, nW, nH );
240cdf0e10cSrcweir     }
241cdf0e10cSrcweir #ifdef SAL_PRINTER_CLIPPATH
242cdf0e10cSrcweir     if ( mbPrinter )
243cdf0e10cSrcweir     {
244cdf0e10cSrcweir         GpiSetClipPath( mhPS, 0, SCP_RESET );
245cdf0e10cSrcweir         GpiBeginPath( mhPS, 1L );
246cdf0e10cSrcweir 
247cdf0e10cSrcweir         for( int i = 0; i < mnClipElementCount; i++ )
248cdf0e10cSrcweir         {
249cdf0e10cSrcweir             POINTL aPt;
250cdf0e10cSrcweir             RECTL* pClipRect = &mpClipRectlAry[ i ];
251cdf0e10cSrcweir 
252cdf0e10cSrcweir             aPt.x = pClipRect->xLeft;
253cdf0e10cSrcweir             aPt.y = pClipRect->yTop-1;
254cdf0e10cSrcweir             Ft2Move( mhPS, &aPt );
255cdf0e10cSrcweir 
256cdf0e10cSrcweir             aPt.x = pClipRect->xRight-1;
257cdf0e10cSrcweir             aPt.y = pClipRect->yBottom;
258cdf0e10cSrcweir 
259cdf0e10cSrcweir             Ft2Box( mhPS, DRO_OUTLINE, &aPt, 0, 0 );
260cdf0e10cSrcweir         }
261cdf0e10cSrcweir 
262cdf0e10cSrcweir         GpiEndPath( mhPS );
263cdf0e10cSrcweir         GpiSetClipPath( mhPS, 1L, SCP_ALTERNATE | SCP_AND );
264cdf0e10cSrcweir     }
265cdf0e10cSrcweir     else
266cdf0e10cSrcweir #endif
267cdf0e10cSrcweir     {
268cdf0e10cSrcweir         HRGN hClipRegion = GpiCreateRegion( mhPS,
269cdf0e10cSrcweir                                             mnClipElementCount,
270cdf0e10cSrcweir                                             mpClipRectlAry );
271cdf0e10cSrcweir         HRGN hOldRegion;
272cdf0e10cSrcweir 
273cdf0e10cSrcweir         GpiSetClipRegion( mhPS, hClipRegion, &hOldRegion );
274cdf0e10cSrcweir         if( hOldRegion )
275cdf0e10cSrcweir             GpiDestroyRegion( mhPS, hOldRegion );
276cdf0e10cSrcweir     }
277cdf0e10cSrcweir 
278cdf0e10cSrcweir     delete [] mpClipRectlAry;
279cdf0e10cSrcweir 
280cdf0e10cSrcweir     return true;
281cdf0e10cSrcweir }
282cdf0e10cSrcweir 
283cdf0e10cSrcweir // -----------------------------------------------------------------------
284cdf0e10cSrcweir 
285cdf0e10cSrcweir void Os2SalGraphics::SetLineColor()
286cdf0e10cSrcweir {
287cdf0e10cSrcweir     // don't draw line!
288cdf0e10cSrcweir     mbLine = FALSE;
289cdf0e10cSrcweir }
290cdf0e10cSrcweir 
291cdf0e10cSrcweir // -----------------------------------------------------------------------
292cdf0e10cSrcweir 
293cdf0e10cSrcweir void Os2SalGraphics::SetLineColor( SalColor nSalColor )
294cdf0e10cSrcweir {
295cdf0e10cSrcweir     LINEBUNDLE lb;
296cdf0e10cSrcweir 
297cdf0e10cSrcweir     // set color
298cdf0e10cSrcweir     lb.lColor = RGBCOLOR( SALCOLOR_RED( nSalColor ),
299cdf0e10cSrcweir                           SALCOLOR_GREEN( nSalColor ),
300cdf0e10cSrcweir                           SALCOLOR_BLUE( nSalColor ) );
301cdf0e10cSrcweir 
302cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
303cdf0e10cSrcweir                  PRIM_LINE,
304cdf0e10cSrcweir                  LBB_COLOR,
305cdf0e10cSrcweir                  0,
306cdf0e10cSrcweir                  &lb );
307cdf0e10cSrcweir 
308cdf0e10cSrcweir     // draw line!
309cdf0e10cSrcweir     mbLine = TRUE;
310cdf0e10cSrcweir }
311cdf0e10cSrcweir 
312cdf0e10cSrcweir // -----------------------------------------------------------------------
313cdf0e10cSrcweir 
314cdf0e10cSrcweir void Os2SalGraphics::SetFillColor()
315cdf0e10cSrcweir {
316cdf0e10cSrcweir     // don't fill area!
317cdf0e10cSrcweir     mbFill = FALSE;
318cdf0e10cSrcweir }
319cdf0e10cSrcweir 
320cdf0e10cSrcweir // -----------------------------------------------------------------------
321cdf0e10cSrcweir 
322cdf0e10cSrcweir void Os2SalGraphics::SetFillColor( SalColor nSalColor )
323cdf0e10cSrcweir {
324cdf0e10cSrcweir     AREABUNDLE ab;
325cdf0e10cSrcweir 
326cdf0e10cSrcweir     // set color
327cdf0e10cSrcweir     ab.lColor = RGBCOLOR( SALCOLOR_RED( nSalColor ),
328cdf0e10cSrcweir                           SALCOLOR_GREEN( nSalColor ),
329cdf0e10cSrcweir                           SALCOLOR_BLUE( nSalColor ) );
330cdf0e10cSrcweir 
331cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
332cdf0e10cSrcweir                  PRIM_AREA,
333cdf0e10cSrcweir                  ABB_COLOR,
334cdf0e10cSrcweir                  0,
335cdf0e10cSrcweir                  &ab );
336cdf0e10cSrcweir 
337cdf0e10cSrcweir     // fill area!
338cdf0e10cSrcweir     mbFill = TRUE;
339cdf0e10cSrcweir }
340cdf0e10cSrcweir 
341cdf0e10cSrcweir // -----------------------------------------------------------------------
342cdf0e10cSrcweir 
343cdf0e10cSrcweir void Os2SalGraphics::SetXORMode( bool bSet, bool )
344cdf0e10cSrcweir {
345cdf0e10cSrcweir     mbXORMode = bSet;
346cdf0e10cSrcweir     LONG nMixMode = bSet ? FM_XOR : FM_OVERPAINT;
347cdf0e10cSrcweir 
348cdf0e10cSrcweir     // set mix mode for lines
349cdf0e10cSrcweir     LINEBUNDLE lb;
350cdf0e10cSrcweir     lb.usMixMode = nMixMode;
351cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
352cdf0e10cSrcweir                  PRIM_LINE,
353cdf0e10cSrcweir                  LBB_MIX_MODE,
354cdf0e10cSrcweir                  0,
355cdf0e10cSrcweir                  &lb );
356cdf0e10cSrcweir 
357cdf0e10cSrcweir     // set mix mode for areas
358cdf0e10cSrcweir     AREABUNDLE ab;
359cdf0e10cSrcweir     ab.usMixMode = nMixMode;
360cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
361cdf0e10cSrcweir                  PRIM_AREA,
362cdf0e10cSrcweir                  ABB_MIX_MODE,
363cdf0e10cSrcweir                  0,
364cdf0e10cSrcweir                  &ab );
365cdf0e10cSrcweir 
366cdf0e10cSrcweir     // set mix mode for text
367cdf0e10cSrcweir     CHARBUNDLE cb;
368cdf0e10cSrcweir     cb.usMixMode = nMixMode;
369cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
370cdf0e10cSrcweir                  PRIM_CHAR,
371cdf0e10cSrcweir                  CBB_MIX_MODE,
372cdf0e10cSrcweir                  0,
373cdf0e10cSrcweir                  &cb );
374cdf0e10cSrcweir }
375cdf0e10cSrcweir 
376cdf0e10cSrcweir // -----------------------------------------------------------------------
377cdf0e10cSrcweir 
378cdf0e10cSrcweir void Os2SalGraphics::SetROPLineColor( SalROPColor nROPColor )
379cdf0e10cSrcweir {
380cdf0e10cSrcweir     SetLineColor( ImplGetROPSalColor( nROPColor ) );
381cdf0e10cSrcweir }
382cdf0e10cSrcweir 
383cdf0e10cSrcweir // -----------------------------------------------------------------------
384cdf0e10cSrcweir 
385cdf0e10cSrcweir void Os2SalGraphics::SetROPFillColor( SalROPColor nROPColor )
386cdf0e10cSrcweir {
387cdf0e10cSrcweir     SetFillColor( ImplGetROPSalColor( nROPColor ) );
388cdf0e10cSrcweir }
389cdf0e10cSrcweir 
390cdf0e10cSrcweir // -----------------------------------------------------------------------
391cdf0e10cSrcweir 
392cdf0e10cSrcweir void Os2SalGraphics::drawPixel( long nX, long nY )
393cdf0e10cSrcweir {
394cdf0e10cSrcweir     POINTL aPt;
395cdf0e10cSrcweir 
396cdf0e10cSrcweir     aPt.x = nX;
397cdf0e10cSrcweir     aPt.y = TY( nY );
398cdf0e10cSrcweir 
399cdf0e10cSrcweir     // set color
400cdf0e10cSrcweir     Ft2SetPel( mhPS, &aPt );
401cdf0e10cSrcweir }
402cdf0e10cSrcweir 
403cdf0e10cSrcweir // -----------------------------------------------------------------------
404cdf0e10cSrcweir 
405cdf0e10cSrcweir void Os2SalGraphics::drawPixel( long nX, long nY, SalColor nSalColor )
406cdf0e10cSrcweir {
407cdf0e10cSrcweir     // save old color
408cdf0e10cSrcweir     LINEBUNDLE oldLb;
409cdf0e10cSrcweir     GpiQueryAttrs( mhPS,
410cdf0e10cSrcweir                    PRIM_LINE,
411cdf0e10cSrcweir                    LBB_COLOR,
412cdf0e10cSrcweir                    &oldLb );
413cdf0e10cSrcweir 
414cdf0e10cSrcweir     // set new color
415cdf0e10cSrcweir     LINEBUNDLE lb;
416cdf0e10cSrcweir     lb.lColor = RGBCOLOR( SALCOLOR_RED( nSalColor ),
417cdf0e10cSrcweir                           SALCOLOR_GREEN( nSalColor ),
418cdf0e10cSrcweir                           SALCOLOR_BLUE( nSalColor ) );
419cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
420cdf0e10cSrcweir                  PRIM_LINE,
421cdf0e10cSrcweir                  LBB_COLOR,
422cdf0e10cSrcweir                  0,
423cdf0e10cSrcweir                  &lb );
424cdf0e10cSrcweir 
425cdf0e10cSrcweir     // set color of pixel
426cdf0e10cSrcweir     POINTL aPt;
427cdf0e10cSrcweir     aPt.x = nX;
428cdf0e10cSrcweir     aPt.y = TY( nY );
429cdf0e10cSrcweir     Ft2SetPel( mhPS, &aPt );
430cdf0e10cSrcweir 
431cdf0e10cSrcweir     // restore old color
432cdf0e10cSrcweir     Ft2SetAttrs( mhPS,
433cdf0e10cSrcweir                  PRIM_LINE,
434cdf0e10cSrcweir                  LBB_COLOR,
435cdf0e10cSrcweir                  0,
436cdf0e10cSrcweir                  &oldLb );
437cdf0e10cSrcweir }
438cdf0e10cSrcweir 
439cdf0e10cSrcweir // -----------------------------------------------------------------------
440cdf0e10cSrcweir 
441cdf0e10cSrcweir void Os2SalGraphics::drawLine( long nX1, long nY1, long nX2, long nY2 )
442cdf0e10cSrcweir {
443cdf0e10cSrcweir     // OS2 zeichnet den Endpunkt mit
444cdf0e10cSrcweir     POINTL aPt;
445cdf0e10cSrcweir     aPt.x = nX1;
446cdf0e10cSrcweir     aPt.y = TY( nY1 );
447cdf0e10cSrcweir     Ft2Move( mhPS, &aPt );
448cdf0e10cSrcweir     aPt.x = nX2;
449cdf0e10cSrcweir     aPt.y = TY( nY2 );
450cdf0e10cSrcweir     GpiLine( mhPS, &aPt );
451cdf0e10cSrcweir }
452cdf0e10cSrcweir 
453cdf0e10cSrcweir // -----------------------------------------------------------------------
454cdf0e10cSrcweir 
455cdf0e10cSrcweir void Os2SalGraphics::drawRect( long nX, long nY, long nWidth, long nHeight )
456cdf0e10cSrcweir {
457cdf0e10cSrcweir     POINTL aPt;
458cdf0e10cSrcweir     long lControl;
459cdf0e10cSrcweir 
460cdf0e10cSrcweir     if ( mbFill )
461cdf0e10cSrcweir     {
462cdf0e10cSrcweir         if ( mbLine )
463cdf0e10cSrcweir             lControl = DRO_OUTLINEFILL;
464cdf0e10cSrcweir         else
465cdf0e10cSrcweir             lControl = DRO_FILL;
466cdf0e10cSrcweir     }
467cdf0e10cSrcweir     else
468cdf0e10cSrcweir     {
469cdf0e10cSrcweir         if ( mbLine )
470cdf0e10cSrcweir             lControl = DRO_OUTLINE;
471cdf0e10cSrcweir         else
472cdf0e10cSrcweir             return;
473cdf0e10cSrcweir     }
474cdf0e10cSrcweir 
475cdf0e10cSrcweir     aPt.x = nX;
476cdf0e10cSrcweir     aPt.y = TY( nY );
477cdf0e10cSrcweir     Ft2Move( mhPS, &aPt );
478cdf0e10cSrcweir     aPt.x = nX + nWidth - 1;
479cdf0e10cSrcweir     aPt.y = TY( nY + nHeight - 1 );
480cdf0e10cSrcweir     Ft2Box( mhPS, lControl, &aPt, 0, 0 );
481cdf0e10cSrcweir }
482cdf0e10cSrcweir 
483cdf0e10cSrcweir // -----------------------------------------------------------------------
484cdf0e10cSrcweir 
485cdf0e10cSrcweir void Os2SalGraphics::drawPolyLine( ULONG nPoints, const SalPoint* pPtAry )
486cdf0e10cSrcweir {
487cdf0e10cSrcweir     // convert all points to sys orientation
488cdf0e10cSrcweir     POINTL*             pOS2PtAry = new POINTL[ nPoints ];
489cdf0e10cSrcweir     POINTL*             pTempOS2PtAry = pOS2PtAry;
490cdf0e10cSrcweir     const SalPoint*     pTempPtAry = pPtAry;
491cdf0e10cSrcweir     ULONG               nTempPoints = nPoints;
492cdf0e10cSrcweir     long                nHeight = mnHeight - 1;
493cdf0e10cSrcweir 
494cdf0e10cSrcweir     while( nTempPoints-- )
495cdf0e10cSrcweir     {
496cdf0e10cSrcweir         (*pTempOS2PtAry).x = (*pTempPtAry).mnX;
497cdf0e10cSrcweir         (*pTempOS2PtAry).y = nHeight - (*pTempPtAry).mnY;
498cdf0e10cSrcweir         pTempOS2PtAry++;
499cdf0e10cSrcweir         pTempPtAry++;
500cdf0e10cSrcweir     }
501cdf0e10cSrcweir 
502cdf0e10cSrcweir     Ft2Move( mhPS, pOS2PtAry );
503cdf0e10cSrcweir     GpiPolyLine( mhPS, nPoints, pOS2PtAry );
504cdf0e10cSrcweir     delete [] pOS2PtAry;
505cdf0e10cSrcweir }
506cdf0e10cSrcweir 
507cdf0e10cSrcweir // -----------------------------------------------------------------------
508cdf0e10cSrcweir 
509cdf0e10cSrcweir void Os2SalGraphics::drawPolygon( ULONG nPoints, const SalPoint* pPtAry )
510cdf0e10cSrcweir {
511cdf0e10cSrcweir     PM_POLYGON aPolygon;
512cdf0e10cSrcweir 
513cdf0e10cSrcweir     // create polygon
514cdf0e10cSrcweir     aPolygon.aPointl = new POINTL[ nPoints ];
515cdf0e10cSrcweir     aPolygon.ulPoints = nPoints;
516cdf0e10cSrcweir 
517cdf0e10cSrcweir     // convert all points to sys orientation
518cdf0e10cSrcweir     POINTL*             pTempOS2PtAry = aPolygon.aPointl;
519cdf0e10cSrcweir     const SalPoint*     pTempPtAry = pPtAry;
520cdf0e10cSrcweir     ULONG               nTempPoints = nPoints;
521cdf0e10cSrcweir     long                nHeight = mnHeight - 1;
522cdf0e10cSrcweir 
523cdf0e10cSrcweir     while( nTempPoints-- )
524cdf0e10cSrcweir     {
525cdf0e10cSrcweir         (*pTempOS2PtAry).x = (*pTempPtAry).mnX;
526cdf0e10cSrcweir         (*pTempOS2PtAry).y = nHeight - (*pTempPtAry).mnY;
527cdf0e10cSrcweir         pTempOS2PtAry++;
528cdf0e10cSrcweir         pTempPtAry++;
529cdf0e10cSrcweir     }
530cdf0e10cSrcweir 
531cdf0e10cSrcweir     // Innenleben zeichnen
532cdf0e10cSrcweir     if ( mbFill )
533cdf0e10cSrcweir     {
534cdf0e10cSrcweir #ifdef SAL_PRINTER_POLYPATH
535cdf0e10cSrcweir         if ( mbPrinter )
536cdf0e10cSrcweir         {
537cdf0e10cSrcweir             Ft2BeginPath( mhPS, 1 );
538cdf0e10cSrcweir             Ft2Move( mhPS, aPolygon.aPointl );
539cdf0e10cSrcweir             Ft2PolyLine( mhPS, aPolygon.ulPoints, aPolygon.aPointl );
540cdf0e10cSrcweir             Ft2EndPath( mhPS );
541cdf0e10cSrcweir             Ft2FillPath( mhPS, 1, 0 );
542cdf0e10cSrcweir 
543cdf0e10cSrcweir             if ( mbLine )
544cdf0e10cSrcweir             {
545cdf0e10cSrcweir                 Ft2Move( mhPS, aPolygon.aPointl );
546cdf0e10cSrcweir                 Ft2PolyLine( mhPS, aPolygon.ulPoints, aPolygon.aPointl );
547cdf0e10cSrcweir             }
548cdf0e10cSrcweir         }
549cdf0e10cSrcweir         else
550cdf0e10cSrcweir #endif
551cdf0e10cSrcweir         {
552cdf0e10cSrcweir             ULONG nOptions = POLYGON_ALTERNATE;
553cdf0e10cSrcweir 
554cdf0e10cSrcweir             if ( mbLine )
555cdf0e10cSrcweir                 nOptions |= POLYGON_BOUNDARY;
556cdf0e10cSrcweir             else
557cdf0e10cSrcweir                 nOptions |= POLYGON_NOBOUNDARY;
558cdf0e10cSrcweir 
559cdf0e10cSrcweir             Ft2Move( mhPS, aPolygon.aPointl );
560cdf0e10cSrcweir             GpiPolygons( mhPS, 1, &aPolygon, nOptions, POLYGON_EXCL );
561cdf0e10cSrcweir         }
562cdf0e10cSrcweir     }
563cdf0e10cSrcweir     else
564cdf0e10cSrcweir     {
565cdf0e10cSrcweir         if ( mbLine )
566cdf0e10cSrcweir         {
567cdf0e10cSrcweir             Ft2Move( mhPS, aPolygon.aPointl );
568cdf0e10cSrcweir             GpiPolyLine( mhPS, nPoints, aPolygon.aPointl );
569cdf0e10cSrcweir         }
570cdf0e10cSrcweir     }
571cdf0e10cSrcweir 
572cdf0e10cSrcweir     delete [] aPolygon.aPointl;
573cdf0e10cSrcweir }
574cdf0e10cSrcweir 
575cdf0e10cSrcweir // -----------------------------------------------------------------------
576cdf0e10cSrcweir 
577cdf0e10cSrcweir void Os2SalGraphics::drawPolyPolygon( ULONG nPoly, const ULONG* pPoints,
578cdf0e10cSrcweir                                    PCONSTSALPOINT* pPtAry )
579cdf0e10cSrcweir {
580cdf0e10cSrcweir     ULONG       i;
581cdf0e10cSrcweir     long        nHeight = mnHeight - 1;
582cdf0e10cSrcweir     PM_POLYGON* aPolygonAry = new PM_POLYGON[ nPoly ];
583cdf0e10cSrcweir 
584cdf0e10cSrcweir     for( i = 0; i < nPoly; i++ )
585cdf0e10cSrcweir     {
586cdf0e10cSrcweir         const SalPoint * pTempPtAry = (const SalPoint*)pPtAry[ i ];
587cdf0e10cSrcweir 
588cdf0e10cSrcweir         // create polygon
589cdf0e10cSrcweir         ULONG nTempPoints = pPoints[ i ];
590cdf0e10cSrcweir         POINTL * pTempOS2PtAry = new POINTL[ nTempPoints ];
591cdf0e10cSrcweir 
592cdf0e10cSrcweir         // convert all points to sys orientation
593cdf0e10cSrcweir         aPolygonAry[ i ].ulPoints = nTempPoints;
594cdf0e10cSrcweir         aPolygonAry[ i ].aPointl = pTempOS2PtAry;
595cdf0e10cSrcweir 
596cdf0e10cSrcweir         while( nTempPoints-- )
597cdf0e10cSrcweir         {
598cdf0e10cSrcweir             (*pTempOS2PtAry).x = (*pTempPtAry).mnX;
599cdf0e10cSrcweir             (*pTempOS2PtAry).y = nHeight - (*pTempPtAry).mnY;
600cdf0e10cSrcweir             pTempOS2PtAry++;
601cdf0e10cSrcweir             pTempPtAry++;
602cdf0e10cSrcweir         }
603cdf0e10cSrcweir     }
604cdf0e10cSrcweir 
605cdf0e10cSrcweir     // Innenleben zeichnen
606cdf0e10cSrcweir     if ( mbFill )
607cdf0e10cSrcweir     {
608cdf0e10cSrcweir #ifdef SAL_PRINTER_POLYPATH
609cdf0e10cSrcweir         if ( mbPrinter )
610cdf0e10cSrcweir         {
611cdf0e10cSrcweir             Ft2BeginPath( mhPS, 1 );
612cdf0e10cSrcweir             for ( i = 0; i < nPoly; i++ )
613cdf0e10cSrcweir             {
614cdf0e10cSrcweir                 Ft2Move( mhPS, aPolygonAry[i].aPointl );
615cdf0e10cSrcweir                 Ft2PolyLine( mhPS, aPolygonAry[i].ulPoints, aPolygonAry[i].aPointl );
616cdf0e10cSrcweir             }
617cdf0e10cSrcweir             Ft2EndPath( mhPS );
618cdf0e10cSrcweir             Ft2FillPath( mhPS, 1, 0 );
619cdf0e10cSrcweir         }
620cdf0e10cSrcweir         else
621cdf0e10cSrcweir #endif
622cdf0e10cSrcweir         {
623cdf0e10cSrcweir             ULONG nOptions = POLYGON_ALTERNATE;
624cdf0e10cSrcweir 
625cdf0e10cSrcweir             if ( mbLine )
626cdf0e10cSrcweir                 nOptions |= POLYGON_BOUNDARY;
627cdf0e10cSrcweir             else
628cdf0e10cSrcweir                 nOptions |= POLYGON_NOBOUNDARY;
629cdf0e10cSrcweir 
630cdf0e10cSrcweir             Ft2Move( mhPS, aPolygonAry[ 0 ].aPointl );
631cdf0e10cSrcweir             GpiPolygons( mhPS, nPoly, aPolygonAry, nOptions, POLYGON_EXCL );
632cdf0e10cSrcweir         }
633cdf0e10cSrcweir     }
634cdf0e10cSrcweir     else
635cdf0e10cSrcweir     {
636cdf0e10cSrcweir         if ( mbLine )
637cdf0e10cSrcweir         {
638cdf0e10cSrcweir             for( i = 0; i < nPoly; i++ )
639cdf0e10cSrcweir             {
640cdf0e10cSrcweir                 Ft2Move( mhPS, aPolygonAry[ i ].aPointl );
641cdf0e10cSrcweir                 GpiPolyLine( mhPS, aPolygonAry[ i ].ulPoints, aPolygonAry[ i ].aPointl );
642cdf0e10cSrcweir             }
643cdf0e10cSrcweir         }
644cdf0e10cSrcweir     }
645cdf0e10cSrcweir 
646cdf0e10cSrcweir     // cleanup
647cdf0e10cSrcweir     for( i = 0; i < nPoly; i++ )
648cdf0e10cSrcweir         delete [] aPolygonAry[ i ].aPointl;
649cdf0e10cSrcweir     delete [] aPolygonAry;
650cdf0e10cSrcweir }
651cdf0e10cSrcweir 
652cdf0e10cSrcweir // -----------------------------------------------------------------------
653cdf0e10cSrcweir 
654cdf0e10cSrcweir bool Os2SalGraphics::drawPolyPolygon( const ::basegfx::B2DPolyPolygon&, double /*fTransparency*/ )
655cdf0e10cSrcweir {
656cdf0e10cSrcweir     // TODO: implement and advertise OutDevSupport_B2DDraw support
657cdf0e10cSrcweir     return false;
658cdf0e10cSrcweir }
659cdf0e10cSrcweir 
660cdf0e10cSrcweir // -----------------------------------------------------------------------
661cdf0e10cSrcweir 
662cdf0e10cSrcweir bool Os2SalGraphics::drawPolyLine(
663cdf0e10cSrcweir     const basegfx::B2DPolygon& /*rPolygon*/,
664cdf0e10cSrcweir     double /*fTransparency*/,
665cdf0e10cSrcweir     const basegfx::B2DVector& /*rLineWidths*/,
666*20a25b3eSYuri Dario     basegfx::B2DLineJoin /*eLineJoin*/,
667*20a25b3eSYuri Dario     com::sun::star::drawing::LineCap /*eLineCap*/)
668cdf0e10cSrcweir {
669cdf0e10cSrcweir     // TODO: implement
670cdf0e10cSrcweir     return false;
671cdf0e10cSrcweir }
672cdf0e10cSrcweir 
673cdf0e10cSrcweir // -----------------------------------------------------------------------
674cdf0e10cSrcweir 
675fc9fd3f1SPedro Giffuni sal_Bool Os2SalGraphics::drawPolyLineBezier( ULONG nPoints, const SalPoint* pPtAry, const sal_uInt8* pFlgAry )
676cdf0e10cSrcweir {
677cdf0e10cSrcweir     return sal_False;
678cdf0e10cSrcweir }
679cdf0e10cSrcweir 
680cdf0e10cSrcweir // -----------------------------------------------------------------------
681cdf0e10cSrcweir 
682fc9fd3f1SPedro Giffuni sal_Bool Os2SalGraphics::drawPolygonBezier( ULONG nPoints, const SalPoint* pPtAry, const sal_uInt8* pFlgAry )
683cdf0e10cSrcweir {
684cdf0e10cSrcweir     return sal_False;
685cdf0e10cSrcweir }
686cdf0e10cSrcweir 
687cdf0e10cSrcweir // -----------------------------------------------------------------------
688cdf0e10cSrcweir 
689cdf0e10cSrcweir sal_Bool Os2SalGraphics::drawPolyPolygonBezier( ULONG nPoly, const ULONG* pPoints,
690fc9fd3f1SPedro Giffuni                                              const SalPoint* const* pPtAry, const sal_uInt8* const* pFlgAry )
691cdf0e10cSrcweir {
692cdf0e10cSrcweir     return sal_False;
693cdf0e10cSrcweir }
694cdf0e10cSrcweir 
695cdf0e10cSrcweir // =======================================================================
696cdf0e10cSrcweir 
697cdf0e10cSrcweir // MAXIMUM BUFSIZE EQ 0xFFFF
698cdf0e10cSrcweir #define POSTSCRIPT_BUFSIZE          0x4000
699fc9fd3f1SPedro Giffuni // we only try to get the BoundingBox in the first 4096 PM_BYTEs
700cdf0e10cSrcweir #define POSTSCRIPT_BOUNDINGSEARCH   0x1000
701cdf0e10cSrcweir 
702fc9fd3f1SPedro Giffuni static PM_BYTE* ImplSearchEntry( PM_BYTE* pSource, PM_BYTE* pDest, ULONG nComp, ULONG nSize )
703cdf0e10cSrcweir {
704cdf0e10cSrcweir     while ( nComp-- >= nSize )
705cdf0e10cSrcweir     {
706cdf0e10cSrcweir         ULONG   i;
707cdf0e10cSrcweir         for ( i = 0; i < nSize; i++ )
708cdf0e10cSrcweir         {
709cdf0e10cSrcweir             if ( ( pSource[i]&~0x20 ) != ( pDest[i]&~0x20 ) )
710cdf0e10cSrcweir                 break;
711cdf0e10cSrcweir         }
712cdf0e10cSrcweir         if ( i == nSize )
713cdf0e10cSrcweir             return pSource;
714cdf0e10cSrcweir         pSource++;
715cdf0e10cSrcweir     }
716cdf0e10cSrcweir     return NULL;
717cdf0e10cSrcweir }
718cdf0e10cSrcweir 
719cdf0e10cSrcweir 
720fc9fd3f1SPedro Giffuni static PM_BOOL ImplGetBoundingBox( double* nNumb, PM_BYTE* pSource, ULONG nSize )
721cdf0e10cSrcweir {
722fc9fd3f1SPedro Giffuni     PM_BOOL bRetValue = FALSE;
723fc9fd3f1SPedro Giffuni     PM_BYTE* pDest = ImplSearchEntry( pSource, (PM_BYTE*)"%%BoundingBox:", nSize, 14 );
724cdf0e10cSrcweir     if ( pDest )
725cdf0e10cSrcweir     {
726cdf0e10cSrcweir         nNumb[0] = nNumb[1] = nNumb[2] = nNumb[3] = 0;
727cdf0e10cSrcweir         pDest += 14;
728cdf0e10cSrcweir 
729cdf0e10cSrcweir         int nSizeLeft = nSize - ( pDest - pSource );
730cdf0e10cSrcweir         if ( nSizeLeft > 100 )
731fc9fd3f1SPedro Giffuni             nSizeLeft = 100;    // only 100 PM_BYTEs following the bounding box will be checked
732cdf0e10cSrcweir 
733cdf0e10cSrcweir         int i;
734cdf0e10cSrcweir         for ( i = 0; ( i < 4 ) && nSizeLeft; i++ )
735cdf0e10cSrcweir         {
736cdf0e10cSrcweir             int     nDivision = 1;
737fc9fd3f1SPedro Giffuni             PM_BOOL bDivision = FALSE;
738fc9fd3f1SPedro Giffuni             PM_BOOL bNegative = FALSE;
739fc9fd3f1SPedro Giffuni             PM_BOOL bValid = TRUE;
740cdf0e10cSrcweir 
741cdf0e10cSrcweir             while ( ( --nSizeLeft ) && ( *pDest == ' ' ) || ( *pDest == 0x9 ) ) pDest++;
742fc9fd3f1SPedro Giffuni             PM_BYTE nPM_BYTE = *pDest;
743fc9fd3f1SPedro Giffuni             while ( nSizeLeft && ( nPM_BYTE != ' ' ) && ( nPM_BYTE != 0x9 ) && ( nPM_BYTE != 0xd ) && ( nPM_BYTE != 0xa ) )
744cdf0e10cSrcweir             {
745fc9fd3f1SPedro Giffuni                 switch ( nPM_BYTE )
746cdf0e10cSrcweir                 {
747cdf0e10cSrcweir                     case '.' :
748cdf0e10cSrcweir                         if ( bDivision )
749cdf0e10cSrcweir                             bValid = FALSE;
750cdf0e10cSrcweir                         else
751cdf0e10cSrcweir                             bDivision = TRUE;
752cdf0e10cSrcweir                         break;
753cdf0e10cSrcweir                     case '-' :
754cdf0e10cSrcweir                         bNegative = TRUE;
755cdf0e10cSrcweir                         break;
756cdf0e10cSrcweir                     default :
757fc9fd3f1SPedro Giffuni                         if ( ( nPM_BYTE < '0' ) || ( nPM_BYTE > '9' ) )
758cdf0e10cSrcweir                             nSizeLeft = 1;  // error parsing the bounding box values
759cdf0e10cSrcweir                         else if ( bValid )
760cdf0e10cSrcweir                         {
761cdf0e10cSrcweir                             if ( bDivision )
762cdf0e10cSrcweir                                 nDivision*=10;
763cdf0e10cSrcweir                             nNumb[i] *= 10;
764fc9fd3f1SPedro Giffuni                             nNumb[i] += nPM_BYTE - '0';
765cdf0e10cSrcweir                         }
766cdf0e10cSrcweir                         break;
767cdf0e10cSrcweir                 }
768cdf0e10cSrcweir                 nSizeLeft--;
769fc9fd3f1SPedro Giffuni                 nPM_BYTE = *(++pDest);
770cdf0e10cSrcweir             }
771cdf0e10cSrcweir             if ( bNegative )
772cdf0e10cSrcweir                 nNumb[i] = -nNumb[i];
773cdf0e10cSrcweir             if ( bDivision && ( nDivision != 1 ) )
774cdf0e10cSrcweir                 nNumb[i] /= nDivision;
775cdf0e10cSrcweir         }
776cdf0e10cSrcweir         if ( i == 4 )
777cdf0e10cSrcweir             bRetValue = TRUE;
778cdf0e10cSrcweir     }
779cdf0e10cSrcweir     return bRetValue;
780cdf0e10cSrcweir }
781cdf0e10cSrcweir 
782cdf0e10cSrcweir #if 0
783fc9fd3f1SPedro Giffuni static void ImplWriteDouble( PM_BYTE** pBuf, double nNumber )
784cdf0e10cSrcweir {
785cdf0e10cSrcweir //  *pBuf += sprintf( (char*)*pBuf, "%f", nNumber );
786cdf0e10cSrcweir 
787cdf0e10cSrcweir     if ( nNumber < 0 )
788cdf0e10cSrcweir     {
789fc9fd3f1SPedro Giffuni         *(*pBuf)++ = (PM_BYTE)'-';
790cdf0e10cSrcweir         nNumber = -nNumber;
791cdf0e10cSrcweir     }
792cdf0e10cSrcweir     ULONG nTemp = (ULONG)nNumber;
793cdf0e10cSrcweir     const String aNumber1( nTemp );
794cdf0e10cSrcweir     ULONG nLen = aNumber1.Len();
795cdf0e10cSrcweir 
796cdf0e10cSrcweir     for ( USHORT n = 0; n < nLen; n++ )
797cdf0e10cSrcweir         *(*pBuf)++ = aNumber1[ n ];
798cdf0e10cSrcweir 
799cdf0e10cSrcweir     nTemp = (ULONG)( ( nNumber - nTemp ) * 100000 );
800cdf0e10cSrcweir     if ( nTemp )
801cdf0e10cSrcweir     {
802fc9fd3f1SPedro Giffuni         *(*pBuf)++ = (PM_BYTE)'.';
803cdf0e10cSrcweir         const String aNumber2( nTemp );
804cdf0e10cSrcweir 
805cdf0e10cSrcweir         ULONG nLen = aNumber2.Len();
806cdf0e10cSrcweir         if ( nLen < 8 )
807cdf0e10cSrcweir         {
808cdf0e10cSrcweir             for ( n = 0; n < ( 5 - nLen ); n++ )
809cdf0e10cSrcweir             {
810fc9fd3f1SPedro Giffuni                 *(*pBuf)++ = (PM_BYTE)'0';
811cdf0e10cSrcweir             }
812cdf0e10cSrcweir         }
813cdf0e10cSrcweir         for ( USHORT n = 0; n < nLen; n++ )
814cdf0e10cSrcweir         {
815cdf0e10cSrcweir             *(*pBuf)++ = aNumber2[ n ];
816cdf0e10cSrcweir         }
817cdf0e10cSrcweir     }
818cdf0e10cSrcweir     *(*pBuf)++ = ' ';
819cdf0e10cSrcweir }
820cdf0e10cSrcweir #endif
821cdf0e10cSrcweir 
822fc9fd3f1SPedro Giffuni inline void ImplWriteString( PM_BYTE** pBuf, const char* sString )
823cdf0e10cSrcweir {
824cdf0e10cSrcweir     strcpy( (char*)*pBuf, sString );
825cdf0e10cSrcweir     *pBuf += strlen( sString );
826cdf0e10cSrcweir }
827cdf0e10cSrcweir 
828fc9fd3f1SPedro Giffuni sal_Bool Os2SalGraphics::drawEPS( long nX, long nY, long nWidth, long nHeight, void* pPtr, ULONG nSize )
829cdf0e10cSrcweir {
830cdf0e10cSrcweir     if ( !mbPrinter )
831cdf0e10cSrcweir         return FALSE;
832cdf0e10cSrcweir 
833fc9fd3f1SPedro Giffuni     PM_BOOL bRet  = FALSE;
834cdf0e10cSrcweir     LONG    nLong = 0;
835cdf0e10cSrcweir     if ( !(DevQueryCaps( mhDC, CAPS_TECHNOLOGY, 1, &nLong ) &&
836cdf0e10cSrcweir            (CAPS_TECH_POSTSCRIPT == nLong)) )
837cdf0e10cSrcweir         return FALSE;
838cdf0e10cSrcweir 
839fc9fd3f1SPedro Giffuni     PM_BYTE*    pBuf = new PM_BYTE[ POSTSCRIPT_BUFSIZE ];
840cdf0e10cSrcweir     double  nBoundingBox[4];
841cdf0e10cSrcweir 
842fc9fd3f1SPedro Giffuni     if ( pBuf && ImplGetBoundingBox( nBoundingBox, (PM_BYTE*)pPtr, nSize ) )
843cdf0e10cSrcweir     {
844cdf0e10cSrcweir         LONG pOS2DXAry[4];        // hack -> print always 2 white space
845cdf0e10cSrcweir         POINTL aPt;
846cdf0e10cSrcweir         aPt.x = 0;
847cdf0e10cSrcweir         aPt.y = 0;
848cdf0e10cSrcweir         PCH pStr = (PCH) "  ";
849cdf0e10cSrcweir         for( long i = 0; i < 4; i++ )
850cdf0e10cSrcweir             pOS2DXAry[i] = i;
851cdf0e10cSrcweir         Ft2CharStringPosAt( mhPS, &aPt, NULL, 0, 2, (PCH)pStr,(PLONG)&pOS2DXAry[0] );
852cdf0e10cSrcweir 
853cdf0e10cSrcweir         OStringBuffer aBuf( POSTSCRIPT_BUFSIZE );
854cdf0e10cSrcweir 
855cdf0e10cSrcweir                 // reserve place for a USHORT
856cdf0e10cSrcweir                 aBuf.append( "aa" );
857cdf0e10cSrcweir 
858cdf0e10cSrcweir                 // #107797# Write out EPS encapsulation header
859cdf0e10cSrcweir                 // ----------------------------------------------------------------------------------
860cdf0e10cSrcweir 
861cdf0e10cSrcweir                 // directly taken from the PLRM 3.0, p. 726. Note:
862cdf0e10cSrcweir                 // this will definitely cause problems when
863cdf0e10cSrcweir                 // recursively creating and embedding PostScript files
864cdf0e10cSrcweir                 // in OOo, since we use statically-named variables
865cdf0e10cSrcweir                 // here (namely, b4_Inc_state_salWin, dict_count_salWin and
866cdf0e10cSrcweir                 // op_count_salWin). Currently, I have no idea on how to
867cdf0e10cSrcweir                 // work around that, except from scanning and
868cdf0e10cSrcweir                 // interpreting the EPS for unused identifiers.
869cdf0e10cSrcweir 
870cdf0e10cSrcweir                 // append the real text
871cdf0e10cSrcweir                 aBuf.append( "\n\n/b4_Inc_state_salWin save def\n"
872cdf0e10cSrcweir                              "/dict_count_salWin countdictstack def\n"
873cdf0e10cSrcweir                              "/op_count_salWin count 1 sub def\n"
874cdf0e10cSrcweir                              "userdict begin\n"
875cdf0e10cSrcweir                              "/showpage {} def\n"
876cdf0e10cSrcweir                              "0 setgray 0 setlinecap\n"
877cdf0e10cSrcweir                              "1 setlinewidth 0 setlinejoin\n"
878cdf0e10cSrcweir                              "10 setmiterlimit [] 0 setdash newpath\n"
879cdf0e10cSrcweir                              "/languagelevel where\n"
880cdf0e10cSrcweir                              "{\n"
881cdf0e10cSrcweir                              "  pop languagelevel\n"
882cdf0e10cSrcweir                              "  1 ne\n"
883cdf0e10cSrcweir                              "  {\n"
884cdf0e10cSrcweir                              "    false setstrokeadjust false setoverprint\n"
885cdf0e10cSrcweir                              "  } if\n"
886cdf0e10cSrcweir                              "} if\n\n" );
887cdf0e10cSrcweir 
888cdf0e10cSrcweir #if 0
889cdf0e10cSrcweir                 // #i10737# Apply clipping manually
890cdf0e10cSrcweir                 // ----------------------------------------------------------------------------------
891cdf0e10cSrcweir 
892cdf0e10cSrcweir                 // Windows seems to ignore any clipping at the HDC,
893cdf0e10cSrcweir                 // when followed by a POSTSCRIPT_PASSTHROUGH
894cdf0e10cSrcweir 
895cdf0e10cSrcweir                 // Check whether we've got a clipping, consisting of
896cdf0e10cSrcweir                 // exactly one rect (other cases should be, but aren't
897cdf0e10cSrcweir                 // handled currently)
898cdf0e10cSrcweir 
899cdf0e10cSrcweir                 // TODO: Handle more than one rectangle here (take
900cdf0e10cSrcweir                 // care, the buffer can handle only POSTSCRIPT_BUFSIZE
901cdf0e10cSrcweir                 // characters!)
902cdf0e10cSrcweir                 if ( mhRegion != 0 &&
903cdf0e10cSrcweir                      mpStdClipRgnData != NULL &&
904cdf0e10cSrcweir                      mpClipRgnData == mpStdClipRgnData &&
905cdf0e10cSrcweir                      mpClipRgnData->rdh.nCount == 1 )
906cdf0e10cSrcweir                 {
907cdf0e10cSrcweir                     RECT* pRect = &(mpClipRgnData->rdh.rcBound);
908cdf0e10cSrcweir 
909cdf0e10cSrcweir                     aBuf.append( "\nnewpath\n" );
910cdf0e10cSrcweir                     aBuf.append( pRect->left );
911cdf0e10cSrcweir                     aBuf.append( " " );
912cdf0e10cSrcweir                     aBuf.append( pRect->top );
913cdf0e10cSrcweir                     aBuf.append( " moveto\n" );
914cdf0e10cSrcweir                     aBuf.append( pRect->right );
915cdf0e10cSrcweir                     aBuf.append( " " );
916cdf0e10cSrcweir                     aBuf.append( pRect->top );
917cdf0e10cSrcweir                     aBuf.append( " lineto\n" );
918cdf0e10cSrcweir                     aBuf.append( pRect->right );
919cdf0e10cSrcweir                     aBuf.append( " " );
920cdf0e10cSrcweir                     aBuf.append( pRect->bottom );
921cdf0e10cSrcweir                     aBuf.append( " lineto\n" );
922cdf0e10cSrcweir                     aBuf.append( pRect->left );
923cdf0e10cSrcweir                     aBuf.append( " " );
924cdf0e10cSrcweir                     aBuf.append( pRect->bottom );
925cdf0e10cSrcweir                     aBuf.append( " lineto\n"
926cdf0e10cSrcweir                                  "closepath\n"
927cdf0e10cSrcweir                                  "clip\n"
928cdf0e10cSrcweir                                  "newpath\n" );
929cdf0e10cSrcweir                 }
930cdf0e10cSrcweir #endif
931cdf0e10cSrcweir 
932cdf0e10cSrcweir                 // #107797# Write out buffer
933cdf0e10cSrcweir                 // ----------------------------------------------------------------------------------
934cdf0e10cSrcweir                 *((USHORT*)aBuf.getStr()) = (USHORT)( aBuf.getLength() - 2 );
935cdf0e10cSrcweir                 //Escape ( mhDC, nEscape, aBuf.getLength(), (LPTSTR)aBuf.getStr(), 0 );
936cdf0e10cSrcweir                 DevEscape( mhDC, DEVESC_RAWDATA, aBuf.getLength(),
937fc9fd3f1SPedro Giffuni                         (PM_BYTE*)aBuf.getStr(), 0, NULL );
938cdf0e10cSrcweir 
939cdf0e10cSrcweir         double dM11 = nWidth / ( nBoundingBox[2] - nBoundingBox[0] );
940cdf0e10cSrcweir         double dM22 = - ( nHeight / (nBoundingBox[1] - nBoundingBox[3] ) );
941cdf0e10cSrcweir 
942cdf0e10cSrcweir                 // reserve a USHORT again
943cdf0e10cSrcweir                 aBuf.setLength( 2 );
944cdf0e10cSrcweir                 aBuf.append( "\n\n[" );
945cdf0e10cSrcweir                 aBuf.append( dM11 );
946cdf0e10cSrcweir                 aBuf.append( " 0 0 " );
947cdf0e10cSrcweir                 aBuf.append( dM22 );
948cdf0e10cSrcweir                 aBuf.append( ' ' );
949cdf0e10cSrcweir                 aBuf.append( nX - ( dM11 * nBoundingBox[0] ) );
950cdf0e10cSrcweir                 aBuf.append( ' ' );
951cdf0e10cSrcweir                 aBuf.append( nY - ( dM22 * nBoundingBox[3] ) );
952cdf0e10cSrcweir                 aBuf.append( "] concat\n"
953cdf0e10cSrcweir                              "%%BeginDocument:\n" );
954cdf0e10cSrcweir                 *((USHORT*)aBuf.getStr()) = (USHORT)( aBuf.getLength() - 2 );
955cdf0e10cSrcweir                 DevEscape( mhDC, DEVESC_RAWDATA, aBuf.getLength(),
956fc9fd3f1SPedro Giffuni                         (PM_BYTE*)aBuf.getStr(), 0, NULL );
957cdf0e10cSrcweir #if 0
958fc9fd3f1SPedro Giffuni         PM_BYTE* pTemp = pBuf;
959cdf0e10cSrcweir         ImplWriteString( &pTemp, "save\n[ " );
960cdf0e10cSrcweir         ImplWriteDouble( &pTemp, dM11 );
961cdf0e10cSrcweir         ImplWriteDouble( &pTemp, 0 );
962cdf0e10cSrcweir         ImplWriteDouble( &pTemp, 0 );
963cdf0e10cSrcweir         ImplWriteDouble( &pTemp, dM22 );
964cdf0e10cSrcweir         ImplWriteDouble( &pTemp, nX - ( dM11 * nBoundingBox[0] ) );
965cdf0e10cSrcweir         ImplWriteDouble( &pTemp, mnHeight - nY - ( dM22 * nBoundingBox[3] ) );
966cdf0e10cSrcweir         ImplWriteString( &pTemp, "] concat /showpage {} def\n" );
967cdf0e10cSrcweir 
968cdf0e10cSrcweir         if ( DevEscape( mhDC, DEVESC_RAWDATA, pTemp - pBuf,
969fc9fd3f1SPedro Giffuni             (PM_BYTE*)pBuf, 0, NULL ) == DEV_OK )
970cdf0e10cSrcweir #endif //
971cdf0e10cSrcweir         {
972fc9fd3f1SPedro Giffuni             sal_uInt32 nToDo = nSize;
973fc9fd3f1SPedro Giffuni             sal_uInt32 nDoNow;
974cdf0e10cSrcweir             bRet = TRUE;
975cdf0e10cSrcweir             while( nToDo && bRet )
976cdf0e10cSrcweir             {
977cdf0e10cSrcweir                 nDoNow = 0x4000;
978cdf0e10cSrcweir                 if ( nToDo < nDoNow )
979cdf0e10cSrcweir                     nDoNow = nToDo;
980cdf0e10cSrcweir 
981fc9fd3f1SPedro Giffuni                 if ( DevEscape( mhDC, DEVESC_RAWDATA, nDoNow, (PM_BYTE*)pPtr + nSize - nToDo,
982cdf0e10cSrcweir                    0, NULL ) == -1 )
983cdf0e10cSrcweir                     bRet = FALSE;
984cdf0e10cSrcweir                 nToDo -= nDoNow;
985cdf0e10cSrcweir             }
986cdf0e10cSrcweir 
987cdf0e10cSrcweir             if ( bRet )
988cdf0e10cSrcweir             {
989cdf0e10cSrcweir                 strcpy ( (char*)pBuf, "\nrestore\n" );
990fc9fd3f1SPedro Giffuni                 if ( DevEscape( mhDC, DEVESC_RAWDATA, 9, (PM_BYTE*)pBuf,
991cdf0e10cSrcweir                     0, NULL ) == DEV_OK ) bRet = TRUE;
992cdf0e10cSrcweir             }
993cdf0e10cSrcweir 
994cdf0e10cSrcweir                 // #107797# Write out EPS encapsulation footer
995cdf0e10cSrcweir                 // ----------------------------------------------------------------------------------
996cdf0e10cSrcweir                 // reserve a USHORT again
997cdf0e10cSrcweir                 aBuf.setLength( 2 );
998cdf0e10cSrcweir                 aBuf.append( "%%EndDocument\n"
999cdf0e10cSrcweir                              "count op_count_salWin sub {pop} repeat\n"
1000cdf0e10cSrcweir                              "countdictstack dict_count_salWin sub {end} repeat\n"
1001cdf0e10cSrcweir                              "b4_Inc_state_salWin restore\n\n" );
1002cdf0e10cSrcweir                 *((USHORT*)aBuf.getStr()) = (USHORT)( aBuf.getLength() - 2 );
1003cdf0e10cSrcweir                 DevEscape( mhDC, DEVESC_RAWDATA, aBuf.getLength(),
1004fc9fd3f1SPedro Giffuni                         (PM_BYTE*)aBuf.getStr(), 0, NULL );
1005cdf0e10cSrcweir                 bRet = TRUE;
1006cdf0e10cSrcweir 
1007cdf0e10cSrcweir         }
1008cdf0e10cSrcweir     }
1009cdf0e10cSrcweir     delete [] pBuf;
1010cdf0e10cSrcweir     return bRet;
1011cdf0e10cSrcweir }
1012cdf0e10cSrcweir 
1013cdf0e10cSrcweir /*
1014cdf0e10cSrcweir  * IsNativeControlSupported()
1015cdf0e10cSrcweir  *
1016cdf0e10cSrcweir  *  Returns TRUE if the platform supports native
1017cdf0e10cSrcweir  *  drawing of the control defined by nPart
1018cdf0e10cSrcweir  */
1019fc9fd3f1SPedro Giffuni sal_Bool Os2SalGraphics::IsNativeControlSupported( ControlType nType, ControlPart nPart )
1020cdf0e10cSrcweir {
1021cdf0e10cSrcweir     return( FALSE );
1022cdf0e10cSrcweir }
1023cdf0e10cSrcweir 
1024cdf0e10cSrcweir // -----------------------------------------------------------------------
1025cdf0e10cSrcweir 
1026cdf0e10cSrcweir SystemGraphicsData Os2SalGraphics::GetGraphicsData() const
1027cdf0e10cSrcweir {
1028cdf0e10cSrcweir     SystemGraphicsData aRes;
1029cdf0e10cSrcweir     aRes.nSize = sizeof(aRes);
1030cdf0e10cSrcweir #if 0
1031cdf0e10cSrcweir     aRes.hDC = mhDC;
1032cdf0e10cSrcweir #endif
1033cdf0e10cSrcweir     return aRes;
1034cdf0e10cSrcweir }
1035cdf0e10cSrcweir 
1036cdf0e10cSrcweir // -----------------------------------------------------------------------
1037