TAChart: Support NaNs in pie series

git-svn-id: trunk@32322 -
This commit is contained in:
ask 2011-09-13 17:08:25 +00:00
parent 6cad306a34
commit 7029ccca10

View File

@ -55,6 +55,8 @@ type
FAngle: Double; FAngle: Double;
FBase: TPoint; FBase: TPoint;
FLabel: TLabelParams; FLabel: TLabelParams;
FOrigIndex: Integer;
FVisible: Boolean;
end; end;
TPieMarkPositions = (pmpAround, pmpInside, pmpLeftRight); TPieMarkPositions = (pmpAround, pmpInside, pmpLeftRight);
@ -193,9 +195,9 @@ end;
procedure TCustomPieSeries.Draw(ADrawer: IChartDrawer); procedure TCustomPieSeries.Draw(ADrawer: IChartDrawer);
var var
i: Integer;
prevAngle: Double = 0; prevAngle: Double = 0;
prevLabelPoly: TPointArray = nil; prevLabelPoly: TPointArray = nil;
ps: TPieSlice;
begin begin
if IsEmpty then exit; if IsEmpty then exit;
@ -203,27 +205,28 @@ begin
Measure(ADrawer); Measure(ADrawer);
ADrawer.PrepareSimplePen(clBlack); ADrawer.PrepareSimplePen(clBlack);
for i := 0 to Count - 1 do begin for ps in FSlices do begin
ADrawer.SetBrushParams(bsSolid, SliceColor(i)); if ps.FVisible then begin
with FSlices[i] do begin ADrawer.SetBrushParams(bsSolid, SliceColor(ps.FOrigIndex));
ADrawer.RadialPie( ADrawer.RadialPie(
FBase.X - FRadius, FBase.Y - FRadius, ps.FBase.X - FRadius, ps.FBase.Y - FRadius,
FBase.X + FRadius, FBase.Y + FRadius, ps.FBase.X + FRadius, ps.FBase.Y + FRadius,
RadToDeg16(prevAngle), RadToDeg16(FAngle)); RadToDeg16(prevAngle), RadToDeg16(ps.FAngle));
prevAngle += FAngle;
end; end;
prevAngle += ps.FAngle;
end; end;
if not Marks.IsMarkLabelsVisible then exit; if not Marks.IsMarkLabelsVisible then exit;
prevAngle := 0; prevAngle := 0;
for i := 0 to Count - 1 do for ps in FSlices do begin
with FSlices[i].FLabel do begin if ps.FVisible then
if FText <> '' then begin with ps.FLabel do
if RotateLabels then if FText <> '' then begin
Marks.SetAdditionalAngle(prevAngle + FSlices[i].FAngle / 2); if RotateLabels then
Marks.DrawLabel(ADrawer, FAttachment, FCenter, FText, prevLabelPoly); Marks.SetAdditionalAngle(prevAngle + ps.FAngle / 2);
end; Marks.DrawLabel(ADrawer, FAttachment, FCenter, FText, prevLabelPoly);
prevAngle += FSlices[i].FAngle; end;
end; prevAngle += ps.FAngle;
end;
end; end;
function TCustomPieSeries.FindContainingSlice(const APoint: TPoint): Integer; function TCustomPieSeries.FindContainingSlice(const APoint: TPoint): Integer;
@ -411,7 +414,7 @@ function TCustomPieSeries.TryRadius(ADrawer: IChartDrawer): TRect;
const const
MARGIN = 4; MARGIN = 4;
var var
i: Integer; i, j: Integer;
di: PChartDataItem; di: PChartDataItem;
prevAngle: Double = 0; prevAngle: Double = 0;
a: Double; a: Double;
@ -419,20 +422,28 @@ begin
Result.TopLeft := FCenter; Result.TopLeft := FCenter;
Result.BottomRight := FCenter; Result.BottomRight := FCenter;
SetLength(FSlices, Count); SetLength(FSlices, Count);
j := 0;
for i := 0 to Count - 1 do begin for i := 0 to Count - 1 do begin
di := Source[i]; di := Source[i];
with FSlices[i] do begin if IsNan(di^.Y) then continue;
with FSlices[j] do begin
FOrigIndex := i;
FAngle := CycleToRad(di^.Y / Source.ValuesTotal); FAngle := CycleToRad(di^.Y / Source.ValuesTotal);
FBase := FCenter; FVisible := not IsNan(di^.X);
a := prevAngle + FAngle / 2; if FVisible then begin
if Exploded and (di^.X > 0) then FBase := FCenter;
FBase += EndPoint(a, FRadius * di^.X); a := prevAngle + FAngle / 2;
ExpandRect(Result, FBase, FRadius, - prevAngle, - prevAngle - FAngle); if Exploded and (di^.X > 0) then
FLabel.FAttachment := EndPoint(a, FRadius) + FBase; FBase += EndPoint(a, FRadius * di^.X);
PrepareLabel(FLabel, i, a); ExpandRect(Result, FBase, FRadius, - prevAngle, - prevAngle - FAngle);
FLabel.FAttachment := EndPoint(a, FRadius) + FBase;
PrepareLabel(FLabel, i, a);
end;
prevAngle += FAngle; prevAngle += FAngle;
end; end;
j += 1;
end; end;
SetLength(FSlices, j);
InflateRect(Result, MARGIN, MARGIN); InflateRect(Result, MARGIN, MARGIN);
end; end;