summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBradley Smith2008-08-03 16:22:59 +0100
committerBradley Smith2008-08-03 16:22:59 +0100
commitae3a780491b700be0258b1c2243c86cf10729fcc (patch)
treef274f87c4d0bd3bc91e29f0dcc8c90da4b59c028
parentAdd more uitest stuff. (diff)
downloadgnurobots-ae3a780491b700be0258b1c2243c86cf10729fcc.tar.gz
Add Gtk interface. Using a Vte for guile input.
Signed-off-by: Bradley Smith <brad@brad-smith.co.uk>
-rw-r--r--Makefile.am2
-rw-r--r--configure.ac52
-rw-r--r--include/Makefile.am16
-rw-r--r--include/grobot.h6
-rw-r--r--include/ui-arena.h (renamed from ui/ui-arena.h)27
-rw-r--r--include/ui-cmdwin.h (renamed from ui/ui-cmdwin.h)2
-rw-r--r--include/ui-window-private.h (renamed from ui/ui-window-private.h)0
-rw-r--r--include/ui-window.h (renamed from ui/ui-window.h)5
-rw-r--r--include/userinterface.h180
-rw-r--r--src/Makefile.am20
-rw-r--r--src/grobot.c1449
-rw-r--r--src/main.c737
-rw-r--r--src/ui-arena.c466
-rw-r--r--src/ui-cmdwin.c (renamed from ui/ui-cmdwin.c)46
-rw-r--r--src/ui-window.c (renamed from ui/ui-window.c)38
-rw-r--r--src/userinterface.c736
-rw-r--r--ui/Makefile.am23
-rw-r--r--ui/design.glade317
-rw-r--r--ui/main.c34
-rw-r--r--ui/ui-arena.c45
20 files changed, 1686 insertions, 2515 deletions
diff --git a/Makefile.am b/Makefile.am
index 4eb65b9..fdc4977 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -16,7 +16,7 @@
## along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
AUTOMAKE_OPTIONS = 1.8.5
-SUBDIRS = contrib doc include maps scheme src xpm ui
+SUBDIRS = contrib doc include maps scheme src xpm
EXTRA_DIST = build
MAINTAINERCLEANFILES = Makefile.in aclocal.m4 configure
diff --git a/configure.ac b/configure.ac
index d4c7838..ff26b62 100644
--- a/configure.ac
+++ b/configure.ac
@@ -28,41 +28,23 @@ dnl Checks for programs.
AC_PROG_CC
dnl libtool stuff
-AC_LIBTOOL_DLOPEN
-dnl AC_LIBLTDL_CONVENIENCE
AC_DISABLE_STATIC
AC_PROG_LIBTOOL
-AC_SUBST(INCLTDL)
-AC_SUBST(LIBLTDL)
-
-dnl Locate X Windows
-dnl We need AC_PATH_XTRA to also locate extra libaries X depends on.
-dnl It will ``export'' X_CFLAGS, X_PRE_LIBS, X_EXTRA_LIBS and X_LIBS,
-dnl but for some reason we need to add -lX11 ourselves.
-AC_PATH_XTRA
-
-dnl Check for math library
-AC_CHECK_LIB(m, pow)
-
dnl Check for guile
GUILE_FLAGS
-dnl Some sytems need -ldl for dynamic library support.
-dnl AC_CHECK_LIB(dl, dlopen)
+PKG_CHECK_MODULES(GTHREAD2, gthread-2.0 >= 2.4)
+AC_SUBST(GTHREAD2_LIBS)
+AC_SUBST(GTHREAD2_CFLAGS)
-PKG_CHECK_MODULES(X,x11 xpm, HAVE_X=yes,HAVE_X=no)
-AC_SUBST(X_LIBS)
-AC_SUBST(X_CFLAGS)
+PKG_CHECK_MODULES(GTK2, gtk+-2.0 >= 2.4)
+AC_SUBST(GTK2_LIBS)
+AC_SUBST(GTK2_CFLAGS)
-dnl Check for glib2
-PKG_CHECK_MODULES(GLIB2,glib-2.0 >= 2.4 gobject-2.0 gmodule-2.0,HAVE_GLIB2=yes,HAVE_GLIB2=no)
-AC_SUBST(GLIB2_LIBS)
-AC_SUBST(GLIB2_CFLAGS)
-
-PKG_CHECK_MODULES(GTK,gtk+-2.0 >= 2.4, HAVE_GTK=yes,HAVE_GTK=no)
-AC_SUBST(GTK_LIBS)
-AC_SUBST(GTK_CFLAGS)
+PKG_CHECK_MODULES(VTE, vte)
+AC_SUBST(VTE_LIBS)
+AC_SUBST(VTE_CFLAGS)
schemedir="\$(pkgdatadir)/scheme"
AC_SUBST(schemedir)
@@ -70,10 +52,6 @@ AC_SUBST(schemedir)
mapsdir="\$(pkgdatadir)/maps"
AC_SUBST(mapsdir)
-if test "x$HAVE_GLIB2" = "xno"; then
- AC_MSG_ERROR([GNU Robots requires GLib2 to compile.])
-fi
-
for termlib in ncurses curses termcap terminfo termlib ; do
AC_CHECK_LIB(${termlib}, tgoto,
[READLINE_EXTRA="-l${termlib}"; break])
@@ -86,8 +64,8 @@ You need the GNU Readline library to build this program.
]),[$READLINE_EXTRA])
-AC_CHECK_HEADER(readline/readline.h,[READLINE_CFLAGS=-I/usr/include/readline/],
- AC_MSG_ERROR([
+AC_CHECK_HEADER(readline/readline.h,
+ [READLINE_CFLAGS=-I/usr/include/readline/], AC_MSG_ERROR([
You need the GNU Readline headers to build this program.
@@ -102,6 +80,13 @@ dnl Checks for header files.
AC_HEADER_STDC
AC_CHECK_HEADERS(unistd.h)
AC_CHECK_HEADERS(getopt.h)
+AC_CHECK_HEADERS(pty.h)
+
+AC_CHECK_LIB(util, openpty, [], AC_MSG_ERROR([
+
+You need openpty to build the program.
+
+]))
dnl Checks for typedefs, structures, and compiler characteristics.
AC_C_CONST
@@ -117,7 +102,6 @@ AC_CONFIG_FILES([Makefile
maps/Makefile
scheme/Makefile
src/Makefile
- ui/Makefile
])
AC_OUTPUT
diff --git a/include/Makefile.am b/include/Makefile.am
index bb2a455..47a3c86 100644
--- a/include/Makefile.am
+++ b/include/Makefile.am
@@ -15,10 +15,12 @@
## You should have received a copy of the GNU General Public License
## along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
-EXTRA_DIST =\
- api.h\
- configs.h\
- map.h\
- main.h\
- grobot.h\
- userinterface.h
+EXTRA_DIST = \
+ api.h \
+ configs.h \
+ map.h \
+ main.h \
+ grobot.h \
+ ui-window.h \
+ ui-arena.h \
+ ui-cmdwin.h
diff --git a/include/grobot.h b/include/grobot.h
index fd7f794..52a7039 100644
--- a/include/grobot.h
+++ b/include/grobot.h
@@ -21,7 +21,7 @@
#include <glib-object.h>
#include <glib.h>
-#include "userinterface.h"
+#include "ui-arena.h"
#include "map.h"
G_BEGIN_DECLS
@@ -53,7 +53,7 @@ struct _GRobot {
glong shots;
glong units;
- UserInterface *ui;
+ UIArena *ui;
Map *map;
};
@@ -73,7 +73,7 @@ GType g_robot_get_type(void) G_GNUC_CONST;
/* Our object functions */
GRobot* g_robot_new(int x, int y, int dir, long score, long energy,
- long shield, long units, long shots, UserInterface *ui, Map *map);
+ long shield, long units, long shots, UIArena *ui, Map *map);
void g_robot_turn (GRobot *robot, gint num_turns);
gboolean g_robot_move (GRobot *robot, gint steps);
diff --git a/ui/ui-arena.h b/include/ui-arena.h
index 5277f54..2fee88f 100644
--- a/ui/ui-arena.h
+++ b/include/ui-arena.h
@@ -21,6 +21,8 @@
#include <gtk/gtk.h>
+#include "map.h"
+
G_BEGIN_DECLS
#define UI_TYPE_ARENA \
@@ -34,6 +36,8 @@ G_BEGIN_DECLS
#define IS_UI_ARENA_CLASS(klass) \
G_TYPE_CHECK_CLASS_TYPE(klass, UI_TYPE_ARENA)
+#define dist(f_x, f_y, t_x, t_y) (abs((f_x)-(t_x))+abs((f_y)-(t_y)))
+
typedef struct _UIArena UIArena;
typedef struct _UIArenaClass UIArenaClass;
typedef struct _UIArenaPrivate UIArenaPrivate;
@@ -51,7 +55,28 @@ struct _UIArenaClass
GType ui_arena_get_type(void) G_GNUC_CONST;
-GtkWidget *ui_arena_new(void);
+GtkWidget *ui_arena_new();
+
+void ui_arena_set_map(UIArena *arena, Map *map);
+void ui_arena_postinit(UIArena *arena);
+void ui_arena_draw(UIArena *arena);
+void ui_arena_update_status(UIArena *arena, const gchar *s, glong energy,
+ glong score, glong shields);
+
+void ui_arena_add_thing(UIArena *arena, gint x, gint y, gint thing);
+void ui_arena_move_robot(UIArena *arena, gint from_x, gint from_y,
+ gint to_x, gint to_y, gint cdir, glong energy, glong score,
+ glong shields);
+void ui_arena_robot_smell(UIArena *arena, gint x, gint y, gint cdir,
+ glong energy, glong score, glong shields);
+void ui_arena_robot_zap(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields);
+void ui_arena_robot_feel(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields);
+void ui_arena_robot_grab(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields);
+void ui_arena_robot_look(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields);
G_END_DECLS
diff --git a/ui/ui-cmdwin.h b/include/ui-cmdwin.h
index c3bcf8a..1c6196d 100644
--- a/ui/ui-cmdwin.h
+++ b/include/ui-cmdwin.h
@@ -52,6 +52,8 @@ struct _UICmdWinClass
GType ui_cmdwin_get_type(void) G_GNUC_CONST;
GtkWidget *ui_cmdwin_new(void);
+void ui_cmdwin_get_string(UICmdWin *cmdwin, gchar *prompt, gchar *buf,
+ gint len);
G_END_DECLS
diff --git a/ui/ui-window-private.h b/include/ui-window-private.h
index cfb8b63..cfb8b63 100644
--- a/ui/ui-window-private.h
+++ b/include/ui-window-private.h
diff --git a/ui/ui-window.h b/include/ui-window.h
index 450223b..7b6c06f 100644
--- a/ui/ui-window.h
+++ b/include/ui-window.h
@@ -19,6 +19,8 @@
#ifndef __UI_WINDOW_H__
#define __UI_WINDOW_H__
+#include "map.h"
+
#include <gtk/gtkwindow.h>
G_BEGIN_DECLS
@@ -51,7 +53,8 @@ struct _UIWindowClass
GType ui_window_get_type(void) G_GNUC_CONST;
-GtkWidget *ui_window_new(void);
+GtkWidget *ui_window_new();
+void ui_window_postinit(UIWindow *window, Map* map);
G_END_DECLS
diff --git a/include/userinterface.h b/include/userinterface.h
deleted file mode 100644
index fc92e9c..0000000
--- a/include/userinterface.h
+++ /dev/null
@@ -1,180 +0,0 @@
-/* Copyright (C) 1998 Jim Hall <jhall1@isd.net>
- * Copyright (C) 2008 Bradley Smith <brad@brad-smith.co.uk>
- *
- * GNU Robots game engine.
- *
- * GNU Robots is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * GNU Robots 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 General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef __USER_INTERFACE_H__
-#define __USER_INTERFACE_H__
-
-#include <X11/Xlib.h>
-#include <X11/Xutil.h>
-#include <X11/xpm.h>
-#include <X11/keysym.h>
-
-#include <glib-object.h>
-/*#include "userinterface.h"*/
-#include "map.h"
-
-G_BEGIN_DECLS
-
-#define G_TYPE_USER_INTERFACE user_interface_get_type()
-#define G_IS_USER_INTERFACE(obj) G_TYPE_CHECK_INSTANCE_TYPE ((obj), \
- G_TYPE_USER_INTERFACE)
-#define G_IS_USER_INTERFACE_CLASS(klass) G_TYPE_CHECK_CLASS_TYPE ((klass), \
- G_TYPE_USER_INTERFACE)
-#define USER_INTERFACE_GET_CLASS(obj) G_TYPE_INSTANCE_GET_CLASS ((obj), \
- G_TYPE_USER_INTERFACE, \
- UserInterfaceClass)
-#define USER_INTERFACE(obj) G_TYPE_CHECK_INSTANCE_CAST ((obj), \
- G_TYPE_USER_INTERFACE, UserInterface)
-#define USER_INTERFACE_CLASS(klass) G_TYPE_CHECK_CLASS_CAST ((klass), \
- G_TYPE_USER_INTERFACE, \
- UserInterfaceClass)
-
-typedef struct _UserInterface UserInterface;
-typedef struct _UserInterfaceClass UserInterfaceClass;
-
-struct _UserInterface {
- GObject object;
- Map *map;
- MapSize *map_size;
-
- Display *dpy;
- Window x_win;
- Atom wm_delete_win;
- Atom wm_protocols;
- GC gc;
- GC buf_gc;
- Font text;
-
-#ifdef USE_MITSHM
-#include <sys/ipc.h>
-#include <sys/shm.h>
-#include <X11/extensions/XShm.h>
- XShmSegmentInfo shm_info;
- guchar use_mitshm = 1;
-#endif
-
- gint win_width;
- gint win_height;
-
- Pixmap win_buf;
-
- XImage *win_bufi;
- XImage *statusbar;
- XImage *space;
- XImage *food;
- XImage *wall;
- XImage *prize;
- XImage *baddie;
- XImage *robotDirs[4];
- XImage *robotPix;
-};
-
-struct _UserInterfaceClass {
- GObjectClass parent_class;
-};
-
-/* normal GObject stuff */
-GType user_interface_get_type (void);
-
-UserInterface* user_interface_new (Map* map);
-
-void user_interface_add_thing (UserInterface *ui,
- gint x,
- gint y,
- gint thing);
-
-void user_interface_run (UserInterface *ui);
-
-void user_interface_draw (UserInterface *ui);
-
-void user_interface_update_status (UserInterface *ui,
- const gchar *s,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_move_robot (UserInterface *ui,
- gint from_x,
- gint from_y,
- gint to_x,
- gint to_y,
- gint cdir,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_robot_smell (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_robot_zap (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_robot_feel (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_robot_grab (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_robot_look (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields);
-
-void user_interface_get_string (UserInterface *ui,
- gchar *prompt,
- gchar *buff,
- gint len);
-
-/* SYMBOLIC CONSTANTS */
-#define dist(f_x, f_y, t_x, t_y) (abs((f_x)-(t_x))+abs((f_y)-(t_y)))
-
-G_END_DECLS
-
-#endif /* __USER_INTERFACE_H__ */
diff --git a/src/Makefile.am b/src/Makefile.am
index b839875..75522e7 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -17,14 +17,16 @@
bin_PROGRAMS = gnurobots
-INCLUDES = $(GLIB2_CFLAGS) $(GUILE_CFLAGS) $(READLINE_CFLAGS) $(X_FLAGS) \
+INCLUDES = $(GUILE_CFLAGS) $(READLINE_CFLAGS) $(GTK2_CFLAGS) $(VTE_CFLAGS) \
+ $(GTHREAD2_CFLAGS) \
-I$(top_builddir)/include \
- -DPKGLIBDIR=\"$(pkglibdir)\" \
- -DABS_TOP_BUILDDIR=\"$(abs_top_builddir)\" \
- -DPKGDATADIR=\"$(pkgdatadir)\" \
- -DMAPS_PATH=\"$(mapsdir)\" \
- -DSCRIPTS_PATH=\"$(schemedir)\"
+ -DPKGLIBDIR=\"$(pkglibdir)\" \
+ -DABS_TOP_BUILDDIR=\"$(abs_top_builddir)\" \
+ -DPKGDATADIR=\"$(pkgdatadir)\" \
+ -DMAPS_PATH=\"$(mapsdir)\" \
+ -DSCRIPTS_PATH=\"$(schemedir)\"
-gnurobots_SOURCES = main.c api.c map.c grobot.c userinterface.c
-gnurobots_LDFLAGS = $(GLIB2_LIBS) $(GUILE_LDFLAGS) $(READLINE_LIBS) \
- $(X_LIBS) -lltdl -lgthread-2.0
+gnurobots_SOURCES = main.c api.c map.c grobot.c \
+ ui-window.c ui-cmdwin.c ui-arena.c
+gnurobots_LDFLAGS = $(GUILE_LDFLAGS) $(READLINE_LIBS) $(GTHREAD2_LIBS) \
+ $(GTK2_LIBS) $(VTE_LIBS) -lutil
diff --git a/src/grobot.c b/src/grobot.c
index 22eb777..bf3c394 100644
--- a/src/grobot.c
+++ b/src/grobot.c
@@ -19,7 +19,6 @@
#include "grobot.h"
#include "configs.h"
-#include "userinterface.h" /* GNU Robots UI */
#include <stdio.h>
#include <glib.h>
#include <string.h>
@@ -29,834 +28,798 @@ G_DEFINE_TYPE(GRobot, g_robot, G_TYPE_OBJECT)
enum
{
- DEATH,
- LAST_SIGNAL
+ DEATH,
+ LAST_SIGNAL
};
enum
{
- ARG_0,
- ARG_POS_X,
- ARG_POS_Y,
- ARG_DIRECTION,
- ARG_SCORE,
- ARG_ENERGY,
- ARG_SHIELDS,
- ARG_UNITS,
- ARG_SHOTS,
- ARG_USER_INTERFACE,
- ARG_MAP
+ ARG_0,
+ ARG_POS_X,
+ ARG_POS_Y,
+ ARG_DIRECTION,
+ ARG_SCORE,
+ ARG_ENERGY,
+ ARG_SHIELDS,
+ ARG_UNITS,
+ ARG_SHOTS,
+ ARG_USER_INTERFACE,
+ ARG_MAP
};
static gchar *things[] = { "space", "food", "prize", "wall", "baddie",
- "robot" };
+ "robot"
+};
static gint cthings[] = { SPACE, FOOD, PRIZE, WALL, BADDIE, ROBOT };
static guint g_robot_signals[LAST_SIGNAL] = { 0 };
-static void g_robot_dispose (GObject * object);
-static void g_robot_finalize (GObject * object);
+static void g_robot_dispose(GObject *object);
+static void g_robot_finalize(GObject *object);
-static void g_robot_set_property (GObject * object, guint prop_id,
- const GValue * value, GParamSpec * pspec);
+static void g_robot_set_property(GObject *object, guint prop_id,
+ const GValue *value, GParamSpec *pspec);
-static void g_robot_get_property (GObject * object, guint prop_id,
- GValue * value, GParamSpec * pspec);
+static void g_robot_get_property(GObject *object, guint prop_id,
+ GValue *value, GParamSpec * pspec);
static GObjectClass *parent_class = NULL;
-static gint what_thing (const gchar *th);
+static gint what_thing(const gchar *th);
-static void
-g_robot_init (GRobot* robot)
+static void g_robot_init(GRobot *robot)
{
- /* Nothing yet, need to do priv stuff */
+ /* Nothing yet, need to do priv stuff */
}
-static void
-g_robot_class_init (GRobotClass *klass)
+static void g_robot_class_init(GRobotClass *klass)
{
- GObjectClass *gobject_class;
-
- gobject_class = (GObjectClass *) klass;
-
- parent_class = g_type_class_ref (G_TYPE_OBJECT);
-
- gobject_class->dispose = g_robot_dispose;
- gobject_class->finalize = g_robot_finalize;
- gobject_class->set_property = g_robot_set_property;
- gobject_class->get_property = g_robot_get_property;
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_POS_X,
- g_param_spec_int ("x",
- "x",
- "X co-ordinate of current Position of the Robot",
- G_MININT,
- G_MAXINT,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_POS_Y,
- g_param_spec_int ("y",
- "y",
- "y co-ordinate of current Position of the Robot",
- G_MININT,
- G_MAXINT,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_DIRECTION,
- g_param_spec_int ("direction",
- "direction",
- "current Direction of the Robot",
- G_MININT,
- G_MAXINT,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_SCORE,
- g_param_spec_long ("score",
- "Score",
- "current Score of the Robot",
- G_MINLONG,
- G_MAXLONG,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_ENERGY,
- g_param_spec_long ("energy",
- "Energy",
- "current Energy-level of the Robot",
- G_MINLONG,
- G_MAXLONG,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_SHIELDS,
- g_param_spec_long ("shields",
- "Shields",
- "current Shield-level of the Robot",
- G_MINLONG,
- G_MAXLONG,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_UNITS,
- g_param_spec_long ("units",
- "Units",
- "Units walked by the Robot so far",
- G_MINLONG,
- G_MAXLONG,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_SHOTS,
- g_param_spec_long ("shots",
- "Shots",
- "Number of Shots fired by the Robot",
- G_MINLONG,
- G_MAXLONG,
- 0,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass),
- ARG_USER_INTERFACE,
- g_param_spec_object ("user-interface",
- "UserInterface",
- "Reference to the UI object",
- G_TYPE_OBJECT,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_MAP,
- g_param_spec_object ("map",
- "Map",
- "Reference to the Game Map object",
- G_TYPE_OBJECT,
- G_PARAM_READWRITE |
- G_PARAM_CONSTRUCT));
-
- g_robot_signals[DEATH] =
- g_signal_new ("death",
- G_TYPE_FROM_CLASS (klass),
- G_SIGNAL_RUN_LAST,
- G_STRUCT_OFFSET (GRobotClass, death),
- NULL,
- NULL,
- g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0,
- NULL);
+ GObjectClass *gobject_class;
+
+ gobject_class = (GObjectClass *) klass;
+
+ parent_class = g_type_class_ref(G_TYPE_OBJECT);
+
+ gobject_class->dispose = g_robot_dispose;
+ gobject_class->finalize = g_robot_finalize;
+ gobject_class->set_property = g_robot_set_property;
+ gobject_class->get_property = g_robot_get_property;
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_POS_X,
+ g_param_spec_int("x",
+ "x",
+ "X co-ordinate of current Position of the Robot",
+ G_MININT, G_MAXINT, 0, G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_POS_Y,
+ g_param_spec_int("y",
+ "y",
+ "y co-ordinate of current Position of the Robot",
+ G_MININT, G_MAXINT, 0, G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_DIRECTION,
+ g_param_spec_int("direction",
+ "direction",
+ "current Direction of the Robot",
+ G_MININT, G_MAXINT, 0, G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_SCORE,
+ g_param_spec_long("score",
+ "Score",
+ "current Score of the Robot",
+ G_MINLONG, G_MAXLONG, 0,
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_ENERGY,
+ g_param_spec_long("energy",
+ "Energy",
+ "current Energy-level of the Robot",
+ G_MINLONG, G_MAXLONG, 0,
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_SHIELDS,
+ g_param_spec_long("shields",
+ "Shields",
+ "current Shield-level of the Robot",
+ G_MINLONG, G_MAXLONG, 0,
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_UNITS,
+ g_param_spec_long("units",
+ "Units",
+ "Units walked by the Robot so far",
+ G_MINLONG, G_MAXLONG, 0,
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_SHOTS,
+ g_param_spec_long("shots",
+ "Shots",
+ "Number of Shots fired by the Robot",
+ G_MINLONG, G_MAXLONG, 0,
+ G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass),
+ ARG_USER_INTERFACE,
+ g_param_spec_object("user-interface",
+ "UserInterface",
+ "Reference to the UI object",
+ G_TYPE_OBJECT, G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_object_class_install_property(G_OBJECT_CLASS(klass), ARG_MAP,
+ g_param_spec_object("map",
+ "Map",
+ "Reference to the Game Map object",
+ G_TYPE_OBJECT, G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+ g_robot_signals[DEATH] =
+ g_signal_new("death",
+ G_TYPE_FROM_CLASS(klass),
+ G_SIGNAL_RUN_LAST,
+ G_STRUCT_OFFSET(GRobotClass, death),
+ NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0, NULL);
}
static void
-g_robot_set_property (GObject *object, guint prop_id, const GValue *value,
- GParamSpec *pspec)
+g_robot_set_property(GObject *object, guint prop_id, const GValue *value,
+ GParamSpec *pspec)
{
- GRobot *robot;
- GObject *obj;
-
- /* it's not null if we got it, but it might not be ours */
- g_return_if_fail (G_IS_ROBOT (object));
-
- robot = G_ROBOT (object);
-
- switch (prop_id)
- {
- case ARG_POS_X:
- robot->x = g_value_get_int (value);
- break;
- case ARG_POS_Y:
- robot->y = g_value_get_int (value);
- break;
- case ARG_DIRECTION:
- robot->dir = g_value_get_int (value);
- break;
- case ARG_SCORE:
- robot->score = g_value_get_long (value);
- break;
- case ARG_ENERGY:
- robot->energy = g_value_get_long (value);
- break;
- case ARG_SHIELDS:
- robot->shields = g_value_get_long (value);
- break;
- case ARG_SHOTS:
- robot->shots = g_value_get_long (value);
- break;
- case ARG_UNITS:
- robot->units = g_value_get_long (value);
- break;
- case ARG_USER_INTERFACE:
- if (robot->ui != NULL)
- {
- g_object_unref (robot->ui);
- }
-
- obj = g_value_get_object (value);
- if (obj != NULL)
- {
- robot->ui = g_object_ref (obj);
- }
-
- else
- {
- robot->ui = NULL;
- }
- break;
- case ARG_MAP:
- if (robot->map != NULL)
- {
- g_object_unref (robot->map);
- }
-
- obj = g_value_get_object (value);
- if (obj != NULL)
- {
- robot->map = g_object_ref (obj);
- }
-
- else
- {
- robot->map = NULL;
- }
- break;
- default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
- break;
- }
+ GRobot *robot;
+ GObject *obj;
+
+ /* it's not null if we got it, but it might not be ours */
+ g_return_if_fail(G_IS_ROBOT(object));
+
+ robot = G_ROBOT(object);
+
+ switch (prop_id)
+ {
+ case ARG_POS_X:
+ robot->x = g_value_get_int(value);
+ break;
+ case ARG_POS_Y:
+ robot->y = g_value_get_int(value);
+ break;
+ case ARG_DIRECTION:
+ robot->dir = g_value_get_int(value);
+ break;
+ case ARG_SCORE:
+ robot->score = g_value_get_long(value);
+ break;
+ case ARG_ENERGY:
+ robot->energy = g_value_get_long(value);
+ break;
+ case ARG_SHIELDS:
+ robot->shields = g_value_get_long(value);
+ break;
+ case ARG_SHOTS:
+ robot->shots = g_value_get_long(value);
+ break;
+ case ARG_UNITS:
+ robot->units = g_value_get_long(value);
+ break;
+ case ARG_USER_INTERFACE:
+ if (robot->ui != NULL)
+ {
+ g_object_unref(robot->ui);
+ }
+
+ obj = g_value_get_object(value);
+ if (obj != NULL)
+ {
+ robot->ui = g_object_ref(obj);
+ }
+
+ else
+ {
+ robot->ui = NULL;
+ }
+ break;
+ case ARG_MAP:
+ if (robot->map != NULL)
+ {
+ g_object_unref(robot->map);
+ }
+
+ obj = g_value_get_object(value);
+ if (obj != NULL)
+ {
+ robot->map = g_object_ref(obj);
+ }
+
+ else
+ {
+ robot->map = NULL;
+ }
+ break;
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
+ break;
+ }
}
static void
-g_robot_get_property (GObject *object, guint prop_id, GValue *value,
- GParamSpec *pspec)
+g_robot_get_property(GObject *object, guint prop_id, GValue *value,
+ GParamSpec *pspec)
{
- GRobot *robot;
-
- /* it's not null if we got it, but it might not be ours */
- g_return_if_fail (G_IS_ROBOT (object));
-
- robot = G_ROBOT (object);
-
- switch (prop_id)
- {
- case ARG_POS_X:
- g_value_set_int (value, robot->x);
- break;
- case ARG_POS_Y:
- g_value_set_int (value, robot->y);
- break;
- case ARG_DIRECTION:
- g_value_set_int (value, robot->dir);
- break;
- case ARG_SCORE:
- g_value_set_long (value, robot->score);
- break;
- case ARG_ENERGY:
- g_value_set_long (value, robot->energy);
- break;
- case ARG_SHIELDS:
- g_value_set_long (value, robot->shields);
- break;
- case ARG_SHOTS:
- g_value_set_long (value, robot->shots);
- break;
- case ARG_UNITS:
- g_value_set_long (value, robot->units);
- break;
- case ARG_USER_INTERFACE:
- g_value_set_object (value, g_object_ref (G_OBJECT (robot->ui)));
- break;
- case ARG_MAP:
- g_value_set_object (value, g_object_ref (G_OBJECT (robot->map)));
- break;
- default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
- break;
- }
+ GRobot *robot;
+
+ /* it's not null if we got it, but it might not be ours */
+ g_return_if_fail(G_IS_ROBOT(object));
+
+ robot = G_ROBOT(object);
+
+ switch (prop_id)
+ {
+ case ARG_POS_X:
+ g_value_set_int(value, robot->x);
+ break;
+ case ARG_POS_Y:
+ g_value_set_int(value, robot->y);
+ break;
+ case ARG_DIRECTION:
+ g_value_set_int(value, robot->dir);
+ break;
+ case ARG_SCORE:
+ g_value_set_long(value, robot->score);
+ break;
+ case ARG_ENERGY:
+ g_value_set_long(value, robot->energy);
+ break;
+ case ARG_SHIELDS:
+ g_value_set_long(value, robot->shields);
+ break;
+ case ARG_SHOTS:
+ g_value_set_long(value, robot->shots);
+ break;
+ case ARG_UNITS:
+ g_value_set_long(value, robot->units);
+ break;
+ case ARG_USER_INTERFACE:
+ g_value_set_object(value, g_object_ref(G_OBJECT(robot->ui)));
+ break;
+ case ARG_MAP:
+ g_value_set_object(value, g_object_ref(G_OBJECT(robot->map)));
+ break;
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
+ break;
+ }
}
-GRobot *
-g_robot_new (gint x, gint y, gint dir, glong score, glong energy,
- glong shields, glong units, glong shots, UserInterface *ui,
- Map *map)
+GRobot *g_robot_new(gint x, gint y, gint dir, glong score, glong energy,
+ glong shields, glong units, glong shots, UIArena *ui, Map *map)
{
- return G_ROBOT(g_object_new (g_robot_get_type(),
- "x", x,
- "y", y,
- "direction", dir,
- "score", score,
- "energy", energy,
- "shields", shields,
- "units", units,
- "shots", shots,
- "user_interface", ui, "map", map, NULL));
+ return G_ROBOT(g_object_new(g_robot_get_type(),
+ "x", x,
+ "y", y,
+ "direction", dir,
+ "score", score,
+ "energy", energy,
+ "shields", shields,
+ "units", units,
+ "shots", shots, "user_interface", ui, "map", map, NULL));
}
-static void
-g_robot_dispose (GObject *object)
+static void g_robot_dispose(GObject *object)
{
- GRobot *robot = G_ROBOT (object);
+ GRobot *robot = G_ROBOT(object);
- if (robot->ui != NULL)
- {
- g_object_unref (G_OBJECT (robot->ui));
- }
+ if (robot->ui != NULL)
+ {
+ g_object_unref(G_OBJECT(robot->ui));
+ }
- if (robot->map != NULL)
- {
- g_object_unref (G_OBJECT (robot->map));
- }
+ if (robot->map != NULL)
+ {
+ g_object_unref(G_OBJECT(robot->map));
+ }
- parent_class->dispose (object);
+ parent_class->dispose(object);
}
-static void
-g_robot_finalize (GObject *object)
+static void g_robot_finalize(GObject *object)
{
- parent_class->finalize (object);
+ parent_class->finalize(object);
}
-void
-g_robot_turn (GRobot *robot, gint num_turns)
+void g_robot_turn(GRobot *robot, gint num_turns)
{
- gint i;
- gint incr;
+ gint i;
+ gint incr;
- /* turn left or right? */
+ /* turn left or right? */
- incr = sign(num_turns);
+ incr = sign(num_turns);
- for (i = 0; i < abs (num_turns); i++)
- {
- robot->dir += incr;
+ for (i = 0; i < abs(num_turns); i++)
+ {
+ robot->dir += incr;
- if (robot->dir > 3)
- {
- robot->dir = 0;
- }
+ if (robot->dir > 3)
+ {
+ robot->dir = 0;
+ }
- else if (robot->dir < 0)
- {
- robot->dir = 3;
- }
+ else if (robot->dir < 0)
+ {
+ robot->dir = 3;
+ }
- /* animate the robot */
- user_interface_move_robot (robot->ui, robot->x, robot->y, robot->x,
- robot->y, robot->dir, robot->energy,
- robot->score, robot->shields);
+ /* animate the robot */
+ gdk_threads_enter();
+ ui_arena_move_robot(robot->ui, robot->x, robot->y, robot->x,
+ robot->y, robot->dir, robot->energy,
+ robot->score, robot->shields);
+ gdk_threads_leave();
- robot->energy -= 2;
+ robot->energy -= 2;
- if (robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- } /* for */
+ if (robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ } /* for */
}
-gboolean
-g_robot_move (GRobot *robot, gint steps)
+gboolean g_robot_move(GRobot *robot, gint steps)
{
- gint x_to, y_to;
- gint dx, dy;
- gint i;
-
- g_return_val_if_fail (robot->ui != NULL && robot->map != NULL, FALSE);
-
- /* determine changes to x,y */
-
- switch (robot->dir)
- {
- case NORTH: /* N */
- dx = 0;
- dy = -1 * sign (steps);
- break;
- case EAST: /* E */
- dx = sign (steps);
- dy = 0;
- break;
- case SOUTH: /* S */
- dx = 0;
- dy = sign (steps);
- break;
- case WEST: /* W */
- dx = -1 * sign (steps);
- dy = 0;
- break;
- }
-
- /* Move the robot */
-
- for (i = 0; i < abs (steps); i++)
- {
- /* check for a space */
-
- x_to = robot->x + dx;
- y_to = robot->y + dy;
-
- /* no matter what, this took energy */
-
- robot->energy -= 2;
- if (robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
-
- switch (MAP_GET_OBJECT (robot->map, x_to, y_to))
- {
- case SPACE:
- /* move the robot there */
- MAP_SET_OBJECT (robot->map, robot->x, robot->y, SPACE);
- MAP_SET_OBJECT (robot->map, x_to, y_to, ROBOT);
-
- user_interface_move_robot (robot->ui, robot->x, robot->y, x_to, y_to,
- robot->dir, robot->energy, robot->score,
- robot->shields);
-
- robot->x = x_to;
- robot->y = y_to;
- robot->units++;
-
- break;
-
- case BADDIE:
- /* Damage */
- robot->shields -= 10;
- if (robot->shields < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- return FALSE;
-
- break;
-
- case WALL:
- /* less damage */
- robot->shields -= 2;
- if (robot->shields < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- return FALSE;
-
- break;
-
- default:
- /* even less damage */
- if (--robot->shields < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- return FALSE;
-
- break;
- }
- } /* for */
-
- return TRUE;
+ gint x_to, y_to;
+ gint dx, dy;
+ gint i;
+
+ g_return_val_if_fail(robot->ui != NULL && robot->map != NULL, FALSE);
+
+ /* determine changes to x,y */
+
+ switch (robot->dir)
+ {
+ case NORTH: /* N */
+ dx = 0;
+ dy = -1 * sign(steps);
+ break;
+ case EAST: /* E */
+ dx = sign(steps);
+ dy = 0;
+ break;
+ case SOUTH: /* S */
+ dx = 0;
+ dy = sign(steps);
+ break;
+ case WEST: /* W */
+ dx = -1 * sign(steps);
+ dy = 0;
+ break;
+ }
+
+ /* Move the robot */
+
+ for (i = 0; i < abs(steps); i++)
+ {
+ /* check for a space */
+
+ x_to = robot->x + dx;
+ y_to = robot->y + dy;
+
+ /* no matter what, this took energy */
+
+ robot->energy -= 2;
+ if (robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+
+ switch (MAP_GET_OBJECT(robot->map, x_to, y_to))
+ {
+ case SPACE:
+ /* move the robot there */
+ MAP_SET_OBJECT(robot->map, robot->x, robot->y, SPACE);
+ MAP_SET_OBJECT(robot->map, x_to, y_to, ROBOT);
+
+ gdk_threads_enter();
+ ui_arena_move_robot(robot->ui, robot->x, robot->y, x_to, y_to,
+ robot->dir, robot->energy, robot->score, robot->shields);
+ gdk_threads_leave();
+
+ robot->x = x_to;
+ robot->y = y_to;
+ robot->units++;
+
+ break;
+
+ case BADDIE:
+ /* Damage */
+ robot->shields -= 10;
+ if (robot->shields < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ return FALSE;
+
+ break;
+
+ case WALL:
+ /* less damage */
+ robot->shields -= 2;
+ if (robot->shields < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ return FALSE;
+
+ break;
+
+ default:
+ /* even less damage */
+ if (--robot->shields < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ return FALSE;
+
+ break;
+ }
+ } /* for */
+
+ return TRUE;
}
-gboolean
-g_robot_smell (GRobot *robot, gchar *str)
+gboolean g_robot_smell(GRobot *robot, gchar *str)
{
- gint th;
- gint i, j;
+ gint th;
+ gint i, j;
- g_return_val_if_fail (robot->ui != NULL && robot->map != NULL, FALSE);
+ g_return_val_if_fail(robot->ui != NULL && robot->map != NULL, FALSE);
- th = what_thing (str);
+ th = what_thing(str);
- /* no matter what, this took energy */
+ /* no matter what, this took energy */
- if (--robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
+ if (--robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
- user_interface_robot_smell (robot->ui, robot->x, robot->y, robot->dir,
- robot->energy, robot->score, robot->shields);
+ gdk_threads_enter();
+ ui_arena_robot_smell(robot->ui, robot->x, robot->y, robot->dir,
+ robot->energy, robot->score, robot->shields);
+ gdk_threads_leave();
- /* Smell for the thing */
+ /* Smell for the thing */
- for (i = robot->x - 1; i <= robot->x + 1; i++)
- {
- for (j = robot->y - 1; j <= robot->y + 1; j++)
- {
- if (!(i == robot->x && j == robot->y)
- && MAP_GET_OBJECT (robot->map, i, j) == th)
- {
- /* Found it */
- return TRUE;
- }
- } /* for */
- } /* for */
+ for (i = robot->x - 1; i <= robot->x + 1; i++)
+ {
+ for (j = robot->y - 1; j <= robot->y + 1; j++)
+ {
+ if (!(i == robot->x && j == robot->y)
+ && MAP_GET_OBJECT(robot->map, i, j) == th)
+ {
+ /* Found it */
+ return TRUE;
+ }
+ } /* for */
+ } /* for */
- /* Failed to find it */
+ /* Failed to find it */
- return FALSE;
+ return FALSE;
}
-gboolean
-g_robot_feel (GRobot *robot, gchar *str)
+gboolean g_robot_feel(GRobot *robot, gchar *str)
{
- gint th;
- gint x_to, y_to;
- gint dx, dy;
-
- g_return_val_if_fail (robot->ui != NULL && robot->map != NULL, FALSE);
-
- th = what_thing (str);
-
- /* determine changes to x,y */
- switch (robot->dir)
- {
- case NORTH: /* N */
- dx = 0;
- dy = -1;
- break;
- case EAST: /* E */
- dx = 1;
- dy = 0;
- break;
- case SOUTH: /* S */
- dx = 0;
- dy = 1;
- break;
- case WEST: /* W */
- dx = -1;
- dy = 0;
- break;
- }
-
- /* no matter what, this took energy */
- if (--robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
-
- /* Feel for the thing */
- x_to = robot->x + dx;
- y_to = robot->y + dy;
-
- user_interface_robot_feel (robot->ui,
- robot->x, robot->y,
- robot->dir, x_to, y_to,
- robot->energy, robot->score, robot->shields);
-
- if (MAP_GET_OBJECT (robot->map, x_to, y_to) == BADDIE)
- {
- /* touching a baddie is hurtful */
- if (robot->shields < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- }
-
- if (MAP_GET_OBJECT (robot->map, x_to, y_to) == th)
- {
- return TRUE;
- }
-
- /* Did not feel it */
- return FALSE;
+ gint th;
+ gint x_to, y_to;
+ gint dx, dy;
+
+ g_return_val_if_fail(robot->ui != NULL && robot->map != NULL, FALSE);
+
+ th = what_thing(str);
+
+ /* determine changes to x,y */
+ switch (robot->dir)
+ {
+ case NORTH: /* N */
+ dx = 0;
+ dy = -1;
+ break;
+ case EAST: /* E */
+ dx = 1;
+ dy = 0;
+ break;
+ case SOUTH: /* S */
+ dx = 0;
+ dy = 1;
+ break;
+ case WEST: /* W */
+ dx = -1;
+ dy = 0;
+ break;
+ }
+
+ /* no matter what, this took energy */
+ if (--robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+
+ /* Feel for the thing */
+ x_to = robot->x + dx;
+ y_to = robot->y + dy;
+
+ gdk_threads_enter();
+ ui_arena_robot_feel(robot->ui, robot->x, robot->y, robot->dir, x_to,
+ y_to, robot->energy, robot->score, robot->shields);
+ gdk_threads_leave();
+
+ if (MAP_GET_OBJECT(robot->map, x_to, y_to) == BADDIE)
+ {
+ /* touching a baddie is hurtful */
+ if (robot->shields < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ }
+
+ if (MAP_GET_OBJECT(robot->map, x_to, y_to) == th)
+ {
+ return TRUE;
+ }
+
+ /* Did not feel it */
+ return FALSE;
}
-gboolean
-g_robot_look (GRobot *robot, gchar *str)
+gboolean g_robot_look(GRobot *robot, gchar *str)
{
- gint th;
- gint x_to, y_to;
- gint dx, dy;
-
- g_return_val_if_fail (robot->ui != NULL && robot->map != NULL, FALSE);
-
- th = what_thing (str);
-
- /* determine changes to x,y */
- switch (robot->dir)
- {
- case 0: /* N */
- dx = 0;
- dy = -1;
- break;
- case 1: /* E */
- dx = 1;
- dy = 0;
- break;
- case 2: /* S */
- dx = 0;
- dy = 1;
- break;
- case 3: /* W */
- dx = -1;
- dy = 0;
- break;
- }
-
- /* no matter what, this took energy */
- if (--robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
-
- /* Look for the thing */
- x_to = robot->x + dx;
- y_to = robot->y + dy;
-
- user_interface_robot_look (robot->ui,
- robot->x, robot->y,
- robot->dir, x_to, y_to,
- robot->energy, robot->score, robot->shields);
-
- while (MAP_GET_OBJECT (robot->map, x_to, y_to) == SPACE)
- {
- /* move the focus */
- x_to += dx;
- y_to += dy;
- }
-
- /* Outside the loop, we have found something */
- if (MAP_GET_OBJECT (robot->map, x_to, y_to) == th)
- {
- return TRUE;
- }
-
- /* else, we did not find it */
- return FALSE;
+ gint th;
+ gint x_to, y_to;
+ gint dx, dy;
+
+ g_return_val_if_fail(robot->ui != NULL && robot->map != NULL, FALSE);
+
+ th = what_thing(str);
+
+ /* determine changes to x,y */
+ switch (robot->dir)
+ {
+ case 0: /* N */
+ dx = 0;
+ dy = -1;
+ break;
+ case 1: /* E */
+ dx = 1;
+ dy = 0;
+ break;
+ case 2: /* S */
+ dx = 0;
+ dy = 1;
+ break;
+ case 3: /* W */
+ dx = -1;
+ dy = 0;
+ break;
+ }
+
+ /* no matter what, this took energy */
+ if (--robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+
+ /* Look for the thing */
+ x_to = robot->x + dx;
+ y_to = robot->y + dy;
+
+ gdk_threads_enter();
+ ui_arena_robot_look(robot->ui, robot->x, robot->y, robot->dir, x_to,
+ y_to, robot->energy, robot->score, robot->shields);
+ gdk_threads_leave();
+
+ while (MAP_GET_OBJECT(robot->map, x_to, y_to) == SPACE)
+ {
+ /* move the focus */
+ x_to += dx;
+ y_to += dy;
+ }
+
+ /* Outside the loop, we have found something */
+ if (MAP_GET_OBJECT(robot->map, x_to, y_to) == th)
+ {
+ return TRUE;
+ }
+
+ /* else, we did not find it */
+ return FALSE;
}
-gboolean
-g_robot_grab (GRobot *robot)
+gboolean g_robot_grab(GRobot *robot)
{
- gint x_to, y_to;
- gint dx, dy;
-
- g_return_val_if_fail (robot->ui != NULL && robot->map != NULL, FALSE);
-
- /* determine changes to x,y */
-
- switch (robot->dir)
- {
- case NORTH: /* N */
- dx = 0;
- dy = -1;
- break;
- case EAST: /* E */
- dx = 1;
- dy = 0;
- break;
- case SOUTH: /* S */
- dx = 0;
- dy = 1;
- break;
- case WEST: /* W */
- dx = -1;
- dy = 0;
- break;
- }
-
- /* Try to grab the thing */
-
- x_to = robot->x + dx;
- y_to = robot->y + dy;
-
- robot->energy -= 5;
- if (robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
-
- user_interface_robot_grab (robot->ui, robot->x, robot->y, robot->dir, x_to,
- y_to, robot->energy, robot->score,
- robot->shields);
-
- /* Did we grab it? */
-
- switch (MAP_GET_OBJECT (robot->map, x_to, y_to))
- {
- case SPACE:
- case WALL:
- case ROBOT:
- return FALSE;
- break;
-
- case BADDIE:
- robot->shields -= 10;
- if (robot->shields < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- return (FALSE);
-
- case FOOD:
- /* I want the net gain to be +10 */
- robot->energy += 15;
- break;
-
- case PRIZE:
- robot->score++;
- break;
- }
-
- /* only successful grabs get here */
- MAP_SET_OBJECT (robot->map, x_to, y_to, SPACE);
- user_interface_add_thing (robot->ui, x_to, y_to, SPACE);
-
- return TRUE;
+ gint x_to, y_to;
+ gint dx, dy;
+
+ g_return_val_if_fail(robot->ui != NULL && robot->map != NULL, FALSE);
+
+ /* determine changes to x,y */
+
+ switch (robot->dir)
+ {
+ case NORTH: /* N */
+ dx = 0;
+ dy = -1;
+ break;
+ case EAST: /* E */
+ dx = 1;
+ dy = 0;
+ break;
+ case SOUTH: /* S */
+ dx = 0;
+ dy = 1;
+ break;
+ case WEST: /* W */
+ dx = -1;
+ dy = 0;
+ break;
+ }
+
+ /* Try to grab the thing */
+
+ x_to = robot->x + dx;
+ y_to = robot->y + dy;
+
+ robot->energy -= 5;
+ if (robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+
+ gdk_threads_enter();
+ ui_arena_robot_grab(robot->ui, robot->x, robot->y, robot->dir, x_to,
+ y_to, robot->energy, robot->score, robot->shields);
+ gdk_threads_leave();
+
+ /* Did we grab it? */
+
+ switch (MAP_GET_OBJECT(robot->map, x_to, y_to))
+ {
+ case SPACE:
+ case WALL:
+ case ROBOT:
+ return FALSE;
+ break;
+
+ case BADDIE:
+ robot->shields -= 10;
+ if (robot->shields < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ return (FALSE);
+
+ case FOOD:
+ /* I want the net gain to be +10 */
+ robot->energy += 15;
+ break;
+
+ case PRIZE:
+ robot->score++;
+ break;
+ }
+
+ /* only successful grabs get here */
+ MAP_SET_OBJECT(robot->map, x_to, y_to, SPACE);
+ gdk_threads_enter();
+ ui_arena_add_thing(robot->ui, x_to, y_to, SPACE);
+ gdk_threads_leave();
+
+ return TRUE;
}
-gboolean
-g_robot_zap (GRobot *robot)
+gboolean g_robot_zap(GRobot *robot)
{
- gint x_to, y_to;
- gint dx, dy;
-
- g_return_val_if_fail (robot->ui != NULL && robot->map != NULL, FALSE);
-
- /* determine changes to x,y */
-
- switch (robot->dir)
- {
- case NORTH: /* N */
- dx = 0;
- dy = -1;
- break;
- case EAST: /* E */
- dx = 1;
- dy = 0;
- break;
- case SOUTH: /* S */
- dx = 0;
- dy = 1;
- break;
- case WEST: /* W */
- dx = -1;
- dy = 0;
- break;
- }
-
- /* Try to zap the thing */
-
- x_to = robot->x + dx;
- y_to = robot->y + dy;
-
- robot->energy -= 10;
- if (robot->energy < 1)
- {
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
- }
- robot->shots++;
- user_interface_robot_zap (robot->ui, robot->x, robot->y, robot->dir, x_to,
- y_to, robot->energy, robot->score,
- robot->shields);
-
- /* Did we destroy it? */
- switch (MAP_GET_OBJECT (robot->map, x_to, y_to))
- {
- case SPACE:
- case WALL:
- case ROBOT: /* what to w/ robots? */
- return (FALSE);
- break;
-
- case BADDIE:
- case FOOD:
- case PRIZE:
- user_interface_add_thing (robot->ui, x_to, y_to, SPACE);
- break;
- }
-
- /* only success gets here */
- MAP_SET_OBJECT (robot->map, x_to, y_to, SPACE);
- user_interface_add_thing (robot->ui, x_to, y_to, SPACE);
-
- return TRUE;
+ gint x_to, y_to;
+ gint dx, dy;
+
+ g_return_val_if_fail(robot->ui != NULL && robot->map != NULL, FALSE);
+
+ /* determine changes to x,y */
+
+ switch (robot->dir)
+ {
+ case NORTH: /* N */
+ dx = 0;
+ dy = -1;
+ break;
+ case EAST: /* E */
+ dx = 1;
+ dy = 0;
+ break;
+ case SOUTH: /* S */
+ dx = 0;
+ dy = 1;
+ break;
+ case WEST: /* W */
+ dx = -1;
+ dy = 0;
+ break;
+ }
+
+ /* Try to zap the thing */
+
+ x_to = robot->x + dx;
+ y_to = robot->y + dy;
+
+ robot->energy -= 10;
+ if (robot->energy < 1)
+ {
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
+ }
+ robot->shots++;
+ gdk_threads_enter();
+ ui_arena_robot_zap(robot->ui, robot->x, robot->y, robot->dir, x_to,
+ y_to, robot->energy, robot->score, robot->shields);
+ gdk_threads_leave();
+
+ /* Did we destroy it? */
+ switch (MAP_GET_OBJECT(robot->map, x_to, y_to))
+ {
+ case SPACE:
+ case WALL:
+ case ROBOT: /* what to w/ robots? */
+ return (FALSE);
+ break;
+
+ case BADDIE:
+ case FOOD:
+ case PRIZE:
+ gdk_threads_enter();
+ ui_arena_add_thing(robot->ui, x_to, y_to, SPACE);
+ gdk_threads_leave();
+ break;
+ }
+
+ /* only success gets here */
+ MAP_SET_OBJECT(robot->map, x_to, y_to, SPACE);
+ gdk_threads_enter();
+ ui_arena_add_thing(robot->ui, x_to, y_to, SPACE);
+ gdk_threads_leave();
+
+ return TRUE;
}
-gboolean
-g_robot_stop (GRobot *robot)
+gboolean g_robot_stop(GRobot *robot)
{
- /* Must be a SCM function, even though it returns no value */
- /* Stop the robot immediately */
+ /* Must be a SCM function, even though it returns no value */
+ /* Stop the robot immediately */
- g_signal_emit (robot, g_robot_signals[DEATH], 0);
+ g_signal_emit(robot, g_robot_signals[DEATH], 0);
- return TRUE; /* never gets here */
+ return TRUE; /* never gets here */
}
-static gint
-what_thing (const gchar *th)
+static gint what_thing(const gchar *th)
{
- /* what_thing - this function scans the list of possible things
- (strings) and returns a cthing. Returns -1 if not found in the
- list. */
-
- /* My idea here is that by return -1 on error, this won't match
- anything in the list of cthings. That way, the function that
- uses what_thing to determine the cthing doesn't have to care if
- the call failed or not. This helps me keep the code simple,
- since now I don't have to add a branch for failure, but which
- also decrements energy. */
-
- gint i;
-
- for (i = 0; i < 6; i++)
- {
- if (strcmp (th, things[i]) == 0)
- {
- return cthings[i];
- }
- } /* for */
-
- /* not found */
-
- return -1;
+ /* what_thing - this function scans the list of possible things
+ (strings) and returns a cthing. Returns -1 if not found in the
+ list. */
+
+ /* My idea here is that by return -1 on error, this won't match
+ anything in the list of cthings. That way, the function that
+ uses what_thing to determine the cthing doesn't have to care if
+ the call failed or not. This helps me keep the code simple,
+ since now I don't have to add a branch for failure, but which
+ also decrements energy. */
+
+ gint i;
+
+ for (i = 0; i < 6; i++)
+ {
+ if (strcmp(th, things[i]) == 0)
+ {
+ return cthings[i];
+ }
+ } /* for */
+
+ /* not found */
+
+ return -1;
}
diff --git a/src/main.c b/src/main.c
index 16dfaf1..3e24e78 100644
--- a/src/main.c
+++ b/src/main.c
@@ -19,254 +19,255 @@
*/
#include <stdio.h>
-#include <unistd.h> /* for getopt */
-#include <string.h> /* for strdup */
+#include <unistd.h> /* for getopt */
+#include <string.h> /* for strdup */
#include <glib.h>
#include <glib/gprintf.h>
#include <libguile.h>
-#include <getopt.h> /* for GNU getopt_long */
+#include <getopt.h> /* for GNU getopt_long */
-#include "grobot.h" /* the robot structure, and robot manipulation
- routines */
+#include "grobot.h" /* the robot structure, and robot manipulation
+ routines */
-#include "api.h" /* robot API, as Scheme functions */
-#include "userinterface.h"
+#include "api.h" /* robot API, as Scheme functions */
+#include "ui-cmdwin.h"
+#include "ui-arena.h"
+#include "ui-window.h"
+#include "ui-window-private.h"
#include "config.h"
#include "configs.h"
-#include "map.h" /* Game Map */
-#include "main.h" /* for this source file */
+#include "map.h" /* Game Map */
+#include "main.h" /* for this source file */
#define BUFF_LEN 1024
/* Globals (share with api.c) */
GList *robots = NULL;
-GRobot *robot = NULL; /* The current robot */
-UserInterface *ui;
+GRobot *robot = NULL; /* The current robot */
+UIWindow *ui;
+UIArena *arena;
Map *map;
gpointer callback(gpointer data);
-SCM catch_handler (void *data, SCM tag, SCM throw_args);
-gint is_file_readable (const gchar *filename);
+SCM catch_handler(void *data, SCM tag, SCM throw_args);
+gint is_file_readable(const gchar * filename);
/************************************************************************
* gint main(gint argc, gchar *argv[]) *
* *
* Entry point *
************************************************************************/
-gint
-main (gint argc, gchar *argv[])
+gint main(gint argc, gchar *argv[])
{
- gint opt; /* the option read from getopt */
- gint flag; /* flag passed back from getopt - NOT USED */
-
- gchar maps_path[MAX_PATH], scripts_path[MAX_PATH];
-
- gchar *main_argv[5] = { "GNU Robots",
- NULL,
- NULL,
- NULL,
- NULL
- };
-
- struct option long_opts[] = {
- {"version", 0, NULL, 'V'},
- {"help", 0, NULL, 'h'},
- {"map-file", 1, NULL, 'f'},
- {"shields", 1, NULL, 's'},
- {"energy", 1, NULL, 'e'},
- {NULL, 0, NULL, 0}
- };
-
- /* Initialize the GType system first */
- g_type_init ();
-
- /* Check command line */
-
- /* Create a robot Object */
- robot = g_robot_new (1, 1, 1, 0, DEFAULT_ENERGY, DEFAULT_SHIELDS, 0, 0,
- NULL, NULL);
-
- g_assert (robot != NULL);
-
- /* And add to to the list of robots */
- robots = g_list_append (robots, robot);
-
- while ((opt = getopt_long (argc, argv, "Vhf:s:e:p:", long_opts,
- &flag)) != EOF)
- {
- switch (opt)
- {
- case 'V':
- /* Display version, then quit */
- g_printf ("%s\n\n", PKGINFO);
- g_printf ("%s\n\n", COPYRIGHT);
- g_printf
- ("GNU Robots is free software: you can redistribute it and/or modify\n"
- "it under the terms of the GNU General Public License as published by\n"
- "the Free Software Foundation, either version 3 of the License, or\n"
- "(at your option) any later version.\n");
- g_printf
- ("\nGNU Robots is distributed in the hope that it will be useful,\n"
- "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
- "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n"
- "GNU General Public License for more details.\n");
- g_printf
- ("\nYou should have received a copy of the GNU General Public License\n"
- "along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.\n");
-
- exit (0);
- break;
-
- case 'h':
- /* Display help, then quit. */
- usage (argv[0]);
- exit (0);
- break;
-
- case 'f':
- /* Set map file */
- main_argv[1] = optarg; /* pointer assignment */
- break;
-
- case 's':
- /* Set shields */
- robot->shields = (glong) atol (optarg);
- break;
-
- case 'e':
- /* Set energy */
- robot->energy = (glong) atol (optarg);
- break;
-
- default:
- /* invalid option */
- usage (argv[0]);
- exit (1);
- break;
- } /* switch */
- } /* while */
-
- /* Extra arg is the Scheme file */
-
- if (optind < argc)
- {
- /* Set Scheme file */
- main_argv[2] = argv[optind]; /* pointer assignment */
- }
-
- /* Check that files have been given */
- if (main_argv[1] == NULL)
- {
- main_argv[1] = g_malloc (MAX_PATH);
- g_strlcpy (main_argv[1], DEFAULT_MAP, MAX_PATH);
- g_fprintf (stderr, "map file not specified, trying default: %s\n",
- main_argv[1]);
- }
-
- /* Check that files exist */
- g_strlcpy (maps_path, main_argv[1], MAX_PATH);
-
- if (!is_file_readable (maps_path))
- {
- g_strlcpy (maps_path, MAPS_PATH, MAX_PATH);
- g_strlcat (maps_path, "/", MAX_PATH);
- g_strlcat (maps_path, main_argv[1], MAX_PATH);
-
- if (!is_file_readable (maps_path))
- {
- gchar *env = getenv (MAPS_PATH_ENV);
-
- if (env != NULL)
- {
- g_strlcpy (maps_path, env, MAX_PATH);
- g_strlcat (maps_path, "/", MAX_PATH);
- g_strlcat (maps_path, main_argv[1], MAX_PATH);
-
- if (!is_file_readable (maps_path))
- {
- g_fprintf (stderr,
- "%s: %s: game map file does not exist or is not \
- readable\n",
- argv[0], main_argv[1]);
- exit (1);
- }
- }
- else
- {
- g_fprintf (stderr,
- "%s: %s: game map file does not exist or is not readable\n",
- argv[0], main_argv[1]);
- exit (1);
- }
- }
- }
-
- main_argv[1] = maps_path;
-
- /* Now the Scheme file */
- if (main_argv[2] != NULL)
- {
- g_strlcpy (scripts_path, main_argv[2], MAX_PATH);
-
- if (!is_file_readable (scripts_path))
- {
- g_strlcpy (scripts_path, SCRIPTS_PATH, MAX_PATH);
- g_strlcat (scripts_path, "/", MAX_PATH);
- g_strlcat (scripts_path, main_argv[2], MAX_PATH);
-
- if (!is_file_readable (scripts_path))
- {
- gchar *env = getenv (SCRIPTS_PATH_ENV);
-
- if (env != NULL)
- {
- g_strlcpy (scripts_path, env, MAX_PATH);
- g_strlcat (scripts_path, "/", MAX_PATH);
- g_strlcat (scripts_path, main_argv[2], MAX_PATH);
-
- if (!is_file_readable (scripts_path))
- {
- g_fprintf (stderr,
- "%s: %s: Scheme file does not exist or is not \
- readable\n",
- argv[0], main_argv[2]);
- exit (1);
- }
- }
- else
- {
- g_fprintf (stderr,
- "%s: %s: Scheme file does not exist or is not readable\n",
- argv[0], main_argv[2]);
- exit (1);
- }
- }
- }
-
- main_argv[2] = scripts_path;
- }
- else
- {
- /* argv[2] can't be NULL as argv[3] may also be NULL */
- main_argv[2] = "";
- }
-
- /* Start Guile environment. Does not exit */
- g_printf ("%s\n", PKGINFO);
- g_printf ("%s\n", COPYRIGHT);
- g_printf ("GNU Robots comes with ABSOLUTELY NO WARRANTY\n");
- g_printf
- ("This is free software, and you are welcome to redistribute it\n");
- g_printf
- ("under certain conditions; see the file `COPYING' for details.\n");
- g_printf ("Loading Guile ... Please wait\n\n");
-
- scm_boot_guile (3, main_argv, main_prog, NULL);
-
- return 0; /* never gets here, but keeps compiler happy */
+ gint opt; /* the option read from getopt */
+ gint flag; /* flag passed back from getopt - NOT USED */
+
+ gchar maps_path[MAX_PATH], scripts_path[MAX_PATH];
+
+ gchar *main_argv[5] = { "GNU Robots",
+ NULL,
+ NULL,
+ NULL,
+ NULL
+ };
+
+ struct option long_opts[] = {
+ {"version", 0, NULL, 'V'},
+ {"help", 0, NULL, 'h'},
+ {"map-file", 1, NULL, 'f'},
+ {"shields", 1, NULL, 's'},
+ {"energy", 1, NULL, 'e'},
+ {NULL, 0, NULL, 0}
+ };
+
+ /* Initialize the GType system first */
+ g_type_init();
+
+ /* Check command line */
+
+ /* Create a robot Object */
+ robot = g_robot_new(1, 1, 1, 0, DEFAULT_ENERGY, DEFAULT_SHIELDS, 0, 0,
+ NULL, NULL);
+
+ g_assert(robot != NULL);
+
+ /* And add to to the list of robots */
+ robots = g_list_append(robots, robot);
+
+ while ((opt = getopt_long(argc, argv, "Vhf:s:e:p:", long_opts,
+ &flag)) != EOF)
+ {
+ switch (opt)
+ {
+ case 'V':
+ /* Display version, then quit */
+ g_printf("%s\n\n", PKGINFO);
+ g_printf("%s\n\n", COPYRIGHT);
+ g_printf
+("GNU Robots is free software: you can redistribute it and/or modify\n"
+ "it under the terms of the GNU General Public License as published by\n"
+ "the Free Software Foundation, either version 3 of the License, or\n"
+ "(at your option) any later version.\n");
+ g_printf
+("\nGNU Robots is distributed in the hope that it will be useful,\n"
+ "but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
+ "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n"
+ "GNU General Public License for more details.\n");
+ g_printf
+("\nYou should have received a copy of the GNU General Public License\n"
+ "along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.\n");
+
+ exit(0);
+ break;
+
+ case 'h':
+ /* Display help, then quit. */
+ usage(argv[0]);
+ exit(0);
+ break;
+
+ case 'f':
+ /* Set map file */
+ main_argv[1] = optarg; /* pointer assignment */
+ break;
+
+ case 's':
+ /* Set shields */
+ robot->shields = (glong) atol(optarg);
+ break;
+
+ case 'e':
+ /* Set energy */
+ robot->energy = (glong) atol(optarg);
+ break;
+
+ default:
+ /* invalid option */
+ usage(argv[0]);
+ exit(1);
+ break;
+ } /* switch */
+ } /* while */
+
+ /* Extra arg is the Scheme file */
+
+ if (optind < argc)
+ {
+ /* Set Scheme file */
+ main_argv[2] = argv[optind]; /* pointer assignment */
+ }
+
+ /* Check that files have been given */
+ if (main_argv[1] == NULL)
+ {
+ main_argv[1] = g_malloc(MAX_PATH);
+ g_strlcpy(main_argv[1], DEFAULT_MAP, MAX_PATH);
+ g_fprintf(stderr, "map file not specified, trying default: %s\n",
+ main_argv[1]);
+ }
+
+ /* Check that files exist */
+ g_strlcpy(maps_path, main_argv[1], MAX_PATH);
+
+ if (!is_file_readable(maps_path))
+ {
+ g_strlcpy(maps_path, MAPS_PATH, MAX_PATH);
+ g_strlcat(maps_path, "/", MAX_PATH);
+ g_strlcat(maps_path, main_argv[1], MAX_PATH);
+
+ if (!is_file_readable(maps_path))
+ {
+ gchar *env = getenv(MAPS_PATH_ENV);
+
+ if (env != NULL)
+ {
+ g_strlcpy(maps_path, env, MAX_PATH);
+ g_strlcat(maps_path, "/", MAX_PATH);
+ g_strlcat(maps_path, main_argv[1], MAX_PATH);
+
+ if (!is_file_readable(maps_path))
+ {
+ g_fprintf(stderr,
+ "%s: %s: game map file does not exist or is not readable\n",
+ argv[0], main_argv[1]);
+ exit(1);
+ }
+ }
+ else
+ {
+ g_fprintf(stderr,
+ "%s: %s: game map file does not exist or is not readable\n",
+ argv[0], main_argv[1]);
+ exit(1);
+ }
+ }
+ }
+
+ main_argv[1] = maps_path;
+
+ /* Now the Scheme file */
+ if (main_argv[2] != NULL)
+ {
+ g_strlcpy(scripts_path, main_argv[2], MAX_PATH);
+
+ if (!is_file_readable(scripts_path))
+ {
+ g_strlcpy(scripts_path, SCRIPTS_PATH, MAX_PATH);
+ g_strlcat(scripts_path, "/", MAX_PATH);
+ g_strlcat(scripts_path, main_argv[2], MAX_PATH);
+
+ if (!is_file_readable(scripts_path))
+ {
+ gchar *env = getenv(SCRIPTS_PATH_ENV);
+
+ if (env != NULL)
+ {
+ g_strlcpy(scripts_path, env, MAX_PATH);
+ g_strlcat(scripts_path, "/", MAX_PATH);
+ g_strlcat(scripts_path, main_argv[2], MAX_PATH);
+
+ if (!is_file_readable(scripts_path))
+ {
+ g_fprintf(stderr,
+ "%s: %s: Scheme file does not exist or is not readable\n",
+ argv[0], main_argv[2]);
+ exit(1);
+ }
+ }
+ else
+ {
+ g_fprintf(stderr,
+ "%s: %s: Scheme file does not exist or is not readable\n",
+ argv[0], main_argv[2]);
+ exit(1);
+ }
+ }
+ }
+
+ main_argv[2] = scripts_path;
+ }
+ else
+ {
+ /* argv[2] can't be NULL as argv[3] may also be NULL */
+ main_argv[2] = "";
+ }
+
+ /* Start Guile environment. Does not exit */
+ g_printf("%s\n", PKGINFO);
+ g_printf("%s\n", COPYRIGHT);
+ g_printf("GNU Robots comes with ABSOLUTELY NO WARRANTY\n");
+ g_printf
+ ("This is free software, and you are welcome to redistribute it\n");
+ g_printf
+ ("under certain conditions; see the file `COPYING' for details.\n");
+ g_printf("Loading Guile ... Please wait\n\n");
+
+ scm_boot_guile(3, main_argv, main_prog, NULL);
+
+ return 0; /* never gets here, but keeps compiler happy */
}
/************************************************************************
@@ -276,79 +277,91 @@ main (gint argc, gchar *argv[])
* the Scheme program as argv[1] and the map file as argv[2]. The *
* program name is still argv[0]. *
************************************************************************/
-void
-main_prog (void *closure, gint argc, gchar *argv[])
+void main_prog(void *closure, gint argc, gchar *argv[])
{
- gchar *map_file = argv[1];
- gchar *robot_program = argv[2];
+ gchar *map_file = argv[1];
+ gchar *robot_program = argv[2];
+ gboolean loading = TRUE;
- api_init ();
+ api_init();
- g_printf ("Map file: %s\n", map_file);
+ g_printf("Map file: %s\n", map_file);
- map = map_new_from_file (map_file, DEFAULT_MAP_ROWS, DEFAULT_MAP_COLUMNS);
+ map = map_new_from_file(map_file, DEFAULT_MAP_ROWS,
+ DEFAULT_MAP_COLUMNS);
- if (map == NULL)
- {
- exit_nicely ();
- }
+ if (map == NULL)
+ {
+ exit_nicely();
+ }
- /* ensure the robot is placed properly */
- MAP_SET_OBJECT (map,
- G_ROBOT_POSITION_Y (robot),
- G_ROBOT_POSITION_X (robot), ROBOT);
+ g_thread_init(NULL);
+ gdk_threads_init();
+ g_thread_create(callback, &loading, FALSE, NULL);
- ui = user_interface_new (map);
+ /* ensure the robot is placed properly */
+ MAP_SET_OBJECT(map, G_ROBOT_POSITION_Y(robot),
+ G_ROBOT_POSITION_X(robot), ROBOT);
- if (ui == NULL)
- {
- exit_nicely ();
- }
+ g_printf("Loading GTK Interface ... Please wait\n\n");
+ while(loading);
- /* Now initialize the rest of the Robot properties */
- g_object_set (G_OBJECT (robot),
- "user-interface", G_OBJECT (ui), "map", G_OBJECT (map), NULL);
+ /* Now initialize the rest of the Robot properties */
+ g_object_set(G_OBJECT(robot),
+ "user-interface", G_OBJECT(arena), "map", G_OBJECT(map), NULL);
- g_signal_connect (G_OBJECT (robot), "death", G_CALLBACK (death), NULL);
+ g_signal_connect(G_OBJECT(robot), "death", G_CALLBACK(death), NULL);
- /* draw the map */
- user_interface_draw (ui);
- user_interface_update_status (ui, "Welcome to GNU Robots", -1,-1, -1);
+ if (strlen(robot_program) != 0)
+ {
+ /* execute a Scheme file */
+ g_printf("Robot program: %s\n", robot_program);
+ scm_c_primitive_load(robot_program);
+ }
+ else
+ {
+ gchar buf[BUFF_LEN];
- g_thread_init(NULL);
- g_thread_create(callback, NULL, FALSE, NULL);
+ g_printf
+ ("Robot program not specified. Entering interactive mode..\n");
- if (strlen (robot_program) != 0)
- {
- /* execute a Scheme file */
- g_printf ("Robot program: %s\n", robot_program);
- scm_c_primitive_load (robot_program);
- }
-
- else
- {
- gchar buff[BUFF_LEN];
+ while (1)
+ {
+ memset(&buf, 0, BUFF_LEN);
- g_printf("Robot program not specified. Entering interactive mode..\n");
+ ui_cmdwin_get_string(UI_CMDWIN(ui->priv->cmdwin), "guile> ",
+ buf, BUFF_LEN);
- while(1)
- {
- user_interface_get_string (ui, "guile> ", buff, BUFF_LEN);
+ scm_internal_catch(SCM_BOOL_T,
+ (scm_t_catch_body) scm_c_eval_string, buf,
+ catch_handler, NULL);
+ }
+ }
- scm_internal_catch (SCM_BOOL_T, (scm_t_catch_body) scm_c_eval_string,
- (void *) buff, catch_handler, NULL);
- }
- }
-
- /* done */
- exit_nicely ();
+ /* done */
+ exit_nicely();
}
gpointer callback(gpointer data)
{
- user_interface_run(ui);
+ gtk_init(0, NULL);
+
+ ui = UI_WINDOW(ui_window_new());
+ ui_window_postinit(ui, map);
+
+ arena = UI_ARENA(ui->priv->arena);
- return NULL;
+ /* draw the map */
+ ui_arena_draw(arena);
+ ui_arena_update_status(arena, "Welcome to GNU Robots", -1, -1, -1);
+
+ *(gboolean*)data = FALSE;
+
+ gdk_threads_enter();
+ gtk_main();
+ gdk_threads_leave();
+
+ return NULL;
}
/************************************************************************
@@ -356,8 +369,7 @@ gpointer callback(gpointer data)
* *
* Responsible for handling errors *
************************************************************************/
-SCM
-catch_handler (void *data, SCM tag, SCM throw_args)
+SCM catch_handler(void *data, SCM tag, SCM throw_args)
{
/*
@@ -377,18 +389,17 @@ catch_handler (void *data, SCM tag, SCM throw_args)
user_interface_update_status (ui, message, -1, -1, -1);
*/
- g_printf("Invalid Instruction\n");
+ g_printf("Invalid Instruction\n");
- return SCM_BOOL_F;
+ return SCM_BOOL_F;
}
-void
-death (GRobot *robot)
+void death(GRobot *robot)
{
- /* We get a ref increment on a signal */
- g_object_unref (G_OBJECT (robot));
+ /* We get a ref increment on a signal */
+ g_object_unref(G_OBJECT(robot));
- exit_nicely ();
+ exit_nicely();
}
/************************************************************************
@@ -397,52 +408,52 @@ death (GRobot *robot)
* A function that allows the program to exit nicely, after freeing all *
* memory pointers, etc. *
************************************************************************/
-void
-exit_nicely ()
+void exit_nicely()
{
- glong score, energy, shields, shots, units;
-
- /* Stop the UI */
- if (ui != NULL)
- {
- g_object_unref (G_OBJECT (ui));
- }
-
- /* Get rid of the map object */
- if (map != NULL)
- {
- g_object_unref (G_OBJECT (map));
- }
-
- /* Show statistics */
- g_object_get (G_OBJECT (robot),
- "shields", &shields,
- "energy", &energy,
- "units", &units, "shots", &shots, "score", &score, NULL);
-
- g_list_foreach (robots, (GFunc)g_object_unref, NULL);
- g_list_free (robots);
-
- g_printf ("\n-----------------------STATISTICS-----------------------\n");
- g_printf ("Shields: %ld\n", (shields < 0 ? 0 : shields));
- g_printf ("Energy: %ld\n", (energy < 0 ? 0 : energy));
- g_printf ("Units walked: %ld\n", (units < 0 ? 0 : units));
- g_printf ("Shots: %ld\n", (shots < 0 ? 0 : shots));
- g_printf ("Score: %ld\n", score);
-
- /* Show results, if any */
- if (shields < 1)
- {
- g_printf ("** Robot took too much damage, and died.\n");
- }
-
- else if (energy < 1)
- {
- g_printf ("** Robot ran out of energy.\n");
- }
-
- /* Quit program */
- exit (0);
+ glong score, energy, shields, shots, units;
+
+ /* Stop the UI */
+ if (ui != NULL)
+ {
+ g_object_unref(G_OBJECT(ui));
+ }
+
+ /* Get rid of the map object */
+ if (map != NULL)
+ {
+ g_object_unref(G_OBJECT(map));
+ }
+
+ /* Show statistics */
+ g_object_get(G_OBJECT(robot),
+ "shields", &shields,
+ "energy", &energy,
+ "units", &units, "shots", &shots, "score", &score, NULL);
+
+ g_list_foreach(robots, (GFunc) g_object_unref, NULL);
+ g_list_free(robots);
+
+ g_printf(
+ "\n-----------------------STATISTICS-----------------------\n");
+ g_printf("Shields: %ld\n", (shields < 0 ? 0 : shields));
+ g_printf("Energy: %ld\n", (energy < 0 ? 0 : energy));
+ g_printf("Units walked: %ld\n", (units < 0 ? 0 : units));
+ g_printf("Shots: %ld\n", (shots < 0 ? 0 : shots));
+ g_printf("Score: %ld\n", score);
+
+ /* Show results, if any */
+ if (shields < 1)
+ {
+ g_printf("** Robot took too much damage, and died.\n");
+ }
+
+ else if (energy < 1)
+ {
+ g_printf("** Robot ran out of energy.\n");
+ }
+
+ /* Quit program */
+ exit(0);
}
/************************************************************************
@@ -451,28 +462,27 @@ exit_nicely ()
* A function that prints the usage of GNU Robots to the user. Assume *
* text mode for this function. We have not initialized X Windows yet. *
************************************************************************/
-void
-usage (const gchar *argv0)
+void usage(const gchar *argv0)
{
- g_printf ("%s\n", PKGINFO);
- g_printf ("%s\n", COPYRIGHT);
- g_printf
- ("Game/diversion where you construct a program for a little robot\n");
- g_printf
- ("then set him loose and watch him explore a world on his own.\n\n");
-
- g_printf ("Usage: %s [OPTION]... [FILE]\n\n", argv0);
- g_printf
- (" -f, --map-file=FILE Load map file\n");
- g_printf (" -s, --shields=N Set initial shields to N\n");
- g_printf (" -e, --energy=N Set initial energy to N\n");
- g_printf (" -V, --version Output version information and exit\n");
- g_printf (" -h, --help Display this help and exit\n");
- g_printf ("\nNote: FILE refers to a scheme file and %s enters into \n",
- argv0);
- g_printf (" interactive mode if it is not specified.\n");
-
- g_printf ("\nReport bugs to <%s>.\n", PACKAGE_BUGREPORT);
+ g_printf("%s\n", PKGINFO);
+ g_printf("%s\n", COPYRIGHT);
+ g_printf
+ ("Game/diversion where you construct a program for a little robot\n");
+ g_printf
+ ("then set him loose and watch him explore a world on his own.\n\n");
+
+ g_printf("Usage: %s [OPTION]... [FILE]\n\n", argv0);
+ g_printf(" -f, --map-file=FILE Load map file\n");
+ g_printf(" -s, --shields=N Set initial shields to N\n");
+ g_printf(" -e, --energy=N Set initial energy to N\n");
+ g_printf
+ (" -V, --version Output version information and exit\n");
+ g_printf(" -h, --help Display this help and exit\n");
+ g_printf("\nNote: FILE refers to a scheme file and %s enters into \n",
+ argv0);
+ g_printf(" interactive mode if it is not specified.\n");
+
+ g_printf("\nReport bugs to <%s>.\n", PACKAGE_BUGREPORT);
}
/************************************************************************
@@ -483,19 +493,18 @@ usage (const gchar *argv0)
* files. This will save on error checking later on, when we may have *
* already initialized another environment (Curses, X Windows, ...) *
************************************************************************/
-gint
-is_file_readable (const gchar *filename)
+gint is_file_readable(const gchar *filename)
{
- FILE *stream;
-
- stream = fopen (filename, "r");
- if (stream == NULL)
- {
- /* Failed */
- return (0);
- }
-
- /* Success */
- fclose (stream);
- return (1);
+ FILE *stream;
+
+ stream = fopen(filename, "r");
+ if (stream == NULL)
+ {
+ /* Failed */
+ return (0);
+ }
+
+ /* Success */
+ fclose(stream);
+ return (1);
}
diff --git a/src/ui-arena.c b/src/ui-arena.c
new file mode 100644
index 0000000..39cbf55
--- /dev/null
+++ b/src/ui-arena.c
@@ -0,0 +1,466 @@
+/* Copyright (C) 2008 Bradley Smith <brad@brad-smith.co.uk>
+ *
+ * GNU Robots, ui-arena.c
+ *
+ * GNU Robots is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * GNU Robots 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "ui-arena.h"
+
+#include "xpm/statusbar.xpm"
+#include "xpm/space.xpm"
+#include "xpm/food.xpm"
+#include "xpm/wall.xpm"
+#include "xpm/prize.xpm"
+#include "xpm/baddie.xpm"
+#include "xpm/robot_north.xpm"
+#include "xpm/robot_east.xpm"
+#include "xpm/robot_south.xpm"
+#include "xpm/robot_west.xpm"
+#include "xpm/robot.xpm"
+
+#include "map.h"
+#include "configs.h"
+
+#include <stdlib.h>
+
+#include <glib/gprintf.h>
+
+#define TILE_SIZE 16
+
+enum
+{
+ ARG_0,
+ ARG_MAP
+};
+
+struct _UIArenaPrivate
+{
+ Map *map;
+ MapSize *map_size;
+
+ GdkPixmap *buf;
+ GdkFont *font;
+
+ int width;
+ int height;
+
+ GdkPixmap *win_bufi;
+ GdkPixmap *statusbar;
+ GdkPixmap *space;
+ GdkPixmap *food;
+ GdkPixmap *wall;
+ GdkPixmap *prize;
+ GdkPixmap *baddie;
+ GdkPixmap *robotDirs[4];
+ GdkPixmap *robotPix;
+};
+
+#define UI_ARENA_GET_PRIVATE(obj) \
+ G_TYPE_INSTANCE_GET_PRIVATE(obj, UI_TYPE_ARENA, UIArenaPrivate)
+
+G_DEFINE_TYPE(UIArena, ui_arena, GTK_TYPE_DRAWING_AREA)
+
+static gboolean ui_arena_expose(GtkWidget *widget, GdkEventExpose *event,
+ UIArena *arena);
+static gboolean ui_arena_configure(GtkWidget *widget,
+ GdkEventConfigure *event, UIArena *arena);
+static void create_image (UIArena *arena, gchar **data, GdkPixmap **image);
+static void put_tile(UIArena *arena, GdkPixmap *image, gint x, gint y);
+
+GtkWidget *ui_arena_new()
+{
+ return GTK_WIDGET(g_object_new(UI_TYPE_ARENA, NULL));
+}
+
+static void ui_arena_init(UIArena *arena)
+{
+ arena->priv = UI_ARENA_GET_PRIVATE(arena);
+
+ arena->priv->map = NULL;
+ arena->priv->map_size = NULL;
+ arena->priv->width = 400;
+ arena->priv->height = 200;
+ arena->priv->font = gdk_font_from_description(
+ pango_font_description_from_string("Fixed 18"));
+
+ gtk_widget_set_size_request(GTK_WIDGET(arena), arena->priv->width,
+ arena->priv->height);
+
+ g_signal_connect(G_OBJECT(arena), "expose_event",
+ G_CALLBACK(ui_arena_expose), arena);
+ g_signal_connect(G_OBJECT(arena), "configure_event",
+ G_CALLBACK(ui_arena_configure), arena);
+
+ gtk_widget_set_events(GTK_WIDGET(arena),
+ GDK_EXPOSURE_MASK | GDK_BUTTON_PRESS_MASK);
+}
+
+static void ui_arena_class_init(UIArenaClass *klass)
+{
+ g_type_class_add_private(G_OBJECT_CLASS(klass),
+ sizeof(UIArenaPrivate));
+}
+
+static gboolean ui_arena_expose(GtkWidget *widget, GdkEventExpose *event,
+ UIArena *arena)
+{
+ gdk_draw_drawable(widget->window,
+ widget->style->fg_gc[GTK_WIDGET_STATE(widget)], arena->priv->buf,
+ event->area.x, event->area.y, event->area.x, event->area.y,
+ event->area.width, event->area.height);
+
+ if(arena->priv->map)
+ {
+ gdk_draw_rectangle(widget->window, widget->style->black_gc, FALSE,
+ 0, 0, widget->allocation.width - 2,
+ widget->allocation.height - 1);
+ }
+
+ return FALSE;
+}
+
+static gboolean ui_arena_configure(GtkWidget *widget,
+ GdkEventConfigure *event, UIArena *arena)
+{
+ if(arena->priv->buf)
+ g_object_unref(arena->priv->buf);
+
+ arena->priv->buf = gdk_pixmap_new(widget->window,
+ widget->allocation.width - 1, widget->allocation.height, -1);
+
+ gdk_draw_rectangle(arena->priv->buf, widget->style->white_gc, TRUE,
+ 0, 0, widget->allocation.width, widget->allocation.height);
+
+ return TRUE;
+}
+
+void ui_arena_set_map(UIArena *arena, Map *map)
+{
+ arena->priv->map = map;
+
+ g_object_get(G_OBJECT(arena->priv->map), "size",
+ &arena->priv->map_size, NULL);
+
+ arena->priv->width = arena->priv->map_size->num_cols * TILE_SIZE;
+ arena->priv->height = arena->priv->map_size->num_rows * TILE_SIZE + 32;
+
+ gtk_widget_set_size_request(GTK_WIDGET(arena), arena->priv->width,
+ arena->priv->height);
+}
+
+void ui_arena_draw(UIArena *arena)
+{
+ gint i, j;
+
+ if(!arena->priv->map)
+ return;
+
+ for (j = 0; j < arena->priv->map_size->num_rows; j++)
+ {
+ for (i = 0; i < arena->priv->map_size->num_cols; i++)
+ {
+ switch(MAP_GET_OBJECT(arena->priv->map, i, j))
+ {
+ case '\0':
+ put_tile(arena, arena->priv->wall, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ case SPACE:
+ put_tile(arena, arena->priv->space, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ case FOOD:
+ put_tile(arena, arena->priv->food, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ case PRIZE:
+ put_tile(arena, arena->priv->prize, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ case WALL:
+ put_tile(arena, arena->priv->wall, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ case BADDIE:
+ put_tile(arena, arena->priv->baddie, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ case ROBOT:
+ put_tile(arena, arena->priv->robotPix, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ default:
+ put_tile(arena, arena->priv->wall, i * TILE_SIZE,
+ j * TILE_SIZE);
+ break;
+ }
+ }
+ }
+
+ gtk_widget_queue_draw_area(GTK_WIDGET(arena), 0, 0, arena->priv->width,
+ arena->priv->height);
+}
+
+void ui_arena_postinit(UIArena *arena)
+{
+ create_image(arena, statusbar_xpm, &arena->priv->statusbar);
+ create_image(arena, space_xpm, &arena->priv->space);
+ create_image(arena, food_xpm, &arena->priv->food);
+ create_image(arena, wall_xpm, &arena->priv->wall);
+ create_image(arena, prize_xpm, &arena->priv->prize);
+ create_image(arena, baddie_xpm, &arena->priv->baddie);
+ create_image(arena, robot_north_xpm, &arena->priv->robotDirs[0]);
+ create_image(arena, robot_east_xpm, &arena->priv->robotDirs[1]);
+ create_image(arena, robot_south_xpm, &arena->priv->robotDirs[2]);
+ create_image(arena, robot_west_xpm, &arena->priv->robotDirs[3]);
+ create_image(arena, robot_xpm, &arena->priv->robotPix);
+}
+
+static void create_image (UIArena *arena, gchar **data, GdkPixmap **image)
+{
+ *image = gdk_pixmap_create_from_xpm_d(GDK_DRAWABLE(arena->priv->buf),
+ NULL, NULL, data);
+ if (*image == NULL)
+ g_fprintf (stderr, "Cannot create image from xpm\n");
+}
+
+static void put_tile(UIArena *arena, GdkPixmap *image, gint x, gint y)
+{
+ gdk_draw_drawable(arena->priv->buf,
+ GTK_WIDGET(arena)->style->fg_gc[GTK_WIDGET_STATE(arena)],
+ GDK_DRAWABLE(image), 0, 0, x, y, TILE_SIZE, TILE_SIZE);
+}
+
+void ui_arena_update_status(UIArena *arena, const gchar *s, glong energy,
+ glong score, glong shields)
+{
+ gchar status[20];
+ gint x = 0;
+
+ while(x < arena->priv->width)
+ {
+ gdk_draw_drawable(arena->priv->buf,
+ GTK_WIDGET(arena)->style->white_gc,
+ arena->priv->statusbar, 0, 0, x,
+ arena->priv->map_size->num_rows * TILE_SIZE, 96, 32);
+ x += 96;
+ }
+
+ gdk_draw_string(arena->priv->buf, arena->priv->font,
+ GTK_WIDGET(arena)->style->white_gc, 3,
+ arena->priv->map_size->num_rows * TILE_SIZE + 16, s);
+
+ if(energy > -1)
+ {
+ g_sprintf(status, "Robot Energy: %3ld", energy);
+ gdk_draw_string(arena->priv->buf, arena->priv->font,
+ GTK_WIDGET(arena)->style->white_gc, 240,
+ arena->priv->map_size->num_rows * TILE_SIZE + 12, status);
+ }
+
+ if (score > -1)
+ {
+ g_sprintf (status, "Robot Score: %3ld", score);
+ gdk_draw_string(arena->priv->buf, arena->priv->font,
+ GTK_WIDGET(arena)->style->white_gc, 240,
+ arena->priv->map_size->num_rows * TILE_SIZE + 25, status);
+ }
+
+ if (shields > -1)
+ {
+ g_sprintf (status, "Robot Shields: %3ld", shields);
+ gdk_draw_string(arena->priv->buf, arena->priv->font,
+ GTK_WIDGET(arena)->style->white_gc, 480,
+ arena->priv->map_size->num_rows * TILE_SIZE + 12, status);
+ }
+
+ gtk_widget_queue_draw_area(GTK_WIDGET(arena), 0, 0, arena->priv->width,
+ arena->priv->height);
+}
+
+/* note that hook_delete_thing(x,y) is the same as
+ * hook_add_thing(x,y,space) */
+void ui_arena_add_thing(UIArena *arena, gint x, gint y, gint thing)
+{
+ gint w_x, w_y;
+
+ w_x = x * TILE_SIZE;
+ w_y = y * TILE_SIZE;
+
+ switch (thing)
+ {
+ case SPACE:
+ put_tile(arena, arena->priv->space, w_x, w_y);
+ break;
+ case FOOD:
+ put_tile(arena, arena->priv->food, w_x, w_y);
+ break;
+ case PRIZE:
+ put_tile(arena, arena->priv->prize, w_x, w_y);
+ break;
+ case WALL:
+ put_tile(arena, arena->priv->wall, w_x, w_y);
+ break;
+ case BADDIE:
+ put_tile(arena, arena->priv->baddie, w_x, w_y);
+ break;
+ case ROBOT:
+ put_tile(arena, arena->priv->robotPix, w_x, w_y);
+ break;
+ default:
+ put_tile(arena, arena->priv->wall, w_x, w_y);
+ break;
+ }
+
+ gtk_widget_queue_draw_area(GTK_WIDGET(arena), 0, 0, arena->priv->width,
+ arena->priv->height);
+}
+
+void ui_arena_move_robot(UIArena *arena, gint from_x, gint from_y,
+ gint to_x, gint to_y, gint cdir, glong energy, glong score,
+ glong shields)
+{
+ const static gint movement = TILE_SIZE / 16;
+ guint8 distance = dist(from_x, from_y, to_x, to_y);
+ guint w_x = to_x * TILE_SIZE, w_y = to_y * TILE_SIZE, tw_x, tw_y;
+ gboolean ok;
+
+ g_assert(distance <= 1);
+
+ ui_arena_update_status(arena, "Robot moves..", energy, score, shields);
+
+ /* Check if robot is moving withing a single box */
+ if (distance == 0)
+ {
+ put_tile(arena, arena->priv->space, from_x * TILE_SIZE,
+ from_y * TILE_SIZE);
+ put_tile(arena, arena->priv->robotDirs[cdir], to_x * TILE_SIZE,
+ to_y * TILE_SIZE);
+
+ gtk_widget_queue_draw_area(GTK_WIDGET(arena), 0, 0,
+ arena->priv->width, arena->priv->height);
+
+ return;
+ }
+
+ from_x *= TILE_SIZE;
+ from_y *= TILE_SIZE;
+ tw_y = w_y;
+ tw_x = w_x;
+ switch (cdir)
+ {
+ case NORTH:
+ tw_y = from_y - movement;
+ break;
+ case SOUTH:
+ tw_y = from_y + movement;
+ break;
+ case EAST:
+ tw_x = from_x + movement;
+ break;
+ case WEST:
+ tw_x = from_x - movement;
+ break;
+ default:
+ g_printf("Weird unknown robot direction. I'm Confused.\n");
+ }
+
+
+ while (1)
+ {
+ put_tile(arena, arena->priv->space, from_x, from_y);
+ put_tile(arena, arena->priv->robotDirs[cdir], tw_x, tw_y);
+
+ ok = FALSE;
+ if (tw_x < w_x)
+ {
+ tw_x += movement;
+ ok = TRUE;
+ }
+ else if (tw_x > w_x)
+ {
+ tw_x -= movement;
+ ok = TRUE;
+ }
+ if (tw_y < w_y)
+ {
+ tw_y += movement;
+ ok = TRUE;
+ }
+ else if (tw_y > w_y)
+ {
+ tw_y -= movement;
+ ok = TRUE;
+ }
+
+ gtk_widget_queue_draw_area(GTK_WIDGET(arena), 0, 0,
+ arena->priv->width, arena->priv->height);
+ gdk_window_process_all_updates();
+
+ g_usleep(USLEEP_TIME / 16);
+
+ if (!ok)
+ break;
+ }
+
+ g_usleep(USLEEP_TIME);
+}
+
+/* hooks to animate the robot */
+void ui_arena_robot_smell(UIArena *arena, gint x, gint y, gint cdir,
+ glong energy, glong score, glong shields)
+{
+ /* If we want to change the pic, do it here */
+ ui_arena_update_status(arena, "Robot sniffs...", energy, score,
+ shields);
+
+ g_usleep(USLEEP_TIME);
+}
+
+void ui_arena_robot_zap(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields)
+{
+ ui_arena_update_status(arena, "Robot fires his little gun...", energy,
+ score, shields);
+
+ g_usleep(USLEEP_TIME);
+}
+
+void ui_arena_robot_feel(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields)
+{
+ ui_arena_update_status(arena, "Robot feels for a thing...", energy,
+ score, shields);
+
+ g_usleep(USLEEP_TIME);
+}
+
+void ui_arena_robot_grab(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields)
+{
+ ui_arena_update_status(arena, "Robot grabs thing...", energy, score,
+ shields);
+
+ g_usleep(USLEEP_TIME);
+}
+
+void ui_arena_robot_look(UIArena *arena, gint x, gint y, gint cdir,
+ gint x_to, gint y_to, glong energy, glong score, glong shields)
+{
+ ui_arena_update_status(arena, "Robot looks for a thing...", energy,
+ score, shields);
+
+ g_usleep(USLEEP_TIME);
+}
diff --git a/ui/ui-cmdwin.c b/src/ui-cmdwin.c
index b743687..71f7b53 100644
--- a/ui/ui-cmdwin.c
+++ b/src/ui-cmdwin.c
@@ -18,9 +18,16 @@
#include "ui-cmdwin.h"
+#include <stdlib.h>
+#include <pty.h>
+
+#include <vte/vte.h>
+#include <readline.h>
+#include <history.h>
+
struct _UICmdWinPrivate
{
- int dummy;
+ GtkWidget *vte;
};
#define UI_CMDWIN_GET_PRIVATE(obj) \
@@ -35,7 +42,26 @@ GtkWidget *ui_cmdwin_new(void)
static void ui_cmdwin_init(UICmdWin *cmdwin)
{
- gtk_widget_set_size_request(GTK_WIDGET(cmdwin), 40*16,200);
+ int master_pty, slave_pty;
+ FILE *in, *out;
+
+ cmdwin->priv = UI_CMDWIN_GET_PRIVATE(cmdwin);
+
+ cmdwin->priv->vte = vte_terminal_new();
+
+ gtk_box_pack_start(GTK_BOX(cmdwin), cmdwin->priv->vte, TRUE, TRUE, 0);
+
+ gtk_widget_set_size_request(GTK_WIDGET(cmdwin), -1, 200);
+
+ g_assert(openpty(&master_pty, &slave_pty, NULL, NULL, NULL) >= 0);
+ vte_terminal_set_pty(VTE_TERMINAL(cmdwin->priv->vte), master_pty);
+ in = fdopen(slave_pty, "r");
+ out = fdopen(slave_pty, "w");
+
+ rl_instream = in;
+ rl_outstream = out;
+
+ gtk_widget_show(cmdwin->priv->vte);
}
static void ui_cmdwin_class_init(UICmdWinClass *klass)
@@ -43,3 +69,19 @@ static void ui_cmdwin_class_init(UICmdWinClass *klass)
g_type_class_add_private(G_OBJECT_CLASS(klass),
sizeof(UICmdWinPrivate));
}
+
+void ui_cmdwin_get_string(UICmdWin *cmdwin, gchar *prompt, gchar *buf,
+ gint len)
+{
+ char *line = (char *)NULL;
+
+ line = readline(prompt);
+
+ if (line && *line)
+ {
+ add_history(line);
+ g_strlcpy(buf, line, len);
+ }
+
+ free(line);
+}
diff --git a/ui/ui-window.c b/src/ui-window.c
index 27c49e9..8758c64 100644
--- a/ui/ui-window.c
+++ b/src/ui-window.c
@@ -22,6 +22,10 @@
#include "ui-cmdwin.h"
#include "ui-arena.h"
+#include "main.h"
+#include "map.h"
+#include "configs.h"
+
#include <gtk/gtkmain.h>
#define UI_WINDOW_GET_PRIVATE(obj) \
@@ -31,7 +35,7 @@ G_DEFINE_TYPE(UIWindow, ui_window, GTK_TYPE_WINDOW)
static void on_ui_window_destroy(GtkWidget *widget, gpointer data);
-GtkWidget *ui_window_new(void)
+GtkWidget *ui_window_new()
{
return GTK_WIDGET(g_object_new(UI_TYPE_WINDOW, NULL));
}
@@ -40,37 +44,41 @@ static void on_ui_window_destroy(GtkWidget *widget, gpointer data)
{
gtk_widget_hide(widget);
gtk_main_quit();
+ exit_nicely();
}
static void ui_window_init(UIWindow *window)
{
- GtkWidget *vbox;
- GtkWidget *vpaned;
-
window->priv = UI_WINDOW_GET_PRIVATE(window);
- vbox = gtk_vbox_new(FALSE, 0);
- vpaned = gtk_vpaned_new();
+ g_signal_connect(G_OBJECT(window), "destroy",
+ G_CALLBACK(on_ui_window_destroy), NULL);
+
+ gtk_window_set_title(GTK_WINDOW(window), "UI Test");
+ gtk_window_set_resizable(GTK_WINDOW(window), FALSE);
+}
+
+void ui_window_postinit(UIWindow *window, Map* map)
+{
+ GtkWidget *vbox;
+
+ vbox = gtk_vbox_new(FALSE, 2);
window->priv->cmdwin = ui_cmdwin_new();
window->priv->arena = ui_arena_new();
-
- gtk_paned_add1(GTK_PANED(vpaned), window->priv->arena);
- gtk_paned_add2(GTK_PANED(vpaned), window->priv->cmdwin);
+ ui_arena_set_map(UI_ARENA(window->priv->arena), map);
/* TODO: Add menu first etc */
- gtk_box_pack_start(GTK_BOX(vbox), vpaned, TRUE, TRUE, 0);
+ gtk_box_pack_start(GTK_BOX(vbox), window->priv->arena, TRUE, TRUE, 0);
+ gtk_box_pack_start(GTK_BOX(vbox), window->priv->cmdwin, TRUE, TRUE, 0);
gtk_container_add(GTK_CONTAINER(window), vbox);
- g_signal_connect(G_OBJECT(window), "destroy",
- G_CALLBACK(on_ui_window_destroy), NULL);
-
- gtk_window_set_title(GTK_WINDOW(window), "UI Test");
gtk_widget_show(window->priv->cmdwin);
gtk_widget_show(window->priv->arena);
- gtk_widget_show(vpaned);
gtk_widget_show(vbox);
gtk_widget_show(GTK_WIDGET(window));
+
+ ui_arena_postinit(UI_ARENA(window->priv->arena));
}
static void ui_window_class_init(UIWindowClass *klass)
diff --git a/src/userinterface.c b/src/userinterface.c
deleted file mode 100644
index b2702e4..0000000
--- a/src/userinterface.c
+++ /dev/null
@@ -1,736 +0,0 @@
-/* Copyright (C) 1998 Jim Hall <jhall1@isd.net>
- * Copyright (C) 2008 Bradley Smith <brad@brad-smith.co.uk>
- *
- * GNU Robots game engine.
- *
- * GNU Robots is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * GNU Robots 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 General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <glib.h>
-#include <glib/gprintf.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include "configs.h"
-#include "userinterface.h"
-
-#include <readline.h>
-#include <history.h>
-
-G_DEFINE_TYPE(UserInterface, user_interface, G_TYPE_OBJECT)
-
-enum
-{
- ARG_0,
- ARG_MAP
-};
-
-static GObject * user_interface_constructor (GType type,
- guint n_construct_properties,
- GObjectConstructParam *construct_properties);
-
-static void user_interface_finalize (GObject * object);
-static void user_interface_dispose (GObject * object);
-
-static void user_interface_set_property (GObject * object, guint prop_id,
- const GValue * value, GParamSpec * pspec);
-
-static void user_interface_get_property (GObject * object, guint prop_id,
- GValue * value, GParamSpec * pspec);
-
-static void put_tile (UserInterface *ui, XImage *image, gint x, gint y);
-static void put_winbuf (UserInterface *ui);
-static void setup_winbuf (UserInterface *ui);
-void create_image (UserInterface *ui, gchar **data, XImage ** image);
-
-static GObjectClass *parent_class = NULL;
-
-static void
-user_interface_class_init (UserInterfaceClass * klass)
-{
- GObjectClass *gobject_class;
-
- gobject_class = (GObjectClass *) klass;
-
- parent_class = g_type_class_ref (G_TYPE_OBJECT);
-
- gobject_class->constructor = user_interface_constructor;
- gobject_class->set_property = user_interface_set_property;
- gobject_class->get_property = user_interface_get_property;
- gobject_class->dispose = user_interface_dispose;
- gobject_class->finalize = user_interface_finalize;
-
- g_object_class_install_property (G_OBJECT_CLASS (klass), ARG_MAP,
- g_param_spec_object ("map",
- "Map",
- "Reference to the Game Map object",
- G_TYPE_MAP,
- G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
-}
-
-static void
-user_interface_init (UserInterface* ui)
-{
- ui->map = NULL;
- ui->map_size = NULL;
-}
-
-static GObject *
-user_interface_constructor (GType type,
- guint n_construct_properties,
- GObjectConstructParam *construct_properties)
-{
- /* Initialize ui */
- GObject *object;
- UserInterface *ui;
-#include "xpm/statusbar.xpm"
-#include "xpm/space.xpm"
-#include "xpm/food.xpm"
-#include "xpm/wall.xpm"
-#include "xpm/prize.xpm"
-#include "xpm/baddie.xpm"
-#include "xpm/robot_north.xpm"
-#include "xpm/robot_east.xpm"
-#include "xpm/robot_south.xpm"
-#include "xpm/robot_west.xpm"
-#include "xpm/robot.xpm"
- XClassHint classhint;
- XWMHints wmhints;
- XGCValues values;
-
- /* Chain up to the parent first */
- object = parent_class->constructor (type, n_construct_properties,
- construct_properties);
-
- ui = USER_INTERFACE (object);
-
- XInitThreads();
-
- if ((ui->dpy = XOpenDisplay ("")) == NULL) {
- g_printf ("Couldn't open the X Server Display!\n");
- exit (1); /* Exit nicely isn't needed yet, and causes segfault */
- }
-
- ui->wm_delete_win = XInternAtom (ui->dpy, "WM_DELETE_WINDOW", False);
-
- ui->win_width = ui->map_size->num_cols * TILE_SIZE;
- ui->win_height = ui->map_size->num_rows * TILE_SIZE + 32;
- ui->x_win = XCreateSimpleWindow (ui->dpy, DefaultRootWindow (ui->dpy),
- 0, 0, ui->win_width, ui->win_height, 0, 0, 0);
-
- XSetWMProtocols (ui->dpy, ui->x_win, &(ui->wm_delete_win), 1);
-
- ui->wm_protocols = XInternAtom(ui->dpy, "WM_PROTOCOLS", False);
-
- XStoreName (ui->dpy, ui->x_win, "GNU Robots");
-
- classhint.res_name = "robots";
- classhint.res_class = "Robots";
- XSetClassHint (ui->dpy, ui->x_win, &classhint);
-
- /* XSetCommand() seems to segfault... */
-
- wmhints.input = True;
- wmhints.flags = InputHint;
- XSetWMHints (ui->dpy, ui->x_win, &wmhints);
-
- XSelectInput (ui->dpy, ui->x_win,
- ExposureMask | KeyPressMask | KeyReleaseMask | StructureNotifyMask
- | FocusChangeMask);
-
- XMapWindow (ui->dpy, ui->x_win);
-
- ui->text = XLoadFont (ui->dpy,
- "-*-fixed-medium-r-*-*-*-120-*-*-*-*-*-*");
- values.font = ui->text;
- values.foreground = WhitePixel (ui->dpy, DefaultScreen (ui->dpy));
-
- ui->gc = XCreateGC (ui->dpy, ui->x_win,
- GCFont | GCForeground, &values);
-
- create_image (ui, statusbar_xpm, &ui->statusbar);
- create_image (ui, space_xpm, &ui->space);
- create_image (ui, food_xpm, &ui->food);
- create_image (ui, wall_xpm, &ui->wall);
- create_image (ui, prize_xpm, &ui->prize);
- create_image (ui, baddie_xpm, &ui->baddie);
- create_image (ui, robot_north_xpm, &ui->robotDirs[0]);
- create_image (ui, robot_east_xpm, &ui->robotDirs[1]);
- create_image (ui, robot_south_xpm, &ui->robotDirs[2]);
- create_image (ui, robot_west_xpm, &ui->robotDirs[3]);
- create_image (ui, robot_xpm, &ui->robotPix);
-
- setup_winbuf (ui);
-
- return object;
-}
-
-static void
-user_interface_dispose (GObject * object)
-{
- UserInterface *ui;
- ui = USER_INTERFACE (object);
-
- if (ui->map != NULL) {
- g_object_unref (G_OBJECT (ui->map));
-
- if (ui->map_size != NULL) {
- g_free (ui->map_size);
- }
- }
-
- parent_class->dispose (object);
-}
-
-/* finalize is called when the object has to free its resources */
-static void
-user_interface_finalize (GObject * object)
-{
- UserInterface *ui = USER_INTERFACE (object);
-
- /* End ui mode */
-#ifdef USE_MITSHM
- if (use_mitshm) {
- XShmDetach (ui->dpy, &shm_info);
- if (shm_info.shmaddr)
- shmdt (shm_info.shmaddr);
- if (shm_info.shmid >= 0)
- shmctl (shm_info.shmid, IPC_RMID, 0);
- }
-#endif
- XDestroyWindow (ui->dpy, ui->x_win);
- XUnloadFont (ui->dpy, ui->text);
-
- parent_class->finalize (object);
-}
-
-static void
-user_interface_set_property (GObject * object, guint prop_id,
- const GValue * value, GParamSpec * pspec)
-{
- UserInterface *ui;
- GObject *obj;
-
- /* it's not null if we got it, but it might not be ours */
- g_return_if_fail (G_IS_USER_INTERFACE (object));
-
- ui = USER_INTERFACE (object);
-
- switch (prop_id) {
- case ARG_MAP:
- obj = g_value_get_object (value);
- g_return_if_fail (obj != NULL);
-
- if (ui->map != NULL) {
- g_object_unref (ui->map);
- }
-
- ui->map = MAP (g_object_ref (obj));
-
- if (ui->map_size != NULL) {
- g_free (ui->map_size);
- }
-
- g_object_get (G_OBJECT (ui->map),
- "size", &ui->map_size,
- NULL);
- break;
- default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
- break;
- }
-}
-
-static void
-user_interface_get_property (GObject * object, guint prop_id,
- GValue * value, GParamSpec * pspec)
-{
- UserInterface *ui;
-
- /* it's not null if we got it, but it might not be ours */
- g_return_if_fail (G_IS_USER_INTERFACE (object));
-
- ui = USER_INTERFACE (object);
-
- switch (prop_id) {
- case ARG_MAP:
- g_value_set_object (value, g_object_ref (G_OBJECT (ui->map)));
- break;
- default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
- break;
- }
-}
-
-UserInterface *
-user_interface_new (Map *map)
-{
- UserInterface *ui;
-
- g_return_val_if_fail (map != NULL, NULL);
-
- ui = USER_INTERFACE (g_object_new (user_interface_get_type (),
- "map", map,
- NULL));
-
- return USER_INTERFACE (ui);
-}
-
-/* note that hook_delete_thing(x,y) is the same as
- hook_add_thing(x,y,space) */
-void user_interface_add_thing (UserInterface *ui,
- gint x,
- gint y,
- gint thing)
-{
- gint w_x, w_y;
-
- w_x = x * TILE_SIZE;
- w_y = y * TILE_SIZE;
-
- switch (thing) {
- case SPACE:
- put_tile (ui, ui->space, w_x, w_y);
- break;
- case FOOD:
- put_tile (ui, ui->food, w_x, w_y);
- break;
- case PRIZE:
- put_tile (ui, ui->prize, w_x, w_y);
- break;
- case WALL:
- put_tile (ui, ui->wall, w_x, w_y);
- break;
- case BADDIE:
- put_tile (ui, ui->baddie, w_x, w_y);
- break;
- case ROBOT:
- put_tile (ui, ui->robotPix, w_x, w_y);
- break;
- default:
- put_tile (ui, ui->wall, w_x, w_y);
- break;
- }
-
- put_winbuf (ui);
- XFlush (ui->dpy);
-}
-
-void user_interface_draw (UserInterface *ui)
-{
- gint i, j;
-
- /* Draw the map for the GNU Robots game. */
- for (j = 0; j < ui->map_size->num_rows; j++) {
- for (i = 0; i < ui->map_size->num_cols; i++) {
- /* Special cases */
- switch (MAP_GET_OBJECT (ui->map, i, j)) {
- /* Add something for the ROBOT?? */
- case '\0':
- put_tile (ui, ui->wall, i * TILE_SIZE, j * TILE_SIZE);
- break;
- case SPACE:
- put_tile (ui, ui->space, i * TILE_SIZE, j * TILE_SIZE);
- break;
- case FOOD:
- put_tile (ui, ui->food, i * TILE_SIZE, j * TILE_SIZE);
- break;
- case PRIZE:
- put_tile (ui, ui->prize, i * TILE_SIZE, j * TILE_SIZE);
- break;
- case WALL:
- put_tile (ui, ui->wall, i * TILE_SIZE, j * TILE_SIZE);
- break;
- case BADDIE:
- put_tile (ui, ui->baddie, i * TILE_SIZE, j * TILE_SIZE);
- break;
- case ROBOT:
- put_tile (ui, ui->robotPix, i * TILE_SIZE, j * TILE_SIZE);
- break;
- default:
- put_tile (ui, ui->wall, i * TILE_SIZE, j * TILE_SIZE);
- break;
- } /* switch */
- } /* for i */
- } /* for j */
-
- put_winbuf (ui);
- XSync (ui->dpy, FALSE);
-}
-
-void user_interface_move_robot (UserInterface *ui,
- gint from_x,
- gint from_y,
- gint to_x,
- gint to_y,
- gint cdir,
- glong energy,
- glong score,
- glong shields)
-{
- const static gint movement = TILE_SIZE / 16;
- guint8 distance = dist (from_x, from_y, to_x, to_y);
- guint w_x = to_x * TILE_SIZE, w_y = to_y * TILE_SIZE, tw_x, tw_y;
- Bool ok;
-
- g_assert (distance <= 1);
-
- user_interface_update_status (ui, "robot moves..", energy, score, shields);
-
- /* Check if robot is moving withing a single box */
- if (distance == 0) {
- put_tile (ui, ui->space, from_x * TILE_SIZE, from_y * TILE_SIZE);
- put_tile (ui, ui->robotDirs[cdir], to_x * TILE_SIZE, to_y * TILE_SIZE);
-
- put_winbuf (ui);
- XSync (ui->dpy, False);
- g_usleep (USLEEP_TIME / 16);
-
- return;
- }
-
- from_x *= TILE_SIZE;
- from_y *= TILE_SIZE;
- tw_y = w_y;
- tw_x = w_x;
- switch (cdir) {
- case NORTH:
- tw_y = from_y - movement;
- break;
- case SOUTH:
- tw_y = from_y + movement;
- break;
- case EAST:
- tw_x = from_x + movement;
- break;
- case WEST:
- tw_x = from_x - movement;
- break;
- default:
- g_printf ("Weird unknown robot direction. I'm Confused.\n");
- }
-
- while (1) {
- put_tile (ui, ui->space, from_x, from_y);
- put_tile (ui, ui->robotDirs[cdir], tw_x, tw_y);
-
- ok = False;
- if (tw_x < w_x) {
- tw_x += movement;
- ok = True;
- } else if (tw_x > w_x) {
- tw_x -= movement;
- ok = True;
- }
- if (tw_y < w_y) {
- tw_y += movement;
- ok = True;
- } else if (tw_y > w_y) {
- tw_y -= movement;
- ok = True;
- }
- put_winbuf (ui);
- XSync (ui->dpy, False);
- g_usleep (USLEEP_TIME / 16);
- if (!ok)
- break;
- }
-
- g_usleep (USLEEP_TIME);
-}
-
-/* hooks to animate the robot */
-void user_interface_robot_smell (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- glong energy,
- glong score,
- glong shields)
-{
- /* If we want to change the pic, do it here */
- user_interface_update_status (ui, "robot sniffs...", energy, score, shields);
- g_usleep (USLEEP_TIME);
-}
-
-void user_interface_robot_zap (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields)
-{
- user_interface_update_status (ui, "robot fires his little gun...", energy, score, shields);
- g_usleep (USLEEP_TIME);
-}
-
-void user_interface_robot_feel (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields)
-{
- user_interface_update_status (ui, "robot feels for a thing...", energy, score, shields);
- g_usleep (USLEEP_TIME);
-}
-
-void user_interface_robot_grab (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields)
-{
- user_interface_update_status (ui, "robot grabs thing...", energy, score, shields);
- g_usleep (USLEEP_TIME);
-}
-
-void user_interface_robot_look (UserInterface *ui,
- gint x,
- gint y,
- gint cdir,
- gint x_to,
- gint y_to,
- glong energy,
- glong score,
- glong shields)
-{
- user_interface_update_status (ui, "robot looks for a thing...", energy, score, shields);
- g_usleep (USLEEP_TIME);
-}
-
-/* hooks to get/display data from/to user */
-void user_interface_get_string (UserInterface *ui,
- gchar *prompt,
- gchar *buff,
- gint len)
-{
- char* line = (char*)NULL;
-
- line = readline(prompt);
-
- if(line && *line)
- {
- add_history(line);
-
- g_strlcpy(buff, line, len);
- }
- else
- buff = "";
-
- free(line);
-}
-
-void ui_update_status (UserInterface *ui,
- const gchar *s,
- glong energy,
- glong score,
- glong shields)
-{
- gchar status[20];
- gint x = 0;
-
- while (x < ui->win_width) {
- XPutImage (ui->dpy, ui->win_buf, ui->buf_gc, ui->statusbar, 0, 0, x, ui->map_size->num_rows * TILE_SIZE, 96,
- 32);
- x = x + 96;
- }
-
- XDrawString (ui->dpy, ui->win_buf, ui->gc, 3, ui->map_size->num_rows * TILE_SIZE + 16, s, strlen (s));
-
- if (energy > -1) {
- g_sprintf (status, "Robot Energy: %3ld", energy);
- XDrawString (ui->dpy, ui->win_buf, ui->gc, 240, ui->map_size->num_rows * TILE_SIZE + 12, status,
- strlen (status));
- }
-
- if (score > -1) {
- g_sprintf (status, "Robot Score: %3ld", score);
- XDrawString (ui->dpy, ui->win_buf, ui->gc, 240, ui->map_size->num_rows * TILE_SIZE + 25, status,
- strlen (status));
- }
-
- if (shields > -1) {
- g_sprintf (status, "Robot Shields: %3ld", shields);
- XDrawString (ui->dpy, ui->win_buf, ui->gc, 480, ui->map_size->num_rows * TILE_SIZE + 12, status,
- strlen (status));
- }
-}
-
-void user_interface_update_status (UserInterface *ui,
- const gchar *s,
- glong energy,
- glong score,
- glong shields)
-{
- ui_update_status (ui, s, energy, score, shields);
-}
-
-void user_interface_run(UserInterface* ui)
-{
- XEvent ev;
- XClientMessageEvent* evt;
-
- while (TRUE)
- {
- XNextEvent (ui->dpy, &ev);
-
- switch (ev.type)
- {
- case KeyPress:
- case KeyRelease:
- switch (XKeycodeToKeysym (ui->dpy, ev.xkey.keycode, 0))
- {
- case XK_Escape:
- exit (0);
- break;
- }
- case ClientMessage:
- evt = (XClientMessageEvent*)&ev;
- if (evt->message_type == ui->wm_protocols
- && evt->data.l[0] == ui->wm_delete_win)
- {
- g_printf("Exited\n");
- exit(0);
- }
- break;
- case Expose:
- user_interface_draw(ui);
- break;
- }
- }
-
- put_winbuf (ui);
-}
-
-#ifdef USE_MITSHM
-static gint
-shm_error_handler (UserInterface *ui, Display * d, XErrorEvent * e)
-{
- ui->use_mitshm = 0;
- return 0;
-}
-#endif
-
-static void
-setup_winbuf (UserInterface *ui)
-{
- XVisualInfo *matches;
- XVisualInfo plate;
- gint count;
- guint depth;
- XGCValues values;
- Visual *vis;
-
- vis = DefaultVisualOfScreen (DefaultScreenOfDisplay (ui->dpy));
- plate.visualid = XVisualIDFromVisual (vis);
- matches = XGetVisualInfo (ui->dpy, VisualIDMask, &plate, &count);
- depth = matches[0].depth;
-
-#ifdef USE_MITSHM
- ui->use_mitshm = 1;
- ui->shm_info.shmid = shmget (IPC_PRIVATE, win_height * win_width * depth,
- IPC_CREAT | 0777);
- if (ui->shm_info.shmid < 0) {
- g_fprintf (stderr, "shmget failed, looks like I'll have to use XPutImage\n");
- ui->use_mitshm = 0;
- } else {
- ui->shm_info.shmaddr = (gchar *) shmat (ui->shm_info.shmid, 0, 0);
-
- if (!ui->shm_info.shmaddr) {
- g_fprintf (stderr, "shmat failed, looks like I'll have to use XPutImage\n");
- shmctl (ui->shm_info.shmid, IPC_RMID, 0);
- use_mitshm = 0;
- } else {
- XErrorHandler error_handler = XSetErrorHandler (shm_error_handler);
-
- ui->win_bufi = XShmCreateImage (ui->dpy, vis, depth, ZPixmap, ui->shm_info.shmaddr,
- &ui->shm_info, ui->win_width, ui->win_height);
- ui->shm_info.readOnly = False;
- XShmAttach (ui->dpy, &ui->shm_info);
- win_buf = XShmCreatePixmap (ui->dpy, ui->x_win, ui->shm_info.shmaddr, &ui->shm_info,
- ui->win_width, ui->win_height, depth);
- XSync (ui->dpy, False);
- (void) XSetErrorHandler (error_handler);
- if (!use_mitshm) {
- p_fprintf (stderr,
- "XShmAttach failed, looks like I'll have to use XPutImage\n");
- XFreePixmap (ui->dpy, ui->win_buf);
- XDestroyImage (ui->win_bufi);
- shmdt (ui->shm_info.shmaddr);
- shmctl (ui->shm_info.shmid, IPC_RMID, 0);
- }
- }
- }
-
- if (!ui->use_mitshm) {
-#endif /* USE_MITSHM */
- ui->win_buf = XCreatePixmap (ui->dpy, ui->x_win, ui->win_width, ui->win_height, depth);
-#ifdef USE_MITSHM
- } else {
- g_printf ("Using MIT Shared Memory Pixmaps. Good.\n", major, minor);
- }
-#endif
-
- values.font = ui->text;
- values.foreground = WhitePixel (ui->dpy, DefaultScreen (ui->dpy));
-
- ui->buf_gc = XCreateGC (ui->dpy, ui->win_buf, GCFont | GCForeground, &values);
-}
-
-void
-create_image (UserInterface *ui, gchar **data, XImage ** image)
-{
- XpmAttributes a;
- gint err;
-
- a.valuemask = XpmCloseness | XpmAllocCloseColors;
- a.closeness = 40000; /* the xpm manual suggests 40000 */
- a.alloc_close_colors = 1; /* allocate the colours chosen */
- err = XpmCreateImageFromData (ui->dpy, data, image, NULL, &a);
- if (err != 0) {
- g_fprintf (stderr, "Cannot create image from xpm: %s\n",
- XpmGetErrorString (err));
- exit (1);
- }
-}
-
-static void
-put_tile (UserInterface *ui, XImage *image, gint x, gint y)
-{
- XPutImage (ui->dpy, ui->win_buf, ui->gc, image, 0, 0, x, y, TILE_SIZE, TILE_SIZE);
-}
-
-static void put_winbuf (UserInterface *ui)
-{
-#ifdef USE_MITSHM
- if (use_mitshm)
- XShmPutImage (ui->dpy, ui->x_win, ui->gc, ui->win_bufi, 0, 0, 0, 0, ui->win_width, ui->win_height,
- False);
- else
-#endif
- XCopyArea (ui->dpy, ui->win_buf, ui->x_win, ui->gc, 0, 0, ui->win_width, ui->win_height, 0, 0);
-
- XSync (ui->dpy, 0);
-}
diff --git a/ui/Makefile.am b/ui/Makefile.am
deleted file mode 100644
index cf01f1b..0000000
--- a/ui/Makefile.am
+++ /dev/null
@@ -1,23 +0,0 @@
-## Copyright (C) 2008 Bradley Smith <brad@brad-smith.co.uk>
-##
-## src/Makefile.am
-##
-## GNU Robots is free software: you can redistribute it and/or modify
-## it under the terms of the GNU General Public License as published by
-## the Free Software Foundation, either version 3 of the License, or
-## (at your option) any later version.
-##
-## GNU Robots 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 General Public License for more details.
-##
-## You should have received a copy of the GNU General Public License
-## along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
-
-bin_PROGRAMS = uitest
-
-INCLUDES = $(GTK_CFLAGS) -I$(top_builddir)/ui/
-
-uitest_SOURCES = main.c ui-window.c ui-arena.c ui-cmdwin.c
-uitest_LDFLAGS = $(GTK_LIBS)
diff --git a/ui/design.glade b/ui/design.glade
deleted file mode 100644
index b8d6fba..0000000
--- a/ui/design.glade
+++ /dev/null
@@ -1,317 +0,0 @@
-<?xml version="1.0" encoding="UTF-8" standalone="no"?>
-<!DOCTYPE glade-interface SYSTEM "glade-2.0.dtd">
-<!--Generated with glade3 3.4.5 on Fri May 16 20:44:59 2008 -->
-<glade-interface>
- <widget class="GtkWindow" id="window1">
- <child>
- <widget class="GtkAlignment" id="alignment1">
- <property name="visible">True</property>
- <property name="left_padding">2</property>
- <property name="right_padding">2</property>
- <child>
- <widget class="GtkVBox" id="vbox1">
- <property name="visible">True</property>
- <child>
- <widget class="GtkMenuBar" id="menubar1">
- <property name="visible">True</property>
- <child>
- <widget class="GtkMenuItem" id="menuitem1">
- <property name="visible">True</property>
- <property name="label" translatable="yes">_File</property>
- <property name="use_underline">True</property>
- <child>
- <widget class="GtkMenu" id="menu1">
- <property name="visible">True</property>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem1">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-new</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem2">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-open</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem3">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-save</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem4">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-save-as</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkSeparatorMenuItem" id="separatormenuitem1">
- <property name="visible">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem5">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-quit</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- </widget>
- </child>
- </widget>
- </child>
- <child>
- <widget class="GtkMenuItem" id="menuitem2">
- <property name="visible">True</property>
- <property name="label" translatable="yes">_Edit</property>
- <property name="use_underline">True</property>
- <child>
- <widget class="GtkMenu" id="menu2">
- <property name="visible">True</property>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem6">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-cut</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem7">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-copy</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem8">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-paste</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem9">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-delete</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- </widget>
- </child>
- </widget>
- </child>
- <child>
- <widget class="GtkMenuItem" id="menuitem3">
- <property name="visible">True</property>
- <property name="label" translatable="yes">_View</property>
- <property name="use_underline">True</property>
- </widget>
- </child>
- <child>
- <widget class="GtkMenuItem" id="menuitem4">
- <property name="visible">True</property>
- <property name="label" translatable="yes">_Help</property>
- <property name="use_underline">True</property>
- <child>
- <widget class="GtkMenu" id="menu3">
- <property name="visible">True</property>
- <child>
- <widget class="GtkImageMenuItem" id="imagemenuitem10">
- <property name="visible">True</property>
- <property name="label" translatable="yes">gtk-about</property>
- <property name="use_underline">True</property>
- <property name="use_stock">True</property>
- </widget>
- </child>
- </widget>
- </child>
- </widget>
- </child>
- </widget>
- <packing>
- <property name="expand">False</property>
- </packing>
- </child>
- <child>
- <widget class="GtkToolbar" id="toolbar1">
- <property name="visible">True</property>
- <child>
- <widget class="GtkToolButton" id="toolbutton1">
- <property name="visible">True</property>
- <property name="stock_id">gtk-open</property>
- </widget>
- <packing>
- <property name="expand">False</property>
- </packing>
- </child>
- </widget>
- <packing>
- <property name="expand">False</property>
- <property name="position">1</property>
- </packing>
- </child>
- <child>
- <widget class="GtkVPaned" id="vpaned1">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <child>
- <widget class="GtkAlignment" id="alignment2">
- <property name="visible">True</property>
- <property name="extension_events">GDK_EXTENSION_EVENTS_ALL</property>
- <property name="top_padding">3</property>
- <property name="bottom_padding">3</property>
- <child>
- <widget class="GtkImage" id="image1">
- <property name="visible">True</property>
- <property name="extension_events">GDK_EXTENSION_EVENTS_ALL</property>
- <property name="stock">gtk-missing-image</property>
- <property name="icon_size">6</property>
- </widget>
- </child>
- </widget>
- <packing>
- <property name="resize">False</property>
- <property name="shrink">True</property>
- </packing>
- </child>
- <child>
- <widget class="GtkVBox" id="vbox2">
- <property name="visible">True</property>
- <child>
- <widget class="GtkHBox" id="hbox1">
- <property name="visible">True</property>
- <property name="spacing">11</property>
- <child>
- <widget class="GtkHBox" id="hbox3">
- <property name="visible">True</property>
- <child>
- <widget class="GtkButton" id="button1">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="relief">GTK_RELIEF_NONE</property>
- <property name="focus_on_click">False</property>
- <property name="response_id">0</property>
- <child>
- <widget class="GtkImage" id="image2">
- <property name="visible">True</property>
- <property name="stock">gtk-media-play</property>
- </widget>
- </child>
- </widget>
- <packing>
- <property name="expand">False</property>
- </packing>
- </child>
- <child>
- <widget class="GtkButton" id="button2">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="relief">GTK_RELIEF_NONE</property>
- <property name="focus_on_click">False</property>
- <property name="response_id">0</property>
- <child>
- <widget class="GtkImage" id="image3">
- <property name="visible">True</property>
- <property name="stock">gtk-media-next</property>
- </widget>
- </child>
- </widget>
- <packing>
- <property name="expand">False</property>
- <property name="position">1</property>
- </packing>
- </child>
- </widget>
- <packing>
- <property name="expand">False</property>
- </packing>
- </child>
- <child>
- <widget class="GtkHBox" id="hbox4">
- <property name="visible">True</property>
- <property name="spacing">2</property>
- <child>
- <widget class="GtkLabel" id="label2">
- <property name="visible">True</property>
- <property name="xalign">1</property>
- <property name="label" translatable="yes">Speed</property>
- <property name="justify">GTK_JUSTIFY_RIGHT</property>
- </widget>
- <packing>
- <property name="expand">False</property>
- </packing>
- </child>
- <child>
- <widget class="GtkHScale" id="hscale1">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="adjustment">0 0 100 1 10 10</property>
- <property name="value_pos">GTK_POS_RIGHT</property>
- </widget>
- <packing>
- <property name="position">1</property>
- </packing>
- </child>
- </widget>
- <packing>
- <property name="position">1</property>
- </packing>
- </child>
- </widget>
- <packing>
- <property name="expand">False</property>
- </packing>
- </child>
- <child>
- <widget class="GtkLabel" id="label3">
- <property name="visible">True</property>
- <property name="label" translatable="yes">Commands/Interaction</property>
- </widget>
- <packing>
- <property name="position">1</property>
- </packing>
- </child>
- </widget>
- <packing>
- <property name="resize">False</property>
- <property name="shrink">True</property>
- </packing>
- </child>
- </widget>
- <packing>
- <property name="position">2</property>
- </packing>
- </child>
- <child>
- <widget class="GtkStatusbar" id="statusbar1">
- <property name="visible">True</property>
- <property name="spacing">2</property>
- </widget>
- <packing>
- <property name="expand">False</property>
- <property name="position">3</property>
- </packing>
- </child>
- </widget>
- </child>
- </widget>
- </child>
- </widget>
-</glade-interface>
diff --git a/ui/main.c b/ui/main.c
deleted file mode 100644
index da7e94c..0000000
--- a/ui/main.c
+++ /dev/null
@@ -1,34 +0,0 @@
-/* Copyright (C) 2008 Bradley Smith <brad@brad-smith.co.uk>
- *
- * GNU Robots UI Test, main.c.
- *
- * GNU Robots is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * GNU Robots 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 General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <gtk/gtkmain.h>
-
-#include "ui-window.h"
-
-int main(int argc, char* argv[])
-{
- GtkWidget* window;
-
- gtk_init(&argc, &argv);
-
- window = ui_window_new();
-
- gtk_main();
-
- return 0;
-}
diff --git a/ui/ui-arena.c b/ui/ui-arena.c
deleted file mode 100644
index 06c7bcc..0000000
--- a/ui/ui-arena.c
+++ /dev/null
@@ -1,45 +0,0 @@
-/* Copyright (C) 2008 Bradley Smith <brad@brad-smith.co.uk>
- *
- * GNU Robots, ui-arena.c
- *
- * GNU Robots is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * GNU Robots 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 General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with GNU Robots. If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include "ui-arena.h"
-
-struct _UIArenaPrivate
-{
- int dummy;
-};
-
-#define UI_ARENA_GET_PRIVATE(obj) \
- G_TYPE_INSTANCE_GET_PRIVATE(obj, UI_TYPE_ARENA, UIArenaPrivate)
-
-G_DEFINE_TYPE(UIArena, ui_arena, GTK_TYPE_DRAWING_AREA)
-
-GtkWidget *ui_arena_new(void)
-{
- return GTK_WIDGET(g_object_new(UI_TYPE_ARENA, NULL));
-}
-
-static void ui_arena_init(UIArena *arena)
-{
- gtk_widget_set_size_request(GTK_WIDGET(arena), 40*16,18*16);
-}
-
-static void ui_arena_class_init(UIArenaClass *klass)
-{
- g_type_class_add_private(G_OBJECT_CLASS(klass),
- sizeof(UIArenaPrivate));
-}