MCPcopy Create free account
hub / github.com/OpenTTD/OpenTTD / TrainApproachingLineEnd

Function TrainApproachingLineEnd

src/train_cmd.cpp:3794–3831  ·  view source on GitHub ↗

* Train is approaching line end, slow down and possibly reverse * * @param v front train engine * @param signal not line end, just a red signal * @param reverse Set to false to not execute the vehicle reversing. This does not change any other logic. * @return true iff we did NOT have to reverse */

Source from the content-addressed store, hash-verified

3792 * @return true iff we did NOT have to reverse
3793 */
3794static bool TrainApproachingLineEnd(Train *v, bool signal, bool reverse)
3795{
3796 /* Calc position within the current tile */
3797 uint x = v->x_pos & 0xF;
3798 uint y = v->y_pos & 0xF;
3799
3800 /* for diagonal directions, 'x' will be 0..15 -
3801 * for other directions, it will be 1, 3, 5, ..., 15 */
3802 switch (v->direction) {
3803 case DIR_N : x = ~x + ~y + 25; break;
3804 case DIR_NW: x = y; [[fallthrough]];
3805 case DIR_NE: x = ~x + 16; break;
3806 case DIR_E : x = ~x + y + 9; break;
3807 case DIR_SE: x = y; break;
3808 case DIR_S : x = x + y - 7; break;
3809 case DIR_W : x = ~y + x + 9; break;
3810 default: break;
3811 }
3812
3813 /* Do not reverse when approaching red signal. Make sure the vehicle's front
3814 * does not cross the tile boundary when we do reverse, but as the vehicle's
3815 * location is based on their center, use half a vehicle's length as offset.
3816 * Multiply the half-length by two for straight directions to compensate that
3817 * we only get odd x offsets there. */
3818 if (!signal && x + (v->gcache.cached_veh_length + 1) / 2 * (IsDiagonalDirection(v->direction) ? 1 : 2) >= TILE_SIZE) {
3819 /* we are too near the tile end, reverse now */
3820 v->cur_speed = 0;
3821 if (reverse) ReverseTrainDirection(v);
3822 return false;
3823 }
3824
3825 /* slow down */
3826 v->vehstatus.Set(VehState::TrainSlowing);
3827 uint16_t break_speed = _breakdown_speeds[x & 0xF];
3828 if (break_speed < v->cur_speed) v->cur_speed = break_speed;
3829
3830 return true;
3831}
3832
3833
3834/**

Callers 1

TrainCheckIfLineEndsFunction · 0.85

Calls 3

IsDiagonalDirectionFunction · 0.85
ReverseTrainDirectionFunction · 0.85
SetMethod · 0.45

Tested by

no test coverage detected