![]() |
#2
yuccn2012-11-19 21:59
|
1.运行程序第一次选择棋盘(4*4),鼠标选择残缺子,可以把棋盘涂满且没问题;但在第二次选择棋盘(8*8),鼠标选择残缺子运行就有问题了,棋盘没填满;第三次(16*16)也填不满,后面都填不满...而且为填的格子一次比一次多。具体是4*4的填满了15格子(有个残缺子没填,不计算),到8*8时,就有15个格子没填满,16*16时
就有15+63=78个格子没填满,后面依次类推....
2.根据上面每次没填满格子的规律,我觉得是画刷(CBrush)画好了后内存没释放,导致第二,第三次填不满(没填满的格子正好是前面画刷没释放的),但我程序中明明
用DeleteObject释放了,为什么还会出现此情况?或者有其他问题没考虑到。。。求大虾帮忙解决,thinks
下面是程序代码...具体看鼠标点击函数部分

void C残缺棋局—界面Dlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // 用于绘制的设备上下文
SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);
// 使图标在工作区矩形中居中
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// 绘制图标
dc.DrawIcon(x, y, m_hIcon);
//dc.DeleteDC();
}
else
{
CDialogEx::OnPaint();
}
}
//当用户拖动最小化窗口时系统调用此函数取得光标
//显示。
HCURSOR C残缺棋局—界面Dlg::OnQueryDragIcon()
{
return static_cast<HCURSOR>(m_hIcon);
}
int amount=0,Board[130][130];
void Cover(int tr,int tc,int dr,int dc,int size)
{
int s,t;
if (size<2) return;
amount=amount+1;
t=amount; // 所使用的三格板的数目
s=size/2; // 子问题棋盘大小
if(dr<tr+s && dc<tc+s) //残缺方格位于左上棋盘
{
Cover(tr,tc,dr,dc,s);
Board[tr + s - 1][tc + s] = t; //覆盖1号三格板
Board[tr + s][tc + s - 1] = t;
Board[tr + s][tc + s] = t;
Cover(tr, tc+s, tr+s-1, tc+s, s); // 覆盖其余部分
Cover(tr+s, tc, tr+s, tc+s-1, s);
Cover(tr+s, tc+s, tr+s, tc+s, s);
}
else if(dr<tr+s&&dc>=tc+s) //残缺方格位于右上象限
{
Cover(tr,tc+s,dr,dc,s);
Board[tr + s - 1][tc + s - 1] = t; // 覆盖2号三格板
Board[tr + s][tc + s - 1] = t;
Board[tr + s][tc + s] = t;
Cover(tr, tc, tr+s-1, tc+s-1, s); //覆盖其余部分
Cover(tr+s, tc, tr+s, tc+s-1, s);
Cover(tr+s, tc+s, tr+s, tc+s, s);
}
else if (dr >= tr + s && dc < tc + s) //残缺方格位于覆盖左下象限
{
Cover(tr+s,tc,dr,dc,s);
Board[tr + s - 1][tc + s - 1] = t; // 覆盖3号三格板
Board[tr + s - 1][tc + s] = t;
Board[tr + s][tc + s] = t;
Cover(tr, tc, tr+s-1, tc+s-1, s); //覆盖其余部分
Cover(tr, tc+s, tr+s-1, tc+s, s);
Cover(tr+s, tc+s, tr+s, tc+s, s);
}
else if (dr >= tr + s && dc >= tc + s) // 残缺方格位于右下象限
{
Cover(tr+s,tc+s,dr,dc,s);
Board[tr + s - 1][tc + s - 1] = t; // 覆盖4号三格板
Board[tr + s - 1][tc + s] = t;
Board[tr + s][tc + s - 1] = t;
Cover(tr, tc, tr+s-1, tc+s-1, s); //覆盖其余部分
Cover(tr, tc+s, tr+s-1, tc+s, s);
Cover(tr+s, tc, tr+s, tc+s-1, s);
}
}
static int size=1;
bool flag=false;
void C残缺棋局—界面Dlg::OnSelendokCombo1()
{
flag=true;
//刷新窗口重绘
RedrawWindow();
// TODO: 在此添加控件通知处理程序代码
CClientDC dc(this);
CPen bi,*jbi;
bi.CreatePen(PS_SOLID,2,RGB(0,0,0)); //创建黑色、画笔
jbi=dc.SelectObject(&bi); //选择画笔
size=1;
int nIndex = m_cb.GetCurSel(); //获取下拉框数据
for(int x=0;x<nIndex+2;x++)
{
size=size*2;
}
int whight=640/size;
for(int i=0;i<size+1;i++)
{
dc.MoveTo(10,10+i*whight);//画水平线
dc.LineTo(10+size*whight,10+i*whight);
dc.MoveTo(10+i*whight,10);//画垂直线
dc.LineTo(10+i*whight,10+size*whight);
}
bi.DeleteObject();
jbi->DeleteObject();
}
void C残缺棋局—界面Dlg::OnLButtonDown(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
if(flag){
CClientDC dc(this); // 用于绘制的设备上下文
int time;
int whight=640/size;
time=1600/size;
GetCursorPos(&point);
ScreenToClient(&point);
if(point.x>650||point.y>650)
MessageBox(_T("不在棋盘范围内!"),_T("无效的点击"),MB_ICONEXCLAMATION|MB_OK);
else{
Cover(0, 0, point.y/whight, point.x/whight, size);
CBrush brush[7];
//CBrush *pBrush=brush;
for(int k=0;k<7;k++)
{
brush[k].CreateSolidBrush(RGB((k/4)*255,((k/2)%2)*255,(k%2)*255));
}
//pBrush=dc.SelectObject(&brush[7]); //载入笔刷
//dc.SelectObject(&pBrush);
CRect fillrect;
for(int k=1;k<((size*size)/3)+1;k++)
{
for(int i=0;i<size;i++)
{
for(int j=0;j<size;j++)
{
if(Board[i][j]==k)
{
fillrect.top=10+whight*i;
fillrect.bottom=10+whight*(i+1);
fillrect.left=10+whight*j;
fillrect.right=10+whight*(j+1);
dc.FillRect(&fillrect,&brush[k%7]);
dc.FrameRect(&fillrect,&brush[0]);
}
}
}
Sleep(time);
}
for(int i=0;i<7;i++) brush[i].DeleteObject();
//pBrush->DeleteObject();
flag=false;
}
}
CDialogEx::OnLButtonDown(nFlags, point);
}
{
if (IsIconic())
{
CPaintDC dc(this); // 用于绘制的设备上下文
SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);
// 使图标在工作区矩形中居中
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// 绘制图标
dc.DrawIcon(x, y, m_hIcon);
//dc.DeleteDC();
}
else
{
CDialogEx::OnPaint();
}
}
//当用户拖动最小化窗口时系统调用此函数取得光标
//显示。
HCURSOR C残缺棋局—界面Dlg::OnQueryDragIcon()
{
return static_cast<HCURSOR>(m_hIcon);
}
int amount=0,Board[130][130];
void Cover(int tr,int tc,int dr,int dc,int size)
{
int s,t;
if (size<2) return;
amount=amount+1;
t=amount; // 所使用的三格板的数目
s=size/2; // 子问题棋盘大小
if(dr<tr+s && dc<tc+s) //残缺方格位于左上棋盘
{
Cover(tr,tc,dr,dc,s);
Board[tr + s - 1][tc + s] = t; //覆盖1号三格板
Board[tr + s][tc + s - 1] = t;
Board[tr + s][tc + s] = t;
Cover(tr, tc+s, tr+s-1, tc+s, s); // 覆盖其余部分
Cover(tr+s, tc, tr+s, tc+s-1, s);
Cover(tr+s, tc+s, tr+s, tc+s, s);
}
else if(dr<tr+s&&dc>=tc+s) //残缺方格位于右上象限
{
Cover(tr,tc+s,dr,dc,s);
Board[tr + s - 1][tc + s - 1] = t; // 覆盖2号三格板
Board[tr + s][tc + s - 1] = t;
Board[tr + s][tc + s] = t;
Cover(tr, tc, tr+s-1, tc+s-1, s); //覆盖其余部分
Cover(tr+s, tc, tr+s, tc+s-1, s);
Cover(tr+s, tc+s, tr+s, tc+s, s);
}
else if (dr >= tr + s && dc < tc + s) //残缺方格位于覆盖左下象限
{
Cover(tr+s,tc,dr,dc,s);
Board[tr + s - 1][tc + s - 1] = t; // 覆盖3号三格板
Board[tr + s - 1][tc + s] = t;
Board[tr + s][tc + s] = t;
Cover(tr, tc, tr+s-1, tc+s-1, s); //覆盖其余部分
Cover(tr, tc+s, tr+s-1, tc+s, s);
Cover(tr+s, tc+s, tr+s, tc+s, s);
}
else if (dr >= tr + s && dc >= tc + s) // 残缺方格位于右下象限
{
Cover(tr+s,tc+s,dr,dc,s);
Board[tr + s - 1][tc + s - 1] = t; // 覆盖4号三格板
Board[tr + s - 1][tc + s] = t;
Board[tr + s][tc + s - 1] = t;
Cover(tr, tc, tr+s-1, tc+s-1, s); //覆盖其余部分
Cover(tr, tc+s, tr+s-1, tc+s, s);
Cover(tr+s, tc, tr+s, tc+s-1, s);
}
}
static int size=1;
bool flag=false;
void C残缺棋局—界面Dlg::OnSelendokCombo1()
{
flag=true;
//刷新窗口重绘
RedrawWindow();
// TODO: 在此添加控件通知处理程序代码
CClientDC dc(this);
CPen bi,*jbi;
bi.CreatePen(PS_SOLID,2,RGB(0,0,0)); //创建黑色、画笔
jbi=dc.SelectObject(&bi); //选择画笔
size=1;
int nIndex = m_cb.GetCurSel(); //获取下拉框数据
for(int x=0;x<nIndex+2;x++)
{
size=size*2;
}
int whight=640/size;
for(int i=0;i<size+1;i++)
{
dc.MoveTo(10,10+i*whight);//画水平线
dc.LineTo(10+size*whight,10+i*whight);
dc.MoveTo(10+i*whight,10);//画垂直线
dc.LineTo(10+i*whight,10+size*whight);
}
bi.DeleteObject();
jbi->DeleteObject();
}
void C残缺棋局—界面Dlg::OnLButtonDown(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
if(flag){
CClientDC dc(this); // 用于绘制的设备上下文
int time;
int whight=640/size;
time=1600/size;
GetCursorPos(&point);
ScreenToClient(&point);
if(point.x>650||point.y>650)
MessageBox(_T("不在棋盘范围内!"),_T("无效的点击"),MB_ICONEXCLAMATION|MB_OK);
else{
Cover(0, 0, point.y/whight, point.x/whight, size);
CBrush brush[7];
//CBrush *pBrush=brush;
for(int k=0;k<7;k++)
{
brush[k].CreateSolidBrush(RGB((k/4)*255,((k/2)%2)*255,(k%2)*255));
}
//pBrush=dc.SelectObject(&brush[7]); //载入笔刷
//dc.SelectObject(&pBrush);
CRect fillrect;
for(int k=1;k<((size*size)/3)+1;k++)
{
for(int i=0;i<size;i++)
{
for(int j=0;j<size;j++)
{
if(Board[i][j]==k)
{
fillrect.top=10+whight*i;
fillrect.bottom=10+whight*(i+1);
fillrect.left=10+whight*j;
fillrect.right=10+whight*(j+1);
dc.FillRect(&fillrect,&brush[k%7]);
dc.FrameRect(&fillrect,&brush[0]);
}
}
}
Sleep(time);
}
for(int i=0;i<7;i++) brush[i].DeleteObject();
//pBrush->DeleteObject();
flag=false;
}
}
CDialogEx::OnLButtonDown(nFlags, point);
}
运行结果:
只有本站会员才能查看附件,请 登录
只有本站会员才能查看附件,请 登录
只有本站会员才能查看附件,请 登录