Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Is Tk_CoordsToWindow() working?

48 views
Skip to first unread message

Georgios Petasis

unread,
Jun 2, 2012, 7:19:06 AM6/2/12
to
Hi all,

I am facing problems in finding the widget under the mouse,
Tk_CoordsToWindow() does not seem to return correct information.

Using also the Tk equivalent:

puts "widget under mouse: [winfo containing {*}[winfo pointerxy .]]"

does not print any Tk path, despite the mouse is over Tk widgets.

Any idea why? (Linux/X11, Tk 8.6 latest fossil sources)

George

Andreas Leitgeb

unread,
Jun 2, 2012, 7:53:21 AM6/2/12
to
Maybe something with virtual-root? (winfo containing)

Georgios Petasis

unread,
Jun 2, 2012, 8:20:38 AM6/2/12
to a...@logic.at, Andreas Leitgeb
I am not sure I have understood. "winfo pointerxy" returns either root,
or virtual window coordinates. "winfo containing" also expects the same
input. Isn't the following supposed to work?

winfo containing {*}[winfo pointerxy .]

Also, I get coordinates from Qt (according to the specification on root
window), which are the same ones returned by winfo pointerxy.

What is the "Tk way" to get mouse coordinates, and find the Tk widget
under the mouse?

George

Georgios Petasis

unread,
Jun 2, 2012, 8:34:07 AM6/2/12
to a...@logic.at, Andreas Leitgeb
Also, "winfo rootx win" returns 10, & "winfo rooty win" returns 85.
"winfo containing 11 96" returns nothing, instead of the window.

"winfo vrootx" & "winfo vrooty" are both 0.

George

Georgios Petasis

unread,
Jun 2, 2012, 5:13:35 PM6/2/12
to
Finally, I gave up on Tk_CoordsToWindow(). It does seem to work ok in
most cases, but not if another application has grabbed the mouse (as it
happens during drag & drop operations). In these cases, it fails to
locate the widget under the mouse (while Tk seems to get the correct
mouse coordinates).

Using XTranslateCoordinates, returns the window id of the widget under
the mouse, which can be found with Tk_IdToWindow(). Seems to work better...

George

Andreas Leitgeb

unread,
Jun 4, 2012, 6:11:34 AM6/4/12
to
Georgios Petasis <pet...@iit.demokritos.gr> wrote:
> Στις 2/6/2012 15:34, ο/η Georgios Petasis έγραψε:
>> Στις 2/6/2012 15:20, ο/η Georgios Petasis έγραψε:
>>> Στις 2/6/2012 14:53, ο/η Andreas Leitgeb έγραψε:
>>>> Georgios Petasis<pet...@iit.demokritos.gr> wrote:
>>>>> puts "widget under mouse: [winfo containing {*}[winfo pointerxy .]]"
>>>>> does not print any Tk path, despite the mouse is over Tk widgets.
>>>>> Any idea why? (Linux/X11, Tk 8.6 latest fossil sources)
>>>> Maybe something with virtual-root? (winfo containing)
>>> I am not sure I have understood. "winfo pointerxy" returns either root,
>>> or virtual window coordinates. "winfo containing" also expects the same
>>> input. Isn't the following supposed to work?
>>> winfo containing {*}[winfo pointerxy .]

Well, it does seem to work on my machine.

>> Also, "winfo rootx win" returns 10, & "winfo rooty win" returns 85.
>> "winfo containing 11 96" returns nothing, instead of the window.
>> "winfo vrootx" & "winfo vrooty" are both 0.

That about virtual root was rather an idle guess. While I use
virtual desktops all the time, I haven't yet grokked the semantics
about virtual root and root windows. I think, there's also a couple
of different approaches to virtual desktops. Gnome seems to consider
the desktops layed out side by side, such that if you move a window
over the right border of first desktop, then the off-part shows up
on left side of second desktop. fvwm also did it that way. With Unity
I no longer observe this, and icewm also had independent desktops like
Unity has now. Then there's also this virtual root thing where the
Xserver does the panning and all apps and windowmanager only see one
desktop and do not know that user sees only part of it at a time.

> Finally, I gave up on Tk_CoordsToWindow(). It does seem to work ok in
> most cases, but not if another application has grabbed the mouse (as it
> happens during drag & drop operations). In these cases, it fails to
> locate the widget under the mouse (while Tk seems to get the correct
> mouse coordinates).

It even works with grabs here:
I type this in an interactive "wish":
set foo {
after 1000 $foo
puts w:[winfo containing {*}[winfo pointerxy .]]
}; after 1000 $foo
and watch the terminal while moving the mouse.
I then start a "text-select"-operation in a different terminal window (so as
not to block wish's output), drag over the toplevel, and see "w:." printed.

> Using XTranslateCoordinates, returns the window id of the widget under
> the mouse, which can be found with Tk_IdToWindow(). Seems to work better...

Good thing you found a workaround, but the problem itself seems to
be not all that generally observable.

Georgios Petasis

unread,
Jun 4, 2012, 6:36:04 AM6/4/12
to a...@logic.at, Andreas Leitgeb
Στις 4/6/2012 13:11, ο/η Andreas Leitgeb έγραψε:
>> Using XTranslateCoordinates, returns the window id of the widget under
>> the mouse, which can be found with Tk_IdToWindow(). Seems to work better...
>
> Good thing you found a workaround, but the problem itself seems to
> be not all that generally observable.
>

It is very easy to reproduce:

Try dragging a file from nautilus (gnome file manager) over the tk
window. No window will be printed in tk, as "winfo containing" will fail
to find the tk window below the mouse.

I just tested in my Fedora 17 gnome (fallback) session, under RealVNC.

George

Andreas Leitgeb

unread,
Jun 4, 2012, 7:02:24 AM6/4/12
to
Georgios Petasis <pet...@iit.demokritos.gr> wrote:
> Στις 4/6/2012 13:11, ο/η Andreas Leitgeb έγραψε:
>>> Using XTranslateCoordinates, returns the window id of the widget under
>>> the mouse, which can be found with Tk_IdToWindow(). Seems to work better...
>> Good thing you found a workaround, but the problem itself seems to
>> be not all that generally observable.
> It is very easy to reproduce:
> Try dragging a file from nautilus (gnome file manager) over the tk
> window. No window will be printed in tk, as "winfo containing" will fail
> to find the tk window below the mouse.

That's a different story. The mouse is actually over that (overrideredirected)
window that shows the icon being dragged.

I did the after-thing (see my previous posting up-thread), and while "holding"
a file from nautilus, I not just dragged it over the wish-window, but moved the
mouse fast over it, forth and back. Casually I got the mouse out of the dragged
icon and inside wish's ".", and when that happened while the after-script ran,
I actually got "w:." printed. Would probably be easier to reproduce with a
maximized "." and the repetition-interval of the after-script reduced.

Anyway, that's not going to help you with determining tk-windows as drop-targets.
(And I fear, I can't help with that, either.)

I'm a bit surprised that XTranslateCoordinates doesn't also just report the
drag-icon.

Georgios Petasis

unread,
Jun 4, 2012, 7:14:44 AM6/4/12
to a...@logic.at, Andreas Leitgeb
No, it doesn't. It reports the Tk widget.

George

Andreas Leitgeb

unread,
Jun 4, 2012, 7:28:17 AM6/4/12
to
Georgios Petasis <pet...@iit.demokritos.gr> wrote:
> Στις 4/6/2012 14:02, ο/η Andreas Leitgeb έγραψε:
>> Georgios Petasis<pet...@iit.demokritos.gr> wrote:
>>> Στις 4/6/2012 13:11, ο/η Andreas Leitgeb έγραψε:
>>>>> Using XTranslateCoordinates, returns the window id of the widget under
>>>>> the mouse, which can be found with Tk_IdToWindow(). Seems to work better...
>>>> Good thing you found a workaround, but the problem itself seems to
>>>> be not all that generally observable.
>>> It is very easy to reproduce:
>>> Try dragging a file from nautilus (gnome file manager) over the tk
>>> window. No window will be printed in tk, as "winfo containing" will fail
>>> to find the tk window below the mouse.
>> That's a different story. The mouse is actually over that (overrideredirected)
>> window that shows the icon being dragged.
>>
>> I'm a bit surprised that XTranslateCoordinates doesn't also just report the
>> drag-icon.
>
> No, it doesn't. It reports the Tk widget.

What did you pass as src_w and dest_w (2nd and 3rd params) to
XTranslateCoordinates ?

Georgios Petasis

unread,
Jun 4, 2012, 10:44:19 AM6/4/12
to a...@logic.at, Andreas Leitgeb
The (virtual) root and a tk toplevel window.

George

Andreas Leitgeb

unread,
Jun 4, 2012, 2:56:01 PM6/4/12
to
Ah, that of course explains, why it doesn't see the icon window.

But then, your app would probably also see itself as drop-target,
if it happened to be below(by stacking order) a normal nautilus
window (likely the actual drop-target intended by the user).

Georgios Petasis

unread,
Jun 5, 2012, 5:11:41 AM6/5/12
to a...@logic.at, Andreas Leitgeb
Στις 4/6/2012 21:56, ο/η Andreas Leitgeb έγραψε:
>
> Ah, that of course explains, why it doesn't see the icon window.
>
> But then, your app would probably also see itself as drop-target,
> if it happened to be below(by stacking order) a normal nautilus
> window (likely the actual drop-target intended by the user).
>

No, because during a drag operations, client messages are delivered only
to the window on top (by stacking order) by the drag source.
When an application receives such a message, its windows are below the
mouse.

George

Andreas Leitgeb

unread,
Jun 8, 2012, 4:57:22 AM6/8/12
to
I surely learned more in this thread, than I was able to help :)

With what I gathered here, I wonder if it was worthwile to TIP a
new option for [winfo containing], that would restrict the search to
the shell's own windows, by passing the respective toplevel to the
lowlevel call.

How common do others consider the scenario of this thread?

Georgios Petasis

unread,
Jun 8, 2012, 6:05:36 AM6/8/12
to a...@logic.at, Andreas Leitgeb
I have the impression that [winfo containing] already restricts itself
to the windows that belong to the same application:

"If no window in this application contains the point then an empty
string is returned."

I mostly lean towards the opinion that it is bug somewhere, and
Tk_CoordsToWindow() silently gives up, when there is a mouse grab.
An easy fix is to add a call to XTranslateCoordinates as an easy "fix"
in Tk_CoordsToWindow(), if everything else goes wrong (as I did in TkDND).

George

Andreas Leitgeb

unread,
Jun 8, 2012, 6:45:31 AM6/8/12
to
Georgios Petasis <pet...@iit.demokritos.gr> wrote:
> Στις 8/6/2012 11:57, ο/η Andreas Leitgeb έγραψε:
>> Georgios Petasis<pet...@iit.demokritos.gr> wrote:
>>> Στις 4/6/2012 21:56, ο/η Andreas Leitgeb έγραψε:
>>>> Ah, that of course explains, why it doesn't see the icon window.
>>>> But then, your app would probably also see itself as drop-target,
>>>> if it happened to be below(by stacking order) a normal nautilus
>>>> window (likely the actual drop-target intended by the user).
>>> No, because during a drag operations, client messages are delivered only
>>> to the window on top (by stacking order) by the drag source.
>>> When an application receives such a message, its windows are below the
>>> mouse.
>> I surely learned more in this thread, than I was able to help :)
>> With what I gathered here, I wonder if it was worthwile to TIP a
>> new option for [winfo containing], that would restrict the search to
>> the shell's own windows, by passing the respective toplevel to the
>> lowlevel call.
>> How common do others consider the scenario of this thread?
> I have the impression that [winfo containing] already restricts itself
> to the windows that belong to the same application:
> "If no window in this application contains the point then an empty
> string is returned."

I think it finds the topmost window under the mouse, then determines
if it is a window of this shell, and if so, maps the OS's window id
to the widget path, otherwise to empty string.

> I mostly lean towards the opinion that it is bug somewhere, and
> Tk_CoordsToWindow() silently gives up, when there is a mouse grab.

It surely doesn't have anything to do with the grab. (just made another
experiment to verify: even without a grab, winfo containing doesn't
see a tk-toplevel that is covered by a foreign window at the pointer-
position.)

> An easy fix is to add a call to XTranslateCoordinates as an easy "fix"
> in Tk_CoordsToWindow(), if everything else goes wrong (as I did in TkDND).

I'd be surprised, if Tk_CoordsToWindow didn't already use XTranslateCoordinates
on X11 platform. I'd expect it to use the root-window for dest_w, rather than
any toplevel as you do. That's why my suggestion :)

Donal K. Fellows

unread,
Jun 9, 2012, 8:31:29 PM6/9/12
to
On 08/06/2012 11:45, Andreas Leitgeb wrote:
> I'd be surprised, if Tk_CoordsToWindow didn't already use XTranslateCoordinates
> on X11 platform.

It does. It always did. (I remember reading that bit of the code in Tk
4.0b1...)

> I'd expect it to use the root-window for dest_w, rather than
> any toplevel as you do. That's why my suggestion :)

