AC_PREREQ([2.54])
- AC_INIT([openbox], [3.5.0], [http://bugzilla.icculus.org])
+ AC_INIT([openbox], [3.5.2], [http://bugzilla.icculus.org])
AC_CONFIG_SRCDIR([openbox/openbox.c])
AM_INIT_AUTOMAKE([foreign])
-AM_SILENT_RULES([yes])
OB_VERSION=$PACKAGE_VERSION
AC_SUBST(OB_VERSION)
dnl
RR_MAJOR_VERSION=3
RR_MINOR_VERSION=5
- RR_MICRO_VERSION=28
+ RR_MICRO_VERSION=30
RR_INTERFACE_AGE=1
RR_BINARY_AGE=1
RR_VERSION=$RR_MAJOR_VERSION.$RR_MINOR_VERSION
OBT_MAJOR_VERSION=3
OBT_MINOR_VERSION=5
- OBT_MICRO_VERSION=1
+ OBT_MICRO_VERSION=3
OBT_INTERFACE_AGE=1
OBT_BINARY_AGE=1
OBT_VERSION=$OBT_MAJOR_VERSION.$OBT_MINOR_VERSION
AM_CONDITIONAL(USE_IMLIB2, [test $imlib2_found = yes])
+ AC_ARG_ENABLE(librsvg,
+ AC_HELP_STRING(
+ [--disable-librsvg],
+ [disable use of SVG image files for loading icons. [default=enabled]]
+ ),
+ [enable_librsvg=$enableval],
+ [enable_librsvg=yes]
+ )
+
+ if test "$enable_librsvg" = yes; then
+ PKG_CHECK_MODULES(LIBRSVG, [librsvg-2.0],
+ [
+ AC_DEFINE(USE_LIBRSVG, [1], [Use SVG image files])
+ AC_SUBST(LIBRSVG_CFLAGS)
+ AC_SUBST(LIBRSVG_LIBS)
+ # export it for the pkg-config file
+ PKG_CONFIG_LIBRSVG=librsvg-2.0
+ AC_SUBST(PKG_CONFIG_LIBRSVG)
+ librsvg_found=yes
+ ],
+ [
+ librsvg_found=no
+ ]
+ )
+ else
+ librsvg_found=no
+ fi
+
+ AM_CONDITIONAL(USE_LIBRSVG, [test $librsvg_found = yes])
+
dnl Check for session management
X11_SM
Startup Notification... $sn_found
X Cursor Library... $xcursor_found
Session Management... $SM
- Imlib2 library... $imlib2_found
+ Imlib2 Library... $imlib2_found
+ SVG Support (librsvg)... $librsvg_found
])
AC_MSG_RESULT([configure complete, now type "make"])
<placement>
<policy>Smart</policy>
<!-- 'Smart' or 'UnderMouse' -->
+ <center>yes</center>
+ <!-- whether to place windows in the center of the free area found or
+ the top left corner -->
<monitor>Primary</monitor>
<!-- with Smart placement on a multi-monitor system, try to place new windows
on: 'Any' - any monitor, 'Mouse' - where the mouse is, 'Active' - where
-->
<keepBorder>yes</keepBorder>
<animateIconify>yes</animateIconify>
+ <flashFrameDelay>600</flashFrameDelay>
+ <flashFrameDuration>5000</flashFrameDuration>
<font place="ActiveWindow">
<name>sans</name>
<size>8</size>
<maximized>true</maximized>
# 'Horizontal', 'Vertical' or boolean (yes/no)
+
+ <opacity>255</opacity>
+ # make the window semi-transparent
+ # value between 0 and 255, inclusive; 0 invisible, 255 fully opaque
</application>
# end of the example
</xsd:annotation>
<xsd:sequence>
<xsd:element minOccurs="0" name="policy" type="ob:placementpolicy"/>
+ <xsd:element minOccurs="0" name="center" type="ob:bool"/>
<xsd:element minOccurs="0" name="monitor" type="ob:placementmonitor"/>
<xsd:element minOccurs="0" name="primaryMonitor" type="ob:primarymonitor"/>
</xsd:sequence>
<xsd:element minOccurs="0" name="titleLayout" type="xsd:string"/>
<xsd:element minOccurs="0" name="keepBorder" type="ob:bool"/>
<xsd:element minOccurs="0" name="animateIconify" type="ob:bool"/>
+ <xsd:element minOccurs="0" name="flashFrameDelay" type="ob:integer"/>
+ <xsd:element minOccurs="0" name="flashFrameDuration" type="ob:integer"/>
<xsd:element minOccurs="0" maxOccurs="unbounded" name="font" type="ob:font"/>
</xsd:sequence>
</xsd:complexType>
<xsd:element minOccurs="0" name="skip_taskbar" type="ob:bool"/>
<xsd:element minOccurs="0" name="fullscreen" type="ob:bool"/>
<xsd:element minOccurs="0" name="maximized" type="ob:maximization"/>
+ <xsd:element minOccurs="0" name="opacity" type="xsd:unsignedByte"/>
</xsd:all>
<!-- at least one of these must be present -->
<xsd:attribute name="role" type="xsd:string"/>
Time launch_time;
guint32 user_time;
gboolean obplaced;
- gulong ignore_start;
+ gulong ignore_start = FALSE;
ob_debug("Managing window: 0x%lx", window);
self->desktop = settings->desktop - 1;
}
+ if (settings->opacity != -1)
+ self->opacity = settings->opacity;
+
if (settings->layer == -1) {
self->below = TRUE;
self->above = FALSE;
self->max_horz = self->session->max_horz;
self->max_vert = self->session->max_vert;
self->undecorated = self->session->undecorated;
+
+ self->opacity = self->session->opacity;
}
static gboolean client_restore_session_stacking(ObClient *self)
}
}
- /*! Save the properties used for app matching rules, as seen by Openbox when
- the window mapped, so that users can still access them later if the app
- changes them */
- static void client_save_app_rule_values(ObClient *self)
+ const gchar *client_type_to_string(ObClient *self)
{
const gchar *type;
- OBT_PROP_SETS(self->window, OB_APP_ROLE, self->role);
- OBT_PROP_SETS(self->window, OB_APP_NAME, self->name);
- OBT_PROP_SETS(self->window, OB_APP_CLASS, self->class);
- OBT_PROP_SETS(self->window, OB_APP_GROUP_NAME, self->group_name);
- OBT_PROP_SETS(self->window, OB_APP_GROUP_CLASS, self->group_class);
- OBT_PROP_SETS(self->window, OB_APP_TITLE, self->original_title);
-
switch (self->type) {
case OB_CLIENT_TYPE_NORMAL:
type = "normal"; break;
case OB_CLIENT_TYPE_DOCK:
type = "dock"; break;
}
- OBT_PROP_SETS(self->window, OB_APP_TYPE, type);
+
+ return type;
+ }
+
+ /*! Save the properties used for app matching rules, as seen by Openbox when
+ the window mapped, so that users can still access them later if the app
+ changes them */
+ static void client_save_app_rule_values(ObClient *self)
+ {
+ OBT_PROP_SETS(self->window, OB_APP_ROLE, self->role);
+ OBT_PROP_SETS(self->window, OB_APP_NAME, self->name);
+ OBT_PROP_SETS(self->window, OB_APP_CLASS, self->class);
+ OBT_PROP_SETS(self->window, OB_APP_GROUP_NAME, self->group_name);
+ OBT_PROP_SETS(self->window, OB_APP_GROUP_CLASS, self->group_class);
+ OBT_PROP_SETS(self->window, OB_APP_TITLE, self->original_title);
+
+ OBT_PROP_SETS(self->window, OB_APP_TYPE, client_type_to_string(self));
}
static void client_change_wm_state(ObClient *self)
gboolean demands_attention = self->demands_attention;
gboolean max_horz = self->max_horz;
gboolean max_vert = self->max_vert;
+ guint8 opacity = self->opacity;
Rect oldarea;
gint l;
/* make sure client_setup_decor_and_functions() is called at least once */
client_setup_decor_and_functions(self, FALSE);
+ /* make the client semi-transparent */
+ client_set_opacity(self, opacity);
+
/* if the window hasn't been configured yet, then do so now, in fact the
x,y,w,h may _not_ be the same as the area rect, which can end up
meaning that the client isn't properly moved/resized by the fullscreen
focus_cycle_addremove(NULL, TRUE);
}
+void client_set_opacity(ObClient *self, guint8 opacity)
+{
+ OBT_PROP_SET32(self->window, NET_WM_WINDOW_OPACITY, CARDINAL,
+ opacity * 16777216);
+}
+
gboolean client_is_direct_child(ObClient *parent, ObClient *child)
{
while (child != parent && (child = client_direct_parent(child)));
gboolean max_vert;
/*! The window is maximized to fill the screen horizontally */
gboolean max_horz;
+ /*! The window is semi-transparent */
+ guint8 opacity;
/*! The window should not be displayed by pagers */
gboolean skip_pager;
/*! The window should not be displayed by taskbars */
void client_set_desktop(ObClient *self, guint target, gboolean donthide,
gboolean dontraise);
+/*! Adjust the client opacity */
+void client_set_opacity(ObClient *self, guint8 opacity);
+
/*! Show the client if it should be shown. Returns if the window is shown. */
gboolean client_show(ObClient *self);
/*! Updates the window's icon geometry (where to iconify to/from) */
void client_update_icon_geometry(ObClient *self);
+ /*! Helper function to convert the ->type member to string representation */
+ const gchar *client_type_to_string(ObClient *self);
+
/*! Set up what decor should be shown on the window and what functions should
be allowed (ObClient::decorations and ObClient::functions).
This also updates the NET_WM_ALLOWED_ACTIONS hint.
gboolean config_unfocus_leave;
ObPlacePolicy config_place_policy;
+ gboolean config_place_center;
ObPlaceMonitor config_place_monitor;
guint config_primary_monitor_index;
gchar *config_theme;
gboolean config_theme_keepborder;
guint config_theme_window_list_icon_size;
+guint config_frame_flash_delay;
+guint config_frame_flash_duration;
gchar *config_title_layout;
settings->fullscreen = -1;
settings->max_horz = -1;
settings->max_vert = -1;
+ settings->opacity = -1;
return settings;
}
copy_if(fullscreen, -1);
copy_if(max_horz, -1);
copy_if(max_vert, -1);
+ copy_if(opacity, -1);
if (src->pos_given) {
dst->pos_given = TRUE;
/* monitor is copied above */
}
- if (src->size_given) {
- dst->size_given = TRUE;
- dst->width_num = src->width_num;
- dst->width_denom = src->width_denom;
- dst->height_num = src->height_num;
- dst->height_denom = src->height_denom;
- }
+ dst->width_num = src->width_num;
+ dst->width_denom = src->width_denom;
+ dst->height_num = src->height_num;
+ dst->height_denom = src->height_denom;
}
void config_parse_relative_number(gchar *s, gint *num, gint *denom)
{
xmlNodePtr n, c;
gboolean x_pos_given = FALSE;
- gboolean width_given = FALSE;
if ((n = obt_xml_find_node(app->children, "decor")))
if (!obt_xml_node_contains(n, "default"))
config_parse_relative_number(s,
&settings->width_num,
&settings->width_denom);
- if (settings->width_num > 0 && settings->width_denom >= 0)
- width_given = TRUE;
+ if (settings->width_num <= 0 || settings->width_denom < 0)
+ settings->width_num = settings->width_denom = 0;
g_free(s);
}
}
- if (width_given && (c = obt_xml_find_node(n->children, "height"))) {
- gchar *s = obt_xml_node_string(c);
- config_parse_relative_number(s,
- &settings->height_num,
- &settings->height_denom);
- if (settings->height_num > 0 && settings->height_denom >= 0)
- settings->size_given = TRUE;
- g_free(s);
+ if ((c = obt_xml_find_node(n->children, "height"))) {
+ if (!obt_xml_node_contains(c, "default")) {
+ gchar *s = obt_xml_node_string(c);
+ config_parse_relative_number(s,
+ &settings->height_num,
+ &settings->height_denom);
+ if (settings->height_num <= 0 || settings->height_denom < 0)
+ settings->height_num = settings->height_denom = 0;
+ g_free(s);
+ }
}
}
g_free(s);
}
}
+
+ if ((n = obt_xml_find_node(app->children, "opacity")))
+ if (!obt_xml_node_contains(n, "default"))
+ settings->opacity = obt_xml_node_int(n);
}
/* Manages settings for individual applications.
node = node->children;
- if ((n = obt_xml_find_node(node, "policy")))
+ if ((n = obt_xml_find_node(node, "policy"))) {
if (obt_xml_node_contains(n, "UnderMouse"))
config_place_policy = OB_PLACE_POLICY_MOUSE;
+ }
+ if ((n = obt_xml_find_node(node, "center"))) {
+ config_place_center = obt_xml_node_bool(n);
+ }
if ((n = obt_xml_find_node(node, "monitor"))) {
if (obt_xml_node_contains(n, "active"))
config_place_monitor = OB_PLACE_MONITOR_ACTIVE;
else if (config_theme_window_list_icon_size > 96)
config_theme_window_list_icon_size = 96;
}
+ if ((n = obt_xml_find_node(node, "flashFrameDelay")))
+ config_frame_flash_delay = obt_xml_node_int(n);
+ if ((n = obt_xml_find_node(node, "flashFrameDuration")))
+ config_frame_flash_duration = obt_xml_node_int(n);
n = obt_xml_find_node(node, "font");
while (n) {
config_menu_manage_desktops = obt_xml_node_bool(n);
if ((n = obt_xml_find_node(node, "showIcons"))) {
config_menu_show_icons = obt_xml_node_bool(n);
- #ifndef USE_IMLIB2
+ #if !defined(USE_IMLIB2) && !defined(USE_LIBRSVG)
if (config_menu_show_icons)
- g_message(_("Openbox was compiled without Imlib2 image loading support. Icons in menus will not be loaded."));
+ g_message(_("Openbox was compiled without image loading support. Icons in menus will not be loaded."));
#endif
}
obt_xml_register(i, "focus", parse_focus, NULL);
config_place_policy = OB_PLACE_POLICY_SMART;
+ config_place_center = TRUE;
config_place_monitor = OB_PLACE_MONITOR_PRIMARY;
config_primary_monitor_index = 1;
config_title_layout = g_strdup("NLIMC");
config_theme_keepborder = TRUE;
config_theme_window_list_icon_size = 36;
+ config_frame_flash_delay = 600;
+ config_frame_flash_duration = 5000;
config_font_activewindow = NULL;
config_font_inactivewindow = NULL;
gint width_denom;
gint height_num;
gint height_denom;
- gboolean size_given;
guint desktop;
gint shade;
gint max_horz;
gint max_vert;
gint fullscreen;
-
gint layer;
+
+ guint8 opacity;
};
/*! Should new windows be focused */
/*! The algorithm to use for placing new windows */
extern ObPlacePolicy config_place_policy;
+ /*! Place windows in the center of the free area */
+ extern gboolean config_place_center;
/*! Place windows on the active monitor (unless they are part of an application
already on another monitor) */
extern ObPlaceMonitor config_place_monitor;
extern gboolean config_animate_iconify;
/*! Size of icons in focus switching dialogs */
extern guint config_theme_window_list_icon_size;
+/*! Amount of time between flashes (0 to disable flashing) */
+extern guint config_frame_flash_delay;
+/*! How long (ms) to flash the window's frame (0 to flash forever) */
+extern guint config_frame_flash_duration;
/*! The font for the active window's title */
extern RrFont *config_font_activewindow;
if (self->decorations & OB_FRAME_DECOR_TITLEBAR)
self->size.top += ob_rr_theme->title_height + self->bwidth;
else if (self->max_horz && self->max_vert) {
- /* A maximized and undecorated window needs a small border on the
+ /* A maximized and undecorated window needs a border on the
top of the window to let the user still undecorate/unmaximize the
window via the client menu. */
- /* XXX This size should probably be a theme option. */
- self->size.top += 1;
+ self->size.top += self->bwidth;
}
if (self->decorations & OB_FRAME_DECOR_HANDLE &&
ObFrame *self = data;
GTimeVal now;
- g_get_current_time(&now);
- if (now.tv_sec > self->flash_end.tv_sec ||
- (now.tv_sec == self->flash_end.tv_sec &&
- now.tv_usec >= self->flash_end.tv_usec))
- self->flashing = FALSE;
+ if (config_frame_flash_duration != 0) {
+ g_get_current_time(&now);
+ if (now.tv_sec > self->flash_end.tv_sec ||
+ (now.tv_sec == self->flash_end.tv_sec &&
+ now.tv_usec >= self->flash_end.tv_usec))
+ self->flashing = FALSE;
+ }
if (!self->flashing)
return FALSE; /* we are done */
void frame_flash_start(ObFrame *self)
{
+ if (config_frame_flash_delay == 0) return;
+
self->flash_on = self->focused;
if (!self->flashing)
self->flash_timer = g_timeout_add_full(G_PRIORITY_DEFAULT,
- 600, flash_timeout, self,
+ config_frame_flash_delay, flash_timeout, self,
flash_done);
- g_get_current_time(&self->flash_end);
- g_time_val_add(&self->flash_end, G_USEC_PER_SEC * 5);
+
+ if (config_frame_flash_duration != 0) {
+ g_get_current_time(&self->flash_end);
+ g_time_val_add(&self->flash_end, 1000 * config_frame_flash_duration);
+ }
self->flashing = TRUE;
}
{
if (moveresize_client == client)
moveresize_end(TRUE);
+ if (popup && client == popup->client)
+ popup->client = NULL;
}
void moveresize_startup(gboolean reconfig)
popup_position(popup, gravity, x, y);
}
+ popup->client = c;
popup_show(popup, text);
g_free(text);
}
ungrab_pointer();
popup_hide(popup);
+ popup->client = NULL;
if (!moving) {
#ifdef SYNC
a = screen_physical_area_all_monitors();
switch (edge_warp_dir) {
- case OB_DIRECTION_NORTH:
- y = a->height - 2;
- break;
- case OB_DIRECTION_EAST:
- x = a->x + 1;
- break;
- case OB_DIRECTION_SOUTH:
- y = a->y + 1;
- break;
- case OB_DIRECTION_WEST:
- x = a->width - 2;
- break;
- default:
+ case OB_DIRECTION_NORTH:
- y = a->height - 1;
++ y = a->height - 2;
+ break;
+ case OB_DIRECTION_EAST:
- x = a->x;
++ x = a->x + 1;
+ break;
+ case OB_DIRECTION_SOUTH:
- y = a->y;
++ y = a->y + 1;
+ break;
+ case OB_DIRECTION_WEST:
- x = a->width - 1;
++ x = a->width - 2;
+ break;
+ default:
g_assert_not_reached();
}