기본적인 vertex up & down, 다이얼로그를 사용한 증감률과 반지름 조절이 가능하다.

 

void CTERRAIN::Intersect( BOOL RBT, BOOL LBT, HWND gm_hWnd, BOOL mouseMove )
{
LPCUSTOMVERTEX pVertices, pCirVertices; //VB에 사용할 구조체 포인터
WORD *pIndices; //IB에 사용될 WORD 포인터
D3DXVECTOR3 centerPos; //삼각형을 이루는 각 한쌍의 인덱스중 좌측 상단의 vetex
BOOL intersect = FALSE; //픽킹의 성공여부
float scale[3] = {0.0f,}; //IntersectTriangle에 인자로 넘겨줄 scale배열
D3DXVECTOR3 orig, dir( 0.0f, -1.0f, 0.0f ); //원의 픽킹에 사용될 변수
static WORD realIBTotalSize = 8 * 8 * 6; //index의 총 길이
static BOOL first = TRUE; //첫 로딩의 판단
static DWORD sNum = 0; //VB의 번호
static DWORD referSNum = 0, referENum = 0; //참조메모리의 시작인덱스와 끝인덱스
static float lenthMinSize = (m_radiusSize * m_intervalRate -0.5f * m_intervalRate)*(m_radiusSize * m_intervalRate -0.5f * m_intervalRate); //원의 최소값의 제곱
static float lenthMaxSize = (m_radiusSize * m_intervalRate +0.5f * m_intervalRate)*(m_radiusSize * m_intervalRate +0.5f * m_intervalRate); //원의 최대값의 제곱
//원 리사이즈시 변수 초기화
if( m_reSize )
{
first = TRUE;
sNum = 0;
referSNum = 0, referENum = 0;
lenthMinSize = (m_radiusSize * m_intervalRate -0.5f * m_intervalRate)*(m_radiusSize * m_intervalRate -0.5f * m_intervalRate);
lenthMaxSize = (m_radiusSize * m_intervalRate +0.5f * m_intervalRate)*(m_radiusSize * m_intervalRate +0.5f * m_intervalRate);
m_reSize = FALSE;
}
//첫 로딩
if( first )
{
//가상 메모리로 픽킹된 삼각형의 좌측 상단 vertex를 구한다.
for( DWORD i = 0; i < m_rIndexTotalSize; i+=3 )
{
if( IntersectTriangle( m_pickOrig, m_pickDir,
m_pReferVB[m_pReferIB[i]], m_pReferVB[m_pReferIB[i+1]], m_pReferVB[m_pReferIB[i+2]],
&scale[0], &scale[1], &scale[2] ) )
{
m_pickPos = m_pickOrig + ( m_pickDir * scale[0] );
centerPos = m_pReferVB[m_pReferIB[(i%2 == 0) ? i+1 : i]] + D3DXVECTOR3( 1.0f, 0.0f, -1.0f);
referSNum = ((i - m_rIndexRoadSize[0])) > m_rIndexTotalSize ? 0 : (i - m_rIndexRoadSize[0]);
referENum = (referSNum + m_rIndexRoadSize[1]) > m_rIndexTotalSize ? m_rIndexTotalSize : (referSNum + m_rIndexRoadSize[1]);
first = FALSE;
}
}
//위에서 구한 centerPos로 VB의 시작 번호를 구한다.
for( short i = m_virtualVBSize / 2; i < m_vbSizeZ-m_virtualVBSize/2; i++ )
{
for( short k = m_virtualVBSize / 2; k < m_vbSizeX-m_virtualVBSize/2; k++ )
{
WORD vbNum = i * m_vbSizeX + k;
DWORD cnt = 0;
m_ppTerVB[vbNum]->Lock( 0, 0, (void**)&pVertices, 0 );
for( WORD a = 0; a < 9; a++ )
{
for( WORD b = 0; b < 9; b++)
{
D3DXVECTOR3 tempV = pVertices[cnt++].v;
tempV.y = 0.0f;
if( tempV == centerPos )
{
sNum = i * m_vbSizeX + k;
}
}
}
m_ppTerVB[vbNum]->Unlock();
}
}
}
//이후의 로딩
else if( !first )
{
for( DWORD i = referSNum; i < referENum; i+=3 )
{
if( IntersectTriangle( m_pickOrig, m_pickDir,
m_pReferVB[m_pReferIB[i]], m_pReferVB[m_pReferIB[i+1]], m_pReferVB[m_pReferIB[i+2]],
&scale[0], &scale[1], &scale[2] ) )
{
m_pickPos = m_pickOrig + ( m_pickDir * scale[0] );
centerPos = m_pReferVB[m_pReferIB[(i%2 == 0) ? i+1 : i]] + D3DXVECTOR3( 1.0f, 0.0f, -1.0f);
referSNum = ((i - m_rIndexRoadSize[0])) > m_rIndexTotalSize ? 0 : (i - m_rIndexRoadSize[0]);
referENum = (referSNum + m_rIndexRoadSize[1]) > m_rIndexTotalSize ? m_rIndexTotalSize : (referSNum + m_rIndexRoadSize[1]);
break;
}
}
DWORD cnt = 0;
m_pCirVB->Lock(0, 0, (void**)&pCirVertices, 0 );
m_pTerIB->Lock(0, 0, (void**)&pIndices, 0 );
for( short i =0; i < m_virtualVBSize; i++ )
{
for( short k = 0; k < m_virtualVBSize; k++)
{
DWORD vbNum = sNum + ((m_vbSizeX) * i) + k - m_fixedVBPoint;
m_ppTerVB[vbNum]->Lock( 0, 0, (void**)&pVertices, 0 );
if( !intersect )
{
DWORD cnt = 0;
for( WORD a = 0; a < 9; a++ )
{
for( WORD b = 0; b < 9; b++)
{
D3DXVECTOR3 tempV = pVertices[cnt++].v;
tempV.y = 0.0f;
if( tempV == centerPos )
{
sNum = vbNum;
intersect = TRUE;
}
}
}
}
if( mouseMove )
{


//가상의 원의 위치와 VB의 삼각형이 픽킹을 하지는지 구해낸후
//실제 원의 y값을 증감 시킨다.
for( WORD m = 0; m < realIBTotalSize; m+=3 )
{
D3DXVECTOR3 tempV = pVertices[pIndices[m]].v;
tempV.y = 0.0f;
float checkLen = D3DXVec3LengthSq(&(tempV - m_pickPos));
if(checkLen < lenthMaxSize && checkLen > lenthMinSize)
{
for(short b = 0; b < m_cirTic; b++)
{
pCirVertices[b].v.x = m_pReferCir[b].x + m_pickPos.x;
pCirVertices[b].v.z = m_pReferCir[b].z + m_pickPos.z;
orig = pCirVertices[b].v;
orig.y = 1000.0f;
if(IntersectTriangle( orig, dir,
pVertices[pIndices[m]].v, pVertices[pIndices[m+1]].v, pVertices[pIndices[m+2]].v,
&scale[0], &scale[1], &scale[2]))
{
cnt++;
pCirVertices[b].v.y = (orig + dir * scale[0]).y+0.1f;
}
}
}
}
}
m_ppTerVB[vbNum]->Unlock();
}
}
m_pTerIB->Unlock();
m_pCirVB->Unlock();
}
if(intersect && LBT)
{
float checkRadius = ( m_radiusSize * m_intervalRate - 1.5f ) * (m_radiusSize * m_intervalRate - 1.5f); //원의 반지름보다 조금 작은값의 제곱
float checkSELine = m_realVBSize * 8.0f * m_intervalRate / 2.0f; //실제 VB의 총 길이
//픽킹된 VB의 vertex의 y값을 증감시킨다.
for( WORD i = 0; i < m_virtualVBSize; i++ )
{
for( WORD k = 0; k < m_virtualVBSize; k++)
{
DWORD vbNum = sNum + ((m_vbSizeX) * i) + k - m_fixedVBPoint;
m_ppTerVB[vbNum]->Lock(0, 0, (void**)&pVertices, 0);
for( WORD a = 0; a < 9; a++)
{
for( WORD b = 0; b < 9; b++)
{
WORD count = 9*a+b;
D3DXVECTOR3 checkV = pVertices[count].v;
checkV.y = 0.0f;
float d = D3DXVec3LengthSq(&(checkV - m_pickPos));
float r = checkRadius;
if( d < r && checkV.x > -checkSELine && checkV.x < checkSELine && checkV.z > -checkSELine && checkV.z < checkSELine)
{
float increaseY = sinf(D3DXToRadian( 90.0f - (90.0f * d / r) ) )*(m_increaseRate);
pVertices[count].v.y += increaseY;
}
}
}
m_ppTerVB[vbNum]->Unlock();
}
}
}
//vertex 초기화
if( RBT )
{
DWORD cnt = 0;
for( WORD i = 0; i < m_vbSizeZ; i++)
{
for( WORD k = 0; k < m_vbSizeX; k++)
{
m_ppTerVB[cnt]->Lock(0, 0, (void**)&pVertices, 0);
DWORD cnt2 = 0;
for( WORD a = 0; a < 9; a++ )
{
for(WORD b = 0; b < 9; b++)
{
pVertices[cnt2++].v.y = 0.0f;
}
}
m_ppTerVB[cnt++]->Unlock();
}
}
m_pCirVB->Lock( 0, 0, (void**)&pCirVertices, 0 );
for( WORD i = 0; i < m_cirTic; i++)
{
pCirVertices[i].v.y = 0.0f;
}
m_pCirVB->Unlock();
}
}

 

 

일반 메모리를 사용하여 픽킹된곳의 실제 좌표값을 얻어내어

VB의 배열을 탐색한 후 해당 VB의 실제 번호를 알아내고

픽킹된 좌표와 탐색한 vertex의 차백터한 백터의 크기가 반지름의 제곱에 크기보다 작은

vertex들의 y값을 증가시킨다.

 

차후에 카메라 클래스를 구현하여 맵툴에 적용시킨후

다른 세부사항을 추가할 계획이다.

 

'programming > direct3d' 카테고리의 다른 글

directx 지형 알파 멀티텍스쳐의 복수 사용  (0) 2024.07.26
directx 지형 알파 텍스쳐 입히기  (0) 2024.07.26
directx 지형 수정사항  (0) 2024.07.26
directx 지형 추가사항  (0) 2024.07.26
IntersectTriangle 픽킹  (0) 2024.07.26
Posted by mainep
: