xref: /AOO41X/main/toolkit/source/awt/vclxgraphics.cxx (revision 8809db7a87f97847b57a57f4cd2b0104b2b83182)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_toolkit.hxx"
26 
27 #include <toolkit/awt/vclxgraphics.hxx>
28 #include <toolkit/awt/vclxdevice.hxx>
29 #include <toolkit/helper/macros.hxx>
30 #include <toolkit/helper/vclunohelper.hxx>
31 #include <cppuhelper/typeprovider.hxx>
32 #include <rtl/memory.h>
33 #include <rtl/uuid.h>
34 
35 #include <vcl/svapp.hxx>
36 #include <vcl/outdev.hxx>
37 #include <vcl/gradient.hxx>
38 #include <tools/debug.hxx>
39 
40 
41 //  ----------------------------------------------------
42 //  class VCLXGraphics
43 //  ----------------------------------------------------
44 
45 // ::com::sun::star::uno::XInterface
46 ::com::sun::star::uno::Any VCLXGraphics::queryInterface( const ::com::sun::star::uno::Type & rType ) throw(::com::sun::star::uno::RuntimeException)
47 {
48     ::com::sun::star::uno::Any aRet = ::cppu::queryInterface( rType,
49                                         SAL_STATIC_CAST( ::com::sun::star::awt::XGraphics*, this ),
50                                         SAL_STATIC_CAST( ::com::sun::star::lang::XTypeProvider*, this ),
51                                         SAL_STATIC_CAST( ::com::sun::star::lang::XUnoTunnel*, this ) );
52     return (aRet.hasValue() ? aRet : OWeakObject::queryInterface( rType ));
53 }
54 
55 // ::com::sun::star::lang::XUnoTunnel
56 IMPL_XUNOTUNNEL( VCLXGraphics )
57 
58 // ::com::sun::star::lang::XTypeProvider
59 IMPL_XTYPEPROVIDER_START( VCLXGraphics )
60     getCppuType( ( ::com::sun::star::uno::Reference< ::com::sun::star::awt::XGraphics>* ) NULL )
61 IMPL_XTYPEPROVIDER_END
62 
63 VCLXGraphics::VCLXGraphics() : mrMutex( Application::GetSolarMutex() )
64 {
65     mpOutputDevice = NULL;
66     mpClipRegion = NULL;
67 }
68 
69 VCLXGraphics::~VCLXGraphics()
70 {
71     List* pLst = mpOutputDevice ? mpOutputDevice->GetUnoGraphicsList() : NULL;
72     if ( pLst )
73         pLst->Remove( this );
74 
75     delete mpClipRegion;
76 }
77 
78 void VCLXGraphics::SetOutputDevice( OutputDevice* pOutDev )
79 {
80     mpOutputDevice = pOutDev;
81     mxDevice = NULL;
82 }
83 
84 void VCLXGraphics::Init( OutputDevice* pOutDev )
85 {
86     DBG_ASSERT( !mpOutputDevice, "VCLXGraphics::Init allready has pOutDev !" );
87     mpOutputDevice  = pOutDev;
88 
89     maFont          = mpOutputDevice->GetFont();
90     maTextColor     = COL_BLACK;
91     maTextFillColor = COL_TRANSPARENT;
92     maLineColor     = COL_BLACK;
93     maFillColor     = COL_WHITE;
94     meRasterOp      = ROP_OVERPAINT;
95     mpClipRegion    = NULL;
96 
97     // Register at OutputDevice
98     List* pLst = mpOutputDevice->GetUnoGraphicsList();
99     if ( !pLst )
100         pLst = mpOutputDevice->CreateUnoGraphicsList();
101     pLst->Insert( this, LIST_APPEND );
102 }
103 
104 void VCLXGraphics::InitOutputDevice( sal_uInt16 nFlags )
105 {
106     if(mpOutputDevice)
107     {
108         vos::OGuard aVclGuard( Application::GetSolarMutex()  );
109 
110         if ( nFlags & INITOUTDEV_FONT )
111         {
112             mpOutputDevice->SetFont( maFont );
113             mpOutputDevice->SetTextColor( maTextColor );
114             mpOutputDevice->SetTextFillColor( maTextFillColor );
115         }
116 
117         if ( nFlags & INITOUTDEV_COLORS )
118         {
119             mpOutputDevice->SetLineColor( maLineColor );
120             mpOutputDevice->SetFillColor( maFillColor );
121         }
122 
123         if ( nFlags & INITOUTDEV_RASTEROP )
124         {
125             mpOutputDevice->SetRasterOp( meRasterOp );
126         }
127 
128         if ( nFlags & INITOUTDEV_CLIPREGION )
129         {
130             if( mpClipRegion )
131                 mpOutputDevice->SetClipRegion( *mpClipRegion );
132             else
133                 mpOutputDevice->SetClipRegion();
134         }
135     }
136 }
137 
138 ::com::sun::star::uno::Reference< ::com::sun::star::awt::XDevice > VCLXGraphics::getDevice() throw(::com::sun::star::uno::RuntimeException)
139 {
140     ::vos::OGuard aGuard( GetMutex() );
141 
142     if( !mxDevice.is() && mpOutputDevice )
143     {
144         VCLXDevice* pDev = new VCLXDevice;
145         pDev->SetOutputDevice( mpOutputDevice );
146         mxDevice = pDev;
147     }
148     return mxDevice;
149 }
150 
151 ::com::sun::star::awt::SimpleFontMetric VCLXGraphics::getFontMetric() throw(::com::sun::star::uno::RuntimeException)
152 {
153     ::vos::OGuard aGuard( GetMutex() );
154 
155     ::com::sun::star::awt::SimpleFontMetric aM;
156     if( mpOutputDevice )
157     {
158         mpOutputDevice->SetFont( maFont );
159         aM = VCLUnoHelper::CreateFontMetric( mpOutputDevice->GetFontMetric() );
160     }
161     return aM;
162 }
163 
164 void VCLXGraphics::setFont( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XFont >& rxFont ) throw(::com::sun::star::uno::RuntimeException)
165 {
166     ::vos::OGuard aGuard( GetMutex() );
167 
168     maFont = VCLUnoHelper::CreateFont( rxFont );
169 }
170 
171 void VCLXGraphics::selectFont( const ::com::sun::star::awt::FontDescriptor& rDescription ) throw(::com::sun::star::uno::RuntimeException)
172 {
173     ::vos::OGuard aGuard( GetMutex() );
174 
175     maFont = VCLUnoHelper::CreateFont( rDescription, Font() );
176 }
177 
178 void VCLXGraphics::setTextColor( sal_Int32 nColor ) throw(::com::sun::star::uno::RuntimeException)
179 {
180     ::vos::OGuard aGuard( GetMutex() );
181 
182     maTextColor = Color( (sal_uInt32)nColor );
183 }
184 
185 void VCLXGraphics::setTextFillColor( sal_Int32 nColor ) throw(::com::sun::star::uno::RuntimeException)
186 {
187     ::vos::OGuard aGuard( GetMutex() );
188 
189     maTextFillColor = Color( (sal_uInt32)nColor );
190 }
191 
192 void VCLXGraphics::setLineColor( sal_Int32 nColor ) throw(::com::sun::star::uno::RuntimeException)
193 {
194     ::vos::OGuard aGuard( GetMutex() );
195 
196     maLineColor = Color( (sal_uInt32)nColor );
197 }
198 
199 void VCLXGraphics::setFillColor( sal_Int32 nColor ) throw(::com::sun::star::uno::RuntimeException)
200 {
201     ::vos::OGuard aGuard( GetMutex() );
202 
203     maFillColor = Color( (sal_uInt32)nColor );
204 }
205 
206 void VCLXGraphics::setRasterOp( ::com::sun::star::awt::RasterOperation eROP ) throw(::com::sun::star::uno::RuntimeException)
207 {
208     ::vos::OGuard aGuard( GetMutex() );
209 
210     meRasterOp = (RasterOp)eROP;
211 }
212 
213 void VCLXGraphics::setClipRegion( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XRegion >& rxRegion ) throw(::com::sun::star::uno::RuntimeException)
214 {
215     ::vos::OGuard aGuard( GetMutex() );
216 
217     delete mpClipRegion;
218     if ( rxRegion.is() )
219         mpClipRegion = new Region( VCLUnoHelper::GetRegion( rxRegion ) );
220     else
221         mpClipRegion = NULL;
222 }
223 
224 void VCLXGraphics::intersectClipRegion( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XRegion >& rxRegion ) throw(::com::sun::star::uno::RuntimeException)
225 {
226     ::vos::OGuard aGuard( GetMutex() );
227 
228     if ( rxRegion.is() )
229     {
230         Region aRegion( VCLUnoHelper::GetRegion( rxRegion ) );
231         if ( !mpClipRegion )
232             mpClipRegion = new Region( aRegion );
233         else
234             mpClipRegion->Intersect( aRegion );
235     }
236 }
237 
238 void VCLXGraphics::push(  ) throw(::com::sun::star::uno::RuntimeException)
239 {
240     ::vos::OGuard aGuard( GetMutex() );
241 
242 
243     if( mpOutputDevice )
244         mpOutputDevice->Push();
245 }
246 
247 void VCLXGraphics::pop(  ) throw(::com::sun::star::uno::RuntimeException)
248 {
249     ::vos::OGuard aGuard( GetMutex() );
250 
251 
252     if( mpOutputDevice )
253         mpOutputDevice->Pop();
254 }
255 
256 void VCLXGraphics::copy( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XDevice >& rxSource, sal_Int32 nSourceX, sal_Int32 nSourceY, sal_Int32 nSourceWidth, sal_Int32 nSourceHeight, sal_Int32 nDestX, sal_Int32 nDestY, sal_Int32 nDestWidth, sal_Int32 nDestHeight ) throw(::com::sun::star::uno::RuntimeException)
257 {
258     ::vos::OGuard aGuard( GetMutex() );
259 
260     if ( mpOutputDevice )
261     {
262         VCLXDevice* pFromDev = VCLXDevice::GetImplementation( rxSource );
263         DBG_ASSERT( pFromDev, "VCLXGraphics::copy - invalid device" );
264         if ( pFromDev )
265         {
266             InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP );
267             mpOutputDevice->DrawOutDev( Point( nDestX, nDestY ), Size( nDestWidth, nDestHeight ),
268                                     Point( nSourceX, nSourceY ), Size( nSourceWidth, nSourceHeight ), *pFromDev->GetOutputDevice() );
269         }
270     }
271 }
272 
273 void VCLXGraphics::draw( const ::com::sun::star::uno::Reference< ::com::sun::star::awt::XDisplayBitmap >& rxBitmapHandle, sal_Int32 nSourceX, sal_Int32 nSourceY, sal_Int32 nSourceWidth, sal_Int32 nSourceHeight, sal_Int32 nDestX, sal_Int32 nDestY, sal_Int32 nDestWidth, sal_Int32 nDestHeight ) throw(::com::sun::star::uno::RuntimeException)
274 {
275     ::vos::OGuard aGuard( GetMutex() );
276 
277     if( mpOutputDevice )
278     {
279         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP);
280         ::com::sun::star::uno::Reference< ::com::sun::star::awt::XBitmap > xBitmap( rxBitmapHandle, ::com::sun::star::uno::UNO_QUERY );
281         BitmapEx aBmpEx = VCLUnoHelper::GetBitmap( xBitmap );
282 
283         Point aPos(nDestX - nSourceX, nDestY - nSourceY);
284         Size aSz = aBmpEx.GetSizePixel();
285 
286         if(nDestWidth != nSourceWidth)
287         {
288             float zoomX = (float)nDestWidth / (float)nSourceWidth;
289             aSz.Width() = (long) ((float)aSz.Width() * zoomX);
290         }
291 
292         if(nDestHeight != nSourceHeight)
293         {
294             float zoomY = (float)nDestHeight / (float)nSourceHeight;
295             aSz.Height() = (long) ((float)aSz.Height() * zoomY);
296         }
297 
298         if(nSourceX || nSourceY || aSz.Width() != nSourceWidth || aSz.Height() != nSourceHeight)
299             mpOutputDevice->IntersectClipRegion(Region(Rectangle(nDestX, nDestY, nDestX + nDestWidth - 1, nDestY + nDestHeight - 1)));
300 
301         mpOutputDevice->DrawBitmapEx( aPos, aSz, aBmpEx );
302     }
303 }
304 
305 void VCLXGraphics::drawPixel( sal_Int32 x, sal_Int32 y ) throw(::com::sun::star::uno::RuntimeException)
306 {
307     ::vos::OGuard aGuard( GetMutex() );
308 
309     if( mpOutputDevice )
310     {
311         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
312         mpOutputDevice->DrawPixel( Point( x, y ) );
313     }
314 }
315 
316 void VCLXGraphics::drawLine( sal_Int32 x1, sal_Int32 y1, sal_Int32 x2, sal_Int32 y2 ) throw(::com::sun::star::uno::RuntimeException)
317 {
318     ::vos::OGuard aGuard( GetMutex() );
319 
320     if( mpOutputDevice )
321     {
322         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
323         mpOutputDevice->DrawLine( Point( x1, y1 ), Point( x2, y2 ) );
324     }
325 }
326 
327 void VCLXGraphics::drawRect( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height ) throw(::com::sun::star::uno::RuntimeException)
328 {
329     ::vos::OGuard aGuard( GetMutex() );
330 
331     if( mpOutputDevice )
332     {
333         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
334         mpOutputDevice->DrawRect( Rectangle( Point( x, y ), Size( width, height ) ) );
335     }
336 }
337 
338 void VCLXGraphics::drawRoundedRect( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height, sal_Int32 nHorzRound, sal_Int32 nVertRound ) throw(::com::sun::star::uno::RuntimeException)
339 {
340     ::vos::OGuard aGuard( GetMutex() );
341 
342     if( mpOutputDevice )
343     {
344         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
345         mpOutputDevice->DrawRect( Rectangle( Point( x, y ), Size( width, height ) ), nHorzRound, nVertRound );
346     }
347 }
348 
349 void VCLXGraphics::drawPolyLine( const ::com::sun::star::uno::Sequence< sal_Int32 >& DataX, const ::com::sun::star::uno::Sequence< sal_Int32 >& DataY ) throw(::com::sun::star::uno::RuntimeException)
350 {
351     ::vos::OGuard aGuard( GetMutex() );
352 
353     if( mpOutputDevice )
354     {
355         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
356         mpOutputDevice->DrawPolyLine( VCLUnoHelper::CreatePolygon( DataX, DataY ) );
357     }
358 }
359 
360 void VCLXGraphics::drawPolygon( const ::com::sun::star::uno::Sequence< sal_Int32 >& DataX, const ::com::sun::star::uno::Sequence< sal_Int32 >& DataY ) throw(::com::sun::star::uno::RuntimeException)
361 {
362     ::vos::OGuard aGuard( GetMutex() );
363 
364     if( mpOutputDevice )
365     {
366         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
367         mpOutputDevice->DrawPolygon( VCLUnoHelper::CreatePolygon( DataX, DataY ) );
368     }
369 }
370 
371 void VCLXGraphics::drawPolyPolygon( const ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Sequence< sal_Int32 > >& DataX, const ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Sequence< sal_Int32 > >& DataY ) throw(::com::sun::star::uno::RuntimeException)
372 {
373     ::vos::OGuard aGuard( GetMutex() );
374 
375     if( mpOutputDevice )
376     {
377         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
378         sal_uInt16 nPolys = (sal_uInt16) DataX.getLength();
379         PolyPolygon aPolyPoly( nPolys );
380         for ( sal_uInt16 n = 0; n < nPolys; n++ )
381             aPolyPoly[n] = VCLUnoHelper::CreatePolygon( DataX.getConstArray()[n], DataY.getConstArray()[n] );
382 
383         mpOutputDevice->DrawPolyPolygon( aPolyPoly );
384     }
385 }
386 
387 void VCLXGraphics::drawEllipse( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height ) throw(::com::sun::star::uno::RuntimeException)
388 {
389     ::vos::OGuard aGuard( GetMutex() );
390 
391     if( mpOutputDevice )
392     {
393         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
394         mpOutputDevice->DrawEllipse( Rectangle( Point( x, y ), Size( width, height ) ) );
395     }
396 }
397 
398 void VCLXGraphics::drawArc( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height, sal_Int32 x1, sal_Int32 y1, sal_Int32 x2, sal_Int32 y2 ) throw(::com::sun::star::uno::RuntimeException)
399 {
400     ::vos::OGuard aGuard( GetMutex() );
401 
402     if( mpOutputDevice )
403     {
404         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
405         mpOutputDevice->DrawArc( Rectangle( Point( x, y ), Size( width, height ) ), Point( x1, y1 ), Point( x2, y2 ) );
406     }
407 }
408 
409 void VCLXGraphics::drawPie( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height, sal_Int32 x1, sal_Int32 y1, sal_Int32 x2, sal_Int32 y2 ) throw(::com::sun::star::uno::RuntimeException)
410 {
411     ::vos::OGuard aGuard( GetMutex() );
412 
413     if( mpOutputDevice )
414     {
415         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
416         mpOutputDevice->DrawPie( Rectangle( Point( x, y ), Size( width, height ) ), Point( x1, y1 ), Point( x2, y2 ) );
417     }
418 }
419 
420 void VCLXGraphics::drawChord( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height, sal_Int32 x1, sal_Int32 y1, sal_Int32 x2, sal_Int32 y2 ) throw(::com::sun::star::uno::RuntimeException)
421 {
422     ::vos::OGuard aGuard( GetMutex() );
423 
424     if( mpOutputDevice )
425     {
426         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
427         mpOutputDevice->DrawChord( Rectangle( Point( x, y ), Size( width, height ) ), Point( x1, y1 ), Point( x2, y2 ) );
428     }
429 }
430 
431 void VCLXGraphics::drawGradient( sal_Int32 x, sal_Int32 y, sal_Int32 width, sal_Int32 height, const ::com::sun::star::awt::Gradient& rGradient ) throw(::com::sun::star::uno::RuntimeException)
432 {
433     ::vos::OGuard aGuard( GetMutex() );
434 
435     if( mpOutputDevice )
436     {
437         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS );
438         Gradient aGradient((GradientStyle)rGradient.Style, rGradient.StartColor, rGradient.EndColor);
439         aGradient.SetAngle(rGradient.Angle);
440         aGradient.SetBorder(rGradient.Border);
441         aGradient.SetOfsX(rGradient.XOffset);
442         aGradient.SetOfsY(rGradient.YOffset);
443         aGradient.SetStartIntensity(rGradient.StartIntensity);
444         aGradient.SetEndIntensity(rGradient.EndIntensity);
445         aGradient.SetSteps(rGradient.StepCount);
446         mpOutputDevice->DrawGradient( Rectangle( Point( x, y ), Size( width, height ) ), aGradient );
447     }
448 }
449 
450 void VCLXGraphics::drawText( sal_Int32 x, sal_Int32 y, const ::rtl::OUString& rText ) throw(::com::sun::star::uno::RuntimeException)
451 {
452     ::vos::OGuard aGuard( GetMutex() );
453 
454     if( mpOutputDevice )
455     {
456         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS |INITOUTDEV_FONT);
457         mpOutputDevice->DrawText( Point( x, y ), rText );
458     }
459 }
460 
461 void VCLXGraphics::drawTextArray( sal_Int32 x, sal_Int32 y, const ::rtl::OUString& rText, const ::com::sun::star::uno::Sequence< sal_Int32 >& rLongs ) throw(::com::sun::star::uno::RuntimeException)
462 {
463     ::vos::OGuard aGuard( GetMutex() );
464 
465     if( mpOutputDevice )
466     {
467         InitOutputDevice( INITOUTDEV_CLIPREGION|INITOUTDEV_RASTEROP|INITOUTDEV_COLORS|INITOUTDEV_FONT );
468         mpOutputDevice->DrawTextArray( Point( x, y ), rText, rLongs.getConstArray() );
469     }
470 }
471 
472 
473 
474 
475