aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lisp/ChangeLog10
-rw-r--r--lisp/menu-bar.el94
-rw-r--r--src/ChangeLog57
-rw-r--r--src/frame.c10
-rw-r--r--src/frame.h6
-rw-r--r--src/gtkutil.c248
-rw-r--r--src/gtkutil.h1
-rw-r--r--src/window.c7
-rw-r--r--src/xfns.c21
-rw-r--r--src/xterm.c3
-rw-r--r--src/xterm.h26
11 files changed, 405 insertions, 78 deletions
diff --git a/lisp/ChangeLog b/lisp/ChangeLog
index 6cd759ee0a..f0332db2c9 100644
--- a/lisp/ChangeLog
+++ b/lisp/ChangeLog
@@ -1,3 +1,13 @@
+2010-07-29 Jan Djärv <[email protected]>
+
+ * menu-bar.el (menu-bar-showhide-tool-bar-menu-customize-enable-left)
+ (menu-bar-showhide-tool-bar-menu-customize-disable)
+ (menu-bar-showhide-tool-bar-menu-customize-enable-right)
+ (menu-bar-showhide-tool-bar-menu-customize-enable-top)
+ (menu-bar-showhide-tool-bar-menu-customize-enable-bottom): New functions
+ (menu-bar-showhide-tool-bar-menu): If tool bar is moveable,
+ make a menu for Options => toolbar that can move it.
+
2010-07-29 Chong Yidong <[email protected]>
* emacs-lisp/package-x.el (package--make-rss-entry):
diff --git a/lisp/menu-bar.el b/lisp/menu-bar.el
index 2c75a8822f..626472605f 100644
--- a/lisp/menu-bar.el
+++ b/lisp/menu-bar.el
@@ -968,11 +968,95 @@ mail status in mode line"))
:help ,(purecopy "Turn menu-bar on/off")
:button (:toggle . (> (frame-parameter nil 'menu-bar-lines) 0))))
-(define-key menu-bar-showhide-menu [showhide-tool-bar]
- `(menu-item ,(purecopy "Tool-bar") toggle-tool-bar-mode-from-frame
- :help ,(purecopy "Turn tool-bar on/off")
- :visible (display-graphic-p)
- :button (:toggle . (> (frame-parameter nil 'tool-bar-lines) 0))))
+(defun menu-bar-showhide-tool-bar-menu-customize-disable ()
+ "Do not display tool bars."
+ (interactive)
+ (customize-set-variable 'tool-bar-mode nil))
+(defun menu-bar-showhide-tool-bar-menu-customize-enable-left ()
+ "Display tool bars on the left side."
+ (interactive)
+ (customize-set-variable 'tool-bar-mode t)
+ (set-frame-parameter nil 'tool-bar-position 'left))
+
+(defun menu-bar-showhide-tool-bar-menu-customize-enable-right ()
+ "Display tool bars on the right side."
+ (interactive)
+ (customize-set-variable 'tool-bar-mode t)
+ (set-frame-parameter nil 'tool-bar-position 'right))
+(defun menu-bar-showhide-tool-bar-menu-customize-enable-top ()
+ "Display tool bars on the top side."
+ (interactive)
+ (customize-set-variable 'tool-bar-mode t)
+ (set-frame-parameter nil 'tool-bar-position 'top))
+(defun menu-bar-showhide-tool-bar-menu-customize-enable-bottom ()
+ "Display tool bars on the bottom side."
+ (interactive)
+ (customize-set-variable 'tool-bar-mode t)
+ (set-frame-parameter nil 'tool-bar-position 'bottom))
+
+(if (featurep 'move-toolbar)
+ (progn
+ (defvar menu-bar-showhide-tool-bar-menu (make-sparse-keymap "Tool-bar"))
+
+ (define-key menu-bar-showhide-tool-bar-menu [showhide-tool-bar-left]
+ `(menu-item ,(purecopy "On the left")
+ menu-bar-showhide-tool-bar-menu-customize-enable-left
+ :help ,(purecopy "Tool-bar at the left side")
+ :visible (display-graphic-p)
+ :button
+ (:radio . (and tool-bar-mode
+ (eq (frame-parameter nil 'tool-bar-position)
+ 'left)))))
+
+ (define-key menu-bar-showhide-tool-bar-menu [showhide-tool-bar-right]
+ `(menu-item ,(purecopy "On the right")
+ menu-bar-showhide-tool-bar-menu-customize-enable-right
+ :help ,(purecopy "Tool-bar at the right side")
+ :visible (display-graphic-p)
+ :button
+ (:radio . (and tool-bar-mode
+ (eq (frame-parameter nil 'tool-bar-position)
+ 'right)))))
+
+ (define-key menu-bar-showhide-tool-bar-menu [showhide-tool-bar-bottom]
+ `(menu-item ,(purecopy "On the bottom")
+ menu-bar-showhide-tool-bar-menu-customize-enable-bottom
+ :help ,(purecopy "Tool-bar at the bottom")
+ :visible (display-graphic-p)
+ :button
+ (:radio . (and tool-bar-mode
+ (eq (frame-parameter nil 'tool-bar-position)
+ 'bottom)))))
+
+ (define-key menu-bar-showhide-tool-bar-menu [showhide-tool-bar-top]
+ `(menu-item ,(purecopy "On the top")
+ menu-bar-showhide-tool-bar-menu-customize-enable-top
+ :help ,(purecopy "Tool-bar at the top")
+ :visible (display-graphic-p)
+ :button
+ (:radio . (and tool-bar-mode
+ (eq (frame-parameter nil 'tool-bar-position)
+ 'top)))))
+
+ (define-key menu-bar-showhide-tool-bar-menu [showhide-tool-bar-none]
+ `(menu-item ,(purecopy "None")
+ menu-bar-showhide-tool-bar-menu-customize-disable
+ :help ,(purecopy "Turn tool-bar off")
+ :visible (display-graphic-p)
+ :button (:radio . (eq tool-bar-mode nil))))
+
+ (define-key menu-bar-showhide-menu [showhide-tool-bar]
+ `(menu-item ,(purecopy "Tool-bar") ,menu-bar-showhide-tool-bar-menu
+ :visible (display-graphic-p)))
+
+ )
+ ;; else not tool bar that can move.
+ (define-key menu-bar-showhide-menu [showhide-tool-bar]
+ `(menu-item ,(purecopy "Tool-bar") toggle-tool-bar-mode-from-frame
+ :help ,(purecopy "Turn tool-bar on/off")
+ :visible (display-graphic-p)
+ :button (:toggle . (> (frame-parameter nil 'tool-bar-lines) 0))))
+)
(define-key menu-bar-options-menu [showhide]
`(menu-item ,(purecopy "Show/Hide") ,menu-bar-showhide-menu))
diff --git a/src/ChangeLog b/src/ChangeLog
index 6dfd993ede..1fd18d0abb 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,60 @@
+2010-07-29 Jan Djärv <[email protected]>
+
+ * xterm.h (struct x_output): Add toolbar_top_height,
+ toolbar_bottom_height, toolbar_left_width, toolbar_right_width. Remove
+ toolbar_height.
+ if USE_GTK: Add hbox_widget and toolbar_in_hbox.
+ (FRAME_TOOLBAR_TOP_HEIGHT, FRAME_TOOLBAR_BOTTOM_HEIGHT)
+ (FRAME_TOOLBAR_LEFT_WIDTH, FRAME_TOOLBAR_RIGHT_WIDTH): New macros.
+ (FRAME_TOOLBAR_HEIGHT): Is now TOP_HEIGHT + BOTTOM_HEIGHT.
+
+ * xterm.c (x_set_window_size_1): Add FRAME_TOOLBAR_WIDTH to pixelwidth.
+
+ * xfns.c (x_set_tool_bar_position): New function.
+ (xic_set_statusarea): Use FRAME_TOOLBAR_TOP_HEIGHT.
+ (x_frame_parm_handlers): Add x_set_tool_bar_position.
+ (syms_of_xfns): if USE_GTK, provide move-toolbar.
+
+ * window.c (calc_absolute_offset): Check for FRAME_TOOLBAR_TOP_HEIGHT
+ and FRAME_TOOLBAR_LEFT_WIDTH.
+
+ * gtkutil.h (xg_change_toolbar_position): Declare.
+
+ * gtkutil.c (FRAME_TOTAL_PIXEL_WIDTH): New macro.
+ (xg_frame_set_char_size): Add FRAME_TOOLBAR_WIDTH to pixelwidth.
+ (xg_height_or_width_changed): Use FRAME_TOTAL_PIXEL_WIDTH.
+ (xg_create_frame_widgets): Create a hobox for placing widgets
+ vertically. Use gtk_box_pack_start.
+ (xg_height_or_width_changed): Renamed from xg_height_changed.
+ (x_wm_set_size_hint): Add FRAME_TOOLBAR_WIDTH to base_width.
+ (xg_update_frame_menubar, free_frame_menubar): Change to
+ xg_height_or_width_changed.
+ (xg_tool_bar_detach_callback): Update left/right/top/bottom tool bar
+ size correctly. Remove hardcoded 4, instead use handlebox size -
+ toolbar size.
+ (xg_tool_bar_attach_callback): Update left/right/top/bottom tool bar
+ size correctly. Use handlebox size + toolbar size as additional
+ size.
+ (xg_pack_tool_bar): POS is a new parameter.
+ Set orientation of tool bar based on pos.
+ Only make handlebox_widget if NULL.
+ Check if tool bar goes to vbox or hbox depending on pos.
+ (xg_update_tool_bar_sizes): New function.
+ (update_frame_tool_bar): Remove old_req, new_req. Do not get tool bar
+ height, call xg_update_tool_bar_sizes instead.
+ (free_frame_tool_bar): Remove from hbox or vbox depending on
+ toolbar_in_hbox, Set all FRAME_TOOLBAR_*_(WIDTH|HEIGHT) to zero.
+ (xg_change_toolbar_position): New function.
+
+ * frame.h (struct frame): Add tool_bar_position.
+ (Qbottom): Declare.
+
+ * frame.c (Qtool_bar_position): New variable.
+ (make_frame): Set tool_bar_position to Qtop.
+ (frame_parms): Add tool-bar-position.
+ (x_report_frame_params): Store tool_bar_position.
+ (x_set_fringe_width): Reset wm size hint after fringe changes.
+
2010-07-29 Dan Nicolaescu <[email protected]>
Make lisp_time_argument declaration work on all systems.
diff --git a/src/frame.c b/src/frame.c
index ae8fdff807..809f660f1d 100644
--- a/src/frame.c
+++ b/src/frame.c
@@ -119,7 +119,7 @@ Lisp_Object Qparent_id;
Lisp_Object Qtitle, Qname;
Lisp_Object Qexplicit_name;
Lisp_Object Qunsplittable;
-Lisp_Object Qmenu_bar_lines, Qtool_bar_lines;
+Lisp_Object Qmenu_bar_lines, Qtool_bar_lines, Qtool_bar_position;
Lisp_Object Vmenu_bar_mode, Vtool_bar_mode;
Lisp_Object Qleft_fringe, Qright_fringe;
Lisp_Object Qbuffer_predicate, Qbuffer_list, Qburied_buffer_list;
@@ -323,6 +323,7 @@ make_frame (int mini_p)
f->menu_bar_window = Qnil;
f->tool_bar_window = Qnil;
f->tool_bar_items = Qnil;
+ f->tool_bar_position = Qtop;
f->desired_tool_bar_string = f->current_tool_bar_string = Qnil;
f->n_tool_bar_items = 0;
f->left_fringe_width = f->right_fringe_width = 0;
@@ -2816,6 +2817,7 @@ static struct frame_parm_table frame_parms[] =
{"font-backend", &Qfont_backend},
{"alpha", &Qalpha},
{"sticky", &Qsticky},
+ {"tool-bar-position", &Qtool_bar_position},
};
#ifdef HAVE_WINDOW_SYSTEM
@@ -3209,6 +3211,7 @@ x_report_frame_params (struct frame *f, Lisp_Object *alistptr)
XSETFASTINT (tem, FRAME_X_OUTPUT (f)->parent_desc);
store_in_alist (alistptr, Qexplicit_name, (f->explicit_name ? Qt : Qnil));
store_in_alist (alistptr, Qparent_id, tem);
+ store_in_alist (alistptr, Qtool_bar_position, f->tool_bar_position);
}
@@ -3441,6 +3444,11 @@ void
x_set_fringe_width (struct frame *f, Lisp_Object new_value, Lisp_Object old_value)
{
compute_fringe_widths (f, 1);
+#ifdef HAVE_X_WINDOWS
+ /* Must adjust this so window managers report correct number of columns. */
+ if (FRAME_X_WINDOW (f) != 0)
+ x_wm_set_size_hint (f, 0, 0);
+#endif
}
void
diff --git a/src/frame.h b/src/frame.h
index 6ab2b07dd9..3b680d5cad 100644
--- a/src/frame.h
+++ b/src/frame.h
@@ -191,6 +191,10 @@ struct frame
/* Desired and current tool-bar items. */
Lisp_Object tool_bar_items;
+ /* Where tool bar is, can be left, right, top or bottom. The native
+ tool bar only supports top. */
+ Lisp_Object tool_bar_position;
+
/* Desired and current contents displayed in tool_bar_window. */
Lisp_Object desired_tool_bar_string, current_tool_bar_string;
@@ -1071,7 +1075,7 @@ extern Lisp_Object Qbackground_mode;
extern Lisp_Object Qx_resource_name;
-extern Lisp_Object Qleft, Qright, Qtop, Qbox;
+extern Lisp_Object Qleft, Qright, Qtop, Qbox, Qbottom;
extern Lisp_Object Qdisplay;
#ifdef HAVE_WINDOW_SYSTEM
diff --git a/src/gtkutil.c b/src/gtkutil.c
index 3fb05ba134..b31eb2d21f 100644
--- a/src/gtkutil.c
+++ b/src/gtkutil.c
@@ -44,6 +44,9 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
#define FRAME_TOTAL_PIXEL_HEIGHT(f) \
(FRAME_PIXEL_HEIGHT (f) + FRAME_MENUBAR_HEIGHT (f) + FRAME_TOOLBAR_HEIGHT (f))
+#define FRAME_TOTAL_PIXEL_WIDTH(f) \
+ (FRAME_PIXEL_WIDTH (f) + FRAME_TOOLBAR_WIDTH (f))
+
/* Avoid "differ in sign" warnings */
#define SSDATA(x) ((char *) SDATA (x))
@@ -640,7 +643,8 @@ xg_frame_set_char_size (FRAME_PTR f, int cols, int rows)
/* FRAME_TEXT_COLS_TO_PIXEL_WIDTH uses scroll_bar_actual_width, so call it
after calculating that value. */
- pixelwidth = FRAME_TEXT_COLS_TO_PIXEL_WIDTH (f, cols);
+ pixelwidth = FRAME_TEXT_COLS_TO_PIXEL_WIDTH (f, cols)
+ + FRAME_TOOLBAR_WIDTH (f);
/* Do this before resize, as we don't know yet if we will be resized. */
@@ -677,14 +681,15 @@ xg_frame_set_char_size (FRAME_PTR f, int cols, int rows)
}
}
-/* Handle height changes (i.e. add/remove menu/toolbar).
+/* Handle height/width changes (i.e. add/remove/move menu/toolbar).
The policy is to keep the number of editable lines. */
static void
-xg_height_changed (FRAME_PTR f)
+xg_height_or_width_changed (FRAME_PTR f)
{
gtk_window_resize (GTK_WINDOW (FRAME_GTK_OUTER_WIDGET (f)),
- FRAME_PIXEL_WIDTH (f), FRAME_TOTAL_PIXEL_HEIGHT (f));
+ FRAME_TOTAL_PIXEL_WIDTH (f),
+ FRAME_TOTAL_PIXEL_HEIGHT (f));
f->output_data.x->hint_flags = 0;
x_wm_set_size_hint (f, 0, 0);
}
@@ -733,7 +738,7 @@ int
xg_create_frame_widgets (FRAME_PTR f)
{
GtkWidget *wtop;
- GtkWidget *wvbox;
+ GtkWidget *wvbox, *whbox;
GtkWidget *wfixed;
GdkColor bg;
GtkRcStyle *style;
@@ -749,12 +754,14 @@ xg_create_frame_widgets (FRAME_PTR f)
xg_set_screen (wtop, f);
wvbox = gtk_vbox_new (FALSE, 0);
+ whbox = gtk_hbox_new (FALSE, 0);
wfixed = gtk_fixed_new (); /* Must have this to place scroll bars */
- if (! wtop || ! wvbox || ! wfixed)
+ if (! wtop || ! wvbox || ! whbox || ! wfixed)
{
if (wtop) gtk_widget_destroy (wtop);
if (wvbox) gtk_widget_destroy (wvbox);
+ if (whbox) gtk_widget_destroy (whbox);
if (wfixed) gtk_widget_destroy (wfixed);
UNBLOCK_INPUT;
@@ -775,11 +782,13 @@ xg_create_frame_widgets (FRAME_PTR f)
FRAME_GTK_OUTER_WIDGET (f) = wtop;
FRAME_GTK_WIDGET (f) = wfixed;
f->output_data.x->vbox_widget = wvbox;
+ f->output_data.x->hbox_widget = whbox;
gtk_widget_set_has_window (wfixed, TRUE);
gtk_container_add (GTK_CONTAINER (wtop), wvbox);
- gtk_box_pack_end (GTK_BOX (wvbox), wfixed, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX (wvbox), whbox, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX (whbox), wfixed, TRUE, TRUE, 0);
if (FRAME_EXTERNAL_TOOL_BAR (f))
update_frame_tool_bar (f);
@@ -889,7 +898,7 @@ x_wm_set_size_hint (FRAME_PTR f, long int flags, int user_position)
size_hints.height_inc = FRAME_LINE_HEIGHT (f);
hint_flags |= GDK_HINT_BASE_SIZE;
- base_width = FRAME_TEXT_COLS_TO_PIXEL_WIDTH (f, 0);
+ base_width = FRAME_TEXT_COLS_TO_PIXEL_WIDTH (f, 0) + FRAME_TOOLBAR_WIDTH (f);
base_height = FRAME_TEXT_LINES_TO_PIXEL_HEIGHT (f, 0)
+ FRAME_MENUBAR_HEIGHT (f) + FRAME_TOOLBAR_HEIGHT (f);
@@ -2828,7 +2837,7 @@ xg_update_frame_menubar (FRAME_PTR f)
gtk_widget_show_all (x->menubar_widget);
gtk_widget_size_request (x->menubar_widget, &req);
FRAME_MENUBAR_HEIGHT (f) = req.height;
- xg_height_changed (f);
+ xg_height_or_width_changed (f);
UNBLOCK_INPUT;
return 1;
@@ -2851,7 +2860,7 @@ free_frame_menubar (FRAME_PTR f)
the container. */
x->menubar_widget = 0;
FRAME_MENUBAR_HEIGHT (f) = 0;
- xg_height_changed (f);
+ xg_height_or_width_changed (f);
UNBLOCK_INPUT;
}
}
@@ -3548,13 +3557,21 @@ xg_tool_bar_detach_callback (GtkHandleBox *wbox,
if (f)
{
+ GtkRequisition req, req2;
FRAME_X_OUTPUT (f)->toolbar_detached = 1;
-
- /* When detaching a tool bar, not everything dissapear. There are
- a few pixels left that are used to drop the tool bar back into
- place. */
- FRAME_TOOLBAR_HEIGHT (f) = 4;
- xg_height_changed (f);
+ gtk_widget_size_request (GTK_WIDGET (wbox), &req);
+ gtk_widget_size_request (w, &req2);
+ req.width -= req2.width;
+ req.height -= req2.height;
+ if (FRAME_TOOLBAR_TOP_HEIGHT (f) != 0)
+ FRAME_TOOLBAR_TOP_HEIGHT (f) = req.height;
+ else if (FRAME_TOOLBAR_BOTTOM_HEIGHT (f) != 0)
+ FRAME_TOOLBAR_BOTTOM_HEIGHT (f) = req.height;
+ else if (FRAME_TOOLBAR_RIGHT_WIDTH (f) != 0)
+ FRAME_TOOLBAR_RIGHT_WIDTH (f) = req.width;
+ else if (FRAME_TOOLBAR_LEFT_WIDTH (f) != 0)
+ FRAME_TOOLBAR_LEFT_WIDTH (f) = req.width;
+ xg_height_or_width_changed (f);
}
}
@@ -3575,13 +3592,21 @@ xg_tool_bar_attach_callback (GtkHandleBox *wbox,
if (f)
{
- GtkRequisition req;
-
+ GtkRequisition req, req2;
FRAME_X_OUTPUT (f)->toolbar_detached = 0;
-
- gtk_widget_size_request (w, &req);
- FRAME_TOOLBAR_HEIGHT (f) = req.height;
- xg_height_changed (f);
+ gtk_widget_size_request (GTK_WIDGET (wbox), &req);
+ gtk_widget_size_request (w, &req2);
+ req.width += req2.width;
+ req.height += req2.height;
+ if (FRAME_TOOLBAR_TOP_HEIGHT (f) != 0)
+ FRAME_TOOLBAR_TOP_HEIGHT (f) = req.height;
+ else if (FRAME_TOOLBAR_BOTTOM_HEIGHT (f) != 0)
+ FRAME_TOOLBAR_BOTTOM_HEIGHT (f) = req.height;
+ else if (FRAME_TOOLBAR_RIGHT_WIDTH (f) != 0)
+ FRAME_TOOLBAR_RIGHT_WIDTH (f) = req.width;
+ else if (FRAME_TOOLBAR_LEFT_WIDTH (f) != 0)
+ FRAME_TOOLBAR_LEFT_WIDTH (f) = req.width;
+ xg_height_or_width_changed (f);
}
}
@@ -3656,41 +3681,63 @@ xg_tool_bar_item_expose_callback (GtkWidget *w,
return FALSE;
}
+#ifdef HAVE_GTK_ORIENTABLE_SET_ORIENTATION
+#define toolbar_set_orientation(w, o) \
+ gtk_orientable_set_orientation (GTK_ORIENTABLE (w), o)
+#else
+#define toolbar_set_orientation(w, o) \
+ gtk_toolbar_set_orientation (GTK_TOOLBAR (w), o)
+#endif
+
/* Attach a tool bar to frame F. */
static void
-xg_pack_tool_bar (FRAME_PTR f)
+xg_pack_tool_bar (FRAME_PTR f, Lisp_Object pos)
{
struct x_output *x = f->output_data.x;
- int vbox_pos = x->menubar_widget ? 1 : 0;
-
- x->handlebox_widget = gtk_handle_box_new ();
- g_signal_connect (G_OBJECT (x->handlebox_widget), "child-detached",
- G_CALLBACK (xg_tool_bar_detach_callback), f);
- g_signal_connect (G_OBJECT (x->handlebox_widget), "child-attached",
- G_CALLBACK (xg_tool_bar_attach_callback), f);
-
- gtk_container_add (GTK_CONTAINER (x->handlebox_widget),
- x->toolbar_widget);
-
- gtk_box_pack_start (GTK_BOX (x->vbox_widget), x->handlebox_widget,
- FALSE, FALSE, 0);
+ int into_hbox = EQ (pos, Qleft) || EQ (pos, Qright);
- gtk_box_reorder_child (GTK_BOX (x->vbox_widget), x->handlebox_widget,
- vbox_pos);
+ toolbar_set_orientation (x->toolbar_widget,
+ into_hbox
+ ? GTK_ORIENTATION_VERTICAL
+ : GTK_ORIENTATION_HORIZONTAL);
+ if (!x->handlebox_widget)
+ {
+ x->handlebox_widget = gtk_handle_box_new ();
+ g_signal_connect (G_OBJECT (x->handlebox_widget), "child-detached",
+ G_CALLBACK (xg_tool_bar_detach_callback), f);
+ g_signal_connect (G_OBJECT (x->handlebox_widget), "child-attached",
+ G_CALLBACK (xg_tool_bar_attach_callback), f);
+ gtk_container_add (GTK_CONTAINER (x->handlebox_widget),
+ x->toolbar_widget);
+ }
- gtk_widget_show (x->toolbar_widget);
- gtk_widget_show (x->handlebox_widget);
+ if (into_hbox)
+ {
+ gtk_box_pack_start (GTK_BOX (x->hbox_widget), x->handlebox_widget,
+ FALSE, FALSE, 0);
+
+ if (EQ (pos, Qleft))
+ gtk_box_reorder_child (GTK_BOX (x->hbox_widget),
+ x->handlebox_widget,
+ 0);
+ x->toolbar_in_hbox = 1;
+ }
+ else
+ {
+ int vbox_pos = x->menubar_widget ? 1 : 0;
+ gtk_box_pack_start (GTK_BOX (x->vbox_widget), x->handlebox_widget,
+ FALSE, FALSE, 0);
+
+ if (EQ (pos, Qtop))
+ gtk_box_reorder_child (GTK_BOX (x->vbox_widget),
+ x->handlebox_widget,
+ vbox_pos);
+ x->toolbar_in_hbox = 0;
+ }
}
/* Create a tool bar for frame F. */
-#ifdef HAVE_GTK_ORIENTABLE_SET_ORIENTATION
-#define toolbar_set_orientation(w, o) \
- gtk_orientable_set_orientation (GTK_ORIENTABLE (w), o)
-#else
-#define toolbar_set_orientation(w, o) \
- gtk_toolbar_set_orientation (GTK_TOOLBAR (w), o)
-#endif
static void
xg_create_tool_bar (FRAME_PTR f)
@@ -3875,6 +3922,50 @@ xg_show_toolbar_item (GtkToolItem *ti)
gtk_widget_show (GTK_WIDGET (ti));
}
+static int
+xg_update_tool_bar_sizes (FRAME_PTR f)
+{
+ struct x_output *x = f->output_data.x;
+ GtkRequisition req;
+ int nl = 0, nr = 0, nt = 0, nb = 0;
+
+ gtk_widget_size_request (GTK_WIDGET (x->handlebox_widget), &req);
+ if (x->toolbar_in_hbox)
+ {
+ int pos;
+ gtk_container_child_get (GTK_CONTAINER (x->hbox_widget),
+ x->handlebox_widget,
+ "position", &pos, NULL);
+ if (pos == 0) nl = req.width;
+ else nr = req.width;
+ }
+ else
+ {
+ int pos;
+ gtk_container_child_get (GTK_CONTAINER (x->vbox_widget),
+ x->handlebox_widget,
+ "position", &pos, NULL);
+ if (pos == 0 || (pos == 1 && x->menubar_widget)) nt = req.height;
+ else nb = req.height;
+ }
+
+ if (nl != FRAME_TOOLBAR_LEFT_WIDTH (f)
+ || nr != FRAME_TOOLBAR_RIGHT_WIDTH (f)
+ || nt != FRAME_TOOLBAR_TOP_HEIGHT (f)
+ || nb != FRAME_TOOLBAR_BOTTOM_HEIGHT (f))
+ {
+ FRAME_TOOLBAR_RIGHT_WIDTH (f) = FRAME_TOOLBAR_LEFT_WIDTH (f)
+ = FRAME_TOOLBAR_TOP_HEIGHT (f) = FRAME_TOOLBAR_BOTTOM_HEIGHT (f) = 0;
+ FRAME_TOOLBAR_LEFT_WIDTH (f) = nl;
+ FRAME_TOOLBAR_RIGHT_WIDTH (f) = nr;
+ FRAME_TOOLBAR_TOP_HEIGHT (f) = nt;
+ FRAME_TOOLBAR_BOTTOM_HEIGHT (f) = nb;
+ return 1;
+ }
+
+ return 0;
+}
+
/* Update the tool bar for frame F. Add new buttons and remove old. */
@@ -3884,7 +3975,6 @@ void
update_frame_tool_bar (FRAME_PTR f)
{
int i;
- GtkRequisition old_req, new_req;
struct x_output *x = f->output_data.x;
int hmargin = 0, vmargin = 0;
GtkToolbar *wtoolbar;
@@ -3925,7 +4015,6 @@ update_frame_tool_bar (FRAME_PTR f)
xg_create_tool_bar (f);
wtoolbar = GTK_TOOLBAR (x->toolbar_widget);
- gtk_widget_size_request (GTK_WIDGET (wtoolbar), &old_req);
dir = gtk_widget_get_direction (GTK_WIDGET (wtoolbar));
for (i = 0; i < f->n_tool_bar_items; ++i)
@@ -4143,18 +4232,16 @@ update_frame_tool_bar (FRAME_PTR f)
if (ti) gtk_widget_hide_all (GTK_WIDGET (ti));
} while (ti != NULL);
- new_req.height = 0;
- if (pack_tool_bar && f->n_tool_bar_items != 0)
- xg_pack_tool_bar (f);
-
-
- gtk_widget_size_request (GTK_WIDGET (wtoolbar), &new_req);
- if (old_req.height != new_req.height
- && ! FRAME_X_OUTPUT (f)->toolbar_detached)
+ if (f->n_tool_bar_items != 0)
{
- FRAME_TOOLBAR_HEIGHT (f) = new_req.height;
- xg_height_changed (f);
+ if (pack_tool_bar)
+ xg_pack_tool_bar (f, f->tool_bar_position);
+ gtk_widget_show (x->toolbar_widget);
+ gtk_widget_show (x->handlebox_widget);
+ if (xg_update_tool_bar_sizes (f))
+ xg_height_or_width_changed (f);
}
+
UNBLOCK_INPUT;
}
@@ -4172,21 +4259,54 @@ free_frame_tool_bar (FRAME_PTR f)
BLOCK_INPUT;
/* We may have created the toolbar_widget in xg_create_tool_bar, but
not the x->handlebox_widget which is created in xg_pack_tool_bar. */
- if (is_packed)
- gtk_container_remove (GTK_CONTAINER (x->vbox_widget),
- x->handlebox_widget);
+ if (is_packed)
+ {
+ if (x->toolbar_in_hbox)
+ gtk_container_remove (GTK_CONTAINER (x->hbox_widget),
+ x->handlebox_widget);
+ else
+ gtk_container_remove (GTK_CONTAINER (x->vbox_widget),
+ x->handlebox_widget);
+ }
else
gtk_widget_destroy (x->toolbar_widget);
x->toolbar_widget = 0;
x->handlebox_widget = 0;
- FRAME_TOOLBAR_HEIGHT (f) = 0;
- xg_height_changed (f);
+ FRAME_TOOLBAR_TOP_HEIGHT (f) = FRAME_TOOLBAR_BOTTOM_HEIGHT (f) = 0;
+ FRAME_TOOLBAR_LEFT_WIDTH (f) = FRAME_TOOLBAR_RIGHT_WIDTH (f) = 0;
+
+ xg_height_or_width_changed (f);
UNBLOCK_INPUT;
}
}
+int
+xg_change_toolbar_position (FRAME_PTR f, Lisp_Object pos)
+{
+ struct x_output *x = f->output_data.x;
+
+ if (! x->toolbar_widget || ! x->handlebox_widget)
+ return 1;
+
+ BLOCK_INPUT;
+ g_object_ref (x->handlebox_widget);
+ if (x->toolbar_in_hbox)
+ gtk_container_remove (GTK_CONTAINER (x->hbox_widget),
+ x->handlebox_widget);
+ else
+ gtk_container_remove (GTK_CONTAINER (x->vbox_widget),
+ x->handlebox_widget);
+ xg_pack_tool_bar (f, pos);
+ g_object_unref (x->handlebox_widget);
+ if (xg_update_tool_bar_sizes (f))
+ xg_height_or_width_changed (f);
+
+ UNBLOCK_INPUT;
+ return 1;
+}
+
/***********************************************************************
diff --git a/src/gtkutil.h b/src/gtkutil.h
index 14693650de..3f1d1a2b85 100644
--- a/src/gtkutil.h
+++ b/src/gtkutil.h
@@ -181,6 +181,7 @@ extern int xg_event_is_for_scrollbar (FRAME_PTR f, XEvent *event);
extern void update_frame_tool_bar (FRAME_PTR f);
extern void free_frame_tool_bar (FRAME_PTR f);
+extern int xg_change_toolbar_position (FRAME_PTR f, Lisp_Object pos);
extern void xg_frame_resized (FRAME_PTR f,
int pixelwidth,
diff --git a/src/window.c b/src/window.c
index 662b587150..3c556fff69 100644
--- a/src/window.c
+++ b/src/window.c
@@ -645,13 +645,18 @@ calc_absolute_offset(struct window *w, int *add_x, int *add_y)
#ifdef FRAME_MENUBAR_HEIGHT
*add_y += FRAME_MENUBAR_HEIGHT (f);
#endif
-#ifdef FRAME_TOOLBAR_HEIGHT
+#ifdef FRAME_TOOLBAR_TOP_HEIGHT
+ *add_y += FRAME_TOOLBAR_TOP_HEIGHT (f);
+#elif FRAME_TOOLBAR_HEIGHT
*add_y += FRAME_TOOLBAR_HEIGHT (f);
#endif
#ifdef FRAME_NS_TITLEBAR_HEIGHT
*add_y += FRAME_NS_TITLEBAR_HEIGHT (f);
#endif
*add_x = f->left_pos;
+#ifdef FRAME_TOOLBAR_LEFT_WIDTH
+ *add_x += FRAME_TOOLBAR_LEFT_WIDTH (f);
+#endif
}
DEFUN ("window-absolute-pixel-edges", Fwindow_absolute_pixel_edges,
diff --git a/src/xfns.c b/src/xfns.c
index f19498dfb8..6b1a78ba74 100644
--- a/src/xfns.c
+++ b/src/xfns.c
@@ -715,6 +715,23 @@ x_set_wait_for_wm (struct frame *f, Lisp_Object new_value, Lisp_Object old_value
f->output_data.x->wait_for_wm = !NILP (new_value);
}
+static void
+x_set_tool_bar_position (struct frame *f,
+ Lisp_Object new_value,
+ Lisp_Object old_value)
+{
+ if (! EQ (new_value, Qleft) && ! EQ (new_value, Qright)
+ && ! EQ (new_value, Qbottom) && ! EQ (new_value, Qtop))
+ return;
+ if (EQ (new_value, old_value)) return;
+
+#ifdef USE_GTK
+ fprintf (stderr, "Pos: %s\n", SDATA (SYMBOL_NAME (new_value)));
+ if (xg_change_toolbar_position (f, new_value))
+ f->tool_bar_position = new_value;
+#endif
+}
+
#ifdef USE_GTK
/* Set icon from FILE for frame F. By using GTK functions the icon
@@ -2344,7 +2361,7 @@ xic_set_statusarea (struct frame *f)
area.x = FRAME_PIXEL_WIDTH (f) - area.width - FRAME_INTERNAL_BORDER_WIDTH (f);
area.y = (FRAME_PIXEL_HEIGHT (f) - area.height
- FRAME_MENUBAR_HEIGHT (f)
- - FRAME_TOOLBAR_HEIGHT (f)
+ - FRAME_TOOLBAR_TOP_HEIGHT (f)
- FRAME_INTERNAL_BORDER_WIDTH (f));
XFree (needed);
@@ -5747,6 +5764,7 @@ frame_parm_handler x_frame_parm_handlers[] =
x_set_font_backend,
x_set_alpha,
x_set_sticky,
+ x_set_tool_bar_position,
};
void
@@ -5897,6 +5915,7 @@ the tool bar buttons. */);
accepts --with-x-toolkit=gtk. */
Fprovide (intern_c_string ("x-toolkit"), Qnil);
Fprovide (intern_c_string ("gtk"), Qnil);
+ Fprovide (intern_c_string ("move-toolbar"), Qnil);
DEFVAR_LISP ("gtk-version-string", &Vgtk_version_string,
doc: /* Version info for GTK+. */);
diff --git a/src/xterm.c b/src/xterm.c
index e51c1fad83..61e93470cb 100644
--- a/src/xterm.c
+++ b/src/xterm.c
@@ -8610,7 +8610,8 @@ x_set_window_size_1 (struct frame *f, int change_gravity, int cols, int rows)
compute_fringe_widths (f, 0);
- pixelwidth = FRAME_TEXT_COLS_TO_PIXEL_WIDTH (f, cols);
+ pixelwidth = FRAME_TEXT_COLS_TO_PIXEL_WIDTH (f, cols)
+ + FRAME_TOOLBAR_WIDTH (f);
pixelheight = FRAME_TEXT_LINES_TO_PIXEL_HEIGHT (f, rows)
+ FRAME_MENUBAR_HEIGHT (f) + FRAME_TOOLBAR_HEIGHT (f);
diff --git a/src/xterm.h b/src/xterm.h
index cfc786632e..c487ae4bd6 100644
--- a/src/xterm.h
+++ b/src/xterm.h
@@ -433,9 +433,15 @@ struct x_output
if the menubar is turned off. */
int menubar_height;
- /* Height of tool bar widget, in pixels.
- Zero if not using an external tool bar. */
- int toolbar_height;
+ /* Height of tool bar widget, in pixels. top_height is used if tool bar
+ at top, bottom_height if tool bar is at the bottom.
+ Zero if not using an external tool bar or if tool bar is vertical. */
+ int toolbar_top_height, toolbar_bottom_height;
+
+ /* Width of tool bar widget, in pixels. left_width is used if tool bar
+ at left, right_width if tool bar is at the right.
+ Zero if not using an external tool bar or if tool bar is horizontal. */
+ int toolbar_left_width, toolbar_right_width;
/* The tiled border used when the mouse is out of the frame. */
Pixmap border_tile;
@@ -480,6 +486,8 @@ struct x_output
GtkWidget *edit_widget;
/* The widget used for laying out widgets vertically. */
GtkWidget *vbox_widget;
+ /* The widget used for laying out widgets horizontally. */
+ GtkWidget *hbox_widget;
/* The menubar in this frame. */
GtkWidget *menubar_widget;
/* The tool bar in this frame */
@@ -488,6 +496,8 @@ struct x_output
GtkWidget *handlebox_widget;
/* Non-zero if the tool bar is detached. */
int toolbar_detached;
+ /* Non-zero if tool bar is packed into the hbox widget (i.e. vertical). */
+ int toolbar_in_hbox;
/* The last size hints set. */
GdkGeometry size_hints;
@@ -700,7 +710,15 @@ enum
#define FRAME_FONT(f) ((f)->output_data.x->font)
#define FRAME_FONTSET(f) ((f)->output_data.x->fontset)
#define FRAME_MENUBAR_HEIGHT(f) ((f)->output_data.x->menubar_height)
-#define FRAME_TOOLBAR_HEIGHT(f) ((f)->output_data.x->toolbar_height)
+#define FRAME_TOOLBAR_TOP_HEIGHT(f) ((f)->output_data.x->toolbar_top_height)
+#define FRAME_TOOLBAR_BOTTOM_HEIGHT(f) \
+ ((f)->output_data.x->toolbar_bottom_height)
+#define FRAME_TOOLBAR_HEIGHT(f) \
+ (FRAME_TOOLBAR_TOP_HEIGHT (f) + FRAME_TOOLBAR_BOTTOM_HEIGHT (f))
+#define FRAME_TOOLBAR_LEFT_WIDTH(f) ((f)->output_data.x->toolbar_left_width)
+#define FRAME_TOOLBAR_RIGHT_WIDTH(f) ((f)->output_data.x->toolbar_right_width)
+#define FRAME_TOOLBAR_WIDTH(f) \
+ (FRAME_TOOLBAR_LEFT_WIDTH (f) + FRAME_TOOLBAR_RIGHT_WIDTH (f))
#define FRAME_BASELINE_OFFSET(f) ((f)->output_data.x->baseline_offset)
/* This gives the x_display_info structure for the display F is on. */