⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 drawview.cpp

📁 陈建春<用VC++开发GIS系统>源码.适合于GIS学习者,以及学习图形图象编程的朋友.
💻 CPP
📖 第 1 页 / 共 5 页
字号:
	p_Screen[0].blc=blc;
	pDoc->m_CurrentScreen=0;
	InitVScroll();
	InitHScroll();
	Invalidate();
}

//“鼠标选中”菜单项的对应函数
void CDrawView::OnSelectMouse() 
{
	m_DrawCurrent=30;	//标识进行图形选中操作
	PushNumb=0;
}

//“放弃选中”菜单项的对应函数,用来放弃所作的选择
void CDrawView::OnSelectClear() 
{
	CDrawDoc* pDoc = GetDocument();
	CClientDC ht(this);
	for(int i=0;i<pDoc->n_GraphSelect;i++)	//将选中的图形元素原样进行绘制
		pDoc->DrawGraph(&ht,pDoc->GraphSelect[i].Lb,pDoc->GraphSelect[i].Index,0,0,m_bColor);
	pDoc->n_GraphSelect=0;
	if(pDoc->b_IsOleSelect)
	{
		POSITION pos=pDoc->GetStartPosition();
		while(pos!=NULL)
		{
			CDrawCntrItem *pItem=(CDrawCntrItem *)pDoc->GetNextClientItem(pos);
			if(pItem!=NULL)
				pItem->b_Select=FALSE;
		}
		pDoc->b_IsOleSelect=0;
		Invalidate();
	}
}

//用来删除一个图形元素的函授数
//Lb-删除图形的类别 Index-删除图形顶序列号
void CDrawView::Delete(CDC* pDC,int Lb,int Index)
{
	float x1,y1,x2,y2;
	CDrawDoc* pDoc = GetDocument();
	if(Lb==1)	//如果是直线,得到直线指针并以屏幕底色重画达到删除的效果
	{
		CLine* p_Line=pDoc->GetLine(Index);
		p_Line->Draw(pDC,0,2,m_bColor);
		p_Line->Delete(1);	//做删除标识
	}
	else if(Lb==2)	//如果是连续直线或多边形
	{
		CPline* p_PLine=pDoc->GetPLine(Index);	//得到连续直线(多边形)的指针
		if(p_PLine->IsPLine()) //如果是连续直线,以屏幕底色重画达到删除的效果
			p_PLine->Draw(pDC,0,2,m_bColor);
		else		//如果是多边形区域
		{
			p_PLine->GetRect(&x1,&y1,&x2,&y2);	//得到多边形区域的边界矩形
			ReDrawRect(x1,y1,x2,y2);			//重画多边形区域所在顶区域
		}
		p_PLine->Delete(1);	//做删除标识
	}
	else if(Lb==3)	//如果是圆或圆形区域
	{
		CCircle* p_Circle=pDoc->GetCircle(Index);//得到圆(圆形区域)的指针
		if(p_Circle->IsCircle()) //如果是圆,则以屏幕底色进行重画
			p_Circle->Draw(pDC,0,2,m_bColor);
		else	//如果是圆形区域,则得到其边界矩形并重画这个区域
		{
			p_Circle->GetRect(&x1,&y1,&x2,&y2);
			ReDrawRect(x1,y1,x2,y2);
		}
		p_Circle->Delete(1);	//做删除标识
	}
	else if(Lb==4)	//如果是圆弧,则以屏幕底色进行重画
	{
		CArc* p_Arc=pDoc->GetArc(Index);	//得到圆弧的指针
		p_Arc->Draw(pDC,0,2,m_bColor);
		p_Arc->Delete(1);		//做删除标识
	}
	else if(Lb==5)	//如果是标注文字,则得到其边界矩形并重画这个区域
	{
		CText* p_Text=pDoc->GetText(Index);	//得到标注文字的指针
		p_Text->GetRect(&x1,&y1,&x2,&y2);
		p_Text->Delete(1);		//做删除标识
		ReDrawRect(x1,y1,x2,y2);//重画屏幕区域
	}
}

