Merge branch 'backport' into wip/mikabox
authorMikael Magnusson <mikachu@gmail.com>
Sat, 4 Jul 2009 15:50:05 +0000 (17:50 +0200)
committerMikael Magnusson <mikachu@gmail.com>
Sat, 4 Jul 2009 15:50:05 +0000 (17:50 +0200)
Conflicts:
openbox/actions/desktop.c
openbox/client.c
openbox/popup.c
openbox/screen.c

1  2 
data/rc.xsd
openbox/actions/desktop.c
openbox/actions/moveresizeto.c
openbox/client.c
openbox/popup.c
openbox/screen.c
render/theme.c

diff --cc data/rc.xsd
index 9c0b1a5a68a9a6eacab30bec329b4a0996400b4a,499b81c92705251da3d92fd232e224f38d5e07f1..7bb85c82bd2865b2ec7c53ebcdd8f5b7069c156d
          <xsd:annotation>
              <xsd:documentation>defines desktop margins</xsd:documentation>
          </xsd:annotation>
-         <xsd:element minOccurs="0" name="top" type="xsd:integer"/>
-         <xsd:element minOccurs="0" name="left" type="xsd:integer"/>
-         <xsd:element minOccurs="0" name="right" type="xsd:integer"/>
-         <xsd:element minOccurs="0" name="bottom" type="xsd:integer"/>
+         <xsd:all>
+             <xsd:element minOccurs="0" name="top" type="xsd:integer"/>
+             <xsd:element minOccurs="0" name="left" type="xsd:integer"/>
+             <xsd:element minOccurs="0" name="right" type="xsd:integer"/>
+             <xsd:element minOccurs="0" name="bottom" type="xsd:integer"/>
+         </xsd:all>
      </xsd:complexType>              
 +    <xsd:element name="windowMargin" type="xsd:integer"/>
      <xsd:complexType name="theme">
-         <xsd:element minOccurs="0" name="name" type="xsd:string"/>
-         <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="font" type="ob:font"/>
+         <xsd:sequence>
+             <xsd:element minOccurs="0" name="name" type="xsd:string"/>
+             <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" maxOccurs="unbounded" name="font" type="ob:font"/>
+         </xsd:sequence>
      </xsd:complexType>
      <xsd:complexType name="font">
-         <xsd:element minOccurs="0" name="name" type="xsd:string"/>
-         <xsd:element minOccurs="0" name="size" type="xsd:integer"/>
-         <xsd:element minOccurs="0" name="weight" type="ob:fontweight"/>
-         <xsd:element minOccurs="0" name="slant" type="ob:fontslant"/>
+         <xsd:all>
+             <xsd:element minOccurs="0" name="name" type="xsd:string"/>
+             <xsd:element minOccurs="0" name="size" type="xsd:integer"/>
+             <xsd:element minOccurs="0" name="weight" type="ob:fontweight"/>
+             <xsd:element minOccurs="0" name="slant" type="ob:fontslant"/>
+         </xsd:all>
          <xsd:attribute name="place" type="ob:fontplace" use="required"/>
      </xsd:complexType>
      <xsd:complexType name="desktops">
index ee05707625a4cf4b8c2413b068e7bb4fafa54ee7,07416151cb7190b588b2272a0a4ad4ecc2060e69..bcf0e3cb1ffb77eceb2fb88a8c4fe8b258bc1d9c
@@@ -47,20 -49,18 +47,20 @@@ static gpointer setup_go_func(xmlNodePt
      o = g_new0(Options, 1);
      /* don't go anywhere if theres no options given */
      o->type = ABSOLUTE;
-     o->abs.desktop = screen_desktop;
+     o->u.abs.desktop = screen_desktop;
      /* wrap by default - it's handy! */
-     o->rel.wrap = TRUE;
+     o->u.rel.wrap = TRUE;
  
 -    if ((n = parse_find_node("to", node))) {
 -        gchar *s = parse_string(doc, n);
 +    if ((n = obt_parse_find_node(node, "to"))) {
 +        gchar *s = obt_parse_node_string(n);
          if (!g_ascii_strcasecmp(s, "last"))
              o->type = LAST;
 +        else if (!g_ascii_strcasecmp(s, "current"))
 +            o->type = CURRENT;
          else if (!g_ascii_strcasecmp(s, "next")) {
              o->type = RELATIVE;
-             o->rel.linear = TRUE;
-             o->rel.dir = OB_DIRECTION_EAST;
+             o->u.rel.linear = TRUE;
+             o->u.rel.dir = OB_DIRECTION_EAST;
          }
          else if (!g_ascii_strcasecmp(s, "previous")) {
              o->type = RELATIVE;
@@@ -94,8 -94,8 +94,8 @@@
          g_free(s);
      }
  
 -    if ((n = parse_find_node("wrap", node)))
 -        o->u.rel.wrap = parse_bool(doc, n);
 +    if ((n = obt_parse_find_node(node, "wrap")))
-         o->rel.wrap = obt_parse_node_bool(n);
++        o->u.rel.wrap = obt_parse_node_bool(n);
  
      return o;
  }
@@@ -125,11 -126,8 +125,11 @@@ static gboolean run_func(ObActionsData 
      case LAST:
          d = screen_last_desktop;
          break;
 +    case CURRENT:
 +        d = screen_desktop;
 +        break;
      case ABSOLUTE:
-         d = o->abs.desktop;
+         d = o->u.abs.desktop;
          break;
      case RELATIVE:
          d = screen_find_desktop(screen_desktop,
index 6ea70682f726bbd0d01b95341720014bf71e9d47,acad73b50a578c91acad4d297936594868eb6f98..272841562936e288c87cae10f941b96f8ce9ead0
@@@ -84,8 -91,12 +86,12 @@@ static gpointer setup_func(xmlNodePtr n
          if (g_ascii_strcasecmp(s, "current") != 0) {
              if (!g_ascii_strcasecmp(s, "all"))
                  o->monitor = ALL_MONITORS;
+             else if(!g_ascii_strcasecmp(s, "next"))
+                 o->monitor = NEXT_MONITOR;
+             else if(!g_ascii_strcasecmp(s, "prev"))
+                 o->monitor = PREV_MONITOR;
              else
 -                o->monitor = parse_int(doc, n) - 1;
 +                o->monitor = obt_parse_node_int(n) - 1;
          }
          g_free(s);
      }
index ad59c2503672d3e99dd877a37513651c3547b672,c1af196b5f08e90403cdd7c47fe0ba96a4515a18..a0d7f9cf1fcc3739c0e5f46d1814deb571345ae3
@@@ -232,9 -311,14 +232,14 @@@ void client_manage(Window window, ObPro
      /* get all the stuff off the window */
      client_get_all(self, TRUE);
  
 -    ob_debug("Window type: %d\n", self->type);
 -    ob_debug("Window group: 0x%x\n", self->group?self->group->leader:0);
 -    ob_debug("Window name: %s class: %s role: %s\n", self->name, self->class, self->role);
 +    ob_debug("Window type: %d", self->type);
 +    ob_debug("Window group: 0x%x", self->group?self->group->leader:0);
-     ob_debug("Window name: %s class: %s", self->name, self->class);
++    ob_debug("Window name: %s class: %s role: %s", self->name, self->class, self->role);
+     /* per-app settings override stuff from client_get_all, and return the
+        settings for other uses too. the returned settings is a shallow copy,
+        that needs to be freed with g_free(). */
+     settings = client_get_settings_state(self);
  
      /* now we have all of the window's information so we can set this up.
         do this before creating the frame, so it can tell that we are still
@@@ -3539,16 -3591,32 +3540,32 @@@ ObClient *client_search_modal_child(ObC
      return NULL;
  }
  
 -    if (XCheckTypedWindowEvent(ob_display, self->window, UnmapNotify, &e)) {
+ static gboolean client_validate_unmap(ObClient *self, int n)
+ {
+     XEvent e;
+     gboolean ret = TRUE;
 -        XPutBackEvent(ob_display, &e);
++    if (XCheckTypedWindowEvent(obt_display, self->window, UnmapNotify, &e)) {
+         if (n < self->ignore_unmaps) // ignore this one, but look for more
+             ret = client_validate_unmap(self, n+1);
+         else
+             ret = FALSE; // the window is going to become unmanaged
+         /* put them back on the event stack so they end up in the same order */
++        XPutBackEvent(obt_display, &e);
+     }
+     return ret;
+ }
  gboolean client_validate(ObClient *self)
  {
      XEvent e;
  
 -    XSync(ob_display, FALSE); /* get all events on the server */
 +    XSync(obt_display, FALSE); /* get all events on the server */
  
-     if (XCheckTypedWindowEvent(obt_display, self->window, DestroyNotify, &e) ||
-         XCheckTypedWindowEvent(obt_display, self->window, UnmapNotify, &e))
-     {
 -    if (XCheckTypedWindowEvent(ob_display, self->window, DestroyNotify, &e)) {
 -        XPutBackEvent(ob_display, &e);
++    if (XCheckTypedWindowEvent(obt_display, self->window, DestroyNotify, &e)) {
 +        XPutBackEvent(obt_display, &e);
          return FALSE;
      }
  
diff --cc openbox/popup.c
index 6ceb972bcf7c772a325e093a639e937d808b3527,2a0d5960d67d11b6f6dc35091ae0078946ad9bb5..4a5a8e0725cd85f024fb0112406e409a3b565c6a
@@@ -322,7 -320,7 +322,7 @@@ void popup_hide(ObPopup *self
  
          event_end_ignore_all_enters(ignore_start);
      } else if (self->delay_mapped) {
-         obt_main_loop_timeout_remove(ob_main_loop, popup_show_timeout);
 -        ob_main_loop_timeout_remove_data(ob_main_loop, popup_show_timeout, self, FALSE);
++        obt_main_loop_timeout_remove_data(ob_main_loop, popup_show_timeout, self, FALSE);
          self->delay_mapped = FALSE;
      }
  }
index 9c93cabb6b80ea790455accf58ea0af4c4f5f1cd,4913b606616c181b7f535338aecba2235859556c..3f035ac2355076d5824f7c69541c1e7177aa5a76
@@@ -928,28 -950,36 +945,36 @@@ void screen_show_desktop_popup(guint d
      /* 0 means don't show the popup */
      if (!config_desktop_popup_time) return;
  
-     a = screen_physical_area_active();
-     pager_popup_position(desktop_popup, CenterGravity,
-                          a->x + a->width / 2, a->y + a->height / 2);
-     pager_popup_icon_size_multiplier(desktop_popup,
-                                      (screen_desktop_layout.columns /
-                                       screen_desktop_layout.rows) / 2,
-                                      (screen_desktop_layout.rows/
-                                       screen_desktop_layout.columns) / 2);
-     pager_popup_max_width(desktop_popup,
-                           MAX(a->width/3, POPUP_WIDTH));
-     pager_popup_show(desktop_popup, screen_desktop_names[d], d);
-     obt_main_loop_timeout_remove(ob_main_loop, hide_desktop_popup_func);
-     obt_main_loop_timeout_add(ob_main_loop, config_desktop_popup_time * 1000,
-                               hide_desktop_popup_func, NULL, NULL, NULL);
-     g_free(a);
+     for (i = 0; i < screen_num_monitors; i++) {
+         a = screen_physical_area_monitor(i);
+         pager_popup_position(desktop_popup[i], CenterGravity,
+                              a->x + a->width / 2, a->y + a->height / 2);
+         pager_popup_icon_size_multiplier(desktop_popup[i],
+                                          (screen_desktop_layout.columns /
+                                           screen_desktop_layout.rows) / 2,
+                                          (screen_desktop_layout.rows/
+                                           screen_desktop_layout.columns) / 2);
+         pager_popup_max_width(desktop_popup[i],
+                               MAX(a->width/3, POPUP_WIDTH));
+         pager_popup_show(desktop_popup[i], screen_desktop_names[d], d);
 -        ob_main_loop_timeout_remove(ob_main_loop, hide_desktop_popup_func);
 -        ob_main_loop_timeout_add(ob_main_loop, config_desktop_popup_time * 1000,
 -                                 hide_desktop_popup_func, desktop_popup[i],
 -                                 g_direct_equal, NULL);
++        obt_main_loop_timeout_remove(ob_main_loop, hide_desktop_popup_func);
++        obt_main_loop_timeout_add(ob_main_loop, config_desktop_popup_time * 1000,
++                                  hide_desktop_popup_func, desktop_popup[i],
++                                  g_direct_equal, NULL);
+         g_free(a);
+     }
  }
  
  void screen_hide_desktop_popup(void)
  {
-     obt_main_loop_timeout_remove(ob_main_loop, hide_desktop_popup_func);
-     pager_popup_hide(desktop_popup);
+     guint i;
+     for (i = 0; i < screen_num_monitors; i++) {
 -        ob_main_loop_timeout_remove_data(ob_main_loop, hide_desktop_popup_func,
 -                                         desktop_popup[i], FALSE);
++        obt_main_loop_timeout_remove_data(ob_main_loop, hide_desktop_popup_func,
++                                          desktop_popup[i], FALSE);
+         pager_popup_hide(desktop_popup[i]);
+     }
  }
  
  guint screen_find_desktop(guint from, ObDirection dir,
@@@ -1361,8 -1346,22 +1388,22 @@@ void screen_update_areas(void
      GSList *sit;
  
      g_free(monitor_area);
 -    extensions_xinerama_screens(&monitor_area, &screen_num_monitors);
 +    get_xinerama_screens(&monitor_area, &screen_num_monitors);
  
+     if (!desktop_popup) {
+         desktop_popup = g_new(ObPagerPopup*, screen_num_monitors);
+         for (i = 0; i < screen_num_monitors; i++) {
+             desktop_popup[i] = pager_popup_new();
+             pager_popup_height(desktop_popup[i], POPUP_HEIGHT);
+             if (screen_desktop_names)
+                 /* update the pager popup's width */
+                 pager_popup_text_width_to_strings(desktop_popup[i],
+                                                   screen_desktop_names,
+                                                   screen_num_desktops);
+         }
+     }
      /* set up the user-specified margins */
      config_margins.top_start = RECT_LEFT(monitor_area[screen_num_monitors]);
      config_margins.top_end = RECT_RIGHT(monitor_area[screen_num_monitors]);
diff --cc render/theme.c
index 667eafc9daaf2defe9caa4ddfe4a7795c4ca0610,0882637a70df257f26b44ea99f4d5bec72bee456..3d28cdeec7befa781c270f52fa23dabba6ff7b37
@@@ -49,49 -45,23 +49,65 @@@ static gboolean read_appearance(XrmData
  static int parse_inline_number(const char *p);
  static RrPixel32* read_c_image(gint width, gint height, const guint8 *data);
  static void set_default_appearance(RrAppearance *a);
 +static void read_button_colors(XrmDatabase db, const RrInstance *inst, 
 +                               const RrTheme *theme, RrButton *btn, 
 +                               const gchar *btnname);
 +
 +#define READ_INT(x_resstr, x_var, x_min, x_max, x_def) \
 +    if (!read_int(db, x_resstr, & x_var) || \
 +            x_var < x_min || x_var > x_max) \
 +        x_var = x_def;
 +
 +#define READ_INT_(x_resstr, x_resstr_fallback, x_var, x_min, x_max, x_def) \
 +    if (!read_int(db, x_resstr, & x_var) && \
 +        !read_int(db, x_resstr_fallback, & x_var) || \
 +            x_var < x_min || x_var > x_max) \
 +        x_var = x_def;
 +
 +#define READ_COLOR(x_resstr, x_var, x_def) \
 +    if (!read_color(db, inst, x_resstr, & x_var)) \
 +        x_var = x_def;
 +
 +#define READ_COLOR_(x_res1, x_res2, x_var, x_def) \
 +    if (!read_color(db, inst, x_res1, & x_var) && \
 +        !read_color(db, inst, x_res2, & x_var)) \
 +        x_var = x_def;
 +
 +#define READ_MASK_COPY(x_file, x_var, x_copysrc) \
 +    if (!read_mask(inst, path, theme, x_file, & x_var)) \
 +        x_var = RrPixmapMaskCopy(x_copysrc);
 +
 +#define READ_APPEARANCE(x_resstr, x_var, x_parrel) \
 +    if (!read_appearance(db, inst, x_resstr, x_var, x_parrel)) \
 +        set_default_appearance(x_var);
 +
 +#define READ_APPEARANCE_COPY(x_resstr, x_var, x_parrel, x_defval) \
 +    if (!read_appearance(db, inst, x_resstr, x_var, x_parrel)) {\
 +        RrAppearanceFree(x_var); \
 +        x_var = RrAppearanceCopy(x_defval); }
 +
 +#define READ_APPEARANCE_(x_res1, x_res2, x_var, x_parrel, x_defval) \
 +    if (!read_appearance(db, inst, x_res1, x_var, x_parrel) && \
 +        !read_appearance(db, inst, x_res2, x_var, x_parrel)) {\
 +        RrAppearanceFree(x_var); \
 +        x_var = RrAppearanceCopy(x_defval); }
  
+ static RrFont *get_font(RrFont *target, RrFont **default_font, const RrInstance *inst)
+ {
+     if (target) {
+         RrFontRef(target);
+         return target;
+     } else {
+         /* Only load the default font once */
+         if (*default_font) {
+             RrFontRef(*default_font);
+         } else {
+             *default_font = RrFontOpenDefault(inst);
+         }
+         return *default_font;
+     }
+ }
  RrTheme* RrThemeNew(const RrInstance *inst, const gchar *name,
                      gboolean allow_fallback,
                      RrFont *active_window_font, RrFont *inactive_window_font,
      RrJustify winjust, mtitlejust;
      gchar *str;
      RrTheme *theme;
+     RrFont *default_font = NULL;
      gchar *path;
      gboolean userdef;
 +    RrAppearance *a_disabled_focused_tmp;
 +    RrAppearance *a_disabled_unfocused_tmp;
 +    RrAppearance *a_hover_focused_tmp;
 +    RrAppearance *a_hover_unfocused_tmp;
 +    RrAppearance *a_focused_unpressed_tmp;
 +    RrAppearance *a_focused_pressed_tmp;
 +    RrAppearance *a_unfocused_unpressed_tmp;
 +    RrAppearance *a_unfocused_pressed_tmp;
 +    RrAppearance *a_toggled_hover_focused_tmp;
 +    RrAppearance *a_toggled_hover_unfocused_tmp;
 +    RrAppearance *a_toggled_focused_unpressed_tmp;
 +    RrAppearance *a_toggled_focused_pressed_tmp;
 +    RrAppearance *a_toggled_unfocused_unpressed_tmp;
 +    RrAppearance *a_toggled_unfocused_pressed_tmp;
  
      if (name) {
          db = loaddb(name, &path);
              mtitlejust = RR_JUSTIFY_CENTER;
      }
  
-     if (menu_item_font) {
-         theme->menu_font = menu_item_font;
-         RrFontRef(menu_item_font);
-     } else
-         theme->menu_font = RrFontOpenDefault(inst);
+     theme->menu_font = get_font(menu_item_font, &default_font, inst);
  
-     if (osd_font) {
-         theme->osd_font = osd_font;
-         RrFontRef(osd_font);
-     } else
-         theme->osd_font = RrFontOpenDefault(inst);
+     theme->osd_font = get_font(osd_font, &default_font, inst);
  
      /* load direct dimensions */
 -    if ((!read_int(db, "menu.overlap.x", &theme->menu_overlap_x) &&
 -         !read_int(db, "menu.overlap", &theme->menu_overlap_x)) ||
 -        theme->menu_overlap_x < -100 || theme->menu_overlap_x > 100)
 -        theme->menu_overlap_x = 0;
 -    if ((!read_int(db, "menu.overlap.y", &theme->menu_overlap_y) &&
 -         !read_int(db, "menu.overlap", &theme->menu_overlap_y)) ||
 -        theme->menu_overlap_y < -100 || theme->menu_overlap_y > 100)
 -        theme->menu_overlap_y = 0;
 -    if (!read_int(db, "window.handle.width", &theme->handle_height) ||
 -        theme->handle_height < 0 || theme->handle_height > 100)
 -        theme->handle_height = 6;
 -    if (!read_int(db, "padding.width", &theme->paddingx) ||
 -        theme->paddingx < 0 || theme->paddingx > 100)
 -        theme->paddingx = 3;
 -    if (!read_int(db, "padding.height", &theme->paddingy) ||
 -        theme->paddingy < 0 || theme->paddingy > 100)
 -        theme->paddingy = theme->paddingx;
 -    if (!read_int(db, "border.width", &theme->fbwidth) ||
 -        theme->fbwidth < 0 || theme->fbwidth > 100)
 -        theme->fbwidth = 1;
 -    /* menu border width inherits from the frame border width */
 -    if (!read_int(db, "menu.border.width", &theme->mbwidth) ||
 -        theme->mbwidth < 0 || theme->mbwidth > 100)
 -        theme->mbwidth = theme->fbwidth;
 -    /* osd border width inherits from the frame border width */
 -    if (!read_int(db, "osd.border.width", &theme->obwidth) ||
 -        theme->obwidth < 0 || theme->obwidth > 100)
 -        theme->obwidth = theme->fbwidth;
 -    if (!read_int(db, "window.client.padding.width", &theme->cbwidthx) ||
 -        theme->cbwidthx < 0 || theme->cbwidthx > 100)
 -        theme->cbwidthx = theme->paddingx;
 -    if (!read_int(db, "window.client.padding.height", &theme->cbwidthy) ||
 -        theme->cbwidthy < 0 || theme->cbwidthy > 100)
 -        theme->cbwidthy = theme->cbwidthx;
 -    if (!read_int(db, "menu.separator.width", &theme->menu_sep_width) ||
 -        theme->menu_sep_width < 1 || theme->menu_sep_width > 100)
 -        theme->menu_sep_width = 1;
 -    if (!read_int(db, "menu.separator.padding.width",
 -                  &theme->menu_sep_paddingx) ||
 -        theme->menu_sep_paddingx < 0 || theme->menu_sep_paddingx > 100)
 -        theme->menu_sep_paddingx = 6;
 -    if (!read_int(db, "menu.separator.padding.height",
 -                  &theme->menu_sep_paddingy) ||
 -        theme->menu_sep_paddingy < 0 || theme->menu_sep_paddingy > 100)
 -        theme->menu_sep_paddingy = 3;
 +    READ_INT_("menu.overlap.x", "menu.overlap", theme->menu_overlap_x, -100, 100, 0)
 +    READ_INT_("menu.overlap.y", "menu.overlap", theme->menu_overlap_y, -100, 100, 0)
 +    READ_INT("window.handle.width", theme->handle_height, 0, 100, 6);
 +    READ_INT("padding.width", theme->paddingx, 0, 100, 3);
 +    READ_INT("padding.height", theme->paddingy, 0, 100, theme->paddingx);
 +    READ_INT("border.width", theme->fbwidth, 0, 100, 1);
 +    READ_INT("menu.border.width", theme->mbwidth, 0, 100, theme->fbwidth);
 +    READ_INT("osd.border.width", theme->obwidth, 0, 100, theme->fbwidth);
 +    READ_INT("window.client.padding.width", theme->cbwidthx, 0, 100,
 +             theme->paddingx);
 +    READ_INT("window.client.padding.height", theme->cbwidthy, 0, 100,
 +             theme->cbwidthx);
 +    READ_INT("menu.separator.width", theme->menu_sep_width, 1, 100, 1);
 +    READ_INT("menu.separator.padding.width", theme->menu_sep_paddingx, 0, 100, 6);
 +    READ_INT("menu.separator.padding.height", theme->menu_sep_paddingx, 0, 100, 3);
  
      /* load colors */
 -    if (!read_color(db, inst,
 -                    "window.active.border.color",
 -                    &theme->frame_focused_border_color) &&
 -        !read_color(db, inst,
 -                    "border.color",
 -                    &theme->frame_focused_border_color))
 -        theme->frame_focused_border_color = RrColorNew(inst, 0, 0, 0);
 +    READ_COLOR_("window.active.border.color", "border.color",
 +                theme->frame_focused_border_color, RrColorNew(inst, 0, 0, 0));
 +
      /* title separator focused color inherits from focused border color */
 -    if (!read_color(db, inst,
 -                    "window.active.title.separator.color",
 -                    &theme->title_separator_focused_color))
 -        theme->title_separator_focused_color =
 -            RrColorNew(inst,
 -                       theme->frame_focused_border_color->r,
 -                       theme->frame_focused_border_color->g,
 -                       theme->frame_focused_border_color->b);
 +    READ_COLOR("window.active.title.separator.color",
 +               theme->title_separator_focused_color,
 +               RrColorCopy(theme->frame_focused_border_color));
 +
      /* unfocused border color inherits from frame focused border color */
 -    if (!read_color(db, inst,
 -                    "window.inactive.border.color",
 -                    &theme->frame_unfocused_border_color))
 -        theme->frame_unfocused_border_color =
 -            RrColorNew(inst, theme->frame_focused_border_color->r,
 -                       theme->frame_focused_border_color->g,
 -                       theme->frame_focused_border_color->b);
 +    READ_COLOR("window.inactive.border.color",
 +               theme->frame_unfocused_border_color,
 +               RrColorCopy(theme->frame_focused_border_color));
 +
      /* title separator unfocused color inherits from unfocused border color */
 -    if (!read_color(db, inst,
 -                    "window.inactive.title.separator.color",
 -                    &theme->title_separator_unfocused_color))
 -        theme->title_separator_unfocused_color =
 -            RrColorNew(inst,
 -                       theme->frame_unfocused_border_color->r,
 -                       theme->frame_unfocused_border_color->g,
 -                       theme->frame_unfocused_border_color->b);
 +    READ_COLOR("window.inactive.title.separator.color",
 +               theme->title_separator_unfocused_color,
 +               RrColorCopy(theme->frame_unfocused_border_color));
  
      /* menu border color inherits from frame focused border color */
 -    if (!read_color(db, inst, "menu.border.color", &theme->menu_border_color))
 -        theme->menu_border_color =
 -            RrColorNew(inst,
 -                       theme->frame_focused_border_color->r,
 -                       theme->frame_focused_border_color->g,
 -                       theme->frame_focused_border_color->b);
 +    READ_COLOR("menu.border.color", theme->menu_border_color,
 +               RrColorCopy(theme->frame_focused_border_color));
 +
      /* osd border color inherits from frame focused border color */
 -    if (!read_color(db, inst, "osd.border.color", &theme->osd_border_color))
 -        theme->osd_border_color =
 -            RrColorNew(inst,
 -                       theme->frame_focused_border_color->r,
 -                       theme->frame_focused_border_color->g,
 -                       theme->frame_focused_border_color->b);
 -    if (!read_color(db, inst,
 -                    "window.active.client.color",
 -                    &theme->cb_focused_color))
 -        theme->cb_focused_color = RrColorNew(inst, 0xff, 0xff, 0xff);
 -    if (!read_color(db, inst,
 -                    "window.inactive.client.color",
 -                    &theme->cb_unfocused_color))
 -        theme->cb_unfocused_color = RrColorNew(inst, 0xff, 0xff, 0xff);
 -    if (!read_color(db, inst,
 -                    "window.active.label.text.color",
 -                    &theme->title_focused_color))
 -        theme->title_focused_color = RrColorNew(inst, 0x0, 0x0, 0x0);
 -    if (!read_color(db, inst, "osd.label.text.color", &theme->osd_color))
 -        theme->osd_color = RrColorNew(inst,
 -                                      theme->title_focused_color->r,
 -                                      theme->title_focused_color->g,
 -                                      theme->title_focused_color->b);
 -    if (!read_color(db, inst,
 -                    "window.inactive.label.text.color",
 -                    &theme->title_unfocused_color))
 -        theme->title_unfocused_color = RrColorNew(inst, 0xff, 0xff, 0xff);
 -    if (!read_color(db, inst,
 -                    "window.active.button.unpressed.image.color",
 -                    &theme->titlebut_focused_unpressed_color))
 -        theme->titlebut_focused_unpressed_color = RrColorNew(inst, 0, 0, 0);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.unpressed.image.color",
 -                    &theme->titlebut_unfocused_unpressed_color))
 -        theme->titlebut_unfocused_unpressed_color =
 -            RrColorNew(inst, 0xff, 0xff, 0xff);
 -    if (!read_color(db, inst,
 -                    "window.active.button.pressed.image.color",
 -                    &theme->titlebut_focused_pressed_color))
 -        theme->titlebut_focused_pressed_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_focused_unpressed_color->r,
 -                       theme->titlebut_focused_unpressed_color->g,
 -                       theme->titlebut_focused_unpressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.pressed.image.color",
 -                    &theme->titlebut_unfocused_pressed_color))
 -        theme->titlebut_unfocused_pressed_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_unfocused_unpressed_color->r,
 -                       theme->titlebut_unfocused_unpressed_color->g,
 -                       theme->titlebut_unfocused_unpressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.active.button.disabled.image.color",
 -                    &theme->titlebut_disabled_focused_color))
 -        theme->titlebut_disabled_focused_color =
 -            RrColorNew(inst, 0xff, 0xff, 0xff);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.disabled.image.color",
 -                    &theme->titlebut_disabled_unfocused_color))
 -        theme->titlebut_disabled_unfocused_color = RrColorNew(inst, 0, 0, 0);
 -    if (!read_color(db, inst,
 -                    "window.active.button.hover.image.color",
 -                    &theme->titlebut_hover_focused_color))
 -        theme->titlebut_hover_focused_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_focused_unpressed_color->r,
 -                       theme->titlebut_focused_unpressed_color->g,
 -                       theme->titlebut_focused_unpressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.hover.image.color",
 -                    &theme->titlebut_hover_unfocused_color))
 -        theme->titlebut_hover_unfocused_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_unfocused_unpressed_color->r,
 -                       theme->titlebut_unfocused_unpressed_color->g,
 -                       theme->titlebut_unfocused_unpressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.active.button.toggled.unpressed.image.color",
 -                    &theme->titlebut_toggled_focused_unpressed_color) &&
 -        !read_color(db, inst,
 -                    "window.active.button.toggled.image.color",
 -                    &theme->titlebut_toggled_focused_unpressed_color))
 -        theme->titlebut_toggled_focused_unpressed_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_focused_pressed_color->r,
 -                       theme->titlebut_focused_pressed_color->g,
 -                       theme->titlebut_focused_pressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.toggled.unpressed.image.color",
 -                    &theme->titlebut_toggled_unfocused_unpressed_color) &&
 -        !read_color(db, inst,
 -                    "window.inactive.button.toggled.image.color",
 -                    &theme->titlebut_toggled_unfocused_unpressed_color))
 -        theme->titlebut_toggled_unfocused_unpressed_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_unfocused_pressed_color->r,
 -                       theme->titlebut_unfocused_pressed_color->g,
 -                       theme->titlebut_unfocused_pressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.active.button.toggled.hover.image.color",
 -                    &theme->titlebut_toggled_hover_focused_color))
 -        theme->titlebut_toggled_hover_focused_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_toggled_focused_unpressed_color->r,
 -                       theme->titlebut_toggled_focused_unpressed_color->g,
 -                       theme->titlebut_toggled_focused_unpressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.toggled.hover.image.color",
 -                    &theme->titlebut_toggled_hover_unfocused_color))
 -        theme->titlebut_toggled_hover_unfocused_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_toggled_unfocused_unpressed_color->r,
 -                       theme->titlebut_toggled_unfocused_unpressed_color->g,
 -                       theme->titlebut_toggled_unfocused_unpressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.active.button.toggled.pressed.image.color",
 -                    &theme->titlebut_toggled_focused_pressed_color))
 -        theme->titlebut_toggled_focused_pressed_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_focused_pressed_color->r,
 -                       theme->titlebut_focused_pressed_color->g,
 -                       theme->titlebut_focused_pressed_color->b);
 -    if (!read_color(db, inst,
 -                    "window.inactive.button.toggled.pressed.image.color",
 -                    &theme->titlebut_toggled_unfocused_pressed_color))
 -        theme->titlebut_toggled_unfocused_pressed_color =
 -            RrColorNew(inst,
 -                       theme->titlebut_unfocused_pressed_color->r,
 -                       theme->titlebut_unfocused_pressed_color->g,
 -                       theme->titlebut_unfocused_pressed_color->b);
 -    if (!read_color(db, inst,
 -                    "menu.title.text.color", &theme->menu_title_color))
 -        theme->menu_title_color = RrColorNew(inst, 0, 0, 0);
 -    if (!read_color(db, inst,
 -                    "menu.items.text.color", &theme->menu_color))
 -        theme->menu_color = RrColorNew(inst, 0xff, 0xff, 0xff);
 -    if (!read_color(db, inst,
 -                    "menu.items.disabled.text.color",
 -                    &theme->menu_disabled_color))
 -        theme->menu_disabled_color = RrColorNew(inst, 0, 0, 0);
 -    if (!read_color(db, inst,
 -                    "menu.items.active.disabled.text.color",
 -                    &theme->menu_disabled_selected_color))
 -        theme->menu_disabled_selected_color =
 -            RrColorNew(inst,
 -                       theme->menu_disabled_color->r,
 -                       theme->menu_disabled_color->g,
 -                       theme->menu_disabled_color->b);
 -    if (!read_color(db, inst,
 -                    "menu.items.active.text.color",
 -                    &theme->menu_selected_color))
 -        theme->menu_selected_color = RrColorNew(inst, 0, 0, 0);
 -    if (!read_color(db, inst,
 -                    "menu.separator.color", &theme->menu_sep_color))
 -        theme->menu_sep_color = RrColorNew(inst,
 -                                           theme->menu_color->r,
 -                                           theme->menu_color->g,
 -                                           theme->menu_color->b);
 +    READ_COLOR("osd.border.color", theme->osd_border_color,
 +               RrColorCopy(theme->frame_focused_border_color));
 +
 +    READ_COLOR("window.active.client.color", theme->cb_focused_color,
 +               RrColorNew(inst, 0xff, 0xff, 0xff));
 +
 +    READ_COLOR("window.inactive.client.color", theme->cb_unfocused_color,
 +               RrColorNew(inst, 0xff, 0xff, 0xff));
 +
 +    READ_COLOR("window.active.label.text.color", theme->title_focused_color,
 +               RrColorNew(inst, 0x0, 0x0, 0x0));
 +
 +    READ_COLOR("osd.label.text.color", theme->osd_color,
 +               RrColorCopy(theme->title_focused_color));
 +
 +    READ_COLOR("window.inactive.label.text.color",
 +               theme->title_unfocused_color,
 +               RrColorNew(inst, 0xff, 0xff, 0xff));
 +
 +    READ_COLOR("window.active.button.unpressed.image.color",
 +               theme->titlebut_focused_unpressed_color,
 +               RrColorNew(inst, 0, 0, 0));
 +
 +    READ_COLOR("window.inactive.button.unpressed.image.color",
 +               theme->titlebut_unfocused_unpressed_color,
 +               RrColorNew(inst, 0xff, 0xff, 0xff));
 +
 +    READ_COLOR("window.active.button.pressed.image.color",
 +               theme->titlebut_focused_pressed_color,
 +               RrColorCopy(theme->titlebut_focused_unpressed_color));
 +
 +    READ_COLOR("window.inactive.button.pressed.image.color",
 +               theme->titlebut_unfocused_pressed_color,
 +               RrColorCopy(theme->titlebut_unfocused_unpressed_color));
 +
 +    READ_COLOR("window.active.button.disabled.image.color",
 +               theme->titlebut_disabled_focused_color,
 +               RrColorNew(inst, 0xff, 0xff, 0xff));
 +
 +    READ_COLOR("window.inactive.button.disabled.image.color",
 +               theme->titlebut_disabled_unfocused_color,
 +               RrColorNew(inst, 0, 0, 0));
 +
 +    READ_COLOR("window.active.button.hover.image.color",
 +               theme->titlebut_hover_focused_color,
 +               RrColorCopy(theme->titlebut_focused_unpressed_color));
 +
 +    READ_COLOR("window.inactive.button.hover.image.color",
 +               theme->titlebut_hover_unfocused_color,
 +               RrColorCopy(theme->titlebut_unfocused_unpressed_color));
 +
 +    READ_COLOR_("window.active.button.toggled.unpressed.image.color",
 +                "window.active.button.toggled.image.color",
 +                theme->titlebut_toggled_focused_unpressed_color,
 +                RrColorCopy(theme->titlebut_focused_pressed_color));
 +
 +    READ_COLOR_("window.inactive.button.toggled.unpressed.image.color",
 +                "window.inactive.button.toggled.image.color",
 +                theme->titlebut_toggled_unfocused_unpressed_color,
 +                RrColorCopy(theme->titlebut_unfocused_pressed_color));
 +
 +    READ_COLOR("window.active.button.toggled.hover.image.color",
 +               theme->titlebut_toggled_hover_focused_color,
 +               RrColorCopy(theme->titlebut_toggled_focused_unpressed_color));
 +
 +    READ_COLOR("window.inactive.button.toggled.hover.image.color",
 +               theme->titlebut_toggled_hover_unfocused_color,
 +               RrColorCopy(theme->titlebut_toggled_unfocused_unpressed_color));
 +
 +    READ_COLOR("window.active.button.toggled.pressed.image.color",
 +               theme->titlebut_toggled_focused_pressed_color,
 +               RrColorCopy(theme->titlebut_focused_pressed_color));
 +
 +    READ_COLOR("window.inactive.button.toggled.pressed.image.color",
 +               theme->titlebut_toggled_unfocused_pressed_color,
 +               RrColorCopy(theme->titlebut_unfocused_pressed_color));
 +
 +    READ_COLOR("menu.title.text.color", theme->menu_title_color,
 +               RrColorNew(inst, 0, 0, 0));
 +
 +    READ_COLOR("menu.items.text.color", theme->menu_color,
 +               RrColorNew(inst, 0xff, 0xff, 0xff));
 +
 +    READ_COLOR("menu.bullet.image.color", theme->menu_bullet_color,
 +               RrColorCopy(theme->menu_color));
 +   
 +    READ_COLOR("menu.items.disabled.text.color", theme->menu_disabled_color,
 +               RrColorNew(inst, 0, 0, 0));
 +
 +    READ_COLOR("menu.items.active.disabled.text.color",
 +               theme->menu_disabled_selected_color,
 +               RrColorCopy(theme->menu_disabled_color));
 +
 +    READ_COLOR("menu.items.active.text.color", theme->menu_selected_color,
 +               RrColorNew(inst, 0, 0, 0));
 +
 +    READ_COLOR("menu.separator.color", theme->menu_sep_color,
 +               RrColorCopy(theme->menu_color));
 +
 +    READ_COLOR("menu.bullet.selected.image.color", 
 +               theme->menu_bullet_selected_color,
 +               RrColorCopy(theme->menu_selected_color));
 + 
  
      /* load the image masks */