zoukankan      html  css  js  c++  java
  • Unity3d学习 预设体(prefab)的一些理解

    之前一直在想如果要在Unity3d上创建很多个具有相同结构的对象,是如何做的,后来查了相关资料发现预设体可以解决这个问题!

    预设体的概念: 组件的集合体 , 预制物体可以实例化成游戏对象.

    创建预设体的作用: 可以重复的创建具有相同结构的游戏对象。

    .1下面来讲解一下如何制作一个简单的预设体(上下为流程和结果图):

      

      

    .2 创建多个prefabs_new(代码,结果图):

     1 using UnityEngine;
     2 using System.Collections;
     3  
     4 //[ExecuteInEditMode]表示在编辑模式下运行(注意改变prefab的属性其他属性也会变)
     5 public class CreateInstance : MonoBehaviour {
     6     public GameObject prefabs = null;
     7     private Vector3 pos;
     8     void Start () {
     9         if (prefabs != null)
    10         {
    11             pos = new Vector3(0, 2.7f, -10.5114f);
    12             for (int i = 0; i < 5; ++i)
    13             {
    14                 Object tmpObj = Instantiate(prefabs, pos , Quaternion.identity);
    15                 pos.x = pos.x - 3;
    16             }
    17         }
    18         else
    19         {
    20             Debug.Log("prefabs is null");
    21         }
    22     }
    23 }

      

     如果(预设物C = 预设物B 和 预设物 A的组合) 则会形成 修改预设物A的数据不会影响预设物C中的内嵌数据,下面方法可以帮助解决!

     .4关于perfab之间的嵌套(主要是一个perfab数据修改了嵌套这个perfab的数据要做对应的更新):

        

    关于预设体嵌套预设体的代码(在实例化时会拿到最新的perfab数据):

    using UnityEngine;
    #if UNITY_EDITOR
    using UnityEditor;
    using UnityEditor.Callbacks;
    #endif
    using System.Collections.Generic;
     
    [ExecuteInEditMode]
    public class PrefabInstance : MonoBehaviour
    {
        public GameObject prefab;
     
    #if UNITY_EDITOR    
        // Struct of all components. Used for edit-time visualization and gizmo drawing
        public struct Thingy {
            public Mesh mesh;
            public Matrix4x4 matrix;
            public List<Material> materials;
        }
     
        [System.NonSerializedAttribute] public List<Thingy> things = new List<Thingy> ();
     
        void OnValidate () {
            things.Clear();
            if (enabled)
                Rebuild (prefab, Matrix4x4.identity);
        }
     
        void OnEnable () {
            things.Clear();
            if (enabled)
                Rebuild (prefab, Matrix4x4.identity);
        }
     
        void Rebuild (GameObject source, Matrix4x4 inMatrix) {
            if (!source)
                return;
     
            Matrix4x4 baseMat = inMatrix * Matrix4x4.TRS (-source.transform.position, Quaternion.identity, Vector3.one);
            
            foreach (MeshRenderer mr in source.GetComponentsInChildren(typeof (Renderer), true))
            {
                things.Add(new Thingy () {
                    mesh = mr.GetComponent<MeshFilter>().sharedMesh,
                    matrix = baseMat * mr.transform.localToWorldMatrix,
                    materials = new List<Material> (mr.sharedMaterials)
                });
            }
     
            foreach (PrefabInstance pi in source.GetComponentsInChildren(typeof (PrefabInstance), true))
            {
                if (pi.enabled && pi.gameObject.activeSelf)
                    Rebuild (pi.prefab, baseMat * pi.transform.localToWorldMatrix);
            }        
        }
     
        // Editor-time-only update: Draw the meshes so we can see the objects in the scene view
        void Update () {
            if (EditorApplication.isPlaying)
                return;
            Matrix4x4 mat = transform.localToWorldMatrix;
            foreach (Thingy t in things)
                for (int i = 0; i < t.materials.Count; i++)
                    Graphics.DrawMesh (t.mesh, mat * t.matrix, t.materials[i], gameObject.layer, null, i);
        }
     
        // Picking logic: Since we don't have gizmos.drawmesh, draw a bounding cube around each thingy
        void OnDrawGizmos () { DrawGizmos (new Color (0,0,0,0)); }
        void OnDrawGizmosSelected () { DrawGizmos (new Color (0,0,1,.2f)); }
        void DrawGizmos (Color col) {
            if (EditorApplication.isPlaying)
                return;
            Gizmos.color = col;
            Matrix4x4 mat = transform.localToWorldMatrix;
            foreach (Thingy t in things)
            {
                Gizmos.matrix = mat * t.matrix;
                Gizmos.DrawCube(t.mesh.bounds.center, t.mesh.bounds.size);
            }        
        }
     
        // Baking stuff: Copy in all the referenced objects into the scene on play or build
        [PostProcessScene(-2)]
        public static void OnPostprocessScene() { 
            foreach (PrefabInstance pi in UnityEngine.Object.FindObjectsOfType (typeof (PrefabInstance)))
                BakeInstance (pi);
        }
     
        public static void BakeInstance (PrefabInstance pi) {
            if(!pi.prefab || !pi.enabled)
                return;
            pi.enabled = false;
            GameObject go = PrefabUtility.InstantiatePrefab(pi.prefab) as GameObject;
            Quaternion rot = go.transform.localRotation;
            Vector3 scale = go.transform.localScale;
            go.transform.parent = pi.transform;
            go.transform.localPosition = Vector3.zero;
            go.transform.localScale = scale;
            go.transform.localRotation = rot;
            pi.prefab = null;
            foreach (PrefabInstance childPi in go.GetComponentsInChildren<PrefabInstance>())
                BakeInstance (childPi);
        }
     
    #endif

      上述是两个 如果是多个关联呢?

  • 相关阅读:
    HashMap的负载因子为什么默认是0.75?这篇文章告诉你答案
    如何设计短网址系统?
    前端HTML史上最全总结,入门级边学边实战!
    阿里2021最全新的java面试题总结
    三万字,100题!Linux知识汇总!
    程序员路线图
    基于nodejs的selenium的自动化测试之网络元素
    Electron桌面程序入门研究
    Git常用命令
    二次探测法
  • 原文地址:https://www.cnblogs.com/yuyaonorthroad/p/6107320.html
Copyright © 2011-2022 走看看