Tidied iocli exports, build macro tweaks.
Removed 4 overloads of CCommandBase::RunCommand[L] that are no longer used at all, and changed one more to not be exported as it's only used internally to iocli.dll.
fixed builds on platforms that don't support btrace or any form of tracing.
// grabscreen.cpp
//
// Copyright (c) 2008 - 2010 Accenture. All rights reserved.
// This component and the accompanying materials are made available
// under the terms of the "Eclipse Public License v1.0"
// which accompanies this distribution, and is available
// at the URL "http://www.eclipse.org/legal/epl-v10.html".
//
// Initial Contributors:
// Accenture - Initial contribution
//
#include <fshell/ioutils.h>
#include <w32std.h>
#include <fbs.h>
#include <bitdev.h>
#include <imageconversion.h>
using namespace IoUtils;
class CCmdGrabscreen : public CCommandBase
{
public:
static CCommandBase* NewLC();
~CCmdGrabscreen();
private:
enum TFormat
{
EJpeg,
EGif,
EBmp,
EPng,
ERaw
};
private:
CCmdGrabscreen();
void WriteEncodedL(TUid aEncodingUid);
void WriteRawL();
private: // From CCommandBase.
virtual const TDesC& Name() const;
virtual void DoRunL();
virtual void ArgumentsL(RCommandArgumentList& aArguments);
virtual void OptionsL(RCommandOptionList& aOptions);
virtual void RunL();
private:
TFileName2 iFileName;
CImageEncoder* iImageEncoder;
HBufC8* iImageData;
CFrameImageData* iFrameImageData;
RFile iFile;
TFormat iFormat;
RArray<TInt> iRect;
TInt iScreen;
CFbsBitmap* iBitMap;
CWsScreenDevice* iDev;
RWsSession iWsSession;
TInt iQuality;
TBool iGreyscale;
};
CCommandBase* CCmdGrabscreen::NewLC()
{
CCmdGrabscreen* self = new(ELeave) CCmdGrabscreen();
CleanupStack::PushL(self);
self->BaseConstructL();
return self;
}
CCmdGrabscreen::~CCmdGrabscreen()
{
delete iImageEncoder;
delete iFrameImageData;
delete iDev;
delete iBitMap;
delete iImageData;
iFile.Close();
iRect.Close();
iWsSession.Close();
REComSession::FinalClose();
}
CCmdGrabscreen::CCmdGrabscreen()
: CCommandBase(EManualComplete), iQuality(100)
{
}
const TDesC& CCmdGrabscreen::Name() const
{
_LIT(KName, "grabscreen");
return KName;
}
void CCmdGrabscreen::DoRunL()
{
if ((iFormat == ERaw) && (!iArguments.IsPresent(0)))
{
PrintError(KErrArgument, _L("STDOUT writing is not supported for raw format; please specify a filename"));
DisplayHelp();
User::Leave(KErrArgument);
}
LeaveIfErr(iWsSession.Connect(), _L("Couldn't connect to windowserver"));
iDev = new(ELeave) CWsScreenDevice(iWsSession);
#ifdef SYMBIAN_WSERV_AND_CONE_MULTIPLE_SCREENS
const TInt numScreens = iWsSession.NumberOfScreens();
if (iScreen >= numScreens)
{
if (numScreens == 1)
{
LeaveIfErr(KErrArgument, _L("Invalid screen number - there is only 1 screen"));
}
else
{
LeaveIfErr(KErrArgument, _L("Invalid screen number - there are only %d screens"));
}
}
#endif
LeaveIfErr(iDev->Construct(iScreen), _L("Couldn't construct CWsScreenDevice for screen %d"), iScreen);
iBitMap = new(ELeave) CFbsBitmap();
TRect rect;
if (iOptions.IsPresent(&iRect))
{
if (iRect.Count() != 4)
{
LeaveIfErr(KErrArgument, _L("Invalid --rect option - four integers must be specifed"));
}
rect.SetRect(iRect[0], iRect[1], iRect[2], iRect[3]);
}
else
{
rect.SetRect(TPoint(0, 0), iDev->SizeInPixels());
}
LeaveIfErr(iBitMap->Create(rect.Size(), iDev->DisplayMode()), _L("Couldn't create fbsbitmap of size (%d,%d) for display mode %d"), rect.Width(), rect.Height(), iDev->DisplayMode());
User::LeaveIfError(iDev->CopyScreenToBitmap(iBitMap, rect));
switch (iFormat)
{
case EJpeg:
WriteEncodedL(KImageTypeJPGUid);
break;
case EGif:
WriteEncodedL(KImageTypeGIFUid);
break;
case EBmp:
WriteEncodedL(KImageTypeBMPUid);
break;
case EPng:
WriteEncodedL(KImageTypePNGUid);
break;
case ERaw:
WriteRawL();
break;
}
}
void CCmdGrabscreen::WriteEncodedL(TUid aEncodingUid)
{
if (aEncodingUid == KImageTypeJPGUid)
{
TJpegImageData* imageData = new(ELeave) TJpegImageData();
CleanupStack::PushL(imageData);
imageData->iSampleScheme = iGreyscale ? TJpegImageData::EMonochrome : TJpegImageData::EColor444;
imageData->iQualityFactor = iQuality;
iFrameImageData = CFrameImageData::NewL();
User::LeaveIfError(iFrameImageData->AppendImageData(imageData));
CleanupStack::Pop(imageData);
}
else if (aEncodingUid == KImageTypeGIFUid)
{
if (iGreyscale)
{
PrintWarning(_L("Greyscale not supported for GIF images."));
}
if (iOptions.IsPresent(&iQuality))
{
PrintWarning(_L("Quality control not supported for GIF images."));
}
}
else if (aEncodingUid == KImageTypeBMPUid)
{
if (iGreyscale)
{
PrintWarning(_L("Greyscale not supported for BMP images."));
}
if (iOptions.IsPresent(&iQuality))
{
PrintWarning(_L("Quality control not supported for BMP images."));
}
}
else if (aEncodingUid == KImageTypePNGUid)
{
if (iOptions.IsPresent(&iQuality))
{
PrintWarning(_L("Quality control not supported for PNG images."));
}
TPngEncodeData* imageData = new(ELeave) TPngEncodeData();
CleanupStack::PushL(imageData);
imageData->iBitsPerPixel = iGreyscale ? 4 : 8;
imageData->iColor = !iGreyscale;
imageData->iLevel = TPngEncodeData::EBestCompression;
imageData->iPaletted = EFalse;
iFrameImageData = CFrameImageData::NewL();
User::LeaveIfError(iFrameImageData->AppendFrameData(imageData));
CleanupStack::Pop(imageData);
}
if (iArguments.IsPresent(0))
{
LeaveIfErr(iFile.Replace(FsL(), iFileName, EFileWrite), _L("Unable to open \"%S\" for writing"), &iFileName);
iImageEncoder = CImageEncoder::FileNewL(iFile, CImageEncoder::EOptionNone, aEncodingUid);
}
else
{
iImageEncoder = CImageEncoder::DataNewL(iImageData, CImageEncoder::EOptionNone, aEncodingUid);
}
iImageEncoder->Convert(&iStatus, *iBitMap, iFrameImageData);
SetActive();
}
void CCmdGrabscreen::RunL()
{
User::LeaveIfError(iStatus.Int());
if (!iArguments.IsPresent(0))
{
User::LeaveIfNull(iImageData);
Stdout().SetModeL(RIoReadWriteHandle::EBinary);
// we need to expand the 8 bit data when writing to stdout
static const TInt KBufferSize = 0x100;
TBuf<KBufferSize> buf;
TPtr8 imageData(iImageData->Des());
while (imageData.Length())
{
TInt thisCopyLen = Min(KBufferSize, imageData.Length());
buf.Copy(imageData.Left(thisCopyLen));
imageData.Set(imageData.MidTPtr(thisCopyLen));
Stdout().WriteL(buf);
}
}
Complete(KErrNone);
}
void CCmdGrabscreen::WriteRawL()
{
if (iGreyscale)
{
PrintWarning(_L("Greyscale not supported for raw images."));
}
if (iOptions.IsPresent(&iQuality))
{
PrintWarning(_L("Quality control not supported for raw images."));
}
LeaveIfErr(iBitMap->Save(iFileName), _L("Unable to write \"%S\""), &iFileName);
Complete(KErrNone);
}
void CCmdGrabscreen::ArgumentsL(RCommandArgumentList& aArguments)
{
_LIT(KArg, "file_name");
aArguments.AppendFileNameL(iFileName, KArg);
}
void CCmdGrabscreen::OptionsL(RCommandOptionList& aOptions)
{
_LIT(KOptFormat, "format");
aOptions.AppendEnumL((TInt&)iFormat, KOptFormat);
_LIT(KOptRect, "rect");
aOptions.AppendIntL(iRect, KOptRect);
_LIT(KOptScreen, "screen");
aOptions.AppendIntL(iScreen, KOptScreen);
_LIT(KOptQuality, "quality");
aOptions.AppendIntL(iQuality, KOptQuality);
_LIT(KOptGreyscale, "greyscale");
aOptions.AppendBoolL(iGreyscale, KOptGreyscale);
}
EXE_BOILER_PLATE(CCmdGrabscreen)