replace small_spawn with something to instantiate any scenario for the map

This commit is contained in:
Dustin Carlino 2019-08-02 22:01:43 +02:00
parent f8cee896bf
commit 27e933fbf8
4 changed files with 118 additions and 31 deletions

View File

@ -105,3 +105,20 @@ https://www.reddit.com/r/gamedev/comments/2yfyi5/drawing_lines_is_hard/
https://blog.mapbox.com/drawing-antialiased-lines-with-opengl-8766f34192dc
http://artgrammer.blogspot.com/2011/07/drawing-polylines-by-tessellation.html
https://www.reddit.com/r/GraphicsProgramming/
- are all the sources of doubling back strangely just directly fixable in the geom?
- keep miter joins, but limit how far out we can explode?
- bevel joins
- outlines miss bevels on one edge
- now there are little gaps between adjacent lanes
- slow!
- some bugs that cover a thick triangular area
- refactor all the methods... confusing.
- ideas
- https://stackoverflow.com/questions/5641769/how-to-draw-an-outline-around-any-line
- http://old.cescg.org/CESCG99/SKrivograd/
- https://www.codeproject.com/Articles/226569/Drawing-polylines-by-tessellation
- https://stackoverflow.com/questions/36475254/polylines-outline-construction-drawing-thick-polylines
- https://forum.libcinder.org/topic/smooth-thick-lines-using-geometry-shader
- https://stackoverflow.com/questions/687173/how-do-i-render-thick-2d-lines-as-polygons

View File

@ -47,7 +47,7 @@ impl SandboxMode {
(hotkey(Key::Y), "load previous sim state"),
(hotkey(Key::U), "load next sim state"),
(hotkey(Key::X), "reset sim"),
(hotkey(Key::S), "seed the sim with agents"),
(hotkey(Key::S), "start a scenario"),
],
vec![
// TODO Strange to always have this. Really it's a case of stacked modal?
@ -96,8 +96,8 @@ impl State for SandboxMode {
return t;
}
if let Some(spawner) = spawner::AgentSpawner::new(ctx, ui, &mut self.menu) {
return Transition::Push(Box::new(spawner));
if let Some(new_state) = spawner::AgentSpawner::new(ctx, ui, &mut self.menu) {
return Transition::Push(new_state);
}
if let Some(explorer) = RouteExplorer::new(ctx, ui) {
return Transition::Push(Box::new(explorer));

View File

@ -4,10 +4,11 @@ use crate::helpers::ID;
use crate::render::DrawOptions;
use crate::ui::{ShowEverything, UI};
use abstutil::Timer;
use ezgui::{hotkey, EventCtx, GfxCtx, Key, ModalMenu};
use ezgui::{hotkey, EventCtx, GfxCtx, Key, ModalMenu, Wizard, WrappedWizard};
use geom::{Duration, PolyLine};
use map_model::{
BuildingID, IntersectionID, IntersectionType, LaneType, PathRequest, Position, LANE_THICKNESS,
BuildingID, IntersectionID, IntersectionType, LaneType, Map, PathRequest, Position,
LANE_THICKNESS,
};
use rand::seq::SliceRandom;
use rand::Rng;
@ -38,7 +39,7 @@ impl AgentSpawner {
ctx: &mut EventCtx,
ui: &mut UI,
sandbox_menu: &mut ModalMenu,
) -> Option<AgentSpawner> {
) -> Option<Box<State>> {
let menu = ModalMenu::new(
"Agent Spawner",
vec![vec![(hotkey(Key::Escape), "quit")]],
@ -51,22 +52,22 @@ impl AgentSpawner {
.input
.contextual_action(Key::F3, "spawn a pedestrian starting here")
{
return Some(AgentSpawner {
return Some(Box::new(AgentSpawner {
menu,
from: Source::Walking(id),
maybe_goal: None,
});
}));
}
if let Some(pos) = Position::bldg_via_driving(id, map) {
if ctx
.input
.contextual_action(Key::F4, "spawn a car starting here")
{
return Some(AgentSpawner {
return Some(Box::new(AgentSpawner {
menu,
from: Source::Driving(pos),
maybe_goal: None,
});
}));
}
}
}
@ -76,11 +77,11 @@ impl AgentSpawner {
.input
.contextual_action(Key::F3, "spawn an agent starting here")
{
return Some(AgentSpawner {
return Some(Box::new(AgentSpawner {
menu,
from: Source::Driving(Position::new(id, map.get_l(id).length() / 2.0)),
maybe_goal: None,
});
}));
}
}
Some(ID::Intersection(i)) => {
@ -92,25 +93,10 @@ impl AgentSpawner {
}
}
None => {
if ui.primary.sim.is_empty() {
if sandbox_menu.action("seed the sim with agents") {
// TODO This covers up the map. :\
ctx.loading_screen("seed sim with agents", |_, timer| {
let map = &ui.primary.map;
let s = if let Some(n) = ui.primary.current_flags.num_agents {
Scenario::scaled_run(map, n)
} else {
Scenario::small_run(map)
};
s.instantiate(
&mut ui.primary.sim,
map,
&mut ui.primary.current_flags.sim_flags.make_rng(),
timer,
);
ui.primary.sim.step(map, SMALL_DT);
});
}
if ui.primary.sim.is_empty() && sandbox_menu.action("start a scenario") {
return Some(Box::new(InstantiateScenario {
wizard: Wizard::new(),
}));
}
}
_ => {}
@ -371,3 +357,75 @@ fn spawn_agents_around(i: IntersectionID, ui: &mut UI, ctx: &EventCtx) {
sim.step(map, SMALL_DT);
ui.recalculate_current_selection(ctx);
}
// TODO Dedupe with code from mission/mod.rs.
struct InstantiateScenario {
wizard: Wizard,
}
impl State for InstantiateScenario {
fn event(&mut self, ctx: &mut EventCtx, ui: &mut UI) -> Transition {
if let Some(scenario) = pick_scenario(
ui.primary.current_flags.num_agents,
&ui.primary.map,
&mut self.wizard.wrap(ctx),
) {
ctx.loading_screen("instantiate scenario", |_, timer| {
scenario.instantiate(
&mut ui.primary.sim,
&ui.primary.map,
&mut ui.primary.current_flags.sim_flags.make_rng(),
timer,
);
ui.primary.sim.step(&ui.primary.map, SMALL_DT);
});
return Transition::Pop;
} else if self.wizard.aborted() {
return Transition::Pop;
}
Transition::Keep
}
fn draw(&self, g: &mut GfxCtx, _: &UI) {
self.wizard.draw(g);
}
}
fn pick_scenario(
num_agents: Option<usize>,
map: &Map,
wizard: &mut WrappedWizard,
) -> Option<Scenario> {
let builtin = if let Some(n) = num_agents {
format!("random scenario with {} agents", n)
} else {
"random scenario with some agents".to_string()
};
let map_name = map.get_name().to_string();
let (_, scenario_name) = wizard.choose_something_no_keys::<String>(
"Instantiate which scenario?",
Box::new(move || {
let mut list = vec![
(builtin.clone(), "builtin".to_string()),
("just buses".to_string(), "just buses".to_string()),
];
list.extend(abstutil::list_all_objects("scenarios", &map_name));
list
}),
)?;
Some(if scenario_name == "builtin" {
if let Some(n) = num_agents {
Scenario::scaled_run(map, n)
} else {
Scenario::small_run(map)
}
} else if scenario_name == "just buses" {
Scenario::empty(map)
} else {
abstutil::read_binary(
&format!("../data/scenarios/{}/{}.bin", map.get_name(), scenario_name),
&mut Timer::throwaway(),
)
.unwrap()
})
}

View File

@ -249,6 +249,18 @@ impl Scenario {
s
}
// Just buses.
pub fn empty(map: &Map) -> Scenario {
Scenario {
scenario_name: "just buses".to_string(),
map_name: map.get_name().to_string(),
seed_parked_cars: Vec::new(),
spawn_over_time: Vec::new(),
border_spawn_over_time: Vec::new(),
individ_trips: Vec::new(),
}
}
// No border agents here, because making the count work is hard.
pub fn scaled_run(map: &Map, num_agents: usize) -> Scenario {
Scenario {