1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: cairo_xlib_cairo.cxx,v $
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_canvas.hxx"
34 #include <tools/prex.h>
35 #include <X11/extensions/Xrender.h>
37 #include <tools/postx.h>
39 #include "cairo_xlib_cairo.hxx"
41 #include <vcl/sysdata.hxx>
42 #include <vcl/bitmap.hxx>
43 #include <vcl/virdev.hxx>
44 #include <basegfx/vector/b2isize.hxx>
49 #include <cairo-xlib.h>
50 #include <cairo-xlib-xrender.h>
52 // TODO(F3): svp headless case!
54 bool IsCairoWorking( OutputDevice
* pOutDev
)
59 Display
* pDisplay
= (Display
*)pOutDev
->GetSystemGfxData().pDisplay
;
61 return XQueryExtension( pDisplay
, "RENDER", &nDummy
, &nDummy
, &nDummy
);
64 X11SysData::X11SysData() :
74 X11SysData::X11SysData( const SystemGraphicsData
& pSysDat
) :
75 pDisplay(pSysDat
.pDisplay
),
76 hDrawable(pSysDat
.hDrawable
),
77 pVisual(pSysDat
.pVisual
),
78 nScreen(pSysDat
.nScreen
),
79 nDepth(pSysDat
.nDepth
),
80 aColormap(pSysDat
.aColormap
),
81 pRenderFormat(pSysDat
.pRenderFormat
)
84 X11SysData::X11SysData( const SystemEnvData
& pSysDat
) :
85 pDisplay(pSysDat
.pDisplay
),
86 hDrawable(pSysDat
.aWindow
),
87 pVisual(pSysDat
.pVisual
),
88 nScreen(pSysDat
.nScreen
),
89 nDepth(pSysDat
.nDepth
),
90 aColormap(pSysDat
.aColormap
),
94 X11Pixmap::~X11Pixmap()
96 if( mpDisplay
&& mhDrawable
)
97 XFreePixmap( (Display
*)mpDisplay
, mhDrawable
);
101 * Surface::Surface: Create Canvas surface with existing data
102 * @param pSysData Platform native system environment data (struct SystemEnvData in vcl/inc/sysdata.hxx)
103 * @param pSurface Cairo surface
105 * pSysData contains the platform native Drawable reference
106 * This constructor only stores data, it does no processing.
107 * It is used by e.g. Surface::getSimilar()
109 * Set the mpSurface as pSurface
111 X11Surface::X11Surface( const X11SysData
& rSysData
,
112 const X11PixmapSharedPtr
& rPixmap
,
113 const CairoSurfaceSharedPtr
& pSurface
) :
120 * Surface::Surface: Create generic Canvas surface using given Cairo Surface
122 * @param pSurface Cairo Surface
124 * This constructor only stores data, it does no processing.
125 * It is used with e.g. cairo_image_surface_create_for_data()
126 * Unlike other constructors, mpSysData is set to NULL
128 * Set the mpSurface as pSurface
130 X11Surface::X11Surface( const CairoSurfaceSharedPtr
& pSurface
) :
137 * Surface::Surface: Create Canvas surface from Window reference.
138 * @param pSysData Platform native system environment data (struct SystemEnvData in vcl/inc/sysdata.hxx)
139 * @param x horizontal location of the new surface
140 * @param y vertical location of the new surface
141 * @param width width of the new surface
142 * @param height height of the new surface
144 * pSysData contains the platform native Window reference.
146 * pSysData is used to create a surface on the Window
148 * Set the mpSurface to the new surface or NULL
150 X11Surface::X11Surface( const X11SysData
& rSysData
, int x
, int y
, int width
, int height
) :
154 cairo_xlib_surface_create( (Display
*)rSysData
.pDisplay
,
156 (Visual
*)rSysData
.pVisual
,
157 width
+ x
, height
+ y
),
158 &cairo_surface_destroy
)
160 cairo_surface_set_device_offset(mpSurface
.get(), x
, y
);
164 * Surface::Surface: Create platfrom native Canvas surface from BitmapSystemData
165 * @param pSysData Platform native system environment data (struct SystemEnvData in vcl/inc/sysdata.hxx)
166 * @param pBmpData Platform native image data (struct BitmapSystemData in vcl/inc/bitmap.hxx)
167 * @param width width of the new surface
168 * @param height height of the new surface
170 * The pBmpData provides the imagedata that the created surface should contain.
172 * Set the mpSurface to the new surface or NULL
174 X11Surface::X11Surface( const X11SysData
& rSysData
,
175 const BitmapSystemData
& rData
) :
176 maSysData( rSysData
),
179 cairo_xlib_surface_create( (Display
*)rSysData
.pDisplay
,
180 (Drawable
)rData
.aPixmap
,
181 (Visual
*) rSysData
.pVisual
,
182 rData
.mnWidth
, rData
.mnHeight
),
183 &cairo_surface_destroy
)
188 * Surface::getCairo: Create Cairo (drawing object) for the Canvas surface
190 * @return new Cairo or NULL
192 CairoSharedPtr
X11Surface::getCairo() const
194 return CairoSharedPtr( cairo_create(mpSurface
.get()),
199 * Surface::getSimilar: Create new similar Canvas surface
200 * @param aContent format of the new surface (cairo_content_t from cairo/src/cairo.h)
201 * @param width width of the new surface
202 * @param height height of the new surface
204 * Creates a new Canvas surface. This normally creates platform native surface, even though
205 * generic function is used.
207 * Cairo surface from aContent (cairo_content_t)
209 * @return new surface or NULL
211 SurfaceSharedPtr
X11Surface::getSimilar( Content aContent
, int width
, int height
) const
215 if( maSysData
.pDisplay
&& maSysData
.hDrawable
)
217 XRenderPictFormat
* pFormat
;
222 case CAIRO_CONTENT_ALPHA
:
223 nFormat
= PictStandardA8
;
225 case CAIRO_CONTENT_COLOR
:
226 nFormat
= PictStandardRGB24
;
228 case CAIRO_CONTENT_COLOR_ALPHA
:
230 nFormat
= PictStandardARGB32
;
234 pFormat
= XRenderFindStandardFormat( (Display
*)maSysData
.pDisplay
, nFormat
);
235 hPixmap
= XCreatePixmap( (Display
*)maSysData
.pDisplay
, maSysData
.hDrawable
,
236 width
> 0 ? width
: 1, height
> 0 ? height
: 1,
239 X11SysData
aSysData(maSysData
);
240 aSysData
.pRenderFormat
= pFormat
;
241 return SurfaceSharedPtr(
242 new X11Surface( aSysData
,
244 new X11Pixmap(hPixmap
, maSysData
.pDisplay
)),
245 CairoSurfaceSharedPtr(
246 cairo_xlib_surface_create_with_xrender_format(
247 (Display
*)maSysData
.pDisplay
,
249 ScreenOfDisplay((Display
*)maSysData
.pDisplay
, maSysData
.nScreen
),
250 pFormat
, width
, height
),
251 &cairo_surface_destroy
) ));
254 return SurfaceSharedPtr(
255 new X11Surface( maSysData
,
256 X11PixmapSharedPtr(),
257 CairoSurfaceSharedPtr(
258 cairo_surface_create_similar( mpSurface
.get(), aContent
, width
, height
),
259 &cairo_surface_destroy
)));
262 boost::shared_ptr
<VirtualDevice
> X11Surface::createVirtualDevice() const
264 SystemGraphicsData aSystemGraphicsData
;
266 aSystemGraphicsData
.nSize
= sizeof(SystemGraphicsData
);
267 aSystemGraphicsData
.hDrawable
= getDrawable();
268 aSystemGraphicsData
.pRenderFormat
= getRenderFormat();
270 return boost::shared_ptr
<VirtualDevice
>(
271 new VirtualDevice( &aSystemGraphicsData
, getDepth() ));
275 * Surface::Resize: Resizes the Canvas surface.
276 * @param width new width of the surface
277 * @param height new height of the surface
281 * @return The new surface or NULL
283 void X11Surface::Resize( int width
, int height
)
285 cairo_xlib_surface_set_size( mpSurface
.get(), width
, height
);
288 void X11Surface::flush() const
290 XSync( (Display
*)maSysData
.pDisplay
, false );
294 * Surface::getDepth: Get the color depth of the Canvas surface.
296 * @return color depth
298 int X11Surface::getDepth() const
300 if( maSysData
.pRenderFormat
)
301 return ((XRenderPictFormat
*) maSysData
.pRenderFormat
)->depth
;
306 SurfaceSharedPtr
createSurface( const CairoSurfaceSharedPtr
& rSurface
)
308 return SurfaceSharedPtr(new X11Surface(rSurface
));
311 static X11SysData
getSysData( const Window
& rWindow
)
313 const SystemEnvData
* pSysData
= GetSysData(&rWindow
);
318 return X11SysData(*pSysData
);
321 static X11SysData
getSysData( const VirtualDevice
& rVirDev
)
323 return X11SysData( rVirDev
.GetSystemGfxData() );
326 SurfaceSharedPtr
createSurface( const OutputDevice
& rRefDevice
,
327 int x
, int y
, int width
, int height
)
329 if( rRefDevice
.GetOutDevType() == OUTDEV_WINDOW
)
330 return SurfaceSharedPtr(new X11Surface(getSysData((const Window
&)rRefDevice
),
332 else if( rRefDevice
.GetOutDevType() == OUTDEV_VIRDEV
)
333 return SurfaceSharedPtr(new X11Surface(getSysData((const VirtualDevice
&)rRefDevice
),
336 return SurfaceSharedPtr();
339 SurfaceSharedPtr
createBitmapSurface( const OutputDevice
& rRefDevice
,
340 const BitmapSystemData
& rData
,
343 OSL_TRACE( "requested size: %d x %d available size: %d x %d",
344 rSize
.Width(), rSize
.Height(), rData
.mnWidth
, rData
.mnHeight
);
345 if ( rData
.mnWidth
== rSize
.Width() && rData
.mnHeight
== rSize
.Height() )
347 if( rRefDevice
.GetOutDevType() == OUTDEV_WINDOW
)
348 return SurfaceSharedPtr(new X11Surface(getSysData((const Window
&)rRefDevice
), rData
));
349 else if( rRefDevice
.GetOutDevType() == OUTDEV_VIRDEV
)
350 return SurfaceSharedPtr(new X11Surface(getSysData((const VirtualDevice
&)rRefDevice
), rData
));
353 return SurfaceSharedPtr();