After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 165939 - "save as" doesn't get the focus -- gedit shouldn't use gtk_window_present
"save as" doesn't get the focus -- gedit shouldn't use gtk_window_present
Status: RESOLVED FIXED
Product: gedit
Classification: Applications
Component: general
2.9.x
Other Linux
: Normal normal
: 2.10.0
Assigned To: Gedit maintainers
gedit QA volunteers
Depends on: 166379
Blocks:
 
 
Reported: 2005-02-01 16:12 UTC by Sebastien Bacher
Modified: 2005-02-26 10:56 UTC
See Also:
GNOME target: ---
GNOME version: ---



Description Sebastien Bacher 2005-02-01 16:12:35 UTC
- open gedit
- enter some chars
- click on the save icon

the dialog doesn't get the focus, it should
Comment 1 Paolo Borelli 2005-02-01 17:25:49 UTC
This happens because when saving we make sure that we gtk_window_present the
window of the document that is being saved. That is necessary for "Save All"
which may need to save document in other windows.

AFAICS the problem is that the presented gedit windows get the timestamp of the
last user interaction, so it steals focus from the dialog.

I tried to explicitely gtk_window_present also the dialog, but it doesn't work...

wild guess (forgive my metacity ignorance): may it be that in both cases the
window and the dialog get exactly the same timestamp... if that is the case
shouldn't metacity focus a window which is presented and that which has the same
 timestamp as the currently focused window?
Comment 2 Paolo Borelli 2005-02-01 17:36:33 UTC
Note that the close dialog is affected as well
Comment 3 Paolo Borelli 2005-02-02 19:53:36 UTC
I was planning to ask elijah on irc, but it looks like he knew that and didn't
connect ;-) so I'm cc'ing him.

elijah: any idea?
Comment 4 Elijah Newren 2005-02-02 22:06:24 UTC
As mentioned on irc, you are apparently calling gtk_window_present() for the
main window _after_ already creating the save dialog.  The log from Metacity:

Window 0x2a00004 (*Unsaved D) has _NET_WM_USER_TIME of 177323150
Window 0x2a00004 (*Unsaved D) has _NET_WM_USER_TIME of 177323302
Metacity set 0x2a00004 (*Unsaved D)'s net_wm_user_time to 177324758.
Window 0x2a00004 (*Unsaved D) has _NET_WM_USER_TIME of 177324758
Updated 0x2a00004 (*Unsaved D) user_time to 177324787 due to activate call.
Window 0x2a012a2 (Save as...) has _NET_WM_USER_TIME of 177324758
COMPARISON:
  net_wm_user_time_set : 1
  net_wm_user_time     : 177324758
  initial_timestamp_set: 0
  initial_timestamp    : 0
  focus_window         : 0x2a00004 (*Unsaved D)
  fw->net_wm_user_time : 177324787

(You can duplicate this log with the patch at
http://www.gnome.org/~newren/temp/debug-focus-problems.patch--just run 'metacity
--replace' in a terminal).

The "Unsaved D[ocument]" window is the focus window at the time the "Save as..."
dialog appears.  Metacity notices that it has a timestamp later than that of the
dialog, which to it means that the user has continued interacting with the main
window while waiting for the dialog to appear.  This was due to the "activate"
call (which is triggered by gtk_window_present()).  You'll need to move your
gtk_window_present() call elsewhere, or remove it, or use a different function.

This could possibly be considered a gtk+ bug, but it'd be hard to tell without
looking closer at the gedit code.  This is because gtk_window_present() uses
gtk_get_current_event_time(), which can be the totally wrong timestamp to use. 
Personally, I think gtk_window_present should be deprecated and an alternate
version with a timestamp argument added in its place.  gtk_window_present() also
needs to be modified due to bug 128380, though that's another story, as is the
fact that I need someone to remind me to file a gtk+ bug about this function...
Comment 5 Elijah Newren 2005-02-04 18:48:14 UTC
Okay, two bugs: (1) gtk_window_present is broken and needs to be fixed (2) gedit
shouldn't be using gtk_window_present.  There's not a single useful thing it
does for you as far as I can tell (bonobo_mdi_set_active_view() is the call that
switches the to appropriate tab so I can't see what you're hoping to achieve
with gtk_window_present, though I'd love to be corrected)
Comment 6 Elijah Newren 2005-02-04 18:50:59 UTC
Oops, forgot one more comment.  On IRC today I was suggesting to pbor to use
gtk_widget_show or something similar, but I think that was just due to
misunderstanding and thinking that gtk_window_present was needed for something
for you.  I really don't think you need to do that.  Just nuke the line with the
gtk_window_present call.  If you think that line used to do something useful,
please point out to me exactly what it is and I'll look for the right solution.  :)
Comment 7 Paolo Borelli 2005-02-05 09:51:32 UTC
The line is required: bonobo_mdi_set_active_view() raises the proper tab in the
current window, but the document we want to make sure is displayed under the
dialog may also be in another window and may even be in another workspace.

As discussed on irc I'll try to use gtk_widget_show.
Comment 8 Elijah Newren 2005-02-05 15:01:22 UTC
How does one open another gedit window (everytime I tried, it merely showed me
the one that already existed)?  How does one close a gedit window which is on
another workspace?  (I tried showing windows in all workspaces in the tasklist
and then right-clicking and selecting "close", but that just results in the
dialog also appearing on the other workspace)
Comment 9 Paolo Borelli 2005-02-05 15:46:21 UTC
for instance by opening two tabs, then right clicking on the tab label,
selecting Move to another window, and then using the menu Documents->Save All.
Comment 10 Elijah Newren 2005-02-05 16:28:30 UTC
Ah, I see.  You could use libwnck for that (wnck_screen_get_active_workspace &&
wnck_window_move_to_workspace), or even copy the relevant xutils.c code from
libwnck and make direct use of it (gnome-panel does something similar for using
many EWMH hints...).  I'm about to file a bug against gtk+ about
gtk_window_present--perhaps I should also suggest a new API for putting windows
on the current workspace without focusing them (since that's what you really
want and since the code will need to be written to fix another bug with that
function anyway)?  Granted, you wouldn't be able to use it in Gnome 2.10, but
you could switch over to it in later releases after gtk+-2.8 came out...
Comment 11 Elijah Newren 2005-02-05 16:53:46 UTC
I filed bug 166379 about the problems with gtk_window_present().  I also asked
for a switch_window_to_current_workspace() API though, considering suggestion 2
I made in that bug, it's possible that a switch_to_workspace_of_this_window()
API would be better...
Comment 12 Paolo Borelli 2005-02-05 17:09:51 UTC
a more complete api to deal with workspaces would definately be useful, for
instance we would also love to have a nice api to see if there is a gedit window
on the current workspace when launching a new instance so that we could decide
if open a new toplevel or if open in a new tab... however I'm going OT.

With regard to this particular topic I would be inclined to think that the
correct behavior would be to make Save all, Close all and quit only act on all
the document in the current workspace, making the user believe that gedit
windows on different workspaces are completely independent (even if it isn't the
case).
To do this once again the api needed is something to allow to get the list of
gedit windows on the workspace... paolo: what do you think? do you agree?
Comment 13 Elijah Newren 2005-02-05 19:40:35 UTC
Both suggestions are not too difficult to implement right now using libwnck (or
by making a special xutils.c similar to gnome-panel's xstuff.c, though going
that route would obligate you to keep up with any EWMH changes made).

For what it's worth (probably nothing), I like the idea of having save all and
close all only acting on documents in the current workspace; personally I think
of workspaces as disjoint and find it very odd to have an action on a window in
one workspace affecting windows on other workspaces.  (But then again, I find
save all and close all confusing altogether as it's in the menu for *a single
window* and yet acts on other windows; it seems that the item for acting on all
windows should be separate from any one of them--to me at least)
Comment 14 Paolo Maggi 2005-02-07 09:16:04 UTC
I think Close All and Save All should act only on the documents in the current
window.
And the document list shoul contains only the documents in the current window too.

We use gtk_window_present a lot of times in gedit. 
Is this the only wrong case?

[paolo@elilix gedit]$ grep "gtk_window_present" -R . --include=*.c
./gedit/gedit-commands.c:               gtk_window_present (GTK_WINDOW (about));
./gedit/gedit-commands.c:       gtk_window_present (GTK_WINDOW (about));
./gedit/gedit-file.c:                   gtk_window_present (window);
./gedit/gedit-file.c:           gtk_window_present (window);
./gedit/gedit-file.c:           gtk_window_present (window);
./gedit/gedit-window-server.c:  gtk_window_present (GTK_WINDOW (window));
./gedit/bonobo-mdi.c:                   gtk_window_present (window);
./gedit/dialogs/gedit-preferences-dialog.c:             gtk_window_present
(GTK_WINDOW (dialog->dialog));
./gedit/dialogs/gedit-dialog-goto-line.c:               gtk_window_present
(GTK_WINDOW (dialog->dialog));
./gedit/dialogs/gedit-plugin-manager.c: gtk_window_present (GTK_WINDOW (about));
./gedit/dialogs/gedit-dialog-replace.c:         gtk_window_present (GTK_WINDOW
(dialog->dialog));
./gedit/dialogs/gedit-dialog-replace.c:         gtk_window_present (GTK_WINDOW
(dialog->dialog));
./gedit/dialogs/gedit-page-setup-dialog.c:              gtk_window_present
(GTK_WINDOW (dialog->dialog));
./gedit/gedit-mdi.c:                    gtk_window_present (window);
./gedit/gedit-mdi.c:                    gtk_window_present (GTK_WINDOW (window));
./plugins/taglist/gedit-taglist-plugin-window.c:               
gtk_window_present (tag_list_window->window);
./plugins/taglist/gedit-taglist-plugin-window.c:               
gtk_window_present (GTK_WINDOW (gedit_get_active_window ()));
./plugins/spell/gedit-spell-language-dialog.c:          gtk_window_present
(GTK_WINDOW (dialog->dialog));
./plugins/time/time.c:          gtk_window_present (GTK_WINDOW (dialog->dialog));
./plugins/docinfo/docinfo.c:            gtk_window_present (GTK_WINDOW
(dialog->dialog));
./plugins/shell_output/shell_output.c:          gtk_window_present (GTK_WINDOW
(dialog->dialog));
./plugins/sort/sort.c:          gtk_window_present (GTK_WINDOW (dialog->dialog));
Comment 15 Paolo Maggi 2005-02-07 09:22:39 UTC
BTW, I don't understand why, in this case, you think the problem is
gtk_window_present.
Comment 16 Paolo Maggi 2005-02-07 09:32:36 UTC
Oh, now I see.
I see two possible solutions:
1. Change Save all, Close all, etc. to work only on the documents of the current
window.
2. Instead of moving the gedit window to the current workspace, we should
probably  swith to the workspace of the window (is this possible?)

BTW, I think we should really go for solution #1.


Comment 17 Paolo Borelli 2005-02-07 09:37:31 UTC
> I think Close All and Save All should act only on the documents in the current
window.
> And the document list shoul contains only the documents in the current window too.

I do not agree. Having in the document list only the documents in the current
window makes it not useful: such a list is already available on tabs.
People like to have different gedit windows open, for instance I often use two
or three windows open with some tabs in each one (e.g. grouped per project) and
many of our users prefer to use a different window for each document instead of
an MDI: the documents menu should allow to fast switch document in this use case.


Beside note that also making save all and close all only act on the current
window, doesn't solve our problem complitely: for instance the problem shows up
again when using Quit, which closes all gedit windows


With regard to the other uses of gtk_window_present, I think that most of them
are ok: the problematic sequence happens only when in response to a user
interaction (button clicked) we present a window and then show a dialog which
showld be on top of the presented window: in this case the presented window ends
up with a timestamp more recent than the dialog and thus the dialog is not focused.
Comment 18 Paolo Maggi 2005-02-07 11:33:02 UTC
I don't know if it is an important new, but I have just noticed that if I use
"Ctrl + S" instead of clicking with the mouse on the toolbar or on the menu, the
"Save As" dialog gets the focus as expected.
Comment 19 Elijah Newren 2005-02-07 16:45:07 UTC
Just my $.02:

> I do not agree. Having in the document list only the documents in the current
> window makes it not useful: such a list is already available on tabs.

Perhaps it should be removed then?  Or placed in a separate window entirely? 
Users may want to work with one document per window, but if so, why does each
document have a link to all the other ones?  (Okay, so it's a gedit window that
links to all the other ones and not the document itself, but users shouldn't
need to distinguish between the two--at least not when they're using one
document per window.)  That sounds like inherently confusing UI, to me at least.

> Beside note that also making save all and close all only act on the current
> window, doesn't solve our problem complitely: for instance the problem shows
> up again when using Quit, which closes all gedit windows

It does solve the problem completely if you actually fix all three (if "quit"
acts like "quit all" then obviously its behavior should be changed if "close
all" and "save all" are).  Personally, I think it's confusing that Quit acts on
all gedit windows when I merely selected a menu option from one of them--just as
with close all and save all.
Comment 20 Elijah Newren 2005-02-07 16:55:18 UTC
Oops, forgot to comment on some other things:
> Instead of moving the gedit window to the current workspace, we should
> probably swith to the workspace of the window (is this possible?)

Yes, see bug 128380. (Note that gtk_window_present sends a _NET_ACTIVE_WINDOW
message).  If you get bug reports about not doing that, feel free to mark them
as duplicates of that bug.  If you want I'll put that bug on the 2.10.x
milestone for Metacity (I've been meaning to get to it anyway).  You could also
add a hack to do this yourself manually, but you'd have focus problems due to
bug 161361; I don't suggest it.

> We use gtk_window_present a lot of times in gedit.  Is this the only wrong
> case?

I think pbor is right about this.  Also, since I believe you don't have any
cases where you have a timeout after a user interaction to display something
(e.g. like a user typing in a URL in a web browser and then being notified 10-15
seconds later that the URL can't be found), I believe we can modify
gtk_window_present in 2.6.x to use display_x11->user_time instead of
gtk_get_current_event_time(), which should solve any problems for you.
Comment 21 Paolo Maggi 2005-02-07 17:02:17 UTC
> I believe we can modify
> gtk_window_present in 2.6.x to use display_x11->user_time instead of
> gtk_get_current_event_time(), which should solve any problems for you.

That would be awesome. Please, do :)
Comment 22 Paolo Borelli 2005-02-07 17:07:28 UTC
> It does solve the problem completely if you actually fix all three (if "quit"
> acts like "quit all" then obviously its behavior should be changed if "close
> all" and "save all" are).  Personally, I think it's confusing that Quit acts on
> all gedit windows when I merely selected a menu option from one of them--just as
> with close all and save all.

By "not completely", I was thinking at cases when quitting is triggered by
external events... I seem to recall that if you logout from gnome with some
unsaved documents in gedit you get prompted for saving them... I may be wrong
though.

About the fact to not have documents of other windows listed in the Documents
menu, I see your point and may indeed be the simpler and better solution...
still it's a bit unfortunate since I think it is an useful feature: I happen
often to have two windows open with some tabs each and switching to a particular
doc in the other window with the menu is faster than clicking your way out of
the app, raise the other window and then switch to the correct tab in the other
window.



With regard to window_present, is there any way in which we can get the
display_x11->user_time from outside gtk, so that we can have our local
non-brcken copy of window_present?
Comment 23 Elijah Newren 2005-02-07 17:38:02 UTC
> That [making gtk_window_present() less broken] would be awesome. Please, do
> :)

I'm not sure exactly how to do it (accessing an implementational detail for the
x11 version of gdk from within gtk doesn't sound trivial), but I'll try to write
a patch for that if the gtk+ maintainers don't do so soon.  Of course, it's up
to the gtk+ maintainers whether they'll accept such a patch (though I don't see
why they wouldn't so long as it can be done cleanly).

> By "not completely", I was thinking at cases when quitting is triggered by
> external events...

Good point.

> With regard to window_present, is there any way in which we can get the
> display_x11->user_time from outside gtk

Not in gtk+-2.6.x.  In gtk+ HEAD there's gdk_x11_display_get_last_user_time().
Comment 24 Elijah Newren 2005-02-11 20:40:07 UTC
There's a patch in bug 166379 to make gtk_window_present() less broken now. 
It'd be great if you could test with that; the bug listed here goes away for me...
Comment 25 Paolo Borelli 2005-02-12 12:31:11 UTC
Yup, I confirm that the patch in bug 166379 fixes the problem.
Comment 26 Elijah Newren 2005-02-21 04:36:36 UTC
The patch in bug 166379 has been committed; you may want to update configure.in
to depend on gtk+ >= 2.6.3, so that people make sure to run with the version of
gtk+ with the fix.  :-)
Comment 27 Paolo Borelli 2005-02-26 10:56:44 UTC
Ok, so this has been fixed in gtk. Closing.

(We decided to not bump the required gtk version: even if this bug is annoying,
gedit can still be built and used with an older gtk, so forcing a user to
download and build gtk+ 2,6.3 seems unpolite. Obviously distros are encouraged
to ship gtk >= 2.6.3 anyway)