void OLCTriangle::add_edges(const ScanTaskPoint& origin) { assert(origin.point_index < n_points); ScanTaskPoint destination(origin.stage_number + 1, origin.point_index + 1); switch (destination.stage_number) { case 1: // add points up to finish for (destination.point_index = 0; destination.point_index < origin.point_index; ++destination.point_index) { const unsigned d = distance(origin, destination); if (!is_fai || (4*d >= best_d)) { // no reason to add candidate if worse // than 25% rule for FAI tasks dijkstra.link(destination, origin, get_weighting(origin.stage_number) * d); } } break; case 2: { ScanTaskPoint previous = dijkstra.get_predecessor(origin); // give first leg points to penultimate node TriangleSecondLeg sl(is_fai, GetPointFast(previous), GetPointFast(origin)); for (; destination.point_index < n_points-1; ++destination.point_index) { TriangleSecondLeg::Result result = sl.Calculate(GetPointFast(destination), best_d); const unsigned d = result.leg_distance; if (d) { best_d = result.total_distance; dijkstra.link(destination, origin, get_weighting(origin.stage_number) * d); // we have an improved solution is_complete = true; // need to scan again whether path is closed is_closed = false; first_tp = origin.point_index; } } } break; case 3: // dummy just to close the triangle destination.point_index = n_points - 1; dijkstra.link(destination, origin, 0); break; default: assert(1); } }
fixed OLCDijkstra::calc_distance() const { fixed dist = fixed_zero; for (unsigned i = 0; i + 1 < num_stages; ++i) dist += get_weighting(i) * solution[i].distance(solution[i + 1].get_location()); static const fixed fixed_fifth(0.2); dist *= fixed_fifth; return dist; }
// ------------------------------------------------------------------- // spell to summon an obstacle // ------------------------------------------------------------------- void t_summon_obstacle::execute( t_combat_creature& caster ) { t_obstacle_data_array const& obstacle_data = get_obstacle_data(); int i; t_obstacle_weight_list weight_list; t_obstacle_weight weight; t_terrain_type terrain; t_obstacle_type type; int total = 0; t_map_point_2d origin = m_target_square - t_map_point_2d(1,1); t_combat_action_message message( *m_caster, get_action_text( false ) ); terrain = get_nearby_terrain( m_battlefield, origin, get_footprint_size() ); for (i = 0; i < obstacle_data.size(); i++) { weight.obstacle = &obstacle_data[i]; if (!weight.obstacle->obstacle.can_be_summoned()) continue; type = weight.obstacle->obstacle.get_type(); weight.weight = get_weighting( type ).terrain[terrain]; if (weight.weight <= 0) continue; total += weight.weight; weight_list.push_back( weight ); } if (total == 0) return; int choice = random( total ); t_obstacle_weight_list::iterator index = weight_list.begin(); for (; index != weight_list.end(); index++) { weight = *index; choice -= weight.weight; if (choice <= 0) break; } std::string name = weight.obstacle->name; double scale = m_battlefield.get_model_scale(); t_combat_object_model_cache cache = get_combat_object_model_cache( name, scale ); t_attackable_obstacle* obstacle; int power = m_caster->get_spell_power( m_spell ); obstacle = new t_attackable_obstacle( cache, power ); obstacle->place( m_battlefield, origin << k_battlefield_subcell_shift ); obstacle->fade_in( m_battlefield, 15, message ); pay_cost(); play_sound(); }
fixed ContestDijkstra::CalcScore() const { assert(num_stages <= MAX_STAGES); fixed score = fixed_zero; for (unsigned i = 0; i + 1 < num_stages; ++i) score += get_weighting(i) * solution[i].distance(solution[i + 1].get_location()); #define fixed_fifth fixed(0.0002) score *= fixed_fifth; return ApplyHandicap(score); }
void OLCDijkstra::add_edges(DijkstraTaskPoint &dijkstra, const ScanTaskPoint& origin) { ScanTaskPoint destination(origin.first + 1, origin.second); find_solution(dijkstra, origin); for (; destination.second != n_points; ++destination.second) { if (admit_candidate(destination)) { const unsigned d = get_weighting(origin.first) * distance(origin, destination); dijkstra.link(destination, origin, d); } } }
void ContestDijkstra::add_edges(const ScanTaskPoint& origin) { ScanTaskPoint destination(origin.stage_number + 1, origin.point_index); find_solution(origin); // only add last point! if (is_final(destination)) { assert(n_points > 0); destination.point_index = n_points - 1; } for (; destination.point_index != n_points; ++destination.point_index) { if (admit_candidate(destination)) { const unsigned d = get_weighting(origin.stage_number) * distance(origin, destination); dijkstra.link(destination, origin, d); } } }