src/viewport.cpp
changeset 8720 4e60c30e2006
parent 8640 1e93b81e96d2
child 8733 9e2d2a2619ff
equal deleted inserted replaced
8719:c13af43ef987 8720:4e60c30e2006
     9 #include "gui.h"
     9 #include "gui.h"
    10 #include "spritecache.h"
    10 #include "spritecache.h"
    11 #include "table/sprites.h"
    11 #include "table/sprites.h"
    12 #include "table/strings.h"
    12 #include "table/strings.h"
    13 #include "landscape.h"
    13 #include "landscape.h"
    14 #include "viewport.h"
    14 #include "viewport_func.h"
    15 #include "station.h"
    15 #include "station.h"
    16 #include "town.h"
    16 #include "town.h"
    17 #include "signs.h"
    17 #include "signs.h"
    18 #include "waypoint.h"
    18 #include "waypoint.h"
    19 #include "variables.h"
    19 #include "variables.h"
    26 #include "zoom_func.h"
    26 #include "zoom_func.h"
    27 #include "vehicle_func.h"
    27 #include "vehicle_func.h"
    28 
    28 
    29 #define VIEWPORT_DRAW_MEM (65536 * 2)
    29 #define VIEWPORT_DRAW_MEM (65536 * 2)
    30 
    30 
       
    31 PlaceProc *_place_proc;
       
    32 Point _tile_fract_coords;
    31 ZoomLevel _saved_scrollpos_zoom;
    33 ZoomLevel _saved_scrollpos_zoom;
    32 
    34 
    33 /**
    35 /**
    34  * The maximum number of viewports depends on the maximum number
    36  * The maximum number of viewports depends on the maximum number
    35  * of windows. Technically is could be the maximum number of
    37  * of windows. Technically is could be the maximum number of
   863 static bool IsPartOfAutoLine(int px, int py)
   865 static bool IsPartOfAutoLine(int px, int py)
   864 {
   866 {
   865 	px -= _thd.selstart.x;
   867 	px -= _thd.selstart.x;
   866 	py -= _thd.selstart.y;
   868 	py -= _thd.selstart.y;
   867 
   869 
   868 	switch (_thd.drawstyle) {
   870 	if ((_thd.drawstyle & ~HT_DIR_MASK) != HT_LINE) return false;
   869 	case HT_LINE | HT_DIR_X:  return py == 0; // x direction
   871 
   870 	case HT_LINE | HT_DIR_Y:  return px == 0; // y direction
   872 	switch (_thd.drawstyle & HT_DIR_MASK) {
   871 	case HT_LINE | HT_DIR_HU: return px == -py || px == -py - 16; // horizontal upper
   873 		case HT_DIR_X:  return py == 0; // x direction
   872 	case HT_LINE | HT_DIR_HL: return px == -py || px == -py + 16; // horizontal lower
   874 		case HT_DIR_Y:  return px == 0; // y direction
   873 	case HT_LINE | HT_DIR_VL: return px == py || px == py + 16; // vertival left
   875 		case HT_DIR_HU: return px == -py || px == -py - 16; // horizontal upper
   874 	case HT_LINE | HT_DIR_VR: return px == py || px == py - 16; // vertical right
   876 		case HT_DIR_HL: return px == -py || px == -py + 16; // horizontal lower
   875 	default:
   877 		case HT_DIR_VL: return px == py || px == py + 16; // vertival left
   876 		NOT_REACHED();
   878 		case HT_DIR_VR: return px == py || px == py - 16; // vertical right
   877 	}
   879 		default:
   878 
   880 			NOT_REACHED();
   879 	/* useless, but avoids compiler warning this way */
   881 	}
   880 	return 0;
       
   881 }
   882 }
   882 
   883 
   883 // [direction][side]
   884 // [direction][side]
   884 static const int _AutorailType[6][2] = {
   885 static const HighLightStyle _autorail_type[6][2] = {
   885 	{ HT_DIR_X,  HT_DIR_X },
   886 	{ HT_DIR_X,  HT_DIR_X },
   886 	{ HT_DIR_Y,  HT_DIR_Y },
   887 	{ HT_DIR_Y,  HT_DIR_Y },
   887 	{ HT_DIR_HU, HT_DIR_HL },
   888 	{ HT_DIR_HU, HT_DIR_HL },
   888 	{ HT_DIR_HL, HT_DIR_HU },
   889 	{ HT_DIR_HL, HT_DIR_HU },
   889 	{ HT_DIR_VL, HT_DIR_VR },
   890 	{ HT_DIR_VL, HT_DIR_VR },
   967 			DrawSelectionSprite(_cur_dpi->zoom <= ZOOM_LVL_DETAIL ? SPR_DOT : SPR_DOT_SMALL, PAL_NONE, ti, z, foundation_part);
   968 			DrawSelectionSprite(_cur_dpi->zoom <= ZOOM_LVL_DETAIL ? SPR_DOT : SPR_DOT_SMALL, PAL_NONE, ti, z, foundation_part);
   968 		} else if (_thd.drawstyle & HT_RAIL /*&& _thd.place_mode == VHM_RAIL*/) {
   969 		} else if (_thd.drawstyle & HT_RAIL /*&& _thd.place_mode == VHM_RAIL*/) {
   969 			/* autorail highlight piece under cursor */
   970 			/* autorail highlight piece under cursor */
   970 			uint type = _thd.drawstyle & 0xF;
   971 			uint type = _thd.drawstyle & 0xF;
   971 			assert(type <= 5);
   972 			assert(type <= 5);
   972 			DrawAutorailSelection(ti, _AutorailType[type][0]);
   973 			DrawAutorailSelection(ti, _autorail_type[type][0]);
   973 		} else if (IsPartOfAutoLine(ti->x, ti->y)) {
   974 		} else if (IsPartOfAutoLine(ti->x, ti->y)) {
   974 			/* autorail highlighting long line */
   975 			/* autorail highlighting long line */
   975 			int dir = _thd.drawstyle & ~0xF0;
   976 			int dir = _thd.drawstyle & ~0xF0;
   976 			uint side;
   977 			uint side;
   977 
   978 
   980 			} else {
   981 			} else {
   981 				TileIndex start = TileVirtXY(_thd.selstart.x, _thd.selstart.y);
   982 				TileIndex start = TileVirtXY(_thd.selstart.x, _thd.selstart.y);
   982 				side = Delta(Delta(TileX(start), TileX(ti->tile)), Delta(TileY(start), TileY(ti->tile)));
   983 				side = Delta(Delta(TileX(start), TileX(ti->tile)), Delta(TileY(start), TileY(ti->tile)));
   983 			}
   984 			}
   984 
   985 
   985 			DrawAutorailSelection(ti, _AutorailType[dir][side]);
   986 			DrawAutorailSelection(ti, _autorail_type[dir][side]);
   986 		}
   987 		}
   987 		return;
   988 		return;
   988 	}
   989 	}
   989 
   990 
   990 	/* Check if it's inside the outer area? */
   991 	/* Check if it's inside the outer area? */
  2227 	_thd.new_outersize.x = sx * TILE_SIZE;
  2228 	_thd.new_outersize.x = sx * TILE_SIZE;
  2228 	_thd.new_outersize.y = sy * TILE_SIZE;
  2229 	_thd.new_outersize.y = sy * TILE_SIZE;
  2229 }
  2230 }
  2230 
  2231 
  2231 /** returns the best autorail highlight type from map coordinates */
  2232 /** returns the best autorail highlight type from map coordinates */
  2232 static byte GetAutorailHT(int x, int y)
  2233 static HighLightStyle GetAutorailHT(int x, int y)
  2233 {
  2234 {
  2234 	return HT_RAIL | _AutorailPiece[x & 0xF][y & 0xF];
  2235 	return HT_RAIL | _autorail_piece[x & 0xF][y & 0xF];
  2235 }
  2236 }
  2236 
  2237 
  2237 /**
  2238 /**
  2238  * Updates tile highlighting for all cases.
  2239  * Updates tile highlighting for all cases.
  2239  * Uses _thd.selstart and _thd.selend and _thd.place_mode (set elsewhere) to determine _thd.pos and _thd.size
  2240  * Uses _thd.selstart and _thd.selend and _thd.place_mode (set elsewhere) to determine _thd.pos and _thd.size
  2374 	_special_mouse_mode = WSM_PRESIZE;
  2375 	_special_mouse_mode = WSM_PRESIZE;
  2375 }
  2376 }
  2376 
  2377 
  2377 /** returns information about the 2x1 piece to be build.
  2378 /** returns information about the 2x1 piece to be build.
  2378  * The lower bits (0-3) are the track type. */
  2379  * The lower bits (0-3) are the track type. */
  2379 static byte Check2x1AutoRail(int mode)
  2380 static HighLightStyle Check2x1AutoRail(int mode)
  2380 {
  2381 {
  2381 	int fxpy = _tile_fract_coords.x + _tile_fract_coords.y;
  2382 	int fxpy = _tile_fract_coords.x + _tile_fract_coords.y;
  2382 	int sxpy = (_thd.selend.x & 0xF) + (_thd.selend.y & 0xF);
  2383 	int sxpy = (_thd.selend.x & 0xF) + (_thd.selend.y & 0xF);
  2383 	int fxmy = _tile_fract_coords.x - _tile_fract_coords.y;
  2384 	int fxmy = _tile_fract_coords.x - _tile_fract_coords.y;
  2384 	int sxmy = (_thd.selend.x & 0xF) - (_thd.selend.y & 0xF);
  2385 	int sxmy = (_thd.selend.x & 0xF) - (_thd.selend.y & 0xF);
  2385 
  2386 
  2386 	switch (mode) {
  2387 	switch (mode) {
  2387 	case 0: // end piece is lower right
  2388 		default: NOT_REACHED();
  2388 		if (fxpy >= 20 && sxpy <= 12) { /*SwapSelection(); DoRailroadTrack(0); */return 3; }
  2389 		case 0: // end piece is lower right
  2389 		if (fxmy < -3 && sxmy > 3) {/* DoRailroadTrack(0); */return 5; }
  2390 			if (fxpy >= 20 && sxpy <= 12) { /*SwapSelection(); DoRailroadTrack(0); */return HT_DIR_HL; }
  2390 		return 1;
  2391 			if (fxmy < -3 && sxmy > 3) {/* DoRailroadTrack(0); */return HT_DIR_VR; }
  2391 
  2392 			return HT_DIR_Y;
  2392 	case 1:
  2393 
  2393 		if (fxmy > 3 && sxmy < -3) { /*SwapSelection(); DoRailroadTrack(0); */return 4; }
  2394 		case 1:
  2394 		if (fxpy <= 12 && sxpy >= 20) { /*DoRailroadTrack(0); */return 2; }
  2395 			if (fxmy > 3 && sxmy < -3) { /*SwapSelection(); DoRailroadTrack(0); */return HT_DIR_VL; }
  2395 		return 1;
  2396 			if (fxpy <= 12 && sxpy >= 20) { /*DoRailroadTrack(0); */return HT_DIR_HU; }
  2396 
  2397 			return HT_DIR_Y;
  2397 	case 2:
  2398 
  2398 		if (fxmy > 3 && sxmy < -3) { /*DoRailroadTrack(3);*/ return 4; }
  2399 		case 2:
  2399 		if (fxpy >= 20 && sxpy <= 12) { /*SwapSelection(); DoRailroadTrack(0); */return 3; }
  2400 			if (fxmy > 3 && sxmy < -3) { /*DoRailroadTrack(3);*/ return HT_DIR_VL; }
  2400 		return 0;
  2401 			if (fxpy >= 20 && sxpy <= 12) { /*SwapSelection(); DoRailroadTrack(0); */return HT_DIR_HL; }
  2401 
  2402 			return HT_DIR_X;
  2402 	case 3:
  2403 
  2403 		if (fxmy < -3 && sxmy > 3) { /*SwapSelection(); DoRailroadTrack(3);*/ return 5; }
  2404 		case 3:
  2404 		if (fxpy <= 12 && sxpy >= 20) { /*DoRailroadTrack(0); */return 2; }
  2405 			if (fxmy < -3 && sxmy > 3) { /*SwapSelection(); DoRailroadTrack(3);*/ return HT_DIR_VR; }
  2405 		return 0;
  2406 			if (fxpy <= 12 && sxpy >= 20) { /*DoRailroadTrack(0); */return HT_DIR_HU; }
  2406 	}
  2407 			return HT_DIR_X;
  2407 
  2408 	}
  2408 	return 0; // avoids compiler warnings
       
  2409 }
  2409 }
  2410 
  2410 
  2411 /** Check if the direction of start and end tile should be swapped based on
  2411 /** Check if the direction of start and end tile should be swapped based on
  2412  * the dragging-style. Default directions are:
  2412  * the dragging-style. Default directions are:
  2413  * in the case of a line (HT_RAIL, HT_LINE):  DIR_NE, DIR_NW, DIR_N, DIR_E
  2413  * in the case of a line (HT_RAIL, HT_LINE):  DIR_NE, DIR_NW, DIR_N, DIR_E
  2747 				byte index = 0;
  2747 				byte index = 0;
  2748 				uint64 params[3];
  2748 				uint64 params[3];
  2749 
  2749 
  2750 				/* If dragging an area (eg dynamite tool) and it is actually a single
  2750 				/* If dragging an area (eg dynamite tool) and it is actually a single
  2751 				 * row/column, change the type to 'line' to get proper calculation for height */
  2751 				 * row/column, change the type to 'line' to get proper calculation for height */
  2752 				style = _thd.next_drawstyle;
  2752 				style = (HighLightStyle)_thd.next_drawstyle;
  2753 				if (style & HT_RECT) {
  2753 				if (style & HT_RECT) {
  2754 					if (dx == 1) {
  2754 					if (dx == 1) {
  2755 						style = HT_LINE | HT_DIR_Y;
  2755 						style = HT_LINE | HT_DIR_Y;
  2756 					} else if (dy == 1) {
  2756 					} else if (dy == 1) {
  2757 						style = HT_LINE | HT_DIR_X;
  2757 						style = HT_LINE | HT_DIR_X;