/// <summary> /// 部屋を作成する /// </summary> /// <returns></returns> private IEnumerator <float> CreateRoom() { for (int i = 0; i < MapRect.RectCount; ++i) { var rectData = MapRect[i]; var rect = rectData.rect; // 矩形の大きさを計算 var w = rect.width - 3; var h = rect.height - 3; // 区画に入る最小部屋の余裕を求める var cw = w - _data.RoomMinSize; var ch = h - _data.RoomMinSize; // 部屋の大きさを決定する var sw = UnityEngine.Random.Range(0, cw + 1); var sh = UnityEngine.Random.Range(0, ch + 1); var rw = w - sw; var rh = h - sh; // 部屋の位置を決定する var rx = UnityEngine.Random.Range(0, sw + 1) + 2; var ry = UnityEngine.Random.Range(0, sh + 1) + 2; // 求めた結果から部屋の情報を設定 rectData.room.xMin = rect.xMin + rx; rectData.room.yMin = rect.yMin + ry; rectData.room.xMax = rect.xMin + rx + rw; rectData.room.yMax = rect.yMin + ry + rh; var room = rectData.room; // 部屋を作る TileDataMap.FillRect(room.xMin, room.yMin, room.xMax, room.yMax, TileFlag.Floor); yield return(0.5f); } }
private IEnumerator <float> CreateEntrance(TileDataMap prevTildeDataMap) { if (prevTildeDataMap == null) { // 部屋のマップを作成する TileDataMap.BuildRoomMap(); yield break; } // 前マップの下階段の位置に部屋を作成する // 下り階段の場所が部屋なら何もしない var stepDownPos = prevTildeDataMap.StepDownPos; var tileData = TileDataMap.GetTile(stepDownPos.x, stepDownPos.y); if (tileData.HasFlag(TileFlag.Floor)) { // 部屋のマップを作成する TileDataMap.BuildRoomMap(); yield break; } // 3マスで部屋を作成 var w = Utility.Random.MaxIncludedRange(1, 1); var h = Utility.Random.MaxIncludedRange(1, 1); // どこかの部屋か道と連結したら終わり var xMin = stepDownPos.x - 1; // - w / 2; var xMax = stepDownPos.x + 1; // + w / 2; var yMin = stepDownPos.y - 1; // - h / 2; var yMax = stepDownPos.y + 1; // + h / 2; bool shouldCreateRoad = true; // 隣接しているかチェック for (int y = yMin; y < yMax; ++y) { for (int x = xMin; x < xMax; ++x) { if (!TileDataMap.InRange(x, y)) { continue; } if (TileDataMap.IsAdjacent(x, y, TileFlag.Floor | TileFlag.Road)) { shouldCreateRoad = false; break; } } } TileDataMap.FillRect(xMin, yMin, xMax, yMax, TileFlag.Floor, tileData_ => { return(true); }); // 部屋のマップを作成する TileDataMap.BuildRoomMap(); // 道を作る必要がある場合作成 if (shouldCreateRoad) { // 部屋マップの値を取得 var roomValue = TileDataMap.GetRoomIndex(stepDownPos.x, stepDownPos.y); // 一番近い部屋か道とつなげる var route = new Route.Tracking(); route.Setup(TileDataMap); // 自分の部屋は1とする。 // 自分以外の部屋か道が見つかったら終わり route.Execute(stepDownPos.x, stepDownPos.y, (tracking_, cellPos_, newValue_, oldValue_) => { // 自分の部屋か if (TileDataMap.EqualRoomMapValue(cellPos_.x, cellPos_.y, roomValue)) { // すでに書き込まれていたらスキップ if (oldValue_ == 1) { return(-1); } // 自分の部屋は 1 として書き込む return(1); } // 自分が2(部屋の外周)じゃないのに部屋の隣りにいるならばだめ if (newValue_ > 2) { if (Utility.Map.CallDirection(cellPos_.x, cellPos_.y, (x_, y_) => { // 自分の部屋があればおわり return(TileDataMap.EqualRoomMapValue(x_, y_, roomValue)); })) { return(-1); } } // 前後左右が自分以外の部屋か道ならおわり Utility.Map.CallDirection(cellPos_.x, cellPos_.y, (x_, y_) => { if (!TileDataMap.InRange(x_, y_)) { return(false); } if (TileDataMap.EqualRoomMapValue(x_, y_, roomValue)) { return(false); } // 部屋か道を見つける var tileFlag = TileDataMap.GetTileFlag(x_, y_); if (tileFlag.HasFlag(TileFlag.Floor) || tileFlag.HasFlag(TileFlag.Road)) { tracking_.ProcessFinish(); return(true); } return(false); }); return(0); }); // ルートを道にする var posList = route.GetRoute(route.ForceFinishPos, useDiagonal: false); foreach (var pos in posList) { // 部屋なら何もしない if (TileDataMap.GetTileFlag(pos.x, pos.y).HasFlag(TileFlag.Floor)) { continue; } TileDataMap.SetTileFlag(pos, TileFlag.Road); } } }