Created
April 17, 2016 05:11
-
-
Save ThomasGaubert/1035973df8a4802525a25dcaefbb5b0d to your computer and use it in GitHub Desktop.
SteamVR Controller Experiments
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package jmevr; | |
import com.jme3.scene.Geometry; | |
import jmevr.input.VRInput; | |
public class DefaultInput implements Input { | |
public InputMode getInputMode() { | |
return InputMode.DEFAULT; | |
} | |
public void handleInput(int controllerIndex, Geometry geo) { | |
if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveTriggerAxis)) { | |
System.out.println("Trigger"); | |
} | |
if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveGripButton)) { | |
System.out.println("Grip"); | |
} | |
if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveTouchpadAxis)) { | |
System.out.println("Touchpad"); | |
} | |
} | |
public void printHelp() { | |
System.out.println("Default Input"); | |
System.out.println("Press buttons to see name. Press menu button to switch input mode."); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package jmevr; | |
import com.jme3.scene.Geometry; | |
interface Input { | |
public abstract InputMode getInputMode(); | |
public abstract void handleInput(int controllerIndex, Geometry geo); | |
public abstract void printHelp(); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package jmevr; | |
public enum InputMode { | |
DEFAULT(new DefaultInput()), | |
JOYSTICK(new JoystickInput()), | |
JOYSTICK_INVERTED(new InvertedJoystickInput()), | |
TRACKING_TEST(new TrackingTestInput()); | |
private Input input; | |
InputMode(Input input) { | |
this.input = input; | |
} | |
public Input getInput() { | |
return input; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package jmevr; | |
import com.jme3.math.Vector3f; | |
import com.jme3.scene.Geometry; | |
import jmevr.input.VRInput; | |
import jopenvr.VRControllerAxis_t; | |
import java.awt.*; | |
import java.awt.event.InputEvent; | |
public class InvertedJoystickInput implements Input { | |
public InputMode getInputMode() { | |
return InputMode.JOYSTICK_INVERTED; | |
} | |
public void handleInput(int controllerIndex, Geometry geo) { | |
// vibrate when holding down trigger | |
if( VRInput.getAxis(controllerIndex, VRInput.VRINPUT_TYPE.ViveTriggerAxis).x >= 1f) { | |
VRInput.triggerHapticPulse(controllerIndex, 0.5f); | |
} | |
// Vibrate if moving fast | |
Vector3f vel = VRInput.getVelocity(controllerIndex); | |
if(vel.getX() > 1 || vel.getY() > 1 || vel.getZ() > 1) { | |
VRInput.triggerHapticPulse(controllerIndex, 0.5f); | |
} | |
VRControllerAxis_t cs = VRInput.getRawControllerState(controllerIndex).rAxis[0]; | |
float padX = cs.x; | |
float padY = cs.y; | |
double distFromOrigin = Math.sqrt(((0 - cs.x) * (0 - cs.x)) + ((0 - cs.y) * (0 - cs.y))); | |
VRInput.triggerHapticPulse(controllerIndex, (float) distFromOrigin / 4); | |
try { | |
Robot robot = new Robot(); | |
if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveTriggerAxis)) { | |
robot.mousePress(InputEvent.BUTTON1_MASK); | |
robot.mouseRelease(InputEvent.BUTTON1_MASK); | |
} else if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveGripButton)) { | |
robot.mousePress(InputEvent.BUTTON3_MASK); | |
robot.mouseRelease(InputEvent.BUTTON3_MASK); | |
} else { | |
PointerInfo a = MouseInfo.getPointerInfo(); | |
Point mousePos = a.getLocation(); | |
if(distFromOrigin > 0) { | |
robot.mouseMove((int) (mousePos.getX() + 5 * padX), (int) (mousePos.getY() + 5 * padY)); | |
} | |
} | |
} catch (Exception e) { | |
e.printStackTrace(); | |
} | |
} | |
public void printHelp() { | |
System.out.println("Inverted Joystick Input"); | |
System.out.println("Use touchpad to move mouse like a joystick. y-axis is inverted."); | |
System.out.println("Trigger - left click"); | |
System.out.println("Grip - right click"); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package jmevr; | |
import com.jme3.math.Vector3f; | |
import com.jme3.scene.Geometry; | |
import jmevr.input.VRInput; | |
import jopenvr.VRControllerAxis_t; | |
import java.awt.*; | |
import java.awt.event.InputEvent; | |
public class JoystickInput implements Input { | |
public InputMode getInputMode() { | |
return InputMode.JOYSTICK; | |
} | |
public void handleInput(int controllerIndex, Geometry geo) { | |
// vibrate when holding down trigger | |
if( VRInput.getAxis(controllerIndex, VRInput.VRINPUT_TYPE.ViveTriggerAxis).x >= 1f) { | |
VRInput.triggerHapticPulse(controllerIndex, 0.5f); | |
} | |
// Vibrate if moving fast | |
Vector3f vel = VRInput.getVelocity(controllerIndex); | |
if(vel.getX() > 1 || vel.getY() > 1 || vel.getZ() > 1) { | |
VRInput.triggerHapticPulse(controllerIndex, 0.5f); | |
} | |
VRControllerAxis_t cs = VRInput.getRawControllerState(controllerIndex).rAxis[0]; | |
float padX = cs.x; | |
float padY = cs.y; | |
double distFromOrigin = Math.sqrt(((0 - cs.x) * (0 - cs.x)) + ((0 - cs.y) * (0 - cs.y))); | |
VRInput.triggerHapticPulse(controllerIndex, (float) distFromOrigin / 4); | |
try { | |
Robot robot = new Robot(); | |
if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveTriggerAxis)) { | |
robot.mousePress(InputEvent.BUTTON1_MASK); | |
robot.mouseRelease(InputEvent.BUTTON1_MASK); | |
} else if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveGripButton)) { | |
robot.mousePress(InputEvent.BUTTON3_MASK); | |
robot.mouseRelease(InputEvent.BUTTON3_MASK); | |
} else { | |
PointerInfo a = MouseInfo.getPointerInfo(); | |
Point mousePos = a.getLocation(); | |
if(distFromOrigin > 0) { | |
robot.mouseMove((int) (mousePos.getX() + 5 * padX), (int) (mousePos.getY() + 5 * -padY)); | |
} | |
} | |
} catch (Exception e) { | |
e.printStackTrace(); | |
} | |
} | |
public void printHelp() { | |
System.out.println("Joystick Input"); | |
System.out.println("Use touchpad to move mouse like a joystick."); | |
System.out.println("Trigger - left click"); | |
System.out.println("Grip - right click"); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
VR Instancing Progress: | |
- igByGeom gets huge, and updateInstances still happens on it, | |
even if the associated geometry is no longer in the scene | |
- track which InstanceGeometry to add or remove inside the Geometry? | |
- have list of instances to render maintained somewhere else? | |
*/ | |
package jmevr; | |
import com.jme3.material.Material; | |
import com.jme3.math.Quaternion; | |
import com.jme3.math.Vector3f; | |
import com.jme3.scene.Geometry; | |
import com.jme3.scene.Node; | |
import com.jme3.scene.Spatial; | |
import com.jme3.scene.Spatial.CullHint; | |
import com.jogamp.newt.Display; | |
import jmevr.app.VRApplication; | |
import jmevr.input.VRInput; | |
import jmevr.input.VRInput.VRINPUT_TYPE; | |
public class TestOpenVR extends VRApplication { | |
private static InputMode[] inputModes = {InputMode.DEFAULT, InputMode.JOYSTICK}; | |
private static int inputMode = 0; | |
private static boolean seenController = false; | |
// set some VR settings & start the app | |
public static void main(String[] args){ | |
TestOpenVR test = new TestOpenVR(); | |
//test.preconfigureVRApp(PRECONFIG_PARAMETER.USE_STEAMVR_COMPOSITOR, false); // disable the SteamVR compositor (kinda needed at the moment) | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.USE_CUSTOM_DISTORTION, false); // use full screen distortion, maximum FOV, possibly quicker (not compatible with instancing) | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.ENABLE_MIRROR_WINDOW, true); // runs faster when set to false, but will allow mirroring | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.FORCE_VR_MODE, false); // render two eyes, regardless of SteamVR | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.SET_GUI_CURVED_SURFACE, true); | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.FLIP_EYES, false); | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.SET_GUI_OVERDRAW, true); // show gui even if it is behind things | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.INSTANCE_VR_RENDERING, true); // faster VR rendering, requires some vertex shader changes (see jmevr/shaders/Unshaded.j3md) | |
test.preconfigureVRApp(PRECONFIG_PARAMETER.NO_GUI, true); | |
test.preconfigureFrustrumNearFar(0.1f, 512f); // set frustum distances here before app starts | |
//test.preconfigureResolutionMultiplier(0.666f); // you can downsample for performance reasons | |
test.start(); | |
} | |
// general objects for scene management | |
Spatial observer; | |
Material mat; | |
Geometry leftHand, rightHand; | |
@Override | |
public void simpleInitApp() { | |
initTestScene(); | |
if(VRApplication.getVRHardware() != null) { | |
System.out.println("Attached device: " + VRApplication.getVRHardware().getType()); | |
} | |
} | |
private void initTestScene(){ | |
observer = new Node("observer"); | |
// Setup controllers | |
leftHand = (Geometry)getAssetManager().loadModel("Models/vive_controller.j3o"); | |
rightHand = leftHand.clone(); | |
Material handMat = new Material(getAssetManager(), "Common/MatDefs/Misc/Unshaded.j3md"); | |
handMat.setTexture("ColorMap", getAssetManager().loadTexture("Textures/vive_controller.png")); | |
leftHand.setMaterial(handMat); | |
rightHand.setMaterial(handMat); | |
rootNode.attachChild(rightHand); | |
rootNode.attachChild(leftHand); | |
observer.setLocalTranslation(new Vector3f(0.0f, 0.0f, 0.0f)); | |
//VRApplication.setObserver(observer); | |
//rootNode.attachChild(observer); | |
getInputManager().setCursorVisible(true); | |
} | |
@Override | |
public void simpleUpdate(float tpf){ | |
if(VRInput.isInputDeviceTracking(0) && !seenController) { | |
seenController = true; | |
System.out.println("=============================================="); | |
System.out.println("Input mode: " + inputModes[inputMode]); | |
inputModes[inputMode].getInput().printHelp(); | |
System.out.println("=============================================="); | |
} else if(!VRInput.isInputDeviceTracking(0)) { | |
seenController = false; | |
} | |
handleWandInput(0, leftHand); | |
handleWandInput(1, rightHand); | |
} | |
private void handleWandInput(int index, Geometry geo) { | |
Quaternion q = VRInput.getFinalObserverRotation(index); | |
Vector3f v = VRInput.getFinalObserverPosition(index); | |
if( q != null && v != null ) { | |
geo.setCullHint(CullHint.Dynamic); // make sure we see it | |
geo.setLocalTranslation(v); | |
geo.setLocalRotation(q); | |
// Handle switching input modes | |
if(VRInput.isButtonDown(index, VRINPUT_TYPE.ViveThumbButton)) { | |
VRInput.triggerHapticPulse(index, 0.7f); | |
try { | |
Thread.sleep(200); | |
} catch (Exception e) { | |
e.printStackTrace(); | |
} | |
VRInput.triggerHapticPulse(index, 0.7f); | |
if(inputMode == inputModes.length - 1) { | |
inputMode = 0; | |
try { | |
Thread.sleep(200); | |
} catch (Exception e) { | |
e.printStackTrace(); | |
} | |
VRInput.triggerHapticPulse(index, 0.7f); | |
} else { | |
inputMode++; | |
} | |
System.out.println("=============================================="); | |
System.out.println("Input mode now: " + inputModes[inputMode]); | |
inputModes[inputMode].getInput().printHelp(); | |
System.out.println("=============================================="); | |
} | |
inputModes[inputMode].getInput().handleInput(index, geo); | |
} else { | |
geo.setCullHint(CullHint.Always); // hide it | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package jmevr; | |
import com.jme3.math.Vector3f; | |
import com.jme3.scene.Geometry; | |
import jmevr.input.VRInput; | |
public class TrackingTestInput implements Input { | |
private Vector3f[] screen = new Vector3f[4]; | |
private int screenPos = 0; | |
private int count; | |
private float xRunning, yRunning, zRunning; | |
public InputMode getInputMode() { | |
return InputMode.TRACKING_TEST; | |
} | |
public void handleInput(int controllerIndex, Geometry geo) { | |
if(VRInput.isButtonDown(controllerIndex, VRInput.VRINPUT_TYPE.ViveGripButton)) { | |
System.out.println(geo.getLocalTranslation()); | |
xRunning += geo.getLocalTranslation().getX(); | |
yRunning += geo.getLocalTranslation().getY(); | |
zRunning += geo.getLocalTranslation().getZ(); | |
count++; | |
} else { | |
if(count > 0) { | |
System.out.println("After " + count + " iterations, averages are:"); | |
System.out.println("x: " + xRunning / count); | |
System.out.println("y: " + yRunning / count); | |
System.out.println("z: " + zRunning / count); | |
screen[screenPos] = new Vector3f(xRunning / count, yRunning / count, zRunning / count); | |
if(screenPos < screen.length - 1) { | |
screenPos++; | |
} else { | |
screenPos = 0; | |
System.out.println("Screen set! Retrain to set new screen..."); | |
for(int x = 0; x < screen.length; x++) { | |
System.out.println(screen[x]); | |
} | |
} | |
count = 0; | |
xRunning = yRunning = zRunning = 0; | |
} | |
} | |
} | |
public void printHelp() { | |
System.out.println("Tracking Test Input"); | |
System.out.println("Move the controller to see tracking information."); | |
System.out.println("You may need to hold menu button to switch input modes."); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment