TeeChart VCL for Borland/CodeGear/Embarcadero RAD Studio, Delphi and C++ Builder.
-
Errol
- Newbie
- Posts: 75
- Joined: Thu Jul 11, 2013 12:00 am
Post
by Errol » Wed Dec 07, 2022 4:05 am
Good afternoon
I have a persistent problem with placing a title above self-stacked bar charts. My code works correctly if the bottom axis has specified scaling, but not if the scaling is automatic. The (edited) procedure I use is shown below.
Code: Select all
procedure TPBQuickGraph.PlaceWellNames;
var
h, LLeft, LWidth, LHeight: integer;
LAcross: integer;
LRect: TRect;
for h := 1 to fIntervalQueryCollection.SeriesListB.Count - 1 do
begin
with (Chart.Tools[h] as TAnnotationTool) do
begin
Shape.CustomPosition := true;
Shape.Pen.Color := clWhite;
Shape.Transparent := true;
Shape.Font.Size := fBarNameFont;
Shape.Font.Style := Shape.Font.Style + [fsBold];
Shape.Angle := fBarNameDir;
PositionUnits := muPixels;
Text := aWellName[h];
// centre of bar, I think
LLeft := TUnitBarSeries(fIntervalQueryCollection.SeriesListB.Objects[h]).CalcXPos(0);
LWidth := Width; // width of shape??
LAcross := LWidth div 2 // half title width
if Chart.BottomAxis.Automatic then
begin
Left := LLeft - LAcross + fBarWidth Div 2; // this sort of works but varies according to bar width
end
else
Left := LLeft - LAcross; // this is correct for non-automatic scaling
end;
end;
The PlaceWellNames procedure is called in ChartBeforeDrawSeries, ChartAfterDraw as well as Zoom, UndoZoom and ChartScroll.
Thanks and regards
Errol
-
Yeray
- Site Admin
- Posts: 9622
- Joined: Tue Dec 05, 2006 12:00 am
- Location: Girona, Catalonia
-
Contact:
Post
by Yeray » Fri Dec 09, 2022 5:53 pm
Hello Errol,
I've done a simple example with 3 self-stacked bars and 3 annotation tools.
I'm using
TAnnotationTool.OnBeforeDraw
event to calculate the position of the tool and it should work both for automatic and custom axis scales, and also for scrolling and zooming:
Code: Select all
uses Series, TeeTools;
procedure TForm1.FormCreate(Sender: TObject);
var i, j: Integer;
begin
Chart1.Title.Hide;
Chart1.View3D:=False;
Chart1.Color:=clWhite;
Chart1.Gradient.Visible:=False;
Chart1.Walls.Back.Color:=clWhite;
Chart1.Walls.Back.Gradient.Visible:=False;
Chart1.Legend.Hide;
for i:=0 to 2 do
begin
with TBarSeries(Chart1.AddSeries(TBarSeries)) do
begin
MultiBar:=mbSelfStack;
Marks.Hide;
for j:=0 to 4 do
Add(5+Random*5);
end;
with TAnnotationTool(Chart1.Tools.Add(TAnnotationTool)) do
begin
Shape.CustomPosition := true;
Shape.Pen.Color := clWhite;
Shape.Transparent := true;
//Shape.Font.Size := fBarNameFont;
Shape.Font.Style := Shape.Font.Style + [fsBold];
//Shape.Angle := fBarNameDir;
//Text := aWellName[h];
Text:='Well ' + IntToStr(i+1);
OnBeforeDraw:=AnnotationToolBeforeDraw;
end;
end;
Chart1.Axes.Bottom.SetMinMax(-1, 3);
Chart1.Draw;
end;
procedure TForm1.AnnotationToolBeforeDraw(Sender: TObject);
var i: Integer;
begin
for i:=0 to Chart1.Tools.Count-1 do
if Sender = Chart1.Tools[i] then
begin
PlaceWellNames(i);
Exit;
end;
end;
procedure TForm1.PlaceWellNames(AIndex: Integer);
var
LLeft, LWidth: integer;
LAcross: integer;
annot: TAnnotationTool;
bar: TBarSeries;
begin
if Chart1.Tools[AIndex] is TAnnotationTool then
begin
annot:=TAnnotationTool(Chart1.Tools[AIndex]);
bar:=TBarSeries(Chart1[AIndex]);
// centre of bar
LLeft := bar.CalcXPos(0) + (bar.BarWidth div 2);
LWidth := annot.Width; // width of shape
LAcross := LWidth div 2; // half title width
annot.PositionUnits := muPixels;
annot.Left := LLeft - LAcross; // this is correct for non-automatic scaling
end;
end;