2012-12-29 2 views
1

.obj 파일에서 모델을로드하고 렌더링 할 수있는 DirectX에서 간단한 "엔진"을 만들었습니다. 내가 만든 객체에 대해서는 괜찮습니다. 좌표가 -1.0 ~ 1.0 범위의 단순 큐브. 그러나 다른 단위를 사용하고 -2k ~ 2k 범위 내의 좌표를 갖는 모델을로드하면 깊이 버퍼에 완전히 맞지 않는 거대한 결과가 발생하므로 거대한 다리 하나 또는 이와 유사한 효과가 나타납니다.DirectX에서 모델 크기를 정규화하는 방법은 무엇입니까?

나는 어딘가에 대해 읽었던 것을 기억하지만, 나는 많은 DX 물건들을 최근에봤을 때, 나는 그것이 어디에 있었는지 기억할 수 없다. 그래서 내 질문은, 다른 단위를 사용하는 다른 모델을로드 할 수 있기를 원한다는 것입니다. 모두 비슷한 크기로 화면에 잘 맞도록하는 가장 좋은 방법은 무엇입니까?

개체를로드 할 때 값을 변환하려고 할 수 있지만 변환 행렬 또는 셰이더를 사용하는 DirectX 방식이 더있을 수 있습니까?

+0

스케일링은 일반적으로 [World Transform] (http://msdn.microsoft.com/en-us/library/windows/desktop/bb206365.aspx)으로 수행되며, 정점은 모델 공간에서 월드 공간으로 변환됩니다. 그런 다음이 행렬을 뷰 및 투영 행렬에 곱하여 최종 변환을 만듭니다. – IInspectable

+0

Tim의 대답은 정확합니다. 스케일 디스 패러티로 그는 부동 소수점 정밀도를 꽤 빨리 잃을 것입니다. – user805547

답변

2

가장 간단한 방법은 모델에 가장 큰 범위가 포함 된 구성 요소를 찾고이 값을 사용하여 모델을 균일하게 스케일링하는 것입니다. 가장 큰 범위를 찾으려면 모델 경계 상자를 계산하고 (wavefront obj 파일에서 이미 제공하지 않는 한 어쨌든 확인하려면), 비교할 범위로 상자 크기를 사용하십시오. 이렇게하면 가져온 모든 모델을 단위 범위까지 줄일 수 있습니다.

예를 들어, 테두리 상자가 374 * 820 * 512 단위 인 모델의 경우 가장 큰 모델은 820 인 Y 축이므로 크기를 820으로 축소하면됩니다 (모든 구성 요소를 820). 이것은 실수가 아닌 경우 D3DXMatrixScaling으로 초기화 할 수있는 획일적 인 스케일링 매트릭스를 사용하여 편리하게 구현할 수 있습니다. 경계 상자가 2 개의 벡터 (최대 및 최소 정점)로 주어져 있다고 가정하면이 벡터의 차이를 계산 한 다음 가장 큰 값을 선택하고 역행렬을 매트릭스의 스케일링 계수로 사용하십시오.

D3DMatrix mScale; 
D3DVector mx, mn; 
obj->getBoundingBox(&mn,&mx); 
float scale = 1.0/max(mx.x - mn.x, max(mx.y - mn.y, mx.z -mn.z)); 
D3DXMatrixScaling(&mScale, scale, scale,scale); 

렌더링 파이프 라인에 매트릭스를 삽입하기 만하면됩니다.

경계 상자의 계산과 관련하여 모델의 모든 꼭지점에 대한 간단한 루프가 최소화 및 최대 구성 요소를 유지 (서로 독립적 임)해야합니다. 물론

D3DVector mn, mx; 
mn.x = mn.y = mn.z = MAX_FLOAT; 
mx.x = mx.y = mx.z = - MAX_FLOAT; 
for (int i = 0; i < numVertices ; i++) { 
    mn.x = min(mn.x, vertex[i].x); 
    mn.y = min(mn.y, vertex[i].y); 
    mn.z = min(mn.z, vertex[i].z); 
    // same for mx using max 
} 

, 당신은 당신의보기는 단위 상자보다 더 큰 영역을 커버하는 경우 일부 배율 인수를 사용해야 할 수도 있습니다 (하지만 분명히 이것은 당신이 사용하는 것입니다).

+0

그래, 그게 효과가 있지만 두 번째 생각을 준 후에, 나는 3D 소프트웨어로 내 모델을 확장하고 코드를 그대로 두는 것이 좋을 것이라고 생각한다. – jaho

+0

나는 D3D 사용자가 아니며 어쩌면 내가 제시 한 코드 샘플에서 보여줄 수도 있지만, 한 번에 하나의 모델을 표시하는 경우 내 생각에 서 있다고 생각합니다. 많은 것을 표시하는 경우, 모델을로드 한 후 스케일링을 한 번 더 수행하는 것이 더 효율적이거나 외부 소프트웨어를 사용하는 것이 좋습니다. – didierc