проблема с кодом пересечения лучей и квадратов (выглядит как разрыв) - PullRequest
2 голосов
/ 02 апреля 2019

Привет! Я использую трассировку Монте-Карло, и у меня она работает нормально, но похоже, что есть проблема с кодом пересечения. Ниже приводится изображение

enter image description here

Если вы видите красный цвет в левом углу, кажется, что отображается фоновый цвет.

следующий

float intersectQuad(Ray r, float3 p1, float3 p2, float3 p3, float3 p4, 
float3* outNormal)
{
 const float3 x1 = p2 - p1;
 const float3 x2 = p4 - p1;
 const float3 n = (cross(x2, x1));
 const float denom = dot(n, r.dir); 

 if (denom < 0.00000000001f) return 0.0f;

 const float3 p0l0 = (p1 - r.origin); 
 const float t = dot(p0l0, n) / denom; 

 if( t < 0.000000000001f ) return 0.0f;

 const float3 hitPoint = r.origin + r.dir * t;

 const float3 V1 = normalize(p2 - p1);
 const float3 V2 = normalize(p3 - p2);
 const float3 V3 = normalize(p4 - p3);
 const float3 V4 = normalize(p1 - p4);
 const float3 V5 = normalize(hitPoint - p1);
 const float3 V6 = normalize(hitPoint - p2);
 const float3 V7 = normalize(hitPoint - p3);
 const float3 V8 = normalize(hitPoint - p4);

 if (dot(V1,V5) < 0.0f) return 0.0f;
 if (dot(V2,V6) < 0.0f) return 0.0f;
 if (dot(V3,V7) < 0.0f) return 0.0f;
 if (dot(V4,V8) < 0.0f) return 0.0f;

 *outNormal = n;

 return t;
}

То, как я вызываю код, это

const float inf = 1e20f;
float t = inf;
float hitDistance = 0.0f;
for(int j = 0; j < numberOfQuads; j+=16)
{
 //v1 , v2 , v3 , v4 are 4 vertices of quad in counter clockwise order
 hitDistance = intersectQuad(*ray, v1, v2, v3 ,v4, &n);

 if(hitDistance != 0.0f && hitDistance < t )
 {
   t = hitDistance; 
   colorIndex = k;
   normal = n;
 }
}
return t < inf;

Я не уверен, где я совершаю ошибку.

1 Ответ

5 голосов
/ 02 апреля 2019

Твоим лучам не хватает обоих квадов это "трещина". Любое несоответствие или числовая неточность в коде тестирования попадания может привести к появлению «трещин» или «швов», когда луч попадает ни в один из поли, когда он должен попасть точно в единицу. Это общая проблема, но решаемая. Это также проблема, которую следует избегать при растеризации, а не только при трассировке лучей. Имейте в виду, что поплавки и двойники не являются бесконечно точными. Всегда проверяйте, чтобы вычисление ребра в одном поли было одинаковым для того же ребра в соседнем поли. Другими словами, оба ваших четырехугольника расположены по часовой стрелке или против часовой стрелки?

Вот хорошая статья: jcgt.org / опубликовано / 0002/01/05 / paper.pdf

...