Forum Discussion
DrGusta
12 years agoHonored Guest
Barrel Distortion
I have been searching the web for hours now and I have yet to find a solution. I want to apply barrel distortion to a live feed from a USB web cam (Logitech 9000), I am currently using OpenCV. I am fairly new to OpenCV so be gentle.
PS I am writing this in C++ (Visual Studio 2010)
Brenden Geary
PS I am writing this in C++ (Visual Studio 2010)
Brenden Geary
13 Replies
- MrGeddingsExplorer
(sorry chances are it is possible but it made me think of this quote) - drashHeroic ExplorerHere's a wiki link:
http://en.wikipedia.org/wiki/Distortion_(optics)#Software_correction
And here's a little piece from Oculus' warp shader in Unity (not including chromatic aberration correction):float2 _Center = float2(0,0);
float2 _ScaleIn = float2(0,0);
float2 _Scale = float2(0,0);
float4 _HmdWarpParam = float4(0,0,0,0);
// Scales input texture coordinates for distortion.
// ScaleIn maps texture coordinates to Scales to ([-1, 1] * scaleFactor),
// where scaleFactor compensates input for K1 and K2, to allow full screen size to be used.
// Scale factor that fits into screen size can be determined by solving this
// equation for Scale: 1 = Scale * (K0 + K1 * Scale^2 + K2 * Scale^4).
float2 HmdWarp(float2 in01)
{
float2 vecFromCenter = (in01 - _Center) * _ScaleIn; // Scales to [-1, 1]
float rSq= vecFromCenter.x * vecFromCenter.x + vecFromCenter.y * vecFromCenter.y;
float2 vecResult = vecFromCenter * (_HmdWarpParam.x + _HmdWarpParam.y * rSq + _HmdWarpParam.z * rSq * rSq);
return _Center + _Scale * vecResult;
}
Where _Center is set to:0.5f + (LensOffsetLeft * 0.5f)
(left eye)
and0.5f + (LensOffsetRight * 0.5f)
(right eye),
where LensOffset* values are calculated from:float halfHSS = HScreenSize * 0.5f;
float halfLSD = LensSeparationDistance * 0.5f;
leftOffset = (((halfHSS - halfLSD) / halfHSS) * 2.0f) - 1.0f;
rightOffset = (( halfLSD / halfHSS) * 2.0f) - 1.0f;
where LensSeparationDistance is retrieved directly from the SDK via OVR_GetLensSeparationDistance().
And, where _Scale, _ScaleIn, and _HmdWarpParams are calculated like this:_Scale.x = (NormalizedWidth / 2.0f) * distortionScale;
_Scale.y = (NormalizedHeight / 2.0f) * distortionScale * aspectRatio;
_ScaleIn.x = (2.0f / NormalizedWidth);
_ScaleIn.y = (2.0f / NormalizedHeight) / aspectRatio;
_HmdWarpParam.x = DistK0;
_HmdWarpParam.y = DistK1;
_HmdWarpParam.z = DistK2;
where NormalizedWidth and NormalizedHeight are 1.0f for Unity, possibly different for other rendering engines,
and where distortionScale is calculated such that the post-warp image fits the screen to some extent,
and where aspectRatio is the aspectRatio of the screen resolution shown to one eye (width / 2 by height)
and where DistK0, DistK1, and DistK2 are distortion coefficients retrieved directly from the SDK's OVR_GetDistortionCoefficients() function.
I'm sure I left out some details, but it's all there in Oculus's Unity integration code if you want to see more! - DrGustaHonored GuestI understand that part of it but my question is how can I incorporate that into/with opencv or did I miss something?
Brenden Geary - jhericoAdventurerThere's code here that demonstrates loading an OpenCV image into an texture. Then it's a matter of rendering that texture onto something in the OpenGL scene. I'm working on something very similar for an augmented reality view, using OpenCV to process depth and color streams to allow for interaction with the rendered UI.
- rudiHonored GuestHey There,
Thank you for the explanation given about the hmdwrap....but I got bit of a problem, I am not on Unity and some of the math operations you are using are not defined in standard vector math...so I am kind of guessing how Unity interprets this operations...
in01 = Texture Coordinates ..Vector(x,y)
_ScaleIn = Vector(x,y)
_Center = Scalar following this lineeg for left: _Center = 0.5f + (leftOffset * 0.5f);
float2 vecFromCenter = (in01 - _Center) * _ScaleIn;
Now I do not get the point of this expressions:
1. (Vector1 - Scalar1) => Substract Scalar from Vector is not defined...what kind of mathematical Operation is happening here and what is the result?
2a. In case (Vector1 - Scalar1) = Vector2, I get Vector2 * _ScaleIn =>multiplication of two vectors is not defined
could be a cross product (which does not make sense)
could be multiplication of the coordinates of the vectors like this Vector2.x * _ScaleIn.x and Vector2.y * _ScaleIn.y ....But what is it???
2b. In case (Vector1 - Scalar1) = Scalar2, I get Scalar2 * _ScaleIn => which is a valid term multiplication of Vector with Scalar. - rudiHonored Guest...to make the question a bit more haptic.....some code from c# visualizing what I mean...
private void ScaleTexture(HmdInfoStruct Info, Vector2 TextureCoordinates, float _distortionScale)
{
//Center for Left Screen / Right Screen
float halfHSS = Info._HScreenSize * 0.5f;
float halfLSD = Info._LensSeparationDistance * 0.5f;
float leftOffset = (((halfHSS - halfLSD) / halfHSS) * 2.0f) - 1.0f;
float rightOffset = ((halfLSD / halfHSS) * 2.0f) - 1.0f;
float vertical = Info._VScreenCenter;
float LCenter = 0.5f + (leftOffset * 0.5f);
Vector2 _LCenter = new Vector2(LCenter, vertical);
//assumption made that we are talking about a Center Point here....??
float RCenter = 0.5f + (rightOffset * 0.5f);
Vector2 _RCenter = new Vector2(RCenter, vertical);
//assumption made that we are talking about a Center Point here....?
//Size and Scale Parameter
float NormalizedWidth = 1.0f;
float NormalizedHeight = 1.0f;
float aspectRatio = (Info._HResolution / 2.0f) / Info._VResolution;
float distortionScale = _distortionScale;
//Scale and ScaleIN
Vector2 ScaleIn = new Vector2(2.0f, 2.0f);
Vector2 Scale = new Vector2(0.3f, 0.35f);
Scale.X = (NormalizedWidth / 2.0f) * distortionScale;
Scale.Y = (NormalizedHeight / 2.0f) * distortionScale * aspectRatio;
ScaleIn.X = (2.0f / NormalizedWidth);
ScaleIn.Y = (2.0f / NormalizedHeight) / aspectRatio;
//Distortion Parameters from LIB
Vector4 HmdWarpParameter = new Vector4(Info._DistortionK1, Info._DistortionK2, Info._DistortionK3, Info._DistortionK4);
//Left Calculation
//original code....resulting in error because * not defined
//Vector2 theta = (TextureCoordinates - _Center) * ScaleIn;
//assumed code interpreations as mulitplication of each coordinate??????????????????
Vector2 v_helper = TextureCoordinates - _LCenter;
Vector2 Ltheta = new Vector2(v_helper.X * ScaleIn.X, v_helper.Y * ScaleIn.Y);
float rSq = Ltheta.X * Ltheta.X + Ltheta.Y * Ltheta.Y;
Vector2 rvector = Ltheta * (HmdWarpParameter[0] + HmdWarpParameter[1] * rSq + HmdWarpParameter[2] * rSq * rSq + HmdWarpParameter[3] * rSq * rSq * rSq);
//original code....resulting in error because * not defined
//assuming a per coordinate mulitplication?????????????????
v_helper = new Vector2(Scale.X * rvector.X, Scale.Y * rvector.Y);
Vector2 LeftScale = _LCenter + v_helper;
//Right Calculation
//original code....resulting in error because * not defined
//Vector2 theta = (TextureCoordinates - _Center) * ScaleIn;
//assumed code interpreations as mulitplication of each coordinate
v_helper = TextureCoordinates - _RCenter;
Vector2 Rtheta = new Vector2(v_helper.X * ScaleIn.X, v_helper.Y * ScaleIn.Y);
rSq = Rtheta.X * Rtheta.X + Rtheta.Y * Rtheta.Y;
rvector = Rtheta * (HmdWarpParameter[0] + HmdWarpParameter[1] * rSq + HmdWarpParameter[2] * rSq * rSq + HmdWarpParameter[3] * rSq * rSq * rSq);
//same problem here original code states LensCenter + Scale * rvector, assuming a per coordinate mulitplication
v_helper = new Vector2(Scale.X * rvector.X, Scale.Y * rvector.Y);
Vector2 RightScale = _RCenter + v_helper;
} - AngelJExplorerHi rudi. Maybe I'm not understanding what you're trying to do, but if you're not very familiar with pixel shaders you might want to read up on them as well as HLSL or GLSL depending on what you're working in.
- AngelJExplorerAlso, if you're just trying to use Oculus VR's pixel shader, in most cases you should just be able to copy it into your project without doing any programming in a shader language at all.
- rudiHonored GuestHi AngelJ,
simple as that I try to understand the underlying math here....and you are right I am just in the process of building up some knowledge about pixel shader programming and understanding the math is part of the process for me.
However it is ok and I think I got the point now after some more googeling last night :-)
Rudi - jhericoAdventurer
"rudi" wrote:
Now I do not get the point of this expressions:
1. (Vector1 - Scalar1) => Substract Scalar from Vector is not defined...what kind of mathematical Operation is happening here and what is the result?
In GLSL you can apply a scalar against a vector with an operation and it and it applies the operation piecewise to the vector components. So:vec2 foo;
float bar;
foo *= bar; // equivalent to foo.x *= bar; foo.y *= bar;
The output of a vectorN operation against a scalar will always be of vectorN type.vec2 foo;
float bar;
foo = foo * bar; // Valid
bar = foo * bar; // Compile failure
Quick Links
- Horizon Developer Support
- Quest User Forums
- Troubleshooting Forum for problems with a game or app
- Quest Support for problems with your device
Other Meta Support
Related Content
- 11 years ago
- 23 days ago