Layout3D::~Layout3D()
{
- while(!signals.empty())
- delete signals.begin()->second;
- while(!tracks.empty())
- delete tracks.begin()->second;
- while(!vehicles.empty())
- delete vehicles.begin()->second;
+ while(!objects.empty())
+ delete objects.begin()->second;
}
void Layout3D::get_bounds(Vector &minp, Vector &maxp) const
{
Geometry::BoundingBox<float, 3> bbox;
- for(TrackMap::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
- bbox = bbox|i->second->get_track().get_type().get_shape()->get_axis_aligned_bounding_box();
+ for(ObjectMap::const_iterator i=objects.begin(); i!=objects.end(); ++i)
+ bbox = bbox|i->second->get_object().get_type().get_shape()->get_axis_aligned_bounding_box();
minp = bbox.get_minimum_point();
maxp = bbox.get_maximum_point();
}
-void Layout3D::add_track(Track3D &t)
+void Layout3D::add(Object3D &o)
{
- insert_unique(tracks, &t.get_track(), &t);
+ insert_unique(objects, &o.get_object(), &o);
}
-void Layout3D::remove_track(Track3D &t)
+Object3D &Layout3D::get(Object &o) const
{
- tracks.erase(&t.get_track());
+ return *get_item(objects, &o);
}
-Track3D &Layout3D::get_track(Track &t) const
+void Layout3D::remove(Object3D &o)
{
- return *get_item(tracks, &t);
-}
-
-void Layout3D::add_vehicle(Vehicle3D &v)
-{
- insert_unique(vehicles, &v.get_vehicle(), &v);
-}
-
-void Layout3D::remove_vehicle(Vehicle3D &v)
-{
- vehicles.erase(&v.get_vehicle());
-}
-
-Vehicle3D &Layout3D::get_vehicle(Vehicle &v) const
-{
- return *get_item(vehicles, &v);
-}
-
-void Layout3D::add_signal(Signal3D &s)
-{
- insert_unique(signals, &s.get_signal(), &s);
-}
-
-void Layout3D::remove_signal(Signal3D &s)
-{
- signals.erase(&s.get_signal());
-}
-
-Signal3D &Layout3D::get_signal(Signal &s) const
-{
- return *get_item(signals, &s);
+ objects.erase(&o.get_object());
}
void Layout3D::object_added(Object &o)
void Layout3D::object_removed(Object &o)
{
- if(Track *t = dynamic_cast<Track *>(&o))
- {
- TrackMap::iterator i = tracks.find(t);
- if(i!=tracks.end())
- delete i->second;
- }
- else if(Signal *s = dynamic_cast<Signal *>(&o))
- {
- SignalMap::iterator i = signals.find(s);
- if(i!=signals.end())
- delete i->second;
- }
- else if(Vehicle *v = dynamic_cast<Vehicle *>(&o))
- {
- VehicleMap::iterator i = vehicles.find(v);
- if(i!=vehicles.end())
- delete i->second;
- }
+ ObjectMap::iterator i = objects.find(&o);
+ if(i!=objects.end())
+ delete i->second;
}
} // namespace R2C2
namespace R2C2 {
-class Signal3D;
-class Track3D;
-class Vehicle3D;
+class Object3D;
class Layout3D: public sigc::trackable
{
public:
- typedef std::map<Track *, Track3D *> TrackMap;
- typedef std::map<Vehicle *, Vehicle3D *> VehicleMap;
- typedef std::map<Signal *, Signal3D *> SignalMap;
+ typedef std::map<Object *, Object3D *> ObjectMap;
private:
Layout &layout;
Catalogue3D catalogue;
- TrackMap tracks;
- VehicleMap vehicles;
- SignalMap signals;
+ ObjectMap objects;
Msp::GL::InstanceScene scene;
Msp::GL::SimpleScene ep_scene;
Msp::GL::InstanceScene path_scene;
const Catalogue3D &get_catalogue() const { return catalogue; }
void get_bounds(Vector &, Vector &) const;
- void add_track(Track3D &);
- void remove_track(Track3D &);
- const TrackMap &get_tracks() const { return tracks; }
- Track3D &get_track(Track &) const;
+ void add(Object3D &);
+ Object3D &get(Object &) const;
+ const ObjectMap &get_all() const { return objects; }
+ void remove(Object3D &);
- void add_vehicle(Vehicle3D &);
- void remove_vehicle(Vehicle3D &);
- Vehicle3D &get_vehicle(Vehicle &) const;
-
- void add_signal(Signal3D &);
- void remove_signal(Signal3D &);
- Signal3D &get_signal(Signal &) const;
+ template<typename T>
+ T &get(Object &o) const
+ { return dynamic_cast<T &>(get(o)); }
Msp::GL::Scene &get_scene() { return scene; }
Msp::GL::Scene &get_endpoint_scene() { return ep_scene; }
+#include "layout.h"
#include "object.h"
using namespace Msp;
namespace R2C2 {
-Object3D::Object3D(Object &o):
+Object3D::Object3D(Layout3D &l, Object &o):
+ layout(l),
object(o)
{
object.signal_moved.connect(sigc::mem_fun(this, &Object3D::moved));
+
+ layout.add(*this);
+}
+
+Object3D::~Object3D()
+{
+ layout.remove(*this);
}
void Object3D::moved()
namespace R2C2 {
+class Layout3D;
+
class Object3D: public sigc::trackable
{
protected:
+ Layout3D &layout;
Object &object;
Msp::GL::Matrix matrix;
- Object3D(Object &);
+ Object3D(Layout3D &, Object &);
public:
- virtual ~Object3D() { }
+ virtual ~Object3D();
+
+ Layout3D &get_layout() const { return layout; }
+ Object &get_object() const { return object; }
const Msp::GL::Matrix &get_matrix() const { return matrix; }
virtual Vector get_node() const = 0;
namespace R2C2 {
Signal3D::Signal3D(Layout3D &l, Signal &s):
- Object3D(s),
+ Object3D(l, s),
GL::ObjectInstance(l.get_catalogue().get_signal(s.get_type()).get_object()),
- layout(l),
signal(s)
{
- layout.add_signal(*this);
layout.get_scene().add(*this);
}
Signal3D::~Signal3D()
{
- layout.remove_signal(*this);
layout.get_scene().remove(*this);
}
namespace R2C2 {
-class Layout3D;
-
class Signal3D: public Object3D, public Msp::GL::ObjectInstance
{
private:
- Layout3D &layout;
Signal &signal;
public:
namespace R2C2 {
Track3D::Track3D(Layout3D &l, Track &t):
- Object3D(t),
+ Object3D(l, t),
GL::ObjectInstance(l.get_catalogue().get_track(t.get_type()).get_object()),
- layout(l),
track(t),
type(layout.get_catalogue().get_track(track.get_type())),
path(new Path3D(*this))
{
- layout.add_track(*this);
layout.get_scene().add(*this);
const vector<TrackType::Endpoint> &type_eps = track.get_type().get_endpoints();
{
delete path;
- layout.remove_track(*this);
layout.get_scene().remove(*this);
for(vector<Endpoint3D *>::iterator i=endpoints.begin(); i!=endpoints.end(); ++i)
namespace R2C2 {
class Endpoint3D;
-class Layout3D;
class Path3D;
class TrackType3D;
class Track3D: public Object3D, public Msp::GL::ObjectInstance
{
private:
- Layout3D &layout;
Track &track;
const TrackType3D &type;
std::vector<Endpoint3D *> endpoints;
namespace R2C2 {
Vehicle3D::Vehicle3D(Layout3D &l, Vehicle &v):
- Object3D(v),
+ Object3D(l, v),
GL::ObjectInstance(*l.get_catalogue().get_vehicle(v.get_type()).get_body_object()),
- layout(l),
vehicle(v),
type(layout.get_catalogue().get_vehicle(vehicle.get_type()))
{
layout.get_scene().add(*r);
}
- layout.add_vehicle(*this);
layout.get_scene().add(*this);
}
Vehicle3D::~Vehicle3D()
{
- layout.remove_vehicle(*this);
layout.get_scene().remove(*this);
for(vector<Axle3D *>::iterator i=axles.begin(); i!=axles.end(); ++i)
{
class Axle3D;
class Bogie3D;
-class Layout3D;
class Rod3D;
class VehicleType3D;
class Vehicle3D: public Object3D, public Msp::GL::ObjectInstance
{
private:
- Layout3D &layout;
Vehicle &vehicle;
const VehicleType3D &type;
std::vector<Axle3D *> axles;
cat_view->view_all(true);
main_view->view_all();
- const Layout3D::TrackMap &tracks = layout_3d->get_tracks();
- for(Layout3D::TrackMap::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
- update_track_icon(*i->second);
+ const set<Track *> &tracks = layout->get_all<Track>();
+ for(set<Track *>::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
+ update_track_icon(layout_3d->get<Track3D>(**i));
}
Designer::~Designer()
selection.clear();
for(set<Track *>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
{
- overlay->clear(layout_3d->get_track(**i));
+ overlay->clear(layout_3d->get<Track3D>(**i));
delete *i;
}
}
camera_ctl->tick(dt);
for(list<Track *>::iterator i=new_tracks.begin(); i!=new_tracks.end(); ++i)
- layout_3d->get_track(**i).get_path().set_mask(0);
+ layout_3d->get<Track3D>(**i).get_path().set_mask(0);
new_tracks.clear();
render();
if(*j!=*i)
(*i)->snap_to(**j, true);
- update_track_icon(layout_3d->get_track(**i));
+ update_track_icon(layout_3d->get<Track3D>(**i));
}
}
else if(key==Msp::Input::KEY_F)
{
const set<Track *> &tracks = selection.get_objects<Track>();
for(set<Track *>::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
- update_track_icon(layout_3d->get_track(**i));
+ update_track_icon(layout_3d->get<Track3D>(**i));
}
void Designer::route_name_accept(const string &text)
const set<Track *> <racks = layout->get_all<Track>();
for(set<Track *>::iterator i=ltracks.begin(); i!=ltracks.end(); ++i)
{
- Track3D &t3d = layout_3d->get_track(**i);
+ Track3D &t3d = layout_3d->get<Track3D>(**i);
t3d.get_path().set_mask(0);
}
}
const set<Track *> &rtracks = route.get_tracks();
for(set<Track *>::iterator i=rtracks.begin(); i!=rtracks.end(); ++i)
{
- Track3D &t3d = layout_3d->get_track(**i);
+ Track3D &t3d = layout_3d->get<Track3D>(**i);
t3d.get_path().set_color(GL::Color(0.5, 0.8, 1.0));
int path = -1;
if(unsigned tid = (*i)->get_turnout_id())
const Zone::TrackSet &ztracks = zone.get_tracks();
for(Zone::TrackSet::const_iterator i=ztracks.begin(); i!=ztracks.end(); ++i)
{
- Track3D &t3d = layout_3d->get_track(**i);
+ Track3D &t3d = layout_3d->get<Track3D>(**i);
t3d.get_path().set_color(GL::Color(0.8, 1.0, 0.5));
t3d.get_path().set_mask((*i)->get_type().get_paths());
}
picking_entry = 0;
delete picking_path;
- picking_path = new Path3D(layout_3d.get_track(*track));
+ picking_path = new Path3D(layout_3d.get<Track3D>(*track));
if(picking_entry>=0)
picking_path->set_mask(picking_track->get_type().get_endpoint(picking_entry).paths);
else
void Engineer::view_all()
{
- const Layout3D::TrackMap &tracks = layout_3d.get_tracks();
+ const Layout3D::ObjectMap &objects = layout_3d.get_all();
float view_aspect = float(window.get_width())/window.get_height();
float view_height = tan(camera.get_field_of_view()/2.0f)*2.0f;
{
Transform trans = Transform::rotation(-angle, Vector(0, 0, 1));
BoundingBox bbox;
- for(Layout3D::TrackMap::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
- bbox = bbox|trans.transform(i->second->get_track().get_bounding_box());
+ for(Layout3D::ObjectMap::const_iterator i=objects.begin(); i!=objects.end(); ++i)
+ bbox = bbox|trans.transform(i->second->get_object().get_bounding_box());
const Vector &minp = bbox.get_minimum_point();
const Vector &maxp = bbox.get_maximum_point();
{
const set<Track *> &tracks = block.get_tracks();
for(set<Track *>::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
- layout_3d.get_track(**i).get_path().set_color(color);
+ layout_3d.get<Track3D>(**i).get_path().set_color(color);
}
void Engineer::reset_block_color(const Block &block)
void Engineer::process_new_train(Train &train)
{
- Vehicle3D &loco3d = layout_3d.get_vehicle(train.get_vehicle(0));
+ Vehicle3D &loco3d = layout_3d.get<Vehicle3D>(train.get_vehicle(0));
overlay->set_label(loco3d, train.get_name());
train.signal_name_changed.connect(sigc::bind<0>(sigc::mem_fun(overlay, &Overlay3D::set_label), sigc::ref(loco3d)));
}