--- a/photosgallery/viewframework/texturemanager/src/glxbitmapdecoderwrapper.cpp Wed Jun 09 09:41:51 2010 +0300
+++ b/photosgallery/viewframework/texturemanager/src/glxbitmapdecoderwrapper.cpp Mon Jun 21 15:40:32 2010 +0300
@@ -29,27 +29,31 @@
#include <hal_data.h>
#include <mglxcache.h>
#include <oommonitorsession.h>
+#include <e32math.h>
+#include <apgcli.h>
+
namespace
-{
-const TInt KGlxDecodingThreshold = 3000000;
-const TInt KGlxDecodingThresholdDimension = 2000;
-
+ {
+ const TInt KGlxDecodingThreshold = 3000000;
+ const TInt KGlxDecodingThresholdDimension = 2000;
-// Photos low_ram_threshold [8.637 MB] as in oomconfig.xml
-const TInt KGlxCriticalRAMForPhotos = 9056550;
-const TInt KGlxDecodeBitmapFactor = 3;
-// All EXIF data is within the first KGlxMaxExifSize bytes of the file
-const TInt KGlxMaxExifSize = 0x10000;
-}
+ // Photos low_ram_threshold [8.637 MB] as in oomconfig.xml
+ const TInt KGlxCriticalRAMForPhotos = 9056550;
+ const TInt KGlxDecodeBitmapFactor = 3;
+
+ _LIT(KMimeJpeg,"image/jpeg");
+ _LIT(KMimeJpg,"image/jpg");
+ }
// ---------------------------------------------------------------------------
// Two-phased constructor.
// ---------------------------------------------------------------------------
//
-CGlxBitmapDecoderWrapper* CGlxBitmapDecoderWrapper::NewL(MGlxBitmapDecoderObserver* aObserver)
+CGlxBitmapDecoderWrapper* CGlxBitmapDecoderWrapper::NewL(
+ MGlxBitmapDecoderObserver* aObserver)
{
- TRACER("CGlxBitmapDecoderWrapper:: NewL ");
- CGlxBitmapDecoderWrapper* self = new(ELeave)CGlxBitmapDecoderWrapper();
+ TRACER("CGlxBitmapDecoderWrapper::NewL()");
+ CGlxBitmapDecoderWrapper* self = new (ELeave) CGlxBitmapDecoderWrapper();
CleanupStack::PushL(self);
self->ConstructL(aObserver);
CleanupStack::Pop(self);
@@ -60,20 +64,19 @@
// Constructor
// ---------------------------------------------------------------------------
//
-CGlxBitmapDecoderWrapper::CGlxBitmapDecoderWrapper()
- :CActive( EPriorityLow )
- {
- TRACER("CGlxBitmapDecoderWrapper:: NewL ");
- }
+CGlxBitmapDecoderWrapper::CGlxBitmapDecoderWrapper() :
+ CActive(EPriorityLow)
+ {
+ TRACER("CGlxBitmapDecoderWrapper::CGlxBitmapDecoderWrapper()");
+ }
// ---------------------------------------------------------------------------
// Destructor
// ---------------------------------------------------------------------------
//
-
CGlxBitmapDecoderWrapper::~CGlxBitmapDecoderWrapper()
{
- TRACER("CGlxBitmapDecoderWrapper:: ~CGlxBitmapDecoderWrapper ");
+ TRACER("CGlxBitmapDecoderWrapper::~CGlxBitmapDecoderWrapper()");
iFs.Close();
Cancel();
if (iImageDecoder)
@@ -81,6 +84,11 @@
delete iImageDecoder;
iImageDecoder = NULL;
}
+ if (iImagePath)
+ {
+ delete iImagePath;
+ iImagePath = NULL;
+ }
}
// ---------------------------------------------------------------------------
@@ -97,16 +105,17 @@
// ---------------------------------------------------------------------------
// DoDecodeImageL
// ---------------------------------------------------------------------------
+void CGlxBitmapDecoderWrapper::DoDecodeImageL(const TDesC& aSourceFileName,
+ TInt aIndex)
+ {
+ TRACER("CGlxBitmapDecoderWrapper::DoDecodeImageL()");
+ GLX_LOG_URI("CGlxBitmapDecoderWrapper::DoDecodeImageL(%S)",
+ &aSourceFileName);
-void CGlxBitmapDecoderWrapper::DoDecodeImageL(const TDesC & aSourceFileName,TInt aIndex)
- {
- TRACER("CGlxBitmapDecoderWrapper:: DoDecodeImageL ");
iThumbnailIndex = aIndex;
- //Variable used to get the decoder type used
- TBool isExtDecoderUsed = ETrue;
-
+
#ifdef _DEBUG
- iDecodeProcessstartTime.HomeTime();
+ iStartTime.HomeTime();
#endif
if (iImageDecoder)
@@ -114,61 +123,40 @@
delete iImageDecoder;
iImageDecoder = NULL;
}
-
- CImageDecoder::TOptions options = (CImageDecoder::TOptions)
- ( CImageDecoder::EOptionNoDither | CImageDecoder::EOptionAlwaysThread );
+
+ CImageDecoder::TOptions options =
+ (CImageDecoder::TOptions) (CImageDecoder::EOptionNoDither
+ | CImageDecoder::EOptionAlwaysThread);
// Use extended JPEG decoder
+ GLX_DEBUG1("DoDecodeImageL:: EHwImplementation" );
TRAPD( err, iImageDecoder = CExtJpegDecoder::FileNewL(
- CExtJpegDecoder::EHwImplementation, iFs, aSourceFileName, options ) );
- if ( KErrNone != err )
+ CExtJpegDecoder::EHwImplementation, iFs,
+ aSourceFileName, options ) );
+ GLX_DEBUG2("DoDecodeImageL:: EHwImplementation (%d)", err);
+ if (KErrNone != err)
{
- GLX_LOG_INFO( "DoDecodeImageL:: ESwImplementation" );
TRAP(err,iImageDecoder = CExtJpegDecoder::FileNewL(
- CExtJpegDecoder::ESwImplementation, iFs, aSourceFileName, options ) );
- if ( KErrNone != err )
+ CExtJpegDecoder::ESwImplementation, iFs,
+ aSourceFileName, options ) );
+ GLX_DEBUG2("DoDecodeImageL:: ESwImplementation (%d)", err);
+ if (KErrNone != err)
{
- GLX_LOG_INFO( "DoDecodeImageL:: CImageDecoder" );
+ GLX_DEBUG1("DoDecodeImageL::CImageDecoder");
// Not a JPEG - use standard decoder
- iImageDecoder = CImageDecoder::FileNewL( iFs, aSourceFileName, options );
- isExtDecoderUsed = EFalse;
+ iImageDecoder = CImageDecoder::FileNewL(iFs, aSourceFileName,
+ options);
}
}
#ifdef _DEBUG
- iStopTime.HomeTime();
- GLX_DEBUG1("=== DECODER CREATION ===");
- GLX_DEBUG2("Decoder Creation took <%d> us",
- (TInt)iStopTime.MicroSecondsFrom(iDecodeProcessstartTime).Int64());
+ iStopTime.HomeTime();
+ GLX_DEBUG2("*** Decoder Creation took <%d> us ***",
+ (TInt)iStopTime.MicroSecondsFrom(iStartTime).Int64());
#endif
-
+
TSize imageSize = iImageDecoder->FrameInfo().iOverallSizeInPixels;
- if(isExtDecoderUsed)
- {
- TUint16 orientation=0;
- //Read the orientation from the Exif header of the image if present
- TRAPD(error, orientation=GetOrientationL(aSourceFileName));
- if(KErrNone == error )
- {
- //Get the rotation angle and the flip status from orientation
- TInt rotAngle = 0;
- TBool flipStatus = EFalse;
- GetRotationParameters(orientation, rotAngle, flipStatus);
- //Set the parameters to the decoder
- CExtJpegDecoder* extDecoder = (CExtJpegDecoder*)iImageDecoder;
- extDecoder->SetRotationL(rotAngle);
- if(flipStatus)
- {
- extDecoder->SetMirroringL();
- }
- //Switch Image Height and width in case orientation > 4 as that
- //corresponds to angles 180 and 270 degrees
- if (orientation > 4)
- {
- imageSize.SetSize(imageSize.iHeight,imageSize.iWidth);
- }
- }
-
- }
+ GLX_DEBUG3("GlxDecoderWrapper::DecodeImageL() - OverallSize: w=%d, h=%d",
+ imageSize.iWidth, imageSize.iHeight);
iOriginalSize.iWidth = imageSize.iWidth;
iOriginalSize.iHeight = imageSize.iHeight;
@@ -177,140 +165,161 @@
delete iBitmap;
iBitmap = NULL;
}
+
+ if (iImagePath)
+ {
+ delete iImagePath;
+ iImagePath = NULL;
+ }
+ iImagePath = aSourceFileName.Alloc();
+
DecodeImageL();
}
+
// ---------------------------------------------------------------------------
// DecodeImageL
// ---------------------------------------------------------------------------
//
void CGlxBitmapDecoderWrapper::DecodeImageL()
{
- TRACER("CGlxBitmapDecoderWrapper:: DecodeImageL ");
+ TRACER("CGlxBitmapDecoderWrapper::DecodeImageL()");
TReal32 mFactor = 1;
- TReal32 mFactor1 = 1;
+ TReal mFactor1 = 1;
TReal32 mFactor2 = 1;
//Set Size according to level and state
TReal32 width = iOriginalSize.iWidth;
TReal32 height = iOriginalSize.iHeight;
- GLX_LOG_INFO1("DecodeImageL:width=%f", width);
- GLX_LOG_INFO1("DecodeImageL:height=%f",height);
-
- if ( KGlxDecodingThreshold < (width * height))
+
+ if (KGlxDecodingThreshold < (width * height))
{
- mFactor1 = TReal32(KGlxDecodingThreshold) / (width*height);
- GLX_LOG_INFO1("mFactor1 =%f",mFactor1);
+ TReal tempFactor = TReal32(KGlxDecodingThreshold)
+ / (width * height);
+ User::LeaveIfError(Math::Sqrt(mFactor1, tempFactor));
+ GLX_DEBUG2("DecodeImageL() - mFactor1 = %f", mFactor1);
}
-
- if ( KGlxDecodingThresholdDimension < width || KGlxDecodingThresholdDimension < height)
+
+ if (KGlxDecodingThresholdDimension < width
+ || KGlxDecodingThresholdDimension < height)
{
- mFactor2 = TReal32(KGlxDecodingThresholdDimension) / Max(width, height);
- GLX_LOG_INFO1("mFactor2 =%f",mFactor2);
+ mFactor2 = TReal32(KGlxDecodingThresholdDimension) / Max(width,
+ height);
+ GLX_DEBUG2("DecodeImageL() - mFactor2 = %f", mFactor2);
}
- mFactor = Min(mFactor1 , mFactor2);
- GLX_LOG_INFO1("Final mFactor =%f",mFactor);
+ mFactor = Min(TReal32(mFactor1), mFactor2);
+ GLX_DEBUG2("DecodeImageL() - Final mFactor = %f", mFactor);
// create the destination bitmap
- if(!iBitmap)
+ if (!iBitmap)
{
TInt freeMemory = 0;
- HAL::Get( HALData::EMemoryRAMFree, freeMemory );
- width*=mFactor;
- height*=mFactor;
- TInt minmemorytodecode = KGlxDecodeBitmapFactor*width*height;
- GLX_LOG_INFO2("DecodeImageL: after factoring width=%f, height=%f", width, height);
- GLX_LOG_INFO2("DecodeImageL:minmemorytodecode=%d, freememory=%d",
+ HAL::Get(HALData::EMemoryRAMFree, freeMemory);
+ width *= mFactor;
+ height *= mFactor;
+ TInt minmemorytodecode = KGlxDecodeBitmapFactor * width * height;
+ GLX_DEBUG3("DecodeImageL: minmemorytodecode=%d, freememory=%d",
minmemorytodecode, freeMemory);
- if(minmemorytodecode < (freeMemory - KGlxCriticalRAMForPhotos))
+
+ iTargetBitmapSize.iWidth = width;
+ iTargetBitmapSize.iHeight = height;
+ GLX_DEBUG3("DecodeImageL: iTargetBitmapSize w=%d, h=%d",
+ iTargetBitmapSize.iWidth, iTargetBitmapSize.iHeight);
+ __ASSERT_DEBUG(width > 0 && height > 0, Panic(EGlxPanicIllegalArgument));
+
+ if (minmemorytodecode < (freeMemory - KGlxCriticalRAMForPhotos))
{
- GLX_LOG_INFO("DecodeImageL:RAM available decoding image");
-
+ GLX_DEBUG1("DecodeImageL:RAM available decoding image");
iBitmap = new (ELeave) CFbsBitmap();
- iBitmap->Create( TSize(width,height),iImageDecoder->FrameInfo().iFrameDisplayMode );
+ iBitmap->Create(ReCalculateSizeL(),
+ iImageDecoder->FrameInfo().iFrameDisplayMode);
#ifdef _DEBUG
iStartTime.HomeTime(); // Get home time
#endif
- iImageDecoder->Convert( &iStatus, *iBitmap );
+ iImageDecoder->Convert(&iStatus, *iBitmap);
}
else
{
//case when sufficient memory is not available
//request OOM FW to release the required memory
- GLX_LOG_INFO("DecodeImageL:insufficient RAM - request OOM");
+ GLX_DEBUG1("DecodeImageL:insufficient RAM - request OOM");
TInt err = OOMRequestFreeMemoryL(minmemorytodecode);
- if(err == KErrNoMemory)
+ if (err == KErrNoMemory)
{
//if OOM fails, release Photos Cache
- GLX_LOG_INFO("DecodeImageL:insufficient RAM - OOM failed - request Cache");
+ GLX_DEBUG1("DecodeImageL:insufficient RAM - OOM failed"
+ " - request Cache");
MGlxCache* cacheManager = MGlxCache::InstanceL();
- cacheManager->ReleaseRAML(ETrue);
+ cacheManager->ReleaseRAML(ETrue);
cacheManager->Close();
//Try and release memory again
err = OOMRequestFreeMemoryL(minmemorytodecode);
}
- if(err != KErrNoMemory)
+ if (err != KErrNoMemory)
{
- GLX_LOG_INFO("DecodeImageL:Sufficient RAM available");
+ GLX_DEBUG1("DecodeImageL:Sufficient RAM available");
iBitmap = new (ELeave) CFbsBitmap();
- iBitmap->Create( TSize(width,height),iImageDecoder->FrameInfo().iFrameDisplayMode );
+ iBitmap->Create(ReCalculateSizeL(),
+ iImageDecoder->FrameInfo().iFrameDisplayMode);
#ifdef _DEBUG
- iStartTime.HomeTime(); // Get home time
+ iStartTime.HomeTime(); // Get home time
#endif
- iImageDecoder->Convert( &iStatus, *iBitmap );
+ iImageDecoder->Convert(&iStatus, *iBitmap);
}
else
{
- GLX_LOG_INFO("NOT ENOUGH MEMORY - Using the Fullscreen Thumbnail For Zoom");
+ GLX_DEBUG1("NOT ENOUGH MEMORY - "
+ "Using the Fullscreen Thumbnail For Zoom");
//release the file held by decoder immediately.
iImageDecoder->Cancel();
delete iImageDecoder;
iImageDecoder = NULL;
//Inform the client that there is no decode happened and there we take care
//of showing the fullscreen thumbnail.
- iObserver->HandleBitmapDecodedL(iThumbnailIndex,NULL);
- return;
+ iObserver->HandleBitmapDecodedL(iThumbnailIndex, NULL);
+ return;
}
}
SetActive();
}
}
+
// ---------------------------------------------------------------------------
// RunL
// ---------------------------------------------------------------------------
//
void CGlxBitmapDecoderWrapper::RunL()
{
- TRACER("CGlxBitmapDecoderWrapper:: RunL ");
+ TRACER("CGlxBitmapDecoderWrapper::RunL()");
if( iStatus == KErrNone )
{
iObserver->HandleBitmapDecodedL(iThumbnailIndex,iBitmap);
iBitmap = NULL;
//release the file held by decoder immediately.
- GLX_LOG_INFO( " CGlxBitmapDecoderWrapper::RunL:Decoding Finished" );
+ GLX_DEBUG1("CGlxBitmapDecoderWrapper::RunL:Decoding Finished");
iImageDecoder->Cancel();
delete iImageDecoder;
iImageDecoder = NULL;
#ifdef _DEBUG
iStopTime.HomeTime();
- GLX_DEBUG1("=== IMAGE DECODE ===");
- GLX_DEBUG2("=>Image Decode Took took <%d> us",
+ GLX_DEBUG2("*** Image Decode took <%d> us ***",
(TInt)iStopTime.MicroSecondsFrom(iStartTime).Int64());
#endif
}
}
+
// ---------------------------------------------------------------------------
// DoCancel
// ---------------------------------------------------------------------------
//
void CGlxBitmapDecoderWrapper::DoCancel()
{
- TRACER("CGlxBitmapDecoderWrapper:: DoCancel ");
+ TRACER("CGlxBitmapDecoderWrapper::DoCancel ");
if(iImageDecoder)
{
- GLX_LOG_INFO( " CGlxBitmapDecoderWrapper::DoCancel:Deleting" );
+ GLX_DEBUG1("CGlxBitmapDecoderWrapper::DoCancel iImageDecoder delete");
iImageDecoder->Cancel();
delete iImageDecoder;
iImageDecoder = NULL;
@@ -323,106 +332,84 @@
}
// ---------------------------------------------------------------------------
-// GetOrientationL
-// ---------------------------------------------------------------------------
-//
-TUint16 CGlxBitmapDecoderWrapper::GetOrientationL(const TDesC& aFileName)
- {
- TRACER("CGlxBitmapDecoderWrapper:: GetOrientationL ");
- //Get Exif Metadata and the orientation tag from the file first
- RFile file;
- CleanupClosePushL(file);
- User::LeaveIfError(file.Open(iFs,
- aFileName, EFileRead));
- TInt size;
- User::LeaveIfError(file.Size(size));
- if ( KGlxMaxExifSize < size )
- {
- size = KGlxMaxExifSize;
- }
- TUint16 orientation = 9;
- HBufC8* exifData = HBufC8::NewLC(size);
- TPtr8 ptr(exifData->Des());
- User::LeaveIfError(file.Read(ptr));
- CExifRead* exifReader = NULL;
- TRAPD(exifErr,exifReader = CExifRead::NewL(*exifData, CExifRead::ENoJpeg));
- if(exifErr == KErrNone)
- {
- CleanupStack::PushL(exifReader);
-
- TInt readErr = exifReader->GetOrientation(orientation);
- if(readErr != KErrNone)
- {
- orientation = 9;
- }
- CleanupStack::PopAndDestroy(exifReader);
- }
- CleanupStack::PopAndDestroy(exifData);
- //Close and pop file Session
- CleanupStack::PopAndDestroy(&file);
- return orientation;
-
- }
-// ---------------------------------------------------------------------------
-// DoCancel
-// ---------------------------------------------------------------------------
-//
-void CGlxBitmapDecoderWrapper::GetRotationParameters(TUint16 aOrientation, TInt& aRotAngle, TBool& aFlipStatus)
- {
- TRACER("CGlxBitmapDecoderWrapper:: DoCancel ");
- //Get the orientation and set rotation on the decoder
- //as well as update the original size
- aRotAngle = 0;
- aFlipStatus = EFalse;
- TInt isOrientationOdd = aOrientation%2;
- if(aOrientation>8)
- {
- return;
- }
- if(aOrientation >= 3 && aOrientation < 5)
- {
- aRotAngle = 180;
- }
- else if(aOrientation >= 5 && aOrientation < 7)
- {
- aRotAngle = 90;
-
- }
- else if(aOrientation >= 7 && aOrientation <= 8)
- {
- aRotAngle = 270;
- }
- if(aOrientation>4 )
- {
- if(isOrientationOdd )
- {
- aFlipStatus = ETrue;
- }
- }
-
- }
-
-// ---------------------------------------------------------------------------
// OOMRequestFreeMemoryL
// ---------------------------------------------------------------------------
//
-TInt CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL( TInt aBytesRequested)
+TInt CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL(TInt aBytesRequested)
{
TRACER("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL");
- GLX_LOG_INFO1("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL() aBytesRequested=%d",
- aBytesRequested);
+ GLX_LOG_INFO1("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL() "
+ "aBytesRequested=%d", aBytesRequested);
ROomMonitorSession oomMonitor;
- User::LeaveIfError( oomMonitor.Connect() );
+ User::LeaveIfError(oomMonitor.Connect());
// No leaving code after this point, so no need to use cleanup stack
// for oomMonitor
- TInt errorCode = oomMonitor.RequestFreeMemory( aBytesRequested );
- GLX_LOG_INFO1("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL(1) errorCode=%d",errorCode);
- if ( errorCode != KErrNone )
+ TInt errorCode = oomMonitor.RequestFreeMemory(aBytesRequested);
+ GLX_LOG_INFO1("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL(1) "
+ "errorCode=%d",errorCode);
+ if (errorCode != KErrNone)
{
// try one more time
- errorCode = oomMonitor.RequestFreeMemory( aBytesRequested );
- GLX_LOG_INFO1("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL(2) errorCode=%d",errorCode);
+ errorCode = oomMonitor.RequestFreeMemory(aBytesRequested);
+ GLX_LOG_INFO1("CGlxBitmapDecoderWrapper::OOMRequestFreeMemoryL(2) "
+ "errorCode=%d",errorCode);
}
oomMonitor.Close();
return errorCode;
}
+
+// -----------------------------------------------------------------------------
+// DoesMimeTypeNeedsRecalculateL()
+// -----------------------------------------------------------------------------
+//
+TBool CGlxBitmapDecoderWrapper::DoesMimeTypeNeedsRecalculateL()
+ {
+ TRACER("CGlxBitmapDecoderWrapper::DoesMimeTypeNeedsRecalculateL");
+ RApaLsSession session;
+ TDataType mimeType;
+ TUid uid;
+
+ User::LeaveIfError(session.Connect());
+ CleanupClosePushL(session);
+ User::LeaveIfError(session.AppForDocument(iImagePath->Des(), uid,
+ mimeType));
+ CleanupStack::PopAndDestroy(&session);
+
+ if (mimeType.Des().Compare(KMimeJpeg) == 0 || mimeType.Des().Compare(
+ KMimeJpg) == 0)
+ {
+ GLX_LOG_INFO("CGlxBitmapDecoderWrapper::DoesMimeTypeNeedsRecalculateL - jpeg");
+ return EFalse;
+ }
+ else
+ {
+ GLX_LOG_INFO("CGlxHdmiSurfaceUpdater::DoesMimeTypeNeedsRecalculateL - non jpeg");
+ return ETrue;
+ }
+ }
+
+// -----------------------------------------------------------------------------
+// ReCalculateSize
+// -----------------------------------------------------------------------------
+TSize CGlxBitmapDecoderWrapper::ReCalculateSizeL()
+ {
+ TRACER("CGlxBitmapDecoderWrapper::ReCalculateSizeL()");
+ if (DoesMimeTypeNeedsRecalculateL())
+ {
+ TSize fullFrameSize = iImageDecoder->FrameInfo().iOverallSizeInPixels;
+ // calculate the reduction factor on what size we need
+ TInt reductionFactor = iImageDecoder->ReductionFactor(fullFrameSize,
+ iTargetBitmapSize);
+ // get the reduced size onto destination size
+ TSize destSize;
+ User::LeaveIfError(iImageDecoder->ReducedSize(fullFrameSize,
+ reductionFactor, destSize));
+ GLX_LOG_INFO2("CGlxBitmapDecoderWrapper::ReCalculateSizeL() "
+ "destSize=%d, %d",destSize.iWidth,destSize.iHeight);
+ return destSize;
+ }
+ else
+ {
+ return iTargetBitmapSize;
+ }
+ }