适用版本:
Series 60 2nd , Series 60 3rd
更多关于在文本中插入图片参见这里: [1]
一般情况下,在CEikRichTextEditor中插入的图片都是绘制在白色的背景上的,包括Forum Nokia提供的示例也是如此,如果在带有背景的Editor中使用会很别扭,下面将演示如何在文本中插入带背景的图片。
方案思路:
首先CRTxPicture是一个继承自CPicture的图片类,在该类的Draw()函数中首先绘制背景,然后在其之上绘制实际的图片。
void CRTxPicture::Draw(CGraphicsContext& aGc, const TPoint& aTopLeft, const TRect& aClipRect, MGraphicsDeviceMap* aMap) const
{
CBitmapContext& gc = static_cast(aGc);
TRect bmpPieceRect(TPoint(0,0),iBitmap->SizeInPixels());
// here is the skin background drawn
iControl.RTxDrawBackground(aTopLeft, bmpPieceRect, gc);
// then the picture itself
gc.BitBltMasked(aTopLeft, iBitmap, bmpPieceRect, iBitmapMask, ETrue);
}
背景实际是在容器(Container)中绘制的,因此Container必须继承自MRTxBackgroundDrawer类,而且必须实现其中的RTxDrawBackground ()函数。
class MRTxBackgroundDrawer
{
public:
virtual void RTxDrawBackground(const TPoint& aDstPos, const TRect& aRect, CBitmapContext& gc) = 0;
};
class CMyAppContainer : public CCoeControl, public MRTxBackgroundDrawer
void CMyAppContainer::RTxDrawBackground(const TPoint& aDstPos, const TRect& aRect, CBitmapContext& gc)
{
#ifdef USE_SKIN
MAknsSkinInstance* skin = AknsUtils::SkinInstance();
MAknsControlContext* cc = AknsDrawUtils::ControlContext(this);
AknsDrawUtils::DrawBackground(skin, cc, this, gc, TPoint(0, 0), aRect, KAknsDrawParamDefault);
#else
gc.SetPenStyle(CGraphicsContext::ENullPen);
gc.SetBrushColor(KRgbBlue);
gc.SetBrushStyle(CGraphicsContext::ESolidBrush);
gc.DrawRect(aRect);
#endif
}
然后我们就可以通过以下 InsertPictureL()函数进行插入图片了。
void CRTx::InsertPictureL(MRTxBackgroundDrawer& aControl, TInt aPos, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask)
{
CRTxPicture* picture;
picture = new(ELeave) CRTxPicture(iTextBox->GetSystemGc(), aControl, aBitmap, aBitmapMask);
CleanupStack::PushL(picture);
TPictureHeader header;
header.iPicture = TSwizzle(picture);
iTextBox->RichText()->InsertL(aPos, header);
CleanupStack::Pop();
}
在绘制背景时(RTxDrawBackground函数)使用了USE_SKIN来判断应用程序中的Editor是否使用了背景,因此如果使用了背景,需要在.mmp文件中加入以下语句:
MACRO USE_SKIN
完整的示例代码如下:
///
// MyAppContainer.cpp (parts)
///
#include
#include
#include
#include
#include "RTx.h"
#include
#include "MyAppDocument.h"
#include "MyAppViewDevices.h"
#include "MyAppContainer.h"
#ifdef USE_SKIN
#include
#include
#endif
#define LKMyAppMIF L"\\resource\\apps\\myapp.mif"
CMyAppContainer::CMyAppContainer(CMyAppViewDevices* aView) : iView(aView)
{
}
CMyAppContainer::~CMyAppContainer()
{
delete iRTx;
delete iTextBox;
for(int i = 0; i < iBitmap->Count(); i++)
delete iBitmap->At(i);
delete iBitmap;
for(int i = 0; i < iBitmapMask->Count(); i++)
delete iBitmapMask->At(i);
delete iBitmapMask;
#ifdef USE_SKIN
delete iBackGround;
#endif
}
void CMyAppContainer::LoadBitmapListL()
{
_LIT(KMyAppMif, KMyAppMIF);
PrepareBitmapL(KMyAppMif, EMbmMyAppmifImage, EMbmMyAppmifImage_mask); // the image (bitmap or svg)
}
void CMyAppContainer::AddSomeTextAndImageL()
{
_LIT(KText1, "Hello World!");
iRTx->AddTextL(KText1);
iRTx->AddCarriageReturnL();
iRTx->AddPictureL(*this, *(iBitmap->At(0)), *(iBitmapMask->At(0)));
}
void CMyAppContainer::ConstructL(const TRect& aRect)
{
CreateWindowL();
iBitmap = new (ELeave) CArrayFixFlat(1);
iBitmapMask = new (ELeave) CArrayFixFlat(1);
LoadBitmapListL();
iTextBox = new (ELeave) CRTxEditor(TGulBorder::ENone);
iTextBox->SetMopParent(this);
iRTx = new (ELeave) CRTx(iTextBox);
TInt edwinFlags = EEikEdwinInclusiveSizeFixed|EEikEdwinNoAutoSelection|EEikEdwinDisplayOnly|EEikEdwinReadOnly|
EEikEdwinLineCursor|EEikEdwinNoHorizScrolling|EEikEdwinAvkonDisableCursor;
iTextBox->ConstructL(this, 0, 0, edwinFlags,EGulFontControlAll, EGulAllFonts);
iTextBox->SetAknEditorFlags(edwinFlags);
iTextBox->SetContainerWindowL(*this);
iTextBox->SetFocus(ETrue);
AddSomeTextAndImageL();
SetRect(aRect);
#ifdef USE_SKIN
iBackGround = CAknsBasicBackgroundControlContext::NewL( KAknsIIDQsnBgAreaMain, Rect(), EFalse );
#endif
ActivateL();
}
void CMyAppContainer::SizeChanged()
{
TRect r = Rect();
if (iTextBox)
{
TSize scr = CEikonEnv::Static()->ScreenDevice()->SizeInPixels();
iTextBox->SetExtent(TPoint(0, 0), TSize(r.Width(), r.Height()));
}
}
void CMyAppContainer::HandleResourceChange(TInt aType)
{
CCoeControl::HandleResourceChange(aType);
if (aType == KEikDynamicLayoutVariantSwitch)
{
SetRect(iView->ClientRect());
}
}
void CMyAppContainer::Draw(const TRect& aRect) const
{
CWindowGc& gc = SystemGc();
#ifdef USE_SKIN
MAknsSkinInstance* skin = AknsUtils::SkinInstance();
MAknsControlContext* cc = AknsDrawUtils::ControlContext(this);
AknsDrawUtils::Background(skin, cc, this, gc, aRect);
#else
gc.SetPenStyle(CGraphicsContext::ENullPen);
gc.SetBrushColor(KRgbBlue);
gc.SetBrushStyle(CGraphicsContext::ESolidBrush);
gc.DrawRect(aRect);
#endif
}
TInt CMyAppContainer::CountComponentControls() const
{
return 1;
}
CCoeControl* CMyAppContainer::ComponentControl(TInt aIndex) const
{
switch (aIndex)
{
case 0:
return iTextBox;
default:
return NULL;
}
}
TKeyResponse CMyAppContainer::OfferKeyEventL(const TKeyEvent& keyEvent, TEventCode type)
{
if (type != EEventKey )
return EKeyWasNotConsumed;
switch (keyEvent.iCode)
{
case EKeyLeftArrow:
case EKeyRightArrow:
return EKeyWasNotConsumed;
}
return iRTx->OfferKeyEventL(keyEvent, type);
}
// from MRTxBackgroundDrawer
void CMyAppContainer::RTxDrawBackground(const TPoint& aDstPos, const TRect& aRect, CBitmapContext& gc)
{
#ifdef USE_SKIN
MAknsSkinInstance* skin = AknsUtils::SkinInstance();
MAknsControlContext* cc = AknsDrawUtils::ControlContext(this);
AknsDrawUtils::DrawBackground(skin, cc, this, gc, TPoint(0, 0), aRect, KAknsDrawParamDefault);
#else
gc.SetPenStyle(CGraphicsContext::ENullPen);
gc.SetBrushColor(KRgbBlue);
gc.SetBrushStyle(CGraphicsContext::ESolidBrush);
gc.DrawRect(aRect);
#endif
}
#ifdef USE_SKIN
TTypeUid::Ptr CMyAppContainer::MopSupplyObject(TTypeUid aId)
{
if (aId.iUid == MAknsControlContext::ETypeId && iBackGround)
return MAknsControlContext::SupplyMopObject(aId, iBackGround);
return CCoeControl::MopSupplyObject(aId);
}
#endif
void CMyAppContainer::PrepareBitmapL(const TDesC& aFileName, TInt aId, TInt aIdMask)
{
CFbsBitmap* bitmap, *bitmap_mask;
AknIconUtils::CreateIconL(bitmap, bitmap_mask, aFileName, aId, aIdMask);
TSize scr = CEikonEnv::Static()->ScreenDevice()->SizeInPixels();
TSize iconSize(scr.iWidth / 2, scr.iWidth / 3); // sample resizing - depends on the image
AknIconUtils::SetSize(bitmap, iconSize, EAspectRatioNotPreserved);
AknIconUtils::SetSize(bitmap_mask, iconSize, EAspectRatioNotPreserved);
iBitmap->AppendL(bitmap);
iBitmapMask->AppendL(bitmap_mask);
}
///
// RTxBackgroundDrawer.h
///
/* Leszek Buczkowski, Ingraal 2006 */
#ifndef __RTX_BACKGROUND_DRAWER_H__
#define __RTX_BACKGROUND_DRAWER_H__
class MRTxBackgroundDrawer
{
public:
virtual void RTxDrawBackground(const TPoint& aDstPos, const TRect& aRect, CBitmapContext& gc) = 0;
};
#endif
///
// RTxPicture.h
///
/* Leszek Buczkowski, Ingraal 2006 */
#ifndef __RTX_PICTURE_H__
#define __RTX_PICTURE_H__
#include
class CWindowGc;
class TSize;
class CFbsBitmap;
class MRTxBackgroundDrawer;
class CRTxPicture : public CPicture
{
public: // no destructor - bitmap not owned
CRTxPicture(CWindowGc& gc, MRTxBackgroundDrawer& aControl, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask);
public:
TBool LineBreakPossible(TUint aClass, TBool aBeforePicture, TBool aHaveSpaces) const {return EFalse;};
void Draw(CGraphicsContext& aGc, const TPoint& aTopLeft, const TRect& aClipRect, MGraphicsDeviceMap* aMap) const;
void ExternalizeL(RWriteStream& aStream) const {};
void GetOriginalSizeInTwips(TSize& aSize) const {aSize = iSizeInTwips;};
protected:
TSize iSizeInTwips;
MRTxBackgroundDrawer& iControl;
CFbsBitmap* iBitmap;
CFbsBitmap* iBitmapMask;
};
#endif
///
// RTxPicture.cpp
///
/* Leszek Buczkowski, Ingraal 2006 */
#include
#include
#include "RTxPicture.h"
#include "RTxBackgroundDrawer.h"
#ifdef USE_SKIN
#include
#include
#endif
CRTxPicture::CRTxPicture(CWindowGc& gc, MRTxBackgroundDrawer& aControl, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask) : iControl(aControl), iBitmap(&aBitmap), iBitmapMask(&aBitmapMask)
{
TSize sizeInPixels = gc.Device()->SizeInPixels();
TSize sizeInTwips = gc.Device()->SizeInTwips();
TSize bitmapSizeInPixels = aBitmap.SizeInPixels();
iSizeInTwips = TSize(sizeInTwips.iWidth * bitmapSizeInPixels.iWidth / sizeInPixels.iWidth, sizeInTwips.iHeight * bitmapSizeInPixels.iHeight / sizeInPixels.iHeight);
}
void CRTxPicture::Draw(CGraphicsContext& aGc, const TPoint& aTopLeft, const TRect& aClipRect, MGraphicsDeviceMap* aMap) const
{
CBitmapContext& gc = static_cast(aGc);
TRect bmpPieceRect(TPoint(0,0),iBitmap->SizeInPixels());
// here is the skin background drawn
iControl.RTxDrawBackground(aTopLeft, bmpPieceRect, gc);
// then the picture itself
gc.BitBltMasked(aTopLeft, iBitmap, bmpPieceRect, iBitmapMask, ETrue);
}
///
// RTx.h
///
/* Leszek Buczkowski, Ingraal 2006 */
#ifndef __RTX_H__
#define __RTX_H__
#include
#include
#include
#include
#include
#include
#include
#include "RTxBackgroundDrawer.h"
class CWindowGc;
class CFbsBitmap;
// CRTxEditor is derived from CEikRichTextEditor in order to make protected GetSystemGc available
// as public (used in CRTx::InsertPictureL)
class CRTxEditor : public CEikRichTextEditor
{
public:
CRTxEditor(const TGulBorder& aBorder) { iBorder = aBorder; };
CWindowGc& GetSystemGc() const { return SystemGc(); };
};
class CRTx : public CBase
{
public:
CRTx(CRTxEditor* aTextBox);
~CRTx();
TKeyResponse OfferKeyEventL(const TKeyEvent& aKeyEvent,TEventCode aType);
void AddCarriageReturnL();
void AddTextL (const TDesC& aText);
void InsertPictureL(MRTxBackgroundDrawer& aControl, TInt aPos, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask);
void AddPictureL(MRTxBackgroundDrawer& aControl, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask);
private:
CRTxEditor* iTextBox;
TCharFormatMask iCharFormatMask;
TCharFormat iCharFormat;
};
#endif
///
// RTx.cpp
///
/* Leszek Buczkowski, Ingraal 2006 */
#include "RTx.h"
#include "RTxPicture.h"
#include
#include
CRTx::CRTx(CRTxEditor* aTextBox)
{
iTextBox = aTextBox;
}
CRTx::~CRTx()
{
}
void CRTx::AddCarriageReturnL()
{
CRichText* richText = iTextBox->RichText();
richText->InsertL(richText->DocumentLength(), CEditableText::ELineBreak);
iTextBox->HandleTextChangedL();
}
void CRTx::AddTextL(const TDesC& aText)
{
CRichText* richText = iTextBox->RichText();
TInt documentLength = richText->DocumentLength();
richText->InsertL (documentLength, aText);
richText->ApplyCharFormatL(iCharFormat, iCharFormatMask,documentLength,aText.Length());
iTextBox->HandleTextChangedL();
}
void CRTx::InsertPictureL(MRTxBackgroundDrawer& aControl, TInt aPos, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask)
{
CRTxPicture* picture;
picture = new(ELeave) CRTxPicture(iTextBox->GetSystemGc(), aControl, aBitmap, aBitmapMask);
CleanupStack::PushL(picture);
TPictureHeader header;
header.iPicture = TSwizzle(picture);
iTextBox->RichText()->InsertL(aPos, header);
CleanupStack::Pop();
}
void CRTx::AddPictureL(MRTxBackgroundDrawer& aControl, CFbsBitmap& aBitmap, CFbsBitmap& aBitmapMask)
{
CRichText* richText = iTextBox->RichText();
TInt documentLength = richText->DocumentLength();
InsertPictureL(aControl, documentLength, aBitmap, aBitmapMask);
}
TKeyResponse CRTx::OfferKeyEventL(const TKeyEvent& aKeyEvent,TEventCode aType)
{
if (aType == EEventKey)
{
if (aKeyEvent.iCode == EKeyDownArrow)
{
iTextBox->MoveCursorL (TCursorPosition::EFPageDown, EFalse);
return EKeyWasConsumed;
}
else if (aKeyEvent.iCode == EKeyUpArrow)
{
iTextBox->MoveCursorL (TCursorPosition::EFPageUp, EFalse);
return EKeyWasConsumed;
}
else
{
return iTextBox->OfferKeyEventL(aKeyEvent, aType);
}
}
return EKeyWasNotConsumed;
}
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/17096048/viewspace-590713/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/17096048/viewspace-590713/