⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 canvas.cpp

📁 smartphone 监听电源状态源码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
#include "StdAfx.h"
#include "Canvas.h"
#include "resourcesp.h"

CCanvas::CCanvas(void)
{
	m_pAnimation=NULL;
	m_CurrentLoop=0;
	m_CurrentImage=0;
	m_bAnimationPlaying=false;
	m_vecSM.clear();
	InitializeCriticalSection(&m_CriticalSection);
	m_arrVisibleBmp.clear();
	memset( m_arrItemRect,0,CANVAS_LINE*CANVAS_ROW*sizeof(RECT));
	m_hDefaultBitmap = NULL;

}

CCanvas::~CCanvas(void)
{
	std::vector<CShortcutManager*>::iterator it;
	for(it = m_vecSM.begin();it!=m_vecSM.end();it++)
	{
		delete (*it);
		*it = NULL;
	}
	m_vecSM.clear();
	std::vector<HBITMAP>::iterator itt;
	for(itt = m_arrVisibleBmp.begin();itt!=m_arrVisibleBmp.end();itt++)
	{
		DeleteObject(*itt);
		*itt = NULL;
	}
	m_arrVisibleBmp.clear();
	Stop();

}
BEGIN_MESSAGE_MAP(CCanvas, CStatic)
	ON_WM_PAINT()
END_MESSAGE_MAP()

void CCanvas::OnPaint()
{
	CPaintDC dc(this); // device context for painting
	// TODO: Add your message handler code here
	m_pMemDC = &dc;
	CDC memDC;
	CBitmap bmpCanvas;
	CBitmap*pOldBitmap;
//	bmpCanvas.CreateCompatibleBitmap(&dc,m_rcCanvas.Width(),m_rcCanvas.Height());
	//画背景图
	memDC.CreateCompatibleDC(&dc);
	HBITMAP hBmpBk = (HBITMAP)SHLoadDIBitmap(m_sBkBmpPath);
	bmpCanvas.Attach(hBmpBk);
	pOldBitmap = memDC.SelectObject(&bmpCanvas);

	DrawShortcutItem(memDC);

	dc.BitBlt(m_rcCanvas.left,m_rcCanvas.top,m_rcCanvas.Width(),m_rcCanvas.Height(),&memDC,0,0,SRCCOPY);
	memDC.SelectObject(pOldBitmap);
	memDC.DeleteDC();
	bmpCanvas.Detach();
	DeleteObject(hBmpBk);
	CString ss = m_smCurrent->GetSelected()->GetTitle();
	if(ss.GetLength()>0)
		AfxGetMainWnd()->SetWindowText(ss);

//	dc.DrawText(_T("good morning!"),20,&rc,DT_CENTER | DT_VCENTER | DT_SINGLELINE);
	// Do not call CStatic::OnPaint() for painting messages
}

void CCanvas::DrawShortcutItem(CDC &dc)
{

	CShortcutItem *pItem = NULL;
	for(int i =0;i<CANVAS_LINE;i++)
	{
		for(int j = 0;j<CANVAS_ROW;j++)
		{
			pItem = m_smCurrent->GetFromVisibleAt(i*CANVAS_ROW+j);
			if(pItem)
			{
				HBITMAP hBmp = NULL;
				BITMAP bm;
				if(i*CANVAS_ROW+j == m_smCurrent->GetSelectedNumber()-1)
				{
					EnterCriticalSection(&m_CriticalSection);
					C_Image* & current = m_pAnimation->img[m_CurrentImage];
					LeaveCriticalSection(&m_CriticalSection);
					CDC SrcDC;
					SrcDC.CreateCompatibleDC(&dc);
					void *ppvbits;
					hBmp=CreateDIBSection(dc.GetSafeHdc(),current->pbmi,DIB_RGB_COLORS,(void**)&ppvbits,NULL,NULL);
					if(hBmp!=NULL)
					{
						HBITMAP hOld = (HBITMAP)SrcDC.SelectObject(hBmp);
						//						::GetObject(hBmp,sizeof(BITMAP),&bm);
						int iItemW = m_arrItemRect[i][j].right - m_arrItemRect[i][j].left;
						int iItemH = m_arrItemRect[i][j].bottom - m_arrItemRect[i][j].top;
						//						int iLeft = m_arrItemRect[i][j].left+(iItemW - current->Width)/2;
						//						int iTop = m_arrItemRect[i][j].top+(iItemH - current->Height)/2;
						//						int iWidth = current->Width<iItemW?current->Width:iItemW;
						//						int iHeight = current->Height<iItemH?current->Height:iItemH;
						SetDIBitsToDevice (SrcDC.GetSafeHdc(),0,0,
							current->Width,current->Height,0,0,0,current->Height,
							(LPVOID)current->Raster,current->pbmi,0);
						//定义源、掩码、透明绘制环境
						CDC MaskDC,TransDC;
						//定义掩码、透明位图
						HBITMAP hMaskBmp,hTransBmp;
						//						BITMAP bm;

						//创建源、掩码、透明绘制环境
						MaskDC.CreateCompatibleDC(&dc);
						TransDC.CreateCompatibleDC(&dc);

						//创建透明位图
						hTransBmp = CreateCompatibleBitmap(dc.GetSafeHdc(),current->Width,current->Height);
						//创建掩码位图
						hMaskBmp=CreateBitmap(current->Width,current->Height,1,1,NULL);

						//将透明位图对象选入到透明绘图环境
						HBITMAP hOldTransBmp = (HBITMAP)TransDC.SelectObject(hTransBmp);
						//将目标位图绘制到透明位图中
						TransDC.BitBlt(0,0,current->Width,current->Height,&dc,
							m_arrItemRect[i][j].left+current->xPos,
							m_arrItemRect[i][j].top+current->yPos,SRCCOPY);

						//设置背景为透明模式
						SrcDC.SetBkMode(TRANSPARENT);
						//设置背景色
						if (current->Transparent)
							SrcDC.SetBkColor(current->Transparent);
						else
						{
							COLORREF col = SrcDC.GetPixel(0,current->Height-1);
							SrcDC.SetBkColor(col);
						}

						HBITMAP hOldMaskBmp = (HBITMAP)MaskDC.SelectObject(hMaskBmp);

						//将源绘图环境绘制到掩码绘图环境中
						MaskDC.BitBlt(0,0,current->Width,current->Height,&SrcDC,0,0,SRCCOPY);

						//将源位图和透明位图进行异或操作融合
						TransDC.BitBlt(0,0,current->Width,current->Height,&SrcDC,0,0,SRCINVERT);
						//将透明位图和掩码位图进行与操作
						TransDC.BitBlt(0,0,current->Width,current->Height,&MaskDC,0,0,SRCAND);
						//再将源位图和透明位图进行异或操作
						TransDC.BitBlt(0,0,current->Width,current->Height,&SrcDC,0,0,SRCINVERT);

						//此时将透明位图绘制到目标设备上
						dc.BitBlt(m_arrItemRect[i][j].left+current->xPos,
							m_arrItemRect[i][j].top+current->yPos,
							current->Width,current->Height,&TransDC,
							0,
							0,SRCCOPY);

						//绘制绘图对象,并释放相应绘图环境和位图对象
						SrcDC.SelectObject(hOld);
						SrcDC.DeleteDC();
						DeleteObject(hBmp);

						TransDC.SelectObject(hOldTransBmp);
						DeleteObject(hTransBmp);
						TransDC.DeleteDC();

						MaskDC.SelectObject(hOldMaskBmp);
						MaskDC.DeleteDC();
						DeleteObject(hMaskBmp);
					}

				}
				else
				{
					hBmp = m_arrVisibleBmp[i*CANVAS_ROW+j];
					CBitmap bmp;
					bmp.Attach(hBmp);
					bmp.GetBitmap(&bm);
					bmp.Detach();
					int iItemW = m_arrItemRect[i][j].right - m_arrItemRect[i][j].left;
					int iItemH = m_arrItemRect[i][j].bottom - m_arrItemRect[i][j].top;
					int iLeft = m_arrItemRect[i][j].left+(iItemW - bm.bmWidth)/2;
					int iTop = m_arrItemRect[i][j].top+(iItemH - bm.bmHeight)/2;
					int iWidth = bm.bmWidth<iItemW?bm.bmWidth:iItemW;
					int iHeight = bm.bmHeight<iItemH?bm.bmHeight:iItemH;
					TransparentImage(dc.m_hDC,iLeft,iTop,iWidth,iHeight,hBmp,0,0,bm.bmWidth,bm.bmHeight,0xD4D0C8);/*0xBGR*/
				}
			}
			else
				break;
		}
	}
}
//画透明图片
void CCanvas::DrawTransParent(HBITMAP hBmp,int const x,int const y,int const cx,int const cy,
	int const srcx,int const srcy,CDC *pDC,COLORREF TransparentColor)
{
	//定义源、掩码、透明绘制环境
	CDC SrcDC,MaskDC,TransDC;
	//定义掩码、透明位图
	HBITMAP hMaskBmp,hTransBmp;
	BITMAP bm;

	//创建源、掩码、透明绘制环境
	SrcDC.CreateCompatibleDC(pDC);
	MaskDC.CreateCompatibleDC(pDC);
	TransDC.CreateCompatibleDC(pDC);

	//得到位图结构
	CBitmap bmp;
	bmp.Attach(hBmp);
	bmp.GetBitmap(&bm);
	bmp.Detach();
	//创建透明位图
	hTransBmp = CreateCompatibleBitmap(pDC->m_hDC,cx,cy);
	//创建掩码位图
	hMaskBmp=CreateBitmap(cx,cy,1,1,NULL);

	//将透明位图对象选入到透明绘图环境
	HBITMAP hOldTransBmp = (HBITMAP)TransDC.SelectObject(hTransBmp);
	//将目标位图绘制到透明位图中
	TransDC.BitBlt(0,0,cx,cy,pDC,srcx,srcy,SRCCOPY);

	//将实际位图对象选入源绘图环境
	HBITMAP hSrcBmp = (HBITMAP)SrcDC.SelectObject(hBmp);

	//设置背景为透明模式
	SrcDC.SetBkMode(TRANSPARENT);
	//设置背景色
	if (TransparentColor)
		SrcDC.SetBkColor(TransparentColor);
	else
	{
		COLORREF col = SrcDC.GetPixel(0,bm.bmHeight-1);
		SrcDC.SetBkColor(col);
	}

	HBITMAP hOldMaskBmp = (HBITMAP)MaskDC.SelectObject(hMaskBmp);

	//将源绘图环境绘制到掩码绘图环境中
	MaskDC.BitBlt(0,0,cx,cy,&SrcDC,0,0,SRCCOPY);

	//将源位图和透明位图进行异或操作融合
	TransDC.BitBlt(0,0,cx,cy,&SrcDC,0,0,SRCINVERT);
	//将透明位图和掩码位图进行与操作
	TransDC.BitBlt(0,0,cx,cy,&MaskDC,0,0,SRCAND);
	//再将源位图和透明位图进行异或操作
	TransDC.BitBlt(0,0,cx,cy,&SrcDC,0,0,SRCINVERT);

	//此时将透明位图绘制到目标设备上
	BOOL bRet = pDC->BitBlt(x,y,cx,cy,&TransDC,0,0,SRCCOPY);

	//绘制绘图对象,并释放相应绘图环境和位图对象
	SrcDC.SelectObject(hSrcBmp);
	SrcDC.DeleteDC();

	TransDC.SelectObject(hOldTransBmp);
	DeleteObject(hTransBmp);
	TransDC.DeleteDC();

	MaskDC.SelectObject(hOldMaskBmp);
	MaskDC.DeleteDC();
	DeleteObject(hMaskBmp);
}

