2017-10-07 2 views
1

this page에서 복사 한 webgl으로 놀고 있습니다. 마우스를 사용하여 조명 위치를 제어하고 싶습니다. 난 그냥 fragment shaderjs에서 정적 값을 보내는 경우Webgl - 동적 마우스 위치

가 작동합니다

function updateMousePosition(e){ 
    console.log(e.pageX); 
    mousex = e.pageX; 
    mousey = e.pageY; 
} 

때 마우스 이동 호출됩니다

mouseLocation = gl.getUniformLocation(program, "mouse"); 
gl.uniform2f(mouseLocation, 0,0); 

을 나는 마우스 위치를 업데이트 할 수있는 기능을 가지고 :

canvas.addEventListener('mousemove', updateMousePosition, false); 

fragment shader 모든 프레임 :

gl.uniform2f(mouseLocation, mousex,mousey); 

그 후 나는 fragment shader에서 마우스 위치를 얻을 것이다 :

uniform vec2 mouse; 

void main(void) { 
    //mp - mouse position 
    vec2 mp = vec2(mouse.x/resolution.x, 1.0 - mouse.y/resolution.y); 

    //lp depend on mp 
    vec3 lp = vec3(mp.x, mp.y, -1.0); 

    //other calculation ... 
} 

그것은 작동하지 않았다. 하지만 updateMousePosition(e)console.log에서 정적 값을 보낼 때 :

gl.uniform2f(mouseLocation, 679, 590);//number taken from console.log 

그 일을.

작동하지 않는 것이 확실하지만 숫자 형식 또는 유형이 의심됩니다. js은 정확히 입력하지 않고 glsl입니다.

어떻게 해결할 수 있습니까?

+0

더 많은 코드를 표시해야합니다. 당신이 보여준 것에는 아무런 문제가 없습니다. – gman

답변

0

Finaly는이 답변 (편집 됨)을 결정했습니다.

Gman이 주석을 달았으므로 코드에는 아무런 문제가 없습니다. 엄밀히 말하면이 방법이 효과적입니다. 그러나 당신은 OpenGL에 비해 WebGL/Javascript의 진짜 까다로운 부분을 지적했습니다 : typage. Javascript 변수가 작동하는 방식 때문에 이상한 버그를 쉽게 생성 할 수 있습니다.

이 absurde 상황을 상상해 : C, C++ 또는 다른 강한 입력 된 언어와

var x = 55; 
var y = 128; 

// some code here... 

x = "blah"; // oups ! 

// some code here... 

gl.uniform2f(mouseLocation, x, y); 

을, 같은 부조리가 할 것은 거의 불가능하다 (이 포인터를 통해 가능하지만 다른 될 수 있습니다) 컴파일러 때문에 그것을 엄격하게 금지하고 오류를 던지십시오. 그러나 자바 스크립트에서는 문제가 없으며이 경우 숫자 변수 x이 문자열 변수가되고 WebGL에 전달되면 NaN이됩니다. x 변수를 올바르게 추적하지 못한 경우 오랫동안이 변수가 작동하지 않는 이유를 검색합니다.

모든 WebGL 함수는 마지막 단계에서 유형이 지정된 데이터 만 허용합니다. 마지막 단계는 GPU이고 GPU는 낮은 수준이기 때문입니다. 즉, 순수한 Javascript Number 변수를 WebGL 함수에 전달하더라도이 Javascript 변수는 이전에 형식화 된 데이터로 변환됩니다. 그러나 JavaScript가 틀린 변수 유형에 대해서는 오류를 던지지 않을 것입니다. 입력 된 데이터로 변환 (캐스팅)하고, 사용자가 시도한 것이 터무니없는 경우에도 경고하지 않습니다. 변환 할 수없는 데이터를 변환합니다. 'NaN'.

다행히도, 어떤 모호성을 피하기 위해, WebGL을 새로운 자바 스크립트 객체의 무리와 함께 제공 : 형식화 된 배열 : 입력 된 배열로 https://developer.mozilla.org/fr/docs/Web/JavaScript/Reference/Objets_globaux/TypedArray

, 당신은 당신의 자바 스크립트 코드 내에서 알 수있는 데이터를 저장하고, 그래서 어떤 데이터 전송하기 전에 GPU로 전송됩니다. 즉, 입력 된 배열을 사용하여 Javascript 변수를 GPU로 보내기 전에 알려진 유형의 데이터로 변환 (형 변환) 할 수 있습니다. 위의 예에서

var mousePos = new Float32Array(2); 

function updateMousePosition(e){ 
    mousePos[0] = e.pageX; 
    mousePos[1] = e.pageY; 
} 

// do something 

console.log(mousePos); 
gl.uniform2fv(mouseLocation, mousePos); 

는 변수 e.pageX e.pageY와 직접 호환 WebGL을 입력 데이터로 변환된다. 그렇게하면 변수를 console.log을 사용하여 인쇄하면 WebGL에 실제로 전송 될 내용을 볼 수 있습니다. 디버그 목적으로 gl.uniform2fv으로 전화하기 직전에 console.log을 넣어 "out of view"오류가 발생하지 않도록 할 수 있습니다.

이 예에서 데이터가 잘못 변환 된 경우 출력 로그에 NaN, NaN과 같은 내용이 표시되므로 코드에서 실수로 어딘가를 검색해야한다는 것을 알 수 있습니다.

+0

나는 실제로 어떤 일이 일어 났는지를 알아 냈지만 답을 잊어 버렸다. 당신은 당신의 대답에 있습니다. 그러나 내 솔루션은 비슷하지만 간단합니다. 방금'var x = 0.0'과 같은 변수를 선언하고 초기화하면 모든 것이 매력처럼 작동합니다. 어쨌든, 세부 설명에 대한 귀하의 답변을 수락합니다. – sooon