1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
23 #include <rtl/bootstrap.hxx>
24 #include <rtl/ref.hxx>
25 #include <comphelper/processfactory.hxx>
26 #include <cppuhelper/servicefactory.hxx>
27 #include <cppuhelper/bootstrap.hxx>
28 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
29 #include <com/sun/star/lang/XInitialization.hpp>
30 #include <com/sun/star/registry/XSimpleRegistry.hpp>
31 #include <com/sun/star/util/Endianness.hpp>
32 #include <com/sun/star/rendering/ColorComponentTag.hpp>
33 #include <com/sun/star/rendering/ColorSpaceType.hpp>
34 #include <com/sun/star/rendering/RenderingIntent.hpp>
35 #include <com/sun/star/rendering/XIntegerReadOnlyBitmap.hpp>
36 #include <com/sun/star/rendering/XIntegerBitmapColorSpace.hpp>
37 #include <com/sun/star/rendering/XBitmapPalette.hpp>
39 #include <cppuhelper/compbase3.hxx>
41 #include <tools/diagnose_ex.h>
42 #include <tools/extendapplicationenvironment.hxx>
44 #include "vcl/svapp.hxx"
45 #include "vcl/canvastools.hxx"
46 #include "vcl/canvasbitmap.hxx"
47 #include "vcl/dialog.hxx"
48 #include "vcl/outdev.hxx"
49 #include "vcl/bmpacc.hxx"
50 #include "vcl/virdev.hxx"
51 #include "vcl/bitmapex.hxx"
54 using namespace ::com::sun::star
;
55 using namespace ::vcl::unotools
;
57 // -----------------------------------------------------------------------
61 // -----------------------------------------------------------------------
65 tools::extendApplicationEnvironment();
67 uno::Reference
< lang::XMultiServiceFactory
> xMS
;
68 xMS
= cppu::createRegistryServiceFactory(
69 OUString( "applicat.rdb" ),
72 comphelper::setProcessServiceFactory( xMS
);
81 // -----------------------------------------------------------------------
83 namespace com
{ namespace sun
{ namespace star
{ namespace rendering
86 bool operator==( const RGBColor
& rLHS
, const ARGBColor
& rRHS
)
88 return rLHS
.Red
== rRHS
.Red
&& rLHS
.Green
== rRHS
.Green
&& rLHS
.Blue
== rRHS
.Blue
;
90 bool operator==( const ARGBColor
& rLHS
, const RGBColor
& rRHS
)
92 return rLHS
.Red
== rRHS
.Red
&& rLHS
.Green
== rRHS
.Green
&& rLHS
.Blue
== rRHS
.Blue
;
97 //----------------------------------------------------------------------------------
102 class TestApp
: public Application
106 virtual sal_uInt16
Exception( sal_uInt16 nError
);
109 class TestWindow
: public Dialog
112 TestWindow() : Dialog( (Window
*) NULL
)
114 SetText( OUString("CanvasBitmap test harness") );
115 SetSizePixel( Size( 1024, 1024 ) );
120 virtual ~TestWindow() {}
121 virtual void Paint( const Rectangle
& rRect
);
124 //----------------------------------------------------------------------------------
126 static bool g_failure
=false;
128 void test( bool bResult
, const char* msg
)
132 OSL_TRACE("Testing: %s - PASSED", msg
);
137 OSL_TRACE("Testing: %s - FAILED", msg
);
141 //----------------------------------------------------------------------------------
143 bool rangeCheck( const rendering::RGBColor
& rColor
)
145 return rColor
.Red
< 0.0 || rColor
.Red
> 1.0 ||
146 rColor
.Green
< 0.0 || rColor
.Green
> 1.0 ||
147 rColor
.Blue
< 0.0 || rColor
.Blue
> 1.0;
150 //----------------------------------------------------------------------------------
152 void checkCanvasBitmap( const rtl::Reference
<VclCanvasBitmap
>& xBmp
,
156 OSL_TRACE("-------------------------");
157 OSL_TRACE("Testing %s, with depth %d", msg
, nOriginalDepth
);
159 BitmapEx
aContainedBmpEx( xBmp
->getBitmapEx() );
160 Bitmap
aContainedBmp( aContainedBmpEx
.GetBitmap() );
161 int nDepth
= nOriginalDepth
;
164 Bitmap::ScopedReadAccess
pAcc( aContainedBmp
);
165 nDepth
= pAcc
->GetBitCount();
168 test( aContainedBmp
.GetSizePixel() == Size(200,200),
169 "Original bitmap size" );
171 test( xBmp
->getSize().Width
== 200 && xBmp
->getSize().Height
== 200,
172 "Original bitmap size via API" );
174 test( xBmp
->hasAlpha() == aContainedBmpEx
.IsTransparent(),
175 "Correct alpha state" );
177 test( xBmp
->getScaledBitmap( geometry::RealSize2D(500,500), sal_False
).is(),
178 "getScaledBitmap()" );
180 rendering::IntegerBitmapLayout aLayout
;
181 uno::Sequence
<sal_Int8
> aPixelData
= xBmp
->getData(aLayout
, geometry::IntegerRectangle2D(0,0,1,1));
183 const sal_Int32
nExpectedBitsPerPixel(
184 aContainedBmpEx
.IsTransparent() ? std::max(8,nDepth
)+8 : nDepth
);
185 test( aLayout
.ScanLines
== 1,
187 test( aLayout
.ScanLineBytes
== (nExpectedBitsPerPixel
+7)/8,
188 "# scanline bytes" );
189 test( aLayout
.ScanLineStride
== (nExpectedBitsPerPixel
+7)/8 ||
190 aLayout
.ScanLineStride
== -(nExpectedBitsPerPixel
+7)/8,
191 "# scanline stride" );
192 test( aLayout
.PlaneStride
== 0,
195 test( aLayout
.ColorSpace
.is(),
196 "Color space there" );
198 test( aLayout
.Palette
.is() == (nDepth
<= 8),
199 "Palette existance conforms to bitmap" );
201 uno::Sequence
<sal_Int8
> aPixelData2
= xBmp
->getPixel( aLayout
, geometry::IntegerPoint2D(0,0) );
203 test( aPixelData2
.getLength() == aPixelData
.getLength(),
204 "getData and getPixel return same amount of data" );
206 aPixelData
= xBmp
->getData(aLayout
, geometry::IntegerRectangle2D(0,0,200,1));
207 test( aLayout
.ScanLines
== 1,
209 test( aLayout
.ScanLineBytes
== (200*nExpectedBitsPerPixel
+7)/8,
210 "# scanline bytes" );
211 test( aLayout
.ScanLineStride
== (200*nExpectedBitsPerPixel
+7)/8 ||
212 aLayout
.ScanLineStride
== -(200*nExpectedBitsPerPixel
+7)/8,
213 "# scanline stride" );
215 uno::Sequence
< rendering::RGBColor
> aRGBColors
= xBmp
->convertIntegerToRGB( aPixelData
);
216 uno::Sequence
< rendering::ARGBColor
> aARGBColors
= xBmp
->convertIntegerToARGB( aPixelData
);
218 const rendering::RGBColor
* pRGBStart ( aRGBColors
.getConstArray() );
219 const rendering::RGBColor
* pRGBEnd ( aRGBColors
.getConstArray()+aRGBColors
.getLength() );
220 const rendering::ARGBColor
* pARGBStart( aARGBColors
.getConstArray() );
221 std::pair
<const rendering::RGBColor
*,
222 const rendering::ARGBColor
*> aRes
= std::mismatch( pRGBStart
, pRGBEnd
, pARGBStart
);
223 test( aRes
.first
== pRGBEnd
,
224 "argb and rgb colors are equal" );
226 test( std::find_if(pRGBStart
,pRGBEnd
,&rangeCheck
) == pRGBEnd
,
227 "rgb colors are within [0,1] range" );
229 test( pRGBStart
[0].Red
== 1.0 && pRGBStart
[0].Green
== 1.0 && pRGBStart
[0].Blue
== 1.0,
230 "First pixel is white" );
231 test( pARGBStart
[1].Alpha
== 1.0,
232 "Second pixel is opaque" );
233 if( aContainedBmpEx
.IsTransparent() )
235 test( pARGBStart
[0].Alpha
== 0.0,
236 "First pixel is fully transparent" );
239 test( pRGBStart
[1].Red
== 0.0 && pRGBStart
[1].Green
== 0.0 && pRGBStart
[1].Blue
== 0.0,
240 "Second pixel is black" );
242 if( nOriginalDepth
> 8 )
244 const Color
aCol(COL_GREEN
);
245 test( pRGBStart
[5].Red
== vcl::unotools::toDoubleColor(aCol
.GetRed()) &&
246 pRGBStart
[5].Green
== vcl::unotools::toDoubleColor(aCol
.GetGreen()) &&
247 pRGBStart
[5].Blue
== vcl::unotools::toDoubleColor(aCol
.GetBlue()),
248 "Sixth pixel is green" );
250 else if( nDepth
<= 8 )
252 uno::Reference
<rendering::XBitmapPalette
> xPal
= xBmp
->getPalette();
254 "8bit or less: needs palette" );
255 test( xPal
->getNumberOfEntries() == 1L << nOriginalDepth
,
256 "Palette has correct entry count" );
257 uno::Sequence
<double> aIndex
;
258 test( xPal
->setIndex(aIndex
,sal_True
,0) == sal_False
,
259 "Palette is read-only" );
260 test( xPal
->getIndex(aIndex
,0),
261 "Palette entry 0 is opaque" );
262 test( xPal
->getColorSpace().is(),
263 "Palette has a valid color space" );
266 test( pRGBStart
[150].Red
== 1.0 && pRGBStart
[150].Green
== 1.0 && pRGBStart
[150].Blue
== 1.0,
267 "150th pixel is white" );
269 if( nOriginalDepth
> 8 )
271 const uno::Sequence
<sal_Int8
> aComponentTags( xBmp
->getComponentTags() );
272 uno::Sequence
<rendering::ARGBColor
> aARGBColor(1);
273 uno::Sequence
<rendering::RGBColor
> aRGBColor(1);
274 uno::Sequence
<sal_Int8
> aPixel3
, aPixel4
;
276 const Color
aCol(COL_GREEN
);
277 aARGBColor
[0].Red
= vcl::unotools::toDoubleColor(aCol
.GetRed());
278 aARGBColor
[0].Green
= vcl::unotools::toDoubleColor(aCol
.GetGreen());
279 aARGBColor
[0].Blue
= vcl::unotools::toDoubleColor(aCol
.GetBlue());
280 aARGBColor
[0].Alpha
= 1.0;
282 aRGBColor
[0].Red
= vcl::unotools::toDoubleColor(aCol
.GetRed());
283 aRGBColor
[0].Green
= vcl::unotools::toDoubleColor(aCol
.GetGreen());
284 aRGBColor
[0].Blue
= vcl::unotools::toDoubleColor(aCol
.GetBlue());
286 aPixel3
= xBmp
->convertIntegerFromARGB( aARGBColor
);
287 aPixel4
= xBmp
->getPixel( aLayout
, geometry::IntegerPoint2D(5,0) );
288 test( aPixel3
== aPixel4
,
289 "Green pixel from bitmap matches with manually converted green pixel" );
291 if( !aContainedBmpEx
.IsTransparent() )
293 aPixel3
= xBmp
->convertIntegerFromRGB( aRGBColor
);
294 test( aPixel3
== aPixel4
,
295 "Green pixel from bitmap matches with manually RGB-converted green pixel" );
300 //----------------------------------------------------------------------------------
302 void checkBitmapImport( const rtl::Reference
<VclCanvasBitmap
>& xBmp
,
306 OSL_TRACE("-------------------------");
307 OSL_TRACE("Testing %s, with depth %d", msg
, nOriginalDepth
);
309 BitmapEx
aContainedBmpEx( xBmp
->getBitmapEx() );
310 Bitmap
aContainedBmp( aContainedBmpEx
.GetBitmap() );
311 int nDepth
= nOriginalDepth
;
314 Bitmap::ScopedReadAccess
pAcc( aContainedBmp
);
315 nDepth
= pAcc
->GetBitCount();
318 test( aContainedBmp
.GetSizePixel() == Size(200,200),
319 "Original bitmap size" );
321 test( xBmp
->getSize().Width
== 200 && xBmp
->getSize().Height
== 200,
322 "Original bitmap size via API" );
324 test( xBmp
->hasAlpha() == aContainedBmpEx
.IsTransparent(),
325 "Correct alpha state" );
327 test( xBmp
->getScaledBitmap( geometry::RealSize2D(500,500), sal_False
).is(),
328 "getScaledBitmap()" );
330 rendering::IntegerBitmapLayout aLayout
;
331 uno::Sequence
<sal_Int8
> aPixelData
= xBmp
->getData(aLayout
, geometry::IntegerRectangle2D(0,0,1,1));
333 const sal_Int32
nExpectedBitsPerPixel(
334 aContainedBmpEx
.IsTransparent() ? std::max(8,nDepth
)+8 : nDepth
);
335 test( aLayout
.ScanLines
== 1,
337 test( aLayout
.ScanLineBytes
== (nExpectedBitsPerPixel
+7)/8,
338 "# scanline bytes" );
339 test( aLayout
.ScanLineStride
== (nExpectedBitsPerPixel
+7)/8 ||
340 aLayout
.ScanLineStride
== -(nExpectedBitsPerPixel
+7)/8,
341 "# scanline stride" );
342 test( aLayout
.PlaneStride
== 0,
345 test( aLayout
.ColorSpace
.is(),
346 "Color space there" );
348 test( aLayout
.Palette
.is() == (nDepth
<= 8),
349 "Palette existance conforms to bitmap" );
351 uno::Sequence
<sal_Int8
> aPixelData2
= xBmp
->getPixel( aLayout
, geometry::IntegerPoint2D(0,0) );
353 test( aPixelData2
.getLength() == aPixelData
.getLength(),
354 "getData and getPixel return same amount of data" );
356 aPixelData
= xBmp
->getData(aLayout
, geometry::IntegerRectangle2D(0,0,200,1));
357 test( aLayout
.ScanLines
== 1,
359 test( aLayout
.ScanLineBytes
== (200*nExpectedBitsPerPixel
+7)/8,
360 "# scanline bytes" );
361 test( aLayout
.ScanLineStride
== (200*nExpectedBitsPerPixel
+7)/8 ||
362 aLayout
.ScanLineStride
== -(200*nExpectedBitsPerPixel
+7)/8,
363 "# scanline stride" );
365 uno::Sequence
< rendering::RGBColor
> aRGBColors
= xBmp
->convertIntegerToRGB( aPixelData
);
366 uno::Sequence
< rendering::ARGBColor
> aARGBColors
= xBmp
->convertIntegerToARGB( aPixelData
);
368 const rendering::RGBColor
* pRGBStart ( aRGBColors
.getConstArray() );
369 const rendering::RGBColor
* pRGBEnd ( aRGBColors
.getConstArray()+aRGBColors
.getLength() );
370 const rendering::ARGBColor
* pARGBStart( aARGBColors
.getConstArray() );
371 std::pair
<const rendering::RGBColor
*,
372 const rendering::ARGBColor
*> aRes
= std::mismatch( pRGBStart
, pRGBEnd
, pARGBStart
);
373 test( aRes
.first
== pRGBEnd
,
374 "argb and rgb colors are equal" );
376 test( std::find_if(pRGBStart
,pRGBEnd
,&rangeCheck
) == pRGBEnd
,
377 "rgb colors are within [0,1] range" );
379 test( pRGBStart
[0].Red
== 1.0 && pRGBStart
[0].Green
== 1.0 && pRGBStart
[0].Blue
== 1.0,
380 "First pixel is white" );
381 test( pARGBStart
[1].Alpha
== 1.0,
382 "Second pixel is opaque" );
383 if( aContainedBmpEx
.IsTransparent() )
385 test( pARGBStart
[0].Alpha
== 0.0,
386 "First pixel is fully transparent" );
389 test( pRGBStart
[1].Red
== 0.0 && pRGBStart
[1].Green
== 0.0 && pRGBStart
[1].Blue
== 0.0,
390 "Second pixel is black" );
392 if( nOriginalDepth
> 8 )
394 const Color
aCol(COL_GREEN
);
395 test( pRGBStart
[5].Red
== vcl::unotools::toDoubleColor(aCol
.GetRed()) &&
396 pRGBStart
[5].Green
== vcl::unotools::toDoubleColor(aCol
.GetGreen()) &&
397 pRGBStart
[5].Blue
== vcl::unotools::toDoubleColor(aCol
.GetBlue()),
398 "Sixth pixel is green" );
400 else if( nDepth
<= 8 )
402 uno::Reference
<rendering::XBitmapPalette
> xPal
= xBmp
->getPalette();
404 "8bit or less: needs palette" );
405 test( xPal
->getNumberOfEntries() == 1L << nOriginalDepth
,
406 "Palette has correct entry count" );
407 uno::Sequence
<double> aIndex
;
408 test( xPal
->setIndex(aIndex
,sal_True
,0) == sal_False
,
409 "Palette is read-only" );
410 test( xPal
->getIndex(aIndex
,0),
411 "Palette entry 0 is opaque" );
412 test( xPal
->getColorSpace().is(),
413 "Palette has a valid color space" );
416 test( pRGBStart
[150].Red
== 1.0 && pRGBStart
[150].Green
== 1.0 && pRGBStart
[150].Blue
== 1.0,
417 "150th pixel is white" );
419 if( nOriginalDepth
> 8 )
421 const uno::Sequence
<sal_Int8
> aComponentTags( xBmp
->getComponentTags() );
422 uno::Sequence
<rendering::ARGBColor
> aARGBColor(1);
423 uno::Sequence
<rendering::RGBColor
> aRGBColor(1);
424 uno::Sequence
<sal_Int8
> aPixel3
, aPixel4
;
426 const Color
aCol(COL_GREEN
);
427 aARGBColor
[0].Red
= vcl::unotools::toDoubleColor(aCol
.GetRed());
428 aARGBColor
[0].Green
= vcl::unotools::toDoubleColor(aCol
.GetGreen());
429 aARGBColor
[0].Blue
= vcl::unotools::toDoubleColor(aCol
.GetBlue());
430 aARGBColor
[0].Alpha
= 1.0;
432 aRGBColor
[0].Red
= vcl::unotools::toDoubleColor(aCol
.GetRed());
433 aRGBColor
[0].Green
= vcl::unotools::toDoubleColor(aCol
.GetGreen());
434 aRGBColor
[0].Blue
= vcl::unotools::toDoubleColor(aCol
.GetBlue());
436 aPixel3
= xBmp
->convertIntegerFromARGB( aARGBColor
);
437 aPixel4
= xBmp
->getPixel( aLayout
, geometry::IntegerPoint2D(5,0) );
438 test( aPixel3
== aPixel4
,
439 "Green pixel from bitmap matches with manually converted green pixel" );
441 if( !aContainedBmpEx
.IsTransparent() )
443 aPixel3
= xBmp
->convertIntegerFromRGB( aRGBColor
);
444 test( aPixel3
== aPixel4
,
445 "Green pixel from bitmap matches with manually RGB-converted green pixel" );
450 //----------------------------------------------------------------------------------
452 class TestBitmap
: public cppu::WeakImplHelper3
< rendering::XIntegerReadOnlyBitmap
,
453 rendering::XBitmapPalette
,
454 rendering::XIntegerBitmapColorSpace
>
457 geometry::IntegerSize2D maSize
;
458 uno::Sequence
<sal_Int8
> maComponentTags
;
459 uno::Sequence
<sal_Int32
> maComponentBitCounts
;
460 rendering::IntegerBitmapLayout maLayout
;
461 const sal_Int32 mnBitsPerPixel
;
464 virtual geometry::IntegerSize2D SAL_CALL
getSize() throw (uno::RuntimeException
) { return maSize
; }
465 virtual ::sal_Bool SAL_CALL
hasAlpha( ) throw (uno::RuntimeException
) { return mnBitsPerPixel
!= 8; }
466 virtual uno::Reference
< rendering::XBitmap
> SAL_CALL
getScaledBitmap( const geometry::RealSize2D
&,
467 sal_Bool
) throw (uno::RuntimeException
) { return this; }
469 // XIntegerReadOnlyBitmap
470 virtual uno::Sequence
< ::sal_Int8
> SAL_CALL
getData( rendering::IntegerBitmapLayout
& bitmapLayout
,
471 const geometry::IntegerRectangle2D
& rect
) throw (lang::IndexOutOfBoundsException
,
472 rendering::VolatileContentDestroyedException
, uno::RuntimeException
)
474 test( rect
.X1
>= 0, "X1 within bounds" );
475 test( rect
.Y1
>= 0, "Y1 within bounds" );
476 test( rect
.X2
<= maSize
.Width
, "X2 within bounds" );
477 test( rect
.Y2
<= maSize
.Height
, "Y2 within bounds" );
479 bitmapLayout
= getMemoryLayout();
481 const sal_Int32 nWidth
= rect
.X2
-rect
.X1
;
482 const sal_Int32 nHeight
= rect
.Y2
-rect
.Y1
;
483 const sal_Int32 nScanlineLen
= (nWidth
* mnBitsPerPixel
+ 7)/8;
484 uno::Sequence
<sal_Int8
> aRes( nScanlineLen
* nHeight
);
485 sal_Int8
* pOut
= aRes
.getArray();
487 bitmapLayout
.ScanLines
= nHeight
;
488 bitmapLayout
.ScanLineBytes
=
489 bitmapLayout
.ScanLineStride
= nScanlineLen
;
491 if( mnBitsPerPixel
== 8 )
493 for( sal_Int32 y
=0; y
<nHeight
; ++y
)
495 for( sal_Int32 x
=0; x
<nWidth
; ++x
)
496 pOut
[ y
*nScanlineLen
+ x
] = sal_Int8(x
);
501 for( sal_Int32 y
=0; y
<nHeight
; ++y
)
503 for( sal_Int32 x
=0; x
<nWidth
; ++x
)
505 pOut
[ y
*nScanlineLen
+ 4*x
] = sal_Int8(rect
.X1
);
506 pOut
[ y
*nScanlineLen
+ 4*x
+ 1 ] = sal_Int8(rect
.Y2
);
507 pOut
[ y
*nScanlineLen
+ 4*x
+ 2 ] = sal_Int8(x
);
508 pOut
[ y
*nScanlineLen
+ 4*x
+ 3 ] = sal_Int8(rect
.Y1
);
516 virtual uno::Sequence
< ::sal_Int8
> SAL_CALL
getPixel( rendering::IntegerBitmapLayout
&,
517 const geometry::IntegerPoint2D
& ) throw (lang::IndexOutOfBoundsException
,
518 rendering::VolatileContentDestroyedException
, uno::RuntimeException
)
520 test(false, "Method not implemented");
521 return uno::Sequence
< sal_Int8
>();
524 virtual uno::Reference
< rendering::XBitmapPalette
> SAL_CALL
getPalette( ) throw (uno::RuntimeException
)
526 uno::Reference
< XBitmapPalette
> aRet
;
527 if( mnBitsPerPixel
== 8 )
532 virtual rendering::IntegerBitmapLayout SAL_CALL
getMemoryLayout( ) throw (uno::RuntimeException
)
534 rendering::IntegerBitmapLayout
aLayout( maLayout
);
536 const sal_Int32 nScanlineLen
= (maSize
.Width
* mnBitsPerPixel
+ 7)/8;
538 aLayout
.ScanLines
= maSize
.Height
;
539 aLayout
.ScanLineBytes
=
540 aLayout
.ScanLineStride
= nScanlineLen
;
541 aLayout
.Palette
= getPalette();
542 aLayout
.ColorSpace
.set( this );
548 virtual sal_Int32 SAL_CALL
getNumberOfEntries() throw (uno::RuntimeException
)
550 test( getPalette().is(),
551 "Got palette interface call without handing out palette?!" );
556 virtual ::sal_Bool SAL_CALL
getIndex( uno::Sequence
< double >& entry
,
557 ::sal_Int32 nIndex
) throw (lang::IndexOutOfBoundsException
,
558 uno::RuntimeException
)
560 test( getPalette().is(),
561 "Got palette interface call without handing out palette?!" );
562 test( nIndex
>= 0 && nIndex
< 256,
563 "Index out of range" );
564 entry
= colorToStdColorSpaceSequence(
569 return sal_True
; // no palette transparency here.
572 virtual ::sal_Bool SAL_CALL
setIndex( const uno::Sequence
< double >&,
574 ::sal_Int32 nIndex
) throw (lang::IndexOutOfBoundsException
,
575 lang::IllegalArgumentException
,
576 uno::RuntimeException
)
578 test( getPalette().is(),
579 "Got palette interface call without handing out palette?!" );
580 test( nIndex
>= 0 && nIndex
< 256,
581 "Index out of range" );
585 struct PaletteColorSpaceHolder
: public rtl::StaticWithInit
<uno::Reference
<rendering::XColorSpace
>,
586 PaletteColorSpaceHolder
>
588 uno::Reference
<rendering::XColorSpace
> operator()()
590 return vcl::unotools::createStandardColorSpace();
594 virtual uno::Reference
< rendering::XColorSpace
> SAL_CALL
getColorSpace( ) throw (uno::RuntimeException
)
596 // this is the method from XBitmapPalette. Return palette color
598 return PaletteColorSpaceHolder::get();
601 // XIntegerBitmapColorSpace
602 virtual ::sal_Int8 SAL_CALL
getType( ) throw (uno::RuntimeException
)
604 return rendering::ColorSpaceType::RGB
;
607 virtual uno::Sequence
< sal_Int8
> SAL_CALL
getComponentTags( ) throw (uno::RuntimeException
)
609 return maComponentTags
;
612 virtual ::sal_Int8 SAL_CALL
getRenderingIntent( ) throw (uno::RuntimeException
)
614 return rendering::RenderingIntent::PERCEPTUAL
;
617 virtual uno::Sequence
< beans::PropertyValue
> SAL_CALL
getProperties( ) throw (uno::RuntimeException
)
619 test(false, "Method not implemented");
620 return uno::Sequence
< ::beans::PropertyValue
>();
623 virtual uno::Sequence
< double > SAL_CALL
convertColorSpace( const uno::Sequence
< double >&,
624 const uno::Reference
< rendering::XColorSpace
>& ) throw (uno::RuntimeException
)
626 test(false, "Method not implemented");
627 return uno::Sequence
< double >();
630 virtual uno::Sequence
< rendering::RGBColor
> SAL_CALL
convertToRGB( const uno::Sequence
< double >& ) throw (lang::IllegalArgumentException
,
631 uno::RuntimeException
)
633 test(false, "Method not implemented");
634 return uno::Sequence
< rendering::RGBColor
>();
637 virtual uno::Sequence
< rendering::ARGBColor
> SAL_CALL
convertToARGB( const uno::Sequence
< double >& ) throw (lang::IllegalArgumentException
,
638 uno::RuntimeException
)
640 test(false, "Method not implemented");
641 return uno::Sequence
< rendering::ARGBColor
>();
644 virtual uno::Sequence
< rendering::ARGBColor
> SAL_CALL
convertToPARGB( const uno::Sequence
< double >& ) throw (lang::IllegalArgumentException
,
645 uno::RuntimeException
)
647 test(false, "Method not implemented");
648 return uno::Sequence
< rendering::ARGBColor
>();
651 virtual uno::Sequence
< double > SAL_CALL
convertFromRGB( const uno::Sequence
< rendering::RGBColor
>& ) throw (lang::IllegalArgumentException
,
652 uno::RuntimeException
)
654 test(false, "Method not implemented");
655 return uno::Sequence
< double >();
658 virtual uno::Sequence
< double > SAL_CALL
convertFromARGB( const uno::Sequence
< rendering::ARGBColor
>& ) throw (lang::IllegalArgumentException
,
659 uno::RuntimeException
)
661 test(false, "This method is not expected to be called!");
662 return uno::Sequence
< double >();
665 virtual uno::Sequence
< double > SAL_CALL
convertFromPARGB( const uno::Sequence
< rendering::ARGBColor
>& ) throw (lang::IllegalArgumentException
,
666 uno::RuntimeException
)
668 test(false, "This method is not expected to be called!");
669 return uno::Sequence
< double >();
672 virtual ::sal_Int32 SAL_CALL
getBitsPerPixel( ) throw (uno::RuntimeException
)
674 return mnBitsPerPixel
;
677 virtual uno::Sequence
< ::sal_Int32
> SAL_CALL
getComponentBitCounts( ) throw (uno::RuntimeException
)
679 return maComponentBitCounts
;
682 virtual ::sal_Int8 SAL_CALL
getEndianness( ) throw (uno::RuntimeException
)
684 return util::Endianness::LITTLE
;
687 virtual uno::Sequence
< double > SAL_CALL
convertFromIntegerColorSpace( const uno::Sequence
< ::sal_Int8
>& ,
688 const uno::Reference
< rendering::XColorSpace
>& ) throw (lang::IllegalArgumentException
,
689 uno::RuntimeException
)
691 test(false, "Method not implemented");
692 return uno::Sequence
< double >();
695 virtual uno::Sequence
< ::sal_Int8
> SAL_CALL
convertToIntegerColorSpace( const uno::Sequence
< ::sal_Int8
>& ,
696 const uno::Reference
< rendering::XIntegerBitmapColorSpace
>& ) throw (lang::IllegalArgumentException
,
697 uno::RuntimeException
)
699 test(false, "Method not implemented");
700 return uno::Sequence
< sal_Int8
>();
703 virtual uno::Sequence
< rendering::RGBColor
> SAL_CALL
convertIntegerToRGB( const uno::Sequence
< ::sal_Int8
>& deviceColor
) throw (lang::IllegalArgumentException
,
704 uno::RuntimeException
)
706 const uno::Sequence
< rendering::ARGBColor
> aTemp( convertIntegerToARGB(deviceColor
) );
707 const sal_Size
nLen(aTemp
.getLength());
708 uno::Sequence
< rendering::RGBColor
> aRes( nLen
);
709 rendering::RGBColor
* pOut
= aRes
.getArray();
710 for( sal_Size i
=0; i
<nLen
; ++i
)
712 *pOut
++ = rendering::RGBColor(aTemp
[i
].Red
,
720 virtual uno::Sequence
< rendering::ARGBColor
> SAL_CALL
convertIntegerToARGB( const uno::Sequence
< ::sal_Int8
>& deviceColor
) throw (lang::IllegalArgumentException
,
721 uno::RuntimeException
)
723 const sal_Size
nLen( deviceColor
.getLength() );
724 const sal_Int32
nBytesPerPixel(mnBitsPerPixel
== 8 ? 1 : 4);
725 test(nLen
%nBytesPerPixel
==0,
726 "number of channels no multiple of pixel element count");
728 uno::Sequence
< rendering::ARGBColor
> aRes( nLen
/ nBytesPerPixel
);
729 rendering::ARGBColor
* pOut( aRes
.getArray() );
731 if( getPalette().is() )
733 for( sal_Size i
=0; i
<nLen
; ++i
)
735 *pOut
++ = rendering::ARGBColor(
737 vcl::unotools::toDoubleColor(deviceColor
[i
]),
738 vcl::unotools::toDoubleColor(deviceColor
[i
]),
739 vcl::unotools::toDoubleColor(deviceColor
[i
]));
744 for( sal_Size i
=0; i
<nLen
; i
+=4 )
746 *pOut
++ = rendering::ARGBColor(
747 vcl::unotools::toDoubleColor(deviceColor
[i
+3]),
748 vcl::unotools::toDoubleColor(deviceColor
[i
+0]),
749 vcl::unotools::toDoubleColor(deviceColor
[i
+1]),
750 vcl::unotools::toDoubleColor(deviceColor
[i
+2]));
757 virtual uno::Sequence
< rendering::ARGBColor
> SAL_CALL
convertIntegerToPARGB( const uno::Sequence
< ::sal_Int8
>& deviceColor
) throw (lang::IllegalArgumentException
,
758 uno::RuntimeException
)
760 const sal_Size
nLen( deviceColor
.getLength() );
761 const sal_Int32
nBytesPerPixel(mnBitsPerPixel
== 8 ? 1 : 4);
762 test(nLen
%nBytesPerPixel
==0,
763 "number of channels no multiple of pixel element count");
765 uno::Sequence
< rendering::ARGBColor
> aRes( nLen
/ nBytesPerPixel
);
766 rendering::ARGBColor
* pOut( aRes
.getArray() );
768 if( getPalette().is() )
770 for( sal_Size i
=0; i
<nLen
; ++i
)
772 *pOut
++ = rendering::ARGBColor(
774 vcl::unotools::toDoubleColor(deviceColor
[i
]),
775 vcl::unotools::toDoubleColor(deviceColor
[i
]),
776 vcl::unotools::toDoubleColor(deviceColor
[i
]));
781 for( sal_Size i
=0; i
<nLen
; i
+=4 )
783 const double fAlpha
=vcl::unotools::toDoubleColor(deviceColor
[i
+3]);
784 *pOut
++ = rendering::ARGBColor(
786 fAlpha
*vcl::unotools::toDoubleColor(deviceColor
[i
+0]),
787 fAlpha
*vcl::unotools::toDoubleColor(deviceColor
[i
+1]),
788 fAlpha
*vcl::unotools::toDoubleColor(deviceColor
[i
+2]));
795 virtual uno::Sequence
< ::sal_Int8
> SAL_CALL
convertIntegerFromRGB( const uno::Sequence
< rendering::RGBColor
>& ) throw (lang::IllegalArgumentException
,
796 uno::RuntimeException
)
798 test(false, "Method not implemented");
799 return uno::Sequence
< sal_Int8
>();
802 virtual uno::Sequence
< ::sal_Int8
> SAL_CALL
convertIntegerFromARGB( const uno::Sequence
< rendering::ARGBColor
>& ) throw (lang::IllegalArgumentException
,
803 uno::RuntimeException
)
805 test(false, "Method not implemented");
806 return uno::Sequence
< sal_Int8
>();
809 virtual uno::Sequence
< ::sal_Int8
> SAL_CALL
convertIntegerFromPARGB( const uno::Sequence
< rendering::ARGBColor
>& ) throw (lang::IllegalArgumentException
,
810 uno::RuntimeException
)
812 test(false, "Method not implemented");
813 return uno::Sequence
< sal_Int8
>();
817 TestBitmap( const geometry::IntegerSize2D
& rSize
, bool bPalette
) :
820 maComponentBitCounts(),
822 mnBitsPerPixel( bPalette
? 8 : 32 )
826 maComponentTags
.realloc(1);
827 maComponentTags
[0] = rendering::ColorComponentTag::INDEX
;
829 maComponentBitCounts
.realloc(1);
830 maComponentBitCounts
[0] = 8;
834 maComponentTags
.realloc(4);
835 sal_Int8
* pTags
= maComponentTags
.getArray();
836 pTags
[0] = rendering::ColorComponentTag::RGB_BLUE
;
837 pTags
[1] = rendering::ColorComponentTag::RGB_GREEN
;
838 pTags
[2] = rendering::ColorComponentTag::RGB_RED
;
839 pTags
[3] = rendering::ColorComponentTag::ALPHA
;
841 maComponentBitCounts
.realloc(4);
842 sal_Int32
* pCounts
= maComponentBitCounts
.getArray();
849 maLayout
.ScanLines
= 0;
850 maLayout
.ScanLineBytes
= 0;
851 maLayout
.ScanLineStride
= 0;
852 maLayout
.PlaneStride
= 0;
853 maLayout
.ColorSpace
.clear();
854 maLayout
.Palette
.clear();
855 maLayout
.IsMsbFirst
= sal_False
;
860 //----------------------------------------------------------------------------------
862 void TestWindow::Paint( const Rectangle
& )
864 static sal_Int8 lcl_depths
[]={1,4,8,16,24};
868 // Testing VclCanvasBitmap wrapper
869 // ===============================
871 for( unsigned int i
=0; i
<SAL_N_ELEMENTS(lcl_depths
); ++i
)
873 const sal_Int8
nDepth( lcl_depths
[i
] );
874 Bitmap
aBitmap(Size(200,200),nDepth
);
875 aBitmap
.Erase(COL_WHITE
);
877 Bitmap::ScopedWriteAccess
pAcc(aBitmap
);
880 BitmapColor
aBlack(0);
881 BitmapColor
aWhite(0);
882 if( pAcc
->HasPalette() )
884 aBlack
.SetIndex( sal::static_int_cast
<BYTE
>(pAcc
->GetBestPaletteIndex(BitmapColor(0,0,0))) );
885 aWhite
.SetIndex( sal::static_int_cast
<BYTE
>(pAcc
->GetBestPaletteIndex(BitmapColor(255,255,255))) );
889 aBlack
= Color(COL_BLACK
);
890 aWhite
= Color(COL_WHITE
);
892 pAcc
->SetFillColor(COL_GREEN
);
893 pAcc
->FillRect(Rectangle(0,0,100,100));
894 pAcc
->SetPixel(0,0,aWhite
);
895 pAcc
->SetPixel(0,1,aBlack
);
896 pAcc
->SetPixel(0,2,aWhite
);
900 rtl::Reference
<VclCanvasBitmap
> xBmp( new VclCanvasBitmap(aBitmap
) );
902 checkCanvasBitmap( xBmp
, "single bitmap", nDepth
);
904 Bitmap
aMask(Size(200,200),1);
905 aMask
.Erase(COL_WHITE
);
907 Bitmap::ScopedWriteAccess
pAcc(aMask
);
910 pAcc
->SetFillColor(COL_BLACK
);
911 pAcc
->FillRect(Rectangle(0,0,100,100));
912 pAcc
->SetPixel(0,0,BitmapColor(1));
913 pAcc
->SetPixel(0,1,BitmapColor(0));
914 pAcc
->SetPixel(0,2,BitmapColor(1));
918 xBmp
.set( new VclCanvasBitmap(BitmapEx(aBitmap
,aMask
)) );
920 checkCanvasBitmap( xBmp
, "masked bitmap", nDepth
);
922 AlphaMask
aAlpha(Size(200,200));
925 BitmapWriteAccess
* pAcc
= aAlpha
.AcquireWriteAccess();
928 pAcc
->SetFillColor(COL_BLACK
);
929 pAcc
->FillRect(Rectangle(0,0,100,100));
930 pAcc
->SetPixel(0,0,BitmapColor(255));
931 pAcc
->SetPixel(0,1,BitmapColor(0));
932 pAcc
->SetPixel(0,2,BitmapColor(255));
933 aAlpha
.ReleaseAccess(pAcc
);
937 xBmp
.set( new VclCanvasBitmap(BitmapEx(aBitmap
,aAlpha
)) );
939 checkCanvasBitmap( xBmp
, "alpha bitmap", nDepth
);
942 // Testing XBitmap import
943 // ======================
944 uno::Reference
< rendering::XIntegerReadOnlyBitmap
> xTestBmp(
945 new TestBitmap( geometry::IntegerSize2D(10,10), true ));
947 BitmapEx aBmp
= vcl::unotools::bitmapExFromXBitmap(xTestBmp
);
948 test( aBmp
.IsTransparent() == false,
949 "Palette bitmap is not transparent" );
950 test( aBmp
.GetSizePixel() == Size(10,10),
951 "Bitmap has size (10,10)" );
952 test( aBmp
.GetBitCount() == 8,
953 "Bitmap has bitcount of 8" );
955 BitmapReadAccess
* pBmpAcc
= aBmp
.GetBitmap().AcquireReadAccess();
958 "Bitmap has valid BitmapReadAccess" );
960 test(pBmpAcc
->GetPixel(0,0) == BitmapColor(0),
961 "(0,0) correct content");
962 test(pBmpAcc
->GetPixel(2,2) == BitmapColor(2),
963 "(2,2) correct content");
964 test(pBmpAcc
->GetPixel(2,9) == BitmapColor(9),
965 "(9,2) correct content");
967 aBmp
.GetBitmap().ReleaseAccess(pBmpAcc
);
970 xTestBmp
.set( new TestBitmap( geometry::IntegerSize2D(10,10), false ));
972 aBmp
= vcl::unotools::bitmapExFromXBitmap(xTestBmp
);
973 test( aBmp
.IsTransparent() == TRUE
,
974 "Palette bitmap is transparent" );
975 test( aBmp
.IsAlpha() == TRUE
,
976 "Palette bitmap has alpha" );
977 test( aBmp
.GetSizePixel() == Size(10,10),
978 "Bitmap has size (10,10)" );
979 test( aBmp
.GetBitCount() == 24,
980 "Bitmap has bitcount of 24" );
982 BitmapReadAccess
* pBmpAcc
= aBmp
.GetBitmap().AcquireReadAccess();
983 BitmapReadAccess
* pAlphaAcc
= aBmp
.GetAlpha().AcquireReadAccess();
986 "Bitmap has valid BitmapReadAccess" );
988 "Bitmap has valid alpha BitmapReadAccess" );
990 test(pBmpAcc
->GetPixel(0,0) == BitmapColor(0,1,0),
991 "(0,0) correct content");
992 test(pAlphaAcc
->GetPixel(0,0) == BitmapColor(255),
993 "(0,0) correct alpha content");
994 test(pBmpAcc
->GetPixel(2,2) == BitmapColor(0,3,2),
995 "(2,2) correct content");
996 test(pAlphaAcc
->GetPixel(2,2) == BitmapColor(253),
997 "(2,2) correct alpha content");
998 test(pBmpAcc
->GetPixel(2,9) == BitmapColor(0,3,9),
999 "(9,2) correct content");
1000 test(pAlphaAcc
->GetPixel(2,9) == BitmapColor(253),
1001 "(9,2) correct alpha content");
1003 aBmp
.GetAlpha().ReleaseAccess(pAlphaAcc
);
1004 aBmp
.GetBitmap().ReleaseAccess(pBmpAcc
);
1007 catch( uno::Exception
& )
1009 DBG_UNHANDLED_EXCEPTION();
1012 catch( std::exception
& )
1014 OSL_TRACE( "Caught std exception!" );
1027 aWindow
.SetText( OUString( "VCL - canvasbitmaptest" ) );
1029 Application::Execute();
1032 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */