728x90

※ 제 개인 공부이므로 풀 소스 코드는 작성하지 않습니다.

※ 생략 되어 있는 부분이 많습니다.

 

 

삼각형을 그리기 위한 셋팅들은 전 글인

 

2. 노란 삼각형을 그려보자..(외부 fx파일, 전역, 지역 변수 핸들 개념 등등..) 와 모두 같다.

 

*shader.fx*

 

// External Variable Semantic
float4x4 m_mtWldViw : WORLDVIEW;
float4 pos: POSITION;


// Struct
struct T
{
    float3 pos : POSITION;
    float3 normal;
};


// User Defined Function Semantic
float4 MyFunc( float3 pos: POSITION) : POSITION
{
     return float4(pos, 1);
}


void VtxPrc( in float3 iPos : POSITION, out float4 oPos : POSITION, out float4 oD0 : COLOR)
{
     float4 posLocal: POSITION; // 지역 변수는 Semantic을 붙일 수 없다.

 

     // 구조체 초기화
     struct T v={ {1,2,3}, {4,5,6}};

 

     // vector 형 초기화
     vector<float, 4> Dif  = float4(1,1,0,1);

 

     // vector 형 갱신
     Dif = vector(1, 0, 1, 1);

 

     // boo형 변수
     bool t=true;

 

     // 사용자 정의 함수 call
     oPos = MyFunc(iPos);
     oD0  = Dif;
}

 

Semantic이라고 하는 것은 변수의 입력과 출력을 확인 또는 지정하거나 데이터의 출처와 역할에 의미를 부여하기 위해 함수나, 변수, 인수 뒤에 선택적으로 붙여서 서술하는 것이라고 한다.

 

방법은 간단하다 변수,인수,함수 끝에 콜론( : )을 붙이고 명시할 시맨틱 이름을 붙이면 된다.

 

위 셰이더 코드에서 빨간색으로 되어있는 posLocal 변수는 지역변수인데 지역 변수에는 시맨틱을 붙일 수 없다고 한다.

 

위 코드 대로 셰이더를 컴파일하게 되면 에러가 난다. 시맨틱을 없애거나 변수를 없애면 정상적으로 보라색 삼각형이 나온다. 

 

1.입력에 사용되는 시맨틱s

 

POSITION[n]: 정점의 위치. POSITION, POSITION0, POSITION1, ….

BLENDWEIGHT[n]: 정점 블렌딩 비중 값

BLENDINDICES[n]: 정점 블렌딩 인덱스 값

NORMAL[n]: 정점 법선 벡터

PSIZE[n]: Point Size

COLOR[n]: 정점 Diffuse(COLOR, COLOR0), Specular(COLOR1)

TEXCOORD[n]: 텍스처 좌표

TANGENT[n]: 정점 접선 벡터

BINORMAL[n]: 정점 종법선 벡터

TESSFACTOR[n]: tessellation factor

2.출력에 사용되는 시맨틱s

 

POSITION: 정점의 출력 위치

PSIZE: Point Size

FOG: 정점 포그 값

COLOR[0,1]: Diffuse, Specular

TEXCOORD[0~7]: 텍스처 좌표

 

D3D에서 사용자가 만든 데이터는 출력 레지스터가 없기 때문에 이 데이터를 픽셀 쉐이더로 전달하기 위한 경우 TEXCOORD 출력 시멘틱을 가장 많이 사용하며 TEXCOORD0, TEXCOORD1은 대부분 사용하기 때문에 보통TEXCOORD7부터 TEXCOORD6, TEXCOORD5, … 등을 이용한다고 한다.

728x90
Posted by 정망스
,
728x90

※ 제 개인 공부이므로 풀 소스 코드는 작성하지 않습니다.

※ 생략 되어 있는 부분이 많습니다.

 

 

삼각형을 그리기 위한 셋팅들은 전 글인

 

2. 노란 삼각형을 그려보자..(외부 fx파일, 전역, 지역 변수 핸들 개념 등등..) 와 모두 같다.

 

이번엔 uniform이라는 키워드를 알아보기 위한 조금 달라진 shader.fx 파일을 본다.

 

*shader.fx*

 

void VtxPrc( in  float3 iPos: POSITION, out float4 oPos: POSITION, out float4 oD0 : COLOR,

float4 Dif)

{
     Dif = float4(0,1,1,1); //청록색
     oPos = float4(iPos, 1);
     oD0  = Dif;
}

 

Vtxprc 인수중 빨간색으로 되어있는 float4 Dif 부분으로 인해 이 셰이더파일을 컴파일할 때 에러가 발생한다. Vtxprc 함수가 void형 이기 때문에 인자들 앞에 입/출력을 명시적으로 지정해줘야하는데 Dif는 그렇게 작정 되지 않았기 때문이다.

 

uniform float4 Dif 와 같이 앞에 uniform이라는 키워드를 붙여주면 컴파일러가 Dif라는 변수를 상수 레지스터에 저장된 데이터라 여기게 되고 컴파일이 성공하게 된다.

 

uniform 키워드는 지역 변수에는 사용 불가 하고 전역, 함수의 인자에 사용이 가능하다.

 

uniform 키워드는 주로 전역 변수등에 선언하고, varing라는 키워드가 있는데 이 키워드는 위치, 색상, 법선 등의 입력 값에 주로 사용한다고 한다.

 

(예전엔 그런거 같은데 지금 이 글을 쓰는 시점에서는 잘 쓰지 않는 키워드들인듯 하다.)

728x90
Posted by 정망스
,
728x90

※ 제 개인 공부이므로 풀 소스 코드는 작성하지 않습니다.

※ 생략 되어 있는 부분이 많습니다.

 

 

struct Vtx
 {
      D3DXVECTOR3 p;

      Vtx() : p(0, 0, 0) {}
      Vtx(FLOAT X, FLOAT Y, FLOAT Z) : p(X, Y, Z) {}

      enum { FVF = (D3DFVF_XYZ), };
 };

 

LPDIRECT3DVERTEXSHADER9  m_pVs;

LPDIRECT3DVERTEXDECLARATION9  m_pFVF;

LPD3DXCONSTANTTABLE  m_pTbl; 

D3DXHANDLE  m_hDif;

Vtx   m_pVtx[3];

 

정점 구조체 선언하고, 필요한 객체들 (정점 셰이더, 정점 선언자, 상수 테이블, 핸들) 선언해주고,

삼각형을 그리기위한 정점 3개 선언해준다. 

 

** shader.fx **

 

// 전역 변수
float4 Dif  = float4(0,1,1,1); //파랑색 계열

void VtxPrc( in float3 iPos : POSITION, out float4 oPos: POSITION, out float4 oD0 : COLOR)
{
     // 지역 변수
     float4 Dif  = float4(1,1,0,1); //노랑색 계열

     oPos = float4(iPos, 1);
     oD0  = Dif;
}

shader.fx라고 하는 셰이더 파일을 외부로부터 작성한다. 정점들의 포지션값을 입력받고 새로 포지션 값과, 색상을 지정하여 리턴해준다.

 

HRESULT hr = D3DXCompileShaderFromFile("data/shader.fx", NULL, NULL, "VtxPrc", "vs_1_1", dwFlags, &pShd, &pErr, &m_pTbl );

 

//m_hDif = m_pTbl->GetConstantByName(NULL, "Dif");

 

m_pVtx[0] = Vtx(-1, -1, 0);
m_pVtx[1] = Vtx(0, 1, 0);
m_pVtx[2] = Vtx(1, -1, 0);

 

D3DXCompileShaderFromFile을 이용하여 외부에서 셰이더파일을 불러와 컴파일을 해준다.

상수 테이블(m_pTbl)로부터 GetConstantByName을 이용하여 셰이더 파일 안에있는 Dif의 핸들을 얻어온다.

 

m_pdev->SetRenderState(D3DRS_LIGHTING, FALSE);


m_pdev->SetVertexShader(m_pVs);
m_pdev->SetVertexDeclaration(m_pFVF);


D3DXCOLOR color(1, 0, 1, 1); //보라색 계열


 

// 이름에 의한 상수 레지스터 설정
m_pTbl->SetVector(m_pdev, "Dif", (D3DXVECTOR4*)&color);

 

// 핸들에 의한 상수 레지스터 설정
m_pTbl->SetVector(m_pdev, m_hDif, (D3DXVECTOR4*)&color);

 

m_pdev->DrawPrimitiveUP(D3DPT_TRIANGLELIST, 1, m_pVtx, sizeof(Vtx));

 

m_pdev->SetVertexDeclaration(NULL);
m_pdev->SetVertexShader(NULL);

 

SetVertexShader을 이용하여 셰이더를 사용한다 알리므로 shader.fx 파일안에 있는 VtxPrc 함수안의 지역변수 Dif값으로 인해 삼각형이 노랑색으로 나오게 된다. 만약 지역변수 Dif값을 삭제하면,

 

D3DXCOLOR color(1, 0, 1, 1); 이 부분으로 인해 전역변수 Dif값이 보라색으로 바뀌게 되고 삼각형이 보라색으로 나오게 된다.

 

셰이더안의 값을 변경하는 방법으로는 

1.

m_pTbl->SetVector(m_pdev, "Dif", (D3DXVECTOR4*)&color);

 

와 같이 "Dif"처럼 직접 이름을 지정해주는 방법.

 

2.

m_hDif = m_pTbl->GetConstantByName(NULL, "Dif");

m_pTbl->SetVector(m_pdev, m_hDif, (D3DXVECTOR4*)&color);

 

와 같이 GetConstantByName을 이용하여 상수 테이블로부터 핸들을 얻어오는 방법이 있다.

 

상수 테이블에는 셰이더파일 안에 들어있는 변수들의 정보가 들어있다.

728x90
Posted by 정망스
,
728x90

※ 제 개인 공부이므로 풀 소스 코드는 작성하지 않습니다.

※ 생략 되어 있는 부분이 많습니다.

 

 

struct Vtx
 {
      D3DXVECTOR3 p;

      Vtx() : p(0, 0, 0) {}
      Vtx(FLOAT X, FLOAT Y, FLOAT Z) : p(X, Y, Z) {}

      enum { FVF = (D3DFVF_XYZ), };
 };

 

LPDIRECT3DVERTEXSHADER9  m_pVs;
LPDIRECT3DVERTEXDECLARATION9  m_pFVF;

Vtx   m_pVtx[3];

 

정점 구조체 선언해주고.. 필요한것들 정점쉐이더 객체와, 정점 선언자 객체, 그리고 삼각형 그릴꺼니까 정점 3개 만들어 준다.

 

const char sHlsl[] =
  "float4 VtxPrc(float3 Pos : POSITION) : POSITION  \n"
  "{                                                               \n"
  "    return float4(Pos, 1);                                  \n"
  "}                                                               \n"
  "                                                                \n"
  ;

 

HRESULT hr = D3DXCompileShader(sHlsl, iLen, NULL, NULL , "VtxPrc" , "vs_1_1"  , dwFlags, &pShd , &pErr, NULL);

 

m_pVtx[0] = Vtx(-1, -1, 0);
m_pVtx[1] = Vtx(0, 1, 0);
m_pVtx[2] = Vtx(1, -1, 0);

 

Create() 함수 안에서,

 

sHlsl 이라고 하는 우리가 적용할 셰이더를 작성해준다. 여기선 포지션 값만을 설정한다.

D3DXCompileShader을 이용해서 셰이더 컴파일을 해주고, 정점 좌표 3개 작성해준다.

 

m_pdev->SetRenderState(D3DRS_LIGHTING, FALSE);


m_pdev->SetVertexShader(m_pVs);
m_pdev->SetVertexDeclaration(m_pFVF);


m_pdev->DrawPrimitiveUP(D3DPT_TRIANGLELIST, 1, m_pVtx, sizeof(Vtx));

m_pdev->SetVertexShader(NULL);
m_pdev->SetVertexDeclaration(NULL);

 

Render() 함수 안에서,

 

랜더링상태 설정, 셰이더를 사용하겟다라고 설정과, 정점선언자 설정을해주고 그린다.

다 그리고 나면 null로 해제 시켜주고 고정 파이프라인으로 돌아오게 한다.

728x90
Posted by 정망스
,
728x90

D3DXCompileShader() -> HLSL로 작성한 셰이더 코드를 컴파일하거나 실패에 대한 문법 에러를 검사하는 함수.

 

D3DXCompileShaderFromFile() -> 파일에서 작성한 HLSL일때 사용하는 함수.

 

D3DXDeclaratorFromFVF() -> FVF를 사용한 정점 선언값을 채워 넣는 함수.

CreateVertexDeclaration() -> 정점 선언값으로 정점들 선언 정보 (LPDIRECT3DVERTEXDECLARATION9)을 생성하는 함수.

 

FVF(Flexible Vertex Format) -> 유연한 정점 포멧, 사용할 정점의 다양한 정보들을 사용자가 필요한 부분만 골라서 정의하여 유연하게 쓸 수 있는 방법

정점에는 많은 정보를 필요로 하지만 매번 모든 정보가 필요한 것이 아니기 때문에 사용자가 사용할 용도에 따라서 원하는 정보만 포함하여 정점을 구성하므로 용량 효율이 증가. 

 

CreateVertexShader(), CreatePixelShader() -> 컴파일 한 결과를 메모리에 적재하기 위해 정점 셰이더 또는 픽셀 셰이더 객체를 생성한다.

 

SetRenderState() -> 랜더링 상태를 설정한다.

 

SetVertexShader(), SetPixelShader() -> 정점셰이더 또는 픽셀 셰이더 사용을 명시함으로써 프로그램 가능한 파이프라인 사용을 알린다. null값을 넣으면 객체 사용을 해제 하고 고정 파이프라인으로 돌아 온다.

 

SetVertexDeclaration() -> 정점들 선언 정보를 디바이스에 설정한다. null값을 넣으면 해제.

 

DrawPrimitive() -> 정점들을 이용하여 그린다.

 

D3DXMatrixIdentity() -> 단위 형랠로 초기화 해줌.

 

D3DXCreateTextureFromFile() -> 외부로 부터 이미지를 읽을때 사용, 이미지의 크기가 2의 제곱승 이여야 한다.

 

SetSamplerState() -> 기본적으로 텍스처는 스크린의 삼각형에 입혀질때, 텍스처 삼각형이 스크린 삼각형 보다 작다면 텍스처 크기를 확대하고, 크다면 텍스터 크기를 축소하여 크기를 마춘다 이 경우 왜곡이 발생할수도 있는데 이 왜곡을 줄이기위해서 이 함수를 사용하여 필터링을 한다.

(1. 첫번째 인자는 텍스쳐 스테이지.

 2. 두번째 인자는 어떤 필터인지.

 3. 세번째 인자는 필터링 방식을 지칭한다.

 

 2. 필터 종류

 D3DSAMP_MINFILTER - 확대 필터

 D3DSAMP_MAGFILTER - 축소 필터

 D3DSAMP_MIPFILTER - 밉맵 레벨간 사용하는 텍스처 필터

 

 3.필터링 방식

D3DTEXF_POINT - 근접점 샘플링, 디폴트 방식이며 품질이 가장 떨어진다, 계산이 빠르다. 텍스처와   primitive 이미지의 크기가 비슷할때 가장 효과적, 크기가 다르면 확/축소 과정으로 인해 흐림,뭉침,alliasing 등의 현상 발생.

 

D3DTEXF_LINEAR - 선형 필터링, 보통 사용하는 필터링, 비교적 높은 품질, 실행속도 빠름.

 

D3DTEXF_ANISOTROPIC - 비등방성필터링, 가장 높은 품질의 결과물이 나오지만, 실행 속도가 느리다.)

 

 

728x90
Posted by 정망스
,


맨 위로
홈으로 ▲위로 ▼아래로 ♥댓글쓰기 새로고침