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

📄 area.cpp

📁 Windows 图形编程 书籍
💻 CPP
📖 第 1 页 / 共 4 页
字号:
//-----------------------------------------------------------------------------------//
//              Windows Graphics Programming: Win32 GDI and DirectDraw               //
//                             ISBN  0-13-086985-6                                   //
//                                                                                   //
//  Written            by  Yuan, Feng                             www.fengyuan.com   //
//  Copyright (c) 2000 by  Hewlett-Packard Company                www.hp.com         //
//  Published          by  Prentice Hall PTR, Prentice-Hall, Inc. www.phptr.com      //
//                                                                                   //
//  FileName   : area.cpp						                                     //
//  Description: Area fill demo program, Chapter 9                                   //
//  Version    : 1.00.000, May 31, 2000                                              //
//-----------------------------------------------------------------------------------//

#define STRICT
#define _WIN32_WINNT 0x0500
#define WINVER 0x0500
#define WIN32_LEAN_AND_MEAN
#define OEMRESOURCE

#include <windows.h>
#include <assert.h>
#include <tchar.h>
#include <math.h>

#include "..\..\include\win.h"
#include "..\..\include\Canvas.h"
#include "..\..\include\Status.h"
#include "..\..\include\FrameWnd.h"
#include "..\..\include\Affine.h"
#include "..\..\include\Pen.h"
#include "..\..\include\Color.h"
#include "..\..\include\GDIObject.h"
#include "..\..\include\areafill.h"
#include "..\..\include\button.h"
#include "..\..\include\region.h"

#include "Resource.h"

class KMyCanvas : public KCanvas
{
	virtual void    OnDraw(HDC hDC, const RECT * rcPaint);
	virtual LRESULT WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
	virtual	BOOL    OnCommand(WPARAM wParam, LPARAM lParam);

	int		m_test;
	int		m_lastx;
	int		m_lasty;

	void SetTest(int test);
	void DrawCrossHair(HDC hDC, bool on);

	void TestDither(HDC hDC);
	void TestHatch(HDC hDC);
	void TestSysColorBrush(HDC hDC);

	void TestRectangle(HDC hDC);
	void TestDrawFrameControl(HDC hDC);

	void TestEllipse(HDC hDC);
	void TestPieChart(HDC hDC);

	void TestPolyFillMode(HDC hDC);
	void TestFillPath(HDC hDC);

	void TestRegion(HDC hDC);
	void TestRegionOper(HDC hDC);
	void TestRegionPaint(HDC hDC);
	void TestGradientFill(HDC hDC);

	KRectButton    rbutton;
	KEllipseButton ebutton;

public:

	KMyCanvas()
	{

		m_test  = -1;
		m_lastx = -1;
		m_lasty = -1;
	}
};

void KMyCanvas::SetTest(int test)
{
	m_test = test;

	HMENU hMain = GetMenu(GetParent(m_hWnd));

	TCHAR Temp[MAX_PATH];

	_tcscpy(Temp, _T("Areas - "));

	GetMenuString(hMain, m_test, Temp + _tcslen(Temp), 
		sizeof(Temp)/sizeof(TCHAR) - _tcslen(Temp), MF_BYCOMMAND);

	SetWindowText(GetParent(m_hWnd), Temp);
}


BOOL KMyCanvas::OnCommand(WPARAM wParam, LPARAM lParam)
{
	switch ( LOWORD(wParam) )
	{
		case IDM_TEST_DITHER:
		case IDM_TEST_HATCHBRUSH:
		case IDM_TEST_SYSCOLORBRUSH:
		case IDM_TEST_RECTANGLE:
		case IDM_TEST_DRAWFRAMECONTROL:	
		case IDM_TEST_ELLIPSE:
		case IDM_TEST_PIECHART:
		case IDM_TEST_POLYFILLMODE:
		case IDM_TEST_FILLPATH:
		case IDM_TEST_REGION:
		case IDM_TEST_REGIONOP:
		case IDM_TEST_REGIONPAINT:
		case IDM_TEST_GRADIENTFILL:
			SetTest( LOWORD(wParam) );
			InvalidateRect(m_hWnd, NULL, TRUE);
			return TRUE;

		case IDM_FILE_EXIT:
			DestroyWindow(GetParent(m_hWnd));
			return TRUE;
	}

	return FALSE;	// not processed
}


