Added traffic
This commit is contained in:
@@ -11,6 +11,7 @@
|
||||
#include "road_grid.h"
|
||||
#include "roads.h"
|
||||
#include "spawner.h"
|
||||
#include "traffic.h"
|
||||
|
||||
void register_world_types()
|
||||
{
|
||||
@@ -22,6 +23,8 @@ void register_world_types()
|
||||
Engine::get_singleton()->add_singleton(Engine::Singleton("RoadsData", RoadsData::get_singleton()));
|
||||
Spawner::create_singleton();
|
||||
Engine::get_singleton()->add_singleton(Engine::Singleton("Spawner", Spawner::get_singleton()));
|
||||
Traffic::create_singleton();
|
||||
Engine::get_singleton()->add_singleton(Engine::Singleton("Traffic", Traffic::get_singleton()));
|
||||
ClassDB::register_class<WorldGenerator>();
|
||||
ClassDB::register_class<WorldHeightMap>();
|
||||
ClassDB::register_class<DensityMap>();
|
||||
@@ -35,6 +38,9 @@ void register_world_types()
|
||||
|
||||
void unregister_world_types()
|
||||
{
|
||||
RoadsData::destroy_singleton();
|
||||
Spawner::destroy_singleton();
|
||||
Traffic::destroy_singleton();
|
||||
WorldMapData::destroy_singleton();
|
||||
}
|
||||
|
||||
|
||||
@@ -14,6 +14,7 @@ RoadGrid::RoadGrid()
|
||||
{
|
||||
grid_width = 16;
|
||||
grid_height = 16;
|
||||
astar.instance();
|
||||
}
|
||||
|
||||
RoadGrid::~RoadGrid()
|
||||
@@ -336,6 +337,10 @@ void RoadGrid::build(Ref<Curve> curve, Ref<FastNoiseLite> noise)
|
||||
}
|
||||
map_sites.write[i].avg_height = min_height * 0.7f + max_height * 0.3f;
|
||||
}
|
||||
for (i = 0; i < vertices.size(); i++)
|
||||
astar->add_point(i, vertices[i], 20.0f);
|
||||
for (i = 0; i < map_hedges.size(); i++)
|
||||
astar->connect_points(map_hedges[i]->a, map_hedges[i]->b, false);
|
||||
generate_building_positions();
|
||||
printf("building 3rd dimention done\n");
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
#include <core/reference.h>
|
||||
#include <scene/resources/curve.h>
|
||||
#include <core/math/random_number_generator.h>
|
||||
#include <core/math/a_star.h>
|
||||
#include <modules/voxel/util/noise/fast_noise_lite.h>
|
||||
|
||||
class CanvasItem;
|
||||
@@ -144,6 +145,7 @@ class RoadGrid: public Reference {
|
||||
GDCLASS(RoadGrid, Object)
|
||||
protected:
|
||||
Ref<RandomNumberGenerator> rnd;
|
||||
Ref<AStar> astar;
|
||||
int keep_seed;
|
||||
List<struct cluster> clusters;
|
||||
Rect2 bounds;
|
||||
@@ -369,5 +371,29 @@ public:
|
||||
}
|
||||
PoolVector<Vector3> get_site_border(int site, float offt);
|
||||
PoolVector<Vector3> get_site_radial_points(int site, float bofft, float offt);
|
||||
Ref<AStar> get_astar() const
|
||||
{
|
||||
return astar;
|
||||
}
|
||||
inline int get_closest_point(Vector3 to_position, bool include_disabled=false) const
|
||||
{
|
||||
return astar->get_closest_point(to_position, include_disabled);
|
||||
}
|
||||
inline Vector3 get_closest_position_in_segment(Vector3 to_position) const
|
||||
{
|
||||
return astar->get_closest_position_in_segment(to_position);
|
||||
}
|
||||
inline PoolVector<Vector3> get_point_path(int p_from_id, int p_to_id)
|
||||
{
|
||||
return astar->get_point_path(p_from_id, p_to_id);
|
||||
}
|
||||
inline PoolVector<int> get_id_path(int p_from_id, int p_to_id)
|
||||
{
|
||||
return astar->get_id_path(p_from_id, p_to_id);
|
||||
}
|
||||
inline Vector3 get_point_position(int p_id) const
|
||||
{
|
||||
return astar->get_point_position(p_id);
|
||||
}
|
||||
};
|
||||
#endif
|
||||
|
||||
@@ -574,6 +574,12 @@ void RoadsData::_bind_methods()
|
||||
ClassDB::bind_method(D_METHOD("get_site_type", "site"), &RoadsData::get_site_type);
|
||||
ClassDB::bind_method(D_METHOD("get_site_border", "site", "offt"), &RoadsData::get_site_border);
|
||||
ClassDB::bind_method(D_METHOD("get_site_radial_points", "site", "bofft", "offt"), &RoadsData::get_site_radial_points);
|
||||
ClassDB::bind_method(D_METHOD("get_closest_point", "to_position"), &RoadsData::get_closest_point);
|
||||
ClassDB::bind_method(D_METHOD("get_closest_position_in_segment", "to_position"), &RoadsData::get_closest_position_in_segment);
|
||||
ClassDB::bind_method(D_METHOD("get_point_path", "p_from_id", "p_to_id"), &RoadsData::get_point_path);
|
||||
ClassDB::bind_method(D_METHOD("get_id_path", "p_from_id", "p_to_id"), &RoadsData::get_id_path);
|
||||
ClassDB::bind_method(D_METHOD("get_point_position", "p_id"), &RoadsData::get_point_position);
|
||||
|
||||
}
|
||||
void RoadsData::set_noise(Ref<FastNoiseLite> noise)
|
||||
{
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
#ifndef ROADS_H
|
||||
#define ROADS_H
|
||||
#include <modules/world/road_grid.h>
|
||||
|
||||
#include <scene/main/node.h>
|
||||
@@ -150,5 +152,30 @@ public:
|
||||
{
|
||||
return rg->get_site_radial_points(site, bofft, offt);
|
||||
}
|
||||
inline Ref<AStar> get_astar() const
|
||||
{
|
||||
return rg->get_astar();
|
||||
}
|
||||
inline int get_closest_point(Vector3 to_position, bool include_disabled=false) const
|
||||
{
|
||||
return rg->get_closest_point(to_position, include_disabled);
|
||||
}
|
||||
inline Vector3 get_closest_position_in_segment(Vector3 to_position) const
|
||||
{
|
||||
return rg->get_closest_position_in_segment(to_position);
|
||||
}
|
||||
inline PoolVector<Vector3> get_point_path(int p_from_id, int p_to_id)
|
||||
{
|
||||
return rg->get_point_path(p_from_id, p_to_id);
|
||||
}
|
||||
inline PoolVector<int> get_id_path(int p_from_id, int p_to_id)
|
||||
{
|
||||
return rg->get_id_path(p_from_id, p_to_id);
|
||||
}
|
||||
inline Vector3 get_point_position(int p_id) const
|
||||
{
|
||||
return rg->get_point_position(p_id);
|
||||
}
|
||||
};
|
||||
#endif
|
||||
|
||||
|
||||
@@ -104,34 +104,38 @@ void Spawner::update_view(Node *node, float distance)
|
||||
int i;
|
||||
PoolVector<struct spawn_object> pos = positions[*key];
|
||||
for (i = 0; i < pos.size(); i++) {
|
||||
if (!pos[i].active) {
|
||||
if (!pos[i].active && !pos[i].pooled) {
|
||||
Transform x = pos[i].xform;
|
||||
float d = org.distance_squared_to(x.origin);
|
||||
if (d < distance * distance && pos[i].instance < 0) {
|
||||
int j;
|
||||
Node *pn = NULL;
|
||||
bool pooling = false;
|
||||
for (j = 0; j < pos.size(); j++) {
|
||||
if (j == i)
|
||||
continue;
|
||||
if (!pos[j].active && pos[j].instance >= 0 && pos[j].pooled) {
|
||||
pos.write()[i].instance = pos[j].instance;
|
||||
pos.write()[j].instance = -1;
|
||||
pos.write()[j].pooled = false;
|
||||
Object *po = ObjectDB::get_instance(pos[i].instance);
|
||||
if (po) {
|
||||
pn = Object::cast_to<Node>(po);
|
||||
if (pn) {
|
||||
pooling = true;
|
||||
break;
|
||||
if (pos.size() > 4) {
|
||||
for (j = 0; j < pos.size(); j++) {
|
||||
if (j == i)
|
||||
continue;
|
||||
if (!pos[j].active && pos[j].instance >= 0 && pos[j].pooled) {
|
||||
pos.write()[i].instance = pos[j].instance;
|
||||
pos.write()[j].instance = -1;
|
||||
pos.write()[j].pooled = false;
|
||||
Object *po = ObjectDB::get_instance(pos[i].instance);
|
||||
if (po) {
|
||||
pn = Object::cast_to<Node>(po);
|
||||
if (pn) {
|
||||
pooling = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!pn)
|
||||
pn = scenes[*key]->instance();
|
||||
assert(pn);
|
||||
if (pn) {
|
||||
Spatial *sp = Object::cast_to<Spatial>(pn);
|
||||
assert(sp);
|
||||
if (sp) {
|
||||
if (!pooling)
|
||||
view->add_child(sp);
|
||||
@@ -144,7 +148,7 @@ void Spawner::update_view(Node *node, float distance)
|
||||
memfree(pn);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
} else if (pos[i].active) {
|
||||
Transform x = pos[i].xform;
|
||||
float d = org.distance_squared_to(x.origin);
|
||||
if (d > distance * distance + 2500.0f) {
|
||||
|
||||
283
modules/world/traffic.cpp
Normal file
283
modules/world/traffic.cpp
Normal file
@@ -0,0 +1,283 @@
|
||||
#include <cassert>
|
||||
#include <core/resource.h>
|
||||
#include <core/os/os.h>
|
||||
#include <scene/main/scene_tree.h>
|
||||
#include <scene/main/viewport.h>
|
||||
#include <scene/3d/camera.h>
|
||||
#include <scene/resources/packed_scene.h>
|
||||
#include <scene/3d/vehicle_body.h>
|
||||
|
||||
#include "traffic.h"
|
||||
|
||||
Traffic::Traffic(): max_spawn_distance(120.0f),
|
||||
min_spawn_distance(80), delete_distance(Vector3(100.0f, -60.0f, 180.0f)),
|
||||
list_cooldown(0.0), debug(false)
|
||||
{
|
||||
state = 0;
|
||||
rnd.instance();
|
||||
rnd->randomize();
|
||||
call_deferred("idle_runner");
|
||||
}
|
||||
|
||||
Traffic::~Traffic()
|
||||
{
|
||||
}
|
||||
|
||||
void Traffic::_bind_methods()
|
||||
{
|
||||
ClassDB::bind_method(D_METHOD("idle_runner"), &Traffic::idle_runner);
|
||||
ClassDB::bind_method(D_METHOD("add_traffic_vehicle", "scene"), &Traffic::add_traffic_vehicle);
|
||||
ClassDB::bind_method(D_METHOD("remove_traffic_vehicle", "scene"), &Traffic::remove_traffic_vehicle);
|
||||
}
|
||||
|
||||
void Traffic::add_traffic_vehicle(Ref<PackedScene> scene)
|
||||
{
|
||||
scenes.push_back(scene);
|
||||
printf("traffic: added_scene: %d\n", scenes.size());
|
||||
}
|
||||
void Traffic::remove_traffic_vehicle(Ref<PackedScene> scene)
|
||||
{
|
||||
scenes.erase(scene);
|
||||
printf("traffic: removed_scene: %d\n", scenes.size());
|
||||
}
|
||||
void Traffic::idle_runner()
|
||||
{
|
||||
uint64_t before, after;
|
||||
float delta;
|
||||
|
||||
SceneTree *tree = SceneTree::get_singleton();
|
||||
Viewport *view;
|
||||
Camera *camera;
|
||||
Transform cam_xform;
|
||||
before = OS::get_singleton()->get_ticks_usec();
|
||||
assert(tree);
|
||||
delta = tree->get_idle_process_time();
|
||||
if (state > 0 && debug)
|
||||
debug_traffic();
|
||||
|
||||
if (state > 0)
|
||||
control_traffic();
|
||||
|
||||
switch(state) {
|
||||
case 0:
|
||||
debug_mat.instance();
|
||||
debug_mat->set_flag(SpatialMaterial::FLAG_DISABLE_DEPTH_TEST, true);
|
||||
debug_mat->set_flag(SpatialMaterial::FLAG_ALBEDO_FROM_VERTEX_COLOR, true);
|
||||
debug_mat->set_flag(SpatialMaterial::FLAG_UNSHADED, true);
|
||||
instance = VS::get_singleton()->instance_create();
|
||||
VS::get_singleton()->instance_set_scenario(instance, tree->get_root()->get_world()->get_scenario());
|
||||
immediate = VS::get_singleton()->immediate_create();
|
||||
VisualServer::get_singleton()->instance_set_base(instance, immediate);
|
||||
VS::get_singleton()->immediate_set_material(immediate, debug_mat->get_rid());
|
||||
tree->connect("idle_frame", this, "idle_runner");
|
||||
state = 1;
|
||||
break;
|
||||
case 1:
|
||||
if (list_cooldown > 0.0f) {
|
||||
list_cooldown -= delta;
|
||||
return;
|
||||
}
|
||||
tree->get_nodes_in_group("traffic_spawn", &spawner_list);
|
||||
spawner_e = spawner_list.front();
|
||||
list_cooldown = 0.1f;
|
||||
if (spawner_list.size() > 0)
|
||||
state = 2;
|
||||
spawn_cooldown = 0.0f;
|
||||
break;
|
||||
case 2:
|
||||
if (scenes.size() == 0)
|
||||
return;
|
||||
if (!spawner_e) {
|
||||
state = 1;
|
||||
return;
|
||||
}
|
||||
if (spawn_cooldown > 0.0f) {
|
||||
spawn_cooldown -= delta;
|
||||
return;
|
||||
}
|
||||
view = tree->get_root();
|
||||
if (!view)
|
||||
return;
|
||||
camera = view->get_camera();
|
||||
if (!camera)
|
||||
return;
|
||||
cam_xform = camera->get_global_transform();
|
||||
while (spawner_e) {
|
||||
float dst;
|
||||
VehicleBody *vb;
|
||||
Node *nscene;
|
||||
Spatial *sscene;
|
||||
Transform xform;
|
||||
Ref<PackedScene> scene;
|
||||
Vector3 check_coordinates;
|
||||
|
||||
after = OS::get_singleton()->get_ticks_usec();
|
||||
if (after - before > 2000ULL)
|
||||
break;
|
||||
Node *spawner;
|
||||
Spatial *obj;
|
||||
spawner = spawner_e->get();
|
||||
if (!spawner)
|
||||
goto pass_loop;
|
||||
if (!spawner->is_in_group("spawn"))
|
||||
goto pass_loop;
|
||||
obj = Object::cast_to<Spatial>(spawner);
|
||||
if (!obj)
|
||||
goto pass_loop;
|
||||
if (obj->has_meta("cooldown")) {
|
||||
float cooldown = obj->get_meta("cooldown");
|
||||
cooldown -= delta;
|
||||
if (cooldown >= 0.0f) {
|
||||
obj->set_meta("cooldown", cooldown);
|
||||
goto pass_loop;
|
||||
} else
|
||||
obj->remove_meta("cooldown");
|
||||
}
|
||||
xform = obj->get_global_transform();
|
||||
check_coordinates = cam_xform.xform_inv(xform.origin);
|
||||
if (check_coordinates.z > -15.0f && check_coordinates.z < min_spawn_distance && fabsf(check_coordinates.x) < 20.0 )
|
||||
goto pass_loop;
|
||||
dst = xform.origin.distance_squared_to(cam_xform.origin);
|
||||
if (check_coordinates.z > max_spawn_distance || check_coordinates.z < -50.0f || fabsf(check_coordinates.x) > 50.0f)
|
||||
goto pass_loop;
|
||||
printf("traffic: spawning scene\n");
|
||||
scene = scenes[rnd->randi() % scenes.size()];
|
||||
nscene = scene->instance();
|
||||
sscene = Object::cast_to<Spatial>(nscene);
|
||||
view->add_child(sscene);
|
||||
sscene->set_global_transform(xform);
|
||||
sscene->add_to_group("traffic_vehicle");
|
||||
sscene->set("parked", false);
|
||||
vb = Object::cast_to<VehicleBody>(nscene);
|
||||
if (vb) {
|
||||
vb->set_engine_force(2500.0f);
|
||||
vb->set_steering(0);
|
||||
RID space = PhysicsServer::get_singleton()->body_get_space(vb->get_rid());
|
||||
vb->set_meta("space", space);
|
||||
PhysicsServer::get_singleton()->body_set_space(vb->get_rid(), RID());
|
||||
}
|
||||
obj->set_meta("cooldown", 30.0f + rnd->randf() * 30.0);
|
||||
spawn_cooldown = 0.2f;
|
||||
pass_loop:
|
||||
spawner_e = spawner_e->next();
|
||||
}
|
||||
break;
|
||||
};
|
||||
}
|
||||
void Traffic::debug_traffic()
|
||||
{
|
||||
SceneTree *tree = SceneTree::get_singleton();
|
||||
List<Node *> traffic_vehicles;
|
||||
List<Node *>::Element *e;
|
||||
tree->get_nodes_in_group("traffic_vehicle", &traffic_vehicles);
|
||||
VS::get_singleton()->immediate_clear(immediate);
|
||||
if (traffic_vehicles.size() == 0)
|
||||
return;
|
||||
printf("traffic: vehicles: %d\n", traffic_vehicles.size());
|
||||
VS::get_singleton()->immediate_begin(immediate, VS::PRIMITIVE_LINES);
|
||||
for (e = traffic_vehicles.front(); e; e = e->next()) {
|
||||
Node *vnode = e->get();
|
||||
if (!vnode)
|
||||
continue;
|
||||
Spatial *vsp = Object::cast_to<Spatial>(vnode);
|
||||
if (!vsp)
|
||||
continue;
|
||||
Transform vxform = vsp->get_global_transform();
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 0, 0, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(0, 0, 1, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin + Vector3(0, 30, 0));
|
||||
if (vsp->has_meta("next_target")) {
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 0, 0, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 0, 0, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vsp->get_meta("next_target"));
|
||||
}
|
||||
if (vsp->has_meta("target")) {
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 0, 1, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 0, 1, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vsp->get_meta("target"));
|
||||
}
|
||||
if (vsp->has_meta("x_target")) {
|
||||
VS::get_singleton()->immediate_color(immediate, Color(0, 1, 0, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(0, 1, 0, 1));
|
||||
Vector3 vp = vsp->get_meta("x_target");
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.xform(vp));
|
||||
}
|
||||
if (vsp->has_meta("vel")) {
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 1, 1, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(0, 0, 1, 1));
|
||||
Vector3 vp = vsp->get_meta("vel");
|
||||
if (vp.length_squared() == 0.0f) {
|
||||
vp += Vector3(0, 2, 0);
|
||||
}
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.xform(vp));
|
||||
}
|
||||
if (vsp->has_meta("curve")) {
|
||||
Ref<Curve3D> curve = vsp->get_meta("curve");
|
||||
if (curve->get_point_count() > 0) {
|
||||
float offt = curve->get_closest_offset(vxform.origin);
|
||||
float plength = curve->get_baked_length();
|
||||
float pstart = CLAMP(offt - 4.0f, 0.0f, plength);
|
||||
Vector3 pt = curve->interpolate_baked(offt, false);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, 1, 1, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, vxform.origin);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(0, 1, 0, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, pt);
|
||||
while (pstart < offt + 8.0 && pstart < plength) {
|
||||
Vector3 opt = curve->interpolate_baked(pstart, false);
|
||||
float c = (pstart - offt + 4.0) / 16.0f;
|
||||
c = CLAMP(c, 0.0f, 1.0f);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, c, c, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, opt);
|
||||
VS::get_singleton()->immediate_color(immediate, Color(1, c, c, 1));
|
||||
VS::get_singleton()->immediate_vertex(immediate, opt + Vector3(0, 10, 0));
|
||||
pstart += 1.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
VS::get_singleton()->immediate_end(immediate);
|
||||
}
|
||||
void Traffic::control_traffic()
|
||||
{
|
||||
Viewport *view;
|
||||
Camera *camera;
|
||||
Transform cam_xform;
|
||||
SceneTree *tree = SceneTree::get_singleton();
|
||||
List<Node *> traffic_vehicles;
|
||||
List<Node *>::Element *e;
|
||||
tree->get_nodes_in_group("traffic_vehicle", &traffic_vehicles);
|
||||
view = tree->get_root();
|
||||
camera = view->get_camera();
|
||||
cam_xform = camera->get_global_transform();
|
||||
for (e = traffic_vehicles.front(); e; e = e->next()) {
|
||||
Node *node = e->get();
|
||||
Spatial *sp = Object::cast_to<Spatial>(node);
|
||||
Transform xform = sp->get_global_transform();
|
||||
Vector3 check = cam_xform.xform_inv(xform.origin);
|
||||
if (fabsf(check.x) > delete_distance.x ||
|
||||
check.z > delete_distance.z ||
|
||||
check.z < delete_distance.y)
|
||||
sp->queue_delete();
|
||||
}
|
||||
}
|
||||
|
||||
static Traffic *g_traffic_data = NULL;
|
||||
Traffic *Traffic::get_singleton()
|
||||
{
|
||||
return g_traffic_data;
|
||||
}
|
||||
void Traffic::create_singleton()
|
||||
{
|
||||
g_traffic_data = memnew(Traffic);
|
||||
}
|
||||
void Traffic::destroy_singleton()
|
||||
{
|
||||
memdelete(g_traffic_data);
|
||||
g_traffic_data = NULL;
|
||||
}
|
||||
|
||||
45
modules/world/traffic.h
Normal file
45
modules/world/traffic.h
Normal file
@@ -0,0 +1,45 @@
|
||||
#include <modules/world/roads.h>
|
||||
class Traffic: public Object {
|
||||
GDCLASS(Traffic, Object);
|
||||
protected:
|
||||
static void _bind_methods();
|
||||
Vector<Ref<PackedScene> > scenes;
|
||||
int state;
|
||||
List<Node *> spawner_list;
|
||||
List<Node *>::Element *spawner_e;
|
||||
float max_spawn_distance;
|
||||
float min_spawn_distance;
|
||||
Vector3 delete_distance;
|
||||
Ref<RandomNumberGenerator> rnd;
|
||||
float list_cooldown, spawn_cooldown;
|
||||
RID immediate, instance;
|
||||
Ref<SpatialMaterial> debug_mat;
|
||||
bool debug;
|
||||
|
||||
void debug_traffic();
|
||||
void control_traffic();
|
||||
public:
|
||||
Traffic();
|
||||
~Traffic();
|
||||
void add_traffic_vehicle(Ref<PackedScene> scene);
|
||||
void remove_traffic_vehicle(Ref<PackedScene> scene);
|
||||
void idle_runner();
|
||||
|
||||
inline void set_seed(int seed)
|
||||
{
|
||||
rnd->set_seed(seed);
|
||||
}
|
||||
inline int get_state()
|
||||
{
|
||||
return rnd->get_state();
|
||||
}
|
||||
inline void set_state(int seed)
|
||||
{
|
||||
rnd->set_state(seed);
|
||||
}
|
||||
|
||||
static Traffic *get_singleton();
|
||||
static void create_singleton();
|
||||
static void destroy_singleton();
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user