Ejemplo n.º 1
0
    MeshData GetMesh(NBTChunk chunk, Vector3Int pos)
    {
        byte eastType     = chunk.GetBlockByte(pos + Vector3Int.right);
        bool eastConnect  = !NBTGeneratorManager.IsTransparent(eastType) || NBTGeneratorManager.IsFence(eastType);
        byte southType    = chunk.GetBlockByte(pos + Vector3Int.back);
        bool southConnect = !NBTGeneratorManager.IsTransparent(southType) || NBTGeneratorManager.IsFence(southType);
        byte westType     = chunk.GetBlockByte(pos + Vector3Int.left);
        bool westConnect  = !NBTGeneratorManager.IsTransparent(westType) || NBTGeneratorManager.IsFence(westType);
        byte northType    = chunk.GetBlockByte(pos + Vector3Int.forward);
        bool northConnect = !NBTGeneratorManager.IsTransparent(northType) || NBTGeneratorManager.IsFence(northType);

        int index = 0;

        if (westConnect)
        {
            index += 8;
        }
        if (northConnect)
        {
            index += 4;
        }
        if (eastConnect)
        {
            index += 2;
        }
        if (southConnect)
        {
            index += 1;
        }

        return(meshes[index]);
    }
Ejemplo n.º 2
0
    //input is local position
    public bool HasOpaqueBlock(int xInChunk, int worldY, int zInChunk)
    {
        byte type = GetBlockByte(xInChunk, worldY, zInChunk);

        return(!NBTGeneratorManager.IsTransparent(type));
    }
Ejemplo n.º 3
0
    public override void AddCube(NBTChunk chunk, byte blockData, Vector3Int pos, NBTGameObject nbtGO)
    {
        ca.pos       = pos;
        ca.blockData = blockData;

        chunk.GetBlockData(pos.x, pos.y, pos.z - 1, out byte frontType, out byte frontData);
        chunk.GetBlockData(pos.x, pos.y, pos.z + 1, out byte backType, out byte backData);
        chunk.GetBlockData(pos.x - 1, pos.y, pos.z, out byte leftType, out byte leftData);
        chunk.GetBlockData(pos.x + 1, pos.y, pos.z, out byte rightType, out byte rightData);
        chunk.GetBlockData(pos.x, pos.y - 1, pos.z, out byte bottomType, out byte bottomData);
        chunk.GetBlockData(pos.x, pos.y + 1, pos.z, out byte topType, out byte topData);

        bool selfIsVerticalWater = IsVerticalWater(blockData);

        chunk.GetLights(pos.x, pos.y, pos.z, out float skyLight, out float blockLight);

        fa.color      = Color.white;
        fa.skyLight   = skylight_default;
        fa.blockLight = blocklight_default;
        fa.uv         = uv_zero;

        if (NBTGeneratorManager.IsTransparent(frontType) && frontType != TYPE_WATER)
        {
            if (selfIsVerticalWater)
            {
                fa.pos[0] = nearBottomLeft;
                fa.pos[1] = nearTopLeft;
                fa.pos[2] = nearTopRight;
                fa.pos[3] = nearBottomRight;
            }
            else
            {
                fa.pos[0] = nearBottomLeft;
                fa.pos[1] = nearTopLeft_still;
                fa.pos[2] = nearTopRight_still;
                fa.pos[3] = nearBottomRight;
            }
            fa.normal = Vector3.forward;
            AddFace(nbtGO.nbtMesh, fa, ca);
        }
        if (NBTGeneratorManager.IsTransparent(backType) && backType != TYPE_WATER)
        {
            if (selfIsVerticalWater)
            {
                fa.pos[0] = farBottomRight;
                fa.pos[1] = farTopRight;
                fa.pos[2] = farTopLeft;
                fa.pos[3] = farBottomLeft;
            }
            else
            {
                fa.pos[0] = farBottomRight;
                fa.pos[1] = farTopRight_still;
                fa.pos[2] = farTopLeft_still;
                fa.pos[3] = farBottomLeft;
            }
            fa.normal = Vector3.back;
            AddFace(nbtGO.nbtMesh, fa, ca);
        }
        if (NBTGeneratorManager.IsTransparent(leftType) && leftType != TYPE_WATER)
        {
            if (selfIsVerticalWater)
            {
                fa.pos[0] = farBottomLeft;
                fa.pos[1] = farTopLeft;
                fa.pos[2] = nearTopLeft;
                fa.pos[3] = nearBottomLeft;
            }
            else
            {
                fa.pos[0] = farBottomLeft;
                fa.pos[1] = farTopLeft_still;
                fa.pos[2] = nearTopLeft_still;
                fa.pos[3] = nearBottomLeft;
            }
            fa.normal = Vector3.left;
            AddFace(nbtGO.nbtMesh, fa, ca);
        }
        if (NBTGeneratorManager.IsTransparent(rightType) && rightType != TYPE_WATER)
        {
            if (selfIsVerticalWater)
            {
                fa.pos[0] = nearBottomRight;
                fa.pos[1] = nearTopRight;
                fa.pos[2] = farTopRight;
                fa.pos[3] = farBottomRight;
            }
            else
            {
                fa.pos[0] = nearBottomRight;
                fa.pos[1] = nearTopRight_still;
                fa.pos[2] = farTopRight_still;
                fa.pos[3] = farBottomRight;
            }
            fa.normal = Vector3.right;
            AddFace(nbtGO.nbtMesh, fa, ca);
        }
        if (NBTGeneratorManager.IsTransparent(topType) && topType != TYPE_WATER)
        {
            if (selfIsVerticalWater)
            {
                fa.pos[0] = farTopRight;
                fa.pos[1] = nearTopRight;
                fa.pos[2] = nearTopLeft;
                fa.pos[3] = farTopLeft;
            }
            else
            {
                bool leftIsVerticalWater  = IsVerticalWater(leftData, leftType);
                bool rightIsVerticalWater = IsVerticalWater(rightData, rightType);
                bool frontIsVerticalWater = IsVerticalWater(frontData, frontType);
                bool backIsVerticalWater  = IsVerticalWater(backData, backType);

                fa.pos[0] = backIsVerticalWater || rightIsVerticalWater ? farTopRight : farTopRight_still;
                fa.pos[1] = frontIsVerticalWater || rightIsVerticalWater ? nearTopRight : nearTopRight_still;
                fa.pos[2] = frontIsVerticalWater || leftIsVerticalWater ? nearTopLeft : nearTopLeft_still;
                fa.pos[3] = backIsVerticalWater || leftIsVerticalWater ? farTopLeft : farTopLeft_still;
            }
            fa.normal = Vector3.up;
            AddFace(nbtGO.nbtMesh, fa, ca);
        }
        if (NBTGeneratorManager.IsTransparent(bottomType) && bottomType != TYPE_WATER)
        {
            fa.pos[0] = nearBottomRight;
            fa.pos[1] = farBottomRight;
            fa.pos[2] = farBottomLeft;
            fa.pos[3] = nearBottomLeft;
            fa.normal = Vector3.down;
            AddFace(nbtGO.nbtMesh, fa, ca);
        }
    }
Ejemplo n.º 4
0
 bool ShouldAddFace(byte type)
 {
     return(NBTGeneratorManager.IsTransparent(type) && type != TYPE_WATER);
 }
Ejemplo n.º 5
0
    public static void UpdateLighting(int x, int y, int z)
    {
        //Debug.Log("update lighting");
        //float start = Time.realtimeSinceStartup;

        Queue <Vector3Int> skyLightQueue = new Queue <Vector3Int>();
        Vector3Int         p             = new Vector3Int();

        // init
        for (int i = -15; i <= 15; i++)
        {
            for (int j = -15; j <= 15; j++)
            {
                p.Set(x + i, y, z + j);

                int chunkX = Mathf.FloorToInt(p.x / 16f);
                int chunkZ = Mathf.FloorToInt(p.z / 16f);

                int xInChunk = p.x - chunkX * 16;
                int zInChunk = p.z - chunkZ * 16;

                NBTChunk chunk = GetChunk(chunkX, chunkZ);
                for (int temp_y = chunk.Sections.Count * 16 - 1; temp_y >= 0; temp_y--)
                {
                    chunk.SetSkyLightByte(xInChunk, temp_y, zInChunk, 0);
                }
            }
        }

        HashSet <Vector3Int> skyLightSet = new HashSet <Vector3Int>();

        // light from sun (no vertical falloff)
        for (int i = -15; i <= 15; i++)
        {
            for (int j = -15; j <= 15; j++)
            {
                p.Set(x + i, y, z + j);

                int chunkX = Mathf.FloorToInt(p.x / 16f);
                int chunkZ = Mathf.FloorToInt(p.z / 16f);

                int xInChunk = p.x - chunkX * 16;
                int zInChunk = p.z - chunkZ * 16;

                NBTChunk chunk  = GetChunk(chunkX, chunkZ);
                int      temp_y = chunk.Sections.Count * 16 - 1;
                while (NBTGeneratorManager.LightCanTravel(chunk.GetBlockByte(xInChunk, temp_y, zInChunk)))
                {
                    chunk.SetSkyLightByte(xInChunk, temp_y, zInChunk, 15);
                    skyLightSet.Add(new Vector3Int(p.x, temp_y, p.z));
                    if (temp_y == 0)
                    {
                        break;
                    }
                    else
                    {
                        temp_y--;
                    }
                }
            }
        }

        foreach (Vector3Int skyLightPos in skyLightSet)
        {
            if (skyLightSet.Contains(skyLightPos + Vector3Int.left) &&
                skyLightSet.Contains(skyLightPos + Vector3Int.right) &&
                skyLightSet.Contains(skyLightPos + Vector3Int.forward) &&
                skyLightSet.Contains(skyLightPos + Vector3Int.back))
            {
                continue;
            }
            skyLightQueue.Enqueue(new Vector3Int(skyLightPos.x, skyLightPos.y, skyLightPos.z));
        }

        int count    = 0;
        int setcount = 0;

        // light propagation (use flood fill)
        Vector3Int[] arr = new Vector3Int[6];
        while (skyLightQueue.Count > 0)
        {
            count++;
            p = skyLightQueue.Dequeue();
            byte skyLight = GetSkyLightByte(p.x, p.y, p.z);

            arr[0] = p + Vector3Int.left;
            arr[1] = p + Vector3Int.right;
            arr[2] = p + Vector3Int.up;
            arr[3] = p + Vector3Int.down;
            arr[4] = p + Vector3Int.forward;
            arr[5] = p + Vector3Int.back;

            for (int i = 0; i < 6; i++)
            {
                Vector3Int nextPos = arr[i];
                if (NBTGeneratorManager.IsTransparent(GetBlockByte(nextPos.x, nextPos.y, nextPos.z)))
                {
                    byte nextSkyLight = GetSkyLightByte(nextPos.x, nextPos.y, nextPos.z);
                    if (nextSkyLight < skyLight - 1)
                    {
                        setcount++;
                        //Debug.Log("SetSkyLightByte,nextPos=" + nextPos.x + "," + nextPos.y + "," + nextPos.z);
                        SetSkyLightByte(nextPos.x, nextPos.y, nextPos.z, (byte)(skyLight - 1));
                        if (skyLight > 2)
                        {
                            skyLightQueue.Enqueue(nextPos);
                        }
                    }
                }
            }
        }

        //float end = Time.realtimeSinceStartup;
        //Debug.Log("time cost =" + (end - start) + ", actual propagation count=" + count + ",setcount=" + setcount);
    }