Bitmap buttons patch
Scott Moynes
smoynes at nexus.carleton.ca
Fri Aug 30 00:49:28 EDT 2002
Here is my bitmap button patch, or as I like to call it bubby-buttons.
It is quite rough, and there's some things I'd like to fix up, but I
wanted some feedback.
Here's how it works:
- new style/rcfile options have been added
window.button.{close,max,icon,stick}_mask: filename
Right now the filename has to be specified absolutely, but that
will change. I don't know whether we should just use expandTilde()
or make the filename relative to the style location.
- the files must be xbm files, which gimp can easily create, or if you
really want to can be created with a simple text editor. I have a
sample set at
http://nexus.carleton.ca/~smoynes/{close,icon,stick,max}.xbm
If there is any problem loading the file the old images are
used. This allows users to override the stile with something like
window.button.close_mask: false
and they don't have to put up with some lame matrix theme buttons
- The images won't scale. Let me repeat that. The images won't
scale. Nor are they likely ever going to. In my experimentation, I
found the difference in size between the smallest title bar I'd ever
consider using and the largest to be pretty small. It might be a
problem across different machines, but it isn't difficult to scale
them yourself with an image editor.
Here's a quick screenshot.
http://nexus.carleton.ca/~smoynes/bubby-buttons.png
Any questions, comments or patches are welcome.
--
Scott Moynes
"Computer science is as much about computers
as astronomy is about telescopes." -- Dijkstra
-------------- next part --------------
? sticky-button-1.diff
Index: src/Screen.cc
===================================================================
RCS file: /cvs/cvsroot/openbox/src/Screen.cc,v
retrieving revision 1.138
diff -p -u -r1.138 Screen.cc
--- src/Screen.cc 2002/08/27 10:57:15 1.138
+++ src/Screen.cc 2002/08/30 04:45:48
@@ -339,6 +339,24 @@ BScreen::~BScreen(void) {
if (resource.tstyle.font)
delete resource.tstyle.font;
+ if (resource.wstyle.close_button.mask != None) {
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.close_button.mask);
+ }
+ if (resource.wstyle.max_button.mask != None) {
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.max_button.mask);
+ }
+ if (resource.wstyle.icon_button.mask != None) {
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.icon_button.mask);
+ }
+ if (resource.wstyle.stick_button.mask != None) {
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.stick_button.mask);
+ }
+
+
+ resource.wstyle.max_button.mask = resource.wstyle.close_button.mask =
+ resource.wstyle.icon_button.mask =
+ resource.wstyle.stick_button.mask = None;
+
XFreeGC(blackbox->getXDisplay(), opGC);
}
@@ -975,6 +993,28 @@ void BScreen::LoadStyle(void) {
resource.wstyle.b_pressed =
readDatabaseTexture("window.button.pressed", "black", style);
+ if (resource.wstyle.close_button.mask != None)
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.close_button.mask);
+ if (resource.wstyle.max_button.mask != None)
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.max_button.mask);
+ if (resource.wstyle.icon_button.mask != None)
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.icon_button.mask);
+ if (resource.wstyle.stick_button.mask != None)
+ XFreePixmap(blackbox->getXDisplay(), resource.wstyle.stick_button.mask);
+
+ resource.wstyle.close_button.mask = resource.wstyle.max_button.mask =
+ resource.wstyle.icon_button.mask =
+ resource.wstyle.icon_button.mask = None;
+
+ readDatabaseMask("window.button.close_mask", resource.wstyle.close_button,
+ style);
+ readDatabaseMask("window.button.max_mask", resource.wstyle.max_button,
+ style);
+ readDatabaseMask("window.button.icon_mask", resource.wstyle.icon_button,
+ style);
+ readDatabaseMask("window.button.stick_mask", resource.wstyle.stick_button,
+ style);
+
// we create the window.frame texture by hand because it exists only to
// make the code cleaner and is not actually used for display
BColor color = readDatabaseColor("window.frame.focusColor", "white", style);
@@ -2501,6 +2541,23 @@ void BScreen::toggleFocusModel(FocusMode
std::mem_fun(&BlackboxWindow::grabButtons));
}
+void BScreen::readDatabaseMask(const string &rname, PixmapMask &pixmapMask,
+ const Configuration &style) {
+ string s;
+ int hx, hy; //ignored
+ int ret;
+ if (style.getValue(rname, s))
+ {
+ ret = XReadBitmapFile(blackbox->getXDisplay(), getRootWindow(),
+ s.c_str(), &pixmapMask.w, &pixmapMask.h,
+ &pixmapMask.mask, &hx, &hy);
+ if (ret == BitmapSuccess)
+ return;
+ }
+
+ pixmapMask.mask = None;
+ pixmapMask.w = pixmapMask.h = 0;
+}
BTexture BScreen::readDatabaseTexture(const string &rname,
const string &default_color,
Index: src/Screen.hh
===================================================================
RCS file: /cvs/cvsroot/openbox/src/Screen.hh,v
retrieving revision 1.34
diff -p -u -r1.34 Screen.hh
--- src/Screen.hh 2002/08/22 03:46:45 1.34
+++ src/Screen.hh 2002/08/30 04:45:49
@@ -61,12 +61,19 @@ struct Strut;
enum TextJustify { LeftJustify = 1, RightJustify, CenterJustify };
+struct PixmapMask {
+ Pixmap mask;
+ unsigned int w, h;
+};
+
struct WindowStyle {
BColor l_text_focus, l_text_unfocus, b_pic_focus,
b_pic_unfocus;
BTexture f_focus, f_unfocus, t_focus, t_unfocus, l_focus, l_unfocus,
h_focus, h_unfocus, b_focus, b_unfocus, b_pressed, g_focus, g_unfocus;
+ PixmapMask close_button, max_button, icon_button, stick_button;
+
BFont *font;
TextJustify justify;
@@ -178,6 +185,9 @@ private:
bool parseMenuFile(FILE *file, Rootmenu *menu);
+ void readDatabaseMask(const string &rname,
+ PixmapMask &pixmapMask,
+ const Configuration &style);
BTexture readDatabaseTexture(const std::string &rname,
const std::string &default_color,
const Configuration &style);
Index: src/Window.cc
===================================================================
RCS file: /cvs/cvsroot/openbox/src/Window.cc,v
retrieving revision 1.168
diff -p -u -r1.168 Window.cc
--- src/Window.cc 2002/08/29 00:07:53 1.168
+++ src/Window.cc 2002/08/30 04:45:56
@@ -722,7 +722,7 @@ void BlackboxWindow::destroyTitlebar(voi
if (frame.stick_button)
destroyStickyButton();
-
+
if (frame.ftitle)
screen->getImageControl()->removeImage(frame.ftitle);
@@ -2608,12 +2608,29 @@ void BlackboxWindow::redrawIconifyButton
XSetWindowBackground(blackbox->getXDisplay(),
frame.iconify_button, frame.pbutton_pixel);
}
- XClearWindow(blackbox->getXDisplay(), frame.iconify_button);
+ XClearWindow(blackbox->getXDisplay(), frame.iconify_button);
BPen pen((flags.focused) ? screen->getWindowStyle()->b_pic_focus :
- screen->getWindowStyle()->b_pic_unfocus);
- XDrawRectangle(blackbox->getXDisplay(), frame.iconify_button, pen.gc(),
- 2, (frame.button_w - 5), (frame.button_w - 5), 2);
+ screen->getWindowStyle()->b_pic_unfocus);
+
+ PixmapMask pm = screen->getWindowStyle()->icon_button;
+
+ if (screen->getWindowStyle()->icon_button.mask != None) {
+ XSetClipMask(blackbox->getXDisplay(), pen.gc(), pm.mask);
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2);
+
+ XFillRectangle(blackbox->getXDisplay(), frame.iconify_button, pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2,
+ (frame.button_w + pm.w)/2, (frame.button_w + pm.h)/2);
+
+ XSetClipMask(blackbox->getXDisplay(), pen.gc(), None);
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(), 0, 0);
+ } else {
+
+ XDrawRectangle(blackbox->getXDisplay(), frame.iconify_button, pen.gc(),
+ 2, (frame.button_w - 5), (frame.button_w - 5), 2);
+ }
}
@@ -2646,10 +2663,26 @@ void BlackboxWindow::redrawMaximizeButto
BPen pen((flags.focused) ? screen->getWindowStyle()->b_pic_focus :
screen->getWindowStyle()->b_pic_unfocus);
- XDrawRectangle(blackbox->getXDisplay(), frame.maximize_button, pen.gc(),
- 2, 2, (frame.button_w - 5), (frame.button_w - 5));
- XDrawLine(blackbox->getXDisplay(), frame.maximize_button, pen.gc(),
- 2, 3, (frame.button_w - 3), 3);
+
+ PixmapMask pm = screen->getWindowStyle()->max_button;
+
+ if (pm.mask != None) {
+ XSetClipMask(blackbox->getXDisplay(), pen.gc(), pm.mask);
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2);
+
+ XFillRectangle(blackbox->getXDisplay(), frame.maximize_button, pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2,
+ (frame.button_w + pm.w)/2, (frame.button_w + pm.h)/2);
+
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(), 0, 0 );
+ XSetClipMask( blackbox->getXDisplay(), pen.gc(), None );
+ } else {
+ XDrawRectangle(blackbox->getXDisplay(), frame.maximize_button, pen.gc(),
+ 2, 2, (frame.button_w - 5), (frame.button_w - 5));
+ XDrawLine(blackbox->getXDisplay(), frame.maximize_button, pen.gc(),
+ 2, 3, (frame.button_w - 3), 3);
+ }
}
@@ -2657,8 +2690,8 @@ void BlackboxWindow::redrawCloseButton(b
if (! pressed) {
if (flags.focused) {
if (frame.fbutton)
- XSetWindowBackgroundPixmap(blackbox->getXDisplay(), frame.close_button,
- frame.fbutton);
+ XSetWindowBackgroundPixmap(blackbox->getXDisplay(),
+ frame.close_button, frame.fbutton);
else
XSetWindowBackground(blackbox->getXDisplay(), frame.close_button,
frame.fbutton_pixel);
@@ -2681,14 +2714,31 @@ void BlackboxWindow::redrawCloseButton(b
XClearWindow(blackbox->getXDisplay(), frame.close_button);
BPen pen((flags.focused) ? screen->getWindowStyle()->b_pic_focus :
- screen->getWindowStyle()->b_pic_unfocus, 0, 2);
- XDrawLine(blackbox->getXDisplay(), frame.close_button, pen.gc(),
- 2, 2, (frame.button_w - 3), (frame.button_w - 3));
- XDrawLine(blackbox->getXDisplay(), frame.close_button, pen.gc(),
- 2, (frame.button_w - 3), (frame.button_w - 3), 2);
-}
+ screen->getWindowStyle()->b_pic_unfocus);
+ PixmapMask pm = screen->getWindowStyle()->close_button;
+
+ if (pm.mask != None) {
+ XSetClipMask(blackbox->getXDisplay(), pen.gc(), pm.mask);
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2);
+
+ XFillRectangle(blackbox->getXDisplay(), frame.close_button, pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2,
+ (frame.button_w + pm.w)/2, (frame.button_w + pm.h)/2);
+
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(), 0, 0 );
+ XSetClipMask( blackbox->getXDisplay(), pen.gc(), None );
+ } else {
+
+ XDrawLine(blackbox->getXDisplay(), frame.close_button, pen.gc(),
+ 2, 2, (frame.button_w - 3), (frame.button_w - 3));
+ XDrawLine(blackbox->getXDisplay(), frame.close_button, pen.gc(),
+ 2, (frame.button_w - 3), (frame.button_w - 3), 2);
+ }
+}
+
void BlackboxWindow::redrawStickyButton(bool pressed) const {
if (! pressed) {
if (flags.focused) {
@@ -2718,9 +2768,25 @@ void BlackboxWindow::redrawStickyButton(
BPen pen((flags.focused) ? screen->getWindowStyle()->b_pic_focus :
screen->getWindowStyle()->b_pic_unfocus);
+
+ PixmapMask pm = screen->getWindowStyle()->stick_button;
+
+ if (pm.mask != None) {
+ XSetClipMask(blackbox->getXDisplay(), pen.gc(), pm.mask);
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2);
+
+ XFillRectangle(blackbox->getXDisplay(), frame.stick_button, pen.gc(),
+ (frame.button_w - pm.w)/2, (frame.button_w - pm.h)/2,
+ (frame.button_w + pm.w)/2, (frame.button_w + pm.h)/2);
+
- XFillRectangle(blackbox->getXDisplay(), frame.stick_button, pen.gc(),
- frame.button_w/2 - 1, frame.button_w/2 -1, 2, 2 );
+ XSetClipOrigin(blackbox->getXDisplay(), pen.gc(), 0, 0 );
+ XSetClipMask( blackbox->getXDisplay(), pen.gc(), None );
+ } else {
+ XFillRectangle(blackbox->getXDisplay(), frame.stick_button, pen.gc(),
+ frame.button_w/2 - 1, frame.button_w/2 -1, 2, 2 );
+ }
}
void BlackboxWindow::mapRequestEvent(const XMapRequestEvent *re) {
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 240 bytes
Desc: not available
URL: <http://icculus.org/pipermail/openbox/attachments/20020830/86ca18e3/attachment.pgp>
More information about the openbox
mailing list