diff options
author | Jan D <jan.h.d@swipnet.se> | 2010-05-16 20:49:26 +0200 |
---|---|---|
committer | Jan D <jan.h.d@swipnet.se> | 2010-05-16 20:49:26 +0200 |
commit | df68b7080ffc59c18f3289a3d4eb157f7c111454 (patch) | |
tree | 49e8c75ac59e77613bd18826319d2f65b8bd2ce0 | |
parent | a2b9f1182d6159061079fa0b480ec9ff81cc95f1 (diff) | |
download | emacs-gtk-tabs.tar.gz |
Tab keys are symbols.gtk-tabs
Tab switch is in elisp.
Save/restore point in tabs also.
-rw-r--r-- | lisp/native-tabs.el | 134 | ||||
-rw-r--r-- | src/emacs.c | 3 | ||||
-rw-r--r-- | src/gtkutil.c | 384 | ||||
-rw-r--r-- | src/gtkutil.h | 3 | ||||
-rw-r--r-- | src/lisp.h | 3 | ||||
-rw-r--r-- | src/window.c | 2 | ||||
-rw-r--r-- | src/xfns.c | 26 | ||||
-rw-r--r-- | src/xterm.c | 8 | ||||
-rw-r--r-- | src/xterm.h | 2 |
9 files changed, 252 insertions, 313 deletions
diff --git a/lisp/native-tabs.el b/lisp/native-tabs.el index afd46a9124b..283c7a640dd 100644 --- a/lisp/native-tabs.el +++ b/lisp/native-tabs.el @@ -33,7 +33,7 @@ (define-key map "\C-x70" 'tab-delete) (define-key map "\C-x71" 'tab-delete-other) (define-key map "\C-x72" 'tab-new) - (define-key map "\C-x73" 'switch-to-buffer-tab) + (define-key map "\C-x73" 'switch-to-buffer-in-tab) (define-key map "\C-x7b" 'switch-to-buffer-other-tab) (define-key map "\C-x7f" 'find-file-new-tab) (define-key map "\C-x7o" 'tab-next) @@ -58,16 +58,34 @@ Keyboard commands for tabs are: :keymap tab-mode-map (modify-all-frames-parameters (list (cons 'disable-tabs (not tab-mode))))) -(declare-function tab-new "xfns.c" ()) -(declare-function tab-delete "xfns.c" ()) -(declare-function tab-delete-other "xfns.c" ()) -(declare-function tab-next "xfns.c" ()) -(declare-function tab-previous "xfns.c" ()) -(declare-function tab-nr-of-tabs "xfns.c" ()) -(declare-function tab-configuration "xfns.c" ()) -(declare-function tab-current "xfns.c" ()) -(declare-function tab-show "xfns.c" ()) -(declare-function tab-enable "xfns.c" ()) +(declare-function tab-new "xfns.c" (&optional label frame)) +(declare-function tab-delete "xfns.c" (&optional label frame)) +(declare-function tab-delete-other "xfns.c" (&optional frame)) +(declare-function tab-next "xfns.c" (&optional frame)) +(declare-function tab-previous "xfns.c" (&optional frame)) +(declare-function tab-nr-of-tabs "xfns.c" (&optional frame)) +(declare-function tab-current "xfns.c" (&optional frame)) +(declare-function tab-show "xfns.c" (key &optional frame)) +(declare-function tab-enable "xfns.c" (enable &optional frame)) + +(defun current-tab-window-config () + (list (current-window-configuration) (point-marker))) + +(defun window-tab-config-frame (config) + (if (and (consp config) (window-configuration-p (car config))) + (window-configuration-frame (car config)) + nil)) + +(defun set-tab-window-config (config) + (and (consp config) (window-configuration-p (car config)) + (set-window-configuration (car config)) + (goto-char (cadr config)))) + +(defun change-tab-window-config-frame (config frame) + (if (and (consp config) (window-configuration-p (car config))) + (list (change-window-configuration-frame (car config) frame) + (cadr config)) + config)) (defun find-file-new-tab (filename &optional wildcards) "Edit file FILENAME, in a new tab. @@ -83,16 +101,20 @@ expand wildcards (if any) and visit multiple files." (interactive (find-file-read-args "Find file in new tab: " (confirm-nonexistent-file-or-buffer))) - (let ((value (find-file-noselect filename nil nil wildcards))) - (if (not (null (tab-new))) - (progn - (delete-other-windows) - (if (listp value) - (progn - (setq value (nreverse value)) - (cons (switch-to-buffer (car value)) - (mapcar 'switch-to-buffer (cdr value)))) - (switch-to-buffer value)))))) + (save-window-excursion + (let* ((value (find-file-noselect filename nil nil wildcards)) + (newtab (tab-new))) + (if newtab + (progn + (delete-other-windows) + (if (listp value) + (progn + (setq value (nreverse value)) + (cons (switch-to-buffer (car value)) + (dolist 'switch-to-buffer (cdr value)))) + (switch-to-buffer value)) + (put newtab 'winconfig (current-tab-window-config))))))) + (defun switch-to-buffer-other-tab (buffer-or-name &optional norecord) "Switch to buffer BUFFER-OR-NAME in another tab. @@ -123,8 +145,8 @@ documentation for additional customization information." (delete-other-windows))))) -(defun display-existing-buffer-in-tab (buffer-or-name &optional frame) - "Switch to a tab that shows BUFFER-OR-NAME on FRAME. +(defun find-tab-for-existing-buffer (buffer-or-name &optional frame) + "Find a tab that shows BUFFER-OR-NAME on FRAME. FRAME nil means selected frame. Returns the key for the tab switch to, or nil if no tab displays @@ -136,21 +158,19 @@ BUFFER-OR-NAME." (tab-key)) (while (and tabs (null tab-key)) (let* ((elt (car tabs)) - (winconf (cadr elt)) + (winconf (get elt 'winconfig)) (buffers (buffers-in-window-configuration winconf))) (if (memq buffer buffers) - (setq tab-key (car elt)) + (setq tab-key elt) (setq tabs (cdr tabs))))) - (if (and tab-key (not (equal tab-key (tab-current frame)))) - (progn - (tab-show tab-key frame) - tab-key) - nil))) + tab-key)) -(defun switch-to-buffer-tab (buffer-or-name &optional frame) +(defun switch-to-buffer-in-tab (buffer-or-name &optional frame) (interactive "BSwitch to buffer:\nP") - (if (not (display-existing-buffer-in-tab buffer-or-name frame)) - (switch-to-buffer buffer-or-name))) + (let ((tab (find-tab-for-existing-buffer buffer-or-name frame))) + (if tab + (tab-show tab frame) + (switch-to-buffer buffer-or-name)))) (defun handle-tab-event (event) "Handle tab-event to change tabs on the frame in EVENT." @@ -161,23 +181,35 @@ BUFFER-OR-NAME." (frame (car n1)) (x (car (cdr n1))) (y (cdr (cdr n1)))) - (if (eq type 2) ;; // A tab is dropped from another frame. - (let ((top y) - (left x) - (width (frame-pixel-width frame)) - (height (frame-pixel-height frame)) - (dw (x-display-pixel-width frame)) - (dh (x-display-pixel-height frame))) - (if (< dw (+ left width)) - (setq left (- dw width))) - (if (< dh (+ top height)) - (setq top (- dh height))) - (make-frame - (list (cons 'width (frame-parameter frame 'width)) - (cons 'height(frame-parameter frame 'height)) - (cons 'top top) - (cons 'left left))))))) - -(define-key special-event-map [tab-event] 'handle-tab-event) + (cond ((eq type 'tab-new-frame) ;; // A tab is dropped to the background. + (let ((tab (car (cdr n2))) + (top y) + (left x) + (width (frame-pixel-width frame)) + (height (frame-pixel-height frame)) + (dw (x-display-pixel-width frame)) + (dh (x-display-pixel-height frame))) + (if (< dw (+ left width)) + (setq left (- dw width))) + (if (< dh (+ top height)) + (setq top (- dh height))) + (make-frame + (list (cons 'width (frame-parameter frame 'width)) + (cons 'height(frame-parameter frame 'height)) + (cons 'top top) + (cons 'left left))))) + + ((eq type 'tab-changed) + (let* ((newtab (car (cdr n2))) + (newcfg (get newtab 'winconfig)) + (oldtab (cdr (cdr n2)))) + (if oldtab (put oldtab 'winconfig (current-tab-window-config))) + (if newcfg (set-tab-window-config + (if (eq (window-tab-config-frame newcfg) frame) + newcfg + (put newtab 'winconfig + (change-tab-window-config-frame newcfg frame)))) + (delete-other-windows))))))) +(define-key special-event-map [tab-event] 'handle-tab-event) diff --git a/src/emacs.c b/src/emacs.c index 400a6b0e594..72680e37615 100644 --- a/src/emacs.c +++ b/src/emacs.c @@ -1626,6 +1626,9 @@ main (int argc, char **argv) syms_of_xmenu (); syms_of_fontset (); syms_of_xsettings (); +#ifdef USE_GTK + syms_of_gtkutil (); +#endif #ifdef HAVE_X_SM syms_of_xsmfns (); #endif diff --git a/src/gtkutil.c b/src/gtkutil.c index 491b1a1c014..fbe744b5124 100644 --- a/src/gtkutil.c +++ b/src/gtkutil.c @@ -46,6 +46,8 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */ /* Avoid "differ in sign" warnings */ #define SSDATA(x) ((char *) SDATA (x)) +static Lisp_Object Qfile_sans_ext, Qx_gtk_map_stock; + /*********************************************************************** Display handling functions @@ -758,34 +760,31 @@ xg_pix_to_gcolor (w, pixel, c) Tab functions ***********************************************************************/ #define XG_TAB_KEY "emacs-tab-key" -#define XG_TAB_CONFIG_KEY "emacs-tab-config-key" + static int xg_tab_nr; -static xg_list_node tabs_gc_list; static GtkNotebook* notebook_on_hold; +static Lisp_Object Qtab_new_frame, Qtab_changed, Qtab_added, Qtab_removed; -/* If 1, show tabs even if there is only one tab. */ +/* If non-zero, show tabs even if there is only one tab. */ static int xg_always_show_tabs; -typedef struct -{ - xg_list_node ptrs; - Lisp_Object object; -} tabs_gc_data; - - -/* Store the current window configuration for frame F in widget W. */ - -static tabs_gc_data * -xg_store_win_config (GtkWidget *w, FRAME_PTR f) +static void +store_tab_event (FRAME_PTR f, + Lisp_Object arg, + int x, + int y) { + struct input_event event; Lisp_Object frame; - tabs_gc_data *conf = xmalloc (sizeof(*conf)); XSETFRAME (frame, f); - g_object_set_data (G_OBJECT (w), XG_TAB_CONFIG_KEY, conf); - xg_list_insert (&tabs_gc_list, &conf->ptrs); - conf->object = Fcurrent_window_configuration (frame); - return conf; + EVENT_INIT (event); + event.kind = TAB_EVENT; + event.frame_or_window = frame; + event.arg = arg; + event.x = make_number (x); + event.y = make_number (y); + kbd_buffer_store_event (&event); } static void @@ -798,17 +797,24 @@ xg_check_show_tabs (FRAME_PTR f, if ((shown && !should_show) || (!shown && should_show)) { - GtkRequisition req; int oldheight, row_add = 0; + if (should_show) + gtk_widget_show_all (GTK_WIDGET (wnote)); + else + gtk_widget_hide (GTK_WIDGET (wnote)); gtk_notebook_set_show_tabs (wnote, should_show); oldheight = FRAME_TABS_HEIGHT (f); - gtk_widget_size_request (f->output_data.x->notebook_widget, &req); - if (req.height > FRAME_PIXEL_HEIGHT (f)) - FRAME_TABS_HEIGHT (f) = req.height - FRAME_PIXEL_HEIGHT (f); + if (should_show) + { + GtkRequisition req; + gtk_widget_size_request (f->output_data.x->notebook_widget, &req); + FRAME_TABS_HEIGHT (f) = req.height; + } else FRAME_TABS_HEIGHT (f) = 0; + x_wm_set_size_hint (f, 0, 0); /* Try to minimize resize, when adding/removing the tabs, add some text @@ -829,8 +835,7 @@ xg_check_show_tabs (FRAME_PTR f, } } -/* Callback called when a new tab has been added. - Handle the case when a page has been dropped from another frame. */ +/* Callback called when a new tab has been added. */ static void xg_page_added_cb (GtkNotebook *notebook, @@ -839,19 +844,37 @@ xg_page_added_cb (GtkNotebook *notebook, gpointer user_data) { FRAME_PTR f = (FRAME_PTR) user_data; - tabs_gc_data *conf = g_object_get_data (G_OBJECT (child), XG_TAB_CONFIG_KEY); + char *newkey = g_object_get_data (G_OBJECT (child), XG_TAB_KEY); + GtkWidget *old = f->output_data.x->current_tab; - /* Dropped from another frame? */ - if (conf - && Fwindow_configuration_p (conf->object) && - XFRAME (Fwindow_configuration_frame (conf->object)) != f) + store_tab_event (f, Fcons (Qtab_added, + Fcons (intern (newkey), Qnil)), + 0, 0); + if (old == NULL) { - Lisp_Object frame; - XSETFRAME (frame, f); - Fchange_window_configuration_frame (conf->object, frame); + old = child; + store_tab_event (f, Fcons (Qtab_changed, Fcons (intern (newkey), Qnil)), + 0, 0); } } +/* Callback called when a new tab has been added. */ + +static void +xg_page_removed_cb (GtkNotebook *notebook, + GtkWidget *child, + guint page_num, + gpointer user_data) +{ + FRAME_PTR f = (FRAME_PTR) user_data; + char *key = g_object_get_data (G_OBJECT (child), XG_TAB_KEY); + + store_tab_event (f, Fcons (Qtab_removed, + Fcons (intern (key), Qnil)), + 0, 0); + +} + /* Callback called when the current tab changes. */ static void @@ -860,75 +883,26 @@ xg_switch_page_cb (GtkNotebook *wnote, guint page_num, gpointer user_data) { - BLOCK_INPUT; GtkWidget *w = gtk_notebook_get_nth_page (wnote, page_num); FRAME_PTR f = (FRAME_PTR) user_data; + GtkWidget *old = f->output_data.x->current_tab; - if (FRAME_GTK_WIDGET (f) && w != FRAME_GTK_WIDGET (f)) + BLOCK_INPUT; + if (w != old) { - GtkWidget *old = FRAME_GTK_WIDGET (f); - GList *children = old ? GTK_FIXED (old)->children : NULL; - GSList *todo = NULL, *iter; char *key = g_object_get_data (G_OBJECT (w), XG_TAB_KEY); - tabs_gc_data *conf = g_object_get_data (G_OBJECT (w), XG_TAB_CONFIG_KEY); - - if (!w->window) gtk_widget_realize (w); - FRAME_GTK_WIDGET (f) = w; - FRAME_X_WINDOW (f) = GTK_WIDGET_TO_X_WIN (w); - for ( ; children; children = g_list_next (children)) - { - GtkFixedChild *child = (GtkFixedChild*)children->data; - if (GTK_IS_EVENT_BOX (child->widget)) - { - GtkFixedChild *node = xmalloc (sizeof(*node)); - *node = *child; - todo = g_slist_prepend (todo, node); - } - } - - for (iter = todo; iter; iter = g_slist_next (iter)) - { - GtkFixedChild *child = (GtkFixedChild*)iter->data; - GtkWidget *wevbox = child->widget; - g_object_ref (G_OBJECT (wevbox)); - gtk_container_remove (GTK_CONTAINER (old), wevbox); - gtk_fixed_put (GTK_FIXED (w), wevbox, child->x, child->y); - g_object_unref (G_OBJECT (wevbox)); - xfree (child); - iter->data = NULL; - } - if (todo) g_slist_free (todo); - - SET_FRAME_GARBAGED (f); - cancel_mouse_face (f); - - if (old) - { - struct input_event event; - Lisp_Object frame; - - char *oldkey = g_object_get_data (G_OBJECT (old), XG_TAB_KEY); - tabs_gc_data *oconf = g_object_get_data (G_OBJECT (old), - XG_TAB_CONFIG_KEY); - if (!oconf) - oconf = xg_store_win_config (old, f); - - XSETFRAME (frame, f); - - EVENT_INIT (event); - event.kind = TAB_EVENT; - event.frame_or_window = frame; - event.arg = Fcons (make_number (1), - Fcons (make_string (key, strlen (key)), - make_string (oldkey, strlen (oldkey)))); - kbd_buffer_store_event (&event); - } - - if (conf) - Fset_window_configuration (conf->object); - else - Fdelete_other_windows (Qnil); + char *oldkey = old + ? g_object_get_data (G_OBJECT (old), XG_TAB_KEY) + : NULL; + + store_tab_event (f, + Fcons (Qtab_changed, + Fcons (intern (key), + oldkey ? intern (oldkey) : Qnil)), + 0, 0); } + + f->output_data.x->current_tab = w; xg_check_show_tabs (f, wnote); UNBLOCK_INPUT; } @@ -938,12 +912,6 @@ xg_fixed_destroy_cb (GtkWidget *widget, gpointer client_data) { char *key = g_object_get_data (G_OBJECT (widget), XG_TAB_KEY); - tabs_gc_data *conf = g_object_get_data (G_OBJECT (widget), XG_TAB_CONFIG_KEY); - if (conf) - { - xg_list_remove (&tabs_gc_list, &conf->ptrs); - xfree (conf); - } xfree (key); } @@ -1006,8 +974,6 @@ xg_add_fixed (FRAME_PTR f) GtkWidget *wfixed = gtk_fixed_new (); GdkColor bg; GtkRcStyle *style; - char buf[64]; - char *key; gtk_widget_set_name (wfixed, SSDATA (Vx_resource_name)); g_object_set_data (G_OBJECT (wfixed), XG_FRAME_DATA, (gpointer)f); @@ -1046,16 +1012,25 @@ xg_add_fixed (FRAME_PTR f) gtk_widget_modify_style (wfixed, style); gtk_widget_show (wfixed); - /* Not really needed on tab-less frames, but set it anyway so enabling - of tabs later becomes easier. */ - sprintf (buf, "Page %d", xg_tab_nr++); + return wfixed; +} + +static GtkWidget * +xg_add_fixed_for_tab (FRAME_PTR f) +{ + char buf[64]; + GtkWidget *wfixed = gtk_fixed_new (); + char *key; + + gtk_widget_set_size_request (wfixed, 0, 0); + g_object_set_data (G_OBJECT (wfixed), XG_FRAME_DATA, (gpointer)f); + sprintf (buf, "Page_%d", xg_tab_nr++); key = xstrdup (buf); g_object_set_data (G_OBJECT (wfixed), XG_TAB_KEY, key); g_signal_connect (G_OBJECT (wfixed), "destroy", G_CALLBACK (xg_fixed_destroy_cb), 0); - - + gtk_widget_show (wfixed); return wfixed; } @@ -1066,23 +1041,25 @@ const char * xg_add_tab (FRAME_PTR f, const char *name) { - GtkNotebook *wnote = GTK_NOTEBOOK (f->output_data.x->notebook_widget); - GtkWidget *wfixed = xg_add_fixed (f); - char *key = g_object_get_data (G_OBJECT (wfixed), XG_TAB_KEY); + GtkNotebook *wnote; + GtkWidget *wfixed; + char *key; int n; - GtkWidget *wlbl = xg_tab_label_widget (f, name, wfixed); + GtkWidget *wlbl; BLOCK_INPUT; + wnote = GTK_NOTEBOOK (f->output_data.x->notebook_widget); + wfixed = xg_add_fixed_for_tab (f); + key = g_object_get_data (G_OBJECT (wfixed), XG_TAB_KEY); + + wlbl = xg_tab_label_widget (f, name, wfixed); n = gtk_notebook_append_page (wnote, wfixed, wlbl); gtk_notebook_set_tab_reorderable (wnote, wfixed, TRUE); gtk_notebook_set_tab_detachable (wnote, wfixed, TRUE); if (n > 0) - { - gtk_notebook_set_current_page (wnote, n); - xg_switch_page_cb (wnote, NULL, n, f); - } + gtk_notebook_set_current_page (wnote, n); UNBLOCK_INPUT; return key; @@ -1129,7 +1106,6 @@ xg_delete_tab (FRAME_PTR f, int new_page = page_to_remove + 1; if (new_page == pages) new_page = page_to_remove - 1; gtk_notebook_set_current_page (wnote, new_page); - xg_switch_page_cb (wnote, NULL, new_page, f); } gtk_notebook_remove_page (wnote, page_to_remove); } @@ -1237,24 +1213,15 @@ xg_nb_window_create (GtkNotebook *source, gint y, gpointer data) { - struct input_event event; - Lisp_Object frame; FRAME_PTR f = g_object_get_data (G_OBJECT (page), XG_FRAME_DATA); - tabs_gc_data *oconf = g_object_get_data (G_OBJECT (page), - XG_TAB_CONFIG_KEY); - XSETFRAME (frame, f); - if (!oconf) oconf = xg_store_win_config (page, f); - - - EVENT_INIT (event); - event.kind = TAB_EVENT; - event.frame_or_window = frame; - event.arg = Fcons (make_number (2), Qnil); - event.x = make_number (x); - event.y = make_number (y); - kbd_buffer_store_event (&event); - - return notebook_on_hold = GTK_NOTEBOOK (gtk_notebook_new ()); + GtkWidget *cur = f->output_data.x->current_tab; + char *key = g_object_get_data (G_OBJECT (cur), XG_TAB_KEY); + + notebook_on_hold = GTK_NOTEBOOK (gtk_notebook_new ()); + store_tab_event (f, Fcons (Qtab_new_frame, + Fcons (intern (key), Qnil)), + x, y); + return notebook_on_hold; } int @@ -1294,10 +1261,7 @@ xg_set_current_tab (FRAME_PTR f, const char *key) } if (page >= 0 && page < pages && page != current_page) - { - gtk_notebook_set_current_page (wnote, page); - xg_switch_page_cb (wnote, NULL, page, f); - } + gtk_notebook_set_current_page (wnote, page); } @@ -1315,28 +1279,6 @@ xg_get_tab_key (FRAME_PTR f, int nr) return (const char *)g_object_get_data (G_OBJECT (w), XG_TAB_KEY); } -Lisp_Object -xg_tab_get_win_config (FRAME_PTR f, int nr) -{ - GtkNotebook *wnote = GTK_NOTEBOOK (f->output_data.x->notebook_widget); - GtkWidget *w; - tabs_gc_data *conf; - - if (!wnote || nr >= gtk_notebook_get_n_pages (wnote) - || (w = gtk_notebook_get_nth_page (wnote, nr)) == NULL) - return Qnil; - - conf = g_object_get_data (G_OBJECT (w), XG_TAB_CONFIG_KEY); - if (!conf) conf = xg_store_win_config (w, f); - else if (w == FRAME_GTK_WIDGET (f)) - { - Lisp_Object frame; - XSETFRAME (frame, f); - conf->object = Fcurrent_window_configuration (frame); - } - return conf ? conf->object : Qnil; -} - void xg_tabs_always_show (FRAME_PTR f, int show) { @@ -1354,11 +1296,15 @@ xg_setup_notebook (FRAME_PTR f, GtkWidget *wvbox, GtkWidget *wnote) { GtkRcStyle *style; - gtk_box_pack_end (GTK_BOX (wvbox), wnote, TRUE, TRUE, 0); + gtk_box_pack_end (GTK_BOX (wvbox), wnote, FALSE, FALSE, 0); + gtk_box_reorder_child (GTK_BOX (wvbox), wnote, -2); + g_signal_connect (G_OBJECT (wnote), "switch-page", G_CALLBACK (xg_switch_page_cb), f); g_signal_connect (G_OBJECT (wnote), "page-added", G_CALLBACK (xg_page_added_cb), f); + g_signal_connect (G_OBJECT (wnote), "page-removed", + G_CALLBACK (xg_page_removed_cb), f); g_object_set (G_OBJECT (wnote), "tab-border", 0, NULL); gtk_notebook_popup_disable (GTK_NOTEBOOK (wnote)); @@ -1389,75 +1335,29 @@ xg_enable_tabs (FRAME_PTR f, int enable) || (wnote != NULL && enable)) return; - g_object_ref (G_OBJECT (wfixed)); if (enable) { GtkWidget *wlbl; - char *key = g_object_get_data (G_OBJECT (wfixed), XG_TAB_KEY); + char *key; wnote = gtk_notebook_new (); + wfixed = xg_add_fixed_for_tab (f); + key = g_object_get_data (G_OBJECT (wfixed), XG_TAB_KEY); f->output_data.x->notebook_widget = wnote; - gtk_container_remove (GTK_CONTAINER (wvbox), wfixed); xg_setup_notebook (f, wvbox, wnote); wlbl = xg_tab_label_widget (f, key, wfixed); gtk_notebook_append_page (GTK_NOTEBOOK (wnote), wfixed, wlbl); gtk_notebook_set_tab_reorderable (GTK_NOTEBOOK (wnote), wfixed, TRUE); gtk_notebook_set_tab_detachable (GTK_NOTEBOOK (wnote), wfixed, TRUE); - gtk_widget_show_all (wnote); } else { xg_delete_all_tabs (f); - - /* Somehow scroll bars get destroyed when the notebook widget is - destroyed even if I take a ref to them. So remove them from - wfixed and later put them back. */ - GList *children = GTK_FIXED (wfixed)->children; - GSList *todo = NULL, *iter; - for ( ; children; children = g_list_next (children)) - { - GtkFixedChild *child = (GtkFixedChild*)children->data; - if (GTK_IS_EVENT_BOX (child->widget)) - { - GtkFixedChild *node = xmalloc (sizeof(*node)); - *node = *child; - todo = g_slist_prepend (todo, node); - } - } - - for (iter = todo; iter; iter = g_slist_next (iter)) - { - GtkFixedChild *child = (GtkFixedChild*)iter->data; - GtkWidget *wevbox = child->widget; - g_object_ref (G_OBJECT (wevbox)); - g_object_ref (G_OBJECT (gtk_bin_get_child (GTK_BIN (wevbox)))); - gtk_container_remove (GTK_CONTAINER (wfixed), wevbox); - } - gtk_container_remove (GTK_CONTAINER (wvbox), wnote); - gtk_box_pack_end (GTK_BOX (wvbox), wfixed, TRUE, TRUE, 0); f->output_data.x->notebook_widget = NULL; - - for (iter = todo; iter; iter = g_slist_next (iter)) - { - GtkFixedChild *child = (GtkFixedChild*)iter->data; - GtkWidget *wevbox = child->widget; - gtk_fixed_put (GTK_FIXED (wfixed), wevbox, child->x, child->y); - g_object_unref (G_OBJECT (wevbox)); - g_object_unref (G_OBJECT (gtk_bin_get_child (GTK_BIN (wevbox)))); - free (iter->data); - } - - if (todo) g_slist_free (todo); + f->output_data.x->current_tab = NULL; } - - gtk_widget_realize (wfixed); - gtk_widget_show_all (wfixed); - FRAME_X_WINDOW (f) = GTK_WIDGET_TO_X_WIN (wfixed); - FRAME_GTK_WIDGET (f) = wfixed; - g_object_unref (G_OBJECT (wfixed)); - gtk_widget_queue_draw (FRAME_GTK_WIDGET (f)); } @@ -1475,7 +1375,6 @@ xg_create_frame_widgets (f) GtkWidget *wnote = NULL; char *title = 0; GtkWidget *wfixed; - tabs_gc_data *conf; BLOCK_INPUT; @@ -1518,6 +1417,7 @@ xg_create_frame_widgets (f) FRAME_GTK_OUTER_WIDGET (f) = wtop; f->output_data.x->vbox_widget = wvbox; f->output_data.x->notebook_widget = wnote; + f->output_data.x->current_tab = NULL; gtk_container_add (GTK_CONTAINER (wtop), wvbox); @@ -1540,20 +1440,22 @@ xg_create_frame_widgets (f) f->win_gravity = gtk_window_get_gravity (GTK_WINDOW (FRAME_GTK_OUTER_WIDGET (f))); + wfixed = xg_add_fixed (f); + gtk_box_pack_end (GTK_BOX (wvbox), wfixed, TRUE, TRUE, 0); + if (wnote) { xg_setup_notebook (f, wvbox, wnote); if (!notebook_on_hold) - xg_add_tab (f, "Page 1"); - - wfixed = gtk_notebook_get_nth_page (GTK_NOTEBOOK (wnote), 0); - } - else - { - wfixed = xg_add_fixed (f); - gtk_box_pack_end (GTK_BOX (wvbox), wfixed, TRUE, TRUE, 0); + xg_add_tab (f, "Page_1"); + else + xg_page_added_cb (GTK_NOTEBOOK (wnote), + gtk_notebook_get_nth_page (GTK_NOTEBOOK (wnote), + 0), + 0, f); } + /* Must realize the windows so the X window gets created. It is used @@ -1563,19 +1465,10 @@ xg_create_frame_widgets (f) FRAME_X_WINDOW (f) = GTK_WIDGET_TO_X_WIN (wfixed); FRAME_GTK_WIDGET (f) = wfixed; - conf = g_object_get_data (G_OBJECT (wfixed), XG_TAB_CONFIG_KEY); - if (conf - && Fwindow_configuration_p (conf->object) && - XFRAME (Fwindow_configuration_frame (conf->object)) != f) - { - Lisp_Object frame; - XSETFRAME (frame, f); - Fchange_window_configuration_frame (conf->object, frame); - Fset_window_configuration (conf->object); - } - notebook_on_hold = NULL; - + gtk_widget_show (wfixed); + gtk_widget_show (wvbox); + UNBLOCK_INPUT; return 1; @@ -2504,8 +2397,6 @@ xg_mark_data () if (! NILP (cb_data->help)) mark_object (cb_data->help); } - for (iter = tabs_gc_list.next; iter; iter = iter->next) - mark_object (((tabs_gc_data *) iter)->object); } @@ -4535,8 +4426,8 @@ find_rtl_image (f, image, rtl) Lisp_Object rtl_image = PROP (TOOL_BAR_ITEM_IMAGES); if (!NILP (file = file_for_image (rtl_image))) { - file = call1 (intern ("file-name-sans-extension"), - Ffile_name_nondirectory (file)); + file = call1 (Qfile_sans_ext, + Ffile_name_nondirectory (file)); if (EQ (Fequal (file, rtl_name), Qt)) { image = rtl_image; @@ -4939,7 +4830,6 @@ xg_initialize () id_to_widget.max_size = id_to_widget.used = 0; id_to_widget.widgets = 0; xg_tab_nr = 1; - tabs_gc_list.prev = tabs_gc_list.next = 0; xg_always_show_tabs = 0; /* Remove F10 as a menu accelerator, it does not mix well with Emacs key @@ -4979,6 +4869,24 @@ xg_initialize () "widget \"*\" style \"noborder\"\n"); } +void +syms_of_gtkutil () +{ + Qtab_new_frame = intern_c_string ("tab-new-frame"); + staticpro (&Qtab_new_frame); + Qtab_changed = intern_c_string ("tab-changed"); + staticpro (&Qtab_changed); + Qtab_added = intern_c_string ("tab-added"); + staticpro (&Qtab_added); + Qtab_removed = intern_c_string ("tab-removed"); + staticpro (&Qtab_removed); + Qfile_sans_ext = intern_c_string ("file-name-sans-extension"); + staticpro (&Qfile_sans_ext); + Qx_gtk_map_stock = intern_c_string ("x-gtk-map-stock"); + staticpro (&Qx_gtk_map_stock); +} + + #endif /* USE_GTK */ /* arch-tag: fe7104da-bc1e-4aba-9bd1-f349c528f7e3 diff --git a/src/gtkutil.h b/src/gtkutil.h index b005498e843..a08d387809b 100644 --- a/src/gtkutil.h +++ b/src/gtkutil.h @@ -135,6 +135,7 @@ extern char *xg_get_file_name P_ ((FRAME_PTR f, int only_dir_p)); extern char *xg_get_font_name P_ ((FRAME_PTR f, char *)); + extern const char *xg_add_tab P_ ((FRAME_PTR f, const char *name)); extern void xg_delete_tab P_ ((FRAME_PTR f, const char *name)); extern void xg_delete_all_tabs P_ ((FRAME_PTR f)); @@ -146,8 +147,6 @@ extern int xg_current_tab P_ ((FRAME_PTR f)); extern const char *xg_get_tab_key P_ ((FRAME_PTR f, int nr)); extern void xg_set_current_tab P_ ((FRAME_PTR f, const char *key)); extern void xg_enable_tabs P_ ((FRAME_PTR f, int enable)); - -extern Lisp_Object xg_tab_get_win_config P_ ((FRAME_PTR f, int nr)); extern void xg_tabs_always_show P_ ((FRAME_PTR f, int show)); diff --git a/src/lisp.h b/src/lisp.h index 7f5d5df66c6..b7920a74c76 100644 --- a/src/lisp.h +++ b/src/lisp.h @@ -2636,6 +2636,9 @@ extern int pos_visible_p P_ ((struct window *, int, int *, /* Defined in xsettings.c */ extern void syms_of_xsettings P_ ((void)); +/* Defined in gtkutil.c */ +extern void syms_of_gtkutil P_ ((void)); + /* Defined in vm-limit.c. */ extern void memory_warnings P_ ((POINTER_TYPE *, void (*warnfun) ())); diff --git a/src/window.c b/src/window.c index 4874b1c7ff6..89f5e312ccb 100644 --- a/src/window.c +++ b/src/window.c @@ -6066,6 +6066,8 @@ DEFUN ("change-window-configuration-frame", Fchange_window_configuration_frame, Vwindow_list = Qnil; #undef MAP_WINDOW + + return config; } DEFUN ("buffers-in-window-configuration", Fbuffers_in_window_configuration, diff --git a/src/xfns.c b/src/xfns.c index b192263e87b..3b40f767544 100644 --- a/src/xfns.c +++ b/src/xfns.c @@ -5903,7 +5903,7 @@ DEFUN ("tab-new", Ftab_new, If LABEL is nil, use current buffer name. FRAME nil means use the selected frame. -Returns the key for the tab, which can be passed to `tab-delete'. */) +Returns the key for the tab ( symbol), which can be passed to `tab-delete'. */) (label, frame) Lisp_Object label, frame; { @@ -5925,7 +5925,7 @@ Returns the key for the tab, which can be passed to `tab-delete'. */) key = xg_add_tab (f, SDATA (label)); UNBLOCK_INPUT; - return make_string (key, strlen (key)); + return intern (key); } DEFUN ("tab-delete", Ftab_delete, @@ -5938,11 +5938,11 @@ FRAME nil means use the selected frame. */) { FRAME_PTR f = check_x_frame (frame); if (f->no_tabs) return Qnil; - if (!NILP (key) && !STRINGP (key)) - error ("Key is not string or nil"); + if (!NILP (key) && !SYMBOLP (key)) + error ("Key is not a symbol or nil"); BLOCK_INPUT; - xg_delete_tab (f, NILP (key) ? NULL : SDATA (key)); + xg_delete_tab (f, NILP (key) ? NULL : SDATA (SYMBOL_NAME (key))); UNBLOCK_INPUT; return Qnil; @@ -6056,9 +6056,7 @@ DEFUN ("tab-configuration", Ftab_configuration, Stab_configuration, 0, 1, 0, doc: /* Return the tab configuration on FRAME. FRAME nil means use the selected frame. -Returns an alist where each element is of type (KEY WINDOWCONFIG). -KEY is the name of the tab as returned by `tab_new´. -WINDOWCONFIG is the window configuration for the tab. +Returns an list where each element is a symbol representing a tab. If FRAME is a tab-less frame, returns nil. */) (frame) @@ -6072,12 +6070,10 @@ If FRAME is a tab-less frame, returns nil. */) nr = xg_tab_count (f); for (i = 0; i < nr; ++i) { - Lisp_Object wc = xg_tab_get_win_config (f, i); const char *key = xg_get_tab_key (f, i); - cc = Fcons (Fcons (key ? make_string (key, strlen (key)) : Qnil, - NILP (wc) ? wc : Fcons (wc, Qnil)), - cc); + if (key) + cc = Fcons (intern (key), cc); } return cc; @@ -6098,7 +6094,7 @@ If FRAME is a tab-less frame, returns nil. */) if (f->no_tabs) return Qnil; nr = xg_current_tab (f); const char *key = xg_get_tab_key (f, nr); - return key ? make_string (key, strlen (key)) : Qnil; + return key ? intern (key) : Qnil; } DEFUN ("tab-show", Ftab_show, @@ -6111,10 +6107,10 @@ If FRAME is a tab-less frame or the key doesn't refer to a tab, do nothing. */) { FRAME_PTR f = check_x_frame (frame); if (f->no_tabs) return Qnil; - CHECK_STRING (key); + CHECK_SYMBOL (key); BLOCK_INPUT; - xg_set_current_tab (f, SDATA (key)); + xg_set_current_tab (f, SDATA (SYMBOL_NAME (key))); UNBLOCK_INPUT; return Qnil; diff --git a/src/xterm.c b/src/xterm.c index 54cac40e091..91a65fc32cb 100644 --- a/src/xterm.c +++ b/src/xterm.c @@ -325,9 +325,6 @@ static Lisp_Object Qlatin_1; #ifdef USE_GTK /* The name of the Emacs icon file. */ static Lisp_Object xg_default_icon_file; - -/* Used in gtkutil.c. */ -Lisp_Object Qx_gtk_map_stock; #endif /* Used in x_flush. */ @@ -9265,7 +9262,7 @@ x_make_frame_visible (f) } #else /* not USE_X_TOOLKIT */ #ifdef USE_GTK - gtk_widget_show_all (FRAME_GTK_OUTER_WIDGET (f)); + gtk_widget_show (FRAME_GTK_OUTER_WIDGET (f)); gtk_window_deiconify (GTK_WINDOW (FRAME_GTK_OUTER_WIDGET (f))); #else if (FRAME_X_EMBEDDED_P (f)) @@ -10970,9 +10967,6 @@ syms_of_xterm () #ifdef USE_GTK xg_default_icon_file = make_pure_c_string ("icons/hicolor/scalable/apps/emacs.svg"); staticpro (&xg_default_icon_file); - - Qx_gtk_map_stock = intern_c_string ("x-gtk-map-stock"); - staticpro (&Qx_gtk_map_stock); #endif DEFVAR_BOOL ("x-use-underline-position-properties", diff --git a/src/xterm.h b/src/xterm.h index 09be1626c19..1925210b623 100644 --- a/src/xterm.h +++ b/src/xterm.h @@ -477,6 +477,8 @@ struct x_output GtkWidget *vbox_widget; /* The notebook (i.e. tab) widget. */ GtkWidget *notebook_widget; + /* The current note book child. */ + GtkWidget *current_tab; /* The menubar in this frame. */ GtkWidget *menubar_widget; /* The tool bar in this frame */ |