198 // |
198 // |
199 void CWmImageConverter::CreateIconFromUidL( const TUid& aUid ) |
199 void CWmImageConverter::CreateIconFromUidL( const TUid& aUid ) |
200 { |
200 { |
201 CFbsBitmap* bitmap = NULL; |
201 CFbsBitmap* bitmap = NULL; |
202 CFbsBitmap* mask = NULL; |
202 CFbsBitmap* mask = NULL; |
203 |
203 |
|
204 |
204 if ( aUid.iUid >= KWidgetUidLowerBound && |
205 if ( aUid.iUid >= KWidgetUidLowerBound && |
205 aUid.iUid < KWidgetUidUpperBound ) |
206 aUid.iUid < KWidgetUidUpperBound ) |
206 { |
207 { |
207 // AknsUtils::CreateAppIconLC panics incase of WRT |
|
208 |
|
209 RApaLsSession lsSession; |
208 RApaLsSession lsSession; |
210 User::LeaveIfError( lsSession.Connect() ); |
209 User::LeaveIfError( lsSession.Connect() ); |
211 CleanupClosePushL( lsSession ); |
210 CleanupClosePushL( lsSession ); |
212 |
211 |
213 const TInt KAppSizeArraySize = 3; |
212 const TInt KAppSizeArraySize = 3; |
214 CArrayFixFlat<TSize>* sizeArray = new (ELeave) |
213 CArrayFixFlat<TSize>* sizeArray = new (ELeave) |
215 CArrayFixFlat<TSize>( KAppSizeArraySize ); |
214 CArrayFixFlat<TSize>( KAppSizeArraySize ); |
216 CleanupStack::PushL( sizeArray ); |
215 CleanupStack::PushL( sizeArray ); |
|
216 |
217 User::LeaveIfError( lsSession.GetAppIconSizes( aUid, *sizeArray ) ); |
217 User::LeaveIfError( lsSession.GetAppIconSizes( aUid, *sizeArray ) ); |
218 TSize size; |
218 |
|
219 // there should be atleast one size available |
|
220 if ( sizeArray->Count() == 0 ){ User::Leave( KErrNotReady ); }; |
|
221 |
|
222 TSize size(0,0); |
219 for( TInt i=0; i < sizeArray->Count(); i++ ) |
223 for( TInt i=0; i < sizeArray->Count(); i++ ) |
220 { |
224 { |
221 size = (*sizeArray)[i]; |
225 TSize s = (*sizeArray)[i]; |
222 if ( size == iSize ) |
226 if ( size.iWidth < s.iWidth || size.iHeight < s.iHeight ) |
223 { |
227 { size = s; } |
224 break; |
228 if ( size == iSize ) { break; } |
225 } |
229 } |
226 } |
230 |
227 CApaMaskedBitmap* maskedBmp = CApaMaskedBitmap::NewLC(); |
231 CApaMaskedBitmap* maskedBmp = CApaMaskedBitmap::NewLC(); |
228 User::LeaveIfError( lsSession.GetAppIcon( aUid, size, *maskedBmp ) ); |
232 User::LeaveIfError( lsSession.GetAppIcon( aUid, size, *maskedBmp ) ); |
229 iBitmap = static_cast<CFbsBitmap*>( maskedBmp ); // ownership transfered |
|
230 |
233 |
231 iMask = new ( ELeave ) CFbsBitmap; |
234 // handle bitmap |
232 User::LeaveIfError( iMask->Create( |
235 iBitmap = new ( ELeave ) CFbsBitmap; |
233 maskedBmp->Mask()->SizeInPixels(), |
236 User::LeaveIfError( iBitmap->Create( |
234 maskedBmp->Mask()->DisplayMode() ) ); |
237 maskedBmp->SizeInPixels(), |
235 // duplicate mask, origional is owned by maskedBmp |
238 maskedBmp->DisplayMode() ) ); |
236 iMask->Duplicate( maskedBmp->Mask()->Handle() ); |
239 |
237 CleanupStack::Pop( maskedBmp ); |
240 // scale bitmap |
238 maskedBmp = NULL; |
241 ScaleBitmapL( iSize, iBitmap, maskedBmp ); |
239 CleanupStack::PopAndDestroy(sizeArray); |
242 |
|
243 // handle mask |
|
244 if ( maskedBmp->Mask() ) |
|
245 { |
|
246 iMask = new ( ELeave ) CFbsBitmap; |
|
247 User::LeaveIfError( iMask->Create( |
|
248 maskedBmp->Mask()->SizeInPixels(), |
|
249 maskedBmp->Mask()->DisplayMode() ) ); |
|
250 |
|
251 // scale mask |
|
252 ScaleBitmapL( iSize, iMask, maskedBmp->Mask() ); |
|
253 } |
|
254 |
|
255 // cleanup |
|
256 CleanupStack::PopAndDestroy( maskedBmp ); |
|
257 CleanupStack::PopAndDestroy( sizeArray ); |
240 CleanupStack::PopAndDestroy( &lsSession ); |
258 CleanupStack::PopAndDestroy( &lsSession ); |
241 |
259 |
242 // scale or notify |
260 // notify |
243 if ( size == iSize ) |
261 iState = EIdle; |
244 { |
262 iObserver->NotifyCompletion( KErrNone ); |
245 iState = EIdle; |
|
246 iObserver->NotifyCompletion( KErrNone ); |
|
247 } |
|
248 else |
|
249 { |
|
250 iScaleNeeded = ETrue; |
|
251 ScaleBitmap( iSize.iWidth, iSize.iHeight ); |
|
252 } |
|
253 } |
263 } |
254 else if ( aUid.iUid != KNullUid.iUid ) |
264 else if ( aUid.iUid != KNullUid.iUid ) |
255 { |
265 { |
256 MAknsSkinInstance* skin = AknsUtils::SkinInstance(); |
266 MAknsSkinInstance* skin = AknsUtils::SkinInstance(); |
257 TInt err( KErrNone ); |
267 TInt err( KErrNone ); |
931 User::Leave( err ); |
941 User::Leave( err ); |
932 } |
942 } |
933 } |
943 } |
934 |
944 |
935 // --------------------------------------------------------------------------- |
945 // --------------------------------------------------------------------------- |
|
946 // CWmImageConverter::DoesScaleBitmapUseFallBack |
|
947 // --------------------------------------------------------------------------- |
|
948 // |
|
949 TBool CWmImageConverter::DoesScaleBitmapUseFallBack( CFbsBitmap* aSrcBitmap ) |
|
950 { |
|
951 if ( !aSrcBitmap ) |
|
952 { |
|
953 return EFalse; |
|
954 } |
|
955 |
|
956 TDisplayMode displayMode = aSrcBitmap->DisplayMode(); |
|
957 TBool fallbackOnly = EFalse; |
|
958 |
|
959 switch ( displayMode ) |
|
960 { |
|
961 case EGray2: |
|
962 case EGray4: |
|
963 case EGray16: |
|
964 case EColor16: |
|
965 case EColor16M: |
|
966 case ERgb: |
|
967 case EColor16MA: |
|
968 fallbackOnly = ETrue; |
|
969 break; |
|
970 case EGray256: |
|
971 case EColor4K: |
|
972 case EColor64K: |
|
973 case EColor256: |
|
974 case EColor16MU: |
|
975 // These are the supported modes |
|
976 break; |
|
977 default: |
|
978 fallbackOnly = ETrue; |
|
979 } |
|
980 |
|
981 return fallbackOnly; |
|
982 } |
|
983 |
|
984 |
|
985 // --------------------------------------------------------------------------- |
|
986 // CWmImageConverter::ScaleBitmapL |
|
987 // --------------------------------------------------------------------------- |
|
988 // |
|
989 void CWmImageConverter::ScaleBitmapL( |
|
990 const TSize& aSize, |
|
991 CFbsBitmap* aTrgBitmap, |
|
992 CFbsBitmap* aSrcBitmap ) |
|
993 { |
|
994 if ( !aSrcBitmap ) User::Leave( KErrArgument ); |
|
995 if ( !aTrgBitmap ) User::Leave( KErrArgument ); |
|
996 if ( aSrcBitmap->DisplayMode() != aTrgBitmap->DisplayMode() ) |
|
997 { |
|
998 User::Leave( KErrArgument ); |
|
999 } |
|
1000 |
|
1001 TRect targetRect( aSize ); |
|
1002 |
|
1003 // calculate aspect ratio |
|
1004 TInt srcHeight = aSrcBitmap->SizeInPixels().iHeight; |
|
1005 TInt srcWidth = aSrcBitmap->SizeInPixels().iWidth; |
|
1006 TReal scaleRatio( 1 ); //no scale as defaul |
|
1007 |
|
1008 //If any dimension is 0, then we do not bother to scale |
|
1009 if ( targetRect.Width() > 0 && targetRect.Height() > 0 ) |
|
1010 { |
|
1011 TReal xRatio = ( ( TReal )srcWidth / ( TReal )targetRect.Width() ); |
|
1012 TReal yRatio = ( ( TReal )srcHeight / ( TReal )targetRect.Height() ); |
|
1013 //Find out appropriate scaling factor |
|
1014 xRatio > yRatio ? ( scaleRatio = xRatio ) : ( scaleRatio = yRatio ); |
|
1015 } |
|
1016 |
|
1017 //Scale the size for target bitmap |
|
1018 targetRect.SetHeight( srcHeight / scaleRatio ); |
|
1019 targetRect.SetWidth( srcWidth / scaleRatio ); |
|
1020 |
|
1021 TSize trgBitmapSize = aTrgBitmap->SizeInPixels(); |
|
1022 |
|
1023 // calculate the valid drawing area |
|
1024 TRect drawRect = targetRect; |
|
1025 drawRect.Intersection( TRect( TPoint( 0, 0 ), trgBitmapSize ) ); |
|
1026 |
|
1027 if( drawRect.IsEmpty() || |
|
1028 aSrcBitmap->SizeInPixels().iHeight <= 0 || |
|
1029 aSrcBitmap->SizeInPixels().iWidth <= 0 ) |
|
1030 { |
|
1031 User::Leave( KErrArgument ); |
|
1032 } |
|
1033 |
|
1034 TSize srcSize = aSrcBitmap->SizeInPixels(); |
|
1035 |
|
1036 TBool srcTemporary = EFalse; |
|
1037 if ( aSrcBitmap->IsRomBitmap() ) |
|
1038 { |
|
1039 srcTemporary = ETrue; |
|
1040 } |
|
1041 |
|
1042 TDisplayMode displayMode = aSrcBitmap->DisplayMode(); |
|
1043 TBool fallbackOnly = DoesScaleBitmapUseFallBack( aSrcBitmap ); |
|
1044 |
|
1045 if ( fallbackOnly ) |
|
1046 { |
|
1047 CFbsBitmapDevice* dev = CFbsBitmapDevice::NewL( aTrgBitmap ); |
|
1048 CleanupStack::PushL( dev ); |
|
1049 CFbsBitGc* gc = NULL; |
|
1050 User::LeaveIfError( dev->CreateContext( gc ) ); |
|
1051 CleanupStack::PushL( gc ); |
|
1052 |
|
1053 // write alpha information if it exists |
|
1054 if ( aSrcBitmap->DisplayMode() == EColor16MA ) |
|
1055 { |
|
1056 gc->SetDrawMode( CGraphicsContext::EDrawModeWriteAlpha ); |
|
1057 } |
|
1058 |
|
1059 // targetRect is used because DrawBitmap handles clipping automatically |
|
1060 gc->DrawBitmap( targetRect, aSrcBitmap ); |
|
1061 CleanupStack::PopAndDestroy( 2 ); // dev, gc |
|
1062 return; |
|
1063 } |
|
1064 |
|
1065 // Heap lock for FBServ large chunk to prevent background |
|
1066 // compression of aSrcBitmap after if IsCompressedInRAM returns EFalse |
|
1067 aSrcBitmap->LockHeapLC( ETrue ); // fbsheaplock |
|
1068 TBool fbsHeapLock = ETrue; |
|
1069 if ( aSrcBitmap->IsCompressedInRAM() ) |
|
1070 { |
|
1071 srcTemporary = ETrue; |
|
1072 } |
|
1073 |
|
1074 CFbsBitmap* realSource = aSrcBitmap; |
|
1075 if ( srcTemporary ) |
|
1076 { |
|
1077 CleanupStack::PopAndDestroy(); // fbsheaplock |
|
1078 fbsHeapLock = EFalse; |
|
1079 |
|
1080 realSource = new ( ELeave ) CFbsBitmap(); |
|
1081 CleanupStack::PushL( realSource ); |
|
1082 User::LeaveIfError( |
|
1083 realSource->Create( srcSize, aSrcBitmap->DisplayMode() ) ); |
|
1084 CFbsBitmapDevice* dev = CFbsBitmapDevice::NewL( realSource ); |
|
1085 CleanupStack::PushL( dev ); |
|
1086 CFbsBitGc* gc = NULL; |
|
1087 User::LeaveIfError( dev->CreateContext( gc ) ); |
|
1088 CleanupStack::PushL( gc ); |
|
1089 gc->BitBlt( TPoint( 0, 0 ), aSrcBitmap ); |
|
1090 CleanupStack::PopAndDestroy( 2 ); // dev, gc |
|
1091 } |
|
1092 |
|
1093 if ( !fbsHeapLock ) |
|
1094 { |
|
1095 // Heap lock for FBServ large chunk is only needed with large bitmaps. |
|
1096 if ( realSource->IsLargeBitmap() || aTrgBitmap->IsLargeBitmap() ) |
|
1097 { |
|
1098 aTrgBitmap->LockHeapLC( ETrue ); // fbsheaplock |
|
1099 } |
|
1100 else |
|
1101 { |
|
1102 CleanupStack::PushL( ( TAny* )NULL ); |
|
1103 } |
|
1104 } |
|
1105 |
|
1106 TUint32* srcAddress = realSource->DataAddress(); |
|
1107 TUint32* trgAddress = aTrgBitmap->DataAddress(); |
|
1108 |
|
1109 const TInt xSkip = ( srcSize.iWidth << 8 ) / targetRect.Width(); |
|
1110 const TInt ySkip = ( srcSize.iHeight << 8 ) / targetRect.Height(); |
|
1111 |
|
1112 const TInt drawWidth = drawRect.Width(); |
|
1113 const TInt drawHeight = drawRect.Height(); |
|
1114 |
|
1115 TRect offsetRect( targetRect.iTl, drawRect.iTl ); |
|
1116 const TInt yPosOffset = ySkip * offsetRect.Height(); |
|
1117 const TInt xPosOffset = xSkip * offsetRect.Width(); |
|
1118 |
|
1119 if ( ( displayMode == EGray256 ) || ( displayMode == EColor256 ) ) |
|
1120 { |
|
1121 TInt srcScanLen8 = CFbsBitmap::ScanLineLength( |
|
1122 srcSize.iWidth, displayMode ); |
|
1123 TInt trgScanLen8 = CFbsBitmap::ScanLineLength( |
|
1124 trgBitmapSize.iWidth, displayMode ); |
|
1125 |
|
1126 TUint8* trgAddress8 = reinterpret_cast< TUint8* >( trgAddress ); |
|
1127 |
|
1128 TInt yPos = yPosOffset; |
|
1129 // skip left and top margins in the beginning |
|
1130 trgAddress8 += trgScanLen8 * drawRect.iTl.iY + drawRect.iTl.iX; |
|
1131 |
|
1132 for ( TInt y = 0; y < drawHeight; y++ ) |
|
1133 { |
|
1134 TUint8* srcAddress8 = reinterpret_cast< TUint8* >( srcAddress ) + |
|
1135 ( srcScanLen8 * ( yPos >> 8 ) ); |
|
1136 |
|
1137 TInt xPos = xPosOffset; |
|
1138 for ( TInt x = 0; x < drawWidth; x++ ) |
|
1139 { |
|
1140 *( trgAddress8++ ) = srcAddress8[xPos >> 8]; |
|
1141 xPos += xSkip; |
|
1142 } |
|
1143 |
|
1144 yPos += ySkip; |
|
1145 |
|
1146 trgAddress8 += trgScanLen8 - drawWidth; |
|
1147 } |
|
1148 } |
|
1149 else if ( displayMode == EColor4K || displayMode == EColor64K ) |
|
1150 { |
|
1151 TInt srcScanLen16 = CFbsBitmap::ScanLineLength( |
|
1152 srcSize.iWidth, displayMode ) /2; |
|
1153 TInt trgScanLen16 = CFbsBitmap::ScanLineLength( |
|
1154 trgBitmapSize.iWidth, displayMode ) /2; |
|
1155 |
|
1156 TUint16* trgAddress16 = reinterpret_cast< TUint16* >( trgAddress ); |
|
1157 |
|
1158 TInt yPos = yPosOffset; |
|
1159 // skip left and top margins in the beginning |
|
1160 trgAddress16 += trgScanLen16 * drawRect.iTl.iY + drawRect.iTl.iX; |
|
1161 |
|
1162 for ( TInt y = 0; y < drawHeight; y++ ) |
|
1163 { |
|
1164 TUint16* srcAddress16 = reinterpret_cast< TUint16* >( srcAddress ) + |
|
1165 ( srcScanLen16 * ( yPos >> 8 ) ); |
|
1166 |
|
1167 TInt xPos = xPosOffset; |
|
1168 for ( TInt x = 0; x < drawWidth; x++ ) |
|
1169 { |
|
1170 *( trgAddress16++ ) = srcAddress16[xPos >> 8]; |
|
1171 xPos += xSkip; |
|
1172 } |
|
1173 |
|
1174 yPos += ySkip; |
|
1175 |
|
1176 trgAddress16 += trgScanLen16 - drawWidth; |
|
1177 } |
|
1178 } |
|
1179 else if ( displayMode == EColor16MU ) |
|
1180 { |
|
1181 TInt srcScanLen32 = CFbsBitmap::ScanLineLength( |
|
1182 srcSize.iWidth, displayMode ) /4; |
|
1183 TInt trgScanLen32 = CFbsBitmap::ScanLineLength( |
|
1184 trgBitmapSize.iWidth, displayMode ) /4; |
|
1185 |
|
1186 TUint32* trgAddress32 = reinterpret_cast< TUint32* >( trgAddress ); |
|
1187 |
|
1188 TInt yPos = yPosOffset; |
|
1189 // skip left and top margins in the beginning |
|
1190 trgAddress32 += trgScanLen32 * drawRect.iTl.iY + drawRect.iTl.iX; |
|
1191 |
|
1192 for ( TInt y = 0; y < drawHeight; y++ ) |
|
1193 { |
|
1194 TUint32* srcAddress32 = reinterpret_cast< TUint32* >( srcAddress ) + |
|
1195 ( srcScanLen32 * ( yPos >> 8 ) ); |
|
1196 |
|
1197 TInt xPos = xPosOffset; |
|
1198 for ( TInt x = 0; x < drawWidth; x++ ) |
|
1199 { |
|
1200 *( trgAddress32++ ) = srcAddress32[xPos >> 8]; |
|
1201 xPos += xSkip; |
|
1202 } |
|
1203 |
|
1204 yPos += ySkip; |
|
1205 |
|
1206 trgAddress32 += trgScanLen32 - drawWidth; |
|
1207 } |
|
1208 } |
|
1209 else |
|
1210 { |
|
1211 User::Leave( KErrUnknown ); |
|
1212 } |
|
1213 |
|
1214 CleanupStack::PopAndDestroy(); // fbsheaplock |
|
1215 |
|
1216 if ( srcTemporary ) |
|
1217 { |
|
1218 CleanupStack::PopAndDestroy(); // realSource |
|
1219 } |
|
1220 } |
|
1221 |
|
1222 // --------------------------------------------------------------------------- |
936 // CWmImageConverter::Finished |
1223 // CWmImageConverter::Finished |
937 // --------------------------------------------------------------------------- |
1224 // --------------------------------------------------------------------------- |
938 // |
1225 // |
939 void CWmImageConverter::Finished() |
1226 void CWmImageConverter::Finished() |
940 { |
1227 { |