graphicsdeviceinterface/screendriver/sbit/BMDRAW8.CPP
changeset 0 5d03bc08d59c
equal deleted inserted replaced
-1:000000000000 0:5d03bc08d59c
       
     1 // Copyright (c) 1997-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 //
       
    15 
       
    16 #include "BMDRAW.H"
       
    17 #include "BitDrawInterfaceId.h"
       
    18 
       
    19 // CDrawEightBppBitmapCommon
       
    20 //EColor256 screen/bitmap device might be scaled.
       
    21 //In this case right-bottom coordinate might go outside the drawing rectangle.
       
    22 //Then - we need to check that we do not try to draw something outside the drawing rectangle.
       
    23 
       
    24 //Initializes iSize, iDrawRect, iLongWidth, iScanlineWords data members.
       
    25 //It should be called every time when iSize is going to be changed - from Construct().
       
    26 //@param aSize Physical screen size in pixels.
       
    27 //@panic EScreenDriverPanicInvalidSize - Invalid aSize parameter. This might happen if the 
       
    28 //device is scaled and the scaling origin goes outside physical drawing rectangle.
       
    29 void CDrawEightBppBitmapCommon::SetSize(const TSize& aSize) 
       
    30 	{
       
    31 	CDrawBitmap::SetSize(aSize);
       
    32 	__ASSERT_DEBUG(iSize == aSize, User::Invariant());
       
    33 	iLongWidth = (iSize.iWidth + 3) & ~3;
       
    34 	iScanLineWords = iLongWidth / 4;
       
    35 	}
       
    36  
       
    37 TInt CDrawEightBppBitmapCommon::Construct(TSize aSize, TInt aStride)
       
    38 	{
       
    39 	iBits = NULL;
       
    40 	CDrawBitmap::SetSize(aSize);
       
    41 	__ASSERT_DEBUG(iSize == aSize, User::Invariant());
       
    42 	if (aStride & 3)
       
    43 		return KErrArgument;
       
    44 	iLongWidth = aStride;
       
    45 	if (iLongWidth < aSize.iWidth)
       
    46 		return KErrArgument;
       
    47 	iScanLineWords = aStride >> 2;
       
    48 	TInt size = Max(aSize.iWidth,aSize.iHeight);
       
    49 	if(size < 0)
       
    50 		return KErrArgument;
       
    51 	iScanLineBuffer = (TUint32*)(User::Heap().Alloc(size));
       
    52 	if(iScanLineBuffer == NULL)
       
    53 		return KErrNoMemory;
       
    54 	return KErrNone;
       
    55 	}
       
    56 
       
    57 //aX, aY - physical coordinates
       
    58 TUint8* CDrawEightBppBitmapCommon::PixelAddress(TInt aX,TInt aY) const
       
    59 	{
       
    60 	return (TUint8*)iBits + aY * iLongWidth + aX;
       
    61 	}
       
    62 
       
    63 void CDrawEightBppBitmapCommon::InvertBuffer(TInt aLength,TUint32* aBuffer)
       
    64 	{
       
    65 	const TUint32* limit = aBuffer + (aLength + 3) / 4;
       
    66 
       
    67 	while (aBuffer < limit)
       
    68 		*aBuffer++ ^= 0xffffffff;
       
    69 	}
       
    70 
       
    71 //CDrawEightBppBitmapCommon::ReadLine() called from CDrawBitmap::ReadLine()
       
    72 //aX and aY - physical coordinates.
       
    73 //Reads aLength pixel values and places them in aBuffer.
       
    74 //aBuffer size should be at least aLength.
       
    75 void CDrawEightBppBitmapCommon::ReadLine(TInt aX,TInt aY,TInt aLength,TAny* aBuffer) const
       
    76 	{
       
    77 	const TUint8* pixelPtr = PixelAddress(aX,aY);
       
    78 
       
    79 	if (iOrientation == EOrientationNormal && iScalingOff)
       
    80 		Mem::Copy(aBuffer,pixelPtr,aLength);
       
    81 	else
       
    82 		{
       
    83 		register TInt pixelPtrInc = LogicalPixelAddressIncrement();
       
    84 
       
    85 		TUint8* bufferPtr = static_cast <TUint8*> (aBuffer);
       
    86 		const TUint8* bufferPtrLimit = bufferPtr + aLength;
       
    87 
       
    88 		while (bufferPtr < bufferPtrLimit)
       
    89 			{
       
    90 			*bufferPtr++ = *pixelPtr;
       
    91 			pixelPtr += pixelPtrInc;
       
    92 			}
       
    93 		}
       
    94 	}
       
    95 
       
    96 //CDrawEightBppBitmapCommon::WriteRgb() called from exported CDrawBitmap::WriteRgb()
       
    97 //aX, aY - physical coordinates
       
    98 void CDrawEightBppBitmapCommon::WriteRgb(TInt aX,TInt aY,TUint8 aPixel)
       
    99 	{
       
   100 	register TUint8* pixelAddr = PixelAddress(aX, aY);
       
   101 	if(iScalingOff)
       
   102 		{
       
   103 		*pixelAddr = aPixel;
       
   104 		}
       
   105 	else
       
   106 		{
       
   107 		const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   108 		const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   109 		const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   110 		SetPixels(pixelAddr, aPixel, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   111 		}
       
   112 	}
       
   113 
       
   114 //CDrawEightBppBitmapCommon::WriteBinary() called from exported CDrawBitmap::WriteBinary()
       
   115 //aX, aY - logical coordinates
       
   116 //"aData" parameter has "aHeight" 32 bits words
       
   117 //"aLength" parameter tells how many bits (up to 32) has to be used from each 32 bit word
       
   118 //This method is used for bitmap font symbols drawing
       
   119 //One possible optimization: If "no scaling" And "pixelPtrInc == 1" Then
       
   120 //writing could be made on 32 bits words (they has to be aligned before the operation)
       
   121 void CDrawEightBppBitmapCommon::WriteBinary(TInt aX,TInt aY,TUint32* aData,TInt aLength,
       
   122 											TInt aHeight,TUint8 aPixel)
       
   123 	{
       
   124 	DeOrientate(aX,aY);//aX, aY - physical coordinates
       
   125 	TInt pixelInc;
       
   126 	TInt rowInc;
       
   127 	SetPixelInc(pixelInc, rowInc);
       
   128 	const TUint32* dataLimit = aData + aHeight;
       
   129 	register TUint32 dataMaskLimit = (aLength < 32) ? 1 << aLength : 0;
       
   130 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   131 	const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   132 	const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   133 	TInt orgY = aY;
       
   134 	while (aData < dataLimit)
       
   135 		{
       
   136 		register TUint32 dataWord = *aData++;
       
   137 		register TUint32 dataMask = 1;
       
   138 		register TUint8* tempPixelPtr = pixelPtr;
       
   139 		if(iScalingOff)
       
   140 			{
       
   141 			while (dataMask != dataMaskLimit)
       
   142 				{
       
   143 				if(dataWord & dataMask)
       
   144 					{
       
   145 					*tempPixelPtr = aPixel;
       
   146 					}
       
   147 				tempPixelPtr += pixelInc;
       
   148 				dataMask <<= 1;
       
   149 				}
       
   150 			}
       
   151 		else
       
   152 			{
       
   153 			while (dataMask != dataMaskLimit)
       
   154 				{
       
   155 				if(dataWord & dataMask)
       
   156 					{
       
   157 					const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   158 					SetPixels(tempPixelPtr, aPixel, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   159 					}
       
   160 				tempPixelPtr += pixelInc;
       
   161 				dataMask <<= 1;
       
   162 				IncScaledY(aY);
       
   163 				}
       
   164 			}
       
   165 		pixelPtr += rowInc;
       
   166 		IncScaledY(aY, orgY);
       
   167 		}
       
   168 	}
       
   169 
       
   170 //CDrawEightBppBitmapCommon::WriteBinaryOp() called from exported CDrawBitmap::WriteBinary()
       
   171 //aX, aY - logical coordinates
       
   172 //"aData" parameter has "aHeight" 32 bits words
       
   173 //"aLength" parameter tells how many bits (up to 32) has to be used from each 32 bit word
       
   174 //This method is used for bitmap font symbols drawing
       
   175 //One possible optimization: If "no scaling" And "pixelPtrInc == 1" Then
       
   176 //writing could be made on 32 bits words (they has to be aligned before the operation)
       
   177 void CDrawEightBppBitmapCommon::WriteBinaryOp(TInt aX,TInt aY,TUint32* aData,TInt aLength,
       
   178 											  TInt aHeight,TUint8 aPixel,
       
   179 											  CGraphicsContext::TDrawMode aDrawMode)
       
   180 	{
       
   181 	if(aLength <= 0)
       
   182 		{
       
   183 		return;
       
   184 		}
       
   185 	DeOrientate(aX,aY);//aX, aY - physical coordinates
       
   186 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   187 	const TUint32* dataPtrLimit = aData + aHeight;
       
   188 	register TUint32 dataMaskLimit = (aLength < 32) ? 1 << aLength : 0;
       
   189 	TInt pixelInc;
       
   190 	TInt rowInc;
       
   191 	SetPixelInc(pixelInc, rowInc);
       
   192 	const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   193 	const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   194 	TInt orgY = aY;
       
   195 	if(aPixel)
       
   196 		{
       
   197 		while(aData < dataPtrLimit)
       
   198 			{
       
   199 			register TUint32 dataWord = *aData++;
       
   200 			register TUint32 dataMask = 1;
       
   201 			register TUint8* tempPixelPtr = pixelPtr;
       
   202 			if(iScalingOff)
       
   203 				{
       
   204 				while(dataMask != dataMaskLimit)
       
   205 					{
       
   206 					if(dataWord & dataMask)
       
   207 						{
       
   208 						if(aDrawMode==CGraphicsContext::EDrawModeXOR)
       
   209 							{
       
   210 							*tempPixelPtr ^= aPixel;
       
   211 							}
       
   212 						else if(aDrawMode==CGraphicsContext::EDrawModeAND)
       
   213 							{
       
   214 							*tempPixelPtr &= aPixel;
       
   215 							}
       
   216 						else if(aDrawMode==CGraphicsContext::EDrawModeOR)
       
   217 							{
       
   218 							*tempPixelPtr |= aPixel;
       
   219 							}
       
   220 						}
       
   221 					tempPixelPtr += pixelInc;
       
   222 					dataMask <<= 1;
       
   223 					}
       
   224 				}
       
   225 			else
       
   226 				{
       
   227 				while(dataMask != dataMaskLimit)
       
   228 					{
       
   229 					if(dataWord & dataMask)
       
   230 						{
       
   231 						const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   232 						if(aDrawMode==CGraphicsContext::EDrawModeXOR)
       
   233 							{
       
   234 							XORPixels(tempPixelPtr, aPixel, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   235 							}
       
   236 						else if(aDrawMode==CGraphicsContext::EDrawModeAND)
       
   237 							{
       
   238 							ANDPixels(tempPixelPtr, aPixel, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   239 							}
       
   240 						else if(aDrawMode==CGraphicsContext::EDrawModeOR)
       
   241 							{
       
   242 							ORPixels(tempPixelPtr, aPixel, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   243 							}
       
   244 						}
       
   245 					tempPixelPtr += pixelInc;
       
   246 					dataMask <<= 1;
       
   247 					IncScaledY(aY);
       
   248 					}
       
   249 				}
       
   250 			pixelPtr += rowInc;
       
   251 			IncScaledY(aY, orgY);
       
   252 			}
       
   253 		}
       
   254 	else if(aDrawMode==CGraphicsContext::EDrawModeAND)
       
   255 		{
       
   256 		while(aData < dataPtrLimit)
       
   257 			{
       
   258 			register TUint32 dataWord = *aData++;
       
   259 			register TUint32 dataMask = 1;
       
   260 			register TUint8* tempPixelPtr = pixelPtr;
       
   261 			if(iScalingOff)
       
   262 				{
       
   263 				while(dataMask != dataMaskLimit)
       
   264 					{
       
   265 					if(dataWord & dataMask)
       
   266 						{
       
   267 						*tempPixelPtr = 0;
       
   268 						}
       
   269 					tempPixelPtr += pixelInc;
       
   270 					dataMask <<= 1;
       
   271 					}
       
   272 				}
       
   273 			else
       
   274 				{
       
   275 				while(dataMask != dataMaskLimit)
       
   276 					{
       
   277 					if(dataWord & dataMask)
       
   278 						{
       
   279 						const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   280 						SetPixels(tempPixelPtr, TUint8(0), pixelRowPtrLimit, bitsStart, bitsEnd);
       
   281 						}
       
   282 					tempPixelPtr += pixelInc;
       
   283 					dataMask <<= 1;
       
   284 					}
       
   285 				}
       
   286 			pixelPtr += rowInc;
       
   287 			IncScaledY(aY, orgY);
       
   288 			}
       
   289 		}
       
   290 	}
       
   291 
       
   292 //aX, aY - logical coordinates
       
   293 //"aData" parameter has 32 bits words
       
   294 //"aLength" parameter tells how many pixels have to be written
       
   295 //This method is used for bitmap font symbols vertical drawing
       
   296 //The method should not be called if the scaling is ON!
       
   297 void CDrawEightBppBitmapCommon::WriteBinaryLineVertical(TInt aX,TInt aY,TUint32* aData,
       
   298 														TInt aLength,TUint8 aPixel,TBool aUp)
       
   299 	{
       
   300 	__ASSERT_DEBUG(iScalingOff, User::Invariant());
       
   301 
       
   302 	DeOrientate(aX,aY);//aX, aY - physical coordinates
       
   303 
       
   304 	TInt scanlineByteLength;
       
   305 	switch(iOrientation)
       
   306 		{
       
   307 		case EOrientationNormal:
       
   308 			scanlineByteLength = iLongWidth;
       
   309 			break;
       
   310 		case EOrientationRotated90:
       
   311 			scanlineByteLength = -1;
       
   312 			break;
       
   313 		case EOrientationRotated180:
       
   314 			scanlineByteLength = -iLongWidth;
       
   315 			break;
       
   316 		default: // EOrientationRotated270
       
   317 			scanlineByteLength = 1;
       
   318 		}
       
   319 
       
   320 	if (aUp)
       
   321 		scanlineByteLength = -scanlineByteLength;
       
   322 
       
   323 	register TUint8* pixelPtr = PixelAddress(aX,aY);
       
   324 	const TUint8* pixelPtrLimit = pixelPtr + aLength * scanlineByteLength;
       
   325 	register TUint32 dataWord = *aData;
       
   326 	register TUint32 dataMask = 1;
       
   327 
       
   328 	while(pixelPtr != pixelPtrLimit)
       
   329 		{
       
   330 		if(!dataMask)
       
   331 			{
       
   332 			dataMask = 1;
       
   333 			aData++;
       
   334 			dataWord = *aData;
       
   335 			}
       
   336 		if(dataWord & dataMask)
       
   337 			{
       
   338 			*pixelPtr = aPixel;
       
   339 			}
       
   340 		dataMask <<= 1;
       
   341 		pixelPtr += scanlineByteLength;
       
   342 		}
       
   343 	}
       
   344 
       
   345 //CDrawEightBppBitmapCommon::WriteLine() called from CDrawBitmap::WriteLine()
       
   346 //aX and aY - physical coordinates
       
   347 void CDrawEightBppBitmapCommon::WriteLine(TInt aX,TInt aY,TInt aLength,TUint32* aBuffer)
       
   348 	{
       
   349 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   350 	if (iOrientation == EOrientationNormal && iScalingOff)
       
   351 		{
       
   352 		Mem::Copy(pixelPtr,aBuffer,aLength);
       
   353 		}
       
   354 	else
       
   355 		{
       
   356 		register TInt pixelPtrInc = LogicalPixelAddressIncrement();
       
   357 		TUint8* bufferPtr = reinterpret_cast <TUint8*> (aBuffer);
       
   358 		const TUint8* bufferPtrLimit = bufferPtr + aLength;
       
   359 		if(iScalingOff)
       
   360 			{
       
   361 			while(bufferPtr < bufferPtrLimit)
       
   362 				{
       
   363 				*pixelPtr = *bufferPtr++;
       
   364 				pixelPtr += pixelPtrInc;
       
   365 				}
       
   366 			}
       
   367 		else
       
   368 			{
       
   369 			const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   370 			const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   371 			while(bufferPtr < bufferPtrLimit)
       
   372 				{
       
   373 				const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   374 				SetPixels(pixelPtr, *bufferPtr++, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   375 				pixelPtr += pixelPtrInc;
       
   376 				IncScaledY(aY);
       
   377 				}
       
   378 			}
       
   379 		}
       
   380 	}
       
   381 
       
   382 //CDrawEightBppBitmapCommon::WriteLineXOR() called from CDrawBitmap::WriteLine()
       
   383 //aX and aY - physical coordinates
       
   384 //One possible optimization: If "no scaling" And "pixelPtrInc == 1" Then
       
   385 //XOR could be made on 32 bits words (they  has to be aligned before the operation)
       
   386 void CDrawEightBppBitmapCommon::WriteLineXOR(TInt aX,TInt aY,TInt aLength,TUint32* aBuffer)
       
   387 	{
       
   388 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   389 	register TInt pixelPtrInc = LogicalPixelAddressIncrement();
       
   390 	TUint8* bufferPtr = reinterpret_cast <TUint8*> (aBuffer);
       
   391 	const TUint8* bufferPtrLimit = bufferPtr + aLength;
       
   392 	if(iScalingOff)
       
   393 		{
       
   394 		while(bufferPtr < bufferPtrLimit)
       
   395 			{
       
   396 			*pixelPtr ^= *bufferPtr++;
       
   397 			pixelPtr += pixelPtrInc;
       
   398 			}
       
   399 		}
       
   400 	else
       
   401 		{
       
   402 		const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   403 		const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   404 		while(bufferPtr < bufferPtrLimit)
       
   405 			{
       
   406 			const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   407 			XORPixels(pixelPtr, *bufferPtr++, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   408 			pixelPtr += pixelPtrInc;
       
   409 			IncScaledY(aY);
       
   410 			}
       
   411 		}
       
   412 	}
       
   413 
       
   414 //CDrawEightBppBitmapCommon::WriteLineAND() called from CDrawBitmap::WriteLine()
       
   415 //aX and aY - deorientated and scaled
       
   416 //aLength - not scaled
       
   417 //One possible optimization: If "no scaling" And "pixelPtrInc == 1" Then
       
   418 //AND could be made on 32 bits words (they  has to be aligned before the operation)
       
   419 void CDrawEightBppBitmapCommon::WriteLineAND(TInt aX,TInt aY,TInt aLength,TUint32* aBuffer)
       
   420 	{
       
   421 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   422 	register TInt pixelPtrInc = LogicalPixelAddressIncrement();
       
   423 	TUint8* bufferPtr = reinterpret_cast <TUint8*> (aBuffer);
       
   424 	const TUint8* bufferPtrLimit = bufferPtr + aLength;
       
   425 	if(iScalingOff)
       
   426 		{
       
   427 		while(bufferPtr < bufferPtrLimit)
       
   428 			{
       
   429 			*pixelPtr &= *bufferPtr++;
       
   430 			pixelPtr += pixelPtrInc;
       
   431 			}
       
   432 		}
       
   433 	else
       
   434 		{
       
   435 		const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   436 		const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   437 		while(bufferPtr < bufferPtrLimit)
       
   438 			{
       
   439 			const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   440 			ANDPixels(pixelPtr, *bufferPtr++, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   441 			pixelPtr += pixelPtrInc;
       
   442 			IncScaledY(aY);
       
   443 			}
       
   444 		}
       
   445 	}
       
   446 
       
   447 //CDrawEightBppBitmapCommon::WriteLineOR() called from CDrawBitmap::WriteLine()
       
   448 //aX and aY - physical coordinates
       
   449 //One possible optimization: If "no scaling" And "pixelPtrInc == 1" Then
       
   450 //OR could be made on 32 bits words (they  has to be aligned before the operation)
       
   451 void CDrawEightBppBitmapCommon::WriteLineOR(TInt aX,TInt aY,TInt aLength,TUint32* aBuffer)
       
   452 	{
       
   453 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   454 	register TInt pixelPtrInc = LogicalPixelAddressIncrement();
       
   455 	TUint8* bufferPtr = reinterpret_cast <TUint8*> (aBuffer);
       
   456 	const TUint8* bufferPtrLimit = bufferPtr + aLength;
       
   457 	if(iScalingOff)
       
   458 		{
       
   459 		while(bufferPtr < bufferPtrLimit)
       
   460 			{
       
   461 			*pixelPtr |= *bufferPtr++;
       
   462 			pixelPtr += pixelPtrInc;
       
   463 			}
       
   464 		}
       
   465 	else
       
   466 		{
       
   467 		const TUint8* bitsStart = reinterpret_cast <const TUint8*> (iBits);
       
   468 		const TUint8* bitsEnd = bitsStart + iLongWidth * iSize.iHeight;
       
   469 		while(bufferPtr < bufferPtrLimit)
       
   470 			{
       
   471 			const TUint8* pixelRowPtrLimit = bitsStart + (aY + 1) * iLongWidth;
       
   472 			ORPixels(pixelPtr, *bufferPtr++, pixelRowPtrLimit, bitsStart, bitsEnd);
       
   473 			pixelPtr += pixelPtrInc;
       
   474 			IncScaledY(aY);
       
   475 			}
       
   476 		}
       
   477 	}
       
   478 
       
   479 //CDrawEightBppBitmapCommon::WriteRgbMulti() called from CDrawBitmap::WriteRgbMulti()
       
   480 //aX and aY - physical coordinates
       
   481 //aLength and aRows - physical length and rows
       
   482 void CDrawEightBppBitmapCommon::WriteRgbMulti(TInt aX,TInt aY,TInt aLength,TInt aRows,
       
   483 											  TUint8 aPixel)
       
   484 	{
       
   485 	register TInt longWidth = iLongWidth;
       
   486 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   487 	const TUint8* pixelRowPtrLimit = pixelPtr + aRows * longWidth;
       
   488 	register const TUint8* bitsEnd = reinterpret_cast <const TUint8*> (iBits) + iLongWidth * iSize.iHeight;
       
   489 	if(pixelRowPtrLimit >= bitsEnd)
       
   490 		{
       
   491 		pixelRowPtrLimit = bitsEnd;
       
   492 		}
       
   493 
       
   494 	while (pixelPtr < pixelRowPtrLimit)
       
   495 		{
       
   496 		Mem::Fill(pixelPtr,aLength,aPixel);
       
   497 		pixelPtr += longWidth;
       
   498 		}
       
   499 	}
       
   500 
       
   501 //CDrawEightBppBitmapCommon::WriteRgbMultiXOR() called from CDrawBitmap::WriteRgbMulti()
       
   502 //aX and aY - physical coordinates
       
   503 //aLength and aRows - physical length and rows
       
   504 void CDrawEightBppBitmapCommon::WriteRgbMultiXOR(TInt aX,TInt aY,TInt aLength,TInt aRows,
       
   505 												 TUint8 aPixel)
       
   506 	{
       
   507 	register TInt longWidth = iLongWidth;
       
   508 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   509 	TUint8* pixelPtrLimit = pixelPtr + aLength;
       
   510 	const TUint8* pixelRowPtrLimit = pixelPtr + aRows * longWidth;
       
   511 	register const TUint8* bitsEnd = reinterpret_cast <const TUint8*> (iBits) + iLongWidth * iSize.iHeight;
       
   512 	if(pixelRowPtrLimit >= bitsEnd)
       
   513 		{
       
   514 		pixelRowPtrLimit = bitsEnd;
       
   515 		}
       
   516 
       
   517 	while (pixelPtr < pixelRowPtrLimit)
       
   518 		{
       
   519 		TUint8* tempPixelPtr = pixelPtr;
       
   520 
       
   521 		while (tempPixelPtr < pixelPtrLimit)
       
   522 			*tempPixelPtr++ ^= aPixel;
       
   523 
       
   524 		pixelPtr += longWidth;
       
   525 		pixelPtrLimit += longWidth;
       
   526 		}
       
   527 	}
       
   528 
       
   529 //CDrawEightBppBitmapCommon::WriteRgbMultiAND() called from CDrawBitmap::WriteRgbMulti()
       
   530 //aX and aY - physical coordinates
       
   531 //aLength and aRows - physical length and rows
       
   532 void CDrawEightBppBitmapCommon::WriteRgbMultiAND(TInt aX,TInt aY,TInt aLength,TInt aRows,
       
   533 												 TUint8 aPixel)
       
   534 	{
       
   535 	register TInt longWidth = iLongWidth;
       
   536 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   537 	const TUint8* pixelPtrLimit = pixelPtr + aLength;
       
   538 	const TUint8* pixelRowPtrLimit = pixelPtr + aRows * longWidth;
       
   539 	register const TUint8* bitsEnd = reinterpret_cast <const TUint8*> (iBits) + iLongWidth * iSize.iHeight;
       
   540 	if(pixelRowPtrLimit >= bitsEnd)
       
   541 		{
       
   542 		pixelRowPtrLimit = bitsEnd;
       
   543 		}
       
   544 
       
   545 	while (pixelPtr < pixelRowPtrLimit)
       
   546 		{
       
   547 		TUint8* tempPixelPtr = pixelPtr;
       
   548 
       
   549 		while (tempPixelPtr < pixelPtrLimit)
       
   550 			*tempPixelPtr++ &= aPixel;
       
   551 
       
   552 		pixelPtr += longWidth;
       
   553 		pixelPtrLimit += longWidth;
       
   554 		}
       
   555 	}
       
   556 
       
   557 //CDrawEightBppBitmapCommon::WriteRgbMultiOR() called from CDrawBitmap::WriteRgbMulti()
       
   558 //aX and aY - physical coordinates
       
   559 //aLength and aRows - physical length and rows
       
   560 void CDrawEightBppBitmapCommon::WriteRgbMultiOR(TInt aX,TInt aY,TInt aLength,TInt aRows,TUint8 aPixel)
       
   561 	{
       
   562 	register TInt longWidth = iLongWidth;
       
   563 	TUint8* pixelPtr = PixelAddress(aX,aY);
       
   564 	TUint8* pixelPtrLimit = pixelPtr + aLength;
       
   565 	const TUint8* pixelRowPtrLimit = pixelPtr + aRows * longWidth;
       
   566 	register const TUint8* bitsEnd = reinterpret_cast <const TUint8*> (iBits) + iLongWidth * iSize.iHeight;
       
   567 	if(pixelRowPtrLimit >= bitsEnd)
       
   568 		{
       
   569 		pixelRowPtrLimit = bitsEnd;
       
   570 		}
       
   571 
       
   572 	while (pixelPtr < pixelRowPtrLimit)
       
   573 		{
       
   574 		TUint8* tempPixelPtr = pixelPtr;
       
   575 
       
   576 		while (tempPixelPtr < pixelPtrLimit)
       
   577 			*tempPixelPtr++ |= aPixel;
       
   578 
       
   579 		pixelPtr += longWidth;
       
   580 		pixelPtrLimit += longWidth;
       
   581 		}
       
   582 	}
       
   583 
       
   584 /**
       
   585 Implementation for CFbsDrawDevice::GetInterface().
       
   586 Retrieves a pointer to a specified interface of CFbsDrawDevice implementation.
       
   587 @param aInterfaceId Interface identifier of the interface to be retrieved.
       
   588 @param aInterface Address of variable that retrieves the specified interface.
       
   589 @return KErrNone If the interface is supported, KErrNotSupported otherwise.
       
   590 */
       
   591 
       
   592 TInt CDrawEightBppBitmapCommon::GetInterface(TInt aInterfaceId, TAny*& aInterface)
       
   593 	{
       
   594 	aInterface = NULL;
       
   595 	TInt ret = KErrNotSupported;
       
   596 	
       
   597 	if (aInterfaceId == KFastBlit2InterfaceID)
       
   598 		{
       
   599 		aInterface = static_cast<MFastBlit2*>(this);
       
   600 		ret = KErrNone;
       
   601 		}
       
   602 	else 
       
   603 		return CDrawBitmap::GetInterface(aInterfaceId, aInterface);
       
   604 		
       
   605 	return ret;
       
   606 	}
       
   607 
       
   608 /**
       
   609 CDrawEightBppBitmapCommon::WriteBitmapBlock() implementation.
       
   610 @internalTechnology
       
   611 @see MFastBlit2::WriteBitmapBlock()
       
   612 */
       
   613 TInt CDrawEightBppBitmapCommon::WriteBitmapBlock(const TPoint& aDest,
       
   614 									CFbsDrawDevice* aSrcDrawDevice,
       
   615 									const TRect& aSrcRect)
       
   616 	{
       
   617 	__ASSERT_DEBUG(aSrcDrawDevice && ((aSrcDrawDevice->DisplayMode()==EColor256) || (aSrcDrawDevice->DisplayMode()==EGray256)), Panic(EScreenDriverPanicInvalidParameter));
       
   618 	
       
   619 	TAny* interface=NULL;
       
   620 	TInt ret = aSrcDrawDevice->GetInterface(KFastBlit2InterfaceID, interface);
       
   621 	if (ret != KErrNone)
       
   622 		{
       
   623 		return KErrNotSupported;
       
   624 		}
       
   625 
       
   626 	TAny* interface1=NULL;
       
   627 	ret = aSrcDrawDevice->GetInterface(KScalingSettingsInterfaceID, interface1);
       
   628 	if(ret != KErrNone || (interface1 && !reinterpret_cast<MScalingSettings*>(interface1)->IsScalingOff()))
       
   629 		{
       
   630 		return KErrNotSupported;
       
   631 		}
       
   632 
       
   633 	ret = aSrcDrawDevice->GetInterface(KOrientationInterfaceID, interface1);
       
   634 	if(ret != KErrNone || (interface1 && reinterpret_cast<MDrawDeviceOrientation*>(interface1)->Orientation() != 0))
       
   635 		{
       
   636 		return KErrNotSupported;
       
   637 		}
       
   638 
       
   639 	ret = aSrcDrawDevice->GetInterface(KDrawDeviceOriginInterfaceID, interface1);
       
   640 	if(ret != KErrNone)
       
   641 		{
       
   642 		return KErrNotSupported;
       
   643 		}
       
   644 	
       
   645 	if(interface1)
       
   646 		{
       
   647 	 	TPoint pt;
       
   648 	 	reinterpret_cast<MDrawDeviceOrigin*>(interface1)->Get(pt);
       
   649 	 	if(pt.iX != 0 || pt.iY != 0)
       
   650 	 		{
       
   651 			return KErrNotSupported;
       
   652 	 		}
       
   653 		}
       
   654 
       
   655 	const TUint32* srcBase = reinterpret_cast<MFastBlit2*>(interface)->Bits();
       
   656 	__ASSERT_DEBUG(srcBase!=NULL, Panic(EScreenDriverPanicInvalidParameter));
       
   657 	TInt srcStride = aSrcDrawDevice->ScanLineBytes();  
       
   658 	__ASSERT_DEBUG((srcStride&3)==0, Panic(EScreenDriverPanicInvalidParameter));  // stride is assumed to be a multiple of 4
       
   659 	TSize srcSize = aSrcDrawDevice->SizeInPixels();
       
   660 
       
   661 	return WriteBitmapBlock(aDest, srcBase, srcStride, srcSize, aSrcRect);
       
   662 	}
       
   663 
       
   664 								
       
   665 /**
       
   666 CDrawEightBppBitmapCommon::WriteBitmapBlock() implementation.
       
   667 @internalTechnology
       
   668 @see MFastBlit2::WriteBitmapBlock()
       
   669 */													
       
   670 TInt CDrawEightBppBitmapCommon::WriteBitmapBlock(const TPoint& aDest,
       
   671 									const TUint32* aSrcBase,
       
   672 									TInt aSrcStride,
       
   673 									const TSize& aSrcSize,
       
   674 									const TRect& aSrcRect)
       
   675 	{
       
   676 	__ASSERT_DEBUG(aSrcBase, Panic(EScreenDriverPanicInvalidParameter));
       
   677 	__ASSERT_DEBUG((aSrcStride&3)==0, Panic(EScreenDriverPanicInvalidParameter));
       
   678 	__ASSERT_DEBUG(iBits, Panic(EScreenDriverPanicInvalidPointer));
       
   679 
       
   680 	if (iShadowMode!=NULL ||
       
   681     	(iUserDispMode!=NULL && iUserDispMode!=iDispMode) ||
       
   682     	iOrientation!=EOrientationNormal ||
       
   683 		!IsScalingOff() ||
       
   684 		!iOriginIsZero)
       
   685 		{
       
   686 		return KErrNotSupported;
       
   687 		}
       
   688 	
       
   689 	__ASSERT_DEBUG(aSrcRect.iTl.iX >= 0, Panic(EScreenDriverPanicOutOfBounds)); 
       
   690 	__ASSERT_DEBUG(aSrcRect.iTl.iY >= 0, Panic(EScreenDriverPanicOutOfBounds));
       
   691 	__ASSERT_DEBUG(aSrcRect.iBr.iX <= aSrcSize.iWidth,  Panic(EScreenDriverPanicOutOfBounds));
       
   692 	__ASSERT_DEBUG(aSrcRect.iBr.iY <= aSrcSize.iHeight, Panic(EScreenDriverPanicOutOfBounds));
       
   693 	__ASSERT_DEBUG(aDest.iX >= 0, Panic(EScreenDriverPanicOutOfBounds));
       
   694 	__ASSERT_DEBUG(aDest.iY >= 0, Panic(EScreenDriverPanicOutOfBounds));
       
   695 	__ASSERT_DEBUG((aDest.iX + aSrcRect.Width())  <= SizeInPixels().iWidth,  Panic(EScreenDriverPanicOutOfBounds));
       
   696 	__ASSERT_DEBUG((aDest.iY + aSrcRect.Height()) <= SizeInPixels().iHeight, Panic(EScreenDriverPanicOutOfBounds));
       
   697 	
       
   698 	const TInt srcStride8 = aSrcStride;
       
   699 	const TInt dstStride8 = iScanLineWords << 2;
       
   700 	
       
   701 	if (aSrcSize.iWidth == aSrcRect.Width() &&
       
   702 		aSrcSize.iWidth == SizeInPixels().iWidth &&
       
   703 		srcStride8 == dstStride8)
       
   704 		{
       
   705 		// Optimum case - one memcpy
       
   706 		__ASSERT_DEBUG(aSrcRect.iTl.iX==0 && aDest.iX==0, Panic(EScreenDriverPanicInvalidParameter));  // this is implied by the above conditions
       
   707 		const TUint32* srcPtr = aSrcBase + (iScanLineWords * aSrcRect.iTl.iY);
       
   708 		TUint32* dstPtr       = iBits    + (iScanLineWords * aDest.iY);
       
   709 		const TInt length = aSrcStride * aSrcRect.Height();
       
   710 		Mem::Move(dstPtr, srcPtr, length);
       
   711 		return KErrNone;
       
   712 		}
       
   713 		
       
   714 	// Sub-optimal case - one memcpy per line
       
   715 	const TUint8* srcPtr = (TUint8*)aSrcBase + (srcStride8 * aSrcRect.iTl.iY) + aSrcRect.iTl.iX;
       
   716 	TUint8* dstPtr       = (TUint8*)iBits    + (dstStride8 * aDest.iY       ) + aDest.iX;
       
   717 	const TInt length = aSrcRect.Width();
       
   718 	TInt lines = aSrcRect.Height();
       
   719 	while (lines--)
       
   720 		{
       
   721 		Mem::Copy(dstPtr, srcPtr, length);
       
   722 		srcPtr += srcStride8;
       
   723 		dstPtr += dstStride8;
       
   724 		}
       
   725 	return KErrNone;
       
   726 	}
       
   727 
       
   728 
       
   729 /**
       
   730 CDrawEightBppBitmapCommon::Bits() implementation.
       
   731 @internalTechnology
       
   732 @see MFastBlit2::Bits()
       
   733 */
       
   734 const TUint32* CDrawEightBppBitmapCommon::Bits() const
       
   735 	{
       
   736 	return iBits;
       
   737 }