Ejemplo n.º 1
0
    public MeshAndColors createMesh(VoxelModelChunk voxelChunk, ShapeNodeChunk shape)
    {
        Vector3 ve = rotateVector(new Vector3(voxelChunk.sizeChunk.sizeX, voxelChunk.sizeChunk.sizeY, voxelChunk.sizeChunk.sizeZ), shape.transform);

        int sizeX = (int)Math.Abs(ve.x);
        int sizeY = (int)Math.Abs(ve.y);
        int sizeZ = (int)Math.Abs(ve.z);

        // WTF? Dont drink and code!!!
        Vector3 correction = new Vector3((ve.x < 0) ? Math.Abs(ve.x) - 1 : 0, (ve.y < 0) ? Math.Abs(ve.y) - 1 : 0, (ve.z < 0) ? Math.Abs(ve.z) - 1 : 0);

        RenderVoxel[,,] voxelArray = new RenderVoxel[sizeX, sizeY, sizeZ];

        float maxX = 0;
        float maxY = 0;
        float maxZ = 0;
        float minX = sizeX;
        float minY = sizeY;
        float minZ = sizeZ;

        foreach (Voxel voxel in voxelChunk.voxels)
        {
            Vector3 rotVec = rotateVector(new Vector3(voxel.x, voxel.y, voxel.z), shape.transform) + correction;
            voxelArray[(int)rotVec.x, (int)rotVec.y, (int)rotVec.z] = new RenderVoxel(voxel.colorIndex);
            if (rotVec.x < minX)
            {
                minX = rotVec.x;
            }
            if (rotVec.y < minY)
            {
                minY = rotVec.y;
            }
            if (rotVec.z < minZ)
            {
                minZ = rotVec.z;
            }
            if (rotVec.x > maxX)
            {
                maxX = rotVec.x;
            }
            if (rotVec.y > maxY)
            {
                maxY = rotVec.y;
            }
            if (rotVec.z > maxZ)
            {
                maxZ = rotVec.z;
            }
        }

        shape.singleCenter = new Vector3((float)Math.Ceiling(minX + (maxX - minX) / 2f), minZ, (float)Math.Ceiling(minY + (maxY - minY) / 2f));
        Vector3 shifts = shape.singleCenter;

        MeshAndColors meshAndColors = createMeshFromVoxelArray(voxelArray, shifts);

        return(meshAndColors);
    }
Ejemplo n.º 2
0
    void Run()
    {
        string[] splits = input.Split(' ');
        size = new Vector3Int(
            Convert.ToInt32(splits[3] + splits[2] + splits[1] + splits[0], 16),
            Convert.ToInt32(splits[7] + splits[6] + splits[5] + splits[4], 16),
            Convert.ToInt32(splits[11] + splits[10] + splits[9] + splits[8], 16));
        RenderVoxel[,,] voxelArray = new RenderVoxel[size.x, size.y, size.z];
        int x = 0;
        int y = 0;
        int z = 0;

        for (int i = 16; i < splits.Length; i += 2)
        {
            int n     = Convert.ToInt32(splits[i], 16) + 1;
            int color = Convert.ToInt32(splits[i + 1], 16);
            for (int k = 0; k < n; k++)
            {
                x++;
                if (x == size.x)
                {
                    y++;
                    x = 0;
                    if (y == size.y)
                    {
                        y = 0;
                        z++;
                    }
                }
                if (color == 0)
                {
                    continue;
                }
                if (z >= size.z)
                {
                    break;
                }
                voxelArray[x, y, z] = new RenderVoxel(color);
            }
        }

        MagicaRenderer renderer      = new MagicaRenderer();
        MeshAndColors  meshAndColors = renderer.createMeshFromVoxelArray(voxelArray, Vector3.zero);
        GameObject     go            = new GameObject();

        Color32[] colors = new Color32[meshAndColors.colors.Count];
        for (int i = 0; i < meshAndColors.colors.Count; i++)
        {
            int c = meshAndColors.colors[i];
            colors[i] = new Color(c / 256f, c / 256f, c / 256f, 1);
        }
        meshAndColors.mesh.colors32                 = colors;
        (go.AddComponent <MeshFilter>()).mesh       = meshAndColors.mesh;
        (go.AddComponent <MeshRenderer>()).material = Resources.Load("VertexShading", typeof(Material)) as Material;
    }
