mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-10-15 17:56:27 +02:00
fpvectorial: Fix rendering of elliptical arc path segments.
git-svn-id: trunk@52895 -
This commit is contained in:
parent
ba13893b95
commit
0ed4960cd0
@ -316,6 +316,8 @@ type
|
||||
{ TPathSegment }
|
||||
|
||||
TPathSegment = class
|
||||
protected
|
||||
FPath: TPath;
|
||||
public
|
||||
SegmentType: TSegmentType;
|
||||
// Fields for linking the list
|
||||
@ -332,6 +334,8 @@ type
|
||||
function GenerateDebugTree(ADestRoutine: TvDebugAddItemProc; APageItem: Pointer): Pointer; virtual;
|
||||
// rendering
|
||||
procedure AddToPoints(ADestX, ADestY: Integer; AMulX, AMulY: Double; var Points: TPointsArray); virtual;
|
||||
// helper methods
|
||||
function UseTopLeftCoordinates: Boolean;
|
||||
end;
|
||||
|
||||
{@@
|
||||
@ -2907,6 +2911,7 @@ var
|
||||
xstart, ystart: Double;
|
||||
n: Integer;
|
||||
done: Boolean;
|
||||
clockwise: Boolean;
|
||||
begin
|
||||
n := 0;
|
||||
SetLength(Points, BUFSIZE);
|
||||
@ -2918,21 +2923,25 @@ begin
|
||||
tstart := CalcEllipsePointAngle(xstart, ystart, RX, RY, CX, CY, XRotation);
|
||||
tend := CalcEllipsePointAngle(X, Y, RX, RY, CX, CY, XRotation);
|
||||
|
||||
// wp: Something's wrong here: I think "clockwise" is the other way round...
|
||||
// Flip clockwise flag in case of top/left coordinates
|
||||
clockwise := ClockwiseArcFlag xor UseTopLeftCoordinates;
|
||||
|
||||
if ClockwiseArcFlag then
|
||||
begin // tend must be larger than tstart
|
||||
if tend < tstart then tend := TWO_PI + tend;
|
||||
end else begin // tend must be smaller than tstart
|
||||
if tstart < tend then tstart := TWO_PI + tstart;
|
||||
if clockwise then
|
||||
begin
|
||||
// clockwise --> angle decreases --> tstart must be > tend
|
||||
dt := -dt;
|
||||
if tstart < tend then tstart := TWO_PI + tstart;
|
||||
end else
|
||||
begin
|
||||
// counter-clockwise --> angle increases --> tstart must be < tend
|
||||
if tend < tstart then tend := TWO_PI + tend;
|
||||
end;
|
||||
|
||||
done := false;
|
||||
t := tstart;
|
||||
while not done do begin
|
||||
if (ClockwiseArcFlag and (t > tend)) or
|
||||
(not ClockwiseArcFlag and (t < tend)) then
|
||||
if (clockwise and (t < tend)) or // angle decreases
|
||||
(not clockwise and (t > tend)) then // angle increases
|
||||
begin
|
||||
t := tend;
|
||||
done := true;
|
||||
@ -2941,7 +2950,7 @@ begin
|
||||
SetLength(Points, Length(Points) + BUFSIZE);
|
||||
CalcEllipsePoint(t, RX, RY, CX, CY, XRotation, Points[n].x, Points[n].y);
|
||||
inc(n);
|
||||
t := t + dt; // Note: dt is <0 in counter-clockwise case
|
||||
t := t + dt; // Note: dt is < 0 in clockwise case
|
||||
end;
|
||||
SetLength(Points, n);
|
||||
end;
|
||||
@ -3345,6 +3354,11 @@ begin
|
||||
// Override by descendants
|
||||
end;
|
||||
|
||||
function TPathSegment.UseTopLeftCoordinates: Boolean;
|
||||
begin
|
||||
Result := (FPath <> nil) and FPath.FPage.UseTopLeftCoordinates;
|
||||
end;
|
||||
|
||||
|
||||
{ T2DSegment }
|
||||
|
||||
@ -4796,6 +4810,8 @@ procedure TPath.AppendSegment(ASegment: TPathSegment);
|
||||
var
|
||||
L: Integer;
|
||||
begin
|
||||
ASegment.FPath := self;
|
||||
|
||||
// Check if we are the first segment in the tmp path
|
||||
if PointsEnd = nil then
|
||||
begin
|
||||
|
@ -553,7 +553,7 @@ begin
|
||||
// Rotate ellipse back to align its major axis with the x axis
|
||||
P := Rotate3dPointInXY(Make3dPoint(x-cx, y-cy, 0), Make3dPoint(0, 0, 0), phi);
|
||||
// Correctly speaking, above line should use -phi, instead of phi. But
|
||||
// Make3DPointInXY seems to define the angle in the opposite way.
|
||||
// Rotate3DPointInXY seems to define the angle in the opposite way.
|
||||
Result := arctan2(P.Y/ry, P.X/rx);
|
||||
if Result < 0 then Result := TWO_PI + Result;
|
||||
end;
|
||||
|
@ -418,7 +418,7 @@ begin
|
||||
TRenderParams.Create(@Render_SelfIntersectingPoly_GradientFill_NonZeroWinding, 'selfintersecting_poly_gradient_nzw.png'));
|
||||
|
||||
node0 := Tree.Items.AddChild(nil, 'Arcs');
|
||||
node := Tree.Items.AddChild(node0, 'clockwise "1" --> "2"');
|
||||
node := Tree.Items.AddChild(node0, 'clockwise from point 1 to point 2');
|
||||
Tree.Items.AddChildObject(node, 'Quarter circle in quadrant I',
|
||||
TRenderParams.Create(@Render_Arc_CW_Q1, 'arc_cw_q1.png'));
|
||||
Tree.Items.AddChildObject(node, 'Quarter circle in quadrant I+II',
|
||||
@ -435,7 +435,7 @@ begin
|
||||
TRenderParams.Create(@Render_Arc_CW_Q4, 'arc_cw_q4.png'));
|
||||
Tree.Items.AddChildObject(node, 'Quarter circle in quadrant IV+I',
|
||||
TRenderParams.Create(@Render_Arc_CW_Q41, 'arc_cw_q41.png'));
|
||||
node := Tree.Items.AddChild(node0, 'counterclockwise "1" --> "2"');
|
||||
node := Tree.Items.AddChild(node0, 'counterclockwise from point 1 to point 2');
|
||||
Tree.Items.AddChildObject(node, 'Quarter circle in quadrant I',
|
||||
TRenderParams.Create(@Render_Arc_CCW_Q1, 'arc_ccw_q1.png'));
|
||||
Tree.Items.AddChildObject(node, 'Quarter circle in quadrant I+II',
|
||||
|
@ -154,12 +154,14 @@ begin
|
||||
txt.Value.Add('1');
|
||||
txt.X := X1;
|
||||
txt.Y := Y1;
|
||||
txt.Font.Color := colRed;
|
||||
APage.AddEntity(txt);
|
||||
|
||||
txt := TvText.Create(APage);
|
||||
txt.Value.Add('2');
|
||||
txt.X := X2;
|
||||
txt.Y := Y2;
|
||||
txt.Font.Color := colRed;
|
||||
APage.AddEntity(txt);
|
||||
end;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user