added the -i option

Widths and x positions no more depend on item->h.
This commit is contained in:
phillbush
2020-07-15 22:57:59 -03:00
parent 92e7609bcd
commit 71b4db9241
4 changed files with 76 additions and 34 deletions

81
xmenu.c
View File

@@ -21,7 +21,7 @@
static void ealloccolor(const char *s, XftColor *color);
static void initresources(void);
static void initdc(void);
static void initscreengeom(void);
static void initconfig(void);
static void initatoms(void);
/* structure builders, and their helper routines */
@@ -31,10 +31,10 @@ static struct Menu *buildmenutree(unsigned level, const char *label, const char
static struct Menu *parsestdin(void);
/* image loader */
static Imlib_Image loadicon(const char *file, int size);
static Imlib_Image loadicon(const char *file);
/* structure setters, and their helper routines */
static void setupmenusize(struct Menu *menu);
static void setupitems(struct Menu *menu);
static void setupmenupos(struct Menu *menu);
static void setupmenu(struct Menu *menu, XClassHint *classh);
@@ -79,6 +79,7 @@ static Atom netatom[NetLast];
/* flags */
static int wflag = 0; /* whether to let the window manager control XMenu */
static int iflag = 0; /* whether to disable icons */
/* include config variable */
#include "config.h"
@@ -96,8 +97,11 @@ main(int argc, char *argv[])
XClassHint classh;
int ch;
while ((ch = getopt(argc, argv, "w")) != -1) {
while ((ch = getopt(argc, argv, "iw")) != -1) {
switch (ch) {
case 'i':
iflag = 1;
break;
case 'w':
wflag = 1;
break;
@@ -121,16 +125,18 @@ main(int argc, char *argv[])
colormap = DefaultColormap(dpy, screen);
/* imlib2 stuff */
imlib_set_cache_size(2048 * 1024);
imlib_context_set_dither(1);
imlib_context_set_display(dpy);
imlib_context_set_visual(visual);
imlib_context_set_colormap(colormap);
if (!iflag) {
imlib_set_cache_size(2048 * 1024);
imlib_context_set_dither(1);
imlib_context_set_display(dpy);
imlib_context_set_visual(visual);
imlib_context_set_colormap(colormap);
}
/* initializers */
initresources();
initdc();
initscreengeom();
initconfig();
initatoms();
/* set window class */
@@ -239,9 +245,9 @@ initdc(void)
dc.gc = XCreateGC(dpy, rootwin, 0, NULL);
}
/* calculate screen geometry */
/* calculate configuration values that are not set manually */
static void
initscreengeom(void)
initconfig(void)
{
Window dw; /* dummy variable */
int di; /* dummy variable */
@@ -250,6 +256,7 @@ initscreengeom(void)
XQueryPointer(dpy, rootwin, &dw, &dw, &config.cursx, &config.cursy, &di, &di, &du);
config.screenw = DisplayWidth(dpy, screen);
config.screenh = DisplayHeight(dpy, screen);
config.iconsize = config.height_pixels - config.iconpadding * 2;
}
/* intern atoms */
@@ -441,7 +448,7 @@ parsestdin(void)
/* load and scale icon */
static Imlib_Image
loadicon(const char *file, int size)
loadicon(const char *file)
{
Imlib_Image icon;
int width;
@@ -458,18 +465,20 @@ loadicon(const char *file, int size)
height = imlib_image_get_height();
imgsize = MIN(width, height);
icon = imlib_create_cropped_scaled_image(0, 0, imgsize, imgsize, size, size);
icon = imlib_create_cropped_scaled_image(0, 0, imgsize, imgsize,
config.iconsize,
config.iconsize);
return icon;
}
/* setup the size of a menu and the position of its items */
/* setup the height, width and icon of the items of a menu */
static void
setupmenusize(struct Menu *menu)
setupitems(struct Menu *menu)
{
XGlyphInfo ext;
struct Item *item;
int labelwidth;
int itemwidth;
menu->w = config.width_pixels;
for (item = menu->list; item != NULL; item = item->next) {
@@ -485,13 +494,25 @@ setupmenusize(struct Menu *menu)
XftTextExtentsUtf8(dpy, dc.font, (XftChar8 *)item->label,
item->labellen, &ext);
/* set menu width */
labelwidth = ext.xOff + item->h * 2;
menu->w = MAX(menu->w, labelwidth);
/*
* set menu width
*
* the item width depends on the size of its label (ext.xOff),
* and it is only used to calculate the width of the menu (which
* is equal to the width of the largest item).
*
* the horizontal padding appears 4 times through the width of a
* item: before and after its icon, and before and after its triangle
* if the iflag is set (icons are disabled) then the horizontal
* padding appears before the label and around the triangle.
*/
itemwidth = ext.xOff + config.triangle_width + config.horzpadding * 3;
itemwidth += (iflag) ? 0 : config.iconsize + config.horzpadding;
menu->w = MAX(menu->w, itemwidth);
/* create icon */
if (item->file != NULL)
item->icon = loadicon(item->file, item->h - config.iconpadding * 2);
if (item->file != NULL && !iflag)
item->icon = loadicon(item->file);
}
}
@@ -539,7 +560,7 @@ setupmenu(struct Menu *menu, XClassHint *classh)
XTextProperty wintitle;
/* setup size and position of menus */
setupmenusize(menu);
setupitems(menu);
setupmenupos(menu);
/* update menu geometry */
@@ -685,7 +706,8 @@ drawseparator(struct Menu *menu, struct Item *item)
y = item->y + item->h/2;
XSetForeground(dpy, dc.gc, dc.separator.pixel);
XDrawLine(dpy, menu->pixmap, dc.gc, 0, y, menu->w, y);
XDrawLine(dpy, menu->pixmap, dc.gc, config.horzpadding, y,
menu->w - config.horzpadding, y);
}
/* draw regular item */
@@ -694,7 +716,8 @@ drawitem(struct Menu *menu, struct Item *item, XftColor *color)
{
int x, y;
x = item->h;
x = config.horzpadding;
x += (iflag) ? 0 : config.horzpadding + config.iconsize;
y = item->y + (item->h + dc.font->ascent) / 2;
XSetForeground(dpy, dc.gc, color[ColorFG].pixel);
XftDrawStringUtf8(menu->draw, &color[ColorFG], dc.font,
@@ -702,7 +725,7 @@ drawitem(struct Menu *menu, struct Item *item, XftColor *color)
/* draw triangle, if item contains a submenu */
if (item->submenu != NULL) {
x = menu->w - (item->h + config.triangle_width + 1) / 2;
x = menu->w - config.triangle_width - config.horzpadding;
y = item->y + (item->h - config.triangle_height + 1) / 2;
XPoint triangle[] = {
@@ -717,8 +740,8 @@ drawitem(struct Menu *menu, struct Item *item, XftColor *color)
}
/* draw icon */
if (item->file != NULL) {
x = config.iconpadding;
if (item->icon != NULL) {
x = config.horzpadding;
y = item->y + config.iconpadding;
imlib_context_set_drawable(menu->pixmap);
imlib_context_set_image(item->icon);
@@ -997,6 +1020,6 @@ cleanup(void)
static void
usage(void)
{
(void)fprintf(stderr, "usage: xmenu [-w] [title]\n");
(void)fprintf(stderr, "usage: xmenu [-iw] [title]\n");
exit(1);
}