Ccculus rift hardware cardboard replacement?

I ran across this link from google.

Note I haven’t looked at docs yet but seems like something that might be useful for they guys who want to test VR with Jmonkey.

I believe you guys have already figured out how to do the lens distortion part so all that would be needed would be the accelerometer code.

-Greg

O.o

Cool!

A friend of mine was at Google IO and got one. I tested it with and it’s really impressive for a card board VR device :stuck_out_tongue:
That can give you head aches pretty fast though :stuck_out_tongue:

Everybody’s talking about VR here and VR there, then these guys show up and build one out of cardboard haha.

1 Like

I have a cardboard and now tested JME on it. First I thought I have to port the Oculus rift code to get the stereo view but first I tried it with a very simple “2 synchronized cameras” app state which I now can switch on and off whenever the cardboard is detected by the magnometer of the device :slight_smile: Works fine so far, even with the 3d effect, here is the first version of the “stereo view app state”. I still have problems with the GUI cameras, I cant set the aspect ration of the GUI camera so I deactivated stereo GUI for now, perhaps someone of you has an idea about it:

[java]

public class AS_StereoCamSyncer extends AbstractAppState {

private static final String RIGHT_GUI_VIEW = "Right Gui";
private static final String RIGHT_EYE_VIEW = "RightEye";
private Camera left;
private Camera right;
private final RenderManager renderManager;
private final ViewPort guiViewPort;
private final Node rootNode;
private boolean use3d = true;
private float eyeDistance = 0.3f; // 30cm woot

/**
 * @param guiViewPort
 * @param renderManager
 * @param rootNode
 * @param guiNode
 * @param leftCam
 *            will be the main camera
 * @param rightCam
 *            will be controlled by the left camera
 */
public AS_StereoCamSyncer(RenderManager renderManager,
		ViewPort guiViewPort, Node rootNode, Camera leftCam) {
	left = leftCam;
	this.renderManager = renderManager;
	this.guiViewPort = guiViewPort;
	this.rootNode = rootNode;
}

public void setLeftCamera(Camera left) {
	this.left = left;
}

public void setUse3d(boolean use3d) {
	this.use3d = use3d;
}

public void setEyeDistance(float eyeDistance) {
	this.eyeDistance = eyeDistance;
}

@Override
public void stateAttached(AppStateManager stateManager) {
	right = left.clone();
	setupBothEyes(left, right);
}

@Override
public void stateDetached(AppStateManager stateManager) {
	setupOneEye(left);
}

@Override
public void update(float tpf) {
	super.update(tpf);
	right.setRotation(left.getRotation());
	if (use3d) {
		right.setLocation(left.getLocation().add(
				left.getLeft().normalize().multLocal(eyeDistance)));
	} else {
		right.setLocation(left.getLocation());
	}
}

private void setupOneEye(Camera cam1) {
	renderManager.removeMainView(RIGHT_EYE_VIEW);
	cam1.setViewPort(0f, 1f, 0f, 1f);
	JmeCameraController.updateAspectRatioOf(cam1);
	setupGuiOneEye(guiViewPort.getCamera());
}

private void setupBothEyes(Camera cam1, Camera cam2) {

	ViewPort view2 = renderManager.createMainView(RIGHT_EYE_VIEW, cam2);
	view2.setClearFlags(true, true, true);
	view2.attachScene(rootNode);

	cam1.setViewPort(0f, 0.5f, 0f, 1f);
	cam2.setViewPort(.5f, 1f, 0f, 1f);

	// now the viewport is only half of its normal size for both cameras so
	// update the aspect ratio:
	updateAspectRatioOf(cam1);
	updateAspectRatioOf(cam2);
	// setupGuiBothEyes(guiViewPort.getCamera());
}

/**
 * returns the FovY of the passed camera, can be used for
 * {@link Camera#setFrustumPerspective(float, float, float, float)} e.g.
 * 
 * @param c
 * @return
 */
public static float getFovY(Camera c) {
	/*
	 * just do the following formula from
	 * Camera#setFrustumPerspective(float, float, float, float) backwards:
	 * 
	 * float h = FastMath.tan(fovY * FastMath.DEG_TO_RAD * .5f) * near;
	 */
	float fovY = FastMath.atan(c.getFrustumTop() / c.getFrustumNear())
			/ (FastMath.DEG_TO_RAD * .5f);
	return fovY;
}

/**
 * update the aspect ratio (and leave the rest of the parameters like they
 * are)
 * 
 * @param c
 */
public static void updateAspectRatioOf(Camera c) {
	c.setFrustumPerspective(getFovY(c), calcAspect(c), c.getFrustumNear(),
			c.getFrustumFar());
}

public static float calcAspect(Camera c) {
	return (c.getWidth() * (c.getViewPortRight() - c.getViewPortLeft()))
			/ (c.getHeight() * (c.getViewPortTop() - c.getViewPortBottom()));
}

private void setupGuiOneEye(Camera guiCam1) {
	renderManager.removePostView(RIGHT_GUI_VIEW);
	guiCam1.setViewPort(0f, 1f, 0f, 1f);
}

/**
 * mirroring the GUI does not work currently, the nifty ui is not cloned for
 * both eyes and the aspect ratio of the gui camera is not correctly
 * adjusted
 * 
 * @param guiCam1
 */
@Deprecated
private void setupGuiBothEyes(Camera guiCam1) {
	Camera guiCam2 = guiCam1.clone();
	guiCam1.setViewPort(0f, 0.5f, 0f, 1f);
	guiCam2.setViewPort(.5f, 1f, 0f, 1f);
	ViewPort guiViewPort2 = renderManager.createPostView(RIGHT_GUI_VIEW,
			guiCam2);
	guiViewPort2.setClearFlags(false, false, false);
	JmeCameraController.updateAspectRatioOf(guiCam1);
	JmeCameraController.updateAspectRatioOf(guiCam2);

	for (Spatial s : guiViewPort.getScenes()) {
		Log.d("guiViewPort2 adding " + s);
		guiViewPort2.attachScene(s);
	}
	for (SceneProcessor p : guiViewPort.getProcessors()) {
		Log.d("guiViewPort2 adding " + p);
		guiViewPort2.addProcessor(p);
	}
}

}

[/java]

2 Likes

Pretty cool!!
I’m amazed by what google did with this cardboard thingy…

1 Like