Weitere ähnliche Inhalte Ähnlich wie 셰이더가 뭐에요? (20) Mehr von Jungsoo Park (10) 셰이더가 뭐에요?2. 셰이더가 뭔데 그래요
컴퓨터 그래픽스 분야에서 셰이
더(shader)는 소프트웨어 명령
의 집합으로 주로 그래픽 하드웨
어의 렌더링 효과를 계산하는 데
쓰인다.
셰이더는 그래픽 처리 장치
(GPU)의 프로그래밍이 가능한
렌더링 파이프라인을 프로그래
밍하는 데 쓰인다.
요약하면 데이터 쪼가리를 모니
터 밖으로 꺼내주는 코드
4. 데이터에서 모니터까지
공간상의 좌표 화면 좌표
좌표계 변
환
픽셀 배열
Rasterize
각각의 정점에 대한 계산 :
이 정점은 화면 어디에 위치해야 할까?
빛을 어느 방향에서 얼만큼 받을까?
각각의 픽셀에
대한 계산 :
이 픽셀은
무슨 색일까?
5. 데이터에서 모니터까지
공간상의 좌표 화면 좌표
좌표계 변
환
픽셀 배열
Rasterize
각각의 정점에 대한 계산 :
이 정점은 화면 어디에 위치해야 할까?
빛을 어느 방향에서 얼만큼 받을까?
각각의 픽셀에
대한 계산 :
이 픽셀은
무슨 색일까?
정점 셰이더 픽셀 셰이더
6. 정점 셰이더에서 픽셀 셰이
더로
정점별 계산 결과물을
위치관계에 따라 선형보
간해서 픽셀 셰이더로
전달
색상 데이터를 전달한다
면 :
정점 1은 흰색,
정점 3은 검은색
-> 가운데 픽셀 셰이더
에게는 회색이 전달된다
!
3
여기는
회색!
7. 실제 코드를 봅시다
유니티의 ShaderLab 코드 안
에 nVidia의 Cg 코드가 삽입된
형태
그래서 외계어처럼 보였었구나
....
이만큼 Cg 코드
요 바깥은 ShaderLab 코드
11. 정반사 / Specular reflection
입사한 빛이 한 방향으
로
반사된다고 가정
보는 방향에 따라 밝게
보이는 위치가 다르다!
시선의 방향과 반사광의
방향을 내적하여 구할
수 있다
12. 난반사 / Diffuse reflection
입사한 빛이 모든 방향
으로
균일하게 반사된다고 가
정
밝은 부분은 어느 방향
에서 봐도 밝다!
표면의 방향과 빛의 방
향을
내적하여 구할 수 있다
13. 정점마다 빛의 반사 계산하
기
카메라의 방향벡터
(World 좌표계)
광선의 방향벡터
(World 좌표계)
정점의 수직벡터
(World 좌표계)
정반사 (0~1)
난반사 (0~1)
(Per-Vertex Diffuse+Specular shading)
밝기 텍스쳐
픽셀 색상
정점 셰이더 픽셀 셰이더
14. 픽셀의 수직벡
터
픽셀마다 빛의 반사 계산하
기
카메라의 방향벡터
(World 좌표계)
광선의 방향벡터
(World 좌표계)
정점의 수직벡터
(World 좌표계)
정반사 (0~1)
난반사 (0~1)
(Per-Pixel Diffuse+Specular shading)
밝기 텍스쳐
픽셀 색상
정점 셰이더 픽셀 셰이더
노멀 맵
범프 맵
스페큘러
맵
X
15. 정점 계산법과 픽셀 계산법
어느 단계에서 계산할 것
인가?
정점에 대해서만 계산하면
계산량이 대폭 줄어들지만
정확도 역시 부족하다
픽셀별 계산을 하면 픽셀
별로 보간된 수직방향을
사용하며, 노멀맵이나 스
페큘러 맵 등을 사용할 수
있다
16. 예시 :
간단한 정점
난반사 셰이딩
Per-Vertex
Diffuse
Shading
#include "UnityCG.cginc"
uniform float4 _LightColor0;
// color of light source (from "Lighting.cginc")
uniform float4 _Color; // define shader property for shaders
struct vertexInput {
float4 vertex : POSITION;
float3 normal : NORMAL;
};
struct vertexOutput {
float4 pos : SV_POSITION;
float4 col : COLOR;
};
vertexOutput vert(vertexInput input)
{
vertexOutput output;
float4x4 modelMatrix = _Object2World;
float4x4 modelMatrixInverse = _World2Object;
// multiplication with unity_Scale.w is unnecessary
// because we normalize transformed vectors
float3 normalDirection = normalize(
mul(float4(input.normal, 0.0), modelMatrixInverse).xyz);
float3 lightDirection = normalize(_WorldSpaceLightPos0.xyz);
float3 diffuseReflection = _LightColor0.rgb * _Color.rgb
* max(0.0, dot(normalDirection, lightDirection));
output.col = float4(diffuseReflection, 1.0);
output.pos = mul(UNITY_MATRIX_MVP, input.vertex);
return output;
}
float4 frag(vertexOutput input) : COLOR
{
return input.col;
}
정점 셰이더에서
입력받을 데이터 선언
정점 셰이더에서 픽셀 셰이
더로 보낼 데이터 선언
정점 라이팅 셰이더이므로
픽셀 셰이더는 그냥 입력받은 색상
값을 그대로 리턴
17. 예시 :
간단한 정점
난반사 셰이딩
Per-Vertex
Diffuse
Shading
vertexOutput vert(vertexInput input)
{
vertexOutput output;
float4x4 modelMatrix = _Object2World;
float4x4 modelMatrixInverse = _World2Object;
// multiplication with unity_Scale.w is unnecessary
// because we normalize transformed vectors
float3 normalDirection = normalize(
mul(float4(input.normal, 0.0), modelMatrixInverse).xyz);
float3 lightDirection = normalize(_WorldSpaceLightPos0.xyz);
float3 diffuseReflection = _LightColor0.rgb * _Color.rgb
* max(0.0, dot(normalDirection, lightDirection));
output.col = float4(diffuseReflection, 1.0);
output.pos = mul(UNITY_MATRIX_MVP, input.vertex);
return output;
}
정점의 수직 방향과 빛의 방향을
월드 좌표계에서 정규화하여 나타냄
정점의 수직 방향과 빛의 방향
을
내적하여 난반사량을 구함
반사량과 정점 위치를 리턴
18. 정리
정점 셰이더는 정점별 계산을 하고,
픽셀 셰이더는 픽셀별 계산을 한다
정반사는 보는 각도에 따라 밝은 부위가 변하고,
난반사는 보는 각도에 상관없이 밝은 부위가 일정하다
정점 셰이더 라이팅은 가볍고,
픽셀 셰이더 라이팅은 정확하다