debug下编译运行没有问题
release下的情况是:在没有显示出edit时,随便怎么操作都没有问题
但是一旦双击某一项出现编辑框后,如果再去点别的控件就会出错,说什么内存不可写
经过分析我发现问题在于一旦edit控件丢失焦点就会出错,
我把代码中有关设置edit焦点的语句注释后就没有问题了
但是要编辑就得在edit中呀。百思不得其解。各位兄弟姐妹们有空帮忙看看到底怎么回事先谢谢了下面是完整的代码://头文件
#if !defined(AFX_NEWLIST_H__F4C02AFA_F4FA_42D8_8765_28C8D2FD7FB4__INCLUDED_)
#define AFX_NEWLIST_H__F4C02AFA_F4FA_42D8_8765_28C8D2FD7FB4__INCLUDED_#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
// EditListCtrl.h : header file
//
#define IDC_EDITLISTCTRL_EDIT_20050228 20050228
/////////////////////////////////////////////////////////////////////////////
// CEditListCtrl windowclass CEditListCtrl : public CListCtrl
{
// Construction
public:
CEditListCtrl();// Attributes
public:
// CEdit *ed;
CEdit edit1; //编辑框
int CurRow,CurCol;
CRect arect;
// Operations
public:// Overrides
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CEditListCtrl)
//}}AFX_VIRTUAL// Implementation
public:
int HitTestEx(CPoint& Point, int* pColumn);
void EditSubItem(int Item, int Column);
void EditCellShow(DWORD dwStyle,CRect rect,int Item,int SubItem);
void UpdateText();
BOOL IsEditing();
virtual ~CEditListCtrl();
virtual BOOL PreTranslateMessage(MSG* pMsg);
// Generated message map functions
protected:
//{{AFX_MSG(CEditListCtrl)
afx_msg void OnLButtonDblClk(UINT nFlags, CPoint point);
afx_msg void OnKillFocus(CWnd* pNewWnd);
afx_msg void OnItemchanging(NMHDR* pNMHDR, LRESULT* pResult);
afx_msg void OnKillfocusedit1(NMHDR* pNMHDR, LRESULT* pResult);
afx_msg VOID OnChangeEditD();
//}}AFX_MSG DECLARE_MESSAGE_MAP()
};///////////////////////////////////////////////////////////////////////////////{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.#endif // !defined(AFX_NEWLIST_H__F4C02AFA_F4FA_42D8_8765_28C8D2FD7FB4__INCLUDED_)
release下的情况是:在没有显示出edit时,随便怎么操作都没有问题
但是一旦双击某一项出现编辑框后,如果再去点别的控件就会出错,说什么内存不可写
经过分析我发现问题在于一旦edit控件丢失焦点就会出错,
我把代码中有关设置edit焦点的语句注释后就没有问题了
但是要编辑就得在edit中呀。百思不得其解。各位兄弟姐妹们有空帮忙看看到底怎么回事先谢谢了下面是完整的代码://头文件
#if !defined(AFX_NEWLIST_H__F4C02AFA_F4FA_42D8_8765_28C8D2FD7FB4__INCLUDED_)
#define AFX_NEWLIST_H__F4C02AFA_F4FA_42D8_8765_28C8D2FD7FB4__INCLUDED_#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
// EditListCtrl.h : header file
//
#define IDC_EDITLISTCTRL_EDIT_20050228 20050228
/////////////////////////////////////////////////////////////////////////////
// CEditListCtrl windowclass CEditListCtrl : public CListCtrl
{
// Construction
public:
CEditListCtrl();// Attributes
public:
// CEdit *ed;
CEdit edit1; //编辑框
int CurRow,CurCol;
CRect arect;
// Operations
public:// Overrides
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CEditListCtrl)
//}}AFX_VIRTUAL// Implementation
public:
int HitTestEx(CPoint& Point, int* pColumn);
void EditSubItem(int Item, int Column);
void EditCellShow(DWORD dwStyle,CRect rect,int Item,int SubItem);
void UpdateText();
BOOL IsEditing();
virtual ~CEditListCtrl();
virtual BOOL PreTranslateMessage(MSG* pMsg);
// Generated message map functions
protected:
//{{AFX_MSG(CEditListCtrl)
afx_msg void OnLButtonDblClk(UINT nFlags, CPoint point);
afx_msg void OnKillFocus(CWnd* pNewWnd);
afx_msg void OnItemchanging(NMHDR* pNMHDR, LRESULT* pResult);
afx_msg void OnKillfocusedit1(NMHDR* pNMHDR, LRESULT* pResult);
afx_msg VOID OnChangeEditD();
//}}AFX_MSG DECLARE_MESSAGE_MAP()
};///////////////////////////////////////////////////////////////////////////////{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.#endif // !defined(AFX_NEWLIST_H__F4C02AFA_F4FA_42D8_8765_28C8D2FD7FB4__INCLUDED_)
// EditListCtrl.cpp : implementation file
//#include "stdafx.h"
#include "mytest.h"
#include "EditListCtrl.h"#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif/////////////////////////////////////////////////////////////////////////////
// CEditListCtrlCEditListCtrl::CEditListCtrl()
{
CurRow = CurCol = -1;
}CEditListCtrl::~CEditListCtrl()
{
}
BEGIN_MESSAGE_MAP(CEditListCtrl, CListCtrl)
//{{AFX_MSG_MAP(CEditListCtrl)
ON_WM_LBUTTONDBLCLK()
ON_WM_KILLFOCUS()
ON_NOTIFY_REFLECT(LVN_ITEMCHANGING, OnItemchanging)
ON_EN_KILLFOCUS(IDC_EDITLISTCTRL_EDIT_20050228, OnKillfocusedit1)
ON_EN_CHANGE(1,OnChangeEditD)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()/////////////////////////////////////////////////////////////////////////////
// CEditListCtrl message handlersvoid CEditListCtrl::OnLButtonDblClk(UINT nFlags, CPoint point)
{
// TODO: Add your message handler code here and/or call default
int Index;
int ColNum;
if ((Index = HitTestEx (point, &ColNum)) != -1)
{
CurCol = ColNum;
CurRow = Index;
if (GetWindowLong (m_hWnd, GWL_STYLE) & LVS_EDITLABELS)
EditSubItem (Index, ColNum);
}// CListCtrl::OnLButtonDblClk(nFlags, point);
}int CEditListCtrl::HitTestEx(CPoint& Point, int* pColumn)
{
int ColumnNum=0;
int Row=HitTest(Point,NULL);
if (pColumn)
*pColumn=0;
//判断ListCtrl 是否为LVS_REPORT ,只有用ClistCtrl自己的EditLable()才有用
if ((GetWindowLong(m_hWnd,GWL_STYLE)&LVS_TYPEMASK)!=LVS_REPORT)
return Row;
Row=GetTopIndex();
int Bottom=Row+GetCountPerPage();
if (Bottom>GetItemCount())
Bottom=GetItemCount();
//判断在哪一行 哪一列
CHeaderCtrl* pHeader=(CHeaderCtrl*)GetDlgItem(0);
int nColumnCount=pHeader->GetItemCount();
for(;Row<=Bottom;++Row)
{
CRect rect;
GetItemRect(Row,&rect,LVIR_BOUNDS);
if (rect.PtInRect(Point))
{
for(ColumnNum=0;ColumnNum<nColumnCount;++ColumnNum)
{
int ColWidth=GetColumnWidth(ColumnNum);
if (Point.x>=rect.left && Point.x<=(rect.left+ColWidth))
{
if (pColumn)
*pColumn=ColumnNum;
return Row;
}
rect.left +=ColWidth;
}
}
}
return -1;
}void CEditListCtrl::EditSubItem(int Item, int Column)
{
CHeaderCtrl* pHeader=(CHeaderCtrl*)GetDlgItem(0);
int nColumnCount=pHeader->GetItemCount();
if (Column>=nColumnCount || GetColumnWidth(Column)<5) //判断宽度是否正确
return;
int Offset=0;
for(int iColumn=0;iColumn<Column;++iColumn) //得到CEditCell的right坐标
{
Offset +=GetColumnWidth(iColumn);
}
CRect rect;
GetItemRect(Item,rect,LVIR_BOUNDS);
CRect ClientRect;
GetClientRect(&ClientRect);
if (Offset+rect.left<0 || Offset+rect.left>ClientRect.right) //得到CEditCell的left坐标
{
CSize size;
if (Offset+rect.left>0)
size.cx=-(Offset-rect.left);
else
size.cx=Offset-rect.left;
size.cy=0;
Scroll(size);
rect.left=size.cx;
}
LV_COLUMN lvCol;
lvCol.mask=LVCF_FMT;
GetColumn(Column,&lvCol);
DWORD dwStyle;
//判断item的显示位子
if ((lvCol.fmt & LVCFMT_JUSTIFYMASK) == LVCFMT_LEFT)
dwStyle = ES_LEFT;
else if ((lvCol.fmt & LVCFMT_JUSTIFYMASK) == LVCFMT_RIGHT)
dwStyle = ES_RIGHT;
else dwStyle = ES_CENTER;
//调整CEditCell 的w位子 (两边缩小2)
rect.left += Offset+2;
rect.right=rect.left+GetColumnWidth(Column)-2;
if (rect.right>ClientRect.right)
rect.right=ClientRect.right;
arect = rect;
//edit1.SetActiveWindow();
//EditCellShow(dwStyle,rect,Item,Column);
EditCellShow(dwStyle,rect,Item,Column);
//ComboCellShow(dwStyle,rect,Item,Column);
}void CEditListCtrl::OnKillFocus(CWnd* pNewWnd)
{
CListCtrl::OnKillFocus(pNewWnd);
if(edit1.GetSafeHwnd())
{
if(GetDlgItem(IDC_EDITLISTCTRL_EDIT_20050228) != GetFocus())
UpdateText();
}
// TODO: Add your message handler code here
}void CEditListCtrl::OnItemchanging(NMHDR* pNMHDR, LRESULT* pResult)
{
NM_LISTVIEW* pNMListView = (NM_LISTVIEW*)pNMHDR;
// TODO: Add your control notification handler code here
UpdateText();
*pResult = 0;
}void CEditListCtrl::UpdateText()
{
if(edit1.GetSafeHwnd())
{
if(edit1.IsWindowVisible())
{
CString buf;
edit1.GetWindowText(buf);
this->SetItemText(CurRow,CurCol,buf);
edit1.SetWindowText("");
edit1.ShowWindow(SW_HIDE);
}
}
}void CEditListCtrl::EditCellShow(DWORD dwStyle,CRect rect, int Item, int SubItem)
{
if(SubItem == 0) //第一列不变
return;
/*
ed = NULL;
ed = this->EditLabel(Item);
if(!ed)
return;
//ed->MoveWindow(rect);//???,在此时move无效
ed->SetWindowText(this->GetItemText(Item,SubItem));
DWORD sty = ed->GetStyle();
ed->ModifyStyle(NULL,LVCFMT_RIGHT | ES_AUTOHSCROLL,1);
//ed->ShowWindow(SW_HIDE);//???,不能hide后move,否则fatal
ed->MoveWindow(rect);//???,此时move有效,问题在于一输入编辑框又跑到最前面了???
ed->ModifyStyle(NULL,dwStyle | ES_AUTOHSCROLL,1);
ed->ShowWindow(SW_SHOW);
*/
if(!edit1.GetSafeHwnd())
edit1.Create(dwStyle |ES_AUTOHSCROLL | WS_CHILD | WS_VISIBLE |
WS_TABSTOP | WS_BORDER | ES_NOHIDESEL,
CRect(0, 0, 0,0), this, IDC_EDITLISTCTRL_EDIT_20050228); edit1.MoveWindow(rect);
edit1.SetWindowText(this->GetItemText(Item,SubItem));
edit1.ShowWindow(SW_SHOW);
edit1.SetFocus();
edit1.SetSel(0,-1);
}void CEditListCtrl::OnKillfocusedit1(NMHDR* pNMHDR, LRESULT* pResult)
{
// TODO: Add your control notification handler code here
UpdateText();
*pResult = 0;
}BOOL CEditListCtrl::IsEditing()
{
if(edit1.GetSafeHwnd())
{
if(GetDlgItem(IDC_EDITLISTCTRL_EDIT_20050228) == GetFocus())
return TRUE;
}
return FALSE;
}void CEditListCtrl::OnChangeEditD()
{
/*
if(ed)
ed->MoveWindow(arect);
*/
}BOOL CEditListCtrl::PreTranslateMessage(MSG* pMsg)
{
// TODO: Add your specialized code here and/or call the base class
if(pMsg->message==WM_KEYDOWN && pMsg->wParam==VK_RETURN)
{
if(IsEditing())
{
UpdateText();
return TRUE;
}
}
return CListCtrl::PreTranslateMessage(pMsg);
}
检查一下ON_EN_KILLFOCUS对应的函数应该是什么格式。
其实我这里有两个OnKillFocus,
一个ListCtrl的,一个edit的,
我这个edit的原型生成方法是先在对话框里放一个edit然后通过ClassWizard生成代码后
拷到这个类里面,我想这个ListCtrl是edit的父窗口,这样他就相当于是对话框了
没想到这样有问题,能说一下为什么吗?to vcleaner
我这就是完整的代码啊
直接拷贝就可以用了
我的应用程序在别的机器上运行不来的
有数据库和些板卡
需要相应的驱动等......
NMHDR是只用于通用控件的结构,Edit控件产生的消息不用这个结构