Discussion:
Get ItemIndex for RadioGroup from cursor position?
(too old to reply)
Brad Blanchard
2010-05-13 11:24:50 UTC
Permalink
Is it possbile to get the ItemIndex for an item in a TRadioGroup from
the cursor position? I can't see any way to do it and my Google
searches haven't helped.

If it's not possible I'll have to go back to the drawing board for
what I'm trying to do, so I'd like to be sure if it's possible or not.
--
Brad Blanchard
http://www.braser.com
ap
2010-05-13 14:11:54 UTC
Permalink
Post by Brad Blanchard
If it's not possible I'll have to go back to the drawing board for
what I'm trying to do,
And what exactly are you trying to do?

TRadiogroup's ItemIndex and current mouse cursor position are totally
separate things. No matter how much you move the cursor around the
Radiogroup, the black dot position does no move anywhere as long as you
do not touch anything with your mouse.

If you do touch, then the OnClick event fires and your code does
automatically know which Radio Item was clicked.

I can only quess that you have some new fancy effect in your mind. And
to achieve that you should have to fight against the standard Windows
Control's behaviour. If this is the case, I can only say that it usually
is not a good idea for an average users' daily bases use.
-ap
Brad Blanchard
2010-05-13 14:33:36 UTC
Permalink
Post by ap
And what exactly are you trying to do?
Users are presented with a list of words or phrases as RadioGroup items
which they can left-click on in order to hear the corresponding .mp3 file.
I want them to be able to right-click to bring up a PopUp menu in order to
be able to copy the sound file somewhere else. No fancy effects.
Post by ap
TRadiogroup's ItemIndex and current mouse cursor position are totally
separate things. No matter how much you move the cursor around the
Radiogroup, the black dot position does no move anywhere as long as you
do not touch anything with your mouse.
Since the TRadioGroup onContextPopup does have a "MousePos: TPoint"
property to situate the PopUp menu, I was hoping there might be some
sneaky way to get the ItemIndex too. Wishful thinking, I guess. If there's
no other way, I'll change the RadioGroup for a ListBox. That shouldn't
cause too much code-rewriting. I'm just hesitant to do it since the
RadioGroup code has been in place and working without hitches for several
years now.
--
Brad Blanchard
http://www.braser.com
a***@aol.com
2010-05-13 16:11:32 UTC
Permalink
�Since the TRadioGroup onContextPopup does have a "MousePos: TPoint"
property to situate the PopUp menu, I was hoping there might be some
sneaky way to get the ItemIndex too. Wishful thinking, I guess. If there's
no other way, I'll change the RadioGroup for a ListBox. That shouldn't
cause too much code-rewriting. I'm just hesitant to do it since the
RadioGroup code has been in place and working without hitches for several
years now.
If you'vr got the MousePoint you could use regions to find where the
mouse is.

Using Windows API, call CreateRectRgn()for each radio-button area
specifying the rectangle for each area where the mouse might fall.
Then you can check each one using PtInRegion(), the appropriate region
handle & the mouse position, and go from there.

I would personaly have replaced the TRadioGroup with TRadioButtons in
a GroupBox. TRadioButtons have MouseDown event handlers.

Alan Lloyd
Brad Blanchard
2010-05-13 16:29:54 UTC
Permalink
Post by a***@aol.com
I would personaly have replaced the TRadioGroup with TRadioButtons in
a GroupBox. TRadioButtons have MouseDown event handlers.
That's what I'm going to try tomorrow. I've been experimenting with a
ListBox this afternoon and though it's easy to use, it's visually very
unattractive for this particular user interface. The one thing I need
is a columns property (which is why I thought of the ListBox first),
but I won't know until tomorrow if there's a way to handle it with a
GroupBox and RadioButtons.

PS: thanks for the other tips too. I'll look into them if the GroupBox
idea doesn't work.
--
Brad Blanchard
http://www.braser.com
Jamie
2010-05-14 00:17:34 UTC
Permalink
Post by Brad Blanchard
Post by a***@aol.com
I would personaly have replaced the TRadioGroup with TRadioButtons in
a GroupBox. TRadioButtons have MouseDown event handlers.
That's what I'm going to try tomorrow. I've been experimenting with a
ListBox this afternoon and though it's easy to use, it's visually very
unattractive for this particular user interface. The one thing I need
is a columns property (which is why I thought of the ListBox first),
but I won't know until tomorrow if there's a way to handle it with a
GroupBox and RadioButtons.
PS: thanks for the other tips too. I'll look into them if the GroupBox
idea doesn't work.
You need to do a little more API coding but it can be done..

Using the GetChildWindowFromPointEx
RadioGroup has checkbox child controls with in it.. Once you
obtain the handle of this child control, you can then use the API's
to ID it or get the status of it etc..
---
You can also monitor the WM_COMMAND for the BN_CLICKED message. This
message is sent to the parent window, which is the radio box.. In order
to do this how ever, you must hook into the RadioGroup boxe's Window
procedure...
Lots to think about I guess :)
Rob Kennedy
2010-05-14 06:51:01 UTC
Permalink
Post by a***@aol.com
I would personaly have replaced the TRadioGroup with TRadioButtons in
a GroupBox. TRadioButtons have MouseDown event handlers.
That's exactly what a TRadioGroup is.
--
Rob
Rob Kennedy
2010-05-14 06:48:26 UTC
Permalink
Post by Brad Blanchard
Post by ap
And what exactly are you trying to do?
Users are presented with a list of words or phrases as RadioGroup items
which they can left-click on in order to hear the corresponding .mp3 file.
I want them to be able to right-click to bring up a PopUp menu in order to
be able to copy the sound file somewhere else. No fancy effects.
Then assign the buttons' PopupMenu properties.

for i := 0 to Pred(Group.Items.Count) do
Group.Buttons[i].PopupMenu := SoundCopyPopup;

No additional code needed to make the menu appear.

In the menu item's OnClick event, the Sender property will refer to the
menu item. To find out which radio button was right-clicked, check the
popup menu's PopupComponent property.
--
Rob
Rob Kennedy
2010-05-14 06:43:31 UTC
Permalink
Post by Brad Blanchard
Is it possbile to get the ItemIndex for an item in a TRadioGroup from
the cursor position? I can't see any way to do it and my Google
searches haven't helped.
If it's not possible I'll have to go back to the drawing board for
what I'm trying to do, so I'd like to be sure if it's possible or not.
Call FindVCLWindow using the current mouse pointer position. If it's a
TRadioButton, then check whether its parent is a TRadioGroup. If so,
then look for the button in the group's Buttons array. The position in
that array corresponds to the button's index.

// Pos is in screen coordinates.
// Returns -1 if there's no control there, or if the control
// isn't a radio group's button.
function GetRadioGroupIndexAt(const Pos: TPoint): Integer;
var
Control: TWinControl;
Button: TRadioButton;
Group: TCustomRadioGroup;
begin
Result := -1;
Control := FindVCLWindow(Pos);
if not Assigned(Control) then
exit;
if not (Control is TRadioButton) then
exit;
Button := TRadioButton(Control);
if not (Button.Parent is TCustomRadioGroup) then
exit;
Group := TCustomRadioGroup(Button.Parent);
try
while True do begin
Inc(Result);
if Group.Buttons[Result] = Button then
exit;
end;
except
on EListError do
exit(-1);
end;
end;
--
Rob
Brad Blanchard
2010-05-14 12:28:36 UTC
Permalink
Rob,

The GetRadioGroupIndexAt function works perfectly, and is more
straightforward to use than your other suggestion, at least to my way
of thinking. Thank you very much - you've saved me hours of having to
recode and test things, in addition to adding the FindVCLWindow
function - which I had never heard of - to my toolbag. I'm still
surprised that I wasn't able to find any information on this subject in
my searches.

For the archives and in case anyone in the future has the same need,
here's how I got it to work (3 steps):

1. Assigned the PopMenu to the RadioGroup in the Object Inspector
2. Added Rob's GetRadioGroupIndexAt to the form:

function GetRadioGroupIndexAt(const Pos: TPoint): Integer;
var
Control: TWinControl;
Button: TRadioButton;
Group: TCustomRadioGroup;
begin
Result := -1;
Control := FindVCLWindow(Pos);
if not Assigned(Control) then
exit;
if not (Control is TRadioButton) then
exit;
Button := TRadioButton(Control);
if not (Button.Parent is TCustomRadioGroup) then
exit;
Group := TCustomRadioGroup(Button.Parent);
try
while True do begin
Inc(Result);
if Group.Buttons[Result] = Button then
exit;
end;
except
on EListError do
exit(-1);
end;
end;

3: Put the following code in the PopupMenu onPopUp event:

procedure TListenForm.Pop1Popup(Sender: TObject);
var
itemnum : integer;
mpos : TPoint;
begin
GetCursorPos(mpos);
itemnum := GetRadioGroupIndexAt(MPos);
//do something with itemnum
end;
--
Brad Blanchard
http://www.braser.com
Loading...