Exemplo n.º 1
0
        /// <summary>
        /// Build an object once at a time, to be reiterated until false is returned.
        /// </summary>
        /// <param name="parentObj">Game object to which the new objects will be attached</param>
        /// <param name="mats">Materials from the previously loaded library</param>
        /// <returns>Return true until no more objects can be added, then false.</returns>
        protected bool BuildNextObject(GameObject parentObj, Dictionary <string, Material> mats)
        {
            // if all the objects were built stop here
            if (buildStatus.objCount >= currDataSet.objectList.Count)
            {
                return(false);
            }

            // get the next object in the list
            DataSet.ObjectData objData = currDataSet.objectList[buildStatus.objCount];

            if (buildStatus.newObject)
            {
                if (buildStatus.objCount == 0 && objData.name == "default")
                {
                    buildStatus.currObjGameObject = parentObj;
                }
                else
                {
                    buildStatus.currObjGameObject = new GameObject();
                    buildStatus.currObjGameObject.transform.parent = parentObj.transform;
                    buildStatus.currObjGameObject.name             = objData.name;
                    // restore the scale if the parent was rescaled
                    buildStatus.currObjGameObject.transform.localScale = Vector3.one;
                }
                buildStatus.subObjParent = buildStatus.currObjGameObject;

                //if (od.Name != "default") go.name = od.Name;
                //Debug.Log("Object: " + objData.name);
                buildStatus.newObject       = false;
                buildStatus.subObjCount     = 0;
                buildStatus.idxCount        = 0;
                buildStatus.grpIdx          = 0;
                buildStatus.grpFaceIdx      = 0;
                buildStatus.meshPartIdx     = 0;
                buildStatus.totFaceIdxCount = 0;
                buildStatus.numGroups       = Mathf.Max(1, objData.faceGroups.Count);
            }

            bool splitLargeMeshes = true;

#if UNITY_2017_3_OR_NEWER
            // GPU support for 32 bit indices is not guaranteed on all platforms;
            // for example Android devices with Mali-400 GPU do not support them.
            // This check is performed in Using32bitIndices().
            // If nothing is rendered on your device problably Using32bitIndices() must be updated.
            if (Using32bitIndices())
            {
                splitLargeMeshes = false;
            }
#endif
            bool splitGrp = false;

            DataSet.FaceGroupData grp = new DataSet.FaceGroupData();
            grp.name         = objData.faceGroups[buildStatus.grpIdx].name;
            grp.materialName = objData.faceGroups[buildStatus.grpIdx].materialName;


            // data for sub-object
            DataSet.ObjectData subObjData = new DataSet.ObjectData();
            subObjData.hasNormals = objData.hasNormals;
            subObjData.hasColors  = objData.hasColors;

            HashSet <int> vertIdxSet = new HashSet <int>();

            bool conv2sided = buildOptions != null && buildOptions.convertToDoubleSided;

            int maxIdx4mesh = conv2sided ? MAX_INDICES_LIMIT_FOR_A_MESH / 2 : MAX_INDICES_LIMIT_FOR_A_MESH;

            // copy blocks of face indices to each sub-object data
            for (int f = buildStatus.grpFaceIdx; f < objData.faceGroups[buildStatus.grpIdx].faces.Count; f++)
            {
                // if large meshed must be split and
                // if passed the max num of vertices and not at the last iteration
                if (splitLargeMeshes && (vertIdxSet.Count / 3 > MAX_VERT_COUNT / 3 || subObjData.allFaces.Count / 3 > maxIdx4mesh / 3))
                {
                    // split the group across more objects
                    splitGrp = true;
                    buildStatus.grpFaceIdx = f;
                    Debug.LogWarningFormat("Maximum vertex number for a mesh exceeded.\nSplitting object {0} (group {1}, starting from index {2})...", grp.name, buildStatus.grpIdx, f);
                    break;
                }
                DataSet.FaceIndices fi = objData.faceGroups[buildStatus.grpIdx].faces[f];
                subObjData.allFaces.Add(fi);
                grp.faces.Add(fi);
                vertIdxSet.Add(fi.vertIdx);
            }
            if (splitGrp || buildStatus.meshPartIdx > 0)
            {
                buildStatus.meshPartIdx++;
            }
            // create an empty (group) object in case the group has been splitted
            if (buildStatus.meshPartIdx == 1)
            {
                GameObject grpObj = new GameObject();
                grpObj.transform.SetParent(buildStatus.currObjGameObject.transform, false);
                grpObj.name = grp.name;
                buildStatus.subObjParent = grpObj;
            }

            // add a suffix to the group name in case the group has been splitted
            if (buildStatus.meshPartIdx > 0)
            {
                grp.name = buildStatus.subObjParent.name + "_MeshPart" + buildStatus.meshPartIdx;
            }
            subObjData.name = grp.name;

            // add the group to the sub object data
            subObjData.faceGroups.Add(grp);

            // update the start index
            buildStatus.idxCount += subObjData.allFaces.Count;

            if (!splitGrp)
            {
                buildStatus.grpFaceIdx = 0;
                buildStatus.grpIdx++;
            }
            buildStatus.totFaceIdxCount += subObjData.allFaces.Count;
            GameObject subobj = ImportSubObject(buildStatus.subObjParent, subObjData, mats);
            if (subobj == null)
            {
                Debug.LogWarningFormat("Error loading sub object n.{0}.", buildStatus.subObjCount);
            }
            //else Debug.LogFormat( "Imported face indices: {0} to {1}", buildStatus.totFaceIdxCount - sub_od.AllFaces.Count, buildStatus.totFaceIdxCount );

            buildStatus.subObjCount++;

            if (buildStatus.totFaceIdxCount >= objData.allFaces.Count || buildStatus.grpIdx >= objData.faceGroups.Count)
            {
                if (buildStatus.totFaceIdxCount != objData.allFaces.Count)
                {
                    Debug.LogWarningFormat("Imported face indices: {0} of {1}", buildStatus.totFaceIdxCount, objData.allFaces.Count);
                    return(false);
                }
                buildStatus.objCount++;
                buildStatus.newObject = true;
            }
            return(true);
        }
Exemplo n.º 2
0
        /// <summary>
        /// Build an object once at a time, to be reiterated until false is returned.
        /// </summary>
        /// <param name="parentObj">Game object to which the new objects will be attached</param>
        /// <param name="mats">Materials from the previously loaded library</param>
        /// <returns>Return true until no more objects can be added, then false.</returns>
        protected bool BuildNextObject(GameObject parentObj, Dictionary <string, Material> mats)
        {
            if (buildStatus.objCount >= currDataSet.objectList.Count)
            {
                return(false);
            }
            DataSet.ObjectData objData = currDataSet.objectList[buildStatus.objCount];

            if (buildStatus.newObject)
            {
                if (buildStatus.objCount == 0 && objData.name == "default")
                {
                    buildStatus.currObjGameObject = parentObj;
                }
                else
                {
                    buildStatus.currObjGameObject = new GameObject();
                    buildStatus.currObjGameObject.transform.parent = parentObj.transform;
                    buildStatus.currObjGameObject.name             = objData.name;
                    // restore the scale if the parent was rescaled
                    buildStatus.currObjGameObject.transform.localScale = Vector3.one;
                }
                buildStatus.subObjParent = buildStatus.currObjGameObject;

                //if (od.Name != "default") go.name = od.Name;
                //Debug.Log("Object: " + objData.name);
                buildStatus.newObject       = false;
                buildStatus.subObjCount     = 0;
                buildStatus.idxCount        = 0;
                buildStatus.grpIdx          = 0;
                buildStatus.grpFaceIdx      = 0;
                buildStatus.meshPartIdx     = 0;
                buildStatus.totFaceIdxCount = 0;
                buildStatus.numGroups       = Mathf.Max(1, objData.faceGroups.Count);
            }

            // data for sub-object
            DataSet.ObjectData subObjData = new DataSet.ObjectData();
            subObjData.hasNormals = objData.hasNormals;

            HashSet <int> vertIdxSet = new HashSet <int>();

            bool splitGrp = false;

            DataSet.FaceGroupData grp = new DataSet.FaceGroupData();
            grp.name         = objData.faceGroups[buildStatus.grpIdx].name;
            grp.materialName = objData.faceGroups[buildStatus.grpIdx].materialName;

            // copy blocks of face indices to each sub-object data
            for (int f = buildStatus.grpFaceIdx; f < objData.faceGroups[buildStatus.grpIdx].faces.Count; f++)
            {
                // if passed the max num of vertices and not at the last iteration
                if (vertIdxSet.Count / 3 > MAX_VERT_COUNT / 3 || subObjData.allFaces.Count / 3 > MAX_INDICES_LIMIT_FOR_A_MESH / 3)
                {
                    // split the group across more objects
                    splitGrp = true;
                    buildStatus.grpFaceIdx = f;
                    Debug.LogWarningFormat("Maximum vertex number for a mesh exceeded.\nSplitting object {0} ({1}th group, starting from index {2})...", grp.name, buildStatus.grpIdx, f);
                    break;
                }
                DataSet.FaceIndices fi = objData.faceGroups[buildStatus.grpIdx].faces[f];
                subObjData.allFaces.Add(fi);
                grp.faces.Add(fi);
                vertIdxSet.Add(fi.vertIdx);
            }
            if (splitGrp || buildStatus.meshPartIdx > 0)
            {
                buildStatus.meshPartIdx++;
            }
            // create an empty (group) object in case the group has been splitted
            if (buildStatus.meshPartIdx == 1)
            {
                GameObject grpObj = new GameObject();
                grpObj.transform.SetParent(buildStatus.currObjGameObject.transform, false);
                grpObj.name = grp.name;
                buildStatus.subObjParent = grpObj;
            }

            // add a suffix to the group name in case the group has been splitted
            if (buildStatus.meshPartIdx > 0)
            {
                grp.name = buildStatus.subObjParent.name + "_MeshPart" + buildStatus.meshPartIdx;
            }
            subObjData.name = grp.name;

            // add the group to the sub object data
            subObjData.faceGroups.Add(grp);

            // update the start index
            buildStatus.idxCount += subObjData.allFaces.Count;

            if (!splitGrp)
            {
                buildStatus.grpFaceIdx = 0;
                buildStatus.grpIdx++;
            }
            buildStatus.totFaceIdxCount += subObjData.allFaces.Count;
            GameObject subobj = ImportSubObject(buildStatus.subObjParent, subObjData, mats);

            if (subobj == null)
            {
                Debug.LogWarningFormat("Error loading sub object n.{0}.", buildStatus.subObjCount);
            }
            //else Debug.LogFormat( "Imported face indices: {0} to {1}", buildStatus.totFaceIdxCount - sub_od.AllFaces.Count, buildStatus.totFaceIdxCount );

            buildStatus.subObjCount++;

            if (buildStatus.totFaceIdxCount >= objData.allFaces.Count || buildStatus.grpIdx >= objData.faceGroups.Count)
            {
                if (buildStatus.totFaceIdxCount != objData.allFaces.Count)
                {
                    Debug.LogWarningFormat("Imported face indices: {0} of {1}", buildStatus.totFaceIdxCount, objData.allFaces.Count);
                    return(false);
                }
                buildStatus.objCount++;
                buildStatus.newObject = true;
            }
            return(true);
        }