質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

89.23%

Unity2D メッシュの結合が出来ない

解決済

回答 1

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 551

t2t21212

score 62

前提・実現したいこと

メッシュの結合がしたい

該当のソースコード

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using AccidentalNoise;
using UnityEditor;

namespace TinyWorld
{
    public class World : MonoBehaviour
    {
        public Tile[,] tiles;

        public Material material;

        Mesh mesh;

        //Noise noise;

        ImplicitFractal HeightMap;

        [SerializeField]
        int TerrainOctaves = 6;
        [SerializeField]
        double TerrainFrequency = 1.25;

        [SerializeField]
        int Width = 250;
        [SerializeField]
        int Height = 250;

        [SerializeField]
        float DeepWater = 0.2f;
        [SerializeField]
        float ShallowWater = 0.4f;
        [SerializeField]
        float Sand = 0.5f;
        [SerializeField]
        float Grass = 0.7f;
        [SerializeField]
        float Forest = 0.8f;
        [SerializeField]
        float Rock = 0.9f;

        MapData HeightData;

        // Use this for initialization
        void Start()
        {
            Initialize();
            GetData(HeightMap, ref HeightData);
            CreateTiles();
            GenerateMesh();

            var meshs = CombineMeshes(new List<Mesh> { mesh });
            GetComponent<MeshFilter>().mesh = meshs;
            var renderer = GetComponent<MeshRenderer>();
            renderer.material = material;
        }

        private Mesh CombineMeshes(List<Mesh> meshes)
        {
            var combine = new CombineInstance[125000];
            for (int i = 0; i < meshes.Count; i++)
            {
                combine[i].mesh = meshes[i];
                combine[i].transform = transform.localToWorldMatrix;
            }

            Mesh newMesh = new Mesh();
            newMesh.CombineMeshes(combine);
            return mesh;
        }

        // Update is called once per frame
        void Update()
        {
            //Graphics.DrawMesh(mesh, Vector3.zero, Quaternion.identity, material, 0);
        }

        private void Initialize()
        {
            // Initialize the HeightMap Generator
            HeightMap = new ImplicitFractal(FractalType.MULTI,
                                           BasisType.SIMPLEX,
                                           InterpolationType.QUINTIC,
                                           TerrainOctaves,
                                           TerrainFrequency,
                                           UnityEngine.Random.Range(0, int.MaxValue));
        }

        private void GetData(ImplicitModuleBase module, ref MapData mapData)
        {
            mapData = new MapData(Width, Height);

            // loop through each x,y point - get height value
            for (var x = 0; x < Width; x++)
            {
                for (var y = 0; y < Height; y++)
                {
                    //Sample the noise at smaller intervals
                    float x1 = x / (float)Width;
                    float y1 = y / (float)Height;

                    float value = (float)HeightMap.Get(x1, y1);

                    //keep track of the max and min values found
                    if (value > mapData.Max) mapData.Max = value;
                    if (value < mapData.Min) mapData.Min = value;

                    mapData.Data[x, y] = value;
                }
            }
        }

        void CreateTiles()
        {
            tiles = new Tile[Width, Height];

            /*float[,] noiseValues = noise.GetNoiseValues(width, height);

            for (int i = 0; i < width; i++)
            {
                for (int j = 0; j < height; j++)
                {
                    if (noiseValues[i, j] > 0.5f)
                    {
                        tiles[i, j] = new Tile(Tile.Type.Grass);
                    }
                    else
                    {
                        tiles[i, j] = new Tile(Tile.Type.Dirt);
                    }
                }
            }*/

            for (var x = 0; x < Width; x++)
            {
                for (var y = 0; y < Height; y++)
                {
                    float value = HeightData.Data[x, y];
                    value = (value - HeightData.Min) / (HeightData.Max - HeightData.Min);

                    //HeightMap Analyze
                    if (value < DeepWater)
                    {
                        int randomTree = Random.Range(0, 2);
                        if (randomTree == 0)
                        {
                            tiles[x, y] = new Tile(Tile.Type.DeepWater);
                        }
                        else if(randomTree == 1)
                        {
                            tiles[x, y] = new Tile(Tile.Type.DeepWater);
                        }
                    }
                    else if (value < ShallowWater)
                    {
                        int randomTree = Random.Range(0, 2);
                        if (randomTree == 0)
                        {
                            tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                        }
                        else if (randomTree == 1)
                        {
                            tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                        }
                    }
                    else if (value < Sand)
                    {
                        tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                    }
                    else if (value < Grass)
                    {
                        tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                    }
                    else if (value < Forest)
                    {
                        tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                    }
                    else if (value < Rock)
                    {
                        tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                    }
                    else
                    {
                        tiles[x, y] = new Tile(Tile.Type.ShallowWater);
                    }
                }
            }

        }

