Page 1 of 1

“Cleaner” way to draw series than PaintSeriesLegend

Posted: Fri Jul 21, 2017 4:30 pm
by 16466355
I have been using PaintSeriesLegend for drawing a series symbol in a checklist box that lists some pre-built series my user may select from. Unfortunately, the quality of the drawing is kind of poor. I think you use this a few places in the TChartEditor. For example, please look at the difference between the series as they are painted on a chart and chart legend versus the way they show up in the Series Tab and on the Data Tab in the TChartEditor. The series are pixilated and sometimes don’t even look correct. For example, please look at the donut style point series. It only paints a quarter of the symbol and is unrecognizable.

That said, can you help me figure out another way to draw a copy of the series that has the same level of quality as it would have on a chart itself and where all the series symbols look correct? I was looking through the source code to try and figure this out myself and it is quite complex and it's very easy to get lost in it...

Thanks!

Re: “Cleaner” way to draw series than PaintSeriesLegend

Posted: Wed Jul 26, 2017 8:17 am
by yeray
Hello,

I see the symbol drawn with the PaintSeriesLegend method looks weird.
However, I'm not sure to understand what symbol would you like to draw in your checklist box:
Project2_2017-07-26_10-15-21.png
Project2_2017-07-26_10-15-21.png (13.7 KiB) Viewed 13318 times

Re: “Cleaner” way to draw series than PaintSeriesLegend

Posted: Wed Jul 26, 2017 3:44 pm
by 16466355
Yes, that is exactly it. So what I would like to be able to paint is the exact symbol as you see it on the chart or in the legend instead of what you see between the checkbox and the text "Series1" in the TChart Editor. For example if you added a point series to the chart you have, you would also see a difference between a smooth, nice looking series on the chart/chart legend versus a more pixelated looking thing in the TChart Editor. PaintSeriesLegend provides what is showing in the TChart Editor. So I was wondering if there is another procedure or easy way for me to paint a series symbol that will look just like the symbol would look on the actual chart/legend.

Re: “Cleaner” way to draw series than PaintSeriesLegend

Posted: Fri Jul 28, 2017 2:23 pm
by yeray
Hello,

I can draw a point into the same Chart canvas as follows:

Code: Select all

procedure TForm1.Chart1AfterDraw(Sender: TObject);
begin
  Chart1.Canvas.Brush.Color:=Series1.Color;
  Series1.Pointer.DrawPointer(Chart1.Canvas, Chart1.View3D, 10, 10, Series1.Pointer.Size, Series1.Pointer.Size, Series1.Color, Series1.Pointer.Style);
end;
If you still find problems to draw the point on top of another control, don't hesitate to let us know.

Re: “Cleaner” way to draw series than PaintSeriesLegend

Posted: Fri Jul 28, 2017 7:41 pm
by 16466355
Thanks!

It seems that method requires a TCanvas3D, which is a steema object. So do you have any recommendations for how to make that work on top of a control like a listbox which would only have a TCanvas? Also, this wouldn't work for series like a bar series which doesn't have a TPointer, would it?

Re: “Cleaner” way to draw series than PaintSeriesLegend

Posted: Tue Aug 01, 2017 9:15 am
by yeray
Hello,

I see the issues you originally reported:
- The quality of the symbol. This is because GDI is used to draw the symbol over the components in the editor while GDIPlus is the default canvas to draw the chart.
- Only a quarter of the donut being drawn. There was a problem in GDI canvas I've just corrected. The next release will include the fix.

I don't think it's possible to draw on top of regular components using GDIPlus. This is how it looks for me after the fix mentioned above:
Project2_2017-08-01_11-14-22.png
Project2_2017-08-01_11-14-22.png (9.74 KiB) Viewed 13225 times

Code: Select all

var Series1: TPointSeries;

procedure TForm1.FormCreate(Sender: TObject);
begin
  Chart1.View3D:=False;

  Series1:=Chart1.AddSeries(TPointSeries) as TPointSeries;
  Series1.Pointer.Style:=psDonut;
  Series1.FillSampleValues(5);

  ListBox1.Items.Add('     Series1');
  ListBox1.Style:=lbOwnerDrawFixed;
end;

procedure TForm1.ListBox1DrawItem(Control: TWinControl; Index: Integer;
  Rect: TRect; State: TOwnerDrawState);
var tmpR: TRect;
begin
  with (Control as TListBox).Canvas do
  begin
    FillRect(Rect);
    TextOut(Rect.Left, Rect.Top, (Control as TListBox).Items[Index]);
    if odFocused In State then begin
      Brush.Color := ListBox1.Color;
      DrawFocusRect(Rect);
    end;
  end;

  tmpR:=Rect;
  tmpR.Right:=tmpR.Left+10;
  PaintSeriesLegend(Series1, (Control as TListBox).Canvas, tmpR);
end;

Re: “Cleaner” way to draw series than PaintSeriesLegend

Posted: Tue Aug 01, 2017 7:36 pm
by 16466355
I see. That makes sense now for the difference. And thank you for correcting the donut issue! I will look forward to that fix in the next release and I think we'll just make do with the PaintSeriesLegend method, at least for the time being...