1 /////////////////////////////////////////////////////////////////////////////
2 // Name: common/dcbase.cpp
3 // Purpose: generic methods of the wxDC Class
4 // Author: Vadim Zeitlin
8 // Copyright: (c) wxWindows team
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
12 // ============================================================================
14 // ============================================================================
16 #if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
17 #pragma implementation "dcbase.h"
20 // ----------------------------------------------------------------------------
22 // ----------------------------------------------------------------------------
24 // For compilers that support precompilation, includes "wx.h".
25 #include "wx/wxprec.h"
35 // bool wxDCBase::sm_cacheing = FALSE;
37 // ============================================================================
39 // ============================================================================
41 // ----------------------------------------------------------------------------
43 // ----------------------------------------------------------------------------
45 void wxDCBase::DoDrawCheckMark(wxCoord x1
, wxCoord y1
,
46 wxCoord width
, wxCoord height
)
48 wxCHECK_RET( Ok(), wxT("invalid window dc") );
50 wxCoord x2
= x1
+ width
,
53 // this is to yield width of 3 for width == height == 10
54 SetPen(wxPen(GetTextForeground(), (width
+ height
+ 1) / 7, wxSOLID
));
56 // we're drawing a scaled version of wx/generic/tick.xpm here
57 wxCoord x3
= x1
+ (4*width
) / 10, // x of the tick bottom
58 y3
= y1
+ height
/ 2; // y of the left tick branch
59 DoDrawLine(x1
, y3
, x3
, y2
);
60 DoDrawLine(x3
, y2
, x2
, y1
);
62 CalcBoundingBox(x1
, y1
);
63 CalcBoundingBox(x2
, y2
);
66 // ----------------------------------------------------------------------------
68 // ----------------------------------------------------------------------------
70 void wxDCBase::DrawLines(const wxList
*list
, wxCoord xoffset
, wxCoord yoffset
)
72 int n
= list
->GetCount();
73 wxPoint
*points
= new wxPoint
[n
];
76 for ( wxList::compatibility_iterator node
= list
->GetFirst(); node
; node
= node
->GetNext(), i
++ )
78 wxPoint
*point
= (wxPoint
*)node
->GetData();
79 points
[i
].x
= point
->x
;
80 points
[i
].y
= point
->y
;
83 DoDrawLines(n
, points
, xoffset
, yoffset
);
89 void wxDCBase::DrawPolygon(const wxList
*list
,
90 wxCoord xoffset
, wxCoord yoffset
,
93 int n
= list
->GetCount();
94 wxPoint
*points
= new wxPoint
[n
];
97 for ( wxList::compatibility_iterator node
= list
->GetFirst(); node
; node
= node
->GetNext(), i
++ )
99 wxPoint
*point
= (wxPoint
*)node
->GetData();
100 points
[i
].x
= point
->x
;
101 points
[i
].y
= point
->y
;
104 DoDrawPolygon(n
, points
, xoffset
, yoffset
, fillStyle
);
110 wxDCBase::DoDrawPolyPolygon(int n
,
113 wxCoord xoffset
, wxCoord yoffset
,
118 DoDrawPolygon(start
[0], points
, xoffset
, yoffset
, fillStyle
);
126 for (i
= j
= lastOfs
= 0; i
< n
; i
++)
131 pts
= new wxPoint
[j
+n
-1];
132 for (i
= 0; i
< j
; i
++)
134 for (i
= 2; i
<= n
; i
++)
136 lastOfs
-= start
[n
-i
];
137 pts
[j
++] = pts
[lastOfs
];
141 SetPen(wxPen(*wxBLACK
, 0, wxTRANSPARENT
));
142 DoDrawPolygon(j
, pts
, xoffset
, yoffset
, fillStyle
);
144 for (i
= j
= 0; i
< n
; i
++)
146 DoDrawLines(start
[i
], pts
+j
, xoffset
, yoffset
);
152 // ----------------------------------------------------------------------------
154 // ----------------------------------------------------------------------------
158 // TODO: this API needs fixing (wxPointList, why (!const) "wxList *"?)
159 void wxDCBase::DrawSpline(wxCoord x1
, wxCoord y1
, wxCoord x2
, wxCoord y2
, wxCoord x3
, wxCoord y3
)
163 wxPoint
*point1
= new wxPoint
;
164 point1
->x
= x1
; point1
->y
= y1
;
165 point_list
.Append((wxObject
*)point1
);
167 wxPoint
*point2
= new wxPoint
;
168 point2
->x
= x2
; point2
->y
= y2
;
169 point_list
.Append((wxObject
*)point2
);
171 wxPoint
*point3
= new wxPoint
;
172 point3
->x
= x3
; point3
->y
= y3
;
173 point_list
.Append((wxObject
*)point3
);
175 DrawSpline(&point_list
);
177 for( wxList::compatibility_iterator node
= point_list
.GetFirst(); node
; node
= node
->GetNext() )
179 wxPoint
*p
= (wxPoint
*)node
->GetData();
184 void wxDCBase::DrawSpline(int n
, wxPoint points
[])
187 for (int i
=0; i
< n
; i
++)
189 list
.Append((wxObject
*)&points
[i
]);
195 // ----------------------------------- spline code ----------------------------------------
197 void wx_quadratic_spline(double a1
, double b1
, double a2
, double b2
,
198 double a3
, double b3
, double a4
, double b4
);
199 void wx_clear_stack();
200 int wx_spline_pop(double *x1
, double *y1
, double *x2
, double *y2
, double *x3
,
201 double *y3
, double *x4
, double *y4
);
202 void wx_spline_push(double x1
, double y1
, double x2
, double y2
, double x3
, double y3
,
203 double x4
, double y4
);
204 static bool wx_spline_add_point(double x
, double y
);
205 static void wx_spline_draw_point_array(wxDCBase
*dc
);
207 wxList wx_spline_point_list
;
209 #define half(z1, z2) ((z1+z2)/2.0)
212 /* iterative version */
214 void wx_quadratic_spline(double a1
, double b1
, double a2
, double b2
, double a3
, double b3
, double a4
,
217 register double xmid
, ymid
;
218 double x1
, y1
, x2
, y2
, x3
, y3
, x4
, y4
;
221 wx_spline_push(a1
, b1
, a2
, b2
, a3
, b3
, a4
, b4
);
223 while (wx_spline_pop(&x1
, &y1
, &x2
, &y2
, &x3
, &y3
, &x4
, &y4
)) {
224 xmid
= (double)half(x2
, x3
);
225 ymid
= (double)half(y2
, y3
);
226 if (fabs(x1
- xmid
) < THRESHOLD
&& fabs(y1
- ymid
) < THRESHOLD
&&
227 fabs(xmid
- x4
) < THRESHOLD
&& fabs(ymid
- y4
) < THRESHOLD
) {
228 wx_spline_add_point( x1
, y1
);
229 wx_spline_add_point( xmid
, ymid
);
231 wx_spline_push(xmid
, ymid
, (double)half(xmid
, x3
), (double)half(ymid
, y3
),
232 (double)half(x3
, x4
), (double)half(y3
, y4
), x4
, y4
);
233 wx_spline_push(x1
, y1
, (double)half(x1
, x2
), (double)half(y1
, y2
),
234 (double)half(x2
, xmid
), (double)half(y2
, ymid
), xmid
, ymid
);
239 /* utilities used by spline drawing routines */
241 typedef struct wx_spline_stack_struct
{
242 double x1
, y1
, x2
, y2
, x3
, y3
, x4
, y4
;
245 #define SPLINE_STACK_DEPTH 20
246 static Stack wx_spline_stack
[SPLINE_STACK_DEPTH
];
247 static Stack
*wx_stack_top
;
248 static int wx_stack_count
;
250 void wx_clear_stack()
252 wx_stack_top
= wx_spline_stack
;
256 void wx_spline_push(double x1
, double y1
, double x2
, double y2
, double x3
, double y3
, double x4
, double y4
)
258 wx_stack_top
->x1
= x1
;
259 wx_stack_top
->y1
= y1
;
260 wx_stack_top
->x2
= x2
;
261 wx_stack_top
->y2
= y2
;
262 wx_stack_top
->x3
= x3
;
263 wx_stack_top
->y3
= y3
;
264 wx_stack_top
->x4
= x4
;
265 wx_stack_top
->y4
= y4
;
270 int wx_spline_pop(double *x1
, double *y1
, double *x2
, double *y2
,
271 double *x3
, double *y3
, double *x4
, double *y4
)
273 if (wx_stack_count
== 0)
277 *x1
= wx_stack_top
->x1
;
278 *y1
= wx_stack_top
->y1
;
279 *x2
= wx_stack_top
->x2
;
280 *y2
= wx_stack_top
->y2
;
281 *x3
= wx_stack_top
->x3
;
282 *y3
= wx_stack_top
->y3
;
283 *x4
= wx_stack_top
->x4
;
284 *y4
= wx_stack_top
->y4
;
288 static bool wx_spline_add_point(double x
, double y
)
290 wxPoint
*point
= new wxPoint
;
293 wx_spline_point_list
.Append((wxObject
*)point
);
297 static void wx_spline_draw_point_array(wxDCBase
*dc
)
299 dc
->DrawLines(&wx_spline_point_list
, 0, 0 );
300 wxList::compatibility_iterator node
= wx_spline_point_list
.GetFirst();
303 wxPoint
*point
= (wxPoint
*)node
->GetData();
305 wx_spline_point_list
.Erase(node
);
306 node
= wx_spline_point_list
.GetFirst();
310 void wxDCBase::DoDrawSpline( wxList
*points
)
312 wxCHECK_RET( Ok(), wxT("invalid window dc") );
315 double cx1
, cy1
, cx2
, cy2
, cx3
, cy3
, cx4
, cy4
;
316 double x1
, y1
, x2
, y2
;
318 wxList::compatibility_iterator node
= points
->GetFirst();
319 p
= (wxPoint
*)node
->GetData();
324 node
= node
->GetNext();
325 p
= (wxPoint
*)node
->GetData();
329 cx1
= (double)((x1
+ x2
) / 2);
330 cy1
= (double)((y1
+ y2
) / 2);
331 cx2
= (double)((cx1
+ x2
) / 2);
332 cy2
= (double)((cy1
+ y2
) / 2);
334 wx_spline_add_point(x1
, y1
);
336 while ((node
= node
->GetNext())
342 p
= (wxPoint
*)node
->GetData();
347 cx4
= (double)(x1
+ x2
) / 2;
348 cy4
= (double)(y1
+ y2
) / 2;
349 cx3
= (double)(x1
+ cx4
) / 2;
350 cy3
= (double)(y1
+ cy4
) / 2;
352 wx_quadratic_spline(cx1
, cy1
, cx2
, cy2
, cx3
, cy3
, cx4
, cy4
);
356 cx2
= (double)(cx1
+ x2
) / 2;
357 cy2
= (double)(cy1
+ y2
) / 2;
360 wx_spline_add_point( cx1
, cy1
);
361 wx_spline_add_point( x2
, y2
);
363 wx_spline_draw_point_array( this );
366 #endif // wxUSE_SPLINES
368 // ----------------------------------------------------------------------------
369 // enhanced text drawing
370 // ----------------------------------------------------------------------------
372 void wxDCBase::GetMultiLineTextExtent(const wxString
& text
,
378 wxCoord widthTextMax
= 0, widthLine
,
379 heightTextTotal
= 0, heightLineDefault
= 0, heightLine
= 0;
382 for ( const wxChar
*pc
= text
; ; pc
++ )
384 if ( *pc
== _T('\n') || *pc
== _T('\0') )
386 if ( curLine
.empty() )
388 // we can't use GetTextExtent - it will return 0 for both width
389 // and height and an empty line should count in height
392 // assume that this line has the same height as the previous
394 if ( !heightLineDefault
)
395 heightLineDefault
= heightLine
;
397 if ( !heightLineDefault
)
399 // but we don't know it yet - choose something reasonable
400 GetTextExtent(_T("W"), NULL
, &heightLineDefault
,
404 heightTextTotal
+= heightLineDefault
;
408 GetTextExtent(curLine
, &widthLine
, &heightLine
,
410 if ( widthLine
> widthTextMax
)
411 widthTextMax
= widthLine
;
412 heightTextTotal
+= heightLine
;
415 if ( *pc
== _T('\n') )
434 *y
= heightTextTotal
;
439 void wxDCBase::DrawLabel(const wxString
& text
,
440 const wxBitmap
& bitmap
,
444 wxRect
*rectBounding
)
446 // find the text position
447 wxCoord widthText
, heightText
, heightLine
;
448 GetMultiLineTextExtent(text
, &widthText
, &heightText
, &heightLine
);
450 wxCoord width
, height
;
453 width
= widthText
+ bitmap
.GetWidth();
454 height
= bitmap
.GetHeight();
463 if ( alignment
& wxALIGN_RIGHT
)
465 x
= rect
.GetRight() - width
;
467 else if ( alignment
& wxALIGN_CENTRE_HORIZONTAL
)
469 x
= (rect
.GetLeft() + rect
.GetRight() + 1 - width
) / 2;
471 else // alignment & wxALIGN_LEFT
476 if ( alignment
& wxALIGN_BOTTOM
)
478 y
= rect
.GetBottom() - height
;
480 else if ( alignment
& wxALIGN_CENTRE_VERTICAL
)
482 y
= (rect
.GetTop() + rect
.GetBottom() + 1 - height
) / 2;
484 else // alignment & wxALIGN_TOP
489 // draw the bitmap first
495 DrawBitmap(bitmap
, x
, y
, TRUE
/* use mask */);
497 wxCoord offset
= bitmap
.GetWidth() + 4;
501 y
+= (height
- heightText
) / 2;
504 // we will draw the underscore under the accel char later
505 wxCoord startUnderscore
= 0,
509 // split the string into lines and draw each of them separately
511 for ( const wxChar
*pc
= text
; ; pc
++ )
513 if ( *pc
== _T('\n') || *pc
== _T('\0') )
515 int xRealStart
= x
; // init it here to avoid compielr warnings
517 if ( !curLine
.empty() )
519 // NB: can't test for !(alignment & wxALIGN_LEFT) because
521 if ( alignment
& (wxALIGN_RIGHT
| wxALIGN_CENTRE_HORIZONTAL
) )
524 GetTextExtent(curLine
, &widthLine
, NULL
);
526 if ( alignment
& wxALIGN_RIGHT
)
528 xRealStart
+= width
- widthLine
;
530 else // if ( alignment & wxALIGN_CENTRE_HORIZONTAL )
532 xRealStart
+= (width
- widthLine
) / 2;
535 //else: left aligned, nothing to do
537 DrawText(curLine
, xRealStart
, y
);
542 // do we have underscore in this line? we can check yUnderscore
543 // because it is set below to just y + heightLine if we do
544 if ( y
== yUnderscore
)
546 // adjust the horz positions to account for the shift
547 startUnderscore
+= xRealStart
;
548 endUnderscore
+= xRealStart
;
551 if ( *pc
== _T('\0') )
556 else // not end of line
558 if ( pc
- text
.c_str() == indexAccel
)
560 // remeber to draw underscore here
561 GetTextExtent(curLine
, &startUnderscore
, NULL
);
563 GetTextExtent(curLine
, &endUnderscore
, NULL
);
565 yUnderscore
= y
+ heightLine
;
574 // draw the underscore if found
575 if ( startUnderscore
!= endUnderscore
)
577 // it should be of the same colour as text
578 SetPen(wxPen(GetTextForeground(), 0, wxSOLID
));
582 DrawLine(startUnderscore
, yUnderscore
, endUnderscore
, yUnderscore
);
585 // return bounding rect if requested
588 *rectBounding
= wxRect(x
, y
- heightText
, widthText
, heightText
);
591 CalcBoundingBox(x0
, y0
);
592 CalcBoundingBox(x0
+ width0
, y0
+ height
);
596 Notes for wxWindows DrawEllipticArcRot(...)
598 wxDCBase::DrawEllipticArcRot(...) draws a rotated elliptic arc or an ellipse.
599 It uses wxDCBase::CalculateEllipticPoints(...) and wxDCBase::Rotate(...),
602 All methods are generic, so they can be implemented in wxDCBase.
603 DoDrawEllipticArcRot(...) is virtual, so it can be called from deeper
604 methods like (WinCE) wxDC::DoDrawArc(...).
606 CalculateEllipticPoints(...) fills a given list of wxPoints with some points
607 of an elliptic arc. The algorithm is pixel-based: In every row (in flat
608 parts) or every column (in steep parts) only one pixel is calculated.
609 Trigonometric calculation (sin, cos, tan, atan) is only done if the
610 starting angle is not equal to the ending angle. The calculation of the
611 pixels is done using simple arithmetic only and should perform not too
612 bad even on devices without floating point processor. I didn't test this yet.
614 Rotate(...) rotates a list of point pixel-based, you will see rounding errors.
615 For instance: an ellipse rotated 180 degrees is drawn
616 slightly different from the original.
618 The points are then moved to an array and used to draw a polyline and/or polygon
619 (with center added, the pie).
620 The result looks quite similar to the native ellipse, only e few pixels differ.
622 The performance on a desktop system (Athlon 1800, WinXP) is about 7 times
623 slower as DrawEllipse(...), which calls the native API.
624 An rotated ellipse outside the clipping region takes nearly the same time,
625 while an native ellipse outside takes nearly no time to draw.
627 If you draw an arc with this new method, you will see the starting and ending angles
628 are calculated properly.
629 If you use DrawEllipticArc(...), you will see they are only correct for circles
630 and not properly calculated for ellipses.
633 p.lenhard@t-online.de
637 void wxDCBase::DoDrawEllipticArcRot( wxCoord x
, wxCoord y
,
638 wxCoord w
, wxCoord h
,
639 double sa
, double ea
, double angle
)
643 CalculateEllipticPoints( &list
, x
, y
, w
, h
, sa
, ea
);
644 Rotate( &list
, angle
, wxPoint( x
+w
/2, y
+h
/2 ) );
646 // Add center (for polygon/pie)
647 list
.Append( (wxObject
*) new wxPoint( x
+w
/2, y
+h
/2 ) );
649 // copy list into array and delete list elements
650 int n
= list
.Number();
651 wxPoint
*points
= new wxPoint
[n
];
654 for ( node
= list
.First(); node
; node
= node
->Next(), i
++ )
656 wxPoint
*point
= (wxPoint
*)node
->Data();
657 points
[i
].x
= point
->x
;
658 points
[i
].y
= point
->y
;
662 // first draw the pie without pen, if necessary
663 if( GetBrush() != *wxTRANSPARENT_BRUSH
)
665 wxPen
tempPen( GetPen() );
666 SetPen( *wxTRANSPARENT_PEN
);
667 DoDrawPolygon( n
, points
, 0, 0 );
671 // then draw the arc without brush, if necessary
672 if( GetPen() != *wxTRANSPARENT_PEN
)
675 DoDrawLines( n
-1, points
, 0, 0 );
680 } // DrawEllipticArcRot
682 void wxDCBase::Rotate( wxList
* points
, double angle
, wxPoint center
)
686 double pi(3.1415926536);
687 double dSinA
= -sin(angle
*2.0*pi
/360.0);
688 double dCosA
= cos(angle
*2.0*pi
/360.0);
689 for ( wxNode
* node
= points
->First(); node
; node
= node
->Next() )
691 wxPoint
* point
= (wxPoint
*)node
->Data();
693 // transform coordinates, if necessary
694 if( center
.x
) point
->x
-= center
.x
;
695 if( center
.y
) point
->y
-= center
.y
;
697 // calculate rotation, rounding simply by implicit cast to integer
698 int xTemp
= point
->x
* dCosA
- point
->y
* dSinA
;
699 point
->y
= point
->x
* dSinA
+ point
->y
* dCosA
;
702 // back transform coordinates, if necessary
703 if( center
.x
) point
->x
+= center
.x
;
704 if( center
.y
) point
->y
+= center
.y
;
709 void wxDCBase::CalculateEllipticPoints( wxList
* points
,
710 wxCoord xStart
, wxCoord yStart
,
711 wxCoord w
, wxCoord h
,
712 double sa
, double ea
)
714 double pi
= 3.1415926535;
723 bool bUseAngles
= false;
729 // decrement 1 pixel if ellipse is smaller than 2*a, 2*b
731 if( 2*a
== w
) decrX
= 1;
733 if( 2*b
== h
) decrY
= 1;
735 wxCoord xCenter
= xStart
+ a
;
736 wxCoord yCenter
= yStart
+ b
;
737 // calculate data for start and end, if necessary
741 // normalisation of angles
742 while( sa
<0 ) sa
+= 360;
743 while( ea
<0 ) ea
+= 360;
744 while( sa
>=360 ) sa
-= 360;
745 while( ea
>=360 ) ea
-= 360;
746 // calculate quadrant numbers
747 if( sa
> 270 ) sq
= 3;
748 else if( sa
> 180 ) sq
= 2;
749 else if( sa
> 90 ) sq
= 1;
750 if( ea
> 270 ) eq
= 3;
751 else if( ea
> 180 ) eq
= 2;
752 else if( ea
> 90 ) eq
= 1;
753 sar
= sa
* pi
/ 180.0;
754 ear
= ea
* pi
/ 180.0;
755 // correct angle circle -> ellipse
756 sar
= atan( -a
/(double)b
* tan( sar
) );
757 if ( sq
== 1 || sq
== 2 ) sar
+= pi
;
758 ear
= atan( -a
/(double)b
* tan( ear
) );
759 if ( eq
== 1 || eq
== 2 ) ear
+= pi
;
760 // coordinates of points
761 xsa
= xCenter
+ a
* cos( sar
);
762 if( sq
== 0 || sq
== 3 ) xsa
-= decrX
;
763 ysa
= yCenter
+ b
* sin( sar
);
764 if( sq
== 2 || sq
== 3 ) ysa
-= decrY
;
765 xea
= xCenter
+ a
* cos( ear
);
766 if( eq
== 0 || eq
== 3 ) xea
-= decrX
;
767 yea
= yCenter
+ b
* sin( ear
);
768 if( eq
== 2 || eq
== 3 ) yea
-= decrY
;
770 // calculate c1 = b^2, c2 = b^2/a^2 with a = w/2, b = h/2
781 // Lists for quadrant 1 to 4
782 wxList pointsarray
[4];
783 // Calculate points for first quadrant and set in all quadrants
784 for( x
= 0; x
<= a
; ++x
)
789 bool bNewPoint
= false;
790 while( y2
> c1
- c2
* x2
&& y
> 0 )
796 // old y now to big: set point with old y, old x
797 if( bNewPoint
&& x
>1)
800 // remove points on the same line
801 pointsarray
[0].Insert( (wxObject
*) new wxPoint( xCenter
+ x1
- decrX
, yCenter
- y_old
) );
802 pointsarray
[1].Append( (wxObject
*) new wxPoint( xCenter
- x1
, yCenter
- y_old
) );
803 pointsarray
[2].Insert( (wxObject
*) new wxPoint( xCenter
- x1
, yCenter
+ y_old
- decrY
) );
804 pointsarray
[3].Append( (wxObject
*) new wxPoint( xCenter
+ x1
- decrX
, yCenter
+ y_old
- decrY
) );
808 // Starting and/or ending points for the quadrants, first quadrant gets both.
809 pointsarray
[0].Insert( (wxObject
*) new wxPoint( xCenter
+ a
- decrX
, yCenter
) );
810 pointsarray
[0].Append( (wxObject
*) new wxPoint( xCenter
, yCenter
- b
) );
811 pointsarray
[1].Append( (wxObject
*) new wxPoint( xCenter
- a
, yCenter
) );
812 pointsarray
[2].Append( (wxObject
*) new wxPoint( xCenter
, yCenter
+ b
- decrY
) );
813 pointsarray
[3].Append( (wxObject
*) new wxPoint( xCenter
+ a
- decrX
, yCenter
) );
815 // copy quadrants in original list
818 // Copy the right part of the points in the lists
819 // and delete the wxPoints, because they do not leave this method.
820 points
->Append( (wxObject
*) new wxPoint( xsa
, ysa
) );
822 bool bStarted
= false;
824 bool bForceTurn
= ( sq
== eq
&& sa
> ea
);
827 for( wxNode
*node
= pointsarray
[q
].First(); node
; node
= node
->Next() )
829 // once: go to starting point in start quadrant
832 ( (wxPoint
*) node
->Data() )->x
< xsa
+1 && q
<= 1
834 ( (wxPoint
*) node
->Data() )->x
> xsa
-1 && q
>= 2
841 // copy point, if not at ending point
844 if( q
!= eq
|| bForceTurn
846 ( (wxPoint
*) node
->Data() )->x
> xea
+1 && q
<= 1
848 ( (wxPoint
*) node
->Data() )->x
< xea
-1 && q
>= 2
852 wxPoint
* pPoint
= new wxPoint( *((wxPoint
*) node
->Data() ) );
853 points
->Append( (wxObject
*) pPoint
);
855 else if( q
== eq
&& !bForceTurn
|| ( (wxPoint
*) node
->Data() )->x
== xea
)
865 } // while not bReady
866 points
->Append( (wxObject
*) new wxPoint( xea
, yea
) );
869 for( q
= 0; q
< 4; ++q
)
871 for( wxNode
*node
= pointsarray
[q
].First(); node
; node
= node
->Next() )
873 wxPoint
*p
= (wxPoint
*)node
->Data();
881 // copy whole ellipse, wxPoints will be deleted outside
882 for( wxNode
*node
= pointsarray
[0].First(); node
; node
= node
->Next() )
884 wxObject
*p
= node
->Data();
887 for( node
= pointsarray
[1].First(); node
; node
= node
->Next() )
889 wxObject
*p
= node
->Data();
892 for( node
= pointsarray
[2].First(); node
; node
= node
->Next() )
894 wxObject
*p
= node
->Data();
897 for( node
= pointsarray
[3].First(); node
; node
= node
->Next() )
899 wxObject
*p
= node
->Data();
903 } // CalculateEllipticPoints