double cTerrainGen2D::BuildNarrowGaps(double width, const tParams& params, cRand& rand, std::vector<float>& out_data) { double spacing_min = params[eParamsNarrowGapSpacingMin]; double spacing_max = params[eParamsNarrowGapSpacingMax]; double dist_min = params[eParamsNarrowGapDistMin]; double dist_max = params[eParamsNarrowGapDistMax]; double gap_w_min = params[eParamsNarrowGapWidthMin]; double gap_w_max = params[eParamsNarrowGapWidthMax]; double gap_d_min = params[eParamsNarrowGapDepthMin]; double gap_d_max = params[eParamsNarrowGapDepthMax]; int count_min = std::max(1, static_cast<int>(params[eParamsNarrowGapCountMin])); int count_max = std::max(1, static_cast<int>(params[eParamsNarrowGapCountMax])); double total_w = 0; while (total_w < width) { double spacing = rand.RandDouble(spacing_min, spacing_max); int count = rand.RandInt(count_min, count_max + 1); for (int i = 0; i < count; ++i) { double w = rand.RandDouble(gap_w_min, gap_w_max); double d = rand.RandDouble(gap_d_min, gap_d_max); double curr_w = AddBox(spacing, w, d, out_data); total_w += curr_w; spacing = rand.RandDouble(dist_min, dist_max); } } return total_w; }
double cTerrainGen2D::BuildMixed(double width, const tParams& params, cRand& rand, std::vector<float>& out_data) { double total_w = 0; const int num_types = 3; const double dummy_w = gVertSpacing; while (total_w < width) { double curr_w = 0; int rand_type = rand.RandInt(0, num_types); if (rand_type == 0) { curr_w = BuildGaps(dummy_w, params, rand, out_data); } else if (rand_type == 1) { curr_w = BuildSteps(dummy_w, params, rand, out_data); } else if (rand_type == 2) { curr_w = BuildWalls(dummy_w, params, rand, out_data); } total_w += curr_w; } return total_w; }
double cTerrainGen2D::BuildCliffs(double width, const tParams& params, cRand& rand, std::vector<float>& out_data) { double spacing_min = params[eParamsCliffSpacingMin]; double spacing_max = params[eParamsCliffSpacingMax]; double cliff_h0_min = params[eParamsCliffHeight0Min]; double cliff_h0_max = params[eParamsCliffHeight0Max]; double cliff_h1_min = params[eParamsCliffHeight1Min]; double cliff_h1_max = params[eParamsCliffHeight1Max]; int mini_count_max = static_cast<int>(params[eParamsCliffMiniCountMax]); double bump_h_min = params[eParamsBumpHeightMin]; double bump_h_max = params[eParamsBumpHeightMax]; const double delta_range = std::abs(params[eParamsSlopeDeltaRange]); const double delta_min = params[eParamsSlopeDeltaMin]; const double delta_max = params[eParamsSlopeDeltaMax]; int beg_idx = static_cast<int>(out_data.size()); double total_w = 0; while (total_w < width) { double min_h = 0; double max_h = 0; bool valid_h0 = (cliff_h0_min != 0 || cliff_h0_max != 0); bool valid_h1 = (cliff_h1_min != 0 || cliff_h1_max != 0); if (valid_h0 && valid_h1) { bool heads = rand.FlipCoin(); min_h = (heads) ? cliff_h0_min : cliff_h1_min; max_h = (heads) ? cliff_h0_max : cliff_h1_max; } else if (valid_h0) { min_h = cliff_h0_min; max_h = cliff_h0_max; } else { min_h = cliff_h1_min; max_h = cliff_h1_max; } double w = rand.RandDouble(spacing_min, spacing_max); double h = rand.RandDouble(min_h, max_h); double curr_w = 0; double curr_delta_h = 0; int num_mini = rand.RandInt(0, mini_count_max + 1); for (int i = 0; i < num_mini + 1; ++i) { const double mini_w = (i == 0) ? w : 0.1; double mini_h = rand.RandDouble(curr_delta_h, h); mini_h = (i == num_mini) ? h : mini_h; double dh = mini_h - curr_delta_h; curr_w += AddStep(mini_w, dh, out_data); curr_delta_h = mini_h; } total_w += curr_w; } int end_idx = static_cast<int>(out_data.size()); OverlaySlopes(delta_range, delta_min, delta_max, 0, beg_idx, end_idx, rand, out_data); OverlayBumps(bump_h_min, bump_h_max, beg_idx, end_idx, rand, out_data); return total_w; }