//此函数用来重画由点(X1,Y1)和点(X2,Y2)确定的区域
void CDrawView::ReDrawRect(float X1, float Y1, float X2, float Y2)
{
	float xx1,xx2,yy1,yy2;
	CRect r1;
	xx1=m_xStart; xx2=m_xStart+blc*m_wScreen;
	yy1=m_yStart; yy2=m_yStart+blc*m_hScreen;
	//得到区域与视图区域相交的矩形
	BOOL IsCross=RectCross(&xx1,&yy1,&xx2,&yy2,X1,Y1,X2,Y2);
	if(IsCross)	//如果相交,则重画这一区域
	{
		//以下得到这个区域顶像素坐标
		r1.left=(int)((xx1-m_xStart)/blc)-1;
		r1.right=(int)((xx2-m_xStart)/blc)+1;
		r1.top=m_hScreen-(int)((yy2-m_yStart)/blc)-1;
		r1.bottom=m_hScreen-(int)((yy1-m_yStart)/blc)+1;
		InvalidateRect(r1);
	}
}

//此函数用来计算由(*x1,*y1),(*x2,*y2)和(xx1,yy1),(xx2,yy2)决定的两个区域的相交区域
//返回:TURE,两区域相交,相交区域由(*x1,*y1),(*x2,*y2)决定
BOOL CDrawView::RectCross(float* x1,float* y1,float* x2,float* y2,float xx1,
						   float yy1,float xx2,float yy2)
{
	float m_X1,m_Y1,m_X2,m_Y2;
	m_X1=*x1; m_Y1=*y1; m_X2=*x2 ;m_Y2=*y2;
	if(m_X1>xx2||m_X2<xx1||m_Y1>yy2||m_Y2<yy1) //两个矩形区域不相交
		return FALSE;	//如不相交函数返回0
	else	//两个矩形相交,得到相交矩形的坐标
	{
		*x1=max(m_X1,xx1);
		*y1=max(m_Y1,yy1);
		*x2=min(m_X2,xx2);
		*y2=min(m_Y2,yy2);
		return TRUE; //如果相交就返回1
	}
}

//“删除图形”菜单项的对应函数,用来删除鼠标选中的图形
void CDrawView::OnSelectDelete()
{
	CDrawDoc* pDoc = GetDocument();
	CClientDC ht(this);
	for(int i=0;i<pDoc->n_GraphSelect;i++)	//删除选中的图形
		Delete(&ht,pDoc->GraphSelect[i].Lb,pDoc->GraphSelect[i].Index);
	//以下是记录删除图形这一操作,供逆操作时用
	pDoc->AddUndo(3,pDoc->n_GraphSelect,pDoc->GraphSelect);
	ReleaseCapture();
	pDoc->n_GraphSelect=0;	//选中的图形元素为0
	if(pDoc->b_IsOleSelect)
	{
		POSITION pos=pDoc->GetStartPosition();
		while(pos!=NULL)
		{
			CDrawCntrItem *pItem=(CDrawCntrItem *)pDoc->GetNextClientItem(pos);
			if(pItem!=NULL)
			{
				if(pItem->b_Select)
				{
					pDoc->RemoveItem(pItem);
					delete pItem;
					m_pSelection =NULL;   // set selection to last inserted item
				}
			}
		}
		pDoc->UpdateAllViews(this);
	}
}

//“Cut"菜单项的对应函数,用来删除鼠标选中的图形并将删除的图形放在剪裁板
void CDrawView::OnEditCut() 
{
	CClientDC ht(this);
	CDrawDoc* pDoc = GetDocument();
	if(pDoc->WriteClipBoard())
	{
		for(int i=0;i<pDoc->n_GraphSelect;i++)		//删除图形
			Delete(&ht,pDoc->GraphSelect[i].Lb,pDoc->GraphSelect[i].Index);
		//以下是记录删除图形这一操作,供逆操作时用
		pDoc->AddUndo(3,pDoc->n_GraphSelect,pDoc->GraphSelect);
		pDoc->n_GraphSelect=0;	//选中的图形元素为0
	}
}


void CDrawView::OnEditPaste() 
{
	m_DrawCurrent=20;
	PushNumb=0;
}

//“Copy"菜单项的对应函数,用来将选中的图形放在剪裁板
void CDrawView::OnEditCopy() 
{
	CDrawDoc* pDoc = GetDocument();
	pDoc->WriteClipBoard();	//将图形写入剪裁板
}

//“Undo"菜单项的对应函数,用来实现完全的逆操作
void CDrawView::OnEditUndo() 
{
	CDrawDoc* pDoc = GetDocument();
	CClientDC ht(this);
	pDoc->OnEditUndo();			//进行一步逆操作
	pDoc->UpdateAllViews(this);	//重画所有视图
}

void CDrawView::OnHScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar) 
{
	short nScrollInc;
	int nNewPos;
	CRect r1;
	switch(nSBCode)
	{
		case SB_TOP:
			nScrollInc=-nHScrollPos;
			break;
		case SB_BOTTOM:
			nScrollInc=nHScrollMax-nHScrollPos;
			break;
		case SB_LINEUP:
			nScrollInc=-nXLine;
			break;
		case SB_LINEDOWN:
			nScrollInc=nXLine;
			break;
		case SB_PAGEUP:
			nScrollInc=-nXPage;
			break;
		case SB_PAGEDOWN:
			nScrollInc=nXPage;
			break;
		case SB_THUMBPOSITION:
			nScrollInc=nPos-nHScrollPos;
			break;
		default:
			nScrollInc=0;
	}
	nNewPos=max(0,min(nHScrollPos+nScrollInc,nHScrollMax));
	nScrollInc=nNewPos-nHScrollPos;
	if(nScrollInc) //如果产生了滚动
	{
		nHScrollPos=nNewPos;  //设定新的滚动位置
		SetScrollPos(SB_HORZ,nHScrollPos);
		UpdateWindow();//使滚动条的位置改动在屏幕上实现
		m_xStart=m_xStart+blc*nScrollInc*nScrollMin;//调整纵坐标使图形产生滚动
		GetClientRect(&r1);  //得到客户区的矩形边界
		if(abs(nScrollInc)*nScrollMin<r1.right) //如果滚动后的屏幕与滚动前有重叠
		{
			if(nScrollInc>0)    //如果是图形向上滚动
				r1.left=nScrollInc*nScrollMin; //得到滚动屏幕上重叠区域的矩形
			else                //如果图形向下滚动
				r1.right=r1.right-nScrollInc*nScrollMin; //得到重叠区域的矩形
			ScrollWindow(-nScrollInc*nScrollMin,0,r1);  //滚动重叠的区域
			if(nScrollInc>0)                            //如果是向上滚动
				r1.left=r1.right-nScrollInc*nScrollMin;   //得到需要重画的区域
			else                                        //如果是向下滚动
				r1.right=-nScrollInc*nScrollMin;         //得到需要重画的区域
			InvalidateRect(r1,0);                       //对图形进行局部重画
		}
		else //如果滚动后的区域与滚动前的区域没有重叠,则全屏重画
			Invalidate();
		//恢复矩形rr原来的坐标
		//        r.left=0;
		//      r.right=ScreenWide;
	}
	/*
	if(nScrollInc)
	{
		nHScrollPos=nNewPos;
		SetScrollPos(SB_HORZ,nHScrollPos);
		UpdateWindow();
		startx=startx+blc*nScrollInc*nScrollMin;
		Screenxy[numb][0]=startx;
		Invalidate();
		r.top=0;
		r.bottom=ScreenHigh;
	}*/
	CView::OnHScroll(nSBCode, nPos, pScrollBar);
}

void CDrawView::OnVScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar) 
{
	short nScrollInc;
	int nNewPos;
	CRect r1;
	switch(nSBCode) //判断按键位置
	{
		case SB_TOP:                 //如果将滚动条滚动到顶部
			nScrollInc=-nVScrollPos;   //得到相对滚动范围
			break;
		case SB_BOTTOM:              //如果将滚动条滚动到底部
			nScrollInc=nVScrollMax-nVScrollPos; //得到相对的滚动范围
			break;
		case SB_LINEUP:             //如果按了滚动条中的向上的按键
			nScrollInc=-nYLine;      //得到相对滚动位置
			break;
		case SB_LINEDOWN:           //如果按中了向下的按键
			nScrollInc=nYLine;        //得到相对的滚动位置
			break;
		case SB_PAGEUP:             //如果按中了中间活动按钮的上部区域
			nScrollInc=-nYPage;       //得到相对的滚动位置
			break;                    
		case SB_PAGEDOWN:           //如果按中了中间活动钮的下部位置
			nScrollInc=nYPage;        //得到相对的滚动位置
			break;
		case SB_THUMBPOSITION:      //如果用鼠标拖动中间活动钮到一个位置
			nScrollInc=nPos-nVScrollPos; //通过信息处理函数得到的按钮位置得到相对移动位置
			break;
		default:
			nScrollInc=0;
	}
	//进行滚动边界检查,得到实际的滚动位置(不能超出滚动条的滚动范围)
	nNewPos=max(0,min(nVScrollPos+nScrollInc,nVScrollMax));
	//得到实际的相对滚动范围
	nScrollInc=nNewPos-nVScrollPos;
	if(nScrollInc) //如果产生了滚动
	{
		nVScrollPos=nNewPos;  //设定新的滚动位置
		SetScrollPos(SB_VERT,nVScrollPos);
		UpdateWindow();//使滚动条的位置改动在屏幕上实现
		m_yStart=m_yStart-blc*nScrollInc*nScrollMin;//调整纵坐标使图形产生滚动
		GetClientRect(&r1);  //得到客户区的矩形边界
		if(abs(nScrollInc)*nScrollMin<r1.bottom) //如果滚动后的屏幕与滚动前有重叠
		{
			if(nScrollInc>0)    //如果是图形向上滚动
				r1.top=nScrollInc*nScrollMin; //得到滚动屏幕上重叠区域的矩形
			else                //如果图形向下滚动
				r1.bottom=r1.bottom+nScrollInc*nScrollMin; //得到重叠区域的矩形
			ScrollWindow(0,-nScrollInc*nScrollMin,r1);  //滚动重叠的区域
			if(nScrollInc>0)                            //如果是向上滚动
				r1.top=r1.bottom-nScrollInc*nScrollMin;   //得到需要重画的区域
			else                                        //如果是向下滚动
				r1.bottom=-nScrollInc*nScrollMin;         //得到需要重画的区域
			InvalidateRect(r1,0);                       //对图形进行局部重画
			//pbdy=1;
		}
		else //如果滚动后的区域与滚动前的区域没有重叠,则全屏重画
			Invalidate();
	}
	CView::OnVScroll(nSBCode, nPos, pScrollBar);
}

void CDrawView::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags) 
{
	switch(nChar)
	{
		case VK_HOME:
			OnHScroll(SB_PAGEUP,0,NULL);
			break;
		case VK_END:
			OnHScroll(SB_PAGEDOWN,0,NULL);
			break;
		case VK_PRIOR:
			OnVScroll(SB_PAGEUP,0,NULL);
			break;
		case VK_NEXT:
			OnVScroll(SB_PAGEDOWN,0,NULL);
			break;
		case VK_UP:
			OnVScroll(SB_LINEUP,0,NULL);
			break;
		case VK_DOWN:
			OnVScroll(SB_LINEDOWN,0,NULL);
			break;
		case VK_LEFT:
			OnHScroll(SB_LINEUP,0,NULL);
			break;
		case VK_RIGHT:
			OnHScroll(SB_LINEDOWN,0,NULL);
			break;
	}
	CView::OnKeyDown(nChar, nRepCnt, nFlags);
}

void CDrawView::OnChangeDlgEdit()
{
	char p1[7];
	CMainFrame* p_Wnd=(CMainFrame *)(AfxGetApp()->m_pMainWnd);
	p_Wnd->m_wndDlgBar.GetDlgItemText(IDC_EDIT1,p1,6);
	m_LineWide=(unsigned char)atoi(p1);
}

void CDrawView::OnChangeDlgCom()
{
	CMainFrame* p_Wnd=(CMainFrame *)(AfxGetApp()->m_pMainWnd);
	CComboBox* plist=(CComboBox*)(p_Wnd->m_wndDlgBar.GetDlgItem(IDC_COMBO1));
	m_LineType=(unsigned char)plist->GetCurSel();
}

void CDrawView::OnBitmapCut() 
{
	CBitmap Bitmap;
	CClientDC ht(this);
	CDC MemDC;
	RECT r1;
	GetClientRect(&r1);
	Bitmap.CreateCompatibleBitmap(&ht,r1.right-r1.left,r1.bottom-r1.top);
	MemDC.CreateCompatibleDC(&ht);
	MemDC.SelectObject(&Bitmap);
	MemDC.BitBlt(0,0,r1.right-r1.left,r1.bottom-r1.top,&ht,0,0,SRCCOPY);
	ht.BitBlt(0,0,r1.right-r1.left,r1.bottom-r1.top,&MemDC,100,100,SRCCOPY);
	if(!OpenClipboard())
		return;
	EmptyClipboard();
	::SetClipboardData(CF_BITMAP,Bitmap.m_hObject);
	Bitmap.Detach();
	CloseClipboard();
}

void CDrawView::OnBitmapPaste() 
{
	CClientDC ht(this);
	CBitmap Bitmap;
	BITMAP BitmapInfo;
	HANDLE HBitmap;
	CDC MemDC;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -