public void UploadInstanceData_TextureWithPlugin()
        {
            BatchRendererUtil.DataConversion cv34 = BatchRendererUtil.DataConversion.Float3ToFloat4;
            BatchRendererUtil.DataConversion cv44 = BatchRendererUtil.DataConversion.Float4ToFloat4;
            if (m_instance_texture.translation.format == TextureFormat.RGBAHalf)
            {
                cv34 = BatchRendererUtil.DataConversion.Float3ToHalf4;
                cv44 = BatchRendererUtil.DataConversion.Float4ToHalf4;
            }

            BatchRendererUtil.CopyToTexturePlugin(m_instance_texture.translation, m_instance_data.translation, m_instance_count, cv34);
            if (m_enable_rotation)
            {
                BatchRendererUtil.CopyToTexturePlugin(m_instance_texture.rotation, m_instance_data.rotation, m_instance_count, cv44);
            }
            if (m_enable_scale)
            {
                BatchRendererUtil.CopyToTexturePlugin(m_instance_texture.scale, m_instance_data.scale, m_instance_count, cv34);
            }
            if (m_enable_color)
            {
                BatchRendererUtil.CopyToTexturePlugin(m_instance_texture.color, m_instance_data.color, m_instance_count, cv44);
            }
            if (m_enable_emission)
            {
                BatchRendererUtil.CopyToTexturePlugin(m_instance_texture.emission, m_instance_data.emission, m_instance_count, cv44);
            }
            if (m_enable_uv_offset)
            {
                BatchRendererUtil.CopyToTexturePlugin(m_instance_texture.uv_offset, m_instance_data.uv_offset, m_instance_count, cv44);
            }
        }
        public override void OnEnable()
        {
            base.OnEnable();
            if (m_mesh == null)
            {
                return;
            }

            if (m_data_transfer_mode == DataTransferMode.Buffer && !SystemInfo.supportsComputeShaders)
            {
                Debug.Log("BatchRenderer: ComputeBuffer is not available. fallback to Texture data transfer mode.");
                m_data_transfer_mode = DataTransferMode.Texture;
            }
            if (m_data_transfer_mode == DataTransferMode.TextureWithPlugin && !BatchRendererUtil.IsCopyToTextureAvailable())
            {
                Debug.Log("BatchRenderer: CopyToTexture plugin is not available. fallback to Texture data transfer mode.");
                m_data_transfer_mode = DataTransferMode.Texture;
            }

            m_instance_data = new InstanceData();
            if (m_data_transfer_mode == DataTransferMode.Buffer)
            {
                m_instance_buffer = new InstanceBuffer();
            }
            else
            {
                m_instance_texture = new InstanceTexture();
            }

            ResetGPUData();
        }
            Texture2D CreateDataTexture(int num_max_instances)
            {
                int       width  = BatchRendererUtil.data_texture_width;
                int       height = BatchRendererUtil.ceildiv(num_max_instances, width);
                Texture2D r      = null;

                if (SystemInfo.SupportsRenderTextureFormat(RenderTextureFormat.ARGBFloat))
                {
                    r = new Texture2D(width, height, TextureFormat.RGBAFloat, false);
                }
                else if (SystemInfo.SupportsRenderTextureFormat(RenderTextureFormat.ARGBHalf))
                {
                    Debug.Log("BatchRenderer: float texture is not available. use half texture instead");
                    r = new Texture2D(width, height, TextureFormat.RGBAHalf, false);
                }
                else
                {
                    Debug.Log("BatchRenderer: both float and half texture are not available. give up.");
                    return(null);
                }


                r.filterMode = FilterMode.Point;
                return(r);
            }
示例#4
0
        void IssueDrawCall(CommandBuffer cb)
        {
            if (properties == null)
            {
                properties = new MaterialPropertyBlock();
            }

            var cont     = GetComponent <IBezierPatchContainer>();
            var bpatches = cont.GetBezierPatches();
            var aabbs    = cont.GetAABBs();

            if (m_buf_vertices == null)
            {
                BatchRendererUtil.CreateVertexBuffer(m_bound_mesh, ref m_buf_vertices, ref m_num_vertices, BatchRendererUtil.VertexFormat.P);
                properties.SetBuffer("_Vertices", m_buf_vertices);
            }
            if (m_buf_bpatches == null)
            {
                m_buf_bpatches = new ComputeBuffer(bpatches.Length, BezierPatchRaw.size);
                properties.SetBuffer("_BezierPatches", m_buf_bpatches);
            }
            if (m_buf_aabbs == null)
            {
                m_buf_aabbs = new ComputeBuffer(aabbs.Length, BezierPatchAABB.size);
                properties.SetBuffer("_AABBs", m_buf_aabbs);
            }
            m_buf_bpatches.SetData(bpatches);
            m_buf_aabbs.SetData(aabbs);

            cb.DrawProcedural(Matrix4x4.identity, m_material, 0, MeshTopology.Triangles, m_num_vertices, bpatches.Length, properties);
        }
        public virtual void ResetGPUResoures()
        {
            ReleaseGPUResources();

            m_buf_trail_params   = new ComputeBuffer(1, MPGPTrailParams.size);
            m_buf_trail_entities = new ComputeBuffer(m_max_entities, MPGPTrailEntity.size);
            m_buf_trail_history  = new ComputeBuffer(m_max_entities * m_max_trail_history, MPGPTrailHistory.size);
            m_buf_trail_vertices = new ComputeBuffer(m_max_entities * m_max_trail_history, MPGPTrailVertex.size);
            {
                int[] indices = new int[(m_max_trail_history - 1) * 6];
                int[] ls      = new int[6] {
                    0, 3, 1, 0, 2, 3
                };
                for (int i = 0; i < m_max_trail_history - 1; ++i)
                {
                    indices[i * 6 + 0] = i * 2 + ls[0];
                    indices[i * 6 + 1] = i * 2 + ls[1];
                    indices[i * 6 + 2] = i * 2 + ls[2];
                    indices[i * 6 + 3] = i * 2 + ls[3];
                    indices[i * 6 + 4] = i * 2 + ls[4];
                    indices[i * 6 + 5] = i * 2 + ls[5];
                }
                m_expanded_mesh = BatchRendererUtil.CreateIndexOnlyMesh(m_max_trail_history * 2, indices, out m_instances_par_batch);
            }
            UpdateGPUResources();
        }
        public virtual void Flush()
        {
            if (m_expanded_mesh == null || m_instance_count == 0)
            {
                m_instance_count = 0;
                return;
            }

            Vector3 scale = m_trans.localScale;

            m_expanded_mesh.bounds = new Bounds(m_trans.position,
                                                new Vector3(m_bounds_size.x * scale.x, m_bounds_size.y * scale.y, m_bounds_size.y * scale.y));
            m_instance_count = Mathf.Min(m_instance_count, m_max_instances);
            m_batch_count    = BatchRendererUtil.ceildiv(m_instance_count, m_instances_par_batch);

            for (int i = 0; i < m_actual_materials.Count; ++i)
            {
                var a = m_actual_materials[i];
                while (a.Count < m_batch_count)
                {
                    Material m = CloneMaterial(m_materials[i], a.Count);
                    a.Add(m);
                }
            }
            UpdateGPUResources();
            IssueDrawCall();
            m_instance_count = m_batch_count = 0;
        }
        public virtual void OnEnable()
        {
            m_trans = GetComponent <Transform>();

            if (m_materials == null || m_materials.Length == 0)
            {
                m_materials = new Material[1] {
                    m_material
                };
            }

            m_actual_materials = new List <List <Material> >();
            while (m_actual_materials.Count < m_materials.Length)
            {
                m_actual_materials.Add(new List <Material>());
            }

            if (m_expanded_mesh == null && m_mesh != null)
            {
                m_expanded_mesh = BatchRendererUtil.CreateExpandedMesh(m_mesh, m_max_instances, out m_instances_par_batch);
                m_expanded_mesh.UploadMeshData(true);
            }

            int layer_mask = m_layer_selector.value;

            for (int i = 0; i < 32; ++i)
            {
                if ((layer_mask & (1 << i)) != 0)
                {
                    m_layer = i;
                    m_layer_selector.value = 1 << i;
                    break;
                }
            }
        }
        public void ResetGPUData()
        {
            ReleaseGPUData();

            m_instance_data.Resize(m_max_instances);
            if (m_instance_buffer != null)
            {
                m_instance_buffer.Allocate(m_max_instances);
            }
            BatchRendererUtil.CreateVertexBuffer(m_mesh, ref m_vertex_buffer, ref m_vertex_count);

            {
                Material m = m_material;
                if (m_enable_rotation)
                {
                    m.EnableKeyword("ENABLE_INSTANCE_ROTATION");
                }
                if (m_enable_scale)
                {
                    m.EnableKeyword("ENABLE_INSTANCE_SCALE");
                }
                if (m_enable_emission)
                {
                    m.EnableKeyword("ENABLE_INSTANCE_EMISSION");
                }
                if (m_enable_color)
                {
                    m.EnableKeyword("ENABLE_INSTANCE_COLOR");
                }
                if (m_enable_uv_offset)
                {
                    m.EnableKeyword("ENABLE_INSTANCE_UVOFFSET");
                }

                if (m_instance_buffer != null)
                {
                    m.SetBuffer("g_vertices", m_vertex_buffer);
                    m.SetBuffer("g_instance_buffer_t", m_instance_buffer.translation);
                    m.SetBuffer("g_instance_buffer_r", m_instance_buffer.rotation);
                    m.SetBuffer("g_instance_buffer_s", m_instance_buffer.scale);
                    m.SetBuffer("g_instance_buffer_color", m_instance_buffer.color);
                    m.SetBuffer("g_instance_buffer_emission", m_instance_buffer.emission);
                    m.SetBuffer("g_instance_buffer_uv", m_instance_buffer.uv_offset);
                }
            }
            {
                m_cb      = new CommandBuffer();
                m_cb.name = "ProceduralGBuffer";
                m_cb.DrawProcedural(Matrix4x4.identity, m_material, 0, MeshTopology.Triangles, m_vertex_count, m_max_instances);
                m_camera.AddCommandBuffer(CameraEvent.AfterGBuffer, m_cb);
            }

            // set default values
            UpdateGPUResources();
        }
        public void UploadInstanceData_Texture()
        {
            if (m_data_transfer_buffer == null)
            {
                var t = m_instance_texture.translation;
                if (t.format == TextureFormat.RGBAFloat)
                {
                    m_data_transfer_buffer = new byte[t.width * t.height * 16];
                }
                else if (t.format == TextureFormat.RGBAHalf)
                {
                    m_data_transfer_buffer = new byte[t.width * t.height * 8];
                }
                else
                {
                    Debug.Log("should not happen");
                }
            }

            BatchRendererUtil.CopyToTextureCS(m_instance_texture.translation, m_instance_data.translation, m_instance_count, m_data_transfer_buffer);
            if (m_enable_rotation)
            {
                BatchRendererUtil.CopyToTextureCS(m_instance_texture.rotation, m_instance_data.rotation, m_instance_count, m_data_transfer_buffer);
            }
            if (m_enable_scale)
            {
                BatchRendererUtil.CopyToTextureCS(m_instance_texture.scale, m_instance_data.scale, m_instance_count, m_data_transfer_buffer);
            }
            if (m_enable_color)
            {
                BatchRendererUtil.CopyToTextureCS(m_instance_texture.color, m_instance_data.color, m_instance_count, m_data_transfer_buffer);
            }
            if (m_enable_emission)
            {
                BatchRendererUtil.CopyToTextureCS(m_instance_texture.emission, m_instance_data.emission, m_instance_count, m_data_transfer_buffer);
            }
            if (m_enable_uv_offset)
            {
                BatchRendererUtil.CopyToTextureCS(m_instance_texture.uv_offset, m_instance_data.uv_offset, m_instance_count, m_data_transfer_buffer);
            }
        }