changeset 16767:3a5666e0d4bc draft

(svn r21500) -Feature [FS#730]: diagonal tile clearing and terraforming. Based on patch by fonsinchen
author rubidium <rubidium@openttd.org>
date Mon, 13 Dec 2010 15:15:02 +0000
parents 72ca13c2eb9b
children d71b4bdc2e35
files src/landscape.cpp src/lang/english.txt src/terraform_cmd.cpp src/terraform_gui.cpp
diffstat 4 files changed, 24 insertions(+), 12 deletions(-) [+]
line wrap: on
line diff
--- a/src/landscape.cpp
+++ b/src/landscape.cpp
@@ -642,7 +642,8 @@
  * @param tile end tile of area dragging
  * @param flags of operation to conduct
  * @param p1 start tile of area dragging
- * @param p2 unused
+ * @param p2 various bitstuffed data.
+ *  bit      0: Whether to use the Orthogonal (0) or Diagonal (1) iterator.
  * @param text unused
  * @return the cost of this operation or an error
  */
@@ -656,7 +657,9 @@
 	bool had_success = false;
 
 	TileArea ta(tile, p1);
-	TILE_AREA_LOOP(t, ta) {
+	TileIterator *iter = HasBit(p2, 0) ? (TileIterator *)new DiagonalTileIterator(tile, p1) : new OrthogonalTileIterator(ta);
+	for (; *iter != INVALID_TILE; ++(*iter)) {
+		TileIndex t = *iter;
 		CommandCost ret = DoCommand(t, 0, 0, flags & ~DC_EXEC, CMD_LANDSCAPE_CLEAR);
 		if (ret.Failed()) {
 			last_error = ret;
@@ -668,6 +671,7 @@
 			money -= ret.GetCost();
 			if (ret.GetCost() > 0 && money < 0) {
 				_additional_cash_required = ret.GetCost();
+				delete iter;
 				return cost;
 			}
 			DoCommand(t, 0, 0, flags, CMD_LANDSCAPE_CLEAR);
@@ -684,6 +688,7 @@
 		cost.AddCost(ret);
 	}
 
+	delete iter;
 	return had_success ? cost : last_error;
 }
 
--- a/src/lang/english.txt
+++ b/src/lang/english.txt
@@ -236,7 +236,7 @@
 STR_TOOLTIP_TOGGLE_LARGE_SMALL_WINDOW                           :{BLACK}Toggle large/small window size
 STR_TOOLTIP_VSCROLL_BAR_SCROLLS_LIST                            :{BLACK}Scroll bar - scrolls list up/down
 STR_TOOLTIP_HSCROLL_BAR_SCROLLS_LIST                            :{BLACK}Scroll bar - scrolls list left/right
-STR_TOOLTIP_DEMOLISH_BUILDINGS_ETC                              :{BLACK}Demolish buildings etc. on a square of land
+STR_TOOLTIP_DEMOLISH_BUILDINGS_ETC                              :{BLACK}Demolish buildings etc. on a square of land. Ctrl selects the area diagonally
 
 # Query window
 STR_BUTTON_DEFAULT                                              :{BLACK}Default
@@ -2069,9 +2069,9 @@
 
 # Landscaping toolbar
 STR_LANDSCAPING_TOOLBAR                                         :{WHITE}Landscaping
-STR_LANDSCAPING_TOOLTIP_LOWER_A_CORNER_OF_LAND                  :{BLACK}Lower a corner of land
-STR_LANDSCAPING_TOOLTIP_RAISE_A_CORNER_OF_LAND                  :{BLACK}Raise a corner of land
-STR_LANDSCAPING_LEVEL_LAND_TOOLTIP                              :{BLACK}Level land
+STR_LANDSCAPING_TOOLTIP_LOWER_A_CORNER_OF_LAND                  :{BLACK}Lower a corner of land. Dragging lowers the first selected corner and levels the selected area to the new corner height. Ctrl selects the area diagonally
+STR_LANDSCAPING_TOOLTIP_RAISE_A_CORNER_OF_LAND                  :{BLACK}Raise a corner of land. Dragging raises the first selected corner and levels the selected area to the new corner height. Ctrl selects the area diagonally
+STR_LANDSCAPING_LEVEL_LAND_TOOLTIP                              :{BLACK}Level an area of land to the height of the first selected corner. Ctrl selects the area diagonally
 STR_LANDSCAPING_TOOLTIP_PURCHASE_LAND                           :{BLACK}Purchase land for future use
 
 # Object construction window
--- a/src/terraform_cmd.cpp
+++ b/src/terraform_cmd.cpp
@@ -379,6 +379,7 @@
  * @param flags for this command type
  * @param p1 start tile of area drag
  * @param p2 various bitstuffed data.
+ *  bit      0: Whether to use the Orthogonal (0) or Diagonal (1) iterator.
  *  bits 1 - 2: Mode of leveling \c LevelMode.
  * @param text unused
  * @return the cost of this operation or an error
@@ -411,7 +412,9 @@
 	bool had_success = false;
 
 	TileArea ta(tile, p1);
-	TILE_AREA_LOOP(t, ta) {
+	TileIterator *iter = HasBit(p2, 0) ? (TileIterator *)new DiagonalTileIterator(tile, p1) : new OrthogonalTileIterator(ta);
+	for (; *iter != INVALID_TILE; ++(*iter)) {
+		TileIndex t = *iter;
 		uint curh = TileHeight(t);
 		while (curh != h) {
 			CommandCost ret = DoCommand(t, SLOPE_N, (curh > h) ? 0 : 1, flags & ~DC_EXEC, CMD_TERRAFORM_LAND);
@@ -424,6 +427,7 @@
 				money -= ret.GetCost();
 				if (money < 0) {
 					_additional_cash_required = ret.GetCost();
+					delete iter;
 					return cost;
 				}
 				DoCommand(t, SLOPE_N, (curh > h) ? 0 : 1, flags, CMD_TERRAFORM_LAND);
@@ -435,5 +439,6 @@
 		}
 	}
 
+	delete iter;
 	return had_success ? cost : last_error;
 }
--- a/src/terraform_gui.cpp
+++ b/src/terraform_gui.cpp
@@ -107,16 +107,16 @@
 
 	switch (proc) {
 		case DDSP_DEMOLISH_AREA:
-			DoCommandP(end_tile, start_tile, 0, CMD_CLEAR_AREA | CMD_MSG(STR_ERROR_CAN_T_CLEAR_THIS_AREA), CcPlaySound10);
+			DoCommandP(end_tile, start_tile, _ctrl_pressed, CMD_CLEAR_AREA | CMD_MSG(STR_ERROR_CAN_T_CLEAR_THIS_AREA), CcPlaySound10);
 			break;
 		case DDSP_RAISE_AND_LEVEL_AREA:
-			DoCommandP(end_tile, start_tile, LM_RAISE << 1, CMD_LEVEL_LAND | CMD_MSG(STR_ERROR_CAN_T_RAISE_LAND_HERE), CcTerraform);
+			DoCommandP(end_tile, start_tile, LM_RAISE << 1 | _ctrl_pressed, CMD_LEVEL_LAND | CMD_MSG(STR_ERROR_CAN_T_RAISE_LAND_HERE), CcTerraform);
 			break;
 		case DDSP_LOWER_AND_LEVEL_AREA:
-			DoCommandP(end_tile, start_tile, LM_LOWER << 1, CMD_LEVEL_LAND | CMD_MSG(STR_ERROR_CAN_T_LOWER_LAND_HERE), CcTerraform);
+			DoCommandP(end_tile, start_tile, LM_LOWER << 1 | _ctrl_pressed, CMD_LEVEL_LAND | CMD_MSG(STR_ERROR_CAN_T_LOWER_LAND_HERE), CcTerraform);
 			break;
 		case DDSP_LEVEL_AREA:
-			DoCommandP(end_tile, start_tile, LM_LEVEL << 1, CMD_LEVEL_LAND | CMD_MSG(STR_ERROR_CAN_T_LEVEL_LAND_HERE), CcTerraform);
+			DoCommandP(end_tile, start_tile, LM_LEVEL << 1 | _ctrl_pressed, CMD_LEVEL_LAND | CMD_MSG(STR_ERROR_CAN_T_LEVEL_LAND_HERE), CcTerraform);
 			break;
 		case DDSP_CREATE_ROCKS:
 			GenerateRockyArea(end_tile, start_tile);
@@ -622,7 +622,9 @@
  */
 bool IsDraggingDiagonal()
 {
-	return false;
+	return _ctrl_pressed && _left_button_down && (
+			_place_proc == PlaceProc_DemolishArea || _place_proc == PlaceProc_LevelLand ||
+			_place_proc == PlaceProc_RaiseLand    || _place_proc == PlaceProc_LowerLand);
 }
 
 struct ScenarioEditorLandscapeGenerationWindow : Window {