AIControl::AIControl(Train &t, Controller *n):
train(t),
- next_model(n),
- target_speed(TrainControl::continuous("speed", 0, 1000)),
+ next_ctrl(n),
+ target_speed(Control::continuous("speed", 0, 1000)),
blocked(false),
approach(false)
{
target_speed.set(0);
train.signal_arrived.connect(sigc::mem_fun(this, &AIControl::arrived));
- next_model->signal_control_changed.connect(sigc::mem_fun(this, &AIControl::control_changed));
+ next_ctrl->signal_control_changed.connect(sigc::mem_fun(this, &AIControl::control_changed));
}
AIControl::~AIControl()
{
- delete next_model;
+ delete next_ctrl;
}
void AIControl::set_control(const string &n, float v)
{
float approach_speed = 5*train.get_layout().get_catalogue().get_scale();
if(approach && target_speed.value>approach_speed)
- next_model->set_control("speed", approach_speed);
+ next_ctrl->set_control("speed", approach_speed);
else
- next_model->set_control("speed", target_speed.value);
+ next_ctrl->set_control("speed", target_speed.value);
}
signal_control_changed.emit(target_speed);
}
else
- next_model->set_control(n, v);
+ next_ctrl->set_control(n, v);
}
-const TrainControl &AIControl::get_control(const string &n) const
+const Controller::Control &AIControl::get_control(const string &n) const
{
if(n=="speed")
return target_speed;
else
- return next_model->get_control(n);
+ return next_ctrl->get_control(n);
}
float AIControl::get_speed() const
{
- return next_model->get_speed();
+ return next_ctrl->get_speed();
}
bool AIControl::get_reverse() const
{
- return next_model->get_reverse();
+ return next_ctrl->get_reverse();
}
float AIControl::get_braking_distance() const
{
- return next_model->get_braking_distance();
+ return next_ctrl->get_braking_distance();
}
void AIControl::tick(const Time::TimeDelta &dt)
{
float scale = train.get_layout().get_catalogue().get_scale();
float rsv_dist = train.get_reserved_distance();
- float brake_dist = next_model->get_braking_distance();
+ float brake_dist = next_ctrl->get_braking_distance();
float approach_margin = 50*scale;
float approach_speed = 5*scale;
float margin = 10*scale;
if(!blocked && rsv_dist<brake_dist+margin)
{
blocked = true;
- next_model->set_control("speed", 0);
+ next_ctrl->set_control("speed", 0);
}
else if((!approach && rsv_dist<brake_dist*1.3+approach_margin) || (blocked && rsv_dist>brake_dist+margin*2))
{
blocked = false;
approach = true;
if(target_speed.value>approach_speed)
- next_model->set_control("speed", approach_speed);
+ next_ctrl->set_control("speed", approach_speed);
else
- next_model->set_control("speed", target_speed.value);
+ next_ctrl->set_control("speed", target_speed.value);
}
else if((blocked || approach) && rsv_dist>brake_dist*1.3+approach_margin*2)
{
blocked = false;
approach = false;
- next_model->set_control("speed", target_speed.value);
+ next_ctrl->set_control("speed", target_speed.value);
}
- next_model->tick(dt);
+ next_ctrl->tick(dt);
- if(!target_speed.value && !next_model->get_speed() && train.is_active())
+ if(!target_speed.value && !next_ctrl->get_speed() && train.is_active())
train.set_active(false);
}
-void AIControl::control_changed(const TrainControl &ctrl)
+void AIControl::control_changed(const Control &ctrl)
{
if(ctrl.name!="speed")
signal_control_changed.emit(ctrl);
#include <sigc++/trackable.h>
#include "controller.h"
-#include "traincontrol.h"
namespace Marklin {
{
private:
Train &train;
- Controller *next_model;
- TrainControl target_speed;
+ Controller *next_ctrl;
+ Control target_speed;
bool blocked;
bool approach;
virtual ~AIControl();
virtual void set_control(const std::string &, float);
- virtual const TrainControl &get_control(const std::string &) const;
+ virtual const Control &get_control(const std::string &) const;
virtual float get_speed() const;
virtual bool get_reverse() const;
virtual void tick(const Msp::Time::TimeDelta &);
private:
- void control_changed(const TrainControl &);
+ void control_changed(const Control &);
void arrived();
};
--- /dev/null
+/* $Id$
+
+This file is part of the MSP Märklin suite
+Copyright © 2010 Mikkosoft Productions, Mikko Rasa
+Distributed under the GPL
+*/
+
+#include <cmath>
+#include <msp/core/except.h>
+#include "controller.h"
+
+using namespace std;
+using namespace Msp;
+
+namespace Marklin {
+
+void Controller::Control::set(float v)
+{
+ if(v<min_value)
+ v = min_value;
+ else if(v>max_value)
+ v = max_value;
+ else if(type==BINARY)
+ value = v ? 1 : 0;
+ else if(type==DISCRETE)
+ value = min_value+floor((v-min_value)/step)*step;
+ else if(type==CONTINUOUS)
+ value = v;
+}
+
+Controller::Control Controller::Control::binary(const string &n)
+{
+ Controller::Control tc;
+ tc.name = n;
+ tc.type = BINARY;
+ tc.min_value = 0;
+ tc.max_value = 1;
+ tc.step = 1;
+ tc.value = 0;
+
+ return tc;
+}
+
+Controller::Control Controller::Control::discrete(const string &n, float m, float x, float s)
+{
+ if(x<m)
+ throw InvalidParameterValue("Max value must be greater than min value");
+
+ Controller::Control tc;
+ tc.name = n;
+ tc.type = DISCRETE;
+ tc.min_value = m;
+ tc.max_value = m+floor((x-m)/s)*s;
+ tc.step = s;
+ tc.value = m;
+
+ return tc;
+}
+
+Controller::Control Controller::Control::continuous(const string &n, float m, float x)
+{
+ if(x<m)
+ throw InvalidParameterValue("Max value must be greater than min value");
+
+ Controller::Control tc;
+ tc.name = n;
+ tc.type = CONTINUOUS;
+ tc.min_value = m;
+ tc.max_value = x;
+ tc.step = 0;
+ tc.value = m;
+
+ return tc;
+}
+
+} // namespace Marklin
namespace Marklin {
-struct TrainControl;
-
/**
Interface class for train controllers. Takes input through a uniform named
control interface. Provides information about train movement on output.
class Controller
{
public:
- sigc::signal<void, const TrainControl &> signal_control_changed;
+ struct Control
+ {
+ enum Type
+ {
+ BINARY,
+ DISCRETE,
+ CONTINUOUS
+ };
+
+ std::string name;
+ Type type;
+ float min_value;
+ float max_value;
+ float step;
+ float value;
+
+ private:
+ Control() { }
+
+ public:
+ void set(float);
+
+ static Control binary(const std::string &);
+ static Control discrete(const std::string &, float, float, float);
+ static Control continuous(const std::string &, float, float);
+ };
+
+ sigc::signal<void, const Control &> signal_control_changed;
protected:
Controller() { }
virtual ~Controller() { }
virtual void set_control(const std::string &, float) = 0;
- virtual const TrainControl &get_control(const std::string &) const = 0;
+ virtual const Control &get_control(const std::string &) const = 0;
/** Returns the current speed. Always non-negative. */
virtual float get_speed() const = 0;
namespace Marklin {
SimpleController::SimpleController():
- target_speed(TrainControl::continuous("speed", 0, 1000)),
- reverse(TrainControl::binary("reverse")),
+ target_speed(Control::continuous("speed", 0, 1000)),
+ reverse(Control::binary("reverse")),
accel(0.07),
speed(0)
{
}
}
-const TrainControl &SimpleController::get_control(const string &name) const
+const Controller::Control &SimpleController::get_control(const string &name) const
{
if(name=="speed")
return target_speed;
#include <string>
#include "controller.h"
-#include "traincontrol.h"
namespace Marklin {
class SimpleController: public Controller
{
private:
- TrainControl target_speed;
- TrainControl reverse;
+ Control target_speed;
+ Control reverse;
float accel;
float speed;
SimpleController();
virtual void set_control(const std::string &, float);
- virtual const TrainControl &get_control(const std::string &) const;
+ virtual const Control &get_control(const std::string &) const;
virtual float get_speed() const { return speed; }
virtual bool get_reverse() const { return reverse.value; }
}
}
-void Train::control_changed(const TrainControl &ctrl)
+void Train::control_changed(const Controller::Control &ctrl)
{
signal_control_changed.emit(ctrl.name, ctrl.value);
}
#include <sigc++/trackable.h>
#include <msp/time/timestamp.h>
#include "block.h"
+#include "controller.h"
namespace Marklin {
-class Controller;
class Route;
class Timetable;
class Vehicle;
class VehicleType;
-struct TrainControl;
class Train: public sigc::trackable
{
void save(std::list<Msp::DataFile::Statement> &) const;
private:
- void control_changed(const TrainControl &);
+ void control_changed(const Controller::Control &);
void loco_speed_event(unsigned, unsigned, bool);
void loco_func_event(unsigned, unsigned, bool);
void sensor_event(unsigned, bool);
+++ /dev/null
-/* $Id$
-
-This file is part of the MSP Märklin suite
-Copyright © 2010 Mikkosoft Productions, Mikko Rasa
-Distributed under the GPL
-*/
-
-#include <cmath>
-#include <msp/core/except.h>
-#include "traincontrol.h"
-
-using namespace std;
-using namespace Msp;
-
-namespace Marklin {
-
-void TrainControl::set(float v)
-{
- if(v<min_value)
- v = min_value;
- else if(v>max_value)
- v = max_value;
- else if(type==BINARY)
- value = v ? 1 : 0;
- else if(type==DISCRETE)
- value = min_value+floor((v-min_value)/step)*step;
- else if(type==CONTINUOUS)
- value = v;
-}
-
-TrainControl TrainControl::binary(const string &n)
-{
- TrainControl tc;
- tc.name = n;
- tc.type = BINARY;
- tc.min_value = 0;
- tc.max_value = 1;
- tc.step = 1;
- tc.value = 0;
-
- return tc;
-}
-
-TrainControl TrainControl::discrete(const string &n, float m, float x, float s)
-{
- if(x<m)
- throw InvalidParameterValue("Max value must be greater than min value");
-
- TrainControl tc;
- tc.name = n;
- tc.type = DISCRETE;
- tc.min_value = m;
- tc.max_value = m+floor((x-m)/s)*s;
- tc.step = s;
- tc.value = m;
-
- return tc;
-}
-
-TrainControl TrainControl::continuous(const string &n, float m, float x)
-{
- if(x<m)
- throw InvalidParameterValue("Max value must be greater than min value");
-
- TrainControl tc;
- tc.name = n;
- tc.type = CONTINUOUS;
- tc.min_value = m;
- tc.max_value = x;
- tc.step = 0;
- tc.value = m;
-
- return tc;
-}
-
-} // namespace Marklin
+++ /dev/null
-/* $Id$
-
-This file is part of the MSP Märklin suite
-Copyright © 2010 Mikkosoft Productions, Mikko Rasa
-Distributed under the GPL
-*/
-
-#ifndef LIBMARKLIN_TRAINCONTROL_H_
-#define LIBMARKLIN_TRAINCONTROL_H_
-
-#include <string>
-
-namespace Marklin {
-
-struct TrainControl
-{
- enum Type
- {
- BINARY,
- DISCRETE,
- CONTINUOUS
- };
-
- std::string name;
- Type type;
- float min_value;
- float max_value;
- float step;
- float value;
-
-private:
- TrainControl() { }
-
-public:
- void set(float);
-
- static TrainControl binary(const std::string &);
- static TrainControl discrete(const std::string &, float, float, float);
- static TrainControl continuous(const std::string &, float, float);
-};
-
-} // namespace Marklin
-
-#endif