Ejemplo n.º 3
0
    public MeshAndColors createMeshFromVoxelArray(RenderVoxel[,,] voxelArray, Vector3 shifts)
    {
        // gravity first
        for (int z = 0; z < voxelArray.GetLength(2); z++)
        {
            for (int y = 0; y < voxelArray.GetLength(1); y++)
            {
                for (int x = 0; x < voxelArray.GetLength(0); x++)
                {
                    if (voxelArray[x, y, z] == null)
                    {
                        continue;
                    }

                    if (x > 0 && voxelArray[x - 1, y, z] != null)
                    {
                        voxelArray[x, y, z].sides     ^= RenderVoxel.LEFT;
                        voxelArray[x - 1, y, z].sides ^= RenderVoxel.RIGHT;
                    }
                    if (y > 0 && voxelArray[x, y - 1, z] != null)
                    {
                        voxelArray[x, y, z].sides     ^= RenderVoxel.BACK;
                        voxelArray[x, y - 1, z].sides ^= RenderVoxel.FRONT;
                    }
                    if (z > 0 && voxelArray[x, y, z - 1] != null)
                    {
                        voxelArray[x, y, z].sides     ^= RenderVoxel.DOWN;
                        voxelArray[x, y, z - 1].sides ^= RenderVoxel.UP;
                    }
                }
            }
        }


        List <int> colors;
        Mesh       mesh;

        List <Vector3> vertices   = new List <Vector3>();
        List <int>     triangles  = new List <int>();
        List <int>     colorOrder = new List <int>();

        colors = new List <int>();
        for (int _z = 0; _z < voxelArray.GetLength(2); _z++)
        {
            for (int _y = 0; _y < voxelArray.GetLength(1); _y++)
            {
                for (int _x = 0; _x < voxelArray.GetLength(0); _x++)
                {
                    RenderVoxel renderVoxel = voxelArray[_x, _y, _z];

                    if (renderVoxel == null || renderVoxel.sides == 0)
                    {
                        continue;
                    }

                    float x = _x - shifts.x;
                    float y = _y - shifts.z;
                    float z = _z - shifts.y;

                    if (!colorOrder.Contains(renderVoxel.color))
                    {
                        colorOrder.Add(renderVoxel.color);
                    }

                    if ((renderVoxel.sides & RenderVoxel.DOWN) != 0)
                    {
                        int startIndex = vertices.Count;

                        vertices.Add(new Vector3(x * size, z * size, y * size));
                        vertices.Add(new Vector3((x + 1) * size, z * size, y * size));
                        vertices.Add(new Vector3(x * size, z * size, (y + 1) * size));
                        vertices.Add(new Vector3((x + 1) * size, z * size, (y + 1) * size));
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);

                        triangles.Add(startIndex);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex + 3);
                        triangles.Add(startIndex + 2);
                    }
                    if ((renderVoxel.sides & RenderVoxel.UP) != 0)
                    {
                        int startIndex = vertices.Count;

                        vertices.Add(new Vector3(x * size, (z + 1) * size, y * size));
                        vertices.Add(new Vector3((x + 1) * size, (z + 1) * size, y * size));
                        vertices.Add(new Vector3(x * size, (z + 1) * size, (y + 1) * size));
                        vertices.Add(new Vector3((x + 1) * size, (z + 1) * size, (y + 1) * size));
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);

                        triangles.Add(startIndex);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 3);
                        triangles.Add(startIndex + 1);
                    }
                    if ((renderVoxel.sides & RenderVoxel.LEFT) != 0)
                    {
                        int startIndex = vertices.Count;

                        vertices.Add(new Vector3(x * size, z * size, y * size));
                        vertices.Add(new Vector3(x * size, z * size, (y + 1) * size));
                        vertices.Add(new Vector3(x * size, (z + 1) * size, (y + 1) * size));
                        vertices.Add(new Vector3(x * size, (z + 1) * size, y * size));
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);

                        triangles.Add(startIndex);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 3);
                        triangles.Add(startIndex);
                    }

                    if ((renderVoxel.sides & RenderVoxel.RIGHT) != 0)
                    {
                        int startIndex = vertices.Count;

                        vertices.Add(new Vector3((x + 1) * size, z * size, y * size));
                        vertices.Add(new Vector3((x + 1) * size, z * size, (y + 1) * size));
                        vertices.Add(new Vector3((x + 1) * size, (z + 1) * size, (y + 1) * size));
                        vertices.Add(new Vector3((x + 1) * size, (z + 1) * size, y * size));
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);

                        triangles.Add(startIndex);
                        triangles.Add(startIndex + 3);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex);
                    }
                    if ((renderVoxel.sides & RenderVoxel.BACK) != 0)
                    {
                        int startIndex = vertices.Count;

                        vertices.Add(new Vector3(x * size, z * size, y * size));
                        vertices.Add(new Vector3(x * size, (z + 1) * size, y * size));
                        vertices.Add(new Vector3((x + 1) * size, (z + 1) * size, y * size));
                        vertices.Add(new Vector3((x + 1) * size, z * size, y * size));
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);

                        triangles.Add(startIndex);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 3);
                        triangles.Add(startIndex);
                    }
                    if ((renderVoxel.sides & RenderVoxel.FRONT) != 0)
                    {
                        int startIndex = vertices.Count;

                        vertices.Add(new Vector3(x * size, z * size, (y + 1) * size));
                        vertices.Add(new Vector3(x * size, (z + 1) * size, (y + 1) * size));
                        vertices.Add(new Vector3((x + 1) * size, (z + 1) * size, (y + 1) * size));
                        vertices.Add(new Vector3((x + 1) * size, z * size, (y + 1) * size));
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);
                        colors.Add(renderVoxel.color);

                        triangles.Add(startIndex);
                        triangles.Add(startIndex + 3);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 2);
                        triangles.Add(startIndex + 1);
                        triangles.Add(startIndex);
                    }
                }
            }
        }

        mesh             = new Mesh();
        mesh.indexFormat = UnityEngine.Rendering.IndexFormat.UInt32;
        mesh.vertices    = vertices.ToArray();
        mesh.triangles   = triangles.ToArray();
        mesh.RecalculateNormals();

        MeshAndColors meshAndColors = new MeshAndColors();

        meshAndColors.mesh   = mesh;
        meshAndColors.colors = colors;

        return(meshAndColors);
    }
