2012-05-03 2 views
0

Я ищу лучший способ (или обратите внимание, что это является лучшим способом) для передачи координат пикселя в соответствующем направлению луча от произвольной камеры положения/направления ,Вычислить направление луча вектор из экрана coordanate

Мой текущий метод заключается в следующем. Я определяю «камеру» как вектор положения, вектор lookat и вектор вверх, названный как таковой. (Обратите внимание, что вектор lookat является единичным вектором в направлении, к которому обращена камера, а не где (position-lookat) - это направление, как и стандарт в матрице XNA.CreateLookAt). Эти три вектора могут однозначно определять положение камеры. Вот реальный код (ну, на самом деле не актуальна, упрощенная отведенной версия) (Язык HLSL)

float xPixelCoordShifted = (xPixelCoord/screenWidth * 2 - 1) * aspectRatio; 
float yPixelCoordShifted = yPixelCoord/screenHeight * 2 - 1; 
float3 right = cross(lookat, up); 
float3 actualUp = cross(right, lookat); 
float3 rightShift = mul(right, xPixelCoordShifted); 
float3 upShift = mul(actualUp, yPixelCoordShifted); 
return normalize(lookat + rightShift + upShift); 

(возвращаемое значение является направление луча)

Так что я спрашиваю Это лучший способ сделать это, возможно, используя матрицы и т. д. Проблема с этим методом заключается в том, что, если у вас слишком широкий угол обзора, края экрана становятся «радиально растянутыми».

ответ

0

Вы можете вычислить его (ray) в пиксельный шейдер, код HLSL:

float4x4 WorldViewProjMatrix; // World*View*Proj 
float4x4 WorldViewProjMatrixInv; // (World*View*Proj)^(-1) 

void VS(float4 vPos : POSITION, 
    out float4 oPos : POSITION, 
    out float4 pos : TEXCOORD0) 
{ 
    oPos = mul(vPos, WorldViewProjMatrix); 
    pos = oPos; 
} 

float4 PS(float4 pos : TEXCOORD0) 
{ 
    float4 posWS = mul(pos, WorldViewProjMatrixInv); 
    float3 ray = posWS.xyz/posWS.w; 

    return float4(0, 0, 0, 1); 
} 

информация о положении вашей камеры и направление в View матрице (Matrix.CreateLookAt).