Recent

Author Topic: [SOLVED] How to get min-max values of zoomed TAChart bottom-axis  (Read 1609 times)

munair

  • Hero Member
  • *****
  • Posts: 798
  • compiler developer @SharpBASIC
    • SharpBASIC
I have a TAChart with zoom tool attached to it. The bottom axis values are dates. When zooming into a specific part of the chart, is it possible to get the first and last date of the zoomed part so that they can be displayed in a separate label?
« Last Edit: August 12, 2019, 10:36:50 pm by Munair »
keep it simple

munair

  • Hero Member
  • *****
  • Posts: 798
  • compiler developer @SharpBASIC
    • SharpBASIC
Re: How to get min-max values of zoomed TAChart bottom-axis
« Reply #1 on: August 12, 2019, 10:36:35 pm »
As I had to do a quick job on this one, I came up with a dirty hack, but at least it works. If anybody knows a more elegant way (e.g. accessing marks by index), please let me know.
Code: Pascal  [Select][+][-]
  1. // ..
  2. Marking: boolean;
  3. FirstMark, LastMark: double;
  4. // ...
  5. procedure TfrmMain.Chart1AfterDraw(ASender: TChart; ADrawer: IChartDrawer);
  6. begin
  7.   lbSelectedTimeValue.Caption := FormatDateTime('YYYY-MM-DD, hh:nn', FirstMark)
  8.     + ' - ' + FormatDateTime('YYYY-MM-DD, hh:nn', LastMark);
  9.   Marking := false;
  10. end;
  11.  
  12. procedure TfrmMain.Chart1AxisList1MarkToText(var AText: String; AMark: Double);
  13. begin
  14.   if Marking = false then
  15.     begin
  16.       FirstMark := AMark;
  17.       Marking := true;
  18.     end
  19.   else
  20.     LastMark := AMark;
  21. end;
keep it simple

wp

  • Hero Member
  • *****
  • Posts: 11858
Re: [SOLVED] How to get min-max values of zoomed TAChart bottom-axis
« Reply #2 on: August 13, 2019, 12:10:23 am »
You mean the first and last axis labels? Hmmm, I don't know a better solution.

munair

  • Hero Member
  • *****
  • Posts: 798
  • compiler developer @SharpBASIC
    • SharpBASIC
Re: [SOLVED] How to get min-max values of zoomed TAChart bottom-axis
« Reply #3 on: August 13, 2019, 06:31:35 am »
Yes, first and last axis label, so that when zoomed in to a level of only days/hours, the full date range can still be displayed.

Example: https://twitter.com/ditrianum/status/1161131417604100096/photo/1
keep it simple

wp

  • Hero Member
  • *****
  • Posts: 11858
Re: [SOLVED] How to get min-max values of zoomed TAChart bottom-axis
« Reply #4 on: August 13, 2019, 10:11:48 am »
Hmmm.... When you want to display information on the visible viewport, wouldn't it be better to use the "true" begin and end of the axis? The position of the axis labels is not under your full control, and depending on the label density the first label may be placed after the first data point.

In order to get the "true" zoomed axis range you can call Chart.CurrentExtent which is a rectangle structure with TDoublePoint records a and b at the left/bottom and right/top corners, respectively. There is also a LogicalExtent which does not consider Margins and data point labels; this is essentially the zoomed rectangle, but I think you need the CurrentExtent here. The begin and end of the x axis, therefore, can be determined like this:

Code: Pascal  [Select][+][-]
  1. procedure GetXAxisRange(Chart: TChart; out FirstX, LastX: double);
  2. var
  3.   ex: TDoubleRect;  // requires TAChartUtils in "uses"
  4. begin
  5.   ex := Chart.CurrentExtent;
  6.   FirstX := ex.a.x;
  7.   LastX := ex.b.x;
  8. end;

Of course, you still must convert FirstX and LastX to date/time strings as needed.

You can call this function in the OnExtentChanged event of the Chart.

munair

  • Hero Member
  • *****
  • Posts: 798
  • compiler developer @SharpBASIC
    • SharpBASIC
Re: [SOLVED] How to get min-max values of zoomed TAChart bottom-axis
« Reply #5 on: August 13, 2019, 11:24:06 am »
Thanks wp, I'll give that a try.
keep it simple

munair

  • Hero Member
  • *****
  • Posts: 798
  • compiler developer @SharpBASIC
    • SharpBASIC
Re: [SOLVED] How to get min-max values of zoomed TAChart bottom-axis
« Reply #6 on: August 13, 2019, 11:47:29 am »
YES. Works much better. The range is more accurate and when zooming/panning, it is updated down to the second. To illustrate this, the data set starts on August 1 at 20:12, which is returned by the CurrentExtent approach. My initial solution returns July 31, 0:00.
Code: Pascal  [Select][+][-]
  1. procedure TfrmMain.Chart1ExtentChanged(ASender: TChart);
  2. begin
  3.   GetXAxisRange(ASender, FirstMark, LastMark);
  4.   lbSelectedTimeValue.Caption := FormatDateTime('YYYY-MM-DD, hh:nn', FirstMark)
  5.     + ' - ' + FormatDateTime('YYYY-MM-DD, hh:nn', LastMark);
  6. end;
keep it simple

 

TinyPortal © 2005-2018