Ejemplo n.º 4
0
    public GameObject ImportMagicaVoxelFileAssets(string path)
    {
        GameObject levelGo = new GameObject(Path.GetFileName(path));

        string fileName = Path.GetFileName(path);

        List <GameObject> gameObjects = new List <GameObject>();
        Dictionary <string, GameObject> namedGameObjects = new Dictionary <string, GameObject>();

        Chunk           mainChunk      = MagicaVoxelReader.ReadMagicaChunks(path);
        List <Material> colorMaterials = ImportColors(mainChunk);
        List <string>   names          = new List <string>();
        List <string>   doubleNames    = new List <string>();

        string localPath      = AssetDatabase.GenerateUniqueAssetPath(Path.Combine("Assets", "ImportedPrefabs", fileName));
        string materialFolder = Path.Combine("Assets", "ImportedPrefabs", fileName, "Materials");
        string meshFolder     = Path.Combine("Assets", "ImportedPrefabs", fileName, "Meshes");

        if (!AssetDatabase.IsValidFolder(localPath))
        {
            AssetDatabase.CreateFolder(Path.Combine("Assets", "ImportedPrefabs"), fileName);
        }
        if (!AssetDatabase.IsValidFolder(materialFolder))
        {
            AssetDatabase.CreateFolder(localPath, "Materials");
        }
        if (!AssetDatabase.IsValidFolder(meshFolder))
        {
            AssetDatabase.CreateFolder(localPath, "Meshes");
        }

        for (int m = 0; m < colorMaterials.Count; m++)
        {
            AssetDatabase.CreateAsset(colorMaterials[m], Path.Combine(materialFolder, "Color_" + m + ".mat"));
        }

        for (int i = 0; i < mainChunk.children.Count; i++)
        {
            Chunk chunk = mainChunk.children[i];
            if (chunk is VoxelModelChunk)
            {
                VoxelModelChunk voxelChunk = (VoxelModelChunk)chunk;

                foreach (ShapeNodeChunk shape in voxelChunk.shapes)
                {
                    TransformNodeChunk transformNodeChunk = shape.transform;

                    bool isPotentialAsset = false;
                    while (transformNodeChunk != null)
                    {
                        if (transformNodeChunk.attributes.Count > 0 && transformNodeChunk.attributes.ContainsKey("_name"))
                        {
                            isPotentialAsset = true;
                            break;
                        }
                    }
                    if (!isPotentialAsset)
                    {
                        continue;
                    }

                    MeshAndColors   meshAndColors = createMesh(voxelChunk, shape);
                    List <Material> materials     = new List <Material>();
                    foreach (int color in meshAndColors.colors)
                    {
                        materials.Add(colorMaterials[color - 1]);
                    }

                    GameObject go = new GameObject();
                    gameObjects.Add(go);
                    ObjectAttributes script = go.AddComponent <ObjectAttributes>();

                    MeshRenderer renderer = go.AddComponent <MeshRenderer>();
                    renderer.materials = materials.ToArray();
                    MeshFilter filter = go.AddComponent <MeshFilter>();
                    filter.mesh = meshAndColors.mesh;

                    Vector3 shift = Vector3.zero; //new Vector3(script.singleCenter.x, 0, script.singleCenter.y);
                    while (transformNodeChunk != null)
                    {
                        if (transformNodeChunk.attributes.Count > 0 && transformNodeChunk.attributes.ContainsKey("_name"))
                        {
                            string name = transformNodeChunk.attributes["_name"];
                            script.names.Add(name);

                            if (names.Contains(name))
                            {
                                if (!doubleNames.Contains(name))
                                {
                                    doubleNames.Add(name);
                                }
                            }
                            else
                            {
                                names.Add(name);
                                namedGameObjects.Add(name, go);
                            }
                        }

                        if (transformNodeChunk.frameAttributes[0].ContainsKey("_r"))
                        {
                            script.rotations.Add(transformNodeChunk.frameAttributes[0]["_r"]);
                        }

                        Vector3[] rotationMatrix = getRotationMatrix(transformNodeChunk);
                        script.rotationMatrices.Add(rotationMatrix);

                        if (transformNodeChunk.frameAttributes[0].ContainsKey("_t"))
                        {
                            string[] coords       = transformNodeChunk.frameAttributes[0]["_t"].Split(' ');
                            Vector3  currentShift = new Vector3(float.Parse(coords[0]) / 10f, float.Parse(coords[2]) / 10f, float.Parse(coords[1]) / 10f);;
                            script.magicaTransitions.Add(currentShift);
                            shift += currentShift;
                        }
                        if (transformNodeChunk.group != null && transformNodeChunk.group.transform != null)
                        {
                            transformNodeChunk = transformNodeChunk.group.transform;
                        }
                        else
                        {
                            transformNodeChunk = null;
                        }
                    }

                    Vector3 ve = rotateVector(new Vector3(voxelChunk.sizeChunk.sizeX, voxelChunk.sizeChunk.sizeY, voxelChunk.sizeChunk.sizeZ), shape.transform);

                    script.magicaTotalSize = new Vector3(Math.Abs(ve.x), Math.Abs(ve.z), Math.Abs(ve.y));

                    script.bottomCenterOfVoxelMass = shape.singleCenter / 10f;

                    script.centerOfMagicaMass = new Vector3((float)Math.Floor((double)(Math.Abs(ve.x) / 2f)) / 10f, (float)Math.Floor((double)(Math.Abs(ve.z) / 2f)) / 10f, (float)Math.Floor((double)(Math.Abs(ve.y) / 2f)) / 10f);
                    script.parentVoxFile      = Path.GetFileName(path);
                    //shift -= script.trans;
                    shift += new Vector3(script.bottomCenterOfVoxelMass.x - script.centerOfMagicaMass.x, script.bottomCenterOfVoxelMass.y - script.centerOfMagicaMass.y, script.bottomCenterOfVoxelMass.z - script.centerOfMagicaMass.z);
                    //shift += (script.bottomCenterOfVoxelMass - script.centerOfMagicaMass);

                    go.transform.localScale = new Vector3(0.1f, 0.1f, 0.1f);
                    go.transform.position   = shift;
                    go.name             = script.names[0];
                    go.transform.parent = levelGo.transform;
                }
            }
        }

        // remove double named objects since we cannot insert them properly
        foreach (string name in doubleNames)
        {
            namedGameObjects.Remove(name);
        }

        foreach (GameObject g in namedGameObjects.Values)
        {
            TeardownProperties teardownProperties = g.AddComponent <TeardownProperties>();

            // Create the new Prefab.
            AssetDatabase.CreateAsset(g.GetComponent <MeshFilter>().sharedMesh, Path.Combine(meshFolder, g.name.Replace(" ", "_") + ".mesh"));
            AssetDatabase.SaveAssets();
            PrefabUtility.SaveAsPrefabAssetAndConnect(g, Path.Combine("Assets", "ImportedPrefabs", fileName, g.name.Replace(" ", "_") + ".prefab"), InteractionMode.UserAction);
        }

        PrefabUtility.SaveAsPrefabAssetAndConnect(levelGo, Path.Combine("Assets", "ImportedPrefabs", fileName, fileName + ".prefab"), InteractionMode.UserAction);

        return(levelGo);
    }
