mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-11-24 07:19:34 +01:00
TAChart: Use axis interval parameters in TDateTimeIntervalChartSource. Update axis demo.
git-svn-id: trunk@31871 -
This commit is contained in:
parent
e916132212
commit
21b9e581d4
@ -328,6 +328,10 @@ object Form1: TForm1
|
|||||||
top = 216
|
top = 216
|
||||||
end
|
end
|
||||||
object DateTimeIntervalChartSource1: TDateTimeIntervalChartSource
|
object DateTimeIntervalChartSource1: TDateTimeIntervalChartSource
|
||||||
|
Params.Count = 10
|
||||||
|
Params.MaxLength = 150
|
||||||
|
Params.MinLength = 20
|
||||||
|
Params.Options = [aipUseCount, aipUseMaxLength, aipUseMinLength, aipUseNiceSteps]
|
||||||
left = 352
|
left = 352
|
||||||
top = 232
|
top = 232
|
||||||
end
|
end
|
||||||
|
|||||||
@ -596,7 +596,8 @@ begin
|
|||||||
Result.FAxisToGraph := @GetTransform.AxisToGraph;
|
Result.FAxisToGraph := @GetTransform.AxisToGraph;
|
||||||
Result.FGraphToAxis := @GetTransform.GraphToAxis;
|
Result.FGraphToAxis := @GetTransform.GraphToAxis;
|
||||||
Result.FGraphToImage := @FHelper.GraphToImage;
|
Result.FGraphToImage := @FHelper.GraphToImage;
|
||||||
Result.FAxisIntervals := Intervals;
|
Result.FIntervals := Intervals;
|
||||||
|
Result.FMinStep := 0;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TChartAxis.Measure(
|
procedure TChartAxis.Measure(
|
||||||
|
|||||||
@ -94,14 +94,19 @@ type
|
|||||||
|
|
||||||
TGraphToImageFunc = function (AX: Double): Integer of object;
|
TGraphToImageFunc = function (AX: Double): Integer of object;
|
||||||
|
|
||||||
TValuesInRangeParams = record
|
TValuesInRangeParams = object
|
||||||
FAxisIntervals: TChartAxisIntervalParams;
|
|
||||||
FAxisToGraph: TTransformFunc;
|
FAxisToGraph: TTransformFunc;
|
||||||
FFormat: String;
|
FFormat: String;
|
||||||
FGraphToAxis: TTransformFunc;
|
FGraphToAxis: TTransformFunc;
|
||||||
FGraphToImage: TGraphToImageFunc;
|
FGraphToImage: TGraphToImageFunc;
|
||||||
|
FIntervals: TChartAxisIntervalParams;
|
||||||
FMin, FMax: Double;
|
FMin, FMax: Double;
|
||||||
|
FMinStep: Double;
|
||||||
FUseY: Boolean;
|
FUseY: Boolean;
|
||||||
|
|
||||||
|
function CountToStep(ACount: Integer): Double; inline;
|
||||||
|
function IsAcceptableStep(AStep: Integer): Boolean; inline;
|
||||||
|
function ToImage(AX: Double): Integer; inline;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TCustomChartSource }
|
{ TCustomChartSource }
|
||||||
@ -194,6 +199,28 @@ begin
|
|||||||
AItem.YList[i] := 0;
|
AItem.YList[i] := 0;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
{ TValuesInRangeParams }
|
||||||
|
|
||||||
|
function TValuesInRangeParams.CountToStep(ACount: Integer): Double;
|
||||||
|
begin
|
||||||
|
Result := Power(10, Floor(Log10((FMax - FMin) / ACount)));
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TValuesInRangeParams.IsAcceptableStep(AStep: Integer): Boolean;
|
||||||
|
begin
|
||||||
|
with FIntervals do
|
||||||
|
Result := not (
|
||||||
|
(aipUseMinLength in Options) and (AStep < MinLength) or
|
||||||
|
(aipUseMaxLength in Options) and (AStep > MaxLength));
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TValuesInRangeParams.ToImage(AX: Double): Integer;
|
||||||
|
begin
|
||||||
|
if not (aipGraphCoords in FIntervals.Options) then
|
||||||
|
AX := FAxisToGraph(AX);
|
||||||
|
Result := FGraphToImage(AX);
|
||||||
|
end;
|
||||||
|
|
||||||
{ TChartAxisIntervalParams }
|
{ TChartAxisIntervalParams }
|
||||||
|
|
||||||
procedure TChartAxisIntervalParams.Changed;
|
procedure TChartAxisIntervalParams.Changed;
|
||||||
|
|||||||
@ -30,9 +30,10 @@ type
|
|||||||
TIntervalChartSource = class(TCustomChartSource)
|
TIntervalChartSource = class(TCustomChartSource)
|
||||||
strict private
|
strict private
|
||||||
FParams: TChartAxisIntervalParams;
|
FParams: TChartAxisIntervalParams;
|
||||||
|
procedure SetParams(AValue: TChartAxisIntervalParams);
|
||||||
|
strict protected
|
||||||
procedure CalculateIntervals(
|
procedure CalculateIntervals(
|
||||||
AParams: TValuesInRangeParams; out ABestStart, ABestStep: Double);
|
AParams: TValuesInRangeParams; out ABestStart, ABestStep: Double);
|
||||||
procedure SetParams(AValue: TChartAxisIntervalParams);
|
|
||||||
protected
|
protected
|
||||||
function GetCount: Integer; override;
|
function GetCount: Integer; override;
|
||||||
function GetItem(AIndex: Integer): PChartDataItem; override;
|
function GetItem(AIndex: Integer): PChartDataItem; override;
|
||||||
@ -48,8 +49,8 @@ type
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
TDateTimeStep = (
|
TDateTimeStep = (
|
||||||
dtsCentury, dtsDecade, dtsYear, dtsQuarter, dtsMonth, dtsWeek, dtsDay,
|
dtsYear, dtsQuarter, dtsMonth, dtsWeek, dtsDay,
|
||||||
dtsHour, dtsTenMinutes, dtsMinute, dtsTenSeconds, dtsSecond, dtsMillisecond
|
dtsHour, dtsMinute, dtsSecond, dtsMillisecond
|
||||||
);
|
);
|
||||||
TDateTimeSteps = set of TDateTimeStep;
|
TDateTimeSteps = set of TDateTimeStep;
|
||||||
|
|
||||||
@ -82,12 +83,32 @@ implementation
|
|||||||
uses
|
uses
|
||||||
DateUtils, Math, StrUtils, SysUtils;
|
DateUtils, Math, StrUtils, SysUtils;
|
||||||
|
|
||||||
|
const
|
||||||
|
YEAR = 365.25;
|
||||||
|
DATE_STEP_INTERVALS: array [TDateTimeStep] of Double = (
|
||||||
|
YEAR, YEAR / 4, YEAR / 12, 7, 1,
|
||||||
|
OneHour, OneMinute, OneSecond, OneMillisecond
|
||||||
|
);
|
||||||
|
|
||||||
type
|
type
|
||||||
TSourceIntervalParams = class(TChartAxisIntervalParams)
|
TSourceIntervalParams = class(TChartAxisIntervalParams)
|
||||||
strict protected
|
strict protected
|
||||||
procedure Changed; override;
|
procedure Changed; override;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
TDateTimeIntervalsHelper = object
|
||||||
|
FBestStep: TDateTimeStep;
|
||||||
|
FBestStepCoeff: Double;
|
||||||
|
FOrigParams: TValuesInRangeParams;
|
||||||
|
FStep: TDateTimeStep;
|
||||||
|
FStepLen: Double;
|
||||||
|
|
||||||
|
function AxisToGraph(AX: Double): Double;
|
||||||
|
procedure CheckStep(AStepCoeff: Double);
|
||||||
|
function GraphToAxis(AX: Double): Double;
|
||||||
|
function NextValue(AValue: TDateTime): Double;
|
||||||
|
end;
|
||||||
|
|
||||||
procedure Register;
|
procedure Register;
|
||||||
begin
|
begin
|
||||||
RegisterComponents(
|
RegisterComponents(
|
||||||
@ -96,6 +117,47 @@ begin
|
|||||||
]);
|
]);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
function SafeRound(AValue: Double): Double; inline;
|
||||||
|
begin
|
||||||
|
Result := Int(AValue * 1e9) / 1e9;
|
||||||
|
end;
|
||||||
|
|
||||||
|
{ TDateTimeIntervalsHelper }
|
||||||
|
|
||||||
|
function TDateTimeIntervalsHelper.AxisToGraph(AX: Double): Double;
|
||||||
|
begin
|
||||||
|
Result := FOrigParams.FAxisToGraph(AX) * DATE_STEP_INTERVALS[FStep];
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure TDateTimeIntervalsHelper.CheckStep(AStepCoeff: Double);
|
||||||
|
begin
|
||||||
|
// Strict inequaltity is importatnt to avoid steps like "ten quarters".
|
||||||
|
if (1.0 <= AStepCoeff) and (AStepCoeff < FBestStepCoeff) then begin
|
||||||
|
FBestStepCoeff := AStepCoeff;
|
||||||
|
FBestStep := FStep;
|
||||||
|
FStepLen := DATE_STEP_INTERVALS[FBestStep] * FBestStepCoeff;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TDateTimeIntervalsHelper.GraphToAxis(AX: Double): Double;
|
||||||
|
begin
|
||||||
|
Result := FOrigParams.FGraphToAxis(AX / DATE_STEP_INTERVALS[FStep]);
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TDateTimeIntervalsHelper.NextValue(AValue: TDateTime): Double;
|
||||||
|
begin
|
||||||
|
case FBestStep of
|
||||||
|
dtsYear:
|
||||||
|
if FBestStepCoeff > 10 then
|
||||||
|
// DateTime arithmetics fails on large year numbers.
|
||||||
|
Result := AValue + FStepLen
|
||||||
|
else
|
||||||
|
Result := IncYear(AValue, Round(FBestStepCoeff));
|
||||||
|
dtsMonth: Result := IncMonth(AValue, Round(FBestStepCoeff));
|
||||||
|
otherwise Result := AValue + FStepLen;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
{ TSourceIntervalParams }
|
{ TSourceIntervalParams }
|
||||||
|
|
||||||
procedure TSourceIntervalParams.Changed;
|
procedure TSourceIntervalParams.Changed;
|
||||||
@ -111,20 +173,14 @@ end;
|
|||||||
procedure TIntervalChartSource.CalculateIntervals(
|
procedure TIntervalChartSource.CalculateIntervals(
|
||||||
AParams: TValuesInRangeParams; out ABestStart, ABestStep: Double);
|
AParams: TValuesInRangeParams; out ABestStart, ABestStep: Double);
|
||||||
|
|
||||||
function A2I(AX: Double): Integer; inline;
|
|
||||||
begin
|
|
||||||
if not (aipGraphCoords in Params.Options) then
|
|
||||||
AX := AParams.FAxisToGraph(AX);
|
|
||||||
Result := AParams.FGraphToImage(AX);
|
|
||||||
end;
|
|
||||||
|
|
||||||
procedure CalcMinMaxCount(out AMinCount, AMaxCount: Integer);
|
procedure CalcMinMaxCount(out AMinCount, AMaxCount: Integer);
|
||||||
var
|
var
|
||||||
imageWidth, d: Integer;
|
imageWidth, d: Integer;
|
||||||
begin
|
begin
|
||||||
// If the axis transformation is non-linear, steps may not be equidistant.
|
// If the axis transformation is non-linear, steps may not be equidistant.
|
||||||
// However, both minimax and maximin will be achieved on equal steps.
|
// However, both minimax and maximin will be achieved on equal steps.
|
||||||
imageWidth := Abs(A2I(AParams.FMax) - A2I(AParams.FMin));
|
with AParams do
|
||||||
|
imageWidth := Abs(ToImage(FMax) - ToImage(FMin));
|
||||||
d := IfThen(aipUseMinLength in Params.Options, Max(Params.MinLength, 2), 2);
|
d := IfThen(aipUseMinLength in Params.Options, Max(Params.MinLength, 2), 2);
|
||||||
AMaxCount := Max(imageWidth div d, 2);
|
AMaxCount := Max(imageWidth div d, 2);
|
||||||
if aipUseMaxLength in Params.Options then
|
if aipUseMaxLength in Params.Options then
|
||||||
@ -133,35 +189,24 @@ procedure TIntervalChartSource.CalculateIntervals(
|
|||||||
AMinCount := 2;
|
AMinCount := 2;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function CountToStep(ACount: Integer): Double;
|
|
||||||
begin
|
|
||||||
Result := (AParams.FMax - AParams.FMin) / ACount;
|
|
||||||
Result := Power(10, Floor(Log10(Result)));
|
|
||||||
end;
|
|
||||||
|
|
||||||
procedure TryStep(AStep: Double; var ABestCount: Integer);
|
procedure TryStep(AStep: Double; var ABestCount: Integer);
|
||||||
var
|
var
|
||||||
m, start: Double;
|
m, start: Double;
|
||||||
mi, prev, cnt: Integer;
|
mi, prev, cnt: Integer;
|
||||||
begin
|
begin
|
||||||
start := Floor(AParams.FMin / AStep) * AStep;
|
start := Int(AParams.FMin / AStep) * AStep;
|
||||||
m := start;
|
m := start;
|
||||||
prev := A2I(m);
|
prev := AParams.ToImage(m);
|
||||||
cnt := 0;
|
cnt := 0;
|
||||||
while m <= AParams.FMax do begin
|
while m <= AParams.FMax do begin
|
||||||
mi := A2I(m + AStep);
|
mi := AParams.ToImage(m + AStep);
|
||||||
prev := Abs(prev - mi);
|
if not AParams.IsAcceptableStep(Abs(prev - mi)) then exit;
|
||||||
if
|
|
||||||
(aipUseMinLength in Params.Options) and (prev < Params.MinLength) or
|
|
||||||
(aipUseMaxLength in Params.Options) and (prev > Params.MaxLength)
|
|
||||||
then
|
|
||||||
exit;
|
|
||||||
m += AStep;
|
m += AStep;
|
||||||
prev := mi;
|
prev := mi;
|
||||||
cnt += 1;
|
cnt += 1;
|
||||||
end;
|
end;
|
||||||
if
|
if
|
||||||
not (aipUseCount in Params.Options) or
|
not (aipUseCount in Params.Options) or (ABestCount <= 0) or
|
||||||
(Abs(cnt - Params.Count) < Abs(ABestCount - Params.Count))
|
(Abs(cnt - Params.Count) < Abs(ABestCount - Params.Count))
|
||||||
then begin
|
then begin
|
||||||
ABestStart := start - AStep;
|
ABestStart := start - AStep;
|
||||||
@ -171,28 +216,28 @@ procedure TIntervalChartSource.CalculateIntervals(
|
|||||||
end;
|
end;
|
||||||
|
|
||||||
var
|
var
|
||||||
minCount, maxCount, cnt: Integer;
|
minCount, maxCount, bestCount: Integer;
|
||||||
s, sv: Double;
|
s, sv: Double;
|
||||||
begin
|
begin
|
||||||
CalcMinMaxCount(minCount, maxCount);
|
CalcMinMaxCount(minCount, maxCount);
|
||||||
cnt := MaxInt;
|
bestCount := 0;
|
||||||
if aipUseNiceSteps in Params.Options then begin
|
if aipUseNiceSteps in Params.Options then begin
|
||||||
s := CountToStep(minCount) * 10;
|
s := AParams.CountToStep(minCount) * 10;
|
||||||
while s >= CountToStep(maxCount) do begin
|
while s >= Max(AParams.CountToStep(maxCount), AParams.FMinStep) do begin
|
||||||
for sv in Params.StepValues do
|
for sv in Params.StepValues do
|
||||||
TryStep(s * sv, cnt);
|
TryStep(s * sv, bestCount);
|
||||||
// We are not required to pick best count, so any one will do.
|
// We are not required to pick best count, so any one will do.
|
||||||
if not (aipUseCount in Params.Options) and (cnt < MaxInt) then break;
|
if not (aipUseCount in Params.Options) and (bestCount > 0) then break;
|
||||||
s *= 0.1;
|
s *= 0.1;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
if cnt < MaxInt then exit;
|
if bestCount > 0 then exit;
|
||||||
// Either nice steps were not required, or we failed to find one.
|
// Either nice steps were not required, or we failed to find one.
|
||||||
if aipUseCount in Params.Options then
|
if aipUseCount in Params.Options then
|
||||||
cnt := EnsureRange(Params.Count, minCount, maxCount)
|
bestCount := EnsureRange(Params.Count, minCount, maxCount)
|
||||||
else
|
else
|
||||||
cnt := minCount;
|
bestCount := minCount;
|
||||||
ABestStep := (AParams.FMax - AParams.FMin) / cnt;
|
ABestStep := (AParams.FMax - AParams.FMin) / bestCount;
|
||||||
ABestStart := AParams.FMin - ABestStep;
|
ABestStart := AParams.FMin - ABestStep;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -241,6 +286,7 @@ var
|
|||||||
i: Integer;
|
i: Integer;
|
||||||
begin
|
begin
|
||||||
if AParams.FMin >= AParams.FMax then exit;
|
if AParams.FMin >= AParams.FMax then exit;
|
||||||
|
AParams.FIntervals := Params;
|
||||||
|
|
||||||
if aipGraphCoords in Params.Options then begin
|
if aipGraphCoords in Params.Options then begin
|
||||||
AParams.FMin := AParams.FAxisToGraph(AParams.FMin);
|
AParams.FMin := AParams.FAxisToGraph(AParams.FMin);
|
||||||
@ -279,100 +325,104 @@ end;
|
|||||||
|
|
||||||
procedure TDateTimeIntervalChartSource.ValuesInRange(
|
procedure TDateTimeIntervalChartSource.ValuesInRange(
|
||||||
AParams: TValuesInRangeParams; var AValues: TChartValueTextArray);
|
AParams: TValuesInRangeParams; var AValues: TChartValueTextArray);
|
||||||
const
|
|
||||||
YEAR = 365.25;
|
|
||||||
STEP_INTERVALS: array [TDateTimeStep] of Double = (
|
|
||||||
100 * YEAR, 10 * YEAR, YEAR, YEAR / 4, YEAR / 12, 7, 1,
|
|
||||||
OneHour, 10 * OneMinute, OneMinute, 10 * OneSecond, OneSecond, OneMillisecond
|
|
||||||
);
|
|
||||||
MIN_STEPS = 4;
|
|
||||||
MAX_STEPS = 20;
|
|
||||||
var
|
var
|
||||||
s: TDateTimeStep;
|
helper: TDateTimeIntervalsHelper;
|
||||||
si, x, start: TDateTime;
|
|
||||||
prevSt: TSystemTime;
|
prevSt: TSystemTime;
|
||||||
|
|
||||||
function FormatLabel: String;
|
function FormatLabel(AValue: TDateTime): String;
|
||||||
var
|
var
|
||||||
st: TSystemTime;
|
st: TSystemTime;
|
||||||
begin
|
begin
|
||||||
if DateTimeFormat <> '' then
|
if DateTimeFormat <> '' then
|
||||||
exit(FormatDateTime(DateTimeFormat, x));
|
exit(FormatDateTime(DateTimeFormat, AValue));
|
||||||
DateTimeToSystemTime(x, st);
|
DateTimeToSystemTime(AValue, st);
|
||||||
case s of
|
case helper.FBestStep of
|
||||||
dtsCentury, dtsDecade, dtsYear:
|
dtsYear:
|
||||||
Result := FormatDateTime('yyyy', x);
|
Result := FormatDateTime('yyyy', AValue);
|
||||||
dtsQuarter:
|
dtsQuarter:
|
||||||
Result := FormatDateTime('yyyy/', x) + IntToStr(Floor(x / si) mod 4 + 1);
|
Result :=
|
||||||
|
IntToRoman(Floor(AValue / helper.FStepLen) mod 4 + 1) +
|
||||||
|
FormatDateTime('/yyyy', AValue);
|
||||||
dtsMonth:
|
dtsMonth:
|
||||||
Result := FormatDateTime(
|
Result := FormatDateTime(
|
||||||
IfThen(st.Year = prevSt.Year, 'mm', 'mm/yyyy'), x);
|
IfThen(st.Year = prevSt.Year, 'mm', 'mm/yyyy'), AValue);
|
||||||
dtsWeek:
|
dtsWeek:
|
||||||
Result := FormatDateTime('dd/mm', x);
|
Result := FormatDateTime('dd/mm', AValue);
|
||||||
dtsDay:
|
dtsDay:
|
||||||
Result := FormatDateTime(
|
Result := FormatDateTime(
|
||||||
IfThen(st.Month = prevSt.Month, 'dd', 'dd/mm'), x);
|
IfThen(st.Month = prevSt.Month, 'dd', 'dd/mm'), AValue);
|
||||||
dtsHour:
|
dtsHour:
|
||||||
Result := FormatDateTime(
|
Result := FormatDateTime(
|
||||||
IfThen(st.Day = prevSt.Day, 'hh:00', 'dd hh:00'), x);
|
IfThen(st.Day = prevSt.Day, 'hh:00', 'dd hh:00'), AValue);
|
||||||
dtsTenMinutes, dtsMinute:
|
dtsMinute:
|
||||||
Result := FormatDateTime(
|
Result := FormatDateTime(
|
||||||
IfThen(st.Hour = prevSt.Hour, 'nn', 'hh:nn'), x);
|
IfThen(st.Hour = prevSt.Hour, 'nn', 'hh:nn'), AValue);
|
||||||
dtsTenSeconds, dtsSecond:
|
dtsSecond:
|
||||||
Result := FormatDateTime(
|
Result := FormatDateTime(
|
||||||
IfThen(st.Minute = prevSt.Minute, 'ss', 'nn:ss'), x);
|
IfThen(st.Minute = prevSt.Minute, 'ss', 'nn:ss'), AValue);
|
||||||
dtsMillisecond:
|
dtsMillisecond:
|
||||||
Result := IntToStr(st.Millisecond) + 'ms';
|
Result :=
|
||||||
|
IfThen(st.Second = prevSt.Second, '', IntToStr(st.Second) + '.') +
|
||||||
|
IntToStr(st.Millisecond) + 'ms';
|
||||||
end;
|
end;
|
||||||
prevSt := st;
|
if InRange(AValue, helper.FOrigParams.FMin, helper.FOrigParams.FMax) then
|
||||||
|
prevSt := st;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
var
|
procedure AddValue(AIndex: Integer; AValue: Double);
|
||||||
i, cnt: Integer;
|
begin
|
||||||
r: Double;
|
with AValues[AIndex] do begin
|
||||||
begin
|
FValue := AValue;
|
||||||
with AParams do begin
|
FText := Format(
|
||||||
r := FMax - FMin;
|
AParams.FFormat, [AValue, 0.0, FormatLabel(AValue), 0.0, 0.0]);
|
||||||
if r / STEP_INTERVALS[dtsCentury] > MAX_STEPS then begin
|
|
||||||
FMin /= STEP_INTERVALS[dtsYear];
|
|
||||||
FMax /= STEP_INTERVALS[dtsYear];
|
|
||||||
inherited ValuesInRange(AParams, AValues);
|
|
||||||
exit;
|
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
s := Low(s);
|
|
||||||
while s < High(s) do begin
|
const
|
||||||
si := STEP_INTERVALS[s];
|
MAX_COUNT = 1000; // Arbitraty limit to prevent OOM in case of a bug.
|
||||||
if (s in Steps) and (r / si > MIN_STEPS) then
|
var
|
||||||
break;
|
i, cnt: Integer;
|
||||||
Inc(s);
|
x, start, stepLen: Double;
|
||||||
|
begin
|
||||||
|
if
|
||||||
|
(AParams.FMin >= AParams.FMax) or (aipGraphCoords in Params.options)
|
||||||
|
then
|
||||||
|
exit;
|
||||||
|
AParams.FIntervals := Params;
|
||||||
|
|
||||||
|
helper.FOrigParams := AParams;
|
||||||
|
AParams.FAxisToGraph := @helper.AxisToGraph;
|
||||||
|
AParams.FGraphToAxis := @helper.GraphToAxis;
|
||||||
|
AParams.FMinStep := 1.0;
|
||||||
|
helper.FBestStepCoeff := SafeInfinity;
|
||||||
|
for helper.FStep in Steps do begin
|
||||||
|
AParams.FMin := helper.FOrigParams.FMin / DATE_STEP_INTERVALS[helper.FStep];
|
||||||
|
AParams.FMax := helper.FOrigParams.FMax / DATE_STEP_INTERVALS[helper.FStep];
|
||||||
|
CalculateIntervals(AParams, start, stepLen);
|
||||||
|
helper.CheckStep(stepLen);
|
||||||
end;
|
end;
|
||||||
start := Int(AParams.FMin / si - 1) * si;
|
|
||||||
x := start;
|
if IsInfinite(helper.FBestStepCoeff) then exit;
|
||||||
|
|
||||||
|
with helper do
|
||||||
|
start := Int(FOrigParams.FMin / FStepLen - 1) * FStepLen;
|
||||||
cnt := 1;
|
cnt := 1;
|
||||||
while x <= AParams.FMax do begin
|
x := start;
|
||||||
|
while (x <= helper.FOrigParams.FMax) and (cnt < MAX_COUNT) do begin
|
||||||
cnt += 1;
|
cnt += 1;
|
||||||
x += si;
|
x := helper.NextValue(x);
|
||||||
end;
|
end;
|
||||||
i := Length(AValues);
|
i := Length(AValues);
|
||||||
SetLength(AValues, i + cnt);
|
SetLength(AValues, i + cnt);
|
||||||
|
|
||||||
FillChar(prevSt, SizeOf(prevSt), $FF);
|
FillChar(prevSt, SizeOf(prevSt), $FF);
|
||||||
x := start;
|
x := start;
|
||||||
while x <= AParams.FMax do begin
|
while (x <= helper.FOrigParams.FMax) and (i < cnt - 1) do begin
|
||||||
AValues[i].FValue := x;
|
AddValue(i, x);
|
||||||
AValues[i].FText := Format(AParams.FFormat, [x, 0.0, FormatLabel, 0.0, 0.0]);
|
|
||||||
i += 1;
|
i += 1;
|
||||||
case s of
|
x := helper.NextValue(x);
|
||||||
dtsCentury: x := IncYear(x, 100);
|
|
||||||
dtsDecade: x := IncYear(x, 10);
|
|
||||||
dtsYear: x := IncYear(x);
|
|
||||||
dtsMonth: x := IncMonth(x);
|
|
||||||
otherwise x += si;
|
|
||||||
end;
|
|
||||||
end;
|
end;
|
||||||
AValues[i].FValue := x;
|
AddValue(i, x);
|
||||||
AValues[i].FText := Format(AParams.FFormat, [x, 0.0, FormatLabel, 0.0, 0.0]);
|
|
||||||
end;
|
end;
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user