inline void Line(HDC hDC, int x1, int y1, int x2, int y2)
{
	MoveToEx(hDC, x1, y1, NULL);
	LineTo(hDC, x2, y2);
}

void KMyCanvas::DrawCrossHair(HDC hDC, bool on)
{
	if ( (m_lastx<0) || (m_lasty<0) )
		return;

	RECT rect;

	GetClientRect(m_hWnd, & rect);

	SetROP2(hDC, R2_XORPEN);
	
	{
		KPen pen(PS_DOT, 0, RGB(0, 0, 0xFF), hDC);

		Line(hDC, rect.left, m_lasty, rect.right, m_lasty);
		Line(hDC, m_lastx, rect.top, m_lastx, rect.bottom);
	}
}


void ZoomRect(HDC hDC, int x0, int y0, int x1, int y1, int dx, int dy, int zoom)
{
	// use black pen for border
	HGDIOBJ hOld = SelectObject(hDC, GetStockObject(BLACK_PEN));

	for (int y=y0; y<y1; y++)
	for (int x=x0; x<x1; x++)
	{
		COLORREF c = GetPixel(hDC, x, y);

		HBRUSH  hBrush = CreateSolidBrush(c);
		HGDIOBJ hOld   = SelectObject(hDC, hBrush);

		Rectangle(hDC, dx+(x-x0)*(zoom+1), dy+(y-y0)*(zoom+1), 
			dx+(x-x0)*(zoom+1)+zoom+2, 
			dy+(y-y0)*(zoom+1)+zoom+2);
		SelectObject(hDC, hOld);
		DeleteObject(hBrush);
	}

	SelectObject(hDC, hOld);
}


void KMyCanvas::TestDither(HDC hDC)
{
	SetViewportOrgEx(hDC, 10, 10, NULL);

	// no outline for dither rectangle
	SelectObject(hDC, GetStockObject(NULL_PEN)); 

	for (int y=0; y<16; y++)
	for (int x=0; x<16; x++)
	{
		HBRUSH  hBrush = CreateSolidBrush(RGB(y*16+x, y*16+x, 0xFF));
		HGDIOBJ hOld   = SelectObject(hDC, hBrush);

		Rectangle(hDC, 235+x*10, y*10, 235+x*10+9, y*10+9);

		if ( x==y ) // zoom in color on diagonal line 
			ZoomRect(hDC, 235+x*10, y*10, 235+x*10+8, y*10+8, 
				80*(x%8), 180+80*(x/8), 6);
		
		SelectObject(hDC, hOld);
		DeleteObject(hBrush);
	}
	SelectObject(hDC, GetStockObject(BLACK_PEN));

	SetViewportOrgEx(hDC, 0, 0, NULL);
}

TCHAR * HS_Names [] = 
{	_T("HS_HORIZONTAL"),
	_T("HS_VERTICAL"),
	_T("HS_FDIAGONAL"),
	_T("HS_BDIAGONAL"),
	_T("HS_CROSS"),
	_T("HS_DIAGCROSS")
};


void Frame(HDC hDC, int x0, int y0, int x1, int y1)
{
	unsigned short ChessBoard[] = { 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55 };

	HBITMAP hBitmap = CreateBitmap(8, 8, 1, 1, ChessBoard);
	HBRUSH hBrush = CreatePatternBrush(hBitmap);
	DeleteObject(hBitmap);

	HGDIOBJ hOld  = SelectObject(hDC, hBrush);

	// PS_ALTERNATE rectangle
	PatBlt(hDC, x0, y0, x1-x0, 1, PATCOPY);
	PatBlt(hDC, x0, y1, x1-x0, 1, PATCOPY);
	PatBlt(hDC, x0, y0, 1, y1-y0, PATCOPY);
	PatBlt(hDC, x1, y0, 1, y1-y0, PATCOPY);
	
	int old = SetROP2(hDC, R2_MASKPEN);
	Rectangle(hDC, x0+5, y0+5, x1-5, y1-5);
	SetROP2(hDC, old);

//	int old = SetROP2(hDC, R2_MASKPEN);
//	SetBkColor(hDC, RGB(0xFF, 0xFF, 0xFF));
//	SetTextColor(hDC, RGB(0, 0, 0));
//	Rectangle(hDC, x0+5, y0+5, x1-5, y1-5);

//	SetBkColor(hDC, RGB(0x0, 0x0, 0x0));
//	SetTextColor(hDC, RGB(0xFF, 0, 0));
//	SetROP2(hDC, R2_MERGEPEN);
//	Rectangle(hDC, x0+5, y0+5, x1-5, y1-5);

	SetROP2(hDC, old);

	SelectObject(hDC, hOld);
	DeleteObject(hBrush);
}

