mirror of https://github.com/OpenTTD/OpenTTD.git
(svn r9558) -Documentation: doxygen and comment changes: 'T' now. Almost done
This commit is contained in:
parent
9b6bf9bd16
commit
f81217bcf4
|
@ -411,7 +411,7 @@ void IConsolePrint(uint16 color_code, const char *string)
|
||||||
/**
|
/**
|
||||||
* Handle the printing of text entered into the console or redirected there
|
* Handle the printing of text entered into the console or redirected there
|
||||||
* by any other means. Uses printf() style format, for more information look
|
* by any other means. Uses printf() style format, for more information look
|
||||||
* at @IConsolePrint()
|
* at IConsolePrint()
|
||||||
*/
|
*/
|
||||||
void CDECL IConsolePrintF(uint16 color_code, const char *s, ...)
|
void CDECL IConsolePrintF(uint16 color_code, const char *s, ...)
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file terraform_gui.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "bridge_map.h"
|
#include "bridge_map.h"
|
||||||
|
@ -91,11 +93,11 @@ static void GenerateRockyArea(TileIndex end, TileIndex start)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A central place to handle all X_AND_Y dragged GUI functions.
|
* A central place to handle all X_AND_Y dragged GUI functions.
|
||||||
* @param e @WindowEvent variable holding in its higher bits (excluding the lower
|
* @param e WindowEvent variable holding in its higher bits (excluding the lower
|
||||||
* 4, since that defined the X_Y drag) the type of action to be performed
|
* 4, since that defined the X_Y drag) the type of action to be performed
|
||||||
* @return Returns true if the action was found and handled, and false otherwise. This
|
* @return Returns true if the action was found and handled, and false otherwise. This
|
||||||
* allows for additional implements that are more local. For example X_Y drag
|
* allows for additional implements that are more local. For example X_Y drag
|
||||||
* of convertrail which belongs in rail_gui.c and not terraform_gui.c
|
* of convertrail which belongs in rail_gui.cpp and not terraform_gui.cpp
|
||||||
**/
|
**/
|
||||||
bool GUIPlaceProcDragXY(const WindowEvent *e)
|
bool GUIPlaceProcDragXY(const WindowEvent *e)
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file texteff.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "functions.h"
|
#include "functions.h"
|
||||||
|
@ -121,7 +123,7 @@ void InitTextMessage()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Hide the textbox */
|
/** Hide the textbox */
|
||||||
void UndrawTextMessage()
|
void UndrawTextMessage()
|
||||||
{
|
{
|
||||||
if (_textmessage_visible) {
|
if (_textmessage_visible) {
|
||||||
|
@ -172,7 +174,7 @@ void UndrawTextMessage()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Check if a message is expired every day */
|
/** Check if a message is expired every day */
|
||||||
void TextMessageDailyLoop()
|
void TextMessageDailyLoop()
|
||||||
{
|
{
|
||||||
uint i;
|
uint i;
|
||||||
|
@ -196,7 +198,7 @@ void TextMessageDailyLoop()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Draw the textmessage-box */
|
/** Draw the textmessage-box */
|
||||||
void DrawTextMessage()
|
void DrawTextMessage()
|
||||||
{
|
{
|
||||||
if (!_textmessage_dirty) return;
|
if (!_textmessage_dirty) return;
|
||||||
|
|
43
src/tgp.cpp
43
src/tgp.cpp
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tgp.cpp OTTD Perlin Noise Landscape Generator, aka TerraGenesis Perlin */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
|
@ -17,7 +19,6 @@
|
||||||
#include "helpers.hpp"
|
#include "helpers.hpp"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* OTTD Perlin Noise Landscape Generator, aka TerraGenesis Perlin
|
|
||||||
*
|
*
|
||||||
* Quickie guide to Perlin Noise
|
* Quickie guide to Perlin Noise
|
||||||
* Perlin noise is a predictable pseudo random number sequence. By generating
|
* Perlin noise is a predictable pseudo random number sequence. By generating
|
||||||
|
@ -167,11 +168,11 @@ static const int amplitude_decimal_bits = 10;
|
||||||
/** Height map - allocated array of heights (MapSizeX() + 1) x (MapSizeY() + 1) */
|
/** Height map - allocated array of heights (MapSizeX() + 1) x (MapSizeY() + 1) */
|
||||||
struct HeightMap
|
struct HeightMap
|
||||||
{
|
{
|
||||||
height_t *h; //! array of heights
|
height_t *h; //< array of heights
|
||||||
uint dim_x; //! height map size_x MapSizeX() + 1
|
uint dim_x; //< height map size_x MapSizeX() + 1
|
||||||
uint total_size; //! height map total size
|
uint total_size; //< height map total size
|
||||||
uint size_x; //! MapSizeX()
|
uint size_x; //< MapSizeX()
|
||||||
uint size_y; //! MapSizeY()
|
uint size_y; //< MapSizeY()
|
||||||
};
|
};
|
||||||
|
|
||||||
/** Global height map instance */
|
/** Global height map instance */
|
||||||
|
@ -200,13 +201,13 @@ static HeightMap _height_map = {NULL, 0, 0, 0, 0};
|
||||||
/** Noise amplitudes (multiplied by 1024)
|
/** Noise amplitudes (multiplied by 1024)
|
||||||
* - indexed by "smoothness setting" and log2(frequency) */
|
* - indexed by "smoothness setting" and log2(frequency) */
|
||||||
static const amplitude_t _amplitudes_by_smoothness_and_frequency[4][12] = {
|
static const amplitude_t _amplitudes_by_smoothness_and_frequency[4][12] = {
|
||||||
// Very smooth
|
/* Very smooth */
|
||||||
{1000, 350, 123, 43, 15, 1, 1, 0, 0, 0, 0, 0},
|
{1000, 350, 123, 43, 15, 1, 1, 0, 0, 0, 0, 0},
|
||||||
// Smooth
|
/* Smooth */
|
||||||
{1000, 1000, 403, 200, 64, 8, 1, 0, 0, 0, 0, 0},
|
{1000, 1000, 403, 200, 64, 8, 1, 0, 0, 0, 0, 0},
|
||||||
// Rough
|
/* Rough */
|
||||||
{1000, 1200, 800, 500, 200, 16, 4, 0, 0, 0, 0, 0},
|
{1000, 1200, 800, 500, 200, 16, 4, 0, 0, 0, 0, 0},
|
||||||
// Very Rough
|
/* Very Rough */
|
||||||
{1500, 1000, 1200, 1000, 500, 32, 20, 0, 0, 0, 0, 0},
|
{1500, 1000, 1200, 1000, 500, 32, 20, 0, 0, 0, 0, 0},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -215,13 +216,17 @@ static const amplitude_t _water_percent[4] = {20, 80, 250, 400};
|
||||||
|
|
||||||
/** Desired maximum height - indexed by _opt.diff.terrain_type */
|
/** Desired maximum height - indexed by _opt.diff.terrain_type */
|
||||||
static const int8 _max_height[4] = {
|
static const int8 _max_height[4] = {
|
||||||
6, // Very flat
|
6, ///< Very flat
|
||||||
9, // Flat
|
9, ///< Flat
|
||||||
12, // Hilly
|
12, ///< Hilly
|
||||||
15 // Mountainous
|
15 ///< Mountainous
|
||||||
};
|
};
|
||||||
|
|
||||||
/** Check if a X/Y set are within the map. */
|
/** Check if a X/Y set are within the map.
|
||||||
|
* @param x coordinate x
|
||||||
|
* @param y coordinate y
|
||||||
|
* @return true if within the map
|
||||||
|
*/
|
||||||
static inline bool IsValidXY(uint x, uint y)
|
static inline bool IsValidXY(uint x, uint y)
|
||||||
{
|
{
|
||||||
return ((int)x) >= 0 && x < _height_map.size_x && ((int)y) >= 0 && y < _height_map.size_y;
|
return ((int)x) >= 0 && x < _height_map.size_x && ((int)y) >= 0 && y < _height_map.size_y;
|
||||||
|
@ -680,10 +685,10 @@ static inline int perlin_landXY(uint x, uint y)
|
||||||
|
|
||||||
/* The following decimals are the octave power modifiers for the Perlin noise */
|
/* The following decimals are the octave power modifiers for the Perlin noise */
|
||||||
static const double _perlin_p_values[][7] = { // perlin frequency per power
|
static const double _perlin_p_values[][7] = { // perlin frequency per power
|
||||||
{ 0.35, 0.35, 0.35, 0.35, 0.35, 0.25, 0.539 }, // Very smooth
|
{ 0.35, 0.35, 0.35, 0.35, 0.35, 0.25, 0.539 }, ///< Very smooth
|
||||||
{ 0.45, 0.55, 0.45, 0.45, 0.35, 0.25, 0.89 }, // Smooth
|
{ 0.45, 0.55, 0.45, 0.45, 0.35, 0.25, 0.89 }, ///< Smooth
|
||||||
{ 0.85, 0.80, 0.70, 0.45, 0.45, 0.35, 1.825 }, // Rough 1.825
|
{ 0.85, 0.80, 0.70, 0.45, 0.45, 0.35, 1.825 }, ///< Rough 1.825
|
||||||
{ 0.95, 0.85, 0.80, 0.55, 0.55, 0.45, 2.245 } // Very Rough 2.25
|
{ 0.95, 0.85, 0.80, 0.55, 0.55, 0.45, 2.245 } //< Very Rough 2.25
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tgp.h */
|
||||||
|
|
||||||
#ifndef TGP_H
|
#ifndef TGP_H
|
||||||
#define TGP_H
|
#define TGP_H
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file thread.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "thread.h"
|
#include "thread.h"
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file thread.h */
|
||||||
|
|
||||||
#ifndef THREAD_H
|
#ifndef THREAD_H
|
||||||
#define THREAD_H
|
#define THREAD_H
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tile.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "tile.h"
|
#include "tile.h"
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tile.h */
|
||||||
|
|
||||||
#ifndef TILE_H
|
#ifndef TILE_H
|
||||||
#define TILE_H
|
#define TILE_H
|
||||||
|
|
||||||
|
|
69
src/town.h
69
src/town.h
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file town.h */
|
||||||
|
|
||||||
#ifndef TOWN_H
|
#ifndef TOWN_H
|
||||||
#define TOWN_H
|
#define TOWN_H
|
||||||
|
|
||||||
|
@ -76,34 +78,34 @@ struct BuildingCounts {
|
||||||
struct Town {
|
struct Town {
|
||||||
TileIndex xy;
|
TileIndex xy;
|
||||||
|
|
||||||
// Current population of people and amount of houses.
|
/* Current population of people and amount of houses. */
|
||||||
uint16 num_houses;
|
uint16 num_houses;
|
||||||
uint32 population;
|
uint32 population;
|
||||||
|
|
||||||
// Town name
|
/* Town name */
|
||||||
uint16 townnametype;
|
uint16 townnametype;
|
||||||
uint32 townnameparts;
|
uint32 townnameparts;
|
||||||
|
|
||||||
// NOSAVE: Location of name sign, UpdateTownVirtCoord updates this.
|
/* NOSAVE: Location of name sign, UpdateTownVirtCoord updates this. */
|
||||||
ViewportSign sign;
|
ViewportSign sign;
|
||||||
|
|
||||||
// Makes sure we don't build certain house types twice.
|
/* Makes sure we don't build certain house types twice.
|
||||||
// bit 0 = Building funds received
|
* bit 0 = Building funds received
|
||||||
// bit 1 = CHURCH
|
* bit 1 = CHURCH
|
||||||
// bit 2 = STADIUM
|
* bit 2 = STADIUM */
|
||||||
byte flags12;
|
byte flags12;
|
||||||
|
|
||||||
// Which players have a statue?
|
/* Which players have a statue? */
|
||||||
byte statues;
|
byte statues;
|
||||||
|
|
||||||
// Player ratings as well as a mask that determines which players have a rating.
|
/* Player ratings as well as a mask that determines which players have a rating. */
|
||||||
byte have_ratings;
|
byte have_ratings;
|
||||||
uint8 unwanted[MAX_PLAYERS]; // how many months companies aren't wanted by towns (bribe)
|
uint8 unwanted[MAX_PLAYERS]; ///< how many months companies aren't wanted by towns (bribe)
|
||||||
PlayerByte exclusivity; // which player has exslusivity
|
PlayerByte exclusivity; ///< which player has exslusivity
|
||||||
uint8 exclusive_counter; // months till the exclusivity expires
|
uint8 exclusive_counter; ///< months till the exclusivity expires
|
||||||
int16 ratings[MAX_PLAYERS];
|
int16 ratings[MAX_PLAYERS];
|
||||||
|
|
||||||
// Maximum amount of passengers and mail that can be transported.
|
/* Maximum amount of passengers and mail that can be transported. */
|
||||||
uint32 max_pass;
|
uint32 max_pass;
|
||||||
uint32 max_mail;
|
uint32 max_mail;
|
||||||
uint32 new_max_pass;
|
uint32 new_max_pass;
|
||||||
|
@ -113,36 +115,36 @@ struct Town {
|
||||||
uint32 new_act_pass;
|
uint32 new_act_pass;
|
||||||
uint32 new_act_mail;
|
uint32 new_act_mail;
|
||||||
|
|
||||||
// Amount of passengers that were transported.
|
/* Amount of passengers that were transported. */
|
||||||
byte pct_pass_transported;
|
byte pct_pass_transported;
|
||||||
byte pct_mail_transported;
|
byte pct_mail_transported;
|
||||||
|
|
||||||
// Amount of food and paper that was transported. Actually a bit mask would be enough.
|
/* Amount of food and paper that was transported. Actually a bit mask would be enough. */
|
||||||
uint16 act_food;
|
uint16 act_food;
|
||||||
uint16 act_water;
|
uint16 act_water;
|
||||||
uint16 new_act_food;
|
uint16 new_act_food;
|
||||||
uint16 new_act_water;
|
uint16 new_act_water;
|
||||||
|
|
||||||
// Time until we rebuild a house.
|
/* Time until we rebuild a house. */
|
||||||
byte time_until_rebuild;
|
byte time_until_rebuild;
|
||||||
|
|
||||||
// When to grow town next time.
|
/* When to grow town next time. */
|
||||||
byte grow_counter;
|
byte grow_counter;
|
||||||
byte growth_rate;
|
byte growth_rate;
|
||||||
|
|
||||||
// Fund buildings program in action?
|
/* Fund buildings program in action? */
|
||||||
byte fund_buildings_months;
|
byte fund_buildings_months;
|
||||||
|
|
||||||
// Fund road reconstruction in action?
|
/* Fund road reconstruction in action? */
|
||||||
byte road_build_months;
|
byte road_build_months;
|
||||||
|
|
||||||
// Index in town array
|
/* Index in town array */
|
||||||
TownID index;
|
TownID index;
|
||||||
|
|
||||||
// NOSAVE: UpdateTownRadius updates this given the house count.
|
/* NOSAVE: UpdateTownRadius updates this given the house count. */
|
||||||
uint16 radius[5];
|
uint16 radius[5];
|
||||||
|
|
||||||
// NOSAVE: The number of each type of building in the town.
|
/* NOSAVE: The number of each type of building in the town. */
|
||||||
BuildingCounts building_counts;
|
BuildingCounts building_counts;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -197,8 +199,8 @@ enum {
|
||||||
};
|
};
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
// These refer to the maximums, so Appalling is -1000 to -400
|
/* These refer to the maximums, so Appalling is -1000 to -400
|
||||||
// MAXIMUM RATINGS BOUNDARIES
|
* MAXIMUM RATINGS BOUNDARIES */
|
||||||
RATING_MINIMUM = -1000,
|
RATING_MINIMUM = -1000,
|
||||||
RATING_APPALLING = -400,
|
RATING_APPALLING = -400,
|
||||||
RATING_VERYPOOR = -200,
|
RATING_VERYPOOR = -200,
|
||||||
|
@ -207,11 +209,11 @@ enum {
|
||||||
RATING_GOOD = 400,
|
RATING_GOOD = 400,
|
||||||
RATING_VERYGOOD = 600,
|
RATING_VERYGOOD = 600,
|
||||||
RATING_EXCELLENT = 800,
|
RATING_EXCELLENT = 800,
|
||||||
RATING_OUTSTANDING = 1000, // OUTSTANDING
|
RATING_OUTSTANDING = 1000, ///< OUTSTANDING
|
||||||
|
|
||||||
RATING_MAXIMUM = RATING_OUTSTANDING,
|
RATING_MAXIMUM = RATING_OUTSTANDING,
|
||||||
|
|
||||||
// RATINGS AFFECTING NUMBERS
|
/* RATINGS AFFECTING NUMBERS */
|
||||||
RATING_TREE_DOWN_STEP = -35,
|
RATING_TREE_DOWN_STEP = -35,
|
||||||
RATING_TREE_MINIMUM = RATING_MINIMUM,
|
RATING_TREE_MINIMUM = RATING_MINIMUM,
|
||||||
RATING_TREE_UP_STEP = 7,
|
RATING_TREE_UP_STEP = 7,
|
||||||
|
@ -241,16 +243,16 @@ enum {
|
||||||
TOWN_HOUSE_COMPLETED = 3,
|
TOWN_HOUSE_COMPLETED = 3,
|
||||||
};
|
};
|
||||||
|
|
||||||
/* This enum is used in conjonction with town->flags12.
|
/** This enum is used in conjonction with town->flags12.
|
||||||
* IT simply states what bit is used for.
|
* IT simply states what bit is used for.
|
||||||
* It is pretty unrealistic (IMHO) to only have one church/stadium
|
* It is pretty unrealistic (IMHO) to only have one church/stadium
|
||||||
* per town, NO MATTER the population of it.
|
* per town, NO MATTER the population of it.
|
||||||
* And there are 5 more bits available on flags12...
|
* And there are 5 more bits available on flags12...
|
||||||
*/
|
*/
|
||||||
enum {
|
enum {
|
||||||
TOWN_IS_FUNDED = 0, // Town has received some funds for
|
TOWN_IS_FUNDED = 0, ///< Town has received some funds for
|
||||||
TOWN_HAS_CHURCH = 1, // There can be only one church by town.
|
TOWN_HAS_CHURCH = 1, ///< There can be only one church by town.
|
||||||
TOWN_HAS_STADIUM = 2 // There can be only one stadium by town.
|
TOWN_HAS_STADIUM = 2 ///< There can be only one stadium by town.
|
||||||
};
|
};
|
||||||
|
|
||||||
bool CheckforTownRating(uint32 flags, Town *t, byte type);
|
bool CheckforTownRating(uint32 flags, Town *t, byte type);
|
||||||
|
@ -267,12 +269,19 @@ static inline HouseSpec *GetHouseSpecs(HouseID house_id)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check if a Town really exists.
|
* Check if a Town really exists.
|
||||||
|
* @param town to inquiry
|
||||||
|
* @return true if it exists
|
||||||
*/
|
*/
|
||||||
static inline bool IsValidTown(const Town* town)
|
static inline bool IsValidTown(const Town* town)
|
||||||
{
|
{
|
||||||
return town->xy != 0;
|
return town->xy != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if a TownID is valid.
|
||||||
|
* @param TownID to inquiry
|
||||||
|
* @return true if it exists
|
||||||
|
*/
|
||||||
static inline bool IsValidTownID(TownID index)
|
static inline bool IsValidTownID(TownID index)
|
||||||
{
|
{
|
||||||
return index < GetTownPoolSize() && IsValidTown(GetTown(index));
|
return index < GetTownPoolSize() && IsValidTown(GetTown(index));
|
||||||
|
|
263
src/town_cmd.cpp
263
src/town_cmd.cpp
|
@ -198,10 +198,10 @@ static void AnimateTile_Town(TileIndex tile)
|
||||||
|
|
||||||
if (_tick_counter & 3) return;
|
if (_tick_counter & 3) return;
|
||||||
|
|
||||||
// If the house is not one with a lift anymore, then stop this animating.
|
/* If the house is not one with a lift anymore, then stop this animating.
|
||||||
// Not exactly sure when this happens, but probably when a house changes.
|
* Not exactly sure when this happens, but probably when a house changes.
|
||||||
// Before this was just a return...so it'd leak animated tiles..
|
* Before this was just a return...so it'd leak animated tiles..
|
||||||
// That bug seems to have been here since day 1??
|
* That bug seems to have been here since day 1?? */
|
||||||
if (!(GetHouseSpecs(GetHouseType(tile))->building_flags & BUILDING_IS_ANIMATED)) {
|
if (!(GetHouseSpecs(GetHouseType(tile))->building_flags & BUILDING_IS_ANIMATED)) {
|
||||||
DeleteAnimatedTile(tile);
|
DeleteAnimatedTile(tile);
|
||||||
return;
|
return;
|
||||||
|
@ -210,7 +210,7 @@ static void AnimateTile_Town(TileIndex tile)
|
||||||
if (!LiftHasDestination(tile)) {
|
if (!LiftHasDestination(tile)) {
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
/** Building has 6 floors, number 0 .. 6, where 1 is illegal.
|
/* Building has 6 floors, number 0 .. 6, where 1 is illegal.
|
||||||
* This is due to the fact that the first floor is, in the graphics,
|
* This is due to the fact that the first floor is, in the graphics,
|
||||||
* the height of 2 'normal' floors.
|
* the height of 2 'normal' floors.
|
||||||
* Furthermore, there are 6 lift positions from floor N (incl) to floor N + 1 (excl) */
|
* Furthermore, there are 6 lift positions from floor N (incl) to floor N + 1 (excl) */
|
||||||
|
@ -328,7 +328,7 @@ static void TileLoop_Town(TileIndex tile)
|
||||||
if (house_id >= NEW_HOUSE_OFFSET && !NewHouseTileLoop(tile)) return;
|
if (house_id >= NEW_HOUSE_OFFSET && !NewHouseTileLoop(tile)) return;
|
||||||
|
|
||||||
if (!IsHouseCompleted(tile)) {
|
if (!IsHouseCompleted(tile)) {
|
||||||
/*Construction is not completed. See if we can go further in construction*/
|
/* Construction is not completed. See if we can go further in construction*/
|
||||||
MakeTownHouseBigger(tile);
|
MakeTownHouseBigger(tile);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -367,7 +367,7 @@ static void TileLoop_Town(TileIndex tile)
|
||||||
|
|
||||||
ClearTownHouse(t, tile);
|
ClearTownHouse(t, tile);
|
||||||
|
|
||||||
// rebuild with another house?
|
/* rebuild with another house? */
|
||||||
if (GB(r, 24, 8) >= 12) DoBuildTownHouse(t, tile);
|
if (GB(r, 24, 8) >= 12) DoBuildTownHouse(t, tile);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -446,8 +446,8 @@ static const TileIndexDiffC _roadblock_tileadd[] = {
|
||||||
{ 0, 1},
|
{ 0, 1},
|
||||||
{-1, 0},
|
{-1, 0},
|
||||||
|
|
||||||
// Store the first 3 elements again.
|
/* Store the first 3 elements again.
|
||||||
// Lets us rotate without using &3.
|
* Lets us rotate without using &3. */
|
||||||
{ 0, -1},
|
{ 0, -1},
|
||||||
{ 1, 0},
|
{ 1, 0},
|
||||||
{ 0, 1}
|
{ 0, 1}
|
||||||
|
@ -510,16 +510,16 @@ static bool IsRoadAllowedHere(TileIndex tile, int dir)
|
||||||
Slope k;
|
Slope k;
|
||||||
Slope slope;
|
Slope slope;
|
||||||
|
|
||||||
// If this assertion fails, it might be because the world contains
|
/* If this assertion fails, it might be because the world contains
|
||||||
// land at the edges. This is not ok.
|
* land at the edges. This is not ok. */
|
||||||
TILE_ASSERT(tile);
|
TILE_ASSERT(tile);
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
// Check if there already is a road at this point?
|
/* Check if there already is a road at this point? */
|
||||||
if (GetAnyRoadTrackBits(tile) == 0) {
|
if (GetAnyRoadTrackBits(tile) == 0) {
|
||||||
// No, try to build one in the direction.
|
/* No, try to build one in the direction.
|
||||||
// if that fails clear the land, and if that fails exit.
|
* if that fails clear the land, and if that fails exit.
|
||||||
// This is to make sure that we can build a road here later.
|
* This is to make sure that we can build a road here later. */
|
||||||
if (CmdFailed(DoCommand(tile, (dir & 1 ? ROAD_X : ROAD_Y), 0, DC_AUTO, CMD_BUILD_ROAD)) &&
|
if (CmdFailed(DoCommand(tile, (dir & 1 ? ROAD_X : ROAD_Y), 0, DC_AUTO, CMD_BUILD_ROAD)) &&
|
||||||
CmdFailed(DoCommand(tile, 0, 0, DC_AUTO, CMD_LANDSCAPE_CLEAR)))
|
CmdFailed(DoCommand(tile, 0, 0, DC_AUTO, CMD_LANDSCAPE_CLEAR)))
|
||||||
return false;
|
return false;
|
||||||
|
@ -528,20 +528,20 @@ static bool IsRoadAllowedHere(TileIndex tile, int dir)
|
||||||
slope = GetTileSlope(tile, NULL);
|
slope = GetTileSlope(tile, NULL);
|
||||||
if (slope == SLOPE_FLAT) {
|
if (slope == SLOPE_FLAT) {
|
||||||
no_slope:
|
no_slope:
|
||||||
// Tile has no slope
|
/* Tile has no slope
|
||||||
// Disallow the road if any neighboring tile has a road.
|
* Disallow the road if any neighboring tile has a road. */
|
||||||
if (HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+1]))), dir^2) ||
|
if (HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+1]))), dir^2) ||
|
||||||
HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+3]))), dir^2) ||
|
HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+3]))), dir^2) ||
|
||||||
HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+1]) + ToTileIndexDiff(_roadblock_tileadd[dir+2]))), dir) ||
|
HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+1]) + ToTileIndexDiff(_roadblock_tileadd[dir+2]))), dir) ||
|
||||||
HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+3]) + ToTileIndexDiff(_roadblock_tileadd[dir+2]))), dir))
|
HASBIT(GetTownRoadMask(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[dir+3]) + ToTileIndexDiff(_roadblock_tileadd[dir+2]))), dir))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// Otherwise allow
|
/* Otherwise allow */
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// If the tile is not a slope in the right direction, then
|
/* If the tile is not a slope in the right direction, then
|
||||||
// maybe terraform some.
|
* maybe terraform some. */
|
||||||
k = (dir & 1) ? SLOPE_NE : SLOPE_NW;
|
k = (dir & 1) ? SLOPE_NE : SLOPE_NW;
|
||||||
if (k != slope && ComplementSlope(k) != slope) {
|
if (k != slope && ComplementSlope(k) != slope) {
|
||||||
uint32 r = Random();
|
uint32 r = Random();
|
||||||
|
@ -557,7 +557,7 @@ no_slope:
|
||||||
CMD_TERRAFORM_LAND);
|
CMD_TERRAFORM_LAND);
|
||||||
}
|
}
|
||||||
if (CmdFailed(res) && CHANCE16I(1, 3, r)) {
|
if (CmdFailed(res) && CHANCE16I(1, 3, r)) {
|
||||||
// We can consider building on the slope, though.
|
/* We can consider building on the slope, though. */
|
||||||
goto no_slope;
|
goto no_slope;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -585,12 +585,12 @@ static void LevelTownLand(TileIndex tile)
|
||||||
|
|
||||||
TILE_ASSERT(tile);
|
TILE_ASSERT(tile);
|
||||||
|
|
||||||
// Don't terraform if land is plain or if there's a house there.
|
/* Don't terraform if land is plain or if there's a house there. */
|
||||||
if (IsTileType(tile, MP_HOUSE)) return;
|
if (IsTileType(tile, MP_HOUSE)) return;
|
||||||
tileh = GetTileSlope(tile, NULL);
|
tileh = GetTileSlope(tile, NULL);
|
||||||
if (tileh == SLOPE_FLAT) return;
|
if (tileh == SLOPE_FLAT) return;
|
||||||
|
|
||||||
// First try up, then down
|
/* First try up, then down */
|
||||||
if (!TerraformTownTile(tile, ~tileh & 0xF, 1)) {
|
if (!TerraformTownTile(tile, ~tileh & 0xF, 1)) {
|
||||||
TerraformTownTile(tile, tileh & 0xF, 0);
|
TerraformTownTile(tile, tileh & 0xF, 0);
|
||||||
}
|
}
|
||||||
|
@ -610,17 +610,17 @@ static void GrowTownInTile(TileIndex* tile_ptr, RoadBits mask, int block, Town*
|
||||||
int a;
|
int a;
|
||||||
int b;
|
int b;
|
||||||
|
|
||||||
// Tile has no road. First reset the status counter
|
/* Tile has no road. First reset the status counter
|
||||||
// to say that this is the last iteration.
|
* to say that this is the last iteration. */
|
||||||
_grow_town_result = 0;
|
_grow_town_result = 0;
|
||||||
|
|
||||||
// Remove hills etc
|
/* Remove hills etc */
|
||||||
LevelTownLand(tile);
|
LevelTownLand(tile);
|
||||||
|
|
||||||
// Is a road allowed here?
|
/* Is a road allowed here? */
|
||||||
if (!IsRoadAllowedHere(tile, block)) return;
|
if (!IsRoadAllowedHere(tile, block)) return;
|
||||||
|
|
||||||
// Randomize new road block numbers
|
/* Randomize new road block numbers */
|
||||||
a = block;
|
a = block;
|
||||||
b = block ^ 2;
|
b = block ^ 2;
|
||||||
if (CHANCE16(1, 4)) {
|
if (CHANCE16(1, 4)) {
|
||||||
|
@ -630,29 +630,29 @@ static void GrowTownInTile(TileIndex* tile_ptr, RoadBits mask, int block, Town*
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!IsRoadAllowedHere(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[a])), a)) {
|
if (!IsRoadAllowedHere(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[a])), a)) {
|
||||||
// A road is not allowed to continue the randomized road,
|
/* A road is not allowed to continue the randomized road,
|
||||||
// return if the road we're trying to build is curved.
|
* return if the road we're trying to build is curved. */
|
||||||
if (a != (b ^ 2)) return;
|
if (a != (b ^ 2)) return;
|
||||||
|
|
||||||
// Return if neither side of the new road is a house
|
/* Return if neither side of the new road is a house */
|
||||||
if (!IsTileType(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[a + 1])), MP_HOUSE) &&
|
if (!IsTileType(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[a + 1])), MP_HOUSE) &&
|
||||||
!IsTileType(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[a + 3])), MP_HOUSE))
|
!IsTileType(TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[a + 3])), MP_HOUSE))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// That means that the road is only allowed if there is a house
|
/* That means that the road is only allowed if there is a house
|
||||||
// at any side of the new road.
|
* at any side of the new road. */
|
||||||
}
|
}
|
||||||
rcmd = (RoadBits)((1 << a) + (1 << b));
|
rcmd = (RoadBits)((1 << a) + (1 << b));
|
||||||
|
|
||||||
} else if (block < 5 && !HASBIT(mask,block^2)) {
|
} else if (block < 5 && !HASBIT(mask,block^2)) {
|
||||||
// Continue building on a partial road.
|
/* Continue building on a partial road.
|
||||||
// Always OK.
|
* Always OK. */
|
||||||
_grow_town_result = 0;
|
_grow_town_result = 0;
|
||||||
rcmd = (RoadBits)(1 << (block ^ 2));
|
rcmd = (RoadBits)(1 << (block ^ 2));
|
||||||
} else {
|
} else {
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
// Reached a tunnel/bridge? Then continue at the other side of it.
|
/* Reached a tunnel/bridge? Then continue at the other side of it. */
|
||||||
if (IsTileType(tile, MP_TUNNELBRIDGE)) {
|
if (IsTileType(tile, MP_TUNNELBRIDGE)) {
|
||||||
if (IsTunnel(tile) && GetTunnelTransportType(tile) == TRANSPORT_ROAD) {
|
if (IsTunnel(tile) && GetTunnelTransportType(tile) == TRANSPORT_ROAD) {
|
||||||
*tile_ptr = GetOtherTunnelEnd(tile);
|
*tile_ptr = GetOtherTunnelEnd(tile);
|
||||||
|
@ -662,27 +662,27 @@ static void GrowTownInTile(TileIndex* tile_ptr, RoadBits mask, int block, Town*
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Possibly extend the road in a direction.
|
/* Possibly extend the road in a direction.
|
||||||
// Randomize a direction and if it has a road, bail out.
|
* Randomize a direction and if it has a road, bail out. */
|
||||||
i = GB(Random(), 0, 2);
|
i = GB(Random(), 0, 2);
|
||||||
if (HASBIT(mask, i)) return;
|
if (HASBIT(mask, i)) return;
|
||||||
|
|
||||||
// This is the tile we will reach if we extend to this direction.
|
/* This is the tile we will reach if we extend to this direction. */
|
||||||
tmptile = TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[i]));
|
tmptile = TILE_ADD(tile, ToTileIndexDiff(_roadblock_tileadd[i]));
|
||||||
|
|
||||||
// Don't do it if it reaches to water.
|
/* Don't do it if it reaches to water. */
|
||||||
if (IsClearWaterTile(tmptile)) return;
|
if (IsClearWaterTile(tmptile)) return;
|
||||||
|
|
||||||
// Build a house at the edge. 60% chance or
|
/* Build a house at the edge. 60% chance or
|
||||||
// always ok if no road allowed.
|
* always ok if no road allowed. */
|
||||||
if (!IsRoadAllowedHere(tmptile, i) || CHANCE16(6, 10)) {
|
if (!IsRoadAllowedHere(tmptile, i) || CHANCE16(6, 10)) {
|
||||||
// But not if there already is a house there.
|
/* But not if there already is a house there. */
|
||||||
if (!IsTileType(tmptile, MP_HOUSE)) {
|
if (!IsTileType(tmptile, MP_HOUSE)) {
|
||||||
// Level the land if possible
|
/* Level the land if possible */
|
||||||
LevelTownLand(tmptile);
|
LevelTownLand(tmptile);
|
||||||
|
|
||||||
// And build a house.
|
/* And build a house.
|
||||||
// Set result to -1 if we managed to build it.
|
* Set result to -1 if we managed to build it. */
|
||||||
if (BuildTownHouse(t1, tmptile)) _grow_town_result = -1;
|
if (BuildTownHouse(t1, tmptile)) _grow_town_result = -1;
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
|
@ -692,11 +692,11 @@ static void GrowTownInTile(TileIndex* tile_ptr, RoadBits mask, int block, Town*
|
||||||
rcmd = (RoadBits)(1 << i);
|
rcmd = (RoadBits)(1 << i);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Return if a water tile
|
/* Return if a water tile */
|
||||||
if (IsClearWaterTile(tile)) return;
|
if (IsClearWaterTile(tile)) return;
|
||||||
|
|
||||||
// Determine direction of slope,
|
/* Determine direction of slope,
|
||||||
// and build a road if not a special slope.
|
* and build a road if not a special slope. */
|
||||||
switch (GetTileSlope(tile, NULL)) {
|
switch (GetTileSlope(tile, NULL)) {
|
||||||
case SLOPE_SW: i = DIAGDIR_NE; break;
|
case SLOPE_SW: i = DIAGDIR_NE; break;
|
||||||
case SLOPE_SE: i = DIAGDIR_NW; break;
|
case SLOPE_SE: i = DIAGDIR_NW; break;
|
||||||
|
@ -713,7 +713,7 @@ build_road_and_exit:
|
||||||
|
|
||||||
tmptile = tile;
|
tmptile = tile;
|
||||||
|
|
||||||
// Now it contains the direction of the slope
|
/* Now it contains the direction of the slope */
|
||||||
j = -11; // max 11 tile long bridges
|
j = -11; // max 11 tile long bridges
|
||||||
do {
|
do {
|
||||||
if (++j == 0)
|
if (++j == 0)
|
||||||
|
@ -721,11 +721,11 @@ build_road_and_exit:
|
||||||
tmptile = TILE_MASK(tmptile + TileOffsByDiagDir(i));
|
tmptile = TILE_MASK(tmptile + TileOffsByDiagDir(i));
|
||||||
} while (IsClearWaterTile(tmptile));
|
} while (IsClearWaterTile(tmptile));
|
||||||
|
|
||||||
// no water tiles in between?
|
/* no water tiles in between? */
|
||||||
if (j == -10)
|
if (j == -10)
|
||||||
goto build_road_and_exit;
|
goto build_road_and_exit;
|
||||||
|
|
||||||
// Quit if it selecting an appropiate bridge type fails a large number of times.
|
/* Quit if it selecting an appropiate bridge type fails a large number of times. */
|
||||||
j = 22;
|
j = 22;
|
||||||
{
|
{
|
||||||
int32 bridge_len = GetBridgeLength(tile, tmptile);
|
int32 bridge_len = GetBridgeLength(tile, tmptile);
|
||||||
|
@ -735,38 +735,42 @@ build_road_and_exit:
|
||||||
if (!CmdFailed(DoCommand(tile, tmptile, 0x8000 + bridge_type, DC_EXEC | DC_AUTO, CMD_BUILD_BRIDGE)))
|
if (!CmdFailed(DoCommand(tile, tmptile, 0x8000 + bridge_type, DC_EXEC | DC_AUTO, CMD_BUILD_BRIDGE)))
|
||||||
_grow_town_result = -1;
|
_grow_town_result = -1;
|
||||||
|
|
||||||
// obviously, if building any bridge would fail, there is no need to try other bridge-types
|
/* obviously, if building any bridge would fail, there is no need to try other bridge-types */
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
} while (--j != 0);
|
} while (--j != 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns true if a house was built, or no if the build failed.
|
/** Returns "growth" if a house was built, or no if the build failed.
|
||||||
|
* @param t town to inquiry
|
||||||
|
* @param tile to inquiry
|
||||||
|
* @return something other than zero(0)if town expansion was possible
|
||||||
|
*/
|
||||||
static int GrowTownAtRoad(Town *t, TileIndex tile)
|
static int GrowTownAtRoad(Town *t, TileIndex tile)
|
||||||
{
|
{
|
||||||
int block = 5; // special case
|
int block = 5; // special case
|
||||||
|
|
||||||
TILE_ASSERT(tile);
|
TILE_ASSERT(tile);
|
||||||
|
|
||||||
// Number of times to search.
|
/* Number of times to search. */
|
||||||
_grow_town_result = 10 + t->num_houses * 4 / 9;
|
_grow_town_result = 10 + t->num_houses * 4 / 9;
|
||||||
|
|
||||||
do {
|
do {
|
||||||
// Get a bitmask of the road blocks on a tile
|
/* Get a bitmask of the road blocks on a tile */
|
||||||
RoadBits mask = GetTownRoadMask(tile);
|
RoadBits mask = GetTownRoadMask(tile);
|
||||||
|
|
||||||
// Try to grow the town from this point
|
/* Try to grow the town from this point */
|
||||||
GrowTownInTile(&tile,mask,block,t);
|
GrowTownInTile(&tile, mask, block, t);
|
||||||
|
|
||||||
// Exclude the source position from the bitmask
|
/* Exclude the source position from the bitmask
|
||||||
// and return if no more road blocks available
|
* and return if no more road blocks available */
|
||||||
ClrBitT(mask, (block ^ 2));
|
ClrBitT(mask, (block ^ 2));
|
||||||
if (mask == 0)
|
if (mask == 0)
|
||||||
return _grow_town_result;
|
return _grow_town_result;
|
||||||
|
|
||||||
// Select a random bit from the blockmask, walk a step
|
/* Select a random bit from the blockmask, walk a step
|
||||||
// and continue the search from there.
|
* and continue the search from there. */
|
||||||
do block = Random() & 3; while (!HASBIT(mask,block));
|
do block = Random() & 3; while (!HASBIT(mask,block));
|
||||||
tile += ToTileIndexDiff(_roadblock_tileadd[block]);
|
tile += ToTileIndexDiff(_roadblock_tileadd[block]);
|
||||||
|
|
||||||
|
@ -782,15 +786,15 @@ static int GrowTownAtRoad(Town *t, TileIndex tile)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Max number of times is checked.
|
/* Max number of times is checked. */
|
||||||
} while (--_grow_town_result >= 0);
|
} while (--_grow_town_result >= 0);
|
||||||
|
|
||||||
return (_grow_town_result == -2);
|
return (_grow_town_result == -2);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Generate a random road block
|
/** Generate a random road block
|
||||||
// The probability of a straight road
|
* The probability of a straight road
|
||||||
// is somewhat higher than a curved.
|
* is somewhat higher than a curved. */
|
||||||
static RoadBits GenRandomRoadBits()
|
static RoadBits GenRandomRoadBits()
|
||||||
{
|
{
|
||||||
uint32 r = Random();
|
uint32 r = Random();
|
||||||
|
@ -800,8 +804,8 @@ static RoadBits GenRandomRoadBits()
|
||||||
return (RoadBits)((1 << a) + (1 << b));
|
return (RoadBits)((1 << a) + (1 << b));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Grow the town
|
/** Grow the town
|
||||||
// Returns true if a house was built, or no if the build failed.
|
* @Return true if a house was built, or no if the build failed. */
|
||||||
static bool GrowTown(Town *t)
|
static bool GrowTown(Town *t)
|
||||||
{
|
{
|
||||||
TileIndex tile;
|
TileIndex tile;
|
||||||
|
@ -824,11 +828,11 @@ static bool GrowTown(Town *t)
|
||||||
{ 0, 0}
|
{ 0, 0}
|
||||||
};
|
};
|
||||||
|
|
||||||
// Current player is a town
|
/* Current player is a town */
|
||||||
old_player = _current_player;
|
old_player = _current_player;
|
||||||
_current_player = OWNER_TOWN;
|
_current_player = OWNER_TOWN;
|
||||||
|
|
||||||
// Find a road that we can base the construction on.
|
/* Find a road that we can base the construction on. */
|
||||||
tile = t->xy;
|
tile = t->xy;
|
||||||
for (ptr = _town_coord_mod; ptr != endof(_town_coord_mod); ++ptr) {
|
for (ptr = _town_coord_mod; ptr != endof(_town_coord_mod); ++ptr) {
|
||||||
if (GetAnyRoadTrackBits(tile) != 0) {
|
if (GetAnyRoadTrackBits(tile) != 0) {
|
||||||
|
@ -839,8 +843,8 @@ static bool GrowTown(Town *t)
|
||||||
tile = TILE_ADD(tile, ToTileIndexDiff(*ptr));
|
tile = TILE_ADD(tile, ToTileIndexDiff(*ptr));
|
||||||
}
|
}
|
||||||
|
|
||||||
// No road available, try to build a random road block by
|
/* No road available, try to build a random road block by
|
||||||
// clearing some land and then building a road there.
|
* clearing some land and then building a road there. */
|
||||||
tile = t->xy;
|
tile = t->xy;
|
||||||
for (ptr = _town_coord_mod; ptr != endof(_town_coord_mod); ++ptr) {
|
for (ptr = _town_coord_mod; ptr != endof(_town_coord_mod); ++ptr) {
|
||||||
/* Only work with plain land that not already has a house */
|
/* Only work with plain land that not already has a house */
|
||||||
|
@ -890,11 +894,11 @@ static void UpdateTownRadius(Town *t)
|
||||||
memcpy(t->radius, _town_radius_data[t->num_houses / 4], sizeof(t->radius));
|
memcpy(t->radius, _town_radius_data[t->num_houses / 4], sizeof(t->radius));
|
||||||
} else {
|
} else {
|
||||||
int mass = t->num_houses / 8;
|
int mass = t->num_houses / 8;
|
||||||
// At least very roughly extrapolate. Empirical numbers dancing between
|
/* At least very roughly extrapolate. Empirical numbers dancing between
|
||||||
// overwhelming by cottages and skyscrapers outskirts.
|
* overwhelming by cottages and skyscrapers outskirts. */
|
||||||
t->radius[0] = mass * mass;
|
t->radius[0] = mass * mass;
|
||||||
// Actually we are proportional to sqrt() but that's right because
|
/* Actually we are proportional to sqrt() but that's right because
|
||||||
// we are covering an area.
|
* we are covering an area. */
|
||||||
t->radius[1] = mass * 7;
|
t->radius[1] = mass * 7;
|
||||||
t->radius[2] = 0;
|
t->radius[2] = 0;
|
||||||
t->radius[3] = mass * 4;
|
t->radius[3] = mass * 4;
|
||||||
|
@ -926,12 +930,12 @@ restart:
|
||||||
SetDParam(0, r);
|
SetDParam(0, r);
|
||||||
GetString(buf1, townnametype, lastof(buf1));
|
GetString(buf1, townnametype, lastof(buf1));
|
||||||
|
|
||||||
// Check size and width
|
/* Check size and width */
|
||||||
if (strlen(buf1) >= 31 || GetStringBoundingBox(buf1).width > 130) continue;
|
if (strlen(buf1) >= 31 || GetStringBoundingBox(buf1).width > 130) continue;
|
||||||
|
|
||||||
FOR_ALL_TOWNS(t2) {
|
FOR_ALL_TOWNS(t2) {
|
||||||
// We can't just compare the numbers since
|
/* We can't just compare the numbers since
|
||||||
// several numbers may map to a single name.
|
* several numbers may map to a single name. */
|
||||||
SetDParam(0, t2->index);
|
SetDParam(0, t2->index);
|
||||||
GetString(buf2, STR_TOWN, lastof(buf2));
|
GetString(buf2, STR_TOWN, lastof(buf2));
|
||||||
if (strcmp(buf1, buf2) == 0) {
|
if (strcmp(buf1, buf2) == 0) {
|
||||||
|
@ -954,7 +958,7 @@ static void DoCreateTown(Town *t, TileIndex tile, uint32 townnameparts, uint siz
|
||||||
{
|
{
|
||||||
int x, i;
|
int x, i;
|
||||||
|
|
||||||
// clear the town struct
|
/* clear the town struct */
|
||||||
i = t->index;
|
i = t->index;
|
||||||
memset(t, 0, sizeof(Town));
|
memset(t, 0, sizeof(Town));
|
||||||
t->index = i;
|
t->index = i;
|
||||||
|
@ -1046,6 +1050,7 @@ static Town *AllocateTown()
|
||||||
* This obviously only works in the scenario editor. Function not removed
|
* This obviously only works in the scenario editor. Function not removed
|
||||||
* as it might be possible in the future to fund your own town :)
|
* as it might be possible in the future to fund your own town :)
|
||||||
* @param tile coordinates where town is built
|
* @param tile coordinates where town is built
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 size of the town (0 = random, 1 = small, 2 = medium, 3 = large)
|
* @param p1 size of the town (0 = random, 1 = small, 2 = medium, 3 = large)
|
||||||
* @param p2 unused
|
* @param p2 unused
|
||||||
*/
|
*/
|
||||||
|
@ -1059,28 +1064,28 @@ int32 CmdBuildTown(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
SET_EXPENSES_TYPE(EXPENSES_OTHER);
|
SET_EXPENSES_TYPE(EXPENSES_OTHER);
|
||||||
|
|
||||||
// Check if too close to the edge of map
|
/* Check if too close to the edge of map */
|
||||||
if (DistanceFromEdge(tile) < 12)
|
if (DistanceFromEdge(tile) < 12)
|
||||||
return_cmd_error(STR_0237_TOO_CLOSE_TO_EDGE_OF_MAP);
|
return_cmd_error(STR_0237_TOO_CLOSE_TO_EDGE_OF_MAP);
|
||||||
|
|
||||||
// Can only build on clear flat areas, possibly with trees.
|
/* Can only build on clear flat areas, possibly with trees. */
|
||||||
if ((!IsTileType(tile, MP_CLEAR) && !IsTileType(tile, MP_TREES)) || GetTileSlope(tile, NULL) != SLOPE_FLAT) {
|
if ((!IsTileType(tile, MP_CLEAR) && !IsTileType(tile, MP_TREES)) || GetTileSlope(tile, NULL) != SLOPE_FLAT) {
|
||||||
return_cmd_error(STR_0239_SITE_UNSUITABLE);
|
return_cmd_error(STR_0239_SITE_UNSUITABLE);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check distance to all other towns.
|
/* Check distance to all other towns. */
|
||||||
if (IsCloseToTown(tile, 20))
|
if (IsCloseToTown(tile, 20))
|
||||||
return_cmd_error(STR_0238_TOO_CLOSE_TO_ANOTHER_TOWN);
|
return_cmd_error(STR_0238_TOO_CLOSE_TO_ANOTHER_TOWN);
|
||||||
|
|
||||||
// Get a unique name for the town.
|
/* Get a unique name for the town. */
|
||||||
if (!CreateTownName(&townnameparts))
|
if (!CreateTownName(&townnameparts))
|
||||||
return_cmd_error(STR_023A_TOO_MANY_TOWNS);
|
return_cmd_error(STR_023A_TOO_MANY_TOWNS);
|
||||||
|
|
||||||
// Allocate town struct
|
/* Allocate town struct */
|
||||||
t = AllocateTown();
|
t = AllocateTown();
|
||||||
if (t == NULL) return_cmd_error(STR_023A_TOO_MANY_TOWNS);
|
if (t == NULL) return_cmd_error(STR_023A_TOO_MANY_TOWNS);
|
||||||
|
|
||||||
// Create the town
|
/* Create the town */
|
||||||
if (flags & DC_EXEC) {
|
if (flags & DC_EXEC) {
|
||||||
_generating_world = true;
|
_generating_world = true;
|
||||||
DoCreateTown(t, tile, townnameparts, p1);
|
DoCreateTown(t, tile, townnameparts, p1);
|
||||||
|
@ -1096,20 +1101,20 @@ Town *CreateRandomTown(uint attempts, uint size_mode)
|
||||||
uint32 townnameparts;
|
uint32 townnameparts;
|
||||||
|
|
||||||
do {
|
do {
|
||||||
// Generate a tile index not too close from the edge
|
/* Generate a tile index not too close from the edge */
|
||||||
tile = RandomTile();
|
tile = RandomTile();
|
||||||
if (DistanceFromEdge(tile) < 20) continue;
|
if (DistanceFromEdge(tile) < 20) continue;
|
||||||
|
|
||||||
// Make sure the tile is plain
|
/* Make sure the tile is plain */
|
||||||
if (!IsTileType(tile, MP_CLEAR) || GetTileSlope(tile, NULL) != SLOPE_FLAT) continue;
|
if (!IsTileType(tile, MP_CLEAR) || GetTileSlope(tile, NULL) != SLOPE_FLAT) continue;
|
||||||
|
|
||||||
// Check not too close to a town
|
/* Check not too close to a town */
|
||||||
if (IsCloseToTown(tile, 20)) continue;
|
if (IsCloseToTown(tile, 20)) continue;
|
||||||
|
|
||||||
// Get a unique name for the town.
|
/* Get a unique name for the town. */
|
||||||
if (!CreateTownName(&townnameparts)) break;
|
if (!CreateTownName(&townnameparts)) break;
|
||||||
|
|
||||||
// Allocate a town struct
|
/* Allocate a town struct */
|
||||||
t = AllocateTown();
|
t = AllocateTown();
|
||||||
if (t == NULL) break;
|
if (t == NULL) break;
|
||||||
|
|
||||||
|
@ -1130,11 +1135,11 @@ bool GenerateTowns()
|
||||||
|
|
||||||
do {
|
do {
|
||||||
IncreaseGeneratingWorldProgress(GWP_TOWN);
|
IncreaseGeneratingWorldProgress(GWP_TOWN);
|
||||||
// try 20 times to create a random-sized town for the first loop.
|
/* try 20 times to create a random-sized town for the first loop. */
|
||||||
if (CreateRandomTown(20, 0) != NULL) num++;
|
if (CreateRandomTown(20, 0) != NULL) num++;
|
||||||
} while (--n);
|
} while (--n);
|
||||||
|
|
||||||
// give it a last try, but now more aggressive
|
/* give it a last try, but now more aggressive */
|
||||||
if (num == 0 && CreateRandomTown(10000, 0) == NULL) {
|
if (num == 0 && CreateRandomTown(10000, 0) == NULL) {
|
||||||
if (GetNumTowns() == 0) {
|
if (GetNumTowns() == 0) {
|
||||||
/* XXX - can we handle that more gracefully? */
|
/* XXX - can we handle that more gracefully? */
|
||||||
|
@ -1223,10 +1228,10 @@ static void DoBuildTownHouse(Town *t, TileIndex tile)
|
||||||
uint oneof = 0;
|
uint oneof = 0;
|
||||||
HouseSpec *hs;
|
HouseSpec *hs;
|
||||||
|
|
||||||
// Above snow?
|
/* Above snow? */
|
||||||
slope = GetTileSlope(tile, &z);
|
slope = GetTileSlope(tile, &z);
|
||||||
|
|
||||||
// Get the town zone type
|
/* Get the town zone type */
|
||||||
{
|
{
|
||||||
uint rad = GetTownRadiusGroup(t, tile);
|
uint rad = GetTownRadiusGroup(t, tile);
|
||||||
|
|
||||||
|
@ -1236,16 +1241,16 @@ static void DoBuildTownHouse(Town *t, TileIndex tile)
|
||||||
bitmask = (1 << rad) + (1 << (land + 12));
|
bitmask = (1 << rad) + (1 << (land + 12));
|
||||||
}
|
}
|
||||||
|
|
||||||
// bits 0-4 are used
|
/* bits 0-4 are used
|
||||||
// bits 11-15 are used
|
* bits 11-15 are used
|
||||||
// bits 5-10 are not used.
|
* bits 5-10 are not used. */
|
||||||
{
|
{
|
||||||
HouseID houses[HOUSE_MAX];
|
HouseID houses[HOUSE_MAX];
|
||||||
int num = 0;
|
int num = 0;
|
||||||
uint cumulative_probs[HOUSE_MAX];
|
uint cumulative_probs[HOUSE_MAX];
|
||||||
uint probability_max = 0;
|
uint probability_max = 0;
|
||||||
|
|
||||||
// Generate a list of all possible houses that can be built.
|
/* Generate a list of all possible houses that can be built. */
|
||||||
for (i = 0; i < HOUSE_MAX; i++) {
|
for (i = 0; i < HOUSE_MAX; i++) {
|
||||||
hs = GetHouseSpecs(i);
|
hs = GetHouseSpecs(i);
|
||||||
if ((~hs->building_availability & bitmask) == 0 && hs->enabled) {
|
if ((~hs->building_availability & bitmask) == 0 && hs->enabled) {
|
||||||
|
@ -1282,7 +1287,7 @@ static void DoBuildTownHouse(Town *t, TileIndex tile)
|
||||||
|
|
||||||
if (_cur_year < hs->min_date || _cur_year > hs->max_date) continue;
|
if (_cur_year < hs->min_date || _cur_year > hs->max_date) continue;
|
||||||
|
|
||||||
// Special houses that there can be only one of.
|
/* Special houses that there can be only one of. */
|
||||||
if (hs->building_flags & BUILDING_IS_CHURCH) {
|
if (hs->building_flags & BUILDING_IS_CHURCH) {
|
||||||
SETBIT(oneof, TOWN_HAS_CHURCH);
|
SETBIT(oneof, TOWN_HAS_CHURCH);
|
||||||
} else if (hs->building_flags & BUILDING_IS_STADIUM) {
|
} else if (hs->building_flags & BUILDING_IS_STADIUM) {
|
||||||
|
@ -1293,7 +1298,7 @@ static void DoBuildTownHouse(Town *t, TileIndex tile)
|
||||||
|
|
||||||
if (HASBITS(t->flags12 , oneof)) continue;
|
if (HASBITS(t->flags12 , oneof)) continue;
|
||||||
|
|
||||||
// Make sure there is no slope?
|
/* Make sure there is no slope? */
|
||||||
if (hs->building_flags & TILE_NOT_SLOPED && slope != SLOPE_FLAT) continue;
|
if (hs->building_flags & TILE_NOT_SLOPED && slope != SLOPE_FLAT) continue;
|
||||||
|
|
||||||
if (hs->building_flags & TILE_SIZE_2x2) {
|
if (hs->building_flags & TILE_SIZE_2x2) {
|
||||||
|
@ -1327,7 +1332,7 @@ static void DoBuildTownHouse(Town *t, TileIndex tile)
|
||||||
t->num_houses++;
|
t->num_houses++;
|
||||||
IncreaseBuildingCount(t, house);
|
IncreaseBuildingCount(t, house);
|
||||||
|
|
||||||
// Special houses that there can be only one of.
|
/* Special houses that there can be only one of. */
|
||||||
t->flags12 |= oneof;
|
t->flags12 |= oneof;
|
||||||
|
|
||||||
{
|
{
|
||||||
|
@ -1379,7 +1384,7 @@ void ClearTownHouse(Town *t, TileIndex tile)
|
||||||
|
|
||||||
assert(IsTileType(tile, MP_HOUSE));
|
assert(IsTileType(tile, MP_HOUSE));
|
||||||
|
|
||||||
// need to align the tile to point to the upper left corner of the house
|
/* need to align the tile to point to the upper left corner of the house */
|
||||||
if (house >= 3) { // house id 0,1,2 MUST be single tile houses, or this code breaks.
|
if (house >= 3) { // house id 0,1,2 MUST be single tile houses, or this code breaks.
|
||||||
if (GetHouseSpecs(house-1)->building_flags & TILE_SIZE_2x1) {
|
if (GetHouseSpecs(house-1)->building_flags & TILE_SIZE_2x1) {
|
||||||
house--;
|
house--;
|
||||||
|
@ -1398,7 +1403,7 @@ void ClearTownHouse(Town *t, TileIndex tile)
|
||||||
|
|
||||||
hs = GetHouseSpecs(house);
|
hs = GetHouseSpecs(house);
|
||||||
|
|
||||||
// Remove population from the town if the house is finished.
|
/* Remove population from the town if the house is finished. */
|
||||||
if (IsHouseCompleted(tile)) {
|
if (IsHouseCompleted(tile)) {
|
||||||
ChangePopulation(t, -hs->population);
|
ChangePopulation(t, -hs->population);
|
||||||
}
|
}
|
||||||
|
@ -1406,14 +1411,14 @@ void ClearTownHouse(Town *t, TileIndex tile)
|
||||||
t->num_houses--;
|
t->num_houses--;
|
||||||
DecreaseBuildingCount(t, house);
|
DecreaseBuildingCount(t, house);
|
||||||
|
|
||||||
// Clear flags for houses that only may exist once/town.
|
/* Clear flags for houses that only may exist once/town. */
|
||||||
if (hs->building_flags & BUILDING_IS_CHURCH) {
|
if (hs->building_flags & BUILDING_IS_CHURCH) {
|
||||||
CLRBIT(t->flags12, TOWN_HAS_CHURCH);
|
CLRBIT(t->flags12, TOWN_HAS_CHURCH);
|
||||||
} else if (hs->building_flags & BUILDING_IS_STADIUM) {
|
} else if (hs->building_flags & BUILDING_IS_STADIUM) {
|
||||||
CLRBIT(t->flags12, TOWN_HAS_STADIUM);
|
CLRBIT(t->flags12, TOWN_HAS_STADIUM);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Do the actual clearing of tiles
|
/* Do the actual clearing of tiles */
|
||||||
eflags = hs->building_flags;
|
eflags = hs->building_flags;
|
||||||
DoClearTownHouseHelper(tile);
|
DoClearTownHouseHelper(tile);
|
||||||
if (eflags & BUILDING_2_TILES_X) DoClearTownHouseHelper(tile + TileDiffXY(1, 0));
|
if (eflags & BUILDING_2_TILES_X) DoClearTownHouseHelper(tile + TileDiffXY(1, 0));
|
||||||
|
@ -1423,6 +1428,7 @@ void ClearTownHouse(Town *t, TileIndex tile)
|
||||||
|
|
||||||
/** Rename a town (server-only).
|
/** Rename a town (server-only).
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 town ID to rename
|
* @param p1 town ID to rename
|
||||||
* @param p2 unused
|
* @param p2 unused
|
||||||
*/
|
*/
|
||||||
|
@ -1452,7 +1458,7 @@ int32 CmdRenameTown(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Called from GUI
|
/** Called from GUI */
|
||||||
void ExpandTown(Town *t)
|
void ExpandTown(Town *t)
|
||||||
{
|
{
|
||||||
int amount, n;
|
int amount, n;
|
||||||
|
@ -1555,16 +1561,16 @@ static void TownActionBuildStatue(Town* t)
|
||||||
TileIndex tile = t->xy;
|
TileIndex tile = t->xy;
|
||||||
|
|
||||||
if (CircularTileSearch(tile, 9, SearchTileForStatue, t->index))
|
if (CircularTileSearch(tile, 9, SearchTileForStatue, t->index))
|
||||||
SETBIT(t->statues, _current_player); ///< Once found and built, "inform" the Town
|
SETBIT(t->statues, _current_player); // Once found and built, "inform" the Town
|
||||||
}
|
}
|
||||||
|
|
||||||
static void TownActionFundBuildings(Town* t)
|
static void TownActionFundBuildings(Town* t)
|
||||||
{
|
{
|
||||||
// Build next tick
|
/* Build next tick */
|
||||||
t->grow_counter = 1;
|
t->grow_counter = 1;
|
||||||
// If we were not already growing
|
/* If we were not already growing */
|
||||||
SETBIT(t->flags12, TOWN_IS_FUNDED);
|
SETBIT(t->flags12, TOWN_IS_FUNDED);
|
||||||
// And grow for 3 months
|
/* And grow for 3 months */
|
||||||
t->fund_buildings_months = 3;
|
t->fund_buildings_months = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1581,18 +1587,18 @@ static void TownActionBribe(Town* t)
|
||||||
if (!RandomRange(15)) {
|
if (!RandomRange(15)) {
|
||||||
Station *st;
|
Station *st;
|
||||||
|
|
||||||
// set as unwanted for 6 months
|
/* set as unwanted for 6 months */
|
||||||
t->unwanted[_current_player] = 6;
|
t->unwanted[_current_player] = 6;
|
||||||
|
|
||||||
// set all close by station ratings to 0
|
/* set all close by station ratings to 0 */
|
||||||
FOR_ALL_STATIONS(st) {
|
FOR_ALL_STATIONS(st) {
|
||||||
if (st->town == t && st->owner == _current_player) {
|
if (st->town == t && st->owner == _current_player) {
|
||||||
for (CargoID i = 0; i < NUM_CARGO; i++) st->goods[i].rating = 0;
|
for (CargoID i = 0; i < NUM_CARGO; i++) st->goods[i].rating = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// only show errormessage to the executing player. All errors are handled command.c
|
/* only show errormessage to the executing player. All errors are handled command.c
|
||||||
// but this is special, because it can only 'fail' on a DC_EXEC
|
* but this is special, because it can only 'fail' on a DC_EXEC */
|
||||||
if (IsLocalPlayer()) ShowErrorMessage(STR_BRIBE_FAILED_2, STR_BRIBE_FAILED, 0, 0);
|
if (IsLocalPlayer()) ShowErrorMessage(STR_BRIBE_FAILED_2, STR_BRIBE_FAILED, 0, 0);
|
||||||
|
|
||||||
/* decrease by a lot!
|
/* decrease by a lot!
|
||||||
|
@ -1625,6 +1631,7 @@ extern uint GetMaskOfTownActions(int *nump, PlayerID pid, const Town *t);
|
||||||
* This performs an action such as advertising, building a statue, funding buildings,
|
* This performs an action such as advertising, building a statue, funding buildings,
|
||||||
* but also bribing the town-council
|
* but also bribing the town-council
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 town to do the action at
|
* @param p1 town to do the action at
|
||||||
* @param p2 action to perform, @see _town_action_proc for the list of available actions
|
* @param p2 action to perform, @see _town_action_proc for the list of available actions
|
||||||
*/
|
*/
|
||||||
|
@ -1658,7 +1665,7 @@ static void UpdateTownGrowRate(Town *t)
|
||||||
byte m;
|
byte m;
|
||||||
Player *p;
|
Player *p;
|
||||||
|
|
||||||
// Reset player ratings if they're low
|
/* Reset player ratings if they're low */
|
||||||
FOR_ALL_PLAYERS(p) {
|
FOR_ALL_PLAYERS(p) {
|
||||||
if (p->is_active && t->ratings[p->index] <= 200) {
|
if (p->is_active && t->ratings[p->index] <= 200) {
|
||||||
t->ratings[p->index] += 5;
|
t->ratings[p->index] += 5;
|
||||||
|
@ -1715,7 +1722,7 @@ static void UpdateTownGrowRate(Town *t)
|
||||||
|
|
||||||
static void UpdateTownAmounts(Town *t)
|
static void UpdateTownAmounts(Town *t)
|
||||||
{
|
{
|
||||||
// Using +1 here to prevent overflow and division by zero
|
/* Using +1 here to prevent overflow and division by zero */
|
||||||
t->pct_pass_transported = t->new_act_pass * 256 / (t->new_max_pass + 1);
|
t->pct_pass_transported = t->new_act_pass * 256 / (t->new_max_pass + 1);
|
||||||
|
|
||||||
t->max_pass = t->new_max_pass; t->new_max_pass = 0;
|
t->max_pass = t->new_max_pass; t->new_max_pass = 0;
|
||||||
|
@ -1723,7 +1730,7 @@ static void UpdateTownAmounts(Town *t)
|
||||||
t->act_food = t->new_act_food; t->new_act_food = 0;
|
t->act_food = t->new_act_food; t->new_act_food = 0;
|
||||||
t->act_water = t->new_act_water; t->new_act_water = 0;
|
t->act_water = t->new_act_water; t->new_act_water = 0;
|
||||||
|
|
||||||
// Using +1 here to prevent overflow and division by zero
|
/* Using +1 here to prevent overflow and division by zero */
|
||||||
t->pct_mail_transported = t->new_act_mail * 256 / (t->new_max_mail + 1);
|
t->pct_mail_transported = t->new_act_mail * 256 / (t->new_max_mail + 1);
|
||||||
t->max_mail = t->new_max_mail; t->new_max_mail = 0;
|
t->max_mail = t->new_max_mail; t->new_max_mail = 0;
|
||||||
t->act_mail = t->new_act_mail; t->new_act_mail = 0;
|
t->act_mail = t->new_act_mail; t->new_act_mail = 0;
|
||||||
|
@ -1793,7 +1800,7 @@ void ChangeTownRating(Town *t, int add, int max)
|
||||||
{
|
{
|
||||||
int rating;
|
int rating;
|
||||||
|
|
||||||
// if magic_bulldozer cheat is active, town doesn't penaltize for removing stuff
|
/* if magic_bulldozer cheat is active, town doesn't penaltize for removing stuff */
|
||||||
if (t == NULL ||
|
if (t == NULL ||
|
||||||
!IsValidPlayer(_current_player) ||
|
!IsValidPlayer(_current_player) ||
|
||||||
(_cheats.magic_bulldozer.value && add < 0)) {
|
(_cheats.magic_bulldozer.value && add < 0)) {
|
||||||
|
@ -1820,17 +1827,17 @@ void ChangeTownRating(Town *t, int add, int max)
|
||||||
|
|
||||||
/* penalty for removing town-owned stuff */
|
/* penalty for removing town-owned stuff */
|
||||||
static const int _default_rating_settings [3][3] = {
|
static const int _default_rating_settings [3][3] = {
|
||||||
// ROAD_REMOVE, TUNNELBRIDGE_REMOVE, INDUSTRY_REMOVE
|
/* ROAD_REMOVE, TUNNELBRIDGE_REMOVE, INDUSTRY_REMOVE */
|
||||||
{ 0, 128, 384}, // Permissive
|
{ 0, 128, 384}, ///< Permissive
|
||||||
{ 48, 192, 480}, // Neutral
|
{ 48, 192, 480}, ///< Neutral
|
||||||
{ 96, 384, 768}, // Hostile
|
{ 96, 384, 768}, ///< Hostile
|
||||||
};
|
};
|
||||||
|
|
||||||
bool CheckforTownRating(uint32 flags, Town *t, byte type)
|
bool CheckforTownRating(uint32 flags, Town *t, byte type)
|
||||||
{
|
{
|
||||||
int modemod;
|
int modemod;
|
||||||
|
|
||||||
// if magic_bulldozer cheat is active, town doesn't restrict your destructive actions
|
/* if magic_bulldozer cheat is active, town doesn't restrict your destructive actions */
|
||||||
if (t == NULL || !IsValidPlayer(_current_player) || _cheats.magic_bulldozer.value)
|
if (t == NULL || !IsValidPlayer(_current_player) || _cheats.magic_bulldozer.value)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
|
@ -1900,7 +1907,7 @@ extern const TileTypeProcs _tile_type_town_procs = {
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
// Save and load of towns.
|
/** Save and load of towns. */
|
||||||
static const SaveLoad _town_desc[] = {
|
static const SaveLoad _town_desc[] = {
|
||||||
SLE_CONDVAR(Town, xy, SLE_FILE_U16 | SLE_VAR_U32, 0, 5),
|
SLE_CONDVAR(Town, xy, SLE_FILE_U16 | SLE_VAR_U32, 0, 5),
|
||||||
SLE_CONDVAR(Town, xy, SLE_UINT32, 6, SL_MAX_VERSION),
|
SLE_CONDVAR(Town, xy, SLE_UINT32, 6, SL_MAX_VERSION),
|
||||||
|
@ -1916,12 +1923,12 @@ static const SaveLoad _town_desc[] = {
|
||||||
SLE_VAR(Town, flags12, SLE_UINT8),
|
SLE_VAR(Town, flags12, SLE_UINT8),
|
||||||
SLE_VAR(Town, statues, SLE_UINT8),
|
SLE_VAR(Town, statues, SLE_UINT8),
|
||||||
|
|
||||||
// sort_index_obsolete was stored here in savegame format 0 - 1
|
/* sort_index_obsolete was stored here in savegame format 0 - 1 */
|
||||||
SLE_CONDNULL(1, 0, 1),
|
SLE_CONDNULL(1, 0, 1),
|
||||||
|
|
||||||
SLE_VAR(Town, have_ratings, SLE_UINT8),
|
SLE_VAR(Town, have_ratings, SLE_UINT8),
|
||||||
SLE_ARR(Town, ratings, SLE_INT16, 8),
|
SLE_ARR(Town, ratings, SLE_INT16, 8),
|
||||||
// failed bribe attempts are stored since savegame format 4
|
/* failed bribe attempts are stored since savegame format 4 */
|
||||||
SLE_CONDARR(Town, unwanted, SLE_INT8, 8, 4,SL_MAX_VERSION),
|
SLE_CONDARR(Town, unwanted, SLE_INT8, 8, 4,SL_MAX_VERSION),
|
||||||
|
|
||||||
SLE_CONDVAR(Town, max_pass, SLE_FILE_U16 | SLE_VAR_U32, 0, 8),
|
SLE_CONDVAR(Town, max_pass, SLE_FILE_U16 | SLE_VAR_U32, 0, 8),
|
||||||
|
@ -1958,7 +1965,7 @@ static const SaveLoad _town_desc[] = {
|
||||||
|
|
||||||
SLE_VAR(Town, exclusivity, SLE_UINT8),
|
SLE_VAR(Town, exclusivity, SLE_UINT8),
|
||||||
SLE_VAR(Town, exclusive_counter, SLE_UINT8),
|
SLE_VAR(Town, exclusive_counter, SLE_UINT8),
|
||||||
// reserve extra space in savegame here. (currently 30 bytes)
|
/* reserve extra space in savegame here. (currently 30 bytes) */
|
||||||
SLE_CONDNULL(30, 2, SL_MAX_VERSION),
|
SLE_CONDNULL(30, 2, SL_MAX_VERSION),
|
||||||
|
|
||||||
SLE_END()
|
SLE_END()
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file town_gui.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "debug.h"
|
#include "debug.h"
|
||||||
|
@ -32,9 +34,9 @@ static const Widget _town_authority_widgets[] = {
|
||||||
extern const byte _town_action_costs[8];
|
extern const byte _town_action_costs[8];
|
||||||
|
|
||||||
/** Get a list of available actions to do at a town.
|
/** Get a list of available actions to do at a town.
|
||||||
* @param *nump if not NULL add put the number of available actions in it
|
* @param nump if not NULL add put the number of available actions in it
|
||||||
* @param pid the player that is querying the town
|
* @param pid the player that is querying the town
|
||||||
* @param *t the town that is queried
|
* @param t the town that is queried
|
||||||
* @return bitmasked value of enabled actions
|
* @return bitmasked value of enabled actions
|
||||||
*/
|
*/
|
||||||
uint GetMaskOfTownActions(int *nump, PlayerID pid, const Town *t)
|
uint GetMaskOfTownActions(int *nump, PlayerID pid, const Town *t)
|
||||||
|
@ -47,9 +49,9 @@ uint GetMaskOfTownActions(int *nump, PlayerID pid, const Town *t)
|
||||||
if (pid != PLAYER_SPECTATOR) {
|
if (pid != PLAYER_SPECTATOR) {
|
||||||
uint i;
|
uint i;
|
||||||
|
|
||||||
// bribe option enabled?
|
/* bribe option enabled? */
|
||||||
if (_patches.bribe) {
|
if (_patches.bribe) {
|
||||||
// if unwanted, disable everything.
|
/* if unwanted, disable everything. */
|
||||||
if (t->unwanted[pid]) {
|
if (t->unwanted[pid]) {
|
||||||
avail_buttons = 0;
|
avail_buttons = 0;
|
||||||
} else if (t->ratings[pid] < RATING_BRIBE_MAXIMUM) {
|
} else if (t->ratings[pid] < RATING_BRIBE_MAXIMUM) {
|
||||||
|
@ -57,7 +59,7 @@ uint GetMaskOfTownActions(int *nump, PlayerID pid, const Town *t)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Things worth more than this are not shown
|
/* Things worth more than this are not shown */
|
||||||
avail = GetPlayer(pid)->player_money + _price.station_value * 200;
|
avail = GetPlayer(pid)->player_money + _price.station_value * 200;
|
||||||
ref = _price.build_industry >> 8;
|
ref = _price.build_industry >> 8;
|
||||||
|
|
||||||
|
@ -119,7 +121,7 @@ static void TownAuthorityWndProc(Window *w, WindowEvent *e)
|
||||||
|
|
||||||
DrawString(2, 15, STR_2023_TRANSPORT_COMPANY_RATINGS, 0);
|
DrawString(2, 15, STR_2023_TRANSPORT_COMPANY_RATINGS, 0);
|
||||||
|
|
||||||
// Draw list of players
|
/* Draw list of players */
|
||||||
y = 25;
|
y = 25;
|
||||||
FOR_ALL_PLAYERS(p) {
|
FOR_ALL_PLAYERS(p) {
|
||||||
if (p->is_active && (HASBIT(t->have_ratings, p->index) || t->exclusivity == p->index)) {
|
if (p->is_active && (HASBIT(t->have_ratings, p->index) || t->exclusivity == p->index)) {
|
||||||
|
@ -150,7 +152,7 @@ static void TownAuthorityWndProc(Window *w, WindowEvent *e)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Draw actions list
|
/* Draw actions list */
|
||||||
{
|
{
|
||||||
int y = 107, i;
|
int y = 107, i;
|
||||||
int pos = w->vscroll.pos;
|
int pos = w->vscroll.pos;
|
||||||
|
@ -234,7 +236,7 @@ static void TownViewWndProc(Window *w, WindowEvent *e)
|
||||||
|
|
||||||
switch (e->event) {
|
switch (e->event) {
|
||||||
case WE_PAINT:
|
case WE_PAINT:
|
||||||
// disable renaming town in network games if you are not the server
|
/* disable renaming town in network games if you are not the server */
|
||||||
SetWindowWidgetDisabledState(w, 8, _networking && !_network_server);
|
SetWindowWidgetDisabledState(w, 8, _networking && !_network_server);
|
||||||
|
|
||||||
SetDParam(0, t->index);
|
SetDParam(0, t->index);
|
||||||
|
@ -365,7 +367,7 @@ static const Widget _town_directory_widgets[] = {
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
// used to get a sorted list of the towns
|
/* used to get a sorted list of the towns */
|
||||||
static uint _num_town_sort;
|
static uint _num_town_sort;
|
||||||
|
|
||||||
static char _bufcache[64];
|
static char _bufcache[64];
|
||||||
|
|
|
@ -127,7 +127,7 @@ static inline byte GetLiftPosition(TileIndex t)
|
||||||
/**
|
/**
|
||||||
* Set the position of the lift on this animated house
|
* Set the position of the lift on this animated house
|
||||||
* @param t the tile
|
* @param t the tile
|
||||||
* @param pos from 0 to 36
|
* @param pos position, from 0 to 36
|
||||||
*/
|
*/
|
||||||
static inline void SetLiftPosition(TileIndex t, byte pos)
|
static inline void SetLiftPosition(TileIndex t, byte pos)
|
||||||
{
|
{
|
||||||
|
|
14
src/train.h
14
src/train.h
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file train.h */
|
||||||
|
|
||||||
#ifndef TRAIN_H
|
#ifndef TRAIN_H
|
||||||
#define TRAIN_H
|
#define TRAIN_H
|
||||||
|
|
||||||
|
@ -14,12 +16,12 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
enum TrainSubtype {
|
enum TrainSubtype {
|
||||||
Train_Front = 0, // Leading engine of a train
|
Train_Front = 0, ///< Leading engine of a train
|
||||||
Train_Articulated_Part = 1, // Articulated part of an engine
|
Train_Articulated_Part = 1, ///< Articulated part of an engine
|
||||||
Train_Wagon = 2, // Wagon
|
Train_Wagon = 2, ///< Wagon
|
||||||
Train_Engine = 3, // Engine, that can be front engines, but might be placed behind another engine
|
Train_Engine = 3, ///< Engine, that can be front engines, but might be placed behind another engine
|
||||||
Train_Free_Wagon = 4, // First in a wagon chain (in depot)
|
Train_Free_Wagon = 4, ///< First in a wagon chain (in depot)
|
||||||
Train_Multiheaded = 5, // Engine is a multiheaded
|
Train_Multiheaded = 5, ///< Engine is a multiheaded
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file train_cmd.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "bridge_map.h"
|
#include "bridge_map.h"
|
||||||
|
@ -105,24 +107,24 @@ static void TrainCargoChanged(Vehicle* v)
|
||||||
for (Vehicle *u = v; u != NULL; u = u->next) {
|
for (Vehicle *u = v; u != NULL; u = u->next) {
|
||||||
uint32 vweight = GetCargo(u->cargo_type)->weight * u->cargo_count * FreightWagonMult(u->cargo_type) / 16;
|
uint32 vweight = GetCargo(u->cargo_type)->weight * u->cargo_count * FreightWagonMult(u->cargo_type) / 16;
|
||||||
|
|
||||||
// Vehicle weight is not added for articulated parts.
|
/* Vehicle weight is not added for articulated parts. */
|
||||||
if (!IsArticulatedPart(u)) {
|
if (!IsArticulatedPart(u)) {
|
||||||
// vehicle weight is the sum of the weight of the vehicle and the weight of its cargo
|
/* vehicle weight is the sum of the weight of the vehicle and the weight of its cargo */
|
||||||
vweight += RailVehInfo(u->engine_type)->weight;
|
vweight += RailVehInfo(u->engine_type)->weight;
|
||||||
|
|
||||||
// powered wagons have extra weight added
|
/* powered wagons have extra weight added */
|
||||||
if (HASBIT(u->u.rail.flags, VRF_POWEREDWAGON))
|
if (HASBIT(u->u.rail.flags, VRF_POWEREDWAGON))
|
||||||
vweight += RailVehInfo(u->u.rail.first_engine)->pow_wag_weight;
|
vweight += RailVehInfo(u->u.rail.first_engine)->pow_wag_weight;
|
||||||
}
|
}
|
||||||
|
|
||||||
// consist weight is the sum of the weight of all vehicles in the consist
|
/* consist weight is the sum of the weight of all vehicles in the consist */
|
||||||
weight += vweight;
|
weight += vweight;
|
||||||
|
|
||||||
// store vehicle weight in cache
|
/* store vehicle weight in cache */
|
||||||
u->u.rail.cached_veh_weight = vweight;
|
u->u.rail.cached_veh_weight = vweight;
|
||||||
}
|
}
|
||||||
|
|
||||||
// store consist weight in cache
|
/* store consist weight in cache */
|
||||||
v->u.rail.cached_weight = weight;
|
v->u.rail.cached_weight = weight;
|
||||||
|
|
||||||
/* Now update train power (tractive effort is dependent on weight) */
|
/* Now update train power (tractive effort is dependent on weight) */
|
||||||
|
@ -151,10 +153,10 @@ void TrainConsistChanged(Vehicle* v)
|
||||||
for (Vehicle *u = v; u != NULL; u = u->next) {
|
for (Vehicle *u = v; u != NULL; u = u->next) {
|
||||||
const RailVehicleInfo *rvi_u = RailVehInfo(u->engine_type);
|
const RailVehicleInfo *rvi_u = RailVehInfo(u->engine_type);
|
||||||
|
|
||||||
// Update the v->first cache. This is faster than having to brute force it later.
|
/* Update the v->first cache. This is faster than having to brute force it later. */
|
||||||
if (u->first == NULL) u->first = v;
|
if (u->first == NULL) u->first = v;
|
||||||
|
|
||||||
// update the 'first engine'
|
/* update the 'first engine' */
|
||||||
u->u.rail.first_engine = v == u ? INVALID_ENGINE : first_engine;
|
u->u.rail.first_engine = v == u ? INVALID_ENGINE : first_engine;
|
||||||
u->u.rail.railtype = rvi_u->railtype;
|
u->u.rail.railtype = rvi_u->railtype;
|
||||||
|
|
||||||
|
@ -164,13 +166,13 @@ void TrainConsistChanged(Vehicle* v)
|
||||||
u->u.rail.cached_vis_effect = rvi_u->visual_effect;
|
u->u.rail.cached_vis_effect = rvi_u->visual_effect;
|
||||||
} else {
|
} else {
|
||||||
if (IsTrainWagon(u) || IsArticulatedPart(u)) {
|
if (IsTrainWagon(u) || IsArticulatedPart(u)) {
|
||||||
// Wagons and articulated parts have no effect by default
|
/* Wagons and articulated parts have no effect by default */
|
||||||
u->u.rail.cached_vis_effect = 0x40;
|
u->u.rail.cached_vis_effect = 0x40;
|
||||||
} else if (rvi_u->engclass == 0) {
|
} else if (rvi_u->engclass == 0) {
|
||||||
// Steam is offset by -4 units
|
/* Steam is offset by -4 units */
|
||||||
u->u.rail.cached_vis_effect = 4;
|
u->u.rail.cached_vis_effect = 4;
|
||||||
} else {
|
} else {
|
||||||
// Diesel fumes and sparks come from the centre
|
/* Diesel fumes and sparks come from the centre */
|
||||||
u->u.rail.cached_vis_effect = 8;
|
u->u.rail.cached_vis_effect = 8;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -204,13 +206,13 @@ void TrainConsistChanged(Vehicle* v)
|
||||||
u->u.rail.compatible_railtypes |= (1 << RAILTYPE_RAIL);
|
u->u.rail.compatible_railtypes |= (1 << RAILTYPE_RAIL);
|
||||||
}
|
}
|
||||||
|
|
||||||
// max speed is the minimum of the speed limits of all vehicles in the consist
|
/* max speed is the minimum of the speed limits of all vehicles in the consist */
|
||||||
if ((rvi_u->railveh_type != RAILVEH_WAGON || _patches.wagon_speed_limits) &&
|
if ((rvi_u->railveh_type != RAILVEH_WAGON || _patches.wagon_speed_limits) &&
|
||||||
rvi_u->max_speed != 0 && !UsesWagonOverride(u))
|
rvi_u->max_speed != 0 && !UsesWagonOverride(u))
|
||||||
max_speed = min(rvi_u->max_speed, max_speed);
|
max_speed = min(rvi_u->max_speed, max_speed);
|
||||||
}
|
}
|
||||||
|
|
||||||
// check the vehicle length (callback)
|
/* check the vehicle length (callback) */
|
||||||
uint16 veh_len = CALLBACK_FAILED;
|
uint16 veh_len = CALLBACK_FAILED;
|
||||||
if (HASBIT(EngInfo(u->engine_type)->callbackmask, CBM_VEHICLE_LENGTH)) {
|
if (HASBIT(EngInfo(u->engine_type)->callbackmask, CBM_VEHICLE_LENGTH)) {
|
||||||
veh_len = GetVehicleCallback(CBID_TRAIN_VEHICLE_LENGTH, 0, 0, u->engine_type, u);
|
veh_len = GetVehicleCallback(CBID_TRAIN_VEHICLE_LENGTH, 0, 0, u->engine_type, u);
|
||||||
|
@ -221,10 +223,10 @@ void TrainConsistChanged(Vehicle* v)
|
||||||
v->u.rail.cached_total_length += u->u.rail.cached_veh_length;
|
v->u.rail.cached_total_length += u->u.rail.cached_veh_length;
|
||||||
}
|
}
|
||||||
|
|
||||||
// store consist weight/max speed in cache
|
/* store consist weight/max speed in cache */
|
||||||
v->u.rail.cached_max_speed = max_speed;
|
v->u.rail.cached_max_speed = max_speed;
|
||||||
|
|
||||||
// recalculate cached weights and power too (we do this *after* the rest, so it is known which wagons are powered and need extra weight added)
|
/* recalculate cached weights and power too (we do this *after* the rest, so it is known which wagons are powered and need extra weight added) */
|
||||||
TrainCargoChanged(v);
|
TrainCargoChanged(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -263,8 +265,8 @@ static bool TrainShouldStop(const Vehicle* v, TileIndex tile)
|
||||||
StationID sid = GetStationIndex(tile);
|
StationID sid = GetStationIndex(tile);
|
||||||
|
|
||||||
assert(v->type == VEH_TRAIN);
|
assert(v->type == VEH_TRAIN);
|
||||||
//When does a train drive through a station
|
/* When does a train drive through a station
|
||||||
//first we deal with the "new nonstop handling"
|
* first we deal with the "new nonstop handling" */
|
||||||
if (_patches.new_nonstop && o->flags & OF_NON_STOP && sid == o->dest) {
|
if (_patches.new_nonstop && o->flags & OF_NON_STOP && sid == o->dest) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -278,14 +280,14 @@ static bool TrainShouldStop(const Vehicle* v, TileIndex tile)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
//new acceleration
|
/** new acceleration*/
|
||||||
static int GetTrainAcceleration(Vehicle *v, bool mode)
|
static int GetTrainAcceleration(Vehicle *v, bool mode)
|
||||||
{
|
{
|
||||||
int max_speed = 2000;
|
int max_speed = 2000;
|
||||||
int speed = v->cur_speed * 10 / 16; //[mph]
|
int speed = v->cur_speed * 10 / 16; //[mph]
|
||||||
int curvecount[2] = {0, 0};
|
int curvecount[2] = {0, 0};
|
||||||
|
|
||||||
//first find the curve speed limit
|
/*first find the curve speed limit */
|
||||||
int numcurve = 0;
|
int numcurve = 0;
|
||||||
int sum = 0;
|
int sum = 0;
|
||||||
int pos = 0;
|
int pos = 0;
|
||||||
|
@ -309,7 +311,7 @@ static int GetTrainAcceleration(Vehicle *v, bool mode)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//if we have a 90 degree turn, fix the speed limit to 60
|
/*if we have a 90 degree turn, fix the speed limit to 60 */
|
||||||
if (_curve_neighbours90[dir][0] == ndir ||
|
if (_curve_neighbours90[dir][0] == ndir ||
|
||||||
_curve_neighbours90[dir][1] == ndir) {
|
_curve_neighbours90[dir][1] == ndir) {
|
||||||
max_speed = 61;
|
max_speed = 61;
|
||||||
|
@ -402,7 +404,7 @@ static int GetTrainAcceleration(Vehicle *v, bool mode)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
//"kickoff" acceleration
|
/* "kickoff" acceleration */
|
||||||
force = (mode == AM_ACCEL && v->u.rail.railtype != RAILTYPE_MAGLEV) ? min(max_te, power) : power;
|
force = (mode == AM_ACCEL && v->u.rail.railtype != RAILTYPE_MAGLEV) ? min(max_te, power) : power;
|
||||||
force = max(force, (mass * 8) + resistance);
|
force = max(force, (mass * 8) + resistance);
|
||||||
}
|
}
|
||||||
|
@ -521,7 +523,7 @@ static void AddArticulatedParts(Vehicle **vl)
|
||||||
bool flip_image = HASBIT(callback, 7);
|
bool flip_image = HASBIT(callback, 7);
|
||||||
const RailVehicleInfo *rvi_artic = RailVehInfo(engine_type);
|
const RailVehicleInfo *rvi_artic = RailVehInfo(engine_type);
|
||||||
|
|
||||||
// get common values from first engine
|
/* get common values from first engine */
|
||||||
u->direction = v->direction;
|
u->direction = v->direction;
|
||||||
u->owner = v->owner;
|
u->owner = v->owner;
|
||||||
u->tile = v->tile;
|
u->tile = v->tile;
|
||||||
|
@ -535,7 +537,7 @@ static void AddArticulatedParts(Vehicle **vl)
|
||||||
u->vehstatus = v->vehstatus & ~VS_STOPPED;
|
u->vehstatus = v->vehstatus & ~VS_STOPPED;
|
||||||
u->u.rail.first_engine = v->engine_type;
|
u->u.rail.first_engine = v->engine_type;
|
||||||
|
|
||||||
// get more settings from rail vehicle info
|
/* get more settings from rail vehicle info */
|
||||||
u->spritenum = rvi_artic->image_index;
|
u->spritenum = rvi_artic->image_index;
|
||||||
if (flip_image) u->spritenum++;
|
if (flip_image) u->spritenum++;
|
||||||
u->cargo_type = rvi_artic->cargo_type;
|
u->cargo_type = rvi_artic->cargo_type;
|
||||||
|
@ -645,7 +647,7 @@ static int32 CmdBuildRailWagon(EngineID engine, TileIndex tile, uint32 flags)
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Move all free vehicles in the depot to the train
|
/** Move all free vehicles in the depot to the train */
|
||||||
static void NormalizeTrainVehInDepot(const Vehicle* u)
|
static void NormalizeTrainVehInDepot(const Vehicle* u)
|
||||||
{
|
{
|
||||||
const Vehicle* v;
|
const Vehicle* v;
|
||||||
|
@ -697,6 +699,7 @@ static void AddRearEngineToMultiheadedTrain(Vehicle* v, Vehicle* u, bool buildin
|
||||||
|
|
||||||
/** Build a railroad vehicle.
|
/** Build a railroad vehicle.
|
||||||
* @param tile tile of the depot where rail-vehicle is built
|
* @param tile tile of the depot where rail-vehicle is built
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 engine type id
|
* @param p1 engine type id
|
||||||
* @param p2 bit 0 when set, the train will get number 0, otherwise it will get a free number
|
* @param p2 bit 0 when set, the train will get number 0, otherwise it will get a free number
|
||||||
* bit 1 prevents any free cars from being added to the train
|
* bit 1 prevents any free cars from being added to the train
|
||||||
|
@ -874,7 +877,7 @@ inline bool CheckTrainIsInsideDepot(const Vehicle *v)
|
||||||
*/
|
*/
|
||||||
static Vehicle *UnlinkWagon(Vehicle *v, Vehicle *first)
|
static Vehicle *UnlinkWagon(Vehicle *v, Vehicle *first)
|
||||||
{
|
{
|
||||||
// unlinking the first vehicle of the chain?
|
/* unlinking the first vehicle of the chain? */
|
||||||
if (v == first) {
|
if (v == first) {
|
||||||
v = GetNextVehicle(v);
|
v = GetNextVehicle(v);
|
||||||
if (v == NULL) return NULL;
|
if (v == NULL) return NULL;
|
||||||
|
@ -898,7 +901,7 @@ static Vehicle *FindGoodVehiclePos(const Vehicle *src)
|
||||||
|
|
||||||
FOR_ALL_VEHICLES(dst) {
|
FOR_ALL_VEHICLES(dst) {
|
||||||
if (dst->type == VEH_TRAIN && IsFreeWagon(dst) && dst->tile == tile) {
|
if (dst->type == VEH_TRAIN && IsFreeWagon(dst) && dst->tile == tile) {
|
||||||
// check so all vehicles in the line have the same engine.
|
/* check so all vehicles in the line have the same engine. */
|
||||||
Vehicle *v = dst;
|
Vehicle *v = dst;
|
||||||
|
|
||||||
while (v->engine_type == eng) {
|
while (v->engine_type == eng) {
|
||||||
|
@ -950,6 +953,7 @@ static void NormaliseTrainConsist(Vehicle *v)
|
||||||
|
|
||||||
/** Move a rail vehicle around inside the depot.
|
/** Move a rail vehicle around inside the depot.
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 various bitstuffed elements
|
* @param p1 various bitstuffed elements
|
||||||
* - p1 (bit 0 - 15) source vehicle index
|
* - p1 (bit 0 - 15) source vehicle index
|
||||||
* - p1 (bit 16 - 31) what wagon to put the source wagon AFTER, XXX - INVALID_VEHICLE to make a new line
|
* - p1 (bit 16 - 31) what wagon to put the source wagon AFTER, XXX - INVALID_VEHICLE to make a new line
|
||||||
|
@ -966,7 +970,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
if (src->type != VEH_TRAIN || !CheckOwnership(src->owner)) return CMD_ERROR;
|
if (src->type != VEH_TRAIN || !CheckOwnership(src->owner)) return CMD_ERROR;
|
||||||
|
|
||||||
// if nothing is selected as destination, try and find a matching vehicle to drag to.
|
/* if nothing is selected as destination, try and find a matching vehicle to drag to. */
|
||||||
Vehicle *dst;
|
Vehicle *dst;
|
||||||
if (d == INVALID_VEHICLE) {
|
if (d == INVALID_VEHICLE) {
|
||||||
dst = IsTrainEngine(src) ? NULL : FindGoodVehiclePos(src);
|
dst = IsTrainEngine(src) ? NULL : FindGoodVehiclePos(src);
|
||||||
|
@ -976,13 +980,13 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
if (dst->type != VEH_TRAIN || !CheckOwnership(dst->owner)) return CMD_ERROR;
|
if (dst->type != VEH_TRAIN || !CheckOwnership(dst->owner)) return CMD_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
// if an articulated part is being handled, deal with its parent vehicle
|
/* if an articulated part is being handled, deal with its parent vehicle */
|
||||||
while (IsArticulatedPart(src)) src = GetPrevVehicleInChain(src);
|
while (IsArticulatedPart(src)) src = GetPrevVehicleInChain(src);
|
||||||
if (dst != NULL) {
|
if (dst != NULL) {
|
||||||
while (IsArticulatedPart(dst)) dst = GetPrevVehicleInChain(dst);
|
while (IsArticulatedPart(dst)) dst = GetPrevVehicleInChain(dst);
|
||||||
}
|
}
|
||||||
|
|
||||||
// don't move the same vehicle..
|
/* don't move the same vehicle.. */
|
||||||
if (src == dst) return 0;
|
if (src == dst) return 0;
|
||||||
|
|
||||||
/* locate the head of the two chains */
|
/* locate the head of the two chains */
|
||||||
|
@ -991,7 +995,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
if (dst != NULL) {
|
if (dst != NULL) {
|
||||||
dst_head = GetFirstVehicleInChain(dst);
|
dst_head = GetFirstVehicleInChain(dst);
|
||||||
if (dst_head->tile != src_head->tile) return CMD_ERROR;
|
if (dst_head->tile != src_head->tile) return CMD_ERROR;
|
||||||
// Now deal with articulated part of destination wagon
|
/* Now deal with articulated part of destination wagon */
|
||||||
dst = GetLastEnginePart(dst);
|
dst = GetLastEnginePart(dst);
|
||||||
} else {
|
} else {
|
||||||
dst_head = NULL;
|
dst_head = NULL;
|
||||||
|
@ -1004,7 +1008,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
dst = GetPrevVehicleInChain(dst);
|
dst = GetPrevVehicleInChain(dst);
|
||||||
/* Now if the vehicle we want to link to is the vehicle itself, drop out */
|
/* Now if the vehicle we want to link to is the vehicle itself, drop out */
|
||||||
if (dst == src) return CMD_ERROR;
|
if (dst == src) return CMD_ERROR;
|
||||||
// if dst is NULL, it means that dst got a rear multiheaded engine as first engine. We can't use that
|
/* if dst is NULL, it means that dst got a rear multiheaded engine as first engine. We can't use that */
|
||||||
if (dst == NULL) return CMD_ERROR;
|
if (dst == NULL) return CMD_ERROR;
|
||||||
} else {
|
} else {
|
||||||
/* there are more units on this train, so we will add the wagon after the next one*/
|
/* there are more units on this train, so we will add the wagon after the next one*/
|
||||||
|
@ -1032,51 +1036,51 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
if (IsMultiheaded(src) && !IsTrainEngine(src)) return_cmd_error(STR_REAR_ENGINE_FOLLOW_FRONT_ERROR);
|
if (IsMultiheaded(src) && !IsTrainEngine(src)) return_cmd_error(STR_REAR_ENGINE_FOLLOW_FRONT_ERROR);
|
||||||
|
|
||||||
// when moving all wagons, we can't have the same src_head and dst_head
|
/* when moving all wagons, we can't have the same src_head and dst_head */
|
||||||
if (HASBIT(p2, 0) && src_head == dst_head) return 0;
|
if (HASBIT(p2, 0) && src_head == dst_head) return 0;
|
||||||
|
|
||||||
{
|
{
|
||||||
int max_len = _patches.mammoth_trains ? 100 : 9;
|
int max_len = _patches.mammoth_trains ? 100 : 9;
|
||||||
|
|
||||||
// check if all vehicles in the source train are stopped inside a depot.
|
/* check if all vehicles in the source train are stopped inside a depot. */
|
||||||
int src_len = CheckTrainStoppedInDepot(src_head);
|
int src_len = CheckTrainStoppedInDepot(src_head);
|
||||||
if (src_len < 0) return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
if (src_len < 0) return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
||||||
|
|
||||||
// check the destination row if the source and destination aren't the same.
|
/* check the destination row if the source and destination aren't the same. */
|
||||||
if (src_head != dst_head) {
|
if (src_head != dst_head) {
|
||||||
int dst_len = 0;
|
int dst_len = 0;
|
||||||
|
|
||||||
if (dst_head != NULL) {
|
if (dst_head != NULL) {
|
||||||
// check if all vehicles in the dest train are stopped.
|
/* check if all vehicles in the dest train are stopped. */
|
||||||
dst_len = CheckTrainStoppedInDepot(dst_head);
|
dst_len = CheckTrainStoppedInDepot(dst_head);
|
||||||
if (dst_len < 0) return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
if (dst_len < 0) return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
||||||
}
|
}
|
||||||
|
|
||||||
// We are moving between rows, so only count the wagons from the source
|
/* We are moving between rows, so only count the wagons from the source
|
||||||
// row that are being moved.
|
* row that are being moved. */
|
||||||
if (HASBIT(p2, 0)) {
|
if (HASBIT(p2, 0)) {
|
||||||
const Vehicle *u;
|
const Vehicle *u;
|
||||||
for (u = src_head; u != src && u != NULL; u = GetNextVehicle(u))
|
for (u = src_head; u != src && u != NULL; u = GetNextVehicle(u))
|
||||||
src_len--;
|
src_len--;
|
||||||
} else {
|
} else {
|
||||||
// If moving only one vehicle, just count that.
|
/* If moving only one vehicle, just count that. */
|
||||||
src_len = 1;
|
src_len = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (src_len + dst_len > max_len) {
|
if (src_len + dst_len > max_len) {
|
||||||
// Abort if we're adding too many wagons to a train.
|
/* Abort if we're adding too many wagons to a train. */
|
||||||
if (dst_head != NULL && IsFrontEngine(dst_head)) return_cmd_error(STR_8819_TRAIN_TOO_LONG);
|
if (dst_head != NULL && IsFrontEngine(dst_head)) return_cmd_error(STR_8819_TRAIN_TOO_LONG);
|
||||||
// Abort if we're making a train on a new row.
|
/* Abort if we're making a train on a new row. */
|
||||||
if (dst_head == NULL && IsTrainEngine(src)) return_cmd_error(STR_8819_TRAIN_TOO_LONG);
|
if (dst_head == NULL && IsTrainEngine(src)) return_cmd_error(STR_8819_TRAIN_TOO_LONG);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// Abort if we're creating a new train on an existing row.
|
/* Abort if we're creating a new train on an existing row. */
|
||||||
if (src_len > max_len && src == src_head && IsTrainEngine(GetNextVehicle(src_head)))
|
if (src_len > max_len && src == src_head && IsTrainEngine(GetNextVehicle(src_head)))
|
||||||
return_cmd_error(STR_8819_TRAIN_TOO_LONG);
|
return_cmd_error(STR_8819_TRAIN_TOO_LONG);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// moving a loco to a new line?, then we need to assign a unitnumber.
|
/* moving a loco to a new line?, then we need to assign a unitnumber. */
|
||||||
if (dst == NULL && !IsFrontEngine(src) && IsTrainEngine(src)) {
|
if (dst == NULL && !IsFrontEngine(src) && IsTrainEngine(src)) {
|
||||||
UnitID unit_num = GetFreeUnitNumber(VEH_TRAIN);
|
UnitID unit_num = GetFreeUnitNumber(VEH_TRAIN);
|
||||||
if (unit_num > _patches.max_trains)
|
if (unit_num > _patches.max_trains)
|
||||||
|
@ -1104,7 +1108,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
for (Vehicle *u = dst_head; u != NULL; u = u->next) u->first = NULL;
|
for (Vehicle *u = dst_head; u != NULL; u = u->next) u->first = NULL;
|
||||||
|
|
||||||
if (HASBIT(p2, 0)) {
|
if (HASBIT(p2, 0)) {
|
||||||
// unlink ALL wagons
|
/* unlink ALL wagons */
|
||||||
if (src != src_head) {
|
if (src != src_head) {
|
||||||
Vehicle *v = src_head;
|
Vehicle *v = src_head;
|
||||||
while (GetNextVehicle(v) != src) v = GetNextVehicle(v);
|
while (GetNextVehicle(v) != src) v = GetNextVehicle(v);
|
||||||
|
@ -1114,9 +1118,9 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
src_head = NULL;
|
src_head = NULL;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// if moving within the same chain, dont use dst_head as it may get invalidated
|
/* if moving within the same chain, dont use dst_head as it may get invalidated */
|
||||||
if (src_head == dst_head) dst_head = NULL;
|
if (src_head == dst_head) dst_head = NULL;
|
||||||
// unlink single wagon from linked list
|
/* unlink single wagon from linked list */
|
||||||
src_head = UnlinkWagon(src, src_head);
|
src_head = UnlinkWagon(src, src_head);
|
||||||
GetLastEnginePart(src)->next = NULL;
|
GetLastEnginePart(src)->next = NULL;
|
||||||
}
|
}
|
||||||
|
@ -1125,10 +1129,10 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
/* We make a new line in the depot, so we know already that we invalidate the window data */
|
/* We make a new line in the depot, so we know already that we invalidate the window data */
|
||||||
InvalidateWindowData(WC_VEHICLE_DEPOT, src->tile);
|
InvalidateWindowData(WC_VEHICLE_DEPOT, src->tile);
|
||||||
|
|
||||||
// move the train to an empty line. for locomotives, we set the type to TS_Front. for wagons, 4.
|
/* move the train to an empty line. for locomotives, we set the type to TS_Front. for wagons, 4. */
|
||||||
if (IsTrainEngine(src)) {
|
if (IsTrainEngine(src)) {
|
||||||
if (!IsFrontEngine(src)) {
|
if (!IsFrontEngine(src)) {
|
||||||
// setting the type to 0 also involves setting up the orders field.
|
/* setting the type to 0 also involves setting up the orders field. */
|
||||||
SetFrontEngine(src);
|
SetFrontEngine(src);
|
||||||
assert(src->orders == NULL);
|
assert(src->orders == NULL);
|
||||||
src->num_orders = 0;
|
src->num_orders = 0;
|
||||||
|
@ -1139,7 +1143,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
dst_head = src;
|
dst_head = src;
|
||||||
} else {
|
} else {
|
||||||
if (IsFrontEngine(src)) {
|
if (IsFrontEngine(src)) {
|
||||||
// the vehicle was previously a loco. need to free the order list and delete vehicle windows etc.
|
/* the vehicle was previously a loco. need to free the order list and delete vehicle windows etc. */
|
||||||
DeleteWindowById(WC_VEHICLE_VIEW, src->index);
|
DeleteWindowById(WC_VEHICLE_VIEW, src->index);
|
||||||
DeleteVehicleOrders(src);
|
DeleteVehicleOrders(src);
|
||||||
}
|
}
|
||||||
|
@ -1151,7 +1155,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
src->unitnumber = 0; // doesn't occupy a unitnumber anymore.
|
src->unitnumber = 0; // doesn't occupy a unitnumber anymore.
|
||||||
}
|
}
|
||||||
|
|
||||||
// link in the wagon(s) in the chain.
|
/* link in the wagon(s) in the chain. */
|
||||||
{
|
{
|
||||||
Vehicle *v;
|
Vehicle *v;
|
||||||
|
|
||||||
|
@ -1165,7 +1169,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
src_head = src_head->next;
|
src_head = src_head->next;
|
||||||
}
|
}
|
||||||
AddWagonToConsist(src->u.rail.other_multiheaded_part, src);
|
AddWagonToConsist(src->u.rail.other_multiheaded_part, src);
|
||||||
// previous line set the front engine to the old front. We need to clear that
|
/* previous line set the front engine to the old front. We need to clear that */
|
||||||
src->u.rail.other_multiheaded_part->first = NULL;
|
src->u.rail.other_multiheaded_part->first = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1184,7 +1188,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
}
|
}
|
||||||
if (engine != NULL && engine->u.rail.other_multiheaded_part != NULL) {
|
if (engine != NULL && engine->u.rail.other_multiheaded_part != NULL) {
|
||||||
AddWagonToConsist(engine->u.rail.other_multiheaded_part, engine);
|
AddWagonToConsist(engine->u.rail.other_multiheaded_part, engine);
|
||||||
// previous line set the front engine to the old front. We need to clear that
|
/* previous line set the front engine to the old front. We need to clear that */
|
||||||
engine->u.rail.other_multiheaded_part->first = NULL;
|
engine->u.rail.other_multiheaded_part->first = NULL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1233,6 +1237,7 @@ int32 CmdMoveRailVehicle(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
/** Start/Stop a train.
|
/** Start/Stop a train.
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 train to start/stop
|
* @param p1 train to start/stop
|
||||||
* @param p2 unused
|
* @param p2 unused
|
||||||
*/
|
*/
|
||||||
|
@ -1269,6 +1274,7 @@ int32 CmdStartStopTrain(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
/** Sell a (single) train wagon/engine.
|
/** Sell a (single) train wagon/engine.
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 the wagon/engine index
|
* @param p1 the wagon/engine index
|
||||||
* @param p2 the selling mode
|
* @param p2 the selling mode
|
||||||
* - p2 = 0: only sell the single dragged wagon/engine (and any belonging rear-engines)
|
* - p2 = 0: only sell the single dragged wagon/engine (and any belonging rear-engines)
|
||||||
|
@ -1290,7 +1296,7 @@ int32 CmdSellRailWagon(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
while (IsArticulatedPart(v)) v = GetPrevVehicleInChain(v);
|
while (IsArticulatedPart(v)) v = GetPrevVehicleInChain(v);
|
||||||
Vehicle *first = GetFirstVehicleInChain(v);
|
Vehicle *first = GetFirstVehicleInChain(v);
|
||||||
|
|
||||||
// make sure the vehicle is stopped in the depot
|
/* make sure the vehicle is stopped in the depot */
|
||||||
if (CheckTrainStoppedInDepot(first) < 0) {
|
if (CheckTrainStoppedInDepot(first) < 0) {
|
||||||
return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
||||||
}
|
}
|
||||||
|
@ -1596,8 +1602,8 @@ static void AdvanceWagons(Vehicle *v, bool before)
|
||||||
uint length = CountVehiclesInChain(v);
|
uint length = CountVehiclesInChain(v);
|
||||||
|
|
||||||
while (length > 2) {
|
while (length > 2) {
|
||||||
// find pairwise matching wagon
|
/* find pairwise matching wagon
|
||||||
// start<>end, start+1<>end-1, ...
|
* start<>end, start+1<>end-1, ... */
|
||||||
Vehicle *last = first;
|
Vehicle *last = first;
|
||||||
for (uint i = length - 3; i > 0; i--) last = last->next;
|
for (uint i = length - 3; i > 0; i--) last = last->next;
|
||||||
|
|
||||||
|
@ -1605,7 +1611,7 @@ static void AdvanceWagons(Vehicle *v, bool before)
|
||||||
if (before) differential *= -1;
|
if (before) differential *= -1;
|
||||||
|
|
||||||
if (differential > 0) {
|
if (differential > 0) {
|
||||||
// disconnect last car to make sure only this subset moves
|
/* disconnect last car to make sure only this subset moves */
|
||||||
Vehicle *tempnext = last->next;
|
Vehicle *tempnext = last->next;
|
||||||
last->next = NULL;
|
last->next = NULL;
|
||||||
|
|
||||||
|
@ -1643,7 +1649,7 @@ static void ReverseTrainDirection(Vehicle *v)
|
||||||
DisableTrainCrossing(tile);
|
DisableTrainCrossing(tile);
|
||||||
}
|
}
|
||||||
|
|
||||||
// count number of vehicles
|
/* count number of vehicles */
|
||||||
int r = -1;
|
int r = -1;
|
||||||
const Vehicle *u = v;
|
const Vehicle *u = v;
|
||||||
do r++; while ( (u = u->next) != NULL );
|
do r++; while ( (u = u->next) != NULL );
|
||||||
|
@ -1667,6 +1673,7 @@ static void ReverseTrainDirection(Vehicle *v)
|
||||||
|
|
||||||
/** Reverse train.
|
/** Reverse train.
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 train to reverse
|
* @param p1 train to reverse
|
||||||
* @param p2 if true, reverse a unit in a train (needs to be in a depot)
|
* @param p2 if true, reverse a unit in a train (needs to be in a depot)
|
||||||
*/
|
*/
|
||||||
|
@ -1679,14 +1686,14 @@ int32 CmdReverseTrainDirection(TileIndex tile, uint32 flags, uint32 p1, uint32 p
|
||||||
if (v->type != VEH_TRAIN || !CheckOwnership(v->owner)) return CMD_ERROR;
|
if (v->type != VEH_TRAIN || !CheckOwnership(v->owner)) return CMD_ERROR;
|
||||||
|
|
||||||
if (p2) {
|
if (p2) {
|
||||||
// turn a single unit around
|
/* turn a single unit around */
|
||||||
|
|
||||||
if (IsMultiheaded(v) || HASBIT(EngInfo(v->engine_type)->callbackmask, CBM_ARTIC_ENGINE)) {
|
if (IsMultiheaded(v) || HASBIT(EngInfo(v->engine_type)->callbackmask, CBM_ARTIC_ENGINE)) {
|
||||||
return_cmd_error(STR_ONLY_TURN_SINGLE_UNIT);
|
return_cmd_error(STR_ONLY_TURN_SINGLE_UNIT);
|
||||||
}
|
}
|
||||||
|
|
||||||
Vehicle *front = GetFirstVehicleInChain(v);
|
Vehicle *front = GetFirstVehicleInChain(v);
|
||||||
// make sure the vehicle is stopped in the depot
|
/* make sure the vehicle is stopped in the depot */
|
||||||
if (CheckTrainStoppedInDepot(front) < 0) {
|
if (CheckTrainStoppedInDepot(front) < 0) {
|
||||||
return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
return_cmd_error(STR_881A_TRAINS_CAN_ONLY_BE_ALTERED);
|
||||||
}
|
}
|
||||||
|
@ -1697,7 +1704,7 @@ int32 CmdReverseTrainDirection(TileIndex tile, uint32 flags, uint32 p1, uint32 p
|
||||||
InvalidateWindow(WC_VEHICLE_DETAILS, v->index);
|
InvalidateWindow(WC_VEHICLE_DETAILS, v->index);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
//turn the whole train around
|
/*turn the whole train around */
|
||||||
if (v->u.rail.crash_anim_pos != 0 || v->breakdown_ctr != 0) return CMD_ERROR;
|
if (v->u.rail.crash_anim_pos != 0 || v->breakdown_ctr != 0) return CMD_ERROR;
|
||||||
|
|
||||||
if (flags & DC_EXEC) {
|
if (flags & DC_EXEC) {
|
||||||
|
@ -1715,6 +1722,7 @@ int32 CmdReverseTrainDirection(TileIndex tile, uint32 flags, uint32 p1, uint32 p
|
||||||
|
|
||||||
/** Force a train through a red signal
|
/** Force a train through a red signal
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 train to ignore the red signal
|
* @param p1 train to ignore the red signal
|
||||||
* @param p2 unused
|
* @param p2 unused
|
||||||
*/
|
*/
|
||||||
|
@ -1733,6 +1741,7 @@ int32 CmdForceTrainProceed(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
/** Refits a train to the specified cargo type.
|
/** Refits a train to the specified cargo type.
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 vehicle ID of the train to refit
|
* @param p1 vehicle ID of the train to refit
|
||||||
* param p2 various bitstuffed elements
|
* param p2 various bitstuffed elements
|
||||||
* - p2 = (bit 0-7) - the new cargo type to refit to
|
* - p2 = (bit 0-7) - the new cargo type to refit to
|
||||||
|
@ -1854,8 +1863,8 @@ static bool NtpCallbFindDepot(TileIndex tile, TrainFindDepotData *tfdd, int trac
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// returns the tile of a depot to goto to. The given vehicle must not be
|
/** returns the tile of a depot to goto to. The given vehicle must not be
|
||||||
// crashed!
|
* crashed! */
|
||||||
static TrainFindDepotData FindClosestTrainDepot(Vehicle *v, int max_distance)
|
static TrainFindDepotData FindClosestTrainDepot(Vehicle *v, int max_distance)
|
||||||
{
|
{
|
||||||
assert(!(v->vehstatus & VS_CRASHED));
|
assert(!(v->vehstatus & VS_CRASHED));
|
||||||
|
@ -1893,7 +1902,7 @@ static TrainFindDepotData FindClosestTrainDepot(Vehicle *v, int max_distance)
|
||||||
if (NPFGetFlag(&ftd.node, NPF_FLAG_REVERSE)) tfdd.reverse = true;
|
if (NPFGetFlag(&ftd.node, NPF_FLAG_REVERSE)) tfdd.reverse = true;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// search in the forward direction first.
|
/* search in the forward direction first. */
|
||||||
DiagDirection i = DirToDiagDir(v->direction);
|
DiagDirection i = DirToDiagDir(v->direction);
|
||||||
if (!(v->direction & 1) && v->u.rail.track != _state_dir_table[i]) {
|
if (!(v->direction & 1) && v->u.rail.track != _state_dir_table[i]) {
|
||||||
i = ChangeDiagDir(i, DIAGDIRDIFF_90LEFT);
|
i = ChangeDiagDir(i, DIAGDIRDIFF_90LEFT);
|
||||||
|
@ -1901,7 +1910,7 @@ static TrainFindDepotData FindClosestTrainDepot(Vehicle *v, int max_distance)
|
||||||
NewTrainPathfind(tile, 0, v->u.rail.compatible_railtypes, i, (NTPEnumProc*)NtpCallbFindDepot, &tfdd);
|
NewTrainPathfind(tile, 0, v->u.rail.compatible_railtypes, i, (NTPEnumProc*)NtpCallbFindDepot, &tfdd);
|
||||||
if (tfdd.best_length == (uint)-1){
|
if (tfdd.best_length == (uint)-1){
|
||||||
tfdd.reverse = true;
|
tfdd.reverse = true;
|
||||||
// search in backwards direction
|
/* search in backwards direction */
|
||||||
i = ReverseDiagDir(DirToDiagDir(v->direction));
|
i = ReverseDiagDir(DirToDiagDir(v->direction));
|
||||||
if (!(v->direction & 1) && v->u.rail.track != _state_dir_table[i]) {
|
if (!(v->direction & 1) && v->u.rail.track != _state_dir_table[i]) {
|
||||||
i = ChangeDiagDir(i, DIAGDIRDIFF_90LEFT);
|
i = ChangeDiagDir(i, DIAGDIRDIFF_90LEFT);
|
||||||
|
@ -1915,6 +1924,7 @@ static TrainFindDepotData FindClosestTrainDepot(Vehicle *v, int max_distance)
|
||||||
|
|
||||||
/** Send a train to a depot
|
/** Send a train to a depot
|
||||||
* @param tile unused
|
* @param tile unused
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 train to send to the depot
|
* @param p1 train to send to the depot
|
||||||
* @param p2 various bitmasked elements
|
* @param p2 various bitmasked elements
|
||||||
* - p2 bit 0-3 - DEPOT_ flags (see vehicle.h)
|
* - p2 bit 0-3 - DEPOT_ flags (see vehicle.h)
|
||||||
|
@ -2010,7 +2020,7 @@ static void HandleLocomotiveSmokeCloud(const Vehicle* v)
|
||||||
byte effect_type = GB(v->u.rail.cached_vis_effect, 4, 2);
|
byte effect_type = GB(v->u.rail.cached_vis_effect, 4, 2);
|
||||||
bool disable_effect = HASBIT(v->u.rail.cached_vis_effect, 6);
|
bool disable_effect = HASBIT(v->u.rail.cached_vis_effect, 6);
|
||||||
|
|
||||||
// no smoke?
|
/* no smoke? */
|
||||||
if ((rvi->railveh_type == RAILVEH_WAGON && effect_type == 0) ||
|
if ((rvi->railveh_type == RAILVEH_WAGON && effect_type == 0) ||
|
||||||
disable_effect ||
|
disable_effect ||
|
||||||
rvi->railtype > RAILTYPE_ELECTRIC ||
|
rvi->railtype > RAILTYPE_ELECTRIC ||
|
||||||
|
@ -2018,14 +2028,14 @@ static void HandleLocomotiveSmokeCloud(const Vehicle* v)
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
// No smoke in depots or tunnels
|
/* No smoke in depots or tunnels */
|
||||||
if (IsTileDepotType(v->tile, TRANSPORT_RAIL) || IsTunnelTile(v->tile)) continue;
|
if (IsTileDepotType(v->tile, TRANSPORT_RAIL) || IsTunnelTile(v->tile)) continue;
|
||||||
|
|
||||||
// No sparks for electric vehicles on nonelectrified tracks
|
/* No sparks for electric vehicles on nonelectrified tracks */
|
||||||
if (!HasPowerOnRail(v->u.rail.railtype, GetTileRailType(v->tile))) continue;
|
if (!HasPowerOnRail(v->u.rail.railtype, GetTileRailType(v->tile))) continue;
|
||||||
|
|
||||||
if (effect_type == 0) {
|
if (effect_type == 0) {
|
||||||
// Use default effect type for engine class.
|
/* Use default effect type for engine class. */
|
||||||
effect_type = rvi->engclass;
|
effect_type = rvi->engclass;
|
||||||
} else {
|
} else {
|
||||||
effect_type--;
|
effect_type--;
|
||||||
|
@ -2041,7 +2051,7 @@ static void HandleLocomotiveSmokeCloud(const Vehicle* v)
|
||||||
|
|
||||||
switch (effect_type) {
|
switch (effect_type) {
|
||||||
case 0:
|
case 0:
|
||||||
// steam smoke.
|
/* steam smoke. */
|
||||||
if (GB(v->tick_counter, 0, 4) == 0) {
|
if (GB(v->tick_counter, 0, 4) == 0) {
|
||||||
CreateEffectVehicleRel(v, x, y, 10, EV_STEAM_SMOKE);
|
CreateEffectVehicleRel(v, x, y, 10, EV_STEAM_SMOKE);
|
||||||
sound = true;
|
sound = true;
|
||||||
|
@ -2049,7 +2059,7 @@ static void HandleLocomotiveSmokeCloud(const Vehicle* v)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 1:
|
case 1:
|
||||||
// diesel smoke
|
/* diesel smoke */
|
||||||
if (u->cur_speed <= 40 && CHANCE16(15, 128)) {
|
if (u->cur_speed <= 40 && CHANCE16(15, 128)) {
|
||||||
CreateEffectVehicleRel(v, 0, 0, 10, EV_DIESEL_SMOKE);
|
CreateEffectVehicleRel(v, 0, 0, 10, EV_DIESEL_SMOKE);
|
||||||
sound = true;
|
sound = true;
|
||||||
|
@ -2057,7 +2067,7 @@ static void HandleLocomotiveSmokeCloud(const Vehicle* v)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 2:
|
case 2:
|
||||||
// blue spark
|
/* blue spark */
|
||||||
if (GB(v->tick_counter, 0, 2) == 0 && CHANCE16(1, 45)) {
|
if (GB(v->tick_counter, 0, 2) == 0 && CHANCE16(1, 45)) {
|
||||||
CreateEffectVehicleRel(v, 0, 0, 10, EV_ELECTRIC_SPARK);
|
CreateEffectVehicleRel(v, 0, 0, 10, EV_ELECTRIC_SPARK);
|
||||||
sound = true;
|
sound = true;
|
||||||
|
@ -2094,12 +2104,12 @@ static void TrainPlayLeaveStationSound(const Vehicle* v)
|
||||||
|
|
||||||
static bool CheckTrainStayInDepot(Vehicle *v)
|
static bool CheckTrainStayInDepot(Vehicle *v)
|
||||||
{
|
{
|
||||||
// bail out if not all wagons are in the same depot or not in a depot at all
|
/* bail out if not all wagons are in the same depot or not in a depot at all */
|
||||||
for (const Vehicle *u = v; u != NULL; u = u->next) {
|
for (const Vehicle *u = v; u != NULL; u = u->next) {
|
||||||
if (u->u.rail.track != TRACK_BIT_DEPOT || u->tile != v->tile) return false;
|
if (u->u.rail.track != TRACK_BIT_DEPOT || u->tile != v->tile) return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// if the train got no power, then keep it in the depot
|
/* if the train got no power, then keep it in the depot */
|
||||||
if (v->u.rail.cached_power == 0) {
|
if (v->u.rail.cached_power == 0) {
|
||||||
v->vehstatus |= VS_STOPPED;
|
v->vehstatus |= VS_STOPPED;
|
||||||
InvalidateWindow(WC_VEHICLE_DEPOT, v->tile);
|
InvalidateWindow(WC_VEHICLE_DEPOT, v->tile);
|
||||||
|
@ -2151,10 +2161,10 @@ struct TrainTrackFollowerData {
|
||||||
|
|
||||||
static bool NtpCallbFindStation(TileIndex tile, TrainTrackFollowerData *ttfd, Trackdir track, uint length)
|
static bool NtpCallbFindStation(TileIndex tile, TrainTrackFollowerData *ttfd, Trackdir track, uint length)
|
||||||
{
|
{
|
||||||
// heading for nowhere?
|
/* heading for nowhere? */
|
||||||
if (ttfd->dest_coords == 0) return false;
|
if (ttfd->dest_coords == 0) return false;
|
||||||
|
|
||||||
// did we reach the final station?
|
/* did we reach the final station? */
|
||||||
if ((ttfd->station_index == INVALID_STATION && tile == ttfd->dest_coords) || (
|
if ((ttfd->station_index == INVALID_STATION && tile == ttfd->dest_coords) || (
|
||||||
IsTileType(tile, MP_STATION) &&
|
IsTileType(tile, MP_STATION) &&
|
||||||
IsRailwayStation(tile) &&
|
IsRailwayStation(tile) &&
|
||||||
|
@ -2163,12 +2173,13 @@ static bool NtpCallbFindStation(TileIndex tile, TrainTrackFollowerData *ttfd, Tr
|
||||||
/* We do not check for dest_coords if we have a station_index,
|
/* We do not check for dest_coords if we have a station_index,
|
||||||
* because in that case the dest_coords are just an
|
* because in that case the dest_coords are just an
|
||||||
* approximation of where the station is */
|
* approximation of where the station is */
|
||||||
// found station
|
|
||||||
|
/* found station */
|
||||||
ttfd->best_track = track;
|
ttfd->best_track = track;
|
||||||
ttfd->best_bird_dist = 0;
|
ttfd->best_bird_dist = 0;
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
// didn't find station, keep track of the best path so far.
|
/* didn't find station, keep track of the best path so far. */
|
||||||
uint dist = DistanceManhattan(tile, ttfd->dest_coords);
|
uint dist = DistanceManhattan(tile, ttfd->dest_coords);
|
||||||
if (dist < ttfd->best_bird_dist) {
|
if (dist < ttfd->best_bird_dist) {
|
||||||
ttfd->best_bird_dist = dist;
|
ttfd->best_bird_dist = dist;
|
||||||
|
@ -2205,12 +2216,12 @@ static const uint32 _reachable_tracks[4] = {
|
||||||
};
|
};
|
||||||
|
|
||||||
static const byte _search_directions[6][4] = {
|
static const byte _search_directions[6][4] = {
|
||||||
{ 0, 9, 2, 9 }, // track 1
|
{ 0, 9, 2, 9 }, ///< track 1
|
||||||
{ 9, 1, 9, 3 }, // track 2
|
{ 9, 1, 9, 3 }, ///< track 2
|
||||||
{ 9, 0, 3, 9 }, // track upper
|
{ 9, 0, 3, 9 }, ///< track upper
|
||||||
{ 1, 9, 9, 2 }, // track lower
|
{ 1, 9, 9, 2 }, ///< track lower
|
||||||
{ 3, 2, 9, 9 }, // track left
|
{ 3, 2, 9, 9 }, ///< track left
|
||||||
{ 9, 9, 1, 0 }, // track right
|
{ 9, 9, 1, 0 }, ///< track right
|
||||||
};
|
};
|
||||||
|
|
||||||
static const byte _pick_track_table[6] = {1, 3, 2, 2, 0, 0};
|
static const byte _pick_track_table[6] = {1, 3, 2, 2, 0, 0};
|
||||||
|
@ -2219,7 +2230,7 @@ static const byte _pick_track_table[6] = {1, 3, 2, 2, 0, 0};
|
||||||
static Track ChooseTrainTrack(Vehicle* v, TileIndex tile, DiagDirection enterdir, TrackBits tracks)
|
static Track ChooseTrainTrack(Vehicle* v, TileIndex tile, DiagDirection enterdir, TrackBits tracks)
|
||||||
{
|
{
|
||||||
Track best_track;
|
Track best_track;
|
||||||
// pathfinders are able to tell that route was only 'guessed'
|
/* pathfinders are able to tell that route was only 'guessed' */
|
||||||
bool path_not_found = false;
|
bool path_not_found = false;
|
||||||
|
|
||||||
#ifdef PF_BENCHMARK
|
#ifdef PF_BENCHMARK
|
||||||
|
@ -2250,9 +2261,9 @@ static Track ChooseTrainTrack(Vehicle* v, TileIndex tile, DiagDirection enterdir
|
||||||
NPFFoundTargetData ftd = NPFRouteToStationOrTile(tile - TileOffsByDiagDir(enterdir), trackdir, &fstd, TRANSPORT_RAIL, v->owner, v->u.rail.compatible_railtypes);
|
NPFFoundTargetData ftd = NPFRouteToStationOrTile(tile - TileOffsByDiagDir(enterdir), trackdir, &fstd, TRANSPORT_RAIL, v->owner, v->u.rail.compatible_railtypes);
|
||||||
|
|
||||||
if (ftd.best_trackdir == 0xff) {
|
if (ftd.best_trackdir == 0xff) {
|
||||||
/* We are already at our target. Just do something */
|
/* We are already at our target. Just do something
|
||||||
//TODO: maybe display error?
|
* @todo maybe display error?
|
||||||
//TODO: go straight ahead if possible?
|
* @todo: go straight ahead if possible? */
|
||||||
best_track = FindFirstTrack(tracks);
|
best_track = FindFirstTrack(tracks);
|
||||||
} else {
|
} else {
|
||||||
/* If ftd.best_bird_dist is 0, we found our target and ftd.best_trackdir contains
|
/* If ftd.best_bird_dist is 0, we found our target and ftd.best_trackdir contains
|
||||||
|
@ -2280,11 +2291,11 @@ static Track ChooseTrainTrack(Vehicle* v, TileIndex tile, DiagDirection enterdir
|
||||||
NewTrainPathfind(tile - TileOffsByDiagDir(enterdir), v->dest_tile,
|
NewTrainPathfind(tile - TileOffsByDiagDir(enterdir), v->dest_tile,
|
||||||
v->u.rail.compatible_railtypes, enterdir, (NTPEnumProc*)NtpCallbFindStation, &fd);
|
v->u.rail.compatible_railtypes, enterdir, (NTPEnumProc*)NtpCallbFindStation, &fd);
|
||||||
|
|
||||||
// check whether the path was found or only 'guessed'
|
/* check whether the path was found or only 'guessed' */
|
||||||
if (fd.best_bird_dist != 0) path_not_found = true;
|
if (fd.best_bird_dist != 0) path_not_found = true;
|
||||||
|
|
||||||
if (fd.best_track == 0xff) {
|
if (fd.best_track == 0xff) {
|
||||||
// blaha
|
/* blaha */
|
||||||
best_track = FindFirstTrack(tracks);
|
best_track = FindFirstTrack(tracks);
|
||||||
} else {
|
} else {
|
||||||
best_track = TrackdirToTrack(fd.best_track);
|
best_track = TrackdirToTrack(fd.best_track);
|
||||||
|
@ -2293,13 +2304,13 @@ static Track ChooseTrainTrack(Vehicle* v, TileIndex tile, DiagDirection enterdir
|
||||||
int time = NpfEndInterval(perf);
|
int time = NpfEndInterval(perf);
|
||||||
DEBUG(yapf, 4, "[NTPT] %d us - %d rounds - %d open - %d closed -- ", time, 0, 0, 0);
|
DEBUG(yapf, 4, "[NTPT] %d us - %d rounds - %d open - %d closed -- ", time, 0, 0, 0);
|
||||||
}
|
}
|
||||||
// handle "path not found" state
|
/* handle "path not found" state */
|
||||||
if (path_not_found) {
|
if (path_not_found) {
|
||||||
// PF didn't find the route
|
/* PF didn't find the route */
|
||||||
if (!HASBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION)) {
|
if (!HASBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION)) {
|
||||||
// it is first time the problem occurred, set the "path not found" flag
|
/* it is first time the problem occurred, set the "path not found" flag */
|
||||||
SETBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION);
|
SETBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION);
|
||||||
// and notify user about the event
|
/* and notify user about the event */
|
||||||
if (_patches.lost_train_warn && v->owner == _local_player) {
|
if (_patches.lost_train_warn && v->owner == _local_player) {
|
||||||
SetDParam(0, v->unitnumber);
|
SetDParam(0, v->unitnumber);
|
||||||
AddNewsItem(
|
AddNewsItem(
|
||||||
|
@ -2310,11 +2321,11 @@ static Track ChooseTrainTrack(Vehicle* v, TileIndex tile, DiagDirection enterdir
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// route found, is the train marked with "path not found" flag?
|
/* route found, is the train marked with "path not found" flag? */
|
||||||
if (HASBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION)) {
|
if (HASBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION)) {
|
||||||
// clear the flag as the PF's problem was solved
|
/* clear the flag as the PF's problem was solved */
|
||||||
CLRBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION);
|
CLRBIT(v->u.rail.flags, VRF_NO_PATH_TO_DESTINATION);
|
||||||
// can we also delete the "News" item somehow?
|
/* can we also delete the "News" item somehow? */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2440,14 +2451,14 @@ static bool ProcessTrainOrder(Vehicle *v)
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// check if we've reached the waypoint?
|
/* check if we've reached the waypoint? */
|
||||||
bool at_waypoint = false;
|
bool at_waypoint = false;
|
||||||
if (v->current_order.type == OT_GOTO_WAYPOINT && v->tile == v->dest_tile) {
|
if (v->current_order.type == OT_GOTO_WAYPOINT && v->tile == v->dest_tile) {
|
||||||
v->cur_order_index++;
|
v->cur_order_index++;
|
||||||
at_waypoint = true;
|
at_waypoint = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// check if we've reached a non-stop station while TTDPatch nonstop is enabled..
|
/* check if we've reached a non-stop station while TTDPatch nonstop is enabled.. */
|
||||||
if (_patches.new_nonstop &&
|
if (_patches.new_nonstop &&
|
||||||
v->current_order.flags & OF_NON_STOP &&
|
v->current_order.flags & OF_NON_STOP &&
|
||||||
IsTileType(v->tile, MP_STATION) &&
|
IsTileType(v->tile, MP_STATION) &&
|
||||||
|
@ -2455,25 +2466,25 @@ static bool ProcessTrainOrder(Vehicle *v)
|
||||||
v->cur_order_index++;
|
v->cur_order_index++;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get the current order
|
/* Get the current order */
|
||||||
if (v->cur_order_index >= v->num_orders) v->cur_order_index = 0;
|
if (v->cur_order_index >= v->num_orders) v->cur_order_index = 0;
|
||||||
|
|
||||||
const Order *order = GetVehicleOrder(v, v->cur_order_index);
|
const Order *order = GetVehicleOrder(v, v->cur_order_index);
|
||||||
|
|
||||||
// If no order, do nothing.
|
/* If no order, do nothing. */
|
||||||
if (order == NULL) {
|
if (order == NULL) {
|
||||||
v->current_order.Free();
|
v->current_order.Free();
|
||||||
v->dest_tile = 0;
|
v->dest_tile = 0;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// If it is unchanged, keep it.
|
/* If it is unchanged, keep it. */
|
||||||
if (order->type == v->current_order.type &&
|
if (order->type == v->current_order.type &&
|
||||||
order->flags == v->current_order.flags &&
|
order->flags == v->current_order.flags &&
|
||||||
order->dest == v->current_order.dest)
|
order->dest == v->current_order.dest)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// Otherwise set it, and determine the destination tile.
|
/* Otherwise set it, and determine the destination tile. */
|
||||||
v->current_order = *order;
|
v->current_order = *order;
|
||||||
|
|
||||||
v->dest_tile = 0;
|
v->dest_tile = 0;
|
||||||
|
@ -2516,7 +2527,7 @@ static void HandleTrainLoading(Vehicle *v, bool mode)
|
||||||
case OT_LOADING: {
|
case OT_LOADING: {
|
||||||
if (mode) return;
|
if (mode) return;
|
||||||
|
|
||||||
// don't mark the train as lost if we're loading on the final station.
|
/* don't mark the train as lost if we're loading on the final station. */
|
||||||
if (v->current_order.flags & OF_NON_STOP) {
|
if (v->current_order.flags & OF_NON_STOP) {
|
||||||
v->u.rail.days_since_order_progr = 0;
|
v->u.rail.days_since_order_progr = 0;
|
||||||
}
|
}
|
||||||
|
@ -2527,13 +2538,13 @@ static void HandleTrainLoading(Vehicle *v, bool mode)
|
||||||
v->current_order.flags & OF_FULL_LOAD ||
|
v->current_order.flags & OF_FULL_LOAD ||
|
||||||
(_patches.gradual_loading && !HASBIT(v->vehicle_flags, VF_LOADING_FINISHED))
|
(_patches.gradual_loading && !HASBIT(v->vehicle_flags, VF_LOADING_FINISHED))
|
||||||
)) {
|
)) {
|
||||||
v->u.rail.days_since_order_progr = 0; /* Prevent a train lost message for full loading trains */
|
v->u.rail.days_since_order_progr = 0; // Prevent a train lost message for full loading trains
|
||||||
SET_EXPENSES_TYPE(EXPENSES_TRAIN_INC);
|
SET_EXPENSES_TYPE(EXPENSES_TRAIN_INC);
|
||||||
if (LoadUnloadVehicle(v, false)) {
|
if (LoadUnloadVehicle(v, false)) {
|
||||||
InvalidateWindow(WC_TRAINS_LIST, v->owner);
|
InvalidateWindow(WC_TRAINS_LIST, v->owner);
|
||||||
MarkTrainDirty(v);
|
MarkTrainDirty(v);
|
||||||
|
|
||||||
// need to update acceleration and cached values since the goods on the train changed.
|
/* need to update acceleration and cached values since the goods on the train changed. */
|
||||||
TrainCargoChanged(v);
|
TrainCargoChanged(v);
|
||||||
UpdateTrainAcceleration(v);
|
UpdateTrainAcceleration(v);
|
||||||
}
|
}
|
||||||
|
@ -2545,7 +2556,7 @@ static void HandleTrainLoading(Vehicle *v, bool mode)
|
||||||
Order b = v->current_order;
|
Order b = v->current_order;
|
||||||
v->LeaveStation();
|
v->LeaveStation();
|
||||||
|
|
||||||
// If this was not the final order, don't remove it from the list.
|
/* If this was not the final order, don't remove it from the list. */
|
||||||
if (!(b.flags & OF_NON_STOP)) return;
|
if (!(b.flags & OF_NON_STOP)) return;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -2614,16 +2625,16 @@ static void TrainEnterStation(Vehicle *v, StationID station)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Did we reach the final destination?
|
/* Did we reach the final destination? */
|
||||||
if (v->current_order.type == OT_GOTO_STATION &&
|
if (v->current_order.type == OT_GOTO_STATION &&
|
||||||
v->current_order.dest == station) {
|
v->current_order.dest == station) {
|
||||||
// Yeah, keep the load/unload flags
|
/* Yeah, keep the load/unload flags
|
||||||
// Non Stop now means if the order should be increased.
|
* Non Stop now means if the order should be increased. */
|
||||||
v->BeginLoading();
|
v->BeginLoading();
|
||||||
v->current_order.flags &= OF_FULL_LOAD | OF_UNLOAD | OF_TRANSFER;
|
v->current_order.flags &= OF_FULL_LOAD | OF_UNLOAD | OF_TRANSFER;
|
||||||
v->current_order.flags |= OF_NON_STOP;
|
v->current_order.flags |= OF_NON_STOP;
|
||||||
} else {
|
} else {
|
||||||
// No, just do a simple load
|
/* No, just do a simple load */
|
||||||
v->BeginLoading();
|
v->BeginLoading();
|
||||||
v->current_order.flags = 0;
|
v->current_order.flags = 0;
|
||||||
}
|
}
|
||||||
|
@ -2641,7 +2652,7 @@ static void TrainEnterStation(Vehicle *v, StationID station)
|
||||||
|
|
||||||
static byte AfterSetTrainPos(Vehicle *v, bool new_tile)
|
static byte AfterSetTrainPos(Vehicle *v, bool new_tile)
|
||||||
{
|
{
|
||||||
// need this hint so it returns the right z coordinate on bridges.
|
/* need this hint so it returns the right z coordinate on bridges. */
|
||||||
byte new_z = GetSlopeZ(v->x_pos, v->y_pos);
|
byte new_z = GetSlopeZ(v->x_pos, v->y_pos);
|
||||||
|
|
||||||
byte old_z = v->z_pos;
|
byte old_z = v->z_pos;
|
||||||
|
@ -2654,7 +2665,7 @@ static byte AfterSetTrainPos(Vehicle *v, bool new_tile)
|
||||||
if (new_z != old_z) {
|
if (new_z != old_z) {
|
||||||
TileIndex tile = TileVirtXY(v->x_pos, v->y_pos);
|
TileIndex tile = TileVirtXY(v->x_pos, v->y_pos);
|
||||||
|
|
||||||
// XXX workaround, whole UP/DOWN detection needs overhaul
|
/* XXX workaround, whole UP/DOWN detection needs overhaul */
|
||||||
if (!IsTunnelTile(tile)) {
|
if (!IsTunnelTile(tile)) {
|
||||||
SETBIT(v->u.rail.flags, (new_z > old_z) ? VRF_GOINGUP : VRF_GOINGDOWN);
|
SETBIT(v->u.rail.flags, (new_z > old_z) ? VRF_GOINGUP : VRF_GOINGDOWN);
|
||||||
}
|
}
|
||||||
|
@ -2727,13 +2738,13 @@ struct RailtypeSlowdownParams {
|
||||||
|
|
||||||
static const RailtypeSlowdownParams _railtype_slowdown[] = {
|
static const RailtypeSlowdownParams _railtype_slowdown[] = {
|
||||||
// normal accel
|
// normal accel
|
||||||
{256 / 4, 256 / 2, 256 / 4, 2}, // normal
|
{256 / 4, 256 / 2, 256 / 4, 2}, ///< normal
|
||||||
{256 / 4, 256 / 2, 256 / 4, 2}, // electrified
|
{256 / 4, 256 / 2, 256 / 4, 2}, ///< electrified
|
||||||
{256 / 4, 256 / 2, 256 / 4, 2}, // monorail
|
{256 / 4, 256 / 2, 256 / 4, 2}, ///< monorail
|
||||||
{0, 256 / 2, 256 / 4, 2}, // maglev
|
{0, 256 / 2, 256 / 4, 2}, ///< maglev
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Modify the speed of the vehicle due to a turn */
|
/** Modify the speed of the vehicle due to a turn */
|
||||||
static void AffectSpeedByDirChange(Vehicle* v, Direction new_dir)
|
static void AffectSpeedByDirChange(Vehicle* v, Direction new_dir)
|
||||||
{
|
{
|
||||||
if (_patches.realistic_acceleration) return;
|
if (_patches.realistic_acceleration) return;
|
||||||
|
@ -2745,7 +2756,7 @@ static void AffectSpeedByDirChange(Vehicle* v, Direction new_dir)
|
||||||
v->cur_speed -= (diff == DIRDIFF_45RIGHT || diff == DIRDIFF_45LEFT ? rsp->small_turn : rsp->large_turn) * v->cur_speed >> 8;
|
v->cur_speed -= (diff == DIRDIFF_45RIGHT || diff == DIRDIFF_45LEFT ? rsp->small_turn : rsp->large_turn) * v->cur_speed >> 8;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Modify the speed of the vehicle due to a change in altitude */
|
/** Modify the speed of the vehicle due to a change in altitude */
|
||||||
static void AffectSpeedByZChange(Vehicle *v, byte old_z)
|
static void AffectSpeedByZChange(Vehicle *v, byte old_z)
|
||||||
{
|
{
|
||||||
if (old_z == v->z_pos || _patches.realistic_acceleration) return;
|
if (old_z == v->z_pos || _patches.realistic_acceleration) return;
|
||||||
|
@ -2820,7 +2831,7 @@ static uint CountPassengersInTrain(const Vehicle* v)
|
||||||
return num;
|
return num;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Checks whether the specified train has a collision with another vehicle. If
|
* Checks whether the specified train has a collision with another vehicle. If
|
||||||
* so, destroys this vehicle, and the other vehicle if its subtype has TS_Front.
|
* so, destroys this vehicle, and the other vehicle if its subtype has TS_Front.
|
||||||
* Reports the incident in a flashy news item, modifies station ratings and
|
* Reports the incident in a flashy news item, modifies station ratings and
|
||||||
|
@ -2848,10 +2859,10 @@ static void CheckTrainCollision(Vehicle *v)
|
||||||
(v->u.rail.track == TRACK_BIT_WORMHOLE && (v->direction & 2) != (realcoll->direction & 2)))
|
(v->u.rail.track == TRACK_BIT_WORMHOLE && (v->direction & 2) != (realcoll->direction & 2)))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
//two drivers + passangers killed in train v
|
/* two drivers + passangers killed in train v */
|
||||||
uint num = 2 + CountPassengersInTrain(v);
|
uint num = 2 + CountPassengersInTrain(v);
|
||||||
if (!(coll->vehstatus & VS_CRASHED))
|
if (!(coll->vehstatus & VS_CRASHED))
|
||||||
//two drivers + passangers killed in train coll (if it was not crashed already)
|
/* two drivers + passangers killed in train coll (if it was not crashed already) */
|
||||||
num += 2 + CountPassengersInTrain(coll);
|
num += 2 + CountPassengersInTrain(coll);
|
||||||
|
|
||||||
SetVehicleCrashed(v);
|
SetVehicleCrashed(v);
|
||||||
|
@ -2959,8 +2970,8 @@ static void TrainController(Vehicle *v, bool update_image)
|
||||||
|
|
||||||
/* Check if it's a red signal and that force proceed is not clicked. */
|
/* Check if it's a red signal and that force proceed is not clicked. */
|
||||||
if ((tracks >> 16) & chosen_track && v->u.rail.force_proceed == 0) {
|
if ((tracks >> 16) & chosen_track && v->u.rail.force_proceed == 0) {
|
||||||
// In front of a red signal
|
/* In front of a red signal
|
||||||
/* find the first set bit in ts. need to do it in 2 steps, since
|
* find the first set bit in ts. need to do it in 2 steps, since
|
||||||
* FIND_FIRST_BIT only handles 6 bits at a time. */
|
* FIND_FIRST_BIT only handles 6 bits at a time. */
|
||||||
Trackdir i = FindFirstTrackdir((TrackdirBits)(uint16)ts);
|
Trackdir i = FindFirstTrackdir((TrackdirBits)(uint16)ts);
|
||||||
|
|
||||||
|
@ -3300,7 +3311,7 @@ static bool TrainCheckIfLineEnds(Vehicle *v)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if ((ts &= (ts >> 16)) == 0) {
|
if ((ts &= (ts >> 16)) == 0) {
|
||||||
// make a rail/road crossing red
|
/* make a rail/road crossing red */
|
||||||
if (IsLevelCrossingTile(tile)) {
|
if (IsLevelCrossingTile(tile)) {
|
||||||
if (!IsCrossingBarred(tile)) {
|
if (!IsCrossingBarred(tile)) {
|
||||||
BarCrossing(tile);
|
BarCrossing(tile);
|
||||||
|
@ -3316,7 +3327,7 @@ static bool TrainCheckIfLineEnds(Vehicle *v)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// slow down
|
/* slow down */
|
||||||
v->vehstatus |= VS_TRAIN_SLOWING;
|
v->vehstatus |= VS_TRAIN_SLOWING;
|
||||||
uint16 break_speed = _breakdown_speeds[x & 0xF];
|
uint16 break_speed = _breakdown_speeds[x & 0xF];
|
||||||
if (!(v->direction & 1)) break_speed >>= 1;
|
if (!(v->direction & 1)) break_speed >>= 1;
|
||||||
|
@ -3369,7 +3380,7 @@ static void TrainLocoHandler(Vehicle *v, bool mode)
|
||||||
|
|
||||||
int j = UpdateTrainSpeed(v);
|
int j = UpdateTrainSpeed(v);
|
||||||
if (j == 0) {
|
if (j == 0) {
|
||||||
// if the vehicle has speed 0, update the last_speed field.
|
/* if the vehicle has speed 0, update the last_speed field. */
|
||||||
if (v->cur_speed != 0) return;
|
if (v->cur_speed != 0) return;
|
||||||
} else {
|
} else {
|
||||||
TrainCheckIfLineEnds(v);
|
TrainCheckIfLineEnds(v);
|
||||||
|
@ -3396,11 +3407,11 @@ void Train_Tick(Vehicle *v)
|
||||||
if (IsFrontEngine(v)) {
|
if (IsFrontEngine(v)) {
|
||||||
TrainLocoHandler(v, false);
|
TrainLocoHandler(v, false);
|
||||||
|
|
||||||
// make sure vehicle wasn't deleted.
|
/* make sure vehicle wasn't deleted. */
|
||||||
if (v->type == VEH_TRAIN && IsFrontEngine(v))
|
if (v->type == VEH_TRAIN && IsFrontEngine(v))
|
||||||
TrainLocoHandler(v, true);
|
TrainLocoHandler(v, true);
|
||||||
} else if (IsFreeWagon(v) && HASBITS(v->vehstatus, VS_CRASHED)) {
|
} else if (IsFreeWagon(v) && HASBITS(v->vehstatus, VS_CRASHED)) {
|
||||||
// Delete flooded standalone wagon
|
/* Delete flooded standalone wagon */
|
||||||
if (++v->u.rail.crash_anim_pos >= 4400)
|
if (++v->u.rail.crash_anim_pos >= 4400)
|
||||||
DeleteVehicle(v);
|
DeleteVehicle(v);
|
||||||
}
|
}
|
||||||
|
@ -3415,8 +3426,8 @@ static void CheckIfTrainNeedsService(Vehicle *v)
|
||||||
if (v->vehstatus & VS_STOPPED) return;
|
if (v->vehstatus & VS_STOPPED) return;
|
||||||
if (_patches.gotodepot && VehicleHasDepotOrders(v)) return;
|
if (_patches.gotodepot && VehicleHasDepotOrders(v)) return;
|
||||||
|
|
||||||
// Don't interfere with a depot visit scheduled by the user, or a
|
/* Don't interfere with a depot visit scheduled by the user, or a
|
||||||
// depot visit by the order list.
|
* depot visit by the order list. */
|
||||||
if (v->current_order.type == OT_GOTO_DEPOT &&
|
if (v->current_order.type == OT_GOTO_DEPOT &&
|
||||||
(v->current_order.flags & (OF_HALT_IN_DEPOT | OF_PART_OF_ORDERS)) != 0)
|
(v->current_order.flags & (OF_HALT_IN_DEPOT | OF_PART_OF_ORDERS)) != 0)
|
||||||
return;
|
return;
|
||||||
|
@ -3507,7 +3518,7 @@ void TrainsYearlyLoop()
|
||||||
|
|
||||||
FOR_ALL_VEHICLES(v) {
|
FOR_ALL_VEHICLES(v) {
|
||||||
if (v->type == VEH_TRAIN && IsFrontEngine(v)) {
|
if (v->type == VEH_TRAIN && IsFrontEngine(v)) {
|
||||||
// show warning if train is not generating enough income last 2 years (corresponds to a red icon in the vehicle list)
|
/* show warning if train is not generating enough income last 2 years (corresponds to a red icon in the vehicle list) */
|
||||||
if (_patches.train_income_warn && v->owner == _local_player && v->age >= 730 && v->profit_this_year < 0) {
|
if (_patches.train_income_warn && v->owner == _local_player && v->age >= 730 && v->profit_this_year < 0) {
|
||||||
SetDParam(1, v->profit_this_year);
|
SetDParam(1, v->profit_this_year);
|
||||||
SetDParam(0, v->unitnumber);
|
SetDParam(0, v->unitnumber);
|
||||||
|
@ -3579,7 +3590,7 @@ void ConnectMultiheadedTrains()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/**
|
||||||
* Converts all trains to the new subtype format introduced in savegame 16.2
|
* Converts all trains to the new subtype format introduced in savegame 16.2
|
||||||
* It also links multiheaded engines or make them forget they are multiheaded if no suitable partner is found
|
* It also links multiheaded engines or make them forget they are multiheaded if no suitable partner is found
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file train_gui.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "debug.h"
|
#include "debug.h"
|
||||||
|
@ -22,7 +24,7 @@ void CcBuildWagon(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
if (!success) return;
|
if (!success) return;
|
||||||
|
|
||||||
// find a locomotive in the depot.
|
/* find a locomotive in the depot. */
|
||||||
found = NULL;
|
found = NULL;
|
||||||
FOR_ALL_VEHICLES(v) {
|
FOR_ALL_VEHICLES(v) {
|
||||||
if (v->type == VEH_TRAIN && IsFrontEngine(v) &&
|
if (v->type == VEH_TRAIN && IsFrontEngine(v) &&
|
||||||
|
@ -33,10 +35,10 @@ void CcBuildWagon(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// if we found a loco,
|
/* if we found a loco, */
|
||||||
if (found != NULL) {
|
if (found != NULL) {
|
||||||
found = GetLastVehicleInChain(found);
|
found = GetLastVehicleInChain(found);
|
||||||
// put the new wagon at the end of the loco.
|
/* put the new wagon at the end of the loco. */
|
||||||
DoCommandP(0, _new_vehicle_id | (found->index << 16), 0, NULL, CMD_MOVE_RAIL_VEHICLE);
|
DoCommandP(0, _new_vehicle_id | (found->index << 16), 0, NULL, CMD_MOVE_RAIL_VEHICLE);
|
||||||
RebuildVehicleLists();
|
RebuildVehicleLists();
|
||||||
}
|
}
|
||||||
|
@ -447,7 +449,7 @@ static void DrawTrainDetailsWindow(Window *w)
|
||||||
y = 57;
|
y = 57;
|
||||||
sel = w->vscroll.pos;
|
sel = w->vscroll.pos;
|
||||||
|
|
||||||
// draw the first 3 details tabs
|
/* draw the first 3 details tabs */
|
||||||
if (det_tab != 3) {
|
if (det_tab != 3) {
|
||||||
x = 1;
|
x = 1;
|
||||||
for (;;) {
|
for (;;) {
|
||||||
|
@ -470,7 +472,7 @@ static void DrawTrainDetailsWindow(Window *w)
|
||||||
default: NOT_REACHED();
|
default: NOT_REACHED();
|
||||||
case 0: TrainDetailsCargoTab( v, px, py); break;
|
case 0: TrainDetailsCargoTab( v, px, py); break;
|
||||||
case 1:
|
case 1:
|
||||||
// Only show name and value for the 'real' part
|
/* Only show name and value for the 'real' part */
|
||||||
if (!IsArticulatedPart(v)) {
|
if (!IsArticulatedPart(v)) {
|
||||||
TrainDetailsInfoTab(v, px, py);
|
TrainDetailsInfoTab(v, px, py);
|
||||||
}
|
}
|
||||||
|
@ -481,7 +483,7 @@ static void DrawTrainDetailsWindow(Window *w)
|
||||||
|
|
||||||
v = u;
|
v = u;
|
||||||
} else {
|
} else {
|
||||||
// Move to the next line
|
/* Move to the next line */
|
||||||
do {
|
do {
|
||||||
v = v->next;
|
v = v->next;
|
||||||
} while (v != NULL && IsArticulatedPart(v) && v->cargo_cap == 0);
|
} while (v != NULL && IsArticulatedPart(v) && v->cargo_cap == 0);
|
||||||
|
@ -489,7 +491,7 @@ static void DrawTrainDetailsWindow(Window *w)
|
||||||
if (v == NULL) return;
|
if (v == NULL) return;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// draw total cargo tab
|
/* draw total cargo tab */
|
||||||
DrawString(x, y + 2, STR_013F_TOTAL_CAPACITY_TEXT, 0);
|
DrawString(x, y + 2, STR_013F_TOTAL_CAPACITY_TEXT, 0);
|
||||||
for (CargoID i = 0; i < NUM_CARGO; i++) {
|
for (CargoID i = 0; i < NUM_CARGO; i++) {
|
||||||
if (max_cargo[i] > 0 && --sel < 0 && sel > -w->vscroll.cap) {
|
if (max_cargo[i] > 0 && --sel < 0 && sel > -w->vscroll.cap) {
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tree_cmd.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "bridge_map.h"
|
#include "bridge_map.h"
|
||||||
|
@ -53,7 +55,7 @@ static void PlaceTree(TileIndex tile, uint32 r)
|
||||||
if (tree != TREE_INVALID) {
|
if (tree != TREE_INVALID) {
|
||||||
MakeTree(tile, tree, GB(r, 22, 2), min(GB(r, 16, 3), 6), TREE_GROUND_GRASS, 0);
|
MakeTree(tile, tree, GB(r, 22, 2), min(GB(r, 16, 3), 6), TREE_GROUND_GRASS, 0);
|
||||||
|
|
||||||
// above snowline?
|
/* above snowline? */
|
||||||
if (_opt.landscape == LT_ARCTIC && GetTileZ(tile) > GetSnowLine()) {
|
if (_opt.landscape == LT_ARCTIC && GetTileZ(tile) > GetSnowLine()) {
|
||||||
SetTreeGroundDensity(tile, TREE_GROUND_SNOW_DESERT, 3);
|
SetTreeGroundDensity(tile, TREE_GROUND_SNOW_DESERT, 3);
|
||||||
SetTreeCounter(tile, (TreeGround)GB(r, 24, 3));
|
SetTreeCounter(tile, (TreeGround)GB(r, 24, 3));
|
||||||
|
@ -207,6 +209,7 @@ void GenerateTrees()
|
||||||
|
|
||||||
/** Plant a tree.
|
/** Plant a tree.
|
||||||
* @param tile start tile of area-drag of tree plantation
|
* @param tile start tile of area-drag of tree plantation
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 tree type, -1 means random.
|
* @param p1 tree type, -1 means random.
|
||||||
* @param p2 end tile of area-drag
|
* @param p2 end tile of area-drag
|
||||||
*/
|
*/
|
||||||
|
@ -240,7 +243,7 @@ int32 CmdPlantTree(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
switch (GetTileType(tile)) {
|
switch (GetTileType(tile)) {
|
||||||
case MP_TREES:
|
case MP_TREES:
|
||||||
// no more space for trees?
|
/* no more space for trees? */
|
||||||
if (_game_mode != GM_EDITOR && GetTreeCount(tile) == 3) {
|
if (_game_mode != GM_EDITOR && GetTreeCount(tile) == 3) {
|
||||||
msg = STR_2803_TREE_ALREADY_HERE;
|
msg = STR_2803_TREE_ALREADY_HERE;
|
||||||
continue;
|
continue;
|
||||||
|
@ -250,7 +253,7 @@ int32 CmdPlantTree(TileIndex tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
AddTreeCount(tile, 1);
|
AddTreeCount(tile, 1);
|
||||||
MarkTileDirtyByTile(tile);
|
MarkTileDirtyByTile(tile);
|
||||||
}
|
}
|
||||||
// 2x as expensive to add more trees to an existing tile
|
/* 2x as expensive to add more trees to an existing tile */
|
||||||
cost += _price.build_trees * 2;
|
cost += _price.build_trees * 2;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -622,7 +625,7 @@ void OnTick_Trees()
|
||||||
MakeTree(tile, tree, 0, 0, ct == CLEAR_ROUGH ? TREE_GROUND_ROUGH : TREE_GROUND_GRASS, 0);
|
MakeTree(tile, tree, 0, 0, ct == CLEAR_ROUGH ? TREE_GROUND_ROUGH : TREE_GROUND_GRASS, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
// byte underflow
|
/* byte underflow */
|
||||||
if (--_trees_tick_ctr != 0) return;
|
if (--_trees_tick_ctr != 0) return;
|
||||||
|
|
||||||
/* place a tree at a random spot */
|
/* place a tree at a random spot */
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tree_map.h */
|
||||||
|
|
||||||
#ifndef TREE_MAP_H
|
#ifndef TREE_MAP_H
|
||||||
#define TREE_MAP_H
|
#define TREE_MAP_H
|
||||||
|
|
||||||
|
@ -26,9 +28,9 @@ enum {
|
||||||
/* ground type, m2 bits 4...5
|
/* ground type, m2 bits 4...5
|
||||||
* valid densities (bits 6...7) in comments after the enum */
|
* valid densities (bits 6...7) in comments after the enum */
|
||||||
enum TreeGround {
|
enum TreeGround {
|
||||||
TREE_GROUND_GRASS = 0, // 0
|
TREE_GROUND_GRASS = 0, ///< 0
|
||||||
TREE_GROUND_ROUGH = 1, // 0
|
TREE_GROUND_ROUGH = 1, ///< 0
|
||||||
TREE_GROUND_SNOW_DESERT = 2 // 0-3 for snow, 3 for desert
|
TREE_GROUND_SNOW_DESERT = 2 ///< 0-3 for snow, 3 for desert
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tunnel_map.cpp */
|
||||||
|
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "openttd.h"
|
#include "openttd.h"
|
||||||
#include "tile.h"
|
#include "tile.h"
|
||||||
|
|
|
@ -1,5 +1,7 @@
|
||||||
/* $Id$ */
|
/* $Id$ */
|
||||||
|
|
||||||
|
/** @file tunnel_map.h */
|
||||||
|
|
||||||
#ifndef TUNNEL_MAP_H
|
#ifndef TUNNEL_MAP_H
|
||||||
#define TUNNEL_MAP_H
|
#define TUNNEL_MAP_H
|
||||||
|
|
||||||
|
|
|
@ -61,8 +61,9 @@ const Bridge orig_bridge[] = {
|
||||||
Bridge _bridge[MAX_BRIDGES];
|
Bridge _bridge[MAX_BRIDGES];
|
||||||
|
|
||||||
|
|
||||||
// calculate the price factor for building a long bridge.
|
/** calculate the price factor for building a long bridge.
|
||||||
// basically the cost delta is 1,1, 1, 2,2, 3,3,3, 4,4,4,4, 5,5,5,5,5, 6,6,6,6,6,6, 7,7,7,7,7,7,7, 8,8,8,8,8,8,8,8,
|
* basically the cost delta is 1,1, 1, 2,2, 3,3,3, 4,4,4,4, 5,5,5,5,5, 6,6,6,6,6,6, 7,7,7,7,7,7,7, 8,8,8,8,8,8,8,8,
|
||||||
|
*/
|
||||||
int CalcBridgeLenCostFactor(int x)
|
int CalcBridgeLenCostFactor(int x)
|
||||||
{
|
{
|
||||||
int n;
|
int n;
|
||||||
|
@ -79,11 +80,11 @@ int CalcBridgeLenCostFactor(int x)
|
||||||
|
|
||||||
#define M(x) (1 << (x))
|
#define M(x) (1 << (x))
|
||||||
enum BridgeFoundation {
|
enum BridgeFoundation {
|
||||||
// foundation, whole tile is leveled up --> 3 corners raised
|
/* foundation, whole tile is leveled up --> 3 corners raised */
|
||||||
BRIDGE_FULL_LEVELED_FOUNDATION = M(SLOPE_WSE) | M(SLOPE_NWS) | M(SLOPE_ENW) | M(SLOPE_SEN),
|
BRIDGE_FULL_LEVELED_FOUNDATION = M(SLOPE_WSE) | M(SLOPE_NWS) | M(SLOPE_ENW) | M(SLOPE_SEN),
|
||||||
// foundation, tile is partly leveled up --> 1 corner raised
|
/* foundation, tile is partly leveled up --> 1 corner raised */
|
||||||
BRIDGE_PARTLY_LEVELED_FOUNDATION = M(SLOPE_W) | M(SLOPE_S) | M(SLOPE_E) | M(SLOPE_N),
|
BRIDGE_PARTLY_LEVELED_FOUNDATION = M(SLOPE_W) | M(SLOPE_S) | M(SLOPE_E) | M(SLOPE_N),
|
||||||
// no foundations (X,Y direction)
|
/* no foundations (X,Y direction) */
|
||||||
BRIDGE_NO_FOUNDATION = M(SLOPE_FLAT) | M(SLOPE_SW) | M(SLOPE_SE) | M(SLOPE_NW) | M(SLOPE_NE),
|
BRIDGE_NO_FOUNDATION = M(SLOPE_FLAT) | M(SLOPE_SW) | M(SLOPE_SE) | M(SLOPE_NW) | M(SLOPE_NE),
|
||||||
BRIDGE_HORZ_RAMP = (BRIDGE_PARTLY_LEVELED_FOUNDATION | BRIDGE_NO_FOUNDATION) & ~M(SLOPE_FLAT)
|
BRIDGE_HORZ_RAMP = (BRIDGE_PARTLY_LEVELED_FOUNDATION | BRIDGE_NO_FOUNDATION) & ~M(SLOPE_FLAT)
|
||||||
};
|
};
|
||||||
|
@ -167,6 +168,7 @@ bool CheckBridge_Stuff(byte bridge_type, uint bridge_len)
|
||||||
|
|
||||||
/** Build a Bridge
|
/** Build a Bridge
|
||||||
* @param end_tile end tile
|
* @param end_tile end tile
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 packed start tile coords (~ dx)
|
* @param p1 packed start tile coords (~ dx)
|
||||||
* @param p2 various bitstuffed elements
|
* @param p2 various bitstuffed elements
|
||||||
* - p2 = (bit 0- 7) - bridge type (hi bh)
|
* - p2 = (bit 0- 7) - bridge type (hi bh)
|
||||||
|
@ -202,7 +204,7 @@ int32 CmdBuildBridge(TileIndex end_tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
if (p1 >= MapSize()) return CMD_ERROR;
|
if (p1 >= MapSize()) return CMD_ERROR;
|
||||||
|
|
||||||
// type of bridge
|
/* type of bridge */
|
||||||
if (HASBIT(p2, 15)) {
|
if (HASBIT(p2, 15)) {
|
||||||
railtype = INVALID_RAILTYPE; // road bridge
|
railtype = INVALID_RAILTYPE; // road bridge
|
||||||
} else {
|
} else {
|
||||||
|
@ -255,7 +257,7 @@ int32 CmdBuildBridge(TileIndex end_tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
|
|
||||||
if (z_start != z_end) return_cmd_error(STR_5009_LEVEL_LAND_OR_WATER_REQUIRED);
|
if (z_start != z_end) return_cmd_error(STR_5009_LEVEL_LAND_OR_WATER_REQUIRED);
|
||||||
|
|
||||||
// Towns are not allowed to use bridges on slopes.
|
/* Towns are not allowed to use bridges on slopes. */
|
||||||
allow_on_slopes = (!_is_old_ai_player
|
allow_on_slopes = (!_is_old_ai_player
|
||||||
&& _current_player != OWNER_TOWN && _patches.build_on_slopes);
|
&& _current_player != OWNER_TOWN && _patches.build_on_slopes);
|
||||||
|
|
||||||
|
@ -315,7 +317,7 @@ int32 CmdBuildBridge(TileIndex end_tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
if (CmdFailed(ret)) return ret;
|
if (CmdFailed(ret)) return ret;
|
||||||
cost += ret;
|
cost += ret;
|
||||||
|
|
||||||
// false - end tile slope check
|
/* false - end tile slope check */
|
||||||
terraformcost = CheckBridgeSlopeSouth(direction, tileh_end);
|
terraformcost = CheckBridgeSlopeSouth(direction, tileh_end);
|
||||||
if (CmdFailed(terraformcost) || (terraformcost != 0 && !allow_on_slopes))
|
if (CmdFailed(terraformcost) || (terraformcost != 0 && !allow_on_slopes))
|
||||||
return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION);
|
return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION);
|
||||||
|
@ -439,6 +441,7 @@ not_valid_below:;
|
||||||
|
|
||||||
/** Build Tunnel.
|
/** Build Tunnel.
|
||||||
* @param tile start tile of tunnel
|
* @param tile start tile of tunnel
|
||||||
|
* @param flags type of operation
|
||||||
* @param p1 railtype, 0x200 for road tunnel
|
* @param p1 railtype, 0x200 for road tunnel
|
||||||
* @param p2 unused
|
* @param p2 unused
|
||||||
*/
|
*/
|
||||||
|
@ -496,10 +499,10 @@ int32 CmdBuildTunnel(TileIndex start_tile, uint32 flags, uint32 p1, uint32 p2)
|
||||||
/* Add the cost of the entrance */
|
/* Add the cost of the entrance */
|
||||||
cost += _price.build_tunnel + ret;
|
cost += _price.build_tunnel + ret;
|
||||||
|
|
||||||
// if the command fails from here on we want the end tile to be highlighted
|
/* if the command fails from here on we want the end tile to be highlighted */
|
||||||
_build_tunnel_endtile = end_tile;
|
_build_tunnel_endtile = end_tile;
|
||||||
|
|
||||||
// slope of end tile must be complementary to the slope of the start tile
|
/* slope of end tile must be complementary to the slope of the start tile */
|
||||||
if (end_tileh != ComplementSlope(start_tileh)) {
|
if (end_tileh != ComplementSlope(start_tileh)) {
|
||||||
ret = DoCommand(end_tile, end_tileh & start_tileh, 0, flags, CMD_TERRAFORM_LAND);
|
ret = DoCommand(end_tile, end_tileh & start_tileh, 0, flags, CMD_TERRAFORM_LAND);
|
||||||
if (CmdFailed(ret)) return_cmd_error(STR_5005_UNABLE_TO_EXCAVATE_LAND);
|
if (CmdFailed(ret)) return_cmd_error(STR_5005_UNABLE_TO_EXCAVATE_LAND);
|
||||||
|
@ -591,12 +594,12 @@ static int32 DoClearTunnel(TileIndex tile, uint32 flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (flags & DC_EXEC) {
|
if (flags & DC_EXEC) {
|
||||||
// We first need to request the direction before calling DoClearSquare
|
/* We first need to request the direction before calling DoClearSquare
|
||||||
// else the direction is always 0.. dah!! ;)
|
* else the direction is always 0.. dah!! ;) */
|
||||||
DiagDirection dir = GetTunnelDirection(tile);
|
DiagDirection dir = GetTunnelDirection(tile);
|
||||||
Track track;
|
Track track;
|
||||||
|
|
||||||
// Adjust the town's player rating. Do this before removing the tile owner info.
|
/* Adjust the town's player rating. Do this before removing the tile owner info. */
|
||||||
if (IsTileOwner(tile, OWNER_TOWN) && _game_mode != GM_EDITOR)
|
if (IsTileOwner(tile, OWNER_TOWN) && _game_mode != GM_EDITOR)
|
||||||
ChangeTownRating(t, RATING_TUNNEL_BRIDGE_DOWN_STEP, RATING_TUNNEL_BRIDGE_MINIMUM);
|
ChangeTownRating(t, RATING_TUNNEL_BRIDGE_DOWN_STEP, RATING_TUNNEL_BRIDGE_MINIMUM);
|
||||||
|
|
||||||
|
@ -661,8 +664,8 @@ static int32 DoClearBridge(TileIndex tile, uint32 flags)
|
||||||
TileIndex c;
|
TileIndex c;
|
||||||
Track track;
|
Track track;
|
||||||
|
|
||||||
//checks if the owner is town then decrease town rating by RATING_TUNNEL_BRIDGE_DOWN_STEP until
|
/* checks if the owner is town then decrease town rating by RATING_TUNNEL_BRIDGE_DOWN_STEP until
|
||||||
// you have a "Poor" (0) town rating
|
* you have a "Poor" (0) town rating */
|
||||||
if (IsTileOwner(tile, OWNER_TOWN) && _game_mode != GM_EDITOR)
|
if (IsTileOwner(tile, OWNER_TOWN) && _game_mode != GM_EDITOR)
|
||||||
ChangeTownRating(t, RATING_TUNNEL_BRIDGE_DOWN_STEP, RATING_TUNNEL_BRIDGE_MINIMUM);
|
ChangeTownRating(t, RATING_TUNNEL_BRIDGE_DOWN_STEP, RATING_TUNNEL_BRIDGE_MINIMUM);
|
||||||
|
|
||||||
|
@ -717,7 +720,7 @@ int32 DoConvertTunnelBridgeRail(TileIndex tile, RailType totype, bool exec)
|
||||||
|
|
||||||
if (GetRailType(tile) == totype) return CMD_ERROR;
|
if (GetRailType(tile) == totype) return CMD_ERROR;
|
||||||
|
|
||||||
// 'hidden' elrails can't be downgraded to normal rail when elrails are disabled
|
/* 'hidden' elrails can't be downgraded to normal rail when elrails are disabled */
|
||||||
if (_patches.disable_elrails && totype == RAILTYPE_RAIL && GetRailType(tile) == RAILTYPE_ELECTRIC) return CMD_ERROR;
|
if (_patches.disable_elrails && totype == RAILTYPE_RAIL && GetRailType(tile) == RAILTYPE_ELECTRIC) return CMD_ERROR;
|
||||||
|
|
||||||
endtile = CheckTunnelBusy(tile, &length);
|
endtile = CheckTunnelBusy(tile, &length);
|
||||||
|
@ -829,7 +832,7 @@ uint GetBridgeFoundation(Slope tileh, Axis axis)
|
||||||
|
|
||||||
if (HASBIT(BRIDGE_FULL_LEVELED_FOUNDATION, tileh)) return tileh;
|
if (HASBIT(BRIDGE_FULL_LEVELED_FOUNDATION, tileh)) return tileh;
|
||||||
|
|
||||||
// inclined sloped building
|
/* inclined sloped building */
|
||||||
switch (tileh) {
|
switch (tileh) {
|
||||||
case SLOPE_W:
|
case SLOPE_W:
|
||||||
case SLOPE_STEEP_W: i = 0; break;
|
case SLOPE_STEEP_W: i = 0; break;
|
||||||
|
@ -850,6 +853,7 @@ uint GetBridgeFoundation(Slope tileh, Axis axis)
|
||||||
* For tunnels, this is rather simple, as you only needa draw the entrance.
|
* For tunnels, this is rather simple, as you only needa draw the entrance.
|
||||||
* Bridges are a bit more complex. base_offset is where the sprite selection comes into play
|
* Bridges are a bit more complex. base_offset is where the sprite selection comes into play
|
||||||
* and it works a bit like a bitmask.<p> For bridge heads:
|
* and it works a bit like a bitmask.<p> For bridge heads:
|
||||||
|
* @param ti TileInfo of the structure to draw
|
||||||
* <ul><li>Bit 0: direction</li>
|
* <ul><li>Bit 0: direction</li>
|
||||||
* <li>Bit 1: northern or southern heads</li>
|
* <li>Bit 1: northern or southern heads</li>
|
||||||
* <li>Bit 2: Set if the bridge head is sloped</li>
|
* <li>Bit 2: Set if the bridge head is sloped</li>
|
||||||
|
@ -884,7 +888,7 @@ static void DrawTile_TunnelBridge(TileInfo *ti)
|
||||||
|
|
||||||
if (GetBridgeTransportType(ti->tile) == TRANSPORT_RAIL) {
|
if (GetBridgeTransportType(ti->tile) == TRANSPORT_RAIL) {
|
||||||
base_offset = GetRailTypeInfo(GetRailType(ti->tile))->bridge_offset;
|
base_offset = GetRailTypeInfo(GetRailType(ti->tile))->bridge_offset;
|
||||||
assert(base_offset != 8); /* This one is used for roads */
|
assert(base_offset != 8); // This one is used for roads
|
||||||
} else {
|
} else {
|
||||||
base_offset = 8;
|
base_offset = 8;
|
||||||
}
|
}
|
||||||
|
@ -897,7 +901,7 @@ static void DrawTile_TunnelBridge(TileInfo *ti)
|
||||||
if (f != 0) DrawFoundation(ti, f);
|
if (f != 0) DrawFoundation(ti, f);
|
||||||
}
|
}
|
||||||
|
|
||||||
// HACK Wizardry to convert the bridge ramp direction into a sprite offset
|
/* HACK Wizardry to convert the bridge ramp direction into a sprite offset */
|
||||||
base_offset += (6 - GetBridgeRampDirection(ti->tile)) % 4;
|
base_offset += (6 - GetBridgeRampDirection(ti->tile)) % 4;
|
||||||
|
|
||||||
if (ti->tileh == SLOPE_FLAT) base_offset += 4; // sloped bridge head
|
if (ti->tileh == SLOPE_FLAT) base_offset += 4; // sloped bridge head
|
||||||
|
@ -915,7 +919,7 @@ static void DrawTile_TunnelBridge(TileInfo *ti)
|
||||||
|
|
||||||
image = psid->sprite;
|
image = psid->sprite;
|
||||||
|
|
||||||
// draw ramp
|
/* draw ramp */
|
||||||
if (_display_opt & DO_TRANS_BUILDINGS) {
|
if (_display_opt & DO_TRANS_BUILDINGS) {
|
||||||
SETBIT(image, PALETTE_MODIFIER_TRANSPARENT);
|
SETBIT(image, PALETTE_MODIFIER_TRANSPARENT);
|
||||||
pal = PALETTE_TO_TRANSPARENT;
|
pal = PALETTE_TO_TRANSPARENT;
|
||||||
|
@ -1030,7 +1034,7 @@ void DrawBridgeMiddle(const TileInfo* ti)
|
||||||
pal = psid->pal;
|
pal = psid->pal;
|
||||||
}
|
}
|
||||||
|
|
||||||
// draw roof, the component of the bridge which is logically between the vehicle and the camera
|
/* draw roof, the component of the bridge which is logically between the vehicle and the camera */
|
||||||
if (axis == AXIS_X) {
|
if (axis == AXIS_X) {
|
||||||
y += 12;
|
y += 12;
|
||||||
if (image & SPRITE_MASK) AddSortableSpriteToDraw(image, pal, x, y, 16, 1, 0x28, z);
|
if (image & SPRITE_MASK) AddSortableSpriteToDraw(image, pal, x, y, 16, 1, 0x28, z);
|
||||||
|
@ -1043,7 +1047,7 @@ void DrawBridgeMiddle(const TileInfo* ti)
|
||||||
|
|
||||||
psid++;
|
psid++;
|
||||||
if (ti->z + 5 == z) {
|
if (ti->z + 5 == z) {
|
||||||
// draw poles below for small bridges
|
/* draw poles below for small bridges */
|
||||||
if (psid->sprite != 0) {
|
if (psid->sprite != 0) {
|
||||||
image = psid->sprite;
|
image = psid->sprite;
|
||||||
if (_display_opt & DO_TRANS_BUILDINGS) {
|
if (_display_opt & DO_TRANS_BUILDINGS) {
|
||||||
|
@ -1056,7 +1060,7 @@ void DrawBridgeMiddle(const TileInfo* ti)
|
||||||
DrawGroundSpriteAt(image, pal, x, y, z);
|
DrawGroundSpriteAt(image, pal, x, y, z);
|
||||||
}
|
}
|
||||||
} else if (_patches.bridge_pillars) {
|
} else if (_patches.bridge_pillars) {
|
||||||
// draw pillars below for high bridges
|
/* draw pillars below for high bridges */
|
||||||
DrawBridgePillars(psid, ti, axis, type, x, y, z);
|
DrawBridgePillars(psid, ti, axis, type, x, y, z);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1073,13 +1077,13 @@ static uint GetSlopeZ_TunnelBridge(TileIndex tile, uint x, uint y)
|
||||||
if (IsTunnel(tile)) {
|
if (IsTunnel(tile)) {
|
||||||
uint pos = (DiagDirToAxis(GetTunnelDirection(tile)) == AXIS_X ? y : x);
|
uint pos = (DiagDirToAxis(GetTunnelDirection(tile)) == AXIS_X ? y : x);
|
||||||
|
|
||||||
// In the tunnel entrance?
|
/* In the tunnel entrance? */
|
||||||
if (5 <= pos && pos <= 10) return z;
|
if (5 <= pos && pos <= 10) return z;
|
||||||
} else {
|
} else {
|
||||||
DiagDirection dir = GetBridgeRampDirection(tile);
|
DiagDirection dir = GetBridgeRampDirection(tile);
|
||||||
uint pos = (DiagDirToAxis(dir) == AXIS_X ? y : x);
|
uint pos = (DiagDirToAxis(dir) == AXIS_X ? y : x);
|
||||||
|
|
||||||
// On the bridge ramp?
|
/* On the bridge ramp? */
|
||||||
if (5 <= pos && pos <= 10) {
|
if (5 <= pos && pos <= 10) {
|
||||||
uint delta;
|
uint delta;
|
||||||
|
|
||||||
|
@ -1302,7 +1306,7 @@ static uint32 VehicleEnter_TunnelBridge(Vehicle *v, TileIndex tile, int x, int y
|
||||||
dir = GetTunnelDirection(tile);
|
dir = GetTunnelDirection(tile);
|
||||||
vdir = DirToDiagDir(v->direction);
|
vdir = DirToDiagDir(v->direction);
|
||||||
|
|
||||||
// Enter tunnel?
|
/* Enter tunnel? */
|
||||||
if (v->u.road.state != RVSB_WORMHOLE && dir == vdir) {
|
if (v->u.road.state != RVSB_WORMHOLE && dir == vdir) {
|
||||||
if (fc == _tunnel_fractcoord_4[dir] ||
|
if (fc == _tunnel_fractcoord_4[dir] ||
|
||||||
fc == _tunnel_fractcoord_5[dir]) {
|
fc == _tunnel_fractcoord_5[dir]) {
|
||||||
|
|
Loading…
Reference in New Issue