Example without BalloonHint1 works as designed. No issues with the Hint refresh.
procedure TForm1.ControlList1MouseMove(Sender: TObject;
Shift: TShiftState; X, Y: Integer);
begin
ControlList1.ShowHint:=false;
//ControlList1.CustomHint <-------value is not set as it is not required.
ControlList1.Hint := IntToStr(ControlList1.HotItemIndex);
ControlList1.ShowHint:=true;
end;
When I add a TBalloonHint, the BalloonHint does not display properly.
procedure TForm1.ControlList1MouseMove(Sender: TObject;
Shift: TShiftState; X, Y: Integer);
begin
ControlList1.ShowHint:=false;
BalloonHint1.Delay:=0;
BalloonHint1.HideAfter:=-1;
ControlList1.CustomHint:=BalloonHint1;
ControlList1.Hint := IntToStr(ControlList1.HotItemIndex);
ControlList1.ShowHint:=true;
end;
When I move my mouse over the ControlList for the first time. A BalloonHint does not show.
If I move my mouse over again (for the 2nd time) then the HotItemIndex from the previous movement shows the index.

Is there a way to do a BalloonHint1.Refresh? I have tested some of the following:
Application.CancelHint; ///something that I dont want to do... but i gave it a try
also
ControlList1.ShowHint:=false;
ControlList1.ShowHint:=true;