void SemiFillRect(HDC hDC, int left, int top, int right, int bottom, COLORREF color)
{
	int nSave = SaveDC(hDC);

	const unsigned short ChessBoard[] = { 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55 };

	HBITMAP hBitmap = CreateBitmap(8, 8, 1, 1, ChessBoard);
	HBRUSH hBrush = CreatePatternBrush(hBitmap);
	DeleteObject(hBitmap);
	HGDIOBJ hOldBrush = SelectObject(hDC, hBrush);
	HGDIOBJ hOldPen   = SelectObject(hDC, GetStockObject(NULL_PEN));

	SetROP2(hDC, R2_MASKPEN);
	SetBkColor(hDC, RGB(0xFF, 0xFF, 0xFF));
	SetTextColor(hDC, RGB(0, 0, 0));
	Rectangle(hDC, left, top, right, bottom);

	SetROP2(hDC, R2_MERGEPEN);
	SetBkColor(hDC, RGB(0x0, 0x0, 0x0));
	SetTextColor(hDC, color);
	Rectangle(hDC, left, top, right, bottom);

	SelectObject(hDC, hOldBrush);
	SelectObject(hDC, hOldPen);
	DeleteObject(hBrush);

	RestoreDC(hDC, nSave);
}

void KMyCanvas::TestHatch(HDC hDC)
{
	int nSave = SaveDC(hDC);

	SetViewportOrgEx(hDC, 24, 24, NULL);

	SelectObject(hDC, GetStockObject(NULL_PEN));
	
	typedef enum { GAP = 120 };

	for (int hs= HS_HORIZONTAL; hs<=HS_DIAGCROSS; hs++)
	{
		HBRUSH hBrush = CreateHatchBrush(hs, RGB(0, 0, 0xFF));
		HGDIOBJ hOld  = SelectObject(hDC, hBrush);

		SetBkColor(hDC, RGB(0xFF, 0xFF, 0));
		Rectangle(hDC, hs*GAP, 0, hs*GAP+89, 89);

		SetBkColor(hDC, RGB(0xFF, 0xFF, 0xFF));
		
		SetTextAlign(hDC, TA_CENTER);
		TextOut(hDC, hs*GAP+88/2, 98, HS_Names[hs-HS_HORIZONTAL], _tcslen(HS_Names[hs-HS_HORIZONTAL]));

		SelectObject(hDC, hOld);
		DeleteObject(hBrush);

		ZoomRect(hDC, hs*GAP, 0, hs*GAP+8, 8, hs*GAP, 120, 8);
	}

/*	SelectObject(hDC, GetStockObject(NULL_PEN));

	SetBkColor(hDC, RGB(0xFF, 0xFF, 0));

	for (int i=0; i<8; i++)
	{
		SetViewportOrgEx(hDC, 24+i*32+i, 300, NULL);

		HBRUSH  hBrush = CreateHatchBrush(HS_FDIAGONAL, RGB(0, 0, 0xFF));
		HGDIOBJ hOld   = SelectObject(hDC, hBrush);
	
		Rectangle(hDC, 0, 0, 32+2, 32+2);

		SelectObject(hDC, hOld);
		DeleteObject(hBrush);
	}

	SetBkColor(hDC, RGB(0xFF, 0xFF, 0xFF));
*/

	// Pattern Brushes Demo
	HINSTANCE hCards = LoadLibrary("cards.dll");

	for (int i=0; i<4; i++)
	{
		HBRUSH hBrush;
		int    width, height;

		switch ( i )
		{
			case 0:
				{
					HBITMAP hBitmap = LoadBitmap(hCards, MAKEINTRESOURCE(52));
					BITMAP  bmp;

					GetObject(hBitmap, sizeof(bmp), & bmp);
					width = bmp.bmWidth; height = bmp.bmHeight;

					hBrush = CreatePatternBrush(hBitmap);
					DeleteObject(hBitmap);
				}
				break;

			case 1:
				{
					HRSRC hResource = FindResource(hCards, MAKEINTRESOURCE(52-14), RT_BITMAP);
					HGLOBAL hGlobal = LoadResource(hCards, hResource);
	
					hBrush  = CreateDIBPatternBrushPt(LockResource(hGlobal), DIB_RGB_COLORS);
					width   = ((BITMAPCOREHEADER *) hGlobal)->bcWidth; // old DIB format
					height  = ((BITMAPCOREHEADER *) hGlobal)->bcHeight;// old DIB format
				}
				break;

			case 2:
			case 3:
				{
					HRSRC hResource = FindResource(hCards, MAKEINTRESOURCE(52-28), RT_BITMAP);
					HGLOBAL hGlobal = LoadResource(hCards, hResource);

					hBrush  = CreateDIBPatternBrush(hGlobal, DIB_RGB_COLORS);
					width   = ((BITMAPCOREHEADER *) hGlobal)->bcWidth;  // old DIB format
					height  = ((BITMAPCOREHEADER *) hGlobal)->bcHeight; // old DIB format
				}
		}
		
		HGDIOBJ hOld  = SelectObject(hDC, hBrush);

		POINT P = { i*140+20 + width*i/4, 250 + height*i/4 };
		LPtoDP(hDC, &P, 1);
		SetBrushOrgEx(hDC, P.x, P.y, NULL); // make sure cards aligned with rectangle
	
		Rectangle(hDC, i*140+20, 250, i*140+20+width*3/2+1, 250+height*3/2+1);
	
		SelectObject(hDC, hOld);
		DeleteObject(hBrush);

		if ( i==3 )
		{
			Frame(hDC, i*140+20-10, 250-10, i*140+20+width*3/2+10, 250+height*3/2+10);

//			SemiFillRect(hDC, i*140+20-10, 250-10, i*140+20+width*3/2+10, 250+height*3/2+10, RGB(0, 0, 0xFF));

			ZoomRect(hDC, i*140+20-10, 250-10, i*140+20+20, 250+20,
						  580, 240, 6);
		}			
	}

	RestoreDC(hDC, nSave);
}


