233 ROAD_ALL |
233 ROAD_ALL |
234 }, |
234 }, |
235 }; |
235 }; |
236 |
236 |
237 |
237 |
238 static uint32 CheckRoadSlope(int tileh, RoadBits* pieces, RoadBits existing) |
238 static uint32 CheckRoadSlope(Slope tileh, RoadBits* pieces, RoadBits existing) |
239 { |
239 { |
240 RoadBits road_bits; |
240 RoadBits road_bits; |
241 |
241 |
242 if (IsSteepTileh(tileh)) return CMD_ERROR; |
242 if (IsSteepSlope(tileh)) return CMD_ERROR; |
243 road_bits = *pieces | existing; |
243 road_bits = *pieces | existing; |
244 |
244 |
245 // no special foundation |
245 // no special foundation |
246 if ((~_valid_tileh_slopes_road[0][tileh] & road_bits) == 0) { |
246 if ((~_valid_tileh_slopes_road[0][tileh] & road_bits) == 0) { |
247 // force that all bits are set when we have slopes |
247 // force that all bits are set when we have slopes |
248 if (tileh != 0) *pieces |= _valid_tileh_slopes_road[0][tileh]; |
248 if (tileh != SLOPE_FLAT) *pieces |= _valid_tileh_slopes_road[0][tileh]; |
249 return 0; // no extra cost |
249 return 0; // no extra cost |
250 } |
250 } |
251 |
251 |
252 // foundation is used. Whole tile is leveled up |
252 // foundation is used. Whole tile is leveled up |
253 if ((~_valid_tileh_slopes_road[1][tileh] & road_bits) == 0) { |
253 if ((~_valid_tileh_slopes_road[1][tileh] & road_bits) == 0) { |
254 return existing ? 0 : _price.terraform; |
254 return existing ? 0 : _price.terraform; |
255 } |
255 } |
256 |
256 |
257 // partly leveled up tile, only if there's no road on that tile |
257 // partly leveled up tile, only if there's no road on that tile |
258 if (existing == 0 && (tileh == 1 || tileh == 2 || tileh == 4 || tileh == 8)) { |
258 if (existing == 0 && (tileh == SLOPE_W || tileh == SLOPE_S || tileh == SLOPE_E || tileh == SLOPE_N)) { |
259 // force full pieces. |
259 // force full pieces. |
260 *pieces |= (*pieces & 0xC) >> 2; |
260 *pieces |= (*pieces & 0xC) >> 2; |
261 *pieces |= (*pieces & 0x3) << 2; |
261 *pieces |= (*pieces & 0x3) << 2; |
262 if (*pieces == ROAD_X || *pieces == ROAD_Y) return _price.terraform; |
262 if (*pieces == ROAD_X || *pieces == ROAD_Y) return _price.terraform; |
263 } |
263 } |
273 { |
273 { |
274 int32 cost = 0; |
274 int32 cost = 0; |
275 int32 ret; |
275 int32 ret; |
276 RoadBits existing = 0; |
276 RoadBits existing = 0; |
277 RoadBits pieces; |
277 RoadBits pieces; |
278 byte tileh; |
278 Slope tileh; |
279 |
279 |
280 SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION); |
280 SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION); |
281 |
281 |
282 /* Road pieces are max 4 bitset values (NE, NW, SE, SW) and town can only be non-zero |
282 /* Road pieces are max 4 bitset values (NE, NW, SE, SW) and town can only be non-zero |
283 * if a non-player is building the road */ |
283 * if a non-player is building the road */ |
310 break; |
310 break; |
311 |
311 |
312 case MP_RAILWAY: { |
312 case MP_RAILWAY: { |
313 Axis roaddir; |
313 Axis roaddir; |
314 |
314 |
315 if (IsSteepTileh(tileh)) { // very steep tile |
315 if (IsSteepSlope(tileh)) { |
316 return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION); |
316 return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION); |
317 } |
317 } |
318 |
318 |
319 #define M(x) (1 << (x)) |
319 #define M(x) (1 << (x)) |
320 /* Level crossings may only be built on these slopes */ |
320 /* Level crossings may only be built on these slopes */ |
321 if (!HASBIT(M(14) | M(13) | M(11) | M(10) | M(7) | M(5) | M(0), tileh)) { |
321 if (!HASBIT(M(SLOPE_SEN) | M(SLOPE_ENW) | M(SLOPE_NWS) | M(SLOPE_NS) | M(SLOPE_WSE) | M(SLOPE_EW) | M(SLOPE_FLAT), tileh)) { |
322 return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION); |
322 return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION); |
323 } |
323 } |
324 #undef M |
324 #undef M |
325 |
325 |
326 if (GetRailTileType(tile) != RAIL_TYPE_NORMAL) goto do_clear; |
326 if (GetRailTileType(tile) != RAIL_TYPE_NORMAL) goto do_clear; |
347 return _price.build_road * 2; |
347 return _price.build_road * 2; |
348 } |
348 } |
349 |
349 |
350 case MP_TUNNELBRIDGE: |
350 case MP_TUNNELBRIDGE: |
351 /* check for flat land */ |
351 /* check for flat land */ |
352 if (IsSteepTileh(tileh)) { // very steep tile |
352 if (IsSteepSlope(tileh)) { |
353 return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION); |
353 return_cmd_error(STR_1000_LAND_SLOPED_IN_WRONG_DIRECTION); |
354 } |
354 } |
355 |
355 |
356 if (!IsBridge(tile) || !IsBridgeMiddle(tile)) goto do_clear; |
356 if (!IsBridge(tile) || !IsBridgeMiddle(tile)) goto do_clear; |
357 |
357 |
549 */ |
549 */ |
550 int32 CmdBuildRoadDepot(TileIndex tile, uint32 flags, uint32 p1, uint32 p2) |
550 int32 CmdBuildRoadDepot(TileIndex tile, uint32 flags, uint32 p1, uint32 p2) |
551 { |
551 { |
552 int32 cost; |
552 int32 cost; |
553 Depot *dep; |
553 Depot *dep; |
554 uint tileh; |
554 Slope tileh; |
555 |
555 |
556 SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION); |
556 SET_EXPENSES_TYPE(EXPENSES_CONSTRUCTION); |
557 |
557 |
558 if (p1 > 3) return CMD_ERROR; // check direction |
558 if (p1 > 3) return CMD_ERROR; // check direction |
559 |
559 |
560 if (!EnsureNoVehicle(tile)) return CMD_ERROR; |
560 if (!EnsureNoVehicle(tile)) return CMD_ERROR; |
561 |
561 |
562 tileh = GetTileSlope(tile, NULL); |
562 tileh = GetTileSlope(tile, NULL); |
563 if (tileh != 0 && ( |
563 if (tileh != SLOPE_FLAT && ( |
564 !_patches.build_on_slopes || |
564 !_patches.build_on_slopes || |
565 IsSteepTileh(tileh) || |
565 IsSteepSlope(tileh) || |
566 !CanBuildDepotByTileh(p1, tileh) |
566 !CanBuildDepotByTileh(p1, tileh) |
567 )) { |
567 )) { |
568 return_cmd_error(STR_0007_FLAT_LAND_REQUIRED); |
568 return_cmd_error(STR_0007_FLAT_LAND_REQUIRED); |
569 } |
569 } |
570 |
570 |
653 } DrawRoadSeqStruct; |
653 } DrawRoadSeqStruct; |
654 |
654 |
655 #include "table/road_land.h" |
655 #include "table/road_land.h" |
656 |
656 |
657 |
657 |
658 uint GetRoadFoundation(uint tileh, RoadBits bits) |
658 uint GetRoadFoundation(Slope tileh, RoadBits bits) |
659 { |
659 { |
660 int i; |
660 int i; |
661 // normal level sloped building |
661 // normal level sloped building |
662 if ((~_valid_tileh_slopes_road[1][tileh] & bits) == 0) return tileh; |
662 if ((~_valid_tileh_slopes_road[1][tileh] & bits) == 0) return tileh; |
663 |
663 |
664 // inclined sloped building |
664 // inclined sloped building |
665 if (( |
665 if (( |
666 (i = 0, tileh == 1) || |
666 (i = 0, tileh == SLOPE_W) || |
667 (i += 2, tileh == 2) || |
667 (i += 2, tileh == SLOPE_S) || |
668 (i += 2, tileh == 4) || |
668 (i += 2, tileh == SLOPE_E) || |
669 (i += 2, tileh == 8) |
669 (i += 2, tileh == SLOPE_N) |
670 ) && ( |
670 ) && ( |
671 ( bits == ROAD_X) || |
671 ( bits == ROAD_X) || |
672 (i++, bits == ROAD_Y) |
672 (i++, bits == ROAD_Y) |
673 )) { |
673 )) { |
674 return i + 15; |
674 return i + 15; |
692 static void DrawRoadBits(TileInfo* ti, RoadBits road) |
692 static void DrawRoadBits(TileInfo* ti, RoadBits road) |
693 { |
693 { |
694 const DrawRoadTileStruct *drts; |
694 const DrawRoadTileStruct *drts; |
695 PalSpriteID image = 0; |
695 PalSpriteID image = 0; |
696 |
696 |
697 if (ti->tileh != 0) { |
697 if (ti->tileh != SLOPE_FLAT) { |
698 int foundation = GetRoadFoundation(ti->tileh, road); |
698 int foundation = GetRoadFoundation(ti->tileh, road); |
699 |
699 |
700 if (foundation != 0) DrawFoundation(ti, foundation); |
700 if (foundation != 0) DrawFoundation(ti, foundation); |
701 |
701 |
702 // DrawFoundation() modifies ti. |
702 // DrawFoundation() modifies ti. |
703 // Default sloped sprites.. |
703 // Default sloped sprites.. |
704 if (ti->tileh != 0) image = _road_sloped_sprites[ti->tileh - 1] + 0x53F; |
704 if (ti->tileh != SLOPE_FLAT) image = _road_sloped_sprites[ti->tileh - 1] + 0x53F; |
705 } |
705 } |
706 |
706 |
707 if (image == 0) image = _road_tile_sprites_1[road]; |
707 if (image == 0) image = _road_tile_sprites_1[road]; |
708 |
708 |
709 if (GetGroundType(ti->tile) == RGT_BARREN) image |= PALETTE_TO_BARE_LAND; |
709 if (GetGroundType(ti->tile) == RGT_BARREN) image |= PALETTE_TO_BARE_LAND; |
729 // Draw extra details. |
729 // Draw extra details. |
730 for (drts = _road_display_table[GetGroundType(ti->tile)][road]; drts->image != 0; drts++) { |
730 for (drts = _road_display_table[GetGroundType(ti->tile)][road]; drts->image != 0; drts++) { |
731 int x = ti->x | drts->subcoord_x; |
731 int x = ti->x | drts->subcoord_x; |
732 int y = ti->y | drts->subcoord_y; |
732 int y = ti->y | drts->subcoord_y; |
733 byte z = ti->z; |
733 byte z = ti->z; |
734 if (ti->tileh != 0) z = GetSlopeZ(x, y); |
734 if (ti->tileh != SLOPE_FLAT) z = GetSlopeZ(x, y); |
735 AddSortableSpriteToDraw(drts->image, x, y, 2, 2, 0x10, z); |
735 AddSortableSpriteToDraw(drts->image, x, y, 2, 2, 0x10, z); |
736 } |
736 } |
737 } |
737 } |
738 |
738 |
739 static void DrawTile_Road(TileInfo *ti) |
739 static void DrawTile_Road(TileInfo *ti) |
744 case ROAD_NORMAL: |
744 case ROAD_NORMAL: |
745 DrawRoadBits(ti, GetRoadBits(ti->tile)); |
745 DrawRoadBits(ti, GetRoadBits(ti->tile)); |
746 break; |
746 break; |
747 |
747 |
748 case ROAD_CROSSING: { |
748 case ROAD_CROSSING: { |
749 if (ti->tileh != 0) DrawFoundation(ti, ti->tileh); |
749 if (ti->tileh != SLOPE_FLAT) DrawFoundation(ti, ti->tileh); |
750 |
750 |
751 image = GetRailTypeInfo(GetRailTypeCrossing(ti->tile))->base_sprites.crossing; |
751 image = GetRailTypeInfo(GetRailTypeCrossing(ti->tile))->base_sprites.crossing; |
752 |
752 |
753 if (GetCrossingRoadAxis(ti->tile) == AXIS_X) image++; |
753 if (GetCrossingRoadAxis(ti->tile) == AXIS_X) image++; |
754 |
754 |
770 case ROAD_DEPOT: { |
770 case ROAD_DEPOT: { |
771 uint32 ormod; |
771 uint32 ormod; |
772 PlayerID player; |
772 PlayerID player; |
773 const DrawRoadSeqStruct* drss; |
773 const DrawRoadSeqStruct* drss; |
774 |
774 |
775 if (ti->tileh != 0) DrawFoundation(ti, ti->tileh); |
775 if (ti->tileh != SLOPE_FLAT) DrawFoundation(ti, ti->tileh); |
776 |
776 |
777 ormod = PALETTE_TO_GREY; //was this a bug/problem? |
777 ormod = PALETTE_TO_GREY; //was this a bug/problem? |
778 player = GetTileOwner(ti->tile); |
778 player = GetTileOwner(ti->tile); |
779 if (player < MAX_PLAYERS) ormod = PLAYER_SPRITE_COLOR(player); |
779 if (player < MAX_PLAYERS) ormod = PLAYER_SPRITE_COLOR(player); |
780 |
780 |
821 } |
821 } |
822 } |
822 } |
823 |
823 |
824 static uint GetSlopeZ_Road(const TileInfo* ti) |
824 static uint GetSlopeZ_Road(const TileInfo* ti) |
825 { |
825 { |
826 uint tileh = ti->tileh; |
826 Slope tileh = ti->tileh; |
827 uint z = ti->z; |
827 uint z = ti->z; |
828 |
828 |
829 if (tileh == 0) return z; |
829 if (tileh == SLOPE_FLAT) return z; |
830 if (GetRoadType(ti->tile) == ROAD_NORMAL) { |
830 if (GetRoadType(ti->tile) == ROAD_NORMAL) { |
831 uint f = GetRoadFoundation(tileh, GetRoadBits(ti->tile)); |
831 uint f = GetRoadFoundation(tileh, GetRoadBits(ti->tile)); |
832 |
832 |
833 if (f != 0) { |
833 if (f != 0) { |
834 if (f < 15) return z + 8; // leveled foundation |
834 if (f < 15) return z + 8; // leveled foundation |
838 } else { |
838 } else { |
839 return z + 8; |
839 return z + 8; |
840 } |
840 } |
841 } |
841 } |
842 |
842 |
843 static uint GetSlopeTileh_Road(TileIndex tile, uint tileh) |
843 static Slope GetSlopeTileh_Road(TileIndex tile, Slope tileh) |
844 { |
844 { |
845 if (tileh == 0) return 0; |
845 if (tileh == SLOPE_FLAT) return SLOPE_FLAT; |
846 if (GetRoadType(tile) == ROAD_NORMAL) { |
846 if (GetRoadType(tile) == ROAD_NORMAL) { |
847 uint f = GetRoadFoundation(tileh, GetRoadBits(tile)); |
847 uint f = GetRoadFoundation(tileh, GetRoadBits(tile)); |
848 |
848 |
849 if (f == 0) return tileh; |
849 if (f == 0) return tileh; |
850 if (f < 15) return 0; // leveled foundation |
850 if (f < 15) return SLOPE_FLAT; // leveled foundation |
851 return _inclined_tileh[f - 15]; // inclined foundation |
851 return _inclined_tileh[f - 15]; // inclined foundation |
852 } else { |
852 } else { |
853 return 0; |
853 return SLOPE_FLAT; |
854 } |
854 } |
855 } |
855 } |
856 |
856 |
857 static void GetAcceptedCargo_Road(TileIndex tile, AcceptedCargo ac) |
857 static void GetAcceptedCargo_Road(TileIndex tile, AcceptedCargo ac) |
858 { |
858 { |
913 |
913 |
914 // Show an animation to indicate road work |
914 // Show an animation to indicate road work |
915 if (t->road_build_months != 0 && |
915 if (t->road_build_months != 0 && |
916 !(DistanceManhattan(t->xy, tile) >= 8 && grp == 0) && |
916 !(DistanceManhattan(t->xy, tile) >= 8 && grp == 0) && |
917 GetRoadType(tile) == ROAD_NORMAL && (GetRoadBits(tile) == ROAD_X || GetRoadBits(tile) == ROAD_Y)) { |
917 GetRoadType(tile) == ROAD_NORMAL && (GetRoadBits(tile) == ROAD_X || GetRoadBits(tile) == ROAD_Y)) { |
918 if (GetTileSlope(tile, NULL) == 0 && EnsureNoVehicle(tile) && CHANCE16(1, 20)) { |
918 if (GetTileSlope(tile, NULL) == SLOPE_FLAT && EnsureNoVehicle(tile) && CHANCE16(1, 20)) { |
919 StartRoadWorks(tile); |
919 StartRoadWorks(tile); |
920 |
920 |
921 SndPlayTileFx(SND_21_JACKHAMMER, tile); |
921 SndPlayTileFx(SND_21_JACKHAMMER, tile); |
922 CreateEffectVehicleAbove( |
922 CreateEffectVehicleAbove( |
923 TileX(tile) * TILE_SIZE + 7, |
923 TileX(tile) * TILE_SIZE + 7, |