diff options
Diffstat (limited to 'dmenu.c')
-rw-r--r-- | dmenu.c | 70 |
1 files changed, 42 insertions, 28 deletions
@@ -34,14 +34,16 @@ typedef struct { | |||
34 | 34 | ||
35 | typedef struct Item Item; | 35 | typedef struct Item Item; |
36 | struct Item { | 36 | struct Item { |
37 | char *text; | ||
38 | Bool matched; | ||
37 | Item *next; /* traverses all items */ | 39 | Item *next; /* traverses all items */ |
38 | Item *left, *right; /* traverses items matching current search pattern */ | 40 | Item *left, *right; /* traverses items matching current search pattern */ |
39 | char *text; | ||
40 | }; | 41 | }; |
41 | 42 | ||
42 | /* forward declarations */ | 43 | /* forward declarations */ |
43 | Item *appenditem(Item *i, Item *last); | 44 | Item *appenditem(Item *i, Item *last); |
44 | void calcoffsets(void); | 45 | void calcoffsets(void); |
46 | char *cistrstr(const char *s, const char *sub); | ||
45 | void cleanup(void); | 47 | void cleanup(void); |
46 | void drawmenu(void); | 48 | void drawmenu(void); |
47 | void drawtext(const char *text, unsigned long col[ColLast]); | 49 | void drawtext(const char *text, unsigned long col[ColLast]); |
@@ -56,7 +58,6 @@ void match(char *pattern); | |||
56 | void readstdin(void); | 58 | void readstdin(void); |
57 | void run(void); | 59 | void run(void); |
58 | void setup(int x, int y, int w); | 60 | void setup(int x, int y, int w); |
59 | char *cistrstr(const char *s, const char *sub); | ||
60 | unsigned int textnw(const char *text, unsigned int len); | 61 | unsigned int textnw(const char *text, unsigned int len); |
61 | unsigned int textw(const char *text); | 62 | unsigned int textw(const char *text); |
62 | 63 | ||
@@ -130,6 +131,29 @@ calcoffsets(void) { | |||
130 | } | 131 | } |
131 | } | 132 | } |
132 | 133 | ||
134 | char * | ||
135 | cistrstr(const char *s, const char *sub) { | ||
136 | int c, csub; | ||
137 | unsigned int len; | ||
138 | |||
139 | if(!sub) | ||
140 | return (char *)s; | ||
141 | if((c = *sub++) != 0) { | ||
142 | c = tolower(c); | ||
143 | len = strlen(sub); | ||
144 | do { | ||
145 | do { | ||
146 | if((csub = *s++) == 0) | ||
147 | return (NULL); | ||
148 | } | ||
149 | while(tolower(csub) != c); | ||
150 | } | ||
151 | while(strncasecmp(s, sub, len) != 0); | ||
152 | s--; | ||
153 | } | ||
154 | return (char *)s; | ||
155 | } | ||
156 | |||
133 | void | 157 | void |
134 | cleanup(void) { | 158 | cleanup(void) { |
135 | Item *itm; | 159 | Item *itm; |
@@ -505,8 +529,10 @@ match(char *pattern) { | |||
505 | item = j = NULL; | 529 | item = j = NULL; |
506 | nitem = 0; | 530 | nitem = 0; |
507 | for(i = allitems; i; i = i->next) | 531 | for(i = allitems; i; i = i->next) |
508 | if(!fstrncmp(pattern, i->text, plen) | 532 | if((i->matched = !fstrncmp(pattern, i->text, plen))) |
509 | || fstrstr(i->text, pattern)) | 533 | j = appenditem(i, j); |
534 | for(i = allitems; i; i = i->next) | ||
535 | if(!i->matched && fstrstr(i->text, pattern)) | ||
510 | j = appenditem(i, j); | 536 | j = appenditem(i, j); |
511 | curr = prev = next = sel = item; | 537 | curr = prev = next = sel = item; |
512 | calcoffsets(); | 538 | calcoffsets(); |
@@ -587,6 +613,12 @@ setup(int x, int y, int w) { | |||
587 | wa.event_mask = ExposureMask | ButtonPressMask | KeyPressMask; | 613 | wa.event_mask = ExposureMask | ButtonPressMask | KeyPressMask; |
588 | mw = w ? w : DisplayWidth(dpy, screen); | 614 | mw = w ? w : DisplayWidth(dpy, screen); |
589 | mh = dc.font.height + 2; | 615 | mh = dc.font.height + 2; |
616 | if(y < 0) { | ||
617 | if(y == (int)(unsigned int)-1) | ||
618 | y = DisplayHeight(dpy, screen) - mh; | ||
619 | else | ||
620 | y = (-1 * y) - mh; | ||
621 | } | ||
590 | win = XCreateWindow(dpy, root, x, y, mw, mh, 0, | 622 | win = XCreateWindow(dpy, root, x, y, mw, mh, 0, |
591 | DefaultDepth(dpy, screen), CopyFromParent, | 623 | DefaultDepth(dpy, screen), CopyFromParent, |
592 | DefaultVisual(dpy, screen), | 624 | DefaultVisual(dpy, screen), |
@@ -611,29 +643,6 @@ setup(int x, int y, int w) { | |||
611 | XMapRaised(dpy, win); | 643 | XMapRaised(dpy, win); |
612 | } | 644 | } |
613 | 645 | ||
614 | char * | ||
615 | cistrstr(const char *s, const char *sub) { | ||
616 | int c, csub; | ||
617 | unsigned int len; | ||
618 | |||
619 | if(!sub) | ||
620 | return (char *)s; | ||
621 | if((c = *sub++) != 0) { | ||
622 | c = tolower(c); | ||
623 | len = strlen(sub); | ||
624 | do { | ||
625 | do { | ||
626 | if((csub = *s++) == 0) | ||
627 | return (NULL); | ||
628 | } | ||
629 | while(tolower(csub) != c); | ||
630 | } | ||
631 | while(strncasecmp(s, sub, len) != 0); | ||
632 | s--; | ||
633 | } | ||
634 | return (char *)s; | ||
635 | } | ||
636 | |||
637 | unsigned int | 646 | unsigned int |
638 | textnw(const char *text, unsigned int len) { | 647 | textnw(const char *text, unsigned int len) { |
639 | XRectangle r; | 648 | XRectangle r; |
@@ -683,7 +692,12 @@ main(int argc, char *argv[]) { | |||
683 | if(++i < argc) x = atoi(argv[i]); | 692 | if(++i < argc) x = atoi(argv[i]); |
684 | } | 693 | } |
685 | else if(!strcmp(argv[i], "-y")) { | 694 | else if(!strcmp(argv[i], "-y")) { |
686 | if(++i < argc) y = atoi(argv[i]); | 695 | if(++i < argc) { |
696 | if(!strcmp(argv[i], "-0")) | ||
697 | y = (int)(unsigned int)-1; | ||
698 | else | ||
699 | y = atoi(argv[i]); | ||
700 | } | ||
687 | } | 701 | } |
688 | else if(!strcmp(argv[i], "-w")) { | 702 | else if(!strcmp(argv[i], "-w")) { |
689 | if(++i < argc) w = atoi(argv[i]); | 703 | if(++i < argc) w = atoi(argv[i]); |