diff options
author | Tomaž Vajngerl <tomaz.vajngerl@collabora.co.uk> | 2021-02-14 21:29:45 +0900 |
---|---|---|
committer | Tomaž Vajngerl <quikee@gmail.com> | 2021-02-17 02:43:18 +0100 |
commit | 246af1d40ec515fe31ef2ac3375401c3fe284157 (patch) | |
tree | e88dd7c878a6fcfe142ebc4b291a50de4e438642 /filter | |
parent | 3885ef7df0e2a648579100e338920054dbadf6e2 (diff) |
Move TGA reader from filter module into VCL
Change-Id: I0fea5d6e75c6bfd05ea91ed7b92aaacfcc5ec177
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/111010
Tested-by: Jenkins
Reviewed-by: Tomaž Vajngerl <quikee@gmail.com>
Diffstat (limited to 'filter')
-rw-r--r-- | filter/CppunitTest_filter_tga_test.mk | 38 | ||||
-rw-r--r-- | filter/Library_gie.mk | 1 | ||||
-rw-r--r-- | filter/Module_filter.mk | 1 | ||||
-rw-r--r-- | filter/qa/cppunit/data/tga/fail/.gitignore | 0 | ||||
-rw-r--r-- | filter/qa/cppunit/data/tga/fail/CVE-2012-3755-1.tga | bin | 1440044 -> 0 bytes | |||
-rw-r--r-- | filter/qa/cppunit/data/tga/indeterminate/.gitignore | 1 | ||||
-rw-r--r-- | filter/qa/cppunit/data/tga/pass/.gitignore | 0 | ||||
-rw-r--r-- | filter/qa/cppunit/data/tga/pass/fdo14924-5.tga | bin | 2005 -> 0 bytes | |||
-rw-r--r-- | filter/qa/cppunit/data/tga/pass/fdo14924-6.tga | bin | 3171 -> 0 bytes | |||
-rw-r--r-- | filter/qa/cppunit/filters-tga-test.cxx | 67 | ||||
-rw-r--r-- | filter/source/config/fragments/internalgraphicfilters/tga_Import.xcu | 21 | ||||
-rw-r--r-- | filter/source/graphicfilter/itga/itga.cxx | 791 |
12 files changed, 11 insertions, 909 deletions
diff --git a/filter/CppunitTest_filter_tga_test.mk b/filter/CppunitTest_filter_tga_test.mk deleted file mode 100644 index 33ae034c0e30..000000000000 --- a/filter/CppunitTest_filter_tga_test.mk +++ /dev/null @@ -1,38 +0,0 @@ -# -*- Mode: makefile-gmake; tab-width: 4; indent-tabs-mode: t -*- -# -# This file is part of the LibreOffice project. -# -# This Source Code Form is subject to the terms of the Mozilla Public -# License, v. 2.0. If a copy of the MPL was not distributed with this -# file, You can obtain one at http://mozilla.org/MPL/2.0/. -# - -$(eval $(call gb_CppunitTest_CppunitTest,filter_tga_test)) - -$(eval $(call gb_CppunitTest_use_external,filter_tga_test,boost_headers)) - -$(eval $(call gb_CppunitTest_add_exception_objects,filter_tga_test, \ - filter/qa/cppunit/filters-tga-test \ -)) - -$(eval $(call gb_CppunitTest_use_libraries,filter_tga_test, \ - gie \ - sal \ - test \ - tl \ - unotest \ - vcl \ -)) - -$(eval $(call gb_CppunitTest_use_sdk_api,filter_tga_test)) - -$(eval $(call gb_CppunitTest_use_ure,filter_tga_test)) -$(eval $(call gb_CppunitTest_use_vcl,filter_tga_test)) - -$(eval $(call gb_CppunitTest_use_components,filter_tga_test,\ - configmgr/source/configmgr \ -)) - -$(eval $(call gb_CppunitTest_use_configuration,filter_tga_test)) - -# vim: set noet sw=4 ts=4: diff --git a/filter/Library_gie.mk b/filter/Library_gie.mk index 8c0cbd46b9b9..be60d68e3de7 100644 --- a/filter/Library_gie.mk +++ b/filter/Library_gie.mk @@ -56,7 +56,6 @@ $(eval $(call gb_Library_add_exception_objects,gie,\ filter/source/graphicfilter/ipict/shape \ filter/source/graphicfilter/ipcx/ipcx \ filter/source/graphicfilter/iras/iras \ - filter/source/graphicfilter/itga/itga \ filter/source/graphicfilter/ieps/ieps \ filter/source/graphicfilter/ipsd/ipsd \ filter/source/graphicfilter/ipbm/ipbm \ diff --git a/filter/Module_filter.mk b/filter/Module_filter.mk index 898ac710db8a..a998c65b60ab 100644 --- a/filter/Module_filter.mk +++ b/filter/Module_filter.mk @@ -64,7 +64,6 @@ $(eval $(call gb_Module_add_check_targets,filter,\ CppunitTest_filter_ppm_test \ CppunitTest_filter_psd_test \ CppunitTest_filter_ras_test \ - CppunitTest_filter_tga_test \ CppunitTest_filter_svg \ )) endif diff --git a/filter/qa/cppunit/data/tga/fail/.gitignore b/filter/qa/cppunit/data/tga/fail/.gitignore deleted file mode 100644 index e69de29bb2d1..000000000000 --- a/filter/qa/cppunit/data/tga/fail/.gitignore +++ /dev/null diff --git a/filter/qa/cppunit/data/tga/fail/CVE-2012-3755-1.tga b/filter/qa/cppunit/data/tga/fail/CVE-2012-3755-1.tga Binary files differdeleted file mode 100644 index 963e5d3aedc3..000000000000 --- a/filter/qa/cppunit/data/tga/fail/CVE-2012-3755-1.tga +++ /dev/null diff --git a/filter/qa/cppunit/data/tga/indeterminate/.gitignore b/filter/qa/cppunit/data/tga/indeterminate/.gitignore deleted file mode 100644 index 38bf024a9b53..000000000000 --- a/filter/qa/cppunit/data/tga/indeterminate/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.tga-* diff --git a/filter/qa/cppunit/data/tga/pass/.gitignore b/filter/qa/cppunit/data/tga/pass/.gitignore deleted file mode 100644 index e69de29bb2d1..000000000000 --- a/filter/qa/cppunit/data/tga/pass/.gitignore +++ /dev/null diff --git a/filter/qa/cppunit/data/tga/pass/fdo14924-5.tga b/filter/qa/cppunit/data/tga/pass/fdo14924-5.tga Binary files differdeleted file mode 100644 index c3b38f313f82..000000000000 --- a/filter/qa/cppunit/data/tga/pass/fdo14924-5.tga +++ /dev/null diff --git a/filter/qa/cppunit/data/tga/pass/fdo14924-6.tga b/filter/qa/cppunit/data/tga/pass/fdo14924-6.tga Binary files differdeleted file mode 100644 index 92b720053702..000000000000 --- a/filter/qa/cppunit/data/tga/pass/fdo14924-6.tga +++ /dev/null diff --git a/filter/qa/cppunit/filters-tga-test.cxx b/filter/qa/cppunit/filters-tga-test.cxx deleted file mode 100644 index c87216803120..000000000000 --- a/filter/qa/cppunit/filters-tga-test.cxx +++ /dev/null @@ -1,67 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - */ - -#include <unotest/filters-test.hxx> -#include <test/bootstrapfixture.hxx> -#include <vcl/FilterConfigItem.hxx> -#include <tools/stream.hxx> -#include <vcl/graph.hxx> - -extern "C" -{ - SAL_DLLPUBLIC_EXPORT bool SAL_CALL - itgGraphicImport(SvStream & rStream, Graphic & rGraphic, - FilterConfigItem*); -} - -using namespace ::com::sun::star; - -/* Implementation of Filters test */ - -class TgaFilterTest - : public test::FiltersTest - , public test::BootstrapFixture -{ -public: - TgaFilterTest() : BootstrapFixture(true, false) {} - - virtual bool load(const OUString &, - const OUString &rURL, const OUString &, - SfxFilterFlags, SotClipboardFormatId, unsigned int) override; - - /** - * Ensure CVEs remain unbroken - */ - void testCVEs(); - - CPPUNIT_TEST_SUITE(TgaFilterTest); - CPPUNIT_TEST(testCVEs); - CPPUNIT_TEST_SUITE_END(); -}; - -bool TgaFilterTest::load(const OUString &, - const OUString &rURL, const OUString &, - SfxFilterFlags, SotClipboardFormatId, unsigned int) -{ - SvFileStream aFileStream(rURL, StreamMode::READ); - Graphic aGraphic; - return itgGraphicImport(aFileStream, aGraphic, nullptr); -} - -void TgaFilterTest::testCVEs() -{ - testDir(OUString(), - m_directories.getURLFromSrc(u"/filter/qa/cppunit/data/tga/")); -} - -CPPUNIT_TEST_SUITE_REGISTRATION(TgaFilterTest); - -CPPUNIT_PLUGIN_IMPLEMENT(); - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/filter/source/config/fragments/internalgraphicfilters/tga_Import.xcu b/filter/source/config/fragments/internalgraphicfilters/tga_Import.xcu index 7ea4d49ec624..922cdefbf1ab 100644 --- a/filter/source/config/fragments/internalgraphicfilters/tga_Import.xcu +++ b/filter/source/config/fragments/internalgraphicfilters/tga_Import.xcu @@ -15,13 +15,14 @@ * except in compliance with the License. You may obtain a copy of * the License at http://www.apache.org/licenses/LICENSE-2.0 . --> - <node oor:name="tga_Import" oor:op="replace" > - <prop oor:name="Type"><value>tga_Truevision_TARGA</value></prop> - <prop oor:name="FormatName"><value>itg</value></prop> - <prop oor:name="RealFilterName"><value>TGA - Truevision TARGA</value></prop> - <prop oor:name="UIComponent"/> - <prop oor:name="UIName"> - <value xml:lang="en-US">TGA - Truevision Targa</value> - </prop> - <prop oor:name="Flags"><value>IMPORT</value></prop> - </node> + +<node oor:name="tga_Import" oor:op="replace" > + <prop oor:name="Type"><value>tga_Truevision_TARGA</value></prop> + <prop oor:name="FormatName"><value>SVTGA</value></prop> + <prop oor:name="RealFilterName"><value>TGA - Truevision TARGA</value></prop> + <prop oor:name="UIComponent"/> + <prop oor:name="UIName"> + <value xml:lang="en-US">TGA - Truevision Targa</value> + </prop> + <prop oor:name="Flags"><value>IMPORT</value></prop> +</node> diff --git a/filter/source/graphicfilter/itga/itga.cxx b/filter/source/graphicfilter/itga/itga.cxx deleted file mode 100644 index 8c8af9d52cd8..000000000000 --- a/filter/source/graphicfilter/itga/itga.cxx +++ /dev/null @@ -1,791 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - - -#include <vcl/graph.hxx> -#include <vcl/BitmapTools.hxx> -#include <tools/stream.hxx> -#include <memory> - -class FilterConfigItem; - -//============================ TGAReader ================================== - -namespace { - -struct TGAFileHeader -{ - sal_uInt8 nImageIDLength; - sal_uInt8 nColorMapType; - sal_uInt8 nImageType; - sal_uInt16 nColorMapFirstEntryIndex; - sal_uInt16 nColorMapLength; - sal_uInt8 nColorMapEntrySize; - sal_uInt16 nColorMapXOrigin; - sal_uInt16 nColorMapYOrigin; - sal_uInt16 nImageWidth; - sal_uInt16 nImageHeight; - sal_uInt8 nPixelDepth; - sal_uInt8 nImageDescriptor; -}; - -#define SizeOfTGAFileFooter 26 - -struct TGAFileFooter -{ - sal_uInt32 nExtensionFileOffset; - sal_uInt32 nDeveloperDirectoryOffset; - sal_uInt32 nSignature[4]; - sal_uInt8 nPadByte; - sal_uInt8 nStringTerminator; -}; - -#define SizeOfTGAExtension 495 - -struct TGAExtension -{ - sal_uInt16 nExtensionSize; - char sAuthorName[41]; - char sAuthorComment[324]; - char sDateTimeStamp[12]; - char sJobNameID[41]; - char sSoftwareID[41]; - sal_uInt16 nSoftwareVersionNumber; - sal_uInt8 nSoftwareVersionLetter; - sal_uInt32 nKeyColor; - sal_uInt16 nPixelAspectRatioNumerator; - sal_uInt16 nPixelAspectRatioDeNumerator; - sal_uInt16 nGammaValueNumerator; - sal_uInt16 nGammaValueDeNumerator; - sal_uInt32 nColorCorrectionOffset; - sal_uInt32 nPostageStampOffset; - sal_uInt32 nScanLineOffset; - sal_uInt8 nAttributesType; -}; - -class TGAReader { - -private: - - SvStream& m_rTGA; - - std::unique_ptr<vcl::bitmap::RawBitmap> mpBitmap; - std::vector<Color> mvPalette; - std::unique_ptr<TGAFileHeader> - mpFileHeader; - std::unique_ptr<TGAFileFooter> - mpFileFooter; - std::unique_ptr<TGAExtension> - mpExtension; - std::unique_ptr<sal_uInt32[]> - mpColorMap; - - bool mbStatus; - - sal_uInt8 mnTGAVersion; // Enhanced TGA is defined as Version 2.0 - sal_uInt16 mnDestBitDepth; - bool mbIndexing; // sal_True if source contains indexing color values - bool mbEncoding; // sal_True if source is compressed - - bool ImplReadHeader(); - bool ImplReadPalette(); - bool ImplReadBody(); - -public: - explicit TGAReader(SvStream &rTGA); - bool ReadTGA(Graphic &rGraphic); -}; - -} - -//=================== Methods of TGAReader ============================== - -TGAReader::TGAReader(SvStream &rTGA) - : m_rTGA(rTGA) - , mbStatus(true) - , mnTGAVersion(1) - , mnDestBitDepth(8) - , mbIndexing(false) - , mbEncoding(false) -{ -} - -bool TGAReader::ReadTGA(Graphic & rGraphic) -{ - if ( m_rTGA.GetError() ) - return false; - - m_rTGA.SetEndian( SvStreamEndian::LITTLE ); - - // Kopf einlesen: - - if ( !m_rTGA.GetError() ) - { - mbStatus = ImplReadHeader(); - if (mbStatus) - mbStatus = mpFileHeader->nImageWidth && mpFileHeader->nImageHeight; - if (mbStatus) - { - sal_Size nSize = mpFileHeader->nImageWidth; - nSize *= mpFileHeader->nImageHeight; - if (nSize > SAL_MAX_INT32/2/3) - return false; - - mpBitmap.reset( new vcl::bitmap::RawBitmap( Size( mpFileHeader->nImageWidth, mpFileHeader->nImageHeight ), 24 ) ); - if ( mbIndexing ) - mbStatus = ImplReadPalette(); - if ( mbStatus ) - mbStatus = ImplReadBody(); - - if ( mbStatus ) - rGraphic = vcl::bitmap::CreateFromData(std::move(*mpBitmap)); - } - } - return mbStatus; -} - - -bool TGAReader::ImplReadHeader() -{ - mpFileHeader.reset( new TGAFileHeader ); - - m_rTGA.ReadUChar( mpFileHeader->nImageIDLength ).ReadUChar( mpFileHeader->nColorMapType ).ReadUChar( mpFileHeader->nImageType ). ReadUInt16( mpFileHeader->nColorMapFirstEntryIndex ).ReadUInt16( mpFileHeader->nColorMapLength ).ReadUChar( mpFileHeader->nColorMapEntrySize ). ReadUInt16( mpFileHeader->nColorMapXOrigin ).ReadUInt16( mpFileHeader->nColorMapYOrigin ).ReadUInt16( mpFileHeader->nImageWidth ). ReadUInt16( mpFileHeader->nImageHeight ).ReadUChar( mpFileHeader->nPixelDepth ).ReadUChar( mpFileHeader->nImageDescriptor ); - - if ( !m_rTGA.good()) - return false; - - if ( mpFileHeader->nColorMapType > 1 ) - return false; - if ( mpFileHeader->nColorMapType == 1 ) - mbIndexing = true; - - // first we want to get the version - mpFileFooter.reset( new TGAFileFooter ); // read the TGA-File-Footer to determine whether - // we got an old TGA format or the new one - - sal_uInt64 nCurStreamPos = m_rTGA.Tell(); - m_rTGA.Seek( STREAM_SEEK_TO_END ); - sal_uInt64 nTemp = m_rTGA.Tell(); - m_rTGA.Seek( nTemp - SizeOfTGAFileFooter ); - - m_rTGA.ReadUInt32( mpFileFooter->nExtensionFileOffset ).ReadUInt32( mpFileFooter->nDeveloperDirectoryOffset ). ReadUInt32( mpFileFooter->nSignature[0] ).ReadUInt32( mpFileFooter->nSignature[1] ).ReadUInt32( mpFileFooter->nSignature[2] ). ReadUInt32( mpFileFooter->nSignature[3] ).ReadUChar( mpFileFooter->nPadByte ).ReadUChar( mpFileFooter->nStringTerminator ); - - - if ( !m_rTGA.good()) - return false; - - // check for sal_True, VISI, ON-X, FILE in the signatures - if ( mpFileFooter->nSignature[ 0 ] == (('T'<<24)|('R'<<16)|('U'<<8)|'E') && - mpFileFooter->nSignature[ 1 ] == (('V'<<24)|('I'<<16)|('S'<<8)|'I') && - mpFileFooter->nSignature[ 2 ] == (('O'<<24)|('N'<<16)|('-'<<8)|'X') && - mpFileFooter->nSignature[ 3 ] == (('F'<<24)|('I'<<16)|('L'<<8)|'E') ) - { - mpExtension.reset( new TGAExtension ); - - m_rTGA.Seek( mpFileFooter->nExtensionFileOffset ); - m_rTGA.ReadUInt16( mpExtension->nExtensionSize ); - if ( !m_rTGA.good()) - return false; - if ( mpExtension->nExtensionSize >= SizeOfTGAExtension ) - { - mnTGAVersion = 2; - - m_rTGA.ReadBytes(mpExtension->sAuthorName, 41); - m_rTGA.ReadBytes(mpExtension->sAuthorComment, 324); - m_rTGA.ReadBytes(mpExtension->sDateTimeStamp, 12); - m_rTGA.ReadBytes(mpExtension->sJobNameID, 12); - m_rTGA.ReadChar( mpExtension->sJobNameID[ 0 ] ).ReadChar( mpExtension->sJobNameID[ 1 ] ).ReadChar( mpExtension->sJobNameID[ 2 ] ); - m_rTGA.ReadBytes(mpExtension->sSoftwareID, 41); - m_rTGA.ReadUInt16( mpExtension->nSoftwareVersionNumber ).ReadUChar( mpExtension->nSoftwareVersionLetter ) - .ReadUInt32( mpExtension->nKeyColor ).ReadUInt16( mpExtension->nPixelAspectRatioNumerator ) - .ReadUInt16( mpExtension->nPixelAspectRatioDeNumerator ).ReadUInt16( mpExtension->nGammaValueNumerator ) - .ReadUInt16( mpExtension->nGammaValueDeNumerator ).ReadUInt32( mpExtension->nColorCorrectionOffset ) - .ReadUInt32( mpExtension->nPostageStampOffset ).ReadUInt32( mpExtension->nScanLineOffset ) - .ReadUChar( mpExtension->nAttributesType ); - - if ( !m_rTGA.good()) - return false; - } - } - m_rTGA.Seek( nCurStreamPos ); - - // using the TGA file specification this was the correct form but adobe photoshop sets nImageDescriptor - // equal to nPixelDepth - // mnDestBitDepth = mpFileHeader->nPixelDepth - ( mpFileHeader->nImageDescriptor & 0xf ); - mnDestBitDepth = mpFileHeader->nPixelDepth; - - if ( mnDestBitDepth == 8 ) // this is a patch for grayscale pictures not including a palette - mbIndexing = true; - - if ( mnDestBitDepth > 32 ) // maybe the pixeldepth is invalid - return false; - else if ( mnDestBitDepth > 8 ) - mnDestBitDepth = 24; - else if ( mnDestBitDepth > 4 ) - mnDestBitDepth = 8; - else if ( mnDestBitDepth > 2 ) - mnDestBitDepth = 4; - - if ( !mbIndexing && ( mnDestBitDepth < 15 ) ) - return false; - - switch ( mpFileHeader->nImageType ) - { - case 9 : // encoding for colortype 9, 10, 11 - case 10 : - case 11 : - mbEncoding = true; - break; - } - - if ( mpFileHeader->nImageIDLength ) // skip the Image ID - m_rTGA.SeekRel( mpFileHeader->nImageIDLength ); - - return mbStatus; -} - - -bool TGAReader::ImplReadBody() -{ - - sal_uInt16 nXCount, nYCount, nRGB16; - sal_uInt8 nRed, nGreen, nBlue, nRunCount, nDummy, nDepth; - - // this four variables match the image direction - tools::Long nY, nYAdd, nX, nXAdd, nXStart; - - nX = nXStart = nY = 0; - nXCount = nYCount = 0; - nYAdd = nXAdd = 1; - - if ( mpFileHeader->nImageDescriptor & 0x10 ) - { - nX = nXStart = mpFileHeader->nImageWidth - 1; - nXAdd -= 2; - } - - if ( !(mpFileHeader->nImageDescriptor & 0x20 ) ) - { - nY = mpFileHeader->nImageHeight - 1; - nYAdd -=2; - } - - nDepth = mpFileHeader->nPixelDepth; - - if ( mbEncoding ) - { - if ( mbIndexing ) - { - switch( nDepth ) - { - // 16 bit encoding + indexing - case 16 : - while ( nYCount < mpFileHeader->nImageHeight ) - { - m_rTGA.ReadUChar( nRunCount ); - if ( !m_rTGA.good()) - return false; - if ( nRunCount & 0x80 ) // a run length packet - { - m_rTGA.ReadUInt16( nRGB16 ); - if ( nRGB16 >= mpFileHeader->nColorMapLength ) - return false; - nRed = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] >> 16 ); - nGreen = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] >> 8 ); - nBlue = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] ); - if ( !m_rTGA.good()) - return false; - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - else // a raw packet - { - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - m_rTGA.ReadUInt16( nRGB16 ); - if ( !m_rTGA.good()) - return false; - if ( nRGB16 >= mpFileHeader->nColorMapLength ) - return false; - nRed = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] >> 16 ); - nGreen = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] >> 8 ); - nBlue = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] ); - if ( !m_rTGA.good()) - return false; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - } - break; - - // 8 bit encoding + indexing - case 8 : - while ( nYCount < mpFileHeader->nImageHeight ) - { - m_rTGA.ReadUChar( nRunCount ); - if ( !m_rTGA.good()) - return false; - if ( nRunCount & 0x80 ) // a run length packet - { - m_rTGA.ReadUChar( nDummy ); - if ( !m_rTGA.good()) - return false; - if ( nDummy >= mpFileHeader->nColorMapLength ) - return false; - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - mpBitmap->SetPixel( nY, nX, mvPalette[nDummy] ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - else // a raw packet - { - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - - m_rTGA.ReadUChar( nDummy ); - if ( !m_rTGA.good()) - return false; - if ( nDummy >= mpFileHeader->nColorMapLength ) - return false; - mpBitmap->SetPixel( nY, nX, mvPalette[nDummy] ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - } - break; - default: - return false; - } - } - else - { - switch( nDepth ) - { - // 32 bit transparent true color encoding - case 32 : - { - while ( nYCount < mpFileHeader->nImageHeight ) - { - m_rTGA.ReadUChar( nRunCount ); - if ( !m_rTGA.good()) - return false; - if ( nRunCount & 0x80 ) // a run length packet - { - m_rTGA.ReadUChar( nBlue ).ReadUChar( nGreen ).ReadUChar( nRed ).ReadUChar( nDummy ); - if ( !m_rTGA.good()) - return false; - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - else // a raw packet - { - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - m_rTGA.ReadUChar( nBlue ).ReadUChar( nGreen ).ReadUChar( nRed ).ReadUChar( nDummy ); - if ( !m_rTGA.good()) - return false; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - } - } - break; - - // 24 bit true color encoding - case 24 : - while ( nYCount < mpFileHeader->nImageHeight ) - { - m_rTGA.ReadUChar( nRunCount ); - if ( !m_rTGA.good()) - return false; - if ( nRunCount & 0x80 ) // a run length packet - { - m_rTGA.ReadUChar( nBlue ).ReadUChar( nGreen ).ReadUChar( nRed ); - if ( !m_rTGA.good()) - return false; - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - else // a raw packet - { - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - m_rTGA.ReadUChar( nBlue ).ReadUChar( nGreen ).ReadUChar( nRed ); - if ( !m_rTGA.good()) - return false; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - } - break; - - // 16 bit true color encoding - case 16 : - while ( nYCount < mpFileHeader->nImageHeight ) - { - m_rTGA.ReadUChar( nRunCount ); - if ( !m_rTGA.good()) - return false; - if ( nRunCount & 0x80 ) // a run length packet - { - m_rTGA.ReadUInt16( nRGB16 ); - if ( !m_rTGA.good()) - return false; - nRed = static_cast<sal_uInt8>( nRGB16 >> 7 ) & 0xf8; - nGreen = static_cast<sal_uInt8>( nRGB16 >> 2 ) & 0xf8; - nBlue = static_cast<sal_uInt8>( nRGB16 << 3 ) & 0xf8; - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - else // a raw packet - { - for ( sal_uInt16 i = 0; i < ( ( nRunCount & 0x7f ) + 1 ); i++ ) - { - m_rTGA.ReadUInt16( nRGB16 ); - if ( !m_rTGA.good()) - return false; - nRed = static_cast<sal_uInt8>( nRGB16 >> 7 ) & 0xf8; - nGreen = static_cast<sal_uInt8>( nRGB16 >> 2 ) & 0xf8; - nBlue = static_cast<sal_uInt8>( nRGB16 << 3 ) & 0xf8; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - nX += nXAdd; - nXCount++; - if ( nXCount == mpFileHeader->nImageWidth ) - { - nX = nXStart; - nXCount = 0; - nY += nYAdd; - nYCount++; - - if( nYCount >= mpFileHeader->nImageHeight ) - break; - } - } - } - } - break; - - default: - return false; - } - } - } - else - { - for ( nYCount = 0; nYCount < mpFileHeader->nImageHeight; nYCount++, nY += nYAdd ) - { - nX = nXStart; - nXCount = 0; - - if ( mbIndexing ) - { - switch( nDepth ) - { - // 16 bit indexing - case 16 : - for (;nXCount < mpFileHeader->nImageWidth; nXCount++, nX += nXAdd ) - { - m_rTGA.ReadUInt16( nRGB16 ); - if ( !m_rTGA.good()) - return false; - if ( nRGB16 >= mpFileHeader->nColorMapLength ) - return false; - nRed = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] >> 16 ); - nGreen = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] >> 8 ); - nBlue = static_cast<sal_uInt8>( mpColorMap[ nRGB16 ] ); - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - } - break; - - // 8 bit indexing - case 8 : - for (;nXCount < mpFileHeader->nImageWidth; nXCount++, nX += nXAdd ) - { - m_rTGA.ReadUChar( nDummy ); - if ( !m_rTGA.good()) - return false; - if ( nDummy >= mpFileHeader->nColorMapLength ) - return false; - mpBitmap->SetPixel( nY, nX, Color(ColorTransparency, nDummy) ); - } - break; - default: - return false; - } - } - else - { - switch( nDepth ) - { - // 32 bit true color - case 32 : - { - for (;nXCount < mpFileHeader->nImageWidth; nXCount++, nX += nXAdd ) - { - m_rTGA.ReadUChar( nBlue ).ReadUChar( nGreen ).ReadUChar( nRed ).ReadUChar( nDummy ); - if ( !m_rTGA.good()) - return false; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - } - } - break; - - // 24 bit true color - case 24 : - for (;nXCount < mpFileHeader->nImageWidth; nXCount++, nX += nXAdd ) - { - m_rTGA.ReadUChar( nBlue ).ReadUChar( nGreen ).ReadUChar( nRed ); - if ( !m_rTGA.good()) - return false; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - } - break; - - // 16 bit true color - case 16 : - for (;nXCount < mpFileHeader->nImageWidth; nXCount++, nX += nXAdd ) - { - m_rTGA.ReadUInt16( nRGB16 ); - if ( !m_rTGA.good()) - return false; - nRed = static_cast<sal_uInt8>( nRGB16 >> 7 ) & 0xf8; - nGreen = static_cast<sal_uInt8>( nRGB16 >> 2 ) & 0xf8; - nBlue = static_cast<sal_uInt8>( nRGB16 << 3 ) & 0xf8; - mpBitmap->SetPixel( nY, nX, Color( nRed, nGreen, nBlue ) ); - } - break; - default: - return false; - } - } - } - } - return mbStatus; -} - - -bool TGAReader::ImplReadPalette() -{ - if ( mbIndexing ) // read the colormap - { - sal_uInt16 nColors = mpFileHeader->nColorMapLength; - - if ( !nColors ) // colors == 0 ? -> we will build a grayscale palette - { - if ( mpFileHeader->nPixelDepth != 8 ) - return false; - nColors = 256; - mpFileHeader->nColorMapLength = 256; - mpFileHeader->nColorMapEntrySize = 0x3f; // patch for the following switch routine - } - mpColorMap.reset( new sal_uInt32[ nColors ] ); // we will always index dwords - - switch( mpFileHeader->nColorMapEntrySize ) - { - case 0x3f : - { - for (sal_uInt32 i = 0; i < nColors; ++i) - { - mpColorMap[ i ] = ( i << 16 ) + ( i << 8 ) + i; - } - } - break; - - case 32 : - for (sal_uInt16 i = 0; i < nColors; i++) - { - m_rTGA.ReadUInt32(mpColorMap[i]); - } - break; - - case 24 : - { - for ( sal_uInt16 i = 0; i < nColors; i++ ) - { - sal_uInt8 nBlue; - sal_uInt8 nGreen; - sal_uInt8 nRed; - m_rTGA.ReadUChar(nBlue).ReadUChar(nGreen).ReadUChar(nRed); - mpColorMap[i] = (nRed << 16) | (nGreen << 8) | nBlue; - } - } - break; - - case 15 : - case 16 : - { - for ( sal_uInt16 i = 0; i < nColors; i++ ) - { - sal_uInt16 nTemp; - m_rTGA.ReadUInt16( nTemp ); - if ( !m_rTGA.good() ) - return false; - mpColorMap[ i ] = ( ( nTemp & 0x7c00 ) << 9 ) + ( ( nTemp & 0x01e0 ) << 6 ) + - ( ( nTemp & 0x1f ) << 3 ); - } - } - break; - - default : - return false; - } - if ( mnDestBitDepth <= 8 ) - { - sal_uInt16 nDestColors = ( 1 << mnDestBitDepth ); - if ( nColors > nDestColors ) - return false; - - mvPalette.resize( nColors ); - for ( sal_uInt16 i = 0; i < nColors; i++ ) - { - mvPalette[i] = Color( static_cast<sal_uInt8>( mpColorMap[ i ] >> 16 ), - static_cast<sal_uInt8>( mpColorMap[ i ] >> 8 ), static_cast<sal_uInt8>(mpColorMap[ i ] ) ); - } - } - } - - return mbStatus; -} - -//================== GraphicImport - the exported function ================ - -extern "C" SAL_DLLPUBLIC_EXPORT bool -itgGraphicImport( SvStream & rStream, Graphic & rGraphic, FilterConfigItem* ) -{ - TGAReader aTGAReader(rStream); - - return aTGAReader.ReadTGA(rGraphic); -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |