OpenGL GLSL version of Pre-warp Shader?

Post Reply
eshan
One Eyed Hopeful
Posts: 30
Joined: Mon Jul 16, 2012 3:49 pm

OpenGL GLSL version of Pre-warp Shader?

Post by eshan »

The Rift SDK contains a DirectX shader that performs the barrel distortion necessary for the Rift. Has anyone converted this to OpenGL GLSL? I want to try using it in Blender Game Engine, as per my other thread. Thanks!

shakesoda
One Eyed Hopeful
Posts: 28
Joined: Mon Sep 24, 2012 11:46 am
Which stereoscopic 3D solution do you primarily use?: Head Mounted Display (HMD)

Re: OpenGL GLSL version of Pre-warp Shader?

Post by shakesoda »

Note: I haven't tested this, so it might contain a minor error or two. I think BGE uses GLSL 1.20, so I wrote it accordingly. Make sure your vertex shader passes oTexCoord as a vec2.

I'm a little unsure about the if(clamp(...) > 0.0) line in main, but it should be functionally the same as HLSL's any(). Other than that, it's just a straight conversion.

Code: Select all

#version 120

uniform sampler2D Texture;
uniform vec2 LensCenter;
uniform vec2 ScreenCenter;
uniform vec2 Scale;
uniform vec2 ScaleIn;
uniform vec4 HmdWarpParam;

varying vec2 oTexCoord;

// Scales input texture coordinates for distortion.
vec2 HmdWarp(vec2 in01)
{
	vec2 theta = (in01 - LensCenter) * ScaleIn; // Scales to [-1, 1]
	float rSq = theta.x * theta.x + theta.y * theta.y;
	vec2 rvector = theta * (HmdWarpParam.x + HmdWarpParam.y * rSq +
		HmdWarpParam.z * rSq * rSq +
		HmdWarpParam.w * rSq * rSq * rSq);
	return LensCenter + Scale * rvector;
}

void main()
{
	vec2 tc = HmdWarp(oTexCoord);
	if (any(bvec2(clamp(tc,ScreenCenter-vec2(0.25,0.5), ScreenCenter+vec2(0.25,0.5)) - tc)))
	{
		gl_FragColor = vec4(vec3(0.0), 1.0);
		return;
	}

	gl_FragColor = texture2D(Texture, tc);
}
edit: fixed blatant typo
edit 2: thanks ben!
Last edited by shakesoda on Tue Apr 09, 2013 11:58 pm, edited 1 time in total.

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

If that clamp line doesn't work, this one should.

Code: Select all

if (any(bvec2(clamp(tc,ScreenCenter-vec2(0.25,0.5), ScreenCenter+vec2(0.25,0.5)) - tc)))

eshan
One Eyed Hopeful
Posts: 30
Joined: Mon Jul 16, 2012 3:49 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by eshan »

Thank you both! The original clamp line threw an error, but the substitute offered by Ben did not.

Now I just need to figure out all the stuff I need to supply at the top! :)

jedthehumanoid
One Eyed Hopeful
Posts: 3
Joined: Tue Apr 09, 2013 11:33 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by jedthehumanoid »

Awesome! I was just tinkering with BGE and GLSL yesterday trying to get the distortion to work, unsuccessfully.

shakesoda
One Eyed Hopeful
Posts: 28
Joined: Mon Sep 24, 2012 11:46 am
Which stereoscopic 3D solution do you primarily use?: Head Mounted Display (HMD)

Re: OpenGL GLSL version of Pre-warp Shader?

Post by shakesoda »

edited post with Ben's line. thanks!

User avatar
TheHolyChicken
Diamond Eyed Freakazoid!
Posts: 733
Joined: Thu Oct 18, 2012 3:34 am
Which stereoscopic 3D solution do you primarily use?: LCD shutter glasses
Location: Brighton, UK
Contact:

Re: OpenGL GLSL version of Pre-warp Shader?

Post by TheHolyChicken »

Thanks very much for this - this may prove to be very handy...
Sometimes I sits and thinks, and sometimes I just sits.

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

eshan wrote:Now I just need to figure out all the stuff I need to supply at the top! :)
I've just been using the default values from the Tuscany demo. If you're not worried about calculating everything based on different IPDs and panel sizes yet then these values should be fine.

Code: Select all

// left
vec2 LensCenter		= vec2(0.2863248, 0.5);
vec2 ScreenCenter	= vec2(0.25, 0.5);
vec2 Scale			= vec2(0.1469278, 0.2350845);
vec2 ScaleIn		= vec2(4, 2.5);
vec4 HmdWarpParam	= vec4(1, 0.22, 0.24, 0);

// right
vec2 LensCenter		= vec2(0.7136753, 0.5);
vec2 ScreenCenter	= vec2(0.75, 0.5);

eshan
One Eyed Hopeful
Posts: 30
Joined: Mon Jul 16, 2012 3:49 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by eshan »

Jed, any luck with the distortion in Blender?

Ben and Shakesoda, not sure if you guys know anything about Blender specifically, but this shader is not working "out of the box", probably due to me not passing something in correctly. I do have Blender sample BlueSepia filter pasted in and working, which is is just:

Code: Select all

uniform sampler2D bgl_RenderedTexture;
void main(void)
{
  vec4 texcolor = texture2D(bgl_RenderedTexture, gl_TexCoord[0].st);
  float gray = dot(texcolor.rgb, vec3(0.299, 0.587, 0.114));
  gl_FragColor = vec4(gray * vec3(0.8, 1.0, 1.2), texcolor.a);
}
Should I be substituting oTexCoord in the distortion shader with something like gl_TexCoord[0]?

I may have to take this shader over to a Blender specific forum.

fredrik
One Eyed Hopeful
Posts: 5
Joined: Fri Jun 08, 2012 5:45 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by fredrik »

The 2D filters in BGE does not work correctly with side-by-side stereo. I have tried Blender versions 2.64, 2.65, and 2.66, and none of them handles this correctly. You need to patch RAS_2DFilterManager::RenderFilters yourself to add a scissor rectangle around the viewport you are rendering for, and then recompile Blender.

Also, I noticed that BGE uses glCopyTexImage2D to copy the framebuffer content into a texture before each render pass. This is not the fastest way to do post-processing effects, but at Rift resolution, it seems fast enough. Using glBlitFramebufferEXT or rendering directly into an FBO would probably be a more efficient way to handle this.

eshan
One Eyed Hopeful
Posts: 30
Joined: Mon Jul 16, 2012 3:49 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by eshan »

fredrik,

I actually never got the stereo camera working. I currently have two cameras Parented, each with a viewport taking half the screen. In this configuration, do you seen any issues using the distortion shader? If not, any tips on getting it working? :)

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

I have no Blender experience, but if there's a built in post-process thing then it won't be passing the oTexCoord attribute through from the vertex stage, so you'll need to completely remove the 'varying' line towards the top and change the other oTexCoord to gl_TexCoord[0].st as you suspected.

I also just realized you're the guy who did the Hydra video with the evil monkey that I stumbled upon while experimenting with input methods last year. Small world. :D

fredrik
One Eyed Hopeful
Posts: 5
Joined: Fri Jun 08, 2012 5:45 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by fredrik »

eshan wrote:fredrik,

I actually never got the stereo camera working. I currently have two cameras Parented, each with a viewport taking half the screen. In this configuration, do you seen any issues using the distortion shader? If not, any tips on getting it working? :)
I have not found a way to pass uniforms to 2D filter shaders, so they need to be replaced with const variables. Also, the built-in gl_TexCoord[0] variable should be used. The following shader should work, provided you apply it per frame.

Code: Select all

#version 120

uniform sampler2D bgl_RenderTexture;

const vec2 LeftLensCenter = vec2(0.2863248, 0.5);
const vec2 RightLensCenter = vec2(0.7136753, 0.5);
const vec2 LeftScreenCenter = vec2(0.25, 0.5);
const vec2 RightScreenCenter = vec2(0.75, 0.5);
const vec2 Scale = vec2(0.1469278, 0.2350845);
const vec2 ScaleIn = vec2(4, 2.5);
const vec4 HmdWarpParam = vec4(1, 0.22, 0.24, 0);

