mirror of
https://github.com/brl/mutter.git
synced 2024-11-24 17:10:40 -05:00
...
This commit is contained in:
parent
0f5fdeb1b1
commit
834452ca2c
51
src/frame.c
51
src/frame.c
@ -35,6 +35,16 @@ struct _MetaFrameActionGrab
|
|||||||
int start_button;
|
int start_button;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* This lacks ButtonReleaseMask to avoid the auto-grab
|
||||||
|
* since it breaks our popup menu
|
||||||
|
*/
|
||||||
|
#define EVENT_MASK (StructureNotifyMask | SubstructureNotifyMask | \
|
||||||
|
ExposureMask | \
|
||||||
|
ButtonPressMask | ButtonReleaseMask | \
|
||||||
|
PointerMotionMask | PointerMotionHintMask | \
|
||||||
|
EnterWindowMask | LeaveWindowMask)
|
||||||
|
|
||||||
|
|
||||||
static void clear_tip (MetaFrame *frame);
|
static void clear_tip (MetaFrame *frame);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@ -244,14 +254,7 @@ meta_window_ensure_frame (MetaWindow *window)
|
|||||||
window->size_hints.win_gravity);
|
window->size_hints.win_gravity);
|
||||||
|
|
||||||
attrs.background_pixel = frame->bg_pixel;
|
attrs.background_pixel = frame->bg_pixel;
|
||||||
attrs.event_mask =
|
attrs.event_mask = EVENT_MASK;
|
||||||
StructureNotifyMask | SubstructureNotifyMask | ExposureMask |
|
|
||||||
/* We need OwnerGrabButtonMask because during a button
|
|
||||||
* press we may need to transfer control to the UI slave.
|
|
||||||
*/
|
|
||||||
ButtonPressMask | ButtonReleaseMask | OwnerGrabButtonMask |
|
|
||||||
PointerMotionMask | PointerMotionHintMask |
|
|
||||||
EnterWindowMask | LeaveWindowMask;
|
|
||||||
|
|
||||||
frame->xwindow = XCreateWindow (window->display->xdisplay,
|
frame->xwindow = XCreateWindow (window->display->xdisplay,
|
||||||
window->screen->xroot,
|
window->screen->xroot,
|
||||||
@ -804,6 +807,38 @@ meta_frame_event (MetaFrame *frame,
|
|||||||
frame->grab->start_window_y = frame->window->rect.height;
|
frame->grab->start_window_y = frame->window->rect.height;
|
||||||
frame->grab->start_button = event->xbutton.button;
|
frame->grab->start_button = event->xbutton.button;
|
||||||
}
|
}
|
||||||
|
else if (control == META_FRAME_CONTROL_MENU &&
|
||||||
|
event->xbutton.button == 1)
|
||||||
|
{
|
||||||
|
int x, y, width, height;
|
||||||
|
MetaFrameInfo info;
|
||||||
|
|
||||||
|
meta_verbose ("Menu control clicked on %s\n",
|
||||||
|
frame->window->desc);
|
||||||
|
|
||||||
|
meta_frame_init_info (frame, &info);
|
||||||
|
frame->window->screen->engine->get_control_rect (&info,
|
||||||
|
META_FRAME_CONTROL_MENU,
|
||||||
|
&x, &y, &width, &height,
|
||||||
|
frame->theme_data);
|
||||||
|
|
||||||
|
/* Let the menu get a grab. The user could release button
|
||||||
|
* before the menu gets the grab, in which case the
|
||||||
|
* menu gets somewhat confused, but it's not that
|
||||||
|
* disastrous.
|
||||||
|
*/
|
||||||
|
XUngrabPointer (frame->window->display->xdisplay,
|
||||||
|
event->xbutton.time);
|
||||||
|
|
||||||
|
meta_ui_slave_show_window_menu (frame->window->screen->uislave,
|
||||||
|
frame->window,
|
||||||
|
frame->rect.x + x,
|
||||||
|
frame->rect.y + y + height,
|
||||||
|
event->xbutton.button,
|
||||||
|
META_MESSAGE_MENU_ALL,
|
||||||
|
META_MESSAGE_MENU_MINIMIZE,
|
||||||
|
event->xbutton.time);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ButtonRelease:
|
case ButtonRelease:
|
||||||
|
@ -52,7 +52,17 @@ struct _MetaKeyBinding
|
|||||||
|
|
||||||
static MetaKeyBinding bindings[] = {
|
static MetaKeyBinding bindings[] = {
|
||||||
{ XK_F1, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (0), 0 },
|
{ XK_F1, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (0), 0 },
|
||||||
{ XK_F2, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (1), 0 }
|
{ XK_F2, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (1), 0 },
|
||||||
|
{ XK_F3, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (2), 0 },
|
||||||
|
{ XK_F4, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (3), 0 },
|
||||||
|
{ XK_F5, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (4), 0 },
|
||||||
|
{ XK_F6, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (5), 0 },
|
||||||
|
{ XK_1, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (0), 0 },
|
||||||
|
{ XK_2, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (1), 0 },
|
||||||
|
{ XK_3, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (2), 0 },
|
||||||
|
{ XK_4, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (3), 0 },
|
||||||
|
{ XK_5, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (4), 0 },
|
||||||
|
{ XK_6, Mod1Mask, handle_activate_workspace, GINT_TO_POINTER (5), 0 }
|
||||||
};
|
};
|
||||||
|
|
||||||
void
|
void
|
||||||
|
190
src/menu.c
Normal file
190
src/menu.c
Normal file
@ -0,0 +1,190 @@
|
|||||||
|
/* Metacity window menu */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2001 Havoc Pennington
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful, but
|
||||||
|
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||||||
|
* 02111-1307, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "menu.h"
|
||||||
|
#include "main.h"
|
||||||
|
#include <gdk/gdkx.h>
|
||||||
|
|
||||||
|
typedef struct _MenuItem MenuItem;
|
||||||
|
typedef struct _MenuData MenuData;
|
||||||
|
|
||||||
|
struct _MenuItem
|
||||||
|
{
|
||||||
|
MetaMessageWindowMenuOps op;
|
||||||
|
const char *stock_id;
|
||||||
|
const char *label;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct _MenuData
|
||||||
|
{
|
||||||
|
GdkWindow *window;
|
||||||
|
MetaMessageWindowMenuOps op;
|
||||||
|
};
|
||||||
|
|
||||||
|
static void activate_cb (GtkWidget *menuitem, gpointer data);
|
||||||
|
|
||||||
|
static GtkWidget *menu = NULL;
|
||||||
|
static MenuItem menuitems[] = {
|
||||||
|
{ META_MESSAGE_MENU_DELETE, GTK_STOCK_CLOSE, N_("Close") },
|
||||||
|
{ META_MESSAGE_MENU_MINIMIZE, NULL, N_("Minimize") },
|
||||||
|
{ META_MESSAGE_MENU_MAXIMIZE, NULL, N_("Maximize") }
|
||||||
|
};
|
||||||
|
|
||||||
|
static void
|
||||||
|
popup_position_func (GtkMenu *menu,
|
||||||
|
gint *x,
|
||||||
|
gint *y,
|
||||||
|
gboolean *push_in,
|
||||||
|
gpointer user_data)
|
||||||
|
{
|
||||||
|
GtkRequisition req;
|
||||||
|
GdkPoint *pos;
|
||||||
|
|
||||||
|
pos = user_data;
|
||||||
|
|
||||||
|
gtk_widget_size_request (GTK_WIDGET (menu), &req);
|
||||||
|
|
||||||
|
*x = pos->x;
|
||||||
|
*y = pos->y;
|
||||||
|
|
||||||
|
/* Ensure onscreen */
|
||||||
|
*x = CLAMP (*x, 0, MAX (0, gdk_screen_width () - req.width));
|
||||||
|
*y = CLAMP (*y, 0, MAX (0, gdk_screen_height () - req.height));
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
meta_window_menu_show (gulong xwindow,
|
||||||
|
int root_x, int root_y,
|
||||||
|
int button,
|
||||||
|
MetaMessageWindowMenuOps ops,
|
||||||
|
MetaMessageWindowMenuOps insensitive,
|
||||||
|
guint32 timestamp)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
GdkWindow *window;
|
||||||
|
GdkPoint *pt;
|
||||||
|
|
||||||
|
if (menu)
|
||||||
|
gtk_widget_destroy (menu);
|
||||||
|
|
||||||
|
window = gdk_xid_table_lookup (xwindow);
|
||||||
|
if (window)
|
||||||
|
g_object_ref (G_OBJECT (window));
|
||||||
|
else
|
||||||
|
window = gdk_window_foreign_new (xwindow);
|
||||||
|
|
||||||
|
/* X error creating the foreign window means NULL here */
|
||||||
|
if (window == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
menu = gtk_menu_new ();
|
||||||
|
|
||||||
|
i = 0;
|
||||||
|
while (i < G_N_ELEMENTS (menuitems))
|
||||||
|
{
|
||||||
|
if (ops & menuitems[i].op)
|
||||||
|
{
|
||||||
|
GtkWidget *mi;
|
||||||
|
MenuData *md;
|
||||||
|
|
||||||
|
if (menuitems[i].stock_id)
|
||||||
|
{
|
||||||
|
GtkWidget *image;
|
||||||
|
|
||||||
|
mi = gtk_image_menu_item_new_with_label (menuitems[i].label);
|
||||||
|
image = gtk_image_new_from_stock (menuitems[i].stock_id,
|
||||||
|
GTK_ICON_SIZE_MENU);
|
||||||
|
gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (mi),
|
||||||
|
image);
|
||||||
|
gtk_widget_show (image);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mi = gtk_menu_item_new_with_label (menuitems[i].label);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (insensitive & menuitems[i].op)
|
||||||
|
gtk_widget_set_sensitive (mi, FALSE);
|
||||||
|
|
||||||
|
md = g_new (MenuData, 1);
|
||||||
|
|
||||||
|
md->window = window;
|
||||||
|
md->op = menuitems[i].op;
|
||||||
|
|
||||||
|
gtk_signal_connect (GTK_OBJECT (mi),
|
||||||
|
"activate",
|
||||||
|
GTK_SIGNAL_FUNC (activate_cb),
|
||||||
|
md);
|
||||||
|
|
||||||
|
gtk_menu_shell_append (GTK_MENU_SHELL (menu),
|
||||||
|
mi);
|
||||||
|
|
||||||
|
gtk_widget_show (mi);
|
||||||
|
}
|
||||||
|
++i;
|
||||||
|
}
|
||||||
|
|
||||||
|
gtk_signal_connect (GTK_OBJECT (menu),
|
||||||
|
"destroy",
|
||||||
|
GTK_SIGNAL_FUNC (gtk_widget_destroyed),
|
||||||
|
&menu);
|
||||||
|
|
||||||
|
pt = g_new (GdkPoint, 1);
|
||||||
|
|
||||||
|
g_object_set_data_full (G_OBJECT (menu),
|
||||||
|
"destroy-point",
|
||||||
|
pt,
|
||||||
|
g_free);
|
||||||
|
|
||||||
|
pt->x = root_x;
|
||||||
|
pt->y = root_y;
|
||||||
|
|
||||||
|
gtk_menu_popup (GTK_MENU (menu),
|
||||||
|
NULL, NULL,
|
||||||
|
popup_position_func, pt,
|
||||||
|
button,
|
||||||
|
timestamp);
|
||||||
|
|
||||||
|
if (!GTK_MENU_SHELL (menu)->have_xgrab)
|
||||||
|
meta_ui_warning ("GtkMenu failed to grab the pointer\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
meta_window_menu_hide (void)
|
||||||
|
{
|
||||||
|
if (menu)
|
||||||
|
gtk_widget_destroy (menu);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
activate_cb (GtkWidget *menuitem, gpointer data)
|
||||||
|
{
|
||||||
|
MenuData *md;
|
||||||
|
|
||||||
|
md = data;
|
||||||
|
|
||||||
|
meta_ui_warning ("Activated menuitem\n");
|
||||||
|
|
||||||
|
gtk_widget_destroy (menu);
|
||||||
|
g_object_unref (G_OBJECT (md->window));
|
||||||
|
g_free (md);
|
||||||
|
}
|
39
src/menu.h
Normal file
39
src/menu.h
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
/* Metacity window menu */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2001 Havoc Pennington
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful, but
|
||||||
|
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||||||
|
* 02111-1307, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef META_MENU_H
|
||||||
|
#define META_MENU_H
|
||||||
|
|
||||||
|
#include <gtk/gtk.h>
|
||||||
|
#include "messages.h"
|
||||||
|
void meta_window_menu_show (gulong xwindow,
|
||||||
|
int root_x,
|
||||||
|
int root_y,
|
||||||
|
int button,
|
||||||
|
MetaMessageWindowMenuOps ops,
|
||||||
|
MetaMessageWindowMenuOps insensitive,
|
||||||
|
guint32 timestamp);
|
||||||
|
void meta_window_menu_hide (void);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
@ -108,7 +108,11 @@ meta_screen_new (MetaDisplay *display,
|
|||||||
* so create that required workspace.
|
* so create that required workspace.
|
||||||
*/
|
*/
|
||||||
screen->active_workspace = meta_workspace_new (screen);
|
screen->active_workspace = meta_workspace_new (screen);
|
||||||
/* FIXME, for debugging create another one. */
|
/* FIXME, for now there are always 6 workspaces... */
|
||||||
|
meta_workspace_new (screen);
|
||||||
|
meta_workspace_new (screen);
|
||||||
|
meta_workspace_new (screen);
|
||||||
|
meta_workspace_new (screen);
|
||||||
meta_workspace_new (screen);
|
meta_workspace_new (screen);
|
||||||
|
|
||||||
meta_screen_init_visual_info (screen);
|
meta_screen_init_visual_info (screen);
|
||||||
|
@ -71,12 +71,10 @@ void meta_screen_foreach_window (MetaScreen *scree
|
|||||||
MetaScreenWindowFunc func,
|
MetaScreenWindowFunc func,
|
||||||
gpointer data);
|
gpointer data);
|
||||||
void meta_screen_queue_frame_redraws (MetaScreen *screen);
|
void meta_screen_queue_frame_redraws (MetaScreen *screen);
|
||||||
|
|
||||||
void meta_screen_show_tip (MetaScreen *screen,
|
void meta_screen_show_tip (MetaScreen *screen,
|
||||||
int root_x,
|
int root_x,
|
||||||
int root_y,
|
int root_y,
|
||||||
const char *markup);
|
const char *markup);
|
||||||
|
|
||||||
void meta_screen_hide_tip (MetaScreen *screen);
|
void meta_screen_hide_tip (MetaScreen *screen);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -20,6 +20,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include "uislave.h"
|
#include "uislave.h"
|
||||||
|
#include "window.h"
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
@ -317,3 +318,42 @@ meta_ui_slave_hide_tip (MetaUISlave *uislave)
|
|||||||
|
|
||||||
send_message (uislave, (MetaMessage*)&hidetip);
|
send_message (uislave, (MetaMessage*)&hidetip);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
meta_ui_slave_show_window_menu (MetaUISlave *uislave,
|
||||||
|
MetaWindow *window,
|
||||||
|
int root_x,
|
||||||
|
int root_y,
|
||||||
|
int button,
|
||||||
|
MetaMessageWindowMenuOps ops,
|
||||||
|
MetaMessageWindowMenuOps insensitive,
|
||||||
|
Time timestamp)
|
||||||
|
{
|
||||||
|
MetaMessageShowWindowMenu showmenu;
|
||||||
|
|
||||||
|
memset (&showmenu, 0, META_MESSAGE_LENGTH (MetaMessageShowWindowMenu));
|
||||||
|
showmenu.header.message_code = MetaMessageShowWindowMenuCode;
|
||||||
|
showmenu.header.length = META_MESSAGE_LENGTH (MetaMessageShowWindowMenu);
|
||||||
|
|
||||||
|
showmenu.window = window->xwindow;
|
||||||
|
showmenu.root_x = root_x;
|
||||||
|
showmenu.root_y = root_y;
|
||||||
|
showmenu.button = button;
|
||||||
|
showmenu.ops = ops;
|
||||||
|
showmenu.insensitive = insensitive;
|
||||||
|
showmenu.timestamp = timestamp;
|
||||||
|
|
||||||
|
send_message (uislave, (MetaMessage*)&showmenu);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
meta_ui_slave_hide_window_menu (MetaUISlave *uislave)
|
||||||
|
{
|
||||||
|
MetaMessageHideWindowMenu hidemenu;
|
||||||
|
|
||||||
|
memset (&hidemenu, 0, META_MESSAGE_LENGTH (MetaMessageHideWindowMenu));
|
||||||
|
hidemenu.header.message_code = MetaMessageHideWindowMenuCode;
|
||||||
|
hidemenu.header.length = META_MESSAGE_LENGTH (MetaMessageHideWindowMenu);
|
||||||
|
|
||||||
|
send_message (uislave, (MetaMessage*)&hidemenu);
|
||||||
|
}
|
||||||
|
@ -64,4 +64,15 @@ void meta_ui_slave_show_tip (MetaUISlave *uislave,
|
|||||||
const char *markup_text);
|
const char *markup_text);
|
||||||
void meta_ui_slave_hide_tip (MetaUISlave *uislave);
|
void meta_ui_slave_hide_tip (MetaUISlave *uislave);
|
||||||
|
|
||||||
|
void meta_ui_slave_show_window_menu (MetaUISlave *uislave,
|
||||||
|
MetaWindow *window,
|
||||||
|
int root_x,
|
||||||
|
int root_y,
|
||||||
|
int button,
|
||||||
|
MetaMessageWindowMenuOps ops,
|
||||||
|
MetaMessageWindowMenuOps insensitive,
|
||||||
|
Time timestamp);
|
||||||
|
void meta_ui_slave_hide_window_menu (MetaUISlave *uislave);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -5,6 +5,8 @@ metacity_uislave_SOURCES = \
|
|||||||
fixedtip.h \
|
fixedtip.h \
|
||||||
fixedtip.c \
|
fixedtip.c \
|
||||||
main.c \
|
main.c \
|
||||||
|
menu.c \
|
||||||
|
menu.h \
|
||||||
messages.c \
|
messages.c \
|
||||||
messages.h \
|
messages.h \
|
||||||
messagequeue.c \
|
messagequeue.c \
|
||||||
|
@ -23,6 +23,7 @@
|
|||||||
#include "messagequeue.h"
|
#include "messagequeue.h"
|
||||||
#include "fixedtip.h"
|
#include "fixedtip.h"
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
|
#include "menu.h"
|
||||||
|
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
@ -68,6 +69,20 @@ message_callback (MetaMessageQueue *mq,
|
|||||||
meta_fixed_tip_hide ();
|
meta_fixed_tip_hide ();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case MetaMessageShowWindowMenuCode:
|
||||||
|
meta_window_menu_show (message->show_menu.window,
|
||||||
|
message->show_menu.root_x,
|
||||||
|
message->show_menu.root_y,
|
||||||
|
message->show_menu.button,
|
||||||
|
message->show_menu.ops,
|
||||||
|
message->show_menu.insensitive,
|
||||||
|
message->show_menu.timestamp);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case MetaMessageHideWindowMenuCode:
|
||||||
|
meta_window_menu_hide ();
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
meta_ui_warning ("Unhandled message code %d\n",
|
meta_ui_warning ("Unhandled message code %d\n",
|
||||||
message->header.message_code);
|
message->header.message_code);
|
||||||
@ -88,6 +103,7 @@ meta_ui_warning (const char *format, ...)
|
|||||||
va_end (args);
|
va_end (args);
|
||||||
|
|
||||||
fputs (str, stderr);
|
fputs (str, stderr);
|
||||||
|
fflush (stderr); /* though stderr is unbuffered right */
|
||||||
|
|
||||||
g_free (str);
|
g_free (str);
|
||||||
}
|
}
|
||||||
|
@ -26,6 +26,7 @@ void meta_ui_warning (const char *format, ...);
|
|||||||
|
|
||||||
/* FIXME */
|
/* FIXME */
|
||||||
#define _(x) x
|
#define _(x) x
|
||||||
|
#define N_(x) x
|
||||||
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
190
src/uislave/menu.c
Normal file
190
src/uislave/menu.c
Normal file
@ -0,0 +1,190 @@
|
|||||||
|
/* Metacity window menu */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2001 Havoc Pennington
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful, but
|
||||||
|
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||||||
|
* 02111-1307, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "menu.h"
|
||||||
|
#include "main.h"
|
||||||
|
#include <gdk/gdkx.h>
|
||||||
|
|
||||||
|
typedef struct _MenuItem MenuItem;
|
||||||
|
typedef struct _MenuData MenuData;
|
||||||
|
|
||||||
|
struct _MenuItem
|
||||||
|
{
|
||||||
|
MetaMessageWindowMenuOps op;
|
||||||
|
const char *stock_id;
|
||||||
|
const char *label;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct _MenuData
|
||||||
|
{
|
||||||
|
GdkWindow *window;
|
||||||
|
MetaMessageWindowMenuOps op;
|
||||||
|
};
|
||||||
|
|
||||||
|
static void activate_cb (GtkWidget *menuitem, gpointer data);
|
||||||
|
|
||||||
|
static GtkWidget *menu = NULL;
|
||||||
|
static MenuItem menuitems[] = {
|
||||||
|
{ META_MESSAGE_MENU_DELETE, GTK_STOCK_CLOSE, N_("Close") },
|
||||||
|
{ META_MESSAGE_MENU_MINIMIZE, NULL, N_("Minimize") },
|
||||||
|
{ META_MESSAGE_MENU_MAXIMIZE, NULL, N_("Maximize") }
|
||||||
|
};
|
||||||
|
|
||||||
|
static void
|
||||||
|
popup_position_func (GtkMenu *menu,
|
||||||
|
gint *x,
|
||||||
|
gint *y,
|
||||||
|
gboolean *push_in,
|
||||||
|
gpointer user_data)
|
||||||
|
{
|
||||||
|
GtkRequisition req;
|
||||||
|
GdkPoint *pos;
|
||||||
|
|
||||||
|
pos = user_data;
|
||||||
|
|
||||||
|
gtk_widget_size_request (GTK_WIDGET (menu), &req);
|
||||||
|
|
||||||
|
*x = pos->x;
|
||||||
|
*y = pos->y;
|
||||||
|
|
||||||
|
/* Ensure onscreen */
|
||||||
|
*x = CLAMP (*x, 0, MAX (0, gdk_screen_width () - req.width));
|
||||||
|
*y = CLAMP (*y, 0, MAX (0, gdk_screen_height () - req.height));
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
meta_window_menu_show (gulong xwindow,
|
||||||
|
int root_x, int root_y,
|
||||||
|
int button,
|
||||||
|
MetaMessageWindowMenuOps ops,
|
||||||
|
MetaMessageWindowMenuOps insensitive,
|
||||||
|
guint32 timestamp)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
GdkWindow *window;
|
||||||
|
GdkPoint *pt;
|
||||||
|
|
||||||
|
if (menu)
|
||||||
|
gtk_widget_destroy (menu);
|
||||||
|
|
||||||
|
window = gdk_xid_table_lookup (xwindow);
|
||||||
|
if (window)
|
||||||
|
g_object_ref (G_OBJECT (window));
|
||||||
|
else
|
||||||
|
window = gdk_window_foreign_new (xwindow);
|
||||||
|
|
||||||
|
/* X error creating the foreign window means NULL here */
|
||||||
|
if (window == NULL)
|
||||||
|
return;
|
||||||
|
|
||||||
|
menu = gtk_menu_new ();
|
||||||
|
|
||||||
|
i = 0;
|
||||||
|
while (i < G_N_ELEMENTS (menuitems))
|
||||||
|
{
|
||||||
|
if (ops & menuitems[i].op)
|
||||||
|
{
|
||||||
|
GtkWidget *mi;
|
||||||
|
MenuData *md;
|
||||||
|
|
||||||
|
if (menuitems[i].stock_id)
|
||||||
|
{
|
||||||
|
GtkWidget *image;
|
||||||
|
|
||||||
|
mi = gtk_image_menu_item_new_with_label (menuitems[i].label);
|
||||||
|
image = gtk_image_new_from_stock (menuitems[i].stock_id,
|
||||||
|
GTK_ICON_SIZE_MENU);
|
||||||
|
gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (mi),
|
||||||
|
image);
|
||||||
|
gtk_widget_show (image);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mi = gtk_menu_item_new_with_label (menuitems[i].label);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (insensitive & menuitems[i].op)
|
||||||
|
gtk_widget_set_sensitive (mi, FALSE);
|
||||||
|
|
||||||
|
md = g_new (MenuData, 1);
|
||||||
|
|
||||||
|
md->window = window;
|
||||||
|
md->op = menuitems[i].op;
|
||||||
|
|
||||||
|
gtk_signal_connect (GTK_OBJECT (mi),
|
||||||
|
"activate",
|
||||||
|
GTK_SIGNAL_FUNC (activate_cb),
|
||||||
|
md);
|
||||||
|
|
||||||
|
gtk_menu_shell_append (GTK_MENU_SHELL (menu),
|
||||||
|
mi);
|
||||||
|
|
||||||
|
gtk_widget_show (mi);
|
||||||
|
}
|
||||||
|
++i;
|
||||||
|
}
|
||||||
|
|
||||||
|
gtk_signal_connect (GTK_OBJECT (menu),
|
||||||
|
"destroy",
|
||||||
|
GTK_SIGNAL_FUNC (gtk_widget_destroyed),
|
||||||
|
&menu);
|
||||||
|
|
||||||
|
pt = g_new (GdkPoint, 1);
|
||||||
|
|
||||||
|
g_object_set_data_full (G_OBJECT (menu),
|
||||||
|
"destroy-point",
|
||||||
|
pt,
|
||||||
|
g_free);
|
||||||
|
|
||||||
|
pt->x = root_x;
|
||||||
|
pt->y = root_y;
|
||||||
|
|
||||||
|
gtk_menu_popup (GTK_MENU (menu),
|
||||||
|
NULL, NULL,
|
||||||
|
popup_position_func, pt,
|
||||||
|
button,
|
||||||
|
timestamp);
|
||||||
|
|
||||||
|
if (!GTK_MENU_SHELL (menu)->have_xgrab)
|
||||||
|
meta_ui_warning ("GtkMenu failed to grab the pointer\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
meta_window_menu_hide (void)
|
||||||
|
{
|
||||||
|
if (menu)
|
||||||
|
gtk_widget_destroy (menu);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
activate_cb (GtkWidget *menuitem, gpointer data)
|
||||||
|
{
|
||||||
|
MenuData *md;
|
||||||
|
|
||||||
|
md = data;
|
||||||
|
|
||||||
|
meta_ui_warning ("Activated menuitem\n");
|
||||||
|
|
||||||
|
gtk_widget_destroy (menu);
|
||||||
|
g_object_unref (G_OBJECT (md->window));
|
||||||
|
g_free (md);
|
||||||
|
}
|
39
src/uislave/menu.h
Normal file
39
src/uislave/menu.h
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
/* Metacity window menu */
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2001 Havoc Pennington
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License as
|
||||||
|
* published by the Free Software Foundation; either version 2 of the
|
||||||
|
* License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful, but
|
||||||
|
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||||||
|
* 02111-1307, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef META_MENU_H
|
||||||
|
#define META_MENU_H
|
||||||
|
|
||||||
|
#include <gtk/gtk.h>
|
||||||
|
#include "messages.h"
|
||||||
|
void meta_window_menu_show (gulong xwindow,
|
||||||
|
int root_x,
|
||||||
|
int root_y,
|
||||||
|
int button,
|
||||||
|
MetaMessageWindowMenuOps ops,
|
||||||
|
MetaMessageWindowMenuOps insensitive,
|
||||||
|
guint32 timestamp);
|
||||||
|
void meta_window_menu_hide (void);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
@ -66,6 +66,8 @@ typedef struct _MetaMessageFooter MetaMessageFooter;
|
|||||||
typedef struct _MetaMessageCheck MetaMessageCheck;
|
typedef struct _MetaMessageCheck MetaMessageCheck;
|
||||||
typedef struct _MetaMessageShowTip MetaMessageShowTip;
|
typedef struct _MetaMessageShowTip MetaMessageShowTip;
|
||||||
typedef struct _MetaMessageHideTip MetaMessageHideTip;
|
typedef struct _MetaMessageHideTip MetaMessageHideTip;
|
||||||
|
typedef struct _MetaMessageShowWindowMenu MetaMessageShowWindowMenu;
|
||||||
|
typedef struct _MetaMessageHideWindowMenu MetaMessageHideWindowMenu;
|
||||||
|
|
||||||
typedef enum
|
typedef enum
|
||||||
{
|
{
|
||||||
@ -75,7 +77,9 @@ typedef enum
|
|||||||
MetaMessageNullCode,
|
MetaMessageNullCode,
|
||||||
MetaMessageCheckCode,
|
MetaMessageCheckCode,
|
||||||
MetaMessageShowTipCode,
|
MetaMessageShowTipCode,
|
||||||
MetaMessageHideTipCode
|
MetaMessageHideTipCode,
|
||||||
|
MetaMessageShowWindowMenuCode,
|
||||||
|
MetaMessageHideWindowMenuCode
|
||||||
} MetaMessageCode;
|
} MetaMessageCode;
|
||||||
|
|
||||||
struct _MetaMessageHeader
|
struct _MetaMessageHeader
|
||||||
@ -124,12 +128,42 @@ struct _MetaMessageHideTip
|
|||||||
MetaMessageFooter footer;
|
MetaMessageFooter footer;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef enum
|
||||||
|
{
|
||||||
|
META_MESSAGE_MENU_DELETE = 1 << 0,
|
||||||
|
META_MESSAGE_MENU_MINIMIZE = 1 << 1,
|
||||||
|
META_MESSAGE_MENU_MAXIMIZE = 1 << 2,
|
||||||
|
META_MESSAGE_MENU_ALL = META_MESSAGE_MENU_DELETE | META_MESSAGE_MENU_MINIMIZE | META_MESSAGE_MENU_MAXIMIZE
|
||||||
|
} MetaMessageWindowMenuOps;
|
||||||
|
|
||||||
|
struct _MetaMessageShowWindowMenu
|
||||||
|
{
|
||||||
|
MetaMessageHeader header;
|
||||||
|
MetaMessageWindowMenuOps ops;
|
||||||
|
MetaMessageWindowMenuOps insensitive;
|
||||||
|
gulong window;
|
||||||
|
int root_x;
|
||||||
|
int root_y;
|
||||||
|
guint32 timestamp;
|
||||||
|
int button;
|
||||||
|
MetaMessageFooter footer;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct _MetaMessageHideWindowMenu
|
||||||
|
{
|
||||||
|
MetaMessageHeader header;
|
||||||
|
|
||||||
|
MetaMessageFooter footer;
|
||||||
|
};
|
||||||
|
|
||||||
union _MetaMessage
|
union _MetaMessage
|
||||||
{
|
{
|
||||||
MetaMessageHeader header;
|
MetaMessageHeader header;
|
||||||
MetaMessageCheck check;
|
MetaMessageCheck check;
|
||||||
MetaMessageShowTip show_tip;
|
MetaMessageShowTip show_tip;
|
||||||
MetaMessageShowTip hide_tip;
|
MetaMessageShowTip hide_tip;
|
||||||
|
MetaMessageShowWindowMenu show_menu;
|
||||||
|
MetaMessageHideWindowMenu hide_menu;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Slave-side message send/read code */
|
/* Slave-side message send/read code */
|
||||||
|
Loading…
Reference in New Issue
Block a user