pending_block(0),
stop_at_block(0),
reserving(false),
- advancing(false)
+ advancing(false),
+ reserve_pending(false)
{
Layout &layout = train.get_layout();
layout.signal_block_reserved.connect(sigc::mem_fun(this, &BlockAllocator::block_reserved));
layout.signal_sensor_state_changed.connect(sigc::mem_fun(this, &BlockAllocator::sensor_state_changed));
+ layout.get_driver().signal_halt.connect(sigc::mem_fun(this, &BlockAllocator::halt_event));
const set<Track *> &tracks = layout.get_all<Track>();
for(set<Track *>::const_iterator i=tracks.begin(); i!=tracks.end(); ++i)
{
release_blocks_end(cur_blocks_end);
pending_block = 0;
+ reserve_pending = false;
}
}
return find_if(blocks.begin(), end, BlockMatch(block))!=cur_blocks_end;
}
+void BlockAllocator::tick()
+{
+ if(reserve_pending)
+ {
+ reserve_pending = false;
+ reserve_more();
+ }
+}
+
void BlockAllocator::reserve_more()
{
if(blocks.empty())
throw logic_error("no blocks");
+ if(train.get_layout().get_driver().is_halted())
+ return;
+
BlockIter start = blocks.back();
if(&*start==stop_at_block)
return;
void BlockAllocator::turnout_path_changed(Track &track)
{
if(&track.get_block()==pending_block && !reserving)
- reserve_more();
+ reserve_pending = true;
}
void BlockAllocator::block_reserved(Block &block, const Train *tr)
{
if(&block==pending_block && !tr && !reserving)
- reserve_more();
+ reserve_pending = true;
}
void BlockAllocator::sensor_state_changed(Sensor &sensor, Sensor::State state)
advance_front(next_sensor);
if(active)
- reserve_more();
+ reserve_pending = true;
}
else if(!is_block_current(*block))
train.get_layout().emergency(block, "Sensor for "+train.get_name()+" triggered out of order");
next_sensor = 0;
}
+void BlockAllocator::halt_event(bool halted)
+{
+ if(active && !halted)
+ reserve_more();
+}
+
void BlockAllocator::save(list<DataFile::Statement> &st) const
{
if(!blocks.empty() && cur_blocks_end!=blocks.begin())
st.push_back((DataFile::Statement("hint"), prev->get_id()));
- for(BlockList::const_iterator i=cur_blocks.begin(); i!=cur_blocks.end(); ++i)
+ for(BlockList::const_iterator i=cur_blocks.begin(); (i!=cur_blocks.end() && i->block()!=pending_block); ++i)
st.push_back((DataFile::Statement("block"), (*i)->get_id()));
}
}