2006-02-10 00:48:01 +03:00
|
|
|
/*
|
|
|
|
* (C)opyright MMIV-MMVI Anselm R. Garbe <garbeam at gmail dot com>
|
|
|
|
* See LICENSE file for license details.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include <string.h>
|
2006-03-09 04:15:43 +03:00
|
|
|
#include <stdlib.h>
|
2006-02-10 00:48:01 +03:00
|
|
|
|
|
|
|
#include "wm.h"
|
|
|
|
|
2006-03-09 04:15:43 +03:00
|
|
|
static int
|
2006-05-23 10:25:13 +04:00
|
|
|
comp_bar(const void *b1, const void *b2)
|
2006-03-09 04:15:43 +03:00
|
|
|
{
|
2006-05-01 22:53:30 +04:00
|
|
|
Bar *bb1 = *(Bar **)b1;
|
|
|
|
Bar *bb2 = *(Bar **)b2;
|
|
|
|
if(bb1->intern && !bb2->intern)
|
2006-03-26 18:37:03 +04:00
|
|
|
return -1;
|
2006-05-01 22:53:30 +04:00
|
|
|
if(!bb1->intern && bb2->intern)
|
2006-03-26 18:37:03 +04:00
|
|
|
return 1;
|
2006-05-01 22:53:30 +04:00
|
|
|
return strcmp(bb1->name, bb2->name);
|
2006-03-09 04:15:43 +03:00
|
|
|
}
|
|
|
|
|
2006-04-03 15:40:34 +04:00
|
|
|
static Vector *
|
2006-05-01 22:53:30 +04:00
|
|
|
vector_of_bars(BarVector *bv)
|
2006-04-03 00:53:56 +04:00
|
|
|
{
|
2006-05-01 22:53:30 +04:00
|
|
|
return (Vector *) bv;
|
2006-04-03 00:53:56 +04:00
|
|
|
}
|
|
|
|
|
2006-04-12 12:44:07 +04:00
|
|
|
Bar *
|
|
|
|
create_bar(char *name, Bool intern)
|
2006-02-10 00:48:01 +03:00
|
|
|
{
|
|
|
|
static unsigned int id = 1;
|
2006-05-01 22:53:30 +04:00
|
|
|
Bar *b = bar_of_name(name);
|
|
|
|
|
|
|
|
if(b)
|
|
|
|
return b;
|
|
|
|
b = cext_emallocz(sizeof(Bar));
|
|
|
|
b->id = id++;
|
|
|
|
b->intern = intern;
|
|
|
|
cext_strlcpy(b->name, name, sizeof(b->name));
|
2006-05-19 22:14:06 +04:00
|
|
|
cext_strlcpy(b->colstr, def.selcolor, sizeof(b->colstr));
|
2006-05-01 22:53:30 +04:00
|
|
|
b->color = def.sel;
|
|
|
|
cext_vattach(vector_of_bars(&bar), b);
|
2006-05-23 10:25:13 +04:00
|
|
|
qsort(bar.data, bar.size, sizeof(Bar *), comp_bar);
|
2006-05-01 22:53:30 +04:00
|
|
|
return b;
|
2006-02-10 00:48:01 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2006-05-01 22:53:30 +04:00
|
|
|
destroy_bar(Bar *b)
|
2006-02-10 00:48:01 +03:00
|
|
|
{
|
2006-05-01 22:53:30 +04:00
|
|
|
cext_vdetach(vector_of_bars(&bar), b);
|
|
|
|
free(b);
|
2006-02-10 00:48:01 +03:00
|
|
|
}
|
|
|
|
|
2006-02-24 12:38:48 +03:00
|
|
|
unsigned int
|
2006-04-12 12:44:07 +04:00
|
|
|
height_of_bar()
|
2006-02-24 12:38:48 +03:00
|
|
|
{
|
2006-04-11 16:23:13 +04:00
|
|
|
enum { BAR_PADDING = 4 };
|
2006-05-02 01:32:04 +04:00
|
|
|
return blitzfont.ascent + blitzfont.descent + BAR_PADDING;
|
2006-02-24 12:38:48 +03:00
|
|
|
}
|
|
|
|
|
2006-02-10 20:32:35 +03:00
|
|
|
void
|
2006-04-12 12:44:07 +04:00
|
|
|
resize_bar()
|
2006-02-10 20:32:35 +03:00
|
|
|
{
|
2006-03-01 13:55:46 +03:00
|
|
|
unsigned int i, j;
|
2006-03-23 01:49:18 +03:00
|
|
|
brect = rect;
|
2006-04-12 12:44:07 +04:00
|
|
|
brect.height = height_of_bar();
|
2006-03-23 01:49:18 +03:00
|
|
|
brect.y = rect.height - brect.height;
|
|
|
|
XMoveResizeWindow(dpy, barwin, brect.x, brect.y, brect.width, brect.height);
|
|
|
|
XSync(dpy, False);
|
|
|
|
XFreePixmap(dpy, barpmap);
|
|
|
|
barpmap = XCreatePixmap(dpy, barwin, brect.width, brect.height,
|
|
|
|
DefaultDepth(dpy, screen));
|
|
|
|
XSync(dpy, False);
|
2006-02-10 20:32:35 +03:00
|
|
|
draw_bar();
|
2006-04-03 00:53:56 +04:00
|
|
|
for(i = 0; i < view.size; i++) {
|
|
|
|
for(j = 1; j < view.data[i]->area.size; j++) {
|
|
|
|
Area *a = view.data[i]->area.data[j];
|
2006-03-11 23:48:02 +03:00
|
|
|
a->rect.height = rect.height - brect.height;
|
2006-04-06 19:03:12 +04:00
|
|
|
arrange_column(a, False);
|
2006-02-19 17:40:44 +03:00
|
|
|
}
|
2006-04-03 00:53:56 +04:00
|
|
|
for(j = 0; j < view.data[i]->area.data[0]->frame.size; j++) {
|
|
|
|
Frame *f = view.data[i]->area.data[0]->frame.data[j];
|
2006-03-15 18:00:39 +03:00
|
|
|
resize_client(f->client, &f->rect, False);
|
2006-03-11 23:48:02 +03:00
|
|
|
}
|
|
|
|
}
|
2006-02-10 20:32:35 +03:00
|
|
|
}
|
|
|
|
|
2006-02-10 00:48:01 +03:00
|
|
|
void
|
|
|
|
draw_bar()
|
|
|
|
{
|
2006-03-26 20:21:12 +04:00
|
|
|
unsigned int i = 0, w = 0;
|
2006-03-27 09:17:47 +04:00
|
|
|
int exp = -1;
|
2006-04-23 22:00:47 +04:00
|
|
|
BlitzDraw d = { 0 };
|
2006-05-01 22:53:30 +04:00
|
|
|
Bar *b = nil;
|
2006-02-10 00:48:01 +03:00
|
|
|
|
2006-03-23 01:49:18 +03:00
|
|
|
d.gc = bargc;
|
|
|
|
d.drawable = barpmap;
|
|
|
|
d.rect = brect;
|
2006-03-23 22:48:26 +03:00
|
|
|
d.rect.x = d.rect.y = 0;
|
2006-04-23 22:00:47 +04:00
|
|
|
d.font = blitzfont;
|
2006-02-10 00:48:01 +03:00
|
|
|
|
2006-03-23 22:48:26 +03:00
|
|
|
d.color = def.norm;
|
|
|
|
blitz_drawlabel(dpy, &d);
|
|
|
|
blitz_drawborder(dpy, &d);
|
2006-03-24 15:36:35 +03:00
|
|
|
|
2006-04-13 18:52:33 +04:00
|
|
|
if(!bar.size)
|
2006-03-24 15:36:35 +03:00
|
|
|
return;
|
2006-03-23 22:48:26 +03:00
|
|
|
|
2006-04-13 18:52:33 +04:00
|
|
|
for(i = 0; (i < bar.size) && (w < brect.width); i++) {
|
2006-05-01 22:53:30 +04:00
|
|
|
b = bar.data[i];
|
|
|
|
if(b->intern) {
|
|
|
|
if(view.size && !strncmp(b->name, view.data[sel]->name, sizeof(b->name)))
|
2006-05-19 22:14:06 +04:00
|
|
|
b->color = def.sel;
|
2006-03-26 18:37:03 +04:00
|
|
|
else
|
2006-05-01 22:53:30 +04:00
|
|
|
b->color = def.norm;
|
2006-03-26 18:37:03 +04:00
|
|
|
}
|
2006-05-01 22:53:30 +04:00
|
|
|
b->rect.x = 0;
|
|
|
|
b->rect.y = 0;
|
|
|
|
b->rect.width = brect.height;
|
|
|
|
if(strlen(b->data))
|
|
|
|
b->rect.width += blitz_textwidth(dpy, &blitzfont, b->data);
|
|
|
|
b->rect.height = brect.height;
|
|
|
|
w += b->rect.width;
|
2006-03-24 15:36:35 +03:00
|
|
|
}
|
2006-02-10 00:48:01 +03:00
|
|
|
|
2006-04-13 18:52:33 +04:00
|
|
|
if(i != bar.size) { /* give all bars same width */
|
|
|
|
w = brect.width / bar.size;
|
|
|
|
for(i = 0; i < bar.size; i++) {
|
2006-05-01 22:53:30 +04:00
|
|
|
b = bar.data[i];
|
|
|
|
b->rect.x = i * w;
|
|
|
|
b->rect.width = w;
|
2006-02-10 00:48:01 +03:00
|
|
|
}
|
2006-03-24 15:36:35 +03:00
|
|
|
}
|
2006-04-13 18:52:33 +04:00
|
|
|
else { /* expand bar properly */
|
|
|
|
for(exp = 0; (exp < bar.size) && (bar.data[exp]->intern); exp++);
|
|
|
|
if(exp == bar.size)
|
2006-03-26 20:21:12 +04:00
|
|
|
exp = -1;
|
|
|
|
else
|
2006-04-13 18:52:33 +04:00
|
|
|
bar.data[exp]->rect.width += (brect.width - w);
|
|
|
|
for(i = 1; i < bar.size; i++)
|
|
|
|
bar.data[i]->rect.x = bar.data[i - 1]->rect.x + bar.data[i - 1]->rect.width;
|
2006-03-26 20:21:12 +04:00
|
|
|
}
|
2006-02-10 00:48:01 +03:00
|
|
|
|
2006-04-13 18:52:33 +04:00
|
|
|
for(i = 0; i < bar.size; i++) {
|
2006-05-01 22:53:30 +04:00
|
|
|
b = bar.data[i];
|
|
|
|
d.color = b->color;
|
|
|
|
d.rect = b->rect;
|
|
|
|
d.data = b->data;
|
2006-03-26 20:21:12 +04:00
|
|
|
if(i == exp)
|
2006-03-26 18:37:03 +04:00
|
|
|
d.align = EAST;
|
2006-03-26 20:21:12 +04:00
|
|
|
else
|
|
|
|
d.align = CENTER;
|
2006-03-24 15:36:35 +03:00
|
|
|
blitz_drawlabel(dpy, &d);
|
|
|
|
blitz_drawborder(dpy, &d);
|
2006-02-10 00:48:01 +03:00
|
|
|
}
|
2006-03-23 01:49:18 +03:00
|
|
|
XCopyArea(dpy, barpmap, barwin, bargc, 0, 0, brect.width, brect.height, 0, 0);
|
|
|
|
XSync(dpy, False);
|
2006-02-10 00:48:01 +03:00
|
|
|
}
|
|
|
|
|
2006-03-09 04:15:43 +03:00
|
|
|
int
|
2006-05-01 22:53:30 +04:00
|
|
|
idx_of_bar(Bar *b)
|
2006-03-09 04:15:43 +03:00
|
|
|
{
|
|
|
|
int i;
|
2006-04-13 18:52:33 +04:00
|
|
|
for(i = 0; i < bar.size; i++)
|
2006-05-01 22:53:30 +04:00
|
|
|
if(bar.data[i] == b)
|
2006-03-09 04:15:43 +03:00
|
|
|
return i;
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
2006-02-10 00:48:01 +03:00
|
|
|
int
|
2006-04-12 12:44:07 +04:00
|
|
|
idx_of_bar_id(unsigned short id)
|
2006-02-10 00:48:01 +03:00
|
|
|
{
|
|
|
|
int i;
|
2006-04-13 18:52:33 +04:00
|
|
|
for(i = 0; i < bar.size; i++)
|
|
|
|
if(bar.data[i]->id == id)
|
2006-02-10 00:48:01 +03:00
|
|
|
return i;
|
|
|
|
return -1;
|
|
|
|
}
|
2006-03-09 04:15:43 +03:00
|
|
|
|
2006-04-12 12:44:07 +04:00
|
|
|
Bar *
|
|
|
|
bar_of_name(const char *name)
|
2006-03-09 04:15:43 +03:00
|
|
|
{
|
2006-03-31 09:57:33 +04:00
|
|
|
static char buf[256];
|
2006-03-09 04:15:43 +03:00
|
|
|
unsigned int i;
|
|
|
|
|
2006-03-23 18:12:06 +03:00
|
|
|
cext_strlcpy(buf, name, sizeof(buf));
|
2006-04-13 18:52:33 +04:00
|
|
|
for(i = 0; i < bar.size; i++)
|
|
|
|
if(!strncmp(bar.data[i]->name, name, sizeof(bar.data[i]->name)))
|
|
|
|
return bar.data[i];
|
2006-03-09 04:15:43 +03:00
|
|
|
return nil;
|
|
|
|
}
|
2006-03-24 15:36:35 +03:00
|
|
|
|
2006-05-02 01:49:05 +04:00
|
|
|
static Bar *
|
|
|
|
next_unused_bar()
|
|
|
|
{
|
|
|
|
unsigned int i;
|
|
|
|
for(i = 0; (i < bar.size) && bar.data[i]->intern; i++)
|
|
|
|
if(!view_of_name(bar.data[i]->name))
|
|
|
|
return bar.data[i];
|
|
|
|
return nil;
|
|
|
|
}
|
|
|
|
|
2006-03-24 15:36:35 +03:00
|
|
|
void
|
2006-04-12 12:44:07 +04:00
|
|
|
update_view_bars()
|
2006-03-24 15:36:35 +03:00
|
|
|
{
|
|
|
|
unsigned int i;
|
2006-05-01 22:53:30 +04:00
|
|
|
Bar *b = nil;
|
2006-03-24 15:36:35 +03:00
|
|
|
|
2006-05-02 01:49:05 +04:00
|
|
|
while((b = next_unused_bar()))
|
|
|
|
destroy_bar(b);
|
2006-04-10 19:43:13 +04:00
|
|
|
for(i = 0; i < view.size; i++) {
|
2006-05-01 22:53:30 +04:00
|
|
|
b = create_bar(view.data[i]->name, True);
|
|
|
|
cext_strlcpy(b->data, view.data[i]->name, sizeof(b->data));
|
2006-03-24 15:36:35 +03:00
|
|
|
}
|
2006-03-31 09:57:33 +04:00
|
|
|
|
2006-03-24 15:36:35 +03:00
|
|
|
draw_bar();
|
|
|
|
}
|