sr2lua/rn07.lua

  1. -- rn07.lua 
  2. -- SR2 mission script 
  3. -- 3/28/07 
  4.  
  5. 	LTNT_DEBUGGED = false 
  6.  
  7. 	-- Coop mission? 
  8. 	IN_COOP	= false 
  9.  
  10. 	-- MISC CONSTANTS 
  11. 	 
  12. 		-- Stage 1 Hospital Escape 
  13. 		GURNEY_SPRINT_USE_OVERRIDE_MS			= 15000	-- How long the player can sprint while holding Gat's gurney. 
  14. 		GURNEY_SPRINT_DELAY_OVERRIDE_MS		= 5000	-- Delay after a sprint before meter refill starts while holding gurney. 
  15. 		GURNEY_SPRINT_RECHARGE_OVERRIDE_MS	= 5000	-- Time for sprint meter to refill while holding gurney. 
  16. 		GAT_HIT_POINTS								= 7000	-- Gat's total hit points 
  17. 		GAT_HIT_POINTS_HELI								= 10000  --Gat's total HP while in the helicopter 
  18. 		GAT_PERCENT_HEALTH						= 1.0		-- Ratio of Gat's starting health to full health. 
  19. 		GAT_MIN_RESTART_PERCENT_HEALTH		= 0.5		-- Min health ratio of Gat upon restart. 
  20. 		GAT_PADDLE_HEALTH_RESTORE				= .40		-- Fraction of Gat's health returned when using the shock paddles. 
  21. 		LIEUTENANT_RESPAWN_DISTANCE			= 1		-- Min distance from player to allow respawn 
  22. 		LIEUTENANT_RESPAWN_TIME_MS				= 250		-- Time in MS before respawning 
  23. 		LIEUTENANT_SPRINT_CHANCE				= 50		-- % of the time that the Lieutenants will sprint to the player 
  24. 		GAT_REVIVE_TIME_S							= 45		-- Amount of time player has to revive Gat after he goes into cardiac arrest 
  25. 		GAT_REVIVE_HUD_INDEX						= 0 
  26. 		GAT_DISTANCE_ALLOWED						= 25		-- Maximum distance the player can be from Gat  
  27. 		GAT_DISTANCE_TIME_S						= 20		-- If player out of range this long, mission fails 
  28. 		GAT_DISTANCE_HUD_INDEX					= 1  
  29. 		GAT_HEALTH_LOSS_TIME_S					= 210		-- Time (in s.) that it will take for Gat to die assuming that he 
  30. 																	-- he takes no additional damage from Ronin soldiers. 
  31. 		GAT_HELI_DAMAGE_RATIO					= .05		-- When Gat is in the helicopter, this fraction of damage dealt to 
  32. 																	-- the copter is applied to Gat as well. 
  33. 	-- GROUPS -- 
  34.   
  35. 		GROUP_AMBULANCE				= "rn07_$Gambulance" 
  36. 		GROUP_GAT						= "rn07_$Ggat" 
  37. 		GROUP_GAT_NORMAL				= "rn07_$Ggat_normal" 
  38. 		GROUP_HELICOPTER				= "rn07_$Ghelicopter" 
  39. 		GROUP_OUTSIDE_HOSPITAL		= "rn07_$Goutside_hospital" -- Ronin outside the front door 
  40. 		GROUP_RONIN_HELICOPTER		= "rn07_$Gronin_helicopter" 
  41. 		GROUP_HELI_ATTACK_RONIN		= "rn07_$Gheli_attack_ronin_1" -- Ronin that attack the player when they enter the helicopter 
  42. 		GROUP_RONIN_STATIONARY		= "rn07_$Gronin_stationary" 
  43. 		GROUP_RONIN_STATIONARY_COOP= "rn07_$Gronin_stationary_coop" 
  44.  
  45. 		-- Patrol groups 
  46. 		FLOOR_PATROL_GROUPS		= {	["floor_1"] = "rn07_$Gronin_floor_1",	["floor_2"] = "rn07_$Gronin_floor_2",  
  47. 												["floor_3"] = "rn07_$Gronin_floor_3",	["floor_4"] = "rn07_$Gronin_floor_4"} 
  48.  
  49. 		-- List of all groups, makes cleaning up more convenient 
  50. 		TABLE_ALL_GROUPS			= {	GROUP_AMBULANCE, GROUP_GAT, GROUP_OUTSIDE_HOSPITAL,  
  51. 												GROUP_RONIN_HELICOPTER, GROUP_HELI_ATTACK_RONIN,  
  52. 												GROUP_RONIN_STATIONARY} 
  53.  
  54. 		TABLE_ALL_COOP_GROUPS	= {	GROUP_RONIN_STATIONARY_COOP} 
  55. 	 
  56. 	-- GROUP MEMBER TABLES --  
  57. 		PATROL_GROUP_MEMBERS		=  
  58. 			{ 
  59. 				["floor_1"] =	{	"rn07_$c007", "rn07_$c008", "rn07_$c009", "rn07_$c010", "rn07_$c011", "rn07_$c012"}; 
  60. 				["floor_2"] =	{	"rn07_$c001", "rn07_$c002", "rn07_$c003", "rn07_$c004", "rn07_$c005", "rn07_$c006"}; 
  61. 				["floor_3"] =	{	"rn07_$c013", "rn07_$c014", "rn07_$c015", "rn07_$c016", "rn07_$c017", "rn07_$c018"}; 
  62. 				["floor_4"] =	{	"rn07_$c019", "rn07_$c020", "rn07_$c021", "rn07_$c022", "rn07_$c023", "rn07_$c024"}; 
  63. 			} 
  64. 		 
  65. 		STATIONARY_GROUP_MEMBERS 		={"rn07_$c032", "rn07_$c033", "rn07_$c034", "rn07_$c035", "rn07_$c036", "rn07_$c037", "rn07_$c038", "rn07_$c039", 
  66. 										  "rn07_$c040", "rn07_$c041", "rn07_$c042", "rn07_$c043", "rn07_$c044", "rn07_$c045"} 
  67. 						 
  68. 		STATIONARY_GROUP_MEMBERS_COOP 	= {"rn07_$c046", "rn07_$c047", "rn07_$c048", "rn07_$c049", "rn07_$c050", "rn07_$c051",  
  69. 										   "rn07_$c052", "rn07_$c053", "rn07_$c054", "rn07_$c055", "rn07_$c056", "rn07_$c057",  
  70. 										   "rn07_$c058", "rn07_$c059", "rn07_$c060", "rn07_$c061"} 
  71. 		 
  72. --		RONIN_HELICOPTER_MEMBERS = {"rn07_$c029",	"rn07_$c030", "rn07_$c031"} 
  73. 		RONIN_HELICOPTER_MEMBERS = {"rn07_$c029",	"rn07_$c030"} 
  74.  
  75. 	-- TRIGGERS --  
  76. 		 
  77. 		TRIGGER_BED						= "rn07_$Tbed" 
  78. 		TRIGGER_ELEVATOR_1			= "rn07_$Televator_1" 
  79. 		TRIGGER_ELEVATOR_2			= "rn07_$Televator_2" 
  80. 		TRIGGER_ELEVATOR_3			= "rn07_$Televator_3" 
  81. 		TRIGGER_ELEVATOR_4			= "rn07_$Televator_4" 
  82. 		TRIGGER_FRONT_DOOR			= "rn07_$Tfront_door" 
  83. 		TRIGGER_AMBULANCE				= "rn07_$Tambulance" 
  84. 		TRIGGER_HELICOPTER			= "rn07_$Thelicopter" 
  85. 		TRIGGER_SAINTS_HQ				= "rn07_$Tsaints_hq" 
  86. 		TRIGGER_SAINTS_HQ_LOCAL		= "rn07_$Tsaints_hq_local" 
  87. 		TRIGGER_SAINTS_HQ_REMOTE	= "rn07_$Tsaints_hq_remote" 
  88. 		TRIGGER_PARKING_FOOT			= "rn07_$Tparking_foot" 
  89. 		TRIGGER_PARKING_HELICOPTER = "rn07_$Tparking_helicopter" 
  90. 		TRIGGER_STAIRWELL				= "rn07_$Tstairwell" -- 2nd floor stairwell 
  91.  
  92. 		TRIGGER_BREADCRUMB_1			= "rn07_$t000" 
  93. 		TRIGGER_BREADCRUMB_2			= "rn07_$t001" 
  94. 		TRIGGER_BREADCRUMB_3			= "rn07_$t002" 
  95. 		TRIGGER_BREADCRUMB_4			= "rn07_$t003" 
  96. 		TRIGGER_BREADCRUMB_5			= "rn07_$t004" 
  97. 		TRIGGER_BREADCRUMB_6			= "rn07_$t005" 
  98. 		TRIGGER_BREADCRUMB_7			= "rn07_$t006" 
  99. 		TRIGGER_BREADCRUMB_8			= "rn07_$t007" 
  100.  
  101. 		-- List of all triggers, makes cleaning up more convenient 
  102. 		TABLE_ALL_TRIGGERS		= {	TRIGGER_BED, TRIGGER_ELEVATOR_1, TRIGGER_ELEVATOR_2, TRIGGER_ELEVATOR_3, 
  103. 												TRIGGER_ELEVATOR_4, TRIGGER_FRONT_DOOR, TRIGGER_AMBULANCE, TRIGGER_HELICOPTER, 
  104. 												TRIGGER_SAINTS_HQ, TRIGGER_PARKING_FOOT, TRIGGER_PARKING_HELICOPTER, 
  105. 												TRIGGER_STAIRWELL, TRIGGER_BREADCRUMB_1, TRIGGER_BREADCRUMB_2, TRIGGER_BREADCRUMB_3, 
  106. 												TRIGGER_BREADCRUMB_4, TRIGGER_BREADCRUMB_5, TRIGGER_BREADCRUMB_6, 
  107. 												TRIGGER_BREADCRUMB_7, TRIGGER_BREADCRUMB_8}		 
  108.  
  109. 	-- VEHICLES -- 
  110. 		VEHICLE_AMBULANCE			= "rn07_$Vambulance" 
  111. 		VEHICLE_HELICOPTER		= "rn07_$Vhelicopter" 
  112. 		VEHICLE_RONIN_HELI		= "rn07_$Vronin_heli" 
  113.  
  114. 	-- CHARACTERS -- 
  115. 		CHARACTER_GAT				= "rn07_$Cgat" 
  116. 		CHARACTER_GAT_NORMAL		= "rn07_$Cgat_normal" 
  117. 		CHARACTER_RPG_GUY			= "rn07_$c000" 
  118.  
  119. 	-- ITEMS -- 
  120. 		SHOCK_PADDLES				= {	"rn07_$Ishock_paddles_floor_1", "rn07_$Ishock_paddles_floor_2", 
  121. 												"rn07_$Ishock_paddles_floor_3", "rn07_$Ishock_paddles_floor_4"} 
  122.  
  123. 	-- NAVPOINTS 
  124.  
  125. 		-- the mission start locations 
  126. 		NAVPOINT_LOCAL_PLAYER_START					= "rn07_$Nlocal_player_start" 
  127. 		NAVPOINT_REMOTE_PLAYER_START					= "rn07_$Nremote_player_start" 
  128.  
  129. 		NAVPOINT_ROOFTOP									= "rn07_$Nrooftop" -- Rooftop near helipad 
  130. 		NAVPOINT_ROOFTOP_GAT								= "rn07_$Nrooftop_gat" -- Next to NAVPOINT_ROOFTOP 
  131.  
  132. 		NAVPOINT_CHECKPOINT_GAT							= "rn07_$n089" 
  133.  
  134. 		NAVPOINT_LOCAL_MISSION_END						= "rn07_$Nlocal_mission_end" 
  135. 		NAVPOINT_REMOTE_MISSION_END					= "rn07_$Nremote_mission_end" 
  136. 		NAVPOINT_HOSPITAL_CENTER						= "rn07_$Nhospital_center" 
  137.  
  138. 	-- PATROL NAVPOINTS 
  139.  
  140. 		PATROL_NAVPOINTS_FLOOR_1	= {	"rn07_$n043",	"rn07_$n044",	"rn07_$n045", "rn07_$n046",  
  141. 												"rn07_$n047",	"rn07_$n048"} 
  142.  
  143. 		PATROL_NAVPOINTS_FLOOR_2	= {	"rn07_$n018",	"rn07_$n019",	"rn07_$n020", "rn07_$n021",  
  144. 												"rn07_$n022",	"rn07_$n023",	"rn07_$n024" } 
  145.  
  146. 		PATROL_NAVPOINTS_FLOOR_3	= {	"rn07_$n067",	"rn07_$n068",	"rn07_$n069", "rn07_$n070",  
  147. 												"rn07_$n071",	"rn07_$n072",	"rn07_$n073" } 
  148.  
  149. 		PATROL_NAVPOINTS_FLOOR_4	= {	"rn07_$n086",	"rn07_$n087",	"rn07_$n088"} 
  150.  
  151. 		PATROL_NAVPOINT_TABLES	= {	["floor_1"]	=	PATROL_NAVPOINTS_FLOOR_1, 
  152. 												["floor_2"]	=	PATROL_NAVPOINTS_FLOOR_2, 
  153. 												["floor_3"] =	PATROL_NAVPOINTS_FLOOR_3, 
  154. 												["floor_4"] =	PATROL_NAVPOINTS_FLOOR_4} 
  155.  
  156. 		-- The navpoints where we can spawn Ronin lieutenants in the key area 
  157. 		SPAWN_NAVPOINT_TABLES	=	 
  158. 			{ 
  159. 				["floor_2_area_1"] = {	"rn07_$n000", "rn07_$n001", "rn07_$n002", "rn07_$n003", "rn07_$n004", "rn07_$n005"}; 
  160.  
  161. 				["floor_2_area_2"] = {	"rn07_$n006", "rn07_$n007", "rn07_$n008", "rn07_$n009", "rn07_$n010", "rn07_$n011"}; 
  162. 	 
  163. 				["floor_2_area_5"] = {	"rn07_$n012", "rn07_$n013", "rn07_$n014", "rn07_$n015", "rn07_$n016", "rn07_$n017"}; 
  164.  
  165. 				["floor_1_area_1"] = {	"rn07_$n025", "rn07_$n026", "rn07_$n027", "rn07_$n028", "rn07_$n029", "rn07_$n030"}; 
  166.  
  167. 				["floor_1_area_2"] = {	"rn07_$n037", "rn07_$n038", "rn07_$n039", "rn07_$n040", "rn07_$n041", "rn07_$n042"}; 
  168. 	 
  169. 				["floor_1_area_4"] = {	"rn07_$n031", "rn07_$n032", "rn07_$n033", "rn07_$n034", "rn07_$n035", "rn07_$n036"}; 
  170.  
  171. 				["floor_3_area_1"] = {	"rn07_$n049", "rn07_$n050", "rn07_$n051", "rn07_$n052", "rn07_$n053", "rn07_$n054"}; 
  172.  
  173. 				["floor_3_area_2"] = {	"rn07_$n055", "rn07_$n056", "rn07_$n057", "rn07_$n058", "rn07_$n059", "rn07_$n060"}; 
  174. 	 
  175. 				["floor_3_area_5"] = {	"rn07_$n061", "rn07_$n062", "rn07_$n063", "rn07_$n064", "rn07_$n065", "rn07_$n066"}; 
  176.  
  177. 				["floor_4_area_1"] = {	"rn07_$n080", "rn07_$n081", "rn07_$n082", "rn07_$n083", "rn07_$n084", "rn07_$n085"}; 
  178.  
  179. 				["floor_4_area_3"] = {	"rn07_$n074", "rn07_$n075", "rn07_$n076", "rn07_$n077", "rn07_$n078", "rn07_$n079"}; 
  180. 				 
  181. 			} 
  182.  
  183. 	-- MOVERS 
  184. 		 
  185. 			-- Two doors exiting onto rooftop near the heli pad 
  186. 			DOOR_FLOOR_4_EXIT		= "rn07_$Dfloor4_exit" 
  187. 			DOOR_FLOOR_4_EXIT_2	= "rn07_$Dfloor4_exit2"		 
  188.  
  189. 			-- Main exit on first floor 
  190. 			DOOR_MAIN_1					= "rn07_$Dmain1" 
  191. 			DOOR_MAIN_2					= "rn07_$Dmain2" 
  192.  
  193. 	-- HELPTEXT 
  194.  
  195. 		-- localized helptext messages 
  196.  
  197. 			HELPTEXT_FAILURE_GAT_DIED					= "rn07_failure_gat_died" 
  198. 			HELPTEXT_FAILURE_GAT_ABANDONED			= "rn07_failure_gat_abandoned" 
  199. 			HELPTEXT_FAILURE_HELICOPTER_DESTROYED	= "rn07_failure_helicopter_destroyed" 
  200.  
  201. 			HELPTEXT_HUD_GAT_HEALTH						= "rn07_hud_gat_health"		-- "Johnny Gat's Health" 
  202.  
  203. 			HELPTEXT_PROMPT_BED					= "rn07_prompt_bed"					-- "Go to the foot of Gat's bed."  
  204. 			-- "Press Y to wheel Gat's bed around. L Stick steers." (Helptext or hospital system?) 
  205. 			HELPTEXT_PROMPT_BED_SPRINT			= "rn07_prompt_sprint_gurney"		-- "Hold {SPRINT_IMG} to sprint with the gurney" 
  206. 			HELPTEXT_PROMPT_EXIT_HOSPITAL		= "rn07_prompt_exit_hospital"		-- "Get Gat out of the hospital!" 
  207. 			HELPTEXT_PROMPT_FRONT_DOOR			= "rn07_prompt_front_door"			-- "Head to the front door." 
  208. 			HELPTEXT_PROMPT_AMBULANCE			= "rn07_prompt_ambulance"			-- "Head to the ambulance!" 
  209. 			HELPTEXT_PROMPT_RETURN_ELEVATOR	= "rn07_prompt_return_elevator"	-- "Head back to the elevator!"  
  210. 			HELPTEXT_PROMPT_ENTER_HELICOPTER = "rn07_prompt_enter_helicopter" -- "Get in the helicopter!"  
  211. 			HELPTEXT_PROMPT_BASE					= "rn07_prompt_base"					-- "Head back to base!"  
  212. 			HELPTEXT_PROMPT_RETURN_GAT			= "rn07_prompt_return_gat"			-- "Get back to Gat before the Yakuza get to him!" 
  213. 			HELPTEXT_PROMPT_SHOCK_PADDLES		= "rn07_prompt_shock_paddles"		-- "Find some shock paddles and revive Gat!"  
  214. 			HELPTEXT_PROMPT_PARKING				= "rn07_prompt_parking"				-- "Wait for your partner in the parking lot" 
  215. 			HELPTEXT_PROMPT_ROOFTOP_ELEVATOR = "rn07_prompt_rooftop_elevator" -- "Take the elevator to the rooftop" 
  216. 			HELPTEXT_PROMPT_CARDIAC_ARREST	= "rn07_prompt_cardiac_arrest"	-- "Gat's gone into cardiac arrest!" 
  217. 			HELPTEXT_PROMPT_USE_PADDLES		= "rn07_prompt_use_paddles"		-- "Use the shock paddles to revive Gat." 
  218. 			HELPTEXT_PROMPT_HAVE_PULSE			= "rn07_prompt_have_pulse"			-- "We have a pulse!" 
  219. 			HELPTEXT_PROMPT_RELEASE_BED		= "rn07_prompt_release_bed"		-- ## Press  to release the bed. 
  220. 			HELPTEXT_PROMPT_ELEVATOR			= "rn07_prompt_elevator"			-- Go to the elevator. 
  221. 			HELPTEXT_PROMPT_HELICOPTER_MED	= "rn07_prompt_helicopter_med"	-- You found some medicine for Gat! 
  222. 			HELPTEXT_PROMPT_NO_GAT_ELEVATOR	= "rn07_prompt_no_gat_elevator"	-- "Don't leave the floor without Gat" 
  223.  
  224. 			HELPTEXT_PROMPT_GAT_HEALTH_1		= "rn07_prompt_gat_health_1" 
  225. 			HELPTEXT_PROMPT_GAT_HEALTH_2		= "rn07_prompt_gat_health_2" 
  226. 			HELPTEXT_PROMPT_GAT_HEALTH_3		= "rn07_prompt_gat_health_3" 
  227.  
  228. 			HELPTEXT_PROMPT_REENTER_HELI		= "rn07_prompt_reenter_heli"		-- Get back in the helicopter. 
  229.  
  230. 			-- coop only prompts 
  231. 			HELPTEXT_PROMPT_STAIRWELL			= "rn07_prompt_stairwell"			-- "Take the stairs to the rooftop" 
  232. 			HELPTEXT_PROMPT_PICKUP				= "rn07_prompt_pickup"				-- "Pickup your partner and Gat in the parking lot" 
  233. 			HELPTEXT_PROMPT_HOLD_GROUND		= "rn07_prompt_hold_ground"		-- "Hold your ground until your homie picks you up!" 
  234. 			HELPTEXT_PROMPT_DEFEND_HELICOPTER= "rn07_prompt_defend_helicopter"-- "Defend the helicopter until your friends arrive!" 
  235.  
  236. 	-- CHECKPOINTS 
  237. 		 
  238. 		CHECKPOINT_START						= MISSION_START_CHECKPOINT -- defined in ug_lib.lua 
  239. 		CHECKPOINT_HOSPITAL					= "rn07_checkpoint_hospital" --  
  240.  
  241. 	-- HOSPITAL AREAS 
  242.  
  243. 	--[[ - Floors listed here for convenience, not needed by code 
  244. 		FLOOR_1_AREA_1							= "floor_1_area_1"	-- Elevator from 2nd floor, operating room. 
  245. 		FLOOR_1_AREA_2							= "floor_1_area_2"	-- Elevator to roof. 
  246. 		FLOOR_1_AREA_3							= "floor_1_area_3"	-- Reception area/ waiting room   
  247. 		FLOOR_1_AREA_4							= "floor_1_area_4"	-- Outdoors 
  248.  
  249. 		FLOOR_2_AREA_1							= "floor_2_area_1"	-- Gat's hospital room 
  250. 		FLOOR_2_AREA_2							= "floor_2_area_2"	-- Nurses station, hallway loop  
  251. 		FLOOR_2_AREA_3							= "floor_2_area_3"	-- Two adjacent operating rooms 
  252. 		FLOOR_2_AREA_4							= "floor_2_area_4"	-- Large operating room 
  253. 		FLOOR_2_AREA_5							= "floor_2_area_5"	-- Elevator to 1st floor 
  254. 	]] 
  255.  
  256. 		-- Index of first navpoint that the Ronin whould pathfind to in the floor's patrol path 
  257. 		AREA_PATROL_START	=  
  258. 			{	["floor_2_area_1"] = 1,	["floor_2_area_2"] = 3, ["floor_2_area_5"] = 7, 
  259. 				["floor_1_area_1"] = 1, ["floor_1_area_2"] = 6, ["floor_1_area_4"] = 3, 
  260. 				["floor_3_area_1"] = 1,	["floor_3_area_2"] = 3, ["floor_3_area_5"] = 7, 
  261. 				["floor_4_area_1"] = 1,	["floor_4_area_3"] = 3 
  262. 			} 
  263.  
  264. 		-- Direction along the patrol route that the Ronin need to follow to get to the target area 
  265. 		AREA_FLOOR_PATROL_DIRECTION =  
  266. 			{ 
  267. 				["floor_2_area_1"] = {	["floor_2_area_2"] = "forward",	["floor_2_area_3"] = "forward", 
  268. 												["floor_2_area_4"] = "forward",	["floor_2_area_5"] = "forward"}; 
  269.  
  270. 				["floor_2_area_2"] = {	["floor_2_area_1"] = "reverse",	["floor_2_area_3"] = "forward", 
  271. 												["floor_2_area_4"] = "forward",	["floor_2_area_5"] = "forward"}; 
  272.  
  273. 				["floor_2_area_3"] = {	["floor_2_area_1"] = "reverse",	["floor_2_area_2"] = "reverse", 
  274. 												["floor_2_area_4"] = "forward",	["floor_2_area_5"] = "forward"}; 
  275.  
  276. 				["floor_2_area_4"] = {	["floor_2_area_1"] = "reverse",	["floor_2_area_2"] = "reverse", 
  277. 												["floor_2_area_3"] = "reverse",	["floor_2_area_5"] = "forward"}; 
  278.  
  279. 				["floor_2_area_5"] = {	["floor_2_area_1"] = "reverse",	["floor_2_area_2"] = "reverse", 
  280. 												["floor_2_area_3"] = "reverse",	["floor_2_area_4"] = "reverse"}; 
  281.  
  282. 				["floor_1_area_1"] = {	["floor_1_area_2"] = "forward",	["floor_1_area_3"] = "forward", 
  283. 												["floor_1_area_4"] = "forward"}; 
  284.  
  285. 				["floor_1_area_2"] = {	["floor_1_area_1"] = "reverse",	["floor_1_area_3"] = "reverse", 
  286. 												["floor_1_area_4"] = "reverse"}; 
  287.  
  288. 				["floor_1_area_3"] = {	["floor_1_area_1"] = "reverse",	["floor_1_area_2"] = "forward", 
  289. 												["floor_1_area_4"] = "forward"}; 
  290.  
  291. 				["floor_1_area_4"] = {	["floor_1_area_1"] = "reverse",	["floor_1_area_2"] = "forward", 
  292. 												["floor_1_area_3"] = "forward"}; 
  293.  
  294. 				["floor_3_area_1"] = {	["floor_3_area_2"] = "forward",	["floor_3_area_3"] = "forward", 
  295. 												["floor_3_area_4"] = "forward",	["floor_3_area_5"] = "forward"}; 
  296.  
  297. 				["floor_3_area_2"] = {	["floor_3_area_1"] = "reverse",	["floor_3_area_3"] = "forward", 
  298. 												["floor_3_area_4"] = "forward",	["floor_3_area_5"] = "forward"}; 
  299.  
  300. 				["floor_3_area_3"] = {	["floor_3_area_1"] = "reverse",	["floor_3_area_2"] = "reverse", 
  301. 												["floor_3_area_4"] = "forward",	["floor_3_area_5"] = "forward"}; 
  302.  
  303. 				["floor_3_area_4"] = {	["floor_3_area_1"] = "reverse",	["floor_3_area_2"] = "reverse", 
  304. 												["floor_3_area_3"] = "reverse",	["floor_3_area_5"] = "forward"}; 
  305.  
  306. 				["floor_3_area_5"] = {	["floor_3_area_1"] = "reverse",	["floor_3_area_2"] = "reverse", 
  307. 												["floor_3_area_3"] = "reverse",	["floor_3_area_4"] = "reverse"}; 
  308.  
  309. 				["floor_4_area_1"] = {	["floor_4_area_2"] = "forward",	["floor_4_area_3"] = "forward"}; 
  310.  
  311. 				["floor_4_area_2"] = {	["floor_4_area_1"] = "reverse",	["floor_4_area_3"] = "forward"}; 
  312.  
  313. 				["floor_4_area_3"] = {	["floor_4_area_1"] = "reverse",	["floor_4_area_2"] = "reverse"}; 
  314. 			} 
  315.  
  316. 		-- Areas where Ronin can safely spawn without popping 
  317. 		FLOOR_1_SAFE_SPAWN_AREAS = 
  318. 			{ 
  319. 				["floor_1_area_1"] = {	"floor_1_area_2",	"floor_1_area_4"}; 
  320.  
  321. 				["floor_1_area_2"] = {	"floor_1_area_1",	"floor_1_area_4"}; 
  322.  
  323. 				["floor_1_area_3"] = {	"floor_1_area_2",	"floor_1_area_4"}; 
  324.  
  325. 				["floor_1_area_4"] = {	"floor_1_area_1",	"floor_1_area_2"}; 
  326. 			} 
  327. 		FLOOR_2_SAFE_SPAWN_AREAS = 
  328. 			{ 
  329. 				["floor_2_area_1"] = {	"floor_2_area_2",	"floor_2_area_5"}; 
  330.  
  331. 				["floor_2_area_2"] = {	"floor_2_area_1",	"floor_2_area_5"}; 
  332.  
  333. 				["floor_2_area_3"] = {	"floor_2_area_1",	"floor_2_area_2",	"floor_2_area_5"}; 
  334.  
  335. 				["floor_2_area_4"] = {	"floor_2_area_1",	"floor_2_area_2"}; 
  336.  
  337. 				["floor_2_area_5"] = {	"floor_2_area_1",	"floor_2_area_2"}; 
  338. 			} 
  339. 		FLOOR_3_SAFE_SPAWN_AREAS = 
  340. 			{ 
  341. 				["floor_3_area_1"] = {	"floor_3_area_2",	"floor_3_area_5"}; 
  342.  
  343. 				["floor_3_area_2"] = {	"floor_3_area_1",	"floor_3_area_5"}; 
  344.  
  345. 				["floor_3_area_3"] = {	"floor_3_area_1",	"floor_3_area_2",	"floor_3_area_5"}; 
  346.  
  347. 				["floor_3_area_4"] = {	"floor_3_area_1",	"floor_3_area_2"}; 
  348.  
  349. 				["floor_3_area_5"] = {	"floor_3_area_1",	"floor_3_area_2"}; 
  350. 			} 
  351. 		FLOOR_4_SAFE_SPAWN_AREAS = 
  352. 		{ 
  353. 				["floor_4_area_1"] = {	"floor_4_area_3"}; 
  354.  
  355. 				["floor_4_area_2"] = {	"floor_4_area_3"}; 
  356.  
  357. 				["floor_4_area_3"] = {	"floor_4_area_1"}; 
  358. 		} 
  359. 		 
  360. 		-- Maps from floor -> safe spawn area table 
  361. 		FLOOR_SAFE_SPAWN_TABLE	= {["floor_1"] = FLOOR_1_SAFE_SPAWN_AREAS, ["floor_2"]=FLOOR_2_SAFE_SPAWN_AREAS, 
  362. 											["floor_3"] = FLOOR_3_SAFE_SPAWN_AREAS, ["floor_4"]=FLOOR_4_SAFE_SPAWN_AREAS} 
  363.  
  364. 		-- Area in which each patrol navpoint is located 
  365. 		FLOOR_1_PATROL_NAVPOINT_AREAS =	{	"floor_1_area_1",	"floor_1_area_3",	"floor_1_area_3", 
  366. 														"floor_1_area_3", "floor_1_area_2", "floor_1_area_2"} 
  367.  
  368. 		FLOOR_2_PATROL_NAVPOINT_AREAS =	{	"floor_2_area_1",	"floor_2_area_2",	"floor_2_area_2", 
  369. 														"floor_2_area_3", "floor_2_area_3", "floor_2_area_4", 
  370. 														"floor_2_area_5"} 
  371.  
  372. 		FLOOR_3_PATROL_NAVPOINT_AREAS =	{	"floor_3_area_1",	"floor_3_area_2",	"floor_3_area_2", 
  373. 														"floor_3_area_3", "floor_3_area_3", "floor_3_area_4", 
  374. 														"floor_3_area_5"} 
  375.  
  376. 		FLOOR_4_PATROL_NAVPOINT_AREAS =	{	"floor_4_area_1",	"floor_4_area_2",	"floor_4_area_3"} 
  377.  
  378. 		FLOOR_PATROL_NAVPOINT_TABLES = {	["floor_1"] = FLOOR_1_PATROL_NAVPOINT_AREAS, 
  379. 													["floor_2"] = FLOOR_2_PATROL_NAVPOINT_AREAS, 
  380. 													["floor_3"] = FLOOR_3_PATROL_NAVPOINT_AREAS, 
  381. 													["floor_4"] = FLOOR_4_PATROL_NAVPOINT_AREAS} 
  382.  
  383. 		-- Number of areas on each floor 
  384. 		AREAS_PER_FLOOR				= {["floor_1"]=4, ["floor_2"]=5, ["floor_3"]=5, ["floor_4"]=3 } 
  385.  
  386. 	-- Areas associated with each entrance (built in rn07_initialize_common) 
  387. 		ENTRANCE_TARGET_AREAS	=	{} 
  388.  
  389. 	-- MINIMAP MODES, highest to lowest priority 
  390. 	MINIMAP_MODE_PADDLES		= 0	-- Only displaying paddle icons 
  391. 	MINIMAP_MODE_GAT			= 1	-- Only displaying Gat's icon 
  392. 	MINIMAP_MODE_HELI			= 2	-- Only displaying the helicopter's icon 
  393. 	MINIMAP_MODE_LOCATIONS	= 3	-- Only displaying location icons 
  394. 	MINIMAP_MODE_NONE			= 4	-- Not displaying any icons on the map 
  395.  
  396. 	MINIMAP_MODE_FIRST		= MINIMAP_MODE_PADDLES 
  397. 	MINIMAP_MODE_LAST			= MINIMAP_MODE_LOCATIONS 
  398.  
  399. 	PLAYER_SYNC	=	 
  400. 	{ 
  401. 		[LOCAL_PLAYER]		= SYNC_LOCAL, 
  402. 		[REMOTE_PLAYER]	= SYNC_REMOTE, 
  403. 	} 
  404.  
  405. 	RN01_RONIN_ATTACK_PERSONAS	= { 
  406. 		["AM_Ron2"]	=	"AMRON2", 
  407.  
  408. 		["AF_Ron1"]	=	"AFRON1", 
  409.  
  410. 		["WM_Ron1"]	=	"WMRON1", 
  411.  
  412. 		["WF_Ron1"]	=	"WFRON1", 
  413. 		["WF_Ron2"]	=	"WFRON2", 
  414. 	} 
  415.  
  416. 	PARKING_SPAWN_AMBULANCE = "parking_spots_$parking_896" 
  417.  
  418. 	-- Dialogue lines 
  419. 	Rn07_bicker_conversations =  
  420. 	{ 
  421. 		{ 
  422. 			{ "PLAYER_RON7_BICKER1_L1", LOCAL_PLAYER, 0.0 }, 
  423. 			{ "RON7_BICKER1_L2", CHARACTER_GAT, 0.0 }, 
  424. 		}; 
  425. 		{ 
  426. 			{ "RON7_BICKER2_L1", CHARACTER_GAT, 0.0 }, 
  427. 			{ "PLAYER_RON7_BICKER2_L2", LOCAL_PLAYER, 0.0 }, 
  428. 		}; 
  429. 		{ 
  430. 			{ "PLAYER_RON7_BICKER3_L1", LOCAL_PLAYER, 0.0 }, 
  431. 			{ "RON7_BICKER3_L2", CHARACTER_GAT, 0.0 }, 
  432. 		}; 
  433. 		{ 
  434. 			{ "RON7_BICKER4_L1", CHARACTER_GAT, 0.0 }, 
  435. 			{ "PLAYER_RON7_BICKER4_L2", LOCAL_PLAYER, 0.0 }, 
  436. 		}; 
  437. 		{ 
  438. 			{ "PLAYER_RON7_BICKER5_L1", LOCAL_PLAYER, 0.0 }, 
  439. 			{ "RON7_BICKER5_L2", CHARACTER_GAT, 0.0 }, 
  440. 		}; 
  441. 	} 
  442.  
  443. 	Rn07_mission_conversations =  
  444. 	{ 
  445. 		["ambulance"] =  
  446. 			{ 
  447. 				{ "PLAYER_RON7_AMBULANCE_L1", LOCAL_PLAYER, 1 }, 
  448. 				{ "RON7_AMBULANCE_L2", CHARACTER_GAT, 1 }, 
  449. 			}; 
  450. 		["heli"] =  
  451. 			{ 
  452. 				{ "GAT_RON7_HELI_01", CHARACTER_GAT, 1 }, 
  453. 			}; 
  454. 	} 
  455.  
  456. -- Global Variables (First letter caps == Global Variable) 
  457.  
  458. 	-- Threads 
  459. 	Thread_remote_player				= -1	-- Main mission thread for remote player in Coop 
  460. 	Thread_floor_patrols				= {	["floor_1"] = -1,	["floor_2"] = -1, ["floor_3"] = -1, ["floor_4"] = -1} 
  461. 	Thread_syphon						= INVALID_THREAD_HANDLE 
  462.  
  463. 	-- Player locations 
  464. 	Local_player_location			= "other dimension" 
  465. 	Remote_player_location			= "other dimension" 
  466.  
  467. 	-- Progress flags 
  468. 	Cutscene_played					= false 
  469. 	Bed_foot_reached					= false 
  470. 	Helicopter_entered				= {[LOCAL_PLAYER] = false, [REMOTE_PLAYER] = false} 
  471. 	Local_reached_parking			= false -- Local player arrived at parking lot 
  472. 	Remote_reached_parking			= false -- Remote player arrived at parking lot 
  473.  
  474. 	-- Misc 
  475. 	Gat_in_cardiac_arrest			= false -- Is Gat in cardiac arrest? 
  476. 	Gat_too_far							= false -- Is Gat too far from the player? 
  477. 	Pushing_gat							= false -- Should the local player be pushing Gat around? 
  478.  
  479. 	Next_navpoint_index				= 1 -- Index into current spawn target where next lieutenant will spawn 
  480. 	Min_wave_size						= 4 
  481. 	Max_wave_size						= 5	 
  482.  
  483. 		-- Number of lieutenants alive on each floor 
  484. 	Floor_living_lieutenants				= {	["floor_1"] = 0,	["floor_2"] = 0, ["floor_3"] = 0, ["floor_4"] = 0} 
  485. 		-- First navpoint that the lieutenants should be pathfinding to 
  486. 	Lieutenant_first_navpoint				= {} 
  487. 	-- Path that the lieutenants should be using 
  488. 	Lieutenant_path							= {} 
  489. 		-- Floor that the lieutenant is on 
  490. 	Lieutenant_floor							= {} 
  491. 		-- Player the Lieutenant is pathfinding to 
  492. 	Lieutenant_target							= {} 
  493.  
  494. -- Called when mission starts 
  495. function rn07_start(rn07_checkpoint, is_restart) 
  496.  
  497. 	if (rn07_checkpoint == CHECKPOINT_START) then 
  498.  
  499. 		-- Determine which groups we'll need to load immediately 
  500. 		local start_groups = {GROUP_RONIN_STATIONARY, GROUP_GAT, GROUP_AMBULANCE, GROUP_OUTSIDE_HOSPITAL} 
  501. 		if (IN_COOP) then 
  502. 			local start_groups = {GROUP_RONIN_STATIONARY, GROUP_GAT, GROUP_RONIN_STATIONARY_COOP, GROUP_OUTSIDE_HOSPITAL} 
  503. 		end 
  504. 		 
  505. 		 
  506. 		if (is_restart) then 
  507.  
  508. 			-- Load starting groups. Will position the players inside of rn07_initialize_checkpoint 
  509. 			for i,group in pairs(start_groups) do 
  510. 				group_create_hidden(group, true) 
  511. 			end 
  512. 			 
  513. 		else 
  514.  
  515. 			-- Play the cutscene. Use it to create groups and position the players 
  516. 			cutscene_play("ro07-01", start_groups, {NAVPOINT_LOCAL_PLAYER_START, NAVPOINT_REMOTE_PLAYER_START}, false) 
  517. 		end 
  518.  
  519. 		for i,group in pairs(start_groups) do 
  520. 			if (group ~= GROUP_OUTSIDE_HOSPITAL) then 
  521. 				group_show(group) 
  522. 			end 
  523. 		end 
  524.  
  525. 	end 
  526.  
  527. 	rn07_initialize(rn07_checkpoint, is_restart) 
  528.  
  529. 	-- Start floor patrols 
  530. 	rn07_start_hospital_patrols() 
  531.  
  532. 	if(rn07_checkpoint == CHECKPOINT_START) then 
  533.  
  534. 		thread_new("rn07_load_later_groups") 
  535.  
  536. 		-- Local player has to get to the first floor 
  537. 		rn07_local_player_to_first_floor() 
  538. 		 
  539. 		if (not IN_COOP) then 
  540.  
  541. 			-- Player is sent to the ambulance which is destroyed by the Ronin 
  542. 			rn07_local_player_the_ambulance() 
  543.  
  544. 			-- Back into the hospital checkpoint 
  545. 			Rn07_gat_health = get_current_hit_points(CHARACTER_GAT) 
  546. 			mission_set_checkpoint(CHECKPOINT_HOSPITAL) 
  547. 			rn07_checkpoint = CHECKPOINT_HOSPITAL 
  548.  
  549. 		else -- Else, do the Coop ending 
  550.  
  551. 			-- Meet partner in the parking lot 
  552. 			rn07_local_player_get_to_parking_lot() 
  553.  
  554. 		end 
  555.  
  556. 	end -- end of CHECKPOINT_START 
  557.  
  558. 	-- Single player only 
  559. 	if (rn07_checkpoint == CHECKPOINT_HOSPITAL) then 
  560.  
  561. 		-- Player has to ge to the roof and take the Hospital's heli back to the Saint's base. 
  562. 		rn07_single_player_ending() 
  563.  
  564. 	end -- end of CHECKPOINT_HOSPITAL 
  565.  
  566. 	rn07_complete() 
  567. end 
  568.  
  569. function rn07_load_later_groups() 
  570.  
  571. 	group_create_hidden(GROUP_GAT_NORMAL, true) 
  572. 	group_create(GROUP_HELICOPTER, true) 
  573. 	group_create(GROUP_OUTSIDE_HOSPITAL, true) 
  574.  
  575. end 
  576.  
  577. function rn07_initialize(checkpoint, is_restart) 
  578.  
  579. 	mission_start_fade_out() 
  580.  
  581. 	rn07_initialize_common() 
  582. 	rn07_initialize_checkpoint(checkpoint, is_restart) 
  583. 	rn07_initialize_common_post() 
  584.  
  585. 	mission_start_fade_in() 
  586.  
  587. end 
  588.  
  589. -- Do initialization that is required for all checkpoints 
  590. function rn07_initialize_common() 
  591.  
  592. 	set_mission_author("Phillip Alexander") 
  593. 	 
  594. 	-- Check for coop being active 
  595. 	if (coop_is_active()) then 
  596. 		IN_COOP	= true 
  597. 	end 
  598.  
  599. 	-- Swap the chunk state 
  600. 	city_chunk_swap("SR2_IntDTMisHospital", "blackout", true, true, true) 
  601. 	city_chunk_swap("SR2_IntDTMisHospital02", "blackout", false, true, true) 
  602. 	city_chunk_swap("SR2_IntDTMisHospital03", "blackout", true, true, true) 
  603.  
  604. 	-- Disable the ambient ambulance parking spawn in front of the hospital 
  605. 	if (not IN_COOP) then 
  606. 		parking_spot_enable(PARKING_SPAWN_AMBULANCE, false) 
  607. 	end 
  608.  
  609. 	door_open(DOOR_MAIN_1) 
  610. 	door_open(DOOR_MAIN_2) 
  611.  
  612. 	-- Build mapping from hospital area entrances to the entrance triggers 
  613. 	for floor,num_areas in pairs(AREAS_PER_FLOOR) do 
  614. 		for area_number = 1, num_areas, 1 do 
  615. 			local area_name = floor .. "_area_" .. area_number								-- e.g. area_name = "floor_1_area_1" 
  616. 			local area_entrance_prefix = "rn07_$T" .. area_name							-- e.g. area_entrance_prefix = "rn07_$Tfloor_1_area_1" 
  617. 			local area_entrances = { trigger_get_all_with_prefix(area_entrance_prefix) } 
  618. 			if (area_entrances ~= nil) then 
  619. 				for i,entrance in pairs(area_entrances) do 
  620. 					ENTRANCE_TARGET_AREAS[entrance] = area_name 
  621. 				end 
  622. 			end 
  623. 		end 
  624. 	end 
  625.  
  626. 	-- Overload Ronin personas 
  627. 	persona_override_group_start(RN01_RONIN_ATTACK_PERSONAS,POT_SITUATIONS[POT_ATTACK], "RO07_ATTACK") 
  628. 	 
  629. 	--Dismiss the player's party 
  630. 	party_dismiss_all() 
  631. 	party_set_recruitable(false) 
  632.  
  633. 	-- Don't let the players knock the heli off of the roof 
  634. 	vehicle_prevent_explosion_fling(VEHICLE_HELICOPTER,true) 
  635.  
  636. 	-- Enable failure conditions 
  637. 	set_unjackable_flag(VEHICLE_HELICOPTER, true) 
  638. 	turn_invulnerable(VEHICLE_HELICOPTER, false) 
  639. 	on_vehicle_destroyed("rn07_failure_helicopter_destroyed", VEHICLE_HELICOPTER) 
  640.  
  641. 	-- Override the npc respawn distance 
  642. 	npc_respawn_dist_override(LIEUTENANT_RESPAWN_DISTANCE) 
  643.  
  644. 	-- Enable the area-entrance triggers for player tracking 
  645. 	rn07_setup_player_tracking_triggers() 
  646.  
  647. 	-- Set Ronin notoriety to 3 
  648. 	notoriety_set_min("Ronin",3) 
  649. 	notoriety_set_max("Ronin",3) 
  650. 	notoriety_set("Ronin",3) 
  651.  
  652. 	-- Start processing the minimap 
  653. 	thread_new("rn07_process_minimap", LOCAL_PLAYER) 
  654. 	if (IN_COOP) then 
  655. 		thread_new("rn07_process_minimap", REMOTE_PLAYER) 
  656. 	end 
  657.  
  658. 	thread_new("rn07_play_dialogue") 
  659.  
  660. 	thread_new("rn07_control_grenade_slot") 
  661.  
  662. end 
  663.  
  664. function rn07_initialize_common_post() 
  665.  
  666. 	-- Enable the Gat died failure conditions 
  667. 	on_death("rn07_failure_gat_died", CHARACTER_GAT) 
  668.  
  669. 	-- Handle gat taking damage in script 
  670. 	on_take_damage("rn07_handle_gat_damaged",CHARACTER_GAT) 
  671. 	turn_invulnerable(CHARACTER_GAT, false) 
  672. 	set_max_hit_points(CHARACTER_GAT, GAT_HIT_POINTS) 
  673. 	hud_bar_on(0, "Health", HELPTEXT_HUD_GAT_HEALTH, GAT_HIT_POINTS) 
  674.  
  675. 	-- Don't let the gurney do things that a gurney shouldn't do 
  676. 	character_allow_ragdoll(CHARACTER_GAT,false) 
  677. 	character_prevent_flinching(CHARACTER_GAT,true) 
  678. 	inv_item_remove_all(CHARACTER_GAT) 
  679. 	npc_combat_enable(CHARACTER_GAT,false) 
  680. 	set_attack_enemies_flag(CHARACTER_GAT, false)  
  681. 	set_attack_peds_flag(CHARACTER_GAT, false)  
  682. 	set_attack_player_flag(CHARACTER_GAT, false) 
  683. 	set_cant_flee_flag(CHARACTER_GAT, true) 
  684.  
  685. 	-- Slowly leech away Gat's health 
  686. 	Thread_syphon = thread_new("rn07_health_syphon_gat", CHARACTER_GAT) 
  687.  
  688. end 
  689.  
  690. function rn07_start_hospital_patrols() 
  691. 	Thread_floor_patrols["floor_1"] = thread_new("rn07_patrol_floor","floor_1") 
  692. 	Thread_floor_patrols["floor_2"] = thread_new("rn07_patrol_floor","floor_2") 
  693. 	Thread_floor_patrols["floor_3"] = thread_new("rn07_patrol_floor","floor_3") 
  694. 	Thread_floor_patrols["floor_4"] = thread_new("rn07_patrol_floor","floor_4") 
  695. end 
  696.  
  697. -- Do checkpoint-specific initialization 
  698. function rn07_initialize_checkpoint(checkpoint, is_restart)		 
  699.  
  700. 	if (checkpoint == CHECKPOINT_START) then 
  701.  
  702. 		set_current_hit_points(CHARACTER_GAT, GAT_HIT_POINTS * GAT_PERCENT_HEALTH) 
  703. 		hud_bar_set_value(0, GAT_HIT_POINTS * GAT_PERCENT_HEALTH, SYNC_LOCAL )		 
  704.  
  705. 		-- Put players in the initial area for player tracking. This causes enemy 
  706. 		-- waves to begin spawning. 
  707. 		Local_player_location			= "floor_2_area_1" 
  708. 		if (IN_COOP) then 
  709. 			Remote_player_location		= "floor_2_area_1" 
  710. 		end 
  711. 		 
  712. 		rn07_setup_rpg_guy() 
  713.  
  714. 		for i, npc in pairs(STATIONARY_GROUP_MEMBERS) do 
  715. 			attack(npc) 
  716. 		end 
  717. 		 
  718. 		if (IN_COOP) then 
  719. 			for i, npc in pairs(STATIONARY_GROUP_MEMBERS_COOP) do 
  720. 				attack(npc) 
  721. 			end 
  722. 		end			 
  723.  
  724. 		if (not IN_COOP) then 
  725. 			thread_new("rn07_check_ambulance_distance") 
  726. 		end 
  727. 		 
  728. 		-- Teleport players to the start location 
  729. 		if (is_restart) then 
  730. 			teleport_coop(NAVPOINT_LOCAL_PLAYER_START, NAVPOINT_REMOTE_PLAYER_START, true) 
  731. 		end 
  732.  
  733.  
  734. 	elseif (checkpoint == CHECKPOINT_HOSPITAL) then 
  735.  
  736. 		-- Start loading groups 
  737. 		rn07_load_later_groups() 
  738.  
  739. 		group_create(GROUP_GAT, true) 
  740.  
  741. 		local min_gat_hit_points = GAT_HIT_POINTS * GAT_MIN_RESTART_PERCENT_HEALTH 
  742. 		local gat_restart_hit_points = max(min_gat_hit_points, Rn07_gat_health) 
  743.  
  744. 		set_current_hit_points(CHARACTER_GAT, gat_restart_hit_points) 
  745. 		hud_bar_set_value(0, gat_restart_hit_points, SYNC_LOCAL )		 
  746. 		teleport(CHARACTER_GAT, NAVPOINT_CHECKPOINT_GAT) 
  747.  
  748. 		Local_player_location			= "floor_1_area_4" 
  749.  
  750. 		Pushing_gat = true 
  751.  
  752. 	end 
  753.  
  754. end 
  755.  
  756. -- Handles enabling/disabling of the grenade slot for the local player depending on whether 
  757. -- or not they hodling Gat. 
  758. function rn07_control_grenade_slot() 
  759.  
  760. 	local grenades_disabled = false 
  761.  
  762. 	local function should_disable_grenades() 
  763. 		if ( (not character_exists(CHARACTER_GAT)) or character_is_dead(CHARACTER_GAT)) then 
  764. 			return false 
  765. 		end 
  766. 		return character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT) 
  767. 	end 
  768.  
  769. 	while(true) do 
  770. 		thread_yield() 
  771.  
  772. 		local should_disable = should_disable_grenades() 
  773. 		if ( should_disable and (not grenades_disabled) ) then 
  774. 			inv_weapon_disable_slot(WEAPON_SLOT_THROWN, true, SYNC_LOCAL) 
  775. 			grenades_disabled = true 
  776. 			sprint_set_local_use_override(GURNEY_SPRINT_USE_OVERRIDE_MS) 
  777. 			sprint_set_local_recharge_override(GURNEY_SPRINT_RECHARGE_OVERRIDE_MS) 
  778. 		end 
  779.  
  780. 		if ( (not should_disable) and grenades_disabled) then 
  781. 			inv_weapon_disable_slot(WEAPON_SLOT_THROWN, false, SYNC_LOCAL) 
  782. 			grenades_disabled = false 
  783. 			sprint_reset_local_overrides() 
  784. 		end 
  785.  
  786. 	end 
  787.  
  788. end 
  789.  
  790. function rn07_local_player_to_first_floor() 
  791.  
  792. 	-- Start coop player's thread 
  793. 	Thread_remote_player = thread_new("rn07_start_coop") 
  794.  
  795. 	-- Send local player to the foot of Gat's bed and have him start pushing gat 
  796. 	rn07_send_to_location(TRIGGER_BED, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_BED, nil, nil, SYNC_LOCAL) 
  797. 	Pushing_gat = true 
  798. 	 
  799. 	--Wait till the player grabs the bed 
  800. 	while (not character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT)) do 
  801. 		thread_yield() 
  802. 	end 
  803.  
  804. 	-- Tell the player he can sprint when he's holding the bed 
  805. 	mission_help_table_nag(HELPTEXT_PROMPT_BED_SPRINT, "", "", SYNC_LOCAL) 
  806. 	delay(5.0) 
  807. 	 
  808. 	-- Send local player to the 2nd floor elevator 
  809. 	rn07_send_to_location({TRIGGER_BREADCRUMB_4, TRIGGER_ELEVATOR_2}, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_EXIT_HOSPITAL, nil, nil, SYNC_LOCAL) 
  810.  
  811. 	if(not character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT)) then 
  812.  
  813. 		-- If the player isn't pushing Gat, tell them not to leave w/out him. 
  814. 		mission_help_table_nag(HELPTEXT_PROMPT_NO_GAT_ELEVATOR) 
  815. 		 
  816. 		local close_enough = get_dist(LOCAL_PLAYER, TRIGGER_ELEVATOR_2) < 1.5 
  817. 		local has_gat = character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT) 
  818. 		while( (not has_gat) or (not close_enough) ) do 
  819. 			thread_yield() 
  820. 		end 
  821. 	end 
  822. 	 
  823. 	-- Elevator was reached, warp to next floor 
  824. 	player_controls_disable(LOCAL_PLAYER) 
  825. 	fade_out(1.0,{0,0,0}, SYNC_LOCAL) 
  826. 	fade_out_block() 
  827. 	teleport(LOCAL_PLAYER, TRIGGER_ELEVATOR_1) 
  828.  
  829. 	rn07_set_hit_points_gat(GAT_HIT_POINTS, CHARACTER_GAT) 
  830. 	fade_in(1.0, SYNC_LOCAL) 
  831. 	player_controls_enable(LOCAL_PLAYER) 
  832.  
  833. 	Local_player_location = "floor_1_area_2" 
  834.  
  835. 	-- Tell the player that Medicine was found for Gat. 
  836. 	mission_help_table_nag(HELPTEXT_PROMPT_HELICOPTER_MED, "", "", SYNC_LOCAL) 
  837. 	delay(3.0) 
  838.  
  839. 	-- Send local player to the front door 
  840. 	group_show(GROUP_OUTSIDE_HOSPITAL) 
  841.  
  842. end 
  843.  
  844. function rn07_local_player_the_ambulance() 
  845.  
  846. 	-- Send player to the ambulance, make the rpg guy and ambulance invulnerable for now 
  847. 	local thread_send_to_ambulance = thread_new("rn07_send_to_ambulance") 
  848. 	turn_invulnerable(CHARACTER_RPG_GUY, false) 
  849. 	turn_invulnerable(VEHICLE_AMBULANCE, false) 
  850.  
  851. 	on_vehicle_destroyed("rn07_ambulance_destroyed",VEHICLE_AMBULANCE) 
  852.  
  853. 	while(not vehicle_is_destroyed(VEHICLE_AMBULANCE)) do 
  854. 		thread_yield() 
  855. 	end 
  856.  
  857. 	-- Clean-up leftovers from send-to-front-door, send-to-ambulance 
  858. 	thread_kill(thread_send_to_ambulance) 
  859. 	rn07_toggle_location_reached(LOCAL_PLAYER, TRIGGER_FRONT_DOOR, SYNC_LOCAL) 
  860. 	rn07_toggle_location_reached(LOCAL_PLAYER, TRIGGER_AMBULANCE, SYNC_LOCAL) 
  861. 	rn07_location_reached[SYNC_LOCAL] = true 
  862. 	delay(1.0) 
  863.  
  864. end 
  865.  
  866. function rn07_local_player_get_to_parking_lot() 
  867.  
  868. 	-- Send to the front door 
  869. 	rn07_send_to_location(TRIGGER_FRONT_DOOR, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_FRONT_DOOR, nil, nil, SYNC_LOCAL) 
  870. 	delay(1.0) 
  871.  
  872. 	-- Send player to the parking lot 
  873. 	rn07_send_to_location(TRIGGER_PARKING_FOOT, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_PARKING, nil, nil, SYNC_LOCAL) 
  874. 	Local_reached_parking = true 
  875.  
  876. 	if(not Remote_reached_parking) then 
  877. 		-- Tell player to hold their ground, wait for the helicopter 
  878. 		thread_new("mission_help_table",HELPTEXT_PROMPT_HOLD_GROUND,"","",SYNC_LOCAL)	 
  879.  
  880. 		while(not Remote_reached_parking) do 
  881. 			thread_yield() 
  882. 		end 
  883. 	end 
  884.  
  885. 	-- Stop pushing Gat now. 
  886. 	Pushing_gat = false 
  887.  
  888. 	-- Stop overloading Ronin personas 
  889. 	persona_override_group_stop(RONIN_PERSONAS,POT_SITUATIONS[POT_ATTACK]) 
  890.  
  891. 	-- Place players,Gat in helicopter 
  892. 	fade_out(1.0,{0,0,0}, SYNC_ALL) 
  893. 	fade_out_block() 
  894.  
  895. 	rn07_swap_gats() 
  896.  
  897. 	-- TODO... need this to be bed-less gat model 
  898. 	set_unjackable_flag(VEHICLE_HELICOPTER, false) 
  899. 	vehicle_enter_teleport(CHARACTER_GAT_NORMAL, VEHICLE_HELICOPTER, 2) 
  900. 	vehicle_enter_teleport(REMOTE_PLAYER, VEHICLE_HELICOPTER, 0) 
  901. 	vehicle_enter_teleport(LOCAL_PLAYER, VEHICLE_HELICOPTER, 1) 
  902. 	delay(1.0) 
  903. 	fade_in(1.0, SYNC_ALL) 
  904. 	fade_in_block() 
  905.  
  906. 	-- Player finds some medicine in the copter, heals Gat 
  907. 	rn07_gat_entered_helicopter() 
  908.  
  909. 	Helicopter_entered[LOCAL_PLAYER] = true 
  910.  
  911. 	-- Send players to the Saints' HQ 
  912. 	trigger_enable(TRIGGER_SAINTS_HQ) 
  913. 	on_trigger("rn07_hq_reached", TRIGGER_SAINTS_HQ) 
  914. 	thread_new("rn07_send_to_location",TRIGGER_SAINTS_HQ_LOCAL, INGAME_EFFECT_VEHICLE_LOCATION, HELPTEXT_PROMPT_BASE, nil, nil, SYNC_LOCAL) 
  915. 	rn07_send_to_location(TRIGGER_SAINTS_HQ_REMOTE, INGAME_EFFECT_VEHICLE_LOCATION, HELPTEXT_PROMPT_BASE, nil, nil, SYNC_REMOTE) 
  916. 	while(true) do 
  917. 		thread_yield() 
  918. 	end 
  919. end 
  920.  
  921. function rn07_single_player_ending() 
  922.  
  923. 	-- Send player back to the 1st floor elevator 
  924. 	rn07_send_to_location({TRIGGER_BREADCRUMB_7, TRIGGER_ELEVATOR_1 }, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_RETURN_ELEVATOR, nil, nil, SYNC_LOCAL) 
  925.  
  926. 	if(not character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT)) then 
  927.  
  928. 		-- If the player isn't pushing Gat, tell them not to leave w/out him. 
  929. 		mission_help_table_nag(HELPTEXT_PROMPT_NO_GAT_ELEVATOR) 
  930. 		 
  931. 		local close_enough = get_dist(LOCAL_PLAYER, TRIGGER_ELEVATOR_1) < 1.5 
  932. 		local has_gat = character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT) 
  933. 		while( (not has_gat) or (not close_enough) ) do 
  934. 			thread_yield() 
  935. 		end 
  936. 	end 
  937.  
  938. 	-- Elevator was reached, warp to the rooftop 
  939. 	fade_out(1.0,{0,0,0}, SYNC_LOCAL) 
  940. 	player_controls_disable(LOCAL_PLAYER) 
  941. 	fade_out_block() 
  942. 	teleport(LOCAL_PLAYER, NAVPOINT_ROOFTOP) 
  943. 	door_open(DOOR_FLOOR_4_EXIT) 
  944. 	door_open(DOOR_FLOOR_4_EXIT_2) 
  945.  
  946. 	fade_in(1.0, SYNC_LOCAL) 
  947. 	player_controls_enable(LOCAL_PLAYER) 
  948.  
  949. 	delay(2.0) 
  950.  
  951. 	Local_player_location = "floor_4_area_3" 
  952.  
  953. 	rn07_send_to_location(	TRIGGER_BREADCRUMB_8,  
  954. 									INGAME_EFFECT_LOCATION, 
  955. 									nil,  
  956. 									nil,  
  957. 									nil,  
  958. 									SYNC_LOCAL) 
  959.  
  960. 	-- Stop pushing Gat 
  961. 	Pushing_gat = false 
  962.  
  963. 	-- Stop overloading Ronin personas 
  964. 	persona_override_group_stop(RONIN_PERSONAS,POT_SITUATIONS[POT_ATTACK]) 
  965.  
  966. 	trigger_enable(TRIGGER_HELICOPTER,false) 
  967. 	on_trigger("",TRIGGER_HELICOPTER) 
  968. 	marker_remove_vehicle(VEHICLE_HELICOPTER) 
  969.  
  970. 	thread_new("rn07_heli_chase_player", LOCAL_PLAYER) 
  971.  
  972. 	-- Place player,Gat in helicopter 
  973. 	fade_out(1.0,{0,0,0}, SYNC_LOCAL) 
  974. 	fade_out_block() 
  975.  
  976. 	rn07_swap_gats() 
  977.  
  978. 	-- TODO... need this to be bed-less gat model 
  979. 	set_unjackable_flag(VEHICLE_HELICOPTER, false) 
  980. 	vehicle_enter_group_teleport({LOCAL_PLAYER, CHARACTER_GAT_NORMAL}, VEHICLE_HELICOPTER) 
  981. 	vehicle_prevent_explosion_fling(VEHICLE_HELICOPTER, false) 
  982. 	delay(1.0) 
  983. 	fade_in(1.0, SYNC_LOCAL) 
  984.  
  985. 	-- Player finds some medicine in the copter, heals Gat 
  986. 	rn07_gat_entered_helicopter() 
  987. 	Helicopter_entered[LOCAL_PLAYER] = true 
  988.  
  989. 	-- Bump notoriety 
  990. 	notoriety_set_max("Ronin",4) 
  991. 	notoriety_set("Ronin",4) 
  992. 	notoriety_set_min("Ronin",4) 
  993.  
  994. 	-- Send player back to the Saints' HQ 
  995. 	rn07_send_to_location(TRIGGER_SAINTS_HQ, INGAME_EFFECT_VEHICLE_LOCATION, HELPTEXT_PROMPT_BASE, nil, nil, SYNC_LOCAL) 
  996.  
  997. end 
  998.  
  999. function rn07_send_to_ambulance() 
  1000. 	rn07_send_to_location(TRIGGER_FRONT_DOOR, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_FRONT_DOOR, nil, nil, SYNC_LOCAL) 
  1001. 	delay(1.0) 
  1002. 	rn07_send_to_location(TRIGGER_AMBULANCE, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_AMBULANCE, nil, nil, SYNC_LOCAL) 
  1003.  
  1004. 	-- Have the rpg guy blow up the ambulance if he hasn't already 
  1005. 	rn07_rpg_guy_destroy_ambulance() 
  1006.  
  1007. end 
  1008.  
  1009. -- Called whenever Gat enters the helicopter 
  1010. function rn07_gat_entered_helicopter() 
  1011.  
  1012. 	-- Handle the helicopter taking damage in script so that we can apply a  
  1013. 	-- portion of that damage to Gat. 
  1014. 	on_take_damage("rn07_handle_helicopter_damaged",VEHICLE_HELICOPTER) 
  1015. 	 
  1016. 	-- Play the Heli entered conversation 
  1017. 	Rn07_dialogue_mission = "heli" 
  1018.  
  1019. 	mission_help_table_nag(HELPTEXT_PROMPT_HELICOPTER_MED, "", "", SYNC_LOCAL) 
  1020. 	delay(3.0) 
  1021. end 
  1022.  
  1023. function rn07_setup_rpg_guy() 
  1024.  
  1025. 	-- Add the rocket launcher 
  1026. 	inv_item_add("rpg_launcher",0,CHARACTER_RPG_GUY) 
  1027. 	inv_item_equip("rpg_launcher", CHARACTER_RPG_GUY) 
  1028.  
  1029. 	-- Handle him taking damage in script 
  1030. 	on_take_damage("rn07_rpg_guy_damaged",CHARACTER_RPG_GUY) 
  1031. 	on_take_damage("rn07_ambulance_damaged",VEHICLE_AMBULANCE) 
  1032.  
  1033. 	-- Rocket d00d never misses 
  1034. 	set_perfect_aim(CHARACTER_RPG_GUY,true) 
  1035.  
  1036. 	-- Make the rpg guy invulnerable to everything 
  1037. 	turn_invulnerable(CHARACTER_RPG_GUY, false) 
  1038. 	character_disallow_ragdoll(CHARACTER_RPG_GUY) 
  1039. 	character_set_cannot_be_grabbed(CHARACTER_RPG_GUY, true) 
  1040. 	character_set_cannot_be_grabbed_by_player(CHARACTER_RPG_GUY, true) 
  1041. 	character_set_only_scripted_grabs(CHARACTER_RPG_GUY, true) 
  1042. 	character_prevent_explosion_fling(CHARACTER_RPG_GUY, true) 
  1043. 	character_prevent_flinching(CHARACTER_RPG_GUY, true) 
  1044. 	character_prevent_kneecapping(CHARACTER_RPG_GUY, true) 
  1045. 	character_set_combat_ready(CHARACTER_RPG_GUY, true, 600 * 1000) 
  1046.  
  1047. end 
  1048.  
  1049. function rn07_check_ambulance_distance() 
  1050.  
  1051. 	local function should_destroy_ambulance() 
  1052.  
  1053. 		if (get_dist(LOCAL_PLAYER, VEHICLE_AMBULANCE) < 20) then 
  1054. 			return true 
  1055. 		end 
  1056. 		if (	character_exists(CHARACTER_RPG_GUY)  
  1057. 				and (not character_is_dead(CHARACTER_RPG_GUY))  
  1058. 				and (get_dist(LOCAL_PLAYER, CHARACTER_RPG_GUY) < 20) 
  1059. 			) then 
  1060. 			return true 
  1061. 		end 
  1062. 		 
  1063. 		return false 
  1064.  
  1065. 	end 
  1066.  
  1067. 	while(not should_destroy_ambulance() ) do 
  1068. 		thread_yield() 
  1069. 	end 
  1070.  
  1071. 	rn07_rpg_guy_destroy_ambulance() 
  1072.  
  1073. end 
  1074.  
  1075. function rn07_rpg_guy_damaged(rpg_guy, attacker, damage_percent, explosion) 
  1076.  
  1077. 	if(damage_percent < 0.1) then 
  1078. 		damage_percent = 0.1 
  1079. 	end 
  1080.  
  1081. 	local new_hit_points = damage_percent * get_max_hit_points(CHARACTER_RPG_GUY) 
  1082. 	set_current_hit_points(CHARACTER_RPG_GUY, new_hit_points) 
  1083.  
  1084. 	if ( (attacker == LOCAL_PLAYER) or (attacker == REMOTE_PLAYER) or explosion) then 
  1085. 		rn07_rpg_guy_destroy_ambulance() 
  1086. 	end 
  1087.  
  1088. end 
  1089.  
  1090. function rn07_ambulance_damaged(ambulance, attacker, damage_percent) 
  1091. 		 
  1092. 	if	(not vehicle_is_destroyed(ambulance) ) then 
  1093.  
  1094. 		-- If someone else attacked the ambulance, have the rpg guy destroy it 
  1095. 		if (attacker ~= CHARACTER_RPG_GUY) then 
  1096. 			rn07_rpg_guy_destroy_ambulance() 
  1097. 		-- If the rpg guy damaged the ambulance, detonate it 
  1098. 		else 
  1099. 			rn07_ambulance_detonate() 
  1100. 		end 
  1101.  
  1102. 	end 
  1103.  
  1104. end 
  1105.  
  1106. Rn07_ambulance_detonated = false 
  1107. function rn07_ambulance_detonate() 
  1108.  
  1109. 	if (Rn07_ambulance_detonated or vehicle_is_destroyed(VEHICLE_AMBULANCE)) then 
  1110. 		return 
  1111. 	end 
  1112. 	Rn07_ambulance_detonated = true 
  1113.  
  1114. 	vehicle_prevent_explosion_fling(VEHICLE_AMBULANCE,false) 
  1115. 	turn_vulnerable(VEHICLE_AMBULANCE) 
  1116. 	vehicle_detonate(VEHICLE_AMBULANCE) 
  1117. end 
  1118.  
  1119. Rn07_rpg_guy_destroying_ambulance = false 
  1120. Rn07_rpg_guy_destruction_attempts = 0 
  1121. function rn07_rpg_guy_destroy_ambulance() 
  1122.  
  1123. 	-- If the rpg guy is already trying to destroy the ambulance, just return 
  1124. 	if (Rn07_rpg_guy_destroying_ambulance) then 
  1125. 		return 
  1126. 	end 
  1127.  
  1128. 	Rn07_rpg_guy_destroying_ambulance = true 
  1129.  
  1130. 	-- Eliminate the on_take_damage callback 
  1131. 	on_take_damage("", CHARACTER_RPG_GUY) 
  1132.  
  1133. 	-- Try to blow up the ambulance 3 times. If we're not successful by the third time, just blow it up 
  1134. 	while(	(not vehicle_is_destroyed(VEHICLE_AMBULANCE))  
  1135. 				and (not character_is_dead(CHARACTER_RPG_GUY)) 
  1136. 				and (Rn07_rpg_guy_destruction_attempts < 3) 
  1137. 			) do 
  1138.  
  1139. 		-- Blow up the ambulance 
  1140. 		force_fire(CHARACTER_RPG_GUY, VEHICLE_AMBULANCE, true) 
  1141.  
  1142. 		-- If we're on the last attempt, make sure that the ambulance detonates 
  1143. 		if (Rn07_rpg_guy_destruction_attempts == 3) then 
  1144. 			rn07_ambulance_detonate() 
  1145. 		end 
  1146.  
  1147. 		delay(1.0) 
  1148. 	end 
  1149.  
  1150. 	-- Allow Rocket man to miss 
  1151. 	set_perfect_aim(CHARACTER_RPG_GUY,false) 
  1152.  
  1153. 	-- Make the rocket guy vulnerable again.	 
  1154. 	turn_vulnerable(CHARACTER_RPG_GUY) 
  1155. 	character_allow_ragdoll(CHARACTER_RPG_GUY, true) 
  1156. 	character_set_cannot_be_grabbed(CHARACTER_RPG_GUY, false) 
  1157. 	character_set_cannot_be_grabbed_by_player(CHARACTER_RPG_GUY, false) 
  1158. 	character_set_only_scripted_grabs(CHARACTER_RPG_GUY, false) 
  1159. 	character_prevent_explosion_fling(CHARACTER_RPG_GUY, false) 
  1160. 	character_prevent_flinching(CHARACTER_RPG_GUY, false) 
  1161. 	character_prevent_kneecapping(CHARACTER_RPG_GUY, false) 
  1162.  
  1163. end 
  1164.  
  1165. function rn07_ambulance_destroyed() 
  1166.  
  1167. 	on_take_damage("",VEHICLE_AMBULANCE) 
  1168.  
  1169. 	Rn07_dialogue_mission = "ambulance" 
  1170.  
  1171. 	-- Send player back to the 1st floor elevator 
  1172. 	rn07_send_to_location({TRIGGER_BREADCRUMB_7, TRIGGER_ELEVATOR_1 }, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_RETURN_ELEVATOR, nil, nil, SYNC_LOCAL) 
  1173.  
  1174. end 
  1175.  
  1176. -- Called when mission starts in coop 
  1177. function rn07_start_coop() 
  1178.  
  1179. 	-- Send player to the stairwell 
  1180. 	rn07_send_to_location(TRIGGER_STAIRWELL, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_STAIRWELL, nil, nil, SYNC_REMOTE) 
  1181.  
  1182. 	-- Send player to the elevator 
  1183. 	rn07_send_to_location(TRIGGER_ELEVATOR_3, INGAME_EFFECT_LOCATION, HELPTEXT_PROMPT_ROOFTOP_ELEVATOR, nil, nil, SYNC_REMOTE) 
  1184.  
  1185. 	mission_debug("rn07_start_coop: elevator arrival",-1) 
  1186.  
  1187. 	-- Elevator was reached, warp to the rooftop 
  1188. 	fade_out(1.0,{0,0,0}, SYNC_REMOTE) 
  1189. 	delay(1.0) 
  1190. 	teleport(REMOTE_PLAYER, NAVPOINT_ROOFTOP) 
  1191. 	door_open(DOOR_FLOOR_4_EXIT) 
  1192. 	door_open(DOOR_FLOOR_4_EXIT_2) 
  1193. 	fade_in(1.0, SYNC_REMOTE) 
  1194.  
  1195. 	-- Prompt the player to enter the helicopter, add minimap and in-game icon to helicopter 
  1196. 	set_unjackable_flag(VEHICLE_HELICOPTER, false) 
  1197. 	thread_new("mission_help_table",HELPTEXT_PROMPT_ENTER_HELICOPTER,"","",SYNC_REMOTE) 
  1198. 	marker_add_vehicle(VEHICLE_HELICOPTER, MINIMAP_ICON_PROTECT_ACQUIRE, INGAME_EFFECT_VEHICLE_PROTECT_ACQUIRE, SYNC_REMOTE) 
  1199.  
  1200. 	-- TODO, when we can hide stuff again in COOP, reenable this 
  1201. 	thread_new("rn07_heli_chase_player", REMOTE_PLAYER) 
  1202.  
  1203. 	-- Wait for a player to enter the helicopter 
  1204. 	on_vehicle_enter("rn07_helicopter_entered_remote", VEHICLE_HELICOPTER) 
  1205.  
  1206. 	while (not Helicopter_entered[REMOTE_PLAYER]) do 
  1207. 		thread_yield() 
  1208. 	end 
  1209. 	vehicle_prevent_explosion_fling(VEHICLE_HELICOPTER, false) 
  1210.  
  1211. 	-- Prompt to fly down to the parking lot, pick up partner 
  1212. 	rn07_send_to_location(TRIGGER_PARKING_HELICOPTER, INGAME_EFFECT_VEHICLE_LOCATION, HELPTEXT_PROMPT_PICKUP, nil, nil, SYNC_REMOTE) 
  1213. 	Remote_reached_parking = true 
  1214.  
  1215. 	if(not Local_reached_parking) then 
  1216. 		-- Tell player to defend the helicopter while waiting for their partner to arrive 
  1217. 		thread_new("mission_help_table",HELPTEXT_PROMPT_DEFEND_HELICOPTER,"","",SYNC_REMOTE) 
  1218.  
  1219. 		--rn07_yield_until(Local_reached_parking) 
  1220. 		while(not Local_reached_parking) do 
  1221. 			thread_yield() 
  1222. 		end 
  1223. 	end 
  1224. 		 
  1225. end 
  1226.  
  1227. -- Keep track of the distance between the local player and Gat 
  1228. function rn07_monitor_distance() 
  1229. 	while (not Helicopter_entered[LOCAL_PLAYER]) do 
  1230. 		-- calculate distances to current dealer's trigger 
  1231. 		local dist_to_gat = get_dist(LOCAL_PLAYER, CHARACTER_GAT) 
  1232.  
  1233. 		if (not Gat_too_far and dist_to_gat > GAT_DISTANCE_ALLOWED) then 
  1234. 			Gat_too_far = true 
  1235.  
  1236. 			-- Tell the player to get back to Gat 
  1237. 			mission_help_table_nag(HELPTEXT_PROMPT_RETURN_GAT, "", "", SYNC_LOCAL) 
  1238.  
  1239. 			-- Start the timer 
  1240. 			hud_timer_set(GAT_DISTANCE_HUD_INDEX, GAT_DISTANCE_TIME_S*1000,"rn07_failure_gat_abandoned") 
  1241.  
  1242. 		elseif (Gat_too_far and dist_to_gat < GAT_DISTANCE_ALLOWED) then 
  1243. 			Gat_too_far = false 
  1244.  
  1245. 			-- Disable timer 
  1246. 			hud_timer_stop(GAT_DISTANCE_HUD_INDEX) 
  1247. 			objective_text_clear(GAT_DISTANCE_HUD_INDEX) 
  1248. 		end 
  1249. 	thread_yield() 
  1250. 	end 
  1251. end 
  1252.  
  1253. -- Handle lieutenant spawning for a floor 
  1254. -- 
  1255. function rn07_patrol_floor(floor) 
  1256.  
  1257. 	-- Create the group, hidden 
  1258. 	group_create_hidden(FLOOR_PATROL_GROUPS[floor]) 
  1259.  
  1260. 	-- Build a list of areas associated with this floor 
  1261. 	local num_areas = AREAS_PER_FLOOR[floor] 
  1262. 	local patrol_areas = {} 
  1263. 	for area_number = 1, num_areas, 1 do 
  1264. 		local area = floor .. "_area_" .. area_number	-- e.g. area= "floor_1_area_1" 
  1265. 		patrol_areas[area] = true 
  1266. 	end 
  1267.  
  1268. 	-- Wait for the group to load 
  1269. 	while (not group_is_loaded(FLOOR_PATROL_GROUPS[floor])) do 
  1270. 		thread_yield() 
  1271. 	end 
  1272.  
  1273. 	-- Monitor current number of Ronin on this floor, add more when needed 
  1274. 	while(true) do 
  1275. 		 
  1276. 		-- Determine which players are on this floor 
  1277. 		local local_present, remote_present = false, false 
  1278. 		if ( patrol_areas[Local_player_location] == true) then 
  1279. 			local_present = true; 
  1280. 		end 
  1281. 		if ( IN_COOP and patrol_areas[Remote_player_location] == true) then 
  1282. 			remote_present = true; 
  1283. 		end 
  1284. 		local player_present = local_present or remote_present 
  1285.  
  1286. 		-- Spawn a new set of Ronin if the current wave is dead and there is a player on this floor 
  1287. 		if (player_present and Floor_living_lieutenants[floor] == 0) then 
  1288.  
  1289. 			local lieutenants_to_spawn = rand_int(Min_wave_size, Max_wave_size) 
  1290.  
  1291. 			for i=1, lieutenants_to_spawn, 1 do 
  1292.  
  1293. 				-- Determine the target player 
  1294. 				local target = "" 
  1295. 				if (local_present and remote_present) then 
  1296. 					local coin_toss = rand_int(1,2) 
  1297. 					if(coin_toss == 1) then 
  1298. 						target = LOCAL_PLAYER 
  1299. 					else 
  1300. 						target = REMOTE_PLAYER 
  1301. 					end 
  1302. 				elseif (local_present) then 
  1303. 					target = LOCAL_PLAYER 
  1304. 				elseif (remote_present) then 
  1305. 					target = REMOTE_PLAYER 
  1306. 				end 
  1307.  
  1308. 				-- If we have a target 
  1309. 				if (target ~= "") then 
  1310.  
  1311. 					-- Select a new spawning site for each lieutenant. Makes the mission play better, 
  1312. 					-- and needs to be done in case the player(s) move between spawns 
  1313. 					local spawn_site = rn07_get_safe_spawn_area(FLOOR_SAFE_SPAWN_TABLE[floor])	 
  1314.  
  1315. 					-- There should always be a valid spawn area, but just in case 
  1316. 					if (not spawn_site) then 
  1317. 						break 
  1318. 					end 
  1319. 	 
  1320. 					-- Get the next lieutenant we'll be spawning 
  1321. 					local lieutenant = PATROL_GROUP_MEMBERS[floor][i] 
  1322.  
  1323. 					-- Determine the lieutenant's spawn navpoint 
  1324. 					local spawn_navpoint = SPAWN_NAVPOINT_TABLES[spawn_site][i] 
  1325.  
  1326. 					-- Teleport the lieutenant to the spawn navpoint 
  1327. 					teleport(lieutenant, spawn_navpoint) 
  1328. 					 
  1329. 					-- Tell the Lieutenant to respawn, override default respawn time 
  1330. 					npc_respawn_after_death(lieutenant, true) 
  1331. 					npc_respawn_after_death_time_override(lieutenant, LIEUTENANT_RESPAWN_TIME_MS, true) 
  1332.  
  1333. 					-- Add respawn callback... needs to be done after each death 
  1334. 					on_respawn("rn07_lieutenant_respawn",lieutenant) 
  1335.  
  1336. 					-- Show the lieutenant 
  1337. 					character_show(lieutenant) 
  1338. 	 
  1339. 					-- Store the target 
  1340. 					Lieutenant_target[lieutenant] = target 
  1341.  
  1342. 					-- Store the first navpoint that the lieutenant should pathfind to 
  1343. 					Lieutenant_first_navpoint[lieutenant] = AREA_PATROL_START[spawn_site] 
  1344.  
  1345. 					-- Store the path that the lieutenant should be using 
  1346. 					Lieutenant_path[lieutenant] = PATROL_NAVPOINT_TABLES[floor] 
  1347.  
  1348. 					-- Store the floor that the lieutenant is on 
  1349. 					Lieutenant_floor[lieutenant] = floor 
  1350.  
  1351. 					-- Start the patrol 
  1352. 					patrol("rn07_lieutenant_patrol",lieutenant) 
  1353.  
  1354. 					-- Increment living lieutenant count 
  1355. 					Floor_living_lieutenants[floor] = Floor_living_lieutenants[floor] + 1 
  1356.  
  1357. 					-- Delay just a tad between spawns 
  1358. 					delay(rand_float(.1,.4)) 
  1359.  
  1360. 				end 
  1361. 			end 
  1362. 		end 
  1363. 		thread_yield() 
  1364. 	end 
  1365. end 
  1366.  
  1367. function rn07_lieutenant_respawn(lieutenant) 
  1368.  
  1369. 	-- Hide the lieutenant for now  
  1370. 	character_hide(lieutenant) 
  1371.  
  1372. 	-- Update the count of living lieutenants on this floor 
  1373. 	Floor_living_lieutenants[Lieutenant_floor[lieutenant]] = Floor_living_lieutenants[Lieutenant_floor[lieutenant]] - 1 
  1374.  
  1375. end 
  1376.  
  1377. function rn07_lieutenant_patrol(lieutenant) 
  1378.  
  1379. 	-- Get the patrol path to follow 
  1380. 	local patrol_navpoints = Lieutenant_path[lieutenant] 
  1381.  
  1382. 	-- Get the index of the first navpoint to pathfind to 
  1383. 	local patrol_navpoint_index = Lieutenant_first_navpoint[lieutenant] 
  1384.  
  1385. 	-- Determine move_to speed. 2==run, 3== sprint 
  1386. 	local roll = rand_int(1,100) 
  1387. 	local move_speed = 2 
  1388. 	if (roll <= LIEUTENANT_SPRINT_CHANCE) then 
  1389. 		move_speed = 3		 
  1390. 	end 
  1391.  
  1392. 	-- Send to the first navpoint 
  1393. 	move_to(lieutenant, patrol_navpoints[patrol_navpoint_index], move_speed, false, false) 
  1394.  
  1395. 	-- Get the number of navpoints in this path 
  1396. 	local number_navpoints = sizeof_table(patrol_navpoints) 
  1397.  
  1398. 	-- Get the floor that the lieutenant is on 
  1399. 	local floor = Lieutenant_floor[lieutenant] 
  1400.  
  1401. 	-- Get the player target for this lieutenant 
  1402. 	local player_target = Lieutenant_target[lieutenant] 
  1403.  
  1404. 	-- function to get the current target's location 
  1405. 	local function get_target_location(target) 
  1406.  
  1407. 		if (not IN_COOP) then 
  1408. 			return Local_player_location 
  1409. 		end 
  1410.  
  1411. 		if (target == LOCAL_PLAYER) then 
  1412. 			return Local_player_location 
  1413. 		else 
  1414. 			return Remote_player_location 
  1415. 		end 
  1416. 	end 
  1417.  
  1418. 	-- Start patrolling 
  1419. 	while (1) do 
  1420.  
  1421. 		-- Get the current lieutenant's current location 
  1422. 		local current_area = FLOOR_PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index] 
  1423.  
  1424. 		local target_location = get_target_location(player_target) 
  1425.  
  1426. 		-- If the target is in the same location, wander around the current location for a bit, 
  1427. 		-- then move back to current navpoint 
  1428. 		if (current_area == target_location) then 
  1429. 			wander_start(lieutenant, PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index], rand_float(8,16)) 
  1430. 			delay(rand_float(8,16)) 
  1431. 			wander_stop(lieutenant) 
  1432. 			move_to(lieutenant, PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index], 2, false, false) 
  1433. 		else 
  1434. 			-- Get the direction we need to travel to get to the player 
  1435. 			local patrol_direction = AREA_FLOOR_PATROL_DIRECTION[current_area][target_location] 
  1436.  
  1437. 			if (player_target == REMOTE_PLAYER and patrol_direction and not LTNT_DEBUGGED) then 
  1438. 					mission_debug(lieutenant .. " initial target location chosen: " .. target_location,-1) 
  1439. 					mission_debug(lieutenant .. " initial patrol direction: " .. patrol_direction,-1) 
  1440. 			end 
  1441.  
  1442. 			-- If we couldn't find a direction, and the target isn't in the lieutenant's area, 
  1443. 			-- then the target is no longer on this floor. Check to see if we can switch to the other player 
  1444. 			if (not patrol_direction and current_area ~= target_location and IN_COOP) then 
  1445. 				if(player_target == LOCAL_PLAYER) then 
  1446. 					player_target = REMOTE_PLAYER 
  1447. 					if (not LTNT_DEBUGGED) then 
  1448. 						mission_debug(lieutenant .. " switching to remote player target ",-1) 
  1449. 					end 
  1450. 				else 
  1451. 					player_target = LOCAL_PLAYER 
  1452. 					if (not LTNT_DEBUGGED) then 
  1453. 						mission_debug(lieutenant .. " switching to local player target ", -1) 
  1454. 					end 
  1455. 				end 
  1456. 				target_location = get_target_location(player_target) 
  1457. 				patrol_direction = AREA_FLOOR_PATROL_DIRECTION[current_area][target_location] 
  1458. 			end 
  1459.  
  1460. 			if (player_target == REMOTE_PLAYER and patrol_direction and not LTNT_DEBUGGED) then 
  1461. 					mission_debug(lieutenant .. " new target location chosen: " .. target_location,-1) 
  1462. 					mission_debug(lieutenant .. " new patrol direction: " .. patrol_direction,-1) 
  1463. 			end 
  1464.  
  1465. 			-- If we still don't have a direction listed, no players are on this floor... don't process 
  1466. 			if (patrol_direction) then 
  1467.  
  1468. 				-- Get the next navpoint along the path in the correct direction 
  1469. 				if (patrol_direction == "forward") then 
  1470. 					patrol_navpoint_index = patrol_navpoint_index + 1 
  1471. 					if (patrol_navpoint_index > number_navpoints) then 
  1472. 						patrol_navpoint_index = patrol_navpoint_index - number_navpoints 
  1473. 					end 
  1474. 				else 
  1475. 					patrol_navpoint_index = patrol_navpoint_index - 1 
  1476. 					if (patrol_navpoint_index < 1) then 
  1477. 						patrol_navpoint_index = patrol_navpoint_index + number_navpoints 
  1478. 					end 
  1479. 				end 
  1480.  
  1481. 				if (player_target == REMOTE_PLAYER and not LTNT_DEBUGGED) then 
  1482. 						mission_debug(lieutenant .. " target navpoint: " .. FLOOR_PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index] .. target_location,-1) 
  1483. 				end 
  1484.  
  1485. 				-- Move to the next navpoint along the path 
  1486. 				move_to(lieutenant, PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index], 2, false, false) 
  1487. 		 
  1488. 			-- Else, no player on this floor. Wander around a bit and return. 
  1489. 			else 
  1490. 				wander_start(lieutenant, PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index], rand_float(10,25)) 
  1491. 				delay(rand_float(5,12)) 
  1492. 				wander_stop(lieutenant) 
  1493. 				move_to(lieutenant, PATROL_NAVPOINT_TABLES[floor][patrol_navpoint_index], 2, false, false) 
  1494. 			end 
  1495. 		 
  1496. 			LTNT_DEBUGGED = true 
  1497. 		end -- Ends else for if(in same areas) 
  1498.  
  1499. 		-- I don't think this is required, but I'm being safe 
  1500. 		thread_yield() 
  1501. 	end -- ends While(1) 
  1502. end 
  1503.  
  1504. -- Returns a random popping-safe spawn area 
  1505. function rn07_get_safe_spawn_area(safe_spawn_areas) 
  1506.  
  1507. 	local valid_local_player_spawn_areas = safe_spawn_areas[Local_player_location] 
  1508. 	local valid_remote_player_spawn_areas = safe_spawn_areas[Remote_player_location] 
  1509. 	local valid_areas = {} 
  1510.  
  1511. 	-- If neither player is on the floor, return nil 
  1512. 	if (not valid_local_player_spawn_areas and not valid_remote_player_spawn_areas) then 
  1513. 		return nil 
  1514. 	end 
  1515. 	 
  1516. 	-- Only the local player is present, use their entire list 
  1517. 	if (valid_local_player_spawn_areas and not valid_remote_player_spawn_areas) then 
  1518. 		for i,area in pairs(valid_local_player_spawn_areas) do 
  1519. 			valid_areas[area] = area 
  1520. 		end 
  1521. 	end 
  1522.  
  1523. 	-- Only remote player present, use their entire list 
  1524. 	if (not valid_local_player_spawn_areas and valid_remote_player_spawn_areas) then 
  1525. 		for i,area in pairs(valid_remote_player_spawn_areas) do 
  1526. 			valid_areas[area] = area 
  1527. 		end 
  1528. 	end 
  1529.  
  1530. 	-- Both players present .. only add those areas valid for both players 
  1531. 	if (valid_local_player_spawn_areas and valid_remote_player_spawn_areas) then 
  1532.  
  1533. 		-- First grab all of the local players safe areas 
  1534. 		local local_valid_areas = {} 
  1535. 		for i,area in pairs(valid_local_player_spawn_areas) do 
  1536. 			local_valid_areas[area] = area 
  1537. 		end 
  1538.  
  1539. 		-- If the are is also in the remote player's list, then it is safe for both 
  1540. 		for i,area in pairs(valid_remote_player_spawn_areas) do 
  1541. 			if(local_valid_areas[area]) then 
  1542. 				valid_areas[area] = area 
  1543. 			end 
  1544. 		end 
  1545.  
  1546. 	end 
  1547.  
  1548. 	-- Get the total number of valid spawn areas 
  1549. 	local num_valid_spawn_areas = sizeof_table(valid_areas) 
  1550.  
  1551. 	-- If there aren't any valid spawn areas, return nil 
  1552. 	if (num_valid_spawn_areas == 0) then 
  1553. 		return nil 
  1554. 	end 
  1555.  
  1556. 	-- Select a random valid spawn area index 
  1557. 	local spawn_index = rand_int(1,num_valid_spawn_areas) 
  1558.  
  1559. 	-- Find the valid spawn area corresponding to the random index 
  1560. 	local count = 1 
  1561. 	for index,value in pairs(valid_areas) do 
  1562. 		if (count == spawn_index) then 
  1563. 			return value 
  1564. 		end 
  1565. 		count = count + 1 
  1566. 	end 
  1567.  
  1568. 	-- Shouldn't get here 
  1569. 	return nil 
  1570.  
  1571. end 
  1572.  
  1573. function rn07_setup_player_tracking_triggers() 
  1574. 	-- enable area-entrance triggers 
  1575. 	for entrance, area in pairs(ENTRANCE_TARGET_AREAS) do 
  1576. 		trigger_enable(entrance, true) 
  1577. 		on_trigger("rn07_area_entered",entrance) 
  1578. 		trigger_set_delay_between_activations(entrance,0) 
  1579. 	end 
  1580. end 
  1581.  
  1582. function rn07_area_entered(triggerer, trigger) 
  1583. 	if (triggerer == LOCAL_PLAYER) then 
  1584. 		Local_player_location = ENTRANCE_TARGET_AREAS[trigger] 
  1585. 	else  
  1586. 		Remote_player_location = ENTRANCE_TARGET_AREAS[trigger] 
  1587. 	end 
  1588. end 
  1589.  
  1590. -- Helicopter has been entered 
  1591. function rn07_helicopter_entered_remote() 
  1592. 	Helicopter_entered[REMOTE_PLAYER] = true; 
  1593. 	 
  1594. 	-- remove the vehicle callback 
  1595. 	marker_remove_vehicle(VEHICLE_HELICOPTER,SYNC_REMOTE) 
  1596. 	on_vehicle_enter("",VEHICLE_HELICOPTER) 
  1597. end 
  1598.  
  1599. -- Gat slowly loses health. 
  1600. -- 
  1601. function rn07_health_syphon_gat(gat) 
  1602.  
  1603. 	local hit_points_per_tick = GAT_HIT_POINTS / GAT_HEALTH_LOSS_TIME_S 
  1604.  
  1605. 	while (true) do 
  1606. 		if ( (not Gat_in_cardiac_arrest) and (fade_get_percent() == 0.0)) then 
  1607. 			local old_hit_points = get_current_hit_points(gat) 
  1608. 			rn07_set_hit_points_gat(old_hit_points - hit_points_per_tick, gat) 
  1609. 			delay(1.0) 
  1610. 		end 
  1611. 		thread_yield() 
  1612. 	end 
  1613. end 
  1614.  
  1615. -- Called when Gat is damaged 
  1616. -- damage_percent is Gat's health percentage after the attack 
  1617. function rn07_handle_gat_damaged(gat, attacker, damage_percent) 
  1618.  
  1619. 	if (not Gat_in_cardiac_arrest) then 
  1620.  
  1621. 		-- Set Gat's new hit point total 
  1622. 		local new_hit_points = damage_percent * get_max_hit_points(CHARACTER_GAT) 
  1623. 		rn07_set_hit_points_gat(new_hit_points, gat) 
  1624.  
  1625. 		-- Maybe have Gat say something 
  1626. 		if(rand_float(0,1) < .5) then 
  1627. 			Rn07_dialogue_gat = "GAT_RON07_TAKEDAM" 
  1628. 		end 
  1629.  
  1630. 	else 
  1631.  
  1632. 		-- Already in Cardiac arrest, see if the player caused the damage w/ shock paddles. 
  1633. 		-- if so, reset Gats health 
  1634. 		if(attacker == LOCAL_PLAYER and inv_item_is_equipped("shock_paddles",LOCAL_PLAYER)) then 
  1635. 		 
  1636. 			rn07_set_hit_points_gat(GAT_HIT_POINTS * GAT_PADDLE_HEALTH_RESTORE, CHARACTER_GAT) 
  1637.  
  1638. 			-- Tell the player that Gat was revived 
  1639. 			mission_help_table_nag(HELPTEXT_PROMPT_HAVE_PULSE,"","",SYNC_LOCAL) 
  1640.  
  1641. 		end 
  1642.  
  1643. 	end 
  1644.  
  1645. end 
  1646.  
  1647. function rn07_set_hit_points_gat(new_hit_points, gat) 
  1648.  
  1649. 	if (Gat_in_cardiac_arrest and new_hit_points > 0) then 
  1650. 		-- Disable timer 
  1651. 		hud_timer_stop(GAT_REVIVE_HUD_INDEX) 
  1652. 		objective_text_clear(GAT_REVIVE_HUD_INDEX) 
  1653. 		Gat_in_cardiac_arrest = false 
  1654. 	end 
  1655. 	 
  1656. 	-- Play a warning sound/message when Gat's health drops below certain levels 
  1657. 	if (new_hit_points >= 1) then 
  1658. 		local warning_levels		= {0.50, 0.30, 0.10} 
  1659.  
  1660. 		local warning_messages	= {HELPTEXT_PROMPT_GAT_HEALTH_1, HELPTEXT_PROMPT_GAT_HEALTH_2, 
  1661. 											HELPTEXT_PROMPT_GAT_HEALTH_3} 
  1662. 		local old_hit_points		= get_current_hit_points(gat) 
  1663.  
  1664. 		for i,health_ratio in pairs(warning_levels) do 
  1665. 			if (	old_hit_points > health_ratio * GAT_HIT_POINTS and 
  1666. 					new_hit_points <= health_ratio * GAT_HIT_POINTS 
  1667. 				) then 
  1668. 				audio_play("SYS_HEALTH_WARNING") 
  1669. 				mission_help_table_nag(warning_messages[i], "", "", SYNC_LOCAL) 
  1670. 			end 
  1671. 		end 
  1672. 	end 
  1673.  
  1674. 	--[[ 
  1675. 	-- If this attack would normally kill Gat, make him go into cardiac arrest instead 
  1676. 	if (	(new_hit_points < 1) and (not Helicopter_entered)) then 
  1677.  
  1678. 		new_hit_points = 1 
  1679. 		set_current_hit_points(CHARACTER_GAT, new_hit_points) 
  1680. 		hud_bar_set_value(0,new_hit_points, SYNC_ALL) 
  1681. 		Gat_in_cardiac_arrest	= true 
  1682.  
  1683. 		-- Tell the player that Gat has gone into cardiac arrest 
  1684. 		mission_help_table_nag(HELPTEXT_PROMPT_CARDIAC_ARREST, "", "", SYNC_LOCAL) 
  1685.  
  1686. 		-- Add a timer 
  1687. 		hud_timer_set(GAT_REVIVE_HUD_INDEX, GAT_REVIVE_TIME_S*1000,"rn07_failure_gat_died") 
  1688. 		--objective_text(GAT_REVIVE_HUD_INDEX, HELPTEXT_PROMPT_SHOCK_PADDLES) 
  1689. 		delay(3) 
  1690.  
  1691. 		-- Tell the player to find some shock paddles if he doesn't have any 
  1692. 		if (not inv_has_item("shock_paddles", LOCAL_PLAYER)) then 
  1693. 			mission_help_table(HELPTEXT_PROMPT_SHOCK_PADDLES,"","",SYNC_LOCAL) 
  1694.  
  1695. 			-- Wait for the player to obtain shock paddles 
  1696. 			while(not inv_has_item("shock_paddles", LOCAL_PLAYER)) do 
  1697. 				thread_yield() 
  1698. 			end 
  1699.  
  1700. 		end 
  1701.  
  1702. 		-- Tell the player to use the shock paddles to revive Gat 
  1703. 		mission_help_table(HELPTEXT_PROMPT_USE_PADDLES,"","",SYNC_LOCAL) 
  1704. 	elseif (new_hit_points < 1) then 
  1705. 		new_hit_points = 0 
  1706. 		rn07_failure_gat_died() 
  1707. 	end 
  1708. 	]] 
  1709.  
  1710.  
  1711. 	-- When Gat actually dies, animation badness sometimes ensues... don't let that happen! 
  1712. 	local gat_died = (new_hit_points <= 0) 
  1713. 	new_hit_points = max(new_hit_points, 1) 
  1714. 	set_current_hit_points(gat, new_hit_points) 
  1715. 	hud_bar_set_value(0,new_hit_points, SYNC_ALL) 
  1716.  
  1717. 	if (gat_died) then 
  1718. 		rn07_failure_gat_died() 
  1719. 	end 
  1720. end 
  1721.  
  1722. rn07_old_helicopter_health = 1.0 
  1723. function rn07_handle_helicopter_damaged(helicopter, attacker, damage_percent) 
  1724.  
  1725. 	-- Determine how much damage was done to the helicopter, apply the damage 
  1726. 	local helicopter_new_hit_points = damage_percent * get_max_hit_points(helicopter) 
  1727. 	local helicopter_old_hit_points = rn07_old_helicopter_health * get_max_hit_points(helicopter) 
  1728. 	local helicopter_damage = helicopter_old_hit_points - helicopter_new_hit_points 
  1729. 	set_current_hit_points(helicopter, helicopter_new_hit_points) 
  1730. 	rn07_old_helicopter_health = damage_percent 
  1731.  
  1732. 	-- Determine how much damage to apply to Gat, apply the damage 
  1733. 	local gat_damage = GAT_HELI_DAMAGE_RATIO * helicopter_damage 
  1734. 	local gat_current_hit_points = get_current_hit_points(CHARACTER_GAT_NORMAL) 
  1735. 	rn07_set_hit_points_gat(gat_current_hit_points - gat_damage, CHARACTER_GAT_NORMAL) 
  1736. end 
  1737.  
  1738. Current_minimap_mode = {[LOCAL_PLAYER] = MINIMAP_MODE_NONE, [REMOTE_PLAYER] = MINIMAP_MODE_NONE} 
  1739. function rn07_process_minimap(player) 
  1740.  
  1741. 	Current_minimap_mode[player]	= MINIMAP_MODE_NONE 
  1742.  
  1743. 	while(true) do 
  1744.  
  1745. 		-- Determine the next minimap mode 
  1746. 		local next_minimap_mode = MINIMAP_MODE_NONE 
  1747. 		for mode = MINIMAP_MODE_FIRST, MINIMAP_MODE_LAST, 1 do 
  1748. 			if (MINIMAP_MODE_FUNCTIONS[mode]["mode_is_active"](player)) then 
  1749. 				next_minimap_mode = mode 
  1750. 				break 
  1751. 			end 
  1752. 		end 
  1753.  
  1754. 		-- If the mode has changed, exit the old mode and enter the new 
  1755. 		if (next_minimap_mode ~= Current_minimap_mode[player]) then 
  1756.  
  1757. 			if (Current_minimap_mode[player] ~= MINIMAP_MODE_NONE) then 
  1758. 				MINIMAP_MODE_FUNCTIONS[Current_minimap_mode[player]]["exit"](player) 
  1759. 			end 
  1760.  
  1761. 			Current_minimap_mode[player] = next_minimap_mode 
  1762. 		 
  1763. 			if (next_minimap_mode ~= MINIMAP_MODE_NONE) then 
  1764. 				MINIMAP_MODE_FUNCTIONS[next_minimap_mode]["enter"](player) 
  1765. 			end 
  1766.  
  1767. 		end 
  1768.  
  1769. 		Current_minimap_mode[player] = next_minimap_mode 
  1770.  
  1771. 		thread_yield() 
  1772. 	 
  1773. 	end 
  1774.  
  1775. end 
  1776.  
  1777. -- Shock paddle marker functions 
  1778. function rn07_should_display_paddle_markers(player) 
  1779.  
  1780. 	return false 
  1781.  
  1782. 	--[[ 
  1783. 	if (player == REMOTE_PLAYER) then 
  1784. 		return false 
  1785. 	else 
  1786. 		return (Gat_in_cardiac_arrest and (not inv_has_item("shock_paddles", LOCAL_PLAYER))) 
  1787. 	end 
  1788. 	]] 
  1789. end 
  1790.  
  1791. function rn07_add_paddle_markers() 
  1792.  
  1793. 	-- Show the player where to find the shock paddles 
  1794. 	for i,shock_paddle in pairs(SHOCK_PADDLES) do 
  1795. 		marker_add_item(shock_paddle, MINIMAP_ICON_PROTECT_ACQUIRE, INGAME_EFFECT_PROTECT_ACQUIRE, SYNC_LOCAL) 
  1796. 	end 
  1797.  
  1798. end 
  1799.  
  1800. function rn07_remove_paddle_markers() 
  1801.  
  1802. 	-- Remove minimap icons, effects from shock paddles 
  1803. 	for i,shock_paddle in pairs(SHOCK_PADDLES) do 
  1804. 		marker_remove_item(shock_paddle, SYNC_LOCAL) 
  1805. 	end 
  1806. end 
  1807.  
  1808. -- Gat marker functions 
  1809. function rn07_should_display_gat_markers(player) 
  1810. 	if (player == REMOTE_PLAYER) then 
  1811. 		return false 
  1812. 	else 
  1813. 		return (Pushing_gat and (not character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT))) 
  1814. 	end 
  1815. end 
  1816.  
  1817. function rn07_add_gat_markers(player) 
  1818. 	marker_add_npc(CHARACTER_GAT, MINIMAP_ICON_PROTECT_ACQUIRE, INGAME_EFFECT_PROTECT_ACQUIRE, SYNC_LOCAL) 
  1819. end 
  1820.  
  1821. function rn07_remove_gat_markers(player) 
  1822. 	marker_remove_npc(CHARACTER_GAT, SYNC_LOCAL) 
  1823. end 
  1824.  
  1825. -- Heli marker functions 
  1826. function rn07_should_display_heli_markers(player) 
  1827.  
  1828. 	-- If the player has not yet entered the helicopter, don't tell them to reenter it. 
  1829. 	if ( not Helicopter_entered[player] ) then 
  1830. 		return false 
  1831. 	end 
  1832.  
  1833. 	if	( character_is_in_vehicle(player, VEHICLE_HELICOPTER) ) then 
  1834. 		return false 
  1835. 	end 
  1836.  
  1837. 	return true 
  1838.  
  1839. end 
  1840.  
  1841. function rn07_add_heli_markers(player) 
  1842. 	mission_help_table_nag(HELPTEXT_PROMPT_REENTER_HELI, "", "", PLAYER_SYNC[player]) 
  1843. 	marker_add_vehicle(VEHICLE_HELICOPTER, MINIMAP_ICON_PROTECT_ACQUIRE, INGAME_EFFECT_VEHICLE_PROTECT_ACQUIRE, PLAYER_SYNC[player]) 
  1844. end 
  1845.  
  1846. function rn07_remove_heli_markers(player) 
  1847. 	marker_remove_vehicle(VEHICLE_HELICOPTER, PLAYER_SYNC[player]) 
  1848. end 
  1849.  
  1850.  
  1851. -- Location marker functions 
  1852. function rn07_should_display_location_markers(player) 
  1853. 	if (not rn07_location_reached[SYNC_ALL]) then 
  1854. 		return true 
  1855. 	end 
  1856. 	if (not rn07_location_reached[PLAYER_SYNC[player]]) then 
  1857. 		return true 
  1858. 	end 
  1859. end 
  1860.  
  1861. Rn07_last_location_message = {[LOCAL_PLAYER] = "", [REMOTE_PLAYER] = ""} 
  1862. function rn07_add_location_markers(player) 
  1863.  
  1864. 	local sync = PLAYER_SYNC[player] 
  1865. 	if (not rn07_location_reached[SYNC_ALL]) then 
  1866. 		sync = SYNC_ALL 
  1867. 	end 
  1868.  
  1869. 	if (rn07_breadcrumb_effect[sync]) then 
  1870.  
  1871. 		local num_breadcrumbs = sizeof_table(rn07_breadcrumb_triggers[sync]) 
  1872.  
  1873. 		-- First traverse the triggers in reverse. If we're close enough, count them as visited. 
  1874. 		local current_trigger = rn07_current_trigger[sync] 
  1875. 		for i = num_breadcrumbs, current_trigger, -1 do 
  1876. 			local trigger = rn07_breadcrumb_triggers[sync][i] 
  1877. 			if (get_dist(player, trigger) < 5) then 
  1878. 				if (i == num_breadcrumbs) then 
  1879. 					rn07_toggle_location_reached(player, trigger, sync) 
  1880. 				else 
  1881. 					rn07_breadcrumb_reached(player, trigger, sync) 
  1882. 				end 
  1883. 			end 
  1884. 		end 
  1885.  
  1886. 		-- If we triggered the final destination during our traversal, then we can return 
  1887. 		if (rn07_location_reached[sync]) then 
  1888. 			return 
  1889. 		end 
  1890.  
  1891. 		for i = rn07_current_trigger[sync], num_breadcrumbs, 1 do			 
  1892. 			trigger_enable(rn07_breadcrumb_triggers[sync][i],true) 
  1893. 		end 
  1894. 		local minimap_icon = MINIMAP_ICON_LOCATION 
  1895. 		if( rn07_breadcrumb_effect[sync] == INGAME_EFFECT_VEHICLE_PROTECT_ACQUIRE) then 
  1896. 			minimap_icon = MINIMAP_ICON_PROTECT_ACQUIRE 
  1897. 		end 
  1898. 		marker_add_trigger(rn07_breadcrumb_triggers[sync][rn07_current_trigger[sync]],minimap_icon,rn07_breadcrumb_effect[sync],sync) 
  1899.  
  1900. 		-- Display helptext 
  1901. 		if (rn07_breadcrumb_helptext[sync]) then 
  1902. 			-- If we've already played the message for this location, make it a nag 
  1903. 			if(Rn07_last_location_message[player] == rn07_breadcrumb_helptext[sync]) then		 
  1904. 				mission_help_table_nag(rn07_breadcrumb_helptext[sync], "", "", sync) 
  1905. 			else 
  1906. 			-- Otherwise, it is an objective 
  1907. 				mission_help_table(rn07_breadcrumb_helptext[sync], "", "", sync) 
  1908. 				Rn07_last_location_message[player] = rn07_breadcrumb_helptext[sync] 
  1909. 			end 
  1910. 		end 
  1911.  
  1912. 	end 
  1913.  
  1914. end 
  1915.  
  1916. function rn07_remove_location_markers(player) 
  1917.  
  1918. 	local sync = PLAYER_SYNC[player] 
  1919. 	if (not rn07_location_reached[SYNC_ALL]) then 
  1920. 		sync = SYNC_ALL 
  1921. 	end 
  1922.  
  1923. 	if (rn07_breadcrumb_effect[sync]) then 
  1924.  
  1925. 		marker_remove_trigger(rn07_breadcrumb_triggers[sync][rn07_current_trigger[sync]]) 
  1926.  
  1927. 	end 
  1928.  
  1929. end 
  1930.  
  1931. 	-- Minimap_mode_functions 
  1932. 	MINIMAP_MODE_FUNCTIONS	= 
  1933. 		{ 
  1934. 			[MINIMAP_MODE_PADDLES]		=  
  1935. 				{ 
  1936. 					["mode_is_active"]	= rn07_should_display_paddle_markers, 
  1937. 					["enter"]				= rn07_add_paddle_markers, 
  1938. 					["exit"]					= rn07_remove_paddle_markers,	 
  1939. 				}; 
  1940. 			[MINIMAP_MODE_GAT]			=  
  1941. 				{ 
  1942. 					["mode_is_active"]	= rn07_should_display_gat_markers, 
  1943. 					["enter"]				= rn07_add_gat_markers, 
  1944. 					["exit"]					= rn07_remove_gat_markers,	 
  1945. 				}; 
  1946. 			[MINIMAP_MODE_HELI]			=  
  1947. 				{ 
  1948. 					["mode_is_active"]	= rn07_should_display_heli_markers, 
  1949. 					["enter"]				= rn07_add_heli_markers, 
  1950. 					["exit"]					= rn07_remove_heli_markers,	 
  1951. 				}; 
  1952. 			[MINIMAP_MODE_LOCATIONS]	=  
  1953. 				{ 
  1954. 					["mode_is_active"]	= rn07_should_display_location_markers, 
  1955. 					["enter"]				= rn07_add_location_markers, 
  1956. 					["exit"]					= rn07_remove_location_markers,	 
  1957. 				}; 
  1958. 		} 
  1959.  
  1960. function rn07_heli_chase_player(player) 
  1961. 	-- Create the heli group 
  1962. 	group_create_hidden(GROUP_RONIN_HELICOPTER) 
  1963.  
  1964. 	vehicle_enter_group_teleport(RONIN_HELICOPTER_MEMBERS, VEHICLE_RONIN_HELI) 
  1965.  
  1966. 	-- Wait for loading 
  1967. 	while (not group_is_loaded(GROUP_RONIN_HELICOPTER)) do 
  1968. 		thread_yield() 
  1969. 	end 
  1970.  
  1971. 	-- give the back seat passenger a rifle 
  1972. 	inv_item_add("AR200",0,RONIN_HELICOPTER_MEMBERS[2]) 
  1973. 	inv_item_equip("AR200", RONIN_HELICOPTER_MEMBERS[2]) 
  1974.  
  1975. 	group_show(GROUP_RONIN_HELICOPTER) 
  1976. 	character_hide("rn07_$c031") 
  1977.  
  1978. 	vehicle_lights_on(VEHICLE_RONIN_HELI, true) 
  1979. 	vehicle_chase(VEHICLE_RONIN_HELI, player) 
  1980. end 
  1981.  
  1982. rn07_location_reached			= {[SYNC_ALL] = true, [SYNC_LOCAL] = true, [SYNC_REMOTE] = true} 
  1983. rn07_current_trigger				= {[SYNC_ALL] = 1, [SYNC_LOCAL] = 1, [SYNC_REMOTE] = 1} 
  1984. rn07_breadcrumb_triggers		= {[SYNC_ALL] = {}, [SYNC_LOCAL] = {}, [SYNC_REMOTE] = {}} 
  1985. rn07_breadcrumb_effect			= {[SYNC_ALL] = "", [SYNC_LOCAL] = "", [SYNC_REMOTE] = ""} 
  1986. rn07_breadcrumb_helptext		= {[SYNC_ALL] = nil, [SYNC_LOCAL] = nil, [SYNC_REMOTE] = nil} 
  1987. -- Send a player to a particular location 
  1988. --  
  1989. -- Handles enabling/disabling of trigger effects when Gat goes into cardiac arrest or is revived. 
  1990. -- Currently, assumes that breadcrumbing only happens for the local player. 
  1991. -- 
  1992. --	trigger:						If a table, then the final trigger is the destination and other triggers are breadcrumbs 
  1993. --									If scalar, then this is the destination. 
  1994. -- effect:						Effect to be placed on the trigger(s). 
  1995. -- helptext:					Helptext to display when the function is called, or when triggers are reenabled after Gat 
  1996. --										comes out of cardiac arrest. 
  1997. -- time:							Time constraint if there is one. 
  1998. -- time_failure_function:	Function called if time runs out. 
  1999. -- sync:							Sync type. 
  2000. -- 
  2001. function rn07_send_to_location(trigger, effect, helptext, time, time_failure_function, sync) 
  2002.  
  2003. 	rn07_location_reached[sync] = false 
  2004. 	rn07_breadcrumb_effect[sync] = false 
  2005. 	if (effect) then 
  2006. 		rn07_breadcrumb_effect[sync] = effect 
  2007. 	end 
  2008. 	rn07_current_trigger[sync] = 1 
  2009. 	rn07_breadcrumb_triggers[sync] = {} 
  2010. 	rn07_breadcrumb_helptext[sync] = nil 
  2011.  
  2012. 	-- Place triggers into a global table variable 
  2013. 	if ((type(trigger) == "table")) then 
  2014. 		rn07_breadcrumb_triggers[sync] = trigger 
  2015. 	else 
  2016. 		rn07_breadcrumb_triggers[sync][1] = trigger 
  2017. 	end 
  2018.  
  2019. 	local final_trigger_function =  
  2020. 		{	 
  2021. 			[SYNC_ALL] = "rn07_toggle_location_reached_all",  
  2022. 			[SYNC_LOCAL] = "rn07_toggle_location_reached_local",  
  2023. 			[SYNC_REMOTE] = "rn07_toggle_location_reached_remote" 
  2024. 		} 
  2025. 	local breadcrumb_trigger_function =  
  2026. 		{	 
  2027. 			[SYNC_ALL] = "rn07_breadcrumb_reached_all",  
  2028. 			[SYNC_LOCAL] = "rn07_breadcrumb_reached_local",  
  2029. 			[SYNC_REMOTE] = "rn07_breadcrumb_reached_remote" 
  2030. 		} 
  2031.  
  2032. 	-- Add callbacks for all triggers, special callback for final trigger 
  2033. 	local num_breadcrumbs = sizeof_table(rn07_breadcrumb_triggers[sync]) 
  2034. 	for i,breadcrumb in pairs(rn07_breadcrumb_triggers[sync]) do 
  2035. 		trigger_enable(breadcrumb,true) 
  2036. 		if (i == num_breadcrumbs) then 
  2037. 			on_trigger(final_trigger_function[sync],breadcrumb)					 
  2038. 		else 
  2039. 			on_trigger(breadcrumb_trigger_function[sync], breadcrumb) 
  2040. 		end 
  2041. 	end 
  2042.  
  2043. 	-- Setup the time constraint if there is one. 
  2044. 	if (time and time_failure_function) then 
  2045. 		hud_timer_set(GAT_REVIVE_HUD_INDEX, time, time_failure_function) 
  2046. 	end 
  2047.  
  2048. 	-- Set helptext 
  2049. 	if (helptext) then 
  2050. 		--mission_help_table(helptext, "", "", sync) 
  2051. 		rn07_breadcrumb_helptext[sync] = helptext 
  2052. 	end 
  2053.  
  2054. 	-- wait for player(s) to arrive 
  2055. 	while (not rn07_location_reached[sync]) do 
  2056.  
  2057. 		thread_yield() 
  2058.  
  2059. 	end 
  2060.  
  2061. 	--hud_timer_stop(GAT_REVIVE_HUD_INDEX) 
  2062. end 
  2063.  
  2064. function rn07_breadcrumb_reached_local(triggerer, trigger) 
  2065. 	if (triggerer == LOCAL_PLAYER) then 
  2066. 		rn07_breadcrumb_reached(triggerer, trigger, SYNC_LOCAL) 
  2067. 	end 
  2068. end 
  2069.  
  2070. function rn07_breadcrumb_reached_remote(triggerer, trigger) 
  2071. 	if (triggerer == REMOTE_PLAYER) then 
  2072. 		rn07_breadcrumb_reached(triggerer, trigger, SYNC_REMOTE) 
  2073. 	end 
  2074. end 
  2075.  
  2076. function rn07_breadcrumb_reached_all(triggerer, trigger) 
  2077. 	rn07_breadcrumb_reached(triggerer, trigger, SYNC_ALL) 
  2078. end 
  2079.  
  2080. function rn07_breadcrumb_reached(triggerer, trigger, sync) 
  2081.  
  2082. 	if ( Current_minimap_mode[triggerer] ~= MINIMAP_MODE_LOCATIONS ) then 
  2083. 		return 
  2084. 	end 
  2085.  
  2086. 	for i = rn07_current_trigger[sync], sizeof_table(rn07_breadcrumb_triggers[sync]), 1 do 
  2087. 		local breadcrumb = rn07_breadcrumb_triggers[sync][i] 
  2088. 		trigger_enable(breadcrumb,false) 
  2089. 		on_trigger("",trigger) 
  2090. 		marker_remove_trigger(trigger, sync) 
  2091. 		rn07_current_trigger[sync] = i+1 
  2092. 		if(rn07_breadcrumb_triggers[sync][i] == trigger) then 
  2093. 			break 
  2094. 		end 
  2095. 	end 
  2096.  
  2097. 	-- Add an effect to the next trigger 
  2098. 	if (rn07_breadcrumb_effect[sync]) then 
  2099. 		local minimap_icon = MINIMAP_ICON_LOCATION 
  2100. 		if( rn07_breadcrumb_effect[sync] == INGAME_EFFECT_VEHICLE_PROTECT_ACQUIRE) then 
  2101. 			minimap_icon = MINIMAP_ICON_PROTECT_ACQUIRE 
  2102. 		end 
  2103.  
  2104. 		marker_add_trigger(	rn07_breadcrumb_triggers[sync][rn07_current_trigger[sync]], 
  2105. 									minimap_icon, 
  2106. 									rn07_breadcrumb_effect[sync], 
  2107. 									sync) 
  2108.  
  2109. 	end 
  2110. 		 
  2111. end 
  2112.  
  2113. function rn07_toggle_location_reached_all(triggerer,trigger) 
  2114. 	rn07_toggle_location_reached(triggerer, trigger, SYNC_ALL) 
  2115. end 
  2116.  
  2117. function rn07_toggle_location_reached_local(triggerer,trigger) 
  2118. 	if (triggerer == LOCAL_PLAYER) then 
  2119. 		rn07_toggle_location_reached(triggerer, trigger, SYNC_LOCAL) 
  2120. 	end 
  2121. end 
  2122.  
  2123. function rn07_toggle_location_reached_remote(triggerer,trigger) 
  2124. 	if (triggerer == REMOTE_PLAYER) then 
  2125. 		rn07_toggle_location_reached(triggerer, trigger, SYNC_REMOTE) 
  2126. 	end 
  2127. end 
  2128.  
  2129. function rn07_toggle_location_reached(triggerer, trigger, sync) 
  2130.  
  2131. 	if ( Current_minimap_mode[triggerer] ~= MINIMAP_MODE_LOCATIONS ) then 
  2132. 		return 
  2133. 	end 
  2134.  
  2135. 	rn07_location_reached[sync] = true		 
  2136.  
  2137. 	-- Disable all breadcrumbs 
  2138. 	for i = rn07_current_trigger[sync], sizeof_table(rn07_breadcrumb_triggers[sync]), 1 do 
  2139. 		local breadcrumb = rn07_breadcrumb_triggers[sync][i] 
  2140. 		trigger_enable(breadcrumb,false) 
  2141. 		on_trigger("",trigger) 
  2142. 		marker_remove_trigger(trigger, sync) 
  2143. 	end 
  2144. 	 
  2145. end 
  2146.  
  2147. function rn07_yield_until(condition) 
  2148. 	while(not condition) do 
  2149. 		thread_yield() 
  2150. 	end 
  2151. end 
  2152.  
  2153. -- Play dialogue lines. Lines are divided into three types: mission conversations, 
  2154. -- random gat lines, and bicker conversations. Mission conversations have the highest 
  2155. -- priority. 
  2156. Rn07_dialogue_mission = "" 
  2157. Rn07_dialogue_gat = "" 
  2158. Rn07_dialogue_bicker = 1 
  2159. function rn07_play_dialogue() 
  2160.  
  2161. 	local dialogue_delay = 0.25	-- The delay between dialogue checks 
  2162. 	local bicker_chance = .05		-- Chance that a bicker is played under valid conditions 
  2163. 	local min_bicker_ticks = 40	-- Min number ticks to skip between bicker conversations  
  2164. 	local cur_bicker_ticks = 0		-- Current number of ticks 
  2165. 	 
  2166. 	--Randomize the order of the bicker conversations 
  2167. 	local rand_order = {} 
  2168. 	local num_bickers = sizeof_table(Rn07_bicker_conversations) 
  2169. 	for i = 1, num_bickers, 1 do 
  2170. 		rand_order[i] = i 
  2171. 	end 
  2172. 	for i = 1, num_bickers, 1 do 
  2173. 		local rand1 = rand_int(1,num_bickers) 
  2174. 		local rand2 = rand_int(1,num_bickers) 
  2175. 		rand_order[rand1],rand_order[rand2] = rand_order[rand2],rand_order[rand1] 
  2176. 	end 
  2177.  
  2178. 	-- Wait a few seconds before we start talking 
  2179. 	delay(8.0) 
  2180.  
  2181. 	-- Play the highest priority line that's available. 
  2182. 	while(true) do 
  2183.  
  2184. 		-- Tick down 
  2185. 		if (cur_bicker_ticks > 0) then 
  2186. 			cur_bicker_ticks = cur_bicker_ticks - 1 
  2187. 		end 
  2188.  
  2189. 		-- Play missions lines if available. 
  2190. 		if(Rn07_dialogue_mission ~= "") then 
  2191.  
  2192. 			audio_play_conversation(Rn07_mission_conversations[Rn07_dialogue_mission])		 
  2193. 			Rn07_dialogue_mission = "" 
  2194.  
  2195. 		-- Play a random Gat line if one is available 
  2196. 		elseif( (Rn07_dialogue_gat ~= "") and (not Gat_in_cardiac_arrest) ) then 
  2197.  
  2198. 			audio_play_for_character(Rn07_dialogue_gat, CHARACTER_GAT, "voice", false, true) 
  2199.  
  2200. 		-- Maybe play a bicker conversation if any are left and Gat isn't in cardiac arrest. 
  2201. 		elseif( (Rn07_dialogue_bicker ~= -1) and (not Gat_in_cardiac_arrest) and (cur_bicker_ticks == 0) ) then 
  2202.  
  2203. 			-- Make sure that the player and Gat are near each other 
  2204. 			local dist = get_dist(LOCAL_PLAYER, CHARACTER_GAT) 
  2205. 			local roll = rand_float(0,1) 
  2206. 			if( (dist <= 8) and (roll <= bicker_chance) ) then 
  2207. 				audio_play_conversation(Rn07_bicker_conversations[rand_order[Rn07_dialogue_bicker]]) 
  2208.  
  2209. 				-- Make sure to wait a ceratin amount of time before the next bicker conversation 
  2210. 				cur_bicker_ticks = min_bicker_ticks 
  2211.  
  2212. 				-- Move to the next bicker conversation if there is one 
  2213. 				Rn07_dialogue_bicker = Rn07_dialogue_bicker + 1 
  2214. 				if(Rn07_dialogue_bicker > num_bickers) then 
  2215. 					Rn07_dialogue_bicker = -1 
  2216. 				end 
  2217.  
  2218. 			end 
  2219. 		end 
  2220.  
  2221. 		-- Gat's lines are triggered by events such as Gat taking damage. We don't want 
  2222. 		-- to play any of these if much time has passed since the event. 
  2223. 		Rn07_dialogue_gat = "" 
  2224.  
  2225. 		delay(dialogue_delay) 
  2226. 		thread_yield() 
  2227. 	end 
  2228. end 
  2229.  
  2230. -- Cleanup mission 
  2231. function rn07_cleanup() 
  2232.  
  2233. 	IN_COOP = coop_is_active() 
  2234.  
  2235. 	-- Make sure that the players don't end up stuck in the hospital 
  2236. 	local local_maybe_stuck = true 
  2237. 	local remote_maybe_stuck = IN_COOP 
  2238.  
  2239. 	-- Not stuck if we're in the heli 
  2240. 	if (vehicle_exists(VEHICLE_HELICOPTER) and (not vehicle_is_destroyed(VEHICLE_HELICOPTER)) ) then 
  2241. 		if (character_is_in_vehicle(LOCAL_PLAYER, VEHICLE_HELICOPTER)) then 
  2242. 			local_maybe_stuck = false 
  2243. 		end 
  2244. 		if (IN_COOP and character_is_in_vehicle(REMOTE_PLAYER, VEHICLE_HELICOPTER)) then 
  2245. 			remote_maybe_stuck = false 
  2246. 		end 
  2247. 	end 
  2248.  
  2249. 	-- Not stuck if we're far from the hospital 
  2250. 	local hospital_radius = 70 
  2251. 	if (get_dist(LOCAL_PLAYER, NAVPOINT_HOSPITAL_CENTER) > hospital_radius) then 
  2252. 		local_maybe_stuck = false 
  2253. 	end 
  2254. 	if (IN_COOP and get_dist(REMOTE_PLAYER, NAVPOINT_HOSPITAL_CENTER) > hospital_radius) then 
  2255. 		remote_maybe_stuck = false 
  2256. 	end 
  2257.  
  2258. 	-- Teleport players who might be stuck to spots in front of the hospital 
  2259. 	if (remote_maybe_stuck) then 
  2260. 		teleport(REMOTE_PLAYER, NAVPOINT_REMOTE_MISSION_END) 
  2261. 	end 
  2262. 	if (local_maybe_stuck) then 
  2263. 		teleport(LOCAL_PLAYER, NAVPOINT_REMOTE_MISSION_END) 
  2264. 	end 
  2265.  
  2266. 	-- Enable the ambient ambulance parking spawn in front of the hospital 
  2267. 	if (not IN_COOP) then 
  2268. 		parking_spot_enable(PARKING_SPAWN_AMBULANCE, true) 
  2269. 	end 
  2270.  
  2271. 	-- Swap out the interior chunks 
  2272. 	city_chunk_swap("SR2_IntDTMisHospital", "normal", true, true, true) 
  2273. 	city_chunk_swap("SR2_IntDTMisHospital02", "normal", false, true, true) 
  2274. 	city_chunk_swap("SR2_IntDTMisHospital03", "normal", true, true, true) 
  2275.  
  2276. 	sprint_reset_local_overrides() 
  2277.  
  2278. 	-- Make sure that the player can use grenades 
  2279. 	inv_weapon_disable_slot(WEAPON_SLOT_THROWN, false, SYNC_LOCAL) 
  2280.  
  2281. 	if(vehicle_exists(VEHICLE_HELICOPTER) and (not vehicle_is_destroyed(VEHICLE_HELICOPTER))) then 
  2282. 		turn_vulnerable(VEHICLE_HELICOPTER) 
  2283. 	end 
  2284.  
  2285. 	if(character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT)) then 
  2286. 		character_release_human_shield(LOCAL_PLAYER, true) 
  2287. 		clear_animation_state(LOCAL_PLAYER) 
  2288. 	end 
  2289.  
  2290. 	-- Stop overloading Ronin personas 
  2291. 	persona_override_group_stop(RONIN_PERSONAS,POT_SITUATIONS[POT_ATTACK]) 
  2292.  
  2293. 	-- Reset the respawn distance 
  2294. 	npc_respawn_dist_reset() 
  2295.  
  2296. 	-- Reset Ronin notoriety 
  2297. 	notoriety_set_min("Ronin",0) 
  2298. 	notoriety_set_max("Ronin",5) 
  2299. 	notoriety_set("Ronin",0) 
  2300. 	 
  2301. 	--Reenable recruiting 
  2302. 	party_set_recruitable(true) 
  2303.  
  2304. 	-- Remove mnimap icons, ingame effects 
  2305. 	marker_remove_vehicle(VEHICLE_HELICOPTER) 
  2306. 	marker_remove_npc(CHARACTER_GAT) 
  2307. 	for i,shock_paddle in pairs(SHOCK_PADDLES) do 
  2308. 		marker_remove_item(shock_paddle, SYNC_LOCAL) 
  2309. 	end 
  2310.  
  2311. 	-- Remove callbacks 
  2312.  
  2313. 		-- Remove failure callbacks 
  2314. 		on_death("", CHARACTER_GAT) 
  2315. 		on_vehicle_destroyed("", VEHICLE_HELICOPTER) 
  2316.  
  2317. 		-- Remove damage callbacks 
  2318. 		on_take_damage("",CHARACTER_GAT) 
  2319. 		on_take_damage("",VEHICLE_HELICOPTER) 
  2320.  
  2321. 		-- Remove vehicle triggers 
  2322. 		on_vehicle_enter("",VEHICLE_HELICOPTER) 
  2323.  
  2324. 		-- disable all triggers, remove callbacks 
  2325. 		for i, trigger in pairs(TABLE_ALL_TRIGGERS) do 
  2326. 			on_trigger("",trigger) 
  2327. 			trigger_enable(trigger,false) 
  2328. 		end 
  2329.  
  2330. 		-- disable area-entrance triggers, remove callbacks 
  2331. 		for entrance, area in pairs(ENTRANCE_TARGET_AREAS) do 
  2332. 			on_trigger("",entrance) 
  2333. 			trigger_enable(entrance, false) 
  2334. 		end 
  2335.  
  2336. 		-- disable all area entrances, remove callbacks 
  2337. 		for entrance, area in pairs(ENTRANCE_TARGET_AREAS) do 
  2338. 			on_trigger("",entrance) 
  2339. 			trigger_enable(entrance,false) 
  2340. 		end 
  2341.  
  2342. 		-- Remove lieutenant callbacks 
  2343. 		for i,lieutenant in pairs(PATROL_GROUP_MEMBERS["floor_1"]) do 
  2344. 			on_death("",lieutenant) 
  2345. 			on_respawn("",lieutenant) 
  2346. 		end 
  2347. 		for i,lieutenant in pairs(PATROL_GROUP_MEMBERS["floor_2"]) do 
  2348. 			on_death("",lieutenant)			 
  2349. 			on_respawn("",lieutenant) 
  2350. 		end 
  2351. 		for i,lieutenant in pairs(PATROL_GROUP_MEMBERS["floor_3"]) do 
  2352. 			on_death("",lieutenant) 
  2353. 			on_respawn("",lieutenant) 
  2354. 		end 
  2355. 		for i,lieutenant in pairs(PATROL_GROUP_MEMBERS["floor_4"]) do 
  2356. 			on_death("",lieutenant) 
  2357. 			on_respawn("",lieutenant) 
  2358. 		end 
  2359.  
  2360. 	-- destroy all groups 
  2361. 	for i, group in pairs(TABLE_ALL_GROUPS) do 
  2362. 		group_destroy(group) 
  2363. 	end 
  2364.  
  2365. 	-- release all coop-only groups 
  2366. 	if (IN_COOP) then 
  2367. 		for i, group in pairs(TABLE_ALL_COOP_GROUPS) do 
  2368. 			group_destroy(group) 
  2369. 		end 
  2370. 	end 
  2371. end 
  2372.  
  2373. function rn07_swap_gats() 
  2374.  
  2375. 	-- Release old gat 
  2376. 	if(character_has_specific_human_shield(LOCAL_PLAYER, CHARACTER_GAT)) then 
  2377. 		character_release_human_shield(LOCAL_PLAYER, true) 
  2378. 	end 
  2379. 	delay(1.0) 
  2380.  
  2381. 	-- Set non gurney-gat's hit points 
  2382. 	set_max_hit_points(CHARACTER_GAT_NORMAL, GAT_HIT_POINTS_HELI) 
  2383. 	set_current_hit_points(CHARACTER_GAT_NORMAL, GAT_HIT_POINTS) 
  2384.  
  2385. 	-- Hide old gat, show new one 
  2386. 	character_hide(CHARACTER_GAT) 
  2387. 	character_show(CHARACTER_GAT_NORMAL) 
  2388.  
  2389. 	-- Eliminate callbacks from the old gat, add to new one (Normals gat's damage handled by rn07_handle_helicopter_damaged) 
  2390. 	on_death("", CHARACTER_GAT) 
  2391. 	on_take_damage("", CHARACTER_GAT) 
  2392. 	on_death("rn07_failure_gat_died", CHARACTER_GAT_NORMAL) 
  2393.  
  2394. 	--remove inventory from new Gat 
  2395. 	inv_item_remove_all(CHARACTER_GAT_NORMAL) 
  2396.  
  2397. 	-- Kill off the old syphon thread and start a new one 
  2398. 	thread_kill(Thread_syphon) 
  2399. 	Thread_syphon = thread_new("rn07_health_syphon_gat", CHARACTER_GAT_NORMAL) 
  2400.  
  2401.  
  2402. end 
  2403.  
  2404. function rn07_hq_reached(triggerer) 
  2405. 	if(vehicle_exists(VEHICLE_HELICOPTER) and character_is_in_vehicle(triggerer, VEHICLE_HELICOPTER)) then 
  2406. 		rn07_complete() 
  2407. 	end 
  2408. end 
  2409.  
  2410. function rn07_complete() 
  2411. 	--bink_play_movie("ro07-2.bik") 
  2412.  
  2413. 	-- End the mission with success 
  2414. 	mission_end_success("rn07", "ro07-02") 
  2415. end 
  2416.  
  2417.  
  2418. function rn07_success() 
  2419. 	-- Called when the mission has ended with success 
  2420. end 
  2421.  
  2422. -- MISSION FAILURE FUNCTIONS -------------------------------- 
  2423.  
  2424. function rn07_failure_gat_died() 
  2425. 	-- End the mission, Gat died 
  2426. 	mission_end_failure("rn07", HELPTEXT_FAILURE_GAT_DIED) 
  2427. end 
  2428.  
  2429. function rn07_failure_gat_abandoned() 
  2430. 	-- End the mission, Gat abandoned 
  2431. 	mission_end_failure("rn07", HELPTEXT_FAILURE_GAT_ABANDONED) 
  2432. end 
  2433.  
  2434. function rn07_failure_helicopter_destroyed() 
  2435. 	-- End the mission, Helicopter destroyed 
  2436. 	delay(2.0) 
  2437. 	mission_end_failure("rn07", HELPTEXT_FAILURE_HELICOPTER_DESTROYED) 
  2438. end 
  2439.