/// <summary> /// エリア生成(実体化)/(データ化) /// </summary> /// <param name="go">生成するエリアのprefab</param> /// <param name="position">生成座標</param> /// <param name="angle">エリアの回る角度</param> void CreateArea(GameObject go, AreaPrefabManager areaManager, Vector2 position, AngleFix angle) { if (mode == MakeMode.MakeSceneMode) { if (areaContainer == null) { areaContainer = new GameObject("Environment"); } GameObject gameObject = Instantiate(Resources.Load(go.name), new Vector3(position.x, 0, position.y), Quaternion.Euler(0, (int)angle, 0)) as GameObject; gameObject.transform.parent = areaContainer.transform; } else { areaDataList.Add( new AreaData( GameController._instance.GetGoingToFloor(), go.name, position.x, 0, position.y, angle, areaManager.GetAreaPrefabInfo(angle).width, areaManager.GetAreaPrefabInfo(angle).height)); bool isCreateEnemy = false; switch (areaManager.type) { case UnitType.Road: isCreateEnemy = Random.value > 0.75; break; case UnitType.Room: isCreateEnemy = Random.value > 0.25; break; case UnitType.End: isCreateEnemy = Random.value > 0.5; break; case UnitType.Corner: isCreateEnemy = Random.value > 0.75; break; } if (isCreateEnemy) { int enemyCount = Random.Range(1, areaManager.GetAreaPrefabInfo(angle).width * areaManager.GetAreaPrefabInfo(angle).height / 25); int enemyID = GameController._instance.GetRandomEnemyInfo().ID; enemyDataList.Add( new EnemyPositionData( GameController._instance.GetGoingToFloor(), enemyID, enemyCount, GameController._instance.GetGoingToFloor() + 11, position.x, 0.25f, position.y, areaManager.GetAreaPrefabInfo(angle).width, areaManager.GetAreaPrefabInfo(angle).height )); } } }
public override void OnInspectorGUI() { areaManager = (AreaPrefabManager)target; if (areaManager.AreaOutGOList == null) { areaManager.AreaOutGOList = new AreaPrefabOutGO[0]; } GUILayout.Label(string.Format("Input the Area's type and next Area's weight point")); areaManager.type= (UnitType)EditorGUILayout.EnumPopup("AreaType", areaManager.type); SerializedProperty basePoint = serializedObject.FindProperty("basePoint"); EditorGUILayout.PropertyField(basePoint); if (basePoint.isExpanded) { EditorGUI.indentLevel += 1; areaManager.basePoint.roadPoint = EditorGUILayout.IntField("roadPoint", areaManager.basePoint.roadPoint); areaManager.basePoint.roomPoint = EditorGUILayout.IntField("roomPoint", areaManager.basePoint.roomPoint); areaManager.basePoint.endPoint = EditorGUILayout.IntField("endPoint", areaManager.basePoint.endPoint); areaManager.basePoint.cornerPoint = EditorGUILayout.IntField("cornerPoint", areaManager.basePoint.cornerPoint); EditorGUI.indentLevel -= 1; } GUILayout.Label(string.Format("Input the data in rota 0°,then put the button to compute other data")); serializedObject.Update(); SerializedProperty areaOutGOList = serializedObject.FindProperty("AreaOutGOList"); EditorGUILayout.PropertyField(areaOutGOList); if (areaOutGOList.isExpanded) { EditorGUI.indentLevel += 1; EditorGUILayout.PropertyField(areaOutGOList.FindPropertyRelative("Array.size")); for (int j = 0; j < areaOutGOList.arraySize; j++) { SerializedProperty areaOut = areaOutGOList.GetArrayElementAtIndex(j); EditorGUILayout.PropertyField(areaOut); if (areaOut.isExpanded) { EditorGUI.indentLevel += 1; if (GUILayout.Button("Create Entry", GUILayout.Width(300))) { if (areaManager.transform.Find(string.Format("entry{0}", j)) == null) { GameObject entryGameObj = new GameObject(string.Format("entry{0}", j)); entryGameObj.transform.parent = areaManager.transform; entryGameObj.transform.localPosition = Vector3.zero; entryGameObj.transform.localScale = Vector3.one; areaManager.AreaOutGOList[j].location = entryGameObj; } } EditorGUILayout.BeginHorizontal(); EditorGUILayout.PropertyField(areaOut.FindPropertyRelative("location")); EditorGUILayout.PropertyField(areaOut.FindPropertyRelative("direction")); EditorGUILayout.EndHorizontal(); EditorGUI.indentLevel -= 1; } } EditorGUI.indentLevel -= 1; } serializedObject.ApplyModifiedProperties(); for (int angle = 0; angle < 360; angle += 90) { AreaPrefabInfo areaInfo = areaManager.AreaAngle0; switch (angle) { case 90: { areaInfo = areaManager.AreaAngle90; break; } case 180: { areaInfo = areaManager.AreaAngle180; break; } case 270: { areaInfo = areaManager.AreaAngle270; break; } default: break; } if (angle == 90) { if (GUILayout.Button("Compute other location info")) { ComputeRotInfo(); } } serializedObject.Update(); SerializedProperty areaInfoPro = serializedObject.FindProperty(string.Format("AreaAngle{0}", angle)); EditorGUILayout.PropertyField(areaInfoPro); EditorGUI.indentLevel += 1; if (areaInfoPro.isExpanded) { GUILayout.Label(string.Format("This is the data after rota {0}", angle)); areaInfo.height = EditorGUILayout.IntField("Height", areaInfo.height); areaInfo.width = EditorGUILayout.IntField("Width", areaInfo.width); areaInfo.centerPointUp = EditorGUILayout.Vector3Field("centerPointUp", new Vector3(-areaInfo.height / 2, 0, 0)); areaInfo.centerPointDown = EditorGUILayout.Vector3Field("centerPointDown", new Vector3(areaInfo.height / 2, 0, 0)); areaInfo.centerPointLeft = EditorGUILayout.Vector3Field("centerPointLeft", new Vector3(0, 0, -areaInfo.width / 2)); areaInfo.centerPointRight = EditorGUILayout.Vector3Field("centerPointRight", new Vector3(0, 0, areaInfo.width / 2)); SerializedProperty areaOutList = areaInfoPro.FindPropertyRelative("areaOut"); EditorGUILayout.PropertyField(areaOutList); if (areaOutList.isExpanded) { areaOutList.FindPropertyRelative("Array.size").intValue = areaManager.AreaOutGOList.Length; EditorGUI.indentLevel += 1; for (int j = 0; j < areaManager.AreaOutGOList.Length; j++) { SerializedProperty areaOut = areaOutList.GetArrayElementAtIndex(j); EditorGUILayout.PropertyField(areaOut); if (areaOut.isExpanded) { EditorGUI.indentLevel += 1; EditorGUILayout.BeginHorizontal(); SerializedProperty postion = areaOut.FindPropertyRelative("position"); SerializedProperty direction = areaOut.FindPropertyRelative("direction"); if (angle == 0) { if (areaManager.AreaOutGOList[j].location.Equals(null) || areaManager.AreaOutGOList[j].direction.Equals(null)) { postion.vector3Value = Vector3.zero; direction.intValue = -1; } else { postion.vector3Value = areaManager.AreaOutGOList[j].location.transform.localPosition; direction.intValue = (int)areaManager.AreaOutGOList[j].direction; } } EditorGUILayout.LabelField(string.Format("Position: x:{0} y:{1} z:{2}", postion.vector3Value.x, postion.vector3Value.y, postion.vector3Value.z)); EditorGUILayout.LabelField(string.Format("Direction: {0} ", (OutDirection)direction.intValue)); EditorGUILayout.EndHorizontal(); EditorGUI.indentLevel -= 1; } } EditorGUI.indentLevel -= 1; } } EditorGUI.indentLevel -= 1; serializedObject.ApplyModifiedProperties(); } //int pix = 10; //GUILayout.Label(string.Format("World : Map(virtual) = {0} : 1", pix)); }
/// <summary> /// ウェイトを調整 调整权重算法 /// </summary> /// <param name="makingAreaPrefabInfo">正在构造的地区的信息</param> /// <param name="thisFloorNumber">現在のエリア深度</param> void TrimWeightPoint(AreaPrefabManager makingAreaPrefabInfo, int thisFloorNumber) { makeingCombo = makingAreaPrefabInfo.type != makingAreaType ? 0 : makeingCombo + 1; if (makeingCombo > 0) { if (makingAreaPrefabInfo.type == UnitType.Road) { nowWeightPoint.CutWeight(UnitType.Road, 2); } else if (makingAreaPrefabInfo.type == UnitType.Corner) { nowWeightPoint.CutWeight(UnitType.Corner, 5); } } else { nowWeightPoint.cornerPoint = makingAreaPrefabInfo.basePoint.cornerPoint; nowWeightPoint.roadPoint = makingAreaPrefabInfo.basePoint.roadPoint; nowWeightPoint.roomPoint = makingAreaPrefabInfo.basePoint.roomPoint; nowWeightPoint.endPoint = makingAreaPrefabInfo.basePoint.endPoint; nowWeightPoint.AddWeight(UnitType.Corner, (10 - thisFloorNumber) >= 0 ? (10 - thisFloorNumber) * 2 : 0); nowWeightPoint.CutWeight(UnitType.Road, (10 - thisFloorNumber) >= 0 ? (10 - thisFloorNumber) : 0); nowWeightPoint.CutWeight(UnitType.Room, (10 - thisFloorNumber) >= 0 ? (10 - thisFloorNumber) : 0); nowWeightPoint.CutWeight(UnitType.End, (10 - thisFloorNumber) >= 0 ? (10 - thisFloorNumber) * 3 : 0); } }
/// <summary> /// 検証:このエリアの生成場所は指定されたマップサイズに超えたか 验证该地区是否超过地图尺寸 /// </summary> /// <param name="position">エリアの中心座標 区域地点</param> /// <param name="areaManager">エリアの情報クラス 区域信息</param> /// <param name="angle">エリア回る角度 是否旋转</param> /// <returns>この検証を通過できるかどうか TRUE=通過 返回是否通过检测 TRUE=通过</returns> bool checkInMap(Vector3 position, AreaPrefabManager areaManager, AngleFix angle) { AreaPrefabInfo info = areaManager.GetAreaPrefabInfo(angle); bool sizeCheck = checkSize(new Vector2(position.x, position.z), info.width, info.height); return sizeCheck; }
/// <summary> /// Simple AABB check /// </summary> /// <param name="position">エリアの中心座標 区域地点</param> /// <param name="areaManager">エリアの情報クラス 区域信息</param> /// <param name="angle">エリア回る角度 是否旋转</param> /// <returns>この検証を通過できるかどうか TRUE=通過 返回是否通过检测 TRUE=通过</returns> bool CheckAreaOverlay(Vector3 position, AreaPrefabManager areaManager, AngleFix angle) { AreaPrefabInfo info = areaManager.GetAreaPrefabInfo(angle); bool OverlayCheck = true; Vector3 relativePosition; for (int i = 0; i < areaDataList.Count; i++) { relativePosition = areaDataList[i].areaPosition - position; if (Mathf.Abs(relativePosition.x) < areaDataList[i].heightHalf + info.centerPointUp.magnitude && Mathf.Abs(relativePosition.z) < areaDataList[i].widthHalf + info.centerPointLeft.magnitude ) { OverlayCheck = false; break; } } return OverlayCheck; }
/// <summary> /// 検証:CapsuleCastを使用し、他のエリアと被るかどうか 用投影的方式确认该地区是否与其他地区重合 /// </summary> /// <param name="position">エリアの中心座標 区域地点</param> /// <param name="areaManager">エリアの情報クラス 区域信息</param> /// <param name="angle">エリア回る角度 是否旋转</param> /// <returns>この検証を通過できるかどうか TRUE=通過 返回是否通过检测 TRUE=通过</returns> bool CheckAreaPhysics(Vector3 position, AreaPrefabManager areaManager, AngleFix angle) { AreaPrefabInfo info = areaManager.GetAreaPrefabInfo(angle); bool physicsCheck = false; //left to right if (info.width > info.height) { //width>height:左から右までのCapsuleCast検証 宽大于长,从左到右 physicsCheck = Physics.CapsuleCast( position + new Vector3(0, 100, info.centerPointLeft.z + 1 + info.centerPointUp.magnitude > 0 ? 0 : info.centerPointLeft.z + 1 + info.centerPointUp.magnitude), position + new Vector3(0, 100, info.centerPointRight.z - 1 - info.centerPointUp.magnitude < 0 ? 0 : info.centerPointRight.z - 1 - info.centerPointUp.magnitude), info.centerPointUp.magnitude - 1f, Vector3.down); } else { //height>width:上から下までのCapsuleCast検証 长大于宽,从上到下 physicsCheck = Physics.CapsuleCast( position + new Vector3(info.centerPointUp.x + 1 + info.centerPointLeft.magnitude > 0 ? 0 : info.centerPointUp.x + 1 + info.centerPointLeft.magnitude, 100, 0), position + new Vector3(info.centerPointDown.x - 1 - info.centerPointLeft.magnitude < 0 ? 0 : info.centerPointDown.x - 1 - info.centerPointLeft.magnitude, 100, 0), info.centerPointLeft.magnitude - 1f, Vector3.down); } //Debug.Log(physicsCheck); return !physicsCheck; }
/// <summary> /// ランダムで可能な角度の中に一つの角度を貰う 在规定范围内产生随机方向 /// </summary> /// <param name="position">エリアの中心座標 生成的位置</param> /// <param name="areaInfo">エリアの情報クラス 需要生成的区域信息</param> /// <returns>方向的Int值()</returns> AngleFix RandomMapRotation(Vector2 position, AreaPrefabManager areaInfo) { List<AngleFix> canSetDirection = new List<AngleFix>(); if (checkSize(position, areaInfo.AreaAngle0.width, areaInfo.AreaAngle0.height)) { canSetDirection.Add(AngleFix.Angle0); canSetDirection.Add(AngleFix.Angle180); } if (checkSize(position, areaInfo.AreaAngle90.width, areaInfo.AreaAngle90.height)) { canSetDirection.Add(AngleFix.Angle90); canSetDirection.Add(AngleFix.Angle270); } return canSetDirection.Count == 0 ? AngleFix.none : canSetDirection[RandomIndex(canSetDirection.Count)]; }