UNPKG

polygonjs-engine

Version:

node-based webgl 3D engine https://polygonjs.com

111 lines (110 loc) 4.14 kB
import {ObjectUtils as ObjectUtils2} from "../../../../../core/ObjectUtils"; import {CoreMaterial} from "../../../../../core/geometry/Material"; import {GlobalsTextureHandler} from "../../../gl/code/globals/Texture"; export class ParticlesSystemGpuRenderController { constructor(node) { this.node = node; this._particles_group_objects = []; this._all_shader_names = []; this._all_uniform_names = []; this.globals_handler = new GlobalsTextureHandler(GlobalsTextureHandler.UV_VARYING); } set_shaders_by_name(shaders_by_name) { this._shaders_by_name = shaders_by_name; this._all_shader_names = []; this._all_uniform_names = []; this._shaders_by_name.forEach((shader, name) => { this._all_shader_names.push(name); this._all_uniform_names.push(`texture_${name}`); }); this.reset_render_material(); } assign_render_material() { if (!this._render_material) { return; } for (let object3d of this._particles_group_objects) { const object = object3d; if (object.geometry) { object.material = this._render_material; CoreMaterial.apply_custom_materials(object, this._render_material); object.matrixAutoUpdate = false; object.updateMatrix(); } } this._render_material.needsUpdate = true; this.update_render_material_uniforms(); } update_render_material_uniforms() { if (!this._render_material) { return; } let uniform_name; let shader_name; for (let i = 0; i < this._all_shader_names.length; i++) { shader_name = this._all_shader_names[i]; uniform_name = this._all_uniform_names[i]; const texture = this.node.gpu_controller.getCurrentRenderTarget(shader_name)?.texture; if (texture) { this._render_material.uniforms[uniform_name].value = texture; CoreMaterial.assign_custom_uniforms(this._render_material, uniform_name, texture); } } } reset_render_material() { this._render_material = void 0; this._particles_group_objects = []; } render_material() { return this._render_material; } get initialized() { return this._render_material != null; } init_core_group(core_group) { for (let child of core_group.objectsWithGeo()) { this._particles_group_objects.push(child); } } async init_render_material() { const assembler = this.node.assemblerController?.assembler; if (this._render_material) { return; } if (this.node.p.material.isDirty()) { await this.node.p.material.compute(); } const mat_node = this.node.p.material.found_node(); if (mat_node) { if (assembler) { const new_texture_allocations_json = assembler.texture_allocations_controller.toJSON(this.node.scene()); const matNodeAssemblerController = mat_node.assemblerController; if (matNodeAssemblerController) { this.globals_handler.set_texture_allocations_controller(assembler.texture_allocations_controller); matNodeAssemblerController.set_assembler_globals_handler(this.globals_handler); } if (!this._texture_allocations_json || JSON.stringify(this._texture_allocations_json) != JSON.stringify(new_texture_allocations_json)) { this._texture_allocations_json = ObjectUtils2.cloneDeep(new_texture_allocations_json); if (matNodeAssemblerController) { matNodeAssemblerController.set_compilation_required_and_dirty(); } } } const container = await mat_node.requestContainer(); this._render_material = container.material(); } else { this.node.states.error.set("render material not valid"); } if (this._render_material) { const uniforms = this._render_material.uniforms; for (let uniform_name of this._all_uniform_names) { const uniform_value = {value: null}; uniforms[uniform_name] = uniform_value; if (this._render_material) { CoreMaterial.init_custom_material_uniforms(this._render_material, uniform_name, uniform_value); } } } this.assign_render_material(); } }