From c8bea21c690aa627fc337a60df17c9d824c9eb91 Mon Sep 17 00:00:00 2001 From: Mikko Rasa Date: Sun, 10 Feb 2013 11:46:25 +0200 Subject: [PATCH] Simulate a delay for switching turnouts in the Dummy driver --- source/libr2c2/driver.cpp | 2 +- source/libr2c2/dummy.cpp | 54 ++++++++++++++++++++++++++++++++++----- source/libr2c2/dummy.h | 16 +++++++++--- 3 files changed, 61 insertions(+), 11 deletions(-) diff --git a/source/libr2c2/driver.cpp b/source/libr2c2/driver.cpp index 46548e8..3b6d649 100644 --- a/source/libr2c2/driver.cpp +++ b/source/libr2c2/driver.cpp @@ -21,7 +21,7 @@ Driver *Driver::create(const string &str) else if(type=="cs" || type=="centralstation") return new CentralStation(params); else if(type=="dummy") - return new Dummy; + return new Dummy(params); throw invalid_argument("Driver::create"); } diff --git a/source/libr2c2/dummy.cpp b/source/libr2c2/dummy.cpp index 99e4a5e..cb625dd 100644 --- a/source/libr2c2/dummy.cpp +++ b/source/libr2c2/dummy.cpp @@ -1,12 +1,28 @@ +#include +#include #include "dummy.h" using namespace std; +using namespace Msp; namespace R2C2 { -Dummy::Dummy(): +Dummy::Dummy(const string ¶ms): power(true) -{ } +{ + vector opts = split(params, ':'); + for(vector::const_iterator i=opts.begin(); i!=opts.end(); ++i) + { + string::size_type equals = i->find('='); + if(equals!=string::npos) + { + string name = i->substr(0, equals); + string value = i->substr(equals+1); + if(name=="turnout_delay") + turnout_delay = lexical_cast(value)*Time::msec; + } + } +} void Dummy::set_power(bool p) { @@ -33,19 +49,29 @@ void Dummy::add_turnout(unsigned addr, const TrackType &) void Dummy::set_turnout(unsigned addr, unsigned state) { - if(turnouts[addr]!=state) + TurnoutState &turnout = turnouts[addr]; + if(turnout.state==state && turnout.pending==state) + { + signal_turnout.emit(addr, state); + return; + } + + turnout.pending = state; + if(turnout_delay) + turnout.timeout = Time::now()+turnout_delay; + else { - turnouts[addr] = state; + turnout.state = state; signal_turnout.emit(addr, state); } } unsigned Dummy::get_turnout(unsigned addr) const { - map::const_iterator i = turnouts.find(addr); + map::const_iterator i = turnouts.find(addr); if(i!=turnouts.end()) - return i->second; - return false; + return i->second.state; + return 0; } void Dummy::set_loco_speed(unsigned addr, unsigned speed) @@ -84,4 +110,18 @@ bool Dummy::get_sensor(unsigned addr) const return false; } +void Dummy::tick() +{ + Time::TimeStamp t = Time::now(); + for(map::iterator i=turnouts.begin(); i!=turnouts.end(); ++i) + { + if(i->second.timeout && t>=i->second.timeout) + { + i->second.state = i->second.pending; + i->second.timeout = Time::TimeStamp(); + signal_turnout.emit(i->first, i->second.state); + } + } +} + } // namespace R2C2 diff --git a/source/libr2c2/dummy.h b/source/libr2c2/dummy.h index 469b7f2..2c6f992 100644 --- a/source/libr2c2/dummy.h +++ b/source/libr2c2/dummy.h @@ -2,6 +2,8 @@ #define LIBR2C2_DUMMY_H_ #include +#include +#include #include "driver.h" namespace R2C2 { @@ -9,6 +11,13 @@ namespace R2C2 { class Dummy: public Driver { private: + struct TurnoutState + { + unsigned state; + unsigned pending; + Msp::Time::TimeStamp timeout; + }; + struct LocoState { unsigned speed; @@ -16,12 +25,13 @@ private: }; bool power; - std::map turnouts; + std::map turnouts; std::map locos; std::map sensors; + Msp::Time::TimeDelta turnout_delay; public: - Dummy(); + Dummy(const std::string &); virtual void set_power(bool); virtual bool get_power() const { return power; } @@ -47,7 +57,7 @@ public: virtual void set_sensor(unsigned, bool); virtual bool get_sensor(unsigned) const; - virtual void tick() { } + virtual void tick(); virtual void flush() { } }; -- 2.43.0