LRESULT KMyCanvas::WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
	LRESULT lr;

	switch( uMsg )
	{
		case WM_CREATE:
			m_hWnd = hWnd;
			SetTest(IDM_TEST_DITHER);

			rbutton.DefineButton(10, 10, 50, 50);
			ebutton.DefineButton(70, 10, 50, 50);
			return 0;

		case WM_PAINT:
			{
				PAINTSTRUCT ps; 

				HDC hDC = BeginPaint(m_hWnd, &ps);

				OnDraw(hDC, &ps.rcPaint);

				if ( m_test== IDM_TEST_REGIONOP )
				{
					rbutton.DrawButton(hDC);
					ebutton.DrawButton(hDC);
				}

				DrawCrossHair(hDC, true);
				
				EndPaint(m_hWnd, &ps);
			}
			return 0;

		case WM_MOUSEMOVE:
			{
				HDC hDC = GetDC(hWnd);

				DrawCrossHair(hDC, false);	// erase

				m_lastx = LOWORD(lParam); m_lasty = HIWORD(lParam);

				if ( m_test==IDM_TEST_REGIONOP )
				{
					rbutton.UpdateButton(hDC, lParam);
					ebutton.UpdateButton(hDC, lParam);
				}

				DrawCrossHair(hDC, true);	// restore
				ReleaseDC(hWnd, hDC);
				
				TCHAR temp[32];
				wsprintf(temp, _T("(%d, %d)"), m_lastx, m_lasty);
				m_pStatus->SetText(0, temp);
		
			}
			return 0;
		
		case WM_LBUTTONDOWN:
			{
				if ( m_test==IDM_TEST_REGIONOP )

⌨️ 快捷键说明

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