aboutsummaryrefslogtreecommitdiff
path: root/dmenu.c
diff options
context:
space:
mode:
Diffstat (limited to 'dmenu.c')
-rw-r--r--dmenu.c44
1 files changed, 19 insertions, 25 deletions
diff --git a/dmenu.c b/dmenu.c
index a1d0ed2..fa37f49 100644
--- a/dmenu.c
+++ b/dmenu.c
@@ -30,7 +30,7 @@ static char *cistrstr(const char *s, const char *sub);
30static void drawmenu(void); 30static void drawmenu(void);
31static void grabkeyboard(void); 31static void grabkeyboard(void);
32static void insert(const char *s, ssize_t n); 32static void insert(const char *s, ssize_t n);
33static void keypress(XKeyEvent *e); 33static void keypress(XKeyEvent *ev);
34static void match(void); 34static void match(void);
35static void paste(void); 35static void paste(void);
36static void readstdin(void); 36static void readstdin(void);
@@ -73,8 +73,7 @@ appenditem(Item *item, Item **list, Item **last) {
73} 73}
74 74
75void 75void
76calcoffsets(void) 76calcoffsets(void) {
77{
78 unsigned int h, i, n; 77 unsigned int h, i, n;
79 78
80 h = dc->font.height+2; 79 h = dc->font.height+2;
@@ -104,26 +103,24 @@ cistrstr(const char *s, const char *sub) {
104 103
105void 104void
106drawmenu(void) { 105drawmenu(void) {
106 int curpos;
107 Item *item; 107 Item *item;
108 108
109 dc->x = 0; 109 dc->x = 0;
110 dc->y = 0; 110 dc->y = 0;
111 drawrect(dc, 0, 0, mw, mh, BG(dc, normcol)); 111 drawrect(dc, 0, 0, mw, mh, BG(dc, normcol));
112
113 dc->h = dc->font.height + 2; 112 dc->h = dc->font.height + 2;
114 dc->y = topbar ? 0 : mh - dc->h; 113 dc->y = topbar ? 0 : mh - dc->h;
115 /* print prompt? */ 114
116 if(prompt) { 115 if(prompt) {
117 dc->w = promptw; 116 dc->w = promptw;
118 drawtext(dc, prompt, selcol); 117 drawtext(dc, prompt, selcol);
119 dc->x = dc->w; 118 dc->x = dc->w;
120 } 119 }
121 dc->w = mw - dc->x; 120 dc->w = (lines > 0 || !matches) ? mw - dc->x : inputw;
122 /* print input field */
123 if(matches && lines == 0 && textw(dc, text) <= inputw)
124 dc->w = inputw;
125 drawtext(dc, text, normcol); 121 drawtext(dc, text, normcol);
126 drawrect(dc, textnw(dc, text, cursor) + dc->h/2 - 2, 2, 1, dc->h - 4, FG(dc, normcol)); 122 if((curpos = textnw(dc, text, cursor) + dc->h/2 - 2) < dc->w)
123 drawrect(dc, curpos, 2, 1, dc->h - 4, FG(dc, normcol));
127 124
128 if(lines > 0) { 125 if(lines > 0) {
129 dc->y = topbar ? dc->h : 0; 126 dc->y = topbar ? dc->h : 0;
@@ -133,7 +130,7 @@ drawmenu(void) {
133 dc->y += dc->h; 130 dc->y += dc->h;
134 } 131 }
135 } 132 }
136 else if(curr && (dc->w == inputw || curr->next)) { 133 else if(matches) {
137 dc->x += inputw; 134 dc->x += inputw;
138 dc->w = textw(dc, "<"); 135 dc->w = textw(dc, "<");
139 if(curr->left) 136 if(curr->left)
@@ -173,15 +170,15 @@ insert(const char *s, ssize_t n) {
173} 170}
174 171
175void 172void
176keypress(XKeyEvent *e) { 173keypress(XKeyEvent *ev) {
177 char buf[sizeof text]; 174 char buf[32];
178 int n; 175 int n;
179 size_t len; 176 size_t len;
180 KeySym ksym; 177 KeySym ksym;
181 178
182 len = strlen(text); 179 len = strlen(text);
183 XLookupString(e, buf, sizeof buf, &ksym, NULL); 180 XLookupString(ev, buf, sizeof buf, &ksym, NULL);
184 if(e->state & ControlMask) { 181 if(ev->state & ControlMask) {
185 switch(tolower(ksym)) { 182 switch(tolower(ksym)) {
186 default: 183 default:
187 return; 184 return;
@@ -235,7 +232,6 @@ keypress(XKeyEvent *e) {
235 break; 232 break;
236 case XK_y: /* paste selection */ 233 case XK_y: /* paste selection */
237 XConvertSelection(dc->dpy, XA_PRIMARY, utf8, None, win, CurrentTime); 234 XConvertSelection(dc->dpy, XA_PRIMARY, utf8, None, win, CurrentTime);
238 /* causes SelectionNotify event */
239 return; 235 return;
240 } 236 }
241 } 237 }
@@ -289,8 +285,7 @@ keypress(XKeyEvent *e) {
289 case XK_Up: 285 case XK_Up:
290 if(!sel || !sel->left) 286 if(!sel || !sel->left)
291 return; 287 return;
292 sel = sel->left; 288 if((sel = sel->left)->right == curr) {
293 if(sel->right == curr) {
294 curr = prev; 289 curr = prev;
295 calcoffsets(); 290 calcoffsets();
296 } 291 }
@@ -309,7 +304,7 @@ keypress(XKeyEvent *e) {
309 break; 304 break;
310 case XK_Return: 305 case XK_Return:
311 case XK_KP_Enter: 306 case XK_KP_Enter:
312 fputs((sel && !(e->state & ShiftMask)) ? sel->text : text, stdout); 307 fputs((sel && !(ev->state & ShiftMask)) ? sel->text : text, stdout);
313 fflush(stdout); 308 fflush(stdout);
314 exit(EXIT_SUCCESS); 309 exit(EXIT_SUCCESS);
315 case XK_Right: 310 case XK_Right:
@@ -322,8 +317,7 @@ keypress(XKeyEvent *e) {
322 case XK_Down: 317 case XK_Down:
323 if(!sel || !sel->right) 318 if(!sel || !sel->right)
324 return; 319 return;
325 sel = sel->right; 320 if((sel = sel->right) == next) {
326 if(sel == next) {
327 curr = next; 321 curr = next;
328 calcoffsets(); 322 calcoffsets();
329 } 323 }
@@ -404,7 +398,7 @@ readstdin(void) {
404 if(!(new = malloc(sizeof *new))) 398 if(!(new = malloc(sizeof *new)))
405 eprintf("cannot malloc %u bytes\n", sizeof *new); 399 eprintf("cannot malloc %u bytes\n", sizeof *new);
406 if(!(new->text = strdup(buf))) 400 if(!(new->text = strdup(buf)))
407 eprintf("cannot strdup %u bytes\n", strlen(buf)); 401 eprintf("cannot strdup %u bytes\n", strlen(buf)+1);
408 inputw = MAX(inputw, textw(dc, new->text)); 402 inputw = MAX(inputw, textw(dc, new->text));
409 new->next = new->left = new->right = NULL; 403 new->next = new->left = new->right = NULL;
410 if(item) 404 if(item)
@@ -485,9 +479,9 @@ setup(void) {
485 wa.background_pixmap = ParentRelative; 479 wa.background_pixmap = ParentRelative;
486 wa.event_mask = ExposureMask | KeyPressMask | VisibilityChangeMask; 480 wa.event_mask = ExposureMask | KeyPressMask | VisibilityChangeMask;
487 win = XCreateWindow(dc->dpy, root, x, y, mw, mh, 0, 481 win = XCreateWindow(dc->dpy, root, x, y, mw, mh, 0,
488 DefaultDepth(dc->dpy, screen), CopyFromParent, 482 DefaultDepth(dc->dpy, screen), CopyFromParent,
489 DefaultVisual(dc->dpy, screen), 483 DefaultVisual(dc->dpy, screen),
490 CWOverrideRedirect | CWBackPixmap | CWEventMask, &wa); 484 CWOverrideRedirect | CWBackPixmap | CWEventMask, &wa);
491 485
492 grabkeyboard(); 486 grabkeyboard();
493 setcanvas(dc, mw, mh); 487 setcanvas(dc, mw, mh);