xkbwatch.c revision b3eb03f3
1/* $Xorg: xkbwatch.c,v 1.4 2000/08/17 19:54:51 cpqbld Exp $ */
2/************************************************************
3 Copyright (c) 1995 by Silicon Graphics Computer Systems, Inc.
4
5 Permission to use, copy, modify, and distribute this
6 software and its documentation for any purpose and without
7 fee is hereby granted, provided that the above copyright
8 notice appear in all copies and that both that copyright
9 notice and this permission notice appear in supporting
10 documentation, and that the name of Silicon Graphics not be
11 used in advertising or publicity pertaining to distribution
12 of the software without specific prior written permission.
13 Silicon Graphics makes no representation about the suitability
14 of this software for any purpose. It is provided "as is"
15 without any express or implied warranty.
16
17 SILICON GRAPHICS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
18 SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
19 AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SILICON
20 GRAPHICS BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
21 DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
22 DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
23 OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION  WITH
24 THE USE OR PERFORMANCE OF THIS SOFTWARE.
25
26 ********************************************************/
27/* $XFree86: xc/programs/xkbutils/xkbwatch.c,v 3.4 2001/01/17 23:46:14 dawes Exp $ */
28
29#include <stdlib.h>
30#include <X11/X.h>
31#include <X11/Xlib.h>
32#include <X11/XKBlib.h>
33#include <X11/Intrinsic.h>
34#include <X11/StringDefs.h>
35#include <X11/Shell.h>
36#include <X11/Xaw/Cardinals.h>
37#include <X11/Xaw/Box.h>
38
39#define	OPAQUE_DEFINED
40#define	BOOLEAN_DEFINED
41#define	DEBUG_VAR_NOT_LOCAL
42#define	DEBUG_VAR debugFlags
43#include "utils.h"
44#include "LED.h"
45
46/***====================================================================***/
47
48static	Display *	inDpy,*outDpy;
49static	int		evBase,errBase;
50
51/***====================================================================***/
52
53
54static XrmOptionDescRec options[] = {
55{"-off",	"*on.on",		XrmoptionNoArg,		"FALSE"},
56{"-on",		"*on.on",		XrmoptionNoArg,		"TRUE"}
57};
58
59/***====================================================================***/
60
61int
62main(int argc, char *argv[])
63{
64Widget		toplevel;
65XtAppContext	app_con;
66Widget		panel;
67Widget		base[XkbNumModifiers];
68Widget		latched[XkbNumModifiers];
69Widget		locked[XkbNumModifiers];
70Widget		effective[XkbNumModifiers];
71Widget		compat[XkbNumModifiers];
72Widget		baseBox,latchBox,lockBox,effBox,compatBox;
73register int	i;
74unsigned	bit;
75XkbEvent	ev;
76XkbStateRec	state;
77static Arg	hArgs[]= {{ XtNorientation, (XtArgVal)XtorientHorizontal }};
78static Arg	vArgs[]= {{ XtNorientation, (XtArgVal)XtorientVertical }};
79static Arg	onArgs[]=  {{ XtNon, (XtArgVal)True }};
80static Arg	offArgs[]=  {{ XtNon, (XtArgVal)False }};
81static char *	fallback_resources[] = {
82    "*Box*background: grey50",
83    "*Box*borderWidth: 0",
84    "*Box*vSpace: 1",
85    NULL
86};
87
88    uSetEntryFile(NullString);
89    uSetDebugFile(NullString);
90    uSetErrorFile(NullString);
91    toplevel = XtOpenApplication(&app_con, "XkbWatch",
92				 options, XtNumber(options), &argc, argv,
93				 fallback_resources,
94				 sessionShellWidgetClass, NULL, ZERO);
95    if (toplevel==NULL) {
96	uFatalError("Couldn't create application top level\n");
97	exit(1);
98    }
99    inDpy= outDpy= XtDisplay(toplevel);
100    if (inDpy) {
101	int i1,mn,mj;
102	mj= XkbMajorVersion;
103	mn= XkbMinorVersion;
104	if (!XkbQueryExtension(inDpy,&i1,&evBase,&errBase,&mj,&mn)) {
105	    uFatalError("Server doesn't support a compatible XKB\n");
106	    exit(1);
107	}
108    }
109    panel= XtCreateManagedWidget("xkbwatch",boxWidgetClass,toplevel,vArgs,1);
110    if (panel==NULL) {
111	uFatalError("Couldn't create top level box\n");
112	exit(1);
113    }
114    baseBox= XtCreateManagedWidget("base",boxWidgetClass,panel,hArgs,1);
115    if (baseBox==NULL)
116	uFatalError("Couldn't create base modifiers box\n");
117    latchBox= XtCreateManagedWidget("latched",boxWidgetClass,panel,hArgs,1);
118    if (latchBox==NULL)
119	uFatalError("Couldn't create latched modifiers box\n");
120    lockBox= XtCreateManagedWidget("locked",boxWidgetClass,panel,hArgs,1);
121    if (lockBox==NULL)
122	uFatalError("Couldn't create locked modifiers box\n");
123    effBox= XtCreateManagedWidget("effective",boxWidgetClass,panel,hArgs,1);
124    if (effBox==NULL)
125	uFatalError("Couldn't create effective modifiers box\n");
126    compatBox= XtCreateManagedWidget("compat",boxWidgetClass,panel,hArgs,1);
127    if (compatBox==NULL)
128	uFatalError("Couldn't create compatibility state box\n");
129    XkbSelectEvents(inDpy,XkbUseCoreKbd,XkbStateNotifyMask,XkbStateNotifyMask);
130    XkbGetState(inDpy,XkbUseCoreKbd,&state);
131    for (i=XkbNumModifiers-1,bit=0x80;i>=0;i--,bit>>=1) {
132	ArgList	list;
133	char	buf[30];
134	sprintf(buf,"base%d",i);
135	if (state.base_mods&bit)	list= onArgs;
136	else				list= offArgs;
137	base[i]= XtCreateManagedWidget(buf,ledWidgetClass,baseBox,list,1);
138	sprintf(buf,"latched%d",i);
139	if (state.latched_mods&bit)	list= onArgs;
140	else				list= offArgs;
141	latched[i]= XtCreateManagedWidget(buf,ledWidgetClass,latchBox,list,1);
142	sprintf(buf,"locked%d",i);
143	if (state.locked_mods&bit)	list= onArgs;
144	else				list= offArgs;
145	locked[i]= XtCreateManagedWidget(buf,ledWidgetClass,lockBox,list,1);
146	sprintf(buf,"effective%d",i);
147	if (state.mods&bit)		list= onArgs;
148	else				list= offArgs;
149	effective[i]= XtCreateManagedWidget(buf,ledWidgetClass,effBox,list,1);
150	sprintf(buf,"compat%d",i);
151	if (state.compat_state&bit)	list= onArgs;
152	else				list= offArgs;
153	compat[i]= XtCreateManagedWidget(buf,ledWidgetClass,compatBox,list,1);
154    }
155    XtRealizeWidget(toplevel);
156    while (1) {
157        XtAppNextEvent(app_con,&ev.core);
158	if (ev.core.type==evBase+XkbEventCode) {
159	    if (ev.any.xkb_type==XkbStateNotify) {
160		unsigned changed;
161		if (ev.state.changed&XkbModifierBaseMask) {
162		    changed= ev.state.base_mods^state.base_mods;
163		    state.base_mods= ev.state.base_mods;
164		    for (i=0,bit=1;i<XkbNumModifiers;i++,bit<<=1) {
165			if (changed&bit) {
166			    ArgList	list;
167			    if (state.base_mods&bit)	list= onArgs;
168			    else			list= offArgs;
169			    XtSetValues(base[i],list,1);
170			}
171		    }
172		}
173		if (ev.state.changed&XkbModifierLatchMask) {
174		    changed= ev.state.latched_mods^state.latched_mods;
175		    state.latched_mods= ev.state.latched_mods;
176		    for (i=0,bit=1;i<XkbNumModifiers;i++,bit<<=1) {
177			if (changed&bit) {
178			    ArgList	list;
179			    if (state.latched_mods&bit)	list= onArgs;
180			    else			list= offArgs;
181			    XtSetValues(latched[i],list,1);
182			}
183		    }
184		}
185		if (ev.state.changed&XkbModifierLockMask) {
186		    changed= ev.state.locked_mods^state.locked_mods;
187		    state.locked_mods= ev.state.locked_mods;
188		    for (i=0,bit=1;i<XkbNumModifiers;i++,bit<<=1) {
189			if (changed&bit) {
190			    ArgList	list;
191			    if (state.locked_mods&bit)	list= onArgs;
192			    else			list= offArgs;
193			    XtSetValues(locked[i],list,1);
194			}
195		    }
196		}
197		if (ev.state.changed&XkbModifierStateMask) {
198		    changed= ev.state.mods^state.mods;
199		    state.mods= ev.state.mods;
200		    for (i=0,bit=1;i<XkbNumModifiers;i++,bit<<=1) {
201			if (changed&bit) {
202			    ArgList	list;
203			    if (state.mods&bit)	list= onArgs;
204			    else		list= offArgs;
205			    XtSetValues(effective[i],list,1);
206			}
207		    }
208		}
209		if (ev.state.changed&XkbCompatStateMask) {
210		    changed= ev.state.compat_state^state.compat_state;
211		    state.compat_state= ev.state.compat_state;
212		    for (i=0,bit=1;i<XkbNumModifiers;i++,bit<<=1) {
213			if (changed&bit) {
214			    ArgList	list;
215			    if (state.compat_state&bit)	list= onArgs;
216			    else			list= offArgs;
217			    XtSetValues(compat[i],list,1);
218			}
219		    }
220		}
221	    }
222	}
223	else XtDispatchEvent(&ev.core);
224    }
225/* BAIL: */
226    if (inDpy)
227	XCloseDisplay(inDpy);
228    if (outDpy!=inDpy)
229	XCloseDisplay(outDpy);
230    inDpy= outDpy= NULL;
231    return 0;
232}
233