【问题标题】:Confusion in two MFC GDI function混淆了两个 MFC GDI 函数
【发布时间】:2011-08-06 19:12:18
【问题描述】:

祝大家有美好的一天。这是我在这里的第一篇文章。 我正在阅读“使用 MFC 编程 Windows - J Prosise (MS Press)”
在第二章中我遇到了 2 个让我很困惑的 GDI 函数,我引用了这段文字:

SetViewportOrg 和 SetWindowOrg 很容易混淆,但是它们之间的区别其实是很清楚的。使用 SetViewportOrg 将视口原点更改为 (x,y) 会告诉 Windows 将逻辑点 (0,0) 映射到设备点 (x,y)。使用 SetWindowOrg 将窗口原点更改为 (x,y) 基本上是相反的,告诉 Windows 将逻辑点 (x,y) 映射到设备点 (0,0) - 显示表面的左上角。在 MM_TEXT 映射模式下,两个函数之间唯一真正的区别是 x 和 y 的符号。在其他映射模式中,还有更多的功能,因为 SetViewportOrg 处理设备坐标,而 SetWindowOrg 处理逻辑坐标

我真的对此感到困惑,就像我们将视点原点更改为 (50,50) 然后使用 dc.ellipse (0,0,50,50) 它将从设备点 (50, 50) 作为原点,但是如果我们将窗口原点更改为 (50,50) 是否意味着现在逻辑点 (50,50) 将映射到 (0,0) 如果是这样,椭圆不会超出客户端上部区域?映射模式是 MM_LOWENGLISH 还是别的什么?届时情况将如何变化?如果有人能对此事有所了解,我将不胜感激

【问题讨论】:

    标签: visual-c++ mfc gdi coordinate-systems


    【解决方案1】:

    这是一个相当复杂的问题,主要是因为您要处理两组完全不同的坐标,并且(只是为了让事情变得有趣)Windows 使用的术语与世界其他地方使用的术语大致相反。

    简短的回答是根本不要使用SetWindowOrg。我很确定我从来没有在实际代码中很好地使用过它。

    SetViewportOrg 很有用,而且它确实比描述听起来更简单——你只是在挑选你想要的来源。例如,您可能希望您的绘图从窗口的左下角开始。你可以这样做:

    CRect rect;
    GetClientRect(&rect);
    
    pDC->SetViewportOrg(0, rect.Height());
    

    OTOH,如果您希望能够同时绘制负数和正数,您可能希望 x=0 位于窗口的左侧,但 y=0 位于窗口顶部和底部之间的中间窗户。你会这样做:

    // get rect as above.
    pDC->SetViewportOrg(0, rect.Height()/2);
    

    如果您希望窗口的中心是您的 (0,0),您可以使用:

    // again, get rect like above
    pDC->SetViewportOrg(rect.Width()/2, rect.Height()/2);
    

    请注意,其中任何一个的主要使用都是将映射模式设置为 MM_ISOTROPIC 或 MM_ANISOTROPIC - 您可以在这些位置完全自行设置坐标。使用其他模式[MM_TEXT or MM_(LO|HI)(ENGLISH|METRIC)],它会自动为您设置原点。

    【讨论】:

    • 感谢您的帮助。起初我也想坚持 KISS 原则,但一遍又一遍地阅读它以完全掌握它让我感到困惑。
    猜你喜欢
    • 2011-11-09
    • 2020-07-10
    • 2021-11-21
    • 1970-01-01
    • 1970-01-01
    • 2013-12-01
    • 2021-07-27
    • 1970-01-01
    • 2014-07-15
    相关资源
    最近更新 更多