sr2lua/rn06.lua

  1. -- rn06.lua 
  2. -- SR2 mission script 
  3. -- 3/28/07 
  4.  
  5. -- Global constants (All caps == GLOBAL CONSTANT) 
  6. --[[	In general, shouldn't be modified in running code, except for maybe in a setup function ) 
  7.  
  8. ]] 
  9. 	-- Coop mission? 
  10. 	IN_COOP	= false 
  11.  
  12. 	-- GROUPS -- 
  13. 		GROUP_START_CAR			= "rn06_$Gstart_car" 
  14. 		GROUP_CUTSCENE				= "rn06_$Gcutscene" 
  15. 		GROUP_MELEE_PART1			= "rn06_$Gmelee_part1" 
  16. 		GROUP_MELEE_PART2_A		= "rn06_$Gmelee_part2_a" 
  17. 		GROUP_MELEE_PART2_B		= "rn06_$Gmelee_part2_b" 
  18. 		GROUP_MELEE_PART2_C		= "rn06_$Gmelee_part2_c" 
  19. 		GROUP_JYUNICHI				= "rn06_$Gjyunichi" 
  20.  
  21. 		-- List of all groups, makes cleaning up more convenient 
  22. 		TABLE_ALL_GROUPS			= {	GROUP_START_CAR, GROUP_CUTSCENE, GROUP_MELEE_PART1, GROUP_MELEE_PART2_A,  
  23. 												GROUP_MELEE_PART2_B, GROUP_MELEE_PART2_C, GROUP_JYUNICHI} 
  24.  
  25. 		TABLE_ALL_COOP_GROUPS	= {	} 
  26. 	 
  27. 	-- GROUP MEMBER TABLES --  
  28. 		MEMBERS_GROUP_MELEE_PART1 = {	"rn06_$c000", "rn06_$c001", "rn06_$c002", "rn06_$c003", "rn06_$c004", 
  29. 												"rn06_$c005", "rn06_$c006", "rn06_$c007", "rn06_$c008", "rn06_$c009", 
  30. 												"rn06_$c010", "rn06_$c011", "rn06_$c012"} 
  31.  
  32. 		MEMBERS_GROUP_MELEE_PART2_A = {	"rn06_$c023", "rn06_$c024", "rn06_$c025", "rn06_$c026", "rn06_$c027", 
  33. 													"rn06_$c028", "rn06_$c029", "rn06_$c030", "rn06_$c031", "rn06_$c032", 
  34. 													"rn06_$c033", "rn06_$c034"} 
  35.  
  36. 		MEMBERS_GROUP_MELEE_PART2_B = {	"rn06_$c036", "rn06_$c035", "rn06_$c037", "rn06_$c038", "rn06_$c039", 
  37. 													"rn06_$c040", "rn06_$c041", "rn06_$c042", "rn06_$c043", "rn06_$c044", 
  38. 													"rn06_$c045", "rn06_$c046"} 
  39.  
  40. 		MEMBERS_GROUP_MELEE_PART2_C = {	"rn06_$c047", "rn06_$c048", "rn06_$c049", "rn06_$c050", "rn06_$c051", 
  41. 													"rn06_$c052", "rn06_$c053", "rn06_$c054", "rn06_$c055", "rn06_$c056", 
  42. 													"rn06_$c057", "rn06_$c058"} 
  43.  
  44. 	-- TRIGGERS --  
  45. 		TRIGGER_RESTAURANT_DEST	= "rn06_$Trestaurant_dest" 
  46.  
  47. 		-- top level entrances 
  48. 		TRIGGER_ENTRANCE_NORTH	= "rn06_$Tentrance_north" 
  49. 		TRIGGER_ENTRANCE_WEST	= "rn06_$Tentrance_west" 
  50. 		TRIGGER_ENTRANCE_EAST	= "rn06_$Tentrance_east" 
  51. 		TRIGGER_ENTRANCE_SOUTH	= "rn06_$Tentrance_south" 
  52.  
  53. 		TABLE_ENTRANCE_TRIGGERS = {	TRIGGER_ENTRANCE_NORTH, TRIGGER_ENTRANCE_WEST, 
  54. 												TRIGGER_ENTRANCE_EAST, TRIGGER_ENTRANCE_SOUTH}	 
  55.  
  56. 		-- List of all triggers, makes cleaning up more convenient 
  57. 		TABLE_ALL_TRIGGERS		= {	TRIGGER_RESTAURANT_DEST, TRIGGER_ENTRANCE_NORTH, TRIGGER_ENTRANCE_WEST, 
  58. 												TRIGGER_ENTRANCE_EAST, TRIGGER_ENTRANCE_SOUTH}		 
  59.  
  60. 	-- VEHICLES -- 
  61.  
  62.  
  63. 	-- CHARACTERS -- 
  64. 		CHARACTER_JYUNICHI		= "rn06_$Cjyunichi" 
  65.  
  66. 	-- CHECKPOINTS 
  67. 		 
  68. 		CHECKPOINT_START						= MISSION_START_CHECKPOINT			-- defined in ug_lib.lua 
  69. 		CHECKPOINT_KANTO						= "rn06_checkpoint_kanto"			-- players have arrived at the restaurant 
  70.  
  71. 	-- NAVPOINTS 
  72.  
  73. 		-- the mission start locations 
  74. 		NAVPOINT_LOCAL_PLAYER_START					= "mission_start_sr2_city_$rn06" 
  75. 		NAVPOINT_REMOTE_PLAYER_START					= "rn06_$Nremote_player_start" 
  76.  
  77. 		-- melee 1 start locations 
  78. 		NAVPOINT_LOCAL_PLAYER_START_MELEE_PART1	= "rn06_$Nlocal_start_melee_part1" 
  79. 		NAVPOINT_REMOTE_PLAYER_START_MELEE_PART1	= "rn06_$Nremote_start_melee_part1" 
  80.  
  81. 		-- Jyunichi fight start locations 
  82. 		NAVPOINT_LOCAL_PLAYER_START_JYUNICHI		= "rn06_$Nlocal_start_jyunichi" 
  83. 		NAVPOINT_REMOTE_PLAYER_START_JYUNICHI		= "rn06_$Nremote_start_jyunichi" 
  84.  
  85. 		-- If the players finish the mission inside of Kanto, they are teleported to these 
  86. 		-- locations. 
  87. 		NAVPOINT_LOCAL_KANTO_EXIT						= "rn06_$Nlocal_kanto_exit" 
  88. 		NAVPOINT_REMOTE_KANTO_EXIT						= "rn06_$Nremote_kanto_exit" 
  89.  
  90. 	-- MOVERS 
  91. 		MOVER_ENTRANCE_MAIN1 = "rn06_$MMdoor_main1" 
  92. 		MOVER_ENTRANCE_MAIN2 = "rn06_$MMdoor_main2" 
  93.  
  94. 		RESTAURANT_MOVERS_TO_HIDE =  
  95. 		{ 
  96. 			"rn06_$MM_table_1", "rn06_$MM_table_2", "rn06_$MM_table_3", "rn06_$MM_table_4", 
  97. 			"rn06_$MM_chair_1", "rn06_$MM_chair_2", "rn06_$MM_chair_3", "rn06_$MM_chair_4", 
  98. 			"rn06_$MM_chair_5", "rn06_$MM_chair_6", "rn06_$MM_chair_7", "rn06_$MM_chair_8", 
  99. 		} 
  100.  
  101. 	-- localized helptext messages 
  102. 		HELPTEXT_HUD_HEALTH_JYUNICHI			= "rn06_hud_jyunichi_health" 
  103.  
  104. 		HELPTEXT_PROMPT_LOCATION_RESTAURANT = "rn06_prompt_location_restaurant" 
  105. 		HELPTEXT_PROMPT_ENTER_RESTAURANT		= "rn06_prompt_enter_restaurant" 
  106. 		HELPTEXT_PROMPT_DEFEND_YOURSELF		= "rn06_prompt_defend_yourself" 
  107. 		HELPTEXT_PROMPT_SWORD_COUNTER			= "rn06_prompt_sword_counter" 
  108.  
  109. 	-- Possible animations for enemies who haven't entered melee combat 
  110. 		TABLE_ENEMY_ANIMATIONS	= {	"react Cheer", "crouch", "stand"} 
  111. 	 
  112. 	-- MISC CONSTANTS 
  113. 		MELEE_ENEMY_HEALTH_MULTIPLIER			= 1.5 
  114. 		MAX_ENEMIES_ATTACKING					= 12 
  115. 		JYUNICHI_HIT_POINTS						= 1500 
  116. 		SWORD											= "samurai_sword" 
  117. 		-- how long Jyunichi remains vulnerable to being grabbed before he revives 
  118. 		JYUNICHI_PASSED_OUT_TIME_S				= 10	 
  119. 		JYUNICHI_REVIVE_PERCENT					= .50 
  120. 		NPC_MAX_CORPSES_OVERRIDE				= 40 
  121.  
  122. 		SWORD_COUNTER_NAG_INITIAL_DELAY_S	= 15 -- How long to wait until the first sword counter nag displays 
  123. 		SWORD_COUNTER_NAG_REPEAT_DELAY_S		= 30 -- How long to wait between nags after the first one. 
  124. 	 
  125. 		RONIN_PERSONAS_ABBREV	=  
  126. 		{ 
  127. 			["AM_Ron2"]	=	"AMRON2", 
  128.  
  129. 			["AF_Ron1"]	=	"AFRON1", 
  130.  
  131. 			["WM_Ron1"]	=	"WMRON1", 
  132.  
  133. 			["WF_Ron1"]	=	"WFRON1", 
  134. 			["WF_Ron2"]	=	"WFRON2", 
  135. 		} 
  136.  
  137. -- Global Variables (First letter caps == Global Variable) 
  138.  
  139. 	Location_reached					= false 
  140. 	Restaurant_entered				= false 
  141. 	Enemy_set_cleared					= false 
  142. 	Enemy_set_objective_helptext	= "" 
  143. 	Sword_loaned						= false 
  144. 	Jyunichi_revived					= false 
  145. 	Rn06_inside_kanto					= false 
  146.  
  147. 	-- THREADS 
  148. 	--Thread_dealer						= -1 
  149. 	Table_all_threads					= {	} 
  150. 	THREAD_SWORD_COUNTER_NAG		= INVALID_THREAD_HANDLE 
  151.  
  152. -- TEMPORARY Global Variables 
  153.  
  154. -- REQUIRED MISSION FUNCTIONS ------------------------------- 
  155.  
  156. function rn06_start(rn06_checkpoint, is_restart) 
  157.  
  158. 	if (rn06_checkpoint == CHECKPOINT_START) then 
  159. 		if (not is_restart) then 
  160. 			cutscene_play("ro06-01") 
  161. 		end 
  162. 		fade_out(0) 
  163. 	end 
  164.  
  165. 	rn06_initialize(rn06_checkpoint) 
  166.  
  167. 	if (rn06_checkpoint == CHECKPOINT_START) then 
  168.  
  169. 		-- Send player(s) to the restaurant's driveway 
  170. 		rn06_send_to_location(TRIGGER_RESTAURANT_DEST, HELPTEXT_PROMPT_LOCATION_RESTAURANT, SYNC_ALL) 
  171.  
  172. 		-- Now send them inside 
  173. 		rn06_enter_restaurant() 
  174.  
  175. 		-- Prepare for the restaurant fight 
  176. 		fade_out(1.0,{0,0,0}, SYNC_ALL) 
  177. 		fade_out_block() 
  178.  
  179. 		-- Disable action nodes and ped spawning 
  180. 		action_nodes_enable(false) 
  181. 		spawning_pedestrians(false, true) 
  182.  
  183. 		rn06_cleanup_drive() 
  184. 		rn06_teleport_players_inside() 
  185.  
  186. 		for i, mover in pairs(RESTAURANT_MOVERS_TO_HIDE) do 
  187. 			mesh_mover_hide(mover) 
  188. 		end 
  189.  
  190. 		cutscene_play("IG_rn06_scene1") 
  191. 		group_destroy(GROUP_CUTSCENE) 
  192.  
  193. 		rn06_setup_restaurant(true) 
  194. 		fade_in(1.0,SYNC_ALL) 
  195.  
  196. 		mission_set_checkpoint(CHECKPOINT_KANTO) 
  197. 		rn06_checkpoint = CHECKPOINT_KANTO 
  198.  
  199. 	-- end of CHECKPOINT_START, begining of CHECKPOINT_KANTO 
  200. 	elseif (rn06_checkpoint == CHECKPOINT_KANTO) then 
  201. 		-- Intentionally not doing anything here 
  202. 	end -- ends CHECKPOINT_KANTO		 
  203.  
  204. 	tutorial_start("combat_swords", 1000, true) 
  205.  
  206. 	-- Wait a bit, then have all civilians flee 
  207. 	delay(1.0) 
  208. 		 
  209. 	-- Delay a bit more, then have Jyunichi attack 
  210. 	delay(2.0) 
  211. 	thread_new("rn06_jyunichi_defend_thread") 
  212.  
  213. 	THREAD_SWORD_COUNTER_NAG = thread_new("rn06_sword_counter_nag") 
  214.  
  215. end 
  216.  
  217. function rn06_sword_counter_nag() 
  218. 	delay(SWORD_COUNTER_NAG_INITIAL_DELAY_S) 
  219. 	while(true) do 
  220. 		mission_help_table_nag(HELPTEXT_PROMPT_SWORD_COUNTER) 
  221. 		delay(SWORD_COUNTER_NAG_REPEAT_DELAY_S) 
  222. 	end 
  223. end 
  224.  
  225. function rn06_initialize(checkpoint) 
  226.  
  227. 	mission_start_fade_out(0.0) 
  228.  
  229. 	rn06_initialize_common() 
  230. 	rn06_initialize_checkpoint(checkpoint) 
  231.  
  232. 	mission_start_fade_in() 
  233. end 
  234.  
  235. function	rn06_initialize_common() 
  236.  
  237. 	set_mission_author("Phillip Alexander") 
  238.  
  239. 	if (coop_is_active()) then 
  240. 		IN_COOP	= true 
  241. 	end 
  242.  
  243. end 
  244.  
  245. function	rn06_initialize_checkpoint(checkpoint) 
  246.  
  247. 	if (checkpoint == CHECKPOINT_START) then 
  248.  
  249. 		-- Create a vehicle for the player(s) to use 
  250. 		group_create(GROUP_START_CAR, true) 
  251.  
  252. 		-- Teleport the player(s) to where they will need to be 
  253. 		teleport_coop(NAVPOINT_LOCAL_PLAYER_START, NAVPOINT_REMOTE_PLAYER_START) 
  254. 	else	 
  255.  
  256. 		-- Disable action nodes and ped spawning 
  257. 		action_nodes_enable(false) 
  258. 		spawning_pedestrians(false, true) 
  259.  
  260. 		rn06_players_inside_restaurant() 
  261. 		rn06_setup_restaurant(false) 
  262. 	end 
  263.  
  264. end 
  265.  
  266. function rn06_enter_restaurant() 
  267. 	mission_help_table(HELPTEXT_PROMPT_ENTER_RESTAURANT) 
  268. 	for i, entrance in pairs(TABLE_ENTRANCE_TRIGGERS) do 
  269. 		on_trigger("rn06_restaurant_entered", entrance) 
  270. 		trigger_enable(entrance,true) 
  271. 	end 
  272. 	marker_add_trigger(TRIGGER_ENTRANCE_SOUTH,MINIMAP_ICON_LOCATION,INGAME_EFFECT_LOCATION,SYNC_ALL) 
  273.  
  274. 	while( not Restaurant_entered) do 
  275. 		thread_yield() 
  276. 	end 
  277. end 
  278.  
  279. function rn06_players_inside_restaurant() 
  280. 	Rn06_inside_kanto = true 
  281. 	set_player_can_enter_exit_vehicles(LOCAL_PLAYER, false) 
  282. 	if(IN_COOP) then 
  283. 		set_player_can_enter_exit_vehicles(REMOTE_PLAYER, false) 
  284. 	end 
  285. end 
  286.  
  287. function rn06_cleanup_drive() 
  288. 	-- Destroy the vehicle, get rid of vehice and ped spawns 
  289. 	group_destroy(GROUP_START_CAR) 
  290. 	spawning_vehicles(false)	 
  291. end 
  292.  
  293. function rn06_teleport_players_inside() 
  294.  
  295. 	party_dismiss_all() 
  296.  
  297. 	if (character_is_in_vehicle(LOCAL_PLAYER)) then 
  298. 		vehicle_exit_teleport(LOCAL_PLAYER) 
  299. 	end 
  300.  
  301. 	-- The teleport coop function handles teleporting the coop player out of the vehicle 
  302. 	teleport_coop(NAVPOINT_LOCAL_PLAYER_START_MELEE_PART1, NAVPOINT_REMOTE_PLAYER_START_MELEE_PART1, true) 
  303.  
  304. 	rn06_players_inside_restaurant() 
  305.  
  306. end 
  307.  
  308. jyunichi_battle_audio_id = 0 
  309.  
  310. function rn06_setup_restaurant(disable_controls) 
  311. 	 
  312. 	-- Disable player controls 
  313. 	if(disable_controls) then 
  314. 		player_controls_disable(LOCAL_PLAYER) 
  315. 		if (IN_COOP) then 
  316. 			player_controls_disable(REMOTE_PLAYER) 
  317. 		end 
  318. 	end 
  319.  
  320. 	for i, mover in pairs(RESTAURANT_MOVERS_TO_HIDE) do 
  321. 		mesh_mover_hide(mover) 
  322. 	end 
  323.  
  324. 	-- Remove all followers 
  325. 	party_dismiss_all() 
  326.  
  327.  
  328. 	-- Give the players swords 
  329. 	inv_weapon_add_temporary(LOCAL_PLAYER, SWORD, 1, true) 
  330. 	inv_item_equip("samurai_sword",LOCAL_PLAYER) 
  331. 	party_use_melee_weapons_only(true) 
  332. 	if (IN_COOP) then 
  333. 		inv_weapon_add_temporary(REMOTE_PLAYER, SWORD, 1, true) 
  334. 		inv_item_equip("samurai_sword",REMOTE_PLAYER) 
  335. 	end 
  336. 	Sword_loaned	= true 
  337.  
  338. 	-- Override Ronin Attack peronas 
  339. 	persona_override_group_start(RONIN_PERSONAS_ABBREV,POT_SITUATIONS[POT_ATTACK], "RO06_ATTACK") 
  340.  
  341. 	-- Shut, lock doors 
  342. 	door_close(MOVER_ENTRANCE_MAIN1) 
  343. 	door_close(MOVER_ENTRANCE_MAIN2) 
  344. 	door_lock(MOVER_ENTRANCE_MAIN1, true) 
  345. 	door_lock(MOVER_ENTRANCE_MAIN2, true) 
  346.  
  347. 	-- Load or start loading Ronin groups 
  348. 	group_create(GROUP_JYUNICHI,true) 
  349. 	group_create_hidden(GROUP_MELEE_PART1, true) 
  350. 	 
  351. 	for i,enemy in pairs(MEMBERS_GROUP_MELEE_PART1) do 
  352. 		local enemy_hit_points = get_max_hit_points(enemy) 
  353. 		set_max_hit_points(enemy,enemy_hit_points * MELEE_ENEMY_HEALTH_MULTIPLIER) 
  354. 		set_always_sees_player_flag(enemy, true)  
  355. 	end 
  356.  
  357. 	-- Allow a larger than normal number of npcs corpses 
  358. 	npc_max_corpses_override(NPC_MAX_CORPSES_OVERRIDE) 
  359.  
  360. 	-- Prepare jyunichi 
  361. 	rn06_setup_jyunichi() 
  362.  
  363. 	-- Have the first set of Ronin attack 
  364. 	rn06_ronin_group_attack(MEMBERS_GROUP_MELEE_PART1) 
  365.  
  366. 	-- Enable sword combat 
  367. 	rn06_enable_sword_combat(true) 
  368. 	audio_throttle_type("Music", 0) 
  369.  
  370. 	--Only play the boss battle music if the player isn't already playing his/her own music 
  371. 	if (not audio_is_xmp_playing()) then 
  372. 		jyunichi_battle_audio_id = audio_play_do("JYUNICHI_BATTLE") 
  373. 	end 
  374.  
  375. 	notoriety_set("Ronin",3)	 
  376. 	notoriety_set_min("Ronin",3)	 
  377.  
  378. 	-- Reenable player controls 
  379. 	if (disable_controls) then 
  380. 		player_controls_enable(LOCAL_PLAYER) 
  381. 		if (IN_COOP) then 
  382. 			player_controls_enable(REMOTE_PLAYER) 
  383. 		end 
  384. 	end 
  385.  
  386. end 
  387.  
  388. function rn06_enable_sword_combat(enable) 
  389. 	combat_enable_sword_parries(enable) 
  390. 	combat_enable_sword_strafing(enable) 
  391.  
  392. 	local take_damage_callback = "" 
  393. 	if (enable) then 
  394. 		take_damage_callback = "rn06_player_damaged" 
  395. 		thread_new("rn06_always_ready") 
  396. 	end 
  397.  
  398. 	on_take_damage(take_damage_callback, LOCAL_PLAYER) 
  399. 	if(IN_COOP) then 
  400. 		on_take_damage(take_damage_callback, REMOTE_PLAYER) 
  401. 	end 
  402.  
  403. 	character_set_cannot_wield_havok_weapon(LOCAL_PLAYER, enable) 
  404. 	if (IN_COOP) then 
  405. 		character_set_cannot_wield_havok_weapon(REMOTE_PLAYER, enable) 
  406. 	end 
  407. end 
  408.  
  409. function rn06_always_ready() 
  410.  
  411. 	local function combat_ready(character) 
  412. 		if (	character_exists(character) and  
  413. 				(not character_is_dead(character)) and  
  414. 				(not character_is_ragdolled(character))  
  415. 			) then 
  416. 			character_set_combat_ready(character, true, 1.0) 
  417. 		end 
  418. 	end 
  419.  
  420. 	while(true) do 
  421. 		thread_yield() 
  422. 		combat_ready(LOCAL_PLAYER) 
  423. 		combat_ready(REMOTE_PLAYER) 
  424. 		combat_ready(CHARACTER_JYUNICHI) 
  425. 	end 
  426.  
  427. end 
  428.  
  429. function rn06_player_damaged(player, attacker, damage_percent) 
  430.  
  431. 	if (attacker == CHARACTER_JYUNICHI) then 
  432. 		character_ragdoll(player, 1000) 
  433. 		audio_play_persona_line(CHARACTER_JYUNICHI, "threat - alert (solo attack)") 
  434. 	end 
  435.  
  436. end 
  437.  
  438. function rn06_setup_jyunichi() 
  439.  
  440. 	inv_item_remove_all(CHARACTER_JYUNICHI) 
  441. 	set_max_hit_points(CHARACTER_JYUNICHI,JYUNICHI_HIT_POINTS) 
  442. 	--on_finished("rn06_complete", CHARACTER_JYUNICHI) 
  443. 	--on_death("rn06_jyunichi_passed_out", CHARACTER_JYUNICHI) 
  444. 	on_death("rn06_complete", CHARACTER_JYUNICHI) 
  445. 	damage_indicator_on(0, CHARACTER_JYUNICHI,0.0, HELPTEXT_HUD_HEALTH_JYUNICHI) 
  446. 	npc_set_boss_type(CHARACTER_JYUNICHI, AI_BOSS_JYUNICHI) 
  447.  
  448. 	persona_override_character_start(CHARACTER_JYUNICHI, POT_SITUATIONS[POT_ATTACK], "JYUNICHI_RON06_ATTACK") 
  449. 	persona_override_character_start(CHARACTER_JYUNICHI, POT_SITUATIONS[POT_TAKE_DAMAGE], "JYUNICHI_RON06_TAKEDAM") 
  450.  
  451. 	inv_item_add("dual_swords", 1, CHARACTER_JYUNICHI)  
  452. 	inv_item_equip("dual_swords",CHARACTER_JYUNICHI) 
  453.  
  454. 	on_take_damage("rn06_jyunichi_damaged", CHARACTER_JYUNICHI) 
  455. 	marker_add_npc(CHARACTER_JYUNICHI, MINIMAP_ICON_KILL, INGAME_EFFECT_KILL, SYNC_ALL) 
  456. --	character_allow_ragdoll(CHARACTER_JYUNICHI, false) 
  457. --	attack(CHARACTER_JYUNICHI) 
  458. end 
  459.  
  460. rn06_current_wave = 1 
  461.  
  462. -- Called when Jyunichi is damaged 
  463. -- damage_percent is Jyunichi's health percentage after the attack 
  464. function rn06_jyunichi_damaged(jyunichi, attacker, damage_percent) 
  465.  
  466. 	local wave_damage_thresholds = {.650, .300} 
  467. 	local wave_group = {GROUP_MELEE_PART2_A, GROUP_MELEE_PART2_B, GROUP_MELEE_PART2_C} 
  468. 	local wave_group_members =  
  469. 		{	MEMBERS_GROUP_MELEE_PART2_A, MEMBERS_GROUP_MELEE_PART2_B, MEMBERS_GROUP_MELEE_PART2_C 
  470. 		} 
  471. 	local wave_group_doors =	 
  472. 		{	{"rn06_$MM_door_1_left", "rn06_$MM_door_1_right"}, 
  473. 			{"rn06_$MM_door_2"}, 
  474. 			{"rn06_$MM_door_3"} 
  475. 		}	 
  476.  
  477. 	if (rn06_current_wave <= sizeof_table(wave_damage_thresholds)) then 
  478.  
  479. 		if (damage_percent < wave_damage_thresholds[rn06_current_wave]) then 
  480.  
  481. 			rn06_current_wave = rn06_current_wave + 1 
  482.  
  483. 			thread_new("rn06_ronin_group_attack", wave_group_members[rn06_current_wave], wave_group[rn06_current_wave],  
  484. 							wave_group_doors[rn06_current_wave][1],wave_group_doors[rn06_current_wave][2]) 
  485.  
  486. 		end 
  487. 		 
  488. 	end 
  489.  
  490. 	audio_play_persona_line(CHARACTER_JYUNICHI, "takes damage") 
  491. end 
  492.  
  493. function rn06_jyunichi_defend_thread() 
  494.  
  495. 	local is_attacking = false 
  496. 	npc_set_boss_always_defend(CHARACTER_JYUNICHI, true) 
  497.  
  498. 	while(not character_is_dead(CHARACTER_JYUNICHI)) do 
  499.  
  500. 		thread_yield() 
  501.  
  502. 		local should_attack = (rn06_living_enemies <= 2) 
  503. 		if (should_attack ~= is_attacking) then 
  504.  
  505. 			npc_set_boss_always_defend(CHARACTER_JYUNICHI, (not should_attack)) 
  506. 			if (should_attack) then 
  507. 				attack(CHARACTER_JYUNICHI) 
  508. 			end 
  509.  
  510. 			is_attacking = should_attack 
  511.  
  512. 		end 
  513. 	end 
  514. end 
  515.  
  516. rn06_max_enemies = 4 
  517. rn06_living_enemies = 0 
  518. function rn06_ronin_group_attack(group_members, group_name, door1,door2) 
  519.  
  520. 	if (group_name ~= nil) then 
  521. 		group_create_hidden(group_name, true) 
  522. 	end 
  523.  
  524. 	local num_to_spawn = rn06_max_enemies - rn06_living_enemies 
  525.  
  526. 	for i=1, num_to_spawn, 1 do 
  527. 		local ronin = group_members[i] 
  528. 		character_show(ronin) 
  529. 		on_death("rn06_ronin_killed",ronin) 
  530. 		rn06_living_enemies = rn06_living_enemies + 1 
  531. 	end 
  532.  
  533. 	if(door1) then 
  534. 		door_open(door1) 
  535. 	end 
  536.  
  537. 	if(door2) then 
  538. 		door_open(door2) 
  539. 	end 
  540.  
  541. 	-- Send the Ronin out one at a time so that they don't bunch up and get stuck in a doorway. 
  542. 	for i=1, num_to_spawn, 1 do 
  543. 		attack(group_members[i]) 
  544. 		delay(0.4) 
  545. 	end 
  546. 	 
  547. end 
  548.  
  549. function rn06_ronin_killed() 
  550. 	rn06_living_enemies = rn06_living_enemies - 1 
  551. end 
  552.  
  553. -- Cleanup mission 
  554. function rn06_cleanup() 
  555.  
  556. 	-- Check if the remote player has dropped 
  557. 	IN_COOP = coop_is_active() 
  558.  
  559. 	-- Turn off the Jyunichi boss-fight music 
  560. 	audio_stop(jyunichi_battle_audio_id) 
  561. 	audio_throttle_type("Music", 1) 
  562.  
  563. 	-- Disable sword combat 
  564. 	rn06_enable_sword_combat(false) 
  565.  
  566. 	-- Reenable action nodes and ped spawning 
  567. 	action_nodes_enable(true) 
  568. 	spawning_pedestrians(true) 
  569.  
  570. 	-- Unlock doors 
  571. 	door_lock(MOVER_ENTRANCE_MAIN1, false) 
  572. 	door_lock(MOVER_ENTRANCE_MAIN2, false) 
  573.  
  574. 	-- Remove Persona overrides 
  575. 	persona_override_group_stop(RONIN_PERSONAS,POT_SITUATIONS[POT_ATTACK]) 
  576.  
  577. 	-- Clean up spawning 
  578. 	npc_max_corpses_reset() 
  579. 	spawning_vehicles(true) 
  580.  
  581. 	-- Kill all secondary threads 
  582. 	for i, thread in pairs(Table_all_threads) do 
  583. 		thread_kill(thread) 
  584. 	end 
  585.  
  586. 	damage_indicator_off(0) 
  587.  
  588. 	-- Remove npc triggers, arrows 
  589. 	for i,enemy in pairs(MEMBERS_GROUP_MELEE_PART1) do 
  590. 		on_death("",enemy) 
  591. 		marker_remove_npc(enemy) 
  592. 	end 
  593. 	for i,enemy in pairs(MEMBERS_GROUP_MELEE_PART2_A) do 
  594. 		on_death("",enemy) 
  595. 		marker_remove_npc(enemy) 
  596. 	end	 
  597. 		for i,enemy in pairs(MEMBERS_GROUP_MELEE_PART2_B) do 
  598. 		on_death("",enemy) 
  599. 		marker_remove_npc(enemy) 
  600. 	end 
  601. 	for i,enemy in pairs(MEMBERS_GROUP_MELEE_PART2_C) do 
  602. 		on_death("",enemy) 
  603. 		marker_remove_npc(enemy) 
  604. 	end 
  605.  
  606. 	-- disable all triggers, remove callbacks 
  607. 	for i, trigger in pairs(TABLE_ALL_TRIGGERS) do 
  608. 		on_trigger("",trigger) 
  609. 		trigger_enable(trigger,false) 
  610. 	end 
  611.  
  612. 	-- destroy Jyunichi, don't need unique characters wandering around the city. 
  613. 	--persona_override_character_stop(CHARACTER_JYUNICHI, POT_SITUATIONS[POT_ATTACK]) 
  614. 	--persona_override_character_stop(CHARACTER_JYUNICHI, POT_SITUATIONS[POT_TAKE_DAMAGE]) 
  615. 	marker_remove_npc(CHARACTER_JYUNICHI) 
  616. 	group_destroy(GROUP_JYUNICHI) 
  617.  
  618. 	-- also destroy the starting vehicle, just so they don't pile up 
  619. 	group_destroy(GROUP_START_CAR) 
  620.  
  621. 	-- release all groups 
  622. 	for i, group in pairs(TABLE_ALL_GROUPS) do 
  623. 		group_destroy(group) 
  624. 	end 
  625. 	if (IN_COOP) then 
  626. 		for i, group in pairs(TABLE_ALL_COOP_GROUPS) do 
  627. 		group_destroy(group) 
  628. 		end 
  629. 	end 
  630.  
  631. 	-- remove temporary weapons 
  632. 	if (Sword_loaned) then 
  633. 		inv_weapon_remove_temporary(LOCAL_PLAYER, SWORD) 
  634. 		party_use_melee_weapons_only(false) 
  635. 		if (IN_COOP) then 
  636. 			inv_weapon_remove_temporary(REMOTE_PLAYER, SWORD) 
  637. 		end 
  638. 	end 
  639.  
  640. 	-- remove vehicle transition callbacks 
  641. 	on_vehicle_enter("",LOCAL_PLAYER) 
  642. 	on_vehicle_exit("",LOCAL_PLAYER) 
  643. 	if (IN_COOP) then 
  644. 		on_vehicle_enter("",REMOTE_PLAYER) 
  645. 		on_vehicle_exit("",REMOTE_PLAYER) 
  646. 	end 
  647.  
  648. 	-- If the players finish the mission inside of Kanto, teleport them outside and make sure that they 
  649. 	-- can enter vehicles. 
  650. 	if (Rn06_inside_kanto) then 
  651. 		set_player_can_enter_exit_vehicles(LOCAL_PLAYER, true) 
  652. 		teleport( LOCAL_PLAYER, NAVPOINT_LOCAL_KANTO_EXIT) 
  653. 		if (IN_COOP) then 
  654. 			teleport( REMOTE_PLAYER, NAVPOINT_REMOTE_KANTO_EXIT) 
  655. 			set_player_can_enter_exit_vehicles(REMOTE_PLAYER, true) 
  656. 		end 
  657. 	end 
  658.  
  659. end 
  660.  
  661. function rn06_success() 
  662. end 
  663.  
  664.  
  665. -- MISSION FUNCTIONS ---------------------------------------- 
  666.  
  667. function rn06_jyunichi_passed_out() 
  668. 	Jyunichi_revived = false 
  669. 	on_game_time_trigger("rn06_jyunichi_maybe_revive", JYUNICHI_PASSED_OUT_TIME_S * 40, 0, 0, 0, 0, 0) 
  670. end 
  671.  
  672. function rn06_jyunichi_maybe_revive() 
  673. 	if (not Jyunichi_revived) then 
  674. 		npc_revive(CHARACTER_JYUNICHI)	 
  675. 		-- Reset the revived flag 
  676. 		Jyunichi_revived = false 
  677. 		local max_hp = get_max_hit_points(CHARACTER_JYUNICHI) 
  678. 		set_current_hit_points(CHARACTER_JYUNICHI,JYUNICHI_REVIVE_PERCENT * max_hp) 
  679. 	end 
  680. end 
  681.  
  682. function rn06_jyunichi_revived() 
  683. 	Jyunichi_revived = true 
  684. end 
  685.  
  686. function rn06_restaurant_entered() 
  687. 	marker_remove_trigger(TRIGGER_ENTRANCE_SOUTH) 
  688. 	for i, entrance in pairs(TABLE_ENTRANCE_TRIGGERS) do 
  689. 		on_trigger("", entrance) 
  690. 		trigger_enable(entrance,false) 
  691. 	end 
  692. 	Restaurant_entered = true; 
  693. end 
  694.  
  695. function rn06_complete() 
  696. 	-- Stop the nag thread 
  697. 	if (THREAD_SWORD_COUNTER_NAG ~= INVALID_THREAD_HANDLE) then 
  698. 		thread_kill(THREAD_SWORD_COUNTER_NAG) 
  699. 	end 
  700. 	-- End the mission with success 
  701. 	inv_item_remove_all(CHARACTER_JYUNICHI) 
  702. 	mission_end_success("rn06", "ro06-02") 
  703. end 
  704.  
  705. -- UTILITY FUNCTIONS ---------------------------------------- 
  706.  
  707. function rn06_send_to_location(trigger, helptext) 
  708.  
  709. 	Location_reached = false 
  710.  
  711. 	-- enable the trigger, add a minimap icon, glow effect, waypoint, and callback 
  712. 	trigger_enable(trigger,true) 
  713. 	marker_add_trigger(trigger,MINIMAP_ICON_LOCATION,INGAME_EFFECT_VEHICLE_LOCATION,SYNC_ALL) 
  714. 	on_trigger("rn06_location_reached",trigger) 
  715. 	mission_waypoint_add( trigger, SYNC_ALL ) 
  716.  
  717. 	-- display helptext 
  718. 	mission_help_table(helptext) 
  719.  
  720. 	-- wait for player to arrive at the dealer 
  721. 	while (not Location_reached) do 
  722. 		thread_yield() 
  723. 	end 
  724.  
  725. 	mission_help_clear(SYNC_ALL) 
  726.  
  727. end 
  728.  
  729. function rn06_location_reached(triggerer,trigger) 
  730. 	Location_reached = true		 
  731. 	trigger_enable(trigger, false) 
  732. 	marker_remove_trigger(trigger, SYNC_ALL) 
  733. 	on_trigger("",trigger) 
  734. 	mission_waypoint_remove() 
  735. end 
  736.  
  737. MAX_VISIBLE_NPCS					= 24 
  738. Enemies_reserved					= 0 
  739. Enemies_attacking					= 0 
  740. Enemies_total						= 0 
  741. Next_wave_size						= 0 
  742.  
  743. function rn06_process_enemy_set_in_waves(wave_size_min, wave_size_max, mission_helptext, objective_helptext, ...) 
  744.  
  745. 	local cur_enemy_pool_ind	= 2 
  746. 	local enemy_pool = arg[cur_enemy_pool_ind] 
  747. 	local cur_enemy_pool_size	= sizeof_table(enemy_pool) 
  748. 	local group_show_ind	=	{} 
  749. 	local next_enemy_ind	= 1 
  750.  
  751. 	Enemies_total	= 0 
  752. 	Enemies_attacking = 0 
  753.  
  754. 	for i = 2, arg.n, 3 do 
  755. 		Enemies_total = Enemies_total + sizeof_table(arg[i]) 
  756. 	end 
  757.  
  758. 	Enemy_set_cleared = false 
  759.  
  760. 	Enemies_reserved = Enemies_total 
  761. 	Next_wave_size = MAX_ENEMIES_ATTACKING 
  762. 	if (Next_wave_size > Enemies_reserved) then 
  763. 		Next_wave_size = Enemies_reserved 
  764. 	end 
  765.  
  766. 	-- Display the help text 
  767. 	if(mission_helptext) then 
  768. 		mission_help_table(mission_helptext) 
  769. 	end 
  770.  
  771. 	-- Display the objective text 
  772. 	if(objective_helptext) then 
  773. 		Enemy_set_objective_helptext = objective_helptext 
  774. 		objective_text(0, Enemy_set_objective_helptext, 0, Enemies_total) 
  775. 	end 
  776. 	 
  777. 	-- assign non-combat callbacks for the first pool 
  778. 	for i=1, cur_enemy_pool_size, 1 do 
  779. 		--character_set_cannot_be_grabbed(enemy_pool[i],true) 
  780. 		npc_combat_enable(enemy_pool[i],false) 
  781. 		on_death("rn06_other_enemy_killed", enemy_pool[i]) 
  782. 	end 
  783.  
  784. 	while (not Enemy_set_cleared) do 
  785. 		-- See if we have room for a new wave of attackers 
  786. 		if (Next_wave_size > 0 and (Enemies_attacking + Next_wave_size) <= MAX_ENEMIES_ATTACKING) then 
  787. 			-- We have room, make them attack 
  788. 			for i= 1, Next_wave_size, 1 do 
  789.  
  790. 				-- if we aren't on the last enemy pool 
  791. 				if (cur_enemy_pool_ind < arg.n -1) then 
  792.  
  793. 					-- see if we need to start drawing from the next enemy pool 
  794. 					if (next_enemy_ind > cur_enemy_pool_size) then 
  795. 	 
  796. 						-- update the enemy pool index and size 
  797. 						cur_enemy_pool_ind = cur_enemy_pool_ind + 3 
  798. 						enemy_pool = arg[cur_enemy_pool_ind] 
  799. 						cur_enemy_pool_size	= sizeof_table(enemy_pool) 
  800. 	 
  801. 						-- reset the next_enemy_ind 
  802. 						next_enemy_ind = 1 
  803. 	 
  804. 						-- assign non-combat callbacks 
  805. 						for ii=1, cur_enemy_pool_size, 1 do 
  806. 							--character_set_cannot_be_grabbed(enemy_pool[ii],true) 
  807. 							npc_combat_enable(enemy_pool[ii],false) 
  808. 							on_death("rn06_other_enemy_killed", enemy_pool[ii]) 
  809. 						end 
  810.  
  811. 						-- make the enemy pool's group visible 
  812. 						group_show(arg[cur_enemy_pool_ind -1]) 
  813.  
  814. 						-- see if we need to open a door to release this group 
  815. 						local group_door = arg[cur_enemy_pool_ind +1] 
  816. 						if (group_door ~= "") then 
  817. 							door_open(group_door) 
  818. 						end 
  819. 					end 
  820. 				end 
  821.  
  822. 				while(character_is_dead(enemy_pool[next_enemy_ind])) do 
  823. 					next_enemy_ind = next_enemy_ind +1 
  824. 				end 
  825.  
  826. 				-- make the next npc attack: assign callback, add marker and make combat ready 
  827. 				on_death("rn06_attacking_enemy_killed", enemy_pool[next_enemy_ind]) 
  828. 				marker_add_npc(enemy_pool[next_enemy_ind], MINIMAP_ICON_KILL, INGAME_EFFECT_KILL, SYNC_ALL) 
  829. 				npc_combat_enable(enemy_pool[next_enemy_ind],true) 
  830.  
  831. 				next_enemy_ind = next_enemy_ind +1 
  832. 			end 
  833. 			-- update the number of npcs in various pools 
  834. 			Enemies_attacking = Enemies_attacking + Next_wave_size 
  835. 			Enemies_reserved = Enemies_reserved - Next_wave_size 
  836. 			-- Get the size of the next wave 
  837. 			Next_wave_size = rand_int(wave_size_min, wave_size_max) 
  838. 			if (Next_wave_size > Enemies_reserved) then 
  839. 				Next_wave_size = Enemies_reserved 
  840. 			end 
  841. 		end 
  842. 		thread_yield() 
  843. 	end 
  844.  
  845. end 
  846.  
  847. function rn06_attacking_enemy_killed(enemy) 
  848. 	marker_remove_npc(enemy) 
  849. 	on_death("",enemy) 
  850. 	--character_set_cannot_be_grabbed(enemy,true) 
  851. 	Enemies_attacking = Enemies_attacking - 1 
  852. 	if (Enemies_attacking == 0 and Next_wave_size == 0) then 
  853. 		Enemy_set_cleared = true 
  854. 		objective_text_clear(0) 
  855. 		Enemy_set_objective_helptext = "" 
  856. 	else 
  857. 		if (Enemy_set_objective_helptext ~= "") then 
  858. 			objective_text(0, Enemy_set_objective_helptext, Enemies_total - Enemies_reserved - Enemies_attacking, Enemies_total) 
  859. 		end 
  860. 	end 
  861. end 
  862.  
  863. function rn06_other_enemy_killed(enemy) 
  864. 	marker_remove_npc(enemy) 
  865. 	on_death("",enemy) 
  866. 	--character_set_cannot_be_grabbed(enemy,true) 
  867. 	-- Update the next wave size 
  868. 	Enemies_reserved = Enemies_reserved - 1 
  869. 	if(Next_wave_size > Enemies_reserved) then 
  870. 		Next_wave_size = Enemies_reserved 
  871. 	end 
  872. 	-- update the objective 
  873. 	if (Enemy_set_objective_helptext ~= "") then 
  874. 		objective_text(0, Enemy_set_objective_helptext, Enemies_total - Enemies_reserved - Enemies_attacking, Enemies_total) 
  875. 	end 
  876. end 
  877.  
  878. -- MISSION FAILURE FUNCTIONS -------------------------------- 
  879.