/*
 * AT-SPI - Assistive Technology Service Provider Interface
 * (Gnome Accessibility Project; http://developer.gnome.org/projects/gap)
 *
 * Copyright 2001, 2002 Sun Microsystems Inc.,
 * Copyright 2001, 2002 Ximian, Inc.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with this library; if not, write to the
 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 * Boston, MA 02111-1307, USA.
 */

#include <stdlib.h>
#include <stdio.h>
#include <ctype.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <sys/un.h>
#include <spi.h>
#include <glib.h>

#define XK_MISCELLANY
#include <X11/keysymdef.h>
#include <gdk/gdk.h>
#include <gdk/gdkx.h>
#include <X11/XKBlib.h>

static gchar *events[] = 
    {
	"focus:",

    	"window:minimize",
    	"window:maximize",
    	"window:restore",
    	"window:close",
    	"window:create",
    	"window:reparent",
	"window:desktop-create",
	"window:desktop-destroy",
    	"window:focus-in",
    	"window:activate",
    	"window:destroy",
	"window:focus-out",
    	"window:deactivate",
    	"window:raise",
    	"window:lower",
    	"window:move",
    	"window:resize",
    	"window:shade",
    	"window:unshade",
    	"window:restyle",
    };


static void report_event (const AccessibleEvent *event, void *user_data);
static SPIBoolean report_command_key_event  (const AccessibleKeystroke *stroke, void *user_data);

static AccessibleKeystrokeListener *command_key_listener;
static AccessibleEventListener *listener = NULL;

int
main (int argc, char **argv)
{
  SPIBoolean retval = FALSE;
  short key;
  Display *disp;
  AccessibleKeySet    *command_keyset;
    gint i;
	
  SPI_init ();

    gtk_init (&argc, &argv);
  command_key_listener = SPI_createAccessibleKeystrokeListener (report_command_key_event, NULL);
  
  disp = GDK_DISPLAY ();
  key = XKeysymToKeycode (disp, XK_KP_0);
  command_keyset = SPI_createAccessibleKeySet (1, NULL, &key, NULL);
  retval = SPI_registerAccessibleKeystrokeListener (command_key_listener,
			       		  command_keyset,
					  SPI_KEYMASK_NUMLOCK,
					  (gulong) ( SPI_KEY_PRESSED | SPI_KEY_RELEASED ),
					  SPI_KEYLISTENER_ALL_WINDOWS);
//					  SPI_KEYLISTENER_NOSYNC | SPI_KEYLISTENER_CANCONSUME);
  
  fprintf (stderr, "Command key registry: result %s\n", retval ? "succeeded" : 
	"failed");


    listener = SPI_createAccessibleEventListener (report_event, NULL);
    for (i = 0; i < G_N_ELEMENTS (events); i++)
	SPI_registerGlobalEventListener (listener, events[i]);

    SPI_event_main();
    SPI_exit ();

    return 0;
}

static SPIBoolean
report_command_key_event (const AccessibleKeystroke *key, void *user_data)
{
    static gint cnt = 0;
  fprintf (stderr, "\nL%d KeyEvent %s%c (keycode %d); string=%s; time=%lx",
	   cnt++,
	  (key->modifiers & SPI_KEYMASK_ALT)?"Alt-":"",
	  ((key->modifiers & SPI_KEYMASK_SHIFT)^(key->modifiers & SPI_KEYMASK_SHIFTLOCK))?
	  (char) toupper((int) key->keyID) : (char) tolower((int) key->keyID),
	  (int) key->keycode,
   	  key->keystring,
	  (long int) key->timestamp);	


  return TRUE;
}


static void 
report_general (const AccessibleEvent *event,
	        void *user_data)
{
    static gint cnt = 0;
    fprintf (stderr, "\nE%d: %xp %s for %s(%s) role %s with details %ld %ld",
		cnt++,
		(unsigned int)event->source, event->type, 
		Accessible_getName (event->source),
		Accessible_getDescription (event->source),
		Accessible_getRoleName (event->source),
		event->detail1, event->detail2);
}

static void 
report_event (const AccessibleEvent *event,
	      void *user_data)
{
    static gboolean busy = FALSE;
    if (busy)
    {
	fprintf (stderr, "\nRRRR:%s", event->type);
	return;
    }
    busy = TRUE;

    report_general (event, user_data);

    busy = FALSE;
}
