배경:
C ++ 및 OpenGL을 사용하여 엔터티 구성 요소 시스템 유형 아키텍처를위한 간단한 3D 렌더링 시스템을 설계하고 있습니다. 이 시스템은 렌더러와 장면 그래프로 구성됩니다. 렌더러의 첫 번째 반복을 마치면 장면 그래프를 ECS 아키텍처에 배포 할 수 있습니다. 현재로서는 자리 표시 자입니다. 가능하면 렌더러의 목표는 다음과 같습니다.
- 단순성 . 이것은 연구 프로젝트를위한 것이며 시스템을 쉽게 변경하고 확장 할 수 있기를 원합니다 (따라서 ECS 접근 방식).
- 성능 . 내 장면에는 많은 작은 모델과 많은 기하학을 가진 큰 볼륨이있을 수 있습니다. 렌더 프레임마다 OGL 컨텍스트 및 버퍼 지오메트리에서 객체를 획득하는 것은 허용되지 않습니다. 캐시 누락을 피하기 위해 데이터 지역성을 목표로하고 있습니다.
- 유연성 . 스프라이트, 모델 및 볼륨 (복셀)을 렌더링 할 수 있어야합니다.
- 분리됨 . 렌더러를 작성한 후 장면 그래프가 핵심 ECS 아키텍처로 리팩터링 될 수 있습니다.
- 모듈 식 . 내 장면 그래프를 변경하지 않고 다른 렌더러에서 교체 할 수 있으면 좋을 것입니다.
- 참조 투명도 는 어느 시점에서나 유효한 장면을 제공 할 수 있으며 항상 해당 장면에 대해 동일한 이미지를 렌더링한다는 의미입니다. 특히이 목표는 반드시 필요한 것은 아닙니다. 장면 직렬화를 단순화하고 (씬을 저장하고로드 할 수 있어야 함) 테스트 / 실험 목적으로 런타임 중에 다른 장면으로 교체 할 수있는 유연성을 제공한다고 생각했습니다.
문제와 아이디어 :
나는 시도하는 몇 가지 다른 접근법을 생각해 냈지만 각 렌더 노드에 대해 OGL 리소스 (VAO, VBO, 쉐이더 등)를 캐시하는 방법으로 어려움을 겪고 있습니다. 다음은 지금까지 생각한 다양한 캐싱 개념입니다.
- 중앙 집중식 캐시. 각 장면 노드에는 ID가 있고 렌더러에는 ID를 렌더링 노드에 매핑하는 캐시가 있습니다. 각 렌더 노드에는 형상과 관련된 VAO 및 VBO가 포함됩니다. 캐시 미스는 리소스를 획득하고 캐시의 렌더링 노드에 지오메트리를 매핑합니다. 지오메트리가 변경되면 더티 플래그가 설정됩니다. 렌더러가 장면 노드를 반복하는 동안 더티 지오메트리 플래그가 표시되면 렌더 노드를 사용하여 데이터를 다시 버퍼링합니다. 장면 노드가 제거되면 이벤트가 브로드 캐스트되고 렌더러는 리소스를 해제하면서 캐시에서 관련 렌더 노드를 제거합니다. 또는 노드가 제거 대상으로 표시되고 렌더러가 노드를 제거해야합니다. 이 접근법은 목표 6을 가장 가깝게 달성하면서도 4와 5를 고려한다고 생각합니다. 2는 어레이 액세스 대신 맵 조회를 통해 데이터 복잡성의 추가 복잡성 및 손실로 인해 어려움을 겪고 있습니다.
- 분산 캐시 . 각 장면 노드에 렌더 노드가 있다는 점을 제외하면 위와 유사합니다. 지도 조회를 무시합니다. 데이터 지역성을 다루기 위해 렌더러에 렌더 노드를 저장할 수 있습니다. 그런 다음 장면 노드는 대신 노드를 렌더링하기위한 포인터를 가질 수 있으며 렌더러는 캐시 미스에 포인터를 설정합니다. 이런 종류의 개체는 엔터티 구성 요소 접근 방식을 모방한다고 생각하므로 나머지 아키텍처와 일치 할 것입니다. 여기서 문제는 이제 씬 노드가 렌더러 구현 관련 데이터를 보유한다는 것입니다. 렌더링 스프라이트와 볼륨과 같이 렌더러에서 렌더링되는 방식을 변경하면 렌더 노드를 변경하거나 장면 노드에 "구성 요소"를 더 추가해야합니다 (씬 그래프도 변경됨). 플러스 측면에서 이것은 첫 번째 반복 렌더러를 시작하고 실행하는 가장 간단한 방법처럼 보입니다.
- 분산 메타 데이터 . 렌더러 캐시 메타 데이터 컴포넌트는 각 장면 노드에 저장됩니다. 이 데이터는 구현 고유의 것이 아니라 캐시에 필요한 ID, 유형 및 기타 관련 데이터를 보유합니다. 그런 다음 ID를 사용하여 캐시 조회를 어레이에서 직접 수행 할 수 있으며, 유형은 사용할 렌더링 방식 유형 (예 : 스프라이트 및 볼륨)을 나타낼 수 있습니다.
- 방문자 + 분산 매핑 . 렌더러는 방문자이고 장면 노드는 방문자 패턴의 요소입니다. 각 장면 노드에는 렌더러 만 조작하는 캐시 키 (메타 데이터와 같지만 ID)가 있습니다. 일반화 된 맵 조회 대신 ID를 배열에 사용할 수 있습니다. 렌더러는 씬 노드가 씬 노드의 유형에 따라 다른 렌더링 기능을 디스패치 할 수 있도록하며, 모든 캐시에서 ID를 사용할 수 있습니다. 기본 또는 범위를 벗어난 ID는 캐시 누락을 나타냅니다.
이 문제를 어떻게 해결 하시겠습니까? 아니면 어떤 제안이 있습니까? 내 벽을 읽어 주셔서 감사합니다!