| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								#pragma once
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								#include <macros.h>
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								#include "primitive/simple/sphere.hpp"
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								#include "primitive/simple/cylinder.hpp"
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
									
										
									
								
							 | 
							
								
							 | 
							
								template <typename Surface, typename Tag>
							 | 
						
					
						
							| 
								
							 | 
							
								
									
										
									
								
							 | 
							
								
							 | 
							
								using surface_container_t = tagged_flat_object_map_mp<internal::paired_model_matrix_ptr_t, Surface, Tag>;
							 | 
						
					
						
							| 
								
							 | 
							
								
									
										
									
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								using plane_container_t    = surface_container_t<internal::plane_t, detail::plane_surface_tag>;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								using sphere_container_t   = surface_container_t<internal::sphere_face_t, detail::sphere_surface_tag>;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								using cylinder_container_t = surface_container_t<internal::cylinder_face_t, detail::cylinder_surface_tag>;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								EXTERN_C struct PE_API primitive_data_center_t {
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    primitive_data_center_t() noexcept;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    ~primitive_data_center_t() noexcept;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
									
										
									
								
							 | 
							
								
							 | 
							
								    flat_object_map_mp<internal::paired_model_matrix, internal::paired_model_matrix> transform_blocks{};
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    // all other data depend on cached transform_blocks
							 | 
						
					
						
							| 
								
							 | 
							
								
									
										
									
								
							 | 
							
								
							 | 
							
								    using surface_containers = std::variant<plane_container_t, sphere_container_t, cylinder_container_t>;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    std::array<surface_containers, static_cast<uint8_t>(surface_type::max_count)> surfaces{};
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    auto require_transform_block(const internal::paired_model_matrix& matrix) -> internal::paired_model_matrix_ptr_t;
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    void require_surface(surface_type                               type,
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								                         const internal::paired_model_matrix_ptr_t& matrix,
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								                         marked_subface_ptr_t<subface>&             subface);
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    void release_transform_block(const internal::paired_model_matrix& matrix);
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								    void release_surface(surface_type type, const marked_subface_ptr_t<subface>& subface);
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								};
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								namespace internal
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								{
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								PE_API primitive* new_primitive(primitive_type type);
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								PE_API primitive* copy_primitive(primitive* ptr);
							 | 
						
					
						
							| 
								
							 | 
							
								
							 | 
							
								
							 | 
							
								} // namespace internal
							 |