src/disaster_cmd.cpp
branchnoai
changeset 9694 e72987579514
parent 9686 d3c195c226f9
child 9701 d1ac22c62f64
equal deleted inserted replaced
9693:31fcaa5375a1 9694:e72987579514
   119 
   119 
   120 /** Initialize a disaster vehicle. These vehicles are of type VEH_DISASTER, are unclickable
   120 /** Initialize a disaster vehicle. These vehicles are of type VEH_DISASTER, are unclickable
   121  * and owned by nobody */
   121  * and owned by nobody */
   122 static void InitializeDisasterVehicle(Vehicle *v, int x, int y, byte z, Direction direction, byte subtype)
   122 static void InitializeDisasterVehicle(Vehicle *v, int x, int y, byte z, Direction direction, byte subtype)
   123 {
   123 {
   124 	v = new (v) DisasterVehicle();
       
   125 	v->x_pos = x;
   124 	v->x_pos = x;
   126 	v->y_pos = y;
   125 	v->y_pos = y;
   127 	v->z_pos = z;
   126 	v->z_pos = z;
   128 	v->tile = TileVirtXY(x, y);
   127 	v->tile = TileVirtXY(x, y);
   129 	v->direction = direction;
   128 	v->direction = direction;
   598 		AddNewsItem(STR_B004_UFO_LANDS_NEAR,
   597 		AddNewsItem(STR_B004_UFO_LANDS_NEAR,
   599 			NEWS_FLAGS(NM_THIN, NF_VIEWPORT | NF_TILE, NT_ACCIDENT, 0),
   598 			NEWS_FLAGS(NM_THIN, NF_VIEWPORT | NF_TILE, NT_ACCIDENT, 0),
   600 			v->tile,
   599 			v->tile,
   601 			0);
   600 			0);
   602 
   601 
   603 		u = ForceAllocateSpecialVehicle();
   602 		u = new DisasterVehicle();
   604 		if (u == NULL) {
   603 		if (u == NULL) {
   605 			DeleteDisasterVeh(v);
   604 			DeleteDisasterVeh(v);
   606 			return;
   605 			return;
   607 		}
   606 		}
   608 
   607 
   609 		InitializeDisasterVehicle(u, -6 * TILE_SIZE, v->y_pos, 135, DIR_SW, ST_Big_Ufo_Destroyer);
   608 		InitializeDisasterVehicle(u, -6 * TILE_SIZE, v->y_pos, 135, DIR_SW, ST_Big_Ufo_Destroyer);
   610 		u->u.disaster.unk2 = v->index;
   609 		u->u.disaster.big_ufo_destroyer_target = v->index;
   611 
   610 
   612 		w = ForceAllocateSpecialVehicle();
   611 		w = new DisasterVehicle();
   613 		if (w == NULL) return;
   612 		if (w == NULL) return;
   614 
   613 
   615 		u->next = w;
   614 		u->next = w;
   616 		InitializeDisasterVehicle(w, -6 * TILE_SIZE, v->y_pos, 0, DIR_SW, ST_Big_Ufo_Destroyer_Shadow);
   615 		InitializeDisasterVehicle(w, -6 * TILE_SIZE, v->y_pos, 0, DIR_SW, ST_Big_Ufo_Destroyer_Shadow);
   617 		w->vehstatus |= VS_SHADOW;
   616 		w->vehstatus |= VS_SHADOW;
   665 		DeleteDisasterVeh(v);
   664 		DeleteDisasterVeh(v);
   666 		return;
   665 		return;
   667 	}
   666 	}
   668 
   667 
   669 	if (v->current_order.dest == 0) {
   668 	if (v->current_order.dest == 0) {
   670 		u = GetVehicle(v->u.disaster.unk2);
   669 		u = GetVehicle(v->u.disaster.big_ufo_destroyer_target);
   671 		if (delta(v->x_pos, u->x_pos) > TILE_SIZE) return;
   670 		if (delta(v->x_pos, u->x_pos) > TILE_SIZE) return;
   672 		v->current_order.dest = 1;
   671 		v->current_order.dest = 1;
   673 
   672 
   674 		CreateEffectVehicleRel(u, 0, 7, 8, EV_EXPLOSION_LARGE);
   673 		CreateEffectVehicleRel(u, 0, 7, 8, EV_EXPLOSION_LARGE);
   675 		SndPlayVehicleFx(SND_12_EXPLOSION, u);
   674 		SndPlayVehicleFx(SND_12_EXPLOSION, u);
   704 
   703 
   705 	if (++v->age > 8880) {
   704 	if (++v->age > 8880) {
   706 		VehiclePositionChanged(v);
   705 		VehiclePositionChanged(v);
   707 		BeginVehicleMove(v);
   706 		BeginVehicleMove(v);
   708 		EndVehicleMove(v);
   707 		EndVehicleMove(v);
   709 		DeleteVehicle(v);
   708 		delete v;
   710 		return;
   709 		return;
   711 	}
   710 	}
   712 
   711 
   713 	if (!HASBIT(v->tick_counter, 0)) return;
   712 	if (!HASBIT(v->tick_counter, 0)) return;
   714 
   713 
   758 
   757 
   759 /** Zeppeliner which crashes on a small airport if one found,
   758 /** Zeppeliner which crashes on a small airport if one found,
   760  * otherwise crashes on a random tile */
   759  * otherwise crashes on a random tile */
   761 static void Disaster_Zeppeliner_Init()
   760 static void Disaster_Zeppeliner_Init()
   762 {
   761 {
   763 	Vehicle *v = ForceAllocateSpecialVehicle(), *u;
   762 	Vehicle *v = new DisasterVehicle(), *u;
   764 	Station *st;
   763 	Station *st;
   765 	int x;
   764 	int x;
   766 
   765 
   767 	if (v == NULL) return;
   766 	if (v == NULL) return;
   768 
   767 
   779 	}
   778 	}
   780 
   779 
   781 	InitializeDisasterVehicle(v, x, 0, 135, DIR_SE, ST_Zeppeliner);
   780 	InitializeDisasterVehicle(v, x, 0, 135, DIR_SE, ST_Zeppeliner);
   782 
   781 
   783 	/* Allocate shadow too? */
   782 	/* Allocate shadow too? */
   784 	u = ForceAllocateSpecialVehicle();
   783 	u = new DisasterVehicle();
   785 	if (u != NULL) {
   784 	if (u != NULL) {
   786 		v->next = u;
   785 		v->next = u;
   787 		InitializeDisasterVehicle(u, x, 0, 0, DIR_SE, ST_Zeppeliner_Shadow);
   786 		InitializeDisasterVehicle(u, x, 0, 0, DIR_SE, ST_Zeppeliner_Shadow);
   788 		u->vehstatus |= VS_SHADOW;
   787 		u->vehstatus |= VS_SHADOW;
   789 	}
   788 	}
   792 
   791 
   793 /** Ufo which flies around aimlessly from the middle of the map a bit
   792 /** Ufo which flies around aimlessly from the middle of the map a bit
   794  * until it locates a road vehicle which it targets and then destroys */
   793  * until it locates a road vehicle which it targets and then destroys */
   795 static void Disaster_Small_Ufo_Init()
   794 static void Disaster_Small_Ufo_Init()
   796 {
   795 {
   797 	Vehicle *v = ForceAllocateSpecialVehicle(), *u;
   796 	Vehicle *v = new DisasterVehicle(), *u;
   798 	int x;
   797 	int x;
   799 
   798 
   800 	if (v == NULL) return;
   799 	if (v == NULL) return;
   801 
   800 
   802 	x = TileX(Random()) * TILE_SIZE + TILE_SIZE / 2;
   801 	x = TileX(Random()) * TILE_SIZE + TILE_SIZE / 2;
   804 	InitializeDisasterVehicle(v, x, 0, 135, DIR_SE, ST_Small_Ufo);
   803 	InitializeDisasterVehicle(v, x, 0, 135, DIR_SE, ST_Small_Ufo);
   805 	v->dest_tile = TileXY(MapSizeX() / 2, MapSizeY() / 2);
   804 	v->dest_tile = TileXY(MapSizeX() / 2, MapSizeY() / 2);
   806 	v->age = 0;
   805 	v->age = 0;
   807 
   806 
   808 	/* Allocate shadow too? */
   807 	/* Allocate shadow too? */
   809 	u = ForceAllocateSpecialVehicle();
   808 	u = new DisasterVehicle();
   810 	if (u != NULL) {
   809 	if (u != NULL) {
   811 		v->next = u;
   810 		v->next = u;
   812 		InitializeDisasterVehicle(u, x, 0, 0, DIR_SE, ST_Small_Ufo_Shadow);
   811 		InitializeDisasterVehicle(u, x, 0, 0, DIR_SE, ST_Small_Ufo_Shadow);
   813 		u->vehstatus |= VS_SHADOW;
   812 		u->vehstatus |= VS_SHADOW;
   814 	}
   813 	}
   831 		}
   830 		}
   832 	}
   831 	}
   833 
   832 
   834 	if (found == NULL) return;
   833 	if (found == NULL) return;
   835 
   834 
   836 	v = ForceAllocateSpecialVehicle();
   835 	v = new DisasterVehicle();
   837 	if (v == NULL) return;
   836 	if (v == NULL) return;
   838 
   837 
   839 	/* Start from the bottom (south side) of the map */
   838 	/* Start from the bottom (south side) of the map */
   840 	x = (MapSizeX() + 9) * TILE_SIZE - 1;
   839 	x = (MapSizeX() + 9) * TILE_SIZE - 1;
   841 	y = TileY(found->xy) * TILE_SIZE + 37;
   840 	y = TileY(found->xy) * TILE_SIZE + 37;
   842 
   841 
   843 	InitializeDisasterVehicle(v, x, y, 135, DIR_NE, ST_Airplane);
   842 	InitializeDisasterVehicle(v, x, y, 135, DIR_NE, ST_Airplane);
   844 
   843 
   845 	u = ForceAllocateSpecialVehicle();
   844 	u = new DisasterVehicle();
   846 	if (u != NULL) {
   845 	if (u != NULL) {
   847 		v->next = u;
   846 		v->next = u;
   848 		InitializeDisasterVehicle(u, x, y, 0, DIR_SE, ST_Airplane_Shadow);
   847 		InitializeDisasterVehicle(u, x, y, 0, DIR_SE, ST_Airplane_Shadow);
   849 		u->vehstatus |= VS_SHADOW;
   848 		u->vehstatus |= VS_SHADOW;
   850 	}
   849 	}
   867 		}
   866 		}
   868 	}
   867 	}
   869 
   868 
   870 	if (found == NULL) return;
   869 	if (found == NULL) return;
   871 
   870 
   872 	v = ForceAllocateSpecialVehicle();
   871 	v = new DisasterVehicle();
   873 	if (v == NULL) return;
   872 	if (v == NULL) return;
   874 
   873 
   875 	x = -16 * TILE_SIZE;
   874 	x = -16 * TILE_SIZE;
   876 	y = TileY(found->xy) * TILE_SIZE + 37;
   875 	y = TileY(found->xy) * TILE_SIZE + 37;
   877 
   876 
   878 	InitializeDisasterVehicle(v, x, y, 135, DIR_SW, ST_Helicopter);
   877 	InitializeDisasterVehicle(v, x, y, 135, DIR_SW, ST_Helicopter);
   879 
   878 
   880 	u = ForceAllocateSpecialVehicle();
   879 	u = new DisasterVehicle();
   881 	if (u != NULL) {
   880 	if (u != NULL) {
   882 		v->next = u;
   881 		v->next = u;
   883 		InitializeDisasterVehicle(u, x, y, 0, DIR_SW, ST_Helicopter_Shadow);
   882 		InitializeDisasterVehicle(u, x, y, 0, DIR_SW, ST_Helicopter_Shadow);
   884 		u->vehstatus |= VS_SHADOW;
   883 		u->vehstatus |= VS_SHADOW;
   885 
   884 
   886 		w = ForceAllocateSpecialVehicle();
   885 		w = new DisasterVehicle();
   887 		if (w != NULL) {
   886 		if (w != NULL) {
   888 			u->next = w;
   887 			u->next = w;
   889 			InitializeDisasterVehicle(w, x, y, 140, DIR_SW, ST_Helicopter_Rotors);
   888 			InitializeDisasterVehicle(w, x, y, 140, DIR_SW, ST_Helicopter_Rotors);
   890 		}
   889 		}
   891 	}
   890 	}
   894 
   893 
   895 /* Big Ufo which lands on a piece of rail and will consequently be shot
   894 /* Big Ufo which lands on a piece of rail and will consequently be shot
   896  * down by a combat airplane, destroying the surroundings */
   895  * down by a combat airplane, destroying the surroundings */
   897 static void Disaster_Big_Ufo_Init()
   896 static void Disaster_Big_Ufo_Init()
   898 {
   897 {
   899 	Vehicle *v = ForceAllocateSpecialVehicle(), *u;
   898 	Vehicle *v = new DisasterVehicle(), *u;
   900 	int x, y;
   899 	int x, y;
   901 
   900 
   902 	if (v == NULL) return;
   901 	if (v == NULL) return;
   903 
   902 
   904 	x = TileX(Random()) * TILE_SIZE + TILE_SIZE / 2;
   903 	x = TileX(Random()) * TILE_SIZE + TILE_SIZE / 2;
   907 	InitializeDisasterVehicle(v, x, y, 135, DIR_NW, ST_Big_Ufo);
   906 	InitializeDisasterVehicle(v, x, y, 135, DIR_NW, ST_Big_Ufo);
   908 	v->dest_tile = TileXY(MapSizeX() / 2, MapSizeY() / 2);
   907 	v->dest_tile = TileXY(MapSizeX() / 2, MapSizeY() / 2);
   909 	v->age = 0;
   908 	v->age = 0;
   910 
   909 
   911 	/* Allocate shadow too? */
   910 	/* Allocate shadow too? */
   912 	u = ForceAllocateSpecialVehicle();
   911 	u = new DisasterVehicle();
   913 	if (u != NULL) {
   912 	if (u != NULL) {
   914 		v->next = u;
   913 		v->next = u;
   915 		InitializeDisasterVehicle(u, x, y, 0, DIR_NW, ST_Big_Ufo_Shadow);
   914 		InitializeDisasterVehicle(u, x, y, 0, DIR_NW, ST_Big_Ufo_Shadow);
   916 		u->vehstatus |= VS_SHADOW;
   915 		u->vehstatus |= VS_SHADOW;
   917 	}
   916 	}
   919 
   918 
   920 
   919 
   921 /* Curious submarine #1, just floats around */
   920 /* Curious submarine #1, just floats around */
   922 static void Disaster_Small_Submarine_Init()
   921 static void Disaster_Small_Submarine_Init()
   923 {
   922 {
   924 	Vehicle *v = ForceAllocateSpecialVehicle();
   923 	Vehicle *v = new DisasterVehicle();
   925 	int x, y;
   924 	int x, y;
   926 	Direction dir;
   925 	Direction dir;
   927 	uint32 r;
   926 	uint32 r;
   928 
   927 
   929 	if (v == NULL) return;
   928 	if (v == NULL) return;
   944 
   943 
   945 
   944 
   946 /* Curious submarine #2, just floats around */
   945 /* Curious submarine #2, just floats around */
   947 static void Disaster_Big_Submarine_Init()
   946 static void Disaster_Big_Submarine_Init()
   948 {
   947 {
   949 	Vehicle *v = ForceAllocateSpecialVehicle();
   948 	Vehicle *v = new DisasterVehicle();
   950 	int x, y;
   949 	int x, y;
   951 	Direction dir;
   950 	Direction dir;
   952 	uint32 r;
   951 	uint32 r;
   953 
   952 
   954 	if (v == NULL) return;
   953 	if (v == NULL) return;
   984 				AddNewsItem(STR_B005_COAL_MINE_SUBSIDENCE_LEAVES,
   983 				AddNewsItem(STR_B005_COAL_MINE_SUBSIDENCE_LEAVES,
   985 					NEWS_FLAGS(NM_THIN, NF_VIEWPORT | NF_TILE, NT_ACCIDENT, 0), i->xy + TileDiffXY(1, 1), 0);
   984 					NEWS_FLAGS(NM_THIN, NF_VIEWPORT | NF_TILE, NT_ACCIDENT, 0), i->xy + TileDiffXY(1, 1), 0);
   986 
   985 
   987 				{
   986 				{
   988 					TileIndex tile = i->xy;
   987 					TileIndex tile = i->xy;
   989 					TileIndexDiff step = TileOffsByDiagDir(GB(Random(), 0, 2));
   988 					TileIndexDiff step = TileOffsByDiagDir((DiagDirection)GB(Random(), 0, 2));
   990 					uint n;
   989 					uint n;
   991 
   990 
   992 					for (n = 0; n < 30; n++) {
   991 					for (n = 0; n < 30; n++) {
   993 						DisasterClearSquare(tile);
   992 						DisasterClearSquare(tile);
   994 						tile = TILE_MASK(tile + step);
   993 						tile = TILE_MASK(tile + step);