win32窗口映射(部分)
先理解一下“窗口”与“视区”的概念。“窗口”是逻辑坐标下的矩形区域,“视区”是设备坐标系下的区域。根据“窗口”和“视区”的大小可以确定x方向和y方向的比例因子。
例子如下:
VOID OnPaint(HWND hwnd,WPARAM wParam,LPARAM lParam)
{
PAINTSTRUCT ps;
RECT rtClient;
GetClientRect(hwnd,&rtClient);
HDC hdc = BeginPaint(hwnd, &ps);
HDC hMemDC = CreateCompatibleDC(hdc);
HBITMAP hBitmap = CreateCompatibleBitmap(hdc, rtClient.right - rtClient.left, rtClient.bottom - rtClient.top);//rt为RECT变量;
SelectObject(hMemDC, hBitmap);
FillRect(hMemDC, &rtClient,WHITE_BRUSH); int OldMapMode =SetMapMode(hMemDC,MM_ANISOTROPIC);
//SetViewportOrgEx(hMemDC,0,rtClient.bottom,NULL);
POINT point = {,};
DPtoLP(hMemDC,&point,);
SetWindowOrgEx(hMemDC,-point.x,-point.y,NULL);
RECT rt = {-,-,,};
HBRUSH hBrush = CreateSolidBrush(RGB(,,));
FillRect(hMemDC,&rt,hBrush); //SetViewportOrgEx(hMemDC,0,0,NULL);
SetWindowOrgEx(hMemDC,,,NULL);
SetMapMode(hMemDC,OldMapMode);
BitBlt(hdc, , ,rtClient.right - rtClient.left, rtClient.bottom - rtClient.top,
hMemDC, , , SRCCOPY);
DeleteDC(hMemDC);
DeleteObject(hBitmap);
EndPaint(hwnd,&ps);
}
注:最后最好把设置都改回来(SetViewportOrgEx(hMemDC,0,0,NULL)或者SetWindowOrgEx(hMemDC,0,0,NULL))。
如果设置SetViewportOrgEx则比较简单,直接把逻辑坐标平移就好。
如何设置SetWindowOrgEx则比较麻烦,比如我想平移到100,100这个点,则先要调用DPtoLP进行转换,然后参数是转换后值的取反。(如果不调用DPtoLP函数,则逻辑坐标与设备坐标方向一样,如果不一样,则不需要取反)
比如居中的两种方法,直接写上书中的例子吧(理解就好,MFC版):
设置x轴正方向向右,y轴正方向向上,客户区中心为坐标系为原点。
(1)、设置视口
pDC->SetWindowExt(rc.Width(),rc.Height());
pDC->SetViewportExt(rc.Width(),-rc.Height());
pDC->SetViewportOrg(rc.Width()/2,rc.Heigth()/2);
(2)、设置窗口
pDC->SetWindowExt(rc.Width(),-rc.Height());
pDC->SetViewportExt(rc.Width(),rc.Height());
pDC->SetWindowOrg(-rc.Width()/2,rc.Heigth()/2);
分析第二种:由于设备与逻辑坐标比率是1比1,所以不需要转换坐标,准备偏移点为(rc.Width()/2,rc.Heigth()/2),由于逻辑与设备坐标系x方向相同,y方向不同,所以x取反,y不需要取反,结果为(-rc.Width()/2,rc.Heigth()/2);
第二种亦可以换成类似:(win32资料,这是我自己的测试代码)
SetWindowExtEx(hMemDC,rtClient.right,-2*rtClient.bottom,NULL);
SetViewportExtEx(hMemDC,rtClient.right,rtClient.bottom,NULL);
POINT point = {rtClient.right/2,rtClient.bottom/2};
DPtoLP(hMemDC,&point,1);
SetWindowOrgEx(hMemDC,-point.x,-point.y,NULL);
通过设置原点变成极坐标,然后可以方便计算。比如计算机图形学基础教程有一道题。
把一个半径为R的圆40等份,以每个等分点为圆心,以r为半径画圆。
RECT rtClient;
GetClientRect(hwnd,&rtClient);
PAINTSTRUCT ps;
HDC hdc = BeginPaint(hwnd,&ps);
SetMapMode(hdc,MM_ANISOTROPIC);
SetViewportExtEx(hdc,rtClient.right,rtClient.bottom,NULL);
SetWindowExtEx(hdc,rtClient.right,-rtClient.bottom,NULL);
POINT pt = {rtClient.right/,rtClient.bottom/};
DPtoLP(hdc,&pt,);
SetWindowOrgEx(hdc,-pt.x,-pt.y,NULL);
HBRUSH hBrush = (HBRUSH)GetStockObject(NULL_BRUSH);
HBRUSH hOldBrush = (HBRUSH)SelectObject(hdc,hBrush);
int bigR = ;
int smallR = ;
for(int i=;i<;++i)
{
int x = (int)(cos(0.0+*i)*bigR);
int y = (int)(sin(0.0+*i)*bigR);
Ellipse(hdc,x-smallR,y-smallR,x+smallR,y+smallR);
}
SetWindowOrgEx(hdc,,,NULL);
SelectObject(hdc,hOldBrush); EndPaint(hwnd,&ps);
效果图:

注:参考资料:http://www.cppblog.com/dragon/archive/2012/09/07/64005.html
win32窗口映射(部分)的更多相关文章
- 第一个手写Win32窗口程序
第一个手写Win32窗口程序 一 Windows编程基础 1 Win32应用程序的基本类型 1.1 控制台程序 不需要完善的Windows窗口,可以使用DOS窗口 的方式显示. 1.2 Win32窗口 ...
- WIN32窗口程序
// Win32.cpp : 定义应用程序的入口点. // #include "stdafx.h" #include "Win32.h" void TRACE( ...
- Win32窗口消息机制 x Android消息机制 x 异步执行
如果你开发过Win32窗口程序,那么当你看到android代码到处都有的mHandler.sendEmptyMessage和 private final Handler mHandler = new ...
- 如何在Console下面生成一个WIN32窗口
一个小挑战? VS2017里面,新建一个控制台工程,输入名字(你不需要也成,有默认的),得到一个控制台工程. 好了,生成的代码,如下: // Win32InConsole.cpp : This fil ...
- Win32窗口框架
Win32窗口框架 WindowClass 单例,负责窗口初始化注册和取消注册: 负责提供静态方法: 放在Window类内部,方便初始化时,wndProc(HandleMsgSetup)的赋值: cl ...
- Win32 - 窗口
Win32 - 窗口 目录 Win32 - 窗口 前言 流程图 创建项目 VS MinGW Win32API字符串 Unicode 和 ANSI 函数 TCHAR WinMain:Win32 Appl ...
- WIN32 窗口封装类实现
CQWnd.h窗口类定义 // QWnd.h: interface for the CQWnd class. // ////////////////////////////////////////// ...
- 解决WIN32窗口不响应WM_LBUTTONDBLCLK消息
原文链接: http://www.cnblogs.com/xukaixiang/archive/2012/05/27/2520059.html 今天在做一个软件时,发现win32创建的窗体不能响应WM ...
- win32窗口程序分析
1.分析消息的附加参数 例如:为了查看程序处理了哪些消息 在回调函数中调用输出函数,在控制台中输出消息的值:
随机推荐
- hdu 2602 简单0-1背包模板题
#include<stdio.h> #include<string.h> #define N 1100 int dp[N]; int main() { int n,t,m,a[ ...
- springboot 2.x 集成 drools 7.x
简介:springboot 2.0.4.RELEASE 集成 drools 7.11.0.Final 1.项目结构 2. pom.xml文件 <?xml version="1.0&qu ...
- HDU——2588 GCD
题目大意: 求1~N中与N的最大公约数大于M的个数 思路: 这个题是不是可以想到暴力枚举??对于每一组数据枚举与他的最大公约数大于m的数的个数. 是,这种做法没错误,但是保准你T成狗.... 我们至少 ...
- CocoaPods: 制作cocoapods国内镜像
制作cocoapods国内镜像∞ March 15, 2014 Tags:cocoapods 国内访问cocoapods spec repo速度非常慢,网络不好的话做一次pod update要等半个小 ...
- Cocos2d-x 3.x 图形学渲染系列十一
笔者介绍:姜雪伟.IT公司技术合伙人,IT高级讲师,CSDN社区专家,特邀编辑,畅销书作者,国家专利发明人;已出版书籍:<手把手教你架构3D游戏引擎>电子工业出版社和<Unity3D ...
- MapR CEO对2016大数据的5个预測
本文来源于我在InfoQ中文站翻译的文章,原文地址是:http://www.infoq.com/cn/news/2016/02/mapr-ceo-5-big-data-predictions MapR ...
- [vs执行报错] CRT detected that the application wrote to memory after end of heap buffer
CRT 是c/c++ run-time lib , 是程序执行时所需的核心库. 这个错误是由于以对内在操作的过程中.所写的地址超出了.所分配内在的边界 有个建议是: 1.内存申请多少释放多少,释放掉你 ...
- js字符转处理
那几个函数的应用: <script> //全局变量删不掉,而全局属性能删掉 var a=123; function aa () { b=321; delete b; } aa(); del ...
- Ubuntu 16.04 安装CodeBlocks
首先将软件源添加进来,就是运行以下命令 sudo add-apt-repository ppa:damien-moore/codeblocks-stable sudo apt-get update 完 ...
- 深入理解7816(1)---- 关于F/D和etu【转】
本文转载自:http://blog.sina.com.cn/s/blog_4df8400a0101gkss.html 深入理解7816(1)---- 关于F/D和etu 对于刚接触智能卡的工程师来说, ...