내가 직접 만든 셰이더 언어

발행: (2025년 12월 29일 오전 06:49 GMT+9)
3 min read
원문: Dev.to

Source: Dev.to

좌표 공간

표준 GLSL에서는 vec4가 단순히 vec4일 뿐입니다. 컴파일러는 해당 벡터가 World Space, Model Space, 혹은 Clip Space 중 어느 위치를 나타내는지 알지 못합니다. 뷰‑스페이스 벡터에 모델 행렬을 실수로 곱해도 컴파일 타임 오류가 발생하지 않으며, 대신 검은 화면이나 잘못된 조명이 나타나 혼란을 디버깅하게 됩니다.

핵심 아이디어

Cast는 좌표 공간에 대한 강한 타입을 도입합니다:

// Cast 구문
let modelPos : vec4 = ...;
let matrix   : mat4 = ...;

// 타입이 일치하므로 정상 동작
let worldPos = matrix * modelPos;

// 컴파일러 오류가 발생합니다
let wrong = projectionMatrix * modelPos;

타입에 공간 정보를 ( , , 등) 인코딩함으로써, 컴파일러는 행렬‑벡터 곱셈이 의미적으로 올바른지 검증할 수 있습니다.

구문 정리

전형적인 GLSL 표현식:

max(pow(dot(N, L), 32.0), 0.0)

안쪽부터 읽어 내려가면 번거로울 수 있습니다. Cast는 왼쪽‑에서‑오른쪽, 메서드 체인 스타일을 제안합니다:

N.dot(L).pow(32.0).max(0.0)

새로운 기능 추가

수신자 타입 (Go에서 영감)

Go 예시:

type SomeStruct struct {
    width, height int
}

func (r *SomeStruct) SomeFunction() { ... }

Cast는 비슷한 패턴을 채택합니다:

struct SomeStruct { x: float, y: float }

fn (SomeStruct) SomeFunction() { ... }

구조화된 Uniform/IO 블록

셰이더 파일을 정리하기 위해, Cast는 uniform, input, output을 그룹화할 수 있게 합니다:

uniform {
    // uniform 선언
}

in {
    // input 선언
}

out {
    // output 선언
}

현재 상태

Cast는 현재 Proof of Concept 단계입니다. 아직 프로덕션에 적합하지 않으며, 많은 표준 기능이 누락되어 있고 특정 상황에서는 컴파일러가 충돌할 수 있습니다.

피드백 요청

명시적인 좌표 공간, 메서드 체인 구문, 수신자 타입이라는 개념은 논의를 환영합니다. 구문과 아키텍처에 대한 의견을 자유롭게 남겨 주세요. 소스 코드를 확인하거나 이슈를 열거나 매트릭스‑곱셈 접근 방식에 대한 생각을 공유해 주시면 좋겠습니다.

Cast repository

Back to Blog

관련 글

더 보기 »

SwiftUI에서 ScrollView와 좌표 공간

스크롤 기반 UI는 현대 앱 어디에나 존재합니다 - collapsing headers - parallax effects - sticky toolbars - section pinning - scroll‑driven animations - pull‑to‑r...