        void GenerateMesh()
        {
            MeshData data = new MeshData(tiles);
            mesh = new Mesh();

            // 頂点インデックスのフォーマットを32ビット整数に変更する
            mesh.indexFormat = UnityEngine.Rendering.IndexFormat.UInt32;

            mesh.vertices = data.vertices.ToArray();
            mesh.triangles = data.triangles.ToArray();
            mesh.uv = data.UVs.ToArray();
            mesh.RecalculateNormals();
            mesh.RecalculateBounds();
        }
    }
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

namespace TinyWorld
{
    public class MeshData
    {
        public List<Vector3> vertices;
        public List<int> triangles;
        public List<Vector2> UVs;

        public MeshData(Tile[,] data)
        {
            vertices = new List<Vector3>();
            triangles = new List<int>();
            UVs = new List<Vector2>();

            for (int i = 0; i < data.GetLength(0); i++)
            {
                for (int j = 0; j < data.GetLength(1); j++)
                {
                    CreateSquare(data[i, j], i, j);
                }
            }
        }

        void CreateSquare(Tile tile, int x, int y)
        {

            vertices.Add(new Vector3(x + 0, y + 0));
            vertices.Add(new Vector3(x + 1, y + 0));
            vertices.Add(new Vector3(x + 0, y + 1));
            vertices.Add(new Vector3(x + 1, y + 1));

            triangles.Add(vertices.Count - 1);
            triangles.Add(vertices.Count - 3);
            triangles.Add(vertices.Count - 4);

            triangles.Add(vertices.Count - 2);
            triangles.Add(vertices.Count - 1);
            triangles.Add(vertices.Count - 4);


            UVs.AddRange(SpriteLoader.instance.GetTileUVs(tile));
        }
    }
}

試したこと

MeshFilterとMeshMeshRendererが一つずつある状態なのですが、メッシュの結合が出来ません。

https://docs.unity3d.com/ja/2018.2/ScriptReference/Mesh.CombineMeshes.html

Mesh.CombineMeshesのリファレンスを読むとMeshFilterの配列を使っていますが、自分は一つのMeshFilterしか使用していません。

横縦250×250で四角形のメッシュを生成しています。

どのようにしたらMesh.CombineMeshesが使えるでしょうか?

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • sakura_hana

    2019/07/02 11:13

    「メッシュの結合が出来ません」とはどういう状態ですか?「理想の状態」と「現状」を明記してください。

    >自分は一つのMeshFilterしか使用していません。
    何故そうしているのですか? 複数のメッシュを結合するのがMesh.CombineMeshesなので、メッシュを1つしか渡さなければ当然結合は出来ません。
    (単純に「複数のタイル(三角面)が組み合わさった1枚のメッシュ」が欲しいのであれば今のソースでもいいように思います)

    キャンセル

回答 1

checkベストアンサー

0

修正依頼書いた後でもう1つの質問を見ましたが、「四角形のメッシュを250×250生成している」というのがそもそも誤解のようですね。

このソースコードではMeshは1枚しか生成されていません。
(「25万個の頂点と12.5万個の三角面(ポリゴン)を持つMesh」が1つ生成されている)
なので当然Mesh.CombineMeshesをやっても何も起こりません。

Mesh.CombineMeshesに複数のMeshを渡す
(=var meshs = CombineMeshes(new List<Mesh> { mesh });のListに複数のMeshを入れる)
と結合出来ます。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2019/07/02 17:16

    なるほど…。なにか勘違いしていたようです

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 89.23%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

同じタグがついた質問を見る