os/graphics/graphicscomposition/surfaceupdate/tsrc/tsurfacehelper.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) 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 "tsurfacehelper.h"
sl@0
    17
#include <w32std.h>
sl@0
    18
sl@0
    19
CSurfaceHelper* CSurfaceHelper::NewL()
sl@0
    20
	{
sl@0
    21
	CSurfaceHelper* helper = new(ELeave)CSurfaceHelper;
sl@0
    22
	CleanupStack::PushL(helper);
sl@0
    23
	helper->ConstructL();
sl@0
    24
	CleanupStack::Pop(helper);
sl@0
    25
	return helper;
sl@0
    26
	}
sl@0
    27
sl@0
    28
CSurfaceHelper::~CSurfaceHelper()
sl@0
    29
	{
sl@0
    30
	DestroySurfaces();
sl@0
    31
	iSurfaces.Close();
sl@0
    32
	iManager.Close();
sl@0
    33
	}
sl@0
    34
sl@0
    35
/**
sl@0
    36
 * Load logical device and open a surface manager
sl@0
    37
 */
sl@0
    38
void CSurfaceHelper::ConstructL()
sl@0
    39
	{
sl@0
    40
	TInt res = iManager.Open();
sl@0
    41
	if (res != KErrNone)
sl@0
    42
		{
sl@0
    43
		User::Leave(res);
sl@0
    44
		}
sl@0
    45
	}
sl@0
    46
sl@0
    47
/**
sl@0
    48
 * Create the surface with the given parameters.
sl@0
    49
 * The surface will be owned by the instance of this class  
sl@0
    50
 */
sl@0
    51
TSurfaceId CSurfaceHelper::CreateSurfaceL(const TSize& aSize, TUidPixelFormat aPixelFormat, TInt aStride, TInt aBuffers)
sl@0
    52
	{
sl@0
    53
	RSurfaceManager::TSurfaceCreationAttributesBuf bf;
sl@0
    54
	RSurfaceManager::TSurfaceCreationAttributes& b = bf();
sl@0
    55
	
sl@0
    56
	b.iSize.iWidth = aSize.iWidth;
sl@0
    57
	b.iSize.iHeight = aSize.iHeight;
sl@0
    58
	b.iBuffers = aBuffers;				// number of buffers in the surface
sl@0
    59
	b.iPixelFormat = aPixelFormat;
sl@0
    60
	b.iStride = aStride;		// Number of bytes between start of one line and start of next
sl@0
    61
	b.iOffsetToFirstBuffer = 0;	// way of reserving space before the surface pixel data
sl@0
    62
	b.iAlignment = 4;			// alignment, 1,2,4,8 byte aligned
sl@0
    63
	b.iContiguous = EFalse;
sl@0
    64
	b.iMappable = ETrue;
sl@0
    65
sl@0
    66
	TSurfaceId surface = TSurfaceId::CreateNullId();
sl@0
    67
sl@0
    68
	User::LeaveIfError(iManager.CreateSurface(bf, surface));
sl@0
    69
	iSurfaces.AppendL(surface);
sl@0
    70
	return surface;
sl@0
    71
	}
sl@0
    72
sl@0
    73
/**
sl@0
    74
 * Destroy all surfaces wich have been created by the instance of this class
sl@0
    75
 */
sl@0
    76
void CSurfaceHelper::DestroySurfaces()
sl@0
    77
	{
sl@0
    78
	TInt numSurfaces = iSurfaces.Count();
sl@0
    79
	for (TInt index = 0; index < numSurfaces; index++)
sl@0
    80
		{
sl@0
    81
		TSurfaceId surfaceId = iSurfaces[index];
sl@0
    82
		TInt err = iManager.CloseSurface(surfaceId);
sl@0
    83
		__ASSERT_DEBUG(err ==KErrNone, User::Panic(_L("CSurfaceHelper::DestroySurfaces"), err));
sl@0
    84
		}
sl@0
    85
	iSurfaces.Reset();
sl@0
    86
	}
sl@0
    87
sl@0
    88
/**
sl@0
    89
Fill a rectangle on the given surface.
sl@0
    90
sl@0
    91
@param aSurface		The surface to be filled.
sl@0
    92
@param aStartPos	Where to place the rectangle.
sl@0
    93
@param aSize		Size of the rectangle.
sl@0
    94
@param aColor		The colour to fill it with.
sl@0
    95
*/
sl@0
    96
