1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/os/graphics/windowing/windowserverplugins/openwfc/src/rendertarget.cpp Fri Jun 15 03:10:57 2012 +0200
1.3 @@ -0,0 +1,412 @@
1.4 +// Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies).
1.5 +// All rights reserved.
1.6 +// This component and the accompanying materials are made available
1.7 +// under the terms of "Eclipse Public License v1.0"
1.8 +// which accompanies this distribution, and is available
1.9 +// at the URL "http://www.eclipse.org/legal/epl-v10.html".
1.10 +//
1.11 +// Initial Contributors:
1.12 +// Nokia Corporation - initial contribution.
1.13 +//
1.14 +// Contributors:
1.15 +//
1.16 +// Description:
1.17 +//
1.18 +
1.19 +#include "rendertarget.h"
1.20 +#include <graphics/directgdidriver.h>
1.21 +#include <graphics/sgutils.h>
1.22 +#include "panic.h"
1.23 +#include <bitdraworigin.h>
1.24 +#include <bitdrawinterfaceid.h>
1.25 +#include "utils.h"
1.26 +#if defined(__WINS__) && defined(_DEBUG)
1.27 +#include "osbwin.h"
1.28 +#endif
1.29 +
1.30 +RWsOffScreenImageTarget::RWsOffScreenImageTarget()
1.31 + {
1.32 + }
1.33 +
1.34 +void RWsOffScreenImageTarget::OpenL(TUint32 aUsage, TSgCpuAccess aCpuAccess, TUidPixelFormat aPixelFormat, const TSize& aSize, TInt aScreenNumber)
1.35 + {
1.36 + CDirectGdiDriver* theDGdiDriver = CDirectGdiDriver::Static();
1.37 + if(!theDGdiDriver)
1.38 + {
1.39 + User::Leave(KErrNotReady);
1.40 + }
1.41 + iImageInfos[CRenderTarget::ENormalAspectRatio].iUsage = aUsage;
1.42 + iImageInfos[CRenderTarget::ENormalAspectRatio].iPixelFormat = aPixelFormat;
1.43 + iImageInfos[CRenderTarget::ENormalAspectRatio].iSizeInPixels = aSize;
1.44 + iImageInfos[CRenderTarget::ENormalAspectRatio].iCpuAccess = aCpuAccess;
1.45 + iImageInfos[CRenderTarget::ENormalAspectRatio].iScreenId = aScreenNumber;
1.46 +
1.47 + iImageInfos[CRenderTarget::EInvertedAspectRatio] = iImageInfos[CRenderTarget::ENormalAspectRatio];
1.48 + iImageInfos[CRenderTarget::EInvertedAspectRatio].iSizeInPixels.SetSize(aSize.iHeight, aSize.iWidth);
1.49 +
1.50 + const TInt KImageCount = 1;
1.51 + User::LeaveIfError(RSgImageCollection::Create(iImageInfos, KImageCount, iImageCollections, CRenderTarget::EAspectRatioCount));
1.52 +
1.53 + for(TInt ii = 0; ii < CRenderTarget::EAspectRatioCount; ii++)
1.54 + {
1.55 + User::LeaveIfError(iImageCollections[ii].GetInfo(iImageInfos[ii])); //should be the same as requested, this is just belt and braces
1.56 + User::LeaveIfError(iImageCollections[ii].OpenImage(0, iImages[ii]));
1.57 + iImageTargets[ii] = RDirectGdiImageTarget(*theDGdiDriver);
1.58 + User::LeaveIfError(iImageTargets[ii].Create(iImages[ii]));
1.59 + }
1.60 + }
1.61 +
1.62 +void RWsOffScreenImageTarget::Close()
1.63 + {
1.64 + for(TInt ii = 0; ii < CRenderTarget::EAspectRatioCount; ii++)
1.65 + {
1.66 + iImageTargets[ii].Close();
1.67 + iImages[ii].Close();
1.68 + iImageCollections[ii].Close();
1.69 + }
1.70 + }
1.71 +
1.72 +/**
1.73 + Create and construct render target. The function creates RSgImage and target associated with it.
1.74 + DirectGc wrapper will also be created at this stage.
1.75 + */
1.76 +CRenderTarget* CRenderTarget::NewL(MWsIniFile* aIniFile, TUint32 aUsage, TSgCpuAccess aCpuAccess, TDisplayMode aDisplayMode, const TSize& aSize, TInt aScreenNumber)
1.77 + {
1.78 + CRenderTarget* self=new(ELeave) CRenderTarget();
1.79 + CleanupStack::PushL(self);
1.80 + self->ConstructL(aIniFile, aUsage, aCpuAccess, aDisplayMode, aSize, aScreenNumber);
1.81 + CleanupStack::Pop(self);
1.82 + return self;
1.83 + }
1.84 +
1.85 +inline CRenderTarget::CRenderTarget()
1.86 + : iCurrentAspectRatio(ENormalAspectRatio)
1.87 + {}
1.88 +
1.89 +CRenderTarget::~CRenderTarget()
1.90 + {
1.91 + delete iDirectGdiGcWrapper;
1.92 + iTarget.Close();
1.93 +#if defined(__WINS__) && defined(_DEBUG)
1.94 + delete iOsbWin;
1.95 +#endif
1.96 + }
1.97 +
1.98 +/**
1.99 + Construct render target. The function creates RSgImage and target associated with it.
1.100 + DirectGc wrapper will also be created at this stage.
1.101 + */
1.102 +#if defined(__WINS__) && defined(_DEBUG)
1.103 +void CRenderTarget::ConstructL(MWsIniFile* aIniFile, TUint32 aUsage, TSgCpuAccess aCpuAccess, TDisplayMode aDisplayMode, const TSize& aSize, TInt aScreenNumber)
1.104 +#else
1.105 +void CRenderTarget::ConstructL(MWsIniFile* /*aIniFile*/, TUint32 aUsage, TSgCpuAccess aCpuAccess, TDisplayMode aDisplayMode, const TSize& aSize, TInt aScreenNumber)
1.106 +#endif
1.107 + {
1.108 + CDirectGdiDriver* theDGdiDriver = CDirectGdiDriver::Static();
1.109 + if(!theDGdiDriver)
1.110 + {
1.111 + User::Leave(KErrNotReady);
1.112 + }
1.113 + iTarget.OpenL(aUsage, aCpuAccess, SgUtils::DisplayModeToPixelFormat(aDisplayMode), aSize, aScreenNumber);
1.114 + iDirectGdiGcWrapper = CDirectGdiGcWrapper::NewL();
1.115 + User::LeaveIfError(iDirectGdiGcWrapper->DirectGdiGc().Activate(iTarget.iImageTargets[iCurrentAspectRatio]));
1.116 +
1.117 +#if defined(__WINS__) && defined(_DEBUG)
1.118 + _LIT(KDebugOsb, "DEBUGOSB");
1.119 + if(aIniFile->FindVar(aScreenNumber, KDebugOsb))
1.120 + {
1.121 + _LIT(KDebugOsbTitleFormatBackBuffer, "Screen %d, back buffer ");
1.122 + _LIT(KDebugOsbTitleFormatScreen, "Screen %d, display buffer");
1.123 + TBuf<32> title;
1.124 + title.Format(((aUsage & ESgUsageScreenSource) ? KDebugOsbTitleFormatScreen : KDebugOsbTitleFormatBackBuffer), aScreenNumber);
1.125 + iOsbWin = CDebugOsbWin::NewL(title, aSize);
1.126 + }
1.127 +#endif
1.128 + }
1.129 +
1.130 +TAny* CRenderTarget::ResolveObjectInterface(TUint aTypeId)
1.131 + {
1.132 + switch(aTypeId)
1.133 + {
1.134 + case MWsUiBuffer::EWsObjectInterfaceId:
1.135 + return static_cast<MWsUiBuffer*>(this);
1.136 + }
1.137 + return DirectGdiGc()->ResolveObjectInterface(aTypeId);
1.138 + }
1.139 +
1.140 +TInt CRenderTarget::MapReadWrite(TAny*& aDataAddress, TInt& aDataStride)
1.141 + {
1.142 + CDirectGdiDriver* driver = CDirectGdiDriver::Static();
1.143 + if(driver)
1.144 + driver->Finish();
1.145 + return Image().MapReadWrite(aDataAddress, aDataStride);
1.146 + }
1.147 +
1.148 +TInt CRenderTarget::MapWriteOnly(TAny*& aDataAddress, TInt& aDataStride)
1.149 + {
1.150 + CDirectGdiDriver* driver = CDirectGdiDriver::Static();
1.151 + if(driver)
1.152 + driver->Finish();
1.153 + return Image().MapWriteOnly(aDataAddress, aDataStride);
1.154 + }
1.155 +
1.156 +TInt CRenderTarget::MapReadOnly(const TAny*& aDataAddress, TInt& aDataStride) const
1.157 + {
1.158 + CDirectGdiDriver* driver = CDirectGdiDriver::Static();
1.159 + if(driver)
1.160 + driver->Finish();
1.161 + return Image().MapReadOnly(aDataAddress, aDataStride);
1.162 + }
1.163 +
1.164 +TInt CRenderTarget::Unmap()
1.165 + {
1.166 + return Image().Unmap();
1.167 + }
1.168 +
1.169 +TInt CRenderTarget::Unmap() const
1.170 + {
1.171 + return Image().Unmap();
1.172 + }
1.173 +
1.174 +TUidPixelFormat CRenderTarget::PixelFormat() const
1.175 + {
1.176 + return ImageInfo().iPixelFormat;
1.177 + }
1.178 +
1.179 +TSize CRenderTarget::SizeInPixels() const
1.180 + {
1.181 + return ImageInfo().iSizeInPixels;
1.182 + }
1.183 +
1.184 +TDisplayMode CRenderTarget::DisplayMode() const
1.185 + {
1.186 + return SgUtils::PixelFormatToDisplayMode(PixelFormat());
1.187 + }
1.188 +
1.189 +const TSurfaceId& CRenderTarget::SurfaceId() const
1.190 + {
1.191 + return ImageCollection().SurfaceId();
1.192 + }
1.193 +
1.194 +const TSgDrawableId& CRenderTarget::ImageId(TAspectRatio aAspectRatio) const
1.195 + {
1.196 + return iTarget.iImages[aAspectRatio].Id();
1.197 + }
1.198 +
1.199 +void CRenderTarget::SetAspectRatio(TAspectRatio aAspectRatio)
1.200 + {
1.201 + STD_ASSERT_DEBUG(aAspectRatio == ENormalAspectRatio || aAspectRatio == EInvertedAspectRatio, EPluginPanicTemp);
1.202 + if(aAspectRatio != iCurrentAspectRatio)
1.203 + {
1.204 + iCurrentAspectRatio = aAspectRatio;
1.205 + iDirectGdiGcWrapper->Reset();
1.206 + }
1.207 + iDirectGdiGcWrapper->DirectGdiGc().Activate(iTarget.iImageTargets[iCurrentAspectRatio]);
1.208 + }
1.209 +
1.210 +TInt CRenderTarget::SetDrawDeviceOffset(TPoint& aOrigin)
1.211 + {
1.212 + //set the offset on both wrappers
1.213 + MDrawDeviceOrigin* originInterface=NULL;
1.214 + TInt result= iDirectGdiGcWrapper->DirectGdiGc().GetInterface(TUid::Uid(KDrawDeviceOriginInterfaceID),reinterpret_cast<TAny*&>(originInterface));
1.215 + if (result>=KErrNone && originInterface!=NULL)
1.216 + {
1.217 + result=originInterface->Set(aOrigin);
1.218 + }
1.219 +
1.220 + if (result>=KErrNone)
1.221 + {
1.222 + iOffset=aOrigin;
1.223 + iDirectGdiGcWrapper->DirectGdiGc().Activate(iTarget.iImageTargets[iCurrentAspectRatio]);
1.224 + }
1.225 + return result;
1.226 + }
1.227 +
1.228 +TInt CRenderTarget::AllocNewTarget(RWsOffScreenImageTarget& aNewTarget, const TSize& aNewSize)
1.229 + {
1.230 + TRAPD(err,
1.231 + aNewTarget.OpenL(
1.232 + iTarget.iImageInfos[CRenderTarget::ENormalAspectRatio].iUsage,
1.233 + iTarget.iImageInfos[CRenderTarget::ENormalAspectRatio].iCpuAccess,
1.234 + iTarget.iImageInfos[CRenderTarget::ENormalAspectRatio].iPixelFormat,
1.235 + aNewSize,
1.236 + iTarget.iImageInfos[CRenderTarget::ENormalAspectRatio].iScreenId))
1.237 + return err;
1.238 + }
1.239 +
1.240 +void CRenderTarget::SwitchTarget(RWsOffScreenImageTarget& aNewTarget)
1.241 + {
1.242 + iTarget.Close();
1.243 + iTarget = aNewTarget;
1.244 + iDirectGdiGcWrapper->DirectGdiGc().Activate(iTarget.iImageTargets[iCurrentAspectRatio]);
1.245 + }
1.246 +
1.247 +void CRenderTarget::GetPixel(TRgb& aColor, const TPoint& aPixel) const
1.248 + {
1.249 + const TAny* dataAddress = NULL;
1.250 + TInt dataStride;
1.251 + const TInt err = MapReadOnly(dataAddress, dataStride);
1.252 + if(!err)
1.253 + {
1.254 + const TUidPixelFormat pixelFormat = PixelFormat();
1.255 + const TInt bpp = SgUtils::MinDataStride(1, pixelFormat);
1.256 + const TUint32 offset = aPixel.iY * dataStride / bpp + aPixel.iX;
1.257 + switch(pixelFormat)
1.258 + {
1.259 + case EUidPixelFormatARGB_8888_PRE:
1.260 + case EUidPixelFormatARGB_8888:
1.261 + {
1.262 + const TInt32* dataAddress1 = static_cast<const TInt32*>(dataAddress) + offset;
1.263 + const TInt32 colValue = *dataAddress1;
1.264 + aColor.SetInternal(colValue);
1.265 + }
1.266 + break;
1.267 + case EUidPixelFormatRGB_565:
1.268 + {
1.269 + const TInt16* dataAddress1 = static_cast<const TInt16*>(dataAddress) + offset;
1.270 + const TInt16 colValue = *dataAddress1;
1.271 + aColor = TRgb::Color64K((TInt)colValue);
1.272 + }
1.273 + break;
1.274 + }
1.275 + Unmap();
1.276 + }
1.277 + }
1.278 +
1.279 +void CRenderTarget::GetScanLine(TDes8& aScanLine, const TPoint& aStartPixel, TInt aPixelLength, TDisplayMode aDispMode) const
1.280 + {
1.281 + TRect rectSrc(aStartPixel, TSize(aPixelLength, 1));
1.282 + const TRect rectClientArea(SizeInPixels());
1.283 + rectSrc.Intersection(rectClientArea);
1.284 + if(rectSrc.IsEmpty())
1.285 + return;
1.286 + const TUidPixelFormat pixelFormatSource = PixelFormat();
1.287 + const TUidPixelFormat pixelFormatDest = SgUtils::DisplayModeToPixelFormat(aDispMode);
1.288 + if((pixelFormatSource == EUidPixelFormatUnknown) || (pixelFormatDest == EUidPixelFormatUnknown))
1.289 + return;
1.290 +
1.291 + aPixelLength = rectSrc.Width();
1.292 + const TInt dataStrideDest = SgUtils::MinDataStride(aPixelLength, pixelFormatDest);
1.293 + if(dataStrideDest <= 0)
1.294 + return;
1.295 + const TAny* dataAddressSource = NULL;
1.296 + TInt dataStrideSource;
1.297 + const TInt err = MapReadOnly(dataAddressSource, dataStrideSource);
1.298 + if(!err)
1.299 + {
1.300 + aScanLine.SetLength(dataStrideDest);
1.301 + SgUtils::TransferPixels(const_cast<TUint8*>(aScanLine.Ptr()), dataStrideDest, pixelFormatDest,
1.302 + dataAddressSource, dataStrideSource, pixelFormatSource, rectSrc);
1.303 + Unmap();
1.304 + }
1.305 + }
1.306 +
1.307 +TBool CRenderTarget::RectCompare(const TRect& aRect1, const TRect& aRect2) const
1.308 + {
1.309 + const TAny* startDataAddress = NULL;
1.310 + TInt dataStride;
1.311 +
1.312 + const TRect clientRect(SizeInPixels());
1.313 + TRect rect1 = aRect1;
1.314 + TRect rect2 = aRect2;
1.315 +
1.316 + rect1.Intersection(clientRect);
1.317 + rect2.Intersection(clientRect);
1.318 + if(rect1.IsEmpty() || rect2.IsEmpty() || (rect1 != aRect1) || (rect2 != aRect2) ||
1.319 + (rect1.Width() != rect2.Width()) || (rect1.Height() != rect2.Height()))
1.320 + return EFalse;
1.321 +
1.322 + TUidPixelFormat pixelFormat = PixelFormat();
1.323 + if(pixelFormat == EUidPixelFormatUnknown)
1.324 + return EFalse;
1.325 +
1.326 + TInt bpp = SgUtils::MinDataStride(1, pixelFormat);
1.327 + if(bpp == 0)
1.328 + return EFalse;
1.329 +
1.330 + TInt err = MapReadOnly(startDataAddress, dataStride);
1.331 + if(err != KErrNone)
1.332 + return EFalse;
1.333 + TBool res = ETrue;
1.334 + TPoint startPoint1 = rect1.iTl;
1.335 + TPoint startPoint2 = rect2.iTl;
1.336 + const TInt length1 = SgUtils::MinDataStride(rect1.Width(), pixelFormat);
1.337 + const TInt length2 = SgUtils::MinDataStride(rect2.Width(), pixelFormat);
1.338 +
1.339 + for(; (startPoint1.iY < rect1.iBr.iY) && (startPoint2.iY < rect2.iBr.iY); startPoint1.iY++, startPoint2.iY++)
1.340 + {
1.341 + const TUint8* dataAddress1 = DataAddress(startDataAddress, startPoint1, dataStride, bpp);
1.342 + const TUint8* dataAddress2 = DataAddress(startDataAddress, startPoint2, dataStride, bpp);
1.343 +
1.344 + if(Mem::Compare(dataAddress1, length1, dataAddress2, length2) != 0)
1.345 + {
1.346 + res = EFalse;
1.347 + break;
1.348 + }
1.349 + }
1.350 + Unmap();
1.351 +
1.352 + return res;
1.353 + }
1.354 +
1.355 +void CRenderTarget::CopyToBitmapL(CFbsBitmap* aBitmap, const TRect& aRect) const
1.356 + {
1.357 + const TUidPixelFormat pixelFormatDest = SgUtils::DisplayModeToPixelFormat(aBitmap->DisplayMode());
1.358 + const TUidPixelFormat pixelFormatSrc = PixelFormat();
1.359 + if((pixelFormatSrc == EUidPixelFormatUnknown) || (pixelFormatDest == EUidPixelFormatUnknown))
1.360 + User::LeaveIfError(KErrNotSupported);
1.361 +
1.362 + aBitmap->BeginDataAccess();
1.363 + const TSize sizeDest = aBitmap->SizeInPixels();
1.364 + TRect rectSrc = aRect;
1.365 + rectSrc.Intersection(TRect(SizeInPixels()));
1.366 + if(rectSrc.IsEmpty())
1.367 + return;
1.368 + if(rectSrc.Height() > sizeDest.iHeight)
1.369 + {
1.370 + rectSrc.SetHeight(sizeDest.iHeight);
1.371 + }
1.372 + if(rectSrc.Width() > sizeDest.iWidth)
1.373 + {
1.374 + rectSrc.SetWidth(sizeDest.iWidth);
1.375 + }
1.376 +
1.377 + const TAny* dataAddressSrc = NULL;
1.378 + TInt dataStrideSrc;
1.379 + User::LeaveIfError(MapReadOnly(dataAddressSrc, dataStrideSrc));
1.380 +
1.381 + SgUtils::TransferPixels(aBitmap->DataAddress(), aBitmap->DataStride(), pixelFormatDest,
1.382 + dataAddressSrc, dataStrideSrc, pixelFormatSrc, rectSrc);
1.383 +
1.384 + aBitmap->EndDataAccess();
1.385 + Unmap();
1.386 + }
1.387 +
1.388 +/*
1.389 + Helper function to obtain the address of the buffer
1.390 + */
1.391 +const TUint8* CRenderTarget::DataAddress(const TAny* aStartDataAddress, const TPoint& aStartPoint, TInt aDataStride, TInt aBpp) const
1.392 + {
1.393 + const TInt offset = aStartPoint.iX * aBpp + aStartPoint.iY * aDataStride;
1.394 + const TUint8* dataAddress = static_cast<TUint8*>(const_cast<TAny*> (aStartDataAddress));
1.395 +
1.396 + return(dataAddress + offset);
1.397 + }
1.398 +
1.399 +#if defined(__WINS__) && defined(_DEBUG)
1.400 +void CRenderTarget::UpdateDebugWin()
1.401 + {
1.402 + if (iOsbWin)
1.403 + {
1.404 + const TAny* dataAddress = NULL;
1.405 + TInt dataStride;
1.406 + const TInt err = MapReadOnly(dataAddress, dataStride);
1.407 + if(!err)
1.408 + {
1.409 + const TUint32* dataAddress1 = static_cast<const TUint32*>(dataAddress);
1.410 + iOsbWin->Refresh(SizeInPixels(), DisplayMode(), dataAddress1);
1.411 + Unmap();
1.412 + }
1.413 + }
1.414 + }
1.415 +#endif