added /tags namespace, added .../tags files to client namespace, added tag display in draw_client

This commit is contained in:
Anselm R. Garbe 2006-03-05 19:20:27 +01:00
parent dcc6e16302
commit 7e8ab56d91
6 changed files with 155 additions and 55 deletions

View File

@ -126,10 +126,16 @@ attach_toarea(Area *a, Client *c)
a->frame = (Frame **)cext_array_attach(
(void **)a->frame, f, sizeof(Frame *), &a->framesz);
a->nframe++;
if(!strstr(c->tags, a->tag->name)) {
if(c->tags[0] != 0)
cext_strlcat(c->tags, " ", sizeof(c->tags));
cext_strlcat(c->tags, a->tag->name, sizeof(c->tags));
}
if(area2index(a)) /* column */
arrange_area(a);
else /* floating */
resize_client(c, &f->rect, nil, False);
update_ctags();
}
void

View File

@ -236,6 +236,7 @@ void
draw_client(Client *c)
{
Draw d = { 0 };
char buf[512];
d.align = WEST;
d.drawable = c->framewin;
@ -259,7 +260,8 @@ draw_client(Client *c)
d.rect.width = c->frame->rect.width;
d.rect.height = bar_height();
d.notch = nil;
d.data = c->name;
snprintf(buf, sizeof(buf), "%s | %s", c->tags, c->name);
d.data = buf;
blitz_drawlabel(dpy, &d);
XSync(dpy, False);
}
@ -341,7 +343,7 @@ attach_client(Client *c)
{
Tag *t;
if(!ntag)
t = alloc_tag();
t = alloc_tag("new");
else
t = tag[sel];
@ -520,7 +522,7 @@ sendtotag_client(Client *c, char *arg)
Client *to;
if(!strncmp(arg, "new", 4))
t = alloc_tag();
t = alloc_tag("new");
else if(!strncmp(arg, "sel", 4))
t = tag[sel];
else {

View File

@ -37,39 +37,41 @@ static char Enocommand[] = "command not supported";
* /def/snap FsFsnap 0..n
* /def/font FsFfont xlib font name
* /def/selcolors FsFselcolors sel color
* /def/normcolors FsFnormcolors normal colors
* /def/normcolors FsFnormcolors normal colors
* /keys/ FsDkeys
* /keys/foo FsFkey
* /tags/ FsDtags
* /tags/foo FsFtag
* /bar/ FsDbar
* /bar/expand FsFexpand id of expandable label
* /bar/expand FsFexpand id of expandable label
* /bar/new/ FsDlabel
* /bar/1/ FsDlabel
* /bar/1/data FsFdata <arbitrary data which gets displayed>
* /bar/1/data FsFdata <arbitrary data which gets displayed>
* /bar/1/colors FsFcolors <#RRGGBB> <#RRGGBB> <#RRGGBB>
* /event FsFevent
* /ctl FsFctl command interface (root)
* /ws/ FsDws returns new tag
* /ws/ FsDws tag
* /ws/ctl FsFctl command interface (tag)
* /ctl FsFctl command interface (root)
* /ws/ FsDws returns new tag
* /ws/ FsDws tag
* /ws/ctl FsFctl command interface (tag)
* /ws/sel/ FsDarea
* /ws/float/ FsDarea floating clients in area 0
* /ws/float/ctl FsFctl command interface (area)
* /ws/float/mode FsFmode col mode
* /ws/float/ FsDarea floating clients in area 0
* /ws/float/ctl FsFctl command interface (area)
* /ws/float/mode FsFmode col mode
* /ws/float/sel/ FsDclient
* /ws/float/1/ FsDclient
* /ws/float/1/name FsFname name of client
* /ws/float/1/tag FsFtag tag of client
* /ws/float/1/geom FsFgeom geometry of client
* /ws/float/1/ctl FsFctl command interface (client)
* /ws/float/1/name FsFname name of client
* /ws/float/1/tags FsFtags tags of client
* /ws/float/1/geom FsFgeom geometry of client
* /ws/float/1/ctl FsFctl command interface (client)
* /ws/1/ FsDarea
* /ws/1/ctl FsFctl command interface (area)
* /ws/1/mode FsFmode col mode
* /ws/1/ctl FsFctl command interface (area)
* /ws/1/mode FsFmode col mode
* /ws/1/1/sel/ FsDclient
* /ws/1/1/1/ FsDclient
* /ws/1/1/name FsFname name of client
* /ws/1/1/tag FsFtag tag of client
* /ws/1/1/geom FsFgeom geometry of client
* /ws/1/1/ctl FsFctl command interface (client)
* /ws/1/1/name FsFname name of client
* /ws/1/1/tags FsFtags tag of client
* /ws/1/1/geom FsFgeom geometry of client
* /ws/1/1/ctl FsFctl command interface (client)
*/
Qid root_qid;
@ -152,6 +154,7 @@ qid2name(Qid *qid)
case FsDroot: return "/"; break;
case FsDdef: return "def"; break;
case FsDkeys: return "keys"; break;
case FsDtags: return "tags"; break;
case FsDbar: return "bar"; break;
case FsDws:
if(i1 == -1)
@ -216,10 +219,10 @@ qid2name(Qid *qid)
return nil;
return "name";
break;
case FsFtag:
case FsFtags:
if(i1 == -1 || i2 == -1 || i3 == -1)
return nil;
return "tag";
return "tags";
break;
case FsFmode:
if(i1 == -1 || i2 == -1)
@ -248,6 +251,12 @@ name2type(char *name, unsigned char dir_type)
case FsDbar: return FsDlabel; break;
}
}
if(!strncmp(name, "tags", 5)) {
switch(dir_type) {
case FsDroot: return FsDtags; break;
case FsDclient: return FsFtags; break;
}
}
if(!strncmp(name, "bar", 4))
return FsDbar;
if(!strncmp(name, "def", 4))
@ -262,8 +271,6 @@ name2type(char *name, unsigned char dir_type)
return FsFsnap;
if(!strncmp(name, "name", 5))
return FsFname;
if(!strncmp(name, "tag", 4))
return FsFtag;
if(!strncmp(name, "border", 7))
return FsFborder;
if(!strncmp(name, "geom", 5))
@ -284,6 +291,8 @@ name2type(char *name, unsigned char dir_type)
return FsFmode;
if(name2key(name))
return FsFkey;
if(has_ctag(name))
return FsFtags;
if(!strncmp(name, "sel", 4))
goto dyndir;
i = (unsigned short) cext_strtonum(name, 0, 0xffff, &err);
@ -317,16 +326,11 @@ mkqid(Qid *dir, char *wname, Qid *new, Bool iswalk)
*new = root_qid;
break;
case FsDdef:
new->type = IXP_QTDIR;
new->path = mkqpath(FsDdef, 0, 0, 0);
break;
case FsDkeys:
new->type = IXP_QTDIR;
new->path = mkqpath(FsDkeys, 0, 0, 0);
break;
case FsDtags:
case FsDbar:
new->type = IXP_QTDIR;
new->path = mkqpath(FsDbar, 0, 0, 0);
new->path = mkqpath(type, 0, 0, 0);
break;
case FsDlabel:
new->type = IXP_QTDIR;
@ -347,7 +351,7 @@ mkqid(Qid *dir, char *wname, Qid *new, Bool iswalk)
new->type = IXP_QTDIR;
if(!strncmp(wname, "new", 4)) {
if(iswalk) {
Tag *p = alloc_tag();
Tag *p = alloc_tag(wname);
new->path = mkqpath(FsDws, p->id, 0, 0);
}
else
@ -426,7 +430,7 @@ mkqid(Qid *dir, char *wname, Qid *new, Bool iswalk)
break;
case FsFgeom:
case FsFname:
case FsFtag:
case FsFtags:
if(dir_i1 == -1 || dir_i2 == -1 || dir_i3 == -1)
return -1;
new->type = IXP_QTFILE;
@ -581,6 +585,7 @@ type2stat(Stat *stat, char *wname, Qid *dir)
case FsDws:
case FsDdef:
case FsDkeys:
case FsDtags:
case FsDbar:
case FsDlabel:
case FsDroot:
@ -608,9 +613,16 @@ type2stat(Stat *stat, char *wname, Qid *dir)
f = tag[dir_i1]->area[dir_i2]->frame[dir_i3];
return mkstat(stat, dir, wname, strlen(f->client->name), DMREAD);
break;
case FsFtag:
f = tag[dir_i1]->area[dir_i2]->frame[dir_i3];
return mkstat(stat, dir, wname, strlen(f->client->tag), DMREAD | DMWRITE);
case FsFtags:
switch(dir_type) {
case FsDclient:
f = tag[dir_i1]->area[dir_i2]->frame[dir_i3];
return mkstat(stat, dir, wname, strlen(f->client->tags), DMREAD | DMWRITE);
break;
case FsDtags:
return mkstat(stat, dir, wname, 0, 0);
break;
}
break;
case FsFkey:
return mkstat(stat, dir, wname, 0, DMWRITE);
@ -712,6 +724,7 @@ xread(IXPConn *c, Fcall *fcall)
len += type2stat(&stat, "def", &m->qid);
len += type2stat(&stat, "keys", &m->qid);
len += type2stat(&stat, "bar", &m->qid);
len += type2stat(&stat, "tags", &m->qid);
len += type2stat(&stat, "new", &m->qid);
for(i = 0; i < ntag; i++) {
if(i == sel)
@ -754,6 +767,24 @@ xread(IXPConn *c, Fcall *fcall)
p = ixp_enc_stat(p, &stat);
}
break;
case FsDtags:
/* jump to offset */
len = 0;
for(i = 0; i < nctag; i++) {
len += type2stat(&stat, ctag[i], &m->qid);
if(len <= fcall->offset)
continue;
break;
}
/* offset found, proceeding */
for(; i < nctag; i++) {
len = type2stat(&stat, ctag[i], &m->qid);
if(fcall->count + len > fcall->iounit)
break;
fcall->count += len;
p = ixp_enc_stat(p, &stat);
}
break;
case FsDbar:
/* jump to offset */
len = type2stat(&stat, "expand", &m->qid);
@ -851,6 +882,8 @@ xread(IXPConn *c, Fcall *fcall)
p = ixp_enc_stat(p, &stat);
fcall->count += type2stat(&stat, "bar", &m->qid);
p = ixp_enc_stat(p, &stat);
fcall->count += type2stat(&stat, "tags", &m->qid);
p = ixp_enc_stat(p, &stat);
fcall->count += type2stat(&stat, "new", &m->qid);
p = ixp_enc_stat(p, &stat);
for(i = 0; i < ntag; i++) {
@ -874,6 +907,15 @@ xread(IXPConn *c, Fcall *fcall)
p = ixp_enc_stat(p, &stat);
}
break;
case FsDtags:
for(i = 0; i < nctag; i++) {
len = type2stat(&stat, ctag[i], &m->qid);
if(fcall->count + len > fcall->iounit)
break;
fcall->count += len;
p = ixp_enc_stat(p, &stat);
}
break;
case FsDbar:
fcall->count = type2stat(&stat, "expand", &m->qid);
p = ixp_enc_stat(p, &stat);
@ -944,7 +986,7 @@ xread(IXPConn *c, Fcall *fcall)
case FsDclient:
fcall->count += type2stat(&stat, "name", &m->qid);
p = ixp_enc_stat(p, &stat);
fcall->count += type2stat(&stat, "tag", &m->qid);
fcall->count += type2stat(&stat, "tags", &m->qid);
p = ixp_enc_stat(p, &stat);
fcall->count += type2stat(&stat, "geom", &m->qid);
p = ixp_enc_stat(p, &stat);
@ -980,9 +1022,9 @@ xread(IXPConn *c, Fcall *fcall)
if((fcall->count = strlen(tag[i1]->area[i2]->frame[i3]->client->name)))
memcpy(p, tag[i1]->area[i2]->frame[i3]->client->name, fcall->count);
break;
case FsFtag:
if((fcall->count = strlen(tag[i1]->area[i2]->frame[i3]->client->tag)))
memcpy(p, tag[i1]->area[i2]->frame[i3]->client->tag, fcall->count);
case FsFtags:
if((fcall->count = strlen(tag[i1]->area[i2]->frame[i3]->client->tags)))
memcpy(p, tag[i1]->area[i2]->frame[i3]->client->tags, fcall->count);
break;
case FsFexpand:
snprintf(buf, sizeof(buf), "%u", iexpand);
@ -1126,12 +1168,12 @@ xwrite(IXPConn *c, Fcall *fcall)
def.border = i;
resize_all_clients();
break;
case FsFtag:
case FsFtags:
f = tag[i1]->area[i2]->frame[i3];
if(fcall->count > sizeof(f->client->tag))
return "tag value too long";
memcpy(f->client->tag, fcall->data, fcall->count);
/* TODO: update_tags */
if(fcall->count > sizeof(f->client->tags))
return "tags value too long";
memcpy(f->client->tags, fcall->data, fcall->count);
update_ctags();
break;
case FsFgeom:
f = tag[i1]->area[i2]->frame[i3];

View File

@ -11,12 +11,13 @@
#include "wm.h"
Tag *
alloc_tag()
alloc_tag(char *name)
{
static unsigned short id = 1;
Tag *t = cext_emallocz(sizeof(Tag));
t->id = id++;
cext_strlcpy(t->name, name, sizeof(t->name));
alloc_area(t);
alloc_area(t);
tag = (Tag **)cext_array_attach((void **)tag, t, sizeof(Tag *), &tagsz);
@ -156,3 +157,45 @@ select_tag(char *arg)
if((c = sel_client_of_tag(tag[new])))
focus_client(c);
}
Bool
has_ctag(char *tag)
{
unsigned int i;
for(i = 0; i < nctag; i++)
if(!strncmp(ctag[i], tag, strlen(ctag[i])))
return True;
return False;
}
void
update_ctags()
{
unsigned int i;
char buf[256];
char *tags[128];
for(i = 0; i < nctag; i++) {
free(ctag[i]);
ctag[i] = nil;
}
nctag = 0;
for(i = 0; i < nclient; i++) {
unsigned int j, k;
cext_strlcpy(buf, client[i]->tags, sizeof(buf));
fprintf(stderr, "update_ctags: %s\n", buf);
j = cext_tokenize(tags, 128, buf, ' ');
fprintf(stderr, "update_ctags: %d\n", j);
for(k = 0; k < j; k++) {
fprintf(stderr, "update_ctags: tag=%s\n", tags[k]);
if(!has_ctag(tags[k])) {
ctag = (char **)cext_array_attach((void **)ctag, strdup(tags[k]),
sizeof(char *), &ctagsz);
nctag++;
}
}
}
for(i = 0; i < nctag; i++)
fprintf(stderr, "tag=%s\n", ctag[i]);
}

View File

@ -311,8 +311,9 @@ main(int argc, char *argv[])
ixp_server_open_conn(&srv, ConnectionNumber(dpy), check_x_event, nil);
init_x_event_handler();
ntag = nclient = tagsz = clientsz = sel = 0;
nctag = ctagsz = ntag = nclient = tagsz = clientsz = sel = 0;
tag = nil;
ctag = nil;
client = nil;
key = nil;
@ -356,8 +357,8 @@ main(int argc, char *argv[])
XMapRaised(dpy, winbar);
draw_bar();
alloc_tag(); /* tag 0 */
alloc_tag(); /* tag 1 */
alloc_tag("scratch");
alloc_tag("default");
scan_wins();
/* main event loop */

View File

@ -57,6 +57,7 @@ enum {
FsDarea,
FsDclient,
FsDkeys,
FsDtags,
FsDbar,
FsDlabel,
FsFexpand,
@ -73,7 +74,7 @@ enum {
FsFevent,
FsFctl,
FsFname,
FsFtag,
FsFtags,
FsFmode
};
@ -118,7 +119,7 @@ struct Frame {
struct Client {
char name[256];
char tag[256];
char tags[256];
int proto;
unsigned int border;
Bool destroyed;
@ -175,6 +176,9 @@ Label **label;
unsigned int nlabel;
unsigned int labelsz;
unsigned int iexpand;
char **ctag;
unsigned int nctag;
unsigned int ctagsz;
Display *dpy;
IXPServer *ixps;
@ -281,13 +285,15 @@ void ungrab_mouse(Window w, unsigned long mod, unsigned int button);
char *warp_mouse(char *arg);
/* tag.c */
Tag *alloc_tag();
Tag *alloc_tag(char *name);
char *destroy_tag(Tag *t);
void focus_tag(Tag *t);
XRectangle *rectangles(unsigned int *num);
int tid2index(unsigned short id);
void select_tag(char *arg);
int tag2index(Tag *t);
Bool has_ctag(char *tag);
void update_ctags();
/* wm.c */
void scan_wins();