예제 #1
0
    public static void Initialize()
    {
        if (isInitialized)
        {
            return;
        }
        isInitialized                = true;
        gpuFrustumShader             = Resources.Load <ComputeShader>("GpuFrustumCulling");
        shadMask.shadowmaskMaterial  = new Material(Shader.Find("Hidden/ShadowMask"));
        shadMask.afterLightingBuffer = new CommandBuffer();
        TextAsset pointText = Resources.Load <TextAsset>("MapPoints");
        TextAsset infoText  = Resources.Load <TextAsset>("MapInfos");

        byte[]      pointBytes  = pointText.bytes;
        byte[]      infoBytes   = infoText.bytes;
        Point *     points      = null;
        ObjectInfo *infos       = null;
        int         pointLength = 0;
        int         infoLength  = 0;

        fixed(void *ptr = &pointBytes[0])
        {
            points      = (Point *)ptr;
            pointLength = pointBytes.Length / Point.SIZE;
        }

        fixed(void *ptr = &infoBytes[0])
        {
            infos      = (ObjectInfo *)ptr;
            infoLength = infoBytes.Length / ObjectInfo.SIZE;
        }

        NativeArray <Point>      allPoints = new NativeArray <Point>(pointLength, Allocator.Temp, NativeArrayOptions.UninitializedMemory);
        NativeArray <ObjectInfo> allInfos  = new NativeArray <ObjectInfo>(infoLength, Allocator.Temp, NativeArrayOptions.UninitializedMemory);
        void *destination = allPoints.GetUnsafePtr();

        UnsafeUtility.MemCpy(destination, points, pointBytes.Length);
        destination = allInfos.GetUnsafePtr();
        UnsafeUtility.MemCpy(destination, infos, infoBytes.Length);
        PipelineFunctions.Initialize(ref baseBuffer, allPoints, allInfos);
        for (int i = 0; i < cascadeShadowMapVP.Length; ++i)
        {
            cascadeShadowMapVP[i] = Matrix4x4.identity;
        }
        Resources.UnloadAsset(pointText);
        Resources.UnloadAsset(infoText);
        allInfos.Dispose();
        allPoints.Dispose();
    }
    private void OnDisable()
    {
        testMesh = GetComponent <MeshFilter>().sharedMesh;
        Vector3[]            vert       = testMesh.vertices;
        Vector3[]            nor        = testMesh.normals;
        Vector4[]            tangents   = testMesh.tangents;
        Vector2[]            uv0        = testMesh.uv;
        int[]                tris       = testMesh.triangles;
        UnsafeList <Cluster> v          = GetAllCluster(tris, vert);
        var clusterDistance             = GetClusterDistances(v, vert);
        List <Cluster[]> clusterGroups  = GetClusters(clusterDistance, v);
        uint             infoByteSize   = (uint)(clusterGroups.Count * ObjectInfo.SIZE);
        ObjectInfo *     infos          = (ObjectInfo *)UnsafeUtility.Malloc(infoByteSize, 16, Allocator.Temp);
        uint             pointsByteSize = (uint)(clusterGroups.Count * 64 * Point.SIZE);
        Point *          points         = (Point *)UnsafeUtility.Malloc(pointsByteSize, 16, Allocator.Temp);

        for (int i = 0, pointsCount = 0; i < clusterGroups.Count; ++i)
        {
            Cluster *group = (Cluster *)UnsafeUtility.Malloc(UnsafeUtility.SizeOf <Cluster>() * clusterGroups[i].Length, 16, Allocator.Temp);
            for (int a = 0; a < clusterGroups[i].Length; ++a)
            {
                group[a] = clusterGroups[i][a];
            }
            int *      decodedGroup = (int *)group;
            ObjectInfo info;
            info.position = Vector3.zero;
            info.extent   = Vector3.zero;
            Vector3 *allPositions = (Vector3 *)UnsafeUtility.Malloc(sizeof(Vector3) * 64, 16, Allocator.Temp);
            for (int a = 0; a < 64; ++a)
            {
                int vertID = decodedGroup[a];

                Point p;
                p.vertex        = vert[vertID];
                p.vertex        = transform.localToWorldMatrix.MultiplyPoint(p.vertex);
                allPositions[a] = p.vertex;
                info.position  += p.vertex;
                p.normal        = nor[vertID];
                p.normal        = transform.localToWorldMatrix.MultiplyVector(p.normal);
                p.tangent       = tangents[vertID];
                Vector3 tangentXYZ = new Vector3(p.tangent.x, p.tangent.y, p.tangent.z);
                tangentXYZ          = transform.localToWorldMatrix.MultiplyVector(tangentXYZ);
                p.tangent.x         = tangentXYZ.x;
                p.tangent.y         = tangentXYZ.y;
                p.tangent.z         = tangentXYZ.z;
                p.texcoord          = uv0[vertID];
                points[pointsCount] = p;
                pointsCount++;
            }
            info.position /= 64f;
            for (int a = 0; a < 64; ++a)
            {
                Vector3 point = allPositions[a];
                Vector3 dir   = point - info.position;
                dir         = dir.Abs();
                info.extent = dir.Max(info.extent);
            }
            infos[i] = info;
            byte[] pointsBytes = new byte[pointsByteSize];
            byte[] infosBytes  = new byte[infoByteSize];
            fixed(byte *pointStartPtr = &pointsBytes[0])
            {
                UnsafeUtility.MemCpy(pointStartPtr, points, pointsByteSize);
            }

            fixed(byte *infoStartPtr = &infosBytes[0])
            {
                UnsafeUtility.MemCpy(infoStartPtr, infos, infoByteSize);
            }

            ByteArrayToFile("Assets/Resources/MapPoints.bytes", pointsBytes);
            ByteArrayToFile("Assets/Resources/MapInfos.bytes", infosBytes);
            UnsafeUtility.Free(allPositions, Allocator.Temp);
            UnsafeUtility.Free(group, Allocator.Temp);
            UnsafeUtility.Free(points, Allocator.Temp);
            UnsafeUtility.Free(infos, Allocator.Temp);
        }
    }