openbox/actions/execute.c \
openbox/actions/exit.c \
openbox/actions/focus.c \
+ openbox/actions/focusfallback.c \
openbox/actions/focustobottom.c \
openbox/actions/fullscreen.c \
openbox/actions/growtoedge.c \
openbox/actions/if.c \
openbox/actions/kill.c \
openbox/actions/layer.c \
+ openbox/actions/lock.c \
openbox/actions/lower.c \
openbox/actions/maximize.c \
openbox/actions/move.c \
openbox/actions/omnipresent.c \
openbox/actions/raise.c \
openbox/actions/raiselower.c \
+ openbox/actions/raisetemp.c \
openbox/actions/reconfigure.c \
openbox/actions/resize.c \
openbox/actions/resizerelative.c \
openbox/actions/restart.c \
+ openbox/actions/sendkeyevent.c \
openbox/actions/shade.c \
openbox/actions/shadelowerraise.c \
openbox/actions/showdesktop.c \
openbox/debug.h \
openbox/dock.c \
openbox/dock.h \
+ openbox/edges.c \
+ openbox/edges.h \
openbox/event.c \
openbox/event.h \
openbox/focus.c \
}
+void RrFontDescriptionFromString(RrFont *font, gchar *description)
+{
+ PangoFontDescription *desc;
+ desc = pango_font_description_from_string(description);
+ pango_font_description_merge(font->font_desc, desc, TRUE);
+ pango_font_description_free(desc);
+ pango_layout_set_font_description(font->layout, font->font_desc);
+}
+
RrFont *RrFontOpen(const RrInstance *inst, const gchar *name, gint size,
RrFontWeight weight, RrFontSlant slant)
{
gboolean flow, gint maxwidth);
gint RrFontHeight (const RrFont *f, gint shadow_offset_y);
gint RrFontMaxCharWidth (const RrFont *f);
+/*! Select a font from a pango description string */
+void RrFontDescriptionFromString(RrFont *font, gchar *description);
/* Paint into the appearance. The old pixmap is returned (if there was one). It
is the responsibility of the caller to call XFreePixmap on the return when
look = RrAppearanceNew(inst, 0);
look->surface.grad = RR_SURFACE_MIRROR_HORIZONTAL;
- look->surface.secondary = RrColorParse(inst, "Yellow");
look->surface.split_secondary = RrColorParse(inst, "Red");
look->surface.split_primary = RrColorParse(inst, "Green");
- look->surface.primary = RrColorParse(inst, "Blue");
+ look->surface.secondary = RrColorParse(inst, "Dark Orange");
+ look->surface.primary = RrColorParse(inst, "Dark Blue");
look->surface.interlaced = FALSE;
if (ob_display == NULL) {
fprintf(stderr, "couldn't connect to X server :0\n");
case Expose:
break;
case ConfigureNotify:
+ look->surface.grad += 1;
+ if (look->surface.grad > RR_SURFACE_MIRROR_HORIZONTAL)
+ look->surface.grad = RR_SURFACE_SPLIT_VERTICAL;
RrPaint(look, win,
report.xconfigure.width,
report.xconfigure.height);
CREATE_(OB_CONFIG_FILE);
CREATE_(OB_WM_ACTION_UNDECORATE);
CREATE_(OB_WM_STATE_UNDECORATED);
+ CREATE_(OB_WM_STATE_LOCKED);
CREATE_(OB_LAST_DESKTOP);
CREATE_(OB_CONTROL);
CREATE_(OB_VERSION);
CREATE_(OB_APP_GROUP_NAME);
CREATE_(OB_APP_GROUP_CLASS);
CREATE_(OB_APP_TYPE);
+ CREATE_(OB_TARGET_WINDOW);
}
Atom obt_prop_atom(ObtPropAtom a)
OBT_PROP_OB_FOCUS,
OBT_PROP_OB_WM_ACTION_UNDECORATE,
OBT_PROP_OB_WM_STATE_UNDECORATED,
+ OBT_PROP_OB_WM_STATE_LOCKED,
OBT_PROP_OPENBOX_PID, /* this is depreecated in favour of ob_control */
OBT_PROP_OB_THEME,
OBT_PROP_OB_CONFIG_FILE,
OBT_PROP_OB_APP_GROUP_NAME,
OBT_PROP_OB_APP_GROUP_CLASS,
OBT_PROP_OB_APP_TYPE,
+ OBT_PROP_OB_TARGET_WINDOW,
OBT_PROP_NUM_ATOMS
} ObtPropAtom;
event_end_ignore_all_enters(ignore_start);
}
}
+
+gboolean actions_client_locked(ObActionsData *data)
+{
+ ObClient *c = data->client;
+
+ return !c || (c && c->locked);
+}
/*! Function for actions to call when they are moving a client around */
void actions_client_move(ObActionsData *data, gboolean start);
+/*! May we do something to this client? */
+gboolean actions_client_locked(ObActionsData *data);
action_move_startup();
action_focus_startup();
action_raise_startup();
+ action_raisetemp_startup();
action_lower_startup();
action_raiselower_startup();
action_unfocus_startup();
+ action_focusfallback_startup();
action_iconify_startup();
action_fullscreen_startup();
action_maximize_startup();
action_growtoedge_startup();
action_if_startup();
action_focustobottom_startup();
+ action_sendkeyevent_startup();
+ action_lock_startup();
/* 3.4-compatibility */
action_shadelowerraise_startup();
}
void action_move_startup(void);
void action_focus_startup(void);
void action_raise_startup(void);
+void action_raisetemp_startup(void);
void action_lower_startup(void);
void action_raiselower_startup(void);
void action_unfocus_startup(void);
+void action_focusfallback_startup(void);
void action_iconify_startup(void);
void action_fullscreen_startup(void);
void action_maximize_startup(void);
void action_growtoedge_startup(void);
void action_if_startup(void);
void action_focustobottom_startup(void);
+void action_sendkeyevent_startup(void);
+void action_lock_startup(void);
/* 3.4-compatibility */
void action_shadelowerraise_startup(void);
/* Always return FALSE because its not interactive */
static gboolean run_func(ObActionsData *data, gpointer options)
{
- if (data->client) client_close(data->client);
+ if (!actions_client_locked(data))
+ client_close(data->client);
return FALSE;
}
/* Always return FALSE because its not interactive */
static gboolean run_func_on(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_set_undecorated(data->client, FALSE);
actions_client_move(data, FALSE);
/* Always return FALSE because its not interactive */
static gboolean run_func_off(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_set_undecorated(data->client, TRUE);
actions_client_move(data, FALSE);
/* Always return FALSE because its not interactive */
static gboolean run_func_toggle(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_set_undecorated(data->client, !data->client->undecorated);
actions_client_move(data, FALSE);
Options *o = options;
guint d;
+
+
switch (o->type) {
case LAST:
d = screen_last_desktop;
(data->context != OB_FRAME_CONTEXT_CLIENT &&
data->context != OB_FRAME_CONTEXT_FRAME))
{
- if (o->stop_int)
- actions_interactive_cancel_act();
+ if (!(data->client->iconic && actions_client_locked(data))) {
+ if (o->stop_int)
+ actions_interactive_cancel_act();
- actions_client_move(data, TRUE);
- client_activate(data->client, TRUE, o->here, FALSE, FALSE, TRUE);
- actions_client_move(data, FALSE);
+ actions_client_move(data, TRUE);
+ client_activate(data->client, TRUE, o->here, FALSE, FALSE, TRUE);
+ actions_client_move(data, FALSE);
+ }
}
} else if (data->context == OB_FRAME_CONTEXT_DESKTOP) {
if (o->stop_int)
--- /dev/null
+#include "openbox/actions.h"
+#include "openbox/focus.h"
+
+static gboolean run_func(ObActionsData *data, gpointer options);
+
+void action_focusfallback_startup(void)
+{
+ actions_register("FocusFallback", NULL, NULL, run_func);
+}
+
+/* Always return FALSE because its not interactive */
+static gboolean run_func(ObActionsData *data, gpointer options)
+{
+ if (data->client && data->client == focus_client)
+ focus_fallback(FALSE, FALSE, TRUE, FALSE);
+ return FALSE;
+}
{
Options *o = options;
- if (!data->client)
+ if (!data->client ||
+ actions_client_locked(data))
return FALSE;
gboolean doing_vertical_resize =
#include "openbox/client.h"
static gboolean run_func(ObActionsData *data, gpointer options);
+static gpointer setup_func(xmlNodePtr node);
void action_iconify_startup(void)
{
actions_register("Iconify",
- NULL, NULL,
+ setup_func,
+ NULL,
run_func);
}
+static gpointer setup_func(xmlNodePtr node)
+{
+ xmlNodePtr n;
+
+ if ((n = obt_xml_find_node(node, "de")))
+ return GINT_TO_POINTER(obt_xml_node_bool(n));
+
+ return GINT_TO_POINTER(0);
+}
+
/* Always return FALSE because its not interactive */
static gboolean run_func(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
- client_iconify(data->client, TRUE, TRUE, FALSE);
+ client_iconify(data->client, !options, FALSE, FALSE);
actions_client_move(data, FALSE);
}
gboolean maxfull_off;
gboolean iconic_on;
gboolean iconic_off;
+ gboolean locked_on;
+ gboolean locked_off;
gboolean focused;
gboolean unfocused;
gboolean urgent_on;
set_bool(node, "maximizedhorizontal", &q->maxhorz_on, &q->maxhorz_off);
set_bool(node, "maximizedvertical", &q->maxvert_on, &q->maxvert_off);
set_bool(node, "iconified", &q->iconic_on, &q->iconic_off);
+ set_bool(node, "locked", &q->locked_on, &q->locked_off);
set_bool(node, "focused", &q->focused, &q->unfocused);
set_bool(node, "urgent", &q->urgent_on, &q->urgent_off);
set_bool(node, "undecorated", &q->decor_off, &q->decor_on);
if (q->iconic_off)
is_true &= !query_target->iconic;
+ if (q->locked_on)
+ is_true &= query_target->locked;
+ if (q->locked_off)
+ is_true &= !query_target->locked;
+
if (q->maxhorz_on)
is_true &= query_target->max_horz;
if (q->maxhorz_off)
/* Always return FALSE because its not interactive */
static gboolean run_func(ObActionsData *data, gpointer options)
{
- if (data->client)
+ if (!actions_client_locked(data))
client_kill(data->client);
return FALSE;
--- /dev/null
+#include "openbox/actions.h"
+#include "openbox/client.h"
+
+static gboolean run_func(ObActionsData *data, gpointer options);
+
+void action_lock_startup(void)
+{
+ actions_register("Lock", NULL, NULL, run_func);
+}
+
+/* Always return FALSE because its not interactive */
+static gboolean run_func(ObActionsData *data, gpointer options)
+{
+ if (data->client)
+ client_set_locked(data->client, !data->client->locked);
+
+ return FALSE;
+}
static gboolean run_func_on(ObActionsData *data, gpointer options)
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_maximize(data->client, TRUE, o->dir);
actions_client_move(data, FALSE);
static gboolean run_func_off(ObActionsData *data, gpointer options)
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_maximize(data->client, FALSE, o->dir);
actions_client_move(data, FALSE);
static gboolean run_func_toggle(ObActionsData *data, gpointer options)
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
gboolean toggle;
actions_client_move(data, TRUE);
toggle = ((o->dir == HORZ && !data->client->max_horz) ||
#include "openbox/actions.h"
+#include "openbox/client.h"
#include "openbox/moveresize.h"
#include "obt/prop.h"
/* Always return FALSE because its not interactive */
static gboolean run_func(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (data->client && !data->client->locked) {
guint32 corner;
corner = data->button != 0 ?
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
ObClient *c;
gint x, y, lw, lh, w, h;
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
Rect *area, *carea;
ObClient *c;
guint mon, cmon;
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
gint x, y;
client_find_move_directional(data->client, o->dir, &x, &y);
--- /dev/null
+#include "openbox/actions.h"
+#include "openbox/stacking.h"
+#include "openbox/window.h"
+#include "openbox/focus_cycle.h"
+
+static gboolean run_func(ObActionsData *data, gpointer options);
+
+void action_raisetemp_startup(void)
+{
+ actions_register("RaiseTemp",
+ NULL, NULL,
+ run_func);
+}
+
+/* Always return FALSE because its not interactive */
+static gboolean run_func(ObActionsData *data, gpointer options)
+{
+ if (focus_cycle_target) {
+ actions_client_move(data, TRUE);
+ stacking_temp_raise(CLIENT_AS_WINDOW(data->client));
+ actions_client_move(data, FALSE);
+ }
+
+ return FALSE;
+}
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
ObClient *c = data->client;
guint32 corner;
{
Options *o = options;
- if (data->client) {
+ if (!actions_client_locked(data)) {
ObClient *c = data->client;
gint x, y, ow, xoff, nw, oh, yoff, nh, lw, lh;
gint left = o->left, right = o->right, top = o->top, bottom = o->bottom;
--- /dev/null
+#include "openbox/actions.h"
+#include "openbox/client.h"
+#include "openbox/window.h"
+#include "openbox/translate.h"
+#include "obt/display.h"
+#include "obt/prop.h"
+#include "openbox/openbox.h"
+#include "gettext.h"
+
+typedef struct {
+ guint key;
+ guint state;
+ gboolean target;
+} Options;
+
+static gpointer setup_sendkey_func(xmlNodePtr node);
+static gboolean sendkey(ObActionsData *data, gpointer options);
+static gboolean settarget(ObActionsData *data, gpointer options);
+
+static Window target;
+
+void action_sendkeyevent_startup(void)
+{
+ actions_register("SendKeyEvent",
+ setup_sendkey_func, g_free,
+ sendkey);
+ actions_register("SetKeyTarget",
+ NULL, NULL,
+ settarget);
+ OBT_PROP_GET32(obt_root(ob_screen), OB_TARGET_WINDOW, WINDOW, (guint32 *)&target);
+}
+
+static gpointer setup_sendkey_func(xmlNodePtr node)
+{
+ xmlNodePtr n;
+ Options *o;
+
+ o = g_new0(Options, 1);
+ o->target = TRUE;
+
+ if ((n = obt_xml_find_node(node, "key"))) {
+ gchar *s = obt_xml_node_string(n);
+ translate_key(s, &o->state, &o->key);
+ g_free(s);
+ } else
+ translate_key("space", &o->state, &o->key);
+ if ((n = obt_xml_find_node(node, "usetarget")))
+ o->target = obt_xml_node_bool(n);
+
+ return o;
+}
+
+/* Always return FALSE because its not interactive */
+static gboolean sendkey(ObActionsData *data, gpointer options)
+{
+ Options *o = options;
+ XEvent ev;
+ Window win;
+
+ if (!o->key) /* the key couldn't be parsed */
+ return FALSE;
+
+ if (o->target)
+ win = target;
+ else if (data->client)
+ win = data->client->window;
+ else
+ return FALSE;
+
+ ev.xkey.window = win;
+ ev.xkey.state = o->state;
+ ev.xkey.keycode = o->key;
+ obt_display_ignore_errors(TRUE);
+ ev.type = KeyPress;
+ XSendEvent(obt_display, win, False, 0, &ev);
+ ev.type = KeyRelease;
+ XSendEvent(obt_display, win, False, 0, &ev);
+ obt_display_ignore_errors(FALSE);
+
+ return FALSE;
+}
+
+/* Always return FALSE because its not interactive */
+static gboolean settarget(ObActionsData *data, gpointer options)
+{
+ if (data->client) {
+ target = data->client->window;
+ OBT_PROP_SET32(obt_root(ob_screen), OB_TARGET_WINDOW, WINDOW, target);
+ }
+
+ return FALSE;
+}
/* Always return FALSE because its not interactive */
static gboolean run_func_on(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_shade(data->client, TRUE);
actions_client_move(data, FALSE);
/* Always return FALSE because its not interactive */
static gboolean run_func_off(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_shade(data->client, FALSE);
actions_client_move(data, FALSE);
/* Always return FALSE because its not interactive */
static gboolean run_func_toggle(ObActionsData *data, gpointer options)
{
- if (data->client) {
+ if (!actions_client_locked(data)) {
actions_client_move(data, TRUE);
client_shade(data->client, !data->client->shaded);
actions_client_move(data, FALSE);
/* Always return FALSE because its not interactive */
static gboolean run_func(ObActionsData *data, gpointer options)
{
- if (data->client && data->client == focus_client)
- focus_fallback(FALSE, FALSE, TRUE, FALSE);
+ actions_interactive_cancel_act();
+ focus_nothing();
return FALSE;
}
self->demands_attention = TRUE;
else if (state[i] == OBT_PROP_ATOM(OB_WM_STATE_UNDECORATED))
self->undecorated = TRUE;
+ else if (state[i] == OBT_PROP_ATOM(OB_WM_STATE_LOCKED))
+ self->locked = TRUE;
}
g_free(state);
gchar *data = NULL;
gchar *visible = NULL;
- g_free(self->title);
g_free(self->original_title);
/* try netwm */
g_free(data);
}
- OBT_PROP_SETS(self->window, NET_WM_VISIBLE_NAME, visible);
- self->title = visible;
+ if (!self->title || strcmp(self->title, visible)) {
+ OBT_PROP_SETS(self->window, NET_WM_VISIBLE_NAME, visible);
+ g_free(self->title);
+ self->title = visible;
+ } else
+ g_free(visible);
if (self->frame)
frame_adjust_title(self->frame);
/* update the icon title */
data = NULL;
- g_free(self->icon_title);
/* try netwm */
if (!OBT_PROP_GETS_UTF8(self->window, NET_WM_ICON_NAME, &data))
g_free(data);
}
- OBT_PROP_SETS(self->window, NET_WM_VISIBLE_ICON_NAME, visible);
- self->icon_title = visible;
+ if (!self->icon_title || strcmp(self->icon_title, visible)) {
+ OBT_PROP_SETS(self->window, NET_WM_VISIBLE_ICON_NAME, visible);
+ g_free(self->icon_title);
+ self->icon_title = visible;
+ } else
+ g_free(visible);
}
void client_update_strut(ObClient *self)
static void client_change_state(ObClient *self)
{
- gulong netstate[12];
+ gulong netstate[13];
guint num;
num = 0;
netstate[num++] = OBT_PROP_ATOM(NET_WM_STATE_DEMANDS_ATTENTION);
if (self->undecorated)
netstate[num++] = OBT_PROP_ATOM(OB_WM_STATE_UNDECORATED);
+ if (self->locked)
+ netstate[num++] = OBT_PROP_ATOM(OB_WM_STATE_LOCKED);
OBT_PROP_SETA32(self->window, NET_WM_STATE, ATOM, netstate, num);
if (self->frame)
gboolean shaded = self->shaded;
gboolean fullscreen = self->fullscreen;
gboolean undecorated = self->undecorated;
+ gboolean locked = self->locked;
gboolean max_horz = self->max_horz;
gboolean max_vert = self->max_vert;
gboolean modal = self->modal;
value = self->demands_attention;
else if (state == OBT_PROP_ATOM(OB_WM_STATE_UNDECORATED))
value = undecorated;
+ else if (state == OBT_PROP_ATOM(OB_WM_STATE_LOCKED))
+ value = locked;
else
g_assert_not_reached();
action = value ? OBT_PROP_ATOM(NET_WM_STATE_REMOVE) :
demands_attention = value;
} else if (state == OBT_PROP_ATOM(OB_WM_STATE_UNDECORATED)) {
undecorated = value;
+ } else if (state == OBT_PROP_ATOM(OB_WM_STATE_LOCKED)) {
+ locked = value;
}
}
client_shade(self, shaded);
if (undecorated != self->undecorated)
client_set_undecorated(self, undecorated);
+ if (locked != self->locked)
+ client_set_locked(self, locked);
if (above != self->above || below != self->below) {
self->above = above;
self->below = below;
client_change_state(self); /* reflect this in the state hints */
}
+void client_set_locked(ObClient *self, gboolean locked)
+{
+ if (self->locked != locked) {
+ self->locked = locked;
+ client_change_state(self);
+ }
+}
+
void client_set_undecorated(ObClient *self, gboolean undecorated)
{
if (self->undecorated != undecorated &&
*/
guint functions;
+ /*! Prevent window from being accidentally acted upon */
+ gboolean locked;
+
/* The window's icon, in a variety of shapes and sizes */
RrImage *icon_set;
*/
void client_shade(ObClient *self, gboolean shade);
+/*! Set a client window to be locked or not */
+void client_set_locked(ObClient *self, gboolean locked);
+
/*! Set a client window to have decorations or not */
void client_set_undecorated(ObClient *self, gboolean undecorated);
ObMenu *menu = frame->menu;
ObMenuEntry *e;
GList *it;
- guint desktop;
+ guint desktop, desktop_it;
menu_clear_entries(menu);
- for (desktop = 0; desktop < screen_num_desktops; desktop++) {
+ for (desktop_it = 0; desktop_it < screen_num_desktops; desktop_it++) {
gboolean empty = TRUE;
gboolean onlyiconic = TRUE;
gboolean noicons = TRUE;
+
+ desktop = desktop_it;
+ if (desktop == 0)
+ desktop = screen_desktop;
+ else if (desktop <= screen_desktop)
+ desktop -= 1;
menu_add_separator(menu, SEPARATOR, screen_desktop_names[desktop]);
for (it = focus_order; it; it = g_list_next(it)) {
}
else {
ObClient *t = self->data.normal.data;
- if (t) { /* it's set to NULL if its destroyed */
+ if (t && !t->locked) { /* it's set to NULL if its destroyed */
gboolean here = state & ShiftMask;
client_activate(t, TRUE, here, TRUE, TRUE, TRUE);
menu_set_update_func(combined_menu, self_update);
menu_set_cleanup_func(combined_menu, self_cleanup);
menu_set_execute_func(combined_menu, menu_execute);
+ combined_menu->warp = TRUE;
}
void client_list_combined_menu_shutdown(gboolean reconfig)
ObClient *c, guint state, gpointer data)
{
ObClient *t = self->data.normal.data;
- if (t) { /* it's set to NULL if its destroyed */
+ if (t && !t->locked) { /* it's set to NULL if its destroyed */
gboolean here = state & ShiftMask;
client_activate(t, TRUE, here, TRUE, TRUE, TRUE);
ObClient *c = frame->client;
if (e->type == OB_MENU_ENTRY_TYPE_NORMAL) {
+ if (c->locked) {
+ *en = FALSE;
+ continue;
+ }
switch (e->id) {
case CLIENT_ICONIFY:
*en = c->functions & OB_CLIENT_FUNC_ICONIFY;
GSList *config_desktops_names;
guint config_screen_firstdesk;
guint config_desktop_popup_time;
+gint config_emulate_xinerama;
gboolean config_resize_redraw;
gint config_resize_popup_show;
gchar *keystring, **keys, **key;
xmlNodePtr n;
gboolean is_chroot = FALSE;
+ gboolean grab = TRUE;
if (!obt_xml_attr_string(node, "key", &keystring))
return;
obt_xml_attr_bool(node, "chroot", &is_chroot);
+ obt_xml_attr_bool(node, "grab", &grab);
keys = g_strsplit(keystring, " ", 0);
for (key = keys; *key; ++key) {
action = actions_parse(n);
if (action)
- keyboard_bind(keylist, action);
+ keyboard_bind(keylist, action, grab);
n = obt_xml_find_node(n->next, "action");
}
}
while (nact) {
ObActionsAct *action;
- if ((action = actions_parse(nact)))
- mouse_bind(buttonstr, cx, mact, action);
+ if ((action = actions_parse(nact))) {
+ gchar *p = buttonstr;
+ while (*p) {
+ gchar *s = strchr(p, ' ');
+ if (s) {
+ *s = '\0';
+ } else {
+ s = p;
+ while (*++s);
+ s--;
+ }
+ mouse_bind(p, cx, mact, action);
+ actions_act_ref(action); /* ref the action for each binding */
+ p = s+1;
+ }
+ actions_act_unref(action); /* remove the extra ref */
+ }
nact = obt_xml_find_node(nact->next, "action");
}
g_free(buttonstr);
if ((n = obt_xml_find_node(node, "policy"))) {
if (obt_xml_node_contains(n, "UnderMouse"))
config_place_policy = OB_PLACE_POLICY_MOUSE;
+ if (obt_xml_node_contains(n, "Random"))
+ config_place_policy = OB_PLACE_POLICY_RANDOM;
}
if ((n = obt_xml_find_node(node, "center"))) {
config_place_center = obt_xml_node_bool(n);
*font = RrFontOpen(ob_rr_inst, name, size, weight, slant);
g_free(name);
+
+ if ((fnode = obt_xml_find_node(n->children, "description"))) {
+ gchar *s = obt_xml_node_string(fnode);
+ RrFontDescriptionFromString(*font, s);
+ g_free(s);
+ }
+
next_font:
n = obt_xml_find_node(n->next, "font");
}
if (d > 0)
config_screen_firstdesk = (unsigned) d;
}
+ if ((n = obt_xml_find_node(node, "emulatexinerama")))
+ config_emulate_xinerama = obt_xml_node_bool(n);
if ((n = obt_xml_find_node(node, "names"))) {
GSList *it;
xmlNodePtr nname;
};
for (it = binds; it->key; ++it) {
GList *l = g_list_append(NULL, g_strdup(it->key));
- keyboard_bind(l, actions_parse_string(it->actname));
+ keyboard_bind(l, actions_parse_string(it->actname), TRUE);
}
}
config_desktops_num = 4;
config_screen_firstdesk = 1;
+ config_emulate_xinerama = FALSE;
config_desktops_names = NULL;
config_desktop_popup_time = 875;
extern guint config_desktops_num;
/*! Desktop to start on, put 5 to start in the center of a 3x3 grid */
extern guint config_screen_firstdesk;
+/*! Emulate xinerama by dividing screen in two halves, left and right. */
+extern gboolean config_emulate_xinerama;
/*! Names for the desktops */
extern GSList *config_desktops_names;
/*! Amount of time to show the desktop switch dialog */
--- /dev/null
+#include "openbox.h"
+#include "config.h"
+#include "screen.h"
+#include "edges.h"
+#include "frame.h"
+
+#include <X11/Xlib.h>
+#include <glib.h>
+
+/* Array of array of monitors of edges: edge[monitor 2][top edge] */
+ObEdge ***edge = NULL;
+#warning put in config.c and parse configs of course
+gboolean config_edge_enabled[OB_NUM_EDGES] = {1, 1, 1, 1, 1, 1, 1, 1};
+/* this could change at runtime, we should hook into that, but for now
+ * don't crash on reconfigure/shutdown */
+static guint edge_monitors;
+
+#ifdef DEBUG
+#define EDGE_WIDTH 10
+#define CORNER_SIZE 20
+#else
+#define EDGE_WIDTH 1
+#define CORNER_SIZE 2
+#endif
+static void get_position(ObEdgeLocation edge, Rect screen, Rect *rect)
+{
+ switch (edge) {
+ case OB_EDGE_TOP:
+ RECT_SET(*rect, CORNER_SIZE, 0,
+ screen.width - 2 * CORNER_SIZE, EDGE_WIDTH);
+ break;
+ case OB_EDGE_TOPRIGHT:
+ RECT_SET(*rect, screen.width - CORNER_SIZE, 0,
+ CORNER_SIZE, CORNER_SIZE);
+ break;
+ case OB_EDGE_RIGHT:
+ RECT_SET(*rect, screen.width - EDGE_WIDTH, CORNER_SIZE,
+ EDGE_WIDTH, screen.height - 2 * CORNER_SIZE);
+ break;
+ case OB_EDGE_BOTTOMRIGHT:
+ RECT_SET(*rect, screen.width - CORNER_SIZE,
+ screen.height - CORNER_SIZE,
+ CORNER_SIZE, CORNER_SIZE);
+ break;
+ case OB_EDGE_BOTTOM:
+ RECT_SET(*rect, CORNER_SIZE, screen.height - EDGE_WIDTH,
+ screen.width - 2 * CORNER_SIZE, EDGE_WIDTH);
+ break;
+ case OB_EDGE_BOTTOMLEFT:
+ RECT_SET(*rect, 0, screen.height - CORNER_SIZE,
+ CORNER_SIZE, CORNER_SIZE);
+ break;
+ case OB_EDGE_LEFT:
+ RECT_SET(*rect, 0, CORNER_SIZE,
+ EDGE_WIDTH, screen.height - 2 * CORNER_SIZE);
+ break;
+ case OB_EDGE_TOPLEFT:
+ RECT_SET(*rect, 0, 0, CORNER_SIZE, CORNER_SIZE);
+ break;
+ }
+ rect->x += screen.x;
+ rect->y += screen.y;
+}
+
+void edges_startup(gboolean reconfigure)
+{
+ ObEdgeLocation i;
+ gint m;
+ Rect r;
+ XSetWindowAttributes xswa;
+
+ xswa.override_redirect = True;
+
+ edge_monitors = screen_num_monitors;
+
+ edge = g_slice_alloc(sizeof(ObEdge**) * edge_monitors);
+ for (m = 0; m < edge_monitors; m++) {
+ const Rect *monitor = screen_physical_area_monitor(m);
+ edge[m] = g_slice_alloc(sizeof(ObEdge*) * OB_NUM_EDGES);
+ for (i=0; i < OB_NUM_EDGES; i++) {
+ if (!config_edge_enabled[i])
+ continue;
+
+ edge[m][i] = g_slice_new(ObEdge);
+ edge[m][i]->obwin.type = OB_WINDOW_CLASS_EDGE;
+ edge[m][i]->location = i;
+
+ get_position(i, *monitor, &r);
+ edge[m][i]->win = XCreateWindow(obt_display, obt_root(ob_screen),
+ r.x, r.y, r.width, r.height, 0, 0, InputOnly,
+ CopyFromParent, CWOverrideRedirect, &xswa);
+ XSelectInput(obt_display, edge[m][i]->win, ButtonPressMask | ButtonReleaseMask
+ | EnterWindowMask | LeaveWindowMask);
+ XMapWindow(obt_display, edge[m][i]->win);
+
+ stacking_add(EDGE_AS_WINDOW(edge[m][i]));
+ window_add(&edge[m][i]->win, EDGE_AS_WINDOW(edge[m][i]));
+
+#ifdef DEBUG
+ ob_debug("mapped edge window %i at %03i %03i %02i %02i", i, r.x, r.y, r.width, r.height);
+#endif
+ }
+ }
+
+ XFlush(obt_display);
+}
+
+void edges_shutdown(gboolean reconfigure)
+{
+ gint i, m;
+
+ /* This is in case we get called before startup by screen_resize() */
+ if (!edge)
+ return;
+
+ for (m = 0; m < edge_monitors; m++) {
+ for (i = 0; i < OB_NUM_EDGES; i++) {
+ if (!config_edge_enabled[i])
+ continue;
+
+ window_remove(edge[m][i]->win);
+ stacking_remove(EDGE_AS_WINDOW(edge[m][i]));
+ XDestroyWindow(obt_display, edge[m][i]->win);
+ g_slice_free(ObEdge, edge[m][i]);
+ }
+ g_slice_free1(sizeof(ObEdge*) * OB_NUM_EDGES, edge[m]);
+ }
+ g_slice_free1(sizeof(ObEdge**) * edge_monitors, edge);
+}
+
+void edges_configure()
+{
+ edges_shutdown(TRUE);
+ edges_startup(TRUE);
+}
--- /dev/null
+#ifndef __edges_h
+#define __edges_h
+
+#include "window.h"
+
+typedef enum
+{
+ OB_EDGE_TOP,
+ OB_EDGE_TOPRIGHT,
+ OB_EDGE_RIGHT,
+ OB_EDGE_BOTTOMRIGHT,
+ OB_EDGE_BOTTOM,
+ OB_EDGE_BOTTOMLEFT,
+ OB_EDGE_LEFT,
+ OB_EDGE_TOPLEFT,
+ OB_NUM_EDGES
+} ObEdgeLocation;
+
+typedef struct _ObEdge ObEdge;
+
+struct _ObEdge
+{
+ ObWindow obwin;
+ Window win;
+ ObEdgeLocation location;
+};
+
+void edges_startup(gboolean reconfigure);
+void edges_shutdown(gboolean reconfigure);
+void edges_configure(void);
+
+#endif
#include "grab.h"
#include "menu.h"
#include "prompt.h"
+#include "edges.h"
#include "menuframe.h"
#include "keyboard.h"
#include "mouse.h"
static guint unfocus_delay_timeout_id = 0;
static ObClient *unfocus_delay_timeout_client = NULL;
+extern guint button;
+
#ifdef USE_SM
static gboolean ice_handler(GIOChannel *source, GIOCondition cond,
gpointer conn)
case OB_WINDOW_CLASS_MENUFRAME:
menu = WINDOW_AS_MENUFRAME(obwin);
break;
- case OB_WINDOW_CLASS_INTERNAL:
- /* we don't do anything with events directly on these windows */
- break;
case OB_WINDOW_CLASS_PROMPT:
prompt = WINDOW_AS_PROMPT(obwin);
break;
/* ...or it if it was physically on an openbox
internal window... */
((w = window_find(e->xbutton.subwindow)) &&
- (WINDOW_IS_INTERNAL(w) || WINDOW_IS_DOCK(w))))
+ (WINDOW_IS_INTERNAL(w) || WINDOW_IS_DOCK(w) || WINDOW_IS_EDGE(w))))
/* ...then process the event, otherwise ignore it */
{
used = event_handle_user_input(client, e);
if (e->type == ButtonPress)
pressed = e->xbutton.button;
+ /* We ignored the release event so make sure we don't think
+ the button is still pressed */
+ else if (e->type == ButtonRelease)
+ button = 0;
}
}
else if (e->type == KeyPress || e->type == KeyRelease ||
}
case ConfigureRequest:
{
+ if (client->locked)
+ break;
+
/* dont compress these unless you're going to watch for property
notifies in between (these can change what the configure would
do to the window).
msgtype = e->xclient.message_type;
if (msgtype == OBT_PROP_ATOM(WM_CHANGE_STATE)) {
if (!more_client_message_event(client->window, msgtype))
- client_set_wm_state(client, e->xclient.data.l[0]);
+ if (!client->locked)
+ client_set_wm_state(client, e->xclient.data.l[0]);
} else if (msgtype == OBT_PROP_ATOM(NET_WM_DESKTOP)) {
if (!more_client_message_event(client->window, msgtype) &&
((unsigned)e->xclient.data.l[0] < screen_num_desktops ||
e->xclient.data.l[1], e->xclient.data.l[2],
client->window);
- /* ignore enter events caused by these like ob actions do */
- if (!config_focus_under_mouse)
- ignore_start = event_start_ignore_all_enters();
- client_set_state(client, e->xclient.data.l[0],
- e->xclient.data.l[1], e->xclient.data.l[2]);
- if (!config_focus_under_mouse)
- event_end_ignore_all_enters(ignore_start);
+ if (!client->locked) {
+ /* ignore enter events caused by these like ob actions do */
+ if (!config_focus_under_mouse)
+ ignore_start = event_start_ignore_all_enters();
+ client_set_state(client, e->xclient.data.l[0],
+ e->xclient.data.l[1], e->xclient.data.l[2]);
+ if (!config_focus_under_mouse)
+ event_end_ignore_all_enters(ignore_start);
+ }
} else if (msgtype == OBT_PROP_ATOM(NET_CLOSE_WINDOW)) {
ob_debug("net_close_window for 0x%lx", client->window);
- client_close(client);
+ if (!client->locked)
+ client_close(client);
} else if (msgtype == OBT_PROP_ATOM(NET_ACTIVE_WINDOW)) {
ob_debug("net_active_window for 0x%lx source=%s",
client->window,
(Atom)e->xclient.data.l[2] ==
OBT_PROP_ATOM(NET_WM_MOVERESIZE_MOVE_KEYBOARD))
{
- moveresize_start(client, e->xclient.data.l[0],
- e->xclient.data.l[1], e->xclient.data.l[3],
- e->xclient.data.l[2]);
+ if (!client->locked)
+ moveresize_start(client, e->xclient.data.l[0],
+ e->xclient.data.l[1], e->xclient.data.l[3],
+ e->xclient.data.l[2]);
}
else if ((Atom)e->xclient.data.l[2] ==
OBT_PROP_ATOM(NET_WM_MOVERESIZE_CANCEL))
if (moveresize_client)
moveresize_end(TRUE);
} else if (msgtype == OBT_PROP_ATOM(NET_MOVERESIZE_WINDOW)) {
+ if (client->locked)
+ break;
+
gint ograv, x, y, w, h;
ograv = client->gravity;
#include "focus_cycle_indicator.h"
#include "moveresize.h"
#include "screen.h"
+#include "edges.h"
#include "obrender/theme.h"
#include "obt/display.h"
#include "obt/xqueue.h"
return OB_FRAME_CONTEXT_MOVE_RESIZE;
else if (!g_ascii_strcasecmp("Dock", name))
return OB_FRAME_CONTEXT_DOCK;
+ else if (!g_ascii_strcasecmp("ScreenTop", name))
+ return OB_FRAME_CONTEXT_EDGE_TOP;
+ else if (!g_ascii_strcasecmp("ScreenTopRight", name))
+ return OB_FRAME_CONTEXT_EDGE_TOPRIGHT;
+ else if (!g_ascii_strcasecmp("ScreenRight", name))
+ return OB_FRAME_CONTEXT_EDGE_RIGHT;
+ else if (!g_ascii_strcasecmp("ScreenBottomRight", name))
+ return OB_FRAME_CONTEXT_EDGE_BOTTOMRIGHT;
+ else if (!g_ascii_strcasecmp("ScreenBottom", name))
+ return OB_FRAME_CONTEXT_EDGE_BOTTOM;
+ else if (!g_ascii_strcasecmp("ScreenBottomLeft", name))
+ return OB_FRAME_CONTEXT_EDGE_BOTTOMLEFT;
+ else if (!g_ascii_strcasecmp("ScreenLeft", name))
+ return OB_FRAME_CONTEXT_EDGE_LEFT;
+ else if (!g_ascii_strcasecmp("ScreenTopLeft", name))
+ return OB_FRAME_CONTEXT_EDGE_TOPLEFT;
return OB_FRAME_CONTEXT_NONE;
}
if (moveresize_in_progress)
return OB_FRAME_CONTEXT_MOVE_RESIZE;
-
if (win == obt_root(ob_screen))
return OB_FRAME_CONTEXT_ROOT;
if ((obwin = window_find(win))) {
if (WINDOW_IS_DOCK(obwin)) {
return OB_FRAME_CONTEXT_DOCK;
+ } else if (WINDOW_IS_EDGE(obwin)) {
+ ObEdge *edge = (ObEdge *)obwin;
+ return OB_FRAME_CONTEXT_EDGE_TOP + edge->location;
}
}
if (client == NULL) return OB_FRAME_CONTEXT_NONE;
a move/resize */
OB_FRAME_CONTEXT_MOVE_RESIZE,
OB_FRAME_CONTEXT_DOCK,
+ OB_FRAME_CONTEXT_EDGE_TOP,
+ OB_FRAME_CONTEXT_EDGE_TOPRIGHT,
+ OB_FRAME_CONTEXT_EDGE_RIGHT,
+ OB_FRAME_CONTEXT_EDGE_BOTTOMRIGHT,
+ OB_FRAME_CONTEXT_EDGE_BOTTOM,
+ OB_FRAME_CONTEXT_EDGE_BOTTOMLEFT,
+ OB_FRAME_CONTEXT_EDGE_LEFT,
+ OB_FRAME_CONTEXT_EDGE_TOPLEFT,
OB_FRAME_NUM_CONTEXTS
} ObFrameContext;
if (grab) {
p = curpos ? curpos->first_child : keyboard_firstnode;
while (p) {
- if (p->key)
+ if (p->key && p->grab)
grab_key(p->key, p->state, obt_root(ob_screen),
GrabModeAsync);
p = p->next_sibling;
chroot binding. so add it to the tree then. */
if (!tree_chroot(keyboard_firstnode, keylist)) {
KeyBindingTree *tree;
- if (!(tree = tree_build(keylist)))
+ if (!(tree = tree_build(keylist, TRUE)))
return;
tree_chroot(tree, keylist);
tree_assimilate(tree);
}
}
-gboolean keyboard_bind(GList *keylist, ObActionsAct *action)
+gboolean keyboard_bind(GList *keylist, ObActionsAct *action, gboolean grab)
{
KeyBindingTree *tree, *t;
gboolean conflict;
g_assert(keylist != NULL);
g_assert(action != NULL);
- if (!(tree = tree_build(keylist)))
+ if (!(tree = tree_build(keylist, grab)))
return FALSE;
if ((t = tree_find(tree, &conflict)) != NULL) {
while (node->actions) {
/* add each action, and remove them from the original tree so
they don't get free'd on us */
- keyboard_bind(node->keylist, node->actions->data);
+ keyboard_bind(node->keylist, node->actions->data, node->grab);
node->actions = g_slist_delete_link(node->actions, node->actions);
}
void keyboard_rebind(void);
void keyboard_chroot(GList *keylist);
-gboolean keyboard_bind(GList *keylist, struct _ObActionsAct *action);
+gboolean keyboard_bind(GList *keylist, struct _ObActionsAct *action, gboolean grab);
void keyboard_unbind_all(void);
gboolean keyboard_event(struct _ObClient *client, const XEvent *e);
}
}
-KeyBindingTree *tree_build(GList *keylist)
+KeyBindingTree *tree_build(GList *keylist, gboolean grab)
{
GList *it;
KeyBindingTree *ret = NULL, *p;
ret->keylist = g_list_prepend(ret->keylist,
g_strdup(kit->data)); /* deep copy */
ret->first_child = p;
+ ret->grab = grab;
if (p != NULL) p->parent = ret;
translate_key(it->data, &ret->state, &ret->key);
}
typedef struct KeyBindingTree {
guint state;
guint key;
+ gboolean grab;
GList *keylist;
GSList *actions; /* list of Action pointers */
gboolean chroot;
} KeyBindingTree;
void tree_destroy(KeyBindingTree *tree);
-KeyBindingTree *tree_build(GList *keylist);
+KeyBindingTree *tree_build(GList *keylist, gboolean grab);
void tree_assimilate(KeyBindingTree *node);
KeyBindingTree *tree_find(KeyBindingTree *search, gboolean *conflict);
gboolean tree_chroot(KeyBindingTree *tree, GList *keylist);
ObMenuDestroyFunc destroy_func;
ObMenuPlaceFunc place_func;
+ gboolean warp;
+
/* Pipe-menu parent, we get destroyed when it is destroyed */
ObMenu *pipe_creator;
}
menu_frame_move(self, x, y);
-
XMapWindow(obt_display, self->window);
if (screen_pointer_pos(&px, &py)) {
- ObMenuEntryFrame *e = menu_entry_frame_under(px, py);
- if (e && e->frame == self)
- e->ignore_enters++;
+
+ if (self->menu->warp) {
+ x += self->area.width / 2;
+ y += 67;
+ XWarpPointer(obt_display, None, obt_root(ob_screen), 0, 0, 0, 0, x, y);
+ self->ox = px;
+ self->oy = py;
+ } else {
+ ObMenuEntryFrame *e = menu_entry_frame_under(px, py);
+ if (e && e->frame == self)
+ e->ignore_enters++;
+ }
}
+
return TRUE;
}
if (self->child)
menu_frame_hide(self->child);
+ if (!self->parent && self->menu->warp)
+ XWarpPointer(obt_display, None, obt_root(ob_screen), 0, 0, 0, 0, self->ox, self->oy);
+
if (self->parent) {
remove_submenu_hide_timeout(self);
/* The client that the visual instance of the menu is associated with for
its actions */
struct _ObClient *client;
+ gint ox, oy;
ObMenuFrame *parent;
ObMenuEntryFrame *parent_entry;
to send it to other applications */
static gboolean replay_pointer_needed;
+guint button;
+
ObFrameContext mouse_button_frame_context(ObFrameContext context,
guint button,
guint state)
gboolean mouse_event(ObClient *client, XEvent *e)
{
static Time ltime;
- static guint button = 0, state = 0, lbutton = 0;
+ static guint state = 0, lbutton = 0;
static Window lwindow = None;
static gint px, py, pwx = -1, pwy = -1, lx = -10, ly = -10;
gboolean used = FALSE;
moveresize_in_progress = TRUE;
waiting_for_sync = 0;
+ if (moving)
+ do_move(FALSE, 0);
+ else
+ do_resize();
+
#ifdef SYNC
if (config_resize_redraw && !moving && obt_display_extension_sync &&
moveresize_client->sync_request && moveresize_client->sync_counter &&
#include "openbox.h"
#include "session.h"
#include "dock.h"
+#include "edges.h"
#include "event.h"
#include "menu.h"
#include "client.h"
static Cursor load_cursor(const gchar *name, guint fontval);
static void run_startup_cmd(void);
+#if 0
+gboolean haxxor_func(gpointer data)
+{
+ int *foo = data;
+ static int dir = 1;
+ *foo += dir;
+ if (*foo >= 200 || *foo <= 0)
+ dir = -dir;
+
+ Colormap cm = RrColormap(ob_rr_inst);
+ static XColor xcb, xcg;
+ xcg.red = *foo << 8;
+ xcg.blue = (*foo / 4) << 8;
+ xcg.green = *foo / 2 << 8;
+
+ xcb.red = 0;
+ xcb.blue = (196 - *foo / 4) << 8;
+ xcb.green = 0;
+ XAllocColor(ob_display, cm, &xcg);
+ XAllocColor(ob_display, cm, &xcb);
+// XAllocNamedColor(ob_display, cm, "dark blue", &xcb, &xcb);
+ static int i;
+ for (i = 1; i <= OB_CURSOR_NORTHWEST; i++)
+ XRecolorCursor(ob_display, cursors[i], &xcb, &xcg);
+
+ return TRUE;
+}
+#endif
+
gint main(gint argc, gchar **argv)
{
gchar *program_name;
cursors[OB_CURSOR_WEST] = load_cursor("left_side", XC_left_side);
cursors[OB_CURSOR_NORTHWEST] = load_cursor("top_left_corner",
XC_top_left_corner);
+#if 0
+ int color = 0;
+ ob_main_loop_timeout_add(ob_main_loop,
+ 25000,
+ haxxor_func,
+ &color, NULL);
+#endif
if (screen_annex()) { /* it will be ours! */
mouse_startup(reconfigure);
menu_frame_startup(reconfigure);
menu_startup(reconfigure);
+ edges_startup(reconfigure);
prompt_startup(reconfigure);
/* do this after everything is started so no events will get
window_unmanage_all();
prompt_shutdown(reconfigure);
+ edges_shutdown(reconfigure);
menu_shutdown(reconfigure);
menu_frame_shutdown(reconfigure);
mouse_shutdown(reconfigure);
typedef enum
{
OB_PLACE_POLICY_SMART,
+ OB_PLACE_POLICY_RANDOM,
OB_PLACE_POLICY_MOUSE
} ObPlacePolicy;
emptyx = emptyy = 0;
}
+ if (texth > textw) textw = texth;
+ popup_set_text_align(self, RR_JUSTIFY_CENTER);
+
w = textw + emptyx + iconw;
/* cap it at maxw/minw */
if (self->maxw) w = MIN(w, self->maxw);
#include "debug.h"
#include "openbox.h"
#include "dock.h"
+#include "edges.h"
#include "grab.h"
#include "startupnotify.h"
#include "moveresize.h"
supported[i++] = OBT_PROP_ATOM(OB_FOCUS);
supported[i++] = OBT_PROP_ATOM(OB_WM_ACTION_UNDECORATE);
supported[i++] = OBT_PROP_ATOM(OB_WM_STATE_UNDECORATED);
+ supported[i++] = OBT_PROP_ATOM(OB_WM_STATE_LOCKED);
supported[i++] = OBT_PROP_ATOM(OPENBOX_PID);
supported[i++] = OBT_PROP_ATOM(OB_THEME);
supported[i++] = OBT_PROP_ATOM(OB_CONFIG_FILE);
supported[i++] = OBT_PROP_ATOM(OB_APP_GROUP_NAME);
supported[i++] = OBT_PROP_ATOM(OB_APP_GROUP_CLASS);
supported[i++] = OBT_PROP_ATOM(OB_APP_TYPE);
+ supported[i++] = OBT_PROP_ATOM(OB_TARGET_WINDOW);
g_assert(i == num_support);
OBT_PROP_SETA32(obt_root(ob_screen),
gboolean namesexist = FALSE;
desktop_popup = pager_popup_new();
+ desktop_popup->popup->a_text->texture[0].data.text.font = ob_rr_theme->menu_title_font;
desktop_popup_perm = FALSE;
pager_popup_height(desktop_popup, POPUP_HEIGHT);
/* this calls screen_update_areas(), which we need ! */
dock_configure();
+ edges_configure();
// bug: this is done in screen_update_areas() already
// for (it = client_list; it; it = g_list_next(it)) {
*xin_areas = g_new(Rect, *nxin + 1);
RECT_SET((*xin_areas)[0], 0, 0, w/2, h);
RECT_SET((*xin_areas)[1], w/2, 0, w-(w/2), h);
+ } else if (config_emulate_xinerama) {
+ *nxin = 2;
+ *xin_areas = g_new(Rect, *nxin + 1);
+ RECT_SET((*xin_areas)[0], 0, 0,
+ WidthOfScreen(ScreenOfDisplay(obt_display, ob_screen)) / 2,
+ HeightOfScreen(ScreenOfDisplay(obt_display, ob_screen)));
+ RECT_SET((*xin_areas)[1],
+ WidthOfScreen(ScreenOfDisplay(obt_display, ob_screen)) / 2,
+ 0,
+ WidthOfScreen(ScreenOfDisplay(obt_display, ob_screen)) / 2,
+ HeightOfScreen(ScreenOfDisplay(obt_display, ob_screen)));
+ RECT_SET((*xin_areas)[*nxin], 0, 0,
+ WidthOfScreen(ScreenOfDisplay(obt_display, ob_screen)),
+ HeightOfScreen(ScreenOfDisplay(obt_display, ob_screen)));
}
#ifdef XINERAMA
else if (obt_display_extension_xinerama &&
#include "frame.h"
#include "openbox.h"
#include "prompt.h"
+#include "edges.h"
#include "debug.h"
#include "grab.h"
#include "obt/prop.h"
return WINDOW_AS_INTERNAL(self)->window;
case OB_WINDOW_CLASS_PROMPT:
return WINDOW_AS_PROMPT(self)->super.window;
+ case OB_WINDOW_CLASS_EDGE:
+ return WINDOW_AS_EDGE(self)->win;
}
g_assert_not_reached();
return None;
return config_dock_layer;
case OB_WINDOW_CLASS_CLIENT:
return ((ObClient*)self)->layer;
+ case OB_WINDOW_CLASS_EDGE:
case OB_WINDOW_CLASS_MENUFRAME:
case OB_WINDOW_CLASS_INTERNAL:
return OB_STACKING_LAYER_INTERNAL;
OB_WINDOW_CLASS_DOCK,
OB_WINDOW_CLASS_CLIENT,
OB_WINDOW_CLASS_INTERNAL,
- OB_WINDOW_CLASS_PROMPT
+ OB_WINDOW_CLASS_PROMPT,
+ OB_WINDOW_CLASS_EDGE
} ObWindowClass;
/* In order to be an ObWindow, you need to make this struct the top of your
(((ObWindow*)win)->type == OB_WINDOW_CLASS_INTERNAL)
#define WINDOW_IS_PROMPT(win) \
(((ObWindow*)win)->type == OB_WINDOW_CLASS_PROMPT)
+#define WINDOW_IS_EDGE(win) \
+ (((ObWindow*)win)->type == OB_WINDOW_CLASS_EDGE)
struct _ObMenu;
struct _ObDock;
#define WINDOW_AS_CLIENT(win) ((struct _ObClient*)win)
#define WINDOW_AS_INTERNAL(win) ((struct _ObInternalWindow*)win)
#define WINDOW_AS_PROMPT(win) ((struct _ObPrompt*)win)
+#define WINDOW_AS_EDGE(win) ((struct _ObEdge*)win)
#define MENUFRAME_AS_WINDOW(menu) ((ObWindow*)menu)
#define DOCK_AS_WINDOW(dock) ((ObWindow*)dock)
#define CLIENT_AS_WINDOW(client) ((ObWindow*)client)
#define INTERNAL_AS_WINDOW(intern) ((ObWindow*)intern)
#define PROMPT_AS_WINDOW(prompt) ((ObWindow*)prompt)
+#define EDGE_AS_WINDOW(edge) ((ObWindow*)edge)
void window_startup (gboolean reconfig);
void window_shutdown(gboolean reconfig);
openbox/actions.c
openbox/actions/execute.c
openbox/actions/exit.c
+openbox/actions/sendkeyevent.c
openbox/client.c
openbox/client_list_combined_menu.c
openbox/client_list_menu.c
#include <stdio.h>
#include <assert.h>
#include <glib.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
Window findClient(Display *d, Window win)
{
XPutImage(d, p, DefaultGC(d, s), i[j], 0, 0, x, 0,
i[j]->width, i[j]->height);
x += i[j]->width;
+ char *filename;
+ asprintf(&filename, "icon%i.raw", j);
+ int fd = open(filename, O_CREAT | O_RDWR);
+ write(fd, i[j]->data, i[j]->width * i[j]->height * i[j]->depth);
XDestroyImage(i[j]);
}
XDestroyWindow(display, win);
XSync(display, False);
- break;
- sleep(2);
+ //break;
+ usleep(200000);
}
return 1;
Display *display;
Window win;
XEvent report;
- Atom _net_fs, _net_state;
XEvent msg;
int x=50,y=50,h=100,w=400;
XWMHints hint;
return 0;
}
- _net_state = XInternAtom(display, "_NET_WM_STATE", False);
- _net_fs = XInternAtom(display, "_NET_WM_STATE_FULLSCREEN", False);
-
win = XCreateWindow(display, RootWindow(display, 0),
x, y, w, h, 10, CopyFromParent, CopyFromParent,
CopyFromParent, 0, NULL);