// Scales input texture coordinates for distortion.
vec2 HmdWarp(vec2 in01, vec2 LensCenter)
{
   vec2 theta = (in01 - LensCenter) * ScaleIn; // Scales to [-1, 1]
   float rSq = theta.x * theta.x + theta.y * theta.y;
   vec2 rvector = theta * (HmdWarpParam.x + HmdWarpParam.y * rSq +
      HmdWarpParam.z * rSq * rSq +
      HmdWarpParam.w * rSq * rSq * rSq);
   return LensCenter + Scale * rvector;
}

void main()
{
   // The following two variables need to be set per eye
   vec2 LensCenter = gl_FragCoord.x < 640 ? LeftLensCenter : RightLensCenter;
   vec2 ScreenCenter = gl_FragCoord.x < 640 ? LeftScreenCenter : RightScreenCenter;

   vec2 oTexCoord = gl_TexCoord[0].xy;
   //vec2 oTexCoord = (gl_FragCoord.xy + vec2(0.5, 0.5)) / vec2(1280, 800);  //Uncomment if using BGE's built-in stereo rendering

   vec2 tc = HmdWarp(oTexCoord, LensCenter);
   if (any(bvec2(clamp(tc,ScreenCenter-vec2(0.25,0.5), ScreenCenter+vec2(0.25,0.5)) - tc)))
   {
      gl_FragColor = vec4(vec3(0.0), 1.0);
      return;
   }

   //tc.x = gl_FragCoord.x < 640 ? (2.0 * tc.x) : (2.0 * (tc.x - 0.5));  //Uncomment if using BGE's built-in stereo rendering
   gl_FragColor = texture2D(bgl_RenderTexture, tc);
}
When using the built-in side-by-side stereo rendering mode, 2D filters are applied per eye. If anyone wants to use the code above with this mode, I have indicated the necessary changes you need to make.

eshan
One Eyed Hopeful
Posts: 30
Joined: Mon Jul 16, 2012 3:49 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by eshan »

Success! I am using fredrik's code unaltered with "custom" side by side, not the built in stereo camera.

Still more work to do, but this is progress. Thank you! :D
You do not have the required permissions to view the files attached to this post.

eshan
One Eyed Hopeful
Posts: 30
Joined: Mon Jul 16, 2012 3:49 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by eshan »

Ben wrote:I also just realized you're the guy who did the Hydra video with the evil monkey that I stumbled upon while experimenting with input methods last year. Small world. :D
Small world, indeed! I hope you found it interesting/amusing. With this recent progress, there may be more videos forthcoming!

druidsbane
Binocular Vision CONFIRMED!
Posts: 237
Joined: Thu Jun 07, 2012 8:40 am
Which stereoscopic 3D solution do you primarily use?: LCD shutter glasses
Location: New York
Contact:

Re: OpenGL GLSL version of Pre-warp Shader?

Post by druidsbane »

Edit: turns out the below optimization is wrong. And using dot(theta) produces the same performance as the original code. Oh well.

Quick tip. The current shader with the code I have is making my program run at half the speed on my MacBook Air but I was able to eke out an extra 6fps by changing this line:

Code: Select all

float rSq = theta.x * theta.x + theta.y * theta.y;
to

Code: Select all

float  rSq =  length(theta);
and adding at the top:

Code: Select all

#version 120

#define highp
Every little bit counts guys :)
Last edited by druidsbane on Mon Apr 15, 2013 5:35 am, edited 1 time in total.
Ibex 3D VR Desktop for the Oculus Rift: http://hwahba.com/ibex - https://bitbucket.org/druidsbane/ibex

User avatar
MrGreen
Diamond Eyed Freakazoid!
Posts: 741
Joined: Mon Sep 03, 2012 1:36 pm
Location: QC, Canada

Re: OpenGL GLSL version of Pre-warp Shader?

Post by MrGreen »

Out of context that code change doesn't make much sense to me but then again, most discussions here don't either. :lol:

druidsbane
Binocular Vision CONFIRMED!
Posts: 237
Joined: Thu Jun 07, 2012 8:40 am
Which stereoscopic 3D solution do you primarily use?: LCD shutter glasses
Location: New York
Contact:

Re: OpenGL GLSL version of Pre-warp Shader?

Post by druidsbane »

MrGreen wrote:Out of context that code change doesn't make much sense to me but then again, most discussions here don't either. :lol:
Adding context to my reply here ;) The line I changed basically uses the built-in length function in GLSL instead of calculating it manually. By doing this we have a chance to use some hardware optimization that may not be available if we just do the calculation manually as it is unlikely the GLSL compiler would catch that we could use the length function here.

Also, I found that:

Code: Select all

gl_FragColor = vec4(0.0, 0.0, 0.0, 1.0);
was faster than the above samples with:

Code: Select all

gl_FragColor = vec4(vec3(0.0), 1.0);
Ibex 3D VR Desktop for the Oculus Rift: http://hwahba.com/ibex - https://bitbucket.org/druidsbane/ibex

shakesoda
One Eyed Hopeful
Posts: 28
Joined: Mon Sep 24, 2012 11:46 am
Which stereoscopic 3D solution do you primarily use?: Head Mounted Display (HMD)

Re: OpenGL GLSL version of Pre-warp Shader?

Post by shakesoda »

druidsbane wrote:Quick tip. The current shader with the code I have is making my program run at half the speed on my MacBook Air but I was able to eke out an extra 6fps by changing this line:

Code: Select all

float rSq = theta.x * theta.x + theta.y * theta.y;
to

Code: Select all

float  rSq =  length(theta);
and adding at the top:
length(theta) is not functionally equivalent though.

for it to be functionally the same you'd have to do pow(length(theta), 2). I personally saw no performance difference when switching these lines to different things (using an nvidia gt 330 + 313.30 drivers on linux). precision highp is the default in glsl, too, so I wonder what's going on.

as for expanding the vec4 initialization, I find it a little hard to believe there's a compiler that might not expand that by itself.

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

The poor speed is probably because the shader's recalculating the distortion every frame. Do it once and write it to a GL_RG32F framebuffer, then just sample that instead.

druidsbane
Binocular Vision CONFIRMED!
Posts: 237
Joined: Thu Jun 07, 2012 8:40 am
Which stereoscopic 3D solution do you primarily use?: LCD shutter glasses
Location: New York
Contact:

Re: OpenGL GLSL version of Pre-warp Shader?

Post by druidsbane »

shakesoda wrote: length(theta) is not functionally equivalent though.

for it to be functionally the same you'd have to do pow(length(theta), 2). I personally saw no performance difference when switching these lines to different things (using an nvidia gt 330 + 313.30 drivers on linux). precision highp is the default in glsl, too, so I wonder what's going on.

