fookb: Port to libdockapp.
In addition to the obvious simplification to the code by removing all the window creation stuff, this also allows us to let users pick whether they want to run fookb as a dockapp or as a normal windowed application at runtime using libdockapp's --windowed command line option. Previously, this was done during build using configure's --enable-wmaker option.
This commit is contained in:
parent
b8ce2c9cd2
commit
0448b4965d
4 changed files with 29 additions and 207 deletions
|
@ -5,8 +5,8 @@ dist_man_MANS = fookb.1x
|
||||||
dist_pkgdata_DATA = 1.xpm 2.xpm 3.xpm 4.xpm rus.xpm lat.xpm boom.xpm \
|
dist_pkgdata_DATA = 1.xpm 2.xpm 3.xpm 4.xpm rus.xpm lat.xpm boom.xpm \
|
||||||
En.xpm Ru.xpm beep_spring.au
|
En.xpm Ru.xpm beep_spring.au
|
||||||
|
|
||||||
AM_CFLAGS = $(Xlib_CFLAGS) $(libXpm_CFLAGS) $(WUtil_CFLAGS)
|
AM_CFLAGS = $(Xlib_CFLAGS) $(libXpm_CFLAGS) $(WUtil_CFLAGS) $(libdockapp_CFLAGS)
|
||||||
LIBS += $(Xlib_LIBS) $(libXpm_LIBS) $(WUtil_LIBS)
|
LIBS += $(Xlib_LIBS) $(libXpm_LIBS) $(WUtil_LIBS) $(libdockapp_LIBS)
|
||||||
|
|
||||||
EXTRA_DIST = copyright fookb.cf KNOWN_BUGS LICENSE README.russian.koi8-r \
|
EXTRA_DIST = copyright fookb.cf KNOWN_BUGS LICENSE README.russian.koi8-r \
|
||||||
README.russian.utf-8
|
README.russian.utf-8
|
||||||
|
|
|
@ -17,6 +17,7 @@ dnl Checks for libraries.
|
||||||
PKG_CHECK_MODULES([Xlib], [x11])
|
PKG_CHECK_MODULES([Xlib], [x11])
|
||||||
PKG_CHECK_MODULES([libXpm], [xpm])
|
PKG_CHECK_MODULES([libXpm], [xpm])
|
||||||
PKG_CHECK_MODULES([WUtil], [WUtil])
|
PKG_CHECK_MODULES([WUtil], [WUtil])
|
||||||
|
PKG_CHECK_MODULES([libdockapp], [dockapp])
|
||||||
|
|
||||||
AC_ARG_ENABLE(
|
AC_ARG_ENABLE(
|
||||||
[wmaker],
|
[wmaker],
|
||||||
|
|
229
fookb/fookb.c
229
fookb/fookb.c
|
@ -17,6 +17,8 @@
|
||||||
/* XKB fun */
|
/* XKB fun */
|
||||||
#include <X11/XKBlib.h>
|
#include <X11/XKBlib.h>
|
||||||
|
|
||||||
|
#include <libdockapp/dockapp.h>
|
||||||
|
|
||||||
/* My own fun */
|
/* My own fun */
|
||||||
#include "fookb.h"
|
#include "fookb.h"
|
||||||
#include "images.h"
|
#include "images.h"
|
||||||
|
@ -26,92 +28,27 @@
|
||||||
#define sterror(x) (void)printf("Strange error, please report! %s:%d, %s\n",\
|
#define sterror(x) (void)printf("Strange error, please report! %s:%d, %s\n",\
|
||||||
__FILE__, __LINE__, x)
|
__FILE__, __LINE__, x)
|
||||||
|
|
||||||
|
|
||||||
static void getGC(Window win, GC *gc, Display *dpy)
|
|
||||||
{
|
|
||||||
unsigned long valuemask = 0; /* No data in ``values'' */
|
|
||||||
XGCValues values;
|
|
||||||
*gc = XCreateGC(dpy, win, valuemask, &values);
|
|
||||||
/* FIXME Check if there was an error */
|
|
||||||
/* XSetForeground(dpy, *gc, BlackPixel(dpy, scr)); */
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int main(int argc, register char *argv[])
|
int main(int argc, register char *argv[])
|
||||||
{
|
{
|
||||||
Display *dpy;
|
XkbEvent labuda; /* Xkb event. X event will be labuda.core */
|
||||||
int scr;
|
|
||||||
Window root;
|
|
||||||
|
|
||||||
int err;
|
|
||||||
|
|
||||||
int event_rtrn; /* for XkbOpenDisplay */
|
|
||||||
int error_rtrn;
|
|
||||||
int reason_rtrn;
|
|
||||||
|
|
||||||
XkbEvent labuda; /* Xkb event. X event will be labuda.core */
|
|
||||||
|
|
||||||
Window billy; /* _The_ Window */
|
|
||||||
|
|
||||||
#ifdef WMAKER
|
|
||||||
Window dilly; /* ...and his icon */
|
|
||||||
#endif
|
|
||||||
|
|
||||||
int border = 0; /* _The_ Window parameters */
|
|
||||||
|
|
||||||
XWMHints *wm_hints;
|
|
||||||
XClassHint class_hints;
|
|
||||||
|
|
||||||
#ifdef WMAKER /* If we use Windowmaker, _The_ Window will */
|
|
||||||
XSizeHints *BigBunny; /* be withdrawn. And we do not want to
|
|
||||||
place empty border by hand. */
|
|
||||||
#endif
|
|
||||||
|
|
||||||
GC gc; /* Graphic context */
|
|
||||||
|
|
||||||
char resn[] = "fookb";
|
|
||||||
char resc[] = "Fookb";
|
|
||||||
|
|
||||||
|
|
||||||
int state = 0; /* We suppose that latin keyboard is the
|
int state = 0; /* We suppose that latin keyboard is the
|
||||||
primal state FIXME */
|
primal state FIXME */
|
||||||
|
Pixmap pixmap;
|
||||||
|
|
||||||
/*
|
|
||||||
event_rtrn = malloc(sizeof(int));
|
|
||||||
error_rtrn = malloc(sizeof(int));
|
|
||||||
reason_rtrn = malloc(sizeof(int));
|
|
||||||
*/
|
|
||||||
|
|
||||||
XrmInitialize(); /* We should initialize X resource
|
DAParseArguments(argc, argv, NULL, 0,
|
||||||
manager before doing something else
|
"XKB state indicator for Window Maker",
|
||||||
*/
|
PACKAGE_STRING);
|
||||||
|
|
||||||
ParseOptions(&argc, argv); /* We should parse command line
|
DAOpenDisplay(NULL, argc, argv);
|
||||||
options and try to find '-display'
|
read_images(DADisplay); /* Let's read icon images */
|
||||||
before opening X display */
|
DACreateIcon(PACKAGE_NAME, get_width(), get_height(), argc, argv);
|
||||||
|
XSelectInput(DADisplay, DAWindow, ButtonPressMask);
|
||||||
/* Go, fighters, go! */
|
|
||||||
dpy = XkbOpenDisplay(mydispname,
|
|
||||||
&event_rtrn,
|
|
||||||
&error_rtrn, NULL, NULL, &reason_rtrn);
|
|
||||||
|
|
||||||
/* Oops. */
|
|
||||||
if (dpy == NULL) {
|
|
||||||
(void)puts("Cannot open display.");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
}
|
|
||||||
|
|
||||||
scr = DefaultScreen(dpy);
|
|
||||||
root = RootWindow(dpy, scr);
|
|
||||||
|
|
||||||
MoreOptions(dpy); /* Now we can parse X server resource
|
|
||||||
database. It is not available
|
|
||||||
before display is opened */
|
|
||||||
|
|
||||||
/* We would like receive the only Xkb event: XkbStateNotify. And only
|
/* We would like receive the only Xkb event: XkbStateNotify. And only
|
||||||
* when XkbLockGroup happens. */
|
* when XkbLockGroup happens. */
|
||||||
|
|
||||||
if (False == XkbSelectEvents(dpy,
|
if (False == XkbSelectEvents(DADisplay,
|
||||||
XkbUseCoreKbd,
|
XkbUseCoreKbd,
|
||||||
XkbAllEventsMask,
|
XkbAllEventsMask,
|
||||||
0)) {
|
0)) {
|
||||||
|
@ -119,7 +56,7 @@ int main(int argc, register char *argv[])
|
||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
} /* Deselect all events */
|
} /* Deselect all events */
|
||||||
|
|
||||||
if (False == XkbSelectEventDetails(dpy,
|
if (False == XkbSelectEventDetails(DADisplay,
|
||||||
XkbUseCoreKbd,
|
XkbUseCoreKbd,
|
||||||
XkbStateNotify,
|
XkbStateNotify,
|
||||||
XkbAllEventsMask,
|
XkbAllEventsMask,
|
||||||
|
@ -128,127 +65,18 @@ int main(int argc, register char *argv[])
|
||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
} /* Select XkbStateNotify/XkbgroupLock */
|
} /* Select XkbStateNotify/XkbgroupLock */
|
||||||
|
|
||||||
read_images(dpy); /* Let's read icon images */
|
pixmap = DAMakePixmap();
|
||||||
|
|
||||||
/* Run out! */
|
update_window(pixmap, DAGC, state, DADisplay);
|
||||||
billy = XCreateSimpleWindow(dpy,
|
DASetPixmap(pixmap);
|
||||||
root,
|
|
||||||
0, 0,
|
|
||||||
get_width(), get_height(),
|
|
||||||
border,
|
|
||||||
BlackPixel(dpy, scr),
|
|
||||||
WhitePixel(dpy, scr));
|
|
||||||
XStoreName(dpy, billy, "fookb");
|
|
||||||
|
|
||||||
#ifdef WMAKER
|
DAShow();
|
||||||
dilly = XCreateSimpleWindow(dpy,
|
|
||||||
root,
|
|
||||||
0, 0,
|
|
||||||
get_width(), get_height(),
|
|
||||||
border,
|
|
||||||
BlackPixel(dpy, scr),
|
|
||||||
WhitePixel(dpy, scr));
|
|
||||||
#endif
|
|
||||||
|
|
||||||
class_hints.res_name = resn;
|
|
||||||
class_hints.res_class = resc;
|
|
||||||
|
|
||||||
err = XSetClassHint(dpy, billy, &class_hints);
|
|
||||||
switch(err) {
|
|
||||||
case BadAlloc:
|
|
||||||
sterror("BadAlloc");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
case BadWindow:
|
|
||||||
sterror("BadWindow");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
}
|
|
||||||
|
|
||||||
wm_hints = XAllocWMHints();
|
|
||||||
wm_hints->window_group = billy;
|
|
||||||
|
|
||||||
#ifdef WMAKER
|
|
||||||
wm_hints->icon_window = dilly;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
wm_hints->input = False;
|
|
||||||
wm_hints->flags = InputHint | WindowGroupHint;
|
|
||||||
|
|
||||||
#ifdef WMAKER
|
|
||||||
wm_hints->flags = wm_hints->flags | IconWindowHint;
|
|
||||||
err = XSetWMHints(dpy, dilly, wm_hints);
|
|
||||||
switch(err) {
|
|
||||||
case BadAlloc:
|
|
||||||
sterror("BadAlloc");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
case BadWindow:
|
|
||||||
sterror("BadWindow");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
}
|
|
||||||
wm_hints->initial_state = WithdrawnState;
|
|
||||||
wm_hints->flags = wm_hints->flags | StateHint;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
err = XSetWMHints(dpy, billy, wm_hints);
|
|
||||||
switch(err) {
|
|
||||||
case BadAlloc:
|
|
||||||
sterror("BadAlloc");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
case BadWindow:
|
|
||||||
sterror("BadWindow");
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef WMAKER
|
|
||||||
/* Look at the comment for XSizeHints * BigBunny */
|
|
||||||
BigBunny = XAllocSizeHints();
|
|
||||||
if (NULL == BigBunny) {
|
|
||||||
(void)printf("Not enough memory, %s:%d.\n", __FILE__, __LINE__);
|
|
||||||
exit(EXIT_FAILURE);
|
|
||||||
}
|
|
||||||
/* Nasty Hack. XSizeHints.x & XSizeHints.y are obsolete. */
|
|
||||||
BigBunny->x = 0;
|
|
||||||
BigBunny->y = 0;
|
|
||||||
BigBunny->flags = PPosition;
|
|
||||||
XSetWMNormalHints(dpy, billy, BigBunny);
|
|
||||||
XFree(BigBunny);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/* The only thing we would like to do - update our billy */
|
|
||||||
#ifndef WMAKER
|
|
||||||
XSelectInput(dpy, billy, ExposureMask | ButtonPressMask);
|
|
||||||
#else /* ...or dilly?! */
|
|
||||||
XSelectInput(dpy, dilly, ExposureMask | ButtonPressMask);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
XSetCommand(dpy, billy, argv, argc);
|
|
||||||
|
|
||||||
/* Programmer supplied functions */
|
|
||||||
#ifndef WMAKER
|
|
||||||
getGC(billy, &gc, dpy);
|
|
||||||
#else
|
|
||||||
getGC(dilly, &gc, dpy);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
/* Let's look */
|
|
||||||
XMapWindow(dpy, billy); /* We would like to see the window. */
|
|
||||||
|
|
||||||
/* HELLO! HELLO! HELLO! Is that our GOOD FRIEND main loop here? */
|
/* HELLO! HELLO! HELLO! Is that our GOOD FRIEND main loop here? */
|
||||||
while (1) {
|
while (1) {
|
||||||
XNextEvent(dpy, &labuda.core);
|
XNextEvent(DADisplay, &labuda.core);
|
||||||
switch (labuda.core.type) {
|
switch (labuda.core.type) {
|
||||||
|
|
||||||
case Expose: /* We should update our window. */
|
|
||||||
if (labuda.core.xexpose.count != 0)
|
|
||||||
/* Well, I knew what does it mean,
|
|
||||||
but I forgot :) */
|
|
||||||
break;
|
|
||||||
#ifndef WMAKER
|
|
||||||
update_window(billy, gc, state, dpy);
|
|
||||||
#else
|
|
||||||
update_window(dilly, gc, state, dpy);
|
|
||||||
#endif
|
|
||||||
break;
|
|
||||||
case ButtonPress:
|
case ButtonPress:
|
||||||
|
|
||||||
switch (labuda.core.xbutton.button) {
|
switch (labuda.core.xbutton.button) {
|
||||||
|
@ -256,7 +84,7 @@ int main(int argc, register char *argv[])
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
puts("Button1 pressed.");
|
puts("Button1 pressed.");
|
||||||
#endif
|
#endif
|
||||||
XkbLockGroup(dpy,
|
XkbLockGroup(DADisplay,
|
||||||
XkbUseCoreKbd,
|
XkbUseCoreKbd,
|
||||||
(state + 1) % 4);
|
(state + 1) % 4);
|
||||||
break;
|
break;
|
||||||
|
@ -264,7 +92,7 @@ int main(int argc, register char *argv[])
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
puts("Button2 pressed.");
|
puts("Button2 pressed.");
|
||||||
#endif
|
#endif
|
||||||
XkbLockGroup(dpy,
|
XkbLockGroup(DADisplay,
|
||||||
XkbUseCoreKbd,
|
XkbUseCoreKbd,
|
||||||
(state + 3) % 4);
|
(state + 3) % 4);
|
||||||
break;
|
break;
|
||||||
|
@ -272,12 +100,9 @@ int main(int argc, register char *argv[])
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
puts("Button3 pressed, bye.");
|
puts("Button3 pressed, bye.");
|
||||||
#endif
|
#endif
|
||||||
XFreeGC(dpy, gc);
|
XFreeGC(DADisplay, DAGC);
|
||||||
XDestroyWindow(dpy, billy);
|
XDestroyWindow(DADisplay, DAWindow);
|
||||||
#ifdef WMAKER
|
XCloseDisplay(DADisplay);
|
||||||
XDestroyWindow(dpy, dilly);
|
|
||||||
#endif
|
|
||||||
XCloseDisplay(dpy);
|
|
||||||
exit(0);
|
exit(0);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -289,16 +114,12 @@ int main(int argc, register char *argv[])
|
||||||
#endif
|
#endif
|
||||||
if ((state < 0) || (state > 4))
|
if ((state < 0) || (state > 4))
|
||||||
state = 4;
|
state = 4;
|
||||||
#ifndef WMAKER
|
update_window(pixmap, DAGC, state, DADisplay);
|
||||||
update_window(billy, gc, state, dpy);
|
DASetPixmap(pixmap);
|
||||||
#else
|
|
||||||
update_window(dilly, gc, state, dpy);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
puts("."); /* XkbLockGroup happens */
|
puts("."); /* XkbLockGroup happens */
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -150,7 +150,7 @@ void read_images(Display *dpy)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void update_window(Window win, GC gc, unsigned int whattodo, Display *dpy)
|
void update_window(Drawable win, GC gc, unsigned int whattodo, Display *dpy)
|
||||||
{
|
{
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue