어레이의 Vertex
구조체에 제공된 완전한 정점 데이터가 있다고 가정합니다. 버텍스 쉐이더에 데이터를 보내기 위해서, 을 호출하여 Vertex
멤버와 셰이더의 매개 변수 사이의 올바른 매핑을 설정해야합니다.glVertexAttribPointer 템플릿의 멤버 오프셋 가져 오기
오픈 템플릿 함수 glVertexAttribPointer
을 멋진 템플릿 방식으로 캡슐화하려고합니다.
glVertexAttribPointer
GLUint index
- 핸들을GLint size
- 구성 요소의 수 (대한 무관 이 문제)GLenum type
- 타입 (GL_FLOAT
,GL_SHORT
을 represeting 열거 값 등)GLboolean normalized
- [0..1] 또는 [-1..1] 로의 정규화 (이 문제와 관련 없음)GLsizei stride
- 연속 된 정점 요소 간 바이트 차이. 내 경우에는 그 크기가Vertex
입니다.const GLvoid* pointer
- 데이터 시작과 관련하여 첫 번째 요소에 대해 오프셋. 제 경우에는, 그것은Vertex
의 시작과 관련하여 회원의 상쇄가 될 것입니다.
나는 다음과 같은 해결책을 온 내 목표를 달성하기 opengl_type
가
template <typename WholeVertex, typename Element>
void attribute(GLuint shaderProgram, const char* name, Element WholeVertex::* memberPointer) {
GLint handle = glGetAttribLocation(shaderProgram, name);
glVertexAttribPointer (
handle,
opengl_type<Element>::arity,
opengl_type<Element>::type,
GL_FALSE,
sizeof(WholeVertex),
(const GLvoid*)(memberPointer) //error
);
}
A A 지정된 형태에 대한 올바른 GLenum 값을 계산 내 자신의 특성 클래스입니다.
불행히도이 솔루션은 멤버 포인터가 단지 정수 오프셋이고 캐스팅 될 수 있다고 가정합니다. (const GLvoid*)
입니다. 내 지식으로는 WholeVertex
에 standard layout이 있다는 가정하에 사실입니다. 아직도, 일반적인 경우에 그것은 사실이 아닐 수도 있고 컴파일러는 이런 종류의 캐스트를 완성하는 것을 금지합니다. 사실 객체가없는 memberPointer
으로는 아무 것도 할 수 없습니다.
내가 원하는 것을 계산할 수있는 매크로와 비슷한 기능을 가진 매크로가 있다는 것을 알았지 만, 멤버 이름이 인수로 사용되므로 이름을 알 수없는 경우 사용할 수 없게됩니다.
그렇다면이 래퍼 함수를 구현하는 방법에 대해 알고 계신가요? 아마도 오프셋을 계산하는 다른 방법일까요? 또는 그것을 다른 종류의 매개 변수로 전달할 수 있습니까?
'Element WholeVertex :: * memberPointer'는 실제로 나를 혼란스럽게하지만, 구조체의 멤버에게 포인터를 전달하고있는 것 같습니다. 구조체의 첫 번째 요소 주소를 알고 있다면 할 수 있습니다. 오프셋을 계산하기위한 포인터 연산. 구조체의 멤버 이름을 모른 채 쉽게이 작업을 수행 할 수 있지만 추가 포인터를 어딘가에 저장해야합니다. –
'attribute'와 궁극적으로'glVertexAttribPointer'는 실제 데이터에서 작동하지 않습니다 (따라서'this' 포인터 나 첫 번째 요소에 대한 포인터가 없습니다). 이 함수들은 단순히 실제 데이터가 제공되기 전에 GL 시스템에 오프셋을 알리는'WholeVertex' 타입을 기술합니다. – CygnusX1
@Andron : '.. 날 믿어.'예. 그것은 멤버에 대한 (오프셋 된) 포인터이다. 하나는'& MyVertex :: nx'와 같은 형태로 전달 될 수 있는데,'.nx'는 일부 struct MyVertex에서 일반적인 데이터 멤버의 시작이됩니다. CygnusX1이 지적했듯이. 그것은 MyVertex 형식의 인스턴스화 된 객체와 아무런 관련이 없습니다. – violet313