Environment: VC 5-6 , Windows 95/98/2000/NT/Me
Recently I had to develop a Graphics Software and wanted to
add support for drawing any N-sided Polygon. When I started, I thought
that I would have to develop code for every ‘N’ separately. After churning my head
in trigonometry for a couple of hours, I realized that effectively 20 lines of code
would do the job.
The figures are drawn (from the center) when you drag the mouse. The drawing mode
used is R2_NOT. When the user drags the mouse, the previous drawn figure is erased
and the new figure is drawn. You need to include "math.h" in your View.cpp file.
This checks when the User Starts dragging the mouse:
void CPolygonsView::OnLButtonDown(UINT nFlags, CPoint point) { m_Drag = true; // for mouse drag check PointOrigin = point; // val when mouse drag starts CView::OnLButtonDown(nFlags, point); } void CPolygonsView::OnLButtonUp(UINT nFlags, CPoint point) { m_Drag = false;// for mouse drag check CView::OnLButtonUp(nFlags, point); }
All the drawing is done in the MouseMove function. First the previously drawn figure is erased (by redrawing over it using R2_NOT). Then the new figure is drawn using the new coordinates. Note that for drawing the figure only 3 things are required:
- The center coordinates
- A vertex coordinate
- The number of sides of the polygon
The loop computes all the other coordinates using these elements and draws lines connecting one vertex to the other.
//value of pi used for trig calcs const double PI = 3.1415926; void CPolygonsView::OnMouseMove(UINT nFlags, CPoint point) { // TODO: Add your message handler code // here and/or call default if (m_Drag && PointOrigin!=point) { // for mouse drag check CClientDC ClientDC(this); // graphics ClientDC.SetROP2(R2_NOT); double Ox , Oy , Px , Py; double phai ; //angle used by me to compute double theta ; //angle used by me to compute double hyp ; double x1 ; double mu ; double x2 ; double y2; int m_Sides = 3;//default figure = triangle Ox = PointOrigin.x; Oy = PointOrigin.y; Px = PointOld.x; Py = PointOld.y; phai = PI / ( m_Sides ); theta = PI / 2 - phai; hyp = sqrt( ( Px - Ox ) * ( Px - Ox ) + ( Py - Oy ) * ( Py - Oy ) ); //hyp = hypotnuse // erase the previous drawn polygon for ( int f = 0;f <m_Sides;f++) { x1 = hyp * cos( theta ); mu = atan2( Py - Oy , Px - Ox ); x2 = x1 * cos( ( mu - theta ) ); y2 = x1 * sin( ( mu - theta ) ); ClientDC.MoveTo( int( Px ) , int( Py ) ); ClientDC.LineTo( int( Px - 2 * x2 ) , int( Py - 2 * y2 ) ); Px = int( Px - 2 * x2 ); Py = int( Py - 2 * y2 ); } // draw the new polygon Px = point.x; Py = point.y; hyp = sqrt( ( Px - Ox ) * ( Px - Ox ) + ( Py - Oy ) * ( Py - Oy ) ); for ( f = 0;f<m_Sides;f++) { x1 = hyp * cos( theta ); mu = atan2( Py - Oy , Px - Ox ); x2 = x1 * cos( ( mu - theta ) ); y2 = x1 * sin( ( mu - theta ) ); ClientDC.MoveTo( int( Px ) , int( Py ) ); ClientDC.LineTo( int( Px - 2 * x2 ) , int( Py - 2 * y2 ) ); Px = int( Px - 2 * x2 ); Py = int( Py - 2 * y2 ); } } PointOld = point;// used to erase the previous drawn figure CView::OnMouseMove(nFlags, point); }
Website : www.mayankmalik.cjb.net
Downloads
Download demo project – 88 Kb
Download source – 25 Kb