//for cloning public ShapeDataAbstract(ShapeDataAbstract data) { name = data.name; area = data.area; bounds = data.bounds; infoMode = data.infoMode; }
public void Refresh() { //Debug.LogWarning(needRefresh); //Debug.LogWarning(treeInstances.Count); if (needRefresh == false) { return; } needRefresh = false; System.Diagnostics.Stopwatch totalTime = new System.Diagnostics.Stopwatch(); totalTime.Start(); if (treeInstances.Count > 0) { ChunkContentMap.RemoveContent(treeInstances); } treeInstances.Clear(); terrain = GetComponent <Terrain>(); TerrainData terrainData = terrain.terrainData; TreePrototype[] prototypes = terrainData.treePrototypes; TreeInstance[] instances = terrainData.treeInstances; bool[] validPrototype = new bool[prototypes.Length]; treePrototypesData = new TreePrototypeData[prototypes.Length]; for (int i = 0; i < prototypes.Length; i++) { bool isValid = IsValidTreePrototype(prototypes[i]); validPrototype[i] = isValid; if (isValid == false) { continue; } GameObject treeInstance = Instantiate(prototypes[i].prefab); HashSet <Collider> tColliders = new HashSet <Collider>(); foreach (var item in treeInstance.GetComponents <Collider>()) { tColliders.Add(item); } foreach (var item in treeInstance.GetComponentsInChildren <Collider>()) { tColliders.Add(item); } if (tColliders.Count == 0) { continue; } Vector3 instancePos = treeInstance.transform.position; List <ShapeDataTreeAbstract> treePrototypeData = new List <ShapeDataTreeAbstract>(); foreach (var item in tColliders) { if (IsValidTreePrototypeCollider(item) == false) { continue; } Transform colliderTransfrom = item.transform; Vector3 transfromLocalPosition = colliderTransfrom.position - instancePos; Quaternion transfromRotation = colliderTransfrom.rotation; Vector3 transfromScale = colliderTransfrom.lossyScale; Matrix4x4 l2wMatrix = Matrix4x4.TRS(transfromLocalPosition, transfromRotation, transfromScale); if (item is BoxCollider) { treePrototypeData.Add(new ShapeDataTreeBox(l2wMatrix, item as BoxCollider)); } else if (item is SphereCollider) { treePrototypeData.Add(new ShapeDataTreeSphere(l2wMatrix, item as SphereCollider)); } else if (item is CapsuleCollider) { treePrototypeData.Add(new ShapeDataTreeCapsule(l2wMatrix, item as CapsuleCollider)); } else { Debug.LogWarningFormat("{0} right now is not supported on tree prototype {1}. only box, sphere and capsule supported. remind developer to add your thing on forum thread", item.GetType(), prototypes[i].prefab.name); } } DestroyImmediate(treeInstance); treePrototypesData[i] = new TreePrototypeData(treePrototypeData); } Vector3 terrainPos = transform.position; Vector3 terrainSize = terrainData.size; string terrainTag = terrain.gameObject.tag;; int terrainLayer = terrain.gameObject.layer; foreach (var instance in instances) { TreePrototypeData TPD = treePrototypesData[instance.prototypeIndex]; if (TPD.colliders == null || TPD.colliders.Count == 0) { continue; } Vector3 instanceWorldScale = new Vector3(instance.widthScale, instance.heightScale, instance.widthScale); Vector3 instanceWorldPos = Vector3.Scale(instance.position, terrainSize) + terrainPos; //Matrix4x4 localToWorldMatrix = Matrix4x4.TRS(instanceWorldPos, Quaternion.identity, instanceWorldScale); //Debuger_K.AddDot(instanceWorldPos, Color.red, 0.1f); //Debuger_K.AddLabelFormat(instanceWorldPos, "Rotation: {0}\nHeight: {1}\nWidth: {2}", instance.rotation * Mathf.Rad2Deg, instance.heightScale, instance.widthScale); //Quaternion rotation = Quaternion.Euler(0, instance.rotation * Mathf.Rad2Deg, 0); List <IShapeDataClonable> treeShapeData = new List <IShapeDataClonable>(); Bounds bounds = new Bounds(instanceWorldPos, new Vector3()); foreach (var item in TPD.colliders) { ShapeDataAbstract data = item.ReturnShapeConstructor(instanceWorldPos, instanceWorldScale); treeShapeData.Add(data as IShapeDataClonable); bounds.Encapsulate(data.bounds); } treeInstances.Add(new TreeInstanceData(this, treeShapeData, bounds)); } int colliders = 0; foreach (var item in treeInstances) { colliders += item.shapeData.Count; } Debug.LogFormat("Trees {0}, Colliders {1}", treeInstances.Count, colliders); if (treeInstances.Count > 0) { ChunkContentMap.Process(treeInstances); } //ChunkContentMap.SceneDebug(); totalTime.Stop(); Debug.Log("Terrain process time: " + totalTime.Elapsed); }