在C++builder中防止画图闪烁,一般需要用到双缓冲,即在内存中画图,然后复制到界面上去。
.h文件如下:
class TForm1 : public TForm
{
__published: // IDE-managed Components
TTimer *Timer1;
TImage *Image1;
void __fastcall Timer1Timer(TObject *Sender);
private: // User declarations
ULONG_PTR GdiplusToken; //GDI初始化相关
Gdiplus::GdiplusStartupInput GdiplusStartupInput;
public: // User declarations
__fastcall TForm1(TComponent* Owner);
__fastcall ~TForm1(void);
HDC m_hdcMemory; //内存句柄
HDC hdcTemp; //设备上下文句柄
HBITMAP hBitMap; //位图句柄
};
//---------------------------------------------------------------------------
extern PACKAGE TForm1 *Form1;
.cpp文件中调用GDI+画图,代码如下:
#include <vcl.h>
#pragma hdrstop
#include <math.h>
#include <algorithm>
using std::min;
using std::max;
#include "gdiplus.h"
using namespace Gdiplus;
#include "Unit1.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
#pragma warn -inl
#pragma warn -8022
Gdiplus::Graphics *g;
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
Image1->Parent->DoubleBuffered = true;
GdiplusStartup(&GdiplusToken, &GdiplusStartupInput, NULL); //初始化GDI+
//---------------------------------------
hdcTemp = GetDC(0);//设备上下文环境句柄
m_hdcMemory = CreateCompatibleDC(hdcTemp);//内存环境句柄
hBitMap = CreateCompatibleBitmap(hdcTemp,450,265);//该函数创建与指定的设备环境相关的设备兼容的位图
SelectObject(m_hdcMemory, hBitMap);//该函数选择一对象到指定的设备上下文环境中
g= new Gdiplus::Graphics(m_hdcMemory);
}
//---------------------------------------------------------------------------
__fastcall TForm1::~TForm1(void)
{
GdiplusShutdown(GdiplusToken); // 关闭GDI+
ReleaseDC(0, hdcTemp);
hdcTemp = NULL;
DeleteObject(hBitMap);
DeleteDC(m_hdcMemory);
m_hdcMemory = NULL;
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Timer1Timer(TObject *Sender)
{
const static int OX = 200, OY = 200;
const static REAL C = 140;
const static REAL PI = 3.14;
static REAL offset = 0;
POINT p[4];
REAL k[4];
//==============================
// 生成正文形四角的新坐标值
for (int i=0; i < 4; i++)
{
k[i] = offset + (PI / 2) * i;
p[i].x = (int)OX + C*sin(k[i]);
p[i].y = (int)OY + C*cos(k[i]);
}
g->SetSmoothingMode(SmoothingModeHighQuality); //高画质、低速
// 重新填充背景
SolidBrush brush(Color::Color(100,0,0));//画刷
Pen pen(Color::Color(255, 0, 0), 1);//画笔
g->FillRectangle(&brush, 0, 0, ClientWidth, ClientHeight); //画矩形
Gdiplus::Point point1(p[0].x, p[0].y);//设置点坐标
Gdiplus::Point point2(p[1].x, p[1].y);
Gdiplus::Point point3(p[2].x, p[2].y);
Gdiplus::Point point4(p[3].x, p[3].y);
Gdiplus::Point point5(p[0].x, p[0].y);
// 在新坐标绘画正方形
Gdiplus::Point points[] = {point1, point2, point3, point4, point5};
g->DrawLines(&pen, points, 5);//画线
offset += 0.1;
BitBlt(Image1->Canvas->Handle, 0, 0, 600, 600, m_hdcMemory, 0, 0, SRCCOPY);//复制内存中的图像到界面上去
Image1->Repaint();
}