commit f45b3ebaf8008da2fe43dfd59f99e0459e566e71
Author: Rik Veenboer
Date: Sat Oct 18 17:43:25 2014 +0100
Import from http://drts.cvs.sourceforge.net/viewvc/drts/projects/jxinput/ tarball
diff --git a/.cvsignore b/.cvsignore
new file mode 100644
index 0000000..21df587
--- /dev/null
+++ b/.cvsignore
@@ -0,0 +1,5 @@
+classes
+tmp
+build
+archiv
+
diff --git a/etc/build.xml b/etc/build.xml
new file mode 100644
index 0000000..509822e
--- /dev/null
+++ b/etc/build.xml
@@ -0,0 +1,68 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/etc/nb5/.cvsignore b/etc/nb5/.cvsignore
new file mode 100644
index 0000000..9d0b71a
--- /dev/null
+++ b/etc/nb5/.cvsignore
@@ -0,0 +1,2 @@
+build
+dist
diff --git a/etc/nb5/build.xml b/etc/nb5/build.xml
new file mode 100644
index 0000000..80ab72e
--- /dev/null
+++ b/etc/nb5/build.xml
@@ -0,0 +1,69 @@
+
+
+
+
+
+ Builds, tests, and runs the project jxinput.
+
+
+
diff --git a/etc/nb5/manifest.mf b/etc/nb5/manifest.mf
new file mode 100644
index 0000000..328e8e5
--- /dev/null
+++ b/etc/nb5/manifest.mf
@@ -0,0 +1,3 @@
+Manifest-Version: 1.0
+X-COMMENT: Main-Class will be added automatically by build
+
diff --git a/etc/nb5/nbproject/.cvsignore b/etc/nb5/nbproject/.cvsignore
new file mode 100644
index 0000000..3e18ebf
--- /dev/null
+++ b/etc/nb5/nbproject/.cvsignore
@@ -0,0 +1 @@
+private
diff --git a/etc/nb5/nbproject/build-impl.xml b/etc/nb5/nbproject/build-impl.xml
new file mode 100644
index 0000000..08b7cd7
--- /dev/null
+++ b/etc/nb5/nbproject/build-impl.xml
@@ -0,0 +1,532 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Must set src.dir
+ Must set build.dir
+ Must set dist.dir
+ Must set build.classes.dir
+ Must set dist.javadoc.dir
+ Must set build.test.classes.dir
+ Must set build.test.results.dir
+ Must set build.classes.excludes
+ Must set dist.jar
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Must select some files in the IDE or set javac.includes
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ To run this application from the command line without Ant, try:
+
+
+
+
+
+
+ java -cp "${run.classpath.with.dist.jar}" ${main.class}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ To run this application from the command line without Ant, try:
+
+ java -jar "${dist.jar.resolved}"
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Must select one file in the IDE or set run.class
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Must select one file in the IDE or set debug.class
+
+
+
+
+ Must set fix.includes
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Must select some files in the IDE or set javac.includes
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Some tests failed; see details above.
+
+
+
+
+
+
+
+
+ Must select some files in the IDE or set test.includes
+
+
+
+ Some tests failed; see details above.
+
+
+
+
+ Must select one file in the IDE or set test.class
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Must select one file in the IDE or set applet.url
+
+
+
+
+
+
+
+
+ Must select one file in the IDE or set applet.url
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/etc/nb5/nbproject/genfiles.properties b/etc/nb5/nbproject/genfiles.properties
new file mode 100644
index 0000000..a6c84f7
--- /dev/null
+++ b/etc/nb5/nbproject/genfiles.properties
@@ -0,0 +1,8 @@
+build.xml.data.CRC32=3ba4020f
+build.xml.script.CRC32=654a06bb
+build.xml.stylesheet.CRC32=d5b6853a
+# This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
+# Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
+nbproject/build-impl.xml.data.CRC32=3ba4020f
+nbproject/build-impl.xml.script.CRC32=00e7e9f7
+nbproject/build-impl.xml.stylesheet.CRC32=99b91518
diff --git a/etc/nb5/nbproject/project.properties b/etc/nb5/nbproject/project.properties
new file mode 100644
index 0000000..a0f0bc5
--- /dev/null
+++ b/etc/nb5/nbproject/project.properties
@@ -0,0 +1,57 @@
+application.args=
+build.classes.dir=${build.dir}/classes
+build.classes.excludes=**/*.java,**/*.form
+# This directory is removed when the project is cleaned:
+build.dir=build
+build.generated.dir=${build.dir}/generated
+# Only compile against the classpath explicitly listed here:
+build.sysclasspath=ignore
+build.test.classes.dir=${build.dir}/test/classes
+build.test.results.dir=${build.dir}/test/results
+debug.classpath=\
+ ${run.classpath}
+debug.test.classpath=\
+ ${run.test.classpath}
+# This directory is removed when the project is cleaned:
+dist.dir=dist
+dist.jar=${dist.dir}/jxinput.jar
+dist.javadoc.dir=${dist.dir}/javadoc
+file.reference.jxinput-java=../../java
+jar.compress=false
+javac.classpath=\
+ ${libs.Java3D.classpath}
+# Space-separated list of extra javac options
+javac.compilerargs=
+javac.deprecation=false
+javac.source=1.5
+javac.target=1.5
+javac.test.classpath=\
+ ${javac.classpath}:\
+ ${build.classes.dir}:\
+ ${libs.junit.classpath}
+javadoc.additionalparam=
+javadoc.author=false
+javadoc.encoding=
+javadoc.noindex=false
+javadoc.nonavbar=false
+javadoc.notree=false
+javadoc.private=false
+javadoc.splitindex=true
+javadoc.use=true
+javadoc.version=false
+javadoc.windowtitle=
+main.class=de.hardcode.jxinput.test.JXInputTestDialog
+manifest.file=manifest.mf
+meta.inf.dir=${src.dir}/META-INF
+platform.active=default_platform
+run.classpath=\
+ ${javac.classpath}:\
+ ${build.classes.dir}
+# Space-separated list of JVM arguments used when running the project
+# (you may also define separate properties like run-sys-prop.name=value instead of -Dname=value
+# or test-sys-prop.name=value to set system properties for unit tests):
+run.jvmargs=
+run.test.classpath=\
+ ${javac.test.classpath}:\
+ ${build.test.classes.dir}
+src.dir=${file.reference.jxinput-java}
diff --git a/etc/nb5/nbproject/project.xml b/etc/nb5/nbproject/project.xml
new file mode 100644
index 0000000..9f941d5
--- /dev/null
+++ b/etc/nb5/nbproject/project.xml
@@ -0,0 +1,14 @@
+
+
+ org.netbeans.modules.java.j2seproject
+
+
+ jxinput
+ 1.6.5
+
+
+
+
+
+
+
diff --git a/java/de/hardcode/jxinput/Axis.java b/java/de/hardcode/jxinput/Axis.java
new file mode 100644
index 0000000..9f1d710
--- /dev/null
+++ b/java/de/hardcode/jxinput/Axis.java
@@ -0,0 +1,72 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 19. Dezember 2001, 21:58
+//**********************************************************************************************
+package de.hardcode.jxinput;
+
+/**
+ * The Axis interface describes the most common feature of a joystick or other input devices.
+ *
+ * @author Herkules
+ */
+public interface Axis extends Feature
+{
+ // Enumeration of axes.
+ final static int ID_X = 0;
+ final static int ID_Y = 1;
+ final static int ID_Z = 2;
+ final static int ID_ROTX = 3;
+ final static int ID_ROTY = 4;
+ final static int ID_ROTZ = 5;
+ final static int ID_SLIDER0 = 6;
+ final static int ID_SLIDER1 = 7;
+ final static int NUMBER_OF_ID = 8;
+
+ // Enumeration of axis types
+ final static int TRANSLATION = 0;
+ final static int ROTATION = 1;
+ final static int SLIDER = 2;
+
+ /**
+ * Retrieve the type of the axis.
+ * The type is describes the meaning and the range of values of the axis.
+ *
+ * TRANSLATION typed axes denote a translational deviation from a center
+ * position. This can be e.g. the common, basic joystick axes.
+ * The range of getValue() is [-1.0,1.0].
+ *
+ * ROTATION typed axes denote a rotational deviation from a center
+ * position. Something on the stick is turned or twisted.
+ * The range of getValue() is [-1.0,1.0].
+ *
+ * SLIDER typed axes denote a shifting device without a center position.
+ * A good sample is a throttle control.
+ * The range of getValue() is [0.0,1.0].
+ *
+ * @return [ TRANSLATION | ROTATION | SLIDER ]
+ */
+ int getType();
+
+ /**
+ * Returns the current value of the axis.
+ * The range of the result depends on the axis type.
+ *
+ * @return value [-1.0,1.0] or [0.0,1.0]
+ */
+ double getValue();
+
+
+ /**
+ * Inform about the resolution of the axis.
+ *
+ * @return resolution, e.g. 2^-16
+ */
+ double getResolution();
+
+}
+
+
diff --git a/java/de/hardcode/jxinput/Button.java b/java/de/hardcode/jxinput/Button.java
new file mode 100644
index 0000000..418e2b6
--- /dev/null
+++ b/java/de/hardcode/jxinput/Button.java
@@ -0,0 +1,35 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 19. Dezember 2001, 21:58
+//**********************************************************************************************
+package de.hardcode.jxinput;
+
+/**
+ *
+ * @author Herkules
+ */
+public interface Button extends Feature
+{
+ // Enumeration of button types
+ final static int PUSHBUTTON = 0;
+ final static int TOGGLEBUTTON = 1;
+
+ /**
+ * Retrieve the type of the button.
+ * Pushbutton will deliver true==getState() as long as they are pressed down.
+ * Togglebuttons will change their state once they are pressed and keep that state
+ * until they are pressed again.
+ * @return [ PUSHBUTTON | TOGGLEBUTTON ]
+ */
+ int getType();
+
+ /**
+ * Tells the state of the button at last update.
+ */
+ boolean getState();
+}
+
diff --git a/java/de/hardcode/jxinput/Directional.java b/java/de/hardcode/jxinput/Directional.java
new file mode 100644
index 0000000..ccd27c1
--- /dev/null
+++ b/java/de/hardcode/jxinput/Directional.java
@@ -0,0 +1,45 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 27. Dezember 2001, 23:33
+//**********************************************************************************************
+package de.hardcode.jxinput;
+
+/**
+ *
+ * @author Herkules
+ */
+public interface Directional extends Feature
+{
+ /**
+ * If the Directional has a center position where it points to no direction, this
+ * flag is true when this position is reached.
+ */
+ boolean isCentered();
+
+ /**
+ * Retrieve the direction pointed to.
+ * Value is given in 1/100 degree, [0,36000]
+ */
+ int getDirection();
+
+ /**
+ * Retrieve the analog value pointing to the angle described by
+ * getDirection().
+ * For coolie hats this will be either 1,0 for any direction or 0.0
+ * when isCentered()==true.
+ */
+ double getValue();
+
+ /**
+ * Inform about the resolution of the value returned by getValue().
+ *
+ * @return resolution, e.g. 1.0 for coolie hats
+ */
+ double getResolution();
+
+}
+
diff --git a/java/de/hardcode/jxinput/Feature.java b/java/de/hardcode/jxinput/Feature.java
new file mode 100644
index 0000000..20c396f
--- /dev/null
+++ b/java/de/hardcode/jxinput/Feature.java
@@ -0,0 +1,38 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 27. Dezember 2001, 00:19
+//**********************************************************************************************
+package de.hardcode.jxinput;
+
+/**
+ * An input device offers a set of features (otherwise it would be pretty useless).
+ * Features in this sense can be axes, buttons and a feature callede directional here.
+ * Coolie hats are typical directionals because they control a direction (to look at e.g.).
+ *
+ * There are no concrete classes directly derived from Feature - it only
+ * provides a basis for other interfaces.
+ *
+ * @see Axis
+ * @see Button
+ * @see Directional
+ *
+ * @author Herkules
+ */
+public abstract interface Feature
+{
+ /**
+ * Features may have a name provided e.g. by the driver.
+ */
+ String getName();
+
+ /**
+ * Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ boolean hasChanged();
+}
+
diff --git a/java/de/hardcode/jxinput/JXInputDevice.java b/java/de/hardcode/jxinput/JXInputDevice.java
new file mode 100644
index 0000000..d8a8bc8
--- /dev/null
+++ b/java/de/hardcode/jxinput/JXInputDevice.java
@@ -0,0 +1,71 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 19. Dezember 2001, 21:47
+//**********************************************************************************************
+package de.hardcode.jxinput;
+
+/**
+ * The JXInputDevise is the main entrypoint to the jxinput package.
+ *
+ * A JXInputDevice represents one physical device like a joystick, a gamepad or
+ * even some emulation (e.g. using keyboard) that implements the interface.
+ *
+ * The basis task of a JXInputDevise is to maintain a consistent state of all its features.
+ *
+ * It is save to distribute the Feature objects into application without worrying
+ * about someone else performing an update method and thereby destructing the consistent state.
+ *
+ * An additional task is to provide basic device features information like number of axes, buttons
+ * and directional features.
+ *
+ * @see Feature
+ * @see JXInputManager
+ *
+ * @author Herkules
+ * @version 0.2beta
+ */
+public interface JXInputDevice
+{
+ /**
+ * @directed
+ */
+ /*#Features lnkFeatures;*/
+
+ /**
+ *@link aggregationByValue
+ */
+ /*#Feature lnkFeature;*/
+
+ /**
+ * Devices may have a name.
+ * This name might be provided by a system dependant driver.
+ */
+ String getName();
+
+ /** Actual number of available axes. */
+ int getNumberOfAxes();
+
+ /** Actual number of available buttons. */
+ int getNumberOfButtons();
+
+ /** Actual number of available directional features. */
+ int getNumberOfDirectionals();
+
+ /** Maximum number of axes as an upper bound for index values. */
+ int getMaxNumberOfAxes();
+
+ /** Maximum number of buttons as an upper bound for index values. */
+ int getMaxNumberOfButtons();
+
+ /** Maximum number of directional features as an upper bound for index values. */
+ int getMaxNumberOfDirectionals();
+
+ Axis getAxis( int idx );
+ Button getButton( int idx );
+ Directional getDirectional( int idx );
+}
+
diff --git a/java/de/hardcode/jxinput/JXInputManager.java b/java/de/hardcode/jxinput/JXInputManager.java
new file mode 100644
index 0000000..8c3e050
--- /dev/null
+++ b/java/de/hardcode/jxinput/JXInputManager.java
@@ -0,0 +1,233 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 29. Dezember 2001, 02:17
+//**********************************************************************************************
+package de.hardcode.jxinput;
+
+//
+// Import driver stuff
+//
+import de.hardcode.jxinput.directinput.DirectInputDevice;
+import de.hardcode.jxinput.event.JXInputEventManager;
+import de.hardcode.jxinput.keyboard.JXKeyboardInputDevice;
+import de.hardcode.jxinput.virtual.JXVirtualInputDevice;
+
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.awt.Component;
+
+
+/**
+ * Manages the available instances of JXInputDevice.
+ * It holds the one central update method which synchronizes with the physical device.
+ * @author Herkules
+ */
+public class JXInputManager
+{
+
+ /** Remember when the last update took place. */
+ private static long mTimeOfLastUpdate;
+
+ /** Maintain a list of devices. */
+ private final static ArrayList mDevices = new ArrayList();
+
+ /** Maintain a list of direct input devices. */
+ private final static ArrayList mDIDevices = new ArrayList();
+
+ /** Maintain a list of virtual devices. */
+ private final static ArrayList mVirtualDevices = new ArrayList();
+
+ /** Maintain a list of keyboard devices. */
+ private final static ArrayList mKBDevices = new ArrayList();
+
+ /**
+ * Statically retrieve all DirectInputDevices available.
+ */
+ static
+ {
+ reset();
+ }
+
+
+ /**
+ * @directed
+ */
+ /*#JXInputDevice lnkJXInputDevice;*/
+
+ /**
+ * Creates a new instance of JXInputManager.
+ * This is prohibited - it only has static members.
+ */
+ private JXInputManager()
+ {
+ }
+
+
+ /**
+ * Retrieve the number of available input devices.
+ */
+ public static int getNumberOfDevices()
+ {
+ return mDevices.size();
+ }
+
+ /**
+ * Delivers the JXInputDevice with the desired index.
+ *
+ * Take care that idx < getNumberOfDevices()!
+ */
+ public static JXInputDevice getJXInputDevice( int idx )
+ {
+ //
+ // Be well-behaved even if idx is out of range.
+ //
+ if ( idx >= mDevices.size() )
+ return null;
+ return (JXInputDevice)mDevices.get( idx );
+ }
+
+
+ /**
+ * Master reset for all devices and events.
+ * After calling reset(), better forget all devices created or retrieved.
+ * They are no longer valid.
+ * Event listeners will no longer be called and should be discarded.
+ */
+ synchronized public static void reset()
+ {
+ JXInputEventManager.reset();
+
+ mDevices.clear();
+
+ mVirtualDevices.clear();
+ mDIDevices.clear();
+
+ DirectInputDevice.reset();
+
+ for ( int i = 0; i < DirectInputDevice.getNumberOfDevices(); ++i )
+ {
+ DirectInputDevice dev = new DirectInputDevice( i );
+ mDevices.add( dev );
+ mDIDevices.add( dev );
+ }
+
+ // I have to call updateFeatures one time here during initialization
+ // bc. I experienced difficulties otherwise while running with the
+ // J3D sensoring stuff!
+// updateFeatures();
+ DirectInputDevice.update();
+
+ int n = mKBDevices.size();
+ for ( int i = 0; i < n; ++i )
+ ((JXKeyboardInputDevice)mKBDevices.get( i )).shutdown();
+ mKBDevices.clear();
+ }
+
+
+ /**
+ * Update the (shared) state of all features in one step.
+ * This method asks the actual device for a consistant state.
+ * After calling this method, all features may have new values.
+ * updateFeatures() is meant to be called e.g. once per frame in a gaming environment.
+ */
+ public static void updateFeatures()
+ {
+ // Get timing
+ long now = System.currentTimeMillis();
+ long deltaT = now - mTimeOfLastUpdate;
+
+ // Update available driver
+ DirectInputDevice.update();
+
+ //
+ // Update the virtual devices.
+ //
+ Iterator vdevices = mVirtualDevices.iterator();
+ while ( vdevices.hasNext() )
+ {
+ ((JXVirtualInputDevice)vdevices.next()).update( deltaT );
+ }
+
+ // Remember time
+ mTimeOfLastUpdate = now;
+
+ // Fire all events.
+ JXInputEventManager.trigger();
+ }
+
+
+
+ /**
+ * Get time when last update occurred.
+ * @return tickervalue in milliseconds
+ */
+ public static long getLastUpdateTime()
+ {
+ return mTimeOfLastUpdate;
+ }
+
+
+ /**
+ * Create a new pseudo-device.
+ */
+ public static JXKeyboardInputDevice createKeyboardDevice()
+ {
+ JXKeyboardInputDevice d = new JXKeyboardInputDevice();
+ mDevices.add( d );
+ mKBDevices.add( d );
+ return d;
+ }
+
+
+ /**
+ * Create a new pseudo-device listening to a Swing component.
+ * Make sure that the component also has the keyboard focus!!
+ */
+ public static JXKeyboardInputDevice createKeyboardDevice( Component comp )
+ {
+ JXKeyboardInputDevice d = new JXKeyboardInputDevice( comp );
+ mDevices.add( d );
+ mKBDevices.add( d );
+ return d;
+ }
+
+
+ /**
+ * Delete a keyboard device again e.g. when the corresponding
+ * JComponent gets deleted.
+ */
+ public static void deleteKeyboardDevice( JXKeyboardInputDevice dev )
+ {
+ mDevices.remove( dev );
+ mKBDevices.remove( dev );
+ ((JXKeyboardInputDevice)dev).shutdown();
+ }
+
+
+ /**
+ * Create a new pseudo-device.
+ */
+ public static JXVirtualInputDevice createVirtualDevice()
+ {
+ JXVirtualInputDevice d = new JXVirtualInputDevice();
+ mDevices.add( d );
+ mVirtualDevices.add( d );
+ return d;
+ }
+
+
+ /**
+ * Delete a virtual device again.
+ */
+ public static void deleteVirtualDevice( JXVirtualInputDevice dev )
+ {
+ mDevices.remove( dev );
+ mVirtualDevices.remove( dev );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/directinput/DIAxis.java b/java/de/hardcode/jxinput/directinput/DIAxis.java
new file mode 100644
index 0000000..a6d0eac
--- /dev/null
+++ b/java/de/hardcode/jxinput/directinput/DIAxis.java
@@ -0,0 +1,70 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 27. Dezember 2001, 00:14
+//**********************************************************************************************
+package de.hardcode.jxinput.directinput;
+
+import de.hardcode.jxinput.Axis;
+
+/**
+ *
+ * @author Herkules
+ */
+class DIAxis implements Axis
+{
+ private final int mDeviceIdx;
+ private final int mIdx;
+
+ /**
+ * Creates a new instance of DIAxis.
+ */
+ DIAxis( int devidx, int idx )
+ {
+ mDeviceIdx = devidx;
+ mIdx = idx;
+ }
+
+ public String getName()
+ {
+ return DirectInputDriver.getAxisName( mDeviceIdx, mIdx );
+ }
+
+
+ /**
+ * Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ public boolean hasChanged()
+ {
+ return true;
+ }
+
+ public double getValue()
+ {
+ return DirectInputDriver.getAxisValue( mDeviceIdx, mIdx );
+ }
+
+ public int getType()
+ {
+ return DirectInputDriver.getAxisType( mDeviceIdx, mIdx );
+ }
+
+ /**
+ * Inform about the resolution of the axis.
+ *
+ * @return resolution, e.g. 2^-16
+ */
+ public double getResolution()
+ {
+ // extend the driver here!!
+ // Here I assume typical 16 bit resolution
+ return ( getType() == Axis.SLIDER ? 1.0/65536.0 : 2.0/65536.0 ) ;
+ }
+
+}
+
+
diff --git a/java/de/hardcode/jxinput/directinput/DIButton.java b/java/de/hardcode/jxinput/directinput/DIButton.java
new file mode 100644
index 0000000..5419550
--- /dev/null
+++ b/java/de/hardcode/jxinput/directinput/DIButton.java
@@ -0,0 +1,55 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 27. Dezember 2001, 00:14
+//**********************************************************************************************
+package de.hardcode.jxinput.directinput;
+
+import de.hardcode.jxinput.Button;
+
+
+/**
+ *
+ * @author Herkules
+ */
+class DIButton implements Button
+{
+ private final int mDeviceIdx;
+ private final int mIdx;
+
+ /**
+ * Creates a new instance of DIButton.
+ */
+ DIButton( int devidx, int idx )
+ {
+ mDeviceIdx = devidx;
+ mIdx = idx;
+ }
+
+ public String getName()
+ {
+ return DirectInputDriver.getButtonName( mDeviceIdx, mIdx );
+ }
+
+ /**
+ * Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ public boolean hasChanged()
+ {
+ return true;
+ }
+
+ public int getType()
+ {
+ return DirectInputDriver.getButtonType( mDeviceIdx, mIdx );
+ }
+
+ public boolean getState()
+ {
+ return DirectInputDriver.getButtonState( mDeviceIdx, mIdx );
+ }
+}
\ No newline at end of file
diff --git a/java/de/hardcode/jxinput/directinput/DIDirectional.java b/java/de/hardcode/jxinput/directinput/DIDirectional.java
new file mode 100644
index 0000000..9da2d3d
--- /dev/null
+++ b/java/de/hardcode/jxinput/directinput/DIDirectional.java
@@ -0,0 +1,78 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 27. Dezember 2001, 23:40
+//**********************************************************************************************
+package de.hardcode.jxinput.directinput;
+
+import de.hardcode.jxinput.Directional;
+
+/**
+ *
+ * @author Herkules
+ */
+class DIDirectional implements Directional
+{
+ private final int mDeviceIdx;
+ private final int mIdx;
+
+ /**
+ * Creates a new instance of DIDirectional.
+ */
+ DIDirectional( int devidx, int idx )
+ {
+ mDeviceIdx = devidx;
+ mIdx = idx;
+ }
+
+ /** Features may have a name provided e.g. by the driver. */
+ public String getName()
+ {
+ return DirectInputDriver.getDirectionalName( mDeviceIdx, mIdx );
+ }
+
+ /**
+ * Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ public boolean hasChanged()
+ {
+ return true;
+ }
+
+
+ public boolean isCentered()
+ {
+ return ( 0xffff == (DirectInputDriver.getDirection( mDeviceIdx, mIdx ) & 0xffff) );
+ }
+
+ public int getDirection()
+ {
+ return isCentered() ? 0 : DirectInputDriver.getDirection( mDeviceIdx, mIdx );
+ }
+
+ public double getValue()
+ {
+ if ( isCentered() )
+ return 0.0;
+ return 1.0;
+ }
+
+ /**
+ * Inform about the resolution of the value returned by getValue().
+ *
+ * @return resolution, e.g. 1.0 for coolie hats
+ */
+ public double getResolution()
+ {
+ // DI POV always return 0.0 or 1.0, so the resolution is 1.0.
+ return 1.0;
+ }
+
+
+}
+
+
diff --git a/java/de/hardcode/jxinput/directinput/DirectInputDevice.java b/java/de/hardcode/jxinput/directinput/DirectInputDevice.java
new file mode 100644
index 0000000..a20eab3
--- /dev/null
+++ b/java/de/hardcode/jxinput/directinput/DirectInputDevice.java
@@ -0,0 +1,170 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 26. Dezember 2001, 00:40
+//**********************************************************************************************
+package de.hardcode.jxinput.directinput;
+
+import de.hardcode.jxinput.JXInputDevice;
+import de.hardcode.jxinput.Axis;
+import de.hardcode.jxinput.Directional;
+import de.hardcode.jxinput.Button;
+
+/**
+ *
+ * @author Herkules
+ */
+public class DirectInputDevice implements JXInputDevice
+{
+ int mDeviceIdx;
+
+ private DIAxis[] mAxes;
+ private DIButton[] mButtons;
+ private DIDirectional[] mDirectionals;
+
+ /**
+ * The number of DirectInput devices available with the driver.
+ */
+ public static int getNumberOfDevices()
+ {
+ if ( DirectInputDriver.isAvailable() )
+ return DirectInputDriver.getNumberOfDevices();
+ return 0;
+ }
+
+
+ /**
+ * Update the state of all devices.
+ */
+ public static void update()
+ {
+ if ( DirectInputDriver.isAvailable() )
+ DirectInputDriver.nativeupdate();
+ }
+
+
+
+
+ /**
+ * Creates a new instance of DirectInputDevice.
+ */
+ public DirectInputDevice( int devidx )
+ {
+ mDeviceIdx = devidx;
+
+ init();
+ }
+
+ /**
+ * Reset the DirectInput connection.
+ */
+ public static void reset()
+ {
+ if ( DirectInputDriver.isAvailable() )
+ DirectInputDriver.reset();
+ }
+
+
+ /**
+ * Initialisation of fields.
+ */
+ private final void init()
+ {
+ //
+ // Allocate arrays for max. number of features
+ //
+ mAxes = new DIAxis [ getMaxNumberOfAxes() ];
+ mButtons = new DIButton [ getMaxNumberOfButtons() ];
+ mDirectionals = new DIDirectional [ getMaxNumberOfDirectionals() ];
+
+ //
+ // Fill arrays due to the state of the driver.
+ //
+ for ( int i = 0; i < mAxes.length; ++i )
+ {
+ if ( DirectInputDriver.isAxisAvailable( mDeviceIdx, i ) )
+ mAxes[ i ] = new DIAxis( mDeviceIdx, i );
+ }
+
+ for ( int i = 0; i < mButtons.length; ++i )
+ {
+ if ( DirectInputDriver.isButtonAvailable( mDeviceIdx, i ) )
+ mButtons[ i ] = new DIButton( mDeviceIdx, i );
+ }
+
+ for ( int i = 0; i < mDirectionals.length; ++i )
+ {
+ if ( DirectInputDriver.isDirectionalAvailable( mDeviceIdx, i ) )
+ mDirectionals[ i ] = new DIDirectional( mDeviceIdx, i );
+ }
+ }
+
+ /** Devices may have a name. */
+ public String getName()
+ {
+ String name = DirectInputDriver.getName( mDeviceIdx );
+ if ( null == name )
+ return "Win32 DirectInput Joystick";
+ return name;
+ }
+
+
+ /** Actual number of available buttons. */
+ public int getNumberOfButtons()
+ {
+ return DirectInputDriver.getNumberOfButtons( mDeviceIdx );
+ }
+
+ /** Actual number of available axes. */
+ public int getNumberOfAxes()
+ {
+ return DirectInputDriver.getNumberOfAxes( mDeviceIdx );
+ }
+
+ /** Actual number of available directional features. */
+ public int getNumberOfDirectionals()
+ {
+ return DirectInputDriver.getNumberOfDirectionals( mDeviceIdx );
+ }
+
+ /** Maximum number of buttons as an upper bound for index values. */
+ public int getMaxNumberOfButtons()
+ {
+ return DirectInputDriver.getMaxNumberOfButtons();
+ }
+
+ /** Maximum number of axes as an upper bound for index values. */
+ public int getMaxNumberOfAxes()
+ {
+ return DirectInputDriver.getMaxNumberOfAxes();
+ }
+
+ /** Maximum number of available directional features. */
+ public int getMaxNumberOfDirectionals()
+ {
+ return DirectInputDriver.getMaxNumberOfDirectionals();
+ }
+
+
+ public Axis getAxis(int idx)
+ {
+ return mAxes[ idx ];
+ }
+
+ public Button getButton(int idx)
+ {
+ return mButtons[ idx ];
+ }
+
+ public Directional getDirectional(int idx)
+ {
+ return mDirectionals[ idx ];
+ }
+
+}
+
+
+
diff --git a/java/de/hardcode/jxinput/directinput/DirectInputDriver.java b/java/de/hardcode/jxinput/directinput/DirectInputDriver.java
new file mode 100644
index 0000000..558f7d8
--- /dev/null
+++ b/java/de/hardcode/jxinput/directinput/DirectInputDriver.java
@@ -0,0 +1,184 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 19. Dezember 2001, 22:44
+//**********************************************************************************************
+package de.hardcode.jxinput.directinput;
+
+import java.lang.reflect.Array;
+
+/**
+ * DirectInputDriver: the connection to the Win32 joystick.
+ * There is only one allowed, so the layout of this class is merely static.
+ *
+ * History:
+ *
+ * Changes since 0.1beta:
+ * - support of multiple devices addressed by the dev index
+ *
+ *
+ * @author Herkules
+ * @version 0.2beta
+ */
+class DirectInputDriver
+{
+ private final static String NATIVE_LIB_NAME = "jxinput";
+
+ /** Remember wether nativeinit() succeeded. */
+ static boolean sIsOperational = false;
+
+ //
+ // Static arrays to hold the values.
+ //
+ private static double [][] sAxisValues;
+ private static boolean [][] sButtonStates;
+ private static int [][] sDirectionalValues;
+
+ /**
+ * Perform the static initialization.
+ */
+ static
+ {
+ try
+ {
+ // Load the native lib.
+ System.loadLibrary( NATIVE_LIB_NAME );
+
+ init();
+ }
+ catch( SecurityException e )
+ {
+ Log.logger.warning("Native library jxinput not loaded due to a SecurityException.");
+ }
+ catch( UnsatisfiedLinkError e )
+ {
+ Log.logger.info("Native library jxinput not loaded due to an UnsatisfiedLinkError.");
+ }
+ }
+
+
+ private final static void init()
+ {
+ sIsOperational = false;
+ //
+ // Initialize it.
+ //
+ if ( nativeinit() )
+ {
+ int devs = getNumberOfDevices();
+ sAxisValues = new double [ devs ][ DirectInputDriver.getMaxNumberOfAxes() ];
+ sButtonStates = new boolean [ devs ][ DirectInputDriver.getMaxNumberOfButtons() ];
+ sDirectionalValues = new int [ devs ][ DirectInputDriver.getMaxNumberOfDirectionals() ];
+
+ // Bind the native lib to my variables.
+ bind();
+
+ // Remember I am fine.
+ sIsOperational = true;
+ }
+
+ }
+
+
+ /**
+ * Static ctor of DirectInputDriver.
+ * No object will be created due to the static layout.
+ */
+ private DirectInputDriver()
+ {
+ }
+
+ // Administration
+ private static native boolean nativeinit();
+ private static native void nativeexit();
+ private static native void bind();
+
+ static native int getNumberOfDevices();
+
+ // Configuration
+ static native String getName( int dev );
+ static native int getNumberOfAxes( int dev );
+ static native int getNumberOfButtons( int dev );
+ static native int getNumberOfDirectionals( int dev );
+ static native int getMaxNumberOfAxes();
+ static native int getMaxNumberOfButtons();
+ static native int getMaxNumberOfDirectionals();
+
+ static native boolean isAxisAvailable( int dev, int idx );
+ static native String getAxisName( int dev, int idx );
+ static native int getAxisType( int dev, int idx );
+
+ static native boolean isButtonAvailable( int dev, int idx );
+ static native String getButtonName( int dev, int idx );
+ static native int getButtonType( int dev, int idx );
+
+ static native boolean isDirectionalAvailable( int dev, int idx );
+ static native String getDirectionalName( int dev, int idx );
+
+ // Operation
+ static native void nativeupdate();
+
+
+ public static boolean isAvailable()
+ {
+ return sIsOperational;
+ }
+
+
+ /**
+ * Shutdown the device and free all Win32 resources.
+ * It is not a good idea to access any joystick features after
+ * shutdown().
+ */
+ static void shutdown()
+ {
+ nativeexit();
+ sAxisValues = null;
+ sButtonStates = null;
+ sDirectionalValues = null;
+ }
+
+
+ /**
+ * Reset the device and free all Win32 resources.
+ */
+ static void reset()
+ {
+ shutdown();
+ init();
+ }
+
+ static double getAxisValue( int dev, int idx )
+ {
+ return sAxisValues[ dev ][ idx ];
+ }
+
+ static boolean getButtonState( int dev, int idx )
+ {
+ return sButtonStates[ dev ][ idx ];
+ }
+
+ static int getDirection( int dev, int idx )
+ {
+ return sDirectionalValues[ dev ][ idx ];
+ }
+
+ /**
+ * @param args the command line arguments
+ */
+ public static void main (String args[])
+ {
+
+ if ( ! sIsOperational )
+ return;
+
+ for( int i = 0; i < 5000; ++i )
+ nativeupdate();
+
+ shutdown();
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/directinput/Log.java b/java/de/hardcode/jxinput/directinput/Log.java
new file mode 100644
index 0000000..95e586c
--- /dev/null
+++ b/java/de/hardcode/jxinput/directinput/Log.java
@@ -0,0 +1,34 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 29. Oktober 2002, 22:57
+//**********************************************************************************************
+package de.hardcode.jxinput.directinput;
+
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+/**
+ *
+ * @author Herkules
+ */
+public class Log
+{
+ public final static Logger logger = Logger.getLogger( Log.class.getPackage().getName() );
+
+// static
+// {
+// logger.setLevel( Level.ALL );
+// }
+
+ /**
+ * Creates a new instance of Log.
+ */
+ private Log()
+ {
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/event/JXInputAxisEvent.java b/java/de/hardcode/jxinput/event/JXInputAxisEvent.java
new file mode 100644
index 0000000..c353b5e
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputAxisEvent.java
@@ -0,0 +1,48 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:33
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+import de.hardcode.jxinput.JXInputDevice;
+import de.hardcode.jxinput.Axis;
+
+/**
+ * Represents an event coming from an axis.
+ * @author Joerg Plewe
+ */
+public class JXInputAxisEvent
+{
+ private final Axis mAxis;
+ double mDelta;
+
+ /**
+ * Creates a new instance of JXInputEvent.
+ */
+ JXInputAxisEvent( Axis axis )
+ {
+ mAxis = axis;
+ }
+
+ /**
+ * The feature that caused the event.
+ */
+ public final Axis getAxis()
+ {
+ return mAxis;
+ }
+
+
+ /**
+ * Return the change in value that caused the event.
+ */
+ public double getDelta()
+ {
+ return mDelta;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/event/JXInputAxisEventListener.java b/java/de/hardcode/jxinput/event/JXInputAxisEventListener.java
new file mode 100644
index 0000000..d8adf46
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputAxisEventListener.java
@@ -0,0 +1,19 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:54
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+/**
+ *
+ * @author Herkules
+ */
+public interface JXInputAxisEventListener
+{
+ void changed( JXInputAxisEvent ev );
+}
+
diff --git a/java/de/hardcode/jxinput/event/JXInputButtonEvent.java b/java/de/hardcode/jxinput/event/JXInputButtonEvent.java
new file mode 100644
index 0000000..d82d0b9
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputButtonEvent.java
@@ -0,0 +1,38 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:33
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+import de.hardcode.jxinput.JXInputDevice;
+import de.hardcode.jxinput.Button;
+
+/**
+ * Represents event coming from a button.
+ * @author Joerg Plewe
+ */
+public class JXInputButtonEvent
+{
+ final Button mButton;
+
+ /**
+ * Creates a new instance of JXInputEvent.
+ */
+ JXInputButtonEvent( Button button )
+ {
+ mButton = button;
+ }
+
+ /**
+ * The feature that caused the event.
+ */
+ public final Button getButton()
+ {
+ return mButton;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/event/JXInputButtonEventListener.java b/java/de/hardcode/jxinput/event/JXInputButtonEventListener.java
new file mode 100644
index 0000000..afdc323
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputButtonEventListener.java
@@ -0,0 +1,19 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:54
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+/**
+ *
+ * @author Herkules
+ */
+public interface JXInputButtonEventListener
+{
+ void changed( JXInputButtonEvent ev );
+}
+
diff --git a/java/de/hardcode/jxinput/event/JXInputDirectionalEvent.java b/java/de/hardcode/jxinput/event/JXInputDirectionalEvent.java
new file mode 100644
index 0000000..70e6bcd
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputDirectionalEvent.java
@@ -0,0 +1,56 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:33
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+import de.hardcode.jxinput.JXInputDevice;
+import de.hardcode.jxinput.Directional;
+
+/**
+ * Represents an event coming from an axis.
+ * @author Joerg Plewe
+ */
+public class JXInputDirectionalEvent
+{
+ private final Directional mDirectional;
+ double mValueDelta;
+ int mDirectionDelta;
+
+ /**
+ * Creates a new instance of JXInputEvent.
+ */
+ JXInputDirectionalEvent( Directional directional )
+ {
+ mDirectional = directional;
+ }
+
+ /**
+ * The feature that caused the event.
+ */
+ public final Directional getDirectional()
+ {
+ return mDirectional;
+ }
+
+ /**
+ * Return the change in value that caused the event.
+ */
+ public double getValueDelta()
+ {
+ return mValueDelta;
+ }
+
+ /**
+ * Return the change in direction that caused the event.
+ */
+ public int getDirectionDelta()
+ {
+ return mDirectionDelta;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/event/JXInputDirectionalEventListener.java b/java/de/hardcode/jxinput/event/JXInputDirectionalEventListener.java
new file mode 100644
index 0000000..65c7efa
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputDirectionalEventListener.java
@@ -0,0 +1,19 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:54
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+/**
+ *
+ * @author Herkules
+ */
+public interface JXInputDirectionalEventListener
+{
+ void changed( JXInputDirectionalEvent ev );
+}
+
diff --git a/java/de/hardcode/jxinput/event/JXInputEventManager.java b/java/de/hardcode/jxinput/event/JXInputEventManager.java
new file mode 100644
index 0000000..aa196d7
--- /dev/null
+++ b/java/de/hardcode/jxinput/event/JXInputEventManager.java
@@ -0,0 +1,284 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 31. Januar 2002, 23:42
+//**********************************************************************************************
+package de.hardcode.jxinput.event;
+
+import de.hardcode.jxinput.JXInputManager;
+import de.hardcode.jxinput.JXInputDevice;
+
+import java.util.ArrayList;
+import de.hardcode.jxinput.Axis;
+import java.util.Iterator;
+import de.hardcode.jxinput.Button;
+import de.hardcode.jxinput.Directional;
+
+/**
+ * Handles all events and listeners.
+ * JXInputEventManager is layed out a static singleton.
+ * @author Herkules
+ */
+public class JXInputEventManager
+{
+
+ private final static ArrayList mAxisEventListeners = new ArrayList();
+ private final static ArrayList mButtonEventListeners = new ArrayList();
+ private final static ArrayList mDirectionalEventListeners = new ArrayList();
+
+ private static autotrigger mAutoTrigger = null;
+
+ /**
+ * Inner class combining a listener with its scheduling parameters.
+ */
+ private static class axislistener
+ {
+ final JXInputAxisEventListener mListener;
+ final double mTreshold;
+ final JXInputAxisEvent mEvent;
+ double mLastValueFired = 0.0;
+
+ axislistener( JXInputAxisEventListener l, Axis axis, double treshold )
+ {
+ mListener = l;
+ mTreshold = treshold;
+ mEvent = new JXInputAxisEvent( axis );
+ }
+
+ final void checkTrigger()
+ {
+ double curval = mEvent.getAxis().getValue();
+ double delta = curval - mLastValueFired;
+
+ if ( Math.abs( delta ) >= mTreshold )
+ {
+ mLastValueFired = curval;
+ mEvent.mDelta = delta;
+ mListener.changed( mEvent );
+ }
+ }
+ }
+
+ /**
+ * Inner class combining a listener with its scheduling parameters.
+ */
+ private static class buttonlistener
+ {
+ final JXInputButtonEventListener mListener;
+ final JXInputButtonEvent mEvent;
+ boolean mLastValueFired = false;
+
+ buttonlistener( JXInputButtonEventListener l, Button button )
+ {
+ mListener = l;
+ mEvent = new JXInputButtonEvent( button );
+ }
+
+ final void checkTrigger()
+ {
+ boolean curstate = mEvent.getButton().getState();
+ if ( curstate != mLastValueFired )
+ {
+ mLastValueFired = curstate;
+ mListener.changed( mEvent );
+ }
+ }
+ }
+
+
+ private static class directionallistener
+ {
+ final JXInputDirectionalEventListener mListener;
+ final double mValueTreshold;
+ final JXInputDirectionalEvent mEvent;
+ double mLastValueFired = 0.0;
+ boolean mLastCenteredFired = true;
+ int mLastDirectionFired = 0;
+
+ directionallistener( JXInputDirectionalEventListener l, Directional directional, double valuetreshold )
+ {
+ mListener = l;
+ mValueTreshold = valuetreshold;
+ mEvent = new JXInputDirectionalEvent( directional );
+ }
+
+ final void checkTrigger()
+ {
+ double curval = mEvent.getDirectional().getValue();
+ int curdir = mEvent.getDirectional().getDirection();
+ boolean curctr = mEvent.getDirectional().isCentered();
+
+ double delta = curval - mLastValueFired;
+ int dirdelta = curdir - mLastDirectionFired;
+ boolean centeredchanged = mLastCenteredFired != curctr;
+
+ if ( Math.abs( delta ) >= mValueTreshold
+ || Math.abs( dirdelta ) > 0
+ || centeredchanged )
+ {
+ mLastValueFired = curval;
+ mLastDirectionFired = curdir;
+ mLastCenteredFired = curctr;
+
+ mEvent.mValueDelta = delta;
+ mEvent.mDirectionDelta = dirdelta;
+ mListener.changed( mEvent );
+ }
+ }
+ }
+
+ /**
+ * Creates a new instance of JXInputEventManager.
+ */
+ private JXInputEventManager()
+ {
+ }
+
+
+ /**
+ * Remove all listeners at once.
+ */
+ public static void reset()
+ {
+ mAxisEventListeners.clear();
+ mButtonEventListeners.clear();
+ mDirectionalEventListeners.clear();
+ }
+
+
+ /**
+ * Query devices and fire all occuring events.
+ * trigger() is thought to be called by JXInputManager#updateFeatures().
+ */
+ public static void trigger()
+ {
+ int n = mAxisEventListeners.size();
+ for ( int i = 0; i < n; i++ )
+ {
+ axislistener l = (axislistener)mAxisEventListeners.get( i );
+ l.checkTrigger();
+ }
+
+ n = mButtonEventListeners.size();
+ for ( int i = 0; i < n; i++ )
+ {
+ buttonlistener l = (buttonlistener)mButtonEventListeners.get( i );
+ l.checkTrigger();
+ }
+
+ n = mDirectionalEventListeners.size();
+ for ( int i = 0; i < n; i++ )
+ {
+ directionallistener l = (directionallistener)mDirectionalEventListeners.get( i );
+ l.checkTrigger();
+ }
+ }
+
+
+ private final static class autotrigger extends Thread
+ {
+ boolean mFinish = false;
+ final int mDelay;
+
+ autotrigger( int delay )
+ {
+ mDelay = delay;
+ }
+
+ public void run()
+ {
+ while ( ! mFinish )
+ {
+ try
+ {
+ Thread.sleep( mDelay );
+ JXInputManager.updateFeatures();
+ }
+ catch ( InterruptedException ex )
+ {
+ }
+ }
+ }
+ }
+
+
+ /**
+ * Set the intervall in ms that is used to check for new values of the features.
+ * Set it to <= 0 to prohibit automatic triggering. Events will then only be fired
+ * when somebody invokes JXInputManager#updateFeatures().
+ */
+ public static void setTriggerIntervall( int ms )
+ {
+ //
+ // Kill current thread, if any
+ //
+ if ( null != mAutoTrigger )
+ {
+ mAutoTrigger.mFinish = true;
+ try
+ {
+ mAutoTrigger.join();
+ }
+ catch ( InterruptedException ex )
+ {
+ }
+ }
+
+ mAutoTrigger = null;
+
+ if ( ms > 0 )
+ {
+ mAutoTrigger = new autotrigger( ms );
+ mAutoTrigger.start();
+ }
+
+ }
+
+
+
+
+ public static void addListener( JXInputAxisEventListener l, Axis axis, double treshold )
+ {
+ mAxisEventListeners.add( new JXInputEventManager.axislistener( l, axis, treshold ) );
+ }
+
+ public static void addListener( JXInputAxisEventListener l, Axis axis )
+ {
+ mAxisEventListeners.add( new JXInputEventManager.axislistener( l, axis, axis.getResolution() ) );
+ }
+
+ public static void removeListener( JXInputAxisEventListener l )
+ {
+ mAxisEventListeners.remove( l );
+ }
+
+
+ public static void addListener( JXInputButtonEventListener l, Button button )
+ {
+ mButtonEventListeners.add( new JXInputEventManager.buttonlistener( l, button ) );
+ }
+
+ public static void removeListener( JXInputButtonEventListener l )
+ {
+ mButtonEventListeners.remove( l );
+ }
+
+ public static void addListener( JXInputDirectionalEventListener l, Directional directional, double valuetreshold )
+ {
+ mDirectionalEventListeners.add( new JXInputEventManager.directionallistener( l, directional, valuetreshold ) );
+ }
+
+ public static void addListener( JXInputDirectionalEventListener l, Directional directional )
+ {
+ mDirectionalEventListeners.add( new JXInputEventManager.directionallistener( l, directional, directional.getResolution() ) );
+ }
+
+ public static void removeListener( JXInputDirectionalEventListener l )
+ {
+ mDirectionalEventListeners.remove( l );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/j3d/DeviceConfiguration.java b/java/de/hardcode/jxinput/j3d/DeviceConfiguration.java
new file mode 100644
index 0000000..8c1288a
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/DeviceConfiguration.java
@@ -0,0 +1,95 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 23. Februar 2002, 14:05
+//**********************************************************************************************
+package de.hardcode.jxinput.j3d;
+
+import de.hardcode.jxinput.Axis;
+
+
+/**
+ * Connects JXInput with J3DInputDevice.
+ *
+ * @author Herkules
+ */
+public class DeviceConfiguration
+{
+ public final static int AXIS_X = 0;
+ public final static int AXIS_Y = 1;
+ public final static int AXIS_Z = 2;
+
+ private final static class axisvalue
+ {
+ private final Axis mAxis;
+ private final IsActiveCondition mIsActive;
+ private final IsActiveCondition mIsIncremental;
+ private final double mScale;
+ private final double mOffset;
+ private double mValue;
+
+ axisvalue( Axis axis, IsActiveCondition active, IsActiveCondition incremental, double offset, double scale )
+ {
+ mAxis = axis;
+ mIsActive = active;
+ mIsIncremental = incremental;
+ mValue = mOffset = offset;
+ mScale = scale;
+ }
+
+ double value()
+ {
+ if ( mIsActive.isActive() )
+ {
+ double newval = mAxis.getValue() * mScale;
+
+ if ( mIsIncremental.isActive() )
+ mValue += newval;
+ else
+ mValue = newval + mOffset;
+ }
+ return mValue;
+ }
+ }
+
+ DeviceConfiguration.axisvalue [] mAxisTrans = new DeviceConfiguration.axisvalue[ 3 ];
+ DeviceConfiguration.axisvalue [] mAxisRot = new DeviceConfiguration.axisvalue[ 3 ];
+
+ /**
+ * Creates a new instance of DeviceConfiguration.
+ */
+ public DeviceConfiguration()
+ {
+ }
+
+
+ double getTranslational( int axisid )
+ {
+ DeviceConfiguration.axisvalue val = mAxisTrans[ axisid ];
+ return null == val ? 0.0 : val.value();
+ }
+
+ double getRotational( int axisid )
+ {
+ DeviceConfiguration.axisvalue val = mAxisRot[ axisid ];
+ return null == val ? 0.0 : val.value();
+ }
+
+ public void setTranslational( int axisid, Axis axis, IsActiveCondition active, IsActiveCondition incremental, double offset, double scale )
+ {
+ if ( axisid < 0 || axisid > AXIS_Z )
+ throw new IllegalArgumentException();
+ mAxisTrans[ axisid ] = new DeviceConfiguration.axisvalue( axis, active, incremental, offset, scale );
+ }
+
+ public void setRotational( int axisid, Axis axis, IsActiveCondition active, IsActiveCondition incremental, double offset, double scale )
+ {
+ if ( axisid < 0 || axisid > AXIS_Z )
+ throw new IllegalArgumentException();
+ mAxisRot[ axisid ] = new DeviceConfiguration.axisvalue( axis, active, incremental, offset, scale );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/j3d/IsActiveCondition.java b/java/de/hardcode/jxinput/j3d/IsActiveCondition.java
new file mode 100644
index 0000000..af6ca08
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/IsActiveCondition.java
@@ -0,0 +1,25 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 25. Februar 2002, 22:41
+//**********************************************************************************************
+package de.hardcode.jxinput.j3d;
+
+/**
+ *
+ * @author Herkules
+ */
+public interface IsActiveCondition
+{
+ public final static IsActiveCondition ALWAYS = IsAlwaysActiveCondition.ALWAYS;
+ public final static IsActiveCondition NEVER = IsAlwaysActiveCondition.NEVER;
+
+ /**
+ * Tell wether a certain thing is active.
+ */
+ boolean isActive();
+}
+
diff --git a/java/de/hardcode/jxinput/j3d/IsActiveOnButtonCondition.java b/java/de/hardcode/jxinput/j3d/IsActiveOnButtonCondition.java
new file mode 100644
index 0000000..98da7bb
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/IsActiveOnButtonCondition.java
@@ -0,0 +1,39 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 25. Februar 2002, 22:43
+//**********************************************************************************************
+package de.hardcode.jxinput.j3d;
+
+import de.hardcode.jxinput.Button;
+
+/**
+ *
+ * @author Herkules
+ */
+public class IsActiveOnButtonCondition implements IsActiveCondition
+{
+ private final boolean mActiveState;
+ private final Button mButton;
+
+ /**
+ * Creates a new instance of IsAlwayActiveCondition.
+ */
+ public IsActiveOnButtonCondition( Button button, boolean activestate )
+ {
+ mActiveState = activestate;
+ mButton = button;
+ }
+
+ /**
+ * Tell wether a certain thing is active.
+ */
+ public boolean isActive()
+ {
+ return mButton.getState() == mActiveState;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/j3d/IsAlwaysActiveCondition.java b/java/de/hardcode/jxinput/j3d/IsAlwaysActiveCondition.java
new file mode 100644
index 0000000..cd8b1fe
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/IsAlwaysActiveCondition.java
@@ -0,0 +1,38 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 25. Februar 2002, 22:43
+//**********************************************************************************************
+package de.hardcode.jxinput.j3d;
+
+/**
+ *
+ * @author Herkules
+ */
+final class IsAlwaysActiveCondition implements IsActiveCondition
+{
+ private final boolean mIsActive;
+
+ public final static IsActiveCondition ALWAYS = new IsAlwaysActiveCondition( true );
+ public final static IsActiveCondition NEVER = new IsAlwaysActiveCondition( false );
+
+ /**
+ * Creates a new instance of IsAlwayActiveCondition.
+ */
+ private IsAlwaysActiveCondition(boolean isactive)
+ {
+ mIsActive = isactive;
+ }
+
+ /**
+ * Tell wether a certain thing is active.
+ */
+ public boolean isActive()
+ {
+ return mIsActive;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/j3d/J3DInputDevice.java b/java/de/hardcode/jxinput/j3d/J3DInputDevice.java
new file mode 100644
index 0000000..f5b08f2
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/J3DInputDevice.java
@@ -0,0 +1,171 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 22. Februar 2002, 13:21
+//**********************************************************************************************
+package de.hardcode.jxinput.j3d;
+
+import javax.media.j3d.InputDevice;
+import javax.media.j3d.Sensor;
+import javax.media.j3d.SensorRead;
+import javax.vecmath.Vector3d;
+import javax.media.j3d.Transform3D;
+import de.hardcode.jxinput.JXInputManager;
+
+
+/**
+ * Implementation of Java3D's InputDevice
+ *
+ * @author Herkules
+ */
+public class J3DInputDevice
+ implements InputDevice
+{
+ private Vector3d mPosition = new Vector3d();
+ private Transform3D mNewTransform = new Transform3D();
+
+ private Transform3D mRotTransX = new Transform3D();
+ private Transform3D mRotTransY = new Transform3D();
+ private Transform3D mRotTransZ = new Transform3D();
+
+ private Vector3d mInitPos = new Vector3d( 0.0, 0.0, 0.0 );
+
+ private Sensor mSensor = new Sensor( this );
+ private SensorRead mSensorRead = new SensorRead();
+
+ private DeviceConfiguration mConfig;
+
+ /**
+ * Creates a new instance of J3DInputDevice.
+ */
+ public J3DInputDevice( DeviceConfiguration config )
+ {
+ mConfig = config;
+ setNominalPositionAndOrientation();
+ }
+
+
+ public void close()
+ {
+ // Intentionally empty
+ }
+
+
+ /**
+ * Retrieve processing mode.
+ * For this device, it always is NON_BLOCKING.
+ */
+ public int getProcessingMode()
+ {
+ return InputDevice.NON_BLOCKING;
+ }
+
+
+ /**
+ * Don't care for the index, I only support one sensor.
+ * And I deliver that.
+ */
+ public Sensor getSensor( int param )
+ {
+ return mSensor;
+ }
+
+
+ /**
+ * Tell the world about the only one sensor I support.
+ */
+ public int getSensorCount()
+ {
+ return 1;
+ }
+
+
+ /**
+ * Well - initialize!
+ * Nothing to do here.
+ */
+ public boolean initialize()
+ {
+ return true;
+ }
+
+
+ /**
+ * The main update method.
+ */
+ public void pollAndProcessInput()
+ {
+ JXInputManager.updateFeatures();
+
+ mSensorRead.setTime( JXInputManager.getLastUpdateTime() );
+
+ mRotTransX.rotX( mConfig.getRotational( DeviceConfiguration.AXIS_X ) );
+ mRotTransY.rotY( mConfig.getRotational( DeviceConfiguration.AXIS_Y ) );
+ mRotTransZ.rotZ( mConfig.getRotational( DeviceConfiguration.AXIS_Z ) );
+
+ mPosition.set(
+ mConfig.getTranslational( DeviceConfiguration.AXIS_X ),
+ mConfig.getTranslational( DeviceConfiguration.AXIS_Y ),
+ mConfig.getTranslational( DeviceConfiguration.AXIS_Z )
+ );
+
+ mNewTransform.set( mPosition );
+
+ mNewTransform.mul( mRotTransX );
+ mNewTransform.mul( mRotTransY );
+ mNewTransform.mul( mRotTransZ );
+
+ mSensorRead.set( mNewTransform );
+ mSensor.setNextSensorRead( mSensorRead );
+ }
+
+
+ /**
+ * Not called by current j3d implementation.
+ */
+ public void processStreamInput()
+ {
+ // Intentionally empty
+ }
+
+
+ /**
+ * Reset state.
+ */
+ public void setNominalPositionAndOrientation()
+ {
+ mSensorRead.setTime( JXInputManager.getLastUpdateTime() );
+
+ mRotTransX.rotX( 0.0 );
+ mRotTransY.rotY( 0.0 );
+ mRotTransZ.rotZ( 0.0 );
+
+ mPosition.set( mInitPos );
+
+ mNewTransform.set( mPosition );
+
+ mNewTransform.mul( mRotTransX );
+ mNewTransform.mul( mRotTransY );
+ mNewTransform.mul( mRotTransZ );
+
+ mSensorRead.set( mNewTransform );
+ mSensor.setNextSensorRead( mSensorRead );
+
+ }
+
+
+ /**
+ * Set the processing mode.
+ * Only NON_BLOCKING is allowed!
+ */
+ public void setProcessingMode(int param)
+ {
+ if ( param != InputDevice.NON_BLOCKING )
+ throw new IllegalArgumentException("Processing mode must be NON_BLOCKING");
+
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/j3d/package.html b/java/de/hardcode/jxinput/j3d/package.html
new file mode 100644
index 0000000..9b92964
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/package.html
@@ -0,0 +1,11 @@
+
+
+
+
+
+
+
+Connecting JXInput to Java3D by implementing the interface
+javax.media.j3d.InputDevice.
+
+
diff --git a/java/de/hardcode/jxinput/j3d/test/HelloUniverse.java b/java/de/hardcode/jxinput/j3d/test/HelloUniverse.java
new file mode 100644
index 0000000..fde34bc
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/test/HelloUniverse.java
@@ -0,0 +1,205 @@
+
+/*
+ * @(#)HelloUniverse.java 1.15 02/02/07 14:48:36
+ *
+ * Copyright (c) 1996-2002 Sun Microsystems, Inc. All Rights Reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistribution in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ *
+ * Neither the name of Sun Microsystems, Inc. or the names of
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * This software is provided "AS IS," without a warranty of any
+ * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND
+ * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY
+ * EXCLUDED. SUN AND ITS LICENSORS SHALL NOT BE LIABLE FOR ANY DAMAGES
+ * SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
+ * DISTRIBUTING THE SOFTWARE OR ITS DERIVATIVES. IN NO EVENT WILL SUN
+ * OR ITS LICENSORS BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR
+ * FOR DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR
+ * PUNITIVE DAMAGES, HOWEVER CAUSED AND REGARDLESS OF THE THEORY OF
+ * LIABILITY, ARISING OUT OF THE USE OF OR INABILITY TO USE SOFTWARE,
+ * EVEN IF SUN HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
+ *
+ * You acknowledge that Software is not designed,licensed or intended
+ * for use in the design, construction, operation or maintenance of
+ * any nuclear facility.
+ */
+
+package de.hardcode.jxinput.j3d.test;
+
+
+import java.applet.Applet;
+import java.awt.*;
+import java.awt.event.*;
+import com.sun.j3d.utils.applet.MainFrame;
+import com.sun.j3d.utils.geometry.ColorCube;
+import com.sun.j3d.utils.universe.*;
+import javax.media.j3d.*;
+import javax.vecmath.*;
+import de.hardcode.jxinput.j3d.DeviceConfiguration;
+import de.hardcode.jxinput.Axis;
+import de.hardcode.jxinput.JXInputManager;
+import de.hardcode.jxinput.j3d.IsActiveCondition;
+import de.hardcode.jxinput.j3d.J3DInputDevice;
+import de.hardcode.jxinput.j3d.IsActiveOnButtonCondition;
+
+
+public class HelloUniverse extends Applet
+{
+
+ private SimpleUniverse u = null;
+ TransformGroup objTrans;
+
+ public BranchGroup createSceneGraph()
+ {
+ BranchGroup objRoot = new BranchGroup();
+ objTrans = new TransformGroup();
+ objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
+ objRoot.addChild(objTrans);
+ objTrans.addChild(new ColorCube(0.4));
+
+// Transform3D yAxis = new Transform3D();
+// Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE,
+// 0, 0,
+// 4000, 0, 0,
+// 0, 0, 0);
+// RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis,
+// 0.0f, (float) Math.PI*2.0f);
+// BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0);
+// rotator.setSchedulingBounds(bounds);
+// objTrans.addChild(rotator);
+ return objRoot;
+ }
+
+
+ public HelloUniverse()
+ {
+
+ }
+
+ public void init()
+ {
+ // These are the string arguments given to the VirtualInputDevice
+ // constructor. These are settable parameters. Look in the
+ // VirtualInputDevice constructor for a complete list.
+ String[] args = new String[10];
+ args[0] = "printvalues";
+ args[1] = "true";
+ args[2] = "yscreeninitloc";
+ args[3] = "50";
+ args[4] = null;
+
+
+ // now create the HelloUniverse Canvas
+ setLayout(new BorderLayout());
+ GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration();
+
+ Canvas3D c = new Canvas3D(config);
+ add("Center", c);
+
+ // Create a simple scene and attach it to the virtual universe
+ BranchGroup scene = createSceneGraph();
+ u = new SimpleUniverse(c);
+
+ //
+ // Use the inputdevice
+ //
+ InputDevice device = createInputDevice();
+
+ // Register the VirtualInputDevice with Java 3D
+ u.getViewer().getPhysicalEnvironment().addInputDevice( device );
+
+// TransformGroup viewTrans = u.getViewingPlatform().getViewPlatformTransform();
+
+ // Put the behavoir to teh object
+ SensorBehavior s = new SensorBehavior( objTrans, device.getSensor(0) );
+ s.setSchedulingBounds( new BoundingSphere( new Point3d(0.0,0.0,0.0), Float.MAX_VALUE ) );
+ objTrans.addChild( s );
+
+ u.getViewingPlatform().setNominalViewingTransform();
+ u.addBranchGraph(scene);
+ }
+
+ public void destroy()
+ {
+ u.removeAllLocales();
+ }
+
+
+ /**
+ * Setup an input device.
+ */
+ private InputDevice createInputDevice()
+ {
+ IsActiveCondition button1down = new IsActiveOnButtonCondition(JXInputManager.getJXInputDevice( 0 ).getButton( 0 ), true );
+ IsActiveCondition button1up = new IsActiveOnButtonCondition(JXInputManager.getJXInputDevice( 0 ).getButton( 0 ), false );
+
+ Axis xaxis = JXInputManager.getJXInputDevice( 0 ).getAxis( Axis.ID_X );
+ Axis yaxis = JXInputManager.getJXInputDevice( 0 ).getAxis( Axis.ID_Y );
+
+ DeviceConfiguration cnf = new DeviceConfiguration();
+
+ //
+ // Setup the configuration to use joysticks x/y for rotation is not button is pressed
+ // and for translation if button1 is pressed.
+ //
+ cnf.setRotational(
+ DeviceConfiguration.AXIS_Y,
+ xaxis,
+ button1up,
+ IsActiveCondition.NEVER,
+ 0.0, Math.PI
+ );
+
+ cnf.setRotational(
+ DeviceConfiguration.AXIS_X,
+ yaxis,
+ button1up,
+ IsActiveCondition.NEVER,
+ 0.0, Math.PI
+ );
+
+ cnf.setTranslational(
+ DeviceConfiguration.AXIS_Z,
+ yaxis,
+ button1down,
+ IsActiveCondition.NEVER,
+ -5.0, 4.0
+ );
+ cnf.setTranslational(
+ DeviceConfiguration.AXIS_X,
+ xaxis,
+ button1down,
+ IsActiveCondition.NEVER,
+ 0.0, 4.0
+ );
+
+ // We have the config, create the device...
+ J3DInputDevice d = new J3DInputDevice( cnf );
+
+ // The InputDevice must be initialized before registering it
+ // with the PhysicalEnvironment object.
+ d.initialize();
+
+ return d;
+ }
+
+
+ public static void main(String[] args)
+ {
+ new MainFrame(new HelloUniverse(), 350, 350);
+ }
+}
diff --git a/java/de/hardcode/jxinput/j3d/test/SensorBehavior.java b/java/de/hardcode/jxinput/j3d/test/SensorBehavior.java
new file mode 100644
index 0000000..6836ebb
--- /dev/null
+++ b/java/de/hardcode/jxinput/j3d/test/SensorBehavior.java
@@ -0,0 +1,70 @@
+package de.hardcode.jxinput.j3d.test;
+
+/*
+ * @(#)SensorBehavior.java 1.8 02/02/07 14:48:34
+ *
+ * Copyright (c) 1996-2002 Sun Microsystems, Inc. All Rights Reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * - Redistribution in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ *
+ * Neither the name of Sun Microsystems, Inc. or the names of
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * This software is provided "AS IS," without a warranty of any
+ * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND
+ * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY
+ * EXCLUDED. SUN AND ITS LICENSORS SHALL NOT BE LIABLE FOR ANY DAMAGES
+ * SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
+ * DISTRIBUTING THE SOFTWARE OR ITS DERIVATIVES. IN NO EVENT WILL SUN
+ * OR ITS LICENSORS BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR
+ * FOR DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR
+ * PUNITIVE DAMAGES, HOWEVER CAUSED AND REGARDLESS OF THE THEORY OF
+ * LIABILITY, ARISING OUT OF THE USE OF OR INABILITY TO USE SOFTWARE,
+ * EVEN IF SUN HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
+ *
+ * You acknowledge that Software is not designed,licensed or intended
+ * for use in the design, construction, operation or maintenance of
+ * any nuclear facility.
+ */
+
+import javax.media.j3d.*;
+import java.util.*;
+
+public class SensorBehavior extends Behavior
+{
+ private WakeupOnElapsedFrames conditions = new WakeupOnElapsedFrames(0);
+ private TransformGroup transformGroup;
+ private Sensor sensor;
+ private Transform3D transform = new Transform3D();
+
+ public SensorBehavior( TransformGroup tg, Sensor sensor )
+ {
+ transformGroup = tg;
+ this.sensor = sensor;
+ }
+
+ public void initialize()
+ {
+ wakeupOn( conditions );
+ }
+
+ public void processStimulus( Enumeration criteria )
+ {
+ sensor.getRead( transform );
+ transformGroup.setTransform( transform );
+ wakeupOn( conditions );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/keyboard/InvalidKeyCodeException.java b/java/de/hardcode/jxinput/keyboard/InvalidKeyCodeException.java
new file mode 100644
index 0000000..f44ee6b
--- /dev/null
+++ b/java/de/hardcode/jxinput/keyboard/InvalidKeyCodeException.java
@@ -0,0 +1,35 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 16. April 2002, 23:31
+//**********************************************************************************************
+package de.hardcode.jxinput.keyboard;
+
+/**
+ * Exeception to be thrown if keycode is not in then range [0,255].
+ *
+ * @author Herkules
+ */
+public class InvalidKeyCodeException
+ extends IllegalArgumentException
+{
+
+ /**
+ * Creates a new instance of InvalidKeyCodeException.
+ */
+ public InvalidKeyCodeException()
+ {
+ }
+
+
+ /**
+ * Creates a new instance of InvalidKeyCodeException.
+ */
+ public InvalidKeyCodeException( String s )
+ {
+ super( s );
+ }
+}
diff --git a/java/de/hardcode/jxinput/keyboard/JXKeyboardInputDevice.java b/java/de/hardcode/jxinput/keyboard/JXKeyboardInputDevice.java
new file mode 100644
index 0000000..858bdb7
--- /dev/null
+++ b/java/de/hardcode/jxinput/keyboard/JXKeyboardInputDevice.java
@@ -0,0 +1,175 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 9. April 2002, 22:40
+//**********************************************************************************************
+package de.hardcode.jxinput.keyboard;
+
+
+import de.hardcode.jxinput.*;
+import java.awt.Component;
+
+
+/**
+ * Virtual input device treating a AWT keyboard as a source for Buttons.
+ *
+ * @author Herkules
+ */
+public class JXKeyboardInputDevice
+ implements JXInputDevice
+{
+ private static final String DEVICENAME = "Swing Keyboard";
+
+ /** The driver doing all the real work. */
+ private final KeyboardDriver mDriver = new KeyboardDriver();
+
+ /** The Component I am listening to. */
+ private Component mComponent = null;
+
+ /** Hold the biggest keycode for which a button has been created. */
+ private int mMaxIdxCreated = 0;
+
+
+ /**
+ * Creates a new instance of JXKeyboardInputDevice.
+ */
+ public JXKeyboardInputDevice()
+ {
+ }
+
+
+ /**
+ * Creates a new instance of JXKeyboardInputDevice
+ * immediately listening to a JComponent.
+ */
+ public JXKeyboardInputDevice( Component comp )
+ {
+ listenTo( comp );
+ }
+
+ /**
+ * Makes this device listen to a certain JComponent.
+ */
+ public final void listenTo( Component comp )
+ {
+ shutdown();
+ mComponent = comp;
+ mComponent.addKeyListener( mDriver );
+ }
+
+ /**
+ * Shut down. No longer listen to my JComponent.
+ */
+ public final void shutdown()
+ {
+ if ( null != mComponent )
+ mComponent.removeKeyListener( mDriver );
+ }
+
+
+ /**
+ * Create a button object for a certain keycode.
+ */
+ public Button createButton( int keycode )
+ {
+ if ( 0 > keycode || 0x100 < keycode )
+ throw new InvalidKeyCodeException();
+
+ KeyButton b;
+ if ( null == (b = mDriver.getButton( keycode ) ) )
+ {
+ b = new KeyButton( keycode );
+ mDriver.registerKeyButton( b );
+ if ( keycode > mMaxIdxCreated )
+ mMaxIdxCreated = keycode;
+ }
+ return b;
+ }
+
+
+ public void removeButton( Button b )
+ {
+ mDriver.unregisterKeyButton( (KeyButton) b );
+ }
+
+
+
+ //*********************************************************************************************
+ //
+ // Implement JXInputDevice
+ //
+ //*********************************************************************************************
+
+ public Axis getAxis(int idx)
+ {
+ // No axes on keyboard.
+ return null;
+ }
+
+
+ public Button getButton(int idx)
+ {
+ // idx is interpreted as the keycode
+ return mDriver.getButton( idx );
+ }
+
+ public Directional getDirectional(int idx)
+ {
+ // No directionals on keyboard.
+ return null;
+ }
+
+ /** Maximum number of axes as an upper bound for index values. */
+ public int getMaxNumberOfAxes()
+ {
+ // No axes on keyboard.
+ return 0;
+ }
+
+ /** Maximum number of buttons as an upper bound for index values. */
+ public int getMaxNumberOfButtons()
+ {
+ // Return biggest keycode (inclusive).
+ return mMaxIdxCreated + 1;
+ }
+
+ /** Maximum number of directional features as an upper bound for index values. */
+ public int getMaxNumberOfDirectionals()
+ {
+ // No directionals on keyboard.
+ return 0;
+ }
+
+ /**
+ * Devices may have a name.
+ * This name might be provided by a system dependant driver.
+ */
+ public String getName()
+ {
+ return DEVICENAME;
+ }
+
+ /** Actual number of available axes. */
+ public int getNumberOfAxes()
+ {
+ // No axes on keyboard.
+ return 0;
+ }
+
+ /** Actual number of available buttons. */
+ public int getNumberOfButtons()
+ {
+ return mDriver.getNumberOfButtons();
+ }
+
+ /** Actual number of available directional features. */
+ public int getNumberOfDirectionals()
+ {
+ // No directionals on keyboard.
+ return 0;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/keyboard/KeyButton.java b/java/de/hardcode/jxinput/keyboard/KeyButton.java
new file mode 100644
index 0000000..3fd7130
--- /dev/null
+++ b/java/de/hardcode/jxinput/keyboard/KeyButton.java
@@ -0,0 +1,94 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 9. April 2002, 22:51
+//**********************************************************************************************
+package de.hardcode.jxinput.keyboard;
+
+import de.hardcode.jxinput.Button;
+import java.awt.event.KeyEvent;
+
+
+/**
+ * Associates a keycode with a Button and handles the current state of that button.
+ *
+ * @author Herkules
+ */
+class KeyButton
+ implements Button
+{
+ private final int mKeyCode;
+ private boolean mIsPressed;
+ private boolean mHasChanged;
+
+ /**
+ * Creates a new instance of KeyButton.
+ */
+ public KeyButton( int keycode )
+ {
+ mKeyCode = keycode;
+ }
+
+
+ /**
+ * Return the keycode assigned with this button.
+ */
+ public final int getKeyCode()
+ {
+ return mKeyCode;
+ }
+
+ final void setIsPressed( boolean flag )
+ {
+ mIsPressed = flag;
+ }
+
+ //*********************************************************************************************
+ //
+ // Implement Button
+ //
+ //*********************************************************************************************
+
+
+ /**
+ * Features may have a name provided e.g. by the driver.
+ */
+ public String getName()
+ {
+ return KeyEvent.getKeyText( mKeyCode );
+ }
+
+ /**
+ * Tells the state of the button at last update.
+ */
+ public boolean getState()
+ {
+ return mIsPressed;
+ }
+
+ /**
+ * Retrieve the type of the button.
+ * Pushbutton will deliver true==getState() as long as they are pressed down.
+ * Togglebuttons will change their state once they are pressed and keep that state
+ * until they are pressed again.
+ * @return [ PUSHBUTTON | TOGGLEBUTTON ]
+ */
+ public int getType()
+ {
+ return Button.PUSHBUTTON;
+ }
+
+
+ /**
+ * Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ public boolean hasChanged()
+ {
+ return true;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/keyboard/KeyboardDriver.java b/java/de/hardcode/jxinput/keyboard/KeyboardDriver.java
new file mode 100644
index 0000000..7eb6232
--- /dev/null
+++ b/java/de/hardcode/jxinput/keyboard/KeyboardDriver.java
@@ -0,0 +1,141 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 9. April 2002, 22:43
+//**********************************************************************************************
+package de.hardcode.jxinput.keyboard;
+
+import java.awt.event.KeyListener;
+import java.awt.event.KeyEvent;
+import java.util.HashMap;
+import java.security.InvalidParameterException;
+
+
+
+/**
+ * Listen to a JComponent handle handle all associated button objects.
+ * This is the main worker class for JXKeyboardInputDevice.
+ *
+ * @author Herkules
+ */
+class KeyboardDriver implements KeyListener
+{
+// HashMap mKeysToObserveMap = new HashMap();
+
+ int mNumberOfKeysObserved = 0;
+ KeyButton [] mKeysObserved = new KeyButton [ 0x100 ];
+
+
+ /**
+ * Creates a new instance of KeyboardDriver.
+ */
+ public KeyboardDriver()
+ {
+ }
+
+
+ /**
+ * How many buttons are registered?
+ */
+ final int getNumberOfButtons()
+ {
+ return mNumberOfKeysObserved;
+// return mKeysToObserveMap.size();
+ }
+
+
+ /**
+ * Place a new button under my observation.
+ */
+ final boolean registerKeyButton( KeyButton b )
+ {
+ final int keycode = b.getKeyCode();
+
+ if ( 0 > keycode || 0x100 < keycode )
+ throw new InvalidKeyCodeException();
+
+ if ( null == mKeysObserved[ keycode ] )
+ {
+ mKeysObserved[ keycode ] = b;
+ mNumberOfKeysObserved++;
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+
+// Integer code = new Integer( b.getKeyCode() );
+// if ( ! mKeysToObserveMap.containsKey( code ) )
+// {
+// mKeysToObserveMap.put( code, b );
+// return true;
+// }
+// else
+// {
+// return false;
+// }
+ }
+
+ final void unregisterKeyButton( KeyButton b )
+ {
+ final int keycode = b.getKeyCode();
+
+ if ( 0 > keycode || 0x100 < keycode )
+ throw new InvalidKeyCodeException();
+
+ if ( null != mKeysObserved[ b.getKeyCode() ] )
+ {
+ mKeysObserved[ keycode ] = null;
+ mNumberOfKeysObserved--;
+ }
+
+// Integer code = new Integer( b.getKeyCode() );
+// mKeysToObserveMap.remove( code );
+ }
+
+
+ /**
+ * Retrieve the button from its keycode.
+ */
+ final KeyButton getButton( int keycode )
+ {
+ if ( 0 > keycode || 0x100 < keycode )
+ throw new InvalidKeyCodeException();
+
+ return mKeysObserved[ keycode ];
+
+// Integer code = new Integer( keycode );
+// return (KeyButton)mKeysToObserveMap.get( code );
+ }
+
+
+ //*********************************************************************************************
+ //
+ // Implement KeyListener
+ //
+ //*********************************************************************************************
+
+ public void keyPressed( KeyEvent keyEvent )
+ {
+ KeyButton b = getButton( keyEvent.getKeyCode() );
+ if ( null != b )
+ b.setIsPressed( true );
+ }
+
+ public void keyReleased( KeyEvent keyEvent )
+ {
+ KeyButton b = getButton( keyEvent.getKeyCode() );
+ if ( null != b )
+ b.setIsPressed( false );
+ }
+
+ public void keyTyped( KeyEvent keyEvent )
+ {
+ // Intentionally empty.
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/keyboard/package.html b/java/de/hardcode/jxinput/keyboard/package.html
new file mode 100644
index 0000000..e1021d1
--- /dev/null
+++ b/java/de/hardcode/jxinput/keyboard/package.html
@@ -0,0 +1,10 @@
+
+
+
+
+ de.hardcode.jxinput.keyboard
+
+
+Connects Swing keyboard handling to the JXInput infrastructure.
+
+
diff --git a/java/de/hardcode/jxinput/package.html b/java/de/hardcode/jxinput/package.html
new file mode 100644
index 0000000..c449914
--- /dev/null
+++ b/java/de/hardcode/jxinput/package.html
@@ -0,0 +1,15 @@
+
+
+
+
+
+
+
+JXInput by HARDCODE Dev., Dipl. Phys. Joerg Plewe.
+
+JXInput connects gaming input devices like joysticks or gamepads to the Java
+environment.
+
+Comments send to jxinput@hardcode.de.
+
+
diff --git a/java/de/hardcode/jxinput/test/AxisListener.java b/java/de/hardcode/jxinput/test/AxisListener.java
new file mode 100644
index 0000000..7d2b138
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/AxisListener.java
@@ -0,0 +1,39 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 20. Februar 2002, 22:19
+//**********************************************************************************************
+package de.hardcode.jxinput.test;
+
+import de.hardcode.jxinput.event.JXInputEventManager;
+import de.hardcode.jxinput.event.JXInputAxisEventListener;
+import de.hardcode.jxinput.event.JXInputAxisEvent;
+import de.hardcode.jxinput.Axis;
+
+/**
+ * Example listener to an axis.
+ *
+ * @author Herkules
+ */
+public class AxisListener
+ implements JXInputAxisEventListener
+{
+
+ /**
+ * Creates a new instance of AxisListener.
+ */
+ public AxisListener( Axis axis )
+ {
+ JXInputEventManager.addListener( this, axis, 0.1 );
+ }
+
+
+ public void changed( JXInputAxisEvent ev )
+ {
+ System.out.println( "Axis " + ev.getAxis().getName() + " changed : value=" + ev.getAxis().getValue() + ", event causing delta=" + ev.getDelta() );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/test/ButtonListener.java b/java/de/hardcode/jxinput/test/ButtonListener.java
new file mode 100644
index 0000000..604002d
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/ButtonListener.java
@@ -0,0 +1,38 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 20. Februar 2002, 22:19
+//**********************************************************************************************
+package de.hardcode.jxinput.test;
+
+import de.hardcode.jxinput.event.JXInputEventManager;
+import de.hardcode.jxinput.event.JXInputButtonEventListener;
+import de.hardcode.jxinput.event.JXInputButtonEvent;
+import de.hardcode.jxinput.Button;
+
+/**
+ * Sample button listener.
+ *
+ * @author Herkules
+ */
+public class ButtonListener implements JXInputButtonEventListener
+{
+
+ /**
+ * Creates a new instance of AxisListener.
+ */
+ public ButtonListener( Button button )
+ {
+ JXInputEventManager.addListener( this, button );
+ }
+
+
+ public void changed( JXInputButtonEvent ev )
+ {
+ System.out.println( "Button " + ev.getButton().getName() + " changed : state=" + ev.getButton().getState() );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/test/DirectionalListener.java b/java/de/hardcode/jxinput/test/DirectionalListener.java
new file mode 100644
index 0000000..9f79796
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/DirectionalListener.java
@@ -0,0 +1,37 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 20. Februar 2002, 22:19
+//**********************************************************************************************
+package de.hardcode.jxinput.test;
+
+import de.hardcode.jxinput.event.JXInputEventManager;
+import de.hardcode.jxinput.event.JXInputDirectionalEventListener;
+import de.hardcode.jxinput.event.JXInputDirectionalEvent;
+import de.hardcode.jxinput.Directional;
+
+/**
+ * Sample directional listener.
+ *
+ * @author Herkules
+ */
+public class DirectionalListener implements JXInputDirectionalEventListener
+{
+ /**
+ * Creates a new instance of AxisListener.
+ */
+ public DirectionalListener( Directional directional )
+ {
+ JXInputEventManager.addListener( this, directional, 1.0 );
+ }
+
+
+ public void changed( JXInputDirectionalEvent ev )
+ {
+ System.out.println( "Directional " + ev.getDirectional().getName() + " changed : direction=" + ev.getDirectional().getDirection() + ", value=" + ev.getDirectional().getValue() + ", event causing delta=" + ev.getDirectionDelta() );
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/test/JXInputDevicePanel.form b/java/de/hardcode/jxinput/test/JXInputDevicePanel.form
new file mode 100644
index 0000000..fe9f69e
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/JXInputDevicePanel.form
@@ -0,0 +1,97 @@
+
+
+
diff --git a/java/de/hardcode/jxinput/test/JXInputDevicePanel.java b/java/de/hardcode/jxinput/test/JXInputDevicePanel.java
new file mode 100644
index 0000000..81fbef3
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/JXInputDevicePanel.java
@@ -0,0 +1,296 @@
+/*
+ * JXInputDevicePanel.java
+ *
+ * Created on 23. Januar 2002, 22:19
+ */
+package de.hardcode.jxinput.test;
+
+import de.hardcode.jxinput.JXInputManager;
+import de.hardcode.jxinput.JXInputDevice;
+import de.hardcode.jxinput.Axis;
+import de.hardcode.jxinput.Directional;
+import de.hardcode.jxinput.Button;
+
+import javax.swing.*;
+import java.awt.GridLayout;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.awt.BorderLayout;
+import java.awt.Font;
+import java.util.Dictionary;
+import java.util.Enumeration;
+
+/**
+ *
+ * @author Herkules
+ */
+public class JXInputDevicePanel extends javax.swing.JPanel
+{
+ private static final Font AXIS_SLIDER_FONT = new Font( "Verdana", Font.PLAIN, 9 );
+
+ private final JXInputDevice mDev;
+ private final ArrayList mAxisSliders = new ArrayList();
+ private final ArrayList mButtonCheckboxes = new ArrayList();
+ private final ArrayList mDirectionalLabels = new ArrayList();
+
+
+ /** Creates new form JXInputDevicePanel */
+ public JXInputDevicePanel( JXInputDevice dev )
+ {
+ mDev = dev;
+ initComponents();
+ initFromDevice();
+ }
+
+ /**
+ * Helper class connecting a JSlider with an Axis.
+ */
+ private class AxisSlider extends JSlider
+ {
+ Axis mAxis;
+ AxisSlider( Axis axis )
+ {
+ super( ( Axis.SLIDER == axis.getType() ? 0 : -100 ), 100 );
+ this.setMajorTickSpacing( Axis.SLIDER == axis.getType() ? 25 : 50 );
+ this.setMinorTickSpacing( 5 );
+ this.setPaintTicks( true );
+ this.setPaintLabels( true );
+ this.setEnabled( false );
+
+ Dictionary labeldict = this.getLabelTable();
+ Enumeration labels = labeldict.elements();
+ while ( labels.hasMoreElements() )
+ {
+ JLabel label = (JLabel)labels.nextElement();
+ label.setFont( AXIS_SLIDER_FONT );
+ label.setSize( 32, 12 );
+ label.setHorizontalAlignment( SwingConstants.LEFT );
+ }
+
+ mAxis = axis;
+ }
+
+ void update()
+ {
+ int ax = (int)(mAxis.getValue() * 100.0);
+
+ //
+ // Only if value really changes
+ //
+ if ( ax != this.getValue() )
+ {
+ this.setValue( ax );
+ this.setToolTipText( mAxis.getName() + ": " + Double.toString( mAxis.getValue() ) );
+ }
+ }
+
+ }
+
+
+ private class ButtonCheckbox extends JCheckBox
+ {
+ Button mButton;
+ ButtonCheckbox( Button button )
+ {
+ super( button.getName() );
+ this.setEnabled( false );
+ mButton = button;
+ }
+
+ void update()
+ {
+ boolean state = mButton.getState();
+
+ //
+ // Only if value really changes
+ //
+ if ( state != this.isSelected() )
+ {
+ this.setSelected( state );
+ }
+ }
+ }
+
+
+ private class DirectionalLabel extends JLabel
+ {
+ Directional mDirectional;
+ int mCurrent = 0;
+
+ DirectionalLabel( Directional directional )
+ {
+ super( directional.getName() );
+ mDirectional = directional;
+ }
+
+ void update()
+ {
+ int dir = mDirectional.getDirection();
+
+ //
+ // Only if value really changes
+ //
+ if ( dir != mCurrent )
+ {
+ this.setText( mDirectional.getName() + ": " + ( mDirectional.isCentered() ? "-" : Integer.toString( dir ) ) );
+ mCurrent = dir;
+ }
+ }
+ }
+
+
+ /**
+ * Setup the dialogs content from the JXInputDevice.
+ */
+ void initFromDevice()
+ {
+ if ( null != mDev )
+ {
+ ((GridLayout)mAxesPanel.getLayout()).setRows( mDev.getNumberOfAxes() );
+
+ for ( int i = 0; i < mDev.getMaxNumberOfAxes(); ++i )
+ {
+ if ( null != mDev.getAxis( i ) )
+ {
+ AxisSlider slider = new AxisSlider( mDev.getAxis( i ) );
+
+ JLabel name = new JLabel( mDev.getAxis( i ).getName() );
+ name.setVerticalAlignment( SwingConstants.TOP );
+ name.setHorizontalAlignment( SwingConstants.CENTER );
+ name.setPreferredSize( new java.awt.Dimension( 90, 0 ) );
+
+ JPanel p = new JPanel();
+ p.setLayout( new BorderLayout() );
+
+ p.add( name, BorderLayout.WEST );
+ p.add( slider, BorderLayout.CENTER );
+
+ mAxesPanel.add( p );
+
+ // Add to list of all AxisSlider controls
+ mAxisSliders.add( slider );
+
+ // Add an event listener:
+ new AxisListener( mDev.getAxis( i ) );
+ }
+ }
+
+
+ ((GridLayout)mButtonsPanel.getLayout()).setRows( mDev.getNumberOfButtons() );
+ for ( int i = 0; i < mDev.getMaxNumberOfButtons(); ++i )
+ {
+ if ( null != mDev.getButton( i ) )
+ {
+ ButtonCheckbox chk = new ButtonCheckbox( mDev.getButton( i ) );
+ mButtonCheckboxes.add( chk );
+ mButtonsPanel.add( chk );
+
+ // Add an event listener:
+ new ButtonListener( mDev.getButton( i ) );
+ }
+ }
+
+ ((GridLayout)mDirectionalPanel.getLayout()).setRows( mDev.getNumberOfDirectionals() / 2 );
+ for ( int i = 0; i < mDev.getMaxNumberOfDirectionals(); ++i )
+ {
+ if ( null != mDev.getDirectional( i ) )
+ {
+ DirectionalLabel lbl = new DirectionalLabel( mDev.getDirectional( i ) );
+ mDirectionalLabels.add( lbl );
+ mDirectionalPanel.add( lbl );
+
+ // Add an event listener:
+ new DirectionalListener( mDev.getDirectional( i ) );
+ }
+ }
+ }
+ }
+
+
+ public void update()
+ {
+ Iterator it = mAxisSliders.iterator();
+ while ( it.hasNext() )
+ {
+ ((AxisSlider)it.next()).update();
+ }
+
+ it = mButtonCheckboxes.iterator();
+ while ( it.hasNext() )
+ {
+ ((ButtonCheckbox)it.next()).update();
+ }
+
+ it = mDirectionalLabels.iterator();
+ while ( it.hasNext() )
+ {
+ ((DirectionalLabel)it.next()).update();
+ }
+ }
+
+
+ /** This method is called from within the constructor to
+ * initialize the form.
+ * WARNING: Do NOT modify this code. The content of this method is
+ * always regenerated by the Form Editor.
+ */
+ // //GEN-BEGIN:initComponents
+ private void initComponents()
+ {
+ mAxesPanelContainer = new javax.swing.JPanel();
+ mAxesPanel = new javax.swing.JPanel();
+ mDirectionalPanel = new javax.swing.JPanel();
+ mButtonScrollPane = new javax.swing.JScrollPane();
+ mButtonsPanel = new javax.swing.JPanel();
+
+ setLayout(new java.awt.BorderLayout(2, 2));
+
+ addComponentListener(new java.awt.event.ComponentAdapter()
+ {
+ public void componentShown(java.awt.event.ComponentEvent evt)
+ {
+ OnShow(evt);
+ }
+ });
+
+ mAxesPanelContainer.setLayout(new java.awt.BorderLayout());
+
+ mAxesPanelContainer.setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.RAISED));
+ mAxesPanel.setLayout(new java.awt.GridLayout(1, 1, 0, 20));
+
+ mAxesPanelContainer.add(mAxesPanel, java.awt.BorderLayout.NORTH);
+
+ add(mAxesPanelContainer, java.awt.BorderLayout.CENTER);
+
+ mDirectionalPanel.setLayout(new java.awt.GridLayout(1, 1));
+
+ mDirectionalPanel.setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.RAISED));
+ add(mDirectionalPanel, java.awt.BorderLayout.SOUTH);
+
+ mButtonsPanel.setLayout(new java.awt.GridLayout(1, 1));
+
+ mButtonsPanel.setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.RAISED));
+ mButtonScrollPane.setViewportView(mButtonsPanel);
+
+ add(mButtonScrollPane, java.awt.BorderLayout.EAST);
+
+ }// //GEN-END:initComponents
+
+ private void OnShow(java.awt.event.ComponentEvent evt)//GEN-FIRST:event_OnShow
+ {//GEN-HEADEREND:event_OnShow
+ // Commented: the focus is held by a parent component
+// System.out.println("OnShow");
+// this.requestFocus();
+ }//GEN-LAST:event_OnShow
+
+
+
+ // Variables declaration - do not modify//GEN-BEGIN:variables
+ private javax.swing.JPanel mAxesPanel;
+ private javax.swing.JPanel mAxesPanelContainer;
+ private javax.swing.JScrollPane mButtonScrollPane;
+ private javax.swing.JPanel mButtonsPanel;
+ private javax.swing.JPanel mDirectionalPanel;
+ // End of variables declaration//GEN-END:variables
+
+}
diff --git a/java/de/hardcode/jxinput/test/JXInputTestDialog.form b/java/de/hardcode/jxinput/test/JXInputTestDialog.form
new file mode 100644
index 0000000..1abc589
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/JXInputTestDialog.form
@@ -0,0 +1,79 @@
+
+
+
diff --git a/java/de/hardcode/jxinput/test/JXInputTestDialog.java b/java/de/hardcode/jxinput/test/JXInputTestDialog.java
new file mode 100644
index 0000000..3829aa2
--- /dev/null
+++ b/java/de/hardcode/jxinput/test/JXInputTestDialog.java
@@ -0,0 +1,286 @@
+//**********************************************************************************************
+// Dipl. Phys. Joerg Plewe, HARDCODE Development
+// Created on 27. Dezember 2001, 01:15
+//**********************************************************************************************
+
+package de.hardcode.jxinput.test;
+
+import de.hardcode.jxinput.*;
+import de.hardcode.jxinput.event.*;
+import de.hardcode.jxinput.keyboard.JXKeyboardInputDevice;
+import de.hardcode.jxinput.virtual.JXVirtualInputDevice;
+import de.hardcode.jxinput.virtual.VirtualAxis;
+
+import javax.swing.*;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import java.awt.event.KeyEvent;
+
+
+/**
+ * Test dialog showing some features of JXInput.
+ * @author Herkules
+ */
+public class JXInputTestDialog extends javax.swing.JDialog
+ implements ActionListener
+{
+
+ private JXKeyboardInputDevice mKeyboardDevice = null;
+ private JXVirtualInputDevice mVirtualDevice = null;
+
+ Button mButtonUp;
+ Button mButtonDown;
+ Button mButtonLeft;
+ Button mButtonRight;
+ Button mButtonFire;
+ Button mButtonSpace;
+
+ /** Creates new form JXInputTestDialog */
+ public JXInputTestDialog(java.awt.Frame parent, boolean modal)
+ {
+ super(parent, modal);
+ initComponents();
+ configureKeyboardInputDevice();
+ configureVirtualInputDevice();
+ initDevicePanels();
+ pack();
+
+ // Request the focus so that the keyboarddevice can work
+ mMainPanel.requestFocus();
+
+ new Timer( 50, this ).start();
+
+ // Uncomment this line as an alternative to the Timer above.
+ // Don't use both!!
+ //JXInputEventManager.setTriggerIntervall( 50 );
+ }
+
+
+ /**
+ * Implement ActionListener#actionPerformed().
+ * This is called by the Timer.
+ */
+ public void actionPerformed( ActionEvent e )
+ {
+ JXInputManager.updateFeatures();
+ SwingUtilities.invokeLater(
+ new Runnable()
+ {
+ public void run()
+ {
+ for ( int i = 0; i < mDevicesTabbedPane.getComponentCount(); ++i )
+ {
+ ((JXInputDevicePanel)mDevicesTabbedPane.getComponent( i )).update();
+ }
+ }
+ }
+ );
+ }
+
+
+ /**
+ * Configure a test JXKeyboardInputdevice.
+ */
+ void configureKeyboardInputDevice()
+ {
+ mKeyboardDevice = JXInputManager.createKeyboardDevice();
+
+ mKeyboardDevice.createButton( KeyEvent.VK_ESCAPE );
+
+ mKeyboardDevice.createButton( KeyEvent.VK_F1 );
+ mKeyboardDevice.createButton( KeyEvent.VK_F2 );
+ mKeyboardDevice.createButton( KeyEvent.VK_F3 );
+ mKeyboardDevice.createButton( KeyEvent.VK_F4 );
+
+ mKeyboardDevice.createButton( KeyEvent.VK_LEFT );
+ mKeyboardDevice.createButton( KeyEvent.VK_RIGHT );
+ mKeyboardDevice.createButton( KeyEvent.VK_UP );
+ mKeyboardDevice.createButton( KeyEvent.VK_DOWN );
+
+ mKeyboardDevice.createButton( KeyEvent.VK_PAGE_UP );
+ mKeyboardDevice.createButton( KeyEvent.VK_PAGE_DOWN );
+
+ mButtonSpace = mKeyboardDevice.createButton( KeyEvent.VK_SPACE );
+ mButtonLeft = mKeyboardDevice.createButton( KeyEvent.VK_A );
+ mButtonRight = mKeyboardDevice.createButton( KeyEvent.VK_D );
+ mButtonDown = mKeyboardDevice.createButton( KeyEvent.VK_S );
+ mButtonUp = mKeyboardDevice.createButton( KeyEvent.VK_W );
+
+ // Configure it to make it listen to the main panel.
+ // I try to keep the kbd focus on it.
+ mKeyboardDevice.listenTo( mMainPanel );
+ }
+
+
+ /**
+ * Configure a test JXVirtualInputdevice.
+ */
+ void configureVirtualInputDevice()
+ {
+ mVirtualDevice = JXInputManager.createVirtualDevice();
+
+ Button firebutton;
+ //
+ // Remember 'fire' button of first device for use
+ // in the virtual device.
+ // For we ran configureKeyboardInputDevice() before,
+ // getJXInputDevice( 0 ) should not return null
+ //
+ firebutton = JXInputManager.getJXInputDevice( 0 ).getButton( 0 );
+
+ VirtualAxis x = mVirtualDevice.createAxis( Axis.ID_X );
+ x.setButtons( mButtonRight, mButtonLeft );
+ x.setName( "x: A-D" );
+
+ VirtualAxis y = mVirtualDevice.createAxis( Axis.ID_Y );
+ y.setButtons( mButtonUp, mButtonDown );
+ y.setSpringSpeed( 0.0 );
+ y.setName( "y: S|W" );
+
+ VirtualAxis slider = mVirtualDevice.createAxis( Axis.ID_SLIDER0 );
+ slider.setIncreaseButton( mButtonSpace );
+ slider.setTimeFor0To1( 2000 );
+ slider.setName( "" );
+ slider.setType( Axis.SLIDER );
+
+ if ( null != firebutton )
+ {
+ slider = mVirtualDevice.createAxis( Axis.ID_SLIDER1 );
+ slider.setIncreaseButton( firebutton );
+ slider.setTimeFor0To1( 2000 );
+ slider.setName( "JoyButton 0" );
+ }
+
+
+ }
+
+
+ /**
+ * Initialize one panel for each device available.
+ */
+ void initDevicePanels()
+ {
+ int cnt = JXInputManager.getNumberOfDevices();
+
+ mLabelNoDevice.setVisible( cnt == 0 );
+ mDevicesTabbedPane.setVisible( cnt != 0 );
+
+ for ( int i = 0; i < cnt; ++i )
+ {
+ JXInputDevice dev = JXInputManager.getJXInputDevice( i );
+ if ( null != dev )
+ {
+ //
+ // Setup an own panel for each device.
+ //
+ JPanel panel = new JXInputDevicePanel( dev );
+ mDevicesTabbedPane.addTab( dev.getName(), panel );
+ }
+ }
+ }
+
+
+
+ /** This method is called from within the constructor to
+ * initialize the form.
+ * WARNING: Do NOT modify this code. The content of this method is
+ * always regenerated by the Form Editor.
+ */
+ // //GEN-BEGIN:initComponents
+ private void initComponents()
+ {
+ mMainPanel = new javax.swing.JPanel();
+ mLabelNoDevice = new javax.swing.JLabel();
+ mDevicesTabbedPane = new javax.swing.JTabbedPane();
+ mButtonReset = new javax.swing.JButton();
+
+ setTitle("JXInput (C) 2001-2006 HARDCODE Dev.");
+ addWindowListener(new java.awt.event.WindowAdapter()
+ {
+ public void windowClosing(java.awt.event.WindowEvent evt)
+ {
+ closeDialog(evt);
+ }
+ });
+
+ mMainPanel.setLayout(new java.awt.BorderLayout(10, 0));
+
+ mLabelNoDevice.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
+ mLabelNoDevice.setText("No JXInputDevice available!");
+ mLabelNoDevice.setBorder(new javax.swing.border.SoftBevelBorder(javax.swing.border.BevelBorder.RAISED));
+ mMainPanel.add(mLabelNoDevice, java.awt.BorderLayout.NORTH);
+
+ mDevicesTabbedPane.addFocusListener(new java.awt.event.FocusAdapter()
+ {
+ public void focusGained(java.awt.event.FocusEvent evt)
+ {
+ mDevicesTabbedPaneFocusGained(evt);
+ }
+ });
+
+ mMainPanel.add(mDevicesTabbedPane, java.awt.BorderLayout.CENTER);
+
+ mButtonReset.setText("Reset ");
+ mButtonReset.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(java.awt.event.ActionEvent evt)
+ {
+ mButtonResetActionPerformed(evt);
+ }
+ });
+
+ mMainPanel.add(mButtonReset, java.awt.BorderLayout.SOUTH);
+
+ getContentPane().add(mMainPanel, java.awt.BorderLayout.CENTER);
+
+ pack();
+ }// //GEN-END:initComponents
+
+ private void mButtonResetActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_mButtonResetActionPerformed
+ {//GEN-HEADEREND:event_mButtonResetActionPerformed
+
+ while ( this.mDevicesTabbedPane.getTabCount() > 0 )
+ this.mDevicesTabbedPane.removeTabAt( 0 );
+
+ JXInputManager.reset();
+ configureKeyboardInputDevice();
+ configureVirtualInputDevice();
+ initDevicePanels();
+ pack();
+
+ // Request the focus so that the keyboarddevice can work
+ mMainPanel.requestFocus();
+
+ }//GEN-LAST:event_mButtonResetActionPerformed
+
+ private void mDevicesTabbedPaneFocusGained(java.awt.event.FocusEvent evt)//GEN-FIRST:event_mDevicesTabbedPaneFocusGained
+ {//GEN-HEADEREND:event_mDevicesTabbedPaneFocusGained
+ // Switch focus back to main panel!
+ this.mMainPanel.requestFocus();
+ }//GEN-LAST:event_mDevicesTabbedPaneFocusGained
+
+ /** Closes the dialog */
+ private void closeDialog(java.awt.event.WindowEvent evt) {//GEN-FIRST:event_closeDialog
+ setVisible(false);
+ dispose();
+ System.exit( 0 );
+ }//GEN-LAST:event_closeDialog
+
+ /**
+ * Allow the dialog to run standalone.
+ * @param args the command line arguments
+ */
+ public static void main(String args[])
+ {
+ new JXInputTestDialog(new javax.swing.JFrame(), true).setVisible(true);
+ }
+
+
+ // Variables declaration - do not modify//GEN-BEGIN:variables
+ private javax.swing.JButton mButtonReset;
+ private javax.swing.JTabbedPane mDevicesTabbedPane;
+ private javax.swing.JLabel mLabelNoDevice;
+ private javax.swing.JPanel mMainPanel;
+ // End of variables declaration//GEN-END:variables
+
+}
diff --git a/java/de/hardcode/jxinput/util/LatestChangedValueAxis.java b/java/de/hardcode/jxinput/util/LatestChangedValueAxis.java
new file mode 100644
index 0000000..f4f2c35
--- /dev/null
+++ b/java/de/hardcode/jxinput/util/LatestChangedValueAxis.java
@@ -0,0 +1,98 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 17. April 2002, 23:24
+//**********************************************************************************************
+package de.hardcode.jxinput.util;
+
+import de.hardcode.jxinput.Axis;
+
+/**
+ *
+ * @author Herkules
+ */
+public class LatestChangedValueAxis implements Axis
+{
+ private final Axis mAxis1;
+ private final Axis mAxis2;
+ private Axis mAxisInUse;
+
+ private double mSaved1;
+ private double mSaved2;
+
+ /**
+ * Creates a new instance of MeanValueAxis.
+ */
+ public LatestChangedValueAxis(Axis a1, Axis a2)
+ {
+ mAxis1 = a1;
+ mAxis2 = a2;
+ mAxisInUse = a1;
+
+ mSaved1 = a1.getValue();
+ mSaved2 = a2.getValue();
+ }
+
+ /**
+ * Features may have a name provided e.g. by the driver.
+ */
+ public String getName()
+ {
+ return mAxis1.getName();
+ }
+
+ /** Inform about the resolution of the axis.
+ *
+ * @return resolution, e.g. 2^-16
+ */
+ public double getResolution()
+ {
+ return mAxis1.getResolution();
+ }
+
+ /**
+ * Retrieve the type of the axis.
+ *
+ * @return [ TRANSLATION | ROTATION | SLIDER ]
+ */
+ public int getType()
+ {
+ return mAxis1.getType();
+ }
+
+ /** Returns the current value of the axis.
+ * The range of the result depends on the axis type.
+ *s
+ * @return value [-1.0,1.0] or [0.0,1.0]
+ */
+ public double getValue()
+ {
+ double v1 = mAxis1.getValue();
+ double v2 = mAxis2.getValue();
+
+ if ( Math.abs( v2 - mSaved2 ) > 0.2 )
+ {
+ mAxisInUse = mAxis2;
+ mSaved2 = v2;
+ }
+ if ( Math.abs( v1 - mSaved1 ) > 0.2 )
+ {
+ mAxisInUse = mAxis1;
+ mSaved1 = v1;
+ }
+
+ return mAxisInUse.getValue();
+ }
+
+ /** Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ public boolean hasChanged()
+ {
+ return true;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/util/OrButton.java b/java/de/hardcode/jxinput/util/OrButton.java
new file mode 100644
index 0000000..338538c
--- /dev/null
+++ b/java/de/hardcode/jxinput/util/OrButton.java
@@ -0,0 +1,52 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 23. Dezember 2002, 19:21
+//**********************************************************************************************
+package de.hardcode.jxinput.util;
+
+import de.hardcode.jxinput.Button;
+
+/**
+ *
+ * @author Herkules
+ */
+public class OrButton implements Button
+{
+ private final Button mButton1;
+ private final Button mButton2;
+
+
+ /**
+ * Creates a new instance of OrButton.
+ */
+ public OrButton( Button b1, Button b2 )
+ {
+ mButton1 = b1;
+ mButton2 = b2;
+ }
+
+ public String getName()
+ {
+ return mButton1.getName();
+ }
+
+ public boolean getState()
+ {
+ return mButton1.getState() || mButton2.getState();
+ }
+
+ public int getType()
+ {
+ return mButton1.getType();
+ }
+
+ public boolean hasChanged()
+ {
+ return mButton1.hasChanged() || mButton2.hasChanged();
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/virtual/JXVirtualInputDevice.java b/java/de/hardcode/jxinput/virtual/JXVirtualInputDevice.java
new file mode 100644
index 0000000..aa125af
--- /dev/null
+++ b/java/de/hardcode/jxinput/virtual/JXVirtualInputDevice.java
@@ -0,0 +1,140 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 9. April 2002, 22:40
+//**********************************************************************************************
+package de.hardcode.jxinput.virtual;
+
+
+import de.hardcode.jxinput.*;
+
+
+/**
+ * Virtual input device.
+ *
+ * @author Herkules
+ */
+public class JXVirtualInputDevice implements JXInputDevice
+{
+ private static final String DEVICENAME = "Virtual Device";
+
+ /** The driver doing all the real work. */
+ private final VirtualDriver mDriver = new VirtualDriver();
+
+
+ /**
+ * Creates a new instance of JXKeyboardInputDevice.
+ */
+ public JXVirtualInputDevice()
+ {
+ }
+
+
+ /**
+ * The virtual input device needs to be updated regularly.
+ */
+ public final void update( long deltaT )
+ {
+ //
+ // Delegate the update call to the driver.
+ //
+ mDriver.update( deltaT );
+ }
+
+ /**
+ * Create a virtual axis object with a certain ID, e.g. Axis.ID_X.
+ */
+ public VirtualAxis createAxis( int id )
+ {
+ VirtualAxis a;
+ a = new VirtualAxis( id );
+ mDriver.registerVirtualAxis( id, a );
+ return a;
+ }
+
+
+ public void removeAxis( VirtualAxis a )
+ {
+ mDriver.unregisterVirtualAxis( a );
+ }
+
+
+
+ //*********************************************************************************************
+ //
+ // Implement JXInputDevice
+ //
+ //*********************************************************************************************
+
+ public Axis getAxis(int idx)
+ {
+ return mDriver.getAxis( idx );
+ }
+
+
+ public Button getButton(int idx)
+ {
+ // No virtual buttons.
+ return null;
+ }
+
+
+ public Directional getDirectional(int idx)
+ {
+ // No virtual directionals.
+ return null;
+ }
+
+ /** Maximum number of axes as an upper bound for index values. */
+ public int getMaxNumberOfAxes()
+ {
+ return Axis.NUMBER_OF_ID;
+ }
+
+ /** Maximum number of buttons as an upper bound for index values. */
+ public int getMaxNumberOfButtons()
+ {
+ // No virtual buttons.
+ return 0;
+ }
+
+ /** Maximum number of directional features as an upper bound for index values. */
+ public int getMaxNumberOfDirectionals()
+ {
+ // No virtual directionals.
+ return 0;
+ }
+
+ /**
+ * Devices may have a name.
+ * This name might be provided by a system dependant driver.
+ */
+ public String getName()
+ {
+ return DEVICENAME;
+ }
+
+ /** Actual number of available axes. */
+ public int getNumberOfAxes()
+ {
+ // No axes on keyboard.
+ return mDriver.getNumberOfAxes();
+ }
+
+ /** Actual number of available buttons. */
+ public int getNumberOfButtons()
+ {
+ return 0;
+ }
+
+ /** Actual number of available directional features. */
+ public int getNumberOfDirectionals()
+ {
+ // No directionals on keyboard.
+ return 0;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/virtual/VirtualAxis.java b/java/de/hardcode/jxinput/virtual/VirtualAxis.java
new file mode 100644
index 0000000..b272c6e
--- /dev/null
+++ b/java/de/hardcode/jxinput/virtual/VirtualAxis.java
@@ -0,0 +1,207 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 11. April 2002, 23:40
+//**********************************************************************************************
+package de.hardcode.jxinput.virtual;
+
+import de.hardcode.jxinput.Axis;
+import de.hardcode.jxinput.Button;
+import java.security.InvalidParameterException;
+
+/**
+ *
+ * @author Jörg Plewe
+ */
+public class VirtualAxis
+ implements Axis
+{
+
+ private int mType = Axis.TRANSLATION;
+ private final int mID;
+ private String mName = "VirtualAxis";
+ private double mCurrentValue = 0;
+
+ private Button mButtonIncrease = null;
+ private Button mButtonDecrease = null;
+ private double mSpeed = 1.0 / 500.0;
+ private double mSpringSpeed = 1.0 / 500.0;
+
+ /**
+ * Creates a new instance of VirtualAxis.
+ */
+ public VirtualAxis( int id )
+ {
+ mID = id;
+ }
+
+
+ /**
+ * Set the type of this axis to be either Axis.ROTATION,
+ * Axis.TRANSLATION or Axis.SLIDER.
+ */
+ public void setType( int type )
+ {
+ if ( Axis.ROTATION != type
+ && Axis.TRANSLATION != type
+ && Axis.SLIDER != type
+ )
+ throw new InvalidParameterException( "Invalid type for axis!" );
+
+ mType = type;
+ }
+
+ /**
+ * Update features under my control.
+ */
+ final void update( long deltaT )
+ {
+ double change = mSpeed * deltaT;
+ double springchange = mSpringSpeed * deltaT;
+ boolean doincrease = ( null != mButtonIncrease && mButtonIncrease.getState() );
+ boolean dodecrease = ( null != mButtonDecrease && mButtonDecrease.getState() );
+ boolean iscontrolled = doincrease || dodecrease;
+
+ double controlledchange = 0.0;
+ if ( doincrease )
+ controlledchange += change;
+ if ( dodecrease )
+ controlledchange -= change;
+
+ mCurrentValue += controlledchange;
+
+ if ( mCurrentValue > 0.0 && ! doincrease )
+ {
+ springchange = Math.min( mCurrentValue, springchange );
+ mCurrentValue -= springchange;
+ }
+ if ( mCurrentValue < 0.0 && ! dodecrease )
+ {
+ springchange = Math.min( -mCurrentValue, springchange );
+ mCurrentValue += springchange;
+ }
+
+ //
+ // Hold value within range
+ //
+ if ( mCurrentValue > 1.0 )
+ mCurrentValue = 1.0;
+ double lowerlimit = Axis.SLIDER == mType ? 0.0 : -1.0;
+ if ( mCurrentValue < lowerlimit )
+ mCurrentValue = lowerlimit;
+ }
+
+
+ /**
+ * Set the button to increase the axis for a single button axis.
+ */
+ public final void setIncreaseButton( Button b )
+ {
+ if ( null == b )
+ throw new InvalidParameterException( "Button may not be null!" );
+
+ mButtonIncrease = b;
+ }
+
+
+ /**
+ * Set the buttons to increase and descrease the axis.
+ */
+ public final void setButtons( Button increase, Button decrease )
+ {
+ if ( null == increase || null == decrease )
+ throw new InvalidParameterException( "Buttons may not be null!" );
+
+ mButtonIncrease = increase;
+ mButtonDecrease = decrease;
+ }
+
+
+ public final void setSpeed( double speed )
+ {
+ mSpeed = speed;
+ }
+
+ public final void setSpringSpeed( double springspeed )
+ {
+ mSpringSpeed = springspeed;
+ }
+
+
+ public final void setTimeFor0To1( int ms )
+ {
+ if ( 0 >= ms )
+ mSpeed = 0.0;
+ else
+ mSpeed = 1.0/ ms;
+ }
+ public final void setTimeFor1To0( int ms )
+ {
+ if ( 0 >= ms )
+ mSpringSpeed = 0.0;
+ else
+ mSpringSpeed = 1.0/ ms;
+ }
+
+
+ public final void setName( String name )
+ {
+ mName = name;
+ }
+
+ //*********************************************************************************************
+ //
+ // Implement Axis
+ //
+ //*********************************************************************************************
+
+ /**
+ * Features may have a name provided e.g. by the driver.
+ */
+ public String getName()
+ {
+ return mName;
+ }
+
+ /**
+ * Inform about the resolution of the axis.
+ *
+ * @return resolution, e.g. 2^-16
+ */
+ public double getResolution()
+ {
+ return 1.0/65536.0;
+ }
+
+
+ /**
+ * Retrieve the type of the axis.
+ * @return [ TRANSLATION | ROTATION | SLIDER ]
+ */
+ public int getType()
+ {
+ return mType;
+ }
+
+ /** Returns the current value of the axis.
+ * The range of the result depends on the axis type.
+ *
+ * @return value [-1.0,1.0] or [0.0,1.0]
+ */
+ public double getValue()
+ {
+ return mCurrentValue;
+ }
+
+ /** Denote wether this feature has changed beyond it's resolution since it got last
+ * updated.
+ */
+ public boolean hasChanged()
+ {
+ return true;
+ }
+
+}
diff --git a/java/de/hardcode/jxinput/virtual/VirtualDriver.java b/java/de/hardcode/jxinput/virtual/VirtualDriver.java
new file mode 100644
index 0000000..5952eff
--- /dev/null
+++ b/java/de/hardcode/jxinput/virtual/VirtualDriver.java
@@ -0,0 +1,95 @@
+//**********************************************************************************************
+// (C) Copyright 2002 by Dipl. Phys. Joerg Plewe, HARDCODE Development
+// All rights reserved. Copying, modification,
+// distribution or publication without the prior written
+// consent of the author is prohibited.
+//
+// Created on 9. April 2002, 22:43
+//**********************************************************************************************
+package de.hardcode.jxinput.virtual;
+
+import java.util.ArrayList;
+import de.hardcode.jxinput.Axis;
+
+
+
+/**
+ * This is the main worker class for JXVirtualInputDevice.
+ *
+ * @author Herkules
+ */
+class VirtualDriver
+{
+
+ private final VirtualAxis[] mVAxes = new VirtualAxis[ Axis.NUMBER_OF_ID ];
+
+ /**
+ * Creates a new instance of KeyboardDriver.
+ */
+ VirtualDriver()
+ {
+ }
+
+
+ /**
+ * Update features under my control.
+ */
+ final void update( long deltaT )
+ {
+ //
+ // Delegate the update call to the axes in use.
+ //
+ for ( int i = 0; i < mVAxes.length; i++ )
+ {
+ if ( null != mVAxes[ i ] )
+ mVAxes[ i ].update( deltaT );
+ }
+ }
+
+
+ /**
+ * How many axes are registered?
+ */
+ final int getNumberOfAxes()
+ {
+ int ctr = 0;
+ for ( int i = 0; i < mVAxes.length; i++ )
+ {
+ if ( null != mVAxes[ i ] )
+ ctr++;
+ }
+ return ctr;
+ }
+
+ Axis getAxis(int idx)
+ {
+ return mVAxes[ idx ];
+ }
+
+
+ /**
+ * Place a new axis under my observation.
+ */
+ final void registerVirtualAxis( int id, VirtualAxis a )
+ {
+ mVAxes[ id ] = a;
+ }
+
+
+ /**
+ * Remove an axis from my control.
+ */
+ final void unregisterVirtualAxis( VirtualAxis a )
+ {
+ for ( int i = 0; i < mVAxes.length; ++i )
+ {
+ if ( mVAxes[ i ] == a )
+ {
+ mVAxes[ i ] = null;
+ break;
+ }
+ }
+ }
+
+
+}
diff --git a/java/de/hardcode/jxinput/virtual/package.html b/java/de/hardcode/jxinput/virtual/package.html
new file mode 100644
index 0000000..d8e1d6a
--- /dev/null
+++ b/java/de/hardcode/jxinput/virtual/package.html
@@ -0,0 +1,11 @@
+
+
+
+
+ de.hardcode.jxinput.virtual
+
+
+Allows to define virtual axes that are not derived from any device
+but from other JXInput feature objects.
+
+
diff --git a/win32/.cvsignore b/win32/.cvsignore
new file mode 100644
index 0000000..252078e
--- /dev/null
+++ b/win32/.cvsignore
@@ -0,0 +1,8 @@
+*.ncb
+Release
+*.plg
+Debug
+*~
+jxinput.vcproj.HERKBOOK.Herkules.user
+jxinput.suo
+*.opt
diff --git a/win32/JXInputManager.cpp b/win32/JXInputManager.cpp
new file mode 100644
index 0000000..3718a7f
--- /dev/null
+++ b/win32/JXInputManager.cpp
@@ -0,0 +1,175 @@
+
+#include "stdafx.h"
+#include "JXInputManager.h"
+#include "JXInput.h"
+
+//
+// Globals
+//
+extern HINSTANCE g_hInst;
+
+
+JXInputManager::JXInputManager( HWND hWnd ) :
+mhWnd( hWnd ),
+mDeviceCounter( 0 )
+{
+
+ for ( int i = 0; i < MAX_JXINPUTS; ++i )
+ {
+ mDevices[ i ] = NULL;
+ }
+
+
+ if ( FAILED( InitDirectInput( hWnd ) ) )
+ {
+ FreeDirectInput();
+ }
+
+}
+
+JXInputManager::~JXInputManager()
+{
+ for ( int i = 0; i < getNumberOfJXInputs(); ++i )
+ {
+ delete mDevices[ i ];
+ mDevices[ i ] = NULL;
+ }
+
+ FreeDirectInput();
+}
+
+int JXInputManager::getNumberOfJXInputs() const
+{
+ return mDeviceCounter;
+}
+
+JXInput& JXInputManager::getJXInput( int idx ) const
+{
+ assert( idx < mDeviceCounter );
+ return * mDevices[ idx ];
+}
+
+
+int JXInputManager::getMaxNumberOfAxes() const
+{
+ return JXINPUT_MAX_AXES;
+}
+
+int JXInputManager::getMaxNumberOfButtons() const
+{
+ return JXINPUT_MAX_BUTTONS;
+}
+
+int JXInputManager::getMaxNumberOfDirectionals() const
+{
+ return JXINPUT_MAX_DIRECTIONALS;
+}
+
+
+
+//-----------------------------------------------------------------------------
+// Name: InitDirectInput()
+// Desc: Initialize the DirectInput variables.
+//-----------------------------------------------------------------------------
+HRESULT JXInputManager::InitDirectInput( HWND hWnd )
+{
+ HRESULT hr;
+
+ // Register with the DirectInput subsystem and get a pointer
+ // to a IDirectInput interface we can use.
+ // Create a DInput object
+ if( FAILED( hr = DirectInput8Create( g_hInst, DIRECTINPUT_VERSION,
+ IID_IDirectInput8, (VOID**)&mpDI, NULL ) ) )
+ return hr;
+
+ // Look for a simple joystick we can use for this sample program.
+ if( FAILED( hr = mpDI->EnumDevices( DI8DEVCLASS_GAMECTRL,
+ EnumJoysticksCallback,
+ (VOID*)this, DIEDFL_ALLDEVICES /*| DIEDFL_INCLUDEPHANTOMS*/ ) ) )
+ return hr;
+
+ // Look for a other devices
+ if( FAILED( hr = mpDI->EnumDevices( DI8DEVCLASS_DEVICE,
+ EnumJoysticksCallback,
+ (VOID*)this, DIEDFL_ALLDEVICES /*| DIEDFL_INCLUDEPHANTOMS*/ ) ) )
+ return hr;
+
+ return S_OK;
+}
+
+
+//-----------------------------------------------------------------------------
+// Name: FreeDirectInput()
+// Desc: Initialize the DirectInput variables.
+//-----------------------------------------------------------------------------
+HRESULT JXInputManager::FreeDirectInput()
+{
+
+ if ( NULL != mpDI )
+ mpDI->Release();
+ mpDI = NULL;
+ return S_OK;
+}
+
+
+//-----------------------------------------------------------------------------
+// Name: EnumJoysticksCallback()
+// Desc: Called once for each enumerated joystick. If we find one, create a
+// device interface on it so we can play with it.
+//-----------------------------------------------------------------------------
+BOOL CALLBACK JXInputManager::EnumJoysticksCallback( const DIDEVICEINSTANCE* pdidInstance,
+ VOID* pContext )
+{
+ HRESULT hr;
+ LPDIRECTINPUTDEVICE8 pJoystick;
+
+ JXInputManager* pThis = (JXInputManager*)pContext;
+
+ //
+ // if the maximum number of devices is already registered,
+ // issue a warning and stop enumeration.
+ //
+ if( MAX_JXINPUTS == pThis->mDeviceCounter )
+ {
+ OutputDebugString( "Max. number of devices exceeded!" );
+ return DIENUM_STOP;
+ }
+
+
+
+ // Obtain an interface to the enumerated joystick.
+ hr = pThis->mpDI->CreateDevice( pdidInstance->guidInstance, &pJoystick, NULL );
+
+ // If it failed, then we can't use this joystick. (Maybe the user unplugged
+ // it while we were in the middle of enumerating it.)
+ if( FAILED(hr) )
+ return DIENUM_CONTINUE;
+
+ JXInput* pJ = new JXInput( pJoystick, pThis->mhWnd );
+
+ //
+ // only register useful devices
+ //
+ if( pJ->getNumberOfAxes() + pJ->getNumberOfButtons() + pJ->getNumberOfDirectionals() > 0 )
+ {
+ pThis->addJXInput( pJ );
+ }
+ else
+ {
+ delete pJ;
+ }
+
+ return DIENUM_CONTINUE;
+}
+
+
+/**
+ * Register a JXInput device.
+ */
+void JXInputManager::addJXInput( JXInput* pJ )
+{
+ assert( mDeviceCounter < MAX_JXINPUTS );
+
+ if( mDeviceCounter < MAX_JXINPUTS )
+ mDevices[ mDeviceCounter++ ] = pJ;
+}
diff --git a/win32/JXInputManager.h b/win32/JXInputManager.h
new file mode 100644
index 0000000..41b9da4
--- /dev/null
+++ b/win32/JXInputManager.h
@@ -0,0 +1,47 @@
+// JXInputManager.h: Schnittstelle für die Klasse JXInputManager.
+//
+//////////////////////////////////////////////////////////////////////
+
+#if !defined(AFX_JXINPUTMANAGER_H__24862402_14C9_407D_8532_A16A6E3A7D64__INCLUDED_)
+#define AFX_JXINPUTMANAGER_H__24862402_14C9_407D_8532_A16A6E3A7D64__INCLUDED_
+
+#if _MSC_VER > 1000
+#pragma once
+#endif // _MSC_VER > 1000
+
+
+#define MAX_JXINPUTS 10
+
+class JXInput;
+
+class JXINPUT_API JXInputManager
+{
+public:
+ JXInputManager( HWND hWnd );
+ virtual ~JXInputManager();
+
+ int getNumberOfJXInputs() const;
+ JXInput& getJXInput( int idx ) const;
+
+ //
+ // Numbering methods
+ //
+ int getMaxNumberOfAxes() const;
+ int getMaxNumberOfButtons() const;
+ int getMaxNumberOfDirectionals() const;
+
+private:
+ LPDIRECTINPUT8 mpDI;
+ HWND mhWnd;
+ JXInput* mDevices[ MAX_JXINPUTS ];
+ int mDeviceCounter;
+
+ HRESULT InitDirectInput( HWND hWnd = NULL );
+ HRESULT FreeDirectInput();
+
+ static BOOL CALLBACK EnumJoysticksCallback( const DIDEVICEINSTANCE* pdidInstance,
+ VOID* pContext );
+ void addJXInput( JXInput* pJ );
+};
+
+#endif // !defined(AFX_JXINPUTMANAGER_H__24862402_14C9_407D_8532_A16A6E3A7D64__INCLUDED_)
diff --git a/win32/ReadMe.txt b/win32/ReadMe.txt
new file mode 100644
index 0000000..755cd4c
--- /dev/null
+++ b/win32/ReadMe.txt
@@ -0,0 +1,37 @@
+========================================================================
+ DYNAMIC LINK LIBRARY : jxinput
+========================================================================
+
+
+Diese jxinput-DLL hat der Anwendungs-Assistent für Sie erstellt.
+
+Diese Datei enthält eine Zusammenfassung dessen, was Sie in jeder der Dateien
+finden, die Ihre jxinput-Anwendung bilden.
+
+jxinput.dsp
+ Diese Datei (Projektdatei) enthält Informationen auf Projektebene und wird zur
+ Erstellung eines einzelnen Projekts oder Teilprojekts verwendet. Andere Benutzer können
+ die Projektdatei (.dsp) gemeinsam nutzen, sollten aber die Makefiles lokal exportieren.
+
+jxinput.cpp
+ Dies ist die Hauptquellcodedatei für die DLL.
+
+jxinput.h
+ Diese Datei enthält Ihre DLL-Exporte.
+
+/////////////////////////////////////////////////////////////////////////////
+Weitere Standarddateien:
+
+StdAfx.h, StdAfx.cpp
+ Diese Dateien werden zum Erstellen einer vorkompilierten Header-Datei (PCH) namens
+ jxinput.pch und einer vorkompilierten Typdatei namens StdAfx.obj verwendet.
+
+
+/////////////////////////////////////////////////////////////////////////////
+Weitere Hinweise:
+
+Der Anwendungs-Assistent verwendet "ZU ERLEDIGEN:", um Bereiche des Quellcodes zu
+kennzeichnen, die Sie hinzufügen oder anpassen sollten.
+
+
+/////////////////////////////////////////////////////////////////////////////
diff --git a/win32/StdAfx.cpp b/win32/StdAfx.cpp
new file mode 100644
index 0000000..a144a09
--- /dev/null
+++ b/win32/StdAfx.cpp
@@ -0,0 +1,9 @@
+// stdafx.cpp : Quelltextdatei, die nur die Standard-Includes einbindet
+// jxinput.pch ist die vorkompilierte Header-Datei
+// stdafx.obj enthält die vorkompilierte Typinformation
+
+#include "stdafx.h"
+
+// ZU ERLEDIGEN: Verweis auf alle zusätzlichen Header-Dateien, die Sie in STDAFX.H
+// und nicht in dieser Datei benötigen
+
diff --git a/win32/StdAfx.h b/win32/StdAfx.h
new file mode 100644
index 0000000..e139c4c
--- /dev/null
+++ b/win32/StdAfx.h
@@ -0,0 +1,32 @@
+// stdafx.h : Include-Datei für Standard-System-Include-Dateien,
+// oder projektspezifische Include-Dateien, die häufig benutzt, aber
+// in unregelmäßigen Abständen geändert werden.
+//
+
+#if !defined(AFX_STDAFX_H__68E14C76_098F_47ED_932B_4C01E8E9EFFB__INCLUDED_)
+#define AFX_STDAFX_H__68E14C76_098F_47ED_932B_4C01E8E9EFFB__INCLUDED_
+
+#if _MSC_VER > 1000
+#pragma once
+#endif // _MSC_VER > 1000
+
+
+// Fügen Sie hier Ihre Header-Dateien ein
+#define WIN32_LEAN_AND_MEAN // Selten benutzte Teile der Windows-Header nicht einbinden
+#define STRICT
+#include
+
+// ZU ERLEDIGEN: Verweisen Sie hier auf zusätzliche Header-Dateien, die Ihr Programm benötigt
+#ifdef JXINPUT_EXPORTS
+#define JXINPUT_API __declspec(dllexport)
+#else
+#define JXINPUT_API __declspec(dllimport)
+#endif
+
+#include
+#include
+
+//{{AFX_INSERT_LOCATION}}
+// Microsoft Visual C++ fügt zusätzliche Deklarationen unmittelbar vor der vorherigen Zeile ein.
+
+#endif // !defined(AFX_STDAFX_H__68E14C76_098F_47ED_932B_4C01E8E9EFFB__INCLUDED_)
diff --git a/win32/de_hardcode_jxinput_directinput_DirectInputDriver.cpp b/win32/de_hardcode_jxinput_directinput_DirectInputDriver.cpp
new file mode 100644
index 0000000..077afe8
--- /dev/null
+++ b/win32/de_hardcode_jxinput_directinput_DirectInputDriver.cpp
@@ -0,0 +1,279 @@
+#include "stdafx.h"
+
+#include "de_hardcode_jxinput_directinput_DirectInputDriver.h"
+#include "jxinput.h"
+#include "JXInputManager.h"
+
+
+//
+// Globals
+//
+extern HINSTANCE g_hInst;
+
+static JXInputManager* pJXInputManager = NULL;
+static JXInput* apJXInput[ MAX_JXINPUTS ];
+static HWND hWndJava;
+
+//
+// IDs of the static Java arrays.
+//
+static jfieldID sAxesFieldID;
+static jfieldID sButtonsFieldID;
+static jfieldID sDirectionsFieldID;
+
+
+
+/**
+ * Remove all resources allocated by the Java binding.
+ */
+void shutdownJavaResources()
+{
+ if ( NULL != pJXInputManager )
+ delete pJXInputManager;
+
+ if ( NULL != hWndJava )
+ DestroyWindow( hWndJava );
+
+ pJXInputManager = NULL;
+
+ for( int i = 0; i < MAX_JXINPUTS; ++i )
+ apJXInput[ i ] = NULL;
+
+ hWndJava = NULL;
+}
+
+
+
+JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved)
+{
+ return JNI_VERSION_1_2;
+}
+
+
+JNIEXPORT void JNICALL JNI_OnUnload(JavaVM *vm, void *reserved)
+{
+ shutdownJavaResources();
+}
+
+
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_nativeinit
+ (JNIEnv * penv, jclass pClazz )
+{
+
+ //
+ // Create a non-visible window as 'owner' of the DI device.
+ //
+ hWndJava = CreateWindowEx(
+ 0/*WS_EX_APPWINDOW*/, // DWORD dwExStyle, // extended window style
+ "STATIC", // LPCTSTR lpClassName, // pointer to registered class name
+ NULL, // LPCTSTR lpWindowName, // pointer to window name
+ 0/*WS_CAPTION*/, // DWORD dwStyle, // window style
+ 0, // int x, // horizontal position of window
+ 0, // int y, // vertical position of window
+ 0, // int nWidth, // window width
+ 0, // int nHeight, // window height
+ NULL, // HWND hWndParent, // handle to parent or owner window
+ NULL, // HMENU hMenu, // handle to menu, or child-window identifier
+ g_hInst, // HINSTANCE hInstance, // handle to application instance
+ NULL // LPVOID lpParam // pointer to window-creation data
+ );
+
+
+ if ( NULL == pJXInputManager )
+ {
+ pJXInputManager = new JXInputManager( hWndJava );
+
+ for( int i = 0; i < MAX_JXINPUTS; ++i )
+ apJXInput[ i ] = NULL;
+
+ for ( int i = 0; i < pJXInputManager->getNumberOfJXInputs(); ++i )
+ {
+ apJXInput[ i ] = & pJXInputManager->getJXInput( i );
+ }
+ }
+
+ return true;
+}
+
+
+
+JNIEXPORT void JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_nativeexit
+ (JNIEnv *, jclass )
+{
+ shutdownJavaResources();
+}
+
+
+/**
+ * Bind my field IDs to the Java variables.
+ */
+JNIEXPORT void JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_bind
+ (JNIEnv * penv, jclass pClazz)
+{
+ //
+ // All fields are static.
+ //
+ sAxesFieldID = penv->GetStaticFieldID( pClazz, "sAxisValues", "[[D" );
+ sButtonsFieldID = penv->GetStaticFieldID( pClazz, "sButtonStates", "[[Z" );
+ sDirectionsFieldID = penv->GetStaticFieldID( pClazz, "sDirectionalValues", "[[I" );
+}
+
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfDevices
+ (JNIEnv *penv, jclass)
+{
+ return pJXInputManager->getNumberOfJXInputs();
+}
+
+
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getName
+ (JNIEnv *penv, jclass, jint dev)
+{
+ return penv->NewStringUTF( apJXInput[ dev ]->getName() );
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfAxes
+ (JNIEnv *, jclass, jint dev)
+{
+ return apJXInput[ dev ]->getNumberOfAxes();
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfButtons
+ (JNIEnv *, jclass, jint dev)
+{
+ return apJXInput[ dev ]->getNumberOfButtons();
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfDirectionals
+ (JNIEnv *, jclass, jint dev)
+{
+ return apJXInput[ dev ]->getNumberOfDirectionals();
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getMaxNumberOfAxes
+ (JNIEnv *, jclass)
+{
+ return pJXInputManager->getMaxNumberOfAxes();
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getMaxNumberOfButtons
+ (JNIEnv *, jclass)
+{
+ return pJXInputManager->getMaxNumberOfButtons();
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getMaxNumberOfDirectionals
+ (JNIEnv *, jclass)
+{
+ return pJXInputManager->getMaxNumberOfDirectionals();
+}
+
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_isAxisAvailable
+ (JNIEnv *, jclass, jint dev, jint idx )
+{
+ return apJXInput[ dev ]->isAxisAvailable( idx );
+}
+
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getAxisName
+ (JNIEnv *penv, jclass, jint dev, jint idx )
+{
+ return penv->NewStringUTF( apJXInput[ dev ]->getAxisName( idx ) );
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getAxisType
+ (JNIEnv *, jclass, jint dev, jint idx )
+{
+ return apJXInput[ dev ]->getAxisType( idx );
+}
+
+
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_isButtonAvailable
+ (JNIEnv *, jclass, jint dev, jint idx )
+{
+ return apJXInput[ dev ]->isButtonAvailable( idx );
+}
+
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getButtonName
+ (JNIEnv *penv, jclass, jint dev, jint idx )
+{
+ return penv->NewStringUTF( apJXInput[ dev ]->getButtonName( idx ) );
+}
+
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getButtonType
+ (JNIEnv *, jclass, jint dev, jint idx )
+{
+ return apJXInput[ dev ]->getButtonType( idx );
+}
+
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_isDirectionalAvailable
+ (JNIEnv *, jclass, jint dev, jint idx )
+{
+ return apJXInput[ dev ]->isDirectionalAvailable( idx );
+}
+
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getDirectionalName
+ (JNIEnv *penv, jclass, jint dev, jint idx )
+{
+ return penv->NewStringUTF( apJXInput[ dev ]->getDirectionalName( idx ) );
+}
+
+
+
+/**
+ * The main update method.
+ * Here, the actual work is done.
+ */
+JNIEXPORT void JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_nativeupdate
+ (JNIEnv * penv, jclass pClazz )
+{
+
+ static jdouble axes [ MAX_JXINPUTS ][ JXINPUT_MAX_AXES ];
+ static jboolean buttons [ MAX_JXINPUTS ][ JXINPUT_MAX_BUTTONS ];
+ static jint directions [ MAX_JXINPUTS ][ JXINPUT_MAX_DIRECTIONALS ];
+
+ static jobjectArray axisarrayarray;
+ static jobjectArray buttonarrayarray;
+ static jobjectArray directionarrayarray;
+
+ static jdoubleArray axisarray;
+ static jbooleanArray buttonarray;
+ static jintArray directionarray;
+
+ axisarrayarray = (jobjectArray)penv->GetStaticObjectField( pClazz, sAxesFieldID );
+ buttonarrayarray = (jobjectArray)penv->GetStaticObjectField( pClazz, sButtonsFieldID );
+ directionarrayarray = (jobjectArray)penv->GetStaticObjectField( pClazz, sDirectionsFieldID );
+
+ //
+ // For each device....
+ //
+ for ( int dev = 0; dev < pJXInputManager->getNumberOfJXInputs(); ++dev )
+ {
+ // Do the update of the device.
+ apJXInput[ dev ]->update();
+
+ //
+ // Copy all values into my arrays.
+ //
+ for ( int i = 0; i < JXINPUT_MAX_AXES; ++i )
+ axes[ dev ][ i ] = apJXInput[ dev ]->getAxisValue( i );
+ for ( int i = 0; i < JXINPUT_MAX_BUTTONS; ++i )
+ buttons[ dev ][ i ] = apJXInput[ dev ]->isButtonDown( i );
+ for ( int i = 0; i < JXINPUT_MAX_DIRECTIONALS; ++i )
+ directions[ dev ][ i ] = apJXInput[ dev ]->getDirection( i );
+
+
+ //
+ // Move my arrays to the Java arrays.
+ //
+ axisarray = (jdoubleArray)penv->GetObjectArrayElement( axisarrayarray, dev );
+ penv->SetDoubleArrayRegion( axisarray, 0, JXINPUT_MAX_AXES, axes[ dev ] );
+
+ buttonarray = (jbooleanArray)penv->GetObjectArrayElement( buttonarrayarray, dev );
+ penv->SetBooleanArrayRegion( buttonarray, 0, JXINPUT_MAX_BUTTONS, buttons[ dev ] );
+
+ directionarray = (jintArray)penv->GetObjectArrayElement( directionarrayarray, dev );
+ penv->SetIntArrayRegion( directionarray, 0, JXINPUT_MAX_DIRECTIONALS, directions[ dev ] );
+ }
+
+}
+
diff --git a/win32/de_hardcode_jxinput_directinput_DirectInputDriver.h b/win32/de_hardcode_jxinput_directinput_DirectInputDriver.h
new file mode 100644
index 0000000..bb93548
--- /dev/null
+++ b/win32/de_hardcode_jxinput_directinput_DirectInputDriver.h
@@ -0,0 +1,183 @@
+/* DO NOT EDIT THIS FILE - it is machine generated */
+#include
+
+/* Header for class de_hardcode_jxinput_directinput_DirectInputDriver */
+
+#ifndef _Included_de_hardcode_jxinput_directinput_DirectInputDriver
+#define _Included_de_hardcode_jxinput_directinput_DirectInputDriver
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* Inaccessible static: sIsOperational */
+/* Inaccessible static: sAxisValues */
+/* Inaccessible static: sButtonStates */
+/* Inaccessible static: sDirectionalValues */
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: nativeinit
+ * Signature: ()Z
+ */
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_nativeinit
+ (JNIEnv *, jclass);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: nativeexit
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_nativeexit
+ (JNIEnv *, jclass);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: bind
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_bind
+ (JNIEnv *, jclass);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getNumberOfDevices
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfDevices
+ (JNIEnv *, jclass);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getName
+ * Signature: (I)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getName
+ (JNIEnv *, jclass, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getNumberOfAxes
+ * Signature: (I)I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfAxes
+
+ (JNIEnv *, jclass, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getNumberOfButtons
+ * Signature: (I)I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfButtons
+ (JNIEnv *, jclass, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getNumberOfDirectionals
+ * Signature: (I)I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getNumberOfDirectionals
+ (JNIEnv *, jclass, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getMaxNumberOfAxes
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getMaxNumberOfAxes
+ (JNIEnv *, jclass);
+
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getMaxNumberOfButtons
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getMaxNumberOfButtons
+ (JNIEnv *, jclass);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getMaxNumberOfDirectionals
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getMaxNumberOfDirectionals
+ (JNIEnv *, jclass);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: isAxisAvailable
+ * Signature: (II)Z
+ */
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_isAxisAvailable
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getAxisName
+ * Signature: (II)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getAxisName
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getAxisType
+ * Signature: (II)I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getAxisType
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: isButtonAvailable
+ * Signature: (II)Z
+ */
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_isButtonAvailable
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getButtonName
+ * Signature: (II)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getButtonName
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getButtonType
+ * Signature: (II)I
+ */
+JNIEXPORT jint JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getButtonType
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: isDirectionalAvailable
+ * Signature: (II)Z
+ */
+JNIEXPORT jboolean JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_isDirectionalAvailable
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: getDirectionalName
+ * Signature: (II)Ljava/lang/String;
+ */
+JNIEXPORT jstring JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_getDirectionalName
+ (JNIEnv *, jclass, jint, jint);
+
+/*
+ * Class: de_hardcode_jxinput_directinput_DirectInputDriver
+ * Method: nativeupdate
+ * Signature: ()V
+ */
+JNIEXPORT void JNICALL Java_de_hardcode_jxinput_directinput_DirectInputDriver_nativeupdate
+ (JNIEnv *, jclass);
+
+#ifdef __cplusplus
+}
+#endif
+#endif
+
diff --git a/win32/dllmain.cpp b/win32/dllmain.cpp
new file mode 100644
index 0000000..567e8d4
--- /dev/null
+++ b/win32/dllmain.cpp
@@ -0,0 +1,24 @@
+#include "stdafx.h"
+
+HINSTANCE g_hInst;
+
+
+BOOL APIENTRY DllMain( HANDLE hModule,
+ DWORD ul_reason_for_call,
+ LPVOID lpReserved
+ )
+{
+ switch (ul_reason_for_call)
+ {
+ case DLL_PROCESS_ATTACH:
+ g_hInst = (HINSTANCE)hModule;
+ break;
+ case DLL_THREAD_ATTACH:
+ case DLL_THREAD_DETACH:
+ break;
+ case DLL_PROCESS_DETACH:
+ g_hInst = NULL;
+ break;
+ }
+ return TRUE;
+}
diff --git a/win32/jxinput.cpp b/win32/jxinput.cpp
new file mode 100644
index 0000000..890805b
--- /dev/null
+++ b/win32/jxinput.cpp
@@ -0,0 +1,600 @@
+//
+// jxinput.cpp
+//
+#include "stdafx.h"
+#include "jxinput.h"
+
+
+//
+// Globals
+//
+extern HINSTANCE g_hInst;
+
+
+/**
+ * Ctor: Connect with DI
+ */
+JXInput::JXInput( LPDIRECTINPUTDEVICE8 pJoystick, HWND hWnd ) :
+ mpJoystick( pJoystick ),
+ mSliderCount( 0 ),
+ mPOVCount( 0 ),
+ mButtonCount( 0 )
+{
+ initAxisConfig();
+ initButtonsConfig();
+ initDirectionalsConfig();
+
+ if ( FAILED( InitDirectInput( hWnd ) ) )
+ {
+ FreeDirectInput();
+ }
+}
+
+
+
+/**
+ * Destructor:
+ * Free DirectInput.
+ */
+JXInput::~JXInput()
+{
+ FreeDirectInput();
+}
+
+
+void JXInput::update()
+{
+ UpdateInputState();
+}
+
+
+TCHAR * const JXInput::getName() const
+{
+ return (TCHAR*)mdiDevInfo.tszInstanceName;
+}
+
+
+
+int JXInput::getNumberOfAxes() const
+{
+ return mdiDevCaps.dwAxes;
+}
+
+int JXInput::getNumberOfButtons() const
+{
+ return mButtonCount;
+}
+
+int JXInput::getNumberOfDirectionals() const
+{
+ return mPOVCount;
+}
+
+
+double JXInput::getAxisValueHelper( LONG val, int idx ) const
+{
+ const AxisConfig& cfg = mAxisConfig[ idx ];
+
+ double span = (double)( cfg.mMaxValue - cfg.mMinValue );
+ double ret = (double)(val - cfg.mMinValue) / span;
+
+ if ( TYPE_SLIDER != cfg.mType )
+ return ret*2.0 - 1.0;
+ return ret;
+}
+
+double JXInput::getX() const
+{
+ return getAxisValueHelper( mJS.lX, ID_X );
+}
+double JXInput::getY() const
+{
+ return getAxisValueHelper( mJS.lY, ID_Y );
+}
+double JXInput::getZ() const
+{
+ return getAxisValueHelper( mJS.lZ, ID_Z );
+}
+double JXInput::getRotX() const
+{
+ return getAxisValueHelper( mJS.lRx, ID_ROTX );
+}
+double JXInput::getRotY() const
+{
+ return getAxisValueHelper( mJS.lRy, ID_ROTY );
+}
+double JXInput::getRotZ() const
+{
+ return getAxisValueHelper( mJS.lRz, ID_ROTZ );
+}
+double JXInput::getSlider0() const
+{
+ return getAxisValueHelper( mJS.rglSlider[ 0 ], ID_SLIDER0 );
+}
+double JXInput::getSlider1() const
+{
+ return getAxisValueHelper( mJS.rglSlider[ 1 ], ID_SLIDER1 );
+}
+
+
+
+bool JXInput::isAxisAvailable( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_AXES );
+ return mAxisConfig[ idx ].mIsAvailable;
+}
+
+TCHAR * const JXInput::getAxisName( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_AXES );
+ return (char*const)mAxisConfig[ idx ].mName;
+}
+
+int JXInput::getAxisType( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_AXES );
+ return mAxisConfig[ idx ].mType;
+}
+
+double JXInput::getAxisValue( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_AXES );
+
+ // Failsafe if called accidentally
+ if ( ! mAxisConfig[ idx ].mIsAvailable )
+ return 0.0;
+
+ return (this->*mAxisConfig[ idx ].mGetValueMethod)();
+}
+
+
+
+
+
+bool JXInput::isButtonAvailable( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_BUTTONS );
+ return mButtonConfig[ idx ].mIsAvailable;
+}
+
+TCHAR * const JXInput::getButtonName( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_BUTTONS );
+ return (char*const)mButtonConfig[ idx ].mName;
+}
+
+int JXInput::getButtonType( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_BUTTONS );
+ return mButtonConfig[ idx ].mType;
+}
+
+bool JXInput::isButtonDown( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_BUTTONS );
+ return 0 != mJS.rgbButtons[ idx ] ;
+}
+
+
+bool JXInput::isDirectionalAvailable( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_DIRECTIONALS );
+ return mDirectionalConfig[ idx ].mIsAvailable;
+}
+
+TCHAR * const JXInput::getDirectionalName( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_DIRECTIONALS );
+ return (char*const)mDirectionalConfig[ idx ].mName;
+}
+
+int JXInput::getDirection( int idx ) const
+{
+ assert( idx < JXINPUT_MAX_DIRECTIONALS );
+ return mJS.rgdwPOV[ idx ] ;
+}
+
+
+/**
+ * Initialize axis configuration array.
+ */
+void JXInput::initAxisConfig()
+{
+ mAxisConfig[ ID_X ].mIsAvailable = false;
+ mAxisConfig[ ID_X ].mType = TYPE_TRANSLATION;
+ mAxisConfig[ ID_X ].mGetValueMethod = &JXInput::getX;
+
+ mAxisConfig[ ID_Y ].mIsAvailable = false;
+ mAxisConfig[ ID_Y ].mType = TYPE_TRANSLATION;
+ mAxisConfig[ ID_Y ].mGetValueMethod = &JXInput::getY;
+
+ mAxisConfig[ ID_Z ].mIsAvailable = false;
+ mAxisConfig[ ID_Z ].mType = TYPE_TRANSLATION;
+ mAxisConfig[ ID_Z ].mGetValueMethod = &JXInput::getZ;
+
+ mAxisConfig[ ID_ROTX ].mIsAvailable = false;
+ mAxisConfig[ ID_ROTX ].mType = TYPE_ROTATION;
+ mAxisConfig[ ID_ROTX ].mGetValueMethod = &JXInput::getRotX;
+
+ mAxisConfig[ ID_ROTY ].mIsAvailable = false;
+ mAxisConfig[ ID_ROTY ].mType = TYPE_ROTATION;
+ mAxisConfig[ ID_ROTY ].mGetValueMethod = &JXInput::getRotY;
+
+ mAxisConfig[ ID_ROTZ ].mIsAvailable = false;
+ mAxisConfig[ ID_ROTZ ].mType = TYPE_ROTATION;
+ mAxisConfig[ ID_ROTZ ].mGetValueMethod = &JXInput::getRotZ;
+
+ mAxisConfig[ ID_SLIDER0 ].mIsAvailable = false;
+ mAxisConfig[ ID_SLIDER0 ].mType = TYPE_SLIDER;
+ mAxisConfig[ ID_SLIDER0 ].mGetValueMethod = &JXInput::getSlider0;
+
+ mAxisConfig[ ID_SLIDER1 ].mIsAvailable = false;
+ mAxisConfig[ ID_SLIDER1 ].mType = TYPE_SLIDER;
+ mAxisConfig[ ID_SLIDER1 ].mGetValueMethod = &JXInput::getSlider1;
+}
+
+
+/**
+ * Initialize buttons configuration array.
+ */
+void JXInput::initButtonsConfig()
+{
+ for ( int i = 0; i < JXINPUT_MAX_BUTTONS; ++i )
+ {
+ mButtonConfig[ i ].mIsAvailable = false;
+ mButtonConfig[ i ].mName[ 0 ] = '\0';
+ mButtonConfig[ i ].mType = TYPE_PUSHBUTTON;
+ }
+
+}
+
+
+/**
+ * Initialize directionals configuration array.
+ */
+void JXInput::initDirectionalsConfig()
+{
+ for ( int i = 0; i < JXINPUT_MAX_DIRECTIONALS; ++i )
+ {
+ mDirectionalConfig[ i ].mIsAvailable = false;
+ mDirectionalConfig[ i ].mName[ 0 ] = '\0';
+ }
+
+}
+
+
+
+//-----------------------------------------------------------------------------
+// Name: EnumAxesCallback()
+// Desc: Callback function for enumerating the axes on a joystick
+//-----------------------------------------------------------------------------
+BOOL CALLBACK JXInput::EnumAxesCallback( const DIDEVICEOBJECTINSTANCE* pdidoi,
+ VOID* pContext )
+{
+ JXInput* pThis = (JXInput*)pContext;
+
+ AxisConfig* pAxCfg = NULL;
+
+ // Set the UI to reflect what objects the joystick supports
+ // Code derived from M$ samples, really sucks, eh?
+ if (pdidoi->guidType == GUID_XAxis)
+ {
+ pAxCfg = & pThis->mAxisConfig[ ID_X ];
+ }
+ if (pdidoi->guidType == GUID_YAxis)
+ {
+ pAxCfg = & pThis->mAxisConfig[ ID_Y ];
+ }
+ if (pdidoi->guidType == GUID_ZAxis)
+ {
+ pAxCfg = & pThis->mAxisConfig[ ID_Z ];
+ }
+ if (pdidoi->guidType == GUID_RxAxis)
+ {
+ pAxCfg = & pThis->mAxisConfig[ ID_ROTX ];
+ }
+ if (pdidoi->guidType == GUID_RyAxis)
+ {
+ pAxCfg = & pThis->mAxisConfig[ ID_ROTY ];
+ }
+ if (pdidoi->guidType == GUID_RzAxis)
+ {
+ pAxCfg = & pThis->mAxisConfig[ ID_ROTZ ];
+ }
+ if (pdidoi->guidType == GUID_Slider)
+ {
+ switch( pThis->mSliderCount++ )
+ {
+ case 0 :
+ pAxCfg = & pThis->mAxisConfig[ ID_SLIDER0 ];
+ break;
+
+ case 1 :
+ pAxCfg = & pThis->mAxisConfig[ ID_SLIDER1 ];
+ break;
+ }
+ }
+
+ // fail-safe
+ if( NULL == pAxCfg ) // e.g. GUID_Unknown
+ return DIENUM_CONTINUE;
+
+
+ //
+ // Perform config.
+ //
+
+ DIPROPRANGE diprg;
+ diprg.diph.dwSize = sizeof(DIPROPRANGE);
+ diprg.diph.dwHeaderSize = sizeof(DIPROPHEADER);
+ diprg.diph.dwHow = DIPH_BYID;
+ diprg.diph.dwObj = pdidoi->dwType; // Specify the enumerated axis
+
+ // Get the range for the axis
+ if( FAILED( pThis->mpJoystick->GetProperty( DIPROP_RANGE, &diprg.diph ) ) )
+ return DIENUM_CONTINUE;
+
+ pAxCfg->mMinValue = diprg.lMin;
+ pAxCfg->mMaxValue = diprg.lMax;
+
+ strcpy( (char*)pAxCfg->mName, (char*)pdidoi->tszName );
+ pAxCfg->mIsAvailable = true;
+
+ return DIENUM_CONTINUE;
+}
+
+
+
+//-----------------------------------------------------------------------------
+// Name: EnumButtonsCallback()
+// Desc: Callback function for enumerating the axes on a joystick
+//-----------------------------------------------------------------------------
+BOOL CALLBACK JXInput::EnumButtonsCallback( const DIDEVICEOBJECTINSTANCE* pdidoi,
+ VOID* pContext )
+{
+ JXInput* pThis = (JXInput*)pContext;
+
+ //
+ // if the maximum number of buttons is already registered,
+ // issue a warning and stop enumeration.
+ //
+ if( JXINPUT_MAX_BUTTONS == pThis->mButtonCount )
+ {
+ OutputDebugString( "Max. number of buttons exceeded!" );
+ return DIENUM_STOP;
+ }
+
+
+ ButtonConfig* pBtCfg = NULL;
+
+ if ( pdidoi->guidType == GUID_Button )
+ {
+ assert( JXINPUT_MAX_BUTTONS > pThis->mButtonCount );
+ pBtCfg = & pThis->mButtonConfig[ pThis->mButtonCount++ ];
+ }
+
+
+ // fail-safe
+ if( NULL == pBtCfg ) // e.g. unknown stuff
+ return DIENUM_CONTINUE;
+ assert( NULL != pBtCfg );
+
+ //
+ // Perform config.
+ //
+
+ strcpy( (char*)pBtCfg->mName, (char*)pdidoi->tszName );
+ pBtCfg->mIsAvailable = true;
+
+ return DIENUM_CONTINUE;
+}
+
+
+//-----------------------------------------------------------------------------
+// Name: EnumPOVsCallback()
+// Desc: Callback function for enumerating the axes on a joystick
+//-----------------------------------------------------------------------------
+BOOL CALLBACK JXInput::EnumPOVsCallback( const DIDEVICEOBJECTINSTANCE* pdidoi,
+ VOID* pContext )
+{
+ JXInput* pThis = (JXInput*)pContext;
+
+ //
+ // if the maximum number of buttons is already registered,
+ // issue a warning and stop enumeration.
+ //
+ if( JXINPUT_MAX_DIRECTIONALS == pThis->mPOVCount )
+ {
+ OutputDebugString( "Max. number of POVs exceeded!" );
+ return DIENUM_STOP;
+ }
+
+ DirectionalConfig* pDirCfg = NULL;
+
+
+ if (pdidoi->guidType == GUID_POV)
+ {
+ assert( JXINPUT_MAX_DIRECTIONALS > pThis->mPOVCount );
+ pDirCfg = & pThis->mDirectionalConfig[ pThis->mPOVCount++ ];
+ }
+
+ // fail-safe
+ if( NULL == pDirCfg ) // e.g. unknown stuff
+ return DIENUM_CONTINUE;
+ assert( NULL != pDirCfg );
+
+ //
+ // Perform config.
+ //
+
+ strcpy( (char*)pDirCfg->mName, (char*)pdidoi->tszName );
+ pDirCfg->mIsAvailable = true;
+
+ return DIENUM_CONTINUE;
+}
+
+
+
+//-----------------------------------------------------------------------------
+// Name: EnumEffectsCallback()
+// Desc: Callback function for enumerating the effects of a joystick
+//-----------------------------------------------------------------------------
+BOOL CALLBACK JXInput::EnumEffectsCallback( const DIEFFECTINFO* pdidoi,
+ VOID* pContext )
+{
+ JXInput* pThis = (JXInput*)pContext;
+
+ //
+ // Work on that!!
+ //
+
+ return DIENUM_CONTINUE;
+}
+
+
+
+//-----------------------------------------------------------------------------
+// Name: InitDirectInput()
+// Desc: Initialize the DirectInput variables.
+//-----------------------------------------------------------------------------
+HRESULT JXInput::InitDirectInput( HWND hWnd )
+{
+ HRESULT hr;
+
+ // Make sure we got a joystick
+ if( NULL == mpJoystick )
+ {
+ return E_FAIL;
+ }
+
+
+ //
+ // Ask the device for some useful information.
+ //
+ mdiDevInfo.dwSize = sizeof( DIDEVICEINSTANCE );
+ hr = mpJoystick->GetDeviceInfo( &mdiDevInfo );
+ if( FAILED(hr) )
+ return hr;
+
+ // Set the data format to "simple joystick" - a predefined data format
+ //
+ // A data format specifies which controls on a device we are interested in,
+ // and how they should be reported. This tells DInput that we will be
+ // passing a DIJOYSTATE structure to IDirectInputDevice::GetDeviceState().
+ hr = mpJoystick->SetDataFormat( &c_dfDIJoystick2 );
+ if( FAILED(hr) )
+ return hr;
+
+ // Set the cooperative level to let DInput know how this device should
+ // interact with the system and with other DInput applications.
+// hr = g_pJoystick->SetCooperativeLevel( hDlg, DISCL_EXCLUSIVE|DISCL_FOREGROUND );
+ DWORD mode = ( NULL == hWnd ? DISCL_NONEXCLUSIVE|DISCL_BACKGROUND : DISCL_EXCLUSIVE|DISCL_BACKGROUND );
+ hr = mpJoystick->SetCooperativeLevel( hWnd, mode );
+ if( FAILED(hr) )
+ return hr;
+
+ // Determine how many axis the joystick has (so we don't error out setting
+ // properties for unavailable axis)
+ mdiDevCaps.dwSize = sizeof(DIDEVCAPS);
+ hr = mpJoystick->GetCapabilities(&mdiDevCaps);
+ if ( FAILED(hr) )
+ return hr;
+
+
+ // Enumerate the axes of the joyctick and set the range of each axis. Note:
+ // we could just use the defaults, but we're just trying to show an example
+ // of enumerating device objects (axes, buttons, etc.).
+ mpJoystick->EnumObjects( EnumAxesCallback, (VOID*)this, DIDFT_AXIS );
+ mpJoystick->EnumObjects( EnumButtonsCallback, (VOID*)this, DIDFT_BUTTON );
+ mpJoystick->EnumObjects( EnumPOVsCallback, (VOID*)this, DIDFT_POV );
+
+ mpJoystick->EnumEffects( EnumEffectsCallback, (VOID*)this, DIEFT_ALL );
+
+ // For FF sticks, switch on autocenter as long as we do not use real FF
+ SwitchAutoCenter( true );
+
+ return S_OK;
+}
+
+
+
+
+
+//-----------------------------------------------------------------------------
+// Name: UpdateInputState()
+// Desc: Get the input device's state and display it.
+//-----------------------------------------------------------------------------
+HRESULT JXInput::UpdateInputState()
+{
+ HRESULT hr;
+
+ if( mpJoystick )
+ {
+
+ // Poll the device to read the current state
+ hr = mpJoystick->Poll();
+ if( FAILED(hr) )
+ {
+ // DInput is telling us that the input stream has been
+ // interrupted. We aren't tracking any state between polls, so
+ // we don't have any special reset that needs to be done. We
+ // just re-acquire and try again.
+ hr = mpJoystick->Acquire();
+ while( hr == DIERR_INPUTLOST )
+ hr = mpJoystick->Acquire();
+
+ // hr may be DIERR_OTHERAPPHASPRIO or other errors. This
+ // may occur when the app is minimized or in the process of
+ // switching, so just try again later
+ return S_OK;
+ }
+
+ // Get the input's device state
+ if( FAILED( hr = mpJoystick->GetDeviceState( sizeof(DIJOYSTATE2), &mJS ) ) )
+ return hr; // The device should have been acquired during the Poll()
+
+ }
+
+ return S_OK;
+}
+
+
+
+
+//-----------------------------------------------------------------------------
+// Name: FreeDirectInput()
+// Desc: Initialize the DirectInput variables.
+//-----------------------------------------------------------------------------
+HRESULT JXInput::FreeDirectInput()
+{
+ // Unacquire and release any DirectInputDevice objects.
+ if( NULL != mpJoystick )
+ {
+ // Unacquire the device one last time just in case
+ // the app tried to exit while the device is still acquired.
+ mpJoystick->Unacquire();
+
+ mpJoystick->Release();
+ mpJoystick = NULL;
+ }
+
+ return S_OK;
+}
+
+
+
+HRESULT JXInput::SwitchAutoCenter( bool onoff )
+{
+ HRESULT hr;
+
+ DIPROPDWORD DIPropAutoCenter;
+
+ DIPropAutoCenter.diph.dwSize = sizeof(DIPropAutoCenter);
+ DIPropAutoCenter.diph.dwHeaderSize = sizeof(DIPROPHEADER);
+ DIPropAutoCenter.diph.dwObj = 0;
+ DIPropAutoCenter.diph.dwHow = DIPH_DEVICE;
+ DIPropAutoCenter.dwData = ( onoff ? DIPROPAUTOCENTER_ON : DIPROPAUTOCENTER_OFF );
+
+ hr = mpJoystick->SetProperty( DIPROP_AUTOCENTER, &DIPropAutoCenter.diph );
+ return hr;
+}
diff --git a/win32/jxinput.dsp b/win32/jxinput.dsp
new file mode 100644
index 0000000..aac15c1
--- /dev/null
+++ b/win32/jxinput.dsp
@@ -0,0 +1,175 @@
+# Microsoft Developer Studio Project File - Name="jxinput" - Package Owner=<4>
+# Microsoft Developer Studio Generated Build File, Format Version 6.00
+# ** NICHT BEARBEITEN **
+
+# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102
+
+CFG=jxinput - Win32 Debug
+!MESSAGE Dies ist kein gültiges Makefile. Zum Erstellen dieses Projekts mit NMAKE
+!MESSAGE verwenden Sie den Befehl "Makefile exportieren" und führen Sie den Befehl
+!MESSAGE
+!MESSAGE NMAKE /f "jxinput.mak".
+!MESSAGE
+!MESSAGE Sie können beim Ausführen von NMAKE eine Konfiguration angeben
+!MESSAGE durch Definieren des Makros CFG in der Befehlszeile. Zum Beispiel:
+!MESSAGE
+!MESSAGE NMAKE /f "jxinput.mak" CFG="jxinput - Win32 Debug"
+!MESSAGE
+!MESSAGE Für die Konfiguration stehen zur Auswahl:
+!MESSAGE
+!MESSAGE "jxinput - Win32 Release" (basierend auf "Win32 (x86) Dynamic-Link Library")
+!MESSAGE "jxinput - Win32 Debug" (basierend auf "Win32 (x86) Dynamic-Link Library")
+!MESSAGE
+
+# Begin Project
+# PROP AllowPerConfigDependencies 0
+# PROP Scc_ProjName ""
+# PROP Scc_LocalPath ""
+CPP=cl.exe
+MTL=midl.exe
+RSC=rc.exe
+
+!IF "$(CFG)" == "jxinput - Win32 Release"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 0
+# PROP BASE Output_Dir "Release"
+# PROP BASE Intermediate_Dir "Release"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 0
+# PROP Output_Dir "Release"
+# PROP Intermediate_Dir "Release"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "JXINPUT_EXPORTS" /Yu"stdafx.h" /FD /c
+# ADD CPP /nologo /MT /W3 /GX /O2 /I "C:\j2sdk1.4.2\include" /I "C:\j2sdk1.4.2\include\win32" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "JXINPUT_EXPORTS" /FR /Yu"stdafx.h" /FD /c
+# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
+# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
+# ADD BASE RSC /l 0x407 /d "NDEBUG"
+# ADD RSC /l 0x407 /d "NDEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386
+# ADD LINK32 dxguid.lib dinput8.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"..\build\jxinput.dll"
+
+!ELSEIF "$(CFG)" == "jxinput - Win32 Debug"
+
+# PROP BASE Use_MFC 0
+# PROP BASE Use_Debug_Libraries 1
+# PROP BASE Output_Dir "Debug"
+# PROP BASE Intermediate_Dir "Debug"
+# PROP BASE Target_Dir ""
+# PROP Use_MFC 0
+# PROP Use_Debug_Libraries 1
+# PROP Output_Dir "Debug"
+# PROP Intermediate_Dir "Debug"
+# PROP Ignore_Export_Lib 0
+# PROP Target_Dir ""
+# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "JXINPUT_EXPORTS" /Yu"stdafx.h" /FD /GZ /c
+# ADD CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /I "C:\j2sdk1.4.2\include" /I "C:\j2sdk1.4.2\include\win32" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "JXINPUT_EXPORTS" /FR /Yu"stdafx.h" /FD /GZ /c
+# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
+# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
+# ADD BASE RSC /l 0x407 /d "_DEBUG"
+# ADD RSC /l 0x407 /d "_DEBUG"
+BSC32=bscmake.exe
+# ADD BASE BSC32 /nologo
+# ADD BSC32 /nologo
+LINK32=link.exe
+# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept
+# ADD LINK32 dxguid.lib dinput8.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"..\Classes\jxinput.dll" /pdbtype:sept
+
+!ENDIF
+
+# Begin Target
+
+# Name "jxinput - Win32 Release"
+# Name "jxinput - Win32 Debug"
+# Begin Group "Quellcodedateien"
+
+# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
+# Begin Source File
+
+SOURCE=.\de_hardcode_jxinput_directinput_DirectInputDriver.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\dllmain.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\jxinput.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\JXInputManager.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=.\StdAfx.cpp
+# ADD CPP /Yc"stdafx.h"
+# End Source File
+# End Group
+# Begin Group "Header-Dateien"
+
+# PROP Default_Filter "h;hpp;hxx;hm;inl"
+# Begin Source File
+
+SOURCE=.\de_hardcode_jxinput_directinput_DirectInputDriver.h
+
+!IF "$(CFG)" == "jxinput - Win32 Release"
+
+# PROP Ignore_Default_Tool 1
+USERDEP__DE_HA="..\classes\de\hardcode\jxinput\directinput\DirectInputDriver.class"
+# Begin Custom Build
+InputPath=.\de_hardcode_jxinput_directinput_DirectInputDriver.h
+
+"de_hardcode_jxinput_directinput_DirectInputDriver.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ cd ..\Classes
+ C:\j2sdk1.4.2\bin\javah -classpath . -d ..\win32 de.hardcode.jxinput.directinput.DirectInputDriver
+ cd ..\win32
+
+# End Custom Build
+
+!ELSEIF "$(CFG)" == "jxinput - Win32 Debug"
+
+# PROP Ignore_Default_Tool 1
+USERDEP__DE_HA="..\classes\de\hardcode\jxinput\directinput\DirectInputDriver.class"
+# Begin Custom Build
+InputPath=.\de_hardcode_jxinput_directinput_DirectInputDriver.h
+
+"de_hardcode_jxinput_directinput_DirectInputDriver.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
+ cd ..\Classes
+ C:\j2sdk1.4.2\bin\javah -classpath . -d ..\win32 de.hardcode.jxinput.directinput.DirectInputDriver
+ cd ..\win32
+
+# End Custom Build
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=.\jxinput.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\JXInputManager.h
+# End Source File
+# Begin Source File
+
+SOURCE=.\StdAfx.h
+# End Source File
+# End Group
+# Begin Group "Ressourcendateien"
+
+# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
+# End Group
+# Begin Source File
+
+SOURCE=.\ReadMe.txt
+# End Source File
+# End Target
+# End Project
diff --git a/win32/jxinput.dsw b/win32/jxinput.dsw
new file mode 100644
index 0000000..deb2877
--- /dev/null
+++ b/win32/jxinput.dsw
@@ -0,0 +1,29 @@
+Microsoft Developer Studio Workspace File, Format Version 6.00
+# WARNUNG: DIESE ARBEITSBEREICHSDATEI DARF NICHT BEARBEITET ODER GELÖSCHT WERDEN!
+
+###############################################################################
+
+Project: "jxinput"=".\jxinput.dsp" - Package Owner=<4>
+
+Package=<5>
+{{{
+}}}
+
+Package=<4>
+{{{
+}}}
+
+###############################################################################
+
+Global:
+
+Package=<5>
+{{{
+}}}
+
+Package=<3>
+{{{
+}}}
+
+###############################################################################
+
diff --git a/win32/jxinput.h b/win32/jxinput.h
new file mode 100644
index 0000000..6d47a31
--- /dev/null
+++ b/win32/jxinput.h
@@ -0,0 +1,183 @@
+
+#define JXINPUT_MAX_AXES 8
+#define JXINPUT_MAX_BUTTONS 256
+#define JXINPUT_MAX_DIRECTIONALS 4
+
+
+/**
+ * This class will be exported by jxinput.dll.
+ */
+class JXINPUT_API JXInput
+{
+
+public:
+
+ typedef enum AXISTYPE
+ {
+ TYPE_TRANSLATION,
+ TYPE_ROTATION,
+ TYPE_SLIDER
+ };
+
+ typedef enum BUTTONTYPE
+ {
+ TYPE_PUSHBUTTON,
+ TYPE_TOGGLEBUTTON
+ };
+
+ typedef enum AXISID
+ {
+ ID_X, ID_Y, ID_Z,
+ ID_ROTX, ID_ROTY, ID_ROTZ,
+ ID_SLIDER0, ID_SLIDER1
+ };
+
+
+ //
+ // Ctor
+ //
+ JXInput( LPDIRECTINPUTDEVICE8 pJoystick, HWND hWnd = NULL );
+
+ //
+ // Dtor
+ //
+ virtual ~JXInput();
+
+ //
+ // Operational methods
+ //
+ void update();
+
+ // Ask for the name
+ TCHAR * const getName() const;
+
+ //
+ // Numbering methods
+ //
+ int getNumberOfAxes() const;
+ int getNumberOfButtons() const;
+ int getNumberOfDirectionals() const;
+
+
+ //
+ // Access axes
+ //
+ double getX() const; /** -1.0 .... 1.0 */
+ double getY() const; /** -1.0 .... 1.0 */
+ double getZ() const; /** -1.0 .... 1.0 */
+ double getRotX() const; /** -1.0 .... 1.0 */
+ double getRotY() const; /** -1.0 .... 1.0 */
+ double getRotZ() const; /** -1.0 .... 1.0 */
+ double getSlider0() const; /** 0.0 .... 1.0 */
+ double getSlider1() const; /** 0.0 .... 1.0 */
+
+
+ //
+ // Axis methods
+ //
+ bool isAxisAvailable( int idx ) const;
+ TCHAR* const getAxisName( int idx ) const;
+ int getAxisType( int idx ) const;
+ double getAxisValue( int idx ) const;
+
+ //
+ // Button methods
+ //
+ bool isButtonAvailable( int idx ) const;
+ TCHAR* const getButtonName( int idx ) const;
+ int getButtonType( int idx ) const;
+ bool isButtonDown( int idx ) const;
+
+ //
+ // Directional methods
+ //
+ bool isDirectionalAvailable( int idx ) const;
+ TCHAR* const getDirectionalName( int idx ) const;
+ int getDirection( int idx ) const;
+
+private://-----------------------------------------------------------------------------------------
+ LPDIRECTINPUTDEVICE8 mpJoystick;
+
+ DIDEVICEINSTANCE mdiDevInfo;
+ DIDEVCAPS mdiDevCaps;
+ DIJOYSTATE2 mJS; // DInput joystick state
+
+ int mSliderCount;
+ int mPOVCount;
+ int mButtonCount;
+
+ double getAxisValueHelper( LONG val, int idx ) const;
+
+ HRESULT SwitchAutoCenter( bool onoff = true );
+
+ HRESULT InitDirectInput( HWND hWnd = NULL );
+ HRESULT FreeDirectInput();
+ HRESULT UpdateInputState();
+
+
+ static BOOL CALLBACK EnumAxesCallback
+ (
+ const DIDEVICEOBJECTINSTANCE* pdidoi,
+ VOID* pContext
+ );
+
+ static BOOL CALLBACK EnumButtonsCallback
+ (
+ const DIDEVICEOBJECTINSTANCE* pdidoi,
+ VOID* pContext
+ );
+
+ static BOOL CALLBACK EnumPOVsCallback
+ (
+ const DIDEVICEOBJECTINSTANCE* pdidoi,
+ VOID* pContext
+ );
+
+ static BOOL CALLBACK EnumEffectsCallback
+ (
+ const DIEFFECTINFO* pdidoi,
+ VOID* pContext
+ );
+
+
+ class JXINPUT_API AxisConfig
+ {
+
+ public:
+ bool mIsAvailable;
+ CHAR mName[MAX_PATH];
+ AXISTYPE mType;
+ LONG mMinValue;
+ LONG mMaxValue;
+ double (JXInput::*mGetValueMethod)() const;
+
+ } mAxisConfig [ JXINPUT_MAX_AXES ];
+
+ void initAxisConfig();
+
+
+ class JXINPUT_API ButtonConfig
+ {
+
+ public:
+ bool mIsAvailable;
+ CHAR mName[MAX_PATH];
+ BUTTONTYPE mType;
+
+ } mButtonConfig[ JXINPUT_MAX_BUTTONS ];
+
+ void initButtonsConfig();
+
+
+ class JXINPUT_API DirectionalConfig
+ {
+
+ public:
+ bool mIsAvailable;
+ CHAR mName[MAX_PATH];
+
+ } mDirectionalConfig[ JXINPUT_MAX_DIRECTIONALS ];
+
+ void initDirectionalsConfig();
+};
+
diff --git a/win32/jxinput.sln b/win32/jxinput.sln
new file mode 100644
index 0000000..714fdc7
--- /dev/null
+++ b/win32/jxinput.sln
@@ -0,0 +1,20 @@
+
+Microsoft Visual Studio Solution File, Format Version 9.00
+# Visual C++ Express 2005
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "jxinput", "jxinput.vcproj", "{8AEA84DC-D8F0-4425-BEBF-A84E91115F76}"
+EndProject
+Global
+ GlobalSection(SolutionConfigurationPlatforms) = preSolution
+ Debug|Win32 = Debug|Win32
+ Release|Win32 = Release|Win32
+ EndGlobalSection
+ GlobalSection(ProjectConfigurationPlatforms) = postSolution
+ {8AEA84DC-D8F0-4425-BEBF-A84E91115F76}.Debug|Win32.ActiveCfg = Debug|Win32
+ {8AEA84DC-D8F0-4425-BEBF-A84E91115F76}.Debug|Win32.Build.0 = Debug|Win32
+ {8AEA84DC-D8F0-4425-BEBF-A84E91115F76}.Release|Win32.ActiveCfg = Release|Win32
+ {8AEA84DC-D8F0-4425-BEBF-A84E91115F76}.Release|Win32.Build.0 = Release|Win32
+ EndGlobalSection
+ GlobalSection(SolutionProperties) = preSolution
+ HideSolutionNode = FALSE
+ EndGlobalSection
+EndGlobal
diff --git a/win32/jxinput.vcproj b/win32/jxinput.vcproj
new file mode 100644
index 0000000..c87fc0f
--- /dev/null
+++ b/win32/jxinput.vcproj
@@ -0,0 +1,367 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/www/.cvsignore b/www/.cvsignore
new file mode 100644
index 0000000..a46c908
--- /dev/null
+++ b/www/.cvsignore
@@ -0,0 +1,5 @@
+.nbattrs
+*~
+javadoc
+
+
diff --git a/www/hardcode.gif b/www/hardcode.gif
new file mode 100644
index 0000000..de640ec
Binary files /dev/null and b/www/hardcode.gif differ
diff --git a/www/images/dl-javawebstart3.jpg b/www/images/dl-javawebstart3.jpg
new file mode 100644
index 0000000..2c1420d
Binary files /dev/null and b/www/images/dl-javawebstart3.jpg differ
diff --git a/www/images/download-button.gif b/www/images/download-button.gif
new file mode 100644
index 0000000..b815543
Binary files /dev/null and b/www/images/download-button.gif differ
diff --git a/www/images/download.j2se14.gif b/www/images/download.j2se14.gif
new file mode 100644
index 0000000..cf0bad6
Binary files /dev/null and b/www/images/download.j2se14.gif differ
diff --git a/www/images/downloadj3d.gif b/www/images/downloadj3d.gif
new file mode 100644
index 0000000..4e0536a
Binary files /dev/null and b/www/images/downloadj3d.gif differ
diff --git a/www/images/footpedal-pic.gif b/www/images/footpedal-pic.gif
new file mode 100644
index 0000000..e627bf7
Binary files /dev/null and b/www/images/footpedal-pic.gif differ
diff --git a/www/images/getjavanow.gif b/www/images/getjavanow.gif
new file mode 100644
index 0000000..bbf6f3e
Binary files /dev/null and b/www/images/getjavanow.gif differ
diff --git a/www/images/jxinput_architecture.gif b/www/images/jxinput_architecture.gif
new file mode 100644
index 0000000..60a19c1
Binary files /dev/null and b/www/images/jxinput_architecture.gif differ
diff --git a/www/index.htm b/www/index.htm
new file mode 100644
index 0000000..d1734ed
--- /dev/null
+++ b/www/index.htm
@@ -0,0 +1,18 @@
+
+
+
+
+
+
+
+
+JXInput - Gaming Input Devices (joystick/gamepad/DirectInput) for Java
+
+
+
+
+
+
\ No newline at end of file
diff --git a/www/jxlinks.htm b/www/jxlinks.htm
new file mode 100644
index 0000000..37325ad
--- /dev/null
+++ b/www/jxlinks.htm
@@ -0,0 +1,53 @@
+
+
+
+
+
+
+
+
+JXLinks - Gaming Input Devices (joystick/gamepad/DirectInput) for Java
+
+
+
+
+
+
+
+Links
+
+
+
+
+
Other input devices with Java
+
+
+
+Java related links
+
+
+
+
+
+
+
diff --git a/www/jxversion.htm b/www/jxversion.htm
new file mode 100644
index 0000000..bedeca4
--- /dev/null
+++ b/www/jxversion.htm
@@ -0,0 +1,98 @@
+
+
+
+
+
+
+
+
+
+Version - Gaming Input Devices (joystick/gamepad/DirectInput) for Java
+
+
+
+
+
+
+Version
+
+The current version of the package is V0.3.3.
+
+How are the versions counted?
+
+The goal of the development is version V1.0. V1.0 means the whole thing is
+feature-complete, tested, documented. Additionally some people should have agreed
+that the design is useful.
+
+Meanwhile, the version number will increase in the first decimal whenever a
+significant change in one of the interfaces occured or a new features is added.
+For minor changes like bugfixes, non-code-breaking enhancements or additional
+documentation, the second decimal will be counted.
+
+A new version will be released as soon as it is implemented. That means that
+versions like 0.X.0 may lack of samples or documentation.
+
+
+
History
+
+V0.3:
+
+
+ - JXInput gives access to the Swing keyboard interpreted as buttons.
+
- 'Virtual' axes can be emulated with the help of buttons (e.g. from the keyboard).
+
+
+V0.3.1:
+
+
+ JXInputManager#createKeyboardDevice() needs only Component
+ instead of JComponent.
+ - Online demo with WebStart .
+
- Bugfixes.
+
- Improved documentation.
+
+
+V0.3.2:
+
+
+ - Bugfix: Z-axis now works correctly.
+
+
+V0.3.3:
+
+
+ - Introduced overall reset()-method that allows to changes devices at
+runtime.
+
- The type of virtual axes (TRANSLATIONAL, ROTATIONAL, SLIDER) can be set explicitely.
+
- Success story: JXInput used in space.
+
+
+
+V0.2:
+
+
+- Support of DirectX8.
+
+- Support of multiple devices.
+
+- Introduced eventing system (de.hardcode.jxinput.event).
+
+- Support of Java3D sensoring interface (de.hardcode.jxinput.j3d).
+
+
+
+V0.1:
+
+
+- First attempts with DirectInput and JNI.
+
+- Setup of project structure.
+
+- Setup of project structure.
+
+- Tests with WebStart.
+
+
+
+
+
diff --git a/www/leftmenu.htm b/www/leftmenu.htm
new file mode 100644
index 0000000..4ec8bb7
--- /dev/null
+++ b/www/leftmenu.htm
@@ -0,0 +1,33 @@
+
+
+
+
+
+
+
+
+Menu - Gaming Input Devices (joystick/gamepad/DirectInput) for Java
+
+
+
+
+
+About JXInput
+
+Version
+
+Documentation
+
+Contact
+
+Download
+
+Links
+
+Test Online!
+
+
+
+
+
+