fixed match() to prefer prefix-matches to strstr-matches in the match list, extended the -y handling, next version is 3.6 745c46d8
Anselm R Garbe · 2008-03-18 16:52 3 file(s) · +46 −30
config.mk +1 −1
1 1
# dmenu version
2 -
VERSION = 3.5
2 +
VERSION = 3.6
3 3
4 4
# Customize below to fit your system
5 5
dmenu.1 +3 −1
26 26
defines the x coordinate dmenu appears at (0 by default).
27 27
.TP
28 28
.B \-y
29 -
defines the y coordinate dmenu appears at (0 by default).
29 +
defines the y coordinate dmenu appears at (0 by default). If it is negative,
30 +
dmenu will appear with the bottom at the given positive coordinate. It it is
31 +
-0, dmenu appears at the screen bottom.
30 32
.TP
31 33
.B \-w
32 34
defines the width of the dmenu window (screen width by default).
dmenu.c +42 −28
34 34
35 35
typedef struct Item Item;
36 36
struct Item {
37 +
	char *text;
38 +
	Bool matched;
37 39
	Item *next;		/* traverses all items */
38 40
	Item *left, *right;	/* traverses items matching current search pattern */
39 -
	char *text;
40 41
};
41 42
42 43
/* forward declarations */
43 44
Item *appenditem(Item *i, Item *last);
44 45
void calcoffsets(void);
46 +
char *cistrstr(const char *s, const char *sub);
45 47
void cleanup(void);
46 48
void drawmenu(void);
47 49
void drawtext(const char *text, unsigned long col[ColLast]);
56 58
void readstdin(void);
57 59
void run(void);
58 60
void setup(int x, int y, int w);
59 -
char *cistrstr(const char *s, const char *sub);
60 61
unsigned int textnw(const char *text, unsigned int len);
61 62
unsigned int textw(const char *text);
62 63
128 129
		if(w > mw)
129 130
			break;
130 131
	}
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;
131 155
}
132 156
133 157
void
505 529
	item = j = NULL;
506 530
	nitem = 0;
507 531
	for(i = allitems; i; i = i->next)
508 -
		if(!fstrncmp(pattern, i->text, plen)
509 -
				|| fstrstr(i->text, pattern))
532 +
		if((i->matched = !fstrncmp(pattern, i->text, plen)))
533 +
			j = appenditem(i, j);
534 +
	for(i = allitems; i; i = i->next)
535 +
		if(!i->matched && fstrstr(i->text, pattern))
510 536
			j = appenditem(i, j);
511 537
	curr = prev = next = sel = item;
512 538
	calcoffsets();
587 613
	wa.event_mask = ExposureMask | ButtonPressMask | KeyPressMask;
588 614
	mw = w ? w : DisplayWidth(dpy, screen);
589 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 622
	win = XCreateWindow(dpy, root, x, y, mw, mh, 0,
591 623
			DefaultDepth(dpy, screen), CopyFromParent,
592 624
			DefaultVisual(dpy, screen),
611 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 646
unsigned int
638 647
textnw(const char *text, unsigned int len) {
639 648
	XRectangle r;
683 692
			if(++i < argc) x = atoi(argv[i]);
684 693
		}
685 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 702
		else if(!strcmp(argv[i], "-w")) {
689 703
			if(++i < argc) w = atoi(argv[i]);