void CSurfaceHelper::FillRectangleL(const TSurfaceId& aSurface, const TPoint& aStartPos, const TSize& aSize, const TRgb& aColor)
sl@0
    97
	{
sl@0
    98
	RSurfaceManager::TInfoBuf infoBuf;
sl@0
    99
	RSurfaceManager::TSurfaceInfoV01& info = infoBuf();
sl@0
   100
	User::LeaveIfError(iManager.SurfaceInfo(aSurface, infoBuf));
sl@0
   101
	TUint32 color = 0;
sl@0
   102
sl@0
   103
	if (info.iSize.iHeight<0 || info.iSize.iWidth<0 || info.iStride<0)
sl@0
   104
		{
sl@0
   105
		User::Leave(KErrCorrupt);
sl@0
   106
		}
sl@0
   107
	if (info.iSize.iHeight==0 || info.iSize.iWidth==0 || info.iStride==0)
sl@0
   108
		{
sl@0
   109
		User::Leave(KErrNotReady);
sl@0
   110
		}
sl@0
   111
sl@0
   112
	switch (info.iPixelFormat)
sl@0
   113
		{
sl@0
   114
		case EUidPixelFormatXRGB_8888:
sl@0
   115
			{
sl@0
   116
			color = aColor.Color16MU();
sl@0
   117
#ifdef ALPHA_FIX_24BIT
sl@0
   118
			color |= ((ALPHA_FIX_24BIT)&0xff)<<24;
sl@0
   119
#endif
sl@0
   120
			break;
sl@0
   121
			}
sl@0
   122
		case EUidPixelFormatARGB_8888:
sl@0
   123
			{
sl@0
   124
			color = aColor.Color16MA();
sl@0
   125
			break;
sl@0
   126
			}
sl@0
   127
		case EUidPixelFormatARGB_8888_PRE:
sl@0
   128
			{
sl@0
   129
			color = aColor.Color16MAP();
sl@0
   130
			break;
sl@0
   131
			}
sl@0
   132
		case EUidPixelFormatRGB_565:
sl@0
   133
			{
sl@0
   134
			color = aColor.Color64K();
sl@0
   135
			break;
sl@0
   136
			}
sl@0
   137
		default:
sl@0
   138
			{
sl@0
   139
			User::Leave(KErrNotSupported);
sl@0
   140
			break;
sl@0
   141
			}
sl@0
   142
		}
sl@0
   143
sl@0
   144
	RChunk chunk;
sl@0
   145
	User::LeaveIfError(iManager.MapSurface(aSurface, chunk));
sl@0
   146
	CleanupClosePushL(chunk);
sl@0
   147
	TUint8* surfacePtr = chunk.Base();
sl@0
   148
	
sl@0
   149
	// Check for out of bounds
sl@0
   150
	TBool validRect = ETrue;
sl@0
   151
	TInt surfaceWidth = info.iSize.iWidth;
sl@0
   152
	TInt surfaceHeight = info.iSize.iHeight;
sl@0
   153
	
sl@0
   154
	// Width and Height
sl@0
   155
	if ((aStartPos.iX + aSize.iWidth) > surfaceWidth)
sl@0
   156
		{
sl@0
   157
		validRect = EFalse;
sl@0
   158
		}
sl@0
   159
	
sl@0
   160
	if ((aStartPos.iY + aSize.iHeight) > surfaceHeight)
sl@0
   161
		{
sl@0
   162
		validRect = EFalse;
sl@0
   163
		}
sl@0
   164
	
sl@0
   165
	// Starting position
sl@0
   166
	if ((aStartPos.iX < 0) || (aStartPos.iY < 0))
sl@0
   167
		{
sl@0
   168
		validRect = EFalse;
sl@0
   169
		}
sl@0
   170
	
sl@0
   171
	if (!validRect)
sl@0
   172
		{
sl@0
   173
		User::Leave(KErrOverflow);
sl@0
   174
		}
sl@0
   175
		
sl@0
   176
	if (info.iPixelFormat == EUidPixelFormatRGB_565)
sl@0
   177
		{//2 bytes per pixel
sl@0
   178
		if ( info.iSize.iWidth*2>info.iStride)
sl@0
   179
			{
sl@0
   180
			User::Leave(KErrOverflow);
sl@0
   181
			}
sl@0
   182
		
sl@0
   183
		TInt offset;
sl@0
   184
		User::LeaveIfError(iManager.GetBufferOffset(aSurface, 0, offset));
sl@0
   185
		TUint16* ptr = reinterpret_cast<TUint16*>(surfacePtr + offset);
sl@0
   186
		
sl@0
   187
		// Fill the rectangle
sl@0
   188
		TInt yPos = aStartPos.iY;
sl@0
   189
		TInt xPos = aStartPos.iX;
sl@0
   190
		for (TInt yy = 0; yy < aSize.iHeight; ++yy)
sl@0
   191
			{
sl@0
   192
			ptr = reinterpret_cast<TUint16*>(surfacePtr + (yPos*info.iStride));
sl@0
   193
			for (TInt xx = 0; xx < aSize.iWidth; ++xx)
sl@0
   194
				{
sl@0
   195
				ptr[xPos] = color;
sl@0
   196
				xPos++;
sl@0
   197
				}
sl@0
   198
			xPos = aStartPos.iX;
sl@0
   199
			yPos++;
sl@0
   200
			}
sl@0
   201
		}
sl@0
   202
	else
sl@0
   203
		{
sl@0
   204
		if ( info.iSize.iWidth*4>info.iStride)
sl@0
   205
			{
sl@0
   206
			User::Leave(KErrOverflow);
sl@0
   207
			}
sl@0
   208
sl@0
   209
		TInt offset;
sl@0
   210
		User::LeaveIfError(iManager.GetBufferOffset(aSurface, 0, offset));
sl@0
   211
		TUint32* ptr = reinterpret_cast<TUint32*>(surfacePtr + offset);		
sl@0
   212
		
sl@0
   213
		// Fill the rectangle
sl@0
   214
		TInt yPos = aStartPos.iY;
sl@0
   215
		TInt xPos = aStartPos.iX;
sl@0
   216
		for (TInt yy = 0; yy < aSize.iHeight; ++yy)
sl@0
   217
			{
sl@0
   218
			ptr = reinterpret_cast<TUint32*>(surfacePtr+(yPos*info.iStride));
sl@0
   219
			for (TInt xx = 0; xx < aSize.iWidth; ++xx)
sl@0
   220
				{
sl@0
   221
				ptr[xPos] = color;
sl@0
   222
				xPos++;
sl@0
   223
				}
sl@0
   224
			xPos = aStartPos.iX;
sl@0
   225
			yPos++;
sl@0
   226
			}
sl@0
   227
		}
sl@0
   228
	CleanupStack::PopAndDestroy(&chunk);
sl@0
   229
	}