The Book of Shaders by Patricio Gonzalez Vivo & Jen Lowe

日本語 - 中文版 - 한국어 - Español - Français - Italiano - Deutsch - English


Hello World

보통 "Hello world!" 예제들은 모든 컴퓨터 언어의 시작챕터의 제목이다. 라인하나를 출력하는 명령어로 보통 시작되며, 이 언어가 어떤 것들을 할수 있는지에 대한 첫번째 발걸음을 시작한다.

GPU-세상에서는 이런 문자열을 출력하는것은 첫번째 발걸음으로 다소 복잡한 경향이 있다. 하여, 우리는 밝은 색하나를 출력하는 것으로 대신해 발걸음을 떼어본다!

이첵을 브라우져에서 읽고 있다면, 위에 구간이 상호작용이 가능하다는것을 알수 있다. 클릭하거나, 코드를 수정하여 결과를 바로 볼수 있다는 것이다. 이런 변화 인풋은 바로 GPU파이프라인으로 주입되어 컴파일되고, 실시간으로 결과를 바꿔준다. 6번째 줄의 코드를 수정하여 이를 체험해보시라.

매우 간단한 코드지만, 상당히 중요한 내용을 우리는 엿볼수 있는데:

  1. 쉐이더 언어는 color값을 리턴하는 main 함수이고, 이는 C와 형태가 유사하다.

  2. 마지막으로 리턴되는 픽셀 색 값은, gl_FragColor라는 전역변수에 대입된다.

  3. 이 C-유형의 언어는, 미리 선언된, 변수들 (gl_FragColor같은), 함수타입를 가진다. 이 예제의 경우, 실수로 이루어진 4차원 벡터 타입인, vec4. 더 나아가면서, vec3vec2, float, int, 또한 bool같은 것들이 보이게 될것이다.

  4. '''vec4''' 타입을 자세히 살펴보면, 각 인수는 RED, GREEN, BLUE and ALPHA 채널이다. 이 값들은 노멀라이즈된 값이 0.0 에서 1.0 으로 맵핑된것이다. 나중에 나아가면서 노멀라이징을 어떻게 하는지, map 을 어떻게 하는지 살펴보게 될것이다.

  5. 예제에서 볼수 있는 또 다른 중요한 C 요소는 전처리기 마크로들에 대한 사용이다. 마크로들은 컴파일되기 전에 일어나는 스텝이다. #define을 이용해, 전역변수를 선언하거나, 기본적인 논리구현이 가능하다 (#ifdef#endif를 통해). 모든 마크로는 해쉬태그 마크 (#) 로 시작한다. 이런 Pre-compilation은 컴파일이 실제로 일어나기 바로 전에 각 해쉬태그의 해당값을 이 코드로 카피한다. 위에 예제 'hello world!'를 보면, 우리는 GL_ES를 선언하였는데, 이는 모바일 기기나, 브라우져에서 컴파일될때 전처리되는 부분들인 것이다.

  6. 실수 타입들은 쉐이더에서 신경써야할 부분중 하나인데, precision(실수정확도)의 정도가 퍼포먼스에 영향을 미치기 때문이다. 낮은 정도의 precision을 가질수록 빠른 렌더 속도를 가지지만, 렌더 퀄리티가 그만큼 떨어진다는 것을 의미한다. 첫번째 라인을 보면, (precision mediump float;) 라는 내용이 보이는데, 실수정확도를 중간정도로 맞춘것이다. 높게는 (precision lowp float;) 낮게는 (precision lowp float;)이다.

  7. 마지막으로, 그리고 제일 중요할지도 모르지만, GLSL에서는 데이터 타입의 casting이 확보되지 않는다. 무슨말인가하면, 제조업체들은 그래픽카드의 연산을 가속화 하기위해 각각 다른 시도들을 하였는데, 결국은 이것은 최소사양을 저격하고 있다. 자동 casting같은 경우는 여기에 포함되지 않고 있다. 우리의 "hello world!" 예제의 vec4 또한, floats라는 데이터타입을 예상하게 되는것이다. 앞으로 쉐이더 프로그램을 하면서 실수의 경우에는 항상 점 (.) 을 포함하여 이 변수가, 값이 실수임을 명시하자. 예를들어 아래와 같은 코드는 작동이 안될것이다:
void main() {
    gl_FragColor = vec4(1,0,0,1);   // ERROR
}

자, 이제 우리의 첫 예제인 "hello world!"프로그램에 대한 설명을 마친다. 예제의 코드를 수정하면서 이 단원에서 배운 내용을 곱씹어보는 시간을 갖길 바란다. 만약 코드에 에러가 있다면 컴파일 에러가 나면서 화면이 하얗게 될것이다. 아래와 같은 재밌는 시도들도 해볼수 있을것이다.:

vec4 red(){
    return vec4(1.0,0.0,0.0,1.0);
}
vec4 color = vec4(vec3(1.0,0.0,1.0),1.0);

이 예제 자체가 그리 흥미롭지는 않지만 매우 중요한 기본 예제중 하나이다 - 캔바스의 모든 색을 같은색으로 바꿔보는 작업. 다음에 오는 챕터에서는 픽셀 색들을 2개의 인풋을 사용하여 바꿔보는 예제를 해볼것이다. (스크린위에 픽셀들의 위치를 이용한) 그리고 시간을 이용해 이들을 바꾸는 작업도 해볼것이다. (페이지가 로드완료된 후로 몇초가 지났는지를 이용한)