os/graphics/graphicscomposition/openwfcompositionengine/test/tscreeninterface/streamutility.cpp
Update contrib.
1 // Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
3 // Permission is hereby granted, free of charge, to any person obtaining a
4 // copy of this software and/or associated documentation files (the
5 // "Materials"), to deal in the Materials without restriction, including
6 // without limitation the rights to use, copy, modify, merge, publish,
7 // distribute, sublicense, and/or sell copies of the Materials, and to
8 // permit persons to whom the Materials are furnished to do so, subject to
9 // the following conditions:
11 // The above copyright notice and this permission notice shall be included
12 // in all copies or substantial portions of the Materials.
14 // THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
17 // IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
18 // CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
19 // TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
20 // MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
30 #include <imageconversion.h>
31 #include <graphics/symbianstream.h>
32 #include "streamutility.h"
34 #define WFC_INVALID_HANDLE NULL
36 CStreamUtility::CStreamUtility()
40 CStreamUtility* CStreamUtility::NewL()
42 CStreamUtility* utility = new (ELeave)CStreamUtility();
43 CleanupStack::PushL(utility);
44 utility->ConstructL();
45 CleanupStack::Pop(utility);
49 void CStreamUtility::ConstructL()
51 TInt r = iManager.Open();
54 LOG(("Surface manager failed to open: %d", r));
59 CStreamUtility::~CStreamUtility()
68 TBool CStreamUtility::DestroyAll()
71 TInt jj = iStreams.Count() - 1;
76 //The following lines are just to get the surface ID for verification
77 SymbianStreamBuffer bufferHandle;
78 User::LeaveIfError(SymbianStreamAcquireReadBuffer(iStreams[jj], &bufferHandle));
80 const TSurfaceId* pSurfaceId = NULL;
82 User::LeaveIfError(SymbianStreamGetBufferId(iStreams[jj],bufferHandle,&bufferIndex,&pSurfaceId));
83 User::LeaveIfError(SymbianStreamReleaseReadBuffer(iStreams[jj], bufferHandle));
85 const TSurfaceId surfaceId = *pSurfaceId; //Need to copy my reference to the ID.
86 //Actually release the stream
87 SymbianStreamRemoveReference(iStreams[jj]);
89 //Verify the stream is now not accessible
91 err = iManager.GetBufferOffset(surfaceId,0,offset);
94 LOG(("Closing stream via DestoryAll did not destroy surface!"));
101 /***************************************
102 * The aim of the RHeapStreamArray is to locally switch in the specified heap for any array operation
103 ***************************************/
105 CStreamUtility::RHeapStreamArray::RHeapStreamArray(RHeapStreamArray* aUseExternalArray)
106 : iUseArray(aUseExternalArray?aUseExternalArray->iUseArray:&this->iLocalArray),
107 iExternalHeapRef(aUseExternalArray?aUseExternalArray->iExternalHeapRef:User::Heap())
111 /************************************
112 * The following methods have been used by the streamutility... some require the heap wrapping, and some don't
113 * I actually need three different strategies (count em) for 7 methods...
114 * Some methods only read the existing objects, so don't need a heap swap at all
115 * Leaving methods have to use PopAndDestroy strategy to restore the heap on leaving or success
116 * Non-leaving methods must not call PushL, so directly make SwitchHeap calls!
117 ************************************/
119 /// PopAndDestroy method to restore the heap
120 /*static*/ void CStreamUtility::RHeapStreamArray::PopHeap(void* aHeapPtr)
122 RHeap* heapPtr=(RHeap*)aHeapPtr;
123 User::SwitchHeap(heapPtr);
126 SymbianStreamType& CStreamUtility::RHeapStreamArray::operator[](TUint aIndex)
128 return iUseArray->operator[](aIndex);
131 /// Close only closes the local array, while Reset resets the active array (may be external)
132 void CStreamUtility::RHeapStreamArray::Close()
137 TInt CStreamUtility::RHeapStreamArray::Count() const
139 return iUseArray->Count();
142 /// Close only closes the local array, while Reset resets the active array (may be external)
143 inline void CStreamUtility::RHeapStreamArray::Reset()
148 void CStreamUtility::RHeapStreamArray::AppendL(const SymbianStreamType &anEntry)
150 iUseArray->AppendL(anEntry);
153 TInt CStreamUtility::RHeapStreamArray::Find(const SymbianStreamType &anEntry) const
155 return iUseArray->Find(anEntry);
158 void CStreamUtility::RHeapStreamArray::Remove(TInt anIndex)
160 iUseArray->Remove(anIndex);
164 Cleanup stack helper object, holding references to both utility and stream, so
165 that the standard Close() semantics can be used.
170 TStreamCleanup(CStreamUtility& aUtility, SymbianStreamType& aStream)
171 : iUtility(aUtility), iStream(aStream)
175 // Removes the stream from the list of streams to clean up, and closes
176 // the stream reference.
177 iUtility.DestroyStream(iStream);
180 CStreamUtility& iUtility;
181 SymbianStreamType& iStream;
185 Get the size of a stream.
187 @param aStream The stream to get the size for.
188 @return The size in pixels, or empty on failure.
190 TSize CStreamUtility::StreamSize(const SymbianStreamType aStream)
192 khronos_int32_t width;
193 khronos_int32_t height;
194 khronos_int32_t stride;
195 khronos_int32_t format;
196 khronos_int32_t pixelSize;
198 SymbianStreamGetHeader(aStream, &width, &height, &stride, &format, &pixelSize);
200 TSize size = TSize(static_cast<TInt>(width), static_cast<TInt>(height));
206 Create a stream using the surface manager.
208 Stores the ID for tear down, as well as returning it.
210 @param aSize Dimensions of the stream.
211 @param aPixelFormat UID of the pixel format.
212 @param aStride Stride value for the stream (usually bytes per pixel * width)
213 @param aReturnSurface Returns TSurfaceId wrapped by the stream
214 @param aContiguous Contiguous flag for creating surfaces
215 @param aBuffers Number of buffers
216 @leave May leave due to lack of memory.
217 @return New stream's ID.
219 SymbianStreamType CStreamUtility::CreateStreamL(const TSize& aSize, TUidPixelFormat aPixelFormat,
220 TInt aStride, TSurfaceId& aReturnSurface,
221 TBool aContiguous, TInt aBuffers)
223 RSurfaceManager::TSurfaceCreationAttributesBuf bf;
224 RSurfaceManager::TSurfaceCreationAttributes& b = bf();
225 if (aStride<aSize.iWidth*BytesPerPixelL(aPixelFormat))
227 User::Leave(KErrOverflow);
229 b.iSize.iWidth = aSize.iWidth;
230 b.iSize.iHeight = aSize.iHeight;
231 b.iBuffers = aBuffers; // number of buffers in the surface
232 b.iPixelFormat = aPixelFormat;
233 b.iStride = aStride; // Number of bytes between start of one line and start of next
234 b.iOffsetToFirstBuffer = 0; // way of reserving space before the surface pixel data
235 b.iAlignment = 4; // alignment, 1,2,4,8 byte aligned
236 b.iContiguous = !!aContiguous;
239 aReturnSurface = TSurfaceId::CreateNullId();
241 User::LeaveIfError(iManager.CreateSurface(bf, aReturnSurface));
243 SymbianStreamType ns;
244 TInt err = SymbianStreamAcquire(&aReturnSurface, &ns);
245 iManager.CloseSurface(aReturnSurface); //The stream should now own the only reference
250 iStreams.AppendL(ns);
255 Fill the given stream with a color.
257 @param aStream The stream to be filled.
258 @param aColor The color to fill it with.
260 void CStreamUtility::FillStreamL(SymbianStreamType aStream, const TRgb& aColor)
263 khronos_int32_t width;
264 khronos_int32_t height;
265 khronos_int32_t stride;
266 khronos_int32_t format;
267 khronos_int32_t pixelSize;
269 SymbianStreamGetHeader(aStream, &width, &height, &stride, &format, &pixelSize);
272 TBool use16 = EFalse;
274 if (height<0 || width<0 || stride<0)
276 User::Leave(KErrCorrupt);
278 if (height==0 || width==0 || stride==0)
280 User::Leave(KErrNotReady);
285 case EUidPixelFormatXRGB_8888:
287 color = aColor.Color16MU();
290 case EUidPixelFormatARGB_8888:
292 color = aColor.Color16MA();
295 case EUidPixelFormatARGB_8888_PRE:
297 color = aColor.Color16MAP();
300 case EUidPixelFormatXRGB_4444:
301 case EUidPixelFormatARGB_4444:
303 color = aColor.Color4K();
307 case EUidPixelFormatRGB_565:
309 color = aColor.Color64K();
315 User::Leave(KErrNotSupported);
320 SymbianStreamBuffer bufferHandle;
321 User::LeaveIfError(SymbianStreamAcquireWriteBuffer(aStream, &bufferHandle));
323 const TSurfaceId* surfaceId = NULL;
324 User::LeaveIfError(SymbianStreamGetBufferId(aStream,bufferHandle,&bufferIndex,&surfaceId));
327 User::LeaveIfError(iManager.MapSurface(*surfaceId, chunk));
328 CleanupClosePushL(chunk);
330 TInt offsetToFirstBuffer;
331 User::LeaveIfError(iManager.GetBufferOffset(*surfaceId, 0, offsetToFirstBuffer));
332 TUint8* streamPtr = chunk.Base() + offsetToFirstBuffer;
333 TUint8* linePtr = streamPtr;
339 User::Leave(KErrOverflow);
341 TUint16* ptr = reinterpret_cast<TUint16*>(streamPtr);
344 for (TInt xx = 0; xx < width; xx++)
346 ptr[xx] = (TUint16)color;
353 User::Leave(KErrOverflow);
355 TUint32* ptr = reinterpret_cast<TUint32*>(streamPtr);
358 for (TInt xx = 0; xx < width; xx++)
364 // Now copy that to the other lines
365 for (TInt yy = 1; yy < height; yy++)
368 Mem::Copy(linePtr, streamPtr, width * BytesPerPixelL(aStream));
370 User::LeaveIfError(SymbianStreamReleaseWriteBuffer(aStream, bufferHandle));
371 CleanupStack::PopAndDestroy(/* chunk */);
377 As well as destroying the stream, it is removed from the set held for
378 destruction during tear down.
380 @param aStream The stream to be destroyed.
382 void CStreamUtility::DestroyStream(SymbianStreamType aStream)
384 TInt index = iStreams.Find(aStream);
386 if (index != KErrNotFound)
388 iStreams.Remove(index);
391 SymbianStreamRemoveReference(aStream);
395 A helper function that returns the bytes per pixel for a given pixel format uid
397 @param aPixelFormat Pixel format UID to convert
398 @return The bytes per pixel
400 TInt CStreamUtility::BytesPerPixelL(TUidPixelFormat aPixelFormat)
402 TInt bytesPerPixel = 0;
403 switch (aPixelFormat)
405 case EUidPixelFormatXRGB_8888:
406 case EUidPixelFormatARGB_8888:
407 case EUidPixelFormatARGB_8888_PRE:
412 case EUidPixelFormatXRGB_4444:
413 case EUidPixelFormatARGB_4444:
414 case EUidPixelFormatRGB_565:
421 User::Leave(KErrNotSupported);
425 return bytesPerPixel;
429 A helper function that returns the bytes per pixel for a given stream
431 @param aStream The stream which is checked
432 @return The bytes per pixel
434 TInt CStreamUtility::BytesPerPixelL(const SymbianStreamType aStream)
436 khronos_int32_t width;
437 khronos_int32_t height;
438 khronos_int32_t stride;
439 khronos_int32_t format;
440 khronos_int32_t pixelSize;
442 SymbianStreamGetHeader(aStream, &width, &height, &stride, &format, &pixelSize);
444 return static_cast<TInt>(pixelSize);