diff options
author | Peter Mikkelsen <petermikkelsen10@gmail.com> | 2024-02-16 23:26:32 +0000 |
---|---|---|
committer | Peter Mikkelsen <petermikkelsen10@gmail.com> | 2024-02-16 23:26:32 +0000 |
commit | c51962a648b3f38fc378ad0081b1d1aa037142d5 (patch) | |
tree | 4cf448275064f7ddbd0ac2a429d9fe5449755102 /props.c | |
parent | ab90a480eb5233abc4d7122739c24656dd42cc94 (diff) |
Implement mouse menus
Setup a menu/some menus by writing to an elements props/menus file
Diffstat (limited to 'props.c')
-rw-r--r-- | props.c | 114 |
1 files changed, 112 insertions, 2 deletions
@@ -109,6 +109,17 @@ deftext(int gtag, int ptag) return v; } +PropVal +defmenus(int gtag, int ptag) +{ + USED(gtag); + USED(ptag); + + PropVal v; + v.menus = emalloc(sizeof(MenuSpec)); + return v; +} + char * printcolour(PropVal p) { @@ -155,6 +166,36 @@ printtext(PropVal p) } char * +printmenus(PropVal p) +{ + MenuSpec *spec = p.menus; + + char which[3] = "LMR"; + char *str = smprint(""); + for(int i = 0; i < 3; i++){ + if(spec->menus[i] == nil) + continue; + + char sep = spec->seps[i]; + char *tmp = str; + str = smprint("%s%c", tmp, which[i]); + free(tmp); + + char **items = spec->menus[i]->item; + for(int j = 0; items[j] != nil; j++){ + tmp = str; + str = smprint("%s%c%s", tmp, sep, items[j]); + free(tmp); + } + + tmp = str; + str = smprint("%s\n", tmp); + free(tmp); + } + return str; +} + +char * parsecolour(char *str, PropVal *p) { char *r; @@ -226,6 +267,74 @@ parsetext(char *str, PropVal *p) return nil; } +char * +parsemenus(char *str, PropVal *p) +{ + char *err = nil; + int n = 0; + for(int i = 0; str[i] != 0; i++) + if(str[i] == '\n') + n++; + + char **lines = emalloc(sizeof(char *) * (n+1)); + n = getfields(str, lines, n, 1, "\n"); + + p->menus = emalloc(sizeof(MenuSpec)); + MenuSpec *spec = p->menus; + for(int i = 0; i < n; i++){ + char *line = lines[i]; + if(strlen(line) == 0) + continue; + + if(strlen(line) <= 2) + return Eparse; + + int which; + switch(line[0]){ + case 'L': which = 0; break; + case 'M': which = 1; break; + case 'R': which = 2; break; + default: + err = Eparse; + goto Lend; + } + + if(spec->menus[which] == nil) + spec->menus[which] = emalloc(sizeof(Menu)); + + int count = 0; + char sep = line[1]; + spec->seps[which] = sep; + spec->menus[which]->item = emalloc(sizeof(char *)); + + char *start = line+2; + char *end; + while(*start != 0){ + count++; + spec->menus[which]->item = erealloc(spec->menus[which]->item, sizeof(char *) * count); + for(end = start; *end != 0 && *end != sep && *end != '\n'; end++); + int len = end-start; + char *buf = emalloc(len+1); + memcpy(buf, start, len); + buf[len] = 0; + + spec->menus[which]->item[count-1] = buf; + start = end; + if(*start != 0){ + do{ + start++; + }while(*start == '\n'); + } + } + spec->menus[which]->item[count] = nil; + print("count: %d\n", count); + } + +Lend: + free(lines); + return err; +} + PropVal getprop(GuiElement *g, int tag, int lock) { @@ -239,7 +348,7 @@ getprop(GuiElement *g, int tag, int lock) runlock(&g->lock); if(v == nil) - sysfatal("invalid prop for this gui element"); + sysfatal("invalid prop %d for this gui element", tag); else return *v; } @@ -268,6 +377,7 @@ PropSpec propspecs[Pmax] = { [Pbordercolour] = {"bordercolour", defcolour, printcolour, parsecolour}, [Ptext] = {"text", deftext, printtext, parsetext}, [Ptextcolour] = {"textcolour", defcolour, printcolour, parsecolour}, + [Pmenus] = {"menus", defmenus, printmenus, parsemenus}, }; -int baseprops[nbaseprops] = {Pbackground, Pborder, Pmargin, Ppadding, Pbordercolour};
\ No newline at end of file +int baseprops[nbaseprops] = {Pbackground, Pborder, Pmargin, Ppadding, Pbordercolour, Pmenus};
\ No newline at end of file |