【问题标题】:CClientDC and DC not Drawing on ChtmlEditCtrlCClientDC 和 DC 不在 ChtmlEditCtrl 上绘图
【发布时间】:2016-06-13 19:48:42
【问题描述】:

大家好,我正在 MFC 中使用 CHtmlEditCtrl。我想在处理右键单击事件的函数中绘制一些随机矩形和线条。

ChtmlEditCtrl 控件是使用这个 sn-p 从静态创建的:

bool CHtmlEditCtrlEx::CreateFromStatic( UINT nID, CWnd* pParent ) {
    CStatic wndStatic;
    if ( !wndStatic.SubclassDlgItem(nID, pParent)) {
        return false;
    }
    CRect rc;
    wndStatic.GetWindowRect( &rc );
    pParent->ScreenToClient( &rc );
    if (Create( 0, (WS_CHILD | WS_VISIBLE), rc, pParent, nID, 0 )) {
        ...
}

然后我这样重写 CWnd::pretranslate() 函数:

  CClientDC dcc(this);
    switch (pMsg->message) {

        case WM_RBUTTONUP:  // Right-click
            // Just some dummy values
            DrawSquigly(dcc, 600, 240, 20);
            break;

    }

DrawSquigly() 函数定义如下:

void CHtmlEditCtrlEx::DrawSquigly(CDC &dcc, int iLeftX, int iWidth, int iY)
{
    CAMTrace trace;
    trace.Trace("Drawing Squiggly");
    //dcc.TextOut(10, 10, CString(_T("I used a client DC!")));

    CPen * oldPen;
    CBrush * oldBrush;
    oldPen = (CPen *) dc.SelectStockObject(WHITE_PEN);
    dcc.MoveTo(5,10);
    dcc.LineTo(80, 10);
    dcc.SelectObject(oldPen);

    //GDI 002_2: Create custom pen with different Line thickness.
    CPen thick_pen(PS_SOLID, 3, RGB(0,255,0));
    oldPen = dc.SelectObject(&thick_pen);
    dcc.MoveTo(5, 20);
    dcc.LineTo(80,20);
    dcc.SelectObject(oldPen);

    //GDI 002_3: Create a Rectangle now
    dcc.Draw3dRect(5,30,80,70, RGB(25,25,255), RGB(120,120,120));

    //GDI 002_4: Create a Brush that we can use for filling the 
    // closed surfaces
    CBrush brush(RGB(255,0,255));
    oldBrush = dc.SelectObject(&brush);
    dcc.Rectangle(5,110,80,140);
    dcc.SelectObject(oldBrush);

    //GDI 002_5: Hatch Brush is useful to apply a pattern in stead 
    //of solid fill color
    CBrush* hatBrush = new CBrush();
    hatBrush->CreateHatchBrush(HS_CROSS, RGB(255,0,255));
    oldBrush = dc.SelectObject(hatBrush);
    dcc.FillRect(new CRect(5,160,80,190), hatBrush);
    dcc.SelectObject(oldBrush);
}

但是当我右键单击时没有绘图发生。我想我错过了一些东西,特别是因为我是 MFC 的新手。

我在事件处理程序的顶部添加了一个跟踪,以确保该函数正在被调用。

谁能指出正确的方向?

【问题讨论】:

  • 您是从CWinApp::PreTranslateMessage() 的覆盖中调用它吗?那不是处理事件的正确位置。
  • 函数有dc参数时,dcc的作用是什么?
  • 是的,我正在调用 CWnd::PreTranslateMessage 的覆盖,我在这里处理了这些事件,因为在包含 CHtmlEditCtrl 的视图上会有几个客户区域。为了测试该函数是否被调用,我在顶部添加了一个跟踪,它跟踪出来,但没有绘制。

标签: c++ mfc gdi cdc


【解决方案1】:

您的代码中实际上有 2 个设备上下文:一个在调用中作为参数传递(我们不知道它来自哪里),另一个在绘图函数中本地创建。

通常,当系统给你一个 DC 时,它希望你在其中画一些东西,而不是你画到其他东西。

如果您正在处理的窗口是分层的,则系统会为您提供一个您在其中绘制的内存上下文 - 在清除时 - 使用一些窗口管理器效果将 blitted 到窗口本身。

我的怀疑是-通过分配第二个 dc- 当从消息处理程序返回时清除第一个(您留空)时,您的绘图被覆盖。

【讨论】:

  • 我在调用处理程序后延迟了 5 秒以验证您的假设:DrawSquigly(dc, 600, 240, 20);睡眠(5000);但仍然看不到任何图纸。
  • 屏幕的刷新不一定是同步发生的。如果你让进程同步进入睡眠状态,你可能会在刷新之前暂停。
  • 我已经编辑了上面的问题,在这种情况下您的建议是什么?
  • 调用 DrawSquigly(dc, 600, 240, 20) 时传递的 dc 是从哪里得到的??
  • 就在 CWnd::pretranslate 函数中的 message swtich 语句之上,但我什至没有使用它,我试图从事件处理程序中获取另一个以测试它是否有效。
猜你喜欢
  • 1970-01-01
  • 2016-05-22
  • 2017-11-05
  • 2013-06-29
  • 2014-02-28
  • 1970-01-01
  • 2011-11-10
  • 1970-01-01
  • 2018-05-18
相关资源
最近更新 更多