Beispiel #1
0
    // 隣のブロックとの閉塞チェック
    private bool IsOcculuded(BlockGroup group, BlockDirection direction)
    {
        int dirIndex = (int)direction;
        // 隣のブロックに完全に覆われていたら省略する(閉塞チェック)
        Block neighborBlock = group.GetBlock(this.position + EditManager.Instance.ToWorldCoordinate(neighborOffsets[dirIndex]));

        if (neighborBlock != null)
        {
            var con1 = this.GetConnection((BlockDirection)(dirIndex));
            var con2 = neighborBlock.GetConnection((BlockDirection)(dirIndex ^ 1));
            if (con2 == BlockConnection.None)
            {
                return(false);
            }
            else if (con2 == BlockConnection.Square)
            {
                return(true);
            }
            else if (con1 == con2)
            {
                var dir1 = this.GetConnectionDir((BlockDirection)(dirIndex));
                var dir2 = neighborBlock.GetConnectionDir((BlockDirection)(dirIndex ^ 1));
                if (dir1 == dir2)
                {
                    return(true);
                }
            }
        }

        return(false);
    }
Beispiel #2
0
        public bool CanMoveTo(FieldPanel target, BlockGroup blockGroup)
        {
            bool movable = true;

            if (target.position.y == this.position.y)
            {
                // 同じ高さのパネル
            }
            else if (target.position.y > this.position.y)
            {
                // 上の方のパネル
                float dy = target.originalPosition.y;
                float sy = this.originalPosition.y;
                for (float j = sy + 0.5f; j <= dy + 1.5f; j += 0.5f)
                {
                    Block block = blockGroup.GetBlock(
                        new Vector3(this.originalPosition.x, j, this.originalPosition.z));
                    if (block != null)
                    {
                        movable = false;
                        break;
                    }
                }
            }
            else if (target.position.y < this.position.y)
            {
                // 下の方のパネル
                float dy = target.originalPosition.y;
                float sy = this.originalPosition.y;
                for (float j = sy + 1.5f; j >= dy + 0.5f; j -= 0.5f)
                {
                    Block block = blockGroup.GetBlock(
                        new Vector3(target.originalPosition.x, j, target.originalPosition.z));
                    if (block != null)
                    {
                        movable = false;
                        break;
                    }
                }
            }
            return(movable);
        }
Beispiel #3
0
 // 上に4ブロック分のスペースがあるか
 public bool IsEnterable(BlockGroup blockGroup)
 {
     if (this.shape.panelVertices == null)
     {
         return(false);
     }
     for (int i = 1; i <= 4; i++)
     {
         var block = blockGroup.GetBlock(this.position + new Vector3(0, 0.5f * i, 0));
         if (block != null)
         {
             return(false);
         }
     }
     return(true);
 }
Beispiel #4
0
    // 自動配置ブロックの処理
    public void WriteToMeshAutoPlacement(BlockGroup blockGroup, BlockMeshMerger meshMerger)
    {
        BlockShape shape = this.shape;
        // 隣接ブロックを取得
        var list = new Vector3[] {
            new Vector3(0, 0, 1), new Vector3(1, 0, 0), new Vector3(0, 0, -1), new Vector3(-1, 0, 0),
            new Vector3(1, 0, 1), new Vector3(1, 0, -1), new Vector3(-1, 0, -1), new Vector3(-1, 0, 1),
            new Vector3(0, 0.5f, 0),
            new Vector3(0, 0.5f, 1), new Vector3(1, 0.5f, 0), new Vector3(0, 0.5f, -1), new Vector3(-1, 0.5f, 0),
        };

        int pattern = 0;

        for (int i = 0; i < list.Length; i++)
        {
            var block = blockGroup.GetBlock(position + EditManager.Instance.ToWorldCoordinate(list[i]));
            if (block != null)
            {
                pattern |= (1 << i);
            }
        }

        for (int i = 0; i < 4; i++)
        {
            bool s1 = (pattern & (1 << (i))) != 0;                          // 隣接1
            bool s2 = (pattern & (1 << ((i + 1) % 4))) != 0;                // 隣接2
            bool s3 = (pattern & (1 << (i + 4))) != 0;                      // 斜め隣接
            bool s4 = (pattern & (1 << 8)) != 0;                            // 上隣接
            bool s5 = (pattern & (1 << (9 + i))) != 0;                      // 上横隣接1
            bool s6 = (pattern & (1 << (9 + (i + 1) % 4))) != 0;            // 上横隣接2

            int meshOffset;
            if (s3)
            {
                if (s1 && s2)
                {
                    meshOffset = (s4 && (s5 || s6)) ? -1 : 0;
                }
                else if (s1)
                {
                    meshOffset = (s4) ? (s5) ? 24 : 32 : 8;
                }
                else if (s2)
                {
                    meshOffset = (s4) ? (s6) ? 28 : 36 : 12;
                }
                else
                {
                    meshOffset = (s4) ? 20 : 4;
                }
            }
            else
            {
                if (s1 && s2)
                {
                    meshOffset = 16;
                }
                else if (s1)
                {
                    meshOffset = (s4) ? (s5) ? 24 : 32 : 8;
                }
                else if (s2)
                {
                    meshOffset = (s4) ? (s6) ? 28 : 36 : 12;
                }
                else
                {
                    meshOffset = (s4) ? 20 : 4;
                }
            }
            if (meshOffset < 0)
            {
                continue;
            }

            var mesh = shape.meshes[6 + meshOffset + i];
            if (mesh == null)
            {
                continue;
            }

            meshMerger.Merge(mesh, this.position, this.direction, Vector3.one,
                             shape.divideChipVert, this.textureChips[6], 0);
        }
    }
Beispiel #5
0
    // 6方向ブロックメッシュ
    public void WriteToMeshStandard(BlockGroup blockGroup, BlockMeshMerger meshMerger)
    {
        BlockShape shape = this.shape;

        for (int i = 0; i < shape.meshes.Length; i++)
        {
            int index = this.ToLocalDirection(i);

            var mesh = shape.meshes[index];
            if (mesh == null)
            {
                continue;
            }

            // 隣のブロックに完全に覆われていたら省略する
            if (i < 6 && this.IsOcculuded(blockGroup, (BlockDirection)i))
            {
                continue;
            }

            // 一番下の底面は省略する
            if ((BlockDirection)i == BlockDirection.Yminus && this.position.y == 0.0f)
            {
                continue;
            }

            Vector3 position = this.position;
            Vector3 scale    = Vector3.one;
            // 側面パネルの場合は分割する
            bool divideChipVert = shape.divideChipVert && i < 6 &&
                                  (BlockDirection)i != BlockDirection.Yplus &&
                                  (BlockDirection)i != BlockDirection.Yminus;
            if (divideChipVert && this.IsCombinable((BlockDirection)i))
            {
                BlockDirection direction = (BlockDirection)i;
                // 上下に2個続いているブロックをまとめる
                if (this.position.y - Math.Floor(this.position.y) >= 0.5f)
                {
                    Block neighborBlock = blockGroup.GetBlock(this.position - new Vector3(0, 0.5f, 0));
                    if (neighborBlock != null && neighborBlock.IsCombinable(direction) &&
                        this.GetTextureChip(direction) == neighborBlock.GetTextureChip(direction))
                    {
                        divideChipVert = false;
                        position.y    -= 0.25f;
                        scale.y        = 2.0f;
                    }
                }
                else
                {
                    Block neighborBlock = blockGroup.GetBlock(this.position + new Vector3(0, 0.5f, 0));
                    if (neighborBlock != null && neighborBlock.IsCombinable(direction) &&
                        this.GetTextureChip(direction) == neighborBlock.GetTextureChip(direction))
                    {
                        if (!neighborBlock.IsOcculuded(blockGroup, direction))
                        {
                            continue;
                        }
                    }
                }
            }

            meshMerger.Merge(mesh, position, this.direction, scale,
                             divideChipVert, this.textureChips[index], i);
        }
    }