os/graphics/graphicsdeviceinterface/screendriver/tsrc/TLLD.CPP
author sl@SLION-WIN7.fritz.box
Fri, 15 Jun 2012 03:10:57 +0200
changeset 0 bde4ae8d615e
permissions -rw-r--r--
First public contribution.
sl@0
     1
// Copyright (c) 1997-2009 Nokia Corporation and/or its subsidiary(-ies).
sl@0
     2
// All rights reserved.
sl@0
     3
// This component and the accompanying materials are made available
sl@0
     4
// under the terms of "Eclipse Public License v1.0"
sl@0
     5
// which accompanies this distribution, and is available
sl@0
     6
// at the URL "http://www.eclipse.org/legal/epl-v10.html".
sl@0
     7
//
sl@0
     8
// Initial Contributors:
sl@0
     9
// Nokia Corporation - initial contribution.
sl@0
    10
//
sl@0
    11
// Contributors:
sl@0
    12
//
sl@0
    13
// Description:
sl@0
    14
//
sl@0
    15
sl@0
    16
#include <e32math.h>
sl@0
    17
#include <hal.h>
sl@0
    18
#include <bitdraw.h>
sl@0
    19
#include "Tlld.h"
sl@0
    20
#include <bitdrawinterfaceid.h>
sl@0
    21
#include <bmalphablend.h>
sl@0
    22
#include <graphics/lookuptable.h>
sl@0
    23
#include <graphics/blendingalgorithms.h>
sl@0
    24
#include <graphics/gdi/gdiconsts.h>
sl@0
    25
#include "BMDRAW.H"
sl@0
    26
sl@0
    27
GLREF_C TInt ByteSize(TDisplayMode aDisplayMode,TInt aWidth);
sl@0
    28
sl@0
    29
TInt KNumberDisplayModes1 = sizeof (TestDisplayMode1) / sizeof (TestDisplayMode1[0]);
sl@0
    30
sl@0
    31
#if defined(SYMBIAN_USE_FAST_FADING)
sl@0
    32
const TBool KFastFading = ETrue;
sl@0
    33
#else
sl@0
    34
const TBool KFastFading = EFalse;
sl@0
    35
#endif
sl@0
    36
sl@0
    37
//these are for EColor16MAP testing
sl@0
    38
const TInt KInaccuracyLimit = 15;
sl@0
    39
const TInt KUserDispModes = 2;
sl@0
    40
//The array below is used in CTLowLevel::TestWriteRGBAlpha() to step through display modes,
sl@0
    41
//to ensure adequate test coverage.
sl@0
    42
const TDisplayMode UserDisplayModes[KUserDispModes] =
sl@0
    43
	{
sl@0
    44
	ENone,
sl@0
    45
	EColor16MAP,
sl@0
    46
	};
sl@0
    47
const TInt KMaskFill =3;
sl@0
    48
const TUint32 MaskFill[KMaskFill] =
sl@0
    49
	{
sl@0
    50
	0x00,
sl@0
    51
	0xff,
sl@0
    52
	0x3A,
sl@0
    53
	};
sl@0
    54
sl@0
    55
TInt DisplayMode2Index(TDisplayMode aMode)
sl@0
    56
	{
sl@0
    57
	TInt i;
sl@0
    58
	for(i=0;i<KNumDispModes;i++)
sl@0
    59
		{
sl@0
    60
		if(TestDisplayMode[i] == aMode)
sl@0
    61
			break;
sl@0
    62
		}
sl@0
    63
	return i;
sl@0
    64
	}
sl@0
    65
sl@0
    66
inline TInt AbsDiff(TInt aValue1, TInt aValue2)
sl@0
    67
	{
sl@0
    68
	return (aValue1 < aValue2) ? (aValue2-aValue1) : (aValue1-aValue2);
sl@0
    69
	}
sl@0
    70
sl@0
    71
//CTLowLevel implementation is shared between TLLD and TLLD2 test apps.
sl@0
    72
//The change was made because the original TLLD test app took too much time (over 0.5 hour)
sl@0
    73
//and usually was terminated with a TIMEOUT on LUBBOCK device.
sl@0
    74
CTLowLevel::CTLowLevel(CTestStep* aStep):
sl@0
    75
	CTGraphicsBase(aStep),
sl@0
    76
	iDrawDevice(NULL),
sl@0
    77
	iBits(NULL),
sl@0
    78
	iBuf(NULL),
sl@0
    79
	iDispMode(ENone),
sl@0
    80
	iUserDispMode(ENone),
sl@0
    81
	iOrientation(CFbsDrawDevice::EOrientationNormal),
sl@0
    82
	iSize(TSize(0,0)),
sl@0
    83
	iLongWidth(0),
sl@0
    84
	iTestNo(0),
sl@0
    85
	iIteration(0),
sl@0
    86
	iReportIteration(0),
sl@0
    87
	iTotalReportIterations(0),
sl@0
    88
	iFuzzyMatch(EFalse),
sl@0
    89
	iBlendTestColors(ETrue),
sl@0
    90
	iUseFastFade(EFalse)
sl@0
    91
	{
sl@0
    92
	iColorConvertor[ENone] = &iNullConvertor;
sl@0
    93
	iColorConvertor[EGray2] = &iGray2Convertor;
sl@0
    94
	iColorConvertor[EGray4] = &iGray4Convertor;
sl@0
    95
	iColorConvertor[EGray16] = &iGray16Convertor;
sl@0
    96
	iColorConvertor[EGray256] = &iGray256Convertor;
sl@0
    97
	iColorConvertor[EColor16] = &iColor16Convertor;
sl@0
    98
	iColorConvertor[EColor256] = &iColor256Convertor;
sl@0
    99
	iColorConvertor[EColor4K] = &iColor4KConvertor;
sl@0
   100
	iColorConvertor[EColor64K] = &iColor64KConvertor;
sl@0
   101
	iColorConvertor[EColor16M] = &iColor16MConvertor;
sl@0
   102
	iColorConvertor[ERgb] = &iColor16MConvertor;
sl@0
   103
	iColorConvertor[EColor16MU] = &iColor16MUConvertor;
sl@0
   104
	iColorConvertor[EColor16MA] = &iColor16MAConvertor;
sl@0
   105
	iColorConvertor[EColor16MAP] = &iColor16MAPConvertor;
sl@0
   106
	iOrientation = CFbsDrawDevice::EOrientationNormal;
sl@0
   107
	iOrientationEnd = CFbsDrawDevice::EOrientationRotated90;
sl@0
   108
	}
sl@0
   109
sl@0
   110
CTLowLevel::~CTLowLevel()
sl@0
   111
	{
sl@0
   112
	Reset();
sl@0
   113
	}
sl@0
   114
sl@0
   115
void CTLowLevel::Reset()
sl@0
   116
	{
sl@0
   117
	delete iDrawDevice;
sl@0
   118
	iDrawDevice = NULL;
sl@0
   119
sl@0
   120
	delete iBits;
sl@0
   121
	iBits = NULL;
sl@0
   122
	delete iBuf;
sl@0
   123
	iBuf = NULL;
sl@0
   124
	iDispMode = ENone;
sl@0
   125
	iSize.SetSize(0,0);
sl@0
   126
	iLongWidth = 0;
sl@0
   127
	}
sl@0
   128
sl@0
   129
