mmplugins/imagingplugins/codecs/PNGCodec/PNGCodec.h
branchRCL_3
changeset 50 948c7f65f6d4
parent 0 40261b775718
equal deleted inserted replaced
49:735348f59235 50:948c7f65f6d4
       
     1 // Copyright (c) 1999-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 //
       
    15 
       
    16 #ifndef __PNGCODEC_H__
       
    17 #define __PNGCODEC_H__
       
    18 
       
    19 #include <bitdev.h>
       
    20 #include <ezcompressor.h>
       
    21 #include <ezdecompressor.h>
       
    22 #include <icl/imageprocessor.h>
       
    23 #include <icl/imagecodec.h>
       
    24 
       
    25 #include "PNGConvert.h"
       
    26 
       
    27 /** @file
       
    28 	@internalComponent */
       
    29 
       
    30 // Constants.
       
    31 const TInt KPngFileSignatureLength = 8;
       
    32 const TUint8 KPngSignature[KPngFileSignatureLength] = { 0x89, 0x50, 0x4E, 0x47, 0x0D, 0x0A, 0x1A, 0x0A };
       
    33 
       
    34 const TInt KPngChunkIdSize = 4;
       
    35 const TInt KPngMaxPLTESize = 256;
       
    36 const TInt KPngNumInterlacedPasses = 8; // 7 passes plus a safety entry
       
    37 
       
    38 const TInt KPngChunkLengthSize = 4;
       
    39 const TInt KPngChunkCRCSize = 4;
       
    40 
       
    41 const TInt KPngIHDRChunkSize = 13;
       
    42 const TInt KPngIENDChunkSize = 0;
       
    43 const TInt KPngcHRMChunkSize = 32;
       
    44 const TInt KPnggAMAChunkSize = 4;
       
    45 const TInt KPngpHYsChunkSize = 9;
       
    46 const TInt KPngtIMEChunkSize = 7;
       
    47 
       
    48 // KPngMaxImageSize is the maximum size for width and height, as defined in the PNG Specification v1.0 page 14
       
    49 const TUint KPngMaxImageSize = ((TUint)2 << 30) - 1;
       
    50 const TInt KPngCrcTableLength = 256;
       
    51 const TUint KPngCrcMask = 0xffffffff;
       
    52 
       
    53 _LIT8(KPngIHDRChunkId,"IHDR");
       
    54 _LIT8(KPngPLTEChunkId,"PLTE");
       
    55 _LIT8(KPngIDATChunkId,"IDAT");
       
    56 _LIT8(KPngIENDChunkId,"IEND");
       
    57 _LIT8(KPngbKGDChunkId,"bKGD");
       
    58 _LIT8(KPngpHYsChunkId,"pHYs");
       
    59 _LIT8(KPngtRNSChunkId,"tRNS");
       
    60 _LIT8(KPngZTXTChunkId,"zTXt");
       
    61 _LIT8(KPngITXTChunkId,"iTXt");
       
    62 _LIT8(KPngTEXTChunkId,"tEXt");
       
    63 
       
    64 
       
    65 // Helper classes.
       
    66 // TPngImageInformation
       
    67 class TPngImageInformation : public TFrameInfo
       
    68 	{
       
    69 public:
       
    70 	TPngImageInformation();
       
    71 public:
       
    72 	enum TColorElements
       
    73 		{
       
    74 		EMonochrome = 0x0,
       
    75 		EPaletteUsed = 0x1,
       
    76 		EColorUsed = 0x2,
       
    77 		EAlphaChannelUsed = 0x4
       
    78 		};
       
    79 	enum TColorType
       
    80 		{
       
    81 		EGrayscale = EMonochrome, // 0
       
    82 		EDirectColor = EColorUsed, // 2
       
    83 		EIndexedColor = EColorUsed | EPaletteUsed, // 3
       
    84 		EAlphaGrayscale = EMonochrome | EAlphaChannelUsed, // 4
       
    85 		EAlphaDirectColor = EColorUsed | EAlphaChannelUsed // 6
       
    86 		};
       
    87 	enum TCompressionMethod
       
    88 		{
       
    89 		EDeflateInflate32K = 0
       
    90 		};
       
    91 	enum TFilterMethod
       
    92 		{
       
    93 		EAdaptiveFiltering = 0
       
    94 		};
       
    95 	enum TInterlaceMethod
       
    96 		{
       
    97 		ENoInterlace = 0,
       
    98 		EAdam7Interlace = 1
       
    99 		};
       
   100 	enum TPhysicalUnits
       
   101 		{
       
   102 		EUnknownUnits = 0,
       
   103 		EMeters = 1
       
   104 		};
       
   105 public:
       
   106 	// IHDR chunk
       
   107 	TSize iSize; // iWidth/iHeight = 1 ... (2^31)-1
       
   108 	TInt iBitDepth; // 1,2,4,8,16 subject to color type restrictions
       
   109 	TColorType iColorType; // 0,2,3,4,6
       
   110 	TCompressionMethod iCompressionMethod; // 0
       
   111 	TFilterMethod iFilterMethod; // 0
       
   112 	TInterlaceMethod iInterlaceMethod; // 0 or 1
       
   113 
       
   114 	// PLTE chunk
       
   115 	TBool iPalettePresent;
       
   116 	TRgb iPalette[KPngMaxPLTESize];
       
   117 
       
   118 	// bKGD chunk
       
   119 	TBool iBackgroundPresent;
       
   120 //	TRgb iBackgroundColor; // declared in TFrameInfo
       
   121 
       
   122 	// pHYs chunk
       
   123 	TBool iPhysicalPresent;
       
   124 	TPhysicalUnits iPhysicalUnits;
       
   125 	TSize iPhysicalSize;
       
   126 
       
   127 	// tRNS chunk
       
   128 	TBool iTransparencyPresent;
       
   129 	TUint16 iTransparentGray;
       
   130 	TUint16 iTransparentRed;
       
   131 	TUint16 iTransparentGreen;
       
   132 	TUint16 iTransparentBlue;
       
   133 	TUint8 iTransparencyValue[KPngMaxPLTESize];
       
   134 	};
       
   135 
       
   136 /**
       
   137 The Base class for different conversion types.
       
   138 It is used when Image Processor is ignored for decoding 24 (or 32) bpp non-interlaced PNG images into 24 (or 32 bpp).
       
   139 All subclasses should provide implementations of SetPixels().
       
   140 */
       
   141 class CFastProcessor : public CBase
       
   142 	{
       
   143 public:
       
   144     static CFastProcessor* NewL(const TPngImageInformation& aImageInfo, CFbsBitmap* aDestination, CFbsBitmap* aMask, TBool aRgbaMode);
       
   145     virtual ~CFastProcessor();
       
   146     void End();
       
   147     virtual void SetPixels(const TUint8* aDataPtr, const TUint8* aDataPtrLimit, TRgb* aLineCache, TPoint& aPos) = 0;
       
   148     void Begin();
       
   149     
       
   150 private:    
       
   151 	void ConstructL();
       
   152 
       
   153 protected:
       
   154     CFastProcessor(CFbsBitmap* aDestination, CFbsBitmap* aMask, TBool aRgbaMode);
       
   155     CFbsBitmap* iBitmap;
       
   156     CFbsBitmap* iMask;
       
   157     TUint8* iBitmapBuffer;
       
   158     TUint8* iMaskBuffer;
       
   159     TSize iBitmapSize;
       
   160     TPoint iPos;
       
   161     TBool iRgbaMode;
       
   162 	};
       
   163 
       
   164 // Read codec
       
   165 
       
   166 class CPngReadSubCodec : public CBase
       
   167 	{
       
   168 public:
       
   169 	static CPngReadSubCodec* NewL(CImageProcessor* aImageProc,CImageProcessor* aMaskProc,const TPngImageInformation& aInfo, CFastProcessor* aFastProc, TBool aFastProcessorMode);
       
   170 	virtual ~CPngReadSubCodec();
       
   171 	TDes8& FirstBuffer();
       
   172 	TDes8& DecodeL();
       
   173 	void ResetL();
       
   174 	void SetRgbaMode(TBool aMode);
       
   175 	void Start();
       
   176 	void Complete();
       
   177 	void SetAlphaMode(TBool aMode);
       
   178 
       
   179 protected:
       
   180 	CPngReadSubCodec();
       
   181 	void WritePixel(TRgb aPixelColor);
       
   182 	void WritePixel(TRgb aPixelColor,TUint8 aAlphaValue);
       
   183 private:
       
   184 	void ConstructL(CImageProcessor* aImageProc,CImageProcessor* aMaskProc,const TPngImageInformation& aInfo,CFastProcessor* aFastProc, TBool aFastProcessorMode);
       
   185 	void FilterScanlineDataL(TUint8* aDataPtr,const TUint8* aDataPtrLimit);
       
   186 	TInt PaethPredictor(TInt aLeft,TInt aAbove,TInt aAboveLeft);
       
   187 	virtual void DoConstructL() = 0;
       
   188 	virtual TInt ScanlineBufferSize(TInt aPixelLength) = 0;
       
   189 	virtual void DoDecode(TUint8* aDataPtr,const TUint8* aDataPtrLimit) = 0;
       
   190 	void UpdatePos();
       
   191 	TInt ClampValue(TInt aValue, TInt aMinValue, TInt aMaxValue) const;
       
   192 	void SetFastProcessorMode(TBool aMode); //Sets iFastProcessorMode to True or False
       
   193 	
       
   194 protected:
       
   195 	CImageProcessor* iImageProc;
       
   196 	CImageProcessor* iMaskProc;
       
   197 	TPngImageInformation iInfo;
       
   198 	TInt iScanlineBufferSize;
       
   199 	TInt iBytesPerPixel;
       
   200 	HBufC8* iScanlineBuffer1;
       
   201 	HBufC8* iScanlineBuffer2;
       
   202 	TPtr8 iScanlineDes1;
       
   203 	TPtr8 iScanlineDes2;
       
   204 	TInt iCurrentScanlineBuffer;
       
   205 	TInt iInterlacedScanlineBufferSize[KPngNumInterlacedPasses];
       
   206 	TInt iPass;
       
   207 	TPoint iPos;
       
   208 	TBool iRgbaMode;
       
   209 	TRgb* iLineCache;
       
   210 	TBool iFastProcessorMode; //Sets the current mode
       
   211 	CFastProcessor* iFastProc;
       
   212 	TBool iAlphaMode; // Are we decoding to a bitmap that contains an alpha channel?
       
   213 	};
       
   214 
       
   215 
       
   216 class MPngDecoder;
       
   217 class CPngReadCodec : public CImageMaskProcessorReadCodec, public MEZBufferManager
       
   218 	{
       
   219 public:
       
   220 	~CPngReadCodec();
       
   221 
       
   222 	static CPngReadCodec* NewL(MPngDecoder& aDecoderIFace);
       
   223 	void SetImageProcessor(CImageProcessor* aImageProc, TBool aOwnsProcessor=ETrue);
       
   224 	void SetMaskProcessor(CImageProcessor* aMaskProc, TBool aOwnsProcessor=ETrue);
       
   225 	void SetFastProcessor(CFastProcessor* aFastProc, TBool aOwnsProcessor=ETrue);
       
   226 
       
   227 	CImageProcessor* MaskProcessor() const;
       
   228 	CImageProcessor* ImageProcessor() const;
       
   229 	CFastProcessor* FastProcessor() const;
       
   230 	
       
   231 		// From CImageReadCodec
       
   232 	virtual void InitFrameL(TFrameInfo& aFrameInfo, CFrameImageData& aFrameImageData, TBool aDisableErrorDiffusion, CFbsBitmap& aDestination, CFbsBitmap* aDestinationMask);
       
   233 	virtual void InitFrameHeader(TFrameInfo& aFrameSettings, CFrameImageData& /* aFrameImageData */);
       
   234 	TFrameState ProcessFrameHeaderL(TBufPtr8& aData);
       
   235 	TFrameState ProcessFrameL(TBufPtr8& aSrc);
       
   236 	TBool DoProcessDataL();
       
   237 	void GetNewDataPosition(TInt& aPosition, TInt&  /*aLength*/ );
       
   238 	TBool SkipImageProcessor(CFbsBitmap& aDestination); //Checks if Image processor is to be used or skipped. If returns ETrue then skip ImageProcessor 
       
   239 	void Complete();
       
   240 	void SetMissingiENDChunkFail(TBool aValue);
       
   241 
       
   242 protected:
       
   243 	CPngReadCodec(MPngDecoder& aDecoderIFace);
       
   244 	void ConstructL();
       
   245 
       
   246 protected:
       
   247 	virtual void DoProcessPLTEL(const TUint8* aDataPtr,TInt aChunkLength);
       
   248 	virtual void DoProcesstRNSL(const TUint8* aDataPtr,TInt aChunkLength);
       
   249 	virtual void DoProcessbKGDL(const TUint8* aDataPtr,TInt aChunkLength);
       
   250 	virtual void DoProcesspHYsL(const TUint8* aDataPtr,TInt aChunkLength);
       
   251 
       
   252 private:
       
   253 	void DoProcessInfoL(const TUint8*& aDataPtr,const TUint8* aDataPtrLimit);
       
   254 	void DoProcessIHDRL(const TUint8* aDataPtr,TInt aChunkLength);
       
   255 
       
   256 	TBool SetupProcessData(TBufPtr8& aSrc,
       
   257 						   TUint8* aStartDataPtr,
       
   258 						   const TUint8*& aDataPtr,
       
   259 						   const TUint8* aDataPtrLimit);
       
   260 
       
   261 	// From MEZBufferManager
       
   262 	virtual void InitializeL(CEZZStream &aZStream);
       
   263 	virtual void NeedInputL(CEZZStream &aZStream);
       
   264 	virtual void NeedOutputL(CEZZStream &aZStream);
       
   265 	virtual void FinalizeL(CEZZStream &aZStream);
       
   266 protected:
       
   267 	MPngDecoder& iDecoderIFace;
       
   268 	TFrameInfo* iFrameInfo;
       
   269 	TPngImageInformation iImageInfo;
       
   270 	TBuf8<KPngChunkIdSize> iChunkId;
       
   271 	TInt iChunkBytesRemaining;
       
   272 	CPngReadSubCodec* iDecoder;
       
   273 	CEZDecompressor* iDecompressor;
       
   274 	TPtrC8 iDataDes;
       
   275 	// used for async decode...
       
   276 	const TUint8* iDataPtr;
       
   277 	TBufPtr8* iSavedSrc;
       
   278 	TUint8* iStartDataPtr;
       
   279 	CImageProcessor* iImageProc;
       
   280 	TBool iOwnsImageProcessor;
       
   281 	CImageProcessor* iMaskProc;
       
   282 	TBool	iOwnsMaskProcessor;
       
   283 	CFastProcessor* iFastProc;
       
   284 	TBool	iOwnsFastProcessor;
       
   285 private:	
       
   286 	TInt iNewPosition;
       
   287 	TBool iReadMore;
       
   288 	TBool iPreviousChunkReadFailed;
       
   289 	TBool iMissingiENDChunkFail;
       
   290 	TInt iPreviousDataPos;
       
   291 	TInt iPreviousDataLength;
       
   292 	};
       
   293 
       
   294 // Write sub-codec
       
   295 class CPngWriteSubCodec : public CBase
       
   296 	{
       
   297 public:
       
   298 	static CPngWriteSubCodec* NewL(const TPngImageInformation& aInfo, const CFbsBitmap* aSource);
       
   299 	virtual ~CPngWriteSubCodec();
       
   300 protected:
       
   301 	CPngWriteSubCodec();
       
   302 private:
       
   303 	void ConstructL(const TPngImageInformation& aInfo, const CFbsBitmap* aSource);
       
   304 public:
       
   305 	TDes8& Buffer();
       
   306 	inline TInt BufferSize() const;
       
   307 	TDes8& EncodeL(const TInt aScanline);
       
   308 	inline CPalette* Palette() const;
       
   309 protected:
       
   310 	TUint8 ReverseBits(const TUint8 aValue) const;
       
   311 	void EncodePalettedScanline(TUint8* aDataPtr, const CFbsBitmap* aSource, const TInt aScanline,
       
   312 								const TInt aPixelsPerByte, const TInt aShiftValue);
       
   313 private:
       
   314 	virtual void DoConstructL();
       
   315 	virtual TInt ScanlineBufferSize(TInt aPixelLength) = 0;
       
   316 	virtual void DoEncode(const CFbsBitmap* aSource, const TInt aScanline,
       
   317 					TUint8* aDataPtr, const TUint8* aDataPtrLimit) = 0;
       
   318 protected:
       
   319 	TPngImageInformation iInfo;
       
   320 	const CFbsBitmap* iSource;
       
   321 	TInt iScanlineBufferSize;
       
   322 	HBufC8* iScanlineBuffer;
       
   323 	TPtr8 iScanlineDes;
       
   324 	CPalette* iPalette;
       
   325 
       
   326 	friend class RPngWriteSubCodecTest;
       
   327 	};
       
   328 
       
   329 // Write codec
       
   330 class CPngWriteCodec : public CImageWriteCodec, public MEZBufferManager
       
   331 	{
       
   332 private:
       
   333 	enum TPngEncoderState
       
   334 		{
       
   335 		EPngInit,		// Initialize compressor
       
   336 		EPngDeflate,	// Deflate encoded image data
       
   337 		EPngWritePLTE,	// Write PLTE chunk
       
   338 		EPngWriteIDAT,	// Write IDAT chunk
       
   339 		EPngEndChunk	// Write end chunk
       
   340 		};
       
   341 public:
       
   342 	static CPngWriteCodec* NewL(CPngEncoder& aPlugin, TInt aBpp, TBool aColor, TBool aPaletted, TInt aCompressionLevel);
       
   343 
       
   344 	virtual ~CPngWriteCodec();
       
   345 public:
       
   346 	void GetCrc(TUint32& aCrc, const TUint8* aPtr, const TInt aLength);
       
   347 	TBool DeflateEncodedDataL();
       
   348 private:
       
   349 	CPngWriteCodec(CPngEncoder& aPlugin, TInt aBpp, TBool aColor, TBool aPaletted, TInt aCompressionLevel);
       
   350 
       
   351 	void WritePngChunk(TUint8*& aDestPtr, const TDesC8& aChunkId, const TDesC8& aData, TInt& aLength);
       
   352 	void InitializeCompressorL(TBufPtr8& aDst);
       
   353 	void SetCompressorOutputL(TBufPtr8& aDst);
       
   354 	void WritePLTEChunk(TBufPtr8& aDst);
       
   355 	void WriteIDATChunk(TBufPtr8& aDst);
       
   356 	void WriteEndChunk(TBufPtr8& aDst);
       
   357 	TInt WriteHeaderChunk(TBufPtr8& aDst);
       
   358 	void GetImageDataL(TInt& aBytesToProcess);
       
   359 	void GetPngScanLine(TDes8& aBuf, const TPoint& aPixel, TInt& aLength);
       
   360 	void CalcCrcTable();
       
   361 	// from CImageWriteCodec
       
   362 public:
       
   363 	virtual void InitFrameL(TBufPtr8& aDst, const CFbsBitmap& aSource);
       
   364 	virtual TFrameState ProcessFrameL(TBufPtr8& aDst);
       
   365 	// from MEZBufferManager
       
   366 private:
       
   367 	virtual void InitializeL(CEZZStream &aZStream);
       
   368 	virtual void NeedInputL(CEZZStream &aZStream);
       
   369 	virtual void NeedOutputL(CEZZStream &aZStream);
       
   370 	virtual void FinalizeL(CEZZStream &aZStream);
       
   371 private:
       
   372 	TUint32 iCrcTable[KPngCrcTableLength];
       
   373 	TBool iCrcTableCalculated;
       
   374 	CPngWriteSubCodec* iEncoder;
       
   375 	TPngEncoderState iEncoderState;
       
   376 	TInt iCompressionLevel;
       
   377 	CEZCompressor* iCompressor;
       
   378 	TInt iScanline;
       
   379 	TUint8* iDestStartPtr;
       
   380 	TUint8* iDestPtr;
       
   381 	TUint8* iDestPtrLimit;
       
   382 	TPngImageInformation iImageInfo;
       
   383 	TPtr8 iCompressorPtr;	// data area for compressor to write to
       
   384 	TBool iCallAgain;
       
   385 	CPngEncoder& iPlugin;
       
   386 
       
   387 	friend class RPngWriteCodecTest;
       
   388 	};
       
   389 
       
   390 
       
   391 #include "PngCodec.inl"
       
   392 
       
   393 #endif // __PNGCODEC_H__