【问题标题】:Cannot edit labels in a CListCtrl无法编辑 CListCtrl 中的标签
【发布时间】:2010-10-20 02:26:57
【问题描述】:

我正在使用 MFC 功能包构建一个项目。这个项目是否有一个包含CView 的窗口,其中包含一个CListCtrl 派生对象。该对象包含LVS_EDITLABELS 标志。

不知何故,我无法通过两次单击(不是双击)图标标签来编辑CListCtrl 图标标签。在我单击选择项目后,第二次单击只会使项目闪烁(向下按钮将文本背景变为白色,向上按钮将其变为蓝色)并且永远不会出现编辑控件。

我将这个问题简化为最简单的形式,即使使用普通的 CListCtrl 对象,我也无法编辑标签。

我还发现:

  • 这个问题出现在 VS2008 中。在VS2003内置的类似项目中不会出现这种情况。

  • 如果我构建 CListView 而不是 CView+CListCtrl,我可以编辑标签。

  • 如果我构建一个CFormView 并将CListCtrl 放在资源对话​​框中,我也可以编辑标签。

下面是一些最简单形式的代码:.h 文件:

// vwTerminaisTeste.h
//
#pragma once
// vwTerminaisTeste view

    class vwTerminaisTeste : public CView
{
    DECLARE_DYNCREATE(vwTerminaisTeste)

protected:
    vwTerminaisTeste();           // protected constructor used by dynamic creation
    virtual ~vwTerminaisTeste();

    CListCtrl m_lstTerminais;

protected:
    DECLARE_MESSAGE_MAP()
    virtual void OnDraw(CDC* /*pDC*/);
public:
    afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct);
    afx_msg void OnSize(UINT nType, int cx, int cy);
};

和 .cpp 文件:

// vwTerminaisTeste.cpp : implementation file
//

#include "stdafx.h"
#include "vwTerminaisTeste.h"

// vwTerminaisTeste

IMPLEMENT_DYNCREATE(vwTerminaisTeste, CView)
vwTerminaisTeste::vwTerminaisTeste()
{
}

vwTerminaisTeste::~vwTerminaisTeste()
{
}

BEGIN_MESSAGE_MAP(vwTerminaisTeste, CView)
    ON_WM_CREATE()
    ON_WM_SIZE()
END_MESSAGE_MAP()

// vwTerminaisTeste message handlers

void vwTerminaisTeste::OnDraw(CDC* /*pDC*/)
{
    CDocument* pDoc = GetDocument();
}

int vwTerminaisTeste::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
    if (CView::OnCreate(lpCreateStruct) == -1)
        return -1;

    m_lstTerminais.Create(WS_CHILD | WS_VISIBLE | LVS_EDITLABELS, CRect(0,0,1,1), this, 0);
    m_lstTerminais.InsertItem(0, "Teste", 0);

    return 0;
}

void vwTerminaisTeste::OnSize(UINT nType, int cx, int cy)
{
    CView::OnSize(nType, cx, cy);

    if (IsWindow(m_lstTerminais.GetSafeHwnd()))
        m_lstTerminais.MoveWindow(0, 0, cx, cy);
}

这样我无法编辑标签。 要将其更改为CListView,我只需将CView 替换为CListView,将m_lstTerminais 替换为GetListCtrl(),并删除OnCreateOnSize 实现。这样就成功了。

注意:vwTerminaisTeste 是从 CMDIChildWndEx 派生类中的 CSplitterWndEx 创建的。

【问题讨论】:

  • 请提供一些代码。 CListCtr 上的所有样式标志(基本和扩展)是什么?你能显示填充列表的代码吗?
  • 提示:如果您真的想回答这个问题,请牺牲您的一些声誉并为其提供赏金。然后人们会努力并尝试重现错误等。stackoverflow.com/questions/483019/…
  • 为什么特别需要CView+CListCtrl而不是CListView?
  • 因为我需要使用 CListCtrl 派生类而不是 CListCtrl/CListView。这个类也有其他形式使用,我不想重复。
  • 感谢您澄清问题。我已经删除了我的答案,因为它不能解决你的问题。

标签: c++ visual-c++ mfc mfc-feature-pack clistctrl


【解决方案1】:

没有人解决这个问题,但我设法通过将 CView 更改为 CFormView 并使用 ListView 控件构建资源对话框,将其附加到 CListCtrl 派生类来解决它。

如果有人对我如何完全解决这个问题有任何建议,我将不胜感激。

【讨论】:

    【解决方案2】:

    这听起来可能是焦点或命令路由问题,尽管这并不能解释为什么它在 VS2003 中可以正常工作。您可以尝试将命令和/或焦点消息从拆分器 ctrl 路由到 vwTerminaisTeste,和/或从 MDIChild 到拆分器。如果您还没有,您可能需要派生自己的拆分器窗口。命令/焦点转发类似于...

    BEGIN_MESSAGE_MAP(MySplitter, CSplitterWnd)
      ON_WM_SETFOCUS()
    END_MESSAGE_MAP(...)
    
    void MySplitter::OnSetFocus(CWnd* pOldWnd)
    {
      // forward focus to the view window
      m_vwTerminaisTeste.SetFocus();
    }
    
    BOOL MySplitter::OnCmdMsg(UINT nID, int nCode, void* pExtra, AFX_CMDHANDLERINFO* pHandlerInfo)
    {
      // let the view have first crack at the command
      if (m_vwTerminaisTeste.OnCmdMsg(nID, nCode, pExtra, pHandlerInfo))
        return TRUE;
    
      // otherwise, do default handling
      return MySplitter::OnCmdMsg(nID, nCode, pExtra, pHandlerInfo);
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-10-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多