as for expanding the vec4 initialization, I find it a little hard to believe there's a compiler that might not expand that by itself.
I think the glsl version on the Mac is a bit old and not very optimized. You're right about length(theta) being wrong though from the docs they didn't mention they were taking the square root which is what one would have expected from length (http://www.opengl.org/sdk/docs/manglsl/xhtml/length.xml, maybe my browser isn't rendering some math characters right :( as I just see blanks where the math symbols should be). Switching to dot(theta,theta) yielded the same performance as the unrolling in the code above. Also, in terms of performance differences, my code is now running at 30fps so any small change can have an effect it would seem :)

Either way I think the final goal is to use Ben's suggestion below and just cache the calculations whenever the distortion parameters change.
Ibex 3D VR Desktop for the Oculus Rift: http://hwahba.com/ibex - https://bitbucket.org/druidsbane/ibex

geekmaster
Petrif-Eyed
Posts: 2708
Joined: Sat Sep 01, 2012 10:47 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by geekmaster »

Try optimizing your shader offline:
https://github.com/aras-p/glsl-optimizer

Kajos
Cross Eyed!
Posts: 117
Joined: Sun Aug 05, 2012 4:19 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Kajos »

What lens variables do I need if I want to do build a shader without a sbs input? Namely, I have two generated textures accessed in the shader and want to apply distortion seperately. I get stuck on the scale and lens variables and I'm too afraid to mess with them.

I figure it's something in the lines of this:

Code: Select all

// left
vec2 leftLensCenter      = vec2(0.2863248 * 2.0, 0.5);
vec2 Scale         = vec2(0.1469278, 0.2350845);
vec2 ScaleIn      = vec2(2.5, 2.5);
vec4 HmdWarpParam   = vec4(1, 0.22, 0.24, 0);

// right
vec2 rightLensCenter      = vec2((0.7136753 - 0.5) * 2.0, 0.5);

vec2 screenCenter   = vec2(0.5, 0.5);
Image

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

I'm not positive, but I think the scale values should be:

Code: Select all

vec2 Scale	= vec2(0.2938556, 0.2350845);
vec2 ScaleIn	= vec2(2, 2.5);
Everything else looks right, but I haven't actually tried it.

Edit: Actually I'm not sure I interpreted the question properly. Are you trying to apply the distortion to each eye in two separate shaders, or applying it to each eye individually within the same shader?

The scale values I've included above should work for a 640x800 texture which is being drawn to a 640x800 viewport, but if you're sampling the 640x800 textures for both eyes and drawing them to their respective halves of a 1280x800 viewport then you need to use the shader provided by shakesoda.

The SDK overview document from the developer center does a good job of explaining everything.

Kajos
Cross Eyed!
Posts: 117
Joined: Sun Aug 05, 2012 4:19 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Kajos »

Ben wrote:I'm not positive, but I think the scale values should be:

Code: Select all

vec2 Scale	= vec2(0.2938556, 0.2350845);
vec2 ScaleIn	= vec2(2, 2.5);
Everything else looks right, but I haven't actually tried it.

Edit: Actually I'm not sure I interpreted the question properly. Are you trying to apply the distortion to each eye in two separate shaders, or applying it to each eye individually within the same shader?

The scale values I've included above should work for a 640x800 texture which is being drawn to a 640x800 viewport, but if you're sampling the 640x800 textures for both eyes and drawing them to their respective halves of a 1280x800 viewport then you need to use the shader provided by shakesoda.

The SDK overview document from the developer center does a good job of explaining everything.
I'll post the shader for people convinience. In textures are variable, for Rift it's normally set to 640x800. Shader is applied on 1280x800 texture.

Code: Select all

uniform sampler2D passedTextureLeft;
uniform sampler2D passedTextureRight;
// left
float as = 1.0;
float w = 1.0;
float h = 1.0;
float scaleFactor = 1.0;

vec2 leftLensCenter      = vec2((w + 0.25 * 0.5)*0.5, h*0.5);
vec2 Scale         = vec2((w/2.0) * scaleFactor, (h/2.0) * scaleFactor * as);
vec2 ScaleIn      = vec2((1.6), (1.6) / as);
vec4 HmdWarpParam   = vec4(1, 0.22, 0.24, 0);

// right
vec2 rightLensCenter      = vec2((w + -0.25 * 0.5)*0.5, h*0.5);

vec2 screenCenter   = vec2(0.5, 0.5);

vec2 HmdWarp(vec2 in01, vec2 lensCenter)
{
   vec2 theta = (in01 - lensCenter) * ScaleIn; // Scales to [-1, 1]
   float rSq = theta.x * theta.x + theta.y * theta.y;
   vec2 rvector = theta * (HmdWarpParam.x + HmdWarpParam.y * rSq +
      HmdWarpParam.z * rSq * rSq +
      HmdWarpParam.w * rSq * rSq * rSq);
   return lensCenter + Scale * rvector;
}

// In the main; far too many if statements I know..

	       vec4 texcoord = gl_TexCoord[0];
		if (texcoord.x > 0.5) {
			texcoord.x -= 0.5;
		}
		texcoord.x *= 2.0; 

		if (gl_TexCoord[0].x > 0.5) {
			vec2 texcoord = HmdWarp(texcoord, rightLensCenter);
		    if (any(bvec2(clamp(texcoord,screenCenter-vec2(0.5,0.5), screenCenter+vec2(0.5,0.5)) - texcoord)))
		    {
				gl_FragColor = vec4(vec3(0.0), 1.0);
				return;
		    }
			vec3 Reye;
			
			Reye = switchEyes == 1 ? texture2D(passedTextureLeft, texcoord.xy).rgb : texture2D(passedTextureRight, texcoord.xy).rgb;
				
			gl_FragColor.rgb = Reye;
			gl_FragColor.a = 1.0;
			
			
		} else {
			vec2 texcoord = HmdWarp(texcoord, leftLensCenter);
		    if (any(bvec2(clamp(texcoord,screenCenter-vec2(0.5,0.5), screenCenter+vec2(0.5,0.5)) - texcoord)))
		    {
				gl_FragColor = vec4(vec3(0.0), 1.0);
				return;
		    }
			vec3 Leye;
			Leye = switchEyes == 1 ? texture2D(passedTextureRight, texcoord.xy).rgb : texture2D(passedTextureLeft, texcoord.xy).rgb;
				
			gl_FragColor.rgb = Leye;
			gl_FragColor.a = 1.0;
		}
Result for this version is seen in VRPaint Alpha topic.

shakesoda
One Eyed Hopeful
Posts: 28
Joined: Mon Sep 24, 2012 11:46 am
Which stereoscopic 3D solution do you primarily use?: Head Mounted Display (HMD)

Re: OpenGL GLSL version of Pre-warp Shader?

Post by shakesoda »

I've having a hard time getting this to converge. As far as I can tell, the issue is just that my images are offset. This seems kind of baffling when I'm using the exact same parameters as the SDK examples/defaults.

before warp:
Image

after warp:
Image

I'm using all the same parameters as the examples as far as I can tell. The relevant part of the rendering code is here: https://github.com/shakesoda/opengrind/ ... r.cpp#L242

Anyone have ideas?

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

Kajos, ah I understand now. The values you originally posted with the screenshot should work, but ScaleIn.x needs to remain at 4, I think. Sorry for the confusion.

shakesoda, I ran the unwarped image through my shader and got nearly identical results, so unless we're both doing the same things wrong I don't think that's the problem. I had a quick look at your code, and can't see anything obviously wrong with it either. Only thing I can think to suggest is printing the matrices out and comparing them to ones from something that works.

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

shakesoda, I took another look at your code, and I think this is the problem.

Try this instead:

Code: Select all

// Projection matrix for the "center eye", which the left/right matrices are based on.
glm::mat4 projCenter = glm::perspective<float>(yfov, aspectRatio, 0.3f, 1000.0f);

glm::mat4 projLeft(1.0);
projLeft[0][3] = projectionCenterOffset;
projLeft *= projCenter;

glm::mat4 projRight(1.0);
projRight[0][3] = -projectionCenterOffset;
projRight *= projCenter;

// View transformation translation in world units.
float halfIPD = hmd.InterpupillaryDistance * 0.5f;
glm::mat4 viewCenter(1.0);

glm::mat4 viewLeft(1.0);
viewLeft[0][3] = halfIPD;
viewLeft *= viewCenter;

glm::mat4 viewRight(1.0);
viewRight[0][3] = -halfIPD;
viewRight *= viewCenter;
There's probably a better way of doing it, but I'm not familiar with GLM.

I should also mention that I haven't actually tried this on my Rift, I just grabbed GLM and looked at what it outputs, so I may have the multiplications the wrong way round.

shakesoda
One Eyed Hopeful
Posts: 28
Joined: Mon Sep 24, 2012 11:46 am
Which stereoscopic 3D solution do you primarily use?: Head Mounted Display (HMD)

Re: OpenGL GLSL version of Pre-warp Shader?

Post by shakesoda »

Ben wrote:shakesoda, I took another look at your code, and I think this is the problem.

Try this instead:

Code: Select all

// Projection matrix for the "center eye", which the left/right matrices are based on.
glm::mat4 projCenter = glm::perspective<float>(yfov, aspectRatio, 0.3f, 1000.0f);

glm::mat4 projLeft(1.0);
projLeft[0][3] = projectionCenterOffset;
projLeft *= projCenter;

glm::mat4 projRight(1.0);
projRight[0][3] = -projectionCenterOffset;
projRight *= projCenter;

// View transformation translation in world units.
float halfIPD = hmd.InterpupillaryDistance * 0.5f;
glm::mat4 viewCenter(1.0);

glm::mat4 viewLeft(1.0);
viewLeft[0][3] = halfIPD;
viewLeft *= viewCenter;

glm::mat4 viewRight(1.0);
viewRight[0][3] = -halfIPD;
viewRight *= viewCenter;
There's probably a better way of doing it, but I'm not familiar with GLM.

I should also mention that I haven't actually tried this on my Rift, I just grabbed GLM and looked at what it outputs, so I may have the multiplications the wrong way round.
I had to switch all the [0][3]'s with [3][0], but otherwise it seems to be correct now. I can't try it on my Rift until tonight, but thanks a bunch for the help!

I've got the SDK partially integrated on my other computer, with any luck I'll be able to look around here properly tonight.

Image

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

Ah, that actually explains some of the extra weirdness I was experiencing with GLM. I really should have thought to check the order was the same as in my matrix class before reusing all my output stuff. Apologies. I hope it didn't take long to notice I had it backwards.

shakesoda
One Eyed Hopeful
Posts: 28
Joined: Mon Sep 24, 2012 11:46 am
Which stereoscopic 3D solution do you primarily use?: Head Mounted Display (HMD)

Re: OpenGL GLSL version of Pre-warp Shader?

Post by shakesoda »

Ben wrote:Ah, that actually explains some of the extra weirdness I was experiencing with GLM. I really should have thought to check the order was the same as in my matrix class before reusing all my output stuff. Apologies. I hope it didn't take long to notice I had it backwards.
It only took a moment, I already knew GLM's matrices were column major (as GL expects) so it was the first thing I tried when I saw that my views got wonky.

With all this sorted out I can get to cleaning up the code and adding content. Thanks again!

geekmaster
Petrif-Eyed
Posts: 2708
Joined: Sat Sep 01, 2012 10:47 pm

Re: OpenGL GLSL version of Pre-warp Shader?

Post by geekmaster »

Low-Level Thinking in High-Level Shading Languages (from GDC 2013):
http://www.humus.name/Articles/Persson_ ... inking.pdf
Optimize all the shaders!

Ben
Two Eyed Hopeful
Posts: 97
Joined: Fri Aug 17, 2012 12:51 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by Ben »

shakesoda wrote:It only took a moment, I already knew GLM's matrices were column major (as GL expects) so it was the first thing I tried when I saw that my views got wonky.
That's what struck me as weird, the matrices I use are column major too, but comparing the values to GLM's showed them to be transposed. Turns out I'm just an idiot and wrote the print method thinking m01 would be the same as m[0][1]. Note to self: just because it works doesn't mean it's right.
geekmaster wrote:Low-Level Thinking in High-Level Shading Languages (from GDC 2013):
That was a great read, thanks. Kind of looking forward to doing another optimization pass on all my shaders now.

User avatar
ThePhilosopher
One Eyed Hopeful
Posts: 37
Joined: Thu Jun 14, 2012 4:42 am

Re: OpenGL GLSL version of Pre-warp Shader?

Post by ThePhilosopher »

Ben wrote:
eshan wrote:Now I just need to figure out all the stuff I need to supply at the top! :)
I've just been using the default values from the Tuscany demo. If you're not worried about calculating everything based on different IPDs and panel sizes yet then these values should be fine.

Code: Select all

// left
vec2 LensCenter		= vec2(0.2863248, 0.5);
vec2 ScreenCenter	= vec2(0.25, 0.5);
vec2 Scale			= vec2(0.1469278, 0.2350845);
vec2 ScaleIn		= vec2(4, 2.5);
vec4 HmdWarpParam	= vec4(1, 0.22, 0.24, 0);

// right
vec2 LensCenter		= vec2(0.7136753, 0.5);
vec2 ScreenCenter	= vec2(0.75, 0.5);
I am using the Riftup! screen upgrade with 1920*1080 5.9" screen.
I've got problems to compute the right numbers for this. Reading the Oculus SDK ( http://static.oculusvr.com/sdk-download ... erview.pdf ) I don't get how they are calculated (in particular Scale and Scalein).

the RiftUp! is a 130mm * 73mm screen
I Would Choose The Matrix

Post Reply

Return to “Oculus VR”