Top > ComputerGraphics > Unity > Tips > Mesh > BasicCombineMeshes
Last-modified: Sun, 05 May 2013 11:18:45 JST
Counter:15291 Today:4 Yesterday:12 Online:15
このエントリーをはてなブックマークに追加

CombineMeshesの基本的な使い方

About

CGではしばしば、複数のメッシュを単一のメッシュにまとめてしまう、という操作があります。一般的には、複数のメッシュを一つにまとめることで描画パフォーマンスを向上する、といった目的で利用されることが多いでしょう。Unityにはメッシュを結合するための"CombineMeshesメソッド"が用意されていますが、リファレンスだけ見ても使い方がパッと想像できなかったので、ここでは公式のサンプルを試験実装したものをまとめておきます。

HowTo

スクリプトの用意

試験したUnityのバージョンは4.x系ですが、リファレンスが少々古いようで、C#のサンプルスクリプトはそのまま実装することができません。そこで次のようなスクリプトに変更しました。

  • 主な変更点
    • "gameObject.active = false;"は古い形式なので"SetActive"へ。
    • "Component.sharedMesh"は取得できないので、一度"MeshFilter"へキャスト。
using UnityEngine;
using System.Collections;

[RequireComponent(typeof(MeshFilter))]
[RequireComponent(typeof(MeshRenderer))]
public class CombineScript : MonoBehaviour
{

    //適当なマテリアルをセットするようにしておく
    public Material targetMaterial;

    void Start()
    {
        Component[] meshFilters = GetComponentsInChildren<MeshFilter>();
        CombineInstance[] combine = new CombineInstance[meshFilters.Length];
        
        int i = 0;
        while (i < meshFilters.Length)
        {
            combine[i].mesh = ((MeshFilter)meshFilters[i]).sharedMesh;
            combine[i].transform = meshFilters[i].transform.localToWorldMatrix;
            meshFilters[i].gameObject.SetActive(false);
            i++;
        }

        print(combine.Length);

        transform.GetComponent<MeshFilter>().mesh = new Mesh();
        transform.GetComponent<MeshFilter>().mesh.CombineMeshes(combine);
        transform.gameObject.SetActive(true);

        //マテリアルを再設定
        transform.gameObject.renderer.material = targetMaterial;
    }
}

ここでは捨てられてしまうマテリアル情報を適当に与えるための"targetMaterial"変数を用意しています。Materialについてはここではあつかいません。

スクリプトのアタッチ

用意したスクリプトを適用する対象は、結合したい全てのメッシュを子要素に持つ、Gameobjectです。まず空のGameObjectを用意して、結合したい全ての(メッシュを持った)GameObjectをその子要素にします。その後、親のGameObjectに用意したスクリプトをアタッチします。

サンプルでは次のようになっています。

  • CombinedObject(空のGameObject-用意したスクリプトがアタッチされる)
    • Cube(結合するオブジェクト)
    • Cube(結合するオブジェクト)

Result

サンプルではオブジェクトを2つしか用意していないのでパフォーマンスが変わるわけがないのですが、結合されていることは確認できます。実行時にMeshRendererのチェックをOn/Offすると結合された全てのオブジェクトを対象にして表示/非表示が切り替わります。

0.png 1.png

Reference