void CTLowLevel::RunTestCaseL(TInt aCurTestCase)
sl@0
   130
	{
sl@0
   131
    ((CTLowLevelStep*)iStep)->SetTestStepID(KUnknownSYMTestCaseIDName);
sl@0
   132
	switch(aCurTestCase)
sl@0
   133
		{
sl@0
   134
	case 1:
sl@0
   135
		INFO_PRINTF1(_L("Bitmap device EGray2"));
sl@0
   136
/**
sl@0
   137
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0004
sl@0
   138
*/
sl@0
   139
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0004"));
sl@0
   140
		TestBitmapDraw(EGray2,TSize(128,100));
sl@0
   141
		break;
sl@0
   142
	case 2:
sl@0
   143
		INFO_PRINTF1(_L("Bitmap device EGray4"));
sl@0
   144
/**
sl@0
   145
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0005
sl@0
   146
*/
sl@0
   147
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0005"));
sl@0
   148
		TestBitmapDraw(EGray4,TSize(112,100));
sl@0
   149
		break;
sl@0
   150
	case 3:
sl@0
   151
		INFO_PRINTF1(_L("Bitmap device EGray16"));
sl@0
   152
/**
sl@0
   153
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0006
sl@0
   154
*/
sl@0
   155
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0006"));
sl@0
   156
		TestBitmapDraw(EGray16,TSize(104,100));
sl@0
   157
		break;
sl@0
   158
	case 4:
sl@0
   159
		INFO_PRINTF1(_L("Bitmap device EGray256"));
sl@0
   160
/**
sl@0
   161
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0007
sl@0
   162
*/
sl@0
   163
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0007"));
sl@0
   164
		TestBitmapDraw(EGray256,TSize(104,100));
sl@0
   165
		break;
sl@0
   166
	case 5:
sl@0
   167
		INFO_PRINTF1(_L("Bitmap device EColor16"));
sl@0
   168
/**
sl@0
   169
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0008
sl@0
   170
*/
sl@0
   171
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0008"));
sl@0
   172
		TestBitmapDraw(EColor16,TSize(104,100));
sl@0
   173
		break;
sl@0
   174
	case 6:
sl@0
   175
		INFO_PRINTF1(_L("Bitmap device EColor256"));
sl@0
   176
/**
sl@0
   177
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0009
sl@0
   178
*/
sl@0
   179
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0009"));
sl@0
   180
		TestBitmapDraw(EColor256,TSize(102,100));
sl@0
   181
		break;
sl@0
   182
	case 7:
sl@0
   183
		INFO_PRINTF1(_L("Bitmap device EColor4K"));
sl@0
   184
/**
sl@0
   185
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0010
sl@0
   186
*/
sl@0
   187
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0010"));
sl@0
   188
		TestBitmapDraw(EColor4K,TSize(100,100));
sl@0
   189
		break;
sl@0
   190
	case 8:
sl@0
   191
		INFO_PRINTF1(_L("Bitmap device EColor64K"));
sl@0
   192
/**
sl@0
   193
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0011
sl@0
   194
*/
sl@0
   195
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0011"));
sl@0
   196
		TestBitmapDraw(EColor64K,TSize(100,100));
sl@0
   197
		break;
sl@0
   198
	case 9:
sl@0
   199
		INFO_PRINTF1(_L("Bitmap device EColor16M"));
sl@0
   200
/**
sl@0
   201
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0012
sl@0
   202
*/
sl@0
   203
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0012"));
sl@0
   204
		TestBitmapDraw(EColor16M,TSize(102,100));
sl@0
   205
		break;
sl@0
   206
	case 10:
sl@0
   207
		INFO_PRINTF1(_L("Bitmap device EColor16MU"));
sl@0
   208
		iFuzzyMatch=ETrue;
sl@0
   209
/**
sl@0
   210
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0013
sl@0
   211
*/
sl@0
   212
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0013"));
sl@0
   213
		TestBitmapDraw(EColor16MU,TSize(102,100));
sl@0
   214
		iFuzzyMatch=EFalse;
sl@0
   215
		break;
sl@0
   216
	case 11:
sl@0
   217
		INFO_PRINTF1(_L("Bitmap device EColor16MA"));
sl@0
   218
/**
sl@0
   219
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0014
sl@0
   220
*/
sl@0
   221
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0014"));
sl@0
   222
		TestBitmapDraw(EColor16MA,TSize(102,100));
sl@0
   223
		break;
sl@0
   224
	case 12:
sl@0
   225
		INFO_PRINTF1(_L("Bitmap device EColor16MAP"));
sl@0
   226
		iFuzzyMatch=ETrue;
sl@0
   227
/**
sl@0
   228
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0015
sl@0
   229
*/
sl@0
   230
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0015"));
sl@0
   231
		TestBitmapDraw(EColor16MAP,TSize(102,100));
sl@0
   232
		iFuzzyMatch=EFalse;
sl@0
   233
		break;
sl@0
   234
	case 13:
sl@0
   235
		INFO_PRINTF1(_L("User display mode mapping"));
sl@0
   236
/**
sl@0
   237
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0016
sl@0
   238
*/
sl@0
   239
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0016"));
sl@0
   240
		TestUserDisplayModeMapping();
sl@0
   241
		((CTLowLevelStep*)iStep)->RecordTestResultL();
sl@0
   242
		break;
sl@0
   243
	default:
sl@0
   244
		if(iOrientation <= iOrientationEnd)
sl@0
   245
			{
sl@0
   246
/**
sl@0
   247
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0017
sl@0
   248
*/
sl@0
   249
			((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0017"));
sl@0
   250
			INFO_PRINTF2(_L("Screen device : %S"), &DisplayModeNames1[iCurScreenDeviceModeIndex]);
sl@0
   251
			TDisplayMode display = TestDisplayMode1[iCurScreenDeviceModeIndex++];
sl@0
   252
			TestScreenDrawL(display);
sl@0
   253
			if(iCurScreenDeviceModeIndex >= KNumberDisplayModes1)
sl@0
   254
				{
sl@0
   255
				iCurScreenDeviceModeIndex = 0;
sl@0
   256
				iOrientation ++;
sl@0
   257
				}
sl@0
   258
			}
sl@0
   259
		else
sl@0
   260
			{
sl@0
   261
            ((CTLowLevelStep*)iStep)->SetTestStepID(KNotATestSYMTestCaseIDName);
sl@0
   262
			((CTLowLevelStep*)iStep)->CloseTMSGraphicsStep();
sl@0
   263
			TestComplete();
sl@0
   264
			((CTLowLevelStep*)iStep)->RecordTestResultL();
sl@0
   265
			}
sl@0
   266
		break;
sl@0
   267
		}
sl@0
   268
	}
sl@0
   269
sl@0
   270
/* this function is used for likeness matching, using a fixed inaccuracy */
sl@0
   271
void CTLowLevel::CheckMatch(TUint32 aFirst,TUint32 aSecond)
sl@0
   272
	{
sl@0
   273
	TBool fail=EFalse;
sl@0
   274
	if (iFuzzyMatch==EFalse)
sl@0
   275
		fail|=Check(aFirst==aSecond);
sl@0
   276
	else
sl@0
   277
		{
sl@0
   278
		TUint8* val1=static_cast<TUint8*>(static_cast<void*>(&aFirst));
sl@0
   279
		TUint8* val2=static_cast<TUint8*>(static_cast<void*>(&aSecond));
sl@0
   280
		fail|=Check(AbsDiff(*val1,*val2)<KInaccuracyLimit);
sl@0
   281
		fail|=Check(AbsDiff(*(val1+1),*(val2+1))<KInaccuracyLimit);
sl@0
   282
		fail|=Check(AbsDiff(*(val1+2),*(val2+2))<KInaccuracyLimit);
sl@0
   283
		fail|=Check(AbsDiff(*(val1+3),*(val2+3))<KInaccuracyLimit);
sl@0
   284
		}
sl@0
   285
	if (fail)
sl@0
   286
		{
sl@0
   287
		_LIT(KLog,"The values 0x%x and 0x%x don't match, fuzzyMatch=%d (limit=%d)");
sl@0
   288
		INFO_PRINTF5(KLog,aFirst,aSecond,iFuzzyMatch,KInaccuracyLimit);
sl@0
   289
		}
sl@0
   290
	}
sl@0
   291
sl@0
   292
void CTLowLevel::TestScreenDrawL(TDisplayMode aDisplayMode)
sl@0
   293
	{
sl@0
   294
	TUint startTime=User::TickCount();
sl@0
   295
sl@0
   296
	Reset();
sl@0
   297
sl@0
   298
	iDispMode = aDisplayMode;
sl@0
   299
sl@0
   300
	INFO_PRINTF1(_L("\n"));
sl@0
   301
	INFO_PRINTF2(_L("Testing Screen driver \"%S\""), &(DisplayModeNames[::DisplayMode2Index(aDisplayMode)]));
sl@0
   302
	INFO_PRINTF1(_L("\r\n"));
sl@0
   303
	TInt address = NULL;
sl@0
   304
	TSize size(0,0);
sl@0
   305
sl@0
   306
	User::LeaveIfError(HAL::Get(KDefaultScreenNo, HALData::EDisplayMemoryAddress,address));
sl@0
   307
	User::LeaveIfError(HAL::Get(KDefaultScreenNo, HALData::EDisplayXPixels,size.iWidth));
sl@0
   308
	User::LeaveIfError(HAL::Get(KDefaultScreenNo, HALData::EDisplayYPixels,size.iHeight));
sl@0
   309
	ASSERT(size.iWidth > 0 && size.iHeight > 0 && address != NULL);
sl@0
   310
sl@0
   311
	TPckgBuf<TScreenInfoV01> info;
sl@0
   312
	info().iScreenAddressValid = ETrue;
sl@0
   313
	info().iScreenAddress = REINTERPRET_CAST(TAny*,address);
sl@0
   314
	info().iScreenSize = size;
sl@0
   315
sl@0
   316
	TRAPD(ret,iDrawDevice = CFbsDrawDevice::NewScreenDeviceL(info(),aDisplayMode));
sl@0
   317
sl@0
   318
	if (ret == KErrNotSupported)
sl@0
   319
		{
sl@0
   320
		INFO_PRINTF1(_L("Not supported\r\n"));
sl@0
   321
		return;
sl@0
   322
		}
sl@0
   323
	else if (ret != KErrNone)
sl@0
   324
		User::Panic(_L("Draw device create"),ret);
sl@0
   325
sl@0
   326
	iDrawDevice->InitScreen();
sl@0
   327
	iDrawDevice->SetDisplayMode(iDrawDevice);
sl@0
   328
	iDrawDevice->SetAutoUpdate(EFalse);
sl@0
   329
	TBool orientation[4];
sl@0
   330
	iDrawDevice->OrientationsAvailable(orientation);
sl@0
   331
sl@0
   332
	TBool orientationSupported = iDrawDevice->SetOrientation(CFbsDrawDevice::TOrientation(iOrientation));
sl@0
   333
	if (orientationSupported)
sl@0
   334
		{
sl@0
   335
		Check(orientation[iOrientation]);
sl@0
   336
		if (iOrientation & 1)
sl@0
   337
			iSize = TSize(size.iHeight,size.iWidth);
sl@0
   338
		else
sl@0
   339
			iSize = size;
sl@0
   340
		iLongWidth = LongWidth(iSize.iWidth,aDisplayMode);
sl@0
   341
		Test();
sl@0
   342
		}
sl@0
   343
	else
sl@0
   344
		{
sl@0
   345
		Check(!orientation[iOrientation]);
sl@0
   346
		INFO_PRINTF1(_L("Orientation not supported\r\n"));
sl@0
   347
		}
sl@0
   348
sl@0
   349
	INFO_PRINTF2(_L("Testing time=%d"), (User::TickCount() - startTime) * 100 / 64);
sl@0
   350
	}
sl@0
   351
sl@0
   352
void CTLowLevel::TestBitmapDraw(TDisplayMode aDisplayMode,const TSize& aSize)
sl@0
   353
	{
sl@0
   354
	TUint startTime=User::TickCount();
sl@0
   355
	Reset();
sl@0
   356
	iDispMode = aDisplayMode;
sl@0
   357
	iSize = aSize;
sl@0
   358
	iLongWidth = LongWidth(aSize.iWidth,aDisplayMode);
sl@0
   359
	TSize size(0,0);
sl@0
   360
	INFO_PRINTF1(KNullDesC);
sl@0
   361
sl@0
   362
	const TInt byteSize=ByteSize()*iSize.iHeight;
sl@0
   363
	_LIT(KNoMem,"Not enough memory for bitmap bits");
sl@0
   364
	iBits = new TUint8[byteSize];
sl@0
   365
	if(!iBits)
sl@0
   366
		{
sl@0
   367
		User::Panic(KNoMem,KErrNoMemory);
sl@0
   368
		}
sl@0
   369
sl@0
   370
	iBuf = new TUint32[byteSize];
sl@0
   371
	if(!iBuf)
sl@0
   372
		{
sl@0
   373
		User::Panic(KNoMem,KErrNoMemory);
sl@0
   374
		}
sl@0
   375
sl@0
   376
	TPckgBuf<TScreenInfoV01> info;
sl@0
   377
	info().iScreenSize = aSize;
sl@0
   378
	info().iScreenAddress = NULL;
sl@0
   379
	info().iScreenAddressValid = ETrue;
sl@0
   380
sl@0
   381
	TRAPD(ret, iDrawDevice = CFbsDrawDevice::NewBitmapDeviceL(info(), aDisplayMode, ByteSize() ));
sl@0
   382
	if (ret == KErrNotSupported)
sl@0
   383
		{
sl@0
   384
		INFO_PRINTF1(_L("Not supported\r\n"));
sl@0
   385
		return;
sl@0
   386
		}
sl@0
   387
	else if (ret != KErrNone)
sl@0
   388
	{
sl@0
   389
		User::Panic(_L("Draw device create"),ret);
sl@0
   390
	}
sl@0
   391
	iDrawDevice->SetAutoUpdate(EFalse);
sl@0
   392
	//Initialize the iDrowDevice object, if successful val=KErrNone
sl@0
   393
	TInt val=iDrawDevice->InitScreen();
sl@0
   394
	TEST(val==KErrNone);
sl@0
   395
	iDrawDevice->CFbsDrawDevice::SetBits(iBits);
sl@0
   396
	iDrawDevice->CFbsDrawDevice::ShadowBuffer(10,iBuf);
sl@0
   397
	iDrawDevice->CFbsDrawDevice::SetUserDisplayMode(iDispMode);
sl@0
   398
	iDrawDevice->SetDisplayMode(iDrawDevice);
sl@0
   399
	iDrawDevice->Update();
sl@0
   400
	iDrawDevice->SetUserDisplayMode(iDispMode);
sl@0
   401
	iDrawDevice->SetBits(iBits);
sl@0
   402
	Test();
sl@0
   403
	TBool orientation[4];
sl@0
   404
	iDrawDevice->OrientationsAvailable(orientation);
sl@0
   405
	TBool orientationSupported = iDrawDevice->SetOrientation(CFbsDrawDevice::TOrientation(iOrientation));
sl@0
   406
	if (orientationSupported)
sl@0
   407
		{
sl@0
   408
		Check(orientation[iOrientation]);
sl@0
   409
		if (iOrientation & 1)
sl@0
   410
			iSize = TSize(size.iHeight,size.iWidth);
sl@0
   411
		else
sl@0
   412
			iSize = size;
sl@0
   413
		iLongWidth = LongWidth(iSize.iWidth,aDisplayMode);
sl@0
   414
		}
sl@0
   415
	else
sl@0
   416
		{
sl@0
   417
		Check(!orientation[iOrientation]);
sl@0
   418
		INFO_PRINTF1(_L("Orientation not supported\r\n"));
sl@0
   419
		}
sl@0
   420
	INFO_PRINTF2(_L("Testing time=%d"), (User::TickCount() - startTime) * 100 / 64);
sl@0
   421
	}
sl@0
   422
sl@0
   423
TInt RgbComponent(TRgb aRgb, TInt aRgbIndex)
sl@0
   424
	{
sl@0
   425
	return(aRgbIndex==0?aRgb.Red():(aRgbIndex==1?aRgb.Green():aRgb.Blue()));
sl@0
   426
	}
sl@0
   427
	
sl@0
   428
TBool CheckNormalizedValue(TRgb aReadCol, TRgb aNormalizedCol1, TRgb aNormalizedCol2, TRgb aNormalizedCol3, TRgb aNormalizedCol4, TInt aRgbIndex)
sl@0
   429
	{
sl@0
   430
	
sl@0
   431
	const TInt KErrorMargin=5;
sl@0
   432
	TInt minCol=Min(RgbComponent(aNormalizedCol1,aRgbIndex),
sl@0
   433
					Min(RgbComponent(aNormalizedCol2,aRgbIndex),
sl@0
   434
						Min(RgbComponent(aNormalizedCol3,aRgbIndex),RgbComponent(aNormalizedCol4,aRgbIndex))))-KErrorMargin;
sl@0
   435
	TInt maxCol=Max(RgbComponent(aNormalizedCol1,aRgbIndex),
sl@0
   436
					Max(RgbComponent(aNormalizedCol2,aRgbIndex),
sl@0
   437
						Max(RgbComponent(aNormalizedCol3,aRgbIndex),RgbComponent(aNormalizedCol4,aRgbIndex))))+KErrorMargin;
sl@0
   438
	TInt readComponent=RgbComponent(aReadCol,aRgbIndex);
sl@0
   439
	return(readComponent>=minCol && readComponent<=maxCol);
sl@0
   440
	}
sl@0
   441
sl@0
   442
void CTLowLevel::CheckNormalizedRgb(TRgb aReadRgb, TRgb aCheckRgb, TDisplayMode aDevDisplayMode, TDisplayMode aUserDisplayMode, TBool aWriteRgbAlphaLine)
sl@0
   443
	{
sl@0
   444
	TRgb normalized1=aCheckRgb;
sl@0
   445
	Normalize(normalized1,aUserDisplayMode);
sl@0
   446
	if (aDevDisplayMode==EColor16MAP)
sl@0
   447
		{
sl@0
   448
		const TInt KNormalizeErrorMargin=3;
sl@0
   449
		TRgb normalizedPMA1=aCheckRgb;
sl@0
   450
// Allow error margin for blending errors before calculating value normalized to user display mode
sl@0
   451
		normalizedPMA1.SetRed(Min(0xFF,normalizedPMA1.Red()+KNormalizeErrorMargin));
sl@0
   452
		normalizedPMA1.SetGreen(Min(0xFF,normalizedPMA1.Green()+KNormalizeErrorMargin));
sl@0
   453
		normalizedPMA1.SetBlue(Min(0xFF,normalizedPMA1.Blue()+KNormalizeErrorMargin));
sl@0
   454
//
sl@0
   455
		Normalize(normalizedPMA1,aUserDisplayMode);
sl@0
   456
		TRgb normalizedPMA3=normalizedPMA1;
sl@0
   457
		normalizedPMA1=TRgb::Color16MAP(normalizedPMA1.Color16MAP());
sl@0
   458
		TRgb normalizedPMA2=aCheckRgb;
sl@0
   459
		normalizedPMA2=TRgb::Color16MAP(normalizedPMA2.Color16MAP());
sl@0
   460
		normalizedPMA2.SetRed(Max(0,normalizedPMA2.Red()-KNormalizeErrorMargin));
sl@0
   461
		normalizedPMA2.SetGreen(Max(0,normalizedPMA2.Green()-KNormalizeErrorMargin));
sl@0
   462
		normalizedPMA2.SetBlue(Max(0,normalizedPMA2.Blue()-KNormalizeErrorMargin));
sl@0
   463
		Normalize(normalizedPMA2,aUserDisplayMode);
sl@0
   464
		TEST(CheckNormalizedValue(aReadRgb,normalizedPMA1,normalizedPMA2,normalizedPMA3,normalized1,0) &&
sl@0
   465
				CheckNormalizedValue(aReadRgb,normalizedPMA1,normalizedPMA2,normalizedPMA3,normalized1,1) &&
sl@0
   466
				CheckNormalizedValue(aReadRgb,normalizedPMA1,normalizedPMA2,normalizedPMA3,normalized1,2));
sl@0
   467
		}
sl@0
   468
	else
sl@0
   469
		{
sl@0
   470
		if (aDevDisplayMode==EColor64K && aWriteRgbAlphaLine)
sl@0
   471
			{
sl@0
   472
	// In EColor64K the WriteRgbAlphaLine code maps to native display mode first, before mapping to
sl@0
   473
	// user mode then back again to device display mode. So use normalized2 to check for that case
sl@0
   474
			TRgb normalized2=aCheckRgb;
sl@0
   475
			Normalize(normalized2,aDevDisplayMode);
sl@0
   476
			Normalize(normalized2,aUserDisplayMode);
sl@0
   477
			Normalize(normalized2,aDevDisplayMode);
sl@0
   478
			TEST(aReadRgb.Color16MU()==normalized2.Color16MU());
sl@0
   479
			}
sl@0
   480
		else
sl@0
   481
			{
sl@0
   482
			Normalize(normalized1,aDevDisplayMode);
sl@0
   483
			TEST(aReadRgb.Color16MU()==normalized1.Color16MU());
sl@0
   484
			}
sl@0
   485
		}
sl@0
   486
	}
sl@0
   487
	
sl@0
   488
void CTLowLevel::PrepareDestPixel(TDisplayMode aDevDisplayMode, TRgb& aRgb, TInt aDstAlpha)
sl@0
   489
	{
sl@0
   490
	CGraphicsContext::TDrawMode drawMode;
sl@0
   491
	if (aDevDisplayMode==EColor16MAP)
sl@0
   492
		{
sl@0
   493
		aRgb.SetAlpha(aDstAlpha);
sl@0
   494
		drawMode=CGraphicsContext::EDrawModeWriteAlpha;
sl@0
   495
		}
sl@0
   496
	else
sl@0
   497
		{
sl@0
   498
		aRgb.SetAlpha(0xFF);
sl@0
   499
		drawMode=CGraphicsContext::EDrawModePEN;
sl@0
   500
		}
sl@0
   501
	iDrawDevice->WriteRgbMulti(0,0,1,1,aRgb,drawMode);
sl@0
   502
	}
sl@0
   503
sl@0
   504
void CTLowLevel::CheckMappedRgb(TDisplayMode aDevDisplayMode, TDisplayMode aUserDisplayMode, TRgb aRgb)
sl@0
   505
	{
sl@0
   506
	const TInt KMaxAlphaModes=5;
sl@0
   507
	TInt alphaModeValues[KMaxAlphaModes]={0xFF,0xC0,0x80,0x40,0};
sl@0
   508
	TInt dstAlphaModeCount=aDevDisplayMode==EColor16MAP?KMaxAlphaModes:1;
sl@0
   509
	for(TInt dstAlphaMode=0;dstAlphaMode<dstAlphaModeCount;dstAlphaMode++)
sl@0
   510
		{
sl@0
   511
		TInt dstAlpha=alphaModeValues[dstAlphaMode];
sl@0
   512
		for(TInt alphaMode=0;alphaMode<KMaxAlphaModes;alphaMode++)
sl@0
   513
			{
sl@0
   514
			TInt alpha=alphaModeValues[alphaMode];
sl@0
   515
			if ((aUserDisplayMode==EColor16 || aUserDisplayMode==EColor256) && (alpha!=0xFF || dstAlpha!=0xFF))
sl@0
   516
				continue;	// Mapping to EColor16 or EColor256 with fuzzy blends and PMA losses impossible to check for accurately
sl@0
   517
			PrepareDestPixel(aDevDisplayMode,aRgb,dstAlpha);
sl@0
   518
			aRgb.SetAlpha(alpha);
sl@0
   519
			iDrawDevice->WriteRgb(0,0,aRgb,CGraphicsContext::EDrawModePEN);
sl@0
   520
			TRgb readRgb=iDrawDevice->ReadPixel(0,0);
sl@0
   521
			CheckNormalizedRgb(readRgb,aRgb,aDevDisplayMode,aUserDisplayMode,EFalse);
sl@0
   522
//
sl@0
   523
			PrepareDestPixel(aDevDisplayMode,aRgb,dstAlpha);
sl@0
   524
			iDrawDevice->WriteRgbMulti(0,0,1,1,aRgb,CGraphicsContext::EDrawModePEN);
sl@0
   525
			readRgb=iDrawDevice->ReadPixel(0,0);
sl@0
   526
			CheckNormalizedRgb(readRgb,aRgb,aDevDisplayMode,aUserDisplayMode,EFalse);
sl@0
   527
//
sl@0
   528
			PrepareDestPixel(aDevDisplayMode,aRgb,dstAlpha);
sl@0
   529
			TUint32 writeBuffer[1];
sl@0
   530
			writeBuffer[0]=aRgb.Internal();
sl@0
   531
			TUint8 mask[1]={0xFF};
sl@0
   532
			iDrawDevice->WriteRgbAlphaLine(0,0,1,(TUint8*)writeBuffer,mask,CGraphicsContext::EDrawModePEN);
sl@0
   533
			readRgb=iDrawDevice->ReadPixel(0,0);
sl@0
   534
			CheckNormalizedRgb(readRgb,aRgb,aDevDisplayMode,aUserDisplayMode,ETrue);
sl@0
   535
			}
sl@0
   536
		}
sl@0
   537
	}
sl@0
   538
sl@0
   539
void CTLowLevel::TestUserDisplayModeMapping()
sl@0
   540
	{
sl@0
   541
	TInt address = NULL;
sl@0
   542
	TSize size;
sl@0
   543
	User::LeaveIfError(HAL::Get(KDefaultScreenNo, HALData::EDisplayMemoryAddress,address));
sl@0
   544
	User::LeaveIfError(HAL::Get(KDefaultScreenNo, HALData::EDisplayXPixels,size.iWidth));
sl@0
   545
	User::LeaveIfError(HAL::Get(KDefaultScreenNo, HALData::EDisplayYPixels,size.iHeight));
sl@0
   546
	ASSERT(size.iWidth > 0 && size.iHeight > 0 && address != NULL);
sl@0
   547
sl@0
   548
	TPckgBuf<TScreenInfoV01> info;
sl@0
   549
	info().iScreenAddressValid = ETrue;
sl@0
   550
	info().iScreenAddress = REINTERPRET_CAST(TAny*,address);
sl@0
   551
	info().iScreenSize = size;
sl@0
   552
//
sl@0
   553
	for (TInt nDispModeDev = 0; nDispModeDev < KNumDispModes; nDispModeDev++)
sl@0
   554
		{
sl@0
   555
		TDisplayMode dispModeDev = TestDisplayMode[nDispModeDev];
sl@0
   556
		if (!TDisplayModeUtils::IsDisplayModeColor(dispModeDev) || TDisplayModeUtils::NumDisplayModeColors(dispModeDev)<65536)
sl@0
   557
			continue; // Older modes have their quirks we don't want to mess with
sl@0
   558
		Reset();
sl@0
   559
		TRAPD(ret,iDrawDevice = CFbsDrawDevice::NewScreenDeviceL(info(),dispModeDev));
sl@0
   560
		if (ret == KErrNotSupported)
sl@0
   561
			continue;
sl@0
   562
		for (TInt nDispMode = 0; nDispMode < KNumDispModes; nDispMode++)
sl@0
   563
			{
sl@0
   564
			TDisplayMode userDispMode = TestDisplayMode[nDispMode];
sl@0
   565
			INFO_PRINTF3(_L("Testing devMode=%d, userMode=%d"), dispModeDev, userDispMode);
sl@0
   566
			iDrawDevice->SetUserDisplayMode(userDispMode);
sl@0
   567
			TUint rgbVal=0;
sl@0
   568
			FOREVER
sl@0
   569
				{
sl@0
   570
				CheckMappedRgb(dispModeDev,userDispMode,rgbVal);
sl@0
   571
				if (rgbVal==0xFFFFFF)
sl@0
   572
					break;
sl@0
   573
				rgbVal+=0x010305;
sl@0
   574
				if (rgbVal>0xFFFFFF)	// We want to make sure we test 0xFFFFFF as a special case
sl@0
   575
					rgbVal=0xFFFFFF;
sl@0
   576
				}
sl@0
   577
			}
sl@0
   578
		}
sl@0
   579
	}
sl@0
   580
sl@0
   581
void CTLowLevel::Test()
sl@0
   582
	{
sl@0
   583
	_LIT(KOrientation,"Orientation: %S");
sl@0
   584
	TBuf<32> buf;
sl@0
   585
	buf.Format(KOrientation,&RotationName(iOrientation));
sl@0
   586
	INFO_PRINTF1(buf);
sl@0
   587
sl@0
   588
	iTestNo = 1;
sl@0
   589
	iIteration = 0;
sl@0
   590
	iReportIteration = 1;
sl@0
   591
	iTotalReportIterations = 1;
sl@0
   592
	TestParams();
sl@0
   593
sl@0
   594
	iTestNo++;
sl@0
   595
	iIteration = 0;
sl@0
   596
	iReportIteration = 1;
sl@0
   597
	iTotalReportIterations = KNumDispModes;
sl@0
   598
	TestReadLine();
sl@0
   599
sl@0
   600
	iTestNo++;
sl@0
   601
	iIteration = 0;
sl@0
   602
	iReportIteration = 1;
sl@0
   603
	iTotalReportIterations = KNumShadowModes * KNumDrawModes;
sl@0
   604
	if(KFastFading && (iDispMode == EColor64K ||iDispMode == EColor16MU || iDispMode == EColor16MA || iDispMode == EColor16MAP))
sl@0
   605
		{
sl@0
   606
		iUseFastFade = ETrue;
sl@0
   607
		}
sl@0
   608
	TestWriteRgb();
sl@0
   609
sl@0
   610
	iTestNo++;
sl@0
   611
	iIteration = 0;
sl@0
   612
	iReportIteration = 1;
sl@0
   613
	TestWriteLine();
sl@0
   614
sl@0
   615
	iTestNo++;
sl@0
   616
	iIteration = 0;
sl@0
   617
	iReportIteration = 1;
sl@0
   618
	TestWriteBinary();
sl@0
   619
sl@0
   620
	iTestNo++;
sl@0
   621
	iIteration = 0;
sl@0
   622
	iReportIteration = 1;
sl@0
   623
	iTotalReportIterations = 4;
sl@0
   624
	TestWriteRGBAlpha();
sl@0
   625
sl@0
   626
	iTestNo++;
sl@0
   627
	iIteration = 0;
sl@0
   628
	iReportIteration = 1;
sl@0
   629
	iTotalReportIterations = KNumShadowModes;
sl@0
   630
	TestShadow();
sl@0
   631
	if(KFastFading && (iDispMode == EColor64K|| iDispMode == EColor16MU || iDispMode == EColor16MA || iDispMode == EColor16MAP))
sl@0
   632
		{
sl@0
   633
		iUseFastFade = EFalse;
sl@0
   634
		}
sl@0
   635
sl@0
   636
	iTestNo++;
sl@0
   637
	iIteration = 0;
sl@0
   638
	iReportIteration = 1;
sl@0
   639
	iTotalReportIterations = 1;
sl@0
   640
	TestWriteAlphaLineEx();
sl@0
   641
sl@0
   642
	iTestNo++;
sl@0
   643
	iIteration = 0;
sl@0
   644
	iReportIteration = 1;
sl@0
   645
	iTotalReportIterations = 1;
sl@0
   646
	TestWriteAlphaLineNoShadowEx();
sl@0
   647
sl@0
   648
	iTestNo++;
sl@0
   649
	iIteration = 0;
sl@0
   650
	iReportIteration = 1;
sl@0
   651
	iTotalReportIterations = 1;
sl@0
   652
	TestWriteMaskLineNoShadowEx();
sl@0
   653
sl@0
   654
	iTestNo++;
sl@0
   655
	iIteration = 0;
sl@0
   656
	iReportIteration = 1;
sl@0
   657
	iTotalReportIterations = 1;
sl@0
   658
	TRAPD(err,((CTLowLevelStep*)iStep)->RecordTestResultL(););
sl@0
   659
    	if (err!=KErrNone)
sl@0
   660
    		INFO_PRINTF1(_L("Failed to record test result"));
sl@0
   661
sl@0
   662
	((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0003"));
sl@0
   663
	TestFastBlendBitmapMasked();
sl@0
   664
	TRAPD(err1,((CTLowLevelStep*)iStep)->RecordTestResultL(););
sl@0
   665
    	if (err1!=KErrNone)
sl@0
   666
    		INFO_PRINTF1(_L("Failed to record test result"));
sl@0
   667
sl@0
   668
	iTestNo++;
sl@0
   669
	iIteration = 0;
sl@0
   670
	iReportIteration = 1;
sl@0
   671
	iTotalReportIterations = KNumBlendingColors;
sl@0
   672
	((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0002"));
sl@0
   673
	//TestWriteRgbOutlineAndShadow(); // commented out pending case resolution #327407
sl@0
   674
	TRAP(err,((CTLowLevelStep*)iStep)->RecordTestResultL(););
sl@0
   675
    	if (err!=KErrNone)
sl@0
   676
    		INFO_PRINTF1(_L("Failed to record test result"));
sl@0
   677
/**
sl@0
   678
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0001
sl@0
   679
*/
sl@0
   680
	((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0001"));
sl@0
   681
	}
sl@0
   682
sl@0
   683
void CTLowLevel::TestParams()
sl@0
   684
	{
sl@0
   685
	Check(iDrawDevice->SizeInPixels()==iSize);
sl@0
   686
	Check(iDrawDevice->DisplayMode()==iDispMode);
sl@0
   687
	Check(iDrawDevice->LongWidth()==iLongWidth);
sl@0
   688
	Check(iDrawDevice->ScanLineBuffer()!=NULL);
sl@0
   689
	Check(iLongWidth%(iDrawDevice->ScanLineBytes())==0
sl@0
   690
			|| iDrawDevice->ScanLineBytes() == iLongWidth * 2
sl@0
   691
			|| iDrawDevice->ScanLineBytes() == iLongWidth * 3
sl@0
   692
			|| iDrawDevice->ScanLineBytes() == iLongWidth * 4);
sl@0
   693
	TInt hT = iDrawDevice->HorzTwipsPerThousandPixels();
sl@0
   694
	Check(hT >= 0);
sl@0
   695
	TInt vT = iDrawDevice->VertTwipsPerThousandPixels();
sl@0
   696
	Check(vT >= 0);
sl@0
   697
	Report();
sl@0
   698
	}
sl@0
   699
sl@0
   700
void CTLowLevel::TestReadLine()
sl@0
   701
	{
sl@0
   702
	TInt byteSize = ByteSize();
sl@0
   703
	TUint8* writeBuffer = new TUint8[byteSize];
sl@0
   704
	TUint8* readBuffer = new TUint8[iSize.iWidth * sizeof(TRgb)];
sl@0
   705
	Check(writeBuffer != NULL);
sl@0
   706
	Check(readBuffer != NULL);
sl@0
   707
sl@0
   708
	for (TInt nDispMode = 0; nDispMode < KNumDispModes; nDispMode++)
sl@0
   709
		{
sl@0
   710
		TDisplayMode dispMode = TestDisplayMode[nDispMode];
sl@0
   711
		iDrawDevice->SetUserDisplayMode(dispMode);
sl@0
   712
sl@0
   713
		if (dispMode == EColor16MU || dispMode == EColor16MAP || iDispMode == EColor16MU || iDispMode == EColor16MAP)
sl@0
   714
			iFuzzyMatch=ETrue;
sl@0
   715
		else
sl@0
   716
			iFuzzyMatch=EFalse;
sl@0
   717
		for (TInt cnt=0;cnt<2;cnt++)
sl@0
   718
			{
sl@0
   719
			if (cnt==0)  //first time
sl@0
   720
				iDrawDevice->SetUserDisplayMode(dispMode);
sl@0
   721
			else
sl@0
   722
				iDrawDevice->SetUserDisplayMode(iDispMode);
sl@0
   723
sl@0
   724
			for (TInt nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
   725
				{
sl@0
   726
				TRect rect = TestRect[nRect];
sl@0
   727
				for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
   728
					{
sl@0
   729
					Clear(KRgbWhite);
sl@0
   730
sl@0
   731
					FillBuffer(writeBuffer, byteSize, iDispMode, ETrue);
sl@0
   732
					Mem::FillZ(readBuffer,byteSize);
sl@0
   733
sl@0
   734
					//we select EDrawModeWriteAlpha because do not test blending here
sl@0
   735
					iDrawDevice->WriteLine(rect.iTl.iX,yy,rect.Width(),(TUint32*)writeBuffer,CGraphicsContext::EDrawModeWriteAlpha);
sl@0
   736
					iDrawDevice->ReadLine(rect.iTl.iX,yy,rect.Width(),(TUint32*)readBuffer,dispMode);
sl@0
   737
sl@0
   738
					CheckBuffer(writeBuffer,iDispMode,readBuffer,dispMode,rect.Width());
sl@0
   739
sl@0
   740
					Mem::FillZ(readBuffer,byteSize);
sl@0
   741
sl@0
   742
					//we select EDrawModeWriteAlpha because do not test blending here
sl@0
   743
					iDrawDevice->WriteLine(iSize.iWidth-rect.Width(),yy,rect.Width(),(TUint32*)writeBuffer,CGraphicsContext::EDrawModeWriteAlpha);
sl@0
   744
					iDrawDevice->ReadLine(iSize.iWidth-rect.Width(),yy,rect.Width(),(TUint32*)readBuffer,dispMode);
sl@0
   745
sl@0
   746
					CheckBuffer(writeBuffer,iDispMode,readBuffer,dispMode,rect.Width());
sl@0
   747
					iIteration++;
sl@0
   748
					}
sl@0
   749
				}
sl@0
   750
			}
sl@0
   751
		if (iDispMode != EColor16MU && iDispMode != EColor16MAP)
sl@0
   752
			iFuzzyMatch=EFalse;
sl@0
   753
		Report();
sl@0
   754
		}
sl@0
   755
	delete [] writeBuffer;
sl@0
   756
	delete [] readBuffer;
sl@0
   757
	}
sl@0
   758
sl@0
   759
void CTLowLevel::TestWriteRgb()
sl@0
   760
	{
sl@0
   761
	for (TInt shadowMode = 0; shadowMode < KNumShadowModes; shadowMode++)
sl@0
   762
		{
sl@0
   763
		for (TInt nMode = 0; nMode < KNumDrawModes; nMode++)
sl@0
   764
			{
sl@0
   765
			for (TInt nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
   766
				{
sl@0
   767
				for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
   768
					{
sl@0
   769
					for (TInt nColor = 0; nColor < KNumTestColors; nColor++)
sl@0
   770
						{
sl@0
   771
sl@0
   772
						//for modes other than EColor16MAP skip the new colours which have alpha, and cause
sl@0
   773
						//test failures.  There are two types of colours which need to be skipped, nColor,
sl@0
   774
						//and nBackColor.  The additional colours were added specificially to test EColor16MAP mode,
sl@0
   775
						//so the test coverage compared to previously is not reduced for non EColor16MAP modes.
sl@0
   776
						if (((nColor>=KMaxNon16Colours)|| (nBackColor>=KMaxNon16BackColours)) && (iDispMode!= EColor16MAP))
sl@0
   777
							continue;
sl@0
   778
sl@0
   779
						TRgb bakCol = TestBackground[nBackColor];
sl@0
   780
						Clear(bakCol);
sl@0
   781
sl@0
   782
						CGraphicsContext::TDrawMode dMode = TestDrawMode[nMode];
sl@0
   783
sl@0
   784
						if ((iDispMode==EColor16MAP)&&(dMode!=CGraphicsContext::EDrawModePEN))
sl@0
   785
							continue;
sl@0
   786
sl@0
   787
sl@0
   788
						TRect rect = TestRect[nRect];
sl@0
   789
						TRgb col = TestColor[nColor];
sl@0
   790
sl@0
   791
						iDrawDevice->CFbsDrawDevice::SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   792
						iDrawDevice->CFbsDrawDevice::SetFadingParameters(100,200);
sl@0
   793
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   794
						iDrawDevice->WriteRgb(rect.iTl.iX,rect.iTl.iY,col,dMode);
sl@0
   795
sl@0
   796
						CheckRgb(rect.iTl,col,bakCol,dMode,shadowMode);
sl@0
   797
						CheckBackground(TRect(rect.iTl,TSize(1,1)),bakCol);
sl@0
   798
sl@0
   799
						Clear(bakCol);
sl@0
   800
sl@0
   801
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   802
						iDrawDevice->WriteRgbMulti(rect.iTl.iX,rect.iTl.iY,rect.Width(),rect.Height(),col,dMode);
sl@0
   803
sl@0
   804
						CheckRgb(rect,col,bakCol,dMode,shadowMode);
sl@0
   805
						CheckBackground(rect,bakCol);
sl@0
   806
						iIteration++;
sl@0
   807
						}
sl@0
   808
					}
sl@0
   809
				}
sl@0
   810
			Report();
sl@0
   811
			}
sl@0
   812
		}
sl@0
   813
	}
sl@0
   814
sl@0
   815
void CTLowLevel::TestWriteLine()
sl@0
   816
	{
sl@0
   817
	TInt byteSize = ByteSize();
sl@0
   818
	TUint8* backBuffer = new TUint8[byteSize];
sl@0
   819
	TUint8* writeBuffer = new TUint8[byteSize];
sl@0
   820
	TUint8* copyBuffer = new TUint8[byteSize];
sl@0
   821
	TUint8* readBuffer = new TUint8[byteSize];
sl@0
   822
	Check(backBuffer != NULL);
sl@0
   823
	Check(writeBuffer != NULL);
sl@0
   824
	Check(copyBuffer != NULL);
sl@0
   825
	Check(readBuffer != NULL);
sl@0
   826
sl@0
   827
	for (TInt shadowMode = 0; shadowMode < KNumShadowModes; shadowMode++)
sl@0
   828
		{
sl@0
   829
		for (TInt nMode = 0; nMode < KNumDrawModes; nMode++)
sl@0
   830
			{
sl@0
   831
			CGraphicsContext::TDrawMode dMode = TestDrawMode[nMode];
sl@0
   832
			for (TInt nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
   833
				{
sl@0
   834
				for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
   835
					{
sl@0
   836
					//skip over new colours with alpha for modes other than EColor16MAP
sl@0
   837
					//these were causing test failures
sl@0
   838
					if ((nBackColor>=KMaxNon16BackColours) && (iDispMode!= EColor16MAP))
sl@0
   839
							continue;
sl@0
   840
sl@0
   841
					TRgb bakCol = TestBackground[nBackColor];
sl@0
   842
					Clear(bakCol);
sl@0
   843
					TRect rect = TestRect[nRect];
sl@0
   844
					/*TBuf<128> buf;		//Some extra logging that might be useful if this test fails
sl@0
   845
					_LIT(KLog1,"Shadow=%d, DrawMode=%d, Rect=(%d,%d,%d,%d), Color=%d");
sl@0
   846
					buf.Format(KLog1,shadowMode,dMode,rect.iTl.iX,rect.iTl.iY,rect.iBr.iX,rect.iBr.iY,nBackColor);
sl@0
   847
					INFO_PRINTF1(buf);*/
sl@0
   848
					for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
   849
						{
sl@0
   850
						iDrawDevice->CFbsDrawDevice::SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   851
						iDrawDevice->CFbsDrawDevice::SetFadingParameters(100,200);
sl@0
   852
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   853
						iDrawDevice->ReadLine(rect.iTl.iX,yy,rect.Width(),(TUint32*)backBuffer,iDispMode);
sl@0
   854
sl@0
   855
						if (nRect != 7)
sl@0
   856
							{
sl@0
   857
							// make sure the alpha value is 0xFF when not blending the buffer into 16MU destination
sl@0
   858
							TBool noAlpha16MU = dMode != CGraphicsContext::EDrawModePEN;
sl@0
   859
							FillBuffer(writeBuffer, byteSize, iDispMode, noAlpha16MU);
sl@0
   860
							}
sl@0
   861
						else // Special check for losing leading 0s in 1 bpp mode at 31 pixel offset
sl@0
   862
							{
sl@0
   863
							Mem::Fill(writeBuffer,byteSize,0xff);
sl@0
   864
							writeBuffer[0] = 0xfe;
sl@0
   865
							}
sl@0
   866
						Mem::Copy(copyBuffer,writeBuffer,byteSize);
sl@0
   867
						iDrawDevice->WriteLine(rect.iTl.iX,yy,rect.Width(),(TUint32*)writeBuffer,dMode);
sl@0
   868
						Shadow(copyBuffer,byteSize,shadowMode);
sl@0
   869
sl@0
   870
						Mem::FillZ(readBuffer,byteSize);
sl@0
   871
						iDrawDevice->ReadLine(rect.iTl.iX,yy,rect.Width(),(TUint32*)readBuffer,iDispMode);
sl@0
   872
						CheckLine(copyBuffer,readBuffer,backBuffer,rect.Width(),dMode,iDispMode);
sl@0
   873
sl@0
   874
						iIteration++;
sl@0
   875
						}
sl@0
   876
					CheckBackground(rect,bakCol);
sl@0
   877
					}
sl@0
   878
				}
sl@0
   879
			Report();
sl@0
   880
			}
sl@0
   881
		}
sl@0
   882
	delete [] backBuffer;
sl@0
   883
	delete [] writeBuffer;
sl@0
   884
	delete [] copyBuffer;
sl@0
   885
	delete [] readBuffer;
sl@0
   886
	}
sl@0
   887
sl@0
   888
void CTLowLevel::TestWriteBinary()
sl@0
   889
	{
sl@0
   890
	TInt byteSize = ByteSize();
sl@0
   891
	TInt wordSize = (byteSize + 3) / 4;
sl@0
   892
	TUint32* writeBuffer = new TUint32[wordSize];
sl@0
   893
	Check(writeBuffer != NULL);
sl@0
   894
sl@0
   895
	for (TInt shadowMode = 0; shadowMode < KNumShadowModes; shadowMode++)
sl@0
   896
		{
sl@0
   897
		for (TInt nMode = 0; nMode < KNumDrawModes; nMode++)
sl@0
   898
			{
sl@0
   899
			for (TInt nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
   900
				{
sl@0
   901
				for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
   902
					{
sl@0
   903
					for (TInt nColor = 0; nColor < KNumTestColors; nColor++)
sl@0
   904
						{
sl@0
   905
						if (((nColor>=KMaxNon16Colours)|| (nBackColor>=KMaxNon16BackColours)) && (iDispMode!= EColor16MAP))
sl@0
   906
							continue;
sl@0
   907
sl@0
   908
						TRect rect = TestRect[nRect];
sl@0
   909
						if (rect.Width() > 32)
sl@0
   910
							{
sl@0
   911
							rect.iBr.iX = rect.iTl.iX + 32;
sl@0
   912
							}
sl@0
   913
						if (rect.Width() < 1)
sl@0
   914
							rect.iBr.iX = rect.iTl.iX + 1;
sl@0
   915
sl@0
   916
						TRgb bakCol = TestBackground[nBackColor];
sl@0
   917
						TRgb col = TestColor[nColor];
sl@0
   918
						CGraphicsContext::TDrawMode dMode = TestDrawMode[nMode];
sl@0
   919
sl@0
   920
						if ((iDispMode==EColor16MAP)&&(dMode!=CGraphicsContext::EDrawModePEN))
sl@0
   921
							continue;
sl@0
   922
sl@0
   923
						Clear(bakCol);
sl@0
   924
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   925
						FillBuffer((TUint8*)writeBuffer, byteSize, EGray2);
sl@0
   926
						iDrawDevice->WriteBinary(rect.iTl.iX,rect.iTl.iY,writeBuffer,rect.Width(),rect.Height(),col,dMode);
sl@0
   927
						CheckBinary(rect,writeBuffer,col,bakCol,dMode,shadowMode,ETrue,EFalse);
sl@0
   928
						CheckBackground(rect,bakCol);
sl@0
   929
sl@0
   930
						Clear(bakCol);
sl@0
   931
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   932
						FillBuffer((TUint8*)writeBuffer, byteSize, EGray2);
sl@0
   933
						iDrawDevice->WriteBinaryLine(rect.iTl.iX,rect.iTl.iY,writeBuffer,rect.Width(),col,dMode);
sl@0
   934
						CheckBinary(TRect(rect.iTl,TSize(rect.Width(),1)),writeBuffer,col,bakCol,dMode,shadowMode,EFalse,EFalse);
sl@0
   935
						CheckBackground(TRect(rect.iTl.iX,rect.iTl.iY,rect.iBr.iX,rect.iTl.iY + 1),bakCol);
sl@0
   936
sl@0
   937
						Clear(bakCol);
sl@0
   938
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   939
						FillBuffer((TUint8*)writeBuffer, byteSize, EGray2);
sl@0
   940
						iDrawDevice->WriteBinaryLineVertical(rect.iTl.iX,rect.iTl.iY,writeBuffer,rect.Height(),col,dMode,EFalse);
sl@0
   941
						CheckBinary(TRect(rect.iTl,TSize(1,rect.Height())),writeBuffer,col,bakCol,dMode,shadowMode,EFalse,EFalse);
sl@0
   942
						CheckBackground(TRect(rect.iTl.iX,rect.iTl.iY,rect.iTl.iX + 1,rect.iBr.iY),bakCol);
sl@0
   943
sl@0
   944
						Clear(bakCol);
sl@0
   945
						iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
   946
						FillBuffer((TUint8*)writeBuffer, byteSize, EGray2);
sl@0
   947
						iDrawDevice->WriteBinaryLineVertical(rect.iTl.iX,rect.iBr.iY - 1,writeBuffer,rect.Height(),col,dMode,ETrue);
sl@0
   948
						CheckBinary(TRect(rect.iTl,TSize(1,rect.Height())),writeBuffer,col,bakCol,dMode,shadowMode,EFalse,ETrue);
sl@0
   949
						CheckBackground(TRect(rect.iTl.iX,rect.iTl.iY,rect.iTl.iX + 1,rect.iBr.iY),bakCol);
sl@0
   950
sl@0
   951
						iIteration++;
sl@0
   952
						}
sl@0
   953
					}
sl@0
   954
				}
sl@0
   955
			Report();
sl@0
   956
			}
sl@0
   957
		}
sl@0
   958
	delete [] writeBuffer;
sl@0
   959
	}
sl@0
   960
sl@0
   961
void CTLowLevel::TestWriteAlphaLineEx()
sl@0
   962
	{
sl@0
   963
	TAny* interface = NULL;
sl@0
   964
	TInt err = iDrawDevice->GetInterface(KFastBlitInterfaceID, interface);
sl@0
   965
	if(err == KErrNone)
sl@0
   966
		{
sl@0
   967
		INFO_PRINTF1(_L("START ---->TestWriteAlphaLineEx"));
sl@0
   968
		TSize size = TSize(30,30);
sl@0
   969
		TRect rect = TRect(size);
sl@0
   970
sl@0
   971
		TUint16* writeBuffer = new TUint16[size.iWidth];
sl@0
   972
		TUint8* maskBuffer =  new TUint8[size.iWidth];
sl@0
   973
sl@0
   974
		TInt nOffset = sizeof(TUint16)*size.iWidth/2;
sl@0
   975
sl@0
   976
		Mem::Fill(writeBuffer,nOffset,0xff);
sl@0
   977
		Mem::Fill((((TUint8*)writeBuffer)+nOffset),nOffset,0x00);
sl@0
   978
		Mem::Fill(maskBuffer,size.iWidth/2,0x00);
sl@0
   979
		Mem::Fill((maskBuffer+size.iWidth/2),size.iWidth/2,0xff);
sl@0
   980
sl@0
   981
		MFastBlit* fastBlit = reinterpret_cast<MFastBlit*>(interface);
sl@0
   982
		Clear(KRgbFadedBlack);
sl@0
   983
		iDrawDevice->SetShadowMode(CFbsDrawDevice::EFade);
sl@0
   984
sl@0
   985
		for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
   986
			{
sl@0
   987
			fastBlit->WriteAlphaLineEx(rect.iTl.iX,yy,rect.Width(),0,(TUint32*)writeBuffer,EColor64K,0,(TUint32*)maskBuffer,MAlphaBlend::EShdwBefore);
sl@0
   988
			iIteration++;
sl@0
   989
			}
sl@0
   990
		CheckRgb(rect,KRgbBlack,KRgbFadedBlack,CGraphicsContext::EDrawModePEN,2);
sl@0
   991
		CheckBackground(rect,KRgbFadedBlack);
sl@0
   992
sl@0
   993
		Report();
sl@0
   994
		INFO_PRINTF1(_L("END ---->TestWriteAlphaLineEx"));
sl@0
   995
		delete [] writeBuffer;
sl@0
   996
		delete [] maskBuffer;
sl@0
   997
		}
sl@0
   998
	}
sl@0
   999
sl@0
  1000
void CTLowLevel::TestWriteAlphaLineNoShadowEx()
sl@0
  1001
	{
sl@0
  1002
	TAny* interface = NULL;
sl@0
  1003
	TInt err = iDrawDevice->GetInterface(KFastBlitInterfaceID, interface);
sl@0
  1004
	if(err == KErrNone)
sl@0
  1005
		{
sl@0
  1006
		INFO_PRINTF1(_L("START ---->TestWriteAlphaLineNoShadowEx"));
sl@0
  1007
		TSize size = TSize(30,30);
sl@0
  1008
		TRect rect = TRect(size);
sl@0
  1009
sl@0
  1010
		TUint16* writeBuffer = new TUint16[size.iWidth];
sl@0
  1011
		Check(writeBuffer != NULL);
sl@0
  1012
		TUint8* maskBuffer =  new TUint8[size.iWidth];
sl@0
  1013
		Check(maskBuffer != NULL);
sl@0
  1014
		TInt nOffset = sizeof(TUint16) * size.iWidth;
sl@0
  1015
sl@0
  1016
		Mem::Fill(writeBuffer,nOffset,0xff);
sl@0
  1017
		Mem::Fill(maskBuffer,size.iWidth/2,0x8e);
sl@0
  1018
		Mem::Fill((maskBuffer+size.iWidth/2),size.iWidth/2,0xff);
sl@0
  1019
sl@0
  1020
		MFastBlit* fastBlit = reinterpret_cast<MFastBlit*>(interface);
sl@0
  1021
sl@0
  1022
		Clear(KRgbWhite);
sl@0
  1023
		for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1024
			{
sl@0
  1025
			fastBlit->WriteAlphaLineEx(rect.iTl.iX,yy,rect.Width(),0,(TUint32*)writeBuffer,EColor64K,0,(TUint32*)maskBuffer,MAlphaBlend::EShdwBefore);
sl@0
  1026
			iIteration++;
sl@0
  1027
			}
sl@0
  1028
		CheckRgb(rect,KRgbWhite,KRgbWhite,CGraphicsContext::EDrawModePEN,0);
sl@0
  1029
sl@0
  1030
		Report();
sl@0
  1031
		INFO_PRINTF1(_L("END ---->TestWriteAlphaLineNoShadowEx"));
sl@0
  1032
		delete [] writeBuffer;
sl@0
  1033
		delete [] maskBuffer;
sl@0
  1034
		}
sl@0
  1035
	}
sl@0
  1036
sl@0
  1037
void CTLowLevel::TestWriteMaskLineNoShadowEx()
sl@0
  1038
	{
sl@0
  1039
	TAny* interface = NULL;
sl@0
  1040
	TInt err = iDrawDevice->GetInterface(KFastBlitInterfaceID, interface);
sl@0
  1041
	if(err == KErrNone)
sl@0
  1042
		{
sl@0
  1043
		INFO_PRINTF1(_L("START ---->TestWriteMaskLineNoShadowEx"));
sl@0
  1044
		TSize size = TSize(30,30);
sl@0
  1045
		TRect rect = TRect(size);
sl@0
  1046
sl@0
  1047
		TUint16* writeBuffer = new TUint16[size.iWidth];
sl@0
  1048
		Check(writeBuffer != NULL);
sl@0
  1049
		TUint8* maskBuffer =  new TUint8[size.iWidth];
sl@0
  1050
		Check(maskBuffer != NULL);
sl@0
  1051
sl@0
  1052
		TInt nOffset = sizeof(TUint16) * size.iWidth;
sl@0
  1053
sl@0
  1054
		Mem::Fill(writeBuffer,nOffset,0xff);
sl@0
  1055
		Mem::Fill(maskBuffer,size.iWidth/2,0x8e);
sl@0
  1056
		Mem::Fill((maskBuffer+size.iWidth/2),size.iWidth/2,0xff);
sl@0
  1057
sl@0
  1058
		MFastBlit* fastBlit = reinterpret_cast<MFastBlit*>(interface);
sl@0
  1059
sl@0
  1060
		Clear(KRgbWhite);
sl@0
  1061
		for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1062
			{
sl@0
  1063
			fastBlit->WriteMaskLineEx(rect.iTl.iX,yy,rect.Width(),0,(TUint32*)writeBuffer,EColor64K,0,(TUint32*)maskBuffer,EFalse);
sl@0
  1064
			iIteration++;
sl@0
  1065
			}
sl@0
  1066
		CheckRgb(rect,KRgbWhite,KRgbWhite,CGraphicsContext::EDrawModePEN,0);
sl@0
  1067
sl@0
  1068
		Report();
sl@0
  1069
		INFO_PRINTF1(_L("END ---->TestWriteMaskLineNoShadowEx"));
sl@0
  1070
		delete [] writeBuffer;
sl@0
  1071
		delete [] maskBuffer;
sl@0
  1072
		}
sl@0
  1073
	}
sl@0
  1074
sl@0
  1075
/**
sl@0
  1076
Overwrite the pixel in the buffer with a given mode with a value already in that
sl@0
  1077
mode.
sl@0
  1078
@param aX		The offset in pixels from the start of the buffer.
sl@0
  1079
@param aPtr		The start of the buffer.
sl@0
  1080
@param aMode	The display mode of the buffer.
sl@0
  1081
@param aValue	The new pixel value.
sl@0
  1082
*/
sl@0
  1083
void CTLowLevel::WriteBinaryValue(TUint32 aX, TAny* const aPtr, 
sl@0
  1084
		TDisplayMode aMode, TUint32 aValue) const
sl@0
  1085
	{
sl@0
  1086
	TUint32* buffer32 = (TUint32*)aPtr;
sl@0
  1087
	TInt shift;
sl@0
  1088
	TUint32 mask;
sl@0
  1089
sl@0
  1090
	switch (aMode)
sl@0
  1091
		{
sl@0
  1092
	case EGray2:
sl@0
  1093
		buffer32 += aX >> 5;
sl@0
  1094
		shift = aX & 0x1F;
sl@0
  1095
		mask = 0x1;
sl@0
  1096
		break;
sl@0
  1097
	case EGray4:
sl@0
  1098
		buffer32 += aX >> 4;
sl@0
  1099
		shift = (aX & 0xF) << 1;
sl@0
  1100
		mask = 0x3;
sl@0
  1101
		break;
sl@0
  1102
	case EGray16:
sl@0
  1103
	case EColor16:
sl@0
  1104
		buffer32 += aX >> 3;
sl@0
  1105
		shift = (aX & 0x7) << 2;
sl@0
  1106
		mask = 0xF;
sl@0
  1107
		break;
sl@0
  1108
	case EGray256:
sl@0
  1109
	case EColor256:
sl@0
  1110
		buffer32 += aX >> 2;
sl@0
  1111
		shift = (aX & 0x3) << 3;
sl@0
  1112
		mask = 0xFF;
sl@0
  1113
		break;
sl@0
  1114
	case EColor4K:
sl@0
  1115
		buffer32 += aX >> 1;
sl@0
  1116
		shift = (aX & 0x1) << 4;
sl@0
  1117
		mask = 0xFFF;
sl@0
  1118
		break;
sl@0
  1119
	case EColor64K:
sl@0
  1120
		buffer32 += aX >> 1;
sl@0
  1121
		shift = (aX & 0x1) << 4;
sl@0
  1122
		mask = 0xFFFF;
sl@0
  1123
		break;
sl@0
  1124
	case EColor16M:
sl@0
  1125
		{
sl@0
  1126
		// This mode requires special handling, because shifts and masks
sl@0
  1127
		// won't work.
sl@0
  1128
		TUint8* buffer8 = ((TUint8*)aPtr) + (aX * 3);
sl@0
  1129
		*buffer8++ = aValue & 0xFF;
sl@0
  1130
		*buffer8++ = (aValue >> 8) & 0xFF;
sl@0
  1131
		*buffer8++ = (aValue >> 16) & 0xFF;
sl@0
  1132
		// Return early as the buffer has been updated.
sl@0
  1133
		return;
sl@0
  1134
		}
sl@0
  1135
	case EColor16MU:
sl@0
  1136
		buffer32 += aX;
sl@0
  1137
		shift = 0;
sl@0
  1138
		mask = 0xFFFFFFFF;
sl@0
  1139
		aValue |= 0xFF000000;	// Force alpha to opaque.
sl@0
  1140
		break;
sl@0
  1141
	default:
sl@0
  1142
		buffer32 += aX;
sl@0
  1143
		shift = 0;
sl@0
  1144
		mask = 0xFFFFFFFF;
sl@0
  1145
		break;
sl@0
  1146
		};
sl@0
  1147
sl@0
  1148
	// Write pixel value into right part of word.
sl@0
  1149
	*buffer32 = (*buffer32 & ~(mask << shift)) | ((aValue & mask) << shift);
sl@0
  1150
	}
sl@0
  1151
sl@0
  1152
/**
sl@0
  1153
Copy contents of one buffer over another, depending on a per-pixel mask bit.
sl@0
  1154
@param aSrc		Source pixel buffer
sl@0
  1155
@param aSrcMode	Display mode of source
sl@0
  1156
@param aDst		Destination pixel buffer
sl@0
  1157
@param aDstMode	Display mode of destination
sl@0
  1158
@param aMsk		Mask buffer. Must be in EGray2 format
sl@0
  1159
@param aWidth	Number of pixels to copy
sl@0
  1160
@param aInvert	If ETrue, copy source where mask bit is clear, else copy where
sl@0
  1161
	it is set.
sl@0
  1162
*/
sl@0
  1163
void CTLowLevel::MaskedBlendBuffer(TAny* aSrc, TDisplayMode aSrcMode, TAny* aDst,
sl@0
  1164
		TDisplayMode aDstMode, TUint32* aMsk, TInt aWidth, TBool aInvert)
sl@0
  1165
	{
sl@0
  1166
	TColorConvertor& srcConvertor = ColorConvertor(aSrcMode);
sl@0
  1167
	TColorConvertor& dstConvertor = ColorConvertor(aDstMode);
sl@0
  1168
sl@0
  1169
	for (TInt xx = 0; xx < aWidth; xx++)
sl@0
  1170
		{
sl@0
  1171
		TUint32 pixelMask = ExtractBinaryValue(xx, aMsk, EGray2);
sl@0
  1172
		if (aInvert)
sl@0
  1173
			{
sl@0
  1174
			pixelMask = !pixelMask;
sl@0
  1175
			}
sl@0
  1176
sl@0
  1177
		if (pixelMask)
sl@0
  1178
			{
sl@0
  1179
			TUint32 dst32 = ExtractBinaryValue(xx, (TUint32*)aDst, aDstMode);
sl@0
  1180
			TUint32 src32 = ExtractBinaryValue(xx, (TUint32*)aSrc, aSrcMode);
sl@0
  1181
sl@0
  1182
			switch (aSrcMode)
sl@0
  1183
				{
sl@0
  1184
				// Only blend for source modes with alpha 
sl@0
  1185
				case EColor16MAP:
sl@0
  1186
				case EColor16MA:
sl@0
  1187
					{
sl@0
  1188
					// Convert source and destination pixel values to 16MAP
sl@0
  1189
					if (aDstMode != EColor16MAP)
sl@0
  1190
						{
sl@0
  1191
						dst32 = dstConvertor.Color(dst32).Color16MAP();
sl@0
  1192
						}
sl@0
  1193
					if (aSrcMode != EColor16MAP)
sl@0
  1194
						{
sl@0
  1195
						src32 = srcConvertor.Color(src32).Color16MAP();
sl@0
  1196
						}
sl@0
  1197
					// Both params must be 16MAP, output is likewise
sl@0
  1198
					dst32 = PMAPixelBlend(dst32, src32);
sl@0
  1199
					// Convert 16MAP to final format
sl@0
  1200
					dst32 = dstConvertor.Index(TRgb::Color16MAP(dst32));
sl@0
  1201
					}
sl@0
  1202
					break;
sl@0
  1203
				// Anything else is a copy (with format conversion) 
sl@0
  1204
				default:
sl@0
  1205
					dst32 = dstConvertor.Index(srcConvertor.Color(src32));
sl@0
  1206
					break;
sl@0
  1207
				}
sl@0
  1208
sl@0
  1209
			WriteBinaryValue(xx, aDst, aDstMode, dst32);
sl@0
  1210
			}
sl@0
  1211
		}
sl@0
  1212
	}
sl@0
  1213
sl@0
  1214
/**
sl@0
  1215
Returns the minimum number of bytes to hold the given number of pixels,
sl@0
  1216
rounded up to the next word boundary.
sl@0
  1217
@param aPixels	Number of pixels
sl@0
  1218
@param aMode	Display mode of pixels
sl@0
  1219
@return	Number of bytes to hold pixels
sl@0
  1220
*/
sl@0
  1221
TUint32 CTLowLevel::BytesForPixels(TUint32 aPixels, TDisplayMode aMode)
sl@0
  1222
	{
sl@0
  1223
	TUint32 bytes = LongWidth(aPixels, aMode);
sl@0
  1224
sl@0
  1225
	switch (aMode)
sl@0
  1226
		{
sl@0
  1227
		case EGray2:
sl@0
  1228
			bytes /= 8;
sl@0
  1229
			break;
sl@0
  1230
		case EGray4:
sl@0
  1231
			bytes /= 4;
sl@0
  1232
			break;
sl@0
  1233
		case EGray16:
sl@0
  1234
		case EColor16:
sl@0
  1235
			bytes /= 2;
sl@0
  1236
			break;
sl@0
  1237
		case EColor4K:
sl@0
  1238
		case EColor64K:
sl@0
  1239
			bytes *= 2;
sl@0
  1240
			break;
sl@0
  1241
		case EColor16M:
sl@0
  1242
			bytes *= 3;
sl@0
  1243
			break;
sl@0
  1244
		case EColor16MU:
sl@0
  1245
		case EColor16MA:
sl@0
  1246
		case EColor16MAP:
sl@0
  1247
			bytes *= 4;
sl@0
  1248
			break;
sl@0
  1249
		}
sl@0
  1250
	return bytes;
sl@0
  1251
	}
sl@0
  1252
sl@0
  1253
/**
sl@0
  1254
Compare the actual blend results with the expected ones, allowing for some
sl@0
  1255
blending errors. Both buffers must be in aMode format
sl@0
  1256
@param aActual		Start of actual results
sl@0
  1257
@param aExpected	Start of expected results
sl@0
  1258
@param aWidth		Number of pixels to check
sl@0
  1259
@param aMode		Display mode of the pixels in the buffers
sl@0
  1260
@param aBlended		ETrue if pixels were blended, EFalse if they were opaque
sl@0
  1261
@return	ETrue if buffers compared OK, EFalse if there was a mismatch.
sl@0
  1262
*/
sl@0
  1263
TBool CTLowLevel::CompareBlendMaskResults(TAny* aActual, TAny* aExpected, 
sl@0
  1264
		TUint32 aWidth, TDisplayMode aMode, TBool aBlended, TDisplayMode aSrcMode)
sl@0
  1265
	{
sl@0
  1266
	if (aBlended)
sl@0
  1267
		{
sl@0
  1268
		// There can be blending rounding errors, so allow for these. In general
sl@0
  1269
		// allow for one bit of error, taking into account the precision of
sl@0
  1270
		// each component.
sl@0
  1271
		TInt maxRBErr;
sl@0
  1272
		TInt maxGErr;
sl@0
  1273
		switch (aMode)
sl@0
  1274
			{
sl@0
  1275
			case EColor4K:
sl@0
  1276
				// All components are four bits
sl@0
  1277
				maxRBErr = maxGErr = 17;
sl@0
  1278
				break;
sl@0
  1279
			case EColor64K:
sl@0
  1280
				// Six bits for green, five for the others, so error
sl@0
  1281
				// varies.
sl@0
  1282
				maxRBErr = 9;
sl@0
  1283
				maxGErr = 5;
sl@0
  1284
				break;
sl@0
  1285
			default:
sl@0
  1286
				// For 16MAP, it will be dependent on the alpha value.
sl@0
  1287
				maxRBErr = maxGErr = 1;
sl@0
  1288
				break;
sl@0
  1289
			}
sl@0
  1290
sl@0
  1291
		// Compare each pixel, allowing for the error in each component.
sl@0
  1292
		for (TInt xx = 0; xx < aWidth; xx++)
sl@0
  1293
			{
sl@0
  1294
			TRgb exp = ExtractRgbValue(xx, (TUint8*)aExpected, aMode);
sl@0
  1295
			TRgb act = ExtractRgbValue(xx, (TUint8*)aActual, aMode);
sl@0
  1296
			
sl@0
  1297
			if (aMode == EColor16MAP)
sl@0
  1298
				{
sl@0
  1299
				// Take into account that components have been premultiplied
sl@0
  1300
				TInt alpha = exp.Alpha();
sl@0
  1301
				if (alpha > 0)
sl@0
  1302
					{
sl@0
  1303
					maxRBErr = maxGErr = (0xFF + alpha - 1) / alpha;
sl@0
  1304
					}
sl@0
  1305
				if (aSrcMode == EColor16MA && (maxGErr < 3 || maxRBErr < 3))
sl@0
  1306
					{
sl@0
  1307
					maxGErr = 3;
sl@0
  1308
					maxRBErr = 3;
sl@0
  1309
					}
sl@0
  1310
				}
sl@0
  1311
			
sl@0
  1312
			if (AbsDiff(exp.Red(), act.Red()) > maxRBErr ||
sl@0
  1313
					AbsDiff(exp.Green(), act.Green()) > maxGErr ||
sl@0
  1314
					AbsDiff(exp.Blue(), act.Blue()) > maxRBErr ||
sl@0
  1315
					exp.Alpha() != act.Alpha())
sl@0
  1316
				{
sl@0
  1317
				INFO_PRINTF4(_L("At %d, expected 0x%08.8x, got 0x%08.8x"), 
sl@0
  1318
						xx, exp.Internal(), act.Internal());
sl@0
  1319
				return EFalse;
sl@0
  1320
				}
sl@0
  1321
			}
sl@0
  1322
		return ETrue;
sl@0
  1323
		}
sl@0
  1324
	else
sl@0
  1325
		{
sl@0
  1326
		// For non-alpha sources there is no blending, so results
sl@0
  1327
		// should be exact.
sl@0
  1328
		TUint32 stride = BytesForPixels(aWidth, aMode);
sl@0
  1329
		return (Mem::Compare((TUint8*)aActual, stride, (TUint8*)aExpected, stride) == 0);
sl@0
  1330
		}
sl@0
  1331
	}
sl@0
  1332
sl@0
  1333
class TFunctionThread
sl@0
  1334
	{
sl@0
  1335
protected:
sl@0
  1336
	TFunctionThread():iExitHow(ENotStarted)	
sl@0
  1337
		{}
sl@0
  1338
	TInt LaunchThreadFunction(const TDesC& aName);
sl@0
  1339
private:
sl@0
  1340
	static TInt TheThreadFunction(TAny*);
sl@0
  1341
	virtual TInt	ThreadFunctionL()=0;
sl@0
  1342
public:
sl@0
  1343
	enum {
sl@0
  1344
		ENotStarted,
sl@0
  1345
		ERunning,	//should never see this
sl@0
  1346
		EReturn,
sl@0
  1347
		ELeave,
sl@0
  1348
		EPanic,
sl@0
  1349
		ETerminate,
sl@0
  1350
		};
sl@0
  1351
	TInt	iExitHow;
sl@0
  1352
	TInt	iExitCode;	//Currently don't store the panic category string.
sl@0
  1353
	};
sl@0
  1354
sl@0
  1355
TInt TFunctionThread::LaunchThreadFunction(const TDesC& aName)
sl@0
  1356
	{
sl@0
  1357
	RThread thrd;
sl@0
  1358
	TRequestStatus stat;
sl@0
  1359
	enum { //8kb to 2mb
sl@0
  1360
		KMinHeapSize=0x2000,
sl@0
  1361
		KMaxHeapSize=0x200000
sl@0
  1362
		};
sl@0
  1363
	TInt created=thrd.Create(aName,TheThreadFunction,KDefaultStackSize,KMinHeapSize,KMaxHeapSize,this);
sl@0
  1364
	if (created<KErrNone)
sl@0
  1365
		{
sl@0
  1366
		iExitCode=created;
sl@0
  1367
		return created;
sl@0
  1368
		}
sl@0
  1369
	thrd.SetPriority(EPriorityMuchMore);
sl@0
  1370
	thrd.Logon(stat);
sl@0
  1371
	User::SetJustInTime(EFalse);
sl@0
  1372
	thrd.Resume();
sl@0
  1373
	User::WaitForRequest(stat);
sl@0
  1374
	if ( iExitHow!=ENotStarted || iExitHow==ERunning )
sl@0
  1375
		{
sl@0
  1376
		iExitCode=thrd.ExitReason();
sl@0
  1377
		switch (thrd.ExitType())
sl@0
  1378
			{
sl@0
  1379
			case EExitKill:			iExitHow=EReturn;		break;
sl@0
  1380
			case EExitPanic:		iExitHow=EPanic;		break;
sl@0
  1381
			case EExitTerminate:	iExitHow=ETerminate;	break;
sl@0
  1382
			default:
sl@0
  1383
				ASSERT(EFalse);
sl@0
  1384
			}
sl@0
  1385
		}
sl@0
  1386
	thrd.Close();
sl@0
  1387
	User::SetJustInTime(ETrue);
sl@0
  1388
	return KErrNone;
sl@0
  1389
	}
sl@0
  1390
sl@0
  1391
TInt TFunctionThread::TheThreadFunction(TAny* aThis)
sl@0
  1392
	{
sl@0
  1393
	TFunctionThread* thisThis=(TFunctionThread*)aThis;
sl@0
  1394
	if (thisThis==NULL)
sl@0
  1395
		{
sl@0
  1396
		User::Panic(_L("NoThis"),0x1);
sl@0
  1397
		}
sl@0
  1398
	thisThis->iExitHow=thisThis->ERunning;
sl@0
  1399
	TInt returnErr = KErrNone;
sl@0
  1400
	TRAPD(leaveErr,returnErr=thisThis->ThreadFunctionL());
sl@0
  1401
	if (leaveErr)
sl@0
  1402
		{
sl@0
  1403
		thisThis->iExitHow=ELeave;
sl@0
  1404
		thisThis->iExitCode=leaveErr;
sl@0
  1405
		return leaveErr;
sl@0
  1406
		}
sl@0
  1407
	else
sl@0
  1408
		{
sl@0
  1409
		thisThis->iExitHow=EReturn;
sl@0
  1410
		thisThis->iExitCode=returnErr;
sl@0
  1411
		return returnErr;
sl@0
  1412
		}
sl@0
  1413
	}
sl@0
  1414
sl@0
  1415
/** This thread verifies whether a range of memory is accessible 
sl@0
  1416
  The range is read sequentially until it panics, or the range is completed.
sl@0
  1417
  It is useful to input a range of addresses where some are valid and some fail 
sl@0
  1418
  in order to demonstrate an edge against which an algorithm that performs illegal reads can subsequently be tested.
sl@0
  1419
  The FailOffset() returned index indicates the offset from the start at which the memory access caused a panic. 
sl@0
  1420
 **/
sl@0
  1421
class TTestMemThread:public TFunctionThread
sl@0
  1422
	{
sl@0
  1423
public:
sl@0
  1424
	TTestMemThread(TUint32* aStartAddress,TUint32* aEndAddress);
sl@0
  1425
	TInt FailOffset();
sl@0
  1426
private:
sl@0
  1427
	virtual TInt	ThreadFunctionL();
sl@0
  1428
private:
sl@0
  1429
	TUint32* iStartAddress;
sl@0
  1430
	TUint32* iEndAddress;
sl@0
  1431
	volatile TUint32* iLastAddressTried;
sl@0
  1432
	volatile TUint32  iCopyValueHere;
sl@0
  1433
	
sl@0
  1434
	};
sl@0
  1435
sl@0
  1436
TTestMemThread::TTestMemThread(TUint32* aStartAddress,TUint32* aEndAddress):
sl@0
  1437
	iStartAddress(aStartAddress),
sl@0
  1438
	iEndAddress(aEndAddress),
sl@0
  1439
	iLastAddressTried(NULL)
sl@0
  1440
	{
sl@0
  1441
	ASSERT(aStartAddress);
sl@0
  1442
	ASSERT(aEndAddress);
sl@0
  1443
	LaunchThreadFunction(_L("MemTest"));
sl@0
  1444
	}
sl@0
  1445
sl@0
  1446
/**
sl@0
  1447
 *	Returns the number of successful memory reads before a panic occurred
sl@0
  1448
 * 	Or various error codes if the test didn't run or didn't panic.
sl@0
  1449
 * 
sl@0
  1450
 **/
sl@0
  1451
TInt TTestMemThread::FailOffset()
sl@0
  1452
	{
sl@0
  1453
	if (iExitHow==EReturn)
sl@0
  1454
		{
sl@0
  1455
		return KErrCompletion;
sl@0
  1456
		}
sl@0
  1457
	else
sl@0
  1458
		{
sl@0
  1459
		if (iExitHow==EPanic)
sl@0
  1460
			{
sl@0
  1461
			if (iLastAddressTried)
sl@0
  1462
				{
sl@0
  1463
				TInt retval=iLastAddressTried-iStartAddress;
sl@0
  1464
				if (iEndAddress-iStartAddress<0)
sl@0
  1465
					{
sl@0
  1466
					retval=-retval;
sl@0
  1467
					}
sl@0
  1468
				if (retval<0)
sl@0
  1469
					{
sl@0
  1470
					return KErrCorrupt;
sl@0
  1471
					}
sl@0
  1472
				else
sl@0
  1473
					{
sl@0
  1474
					return retval;
sl@0
  1475
					}
sl@0
  1476
				}
sl@0
  1477
			else
sl@0
  1478
				{
sl@0
  1479
				return KErrNotFound;
sl@0
  1480
				}
sl@0
  1481
			}
sl@0
  1482
		else
sl@0
  1483
			{
sl@0
  1484
			return KErrGeneral; 
sl@0
  1485
			}
sl@0
  1486
		}
sl@0
  1487
	}
sl@0
  1488
/*
sl@0
  1489
 * This thread function allows a test to verify that a particular address range 
sl@0
  1490
 * is actually inaccessable.
sl@0
  1491
 * I.e. that attempting to read from the given address range causes a panic.
sl@0
  1492
 */
sl@0
  1493
TInt TTestMemThread::ThreadFunctionL()
sl@0
  1494
	{
sl@0
  1495
	if (iStartAddress && iEndAddress)
sl@0
  1496
		{
sl@0
  1497
		TInt delta=1;
sl@0
  1498
		if (iStartAddress>iEndAddress)
sl@0
  1499
			{
sl@0
  1500
			delta=-1;
sl@0
  1501
			}
sl@0
  1502
		for (TUint32 volatile* tryAddress=iStartAddress;tryAddress!=iEndAddress;tryAddress+=delta)
sl@0
  1503
			{
sl@0
  1504
			iLastAddressTried=tryAddress;
sl@0
  1505
			iCopyValueHere=*tryAddress;
sl@0
  1506
			}
sl@0
  1507
		return 0;
sl@0
  1508
		}
sl@0
  1509
	return KErrArgument;
sl@0
  1510
	}
sl@0
  1511
sl@0
  1512
void CTLowLevel::ClosePanicDialogs()
sl@0
  1513
	{
sl@0
  1514
	RWsSession session;
sl@0
  1515
	TInt err = session.Connect();
sl@0
  1516
	TEST(err == KErrNone);
sl@0
  1517
	TInt idFocus = session.GetFocusWindowGroup();
sl@0
  1518
	TWsEvent event;
sl@0
  1519
	event.SetType(EEventKey); //EEventKeyDown
sl@0
  1520
	TKeyEvent* keyEvent = event.Key();
sl@0
  1521
	keyEvent->iCode = EKeyEscape;
sl@0
  1522
	keyEvent->iScanCode = EStdKeyEscape;
sl@0
  1523
	keyEvent->iModifiers = 0;
sl@0
  1524
	TInt theLimit = 50;
sl@0
  1525
	while(idFocus != NULL && (theLimit-- > 0))
sl@0
  1526
		{
sl@0
  1527
		session.SendEventToAllWindowGroups(event);
sl@0
  1528
		TInt idNewFocus = session.GetFocusWindowGroup();
sl@0
  1529
		idFocus=idNewFocus;
sl@0
  1530
		}
sl@0
  1531
	session.Flush();
sl@0
  1532
	session.Close();
sl@0
  1533
	}
sl@0
  1534
sl@0
  1535
sl@0
  1536
/**
sl@0
  1537
@SYMTestCaseID GRAPHICS-SCREENDRIVER-0003
sl@0
  1538
@SYMTestCaseDesc Test that FastBlendBitmapMasked masking works correctly
sl@0
  1539
@SYMDEF INC120146 PDEF120693 PDEF120680 INC120742 PDEF121725
sl@0
  1540
@SYMTestPriority High
sl@0
  1541
@SYMTestActions Test actions are:
sl@0
  1542
	Create pseudorandom initial contents, source and mask lines.
sl@0
  1543
	Set a line of the screen to the initial contents.
sl@0
  1544
	Use FastBlendBitmapMasked, with and without inverted bitmask, to write
sl@0
  1545
		source to target.
sl@0
  1546
	Read line contents back.
sl@0
  1547
	Check each pixel is either the initial value, or the source or a blend,
sl@0
  1548
		depending on corresponding mask pixel.
sl@0
  1549
	Repeat this whole sequence with supported source display modes.
sl@0
  1550
	NOTE - wrapped in memory check for edge case defect INC120742
sl@0
  1551
@SYMTestExpectedResults The correct pixel values are set, based on the mask.
sl@0
  1552
*/
sl@0
  1553
void CTLowLevel::TestFastBlendBitmapMasked(const TInt aRetry)
sl@0
  1554
	{
sl@0
  1555
	const TInt KRetryAmount = 10;
sl@0
  1556
sl@0
  1557
	TAny* interface = NULL;
sl@0
  1558
	TInt err = iDrawDevice->GetInterface(KFastBlendInterfaceID, interface);
sl@0
  1559
	if(err == KErrNone)
sl@0
  1560
		{
sl@0
  1561
		if (aRetry == 0)
sl@0
  1562
			{
sl@0
  1563
			INFO_PRINTF1(_L("START ---->TestFastBlendBitmapMasked"));
sl@0
  1564
			}
sl@0
  1565
sl@0
  1566
		MFastBlend* fastBlend = reinterpret_cast<MFastBlend*>(interface);
sl@0
  1567
		TInt yPos = iSize.iHeight / 2;
sl@0
  1568
		TPoint pt(0,yPos);
sl@0
  1569
		TSize lineSize(iSize.iWidth, 1);
sl@0
  1570
		TRect lineRect(lineSize);
sl@0
  1571
sl@0
  1572
		TInt destStride = iDrawDevice->ScanLineBytes();
sl@0
  1573
 		TInt maskStride = (iSize.iWidth + 7) / 8;
sl@0
  1574
		TInt maskPages = (maskStride/4096+1);
sl@0
  1575
		maskPages+=20;
sl@0
  1576
		// Allocate large enough buffers for all modes
sl@0
  1577
		TAny* source = User::Alloc(iSize.iWidth * 4);
sl@0
  1578
		TAny* expected = User::Alloc(destStride);
sl@0
  1579
		CFbsBitmap testBitmap;
sl@0
  1580
		testBitmap.Create(TSize(1024,maskPages),EColor16MA);
sl@0
  1581
		TUint32* mask = testBitmap.DataAddress()+1024-(maskStride%4096)/4;
sl@0
  1582
		TUint32* slb = iDrawDevice->ScanLineBuffer();
sl@0
  1583
sl@0
  1584
		Check(source != NULL && expected != NULL && mask != NULL);
sl@0
  1585
sl@0
  1586
		TUint32* bitmapData=testBitmap.DataAddress();
sl@0
  1587
		SEpocBitmapHeader header1 = testBitmap.Header();
sl@0
  1588
		TUint32* pastBitmapData=bitmapData+((header1.iBitmapSize-header1.iStructSize)>>2);
sl@0
  1589
		mask = pastBitmapData- (maskStride+3)/4;
sl@0
  1590
	
sl@0
  1591
		TBool canGenerateDefectScenario = EFalse;
sl@0
  1592
		TTestMemThread memThread(pastBitmapData-2,pastBitmapData+2);
sl@0
  1593
		TInt failAt=memThread.FailOffset();
sl@0
  1594
		if (failAt<0)
sl@0
  1595
			{
sl@0
  1596
			INFO_PRINTF2(_L("Error generated by test thread! %i - BAD"),failAt);
sl@0
  1597
			}
sl@0
  1598
		else if (failAt<=1)
sl@0
  1599
			{
sl@0
  1600
			INFO_PRINTF1(_L("Bitmap memory is inaccessable - BAD"));
sl@0
  1601
			}
sl@0
  1602
		else if (failAt>2)
sl@0
  1603
			{
sl@0
  1604
			INFO_PRINTF1(_L("Memory after bitmap is accessable - BAD"));
sl@0
  1605
			}
sl@0
  1606
		else
sl@0
  1607
			{
sl@0
  1608
			INFO_PRINTF1(_L("Memory after bitmap is inaccessable - GOOD"));
sl@0
  1609
			canGenerateDefectScenario=ETrue;
sl@0
  1610
			}
sl@0
  1611
		ClosePanicDialogs();
sl@0
  1612
sl@0
  1613
		if (!canGenerateDefectScenario)
sl@0
  1614
			{
sl@0
  1615
			//if this doesn't work out then the memory allocator is not like it was when the defect was raised!
sl@0
  1616
			//so the test is no longer any good.
sl@0
  1617
			if (aRetry == KRetryAmount)
sl@0
  1618
				{
sl@0
  1619
				INFO_PRINTF2(_L("Failed %d times - Overall test failure"),KRetryAmount);
sl@0
  1620
				Check(EFalse);
sl@0
  1621
				}
sl@0
  1622
			else
sl@0
  1623
				{
sl@0
  1624
				INFO_PRINTF2(_L("RETRYING - attempt %d"),aRetry+2);
sl@0
  1625
				TestFastBlendBitmapMasked(aRetry+1);
sl@0
  1626
				}
sl@0
  1627
			}
sl@0
  1628
		else
sl@0
  1629
			{
sl@0
  1630
			INFO_PRINTF1(_L("Performing test"));
sl@0
  1631
			for (TInt sourceModeIndex = 0; sourceModeIndex < KNumberDisplayModes1; sourceModeIndex++)
sl@0
  1632
			 	{
sl@0
  1633
			 	for (TInt invert = 0; invert < 2; invert++)
sl@0
  1634
			 		{
sl@0
  1635
			 		TDisplayMode sourceMode = TestDisplayMode1[sourceModeIndex];
sl@0
  1636
			 		TInt sourceStride = BytesForPixels(iSize.iWidth, sourceMode);
sl@0
  1637
			 		TBool blended = (sourceMode == EColor16MA || sourceMode == EColor16MAP);
sl@0
  1638
			 		
sl@0
  1639
			 		// Initialise (randomise) the buffers for this iteration
sl@0
  1640
			 		FillBuffer((TUint8*)source, sourceStride, sourceMode, ETrue);
sl@0
  1641
			 		FillBuffer((TUint8*)expected, destStride, iDispMode, ETrue);
sl@0
  1642
			 		FillBuffer((TUint8*)mask, maskStride, EGray2, ETrue);
sl@0
  1643
			 		
sl@0
  1644
			 		// Write out the initial contents
sl@0
  1645
			 		iDrawDevice->WriteLine(0, yPos, iSize.iWidth, (TUint32*)expected,
sl@0
  1646
			 				CGraphicsContext::EDrawModeWriteAlpha);
sl@0
  1647
		
sl@0
  1648
			 		// Fast, masked overwrite, with or without mask inversion
sl@0
  1649
			 		TInt result = fastBlend->FastBlendBitmapMasked(pt, 
sl@0
  1650
			 				(TUint32*)source, sourceStride, lineSize, lineRect,
sl@0
  1651
			 				sourceMode, mask, maskStride, EGray2, lineSize,
sl@0
  1652
			 				TPoint(), invert, CGraphicsContext::EDrawModePEN, 
sl@0
  1653
			 				CFbsDrawDevice::ENoShadow);
sl@0
  1654
sl@0
  1655
			 		if (result == KErrNotSupported)
sl@0
  1656
			 			{
sl@0
  1657
			 			// Unsupported combination of parameters, move on.
sl@0
  1658
			 			continue;
sl@0
  1659
			 			}
sl@0
  1660
		
sl@0
  1661
			 		// Use mask to blend source with 'expected' to get the expected
sl@0
  1662
			 		// output
sl@0
  1663
			 		MaskedBlendBuffer(source, sourceMode, expected, iDispMode, 
sl@0
  1664
			 				mask, iSize.iWidth, invert);
sl@0
  1665
sl@0
  1666
			 		// Read back actual output and compare with expected.
sl@0
  1667
			 		iDrawDevice->ReadLine(0, yPos, iSize.iWidth, slb, iDispMode);
sl@0
  1668
sl@0
  1669
			 		if (!CompareBlendMaskResults(slb, expected, iSize.iWidth,
sl@0
  1670
			 				iDispMode, blended, sourceMode))
sl@0
  1671
			 			{
sl@0
  1672
			 			INFO_PRINTF3(_L("Output mismatch: source mode %S, invert=%d"), 
sl@0
  1673
			 					&DisplayModeNames1[sourceModeIndex], invert);
sl@0
  1674
			 			// Report other details, plus fail the overall test.
sl@0
  1675
			 			Check(EFalse);
sl@0
  1676
			 			}
sl@0
  1677
			 		iIteration++;
sl@0
  1678
			 		}
sl@0
  1679
sl@0
  1680
			 	}
sl@0
  1681
			TTestMemThread memThreadAfter(pastBitmapData-2,pastBitmapData+2);
sl@0
  1682
			failAt=memThreadAfter.FailOffset();
sl@0
  1683
			if (failAt != 2)
sl@0
  1684
				{
sl@0
  1685
				INFO_PRINTF1(_L("Memory after bitmap is accessable - BAD"));
sl@0
  1686
				if (aRetry >= KRetryAmount)
sl@0
  1687
					{
sl@0
  1688
					INFO_PRINTF2(_L("Failed %d times - Overall test failure"),KRetryAmount);
sl@0
  1689
					Check(EFalse);
sl@0
  1690
					}
sl@0
  1691
				else
sl@0
  1692
					{
sl@0
  1693
					INFO_PRINTF2(_L("RETRYING - attempt %d"),aRetry+2);
sl@0
  1694
					TestFastBlendBitmapMasked(aRetry+1);
sl@0
  1695
					}
sl@0
  1696
				}
sl@0
  1697
			else
sl@0
  1698
				{
sl@0
  1699
				INFO_PRINTF1(_L("Memory after bitmap is inaccessable - GOOD"));
sl@0
  1700
				}
sl@0
  1701
			ClosePanicDialogs();
sl@0
  1702
			}
sl@0
  1703
		if (aRetry == 0)
sl@0
  1704
			{
sl@0
  1705
			INFO_PRINTF1(_L("END ---->TestFastBlendBitmapMasked"));
sl@0
  1706
			Report();
sl@0
  1707
			}
sl@0
  1708
sl@0
  1709
		User::Free(source);
sl@0
  1710
		User::Free(expected);
sl@0
  1711
		testBitmap.Reset();
sl@0
  1712
		}
sl@0
  1713
	}
sl@0
  1714
sl@0
  1715
void CTLowLevel::TestWriteRGBAlpha()
sl@0
  1716
	{
sl@0
  1717
	TUint8* writeBuffer = new TUint8[iSize.iWidth * 4];
sl@0
  1718
	TUint8* writeBuffer2 = new TUint8[iSize.iWidth * 4];
sl@0
  1719
	TUint8* maskBuffer = new TUint8[iSize.iWidth];
sl@0
  1720
	Check(writeBuffer != NULL);
sl@0
  1721
	Check(maskBuffer != NULL);
sl@0
  1722
sl@0
  1723
	TInt nRect;
sl@0
  1724
sl@0
  1725
	//special test for EColor16MAP
sl@0
  1726
	if (iDispMode == EColor16MAP)
sl@0
  1727
		{
sl@0
  1728
		//mask fill has vaues 0x00, 0xff, and 0x3A.  The mask is used for blending
sl@0
  1729
		for (TInt maskFillCount=0; maskFillCount<KMaskFill;maskFillCount++)
sl@0
  1730
			{
sl@0
  1731
			for (TInt userDispMode=0; userDispMode< KUserDispModes; userDispMode++)
sl@0
  1732
				{
sl@0
  1733
				for (TInt shadowMode = 0; shadowMode < KNumShadowModes; shadowMode++)
sl@0
  1734
					{
sl@0
  1735
					for (nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  1736
						{
sl@0
  1737
						for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
  1738
							{
sl@0
  1739
							for (TInt nColor = 0; nColor < KNumTestColors; nColor++)
sl@0
  1740
								{
sl@0
  1741
								iDrawDevice->SetUserDisplayMode(UserDisplayModes[userDispMode]);
sl@0
  1742
								iUserDispMode = UserDisplayModes[userDispMode];
sl@0
  1743
								if (iUserDispMode == EColor16MA)
sl@0
  1744
									i16MAUserDispMode = ETrue;
sl@0
  1745
								else
sl@0
  1746
									i16MAUserDispMode = EFalse;
sl@0
  1747
sl@0
  1748
								TRgb col = TestColor[nColor];
sl@0
  1749
								TUint32 internal = col.Internal();
sl@0
  1750
								TUint32 *writeBuf32 = (TUint32*)writeBuffer;
sl@0
  1751
								TInt cnt;
sl@0
  1752
								//fill the buffer with colour
sl@0
  1753
								for (cnt=0;cnt<iSize.iWidth;cnt++)
sl@0
  1754
									{
sl@0
  1755
									*writeBuf32=internal;
sl@0
  1756
									writeBuf32++;
sl@0
  1757
									}
sl@0
  1758
sl@0
  1759
								Mem::Fill(maskBuffer,iSize.iWidth,MaskFill[maskFillCount]);
sl@0
  1760
sl@0
  1761
								TRgb bakCol = TestBackground[nBackColor];
sl@0
  1762
								Clear(bakCol);
sl@0
  1763
								TRect rect = TestRect[nRect];
sl@0
  1764
sl@0
  1765
								iDrawDevice->CFbsDrawDevice::SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1766
								iDrawDevice->CFbsDrawDevice::SetFadingParameters(100,200);
sl@0
  1767
								iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1768
sl@0
  1769
								TInt yy;
sl@0
  1770
								for (yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1771
									{
sl@0
  1772
									iDrawDevice->WriteRgbAlphaLine(rect.iTl.iX,yy,rect.Width(),writeBuffer,maskBuffer,CGraphicsContext::EDrawModePEN);
sl@0
  1773
									iIteration++;
sl@0
  1774
									}
sl@0
  1775
sl@0
  1776
								//ensure the colour has the 0xff mask value
sl@0
  1777
								TRgb checkColor;
sl@0
  1778
								//use a combined alpha for the check colour
sl@0
  1779
								TUint32 combinedAlpha = MaskFill[maskFillCount]*((internal&0xff000000)>>24);
sl@0
  1780
								combinedAlpha = ((combinedAlpha <<16) & 0xff000000);
sl@0
  1781
								checkColor.SetInternal((internal&0x00ffffff)|combinedAlpha);
sl@0
  1782
								//check colour is not a PMA colour, but has alpha
sl@0
  1783
								CheckRgb(rect,checkColor,bakCol,CGraphicsContext::EDrawModePEN,CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1784
								CheckBackground(rect,bakCol);
sl@0
  1785
sl@0
  1786
								//the other WriteRgbAlpha line uses the other shadow mode
sl@0
  1787
								TUint32 *writeBuf2 = (TUint32*)writeBuffer2;
sl@0
  1788
								TUint32 buf2val= NonPMA2PMAPixel(bakCol.Internal());
sl@0
  1789
								//fill the buffer with colour
sl@0
  1790
								for (cnt=0;cnt<iSize.iWidth;cnt++)
sl@0
  1791
									{
sl@0
  1792
									*writeBuf2=buf2val;
sl@0
  1793
									writeBuf2++;
sl@0
  1794
									}
sl@0
  1795
sl@0
  1796
								iDrawDevice->CFbsDrawDevice::SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1797
								iDrawDevice->CFbsDrawDevice::SetFadingParameters(100,200);
sl@0
  1798
								iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1799
sl@0
  1800
								for (yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1801
									{
sl@0
  1802
									iDrawDevice->WriteRgbAlphaLine(rect.iTl.iX,yy,rect.Width(),
sl@0
  1803
										writeBuffer,
sl@0
  1804
										writeBuffer2,
sl@0
  1805
										maskBuffer,
sl@0
  1806
										CGraphicsContext::EDrawModeWriteAlpha);
sl@0
  1807
									iIteration++;
sl@0
  1808
									}
sl@0
  1809
								//require to Shadow After the checkColor, no shadow with a zero mask
sl@0
  1810
								TBool shadowModeChanged = EFalse;
sl@0
  1811
								if (MaskFill[maskFillCount])
sl@0
  1812
									{
sl@0
  1813
									iPostBlendShadow = (TPostShadowMode) shadowMode;
sl@0
  1814
									shadowMode = 0;
sl@0
  1815
									shadowModeChanged = ETrue;
sl@0
  1816
									}
sl@0
  1817
								CheckRgb(rect,checkColor,bakCol,CGraphicsContext::EDrawModePEN,shadowMode);
sl@0
  1818
								if(shadowModeChanged) shadowMode = iPostBlendShadow;
sl@0
  1819
								iPostBlendShadow = ENoPostShadow;
sl@0
  1820
								CheckBackground(rect,bakCol);
sl@0
  1821
sl@0
  1822
								Clear(bakCol);
sl@0
  1823
sl@0
  1824
								iDrawDevice->CFbsDrawDevice::SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1825
								iDrawDevice->CFbsDrawDevice::SetFadingParameters(100,200);
sl@0
  1826
								iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1827
sl@0
  1828
								for (TInt yy2 = rect.iTl.iY; yy2 < rect.iBr.iY; yy2++)
sl@0
  1829
									{
sl@0
  1830
									iDrawDevice->WriteRgbAlphaMulti(rect.iTl.iX,yy2,rect.Width(),col,maskBuffer);
sl@0
  1831
									iIteration++;
sl@0
  1832
									}
sl@0
  1833
sl@0
  1834
								CheckRgb(rect,checkColor,bakCol,CGraphicsContext::EDrawModePEN,CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  1835
								CheckBackground(rect,bakCol);
sl@0
  1836
								}
sl@0
  1837
							}
sl@0
  1838
						}
sl@0
  1839
					}
sl@0
  1840
				}
sl@0
  1841
			}
sl@0
  1842
		}
sl@0
  1843
sl@0
  1844
	Report();
sl@0
  1845
	iDrawDevice->SetUserDisplayMode(iDispMode);
sl@0
  1846
	i16MAUserDispMode = EFalse;
sl@0
  1847
	iUserDispMode = ENone;
sl@0
  1848
	Mem::Fill(writeBuffer,iSize.iWidth * 4,0xff);
sl@0
  1849
	Mem::Fill(maskBuffer,iSize.iWidth,0xff);
sl@0
  1850
sl@0
  1851
	for (nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  1852
		{
sl@0
  1853
		for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
  1854
			{
sl@0
  1855
			if ((nBackColor>=KMaxNon16BackColours) && (iDispMode!= EColor16MAP))
sl@0
  1856
				continue;
sl@0
  1857
sl@0
  1858
			TRgb bakCol = TestBackground[nBackColor];
sl@0
  1859
			Clear(bakCol);
sl@0
  1860
			TRect rect = TestRect[nRect];
sl@0
  1861
sl@0
  1862
			for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1863
				{
sl@0
  1864
				iDrawDevice->WriteRgbAlphaLine(rect.iTl.iX,yy,rect.Width(),writeBuffer,maskBuffer,CGraphicsContext::EDrawModePEN);
sl@0
  1865
				iIteration++;
sl@0
  1866
				}
sl@0
  1867
sl@0
  1868
			CheckRgb(rect,KRgbWhite,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1869
			CheckBackground(rect,bakCol);
sl@0
  1870
sl@0
  1871
			Clear(bakCol);
sl@0
  1872
sl@0
  1873
			for (TInt yy2 = rect.iTl.iY; yy2 < rect.iBr.iY; yy2++)
sl@0
  1874
				{
sl@0
  1875
				iDrawDevice->WriteRgbAlphaMulti(rect.iTl.iX,yy2,rect.Width(),KRgbWhite,maskBuffer);
sl@0
  1876
				iIteration++;
sl@0
  1877
				}
sl@0
  1878
sl@0
  1879
			CheckRgb(rect,KRgbWhite,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1880
			CheckBackground(rect,bakCol);
sl@0
  1881
sl@0
  1882
			}
sl@0
  1883
		}
sl@0
  1884
	Report();
sl@0
  1885
sl@0
  1886
	Mem::FillZ(writeBuffer,iSize.iWidth * 3);
sl@0
  1887
sl@0
  1888
	for (nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  1889
		{
sl@0
  1890
		for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
  1891
			{
sl@0
  1892
			if ((nBackColor>=KMaxNon16BackColours) && (iDispMode!= EColor16MAP))
sl@0
  1893
				continue;
sl@0
  1894
sl@0
  1895
			//need to fill with 0xff alpha, so blending takes place
sl@0
  1896
			if (iDispMode== EColor16MAP)
sl@0
  1897
				{
sl@0
  1898
				const TUint32 black = 0xff000000;
sl@0
  1899
				TUint32 *writeBuf32 = (TUint32*) writeBuffer;
sl@0
  1900
				for (TInt cnt=0;cnt<iSize.iWidth;cnt++)
sl@0
  1901
					{
sl@0
  1902
					*writeBuf32=black;
sl@0
  1903
					writeBuf32++;
sl@0
  1904
					}
sl@0
  1905
				}
sl@0
  1906
sl@0
  1907
			TRgb bakCol = TestBackground[nBackColor];
sl@0
  1908
			Clear(bakCol);
sl@0
  1909
			TRect rect = TestRect[nRect];
sl@0
  1910
sl@0
  1911
			for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1912
				{
sl@0
  1913
				iDrawDevice->WriteRgbAlphaLine(rect.iTl.iX,yy,rect.Width(),writeBuffer,maskBuffer,CGraphicsContext::EDrawModePEN);
sl@0
  1914
				iIteration++;
sl@0
  1915
				}
sl@0
  1916
sl@0
  1917
			CheckRgb(rect,KRgbBlack,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1918
			CheckBackground(rect,bakCol);
sl@0
  1919
sl@0
  1920
			Clear(bakCol);
sl@0
  1921
sl@0
  1922
			for (TInt yy2 = rect.iTl.iY; yy2 < rect.iBr.iY; yy2++)
sl@0
  1923
				{
sl@0
  1924
				iDrawDevice->WriteRgbAlphaMulti(rect.iTl.iX,yy2,rect.Width(),KRgbBlack,maskBuffer);
sl@0
  1925
				iIteration++;
sl@0
  1926
				}
sl@0
  1927
sl@0
  1928
			CheckRgb(rect,KRgbBlack,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1929
			CheckBackground(rect,bakCol);
sl@0
  1930
			}
sl@0
  1931
		}
sl@0
  1932
	Report();
sl@0
  1933
sl@0
  1934
	Mem::FillZ(maskBuffer,iSize.iWidth);
sl@0
  1935
sl@0
  1936
	for (nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  1937
		{
sl@0
  1938
		for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
  1939
			{
sl@0
  1940
			if ((nBackColor>=KMaxNon16BackColours) && (iDispMode!= EColor16MAP))
sl@0
  1941
				continue;
sl@0
  1942
sl@0
  1943
			TRgb bakCol = TestBackground[nBackColor];
sl@0
  1944
			Clear(bakCol);
sl@0
  1945
			TRect rect = TestRect[nRect];
sl@0
  1946
sl@0
  1947
			for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1948
				{
sl@0
  1949
				iDrawDevice->WriteRgbAlphaLine(rect.iTl.iX,yy,rect.Width(),writeBuffer,maskBuffer,CGraphicsContext::EDrawModePEN);
sl@0
  1950
				iIteration++;
sl@0
  1951
				}
sl@0
  1952
sl@0
  1953
			TRgb checkColor2=bakCol;
sl@0
  1954
			if (iDispMode == EColor16MAP)
sl@0
  1955
				checkColor2.SetInternal (0);
sl@0
  1956
sl@0
  1957
			CheckRgb(rect,checkColor2,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1958
			CheckBackground(rect,bakCol);
sl@0
  1959
sl@0
  1960
			Clear(bakCol);
sl@0
  1961
sl@0
  1962
			for (TInt yy2 = rect.iTl.iY; yy2 < rect.iBr.iY; yy2++)
sl@0
  1963
				{
sl@0
  1964
				iDrawDevice->WriteRgbAlphaMulti(rect.iTl.iX,yy2,rect.Width(),KRgbBlack,maskBuffer);
sl@0
  1965
				iIteration++;
sl@0
  1966
				}
sl@0
  1967
sl@0
  1968
			CheckRgb(rect,checkColor2,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1969
			CheckBackground(rect,bakCol);
sl@0
  1970
sl@0
  1971
			}
sl@0
  1972
		}
sl@0
  1973
	Report();
sl@0
  1974
sl@0
  1975
	Mem::Fill(writeBuffer,iSize.iWidth * 3,0xff);
sl@0
  1976
sl@0
  1977
	for (nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  1978
		{
sl@0
  1979
		for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
  1980
			{
sl@0
  1981
			if ((nBackColor>=KMaxNon16BackColours) && (iDispMode!= EColor16MAP))
sl@0
  1982
				continue;
sl@0
  1983
sl@0
  1984
			TRgb bakCol = TestBackground[nBackColor];
sl@0
  1985
			Clear(bakCol);
sl@0
  1986
			TRect rect = TestRect[nRect];
sl@0
  1987
sl@0
  1988
			for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  1989
				{
sl@0
  1990
				iDrawDevice->WriteRgbAlphaLine(rect.iTl.iX,yy,rect.Width(),writeBuffer,maskBuffer,CGraphicsContext::EDrawModePEN);
sl@0
  1991
				iIteration++;
sl@0
  1992
				}
sl@0
  1993
			TRgb checkColor3=bakCol;
sl@0
  1994
			if (iDispMode == EColor16MAP)
sl@0
  1995
				checkColor3.SetInternal (0xffffff);
sl@0
  1996
sl@0
  1997
			CheckRgb(rect,checkColor3,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  1998
			CheckBackground(rect,bakCol);
sl@0
  1999
sl@0
  2000
			Clear(bakCol);
sl@0
  2001
sl@0
  2002
			for (TInt yy2 = rect.iTl.iY; yy2 < rect.iBr.iY; yy2++)
sl@0
  2003
				{
sl@0
  2004
				iDrawDevice->WriteRgbAlphaMulti(rect.iTl.iX,yy2,rect.Width(),KRgbWhite,maskBuffer);
sl@0
  2005
				iIteration++;
sl@0
  2006
				}
sl@0
  2007
sl@0
  2008
			CheckRgb(rect,checkColor3,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  2009
			CheckBackground(rect,bakCol);
sl@0
  2010
			}
sl@0
  2011
		}
sl@0
  2012
	Report();
sl@0
  2013
sl@0
  2014
	//Extra test for DEF082251
sl@0
  2015
	if (iDispMode==EColor16MU)
sl@0
  2016
		{
sl@0
  2017
		Mem::Fill(maskBuffer,iSize.iWidth,0x7f);
sl@0
  2018
sl@0
  2019
		for (nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  2020
			{
sl@0
  2021
			for (TInt nBackColor = 0; nBackColor < KNumTestBackgrounds; nBackColor++)
sl@0
  2022
				{
sl@0
  2023
				TRgb bakCol = TestBackground[nBackColor];
sl@0
  2024
				Clear(bakCol);
sl@0
  2025
				TRect rect=TestRect[nRect];
sl@0
  2026
sl@0
  2027
				const TInt red = 50;
sl@0
  2028
				const TInt green = 60;
sl@0
  2029
				const TInt blue = 70;
sl@0
  2030
				const TInt alpha = 80;
sl@0
  2031
sl@0
  2032
				for (TInt yy2 = rect.iTl.iY; yy2 < rect.iBr.iY; yy2++)
sl@0
  2033
					{
sl@0
  2034
					iDrawDevice->WriteRgbAlphaMulti(rect.iTl.iX,yy2,rect.Width(),
sl@0
  2035
					TRgb(red,green,blue,alpha),maskBuffer);
sl@0
  2036
					iIteration++;
sl@0
  2037
					}
sl@0
  2038
sl@0
  2039
				//work out the color - based on OptimizedBlend32 in the
sl@0
  2040
				//screendriver bmdraw32.cpp
sl@0
  2041
				TInt combinedAlpha = (alpha * 0x7f)>>8;
sl@0
  2042
sl@0
  2043
				const TUint32 alphaValue = (combinedAlpha << 8) + combinedAlpha;
sl@0
  2044
 				TUint32 secondary= bakCol.Value();
sl@0
  2045
sl@0
  2046
 				const TInt r2 = secondary & 0x000000ff;
sl@0
  2047
 				const TInt g2 = (secondary & 0x0000ff00) >> 8;
sl@0
  2048
 				const TInt b2 = (secondary & 0x00ff0000) >> 16;
sl@0
  2049
sl@0
  2050
 				const TInt r3 = ((alphaValue * (red   - r2)) >> 16) + r2;
sl@0
  2051
				const TInt g3 = ((alphaValue * (green - g2)) >> 16) + g2;
sl@0
  2052
				const TInt b3 = ((alphaValue * (blue  - b2)) >> 16) + b2;
sl@0
  2053
sl@0
  2054
				TInt result= (b3 & 0xFF) | ((g3<<8) & 0xFF00) | ((r3<<16) & 0xFF0000) | 0xFF000000;
sl@0
  2055
				TRgb resultColor = TRgb(result,0);
sl@0
  2056
sl@0
  2057
				CheckRgb(rect,resultColor,bakCol,CGraphicsContext::EDrawModePEN,0);
sl@0
  2058
				CheckBackground(rect,bakCol);
sl@0
  2059
				}
sl@0
  2060
			}
sl@0
  2061
			Report();
sl@0
  2062
		}
sl@0
  2063
	delete [] writeBuffer;
sl@0
  2064
	delete [] maskBuffer;
sl@0
  2065
	delete [] writeBuffer2;
sl@0
  2066
	}
sl@0
  2067
sl@0
  2068
void CTLowLevel::TestShadow()
sl@0
  2069
	{
sl@0
  2070
	for (TInt shadowMode = 0; shadowMode < KNumShadowModes; shadowMode++)
sl@0
  2071
		{
sl@0
  2072
		for (TInt nRect = 0; nRect < KNumTestRects; nRect++)
sl@0
  2073
			{
sl@0
  2074
			for (TInt nColor = 0; nColor < KNumTestColors; nColor++)
sl@0
  2075
				{
sl@0
  2076
				if ((nColor>=KMaxNon16Colours) && (iDispMode!= EColor16MAP))
sl@0
  2077
					continue;
sl@0
  2078
sl@0
  2079
				TRgb col = TestColor[nColor];
sl@0
  2080
				Clear(col);
sl@0
  2081
sl@0
  2082
				TRect rect = TestRect[nRect];
sl@0
  2083
sl@0
  2084
				iDrawDevice->SetShadowMode(CFbsDrawDevice::TShadowMode(shadowMode));
sl@0
  2085
				iDrawDevice->ShadowArea(rect);
sl@0
  2086
sl@0
  2087
				CheckShadowRgb(rect,col,shadowMode);
sl@0
  2088
sl@0
  2089
				TRgb checkColor=col;
sl@0
  2090
				if (iDispMode == EColor16MAP)
sl@0
  2091
					{
sl@0
  2092
					checkColor.SetInternal (0); //only want contribution from one colour
sl@0
  2093
					}
sl@0
  2094
sl@0
  2095
				TRect outside(0,0,iSize.iWidth,rect.iTl.iY);
sl@0
  2096
				if (!outside.IsEmpty())
sl@0
  2097
					CheckRgb(outside,checkColor,col,CGraphicsContext::EDrawModePEN,0);
sl@0
  2098
				outside.SetRect(0,rect.iBr.iY,iSize.iWidth,iSize.iHeight);
sl@0
  2099
				if (!outside.IsEmpty())
sl@0
  2100
					CheckRgb(outside,checkColor,col,CGraphicsContext::EDrawModePEN,0);
sl@0
  2101
				outside.SetRect(0,rect.iTl.iY,rect.iTl.iX,rect.iBr.iY);
sl@0
  2102
				if (!outside.IsEmpty())
sl@0
  2103
					CheckRgb(outside,checkColor,col,CGraphicsContext::EDrawModePEN,0);
sl@0
  2104
				outside.SetRect(rect.iBr.iX,rect.iTl.iY,iSize.iWidth,rect.iBr.iY);
sl@0
  2105
				if (!outside.IsEmpty())
sl@0
  2106
					CheckRgb(outside,checkColor,col,CGraphicsContext::EDrawModePEN,0);
sl@0
  2107
				iIteration++;
sl@0
  2108
				}
sl@0
  2109
			}
sl@0
  2110
		Report();
sl@0
  2111
		}
sl@0
  2112
	}
sl@0
  2113
sl@0
  2114
/**
sl@0
  2115
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0002
sl@0
  2116
sl@0
  2117
	@SYMPREQ PREQ1543
sl@0
  2118
sl@0
  2119
	@SYMTestCaseDesc This test code tests WriteRgbOutlineAndShadow() which blends the four colours.
sl@0
  2120
	Colours used for blending are outline, shadow, foreground and background.
sl@0
  2121
sl@0
  2122
	@SYMTestPriority High
sl@0
  2123
sl@0
  2124
	@SYMTestStatus Implemented
sl@0
  2125
sl@0
  2126
	@SYMTestActions It compares the colour written by WriteRgbOutlineAndShadow() with colour
sl@0
  2127
	calculated using lookup table provided by Monotype.
sl@0
  2128
	API Calls:
sl@0
  2129
	CDrawBitmap::GetInterface()
sl@0
  2130
	MOutlineAndShadowBlend::WriteRgbOutlineAndShadow()
sl@0
  2131
	CDrawBitmap::ReadLine()
sl@0
  2132
sl@0
  2133
	@SYMTestExpectedResults Test should pass and colour written by WriteRgbOutlineAndShadow should
sl@0
  2134
	match with the colour calculated through lookup table.
sl@0
  2135
*/
sl@0
  2136
void CTLowLevel::TestWriteRgbOutlineAndShadow()
sl@0
  2137
	{
sl@0
  2138
	MOutlineAndShadowBlend* outlineAndShadow = NULL;
sl@0
  2139
	TInt byteSize = ByteSize();
sl@0
  2140
	TUint8* writeBuffer = new TUint8[iSize.iWidth * sizeof(TRgb)];
sl@0
  2141
	TUint8* readBuffer = new TUint8[iSize.iWidth * sizeof(TRgb)];
sl@0
  2142
	TColorConvertor& colorConvertor = ColorConvertor(iDispMode);
sl@0
  2143
	Check(writeBuffer != NULL);
sl@0
  2144
	Check(readBuffer != NULL);
sl@0
  2145
	TInt err = iDrawDevice->GetInterface(KOutlineAndShadowInterfaceID, reinterpret_cast <TAny*&> (outlineAndShadow));
sl@0
  2146
	Check(err == KErrNone);
sl@0
  2147
sl@0
  2148
	TRect rect = TestRect[0];
sl@0
  2149
	for (TInt nBlendingColors = 0; nBlendingColors < KNumBlendingColors; nBlendingColors++)
sl@0
  2150
		{
sl@0
  2151
		// Select different combinations of colours for testing from the array
sl@0
  2152
		TRgb outlinePenColor = TestOSFBColorsForBlending[nBlendingColors][0];
sl@0
  2153
		TRgb shadowColor = TestOSFBColorsForBlending[nBlendingColors][1];
sl@0
  2154
		TRgb fillColor = TestOSFBColorsForBlending[nBlendingColors][2];
sl@0
  2155
		TRgb backgroundColor = colorConvertor.Color(colorConvertor.Index(TestOSFBColorsForBlending[nBlendingColors][3]));
sl@0
  2156
		Clear(backgroundColor);
sl@0
  2157
		for (TInt yy = rect.iTl.iY; yy < rect.iBr.iY; yy++)
sl@0
  2158
			{
sl@0
  2159
			// Run the test for values from 0 to 255 so that it will cover all the entries
sl@0
  2160
			// of lookup table provided by Monotype
sl@0
  2161
			for (TInt index = 0; index < 256; index++)
sl@0
  2162
				{
sl@0
  2163
				// In case alpha is supported and if alpha value is less than 255 then the colour drawn will be different
sl@0
  2164
				// than the colour specified as it blends with the existing background pixel colour.
sl@0
  2165
				TRgb backgroundColorDrawn= iDrawDevice->ReadPixel(rect.iTl.iX, yy);
sl@0
  2166
sl@0
  2167
				// Fill zeroes in the readBuffer so that we can make sure that there is no garbage value.
sl@0
  2168
				Mem::FillZ(readBuffer, iSize.iWidth * 3);
sl@0
  2169
sl@0
  2170
				// We are writing index in writeBuffer to simulate the buffer provided by rasterizer
sl@0
  2171
				// This index should be a value between 0-255, It would be corresponding the entries of lookup table
sl@0
  2172
				Mem::Fill(writeBuffer, iSize.iWidth * 3, index);
sl@0
  2173
sl@0
  2174
				// Below function blends outline, shadow, foreground and background colours, and writes aLength pixels with new colour
sl@0
  2175
				// starting from aX, aY.
sl@0
  2176
				err = outlineAndShadow->WriteRgbOutlineAndShadow(rect.iTl.iX, yy , rect.Width(), outlinePenColor.Internal(),
sl@0
  2177
																					shadowColor.Internal(),fillColor.Internal(),writeBuffer);
sl@0
  2178
				Check(err == KErrNone);
sl@0
  2179
sl@0
  2180
				// Read the whole line which has been written by WriteRgbOutlineAndShadow()
sl@0
  2181
				iDrawDevice->ReadLine(rect.iTl.iX, yy, rect.Width(), (TUint32*)readBuffer, iDispMode);
sl@0
  2182
sl@0
  2183
				// Check colour of each pixel, it should be same as the colour which is calulated manually in CheckBlendedOutlineAndShadow()
sl@0
  2184
				TBool result = CheckBlendedOutlineAndShadow(outlinePenColor, shadowColor, fillColor, backgroundColorDrawn, index, rect.Width(), readBuffer);
sl@0
  2185
				Check(result);
sl@0
  2186
				if (!result)
sl@0
  2187
					{
sl@0
  2188
					Report();
sl@0
  2189
					delete [] writeBuffer;
sl@0
  2190
					delete [] readBuffer;
sl@0
  2191
					return;
sl@0
  2192
					}
sl@0
  2193
sl@0
  2194
				iIteration++;
sl@0
  2195
				}
sl@0
  2196
			}
sl@0
  2197
		Report();
sl@0
  2198
		}
sl@0
  2199
	delete [] writeBuffer;
sl@0
  2200
	delete [] readBuffer;
sl@0
  2201
	}
sl@0
  2202
sl@0
  2203
inline TInt CTLowLevel::ByteSize()
sl@0
  2204
	{
sl@0
  2205
	return ::ByteSize(iDispMode,iSize.iWidth);
sl@0
  2206
	}
sl@0
  2207
sl@0
  2208
TInt CTLowLevel::LongWidth(TInt aWidth,TDisplayMode aDispMode)
sl@0
  2209
	{
sl@0
  2210
	switch (aDispMode)
sl@0
  2211
		{
sl@0
  2212
	case EGray2:
sl@0
  2213
		return (aWidth + 31) & ~31;
sl@0
  2214
	case EGray4:
sl@0
  2215
		return (aWidth + 15) & ~15;
sl@0
  2216
	case EGray16:
sl@0
  2217
	case EColor16:
sl@0
  2218
		return (aWidth + 7) & ~7;
sl@0
  2219
	case EGray256:
sl@0
  2220
	case EColor256:
sl@0
  2221
		return (aWidth + 3) & ~3;
sl@0
  2222
	case EColor4K:
sl@0
  2223
	case EColor64K:
sl@0
  2224
		return (aWidth + 1) & ~1;
sl@0
  2225
	case EColor16M:
sl@0
  2226
		return (((aWidth * 3) + 11) / 12) * 4;
sl@0
  2227
	case EColor16MU:
sl@0
  2228
	case EColor16MA:
sl@0
  2229
	case EColor16MAP:
sl@0
  2230
		return aWidth;
sl@0
  2231
	default:
sl@0
  2232
		break;
sl@0
  2233
		};
sl@0
  2234
	return 0;
sl@0
  2235
	}
sl@0
  2236
sl@0
  2237
void CTLowLevel::Clear(TRgb aColor)
sl@0
  2238
	{
sl@0
  2239
	iDrawDevice->SetShadowMode(CFbsDrawDevice::ENoShadow);
sl@0
  2240
	iDrawDevice->WriteRgbMulti(0,0,iSize.iWidth,iSize.iHeight,aColor,CGraphicsContext::EDrawModeWriteAlpha);
sl@0
  2241
	}
sl@0
  2242
sl@0
  2243
/*
sl@0
  2244
Fill aBuffer with aByteSize random bytes in such a way that the result is a
sl@0
  2245
valid scan line buffer for a driver of which the display mode is aDispMode.
sl@0
  2246
If aDispMode is EColor16MU, the alpha bytes will be 0xFF if aNoAlpha16MU is ETrue,
sl@0
  2247
or random bytes if aNoAlpha16MU is EFalse.
sl@0
  2248
*/
sl@0
  2249
void CTLowLevel::FillBuffer(TUint8* aBuffer, TInt aByteSize, TDisplayMode aDispMode, TBool aNoAlpha16MU)
sl@0
  2250
	{
sl@0
  2251
	TUint8* bufferLimit = aBuffer + aByteSize;
sl@0
  2252
	TUint8* buffer=aBuffer;
sl@0
  2253
sl@0
  2254
	TInt64 seed = TInt64(TInt(aBuffer) * aByteSize * aDispMode * User::TickCount());
sl@0
  2255
sl@0
  2256
	if (aDispMode != EColor16MU || !aNoAlpha16MU)
sl@0
  2257
		{
sl@0
  2258
		while (aBuffer < bufferLimit)
sl@0
  2259
			{
sl@0
  2260
			*aBuffer++ = (TUint8)Math::Rand(seed);
sl@0
  2261
			}
sl@0
  2262
		}
sl@0
  2263
	else
sl@0
  2264
		{
sl@0
  2265
		while (aBuffer < bufferLimit)
sl@0
  2266
			{
sl@0
  2267
			if (TInt(aBuffer) & 3 == 3)
sl@0
  2268
				*aBuffer++ = 0xFF;
sl@0
  2269
			else
sl@0
  2270
				*aBuffer++ = (TUint8)Math::Rand(seed);
sl@0
  2271
			}
sl@0
  2272
		}
sl@0
  2273
	if (aDispMode == EColor16MU && !aNoAlpha16MU || aDispMode == EColor16MAP)
sl@0
  2274
		{
sl@0
  2275
		//need to do the premultiply alpha to ensure that all the colours are valid
sl@0
  2276
		//in the colour space
sl@0
  2277
		for (;buffer < (bufferLimit-3);buffer+=4)
sl@0
  2278
			{
sl@0
  2279
			TUint alpha=*(buffer+3);
sl@0
  2280
			*(buffer)=((*(buffer))* alpha)/255; //do a pre multiply alpha operation
sl@0
  2281
			*(buffer+1)=((*(buffer+1))* alpha)/255;
sl@0
  2282
			*(buffer+2)=((*(buffer+2))* alpha)/255;
sl@0
  2283
			}
sl@0
  2284
		}
sl@0
  2285
sl@0
  2286
	}
sl@0
  2287
sl@0
  2288
void CTLowLevel::CheckBuffer(TUint8* aWriteBuffer,TDisplayMode aWriteDispMode,TUint8* aReadBuffer,TDisplayMode aReadDispMode,TInt aPixelLength)
sl@0
  2289
	{
sl@0
  2290
	switch (aWriteDispMode)
sl@0
  2291
		{
sl@0
  2292
	case EGray2:
sl@0
  2293
		CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2294
		break;
sl@0
  2295
	case EGray4:
sl@0
  2296
		if (aReadDispMode == EGray2)
sl@0
  2297
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2298
		else
sl@0
  2299
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2300
		break;
sl@0
  2301
	case EGray16:
sl@0
  2302
		if (aReadDispMode == EGray2)
sl@0
  2303
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2304
		else if (aReadDispMode == EGray4)
sl@0
  2305
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2306
		else if (aReadDispMode == EColor16)
sl@0
  2307
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor16);
sl@0
  2308
		else
sl@0
  2309
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray16);
sl@0
  2310
		break;
sl@0
  2311
	case EGray256:
sl@0
  2312
		switch (aReadDispMode)
sl@0
  2313
			{
sl@0
  2314
		case EGray2:
sl@0
  2315
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2316
			break;
sl@0
  2317
		case EGray4:
sl@0
  2318
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2319
			break;
sl@0
  2320
		case EGray16:
sl@0
  2321
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray16);
sl@0
  2322
			break;
sl@0
  2323
		case EGray256:
sl@0
  2324
		case EColor16M:
sl@0
  2325
		case ERgb:
sl@0
  2326
		case EColor16MU:
sl@0
  2327
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray256);
sl@0
  2328
			break;
sl@0
  2329
		case EColor16:
sl@0
  2330
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor16);
sl@0
  2331
			break;
sl@0
  2332
		case EColor256:
sl@0
  2333
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor256);
sl@0
  2334
			break;
sl@0
  2335
		case EColor4K:
sl@0
  2336
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor4K);
sl@0
  2337
			break;
sl@0
  2338
		case EColor64K:
sl@0
  2339
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor64K);
sl@0
  2340
			break;
sl@0
  2341
		default:
sl@0
  2342
			break;
sl@0
  2343
			}
sl@0
  2344
		break;
sl@0
  2345
	case EColor16:
sl@0
  2346
		switch (aReadDispMode)
sl@0
  2347
			{
sl@0
  2348
		case EGray2:
sl@0
  2349
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2350
			break;
sl@0
  2351
		case EGray4:
sl@0
  2352
		case EGray16:
sl@0
  2353
		case EGray256:
sl@0
  2354
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2355
			break;
sl@0
  2356
		case EColor16:
sl@0
  2357
		case EColor256:
sl@0
  2358
		case EColor4K:
sl@0
  2359
		case EColor64K:
sl@0
  2360
		case EColor16M:
sl@0
  2361
		case ERgb:
sl@0
  2362
		case EColor16MU:
sl@0
  2363
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor16);
sl@0
  2364
			break;
sl@0
  2365
		default:
sl@0
  2366
			break;
sl@0
  2367
			}
sl@0
  2368
		break;
sl@0
  2369
	case EColor256:
sl@0
  2370
		switch (aReadDispMode)
sl@0
  2371
			{
sl@0
  2372
		case EGray2:
sl@0
  2373
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2374
			break;
sl@0
  2375
		case EGray4:
sl@0
  2376
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2377
			break;
sl@0
  2378
		case EGray16:
sl@0
  2379
		case EGray256:
sl@0
  2380
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray16);
sl@0
  2381
			break;
sl@0
  2382
		case EColor16:
sl@0
  2383
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor16);
sl@0
  2384
			break;
sl@0
  2385
		case EColor256:
sl@0
  2386
		case EColor4K:
sl@0
  2387
		case EColor64K:
sl@0
  2388
		case EColor16M:
sl@0
  2389
		case ERgb:
sl@0
  2390
		case EColor16MU:
sl@0
  2391
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor256);
sl@0
  2392
			break;
sl@0
  2393
		default:
sl@0
  2394
			break;
sl@0
  2395
			}
sl@0
  2396
		break;
sl@0
  2397
	case EColor4K:
sl@0
  2398
		switch (aReadDispMode)
sl@0
  2399
			{
sl@0
  2400
		case EGray2:
sl@0
  2401
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2402
			break;
sl@0
  2403
		case EGray4:
sl@0
  2404
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2405
			break;
sl@0
  2406
		case EGray16:
sl@0
  2407
		case EGray256:
sl@0
  2408
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray16);
sl@0
  2409
			break;
sl@0
  2410
		case EColor16:
sl@0
  2411
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor16);
sl@0
  2412
			break;
sl@0
  2413
		case EColor256:
sl@0
  2414
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor256);
sl@0
  2415
			break;
sl@0
  2416
		case EColor4K:
sl@0
  2417
		case EColor64K:
sl@0
  2418
		case EColor16M:
sl@0
  2419
		case ERgb:
sl@0
  2420
		case EColor16MU:
sl@0
  2421
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor4K);
sl@0
  2422
			break;
sl@0
  2423
		default:
sl@0
  2424
			break;
sl@0
  2425
			}
sl@0
  2426
		break;
sl@0
  2427
	case EColor64K:
sl@0
  2428
		switch (aReadDispMode)
sl@0
  2429
			{
sl@0
  2430
		case EGray2:
sl@0
  2431
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray2);
sl@0
  2432
			break;
sl@0
  2433
		case EGray4:
sl@0
  2434
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray4);
sl@0
  2435
			break;
sl@0
  2436
		case EGray16:
sl@0
  2437
		case EGray256:
sl@0
  2438
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EGray16);
sl@0
  2439
			break;
sl@0
  2440
		case EColor16:
sl@0
  2441
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor16);
sl@0
  2442
			break;
sl@0
  2443
		case EColor256:
sl@0
  2444
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor256);
sl@0
  2445
			break;
sl@0
  2446
		case EColor4K:
sl@0
  2447
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor4K);
sl@0
  2448
			break;
sl@0
  2449
		case EColor64K:
sl@0
  2450
		case EColor16M:
sl@0
  2451
		case ERgb:
sl@0
  2452
		case EColor16MU:
sl@0
  2453
			CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,EColor64K);
sl@0
  2454
			break;
sl@0
  2455
		default:
sl@0
  2456
			break;
sl@0
  2457
			}
sl@0
  2458
		break;
sl@0
  2459
	case EColor16M:
sl@0
  2460
	case EColor16MU:
sl@0
  2461
	case EColor16MA:
sl@0
  2462
	case EColor16MAP:
sl@0
  2463
		CheckPixel(aWriteBuffer,aWriteDispMode,aReadBuffer,aReadDispMode,aPixelLength,aReadDispMode);
sl@0
  2464
		break;
sl@0
  2465
	default:
sl@0
  2466
		break;
sl@0
  2467
		};
sl@0
  2468
	}
sl@0
  2469
sl@0
  2470
void CTLowLevel::CheckPixel(TUint8* aWriteBuffer,TDisplayMode aWriteDispMode,TUint8* aReadBuffer,TDisplayMode aReadDispMode,TInt aPixelLength,TDisplayMode aCompareDispMode)
sl@0
  2471
	{
sl@0
  2472
	TColorConvertor& colorConvertor = ColorConvertor(aCompareDispMode);
sl@0
  2473
sl@0
  2474
	for (TInt count = 0; count < aPixelLength; count++)
sl@0
  2475
		{
sl@0
  2476
		TRgb writeValue = ExtractRgbValue(count,aWriteBuffer,aWriteDispMode);
sl@0
  2477
		TRgb readValue = ExtractRgbValue(count,aReadBuffer,aReadDispMode);
sl@0
  2478
		CheckMatch(colorConvertor.Index(writeValue),colorConvertor.Index(readValue));
sl@0
  2479
		}
sl@0
  2480
	}
sl@0
  2481
sl@0
  2482
void CTLowLevel::CheckRgb(const TPoint& aPoint,TRgb aColor,TRgb aBackgroundColor,CGraphicsContext::TDrawMode aDrawMode,TInt aShadowMode)
sl@0
  2483
	{
sl@0
  2484
	TRect rect(aPoint,TSize(1,1));
sl@0
  2485
	iDrawDevice->CFbsDrawDevice::SetDitherOrigin(aPoint);
sl@0
  2486
	CheckRgb(rect,aColor,aBackgroundColor,aDrawMode,aShadowMode);
sl@0
  2487
	}
sl@0
  2488
sl@0
  2489
void CTLowLevel::CheckRgb(const TRect& aRect,TRgb aColor,TRgb aBackgroundColor,CGraphicsContext::TDrawMode aDrawMode,TInt aShadowMode)
sl@0
  2490
	{
sl@0
  2491
	Shadow(aColor,aShadowMode);
sl@0
  2492
sl@0
  2493
	if (aDrawMode == CGraphicsContext::EDrawModeNOTPEN)
sl@0
  2494
		aColor = ~aColor;
sl@0
  2495
sl@0
  2496
	TRgb foreColor[4];
sl@0
  2497
	Normalize(aColor,foreColor);
sl@0
  2498
sl@0
  2499
	TRgb backColor[4];
sl@0
  2500
	Normalize(aBackgroundColor,backColor);
sl@0
  2501
sl@0
  2502
	TRgb fore11 = foreColor[0];
sl@0
  2503
	TRgb fore21 = foreColor[1];
sl@0
  2504
	TRgb back11 = backColor[0];
sl@0
  2505
	TRgb back21 = backColor[1];
sl@0
  2506
	TRgb fore12 = foreColor[2];
sl@0
  2507
	TRgb fore22 = foreColor[3];
sl@0
  2508
	TRgb back12 = backColor[2];
sl@0
  2509
	TRgb back22 = backColor[3];
sl@0
  2510
sl@0
  2511
	TInt startY = aRect.iTl.iY;
sl@0
  2512
	TInt endY = aRect.iBr.iY - 1;
sl@0
  2513
sl@0
  2514
	if (startY & 1)
sl@0
  2515
		{
sl@0
  2516
		CheckScanline(aRect.iTl.iX,startY,aRect.Width(),fore12,fore22,back12,back22,aDrawMode);
sl@0
  2517
		startY++;
sl@0
  2518
		}
sl@0
  2519
sl@0
  2520
	for (TInt yy = startY; yy < endY; yy += 2)
sl@0
  2521
		{
sl@0
  2522
		CheckScanline(aRect.iTl.iX,yy,aRect.Width(),fore11,fore21,back11,back21,aDrawMode);
sl@0
  2523
		CheckScanline(aRect.iTl.iX,yy + 1,aRect.Width(),fore12,fore22,back12,back22,aDrawMode);
sl@0
  2524
		}
sl@0
  2525
sl@0
  2526
	if (aRect.iBr.iY & 1)
sl@0
  2527
		{
sl@0
  2528
		CheckScanline(aRect.iTl.iX,endY,aRect.Width(),fore11,fore21,back11,back21,aDrawMode);
sl@0
  2529
		}
sl@0
  2530
	}
sl@0
  2531
sl@0
  2532
void CTLowLevel::CheckShadowRgb(const TRect& aRect,TRgb aColor,TInt aShadowMode)
sl@0
  2533
	{
sl@0
  2534
	TRgb foreColor[4];
sl@0
  2535
	Normalize(aColor,foreColor);
sl@0
  2536
sl@0
  2537
	TRgb fore11 = foreColor[0];
sl@0
  2538
	TRgb fore21 = foreColor[1];
sl@0
  2539
	TRgb fore12 = foreColor[2];
sl@0
  2540
	TRgb fore22 = foreColor[3];
sl@0
  2541
sl@0
  2542
	Shadow(fore11,aShadowMode & 2);
sl@0
  2543
	Shadow(fore21,aShadowMode & 2);
sl@0
  2544
	Shadow(fore12,aShadowMode & 2);
sl@0
  2545
	Shadow(fore22,aShadowMode & 2);
sl@0
  2546
sl@0
  2547
	Normalize(fore11);
sl@0
  2548
	Normalize(fore21);
sl@0
  2549
	Normalize(fore12);
sl@0
  2550
	Normalize(fore22);
sl@0
  2551
sl@0
  2552
	Shadow(fore11,aShadowMode & 1);
sl@0
  2553
	Shadow(fore21,aShadowMode & 1);
sl@0
  2554
	Shadow(fore12,aShadowMode & 1);
sl@0
  2555
	Shadow(fore22,aShadowMode & 1);
sl@0
  2556
sl@0
  2557
	Normalize(fore11);
sl@0
  2558
	Normalize(fore21);
sl@0
  2559
	Normalize(fore12);
sl@0
  2560
	Normalize(fore22);
sl@0
  2561
sl@0
  2562
	TInt startY = aRect.iTl.iY;
sl@0
  2563
	TInt endY = aRect.iBr.iY - 1;
sl@0
  2564
sl@0
  2565
	iDrawDevice->CFbsDrawDevice::ShadowArea(aRect);
sl@0
  2566
sl@0
  2567
	if (iDispMode== EColor16MAP)
sl@0
  2568
		{
sl@0
  2569
		//No dithering, no blending, just checking for a solid colour
sl@0
  2570
		fore12.SetAlpha(0);//do not want any blending to take place
sl@0
  2571
		fore22.SetAlpha(0);//do not want any blending to take place
sl@0
  2572
		for (TInt yy = startY; yy < endY; yy ++)
sl@0
  2573
			{
sl@0
  2574
			CheckScanline(aRect.iTl.iX,yy,aRect.Width(),fore11,fore11,fore22,fore22,CGraphicsContext::EDrawModePEN);
sl@0
  2575
			}
sl@0
  2576
		return;
sl@0
  2577
		}
sl@0
  2578
sl@0
  2579
	if (startY & 1)
sl@0
  2580
		{
sl@0
  2581
		CheckScanline(aRect.iTl.iX,startY,aRect.Width(),fore12,fore22,fore12,fore22,CGraphicsContext::EDrawModePEN);
sl@0
  2582
		startY++;
sl@0
  2583
		}
sl@0
  2584
sl@0
  2585
	for (TInt yy = startY; yy < endY; yy += 2)
sl@0
  2586
		{
sl@0
  2587
		CheckScanline(aRect.iTl.iX,yy,aRect.Width(),fore11,fore21,fore11,fore21,CGraphicsContext::EDrawModePEN);
sl@0
  2588
		CheckScanline(aRect.iTl.iX,yy + 1,aRect.Width(),fore12,fore22,fore12,fore22,CGraphicsContext::EDrawModePEN);
sl@0
  2589
		}
sl@0
  2590
sl@0
  2591
	if (aRect.iBr.iY & 1)
sl@0
  2592
		{
sl@0
  2593
		CheckScanline(aRect.iTl.iX,endY,aRect.Width(),fore11,fore21,fore11,fore21,CGraphicsContext::EDrawModePEN);
sl@0
  2594
		}
sl@0
  2595
	}
sl@0
  2596
sl@0
  2597
void CTLowLevel::CheckScanline(TInt aX,TInt aY,TInt aLength,TRgb aFore1,TRgb aFore2,TRgb aBack1,TRgb aBack2,CGraphicsContext::TDrawMode aDrawMode)
sl@0
  2598
	{
sl@0
  2599
	iDrawDevice->ReadLine(aX,aY,aLength,iDrawDevice->ScanLineBuffer(),iDispMode);
sl@0
  2600
sl@0
  2601
	TUint32 binaryPixel1 = BinaryValue(aFore1,aBack1,aDrawMode);
sl@0
  2602
	TUint32 binaryPixel2 = BinaryValue(aFore2,aBack2,aDrawMode);
sl@0
  2603
	if (aX & 1)
sl@0
  2604
		{
sl@0
  2605
		TUint32 spare = binaryPixel1;
sl@0
  2606
		binaryPixel1 = binaryPixel2;
sl@0
  2607
		binaryPixel2 = spare;
sl@0
  2608
		}
sl@0
  2609
sl@0
  2610
	TInt extra = aLength & 1;
sl@0
  2611
	aLength &= ~1;
sl@0
  2612
	TInt x = 0;
sl@0
  2613
sl@0
  2614
	if (iPostBlendShadow)
sl@0
  2615
		{
sl@0
  2616
		PostBlendShadow(binaryPixel1);
sl@0
  2617
		PostBlendShadow(binaryPixel2);
sl@0
  2618
		}
sl@0
  2619
	if (i16MAUserDispMode)
sl@0
  2620
		{
sl@0
  2621
		binaryPixel1 = PMA2NonPMAPixel(binaryPixel1,PtrTo16BitNormalisationTable());
sl@0
  2622
		binaryPixel2 = PMA2NonPMAPixel(binaryPixel1,PtrTo16BitNormalisationTable());
sl@0
  2623
		}
sl@0
  2624
	while (x < aLength)
sl@0
  2625
		{
sl@0
  2626
		TUint32 binaryValue = ExtractBinaryValue(x,iDrawDevice->ScanLineBuffer(),iDispMode);
sl@0
  2627
		CheckMatch(binaryPixel1,binaryValue);
sl@0
  2628
		x++;
sl@0
  2629
sl@0
  2630
		binaryValue = ExtractBinaryValue(x,iDrawDevice->ScanLineBuffer(),iDispMode);
sl@0
  2631
		CheckMatch(binaryPixel2,binaryValue);
sl@0
  2632
		x++;
sl@0
  2633
		}
sl@0
  2634
	if (extra)
sl@0
  2635
		{
sl@0
  2636
		TUint32 binaryValue = ExtractBinaryValue(x,iDrawDevice->ScanLineBuffer(),iDispMode);
sl@0
  2637
		CheckMatch(binaryPixel1,binaryValue);
sl@0
  2638
		}
sl@0
  2639
	}
sl@0
  2640
sl@0
  2641
void CTLowLevel::CheckLine(TUint8* aWriteBuffer,TUint8* aReadBuffer,TUint8* aBackBuffer,TInt aPixelLength,CGraphicsContext::TDrawMode aDrawMode,TDisplayMode aDispMode)
sl@0
  2642
	{
sl@0
  2643
	TInt wholeBytes = 0;
sl@0
  2644
	TInt extraBits = 0;
sl@0
  2645
sl@0
  2646
	switch (aDispMode)
sl@0
  2647
		{
sl@0
  2648
	case EGray2:
sl@0
  2649
		wholeBytes = aPixelLength / 8;
sl@0
  2650
		extraBits = aPixelLength & 7;
sl@0
  2651
		break;
sl@0
  2652
	case EGray4:
sl@0
  2653
		wholeBytes = aPixelLength / 4;
sl@0
  2654
		extraBits = (aPixelLength & 3) * 2;
sl@0
  2655
		break;
sl@0
  2656
	case EGray16:
sl@0
  2657
	case EColor16:
sl@0
  2658
		wholeBytes = aPixelLength / 2;
sl@0
  2659
		extraBits = (aPixelLength & 1) * 4;
sl@0
  2660
		break;
sl@0
  2661
	case EGray256:
sl@0
  2662
	case EColor256:
sl@0
  2663
		wholeBytes = aPixelLength;
sl@0
  2664
		break;
sl@0
  2665
	case EColor4K:
sl@0
  2666
	case EColor64K:
sl@0
  2667
		wholeBytes = aPixelLength * 2;
sl@0
  2668
		break;
sl@0
  2669
	case EColor16M:
sl@0
  2670
		wholeBytes = aPixelLength * 3;
sl@0
  2671
		break;
sl@0
  2672
	case EColor16MU:
sl@0
  2673
	case EColor16MA:
sl@0
  2674
	case EColor16MAP:
sl@0
  2675
		wholeBytes = aPixelLength * 4;
sl@0
  2676
		break;
sl@0
  2677
	default:
sl@0
  2678
		break;
sl@0
  2679
		};
sl@0
  2680
sl@0
  2681
	TUint8* readLimit = aReadBuffer + wholeBytes;
sl@0
  2682
	TUint8 mask = TUint8(0xff >> (8 - extraBits));
sl@0
  2683
	TInt byteCounter = 0;
sl@0
  2684
sl@0
  2685
	switch (aDrawMode)
sl@0
  2686
		{
sl@0
  2687
	case CGraphicsContext::EDrawModeAND:
sl@0
  2688
		if (iDispMode==EColor16MAP)
sl@0
  2689
			break; //logical opeations not supported for premultiplied alpha
sl@0
  2690
		for (; aReadBuffer < readLimit; aReadBuffer++, aWriteBuffer++, aBackBuffer++)
sl@0
  2691
			{
sl@0
  2692
			if(!((aDispMode == EColor16MU || aDispMode == EColor16MA || aDispMode == EColor16MAP)
sl@0
  2693
				  && ++byteCounter % 4 == 0))
sl@0
  2694
				Check(*aReadBuffer == (*aWriteBuffer & *aBackBuffer));
sl@0
  2695
			}
sl@0
  2696
		if (extraBits > 0)
sl@0
  2697
			Check((*aReadBuffer & mask) == (*aWriteBuffer & *aBackBuffer & mask));
sl@0
  2698
		break;
sl@0
  2699
	case CGraphicsContext::EDrawModePEN:
sl@0
  2700
		if(aDispMode == EColor16MU || aDispMode == EColor16MA || aDispMode == EColor16MAP)
sl@0
  2701
			{
sl@0
  2702
			for (; aReadBuffer<readLimit; aReadBuffer+=4, aWriteBuffer+=4)
sl@0
  2703
				{
sl@0
  2704
				TBool fail=EFalse;
sl@0
  2705
				Blend(aWriteBuffer,aBackBuffer,aDispMode);
sl@0
  2706
				if (!iFuzzyMatch)
sl@0
  2707
					{
sl@0
  2708
					fail|=Check(AbsDiff(*aReadBuffer,*aWriteBuffer)<2);
sl@0
  2709
					fail|=Check(AbsDiff(*(aReadBuffer+1),*(aWriteBuffer+1))<2);
sl@0
  2710
					fail|=Check(AbsDiff(*(aReadBuffer+2),*(aWriteBuffer+2))<2);
sl@0
  2711
					fail|=Check(AbsDiff(*(aReadBuffer+3),*(aWriteBuffer+3))<2);
sl@0
  2712
					}
sl@0
  2713
				else
sl@0
  2714
					{
sl@0
  2715
					fail|=Check(AbsDiff(*aReadBuffer,*aWriteBuffer)<KInaccuracyLimit);
sl@0
  2716
					fail|=Check(AbsDiff(*(aReadBuffer+1),*(aWriteBuffer+1))<KInaccuracyLimit);
sl@0
  2717
					fail|=Check(AbsDiff(*(aReadBuffer+2),*(aWriteBuffer+2))<KInaccuracyLimit);
sl@0
  2718
					fail|=Check(AbsDiff(*(aReadBuffer+3),*(aWriteBuffer+3))<KInaccuracyLimit);
sl@0
  2719
					}
sl@0
  2720
				if (fail)
sl@0
  2721
					{
sl@0
  2722
					_LIT(KLog,"The values 0x%x and 0x%x don't match, fuzzyMatch=%d (limit=%d), memory 0x%x 0x%x");
sl@0
  2723
					INFO_PRINTF7(KLog,*reinterpret_cast<TUint*>(aReadBuffer),*reinterpret_cast<TUint*>(aWriteBuffer),iFuzzyMatch,KInaccuracyLimit,aReadBuffer,aWriteBuffer);
sl@0
  2724
					}
sl@0
  2725
				}
sl@0
  2726
			}
sl@0
  2727
		else
sl@0
  2728
			{
sl@0
  2729
			for (; aReadBuffer < readLimit; aReadBuffer++, aWriteBuffer++)
sl@0
  2730
				{
sl@0
  2731
				if (Check(*aReadBuffer == *aWriteBuffer))
sl@0
  2732
					{
sl@0
  2733
					_LIT(KLog,"The values 0x%x and 0x%x don't match, memory 0x%x 0x%x");
sl@0
  2734
					INFO_PRINTF5(KLog,*aReadBuffer,*aWriteBuffer,aReadBuffer,aWriteBuffer);
sl@0
  2735
					}
sl@0
  2736
				}
sl@0
  2737
			if (extraBits > 0)
sl@0
  2738
				Check((*aReadBuffer & mask) == (*aWriteBuffer & mask));
sl@0
  2739
			}
sl@0
  2740
		break;
sl@0
  2741
	case CGraphicsContext::EDrawModeNOTPEN:
sl@0
  2742
		if (iDispMode==EColor16MAP)
sl@0
  2743
			break; //logical opeations not supported for premultiplied alpha
sl@0
  2744
		if(aDispMode == EColor16MU || aDispMode == EColor16MA )
sl@0
  2745
			{
sl@0
  2746
			for (; aReadBuffer < readLimit; aReadBuffer +=4, aWriteBuffer+=4)
sl@0
  2747
				{
sl@0
  2748
				*aWriteBuffer ^= 0xff;
sl@0
  2749
				*(aWriteBuffer+1) ^= 0xff;
sl@0
  2750
				*(aWriteBuffer+2) ^= 0xff;
sl@0
  2751
sl@0
  2752
				Blend(aWriteBuffer,aBackBuffer,aDispMode);
sl@0
  2753
sl@0
  2754
				if (!iFuzzyMatch)
sl@0
  2755
					{
sl@0
  2756
					Check(AbsDiff(*aReadBuffer, *aWriteBuffer) < 2);
sl@0
  2757
					Check(AbsDiff(*(aReadBuffer+1), *(aWriteBuffer+1)) < 2);
sl@0
  2758
					Check(AbsDiff(*(aReadBuffer+2), *(aWriteBuffer+2)) < 2);
sl@0
  2759
					Check(AbsDiff(*(aReadBuffer+3), *(aWriteBuffer+3)) < 2);
sl@0
  2760
					}
sl@0
  2761
				else
sl@0
  2762
					{
sl@0
  2763
					Check(AbsDiff(*aReadBuffer, *aWriteBuffer) < KInaccuracyLimit);
sl@0
  2764
					Check(AbsDiff(*(aReadBuffer+1), *(aWriteBuffer+1)) < KInaccuracyLimit);
sl@0
  2765
					Check(AbsDiff(*(aReadBuffer+2), *(aWriteBuffer+2)) < KInaccuracyLimit);
sl@0
  2766
					Check(AbsDiff(*(aReadBuffer+3), *(aWriteBuffer+3)) < KInaccuracyLimit);
sl@0
  2767
					}
sl@0
  2768
				}
sl@0
  2769
			}
sl@0
  2770
		else
sl@0
  2771
			{
sl@0
  2772
sl@0
  2773
			for (; aReadBuffer < readLimit; aReadBuffer++, aWriteBuffer++)
sl@0
  2774
				{
sl@0
  2775
				if(!((aDispMode == EColor16MU || aDispMode == EColor16MA || aDispMode == EColor16MAP) && ++byteCounter % 4 == 0))
sl@0
  2776
					Check(*aReadBuffer == (*aWriteBuffer ^ 0xff));
sl@0
  2777
				}
sl@0
  2778
			if (extraBits > 0)
sl@0
  2779
				Check((*aReadBuffer & mask) == ((*aWriteBuffer ^ 0xff) & mask));
sl@0
  2780
			}
sl@0
  2781
		break;
sl@0
  2782
	case CGraphicsContext::EDrawModeXOR:
sl@0
  2783
		if (iDispMode==EColor16MAP)
sl@0
  2784
			break;//logical opeations not supported for premultiplied alpha
sl@0
  2785
		for (; aReadBuffer < readLimit; aReadBuffer++, aWriteBuffer++, aBackBuffer++)
sl@0
  2786
			{
sl@0
  2787
			if(!((aDispMode == EColor16MU || aDispMode == EColor16MA || aDispMode == EColor16MAP) && ++byteCounter % 4 == 0))
sl@0
  2788
				Check(*aReadBuffer == (*aWriteBuffer ^ *aBackBuffer));
sl@0
  2789
			}
sl@0
  2790
		if (extraBits > 0)
sl@0
  2791
			Check((*aReadBuffer & mask) == ((*aWriteBuffer ^ *aBackBuffer) & mask));
sl@0
  2792
		break;
sl@0
  2793
	case CGraphicsContext::EDrawModeOR:
sl@0
  2794
		if (iDispMode==EColor16MAP)
sl@0
  2795
			break;//logical opeations not supported for premultiplied alpha
sl@0
  2796
		for (; aReadBuffer < readLimit; aReadBuffer++, aWriteBuffer++, aBackBuffer++)
sl@0
  2797
			{
sl@0
  2798
			if(!((aDispMode == EColor16MU || aDispMode == EColor16MA || aDispMode == EColor16MAP) && ++byteCounter % 4 == 0))
sl@0
  2799
				Check(*aReadBuffer == (*aWriteBuffer | *aBackBuffer));
sl@0
  2800
			}
sl@0
  2801
		if (extraBits > 0)
sl@0
  2802
			Check((*aReadBuffer & mask) == ((*aWriteBuffer | *aBackBuffer) & mask));
sl@0
  2803
		break;
sl@0
  2804
	case CGraphicsContext::EDrawModeNOTSCREEN:
sl@0
  2805
		if (iDispMode==EColor16MAP)
sl@0
  2806
			break;//logical opeations not supported for premultiplied alpha
sl@0
  2807
		if (aDispMode != EColor4K)
sl@0
  2808
			{
sl@0
  2809
			for (; aReadBuffer < readLimit; aReadBuffer++, aBackBuffer++)
sl@0
  2810
				{
sl@0
  2811
				if(!((aDispMode == EColor16MU || aDispMode == EColor16MA || aDispMode == EColor16MAP) && ++byteCounter % 4 == 0))
sl@0
  2812
					{
sl@0
  2813
					if (iFuzzyMatch==EFalse)
sl@0
  2814
						Check(*aReadBuffer == (*aBackBuffer ^ 0xff));
sl@0
  2815
					else
sl@0
  2816
						{
sl@0
  2817
						TUint8 vals[3];
sl@0
  2818
						vals[0]=*aReadBuffer;
sl@0
  2819
						//put in some tolerance values, try with +/- 1, to begin with
sl@0
  2820
						if (vals[0]<255)
sl@0
  2821
							vals[1]=vals[0]+1;
sl@0
  2822
						else
sl@0
  2823
							vals[1]=vals[0];
sl@0
  2824
						if (vals[0]>0)
sl@0
  2825
							vals[2]=vals[0]-1;
sl@0
  2826
						else
sl@0
  2827
							vals[2]=vals[0];
sl@0
  2828
						Check((vals[0] == (*aBackBuffer ^ 0xff))||
sl@0
  2829
							  (vals[1] == (*aBackBuffer ^ 0xff))||
sl@0
  2830
							  (vals[2] == (*aBackBuffer ^ 0xff)));
sl@0
  2831
						}
sl@0
  2832
					}
sl@0
  2833
				}
sl@0
  2834
			if (extraBits > 0)
sl@0
  2835
				Check((*aReadBuffer & mask) == ((*aBackBuffer ^ 0xff) & mask));
sl@0
  2836
			}
sl@0
  2837
		else
sl@0
  2838
			{
sl@0
  2839
			while (aReadBuffer < readLimit)
sl@0
  2840
				{
sl@0
  2841
				if (TInt(aReadBuffer) & 1)
sl@0
  2842
					Check(*aReadBuffer++ == (*aBackBuffer++ ^ 0x0f));
sl@0
  2843
				else
sl@0
  2844
					Check(*aReadBuffer++ == (*aBackBuffer++ ^ 0xff));
sl@0
  2845
				}
sl@0
  2846
			}
sl@0
  2847
		break;
sl@0
  2848
	default:
sl@0
  2849
		break;
sl@0
  2850
		};
sl@0
  2851
	}
sl@0
  2852
sl@0
  2853
void CTLowLevel::CheckBinary(const TRect& aRect,TUint32* aBuffer,TRgb aForeColor,TRgb aBackColor,CGraphicsContext::TDrawMode aDrawMode,TInt aShadowMode,TBool aWrapDataWords,TBool aUp)
sl@0
  2854
	{
sl@0
  2855
	Shadow(aForeColor,aShadowMode);
sl@0
  2856
sl@0
  2857
	if (aDrawMode == CGraphicsContext::EDrawModeNOTPEN)
sl@0
  2858
		aForeColor = ~aForeColor;
sl@0
  2859
sl@0
  2860
	TRgb foreColor[4];
sl@0
  2861
	Normalize(aForeColor,foreColor);
sl@0
  2862
sl@0
  2863
	TRgb backColor[4];
sl@0
  2864
	Normalize(aBackColor,backColor);
sl@0
  2865
sl@0
  2866
	foreColor[0] = RgbValue(foreColor[0],backColor[0],aDrawMode);
sl@0
  2867
	foreColor[1] = RgbValue(foreColor[1],backColor[1],aDrawMode);
sl@0
  2868
	foreColor[2] = RgbValue(foreColor[2],backColor[2],aDrawMode);
sl@0
  2869
	foreColor[3] = RgbValue(foreColor[3],backColor[3],aDrawMode);
sl@0
  2870
sl@0
  2871
sl@0
  2872
	if (iDispMode==EColor16MAP)
sl@0
  2873
		{
sl@0
  2874
		//pre-multiply and unpremultiply
sl@0
  2875
		TInt count;
sl@0
  2876
		for (count=0;count<4;count++)
sl@0
  2877
			{
sl@0
  2878
			TUint32 tempInt;
sl@0
  2879
			tempInt = backColor[count].Color16MAP(); //Now premultiplied
sl@0
  2880
			backColor[count] = TRgb::Color16MAP(tempInt);
sl@0
  2881
			}
sl@0
  2882
		}
sl@0
  2883
sl@0
  2884
	TUint32 data = *aBuffer++;
sl@0
  2885
	TUint32 mask = 1;
sl@0
  2886
sl@0
  2887
	TInt yy = (aUp) ? aRect.iBr.iY - 1  : aRect.iTl.iY;
sl@0
  2888
	TInt ylimit = (aUp) ? aRect.iTl.iY - 1 : aRect.iBr.iY;
sl@0
  2889
	TInt yinc = (aUp) ? -1 : 1;
sl@0
  2890
sl@0
  2891
	TRgb pixelBuffer[KCheckBinaryPixelBufferSize];
sl@0
  2892
	__ASSERT_ALWAYS(aRect.Width() <= KCheckBinaryPixelBufferSize,User::Panic(_L("CheckBinary buffer"),KErrOverflow));
sl@0
  2893
sl@0
  2894
	for (; yy != ylimit; yy += yinc)
sl@0
  2895
		{
sl@0
  2896
		TInt yoffset = 2 * (yy & 1);
sl@0
  2897
sl@0
  2898
		iDrawDevice->ReadLine(aRect.iTl.iX,yy,aRect.Width(),pixelBuffer,ERgb);
sl@0
  2899
		TRgb* color = pixelBuffer;
sl@0
  2900
sl@0
  2901
		for (TInt xx = aRect.iTl.iX; xx < aRect.iBr.iX; xx++)
sl@0
  2902
			{
sl@0
  2903
			if (!mask)
sl@0
  2904
				{
sl@0
  2905
				mask = 1;
sl@0
  2906
				data = *aBuffer++;
sl@0
  2907
				}
sl@0
  2908
sl@0
  2909
			if (data & mask)
sl@0
  2910
				CheckMatch((*color).Internal(), foreColor[(xx & 1) + yoffset].Internal());
sl@0
  2911
			else
sl@0
  2912
				CheckMatch((*color).Internal(), backColor[(xx & 1) + yoffset].Internal());
sl@0
  2913
sl@0
  2914
			color++;
sl@0
  2915
			mask <<= 1;
sl@0
  2916
			}
sl@0
  2917
sl@0
  2918
		if (aWrapDataWords)
sl@0
  2919
			mask = 0;
sl@0
  2920
		}
sl@0
  2921
	}
sl@0
  2922
sl@0
  2923
void CTLowLevel::CheckBackground(const TRect& aRect,TRgb aBackgroundColor)
sl@0
  2924
	{
sl@0
  2925
	iBlendTestColors= EFalse;
sl@0
  2926
	if (aRect.iTl.iX > 0)
sl@0
  2927
		CheckRgb(TRect(aRect.iTl.iX - 1,aRect.iTl.iY,aRect.iTl.iX,aRect.iBr.iY),aBackgroundColor,aBackgroundColor,CGraphicsContext::EDrawModePEN,0);
sl@0
  2928
	if (aRect.iTl.iY > 0)
sl@0
  2929
		CheckRgb(TRect(aRect.iTl.iX,aRect.iTl.iY - 1,aRect.iBr.iX,aRect.iTl.iY),aBackgroundColor,aBackgroundColor,CGraphicsContext::EDrawModePEN,0);
sl@0
  2930
	if (aRect.iBr.iX < iSize.iWidth - 1)
sl@0
  2931
		CheckRgb(TRect(aRect.iBr.iX,aRect.iTl.iY,aRect.iBr.iX + 1,aRect.iBr.iY),aBackgroundColor,aBackgroundColor,CGraphicsContext::EDrawModePEN,0);
sl@0
  2932
	if (aRect.iBr.iY < iSize.iHeight - 1)
sl@0
  2933
		CheckRgb(TRect(aRect.iTl.iX,aRect.iBr.iY,aRect.iBr.iX,aRect.iBr.iY + 1),aBackgroundColor,aBackgroundColor,CGraphicsContext::EDrawModePEN,0);
sl@0
  2934
	iBlendTestColors= ETrue;
sl@0
  2935
	}
sl@0
  2936
/**
sl@0
  2937
This function is copied as it is from BMDRAW32A.CPP which is used to test WriteRgbOutlineAndShadow for EColor16MA.
sl@0
  2938
It is used in CTLowLevel::CheckBlendedOutlineAndShadow.
sl@0
  2939
@param aBeneath The background pixel colour value
sl@0
  2940
@param aSrcColor The source pixel colour value
sl@0
  2941
@param aAlpha The alpha value
sl@0
  2942
*/
sl@0
  2943
FORCEINLINE TUint32 OptimizedBlend32A(TUint32 aBeneath,TUint32 aSrcColor,TUint8 aAlpha)
sl@0
  2944
 	{
sl@0
  2945
	if(aAlpha)
sl@0
  2946
		{
sl@0
  2947
		if(aAlpha == 0xff) // opaque, so unchanged
sl@0
  2948
			{
sl@0
  2949
			//Still need to convert source to destination from non-multiplied to pre-multiplied
sl@0
  2950
			//But this code resolves to a copy. The ARM optimiser prefers shifts over big constants.
sl@0
  2951
			return (aSrcColor|(aAlpha<<24));
sl@0
  2952
			}
sl@0
  2953
		else
sl@0
  2954
			{
sl@0
  2955
			//0, 1, 2, 3
sl@0
  2956
			//b, g, rect, alpha
sl@0
  2957
sl@0
  2958
			const TUint32 srcMult = aAlpha;
sl@0
  2959
			TUint32 destMult = ((255 - aAlpha) * ((aBeneath >> 24)));
sl@0
  2960
			//This gives a slightly more accurate result than ((aBeneath >> 24)+1)
sl@0
  2961
			destMult=destMult+(destMult>>8);
sl@0
  2962
			destMult+= 0x0080;
sl@0
  2963
			destMult >>= 8;
sl@0
  2964
sl@0
  2965
			TUint32 rb =(((aSrcColor&0x00ff00ff)*srcMult)) + (((aBeneath&0x00ff00ff)*destMult));
sl@0
  2966
			rb = rb+((rb>>8)&0x00ff00ff);
sl@0
  2967
			rb+=0x00800080;
sl@0
  2968
			rb>>=8;
sl@0
  2969
			TUint32 ag = (((aSrcColor&0x0000ff00)*srcMult)) + (((aBeneath&0x0000ff00)*destMult));
sl@0
  2970
			ag>>=8;	 //Note that if alpha is processed here, this shift must be performed before the multiplies
sl@0
  2971
			ag = ag+((ag>>8)&0x00ff00ff);
sl@0
  2972
			ag+=0x00800080;
sl@0
  2973
			TUint32 aa = srcMult+destMult;
sl@0
  2974
			return (rb&0x00ff00ff) | (ag&0x0000ff00) | (aa << 24);
sl@0
  2975
sl@0
  2976
			}
sl@0
  2977
		}
sl@0
  2978
 	else // completely transparent
sl@0
  2979
		{
sl@0
  2980
		return aBeneath;
sl@0
  2981
 		}
sl@0
  2982
sl@0
  2983
 	}
sl@0
  2984
sl@0
  2985
/**
sl@0
  2986
Helper function for TestWriteRgbOutlineAndShadow(). Creates the final colour, blending the outline, shadow,
sl@0
  2987
fill and background colour using lookup table provided by Monotype and compares with the
sl@0
  2988
pixel colour drawn using WriteRgbOutlineAndShadow.
sl@0
  2989
sl@0
  2990
@param aOutlinePenColor Colour used for drawing outline of font
sl@0
  2991
@param aShadowColor Colour used for drawing shadow of font
sl@0
  2992
@param aFillColor Colour used for filling of font
sl@0
  2993
@param aBackgroundColor Background colour of the pixel
sl@0
  2994
@param aLookupIndex Index of the lookup table to be used for generating final colour
sl@0
  2995
@param aLength Number of pixels to compare the pixel colour with the generated colour
sl@0
  2996
@param aReadBuffer Buffer containing the colours drawn using WriteRgbOutlineAndShadow.This will be used for comparing
sl@0
  2997
@return EFalse if pixel colour doesnt match with the calculated colour, otherwise ETrue on success.
sl@0
  2998
*/
sl@0
  2999
TBool CTLowLevel::CheckBlendedOutlineAndShadow(TRgb aOutlinePenColor, TRgb aShadowColor, TRgb aFillColor,
sl@0
  3000
												TRgb aBackgroundColor, TInt aLookupIndex, TInt aLength, TUint8* aReadBuffer)
sl@0
  3001
	{
sl@0
  3002
	TRgb finalColor;
sl@0
  3003
	TInt alpha = aOutlinePenColor.Internal() >> 24;
sl@0
  3004
sl@0
  3005
	if (255 == FourColorBlendLookup[aLookupIndex][3])
sl@0
  3006
		{
sl@0
  3007
		//background colour
sl@0
  3008
		finalColor.SetInternal(aBackgroundColor.Internal());
sl@0
  3009
sl@0
  3010
		/*Reset the alpha with background colour alpha as in product code in case of 255 == FourColorBlendLookup[aLookupIndex][3]
sl@0
  3011
		it doesnt draw and leaves the background colour as it is. So the alpha to be checked should be of background colour alpha*/
sl@0
  3012
		alpha = aBackgroundColor.Alpha();
sl@0
  3013
		}
sl@0
  3014
	else if (255 == FourColorBlendLookup[aLookupIndex][2])
sl@0
  3015
		{
sl@0
  3016
		//fill colour
sl@0
  3017
		finalColor.SetInternal(aFillColor.Internal());
sl@0
  3018
		}
sl@0
  3019
	else if (255 == FourColorBlendLookup[aLookupIndex][1])
sl@0
  3020
		{
sl@0
  3021
		//Shadow colour
sl@0
  3022
		finalColor.SetInternal(aShadowColor.Internal());
sl@0
  3023
		}
sl@0
  3024
	else if (255 == FourColorBlendLookup[aLookupIndex][0])
sl@0
  3025
		{
sl@0
  3026
		//Outline colour
sl@0
  3027
		finalColor.SetInternal(aOutlinePenColor.Internal());
sl@0
  3028
		}
sl@0
  3029
	else
sl@0
  3030
		{
sl@0
  3031
		TInt blendedRedColor = (aOutlinePenColor.Red() * FourColorBlendLookup[aLookupIndex][0] +
sl@0
  3032
				  				aShadowColor.Red() * FourColorBlendLookup[aLookupIndex][1] +
sl@0
  3033
				  				aFillColor.Red() * FourColorBlendLookup[aLookupIndex][2] +
sl@0
  3034
				  				aBackgroundColor.Red() * FourColorBlendLookup[aLookupIndex][3]) >> 8;
sl@0
  3035
sl@0
  3036
		TInt blendedGreenColor = (aOutlinePenColor.Green() * FourColorBlendLookup[aLookupIndex][0] +
sl@0
  3037
							 	aShadowColor.Green() * FourColorBlendLookup[aLookupIndex][1] +
sl@0
  3038
							 	aFillColor.Green() * FourColorBlendLookup[aLookupIndex][2] +
sl@0
  3039
							 	aBackgroundColor.Green() * FourColorBlendLookup[aLookupIndex][3]) >> 8;
sl@0
  3040
sl@0
  3041
		TInt blendedBlueColor = (aOutlinePenColor.Blue() * FourColorBlendLookup[aLookupIndex][0] +
sl@0
  3042
								aShadowColor.Blue() * FourColorBlendLookup[aLookupIndex][1] +
sl@0
  3043
								aFillColor.Blue() * FourColorBlendLookup[aLookupIndex][2] +
sl@0
  3044
								aBackgroundColor.Blue() * FourColorBlendLookup[aLookupIndex][3]) >> 8;
sl@0
  3045
sl@0
  3046
		finalColor = TRgb(blendedRedColor, blendedGreenColor, blendedBlueColor);
sl@0
  3047
		}
sl@0
  3048
sl@0
  3049
	//Set the alpha in the final colour
sl@0
  3050
	finalColor.SetAlpha(alpha);
sl@0
  3051
sl@0
  3052
	//Alpha blending is not supported for display modes below EColor64K.
sl@0
  3053
	switch(iDispMode)
sl@0
  3054
		{
sl@0
  3055
	case EColor64K:
sl@0
  3056
	case EColor16M:
sl@0
  3057
	case EColor16MU:
sl@0
  3058
		if (alpha != 0xff)
sl@0
  3059
			{
sl@0
  3060
			finalColor = AlphaBlend(finalColor.Red(), finalColor.Green(), finalColor.Blue(), aBackgroundColor.Red(), aBackgroundColor.Green(), aBackgroundColor.Blue(), alpha);
sl@0
  3061
			}
sl@0
  3062
		break;
sl@0
  3063
	case EColor16MA:
sl@0
  3064
		//Just use the background color to draw in case 255 == FourColorBlendLookup[aLookupIndex][3]
sl@0
  3065
		if (255 != FourColorBlendLookup[aLookupIndex][3])
sl@0
  3066
			{
sl@0
  3067
			finalColor.SetInternal(OptimizedBlend32A(aBackgroundColor.Internal(), finalColor.Internal(), alpha));
sl@0
  3068
			}
sl@0
  3069
		break;
sl@0
  3070
	case EColor16MAP:
sl@0
  3071
		//Just use the background color to draw in case 255 == FourColorBlendLookup[aLookupIndex][3]
sl@0
  3072
		if (255 != FourColorBlendLookup[aLookupIndex][3])
sl@0
  3073
			{
sl@0
  3074
			TUint32 color16MAP = finalColor.Internal();
sl@0
  3075
			Convert2PMA(color16MAP);
sl@0
  3076
			finalColor.SetInternal(PMAPixelBlend(aBackgroundColor.Internal(), color16MAP));
sl@0
  3077
			}
sl@0
  3078
		break;
sl@0
  3079
		};
sl@0
  3080
sl@0
  3081
	Normalize(finalColor);
sl@0
  3082
	TColorConvertor& colorConvertor = ColorConvertor(iDispMode);
sl@0
  3083
	// Check each pixel of the line, it should match with the calculated blended color.
sl@0
  3084
	for (TInt count = 0; count < aLength; count++)
sl@0
  3085
		{
sl@0
  3086
		TRgb readValue = ExtractRgbValue(count, aReadBuffer, iDispMode);
sl@0
  3087
		if (colorConvertor.Index(finalColor) != colorConvertor.Index(readValue))
sl@0
  3088
			{
sl@0
  3089
			return EFalse;
sl@0
  3090
			}
sl@0
  3091
		}
sl@0
  3092
	return ETrue;
sl@0
  3093
	}
sl@0
  3094
sl@0
  3095
TRgb CTLowLevel::RgbValue(TRgb aFore,TRgb aBack,CGraphicsContext::TDrawMode aDrawMode)
sl@0
  3096
	{
sl@0
  3097
	TUint32 value = BinaryValue(aFore,aBack,aDrawMode);
sl@0
  3098
sl@0
  3099
	switch (iDispMode)
sl@0
  3100
		{
sl@0
  3101
	case EGray2:
sl@0
  3102
		return TRgb::Gray2(value);
sl@0
  3103
	case EGray4:
sl@0
  3104
		return TRgb::Gray4(value);
sl@0
  3105
	case EGray16:
sl@0
  3106
		return TRgb::Gray16(value);
sl@0
  3107
	case EGray256:
sl@0
  3108
		return TRgb::Gray256(value);
sl@0
  3109
	case EColor16:
sl@0
  3110
		return TRgb::Color16(value);
sl@0
  3111
	case EColor256:
sl@0
  3112
		return TRgb::Color256(value);
sl@0
  3113
	case EColor4K:
sl@0
  3114
		return TRgb::Color4K(value);
sl@0
  3115
	case EColor64K:
sl@0
  3116
		return TRgb::Color64K(value);
sl@0
  3117
	case EColor16M:
sl@0
  3118
		return TRgb::Color16M(value);
sl@0
  3119
	case EColor16MU:
sl@0
  3120
		return TRgb::Color16MU(value);
sl@0
  3121
	case EColor16MA:
sl@0
  3122
		return TRgb::Color16MA(value);
sl@0
  3123
	case EColor16MAP:
sl@0
  3124
		return TRgb::Color16MAP(value);
sl@0
  3125
	default:
sl@0
  3126
		break;
sl@0
  3127
		};
sl@0
  3128
	return KRgbBlack;
sl@0
  3129
	}
sl@0
  3130
sl@0
  3131
TUint32 CTLowLevel::BinaryValue(TRgb aFore,TRgb aBack,CGraphicsContext::TDrawMode aDrawMode)
sl@0
  3132
	{
sl@0
  3133
	TUint32 f = 0;
sl@0
  3134
	TUint32 b = 0;
sl@0
  3135
	TUint32 notVal = 0;
sl@0
  3136
sl@0
  3137
	switch (iDispMode)
sl@0
  3138
		{
sl@0
  3139
	case EGray2:
sl@0
  3140
		f = aFore.Gray2();
sl@0
  3141
		b = aBack.Gray2();
sl@0
  3142
		notVal = 1;
sl@0
  3143
		break;
sl@0
  3144
	case EGray4:
sl@0
  3145
		f = aFore.Gray4();
sl@0
  3146
		b = aBack.Gray4();
sl@0
  3147
		notVal = 3;
sl@0
  3148
		break;
sl@0
  3149
	case EGray16:
sl@0
  3150
		f = aFore.Gray16();
sl@0
  3151
		b = aBack.Gray16();
sl@0
  3152
		notVal = 0xf;
sl@0
  3153
		break;
sl@0
  3154
	case EGray256:
sl@0
  3155
		f = aFore.Gray256();
sl@0
  3156
		b = aBack.Gray256();
sl@0
  3157
		notVal = 0xff;
sl@0
  3158
		break;
sl@0
  3159
	case EColor16:
sl@0
  3160
		f = aFore.Color16();
sl@0
  3161
		b = aBack.Color16();
sl@0
  3162
		notVal = 0xf;
sl@0
  3163
		break;
sl@0
  3164
	case EColor256:
sl@0
  3165
		f = aFore.Color256();
sl@0
  3166
		b = aBack.Color256();
sl@0
  3167
		notVal = 0xff;
sl@0
  3168
		break;
sl@0
  3169
	case EColor4K:
sl@0
  3170
		f = aFore.Color4K();
sl@0
  3171
		b = aBack.Color4K();
sl@0
  3172
		notVal = 0xfff;
sl@0
  3173
		break;
sl@0
  3174
	case EColor64K:
sl@0
  3175
		f = aFore.Color64K();
sl@0
  3176
		b = aBack.Color64K();
sl@0
  3177
		notVal = 0xffff;
sl@0
  3178
		break;
sl@0
  3179
	case EColor16M:
sl@0
  3180
		f = aFore.Color16M();
sl@0
  3181
		b = aBack.Color16M();
sl@0
  3182
		notVal = 0xffffff;
sl@0
  3183
		break;
sl@0
  3184
	case EColor16MU:
sl@0
  3185
		f = aFore.Color16MU();
sl@0
  3186
		b = aBack.Color16MU();
sl@0
  3187
		notVal = 0x00ffffff;
sl@0
  3188
		break;
sl@0
  3189
	case EColor16MA:
sl@0
  3190
		f = aFore.Color16MA();
sl@0
  3191
		b = aBack.Color16MA();
sl@0
  3192
		notVal = 0xffffffff;
sl@0
  3193
		break;
sl@0
  3194
	case EColor16MAP:
sl@0
  3195
		f = aFore.Color16MAP();
sl@0
  3196
		b = aBack.Color16MAP();
sl@0
  3197
sl@0
  3198
		//do not want to blend backgound colours for testing
sl@0
  3199
		if (iBlendTestColors && (aDrawMode&CGraphicsContext::EDrawModePEN))
sl@0
  3200
			{
sl@0
  3201
			Blend((TUint8*)(&f),(TUint8*)(&b),iDispMode);
sl@0
  3202
			}
sl@0
  3203
		notVal = 0xffffffff;
sl@0
  3204
		break;
sl@0
  3205
	default:
sl@0
  3206
		break;
sl@0
  3207
		};
sl@0
  3208
sl@0
  3209
	switch (aDrawMode)
sl@0
  3210
		{
sl@0
  3211
	case CGraphicsContext::EDrawModeAND:		return f & b;
sl@0
  3212
	case CGraphicsContext::EDrawModePEN:		return f;
sl@0
  3213
	case CGraphicsContext::EDrawModeWriteAlpha:	return f;
sl@0
  3214
	case CGraphicsContext::EDrawModeXOR:		return f ^ b;
sl@0
  3215
	case CGraphicsContext::EDrawModeOR:			return f | b;
sl@0
  3216
	case CGraphicsContext::EDrawModeNOTSCREEN:	return b ^ notVal;
sl@0
  3217
	case CGraphicsContext::EDrawModeNOTPEN:		return f;
sl@0
  3218
	default:
sl@0
  3219
		break;
sl@0
  3220
		};
sl@0
  3221
	return 0;
sl@0
  3222
	}
sl@0
  3223
sl@0
  3224
TRgb CTLowLevel::ExtractRgbValue(TInt aX,TUint8* aBuffer,TDisplayMode aDispMode)
sl@0
  3225
	{
sl@0
  3226
	TUint32 value = ExtractBinaryValue(aX,(TUint32*)aBuffer,aDispMode);
sl@0
  3227
sl@0
  3228
	switch (aDispMode)
sl@0
  3229
		{
sl@0
  3230
	case EGray2:
sl@0
  3231
		return TRgb::Gray2(value);
sl@0
  3232
	case EGray4:
sl@0
  3233
		return TRgb::Gray4(value);
sl@0
  3234
	case EGray16:
sl@0
  3235
		return TRgb::Gray16(value);
sl@0
  3236
	case EGray256:
sl@0
  3237
		return TRgb::Gray256(value);
sl@0
  3238
	case EColor16:
sl@0
  3239
		return TRgb::Color16(value);
sl@0
  3240
	case EColor256:
sl@0
  3241
		return TRgb::Color256(value);
sl@0
  3242
	case EColor4K:
sl@0
  3243
		return TRgb::Color4K(value);
sl@0
  3244
	case EColor64K:
sl@0
  3245
		return TRgb::Color64K(value);
sl@0
  3246
	case EColor16M:
sl@0
  3247
		return TRgb::Color16M(value);
sl@0
  3248
	case ERgb:
sl@0
  3249
		return TRgb(value, value>>24);
sl@0
  3250
	case EColor16MU:
sl@0
  3251
		return TRgb::Color16MU(value);
sl@0
  3252
	case EColor16MA:
sl@0
  3253
		return TRgb::Color16MA(value);
sl@0
  3254
	case EColor16MAP:
sl@0
  3255
		return TRgb::Color16MAP(value);
sl@0
  3256
	default:
sl@0
  3257
		break;
sl@0
  3258
		};
sl@0
  3259
	return KRgbBlack;
sl@0
  3260
	}
sl@0
  3261
sl@0
  3262
TUint32 CTLowLevel::ExtractBinaryValue(TInt aX,TUint32* aBuffer,TDisplayMode aDispMode)
sl@0
  3263
	{
sl@0
  3264
	switch (aDispMode)
sl@0
  3265
		{
sl@0
  3266
	case EGray2:
sl@0
  3267
		return ((*(aBuffer + (aX >> 5))) >> (aX & 0x1f)) & 1;
sl@0
  3268
	case EGray4:
sl@0
  3269
		return ((*(aBuffer + (aX >> 4))) >> ((aX & 0xf) * 2)) & 3;
sl@0
  3270
	case EGray16:
sl@0
  3271
	case EColor16:
sl@0
  3272
		return ((*(aBuffer + (aX >> 3))) >> ((aX & 7) * 4)) & 0xf;
sl@0
  3273
	case EGray256:
sl@0
  3274
	case EColor256:
sl@0
  3275
		return ((*(aBuffer + (aX >> 2))) >> ((aX & 3) * 8)) & 0xff;
sl@0
  3276
	case EColor4K:
sl@0
  3277
		return ((*(aBuffer + (aX >> 1))) >> ((aX & 1) * 16)) & 0xfff;
sl@0
  3278
	case EColor64K:
sl@0
  3279
		return ((*(aBuffer + (aX >> 1))) >> ((aX & 1) * 16)) & 0xffff;
sl@0
  3280
	case EColor16M:
sl@0
  3281
		{
sl@0
  3282
		TUint8* buffer = ((TUint8*)aBuffer) + (aX * 3);
sl@0
  3283
		return *buffer | (*(buffer + 1) << 8) | (*(buffer + 2) << 16);
sl@0
  3284
		}
sl@0
  3285
	case ERgb:
sl@0
  3286
		return *(aBuffer + aX);
sl@0
  3287
	case EColor16MU:
sl@0
  3288
		return *(aBuffer + aX) & 0x00FFFFFF;
sl@0
  3289
	case EColor16MA:
sl@0
  3290
	case EColor16MAP:
sl@0
  3291
		return *(aBuffer + aX);
sl@0
  3292
	default:
sl@0
  3293
		break;
sl@0
  3294
		};
sl@0
  3295
	return 0;
sl@0
  3296
	}
sl@0
  3297
sl@0
  3298
void CTLowLevel::Normalize(TRgb& aColor)
sl@0
  3299
	{
sl@0
  3300
	return(Normalize(aColor,iDispMode));
sl@0
  3301
	}
sl@0
  3302
sl@0
  3303
void CTLowLevel::Normalize(TRgb& aColor, TDisplayMode aDispMode)
sl@0
  3304
	{
sl@0
  3305
	switch (aDispMode)
sl@0
  3306
		{
sl@0
  3307
	case EGray2:
sl@0
  3308
		aColor = TRgb::Gray2(aColor.Gray2());
sl@0
  3309
		break;
sl@0
  3310
	case EGray4:
sl@0
  3311
		aColor = TRgb::Gray4(aColor.Gray4());
sl@0
  3312
		break;
sl@0
  3313
	case EGray16:
sl@0
  3314
		aColor = TRgb::Gray16(aColor.Gray16());
sl@0
  3315
		break;
sl@0
  3316
	case EGray256:
sl@0
  3317
		aColor = TRgb::Gray256(aColor.Gray256());
sl@0
  3318
		break;
sl@0
  3319
	case EColor16:
sl@0
  3320
		aColor = TRgb::Color16(aColor.Color16());
sl@0
  3321
		break;
sl@0
  3322
	case EColor256:
sl@0
  3323
		aColor = TRgb::Color256(aColor.Color256());
sl@0
  3324
		break;
sl@0
  3325
	case EColor4K:
sl@0
  3326
		aColor = TRgb::Color4K(aColor.Color4K());
sl@0
  3327
		break;
sl@0
  3328
	case EColor64K:
sl@0
  3329
		aColor = TRgb::Color64K(aColor.Color64K());
sl@0
  3330
		break;
sl@0
  3331
	case EColor16M:
sl@0
  3332
		aColor = TRgb::Color16M(aColor.Color16M());
sl@0
  3333
		break;
sl@0
  3334
	case EColor16MU:
sl@0
  3335
		aColor = TRgb::Color16MU(aColor.Color16MU());
sl@0
  3336
		break;
sl@0
  3337
	case EColor16MA:
sl@0
  3338
		aColor = TRgb::Color16MA(aColor.Color16MA());
sl@0
  3339
		break;
sl@0
  3340
	case EColor16MAP:
sl@0
  3341
		//do nothing, because TRGb is already unpremultiplied
sl@0
  3342
		break;
sl@0
  3343
	default:
sl@0
  3344
		break;
sl@0
  3345
		};
sl@0
  3346
	}
sl@0
  3347
sl@0
  3348
void CTLowLevel::Normalize(TRgb& aColor,TRgb aDitherColors[4])
sl@0
  3349
	{
sl@0
  3350
	switch (iDispMode)
sl@0
  3351
		{
sl@0
  3352
	case EGray2:
sl@0
  3353
		FillArray(TRgb::Gray2(aColor.Gray2()),aDitherColors);
sl@0
  3354
		break;
sl@0
  3355
	case EGray4:
sl@0
  3356
		if (iUserDispMode == EGray2)
sl@0
  3357
			FillArray(TRgb::Gray2(aColor.Gray2()),aDitherColors);
sl@0
  3358
		else
sl@0
  3359
			{
sl@0
  3360
			TInt gray16 = aColor.Gray16();
sl@0
  3361
			aDitherColors[0] = TRgb::Gray4(ditherlutab[gray16][0]);
sl@0
  3362
			aDitherColors[1] = TRgb::Gray4(ditherlutab[gray16][1]);
sl@0
  3363
			aDitherColors[2] = TRgb::Gray4(ditherlutab[gray16][2]);
sl@0
  3364
			aDitherColors[3] = TRgb::Gray4(ditherlutab[gray16][3]);
sl@0
  3365
			}
sl@0
  3366
		break;
sl@0
  3367
	case EGray16:
sl@0
  3368
		if (iUserDispMode == EGray2)
sl@0
  3369
			FillArray(TRgb::Gray2(aColor.Gray2()),aDitherColors);
sl@0
  3370
		else if (iUserDispMode == EGray4)
sl@0
  3371
			{
sl@0
  3372
			TInt gray16 = aColor.Gray16();
sl@0
  3373
			aDitherColors[0] = TRgb::Gray4(ditherlutab[gray16][0]);
sl@0
  3374
			aDitherColors[1] = TRgb::Gray4(ditherlutab[gray16][1]);
sl@0
  3375
			aDitherColors[2] = TRgb::Gray4(ditherlutab[gray16][2]);
sl@0
  3376
			aDitherColors[3] = TRgb::Gray4(ditherlutab[gray16][3]);
sl@0
  3377
			}
sl@0
  3378
		else
sl@0
  3379
			FillArray(TRgb::Gray16(aColor.Gray16()),aDitherColors);
sl@0
  3380
		break;
sl@0
  3381
	case EGray256:
sl@0
  3382
		FillArray(TRgb::Gray256(aColor.Gray256()),aDitherColors);
sl@0
  3383
		break;
sl@0
  3384
	case EColor16:
sl@0
  3385
		FillArray(TRgb::Color16(aColor.Color16()),aDitherColors);
sl@0
  3386
		break;
sl@0
  3387
	case EColor256:
sl@0
  3388
		FillArray(TRgb::Color256(aColor.Color256()),aDitherColors);
sl@0
  3389
		break;
sl@0
  3390
	case EColor4K:
sl@0
  3391
		FillArray(TRgb::Color4K(aColor.Color4K()),aDitherColors);
sl@0
  3392
		break;
sl@0
  3393
	case EColor64K:
sl@0
  3394
		FillArray(TRgb::Color64K(aColor.Color64K()),aDitherColors);
sl@0
  3395
		break;
sl@0
  3396
	case EColor16M:
sl@0
  3397
	case EColor16MU:
sl@0
  3398
	case EColor16MA:
sl@0
  3399
	case EColor16MAP:
sl@0
  3400
		FillArray(aColor,aDitherColors);
sl@0
  3401
		break;
sl@0
  3402
	default:
sl@0
  3403
		break;
sl@0
  3404
		};
sl@0
  3405
	}
sl@0
  3406
sl@0
  3407
void CTLowLevel::FillArray(TRgb aColor,TRgb aArray[4])
sl@0
  3408
	{
sl@0
  3409
	aArray[0] = aColor;
sl@0
  3410
	aArray[1] = aColor;
sl@0
  3411
	aArray[2] = aColor;
sl@0
  3412
	aArray[3] = aColor;
sl@0
  3413
	}
sl@0
  3414
sl@0
  3415
sl@0
  3416
void CTLowLevel::PostBlendShadow(TUint32 &aPmaColor)
sl@0
  3417
	{
sl@0
  3418
	//this function should only be called for PMA colours
sl@0
  3419
	const TInt alpha = aPmaColor >> 24;
sl@0
  3420
	TUint32 value = aPmaColor & 0x00ffffff;
sl@0
  3421
sl@0
  3422
	if (iPostBlendShadow & CFbsDrawDevice::EFade)
sl@0
  3423
		{
sl@0
  3424
#if defined(SYMBIAN_USE_FAST_FADING)
sl@0
  3425
		TUint32 fast_fade_offset = ((SYMBIAN_USE_FAST_FADING & 0xff) * alpha) >>8;
sl@0
  3426
		fast_fade_offset = fast_fade_offset | (fast_fade_offset << 8) | (fast_fade_offset <<16);
sl@0
  3427
		value = ((value >> 1) & ~0x00808080) + (fast_fade_offset);
sl@0
  3428
		value = value | (((TUint32)alpha)<<24);
sl@0
  3429
#else
sl@0
  3430
	/*
sl@0
  3431
	here blackmap = 200,
sl@0
  3432
		 whitemap = 100
sl@0
  3433
	iFadeMapFactor = aWhiteMap - aBlackMap + 1;
sl@0
  3434
	iFadeMapOffset = aBlackMap;
sl@0
  3435
	*/
sl@0
  3436
sl@0
  3437
		const TInt fadeMapOffset = ((alpha * 0x7f) >> 8) & 0xff;
sl@0
  3438
		const TInt wordFadeMapOffset = ((fadeMapOffset) << 16) | (fadeMapOffset);
sl@0
  3439
		const TInt rb = ((((value & 0x00ff00ff) * 0x7f) >> 8) + wordFadeMapOffset) & 0x00ff00ff;
sl@0
  3440
	  	const TInt g = ((((value & 0x0000ff00) * 0x7f) >> 16) + fadeMapOffset) << 8;
sl@0
  3441
		value = rb | g | (((TUint32)alpha)<<24);
sl@0
  3442
#endif
sl@0
  3443
		}
sl@0
  3444
sl@0
  3445
	if (iPostBlendShadow & CFbsDrawDevice::EShadow)
sl@0
  3446
		{
sl@0
  3447
		TInt alpha = (aPmaColor>>24);
sl@0
  3448
		TInt red = (value>>16)&0xff;
sl@0
  3449
		TInt green = (value>>8)&0xff;
sl@0
  3450
		TInt blue = value &0xff;
sl@0
  3451
sl@0
  3452
		TInt shadow= (alpha*0x40)>>8;
sl@0
  3453
		red = Max(0,red-shadow);
sl@0
  3454
		green = Max (0,green-shadow);
sl@0
  3455
		blue = Max (0,blue-shadow);
sl@0
  3456
		value = (((TUint32)alpha)<<24)|(((TUint32)red)<<16)|(((TUint32)green)<<8)|((TUint32)blue);
sl@0
  3457
		}
sl@0
  3458
	aPmaColor = value;
sl@0
  3459
	}
sl@0
  3460
sl@0
  3461
void CTLowLevel::Shadow(TRgb& aColor,TInt aShadowMode)
sl@0
  3462
	{
sl@0
  3463
	if (aShadowMode & 2)
sl@0
  3464
		{
sl@0
  3465
		switch (iDrawDevice->DisplayMode())
sl@0
  3466
			{
sl@0
  3467
		case EGray2:
sl@0
  3468
			aColor = TRgb::Gray256(FadeGray(aColor.Gray2() * 255));
sl@0
  3469
			break;
sl@0
  3470
		case EGray4:
sl@0
  3471
		case EGray16:
sl@0
  3472
			aColor = TRgb::Gray256(FadeGray(aColor.Gray16() * 17));
sl@0
  3473
			break;
sl@0
  3474
		case EGray256:
sl@0
  3475
			aColor = TRgb::Gray256(FadeGray(aColor.Gray256()));
sl@0
  3476
			break;
sl@0
  3477
		case EColor16:
sl@0
  3478
			aColor = FadeRgb(TRgb::Color16(aColor.Color16()));
sl@0
  3479
			break;
sl@0
  3480
		case EColor256:
sl@0
  3481
			aColor = FadeRgb(TRgb::Color256(aColor.Color256()));
sl@0
  3482
			break;
sl@0
  3483
		case EColor4K:
sl@0
  3484
			aColor = FadeRgb(TRgb::Color4K(aColor.Color4K()));
sl@0
  3485
			break;
sl@0
  3486
		case EColor64K:
sl@0
  3487
			aColor = FadeRgb(TRgb::Color64K(aColor.Color64K()),KFastFading && iUseFastFade);
sl@0
  3488
			break;
sl@0
  3489
		case EColor16M:
sl@0
  3490
			aColor = FadeRgb(TRgb::Color16M(aColor.Color16M()));
sl@0
  3491
			break;
sl@0
  3492
		case EColor16MU:
sl@0
  3493
			aColor = FadeRgb(TRgb::Color16MU(aColor.Color16MU()),KFastFading && iUseFastFade);
sl@0
  3494
			break;
sl@0
  3495
		case EColor16MA:
sl@0
  3496
			aColor = FadeRgb(TRgb::Color16MA(aColor.Color16MA()),KFastFading && iUseFastFade);
sl@0
  3497
			break;
sl@0
  3498
		case EColor16MAP:
sl@0
  3499
			aColor = FadeRgb(TRgb::Color16MAP(aColor.Color16MAP()),KFastFading && iUseFastFade);
sl@0
  3500
			break;
sl@0
  3501
		default:
sl@0
  3502
			break;
sl@0
  3503
			};
sl@0
  3504
		}
sl@0
  3505
sl@0
  3506
	if (aShadowMode & 1)
sl@0
  3507
		{
sl@0
  3508
		switch (iDrawDevice->DisplayMode())
sl@0
  3509
			{
sl@0
  3510
		case EGray2:
sl@0
  3511
			aColor = KRgbBlack;
sl@0
  3512
			break;
sl@0
  3513
		case EGray4:
sl@0
  3514
		case EGray16:
sl@0
  3515
			aColor = TRgb::Gray16(Max(0,aColor.Gray16()-5));
sl@0
  3516
			break;
sl@0
  3517
		case EGray256:
sl@0
  3518
			aColor = TRgb::Gray256(Max(0,aColor.Gray256()-85));
sl@0
  3519
			break;
sl@0
  3520
		case EColor16:
sl@0
  3521
			{
sl@0
  3522
			TInt color = aColor.Color16();
sl@0
  3523
			if (color == 15) color--;
sl@0
  3524
			else if (color == 14) color = 1;
sl@0
  3525
			else if (color > 7) color += 3;
sl@0
  3526
			else if (color > 4) color -= 3;
sl@0
  3527
			else color = 0;
sl@0
  3528
			aColor = TRgb::Color16(color);
sl@0
  3529
			}
sl@0
  3530
			break;
sl@0
  3531
		case EColor256:
sl@0
  3532
			{
sl@0
  3533
			aColor = TRgb::Color256(aColor.Color256());
sl@0
  3534
			TInt red = aColor.Red();
sl@0
  3535
			TInt green = aColor.Green();
sl@0
  3536
			TInt blue = aColor.Blue();
sl@0
  3537
			red = Max(0,red-0x33);
sl@0
  3538
			green = Max(0,green-0x33);
sl@0
  3539
			blue = Max(0,blue-0x33);
sl@0
  3540
			aColor = TRgb(red,green,blue);
sl@0
  3541
			}
sl@0
  3542
			break;
sl@0
  3543
		case EColor4K:
sl@0
  3544
			{
sl@0
  3545
			TInt color = aColor.Color4K();
sl@0
  3546
			TInt red = (color & 0xf00) >> 8;
sl@0
  3547
			TInt green = (color & 0x0f0) >> 4;
sl@0
  3548
			TInt blue = color & 0x00f;
sl@0
  3549
sl@0
  3550
			red = Max(0,red-5);
sl@0
  3551
			green = Max(0,green-5);
sl@0
  3552
			blue = Max(0,blue-5);
sl@0
  3553
sl@0
  3554
			aColor = TRgb::Color4K((red << 8) | (green << 4) | blue);
sl@0
  3555
			}
sl@0
  3556
			break;
sl@0
  3557
		case EColor64K:
sl@0
  3558
			{
sl@0
  3559
			TInt color = aColor.Color64K();
sl@0
  3560
			TInt red = (color & 0xf800) >> 11;
sl@0
  3561
			TInt green = (color & 0x07e0) >> 5;
sl@0
  3562
			TInt blue = color & 0x001f;
sl@0
  3563
sl@0
  3564
			red = Max(0,red-8);
sl@0
  3565
			green = Max(0,green-16);
sl@0
  3566
			blue = Max(0,blue-8);
sl@0
  3567
sl@0
  3568
			aColor = TRgb::Color64K((red << 11) | (green << 5) | blue);
sl@0
  3569
			}
sl@0
  3570
			break;
sl@0
  3571
		case EColor16M:
sl@0
  3572
		case EColor16MU:
sl@0
  3573
		case EColor16MA:
sl@0
  3574
		case EColor16MAP:
sl@0
  3575
			{
sl@0
  3576
			TInt red = aColor.Red();
sl@0
  3577
			TInt green = aColor.Green();
sl@0
  3578
			TInt blue = aColor.Blue();
sl@0
  3579
			red = Max(0,red-0x40);
sl@0
  3580
			green = Max(0,green-0x40);
sl@0
  3581
			blue = Max(0,blue-0x40);
sl@0
  3582
			aColor = TRgb(red,green,blue,aColor.Alpha());
sl@0
  3583
			}
sl@0
  3584
			break;
sl@0
  3585
		default:
sl@0
  3586
			break;
sl@0
  3587
			};
sl@0
  3588
		}
sl@0
  3589
	}
sl@0
  3590
sl@0
  3591
void CTLowLevel::Blend(TUint8* aBuffer,TUint8* aBufferDest, TDisplayMode aDispMode)
sl@0
  3592
	{
sl@0
  3593
	TUint32* buffer = reinterpret_cast<TUint32*> (aBuffer);
sl@0
  3594
	TUint32* bufferDest = reinterpret_cast<TUint32*> (aBufferDest);
sl@0
  3595
	TInt mask = (*buffer & 0xff000000) >> 24;
sl@0
  3596
	TRgb rgbDest;
sl@0
  3597
sl@0
  3598
	switch(aDispMode)
sl@0
  3599
		{
sl@0
  3600
	case EColor16MU:
sl@0
  3601
		{
sl@0
  3602
		// src + ((255 - mask) * dest) / 255
sl@0
  3603
		if(mask!=255)
sl@0
  3604
			{
sl@0
  3605
			rgbDest=TRgb::Color16MU(*bufferDest);
sl@0
  3606
			if(mask)
sl@0
  3607
				{
sl@0
  3608
				TRgb rgbSrc=TRgb::Color16MU(*buffer);
sl@0
  3609
				rgbDest.SetRed(rgbSrc.Red() + ((255 - mask) * rgbDest.Red()) / 255);
sl@0
  3610
				rgbDest.SetGreen(rgbSrc.Green() + ((255 - mask) * rgbDest.Green()) / 255);
sl@0
  3611
				rgbDest.SetBlue(rgbSrc.Blue() + ((255 - mask) * rgbDest.Blue()) / 255);
sl@0
  3612
				}
sl@0
  3613
			*buffer=rgbDest.Internal();
sl@0
  3614
			}
sl@0
  3615
		}
sl@0
  3616
		break;
sl@0
  3617
	case EColor16MA:
sl@0
  3618
		{
sl@0
  3619
		// (mask * src + (255 - mask) * dest) / 255
sl@0
  3620
		if(mask!=255)
sl@0
  3621
			{
sl@0
  3622
			rgbDest=TRgb::Color16MA(*bufferDest);
sl@0
  3623
			if(mask)
sl@0
  3624
				{
sl@0
  3625
				TRgb rgbSrc=TRgb::Color16MA(*buffer);
sl@0
  3626
				rgbDest.SetRed((mask * rgbSrc.Red() + (255 - mask) * rgbDest.Red()) / 255);
sl@0
  3627
				rgbDest.SetGreen((mask * rgbSrc.Green() + (255 - mask) * rgbDest.Green()) / 255);
sl@0
  3628
				rgbDest.SetBlue((mask * rgbSrc.Blue() + (255 - mask) * rgbDest.Blue()) / 255);
sl@0
  3629
				}
sl@0
  3630
			*buffer=rgbDest.Internal();
sl@0
  3631
			}
sl@0
  3632
		}
sl@0
  3633
		break;
sl@0
  3634
	case EColor16MAP:
sl@0
  3635
		{
sl@0
  3636
		/*
sl@0
  3637
		* Blend function uses the Porter Duff composition equation
sl@0
  3638
		* This blends two pixels with alphas:
sl@0
  3639
		* Ar  = As  + Ad * (1 - As) (Blended Alpha)
sl@0
  3640
		* Cr = Cs + Cd(1 - As) (Blended Colour)
sl@0
  3641
		* Cr = Cs + Cd(255-As)/255 : for alpha 0-255
sl@0
  3642
		* where Ar = alpha result
sl@0
  3643
		* where Cr = colour result
sl@0
  3644
		* where Cs = source colour
sl@0
  3645
		* where Cd = destination colour
sl@0
  3646
		* The function assumes that the mask buffer is the alpha value of the source pixel.
sl@0
  3647
		*/
sl@0
  3648
		if(mask!=255)
sl@0
  3649
			{
sl@0
  3650
			rgbDest=TRgb::Color16MA(*bufferDest);
sl@0
  3651
			if(mask)
sl@0
  3652
				{
sl@0
  3653
				TInt destAlpha = (*bufferDest & 0xff000000) >> 24;
sl@0
  3654
				TInt sourceAlpha = (*buffer & 0xff000000) >> 24;
sl@0
  3655
				TRgb rgbSrc;
sl@0
  3656
				rgbSrc.SetInternal(*buffer);
sl@0
  3657
				rgbDest.SetInternal(*bufferDest);
sl@0
  3658
				TInt resultAlpha = sourceAlpha +((255-sourceAlpha)*destAlpha)/255;
sl@0
  3659
				rgbDest.SetRed(rgbSrc.Red() + ((255 - sourceAlpha) * rgbDest.Red()) / 255);
sl@0
  3660
				rgbDest.SetGreen(rgbSrc.Green() + ((255 - sourceAlpha) * rgbDest.Green()) / 255);
sl@0
  3661
				rgbDest.SetBlue(rgbSrc.Blue() + ((255 - sourceAlpha) * rgbDest.Blue())/ 255);
sl@0
  3662
				rgbDest.SetAlpha(resultAlpha);
sl@0
  3663
				}
sl@0
  3664
			*buffer=rgbDest.Internal();
sl@0
  3665
			}
sl@0
  3666
		}
sl@0
  3667
		break;
sl@0
  3668
	default: break;
sl@0
  3669
		}
sl@0
  3670
	}
sl@0
  3671
sl@0
  3672
void CTLowLevel::Shadow(TUint8* aBuffer,TInt aByteLength,TInt aShadowMode)
sl@0
  3673
	{
sl@0
  3674
	TUint8* buffer = aBuffer;
sl@0
  3675
	const TUint8* bufferLimit = aBuffer + aByteLength;
sl@0
  3676
sl@0
  3677
	if (aShadowMode & 2)
sl@0
  3678
		{
sl@0
  3679
		switch (iDrawDevice->DisplayMode())
sl@0
  3680
			{
sl@0
  3681
		case EGray2:
sl@0
  3682
			while (buffer < bufferLimit)
sl@0
  3683
				*buffer++ = 0xff;
sl@0
  3684
			break;
sl@0
  3685
		case EGray4:
sl@0
  3686
			while (buffer < bufferLimit)
sl@0
  3687
				{
sl@0
  3688
				TInt first = FadeGray((buffer[0] & 0x03) * 85) >> 6;
sl@0
  3689
				TInt second = FadeGray(((buffer[0] >> 2) & 0x03) * 85) >> 6;
sl@0
  3690
				TInt third = FadeGray(((buffer[0] >> 4) & 0x03) * 85) >> 6;
sl@0
  3691
				TInt fourth = FadeGray(((buffer[0] >> 6) & 0x03) * 85) >> 6;
sl@0
  3692
				*buffer++ = TUint8(first | (second << 2) | (third << 4) | (fourth << 6));
sl@0
  3693
				}
sl@0
  3694
			break;
sl@0
  3695
		case EGray16:
sl@0
  3696
			while (buffer < bufferLimit)
sl@0
  3697
				{
sl@0
  3698
				TInt low = FadeGray((buffer[0] & 0x0f) * 17) >> 4;
sl@0
  3699
				TInt high = FadeGray((buffer[0] >> 4) * 17) >> 4;
sl@0
  3700
				*buffer++ = TUint8((high << 4) | low);
sl@0
  3701
				}
sl@0
  3702
			break;
sl@0
  3703
		case EGray256:
sl@0
  3704
			while (buffer < bufferLimit)
sl@0
  3705
				*buffer++ = FadeGray(*buffer);
sl@0
  3706
			break;
sl@0
  3707
		case EColor16:
sl@0
  3708
			while (buffer < bufferLimit)
sl@0
  3709
				{
sl@0
  3710
				TInt low = FadeRgb(TRgb::Color16(buffer[0] & 0x0f)).Color16();
sl@0
  3711
				TInt high = FadeRgb(TRgb::Color16(buffer[0] >> 4)).Color16();
sl@0
  3712
				*buffer++ = TUint8((high << 4) | low);
sl@0
  3713
				}
sl@0
  3714
			break;
sl@0
  3715
		case EColor256:
sl@0
  3716
			while (buffer < bufferLimit)
sl@0
  3717
				*buffer++ = TUint8(FadeRgb(TRgb::Color256(buffer[0])).Color256());
sl@0
  3718
			break;
sl@0
  3719
		case EColor4K:
sl@0
  3720
			while (buffer < bufferLimit)
sl@0
  3721
				{
sl@0
  3722
				TInt color4K = FadeRgb(TRgb::Color4K(buffer[0] | (buffer[1] << 8))).Color4K();
sl@0
  3723
				buffer[0] = TUint8(color4K);
sl@0
  3724
				buffer[1] = TUint8(color4K >> 8);
sl@0
  3725
				buffer += 2;
sl@0
  3726
				}
sl@0
  3727
			break;
sl@0
  3728
		case EColor64K:
sl@0
  3729
			while (buffer < bufferLimit)
sl@0
  3730
				{
sl@0
  3731
				TInt color64K = FadeRgb(TRgb::Color64K(buffer[0] | (buffer[1] << 8)),ETrue).Color64K();
sl@0
  3732
				buffer[0] = TUint8(color64K);
sl@0
  3733
				buffer[1] = TUint8(color64K >> 8);
sl@0
  3734
				buffer += 2;
sl@0
  3735
				}
sl@0
  3736
			break;
sl@0
  3737
		case EColor16M:
sl@0
  3738
			{
sl@0
  3739
			while (buffer < bufferLimit)
sl@0
  3740
				*buffer++ = FadeGray(buffer[0]);
sl@0
  3741
			}
sl@0
  3742
			break;
sl@0
  3743
		case EColor16MU:
sl@0
  3744
			{
sl@0
  3745
			TUint32* buffer32 = reinterpret_cast <TUint32*> (buffer);
sl@0
  3746
			TUint32* bufferLimit32 = buffer32 + aByteLength / 4;
sl@0
  3747
			while (buffer32 < bufferLimit32)
sl@0
  3748
				{
sl@0
  3749
				// scanline buffer for 16MU driver is pre-multiplied
sl@0
  3750
				TRgb color = FadeRgb(TRgb::Color16MAP(*buffer32),ETrue);
sl@0
  3751
				// avoid rounding errors with EDrawModeAND etc.
sl@0
  3752
				*buffer32++ = color.Alpha() == 255 ? color.Internal() : color.Color16MAP();
sl@0
  3753
				}
sl@0
  3754
			}
sl@0
  3755
			break;
sl@0
  3756
		case EColor16MA:
sl@0
  3757
			{
sl@0
  3758
			TUint32* buffer32 = reinterpret_cast <TUint32*> (buffer);
sl@0
  3759
			TUint32* bufferLimit32 = buffer32 + aByteLength / 4;
sl@0
  3760
			while (buffer32 < bufferLimit32)
sl@0
  3761
				{
sl@0
  3762
				TRgb color = FadeRgb(TRgb::Color16MA(*buffer32),ETrue);
sl@0
  3763
				*buffer32++ = color.Color16MA();
sl@0
  3764
				}
sl@0
  3765
			}
sl@0
  3766
			break;
sl@0
  3767
		case EColor16MAP:
sl@0
  3768
			{
sl@0
  3769
			TUint32* buffer32 = reinterpret_cast <TUint32*> (buffer);
sl@0
  3770
			TUint32* bufferLimit32 = buffer32 + aByteLength / 4;
sl@0
  3771
			while (buffer32 < bufferLimit32)
sl@0
  3772
				{
sl@0
  3773
				TRgb color = FadeRgb(TRgb::Color16MAP(*buffer32),ETrue);
sl@0
  3774
				*buffer32++ = color.Color16MAP();
sl@0
  3775
				}
sl@0
  3776
			}
sl@0
  3777
			break;
sl@0
  3778
		default:
sl@0
  3779
			break;
sl@0
  3780
			}
sl@0
  3781
		}
sl@0
  3782
sl@0
  3783
	buffer = aBuffer;
sl@0
  3784
sl@0
  3785
	if (aShadowMode & 1)
sl@0
  3786
		{
sl@0
  3787
		switch (iDrawDevice->DisplayMode())
sl@0
  3788
			{
sl@0
  3789
		case EGray2:
sl@0
  3790
			while (buffer < bufferLimit)
sl@0
  3791
				{
sl@0
  3792
				*buffer++ = 0;
sl@0
  3793
				}
sl@0
  3794
			break;
sl@0
  3795
		case EGray4:
sl@0
  3796
			while (buffer < bufferLimit)
sl@0
  3797
				{
sl@0
  3798
				TInt first = buffer[0] & 0x03;
sl@0
  3799
				TInt second = buffer[0] & 0x0c;
sl@0
  3800
				TInt third = buffer[0] & 0x30;
sl@0
  3801
				TInt fourth = buffer[0] & 0xc0;
sl@0
  3802
				first = Max(0,first-1);
sl@0
  3803
				second = Max(0,second-4);
sl@0
  3804
				third = Max(0,third-16);
sl@0
  3805
				fourth = Max(0,fourth-64);
sl@0
  3806
				*buffer++ = TUint8(fourth | third | second | first);
sl@0
  3807
				}
sl@0
  3808
			break;
sl@0
  3809
		case EGray16:
sl@0
  3810
			while (buffer < bufferLimit)
sl@0
  3811
				{
sl@0
  3812
				TInt low = buffer[0] & 0x0f;
sl@0
  3813
				TInt high = buffer[0] >> 4;
sl@0
  3814
				low = Max(0,low-5);
sl@0
  3815
				high = Max(0,high-5);
sl@0
  3816
				*buffer++ = TUint8((high << 4) | low);
sl@0
  3817
				}
sl@0
  3818
			break;
sl@0
  3819
		case EGray256:
sl@0
  3820
			while (buffer < bufferLimit)
sl@0
  3821
				{
sl@0
  3822
				buffer[0] = TUint8(Max(0,buffer[0]-85));
sl@0
  3823
				buffer++;
sl@0
  3824
				}
sl@0
  3825
			break;
sl@0
  3826
		case EColor16:
sl@0
  3827
			while (buffer < bufferLimit)
sl@0
  3828
				{
sl@0
  3829
				TInt low = buffer[0] & 0x0f;
sl@0
  3830
				TInt high = buffer[0] >> 4;
sl@0
  3831
				if (low == 15) low = 14;
sl@0
  3832
				else if (low == 14) low = 1;
sl@0
  3833
				else if (low >= 11) low = 0;
sl@0
  3834
				else if (low >= 8) low += 3;
sl@0
  3835
				else if (low >= 5) low -= 3;
sl@0
  3836
				else low = 0;
sl@0
  3837
				if (high == 15) high = 14;
sl@0
  3838
				else if (high == 14) high = 1;
sl@0
  3839
				else if (high >= 11) high = 0;
sl@0
  3840
				else if (high >= 8) high += 3;
sl@0
  3841
				else if (high >= 5) high -= 3;
sl@0
  3842
				else high = 0;
sl@0
  3843
				*buffer++ = TUint8((high << 4) | low);
sl@0
  3844
				}
sl@0
  3845
			break;
sl@0
  3846
		case EColor256:
sl@0
  3847
			while (buffer < bufferLimit)
sl@0
  3848
				{
sl@0
  3849
				TRgb color(TRgb::Color256(buffer[0]));
sl@0
  3850
				TInt red = color.Red();
sl@0
  3851
				TInt green = color.Green();
sl@0
  3852
				TInt blue = color.Blue();
sl@0
  3853
				red = Max(0,red-0x33);
sl@0
  3854
				green = Max(0,green-0x33);
sl@0
  3855
				blue = Max(0,blue-0x33);
sl@0
  3856
				*buffer++ = TUint8(TRgb(red,green,blue).Color256());
sl@0
  3857
				}
sl@0
  3858
			break;
sl@0
  3859
		case EColor4K:
sl@0
  3860
			while (buffer < bufferLimit)
sl@0
  3861
				{
sl@0
  3862
				TInt data = (buffer[1] << 8) | buffer[0];
sl@0
  3863
				TInt red = (data & 0xf00) >> 8;
sl@0
  3864
				TInt green = (data & 0x0f0) >> 4;
sl@0
  3865
				TInt blue = data & 0x00f;
sl@0
  3866
				red = Max(0,red-5);
sl@0
  3867
				green = Max(0,green-5);
sl@0
  3868
				blue = Max(0,blue-5);
sl@0
  3869
				data = (red << 8) | (green << 4) | blue;
sl@0
  3870
				buffer[0] = TUint8(data);
sl@0
  3871
				buffer[1] = TUint8(data >> 8);
sl@0
  3872
				buffer += 2;
sl@0
  3873
				}
sl@0
  3874
			break;
sl@0
  3875
		case EColor64K:
sl@0
  3876
			while (buffer < bufferLimit)
sl@0
  3877
				{
sl@0
  3878
				TInt data = (buffer[1] << 8) | buffer[0];
sl@0
  3879
				TInt red = (data & 0xf800) >> 11;
sl@0
  3880
				TInt green = (data & 0x07e0) >> 5;
sl@0
  3881
				TInt blue = data & 0x001f;
sl@0
  3882
				red = Max(0,red-8);
sl@0
  3883
				green = Max(0,green-16);
sl@0
  3884
				blue = Max(0,blue-8);
sl@0
  3885
				data = (red << 11) | (green << 5) | blue;
sl@0
  3886
				buffer[0] = TUint8(data);
sl@0
  3887
				buffer[1] = TUint8(data >> 8);
sl@0
  3888
				buffer += 2;
sl@0
  3889
				}
sl@0
  3890
			break;
sl@0
  3891
		case EColor16M:
sl@0
  3892
			while (buffer < bufferLimit)
sl@0
  3893
				{
sl@0
  3894
				buffer[0] = TUint8(Max(0,buffer[0]-0x40));
sl@0
  3895
				buffer++;
sl@0
  3896
				}
sl@0
  3897
			break;
sl@0
  3898
		case EColor16MU:
sl@0
  3899
			{
sl@0
  3900
			TUint32* buffer32 = reinterpret_cast <TUint32*> (buffer);
sl@0
  3901
			TUint32* bufferLimit32 = buffer32 + aByteLength / 4;
sl@0
  3902
			while (buffer32 < bufferLimit32)
sl@0
  3903
				{
sl@0
  3904
				// scanline buffer for 16MU driver is pre-multiplied
sl@0
  3905
				TRgb color = TRgb::Color16MAP(*buffer32);
sl@0
  3906
				color = TRgb(Max(0,color.Red()-0x40),Max(0,color.Green()-0x40),Max(0,color.Blue()-0x40), color.Alpha());
sl@0
  3907
				// avoid rounding errors with EDrawModeAND etc.
sl@0
  3908
				*buffer32++ = color.Alpha() == 255 ? color.Internal() : color.Color16MAP();
sl@0
  3909
				}
sl@0
  3910
			}
sl@0
  3911
			break;
sl@0
  3912
		case EColor16MA:
sl@0
  3913
			{
sl@0
  3914
			TUint32* buffer32 = reinterpret_cast <TUint32*> (buffer);
sl@0
  3915
			TUint32* bufferLimit32 = buffer32 + aByteLength / 4;
sl@0
  3916
			while (buffer32 < bufferLimit32)
sl@0
  3917
				{
sl@0
  3918
				TRgb color = TRgb::Color16MA(*buffer32);
sl@0
  3919
				color = TRgb(Max(0,color.Red()-0x40),Max(0,color.Green()-0x40),Max(0,color.Blue()-0x40), color.Alpha());
sl@0
  3920
				*buffer32++ = color.Color16MA();
sl@0
  3921
				}
sl@0
  3922
			}
sl@0
  3923
			break;
sl@0
  3924
		case EColor16MAP:
sl@0
  3925
			{
sl@0
  3926
			TUint32* buffer32 = reinterpret_cast <TUint32*> (buffer);
sl@0
  3927
			TUint32* bufferLimit32 = buffer32 + aByteLength / 4;
sl@0
  3928
			while (buffer32 < bufferLimit32)
sl@0
  3929
				{
sl@0
  3930
				TRgb color = TRgb::Color16MAP(*buffer32);
sl@0
  3931
				color = TRgb(Max(0,color.Red()-0x40),Max(0,color.Green()-0x40),Max(0,color.Blue()-0x40), color.Alpha());
sl@0
  3932
				*buffer32++ = color.Color16MAP();
sl@0
  3933
				}
sl@0
  3934
			}
sl@0
  3935
			break;
sl@0
  3936
		default:
sl@0
  3937
			break;
sl@0
  3938
			}
sl@0
  3939
		}
sl@0
  3940
	}
sl@0
  3941
sl@0
  3942
TUint8 CTLowLevel::FadeGray(TInt aGray256)
sl@0
  3943
	{
sl@0
  3944
	return TUint8((aGray256 >> 1) + 128);
sl@0
  3945
	}
sl@0
  3946
sl@0
  3947
/**
sl@0
  3948
A test code function for Fading colour values.
sl@0
  3949
@param aColor Colour value for which faded colour is needed.
sl@0
  3950
@param aFastFade Used to check whether Fast Fading method is required or not.
sl@0
  3951
		aFastFade flag should be true only when there is a corresponding Fast Fading
sl@0
  3952
		implementation in product code and the fading method uses the Fast Fading method.
sl@0
  3953
@return TRgb Faded colour value.
sl@0
  3954
*/
sl@0
  3955
TRgb CTLowLevel::FadeRgb(TRgb aColor, TBool aFastFade/*=EFalse*/)
sl@0
  3956
	{
sl@0
  3957
	if(aFastFade)
sl@0
  3958
		{
sl@0
  3959
#if defined(SYMBIAN_USE_FAST_FADING)
sl@0
  3960
		TUint32 value = ((aColor.Internal() >> 1) & ~0x00808080) + SYMBIAN_USE_FAST_FADING;
sl@0
  3961
		TInt alpha = aColor.Alpha();
sl@0
  3962
		return TRgb(value, alpha);
sl@0
  3963
#endif
sl@0
  3964
		}
sl@0
  3965
	TInt red = (aColor.Red() >> 1) + 128;
sl@0
  3966
	TInt green = (aColor.Green() >> 1) + 128;
sl@0
  3967
	TInt blue = (aColor.Blue() >> 1) + 128;
sl@0
  3968
	TInt alpha = aColor.Alpha();
sl@0
  3969
	return TRgb(red,green,blue,alpha);
sl@0
  3970
	}
sl@0
  3971
sl@0
  3972
TColorConvertor& CTLowLevel::ColorConvertor(TDisplayMode aDisplayMode)
sl@0
  3973
	{
sl@0
  3974
	return *iColorConvertor[aDisplayMode];
sl@0
  3975
	}
sl@0
  3976
sl@0
  3977
void CTLowLevel::Report()
sl@0
  3978
	{
sl@0
  3979
	INFO_PRINTF4(_L("Test %d: %d/%d"),iTestNo,iReportIteration,iTotalReportIterations);
sl@0
  3980
	if (iReportIteration < iTotalReportIterations)
sl@0
  3981
		iReportIteration++;
sl@0
  3982
	}
sl@0
  3983
sl@0
  3984
inline TBool CTLowLevel::Check(TBool aValue)
sl@0
  3985
	{
sl@0
  3986
	if (iLastFailTestNo!=iIteration)
sl@0
  3987
		{
sl@0
  3988
		if (!aValue)
sl@0
  3989
			{
sl@0
  3990
			_LIT(KLog,"Test %d, iteration %d failed  iDispMode %d  iUserDispMode %d  iOrientation %d");
sl@0
  3991
			INFO_PRINTF6(KLog,iTestNo,iIteration,iDispMode,iUserDispMode,iOrientation);
sl@0
  3992
			iLastFailTestNo=iIteration;
sl@0
  3993
			}
sl@0
  3994
		TEST(aValue);
sl@0
  3995
		}
sl@0
  3996
	return !aValue;
sl@0
  3997
	}
sl@0
  3998
sl@0
  3999
//-----------
sl@0
  4000
CTLowLevel1::CTLowLevel1(CTestStep* aStep):
sl@0
  4001
	CTLowLevel(aStep)
sl@0
  4002
	{
sl@0
  4003
	iOrientation = CFbsDrawDevice::EOrientationRotated180;
sl@0
  4004
	iOrientationEnd = CFbsDrawDevice::EOrientationRotated270;
sl@0
  4005
	}
sl@0
  4006
sl@0
  4007
void CTLowLevel1::RunTestCaseL(TInt /*aCurTestCase*/)
sl@0
  4008
	{
sl@0
  4009
	if(iOrientation <= iOrientationEnd)
sl@0
  4010
		{
sl@0
  4011
		INFO_PRINTF2(_L("Screen device : %S"), &DisplayModeNames1[iCurScreenDeviceModeIndex]);
sl@0
  4012
		TDisplayMode display = TestDisplayMode1[iCurScreenDeviceModeIndex++];
sl@0
  4013
/**
sl@0
  4014
	@SYMTestCaseID GRAPHICS-SCREENDRIVER-0018
sl@0
  4015
*/
sl@0
  4016
		((CTLowLevelStep*)iStep)->SetTestStepID(_L("GRAPHICS-SCREENDRIVER-0018"));
sl@0
  4017
		TestScreenDrawL(display);
sl@0
  4018
		if(iCurScreenDeviceModeIndex >= KNumberDisplayModes1)
sl@0
  4019
			{
sl@0
  4020
			iCurScreenDeviceModeIndex = 0;
sl@0
  4021
			iOrientation ++;
sl@0
  4022
			}
sl@0
  4023
		((CTLowLevelStep*)iStep)->RecordTestResultL();
sl@0
  4024
		}
sl@0
  4025
	else
sl@0
  4026
		{
sl@0
  4027
		((CTLowLevelStep*)iStep)->CloseTMSGraphicsStep();
sl@0
  4028
		TestComplete();
sl@0
  4029
		}
sl@0
  4030
	}
sl@0
  4031
sl@0
  4032
//--------------
sl@0
  4033
__CONSTRUCT_STEP__(LowLevel)
sl@0
  4034
sl@0
  4035
__CONSTRUCT_STEP__(LowLevel1)