Ejemplo n.º 5
0
    public GameObject ImportMagicaVoxelFile(string path)
    {
        Material vertexMaterial = Resources.Load("VertexShading", typeof(Material)) as Material;

        GameObject levelGo = new GameObject(Path.GetFileName(path));

        levelGo.AddComponent <TeardownProperties>();
        MagicaImportedFile magicaImportedFile = levelGo.AddComponent <MagicaImportedFile>();

        magicaImportedFile.voxFile = Path.GetFileName(path);

        List <GameObject> gameObjects = new List <GameObject>();
        Dictionary <string, GameObject> namedGameObjects = new Dictionary <string, GameObject>();

        Chunk           mainChunk      = MagicaVoxelReader.ReadMagicaChunks(path);
        List <Material> colorMaterials = ImportColors(mainChunk);
        List <string>   names          = new List <string>();
        List <string>   doubleNames    = new List <string>();

        for (int i = 0; i < mainChunk.children.Count; i++)
        {
            Chunk chunk = mainChunk.children[i];
            if (chunk is VoxelModelChunk)
            {
                VoxelModelChunk voxelChunk = (VoxelModelChunk)chunk;

                foreach (ShapeNodeChunk shape in voxelChunk.shapes)
                {
                    MeshAndColors meshAndColors = createMesh(voxelChunk, shape);
                    Color[]       colors        = new Color[meshAndColors.colors.Count];
                    for (int c = 0; c < meshAndColors.colors.Count; c++)
                    {
                        colors[c] = colorMaterials[meshAndColors.colors[c] - 1].color;
                    }
                    meshAndColors.mesh.colors = colors;

                    TransformNodeChunk transformNodeChunk = shape.transform;
                    GameObject         go = new GameObject();
                    gameObjects.Add(go);
                    ObjectAttributes script   = go.AddComponent <ObjectAttributes>();
                    MeshRenderer     renderer = go.AddComponent <MeshRenderer>();
                    renderer.material = vertexMaterial;
                    MeshFilter filter = go.AddComponent <MeshFilter>();
                    filter.mesh = meshAndColors.mesh;

                    Vector3 shift = Vector3.zero; //new Vector3(script.singleCenter.x, 0, script.singleCenter.y);
                    while (transformNodeChunk != null)
                    {
                        if (transformNodeChunk.attributes.Count > 0 && transformNodeChunk.attributes.ContainsKey("_name"))
                        {
                            string name = transformNodeChunk.attributes["_name"];
                            script.names.Add(name);

                            if (names.Contains(name))
                            {
                                if (!doubleNames.Contains(name))
                                {
                                    doubleNames.Add(name);
                                }
                            }
                            else
                            {
                                names.Add(name);
                                namedGameObjects.Add(name, go);
                            }
                        }

                        if (transformNodeChunk.frameAttributes[0].ContainsKey("_r"))
                        {
                            script.rotations.Add(transformNodeChunk.frameAttributes[0]["_r"]);
                        }

                        Vector3[] rotationMatrix = getRotationMatrix(transformNodeChunk);
                        script.rotationMatrices.Add(rotationMatrix);

                        if (transformNodeChunk.frameAttributes[0].ContainsKey("_t"))
                        {
                            string[] coords       = transformNodeChunk.frameAttributes[0]["_t"].Split(' ');
                            Vector3  currentShift = new Vector3(float.Parse(coords[0]) / 10f, float.Parse(coords[2]) / 10f, float.Parse(coords[1]) / 10f);;
                            script.magicaTransitions.Add(currentShift);
                            shift += currentShift;
                        }
                        if (transformNodeChunk.group != null && transformNodeChunk.group.transform != null)
                        {
                            transformNodeChunk = transformNodeChunk.group.transform;
                        }
                        else
                        {
                            transformNodeChunk = null;
                        }
                    }

                    Vector3 ve = rotateVector(new Vector3(voxelChunk.sizeChunk.sizeX, voxelChunk.sizeChunk.sizeY, voxelChunk.sizeChunk.sizeZ), shape.transform);

                    script.magicaTotalSize = new Vector3(Math.Abs(ve.x), Math.Abs(ve.z), Math.Abs(ve.y));

                    script.bottomCenterOfVoxelMass = shape.singleCenter / 10f;

                    script.centerOfMagicaMass = new Vector3((float)Math.Floor((double)(Math.Abs(ve.x) / 2f)) / 10f, (float)Math.Floor((double)(Math.Abs(ve.z) / 2f)) / 10f, (float)Math.Floor((double)(Math.Abs(ve.y) / 2f)) / 10f);
                    script.parentVoxFile      = Path.GetFileName(path);
                    //shift -= script.trans;
                    shift += new Vector3(script.bottomCenterOfVoxelMass.x - script.centerOfMagicaMass.x, script.bottomCenterOfVoxelMass.y - script.centerOfMagicaMass.y, script.bottomCenterOfVoxelMass.z - script.centerOfMagicaMass.z);
                    //shift += (script.bottomCenterOfVoxelMass - script.centerOfMagicaMass);

                    go.transform.localScale = new Vector3(0.1f, 0.1f, 0.1f);
                    go.transform.position   = shift;

                    go.transform.parent = levelGo.transform;

                    if (script.names.Count > 0)
                    {
                        go.name = script.names[0];
                    }
                }
            }
        }

        // remove double named objects since we cannot insert them properly
        foreach (string name in doubleNames)
        {
            namedGameObjects.Remove(name);
        }

        foreach (GameObject g in gameObjects)
        {
            if (namedGameObjects.Values.Contains(g))
            {
                TeardownProperties teardownProperties = g.AddComponent <TeardownProperties>();
            }
        }

        return(levelGo);
    }