mirror of
https://github.com/OpenTTD/OpenTTD.git
synced 2026-07-21 01:59:44 +00:00
Compare commits
1100 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 77a1900374 | |||
| 6fc3080fc3 | |||
| 1f2714ca79 | |||
| 024db8d058 | |||
| 896551850a | |||
| f2448ebfd4 | |||
| 9d07426a29 | |||
| 4e2bb34be3 | |||
| 0f535026cf | |||
| 9fd6b1009e | |||
| 822afdcecd | |||
| 58f5dbd365 | |||
| a092ee463f | |||
| e2df07ec05 | |||
| e2dda7bce6 | |||
| 5e1e902600 | |||
| c8dd64bdbc | |||
| 7d03773383 | |||
| 2f668b8669 | |||
| 876813cd9d | |||
| 61a7b45dd9 | |||
| 8c7e594b08 | |||
| b7beb3d87d | |||
| e6d16d17dc | |||
| f3b0de85bf | |||
| b2fac2e99f | |||
| f7603ba3ac | |||
| ddfe8f608f | |||
| 8b8ef85ccb | |||
| 524934bbf6 | |||
| 132125de77 | |||
| 9d11d11d68 | |||
| 98c62ba8e0 | |||
| 4e09974975 | |||
| bb49381cd3 | |||
| 20538e9b40 | |||
| 2de4331931 | |||
| 5fed533ce8 | |||
| f4e7d3203a | |||
| ff8b3f980f | |||
| 051c5da378 | |||
| 0e41c3dc58 | |||
| 8931913884 | |||
| a235c72b0d | |||
| 3924b84744 | |||
| 691c93ee99 | |||
| 0bcdd910f9 | |||
| 0d010c97e6 | |||
| 585b47b6c5 | |||
| 9c1ad5d610 | |||
| b3a2f09ae9 | |||
| d6933998e4 | |||
| 7e604b72db | |||
| d16dea5859 | |||
| 571bbc06d7 | |||
| a6756ccf21 | |||
| 1a2fac805c | |||
| 6fb36934a8 | |||
| 663b1c6c00 | |||
| 452ae7470b | |||
| c8a2c7ae94 | |||
| 070edf2f73 | |||
| 2612d48550 | |||
| bc450bbc9a | |||
| fa735869e1 | |||
| 8721b05453 | |||
| 952f246433 | |||
| a8758cbf5e | |||
| 2b287a9e72 | |||
| 0d80c70b5f | |||
| 78fa9c7393 | |||
| 42a9353ae2 | |||
| a4807caf6a | |||
| ec7d2fbb39 | |||
| 098300cc7d | |||
| 0f28e74e3e | |||
| 70efa805cb | |||
| 93082104dd | |||
| 188352ea3e | |||
| cc7a9d1ce6 | |||
| 979a8fea86 | |||
| 128249e63e | |||
| a1342c9d52 | |||
| d13763a9c4 | |||
| d22e8c636d | |||
| 935ab76f0f | |||
| 016c498216 | |||
| 102f9be296 | |||
| e78997fdfd | |||
| 6971aee967 | |||
| a292621b14 | |||
| 26226f1d43 | |||
| d161a8a330 | |||
| 27954279d6 | |||
| e35a131153 | |||
| b87b5f1187 | |||
| 8403f2bd33 | |||
| 887ad00dff | |||
| 5988069372 | |||
| f1b53b113f | |||
| 2a746ffa2d | |||
| 90aff7a026 | |||
| 28ca056d56 | |||
| 2067b2e7b4 | |||
| be288e4d1b | |||
| 7c5a58bbad | |||
| 019e794234 | |||
| 4bf1741783 | |||
| de34ab97a2 | |||
| e81c316134 | |||
| 18de531671 | |||
| 793a0099d4 | |||
| c86e6e008d | |||
| 473b3072ea | |||
| 1cfabfbb09 | |||
| 015db8a461 | |||
| e8c871a603 | |||
| e373bd02ba | |||
| 835cd6ea28 | |||
| 79ce0def50 | |||
| 4cda74cb31 | |||
| efd3d42107 | |||
| 10a2787fd5 | |||
| b542f784f9 | |||
| 54501dc6df | |||
| 183f6f6d07 | |||
| b23ffe4045 | |||
| 71fb252a8a | |||
| 08a3e346cd | |||
| 72b70fa042 | |||
| af70b49bf7 | |||
| 5ac1a89f92 | |||
| e272b03fee | |||
| 980e8f525b | |||
| 1d88dfd460 | |||
| 4b464093e7 | |||
| 911a8aa08d | |||
| f55153ce3c | |||
| eeeebf9f6d | |||
| 5353d05865 | |||
| 608e9a7203 | |||
| 2a94a64711 | |||
| 10c6d4c738 | |||
| 6820aada04 | |||
| 246c126d25 | |||
| 1ffc700797 | |||
| a4de62577d | |||
| d6bfff85cb | |||
| 37c3cd2e5b | |||
| 7e5da7d8b2 | |||
| 0f03d94fbe | |||
| 6319e8910f | |||
| 8c707f6211 | |||
| fad5dcffda | |||
| 878c868f02 | |||
| a857706145 | |||
| 8ffe9da482 | |||
| 19d0517c71 | |||
| fa78c057ee | |||
| e5e15808f1 | |||
| c11fb56bf7 | |||
| f2db7e7245 | |||
| 955f06b9ac | |||
| 9b0b2e8d2e | |||
| 5df6a12ed3 | |||
| 671c085206 | |||
| 9abf05dcef | |||
| 128317d3ec | |||
| be01586049 | |||
| 15220f3578 | |||
| 97e9141c65 | |||
| a24de0ba3b | |||
| 7142512754 | |||
| db03c5d5e8 | |||
| 0f41b99c5e | |||
| 8f873d4ece | |||
| bb90e51ac5 | |||
| e744bbee59 | |||
| a7793e97a5 | |||
| e66db9c6d4 | |||
| 3532b91eef | |||
| 3561a3068e | |||
| b06b3e2ca2 | |||
| 2956b119b2 | |||
| bd909b0952 | |||
| 592aee1e27 | |||
| 28fe368b7f | |||
| ca52ec33b2 | |||
| 6884453b66 | |||
| 531073bea0 | |||
| f94da63a8d | |||
| f6330faead | |||
| ec274769b9 | |||
| 560e92aa4a | |||
| cc2b51320f | |||
| 4634243110 | |||
| bf98086de8 | |||
| 23bfc03054 | |||
| ce94c90a7b | |||
| d8727d7fcd | |||
| 56998926e7 | |||
| 2a60262c99 | |||
| 560a4a9c4a | |||
| 04f39ef749 | |||
| 07c3abfe92 | |||
| 2dc8e0c3d9 | |||
| f4e1f18a15 | |||
| ec2675c2c5 | |||
| 42d8e8410b | |||
| be65f908c8 | |||
| 0de260182b | |||
| ba7cc8e190 | |||
| 809b03c81a | |||
| 6a6e145010 | |||
| f1877b3fe9 | |||
| b6ca90e021 | |||
| c872ac4eb4 | |||
| e9e1c4de53 | |||
| 26a5e120e8 | |||
| 6cfdfcc4ba | |||
| 111e5ef0fd | |||
| 578883266f | |||
| 05fbf0ada5 | |||
| 2148e1fa89 | |||
| 1c57091230 | |||
| 54cb542e1d | |||
| bfc8b30325 | |||
| 4bc7265b03 | |||
| 4f9bb11846 | |||
| af87b2916a | |||
| 686da2f4e1 | |||
| a3d142ed57 | |||
| 1a93bcb5bb | |||
| 414481cdd8 | |||
| 0f2a0df165 | |||
| 2946f3c1f9 | |||
| 961b71f434 | |||
| 8277a0651e | |||
| b860d1194d | |||
| bfeddf1db1 | |||
| 214ed794a1 | |||
| 7460ecd42a | |||
| ea9cb3ee5b | |||
| 480b1575fe | |||
| 6ed22fb3d4 | |||
| fde99748c0 | |||
| 4191adb92c | |||
| 44c70c24d3 | |||
| c963c59b67 | |||
| 2eb1c8a215 | |||
| 4b4d171ca5 | |||
| a2ae8a707c | |||
| 87f54ebf92 | |||
| 9a381f4d5d | |||
| 10ce514f59 | |||
| 728aba9d7c | |||
| a090886073 | |||
| 732e71228b | |||
| aa39eb5a9a | |||
| 8733f49e88 | |||
| b8f8f3869d | |||
| 08b990886d | |||
| 4927236912 | |||
| f6ddaf6a23 | |||
| 4845ff063b | |||
| 6a4ba84320 | |||
| 4d2c4c5d8a | |||
| 31f218fdf9 | |||
| c7f3192f6b | |||
| f2b344084a | |||
| c7683a63ce | |||
| 24eda23b80 | |||
| e472fed85a | |||
| 22a4679837 | |||
| 40ec9bb123 | |||
| a87ff2dc88 | |||
| cac9cfe249 | |||
| eba1f68439 | |||
| 3e702afc08 | |||
| 754d26407e | |||
| 5cb9de35d1 | |||
| c1b012171d | |||
| b739674307 | |||
| 89cfe202b8 | |||
| 1bffec2c27 | |||
| f750a773a4 | |||
| ec57ef78a2 | |||
| 8cebe2f607 | |||
| 272d63b062 | |||
| d177e5da67 | |||
| aaed2a41a0 | |||
| 7a7847ed61 | |||
| cc61dd4890 | |||
| 06a708b7b3 | |||
| d76fc8d7d1 | |||
| ce9cbb9c47 | |||
| 8d57bfc921 | |||
| 1806293e46 | |||
| 62b2b4613f | |||
| 784d41b650 | |||
| 1d109214bc | |||
| 3bf8d2ccbb | |||
| 66d44766a7 | |||
| b5dafb8f94 | |||
| 24f857ed5e | |||
| 9f8c5d8fd2 | |||
| b9729fb72e | |||
| 1b0091e0d2 | |||
| 8658560229 | |||
| 7b7593d092 | |||
| f7abff5f96 | |||
| d8b56c123e | |||
| 5fa6b7eb06 | |||
| 6124ee0974 | |||
| 833032adc0 | |||
| 357aba7475 | |||
| eeade69786 | |||
| 8a05c1e31d | |||
| 4a14a586e2 | |||
| ee15e3de13 | |||
| 59e885c2bf | |||
| 422bea5a0b | |||
| b3056bc799 | |||
| a7fe1495cd | |||
| ff8223150a | |||
| b1075ca7a4 | |||
| 1c867927a3 | |||
| 53ddd87dc2 | |||
| a20b9c2240 | |||
| 7d888a5715 | |||
| 350f0f2cdb | |||
| 5e278b7ec3 | |||
| 5481dcd191 | |||
| 723e789b2f | |||
| 947fc8a8ec | |||
| 7304bbe500 | |||
| f816b74536 | |||
| 8bcfa23d29 | |||
| bc25cd89bf | |||
| 220b4c27c1 | |||
| b58cfc36da | |||
| de76933337 | |||
| 63842939ed | |||
| b6d1f81635 | |||
| 58785904a6 | |||
| 49335b4daa | |||
| 0412040bcc | |||
| 267314b4d0 | |||
| d86829d0e0 | |||
| 7d4d13df35 | |||
| c8ea743e47 | |||
| d42b7649a4 | |||
| a21762980d | |||
| 62d7732273 | |||
| 081bae03d9 | |||
| 04134d1481 | |||
| c8ea909811 | |||
| ea720689a3 | |||
| b950fee119 | |||
| 80af1ebca8 | |||
| 01b6109751 | |||
| 7c40462d24 | |||
| e80d448478 | |||
| 689006ee73 | |||
| 9d786d3e53 | |||
| b850806205 | |||
| 9bcf0cd1e2 | |||
| 422a8654e3 | |||
| 94e09ba605 | |||
| 7e03f1cc3c | |||
| 59913ae719 | |||
| 6390bcc636 | |||
| f6fdb150e7 | |||
| 8ea1639603 | |||
| 35217570a9 | |||
| 682b9ee8e4 | |||
| 95d1c43565 | |||
| 7298b0b31b | |||
| c1c086d9a0 | |||
| 1a2ad83b00 | |||
| 328158395b | |||
| 1ef02f8cca | |||
| c406487b14 | |||
| 6c4b37c9fe | |||
| b5583659e0 | |||
| 6d41c23cf2 | |||
| 76f4c5b6f9 | |||
| 187ea08e1d | |||
| 9e957ff80b | |||
| 9bbf8ea9d0 | |||
| f561993112 | |||
| 1cc5379706 | |||
| 203726ed34 | |||
| b97473e874 | |||
| 477aa9f69c | |||
| 66e688cba3 | |||
| 7cace07e01 | |||
| bf467bd99c | |||
| e0dd7efc82 | |||
| f5ea31b9da | |||
| 47137cefb7 | |||
| 2cc2154ad2 | |||
| 0163870006 | |||
| 5565abb871 | |||
| 8bf11c2e41 | |||
| 2b91f55b32 | |||
| 6a5c0fabdd | |||
| d5eb4183b8 | |||
| 4253f3d330 | |||
| afc9951648 | |||
| 4fb76f67ae | |||
| e611fee4e5 | |||
| ece9b9b2b6 | |||
| 5f604ec63a | |||
| 758ae7e8f6 | |||
| cb67ee9bf5 | |||
| ec66b1ca3b | |||
| be984d9bcc | |||
| 8419473453 | |||
| f3de172560 | |||
| d4752ba0da | |||
| d4463b4b95 | |||
| 6bf4e4af3c | |||
| 23ecc82ad3 | |||
| b85da4fef2 | |||
| 60882b29c8 | |||
| 9314ea877f | |||
| 0834a88a12 | |||
| b537cc6618 | |||
| 66bf4f863d | |||
| ab657338ec | |||
| d52bf846f3 | |||
| d5042d4ab2 | |||
| ab41ccb23c | |||
| 5c3625b88f | |||
| f97d1274bc | |||
| 1667628659 | |||
| 67741ceace | |||
| 7520ef8f33 | |||
| d37639ac3e | |||
| 03e947cbfe | |||
| 5551b423fc | |||
| 0321dc9fc5 | |||
| c78e87d4da | |||
| d678a12445 | |||
| 9fea263c77 | |||
| 6fb7381efa | |||
| 76db75d81a | |||
| cafd3528a4 | |||
| 7ba69ad146 | |||
| 9134e19d7e | |||
| 3397e202c8 | |||
| 2b44da199c | |||
| 37af5bc475 | |||
| 9666e753fb | |||
| 6006aa1a04 | |||
| ae4a1f3675 | |||
| 102cf2615f | |||
| abe60acbbb | |||
| c655e13e92 | |||
| d1591e864d | |||
| 9fabe008a0 | |||
| c3a73d4047 | |||
| 8bd4a63c47 | |||
| 01559c99b1 | |||
| db3b1228bf | |||
| b0a365ee67 | |||
| a3d40a29fc | |||
| e8fac6c6cb | |||
| c294de06b9 | |||
| 4fe06ceecc | |||
| adc5c1230f | |||
| 0cc45ecd8e | |||
| eb1d025d08 | |||
| ed8c9c91d6 | |||
| af5b74f0ed | |||
| f6bda82806 | |||
| f8d1267d71 | |||
| e33faa5ed5 | |||
| 3a964862f7 | |||
| ce1c72cf6e | |||
| 6249dd46ad | |||
| 5f3bb18eb7 | |||
| ff30404170 | |||
| 50f1a93664 | |||
| fbf06041ca | |||
| 2314431a59 | |||
| c76f01b6ff | |||
| d28067445a | |||
| 23838df7fa | |||
| 269627b0ba | |||
| c2c865e4b9 | |||
| 03ad234d47 | |||
| c02b1d555d | |||
| 47de27ab69 | |||
| 5dad0588df | |||
| 1b16f210c2 | |||
| b1e6b54f94 | |||
| d5d8d29c9f | |||
| 35ce780bb6 | |||
| 7ee0b8ac86 | |||
| 9c2700b14c | |||
| 313fcfbd83 | |||
| afcb9f0d60 | |||
| eeeeecb030 | |||
| e380abec97 | |||
| 02c2de2a67 | |||
| 1195076373 | |||
| 4d8c903d62 | |||
| 5676cc32b4 | |||
| 2f0616e9f2 | |||
| a3b3c3cf31 | |||
| 3d197e0861 | |||
| 8e6a911700 | |||
| 3097ee2429 | |||
| 72ef17dace | |||
| c930f8f8c0 | |||
| 4797310f91 | |||
| 2525e1d507 | |||
| 180997534c | |||
| 1419244551 | |||
| e9401f09a7 | |||
| 7164ff86f9 | |||
| db31fe8e15 | |||
| 2131f68ae2 | |||
| 1bf06d7da4 | |||
| 236abb6a6c | |||
| 2e87864d0b | |||
| 42813c5426 | |||
| b84e36d717 | |||
| 02472528ad | |||
| c5fa3848f6 | |||
| 802edd7f0d | |||
| aa08027ab3 | |||
| e78d41bbb2 | |||
| ffd044c5e8 | |||
| b0ddaae4af | |||
| 08e0769967 | |||
| 8894b930ae | |||
| edb56c2c46 | |||
| 2c89b0f539 | |||
| 287684e953 | |||
| 9de2c05c56 | |||
| 0fe36a6900 | |||
| 04f051e423 | |||
| 2e0e932e9d | |||
| cd54bf48d1 | |||
| a744b15907 | |||
| b45ab0fab4 | |||
| 4b59946ffe | |||
| 5d3f87bcd8 | |||
| 45ca3b6336 | |||
| d73d12ae8a | |||
| 73662f2fcb | |||
| 991d5c6234 | |||
| e39bf0dc34 | |||
| 8328bff7bf | |||
| 01d83166c7 | |||
| 948e470b3a | |||
| 2bc18c456f | |||
| 5b0a5c70a9 | |||
| 9a2ee23c98 | |||
| e2000ab858 | |||
| 864cb3fa11 | |||
| 3ace3769c9 | |||
| 3dd2dab7e9 | |||
| 828e7ed3e7 | |||
| 92270500e9 | |||
| d05f504c01 | |||
| a181446829 | |||
| ae356b641d | |||
| 6a69687ea1 | |||
| 3fb5aa8e23 | |||
| 9d8a39a3f6 | |||
| 74f0c8b55a | |||
| a02ee8ffda | |||
| d975abc96c | |||
| 70c07d13be | |||
| abb034c2cd | |||
| 175b2cd12a | |||
| 7e84d8b295 | |||
| 1677748d4d | |||
| ffdefbdee2 | |||
| 8b85cf53e5 | |||
| a38d2f15b7 | |||
| f914a7eca6 | |||
| 51c2ef8685 | |||
| b01c951224 | |||
| 65bdb2ce67 | |||
| b45aeb5c36 | |||
| 9d9ee2fe56 | |||
| a2a15784ac | |||
| ad4243ab7d | |||
| 4a1f46a99a | |||
| 1c686229af | |||
| 7a184a0ea3 | |||
| ae49d487cc | |||
| c1f4acd4a0 | |||
| 2080cf991f | |||
| 8b3c50147e | |||
| 01f0af5189 | |||
| 67a1507b83 | |||
| 1c3958c8fc | |||
| 0c7af4a5ad | |||
| 1637df1788 | |||
| 7e0c06e018 | |||
| 9ee5d61b73 | |||
| 52c859cbe8 | |||
| d057d8b366 | |||
| 19f5036c46 | |||
| 26d24f64fc | |||
| bdd5d4ebb1 | |||
| 38f344b351 | |||
| 302055fc15 | |||
| d7eaf35357 | |||
| bdff0fa2d2 | |||
| 7e702e2d50 | |||
| 732acc8ead | |||
| 235d84583f | |||
| 61e97e733d | |||
| d1c5128c42 | |||
| e16ae164af | |||
| 038501e174 | |||
| bfe8f13a8a | |||
| ecf20af742 | |||
| f7593f1b99 | |||
| 4582eb85a2 | |||
| 042f079b8d | |||
| 8f398f2f50 | |||
| bed459d5d3 | |||
| e42b560049 | |||
| b67af2df3e | |||
| a837d74ae6 | |||
| 062ed26b4d | |||
| a7e4057d2d | |||
| af819c3822 | |||
| 47e28d9152 | |||
| 129898cd77 | |||
| 64bf2a4f29 | |||
| b0d4e391da | |||
| b101846d3b | |||
| 0b6864b589 | |||
| 3f39db10d7 | |||
| 14e80ca159 | |||
| 59da8350c1 | |||
| 2b4e85db0b | |||
| dc20e0ae81 | |||
| dd03e018b5 | |||
| bb3ab916b3 | |||
| 3ff46bd8ba | |||
| a587c38864 | |||
| 73d0f36175 | |||
| 5d5a7c48ee | |||
| b0f307365a | |||
| 03e860d06d | |||
| 3b6b3af629 | |||
| ed8e2bac04 | |||
| ddb58492f3 | |||
| baca040df0 | |||
| 4f15ada6cd | |||
| eb826dfb66 | |||
| 747a0f6a55 | |||
| a8e53be6b9 | |||
| c78af95d1d | |||
| 4696ef802a | |||
| 4f9b0d5f29 | |||
| a86e9689df | |||
| 647fe2e866 | |||
| d327ab1d3e | |||
| 9470fdbdb2 | |||
| 570c5794eb | |||
| ec8f481311 | |||
| 91d21d1a1a | |||
| 076f7ada6b | |||
| e4cad82b00 | |||
| 1d527c58cb | |||
| 017b72d98a | |||
| 124b352862 | |||
| 0be9459ece | |||
| e44b9934b1 | |||
| bc3a8cbdc8 | |||
| df5e328f37 | |||
| de298f9250 | |||
| 517619ac35 | |||
| 09deb41e36 | |||
| e0cf20441f | |||
| 9a6975504b | |||
| 66fa62b3ea | |||
| 29564f9fcf | |||
| 91353c841f | |||
| e06d017b91 | |||
| 211280ab0e | |||
| 0226e0799d | |||
| 49c399fa83 | |||
| fc5e2d4861 | |||
| fcf5ace08f | |||
| 132ce0a598 | |||
| 4190e5581d | |||
| 1adb0e868c | |||
| 42ec43e4b2 | |||
| 74d4aff64b | |||
| de45efa479 | |||
| ed2f5d02c8 | |||
| 11a70c5e91 | |||
| 773dedfd03 | |||
| 546c34f2e5 | |||
| 50e41dc1d1 | |||
| a2c42e06ed | |||
| 4761d92399 | |||
| 2f54ad9310 | |||
| b629745c16 | |||
| 9b676d2cd9 | |||
| 79620db9be | |||
| 24986e9144 | |||
| bb1e1f2b5f | |||
| 3a162799fd | |||
| 1736566e22 | |||
| 3868b151a9 | |||
| 12b5dcb1b8 | |||
| f57d263d83 | |||
| 6abf8f89a2 | |||
| f359d1a394 | |||
| 1a5de9ff9b | |||
| 0432a02054 | |||
| 30a5f299f8 | |||
| 79292d193e | |||
| a2a5593fcc | |||
| 8677020a8b | |||
| 177fa1d163 | |||
| 64ac1a6414 | |||
| ff61e34d6c | |||
| 04f4d8237b | |||
| 139f0c95ca | |||
| 727dea5824 | |||
| 4a4829fa0e | |||
| 21ed40bc53 | |||
| 502718caa6 | |||
| e2ce1f997a | |||
| 2ff85cdc56 | |||
| 5821529859 | |||
| 6c52a8629d | |||
| c43653b565 | |||
| 286f8726d5 | |||
| 6f74bbaeec | |||
| 249a35cfe8 | |||
| af9f55c977 | |||
| 102653eb63 | |||
| 31b480d079 | |||
| a16418266e | |||
| 7e65f44168 | |||
| 7f1877a617 | |||
| 44691cde0f | |||
| ed2e3c77af | |||
| 09204dcf44 | |||
| 84f78ea44a | |||
| f60b122a68 | |||
| 28a2ed0a2c | |||
| 4f6b8232c9 | |||
| 2dfbb2963d | |||
| b18af859ef | |||
| 201990b5d9 | |||
| cb3c325e5f | |||
| 238e47cd42 | |||
| a227065ab7 | |||
| c7980036e9 | |||
| 384b284846 | |||
| 475d7fc0ae | |||
| 23c20173b1 | |||
| e36506b1d1 | |||
| 86a76d735e | |||
| 3ecbbf3baf | |||
| aef046b4d7 | |||
| 4a14350711 | |||
| 60d2232c60 | |||
| 1e70ba752e | |||
| 10fd03e222 | |||
| 54e02a620a | |||
| 5178ad768d | |||
| 07a6e612ec | |||
| af1d719856 | |||
| dd7321a014 | |||
| a13d515d5e | |||
| c50223526c | |||
| 1b6ff121f4 | |||
| 290bb2fda6 | |||
| aa29ee6eda | |||
| 559babcdc9 | |||
| 18d79cc30f | |||
| ad97673399 | |||
| 11d21bb2a1 | |||
| 0762aa9ec9 | |||
| a446294e7c | |||
| f1bd4f1055 | |||
| 317beebd7d | |||
| e2a305144c | |||
| e53c4db866 | |||
| 284d9ed7fb | |||
| 31e87de71e | |||
| 4dde700458 | |||
| d71788c402 | |||
| 5c5840417e | |||
| 85f06d6e7b | |||
| 18a93cca3d | |||
| 030c37160d | |||
| 389f61218d | |||
| 4130198f48 | |||
| 3720503e7c | |||
| 29b81f63fd | |||
| 7da16dbf4b | |||
| ac66e3e28f | |||
| f432314fa9 | |||
| 951cde5b72 | |||
| 26c8bdde43 | |||
| b8b14ac6c8 | |||
| 2379c59ab8 | |||
| f0c0c03c5f | |||
| 7c694f2553 | |||
| 4b1c520264 | |||
| 7a553d8439 | |||
| 34253195a2 | |||
| 448467a9a1 | |||
| 99c17f8ac7 | |||
| e3a75901c9 | |||
| 5862c0a174 | |||
| 3e97dda275 | |||
| 29f6ada06a | |||
| c1da382e9a | |||
| bbc4c5fc34 | |||
| 28a6e10a63 | |||
| 6b439d6f82 | |||
| dcd97a431b | |||
| 5695330940 | |||
| e52443ebc1 | |||
| 59d4ab3752 | |||
| 1d11bbb34d | |||
| eabc482184 | |||
| 0550c4a87a | |||
| 52b42ff508 | |||
| edbe969d23 | |||
| df08e10cfa | |||
| abc9376308 | |||
| 39c9b8a665 | |||
| ff2662ebe7 | |||
| b9a6c16461 | |||
| 71277a2283 | |||
| dfc3695ad7 | |||
| f8b7b107d8 | |||
| 99c6944497 | |||
| 0eef2daf06 | |||
| 3e49626aec | |||
| 80aa8c868b | |||
| d355aa11a5 | |||
| 7fceed0446 | |||
| a09342c1fc | |||
| 1022bf7d93 | |||
| 2fd162b8dd | |||
| 62011eed95 | |||
| 658f9cb03f | |||
| 3ce9fb6bbd | |||
| b76a0b8158 | |||
| 718307ffa4 | |||
| 2469cedd15 | |||
| b72e1fb67d | |||
| 10bc66eb42 | |||
| 9ca761b065 | |||
| 64f6839816 | |||
| 01f3b6b6fe | |||
| 61558dcb3d | |||
| 11d9f50115 | |||
| bd974bb443 | |||
| 8ff1f8c526 | |||
| f12b3a0c18 | |||
| 19cb5e054a | |||
| 85ef06a0b5 | |||
| 95463428c8 | |||
| c496d92c3e | |||
| 71f9078bdd | |||
| c964809d37 | |||
| 6a3f58e050 | |||
| 3486e7e9d5 | |||
| 157addf5e9 | |||
| ade7446522 | |||
| a528102994 | |||
| ab51051fcf | |||
| 20e60e5411 | |||
| a069876725 | |||
| 2fa79c9b4d | |||
| 8f71864bef | |||
| b21ee889fe | |||
| a9b4e7963b | |||
| a9aa4dc61b | |||
| 90e2a41027 | |||
| b4f549f4ee | |||
| 53851d5e77 | |||
| 3e62457107 | |||
| 1a046ff4c6 | |||
| be98b1bf7e | |||
| a1ec4aff77 | |||
| 6013b327f7 | |||
| 4b006aa6cf | |||
| 8c1d74162f | |||
| 1a1dde7c8d | |||
| 4c8e6bbbb3 | |||
| 9c94a0ed6f | |||
| ebe3b89b98 | |||
| f523be81d4 | |||
| dc9b51f110 | |||
| 9a1b3fc181 | |||
| b5a30ed0fc | |||
| 6ea60aba31 | |||
| b867b113cc | |||
| db04a7cb35 | |||
| 9c3188741f | |||
| f479013b14 | |||
| a63bb6f650 | |||
| 8c0dfab281 | |||
| 3c9456dd45 | |||
| b45eee3157 | |||
| 5286a014ec | |||
| ff0383dace | |||
| 418e032fac | |||
| 6cef71b1b2 | |||
| 6a645a3eb8 | |||
| 1b4a0897b6 | |||
| 83f72f696a | |||
| 3f91650d6e | |||
| fbe617baba | |||
| 15a783ef82 | |||
| a014ef6340 | |||
| 480ced43c9 | |||
| edcccb6ab2 | |||
| 86d6cebb53 | |||
| e5df099c9b | |||
| e4215f1751 | |||
| 513dc78ebc | |||
| a06b2fdc44 | |||
| b29556e6b5 | |||
| 7b39e32c93 | |||
| 9b395f4d81 | |||
| 42d086b212 | |||
| 5fb14350a0 | |||
| 60ddaf95f0 | |||
| b872cf7f7b | |||
| fb8e5f61b1 | |||
| 6df35235d5 | |||
| 6c5df28d7c | |||
| ae032390e2 | |||
| 8051d5c296 | |||
| ee97db70c5 | |||
| 265e243832 | |||
| 229fbefc03 | |||
| b64c9b8b1f | |||
| cd8d2643d3 | |||
| c92e85a357 | |||
| 75bb548da4 | |||
| 46074e0dd8 | |||
| 27e61cbd84 | |||
| 7ff19d7dfd | |||
| 9d75047211 | |||
| 6e72d514b7 | |||
| a45b6278d1 | |||
| fc43b1ba09 | |||
| b38358f8b7 | |||
| ab7b8b50e3 | |||
| 78fed52627 | |||
| 0407bc8cfe | |||
| d29b922636 | |||
| 9e239ec36e | |||
| bec5e4fb4c | |||
| 61f6f07edd | |||
| cea090af09 | |||
| c12319535b | |||
| 3154e7148d | |||
| 3448729ff3 | |||
| 9a2b39f0ba | |||
| 86ddee5d79 | |||
| f39f9fab3d | |||
| 2a65590755 | |||
| f1b7957028 | |||
| f43275fab4 | |||
| 56f3bc9e69 | |||
| 7b0c767238 | |||
| 7549cb5271 | |||
| 3192b4becd | |||
| 4806ac05a7 | |||
| 003b4e7f15 | |||
| 5119cce2a8 | |||
| aa7334a3ec | |||
| e2df1d71d5 | |||
| e5ccce418f | |||
| c887ff331a | |||
| 0be5b38286 | |||
| e9115f28c9 | |||
| 6b5fa4cd0e | |||
| 1a96770d81 | |||
| 4754dad0d6 | |||
| 3042e945d3 | |||
| fc96e80688 | |||
| 7721a2efe4 | |||
| d90840f7f8 | |||
| 7e9e233b37 | |||
| 958df2b229 | |||
| 3c133f1f53 | |||
| 8c6fa13faa | |||
| c81de3e1e9 | |||
| 8e53533786 | |||
| bacc5396e6 | |||
| 9cb58e0bb3 | |||
| fc5784a310 | |||
| 085cc7ca0e | |||
| 2e42c82793 | |||
| 8607bbf06d | |||
| b73099e083 | |||
| 6358c91a5e | |||
| 9b8cb17831 | |||
| 85fae22fa8 | |||
| d2869fbb5f | |||
| 6533db736c | |||
| 89bd0b50b6 | |||
| 65a00ea754 | |||
| 9ec944003b | |||
| ea0f21fbcc | |||
| 0171aae109 | |||
| fa8f46c0b7 | |||
| d0cdb45b6c | |||
| 8a0f4f32ea | |||
| 0d926eee37 | |||
| 6d78b70075 | |||
| 4184611d3a | |||
| ac1af7848e | |||
| b2b0f6f3ce | |||
| 7dd5578477 | |||
| 2d19785e43 | |||
| d549523f96 | |||
| fd80208af9 | |||
| 5fed47964e | |||
| 71c2a573e1 | |||
| c1173657c7 | |||
| 2bcb41293f | |||
| 7992e105f9 | |||
| 2fbb96bfa5 | |||
| 1018d3b786 | |||
| 09aadafda1 | |||
| ea57dee837 | |||
| eb173099e9 | |||
| 9ac03e7181 | |||
| c2e977a0b8 | |||
| 74541c1dcc | |||
| 0c4ecbe9ec | |||
| 19e2b40a78 | |||
| 43f7974f6d | |||
| 7f0caaa89a | |||
| 6933aaa210 | |||
| 137e67ae70 | |||
| ad2eef0a30 | |||
| 3f3cbea5c4 | |||
| e8c6b8feca | |||
| 81ac4ac152 | |||
| b438b1248c | |||
| 62c96b52a0 | |||
| 210540ce1a | |||
| 4719bb0c6e | |||
| 5f652e632b | |||
| 6b7f3da7c6 | |||
| a51cfd58b8 | |||
| f7dcd2e834 | |||
| 351d7aaa9f | |||
| d1c1a7cba7 | |||
| 55423efb06 | |||
| 628b1adbd2 | |||
| d0a0d6fcb5 | |||
| 0cd53574ec | |||
| 00cf2eae38 | |||
| feec9cc7cf | |||
| 01f06784e7 | |||
| e06c121d78 | |||
| 98b3840a3e | |||
| 8ef11fc41f | |||
| 188d1e2e19 | |||
| 7d9fe86622 | |||
| c757606502 | |||
| acef413f00 | |||
| df4c22e358 | |||
| 426aa514ff | |||
| 8ef3f896f5 | |||
| f9989998a7 | |||
| 2aaff36eef | |||
| 72f673f36d | |||
| 4cd4a2be79 | |||
| 6566941077 | |||
| d90948abb7 | |||
| 1498d42ef6 | |||
| a2f691b24a | |||
| 5e040110fc | |||
| 726f86e020 | |||
| ec4f1d12f4 | |||
| aa1c202577 | |||
| 870127fd30 | |||
| 27dee01623 | |||
| bff8dfea1c |
@@ -0,0 +1,233 @@
|
||||
#---------------------------------------------------------------------------
|
||||
# Project related configuration options
|
||||
#---------------------------------------------------------------------------
|
||||
PROJECT_NAME = openttd
|
||||
OUTPUT_DIRECTORY = docs/source/
|
||||
CREATE_SUBDIRS = NO
|
||||
OUTPUT_LANGUAGE = English
|
||||
USE_WINDOWS_ENCODING = NO
|
||||
BRIEF_MEMBER_DESC = YES
|
||||
REPEAT_BRIEF = YES
|
||||
ABBREVIATE_BRIEF = "The $name class" \
|
||||
"The $name widget" \
|
||||
"The $name file" \
|
||||
is \
|
||||
provides \
|
||||
specifies \
|
||||
contains \
|
||||
represents \
|
||||
a \
|
||||
an \
|
||||
the
|
||||
ALWAYS_DETAILED_SEC = NO
|
||||
INLINE_INHERITED_MEMB = NO
|
||||
FULL_PATH_NAMES = YES
|
||||
STRIP_FROM_PATH = ./
|
||||
STRIP_FROM_INC_PATH =
|
||||
SHORT_NAMES = NO
|
||||
JAVADOC_AUTOBRIEF = YES
|
||||
MULTILINE_CPP_IS_BRIEF = NO
|
||||
DETAILS_AT_TOP = NO
|
||||
INHERIT_DOCS = YES
|
||||
DISTRIBUTE_GROUP_DOC = NO
|
||||
TAB_SIZE = 2
|
||||
ALIASES =
|
||||
OPTIMIZE_OUTPUT_FOR_C = YES
|
||||
OPTIMIZE_OUTPUT_JAVA = NO
|
||||
SUBGROUPING = YES
|
||||
#---------------------------------------------------------------------------
|
||||
# Build related configuration options
|
||||
#---------------------------------------------------------------------------
|
||||
EXTRACT_ALL = NO
|
||||
EXTRACT_PRIVATE = YES
|
||||
EXTRACT_STATIC = YES
|
||||
EXTRACT_LOCAL_CLASSES = YES
|
||||
EXTRACT_LOCAL_METHODS = YES
|
||||
HIDE_UNDOC_MEMBERS = NO
|
||||
HIDE_UNDOC_CLASSES = NO
|
||||
HIDE_FRIEND_COMPOUNDS = NO
|
||||
HIDE_IN_BODY_DOCS = NO
|
||||
INTERNAL_DOCS = NO
|
||||
CASE_SENSE_NAMES = YES
|
||||
HIDE_SCOPE_NAMES = NO
|
||||
SHOW_INCLUDE_FILES = YES
|
||||
INLINE_INFO = YES
|
||||
SORT_MEMBER_DOCS = YES
|
||||
SORT_BRIEF_DOCS = NO
|
||||
SORT_BY_SCOPE_NAME = NO
|
||||
GENERATE_TODOLIST = YES
|
||||
GENERATE_TESTLIST = YES
|
||||
GENERATE_BUGLIST = YES
|
||||
GENERATE_DEPRECATEDLIST= YES
|
||||
ENABLED_SECTIONS =
|
||||
MAX_INITIALIZER_LINES = 30
|
||||
SHOW_USED_FILES = YES
|
||||
SHOW_DIRECTORIES = YES
|
||||
FILE_VERSION_FILTER =
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to warning and progress messages
|
||||
#---------------------------------------------------------------------------
|
||||
QUIET = NO
|
||||
WARNINGS = YES
|
||||
WARN_IF_UNDOCUMENTED = YES
|
||||
WARN_IF_DOC_ERROR = YES
|
||||
WARN_NO_PARAMDOC = NO
|
||||
WARN_FORMAT = "$file:$line: $text"
|
||||
WARN_LOGFILE =
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the input files
|
||||
#---------------------------------------------------------------------------
|
||||
INPUT = ./
|
||||
FILE_PATTERNS = *.c \
|
||||
*.cc \
|
||||
*.cxx \
|
||||
*.cpp \
|
||||
*.c++ \
|
||||
*.h \
|
||||
table/*.h
|
||||
RECURSIVE = YES
|
||||
EXCLUDE =
|
||||
EXCLUDE_SYMLINKS = NO
|
||||
EXCLUDE_PATTERNS =
|
||||
EXAMPLE_PATH =
|
||||
EXAMPLE_PATTERNS = *
|
||||
EXAMPLE_RECURSIVE = NO
|
||||
IMAGE_PATH =
|
||||
INPUT_FILTER =
|
||||
FILTER_PATTERNS =
|
||||
FILTER_SOURCE_FILES = NO
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to source browsing
|
||||
#---------------------------------------------------------------------------
|
||||
SOURCE_BROWSER = YES
|
||||
INLINE_SOURCES = NO
|
||||
STRIP_CODE_COMMENTS = YES
|
||||
REFERENCED_BY_RELATION = YES
|
||||
REFERENCES_RELATION = YES
|
||||
VERBATIM_HEADERS = YES
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the alphabetical class index
|
||||
#---------------------------------------------------------------------------
|
||||
ALPHABETICAL_INDEX = NO
|
||||
COLS_IN_ALPHA_INDEX = 5
|
||||
IGNORE_PREFIX =
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the HTML output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_HTML = YES
|
||||
HTML_OUTPUT = html
|
||||
HTML_FILE_EXTENSION = .html
|
||||
HTML_HEADER =
|
||||
HTML_FOOTER =
|
||||
HTML_STYLESHEET =
|
||||
HTML_ALIGN_MEMBERS = YES
|
||||
GENERATE_HTMLHELP = YES
|
||||
CHM_FILE =
|
||||
HHC_LOCATION =
|
||||
GENERATE_CHI = NO
|
||||
BINARY_TOC = NO
|
||||
TOC_EXPAND = YES
|
||||
DISABLE_INDEX = NO
|
||||
ENUM_VALUES_PER_LINE = 4
|
||||
GENERATE_TREEVIEW = YES
|
||||
TREEVIEW_WIDTH = 250
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the LaTeX output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_LATEX = NO
|
||||
LATEX_OUTPUT = latex
|
||||
LATEX_CMD_NAME = latex
|
||||
MAKEINDEX_CMD_NAME = makeindex
|
||||
COMPACT_LATEX = NO
|
||||
PAPER_TYPE = a4wide
|
||||
EXTRA_PACKAGES =
|
||||
LATEX_HEADER =
|
||||
PDF_HYPERLINKS = NO
|
||||
USE_PDFLATEX = NO
|
||||
LATEX_BATCHMODE = NO
|
||||
LATEX_HIDE_INDICES = NO
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the RTF output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_RTF = NO
|
||||
RTF_OUTPUT = rtf
|
||||
COMPACT_RTF = NO
|
||||
RTF_HYPERLINKS = NO
|
||||
RTF_STYLESHEET_FILE =
|
||||
RTF_EXTENSIONS_FILE =
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the man page output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_MAN = YES
|
||||
MAN_OUTPUT = man
|
||||
MAN_EXTENSION = .3
|
||||
MAN_LINKS = NO
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the XML output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_XML = NO
|
||||
XML_OUTPUT = xml
|
||||
XML_SCHEMA =
|
||||
XML_DTD =
|
||||
XML_PROGRAMLISTING = YES
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options for the AutoGen Definitions output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_AUTOGEN_DEF = NO
|
||||
#---------------------------------------------------------------------------
|
||||
# configuration options related to the Perl module output
|
||||
#---------------------------------------------------------------------------
|
||||
GENERATE_PERLMOD = NO
|
||||
PERLMOD_LATEX = NO
|
||||
PERLMOD_PRETTY = YES
|
||||
PERLMOD_MAKEVAR_PREFIX =
|
||||
#---------------------------------------------------------------------------
|
||||
# Configuration options related to the preprocessor
|
||||
#---------------------------------------------------------------------------
|
||||
ENABLE_PREPROCESSING = YES
|
||||
MACRO_EXPANSION = NO
|
||||
EXPAND_ONLY_PREDEF = NO
|
||||
SEARCH_INCLUDES = YES
|
||||
INCLUDE_PATH =
|
||||
INCLUDE_FILE_PATTERNS =
|
||||
PREDEFINED =
|
||||
EXPAND_AS_DEFINED =
|
||||
SKIP_FUNCTION_MACROS = YES
|
||||
#---------------------------------------------------------------------------
|
||||
# Configuration::additions related to external references
|
||||
#---------------------------------------------------------------------------
|
||||
TAGFILES =
|
||||
GENERATE_TAGFILE = openttd.tag
|
||||
ALLEXTERNALS = NO
|
||||
EXTERNAL_GROUPS = YES
|
||||
PERL_PATH = /usr/bin/perl
|
||||
#---------------------------------------------------------------------------
|
||||
# Configuration options related to the dot tool
|
||||
#---------------------------------------------------------------------------
|
||||
CLASS_DIAGRAMS = YES
|
||||
HIDE_UNDOC_RELATIONS = YES
|
||||
HAVE_DOT = NO
|
||||
CLASS_GRAPH = YES
|
||||
COLLABORATION_GRAPH = YES
|
||||
GROUP_GRAPHS = YES
|
||||
UML_LOOK = NO
|
||||
TEMPLATE_RELATIONS = NO
|
||||
INCLUDE_GRAPH = YES
|
||||
INCLUDED_BY_GRAPH = YES
|
||||
CALL_GRAPH = NO
|
||||
GRAPHICAL_HIERARCHY = YES
|
||||
DIRECTORY_GRAPH = YES
|
||||
DOT_IMAGE_FORMAT = png
|
||||
DOT_PATH =
|
||||
DOTFILE_DIRS =
|
||||
MAX_DOT_GRAPH_WIDTH = 1024
|
||||
MAX_DOT_GRAPH_HEIGHT = 1024
|
||||
MAX_DOT_GRAPH_DEPTH = 1000
|
||||
DOT_TRANSPARENT = NO
|
||||
DOT_MULTI_TARGETS = NO
|
||||
GENERATE_LEGEND = YES
|
||||
DOT_CLEANUP = YES
|
||||
#---------------------------------------------------------------------------
|
||||
# Configuration::additions related to the search engine
|
||||
#---------------------------------------------------------------------------
|
||||
SEARCHENGINE = NO
|
||||
@@ -1,13 +1,4 @@
|
||||
# This Makefile is partially based on "a completely generic Makefile",
|
||||
# originally created by Justin Husted <husted@cs>
|
||||
#
|
||||
# Rewrite and sane dependencies support by Petr Baudis <pasky@ucw.cz>
|
||||
# Cygwin support and configuration by Jaen Saul <slowbyte@hot.ee>
|
||||
# A lot of modifications by Bjarni Corfitzen <bjarni@openttd.com>
|
||||
#
|
||||
# Last modified by: $Author: strigeus $
|
||||
# On: $Date: 2004/03/11 19:15:06 $
|
||||
|
||||
# $Id$
|
||||
|
||||
##############################################################################
|
||||
#
|
||||
@@ -52,6 +43,7 @@
|
||||
# WITH_ZLIB: savegames using zlib
|
||||
# WITH_PNG: screenshots using PNG
|
||||
# WITH_SDL: SDL video driver support
|
||||
# WITH_COCOA: Cocoa video driver support
|
||||
#
|
||||
# Summary of other defines:
|
||||
# MANUAL_CONFIG: do not use Makefile.config, config options set manually
|
||||
@@ -64,8 +56,12 @@
|
||||
# MIDI: if set, it will use it as custom path to midi player.
|
||||
# If unset, it will use the hardcoded path in the c code
|
||||
# This can still be overriden by the music.extmidi openttd.cfg option.
|
||||
# WITH_DIRECTMUSIC: enable DirectMusic MIDI support
|
||||
# WITH_NETWORK: enable networking
|
||||
# DEDICATED: allows compilation on UNIX without SDL. Useful for dedicated servers
|
||||
# MAX_NUM_AUTOSAVES: sets the number of autosaves the games will make before starting
|
||||
# to overwrite the old ones. If not set, the game will use 16.
|
||||
# NOTE: assign a number, not a string of a number
|
||||
#
|
||||
# Paths:
|
||||
# INSTALL: If not set, the game uses the directory of the binary to
|
||||
@@ -83,8 +79,12 @@
|
||||
# PREFIX: Normally /usr/local
|
||||
# BINARY_DIR: The location of the binary, normally games. (Will be prefixed
|
||||
# with $PREFIX)
|
||||
# DATA_DIR: The location of the data (lang, data and gm), normally
|
||||
# share/games/openttd. (Will be prefixed with $PREFIX)
|
||||
# DATA_DIR: The location of the data (lang, data, gm and scenario), normally
|
||||
# share/games/openttd. (Will be prefixed with $PREFIX) Note that scenarios
|
||||
# are only put here if USE_HOMEDIR is true, otherwise they are placed in
|
||||
# PERSONAL_DIR/scenario
|
||||
# ICON_DIR: The location of the openttd icon. (Will be prefixed with
|
||||
# $PREFIX).
|
||||
# PERSONAL_DIR: The directory where openttd.cfg and the save folder will be
|
||||
# stored. You cannot use ~ here, define USE_HOMEDIR for that.
|
||||
# USE_HOMEDIR: If this variable is set, PERSONAL_DIR will be prefixed with
|
||||
@@ -109,14 +109,19 @@
|
||||
#
|
||||
# Special for crosscompiling there are some commands available:
|
||||
#
|
||||
# ENDIAN_FORCE: forces the endian-check to give a certain result. Can be either BE or LE.
|
||||
# FAT_BINARY: builds a universal binary for OSX. Make sure you got both PPC and x86 libs. Only works with GCC 4 or newer
|
||||
#
|
||||
# JAGUAR: Crosscompiling for OSX 1.2.8 (codenamed Jaguar). Only works if OSX is defined too. Only works with GCC 4 or newer
|
||||
# This can be changed to any PPC version of OSX by changing the ppc flags in Makefile.config
|
||||
#
|
||||
# ENDIAN_FORCE: forces the endian-check to give a certain result. Can be BE, LE or PREPROCESSOR.
|
||||
# PREPROCESSOR is always used on all OSX targets and will make the preprocessor pick the right endian.
|
||||
# this means that you don't have to think about endianess when compiling for OSX.
|
||||
# Very useful for universal binaries and crosscompilers. Not sure if it works on non OSX targets
|
||||
# WINDRES: the location of your windres
|
||||
# CC_HOST: the gcc of your localhost if you are making a target that produces incompatible executables
|
||||
# CFLAGS_HOST: cflags used for CC_HOST. Make it something if you are getting errors when you try to compi
|
||||
# windows executables on linux. (just: CFLAGS_HOST:='-I' or something)
|
||||
#
|
||||
# Experimental (does not work properly):
|
||||
# WITH_DIRECTMUSIC: enable DirectMusic MIDI support
|
||||
|
||||
|
||||
##############################################################################
|
||||
@@ -127,7 +132,7 @@
|
||||
|
||||
# Makefile version tag
|
||||
# it checks if the version tag in Makefile.config is the same and force update outdated config files
|
||||
MAKEFILE_VERSION:=7
|
||||
MAKEFILE_VERSION:=8
|
||||
|
||||
# CONFIG_WRITER has to be found even for manual configuration
|
||||
CONFIG_WRITER=makefiledir/Makefile.config_writer
|
||||
@@ -147,6 +152,10 @@ else
|
||||
CONFIG_INCLUDED:=1
|
||||
endif
|
||||
|
||||
ifndef LIBPNG-CONFIG
|
||||
LIBPNG-CONFIG :=libpng-config
|
||||
endif
|
||||
|
||||
# updates Makefile.config if it's outdated
|
||||
ifneq ($(MAKEFILE_VERSION),$(CONFIG_VERSION))
|
||||
ifndef MANUAL_CONFIG # manual config should not check this
|
||||
@@ -187,6 +196,10 @@ ifdef SUPRESS_LANG_ERRORS
|
||||
LANG_ERRORS = >/dev/null 2>&1
|
||||
endif
|
||||
|
||||
ifdef OSX
|
||||
-include os/MacOSX/Makefile.setup
|
||||
endif
|
||||
|
||||
ifdef STATIC
|
||||
ifndef WIN32
|
||||
ifndef OSX
|
||||
@@ -199,14 +212,14 @@ endif
|
||||
endif
|
||||
endif
|
||||
|
||||
ifdef RELEASE
|
||||
ifdef OSX
|
||||
ifndef STATIC
|
||||
$(error do not make dynamically linked releases. Most users can't use those)
|
||||
ifdef WITH_COCOA
|
||||
ifdef WITH_SDL
|
||||
$(error You can not use both the SDL video driver and the Cocoa video driver at the same time)
|
||||
endif
|
||||
ifdef DEDICATED
|
||||
$(error You can not use the Cocoa video driver in a dedicated server)
|
||||
endif
|
||||
endif
|
||||
|
||||
else
|
||||
# Force SDL on UNIX platforms
|
||||
ifndef WITH_SDL
|
||||
ifdef UNIX
|
||||
@@ -215,10 +228,24 @@ $(error You need to have SDL installed in order to run OpenTTD on UNIX. Use DEDI
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
|
||||
# remove the dependancy for sdl if DEDICALTED is used
|
||||
ifdef DEDICATED
|
||||
WITH_SDL:=
|
||||
WITH_SDL:=
|
||||
endif
|
||||
|
||||
# add -lpthread to LDFLAGS
|
||||
ifndef WIN32
|
||||
ifndef MORPHOS
|
||||
ifndef OSX
|
||||
LDFLAGS+=-lpthread
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
|
||||
ifdef OSX
|
||||
LDFLAGS+=-framework Cocoa
|
||||
endif
|
||||
|
||||
|
||||
@@ -240,33 +267,11 @@ ENDIAN_CHECK=endian_check$(EXE)
|
||||
STRGEN=strgen/strgen$(EXE)
|
||||
OSXAPP="OpenTTD.app"
|
||||
|
||||
# What revision are we compiling, if we have an idea?
|
||||
REV_NUMBER := $(shell if test -d .svn; then svnversion . | tr -dc 0-9; fi)
|
||||
|
||||
ifdef RELEASE
|
||||
REV:=$(RELEASE)
|
||||
else
|
||||
REV := $(shell if test -d .svn; then svnversion . | awk '{ print "r"$$0 }'; fi)
|
||||
tmp_test:=$(shell echo "$(REV)" | grep "M" )
|
||||
ifdef tmp_test
|
||||
REV_NUMBER:=1
|
||||
endif
|
||||
endif
|
||||
|
||||
ifndef REV_NUMBER
|
||||
REV_NUMBER:=0
|
||||
endif
|
||||
REV := 0.4.5
|
||||
|
||||
# MorphOS needs builddate
|
||||
BUILDDATE=`date +%d.%m.%y`
|
||||
|
||||
# AMD64 needs a little more settings to work
|
||||
ifeq ($(shell uname -m), x86_64)
|
||||
endwarnings:=endwarnings
|
||||
64_bit_warnings:=64_bit_warnings
|
||||
BASECFLAGS += -m64
|
||||
endif
|
||||
|
||||
# Check if there is a windres override
|
||||
ifndef WINDRES
|
||||
WINDRES = windres
|
||||
@@ -285,27 +290,19 @@ ifndef CFLAGS_HOST
|
||||
CFLAGS_HOST = $(BASECFLAGS)
|
||||
endif
|
||||
|
||||
# When calling the compiler, use these flags
|
||||
# -g debugging symbols
|
||||
# -Wall all warnings
|
||||
# -s automatic strip
|
||||
#
|
||||
# You may also want:
|
||||
# -O optimize or -O2 fully optimize (O's above 2 are not recommended)
|
||||
# -pg profile - generate profiling data. See "man gprof" to use this.
|
||||
|
||||
CC_VERSION = $(shell $(CC) -dumpversion | cut -c 1,3)
|
||||
|
||||
# GNU make can only test for (in)equality
|
||||
# this is a workaround to test for >=
|
||||
ifeq ($(shell if test $(CC_VERSION) -ge 29; then echo true; fi), true)
|
||||
CFLAGS += -O -Wall -Wno-multichar -Wsign-compare -Wstrict-prototypes
|
||||
ifeq ($(shell expr $(CC_VERSION) \>= 29), 1)
|
||||
CFLAGS += -O -Wall -Wno-multichar -Wsign-compare -Wstrict-prototypes -Wundef
|
||||
CFLAGS += -Wwrite-strings -Wpointer-arith
|
||||
endif
|
||||
ifeq ($(shell if test $(CC_VERSION) -ge 30; then echo true; fi), true)
|
||||
ifeq ($(shell expr $(CC_VERSION) \>= 30), 1)
|
||||
CFLAGS += -W -Wno-unused-parameter
|
||||
endif
|
||||
ifeq ($(shell if test $(CC_VERSION) -ge 34; then echo true; fi), true)
|
||||
ifeq ($(shell expr $(CC_VERSION) \>= 34), 1)
|
||||
CFLAGS += -Wdeclaration-after-statement -Wold-style-definition
|
||||
endif
|
||||
|
||||
@@ -342,10 +339,10 @@ endif
|
||||
|
||||
ifdef OSX
|
||||
# these compilerflags makes the app run as fast as possible without making the app unstable. It works on G3 or newer
|
||||
BASECFLAGS += -O3 -funroll-loops -fsched-interblock -falign-loops=16 -falign-jumps=16 -falign-functions=16 -falign-jumps-max-skip=15 -falign-loops-max-skip=15 -mdynamic-no-pic -mpowerpc-gpopt -force_cpusubtype_ALL
|
||||
BASECFLAGS += -O3 -funroll-loops -fsched-interblock -falign-loops=16 -falign-jumps=16 -falign-functions=16 -falign-jumps-max-skip=15 -falign-loops-max-skip=15 -mdynamic-no-pic
|
||||
else
|
||||
ifdef MORPHOS
|
||||
BASECFLAGS += -O2 -noixemul -fstrict-aliasing -fexpensive-optimizations
|
||||
BASECFLAGS += -I/gg/os-include -O2 -noixemul -fstrict-aliasing -fexpensive-optimizations
|
||||
BASECFLAGS += -mcpu=604 -fno-inline -mstring -mmultiple
|
||||
else
|
||||
BASECFLAGS += -O2
|
||||
@@ -384,12 +381,13 @@ endif
|
||||
|
||||
ifdef BEOS
|
||||
CDEFS += -DBEOS
|
||||
LDFLAGS += -lmidi -lbe
|
||||
LDFLAGS += -lmidi -lbe -lpthread
|
||||
ifdef WITH_NETWORK
|
||||
ifdef BEOS_NET_SERVER
|
||||
CDEFS += -DBEOS_NET_SERVER
|
||||
LDFLAGS += -lnet
|
||||
else
|
||||
# Zeta needs a few more libraries than R5
|
||||
# BONE needs a few more libraries than R5
|
||||
LDFLAGS += -lbind -lsocket
|
||||
endif
|
||||
endif
|
||||
@@ -407,6 +405,11 @@ LDFLAGS += -lnsl -lsocket
|
||||
endif
|
||||
endif
|
||||
|
||||
# tell the source that we are building a dedicated server
|
||||
ifdef DEDICATED
|
||||
CDEFS += -DDEDICATED
|
||||
endif
|
||||
|
||||
# SDL config
|
||||
ifdef WITH_SDL
|
||||
CDEFS += -DWITH_SDL
|
||||
@@ -418,7 +421,6 @@ LIBS += $(shell $(SDL-CONFIG) --libs)
|
||||
endif
|
||||
endif
|
||||
|
||||
|
||||
# zlib config
|
||||
ifdef WITH_ZLIB
|
||||
CDEFS += -DWITH_ZLIB
|
||||
@@ -457,19 +459,19 @@ endif
|
||||
# libpng config
|
||||
ifdef WITH_PNG
|
||||
CDEFS += -DWITH_PNG
|
||||
CFLAGS += $(shell libpng-config --cflags)
|
||||
CFLAGS += $(shell $(LIBPNG-CONFIG) --cppflags --I_opts)
|
||||
|
||||
# seems like older libpng versions are broken and need this
|
||||
PNGCONFIG_FLAGS = --ldflags --libs
|
||||
ifdef STATIC
|
||||
ifdef OSX
|
||||
# Seems like we need a tiny hack for OSX static to work
|
||||
LIBS += $(shell libpng-config --prefix)/lib/libpng.a
|
||||
LIBS += $(shell $(LIBPNG-CONFIG) --prefix)/lib/libpng.a
|
||||
else
|
||||
LIBS += $(shell libpng-config --static $(PNGCONFIG_FLAGS))
|
||||
LIBS += $(shell $(LIBPNG-CONFIG) --static $(PNGCONFIG_FLAGS))
|
||||
endif
|
||||
else
|
||||
LIBS += $(shell libpng-config --L_opts $(PNGCONFIG_FLAGS))
|
||||
LIBS += $(shell $(LIBPNG-CONFIG) --L_opts $(PNGCONFIG_FLAGS))
|
||||
endif
|
||||
endif
|
||||
|
||||
@@ -491,18 +493,30 @@ else
|
||||
STRGEN_FLAGS=
|
||||
endif
|
||||
|
||||
|
||||
# MIDI setup
|
||||
# OSX specific setup
|
||||
ifdef OSX
|
||||
ifndef MIDI
|
||||
MIDI:=$(OSXAPP)/Contents/macosx/track_starter
|
||||
endif
|
||||
ifndef SECOND_DATA_PATH
|
||||
SECOND_DATA_PATH:="$(OSXAPP)/Contents/Data/"
|
||||
endif
|
||||
ifndef CUSTOM_LANG_DIR
|
||||
CUSTOM_LANG_DIR:="$(OSXAPP)/Contents/Lang/"
|
||||
endif
|
||||
# set the endian flag for OSX, that can't fail
|
||||
ENDIAN_FORCE:=PREPROCESSOR
|
||||
|
||||
ifndef DEDICATED
|
||||
LIBS += -framework QuickTime
|
||||
endif
|
||||
|
||||
ifdef WITH_COCOA
|
||||
CDEFS += -DWITH_COCOA
|
||||
LIBS += -F/System/Library/Frameworks -framework Cocoa -framework Carbon -framework AudioUnit
|
||||
endif
|
||||
|
||||
# OSX path setup
|
||||
ifndef SECOND_DATA_PATH
|
||||
SECOND_DATA_PATH:="$(OSXAPP)/Contents/Data/"
|
||||
endif
|
||||
|
||||
ifndef CUSTOM_LANG_DIR
|
||||
ifndef DEDICATED
|
||||
CUSTOM_LANG_DIR:="$(OSXAPP)/Contents/Lang/"
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
|
||||
ifdef MIDI
|
||||
@@ -512,20 +526,15 @@ CDEFS += -DMIDI_ARG=\"$(MIDI_ARG)\"
|
||||
endif
|
||||
endif
|
||||
|
||||
ifdef MAX_NUM_AUTOSAVES
|
||||
CDEFS += -DMAX_NUM_AUTOSAVES=$(MAX_NUM_AUTOSAVES)
|
||||
endif
|
||||
|
||||
ifdef WITH_NETWORK
|
||||
CDEFS += -DENABLE_NETWORK
|
||||
ifdef QNX
|
||||
LIBS += -lsocket
|
||||
endif
|
||||
ifdef UNIX
|
||||
ifndef OSX
|
||||
ifndef MORPHOS
|
||||
# this have caused problems on many platforms and disabling it didn't break anything
|
||||
# now we test if disabling it as a general breaks it for anybody
|
||||
#LIBS += -lresolv
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
|
||||
|
||||
@@ -559,10 +568,12 @@ ifdef INSTALL
|
||||
# the prefix is not prepended in the makefile config
|
||||
BINARY_DIR_PREFIXED:=$(PREFIX)/$(BINARY_DIR)
|
||||
DATA_DIR_PREFIXED:=$(PREFIX)/$(DATA_DIR)
|
||||
ICON_DIR_PREFIXED:=$(PREFIX)/$(ICON_DIR)
|
||||
# We use _INSTALL vars here, these vars are the locations where the files will
|
||||
# be installed
|
||||
DATA_DIR_INSTALL=$(DEST_DIR)/$(DATA_DIR_PREFIXED)
|
||||
BINARY_DIR_INSTALL=$(DEST_DIR)/$(BINARY_DIR_PREFIXED)
|
||||
ICON_DIR_INSTALL=$(DEST_DIR)/$(ICON_DIR_PREFIXED)
|
||||
# Let the code know where to find stuff
|
||||
ifdef DATA_DIR_PREFIXED
|
||||
CDEFS += -DGAME_DATA_DIR=\"$(DATA_DIR_PREFIXED)/\"
|
||||
@@ -586,136 +597,166 @@ endif
|
||||
|
||||
### Sources
|
||||
|
||||
C_SOURCES += ai.c
|
||||
C_SOURCES += ai_build.c
|
||||
C_SOURCES += ai_new.c
|
||||
C_SOURCES += ai_pathfinder.c
|
||||
C_SOURCES += ai_shared.c
|
||||
C_SOURCES += aircraft_cmd.c
|
||||
C_SOURCES += aircraft_gui.c
|
||||
C_SOURCES += airport.c
|
||||
C_SOURCES += airport_gui.c
|
||||
C_SOURCES += aystar.c
|
||||
C_SOURCES += bridge_gui.c
|
||||
C_SOURCES += callback_table.c
|
||||
C_SOURCES += clear_cmd.c
|
||||
C_SOURCES += command.c
|
||||
C_SOURCES += console.c
|
||||
C_SOURCES += console_cmds.c
|
||||
C_SOURCES += debug.c
|
||||
C_SOURCES += dedicated.c
|
||||
C_SOURCES += depot.c
|
||||
C_SOURCES += disaster_cmd.c
|
||||
C_SOURCES += dock_gui.c
|
||||
C_SOURCES += dummy_land.c
|
||||
C_SOURCES += economy.c
|
||||
C_SOURCES += engine.c
|
||||
C_SOURCES += engine_gui.c
|
||||
C_SOURCES += fileio.c
|
||||
C_SOURCES += gfx.c
|
||||
C_SOURCES += graph_gui.c
|
||||
C_SOURCES += newgrf.c
|
||||
C_SOURCES += industry_cmd.c
|
||||
C_SOURCES += industry_gui.c
|
||||
C_SOURCES += intro_gui.c
|
||||
C_SOURCES += landscape.c
|
||||
C_SOURCES += main_gui.c
|
||||
C_SOURCES += map.c
|
||||
C_SOURCES += md5.c
|
||||
C_SOURCES += minilzo.c
|
||||
C_SOURCES += misc.c
|
||||
C_SOURCES += misc_cmd.c
|
||||
C_SOURCES += misc_gui.c
|
||||
C_SOURCES += mixer.c
|
||||
C_SOURCES += music_gui.c
|
||||
C_SOURCES += namegen.c
|
||||
C_SOURCES += network.c
|
||||
C_SOURCES += network_client.c
|
||||
C_SOURCES += network_data.c
|
||||
C_SOURCES += network_gamelist.c
|
||||
C_SOURCES += network_gui.c
|
||||
C_SOURCES += network_server.c
|
||||
C_SOURCES += network_udp.c
|
||||
C_SOURCES += news_gui.c
|
||||
C_SOURCES += npf.c
|
||||
C_SOURCES += oldloader.c
|
||||
C_SOURCES += order_cmd.c
|
||||
C_SOURCES += order_gui.c
|
||||
C_SOURCES += pathfind.c
|
||||
C_SOURCES += player_gui.c
|
||||
C_SOURCES += players.c
|
||||
C_SOURCES += pool.c
|
||||
C_SOURCES += queue.c
|
||||
C_SOURCES += rail_cmd.c
|
||||
C_SOURCES += rail_gui.c
|
||||
C_SOURCES += rev.c
|
||||
C_SOURCES += road_cmd.c
|
||||
C_SOURCES += road_gui.c
|
||||
C_SOURCES += roadveh_cmd.c
|
||||
C_SOURCES += roadveh_gui.c
|
||||
C_SOURCES += saveload.c
|
||||
C_SOURCES += screenshot.c
|
||||
C_SOURCES += settings.c
|
||||
C_SOURCES += settings_gui.c
|
||||
C_SOURCES += ship_cmd.c
|
||||
C_SOURCES += ship_gui.c
|
||||
C_SOURCES += signs.c
|
||||
C_SOURCES += smallmap_gui.c
|
||||
C_SOURCES += sound.c
|
||||
C_SOURCES += sprite.c
|
||||
C_SOURCES += spritecache.c
|
||||
C_SOURCES += station_cmd.c
|
||||
C_SOURCES += station_gui.c
|
||||
C_SOURCES += string.c
|
||||
C_SOURCES += strings.c
|
||||
C_SOURCES += subsidy_gui.c
|
||||
C_SOURCES += terraform_gui.c
|
||||
C_SOURCES += texteff.c
|
||||
C_SOURCES += tile.c
|
||||
C_SOURCES += town_cmd.c
|
||||
C_SOURCES += town_gui.c
|
||||
C_SOURCES += train_cmd.c
|
||||
C_SOURCES += train_gui.c
|
||||
C_SOURCES += tree_cmd.c
|
||||
C_SOURCES += ttd.c
|
||||
C_SOURCES += tunnelbridge_cmd.c
|
||||
C_SOURCES += unmovable_cmd.c
|
||||
C_SOURCES += vehicle.c
|
||||
C_SOURCES += vehicle_gui.c
|
||||
C_SOURCES += viewport.c
|
||||
C_SOURCES += water_cmd.c
|
||||
C_SOURCES += waypoint.c
|
||||
C_SOURCES += widget.c
|
||||
C_SOURCES += window.c
|
||||
# clean up C_SOURCES first. Needed since building universal binaries on OSX calls the makefile recursively (just one time)
|
||||
SRCS :=
|
||||
|
||||
CXX_SOURCES =
|
||||
SRCS += aircraft_cmd.c
|
||||
SRCS += aircraft_gui.c
|
||||
SRCS += airport.c
|
||||
SRCS += airport_gui.c
|
||||
SRCS += aystar.c
|
||||
SRCS += bridge_gui.c
|
||||
SRCS += callback_table.c
|
||||
SRCS += clear_cmd.c
|
||||
SRCS += command.c
|
||||
SRCS += console.c
|
||||
SRCS += console_cmds.c
|
||||
SRCS += currency.c
|
||||
SRCS += debug.c
|
||||
SRCS += dedicated.c
|
||||
SRCS += depot.c
|
||||
SRCS += disaster_cmd.c
|
||||
SRCS += dock_gui.c
|
||||
SRCS += driver.c
|
||||
SRCS += dummy_land.c
|
||||
SRCS += economy.c
|
||||
SRCS += engine.c
|
||||
SRCS += engine_gui.c
|
||||
SRCS += fileio.c
|
||||
SRCS += gfx.c
|
||||
SRCS += gfxinit.c
|
||||
SRCS += graph_gui.c
|
||||
SRCS += industry_cmd.c
|
||||
SRCS += industry_gui.c
|
||||
SRCS += intro_gui.c
|
||||
SRCS += landscape.c
|
||||
SRCS += main_gui.c
|
||||
SRCS += map.c
|
||||
SRCS += md5.c
|
||||
SRCS += mersenne.c
|
||||
SRCS += minilzo.c
|
||||
SRCS += misc.c
|
||||
SRCS += misc_cmd.c
|
||||
SRCS += misc_gui.c
|
||||
SRCS += mixer.c
|
||||
SRCS += music_gui.c
|
||||
SRCS += namegen.c
|
||||
SRCS += network.c
|
||||
SRCS += network_client.c
|
||||
SRCS += network_data.c
|
||||
SRCS += network_gamelist.c
|
||||
SRCS += network_gui.c
|
||||
SRCS += network_server.c
|
||||
SRCS += network_udp.c
|
||||
SRCS += newgrf.c
|
||||
SRCS += news_gui.c
|
||||
SRCS += npf.c
|
||||
SRCS += oldloader.c
|
||||
SRCS += openttd.c
|
||||
SRCS += order_cmd.c
|
||||
SRCS += order_gui.c
|
||||
SRCS += pathfind.c
|
||||
SRCS += player_gui.c
|
||||
SRCS += players.c
|
||||
SRCS += pool.c
|
||||
SRCS += queue.c
|
||||
SRCS += rail.c
|
||||
SRCS += rail_cmd.c
|
||||
SRCS += rail_gui.c
|
||||
SRCS += rev.c
|
||||
SRCS += road_cmd.c
|
||||
SRCS += road_gui.c
|
||||
SRCS += roadveh_cmd.c
|
||||
SRCS += roadveh_gui.c
|
||||
SRCS += saveload.c
|
||||
SRCS += screenshot.c
|
||||
SRCS += settings.c
|
||||
SRCS += settings_gui.c
|
||||
SRCS += ship_cmd.c
|
||||
SRCS += ship_gui.c
|
||||
SRCS += signs.c
|
||||
SRCS += smallmap_gui.c
|
||||
SRCS += sound.c
|
||||
SRCS += sprite.c
|
||||
SRCS += spritecache.c
|
||||
SRCS += station_cmd.c
|
||||
SRCS += station_gui.c
|
||||
SRCS += station_newgrf.c
|
||||
SRCS += string.c
|
||||
SRCS += strings.c
|
||||
SRCS += subsidy_gui.c
|
||||
SRCS += terraform_gui.c
|
||||
SRCS += texteff.c
|
||||
SRCS += thread.c
|
||||
SRCS += tile.c
|
||||
SRCS += town_cmd.c
|
||||
SRCS += town_gui.c
|
||||
SRCS += train_cmd.c
|
||||
SRCS += train_gui.c
|
||||
SRCS += tree_cmd.c
|
||||
SRCS += tunnelbridge_cmd.c
|
||||
SRCS += unmovable_cmd.c
|
||||
SRCS += vehicle.c
|
||||
SRCS += vehicle_gui.c
|
||||
SRCS += viewport.c
|
||||
SRCS += water_cmd.c
|
||||
SRCS += waypoint.c
|
||||
SRCS += widget.c
|
||||
SRCS += window.c
|
||||
SRCS += music/null_m.c
|
||||
SRCS += sound/null_s.c
|
||||
SRCS += video/dedicated_v.c
|
||||
SRCS += video/null_v.c
|
||||
|
||||
# AI related files
|
||||
SRCS += ai/ai.c
|
||||
SRCS += ai/default/default.c
|
||||
SRCS += ai/trolly/build.c
|
||||
SRCS += ai/trolly/pathfinder.c
|
||||
SRCS += ai/trolly/shared.c
|
||||
SRCS += ai/trolly/trolly.c
|
||||
|
||||
ifdef WITH_SDL
|
||||
C_SOURCES += sdl.c
|
||||
SRCS += sdl.c
|
||||
SRCS += sound/sdl_s.c
|
||||
SRCS += video/sdl_v.c
|
||||
endif
|
||||
|
||||
ifdef WIN32
|
||||
C_SOURCES += win32.c w32dm.c
|
||||
SRCS += win32.c
|
||||
SRCS += music/win32_m.c
|
||||
SRCS += sound/win32_s.c
|
||||
SRCS += video/win32_v.c
|
||||
else
|
||||
C_SOURCES += extmidi.c unix.c
|
||||
SRCS += unix.c
|
||||
SRCS += music/extmidi.c
|
||||
endif
|
||||
|
||||
OBJS = $(C_SOURCES:%.c=%.o) $(CXX_SOURCES:%.cpp=%.o)
|
||||
ifdef OSX
|
||||
SRCS += os/macosx/macos.m
|
||||
ifndef DEDICATED
|
||||
SRCS += music/qtmidi.c
|
||||
endif
|
||||
ifdef WITH_COCOA
|
||||
SRCS += video/cocoa_v.m
|
||||
SRCS += sound/cocoa_s.c
|
||||
SRCS += os/macosx/splash.c
|
||||
endif
|
||||
endif
|
||||
|
||||
ifdef BEOS
|
||||
CXX_SOURCES += os/beos/bemidi.cpp
|
||||
CFLAGS += -I.
|
||||
SRCS += music/bemidi.cpp
|
||||
endif
|
||||
|
||||
ifdef WIN32
|
||||
# Resource file
|
||||
OBJS += winres.o
|
||||
SRCS += ottdres.rc
|
||||
endif
|
||||
|
||||
ifdef WITH_DIRECTMUSIC
|
||||
CXX_SOURCES += w32dm2.cpp
|
||||
SRCS += music/dmusic.cpp
|
||||
endif
|
||||
|
||||
OBJS += $(filter %.o, $(SRCS:%.cpp=%.o) $(SRCS:%.m=%.o) $(SRCS:%.c=%.o) $(SRCS:%.rc=%.o))
|
||||
DEPS = $(OBJS:%.o=.deps/%.d)
|
||||
|
||||
LANG_TXT = $(filter-out %.unfinished.txt,$(wildcard lang/*.txt))
|
||||
@@ -727,40 +768,15 @@ LANGS = $(LANG_TXT:%.txt=%.lng)
|
||||
# Build commands
|
||||
#
|
||||
|
||||
# If we are verbose, we will show commands prefixed by $(Q) (which acts as
|
||||
# @ in the non-verbose mode), and we will show the "real" cmds instead of
|
||||
# their quiet versions (which are used in the non-verbose mode).
|
||||
# If we are verbose, we will show commands prefixed by $(Q).
|
||||
# The $(Q)s get replaced by @ in non-verbose mode.
|
||||
# Inspired by the Linux kernel build system.
|
||||
ifdef VERBOSE
|
||||
Q =
|
||||
quiet =
|
||||
else
|
||||
Q = @
|
||||
quiet = quiet_
|
||||
endif
|
||||
|
||||
# Show the command (quiet or non-quiet version based on the assignment
|
||||
# just above) and then execute it.
|
||||
cmd = @$(if $($(quiet)cmd_$(1)),echo $($(quiet)cmd_$(1)) &&) $(cmd_$(1))
|
||||
|
||||
|
||||
# The build commands themselves. Note that if you omit the quiet version,
|
||||
# nothing will be shown in the non-verbose mode.
|
||||
|
||||
quiet_cmd_compile_link = '===> Compiling and Linking $@'
|
||||
cmd_compile_link = $(CC_HOST) $(CFLAGS_HOST) $(CDEFS) $< -o $@
|
||||
|
||||
quiet_cmd_ttd_link = '===> Linking $@'
|
||||
cmd_ttd_link = $(CC) $(LDFLAGS) $(TTDLDFLAGS) $(OBJS) $(LIBS) -o $@
|
||||
|
||||
COMPILE_PARAMS=$(CFLAGS) $(CDEFS) -MD -c $< -o $@
|
||||
|
||||
quiet_cmd_c_compile = '===> Compiling $<'
|
||||
cmd_c_compile = $(CC) $(COMPILE_PARAMS)
|
||||
|
||||
quiet_cmd_cxx_compile = '===> Compiling $<'
|
||||
cmd_cxx_compile = $(CXX) $(COMPILE_PARAMS)
|
||||
|
||||
|
||||
##############################################################################
|
||||
#
|
||||
@@ -772,12 +788,16 @@ quiet_cmd_cxx_compile = '===> Compiling $<'
|
||||
|
||||
|
||||
ifdef OSX
|
||||
# needs to be before all
|
||||
OSX:=OSX
|
||||
OSX_MIDI_PLAYER_FILE:=os/macos/OpenTTDMidi.class
|
||||
endif
|
||||
|
||||
|
||||
all: endian_target.h endian_host.h $(UPDATECONFIG) $(LANGS) $(TTD) $(OSX) $(endwarnings)
|
||||
all: endian_target.h endian_host.h $(UPDATECONFIG) $(LANGS) $(TTD) $(OSX)
|
||||
|
||||
ifdef OSX
|
||||
-include os/macosx/Makefile
|
||||
endif
|
||||
|
||||
endian_host.h: $(ENDIAN_CHECK)
|
||||
@echo '===> Testing endianness for host'
|
||||
@@ -788,37 +808,17 @@ endian_target.h: $(ENDIAN_CHECK)
|
||||
$(Q)./$(ENDIAN_CHECK) $(ENDIAN_FORCE) > $@
|
||||
|
||||
$(ENDIAN_CHECK): endian_check.c
|
||||
$(call cmd,compile_link)
|
||||
@echo '===> Compiling and Linking $@'
|
||||
$(Q)$(CC_HOST) $(CFLAGS_HOST) $(CDEFS) $< -o $@
|
||||
|
||||
|
||||
$(TTD): table/strings.h $(OBJS) $(MAKE_CONFIG)
|
||||
$(call cmd,ttd_link)
|
||||
|
||||
$(OSX): $(TTD)
|
||||
$(Q)rm -fr "$(OSXAPP)"
|
||||
$(Q)mkdir -p "$(OSXAPP)"/Contents/MacOS
|
||||
$(Q)mkdir -p "$(OSXAPP)"/Contents/Resources
|
||||
$(Q)mkdir -p "$(OSXAPP)"/Contents/Data
|
||||
$(Q)mkdir -p "$(OSXAPP)"/Contents/Lang
|
||||
$(Q)echo "APPL????" > "$(OSXAPP)"/Contents/PkgInfo
|
||||
$(Q)cp os/macosx/openttd.icns "$(OSXAPP)"/Contents/Resources/openttd.icns
|
||||
$(Q)os/macosx/plistgen.sh "$(OSXAPP)" "$(REV)"
|
||||
$(Q)cp os/macosx/track_starter "$(OSXAPP)"/Contents/MacOS
|
||||
$(Q)ls os/macosx | grep -q "\.class" || \
|
||||
javac os/macosx/OpenTTDMidi.java
|
||||
$(Q)cp os/macosx/OpenTTDMidi.class "$(OSXAPP)"/Contents/MacOS
|
||||
$(Q)cp data/* "$(OSXAPP)"/Contents/Data/
|
||||
$(Q)cp lang/*.lng "$(OSXAPP)"/Contents/Lang/
|
||||
$(Q)cp $(TTD) "$(OSXAPP)"/Contents/MacOS/$(TTD)
|
||||
|
||||
$(endwarnings): $(64_bit_warnings)
|
||||
|
||||
$(64_bit_warnings):
|
||||
$(warning 64 bit CPUs will get some 64 bit specific bugs!)
|
||||
$(warning If you see any bugs, include in your bug report that you use a 64 bit CPU)
|
||||
$(TTD): $(OBJS) $(MAKE_CONFIG)
|
||||
@echo '===> Linking $@'
|
||||
$(Q)$(CC) $(LDFLAGS) $(TTDLDFLAGS) $(OBJS) $(LIBS) -o $@
|
||||
|
||||
$(STRGEN): strgen/strgen.c endian_host.h
|
||||
$(call cmd,compile_link)
|
||||
@echo '===> Compiling and Linking $@'
|
||||
$(Q)$(CC_HOST) $(CFLAGS_HOST) $(CDEFS) $< -o $@
|
||||
|
||||
table/strings.h: lang/english.txt $(STRGEN)
|
||||
@echo '===> Generating $@'
|
||||
@@ -826,11 +826,7 @@ table/strings.h: lang/english.txt $(STRGEN)
|
||||
|
||||
lang/%.lng: lang/%.txt $(STRGEN) lang/english.txt
|
||||
@echo '===> Compiling language $(*F)'
|
||||
$(Q)$(STRGEN) $(STRGEN_FLAGS) $< $(LANG_ERRORS)
|
||||
|
||||
winres.o: ttd.rc
|
||||
@echo '===> Compiling resource $<'
|
||||
$(Q)$(WINDRES) -o $@ $<
|
||||
$(Q)$(STRGEN) $(STRGEN_FLAGS) $< $(LANG_ERRORS) || rm -f $@
|
||||
|
||||
ifdef MORPHOS
|
||||
release: all
|
||||
@@ -867,47 +863,9 @@ release: all
|
||||
.PHONY: release
|
||||
endif
|
||||
|
||||
ifdef OSX
|
||||
release: all
|
||||
$(Q)mkdir -p "OpenTTD $(RELEASE)"
|
||||
$(Q)mkdir -p "OpenTTD $(RELEASE)"/docs
|
||||
$(Q)mkdir -p "OpenTTD $(RELEASE)"/scenario
|
||||
$(Q)cp -R $(OSXAPP) "OpenTTD $(RELEASE)"/
|
||||
$(Q)cp docs/OSX_where_did_the_package_go.txt "OpenTTD $(RELEASE)"/Where\ did\ the\ package\ go.txt
|
||||
$(Q)cp readme.txt "OpenTTD $(RELEASE)"/docs/
|
||||
$(Q)cp docs/README_if_game_crashed_on_OSX.txt "OpenTTD $(RELEASE)"/docs/readme\ if\ crashed\ on\ OSX.txt
|
||||
$(Q)cp docs/console.txt "OpenTTD $(RELEASE)"/docs/
|
||||
$(Q)cp COPYING "OpenTTD $(RELEASE)"/docs/
|
||||
$(Q)cp changelog.txt "OpenTTD $(RELEASE)"/docs/
|
||||
$(Q)cp docs/README_if_game_crashed_on_OSX.txt "OpenTTD $(RELEASE)"/docs/
|
||||
$(Q)cp os/macosx/*.webloc "OpenTTD $(RELEASE)"
|
||||
$(Q)cp known-bugs.txt "OpenTTD $(RELEASE)"/known-bugs.txt
|
||||
$(Q)cp scenario/* "OpenTTD $(RELEASE)"/scenario/
|
||||
$(Q)/usr/bin/hdiutil create -ov -format UDZO -srcfolder "OpenTTD $(RELEASE)" openttd-"$(RELEASE)"-osx.dmg
|
||||
$(Q)rm -fr "OpenTTD $(RELEASE)"
|
||||
|
||||
nightly_build: all
|
||||
$(Q)mkdir -p "OpenTTD_nightly_$(DATE)"
|
||||
$(Q)mkdir -p "OpenTTD_nightly_$(DATE)"/docs
|
||||
$(Q)cp -R $(OSXAPP) "OpenTTD_nightly_$(DATE)"/
|
||||
$(Q)cp docs/OSX_where_did_the_package_go.txt "OpenTTD_nightly_$(DATE)"/Where\ did\ the\ package\ go.txt
|
||||
$(Q)cp readme.txt "OpenTTD_nightly_$(DATE)"/docs/
|
||||
$(Q)cp docs/README_if_game_crashed_on_OSX.txt "OpenTTD_nightly_$(DATE)"/docs/readme\ if\ crashed\ on\ OSX.txt
|
||||
$(Q)cp docs/console.txt "OpenTTD_nightly_$(DATE)"/docs/
|
||||
$(Q)cp COPYING "OpenTTD_nightly_$(DATE)"/docs/
|
||||
$(Q)cp revisionlog.txt "OpenTTD_nightly_$(DATE)"/revisionlog.txt
|
||||
$(Q)cp docs/README_if_game_crashed_on_OSX.txt "OpenTTD_nightly_$(DATE)"/docs/
|
||||
$(Q)cp os/macosx/*.webloc "OpenTTD_nightly_$(DATE)"/
|
||||
$(Q)/usr/bin/hdiutil create -ov -format UDZO -srcfolder "OpenTTD_nightly_$(DATE)" openttd-nightly-"$(DATE)".dmg
|
||||
$(Q)rm -fr "OpenTTD_nightly_$(DATE)"
|
||||
|
||||
.PHONY: release nightly_build
|
||||
endif
|
||||
|
||||
rev.c: FORCE
|
||||
@# setting the revision number in a place, there the binary can read it
|
||||
@echo 'const char _openttd_revision[] = "$(REV)";' >>rev.c.new
|
||||
@echo 'const int _revision_number = $(REV_NUMBER);' >>rev.c.new
|
||||
@# some additions for MorphOS versions tag
|
||||
@echo '#ifdef __MORPHOS__' >>rev.c.new
|
||||
@echo 'const char morphos_versions_tag[] = "\\0$$VER: OpenTTD $(REV) ('${BUILDDATE}') © OpenTTD Team [MorphOS, PowerPC]";' >>rev.c.new
|
||||
@@ -954,13 +912,22 @@ endif
|
||||
$(DATA_DIR_INSTALL)/data \
|
||||
$(DATA_DIR_INSTALL)/gm \
|
||||
$(BINARY_DIR_INSTALL)
|
||||
mkdir -p $(PERSONAL_DIR)/scenario
|
||||
ifndef USE_HOMEDIR
|
||||
mkdir -p $(PERSONAL_DIR)/scenario
|
||||
else
|
||||
mkdir -p $(DATA_DIR_INSTALL)/scenario
|
||||
endif
|
||||
install $(TTD) $(BINARY_DIR_INSTALL)
|
||||
install -m 644 lang/*.lng $(DATA_DIR_INSTALL)/lang
|
||||
install -m 644 data/*.grf $(DATA_DIR_INSTALL)/data
|
||||
install -m 644 data/opntitle.dat $(DATA_DIR_INSTALL)/data
|
||||
install -m 644 media/openttd.64.png $(DATA_DIR_INSTALL)
|
||||
install -m 644 media/openttd.64.png $(ICON_DIR_INSTALL)
|
||||
install -m 644 media/openttd.32.xpm $(ICON_DIR_INSTALL)
|
||||
ifndef USE_HOMEDIR
|
||||
cp scenario/* $(PERSONAL_DIR)/scenario/
|
||||
else
|
||||
cp scenario/* $(DATA_DIR_INSTALL)/scenario/
|
||||
endif
|
||||
else #MorphOS
|
||||
install:
|
||||
$(error make install is not supported on MorphOS)
|
||||
@@ -974,7 +941,7 @@ endif
|
||||
love:
|
||||
@echo "YES! I thought you would never ask. We will have a great time. You can keep me turned on all night"
|
||||
|
||||
.PHONY: clean all $(OSX) install $(64_bit_warnings) $(endwarnings) love
|
||||
.PHONY: clean all $(OSX) install love
|
||||
|
||||
|
||||
### Automatic configuration
|
||||
@@ -993,30 +960,52 @@ upgradeconf: $(MAKE_CONFIG)
|
||||
### Internal build rules
|
||||
|
||||
# This makes sure the .deps dir is always around.
|
||||
DEPS_MAGIC := $(shell mkdir .deps > /dev/null 2>&1 || :)
|
||||
DEPS_MAGIC := $(shell mkdir -p $(sort $(dir $(DEPS))))
|
||||
|
||||
depend:
|
||||
@true # The include handles this automagically
|
||||
|
||||
# Introduce the dependencies
|
||||
ifeq ($(findstring $(MAKECMDGOALS), clean info),)
|
||||
-include $(DEPS)
|
||||
endif
|
||||
|
||||
# This compiles the object file as well as silently updating its dependencies
|
||||
# list at the same time. It is not an issue that they aren't around during the
|
||||
# first compilation round as we just build everything at that time anyway,
|
||||
# therefore we do not need to watch deps.
|
||||
|
||||
%.o: %.c $(MAKE_CONFIG) endian_target.h table/strings.h
|
||||
$(call cmd,c_compile)
|
||||
@mv $(<:%.c=%.d) $(<:%.c=.deps/%.d)
|
||||
|
||||
%.o: %.cpp $(MAKE_CONFIG) endian_target.h table/strings.h
|
||||
$(call cmd,cxx_compile)
|
||||
@mv $(<:%.cpp=%.d) $(<:%.cpp=.deps/%.d)
|
||||
|
||||
# Silence stale header dependencies
|
||||
# Silence stale header dependency errors
|
||||
%.h:
|
||||
@true
|
||||
|
||||
.deps/%.d: %.c $(MAKE_CONFIG) table/strings.h endian_target.h
|
||||
@echo '===> DEP $<'
|
||||
$(Q)$(CC) $(CFLAGS) $(CDEFS) -MM $< | sed 's#^$(@F:%.d=%.o):#$@ $(@:.deps/%.d=%.o):#' > $@
|
||||
|
||||
.deps/%.d: %.cpp $(MAKE_CONFIG) table/strings.h endian_target.h
|
||||
@echo '===> DEP $<'
|
||||
$(Q)$(CXX) $(CFLAGS) $(CDEFS) -MM $< | sed 's#^$(@F:%.d=%.o):#$@ $(@:.deps/%.d=%.o):#' > $@
|
||||
|
||||
.deps/%.d: %.m $(MAKE_CONFIG) table/strings.h endian_target.h
|
||||
@echo '===> DEP $<'
|
||||
$(Q)$(CC) $(OBJCFLAGS) $(CDEFS) -MM $< | sed 's#^$(@F:%.d=%.o):#$@ $(@:.deps/%.d=%.o):#' > $@
|
||||
|
||||
|
||||
%.o: %.c $(MAKE_CONFIG)
|
||||
@echo '===> Compiling $<'
|
||||
$(Q)$(CC) $(CFLAGS) $(CDEFS) -c -o $@ $<
|
||||
|
||||
%.o: %.cpp $(MAKE_CONFIG)
|
||||
@echo '===> Compiling $<'
|
||||
$(Q)$(CXX) $(CFLAGS) $(CDEFS) -c -o $@ $<
|
||||
|
||||
%.o: %.m $(MAKE_CONFIG)
|
||||
@echo '===> Compiling $<'
|
||||
$(Q)$(CC) $(CFLAGS) $(CDEFS) -c -o $@ $<
|
||||
|
||||
%.o: %.rc
|
||||
@echo '===> Compiling resource $<'
|
||||
$(Q)$(WINDRES) -o $@ $<
|
||||
|
||||
|
||||
info:
|
||||
@echo 'CFLAGS = $(CFLAGS)'
|
||||
@echo 'LDFLAGS = $(LDFLAGS)'
|
||||
@echo 'LIBS = $(LIBS)'
|
||||
@echo 'CDEFS = $(CDEFS)'
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
// stdafx.cpp : source file that includes just the standard includes
|
||||
// ttd.pch will be the pre-compiled header
|
||||
// stdafx.obj will contain the pre-compiled type information
|
||||
|
||||
@@ -0,0 +1,263 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "../stdafx.h"
|
||||
#include "../openttd.h"
|
||||
#include "../variables.h"
|
||||
#include "../command.h"
|
||||
#include "../network.h"
|
||||
#include "ai.h"
|
||||
#include "default/default.h"
|
||||
|
||||
/**
|
||||
* Dequeues commands put in the queue via AI_PutCommandInQueue.
|
||||
*/
|
||||
static void AI_DequeueCommands(byte player)
|
||||
{
|
||||
AICommand *com, *entry_com;
|
||||
|
||||
entry_com = _ai_player[player].queue;
|
||||
|
||||
/* It happens that DoCommandP issues a new DoCommandAI which adds a new command
|
||||
* to this very same queue (don't argue about this, if it currently doesn't
|
||||
* happen I can tell you it will happen with AIScript -- TrueLight). If we
|
||||
* do not make the queue NULL, that commands will be dequeued immediatly.
|
||||
* Therefor we safe the entry-point to entry_com, and make the queue NULL, so
|
||||
* the new queue can be safely built up. */
|
||||
_ai_player[player].queue = NULL;
|
||||
_ai_player[player].queue_tail = NULL;
|
||||
|
||||
/* Dequeue all commands */
|
||||
while ((com = entry_com) != NULL) {
|
||||
_current_player = player;
|
||||
|
||||
/* Copy the DP back in place */
|
||||
_cmd_text = com->text;
|
||||
DoCommandP(com->tile, com->p1, com->p2, NULL, com->procc);
|
||||
|
||||
/* Free item */
|
||||
entry_com = com->next;
|
||||
if (com->text != NULL)
|
||||
free(com->text);
|
||||
free(com);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Needed for SP; we need to delay DoCommand with 1 tick, because else events
|
||||
* will make infinite loops (AIScript).
|
||||
*/
|
||||
static void AI_PutCommandInQueue(byte player, uint tile, uint32 p1, uint32 p2, uint procc)
|
||||
{
|
||||
AICommand *com;
|
||||
|
||||
if (_ai_player[player].queue_tail == NULL) {
|
||||
/* There is no item in the queue yet, create the queue */
|
||||
_ai_player[player].queue = malloc(sizeof(AICommand));
|
||||
_ai_player[player].queue_tail = _ai_player[player].queue;
|
||||
} else {
|
||||
/* Add an item at the end */
|
||||
_ai_player[player].queue_tail->next = malloc(sizeof(AICommand));
|
||||
_ai_player[player].queue_tail = _ai_player[player].queue_tail->next;
|
||||
}
|
||||
|
||||
/* This is our new item */
|
||||
com = _ai_player[player].queue_tail;
|
||||
|
||||
/* Assign the info */
|
||||
com->tile = tile;
|
||||
com->p1 = p1;
|
||||
com->p2 = p2;
|
||||
com->procc = procc;
|
||||
com->next = NULL;
|
||||
com->text = NULL;
|
||||
|
||||
/* Copy the cmd_text, if needed */
|
||||
if (_cmd_text != NULL) {
|
||||
com->text = strdup(_cmd_text);
|
||||
_cmd_text = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Executes a raw DoCommand for the AI.
|
||||
*/
|
||||
int32 AI_DoCommand(uint tile, uint32 p1, uint32 p2, uint32 flags, uint procc)
|
||||
{
|
||||
PlayerID old_lp;
|
||||
int32 res = 0;
|
||||
char *tmp_cmdtext = NULL;
|
||||
|
||||
/* If you enable DC_EXEC with DC_QUERY_COST you are a really strange
|
||||
* person.. should we check for those funny jokes?
|
||||
*/
|
||||
|
||||
/* The test already free _cmd_text in most cases, so let's backup the string, else we have a problem ;) */
|
||||
if (_cmd_text != NULL)
|
||||
tmp_cmdtext = strdup(_cmd_text);
|
||||
|
||||
/* First, do a test-run to see if we can do this */
|
||||
res = DoCommandByTile(tile, p1, p2, flags & ~DC_EXEC, procc);
|
||||
/* The command failed, or you didn't want to execute, or you are quering, return */
|
||||
if ((CmdFailed(res)) || !(flags & DC_EXEC) || (flags & DC_QUERY_COST)) {
|
||||
if (tmp_cmdtext != NULL)
|
||||
free(tmp_cmdtext);
|
||||
return res;
|
||||
}
|
||||
|
||||
/* Recover _cmd_text */
|
||||
if (tmp_cmdtext != NULL)
|
||||
_cmd_text = tmp_cmdtext;
|
||||
|
||||
/* If we did a DC_EXEC, and the command did not return an error, execute it
|
||||
over the network */
|
||||
if (flags & DC_AUTO) procc |= CMD_AUTO;
|
||||
if (flags & DC_NO_WATER) procc |= CMD_NO_WATER;
|
||||
|
||||
/* NetworkSend_Command needs _local_player to be set correctly, so
|
||||
adjust it, and put it back right after the function */
|
||||
old_lp = _local_player;
|
||||
_local_player = _current_player;
|
||||
|
||||
#ifdef ENABLE_NETWORK
|
||||
/* Send the command */
|
||||
if (_networking)
|
||||
/* Network is easy, send it to his handler */
|
||||
NetworkSend_Command(tile, p1, p2, procc, NULL);
|
||||
else
|
||||
#endif
|
||||
/* If we execute BuildCommands directly in SP, we have a big problem with events
|
||||
* so we need to delay is for 1 tick */
|
||||
AI_PutCommandInQueue(_current_player, tile, p1, p2, procc);
|
||||
|
||||
/* Set _local_player back */
|
||||
_local_player = old_lp;
|
||||
|
||||
/* Free the temp _cmd_text var */
|
||||
if (tmp_cmdtext != NULL)
|
||||
free(tmp_cmdtext);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* Run 1 tick of the AI. Don't overdo it, keep it realistic.
|
||||
*/
|
||||
static void AI_RunTick(PlayerID player)
|
||||
{
|
||||
extern void AiNewDoGameLoop(Player *p);
|
||||
|
||||
Player *p = GetPlayer(player);
|
||||
_current_player = player;
|
||||
|
||||
if (_patches.ainew_active) {
|
||||
AiNewDoGameLoop(p);
|
||||
} else {
|
||||
/* Enable all kind of cheats the old AI needs in order to operate correctly... */
|
||||
_is_old_ai_player = true;
|
||||
AiDoGameLoop(p);
|
||||
_is_old_ai_player = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* The gameloop for AIs.
|
||||
* Handles one tick for all the AIs.
|
||||
*/
|
||||
void AI_RunGameLoop(void)
|
||||
{
|
||||
/* Don't do anything if ai is disabled */
|
||||
if (!_ai.enabled) return;
|
||||
|
||||
/* Don't do anything if we are a network-client
|
||||
* (too bad when a client joins, he thinks the AIs are real, so it wants to control
|
||||
* them.. this avoids that, while loading a network game in singleplayer, does make
|
||||
* the AIs to continue ;))
|
||||
*/
|
||||
if (_networking && !_network_server && !_ai.network_client)
|
||||
return;
|
||||
|
||||
/* New tick */
|
||||
_ai.tick++;
|
||||
|
||||
/* Make sure the AI follows the difficulty rule.. */
|
||||
assert(_opt.diff.competitor_speed <= 4);
|
||||
if ((_ai.tick & ((1 << (4 - _opt.diff.competitor_speed)) - 1)) != 0)
|
||||
return;
|
||||
|
||||
/* Check for AI-client (so joining a network with an AI) */
|
||||
if (_ai.network_client && _ai_player[_ai.network_playas].active) {
|
||||
/* Run the script */
|
||||
AI_DequeueCommands(_ai.network_playas);
|
||||
AI_RunTick(_ai.network_playas);
|
||||
} else if (!_networking || _network_server) {
|
||||
/* Check if we want to run AIs (server or SP only) */
|
||||
Player *p;
|
||||
|
||||
FOR_ALL_PLAYERS(p) {
|
||||
if (p->is_active && p->is_ai) {
|
||||
/* This should always be true, else something went wrong... */
|
||||
assert(_ai_player[p->index].active);
|
||||
|
||||
/* Run the script */
|
||||
AI_DequeueCommands(p->index);
|
||||
AI_RunTick(p->index);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
_current_player = OWNER_NONE;
|
||||
}
|
||||
|
||||
/**
|
||||
* A new AI sees the day of light. You can do here what ever you think is needed.
|
||||
*/
|
||||
void AI_StartNewAI(PlayerID player)
|
||||
{
|
||||
assert(player < MAX_PLAYERS);
|
||||
|
||||
/* Called if a new AI is booted */
|
||||
_ai_player[player].active = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* This AI player died. Give it some chance to make a final puf.
|
||||
*/
|
||||
void AI_PlayerDied(PlayerID player)
|
||||
{
|
||||
if (_ai.network_client && _ai.network_playas == player)
|
||||
_ai.network_playas = OWNER_SPECTATOR;
|
||||
|
||||
/* Called if this AI died */
|
||||
_ai_player[player].active = false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialize some AI-related stuff.
|
||||
*/
|
||||
void AI_Initialize(void)
|
||||
{
|
||||
bool ai_network_client = _ai.network_client;
|
||||
|
||||
/* First, make sure all AIs are DEAD! */
|
||||
AI_Uninitialize();
|
||||
|
||||
memset(&_ai, 0, sizeof(_ai));
|
||||
memset(&_ai_player, 0, sizeof(_ai_player));
|
||||
|
||||
_ai.network_client = ai_network_client;
|
||||
_ai.network_playas = OWNER_SPECTATOR;
|
||||
_ai.enabled = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Deinitializer for AI-related stuff.
|
||||
*/
|
||||
void AI_Uninitialize(void)
|
||||
{
|
||||
Player* p;
|
||||
|
||||
FOR_ALL_PLAYERS(p) {
|
||||
if (p->is_active && p->is_ai) AI_PlayerDied(p->index);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,112 @@
|
||||
#ifndef AI_H
|
||||
#define AI_H
|
||||
|
||||
#include "../functions.h"
|
||||
#include "../network.h"
|
||||
#include "../player.h"
|
||||
|
||||
/* How DoCommands look like for an AI */
|
||||
typedef struct AICommand {
|
||||
uint32 tile;
|
||||
uint32 p1;
|
||||
uint32 p2;
|
||||
uint32 procc;
|
||||
|
||||
char *text;
|
||||
uint uid;
|
||||
|
||||
struct AICommand *next;
|
||||
} AICommand;
|
||||
|
||||
/* The struct for an AIScript Player */
|
||||
typedef struct AIPlayer {
|
||||
bool active; //! Is this AI active?
|
||||
AICommand *queue; //! The commands that he has in his queue
|
||||
AICommand *queue_tail; //! The tail of this queue
|
||||
} AIPlayer;
|
||||
|
||||
/* The struct to keep some data about the AI in general */
|
||||
typedef struct AIStruct {
|
||||
/* General */
|
||||
bool enabled; //! Is AI enabled?
|
||||
uint tick; //! The current tick (something like _frame_counter, only for AIs)
|
||||
|
||||
/* For network-clients (a OpenTTD client who acts as an AI connected to a server) */
|
||||
bool network_client; //! Are we a network_client?
|
||||
uint8 network_playas; //! The current network player we are connected as
|
||||
} AIStruct;
|
||||
|
||||
VARDEF AIStruct _ai;
|
||||
VARDEF AIPlayer _ai_player[MAX_PLAYERS];
|
||||
|
||||
// ai.c
|
||||
void AI_StartNewAI(PlayerID player);
|
||||
void AI_PlayerDied(PlayerID player);
|
||||
void AI_RunGameLoop(void);
|
||||
void AI_Initialize(void);
|
||||
void AI_Uninitialize(void);
|
||||
int32 AI_DoCommand(uint tile, uint32 p1, uint32 p2, uint32 flags, uint procc);
|
||||
|
||||
/** Is it allowed to start a new AI.
|
||||
* This function checks some boundries to see if we should launch a new AI.
|
||||
* @return True if we can start a new AI.
|
||||
*/
|
||||
static inline bool AI_AllowNewAI(void)
|
||||
{
|
||||
/* If disabled, no AI */
|
||||
if (!_ai.enabled)
|
||||
return false;
|
||||
|
||||
/* If in network, but no server, no AI */
|
||||
if (_networking && !_network_server)
|
||||
return false;
|
||||
|
||||
/* If in network, and server, possible AI */
|
||||
if (_networking && _network_server) {
|
||||
/* Do we want AIs in multiplayer? */
|
||||
if (!_patches.ai_in_multiplayer)
|
||||
return false;
|
||||
|
||||
/* Only the NewAI is allowed... sadly enough the old AI just doesn't support this
|
||||
* system, because all commands are delayed by at least 1 tick, which causes
|
||||
* a big problem, because it uses variables that are only set AFTER the command
|
||||
* is really executed... */
|
||||
if (!_patches.ainew_active)
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
#define AI_CHANCE16(a,b) ((uint16) AI_Random() <= (uint16)((65536 * a) / b))
|
||||
#define AI_CHANCE16R(a,b,r) ((uint16)(r = AI_Random()) <= (uint16)((65536 * a) / b))
|
||||
|
||||
/**
|
||||
* The random-function that should be used by ALL AIs.
|
||||
*/
|
||||
static inline uint AI_RandomRange(uint max)
|
||||
{
|
||||
/* We pick RandomRange if we are in SP (so when saved, we do the same over and over)
|
||||
* but we pick InteractiveRandomRange if we are a network_server or network-client.
|
||||
*/
|
||||
if (_networking)
|
||||
return InteractiveRandomRange(max);
|
||||
else
|
||||
return RandomRange(max);
|
||||
}
|
||||
|
||||
/**
|
||||
* The random-function that should be used by ALL AIs.
|
||||
*/
|
||||
static inline uint32 AI_Random(void)
|
||||
{
|
||||
/* We pick RandomRange if we are in SP (so when saved, we do the same over and over)
|
||||
* but we pick InteractiveRandomRange if we are a network_server or network-client.
|
||||
*/
|
||||
if (_networking)
|
||||
return InteractiveRandom();
|
||||
else
|
||||
return Random();
|
||||
}
|
||||
|
||||
#endif /* AI_H */
|
||||
+232
-245
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,8 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef DEFAULT_H
|
||||
#define DEFAULT_H
|
||||
|
||||
void AiDoGameLoop(Player*);
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,273 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "../../stdafx.h"
|
||||
#include "../../openttd.h"
|
||||
#include "../../debug.h"
|
||||
#include "../../functions.h"
|
||||
#include "../../map.h"
|
||||
#include "../../tile.h"
|
||||
#include "../../command.h"
|
||||
#include "trolly.h"
|
||||
#include "../../engine.h"
|
||||
#include "../../station.h"
|
||||
#include "../../variables.h"
|
||||
#include "../ai.h"
|
||||
|
||||
// Build HQ
|
||||
// Params:
|
||||
// tile : tile where HQ is going to be build
|
||||
bool AiNew_Build_CompanyHQ(Player *p, TileIndex tile)
|
||||
{
|
||||
if (CmdFailed(AI_DoCommand(tile, 0, 0, DC_AUTO | DC_NO_WATER, CMD_BUILD_COMPANY_HQ)))
|
||||
return false;
|
||||
AI_DoCommand(tile, 0, 0, DC_EXEC | DC_AUTO | DC_NO_WATER, CMD_BUILD_COMPANY_HQ);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
// Build station
|
||||
// Params:
|
||||
// type : AI_TRAIN/AI_BUS/AI_TRUCK : indicates the type of station
|
||||
// tile : tile where station is going to be build
|
||||
// length : in case of AI_TRAIN: length of station
|
||||
// numtracks : in case of AI_TRAIN: tracks of station
|
||||
// direction : the direction of the station
|
||||
// flag : flag passed to DoCommand (normally 0 to get the cost or DC_EXEC to build it)
|
||||
int AiNew_Build_Station(Player *p, byte type, TileIndex tile, byte length, byte numtracks, byte direction, byte flag)
|
||||
{
|
||||
if (type == AI_TRAIN)
|
||||
return AI_DoCommand(tile, direction + (numtracks << 8) + (length << 16), 0, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_RAILROAD_STATION);
|
||||
|
||||
if (type == AI_BUS)
|
||||
return AI_DoCommand(tile, direction, RS_BUS, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD_STOP);
|
||||
|
||||
return AI_DoCommand(tile, direction, RS_TRUCK, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD_STOP);
|
||||
}
|
||||
|
||||
|
||||
// Builds a brdige. The second best out of the ones available for this player
|
||||
// Params:
|
||||
// tile_a : starting point
|
||||
// tile_b : end point
|
||||
// flag : flag passed to DoCommand
|
||||
int AiNew_Build_Bridge(Player *p, TileIndex tile_a, TileIndex tile_b, byte flag)
|
||||
{
|
||||
int bridge_type, bridge_len, type, type2;
|
||||
|
||||
// Find a good bridgetype (the best money can buy)
|
||||
bridge_len = GetBridgeLength(tile_a, tile_b);
|
||||
type = type2 = 0;
|
||||
for (bridge_type = MAX_BRIDGES-1; bridge_type >= 0; bridge_type--) {
|
||||
if (CheckBridge_Stuff(bridge_type, bridge_len)) {
|
||||
type2 = type;
|
||||
type = bridge_type;
|
||||
// We found two bridges, exit
|
||||
if (type2 != 0) break;
|
||||
}
|
||||
}
|
||||
// There is only one bridge that can be build..
|
||||
if (type2 == 0 && type != 0) type2 = type;
|
||||
|
||||
// Now, simply, build the bridge!
|
||||
if (p->ainew.tbt == AI_TRAIN)
|
||||
return AI_DoCommand(tile_a, tile_b, (0<<8) + type2, flag | DC_AUTO, CMD_BUILD_BRIDGE);
|
||||
|
||||
return AI_DoCommand(tile_a, tile_b, (0x80 << 8) + type2, flag | DC_AUTO, CMD_BUILD_BRIDGE);
|
||||
}
|
||||
|
||||
|
||||
// Build the route part by part
|
||||
// Basicly what this function do, is build that amount of parts of the route
|
||||
// that go in the same direction. It sets 'part' to the last part of the route builded.
|
||||
// The return value is the cost for the builded parts
|
||||
//
|
||||
// Params:
|
||||
// PathFinderInfo : Pointer to the PathFinderInfo used for AiPathFinder
|
||||
// part : Which part we need to build
|
||||
//
|
||||
// TODO: skip already builded road-pieces (e.g.: cityroad)
|
||||
int AiNew_Build_RoutePart(Player *p, Ai_PathFinderInfo *PathFinderInfo, byte flag)
|
||||
{
|
||||
int part = PathFinderInfo->position;
|
||||
byte *route_extra = PathFinderInfo->route_extra;
|
||||
TileIndex *route = PathFinderInfo->route;
|
||||
int dir;
|
||||
int old_dir = -1;
|
||||
int cost = 0;
|
||||
int res;
|
||||
// We need to calculate the direction with the parent of the parent.. so we skip
|
||||
// the first pieces and the last piece
|
||||
if (part < 1) part = 1;
|
||||
// When we are done, stop it
|
||||
if (part >= PathFinderInfo->route_length - 1) { PathFinderInfo->position = -2; return 0; }
|
||||
|
||||
|
||||
if (PathFinderInfo->rail_or_road) {
|
||||
// Tunnel code
|
||||
if ((AI_PATHFINDER_FLAG_TUNNEL & route_extra[part]) != 0) {
|
||||
cost += AI_DoCommand(route[part], 0, 0, flag, CMD_BUILD_TUNNEL);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: tunnel could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
// Bridge code
|
||||
if ((AI_PATHFINDER_FLAG_BRIDGE & route_extra[part]) != 0) {
|
||||
cost += AiNew_Build_Bridge(p, route[part], route[part-1], flag);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: bridge could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
// Build normal rail
|
||||
// Keep it doing till we go an other way
|
||||
if (route_extra[part-1] == 0 && route_extra[part] == 0) {
|
||||
while (route_extra[part] == 0) {
|
||||
// Get the current direction
|
||||
dir = AiNew_GetRailDirection(route[part-1], route[part], route[part+1]);
|
||||
// Is it the same as the last one?
|
||||
if (old_dir != -1 && old_dir != dir) break;
|
||||
old_dir = dir;
|
||||
// Build the tile
|
||||
res = AI_DoCommand(route[part], 0, dir, flag, CMD_BUILD_SINGLE_RAIL);
|
||||
if (CmdFailed(res)) {
|
||||
// Problem.. let's just abort it all!
|
||||
p->ainew.state = AI_STATE_NOTHING;
|
||||
return 0;
|
||||
}
|
||||
cost += res;
|
||||
// Go to the next tile
|
||||
part++;
|
||||
// Check if it is still in range..
|
||||
if (part >= PathFinderInfo->route_length - 1) break;
|
||||
}
|
||||
part--;
|
||||
}
|
||||
// We want to return the last position, so we go back one
|
||||
PathFinderInfo->position = part;
|
||||
} else {
|
||||
// Tunnel code
|
||||
if ((AI_PATHFINDER_FLAG_TUNNEL & route_extra[part]) != 0) {
|
||||
cost += AI_DoCommand(route[part], 0x200, 0, flag, CMD_BUILD_TUNNEL);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: tunnel could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
// Bridge code
|
||||
if ((AI_PATHFINDER_FLAG_BRIDGE & route_extra[part]) != 0) {
|
||||
cost += AiNew_Build_Bridge(p, route[part], route[part+1], flag);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: bridge could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
// Build normal road
|
||||
// Keep it doing till we go an other way
|
||||
// EnsureNoVehicle makes sure we don't build on a tile where a vehicle is. This way
|
||||
// it will wait till the vehicle is gone..
|
||||
if (route_extra[part-1] == 0 && route_extra[part] == 0 && (flag != DC_EXEC || EnsureNoVehicle(route[part]))) {
|
||||
while (route_extra[part] == 0 && (flag != DC_EXEC || EnsureNoVehicle(route[part]))) {
|
||||
// Get the current direction
|
||||
dir = AiNew_GetRoadDirection(route[part-1], route[part], route[part+1]);
|
||||
// Is it the same as the last one?
|
||||
if (old_dir != -1 && old_dir != dir) break;
|
||||
old_dir = dir;
|
||||
// There is already some road, and it is a bridge.. don't build!!!
|
||||
if (!IsTileType(route[part], MP_TUNNELBRIDGE)) {
|
||||
// Build the tile
|
||||
res = AI_DoCommand(route[part], dir, 0, flag | DC_NO_WATER, CMD_BUILD_ROAD);
|
||||
// Currently, we ignore CMD_ERRORs!
|
||||
if (CmdFailed(res) && flag == DC_EXEC && !IsTileType(route[part], MP_STREET) && !EnsureNoVehicle(route[part])) {
|
||||
// Problem.. let's just abort it all!
|
||||
DEBUG(ai,0)("Darn, the route could not be builded.. aborting!");
|
||||
p->ainew.state = AI_STATE_NOTHING;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!CmdFailed(res)) cost += res;
|
||||
}
|
||||
// Go to the next tile
|
||||
part++;
|
||||
// Check if it is still in range..
|
||||
if (part >= PathFinderInfo->route_length - 1) break;
|
||||
}
|
||||
part--;
|
||||
// We want to return the last position, so we go back one
|
||||
}
|
||||
if (!EnsureNoVehicle(route[part]) && flag == DC_EXEC) part--;
|
||||
PathFinderInfo->position = part;
|
||||
}
|
||||
|
||||
return cost;
|
||||
}
|
||||
|
||||
|
||||
// This functions tries to find the best vehicle for this type of cargo
|
||||
// It returns vehicle_id or -1 if not found
|
||||
int AiNew_PickVehicle(Player *p)
|
||||
{
|
||||
if (p->ainew.tbt == AI_TRAIN) {
|
||||
// Not supported yet
|
||||
return -1;
|
||||
} else {
|
||||
int start, count, i, ret = CMD_ERROR;
|
||||
start = _cargoc.ai_roadveh_start[p->ainew.cargo];
|
||||
count = _cargoc.ai_roadveh_count[p->ainew.cargo];
|
||||
|
||||
// Let's check it backwards.. we simply want to best engine available..
|
||||
for (i = start + count - 1; i >= start; i--) {
|
||||
// Is it availiable?
|
||||
// Also, check if the reliability of the vehicle is above the AI_VEHICLE_MIN_RELIABILTY
|
||||
if (!HASBIT(GetEngine(i)->player_avail, _current_player) || GetEngine(i)->reliability * 100 < AI_VEHICLE_MIN_RELIABILTY << 16) continue;
|
||||
// Can we build it?
|
||||
ret = AI_DoCommand(0, i, 0, DC_QUERY_COST, CMD_BUILD_ROAD_VEH);
|
||||
if (!CmdFailed(ret)) break;
|
||||
}
|
||||
// We did not find a vehicle :(
|
||||
if (CmdFailed(ret)) return -1;
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Builds the best vehicle possible
|
||||
int AiNew_Build_Vehicle(Player *p, TileIndex tile, byte flag)
|
||||
{
|
||||
int i = AiNew_PickVehicle(p);
|
||||
if (i == -1) return CMD_ERROR;
|
||||
|
||||
if (p->ainew.tbt == AI_TRAIN) return CMD_ERROR;
|
||||
|
||||
return AI_DoCommand(tile, i, 0, flag, CMD_BUILD_ROAD_VEH);
|
||||
}
|
||||
|
||||
int AiNew_Build_Depot(Player *p, TileIndex tile, byte direction, byte flag)
|
||||
{
|
||||
static const byte _roadbits_by_dir[4] = {2,1,8,4};
|
||||
int ret, ret2;
|
||||
if (p->ainew.tbt == AI_TRAIN)
|
||||
return AI_DoCommand(tile, 0, direction, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_TRAIN_DEPOT);
|
||||
|
||||
ret = AI_DoCommand(tile, direction, 0, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD_DEPOT);
|
||||
if (CmdFailed(ret)) return ret;
|
||||
// Try to build the road from the depot
|
||||
ret2 = AI_DoCommand(tile + TileOffsByDir(direction), _roadbits_by_dir[direction], 0, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD);
|
||||
// If it fails, ignore it..
|
||||
if (CmdFailed(ret2)) return ret;
|
||||
return ret + ret2;
|
||||
}
|
||||
@@ -1,19 +1,24 @@
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "debug.h"
|
||||
#include "map.h"
|
||||
#include "tile.h"
|
||||
#include "command.h"
|
||||
#include "ai.h"
|
||||
#include "depot.h"
|
||||
/* $Id$ */
|
||||
|
||||
#include "../../stdafx.h"
|
||||
#include "../../openttd.h"
|
||||
#include "../../debug.h"
|
||||
#include "../../functions.h"
|
||||
#include "../../map.h"
|
||||
#include "../../tile.h"
|
||||
#include "../../command.h"
|
||||
#include "trolly.h"
|
||||
#include "../../depot.h"
|
||||
#include "../../variables.h"
|
||||
#include "../ai.h"
|
||||
|
||||
#define TEST_STATION_NO_DIR 0xFF
|
||||
|
||||
// Tests if a station can be build on the given spot
|
||||
// TODO: make it train compatible
|
||||
static bool TestCanBuildStationHere(uint tile, byte dir)
|
||||
static bool TestCanBuildStationHere(TileIndex tile, byte dir)
|
||||
{
|
||||
Player *p = DEREF_PLAYER(_current_player);
|
||||
Player *p = GetPlayer(_current_player);
|
||||
|
||||
if (dir == TEST_STATION_NO_DIR) {
|
||||
int32 ret;
|
||||
@@ -38,9 +43,9 @@ static bool IsRoad(TileIndex tile)
|
||||
(IsTileType(tile, MP_STREET) && !IsTileDepotType(tile, TRANSPORT_ROAD)) ||
|
||||
(IsTileType(tile, MP_TUNNELBRIDGE) && (
|
||||
// road tunnel?
|
||||
((_map5[tile] & 0x80) == 0 && (_map5[tile] & 0x4) == 0x4) ||
|
||||
((_m[tile].m5 & 0x80) == 0 && (_m[tile].m5 & 0x4) == 0x4) ||
|
||||
// road bridge?
|
||||
((_map5[tile] & 0x80) != 0 && (_map5[tile] & 0x2) == 0x2)
|
||||
((_m[tile].m5 & 0x80) != 0 && (_m[tile].m5 & 0x2) == 0x2)
|
||||
));
|
||||
}
|
||||
|
||||
@@ -48,6 +53,7 @@ static bool IsRoad(TileIndex tile)
|
||||
// Checks if a tile 'a' is between the tiles 'b' and 'c'
|
||||
#define TILES_BETWEEN(a, b, c) (TileX(a) >= TileX(b) && TileX(a) <= TileX(c) && TileY(a) >= TileY(b) && TileY(a) <= TileY(c))
|
||||
|
||||
|
||||
// Check if the current tile is in our end-area
|
||||
static int32 AyStar_AiPathFinder_EndNodeCheck(AyStar *aystar, OpenListNode *current)
|
||||
{
|
||||
@@ -62,6 +68,7 @@ static int32 AyStar_AiPathFinder_EndNodeCheck(AyStar *aystar, OpenListNode *curr
|
||||
return AYSTAR_DONE;
|
||||
}
|
||||
|
||||
|
||||
// Calculates the hash
|
||||
// Currently it is a 10 bit hash, so the hash array has a max depth of 6 bits (so 64)
|
||||
static uint AiPathFinder_Hash(uint key1, uint key2)
|
||||
@@ -69,6 +76,7 @@ static uint AiPathFinder_Hash(uint key1, uint key2)
|
||||
return (TileX(key1) & 0x1F) + ((TileY(key1) & 0x1F) << 5);
|
||||
}
|
||||
|
||||
|
||||
// Clear the memory of all the things
|
||||
static void AyStar_AiPathFinder_Free(AyStar *aystar)
|
||||
{
|
||||
@@ -76,11 +84,13 @@ static void AyStar_AiPathFinder_Free(AyStar *aystar)
|
||||
free(aystar);
|
||||
}
|
||||
|
||||
|
||||
static int32 AyStar_AiPathFinder_CalculateG(AyStar *aystar, AyStarNode *current, OpenListNode *parent);
|
||||
static int32 AyStar_AiPathFinder_CalculateH(AyStar *aystar, AyStarNode *current, OpenListNode *parent);
|
||||
static void AyStar_AiPathFinder_FoundEndNode(AyStar *aystar, OpenListNode *current);
|
||||
static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *current);
|
||||
|
||||
|
||||
// This creates the AiPathFinder
|
||||
AyStar *new_AyStar_AiPathFinder(int max_tiles_around, Ai_PathFinderInfo *PathFinderInfo)
|
||||
{
|
||||
@@ -115,7 +125,7 @@ AyStar *new_AyStar_AiPathFinder(int max_tiles_around, Ai_PathFinderInfo *PathFin
|
||||
// Now we add all the starting tiles
|
||||
for (x = TileX(PathFinderInfo->start_tile_tl); x <= TileX(PathFinderInfo->start_tile_br); x++) {
|
||||
for (y = TileY(PathFinderInfo->start_tile_tl); y <= TileY(PathFinderInfo->start_tile_br); y++) {
|
||||
start_node.node.tile = TILE_XY(x, y);
|
||||
start_node.node.tile = TileXY(x, y);
|
||||
result->addstart(result, &start_node.node, 0);
|
||||
}
|
||||
}
|
||||
@@ -123,6 +133,7 @@ AyStar *new_AyStar_AiPathFinder(int max_tiles_around, Ai_PathFinderInfo *PathFin
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
// To reuse AyStar we sometimes have to clean all the memory
|
||||
void clean_AyStar_AiPathFinder(AyStar *aystar, Ai_PathFinderInfo *PathFinderInfo)
|
||||
{
|
||||
@@ -144,14 +155,15 @@ void clean_AyStar_AiPathFinder(AyStar *aystar, Ai_PathFinderInfo *PathFinderInfo
|
||||
// Now we add all the starting tiles
|
||||
for (x = TileX(PathFinderInfo->start_tile_tl); x <= TileX(PathFinderInfo->start_tile_br); x++) {
|
||||
for (y = TileY(PathFinderInfo->start_tile_tl); y <= TileY(PathFinderInfo->start_tile_br); y++) {
|
||||
if (!(IsTileType(TILE_XY(x, y), MP_CLEAR) || IsTileType(TILE_XY(x, y), MP_TREES))) continue;
|
||||
if (!TestCanBuildStationHere(TILE_XY(x, y), TEST_STATION_NO_DIR)) continue;
|
||||
start_node.node.tile = TILE_XY(x, y);
|
||||
if (!(IsTileType(TileXY(x, y), MP_CLEAR) || IsTileType(TileXY(x, y), MP_TREES))) continue;
|
||||
if (!TestCanBuildStationHere(TileXY(x, y), TEST_STATION_NO_DIR)) continue;
|
||||
start_node.node.tile = TileXY(x, y);
|
||||
aystar->addstart(aystar, &start_node.node, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// The h-value, simple calculation
|
||||
static int32 AyStar_AiPathFinder_CalculateH(AyStar *aystar, AyStarNode *current, OpenListNode *parent)
|
||||
{
|
||||
@@ -171,6 +183,7 @@ static int32 AyStar_AiPathFinder_CalculateH(AyStar *aystar, AyStarNode *current,
|
||||
return r * AI_PATHFINDER_H_MULTIPLER;
|
||||
}
|
||||
|
||||
|
||||
// We found the end.. let's get the route back and put it in an array
|
||||
static void AyStar_AiPathFinder_FoundEndNode(AyStar *aystar, OpenListNode *current)
|
||||
{
|
||||
@@ -193,6 +206,7 @@ static void AyStar_AiPathFinder_FoundEndNode(AyStar *aystar, OpenListNode *curre
|
||||
DEBUG(ai, 1)("[Ai-PathFinding] Found route of %d nodes long in %d nodes of searching", i, Hash_Size(&aystar->ClosedListHash));
|
||||
}
|
||||
|
||||
|
||||
// What tiles are around us.
|
||||
static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *current)
|
||||
{
|
||||
@@ -218,11 +232,11 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
if (!PathFinderInfo->rail_or_road && IsRoad(atile)) {
|
||||
if (IsTileType(atile, MP_TUNNELBRIDGE)) {
|
||||
// An existing bridge... let's test the direction ;)
|
||||
if ((_map5[atile] & 1U) != (i & 1)) continue;
|
||||
if ((_m[atile].m5 & 1U) != (i & 1)) continue;
|
||||
// This problem only is valid for tunnels:
|
||||
// When the last tile was not yet a tunnel, check if we enter from the right side..
|
||||
if ((_map5[atile] & 0x80) == 0) {
|
||||
if (i != (_map5[atile] & 3U)) continue;
|
||||
if ((_m[atile].m5 & 0x80) == 0) {
|
||||
if (i != (_m[atile].m5 & 3U)) continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -230,7 +244,7 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
if (!PathFinderInfo->rail_or_road && IsRoad(ctile)) {
|
||||
if (IsTileType(ctile, MP_TUNNELBRIDGE)) {
|
||||
// An existing bridge/tunnel... let's test the direction ;)
|
||||
if ((_map5[ctile] & 1U) != (i & 1)) continue;
|
||||
if ((_m[ctile].m5 & 1U) != (i & 1)) continue;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -256,7 +270,7 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
if (PathFinderInfo->rail_or_road) {
|
||||
// Rail check
|
||||
dir = AiNew_GetRailDirection(current->path.parent->node.tile, ctile, atile);
|
||||
ret = DoCommandByTile(ctile, 0, dir, DC_AUTO | DC_NO_WATER, CMD_BUILD_SINGLE_RAIL);
|
||||
ret = AI_DoCommand(ctile, 0, dir, DC_AUTO | DC_NO_WATER, CMD_BUILD_SINGLE_RAIL);
|
||||
if (CmdFailed(ret)) continue;
|
||||
#ifdef AI_PATHFINDER_NO_90DEGREES_TURN
|
||||
if (current->path.parent->parent != NULL) {
|
||||
@@ -276,9 +290,9 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
dir = 0;
|
||||
} else {
|
||||
// It already has road.. check if we miss any bits!
|
||||
if ((_map5[ctile] & dir) != dir) {
|
||||
if ((_m[ctile].m5 & dir) != dir) {
|
||||
// We do miss some pieces :(
|
||||
dir &= ~_map5[ctile];
|
||||
dir &= ~_m[ctile].m5;
|
||||
} else {
|
||||
dir = 0;
|
||||
}
|
||||
@@ -286,7 +300,7 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
}
|
||||
// Only destruct things if it is MP_CLEAR of MP_TREES
|
||||
if (dir != 0) {
|
||||
ret = DoCommandByTile(ctile, dir, 0, DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD);
|
||||
ret = AI_DoCommand(ctile, dir, 0, DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD);
|
||||
if (CmdFailed(ret)) continue;
|
||||
}
|
||||
}
|
||||
@@ -315,7 +329,6 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
if (ti.tileh != 0 ||
|
||||
(PathFinderInfo->rail_or_road && IsTileType(tile + TileOffsByDir(dir), MP_STREET)) ||
|
||||
(!PathFinderInfo->rail_or_road && IsTileType(tile + TileOffsByDir(dir), MP_RAILWAY))) {
|
||||
|
||||
for (;;) {
|
||||
new_tile += TileOffsByDir(dir);
|
||||
|
||||
@@ -326,7 +339,7 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
if (TILES_BETWEEN(new_tile, PathFinderInfo->end_tile_tl, PathFinderInfo->end_tile_br)) break;
|
||||
|
||||
// Try building the bridge..
|
||||
ret = DoCommandByTile(tile, new_tile, (0 << 8) + (MAX_BRIDGES / 2), DC_AUTO, CMD_BUILD_BRIDGE);
|
||||
ret = AI_DoCommand(tile, new_tile, (0 << 8) + (MAX_BRIDGES / 2), DC_AUTO, CMD_BUILD_BRIDGE);
|
||||
if (CmdFailed(ret)) continue;
|
||||
// We can build a bridge here.. add him to the neighbours
|
||||
aystar->neighbours[aystar->num_neighbours].tile = new_tile;
|
||||
@@ -345,7 +358,7 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
(dir == 2 && ti.tileh == 3) ||
|
||||
(dir == 3 && ti.tileh == 9)) {
|
||||
// Now simply check if a tunnel can be build
|
||||
ret = DoCommandByTile(tile, (PathFinderInfo->rail_or_road?0:0x200), 0, DC_AUTO, CMD_BUILD_TUNNEL);
|
||||
ret = AI_DoCommand(tile, (PathFinderInfo->rail_or_road?0:0x200), 0, DC_AUTO, CMD_BUILD_TUNNEL);
|
||||
FindLandscapeHeightByTile(&ti, _build_tunnel_endtile);
|
||||
if (!CmdFailed(ret) && (ti.tileh == 3 || ti.tileh == 6 || ti.tileh == 9 || ti.tileh == 12)) {
|
||||
aystar->neighbours[aystar->num_neighbours].tile = _build_tunnel_endtile;
|
||||
@@ -356,6 +369,7 @@ static void AyStar_AiPathFinder_GetNeighbours(AyStar *aystar, OpenListNode *curr
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
extern uint GetRailFoundation(uint tileh, uint bits);
|
||||
extern uint GetRoadFoundation(uint tileh, uint bits);
|
||||
extern uint GetBridgeFoundation(uint tileh, byte direction);
|
||||
@@ -377,9 +391,10 @@ static int32 AyStar_AiPathFinder_CalculateG(AyStar *aystar, AyStarNode *current,
|
||||
// Check if we hit the end-tile
|
||||
if (TILES_BETWEEN(current->tile, PathFinderInfo->end_tile_tl, PathFinderInfo->end_tile_br)) {
|
||||
// We are at the end-tile, check if we had a direction or something...
|
||||
if (PathFinderInfo->end_direction != AI_PATHFINDER_NO_DIRECTION && AiNew_GetDirection(current->tile, parent->path.node.tile) != PathFinderInfo->end_direction)
|
||||
if (PathFinderInfo->end_direction != AI_PATHFINDER_NO_DIRECTION && AiNew_GetDirection(current->tile, parent->path.node.tile) != PathFinderInfo->end_direction) {
|
||||
// We are not pointing the right way, invalid tile
|
||||
return AYSTAR_INVALID_NODE;
|
||||
}
|
||||
// If it was valid, drop out.. we don't build on the endtile
|
||||
return 0;
|
||||
}
|
||||
@@ -447,10 +462,8 @@ static int32 AyStar_AiPathFinder_CalculateG(AyStar *aystar, AyStarNode *current,
|
||||
if (GetBridgeFoundation(ti.tileh, (current->user_data[0] >> 8) & 1) < 15)
|
||||
res += AI_PATHFINDER_BRIDGE_GOES_UP_PENALTY;
|
||||
}
|
||||
if (parent_ti.tileh == 0)
|
||||
res += AI_PATHFINDER_BRIDGE_GOES_UP_PENALTY;
|
||||
if (ti.tileh == 0)
|
||||
res += AI_PATHFINDER_BRIDGE_GOES_UP_PENALTY;
|
||||
if (parent_ti.tileh == 0) res += AI_PATHFINDER_BRIDGE_GOES_UP_PENALTY;
|
||||
if (ti.tileh == 0) res += AI_PATHFINDER_BRIDGE_GOES_UP_PENALTY;
|
||||
}
|
||||
|
||||
// To prevent the AI from taking the fastest way in tiles, but not the fastest way
|
||||
@@ -458,7 +471,7 @@ static int32 AyStar_AiPathFinder_CalculateG(AyStar *aystar, AyStarNode *current,
|
||||
// This way, we get almost the fastest way in tiles, and a very good speed on the track
|
||||
if (!PathFinderInfo->rail_or_road) {
|
||||
if (parent->path.parent != NULL &&
|
||||
AiNew_GetDirection(current->tile, parent->path.node.tile) != AiNew_GetDirection(parent->path.node.tile, parent->path.parent->node.tile)) {
|
||||
AiNew_GetDirection(current->tile, parent->path.node.tile) != AiNew_GetDirection(parent->path.node.tile, parent->path.parent->node.tile)) {
|
||||
// When road exists, we don't like turning, but its free, so don't be to piggy about it
|
||||
if (IsRoad(parent->path.node.tile))
|
||||
res += AI_PATHFINDER_DIRECTION_CHANGE_ON_EXISTING_ROAD_PENALTY;
|
||||
@@ -492,9 +505,5 @@ static int32 AyStar_AiPathFinder_CalculateG(AyStar *aystar, AyStarNode *current,
|
||||
}
|
||||
}
|
||||
|
||||
// Res should never be below zero.. if so, make it zero!
|
||||
if (res < 0) { res = 0; }
|
||||
|
||||
// Return our value
|
||||
return res;
|
||||
return (res < 0) ? 0 : res;
|
||||
}
|
||||
@@ -1,11 +1,14 @@
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "debug.h"
|
||||
#include "map.h"
|
||||
#include "ai.h"
|
||||
#include "vehicle.h"
|
||||
/* $Id$ */
|
||||
|
||||
int AiNew_GetRailDirection(uint tile_a, uint tile_b, uint tile_c) {
|
||||
#include "../../stdafx.h"
|
||||
#include "../../openttd.h"
|
||||
#include "../../debug.h"
|
||||
#include "../../map.h"
|
||||
#include "trolly.h"
|
||||
#include "../../vehicle.h"
|
||||
|
||||
int AiNew_GetRailDirection(TileIndex tile_a, TileIndex tile_b, TileIndex tile_c)
|
||||
{
|
||||
// 0 = vert
|
||||
// 1 = horz
|
||||
// 2 = dig up-left
|
||||
@@ -46,7 +49,8 @@ int AiNew_GetRailDirection(uint tile_a, uint tile_b, uint tile_c) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int AiNew_GetRoadDirection(uint tile_a, uint tile_b, uint tile_c) {
|
||||
int AiNew_GetRoadDirection(TileIndex tile_a, TileIndex tile_b, TileIndex tile_c)
|
||||
{
|
||||
int x1, x2, x3;
|
||||
int y1, y2, y3;
|
||||
int r;
|
||||
@@ -75,7 +79,8 @@ int AiNew_GetRoadDirection(uint tile_a, uint tile_b, uint tile_c) {
|
||||
}
|
||||
|
||||
// Get's the direction between 2 tiles seen from tile_a
|
||||
int AiNew_GetDirection(uint tile_a, uint tile_b) {
|
||||
int AiNew_GetDirection(TileIndex tile_a, TileIndex tile_b)
|
||||
{
|
||||
if (TileY(tile_a) < TileY(tile_b)) return 1;
|
||||
if (TileY(tile_a) > TileY(tile_b)) return 3;
|
||||
if (TileX(tile_a) < TileX(tile_b)) return 2;
|
||||
+1364
File diff suppressed because it is too large
Load Diff
+40
-38
@@ -1,7 +1,10 @@
|
||||
#ifndef AI_H
|
||||
#define AI_H
|
||||
/* $Id$ */
|
||||
|
||||
#include "aystar.h"
|
||||
#ifndef AI_TROLLY_H
|
||||
#define AI_TROLLY_H
|
||||
|
||||
#include "../../aystar.h"
|
||||
#include "../../player.h"
|
||||
|
||||
/*
|
||||
* These defines can be altered to change the behavoir of the AI
|
||||
@@ -163,33 +166,33 @@
|
||||
|
||||
// This stops 90degrees curves
|
||||
static const byte _illegal_curves[6] = {
|
||||
255, 255, // Horz and vert, don't have the effect
|
||||
5, // upleft and upright are not valid
|
||||
4, // downright and downleft are not valid
|
||||
2, // downleft and upleft are not valid
|
||||
3, // upright and downright are not valid
|
||||
255, 255, // Horz and vert, don't have the effect
|
||||
5, // upleft and upright are not valid
|
||||
4, // downright and downleft are not valid
|
||||
2, // downleft and upleft are not valid
|
||||
3, // upright and downright are not valid
|
||||
};
|
||||
|
||||
enum {
|
||||
AI_STATE_STARTUP = 0,
|
||||
AI_STATE_FIRST_TIME,
|
||||
AI_STATE_NOTHING,
|
||||
AI_STATE_WAKE_UP,
|
||||
AI_STATE_LOCATE_ROUTE,
|
||||
AI_STATE_FIND_STATION,
|
||||
AI_STATE_FIND_PATH,
|
||||
AI_STATE_FIND_DEPOT,
|
||||
AI_STATE_VERIFY_ROUTE,
|
||||
AI_STATE_BUILD_STATION,
|
||||
AI_STATE_BUILD_PATH,
|
||||
AI_STATE_BUILD_DEPOT,
|
||||
AI_STATE_BUILD_VEHICLE,
|
||||
AI_STATE_GIVE_ORDERS,
|
||||
AI_STATE_START_VEHICLE,
|
||||
AI_STATE_REPAY_MONEY,
|
||||
AI_STATE_STARTUP = 0,
|
||||
AI_STATE_FIRST_TIME,
|
||||
AI_STATE_NOTHING,
|
||||
AI_STATE_WAKE_UP,
|
||||
AI_STATE_LOCATE_ROUTE,
|
||||
AI_STATE_FIND_STATION,
|
||||
AI_STATE_FIND_PATH,
|
||||
AI_STATE_FIND_DEPOT,
|
||||
AI_STATE_VERIFY_ROUTE,
|
||||
AI_STATE_BUILD_STATION,
|
||||
AI_STATE_BUILD_PATH,
|
||||
AI_STATE_BUILD_DEPOT,
|
||||
AI_STATE_BUILD_VEHICLE,
|
||||
AI_STATE_GIVE_ORDERS,
|
||||
AI_STATE_START_VEHICLE,
|
||||
AI_STATE_REPAY_MONEY,
|
||||
AI_STATE_CHECK_ALL_VEHICLES,
|
||||
AI_STATE_ACTION_DONE,
|
||||
AI_STATE_STOP, // Temporary function to stop the AI
|
||||
AI_STATE_ACTION_DONE,
|
||||
AI_STATE_STOP, // Temporary function to stop the AI
|
||||
};
|
||||
|
||||
// Used for tbt (train/bus/truck)
|
||||
@@ -209,7 +212,7 @@ enum {
|
||||
|
||||
// Used for from_type/to_type
|
||||
enum {
|
||||
AI_NO_TYPE = 0,
|
||||
AI_NO_TYPE = 0,
|
||||
AI_CITY,
|
||||
AI_INDUSTRY,
|
||||
};
|
||||
@@ -222,7 +225,7 @@ enum {
|
||||
|
||||
#define AI_NO_CARGO 0xFF // Means that there is no cargo defined yet (used for industry)
|
||||
#define AI_NEED_CARGO 0xFE // Used when the AI needs to find out a cargo for the route
|
||||
#define AI_STATION_RANGE TILE_XY(MapMaxX(), MapMaxY())
|
||||
#define AI_STATION_RANGE TileXY(MapMaxX(), MapMaxY())
|
||||
|
||||
#define AI_PATHFINDER_NO_DIRECTION (byte)-1
|
||||
|
||||
@@ -240,20 +243,19 @@ AyStar *new_AyStar_AiPathFinder(int max_tiles_around, Ai_PathFinderInfo *PathFin
|
||||
void clean_AyStar_AiPathFinder(AyStar *aystar, Ai_PathFinderInfo *PathFinderInfo);
|
||||
|
||||
// ai_shared.c
|
||||
int AiNew_GetRailDirection(uint tile_a, uint tile_b, uint tile_c);
|
||||
int AiNew_GetRoadDirection(uint tile_a, uint tile_b, uint tile_c);
|
||||
int AiNew_GetDirection(uint tile_a, uint tile_b);
|
||||
int AiNew_GetRailDirection(TileIndex tile_a, TileIndex tile_b, TileIndex tile_c);
|
||||
int AiNew_GetRoadDirection(TileIndex tile_a, TileIndex tile_b, TileIndex tile_c);
|
||||
int AiNew_GetDirection(TileIndex tile_a, TileIndex tile_b);
|
||||
bool AiNew_SetSpecialVehicleFlag(Player *p, Vehicle *v, uint flag);
|
||||
uint AiNew_GetSpecialVehicleFlag(Player *p, Vehicle *v);
|
||||
|
||||
// ai_build.c
|
||||
bool AiNew_Build_CompanyHQ(Player *p, uint tile);
|
||||
int AiNew_Build_Station(Player *p, byte type, uint tile, byte length, byte numtracks, byte direction, byte flag);
|
||||
int AiNew_Build_Bridge(Player *p, uint tile_a, uint tile_b, byte flag);
|
||||
bool AiNew_Build_CompanyHQ(Player *p, TileIndex tile);
|
||||
int AiNew_Build_Station(Player *p, byte type, TileIndex tile, byte length, byte numtracks, byte direction, byte flag);
|
||||
int AiNew_Build_Bridge(Player *p, TileIndex tile_a, TileIndex tile_b, byte flag);
|
||||
int AiNew_Build_RoutePart(Player *p, Ai_PathFinderInfo *PathFinderInfo, byte flag);
|
||||
int AiNew_PickVehicle(Player *p);
|
||||
int AiNew_Build_Vehicle(Player *p, uint tile, byte flag);
|
||||
int AiNew_Build_Depot(Player *p, uint tile, byte direction, byte flag);
|
||||
int AiNew_Build_Vehicle(Player *p, TileIndex tile, byte flag);
|
||||
int AiNew_Build_Depot(Player *p, TileIndex tile, byte direction, byte flag);
|
||||
|
||||
|
||||
#endif
|
||||
#endif /* AI_TROLLY_H */
|
||||
-260
@@ -1,260 +0,0 @@
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "debug.h"
|
||||
#include "map.h"
|
||||
#include "tile.h"
|
||||
#include "command.h"
|
||||
#include "ai.h"
|
||||
#include "engine.h"
|
||||
#include "station.h"
|
||||
|
||||
// Build HQ
|
||||
// Params:
|
||||
// tile : tile where HQ is going to be build
|
||||
bool AiNew_Build_CompanyHQ(Player *p, uint tile) {
|
||||
if (CmdFailed(DoCommandByTile(tile, 0, 0, DC_AUTO | DC_NO_WATER, CMD_BUILD_COMPANY_HQ)))
|
||||
return false;
|
||||
DoCommandByTile(tile, 0, 0, DC_EXEC | DC_AUTO | DC_NO_WATER, CMD_BUILD_COMPANY_HQ);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Build station
|
||||
// Params:
|
||||
// type : AI_TRAIN/AI_BUS/AI_TRUCK : indicates the type of station
|
||||
// tile : tile where station is going to be build
|
||||
// length : in case of AI_TRAIN: length of station
|
||||
// numtracks : in case of AI_TRAIN: tracks of station
|
||||
// direction : the direction of the station
|
||||
// flag : flag passed to DoCommand (normally 0 to get the cost or DC_EXEC to build it)
|
||||
int AiNew_Build_Station(Player *p, byte type, uint tile, byte length, byte numtracks, byte direction, byte flag) {
|
||||
if (type == AI_TRAIN)
|
||||
return DoCommandByTile(tile, direction + (numtracks << 8) + (length << 16), 0, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_RAILROAD_STATION);
|
||||
|
||||
if (type == AI_BUS)
|
||||
return DoCommandByTile(tile, direction, RS_BUS, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD_STOP);
|
||||
|
||||
return DoCommandByTile(tile, direction, RS_TRUCK, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD_STOP);
|
||||
}
|
||||
|
||||
// Builds a brdige. The second best out of the ones available for this player
|
||||
// Params:
|
||||
// tile_a : starting point
|
||||
// tile_b : end point
|
||||
// flag : flag passed to DoCommand
|
||||
int AiNew_Build_Bridge(Player *p, uint tile_a, uint tile_b, byte flag) {
|
||||
int bridge_type, bridge_len, type, type2;
|
||||
|
||||
// Find a good bridgetype (the best money can buy)
|
||||
bridge_len = GetBridgeLength(tile_a, tile_b);
|
||||
type = type2 = 0;
|
||||
for (bridge_type = MAX_BRIDGES-1; bridge_type >= 0; bridge_type--) {
|
||||
if (CheckBridge_Stuff(bridge_type, bridge_len)) {
|
||||
type2 = type;
|
||||
type = bridge_type;
|
||||
// We found two bridges, exit
|
||||
if (type2 != 0)
|
||||
break;
|
||||
}
|
||||
}
|
||||
// There is only one bridge that can be build..
|
||||
if (type2 == 0 && type != 0) type2 = type;
|
||||
|
||||
// Now, simply, build the bridge!
|
||||
if (p->ainew.tbt == AI_TRAIN)
|
||||
return DoCommandByTile(tile_a, tile_b, (0<<8) + type2, flag | DC_AUTO, CMD_BUILD_BRIDGE);
|
||||
|
||||
return DoCommandByTile(tile_a, tile_b, (0x80 << 8) + type2, flag | DC_AUTO, CMD_BUILD_BRIDGE);
|
||||
}
|
||||
|
||||
|
||||
// Build the route part by part
|
||||
// Basicly what this function do, is build that amount of parts of the route
|
||||
// that go in the same direction. It sets 'part' to the last part of the route builded.
|
||||
// The return value is the cost for the builded parts
|
||||
//
|
||||
// Params:
|
||||
// PathFinderInfo : Pointer to the PathFinderInfo used for AiPathFinder
|
||||
// part : Which part we need to build
|
||||
//
|
||||
// TODO: skip already builded road-pieces (e.g.: cityroad)
|
||||
int AiNew_Build_RoutePart(Player *p, Ai_PathFinderInfo *PathFinderInfo, byte flag) {
|
||||
int part = PathFinderInfo->position;
|
||||
byte *route_extra = PathFinderInfo->route_extra;
|
||||
TileIndex *route = PathFinderInfo->route;
|
||||
int dir;
|
||||
int old_dir = -1;
|
||||
int cost = 0;
|
||||
int res;
|
||||
// We need to calculate the direction with the parent of the parent.. so we skip
|
||||
// the first pieces and the last piece
|
||||
if (part < 1) part = 1;
|
||||
// When we are done, stop it
|
||||
if (part >= PathFinderInfo->route_length - 1) { PathFinderInfo->position = -2; return 0; }
|
||||
|
||||
|
||||
if (PathFinderInfo->rail_or_road) {
|
||||
// Tunnel code
|
||||
if ((AI_PATHFINDER_FLAG_TUNNEL & route_extra[part]) != 0) {
|
||||
cost += DoCommandByTile(route[part], 0, 0, flag, CMD_BUILD_TUNNEL);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: tunnel could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
// Bridge code
|
||||
if ((AI_PATHFINDER_FLAG_BRIDGE & route_extra[part]) != 0) {
|
||||
cost += AiNew_Build_Bridge(p, route[part], route[part-1], flag);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: bridge could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
// Build normal rail
|
||||
// Keep it doing till we go an other way
|
||||
if (route_extra[part-1] == 0 && route_extra[part] == 0) {
|
||||
while (route_extra[part] == 0) {
|
||||
// Get the current direction
|
||||
dir = AiNew_GetRailDirection(route[part-1], route[part], route[part+1]);
|
||||
// Is it the same as the last one?
|
||||
if (old_dir != -1 && old_dir != dir) break;
|
||||
old_dir = dir;
|
||||
// Build the tile
|
||||
res = DoCommandByTile(route[part], 0, dir, flag, CMD_BUILD_SINGLE_RAIL);
|
||||
if (CmdFailed(res)) {
|
||||
// Problem.. let's just abort it all!
|
||||
p->ainew.state = AI_STATE_NOTHING;
|
||||
return 0;
|
||||
}
|
||||
cost += res;
|
||||
// Go to the next tile
|
||||
part++;
|
||||
// Check if it is still in range..
|
||||
if (part >= PathFinderInfo->route_length - 1) break;
|
||||
}
|
||||
part--;
|
||||
}
|
||||
// We want to return the last position, so we go back one
|
||||
PathFinderInfo->position = part;
|
||||
} else {
|
||||
// Tunnel code
|
||||
if ((AI_PATHFINDER_FLAG_TUNNEL & route_extra[part]) != 0) {
|
||||
cost += DoCommandByTile(route[part], 0x200, 0, flag, CMD_BUILD_TUNNEL);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: tunnel could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
// Bridge code
|
||||
if ((AI_PATHFINDER_FLAG_BRIDGE & route_extra[part]) != 0) {
|
||||
cost += AiNew_Build_Bridge(p, route[part], route[part+1], flag);
|
||||
PathFinderInfo->position++;
|
||||
// TODO: problems!
|
||||
if (CmdFailed(cost)) {
|
||||
DEBUG(ai,0)("[AiNew - BuildPath] We have a serious problem: bridge could not be build!");
|
||||
return 0;
|
||||
}
|
||||
return cost;
|
||||
}
|
||||
|
||||
// Build normal road
|
||||
// Keep it doing till we go an other way
|
||||
// EnsureNoVehicle makes sure we don't build on a tile where a vehicle is. This way
|
||||
// it will wait till the vehicle is gone..
|
||||
if (route_extra[part-1] == 0 && route_extra[part] == 0 && (flag != DC_EXEC || EnsureNoVehicle(route[part]))) {
|
||||
while (route_extra[part] == 0 && (flag != DC_EXEC || EnsureNoVehicle(route[part]))) {
|
||||
// Get the current direction
|
||||
dir = AiNew_GetRoadDirection(route[part-1], route[part], route[part+1]);
|
||||
// Is it the same as the last one?
|
||||
if (old_dir != -1 && old_dir != dir) break;
|
||||
old_dir = dir;
|
||||
// There is already some road, and it is a bridge.. don't build!!!
|
||||
if (!IsTileType(route[part], MP_TUNNELBRIDGE)) {
|
||||
// Build the tile
|
||||
res = DoCommandByTile(route[part], dir, 0, flag | DC_NO_WATER, CMD_BUILD_ROAD);
|
||||
// Currently, we ignore CMD_ERRORs!
|
||||
if (CmdFailed(res) && flag == DC_EXEC && !IsTileType(route[part], MP_STREET) && !EnsureNoVehicle(route[part])) {
|
||||
// Problem.. let's just abort it all!
|
||||
DEBUG(ai,0)("Darn, the route could not be builded.. aborting!");
|
||||
p->ainew.state = AI_STATE_NOTHING;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!CmdFailed(res)) cost += res;
|
||||
}
|
||||
// Go to the next tile
|
||||
part++;
|
||||
// Check if it is still in range..
|
||||
if (part >= PathFinderInfo->route_length - 1) break;
|
||||
}
|
||||
part--;
|
||||
// We want to return the last position, so we go back one
|
||||
}
|
||||
if (!EnsureNoVehicle(route[part]) && flag == DC_EXEC) part--;
|
||||
PathFinderInfo->position = part;
|
||||
}
|
||||
|
||||
return cost;
|
||||
}
|
||||
|
||||
// This functions tries to find the best vehicle for this type of cargo
|
||||
// It returns vehicle_id or -1 if not found
|
||||
int AiNew_PickVehicle(Player *p) {
|
||||
if (p->ainew.tbt == AI_TRAIN) {
|
||||
// Not supported yet
|
||||
return -1;
|
||||
} else {
|
||||
int start, count, i, ret = CMD_ERROR;
|
||||
start = _cargoc.ai_roadveh_start[p->ainew.cargo];
|
||||
count = _cargoc.ai_roadveh_count[p->ainew.cargo];
|
||||
|
||||
// Let's check it backwards.. we simply want to best engine available..
|
||||
for (i=start+count-1;i>=start;i--) {
|
||||
// Is it availiable?
|
||||
// Also, check if the reliability of the vehicle is above the AI_VEHICLE_MIN_RELIABILTY
|
||||
if (!HASBIT(_engines[i].player_avail, _current_player) || _engines[i].reliability * 100 < AI_VEHICLE_MIN_RELIABILTY << 16) continue;
|
||||
// Can we build it?
|
||||
ret = DoCommandByTile(0, i, 0, DC_QUERY_COST, CMD_BUILD_ROAD_VEH);
|
||||
if (!CmdFailed(ret)) break;
|
||||
}
|
||||
// We did not find a vehicle :(
|
||||
if (CmdFailed(ret)) { return -1; }
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
// Builds the best vehicle possible
|
||||
int AiNew_Build_Vehicle(Player *p, uint tile, byte flag) {
|
||||
int i = AiNew_PickVehicle(p);
|
||||
if (i == -1) return CMD_ERROR;
|
||||
|
||||
if (p->ainew.tbt == AI_TRAIN)
|
||||
return CMD_ERROR;
|
||||
|
||||
return DoCommandByTile(tile, i, 0, flag, CMD_BUILD_ROAD_VEH);
|
||||
}
|
||||
|
||||
int AiNew_Build_Depot(Player *p, uint tile, byte direction, byte flag)
|
||||
{
|
||||
static const byte _roadbits_by_dir[4] = {2,1,8,4};
|
||||
int ret, ret2;
|
||||
if (p->ainew.tbt == AI_TRAIN)
|
||||
return DoCommandByTile(tile, 0, direction, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_TRAIN_DEPOT);
|
||||
|
||||
ret = DoCommandByTile(tile, direction, 0, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD_DEPOT);
|
||||
if (CmdFailed(ret)) return ret;
|
||||
// Try to build the road from the depot
|
||||
ret2 = DoCommandByTile(tile + TileOffsByDir(direction), _roadbits_by_dir[direction], 0, flag | DC_AUTO | DC_NO_WATER, CMD_BUILD_ROAD);
|
||||
// If it fails, ignore it..
|
||||
if (CmdFailed(ret2)) return ret;
|
||||
return ret + ret2;
|
||||
}
|
||||
+233
-321
File diff suppressed because it is too large
Load Diff
+239
-157
@@ -1,6 +1,10 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "debug.h"
|
||||
#include "functions.h"
|
||||
#include "table/sprites.h"
|
||||
#include "table/strings.h"
|
||||
#include "map.h"
|
||||
#include "tile.h"
|
||||
@@ -14,47 +18,66 @@
|
||||
#include "viewport.h"
|
||||
#include "player.h"
|
||||
#include "depot.h"
|
||||
#include "vehicle_gui.h"
|
||||
|
||||
|
||||
void Set_DPARAM_Aircraft_Build_Window(uint16 engine_number)
|
||||
/**
|
||||
* Draw the purchase info details of an aircraft at a given location.
|
||||
* @param x,y location where to draw the info
|
||||
* @param engine_number the engine of which to draw the info of
|
||||
*/
|
||||
void DrawAircraftPurchaseInfo(int x, int y, EngineID engine_number)
|
||||
{
|
||||
const AircraftVehicleInfo *avi = AircraftVehInfo(engine_number);
|
||||
Engine *e;
|
||||
const Engine* e = GetEngine(engine_number);
|
||||
YearMonthDay ymd;
|
||||
ConvertDayToYMD(&ymd, e->intro_date);
|
||||
|
||||
/* Purchase cost - Max speed */
|
||||
SetDParam(0, avi->base_cost * (_price.aircraft_base>>3)>>5);
|
||||
SetDParam(1, avi->max_speed * 8);
|
||||
SetDParam(2, avi->passenger_capacity);
|
||||
SetDParam(3, avi->mail_capacity);
|
||||
SetDParam(4, avi->running_cost * _price.aircraft_running >> 8);
|
||||
DrawString(x, y, STR_PURCHASE_INFO_COST_SPEED, 0);
|
||||
y += 10;
|
||||
|
||||
e = &_engines[engine_number];
|
||||
SetDParam(6, e->lifelength);
|
||||
SetDParam(7, e->reliability * 100 >> 16);
|
||||
ConvertDayToYMD(&ymd, e->intro_date);
|
||||
SetDParam(5, ymd.year + 1920);
|
||||
/* Cargo capacity */
|
||||
SetDParam(0, avi->passenger_capacity);
|
||||
SetDParam(1, avi->mail_capacity);
|
||||
DrawString(x, y, STR_PURCHASE_INFO_AIRCRAFT_CAPACITY, 0);
|
||||
y += 10;
|
||||
|
||||
/* Running cost */
|
||||
SetDParam(0, avi->running_cost * _price.aircraft_running >> 8);
|
||||
DrawString(x, y, STR_PURCHASE_INFO_RUNNINGCOST, 0);
|
||||
y += 10;
|
||||
|
||||
/* Design date - Life length */
|
||||
SetDParam(0, ymd.year + 1920);
|
||||
SetDParam(1, e->lifelength);
|
||||
DrawString(x, y, STR_PURCHASE_INFO_DESIGNED_LIFE, 0);
|
||||
y += 10;
|
||||
|
||||
/* Reliability */
|
||||
SetDParam(0, e->reliability * 100 >> 16);
|
||||
DrawString(x, y, STR_PURCHASE_INFO_RELIABILITY, 0);
|
||||
y += 10;
|
||||
}
|
||||
|
||||
static void DrawAircraftImage(const Vehicle *v, int x, int y, VehicleID selection)
|
||||
{
|
||||
int image = GetAircraftImage(v, 6);
|
||||
uint32 ormod = SPRITE_PALETTE(PLAYER_SPRITE_COLOR(v->owner));
|
||||
if (v->vehstatus & VS_CRASHED) ormod = 0x3248000;
|
||||
DrawSprite(image | ormod, x+25, y+10);
|
||||
if (v->subtype == 0)
|
||||
DrawSprite(0xF3D, x+25, y+5);
|
||||
if (v->vehstatus & VS_CRASHED) ormod = PALETTE_CRASH;
|
||||
DrawSprite(image | ormod, x + 25, y + 10);
|
||||
if (v->subtype == 0) DrawSprite(SPR_ROTOR_STOPPED, x + 25, y + 5);
|
||||
if (v->index == selection) {
|
||||
DrawFrameRect(x-1, y-1, x+58, y+21, 0xF, 0x10);
|
||||
DrawFrameRect(x - 1, y - 1, x + 58, y + 21, 0xF, FR_BORDERONLY);
|
||||
}
|
||||
}
|
||||
|
||||
void CcBuildAircraft(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
void CcBuildAircraft(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||
{
|
||||
Vehicle *v;
|
||||
|
||||
if (success) {
|
||||
v = GetVehicle(_new_aircraft_id);
|
||||
const Vehicle* v = GetVehicle(_new_aircraft_id);
|
||||
|
||||
if (v->tile == _backup_orders_tile) {
|
||||
_backup_orders_tile = 0;
|
||||
RestoreVehicleOrders(v, _backup_orders_data);
|
||||
@@ -63,22 +86,24 @@ void CcBuildAircraft(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
}
|
||||
}
|
||||
|
||||
void CcCloneAircraft(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
{
|
||||
if (success) ShowAircraftViewWindow(GetVehicle(_new_aircraft_id));
|
||||
}
|
||||
|
||||
static void NewAircraftWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
|
||||
switch (e->event) {
|
||||
case WE_PAINT: {
|
||||
if (w->window_number == 0)
|
||||
SETBIT(w->disabled_state, 5);
|
||||
if (w->window_number == 0) SETBIT(w->disabled_state, 5);
|
||||
|
||||
{
|
||||
int count = 0;
|
||||
int num = NUM_AIRCRAFT_ENGINES;
|
||||
Engine *e = &_engines[AIRCRAFT_ENGINES_INDEX];
|
||||
const Engine* e = GetEngine(AIRCRAFT_ENGINES_INDEX);
|
||||
|
||||
do {
|
||||
if (HASBIT(e->player_avail, _local_player))
|
||||
count++;
|
||||
if (HASBIT(e->player_avail, _local_player)) count++;
|
||||
} while (++e,--num);
|
||||
SetVScrollCount(w, count);
|
||||
}
|
||||
@@ -87,13 +112,13 @@ static void NewAircraftWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
{
|
||||
int num = NUM_AIRCRAFT_ENGINES;
|
||||
Engine *e = &_engines[AIRCRAFT_ENGINES_INDEX];
|
||||
const Engine* e = GetEngine(AIRCRAFT_ENGINES_INDEX);
|
||||
int x = 2;
|
||||
int y = 15;
|
||||
int sel = WP(w,buildtrain_d).sel_index;
|
||||
int pos = w->vscroll.pos;
|
||||
int engine_id = AIRCRAFT_ENGINES_INDEX;
|
||||
int selected_id = -1;
|
||||
EngineID engine_id = AIRCRAFT_ENGINES_INDEX;
|
||||
EngineID selected_id = INVALID_ENGINE;
|
||||
|
||||
do {
|
||||
if (HASBIT(e->player_avail, _local_player)) {
|
||||
@@ -109,10 +134,8 @@ static void NewAircraftWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
WP(w,buildtrain_d).sel_engine = selected_id;
|
||||
|
||||
if (selected_id != -1) {
|
||||
Set_DPARAM_Aircraft_Build_Window(selected_id);
|
||||
|
||||
DrawString(2, w->widget[4].top + 1, STR_A007_COST_SPEED_CAPACITY_PASSENGERS, 0);
|
||||
if (selected_id != INVALID_ENGINE) {
|
||||
DrawAircraftPurchaseInfo(2, w->widget[4].top + 1, selected_id);
|
||||
}
|
||||
}
|
||||
} break;
|
||||
@@ -128,14 +151,14 @@ static void NewAircraftWndProc(Window *w, WindowEvent *e)
|
||||
} break;
|
||||
|
||||
case 5: { /* build */
|
||||
int sel_eng = WP(w,buildtrain_d).sel_engine;
|
||||
if (sel_eng != -1)
|
||||
EngineID sel_eng = WP(w,buildtrain_d).sel_engine;
|
||||
if (sel_eng != INVALID_ENGINE)
|
||||
DoCommandP(w->window_number, sel_eng, 0, CcBuildAircraft, CMD_BUILD_AIRCRAFT | CMD_MSG(STR_A008_CAN_T_BUILD_AIRCRAFT));
|
||||
} break;
|
||||
|
||||
case 6: { /* rename */
|
||||
int sel_eng = WP(w,buildtrain_d).sel_engine;
|
||||
if (sel_eng != -1) {
|
||||
EngineID sel_eng = WP(w,buildtrain_d).sel_engine;
|
||||
if (sel_eng != INVALID_ENGINE) {
|
||||
WP(w,buildtrain_d).rename_engine = sel_eng;
|
||||
ShowQueryString(GetCustomEngineName(sel_eng),
|
||||
STR_A039_RENAME_AIRCRAFT_TYPE, 31, 160, w->window_class, w->window_number);
|
||||
@@ -166,7 +189,7 @@ static void NewAircraftWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _new_aircraft_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 239, 0, 13, STR_A005_NEW_AIRCRAFT, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_MATRIX, RESIZE_BOTTOM, 14, 0, 227, 14, 109, 0x401, STR_A025_AIRCRAFT_SELECTION_LIST},
|
||||
{ WWT_SCROLLBAR, RESIZE_BOTTOM, 14, 228, 239, 14, 109, 0x0, STR_0190_SCROLL_BAR_SCROLLS_LIST},
|
||||
@@ -185,7 +208,7 @@ static const WindowDesc _new_aircraft_desc = {
|
||||
NewAircraftWndProc
|
||||
};
|
||||
|
||||
static void ShowBuildAircraftWindow(uint tile)
|
||||
static void ShowBuildAircraftWindow(TileIndex tile)
|
||||
{
|
||||
Window *w;
|
||||
|
||||
@@ -199,7 +222,7 @@ static void ShowBuildAircraftWindow(uint tile)
|
||||
w->resize.step_height = 24;
|
||||
|
||||
if (tile != 0) {
|
||||
w->caption_color = _map_owner[tile];
|
||||
w->caption_color = GetTileOwner(tile);
|
||||
} else {
|
||||
w->caption_color = _local_player;
|
||||
}
|
||||
@@ -224,9 +247,9 @@ static void AircraftRefitWndProc(Window *w, WindowEvent *e)
|
||||
int32 cost = DoCommandByTile(v->tile, v->index, WP(w,refit_d).cargo, DC_QUERY_COST, CMD_REFIT_AIRCRAFT);
|
||||
if (!CmdFailed(cost)) {
|
||||
SetDParam(2, cost);
|
||||
SetDParam(0, _cargoc.names_long_p[WP(w,refit_d).cargo]);
|
||||
SetDParam(0, _cargoc.names_long[WP(w,refit_d).cargo]);
|
||||
SetDParam(1, _aircraft_refit_capacity);
|
||||
DrawString(1, 137, STR_A041_NEW_CAPACITY_COST_OF_REFIT, 0);
|
||||
DrawString(1, 147, STR_A041_NEW_CAPACITY_COST_OF_REFIT, 0);
|
||||
}
|
||||
}
|
||||
} break;
|
||||
@@ -253,23 +276,23 @@ static void AircraftRefitWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _aircraft_refit_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 239, 0, 13, STR_A03C_REFIT, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 239, 14, 135, 0x0, STR_A03E_SELECT_TYPE_OF_CARGO_FOR},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 239, 136, 157, 0x0, STR_NULL},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 0, 239, 158, 169, STR_A03D_REFIT_AIRCRAFT, STR_A03F_REFIT_AIRCRAFT_TO_CARRY},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 239, 14, 145, 0x0, STR_A03E_SELECT_TYPE_OF_CARGO_FOR},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 239, 146, 167, 0x0, STR_NULL},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 0, 239, 168, 179, STR_A03D_REFIT_AIRCRAFT, STR_A03F_REFIT_AIRCRAFT_TO_CARRY},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
static const WindowDesc _aircraft_refit_desc = {
|
||||
-1,-1, 240, 170,
|
||||
-1,-1, 240, 180,
|
||||
WC_VEHICLE_REFIT,WC_VEHICLE_VIEW,
|
||||
WDF_STD_TOOLTIPS | WDF_STD_BTN | WDF_DEF_WIDGET | WDF_UNCLICK_BUTTONS,
|
||||
_aircraft_refit_widgets,
|
||||
AircraftRefitWndProc
|
||||
};
|
||||
|
||||
static void ShowAircraftRefitWindow(Vehicle *v)
|
||||
static void ShowAircraftRefitWindow(const Vehicle* v)
|
||||
{
|
||||
Window *w;
|
||||
|
||||
@@ -299,17 +322,10 @@ static void AircraftDetailsWndProc(Window *w, WindowEvent *e)
|
||||
/* Draw running cost */
|
||||
{
|
||||
int year = v->age / 366;
|
||||
StringID str;
|
||||
|
||||
SetDParam(1, year);
|
||||
|
||||
str = STR_0199_YEAR;
|
||||
if (year != 1) {
|
||||
str++;
|
||||
if (v->max_age - 366 < v->age)
|
||||
str++;
|
||||
}
|
||||
SetDParam(0, str);
|
||||
SetDParam(0, (v->age + 365 < v->max_age) ? STR_AGE : STR_AGE_RED);
|
||||
SetDParam(2, v->max_age / 366);
|
||||
SetDParam(3, _price.aircraft_running * AircraftVehInfo(v->engine_type)->running_cost >> 8);
|
||||
DrawString(2, 15, STR_A00D_AGE_RUNNING_COST_YR, 0);
|
||||
@@ -356,12 +372,12 @@ static void AircraftDetailsWndProc(Window *w, WindowEvent *e)
|
||||
DrawString(60, y, STR_A011_BUILT_VALUE, 0);
|
||||
y += 10;
|
||||
|
||||
SetDParam(0, _cargoc.names_long_p[v->cargo_type]);
|
||||
SetDParam(0, _cargoc.names_long[v->cargo_type]);
|
||||
SetDParam(1, v->cargo_cap);
|
||||
u = v->next;
|
||||
SetDParam(2, _cargoc.names_long_p[u->cargo_type]);
|
||||
SetDParam(2, _cargoc.names_long[u->cargo_type]);
|
||||
SetDParam(3, u->cargo_cap);
|
||||
DrawString(60, y, STR_A019_CAPACITY + (u->cargo_cap == 0), 0);
|
||||
DrawString(60, y, (u->cargo_cap != 0) ? STR_A019_CAPACITY : STR_A01A_CAPACITY, 0);
|
||||
y += 14;
|
||||
}
|
||||
|
||||
@@ -399,7 +415,7 @@ do_change_service_int:
|
||||
mod = GetServiceIntervalClamped(mod + v->service_interval);
|
||||
if (mod == v->service_interval) return;
|
||||
|
||||
DoCommandP(v->tile, v->index, mod, NULL, CMD_CHANGE_AIRCRAFT_SERVICE_INT | CMD_MSG(STR_018A_CAN_T_CHANGE_SERVICING));
|
||||
DoCommandP(v->tile, v->index, mod, NULL, CMD_CHANGE_SERVICE_INT | CMD_MSG(STR_018A_CAN_T_CHANGE_SERVICING));
|
||||
break;
|
||||
}
|
||||
} break;
|
||||
@@ -409,20 +425,19 @@ do_change_service_int:
|
||||
DeleteWindow(w);
|
||||
break;
|
||||
|
||||
case WE_ON_EDIT_TEXT: {
|
||||
case WE_ON_EDIT_TEXT:
|
||||
if (e->edittext.str[0] != '\0') {
|
||||
_cmd_text = e->edittext.str;
|
||||
DoCommandP(0, w->window_number, 0, NULL,
|
||||
CMD_NAME_VEHICLE | CMD_MSG(STR_A031_CAN_T_NAME_AIRCRAFT));
|
||||
}
|
||||
} break;
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static const Widget _aircraft_details_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 349, 0, 13, STR_A00C_DETAILS, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 350, 389, 0, 13, STR_01AA_NAME, STR_A032_NAME_AIRCRAFT},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 389, 14, 55, 0x0, STR_NULL},
|
||||
@@ -442,7 +457,7 @@ static const WindowDesc _aircraft_details_desc = {
|
||||
};
|
||||
|
||||
|
||||
static void ShowAircraftDetailsWindow(Vehicle *v)
|
||||
static void ShowAircraftDetailsWindow(const Vehicle* v)
|
||||
{
|
||||
Window *w;
|
||||
VehicleID veh = v->index;
|
||||
@@ -460,7 +475,7 @@ static void ShowAircraftDetailsWindow(Vehicle *v)
|
||||
|
||||
|
||||
static const Widget _aircraft_view_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW },
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW },
|
||||
{ WWT_CAPTION, RESIZE_RIGHT, 14, 11, 237, 0, 13, STR_A00A, STR_018C_WINDOW_TITLE_DRAG_THIS },
|
||||
{ WWT_STICKYBOX, RESIZE_LR, 14, 238, 249, 0, 13, 0x0, STR_STICKY_BUTTON },
|
||||
{ WWT_IMGBTN, RESIZE_RB, 14, 0, 231, 14, 103, 0x0, STR_NULL },
|
||||
@@ -471,29 +486,27 @@ static const Widget _aircraft_view_widgets[] = {
|
||||
{ WWT_PUSHIMGBTN, RESIZE_LR, 14, 232, 249, 50, 67, 0x2B4, STR_A03B_REFIT_AIRCRAFT_TO_CARRY },
|
||||
{ WWT_PUSHIMGBTN, RESIZE_LR, 14, 232, 249, 68, 85, 0x2B2, STR_A028_SHOW_AIRCRAFT_S_ORDERS },
|
||||
{ WWT_PUSHIMGBTN, RESIZE_LR, 14, 232, 249, 86, 103, 0x2B3, STR_A02B_SHOW_AIRCRAFT_DETAILS },
|
||||
{ WWT_PUSHIMGBTN, RESIZE_LR, 14, 232, 249, 32, 49, SPR_CLONE_AIRCRAFT, STR_CLONE_AIRCRAFT_INFO },
|
||||
{ WWT_PANEL, RESIZE_LRB, 14, 232, 249, 104, 103, 0x0, STR_NULL },
|
||||
{ WWT_RESIZEBOX, RESIZE_LRTB, 14, 238, 249, 104, 115, 0x0, STR_NULL },
|
||||
{ WIDGETS_END }
|
||||
};
|
||||
|
||||
bool CheckStoppedInHangar(const Vehicle* v); /* XXX extern function declaration in .c */
|
||||
|
||||
static void AircraftViewWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
Vehicle *v = GetVehicle(w->window_number);
|
||||
uint32 disabled = 1<<8;
|
||||
const Vehicle* v = GetVehicle(w->window_number);
|
||||
uint32 disabled = 1 << 8;
|
||||
StringID str;
|
||||
|
||||
{
|
||||
uint tile = v->tile;
|
||||
if (IsTileType(tile, MP_STATION) &&
|
||||
(_map5[tile] == 32 || _map5[tile] == 65) &&
|
||||
v->vehstatus&VS_STOPPED)
|
||||
disabled = 0;
|
||||
if (v->vehstatus & VS_STOPPED && IsAircraftHangarTile(v->tile)) {
|
||||
disabled = 0;
|
||||
}
|
||||
|
||||
if (v->owner != _local_player)
|
||||
disabled |= 1<<8 | 1<<7;
|
||||
if (v->owner != _local_player) disabled |= 1 << 8 | 1 << 7;
|
||||
w->disabled_state = disabled;
|
||||
|
||||
/* draw widgets & caption */
|
||||
@@ -501,10 +514,6 @@ static void AircraftViewWndProc(Window *w, WindowEvent *e)
|
||||
SetDParam(1, v->unitnumber);
|
||||
DrawWindowWidgets(w);
|
||||
|
||||
/* draw the flag */
|
||||
DrawSprite(v->vehstatus & VS_STOPPED ? 0xC12 : 0xC13, 2,
|
||||
w->widget[5].top + 1);
|
||||
|
||||
if (v->vehstatus & VS_CRASHED) {
|
||||
str = STR_8863_CRASHED;
|
||||
} else if (v->vehstatus & VS_STOPPED) {
|
||||
@@ -531,21 +540,23 @@ static void AircraftViewWndProc(Window *w, WindowEvent *e)
|
||||
if (v->num_orders == 0) {
|
||||
str = STR_NO_ORDERS + _patches.vehicle_speed;
|
||||
SetDParam(0, v->cur_speed * 8);
|
||||
} else
|
||||
} else {
|
||||
str = STR_EMPTY;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
DrawStringCentered((w->widget[5].right - w->widget[5].left) / 2,
|
||||
w->widget[5].top + 1, str, 0);
|
||||
/* draw the flag plus orders */
|
||||
DrawSprite(v->vehstatus & VS_STOPPED ? SPR_FLAG_VEH_STOPPED : SPR_FLAG_VEH_RUNNING, 2, w->widget[5].top + 1);
|
||||
DrawStringCenteredTruncated(w->widget[5].left + 8, w->widget[5].right, w->widget[5].top + 1, str, 0);
|
||||
DrawWindowViewport(w);
|
||||
} break;
|
||||
|
||||
case WE_CLICK: {
|
||||
Vehicle *v = GetVehicle(w->window_number);
|
||||
const Vehicle* v = GetVehicle(w->window_number);
|
||||
|
||||
switch(e->click.widget) {
|
||||
switch (e->click.widget) {
|
||||
case 5: /* start stop */
|
||||
DoCommandP(v->tile, v->index, 0, NULL, CMD_START_STOP_AIRCRAFT | CMD_MSG(STR_A016_CAN_T_STOP_START_AIRCRAFT));
|
||||
break;
|
||||
@@ -564,6 +575,10 @@ static void AircraftViewWndProc(Window *w, WindowEvent *e)
|
||||
case 10: /* show details */
|
||||
ShowAircraftDetailsWindow(v);
|
||||
break;
|
||||
case 11:
|
||||
/* clone vehicle */
|
||||
DoCommandP(v->tile, v->index, _ctrl_pressed ? 1 : 0, CcCloneAircraft, CMD_CLONE_VEHICLE | CMD_MSG(STR_A008_CAN_T_BUILD_AIRCRAFT));
|
||||
break;
|
||||
}
|
||||
} break;
|
||||
|
||||
@@ -579,6 +594,16 @@ static void AircraftViewWndProc(Window *w, WindowEvent *e)
|
||||
DeleteWindowById(WC_VEHICLE_REFIT, w->window_number);
|
||||
DeleteWindowById(WC_VEHICLE_DETAILS, w->window_number);
|
||||
break;
|
||||
|
||||
case WE_MOUSELOOP: {
|
||||
const Vehicle* v = GetVehicle(w->window_number);
|
||||
uint32 h = CheckStoppedInHangar(v) ? (1 << 7) : (1 << 11);
|
||||
|
||||
if (h != w->hidden_state) {
|
||||
w->hidden_state = h;
|
||||
SetWindowDirty(w);
|
||||
}
|
||||
} break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -592,12 +617,11 @@ static const WindowDesc _aircraft_view_desc = {
|
||||
};
|
||||
|
||||
|
||||
void ShowAircraftViewWindow(Vehicle *v)
|
||||
void ShowAircraftViewWindow(const Vehicle* v)
|
||||
{
|
||||
Window *w;
|
||||
Window* w = AllocateWindowDescFront(&_aircraft_view_desc, v->index);
|
||||
|
||||
w = AllocateWindowDescFront(&_aircraft_view_desc, v->index);
|
||||
if (w) {
|
||||
if (w != NULL) {
|
||||
w->caption_color = v->owner;
|
||||
AssignWindowViewport(w, 3, 17, 0xE2, 0x54, w->window_number | (1 << 31), 0);
|
||||
}
|
||||
@@ -605,25 +629,29 @@ void ShowAircraftViewWindow(Vehicle *v)
|
||||
|
||||
static void DrawAircraftDepotWindow(Window *w)
|
||||
{
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
Vehicle *v;
|
||||
int num,x,y;
|
||||
|
||||
tile = w->window_number;
|
||||
|
||||
/* setup disabled buttons */
|
||||
w->disabled_state = (_map_owner[tile]==_local_player) ? 0 : ((1<<4)|(1<<7));
|
||||
w->disabled_state =
|
||||
IsTileOwner(tile, _local_player) ? 0 : ((1<<4) | (1<<7) | (1<<8));
|
||||
|
||||
/* determine amount of items for scroller */
|
||||
num = 0;
|
||||
FOR_ALL_VEHICLES(v) {
|
||||
if (v->type == VEH_Aircraft && v->subtype <= 2 && v->vehstatus&VS_HIDDEN &&
|
||||
v->tile == (TileIndex)tile)
|
||||
num++;
|
||||
if (v->type == VEH_Aircraft &&
|
||||
v->subtype <= 2 &&
|
||||
v->vehstatus & VS_HIDDEN &&
|
||||
v->tile == tile) {
|
||||
num++;
|
||||
}
|
||||
}
|
||||
SetVScrollCount(w, (num + w->hscroll.cap - 1) / w->hscroll.cap);
|
||||
|
||||
SetDParam(0, _map2[tile]);
|
||||
SetDParam(0, _m[tile].m2);
|
||||
DrawWindowWidgets(w);
|
||||
|
||||
x = 2;
|
||||
@@ -634,7 +662,7 @@ static void DrawAircraftDepotWindow(Window *w)
|
||||
if (v->type == VEH_Aircraft &&
|
||||
v->subtype <= 2 &&
|
||||
v->vehstatus&VS_HIDDEN &&
|
||||
v->tile == (TileIndex)tile &&
|
||||
v->tile == tile &&
|
||||
--num < 0 && num >= -w->vscroll.cap * w->hscroll.cap) {
|
||||
|
||||
DrawAircraftImage(v, x+12, y, WP(w,traindepot_d).sel);
|
||||
@@ -642,7 +670,7 @@ static void DrawAircraftDepotWindow(Window *w)
|
||||
SetDParam(0, v->unitnumber);
|
||||
DrawString(x, y+2, (uint16)(v->max_age-366) >= v->age ? STR_00E2 : STR_00E3, 0);
|
||||
|
||||
DrawSprite( (v->vehstatus & VS_STOPPED) ? 0xC12 : 0xC13, x, y+12);
|
||||
DrawSprite((v->vehstatus & VS_STOPPED) ? SPR_FLAG_VEH_STOPPED : SPR_FLAG_VEH_RUNNING, x, y + 12);
|
||||
|
||||
if ((x+=74) == 2 + 74 * w->hscroll.cap) {
|
||||
x = 2;
|
||||
@@ -652,10 +680,10 @@ static void DrawAircraftDepotWindow(Window *w)
|
||||
}
|
||||
}
|
||||
|
||||
static int GetVehicleFromAircraftDepotWndPt(Window *w, int x, int y, Vehicle **veh) {
|
||||
static int GetVehicleFromAircraftDepotWndPt(const Window *w, int x, int y, Vehicle **veh) {
|
||||
uint xt,row,xm,ym;
|
||||
Vehicle *v;
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
int pos;
|
||||
|
||||
xt = x / 74;
|
||||
@@ -672,20 +700,14 @@ static int GetVehicleFromAircraftDepotWndPt(Window *w, int x, int y, Vehicle **v
|
||||
|
||||
tile = w->window_number;
|
||||
FOR_ALL_VEHICLES(v) {
|
||||
if (v->type == VEH_Aircraft &&
|
||||
v->subtype <= 2 &&
|
||||
v->vehstatus&VS_HIDDEN &&
|
||||
v->tile == (TileIndex)tile &&
|
||||
if (v->type == VEH_Aircraft && v->subtype <= 2 &&
|
||||
v->vehstatus & VS_HIDDEN && v->tile == tile &&
|
||||
--pos < 0) {
|
||||
*veh = v;
|
||||
if (xm >= 12)
|
||||
return 0;
|
||||
|
||||
if (ym <= 12)
|
||||
return -1; /* show window */
|
||||
|
||||
return -2; /* start stop */
|
||||
}
|
||||
*veh = v;
|
||||
if (xm >= 12) return 0;
|
||||
if (ym <= 12) return -1; /* show window */
|
||||
return -2; /* start stop */
|
||||
}
|
||||
}
|
||||
return 1; /* outside */
|
||||
}
|
||||
@@ -696,9 +718,12 @@ static void AircraftDepotClickAircraft(Window *w, int x, int y)
|
||||
int mode = GetVehicleFromAircraftDepotWndPt(w, x, y, &v);
|
||||
|
||||
// share / copy orders
|
||||
if (_thd.place_mode && mode <= 0) { _place_clicked_vehicle = v; return; }
|
||||
if (_thd.place_mode && mode <= 0) {
|
||||
_place_clicked_vehicle = v;
|
||||
return;
|
||||
}
|
||||
|
||||
switch(mode) {
|
||||
switch (mode) {
|
||||
case 1:
|
||||
return;
|
||||
|
||||
@@ -723,6 +748,30 @@ static void AircraftDepotClickAircraft(Window *w, int x, int y)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clones an aircraft
|
||||
* @param *v is the original vehicle to clone
|
||||
* @param *w is the window of the hangar where the clone is build
|
||||
*/
|
||||
static void HandleCloneVehClick(const Vehicle* v, const Window* w)
|
||||
{
|
||||
if (v == NULL || v->type != VEH_Aircraft) return;
|
||||
|
||||
DoCommandP(w->window_number, v->index, _ctrl_pressed ? 1 : 0,
|
||||
CcCloneAircraft, CMD_CLONE_VEHICLE | CMD_MSG(STR_A008_CAN_T_BUILD_AIRCRAFT)
|
||||
);
|
||||
|
||||
ResetObjectToPlace();
|
||||
}
|
||||
|
||||
static void ClonePlaceObj(TileIndex tile, const Window* w)
|
||||
{
|
||||
const Vehicle* v = CheckMouseOverVehicle();
|
||||
|
||||
if (v != NULL) HandleCloneVehClick(v, w);
|
||||
}
|
||||
|
||||
|
||||
static void AircraftDepotWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
@@ -732,23 +781,59 @@ static void AircraftDepotWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
case WE_CLICK:
|
||||
switch(e->click.widget) {
|
||||
case 5: /* click aircraft */
|
||||
AircraftDepotClickAircraft(w, e->click.pt.x, e->click.pt.y);
|
||||
break;
|
||||
case 7: /* show build aircraft window */
|
||||
ShowBuildAircraftWindow(w->window_number);
|
||||
break;
|
||||
case 8: /* scroll to tile */
|
||||
ScrollMainWindowToTile(w->window_number);
|
||||
break;
|
||||
case 5: /* click aircraft */
|
||||
AircraftDepotClickAircraft(w, e->click.pt.x, e->click.pt.y);
|
||||
break;
|
||||
|
||||
case 7: /* show build aircraft window */
|
||||
ResetObjectToPlace();
|
||||
ShowBuildAircraftWindow(w->window_number);
|
||||
break;
|
||||
|
||||
case 8: /* clone button */
|
||||
InvalidateWidget(w, 8);
|
||||
TOGGLEBIT(w->click_state, 8);
|
||||
|
||||
if (HASBIT(w->click_state, 8)) {
|
||||
_place_clicked_vehicle = NULL;
|
||||
SetObjectToPlaceWnd(SPR_CURSOR_CLONE, VHM_RECT, w);
|
||||
} else {
|
||||
ResetObjectToPlace();
|
||||
}
|
||||
break;
|
||||
|
||||
case 9: /* scroll to tile */
|
||||
ResetObjectToPlace();
|
||||
ScrollMainWindowToTile(w->window_number);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case WE_PLACE_OBJ: {
|
||||
ClonePlaceObj(e->place.tile, w);
|
||||
} break;
|
||||
|
||||
case WE_ABORT_PLACE_OBJ: {
|
||||
CLRBIT(w->click_state, 8);
|
||||
InvalidateWidget(w, 8);
|
||||
} break;
|
||||
|
||||
// check if a vehicle in a depot was clicked..
|
||||
case WE_MOUSELOOP: {
|
||||
const Vehicle* v = _place_clicked_vehicle;
|
||||
|
||||
// since OTTD checks all open depot windows, we will make sure that it triggers the one with a clicked clone button
|
||||
if (v != NULL && HASBIT(w->click_state, 8)) {
|
||||
_place_clicked_vehicle = NULL;
|
||||
HandleCloneVehClick(v, w);
|
||||
}
|
||||
} break;
|
||||
|
||||
case WE_DESTROY:
|
||||
DeleteWindowById(WC_BUILD_VEHICLE, w->window_number);
|
||||
break;
|
||||
|
||||
case WE_DRAGDROP: {
|
||||
case WE_DRAGDROP:
|
||||
switch(e->click.widget) {
|
||||
case 5: {
|
||||
Vehicle *v;
|
||||
@@ -786,8 +871,6 @@ static void AircraftDepotWndProc(Window *w, WindowEvent *e)
|
||||
SetWindowDirty(w);
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case WE_RESIZE:
|
||||
w->vscroll.cap += e->sizing.diff.y / 24;
|
||||
@@ -798,7 +881,7 @@ static void AircraftDepotWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _aircraft_depot_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_RIGHT, 14, 11, 318, 0, 13, STR_A002_AIRCRAFT_HANGAR, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_STICKYBOX, RESIZE_LR, 14, 319, 330, 0, 13, 0x0, STR_STICKY_BUTTON},
|
||||
{ WWT_PANEL, RESIZE_LRB, 14, 296, 318, 14, 13, 0x0, STR_NULL},
|
||||
@@ -806,8 +889,9 @@ static const Widget _aircraft_depot_widgets[] = {
|
||||
|
||||
{ WWT_MATRIX, RESIZE_RB, 14, 0, 295, 14, 61, 0x204, STR_A021_AIRCRAFT_CLICK_ON_AIRCRAFT},
|
||||
{ WWT_SCROLLBAR, RESIZE_LRB, 14, 319, 330, 14, 61, 0x0, STR_0190_SCROLL_BAR_SCROLLS_LIST},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_TB, 14, 0, 159, 62, 73, STR_A003_NEW_AIRCRAFT, STR_A022_BUILD_NEW_AIRCRAFT},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_TB, 14, 160, 318, 62, 73, STR_00E4_LOCATION, STR_A024_CENTER_MAIN_VIEW_ON_HANGAR},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_TB, 14, 0, 105, 62, 73, STR_A003_NEW_AIRCRAFT, STR_A022_BUILD_NEW_AIRCRAFT},
|
||||
{WWT_NODISTXTBTN, RESIZE_TB, 14, 106, 212, 62, 73, STR_CLONE_AIRCRAFT, STR_CLONE_AIRCRAFT_INFO_HANGAR_WINDOW},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_TB, 14, 213, 318, 62, 73, STR_00E4_LOCATION, STR_A024_CENTER_MAIN_VIEW_ON_HANGAR},
|
||||
{ WWT_PANEL, RESIZE_RTB, 14, 319, 318, 62, 73, 0x0, STR_NULL},
|
||||
{ WWT_RESIZEBOX, RESIZE_LRTB, 14, 319, 330, 62, 73, 0x0, STR_RESIZE_BUTTON},
|
||||
{ WIDGETS_END},
|
||||
@@ -822,13 +906,13 @@ static const WindowDesc _aircraft_depot_desc = {
|
||||
};
|
||||
|
||||
|
||||
void ShowAircraftDepotWindow(uint tile)
|
||||
void ShowAircraftDepotWindow(TileIndex tile)
|
||||
{
|
||||
Window *w;
|
||||
|
||||
w = AllocateWindowDescFront(&_aircraft_depot_desc, tile);
|
||||
if (w) {
|
||||
w->caption_color = _map_owner[tile];
|
||||
if (w != NULL) {
|
||||
w->caption_color = GetTileOwner(tile);
|
||||
w->vscroll.cap = 2;
|
||||
w->hscroll.cap = 4;
|
||||
w->resize.step_width = 74;
|
||||
@@ -838,7 +922,7 @@ void ShowAircraftDepotWindow(uint tile)
|
||||
}
|
||||
}
|
||||
|
||||
static void DrawSmallOrderList(Vehicle *v, int x, int y) {
|
||||
static void DrawSmallOrderList(const Vehicle *v, int x, int y) {
|
||||
const Order *order;
|
||||
int sel, i = 0;
|
||||
|
||||
@@ -857,8 +941,7 @@ static void DrawSmallOrderList(Vehicle *v, int x, int y) {
|
||||
DrawString(x, y, STR_A036, 0);
|
||||
|
||||
y += 6;
|
||||
if (++i == 4)
|
||||
break;
|
||||
if (++i == 4) break;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -868,9 +951,9 @@ static const Widget _player_aircraft_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_RIGHT, 14, 11, 247, 0, 13, STR_A009_AIRCRAFT, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_STICKYBOX, RESIZE_LR, 14, 248, 259, 0, 13, 0x0, STR_STICKY_BUTTON},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 0, 80, 14, 25, SRT_SORT_BY, STR_SORT_ORDER_TIP},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 0, 80, 14, 25, STR_SORT_BY, STR_SORT_ORDER_TIP},
|
||||
{ WWT_PANEL, RESIZE_NONE, 14, 81, 235, 14, 25, 0x0, STR_SORT_CRITERIA_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 236, 247, 14, 25, STR_0225, STR_SORT_CRITERIA_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 236, 247, 14, 25, STR_0225, STR_SORT_CRITERIA_TIP},
|
||||
{ WWT_PANEL, RESIZE_RIGHT, 14, 248, 259, 14, 25, 0x0, STR_NULL},
|
||||
{ WWT_MATRIX, RESIZE_RB, 14, 0, 247, 26, 169, 0x401, STR_A01F_AIRCRAFT_CLICK_ON_AIRCRAFT},
|
||||
{ WWT_SCROLLBAR, RESIZE_LRB, 14, 248, 259, 26, 169, 0x0, STR_0190_SCROLL_BAR_SCROLLS_LIST},
|
||||
@@ -885,9 +968,9 @@ static const Widget _other_player_aircraft_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_RIGHT, 14, 11, 247, 0, 13, STR_A009_AIRCRAFT, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_STICKYBOX, RESIZE_LR, 14, 248, 259, 0, 13, 0x0, STR_STICKY_BUTTON},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 0, 80, 14, 25, SRT_SORT_BY, STR_SORT_ORDER_TIP},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 0, 80, 14, 25, STR_SORT_BY, STR_SORT_ORDER_TIP},
|
||||
{ WWT_PANEL, RESIZE_NONE, 14, 81, 235, 14, 25, 0x0, STR_SORT_CRITERIA_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 236, 247, 14, 25, STR_0225, STR_SORT_CRITERIA_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 236, 247, 14, 25, STR_0225, STR_SORT_CRITERIA_TIP},
|
||||
{ WWT_PANEL, RESIZE_RIGHT, 14, 248, 259, 14, 25, 0x0, STR_NULL},
|
||||
{ WWT_MATRIX, RESIZE_RB, 14, 0, 247, 26, 169, 0x401, STR_A01F_AIRCRAFT_CLICK_ON_AIRCRAFT},
|
||||
{ WWT_SCROLLBAR, RESIZE_LRB, 14, 248, 259, 26, 169, 0x0, STR_0190_SCROLL_BAR_SCROLLS_LIST},
|
||||
@@ -898,8 +981,8 @@ static const Widget _other_player_aircraft_widgets[] = {
|
||||
|
||||
static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
int station = (int)w->window_number >> 16;
|
||||
int owner = w->window_number & 0xff;
|
||||
StationID station = GB(w->window_number, 16, 16);
|
||||
PlayerID owner = GB(w->window_number, 0, 8);
|
||||
vehiclelist_d *vl = &WP(w, vehiclelist_d);
|
||||
|
||||
switch(e->event) {
|
||||
@@ -915,13 +998,12 @@ static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
SetVScrollCount(w, vl->list_length);
|
||||
|
||||
// disable 'Sort By' tooltip on Unsorted sorting criteria
|
||||
if (vl->sort_type == SORT_BY_UNSORTED)
|
||||
w->disabled_state |= (1 << 3);
|
||||
if (vl->sort_type == SORT_BY_UNSORTED) w->disabled_state |= (1 << 3);
|
||||
|
||||
/* draw the widgets */
|
||||
{
|
||||
const Player *p = DEREF_PLAYER(owner);
|
||||
if (station == -1) {
|
||||
const Player *p = GetPlayer(owner);
|
||||
if (station == INVALID_STATION) {
|
||||
/* Company Name -- (###) Aircraft */
|
||||
SetDParam(0, p->name_1);
|
||||
SetDParam(1, p->name_2);
|
||||
@@ -938,7 +1020,7 @@ static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
/* draw sorting criteria string */
|
||||
DrawString(85, 15, _vehicle_sort_listing[vl->sort_type], 0x10);
|
||||
/* draw arrow pointing up/down for ascending/descending sorting */
|
||||
DoDrawString(vl->flags & VL_DESC ? "\xAA" : "\xA0", 69, 15, 0x10);
|
||||
DoDrawString(vl->flags & VL_DESC ? DOWNARROW : UPARROW, 69, 15, 0x10);
|
||||
|
||||
max = min(w->vscroll.pos + w->vscroll.cap, vl->list_length);
|
||||
for (i = w->vscroll.pos; i < max; ++i) {
|
||||
@@ -951,10 +1033,11 @@ static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
DrawVehicleProfitButton(v, x, y + 13);
|
||||
|
||||
SetDParam(0, v->unitnumber);
|
||||
if (IsAircraftHangarTile(v->tile) && (v->vehstatus & VS_HIDDEN))
|
||||
if (IsAircraftHangarTile(v->tile) && (v->vehstatus & VS_HIDDEN)) {
|
||||
str = STR_021F;
|
||||
else
|
||||
} else {
|
||||
str = v->age > v->max_age - 366 ? STR_00E3 : STR_00E2;
|
||||
}
|
||||
DrawString(x, y + 2, str, 0);
|
||||
|
||||
SetDParam(0, v->profit_this_year);
|
||||
@@ -988,7 +1071,7 @@ static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
case 7: { /* Matrix to show vehicles */
|
||||
uint32 id_v = (e->click.pt.y - PLY_WND_PRC__OFFSET_TOP_WIDGET) / PLY_WND_PRC__SIZE_OF_ROW_BIG;
|
||||
|
||||
if (id_v >= w->vscroll.cap) { return;} // click out of bounds
|
||||
if (id_v >= w->vscroll.cap) return; // click out of bounds
|
||||
|
||||
id_v += w->vscroll.pos;
|
||||
|
||||
@@ -1006,14 +1089,14 @@ static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
} break;
|
||||
|
||||
case 9: { /* Build new Vehicle */
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
|
||||
if (!IsWindowOfPrototype(w, _player_aircraft_widgets))
|
||||
break;
|
||||
|
||||
tile = _last_built_aircraft_depot_tile;
|
||||
do {
|
||||
if (_map_owner[tile] == _local_player && IsAircraftHangarTile(tile)) {
|
||||
if (IsAircraftHangarTile(tile) && IsTileOwner(tile, _local_player)) {
|
||||
ShowAircraftDepotWindow(tile);
|
||||
ShowBuildAircraftWindow(tile);
|
||||
return;
|
||||
@@ -1043,8 +1126,7 @@ static void PlayerAircraftWndProc(Window *w, WindowEvent *e)
|
||||
_sorting.aircraft.criteria = vl->sort_type;
|
||||
|
||||
// enable 'Sort By' if a sorter criteria is chosen
|
||||
if (vl->sort_type != SORT_BY_UNSORTED)
|
||||
CLRBIT(w->disabled_state, 3);
|
||||
if (vl->sort_type != SORT_BY_UNSORTED) CLRBIT(w->disabled_state, 3);
|
||||
}
|
||||
SetWindowDirty(w);
|
||||
break;
|
||||
@@ -1094,7 +1176,7 @@ static const WindowDesc _other_player_aircraft_desc = {
|
||||
PlayerAircraftWndProc
|
||||
};
|
||||
|
||||
void ShowPlayerAircraft(int player, int station)
|
||||
void ShowPlayerAircraft(PlayerID player, StationID station)
|
||||
{
|
||||
Window *w;
|
||||
|
||||
@@ -1104,7 +1186,7 @@ void ShowPlayerAircraft(int player, int station)
|
||||
w = AllocateWindowDescFront(&_other_player_aircraft_desc, (station << 16) | player);
|
||||
}
|
||||
|
||||
if (w) {
|
||||
if (w != NULL) {
|
||||
w->caption_color = w->window_number;
|
||||
w->vscroll.cap = 4;
|
||||
w->widget[7].unkA = (w->vscroll.cap << 8) + 1;
|
||||
|
||||
@@ -1,14 +1,19 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "debug.h"
|
||||
#include "map.h"
|
||||
#include "airport.h"
|
||||
#include "macros.h"
|
||||
#include "variables.h"
|
||||
|
||||
AirportFTAClass *CountryAirport;
|
||||
AirportFTAClass *CityAirport;
|
||||
AirportFTAClass *Heliport, *Oilrig;
|
||||
AirportFTAClass *MetropolitanAirport;
|
||||
AirportFTAClass *InternationalAirport;
|
||||
static AirportFTAClass* CountryAirport;
|
||||
static AirportFTAClass* CityAirport;
|
||||
static AirportFTAClass* Oilrig;
|
||||
static AirportFTAClass* Heliport;
|
||||
static AirportFTAClass* MetropolitanAirport;
|
||||
static AirportFTAClass* InternationalAirport;
|
||||
|
||||
static void AirportFTAClass_Constructor(AirportFTAClass *Airport,
|
||||
const byte *terminals, const byte *helipads,
|
||||
@@ -172,14 +177,15 @@ static void AirportFTAClass_Constructor(AirportFTAClass *Airport,
|
||||
|
||||
// build the state machine
|
||||
AirportBuildAutomata(Airport, FA);
|
||||
DEBUG(misc, 1) ("#Elements %2d; #Terminals %2d in %d group(s); #Helipads %2d in %d group(s); Entry Point %d", Airport->nofelements,
|
||||
nofterminals, nofterminalgroups, nofhelipads, nofhelipadgroups, Airport->entry_point);
|
||||
DEBUG(misc, 1) ("#Elements %2d; #Terminals %2d in %d group(s); #Helipads %2d in %d group(s); Entry Point %d",
|
||||
Airport->nofelements, nofterminals, nofterminalgroups, nofhelipads, nofhelipadgroups, Airport->entry_point
|
||||
);
|
||||
|
||||
|
||||
{
|
||||
byte _retval = AirportTestFTA(Airport);
|
||||
if (_retval != MAX_ELEMENTS) {printf("ERROR with element: %d\n", _retval-1);}
|
||||
assert(_retval == MAX_ELEMENTS);
|
||||
byte ret = AirportTestFTA(Airport);
|
||||
if (ret != MAX_ELEMENTS) printf("ERROR with element: %d\n", ret - 1);
|
||||
assert(ret == MAX_ELEMENTS);
|
||||
}
|
||||
// print out full information
|
||||
// true -- full info including heading, block, etc
|
||||
@@ -209,12 +215,13 @@ static uint16 AirportGetNofElements(const AirportFTAbuildup *FA)
|
||||
int i;
|
||||
uint16 nofelements = 0;
|
||||
int temp = FA[0].position;
|
||||
|
||||
for (i = 0; i < MAX_ELEMENTS; i++) {
|
||||
if (temp != FA[i].position) {
|
||||
nofelements++;
|
||||
temp = FA[i].position;
|
||||
}
|
||||
if (FA[i].position == MAX_ELEMENTS) {break;}
|
||||
if (FA[i].position == MAX_ELEMENTS) break;
|
||||
}
|
||||
return nofelements;
|
||||
}
|
||||
@@ -224,7 +231,7 @@ static void AirportBuildAutomata(AirportFTAClass *Airport, const AirportFTAbuild
|
||||
AirportFTA *FAutomata;
|
||||
AirportFTA *current;
|
||||
uint16 internalcounter, i;
|
||||
FAutomata = (AirportFTA *)malloc(sizeof(AirportFTA) * Airport->nofelements);
|
||||
FAutomata = malloc(sizeof(AirportFTA) * Airport->nofelements);
|
||||
Airport->layout = FAutomata;
|
||||
internalcounter = 0;
|
||||
|
||||
@@ -236,12 +243,13 @@ static void AirportBuildAutomata(AirportFTAClass *Airport, const AirportFTAbuild
|
||||
current->next_position = FA[internalcounter].next_in_chain;
|
||||
|
||||
// outgoing nodes from the same position, create linked list
|
||||
while (current->position == FA[internalcounter+1].position) {
|
||||
AirportFTA *newNode = (AirportFTA *)malloc(sizeof(AirportFTA));
|
||||
newNode->position = FA[internalcounter+1].position;
|
||||
newNode->heading = FA[internalcounter+1].heading;
|
||||
newNode->block = FA[internalcounter+1].block;
|
||||
newNode->next_position = FA[internalcounter+1].next_in_chain;
|
||||
while (current->position == FA[internalcounter + 1].position) {
|
||||
AirportFTA* newNode = malloc(sizeof(AirportFTA));
|
||||
|
||||
newNode->position = FA[internalcounter + 1].position;
|
||||
newNode->heading = FA[internalcounter + 1].heading;
|
||||
newNode->block = FA[internalcounter + 1].block;
|
||||
newNode->next_position = FA[internalcounter + 1].next_in_chain;
|
||||
// create link
|
||||
current->next_in_chain = newNode;
|
||||
current = current->next_in_chain;
|
||||
@@ -260,14 +268,14 @@ static byte AirportTestFTA(const AirportFTAClass *Airport)
|
||||
|
||||
for (i = 0; i < Airport->nofelements; i++) {
|
||||
position = Airport->layout[i].position;
|
||||
if (position != next_element) {return i;}
|
||||
if (position != next_element) return i;
|
||||
temp = &Airport->layout[i];
|
||||
|
||||
do {
|
||||
if (temp->heading > MAX_HEADINGS && temp->heading != 255) {return i;}
|
||||
if (temp->heading == 0 && temp->next_in_chain != 0) {return i;}
|
||||
if (position != temp->position) {return i;}
|
||||
if (temp->next_position >= Airport->nofelements) {return i;}
|
||||
if (temp->heading > MAX_HEADINGS && temp->heading != 255) return i;
|
||||
if (temp->heading == 0 && temp->next_in_chain != 0) return i;
|
||||
if (position != temp->position) return i;
|
||||
if (temp->next_position >= Airport->nofelements) return i;
|
||||
temp = temp->next_in_chain;
|
||||
} while (temp != NULL);
|
||||
next_element++;
|
||||
@@ -275,7 +283,8 @@ static byte AirportTestFTA(const AirportFTAClass *Airport)
|
||||
return MAX_ELEMENTS;
|
||||
}
|
||||
|
||||
static const char* const _airport_heading_strings[MAX_HEADINGS+2] = {
|
||||
#if 0
|
||||
static const char* const _airport_heading_strings[] = {
|
||||
"TO_ALL",
|
||||
"HANGAR",
|
||||
"TERM1",
|
||||
@@ -298,7 +307,6 @@ static const char* const _airport_heading_strings[MAX_HEADINGS+2] = {
|
||||
"DUMMY" // extra heading for 255
|
||||
};
|
||||
|
||||
/*
|
||||
static void AirportPrintOut(const AirportFTAClass *Airport, const bool full_report)
|
||||
{
|
||||
AirportFTA *temp;
|
||||
@@ -312,16 +320,18 @@ static void AirportPrintOut(const AirportFTAClass *Airport, const bool full_repo
|
||||
heading = (temp->heading == 255) ? MAX_HEADINGS+1 : temp->heading;
|
||||
printf("Pos:%2d NPos:%2d Heading:%15s Block:%2d\n", temp->position, temp->next_position,
|
||||
_airport_heading_strings[heading], AirportBlockToString(temp->block));
|
||||
} else {
|
||||
printf("P:%2d NP:%2d", temp->position, temp->next_position);
|
||||
}
|
||||
else { printf("P:%2d NP:%2d", temp->position, temp->next_position);}
|
||||
while (temp->next_in_chain != NULL) {
|
||||
temp = temp->next_in_chain;
|
||||
if (full_report) {
|
||||
heading = (temp->heading == 255) ? MAX_HEADINGS+1 : temp->heading;
|
||||
printf("Pos:%2d NPos:%2d Heading:%15s Block:%2d\n", temp->position, temp->next_position,
|
||||
_airport_heading_strings[heading], AirportBlockToString(temp->block));
|
||||
} else {
|
||||
printf("P:%2d NP:%2d", temp->position, temp->next_position);
|
||||
}
|
||||
else { printf("P:%2d NP:%2d", temp->position, temp->next_position);}
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
@@ -337,7 +347,8 @@ static byte AirportBlockToString(uint32 block)
|
||||
if (block & 0x0000000c) { block >>= 2; i += 2; }
|
||||
if (block & 0x00000002) { i += 1; }
|
||||
return i;
|
||||
}*/
|
||||
}
|
||||
#endif
|
||||
|
||||
const AirportFTAClass* GetAirport(const byte airport_type)
|
||||
{
|
||||
@@ -359,3 +370,14 @@ const AirportFTAClass* GetAirport(const byte airport_type)
|
||||
}
|
||||
return Airport;
|
||||
}
|
||||
|
||||
uint32 GetValidAirports(void)
|
||||
{
|
||||
uint32 bytemask = _avail_aircraft; /// sets the first 3 bytes, 0 - 2, @see AdjustAvailAircraft()
|
||||
|
||||
// 1980-1-1 is --> 21915
|
||||
// 1990-1-1 is --> 25568
|
||||
if (_date >= 21915) SETBIT(bytemask, 3); // metropilitan airport 1980
|
||||
if (_date >= 25568) SETBIT(bytemask, 4); // international airport 1990
|
||||
return bytemask;
|
||||
}
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef AIRPORT_H
|
||||
#define AIRPORT_H
|
||||
|
||||
@@ -53,15 +55,6 @@ const AirportFTAClass* GetAirport(const byte airport_type);
|
||||
* Bit 0 means the small airport is buildable, etc.
|
||||
* @todo set availability of airports by year, instead of airplane
|
||||
*/
|
||||
static inline uint32 GetValidAirports(void)
|
||||
{
|
||||
uint32 bytemask = _avail_aircraft; /// sets the first 3 bytes, 0 - 2, @see AdjustAvailAircraft()
|
||||
|
||||
// 1980-1-1 is --> 21915
|
||||
// 1990-1-1 is --> 25568
|
||||
if (_date >= 21915) {SETBIT(bytemask, 3);} // metropilitan airport 1980
|
||||
if (_date >= 25568) {SETBIT(bytemask, 4);} // international airport 1990
|
||||
return bytemask;
|
||||
}
|
||||
uint32 GetValidAirports(void);
|
||||
|
||||
#endif /* AIRPORT_H */
|
||||
|
||||
+33
-27
@@ -1,7 +1,10 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/sprites.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "window.h"
|
||||
#include "gui.h"
|
||||
@@ -19,7 +22,7 @@ static byte _selected_airport_type;
|
||||
static void ShowBuildAirportPicker(void);
|
||||
|
||||
|
||||
void CcBuildAirport(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
void CcBuildAirport(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||
{
|
||||
if (success) {
|
||||
SndPlayTileFx(SND_1F_SPLAT, tile);
|
||||
@@ -27,12 +30,12 @@ void CcBuildAirport(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
}
|
||||
}
|
||||
|
||||
static void PlaceAirport(uint tile)
|
||||
static void PlaceAirport(TileIndex tile)
|
||||
{
|
||||
DoCommandP(tile, _selected_airport_type, 0, CcBuildAirport, CMD_BUILD_AIRPORT | CMD_AUTO | CMD_NO_WATER | CMD_MSG(STR_A001_CAN_T_BUILD_AIRPORT_HERE));
|
||||
}
|
||||
|
||||
static void PlaceAir_DemolishArea(uint tile)
|
||||
static void PlaceAir_DemolishArea(TileIndex tile)
|
||||
{
|
||||
VpStartPlaceSizing(tile, 4);
|
||||
}
|
||||
@@ -40,7 +43,7 @@ static void PlaceAir_DemolishArea(uint tile)
|
||||
|
||||
static void BuildAirClick_Airport(Window *w)
|
||||
{
|
||||
if (HandlePlacePushButton(w, 3, 0xAA4, 1, PlaceAirport)) ShowBuildAirportPicker();
|
||||
if (HandlePlacePushButton(w, 3, SPR_CURSOR_AIRPORT, 1, PlaceAirport)) ShowBuildAirportPicker();
|
||||
}
|
||||
|
||||
static void BuildAirClick_Demolish(Window *w)
|
||||
@@ -62,7 +65,7 @@ static OnButtonClick * const _build_air_button_proc[] = {
|
||||
|
||||
static void BuildAirToolbWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
switch (e->event) {
|
||||
case WE_PAINT:
|
||||
DrawWindowWidgets(w);
|
||||
break;
|
||||
@@ -77,8 +80,7 @@ static void BuildAirToolbWndProc(Window *w, WindowEvent *e)
|
||||
case '1': BuildAirClick_Airport(w); break;
|
||||
case '2': BuildAirClick_Demolish(w); break;
|
||||
case 'l': BuildAirClick_Landscaping(w); break;
|
||||
default:
|
||||
return;
|
||||
default: return;
|
||||
}
|
||||
} break;
|
||||
|
||||
@@ -104,6 +106,10 @@ static void BuildAirToolbWndProc(Window *w, WindowEvent *e)
|
||||
if (w != 0)
|
||||
WP(w,def_d).close = true;
|
||||
break;
|
||||
|
||||
case WE_DESTROY:
|
||||
if (_patches.link_terraform_toolbar) DeleteWindowById(WC_SCEN_LAND_GEN, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -131,6 +137,7 @@ void ShowBuildAirToolbar(void)
|
||||
if (_current_player == OWNER_SPECTATOR) return;
|
||||
DeleteWindowById(WC_BUILD_TOOLBAR, 0);
|
||||
AllocateWindowDescFront(&_air_toolbar_desc, 0);
|
||||
if (_patches.link_terraform_toolbar) ShowTerraformToolbar();
|
||||
}
|
||||
|
||||
static void BuildAirportPickerWndProc(Window *w, WindowEvent *e)
|
||||
@@ -149,9 +156,9 @@ static void BuildAirportPickerWndProc(Window *w, WindowEvent *e)
|
||||
if (!HASBIT(avail_airports, 0) && sel == AT_SMALL) sel = AT_LARGE;
|
||||
if (!HASBIT(avail_airports, 1) && sel == AT_LARGE) sel = AT_SMALL;
|
||||
|
||||
/* 'Country Airport' starts at widget 3, and if its bit is set, it is available,
|
||||
* so take its opposite value to set the disabled_state. There are only 5 available
|
||||
* airports, so XOr with 0x1F (1 1111) */
|
||||
/* 'Country Airport' starts at widget 3, and if its bit is set, it is
|
||||
* available, so take its opposite value to set the disabled_state. There
|
||||
* are only 5 available airports, so XOR with 0x1F (1 1111) */
|
||||
w->disabled_state = (avail_airports ^ 0x1F) << 3;
|
||||
|
||||
_selected_airport_type = sel;
|
||||
@@ -159,18 +166,18 @@ static void BuildAirportPickerWndProc(Window *w, WindowEvent *e)
|
||||
w->click_state = ((1<<3) << sel) | ((1<<8) << _station_show_coverage);
|
||||
SetTileSelectSize(_airport_size_x[sel],_airport_size_y[sel]);
|
||||
|
||||
if (_patches.modified_catchment) {
|
||||
switch (sel) {
|
||||
case AT_OILRIG: rad = CA_AIR_OILPAD; break;
|
||||
case AT_HELIPORT: rad = CA_AIR_HELIPORT; break;
|
||||
case AT_SMALL: rad = CA_AIR_SMALL; break;
|
||||
case AT_LARGE: rad = CA_AIR_LARGE; break;
|
||||
case AT_METROPOLITAN: rad = CA_AIR_METRO; break;
|
||||
case AT_INTERNATIONAL: rad = CA_AIR_INTER; break;
|
||||
}
|
||||
}
|
||||
if (_patches.modified_catchment) {
|
||||
switch (sel) {
|
||||
case AT_OILRIG: rad = CA_AIR_OILPAD; break;
|
||||
case AT_HELIPORT: rad = CA_AIR_HELIPORT; break;
|
||||
case AT_SMALL: rad = CA_AIR_SMALL; break;
|
||||
case AT_LARGE: rad = CA_AIR_LARGE; break;
|
||||
case AT_METROPOLITAN: rad = CA_AIR_METRO; break;
|
||||
case AT_INTERNATIONAL: rad = CA_AIR_INTER; break;
|
||||
}
|
||||
}
|
||||
|
||||
if (_station_show_coverage) SetTileSelectBigSize(-rad, -rad, 2 * rad, 2 * rad);
|
||||
if (_station_show_coverage) SetTileSelectBigSize(-rad, -rad, 2 * rad, 2 * rad);
|
||||
|
||||
DrawWindowWidgets(w);
|
||||
// strings such as 'Size' and 'Coverage Area'
|
||||
@@ -181,7 +188,7 @@ static void BuildAirportPickerWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
case WE_CLICK: {
|
||||
switch(e->click.widget) {
|
||||
switch (e->click.widget) {
|
||||
case 3: case 4: case 5: case 6: case 7:
|
||||
_selected_airport_type = e->click.widget - 3;
|
||||
SndPlayFx(SND_15_BEEP);
|
||||
@@ -205,8 +212,7 @@ static void BuildAirportPickerWndProc(Window *w, WindowEvent *e)
|
||||
} break;
|
||||
|
||||
case WE_DESTROY:
|
||||
if (!WP(w,def_d).close)
|
||||
ResetObjectToPlace();
|
||||
if (!WP(w,def_d).close) ResetObjectToPlace();
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -220,8 +226,8 @@ static const Widget _build_airport_picker_widgets[] = {
|
||||
{WWT_NODISTXTBTN, RESIZE_NONE, 14, 2, 145, 63, 74, STR_306B_HELIPORT, STR_3058_SELECT_SIZE_TYPE_OF_AIRPORT},
|
||||
{WWT_NODISTXTBTN, RESIZE_NONE, 14, 2, 145, 39, 50, STR_305AA_LARGE, STR_3058_SELECT_SIZE_TYPE_OF_AIRPORT},
|
||||
{WWT_NODISTXTBTN, RESIZE_NONE, 14, 2, 145, 51, 62, STR_305AB_LARGE, STR_3058_SELECT_SIZE_TYPE_OF_AIRPORT},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 14, 73, 88, 98, STR_02DB_OFF, STR_3065_DON_T_HIGHLIGHT_COVERAGE},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 74, 133, 88, 98, STR_02DA_ON, STR_3064_HIGHLIGHT_COVERAGE_AREA},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 14, 73, 88, 98, STR_02DB_OFF, STR_3065_DON_T_HIGHLIGHT_COVERAGE},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 74, 133, 88, 98, STR_02DA_ON, STR_3064_HIGHLIGHT_COVERAGE_AREA},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
|
||||
+2
-1
@@ -1,8 +1,9 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef AIRPORT_MOVEMENT_H
|
||||
#define AIRPORT_MOVEMENT_H
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "macros.h"
|
||||
|
||||
typedef struct AirportMovingData {
|
||||
int x,y;
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
/*
|
||||
* This file has the core function for AyStar
|
||||
* AyStar is a fast pathfinding routine and is used for things like
|
||||
@@ -15,7 +17,7 @@
|
||||
*/
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "aystar.h"
|
||||
// This looks in the Hash if a node exists in ClosedList
|
||||
// If so, it returns the PathNode, else NULL
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
/*
|
||||
* This file has the header for AyStar
|
||||
* AyStar is a fast pathfinding routine and is used for things like
|
||||
@@ -27,7 +29,7 @@ enum{
|
||||
|
||||
typedef struct AyStarNode AyStarNode;
|
||||
struct AyStarNode {
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
uint direction;
|
||||
uint user_data[2];
|
||||
};
|
||||
@@ -174,4 +176,4 @@ void AyStarMain_Clear(AyStar *aystar);
|
||||
void init_AyStar(AyStar* aystar, Hash_HashProc hash, uint num_buckets);
|
||||
|
||||
|
||||
#endif
|
||||
#endif /* AYSTAR_H */
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
/* $Id$ */
|
||||
|
||||
/** @file bridge.h Header file for bridges */
|
||||
|
||||
#ifndef BRIDGE_H
|
||||
#define BRIDGE_H
|
||||
|
||||
/** Struct containing information about a single bridge type
|
||||
*/
|
||||
typedef struct Bridge {
|
||||
byte avail_year; ///< the year in which the bridge becomes available
|
||||
byte min_length; ///< the minimum length of the bridge (not counting start and end tile)
|
||||
byte max_length; ///< the maximum length of the bridge (not counting start and end tile)
|
||||
uint16 price; ///< the relative price of the bridge
|
||||
uint16 speed; ///< maximum travel speed
|
||||
PalSpriteID sprite; ///< the sprite which is used in the GUI (possibly with a recolor sprite)
|
||||
StringID material; ///< the string that contains the bridge description
|
||||
PalSpriteID **sprite_table; ///< table of sprites for drawing the bridge
|
||||
byte flags; ///< bit 0 set: disable drawing of far pillars.
|
||||
} Bridge;
|
||||
|
||||
extern const Bridge orig_bridge[MAX_BRIDGES];
|
||||
extern Bridge _bridge[MAX_BRIDGES];
|
||||
|
||||
#endif /* BRIDGE_H */
|
||||
+43
-42
@@ -1,6 +1,11 @@
|
||||
/* $Id$ */
|
||||
|
||||
/** @file bridge_gui.c Graphical user interface for bridge construction*/
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "window.h"
|
||||
#include "gui.h"
|
||||
@@ -8,23 +13,19 @@
|
||||
#include "gfx.h"
|
||||
#include "command.h"
|
||||
#include "sound.h"
|
||||
#include "variables.h"
|
||||
#include "bridge.h"
|
||||
|
||||
static struct BridgeData {
|
||||
int count;
|
||||
uint count;
|
||||
TileIndex start_tile;
|
||||
TileIndex end_tile;
|
||||
byte type;
|
||||
byte indexes[MAX_BRIDGES];
|
||||
int32 costs[MAX_BRIDGES];
|
||||
} _bridge;
|
||||
} _bridgedata;
|
||||
|
||||
extern const uint16 _bridge_type_price_mod[MAX_BRIDGES];
|
||||
|
||||
extern const PalSpriteID _bridge_sprites[MAX_BRIDGES];
|
||||
extern const uint16 _bridge_speeds[MAX_BRIDGES];
|
||||
extern const StringID _bridge_material[MAX_BRIDGES];
|
||||
|
||||
void CcBuildBridge(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
void CcBuildBridge(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||
{
|
||||
if (success) SndPlayTileFx(SND_27_BLACKSMITH_ANVIL, tile);
|
||||
}
|
||||
@@ -32,7 +33,8 @@ void CcBuildBridge(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
static void BuildBridge(Window *w, int i)
|
||||
{
|
||||
DeleteWindow(w);
|
||||
DoCommandP(_bridge.end_tile, _bridge.start_tile, _bridge.indexes[i] | (_bridge.type << 8), CcBuildBridge,
|
||||
DoCommandP(_bridgedata.end_tile, _bridgedata.start_tile,
|
||||
_bridgedata.indexes[i] | (_bridgedata.type << 8), CcBuildBridge,
|
||||
CMD_BUILD_BRIDGE | CMD_AUTO | CMD_MSG(STR_5015_CAN_T_BUILD_BRIDGE_HERE));
|
||||
}
|
||||
|
||||
@@ -40,25 +42,25 @@ static void BuildBridgeWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
int i;
|
||||
uint i;
|
||||
|
||||
DrawWindowWidgets(w);
|
||||
|
||||
for(i=0; i < 4 && i + w->vscroll.pos < _bridge.count; i++) {
|
||||
int ind = _bridge.indexes[i + w->vscroll.pos];
|
||||
for (i = 0; i < 4 && i + w->vscroll.pos < _bridgedata.count; i++) {
|
||||
const Bridge *b = &_bridge[_bridgedata.indexes[i + w->vscroll.pos]];
|
||||
|
||||
SetDParam(2, _bridge.costs[i + w->vscroll.pos]);
|
||||
SetDParam(1, (_bridge_speeds[ind] >> 4) * 10);
|
||||
SetDParam(0, _bridge_material[ind]);
|
||||
DrawSprite(_bridge_sprites[ind], 3, 15 + i * 22);
|
||||
SetDParam(2, _bridgedata.costs[i + w->vscroll.pos]);
|
||||
SetDParam(1, (b->speed >> 4) * 10);
|
||||
SetDParam(0, b->material);
|
||||
DrawSprite(b->sprite, 3, 15 + i * 22);
|
||||
|
||||
DrawString(44, 15 + i*22 , STR_500D, 0);
|
||||
DrawString(44, 15 + i * 22 , STR_500D, 0);
|
||||
}
|
||||
} break;
|
||||
|
||||
case WE_KEYPRESS: {
|
||||
uint i = e->keypress.keycode - '1';
|
||||
if (i < 9 && i < (uint)_bridge.count) {
|
||||
if (i < 9 && i < _bridgedata.count) {
|
||||
e->keypress.cont = false;
|
||||
BuildBridge(w, i);
|
||||
}
|
||||
@@ -67,9 +69,9 @@ static void BuildBridgeWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
case WE_CLICK:
|
||||
if (e->click.widget == 2) {
|
||||
if (e->click.widget == 2) {
|
||||
uint ind = ((int)e->click.pt.y - 14) / 22;
|
||||
if (ind < 4 && (ind += w->vscroll.pos) < (uint)_bridge.count)
|
||||
if (ind < 4 && (ind += w->vscroll.pos) < _bridgedata.count)
|
||||
BuildBridge(w, ind);
|
||||
}
|
||||
break;
|
||||
@@ -110,54 +112,53 @@ static const WindowDesc _build_road_bridge_desc = {
|
||||
};
|
||||
|
||||
|
||||
void ShowBuildBridgeWindow(uint start, uint end, byte bridge_type)
|
||||
void ShowBuildBridgeWindow(TileIndex start, TileIndex end, byte bridge_type)
|
||||
{
|
||||
int j = 0;
|
||||
uint j = 0;
|
||||
int32 ret;
|
||||
uint16 errmsg;
|
||||
StringID errmsg;
|
||||
|
||||
DeleteWindowById(WC_BUILD_BRIDGE, 0);
|
||||
|
||||
_bridge.type = bridge_type;
|
||||
_bridge.start_tile = start;
|
||||
_bridge.end_tile = end;
|
||||
_bridgedata.type = bridge_type;
|
||||
_bridgedata.start_tile = start;
|
||||
_bridgedata.end_tile = end;
|
||||
|
||||
errmsg = 0xFFFF;
|
||||
errmsg = INVALID_STRING_ID;
|
||||
|
||||
// only query bridge building possibility once, result is the same for all bridges!
|
||||
// returns CMD_ERROR on failure, and priCe on success
|
||||
// returns CMD_ERROR on failure, and price on success
|
||||
ret = DoCommandByTile(end, start, (bridge_type << 8), DC_AUTO | DC_QUERY_COST, CMD_BUILD_BRIDGE);
|
||||
|
||||
if (ret == CMD_ERROR) {
|
||||
if (CmdFailed(ret)) {
|
||||
errmsg = _error_message;
|
||||
}
|
||||
// check which bridges can be built
|
||||
else {
|
||||
} else {
|
||||
// check which bridges can be built
|
||||
int bridge_len; // length of the middle parts of the bridge
|
||||
int tot_bridge_len; // total length of bridge
|
||||
int tot_bridgedata_len; // total length of bridge
|
||||
|
||||
// get absolute bridge length
|
||||
bridge_len = GetBridgeLength(start, end);
|
||||
tot_bridge_len = bridge_len + 2;
|
||||
tot_bridgedata_len = bridge_len + 2;
|
||||
|
||||
tot_bridge_len = CalcBridgeLenCostFactor(tot_bridge_len);
|
||||
tot_bridgedata_len = CalcBridgeLenCostFactor(tot_bridgedata_len);
|
||||
|
||||
for (bridge_type = 0; bridge_type != MAX_BRIDGES; bridge_type++) { // loop for all bridgetypes
|
||||
|
||||
if (CheckBridge_Stuff(bridge_type, bridge_len)) {
|
||||
const Bridge *b = &_bridge[bridge_type];
|
||||
// bridge is accepted, add to list
|
||||
// add to terraforming & bulldozing costs the cost of the bridge itself (not computed with DC_QUERY_COST)
|
||||
_bridge.costs[j] = ret + (((int64)tot_bridge_len * _price.build_bridge * _bridge_type_price_mod[bridge_type]) >> 8);
|
||||
_bridge.indexes[j] = bridge_type;
|
||||
_bridgedata.costs[j] = ret + (((int64)tot_bridgedata_len * _price.build_bridge * b->price) >> 8);
|
||||
_bridgedata.indexes[j] = bridge_type;
|
||||
j++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
_bridge.count = j;
|
||||
_bridgedata.count = j;
|
||||
|
||||
if (j != 0) {
|
||||
Window *w = AllocateWindowDesc((_bridge.type & 0x80) ? &_build_road_bridge_desc : &_build_bridge_desc);
|
||||
Window *w = AllocateWindowDesc((_bridgedata.type & 0x80) ? &_build_road_bridge_desc : &_build_bridge_desc);
|
||||
w->vscroll.cap = 4;
|
||||
w->vscroll.count = (byte)j;
|
||||
} else {
|
||||
|
||||
+13
-3
@@ -1,5 +1,8 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "callback_table.h"
|
||||
#include "functions.h"
|
||||
|
||||
// If you add a callback for DoCommandP, also add the callback in here
|
||||
@@ -8,6 +11,7 @@
|
||||
|
||||
/* aircraft_gui.c */
|
||||
CommandCallback CcBuildAircraft;
|
||||
CommandCallback CcCloneAircraft;
|
||||
|
||||
/* airport_gui.c */
|
||||
CommandCallback CcBuildAirport;
|
||||
@@ -23,7 +27,6 @@ CommandCallback CcBuildCanal;
|
||||
CommandCallback CcPlaySound10;
|
||||
CommandCallback CcPlaceSign;
|
||||
CommandCallback CcTerraform;
|
||||
//CommandCallback CcDemolish;
|
||||
CommandCallback CcBuildTown;
|
||||
|
||||
/* rail_gui.c */
|
||||
@@ -39,13 +42,16 @@ CommandCallback CcRoadDepot;
|
||||
|
||||
/* roadveh_gui.c */
|
||||
CommandCallback CcBuildRoadVeh;
|
||||
CommandCallback CcCloneRoadVeh;
|
||||
|
||||
/* ship_gui.c */
|
||||
CommandCallback CcBuildShip;
|
||||
CommandCallback CcCloneShip;
|
||||
|
||||
/* train_gui.c */
|
||||
CommandCallback CcBuildWagon;
|
||||
CommandCallback CcBuildLoco;
|
||||
CommandCallback CcCloneTrain;
|
||||
|
||||
CommandCallback *_callback_table[] = {
|
||||
/* 0x00 */ NULL,
|
||||
@@ -68,7 +74,11 @@ CommandCallback *_callback_table[] = {
|
||||
/* 0x11 */ CcPlaySound1D,
|
||||
/* 0x12 */ CcPlaySound1E,
|
||||
/* 0x13 */ CcStation,
|
||||
/* 0x14 */ CcTerraform
|
||||
/* 0x14 */ CcTerraform,
|
||||
/* 0x15 */ CcCloneAircraft,
|
||||
/* 0x16 */ CcCloneRoadVeh,
|
||||
/* 0x17 */ CcCloneShip,
|
||||
/* 0x18 */ CcCloneTrain,
|
||||
};
|
||||
|
||||
const int _callback_table_count = lengthof(_callback_table);
|
||||
|
||||
+5
-1
@@ -1,7 +1,11 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef CALLBACK_TABLE_H
|
||||
#define CALLBACK_TABLE_H
|
||||
|
||||
#include "functions.h"
|
||||
|
||||
extern CommandCallback *_callback_table[];
|
||||
extern const int _callback_table_count;
|
||||
|
||||
#endif
|
||||
#endif /* CALLBACK_TABLE_H */
|
||||
|
||||
+153
@@ -1,3 +1,156 @@
|
||||
0.4.5 (2006-01-31)
|
||||
------------------------------------------------------------------------
|
||||
|
||||
- Feature: [newgrf] Implement varaction2 property 0x41 and 0xDA. (2361)
|
||||
- Feature: giving server_ip a value of 'all' will make the server listen on any interface (2374)
|
||||
- Feature: shortcut CTRL + U that clears the current input-box (2385)
|
||||
- Feature: [newgrf] Implement the mechanism for handling newgrf callbacks (2389)
|
||||
- Feature: [newgrf] Implement the 'refit capacity' callback (2389)
|
||||
- Feature: saving games happen in a seperate thread (2391)
|
||||
- Feature: [newgrf] Implement powered wagons, and the callback that goes with it (2414)
|
||||
- Feature: [newgrf] Implement shorter train vehicles (2428)
|
||||
- Feature: New display option: 'transparent station signs' (2438)
|
||||
- Feature: You can now give transfer order to set up feeder systems (2441)
|
||||
- Feature: Removing tracks with the 'remove' tool, automatically removes signals on the tracks (2469)
|
||||
- Feature: [localisation] Allow changing the order of parameters in translated strings (2573)
|
||||
- Feature: [localisation] New way to specify plural forms (2592)
|
||||
- Feature: [localisation] Support genders (2594)
|
||||
- Feature: [localisation] Support cases (2597)
|
||||
- Feature: add support for truncating strings to a given (pixel) length (2607)
|
||||
- Feature: Overhaul DirectMusic MIDI backend, remove "experimental" status (2712)
|
||||
- Feature: Change the driver probing algorithm: Use the first music/sound/video which succeeds initialising instead of bailing out after the first. No need to specify -snull if no soundcard is present anymore (2728)
|
||||
- Feature: The Main Toolbar Dropdown Menu can now display disabled items (2734)
|
||||
- Feature: Clone vehicles (2764)
|
||||
- Feature: When starting without a config file determine the language on basis of the current locale (2777)
|
||||
- Feature: [NewGRF] Add support for "extended bytes" (2872)
|
||||
- Feature: [localisation] Major step twoards ISO-8859-15: Implement missing characters (2879)
|
||||
- Feature: Implement the console command rm to remove savegames (2941)
|
||||
- Feature: Danish town names (2957)
|
||||
- Feature: Menu option to toggle console (2958)
|
||||
- Feature: Calculate proportions of non-square giant screenshot correctly (2963)
|
||||
- Feature: [newgrf] Implement current set of action D (ParamSet) operations (2968)
|
||||
- Feature: [newgrf] Show a wagon's speed limit in purchase list (2969)
|
||||
- Feature: [newgrf] Support loading VarAction2 parameter for variables 0x60-0x7F (2971)
|
||||
- Feature: [newgrf] Add patch option for wagon speed limits (2982)
|
||||
- Feature: [newgrf] Support loading of bridge attributes and tables from GRF (3004)
|
||||
- Feature: Native Support for Win64 (3008)
|
||||
- Feature: OSX now uses quicktime to play midi files (3022)
|
||||
- Feature: [OSX] Command+Q now works in main menu (3027)
|
||||
- Feature: Allow unbanning players based on banlist-id (as well as IP) (3067)
|
||||
- Feature: 'status' and 'clients' now show the IP of the players (3067)
|
||||
- Feature: Make it possible to create a screenshot from the console that is both big and has no console, or any combination of (3068)
|
||||
- Feature: [newgrf] Add support for rail vehicle weight greater than 255 tons (3071)
|
||||
- Feature: 'HOME' icon to saveload dialogs that jumps to the default save/load directory based on the dialog (3096)
|
||||
- Feature: Turkish translation (3120)
|
||||
- Feature: [newgrf] Support positioning of rail vehicle visual effects (3132)
|
||||
- Feature: [newgrf] Support for articulated rail vehicles (3139)
|
||||
- Feature: [newgrf] Add support for cargo refitting specification by cargo classes (3148)
|
||||
- Feature: [newgrf] Action 7/9 new value : is it TTDPatch or OpenTTD? (3152)
|
||||
- Feature: Drag and drop rocky areas in scenario editor (3153)
|
||||
- Feature: Added patch option to link the terraform toolbar to the rail, road, water and airport toolbars (3157)
|
||||
- Feature: Right-Click-Scrolling optionally moves in the opposite direction (3222)
|
||||
- Feature: Native cocoa sound and video drivers for OSX (3281)
|
||||
- Feature: [newgrf] Allow train running cost class to differ from engine class (3388)
|
||||
- Feature: Kick and ban now with IP numbers (3407)
|
||||
- Feature: Allow seeing and setting the maximum amount of companies and spectators for a server. This can be changed/viewed during runtime as well in the console (3427)
|
||||
- Feature: Allow the network game list to be sorted (by name/clients/compatibility ascending/descending) (3441)
|
||||
- Feature: Make it possible to ban offline clients (3469)
|
||||
- Fix: The refit window now shows the correct refit options (2365)
|
||||
- Fix: Refitting to a cargo which is already carried by some vehicles takes their capacities into account for display (2365)
|
||||
- Fix: Add 'multihead' TTDPatch option to OpenTTD newgrf flags-emulation (2368)
|
||||
- Fix: make install tried to install scenarios in the (non-existing) personal dir when USE_HOMEDIR is specified (2371)
|
||||
- Fix: [console] update the example scripts in the scripts/ directory to reflect the new console functionality (2372)
|
||||
- Fix: [console] any line starting with a '#' is a comment so ignore it (2372)
|
||||
- Fix: [console] The special variables whose value can only be set by a custom process should, also print out their newly set value there (2372)
|
||||
- Fix: [newgrf] Ignore action 0 prop 0x20 (air drag) (2377)
|
||||
- Fix: [newgrf] Further property stubs, help prevents subsequent incorrect reading of newgrf data (2378)
|
||||
- Fix: Build year for mail compartment of planes was not set correctly, affected station ratings (2380)
|
||||
- Fix: Endgame window on easy difficulty resulted in infinite loop (2381)
|
||||
- Fix: Check the airport type when building an airport (2382)
|
||||
- Fix: Monkey-testing turned up some command crashes (2383)
|
||||
- Fix: Check selling land and setting player colour. Also an extra map-bounds check for terraforming (2384)
|
||||
- Fix: [realistic accel] Very slow trains no longer get an increase in maximum speed when part of them is in a depot (2388)
|
||||
- Fix: [newgrf] Load power for dual-headed engines correctly (2400)
|
||||
- Fix: [newgrf] When resolving callbacks, dont ignore wagon overrides (2410)
|
||||
- Fix: Station ratings aren't affected by speed limits from realistic acceleration anymore (2411)
|
||||
- Fix: building vehicles without depot crashed the game (2412)
|
||||
- Fix: certain resolutions caused a crash when minimap was partly dragged outside the game window (2424)
|
||||
- Fix: Deleting canals under bridges removed bridges first in certain configurations (2436)
|
||||
- Fix: [NPF] Vehicles try to drive into a tunnel entrance from above (2471)
|
||||
- Fix: [newgrf] Some road vehicle action 0 properties were loaded as the wrong type (int8,int16,int32) causing undefined results. (like cargo types being wrong) (2474)
|
||||
- Fix: The console variable autoclean_unprotected was linked to the variable _network_autoclean_protected (2498)
|
||||
- Fix: Old bug in the PCX writer: The first pixel column contained garbage, the picture was shifted one to the right, and the last column was dropped (2512)
|
||||
- Fix: Using the mouse wheel could lead to a crash if mouse was not over a widget (2530)
|
||||
- Fix: blinking 'lock' gfx in multiplayer games (2548)
|
||||
- Fix: Remove original train pathfinder. Enhanced old pathfinder. (2553)
|
||||
- Fix: Spaces in the path to the MIDI files caused the win32 MIDI player to fail (2563)
|
||||
- Fix: set server map name to the loaded name of the game/scenario (2610)
|
||||
- Fix: Improve the old pathfinder. Changed it to A* instead of Dijkstra. Benchmark shows that NTP is now around 10x faster than NPF (2635)
|
||||
- Fix: Correctly save and load company_value, it's 64 bits wide, not 32 bits (2684)
|
||||
- Fix: Volume control works now for the DirectMusic MIDI backend (2712)
|
||||
- Fix: Change the fence algorithm so it removes fences when no farm tile is adjacent (2739)
|
||||
- Fix: Tree tiles above the snow line got redrawn disproportionately often (2750)
|
||||
- Fix: Depots could build trains of the wrong track type (2764)
|
||||
- Fix: Sort the directories in the scenarion/savegame list (2860)
|
||||
- Fix: On OS/2 show the trailing \ if the current directory is a root directory (2860)
|
||||
- Fix: Return a proper version number, when testing the TTDPatch version in the SkipIf action (2862)
|
||||
- Fix: Change the way NewGRFs are loaded, this saves quite some sprite slots - about 2000 for DBSetXL for example (2868)
|
||||
- Fix: Several format string vulnerabilities and buffer overflows in the network code (2899)
|
||||
- Fix: fixed issue where autorenewed vehicles didn't get all stats updated (2912)
|
||||
- Fix: Exit the child of the extmidi backend with _exit() instead of exit(), because we don't want any atexit handlers - especially flushing output streams - to run, if exec() fails (2938)
|
||||
- Fix: Server crash with "say"-command (2950)
|
||||
- Fix: Fix win32 midi volume level control which didn't work (2960)
|
||||
- Fix: [OSX] quitting the game no longer leaves a process behind that eats all the CPU power (3281)
|
||||
- Fix: Fix for [ 1216203 ] UFO-broken waypoint (2961)
|
||||
- Fix: [newgrf] Include missing grf feature canal
|
||||
- Fix: [newgrf] Add bounds checking to VehicleChangeInfo for vehicles
|
||||
- Fix: [newgrf] Wagon speed limits don't apply for wagons with livery overrides
|
||||
- Fix: Align settings pool items to the size of void* to fix bus errors on 64bit architectures which require aligned variables (2976)
|
||||
- Fix: restart_game_date is an UINT16, not a BYTE. Now setting the game restart year via the console should work (2987)
|
||||
- Fix: [newgrf] Some GRF files don't specify a name or description, in which case the Action 8 is 8 bytes, not 9 (3005)
|
||||
- Fix: The finnish markka was never abbreviated with capital letters (3021)
|
||||
- Fix: Improve handling of non-existent sprite sets (3044)
|
||||
- Fix: Don't attempt to map and empty sprite group to a vehicle (3045)
|
||||
- Fix: Fixed typo and hang for BeOS Networking (3053)
|
||||
- Fix: On Win98 and lower when you go to the root directory of a drive (eg. C:\) you were stuck there indefinitely and couldn't change any directories or see any files (3056)
|
||||
- Fix: Complete rewrite of autoreplace; multiheaded train engines are replaced correctly (3081)
|
||||
- Fix: A new train is now made if the front unit is an engine and the former front engine is moved away (3144)
|
||||
- Fix: There are only 2 possible directions for ship depots, not 4 (3199)
|
||||
- Fix: Allow bribing up to the maximum rating for bribing, don't disable this option at some arbitrary value early (3201)
|
||||
- Fix: Don't lower land on tunnel, even with diag tracks on it (3228)
|
||||
- Fix: Crash when making a screenshotin the main menu (3235)
|
||||
- Fix: Crash when starting a scenarion via 'New Game' fails (3235)
|
||||
- Fix: Determine clicked status of sticky icon from window flags rather than the widget click state (3247)
|
||||
- Fix: Graphical glitch with autorail tool on a certain tile-types (3254)
|
||||
- Fix: Center the X of the window close button (3302)
|
||||
- Fix: [newgrf] Unload engine names before loading grf files (3316)
|
||||
- Fix: Network window crash when it receives invalid information for example from the integrated nightly, so validate the network-input when it is received (3322)
|
||||
- Fix: Build failed if SDL is built without pthread support (3326)
|
||||
- Fix: Move initialization of vehicle random_bits to DC_EXEC blocks to allow use of Random() instead of InteractiveRandom(), which will alleviate some possib le network desyncs (3352)
|
||||
- Fix: The default AI tried to change the service intervals of vehicles via the CMD_CHANGE_TRAIN_SERVICE_INT command - regardless of the type of the vehicle (3367)
|
||||
- Fix: Out-of-bounds array access when road vehicles overtook in a curve caused desyncs (3371)
|
||||
- Fix: Update signal states when building or removing rail station blocks (3372)
|
||||
- Fix: Don't allow trains to get bigger than 100 via drag and drop (3374)
|
||||
- Fix: Don't reset date in the scenario editor when pressing RandomLand (3376)
|
||||
- Fix: [newgrf] Running cost should be halved for dual head vehicles (3384)
|
||||
- Fix: No fence was placed when placing fences and the neighbouring tile is a rail configuration which permits a fence but has a signal (3389)
|
||||
- Fix: [newgrf] Ignore non-climate dependent cargo types (3394)
|
||||
- Fix: [newgrf] Only add a random number of days to an engine's base introduction date if that date is not 0 (3410)
|
||||
- Fix: When changing the server password via the console, actually set the password as well as flag whether it is required (3411)
|
||||
- Fix: Under certain conditions placing a road tile parallel under a bridge would, instead of failing, succeed and place a perpendicular piece (3413)
|
||||
- Fix: Disable the Fund New Industry menu item and window when connected to a server as a spectator (3414)
|
||||
- Fix: Disable the clone and refit buttons in the train view when viewing another player's vehicles, or as a spectator (3415)
|
||||
- Fix: Disallow building an oil rig above sea level (3416)
|
||||
- Fix: When removing a town-owned tunnel the player's rating was not reduced (3418)
|
||||
- Fix: (Possible) game crash on removing track/road under bridge if a vehicle was on the track/road under the bridge and the track/road sloped (3419)
|
||||
- Fix: [newgrf] Only power should decide whether a rail vehicle is an engine or a wagon. (fixes SHIKI 810 in jpsetw.grf) (3424)
|
||||
- Fix: Incorrect validating of tree-planting command which can allow a buffer-overflow (3446)
|
||||
- Fix: [newgrf] When changing the sprite ID of a vehicle, if it is not FD (custom graphics), the value needs to changed from a 16bit array offset to an array index. (fixes tropicstw.grf) (3449)
|
||||
- Fix: You couldn't remove an item from a list-type of config ingame from the configuration file (3475)
|
||||
- Fix: [newgrf] Always reinitialize the ttdpatch flags as patch settings may have changed (3486)
|
||||
- Fix: Price for demolishing a bridge was dependent on orientation and map size (3487)
|
||||
|
||||
|
||||
0.4.0.1 (2005-05-21)
|
||||
------------------------------------------------------------------------
|
||||
|
||||
|
||||
+191
-202
@@ -1,10 +1,16 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "player.h"
|
||||
#include "tile.h"
|
||||
#include "viewport.h"
|
||||
#include "command.h"
|
||||
#include "variables.h"
|
||||
#include "table/sprites.h"
|
||||
|
||||
typedef struct TerraformerHeightMod {
|
||||
TileIndex tile;
|
||||
@@ -31,13 +37,11 @@ static int TerraformAllowTileProcess(TerraformerState *ts, TileIndex tile)
|
||||
TileIndex *t;
|
||||
int count;
|
||||
|
||||
if (TileX(tile) == MapMaxX() || TileY(tile) == MapMaxY())
|
||||
return -1;
|
||||
if (TileX(tile) == MapMaxX() || TileY(tile) == MapMaxY()) return -1;
|
||||
|
||||
t = ts->tile_table;
|
||||
for(count = ts->tile_table_count; count != 0; count--,t++) {
|
||||
if (*t == tile)
|
||||
return 0;
|
||||
for (count = ts->tile_table_count; count != 0; count--, t++) {
|
||||
if (*t == tile) return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
@@ -48,9 +52,8 @@ static int TerraformGetHeightOfTile(TerraformerState *ts, TileIndex tile)
|
||||
TerraformerHeightMod *mod = ts->modheight;
|
||||
int count;
|
||||
|
||||
for(count = ts->modheight_count; count != 0; count--, mod++) {
|
||||
if (mod->tile == tile)
|
||||
return mod->height;
|
||||
for (count = ts->modheight_count; count != 0; count--, mod++) {
|
||||
if (mod->tile == tile) return mod->height;
|
||||
}
|
||||
|
||||
return TileHeight(tile);
|
||||
@@ -63,12 +66,10 @@ static void TerraformAddDirtyTile(TerraformerState *ts, TileIndex tile)
|
||||
|
||||
count = ts->tile_table_count;
|
||||
|
||||
if (count >= 625)
|
||||
return;
|
||||
if (count >= 625) return;
|
||||
|
||||
for(t = ts->tile_table; count != 0; count--,t++) {
|
||||
if (*t == tile)
|
||||
return;
|
||||
if (*t == tile) return;
|
||||
}
|
||||
|
||||
ts->tile_table[ts->tile_table_count++] = tile;
|
||||
@@ -76,16 +77,16 @@ static void TerraformAddDirtyTile(TerraformerState *ts, TileIndex tile)
|
||||
|
||||
static void TerraformAddDirtyTileAround(TerraformerState *ts, TileIndex tile)
|
||||
{
|
||||
TerraformAddDirtyTile(ts, tile+TILE_XY(0,-1));
|
||||
TerraformAddDirtyTile(ts, tile+TILE_XY(-1,-1));
|
||||
TerraformAddDirtyTile(ts, tile+TILE_XY(-1,0));
|
||||
TerraformAddDirtyTile(ts, tile + TileDiffXY( 0, -1));
|
||||
TerraformAddDirtyTile(ts, tile + TileDiffXY(-1, -1));
|
||||
TerraformAddDirtyTile(ts, tile + TileDiffXY(-1, 0));
|
||||
TerraformAddDirtyTile(ts, tile);
|
||||
}
|
||||
|
||||
static int TerraformProc(TerraformerState *ts, uint tile, int mode)
|
||||
static int TerraformProc(TerraformerState *ts, TileIndex tile, int mode)
|
||||
{
|
||||
int r;
|
||||
int32 ret;
|
||||
bool skip_clear = false;
|
||||
|
||||
assert(tile < MapSize());
|
||||
|
||||
@@ -110,27 +111,30 @@ static int TerraformProc(TerraformerState *ts, uint tile, int mode)
|
||||
|
||||
// If we have a single diagonal track there, the other side of
|
||||
// tile can be terraformed.
|
||||
if ((_map5[tile]&~0x40) == _railway_modes[mode])
|
||||
return 0;
|
||||
if ((_m[tile].m5 & ~0x40) == _railway_modes[mode]) {
|
||||
if (ts->direction == 1) return 0;
|
||||
skip_clear = true;
|
||||
}
|
||||
}
|
||||
|
||||
ret = DoCommandByTile(tile, 0,0, ts->flags & ~DC_EXEC, CMD_LANDSCAPE_CLEAR);
|
||||
if (!skip_clear) {
|
||||
int32 ret = DoCommandByTile(tile, 0,0, ts->flags & ~DC_EXEC, CMD_LANDSCAPE_CLEAR);
|
||||
|
||||
if (ret == CMD_ERROR) {
|
||||
_terraform_err_tile = tile;
|
||||
return -1;
|
||||
if (CmdFailed(ret)) {
|
||||
_terraform_err_tile = tile;
|
||||
return -1;
|
||||
}
|
||||
|
||||
ts->cost += ret;
|
||||
}
|
||||
|
||||
ts->cost += ret;
|
||||
|
||||
if (ts->tile_table_count >= 625)
|
||||
return -1;
|
||||
if (ts->tile_table_count >= 625) return -1;
|
||||
ts->tile_table[ts->tile_table_count++] = tile;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static bool TerraformTileHeight(TerraformerState *ts, uint tile, int height)
|
||||
static bool TerraformTileHeight(TerraformerState *ts, TileIndex tile, int height)
|
||||
{
|
||||
int nh;
|
||||
TerraformerHeightMod *mod;
|
||||
@@ -145,42 +149,32 @@ static bool TerraformTileHeight(TerraformerState *ts, uint tile, int height)
|
||||
|
||||
_error_message = STR_1004_TOO_HIGH;
|
||||
|
||||
if (height > 0xF)
|
||||
return false;
|
||||
if (height > 15) return false;
|
||||
|
||||
nh = TerraformGetHeightOfTile(ts, tile);
|
||||
if (nh < 0 || height == nh)
|
||||
return false;
|
||||
if (nh < 0 || height == nh) return false;
|
||||
|
||||
if (TerraformProc(ts, tile, 0)<0)
|
||||
return false;
|
||||
|
||||
if (TerraformProc(ts, tile + TILE_XY(0,-1), 1)<0)
|
||||
return false;
|
||||
|
||||
if (TerraformProc(ts, tile + TILE_XY(-1,-1), 2)<0)
|
||||
return false;
|
||||
|
||||
if (TerraformProc(ts, tile + TILE_XY(-1,0), 3)<0)
|
||||
return false;
|
||||
if (TerraformProc(ts, tile, 0) < 0) return false;
|
||||
if (TerraformProc(ts, tile + TileDiffXY( 0, -1), 1) < 0) return false;
|
||||
if (TerraformProc(ts, tile + TileDiffXY(-1, -1), 2) < 0) return false;
|
||||
if (TerraformProc(ts, tile + TileDiffXY(-1, 0), 3) < 0) return false;
|
||||
|
||||
mod = ts->modheight;
|
||||
count = ts->modheight_count;
|
||||
|
||||
for(;;) {
|
||||
for (;;) {
|
||||
if (count == 0) {
|
||||
if (ts->modheight_count >= 576)
|
||||
return false;
|
||||
ts->modheight_count++;
|
||||
break;
|
||||
}
|
||||
if (mod->tile == (TileIndex)tile)
|
||||
break;
|
||||
if (mod->tile == tile) break;
|
||||
mod++;
|
||||
count--;
|
||||
}
|
||||
|
||||
mod->tile = (TileIndex)tile;
|
||||
mod->tile = tile;
|
||||
mod->height = (byte)height;
|
||||
|
||||
ts->cost += _price.terraform;
|
||||
@@ -236,29 +230,32 @@ int32 CmdTerraformLand(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
ts.modheight = modheight_data;
|
||||
ts.tile_table = tile_table_data;
|
||||
|
||||
tile = TILE_FROM_XY(x,y);
|
||||
tile = TileVirtXY(x, y);
|
||||
|
||||
/* Make an extra check for map-bounds cause we add tiles to the originating tile */
|
||||
if (tile + TileDiffXY(1, 1) >= MapSize()) return CMD_ERROR;
|
||||
|
||||
if (p1 & 1) {
|
||||
if (!TerraformTileHeight(&ts, tile+TILE_XY(1,0),
|
||||
TileHeight(tile + TILE_XY(1, 0)) + direction))
|
||||
if (!TerraformTileHeight(&ts, tile + TileDiffXY(1, 0),
|
||||
TileHeight(tile + TileDiffXY(1, 0)) + direction))
|
||||
return CMD_ERROR;
|
||||
}
|
||||
|
||||
if (p1 & 2) {
|
||||
if (!TerraformTileHeight(&ts, tile+TILE_XY(1,1),
|
||||
TileHeight(tile + TILE_XY(1, 1)) + direction))
|
||||
if (!TerraformTileHeight(&ts, tile + TileDiffXY(1, 1),
|
||||
TileHeight(tile + TileDiffXY(1, 1)) + direction))
|
||||
return CMD_ERROR;
|
||||
}
|
||||
|
||||
if (p1 & 4) {
|
||||
if (!TerraformTileHeight(&ts, tile+TILE_XY(0,1),
|
||||
TileHeight(tile + TILE_XY(0, 1)) + direction))
|
||||
if (!TerraformTileHeight(&ts, tile + TileDiffXY(0, 1),
|
||||
TileHeight(tile + TileDiffXY(0, 1)) + direction))
|
||||
return CMD_ERROR;
|
||||
}
|
||||
|
||||
if (p1 & 8) {
|
||||
if (!TerraformTileHeight(&ts, tile+TILE_XY(0,0),
|
||||
TileHeight(tile + TILE_XY(0, 0)) + direction))
|
||||
if (!TerraformTileHeight(&ts, tile + TileDiffXY(0, 0),
|
||||
TileHeight(tile + TileDiffXY(0, 0)) + direction))
|
||||
return CMD_ERROR;
|
||||
}
|
||||
|
||||
@@ -269,18 +266,19 @@ int32 CmdTerraformLand(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
|
||||
for (count = ts.tile_table_count; count != 0; count--, ti++) {
|
||||
uint z, t;
|
||||
uint tile = *ti;
|
||||
TileIndex tile = *ti;
|
||||
|
||||
z = TerraformGetHeightOfTile(&ts, tile + TILE_XY(0,0));
|
||||
t = TerraformGetHeightOfTile(&ts, tile + TILE_XY(1,0));
|
||||
z = TerraformGetHeightOfTile(&ts, tile + TileDiffXY(0, 0));
|
||||
t = TerraformGetHeightOfTile(&ts, tile + TileDiffXY(1, 0));
|
||||
if (t <= z) z = t;
|
||||
t = TerraformGetHeightOfTile(&ts, tile + TILE_XY(1,1));
|
||||
t = TerraformGetHeightOfTile(&ts, tile + TileDiffXY(1, 1));
|
||||
if (t <= z) z = t;
|
||||
t = TerraformGetHeightOfTile(&ts, tile + TILE_XY(0,1));
|
||||
t = TerraformGetHeightOfTile(&ts, tile + TileDiffXY(0, 1));
|
||||
if (t <= z) z = t;
|
||||
|
||||
if (!CheckTunnelInWay(tile, z*8))
|
||||
if (!CheckTunnelInWay(tile, z * 8)) {
|
||||
return_cmd_error(STR_1002_EXCAVATION_WOULD_DAMAGE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -298,11 +296,10 @@ int32 CmdTerraformLand(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
{
|
||||
int count;
|
||||
TerraformerHeightMod *mod;
|
||||
uint til;
|
||||
|
||||
mod = ts.modheight;
|
||||
for (count = ts.modheight_count; count != 0; count--, mod++) {
|
||||
til = mod->tile;
|
||||
TileIndex til = mod->tile;
|
||||
|
||||
SetTileHeight(til, mod->height);
|
||||
TerraformAddDirtyTileAround(&ts, til);
|
||||
@@ -335,7 +332,7 @@ int32 CmdLevelLand(int ex, int ey, uint32 flags, uint32 p1, uint32 p2)
|
||||
TileIndex tile;
|
||||
int32 ret, cost, money;
|
||||
|
||||
if (p1 > MapSize()) return CMD_ERROR;
|
||||
if (p1 >= MapSize()) return CMD_ERROR;
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION);
|
||||
|
||||
@@ -349,7 +346,7 @@ int32 CmdLevelLand(int ex, int ey, uint32 flags, uint32 p1, uint32 p2)
|
||||
sy = TileY(p1);
|
||||
if (ex < sx) intswap(ex, sx);
|
||||
if (ey < sy) intswap(ey, sy);
|
||||
tile = TILE_XY(sx,sy);
|
||||
tile = TileXY(sx, sy);
|
||||
|
||||
size_x = ex-sx+1;
|
||||
size_y = ey-sy+1;
|
||||
@@ -392,11 +389,12 @@ int32 CmdPurchaseLandArea(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION);
|
||||
|
||||
tile = TILE_FROM_XY(x,y);
|
||||
tile = TileVirtXY(x, y);
|
||||
|
||||
if (!EnsureNoVehicle(tile)) return CMD_ERROR;
|
||||
|
||||
if (IsTileType(tile, MP_UNMOVABLE) && _map5[tile] == 3 && _map_owner[tile] == _current_player)
|
||||
if (IsTileType(tile, MP_UNMOVABLE) && _m[tile].m5 == 3 &&
|
||||
IsTileOwner(tile, _current_player))
|
||||
return_cmd_error(STR_5807_YOU_ALREADY_OWN_IT);
|
||||
|
||||
cost = DoCommandByTile(tile, 0, 0, flags, CMD_LANDSCAPE_CLEAR);
|
||||
@@ -413,25 +411,43 @@ int32 CmdPurchaseLandArea(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
}
|
||||
|
||||
|
||||
static int32 ClearTile_Clear(uint tile, byte flags)
|
||||
static int32 ClearTile_Clear(TileIndex tile, byte flags)
|
||||
{
|
||||
static const int32 * _clear_price_table[] = {
|
||||
NULL,
|
||||
&_price.clear_1, &_price.clear_1,&_price.clear_1,
|
||||
&_price.purchase_land,&_price.purchase_land,&_price.purchase_land,&_price.purchase_land,
|
||||
&_price.clear_2,&_price.clear_2,&_price.clear_2,&_price.clear_2,
|
||||
&_price.clear_3,&_price.clear_3,&_price.clear_3,&_price.clear_3,
|
||||
&_price.purchase_land,&_price.purchase_land,&_price.purchase_land,&_price.purchase_land,
|
||||
&_price.purchase_land,&_price.purchase_land,&_price.purchase_land,&_price.purchase_land,
|
||||
&_price.clear_2,&_price.clear_2,&_price.clear_2,&_price.clear_2,
|
||||
static const int32 null = 0;
|
||||
static const int32* clear_price_table[] = {
|
||||
&null,
|
||||
&_price.clear_1,
|
||||
&_price.clear_1,
|
||||
&_price.clear_1,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.clear_2,
|
||||
&_price.clear_2,
|
||||
&_price.clear_2,
|
||||
&_price.clear_2,
|
||||
&_price.clear_3,
|
||||
&_price.clear_3,
|
||||
&_price.clear_3,
|
||||
&_price.clear_3,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.purchase_land,
|
||||
&_price.clear_2,
|
||||
&_price.clear_2,
|
||||
&_price.clear_2,
|
||||
&_price.clear_2,
|
||||
};
|
||||
const int32 *price = _clear_price_table[_map5[tile] & 0x1F];
|
||||
const int32 *price = clear_price_table[GB(_m[tile].m5, 0, 5)];
|
||||
|
||||
if (flags & DC_EXEC)
|
||||
DoClearSquare(tile);
|
||||
if (flags & DC_EXEC) DoClearSquare(tile);
|
||||
|
||||
if (price == NULL)
|
||||
return 0;
|
||||
return *price;
|
||||
}
|
||||
|
||||
@@ -447,10 +463,11 @@ int32 CmdSellLandArea(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION);
|
||||
|
||||
tile = TILE_FROM_XY(x,y);
|
||||
tile = TileVirtXY(x, y);
|
||||
|
||||
if (!IsTileType(tile, MP_UNMOVABLE) || _m[tile].m5 != 3) return CMD_ERROR;
|
||||
if (!CheckTileOwnership(tile) && _current_player != OWNER_WATER) return CMD_ERROR;
|
||||
|
||||
if (!CheckTileOwnership(tile) && _current_player != OWNER_WATER)
|
||||
return CMD_ERROR;
|
||||
|
||||
if (!EnsureNoVehicle(tile)) return CMD_ERROR;
|
||||
|
||||
@@ -464,45 +481,44 @@ int32 CmdSellLandArea(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
#include "table/clear_land.h"
|
||||
|
||||
|
||||
void DrawClearLandTile(TileInfo *ti, byte set)
|
||||
void DrawClearLandTile(const TileInfo *ti, byte set)
|
||||
{
|
||||
DrawGroundSprite(0xF54 + _tileh_to_sprite[ti->tileh] + set * 19);
|
||||
DrawGroundSprite(SPR_FLAT_BARE_LAND + _tileh_to_sprite[ti->tileh] + set * 19);
|
||||
}
|
||||
|
||||
void DrawHillyLandTile(TileInfo *ti)
|
||||
void DrawHillyLandTile(const TileInfo *ti)
|
||||
{
|
||||
if (ti->tileh != 0) {
|
||||
DrawGroundSprite(0xFA0 + _tileh_to_sprite[ti->tileh]);
|
||||
DrawGroundSprite(SPR_FLAT_ROUGH_LAND + _tileh_to_sprite[ti->tileh]);
|
||||
} else {
|
||||
DrawGroundSprite(_landscape_clear_sprites[((ti->x^ti->y) >> 4) & 0x7]);
|
||||
DrawGroundSprite(_landscape_clear_sprites[GB(ti->x ^ ti->y, 4, 3)]);
|
||||
}
|
||||
}
|
||||
|
||||
void DrawClearLandFence(TileInfo *ti, byte img)
|
||||
void DrawClearLandFence(const TileInfo *ti)
|
||||
{
|
||||
byte m4 = _m[ti->tile].m4;
|
||||
byte z = ti->z;
|
||||
|
||||
if (ti->tileh & 2) {
|
||||
z += 8;
|
||||
if (ti->tileh == 0x17)
|
||||
z += 8;
|
||||
if (ti->tileh == 0x17) z += 8;
|
||||
}
|
||||
|
||||
if (img & 0x38) {
|
||||
DrawGroundSpriteAt(_clear_land_fence_sprites_1[((img >> 3) & 7) - 1] + _fence_mod_by_tileh[ti->tileh], ti->x, ti->y, z);
|
||||
if (GB(m4, 5, 3) != 0) {
|
||||
DrawGroundSpriteAt(_clear_land_fence_sprites_1[GB(m4, 5, 3) - 1] + _fence_mod_by_tileh[ti->tileh], ti->x, ti->y, z);
|
||||
}
|
||||
|
||||
if (img & 0x7) {
|
||||
DrawGroundSpriteAt(_clear_land_fence_sprites_1[(img & 7) - 1] + _fence_mod_by_tileh_2[ti->tileh], ti->x, ti->y, z);
|
||||
if (GB(m4, 2, 3) != 0) {
|
||||
DrawGroundSpriteAt(_clear_land_fence_sprites_1[GB(m4, 2, 3) - 1] + _fence_mod_by_tileh_2[ti->tileh], ti->x, ti->y, z);
|
||||
}
|
||||
}
|
||||
|
||||
static void DrawTile_Clear(TileInfo *ti)
|
||||
{
|
||||
|
||||
switch((ti->map5 & (7<<2)) >> 2) {
|
||||
switch (GB(ti->map5, 2, 3)) {
|
||||
case 0:
|
||||
DrawClearLandTile(ti, (ti->map5 & 3));
|
||||
DrawClearLandTile(ti, GB(ti->map5, 0, 2));
|
||||
break;
|
||||
|
||||
case 1:
|
||||
@@ -510,134 +526,111 @@ static void DrawTile_Clear(TileInfo *ti)
|
||||
break;
|
||||
|
||||
case 2:
|
||||
DrawGroundSprite(0xFB7 + _tileh_to_sprite[ti->tileh]);
|
||||
DrawGroundSprite(SPR_FLAT_ROCKY_LAND_1 + _tileh_to_sprite[ti->tileh]);
|
||||
break;
|
||||
|
||||
case 3:
|
||||
DrawGroundSprite( _clear_land_sprites_1[_map3_lo[ti->tile]&0xF] + _tileh_to_sprite[ti->tileh]);
|
||||
DrawGroundSprite(_clear_land_sprites_1[GB(_m[ti->tile].m3, 0, 4)] + _tileh_to_sprite[ti->tileh]);
|
||||
break;
|
||||
|
||||
case 4:
|
||||
DrawGroundSprite( _clear_land_sprites_2[ti->map5&3] + _tileh_to_sprite[ti->tileh]);
|
||||
DrawGroundSprite(_clear_land_sprites_2[GB(ti->map5, 0, 2)] + _tileh_to_sprite[ti->tileh]);
|
||||
break;
|
||||
|
||||
case 5:
|
||||
DrawGroundSprite( _clear_land_sprites_3[ti->map5&3] + _tileh_to_sprite[ti->tileh]);
|
||||
DrawGroundSprite(_clear_land_sprites_3[GB(ti->map5, 0, 2)] + _tileh_to_sprite[ti->tileh]);
|
||||
break;
|
||||
}
|
||||
|
||||
DrawClearLandFence(ti, _map3_hi[ti->tile] >> 2);
|
||||
DrawClearLandFence(ti);
|
||||
}
|
||||
|
||||
static uint GetSlopeZ_Clear(TileInfo *ti)
|
||||
static uint GetSlopeZ_Clear(const TileInfo* ti)
|
||||
{
|
||||
return GetPartialZ(ti->x & 0xF, ti->y & 0xF, ti->tileh) + ti->z;
|
||||
}
|
||||
|
||||
static uint GetSlopeTileh_Clear(TileInfo *ti)
|
||||
static uint GetSlopeTileh_Clear(const TileInfo *ti)
|
||||
{
|
||||
return ti->tileh;
|
||||
}
|
||||
|
||||
static void GetAcceptedCargo_Clear(uint tile, AcceptedCargo ac)
|
||||
static void GetAcceptedCargo_Clear(TileIndex tile, AcceptedCargo ac)
|
||||
{
|
||||
/* unused */
|
||||
}
|
||||
|
||||
static void AnimateTile_Clear(uint tile)
|
||||
static void AnimateTile_Clear(TileIndex tile)
|
||||
{
|
||||
/* unused */
|
||||
}
|
||||
|
||||
void TileLoopClearHelper(TileIndex tile)
|
||||
{
|
||||
byte img_1;
|
||||
byte img_2;
|
||||
static const byte img_by_map5[] = { 0, 0, 0, 2, 1, 1, 0, 0 };
|
||||
byte self;
|
||||
byte neighbour;
|
||||
TileIndex dirty = INVALID_TILE;
|
||||
|
||||
switch (GetTileType(tile)) {
|
||||
case MP_CLEAR:
|
||||
img_1 = img_by_map5[(_map5[tile] & 0x1C) >> 2];
|
||||
break;
|
||||
|
||||
case MP_TREES:
|
||||
if ((_map2[tile] & 0x30) == 0x20)
|
||||
img_1 = 1;
|
||||
else
|
||||
img_1 = 0;
|
||||
self = (GB(_m[tile].m5, 0, 5) == 15);
|
||||
break;
|
||||
|
||||
default:
|
||||
img_1 = 0;
|
||||
self = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
switch (GetTileType(TILE_ADDXY(tile, 1, 0))) {
|
||||
case MP_CLEAR:
|
||||
img_2 = img_by_map5[(_map5[TILE_ADDXY(tile, 1, 0)] & 0x1C) >> 2];
|
||||
break;
|
||||
|
||||
case MP_TREES:
|
||||
if ((_map2[TILE_ADDXY(tile, 1, 0)] & 0x30) == 0x20)
|
||||
img_2 = 1;
|
||||
else
|
||||
img_2 = 0;
|
||||
neighbour = (GB(_m[TILE_ADDXY(tile, 1, 0)].m5, 0, 5) == 15);
|
||||
break;
|
||||
|
||||
default:
|
||||
img_2 = 0;
|
||||
neighbour = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
if ((_map3_hi[tile] & 0xE0) == 0) {
|
||||
if ((img_1 & 2) != (img_2 & 2)) {
|
||||
_map3_hi[tile] |= 3 << 5;
|
||||
if (GB(_m[tile].m4, 5, 3) == 0) {
|
||||
if (self != neighbour) {
|
||||
SB(_m[tile].m4, 5, 3, 3);
|
||||
dirty = tile;
|
||||
}
|
||||
} else {
|
||||
if (img_1 == 1 && img_2 == 1) {
|
||||
_map3_hi[tile] &= ~(3 << 5);
|
||||
if (self == 0 && neighbour == 0) {
|
||||
SB(_m[tile].m4, 5, 3, 0);
|
||||
dirty = tile;
|
||||
}
|
||||
}
|
||||
|
||||
switch (GetTileType(TILE_ADDXY(tile, 0, 1))) {
|
||||
case MP_CLEAR:
|
||||
img_2 = img_by_map5[(_map5[TILE_ADDXY(tile, 0, 1)] & 0x1C) >> 2];
|
||||
break;
|
||||
|
||||
case MP_TREES:
|
||||
if ((_map2[TILE_ADDXY(tile, 0, 1)] & 0x30) == 0x20)
|
||||
img_2 = 1;
|
||||
else
|
||||
img_2 = 0;
|
||||
neighbour = (GB(_m[TILE_ADDXY(tile, 0, 1)].m5, 0, 5) == 15);
|
||||
break;
|
||||
|
||||
default:
|
||||
img_2 = 0;
|
||||
neighbour = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
if ((_map3_hi[tile] & 0x1C) == 0) {
|
||||
if ((img_1 & 2) != (img_2 & 2)) {
|
||||
_map3_hi[tile] |= 3 << 2;
|
||||
if (GB(_m[tile].m4, 2, 3) == 0) {
|
||||
if (self != neighbour) {
|
||||
SB(_m[tile].m4, 2, 3, 3);
|
||||
dirty = tile;
|
||||
}
|
||||
} else {
|
||||
if (img_1 == 1 && img_2 == 1) {
|
||||
_map3_hi[tile] &= ~(3 << 2);
|
||||
if (self == 0 && neighbour == 0) {
|
||||
SB(_m[tile].m4, 2, 3, 0);
|
||||
dirty = tile;
|
||||
}
|
||||
}
|
||||
|
||||
if (dirty != INVALID_TILE)
|
||||
MarkTileDirtyByTile(dirty);
|
||||
if (dirty != INVALID_TILE) MarkTileDirtyByTile(dirty);
|
||||
}
|
||||
|
||||
|
||||
/* convert into snowy tiles */
|
||||
static void TileLoopClearAlps(uint tile)
|
||||
static void TileLoopClearAlps(TileIndex tile)
|
||||
{
|
||||
int k;
|
||||
byte m5,tmp;
|
||||
@@ -645,8 +638,8 @@ static void TileLoopClearAlps(uint tile)
|
||||
/* distance from snow line, in steps of 8 */
|
||||
k = GetTileZ(tile) - _opt.snow_line;
|
||||
|
||||
m5 = _map5[tile] & 0x1C;
|
||||
tmp = _map5[tile] & 3;
|
||||
m5 = _m[tile].m5 & 0x1C;
|
||||
tmp = _m[tile].m5 & 3;
|
||||
|
||||
if (k < -8) {
|
||||
/* snow_m2_down */
|
||||
@@ -694,30 +687,29 @@ static void TileLoopClearAlps(uint tile)
|
||||
return;
|
||||
}
|
||||
|
||||
_map5[tile] = m5;
|
||||
_m[tile].m5 = m5;
|
||||
MarkTileDirtyByTile(tile);
|
||||
}
|
||||
|
||||
static void TileLoopClearDesert(uint tile)
|
||||
static void TileLoopClearDesert(TileIndex tile)
|
||||
{
|
||||
if ( (_map5[tile] & 0x1C) == 0x14)
|
||||
return;
|
||||
if ((_m[tile].m5 & 0x1C) == 0x14) return;
|
||||
|
||||
if (GetMapExtraBits(tile) == 1) {
|
||||
_map5[tile] = 0x17;
|
||||
_m[tile].m5 = 0x17;
|
||||
} else {
|
||||
if (GetMapExtraBits(tile+TILE_XY(1,0)) != 1 &&
|
||||
GetMapExtraBits(tile+TILE_XY(-1,0)) != 1 &&
|
||||
GetMapExtraBits(tile+TILE_XY(0,1)) != 1 &&
|
||||
GetMapExtraBits(tile+TILE_XY(0,-1)) != 1)
|
||||
return;
|
||||
_map5[tile] = 0x15;
|
||||
if (GetMapExtraBits(tile + TileDiffXY( 1, 0)) != 1 &&
|
||||
GetMapExtraBits(tile + TileDiffXY(-1, 0)) != 1 &&
|
||||
GetMapExtraBits(tile + TileDiffXY( 0, 1)) != 1 &&
|
||||
GetMapExtraBits(tile + TileDiffXY( 0, -1)) != 1)
|
||||
return;
|
||||
_m[tile].m5 = 0x15;
|
||||
}
|
||||
|
||||
MarkTileDirtyByTile(tile);
|
||||
}
|
||||
|
||||
static void TileLoop_Clear(uint tile)
|
||||
static void TileLoop_Clear(TileIndex tile)
|
||||
{
|
||||
byte m5,m3;
|
||||
|
||||
@@ -729,24 +721,22 @@ static void TileLoop_Clear(uint tile)
|
||||
TileLoopClearAlps(tile);
|
||||
}
|
||||
|
||||
m5 = _map5[tile];
|
||||
if ( (m5 & 0x1C) == 0x10 || (m5 & 0x1C) == 0x14)
|
||||
return;
|
||||
m5 = _m[tile].m5;
|
||||
if ((m5 & 0x1C) == 0x10 || (m5 & 0x1C) == 0x14) return;
|
||||
|
||||
if ( (m5 & 0x1C) != 0xC) {
|
||||
if ( (m5 & 3) == 3)
|
||||
return;
|
||||
if ((m5 & 0x1C) != 0xC) {
|
||||
if ((m5 & 3) == 3) return;
|
||||
|
||||
if (_game_mode != GM_EDITOR) {
|
||||
m5 += 0x20;
|
||||
if (m5 >= 0x20) {
|
||||
// Didn't overflow
|
||||
_map5[tile] = m5;
|
||||
_m[tile].m5 = m5;
|
||||
return;
|
||||
}
|
||||
/* did overflow, so continue */
|
||||
} else {
|
||||
m5 = ((byte)Random() > 21) ? (2) : (6);
|
||||
m5 = (GB(Random(), 0, 8) > 21) ? 2 : 6;
|
||||
}
|
||||
m5++;
|
||||
} else if (_game_mode != GM_EDITOR) {
|
||||
@@ -754,47 +744,47 @@ static void TileLoop_Clear(uint tile)
|
||||
m5 += 0x20;
|
||||
if (m5 >= 0x20) {
|
||||
// Didn't overflow
|
||||
_map5[tile] = m5;
|
||||
_m[tile].m5 = m5;
|
||||
return;
|
||||
}
|
||||
/* overflowed */
|
||||
m3 = _map3_lo[tile] + 1;
|
||||
m3 = _m[tile].m3 + 1;
|
||||
assert( (m3 & 0xF) != 0);
|
||||
if ( (m3 & 0xF) >= 9) /* NOTE: will not work properly if m3&0xF == 0xF */
|
||||
m3 &= ~0xF;
|
||||
_map3_lo[tile] = m3;
|
||||
_m[tile].m3 = m3;
|
||||
}
|
||||
|
||||
_map5[tile] = m5;
|
||||
_m[tile].m5 = m5;
|
||||
MarkTileDirtyByTile(tile);
|
||||
}
|
||||
|
||||
void GenerateClearTile(void)
|
||||
{
|
||||
int i,j;
|
||||
uint tile,tile_new;
|
||||
uint32 r;
|
||||
uint i;
|
||||
TileIndex tile;
|
||||
|
||||
/* add hills */
|
||||
i = ScaleByMapSize((Random() & 0x3FF) + 0x400);
|
||||
i = ScaleByMapSize(GB(Random(), 0, 10) + 0x400);
|
||||
do {
|
||||
tile = TILE_MASK(Random());
|
||||
if (IsTileType(tile, MP_CLEAR))
|
||||
_map5[tile] = (byte)((_map5[tile] & ~(3<<2)) | (1<<2));
|
||||
tile = RandomTile();
|
||||
if (IsTileType(tile, MP_CLEAR)) SB(_m[tile].m5, 2, 2, 1);
|
||||
} while (--i);
|
||||
|
||||
/* add grey squares */
|
||||
i = ScaleByMapSize((Random() & 0x7F) + 0x80);
|
||||
i = ScaleByMapSize(GB(Random(), 0, 7) + 0x80);
|
||||
do {
|
||||
r = Random();
|
||||
tile = TILE_MASK(r);
|
||||
uint32 r = Random();
|
||||
tile = RandomTileSeed(r);
|
||||
if (IsTileType(tile, MP_CLEAR)) {
|
||||
j = ((r >> 16) & 0xF) + 5;
|
||||
uint j = GB(r, 16, 4) + 5;
|
||||
for(;;) {
|
||||
_map5[tile] = (byte)((_map5[tile] & ~(3<<2)) | (2<<2));
|
||||
TileIndex tile_new;
|
||||
|
||||
SB(_m[tile].m5, 2, 2, 2);
|
||||
do {
|
||||
if (--j == 0) goto get_out;
|
||||
tile_new = tile + TileOffsByDir(Random() & 3);
|
||||
tile_new = tile + TileOffsByDir(GB(Random(), 0, 2));
|
||||
} while (!IsTileType(tile_new, MP_CLEAR));
|
||||
tile = tile_new;
|
||||
}
|
||||
@@ -803,17 +793,17 @@ get_out:;
|
||||
} while (--i);
|
||||
}
|
||||
|
||||
static void ClickTile_Clear(uint tile)
|
||||
static void ClickTile_Clear(TileIndex tile)
|
||||
{
|
||||
/* not used */
|
||||
}
|
||||
|
||||
static uint32 GetTileTrackStatus_Clear(uint tile, TransportType mode)
|
||||
static uint32 GetTileTrackStatus_Clear(TileIndex tile, TransportType mode)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const StringID _clear_land_str[4+8-1] = {
|
||||
static const StringID _clear_land_str[] = {
|
||||
STR_080B_ROUGH_LAND,
|
||||
STR_080A_ROCKS,
|
||||
STR_080E_FIELDS,
|
||||
@@ -827,16 +817,15 @@ static const StringID _clear_land_str[4+8-1] = {
|
||||
STR_080D_GRASS,
|
||||
};
|
||||
|
||||
static void GetTileDesc_Clear(uint tile, TileDesc *td)
|
||||
static void GetTileDesc_Clear(TileIndex tile, TileDesc *td)
|
||||
{
|
||||
int i = (_map5[tile]>>2) & 7;
|
||||
if (i == 0)
|
||||
i = (_map5[tile] & 3) + 8;
|
||||
uint i = GB(_m[tile].m5, 2, 3);
|
||||
if (i == 0) i = GB(_m[tile].m5, 0, 2) + 8;
|
||||
td->str = _clear_land_str[i - 1];
|
||||
td->owner = _map_owner[tile];
|
||||
td->owner = GetTileOwner(tile);
|
||||
}
|
||||
|
||||
static void ChangeTileOwner_Clear(uint tile, byte old_player, byte new_player)
|
||||
static void ChangeTileOwner_Clear(TileIndex tile, PlayerID old_player, PlayerID new_player)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1,11 +1,15 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "gui.h"
|
||||
#include "command.h"
|
||||
#include "player.h"
|
||||
#include "network.h"
|
||||
#include "variables.h"
|
||||
|
||||
const char* _cmd_text = NULL;
|
||||
|
||||
@@ -73,7 +77,7 @@ DEF_COMMAND(CmdModifyOrder);
|
||||
DEF_COMMAND(CmdSkipOrder);
|
||||
DEF_COMMAND(CmdDeleteOrder);
|
||||
DEF_COMMAND(CmdInsertOrder);
|
||||
DEF_COMMAND(CmdChangeTrainServiceInt);
|
||||
DEF_COMMAND(CmdChangeServiceInt);
|
||||
DEF_COMMAND(CmdRestoreOrderIndex);
|
||||
|
||||
DEF_COMMAND(CmdBuildIndustry);
|
||||
@@ -99,7 +103,6 @@ DEF_COMMAND(CmdSellAircraft);
|
||||
DEF_COMMAND(CmdStartStopAircraft);
|
||||
DEF_COMMAND(CmdBuildAircraft);
|
||||
DEF_COMMAND(CmdSendAircraftToHangar);
|
||||
DEF_COMMAND(CmdChangeAircraftServiceInt);
|
||||
DEF_COMMAND(CmdRefitAircraft);
|
||||
|
||||
DEF_COMMAND(CmdPlaceSign);
|
||||
@@ -110,7 +113,6 @@ DEF_COMMAND(CmdStartStopRoadVeh);
|
||||
DEF_COMMAND(CmdSellRoadVeh);
|
||||
DEF_COMMAND(CmdSendRoadVehToDepot);
|
||||
DEF_COMMAND(CmdTurnRoadVeh);
|
||||
DEF_COMMAND(CmdChangeRoadVehServiceInt);
|
||||
|
||||
DEF_COMMAND(CmdPause);
|
||||
|
||||
@@ -132,7 +134,6 @@ DEF_COMMAND(CmdStartStopShip);
|
||||
DEF_COMMAND(CmdSellShip);
|
||||
DEF_COMMAND(CmdBuildShip);
|
||||
DEF_COMMAND(CmdSendShipToDepot);
|
||||
DEF_COMMAND(CmdChangeShipServiceInt);
|
||||
DEF_COMMAND(CmdRefitShip);
|
||||
|
||||
DEF_COMMAND(CmdCloneOrder);
|
||||
@@ -155,6 +156,9 @@ DEF_COMMAND(CmdRemoveSignalTrack);
|
||||
|
||||
DEF_COMMAND(CmdReplaceVehicle);
|
||||
|
||||
DEF_COMMAND(CmdCloneVehicle);
|
||||
|
||||
|
||||
/* The master command table */
|
||||
static const Command _command_proc_table[] = {
|
||||
{CmdBuildRailroadTrack, 0}, /* 0 */
|
||||
@@ -205,7 +209,7 @@ static const Command _command_proc_table[] = {
|
||||
{CmdDeleteOrder, 0}, /* 44 */
|
||||
{CmdInsertOrder, 0}, /* 45 */
|
||||
|
||||
{CmdChangeTrainServiceInt, 0}, /* 46 */
|
||||
{CmdChangeServiceInt, 0}, /* 46 */
|
||||
|
||||
{CmdBuildIndustry, 0}, /* 47 */
|
||||
{CmdBuildCompanyHQ, 0}, /* 48 */
|
||||
@@ -230,7 +234,7 @@ static const Command _command_proc_table[] = {
|
||||
|
||||
{CmdBuildAircraft, 0}, /* 61 */
|
||||
{CmdSendAircraftToHangar, 0}, /* 62 */
|
||||
{CmdChangeAircraftServiceInt, 0}, /* 63 */
|
||||
{NULL, 0}, /* 63 */
|
||||
{CmdRefitAircraft, 0}, /* 64 */
|
||||
|
||||
{CmdPlaceSign, 0}, /* 65 */
|
||||
@@ -241,7 +245,7 @@ static const Command _command_proc_table[] = {
|
||||
{CmdSellRoadVeh, 0}, /* 69 */
|
||||
{CmdSendRoadVehToDepot, 0}, /* 70 */
|
||||
{CmdTurnRoadVeh, 0}, /* 71 */
|
||||
{CmdChangeRoadVehServiceInt, 0}, /* 72 */
|
||||
{NULL, 0}, /* 72 */
|
||||
|
||||
{CmdPause, CMD_SERVER}, /* 73 */
|
||||
|
||||
@@ -264,7 +268,7 @@ static const Command _command_proc_table[] = {
|
||||
{CmdSellShip, 0}, /* 87 */
|
||||
{CmdBuildShip, 0}, /* 88 */
|
||||
{CmdSendShipToDepot, 0}, /* 89 */
|
||||
{CmdChangeShipServiceInt, 0}, /* 90 */
|
||||
{NULL, 0}, /* 90 */
|
||||
{CmdRefitShip, 0}, /* 91 */
|
||||
|
||||
{NULL, 0}, /* 92 */
|
||||
@@ -296,17 +300,17 @@ static const Command _command_proc_table[] = {
|
||||
{CmdGiveMoney, 0}, /* 113 */
|
||||
{CmdChangePatchSetting, CMD_SERVER}, /* 114 */
|
||||
{CmdReplaceVehicle, 0}, /* 115 */
|
||||
{CmdCloneVehicle, 0}, /* 116 */
|
||||
};
|
||||
|
||||
/* This function range-checks a cmd, and checks if the cmd is not NULL */
|
||||
bool IsValidCommand(uint cmd)
|
||||
{
|
||||
cmd = cmd & 0xFF;
|
||||
cmd &= 0xFF;
|
||||
|
||||
if (cmd >= lengthof(_command_proc_table) || _command_proc_table[cmd].proc == NULL)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
return
|
||||
cmd < lengthof(_command_proc_table) &&
|
||||
_command_proc_table[cmd].proc != NULL;
|
||||
}
|
||||
|
||||
byte GetCommandFlags(uint cmd) {return _command_proc_table[cmd & 0xFF].flags;}
|
||||
@@ -317,7 +321,7 @@ int32 DoCommandByTile(TileIndex tile, uint32 p1, uint32 p2, uint32 flags, uint p
|
||||
}
|
||||
|
||||
|
||||
//extern void _stdcall Sleep(int s);
|
||||
static int _docommand_recursive;
|
||||
|
||||
int32 DoCommand(int x, int y, uint32 p1, uint32 p2, uint32 flags, uint procc)
|
||||
{
|
||||
@@ -325,20 +329,14 @@ int32 DoCommand(int x, int y, uint32 p1, uint32 p2, uint32 flags, uint procc)
|
||||
CommandProc *proc;
|
||||
|
||||
/* Do not even think about executing out-of-bounds tile-commands */
|
||||
if (TILE_FROM_XY(x,y) > MapSize()) {
|
||||
if (TileVirtXY(x, y) >= MapSize()) {
|
||||
_cmd_text = NULL;
|
||||
return CMD_ERROR;
|
||||
}
|
||||
|
||||
proc = _command_proc_table[procc].proc;
|
||||
|
||||
if (_docommand_recursive == 0) {
|
||||
_error_message = INVALID_STRING_ID;
|
||||
// update last build coord of player
|
||||
if ( (x|y) != 0 && _current_player < MAX_PLAYERS) {
|
||||
DEREF_PLAYER(_current_player)->last_build_coordinate = TILE_FROM_XY(x,y);
|
||||
}
|
||||
}
|
||||
if (_docommand_recursive == 0) _error_message = INVALID_STRING_ID;
|
||||
|
||||
_docommand_recursive++;
|
||||
|
||||
@@ -376,6 +374,10 @@ error:
|
||||
// if toplevel, subtract the money.
|
||||
if (--_docommand_recursive == 0) {
|
||||
SubtractMoneyFromPlayer(res);
|
||||
// XXX - Old AI hack which doesn't use DoCommandDP; update last build coord of player
|
||||
if ( (x|y) != 0 && _current_player < MAX_PLAYERS) {
|
||||
GetPlayer(_current_player)->last_build_coordinate = TileVirtXY(x, y);
|
||||
}
|
||||
}
|
||||
|
||||
_cmd_text = NULL;
|
||||
@@ -386,7 +388,7 @@ int32 GetAvailableMoneyForCommand(void)
|
||||
{
|
||||
PlayerID pid = _current_player;
|
||||
if (pid >= MAX_PLAYERS) return 0x7FFFFFFF; // max int
|
||||
return DEREF_PLAYER(pid)->player_money;
|
||||
return GetPlayer(pid)->player_money;
|
||||
}
|
||||
|
||||
// toplevel network safe docommand function for the current player. must not be called recursively.
|
||||
@@ -402,7 +404,7 @@ bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback,
|
||||
int y = TileY(tile) * 16;
|
||||
|
||||
/* Do not even think about executing out-of-bounds tile-commands */
|
||||
if (tile > MapSize()) {
|
||||
if (tile >= MapSize()) {
|
||||
_cmd_text = NULL;
|
||||
return false;
|
||||
}
|
||||
@@ -428,6 +430,10 @@ bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback,
|
||||
// get pointer to command handler
|
||||
assert((cmd & 0xFF) < lengthof(_command_proc_table));
|
||||
proc = _command_proc_table[cmd & 0xFF].proc;
|
||||
if (proc == NULL) {
|
||||
_cmd_text = NULL;
|
||||
return false;
|
||||
}
|
||||
|
||||
// Some commands have a different output in dryrun than the realrun
|
||||
// e.g.: if you demolish a whole town, the dryrun would say okay.
|
||||
@@ -448,7 +454,7 @@ bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback,
|
||||
_docommand_recursive = 1;
|
||||
|
||||
// cost estimation only?
|
||||
if (_shift_pressed && _current_player == _local_player && !(cmd & (CMD_NETWORK_COMMAND | CMD_SHOW_NO_ERROR))) {
|
||||
if (_shift_pressed && IsLocalPlayer() && !(cmd & (CMD_NETWORK_COMMAND | CMD_SHOW_NO_ERROR))) {
|
||||
// estimate the cost.
|
||||
res = proc(x, y, flags, p1, p2);
|
||||
if (CmdFailed(res)) {
|
||||
@@ -493,7 +499,7 @@ bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback,
|
||||
#endif /* ENABLE_NETWORK */
|
||||
|
||||
// update last build coordinate of player.
|
||||
if ( tile != 0 && _current_player < MAX_PLAYERS) DEREF_PLAYER(_current_player)->last_build_coordinate = tile;
|
||||
if ( tile != 0 && _current_player < MAX_PLAYERS) GetPlayer(_current_player)->last_build_coordinate = tile;
|
||||
|
||||
/* Actually try and execute the command. If no cost-type is given
|
||||
* use the construction one */
|
||||
@@ -513,7 +519,7 @@ bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback,
|
||||
|
||||
SubtractMoneyFromPlayer(res2);
|
||||
|
||||
if (_current_player == _local_player && _game_mode != GM_EDITOR) {
|
||||
if (IsLocalPlayer() && _game_mode != GM_EDITOR) {
|
||||
if (res2 != 0)
|
||||
ShowCostOrIncomeAnimation(x, y, GetSlopeZ(x, y), res2);
|
||||
if (_additional_cash_required) {
|
||||
@@ -531,7 +537,7 @@ bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback,
|
||||
|
||||
show_error:
|
||||
// show error message if the command fails?
|
||||
if (_current_player == _local_player && _error_message_2 != 0)
|
||||
if (IsLocalPlayer() && _error_message_2 != 0)
|
||||
ShowErrorMessage(_error_message, _error_message_2, x,y);
|
||||
|
||||
callb_err:
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef COMMAND_H
|
||||
#define COMMAND_H
|
||||
|
||||
@@ -56,7 +58,7 @@ enum {
|
||||
CMD_DELETE_ORDER = 44,
|
||||
CMD_INSERT_ORDER = 45,
|
||||
|
||||
CMD_CHANGE_TRAIN_SERVICE_INT = 46,
|
||||
CMD_CHANGE_SERVICE_INT = 46,
|
||||
|
||||
CMD_BUILD_INDUSTRY = 47,
|
||||
|
||||
@@ -79,7 +81,6 @@ enum {
|
||||
CMD_START_STOP_AIRCRAFT = 60,
|
||||
CMD_BUILD_AIRCRAFT = 61,
|
||||
CMD_SEND_AIRCRAFT_TO_HANGAR = 62,
|
||||
CMD_CHANGE_AIRCRAFT_SERVICE_INT = 63,
|
||||
CMD_REFIT_AIRCRAFT = 64,
|
||||
|
||||
CMD_PLACE_SIGN = 65,
|
||||
@@ -90,7 +91,6 @@ enum {
|
||||
CMD_SELL_ROAD_VEH = 69,
|
||||
CMD_SEND_ROADVEH_TO_DEPOT = 70,
|
||||
CMD_TURN_ROADVEH = 71,
|
||||
CMD_CHANGE_ROADVEH_SERVICE_INT = 72,
|
||||
|
||||
CMD_PAUSE = 73,
|
||||
|
||||
@@ -111,7 +111,6 @@ enum {
|
||||
CMD_SELL_SHIP = 87,
|
||||
CMD_BUILD_SHIP = 88,
|
||||
CMD_SEND_SHIP_TO_DEPOT = 89,
|
||||
CMD_CHANGE_SHIP_SERVICE_INT = 90,
|
||||
CMD_REFIT_SHIP = 91,
|
||||
|
||||
CMD_CLONE_ORDER = 99,
|
||||
@@ -134,6 +133,9 @@ enum {
|
||||
CMD_CHANGE_PATCH_SETTING = 114,
|
||||
|
||||
CMD_REPLACE_VEHICLE = 115,
|
||||
|
||||
CMD_CLONE_VEHICLE = 116,
|
||||
|
||||
};
|
||||
|
||||
enum {
|
||||
|
||||
@@ -1,13 +1,15 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "window.h"
|
||||
#include "gui.h"
|
||||
#include "gfx.h"
|
||||
#include "player.h"
|
||||
#include "variables.h"
|
||||
#include "string.h"
|
||||
#include "hal.h"
|
||||
#include <stdarg.h>
|
||||
#include <string.h>
|
||||
#include "console.h"
|
||||
@@ -56,6 +58,10 @@ static void IConsoleClearCommand(void)
|
||||
|
||||
static inline void IConsoleResetHistoryPos(void) {_iconsole_historypos = ICON_HISTORY_SIZE - 1;}
|
||||
|
||||
|
||||
static void IConsoleHistoryAdd(const char* cmd);
|
||||
static void IConsoleHistoryNavigate(int direction);
|
||||
|
||||
// ** console window ** //
|
||||
static void IConsoleWndProc(Window* w, WindowEvent* e)
|
||||
{
|
||||
@@ -151,9 +157,13 @@ static void IConsoleWndProc(Window* w, WindowEvent* e)
|
||||
SetWindowDirty(w);
|
||||
}
|
||||
break;
|
||||
case (WKC_CTRL | 'L'):
|
||||
case (WKC_CTRL | 'L'):
|
||||
IConsoleCmdExec("clear");
|
||||
break;
|
||||
case (WKC_CTRL | 'U'):
|
||||
DeleteTextBufferAll(&_iconsole_cmdline);
|
||||
SetWindowDirty(w);
|
||||
break;
|
||||
case WKC_BACKSPACE: case WKC_DELETE:
|
||||
if (DeleteTextBufferChar(&_iconsole_cmdline, e->keypress.keycode)) {
|
||||
IConsoleResetHistoryPos();
|
||||
@@ -316,7 +326,7 @@ void IConsoleOpen(void) {if (_iconsole_mode == ICONSOLE_CLOSED) IConsoleSwitch(
|
||||
* scroll, etc. Put it to the beginning as it is the latest text
|
||||
* @param cmd Text to be entered into the 'history'
|
||||
*/
|
||||
void IConsoleHistoryAdd(const char *cmd)
|
||||
static void IConsoleHistoryAdd(const char* cmd)
|
||||
{
|
||||
free(_iconsole_history[ICON_HISTORY_SIZE - 1]);
|
||||
|
||||
@@ -329,7 +339,7 @@ void IConsoleHistoryAdd(const char *cmd)
|
||||
* Navigate Up/Down in the history of typed commands
|
||||
* @param direction Go further back in history (+1), go to recently typed commands (-1)
|
||||
*/
|
||||
void IConsoleHistoryNavigate(signed char direction)
|
||||
static void IConsoleHistoryNavigate(int direction)
|
||||
{
|
||||
int i = _iconsole_historypos + direction;
|
||||
|
||||
@@ -469,7 +479,7 @@ bool GetArgumentInteger(uint32 *value, const char *arg)
|
||||
}
|
||||
|
||||
*value = strtoul(arg, &endptr, 0);
|
||||
return (arg == endptr) ? false : true;
|
||||
return arg != endptr;
|
||||
}
|
||||
|
||||
// * ************************* * //
|
||||
@@ -495,7 +505,7 @@ static void IConsoleHookAdd(IConsoleHooks *hooks, IConsoleHookTypes type, IConso
|
||||
case ICONSOLE_HOOK_POST_ACTION:
|
||||
hooks->post = proc;
|
||||
break;
|
||||
default: NOT_REACHED();
|
||||
default: NOT_REACHED();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -522,7 +532,7 @@ static bool IConsoleHookHandle(const IConsoleHooks *hooks, IConsoleHookTypes typ
|
||||
case ICONSOLE_HOOK_POST_ACTION:
|
||||
proc = hooks->post;
|
||||
break;
|
||||
default: NOT_REACHED();
|
||||
default: NOT_REACHED();
|
||||
}
|
||||
|
||||
return (proc == NULL) ? true : proc();
|
||||
@@ -681,7 +691,7 @@ static inline int IConsoleCopyInParams(char *dst, const char *src, uint bufpos)
|
||||
* @param tokencount the number of parameters passed
|
||||
* @param *tokens are the parameters given to the original command (0 is the first param)
|
||||
*/
|
||||
void IConsoleAliasExec(const IConsoleAlias *alias, byte tokencount, char *tokens[ICON_TOKEN_COUNT])
|
||||
static void IConsoleAliasExec(const IConsoleAlias* alias, byte tokencount, char* tokens[ICON_TOKEN_COUNT])
|
||||
{
|
||||
const char *cmdptr;
|
||||
char *aliases[ICON_MAX_ALIAS_LINES], aliasstream[ICON_MAX_STREAMSIZE];
|
||||
@@ -691,6 +701,9 @@ void IConsoleAliasExec(const IConsoleAlias *alias, byte tokencount, char *tokens
|
||||
memset(&aliases, 0, sizeof(aliases));
|
||||
memset(&aliasstream, 0, sizeof(aliasstream));
|
||||
|
||||
if (_stdlib_con_developer)
|
||||
IConsolePrintF(_icolour_dbg, "condbg: requested command is an alias; parsing...");
|
||||
|
||||
aliases[0] = aliasstream;
|
||||
for (cmdptr = alias->cmdline, a_index = 0, astream_i = 0; *cmdptr != '\0'; cmdptr++) {
|
||||
if (a_index >= lengthof(aliases) || astream_i >= lengthof(aliasstream)) break;
|
||||
@@ -820,7 +833,7 @@ static void IConsoleVarSetValue(const IConsoleVar *var, uint32 value)
|
||||
*(byte*)var->addr = (byte)value;
|
||||
break;
|
||||
case ICONSOLE_VAR_UINT16:
|
||||
*(uint16*)var->addr = (byte)value;
|
||||
*(uint16*)var->addr = (uint16)value;
|
||||
break;
|
||||
case ICONSOLE_VAR_INT16:
|
||||
*(int16*)var->addr = (int16)value;
|
||||
@@ -918,6 +931,7 @@ static char *IConsoleVarGetStringValue(const IConsoleVar *var)
|
||||
break;
|
||||
case ICONSOLE_VAR_STRING:
|
||||
value = (char*)var->addr;
|
||||
break;
|
||||
default: NOT_REACHED();
|
||||
}
|
||||
|
||||
@@ -964,6 +978,9 @@ void IConsoleVarExec(const IConsoleVar *var, byte tokencount, char *token[ICON_T
|
||||
byte t_index = tokencount;
|
||||
uint32 value;
|
||||
|
||||
if (_stdlib_con_developer)
|
||||
IConsolePrintF(_icolour_dbg, "condbg: requested command is a variable");
|
||||
|
||||
if (tokencount == 0) { /* Just print out value */
|
||||
IConsoleVarPrintGetValue(var);
|
||||
return;
|
||||
@@ -976,7 +993,6 @@ void IConsoleVarExec(const IConsoleVar *var, byte tokencount, char *token[ICON_T
|
||||
/* Some variables need really special handling, handle it in their callback procedure */
|
||||
if (var->proc != NULL) {
|
||||
var->proc(tokencount, &token[t_index - tokencount]); // set the new value
|
||||
var->proc(0, NULL); // print out new value
|
||||
return;
|
||||
}
|
||||
/* Strings need special processing. No need to convert the argument to
|
||||
@@ -1035,6 +1051,8 @@ void IConsoleCmdExec(const char *cmdstr)
|
||||
bool longtoken = false;
|
||||
bool foundtoken = false;
|
||||
|
||||
if (cmdstr[0] == '#') return; // comments
|
||||
|
||||
for (cmdptr = cmdstr; *cmdptr != '\0'; cmdptr++) {
|
||||
if (!IsValidAsciiChar(*cmdptr)) {
|
||||
IConsoleError("command contains malformed characters, aborting");
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef CONSOLE_H
|
||||
#define CONSOLE_H
|
||||
|
||||
@@ -121,10 +123,6 @@ void IConsoleSwitch(void);
|
||||
void IConsoleClose(void);
|
||||
void IConsoleOpen(void);
|
||||
|
||||
// ** console cmd buffer ** //
|
||||
void IConsoleHistoryAdd(const char *cmd);
|
||||
void IConsoleHistoryNavigate(signed char direction);
|
||||
|
||||
// ** console output ** //
|
||||
void IConsolePrint(uint16 color_code, const char *string);
|
||||
void CDECL IConsolePrintF(uint16 color_code, const char *s, ...);
|
||||
@@ -148,7 +146,6 @@ void IConsoleVarPrintSetValue(const IConsoleVar *var);
|
||||
// *** Parser *** //
|
||||
void IConsoleCmdExec(const char *cmdstr);
|
||||
void IConsoleVarExec(const IConsoleVar *var, byte tokencount, char *token[]);
|
||||
void IConsoleAliasExec(const IConsoleAlias *alias, byte tokencount, char *tokens[]);
|
||||
|
||||
// ** console std lib (register ingame commands/aliases/variables) ** //
|
||||
void IConsoleStdLibRegister(void);
|
||||
|
||||
+235
-114
@@ -1,9 +1,12 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "console.h"
|
||||
#include "debug.h"
|
||||
#include "engine.h"
|
||||
#include "functions.h"
|
||||
#include "saveload.h"
|
||||
#include "string.h"
|
||||
#include "variables.h"
|
||||
#include "network_data.h"
|
||||
@@ -13,6 +16,7 @@
|
||||
#include "command.h"
|
||||
#include "settings.h"
|
||||
#include "hal.h" /* for file list */
|
||||
#include "vehicle.h"
|
||||
|
||||
// ** scriptfile handling ** //
|
||||
static FILE *_script_file;
|
||||
@@ -87,6 +91,28 @@ static void IConsoleHelp(const char *str)
|
||||
IConsolePrintF(_icolour_warn, "- %s", str);
|
||||
}
|
||||
|
||||
DEF_CONSOLE_CMD(ConStopAllVehicles)
|
||||
{
|
||||
Vehicle* v;
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Stops all vehicles in the game. For debugging only! Use at your own risk... Usage: 'stopall'");
|
||||
return true;
|
||||
}
|
||||
|
||||
FOR_ALL_VEHICLES(v) {
|
||||
if (IsValidVehicle(v)) {
|
||||
/* Code ripped from CmdStartStopTrain. Can't call it, because of
|
||||
* ownership problems, so we'll duplicate some code, for now */
|
||||
if (v->type == VEH_Train)
|
||||
v->u.rail.days_since_order_progr = 0;
|
||||
v->vehstatus |= VS_STOPPED;
|
||||
InvalidateWindowWidget(WC_VEHICLE_VIEW, v->index, STATUS_BAR);
|
||||
InvalidateWindow(WC_VEHICLE_DEPOT, v->tile);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
DEF_CONSOLE_CMD(ConResetEngines)
|
||||
{
|
||||
if (argc == 0) {
|
||||
@@ -175,6 +201,7 @@ static const FiosItem* GetFiosItem(const char* file)
|
||||
|
||||
for (i = 0; i < _fios_num; i++) {
|
||||
if (strcmp(file, _fios_list[i].name) == 0) break;
|
||||
if (strcmp(file, _fios_list[i].title) == 0) break;
|
||||
}
|
||||
|
||||
if (i == _fios_num) { /* If no name matches, try to parse it as number */
|
||||
@@ -194,7 +221,7 @@ DEF_CONSOLE_CMD(ConLoad)
|
||||
const char *file;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Load a game by name or index. Usage: 'load <file \\ number>'");
|
||||
IConsoleHelp("Load a game by name or index. Usage: 'load <file | number>'");
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -204,11 +231,13 @@ DEF_CONSOLE_CMD(ConLoad)
|
||||
item = GetFiosItem(file);
|
||||
if (item != NULL) {
|
||||
switch (item->type) {
|
||||
case FIOS_TYPE_FILE: case FIOS_TYPE_OLDFILE:
|
||||
case FIOS_TYPE_FILE: case FIOS_TYPE_OLDFILE: {
|
||||
_switch_mode = SM_LOAD;
|
||||
SetFiosType(item->type);
|
||||
strcpy(_file_to_saveload.name, FiosBrowseTo(item));
|
||||
break;
|
||||
|
||||
ttd_strlcpy(_file_to_saveload.name, FiosBrowseTo(item), sizeof(_file_to_saveload.name));
|
||||
ttd_strlcpy(_file_to_saveload.title, item->title, sizeof(_file_to_saveload.title));
|
||||
} break;
|
||||
default: IConsolePrintF(_icolour_err, "%s: Not a savegame.", file);
|
||||
}
|
||||
} else
|
||||
@@ -218,13 +247,39 @@ DEF_CONSOLE_CMD(ConLoad)
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
DEF_CONSOLE_CMD(ConRemove)
|
||||
{
|
||||
const FiosItem* item;
|
||||
const char* file;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Remove a savegame by name or index. Usage: 'rm <file | number>'");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (argc != 2) return false;
|
||||
|
||||
file = argv[1];
|
||||
item = GetFiosItem(file);
|
||||
if (item != NULL) {
|
||||
if (!FiosDelete(item->name))
|
||||
IConsolePrintF(_icolour_err, "%s: Failed to delete file", file);
|
||||
} else
|
||||
IConsolePrintF(_icolour_err, "%s: No such file or directory.", file);
|
||||
|
||||
FiosFreeSavegameList();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/* List all the files in the current dir via console */
|
||||
DEF_CONSOLE_CMD(ConListFiles)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("List all loadable savegames and directories in the current dir via console. Usage: 'ls \\ dir'");
|
||||
IConsoleHelp("List all loadable savegames and directories in the current dir via console. Usage: 'ls | dir'");
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -232,7 +287,7 @@ DEF_CONSOLE_CMD(ConListFiles)
|
||||
|
||||
for (i = 0; i < _fios_num; i++) {
|
||||
const FiosItem *item = &_fios_list[i];
|
||||
IConsolePrintF(_icolour_def, "%d) %s", i, (item->title[0] != '\0') ? item->title : item->name);
|
||||
IConsolePrintF(_icolour_def, "%d) %s", i, item->title);
|
||||
}
|
||||
|
||||
FiosFreeSavegameList();
|
||||
@@ -246,7 +301,7 @@ DEF_CONSOLE_CMD(ConChangeDirectory)
|
||||
const char *file;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Change the dir via console. Usage: 'cd <directory \\ number>'");
|
||||
IConsoleHelp("Change the dir via console. Usage: 'cd <directory | number>'");
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -307,63 +362,80 @@ DEF_CONSOLE_CMD(ConClearBuffer)
|
||||
DEF_CONSOLE_CMD(ConBan)
|
||||
{
|
||||
NetworkClientInfo *ci;
|
||||
const char *banip = NULL;
|
||||
uint32 index;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Ban a player from a network game. Usage: 'ban <client-id>'");
|
||||
IConsoleHelp("Ban a player from a network game. Usage: 'ban <ip | client-id>'");
|
||||
IConsoleHelp("For client-id's, see the command 'clients'");
|
||||
IConsoleHelp("If the client is no longer online, you can still ban his/her IP");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (argc != 2) return false;
|
||||
|
||||
index = atoi(argv[1]);
|
||||
if (strchr(argv[1], '.') == NULL) { // banning with ID
|
||||
index = atoi(argv[1]);
|
||||
ci = NetworkFindClientInfoFromIndex(index);
|
||||
} else { // banning IP
|
||||
ci = NetworkFindClientInfoFromIP(argv[1]);
|
||||
if (ci == NULL) {
|
||||
banip = argv[1];
|
||||
index = (uint32)-1;
|
||||
} else {
|
||||
index = ci->client_index;
|
||||
}
|
||||
}
|
||||
|
||||
if (index == NETWORK_SERVER_INDEX) {
|
||||
IConsolePrint(_icolour_def, "Silly boy, you can not ban yourself!");
|
||||
return true;
|
||||
}
|
||||
if (index == 0) {
|
||||
IConsoleError("Invalid Client-ID");
|
||||
IConsoleError("Silly boy, you can not ban yourself!");
|
||||
return true;
|
||||
}
|
||||
|
||||
ci = NetworkFindClientInfoFromIndex(index);
|
||||
if (index == 0 || (ci == NULL && index != (uint32)-1)) {
|
||||
IConsoleError("Invalid client");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ci != NULL) {
|
||||
uint i;
|
||||
/* Add user to ban-list */
|
||||
for (i = 0; i < lengthof(_network_ban_list); i++) {
|
||||
if (_network_ban_list[i] == NULL || _network_ban_list[i][0] == '\0') {
|
||||
_network_ban_list[i] = strdup(inet_ntoa(*(struct in_addr *)&ci->client_ip));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
banip = inet_ntoa(*(struct in_addr *)&ci->client_ip);
|
||||
SEND_COMMAND(PACKET_SERVER_ERROR)(NetworkFindClientStateFromIndex(index), NETWORK_ERROR_KICKED);
|
||||
IConsolePrint(_icolour_def, "Client banned");
|
||||
} else
|
||||
IConsoleError("Client-ID not found");
|
||||
IConsolePrint(_icolour_def, "Client not online, banned IP");
|
||||
|
||||
/* Add user to ban-list */
|
||||
for (index = 0; index < lengthof(_network_ban_list); index++) {
|
||||
if (_network_ban_list[index] == NULL) {
|
||||
_network_ban_list[index] = strdup(banip);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
DEF_CONSOLE_CMD(ConUnBan)
|
||||
{
|
||||
uint i;
|
||||
uint i, index;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Unban a player from a network game. Usage: 'unban <ip>'");
|
||||
IConsoleHelp("Unban a player from a network game. Usage: 'unban <ip | client-id>'");
|
||||
IConsoleHelp("For a list of banned IP's, see the command 'banlist'");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (argc != 2) return false;
|
||||
|
||||
for (i = 0; i < lengthof(_network_ban_list); i++) {
|
||||
if (_network_ban_list[i] == NULL || _network_ban_list[i][0] == '\0')
|
||||
continue;
|
||||
index = (strchr(argv[1], '.') == NULL) ? atoi(argv[1]) : 0;
|
||||
index--;
|
||||
|
||||
if (strncmp(_network_ban_list[i], argv[1], strlen(_network_ban_list[i])) == 0) {
|
||||
_network_ban_list[i][0] = '\0';
|
||||
for (i = 0; i < lengthof(_network_ban_list); i++) {
|
||||
if (_network_ban_list[i] == NULL) continue;
|
||||
|
||||
if (strncmp(_network_ban_list[i], argv[1], strlen(_network_ban_list[i])) == 0 || index == i) {
|
||||
free(_network_ban_list[i]);
|
||||
_network_ban_list[i] = NULL;
|
||||
IConsolePrint(_icolour_def, "IP unbanned.");
|
||||
return true;
|
||||
}
|
||||
@@ -385,10 +457,8 @@ DEF_CONSOLE_CMD(ConBanList)
|
||||
IConsolePrint(_icolour_def, "Banlist: ");
|
||||
|
||||
for (i = 0; i < lengthof(_network_ban_list); i++) {
|
||||
if (_network_ban_list[i] == NULL || _network_ban_list[i][0] == '\0')
|
||||
continue;
|
||||
|
||||
IConsolePrintF(_icolour_def, " %d) %s", i + 1, _network_ban_list[i]);
|
||||
if (_network_ban_list[i] != NULL)
|
||||
IConsolePrintF(_icolour_def, " %d) %s", i + 1, _network_ban_list[i]);
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -447,7 +517,7 @@ DEF_CONSOLE_CMD(ConStatus)
|
||||
const NetworkClientState *cs;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("List the status of all clients connected to the server: Usage 'status'");
|
||||
IConsoleHelp("List the status of all clients connected to the server. Usage 'status'");
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -456,8 +526,37 @@ DEF_CONSOLE_CMD(ConStatus)
|
||||
const NetworkClientInfo *ci = DEREF_CLIENT_INFO(cs);
|
||||
|
||||
status = (cs->status <= STATUS_ACTIVE) ? stat_str[cs->status] : "unknown";
|
||||
IConsolePrintF(8, "Client #%d/%s status: %s frame-lag: %d play-as: %d unique-id: %s",
|
||||
cs->index, ci->client_name, status, lag, ci->client_playas, ci->unique_id);
|
||||
IConsolePrintF(8, "Client #%1d name: '%s' status: '%s' frame-lag: %3d company: %1d IP: %s unique-id: '%s'",
|
||||
cs->index, ci->client_name, status, lag, ci->client_playas, GetPlayerIP(ci), ci->unique_id);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
DEF_CONSOLE_CMD(ConServerInfo)
|
||||
{
|
||||
const NetworkGameInfo *gi;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("List current and maximum client/player limits. Usage 'server_info'");
|
||||
IConsoleHelp("You can change these values by setting the variables 'max_clients', 'max_companies' and 'max_spectators'");
|
||||
return true;
|
||||
}
|
||||
|
||||
gi = &_network_game_info;
|
||||
IConsolePrintF(_icolour_def, "Current/maximum clients: %2d/%2d", gi->clients_on, gi->clients_max);
|
||||
IConsolePrintF(_icolour_def, "Current/maximum companies: %2d/%2d", ActivePlayerCount(), gi->companies_max);
|
||||
IConsolePrintF(_icolour_def, "Current/maximum spectators: %2d/%2d", NetworkSpectatorCount(), gi->spectators_max);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
DEF_CONSOLE_HOOK(ConHookValidateMaxClientsCount) {
|
||||
/* XXX - hardcoded, string limiation -- TrueLight
|
||||
* XXX - also see network.c:NetworkStartup ~1343 */
|
||||
if (_network_game_info.clients_max > 10) {
|
||||
_network_game_info.clients_max = 10;
|
||||
IConsoleError("Maximum clients is 10, truncating.");
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -469,29 +568,35 @@ DEF_CONSOLE_CMD(ConKick)
|
||||
uint32 index;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Kick a player from a network game. Usage: 'kick <client-id>'");
|
||||
IConsoleHelp("Kick a player from a network game. Usage: 'kick <ip | client-id>'");
|
||||
IConsoleHelp("For client-id's, see the command 'clients'");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (argc != 2) return false;
|
||||
|
||||
index = atoi(argv[1]);
|
||||
if (index == NETWORK_SERVER_INDEX) {
|
||||
IConsolePrint(_icolour_def, "Silly boy, you can not kick yourself!");
|
||||
return true;
|
||||
if (strchr(argv[1], '.') == NULL) {
|
||||
index = atoi(argv[1]);
|
||||
ci = NetworkFindClientInfoFromIndex(index);
|
||||
} else {
|
||||
ci = NetworkFindClientInfoFromIP(argv[1]);
|
||||
index = (ci == NULL) ? 0 : ci->client_index;
|
||||
}
|
||||
if (index == 0) {
|
||||
IConsoleError("Invalid client-id");
|
||||
|
||||
if (index == NETWORK_SERVER_INDEX) {
|
||||
IConsoleError("Silly boy, you can not kick yourself!");
|
||||
return true;
|
||||
}
|
||||
|
||||
ci = NetworkFindClientInfoFromIndex(index);
|
||||
if (index == 0) {
|
||||
IConsoleError("Invalid client");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ci != NULL) {
|
||||
SEND_COMMAND(PACKET_SERVER_ERROR)(NetworkFindClientStateFromIndex(index), NETWORK_ERROR_KICKED);
|
||||
} else
|
||||
IConsoleError("Client-id not found");
|
||||
IConsoleError("Client not found");
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -521,7 +626,7 @@ DEF_CONSOLE_CMD(ConResetCompany)
|
||||
|
||||
/* Check if company does exist */
|
||||
index--;
|
||||
p = DEREF_PLAYER(index);
|
||||
p = GetPlayer(index);
|
||||
if (!p->is_active) {
|
||||
IConsoleError("Company does not exist.");
|
||||
return true;
|
||||
@@ -558,13 +663,14 @@ DEF_CONSOLE_CMD(ConNetworkClients)
|
||||
NetworkClientInfo *ci;
|
||||
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Get a list of connected clients including their ID, name, and company-id. Usage: 'clients'");
|
||||
IConsoleHelp("Get a list of connected clients including their ID, name, company-id, and IP. Usage: 'clients'");
|
||||
return true;
|
||||
}
|
||||
|
||||
for (ci = _network_client_info; ci != &_network_client_info[MAX_CLIENT_INFO]; ci++) {
|
||||
if (ci->client_index != NETWORK_EMPTY_INDEX) {
|
||||
IConsolePrintF(8, "Client #%d name: %s play-as company: %d", ci->client_index, ci->client_name, ci->client_playas);
|
||||
IConsolePrintF(8, "Client #%1d name: '%s' company: %1d IP: %s",
|
||||
ci->client_index, ci->client_name, ci->client_playas, GetPlayerIP(ci));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -684,7 +790,7 @@ DEF_CONSOLE_CMD(ConScript)
|
||||
if (!CloseConsoleLogIfActive()) {
|
||||
if (argc < 2) return false;
|
||||
|
||||
IConsolePrintF(_icolour_def, "file output started to: %s", argv[1]);
|
||||
IConsolePrintF(_icolour_def, "file output started to: %s", argv[1]);
|
||||
_iconsole_output_file = fopen(argv[1], "ab");
|
||||
if (_iconsole_output_file == NULL) IConsoleError("could not open file");
|
||||
}
|
||||
@@ -755,22 +861,22 @@ DEF_CONSOLE_CMD(ConAlias)
|
||||
DEF_CONSOLE_CMD(ConScreenShot)
|
||||
{
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Create a screenshot of the game. Usage: 'screenshot [big\\no_con]'");
|
||||
IConsoleHelp("Create a screenshot of the game. Usage: 'screenshot [big | no_con]'");
|
||||
IConsoleHelp("'big' makes a screenshot of the whole map, 'no_con' hides the console to create the screenshot");
|
||||
return true;
|
||||
}
|
||||
|
||||
if (argc < 2) {
|
||||
_make_screenshot = 1;
|
||||
} else {
|
||||
if (strcmp(argv[1], "big") == 0)
|
||||
if (argc > 3) return false;
|
||||
|
||||
_make_screenshot = 1;
|
||||
if (argc > 1) {
|
||||
if (strcmp(argv[1], "big") == 0 || (argc == 3 && strcmp(argv[2], "big") == 0))
|
||||
_make_screenshot = 2;
|
||||
|
||||
if (strcmp(argv[1], "no_con") == 0) {
|
||||
if (strcmp(argv[1], "no_con") == 0 || (argc == 3 && strcmp(argv[2], "no_con") == 0))
|
||||
IConsoleClose();
|
||||
_make_screenshot = 1;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -879,31 +985,31 @@ DEF_CONSOLE_CMD(ConHelp)
|
||||
const IConsoleAlias *alias;
|
||||
|
||||
cmd = IConsoleCmdGet(argv[1]);
|
||||
if (cmd != NULL) {
|
||||
cmd->proc(0, NULL);
|
||||
return true;
|
||||
}
|
||||
if (cmd != NULL) {
|
||||
cmd->proc(0, NULL);
|
||||
return true;
|
||||
}
|
||||
|
||||
alias = IConsoleAliasGet(argv[1]);
|
||||
if (alias != NULL) {
|
||||
cmd = IConsoleCmdGet(alias->cmdline);
|
||||
if (cmd != NULL) {
|
||||
cmd->proc(0, NULL);
|
||||
return true;
|
||||
}
|
||||
IConsolePrintF(_icolour_err, "ERROR: alias is of special type, please see its execution-line: '%s'", alias->cmdline);
|
||||
return true;
|
||||
}
|
||||
alias = IConsoleAliasGet(argv[1]);
|
||||
if (alias != NULL) {
|
||||
cmd = IConsoleCmdGet(alias->cmdline);
|
||||
if (cmd != NULL) {
|
||||
cmd->proc(0, NULL);
|
||||
return true;
|
||||
}
|
||||
IConsolePrintF(_icolour_err, "ERROR: alias is of special type, please see its execution-line: '%s'", alias->cmdline);
|
||||
return true;
|
||||
}
|
||||
|
||||
var = IConsoleVarGet(argv[1]);
|
||||
if (var != NULL && var->help != NULL) {
|
||||
IConsoleHelp(var->help);
|
||||
return true;
|
||||
}
|
||||
var = IConsoleVarGet(argv[1]);
|
||||
if (var != NULL && var->help != NULL) {
|
||||
IConsoleHelp(var->help);
|
||||
return true;
|
||||
}
|
||||
|
||||
IConsoleError("command or variable not found");
|
||||
return true;
|
||||
}
|
||||
IConsoleError("command or variable not found");
|
||||
return true;
|
||||
}
|
||||
|
||||
IConsolePrint(13, " ---- OpenTTD Console Help ---- ");
|
||||
IConsolePrint( 1, " - variables: [command to list all variables: list_vars]");
|
||||
@@ -913,9 +1019,9 @@ DEF_CONSOLE_CMD(ConHelp)
|
||||
IConsolePrint( 1, " call commands with '<command> <arg2> <arg3>...'");
|
||||
IConsolePrint( 1, " - to assign strings, or use them as arguments, enclose it within quotes");
|
||||
IConsolePrint( 1, " like this: '<command> \"string argument with spaces\"'");
|
||||
IConsolePrint( 1, " - use 'help <command>\\<variable>' to get specific information");
|
||||
IConsolePrint( 1, " - scroll console output with shift + (up\\down)\\(pageup\\pagedown))");
|
||||
IConsolePrint( 1, " - scroll console input history with the up\\down arrows");
|
||||
IConsolePrint( 1, " - use 'help <command> | <variable>' to get specific information");
|
||||
IConsolePrint( 1, " - scroll console output with shift + (up | down) | (pageup | pagedown))");
|
||||
IConsolePrint( 1, " - scroll console input history with the up | down arrows");
|
||||
IConsolePrint( 1, "");
|
||||
return true;
|
||||
}
|
||||
@@ -1027,7 +1133,7 @@ DEF_CONSOLE_CMD(ConSayClient)
|
||||
{
|
||||
if (argc == 0) {
|
||||
IConsoleHelp("Chat to a certain player in a multiplayer game. Usage: 'say_client <client-no> \"<msg>\"'");
|
||||
IConsoleHelp("For client-id's, see the command 'clients'");
|
||||
IConsoleHelp("For client-id's, see the command 'clients'");
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -1046,8 +1152,10 @@ DEF_CONSOLE_HOOK(ConHookServerPW)
|
||||
if (strncmp(_network_server_password, "*", NETWORK_PASSWORD_LENGTH) == 0) {
|
||||
_network_server_password[0] = '\0';
|
||||
_network_game_info.use_password = 0;
|
||||
} else
|
||||
} else {
|
||||
ttd_strlcpy(_network_game_info.server_password, _network_server_password, sizeof(_network_server_password));
|
||||
_network_game_info.use_password = 1;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -1086,6 +1194,8 @@ bool NetworkChangeCompanyPassword(byte argc, char *argv[])
|
||||
if (!_network_server)
|
||||
SEND_COMMAND(PACKET_CLIENT_SET_PASSWORD)(_network_player_info[_local_player].password);
|
||||
|
||||
IConsolePrintF(_icolour_warn, "'company_pw' changed to: %s", _network_player_info[_local_player].password);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -1101,7 +1211,7 @@ DEF_CONSOLE_HOOK(ConProcPlayerName)
|
||||
SEND_COMMAND(PACKET_CLIENT_SET_NAME)(_network_player_name);
|
||||
} else {
|
||||
if (NetworkFindName(_network_player_name)) {
|
||||
NetworkTextMessage(NETWORK_ACTION_NAME_CHANGE, 1, false, ci->client_name, _network_player_name);
|
||||
NetworkTextMessage(NETWORK_ACTION_NAME_CHANGE, 1, false, ci->client_name, "%s", _network_player_name);
|
||||
ttd_strlcpy(ci->client_name, _network_player_name, sizeof(ci->client_name));
|
||||
NetworkUpdateClientInfo(NETWORK_SERVER_INDEX);
|
||||
}
|
||||
@@ -1134,8 +1244,9 @@ DEF_CONSOLE_CMD(ConProcServerIP)
|
||||
|
||||
if (argc != 1) return false;
|
||||
|
||||
_network_server_bind_ip = inet_addr(argv[0]);
|
||||
_network_server_bind_ip = (strcmp(argv[0], "all") == 0) ? inet_addr("0.0.0.0") : inet_addr(argv[0]);
|
||||
snprintf(_network_server_bind_ip_host, sizeof(_network_server_bind_ip_host), "%s", inet_ntoa(*(struct in_addr *)&_network_server_bind_ip));
|
||||
IConsolePrintF(_icolour_warn, "'server_ip' changed to: %s", inet_ntoa(*(struct in_addr *)&_network_server_bind_ip));
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -1226,15 +1337,18 @@ void IConsoleStdLibRegister(void)
|
||||
IConsoleCmdRegister("screenshot", ConScreenShot);
|
||||
IConsoleCmdRegister("script", ConScript);
|
||||
IConsoleCmdRegister("scrollto", ConScrollToTile);
|
||||
IConsoleCmdRegister("alias", ConAlias);
|
||||
IConsoleCmdRegister("load", ConLoad);
|
||||
IConsoleCmdRegister("save", ConSave);
|
||||
IConsoleCmdRegister("alias", ConAlias);
|
||||
IConsoleCmdRegister("load", ConLoad);
|
||||
IConsoleCmdRegister("rm", ConRemove);
|
||||
IConsoleCmdRegister("save", ConSave);
|
||||
IConsoleCmdRegister("ls", ConListFiles);
|
||||
IConsoleCmdRegister("cd", ConChangeDirectory);
|
||||
IConsoleCmdRegister("pwd", ConPrintWorkingDirectory);
|
||||
IConsoleCmdRegister("clear", ConClearBuffer);
|
||||
IConsoleCmdRegister("stopall", ConStopAllVehicles);
|
||||
|
||||
IConsoleAliasRegister("dir", "ls");
|
||||
IConsoleAliasRegister("del", "rm %+");
|
||||
IConsoleAliasRegister("newmap", "newgame");
|
||||
IConsoleAliasRegister("new_map", "newgame");
|
||||
IConsoleAliasRegister("new_game", "newgame");
|
||||
@@ -1244,6 +1358,10 @@ void IConsoleStdLibRegister(void)
|
||||
|
||||
/* networking variables and functions */
|
||||
#ifdef ENABLE_NETWORK
|
||||
/* Network hooks; only active in network */
|
||||
IConsoleCmdHookAdd ("stopall", ICONSOLE_HOOK_ACCESS, ConHookNoNetwork);
|
||||
IConsoleCmdHookAdd ("resetengines", ICONSOLE_HOOK_ACCESS, ConHookNoNetwork);
|
||||
|
||||
/*** Networking commands ***/
|
||||
IConsoleCmdRegister("say", ConSay);
|
||||
IConsoleCmdHookAdd("say", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
@@ -1251,29 +1369,32 @@ void IConsoleStdLibRegister(void)
|
||||
IConsoleCmdHookAdd("say_player", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
IConsoleCmdRegister("say_client", ConSayClient);
|
||||
IConsoleCmdHookAdd("say_client", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
IConsoleCmdRegister("kick", ConKick);
|
||||
IConsoleCmdHookAdd("kick", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleCmdRegister("reset_company", ConResetCompany);
|
||||
IConsoleCmdHookAdd("reset_company", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleAliasRegister("clean_company", "reset_company %A");
|
||||
|
||||
IConsoleCmdRegister("connect", ConNetworkConnect);
|
||||
IConsoleAliasRegister("join", "connect %A");
|
||||
IConsoleCmdHookAdd("connect", ICONSOLE_HOOK_ACCESS, ConHookClientOnly);
|
||||
IConsoleAliasRegister("join", "connect %A");
|
||||
IConsoleCmdRegister("clients", ConNetworkClients);
|
||||
IConsoleCmdHookAdd("clients", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
IConsoleCmdRegister("status", ConStatus);
|
||||
IConsoleCmdHookAdd("status", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleCmdHookAdd("resetengines", ICONSOLE_HOOK_ACCESS, ConHookNoNetwork);
|
||||
|
||||
IConsoleCmdRegister("server_info", ConServerInfo);
|
||||
IConsoleCmdHookAdd("server_info", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleAliasRegister("info", "server_info");
|
||||
IConsoleCmdRegister("rcon", ConRcon);
|
||||
IConsoleCmdHookAdd("rcon", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
|
||||
IConsoleCmdRegister("reset_company", ConResetCompany);
|
||||
IConsoleCmdHookAdd("reset_company", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleAliasRegister("clean_company", "reset_company %A");
|
||||
IConsoleCmdRegister("kick", ConKick);
|
||||
IConsoleCmdHookAdd("kick", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleCmdRegister("ban", ConBan);
|
||||
IConsoleCmdHookAdd("ban", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleCmdRegister("unban", ConUnBan);
|
||||
IConsoleCmdHookAdd("unban", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleCmdRegister("banlist", ConBanList);
|
||||
IConsoleCmdHookAdd("banlist", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
IConsoleCmdRegister("pause", ConPauseGame);
|
||||
IConsoleCmdHookAdd("pause", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleCmdRegister("unpause", ConUnPauseGame);
|
||||
@@ -1292,12 +1413,10 @@ void IConsoleStdLibRegister(void)
|
||||
IConsoleVarHookAdd("server_pw", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleVarHookAdd("server_pw", ICONSOLE_HOOK_POST_ACTION, ConHookServerPW);
|
||||
IConsoleAliasRegister("server_password", "server_pw %+");
|
||||
|
||||
IConsoleVarStringRegister("rcon_pw", &_network_rcon_password, sizeof(_network_rcon_password), "Set the rcon-password to change server behaviour. Use '*' to disable rcon");
|
||||
IConsoleVarHookAdd("rcon_pw", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleVarHookAdd("rcon_pw", ICONSOLE_HOOK_POST_ACTION, ConHookRconPW);
|
||||
IConsoleAliasRegister("rcon_password", "rcon_pw %+");
|
||||
|
||||
IConsoleVarStringRegister("company_pw", NULL, 0, "Set a password for your company, so no one without the correct password can join. Use '*' to clear the password");
|
||||
IConsoleVarHookAdd("company_pw", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
IConsoleVarProcAdd("company_pw", NetworkChangeCompanyPassword);
|
||||
@@ -1306,38 +1425,40 @@ void IConsoleStdLibRegister(void)
|
||||
IConsoleVarStringRegister("name", &_network_player_name, sizeof(_network_player_name), "Set your name for multiplayer");
|
||||
IConsoleVarHookAdd("name", ICONSOLE_HOOK_ACCESS, ConHookNeedNetwork);
|
||||
IConsoleVarHookAdd("name", ICONSOLE_HOOK_POST_ACTION, ConProcPlayerName);
|
||||
|
||||
IConsoleVarStringRegister("server_name", &_network_server_name, sizeof(_network_server_name), "Set the name of the server for multiplayer");
|
||||
IConsoleVarHookAdd("server_name", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleVarHookAdd("server_name", ICONSOLE_HOOK_POST_ACTION, ConHookServerName);
|
||||
|
||||
IConsoleVarRegister("server_port", &_network_server_port, ICONSOLE_VAR_UINT32, "Set the server port. Changes take effect the next time you start a server");
|
||||
|
||||
IConsoleVarRegister("server_ip", &_network_server_bind_ip, ICONSOLE_VAR_UINT32, "Set the IP the server binds to. Changes take effect the next time you start a server");
|
||||
IConsoleVarRegister("server_ip", &_network_server_bind_ip, ICONSOLE_VAR_UINT32, "Set the IP the server binds to. Changes take effect the next time you start a server. Use 'all' to bind to any IP.");
|
||||
IConsoleVarProcAdd("server_ip", ConProcServerIP);
|
||||
IConsoleAliasRegister("server_bind_ip", "server_ip %+");
|
||||
IConsoleAliasRegister("server_ip_bind", "server_ip %+");
|
||||
IConsoleAliasRegister("server_bind", "server_ip %+");
|
||||
|
||||
IConsoleVarRegister("max_join_time", &_network_max_join_time, ICONSOLE_VAR_UINT16, "Set the maximum amount of time (ticks) a client is allowed to join. Default value: 500");
|
||||
|
||||
IConsoleVarRegister("server_advertise", &_network_advertise, ICONSOLE_VAR_BOOLEAN, "Set if the server will advertise to the master server and show up there");
|
||||
IConsoleVarHookAdd("server_advertise", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleVarHookAdd("server_advertise", ICONSOLE_HOOK_POST_ACTION, ConHookServerAdvertise);
|
||||
|
||||
IConsoleVarRegister("max_clients", &_network_game_info.clients_max, ICONSOLE_VAR_BYTE, "Control the maximum amount of connected players during runtime. Default value: 10");
|
||||
IConsoleVarHookAdd("max_clients", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleVarHookAdd("max_clients", ICONSOLE_HOOK_POST_ACTION, ConHookValidateMaxClientsCount);
|
||||
IConsoleVarRegister("max_companies", &_network_game_info.companies_max, ICONSOLE_VAR_BYTE, "Control the maximum amount of active companies during runtime. Default value: 8");
|
||||
IConsoleVarHookAdd("max_companies", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
IConsoleVarRegister("max_spectators", &_network_game_info.spectators_max, ICONSOLE_VAR_BYTE, "Control the maximum amount of active spectators during runtime. Default value: 9");
|
||||
IConsoleVarHookAdd("max_spectators", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
IConsoleVarRegister("max_join_time", &_network_max_join_time, ICONSOLE_VAR_UINT16, "Set the maximum amount of time (ticks) a client is allowed to join. Default value: 500");
|
||||
|
||||
IConsoleVarRegister("pause_on_join", &_network_pause_on_join, ICONSOLE_VAR_BOOLEAN, "Set if the server should pause gameplay while a client is joining. This might help slow users");
|
||||
IConsoleVarHookAdd("pause_on_join", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
IConsoleVarRegister("autoclean_companies", &_network_autoclean_companies, ICONSOLE_VAR_BOOLEAN, "Automatically shut down inactive companies to free them up for other players. Customize with 'autoclean_(un)protected'");
|
||||
IConsoleVarHookAdd("autoclean_companies", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
IConsoleVarRegister("autoclean_protected", &_network_autoclean_protected, ICONSOLE_VAR_BYTE, "Automatically remove the password from an inactive company after the given amount of months");
|
||||
IConsoleVarHookAdd("autoclean_protected", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
IConsoleVarRegister("autoclean_unprotected", &_network_autoclean_protected, ICONSOLE_VAR_BYTE, "Automatically shut down inactive companies after the given amount of months");
|
||||
IConsoleVarRegister("autoclean_unprotected", &_network_autoclean_unprotected, ICONSOLE_VAR_BYTE, "Automatically shut down inactive companies after the given amount of months");
|
||||
IConsoleVarHookAdd("autoclean_unprotected", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
IConsoleVarRegister("restart_game_date", &_network_restart_game_date, ICONSOLE_VAR_BYTE, "Auto-restart the server when Jan 1st of the set year is reached. Use '0' to disable this");
|
||||
IConsoleVarRegister("restart_game_date", &_network_restart_game_date, ICONSOLE_VAR_UINT16, "Auto-restart the server when Jan 1st of the set year is reached. Use '0' to disable this");
|
||||
IConsoleVarHookAdd("restart_game_date", ICONSOLE_HOOK_ACCESS, ConHookServerOnly);
|
||||
|
||||
#endif /* ENABLE_NETWORK */
|
||||
|
||||
+100
@@ -0,0 +1,100 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "openttd.h"
|
||||
#include "currency.h"
|
||||
#include "news.h"
|
||||
#include "variables.h"
|
||||
#include "table/strings.h"
|
||||
|
||||
// exchange rate prefix
|
||||
// | separator | postfix
|
||||
// | | Euro year | |
|
||||
// | | | | |
|
||||
CurrencySpec _currency_specs[] = {
|
||||
{ 1, ',', CF_NOEURO, "\xA3", "" }, // british pounds
|
||||
{ 2, ',', CF_NOEURO, "$", "" }, // us dollars
|
||||
{ 2, ',', CF_ISEURO, "¤", "" }, // Euro
|
||||
{ 200, ',', CF_NOEURO, "\xA5", "" }, // yen
|
||||
{ 19, ',', 2002, "", " S." }, // austrian schilling
|
||||
{ 57, ',', 2002, "BEF ", "" }, // belgian franc
|
||||
{ 2, ',', CF_NOEURO, "CHF ", "" }, // swiss franc
|
||||
{ 50, ',', CF_NOEURO, "", " Kc" }, // czech koruna // TODO: Should use the "c" with an upside down "^"
|
||||
{ 4, '.', 2002, "DM ", "" }, // deutsche mark
|
||||
{ 10, '.', CF_NOEURO, "", " kr" }, // danish krone
|
||||
{ 200, '.', 2002, "Pts ", "" }, // spanish pesetas
|
||||
{ 8, ',', 2002, "", " mk" }, // finnish markka
|
||||
{ 10, '.', 2002, "FF ", "" }, // french francs
|
||||
{ 480, ',', 2002, "", "Dr." }, // greek drachma
|
||||
{ 376, ',', 2002, "", " Ft" }, // hungarian forint
|
||||
{ 130, '.', CF_NOEURO, "", " Kr" }, // icelandic krona
|
||||
{ 2730, ',', 2002, "", " L." }, // italian lira
|
||||
{ 3, ',', 2002, "NLG ", "" }, // dutch gulden
|
||||
{ 11, '.', CF_NOEURO, "", " Kr" }, // norwegian krone
|
||||
{ 6, ' ', CF_NOEURO, "", " zl" }, // polish zloty
|
||||
{ 6, '.', CF_NOEURO, "", " Lei" }, // romanian Lei
|
||||
{ 5, ' ', CF_NOEURO, "", " p" }, // russian rouble
|
||||
{ 13, '.', CF_NOEURO, "", " Kr" }, // swedish krona
|
||||
{ 1, ' ', CF_NOEURO, "", "" }, // custom currency
|
||||
};
|
||||
|
||||
const StringID _currency_string_list[] = {
|
||||
STR_CURR_GBP,
|
||||
STR_CURR_USD,
|
||||
STR_CURR_EUR,
|
||||
STR_CURR_YEN,
|
||||
STR_CURR_ATS,
|
||||
STR_CURR_BEF,
|
||||
STR_CURR_CHF,
|
||||
STR_CURR_CZK,
|
||||
STR_CURR_DEM,
|
||||
STR_CURR_DKK,
|
||||
STR_CURR_ESP,
|
||||
STR_CURR_FIM,
|
||||
STR_CURR_FRF,
|
||||
STR_CURR_GRD,
|
||||
STR_CURR_HUF,
|
||||
STR_CURR_ISK,
|
||||
STR_CURR_ITL,
|
||||
STR_CURR_NLG,
|
||||
STR_CURR_NOK,
|
||||
STR_CURR_PLN,
|
||||
STR_CURR_ROL,
|
||||
STR_CURR_RUR,
|
||||
STR_CURR_SEK,
|
||||
STR_CURR_CUSTOM,
|
||||
INVALID_STRING_ID
|
||||
};
|
||||
|
||||
// NOTE: Make sure both lists are in the same order
|
||||
// + 1 string list terminator
|
||||
assert_compile(lengthof(_currency_specs) + 1 == lengthof(_currency_string_list));
|
||||
|
||||
|
||||
// get a mask of the allowed currencies depending on the year
|
||||
uint GetMaskOfAllowedCurrencies(void)
|
||||
{
|
||||
uint mask = 0;
|
||||
uint i;
|
||||
|
||||
for (i = 0; i != lengthof(_currency_specs); i++) {
|
||||
uint16 to_euro = _currency_specs[i].to_euro;
|
||||
|
||||
if (to_euro != CF_NOEURO && to_euro != CF_ISEURO && _cur_year >= to_euro - MAX_YEAR_BEGIN_REAL) continue;
|
||||
if (to_euro == CF_ISEURO && _cur_year < 2000 - MAX_YEAR_BEGIN_REAL) continue;
|
||||
mask |= (1 << i);
|
||||
}
|
||||
mask |= (1 << 23); // always allow custom currency
|
||||
return mask;
|
||||
}
|
||||
|
||||
|
||||
void CheckSwitchToEuro(void)
|
||||
{
|
||||
if (_currency_specs[_opt.currency].to_euro != CF_NOEURO &&
|
||||
_currency_specs[_opt.currency].to_euro != CF_ISEURO &&
|
||||
MAX_YEAR_BEGIN_REAL + _cur_year >= _currency_specs[_opt.currency].to_euro) {
|
||||
_opt.currency = 2; // this is the index of euro above.
|
||||
AddNewsItem(STR_EURO_INTRODUCE, NEWS_FLAGS(NM_NORMAL, 0, NT_ECONOMY, 0), 0, 0);
|
||||
}
|
||||
}
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef CURRENCY_H
|
||||
#define CURRENCY_H
|
||||
|
||||
enum {
|
||||
CF_NOEURO = 0,
|
||||
CF_ISEURO = 1,
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
uint16 rate;
|
||||
char separator;
|
||||
uint16 to_euro;
|
||||
char prefix[16];
|
||||
char suffix[16];
|
||||
} CurrencySpec;
|
||||
|
||||
extern CurrencySpec _currency_specs[];
|
||||
extern const StringID _currency_string_list[];
|
||||
|
||||
// XXX small hack, but makes the rest of the code a bit nicer to read
|
||||
#define _custom_currency (_currency_specs[23])
|
||||
#define _currency ((const CurrencySpec*)&_currency_specs[_opt_ptr->currency])
|
||||
|
||||
uint GetMaskOfAllowedCurrencies(void);
|
||||
void CheckSwitchToEuro(void);
|
||||
|
||||
#endif /* CURRENCY_H */
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -1,12 +1,16 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include <stdio.h>
|
||||
#include <stdarg.h>
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "console.h"
|
||||
#include "debug.h"
|
||||
#include "functions.h"
|
||||
#include "string.h"
|
||||
|
||||
int _debug_ai_level;
|
||||
int _debug_driver_level;
|
||||
int _debug_grf_level;
|
||||
int _debug_map_level;
|
||||
int _debug_misc_level;
|
||||
@@ -14,6 +18,7 @@ int _debug_ms_level;
|
||||
int _debug_net_level;
|
||||
int _debug_spritecache_level;
|
||||
int _debug_oldloader_level;
|
||||
int _debug_ntp_level;
|
||||
int _debug_npf_level;
|
||||
|
||||
|
||||
@@ -37,6 +42,7 @@ typedef struct DebugLevel {
|
||||
#define DEBUG_LEVEL(x) { #x, &_debug_##x##_level }
|
||||
static const DebugLevel debug_level[] = {
|
||||
DEBUG_LEVEL(ai),
|
||||
DEBUG_LEVEL(driver),
|
||||
DEBUG_LEVEL(grf),
|
||||
DEBUG_LEVEL(map),
|
||||
DEBUG_LEVEL(misc),
|
||||
@@ -44,6 +50,7 @@ typedef struct DebugLevel {
|
||||
DEBUG_LEVEL(net),
|
||||
DEBUG_LEVEL(spritecache),
|
||||
DEBUG_LEVEL(oldloader),
|
||||
DEBUG_LEVEL(ntp),
|
||||
DEBUG_LEVEL(npf)
|
||||
};
|
||||
#undef DEBUG_LEVEL
|
||||
@@ -61,12 +68,11 @@ void SetDebugString(const char *s)
|
||||
v = strtoul(s, &end, 0);
|
||||
s = end;
|
||||
|
||||
for (i = debug_level; i != endof(debug_level); ++i)
|
||||
*i->level = v;
|
||||
for (i = debug_level; i != endof(debug_level); ++i) *i->level = v;
|
||||
}
|
||||
|
||||
// individual levels
|
||||
for(;;) {
|
||||
for (;;) {
|
||||
const DebugLevel *i;
|
||||
int *p;
|
||||
|
||||
@@ -88,9 +94,9 @@ void SetDebugString(const char *s)
|
||||
if (*s == '=') s++;
|
||||
v = strtoul(s, &end, 0);
|
||||
s = end;
|
||||
if (p != NULL)
|
||||
if (p != NULL) {
|
||||
*p = v;
|
||||
else {
|
||||
} else {
|
||||
ShowInfoF("Unknown debug level '%.*s'", s - t, t);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef DEBUG_H
|
||||
#define DEBUG_H
|
||||
|
||||
@@ -7,6 +9,7 @@
|
||||
#define DEBUG(name, level) if (level == 0 || _debug_ ## name ## _level >= level) debug
|
||||
|
||||
extern int _debug_ai_level;
|
||||
extern int _debug_driver_level;
|
||||
extern int _debug_grf_level;
|
||||
extern int _debug_map_level;
|
||||
extern int _debug_misc_level;
|
||||
@@ -14,6 +17,7 @@
|
||||
extern int _debug_net_level;
|
||||
extern int _debug_spritecache_level;
|
||||
extern int _debug_oldloader_level;
|
||||
extern int _debug_ntp_level;
|
||||
extern int _debug_npf_level;
|
||||
#endif
|
||||
|
||||
@@ -22,4 +26,4 @@ void CDECL debug(const char *s, ...);
|
||||
void SetDebugString(const char *s);
|
||||
const char *GetDebugString(void);
|
||||
|
||||
#endif
|
||||
#endif /* DEBUG_H */
|
||||
|
||||
+16
-314
@@ -1,54 +1,17 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "debug.h"
|
||||
#include "network.h"
|
||||
#include "hal.h"
|
||||
|
||||
#ifdef ENABLE_NETWORK
|
||||
|
||||
#include "gfx.h"
|
||||
#include "window.h"
|
||||
#include "command.h"
|
||||
#include "console.h"
|
||||
#ifdef WIN32
|
||||
# include <windows.h> /* GetTickCount */
|
||||
# include <conio.h>
|
||||
#endif
|
||||
#if defined(UNIX) && !defined(__MORPHOS__)
|
||||
|
||||
#ifdef __OS2__
|
||||
# include <sys/time.h> /* gettimeofday */
|
||||
# include <sys/types.h>
|
||||
# include <unistd.h>
|
||||
# include <conio.h>
|
||||
# define STDIN 0 /* file descriptor for standard input */
|
||||
#include "openttd.h"
|
||||
#include "variables.h"
|
||||
|
||||
extern void OS2_SwitchToConsoleMode();
|
||||
#endif
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#ifdef UNIX
|
||||
# include <sys/time.h> /* gettimeofday */
|
||||
# include <sys/types.h>
|
||||
# include <unistd.h>
|
||||
# include <signal.h>
|
||||
# define STDIN 0 /* file descriptor for standard input */
|
||||
#endif
|
||||
#ifdef __MORPHOS__
|
||||
/* Voids the fork, option will be disabled for MorphOS build anyway, because
|
||||
* MorphOS doesn't support forking (could only implemented with lots of code
|
||||
* changes here). */
|
||||
int fork(void) { return -1; }
|
||||
int dup2(int oldd, int newd) { return -1; }
|
||||
#endif
|
||||
|
||||
// This file handles all dedicated-server in- and outputs
|
||||
|
||||
static void *_dedicated_video_mem;
|
||||
|
||||
extern bool SafeSaveOrLoad(const char *filename, int mode, int newgm);
|
||||
extern void SwitchMode(int new_mode);
|
||||
|
||||
#ifdef UNIX
|
||||
/* We want to fork our dedicated server */
|
||||
void DedicatedFork(void)
|
||||
{
|
||||
/* Fork the program */
|
||||
@@ -57,25 +20,28 @@ void DedicatedFork(void)
|
||||
case -1:
|
||||
perror("Unable to fork");
|
||||
exit(1);
|
||||
case 0:
|
||||
// We're the child
|
||||
|
||||
case 0: { // We're the child
|
||||
FILE* f;
|
||||
|
||||
/* Open the log-file to log all stuff too */
|
||||
_log_file_fd = fopen(_log_file, "a");
|
||||
if (!_log_file_fd) {
|
||||
f = fopen(_log_file, "a");
|
||||
if (f == NULL) {
|
||||
perror("Unable to open logfile");
|
||||
exit(1);
|
||||
}
|
||||
/* Redirect stdout and stderr to log-file */
|
||||
if (dup2(fileno(_log_file_fd), fileno(stdout)) == -1) {
|
||||
if (dup2(fileno(f), fileno(stdout)) == -1) {
|
||||
perror("Rerouting stdout");
|
||||
exit(1);
|
||||
}
|
||||
if (dup2(fileno(_log_file_fd), fileno(stderr)) == -1) {
|
||||
if (dup2(fileno(f), fileno(stderr)) == -1) {
|
||||
perror("Rerouting stderr");
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
// We're the parent
|
||||
printf("Loading dedicated server...\n");
|
||||
@@ -83,274 +49,10 @@ void DedicatedFork(void)
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
|
||||
/* Signal handlers */
|
||||
static void DedicatedSignalHandler(int sig)
|
||||
{
|
||||
_exit_game = true;
|
||||
signal(sig, DedicatedSignalHandler);
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef WIN32
|
||||
#include <time.h>
|
||||
HANDLE hEvent;
|
||||
static HANDLE hThread; // Thread to close
|
||||
static char _win_console_thread_buffer[200];
|
||||
|
||||
/* Windows Console thread. Just loop and signal when input has been received */
|
||||
void WINAPI CheckForConsoleInput(void)
|
||||
{
|
||||
while (true) {
|
||||
fgets(_win_console_thread_buffer, lengthof(_win_console_thread_buffer), stdin);
|
||||
SetEvent(hEvent); // signal input waiting that the line is ready
|
||||
}
|
||||
}
|
||||
|
||||
void CreateWindowsConsoleThread(void)
|
||||
{
|
||||
static char tbuffer[9];
|
||||
DWORD dwThreadId;
|
||||
/* Create event to signal when console input is ready */
|
||||
hEvent = CreateEvent(NULL, false, false, _strtime(tbuffer));
|
||||
if (hEvent == NULL)
|
||||
error("Cannot create console event!");
|
||||
|
||||
hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)CheckForConsoleInput, NULL, 0, &dwThreadId);
|
||||
if (hThread == NULL)
|
||||
error("Cannot create console thread!");
|
||||
|
||||
DEBUG(misc, 0) ("Windows console thread started...");
|
||||
}
|
||||
|
||||
void CloseWindowsConsoleThread(void)
|
||||
{
|
||||
CloseHandle(hThread);
|
||||
CloseHandle(hEvent);
|
||||
DEBUG(misc, 0) ("Windows console thread shut down...");
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
static const char *DedicatedVideoStart(const char * const *parm)
|
||||
{
|
||||
_screen.width = _screen.pitch = _cur_resolution[0];
|
||||
_screen.height = _cur_resolution[1];
|
||||
_dedicated_video_mem = malloc(_cur_resolution[0]*_cur_resolution[1]);
|
||||
|
||||
_debug_net_level = 6;
|
||||
_debug_misc_level = 0;
|
||||
|
||||
#ifdef WIN32
|
||||
// For win32 we need to allocate an console (debug mode does the same)
|
||||
CreateConsole();
|
||||
CreateWindowsConsoleThread();
|
||||
SetConsoleTitle("OpenTTD Dedicated Server");
|
||||
#endif
|
||||
|
||||
#ifdef __OS2__
|
||||
// For OS/2 we also need to switch to console mode instead of PM mode
|
||||
OS2_SwitchToConsoleMode();
|
||||
#endif
|
||||
|
||||
DEBUG(misc,0)("Loading dedicated server...");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void DedicatedVideoStop(void)
|
||||
{
|
||||
#ifdef WIN32
|
||||
CloseWindowsConsoleThread();
|
||||
#endif
|
||||
free(_dedicated_video_mem);
|
||||
}
|
||||
|
||||
static void DedicatedVideoMakeDirty(int left, int top, int width, int height) {}
|
||||
static bool DedicatedVideoChangeRes(int w, int h) { return false; }
|
||||
static void DedicatedVideoFullScreen(bool fs) {}
|
||||
|
||||
#if defined(UNIX) || defined(__OS2__)
|
||||
static bool InputWaiting(void)
|
||||
{
|
||||
struct timeval tv;
|
||||
fd_set readfds;
|
||||
byte ret;
|
||||
|
||||
tv.tv_sec = 0;
|
||||
tv.tv_usec = 1;
|
||||
|
||||
FD_ZERO(&readfds);
|
||||
FD_SET(STDIN, &readfds);
|
||||
|
||||
/* don't care about writefds and exceptfds: */
|
||||
ret = select(STDIN + 1, &readfds, NULL, NULL, &tv);
|
||||
|
||||
if (ret > 0)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
#else
|
||||
static bool InputWaiting(void)
|
||||
{
|
||||
if (WaitForSingleObject(hEvent, 1) == WAIT_OBJECT_0)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
|
||||
static void DedicatedHandleKeyInput(void)
|
||||
{
|
||||
static char input_line[200] = "";
|
||||
|
||||
if (!InputWaiting())
|
||||
return;
|
||||
|
||||
if (_exit_game)
|
||||
return;
|
||||
|
||||
#if defined(UNIX) || defined(__OS2__)
|
||||
fgets(input_line, lengthof(input_line), stdin);
|
||||
#else
|
||||
strncpy(input_line, _win_console_thread_buffer, lengthof(input_line));
|
||||
#endif
|
||||
|
||||
/* XXX - strtok() does not 'forget' \n\r if it is the first character! */
|
||||
strtok(input_line, "\r\n"); // Forget about the final \n (or \r)
|
||||
{ /* Remove any special control characters */
|
||||
uint i;
|
||||
for (i = 0; i < lengthof(input_line); i++) {
|
||||
if (input_line[i] == '\n' || input_line[i] == '\r') // cut missed beginning '\0'
|
||||
input_line[i] = '\0';
|
||||
|
||||
if (input_line[i] == '\0')
|
||||
break;
|
||||
|
||||
if (!IS_INT_INSIDE(input_line[i], ' ', 256))
|
||||
input_line[i] = ' ';
|
||||
}
|
||||
}
|
||||
|
||||
IConsoleCmdExec(input_line); // execute command
|
||||
}
|
||||
|
||||
static int DedicatedVideoMainLoop(void)
|
||||
{
|
||||
#ifndef WIN32
|
||||
struct timeval tim;
|
||||
#endif
|
||||
uint32 next_tick;
|
||||
uint32 cur_ticks;
|
||||
|
||||
#ifdef WIN32
|
||||
next_tick = GetTickCount() + 30;
|
||||
#else
|
||||
gettimeofday(&tim, NULL);
|
||||
next_tick = (tim.tv_usec / 1000) + 30 + (tim.tv_sec * 1000);
|
||||
#endif
|
||||
|
||||
/* Signal handlers */
|
||||
#ifdef UNIX
|
||||
signal(SIGTERM, DedicatedSignalHandler);
|
||||
signal(SIGINT, DedicatedSignalHandler);
|
||||
signal(SIGQUIT, DedicatedSignalHandler);
|
||||
#endif
|
||||
|
||||
// Load the dedicated server stuff
|
||||
_is_network_server = true;
|
||||
_network_dedicated = true;
|
||||
_network_playas = OWNER_SPECTATOR;
|
||||
_local_player = OWNER_SPECTATOR;
|
||||
|
||||
/* If SwitchMode is SM_LOAD, it means that the user used the '-g' options */
|
||||
if (_switch_mode != SM_LOAD) {
|
||||
_switch_mode = SM_NONE;
|
||||
GenRandomNewGame(Random(), InteractiveRandom());
|
||||
} else {
|
||||
_switch_mode = SM_NONE;
|
||||
/* First we need to test if the savegame can be loaded, else we will end up playing the
|
||||
* intro game... */
|
||||
if (!SafeSaveOrLoad(_file_to_saveload.name, _file_to_saveload.mode, GM_NORMAL)) {
|
||||
/* Loading failed, pop out.. */
|
||||
DEBUG(net, 0)("Loading requested map failed. Aborting.");
|
||||
_networking = false;
|
||||
} else {
|
||||
/* We can load this game, so go ahead */
|
||||
SwitchMode(SM_LOAD);
|
||||
}
|
||||
}
|
||||
|
||||
// Done loading, start game!
|
||||
|
||||
if (!_networking) {
|
||||
DEBUG(net, 1)("Dedicated server could not be launched. Aborting.");
|
||||
return ML_QUIT;
|
||||
}
|
||||
|
||||
while (true) {
|
||||
InteractiveRandom(); // randomness
|
||||
|
||||
if (_exit_game) return ML_QUIT;
|
||||
|
||||
if (!_dedicated_forks)
|
||||
DedicatedHandleKeyInput();
|
||||
|
||||
#ifdef WIN32
|
||||
cur_ticks = GetTickCount();
|
||||
#else
|
||||
gettimeofday(&tim, NULL);
|
||||
cur_ticks = (tim.tv_usec / 1000) + (tim.tv_sec * 1000);
|
||||
#endif
|
||||
|
||||
if (cur_ticks >= next_tick) {
|
||||
next_tick += 30;
|
||||
|
||||
GameLoop();
|
||||
_screen.dst_ptr = _dedicated_video_mem;
|
||||
UpdateWindows();
|
||||
}
|
||||
CSleep(1);
|
||||
}
|
||||
|
||||
return ML_QUIT;
|
||||
}
|
||||
|
||||
|
||||
const HalVideoDriver _dedicated_video_driver = {
|
||||
DedicatedVideoStart,
|
||||
DedicatedVideoStop,
|
||||
DedicatedVideoMakeDirty,
|
||||
DedicatedVideoMainLoop,
|
||||
DedicatedVideoChangeRes,
|
||||
DedicatedVideoFullScreen,
|
||||
};
|
||||
|
||||
#else
|
||||
|
||||
static void *_dedicated_video_mem;
|
||||
|
||||
static const char *DedicatedVideoStart(const char * const *parm)
|
||||
{
|
||||
DEBUG(misc, 0) ("OpenTTD compiled without network support, exiting.");
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void DedicatedFork(void) {}
|
||||
static void DedicatedVideoStop(void) { free(_dedicated_video_mem); }
|
||||
static void DedicatedVideoMakeDirty(int left, int top, int width, int height) {}
|
||||
static bool DedicatedVideoChangeRes(int w, int h) { return false; }
|
||||
static void DedicatedVideoFullScreen(bool fs) {}
|
||||
static int DedicatedVideoMainLoop(void) { return ML_QUIT; }
|
||||
|
||||
const HalVideoDriver _dedicated_video_driver = {
|
||||
DedicatedVideoStart,
|
||||
DedicatedVideoStop,
|
||||
DedicatedVideoMakeDirty,
|
||||
DedicatedVideoMainLoop,
|
||||
DedicatedVideoChangeRes,
|
||||
DedicatedVideoFullScreen,
|
||||
};
|
||||
|
||||
#endif /* ENABLE_NETWORK */
|
||||
|
||||
@@ -1,6 +1,9 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "depot.h"
|
||||
#include "functions.h"
|
||||
#include "tile.h"
|
||||
#include "map.h"
|
||||
#include "table/strings.h"
|
||||
@@ -33,7 +36,7 @@ MemoryPool _depot_pool = { "Depots", DEPOT_POOL_MAX_BLOCKS, DEPOT_POOL_BLOCK_SIZ
|
||||
*
|
||||
* @return Returns the depot if the tile had a depot, else it returns NULL
|
||||
*/
|
||||
Depot *GetDepotByTile(uint tile)
|
||||
Depot *GetDepotByTile(TileIndex tile)
|
||||
{
|
||||
Depot *depot;
|
||||
|
||||
@@ -73,7 +76,7 @@ Depot *AllocateDepot(void)
|
||||
/**
|
||||
* Delete a depot
|
||||
*/
|
||||
void DoDeleteDepot(uint tile)
|
||||
void DoDeleteDepot(TileIndex tile)
|
||||
{
|
||||
Order order;
|
||||
Depot *depot;
|
||||
@@ -103,7 +106,7 @@ void InitializeDepot(void)
|
||||
}
|
||||
|
||||
|
||||
static const byte _depot_desc[] = {
|
||||
static const SaveLoad _depot_desc[] = {
|
||||
SLE_CONDVAR(Depot, xy, SLE_FILE_U16 | SLE_VAR_U32, 0, 5),
|
||||
SLE_CONDVAR(Depot, xy, SLE_UINT32, 6, 255),
|
||||
SLE_VAR(Depot,town_index, SLE_UINT16),
|
||||
|
||||
@@ -1,8 +1,14 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef DEPOT_H
|
||||
#define DEPOT_H
|
||||
|
||||
/** @file depot.h Header files for depots (not hangars)
|
||||
* @see depot.c */
|
||||
|
||||
#include "pool.h"
|
||||
#include "tile.h"
|
||||
#include "variables.h"
|
||||
|
||||
struct Depot {
|
||||
TileIndex xy;
|
||||
@@ -72,14 +78,14 @@ static inline bool IsTileDepotType(TileIndex tile, TransportType type)
|
||||
switch(type)
|
||||
{
|
||||
case TRANSPORT_RAIL:
|
||||
return IsTileType(tile, MP_RAILWAY) && (_map5[tile] & 0xFC) == 0xC0;
|
||||
break;
|
||||
return IsTileType(tile, MP_RAILWAY) && (_m[tile].m5 & 0xFC) == 0xC0;
|
||||
|
||||
case TRANSPORT_ROAD:
|
||||
return IsTileType(tile, MP_STREET) && (_map5[tile] & 0xF0) == 0x20;
|
||||
break;
|
||||
return IsTileType(tile, MP_STREET) && (_m[tile].m5 & 0xF0) == 0x20;
|
||||
|
||||
case TRANSPORT_WATER:
|
||||
return IsTileType(tile, MP_WATER) && (_map5[tile] & ~3) == 0x80;
|
||||
break;
|
||||
return IsTileType(tile, MP_WATER) && (_m[tile].m5 & ~3) == 0x80;
|
||||
|
||||
default:
|
||||
assert(0);
|
||||
return false;
|
||||
@@ -89,7 +95,7 @@ static inline bool IsTileDepotType(TileIndex tile, TransportType type)
|
||||
/**
|
||||
* Returns the direction the exit of the depot on the given tile is facing.
|
||||
*/
|
||||
static inline uint GetDepotDirection(TileIndex tile, TransportType type)
|
||||
static inline DiagDirection GetDepotDirection(TileIndex tile, TransportType type)
|
||||
{
|
||||
assert(IsTileDepotType(tile, type));
|
||||
|
||||
@@ -98,23 +104,45 @@ static inline uint GetDepotDirection(TileIndex tile, TransportType type)
|
||||
case TRANSPORT_RAIL:
|
||||
case TRANSPORT_ROAD:
|
||||
/* Rail and road store a diagonal direction in bits 0 and 1 */
|
||||
return _map5[tile] & 3;
|
||||
return (DiagDirection)GB(_m[tile].m5, 0, 2);
|
||||
case TRANSPORT_WATER:
|
||||
/* Water is stubborn, it stores the directions in a different order. */
|
||||
switch (_map5[tile] & 3) {
|
||||
case 0: return 0;
|
||||
case 1: return 2;
|
||||
case 2: return 3;
|
||||
case 3: return 1;
|
||||
switch (GB(_m[tile].m5, 0, 2)) {
|
||||
case 0: return DIAGDIR_NE;
|
||||
case 1: return DIAGDIR_SW;
|
||||
case 2: return DIAGDIR_NW;
|
||||
case 3: return DIAGDIR_SE;
|
||||
}
|
||||
default:
|
||||
return 0; /* Not reached */
|
||||
return INVALID_DIAGDIR; /* Not reached */
|
||||
}
|
||||
}
|
||||
|
||||
Depot *GetDepotByTile(uint tile);
|
||||
/**
|
||||
Find out if the slope of the tile is suitable to build a depot of given direction
|
||||
@param direction The direction in which the depot's exit points. Starts with 0 as NE and goes Clockwise
|
||||
@param tileh The slope of the tile in question
|
||||
@return true if the construction is possible
|
||||
|
||||
|
||||
This is checked by the ugly 0x4C >> direction magic, which does the following:
|
||||
0x4C is 0100 1100 and tileh has only bits 0..3 set (steep tiles are ruled out)
|
||||
So: for direction (only the significant bits are shown)<p>
|
||||
00 (exit towards NE) we need either bit 2 or 3 set in tileh: 0x4C >> 0 = 1100<p>
|
||||
01 (exit towards SE) we need either bit 1 or 2 set in tileh: 0x4C >> 1 = 0110<p>
|
||||
02 (exit towards SW) we need either bit 0 or 1 set in tileh: 0x4C >> 2 = 0011<p>
|
||||
03 (exit towards NW) we need either bit 0 or 4 set in tileh: 0x4C >> 3 = 1001<p>
|
||||
So ((0x4C >> p2) & tileh) determines whether the depot can be built on the current tileh
|
||||
*/
|
||||
static inline bool CanBuildDepotByTileh(uint32 direction, uint tileh)
|
||||
{
|
||||
return (0x4C >> direction) & tileh;
|
||||
}
|
||||
|
||||
|
||||
Depot *GetDepotByTile(TileIndex tile);
|
||||
void InitializeDepot(void);
|
||||
Depot *AllocateDepot(void);
|
||||
void DoDeleteDepot(uint tile);
|
||||
void DoDeleteDepot(TileIndex tile);
|
||||
|
||||
#endif /* DEPOT_H */
|
||||
|
||||
+104
-112
@@ -1,31 +1,35 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "tile.h"
|
||||
#include "vehicle.h"
|
||||
#include "command.h"
|
||||
#include "news.h"
|
||||
#include "gfx.h"
|
||||
#include "station.h"
|
||||
#include "waypoint.h"
|
||||
#include "town.h"
|
||||
#include "industry.h"
|
||||
#include "player.h"
|
||||
#include "airport_movement.h"
|
||||
#include "sound.h"
|
||||
#include "variables.h"
|
||||
#include "table/sprites.h"
|
||||
|
||||
static void DisasterClearSquare(TileIndex tile)
|
||||
{
|
||||
if (!EnsureNoVehicle(tile))
|
||||
return;
|
||||
if (!EnsureNoVehicle(tile)) return;
|
||||
|
||||
switch (GetTileType(tile)) {
|
||||
case MP_RAILWAY:
|
||||
if (IS_HUMAN_PLAYER(_map_owner[tile])) DoClearSquare(tile);
|
||||
if (IS_HUMAN_PLAYER(GetTileOwner(tile)) && !IsRailWaypoint(tile)) DoClearSquare(tile);
|
||||
break;
|
||||
|
||||
case MP_HOUSE: {
|
||||
byte p = _current_player;
|
||||
PlayerID p = _current_player;
|
||||
_current_player = OWNER_NONE;
|
||||
DoCommandByTile(tile, 0, 0, DC_EXEC, CMD_LANDSCAPE_CLEAR);
|
||||
_current_player = p;
|
||||
@@ -76,7 +80,7 @@ static void InitializeDisasterVehicle(Vehicle *v, int x, int y, byte z, byte dir
|
||||
v->x_pos = x;
|
||||
v->y_pos = y;
|
||||
v->z_pos = z;
|
||||
v->tile = TILE_FROM_XY(x,y);
|
||||
v->tile = TileVirtXY(x, y);
|
||||
v->direction = direction;
|
||||
v->subtype = subtype;
|
||||
v->x_offs = -1;
|
||||
@@ -111,7 +115,7 @@ static void SetDisasterVehiclePos(Vehicle *v, int x, int y, byte z)
|
||||
v->x_pos = x;
|
||||
v->y_pos = y;
|
||||
v->z_pos = z;
|
||||
v->tile = TILE_FROM_XY(x,y);
|
||||
v->tile = TileVirtXY(x, y);
|
||||
|
||||
DisasterVehicleUpdateImage(v);
|
||||
VehiclePositionChanged(v);
|
||||
@@ -147,7 +151,7 @@ static void DisasterTick_Zeppeliner(Vehicle *v)
|
||||
Station *st;
|
||||
int x,y;
|
||||
byte z;
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
|
||||
++v->tick_counter;
|
||||
|
||||
@@ -173,13 +177,12 @@ static void DisasterTick_Zeppeliner(Vehicle *v)
|
||||
|
||||
if (IsValidTile(tile) &&
|
||||
IsTileType(tile, MP_STATION) &&
|
||||
IS_BYTE_INSIDE(_map5[tile], 8, 0x43) &&
|
||||
IS_HUMAN_PLAYER(_map_owner[tile])) {
|
||||
|
||||
IS_BYTE_INSIDE(_m[tile].m5, 8, 0x43) &&
|
||||
IS_HUMAN_PLAYER(GetTileOwner(tile))) {
|
||||
v->current_order.station = 1;
|
||||
v->age = 0;
|
||||
|
||||
SetDParam(0, _map2[tile]);
|
||||
SetDParam(0, _m[tile].m2);
|
||||
AddNewsItem(STR_B000_ZEPPELIN_DISASTER_AT,
|
||||
NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_VEHICLE, NT_ACCIDENT, 0),
|
||||
v->index,
|
||||
@@ -199,10 +202,9 @@ static void DisasterTick_Zeppeliner(Vehicle *v)
|
||||
|
||||
if (IsValidTile(tile) &&
|
||||
IsTileType(tile, MP_STATION) &&
|
||||
IS_BYTE_INSIDE(_map5[tile], 8, 0x43) &&
|
||||
IS_HUMAN_PLAYER(_map_owner[tile])) {
|
||||
|
||||
st = GetStation(_map2[tile]);
|
||||
IS_BYTE_INSIDE(_m[tile].m5, 8, 0x43) &&
|
||||
IS_HUMAN_PLAYER(GetTileOwner(tile))) {
|
||||
st = GetStation(_m[tile].m2);
|
||||
CLRBITS(st->airport_flags, RUNWAY_IN_block);
|
||||
}
|
||||
|
||||
@@ -221,17 +223,17 @@ static void DisasterTick_Zeppeliner(Vehicle *v)
|
||||
if (++v->age == 1) {
|
||||
CreateEffectVehicleRel(v, 0, 7, 8, EV_EXPLOSION_LARGE);
|
||||
SndPlayVehicleFx(SND_12_EXPLOSION, v);
|
||||
v->u.disaster.image_override = 0xF42;
|
||||
v->u.disaster.image_override = SPR_BLIMP_CRASHING;
|
||||
} else if (v->age == 70) {
|
||||
v->u.disaster.image_override = 0xF43;
|
||||
v->u.disaster.image_override = SPR_BLIMP_CRASHED;
|
||||
} else if (v->age <= 300) {
|
||||
if (!(v->tick_counter&7)) {
|
||||
uint32 r = Random();
|
||||
|
||||
CreateEffectVehicleRel(v,
|
||||
-7 + (r&0xF),
|
||||
-7 + (r>>4&0xF),
|
||||
5 + (r>>8&0x7),
|
||||
GB(r, 0, 4) - 7,
|
||||
GB(r, 4, 4) - 7,
|
||||
GB(r, 8, 3) + 5,
|
||||
EV_EXPLOSION_SMALL);
|
||||
}
|
||||
} else if (v->age == 350) {
|
||||
@@ -242,10 +244,10 @@ static void DisasterTick_Zeppeliner(Vehicle *v)
|
||||
tile = v->tile;/**/
|
||||
if (IsValidTile(tile) &&
|
||||
IsTileType(tile, MP_STATION) &&
|
||||
IS_BYTE_INSIDE(_map5[tile], 8, 0x43) &&
|
||||
IS_HUMAN_PLAYER(_map_owner[tile])) {
|
||||
IS_BYTE_INSIDE(_m[tile].m5, 8, 0x43) &&
|
||||
IS_HUMAN_PLAYER(GetTileOwner(tile))) {
|
||||
|
||||
st = GetStation(_map2[tile]);
|
||||
st = GetStation(_m[tile].m2);
|
||||
SETBITS(st->airport_flags, RUNWAY_IN_block);
|
||||
}
|
||||
}
|
||||
@@ -259,20 +261,20 @@ static void DisasterTick_UFO(Vehicle *v)
|
||||
uint dist;
|
||||
byte z;
|
||||
|
||||
v->u.disaster.image_override = (++v->tick_counter & 8) ? 0xF45 : 0xF44;
|
||||
v->u.disaster.image_override = (++v->tick_counter & 8) ? SPR_UFO_SMALL_SCOUT_DARKER : SPR_UFO_SMALL_SCOUT;
|
||||
|
||||
if (v->current_order.station == 0) {
|
||||
// fly around randomly
|
||||
int x = TileX(v->dest_tile) * 16;
|
||||
int y = TileY(v->dest_tile) * 16;
|
||||
if (abs(x - v->x_pos) + abs(y - v->y_pos) >= 16) {
|
||||
if (abs(x - v->x_pos) + abs(y - v->y_pos) >= 16) {
|
||||
v->direction = GetDirectionTowards(v, x, y);
|
||||
GetNewVehiclePos(v, &gp);
|
||||
SetDisasterVehiclePos(v, gp.x, gp.y, v->z_pos);
|
||||
return;
|
||||
}
|
||||
if (++v->age < 6) {
|
||||
v->dest_tile = TILE_MASK(Random());
|
||||
v->dest_tile = RandomTile();
|
||||
return;
|
||||
}
|
||||
v->current_order.station = 1;
|
||||
@@ -332,11 +334,11 @@ static void DisasterTick_UFO(Vehicle *v)
|
||||
|
||||
static void DestructIndustry(Industry *i)
|
||||
{
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
|
||||
for(tile=0; tile != MapSize(); tile++) {
|
||||
if (IsTileType(tile, MP_INDUSTRY) && _map2[tile] == i->index) {
|
||||
_map_owner[tile] = 0;
|
||||
for (tile = 0; tile != MapSize(); tile++) {
|
||||
if (IsTileType(tile, MP_INDUSTRY) && _m[tile].m2 == i->index) {
|
||||
_m[tile].m1 = 0;
|
||||
MarkTileDirtyByTile(tile);
|
||||
}
|
||||
}
|
||||
@@ -349,7 +351,7 @@ static void DisasterTick_2(Vehicle *v)
|
||||
|
||||
v->tick_counter++;
|
||||
v->u.disaster.image_override =
|
||||
(v->current_order.station == 1 && v->tick_counter&4) ? 0xF4F : 0;
|
||||
(v->current_order.station == 1 && v->tick_counter & 4) ? SPR_F_15_FIRING : 0;
|
||||
|
||||
GetNewVehiclePos(v, &gp);
|
||||
SetDisasterVehiclePos(v, gp.x, gp.y, v->z_pos);
|
||||
@@ -367,9 +369,9 @@ static void DisasterTick_2(Vehicle *v)
|
||||
uint32 r = Random();
|
||||
|
||||
CreateEffectVehicleAbove(
|
||||
x + (r & 0x3F),
|
||||
y + (r >> 6 & 0x3F),
|
||||
(r >> 12 & 0xF),
|
||||
GB(r, 0, 6) + x,
|
||||
GB(r, 6, 6) + y,
|
||||
GB(r, 12, 4),
|
||||
EV_EXPLOSION_SMALL);
|
||||
|
||||
if (++v->age >= 55)
|
||||
@@ -391,7 +393,7 @@ static void DisasterTick_2(Vehicle *v)
|
||||
}
|
||||
} else if (v->current_order.station == 0) {
|
||||
int x,y;
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
int ind;
|
||||
|
||||
x = v->x_pos - 15*16;
|
||||
@@ -400,11 +402,11 @@ static void DisasterTick_2(Vehicle *v)
|
||||
if ( (uint)x > MapMaxX() * 16-1)
|
||||
return;
|
||||
|
||||
tile = TILE_FROM_XY(x,y);
|
||||
tile = TileVirtXY(x, y);
|
||||
if (!IsTileType(tile, MP_INDUSTRY))
|
||||
return;
|
||||
|
||||
v->dest_tile = ind = _map2[tile];
|
||||
v->dest_tile = ind = _m[tile].m2;
|
||||
|
||||
if (GetIndustry(ind)->type == IT_OIL_REFINERY) {
|
||||
v->current_order.station = 1;
|
||||
@@ -420,7 +422,7 @@ static void DisasterTick_3(Vehicle *v)
|
||||
|
||||
v->tick_counter++;
|
||||
v->u.disaster.image_override =
|
||||
(v->current_order.station == 1 && v->tick_counter&4) ? 0xF53 : 0;
|
||||
(v->current_order.station == 1 && v->tick_counter & 4) ? SPR_AH_64A_FIRING : 0;
|
||||
|
||||
GetNewVehiclePos(v, &gp);
|
||||
SetDisasterVehiclePos(v, gp.x, gp.y, v->z_pos);
|
||||
@@ -438,9 +440,9 @@ static void DisasterTick_3(Vehicle *v)
|
||||
uint32 r = Random();
|
||||
|
||||
CreateEffectVehicleAbove(
|
||||
x + (r & 0x3F),
|
||||
y + (r >> 6 & 0x3F),
|
||||
(r >> 12 & 0xF),
|
||||
GB(r, 0, 6) + x,
|
||||
GB(r, 6, 6) + y,
|
||||
GB(r, 12, 4),
|
||||
EV_EXPLOSION_SMALL);
|
||||
|
||||
if (++v->age >= 55)
|
||||
@@ -462,7 +464,7 @@ static void DisasterTick_3(Vehicle *v)
|
||||
}
|
||||
} else if (v->current_order.station == 0) {
|
||||
int x,y;
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
int ind;
|
||||
|
||||
x = v->x_pos - 15*16;
|
||||
@@ -471,11 +473,11 @@ static void DisasterTick_3(Vehicle *v)
|
||||
if ( (uint)x > MapMaxX() * 16-1)
|
||||
return;
|
||||
|
||||
tile = TILE_FROM_XY(x,y);
|
||||
tile = TileVirtXY(x, y);
|
||||
if (!IsTileType(tile, MP_INDUSTRY))
|
||||
return;
|
||||
|
||||
v->dest_tile = ind = _map2[tile];
|
||||
v->dest_tile = ind = _m[tile].m2;
|
||||
|
||||
if (GetIndustry(ind)->type == IT_FACTORY) {
|
||||
v->current_order.station = 1;
|
||||
@@ -490,8 +492,7 @@ static void DisasterTick_3b(Vehicle *v)
|
||||
if (++v->tick_counter & 1)
|
||||
return;
|
||||
|
||||
if (++v->cur_image == 0xF40 + 1)
|
||||
v->cur_image = 0xF3E;
|
||||
if (++v->cur_image > SPR_ROTOR_MOVING_3) v->cur_image = SPR_ROTOR_MOVING_1;
|
||||
|
||||
VehiclePositionChanged(v);
|
||||
BeginVehicleMove(v);
|
||||
@@ -506,7 +507,8 @@ static void DisasterTick_4(Vehicle *v)
|
||||
byte z;
|
||||
Vehicle *u,*w;
|
||||
Town *t;
|
||||
uint tile,tile_org;
|
||||
TileIndex tile;
|
||||
TileIndex tile_org;
|
||||
|
||||
v->tick_counter++;
|
||||
|
||||
@@ -565,7 +567,7 @@ static void DisasterTick_4(Vehicle *v)
|
||||
|
||||
int x = TileX(v->dest_tile) * 16;
|
||||
int y = TileY(v->dest_tile) * 16;
|
||||
if (abs(x - v->x_pos) + abs(y - v->y_pos) >= 16) {
|
||||
if (abs(x - v->x_pos) + abs(y - v->y_pos) >= 16) {
|
||||
v->direction = GetDirectionTowards(v, x, y);
|
||||
GetNewVehiclePos(v, &gp);
|
||||
SetDisasterVehiclePos(v, gp.x, gp.y, v->z_pos);
|
||||
@@ -573,16 +575,16 @@ static void DisasterTick_4(Vehicle *v)
|
||||
}
|
||||
|
||||
if (++v->age < 6) {
|
||||
v->dest_tile = TILE_MASK(Random());
|
||||
v->dest_tile = RandomTile();
|
||||
return;
|
||||
}
|
||||
v->current_order.station = 1;
|
||||
|
||||
tile_org = tile = TILE_MASK(Random());
|
||||
tile_org = tile = RandomTile();
|
||||
do {
|
||||
if (IsTileType(tile, MP_RAILWAY) &&
|
||||
(_map5[tile]&~3)!=0xC0 && IS_HUMAN_PLAYER(_map_owner[tile]))
|
||||
break;
|
||||
(_m[tile].m5 & ~3) != 0xC0 && IS_HUMAN_PLAYER(GetTileOwner(tile)))
|
||||
break;
|
||||
tile = TILE_MASK(tile+1);
|
||||
} while (tile != tile_org);
|
||||
v->dest_tile = tile;
|
||||
@@ -622,16 +624,16 @@ static void DisasterTick_4b(Vehicle *v)
|
||||
for(i=0; i!=80; i++) {
|
||||
uint32 r = Random();
|
||||
CreateEffectVehicleAbove(
|
||||
v->x_pos-32+(r&0x3F),
|
||||
v->y_pos-32+(r>>5&0x3F),
|
||||
GB(r, 0, 6) + v->x_pos - 32,
|
||||
GB(r, 5, 6) + v->y_pos - 32,
|
||||
0,
|
||||
EV_EXPLOSION_SMALL);
|
||||
}
|
||||
|
||||
BEGIN_TILE_LOOP(tile,6,6,v->tile - TILE_XY(3,3))
|
||||
BEGIN_TILE_LOOP(tile, 6, 6, v->tile - TileDiffXY(3, 3))
|
||||
tile = TILE_MASK(tile);
|
||||
DisasterClearSquare(tile);
|
||||
END_TILE_LOOP(tile,6,6,v->tile - TILE_XY(3,3))
|
||||
END_TILE_LOOP(tile, 6, 6, v->tile - TileDiffXY(3, 3))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -640,7 +642,7 @@ static void DisasterTick_5_and_6(Vehicle *v)
|
||||
{
|
||||
uint32 r;
|
||||
GetNewVehiclePosResult gp;
|
||||
uint tile;
|
||||
TileIndex tile;
|
||||
|
||||
v->tick_counter++;
|
||||
|
||||
@@ -664,7 +666,7 @@ static void DisasterTick_5_and_6(Vehicle *v)
|
||||
return;
|
||||
}
|
||||
|
||||
v->direction = (v->direction + ((Random()&1)?2:-2))&7;
|
||||
v->direction = (v->direction + (GB(Random(), 0, 1) ? 2 : -2)) & 7;
|
||||
}
|
||||
|
||||
|
||||
@@ -688,10 +690,6 @@ void DisasterVehicle_Tick(Vehicle *v)
|
||||
_disastervehicle_tick_procs[v->subtype](v);
|
||||
}
|
||||
|
||||
void HandleClickOnDisasterVeh(Vehicle *v)
|
||||
{
|
||||
// not used
|
||||
}
|
||||
|
||||
void OnNewDay_DisasterVehicle(Vehicle *v)
|
||||
{
|
||||
@@ -745,7 +743,7 @@ static void Disaster1_Init(void)
|
||||
x = TileX(Random()) * 16 + 8;
|
||||
|
||||
InitializeDisasterVehicle(v, x, 0, 135, 3, 2);
|
||||
v->dest_tile = TILE_XY(MapSizeX() / 2, MapSizeY() / 2);
|
||||
v->dest_tile = TileXY(MapSizeX() / 2, MapSizeY() / 2);
|
||||
v->age = 0;
|
||||
|
||||
// Allocate shadow too?
|
||||
@@ -840,14 +838,13 @@ static void Disaster4_Init(void)
|
||||
Vehicle *v = ForceAllocateSpecialVehicle(), *u;
|
||||
int x,y;
|
||||
|
||||
if (v == NULL)
|
||||
return;
|
||||
if (v == NULL) return;
|
||||
|
||||
x = TileX(Random()) * 16 + 8;
|
||||
|
||||
y = MapMaxX() * 16 - 1;
|
||||
InitializeDisasterVehicle(v, x, y, 135, 7, 9);
|
||||
v->dest_tile = TILE_XY(MapSizeX() / 2, MapSizeY() / 2);
|
||||
v->dest_tile = TileXY(MapSizeX() / 2, MapSizeY() / 2);
|
||||
v->age = 0;
|
||||
|
||||
// Allocate shadow too?
|
||||
@@ -867,8 +864,7 @@ static void Disaster5_Init(void)
|
||||
byte dir;
|
||||
uint32 r;
|
||||
|
||||
if (v == NULL)
|
||||
return;
|
||||
if (v == NULL) return;
|
||||
|
||||
r = Random();
|
||||
x = TileX(r) * 16 + 8;
|
||||
@@ -888,8 +884,7 @@ static void Disaster6_Init(void)
|
||||
byte dir;
|
||||
uint32 r;
|
||||
|
||||
if (v == NULL)
|
||||
return;
|
||||
if (v == NULL) return;
|
||||
|
||||
r = Random();
|
||||
x = TileX(r) * 16 + 8;
|
||||
@@ -903,31 +898,32 @@ static void Disaster6_Init(void)
|
||||
|
||||
static void Disaster7_Init(void)
|
||||
{
|
||||
int index = GB(Random(), 0, 4);
|
||||
Industry *i;
|
||||
int maxloop = 15;
|
||||
int index = Random() & 0xF;
|
||||
uint m;
|
||||
|
||||
do {
|
||||
for (m = 0; m < 15; m++) {
|
||||
FOR_ALL_INDUSTRIES(i) {
|
||||
if (i->xy != 0 && i->type == IT_COAL_MINE && --index < 0) {
|
||||
if (i->xy != 0 && i->type == IT_COAL_MINE && --index < 0) {
|
||||
|
||||
SetDParam(0, i->town->index);
|
||||
AddNewsItem(STR_B005_COAL_MINE_SUBSIDENCE_LEAVES,
|
||||
NEWS_FLAGS(NM_THIN,NF_VIEWPORT|NF_TILE,NT_ACCIDENT,0), i->xy + TILE_XY(1,1), 0);
|
||||
NEWS_FLAGS(NM_THIN,NF_VIEWPORT|NF_TILE,NT_ACCIDENT,0), i->xy + TileDiffXY(1, 1), 0);
|
||||
|
||||
{
|
||||
uint tile = i->xy;
|
||||
TileIndexDiff step = TileOffsByDir(Random() & 3);
|
||||
int count = 30;
|
||||
do {
|
||||
TileIndex tile = i->xy;
|
||||
TileIndexDiff step = TileOffsByDir(GB(Random(), 0, 2));
|
||||
uint n;
|
||||
|
||||
for (n = 0; n < 30; n++) {
|
||||
DisasterClearSquare(tile);
|
||||
tile = TILE_MASK(tile + step);
|
||||
} while (--count);
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
} while (--maxloop != 0);
|
||||
}
|
||||
}
|
||||
|
||||
static DisasterInitProc * const _disaster_initprocs[] = {
|
||||
@@ -941,60 +937,56 @@ static DisasterInitProc * const _disaster_initprocs[] = {
|
||||
Disaster7_Init,
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
byte min,max;
|
||||
} DisasterYears;
|
||||
|
||||
#define MK(a,b) {a-20,b-20}
|
||||
static const DisasterYears _dis_years[8] = {
|
||||
MK(30,55),
|
||||
MK(40,70),
|
||||
MK(60,90),
|
||||
MK(70,100),
|
||||
MK(100,200),
|
||||
MK(40,65),
|
||||
MK(75,110),
|
||||
MK(50,85),
|
||||
#define MK(a, b) { (a) - MAX_YEAR_BEGIN_REAL, (b) - MAX_YEAR_BEGIN_REAL }
|
||||
static const struct {
|
||||
byte min;
|
||||
byte max;
|
||||
} _dis_years[] = {
|
||||
MK(1930, 1955),
|
||||
MK(1940, 1970),
|
||||
MK(1960, 1990),
|
||||
MK(1970, 2000),
|
||||
MK(2000, 2100),
|
||||
MK(1940, 1965),
|
||||
MK(1975, 2010),
|
||||
MK(1950, 1985)
|
||||
};
|
||||
#undef MK
|
||||
|
||||
|
||||
static void DoDisaster(void)
|
||||
{
|
||||
byte buf[8];
|
||||
byte buf[lengthof(_dis_years)];
|
||||
byte year = _cur_year;
|
||||
int i,j;
|
||||
uint i;
|
||||
uint j;
|
||||
|
||||
for(i=j=0; i!=lengthof(_dis_years); i++) {
|
||||
if (year >= _dis_years[i].min &&
|
||||
year < _dis_years[i].max)
|
||||
buf[j++] = i;
|
||||
j = 0;
|
||||
for (i = 0; i != lengthof(_dis_years); i++) {
|
||||
if (year >= _dis_years[i].min && year < _dis_years[i].max) buf[j++] = i;
|
||||
}
|
||||
|
||||
if (j == 0)
|
||||
return;
|
||||
if (j == 0) return;
|
||||
|
||||
_disaster_initprocs[buf[(uint16)Random() * j >> 16]]();
|
||||
_disaster_initprocs[buf[RandomRange(j)]]();
|
||||
}
|
||||
|
||||
|
||||
static void ResetDisasterDelay(void)
|
||||
{
|
||||
_disaster_delay = (int)(Random() & 0x1FF) + 730;
|
||||
_disaster_delay = GB(Random(), 0, 9) + 730;
|
||||
}
|
||||
|
||||
void DisasterDailyLoop(void)
|
||||
{
|
||||
if (--_disaster_delay != 0)
|
||||
return;
|
||||
if (--_disaster_delay != 0) return;
|
||||
|
||||
ResetDisasterDelay();
|
||||
|
||||
if (_opt.diff.disasters != 0)
|
||||
DoDisaster();
|
||||
if (_opt.diff.disasters != 0) DoDisaster();
|
||||
}
|
||||
|
||||
void StartupDisasters(void)
|
||||
{
|
||||
ResetDisasterDelay();
|
||||
}
|
||||
|
||||
|
||||
+71
-64
@@ -1,7 +1,10 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/sprites.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "window.h"
|
||||
#include "station.h"
|
||||
@@ -10,13 +13,14 @@
|
||||
#include "gfx.h"
|
||||
#include "sound.h"
|
||||
#include "command.h"
|
||||
#include "variables.h"
|
||||
|
||||
static void ShowBuildDockStationPicker(void);
|
||||
static void ShowBuildDocksDepotPicker(void);
|
||||
|
||||
static byte _ship_depot_direction;
|
||||
|
||||
void CcBuildDocks(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
void CcBuildDocks(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||
{
|
||||
if (success) {
|
||||
SndPlayTileFx(SND_02_SPLAT, tile);
|
||||
@@ -24,38 +28,38 @@ void CcBuildDocks(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
}
|
||||
}
|
||||
|
||||
void CcBuildCanal(bool success, uint tile, uint32 p1, uint32 p2)
|
||||
void CcBuildCanal(bool success, TileIndex tile, uint32 p1, uint32 p2)
|
||||
{
|
||||
if (success) SndPlayTileFx(SND_02_SPLAT, tile);
|
||||
}
|
||||
|
||||
|
||||
static void PlaceDocks_Dock(uint tile)
|
||||
static void PlaceDocks_Dock(TileIndex tile)
|
||||
{
|
||||
DoCommandP(tile, 0, 0, CcBuildDocks, CMD_BUILD_DOCK | CMD_AUTO | CMD_MSG(STR_9802_CAN_T_BUILD_DOCK_HERE));
|
||||
}
|
||||
|
||||
static void PlaceDocks_Depot(uint tile)
|
||||
static void PlaceDocks_Depot(TileIndex tile)
|
||||
{
|
||||
DoCommandP(tile, _ship_depot_direction, 0, CcBuildDocks, CMD_BUILD_SHIP_DEPOT | CMD_AUTO | CMD_MSG(STR_3802_CAN_T_BUILD_SHIP_DEPOT));
|
||||
}
|
||||
|
||||
static void PlaceDocks_Buoy(uint tile)
|
||||
static void PlaceDocks_Buoy(TileIndex tile)
|
||||
{
|
||||
DoCommandP(tile, 0, 0, CcBuildDocks, CMD_BUILD_BUOY | CMD_AUTO | CMD_MSG(STR_9835_CAN_T_POSITION_BUOY_HERE));
|
||||
}
|
||||
|
||||
static void PlaceDocks_DemolishArea(uint tile)
|
||||
static void PlaceDocks_DemolishArea(TileIndex tile)
|
||||
{
|
||||
VpStartPlaceSizing(tile, VPM_X_AND_Y | GUI_PlaceProc_DemolishArea);
|
||||
}
|
||||
|
||||
static void PlaceDocks_BuildCanal(uint tile)
|
||||
static void PlaceDocks_BuildCanal(TileIndex tile)
|
||||
{
|
||||
VpStartPlaceSizing(tile, VPM_X_OR_Y);
|
||||
}
|
||||
|
||||
static void PlaceDocks_BuildLock(uint tile)
|
||||
static void PlaceDocks_BuildLock(TileIndex tile)
|
||||
{
|
||||
DoCommandP(tile, 0, 0, CcBuildDocks, CMD_BUILD_LOCK | CMD_AUTO | CMD_MSG(STR_CANT_BUILD_LOCKS));
|
||||
}
|
||||
@@ -63,12 +67,12 @@ static void PlaceDocks_BuildLock(uint tile)
|
||||
|
||||
static void BuildDocksClick_Canal(Window *w)
|
||||
{
|
||||
HandlePlacePushButton(w, 3, SPR_OPENTTD_BASE + 11, 1, PlaceDocks_BuildCanal);
|
||||
HandlePlacePushButton(w, 3, SPR_CURSOR_CANAL, 1, PlaceDocks_BuildCanal);
|
||||
}
|
||||
|
||||
static void BuildDocksClick_Lock(Window *w)
|
||||
{
|
||||
HandlePlacePushButton(w, 4, SPR_OPENTTD_BASE + 64, 1, PlaceDocks_BuildLock);
|
||||
HandlePlacePushButton(w, 4, SPR_CURSOR_LOCK, 1, PlaceDocks_BuildLock);
|
||||
}
|
||||
|
||||
static void BuildDocksClick_Demolish(Window *w)
|
||||
@@ -78,18 +82,18 @@ static void BuildDocksClick_Demolish(Window *w)
|
||||
|
||||
static void BuildDocksClick_Depot(Window *w)
|
||||
{
|
||||
if (HandlePlacePushButton(w, 7, 0x2D1, 1, PlaceDocks_Depot)) ShowBuildDocksDepotPicker();
|
||||
if (HandlePlacePushButton(w, 7, SPR_CURSOR_SHIP_DEPOT, 1, PlaceDocks_Depot)) ShowBuildDocksDepotPicker();
|
||||
}
|
||||
|
||||
static void BuildDocksClick_Dock(Window *w)
|
||||
{
|
||||
|
||||
if (HandlePlacePushButton(w, 8, 0xE54, 3, PlaceDocks_Dock)) ShowBuildDockStationPicker();
|
||||
if (HandlePlacePushButton(w, 8, SPR_CURSOR_DOCK, 3, PlaceDocks_Dock)) ShowBuildDockStationPicker();
|
||||
}
|
||||
|
||||
static void BuildDocksClick_Buoy(Window *w)
|
||||
{
|
||||
HandlePlacePushButton(w, 9, 0x2BE, 1, PlaceDocks_Buoy);
|
||||
HandlePlacePushButton(w, 9, SPR_CURSOR_BOUY, 1, PlaceDocks_Buoy);
|
||||
}
|
||||
|
||||
static void BuildDocksClick_Landscaping(Window *w)
|
||||
@@ -101,7 +105,7 @@ typedef void OnButtonClick(Window *w);
|
||||
static OnButtonClick * const _build_docks_button_proc[] = {
|
||||
BuildDocksClick_Canal,
|
||||
BuildDocksClick_Lock,
|
||||
0,
|
||||
NULL,
|
||||
BuildDocksClick_Demolish,
|
||||
BuildDocksClick_Depot,
|
||||
BuildDocksClick_Dock,
|
||||
@@ -116,12 +120,12 @@ static void BuildDocksToolbWndProc(Window *w, WindowEvent *e)
|
||||
DrawWindowWidgets(w);
|
||||
break;
|
||||
|
||||
case WE_CLICK: {
|
||||
case WE_CLICK:
|
||||
if (e->click.widget - 3 >= 0 && e->click.widget != 5) _build_docks_button_proc[e->click.widget - 3](w);
|
||||
} break;
|
||||
break;
|
||||
|
||||
case WE_KEYPRESS: {
|
||||
switch(e->keypress.keycode) {
|
||||
case WE_KEYPRESS:
|
||||
switch (e->keypress.keycode) {
|
||||
case '1': BuildDocksClick_Canal(w); break;
|
||||
case '2': BuildDocksClick_Lock(w); break;
|
||||
case '3': BuildDocksClick_Demolish(w); break;
|
||||
@@ -129,10 +133,9 @@ static void BuildDocksToolbWndProc(Window *w, WindowEvent *e)
|
||||
case '5': BuildDocksClick_Dock(w); break;
|
||||
case '6': BuildDocksClick_Buoy(w); break;
|
||||
case 'l': BuildDocksClick_Landscaping(w); break;
|
||||
default:
|
||||
return;
|
||||
default: return;
|
||||
}
|
||||
} break;
|
||||
break;
|
||||
|
||||
case WE_PLACE_OBJ:
|
||||
_place_proc(e->place.tile);
|
||||
@@ -147,8 +150,9 @@ static void BuildDocksToolbWndProc(Window *w, WindowEvent *e)
|
||||
if (e->click.pt.x != -1) {
|
||||
if ((e->place.userdata & 0xF) == VPM_X_AND_Y) { // dragged actions
|
||||
GUIPlaceProcDragXY(e);
|
||||
} else if(e->place.userdata == VPM_X_OR_Y)
|
||||
} else if (e->place.userdata == VPM_X_OR_Y) {
|
||||
DoCommandP(e->place.tile, e->place.starttile, 0, CcBuildCanal, CMD_BUILD_CANAL | CMD_AUTO | CMD_MSG(STR_CANT_BUILD_CANALS));
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
@@ -157,24 +161,29 @@ static void BuildDocksToolbWndProc(Window *w, WindowEvent *e)
|
||||
SetWindowDirty(w);
|
||||
|
||||
w = FindWindowById(WC_BUILD_STATION, 0);
|
||||
if (w != NULL) WP(w,def_d).close=true;
|
||||
if (w != NULL) WP(w,def_d).close = true;
|
||||
|
||||
w = FindWindowById(WC_BUILD_DEPOT, 0);
|
||||
if (w != NULL) WP(w,def_d).close=true;
|
||||
if (w != NULL) WP(w,def_d).close = true;
|
||||
break;
|
||||
|
||||
case WE_PLACE_PRESIZE: {
|
||||
uint tile_from, tile_to;
|
||||
TileIndex tile_from;
|
||||
TileIndex tile_to;
|
||||
|
||||
tile_from = tile_to = e->place.tile;
|
||||
switch(GetTileSlope(tile_from, NULL)) {
|
||||
case 3: tile_to += TILE_XY(-1,0); break;
|
||||
case 6: tile_to += TILE_XY(0,-1); break;
|
||||
case 9: tile_to += TILE_XY(0,1); break;
|
||||
case 12:tile_to += TILE_XY(1,0); break;
|
||||
switch (GetTileSlope(tile_from, NULL)) {
|
||||
case 3: tile_to += TileDiffXY(-1, 0); break;
|
||||
case 6: tile_to += TileDiffXY( 0, -1); break;
|
||||
case 9: tile_to += TileDiffXY( 0, 1); break;
|
||||
case 12: tile_to += TileDiffXY( 1, 0); break;
|
||||
}
|
||||
VpSetPresizeRange(tile_from, tile_to);
|
||||
} break;
|
||||
|
||||
case WE_DESTROY:
|
||||
if (_patches.link_terraform_toolbar) DeleteWindowById(WC_SCEN_LAND_GEN, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -208,42 +217,44 @@ void ShowBuildDocksToolbar(void)
|
||||
if (_current_player == OWNER_SPECTATOR) return;
|
||||
DeleteWindowById(WC_BUILD_TOOLBAR, 0);
|
||||
AllocateWindowDesc(&_build_docks_toolbar_desc);
|
||||
if (_patches.link_terraform_toolbar) ShowTerraformToolbar();
|
||||
}
|
||||
|
||||
static void BuildDockStationWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
int rad;
|
||||
|
||||
switch(e->event) {
|
||||
switch (e->event) {
|
||||
case WE_PAINT: {
|
||||
if (WP(w,def_d).close)
|
||||
return;
|
||||
int rad;
|
||||
|
||||
if (WP(w,def_d).close) return;
|
||||
w->click_state = (1<<3) << _station_show_coverage;
|
||||
DrawWindowWidgets(w);
|
||||
if (_patches.modified_catchment) {
|
||||
rad = CA_DOCK;
|
||||
} else {
|
||||
rad = 4;
|
||||
}
|
||||
|
||||
if (_station_show_coverage) SetTileSelectBigSize(-rad, -rad, 2 * rad, 2 * rad);
|
||||
else SetTileSelectBigSize(0, 0, 0, 0);
|
||||
rad = (_patches.modified_catchment) ? CA_DOCK : 4;
|
||||
|
||||
if (_station_show_coverage) {
|
||||
SetTileSelectBigSize(-rad, -rad, 2 * rad, 2 * rad);
|
||||
} else {
|
||||
SetTileSelectBigSize(0, 0, 0, 0);
|
||||
}
|
||||
|
||||
DrawStringCentered(74, 17, STR_3066_COVERAGE_AREA_HIGHLIGHT, 0);
|
||||
DrawStationCoverageAreaText(4, 50, (uint)-1, rad);
|
||||
} break;
|
||||
break;
|
||||
}
|
||||
|
||||
case WE_CLICK: {
|
||||
switch(e->click.widget) {
|
||||
case 3: case 4:
|
||||
_station_show_coverage = e->click.widget - 3;
|
||||
SndPlayFx(SND_15_BEEP);
|
||||
SetWindowDirty(w);
|
||||
break;
|
||||
case WE_CLICK:
|
||||
switch (e->click.widget) {
|
||||
case 3:
|
||||
case 4:
|
||||
_station_show_coverage = e->click.widget - 3;
|
||||
SndPlayFx(SND_15_BEEP);
|
||||
SetWindowDirty(w);
|
||||
break;
|
||||
}
|
||||
} break;
|
||||
break;
|
||||
|
||||
case WE_MOUSELOOP: {
|
||||
case WE_MOUSELOOP:
|
||||
if (WP(w,def_d).close) {
|
||||
DeleteWindow(w);
|
||||
return;
|
||||
@@ -251,11 +262,9 @@ static void BuildDockStationWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
CheckRedrawStationCoverage(w);
|
||||
break;
|
||||
}
|
||||
|
||||
case WE_DESTROY:
|
||||
if (!WP(w,def_d).close)
|
||||
ResetObjectToPlace();
|
||||
if (!WP(w,def_d).close) ResetObjectToPlace();
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -264,8 +273,8 @@ static const Widget _build_dock_station_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 7, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 147, 0, 13, STR_3068_DOCK, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 147, 14, 74, 0x0, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 14, 73, 30, 40, STR_02DB_OFF, STR_3065_DON_T_HIGHLIGHT_COVERAGE},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 74, 133, 30, 40, STR_02DA_ON, STR_3064_HIGHLIGHT_COVERAGE_AREA},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 14, 73, 30, 40, STR_02DB_OFF, STR_3065_DON_T_HIGHLIGHT_COVERAGE},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 74, 133, 30, 40, STR_02DA_ON, STR_3064_HIGHLIGHT_COVERAGE_AREA},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -293,7 +302,7 @@ static void UpdateDocksDirection(void)
|
||||
|
||||
static void BuildDocksDepotWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
switch (e->event) {
|
||||
case WE_PAINT:
|
||||
w->click_state = (1<<3) << _ship_depot_direction;
|
||||
DrawWindowWidgets(w);
|
||||
@@ -305,7 +314,7 @@ static void BuildDocksDepotWndProc(Window *w, WindowEvent *e)
|
||||
return;
|
||||
|
||||
case WE_CLICK: {
|
||||
switch(e->click.widget) {
|
||||
switch (e->click.widget) {
|
||||
case 3:
|
||||
case 4:
|
||||
_ship_depot_direction = e->click.widget - 3;
|
||||
@@ -317,13 +326,11 @@ static void BuildDocksDepotWndProc(Window *w, WindowEvent *e)
|
||||
} break;
|
||||
|
||||
case WE_MOUSELOOP:
|
||||
if (WP(w,def_d).close)
|
||||
DeleteWindow(w);
|
||||
if (WP(w,def_d).close) DeleteWindow(w);
|
||||
break;
|
||||
|
||||
case WE_DESTROY:
|
||||
if (!WP(w,def_d).close)
|
||||
ResetObjectToPlace();
|
||||
if (!WP(w,def_d).close) ResetObjectToPlace();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,54 +1,50 @@
|
||||
Compiling OpenTTD using Microsoft Visual C++ 6.0
|
||||
|
||||
|
||||
---Step 1
|
||||
Step 1: Ingredients
|
||||
|
||||
Download the following files:
|
||||
|
||||
* Useful.zip (http://sourceforge.net/project/showfiles.php?group_id=103924&package_id=114307&release_id=228633)
|
||||
* SDL-1.2.8-VC6.zip (http://www.libsdl.org/release/SDL-devel-1.2.8-VC6.zip)
|
||||
* DirectX7.0 SDK (http://www.tt-forums.net/download.php?id=15989) (or alternatively the latest DirectX SDK from Microsoft)
|
||||
* afxres.h (http://www-d0.fnal.gov/d0dist/dist/packages/d0ve/devel/windows/AFXRES.H)
|
||||
* Openttd-useful.zip (http://sourceforge.net/project/showfiles.php?group_id=103924&package_id=114307&release_id=228633)
|
||||
* DirectX 8.1 SDK (http://neuron.tuke.sk/~mizanin/eng/Dx81sdk-include-lib.rar) (or alternatively the latest DirectX SDK from Microsoft)
|
||||
* The February 2003 Microsoft Platform SDK (http://www.microsoft.com/msdownload/platformsdk/sdkupdate/XPSP2FULLInstall.htm) (newer SDK's do not work with MSVC6)
|
||||
* afxres.h (http://www-d0.fnal.gov/d0dist/dist/packages/d0ve/devel/windows/AFXRES.H) (maybe you not need this)
|
||||
|
||||
...and of course the newest source from svn://svn.openttd.com/trunk
|
||||
...and of course the newest source from svn://svn.openttd.org/trunk
|
||||
|
||||
(The alpha version of the new map array can be found at svn://svn.openttd.com/branch/map)
|
||||
You have to have a SVN-client to download the source:
|
||||
|
||||
You have to have and SVN-client to download the source:
|
||||
* Command line version (Subversion 1.2.3 Win32 binaries) (http://subversion.tigris.org/servlets/ProjectDocumentList?folderID=91)
|
||||
* GUI TortoiseSVN (http://tortoisesvn.tigris.org/download.html)
|
||||
|
||||
* Command line version (http://subversion.tigris.org/servlets/ProjectDocumentList?folderID=91)
|
||||
* TortoiseSVN (http://tortoisesvn.tigris.org/download.html)
|
||||
Step 2: Includes and Libraries
|
||||
|
||||
|
||||
---Step 2
|
||||
|
||||
Put the newly downloaded files in the VC lib and include directories (Where C:\program files\ is your local location of VC)
|
||||
Put the newly downloaded files in the VC lib and include directories (Where "C:\Program Files\Microsoft Visual Studio\VC98" is your local location of VC)
|
||||
|
||||
|
||||
* zconf.h [useful.zip]
|
||||
* zlib.h [useful.zip]
|
||||
* png.h [useful.zip]
|
||||
* pngconf.h [useful.zip]
|
||||
* afxres.h
|
||||
* afxres.h
|
||||
|
||||
in
|
||||
|
||||
C:\Program Files\Microsoft Visual Studio\VC98\Include
|
||||
C:\Program Files\Microsoft Visual Studio\VC98\Include
|
||||
|
||||
and
|
||||
|
||||
* zlibstat.lib [useful.zip]
|
||||
* SDL.lib [SDL.zip]
|
||||
* libpng.lib [useful.zip]
|
||||
* libpng.lib [useful.zip]
|
||||
|
||||
in
|
||||
|
||||
C:\Program Files\Microsoft Visual Studio\VC98\Lib
|
||||
C:\Program Files\Microsoft Visual Studio\VC98\Lib
|
||||
|
||||
|
||||
---Step 3: DirectX SDK
|
||||
Step 3: DirectX SDK
|
||||
|
||||
(This should work with the latest DirectX SDK as well.) The installation with DirectX 7 was odd, so you'd better use the version available via the forum, see also the download link on top.
|
||||
(This should work with the latest DirectX SDK as well.)
|
||||
|
||||
There are 2 folder in the compressed file: Include and Lib
|
||||
|
||||
@@ -62,16 +58,17 @@ C:\Program Files\Microsoft Visual Studio\VC98\Lib
|
||||
|
||||
|
||||
|
||||
You can also make custom directories, for libraries (.lib) and includes/header files (.h) and add it to the VC paths via:
|
||||
You can also make custom directories, which is recommended so you don't overwrite VS6 files, for libraries (.lib) and includes/header files (.h) and add it to the VC paths via:
|
||||
|
||||
Tools -> Options -> Directories -> show directories for:
|
||||
|
||||
a) include files (the include dir: C:\Program Files\Microsoft Visual Studio\VC98\DirectX 7 SDK\include )
|
||||
a) include files (the include dir: C:\Program Files\Microsoft Visual Studio\VC98\DirectX 8.1 SDK\include )
|
||||
|
||||
b) library files (the lib dir, C:\Program Files\Microsoft Visual Studio\VC98\DirectX 7 SDK\lib )
|
||||
b) library files (the lib dir, C:\Program Files\Microsoft Visual Studio\VC98\DirectX 8.1 SDK\lib )
|
||||
|
||||
NOTE: make sure that the directory for the DirectX SDK is the first one in the list, above all others, otherwise compilation will most likely fail!!
|
||||
|
||||
---Step 4
|
||||
Step 4: TTD Graphics files
|
||||
|
||||
Copy the following files from Transport Tycoon Deluxe to the data folder
|
||||
|
||||
@@ -80,14 +77,14 @@ Copy the following files from Transport Tycoon Deluxe to the data folder
|
||||
* trgcr.grf
|
||||
* trghr.grf
|
||||
* trgir.grf
|
||||
* trgtr.grf
|
||||
* trgtr.grf
|
||||
|
||||
|
||||
---Step 5
|
||||
Step 5: Compiling
|
||||
|
||||
Open trunk/ttd.dsw
|
||||
Open trunk/openttd.dsw
|
||||
|
||||
Build menu > Set active configuration > Select: "ttd - Win32 Release with PNG"
|
||||
Build menu > Set active configuration > Select: "openttd - Win32 Release"
|
||||
|
||||
Compile...
|
||||
|
||||
@@ -96,10 +93,12 @@ Now it should work, it worked for me :)
|
||||
|
||||
From r1319 you can compile branch/map in Debug mode (by Bociusz)
|
||||
|
||||
If it's not working, and you checked that you using the newest SVN (!) report to Bociusz on IRC (irc://irc.freenode.net/#openttd)
|
||||
For compiling branch/cargo-packets you have to add cargo.c and .h to this tree's openttd.dsp
|
||||
|
||||
If it's not working, and you checked that you using the newest SVN (!) report to Bociusz on IRC (irc://irc.freenode.net/openttd)
|
||||
|
||||
Go ahead and make that patch! Happy Hacking! :)
|
||||
|
||||
Originally written by Dribbel
|
||||
|
||||
Project file updating by Bociusz
|
||||
Project file updating by Bociusz
|
||||
|
||||
+120
-110
@@ -11,7 +11,17 @@
|
||||
|
||||
<h3><a name="Landscape">Landscape</a></h3>
|
||||
<p>
|
||||
Five arrays are used to encode the information of the contents of each tile. These arrays are referred to as "<span style="font-weight: bold;">map_owner</span>", "<span style="font-weight: bold;">map2</span>", "<span style="font-weight: bold;">map3_lo|_hi</span>", "<span style="font-weight: bold;">map_type_and_height</span>" and "<span style="font-weight: bold;">map5</span>". The known encodings are listed in the table below. The most important value is the class of a tile, stored in the upper 4 bits of the type_and_height array. The lower 4 bits are used to encode the height and slope data. For a graphical represenation of the tile-layout have a look at <a href="landscape_grid.html">Landscape grid</a> page.
|
||||
Five attributes hold the information about a tile.
|
||||
These attributes are referred to as
|
||||
"<span style="font-weight: bold;">type_height</span>",
|
||||
"<span style="font-weight: bold;">m1</span>",
|
||||
"<span style="font-weight: bold;">m2</span>",
|
||||
"<span style="font-weight: bold;">m3</span>",
|
||||
"<span style="font-weight: bold;">m4</span>" and
|
||||
"<span style="font-weight: bold;">m5</span>".
|
||||
The most important value is the class of a tile, stored in the upper 4 bits of the type_height array.
|
||||
The lower 4 bits are used to encode the height and slope data.
|
||||
For a graphical represenation of the tile-layout have a look at <a href="landscape_grid.html">Landscape grid</a> page.
|
||||
</p>
|
||||
<p>
|
||||
OTTD's class-specific periodic tile processing routine is called once every +256 ticks for each tile.
|
||||
@@ -22,7 +32,7 @@ OTTD's class-specific periodic tile processing routine is called once every +256
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class0"><tt> 0 </tt></a></td><td>
|
||||
<ul>
|
||||
<li>map5 bits 4..0: tile type:
|
||||
<li>m5 bits 4..0: tile type:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt> </td><td align=left>bare land</td></tr>
|
||||
<tr><td nowrap valign=top><tt>01</tt> </td><td align=left>1/3 grass</td></tr>
|
||||
@@ -30,7 +40,7 @@ OTTD's class-specific periodic tile processing routine is called once every +256
|
||||
<tr><td nowrap valign=top><tt>03</tt> </td><td align=left>full grass</td></tr>
|
||||
<tr><td nowrap valign=top><tt>07</tt> </td><td align=left>rough land</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0B</tt> </td><td align=left>rocks</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0F</tt> </td><td align=left>fields; type of fields in map3_lo bits 3..0 (legal values: 0 through 9)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0F</tt> </td><td align=left>fields; type of fields in m3 bits 3..0 (legal values: 0 through 9)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>10</tt> </td><td align=left>1/4 snow</td></tr>
|
||||
<tr><td nowrap valign=top><tt>11</tt> </td><td align=left>2/4 snow</td></tr>
|
||||
<tr><td nowrap valign=top><tt>12</tt> </td><td align=left>3/4 snow</td></tr>
|
||||
@@ -39,20 +49,20 @@ OTTD's class-specific periodic tile processing routine is called once every +256
|
||||
<tr><td nowrap valign=top><tt>17</tt> </td><td align=left>full desert</td></tr>
|
||||
</table>
|
||||
</li>
|
||||
<li>map5 bits 7..6: update counter, incremented on every periodic processing for tile types other than <tt>03</tt>, <tt>07</tt>, <tt>0B</tt> and <tt>10</tt> and above, on wraparound the tile is updated (for fields, the type of fields in map3_lo is increased, for other types the tile type in map5 is increased)
|
||||
<li>m5 bits 7..5: update counter, incremented on every periodic processing for tile types other than <tt>03</tt>, <tt>07</tt>, <tt>0B</tt> and <tt>10</tt> and above, on wraparound the tile is updated (for fields, the type of fields in m3 is increased, for other types the tile type in m5 is increased)
|
||||
<br>(for snow and desert, these bits are not used, tile is updated on every periodic processing)
|
||||
</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the tile (normally <tt>10</tt>)
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the tile (normally <tt>10</tt>)
|
||||
</li>
|
||||
<li>map3_hi bits 7..5: type of hedge on the SW border of the tile (1 through 6, or 0=none); bits 4..2: same for the SE border
|
||||
<li>m4 bits 7..5: type of hedge on the SW border of the tile (1 through 6, or 0=none); bits 4..2: same for the SE border
|
||||
</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class1"><tt> 1 </tt></a></td><td>
|
||||
map5 bit 7 clear: railway track
|
||||
m5 bit 7 clear: railway track
|
||||
<ul>
|
||||
<li>map5 bits 0..5: track layout: bit set = track present:
|
||||
<li>m5 bits 0..5: track layout: bit set = track present:
|
||||
<table>
|
||||
<tr><td nowrap valign=top>bit 0: </td><td align=left>in the X direction</td></tr>
|
||||
<tr><td nowrap valign=top>bit 1: </td><td align=left>in the Y direction</td></tr>
|
||||
@@ -61,9 +71,9 @@ map5 bit 7 clear: railway track
|
||||
<tr><td nowrap valign=top>bit 4: </td><td align=left>in the west corner (direction N-S)</td></tr>
|
||||
<tr><td nowrap valign=top>bit 5: </td><td align=left>in the east corner (direction N-S)</td></tr>
|
||||
</table></li>
|
||||
<li>map5 bit 6 set = with signals:
|
||||
<li>m5 bit 6 set = with signals:
|
||||
<ul>
|
||||
<li>map3_lo bits 7..4: bit set = signal present:
|
||||
<li>m3 bits 7..4: bit set = signal present:
|
||||
<ul>
|
||||
<li>For track in the X direction:
|
||||
<table>
|
||||
@@ -90,8 +100,8 @@ map5 bit 7 clear: railway track
|
||||
<tr><td nowrap valign=top>bit 7: </td><td align=left>signal in the N direction on the track in the W corner</td></tr>
|
||||
</table></li>
|
||||
</ul></li>
|
||||
<li>map2 bits 7..4: bit clear = signal shows red; same bits as in map3_lo</li>
|
||||
<li>OpenTTD bits in map3_hi:
|
||||
<li>m2 bits 7..4: bit clear = signal shows red; same bits as in m3</li>
|
||||
<li>OpenTTD bits in m4:
|
||||
<table>
|
||||
<tr><td nowrap valign=top>bits 1..0: </td><td align=left>type of signal:</td></tr>
|
||||
<tr><td nowrap valign=top><tt>00</tt>: </td><td align=left>normal signals</td></tr>
|
||||
@@ -101,9 +111,9 @@ map5 bit 7 clear: railway track
|
||||
<tr><td nowrap valign=top>bit 2: </td><td align=left>set = semaphore signals, clear = light signals</td></tr>
|
||||
</table></li>
|
||||
</ul></li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the track
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the track
|
||||
</li>
|
||||
<li>map2 bits 0..3:
|
||||
<li>m2 bits 0..3:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>0</tt> </td><td align=left>on bare land</td></tr>
|
||||
<tr><td nowrap valign=top><tt>1</tt> </td><td align=left>on grass, no fences</td></tr>
|
||||
@@ -119,64 +129,64 @@ map5 bit 7 clear: railway track
|
||||
<tr><td nowrap valign=top><tt>B</tt> </td><td align=left>fence on the N side (track in the S corner)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>C</tt> </td><td align=left>on snow or desert</td></tr>
|
||||
</table></li>
|
||||
<li>map3_lo bits 0..3 = <a name="TrackType">track type</a>: <tt>0</tt> - conventional railway, <tt>1</tt> - monorail, <tt>2</tt> - maglev
|
||||
</li>
|
||||
<li>m3 bits 0..3 = <a name="TrackType">track type</a>: <tt>0</tt> - conventional railway, <tt>1</tt> - monorail, <tt>2</tt> - maglev
|
||||
</ul>
|
||||
map5 bits 7 and 6 set: railway depot / checkpoints
|
||||
m5 bits 7 and 6 set: railway depot / checkpoints
|
||||
<ul>
|
||||
<li>map5 value C0..C3: railway depot
|
||||
<br>map5 bits 1..0 - direction: exit towards: <tt>00</tt> = NE, <tt>01</tt> = SE, <tt>02</tt> = SW, <tt>03</tt> = NW</li>
|
||||
<li>map5 value C4..C5: checkpoint
|
||||
<li>m5 value C0..C3: railway depot
|
||||
<br>m5 bits 1..0 - direction: exit towards: <tt>00</tt> = NE, <tt>01</tt> = SE, <tt>02</tt> = SW, <tt>03</tt> = NW</li>
|
||||
<li>m5 value C4..C5: checkpoint
|
||||
<br>bit 0: clear = in X direction, set = in Y direction
|
||||
<br>
|
||||
<br>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the depot / checkpoint</li>
|
||||
<li>map3_lo bits 0..3 = <a href="#TrackType">track type</a></li>
|
||||
<li>map3_lo bit 4 = use custom sprite (valid only for the checkpoint)</li>
|
||||
<li>map3_hi = custom station id</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the depot / checkpoint</li>
|
||||
<li>m2: For waypoints, index into the array of waypoints.</li>
|
||||
<li>m3 bits 0..3 = <a href="#TrackType">track type</a></li>
|
||||
<li>m3 bit 4 = use custom sprite (valid only for the checkpoint)</li>
|
||||
<li>m4 bits 0..3 = ground type, as per m2 bits 0..3 for railway tiles.</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class2"><tt> 2 </tt></a></td><td>
|
||||
map5 bits 7..4 clear: road
|
||||
m5 bits 7..4 clear: road
|
||||
<ul>
|
||||
<li>map5 bits 3..0: road layout: bit set = road piece present:
|
||||
<li>m5 bits 3..0: road layout: bit set = road piece present:
|
||||
<table>
|
||||
<tr><td nowrap valign=top>bit 0: </td><td align=left>NW piece</td></tr>
|
||||
<tr><td nowrap valign=top>bit 1: </td><td align=left>SW piece</td></tr>
|
||||
<tr><td nowrap valign=top>bit 2: </td><td align=left>SE piece</td></tr>
|
||||
<tr><td nowrap valign=top>bit 3: </td><td align=left>NE piece</td></tr>
|
||||
</table></li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the road</li>
|
||||
<li>map2: Index into the array of towns, 0 for non-town roads</li>
|
||||
<li>map3_hi bits 0..3: counter for the roadworks</li>
|
||||
<li>map3_hi bits 4..6: <tt>0</tt> - on bare land, <tt>1</tt> - on grass, <tt>2</tt> - paved, <tt>3</tt> - with streetlights, <tt>5</tt> - tree-lined, <tt>6</tt> - on grass with road works, <tt>7</tt> - paved with road works</li>
|
||||
<li>map3_hi bit 7 set = on snow or desert</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the road</li>
|
||||
<li>m2: Index into the array of towns, 0 for non-town roads</li>
|
||||
<li>m4 bits 0..3: counter for the roadworks</li>
|
||||
<li>m4 bits 4..6: <tt>0</tt> - on bare land, <tt>1</tt> - on grass, <tt>2</tt> - paved, <tt>3</tt> - with streetlights, <tt>5</tt> - tree-lined, <tt>6</tt> - on grass with road works, <tt>7</tt> - paved with road works</li>
|
||||
<li>m4 bit 7 set = on snow or desert</li>
|
||||
</ul>
|
||||
map5 bit 4 set, bits 7..5 clear: level crossing
|
||||
m5 bit 4 set, bits 7..5 clear: level crossing
|
||||
<ul>
|
||||
<li>map5 bit 3: clear - road in the X direction, set - road in the Y direction (railway track always perpendicular)</li>
|
||||
<li>map5 bit 2: set if crossing lights are on</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the railway track</li>
|
||||
<li>map2: Index into the array of towns, 0 for non-town roads</li>
|
||||
<li>map3_lo bits 0..7: <a href="#OwnershipInfo">owner</a> of the road</li>
|
||||
<li>map3_hi bits 3..0: <a href="#TrackType">track type</a></li>
|
||||
<li>map3_hi bits 4..6: <tt>0</tt> - on bare land, <tt>1</tt> - on grass, <tt>2</tt> or higher - paved</li>
|
||||
<li>map3_hi bit 7 set = on snow or desert</li>
|
||||
<li>m5 bit 3: clear - road in the X direction, set - road in the Y direction (railway track always perpendicular)</li>
|
||||
<li>m5 bit 2: set if crossing lights are on</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the railway track</li>
|
||||
<li>m2: Index into the array of towns, 0 for non-town roads</li>
|
||||
<li>m3 bits 0..7: <a href="#OwnershipInfo">owner</a> of the road</li>
|
||||
<li>m4 bits 3..0: <a href="#TrackType">track type</a></li>
|
||||
<li>m4 bits 4..6: <tt>0</tt> - on bare land, <tt>1</tt> - on grass, <tt>2</tt> or higher - paved</li>
|
||||
<li>m4 bit 7 set = on snow or desert</li>
|
||||
</ul>
|
||||
map5 bit 5 set: road depot
|
||||
m5 bit 5 set: road depot
|
||||
<ul>
|
||||
<li>map5 bits 3..0 - direction: exit towards: <tt>0</tt> = NE, <tt>1</tt> = SE, <tt>2</tt> = SW, <tt>3</tt> = NW</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the depot</li>
|
||||
<li>map3_hi bit 7 set = on snow or desert (not displayed, but set internally)</li>
|
||||
<li>m5 bits 3..0 - direction: exit towards: <tt>0</tt> = NE, <tt>1</tt> = SE, <tt>2</tt> = SW, <tt>3</tt> = NW</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the depot</li>
|
||||
<li>m4 bit 7 set = on snow or desert (not displayed, but set internally)</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class3"><tt> 3 </tt></a></td><td>
|
||||
Town building
|
||||
<ul>
|
||||
<li>map2: Index into the array of towns</li>
|
||||
<li>map3_hi: <a name="HouseTypes">town building type</a>:
|
||||
<li>m2: Index into the array of towns</li>
|
||||
<li>m4: <a name="HouseTypes">town building type</a>:
|
||||
<p><small>Note: In the climate list, 'sub-arctic' means below the <a href="#_snowline">snow line</a>, and 'snow' means above the snow line in the sub-arctic climate.</small></p>
|
||||
<table>
|
||||
<tr><th align=left>Type </th><th align=left>Size </th><th align=left>Climates </th><th align=left>Description</th></tr>
|
||||
@@ -266,13 +276,13 @@ Town building
|
||||
<tr><td nowrap valign=top><tt>6D</tt> </td><td>1×1</td><td>toyland</td><td align=left>piggy-bank</td></tr>
|
||||
<tr><td colspan=2></td></tr> <!-- spacer -- -- (and I don't mean a walk) -->
|
||||
</table></li>
|
||||
<li>map3_lo bits 7..6: stage of construction (<tt>3</tt> = completed)</li>
|
||||
<li>map5 bits 2..0: construction counter, for buildings under construction incremented on every periodic tile processing, on wraparound the stage of construction in map3_lo is increased</li>
|
||||
<li>m3 bits 7..6: stage of construction (<tt>3</tt> = completed)</li>
|
||||
<li>m5 bits 2..0: construction counter, for buildings under construction incremented on every periodic tile processing, on wraparound the stage of construction in m3 is increased</li>
|
||||
<li>for large office blocks (types <tt>04</tt> and <tt>05</tt>):
|
||||
<ul>
|
||||
<li>map_owner bits 6..0: position of the lift</li>
|
||||
<li>map_owner bit 7: if set the lift is moving</li>
|
||||
<li>map5 bit 7: if set then map5 bits 5..0 hold the final position of the lift divided by 6 (valid values 0..6 except 1)</li>
|
||||
<li>m1 bits 6..0: position of the lift</li>
|
||||
<li>m1 bit 7: if set the lift is moving</li>
|
||||
<li>m5 bit 7: if set then m5 bits 5..0 hold the destination floor of the lift, which could be 0..6, except 1, so the building has 6 effective floors. This due to the fact that the first floor is 2 'normal' floors high. One 'normal' floor has a height of 6 lift positions.</li>
|
||||
</ul></li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
@@ -280,9 +290,9 @@ Town building
|
||||
<tr><td valign=top nowrap><a name="Class4"><tt> 4 </tt></a></td><td>
|
||||
Trees
|
||||
<ul>
|
||||
<li>map5 bits 7..6: number of trees minus one</li>
|
||||
<li>map5 bits 2..0: growth status: <tt>0</tt>..<tt>2</tt> - one of trees is growing, <tt>3</tt> - all trees are fully grown, <tt>4</tt>..<tt>6</tt> - one of trees is withering</li>
|
||||
<li>map3_lo bits 7..0: type of trees:
|
||||
<li>m5 bits 7..6: number of trees minus one</li>
|
||||
<li>m5 bits 2..0: growth status: <tt>0</tt>..<tt>2</tt> - one of trees is growing, <tt>3</tt> - all trees are fully grown, <tt>4</tt>..<tt>6</tt> - one of trees is withering</li>
|
||||
<li>m3 bits 7..0: type of trees:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt>..<tt>0B</tt> </td><td align=left>temperate climate trees</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0C</tt>..<tt>13</tt> </td><td align=left>sub-arctic climate trees</td></tr>
|
||||
@@ -293,24 +303,24 @@ Trees
|
||||
</table>
|
||||
(note: the actually displayed set of trees depends on both type and number of trees)
|
||||
</li>
|
||||
<li>map3_hi bits 7..5: type of hedge on the SW border of the tile (1 through 6, or 0=none)</li>
|
||||
<li>map3_hi bits 4..2: type of hedge on the SE border of the tile (1 through 6, or 0=none)</li>
|
||||
<li>map2 bits 5..4:
|
||||
<li>m4 bits 7..5: type of hedge on the SW border of the tile (1 through 6, or 0=none)</li>
|
||||
<li>m4 bits 4..2: type of hedge on the SE border of the tile (1 through 6, or 0=none)</li>
|
||||
<li>m2 bits 5..4:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>0</tt> </td><td align=left>on grass</td></tr>
|
||||
<tr><td nowrap valign=top><tt>1</tt> </td><td align=left>on rough land</td></tr>
|
||||
<tr><td nowrap valign=top><tt>2</tt> </td><td align=left>on snow or desert; map2 bits 7..6 - amount of snow or desert (for desert always set to 3 in TTD)
|
||||
<tr><td nowrap valign=top><tt>2</tt> </td><td align=left>on snow or desert; m2 bits 7..6 - amount of snow or desert (for desert always set to 3 in TTD)
|
||||
</td></tr>
|
||||
</table></li>
|
||||
<li>map2 bits 3..0: update counter, incremented on every periodic processing, on wraparound the growth status is updated (or, if it's <tt>3</tt>, a random action is taken)</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> (normally <tt>10</tt>)</li>
|
||||
<li>m2 bits 3..0: update counter, incremented on every periodic processing, on wraparound the growth status is updated (or, if it's <tt>3</tt>, a random action is taken)</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> (normally <tt>10</tt>)</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class5"><tt> 5 </tt></a></td><td>
|
||||
Station tile
|
||||
<ul>
|
||||
<li>map5: tile type:
|
||||
<li>m5: tile type:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt>..<tt>07</tt> </td><td align=left>railway station
|
||||
<br><tt>00</tt>..<tt>01</tt> - open platform, <tt>02</tt>..<tt>03</tt> - open platform with station building, <tt>04</tt>....<tt>07</tt> - roofed platform
|
||||
@@ -368,17 +378,17 @@ exit towards: <tt>47</tt> - NE, <tt>48</tt> - SE, <tt>49</tt> - SW, <tt>4A</tt>
|
||||
<tr><td colspan=2></td></tr> <!-- spacer -->
|
||||
</table>
|
||||
</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the station</li>
|
||||
<li>map2: index into the <a href="#_StationArray">array of stations</a></li>
|
||||
<li>map3_lo bits 0..3: <a href="#TrackType">track type</a> for railway stations, must be 0 for all the other stations</li>
|
||||
<li>map3_lo bit 4 = use custom sprite (valid only railway stations FOR NOW)</li>
|
||||
<li>map3_hi = custom station id</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the station</li>
|
||||
<li>m2: index into the <a href="#_StationArray">array of stations</a></li>
|
||||
<li>m3 bits 0..3: <a href="#TrackType">track type</a> for railway stations, must be 0 for all the other stations</li>
|
||||
<li>m3 bit 4 = use custom sprite (valid only railway stations FOR NOW)</li>
|
||||
<li>m4 = custom station id</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class6"><tt> 6 </tt></a></td><td>
|
||||
<ul>
|
||||
<li>map5: tile type:
|
||||
<li>m5: tile type:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt> </td><td align=left>water</td></tr>
|
||||
<tr><td nowrap valign=top><tt>01</tt> </td><td align=left>coast or riverbank</td></tr>
|
||||
@@ -409,7 +419,7 @@ exit towards: <tt>47</tt> - NE, <tt>48</tt> - SE, <tt>49</tt> - SW, <tt>4A</tt>
|
||||
</table>
|
||||
</td></tr>
|
||||
</table></li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> (for water and coasts normally <tt>11</tt>)</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> (for water and coasts normally <tt>11</tt>)</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
@@ -423,19 +433,19 @@ Tiles of this class form an invisible, one tile wide border at the south (bottom
|
||||
<tr><td valign=top nowrap><a name="Class8"><tt> 8 </tt></a></td><td>
|
||||
Industry tile
|
||||
<ul>
|
||||
<li>map5: type:
|
||||
<li>m5: type:
|
||||
<br><small>(note: this is not the same as the <a href="#industry.type">industry type</a> stored in the <a href="#_IndustryArray">array of industries</a>)</small>
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt>..<tt>06</tt> </td><td align=left>coal mine
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt> </td><td align=left>wheel tower when not animated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>01</tt> </td><td align=left>wheel tower when animated; animation state in map_owner bits 5..0; map_owner bit 6 set = sound already generated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>01</tt> </td><td align=left>wheel tower when animated; animation state in m1 bits 5..0; m1 bit 6 set = sound already generated</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>07</tt>..<tt>0A</tt> </td><td align=left>power station
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>08</tt> </td><td align=left>chimney</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0A</tt> </td><td align=left>transformer; animation progress in map_owner bits 5..2 (valid range <tt>0</tt>..<tt>7</tt>)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0A</tt> </td><td align=left>transformer; animation progress in m1 bits 5..2 (valid range <tt>0</tt>..<tt>7</tt>)</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>0B</tt>..<tt>0F</tt> </td><td align=left>sawmill</td></tr>
|
||||
@@ -449,7 +459,7 @@ Industry tile
|
||||
<tr><td nowrap valign=top><tt>1D</tt>..<tt>20</tt> </td><td align=left>oil wells
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>1D</tt> </td><td align=left>not animated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>1E</tt>..<tt>20</tt> </td><td align=left>various stages of animation; progress of animation in map_owner bits 1..0</td></tr>
|
||||
<tr><td nowrap valign=top><tt>1E</tt>..<tt>20</tt> </td><td align=left>various stages of animation; progress of animation in m1 bits 1..0</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>21</tt>..<tt>26</tt> </td><td align=left>farm</td></tr>
|
||||
@@ -458,7 +468,7 @@ Industry tile
|
||||
<tr><td nowrap valign=top><tt>2F</tt>..<tt>33</tt> </td><td align=left>copper ore mine
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>2F</tt> </td><td align=left>wheel tower when not animated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>30</tt> </td><td align=left>wheel tower when animated; animation state in map_owner bits 5..0; map_owner bit 6 set = sound already generated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>30</tt> </td><td align=left>wheel tower when animated; animation state in m1 bits 5..0; m1 bit 6 set = sound already generated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>31</tt> </td><td align=left>chimney</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
@@ -469,7 +479,7 @@ Industry tile
|
||||
<tr><td nowrap valign=top><tt>48</tt>..<tt>58</tt> </td><td align=left>gold mine
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>4F</tt> </td><td align=left>wheel tower when not animated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>58</tt> </td><td align=left>wheel tower when animated; animation state in map_owner bits 5..0; map_owner bit 6 set = sound already generated</td></tr>
|
||||
<tr><td nowrap valign=top><tt>58</tt> </td><td align=left>wheel tower when animated; animation state in m1 bits 5..0; m1 bit 6 set = sound already generated</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>59</tt>..<tt>5A</tt> </td><td align=left>bank (sub-arctic or sub-tropical climate)</td></tr>
|
||||
@@ -496,9 +506,9 @@ Industry tile
|
||||
<tr><td nowrap valign=top><tt>8A</tt>..<tt>8D</tt> </td><td align=left>toy shop</td></tr>
|
||||
<tr><td nowrap valign=top><tt>8E</tt>..<tt>93</tt> </td><td align=left>toy factory
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>8F</tt> </td><td align=left>animated part; animation state in map3_lo (valid range <tt>00</tt>..<tt>31</tt>)<br>
|
||||
tile animation is started (map3_hi zeroed) on the periodic processing if <a href="#industry.didtransform">field <tt>2C</tt></a> in the corresponding industry array entry is nonzero<br>
|
||||
while the animation is in progress (see the <a href="#_AnimatedTilesList">array at <tt>04328</tt></a>) map3_hi holds the number of animation cycles that have already taken place; when this number reaches 8 the animation is stopped</td></tr>
|
||||
<tr><td nowrap valign=top><tt>8F</tt> </td><td align=left>animated part; animation state in m3 (valid range <tt>00</tt>..<tt>31</tt>)<br>
|
||||
tile animation is started (m4 zeroed) on the periodic processing if <a href="#industry.didtransform">field <tt>2C</tt></a> in the corresponding industry array entry is nonzero<br>
|
||||
while the animation is in progress (see the <a href="#_AnimatedTilesList">array at <tt>04328</tt></a>) m4 holds the number of animation cycles that have already taken place; when this number reaches 8 the animation is stopped</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>94</tt>..<tt>9B</tt> </td><td align=left>plastic fountains (various stages of cyclic animation)</td></tr>
|
||||
@@ -506,69 +516,69 @@ while the animation is in progress (see the <a href="#_AnimatedTilesList">array
|
||||
<tr><td nowrap valign=top><tt>A0</tt>..<tt>A3</tt> </td><td align=left>bubble generator
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>A1</tt> </td><td align=left>generators</td></tr>
|
||||
<tr><td nowrap valign=top><tt>A2</tt> </td><td align=left>bubble capture facility; animation state in map3_lo (valid range <tt>00</tt>..<tt>27</tt>)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>A2</tt> </td><td align=left>bubble capture facility; animation state in m3 (valid range <tt>00</tt>..<tt>27</tt>)</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>A4</tt>..<tt>A6</tt> </td><td align=left>toffee quarry
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>A5</tt> </td><td align=left>animated part; animation state in map3_lo (valid range <tt>00</tt>..<tt>45</tt>)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>A5</tt> </td><td align=left>animated part; animation state in m3 (valid range <tt>00</tt>..<tt>45</tt>)</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td nowrap valign=top><tt>A7</tt>..<tt>AE</tt> </td><td align=left>sugar mine
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>AE</tt> </td><td align=left>animated part; animation state in map3_lo (valid range <tt>00</tt>..<tt>5F</tt>)</td></tr>
|
||||
<tr><td nowrap valign=top><tt>AE</tt> </td><td align=left>animated part; animation state in m3 (valid range <tt>00</tt>..<tt>5F</tt>)</td></tr>
|
||||
</table>
|
||||
</td></tr>
|
||||
<tr><td colspan=2></td></tr> <!-- spacer -->
|
||||
</table></li>
|
||||
<li>map2: index into the <a href="#_IndustryArray">array of industries</a>
|
||||
<li>m2: index into the <a href="#_IndustryArray">array of industries</a>
|
||||
</li>
|
||||
<li>map_owner bit 7: clear = under construction
|
||||
<li>m1 bit 7: clear = under construction
|
||||
<ul>
|
||||
<li>map_owner bits 4..2: construction counter, for buildings under construction incremented on every periodic tile processing
|
||||
<li>m1 bits 4..2: construction counter, for buildings under construction incremented on every periodic tile processing
|
||||
</li>
|
||||
</ul></li>
|
||||
<li>map_owner bits 1..0: stage of construction (<tt>3</tt> = completed), incremented when the construction counter wraps around
|
||||
<li>m1 bits 1..0: stage of construction (<tt>3</tt> = completed), incremented when the construction counter wraps around
|
||||
<br>the meaning is different for some animated tiles which are never under construction (types <tt>01</tt>, <tt>1E</tt>..<tt>20</tt>, <tt>30</tt>, <tt>58</tt>; see above)
|
||||
</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="Class9"><tt> 9 </tt></a></td><td>
|
||||
map5 bits 7..4 clear: tunnel entrance/exit
|
||||
m5 bits 7..4 clear: tunnel entrance/exit
|
||||
<ul>
|
||||
<li>map5 bits 3..2: <tt>0</tt> - railway tunnel, <tt>1</tt> - road tunnel</li>
|
||||
<li>map5 bits 1..0 - direction: entrance towards: <tt>0</tt> = NE, <tt>1</tt> = SE, <tt>2</tt> = SW, <tt>3</tt> = NW</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the tunnel</li>
|
||||
<li>map3_lo bits 3..0 = <a href="#TrackType">track type</a> for railway tunnel, must be 0 for road tunnel</li>
|
||||
<li>map3_hi bit 7 set = on snow or desert</li>
|
||||
<li>m5 bits 3..2: <tt>0</tt> - railway tunnel, <tt>1</tt> - road tunnel</li>
|
||||
<li>m5 bits 1..0 - direction: entrance towards: <tt>0</tt> = NE, <tt>1</tt> = SE, <tt>2</tt> = SW, <tt>3</tt> = NW</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the tunnel</li>
|
||||
<li>m3 bits 3..0 = <a href="#TrackType">track type</a> for railway tunnel, must be 0 for road tunnel</li>
|
||||
<li>m4 bit 7 set = on snow or desert</li>
|
||||
</ul>
|
||||
map5 bit 7 set: bridge
|
||||
m5 bit 7 set: bridge
|
||||
<ul><li>
|
||||
map5 bit 6 clear: bridge ending
|
||||
m5 bit 6 clear: bridge ending
|
||||
<ul>
|
||||
<li>map5 bit 5: clear - northern, set - southern ending</li>
|
||||
<li>map3_lo bits 3..0 = <a href="#TrackType">type of track</a> on the bridge, must be 0 for road bridge</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the bridge</li>
|
||||
<li>m5 bit 5: clear - northern, set - southern ending</li>
|
||||
<li>m3 bits 3..0 = <a href="#TrackType">type of track</a> on the bridge, must be 0 for road bridge</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the bridge</li>
|
||||
</ul>
|
||||
map5 bit 6 set: bridge middle part
|
||||
m5 bit 6 set: bridge middle part
|
||||
<ul>
|
||||
<li>map5 bit 5 clear:
|
||||
<li>m5 bit 5 clear:
|
||||
<ul>
|
||||
<li>map5 bits 4..3: land under bridge: <tt>0</tt> - grass, snow or desert, <tt>1</tt> - water</li>
|
||||
<li>m5 bits 4..3: land under bridge: <tt>0</tt> - grass, snow or desert, <tt>1</tt> - water</li>
|
||||
</ul>
|
||||
map5 bit 5 set:
|
||||
m5 bit 5 set:
|
||||
<ul>
|
||||
<li>map5 bits 4..3: transport route under bridge: <tt>0</tt> - railway, <tt>1</tt> - road</li>
|
||||
<li>m5 bits 4..3: transport route under bridge: <tt>0</tt> - railway, <tt>1</tt> - road</li>
|
||||
</ul>
|
||||
<li>map3_lo bits 7..4 = <a href="#TrackType">type of track</a> on the bridge, must be 0 for road bridge</li>
|
||||
<li>map3_lo bits 3..0 = <a href="#TrackType">type of track</a> under the bridge, if any</li>
|
||||
<li>map2 bits 3..0: bridge piece (<tt>0</tt>..<tt>5</tt>)
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the land under bridge</li>
|
||||
<li>m3 bits 7..4 = <a href="#TrackType">type of track</a> on the bridge, must be 0 for road bridge</li>
|
||||
<li>m3 bits 3..0 = <a href="#TrackType">type of track</a> under the bridge, if any</li>
|
||||
<li>m2 bits 3..0: bridge piece (<tt>0</tt>..<tt>5</tt>)
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the land under bridge</li>
|
||||
</ul></li>
|
||||
<li>map5 bits 2..1: <tt>0</tt> - railway bridge, <tt>1</tt> - road bridge</li>
|
||||
<li>map5 bit 0: clear - bridge in the X direction, set - bridge in the Y direction</li>
|
||||
<li>map2 bits 7..4: <a name="BridgeType">bridge type</a>:
|
||||
<li>m5 bits 2..1: <tt>0</tt> - railway bridge, <tt>1</tt> - road bridge</li>
|
||||
<li>m5 bit 0: clear - bridge in the X direction, set - bridge in the Y direction</li>
|
||||
<li>m2 bits 7..4: <a name="BridgeType">bridge type</a>:
|
||||
<table>
|
||||
<tr><th align=left>Type </th><th align=left>Max. speed (mph) </th><th align=left>Description</th></tr>
|
||||
<tr><td nowrap valign=top><tt>0</tt> </td><td align=center>20</td><td align=left>wooden</td></tr>
|
||||
@@ -583,13 +593,13 @@ map5 bit 5 set:
|
||||
<tr><td nowrap valign=top><tt>9</tt> </td><td align=center>160</td><td align=left>girder, steel</td></tr>
|
||||
<tr><td nowrap valign=top><tt>A</tt> </td><td align=center>200</td><td align=left>tubular, steel</td></tr>
|
||||
</table></li>
|
||||
<li>map3_hi bit 7 set = on snow or desert</li>
|
||||
<li>m4 bit 7 set = on snow or desert</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
<tr><td valign=top nowrap><a name="ClassA"><tt> A </tt></a></td><td>
|
||||
<ul>
|
||||
<li>map5: tile type:
|
||||
<li>m5: tile type:
|
||||
<table>
|
||||
<tr><td nowrap valign=top><tt>00</tt> </td><td align=left>transmitter</td></tr>
|
||||
<tr><td nowrap valign=top><tt>01</tt> </td><td align=left>lighthouse</td></tr>
|
||||
@@ -598,7 +608,7 @@ map5 bit 5 set:
|
||||
<tr><td nowrap valign=top><tt>80</tt>..<tt>93</tt> </td><td align=left>company headquarters (5 sets of 4 tiles each, updated quarterly depending on the company performance)</td></tr>
|
||||
</table>
|
||||
</li>
|
||||
<li>map_owner: <a href="#OwnershipInfo">owner</a> of the object (for lighthouses and transmitters normally <tt>10</tt>)</li>
|
||||
<li>m1: <a href="#OwnershipInfo">owner</a> of the object (for lighthouses and transmitters normally <tt>10</tt>)</li>
|
||||
</ul>
|
||||
</td></tr>
|
||||
|
||||
|
||||
+186
-174
@@ -5,232 +5,244 @@
|
||||
<meta name="Description" content="Structure of OpenTTD (OTTD) landscape arrays #2">
|
||||
<title>OpenTTD Landscape Internals - #2</title>
|
||||
<style type="text/css">
|
||||
.freebits { background-color: rgb(30, 178, 54);}
|
||||
.abuse { background-color: rgb(255, 58, 31);}
|
||||
span.abuse { font-family: "Courier New", Courier, mono; background-color: rgb(255, 58, 31); }
|
||||
span.free { font-family: "Courier New", Courier, mono; background-color: rgb(30, 178, 54); }
|
||||
span.used { font-family: "Courier New", Courier, mono; }
|
||||
td.bits { white-space: nowrap; text-align: center; font-family: "Courier New", Courier, mono; }
|
||||
td.caption { white-space: nowrap; text-align: left; }
|
||||
td li { white-space: nowrap; text-align: left; }
|
||||
th { white-space: nowrap; text-align: center; }
|
||||
</style>
|
||||
</head>
|
||||
<body style="direction: ltr;">
|
||||
<h3 style="font-weight: bold;">Landscape</h3>
|
||||
<span style="font-weight: bold;"></span>Five arrays are used to encode the information of the contents of the tile.
|
||||
<span style="font-weight: bold;"></span>Five attributes hold the information about a tile.
|
||||
This can be seen in the <a href="landscape.html">Landscape</a> document. This page tries to give an overview of used and free bits of
|
||||
the array so you can quickly see what is used and what is not.
|
||||
<ul>
|
||||
<li><span style="font-weight: bold;"><span class="freebits">O</span></span> - bit is free</li>
|
||||
<li><span style="font-weight: bold;">X</span> - bit is used</li>
|
||||
<li><span style="font-weight: bold;"><span class="abuse"> </span></span> - bit of _map_* is abused for different purposes</li>
|
||||
<li><span style="font-weight: bold;"><span class="free">O</span></span> - bit is free</li>
|
||||
<li><span style="font-weight: bold;"><span class="used">X</span></span> - bit is used</li>
|
||||
<li><span style="font-weight: bold;"><span class="abuse"> </span></span> - bit of attribute is abused for different purposes</li>
|
||||
</ul>
|
||||
<p>
|
||||
<ul>
|
||||
<li><span style="font-weight: bold;">_map_owner[]</span> - 8 bits in size, used to identify the owner of that tile (eg piece of rail, bridge, etc.).</li>
|
||||
<li><span style="font-weight: bold;">_map2[]</span> - 16 bits in size, used to identify the index of the given tile (object) in the (object-)array.</li>
|
||||
<li><span style="font-weight: bold;">_map3[]</span> - 16 bits in size, which is split up into _map3lo[] and _map3hi[] is used for general storage.</li>
|
||||
<li><span style="font-weight: bold;">_map_type_and_height[]</span> - 8 bits in size, stores tile height (lower 4 bits) and tile class (upper 4 bits).</li>
|
||||
<li><span style="font-weight: bold;">_map5[]</span> - 8 bits in size, is used for general storage.</li>
|
||||
<li><span style="font-weight: bold;">type_height</span> - 8 bits in size, stores tile height (lower 4 bits) and tile class (upper 4 bits)</li>
|
||||
<li><span style="font-weight: bold;">m1</span> - 8 bits in size, used to identify the owner of that tile (eg piece of rail, bridge, etc.)</li>
|
||||
<li><span style="font-weight: bold;">m2</span> - 16 bits in size, used to identify the index of the given tile (object) in the (object-)array</li>
|
||||
<li><span style="font-weight: bold;">m3</span> - 8 bits in size, is used for general storage</li>
|
||||
<li><span style="font-weight: bold;">m4</span> - 8 bits in size, is used for general storage</li>
|
||||
<li><span style="font-weight: bold;">m5</span> - 8 bits in size, is used for general storage</li>
|
||||
</ul>
|
||||
|
||||
<table style="text-align: left;" border="1" cellpadding="2"
|
||||
cellspacing="2" width="100%">
|
||||
<table align=center border="1" cellpadding="2" cellspacing="2">
|
||||
<tbody>
|
||||
<tr>
|
||||
<th style="white-space: nowrap; text-align: left;">class</th>
|
||||
<th style="white-space: nowrap; text-align: center;">_map_owner[L1] (8)</th>
|
||||
<th style="white-space: nowrap; text-align: center;">_map2[L2] (16)</th>
|
||||
<th style="white-space: nowrap; text-align: center;">_map3[lo& hi,L3] (16)</th>
|
||||
<th style="white-space: nowrap; text-align: center;">_map_type_and_height[L4] (8)</th>
|
||||
<th style="white-space: nowrap; text-align: center;">_map5[L5] (8)</th>
|
||||
<th colspan=2>class</th>
|
||||
<th>m1 (8)</th>
|
||||
<th>m2 (16)</th>
|
||||
<th>m3 (8)</th>
|
||||
<th>m4 (8)</th>
|
||||
<th>type_height (8)</th>
|
||||
<th>m5 (8)</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(0) ground</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX <span class="freebits">OOOO OO</span>XX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX X<span class="freebits">O</span>XX</td>
|
||||
<td colspan=2 class="caption">bits</td>
|
||||
<td class="bits">7654 3210</td>
|
||||
<td class="bits">FEDC BA98 7654 3210</td>
|
||||
<td class="bits">7654 3210</td>
|
||||
<td class="bits">7654 3210</td>
|
||||
<td class="bits">7654 3210</td>
|
||||
<td class="bits">7654 3210</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(1) rail</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="abuse">XXXX XXXX</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX <span class="freebits">OOOO OOOO</span><br>
|
||||
</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX XXX<span class="freebits">O OOOO</span><br>
|
||||
</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX<br>
|
||||
</td>
|
||||
<td>0</td>
|
||||
<td class="caption">ground</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO</span> XXXX</td>
|
||||
<td class="bits">XXXX XX<span class="free">OO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">depot/checkpoint</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="text-align: center;">XXXX X<span class="freebits">OOO</span> XXXX XXXX</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXX<span class="freebits">O OO</span>XX</td>
|
||||
<td rowspan=3>1</td>
|
||||
<td class="caption">rail</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span> XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO O</span>XXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(2) road</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td style="text-align: center;"><span class="abuse">XXXX XXXX XXXX XXXX</span></td>
|
||||
<td style="text-align: center;"><span class="freebits">OOOO OOOO</span> XXXX XXXX</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td class="caption">depot</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO</span> XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO</span> XXXX</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XX<span class="free">OO O</span>XXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">level crossing</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;"><span class="abuse">XXXX XXXX XXXX XXXX</span></td>
|
||||
<td style="text-align: center;">XXXX XXXX XXXX XXXX</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;"><span class="freebits">OO</span>XX XXXX</td>
|
||||
<td class="caption">waypoint</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XXXX XXXX XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOO</span>X XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO</span> XXXX</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XX<span class="free">OO O</span>XXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">road depot</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="text-align: center;"><span class="freebits">OOOO OOOO OOOO OOO</span>X</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td rowspan=3>2</td>
|
||||
<td class="caption">road</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(3) town</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="abuse">XXXX XXXX</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX XXXX XXXX<br>
|
||||
</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX XXXX XXXX<br>
|
||||
</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XX<span class="freebits">O</span>X</td>
|
||||
<td class="caption">level crossing</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XXXX XX<span class="free">OO</span></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(4) trees</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="abuse">XXXX XXXX</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XX<span class="freebits">OO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX <span class="freebits">OO</span>XX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXX<span class="freebits">O OO</span>XX</td>
|
||||
<td class="caption">road depot</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits">X<span class="free">OOO OOOO</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(5) station</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX X<span class="freebits">OOO</span> XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td>3</td>
|
||||
<td class="caption">town</td>
|
||||
<td class="bits"><span class="abuse">XXXX XXXX</span></td>
|
||||
<td class="bits">XXXX XXXX XXXX XXXX</td>
|
||||
<td class="bits">XX<span class="free">OO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">X<span class="free">O</span>XX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(6) water</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td>4</td>
|
||||
<td class="caption">trees</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span> XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XX<span class="free">OO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XX<span class="free">OO O</span>XXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(8) industry</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="abuse">XXXX X</span><span class="freebits">OO</span><span class="abuse">X</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td>5</td>
|
||||
<td class="caption">station</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOO</span>X XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">bubble/sugar/toffee</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">XXXX XXXX <span class="freebits">OOOO OOOO</span></td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td>6</td>
|
||||
<td class="caption">water</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">toy factory</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">XXXX XXXX XXXX XXXX</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td rowspan=6>8</td>
|
||||
<td class="caption">industry</td>
|
||||
<td class="bits"><span class="abuse">X</span><span class="free">OO</span><span class="abuse">X XXXX</span></td>
|
||||
<td class="bits">XXXX XXXX XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">gold/copper/coal</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td>bubble/sugar/toffee</td>
|
||||
<td class="bits"><span class="abuse">X</span><span class="free">OOO OOOO</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">oil wells</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td>toy factory</td>
|
||||
<td class="bits"><span class="abuse">X</span><span class="free">OOO OOOO</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">power station</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">XXXX XX<span class="freebits">O</span>X</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td style="text-align: center;">-inherit-</td>
|
||||
<td>gold/copper/coal</td>
|
||||
<td class="bits"><span class="abuse">XX</span><span class="free">OO OO</span><span class="abuse">XX</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(9) tunnel</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX <span class="freebits">OOOO OOOO OOO</span>X</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td>oil wells</td>
|
||||
<td class="bits"><span class="abuse">X</span><span class="free">OOO OO</span><span class="abuse">XX</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<ul>
|
||||
<li style="white-space: nowrap; text-align: left;">bridge</li>
|
||||
</ul>
|
||||
</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td style="text-align: center;"><span class="abuse">XXXX XXXX</span> <span class="freebits">OOOO OOOO</span></td>
|
||||
<td style="text-align: center;">XXXX XXXX <span class="freebits">OOOO OOO</span>X</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td style="text-align: center;">XXXX XXXX</td>
|
||||
<td>power station</td>
|
||||
<td class="bits"><span class="abuse">X</span><span class="free">O</span><span class="abuse">XX XX</span><span class="free">OO</span></td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
<td class="bits">-inherit-</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="white-space: nowrap; text-align: left;">(10) various (HQ)</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;"><span class="freebits">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td style="white-space: nowrap; text-align: center;">XXXX XXXX</td>
|
||||
<td rowspan=2>9</td>
|
||||
<td class="caption">tunnel</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO</span> XXXX</td>
|
||||
<td class="bits">X<span class="free">OOO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>bridge</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span> <span class="abuse">XXXX XXXX</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">X<span class="free">OOO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>A</td>
|
||||
<td class="caption">various (HQ)</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits"><span class="free">OOOO OOOO OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits"><span class="free">OOOO OOOO</span></td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
<td class="bits">XXXX XXXX</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
+65
-48
@@ -1,50 +1,67 @@
|
||||
.\" Hey, EMACS: -*- nroff -*-
|
||||
.\" First parameter, NAME, should be all caps
|
||||
.\" Second parameter, SECTION, should be 1-8, maybe w/ subsection
|
||||
.\" other parameters are allowed: see man(7), man(1)
|
||||
.TH OPENTTD 6 "September 16, 2004"
|
||||
.\" Please adjust this date whenever revising the manpage.
|
||||
.\"
|
||||
.\" Some roff macros, for reference:
|
||||
.\" .nh disable hyphenation
|
||||
.\" .hy enable hyphenation
|
||||
.\" .ad l left justify
|
||||
.\" .ad b justify to both left and right margins
|
||||
.\" .nf disable filling
|
||||
.\" .fi enable filling
|
||||
.\" .br insert line break
|
||||
.\" .sp <n> insert n+1 empty lines
|
||||
.\" for manpage-specific macros, see man(7)
|
||||
.SH NAME
|
||||
openttd \- An open source clone of the Microprose game "Transport Tycoon Deluxe"
|
||||
.SH SYNOPSIS
|
||||
.B openttd
|
||||
.RI [ options ]
|
||||
.br
|
||||
.SH DESCRIPTION
|
||||
Unfortunately, there is no real manpage for openttd yet. Hopefully someone
|
||||
will write one soon. For now you should use
|
||||
.B openttd -h
|
||||
for more information, or check our Wiki manual: http://wiki.openttd.org/
|
||||
.PP
|
||||
.\" TeX users may be more comfortable with the \fB<whatever>\fP and
|
||||
.\" \fI<whatever>\fP escape sequences to invoke bold face and italics,
|
||||
.\" respectively.
|
||||
.\" \fBopenttd\fP is a program that...
|
||||
.SH OPTIONS
|
||||
Wouldn't we like to have something here?
|
||||
.\" below are commented out, to serve as layout examples for when somebody
|
||||
.\" does actually fill this page
|
||||
.\" .TP
|
||||
.\" .B \-h, \-\-help
|
||||
.\" Show summary of options.
|
||||
.\" .TP
|
||||
.\" .B \-v, \-\-version
|
||||
.\" Show version of program.
|
||||
.\" .SH SEE ALSO
|
||||
.\" .BR bar (1),
|
||||
.\" .BR baz (1).
|
||||
.br
|
||||
.SH AUTHOR
|
||||
This manual page was written by Matthijs Kooijman <matthijs@katherina.student.utwente.nl>,
|
||||
for the Debian project (but may be used by others).
|
||||
.Dd July 27, 2005
|
||||
.Dt OPENTTD 6
|
||||
.Sh NAME
|
||||
.Nm openttd
|
||||
.Nd An open source clone of the Microprose game "Transport Tycoon Deluxe"
|
||||
.Sh SYNOPSIS
|
||||
.Nm
|
||||
.Op Fl Defhi
|
||||
.Op Fl G Ar seed
|
||||
.Op Fl d Ar [level | cat=lvl[, ...]]
|
||||
.Op Fl g Ar [savegame]
|
||||
.Op Fl n Ar [host[#player][:port]]
|
||||
.Op Fl r Ar widthxheight
|
||||
.Op Fl t Ar date
|
||||
.Op Fl m Ar driver
|
||||
.Op Fl s Ar driver
|
||||
.Op Fl v Ar driver
|
||||
.Sh OPTIONS
|
||||
.Bl -tag -width ".Fl n Ar host[#player][:port]"
|
||||
.It Fl D
|
||||
Start a dedicated server
|
||||
.It Fl G Ar seed
|
||||
Seed the pseudo random number generator
|
||||
.It Fl d Ar [level]
|
||||
Set debug verbosity for all categories to
|
||||
.Ar level
|
||||
or 1 if omitted
|
||||
.It Fl d Ar cat=level[, ...]
|
||||
Set debug verbosity for a specific category
|
||||
.It Fl e
|
||||
Start in world editor mode
|
||||
.It Fl f
|
||||
Fork into background (dedicated only, see
|
||||
.Fl D )
|
||||
.It Fl g Ar [savegame]
|
||||
Load
|
||||
.Ar savegame
|
||||
at start or start a new game if omitted
|
||||
.It Fl h
|
||||
Display a summary of all options and available drivers
|
||||
.It Fl i
|
||||
Force to use the DOS palette (use this if you see a lot of magenta)
|
||||
.It Fl m Ar driver
|
||||
Set the music driver, see
|
||||
.Fl h
|
||||
.It Fl n
|
||||
Start a network server
|
||||
.It Fl n Ar host[#player][:port]
|
||||
Join a network game, optionally specify player to play as and port to connect to
|
||||
.It Fl r Ar widthxheight
|
||||
Set the resolution
|
||||
.It Fl s Ar driver
|
||||
Set the sound driver, see
|
||||
.Fl h
|
||||
.It Fl t Ar date
|
||||
Set the starting date
|
||||
.It Fl v Ar driver
|
||||
Set the video driver, see
|
||||
.Fl h
|
||||
.Sh SEE ALSO
|
||||
http://wiki.openttd.org/
|
||||
.Sh HISTORY
|
||||
Transport Tycoon Deluxe was written by Chris Sawyer and published by Microprose.
|
||||
.Nm
|
||||
is a free reimplementation.
|
||||
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 2.2 KiB |
@@ -1,38 +0,0 @@
|
||||
0,9,10,2,3,13,9,9,0,10,4,15,6,11,14,1
|
||||
dark blue=0 =0
|
||||
pale_green=1 =9
|
||||
pink=2 =10
|
||||
yellow=3 =2
|
||||
red=4 =3
|
||||
light blue=5 =13
|
||||
green=6 =9
|
||||
dark green=7 =9
|
||||
blue=8 =0
|
||||
cream=9 =10
|
||||
mauve=10 =4
|
||||
purple=11 =15
|
||||
orange=12 =6
|
||||
brown=13 =11
|
||||
grey=14 =14
|
||||
white=15 =1
|
||||
|
||||
|
||||
=blue=0
|
||||
=white=1
|
||||
=yellow=2
|
||||
=red=3
|
||||
=blue=4
|
||||
=grey=5
|
||||
=orange=6
|
||||
=green=7
|
||||
=light yellow=8
|
||||
=light green=9
|
||||
=cream=10
|
||||
=brown=11
|
||||
=white=12
|
||||
=light blue=13
|
||||
=dark grey=14
|
||||
=purple=15
|
||||
=black=16
|
||||
=dark green=17=not good
|
||||
=dark grey=21
|
||||
@@ -0,0 +1,224 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "openttd.h"
|
||||
#include "debug.h"
|
||||
#include "driver.h"
|
||||
#include "functions.h"
|
||||
#include "hal.h"
|
||||
#include "string.h"
|
||||
|
||||
#include "music/bemidi.h"
|
||||
#include "music/dmusic.h"
|
||||
#include "music/extmidi.h"
|
||||
#include "music/null_m.h"
|
||||
#include "music/os2_m.h"
|
||||
#include "music/win32_m.h"
|
||||
#include "music/qtmidi.h"
|
||||
|
||||
#include "sound/null_s.h"
|
||||
#include "sound/sdl_s.h"
|
||||
#include "sound/cocoa_s.h"
|
||||
#include "sound/win32_s.h"
|
||||
|
||||
#include "video/dedicated_v.h"
|
||||
#include "video/null_v.h"
|
||||
#include "video/sdl_v.h"
|
||||
#include "video/cocoa_v.h"
|
||||
#include "video/win32_v.h"
|
||||
|
||||
typedef struct DriverDesc {
|
||||
const char* name;
|
||||
const char* longname;
|
||||
const HalCommonDriver* drv;
|
||||
} DriverDesc;
|
||||
|
||||
typedef struct DriverClass {
|
||||
const DriverDesc *descs;
|
||||
const char *name;
|
||||
const HalCommonDriver** drv;
|
||||
} DriverClass;
|
||||
|
||||
|
||||
#define M(x, y, z) { x, y, (const HalCommonDriver *)(void *)z }
|
||||
static const DriverDesc _music_driver_descs[] = {
|
||||
#ifdef __BEOS__
|
||||
M("bemidi", "BeOS MIDI Driver", &_bemidi_music_driver),
|
||||
#endif
|
||||
#ifdef __OS2__
|
||||
M("os2", "OS/2 Music Driver", &_os2_music_driver),
|
||||
#endif
|
||||
#ifdef WIN32_ENABLE_DIRECTMUSIC_SUPPORT
|
||||
M("dmusic", "DirectMusic MIDI Driver", &_dmusic_midi_driver),
|
||||
#endif
|
||||
#ifdef WIN32
|
||||
M("win32", "Win32 MIDI Driver", &_win32_music_driver),
|
||||
#endif
|
||||
#if defined(__APPLE__) && !defined(DEDICATED)
|
||||
M("qt", "QuickTime MIDI Driver", &_qtime_music_driver),
|
||||
#endif
|
||||
#ifdef UNIX
|
||||
#if !defined(__MORPHOS__) && !defined(__AMIGA__)
|
||||
M("extmidi", "External MIDI Driver", &_extmidi_music_driver),
|
||||
#endif
|
||||
#endif
|
||||
M("null", "Null Music Driver", &_null_music_driver),
|
||||
M(NULL, NULL, NULL)
|
||||
};
|
||||
|
||||
static const DriverDesc _sound_driver_descs[] = {
|
||||
#ifdef WIN32
|
||||
M("win32", "Win32 WaveOut Driver", &_win32_sound_driver),
|
||||
#endif
|
||||
#ifdef WITH_SDL
|
||||
M("sdl", "SDL Sound Driver", &_sdl_sound_driver),
|
||||
#endif
|
||||
#ifdef WITH_COCOA
|
||||
M("cocoa", "Cocoa Sound Driver", &_cocoa_sound_driver),
|
||||
#endif
|
||||
M("null", "Null Sound Driver", &_null_sound_driver),
|
||||
M(NULL, NULL, NULL)
|
||||
};
|
||||
|
||||
static const DriverDesc _video_driver_descs[] = {
|
||||
#ifdef WIN32
|
||||
M("win32", "Win32 GDI Video Driver", &_win32_video_driver),
|
||||
#endif
|
||||
#ifdef WITH_SDL
|
||||
M("sdl", "SDL Video Driver", &_sdl_video_driver),
|
||||
#endif
|
||||
#ifdef WITH_COCOA
|
||||
M("cocoa", "Cocoa Video Driver", &_cocoa_video_driver),
|
||||
#endif
|
||||
M("null", "Null Video Driver", &_null_video_driver),
|
||||
#ifdef ENABLE_NETWORK
|
||||
M("dedicated", "Dedicated Video Driver", &_dedicated_video_driver),
|
||||
#endif
|
||||
M(NULL, NULL, NULL)
|
||||
};
|
||||
#undef M
|
||||
|
||||
|
||||
#define M(x, y, z) { x, y, (const HalCommonDriver **)(void *)z }
|
||||
static const DriverClass _driver_classes[] = {
|
||||
M(_video_driver_descs, "video", &_video_driver),
|
||||
M(_sound_driver_descs, "sound", &_sound_driver),
|
||||
M(_music_driver_descs, "music", &_music_driver)
|
||||
};
|
||||
#undef M
|
||||
|
||||
static const DriverDesc* GetDriverByName(const DriverDesc* dd, const char* name)
|
||||
{
|
||||
for (; dd->name != NULL; dd++) {
|
||||
if (strcmp(dd->name, name) == 0) return dd;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void LoadDriver(int driver, const char *name)
|
||||
{
|
||||
const DriverClass *dc = &_driver_classes[driver];
|
||||
const DriverDesc *dd;
|
||||
const char *err;
|
||||
|
||||
if (*name == '\0') {
|
||||
for (dd = dc->descs; dd->name != NULL; dd++) {
|
||||
err = dd->drv->start(NULL);
|
||||
if (err == NULL) break;
|
||||
DEBUG(driver, 1) ("Probing %s driver \"%s\" failed with error: %s",
|
||||
dc->name, dd->name, err
|
||||
);
|
||||
}
|
||||
if (dd->name == NULL) {
|
||||
error("Couldn't find any suitable %s driver", dc->name);
|
||||
}
|
||||
|
||||
DEBUG(driver, 1)
|
||||
("Successfully probed %s driver \"%s\"", dc->name, dd->name);
|
||||
|
||||
*dc->drv = dd->drv;
|
||||
} else {
|
||||
char* parm;
|
||||
char buffer[256];
|
||||
const char* parms[32];
|
||||
|
||||
// Extract the driver name and put parameter list in parm
|
||||
ttd_strlcpy(buffer, name, sizeof(buffer));
|
||||
parm = strchr(buffer, ':');
|
||||
parms[0] = NULL;
|
||||
if (parm != NULL) {
|
||||
uint np = 0;
|
||||
// Tokenize the parm.
|
||||
do {
|
||||
*parm++ = '\0';
|
||||
if (np < lengthof(parms) - 1)
|
||||
parms[np++] = parm;
|
||||
while (*parm != '\0' && *parm != ',')
|
||||
parm++;
|
||||
} while (*parm == ',');
|
||||
parms[np] = NULL;
|
||||
}
|
||||
dd = GetDriverByName(dc->descs, buffer);
|
||||
if (dd == NULL)
|
||||
error("No such %s driver: %s\n", dc->name, buffer);
|
||||
|
||||
if (*dc->drv != NULL) (*dc->drv)->stop();
|
||||
*dc->drv = NULL;
|
||||
|
||||
err = dd->drv->start(parms);
|
||||
if (err != NULL) {
|
||||
error("Unable to load driver %s(%s). The error was: %s\n",
|
||||
dd->name, dd->longname, err
|
||||
);
|
||||
}
|
||||
*dc->drv = dd->drv;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static const char* GetDriverParam(const char* const* parm, const char* name)
|
||||
{
|
||||
size_t len;
|
||||
|
||||
if (parm == NULL) return NULL;
|
||||
|
||||
len = strlen(name);
|
||||
for (; *parm != NULL; parm++) {
|
||||
const char* p = *parm;
|
||||
|
||||
if (strncmp(p, name, len) == 0) {
|
||||
if (p[len] == '=') return p + len + 1;
|
||||
if (p[len] == '\0') return p + len;
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bool GetDriverParamBool(const char* const* parm, const char* name)
|
||||
{
|
||||
return GetDriverParam(parm, name) != NULL;
|
||||
}
|
||||
|
||||
int GetDriverParamInt(const char* const* parm, const char* name, int def)
|
||||
{
|
||||
const char* p = GetDriverParam(parm, name);
|
||||
return p != NULL ? atoi(p) : def;
|
||||
}
|
||||
|
||||
|
||||
char *GetDriverList(char* p)
|
||||
{
|
||||
const DriverClass* dc;
|
||||
|
||||
for (dc = _driver_classes; dc != endof(_driver_classes); dc++) {
|
||||
const DriverDesc* dd;
|
||||
|
||||
p += sprintf(p, "List of %s drivers:\n", dc->name);
|
||||
for (dd = dc->descs; dd->name != NULL; dd++) {
|
||||
p += sprintf(p, "%10s: %s\n", dd->name, dd->longname);
|
||||
}
|
||||
p += sprintf(p, "\n");
|
||||
}
|
||||
|
||||
return p;
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef DRIVER_H
|
||||
#define DRIVER_H
|
||||
|
||||
void LoadDriver(int driver, const char *name);
|
||||
|
||||
bool GetDriverParamBool(const char* const* parm, const char* name);
|
||||
int GetDriverParamInt(const char* const* parm, const char* name, int def);
|
||||
|
||||
char *GetDriverList(char* p);
|
||||
|
||||
#endif /* DRIVER_H */
|
||||
+20
-14
@@ -1,60 +1,67 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "viewport.h"
|
||||
#include "command.h"
|
||||
#include "table/sprites.h"
|
||||
|
||||
static void DrawTile_Dummy(TileInfo *ti)
|
||||
{
|
||||
DrawGroundSpriteAt(0x3EC, ti->x, ti->y, ti->z);
|
||||
DrawGroundSpriteAt(SPR_SHADOW_CELL, ti->x, ti->y, ti->z);
|
||||
}
|
||||
|
||||
|
||||
static uint GetSlopeZ_Dummy(TileInfo *ti) {
|
||||
return GetPartialZ(ti->x&0xF, ti->y&0xF, ti->tileh) + ti->z;
|
||||
static uint GetSlopeZ_Dummy(const TileInfo* ti)
|
||||
{
|
||||
return GetPartialZ(ti->x & 0xF, ti->y & 0xF, ti->tileh) + ti->z;
|
||||
}
|
||||
|
||||
static uint GetSlopeTileh_Dummy(TileInfo *ti) {
|
||||
static uint GetSlopeTileh_Dummy(const TileInfo* ti)
|
||||
{
|
||||
return ti->tileh;
|
||||
}
|
||||
|
||||
static int32 ClearTile_Dummy(uint tile, byte flags) {
|
||||
static int32 ClearTile_Dummy(TileIndex tile, byte flags)
|
||||
{
|
||||
return_cmd_error(STR_0001_OFF_EDGE_OF_MAP);
|
||||
}
|
||||
|
||||
|
||||
static void GetAcceptedCargo_Dummy(uint tile, AcceptedCargo ac)
|
||||
static void GetAcceptedCargo_Dummy(TileIndex tile, AcceptedCargo ac)
|
||||
{
|
||||
/* not used */
|
||||
}
|
||||
|
||||
static void GetTileDesc_Dummy(uint tile, TileDesc *td)
|
||||
static void GetTileDesc_Dummy(TileIndex tile, TileDesc *td)
|
||||
{
|
||||
td->str = STR_EMPTY;
|
||||
td->owner = OWNER_NONE;
|
||||
}
|
||||
|
||||
static void AnimateTile_Dummy(uint tile)
|
||||
static void AnimateTile_Dummy(TileIndex tile)
|
||||
{
|
||||
/* not used */
|
||||
}
|
||||
|
||||
static void TileLoop_Dummy(uint tile)
|
||||
static void TileLoop_Dummy(TileIndex tile)
|
||||
{
|
||||
/* not used */
|
||||
}
|
||||
|
||||
static void ClickTile_Dummy(uint tile)
|
||||
static void ClickTile_Dummy(TileIndex tile)
|
||||
{
|
||||
/* not used */
|
||||
}
|
||||
|
||||
static void ChangeTileOwner_Dummy(uint tile, byte old_player, byte new_player)
|
||||
static void ChangeTileOwner_Dummy(TileIndex tile, PlayerID old_player, PlayerID new_player)
|
||||
{
|
||||
/* not used */
|
||||
}
|
||||
|
||||
static uint32 GetTileTrackStatus_Dummy(uint tile, TransportType mode)
|
||||
static uint32 GetTileTrackStatus_Dummy(TileIndex tile, TransportType mode)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
@@ -75,4 +82,3 @@ const TileTypeProcs _tile_type_dummy_procs = {
|
||||
NULL, /* vehicle_leave_tile_proc */
|
||||
GetSlopeTileh_Dummy, /* get_slope_tileh_proc */
|
||||
};
|
||||
|
||||
|
||||
@@ -1,7 +1,12 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "currency.h"
|
||||
#include "functions.h"
|
||||
#include "strings.h" // XXX InjectDParam()
|
||||
#include "table/strings.h"
|
||||
#include "table/sprites.h"
|
||||
#include "map.h"
|
||||
#include "news.h"
|
||||
#include "player.h"
|
||||
@@ -18,36 +23,31 @@
|
||||
#include "sound.h"
|
||||
#include "engine.h"
|
||||
#include "network_data.h"
|
||||
#include "variables.h"
|
||||
#include "vehicle_gui.h"
|
||||
#include "ai/ai.h"
|
||||
#include "train.h"
|
||||
|
||||
// get a mask of the allowed currencies depending on the year
|
||||
uint GetMaskOfAllowedCurrencies(void)
|
||||
{
|
||||
int i;
|
||||
uint mask = 0;
|
||||
for (i = 0; i != lengthof(_currency_specs); i++) {
|
||||
uint16 to_euro = _currency_specs[i].to_euro;
|
||||
if (i == 23) mask |= (1 << 23); // always allow custom currency
|
||||
if (to_euro != CF_NOEURO && to_euro != CF_ISEURO && _cur_year >= (to_euro-MAX_YEAR_BEGIN_REAL)) continue;
|
||||
if (_cur_year < (2000-MAX_YEAR_BEGIN_REAL) && (to_euro == CF_ISEURO)) continue;
|
||||
mask |= (1 << i);
|
||||
}
|
||||
return mask;
|
||||
}
|
||||
// Score info
|
||||
const ScoreInfo _score_info[] = {
|
||||
{SCORE_VEHICLES, 120, 100},
|
||||
{SCORE_STATIONS, 80, 100},
|
||||
{SCORE_MIN_PROFIT, 10000, 100},
|
||||
{SCORE_MIN_INCOME, 50000, 50},
|
||||
{SCORE_MAX_INCOME, 100000, 100},
|
||||
{SCORE_DELIVERED, 40000, 400},
|
||||
{SCORE_CARGO, 8, 50},
|
||||
{SCORE_MONEY, 10000000, 50},
|
||||
{SCORE_LOAN, 250000, 50},
|
||||
{SCORE_TOTAL, 0, 0}
|
||||
};
|
||||
|
||||
void CheckSwitchToEuro(void)
|
||||
{
|
||||
if (_currency_specs[_opt.currency].to_euro != CF_NOEURO &&
|
||||
_currency_specs[_opt.currency].to_euro != CF_ISEURO &&
|
||||
_cur_year >= (_currency_specs[_opt.currency].to_euro-MAX_YEAR_BEGIN_REAL)) {
|
||||
_opt.currency = 2; // this is the index of euro above.
|
||||
AddNewsItem(STR_EURO_INTRODUCE, NEWS_FLAGS(NM_NORMAL,0,NT_ECONOMY,0), 0, 0);
|
||||
}
|
||||
}
|
||||
int _score_part[MAX_PLAYERS][NUM_SCORE];
|
||||
|
||||
void UpdatePlayerHouse(Player *p, uint score)
|
||||
{
|
||||
byte val;
|
||||
uint tile = p->location_of_house;
|
||||
TileIndex tile = p->location_of_house;
|
||||
|
||||
if (tile == 0)
|
||||
return;
|
||||
@@ -59,22 +59,23 @@ void UpdatePlayerHouse(Player *p, uint score)
|
||||
(val+= 4, true);
|
||||
|
||||
/* house is already big enough */
|
||||
if (val <= _map5[tile])
|
||||
if (val <= _m[tile].m5)
|
||||
return;
|
||||
|
||||
_map5[tile + TILE_XY(0,0)] = val;
|
||||
_map5[tile + TILE_XY(0,1)] = ++val;
|
||||
_map5[tile + TILE_XY(1,0)] = ++val;
|
||||
_map5[tile + TILE_XY(1,1)] = ++val;
|
||||
_m[tile + TileDiffXY(0, 0)].m5 = val;
|
||||
_m[tile + TileDiffXY(0, 1)].m5 = ++val;
|
||||
_m[tile + TileDiffXY(1, 0)].m5 = ++val;
|
||||
_m[tile + TileDiffXY(1, 1)].m5 = ++val;
|
||||
|
||||
MarkTileDirtyByTile(tile + TILE_XY(0,0));
|
||||
MarkTileDirtyByTile(tile + TILE_XY(0,1));
|
||||
MarkTileDirtyByTile(tile + TILE_XY(1,0));
|
||||
MarkTileDirtyByTile(tile + TILE_XY(1,1));
|
||||
MarkTileDirtyByTile(tile + TileDiffXY(0, 0));
|
||||
MarkTileDirtyByTile(tile + TileDiffXY(0, 1));
|
||||
MarkTileDirtyByTile(tile + TileDiffXY(1, 0));
|
||||
MarkTileDirtyByTile(tile + TileDiffXY(1, 1));
|
||||
}
|
||||
|
||||
int64 CalculateCompanyValue(Player *p) {
|
||||
byte owner = p->index;
|
||||
int64 CalculateCompanyValue(const Player* p)
|
||||
{
|
||||
PlayerID owner = p->index;
|
||||
int64 value;
|
||||
|
||||
{
|
||||
@@ -123,25 +124,31 @@ int UpdateCompanyRatingAndValue(Player *p, bool update)
|
||||
/* Count vehicles */
|
||||
{
|
||||
Vehicle *v;
|
||||
int32 min_profit = score_info[SCORE_MIN_PROFIT].needed;
|
||||
int32 min_profit = 0;
|
||||
bool min_profit_first = true;
|
||||
uint num = 0;
|
||||
|
||||
FOR_ALL_VEHICLES(v) {
|
||||
if (v->owner != owner)
|
||||
continue;
|
||||
if ((v->type == VEH_Train && v->subtype == TS_Front_Engine) ||
|
||||
v->type == VEH_Road ||
|
||||
(v->type == VEH_Aircraft && v->subtype<=2) ||
|
||||
v->type == VEH_Ship) {
|
||||
if ((v->type == VEH_Train && IsFrontEngine(v)) ||
|
||||
v->type == VEH_Road ||
|
||||
(v->type == VEH_Aircraft && v->subtype <= 2) ||
|
||||
v->type == VEH_Ship) {
|
||||
num++;
|
||||
if (v->age > 730) {
|
||||
if (min_profit > v->profit_last_year)
|
||||
/* Find the vehicle with the lowest amount of profit */
|
||||
if (min_profit_first == true) {
|
||||
min_profit = v->profit_last_year;
|
||||
min_profit_first = false;
|
||||
} else if (min_profit > v->profit_last_year)
|
||||
min_profit = v->profit_last_year;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
_score_part[owner][SCORE_VEHICLES] = num;
|
||||
/* Don't allow negative min_profit to show */
|
||||
if (min_profit > 0)
|
||||
_score_part[owner][SCORE_MIN_PROFIT] = min_profit;
|
||||
}
|
||||
@@ -222,7 +229,7 @@ int UpdateCompanyRatingAndValue(Player *p, bool update)
|
||||
|
||||
/* Generate score for loan */
|
||||
{
|
||||
_score_part[owner][SCORE_LOAN] = score_info[SCORE_LOAN].needed - p->current_loan;
|
||||
_score_part[owner][SCORE_LOAN] = _score_info[SCORE_LOAN].needed - p->current_loan;
|
||||
}
|
||||
|
||||
// Now we calculate the score for each item..
|
||||
@@ -235,10 +242,12 @@ int UpdateCompanyRatingAndValue(Player *p, bool update)
|
||||
// Skip the total
|
||||
if (i == SCORE_TOTAL) continue;
|
||||
// Check the score
|
||||
s = (_score_part[owner][i] >= score_info[i].needed) ? score_info[i].score : ((_score_part[owner][i] * score_info[i].score) / score_info[i].needed);
|
||||
s = (_score_part[owner][i] >= _score_info[i].needed) ?
|
||||
_score_info[i].score :
|
||||
((_score_part[owner][i] * _score_info[i].score) / _score_info[i].needed);
|
||||
if (s < 0) s = 0;
|
||||
score += s;
|
||||
total_score += score_info[i].score;
|
||||
total_score += _score_info[i].score;
|
||||
}
|
||||
|
||||
_score_part[owner][SCORE_TOTAL] = score;
|
||||
@@ -258,7 +267,7 @@ int UpdateCompanyRatingAndValue(Player *p, bool update)
|
||||
return score;
|
||||
}
|
||||
|
||||
// use 255 as new_player to delete the player.
|
||||
// use OWNER_SPECTATOR as new_player to delete the player.
|
||||
void ChangeOwnershipOfPlayerItems(PlayerID old_player, PlayerID new_player)
|
||||
{
|
||||
PlayerID old = _current_player;
|
||||
@@ -268,9 +277,9 @@ void ChangeOwnershipOfPlayerItems(PlayerID old_player, PlayerID new_player)
|
||||
Subsidy *s;
|
||||
|
||||
for (s = _subsidies; s != endof(_subsidies); s++) {
|
||||
if (s->cargo_type != 0xff && s->age >= 12) {
|
||||
if (s->cargo_type != CT_INVALID && s->age >= 12) {
|
||||
if (GetStation(s->to)->owner == old_player)
|
||||
s->cargo_type = 0xff;
|
||||
s->cargo_type = CT_INVALID;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -311,7 +320,7 @@ void ChangeOwnershipOfPlayerItems(PlayerID old_player, PlayerID new_player)
|
||||
if (v->owner == new_player) {
|
||||
switch (v->type) {
|
||||
case VEH_Train:
|
||||
if (v->subtype == TS_Front_Engine) num_train++;
|
||||
if (IsFrontEngine(v)) num_train++;
|
||||
break;
|
||||
case VEH_Road:
|
||||
num_road++;
|
||||
@@ -336,7 +345,7 @@ void ChangeOwnershipOfPlayerItems(PlayerID old_player, PlayerID new_player)
|
||||
DeleteVehicle(v);
|
||||
} else {
|
||||
v->owner = new_player;
|
||||
if (v->type == VEH_Train && v->subtype == TS_Front_Engine)
|
||||
if (v->type == VEH_Train && IsFrontEngine(v))
|
||||
v->unitnumber = ++num_train;
|
||||
else if (v->type == VEH_Road)
|
||||
v->unitnumber = ++num_road;
|
||||
@@ -375,13 +384,13 @@ void ChangeOwnershipOfPlayerItems(PlayerID old_player, PlayerID new_player)
|
||||
for (i = 0; i < 4; i++) {
|
||||
/* 'Sell' the share if this player has any */
|
||||
if (p->share_owners[i] == _current_player)
|
||||
p->share_owners[i] = 0xFF;
|
||||
p->share_owners[i] = OWNER_SPECTATOR;
|
||||
}
|
||||
}
|
||||
p = DEREF_PLAYER(_current_player);
|
||||
p = GetPlayer(_current_player);
|
||||
/* Sell all the shares that people have on this company */
|
||||
for (i = 0; i < 4; i++)
|
||||
p->share_owners[i] = 0xFF;
|
||||
p->share_owners[i] = OWNER_SPECTATOR;
|
||||
}
|
||||
|
||||
_current_player = old;
|
||||
@@ -389,11 +398,9 @@ void ChangeOwnershipOfPlayerItems(PlayerID old_player, PlayerID new_player)
|
||||
MarkWholeScreenDirty();
|
||||
}
|
||||
|
||||
extern void DeletePlayerWindows(int pi);
|
||||
|
||||
static void PlayersCheckBankrupt(Player *p)
|
||||
{
|
||||
int owner;
|
||||
PlayerID owner;
|
||||
int64 val;
|
||||
|
||||
// If the player has money again, it does not go bankrupt
|
||||
@@ -470,9 +477,14 @@ static void PlayersCheckBankrupt(Player *p)
|
||||
|
||||
// Convert everything the player owns to NO_OWNER
|
||||
p->money64 = p->player_money = 100000000;
|
||||
ChangeOwnershipOfPlayerItems(owner, 0xFF); // 255 is no owner
|
||||
ChangeOwnershipOfPlayerItems(owner, OWNER_SPECTATOR);
|
||||
// Register the player as not-active
|
||||
p->is_active = false;
|
||||
|
||||
if (!IS_HUMAN_PLAYER(owner) && (!_networking || _network_server) && _ai.enabled)
|
||||
AI_PlayerDied(owner);
|
||||
if (IS_HUMAN_PLAYER(owner) && owner == _local_player && _ai.network_client)
|
||||
AI_PlayerDied(owner);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -484,9 +496,9 @@ void DrawNewsBankrupcy(Window *w)
|
||||
|
||||
DrawNewsBorder(w);
|
||||
|
||||
p = DEREF_PLAYER(WP(w,news_d).ni->string_id & 15);
|
||||
p = GetPlayer(WP(w,news_d).ni->string_id & 15);
|
||||
DrawPlayerFace(p->face, p->player_color, 2, 23);
|
||||
GfxFillRect(3, 23, 3+91, 23+118, 0x4323);
|
||||
GfxFillRect(3, 23, 3+91, 23+118, 0x323 | USE_COLORTABLE);
|
||||
|
||||
SetDParam(0, p->president_name_1);
|
||||
SetDParam(1, p->president_name_2);
|
||||
@@ -551,11 +563,11 @@ void DrawNewsBankrupcy(Window *w)
|
||||
}
|
||||
}
|
||||
|
||||
StringID GetNewsStringBankrupcy(NewsItem *ni)
|
||||
StringID GetNewsStringBankrupcy(const NewsItem *ni)
|
||||
{
|
||||
Player *p = DEREF_PLAYER(ni->string_id & 0xF);
|
||||
const Player *p = GetPlayer(ni->string_id & 0xF);
|
||||
|
||||
switch(ni->string_id >> 4) {
|
||||
switch (ni->string_id >> 4) {
|
||||
case 1:
|
||||
SetDParam(0, STR_7056_TRANSPORT_COMPANY_IN_TROUBLE);
|
||||
SetDParam(1, STR_7057_WILL_BE_SOLD_OFF_OR_DECLARED);
|
||||
@@ -644,8 +656,8 @@ static void AddInflation(void)
|
||||
int i;
|
||||
int32 inf = _economy.infl_amount * 54;
|
||||
|
||||
for(i=0; i!=NUM_PRICES; i++) {
|
||||
AddSingleInflation( (int32*)&_price + i, _price_frac + i, inf );
|
||||
for (i = 0; i != NUM_PRICES; i++) {
|
||||
AddSingleInflation((int32*)&_price + i, _price_frac + i, inf);
|
||||
}
|
||||
|
||||
_economy.max_loan_unround += BIGMULUS(_economy.max_loan_unround, inf, 16);
|
||||
@@ -654,9 +666,9 @@ static void AddInflation(void)
|
||||
_economy.max_loan += 50000;
|
||||
|
||||
inf = _economy.infl_amount_pr * 54;
|
||||
for(i=0; i!=NUM_CARGO; i++) {
|
||||
for (i = 0; i != NUM_CARGO; i++) {
|
||||
AddSingleInflation(
|
||||
_cargo_payment_rates + i,
|
||||
(int32*)_cargo_payment_rates + i,
|
||||
_cargo_payment_rates_frac + i,
|
||||
inf
|
||||
);
|
||||
@@ -670,12 +682,11 @@ static void AddInflation(void)
|
||||
|
||||
static void PlayersPayInterest(void)
|
||||
{
|
||||
Player *p;
|
||||
const Player* p;
|
||||
int interest = _economy.interest_rate * 54;
|
||||
|
||||
FOR_ALL_PLAYERS(p) {
|
||||
if (!p->is_active)
|
||||
continue;
|
||||
if (!p->is_active) continue;
|
||||
|
||||
_current_player = p->index;
|
||||
SET_EXPENSES_TYPE(EXPENSES_LOAN_INT);
|
||||
@@ -689,14 +700,13 @@ static void PlayersPayInterest(void)
|
||||
|
||||
static void HandleEconomyFluctuations(void)
|
||||
{
|
||||
if (_opt.diff.economy == 0)
|
||||
return;
|
||||
if (_opt.diff.economy == 0) return;
|
||||
|
||||
if (--_economy.fluct == 0) {
|
||||
_economy.fluct = - (int)(Random()&3);
|
||||
_economy.fluct = -(int)GB(Random(), 0, 2);
|
||||
AddNewsItem(STR_7073_WORLD_RECESSION_FINANCIAL, NEWS_FLAGS(NM_NORMAL,0,NT_ECONOMY,0), 0, 0);
|
||||
} else if (_economy.fluct == -12) {
|
||||
_economy.fluct = (Random()&255) + 312;
|
||||
_economy.fluct = GB(Random(), 0, 8) + 312;
|
||||
AddNewsItem(STR_7074_RECESSION_OVER_UPTURN_IN, NEWS_FLAGS(NM_NORMAL,0,NT_ECONOMY,0), 0, 0);
|
||||
}
|
||||
}
|
||||
@@ -763,6 +773,33 @@ static const int32 _price_base[NUM_PRICES] = {
|
||||
1000000, // build_industry
|
||||
};
|
||||
|
||||
static byte price_base_multiplier[NUM_PRICES];
|
||||
|
||||
/**
|
||||
* Reset changes to the price base multipliers.
|
||||
*/
|
||||
void ResetPriceBaseMultipliers(void)
|
||||
{
|
||||
uint i;
|
||||
|
||||
// 8 means no multiplier.
|
||||
for (i = 0; i < NUM_PRICES; i++)
|
||||
price_base_multiplier[i] = 8;
|
||||
}
|
||||
|
||||
/**
|
||||
* Change a price base by the given factor.
|
||||
* The price base is altered by factors of two, with an offset of 8.
|
||||
* NewBaseCost = OldBaseCost * 2^(n-8)
|
||||
* @param price Index of price base to change.
|
||||
* @param factor Amount to change by.
|
||||
*/
|
||||
void SetPriceBaseMultiplier(uint price, byte factor)
|
||||
{
|
||||
assert(price < NUM_PRICES);
|
||||
price_base_multiplier[price] = factor;
|
||||
}
|
||||
|
||||
void StartupEconomy(void)
|
||||
{
|
||||
int i;
|
||||
@@ -779,6 +816,11 @@ void StartupEconomy(void)
|
||||
price = price * 9 >> 3;
|
||||
}
|
||||
}
|
||||
if (price_base_multiplier[i] > 8) {
|
||||
price <<= price_base_multiplier[i] - 8;
|
||||
} else {
|
||||
price >>= 8 - price_base_multiplier[i];
|
||||
}
|
||||
((int32*)&_price)[i] = price;
|
||||
_price_frac[i] = 0;
|
||||
}
|
||||
@@ -787,62 +829,48 @@ void StartupEconomy(void)
|
||||
_economy.infl_amount = _opt.diff.initial_interest;
|
||||
_economy.infl_amount_pr = max(0, _opt.diff.initial_interest - 1);
|
||||
_economy.max_loan_unround = _economy.max_loan = _opt.diff.max_loan * 1000;
|
||||
_economy.fluct = (byte)(Random()) + 168;
|
||||
_economy.fluct = GB(Random(), 0, 8) + 168;
|
||||
}
|
||||
|
||||
Pair SetupSubsidyDecodeParam(Subsidy *s, bool mode)
|
||||
Pair SetupSubsidyDecodeParam(const Subsidy* s, bool mode)
|
||||
{
|
||||
int tile, tile2;
|
||||
Industry *i;
|
||||
Town *t;
|
||||
Station *st;
|
||||
TileIndex tile;
|
||||
TileIndex tile2;
|
||||
Pair tp;
|
||||
|
||||
/* if mode is false, convert into plural */
|
||||
SetDParam(0, _cargoc.names_s[s->cargo_type] + (mode?0:32));
|
||||
/* if mode is false, use the singular form */
|
||||
SetDParam(0, _cargoc.names_s[s->cargo_type] + (mode ? 0 : 32));
|
||||
|
||||
if (s->age < 12) {
|
||||
if (!(s->cargo_type == CT_PASSENGERS || s->cargo_type == CT_MAIL)) {
|
||||
SetDParam(1, STR_2029);
|
||||
i = GetIndustry(s->from);
|
||||
tile = i->xy;
|
||||
SetDParam(2, i->town->townnametype);
|
||||
SetDParam(3, i->town->townnameparts);
|
||||
|
||||
SetDParam(4, i->type + STR_4802_COAL_MINE);
|
||||
if (s->cargo_type != CT_PASSENGERS && s->cargo_type != CT_MAIL) {
|
||||
SetDParam(1, STR_INDUSTRY);
|
||||
SetDParam(2, s->from);
|
||||
tile = GetIndustry(s->from)->xy;
|
||||
|
||||
if (s->cargo_type != CT_GOODS && s->cargo_type != CT_FOOD) {
|
||||
SetDParam(5, STR_2029);
|
||||
i = GetIndustry(s->to);
|
||||
tile2 = i->xy;
|
||||
SetDParam(8, i->type + STR_4802_COAL_MINE);
|
||||
SetDParam(6, i->town->townnametype);
|
||||
SetDParam(7, i->town->townnameparts);
|
||||
SetDParam(4, STR_INDUSTRY);
|
||||
SetDParam(5, s->to);
|
||||
tile2 = GetIndustry(s->to)->xy;
|
||||
} else {
|
||||
t = GetTown(s->to);
|
||||
tile2 = t->xy;
|
||||
SetDParam(5, t->townnametype);
|
||||
SetDParam(6, t->townnameparts);
|
||||
SetDParam(4, STR_TOWN);
|
||||
SetDParam(5, s->to);
|
||||
tile2 = GetTown(s->to)->xy;
|
||||
}
|
||||
} else {
|
||||
t = GetTown(s->from);
|
||||
tile = t->xy;
|
||||
SetDParam(1, t->townnametype);
|
||||
SetDParam(2, t->townnameparts);
|
||||
SetDParam(1, STR_TOWN);
|
||||
SetDParam(2, s->from);
|
||||
tile = GetTown(s->from)->xy;
|
||||
|
||||
t = GetTown(s->to);
|
||||
tile2 = t->xy;
|
||||
SetDParam(3, t->townnametype);
|
||||
SetDParam(4, t->townnameparts);
|
||||
SetDParam(4, STR_TOWN);
|
||||
SetDParam(5, s->to);
|
||||
tile2 = GetTown(s->to)->xy;
|
||||
}
|
||||
} else {
|
||||
st = GetStation(s->from);
|
||||
tile = st->xy;
|
||||
SetDParam(1, st->index);
|
||||
SetDParam(1, s->from);
|
||||
tile = GetStation(s->from)->xy;
|
||||
|
||||
st = GetStation(s->to);
|
||||
tile2 = st->xy;
|
||||
SetDParam(2, st->index);
|
||||
SetDParam(2, s->to);
|
||||
tile2 = GetStation(s->to)->xy;
|
||||
}
|
||||
|
||||
tp.a = tile;
|
||||
@@ -856,10 +884,10 @@ void DeleteSubsidyWithIndustry(uint16 index)
|
||||
Subsidy *s;
|
||||
|
||||
for(s=_subsidies; s != endof(_subsidies); s++) {
|
||||
if (s->cargo_type != 0xFF && s->age < 12 &&
|
||||
if (s->cargo_type != CT_INVALID && s->age < 12 &&
|
||||
s->cargo_type != CT_PASSENGERS && s->cargo_type != CT_MAIL &&
|
||||
(index == s->from || (s->cargo_type!=CT_GOODS && s->cargo_type!=CT_FOOD && index==s->to))) {
|
||||
s->cargo_type = 0xFF;
|
||||
s->cargo_type = CT_INVALID;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -870,9 +898,9 @@ void DeleteSubsidyWithStation(uint16 index)
|
||||
bool dirty = false;
|
||||
|
||||
for(s=_subsidies; s != endof(_subsidies); s++) {
|
||||
if (s->cargo_type != 0xFF && s->age >= 12 &&
|
||||
if (s->cargo_type != CT_INVALID && s->age >= 12 &&
|
||||
(s->from == index || s->to == index)) {
|
||||
s->cargo_type = 0xFF;
|
||||
s->cargo_type = CT_INVALID;
|
||||
dirty = true;
|
||||
}
|
||||
}
|
||||
@@ -918,7 +946,7 @@ static void FindSubsidyCargoRoute(FoundRoute *fr)
|
||||
return;
|
||||
|
||||
// Randomize cargo type
|
||||
if (Random()&1 && i->produced_cargo[1] != 0xFF) {
|
||||
if (Random()&1 && i->produced_cargo[1] != CT_INVALID) {
|
||||
cargo = i->produced_cargo[1];
|
||||
trans = i->pct_transported[1];
|
||||
total = i->total_production[1];
|
||||
@@ -931,7 +959,7 @@ static void FindSubsidyCargoRoute(FoundRoute *fr)
|
||||
// Quit if no production in this industry
|
||||
// or if the cargo type is passengers
|
||||
// or if the pct transported is already large enough
|
||||
if (total == 0 || trans > 42 || cargo == 0xFF || cargo == CT_PASSENGERS)
|
||||
if (total == 0 || trans > 42 || cargo == CT_INVALID || cargo == CT_PASSENGERS)
|
||||
return;
|
||||
|
||||
fr->cargo = cargo;
|
||||
@@ -962,38 +990,20 @@ static void FindSubsidyCargoRoute(FoundRoute *fr)
|
||||
|
||||
static bool CheckSubsidyDuplicate(Subsidy *s)
|
||||
{
|
||||
Subsidy *ss;
|
||||
const Subsidy* ss;
|
||||
|
||||
for(ss=_subsidies; ss != endof(_subsidies); ss++) {
|
||||
for (ss = _subsidies; ss != endof(_subsidies); ss++) {
|
||||
if (s != ss &&
|
||||
// ss->age < 12 &&
|
||||
ss->from == s->from &&
|
||||
ss->to == s->to &&
|
||||
ss->cargo_type == s->cargo_type) {
|
||||
s->cargo_type = 0xFF;
|
||||
s->cargo_type = CT_INVALID;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void RemoteSubsidyAdd(Subsidy *s_new)
|
||||
{
|
||||
Subsidy *s;
|
||||
Pair pair;
|
||||
|
||||
// search the first free subsidy
|
||||
for(s=_subsidies; s != endof(_subsidies); s++)
|
||||
if (s->cargo_type == 0xFF)
|
||||
break;
|
||||
|
||||
memcpy(s,s_new,sizeof(Subsidy));
|
||||
|
||||
pair = SetupSubsidyDecodeParam(s, 0);
|
||||
AddNewsItem(STR_2030_SERVICE_SUBSIDY_OFFERED, NEWS_FLAGS(NM_NORMAL, NF_TILE, NT_SUBSIDIES, 0), pair.a, pair.b);
|
||||
|
||||
InvalidateWindow(WC_SUBSIDIES_LIST, 0);
|
||||
}
|
||||
|
||||
static void SubsidyMonthlyHandler(void)
|
||||
{
|
||||
@@ -1005,13 +1015,13 @@ static void SubsidyMonthlyHandler(void)
|
||||
bool modified = false;
|
||||
|
||||
for(s=_subsidies; s != endof(_subsidies); s++) {
|
||||
if (s->cargo_type == 0xFF)
|
||||
if (s->cargo_type == CT_INVALID)
|
||||
continue;
|
||||
|
||||
if (s->age == 12-1) {
|
||||
pair = SetupSubsidyDecodeParam(s, 1);
|
||||
AddNewsItem(STR_202E_OFFER_OF_SUBSIDY_EXPIRED, NEWS_FLAGS(NM_NORMAL, NF_TILE, NT_SUBSIDIES, 0), pair.a, pair.b);
|
||||
s->cargo_type = 0xFF;
|
||||
s->cargo_type = CT_INVALID;
|
||||
modified = true;
|
||||
} else if (s->age == 2*12-1) {
|
||||
st = GetStation(s->to);
|
||||
@@ -1019,7 +1029,7 @@ static void SubsidyMonthlyHandler(void)
|
||||
pair = SetupSubsidyDecodeParam(s, 1);
|
||||
AddNewsItem(STR_202F_SUBSIDY_WITHDRAWN_SERVICE, NEWS_FLAGS(NM_NORMAL, NF_TILE, NT_SUBSIDIES, 0), pair.a, pair.b);
|
||||
}
|
||||
s->cargo_type = 0xFF;
|
||||
s->cargo_type = CT_INVALID;
|
||||
modified = true;
|
||||
} else {
|
||||
s->age++;
|
||||
@@ -1030,7 +1040,7 @@ static void SubsidyMonthlyHandler(void)
|
||||
if (CHANCE16(1,4)) {
|
||||
// Find a free slot
|
||||
s = _subsidies;
|
||||
while (s->cargo_type != 0xFF) {
|
||||
while (s->cargo_type != CT_INVALID) {
|
||||
if (++s == endof(_subsidies))
|
||||
goto no_add;
|
||||
}
|
||||
@@ -1065,7 +1075,7 @@ no_add:;
|
||||
InvalidateWindow(WC_SUBSIDIES_LIST, 0);
|
||||
}
|
||||
|
||||
static const byte _subsidies_desc[] = {
|
||||
static const SaveLoad _subsidies_desc[] = {
|
||||
SLE_VAR(Subsidy,cargo_type, SLE_UINT8),
|
||||
SLE_VAR(Subsidy,age, SLE_UINT8),
|
||||
SLE_CONDVAR(Subsidy,from, SLE_FILE_U8 | SLE_VAR_U16, 0, 4),
|
||||
@@ -1082,7 +1092,7 @@ static void Save_SUBS(void)
|
||||
|
||||
for(i=0; i!=lengthof(_subsidies); i++) {
|
||||
s = &_subsidies[i];
|
||||
if (s->cargo_type != 0xFF) {
|
||||
if (s->cargo_type != CT_INVALID) {
|
||||
SlSetArrayIndex(i);
|
||||
SlObject(s, _subsidies_desc);
|
||||
}
|
||||
@@ -1136,7 +1146,7 @@ static void DeliverGoodsToIndustry(TileIndex xy, byte cargo_type, int num_pieces
|
||||
FOR_ALL_INDUSTRIES(ind) {
|
||||
if (ind->xy != 0 && (cargo_type == ind->accepts_cargo[0] || cargo_type
|
||||
== ind->accepts_cargo[1] || cargo_type == ind->accepts_cargo[2]) &&
|
||||
ind->produced_cargo[0] != 0xFF &&
|
||||
ind->produced_cargo[0] != CT_INVALID &&
|
||||
ind->produced_cargo[0] != cargo_type &&
|
||||
(t = DistanceManhattan(ind->xy, xy)) < 2 * u) {
|
||||
u = t;
|
||||
@@ -1199,7 +1209,7 @@ static bool CheckSubsidised(Station *from, Station *to, byte cargo_type)
|
||||
pair = SetupSubsidyDecodeParam(s, 0);
|
||||
InjectDParam(2);
|
||||
|
||||
p = DEREF_PLAYER(_current_player);
|
||||
p = GetPlayer(_current_player);
|
||||
SetDParam(0, p->name_1);
|
||||
SetDParam(1, p->name_2);
|
||||
AddNewsItem(
|
||||
@@ -1224,7 +1234,7 @@ static int32 DeliverGoods(int num_pieces, byte cargo_type, uint16 source, uint16
|
||||
|
||||
// Update player statistics
|
||||
{
|
||||
Player *p = DEREF_PLAYER(_current_player);
|
||||
Player *p = GetPlayer(_current_player);
|
||||
p->cur_economy.delivered_cargo += num_pieces;
|
||||
SETBIT(p->cargo_types, cargo_type);
|
||||
}
|
||||
@@ -1237,26 +1247,14 @@ static int32 DeliverGoods(int num_pieces, byte cargo_type, uint16 source, uint16
|
||||
subsidised = CheckSubsidised(s_from, s_to, cargo_type);
|
||||
|
||||
// Increase town's counter for some special goods types
|
||||
{
|
||||
Town *t = s_to->town;
|
||||
if (cargo_type == CT_FOOD) t->new_act_food += num_pieces;
|
||||
if (cargo_type == CT_WATER) t->new_act_water += num_pieces;
|
||||
}
|
||||
if (cargo_type == CT_FOOD) s_to->town->new_act_food += num_pieces;
|
||||
if (cargo_type == CT_WATER) s_to->town->new_act_water += num_pieces;
|
||||
|
||||
// Give the goods to the industry.
|
||||
DeliverGoodsToIndustry(s_to->xy, cargo_type, num_pieces);
|
||||
|
||||
// Determine profit
|
||||
{
|
||||
int t = DistanceManhattan(s_from->xy, s_to->xy);
|
||||
int r = num_pieces;
|
||||
profit = 0;
|
||||
do {
|
||||
int u = min(r, 255);
|
||||
r -= u;
|
||||
profit += GetTransportedGoodsIncome(u, t, days_in_transit, cargo_type);
|
||||
} while (r != 0);
|
||||
}
|
||||
profit = GetTransportedGoodsIncome(num_pieces, DistanceManhattan(s_from->xy, s_to->xy), days_in_transit, cargo_type);
|
||||
|
||||
// Modify profit if a subsidy is in effect
|
||||
if (subsidised) {
|
||||
@@ -1275,10 +1273,6 @@ static int32 DeliverGoods(int num_pieces, byte cargo_type, uint16 source, uint16
|
||||
}
|
||||
}
|
||||
|
||||
// Computers get 25% extra profit if they're intelligent.
|
||||
if (_opt.diff.competitor_intelligence>=1 && !IS_HUMAN_PLAYER(_current_player))
|
||||
profit += profit >> 2;
|
||||
|
||||
return profit;
|
||||
}
|
||||
|
||||
@@ -1304,7 +1298,7 @@ static bool LoadWait(const Vehicle *v, const Vehicle *u) {
|
||||
}
|
||||
|
||||
FOR_ALL_VEHICLES(x) {
|
||||
if ((x->type != VEH_Train || x->subtype == TS_Front_Engine) && // for all locs
|
||||
if ((x->type != VEH_Train || IsFrontEngine(x)) && // for all locs
|
||||
u->last_station_visited == x->last_station_visited && // at the same station
|
||||
!(x->vehstatus & VS_STOPPED) && // not stopped
|
||||
x->current_order.type == OT_LOADING && // loading
|
||||
@@ -1338,15 +1332,16 @@ static bool LoadWait(const Vehicle *v, const Vehicle *u) {
|
||||
int LoadUnloadVehicle(Vehicle *v)
|
||||
{
|
||||
int profit = 0;
|
||||
int v_profit; //virtual profit for feeder systems
|
||||
int v_profit_total = 0;
|
||||
int unloading_time = 20;
|
||||
Vehicle *u = v;
|
||||
int result = 0;
|
||||
uint16 last_visited;
|
||||
Station *st;
|
||||
GoodsEntry *ge;
|
||||
int t;
|
||||
uint count, cap;
|
||||
byte old_player;
|
||||
PlayerID old_player;
|
||||
bool completely_empty = true;
|
||||
|
||||
assert(v->current_order.type == OT_LOADING);
|
||||
@@ -1359,13 +1354,15 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
st = GetStation(last_visited = v->last_station_visited);
|
||||
|
||||
for (; v != NULL; v = v->next) {
|
||||
GoodsEntry* ge;
|
||||
|
||||
if (v->cargo_cap == 0) continue;
|
||||
|
||||
ge = &st->goods[v->cargo_type];
|
||||
|
||||
/* unload? */
|
||||
if (v->cargo_count != 0) {
|
||||
if (v->cargo_source != last_visited && ge->waiting_acceptance & 0x8000) {
|
||||
if (v->cargo_source != last_visited && ge->waiting_acceptance & 0x8000 && !(u->current_order.flags & OF_TRANSFER)) {
|
||||
// deliver goods to the station
|
||||
st->time_since_unload = 0;
|
||||
|
||||
@@ -1373,11 +1370,22 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
profit += DeliverGoods(v->cargo_count, v->cargo_type, v->cargo_source, last_visited, v->cargo_days);
|
||||
result |= 1;
|
||||
v->cargo_count = 0;
|
||||
} else if (u->current_order.flags & OF_UNLOAD) {
|
||||
} else if (u->current_order.flags & (OF_UNLOAD | OF_TRANSFER)) {
|
||||
/* unload goods and let it wait at the station */
|
||||
st->time_since_unload = 0;
|
||||
|
||||
if ((t=ge->waiting_acceptance & 0xFFF) == 0) {
|
||||
v_profit = GetTransportedGoodsIncome(
|
||||
v->cargo_count,
|
||||
DistanceManhattan(GetStation(v->cargo_source)->xy, GetStation(last_visited)->xy),
|
||||
v->cargo_days,
|
||||
v->cargo_type) * 3 / 2;
|
||||
|
||||
v_profit_total += v_profit;
|
||||
|
||||
|
||||
unloading_time += v->cargo_count;
|
||||
t = GB(ge->waiting_acceptance, 0, 12);
|
||||
if (t == 0) {
|
||||
// No goods waiting at station
|
||||
ge->enroute_time = v->cargo_days;
|
||||
ge->enroute_from = v->cargo_source;
|
||||
@@ -1389,7 +1397,9 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
ge->enroute_from = v->cargo_source;
|
||||
}
|
||||
// Update amount of waiting cargo
|
||||
ge->waiting_acceptance = (ge->waiting_acceptance &~0xFFF) | min(v->cargo_count + t, 0xFFF);
|
||||
SB(ge->waiting_acceptance, 0, 12, min(v->cargo_count + t, 0xFFF));
|
||||
ge->feeder_profit += v_profit;
|
||||
u->profit_this_year += v_profit;
|
||||
result |= 2;
|
||||
v->cargo_count = 0;
|
||||
}
|
||||
@@ -1405,6 +1415,7 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
ge->days_since_pickup = 0;
|
||||
t = u->max_speed;
|
||||
if (u->type == VEH_Road) t >>=1;
|
||||
if (u->type == VEH_Train) t = u->u.rail.cached_max_speed;
|
||||
|
||||
// if last speed is 0, we treat that as if no vehicle has ever visited the station.
|
||||
ge->last_speed = t < 255 ? t : 255;
|
||||
@@ -1412,8 +1423,12 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
|
||||
// If there's goods waiting at the station, and the vehicle
|
||||
// has capacity for it, load it on the vehicle.
|
||||
if ((count=ge->waiting_acceptance & 0xFFF) != 0 &&
|
||||
count = GB(ge->waiting_acceptance, 0, 12);
|
||||
if (count != 0 &&
|
||||
(cap = v->cargo_cap - v->cargo_count) != 0) {
|
||||
int cargoshare;
|
||||
int feeder_profit_share;
|
||||
|
||||
if (v->cargo_count == 0)
|
||||
TriggerVehicle(v, VEHICLE_TRIGGER_NEW_CARGO);
|
||||
|
||||
@@ -1431,8 +1446,12 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
completely_empty = false;
|
||||
|
||||
if (cap > count) cap = count;
|
||||
cargoshare = cap * 10000 / ge->waiting_acceptance;
|
||||
feeder_profit_share = ge->feeder_profit * cargoshare / 10000;
|
||||
v->cargo_count += cap;
|
||||
ge->waiting_acceptance -= cap;
|
||||
v->profit_this_year -= feeder_profit_share;
|
||||
ge->feeder_profit -= feeder_profit_share;
|
||||
unloading_time += cap;
|
||||
st->time_since_load = 0;
|
||||
|
||||
@@ -1444,16 +1463,19 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
v = u;
|
||||
|
||||
if (v_profit_total > 0)
|
||||
ShowFeederIncomeAnimation(v->x_pos, v->y_pos, v->z_pos, v_profit_total);
|
||||
|
||||
if (v->type == VEH_Train) {
|
||||
int num = - (int)GetStationPlatforms(st, v->tile) * 2;
|
||||
do num++; while ( (v=v->next) != NULL);
|
||||
if (num > 0) {
|
||||
unloading_time <<=1;
|
||||
unloading_time += num * unloading_time;
|
||||
// Each platform tile is worth 2 rail vehicles.
|
||||
int overhang = v->u.rail.cached_total_length - GetStationPlatforms(st, v->tile) * 16;
|
||||
if (overhang > 0) {
|
||||
unloading_time <<= 1;
|
||||
unloading_time += (overhang * unloading_time) / 8;
|
||||
}
|
||||
v = u;
|
||||
}
|
||||
|
||||
v->load_unload_time_rem = unloading_time;
|
||||
@@ -1472,8 +1494,7 @@ int LoadUnloadVehicle(Vehicle *v)
|
||||
v->profit_this_year += profit;
|
||||
SubtractMoneyFromPlayer(-profit);
|
||||
|
||||
if (_current_player == _local_player)
|
||||
SndPlayVehicleFx(SND_14_CASHTILL, v);
|
||||
if (IsLocalPlayer()) SndPlayVehicleFx(SND_14_CASHTILL, v);
|
||||
|
||||
ShowCostOrIncomeAnimation(v->x_pos, v->y_pos, v->z_pos, -profit);
|
||||
}
|
||||
@@ -1511,14 +1532,14 @@ static void DoAcquireCompany(Player *p)
|
||||
ChangeOwnershipOfPlayerItems(pi, _current_player);
|
||||
|
||||
if (p->bankrupt_value == 0) {
|
||||
owner = DEREF_PLAYER(_current_player);
|
||||
owner = GetPlayer(_current_player);
|
||||
owner->current_loan += p->current_loan;
|
||||
}
|
||||
|
||||
value = CalculateCompanyValue(p) >> 2;
|
||||
for(i=0; i!=4; i++) {
|
||||
if (p->share_owners[i] != 0xFF) {
|
||||
owner = DEREF_PLAYER(p->share_owners[i]);
|
||||
if (p->share_owners[i] != OWNER_SPECTATOR) {
|
||||
owner = GetPlayer(p->share_owners[i]);
|
||||
owner->money64 += value;
|
||||
owner->yearly_expenses[0][EXPENSES_OTHER] += value;
|
||||
UpdatePlayerMoney32(owner);
|
||||
@@ -1547,7 +1568,7 @@ int32 CmdBuyShareInCompany(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
if (p1 >= MAX_PLAYERS || !_patches.allow_shares) return CMD_ERROR;
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_OTHER);
|
||||
p = DEREF_PLAYER(p1);
|
||||
p = GetPlayer(p1);
|
||||
|
||||
/* Protect new companies from hostile takeovers */
|
||||
if (_cur_year - p->inaugurated_year < 6) return_cmd_error(STR_7080_PROTECTED);
|
||||
@@ -1560,10 +1581,10 @@ int32 CmdBuyShareInCompany(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
|
||||
cost = CalculateCompanyValue(p) >> 2;
|
||||
if (flags & DC_EXEC) {
|
||||
PlayerID* b = p->share_owners;
|
||||
int i;
|
||||
byte *b = p->share_owners;
|
||||
|
||||
while (*b != 0xFF) b++; /* share owners is guaranteed to contain at least one 0xFF */
|
||||
while (*b != OWNER_SPECTATOR) b++; /* share owners is guaranteed to contain at least one OWNER_SPECTATOR */
|
||||
*b = _current_player;
|
||||
|
||||
for (i = 0; p->share_owners[i] == _current_player;) {
|
||||
@@ -1592,7 +1613,7 @@ int32 CmdSellShareInCompany(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
if (p1 >= MAX_PLAYERS || !_patches.allow_shares) return CMD_ERROR;
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_OTHER);
|
||||
p = DEREF_PLAYER(p1);
|
||||
p = GetPlayer(p1);
|
||||
|
||||
/* Those lines are here for network-protection (clients can be slow) */
|
||||
if (GetAmountOwnedBy(p, _current_player) == 0) return 0;
|
||||
@@ -1602,9 +1623,9 @@ int32 CmdSellShareInCompany(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
cost = -(cost - (cost >> 7));
|
||||
|
||||
if (flags & DC_EXEC) {
|
||||
byte *b = p->share_owners;
|
||||
PlayerID* b = p->share_owners;
|
||||
while (*b != _current_player) b++; /* share owners is guaranteed to contain player */
|
||||
*b = 0xFF;
|
||||
*b = OWNER_SPECTATOR;
|
||||
InvalidateWindow(WC_COMPANY, (int)p1);
|
||||
}
|
||||
return cost;
|
||||
@@ -1626,7 +1647,7 @@ int32 CmdBuyCompany(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
if (p1 >= MAX_PLAYERS || _networking) return CMD_ERROR;
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_OTHER);
|
||||
p = DEREF_PLAYER(p1);
|
||||
p = GetPlayer(p1);
|
||||
|
||||
if (!p->is_ai) return CMD_ERROR;
|
||||
|
||||
@@ -1650,7 +1671,7 @@ static void SaveLoad_CAPR(void)
|
||||
SlArray(&_cargo_payment_rates_frac, NUM_CARGO, SLE_UINT16);
|
||||
}
|
||||
|
||||
static const byte _economy_desc[] = {
|
||||
static const SaveLoad _economy_desc[] = {
|
||||
SLE_VAR(Economy,max_loan, SLE_INT32),
|
||||
SLE_VAR(Economy,max_loan_unround, SLE_INT32),
|
||||
SLE_VAR(Economy,fluct, SLE_FILE_I16 | SLE_VAR_I32),
|
||||
@@ -1663,7 +1684,7 @@ static const byte _economy_desc[] = {
|
||||
// Economy variables
|
||||
static void SaveLoad_ECMY(void)
|
||||
{
|
||||
SlObject(&_economy, &_economy_desc);
|
||||
SlObject(&_economy, _economy_desc);
|
||||
}
|
||||
|
||||
const ChunkHandler _economy_chunk_handlers[] = {
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef ECONOMY_H
|
||||
#define ECONOMY_H
|
||||
|
||||
void ResetPriceBaseMultipliers(void);
|
||||
void SetPriceBaseMultiplier(uint price, byte factor);
|
||||
|
||||
typedef struct {
|
||||
// Maximum possible loan
|
||||
int32 max_loan;
|
||||
@@ -47,32 +52,19 @@ typedef struct ScoreInfo {
|
||||
int score; // How much score it will give
|
||||
} ScoreInfo;
|
||||
|
||||
static const ScoreInfo score_info[] = {
|
||||
{SCORE_VEHICLES, 120, 100},
|
||||
{SCORE_STATIONS, 80, 100},
|
||||
{SCORE_MIN_PROFIT, 10000, 100},
|
||||
{SCORE_MIN_INCOME, 50000, 50},
|
||||
{SCORE_MAX_INCOME, 100000, 100},
|
||||
{SCORE_DELIVERED, 40000, 400},
|
||||
{SCORE_CARGO, 8, 50},
|
||||
{SCORE_MONEY, 10000000, 50},
|
||||
{SCORE_LOAN, 250000, 50},
|
||||
{SCORE_TOTAL, 0, 0}
|
||||
};
|
||||
|
||||
int _score_part[MAX_PLAYERS][NUM_SCORE];
|
||||
extern const ScoreInfo _score_info[];
|
||||
extern int _score_part[MAX_PLAYERS][NUM_SCORE];
|
||||
|
||||
int UpdateCompanyRatingAndValue(Player *p, bool update);
|
||||
void UpdatePlayerHouse(Player *p, uint score);
|
||||
|
||||
|
||||
VARDEF Subsidy _subsidies[MAX_PLAYERS];
|
||||
Pair SetupSubsidyDecodeParam(Subsidy *s, bool mode);
|
||||
Pair SetupSubsidyDecodeParam(const Subsidy* s, bool mode);
|
||||
void DeleteSubsidyWithIndustry(uint16 index);
|
||||
void DeleteSubsidyWithStation(uint16 index);
|
||||
void RemoteSubsidyAdd(Subsidy *s_new);
|
||||
|
||||
int32 GetTransportedGoodsIncome(uint num_pieces, uint dist, byte transit_days, byte cargo_type);
|
||||
uint MoveGoodsToStation(uint tile, int w, int h, int type, uint amount);
|
||||
uint MoveGoodsToStation(TileIndex tile, int w, int h, int type, uint amount);
|
||||
|
||||
#endif /* ECONOMY_H */
|
||||
|
||||
+36
-14
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
// This pretty simple file checks if the system is LITTLE_ENDIAN or BIG_ENDIAN
|
||||
@@ -9,22 +11,42 @@
|
||||
// care of the real writing to the file.
|
||||
|
||||
int main (int argc, char *argv[]) {
|
||||
unsigned char EndianTest[2] = { 1, 0 };
|
||||
int force_BE = 0, force_LE = 0;
|
||||
unsigned char EndianTest[2] = { 1, 0 };
|
||||
int force_BE = 0, force_LE = 0, force_PREPROCESSOR = 0;
|
||||
|
||||
if (argc > 1 && strcmp(argv[1], "BE") == 0)
|
||||
force_BE = 1;
|
||||
if (argc > 1 && strcmp(argv[1], "LE") == 0)
|
||||
force_LE = 1;
|
||||
if (argc > 1 && strcmp(argv[1], "BE") == 0)
|
||||
force_BE = 1;
|
||||
if (argc > 1 && strcmp(argv[1], "LE") == 0)
|
||||
force_LE = 1;
|
||||
if (argc > 1 && strcmp(argv[1], "PREPROCESSOR") == 0)
|
||||
force_PREPROCESSOR = 1;
|
||||
|
||||
printf("#ifndef ENDIAN_H\n#define ENDIAN_H\n");
|
||||
printf("#ifndef ENDIAN_H\n#define ENDIAN_H\n");
|
||||
|
||||
if ( (*(short *) EndianTest == 1 && force_BE != 1) || force_LE == 1)
|
||||
printf("#define TTD_LITTLE_ENDIAN\n");
|
||||
else
|
||||
printf("#define TTD_BIG_ENDIAN\n");
|
||||
if (force_LE == 1) {
|
||||
printf("#define TTD_LITTLE_ENDIAN\n");
|
||||
} else {
|
||||
if (force_BE == 1) {
|
||||
printf("#define TTD_BIG_ENDIAN\n");
|
||||
} else {
|
||||
if (force_PREPROCESSOR == 1) {
|
||||
// adding support for universal binaries on OSX
|
||||
// Universal binaries supports both PPC and x86
|
||||
// If a compiler for OSX gets this setting, it will always pick the correct endian and no test is needed
|
||||
printf("#ifdef __BIG_ENDIAN__\n");
|
||||
printf("#define TTD_BIG_ENDIAN\n");
|
||||
printf("#else\n");
|
||||
printf("#define TTD_LITTLE_ENDIAN\n");
|
||||
printf("#endif\n");
|
||||
} else {
|
||||
if ( *(short *) EndianTest == 1 )
|
||||
printf("#define TTD_LITTLE_ENDIAN\n");
|
||||
else
|
||||
printf("#define TTD_BIG_ENDIAN\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
printf("#endif\n");
|
||||
|
||||
printf("#endif\n");
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef ENGINE_H
|
||||
#define ENGINE_H
|
||||
|
||||
/** @file engine.h
|
||||
*/
|
||||
|
||||
#include "sprite.h"
|
||||
#include "pool.h"
|
||||
|
||||
typedef struct RailVehicleInfo {
|
||||
byte image_index;
|
||||
@@ -9,11 +15,20 @@ typedef struct RailVehicleInfo {
|
||||
byte base_cost;
|
||||
uint16 max_speed;
|
||||
uint16 power;
|
||||
byte weight;
|
||||
uint16 weight;
|
||||
byte running_cost_base;
|
||||
byte running_cost_class;
|
||||
byte engclass; // 0: steam, 1: diesel, 2: electric
|
||||
byte capacity;
|
||||
byte cargo_type;
|
||||
byte callbackmask; // see CallbackMask enum
|
||||
uint16 pow_wag_power;
|
||||
byte pow_wag_weight;
|
||||
byte visual_effect; // NOTE: this is not 100% implemented yet, at the moment it is only used as a 'fallback' value
|
||||
// for when the 'powered wagon' callback fails. But it should really also determine what
|
||||
// kind of visual effect to generate for a vehicle (default, steam, diesel, electric).
|
||||
// Same goes for the callback result, which atm is only used to check if a wagon is powered.
|
||||
byte shorten_factor; // length on main map for this type is 8 - shorten_factor
|
||||
} RailVehicleInfo;
|
||||
|
||||
typedef struct ShipVehicleInfo {
|
||||
@@ -49,12 +64,17 @@ typedef struct RoadVehicleInfo {
|
||||
byte cargo_type;
|
||||
} RoadVehicleInfo;
|
||||
|
||||
/** Information about a vehicle
|
||||
* @see table/engines.h
|
||||
*/
|
||||
typedef struct EngineInfo {
|
||||
uint16 base_intro;
|
||||
byte unk2;
|
||||
byte unk2; ///< Carriages have the highest bit set in this one
|
||||
byte lifelength;
|
||||
byte base_life;
|
||||
byte railtype_climates;
|
||||
byte railtype:4;
|
||||
byte climates:4;
|
||||
uint32 refit_mask;
|
||||
} EngineInfo;
|
||||
|
||||
typedef struct Engine {
|
||||
@@ -66,10 +86,10 @@ typedef struct Engine {
|
||||
uint16 duration_phase_1, duration_phase_2, duration_phase_3;
|
||||
byte lifelength;
|
||||
byte flags;
|
||||
PlayerID preview_player;
|
||||
byte preview_player;
|
||||
byte preview_wait;
|
||||
byte railtype;
|
||||
PlayerID player_avail;
|
||||
byte player_avail;
|
||||
byte type; // type, ie VEH_Road, VEH_Train, etc. Same as in vehicle.h
|
||||
} Engine;
|
||||
|
||||
@@ -83,6 +103,10 @@ enum {
|
||||
NUM_VEHICLE_TYPES = 6
|
||||
};
|
||||
|
||||
enum {
|
||||
INVALID_ENGINE = 0xFFFF,
|
||||
};
|
||||
|
||||
void AddTypeToEngines(void);
|
||||
void StartupEngines(void);
|
||||
|
||||
@@ -122,17 +146,49 @@ enum GlobalCargo {
|
||||
NUM_GLOBAL_CID = 31
|
||||
};
|
||||
|
||||
// This enum lists the implemented callbacks
|
||||
// Use as argument for the GetCallBackResult function (see comments there)
|
||||
enum CallbackID {
|
||||
// Powered wagons, if the result is lower as 0x40 then the wagon is powered
|
||||
// TODO: interpret the rest of the result, aka "visual effects"
|
||||
CBID_WAGON_POWER = 0x10,
|
||||
|
||||
// Vehicle length, returns the amount of 1/8's the vehicle is shorter
|
||||
// only for train vehicles
|
||||
CBID_VEH_LENGTH = 0x11,
|
||||
|
||||
// Refit capacity, the passed vehicle needs to have its ->cargo_type set to
|
||||
// the cargo we are refitting to, returns the new cargo capacity
|
||||
CBID_REFIT_CAP = 0x15,
|
||||
|
||||
CBID_ARTIC_ENGINE = 0x16,
|
||||
};
|
||||
|
||||
// bit positions for rvi->callbackmask, indicates which callbacks are used by an engine
|
||||
// (some callbacks are always used, and dont appear here)
|
||||
enum CallbackMask {
|
||||
CBM_WAGON_POWER = 0,
|
||||
CBM_VEH_LENGTH = 1,
|
||||
CBM_REFIT_CAP = 3,
|
||||
CBM_ARTIC_ENGINE = 4,
|
||||
};
|
||||
|
||||
enum {
|
||||
CALLBACK_FAILED = 0xFFFF
|
||||
};
|
||||
|
||||
VARDEF const uint32 _default_refitmasks[NUM_VEHICLE_TYPES];
|
||||
VARDEF const CargoID _global_cargo_id[NUM_LANDSCAPE][NUM_CARGO];
|
||||
VARDEF const uint32 _landscape_global_cargo_mask[NUM_LANDSCAPE];
|
||||
VARDEF const CargoID _local_cargo_id_ctype[NUM_GLOBAL_CID];
|
||||
VARDEF const uint32 cargo_classes[16];
|
||||
|
||||
VARDEF uint32 _engine_refit_masks[256];
|
||||
VARDEF byte _engine_original_sprites[256];
|
||||
void SetWagonOverrideSprites(byte engine, struct SpriteGroup *group, byte *train_id, int trains);
|
||||
void SetCustomEngineSprites(byte engine, byte cargo, struct SpriteGroup *group);
|
||||
void SetWagonOverrideSprites(EngineID engine, struct SpriteGroup *group, byte *train_id, int trains);
|
||||
void SetCustomEngineSprites(EngineID engine, byte cargo, struct SpriteGroup *group);
|
||||
// loaded is in percents, overriding_engine 0xffff is none
|
||||
int GetCustomEngineSprite(byte engine, const Vehicle *v, byte direction);
|
||||
int GetCustomEngineSprite(EngineID engine, const Vehicle *v, byte direction);
|
||||
uint16 GetCallBackResult(uint16 callback_info, EngineID engine, const Vehicle *v);
|
||||
bool UsesWagonOverride(const Vehicle *v);
|
||||
#define GetCustomVehicleSprite(v, direction) GetCustomEngineSprite(v->engine_type, v, direction)
|
||||
#define GetCustomVehicleIcon(et, direction) GetCustomEngineSprite(et, NULL, direction)
|
||||
|
||||
@@ -147,27 +203,19 @@ typedef enum VehicleTrigger {
|
||||
} VehicleTrigger;
|
||||
void TriggerVehicle(Vehicle *veh, VehicleTrigger trigger);
|
||||
|
||||
void SetCustomEngineName(int engine, const char *name);
|
||||
StringID GetCustomEngineName(int engine);
|
||||
void SetCustomEngineName(EngineID engine, const char *name);
|
||||
StringID GetCustomEngineName(EngineID engine);
|
||||
|
||||
|
||||
void DrawTrainEngine(int x, int y, int engine, uint32 image_ormod);
|
||||
void DrawRoadVehEngine(int x, int y, int engine, uint32 image_ormod);
|
||||
void DrawShipEngine(int x, int y, int engine, uint32 image_ormod);
|
||||
void DrawAircraftEngine(int x, int y, int engine, uint32 image_ormod);
|
||||
|
||||
void DrawTrainEngineInfo(int engine, int x, int y, int maxw);
|
||||
void DrawRoadVehEngineInfo(int engine, int x, int y, int maxw);
|
||||
void DrawShipEngineInfo(int engine, int x, int y, int maxw);
|
||||
void DrawAircraftEngineInfo(int engine, int x, int y, int maxw);
|
||||
|
||||
void AcceptEnginePreview(Engine *e, PlayerID player);
|
||||
void DrawTrainEngine(int x, int y, EngineID engine, uint32 image_ormod);
|
||||
void DrawRoadVehEngine(int x, int y, EngineID engine, uint32 image_ormod);
|
||||
void DrawShipEngine(int x, int y, EngineID engine, uint32 image_ormod);
|
||||
void DrawAircraftEngine(int x, int y, EngineID engine, uint32 image_ormod);
|
||||
|
||||
void LoadCustomEngineNames(void);
|
||||
void DeleteCustomEngineNames(void);
|
||||
|
||||
bool IsEngineBuildable(uint engine, byte type);
|
||||
void UnInitNewgrEngines(void);
|
||||
|
||||
enum {
|
||||
NUM_NORMAL_RAIL_ENGINES = 54,
|
||||
@@ -184,8 +232,8 @@ enum {
|
||||
};
|
||||
VARDEF Engine _engines[TOTAL_NUM_ENGINES];
|
||||
#define FOR_ALL_ENGINES(e) for (e = _engines; e != endof(_engines); e++)
|
||||
#define DEREF_ENGINE(i) (GetEngine(i))
|
||||
static inline Engine* GetEngine(uint i)
|
||||
|
||||
static inline Engine* GetEngine(EngineID i)
|
||||
{
|
||||
assert(i < lengthof(_engines));
|
||||
return &_engines[i];
|
||||
@@ -200,34 +248,120 @@ static inline bool IsEngineIndex(uint index)
|
||||
|
||||
/* Access Vehicle Data */
|
||||
//#include "table/engines.h"
|
||||
extern const EngineInfo orig_engine_info[TOTAL_NUM_ENGINES];
|
||||
extern const RailVehicleInfo orig_rail_vehicle_info[NUM_TRAIN_ENGINES];
|
||||
extern const ShipVehicleInfo orig_ship_vehicle_info[NUM_SHIP_ENGINES];
|
||||
extern const AircraftVehicleInfo orig_aircraft_vehicle_info[NUM_AIRCRAFT_ENGINES];
|
||||
extern const RoadVehicleInfo orig_road_vehicle_info[NUM_ROAD_ENGINES];
|
||||
|
||||
extern EngineInfo _engine_info[TOTAL_NUM_ENGINES];
|
||||
extern RailVehicleInfo _rail_vehicle_info[NUM_TRAIN_ENGINES];
|
||||
extern ShipVehicleInfo _ship_vehicle_info[NUM_SHIP_ENGINES];
|
||||
extern AircraftVehicleInfo _aircraft_vehicle_info[NUM_AIRCRAFT_ENGINES];
|
||||
extern RoadVehicleInfo _road_vehicle_info[NUM_ROAD_ENGINES];
|
||||
|
||||
static inline RailVehicleInfo *RailVehInfo(uint e)
|
||||
static inline const RailVehicleInfo* RailVehInfo(EngineID e)
|
||||
{
|
||||
assert(e < lengthof(_rail_vehicle_info));
|
||||
return &_rail_vehicle_info[e];
|
||||
}
|
||||
|
||||
static inline ShipVehicleInfo *ShipVehInfo(uint e)
|
||||
static inline const ShipVehicleInfo* ShipVehInfo(EngineID e)
|
||||
{
|
||||
assert(e - SHIP_ENGINES_INDEX < lengthof(_ship_vehicle_info));
|
||||
assert(e >= SHIP_ENGINES_INDEX && e < SHIP_ENGINES_INDEX + lengthof(_ship_vehicle_info));
|
||||
return &_ship_vehicle_info[e - SHIP_ENGINES_INDEX];
|
||||
}
|
||||
|
||||
static inline AircraftVehicleInfo *AircraftVehInfo(uint e)
|
||||
static inline const AircraftVehicleInfo* AircraftVehInfo(EngineID e)
|
||||
{
|
||||
assert(e - AIRCRAFT_ENGINES_INDEX < lengthof(_aircraft_vehicle_info));
|
||||
assert(e >= AIRCRAFT_ENGINES_INDEX && e < AIRCRAFT_ENGINES_INDEX + lengthof(_aircraft_vehicle_info));
|
||||
return &_aircraft_vehicle_info[e - AIRCRAFT_ENGINES_INDEX];
|
||||
}
|
||||
|
||||
static inline RoadVehicleInfo *RoadVehInfo(uint e)
|
||||
static inline const RoadVehicleInfo* RoadVehInfo(EngineID e)
|
||||
{
|
||||
assert(e - ROAD_ENGINES_INDEX < lengthof(_road_vehicle_info));
|
||||
assert(e >= ROAD_ENGINES_INDEX && e < ROAD_ENGINES_INDEX + lengthof(_road_vehicle_info));
|
||||
return &_road_vehicle_info[e - ROAD_ENGINES_INDEX];
|
||||
}
|
||||
|
||||
#endif
|
||||
void UnloadWagonOverrides(void);
|
||||
void UnloadCustomEngineSprites(void);
|
||||
void UnloadCustomEngineNames(void);
|
||||
|
||||
/************************************************************************
|
||||
* Engine Replacement stuff
|
||||
************************************************************************/
|
||||
|
||||
/**
|
||||
* Struct to store engine replacements. DO NOT USE outside of engine.c. Is
|
||||
* placed here so the only exception to this rule, the saveload code, can use
|
||||
* it.
|
||||
*/
|
||||
struct EngineRenew {
|
||||
uint16 index;
|
||||
EngineID from;
|
||||
EngineID to;
|
||||
struct EngineRenew *next;
|
||||
};
|
||||
|
||||
typedef struct EngineRenew EngineRenew;
|
||||
|
||||
/**
|
||||
* Memory pool for engine renew elements. DO NOT USE outside of engine.c. Is
|
||||
* placed here so the only exception to this rule, the saveload code, can use
|
||||
* it.
|
||||
*/
|
||||
extern MemoryPool _engine_renew_pool;
|
||||
|
||||
/**
|
||||
* DO NOT USE outside of engine.c. Is
|
||||
* placed here so the only exception to this rule, the saveload code, can use
|
||||
* it.
|
||||
*/
|
||||
static inline EngineRenew *GetEngineRenew(uint16 index)
|
||||
{
|
||||
return (EngineRenew*)GetItemFromPool(&_engine_renew_pool, index);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* A list to group EngineRenew directives together (such as per-player).
|
||||
*/
|
||||
typedef EngineRenew* EngineRenewList;
|
||||
|
||||
/**
|
||||
* Remove all engine replacement settings for the player.
|
||||
* @param er The renewlist for a given player.
|
||||
* @return The new renewlist for the player.
|
||||
*/
|
||||
void RemoveAllEngineReplacement(EngineRenewList* erl);
|
||||
|
||||
/**
|
||||
* Retrieve the engine replacement in a given renewlist for an original engine type.
|
||||
* @param erl The renewlist to search in.
|
||||
* @param engine Engine type to be replaced.
|
||||
* @return The engine type to replace with, or INVALID_ENGINE if no
|
||||
* replacement is in the list.
|
||||
*/
|
||||
EngineID EngineReplacement(EngineRenewList erl, EngineID engine);
|
||||
|
||||
/**
|
||||
* Add an engine replacement to the given renewlist.
|
||||
* @param erl The renewlist to add to.
|
||||
* @param old_engine The original engine type.
|
||||
* @param new_engine The replacement engine type.
|
||||
* @param flags The calling command flags.
|
||||
* @return 0 on success, CMD_ERROR on failure.
|
||||
*/
|
||||
int32 AddEngineReplacement(EngineRenewList* erl, EngineID old_engine, EngineID new_engine, uint32 flags);
|
||||
|
||||
/**
|
||||
* Remove an engine replacement from a given renewlist.
|
||||
* @param erl The renewlist from which to remove the replacement
|
||||
* @param engine The original engine type.
|
||||
* @param flags The calling command flags.
|
||||
* @return 0 on success, CMD_ERROR on failure.
|
||||
*/
|
||||
int32 RemoveEngineReplacement(EngineRenewList* erl, EngineID engine, uint32 flags);
|
||||
|
||||
#endif /* ENGINE_H */
|
||||
|
||||
+112
-46
@@ -1,6 +1,10 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "table/sprites.h"
|
||||
#include "functions.h"
|
||||
#include "window.h"
|
||||
#include "gui.h"
|
||||
#include "viewport.h"
|
||||
@@ -8,18 +12,16 @@
|
||||
#include "engine.h"
|
||||
#include "command.h"
|
||||
#include "news.h"
|
||||
#include "variables.h"
|
||||
|
||||
|
||||
static StringID GetEngineCategoryName(byte engine)
|
||||
static StringID GetEngineCategoryName(EngineID engine)
|
||||
{
|
||||
if (engine < NUM_TRAIN_ENGINES) {
|
||||
switch (_engines[engine].railtype) {
|
||||
case 0:
|
||||
return STR_8102_RAILROAD_LOCOMOTIVE;
|
||||
case 1:
|
||||
return STR_8106_MONORAIL_LOCOMOTIVE;
|
||||
case 2:
|
||||
return STR_8107_MAGLEV_LOCOMOTIVE;
|
||||
switch (GetEngine(engine)->railtype) {
|
||||
case RAILTYPE_RAIL: return STR_8102_RAILROAD_LOCOMOTIVE;
|
||||
case RAILTYPE_MONO: return STR_8106_MONORAIL_LOCOMOTIVE;
|
||||
case RAILTYPE_MAGLEV: return STR_8107_MAGLEV_LOCOMOTIVE;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,7 +35,7 @@ static StringID GetEngineCategoryName(byte engine)
|
||||
}
|
||||
|
||||
static const Widget _engine_preview_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 5, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 5, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 5, 11, 299, 0, 13, STR_8100_MESSAGE_FROM_VEHICLE_MANUFACTURE, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 5, 0, 299, 14, 191, 0x0, STR_NULL},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 5, 85, 144, 172, 183, STR_00C9_NO, STR_NULL},
|
||||
@@ -41,14 +43,19 @@ static const Widget _engine_preview_widgets[] = {
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
typedef void DrawEngineProc(int x, int y, int engine, uint32 image_ormod);
|
||||
typedef void DrawEngineInfoProc(int x, int y, int engine, int maxw);
|
||||
typedef void DrawEngineProc(int x, int y, EngineID engine, uint32 image_ormod);
|
||||
typedef void DrawEngineInfoProc(EngineID, int x, int y, int maxw);
|
||||
|
||||
typedef struct DrawEngineInfo {
|
||||
DrawEngineProc *engine_proc;
|
||||
DrawEngineInfoProc *info_proc;
|
||||
} DrawEngineInfo;
|
||||
|
||||
static void DrawTrainEngineInfo(EngineID engine, int x, int y, int maxw);
|
||||
static void DrawRoadVehEngineInfo(EngineID engine, int x, int y, int maxw);
|
||||
static void DrawShipEngineInfo(EngineID engine, int x, int y, int maxw);
|
||||
static void DrawAircraftEngineInfo(EngineID engine, int x, int y, int maxw);
|
||||
|
||||
static const DrawEngineInfo _draw_engine_list[4] = {
|
||||
{DrawTrainEngine,DrawTrainEngineInfo},
|
||||
{DrawRoadVehEngine,DrawRoadVehEngineInfo},
|
||||
@@ -58,39 +65,40 @@ static const DrawEngineInfo _draw_engine_list[4] = {
|
||||
|
||||
static void EnginePreviewWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
byte eng;
|
||||
int engine;
|
||||
const DrawEngineInfo *dei;
|
||||
int width;
|
||||
switch (e->event) {
|
||||
case WE_PAINT: {
|
||||
EngineID engine = w->window_number;
|
||||
const DrawEngineInfo* dei;
|
||||
int width;
|
||||
|
||||
switch(e->event) {
|
||||
case WE_PAINT:
|
||||
DrawWindowWidgets(w);
|
||||
engine = w->window_number;
|
||||
|
||||
SetDParam(0, GetEngineCategoryName(engine));
|
||||
DrawStringMultiCenter(150, 44, STR_8101_WE_HAVE_JUST_DESIGNED_A, 296);
|
||||
|
||||
DrawStringCentered(w->width >> 1, 80, GetCustomEngineName(engine), 0x10);
|
||||
|
||||
eng = (byte)engine;
|
||||
(dei = _draw_engine_list,eng < NUM_TRAIN_ENGINES) ||
|
||||
(dei++,eng < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES) ||
|
||||
(dei++,eng < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES + NUM_SHIP_ENGINES) ||
|
||||
(dei = _draw_engine_list,engine < NUM_TRAIN_ENGINES) ||
|
||||
(dei++,engine < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES) ||
|
||||
(dei++,engine < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES + NUM_SHIP_ENGINES) ||
|
||||
(dei++, true);
|
||||
|
||||
width = w->width;
|
||||
dei->engine_proc(width >> 1, 100, engine, 0);
|
||||
dei->info_proc(engine, width >> 1, 130, width - 52);
|
||||
break;
|
||||
}
|
||||
|
||||
case WE_CLICK:
|
||||
switch(e->click.widget) {
|
||||
case 3: DeleteWindow(w); break;
|
||||
case 4:
|
||||
DoCommandP(0, w->window_number, 0, NULL, CMD_WANT_ENGINE_PREVIEW);
|
||||
DeleteWindow(w);
|
||||
break;
|
||||
switch (e->click.widget) {
|
||||
case 3:
|
||||
DeleteWindow(w);
|
||||
break;
|
||||
|
||||
case 4:
|
||||
DoCommandP(0, w->window_number, 0, NULL, CMD_WANT_ENGINE_PREVIEW);
|
||||
DeleteWindow(w);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -105,7 +113,7 @@ static const WindowDesc _engine_preview_desc = {
|
||||
};
|
||||
|
||||
|
||||
void ShowEnginePreviewWindow(int engine)
|
||||
void ShowEnginePreviewWindow(EngineID engine)
|
||||
{
|
||||
Window *w;
|
||||
|
||||
@@ -113,9 +121,30 @@ void ShowEnginePreviewWindow(int engine)
|
||||
w->window_number = engine;
|
||||
}
|
||||
|
||||
static void DrawTrainEngineInfo(EngineID engine, int x, int y, int maxw)
|
||||
{
|
||||
const RailVehicleInfo *rvi = RailVehInfo(engine);
|
||||
uint multihead = (rvi->flags & RVI_MULTIHEAD) ? 1 : 0;
|
||||
|
||||
SetDParam(0, (_price.build_railvehicle >> 3) * rvi->base_cost >> 5);
|
||||
SetDParam(2, rvi->max_speed * 10 >> 4);
|
||||
SetDParam(3, rvi->power << multihead);
|
||||
SetDParam(1, rvi->weight << multihead);
|
||||
|
||||
SetDParam(4, rvi->running_cost_base * _price.running_rail[rvi->running_cost_class] >> 8 << multihead);
|
||||
|
||||
if (rvi->capacity != 0) {
|
||||
SetDParam(5, _cargoc.names_long[rvi->cargo_type]);
|
||||
SetDParam(6, rvi->capacity << multihead);
|
||||
} else {
|
||||
SetDParam(5, STR_8838_N_A);
|
||||
}
|
||||
DrawStringMultiCenter(x, y, STR_885B_COST_WEIGHT_T_SPEED_POWER, maxw);
|
||||
}
|
||||
|
||||
void DrawNewsNewTrainAvail(Window *w)
|
||||
{
|
||||
int engine;
|
||||
EngineID engine;
|
||||
|
||||
DrawNewsBorder(w);
|
||||
|
||||
@@ -129,22 +158,34 @@ void DrawNewsNewTrainAvail(Window *w)
|
||||
DrawStringMultiCenter(w->width >> 1, 57, STR_885A, w->width - 2);
|
||||
|
||||
DrawTrainEngine(w->width >> 1, 88, engine, 0);
|
||||
GfxFillRect(25, 56, w->width - 56, 112, 0x4323);
|
||||
GfxFillRect(25, 56, w->width - 56, 112, 0x323 | USE_COLORTABLE);
|
||||
DrawTrainEngineInfo(engine, w->width >> 1, 129, w->width - 52);
|
||||
}
|
||||
|
||||
StringID GetNewsStringNewTrainAvail(NewsItem *ni)
|
||||
StringID GetNewsStringNewTrainAvail(const NewsItem *ni)
|
||||
{
|
||||
int engine = ni->string_id;
|
||||
EngineID engine = ni->string_id;
|
||||
SetDParam(0, STR_8859_NEW_NOW_AVAILABLE);
|
||||
SetDParam(1, GetEngineCategoryName(engine));
|
||||
SetDParam(2, GetCustomEngineName(engine));
|
||||
return STR_02B6;
|
||||
}
|
||||
|
||||
static void DrawAircraftEngineInfo(EngineID engine, int x, int y, int maxw)
|
||||
{
|
||||
const AircraftVehicleInfo *avi = AircraftVehInfo(engine);
|
||||
SetDParam(0, (_price.aircraft_base >> 3) * avi->base_cost >> 5);
|
||||
SetDParam(1, avi->max_speed << 3);
|
||||
SetDParam(2, avi->passenger_capacity);
|
||||
SetDParam(3, avi->mail_capacity);
|
||||
SetDParam(4, avi->running_cost * _price.aircraft_running >> 8);
|
||||
|
||||
DrawStringMultiCenter(x, y, STR_A02E_COST_MAX_SPEED_CAPACITY, maxw);
|
||||
}
|
||||
|
||||
void DrawNewsNewAircraftAvail(Window *w)
|
||||
{
|
||||
int engine;
|
||||
EngineID engine;
|
||||
|
||||
DrawNewsBorder(w);
|
||||
|
||||
@@ -157,21 +198,35 @@ void DrawNewsNewAircraftAvail(Window *w)
|
||||
DrawStringMultiCenter(w->width >> 1, 57, STR_A02D, w->width - 2);
|
||||
|
||||
DrawAircraftEngine(w->width >> 1, 93, engine, 0);
|
||||
GfxFillRect(25, 56, w->width - 56, 110, 0x4323);
|
||||
GfxFillRect(25, 56, w->width - 56, 110, 0x323 | USE_COLORTABLE);
|
||||
DrawAircraftEngineInfo(engine, w->width >> 1, 131, w->width - 52);
|
||||
}
|
||||
|
||||
StringID GetNewsStringNewAircraftAvail(NewsItem *ni)
|
||||
StringID GetNewsStringNewAircraftAvail(const NewsItem *ni)
|
||||
{
|
||||
int engine = ni->string_id;
|
||||
EngineID engine = ni->string_id;
|
||||
SetDParam(0, STR_A02C_NEW_AIRCRAFT_NOW_AVAILABLE);
|
||||
SetDParam(1, GetCustomEngineName(engine));
|
||||
return STR_02B6;
|
||||
}
|
||||
|
||||
static void DrawRoadVehEngineInfo(EngineID engine, int x, int y, int maxw)
|
||||
{
|
||||
const RoadVehicleInfo *rvi = RoadVehInfo(engine);
|
||||
|
||||
SetDParam(0, (_price.roadveh_base >> 3) * rvi->base_cost >> 5);
|
||||
SetDParam(1, rvi->max_speed * 10 >> 5);
|
||||
SetDParam(2, rvi->running_cost * _price.roadveh_running >> 8);
|
||||
|
||||
SetDParam(4, rvi->capacity);
|
||||
SetDParam(3, _cargoc.names_long[rvi->cargo_type]);
|
||||
|
||||
DrawStringMultiCenter(x, y, STR_902A_COST_SPEED_RUNNING_COST, maxw);
|
||||
}
|
||||
|
||||
void DrawNewsNewRoadVehAvail(Window *w)
|
||||
{
|
||||
int engine;
|
||||
EngineID engine;
|
||||
|
||||
DrawNewsBorder(w);
|
||||
|
||||
@@ -183,21 +238,32 @@ void DrawNewsNewRoadVehAvail(Window *w)
|
||||
DrawStringMultiCenter(w->width >> 1, 57, STR_9029, w->width - 2);
|
||||
|
||||
DrawRoadVehEngine(w->width >> 1, 88, engine, 0);
|
||||
GfxFillRect(25, 56, w->width - 56, 112, 0x4323);
|
||||
GfxFillRect(25, 56, w->width - 56, 112, 0x323 | USE_COLORTABLE);
|
||||
DrawRoadVehEngineInfo(engine, w->width >> 1, 129, w->width - 52);
|
||||
}
|
||||
|
||||
StringID GetNewsStringNewRoadVehAvail(NewsItem *ni)
|
||||
StringID GetNewsStringNewRoadVehAvail(const NewsItem *ni)
|
||||
{
|
||||
int engine = ni->string_id;
|
||||
EngineID engine = ni->string_id;
|
||||
SetDParam(0, STR_9028_NEW_ROAD_VEHICLE_NOW_AVAILABLE);
|
||||
SetDParam(1, GetCustomEngineName(engine));
|
||||
return STR_02B6;
|
||||
}
|
||||
|
||||
static void DrawShipEngineInfo(EngineID engine, int x, int y, int maxw)
|
||||
{
|
||||
const ShipVehicleInfo *svi = ShipVehInfo(engine);
|
||||
SetDParam(0, svi->base_cost * (_price.ship_base >> 3) >> 5);
|
||||
SetDParam(1, svi->max_speed * 10 >> 5);
|
||||
SetDParam(2, _cargoc.names_long[svi->cargo_type]);
|
||||
SetDParam(3, svi->capacity);
|
||||
SetDParam(4, svi->running_cost * _price.ship_running >> 8);
|
||||
DrawStringMultiCenter(x, y, STR_982E_COST_MAX_SPEED_CAPACITY, maxw);
|
||||
}
|
||||
|
||||
void DrawNewsNewShipAvail(Window *w)
|
||||
{
|
||||
int engine;
|
||||
EngineID engine;
|
||||
|
||||
DrawNewsBorder(w);
|
||||
|
||||
@@ -210,13 +276,13 @@ void DrawNewsNewShipAvail(Window *w)
|
||||
DrawStringMultiCenter(w->width >> 1, 57, STR_982D, w->width - 2);
|
||||
|
||||
DrawShipEngine(w->width >> 1, 93, engine, 0);
|
||||
GfxFillRect(25, 56, w->width - 56, 110, 0x4323);
|
||||
GfxFillRect(25, 56, w->width - 56, 110, 0x323 | USE_COLORTABLE);
|
||||
DrawShipEngineInfo(engine, w->width >> 1, 131, w->width - 52);
|
||||
}
|
||||
|
||||
StringID GetNewsStringNewShipAvail(NewsItem *ni)
|
||||
StringID GetNewsStringNewShipAvail(const NewsItem *ni)
|
||||
{
|
||||
int engine = ni->string_id;
|
||||
EngineID engine = ni->string_id;
|
||||
SetDParam(0, STR_982C_NEW_SHIP_NOW_AVAILABLE);
|
||||
SetDParam(1, GetCustomEngineName(engine));
|
||||
return STR_02B6;
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "fileio.h"
|
||||
#include "functions.h"
|
||||
#include "macros.h"
|
||||
#include "variables.h"
|
||||
#if defined(UNIX) || defined(__OS2__)
|
||||
#include <ctype.h> // required for tolower()
|
||||
#endif
|
||||
@@ -136,6 +141,37 @@ bool FiosCheckFileExists(const char *filename)
|
||||
}
|
||||
}
|
||||
|
||||
FILE *FioFOpenFile(const char *filename)
|
||||
{
|
||||
FILE *f;
|
||||
char buf[MAX_PATH];
|
||||
|
||||
sprintf(buf, "%s%s", _path.data_dir, filename);
|
||||
|
||||
f = fopen(buf, "rb");
|
||||
#if !defined(WIN32)
|
||||
if (f == NULL) {
|
||||
char *s;
|
||||
// Make lower case and try again
|
||||
for(s=buf + strlen(_path.data_dir) - 1; *s != 0; s++)
|
||||
*s = tolower(*s);
|
||||
f = fopen(buf, "rb");
|
||||
|
||||
#if defined SECOND_DATA_DIR
|
||||
// tries in the 2nd data directory
|
||||
if (f == NULL) {
|
||||
sprintf(buf, "%s%s", _path.second_data_dir, filename);
|
||||
for(s=buf + strlen(_path.second_data_dir) - 1; *s != 0; s++)
|
||||
*s = tolower(*s);
|
||||
f = fopen(buf, "rb");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
return f;
|
||||
}
|
||||
|
||||
void FioOpenFile(int slot, const char *filename)
|
||||
{
|
||||
FILE *f;
|
||||
@@ -160,6 +196,10 @@ void FioOpenFile(int slot, const char *filename)
|
||||
*s = tolower(*s);
|
||||
f = fopen(buf, "rb");
|
||||
}
|
||||
|
||||
if (f == NULL)
|
||||
sprintf(buf, "%s%s", _path.data_dir, filename); //makes it print the primary datadir path instead of the secundary one
|
||||
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
@@ -171,5 +211,3 @@ void FioOpenFile(int slot, const char *filename)
|
||||
_fio.handles[slot] = f;
|
||||
FioSeekToFile(slot << 24);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef FILEIO_H
|
||||
#define FILEIO_H
|
||||
|
||||
@@ -8,6 +10,7 @@ byte FioReadByte(void);
|
||||
uint16 FioReadWord(void);
|
||||
uint32 FioReadDword(void);
|
||||
void FioCloseAll(void);
|
||||
FILE *FioFOpenFile(const char *filename);
|
||||
void FioOpenFile(int slot, const char *filename);
|
||||
void FioReadBlock(void *ptr, uint size);
|
||||
void FioSkipBytes(int n);
|
||||
|
||||
+52
-54
@@ -1,11 +1,8 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef FUNCTIONS_H
|
||||
#define FUNCTIONS_H
|
||||
|
||||
/* vehicle.c */
|
||||
|
||||
/* window.c */
|
||||
|
||||
|
||||
/* landscape.c */
|
||||
void FindLandscapeHeight(TileInfo *ti, uint x, uint y);
|
||||
void FindLandscapeHeightByTile(TileInfo *ti, TileIndex tile);
|
||||
@@ -48,38 +45,32 @@ static inline Point RemapCoords2(int x, int y)
|
||||
|
||||
|
||||
/* clear_land.c */
|
||||
void DrawHillyLandTile(TileInfo *ti);
|
||||
void DrawClearLandTile(TileInfo *ti, byte set);
|
||||
void DrawClearLandFence(TileInfo *ti, byte img);
|
||||
void DrawHillyLandTile(const TileInfo *ti);
|
||||
void DrawClearLandTile(const TileInfo *ti, byte set);
|
||||
void DrawClearLandFence(const TileInfo *ti);
|
||||
void TileLoopClearHelper(TileIndex tile);
|
||||
|
||||
/* station_land.c */
|
||||
void StationPickerDrawSprite(int x, int y, int railtype, int image);
|
||||
|
||||
/* track_land.c */
|
||||
void DrawTrainDepotSprite(int x, int y, int image, int railtype);
|
||||
|
||||
/* road_land.c */
|
||||
void DrawRoadDepotSprite(int x, int y, int image);
|
||||
|
||||
/* water_land.c */
|
||||
void DrawShipDepotSprite(int x, int y, int image);
|
||||
void TileLoop_Water(uint tile);
|
||||
void TileLoop_Water(TileIndex tile);
|
||||
|
||||
/* players.c */
|
||||
bool CheckPlayerHasMoney(int32 cost);
|
||||
void SubtractMoneyFromPlayer(int32 cost);
|
||||
void SubtractMoneyFromPlayerFract(byte player, int32 cost);
|
||||
bool CheckOwnership(byte owner);
|
||||
bool CheckTileOwnership(uint tile);
|
||||
StringID GetPlayerNameString(byte player, byte index);
|
||||
void SubtractMoneyFromPlayerFract(PlayerID player, int32 cost);
|
||||
bool CheckOwnership(PlayerID owner);
|
||||
bool CheckTileOwnership(TileIndex tile);
|
||||
StringID GetPlayerNameString(PlayerID player, uint index);
|
||||
|
||||
/* standard */
|
||||
void ShowInfo(const char *str);
|
||||
void CDECL ShowInfoF(const char *str, ...);
|
||||
void NORETURN CDECL error(const char *str, ...);
|
||||
|
||||
/* ttd.c */
|
||||
/* openttd.c */
|
||||
|
||||
// **************
|
||||
// * Warning: DO NOT enable this unless you understand what it does
|
||||
@@ -93,6 +84,21 @@ void NORETURN CDECL error(const char *str, ...);
|
||||
|
||||
//#define RANDOM_DEBUG
|
||||
|
||||
|
||||
// Enable this to produce higher quality random numbers.
|
||||
// Doesn't work with network yet.
|
||||
//#define MERSENNE_TWISTER
|
||||
|
||||
// Mersenne twister functions
|
||||
void SeedMT(uint32 seed);
|
||||
uint32 RandomMT(void);
|
||||
|
||||
|
||||
#ifdef MERSENNE_TWISTER
|
||||
static inline uint32 Random(void) { return RandomMT(); }
|
||||
uint RandomRange(uint max);
|
||||
#else
|
||||
|
||||
#ifdef RANDOM_DEBUG
|
||||
#define Random() DoRandom(__LINE__, __FILE__)
|
||||
uint32 DoRandom(int line, const char *file);
|
||||
@@ -102,12 +108,21 @@ void NORETURN CDECL error(const char *str, ...);
|
||||
uint32 Random(void);
|
||||
uint RandomRange(uint max);
|
||||
#endif
|
||||
#endif // MERSENNE_TWISTER
|
||||
|
||||
static inline TileIndex RandomTileSeed(uint32 r) { return TILE_MASK(r); }
|
||||
static inline TileIndex RandomTile(void) { return TILE_MASK(Random()); }
|
||||
|
||||
void InitPlayerRandoms(void);
|
||||
|
||||
uint32 InteractiveRandom(void); /* Used for random sequences that are not the same on the other end of the multiplayer link */
|
||||
uint InteractiveRandomRange(uint max);
|
||||
|
||||
|
||||
// Used for profiling
|
||||
#define TIC() { extern uint32 _rdtsc(void); uint32 _xxx_ = _rdtsc(); static float __avg__;
|
||||
#define TOC(s) _xxx_ = _rdtsc() - _xxx_; __avg__=__avg__*0.99+_xxx_*0.01; printf("%s: %8d %f\n", s, _xxx_,__avg__); }
|
||||
|
||||
|
||||
void SetDate(uint date);
|
||||
/* facedraw.c */
|
||||
void DrawPlayerFace(uint32 face, int color, int x, int y);
|
||||
@@ -124,18 +139,18 @@ void CDECL AddTextMessage(uint16 color, uint8 duration, const char *message, ...
|
||||
void UndrawTextMessage(void);
|
||||
void TextMessageDailyLoop(void);
|
||||
|
||||
bool AddAnimatedTile(uint tile);
|
||||
void DeleteAnimatedTile(uint tile);
|
||||
bool AddAnimatedTile(TileIndex tile);
|
||||
void DeleteAnimatedTile(TileIndex tile);
|
||||
void AnimateAnimatedTiles(void);
|
||||
void InitializeAnimatedTiles(void);
|
||||
|
||||
/* tunnelbridge_cmd.c */
|
||||
bool CheckTunnelInWay(uint tile, int z);
|
||||
bool CheckBridge_Stuff(byte bridge_type, int bridge_len);
|
||||
bool CheckTunnelInWay(TileIndex tile, int z);
|
||||
bool CheckBridge_Stuff(byte bridge_type, uint bridge_len);
|
||||
uint32 GetBridgeLength(TileIndex begin, TileIndex end);
|
||||
int CalcBridgeLenCostFactor(int x);
|
||||
|
||||
typedef void CommandCallback(bool success, uint tile, uint32 p1, uint32 p2);
|
||||
typedef void CommandCallback(bool success, TileIndex tile, uint32 p1, uint32 p2);
|
||||
bool DoCommandP(TileIndex tile, uint32 p1, uint32 p2, CommandCallback *callback, uint32 cmd);
|
||||
|
||||
/* network.c */
|
||||
@@ -148,7 +163,7 @@ bool NetworkServerStart(void);
|
||||
bool NetworkClientConnectGame(const char* host, unsigned short port);
|
||||
void NetworkReboot(void);
|
||||
void NetworkDisconnect(void);
|
||||
void NetworkSend_Command(uint32 tile, uint32 p1, uint32 p2, uint32 cmd, CommandCallback *callback);
|
||||
void NetworkSend_Command(TileIndex tile, uint32 p1, uint32 p2, uint32 cmd, CommandCallback *callback);
|
||||
|
||||
/* misc_cmd.c */
|
||||
void PlaceTreesRandomly(void);
|
||||
@@ -171,18 +186,17 @@ uint ConvertIntDate(uint date);
|
||||
/* misc functions */
|
||||
void MarkTileDirty(int x, int y);
|
||||
void MarkTileDirtyByTile(TileIndex tile);
|
||||
void InvalidateWindow(byte cls, WindowNumber number);
|
||||
void InvalidateWindowWidget(byte cls, WindowNumber number, byte widget_index);
|
||||
void InvalidateWindowClasses(byte cls);
|
||||
void InvalidateWindow(WindowClass cls, WindowNumber number);
|
||||
void InvalidateWindowWidget(WindowClass cls, WindowNumber number, byte widget_index);
|
||||
void InvalidateWindowClasses(WindowClass cls);
|
||||
void DeleteWindowById(WindowClass cls, WindowNumber number);
|
||||
void DeleteWindowByClass(WindowClass cls);
|
||||
|
||||
void SetObjectToPlaceWnd(int icon, byte mode, Window *w);
|
||||
void SetObjectToPlace(int icon, byte mode, WindowClass window_class, WindowNumber window_num);
|
||||
void SetObjectToPlaceWnd(CursorID icon, byte mode, Window *w);
|
||||
void SetObjectToPlace(CursorID icon, byte mode, WindowClass window_class, WindowNumber window_num);
|
||||
|
||||
void ResetObjectToPlace(void);
|
||||
|
||||
bool ScrollWindowToTile(TileIndex tile, Window * w);
|
||||
bool ScrollWindowTo(int x, int y, Window * w);
|
||||
|
||||
bool ScrollMainWindowToTile(TileIndex tile);
|
||||
@@ -193,15 +207,16 @@ bool EnsureNoVehicle(TileIndex tile);
|
||||
bool EnsureNoVehicleZ(TileIndex tile, byte z);
|
||||
void MarkAllViewportsDirty(int left, int top, int right, int bottom);
|
||||
void ShowCostOrIncomeAnimation(int x, int y, int z, int32 cost);
|
||||
void ShowFeederIncomeAnimation(int x, int y, int z, int32 cost);
|
||||
|
||||
void DrawFoundation(TileInfo *ti, uint f);
|
||||
|
||||
bool CheckIfAuthorityAllows(uint tile);
|
||||
Town *ClosestTownFromTile(uint tile, uint threshold);
|
||||
bool CheckIfAuthorityAllows(TileIndex tile);
|
||||
Town *ClosestTownFromTile(TileIndex tile, uint threshold);
|
||||
void ChangeTownRating(Town *t, int add, int max);
|
||||
|
||||
uint GetRoadBitsByTile(TileIndex tile);
|
||||
int GetTownRadiusGroup(Town *t, uint tile);
|
||||
int GetTownRadiusGroup(const Town *t, TileIndex tile);
|
||||
void ShowNetworkChatQueryWindow(byte desttype, byte dest);
|
||||
void ShowNetworkGiveMoneyWindow(byte player);
|
||||
void ShowNetworkNeedGamePassword(void);
|
||||
@@ -211,20 +226,6 @@ void ShowHighscoreTable(int difficulty, int8 rank);
|
||||
void ShowEndGameChart(void);
|
||||
TileIndex AdjustTileCoordRandomly(TileIndex a, byte rng);
|
||||
|
||||
enum SaveOrLoadResult {
|
||||
SL_OK = 0, // completed successfully
|
||||
SL_ERROR = 1, // error that was caught before internal structures were modified
|
||||
SL_REINIT = 2, // error that was caught in the middle of updating game state, need to clear it. (can only happen during load)
|
||||
};
|
||||
enum SaveOrLoadMode {
|
||||
SL_INVALID = -1,
|
||||
SL_LOAD = 0,
|
||||
SL_SAVE = 1,
|
||||
SL_OLD_LOAD = 2,
|
||||
};
|
||||
|
||||
int SaveOrLoad(const char *filename, int mode);
|
||||
|
||||
void AfterLoadTown(void);
|
||||
void GenRandomNewGame(uint32 rnd1, uint32 rnd2);
|
||||
void StartScenarioEditor(uint32 rnd1, uint32 rnd2);
|
||||
@@ -254,16 +255,13 @@ void InitializeLanguagePacks(void);
|
||||
void *ReadFileToMem(const char *filename, size_t *lenp, size_t maxsize);
|
||||
int GetLanguageList(char **languages, int max);
|
||||
|
||||
void CheckSwitchToEuro(void);
|
||||
|
||||
void LoadFromConfig(void);
|
||||
void SaveToConfig(void);
|
||||
void CheckConfig(void);
|
||||
int ttd_main(int argc, char* argv[]);
|
||||
byte GetOSVersion(void);
|
||||
|
||||
void DeterminePaths(void);
|
||||
char * CDECL str_fmt(const char *str, ...);
|
||||
|
||||
void bubblesort(void *base, size_t nmemb, size_t size, int(*compar)(const void *, const void *));
|
||||
void CSleep(int milliseconds);
|
||||
#endif /* FUNCTIONS_H */
|
||||
|
||||
@@ -1,6 +1,9 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef GFX_H
|
||||
#define GFX_H
|
||||
|
||||
typedef byte Pixel;
|
||||
|
||||
typedef struct ColorList {
|
||||
byte unk0, unk1, unk2;
|
||||
@@ -10,7 +13,7 @@ typedef struct ColorList {
|
||||
} ColorList;
|
||||
|
||||
struct DrawPixelInfo {
|
||||
byte *dst_ptr;
|
||||
Pixel *dst_ptr;
|
||||
int left, top, width, height;
|
||||
int pitch;
|
||||
uint16 zoom;
|
||||
@@ -20,10 +23,10 @@ struct DrawPixelInfo {
|
||||
typedef struct CursorVars {
|
||||
Point pos, size, offs, delta;
|
||||
Point draw_pos, draw_size;
|
||||
uint32 sprite;
|
||||
CursorID sprite;
|
||||
|
||||
int wheel; // mouse wheel movement
|
||||
const uint16 *animate_list, *animate_cur;
|
||||
const CursorID *animate_list, *animate_cur;
|
||||
uint animate_timeout;
|
||||
|
||||
bool visible;
|
||||
@@ -34,33 +37,52 @@ typedef struct CursorVars {
|
||||
|
||||
void RedrawScreenRect(int left, int top, int right, int bottom);
|
||||
void GfxScroll(int left, int top, int width, int height, int xo, int yo);
|
||||
int DrawStringCentered(int x, int y, uint16 str, uint16 color);
|
||||
int DrawString(int x, int y, uint16 str, uint16 color);
|
||||
void DrawStringCenterUnderline(int x, int y, uint16 str, uint16 color);
|
||||
|
||||
|
||||
// XXX doesn't really belong here, but the only
|
||||
// consumers always use it in conjunction with DoDrawString()
|
||||
#define UPARROW "\x80"
|
||||
#define DOWNARROW "\xAA"
|
||||
|
||||
|
||||
int DrawStringCentered(int x, int y, StringID str, uint16 color);
|
||||
int DrawStringCenteredTruncated(int xl, int xr, int y, StringID str, uint16 color);
|
||||
int DoDrawStringCentered(int x, int y, const char *str, uint16 color);
|
||||
|
||||
int DrawString(int x, int y, StringID str, uint16 color);
|
||||
int DrawStringTruncated(int x, int y, StringID str, uint16 color, uint maxw);
|
||||
|
||||
int DoDrawString(const char *string, int x, int y, uint16 color);
|
||||
void DrawStringRightAligned(int x, int y, uint16 str, uint16 color);
|
||||
int DoDrawStringTruncated(const char *str, int x, int y, uint16 color, uint maxw);
|
||||
|
||||
void DrawStringCenterUnderline(int x, int y, StringID str, uint16 color);
|
||||
void DrawStringCenterUnderlineTruncated(int xl, int xr, int y, StringID str, uint16 color);
|
||||
|
||||
void DrawStringRightAligned(int x, int y, StringID str, uint16 color);
|
||||
void DrawStringRightAlignedTruncated(int x, int y, StringID str, uint16 color, uint maxw);
|
||||
|
||||
void GfxFillRect(int left, int top, int right, int bottom, int color);
|
||||
void GfxDrawLine(int left, int top, int right, int bottom, int color);
|
||||
void DrawFrameRect(int left, int top, int right, int bottom, int color, int flags);
|
||||
uint16 GetDrawStringPlayerColor(byte player);
|
||||
uint16 GetDrawStringPlayerColor(PlayerID player);
|
||||
|
||||
int GetStringWidth(const char *str);
|
||||
void LoadStringWidthTable(void);
|
||||
void DrawStringMultiCenter(int x, int y, uint16 str, int maxw);
|
||||
void DrawStringMultiLine(int x, int y, uint16 str, int maxw);
|
||||
void DrawStringMultiCenter(int x, int y, StringID str, int maxw);
|
||||
void DrawStringMultiLine(int x, int y, StringID str, int maxw);
|
||||
void DrawDirtyBlocks(void);
|
||||
void SetDirtyBlocks(int left, int top, int right, int bottom);
|
||||
void MarkWholeScreenDirty(void);
|
||||
|
||||
void GfxInitPalettes(void);
|
||||
|
||||
bool FillDrawPixelInfo(DrawPixelInfo *n, DrawPixelInfo *o, int left, int top, int width, int height);
|
||||
bool FillDrawPixelInfo(DrawPixelInfo* n, const DrawPixelInfo* o, int left, int top, int width, int height);
|
||||
|
||||
/* window.c */
|
||||
void DrawOverlappedWindowForAll(int left, int top, int right, int bottom);
|
||||
|
||||
void SetMouseCursor(uint cursor);
|
||||
void SetAnimatedMouseCursor(const uint16 *table);
|
||||
void SetAnimatedMouseCursor(const CursorID *table);
|
||||
void CursorTick(void);
|
||||
void DrawMouseCursor(void);
|
||||
void ScreenSizeChanged(void);
|
||||
@@ -89,18 +111,21 @@ VARDEF int _pal_last_dirty;
|
||||
|
||||
VARDEF bool _use_dos_palette;
|
||||
|
||||
/* spritecache.c */
|
||||
//enum { NUM_SPRITES = 0x1320 };
|
||||
//enum { NUM_SPRITES = 0x1500 };
|
||||
enum { NUM_SPRITES = 0x3500 }; // 1500 + space for custom GRF sets
|
||||
typedef struct Colour {
|
||||
byte r;
|
||||
byte g;
|
||||
byte b;
|
||||
} Colour;
|
||||
|
||||
/* tables.h */
|
||||
extern byte _palettes[4][256 * 3];
|
||||
VARDEF byte _cur_palette[768];
|
||||
extern Colour _cur_palette[256];
|
||||
|
||||
|
||||
typedef enum StringColorFlags {
|
||||
IS_PALETTE_COLOR = 0x100, // color value is already a real palette color index, not an index of a StringColor
|
||||
} StringColorFlags;
|
||||
|
||||
#ifdef _DEBUG
|
||||
extern bool _dbg_screen_rect;
|
||||
#endif
|
||||
|
||||
#endif /* GFX_H */
|
||||
|
||||
@@ -0,0 +1,376 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "openttd.h"
|
||||
#include "debug.h"
|
||||
#include "functions.h"
|
||||
#include "gfx.h"
|
||||
#include "gfxinit.h"
|
||||
#include "spritecache.h"
|
||||
#include "table/sprites.h"
|
||||
#include "fileio.h"
|
||||
#include "newgrf.h"
|
||||
#include "md5.h"
|
||||
#include "variables.h"
|
||||
#include <ctype.h>
|
||||
|
||||
typedef struct MD5File {
|
||||
const char * const filename; // filename
|
||||
const md5_byte_t hash[16]; // md5 sum of the file
|
||||
} MD5File;
|
||||
|
||||
typedef struct FileList {
|
||||
const MD5File basic[5]; // grf files that always have to be loaded
|
||||
const MD5File landscape[3]; // landscape specific grf files
|
||||
} FileList;
|
||||
|
||||
enum {
|
||||
SKIP = 0xFFFE,
|
||||
END = 0xFFFF
|
||||
};
|
||||
|
||||
#include "table/files.h"
|
||||
#include "table/landscape_sprite.h"
|
||||
|
||||
static const SpriteID * const _landscape_spriteindexes[] = {
|
||||
_landscape_spriteindexes_1,
|
||||
_landscape_spriteindexes_2,
|
||||
_landscape_spriteindexes_3,
|
||||
};
|
||||
|
||||
static const SpriteID * const _slopes_spriteindexes[] = {
|
||||
_slopes_spriteindexes_0,
|
||||
_slopes_spriteindexes_1,
|
||||
_slopes_spriteindexes_2,
|
||||
_slopes_spriteindexes_3,
|
||||
};
|
||||
|
||||
|
||||
static uint LoadGrfFile(const char* filename, uint load_index, int file_index)
|
||||
{
|
||||
uint load_index_org = load_index;
|
||||
|
||||
FioOpenFile(file_index, filename);
|
||||
|
||||
DEBUG(spritecache, 2) ("Reading grf-file ``%s''", filename);
|
||||
|
||||
while (LoadNextSprite(load_index, file_index)) {
|
||||
load_index++;
|
||||
if (load_index >= MAX_SPRITES) {
|
||||
error("Too many sprites. Recompile with higher MAX_SPRITES value or remove some custom GRF files.");
|
||||
}
|
||||
}
|
||||
DEBUG(spritecache, 2) ("Currently %i sprites are loaded", load_index);
|
||||
|
||||
return load_index - load_index_org;
|
||||
}
|
||||
|
||||
|
||||
static void LoadGrfIndexed(const char* filename, const SpriteID* index_tbl, int file_index)
|
||||
{
|
||||
uint start;
|
||||
|
||||
FioOpenFile(file_index, filename);
|
||||
|
||||
DEBUG(spritecache, 2) ("Reading indexed grf-file ``%s''", filename);
|
||||
|
||||
while ((start = *index_tbl++) != END) {
|
||||
uint end = *index_tbl++;
|
||||
|
||||
if (start == SKIP) { // skip sprites (amount in second var)
|
||||
SkipSprites(end);
|
||||
} else { // load sprites and use indexes from start to end
|
||||
do {
|
||||
#ifdef NDEBUG
|
||||
LoadNextSprite(start, file_index);
|
||||
#else
|
||||
bool b = LoadNextSprite(start, file_index);
|
||||
assert(b);
|
||||
#endif
|
||||
} while (++start <= end);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Check that the supplied MD5 hash matches that stored for the supplied filename */
|
||||
static bool CheckMD5Digest(const MD5File file, md5_byte_t *digest, bool warn)
|
||||
{
|
||||
uint i;
|
||||
|
||||
/* Loop through each byte of the file MD5 and the stored MD5... */
|
||||
for (i = 0; i < 16; i++) if (file.hash[i] != digest[i]) break;
|
||||
|
||||
/* If all bytes of the MD5's match (i.e. the MD5's match)... */
|
||||
if (i == 16) {
|
||||
return true;
|
||||
} else {
|
||||
if (warn) fprintf(stderr, "MD5 of %s is ****INCORRECT**** - File Corrupt.\n", file.filename);
|
||||
return false;
|
||||
};
|
||||
}
|
||||
|
||||
/* Calculate and check the MD5 hash of the supplied filename.
|
||||
* returns true if the checksum is correct */
|
||||
static bool FileMD5(const MD5File file, bool warn)
|
||||
{
|
||||
FILE *f;
|
||||
char buf[MAX_PATH];
|
||||
|
||||
// open file
|
||||
sprintf(buf, "%s%s", _path.data_dir, file.filename);
|
||||
f = fopen(buf, "rb");
|
||||
|
||||
#if !defined(WIN32)
|
||||
if (f == NULL) {
|
||||
char *s;
|
||||
// make lower case and check again
|
||||
for (s = buf + strlen(_path.data_dir) - 1; *s != '\0'; s++)
|
||||
*s = tolower(*s);
|
||||
f = fopen(buf, "rb");
|
||||
}
|
||||
#endif
|
||||
|
||||
if (f != NULL) {
|
||||
md5_state_t filemd5state;
|
||||
md5_byte_t buffer[1024];
|
||||
md5_byte_t digest[16];
|
||||
size_t len;
|
||||
|
||||
md5_init(&filemd5state);
|
||||
while ((len = fread(buffer, 1, sizeof(buffer), f)) != 0)
|
||||
md5_append(&filemd5state, buffer, len);
|
||||
|
||||
if (ferror(f) && warn) fprintf(stderr, "Error Reading from %s \n", buf);
|
||||
fclose(f);
|
||||
|
||||
md5_finish(&filemd5state, digest);
|
||||
return CheckMD5Digest(file, digest, warn);
|
||||
} else { // file not found
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/* Checks, if either the Windows files exist (TRG1R.GRF) or the DOS files (TRG1.GRF)
|
||||
* by comparing the MD5 checksums of the files. _use_dos_palette is set accordingly.
|
||||
* If neither are found, Windows palette is assumed.
|
||||
*
|
||||
* (Note: Also checks sample.cat for corruption) */
|
||||
void CheckExternalFiles(void)
|
||||
{
|
||||
uint i;
|
||||
// count of files from this version
|
||||
uint dos = 0;
|
||||
uint win = 0;
|
||||
|
||||
for (i = 0; i < 2; i++) if (FileMD5(files_dos.basic[i], true)) dos++;
|
||||
for (i = 0; i < 3; i++) if (FileMD5(files_dos.landscape[i], true)) dos++;
|
||||
|
||||
for (i = 0; i < 2; i++) if (FileMD5(files_win.basic[i], true)) win++;
|
||||
for (i = 0; i < 3; i++) if (FileMD5(files_win.landscape[i], true)) win++;
|
||||
|
||||
if (!FileMD5(sample_cat_win, false) && !FileMD5(sample_cat_dos, false))
|
||||
fprintf(stderr, "Your sample.cat file is corrupted or missing!\n");
|
||||
|
||||
/*
|
||||
* forced DOS palette via command line -> leave it that way
|
||||
* all Windows files present -> Windows palette
|
||||
* all DOS files present -> DOS palette
|
||||
* no Windows files present and any DOS file present -> DOS palette
|
||||
* otherwise -> Windows palette
|
||||
*/
|
||||
if (_use_dos_palette) {
|
||||
return;
|
||||
} else if (win == 5) {
|
||||
_use_dos_palette = false;
|
||||
} else if (dos == 5 || (win == 0 && dos > 0)) {
|
||||
_use_dos_palette = true;
|
||||
} else {
|
||||
_use_dos_palette = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static const SpriteID trg1idx[] = {
|
||||
0, 1, // Mouse cursor, ZZZ
|
||||
/* Medium font */
|
||||
2, 92, // ' ' till 'z'
|
||||
SKIP, 36,
|
||||
160, 160, // Move ¾ to the correct position
|
||||
98, 98, // Up arrow
|
||||
131, 133,
|
||||
SKIP, 1, // skip currency sign
|
||||
135, 135,
|
||||
SKIP, 1,
|
||||
137, 137,
|
||||
SKIP, 1,
|
||||
139, 139,
|
||||
140, 140, // TODO Down arrow
|
||||
141, 141,
|
||||
142, 142, // TODO Check mark
|
||||
143, 143, // TODO Cross
|
||||
144, 144,
|
||||
145, 145, // TODO Right arrow
|
||||
146, 149,
|
||||
118, 122, // Transport markers
|
||||
SKIP, 2,
|
||||
157, 157,
|
||||
114, 115, // Small up/down arrows
|
||||
SKIP, 1,
|
||||
161, 225,
|
||||
/* Small font */
|
||||
226, 316, // ' ' till 'z'
|
||||
SKIP, 36,
|
||||
384, 384, // Move ¾ to the correct position
|
||||
322, 322, // Up arrow
|
||||
355, 357,
|
||||
SKIP, 1, // skip currency sign
|
||||
359, 359,
|
||||
SKIP, 1,
|
||||
361, 361,
|
||||
SKIP, 1,
|
||||
363, 363,
|
||||
364, 364, // TODO Down arrow
|
||||
365, 366,
|
||||
SKIP, 1,
|
||||
368, 368,
|
||||
369, 369, // TODO Right arrow
|
||||
370, 373,
|
||||
SKIP, 7,
|
||||
381, 381,
|
||||
SKIP, 3,
|
||||
385, 449,
|
||||
/* Big font */
|
||||
450, 540, // ' ' till 'z'
|
||||
SKIP, 36,
|
||||
608, 608, // Move ¾ to the correct position
|
||||
SKIP, 1,
|
||||
579, 581,
|
||||
SKIP, 1,
|
||||
583, 583,
|
||||
SKIP, 5,
|
||||
589, 589,
|
||||
SKIP, 15,
|
||||
605, 605,
|
||||
SKIP, 3,
|
||||
609, 625,
|
||||
SKIP, 1,
|
||||
627, 632,
|
||||
SKIP, 1,
|
||||
634, 639,
|
||||
SKIP, 1,
|
||||
641, 657,
|
||||
SKIP, 1,
|
||||
659, 664,
|
||||
SKIP, 2,
|
||||
667, 671,
|
||||
SKIP, 1,
|
||||
673, 673,
|
||||
/* Graphics */
|
||||
674, 4792,
|
||||
END
|
||||
};
|
||||
|
||||
/* NOTE: When adding a normal sprite, increase OPENTTD_SPRITES_COUNT with the
|
||||
* amount of sprites and add them to the end of the list, with the index of
|
||||
* the old sprite-count offset from SPR_OPENTTD_BASE. With this there is no
|
||||
* correspondence of any kind with the ID's in the grf file, but results in
|
||||
* a maximum use of sprite slots. */
|
||||
#define OPENTTD_SPRITES_COUNT 95
|
||||
static const SpriteID _openttd_grf_indexes[] = {
|
||||
SPR_IMG_AUTORAIL, SPR_CURSOR_WAYPOINT, // icons etc
|
||||
134, 134, // euro symbol medium size
|
||||
582, 582, // euro symbol large size
|
||||
358, 358, // euro symbol tiny
|
||||
SPR_CURSOR_CANAL, SPR_IMG_FASTFORWARD, // more icons
|
||||
648, 648, // nordic char: æ
|
||||
616, 616, // nordic char: Æ
|
||||
666, 666, // nordic char: ø
|
||||
634, 634, // nordic char: Ø
|
||||
SPR_PIN_UP, SPR_CURSOR_CLONE, // more icons
|
||||
382, 383, // ¼ ½ tiny
|
||||
158, 159, // ¼ ½ medium
|
||||
606, 607, // ¼ ½ large
|
||||
360, 360, // ¦ tiny
|
||||
362, 362, // ¨ tiny
|
||||
136, 136, // ¦ medium
|
||||
138, 138, // ¨ medium
|
||||
584, 584, // ¦ large
|
||||
586, 586, // ¨ large
|
||||
626, 626, // Ð large
|
||||
658, 658, // ð large
|
||||
374, 374, // ´ tiny
|
||||
378, 378, // ¸ tiny
|
||||
150, 150, // ´ medium
|
||||
154, 154, // ¸ medium
|
||||
598, 598, // ´ large
|
||||
602, 602, // ¸ large
|
||||
640, 640, // Þ large
|
||||
672, 672, // þ large
|
||||
380, 380, // º tiny
|
||||
156, 156, // º medium
|
||||
604, 604, // º large
|
||||
317, 320, // { | } ~ tiny
|
||||
93, 96, // { | } ~ medium
|
||||
541, 544, // { | } ~ large
|
||||
SPR_HOUSE_ICON, SPR_HOUSE_ICON,
|
||||
END
|
||||
};
|
||||
|
||||
static byte _sprite_page_to_load = 0xFF;
|
||||
|
||||
static void LoadSpriteTables(void)
|
||||
{
|
||||
const FileList* files = _use_dos_palette ? &files_dos : &files_win;
|
||||
uint load_index;
|
||||
uint i;
|
||||
|
||||
LoadGrfIndexed(files->basic[0].filename, trg1idx, 0);
|
||||
DupSprite( 2, 130); // non-breaking space medium
|
||||
DupSprite(226, 354); // non-breaking space tiny
|
||||
DupSprite(450, 578); // non-breaking space large
|
||||
load_index = 4793;
|
||||
|
||||
for (i = 1; files->basic[i].filename != NULL; i++) {
|
||||
load_index += LoadGrfFile(files->basic[i].filename, load_index, i);
|
||||
}
|
||||
|
||||
if (_sprite_page_to_load != 0) {
|
||||
LoadGrfIndexed(
|
||||
files->landscape[_sprite_page_to_load - 1].filename,
|
||||
_landscape_spriteindexes[_sprite_page_to_load - 1],
|
||||
i++
|
||||
);
|
||||
}
|
||||
|
||||
assert(load_index == SPR_CANALS_BASE);
|
||||
load_index += LoadGrfFile("canalsw.grf", load_index, i++);
|
||||
|
||||
assert(load_index == SPR_SLOPES_BASE);
|
||||
LoadGrfIndexed("trkfoundw.grf", _slopes_spriteindexes[_opt.landscape], i++);
|
||||
|
||||
load_index = SPR_AUTORAIL_BASE;
|
||||
load_index += LoadGrfFile("autorail.grf", load_index, i++);
|
||||
|
||||
assert(load_index == SPR_OPENTTD_BASE);
|
||||
LoadGrfIndexed("openttd.grf", _openttd_grf_indexes, i++);
|
||||
load_index = SPR_OPENTTD_BASE + OPENTTD_SPRITES_COUNT;
|
||||
|
||||
LoadNewGRF(load_index, i);
|
||||
}
|
||||
|
||||
|
||||
void GfxLoadSprites(void)
|
||||
{
|
||||
// Need to reload the sprites only if the landscape changed
|
||||
if (_sprite_page_to_load != _opt.landscape) {
|
||||
_sprite_page_to_load = _opt.landscape;
|
||||
|
||||
// Sprite cache
|
||||
DEBUG(spritecache, 1) ("Loading sprite set %d.", _sprite_page_to_load);
|
||||
|
||||
GfxInitSpriteMem();
|
||||
LoadSpriteTables();
|
||||
GfxInitPalettes();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef GFXINIT_H
|
||||
#define GFXINIT_H
|
||||
|
||||
void CheckExternalFiles(void);
|
||||
void GfxLoadSprites(void);
|
||||
|
||||
#endif /* GFXINIT_H */
|
||||
+74
-82
@@ -1,6 +1,10 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "table/sprites.h"
|
||||
#include "functions.h"
|
||||
#include "window.h"
|
||||
#include "gui.h"
|
||||
#include "gfx.h"
|
||||
@@ -9,6 +13,7 @@
|
||||
#include "signs.h"
|
||||
#include "strings.h"
|
||||
#include "debug.h"
|
||||
#include "variables.h"
|
||||
|
||||
static uint _legend_excludebits;
|
||||
static uint _legend_cargobits;
|
||||
@@ -39,7 +44,7 @@ typedef struct GraphDrawer {
|
||||
|
||||
#define INVALID_VALUE 0x80000000
|
||||
|
||||
static void DrawGraph(GraphDrawer *gw)
|
||||
static void DrawGraph(const GraphDrawer *gw)
|
||||
{
|
||||
|
||||
int i,j,k;
|
||||
@@ -47,7 +52,7 @@ static void DrawGraph(GraphDrawer *gw)
|
||||
int color;
|
||||
int right, bottom;
|
||||
int num_x, num_dataset;
|
||||
uint64 *row_ptr, *col_ptr;
|
||||
const uint64 *row_ptr, *col_ptr;
|
||||
int64 mx;
|
||||
int adj_height;
|
||||
uint64 y_scaling, tmp;
|
||||
@@ -214,20 +219,18 @@ void DrawPlayerIcon(int p, int x, int y)
|
||||
|
||||
static void GraphLegendWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
Player *p;
|
||||
const Player* p;
|
||||
|
||||
switch(e->event) {
|
||||
case WE_PAINT:
|
||||
FOR_ALL_PLAYERS(p) {
|
||||
if (!p->is_active)
|
||||
SETBIT(_legend_excludebits, p->index);
|
||||
if (!p->is_active) SETBIT(_legend_excludebits, p->index);
|
||||
}
|
||||
w->click_state = ((~_legend_excludebits) << 3);
|
||||
w->click_state = (~_legend_excludebits) << 3;
|
||||
DrawWindowWidgets(w);
|
||||
|
||||
FOR_ALL_PLAYERS(p) {
|
||||
if (!p->is_active)
|
||||
continue;
|
||||
if (!p->is_active) continue;
|
||||
|
||||
DrawPlayerIcon(p->index, 4, 18+p->index*12);
|
||||
|
||||
@@ -240,7 +243,7 @@ static void GraphLegendWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
case WE_CLICK:
|
||||
if (IS_INT_INSIDE(e->click.widget, 3, 11)) {
|
||||
_legend_excludebits ^= (1 << (e->click.widget-3));
|
||||
_legend_excludebits ^= (1 << (e->click.widget - 3));
|
||||
SetWindowDirty(w);
|
||||
InvalidateWindow(WC_INCOME_GRAPH, 0);
|
||||
InvalidateWindow(WC_OPERATING_PROFIT, 0);
|
||||
@@ -253,7 +256,7 @@ static void GraphLegendWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _graph_legend_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 249, 0, 13, STR_704E_KEY_TO_COMPANY_GRAPHS, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 249, 14, 113, 0x0,STR_NULL},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 2, 247, 16, 27, 0x0,STR_704F_CLICK_HERE_TO_TOGGLE_COMPANY},
|
||||
@@ -286,7 +289,7 @@ static void ShowGraphLegend(void)
|
||||
|
||||
static void SetupGraphDrawerForPlayers(GraphDrawer *gd)
|
||||
{
|
||||
Player *p;
|
||||
const Player* p;
|
||||
uint excludebits = _legend_excludebits;
|
||||
int nums;
|
||||
int mo,yr;
|
||||
@@ -320,7 +323,7 @@ static void OperatingProfitWndProc(Window *w, WindowEvent *e)
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
GraphDrawer gd;
|
||||
Player *p;
|
||||
const Player* p;
|
||||
int i,j;
|
||||
int numd;
|
||||
|
||||
@@ -330,7 +333,7 @@ static void OperatingProfitWndProc(Window *w, WindowEvent *e)
|
||||
gd.top = 18;
|
||||
gd.height = 136;
|
||||
gd.include_neg = true;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT32;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT;
|
||||
gd.color_3 = 0x10;
|
||||
gd.color_2 = 0xD7;
|
||||
gd.bg_line_color = 0xE;
|
||||
@@ -361,7 +364,7 @@ static void OperatingProfitWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _operating_profit_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 525, 0, 13, STR_7025_OPERATING_PROFIT_GRAPH, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 526, 575, 0, 13, STR_704C_KEY, STR_704D_SHOW_KEY_TO_GRAPHS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 575, 14, 173, 0x0, STR_NULL},
|
||||
@@ -394,7 +397,7 @@ static void IncomeGraphWndProc(Window *w, WindowEvent *e)
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
GraphDrawer gd;
|
||||
Player *p;
|
||||
const Player* p;
|
||||
int i,j;
|
||||
int numd;
|
||||
|
||||
@@ -404,7 +407,7 @@ static void IncomeGraphWndProc(Window *w, WindowEvent *e)
|
||||
gd.top = 18;
|
||||
gd.height = 104;
|
||||
gd.include_neg = false;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT32;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT;
|
||||
gd.color_3 = 0x10;
|
||||
gd.color_2 = 0xD7;
|
||||
gd.bg_line_color = 0xE;
|
||||
@@ -436,7 +439,7 @@ static void IncomeGraphWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _income_graph_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 525, 0, 13, STR_7022_INCOME_GRAPH, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 526, 575, 0, 13, STR_704C_KEY, STR_704D_SHOW_KEY_TO_GRAPHS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 575, 14, 141, 0x0, STR_NULL},
|
||||
@@ -467,7 +470,7 @@ static void DeliveredCargoGraphWndProc(Window *w, WindowEvent *e)
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
GraphDrawer gd;
|
||||
Player *p;
|
||||
const Player* p;
|
||||
int i,j;
|
||||
int numd;
|
||||
|
||||
@@ -509,7 +512,7 @@ static void DeliveredCargoGraphWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _delivered_cargo_graph_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 525, 0, 13, STR_7050_UNITS_OF_CARGO_DELIVERED, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 526, 575, 0, 13, STR_704C_KEY, STR_704D_SHOW_KEY_TO_GRAPHS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 575, 14, 141, 0x0, STR_NULL},
|
||||
@@ -540,7 +543,7 @@ static void PerformanceHistoryWndProc(Window *w, WindowEvent *e)
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
GraphDrawer gd;
|
||||
Player *p;
|
||||
const Player* p;
|
||||
int i,j;
|
||||
int numd;
|
||||
|
||||
@@ -584,7 +587,7 @@ static void PerformanceHistoryWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _performance_history_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 475, 0, 13, STR_7051_COMPANY_PERFORMANCE_RATINGS, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 526, 575, 0, 13, STR_704C_KEY, STR_704D_SHOW_KEY_TO_GRAPHS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 476, 525, 0, 13, STR_PERFORMANCE_DETAIL_KEY, STR_704D_SHOW_KEY_TO_GRAPHS},
|
||||
@@ -616,7 +619,7 @@ static void CompanyValueGraphWndProc(Window *w, WindowEvent *e)
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
GraphDrawer gd;
|
||||
Player *p;
|
||||
const Player* p;
|
||||
int i,j;
|
||||
int numd;
|
||||
|
||||
@@ -626,7 +629,7 @@ static void CompanyValueGraphWndProc(Window *w, WindowEvent *e)
|
||||
gd.top = 18;
|
||||
gd.height = 200;
|
||||
gd.include_neg = false;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT64;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT;
|
||||
gd.color_3 = 0x10;
|
||||
gd.color_2 = 0xD7;
|
||||
gd.bg_line_color = 0xE;
|
||||
@@ -658,7 +661,7 @@ static void CompanyValueGraphWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _company_value_graph_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 525, 0, 13, STR_7052_COMPANY_VALUES, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 14, 526, 575, 0, 13, STR_704C_KEY, STR_704D_SHOW_KEY_TO_GRAPHS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 575, 14, 237, 0x0, STR_NULL},
|
||||
@@ -712,7 +715,7 @@ static void CargoPaymentRatesWndProc(Window *w, WindowEvent *e)
|
||||
gd.top = 24;
|
||||
gd.height = 104;
|
||||
gd.include_neg = false;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT32;
|
||||
gd.format_str_y_axis = STR_CURRCOMPACT;
|
||||
gd.color_3 = 16;
|
||||
gd.color_2 = 215;
|
||||
gd.bg_line_color = 14;
|
||||
@@ -810,69 +813,60 @@ static inline StringID GetPerformanceTitleFromValue(uint value)
|
||||
return _performance_titles[minu(value, 1000) >> 6];
|
||||
}
|
||||
|
||||
static int CDECL _perf_hist_comp(const void *elem1, const void *elem2 ) {
|
||||
const Player *p1 = *(const Player* const *)elem1;
|
||||
const Player *p2 = *(const Player* const *)elem2;
|
||||
int32 v = p2->old_economy[1].performance_history - p1->old_economy[1].performance_history;
|
||||
return (v!=0) | (v >> (sizeof(int32)*8-1));
|
||||
static int CDECL PerfHistComp(const void* elem1, const void* elem2)
|
||||
{
|
||||
const Player* p1 = *(const Player* const*)elem1;
|
||||
const Player* p2 = *(const Player* const*)elem2;
|
||||
|
||||
return p2->old_economy[1].performance_history - p1->old_economy[1].performance_history;
|
||||
}
|
||||
|
||||
static void CompanyLeagueWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch(e->event) {
|
||||
case WE_PAINT: {
|
||||
Player *p;
|
||||
Player *plist[MAX_PLAYERS];
|
||||
size_t pl_num, i;
|
||||
switch (e->event) {
|
||||
case WE_PAINT: {
|
||||
const Player* plist[MAX_PLAYERS];
|
||||
const Player* p;
|
||||
uint pl_num;
|
||||
uint i;
|
||||
|
||||
DrawWindowWidgets(w);
|
||||
DrawWindowWidgets(w);
|
||||
|
||||
pl_num=0;
|
||||
FOR_ALL_PLAYERS(p) {
|
||||
if (p->is_active)
|
||||
plist[pl_num++] = p;
|
||||
pl_num = 0;
|
||||
FOR_ALL_PLAYERS(p) if (p->is_active) plist[pl_num++] = p;
|
||||
|
||||
qsort((void*)plist, pl_num, sizeof(*plist), PerfHistComp);
|
||||
|
||||
for (i = 0; i != pl_num; i++) {
|
||||
p = plist[i];
|
||||
SetDParam(0, i + STR_01AC_1ST);
|
||||
SetDParam(1, p->name_1);
|
||||
SetDParam(2, p->name_2);
|
||||
SetDParam(3, GetPlayerNameString(p->index, 4));
|
||||
SetDParam(5, GetPerformanceTitleFromValue(p->old_economy[1].performance_history));
|
||||
|
||||
DrawString(2, 15 + i * 10, i == 0 ? STR_7054 : STR_7055, 0);
|
||||
DrawPlayerIcon(p->index, 27, 16 + i * 10);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
assert(pl_num > 0);
|
||||
|
||||
qsort(plist, pl_num, sizeof(Player*), _perf_hist_comp);
|
||||
|
||||
i = 0;
|
||||
do {
|
||||
SetDParam(0, i + 1 + STR_01AB);
|
||||
p = plist[i];
|
||||
SetDParam(1, p->name_1);
|
||||
SetDParam(2, p->name_2);
|
||||
|
||||
SetDParam(3, GetPlayerNameString(p->index, 4));
|
||||
/* WARNING ugly hack!
|
||||
GetPlayerNameString sets up (Player #) if the player is human in an extra DPARAM16
|
||||
It seems that if player is non-human, nothing is set up, so param is 0. GetString doesn't like
|
||||
that because there is another param after it.
|
||||
So we'll just shift the rating one back if player is AI and all is fine
|
||||
*/
|
||||
SetDParam((IS_HUMAN_PLAYER(p->index) ? 5 : 4), GetPerformanceTitleFromValue(p->old_economy[1].performance_history));
|
||||
|
||||
DrawString(2, 15 + i * 10, i == 0 ? STR_7054 : STR_7055, 0);
|
||||
DrawPlayerIcon(p->index, 27, 16 + i * 10);
|
||||
} while (++i != pl_num);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static const Widget _company_league_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 399, 0, 13, STR_7053_COMPANY_LEAGUE_TABLE, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 399, 14, 96, 0x0, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 387, 0, 13, STR_7053_COMPANY_LEAGUE_TABLE, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_STICKYBOX, RESIZE_NONE, 14, 388, 399, 0, 13, STR_NULL, STR_STICKY_BUTTON},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 399, 14, 96, 0x0, STR_NULL},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
static const WindowDesc _company_league_desc = {
|
||||
-1, -1, 400, 97,
|
||||
WC_COMPANY_LEAGUE,0,
|
||||
WDF_STD_TOOLTIPS | WDF_STD_BTN | WDF_DEF_WIDGET,
|
||||
WDF_STD_TOOLTIPS | WDF_STD_BTN | WDF_DEF_WIDGET | WDF_STICKY_BUTTON,
|
||||
_company_league_widgets,
|
||||
CompanyLeagueWndProc
|
||||
};
|
||||
@@ -904,7 +898,7 @@ static void PerformanceRatingDetailWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
// Paint the player icons
|
||||
for (i=0;i<MAX_PLAYERS;i++) {
|
||||
if (!DEREF_PLAYER(i)->is_active) {
|
||||
if (!GetPlayer(i)->is_active) {
|
||||
// Check if we have the player as an active player
|
||||
if (!(w->disabled_state & (1 << (i+13)))) {
|
||||
// Bah, player gone :(
|
||||
@@ -938,8 +932,8 @@ static void PerformanceRatingDetailWndProc(Window *w, WindowEvent *e)
|
||||
for (i=0;i<NUM_SCORE;i++) {
|
||||
y += 20;
|
||||
val = _score_part[owner][i];
|
||||
needed = score_info[i].needed;
|
||||
score = score_info[i].score;
|
||||
needed = _score_info[i].needed;
|
||||
score = _score_info[i].score;
|
||||
// SCORE_TOTAL has his own rulez ;)
|
||||
if (i == SCORE_TOTAL) {
|
||||
needed = total_score;
|
||||
@@ -1024,7 +1018,7 @@ static void PerformanceRatingDetailWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
// Hide the player who are not active
|
||||
for (i=0;i<MAX_PLAYERS;i++) {
|
||||
if (!DEREF_PLAYER(i)->is_active) {
|
||||
if (!GetPlayer(i)->is_active) {
|
||||
w->disabled_state += 1 << (i+13);
|
||||
}
|
||||
}
|
||||
@@ -1063,7 +1057,7 @@ static void PerformanceRatingDetailWndProc(Window *w, WindowEvent *e)
|
||||
}
|
||||
|
||||
static const Widget _performance_rating_detail_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 14, 11, 298, 0, 13, STR_PERFORMANCE_DETAIL, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 14, 0, 298, 14, 27, 0x0, STR_NULL},
|
||||
|
||||
@@ -1157,7 +1151,6 @@ static void SignListWndProc(Window *w, WindowEvent *e)
|
||||
{
|
||||
switch (e->event) {
|
||||
case WE_PAINT: {
|
||||
uint32 i;
|
||||
int y = 16; // offset from top of widget
|
||||
|
||||
if (_sign_sort_dirty)
|
||||
@@ -1174,12 +1167,11 @@ static void SignListWndProc(Window *w, WindowEvent *e)
|
||||
return;
|
||||
}
|
||||
|
||||
{
|
||||
SignStruct *ss;
|
||||
{ const SignStruct *ss;
|
||||
uint16 i;
|
||||
|
||||
/* Start drawing the signs */
|
||||
i = 0;
|
||||
for (i = w->vscroll.pos; i < (uint)w->vscroll.cap + w->vscroll.pos && i < w->vscroll.count; i++) {
|
||||
for (i = w->vscroll.pos; i < w->vscroll.cap + w->vscroll.pos && i < w->vscroll.count; i++) {
|
||||
ss = GetSign(_sign_sort[i]);
|
||||
|
||||
if (ss->owner != OWNER_NONE)
|
||||
@@ -1206,7 +1198,7 @@ static void SignListWndProc(Window *w, WindowEvent *e)
|
||||
return;
|
||||
|
||||
ss = GetSign(_sign_sort[id_v]);
|
||||
ScrollMainWindowToTile(TILE_FROM_XY(ss->x, ss->y));
|
||||
ScrollMainWindowToTile(TileVirtXY(ss->x, ss->y));
|
||||
} break;
|
||||
}
|
||||
} break;
|
||||
|
||||
@@ -1,20 +1,22 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef GUI_H
|
||||
#define GUI_H
|
||||
|
||||
#include "station.h"
|
||||
#include "window.h"
|
||||
|
||||
/* main_gui.c */
|
||||
void SetupColorsAndInitialWindow(void);
|
||||
void CcPlaySound10(bool success, uint tile, uint32 p1, uint32 p2);
|
||||
void CcBuildCanal(bool success, uint tile, uint32 p1, uint32 p2);
|
||||
void CcTerraform(bool success, uint tile, uint32 p1, uint32 p2);
|
||||
void CcPlaySound10(bool success, TileIndex tile, uint32 p1, uint32 p2);
|
||||
void CcBuildCanal(bool success, TileIndex tile, uint32 p1, uint32 p2);
|
||||
void CcTerraform(bool success, TileIndex tile, uint32 p1, uint32 p2);
|
||||
|
||||
/* settings_gui.c */
|
||||
void ShowGameOptions(void);
|
||||
void ShowGameDifficulty(void);
|
||||
void ShowPatchesSelection(void);
|
||||
void ShowNewgrf(void);
|
||||
void ShowCustCurrency(void);
|
||||
|
||||
/* graph_gui.c */
|
||||
void ShowOperatingProfitGraph(void);
|
||||
@@ -32,39 +34,36 @@ void ShowMessageOptions(void);
|
||||
void ShowMessageHistory(void);
|
||||
|
||||
/* traintoolb_gui.c */
|
||||
void ShowBuildRailToolbar(int index, int button);
|
||||
void PlaceProc_BuyLand(uint tile);
|
||||
void ShowBuildRailToolbar(RailType railtype, int button);
|
||||
void PlaceProc_BuyLand(TileIndex tile);
|
||||
|
||||
/* train_gui.c */
|
||||
void ShowPlayerTrains(int player, int station);
|
||||
void ShowTrainViewWindow(Vehicle *v);
|
||||
void ShowTrainDetailsWindow(Vehicle *v);
|
||||
void ShowOrdersWindow(Vehicle *v);
|
||||
void ShowPlayerTrains(PlayerID player, StationID station);
|
||||
void ShowTrainViewWindow(const Vehicle *v);
|
||||
void ShowOrdersWindow(const Vehicle* v);
|
||||
|
||||
void ShowRoadVehViewWindow(Vehicle *v);
|
||||
void ShowRoadVehViewWindow(const Vehicle* v);
|
||||
|
||||
/* road_gui.c */
|
||||
void ShowBuildRoadToolbar(void);
|
||||
void ShowBuildRoadScenToolbar(void);
|
||||
void ShowPlayerRoadVehicles(int player, int station);
|
||||
void ShowPlayerRoadVehicles(PlayerID player, StationID station);
|
||||
|
||||
/* dock_gui.c */
|
||||
void ShowBuildDocksToolbar(void);
|
||||
void ShowPlayerShips(int player, int station);
|
||||
void ShowPlayerShips(PlayerID player, StationID station);
|
||||
|
||||
void ShowShipViewWindow(Vehicle *v);
|
||||
void ShowShipViewWindow(const Vehicle* v);
|
||||
|
||||
/* aircraft_gui.c */
|
||||
void ShowBuildAirToolbar(void);
|
||||
void ShowPlayerAircraft(int player, int station);
|
||||
void ShowPlayerAircraft(PlayerID player, StationID station);
|
||||
|
||||
/* terraform_gui.c */
|
||||
void ShowTerraformToolbar(void);
|
||||
|
||||
void PlaceProc_DemolishArea(uint tile);
|
||||
void PlaceProc_LowerLand(uint tile);
|
||||
void PlaceProc_RaiseLand(uint tile);
|
||||
void PlaceProc_LevelLand(uint tile);
|
||||
void PlaceProc_DemolishArea(TileIndex tile);
|
||||
void PlaceProc_LevelLand(TileIndex tile);
|
||||
bool GUIPlaceProcDragXY(const WindowEvent *we);
|
||||
|
||||
enum { // max 32 - 4 = 28 types
|
||||
@@ -72,7 +71,8 @@ enum { // max 32 - 4 = 28 types
|
||||
GUI_PlaceProc_LevelArea = 1 << 4,
|
||||
GUI_PlaceProc_DesertArea = 2 << 4,
|
||||
GUI_PlaceProc_WaterArea = 3 << 4,
|
||||
GUI_PlaceProc_ConvertRailArea = 4 << 4
|
||||
GUI_PlaceProc_ConvertRailArea = 4 << 4,
|
||||
GUI_PlaceProc_RockyArea = 5 << 4,
|
||||
};
|
||||
|
||||
/* misc_gui.c */
|
||||
@@ -83,16 +83,16 @@ void ShowBuildTreesScenToolbar(void);
|
||||
void ShowTownDirectory(void);
|
||||
void ShowIndustryDirectory(void);
|
||||
void ShowSubsidiesList(void);
|
||||
void ShowPlayerStations(int player);
|
||||
void ShowPlayerFinances(int player);
|
||||
void ShowPlayerCompany(int player);
|
||||
void ShowPlayerStations(PlayerID player);
|
||||
void ShowPlayerFinances(PlayerID player);
|
||||
void ShowPlayerCompany(PlayerID player);
|
||||
void ShowSignList(void);
|
||||
|
||||
void ShowEstimatedCostOrIncome(int32 cost, int x, int y);
|
||||
void ShowErrorMessage(StringID msg_1, StringID msg_2, int x, int y);
|
||||
|
||||
void DrawStationCoverageAreaText(int sx, int sy, uint mask,int rad);
|
||||
void CheckRedrawStationCoverage(Window *w);
|
||||
void CheckRedrawStationCoverage(const Window* w);
|
||||
|
||||
void ShowSmallMap(void);
|
||||
void ShowExtraViewPortWindow(void);
|
||||
@@ -103,29 +103,27 @@ void SetHScrollCount(Window *w, int num);
|
||||
void ShowCheatWindow(void);
|
||||
void AskForNewGameToStart(void);
|
||||
|
||||
void DrawEditBox(Window *w, int wid);
|
||||
void HandleEditBox(Window *w, int wid);
|
||||
int HandleEditBoxKey(Window *w, int wid, WindowEvent *we);
|
||||
void DrawEditBox(Window *w, querystr_d *string, int wid);
|
||||
void HandleEditBox(Window *w, querystr_d *string, int wid);
|
||||
int HandleEditBoxKey(Window *w, querystr_d *string, int wid, WindowEvent *we);
|
||||
bool HandleCaret(Textbuf *tb);
|
||||
|
||||
void DeleteTextBufferAll(Textbuf *tb);
|
||||
bool DeleteTextBufferChar(Textbuf *tb, int delmode);
|
||||
bool InsertTextBufferChar(Textbuf *tb, byte key);
|
||||
bool InsertTextBufferClipboard(Textbuf *tb);
|
||||
bool MoveTextBufferPos(Textbuf *tb, int navmode);
|
||||
void UpdateTextBufferSize(Textbuf *tb);
|
||||
/* IS_INT_INSIDE = filter for ascii-function codes like BELL and so on [we need an special filter here later] */
|
||||
static inline bool IsValidAsciiChar(byte key) {return IS_INT_INSIDE(key, ' ', 256);}
|
||||
|
||||
void BuildFileList(void);
|
||||
void SetFiosType(const byte fiostype);
|
||||
|
||||
/* FIOS_TYPE_FILE, FIOS_TYPE_OLDFILE etc. different colours */
|
||||
static const byte _fios_colors[] = {13, 9, 9, 6, 5, 6, 5};
|
||||
|
||||
extern const byte _fios_colors[];
|
||||
|
||||
/* network gui */
|
||||
void ShowNetworkGameWindow(void);
|
||||
void ShowChatWindow(StringID str, StringID caption, int maxlen, int maxwidth, byte window_class, uint16 window_number);
|
||||
void ShowChatWindow(StringID str, StringID caption, int maxlen, int maxwidth, WindowClass window_class, WindowNumber window_number);
|
||||
|
||||
/* bridge_gui.c */
|
||||
void ShowBuildBridgeWindow(uint start, uint end, byte type);
|
||||
@@ -142,10 +140,8 @@ void ShowQueryString(StringID str, StringID caption, uint maxlen, uint maxwidth,
|
||||
void ShowMusicWindow(void);
|
||||
|
||||
/* main_gui.c */
|
||||
VARDEF byte _construct_mode;
|
||||
VARDEF byte _station_show_coverage;
|
||||
VARDEF PlaceProc *_place_proc;
|
||||
VARDEF bool _no_button_sound;
|
||||
|
||||
/* vehicle_gui.c */
|
||||
void InitializeGUI(void);
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef HAL_H
|
||||
#define HAL_H
|
||||
|
||||
@@ -10,16 +12,11 @@ typedef struct {
|
||||
const char *(*start)(const char * const *parm);
|
||||
void (*stop)(void);
|
||||
void (*make_dirty)(int left, int top, int width, int height);
|
||||
int (*main_loop)(void);
|
||||
void (*main_loop)(void);
|
||||
bool (*change_resolution)(int w, int h);
|
||||
void (*toggle_fullscreen)(bool fullscreen);
|
||||
} HalVideoDriver;
|
||||
|
||||
enum {
|
||||
ML_QUIT = 0,
|
||||
ML_SWITCHDRIVER = 1,
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
const char *(*start)(const char * const *parm);
|
||||
void (*stop)(void);
|
||||
@@ -35,49 +32,10 @@ typedef struct {
|
||||
void (*set_volume)(byte vol);
|
||||
} HalMusicDriver;
|
||||
|
||||
typedef struct {
|
||||
const char *name;
|
||||
const char *longname;
|
||||
const void *drv;
|
||||
uint32 flags;
|
||||
} DriverDesc;
|
||||
|
||||
enum {
|
||||
HALERR_OK = 0,
|
||||
HALERR_ERROR = 1,
|
||||
};
|
||||
|
||||
extern const HalMusicDriver _null_music_driver;
|
||||
extern const HalVideoDriver _null_video_driver;
|
||||
extern const HalSoundDriver _null_sound_driver;
|
||||
|
||||
VARDEF HalMusicDriver *_music_driver;
|
||||
VARDEF HalSoundDriver *_sound_driver;
|
||||
VARDEF HalVideoDriver *_video_driver;
|
||||
|
||||
extern const DriverDesc _video_driver_descs[];
|
||||
extern const DriverDesc _sound_driver_descs[];
|
||||
extern const DriverDesc _music_driver_descs[];
|
||||
|
||||
#if defined(WITH_SDL)
|
||||
extern const HalSoundDriver _sdl_sound_driver;
|
||||
extern const HalVideoDriver _sdl_video_driver;
|
||||
#endif
|
||||
|
||||
#if defined(UNIX)
|
||||
extern const HalMusicDriver _extmidi_music_driver;
|
||||
#endif
|
||||
|
||||
#if defined(__BEOS__)
|
||||
extern const HalMusicDriver _bemidi_music_driver;
|
||||
#endif
|
||||
|
||||
#if defined(__OS2__)
|
||||
extern const HalMusicDriver _os2_music_driver;
|
||||
#endif
|
||||
|
||||
extern const HalVideoDriver _dedicated_video_driver;
|
||||
|
||||
enum DriverType {
|
||||
VIDEO_DRIVER = 0,
|
||||
SOUND_DRIVER = 1,
|
||||
@@ -85,19 +43,10 @@ enum DriverType {
|
||||
};
|
||||
|
||||
extern void GameLoop(void);
|
||||
extern bool _dbg_screen_rect;
|
||||
|
||||
void LoadDriver(int driver, const char *name);
|
||||
|
||||
const char *GetDriverParam(const char * const *parm, const char *name);
|
||||
bool GetDriverParamBool(const char * const *parm, const char *name);
|
||||
int GetDriverParamInt(const char * const *parm, const char *name, int def);
|
||||
|
||||
|
||||
|
||||
// Deals with finding savegames
|
||||
typedef struct {
|
||||
uint16 id;
|
||||
byte type;
|
||||
uint64 mtime;
|
||||
char title[64];
|
||||
@@ -112,6 +61,7 @@ enum {
|
||||
FIOS_TYPE_OLDFILE = 4,
|
||||
FIOS_TYPE_SCENARIO = 5,
|
||||
FIOS_TYPE_OLD_SCENARIO = 6,
|
||||
FIOS_TYPE_DIRECT = 7,
|
||||
};
|
||||
|
||||
|
||||
@@ -136,7 +86,7 @@ char *FiosBrowseTo(const FiosItem *item);
|
||||
// Return path, free space and stringID
|
||||
StringID FiosGetDescText(const char **path, uint32 *tot);
|
||||
// Delete a name
|
||||
void FiosDelete(const char *name);
|
||||
bool FiosDelete(const char *name);
|
||||
// Make a filename from a name
|
||||
void FiosMakeSavegameName(char *buf, const char *name);
|
||||
|
||||
|
||||
+4
-2
@@ -1,3 +1,5 @@
|
||||
/* $Id$ */
|
||||
|
||||
#ifndef INDUSTRY_H
|
||||
#define INDUSTRY_H
|
||||
|
||||
@@ -7,7 +9,7 @@ struct Industry {
|
||||
TileIndex xy;
|
||||
byte width; /* swapped order of w/h with town */
|
||||
byte height;
|
||||
Town *town;
|
||||
const Town* town;
|
||||
byte produced_cargo[2];
|
||||
uint16 cargo_waiting[2];
|
||||
byte production_rate[2];
|
||||
@@ -105,4 +107,4 @@ enum {
|
||||
IT_SUGAR_MINE = 36,
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif /* INDUSTRY_H */
|
||||
|
||||
+350
-381
File diff suppressed because it is too large
Load Diff
+103
-102
@@ -1,8 +1,12 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "debug.h"
|
||||
#include "functions.h"
|
||||
#include "strings.h"
|
||||
#include "table/strings.h"
|
||||
#include "table/sprites.h"
|
||||
#include "map.h"
|
||||
#include "gui.h"
|
||||
#include "window.h"
|
||||
@@ -11,6 +15,7 @@
|
||||
#include "viewport.h"
|
||||
#include "industry.h"
|
||||
#include "town.h"
|
||||
#include "variables.h"
|
||||
|
||||
/* Present in table/build_industry.h" */
|
||||
extern const byte _build_industry_types[4][12];
|
||||
@@ -35,7 +40,7 @@ static void BuildIndustryWndProc(Window *w, WindowEvent *e)
|
||||
case WE_CLICK: {
|
||||
int wid = e->click.widget;
|
||||
if (wid >= 3) {
|
||||
if (HandlePlacePushButton(w, wid, 0xFF1, 1, NULL))
|
||||
if (HandlePlacePushButton(w, wid, SPR_CURSOR_INDUSTRY, 1, NULL))
|
||||
WP(w,def_d).data_1 = wid - 3;
|
||||
}
|
||||
} break;
|
||||
@@ -56,11 +61,11 @@ static const Widget _build_industry_land0_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 7, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 115, 0x0, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION, STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_0242_SAWMILL, STR_0264_CONSTRUCT_SAWMILL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0247_STEEL_MILL, STR_0269_CONSTRUCT_STEEL_MILL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION, STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_0242_SAWMILL, STR_0264_CONSTRUCT_SAWMILL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0247_STEEL_MILL, STR_0269_CONSTRUCT_STEEL_MILL},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -68,11 +73,11 @@ static const Widget _build_industry_land1_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 7, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 115, 0x0, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION, STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024C_PAPER_MILL, STR_026E_CONSTRUCT_PAPER_MILL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68, 79, STR_024E_PRINTING_WORKS, STR_0270_CONSTRUCT_PRINTING_WORKS},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION, STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024C_PAPER_MILL, STR_026E_CONSTRUCT_PAPER_MILL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68, 79, STR_024E_PRINTING_WORKS, STR_0270_CONSTRUCT_PRINTING_WORKS},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -80,11 +85,11 @@ static const Widget _build_industry_land2_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 7, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 115, 0x0, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0250_LUMBER_MILL, STR_0273_CONSTRUCT_LUMBER_MILL_TO},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0254_WATER_TOWER, STR_0277_CONSTRUCT_WATER_TOWER_CAN},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0250_LUMBER_MILL, STR_0273_CONSTRUCT_LUMBER_MILL_TO},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0254_WATER_TOWER, STR_0277_CONSTRUCT_WATER_TOWER_CAN},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -92,10 +97,10 @@ static const Widget _build_industry_land3_widgets[] = {
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 7, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 115, 0x0, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0258_CANDY_FACTORY, STR_027B_CONSTRUCT_CANDY_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_025B_TOY_SHOP, STR_027E_CONSTRUCT_TOY_SHOP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_025C_TOY_FACTORY, STR_027F_CONSTRUCT_TOY_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_025E_FIZZY_DRINK_FACTORY, STR_0281_CONSTRUCT_FIZZY_DRINK_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0258_CANDY_FACTORY, STR_027B_CONSTRUCT_CANDY_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_025B_TOY_SHOP, STR_027E_CONSTRUCT_TOY_SHOP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_025C_TOY_FACTORY, STR_027F_CONSTRUCT_TOY_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_025E_FIZZY_DRINK_FACTORY, STR_0281_CONSTRUCT_FIZZY_DRINK_FACTORY},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -104,18 +109,18 @@ static const Widget _build_industry_land0_widgets_extra[] = {
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY,STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 187, 0x0, STR_NULL},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION,STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_0242_SAWMILL, STR_0264_CONSTRUCT_SAWMILL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0247_STEEL_MILL, STR_0269_CONSTRUCT_STEEL_MILL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION,STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_0242_SAWMILL, STR_0264_CONSTRUCT_SAWMILL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0247_STEEL_MILL, STR_0269_CONSTRUCT_STEEL_MILL},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 84, 95, STR_0240_COAL_MINE, STR_CONSTRUCT_COAL_MINE_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 97, 108, STR_0243_FOREST, STR_CONSTRUCT_FOREST_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 110, 121, STR_0245_OIL_RIG, STR_CONSTRUCT_OIL_RIG_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 123, 134, STR_0248_FARM, STR_CONSTRUCT_FARM_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 136, 147, STR_024A_OIL_WELLS, STR_CONSTRUCT_OIL_WELLS_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 149, 160, STR_0249_IRON_ORE_MINE, STR_CONSTRUCT_IRON_ORE_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 84, 95, STR_0240_COAL_MINE, STR_CONSTRUCT_COAL_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 97, 108, STR_0243_FOREST, STR_CONSTRUCT_FOREST_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 110, 121, STR_0245_OIL_RIG, STR_CONSTRUCT_OIL_RIG_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 123, 134, STR_0248_FARM, STR_CONSTRUCT_FARM_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 136, 147, STR_024A_OIL_WELLS, STR_CONSTRUCT_OIL_WELLS_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 149, 160, STR_0249_IRON_ORE_MINE, STR_CONSTRUCT_IRON_ORE_MINE_TIP},
|
||||
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
@@ -125,17 +130,17 @@ static const Widget _build_industry_land1_widgets_extra[] = {
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 174, 0x0, STR_NULL},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION, STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024C_PAPER_MILL, STR_026E_CONSTRUCT_PAPER_MILL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68, 79, STR_024E_PRINTING_WORKS, STR_0270_CONSTRUCT_PRINTING_WORKS},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0241_POWER_STATION, STR_0263_CONSTRUCT_POWER_STATION},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024C_PAPER_MILL, STR_026E_CONSTRUCT_PAPER_MILL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68, 79, STR_024E_PRINTING_WORKS, STR_0270_CONSTRUCT_PRINTING_WORKS},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 81+3, 92+3, STR_0240_COAL_MINE, STR_CONSTRUCT_COAL_MINE_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 94+3, 105+3, STR_0243_FOREST, STR_CONSTRUCT_FOREST_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 107+3, 118+3, STR_0248_FARM, STR_CONSTRUCT_FARM_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 120+3, 131+3, STR_024A_OIL_WELLS, STR_CONSTRUCT_OIL_WELLS_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 133+3, 144+3, STR_024F_GOLD_MINE, STR_CONSTRUCT_GOLD_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 81+3, 92+3, STR_0240_COAL_MINE, STR_CONSTRUCT_COAL_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 94+3, 105+3, STR_0243_FOREST, STR_CONSTRUCT_FOREST_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 107+3, 118+3, STR_0248_FARM, STR_CONSTRUCT_FARM_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 120+3, 131+3, STR_024A_OIL_WELLS, STR_CONSTRUCT_OIL_WELLS_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 133+3, 144+3, STR_024F_GOLD_MINE, STR_CONSTRUCT_GOLD_MINE_TIP},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -144,19 +149,19 @@ static const Widget _build_industry_land2_widgets_extra[] = {
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 200, 0x0, STR_NULL},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0250_LUMBER_MILL, STR_0273_CONSTRUCT_LUMBER_MILL_TO},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0254_WATER_TOWER, STR_0277_CONSTRUCT_WATER_TOWER_CAN},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0250_LUMBER_MILL, STR_0273_CONSTRUCT_LUMBER_MILL_TO},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_024D_FOOD_PROCESSING_PLANT,STR_026F_CONSTRUCT_FOOD_PROCESSING},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_0244_OIL_REFINERY, STR_0266_CONSTRUCT_OIL_REFINERY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_0246_FACTORY, STR_0268_CONSTRUCT_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68, 79, STR_0254_WATER_TOWER, STR_0277_CONSTRUCT_WATER_TOWER_CAN},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 81+3, 92+3, STR_024A_OIL_WELLS,STR_CONSTRUCT_OIL_WELLS_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 94+3, 105+3, STR_0255_DIAMOND_MINE, STR_CONSTRUCT_DIAMOND_MINE_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 107+3, 118+3, STR_0256_COPPER_ORE_MINE, STR_CONSTRUCT_COPPER_ORE_MINE_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 120+3, 131+3, STR_0248_FARM, STR_CONSTRUCT_FARM_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 133+3, 144+3, STR_0251_FRUIT_PLANTATION, STR_CONSTRUCT_FRUIT_PLANTATION_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 146+3, 157+3, STR_0252_RUBBER_PLANTATION,STR_CONSTRUCT_RUBBER_PLANTATION_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 159+3, 170+3, STR_0253_WATER_SUPPLY, STR_CONSTRUCT_WATER_SUPPLY_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 81+3, 92+3, STR_024A_OIL_WELLS,STR_CONSTRUCT_OIL_WELLS_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 94+3, 105+3, STR_0255_DIAMOND_MINE, STR_CONSTRUCT_DIAMOND_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 107+3, 118+3, STR_0256_COPPER_ORE_MINE, STR_CONSTRUCT_COPPER_ORE_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 120+3, 131+3, STR_0248_FARM, STR_CONSTRUCT_FARM_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 133+3, 144+3, STR_0251_FRUIT_PLANTATION, STR_CONSTRUCT_FRUIT_PLANTATION_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 146+3, 157+3, STR_0252_RUBBER_PLANTATION,STR_CONSTRUCT_RUBBER_PLANTATION_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 159+3, 170+3, STR_0253_WATER_SUPPLY, STR_CONSTRUCT_WATER_SUPPLY_TIP},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -165,18 +170,18 @@ static const Widget _build_industry_land3_widgets_extra[] = {
|
||||
{ WWT_CAPTION, RESIZE_NONE, 7, 11, 169, 0, 13, STR_0314_FUND_NEW_INDUSTRY, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_PANEL, RESIZE_NONE, 7, 0, 169, 14, 187, 0x0, STR_NULL},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0258_CANDY_FACTORY, STR_027B_CONSTRUCT_CANDY_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 29, 40, STR_025B_TOY_SHOP, STR_027E_CONSTRUCT_TOY_SHOP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 42, 53, STR_025C_TOY_FACTORY, STR_027F_CONSTRUCT_TOY_FACTORY},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 55, 66, STR_025E_FIZZY_DRINK_FACTORY, STR_0281_CONSTRUCT_FIZZY_DRINK_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 16, 27, STR_0258_CANDY_FACTORY, STR_027B_CONSTRUCT_CANDY_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 29, 40, STR_025B_TOY_SHOP, STR_027E_CONSTRUCT_TOY_SHOP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 42, 53, STR_025C_TOY_FACTORY, STR_027F_CONSTRUCT_TOY_FACTORY},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 55, 66, STR_025E_FIZZY_DRINK_FACTORY, STR_0281_CONSTRUCT_FIZZY_DRINK_FACTORY},
|
||||
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 68+3, 79+3, STR_0257_COTTON_CANDY_FOREST,STR_CONSTRUCT_COTTON_CANDY_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 81+3, 92+3, STR_0259_BATTERY_FARM, STR_CONSTRUCT_BATTERY_FARM_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 94+3, 105+3, STR_025A_COLA_WELLS, STR_CONSTRUCT_COLA_WELLS_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 107+3, 118+3, STR_025D_PLASTIC_FOUNTAINS,STR_CONSTRUCT_PLASTIC_FOUNTAINS_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 120+3, 131+3, STR_025F_BUBBLE_GENERATOR, STR_CONSTRUCT_BUBBLE_GENERATOR_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 133+3, 144+3, STR_0260_TOFFEE_QUARRY, STR_CONSTRUCT_TOFFEE_QUARRY_TIP},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 14, 2, 167, 146+3, 157+3, STR_0261_SUGAR_MINE, STR_CONSTRUCT_SUGAR_MINE_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 68+3, 79+3, STR_0257_COTTON_CANDY_FOREST,STR_CONSTRUCT_COTTON_CANDY_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 81+3, 92+3, STR_0259_BATTERY_FARM, STR_CONSTRUCT_BATTERY_FARM_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 94+3, 105+3, STR_025A_COLA_WELLS, STR_CONSTRUCT_COLA_WELLS_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 107+3, 118+3, STR_025D_PLASTIC_FOUNTAINS,STR_CONSTRUCT_PLASTIC_FOUNTAINS_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 120+3, 131+3, STR_025F_BUBBLE_GENERATOR, STR_CONSTRUCT_BUBBLE_GENERATOR_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 133+3, 144+3, STR_0260_TOFFEE_QUARRY, STR_CONSTRUCT_TOFFEE_QUARRY_TIP},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 14, 2, 167, 146+3, 157+3, STR_0261_SUGAR_MINE, STR_CONSTRUCT_SUGAR_MINE_TIP},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -262,6 +267,7 @@ static const WindowDesc * const _industry_window_desc[2][4] = {
|
||||
|
||||
void ShowBuildIndustryWindow(void)
|
||||
{
|
||||
if (_current_player == OWNER_SPECTATOR) return;
|
||||
AllocateWindowDescFront(_industry_window_desc[_patches.build_rawmaterial_ind][_opt_ptr->landscape],0);
|
||||
}
|
||||
|
||||
@@ -276,12 +282,9 @@ static void IndustryViewWndProc(Window *w, WindowEvent *e)
|
||||
case WE_PAINT: {
|
||||
const Industry *i;
|
||||
StringID str;
|
||||
// in editor, use bulldoze to destroy industry
|
||||
// Destroy Industry button costing money removed per request of dominik
|
||||
//w->disabled_state = (_patches.extra_dynamite && !_networking && _game_mode != GM_EDITOR) ? 0 : (1 << 6);
|
||||
|
||||
i = GetIndustry(w->window_number);
|
||||
SetDParam(0, i->town->index);
|
||||
SetDParam(1, i->type + STR_4802_COAL_MINE);
|
||||
SetDParam(0, w->window_number);
|
||||
DrawWindowWidgets(w);
|
||||
|
||||
if (i->accepts_cargo[0] != CT_INVALID) {
|
||||
@@ -301,8 +304,9 @@ static void IndustryViewWndProc(Window *w, WindowEvent *e)
|
||||
if (i->produced_cargo[0] != CT_INVALID) {
|
||||
DrawString(2, 117, STR_482A_PRODUCTION_LAST_MONTH, 0);
|
||||
|
||||
SetDParam(0, _cargoc.names_long[i->produced_cargo[0]]);
|
||||
SetDParam(1, i->total_production[0]);
|
||||
SetDParam(0, _cargoc.names_long_s[i->produced_cargo[0]] + ((i->total_production[0]!=1)<<5));
|
||||
|
||||
SetDParam(2, i->pct_transported[0] * 100 >> 8);
|
||||
DrawString(4 + (NEED_ALTERB ? 30 : 0), 127, STR_482B_TRANSPORTED, 0);
|
||||
// Let's put out those buttons..
|
||||
@@ -310,8 +314,8 @@ static void IndustryViewWndProc(Window *w, WindowEvent *e)
|
||||
DrawArrowButtons(5, 127, (WP(w,vp2_d).data_2 == 1 ? WP(w,vp2_d).data_3 : 0));
|
||||
|
||||
if (i->produced_cargo[1] != CT_INVALID) {
|
||||
SetDParam(0, _cargoc.names_long[i->produced_cargo[1]]);
|
||||
SetDParam(1, i->total_production[1]);
|
||||
SetDParam(0, _cargoc.names_long_s[i->produced_cargo[1]] + ((i->total_production[1]!=1)<<5));
|
||||
SetDParam(2, i->pct_transported[1] * 100 >> 8);
|
||||
DrawString(4 + (NEED_ALTERB ? 30 : 0), 137, STR_482B_TRANSPORTED, 0);
|
||||
// Let's put out those buttons..
|
||||
@@ -375,7 +379,7 @@ static void IndustryViewWndProc(Window *w, WindowEvent *e)
|
||||
break;
|
||||
case 6:
|
||||
i = GetIndustry(w->window_number);
|
||||
ScrollMainWindowToTile(i->xy + TILE_XY(1,1));
|
||||
ScrollMainWindowToTile(i->xy + TileDiffXY(1, 1));
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -416,7 +420,7 @@ static void UpdateIndustryProduction(Industry *i)
|
||||
}
|
||||
|
||||
static const Widget _industry_view_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 9, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 9, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 9, 11, 247, 0, 13, STR_4801, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_STICKYBOX, RESIZE_NONE, 9, 248, 259, 0, 13, 0x0, STR_STICKY_BUTTON},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 9, 0, 259, 14, 105, 0x0, STR_NULL},
|
||||
@@ -424,8 +428,6 @@ static const Widget _industry_view_widgets[] = {
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 9, 0, 259, 106, 147, 0x0, STR_NULL},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 9, 0, 129, 148, 159, STR_00E4_LOCATION, STR_482C_CENTER_THE_MAIN_VIEW_ON},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 9, 130, 259, 148, 159, 0x0, STR_NULL},
|
||||
// Destroy Industry button costing money removed per request of dominik
|
||||
//{ WWT_PUSHTXTBTN, RESIZE_NONE, 9, 130, 259, 148, 159, STR_INDUSTRYDIR_DESTROY, STR_482C_DESTROY_INDUSTRY},
|
||||
{ WIDGETS_END},
|
||||
};
|
||||
|
||||
@@ -449,12 +451,12 @@ void ShowIndustryViewWindow(int industry)
|
||||
WP(w,vp2_d).data_2 = 0;
|
||||
WP(w,vp2_d).data_3 = 0;
|
||||
i = GetIndustry(w->window_number);
|
||||
AssignWindowViewport(w, 3, 17, 0xFE, 0x56, i->xy + TILE_XY(1,1), 1);
|
||||
AssignWindowViewport(w, 3, 17, 0xFE, 0x56, i->xy + TileDiffXY(1, 1), 1);
|
||||
}
|
||||
}
|
||||
|
||||
static const Widget _industry_directory_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 13, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 13, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 13, 11, 495, 0, 13, STR_INDUSTRYDIR_CAPTION, STR_018C_WINDOW_TITLE_DRAG_THIS},
|
||||
{ WWT_STICKYBOX, RESIZE_NONE, 13, 496, 507, 0, 13, 0x0, STR_STICKY_BUTTON},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 13, 0, 100, 14, 25, STR_SORT_BY_NAME, STR_SORT_ORDER_TIP},
|
||||
@@ -491,28 +493,28 @@ static int CDECL GeneralIndustrySorter(const void *a, const void *b)
|
||||
// FIXME - Production & Transported sort need to be inversed...but, WTF it does not wanna!
|
||||
// FIXME - And no simple --> "if (!(_industry_sort_order & 1)) r = -r;" hack at the bottom!!
|
||||
case 2: { /* Sort by Production */
|
||||
if (i->produced_cargo[0] != 0xFF && j->produced_cargo[0] != 0xFF) { // both industries produce cargo?
|
||||
if (i->produced_cargo[1] == 0xFF) // producing one or two things?
|
||||
if (i->produced_cargo[0] != CT_INVALID && j->produced_cargo[0] != CT_INVALID) { // both industries produce cargo?
|
||||
if (i->produced_cargo[1] == CT_INVALID) // producing one or two things?
|
||||
r = j->total_production[0] - i->total_production[0];
|
||||
else
|
||||
r = (j->total_production[0] + j->total_production[1]) / 2 - (i->total_production[0] + i->total_production[1]) / 2;
|
||||
} else if (i->produced_cargo[0] == 0xFF && j->produced_cargo[0] == 0xFF) // none of them producing anything, let them go to the name-sorting
|
||||
} else if (i->produced_cargo[0] == CT_INVALID && j->produced_cargo[0] == CT_INVALID) // none of them producing anything, let them go to the name-sorting
|
||||
r = 0;
|
||||
else if (i->produced_cargo[0] == 0xFF) // end up the non-producer industry first/last in list
|
||||
else if (i->produced_cargo[0] == CT_INVALID) // end up the non-producer industry first/last in list
|
||||
r = 1;
|
||||
else
|
||||
r = -1;
|
||||
break;
|
||||
}
|
||||
case 3: /* Sort by Transported amount */
|
||||
if (i->produced_cargo[0] != 0xFF && j->produced_cargo[0] != 0xFF) { // both industries produce cargo?
|
||||
if (i->produced_cargo[1] == 0xFF) // producing one or two things?
|
||||
if (i->produced_cargo[0] != CT_INVALID && j->produced_cargo[0] != CT_INVALID) { // both industries produce cargo?
|
||||
if (i->produced_cargo[1] == CT_INVALID) // producing one or two things?
|
||||
r = (j->pct_transported[0] * 100 >> 8) - (i->pct_transported[0] * 100 >> 8);
|
||||
else
|
||||
r = ((j->pct_transported[0] * 100 >> 8) + (j->pct_transported[1] * 100 >> 8)) / 2 - ((i->pct_transported[0] * 100 >> 8) + (i->pct_transported[1] * 100 >> 8)) / 2;
|
||||
} else if (i->produced_cargo[0] == 0xFF && j->produced_cargo[0] == 0xFF) // none of them producing anything, let them go to the name-sorting
|
||||
} else if (i->produced_cargo[0] == CT_INVALID && j->produced_cargo[0] == CT_INVALID) // none of them producing anything, let them go to the name-sorting
|
||||
r = 0;
|
||||
else if (i->produced_cargo[0] == 0xFF) // end up the non-producer industry first/last in list
|
||||
else if (i->produced_cargo[0] == CT_INVALID) // end up the non-producer industry first/last in list
|
||||
r = 1;
|
||||
else
|
||||
r = -1;
|
||||
@@ -521,13 +523,13 @@ static int CDECL GeneralIndustrySorter(const void *a, const void *b)
|
||||
|
||||
// default to string sorting if they are otherwise equal
|
||||
if (r == 0) {
|
||||
SetDParam(0, i->town->townnameparts);
|
||||
GetString(buf1, i->town->townnametype);
|
||||
SetDParam(0, i->town->index);
|
||||
GetString(buf1, STR_TOWN);
|
||||
|
||||
if ( (val=*(const uint16*)b) != _last_industry_idx) {
|
||||
_last_industry_idx = val;
|
||||
SetDParam(0, j->town->townnameparts);
|
||||
GetString(_bufcache, j->town->townnametype);
|
||||
SetDParam(0, j->town->index);
|
||||
GetString(_bufcache, STR_TOWN);
|
||||
}
|
||||
r = strcmp(buf1, _bufcache);
|
||||
}
|
||||
@@ -576,27 +578,26 @@ static void IndustryDirectoryWndProc(Window *w, WindowEvent *e)
|
||||
SetVScrollCount(w, _num_industry_sort);
|
||||
|
||||
DrawWindowWidgets(w);
|
||||
DoDrawString(_industry_sort_order & 1 ? "\xAA" : "\xA0", _indicator_positions[_industry_sort_order>>1], 15, 0x10);
|
||||
DoDrawString(_industry_sort_order & 1 ? DOWNARROW : UPARROW, _indicator_positions[_industry_sort_order>>1], 15, 0x10);
|
||||
|
||||
p = w->vscroll.pos;
|
||||
n = 0;
|
||||
|
||||
while (p < _num_industry_sort) {
|
||||
i = GetIndustry(_industry_sort[p]);
|
||||
SetDParam(0, i->town->index);
|
||||
SetDParam(1, i->type + STR_4802_COAL_MINE);
|
||||
if (i->produced_cargo[0] != 0xFF) {
|
||||
SetDParam(3, i->total_production[0]);
|
||||
SetDParam(2, _cargoc.names_long_s[i->produced_cargo[0]] + ((i->total_production[0]!=1)<<5));
|
||||
SetDParam(0, i->index);
|
||||
if (i->produced_cargo[0] != CT_INVALID) {
|
||||
SetDParam(1, _cargoc.names_long[i->produced_cargo[0]]);
|
||||
SetDParam(2, i->total_production[0]);
|
||||
|
||||
if (i->produced_cargo[1] != 0xFF) {
|
||||
SetDParam(5, i->total_production[1]);
|
||||
SetDParam(4, _cargoc.names_long_s[i->produced_cargo[1]] + ((i->total_production[1]!=1)<<5));
|
||||
SetDParam(6, i->pct_transported[0] * 100 >> 8);
|
||||
SetDParam(7, i->pct_transported[1] * 100 >> 8);
|
||||
if (i->produced_cargo[1] != CT_INVALID) {
|
||||
SetDParam(3, _cargoc.names_long[i->produced_cargo[1]]);
|
||||
SetDParam(4, i->total_production[1]);
|
||||
SetDParam(5, i->pct_transported[0] * 100 >> 8);
|
||||
SetDParam(6, i->pct_transported[1] * 100 >> 8);
|
||||
DrawString(4, 28+n*10, STR_INDUSTRYDIR_ITEM_TWO, 0);
|
||||
} else {
|
||||
SetDParam(4, i->pct_transported[0] * 100 >> 8);
|
||||
SetDParam(3, i->pct_transported[0] * 100 >> 8);
|
||||
DrawString(4, 28+n*10, STR_INDUSTRYDIR_ITEM, 0);
|
||||
}
|
||||
} else {
|
||||
|
||||
+47
-51
@@ -1,21 +1,18 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "table/strings.h"
|
||||
#include "functions.h"
|
||||
#include "window.h"
|
||||
#include "gui.h"
|
||||
#include "viewport.h"
|
||||
#include "gfx.h"
|
||||
#include "player.h"
|
||||
#include "command.h"
|
||||
#include "console.h"
|
||||
#include "network.h"
|
||||
#include "variables.h"
|
||||
|
||||
extern void SwitchMode(int new_mode);
|
||||
|
||||
#if 0
|
||||
static void ShowSelectTutorialWindow() {}
|
||||
#endif
|
||||
|
||||
static const Widget _select_game_widgets[] = {
|
||||
{ WWT_CAPTION, RESIZE_NONE, 13, 0, 335, 0, 13, STR_0307_OPENTTD, STR_NULL},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 13, 0, 335, 14, 196, STR_NULL, STR_NULL},
|
||||
@@ -29,9 +26,9 @@ static const Widget _select_game_widgets[] = {
|
||||
{ WWT_PANEL_2, RESIZE_NONE, 12, 250, 326, 59, 113, 0x1318, STR_0311_SELECT_TOYLAND_LANDSCAPE},
|
||||
|
||||
{ WWT_PANEL, RESIZE_NONE, 12, 219, 254, 120, 131, STR_NULL, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 12, 255, 266, 120, 131, STR_0225, STR_NULL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 12, 255, 266, 120, 131, STR_0225, STR_NULL},
|
||||
{ WWT_PANEL, RESIZE_NONE, 12, 279, 314, 120, 131, STR_NULL, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 12, 315, 326, 120, 131, STR_0225, STR_NULL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 12, 315, 326, 120, 131, STR_0225, STR_NULL},
|
||||
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 12, 10, 167, 138, 149, STR_SINGLE_PLAYER, STR_02FF_SELECT_SINGLE_PLAYER_GAME},
|
||||
{ WWT_PUSHTXTBTN, RESIZE_NONE, 12, 168, 325, 138, 149, STR_MULTIPLAYER, STR_0300_SELECT_MULTIPLAYER_GAME},
|
||||
@@ -88,11 +85,11 @@ static void SelectGameWndProc(Window *w, WindowEvent *e)
|
||||
case 15:
|
||||
#ifdef ENABLE_NETWORK
|
||||
if (!_network_available) {
|
||||
ShowErrorMessage(-1, STR_NETWORK_ERR_NOTAVAILABLE, 0, 0);
|
||||
ShowErrorMessage(INVALID_STRING_ID, STR_NETWORK_ERR_NOTAVAILABLE, 0, 0);
|
||||
} else
|
||||
ShowNetworkGameWindow();
|
||||
#else
|
||||
ShowErrorMessage(-1 ,STR_NETWORK_ERR_NOTAVAILABLE, 0, 0);
|
||||
ShowErrorMessage(INVALID_STRING_ID ,STR_NETWORK_ERR_NOTAVAILABLE, 0, 0);
|
||||
#endif
|
||||
break;
|
||||
case 16: ShowGameOptions(); break;
|
||||
@@ -107,8 +104,8 @@ static void SelectGameWndProc(Window *w, WindowEvent *e)
|
||||
|
||||
case WE_DROPDOWN_SELECT: /* Mapsize selection */
|
||||
switch (e->dropdown.button) {
|
||||
case 11: _patches.map_x = e->dropdown.index + 6; break;
|
||||
case 13: _patches.map_y = e->dropdown.index + 6; break;
|
||||
case 11: _patches.map_x = e->dropdown.index + 6; break;
|
||||
case 13: _patches.map_y = e->dropdown.index + 6; break;
|
||||
}
|
||||
SetWindowDirty(w);
|
||||
break;
|
||||
@@ -146,7 +143,7 @@ void StartScenarioEditor(uint32 rnd1, uint32 rnd2)
|
||||
}
|
||||
|
||||
static const Widget _ask_abandon_game_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 4, 0, 10, 0, 13, STR_00C5, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 4, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 4, 11, 179, 0, 13, STR_00C7_QUIT, STR_NULL},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 4, 0, 179, 14, 91, 0x0, STR_NULL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 12, 25, 84, 72, 83, STR_00C9_NO, STR_NULL},
|
||||
@@ -154,8 +151,9 @@ static const Widget _ask_abandon_game_widgets[] = {
|
||||
{ WIDGETS_END },
|
||||
};
|
||||
|
||||
static void AskAbandonGameWndProc(Window *w, WindowEvent *e) {
|
||||
switch(e->event) {
|
||||
static void AskAbandonGameWndProc(Window* w, WindowEvent* e)
|
||||
{
|
||||
switch (e->event) {
|
||||
case WE_PAINT:
|
||||
DrawWindowWidgets(w);
|
||||
#if defined(_WIN32)
|
||||
@@ -173,22 +171,23 @@ static void AskAbandonGameWndProc(Window *w, WindowEvent *e) {
|
||||
#else
|
||||
SetDParam(0, STR_0134_UNIX);
|
||||
#endif
|
||||
DrawStringMultiCenter(0x5A, 0x26, STR_00CA_ARE_YOU_SURE_YOU_WANT_TO, 178);
|
||||
DrawStringMultiCenter(90, 38, STR_00CA_ARE_YOU_SURE_YOU_WANT_TO, 178);
|
||||
return;
|
||||
|
||||
case WE_CLICK:
|
||||
switch(e->click.widget) {
|
||||
case 3:
|
||||
DeleteWindow(w);
|
||||
break;
|
||||
case 4:
|
||||
_exit_game = true;
|
||||
break;
|
||||
switch (e->click.widget) {
|
||||
case 3: DeleteWindow(w); break;
|
||||
case 4: _exit_game = true; break;
|
||||
}
|
||||
break;
|
||||
|
||||
case WE_KEYPRESS: /* Exit game on pressing 'Enter' */
|
||||
if (e->keypress.keycode == WKC_RETURN || e->keypress.keycode == WKC_NUM_ENTER)
|
||||
_exit_game = true;
|
||||
switch (e->keypress.keycode) {
|
||||
case WKC_RETURN:
|
||||
case WKC_NUM_ENTER:
|
||||
_exit_game = true;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -208,7 +207,7 @@ void AskExitGame(void)
|
||||
|
||||
|
||||
static const Widget _ask_quit_game_widgets[] = {
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 4, 0, 10, 0, 13, STR_00C5, STR_NULL},
|
||||
{ WWT_CLOSEBOX, RESIZE_NONE, 4, 0, 10, 0, 13, STR_00C5, STR_018B_CLOSE_WINDOW},
|
||||
{ WWT_CAPTION, RESIZE_NONE, 4, 11, 179, 0, 13, STR_0161_QUIT_GAME, STR_NULL},
|
||||
{ WWT_IMGBTN, RESIZE_NONE, 4, 0, 179, 14, 91, 0x0, STR_NULL},
|
||||
{ WWT_TEXTBTN, RESIZE_NONE, 12, 25, 84, 72, 83, STR_00C9_NO, STR_NULL},
|
||||
@@ -216,32 +215,29 @@ static const Widget _ask_quit_game_widgets[] = {
|
||||
{ WIDGETS_END },
|
||||
};
|
||||
|
||||
static void AskQuitGameWndProc(Window *w, WindowEvent *e) {
|
||||
switch(e->event) {
|
||||
case WE_PAINT:
|
||||
DrawWindowWidgets(w);
|
||||
DrawStringMultiCenter(0x5A, 0x26,
|
||||
_game_mode != GM_EDITOR ? STR_0160_ARE_YOU_SURE_YOU_WANT_TO :
|
||||
STR_029B_ARE_YOU_SURE_YOU_WANT_TO,
|
||||
178);
|
||||
return;
|
||||
|
||||
case WE_CLICK:
|
||||
switch(e->click.widget) {
|
||||
case 3:
|
||||
DeleteWindow(w);
|
||||
static void AskQuitGameWndProc(Window* w, WindowEvent* e)
|
||||
{
|
||||
switch (e->event) {
|
||||
case WE_PAINT:
|
||||
DrawWindowWidgets(w);
|
||||
DrawStringMultiCenter(
|
||||
90, 38,
|
||||
_game_mode != GM_EDITOR ?
|
||||
STR_0160_ARE_YOU_SURE_YOU_WANT_TO : STR_029B_ARE_YOU_SURE_YOU_WANT_TO,
|
||||
178
|
||||
);
|
||||
break;
|
||||
case 4:
|
||||
_switch_mode = SM_MENU;
|
||||
|
||||
case WE_CLICK:
|
||||
switch (e->click.widget) {
|
||||
case 3: DeleteWindow(w); break;
|
||||
case 4: _switch_mode = SM_MENU; break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case WE_KEYPRESS: /* Return to main menu on pressing 'Enter' */
|
||||
if (e->keypress.keycode == WKC_RETURN)
|
||||
_switch_mode = SM_MENU;
|
||||
break;
|
||||
|
||||
case WE_KEYPRESS: /* Return to main menu on pressing 'Enter' */
|
||||
if (e->keypress.keycode == WKC_RETURN) _switch_mode = SM_MENU;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+53
-23
@@ -11,49 +11,83 @@ go to: http://www.tt-forums.net/viewtopic.php?t=9576
|
||||
Of course if you have more knowledge about any of these bugs, have more
|
||||
specifics, we welcome you to report them. React to the given bug indicated
|
||||
by the number below on http://sourceforge.net/tracker/?group_id=103924&atid=636365
|
||||
or http://bugs.openttd.org.
|
||||
If the the bug report is closed, it has been fixed, which then can be verified
|
||||
in the latest SVN version.
|
||||
|
||||
Bugs for 0.4.0.1
|
||||
Bugs for 0.4.5
|
||||
------------------------------------------------------------------------
|
||||
URL: http://bugs.openttd.org
|
||||
|
||||
-20 Saving files when run from gdb
|
||||
-45 NORETURN wrongly declared for gcc
|
||||
-46 Some if, for, switch and while have no space before (
|
||||
-47 rating calculation and cargo loading priority
|
||||
-9 [MorphOS] write to NULL when going to device root in filerequester
|
||||
-8 [MorphOS] game crashes if no TCP/IP stack is loaded
|
||||
|
||||
------------------------------------------------------------------------
|
||||
URL: http://sourceforge.net/tracker/?atid=636365&group_id=103924&func=browse
|
||||
|
||||
- Minimap crash with certain views and certain resolutions
|
||||
- "Broken" autoreplace for dual-headed trains
|
||||
-1203319 Pre-signal exits not working when one way signal
|
||||
-1417453 Makefile and Variables issue
|
||||
-1415782 crash in string code with openbsd/zaurus
|
||||
-1397638 Economics bug?
|
||||
-1395628 Trackpad panning/scrolling broken
|
||||
-1394799 Dual headed engines disagreement
|
||||
-1393415 NPF & one-way sigs
|
||||
-1393411 "Void Order" reporting.
|
||||
-1390260 Mis-reporting of Plane Crash
|
||||
-1389999 Child windows not sticking
|
||||
-1389986 Shares problem (nightly 3330)
|
||||
-1380497 problems with competitors during multiplayer
|
||||
-1372772 Train gets lost between two stations
|
||||
-1366446 different names for patches
|
||||
-1362784 Incorrect vehicule profit calcul with inflation on
|
||||
-1299162 Music volume too low
|
||||
-1288024 Strange string on OTTD initial screen
|
||||
-1250094 Towns Shrink when center tile is built on
|
||||
-1244842 Multiplayer interface bug (0.4.0.1)
|
||||
-1212267 station visited twice when servicing
|
||||
-1211764 AI companies behave weird on the stock market
|
||||
-1208170 Duplicate station names can be created
|
||||
-1197116 Some stations are cargo-less
|
||||
-1188897 Station with cargo enroute_from INVALID_STATION
|
||||
-1186802 Company value problem (loans)
|
||||
-1181888 Invaild Station Order => Crash
|
||||
-1174829 Waypoint / Orders Bug
|
||||
-1168820 Some mouse and keyboard events are lost
|
||||
-1167810 Cargo payment after deleting stations (st->xy = 0)
|
||||
-1157244 Can't save game if name contains german umlauts
|
||||
-1144510 Make install tries to install scenarios to the wrong place
|
||||
-1116638 "More, but smaller changes" deficiency
|
||||
-1106356 re-offered prototypes
|
||||
-1099233 production down before it's working
|
||||
-1085486 Subsidies: Only count when station is in right suburb
|
||||
-992677 BeOS MIDI does not initialise on newer BeOS releases
|
||||
|
||||
Minor Bugs for 0.4.0.1
|
||||
Minor Bugs for 0.4.5
|
||||
------------------------------------------------------------------------
|
||||
URL: http://sourceforge.net/tracker/?atid=669662&group_id=103924&func=browse
|
||||
|
||||
-1412033 autoreplace not possible on monorail/maglev trains
|
||||
-1412031 fast forward scrolling is also fast forward :)
|
||||
-1395489 Nightly 3358 Linux Driver warnings
|
||||
-1394316 Multistop traffic jam
|
||||
-1394231 Autorenew glitch on helicopters
|
||||
-1387424 overtake insolvent company is to cheap
|
||||
-1382782 Loan interest calculated 'wrong'
|
||||
-1372891 Performance loss with NTP & NPF
|
||||
-1342383 Last built rail type not cleared when starting new game
|
||||
-1296259 Autosave override for multiplayer games
|
||||
-1254226 giant screenshot crashes multiplayer
|
||||
-1242753 Town population minus 10
|
||||
-1236320 Bug in main menu allows moving screen
|
||||
-1201284 permanent hilight in a depot
|
||||
-1197258 Window Z-order locked when exiting openttd
|
||||
-1193882 problems with dualhead engins in DB Set XL (v0.81)
|
||||
-1193870 keep the date counter running
|
||||
-1185852 Scrollbars get arbitrarily small
|
||||
-1184634 Replace vehicles window bug
|
||||
-1183253 Incorrect Load vs Loading Sprites
|
||||
-1183251 Hangar sprite does not update when refit.
|
||||
-1179933 autorail removal does not go completely red.
|
||||
-1160732 little bug with transparency
|
||||
-1153937 Game wont run from a start menu shortcut
|
||||
-1117731 Editor-StartingDate
|
||||
-1114237 Wrong autoreplace hint
|
||||
-1112784 detailed sound options
|
||||
-1108046 game freezes
|
||||
-1106889 Chat Interface enhancements
|
||||
-1104358 train lost message - history
|
||||
@@ -63,13 +97,9 @@ URL: http://sourceforge.net/tracker/?atid=669662&group_id=103924&func=browse
|
||||
-1034310 color mauve in diagrams
|
||||
-1030661 It's possible to build a tunnel under oil wells
|
||||
-1009171 Canals and locks at sea level cause flooding
|
||||
-993516 Canal + bouy -> wrong graphics.
|
||||
-987891 Large UFO destruction bug
|
||||
-987884 farm fences
|
||||
-987883 Aircraft landing/taking off
|
||||
-987880 company league table updating
|
||||
-985924 aircraft taxi speed
|
||||
-980276 Overflow in factory directory
|
||||
-976824 transmitter base
|
||||
-941694 Clipping problems stations/vehicles on slopes
|
||||
-936997 Stationname too long to fit in trainwindow bug
|
||||
-0993516 Canal + bouy -> wrong graphics.
|
||||
-0987891 Large UFO destruction bug
|
||||
-0987883 Aircraft landing/taking off
|
||||
-0987880 company league table updating
|
||||
-0985924 aircraft taxi speed
|
||||
-0941694 Clipping problems stations/vehicles on slopes
|
||||
|
||||
+74
-65
@@ -1,14 +1,18 @@
|
||||
/* $Id$ */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ttd.h"
|
||||
#include "openttd.h"
|
||||
#include "functions.h"
|
||||
#include "map.h"
|
||||
#include "player.h"
|
||||
#include "spritecache.h"
|
||||
#include "table/sprites.h"
|
||||
#include "tile.h"
|
||||
#include <stdarg.h>
|
||||
#include "gfx.h"
|
||||
#include "viewport.h"
|
||||
#include "command.h"
|
||||
#include "vehicle.h"
|
||||
#include "variables.h"
|
||||
|
||||
extern const TileTypeProcs
|
||||
_tile_type_clear_procs,
|
||||
@@ -43,13 +47,17 @@ const byte _tileh_to_sprite[32] = {
|
||||
0,0,0,0,0,0,0,16,0,0,0,17,0,15,18,0,
|
||||
};
|
||||
|
||||
const byte _inclined_tileh[] = {
|
||||
3, 9, 3, 6, 12, 6, 12, 9
|
||||
};
|
||||
|
||||
|
||||
void FindLandscapeHeightByTile(TileInfo *ti, TileIndex tile)
|
||||
{
|
||||
assert(tile < MapSize());
|
||||
|
||||
ti->tile = tile;
|
||||
ti->map5 = _map5[tile];
|
||||
ti->map5 = _m[tile].m5;
|
||||
ti->type = GetTileType(tile);
|
||||
ti->tileh = GetTileSlope(tile, &ti->z);
|
||||
}
|
||||
@@ -69,7 +77,7 @@ void FindLandscapeHeight(TileInfo *ti, uint x, uint y)
|
||||
return;
|
||||
}
|
||||
|
||||
FindLandscapeHeightByTile(ti, TILE_FROM_XY(x,y));
|
||||
FindLandscapeHeightByTile(ti, TileVirtXY(x, y));
|
||||
}
|
||||
|
||||
uint GetPartialZ(int x, int y, int corners)
|
||||
@@ -178,21 +186,21 @@ uint GetSlopeZ(int x, int y)
|
||||
|
||||
// direction=true: check for foundation in east and south corner
|
||||
// direction=false: check for foundation in west and south corner
|
||||
static bool hasFoundation(TileInfo *ti, bool direction)
|
||||
static bool hasFoundation(const TileInfo* ti, bool direction)
|
||||
{
|
||||
bool south, other; // southern corner and east/west corner
|
||||
uint slope = _tile_type_procs[ti->type]->get_slope_tileh_proc(ti);
|
||||
uint tileh = ti->tileh;
|
||||
|
||||
if(slope==0 && slope!=tileh) tileh=15;
|
||||
if (slope == 0 && slope != tileh) tileh = 15;
|
||||
south = (tileh & 2) != (slope & 2);
|
||||
|
||||
if(direction)
|
||||
if (direction) {
|
||||
other = (tileh & 4) != (slope & 4);
|
||||
else
|
||||
} else {
|
||||
other = (tileh & 1) != (slope & 1);
|
||||
}
|
||||
return south || other;
|
||||
|
||||
}
|
||||
|
||||
void DrawFoundation(TileInfo *ti, uint f)
|
||||
@@ -200,16 +208,16 @@ void DrawFoundation(TileInfo *ti, uint f)
|
||||
uint32 sprite_base = SPR_SLOPES_BASE-14;
|
||||
|
||||
TileInfo ti2;
|
||||
FindLandscapeHeight(&ti2, ti->x, ti->y-1);
|
||||
if(hasFoundation( &ti2, true )) sprite_base += 22; // foundation in NW direction
|
||||
FindLandscapeHeight(&ti2, ti->x-1, ti->y);
|
||||
if(hasFoundation( &ti2, false )) sprite_base += 22*2; // foundation in NE direction
|
||||
FindLandscapeHeight(&ti2, ti->x, ti->y - 1);
|
||||
if (hasFoundation(&ti2, true)) sprite_base += 22; // foundation in NW direction
|
||||
FindLandscapeHeight(&ti2, ti->x - 1, ti->y);
|
||||
if (hasFoundation(&ti2, false)) sprite_base += 22 * 2; // foundation in NE direction
|
||||
|
||||
if (f < 15) {
|
||||
// leveled foundation
|
||||
if( sprite_base < SPR_SLOPES_BASE ) sprite_base = 990; // use original slope sprites
|
||||
if (sprite_base < SPR_SLOPES_BASE) sprite_base = SPR_FOUNDATION_BASE + 1; // use original slope sprites
|
||||
|
||||
AddSortableSpriteToDraw(f-1 + sprite_base, ti->x, ti->y, 16, 16, 7, ti->z);
|
||||
AddSortableSpriteToDraw(f - 1 + sprite_base, ti->x, ti->y, 16, 16, 7, ti->z);
|
||||
ti->z += 8;
|
||||
ti->tileh = 0;
|
||||
OffsetGroundSprite(31, 1);
|
||||
@@ -218,7 +226,7 @@ void DrawFoundation(TileInfo *ti, uint f)
|
||||
sprite_base += 14;
|
||||
|
||||
AddSortableSpriteToDraw(
|
||||
HASBIT( (1<<1) | (1<<2) | (1<<4) | (1<<8), ti->tileh) ? sprite_base + (f - 15) : ti->tileh + 0x3DE - 1,
|
||||
HASBIT((1<<1) | (1<<2) | (1<<4) | (1<<8), ti->tileh) ? sprite_base + (f - 15) : SPR_FOUNDATION_BASE + ti->tileh,
|
||||
ti->x, ti->y, 1, 1, 1, ti->z
|
||||
);
|
||||
|
||||
@@ -280,7 +288,7 @@ void GetTileDesc(TileIndex tile, TileDesc *td)
|
||||
*/
|
||||
int32 CmdLandscapeClear(int x, int y, uint32 flags, uint32 p1, uint32 p2)
|
||||
{
|
||||
TileIndex tile = TILE_FROM_XY(x, y);
|
||||
TileIndex tile = TileVirtXY(x, y);
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION);
|
||||
|
||||
@@ -299,7 +307,7 @@ int32 CmdClearArea(int ex, int ey, uint32 flags, uint32 p1, uint32 p2)
|
||||
int x,y;
|
||||
bool success = false;
|
||||
|
||||
if (p1 > MapSize()) return CMD_ERROR;
|
||||
if (p1 >= MapSize()) return CMD_ERROR;
|
||||
|
||||
SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION);
|
||||
|
||||
@@ -314,7 +322,7 @@ int32 CmdClearArea(int ex, int ey, uint32 flags, uint32 p1, uint32 p2)
|
||||
|
||||
for (x = sx; x <= ex; x += 16) {
|
||||
for (y = sy; y <= ey; y += 16) {
|
||||
ret = DoCommandByTile(TILE_FROM_XY(x,y), 0, 0, flags &~DC_EXEC, CMD_LANDSCAPE_CLEAR);
|
||||
ret = DoCommandByTile(TileVirtXY(x, y), 0, 0, flags & ~DC_EXEC, CMD_LANDSCAPE_CLEAR);
|
||||
if (CmdFailed(ret)) continue;
|
||||
cost += ret;
|
||||
success = true;
|
||||
@@ -324,7 +332,7 @@ int32 CmdClearArea(int ex, int ey, uint32 flags, uint32 p1, uint32 p2)
|
||||
_additional_cash_required = ret;
|
||||
return cost - ret;
|
||||
}
|
||||
DoCommandByTile(TILE_FROM_XY(x,y), 0, 0, flags, CMD_LANDSCAPE_CLEAR);
|
||||
DoCommandByTile(TileVirtXY(x, y), 0, 0, flags, CMD_LANDSCAPE_CLEAR);
|
||||
|
||||
// draw explosion animation...
|
||||
if ((x == sx || x == ex) && (y == sy || y == ey)) {
|
||||
@@ -349,36 +357,36 @@ void CDECL ModifyTile(TileIndex tile, uint flags, ...)
|
||||
|
||||
va_start(va, flags);
|
||||
|
||||
if ((i = (flags >> 8) & 0xF) != 0) {
|
||||
if ((i = GB(flags, 8, 4)) != 0) {
|
||||
SetTileType(tile, i - 1);
|
||||
}
|
||||
|
||||
if (flags & (MP_MAP2_CLEAR | MP_MAP2)) {
|
||||
int x = 0;
|
||||
if (flags & MP_MAP2) x = va_arg(va, int);
|
||||
_map2[tile] = x;
|
||||
_m[tile].m2 = x;
|
||||
}
|
||||
|
||||
if (flags & (MP_MAP3LO_CLEAR | MP_MAP3LO)) {
|
||||
int x = 0;
|
||||
if (flags & MP_MAP3LO) x = va_arg(va, int);
|
||||
_map3_lo[tile] = x;
|
||||
_m[tile].m3 = x;
|
||||
}
|
||||
|
||||
if (flags & (MP_MAP3HI_CLEAR | MP_MAP3HI)) {
|
||||
int x = 0;
|
||||
if (flags & MP_MAP3HI) x = va_arg(va, int);
|
||||
_map3_hi[tile] = x;
|
||||
_m[tile].m4 = x;
|
||||
}
|
||||
|
||||
if (flags & (MP_MAPOWNER|MP_MAPOWNER_CURRENT)) {
|
||||
byte x = _current_player;
|
||||
PlayerID x = _current_player;
|
||||
if (flags & MP_MAPOWNER) x = va_arg(va, int);
|
||||
_map_owner[tile] = x;
|
||||
_m[tile].m1 = x;
|
||||
}
|
||||
|
||||
if (flags & MP_MAP5) {
|
||||
_map5[tile] = va_arg(va, int);
|
||||
_m[tile].m5 = va_arg(va, int);
|
||||
}
|
||||
|
||||
va_end(va);
|
||||
@@ -408,7 +416,7 @@ void RunTileLoop(void)
|
||||
if (TileX(tile) < MapSizeX() - TILELOOP_SIZE) {
|
||||
tile += TILELOOP_SIZE; /* no overflow */
|
||||
} else {
|
||||
tile = TILE_MASK(tile - TILELOOP_SIZE * (MapSizeX() / TILELOOP_SIZE-1) + TILE_XY(0, TILELOOP_SIZE)); /* x would overflow, also increase y */
|
||||
tile = TILE_MASK(tile - TILELOOP_SIZE * (MapSizeX() / TILELOOP_SIZE - 1) + TileDiffXY(0, TILELOOP_SIZE)); /* x would overflow, also increase y */
|
||||
}
|
||||
} while (--count);
|
||||
assert( (tile & ~TILELOOP_ASSERTMASK) == 0);
|
||||
@@ -419,21 +427,22 @@ void RunTileLoop(void)
|
||||
_cur_tileloop_tile = tile;
|
||||
}
|
||||
|
||||
void InitializeLandscape(uint log_x, uint log_y)
|
||||
void InitializeLandscape(void)
|
||||
{
|
||||
uint map_size;
|
||||
uint i;
|
||||
|
||||
InitMap(log_x, log_y);
|
||||
map_size = MapSize();
|
||||
|
||||
memset(_map_type_and_height, MP_CLEAR << 4, map_size);
|
||||
memset(_map_owner, OWNER_NONE, map_size);
|
||||
memset(_map2, 0, map_size * sizeof(_map2[0]));
|
||||
memset(_map3_lo, 0, map_size);
|
||||
memset(_map3_hi, 0, map_size);
|
||||
memset(_map5, 3, map_size);
|
||||
memset(_map_extra_bits, 0, map_size / 4);
|
||||
map_size = MapSize();
|
||||
for (i = 0; i < map_size; i++) {
|
||||
_m[i].type_height = MP_CLEAR << 4;
|
||||
_m[i].m1 = OWNER_NONE;
|
||||
_m[i].m2 = 0;
|
||||
_m[i].m3 = 0;
|
||||
_m[i].m4 = 0;
|
||||
_m[i].m5 = 3;
|
||||
_m[i].extra = 0;
|
||||
}
|
||||
|
||||
// create void tiles at the border
|
||||
for (i = 0; i < MapMaxY(); ++i)
|
||||
@@ -450,8 +459,8 @@ void ConvertGroundTilesIntoWaterTiles(void)
|
||||
for (tile = 0; tile < MapSize(); ++tile) {
|
||||
if (IsTileType(tile, MP_CLEAR) && GetTileSlope(tile, &h) == 0 && h == 0) {
|
||||
SetTileType(tile, MP_WATER);
|
||||
_map5[tile] = 0;
|
||||
_map_owner[tile] = OWNER_WATER;
|
||||
_m[tile].m5 = 0;
|
||||
SetTileOwner(tile, OWNER_WATER);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -468,7 +477,7 @@ static void GenerateTerrain(int type, int flag)
|
||||
uint h;
|
||||
const Sprite* template;
|
||||
const byte *p;
|
||||
byte *tile;
|
||||
Tile* tile;
|
||||
byte direction;
|
||||
|
||||
r = Random();
|
||||
@@ -481,7 +490,7 @@ static void GenerateTerrain(int type, int flag)
|
||||
if (x < 2 || y < 2)
|
||||
return;
|
||||
|
||||
direction = (r >> 22) & 3;
|
||||
direction = GB(r, 22, 2);
|
||||
if (direction & 1) {
|
||||
w = template->height;
|
||||
h = template->width;
|
||||
@@ -521,62 +530,62 @@ static void GenerateTerrain(int type, int flag)
|
||||
if (y + h >= MapMaxY() - 1)
|
||||
return;
|
||||
|
||||
tile = &_map_type_and_height[TILE_XY(x, y)];
|
||||
tile = &_m[TileXY(x, y)];
|
||||
|
||||
switch (direction) {
|
||||
case 0:
|
||||
do {
|
||||
byte *tile_cur = tile;
|
||||
Tile* tile_cur = tile;
|
||||
uint w_cur;
|
||||
|
||||
for (w_cur = w; w_cur != 0; --w_cur) {
|
||||
if (*p >= *tile_cur) *tile_cur = *p;
|
||||
if (*p >= tile_cur->type_height) tile_cur->type_height = *p;
|
||||
p++;
|
||||
tile_cur++;
|
||||
}
|
||||
tile += TILE_XY(0, 1);
|
||||
tile += TileDiffXY(0, 1);
|
||||
} while (--h != 0);
|
||||
break;
|
||||
|
||||
case 1:
|
||||
do {
|
||||
byte *tile_cur = tile;
|
||||
Tile* tile_cur = tile;
|
||||
uint h_cur;
|
||||
|
||||
for (h_cur = h; h_cur != 0; --h_cur) {
|
||||
if (*p >= *tile_cur) *tile_cur = *p;
|
||||
if (*p >= tile_cur->type_height) tile_cur->type_height = *p;
|
||||
p++;
|
||||
tile_cur += TILE_XY(0, 1);
|
||||
tile_cur += TileDiffXY(0, 1);
|
||||
}
|
||||
tile++;
|
||||
} while (--w != 0);
|
||||
break;
|
||||
|
||||
case 2:
|
||||
tile += TILE_XY(w - 1, 0);
|
||||
tile += TileDiffXY(w - 1, 0);
|
||||
do {
|
||||
byte *tile_cur = tile;
|
||||
Tile* tile_cur = tile;
|
||||
uint w_cur;
|
||||
|
||||
for (w_cur = w; w_cur != 0; --w_cur) {
|
||||
if (*p >= *tile_cur) *tile_cur = *p;
|
||||
if (*p >= tile_cur->type_height) tile_cur->type_height = *p;
|
||||
p++;
|
||||
tile_cur--;
|
||||
}
|
||||
tile += TILE_XY(0, 1);
|
||||
tile += TileDiffXY(0, 1);
|
||||
} while (--h != 0);
|
||||
break;
|
||||
|
||||
case 3:
|
||||
tile += TILE_XY(0, h - 1);
|
||||
tile += TileDiffXY(0, h - 1);
|
||||
do {
|
||||
byte *tile_cur = tile;
|
||||
Tile* tile_cur = tile;
|
||||
uint h_cur;
|
||||
|
||||
for (h_cur = h; h_cur != 0; --h_cur) {
|
||||
if (*p >= *tile_cur) *tile_cur = *p;
|
||||
if (*p >= tile_cur->type_height) tile_cur->type_height = *p;
|
||||
p++;
|
||||
tile_cur -= TILE_XY(0, 1);
|
||||
tile_cur -= TileDiffXY(0, 1);
|
||||
}
|
||||
tile++;
|
||||
} while (--w != 0);
|
||||
@@ -610,7 +619,7 @@ static void CreateDesertOrRainForest(void)
|
||||
for (data = _make_desert_or_rainforest_data;
|
||||
data != endof(_make_desert_or_rainforest_data); ++data) {
|
||||
TileIndex t = TILE_MASK(tile + ToTileIndexDiff(*data));
|
||||
if (IsTileType(t, MP_CLEAR) && (_map5[t] & 0x1c) == 0x14) break;
|
||||
if (IsTileType(t, MP_CLEAR) && (_m[t].m5 & 0x1c) == 0x14) break;
|
||||
}
|
||||
if (data == endof(_make_desert_or_rainforest_data))
|
||||
SetMapExtraBits(tile, 2);
|
||||
@@ -628,16 +637,16 @@ void GenerateLandscape(void)
|
||||
GenerateTerrain(2, 0);
|
||||
|
||||
r = Random();
|
||||
flag = (r & 3) | 4;
|
||||
for (i = ScaleByMapSize(((r >> 16) & 0x7F) + 450); i != 0; --i)
|
||||
flag = GB(r, 0, 2) | 4;
|
||||
for (i = ScaleByMapSize(GB(r, 16, 7) + 450); i != 0; --i)
|
||||
GenerateTerrain(4, flag);
|
||||
} else if (_opt.landscape == LT_DESERT) {
|
||||
for (i = ScaleByMapSize((Random()&0x7F) + 170); i != 0; --i)
|
||||
GenerateTerrain(0, 0);
|
||||
|
||||
r = Random();
|
||||
flag = (r & 3) | 4;
|
||||
for (i = ScaleByMapSize(((r >> 16) & 0xFF) + 1700); i != 0; --i)
|
||||
flag = GB(r, 0, 2) | 4;
|
||||
for (i = ScaleByMapSize(GB(r, 16, 8) + 1700); i != 0; --i)
|
||||
GenerateTerrain(0, flag);
|
||||
|
||||
flag ^= 2;
|
||||
@@ -680,9 +689,9 @@ TileIndex AdjustTileCoordRandomly(TileIndex a, byte rng)
|
||||
int rn = rng;
|
||||
uint32 r = Random();
|
||||
|
||||
return TILE_MASK(TILE_XY(
|
||||
TileX(a) + ((byte)r * rn * 2 >> 8) - rn,
|
||||
TileY(a) + ((byte)(r >> 8) * rn * 2 >> 8) - rn
|
||||
return TILE_MASK(TileXY(
|
||||
TileX(a) + (GB(r, 0, 8) * rn * 2 >> 8) - rn,
|
||||
TileY(a) + (GB(r, 8, 8) * rn * 2 >> 8) - rn
|
||||
));
|
||||
}
|
||||
|
||||
|
||||
+342
-369
File diff suppressed because it is too large
Load Diff
+338
-382
File diff suppressed because it is too large
Load Diff
+333
-378
File diff suppressed because it is too large
Load Diff
+975
-961
File diff suppressed because it is too large
Load Diff
+368
-396
File diff suppressed because it is too large
Load Diff
+349
-376
File diff suppressed because it is too large
Load Diff
+473
-500
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
+506
-534
File diff suppressed because it is too large
Load Diff
+667
-693
File diff suppressed because it is too large
Load Diff
+297
-371
File diff suppressed because it is too large
Load Diff
+455
-481
File diff suppressed because it is too large
Load Diff
+455
-380
File diff suppressed because it is too large
Load Diff
+329
-375
File diff suppressed because it is too large
Load Diff
+375
-402
File diff suppressed because it is too large
Load Diff
+319
-367
File diff suppressed because it is too large
Load Diff
+438
-465
File diff suppressed because it is too large
Load Diff
+326
-371
File diff suppressed because it is too large
Load Diff
+324
-370
File diff suppressed because it is too large
Load Diff
+334
-373
File diff suppressed because it is too large
Load Diff
+325
-369
File diff suppressed because it is too large
Load Diff
+371
-398
File diff suppressed because it is too large
Load Diff
+2406
-2431
File diff suppressed because it is too large
Load Diff
+18
-30
@@ -1,32 +1,21 @@
|
||||
##name Frisian
|
||||
##ownname Frysk
|
||||
##isocode fy
|
||||
##plural 0
|
||||
|
||||
##id 0x0000
|
||||
STR_NULL :
|
||||
STR_0001_OFF_EDGE_OF_MAP :{WHITE}Off edge of map
|
||||
STR_0002_TOO_CLOSE_TO_EDGE_OF_MAP :{WHITE}Too close to edge of map
|
||||
STR_0003_NOT_ENOUGH_CASH_REQUIRES :{WHITE}Not enough cash - requires {CURRENCY}
|
||||
STR_0004 :{WHITE}{CURRENCY64}
|
||||
STR_0005 :{RED}{CURRENCY64}
|
||||
STR_EMPTY :
|
||||
STR_0007_FLAT_LAND_REQUIRED :{WHITE}Flat land required
|
||||
STR_0008_WAITING :{BLACK}Waiting: {WHITE}{STRING}
|
||||
STR_0009 :{WHITE}{STRING}
|
||||
STR_000A_EN_ROUTE_FROM :{WHITE}{STRING}{YELLOW} (en-route from
|
||||
STR_000B :{YELLOW}{STATION})
|
||||
STR_000C_ACCEPTS :{BLACK}Accepts: {WHITE}
|
||||
STR_000D_ACCEPTS :{BLACK}Accepts: {GOLD}
|
||||
STR_000E :
|
||||
STR_000F_PASSENGERS :Passengers
|
||||
STR_0010_COAL :Coal
|
||||
STR_0011_MAIL :Post
|
||||
STR_0012_OIL :Oalje
|
||||
STR_0013_LIVESTOCK :Livestock
|
||||
STR_0014_GOODS :Guod
|
||||
STR_0015_GRAIN :Graan
|
||||
STR_0016_WOOD :Hout
|
||||
STR_0017_IRON_ORE :Iron Ore
|
||||
STR_0018_STEEL :Stiel
|
||||
STR_0019_VALUABLES :Kostbere spullen
|
||||
STR_001A_COPPER_ORE :Koper erts
|
||||
@@ -50,7 +39,6 @@ STR_002B_BATTERIES :Batterijen
|
||||
STR_002C_PLASTIC :Plestik
|
||||
STR_002E :
|
||||
STR_002F_PASSENGER :Passazjier
|
||||
STR_0030_COAL :Coal
|
||||
STR_0031_MAIL :Post
|
||||
STR_0032_OIL :Oalje
|
||||
STR_0033_LIVESTOCK :Fee
|
||||
@@ -76,21 +64,21 @@ STR_0047_COLA :Cola
|
||||
STR_004A_TOFFEE :Toffee
|
||||
STR_004B_BATTERY :Batterij
|
||||
STR_004C_PLASTIC :Plestik
|
||||
STR_004E :
|
||||
STR_004F_PASSENGER :{COMMA16} passazjier
|
||||
STR_0050_TON_OF_COAL :{COMMA16} ton coal
|
||||
STR_0051_BAG_OF_MAIL :{COMMA16} tassen mei post
|
||||
STR_0052_OF_OIL :{VOLUME} oalje
|
||||
STR_0055_TON_OF_GRAIN :{COMMA16} ton graan
|
||||
STR_0056_TON_OF_WOOD :{COMMA16} ton hout
|
||||
STR_0058_TON_OF_STEEL :{COMMA16} ton stiel
|
||||
STR_0059_BAG_OF_VALUABLES :{COMMA16} tas kostber guod
|
||||
STR_005B_TON_OF_MAIZE :{COMMA16} ton mais
|
||||
STR_005C_TON_OF_FRUIT :{COMMA16} ton fruit
|
||||
STR_005E_TON_OF_FOOD :{COMMA16} ton iten
|
||||
STR_005F_TON_OF_PAPER :{COMMA16} ton papier
|
||||
STR_0060_BAG_OF_GOLD :{COMMA16} tas goud
|
||||
STR_0061_OF_WATER :{VOLUME} wetter
|
||||
STR_QUANTITY_NOTHING :
|
||||
STR_QUANTITY_PASSENGERS :{COMMA} passazjier
|
||||
STR_QUANTITY_COAL :{COMMA} ton coal
|
||||
STR_QUANTITY_MAIL :{COMMA} tassen mei post
|
||||
STR_QUANTITY_OIL :{VOLUME} oalje
|
||||
STR_QUANTITY_GRAIN :{COMMA} ton graan
|
||||
STR_QUANTITY_WOOD :{COMMA} ton hout
|
||||
STR_QUANTITY_STEEL :{COMMA} ton stiel
|
||||
STR_QUANTITY_VALUABLES :{COMMA} tas kostber guod
|
||||
STR_QUANTITY_MAIZE :{COMMA} ton mais
|
||||
STR_QUANTITY_FRUIT :{COMMA} ton fruit
|
||||
STR_QUANTITY_FOOD :{COMMA} ton iten
|
||||
STR_QUANTITY_PAPER :{COMMA} ton papier
|
||||
STR_QUANTITY_GOLD :{COMMA} tas goud
|
||||
STR_QUANTITY_WATER :{VOLUME} wetter
|
||||
STR_00B2_MESSAGE :{YELLOW}Bericht
|
||||
STR_00B3_MESSAGE_FROM :{YELLOW}Bericht fan {STRING}
|
||||
STR_00B7_VERSION :{BLACK}OpenTTD fersje {REV}
|
||||
@@ -157,8 +145,6 @@ STR_01C8_29TH :29
|
||||
############ range for days ends
|
||||
|
||||
|
||||
############ range for cargo acecpted starts
|
||||
############ range for cargo acecpted ends
|
||||
|
||||
|
||||
|
||||
@@ -286,6 +272,7 @@ STR_01C8_29TH :29
|
||||
|
||||
##id 0x2000
|
||||
|
||||
|
||||
##id 0x2800
|
||||
|
||||
##id 0x3000
|
||||
@@ -364,3 +351,4 @@ STR_01C8_29TH :29
|
||||
|
||||
############ End of list of rail types
|
||||
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user