To pick between toplevels (which are have no parent-child relationship
at the X11 level) you have to start from the root window. Perhaps there
is a need for [winfo containing] to have a '-within $window' option?

Donal.

Georgios Petasis

unread,
Jun 10, 2012, 4:37:36 AM6/10/12
to
Perhaps yes, but I would like to see that reflected also in the C API.

To say the truth, in re-implementing tkdnd to be more "compatible" with
Tk than tkdnd 1.x series (i.e. to not start its own event loops, but
re-use Tk's loop), I faced many limitations.

The main problems were:

1) Tk_CoordsToWindow() mentioned here.

2) The fact that you cannot pass a timestamp when retrieving the
selection. GTK has no problem with it (i.e. you will get the selection
no matter what the timestamp is), Qt will not return the selection
unless a specific timestamp (as the XDND speciffication states) is used.
The current workaround is to use Tk's selection mechanism if I detect an
in-process drop, and use another implementation:
Register an event handler for SelectionNotify, perform
XConvertSelection() with the proper timestamp, and get the selection.

It mostly works, except with a small delay that is added (which at times
may exceed 10 sec, so you get a timeout). Usually clicking on the Tk
window helps (you get immediately the selection) - I don't know why.

3) The Tk selection is limited, in that it can handle only 8 & 32 bits
in format. No support for 16 bits (i.e. application/x-color).

4) The fact that Tk selection cannot deal with 16 bit data, poses also
difficulties in sending data to other applications: Tk is very good in
sending text, so I have implemented a hybrid scheme: I use tk selection
to send anything that is 8 bits, and XChangeProperty() to send data in
16 bit format (without support for INCR of course).
I miss of course the ability to specify the format (and not "auto-guess"
it from the ATOM), and of course add support for 16 bits. It is easy to
add these to Tk, its a pain to re-implement everything.

5) It is unclear how you can stop Tk from a selection handler.
I register a selection handler for every dnd type. If my type is 8 bits,
everything is fine, I just pass the string to Tk.
(There is a problem also there, as Tk expects strings to be chopped at
bytes, and the script level is very bad in working with bytes - I
convert every string to a list of bytes, get the part I want with
lrange, and convert back the bytes into a string).

But if the format should be 16 bits, and I use my selection
implementation, how can I stop the selection handler for continuing?
According to the manual, I can create an error, but in this case Tk
issues a background error (it is not obvious from the manual that it
should do so). Looking at the code, I saw a "hole" (TCL_OK & TCL_ERROR
are checked explicitly), so I return TCL_BREAK. But nothing is said
about this in the manual, and I don't know in which versions this
workaround works.

George
0 new messages