public void SetMatrixArray( int propertyId, Matrix4x4[] value, bool isInstanced) { if (isInstanced) { materialPropertyBlock.SetMatrixArray(propertyId, value); renderer.SetPropertyBlock(materialPropertyBlock); instancedProperties.Add(propertyId); } else { material.SetMatrixArray(propertyId, value); } }
private int CreateChunkIndex(Material material) { if (!m_MaterialToChunkIndex.TryGetValue(material, out int chunkIndex)) { var propertyBlock = new MaterialPropertyBlock(); // In order instanced and non instanced rendering to work with _NormalToWorld // We need to make sure array is created with maximum size propertyBlock.SetMatrixArray("_NormalToWorld", new Matrix4x4[250]); entityChunks.Add(new DecalEntityChunk() { material = material }); cachedChunks.Add(new DecalCachedChunk() { propertyBlock = propertyBlock, }); culledChunks.Add(new DecalCulledChunk()); drawCallChunks.Add(new DecalDrawCallChunk() { subCallCounts = new NativeArray <int>(1, Allocator.Persistent) }); m_CombinedChunks.Add(new CombinedChunks()); m_CombinedChunkRemmap.Add(0); m_MaterialToChunkIndex.Add(material, chunkCount); return(chunkCount++); } return(chunkIndex); }
public override void Render(CommandBuffer commandBuffer, bool monitor) { if (!_manager.IsZEDReady) { return; } if (_manager.HMDSyncRotation.x == 0 && _manager.HMDSyncRotation.y == 0 && _manager.HMDSyncRotation.z == 0 && _manager.HMDSyncRotation.w == 0) { return; } var mat = Matrix4x4.TRS(_camera.transform.position, _manager.HMDSyncRotation, Vector3.one); // var rotMatrix = Matrix4x4.Rotate(_manager.HMDSyncRotation * Quaternion.Inverse(_camera.transform.rotation)); _transformMatrices[0] = mat * _planeMatrices[0]; _transformMatrices[1] = mat * _planeMatrices[1]; _propertyBlock.SetMatrixArray("_TransformMatrices", _transformMatrices); _propertyBlock.SetTexture("_DepthTextureLeft", _depthTexture); _propertyBlock.SetTexture("_DepthTextureRight", _depthRightTexture); // _propertyBlock.SetTexture("_NormalTextureLeft", _normalTexture); // _propertyBlock.SetTexture("_NormalTextureRight", _normalRightTexture); _propertyBlock.SetTexture("_ColorTextureLeft", _colorTexture); _propertyBlock.SetTexture("_ColorTextureRight", _colorRightTexture); commandBuffer.DrawMesh(_quadMesh, Matrix4x4.identity, _material, 0, -1, _propertyBlock); }
public override void RenderSky(BuiltinSkyParameters builtinParams, bool stereo, bool renderForCubemap) { m_SkyHDRIMaterial.SetTexture(RenderGraphShaderIDs._Cubemap, m_HdriSkyParams.skyHDRI); m_SkyHDRIMaterial.SetVector(RenderGraphShaderIDs._SkyParam, new Vector4(m_HdriSkyParams.exposure, m_HdriSkyParams.multiplier, m_HdriSkyParams.rotation, 0.0f)); // This matrix needs to be updated at the draw call frequency. if (stereo) { m_PropertyBlock.SetMatrixArray(RenderGraphShaderIDs._PixelCoordToViewDirWS, builtinParams.pixelCoordToViewDirMatrix); builtinParams.commandBuffer.DrawProcedural(Matrix4x4.identity, m_SkyHDRIMaterial, renderForCubemap ? 0 : 1, MeshTopology.Triangles, 3, 1, m_PropertyBlock); //CoreUtils.DrawFullScreen(builtinParams.commandBuffer, m_SkyHDRIMaterial, m_PropertyBlock, renderForCubemap ? 0 : 1); } else { m_PropertyBlock.SetMatrixArray(RenderGraphShaderIDs._PixelCoordToViewDirWS, builtinParams.pixelCoordToViewDirMatrix); CoreUtils.DrawFullScreen(builtinParams.commandBuffer, m_SkyHDRIMaterial, m_PropertyBlock, renderForCubemap ? 0 : 2); } }
private void DebugSetup(Camera camera, MaterialPropertyBlock materialPropertyBlock) { int tileNum = drawInfo.tileX * drawInfo.tileY; Matrix4x4[] lookingView = new Matrix4x4[tileNum]; Matrix4x4[] lookingProjection = new Matrix4x4[tileNum]; Matrix4x4[] lookingVp = new Matrix4x4[tileNum]; int counter = 0; for (int i = 0; i < drawInfo.tileY; ++i) { for (int j = 0; j < drawInfo.tileX; ++j) { Matrix4x4 projMatrix = camera.projectionMatrix; Matrix4x4 viewMatrix = camera.worldToCameraMatrix; float adjustedDistance = LookingGlassUtil.GetAdjustedDistance(perCameraInfo.fov, perCameraInfo.size); float verticalAngle = 0.0f; float horizontalAngle = LookingGlassUtil.AngleAtView(counter, tileNum); float offsetX = adjustedDistance * Mathf.Tan(horizontalAngle * Mathf.Deg2Rad); float offsetY = adjustedDistance * Mathf.Tan(verticalAngle * Mathf.Deg2Rad); // view matrix viewMatrix.m03 -= offsetX; viewMatrix.m13 -= offsetY; // proj matrix projMatrix.m02 -= offsetX / (perCameraInfo.size * camera.aspect); projMatrix.m12 -= offsetY / perCameraInfo.size; lookingView[counter] = viewMatrix; lookingProjection[counter] = projMatrix; lookingVp[counter] = viewMatrix * projMatrix; ++counter; } } materialPropertyBlock.SetMatrixArray("LookingView", lookingView); materialPropertyBlock.SetMatrixArray("LookingProjection", lookingProjection); materialPropertyBlock.SetMatrixArray("LookingVP", lookingVp); }
public void SetData(UIForiaData data, StructList <Matrix4x4> matrices) { Array.Copy(matrices.array, 0, transformData, 0, matrices.size); Array.Copy(data.colors.array, 0, colorData, 0, data.colors.size); Array.Copy(data.objectData0.array, 0, objectData, 0, data.objectData0.size); Array.Copy(data.objectData1.array, 0, miscData, 0, data.objectData1.size); Array.Copy(data.clipUVs.array, 0, clipUVs, 0, data.clipUVs.size); Array.Copy(data.clipRects.array, 0, clipRects, 0, data.clipRects.size); Array.Copy(data.cornerData.array, 0, cornerData, 0, data.cornerData.size); matBlock.SetMatrixArray(s_TransformDataKey, transformData); matBlock.SetVectorArray(s_ColorDataKey, colorData); matBlock.SetVectorArray(s_ObjectDataKey, objectData); matBlock.SetVectorArray(s_MiscDataKey, miscData); matBlock.SetVectorArray(s_ClipUVKey, clipUVs); matBlock.SetVectorArray(s_ClipRectKey, clipRects); matBlock.SetVectorArray(s_CornerDataKey, cornerData); matBlock.SetFloat(s_DPIScaleKey, 1f / Application.dpiScaleFactor); if (data.mainTexture != null) { matBlock.SetTexture(s_MainTextureKey, data.mainTexture); } if (data.clipTexture != null) { matBlock.SetTexture(s_ClipTextureKey, data.clipTexture); } if (data.fontData.fontAsset != null) { FontData fontData = data.fontData; matBlock.SetVector(s_FontDataScales, new Vector4(fontData.gradientScale, fontData.scaleRatioA, fontData.scaleRatioB, fontData.scaleRatioC)); matBlock.SetVector(s_FontTextureSize, new Vector4(fontData.textureWidth, fontData.textureHeight, 0, 0)); matBlock.SetTexture(s_FontTexture, fontData.fontAsset.atlas); } }
public void SetData(ClipBatch data) { Array.Copy(data.transforms.array, 0, transformData, 0, data.transforms.size); Array.Copy(data.objectData.array, 0, objectData, 0, data.objectData.size); Array.Copy(data.colorData.array, 0, colorData, 0, data.colorData.size); matBlock.SetMatrixArray(s_TransformDataKey, transformData); matBlock.SetVectorArray(s_ColorDataKey, colorData); matBlock.SetVectorArray(s_ObjectDataKey, objectData); if (data.texture != null) { material.SetTexture(s_MainTextureKey, data.texture); } }
public void UpdateMaterialblcok() { block.SetFloat("_TextureIndex", textureIndex); for (int i = 0; i < characterList.Count; i++) { Character.InstancedData data = characterList[i].GetInstancedData(); for (int j = 0; j < CharacterData.boneCount; j++) { boneRSMatrix[j][i] = data.boneTransformMatrix[j]; bonePosition[j][i] = data.bonePosition[j]; } } for (int j = 0; j < CharacterData.boneCount; j++) { block.SetMatrixArray(boneMatrixNameArray[j], boneRSMatrix[j]); block.SetVectorArray(bonePositionNameArray[j], bonePosition[j]); } }
public static void RenderLod(RenderManager.CameraInfo cameraInfo, NetInfo.LodValue lod) { NetManager netMan = Singleton <NetManager> .instance; MaterialPropertyBlock materialBlock = netMan.m_materialBlock; materialBlock.Clear(); Mesh mesh; int upperLoadCount; if (lod.m_lodCount <= 1) { mesh = lod.m_key.m_mesh.m_mesh1; upperLoadCount = 1; } else if (lod.m_lodCount <= 4) { mesh = lod.m_key.m_mesh.m_mesh4; upperLoadCount = 4; } else { mesh = lod.m_key.m_mesh.m_mesh8; upperLoadCount = 8; } for (int i = lod.m_lodCount; i < upperLoadCount; i++) { lod.m_leftMatrices[i] = default(Matrix4x4); lod.m_rightMatrices[i] = default(Matrix4x4); lod.m_meshScales[i] = default; lod.m_objectIndices[i] = default; lod.m_meshLocations[i] = cameraInfo.m_forward * -100000f; } materialBlock.SetMatrixArray(netMan.ID_LeftMatrices, lod.m_leftMatrices); materialBlock.SetMatrixArray(netMan.ID_RightMatrices, lod.m_rightMatrices); materialBlock.SetVectorArray(netMan.ID_MeshScales, lod.m_meshScales); materialBlock.SetVectorArray(netMan.ID_ObjectIndices, lod.m_objectIndices); materialBlock.SetVectorArray(netMan.ID_MeshLocations, lod.m_meshLocations); if (lod.m_surfaceTexA != null) { materialBlock.SetTexture(netMan.ID_SurfaceTexA, lod.m_surfaceTexA); materialBlock.SetTexture(netMan.ID_SurfaceTexB, lod.m_surfaceTexB); materialBlock.SetVector(netMan.ID_SurfaceMapping, lod.m_surfaceMapping); lod.m_surfaceTexA = null; lod.m_surfaceTexB = null; } if (lod.m_heightMap != null) { materialBlock.SetTexture(netMan.ID_HeightMap, lod.m_heightMap); materialBlock.SetVector(netMan.ID_HeightMapping, lod.m_heightMapping); materialBlock.SetVector(netMan.ID_SurfaceMapping, lod.m_surfaceMapping); lod.m_heightMap = null; } if (mesh != null) { Bounds bounds = default(Bounds); bounds.SetMinMax(lod.m_lodMin - new Vector3(100f, 100f, 100f), lod.m_lodMax + new Vector3(100f, 100f, 100f)); mesh.bounds = bounds; lod.m_lodMin = new Vector3(100000f, 100000f, 100000f); lod.m_lodMax = new Vector3(-100000f, -100000f, -100000f); netMan.m_drawCallData.m_lodCalls++; netMan.m_drawCallData.m_batchedCalls += lod.m_lodCount - 1; Graphics.DrawMesh(mesh, Matrix4x4.identity, lod.m_material, lod.m_key.m_layer, null, 0, materialBlock); } lod.m_lodCount = 0; }
public void Update() { if (!isDrawing) { return; } if (bone == null) { bone = gpuSkinning.model.GetBoneByHierarchyName(jointPath); if (bone != null) { boneIndex = System.Array.IndexOf(gpuSkinning.model.bones, bone); } } if (bone == null) { return; } if (instancingMatrices == null) { instancingMatrices = new Matrix4x4[gpuSkinning.model.spawnObjects.Length]; playMode0_mpb = new MaterialPropertyBlock(); hierarchyToObjectMatrices = new Matrix4x4[gpuSkinning.model.spawnObjects.Length]; playMode1_mpb = new MaterialPropertyBlock(); } if (gpuSkinning.playingMode.IsPlayMode0()) { Matrix4x4 hierarchyToObject = bone.hierarchyMatrix * localMatrix; var spawnObjects = gpuSkinning.model.spawnObjects; int numSpawnObjects = spawnObjects == null ? 0 : spawnObjects.Length; for (int i = 0; i < numSpawnObjects; ++i) { var spawnObject = spawnObjects[i]; // (1) // I think "transform.hasChanged" is not a reliable api in a complex case, it would be better to write your own game logic instead. if (spawnObject.transform.hasChanged) { spawnObject.transform.hasChanged = false; // (2) // Huge amount of accessing "transform.localToWorldMatrix" will spend much cpu time, so cache these in a buffer, updating once data is dirty. instancingMatrices[i] = spawnObject.transform.localToWorldMatrix; } if (!isBuiltInDrawMeshInstancedSupported || !gpuSkinning.instancing.IsGPUInstancingOn()) { // (3) // Matrix multiplication is a slow operation. Optimize it. Matrix4x4 hierarchyToWorld = instancingMatrices[i] * hierarchyToObject; // (4) // Invoke many times of "Graphics.DrawMesh" api will cause performance impact. // So "Graphics.DrawMesh" is not better than MeshRenderer in some cases. // Here is just a example for joint. Overhead should be considered in production. Graphics.DrawMesh(mesh, hierarchyToWorld, material, 0); } } if (isBuiltInDrawMeshInstancedSupported && gpuSkinning.instancing.IsGPUInstancingOn()) { playMode0_mpb.SetMatrix(shaderPropId_HierarchyToObjectMat, hierarchyToObject); #if UNITY_5_5 || UNITY_5_6 || UNITY_5_7 || UNITY_5_8 || UNITY_5_9 || UNITY_6 || UNITY_2017 || UNITY_2018 // etc. // (5) // https://forum.unity3d.com/threads/graphics-drawmesh-drawmeshinstanced-fundamentally-bottlenecked-by-the-cpu.429120/ Graphics.DrawMeshInstanced(mesh, 0, material, instancingMatrices, numSpawnObjects, playMode0_mpb); #endif } } else { var spawnObjects = gpuSkinning.model.spawnObjects; int numSpawnObjects = spawnObjects == null ? 0 : spawnObjects.Length; bool isInstancingOn = gpuSkinning.instancing.IsGPUInstancingOn(); int fps = gpuSkinning.model.boneAnimations[0].fps; float animLength = gpuSkinning.model.boneAnimations[0].length; for (int i = 0; i < numSpawnObjects; ++i) { var spawnObject = spawnObjects[i]; // (1) if (spawnObject.transform.hasChanged) { spawnObject.transform.hasChanged = false; // (2) instancingMatrices[i] = spawnObject.transform.localToWorldMatrix; } float timeOffset = isInstancingOn ? spawnObject.timeOffset_instancingOn : spawnObject.timeOffset_instancingOff; int frameIndex = (int)(((gpuSkinning.second + timeOffset) * fps) % (animLength * fps)); int frameStartIndex = frameIndex * gpuSkinning.matrixTexture.numHierarchyMatricesPerFrame; Matrix4x4 hierarchyToObject = gpuSkinning.matrixTexture.hierarchyMatrices[frameStartIndex + boneIndex]; if (!isBuiltInDrawMeshInstancedSupported || !gpuSkinning.instancing.IsGPUInstancingOn()) { // (3) Matrix4x4 hierarchyToWorld = instancingMatrices[i] * hierarchyToObject * localMatrix; // (4) Graphics.DrawMesh(mesh, hierarchyToWorld, material, 0); } else { hierarchyToObjectMatrices[i] = hierarchyToObject; } } if (isBuiltInDrawMeshInstancedSupported && gpuSkinning.instancing.IsGPUInstancingOn()) { playMode1_mpb.SetMatrixArray(shaderPorpId_HierarchyToObjectMats, hierarchyToObjectMatrices); playMode1_mpb.SetMatrix(shaderPropId_JointLocalMatrix, localMatrix); #if UNITY_5_5 || UNITY_5_6 || UNITY_5_7 || UNITY_5_8 || UNITY_5_9 || UNITY_6 || UNITY_2017 || UNITY_2018 // etc. // (5) Graphics.DrawMeshInstanced(mesh, 0, material, instancingMatrices, numSpawnObjects, playMode1_mpb); #endif } } }
public static int SetMatrixArray(IntPtr l) { int result; try { int total = LuaDLL.lua_gettop(l); if (LuaObject.matchType(l, total, 2, typeof(string), typeof(Matrix4x4[]))) { MaterialPropertyBlock materialPropertyBlock = (MaterialPropertyBlock)LuaObject.checkSelf(l); string name; LuaObject.checkType(l, 2, out name); Matrix4x4[] values; LuaObject.checkArray <Matrix4x4>(l, 3, out values); materialPropertyBlock.SetMatrixArray(name, values); LuaObject.pushValue(l, true); result = 1; } else if (LuaObject.matchType(l, total, 2, typeof(int), typeof(Matrix4x4[]))) { MaterialPropertyBlock materialPropertyBlock2 = (MaterialPropertyBlock)LuaObject.checkSelf(l); int nameID; LuaObject.checkType(l, 2, out nameID); Matrix4x4[] values2; LuaObject.checkArray <Matrix4x4>(l, 3, out values2); materialPropertyBlock2.SetMatrixArray(nameID, values2); LuaObject.pushValue(l, true); result = 1; } else if (LuaObject.matchType(l, total, 2, typeof(string), typeof(List <Matrix4x4>))) { MaterialPropertyBlock materialPropertyBlock3 = (MaterialPropertyBlock)LuaObject.checkSelf(l); string name2; LuaObject.checkType(l, 2, out name2); List <Matrix4x4> values3; LuaObject.checkType <List <Matrix4x4> >(l, 3, out values3); materialPropertyBlock3.SetMatrixArray(name2, values3); LuaObject.pushValue(l, true); result = 1; } else if (LuaObject.matchType(l, total, 2, typeof(int), typeof(List <Matrix4x4>))) { MaterialPropertyBlock materialPropertyBlock4 = (MaterialPropertyBlock)LuaObject.checkSelf(l); int nameID2; LuaObject.checkType(l, 2, out nameID2); List <Matrix4x4> values4; LuaObject.checkType <List <Matrix4x4> >(l, 3, out values4); materialPropertyBlock4.SetMatrixArray(nameID2, values4); LuaObject.pushValue(l, true); result = 1; } else { LuaObject.pushValue(l, false); LuaDLL.lua_pushstring(l, "No matched override function SetMatrixArray to call"); result = 2; } } catch (Exception e) { result = LuaObject.error(l, e); } return(result); }
void RenderAsInstances(List <TTexturePointBlockAndScore> Instances) { var mf = GetComponent <MeshFilter> (); var mr = GetComponent <MeshRenderer> (); var TriangleMesh = mf.sharedMesh; var TriangleMaterial = mr.sharedMaterial; int PointSplit = TriangleMesh.triangles.Length / 3; List <Matrix4x4> InstanceCaches = null; int RunningPointCount = 0; var MtxIdentityList = new List <Matrix4x4> () { Matrix4x4.identity }; int InstancesDrawn = 0; int WastedPoints = 0; int BiggestInstanceCacheCount = 0; System.Action Flush = () => { if (InstanceCaches != null && InstanceCaches.Count > 0) { var InstanceUniforms = new MaterialPropertyBlock(); InstanceUniforms.SetMatrixArray(TexturePointBlocksUniform, InstanceCaches); InstanceUniforms.SetFloat(TexturePointBlockCountUniform, InstanceCaches.Count); // draw with instancing to draw in scene editor, but we don't wanna use it on mobile because of north american s6 #if UNITY_EDITOR Graphics.DrawMeshInstanced(TriangleMesh, 0, TriangleMaterial, MtxIdentityList, InstanceUniforms); #else Graphics.DrawMesh(TriangleMesh, Matrix4x4.identity, TriangleMaterial, 0, Camera.main, 0, InstanceUniforms); #endif InstancesDrawn += MtxIdentityList.Count; BiggestInstanceCacheCount = Mathf.Max(BiggestInstanceCacheCount, InstanceCaches.Count); } InstanceCaches = new List <Matrix4x4>(); RunningPointCount = 0; }; // init Flush(); // iterate and break up for (int i = 0; i < Instances.Count; i++) { var Block = Instances [i].Block; if (InstanceCaches.Count >= TTEXTUREPOINTBLOCK_MAX) { WastedPoints += PointSplit - RunningPointCount; Flush(); } // have we overflowed? if (Block.LodPointCount + RunningPointCount > PointSplit) { WastedPoints += PointSplit - RunningPointCount; Flush(); } RunningPointCount += Block.LodPointCount; InstanceCaches.Add(Block.DataMatrix); } Flush(); #if UNITY_EDITOR //Debug.Log ("Meshes drawn=" + InstancesDrawn + " wasted points=" + WastedPoints + " BiggestInstanceCacheCount="+BiggestInstanceCacheCount); #endif }