int CCanvas::LoadAnimatedGif(LPTSTR FileName)
{
	Stop();
	EnterCriticalSection(&m_CriticalSection);
	m_AnimGif.Reset();
	m_pAnimation = NULL;
#ifdef _UNICODE
	char szTemp[MAX_PATH] = {0};
	WideCharToMultiByte(CP_ACP,0,FileName,_tcslen(FileName),szTemp,_tcslen(FileName),NULL,false);
	int Result=m_AnimGif.LoadGIF(szTemp);
#else
	int Result=m_AnimGif.LoadGIF(FileName);
#endif
	m_pAnimation=&m_AnimGif;
	LeaveCriticalSection(&m_CriticalSection);
	Play();

	return Result;
}
// fnThread: Thread function in charge of looping animation frames.
DWORD WINAPI CCanvas::fnThread (LPVOID lpParameter)
{
	do
	{
		Sleep(10);
		CCanvas* window;
		C_ImageSet* anim;
		window=(CCanvas*) lpParameter;
		if(window->m_pAnimation==NULL)
		{
			continue;
		}
		anim=window->m_pAnimation;
		window->m_bAnimationPlaying=TRUE;
		while (	anim->nLoops ? window->m_CurrentLoop < anim->nLoops : true )
		{
			while (1)
			{
				//window->DrawGif();
				::InvalidateRect(window->m_hWnd,NULL,FALSE);
				window->EnterCriticalSec();
				C_Image* & image = anim->img[window->m_CurrentImage];
				int iDelay = image->Delay?image->Delay:100;
				window->LeaveCriticalSec();

				if (window->m_CurrentImage < anim->nImages-1)
					++window->m_CurrentImage;
				else
				{
					window->Rewind();
//					window->m_CurrentImage=0; 
//					break;
				}
				Sleep (iDelay);
				// CurrentImage must always be valid!

			} 
			++window->m_CurrentLoop;
		}
		window->Rewind();
		window->m_bAnimationPlaying=FALSE;
	}while(1);
	return 0;
}

// Play: Start/Resume animation loop
void CCanvas::Play ()
{
	if (!m_bAnimationPlaying)
		if (m_pAnimation->nImages > 1)
			m_hThreadAnim = CreateThread(NULL,0,fnThread,this,0,&m_dwThreadIdAnim);
}

// Stop: Stop animation loop
void CCanvas::Stop ()
{
	if (m_bAnimationPlaying)
	{
		TerminateThread(m_hThreadAnim,0);
		Rewind();
		m_bAnimationPlaying=FALSE;
	}
}

// Rewind: Reset animation loop to its initial values
void CCanvas::Rewind ()
{
	m_CurrentLoop=0;
	m_CurrentImage=0;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -