public static void init()
 {
     foreach (Transform t in Selection.transforms)
     {
         if (t.GetComponent <MeshFilter>())
         {
             pb_Object pb = ProBuilderize(t);
             if (pb.GetComponent <MeshCollider>())
             {
                 DestroyImmediate(pb.GetComponent <MeshCollider>());
             }
         }
     }
 }
        /**
         *	Do the thing.  Return a pb_ActionResult indicating the success/failure of action.
         */
        public override pb_ActionResult DoAction()
        {
                        #if !UNITY_4_6 && !UNITY_4_7
            ShadowCastingMode shadowMode = (ShadowCastingMode)EditorPrefs.GetInt("pb_CreateShadowObject_shadowMode", (int)ShadowCastingMode.ShadowsOnly);
                        #endif
            float         extrudeDistance = EditorPrefs.GetFloat("pb_CreateShadowObject_volumeSize", .08f);
            ExtrudeMethod extrudeMethod   = (ExtrudeMethod)EditorPrefs.GetInt("pb_CreateShadowObject_extrudeMethod", (int)ExtrudeMethod.FaceNormal);

            foreach (pb_Object pb in selection)
            {
                pb_Object shadow = GetShadowObject(pb);

                if (shadow == null)
                {
                    continue;
                }

                foreach (pb_Face f in shadow.faces)
                {
                    f.ReverseIndices(); f.manualUV = true;
                }
                shadow.Extrude(shadow.faces, extrudeMethod, extrudeDistance);
                shadow.ToMesh();
                shadow.Refresh();
                shadow.Optimize();

                                #if !UNITY_4_6 && !UNITY_4_7
                MeshRenderer mr = shadow.gameObject.GetComponent <MeshRenderer>();
                mr.shadowCastingMode = shadowMode;
                if (shadowMode == ShadowCastingMode.ShadowsOnly)
                {
                    mr.receiveShadows = false;
                }
                                #endif

                Collider collider = shadow.GetComponent <Collider>();

                while (collider != null)
                {
                    GameObject.DestroyImmediate(collider);
                    collider = shadow.GetComponent <Collider>();
                }
            }

            // This is necessary!  Otherwise the pb_Editor will be working with caches from
            // outdated meshes and throw errors.
            pb_Editor.Refresh();

            return(new pb_ActionResult(Status.Success, "Create Shadow Object"));
        }
示例#3
0
        public static void ProBuilderizeObjects(bool preserveFaces)
        {
            foreach (Transform t in Selection.transforms)
            {
                if (t.GetComponent <MeshFilter>())
                {
                    pb_Object pb = ProBuilderize(t, preserveFaces);

                    if (pb.GetComponent <MeshCollider>())
                    {
                        DestroyImmediate(pb.GetComponent <MeshCollider>());
                    }
                }
            }
        }
示例#4
0
    bool FaceRaycast(Vector2 mouse, out pb_Object pb, out pb_Face face)
    {
        var        ray = Camera.main.ScreenPointToRay(mouse);
        RaycastHit rayHit;

        if (Physics.Raycast(ray.origin, ray.direction, out rayHit))
        {
            pb = rayHit.transform.gameObject.GetComponent <pb_Object>();

            if (pb == null)
            {
                face = null;
                return(false);
            }

            Mesh m = pb.GetComponent <MeshFilter>().sharedMesh;

            int[] tri = new int[3] {
                m.triangles[rayHit.triangleIndex * 3 + 0],
                m.triangles[rayHit.triangleIndex * 3 + 1],
                m.triangles[rayHit.triangleIndex * 3 + 2]
            };

            return(pb.FaceWithTriangle(tri, out face));
        }

        pb   = null;
        face = null;

        return(false);
    }
        /**
         *	\brief This is how we figure out what face is clicked.
         */
        public bool FaceCheck(Vector3 pos)
        {
            Ray        ray = Camera.main.ScreenPointToRay(pos);
            RaycastHit hit;

            if (Physics.Raycast(ray.origin, ray.direction, out hit))
            {
                pb_Object hitpb = hit.transform.gameObject.GetComponent <pb_Object>();

                if (hitpb == null)
                {
                    return(false);
                }

                Mesh m = hitpb.GetComponent <MeshFilter>().sharedMesh;

                int[] tri = new int[3] {
                    m.triangles[hit.triangleIndex * 3 + 0],
                    m.triangles[hit.triangleIndex * 3 + 1],
                    m.triangles[hit.triangleIndex * 3 + 2]
                };

                currentSelection.pb = hitpb;

                return(hitpb.FaceWithTriangle(tri, out currentSelection.face));
            }
            return(false);
        }
示例#6
0
    /// <summary>
    /// <b>호출</b> : Util.MakeWalls(), Util.MakeOutlineWalls()<br></br>
    /// <b>참조</b> : GetVertices(), FindFace(), GetIntersect(), Util.Index(), pb_Object.CreateInstanceWithVerticesFaces() <br></br>
    /// 벽 생성 함수.
    /// 문/창문이 있을 경우, 그 부분에 구멍이 뚫린 벽 모델을 얻기 위해
    /// Probuilder로 기존 벽과 오브젝트의 transfrom 정보를 참조하여 모든 점과 교점을 수집한 뒤,
    /// 부분적으로 사각형 단위로 submesh를 생성하고 통합하여 mesh를 생성한다.<br></br>
    /// 현재 월드좌표에서 y축을 높이 축으로 사용 중이며,
    /// 따라서 벽 생성이 xy 평면 또는 zy평면에서 생성되므로
    /// 각 벽의 방향에 따라 주 좌표 축(메인 인덱스, index)로 삼고, y축을 sub 좌표 축(index2)로 사용한다.
    /// 또 mesh 생성시 normal(앞/뒷면)구분을 위해 벽의 회전 각도에 따라 주 좌표 축의 방향(dir)을 음수나 양수로 지정하였다.
    /// </summary>
    /// <param name="wall">생성시 참조할 기본벽</param>
    /// <param name="elements">문/창문 리스트</param>
    /// <param name="material">생성된 벽에 적용할 재질</param>
    /// <param name="area">생성된 벽의 면적</param>
    /// <param name="isDebug">디버그 옵션</param>
    /// <returns>
    /// probuilder로 새로 생성한 벽 mesh 오브젝트
    /// </returns>
    public static GameObject MakeWalls(Transform wall, List <Transform> elements, Material material, out float area, bool isDebug = false)
    {
        debugMode = isDebug;
        List <Vector3>   vertices       = new List <Vector3>();
        List <Transform> elementsInThis = new List <Transform>();

        area = 0;

        // 벽의 회전 각도로 메인 축 인덱스 찾기 : x = 0, z = 2
        int index = Util.Index(wall);

        // 벽의 회전 각도로 메인 축의 방향 찾기 : 정방향 = 1, 역방향 = -1
        float dir = (wall.eulerAngles.y == 90 || wall.eulerAngles.y == 180) ? -1 : 1;

        // 기본 벽을 기준으로 모서리 점 추가
        vertices.AddRange(GetVertices(wall, wall, index));

        // 벽 안에 문/창문이 있을 경우 점 추가
        foreach (var element in elements)
        {
            if (GetIntersect(wall, element, index, dir))
            {
                Vector3[] verts = GetVertices(element, wall, index);
                vertices.AddRange(verts);
                elementsInThis.Add(element);
            }
        }

        // 초기 dot 생성 확인
        //if (debugMode) GameObject.DontDestroyOnLoad(Util.Visualize(vertices, "dots"));

        // 면 만들기
        pb_Object pb = pb_Object.CreateInstanceWithVerticesFaces(vertices.ToArray(), FindFace(vertices, elementsInThis, index, 1, dir, out area));

        pb.GetComponent <MeshRenderer>().material          = material;
        pb.GetComponent <MeshRenderer>().shadowCastingMode = UnityEngine.Rendering.ShadowCastingMode.TwoSided;
        //pb.name = "Wall"+index;
        return(pb.gameObject);
    }
示例#7
0
    /// <summary>
    /// <b>호출</b> : DecoratePresenter.BindItem()<br></br>
    /// <b>참조</b> : Util.GetGridValue(), pb_Object.CreateInstanceWithVerticesFaces() <br></br>
    /// 문 없음 객체에서 문 모델 오브젝트 대신 빈 벽을 땜빵할 mesh를 새롭게 생성하는 함수.
    /// 벽지/바닥재 적용 시 uv 스케일링과 월드좌표 반영을 위해서 참조 quad를 probuilder로 다시 생성한다.
    /// </summary>
    /// <param name="quad">다시 생성할 참조 quad</param>
    /// <param name="material">적용할 기본 재질</param>
    /// <param name="area">생성된 mesh의 면적 - 견적에서 사용됨.</param>
    /// <returns>probuilder로 생성된 mesh 오브젝트</returns>
    public static GameObject MakeQuad(GameObject quad, Material material, out float area)
    {
        // quad의 모서리 정보(x,y)를 월드 좌표로 수집.
        Vector3[] vertices = new Vector3[4];
        vertices[0] = quad.transform.TransformPoint(Vector3.left * 0.5f + Vector3.down * 0.5f);
        vertices[1] = quad.transform.TransformPoint(Vector3.right * 0.5f + Vector3.down * 0.5f);
        vertices[2] = quad.transform.TransformPoint(Vector3.left * 0.5f + Vector3.up * 0.5f);
        vertices[3] = quad.transform.TransformPoint(Vector3.right * 0.5f + Vector3.up * 0.5f);

        pb_Object pb = pb_Object.CreateInstanceWithVerticesFaces(vertices, MakeBox(new int[] { 0, 1, 2, 3 }));

        pb.GetComponent <MeshRenderer>().material = material;
        pb.name = quad.name;

        GameObject.Destroy(quad);
        area = Util.GetGridValue(quad.transform.localScale.x * quad.transform.localScale.y);

        return(pb.gameObject);
    }
示例#8
0
    /**
     *	\brief Creates a new #pb_Object using passed vertices to construct geometry.
     *	Typically you would not call this directly, as the #ProBuilder class contains
     *	a wrapper for this purpose.  In fact, I'm not sure why this is public...
     *	@param vertices A vertex array (Vector3[]) containing the points to be used in
     *	the construction of the #pb_Object.  Vertices must be wound in counter-clockise
     *	order.  Triangles will be wound in vertex groups of 4, with the winding order
     *	0,1,2 1,3,2.  Ex:
     *	\code{.cs}
     *	// Creates a pb_Object plane
     *	pb_Object.CreateInstanceWithPoints(new Vector3[4]{
     *		new Vector3(-.5f, -.5f, 0f),
     *		new Vector3(.5f, -.5f, 0f),
     *		new Vector3(-.5f, .5f, 0f),
     *		new Vector3(.5f, .5f, 0f)
     *		});
     *
     *	\endcode
     *	\returns The resulting #pb_Object.
     */
    public static pb_Object CreateInstanceWithPoints(Vector3[] vertices)
    {
        if (vertices.Length % 4 != 0)
        {
            Debug.LogWarning("Invalid Geometry.  Make sure vertices in are pairs of 4 (faces).");
            return(null);
        }

        GameObject _gameObject = new GameObject();
        pb_Object  pb_obj      = _gameObject.AddComponent <pb_Object>();

        pb_obj.SetName("Object");

        pb_obj.GeometryWithPoints(vertices);

        pb_obj.GetComponent <pb_Entity>().SetEntity(EntityType.Detail);

        return(pb_obj);
    }
示例#9
0
		/**
		 *	\brief Duplicates and mirrors the passed pb_Object.
		 *	@param pb The donor pb_Object.
		 *	@param axe The axis to mirror the object on.
		 *	\returns The newly duplicated pb_Object.
		 *	\sa ProBuilder.Axis
		 */
		public static pb_Object Mirror(pb_Object pb, Vector3 scale)
		{
			pb_Object p = pb_Object.InitWithObject(pb);
			p.MakeUnique();

			p.transform.parent = pb.transform.parent;

			p.transform.localRotation = pb.transform.localRotation;

			Vector3 lScale = p.gameObject.transform.localScale;

			p.transform.localScale = new Vector3(lScale.x * scale.x, lScale.y * scale.y, lScale.z * scale.z);

			// if flipping on an odd number of axes, flip winding order
			if( (scale.x * scale.y * scale.z) < 0)
				p.ReverseWindingOrder(p.faces);

			p.FreezeScaleTransform();

			p.transform.localScale = pb.transform.localScale;
			
			Collider col = pb.GetComponent<Collider>();
			ColliderType colType = ColliderType.None;
			if(col != null)
			{
				if(col is MeshCollider)
					colType = ColliderType.MeshCollider;
				else
					colType = ColliderType.BoxCollider;
			}

			pb_Editor_Utility.InitObjectFlags(p, colType, pb.GetComponent<pb_Entity>().entityType);
			
			p.ToMesh();
			p.Refresh();

			// InitObjectFlags runs ScreenCenter()
			p.transform.position = pb.transform.position;

			Undo.RegisterCreatedObjectUndo(p.gameObject, "Mirror Object");

			return p;
		}
示例#10
0
    public static void GenerateUV2(this pb_Object pb, bool forceUpdate)
    {
        if (pb_Preferences_Internal.GetBool(pb_Constant.pbDisableAutoUV2Generation) && !forceUpdate)
        {
            return;
        }

        // SetUVParams(8f, 15f, 15f, 20f);
        UnwrapParam param;

        UnwrapParam.SetDefaults(out param);

        param.angleError = Mathf.Clamp(pb.angleError, 1f, 75f) * .01f;
        param.areaError  = Mathf.Clamp(pb.areaError, 1f, 75f) * .01f;
        param.hardAngle  = Mathf.Clamp(pb.hardAngle, 0f, 180f);
        param.packMargin = Mathf.Clamp(pb.packMargin, 1f, 64) * .001f;

        Unwrapping.GenerateSecondaryUVSet(pb.GetComponent <MeshFilter>().sharedMesh, param);

        EditorUtility.SetDirty(pb);
    }
示例#11
0
        private static bool GetMeshForComponent(ModelExporter exporter, pb_Object component, FbxNode fbxNode)
        {
            Mesh mesh = new Mesh();

            Material[] materials = null;
            pb_MeshCompiler.Compile(component, ref mesh, out materials, m_FbxOptions.quads ? MeshTopology.Quads : MeshTopology.Triangles);
            exporter.ExportMesh(mesh, fbxNode, materials);
            UnityEngine.Object.DestroyImmediate(mesh);

            // since probuilder can't handle mesh assets that may be externally reloaded, just strip pb
            // stuff for now.
            pb_Entity entity = component.GetComponent <pb_Entity>();

            component.dontDestroyMeshOnDelete = true;
            UnityEngine.Object.DestroyImmediate(component);
            if (entity != null)
            {
                UnityEngine.Object.DestroyImmediate(entity);
            }

            return(true);
        }
示例#12
0
    /**
     * Creates a new pb_Object instance with the provided vertices, faces, and sharedIndex information.
     */
    public static pb_Object CreateInstanceWithElements(Vector3[] v, Vector2[] u, Color[] c, pb_Face[] f, pb_IntArray[] si, pb_IntArray[] si_uv)
    {
        GameObject _gameObject = new GameObject();
        pb_Object  pb          = _gameObject.AddComponent <pb_Object>();

        pb.SetVertices(v);
        pb.SetUV(u);
        pb.SetColors(c);

        pb.SetSharedIndices(si ?? pb_IntArrayUtility.ExtractSharedIndices(v));

        pb.SetSharedIndicesUV(si_uv ?? new pb_IntArray[0] {
        });

        pb.SetFaces(f);

        pb.ToMesh();
        pb.Refresh();

        pb.GetComponent <pb_Entity>().SetEntity(EntityType.Detail);

        return(pb);
    }
示例#13
0
    private static void OnFaceChanged(pb_Object pb)
    {
        StaticEditorFlags flags = GameObjectUtility.GetStaticEditorFlags(pb.gameObject);

        // if nodraw found
        if (pb.containsNodraw)
        {
            if ((flags & StaticEditorFlags.BatchingStatic) == StaticEditorFlags.BatchingStatic)
            {
                flags ^= StaticEditorFlags.BatchingStatic;
                GameObjectUtility.SetStaticEditorFlags(pb.gameObject, flags);
            }
        }
        else
        {
            // if nodraw not found, and entity type should be batching static
            if (pb.GetComponent <pb_Entity>().entityType != EntityType.Mover)
            {
                flags = flags | StaticEditorFlags.BatchingStatic;
                GameObjectUtility.SetStaticEditorFlags(pb.gameObject, flags);
            }
        }
    }
示例#14
0
    public static void GenerateUV2(this pb_Object pb, bool show_NoDraw)
    {
        if (pb.onlyNodraw)
        {
            Vector2[] u = new Vector2[pb.msh.vertices.Length];
            for (int n = 0; n < u.Length; n++)
            {
                u[n] = Vector2.zero;
            }
            pb.SetUV2(u);
            return;
        }

        Vector2[] uvs = pb.msh.uv;              // nodraw uvs are nuked in this process, so save 'em
        pb.ToMesh(true);                        // re-draw meshes without nodraw faces

        // SetUVParams(8f, 15f, 15f, 20f);
        UnwrapParam param;

        UnwrapParam.SetDefaults(out param);

        param.angleError = Mathf.Clamp(pb.angleError, 1f, 75f) * .01f;
        param.areaError  = Mathf.Clamp(pb.areaError, 1f, 75f) * .01f;
        param.hardAngle  = Mathf.Clamp(pb.hardAngle, 0f, 180f);
        param.packMargin = Mathf.Clamp(pb.packMargin, 1f, 64) * .001f;

        Unwrapping.GenerateSecondaryUVSet(pb.GetComponent <MeshFilter>().sharedMesh, param);

        if (show_NoDraw)
        {
            pb.ToMesh(false);
        }

        pb.msh.uv = uvs;

        EditorUtility.SetDirty(pb);
    }
	private static void OnFaceChanged( pb_Object pb )
	{
		StaticEditorFlags flags = GameObjectUtility.GetStaticEditorFlags( pb.gameObject );
		
		// if nodraw found
		if(pb.containsNodraw)
		{
			if( (flags & StaticEditorFlags.BatchingStatic) == StaticEditorFlags.BatchingStatic )
			{
				flags ^= StaticEditorFlags.BatchingStatic;
				GameObjectUtility.SetStaticEditorFlags(pb.gameObject, flags);
			}
		}
		else
		{
			// if nodraw not found, and entity type should be batching static
			if(pb.GetComponent<pb_Entity>().entityType != EntityType.Mover)
			{
				flags = flags | StaticEditorFlags.BatchingStatic;
				GameObjectUtility.SetStaticEditorFlags(pb.gameObject, flags);
			}
		}
	}
示例#16
0
	/**
	 *	\brief Given an array of "donors", this method returns a merged #pb_Object.
	 */
	 public static bool CombineObjects(pb_Object[] pbs, out pb_Object combined)
	 {
	 	combined = null;

	 	if(pbs.Length < 1) return false;

	 	List<Vector3> v = new List<Vector3>();
	 	List<Vector2> u = new List<Vector2>();
	 	List<Color> c = new List<Color>();
	 	List<pb_Face> f = new List<pb_Face>();
	 	List<pb_IntArray> s = new List<pb_IntArray>();
	 	List<pb_IntArray> suv = new List<pb_IntArray>();

	 	foreach(pb_Object pb in pbs)
	 	{
	 		int vertexCount = v.Count;

	 		// Vertices
	 		v.AddRange(pb.VerticesInWorldSpace());

	 		// UVs
	 		u.AddRange(pb.uv);

	 		// Colors
	 		c.AddRange(pb.colors);

			// Faces
	 		pb_Face[] faces = new pb_Face[pb.faces.Length];
	 		for(int i = 0; i < faces.Length; i++)
	 		{
	 			faces[i] = new pb_Face(pb.faces[i]);
	 			faces[i].manualUV = true;
	 			faces[i].ShiftIndices(vertexCount);
	 			faces[i].RebuildCaches();
	 		}
	 		f.AddRange(faces);

	 		// Shared Indices
	 		pb_IntArray[] si = pb.GetSharedIndices();
	 		for(int i = 0; i < si.Length; i++)
	 		{
	 			for(int n = 0; n < si[i].Length; n++)
	 				si[i][n] += vertexCount;
	 		}
	 		s.AddRange(si);

	 		// Shared Indices UV
	 		{
		 		pb_IntArray[] si_uv = pb.GetSharedIndicesUV();
		 		for(int i = 0; i < si_uv.Length; i++)
		 		{
		 			for(int n = 0; n < si_uv[i].Length; n++)
		 				si_uv[i][n] += vertexCount;
		 		}

		 		suv.AddRange(si_uv);
		 	}
	 	}

		GameObject go = (GameObject)GameObject.Instantiate(pbs[0].gameObject);
	 	go.transform.position = Vector3.zero;
	 	go.transform.localRotation = Quaternion.identity;
	 	go.transform.localScale = Vector3.one;

	 	// Destroy the children
	 	foreach(Transform t in go.transform)
	 		GameObject.DestroyImmediate(t.gameObject);

	 	if(go.GetComponent<pb_Object>()) GameObject.DestroyImmediate(go.GetComponent<pb_Object>());
	 	if(go.GetComponent<pb_Entity>()) GameObject.DestroyImmediate(go.GetComponent<pb_Entity>());

	 	combined = go.AddComponent<pb_Object>();

		combined.SetVertices(v.ToArray());
		combined.SetUV(u.ToArray());
		combined.SetColors(c.ToArray());
		combined.SetFaces(f.ToArray());

		combined.SetSharedIndices( s.ToArray() ?? pb_IntArrayUtility.ExtractSharedIndices(v.ToArray()) );
		combined.SetSharedIndicesUV( suv.ToArray() ?? new pb_IntArray[0] {});

		combined.ToMesh();

		combined.GetComponent<pb_Entity>().SetEntity( pbs[0].GetComponent<pb_Entity>().entityType );
	 	
	 	combined.CenterPivot( pbs[0].transform.position );

		combined.Refresh();

		// refresh donors since deleting the children of the instantiated object could cause them to lose references
		foreach(pb_Object pb in pbs)
			pb.Verify();

	 	return true;
	 }
示例#17
0
        /**
         *	\brief Given an array of "donors", this method returns a merged #pb_Object.
         */
        public static bool CombineObjects(pb_Object[] pbs, out pb_Object combined)
        {
            combined = null;

            if (pbs.Length < 1)
            {
                return(false);
            }

            List <Vector3>     v   = new List <Vector3>();
            List <Vector2>     u   = new List <Vector2>();
            List <Color>       c   = new List <Color>();
            List <pb_Face>     f   = new List <pb_Face>();
            List <pb_IntArray> s   = new List <pb_IntArray>();
            List <pb_IntArray> suv = new List <pb_IntArray>();

            foreach (pb_Object pb in pbs)
            {
                int vertexCount = v.Count;

                // Vertices
                v.AddRange(pb.VerticesInWorldSpace());

                // UVs
                u.AddRange(pb.uv);

                // Colors
                c.AddRange(pb.colors);

                // Faces
                pb_Face[] faces = new pb_Face[pb.faces.Length];
                for (int i = 0; i < faces.Length; i++)
                {
                    faces[i]          = new pb_Face(pb.faces[i]);
                    faces[i].manualUV = true;
                    faces[i].ShiftIndices(vertexCount);
                    faces[i].RebuildCaches();
                }
                f.AddRange(faces);

                // Shared Indices
                pb_IntArray[] si = pb.GetSharedIndices();
                for (int i = 0; i < si.Length; i++)
                {
                    for (int n = 0; n < si[i].Length; n++)
                    {
                        si[i][n] += vertexCount;
                    }
                }
                s.AddRange(si);

                // Shared Indices UV
                {
                    pb_IntArray[] si_uv = pb.GetSharedIndicesUV();
                    for (int i = 0; i < si_uv.Length; i++)
                    {
                        for (int n = 0; n < si_uv[i].Length; n++)
                        {
                            si_uv[i][n] += vertexCount;
                        }
                    }

                    suv.AddRange(si_uv);
                }
            }

            GameObject go = (GameObject)GameObject.Instantiate(pbs[0].gameObject);

            go.transform.position      = Vector3.zero;
            go.transform.localRotation = Quaternion.identity;
            go.transform.localScale    = Vector3.one;

            // Destroy the children
            foreach (Transform t in go.transform)
            {
                GameObject.DestroyImmediate(t.gameObject);
            }

            if (go.GetComponent <pb_Object>())
            {
                GameObject.DestroyImmediate(go.GetComponent <pb_Object>());
            }
            if (go.GetComponent <pb_Entity>())
            {
                GameObject.DestroyImmediate(go.GetComponent <pb_Entity>());
            }

            combined = go.AddComponent <pb_Object>();

            combined.SetVertices(v.ToArray());
            combined.SetUV(u.ToArray());
            combined.SetColors(c.ToArray());
            combined.SetFaces(f.ToArray());

            combined.SetSharedIndices(s.ToArray() ?? pb_IntArrayUtility.ExtractSharedIndices(v.ToArray()));
            combined.SetSharedIndicesUV(suv.ToArray() ?? new pb_IntArray[0] {
            });

            combined.ToMesh();

            combined.GetComponent <pb_Entity>().SetEntity(pbs[0].GetComponent <pb_Entity>().entityType);

            combined.CenterPivot(pbs[0].transform.position);

            combined.Refresh();

            // refresh donors since deleting the children of the instantiated object could cause them to lose references
            foreach (pb_Object pb in pbs)
            {
                pb.Verify();
            }

            return(true);
        }
示例#18
0
        /**
         * Creates the icosphere, and loads all the cache information.
         */
        void Start()
        {
            audioSource = GetComponent <AudioSource>();

            if (audioSource.clip == null)
            {
                missingClipWarning.SetActive(true);
            }

            // Create a new icosphere.
            ico = pb_ShapeGenerator.IcosahedronGenerator(icoRadius, icoSubdivisions);

            // Shell is all the faces on the new icosphere.
            pb_Face[] shell = ico.faces;

            // Materials are set per-face on pb_Object meshes.  pb_Objects will automatically
            // condense the mesh to the smallest set of subMeshes possible based on materials.
#if !PROTOTYPE
            foreach (pb_Face f in shell)
            {
                f.material = material;
            }
#else
            ico.gameObject.GetComponent <MeshRenderer>().sharedMaterial = material;
#endif

            // Extrude all faces on the icosphere by a small amount.  The third boolean parameter
            // specifies that extrusion should treat each face as an individual, not try to group
            // all faces together.
            ico.Extrude(shell, ExtrudeMethod.IndividualFaces, startingExtrusion);

            // ToMesh builds the mesh positions, submesh, and triangle arrays.  Call after adding
            // or deleting vertices, or changing face properties.
            ico.ToMesh();

            // Refresh builds the normals, tangents, and UVs.
            ico.Refresh();

            outsides = new FaceRef[shell.Length];
            Dictionary <int, int> lookup = ico.sharedIndices.ToDictionary();

            // Populate the outsides[] cache.  This is a reference to the tops of each extruded column, including
            // copies of the sharedIndices.
            for (int i = 0; i < shell.Length; ++i)
            {
                outsides[i] = new FaceRef(shell[i],
                                          pb_Math.Normal(ico, shell[i]),
                                          ico.sharedIndices.AllIndicesWithValues(lookup, shell[i].distinctIndices).ToArray()
                                          );
            }

            // Store copy of positions array un-modified
            original_vertices = new Vector3[ico.vertices.Length];
            System.Array.Copy(ico.vertices, original_vertices, ico.vertices.Length);

            // displaced_vertices should mirror icosphere mesh vertices.
            displaced_vertices = ico.vertices;

            icoMesh      = ico.GetComponent <MeshFilter>().sharedMesh;
            icoTransform = ico.transform;

            faces_length = (float)outsides.Length;

            // Build the waveform ring.
            icoPosition = icoTransform.position;
#if UNITY_4_5 || UNITY_4_6 || UNITY_4_7 || UNITY_5_0 || UNITY_5_1 || UNITY_5_2 || UNITY_5_3 || UNITY_5_4
            waveform.SetVertexCount(WAVEFORM_SAMPLES);
#elif UNITY_5_5
            waveform.numPositions = WAVEFORM_SAMPLES;
#else
            waveform.positionCount = WAVEFORM_SAMPLES;
#endif


            if (bounceWaveform)
            {
                waveform.transform.parent = icoTransform;
            }

            audioSource.Play();
        }