--I Moved some local functions here for sortation convenience.
local SAM = MetroidVanguard

SAM.RunSamusMission = function(s,p) --Mobjthinker extension
	if not (s or p) return end --
	if splitscreen and p == players[1] return end --
	local r = s.samusmission
	
	if r.dontrender --Don't render yet....
		r.dontrender = $-1
		if not r.dontrender
			S_StartSound(nil, sfx_samtm1, p)
		end
	else
		if not r.goodbyedialogue and not r.animtimer
			if r.textboxtrns and (leveltime%2==0)
				r.textboxtrns = max(0, $-FRACUNIT)
			end
		end

		if not (string.find(r.text1, "Gruesome"))-- Never skip this particular one.
			--Cancel conditions!
			if (p.cmd.buttons & BT_TOSSFLAG)
			or not (YouAreSamus(s) or s.samusforcetext) --Must either be Samus or have the forcetext variable.
			or not s.health
			or s.crystalflashanim
			or p.sam_intoship
				if not r.goodbyedialogue --End the text entirely.
					r.goodbyedialogue = 12
					S_StartSound(nil, sfx_samtm6, p)
					r.textwait = 99
				end
			end
		end
		
		if r.textwait
			r.textwait = $-1
			if r.textwait
				r.textwait = $-1
			end
		elseif r.animtimer --Start with animation
			r.animtimer = $-1
		elseif r.maxchars1 and r.currentchars1 < r.maxchars1 --Do first line		
			if leveltime
				if not (string.sub(r.text1, r.currentchars1, r.currentchars1) == " ") --Don't make a sound if there's a space!
					if (r.textboxstyle == 1) or (r.textboxstyle == 4)
						S_StartSound(nil, sfx_samtm4, p)
					else
						S_StartSound(nil, sfx_samtm5, p)
					end
				end
				if (string.sub(r.text1, r.currentchars1, r.currentchars1) == ".")
					r.textwait = 7						
				elseif (string.sub(r.text1, r.currentchars1, r.currentchars1) == "?")
				or (string.sub(r.text1, r.currentchars1, r.currentchars1) == "!")
					r.textwait = 15
				end		
				r.currentchars1 = $+1
			end
			
		elseif r.maxchars2
		and r.currentchars1 >= r.maxchars1 --Do second line
		and r.currentchars2 < r.maxchars2
		
			if leveltime
				if not (string.sub(r.text2, r.currentchars2, r.currentchars2) == " ") --Don't make a sound if there's a space!
					if (r.textboxstyle == 1) or (r.textboxstyle == 4)
						S_StartSound(nil, sfx_samtm4, p)
					else
						S_StartSound(nil, sfx_samtm5, p)
					end
				end
				if (string.sub(r.text2, r.currentchars2, r.currentchars2) == ".")
					r.textwait = 7
				elseif (string.sub(r.text2, r.currentchars2, r.currentchars2) == "?")
				or (string.sub(r.text2, r.currentchars2, r.currentchars2) == "!")
					r.textwait = 15
				end			
				r.currentchars2 = $+1
			end
			
		elseif r.maxchars3
		and r.currentchars1 >= r.maxchars1 --Do second line
		and r.currentchars2 >= r.maxchars2
		and r.currentchars3 < r.maxchars3
		
			if leveltime
				if not (string.sub(r.text3, r.currentchars3, r.currentchars3) == " ") --Don't make a sound if there's a space!
					if (r.textboxstyle == 1) or (r.textboxstyle == 4)
						S_StartSound(nil, sfx_samtm4, p)
					else
						S_StartSound(nil, sfx_samtm5, p)
					end
				end
				if (string.sub(r.text3, r.currentchars3, r.currentchars3) == ".")
					r.textwait = 7
				elseif (string.sub(r.text3, r.currentchars3, r.currentchars3) == "?")
				or (string.sub(r.text3, r.currentchars3, r.currentchars3) == "!")
					r.textwait = 15
				end							
				r.currentchars3 = $+1
			end			
			
		elseif not r.goodbyedialogue
		
			if r.animendtimer --Wait a bir...
				r.animendtimer = $-1
				if r.animendtimer == 119
					if (r.textboxstyle == 3) --Ya did it.
						S_StartSound(nil, sfx_spsmsh, p)
						S_StartSound(nil, sfx_spsmsh, p)
						S_StartSound(nil, sfx_spsmsh, p)
					end
				end	
			else --Is there more? Here it goes.	
				if r.delay
					r.delay = $-1
					if(r.delay == 9)
						S_StartSound(nil, sfx_samtm6, p)
					end
					if (r.textboxtrns < 9<<16)
						r.textboxtrns = $+FRACUNIT
					end
				elseif r.nextbox
					r.active = false
					if r.nextbox == 1 --What's next?
						SamusDialogue(p.mo, "Fuck. I really want some gum.", nil, "SAMDEF", 2)	
					end
				else --No more? Then fade away.
					r.goodbyedialogue = 12
				end
			end
		end

		--END THE MISSION TEXT THINKER!
		if r.goodbyedialogue
			r.goodbyedialogue = $-1
			if (r.textboxtrns < 9<<16)
				r.textboxtrns = $+FRACUNIT
			end
			if not r.goodbyedialogue
				r.active = false
			end
		end
	end
end

--Menu!
SAM.RunSamusSaveMenu = function(s, p)
	p.pflags = $|PF_FORCESTRAFE|PF_INVIS
	if (p.visorclosein < 15)
		p.visorclosein = $+1
	end
	p.powers[pw_underwater] = 1000
	p.powers[pw_spacetime] = 1000
	p.sams_chargetimecd = 2
	p.sams_mshotcd = 2
	p.sams_shotcd = 2
	p.sams_usecd = 2
	p.sams_morphcd = 2
	p.sams_notyet = 2
	p.sam_gravitysuitjustgot = 0
	
	if s.valid
		s.flags = $|MF_NOCLIP|MF_NOCLIPHEIGHT|MF_NOGRAVITY & ~MF_SHOOTABLE
		s.flags2 = $|MF2_DONTDRAW|MF2_SHADOW
		s.momx,s.momy,s.momz = 0,0,0
		if P_IsObjectOnGround(s)
			s.z = s.z+10<<16
		end
		if p.sammorphed
			MorphballReturn(s, true)
		end
		s.state = S_PLAY_FALL	
		S_StopSound(s)
	end	
	
	local t = p.sam_saveselect
	if not t.randomsparkscale
		t.randomsparkscale = 356
		t.randomsparkx = P_RandomRange(1,14)<<16
		t.randomsparky = P_RandomRange(1,14)<<16
		t.randomsparkt = P_RandomRange(0,9)<<16
	elseif t.randomsparkscale
		t.randomsparkscale = $+5000
		if (t.randomsparkscale > FRACUNIT/2)
		t.randomsparkscale = nil
		end
	end
	if t.backgroundx == nil or t.backgroundx >= 32			
		t.backgroundx = 0
	else
		t.backgroundx = $+1
	end
	if t.backgroundy == nil or t.backgroundy >= 256		
		t.backgroundy = 0
	else
		t.backgroundy = $+1
	end
	if t.fadein --Slides in the menu parts!
		t.fadein = $-FRACUNIT
	end
	if (t.transfadebg != FF_TRANS10)
		t.transfadebg = $-FRACUNIT
	end
	if (t.textbgfade != FF_TRANS30)
		t.textbgfade = $-FRACUNIT
	end
	if t.transfadebuttons
		t.transfadebuttons = $-FRACUNIT
	end
	if t.transfadebuttons2
		t.transfadebuttons2 = $-FRACUNIT
	end					
	if t.scale <= FRACUNIT
		t.scale = $+5000
	end
	if t.arrowanim <= 0
		t.arrowanim = 16<<16
	else
		t.arrowanim = $-FRACUNIT
	end			
	if (leveltime % 6 == 0)
		if t.cursoranim == "SAMSAVS3"
			t.cursoranim = "SAMSAVS2"
		else
			t.cursoranim = "SAMSAVS3"
		end
	end
	if p.sam_savedgamemap
	t.chosenstage = p.sam_savedgamemap
	end

	if t.begintrans
		t.begintrans = $-1 
		t.jump = 5
		if (p.jointime < 105) and not p == server --wait, damnit.
		t.begintrans = $+1
		end
		if not t.begintrans --Give the game 3 tics to process all of Samus, or it might crash.
		ProfileSamusSave(s, p, 9001, false, true, true) --Load the first save!
		end
	end			
	--Menus dashing on and off-screen
	
	if t.submenu == 50
		if t.menuvertical == 1
			if t.huddash1
			t.huddash1 = $-15
			end
		elseif t.huddash1 < 75
		t.huddash1 = $+15
		end
		
		if t.menuvertical == 2
			if t.huddash2
			t.huddash2 = $-15
			end
		elseif t.huddash2 < 75
		t.huddash2 = $+15
		end
		
		if t.menuvertical == 3
			if t.huddash3
			t.huddash3 = $-15
			end
		elseif t.huddash3 < 75
		t.huddash3 = $+15
		end
	end
	
	-- Menu trans and growth stuff....
	if t.submenu >= 10 and t.submenu <= 15
		if t.menuhorizontal == 1
			t.firsttrans1 = t.firsttrans1 and ($-FRACUNIT) or t.firsttrans1
			t.firsttrans2 = (t.firsttrans2 < FF_TRANS70) and ($+FRACUNIT) or t.firsttrans2
			t.firsttrans3 = (t.firsttrans3 < FF_TRANS70) and ($+FRACUNIT) or t.firsttrans3
		elseif t.menuhorizontal == 2 
			t.firsttrans1 = (t.firsttrans1 < FF_TRANS70) and ($+FRACUNIT) or t.firsttrans1
			t.firsttrans2 = t.firsttrans2 and ($-FRACUNIT) or t.firsttrans2
			t.firsttrans3 = (t.firsttrans3 < FF_TRANS70) and ($+FRACUNIT) or t.firsttrans3
		elseif t.menuhorizontal == 3
			t.firsttrans1 = (t.firsttrans1 < FF_TRANS70) and ($+FRACUNIT) or t.firsttrans1
			t.firsttrans2 = (t.firsttrans2 < FF_TRANS70) and ($+FRACUNIT) or t.firsttrans2
			t.firsttrans3 = t.firsttrans3 and ($-FRACUNIT) or t.firsttrans3
		end
	
		t.runanim = (t.runanim == A) and B or (t.runanim == B) and C or (t.runanim == C) and D or A
	
		if (p.cmd.buttons & BT_CUSTOM1 and t.menuhorizontal == 2) or (leveltime % 5 == 0) 
			if t.custom1 == 1
				S_StartSound(nil, sfx_sprna, p)
			end
			t.runanim2 = (t.runanim2 == A) and B or (t.runanim2 == B) and C or (t.runanim2 == C) and D or A
		end
	end

	if t.submenu == 14
		if t.delaycrash --Give game some time....
			t.delaycrash = $-1
			p.powers[pw_nocontrol] = 2
			t.backgroundx = $+20
			t.backgroundy = $+6
			if t.delaycrash == 100
				ConfigSamusSave(s, p, true, false)
			elseif t.delaycrash == 50			
				if io and p == consoleplayer
				local file = io.openlocal("client/MetroidVanguard/firstsetup.dat", "w+")
					file:write("COMPLETE "+tostring(21473636))
					file:close()
					CONS_Printf(p, "\x89"+"FIRST-TIME SETUP COMPLETE!")
				end
			end
		else --Alright, we're good!
			p.samusloadconfig = 20
			t.fadein = 20<<16
			t.transfadebg = FF_TRANS90
			t.transfadebuttons = FF_TRANS90
			t.transfadebuttons2 = FF_TRANS90
			t.begintrans = 3
			t.textbgfade = FF_TRANS90			
			S_StartSound(nil, sfx_samtm7, p)
			t.submenu = 1
			t.menuhorizontal = 1
			t.menuvertical = 2
		end

	elseif t.submenu == 10  //First Time - Lock On

		if t.left == 1
			if t.menuhorizontal > 1
				t.menuhorizontal = $-1
				S_StartSound(nil, sfx_ssmenm, p)
			end
		elseif t.right == 1
			if t.menuhorizontal < 3
				t.menuhorizontal = $+1
				S_StartSound(nil, sfx_ssmenm, p)
			end
		elseif t.jump == 1
			if t.menuhorizontal == 1
				CONS_Printf(p, "\x83"+"The Lock-On can be activated with Custom 1 or Custom 3.")
	  			p.sam_lockonpower = 1							
			elseif t.menuhorizontal == 2
				CONS_Printf(p, "\x84"+"The Lock-On can be activated with Custom 3.")
	  			p.sam_lockonpower = 2								
			else
				CONS_Printf(p, "\x87"+"The Lock-On has been de-activated. Using the mouse to aim is recommended.")
				p.sam_lockonpower = 0	
				if p.mo
					SamusTutorial(p.mo, "lockon", true)
				end
			end
			t.menuhorizontal = 1
			t.submenu = 11
			S_StartSound(nil, sfx_ssmeno, p)
			SAM_COM_BufInsertText(p, "crosshair angle")
		end
	elseif t.submenu == 11 // First Time - AutoSpeedBooster
			if t.left == 1
				if t.menuhorizontal == 2
				t.menuhorizontal = $-1
				S_StartSound(nil, sfx_ssmenm, p)
				end
			elseif t.right == 1
				if t.menuhorizontal == 1
				t.menuhorizontal = $+1
				S_StartSound(nil, sfx_ssmenm, p)
				end
			elseif t.jump == 1
				if t.menuhorizontal == 1
					CONS_Printf(p, "\x82"+"Auto Speed Booster toggled on")
	  				p.autospeedbooster = 1
				else
					CONS_Printf(p, "\x85"+"Auto Speed Booster toggled off") 
	  				p.autospeedbooster = 0
				end
				t.menuhorizontal = 1
				t.submenu = 12
				S_StartSound(nil, sfx_ssmeno, p)
			end
	elseif t.submenu == 12  //First Time - Samus Music
			if t.left == 1
				if t.menuhorizontal > 1
				t.menuhorizontal = $-1
				S_StartSound(nil, sfx_ssmenm, p)
				end
			elseif t.right == 1
				if t.menuhorizontal < 3
				t.menuhorizontal = $+1
				S_StartSound(nil, sfx_ssmenm, p)
				end
			elseif t.jump --wariomon
				if t.jump == 1 and t.menuhorizontal == 1
					if not p.samusmusicadded
						SAM_COM_BufInsertText(p, "addfile SamusMusic.pk3; wait 7; tunes SAMMU1")
						p.samusmusicadded = true
					else
						SAM_COM_BufInsertText(p, "tunes SAMMU1")
					end
					p.sam_autoaddmusic = true
					
					t.submenu = 14	--enable music
					S_StartSound(nil, sfx_ssmeno, p)
			--		S_ChangeMusic("SAMMU1", true, p, 0, 0, 699, 699) --Don't use this, SRB2's lua music change system is broken.
					P_SamFP(p, PAL_RECYCLE, 5)
				elseif t.jump == 1 and t.menuhorizontal == 2
					S_StartSound(nil, sfx_samtm7, p)
					t.submenu = 13	--get link for music	
				elseif t.jump and t.menuhorizontal == 3
				
					if (t.jump == 1)
					S_StartSound(nil, sfx_rumble, p)
					end
					
					if (t.jump == 160)
					P_SamFP(p, PAL_NUKE, 12)
					S_StartSound(nil, sfx_crumbl, p)
					t.submenu = 14	--disable music. Seriously not recommended, but possible and totally fine with some mods.
					end
					
				end
			end
	elseif t.submenu == 13  //Samus Music link
		if t.jump == 1 or t.spin == 1
		S_StartSound(nil, sfx_ssmenc, p)
		t.submenu = 12
		t.menuhorizontal = 1
		end
	elseif t.submenu == 50  //Difficulty Select
	
		if t.down == 1
			if t.menuvertical == 1 
				t.menuvertical = 2
			elseif t.menuvertical == 2
				t.menuvertical = 3
			elseif t.menuvertical == 3
				t.menuvertical = 1
			end
			S_StartSound(nil, sfx_ssmenm, p)
		elseif t.up == 1
			if t.menuvertical == 1
				t.menuvertical = 3
			elseif t.menuvertical == 2 
				t.menuvertical = 1
			elseif t.menuvertical == 3
				t.menuvertical = 2
			end
			S_StartSound(nil, sfx_ssmenm, p)					
		elseif t.jump == 1
			S_StartSound(nil, sfx_ssmenc, p)
			if t.menuvertical == 1
				SAMUSDIFFICULTY = 0						
			elseif t.menuvertical == 2
				SAMUSDIFFICULTY = 1				
			elseif t.menuvertical == 3
				SAMUSDIFFICULTY = 2
			end
			CollectSamusTax(p)
			FinishSamusSaveSelect(p, true)
			CollectSamusTax(p)
			p.samcheat = nil
		end				
	elseif t.submenu == 1  //Save Select
		if t.noloadsave 
		and (t.menuvertical != 1 or not t.jump)
			t.noloadsave = 0
			S_StartSound(nil, sfx_sdenid, p)
		end
		if t.menuvertical == 1 --"play without saving"?
			if t.down == 1 or t.up == 1
				t.menuvertical = 2
				S_StartSound(nil, sfx_ssmenm, p)
			elseif t.jump --Go without a save!
				if (t.noloadsave < 40)
				t.noloadsave = $+1
				else
					t.noloadsave = 0
					S_StartSound(nil, sfx_ssmeno, p)
					p.sam_emeraldflags = 0
					CollectSamusTax(p)
					p.sam_saveselected = 0
					p.sam_scanvisor = false
					if p == server
						t.menuvertical = 1
						t.submenu = 50
					else
						FinishSamusSaveSelect(p, true)
						CollectSamusTax(p)
						p.samcheat = nil				
					end
				end
			end
		elseif t.menuvertical == 2 --Samus Save File 1/2/3/4/etc
			if t.down == 1 or t.up == 1
				t.menuvertical = 1
				S_StartSound(nil, sfx_ssmenm, p)
			elseif t.left == 1
				if t.menuhorizontal <= 1
					t.menuhorizontal = 99
				else
					t.menuhorizontal = $-1
				end
				ProfileSamusSave(s, p, t.menuhorizontal, false, true, true)
				t.transfadebuttons2 = FF_TRANS90
				S_StartSound(nil, sfx_ssmenm, p)
				p.powers[pw_nocontrol] = 4
				if p.sam_initmenu
					p.sam_initmenu = nil
				end
			elseif t.right == 1
				if t.menuhorizontal >= 99
					t.menuhorizontal = 1
				else
					t.menuhorizontal = $+1
					if p.sam_initmenu
					p.sam_initmenu = nil
					t.menuhorizontal = 1
					end
				end
				ProfileSamusSave(s, p, t.menuhorizontal, false, true, true)
				t.transfadebuttons2 = FF_TRANS90
				S_StartSound(nil, sfx_ssmenm, p)
				p.powers[pw_nocontrol] = 4
			elseif t.jump == 1
				if p.sam_initmenu
					--nope
				elseif p.newsamfile
					S_StartSound(nil, sfx_ssmeno, p)
					p.sam_emeraldflags = 0
					p.sam_saveselected = t.menuhorizontal
					if p == server
						t.menuvertical = 1
						t.submenu = 50
					else
						FinishSamusSaveSelect(p, true)
						CollectSamusTax(p)
						p.samcheat = nil				
					end							
				else
					t.submenu = 2 --Go to save menu.
					t.tempsavenum = t.menuhorizontal
					ProfileSamusSave(s, p, t.tempsavenum, false, true, true)
					S_StartSound(nil, sfx_ssmenc, p)
					t.transfadebuttons = FF_TRANS90
					t.menuvertical = 1
					t.textbgfade = FF_TRANS90
				end
			end
		end
		
	elseif t.submenu == 2  //Continue? From which stage? Or restart altogether?
		if t.spin == 1 --Return to main save menu?			
			t.submenu = 1
			S_StartSound(nil, sfx_ssmenb, p)
			t.transfadebuttons = FF_TRANS90
			t.menuvertical = 2
			
		elseif t.down == 1 or t.up == 1 --Movement.
			if t.menuvertical == 1 
			t.menuvertical = 2
			else
			t.menuvertical = 1
			end
			S_StartSound(nil, sfx_ssmenm, p)
			
		elseif t.jump == 1 --Confirm!
			if t.menuvertical == 1 --Continue game
				if (netgame and (IsPlayerAdmin(p) or (p == server)) ) or not netgame
				or SAMUSNETSAVES == true
					t.submenu = 3 --Transition to the continue menu.					
					S_StartSound(nil, sfx_ssmeno, p)
					t.transfadebuttons = FF_TRANS90
					t.menuvertical = 1
				else
					S_StartSound(nil, sfx_sdenid, p)
					CONS_Printf(p, "\x85"+"The use of existing saves are turned off in this netgame!")
				end
			elseif t.menuvertical == 2 --Start Fresh
				t.submenu = 4 --transition to Restart Menu
				S_StartSound(nil, sfx_ssmeno, p)
				t.transfadebuttons = FF_TRANS90
				t.menuvertical = 1							
			end
			S_StartSound(nil, sfx_ssmeno, p)
		end

	elseif t.submenu == 3  //Continue? From last stage or this stage?
		if t.spin == 1 --Return to save/restart select
		or SAMUSNETSAVES == false and not (IsPlayerAdmin(p) or (p == server)) --You shouldn't be here.
			t.submenu = 2
			S_StartSound(nil, sfx_ssmenb, p)
			t.transfadebuttons = FF_TRANS90
			t.menuvertical = 1					
			
		elseif t.jump == 1 --Return to main save menu?
		or not (IsPlayerAdmin(p) or (p == server))
		
			if t.menuvertical == 2 --From current stage. Automatically goes here if you're not the server.
			or not (IsPlayerAdmin(p) or (p == server))
				p.sam_saveselected = t.tempsavenum
				FinishSamusSaveSelect(p, true)				
			elseif t.menuvertical == 1 --From last stage?
				if (netgame and (IsPlayerAdmin(p) or (p == server)) ) or not netgame
					p.sam_saveselected = t.tempsavenum
					FinishSamusSaveSelect(p)
				else --Hold on, only the host and admins can change the stage!
					CONS_Printf(p, "\x85"+"You can't change the stage if you're not the server!")
					S_StartSound(nil, sfx_sdenid, p)
				end
			end
		elseif t.down == 1 or t.up == 1 --Movement.
			t.menuvertical = (t.menuvertical == 1) and 2 or 1
			S_StartSound(nil, sfx_ssmenm, p)		
		end
		
	elseif t.submenu == 4  //Restart altogether or just from this stage?
	
		if t.spin == 1 --Return to save/restart select		
			t.submenu = 2
			S_StartSound(nil, sfx_ssmenb, p)
			t.transfadebuttons = FF_TRANS90
			t.menuvertical = 2
			
		elseif t.down == 1 or t.up == 1 --Movement.
			if t.menuvertical == 1 
				t.menuvertical = 2
			else
				t.menuvertical = 1
			end
			S_StartSound(nil, sfx_ssmenm, p)
		elseif t.jump == 1
		or not (IsPlayerAdmin(p) or (p == server))
			if t.menuvertical == 1  --Start Fresh from current stage
			or not (IsPlayerAdmin(p) or (p == server))
				p.sam_saveselected = t.tempsavenum			
				FinishSamusSaveSelect(p, true)
				S_StartSound(nil, sfx_ssmeno, p)
				CollectSamusTax(p, true)
				p.sam_emeraldflags = 0
			else --Start a True Restart from GFZ1!
				if not (IsPlayerAdmin(p) or (p == server))
					S_StartSound(nil, sfx_sdenid, p)
					CONS_Printf(p, "\x85"+"Joiners cannot use true restart in netgames!")
				else
					CollectSamusTax(p, true)
					p.sam_saveselected = t.tempsavenum
					FinishSamusSaveSelect(p, true, true)
					S_StartSound(nil, sfx_ssmeno, p)
					p.sam_emeraldflags = 0
				end
			end
		end
	end
	
	--Menu controls handler.

	//Keep these below the menu Lua or it'll break.
	t.left = (p.cmd.sidemove < 0) and ($+1) or 0
	t.right = (p.cmd.sidemove > 0) and ($+1) or 0
	t.up = (p.cmd.forwardmove > 0) and ($+1) or 0
	t.down = (p.cmd.forwardmove < 0) and ($+1) or 0
	t.jump = (p.cmd.buttons & BT_JUMP) and ($+1) or 0
	t.spin = (p.cmd.buttons & BT_USE) and ($+1) or 0
	t.custom1 = (p.cmd.buttons & BT_CUSTOM1) and ($+1) or 0		
end

SAM.RunSamusDialogue = function(s,p) --Mobjthinker extension
	if not s and p
	or p.sam_saveselect
		return --
	end
	if p.sam_achievement1 and not s.samusforcetext
		if gamemap == 28
			s.samusdialogue = nil
		end
		return	
	end
	local t = s.samusdialogue
	--Keep updating colors live
	if s.player.sam_screwattacking and s.player.prescrewcolor --Don't use the screw attack colors!
	t.samuscolor = s.player.prescrewcolor
	else
	t.samuscolor = s.color
	end
	if (t.textboxstyle == 1)
		if (leveltime % 4 == 0)
			if t.tbscolor <= SKINCOLOR_SUPERRED1
			t.tbscolor = SKINCOLOR_SUPERRED1
			t.tbsd = 1
			elseif t.tbscolor >= SKINCOLOR_SUPERRED5
			t.tbscolor = SKINCOLOR_SUPERRED5
			t.tbsd = -1
			end
			t.tbscolor = $+t.tbsd
		end
	end			
	if t.dontrender --Don't render yet....
		t.dontrender = $-1
	 	if not t.dontrender
		and not (t.textboxstyle == 5)
			S_StartSound(nil, sfx_samtm1, p)
		end
	else
	 	if not t.goodbyedialogue
			if t.transitflash
				t.transitflash = $-FRACUNIT
			end
			if t.textboxscale < FRACUNIT --Gradually expand
				t.textboxscale = $+5000
				if t.textboxtrns
					t.textboxtrns = $-FRACUNIT
				end
			end
		end
		if ( (p.cmd.buttons & BT_TOSSFLAG)
		or not s.health
		or not (YouAreSamus(s) or s.samusforcetext) --If player.mo.samusforcetext is added, don't stop even if you're the wrong skin.
		or s.crystalflashanim or p.sam_intoship
		or p.sam_saveselect)
		and not t.goodbyedialogue --End the text entirely.
		t.goodbyedialogue = 12
		S_StartSound(nil, sfx_ssmenc, p)
		t.textwait = 99
		end
		if t.textwait
		t.textwait = $-1
			for d = 1,2
				if (p.cmd.buttons & BT_CUSTOM1)
				and t.textwait
				t.textwait = $-1
				end
			end
		elseif t.animtimer --Start with animation
		t.animtimer = $-1		
		elseif t.maxchars1 and t.currentchars1 < t.maxchars1 --Do first line
			if leveltime % 2 == 0 or (p.cmd.buttons & BT_CUSTOM1)
				if not (string.sub(t.text1, t.currentchars1, t.currentchars1) == " ") --Don't make a sound if there's a space!
				and not (t.textboxstyle == 5)
					if (t.textboxstyle == 1)
					S_StartSound(nil, sfx_samtm2, p)
					else
					S_StartSound(nil, sfx_samtm3, p)
					end
				end
				if (string.sub(t.text1, t.currentchars1, t.currentchars1) == ".")
				t.textwait = 7
				
				elseif (string.sub(t.text1, t.currentchars1, t.currentchars1) == "?")
				or (string.sub(t.text1, t.currentchars1, t.currentchars1) == "!")
				t.textwait = 15
				end		
			t.currentchars1 = $+1
			end
		elseif t.maxchars2
		and t.currentchars1 >= t.maxchars1 --Do second line
		and t.currentchars2 < t.maxchars2
			if leveltime % 2 == 0 or (p.cmd.buttons & BT_CUSTOM1)
				if not (string.sub(t.text2, t.currentchars2, t.currentchars2) == " ") --Don't make a sound if there's a space!
					if (t.textboxstyle == 1)
					S_StartSound(nil, sfx_samtm2, p)
					else
					S_StartSound(nil, sfx_samtm3, p)
					end
				end
				if (string.sub(t.text2, t.currentchars2, t.currentchars2) == ".")
				t.textwait = 7
				elseif (string.sub(t.text2, t.currentchars2, t.currentchars2) == "?")
				or (string.sub(t.text2, t.currentchars2, t.currentchars2) == "!")
				t.textwait = 15
				end							
			t.currentchars2 = $+1
			end
		elseif t.maxchars3
		and t.currentchars1 >= t.maxchars1 --Do second line
		and t.currentchars2 >= t.maxchars2
		and t.currentchars3 < t.maxchars3
			if leveltime % 2 == 0 or (p.cmd.buttons & BT_CUSTOM1)
				if not (string.sub(t.text3, t.currentchars3, t.currentchars3) == " ") --Don't make a sound if there's a space!
					if (t.textboxstyle == 1)
					S_StartSound(nil, sfx_samtm2, p)
					else
					S_StartSound(nil, sfx_samtm3, p)
					end
				end
				if (string.sub(t.text3, t.currentchars3, t.currentchars3) == ".")
				t.textwait = 7
				elseif (string.sub(t.text3, t.currentchars3, t.currentchars3) == "?")
				or (string.sub(t.text3, t.currentchars3, t.currentchars3) == "!")
				t.textwait = 15
				end							
			t.currentchars3 = $+1
			end				
		elseif not t.goodbyedialogue
			if t.animendtimer --Wait a bit...
			t.animendtimer = $-1
				for d = 1,2
					if ((p.cmd.buttons & BT_CUSTOM1) or (t.textboxstyle == 5))
					and t.animendtimer
					t.animendtimer  = $-1
					end
				end		
			else --Is there another box to go to? They're set up here!
				if t.nextbox
					t.noscale = true
					t.active = false
				--playermobj, line1, line2, icon, style, nextbox, waittime, align1, align2 
					if t.nextbox == 1 --GFZ1
						SamusDialogue(s,
						"Nothing else to it, the rest of the", 
						"way will have to be on foot.",
						"SAMPRE", 2, 3, nil)
					elseif t.nextbox == 2 --DSZ2
						if p.sam_icebeam and (p.sams_itemcompletion != nil and (p.sams_itemcompletion < 20))
							SamusDialogue(s, 
							"This is foolishness. Relying on only", 
							"the Ice Beam is much too dangerous.", 
							"SAMDEF", 2, 0)
						elseif p.sam_icebeam
							SamusDialogue(s, 
							"Deep breaths. I should be ready... but ",
							"Metroids never fail to be unpredictable.", 
							"SAMSAD", 2, 0)
						else
							SamusDialogue(s, 
							"Walking into this without Ice equipment", 
							"is just suicide. Gotta power up. Fast.",
							"SAMPRE", 2, 0)
						end
					elseif t.nextbox == 3 --GFZ1
						SamusDialogue(s, "But who fired that laser? Does the",
						"target have access to such firepower?",
						"SAMSAD", 2, 4)
					elseif t.nextbox == 4 --GFZ1
						SamusDialogue(s, "So much for a simple bounty.", nil, "SAMDEF", 2, 0)
					elseif t.nextbox == 5 --GFZ2	
						SamusDialogue(s, 
						"My arrival was intended as an ambush. ", 
						"Surely Aether's escapee couldn't have taken control over all these machines? ",
						"SAMPRE", 2, 0, nil, nil, "small")
					elseif t.nextbox == 6 --THZ1	
						SamusDialogue(s, " ...let's focus on the mission. ", nil, "SAMDEF", 2, 0)
					elseif t.nextbox == 7 --THZ2	
						SamusDialogue(s, "Here? So they must've encountered...", nil, "SAMDEF", 2, 0)
					elseif t.nextbox == 8 --CEZ1	
						SamusDialogue(s, 
						"Propagating that would take years of", 
						"experience and specialty knowledge.", "SAMPRE", 2, 9)
					elseif t.nextbox == 9 --CEZ1
						SamusDialogue(s, 
						"Even Space Pirates lack that specialty", 
						"knowledge. What IS this 'smuggler'?", 
						"SAMSAD", 2, 12)
					elseif t.nextbox == 12 --CEZ1
						SamusDialogue(s, "At least an alliance can be ruled out. ", nil, "SAMPRE", 2, 0)
					elseif t.nextbox == 13 --ACZ1	
						SamusDialogue(s, 
						"They're moving fast. How am I", 
						"going to catch up with this gear?", 
						"SAMSAD", 2, 0)
					elseif t.nextbox == 14 --ACZ1	
						SamusDialogue(s, 
						"How's it even possible to move so", 
						"swiftly whilst transporting Metroids?", 
						"SAMPRE", 2, 0)
					elseif t.nextbox == 15 --ACZ2	
						SamusDialogue(s, 
						"Nowhere to run. ", 
						"I won't let you escape this time.", 
						"SAMDEF", 2, 0)
					elseif t.nextbox == 11 --ACZ2	
						SamusDialogue(s, 
						"This mystery smuggler's turned out", 
						"interesting. Can't let my guard down. ", 
						"SAMSAD", 2, 0)
					elseif t.nextbox == 10 --ACZ2	
						SamusDialogue(s, 
						"It stopped for me? This is a trap... ", 
						"So it knows I've been following... ", 
						"SAMDEF", 2, 0)
					elseif t.nextbox == 17 --RVZ1
						if p.sams_itemcompletion != nil and (p.sams_itemcompletion < 4) --Hesitant when unequipped
							SamusDialogue(s, 
							"Thank the stars... but am I finished? ", 
							"To depart, even if I'm like this... ", 
							"SAMSAD", 2, 18)
						elseif p.sams_itemcompletion != nil and (p.sams_itemcompletion > 94) --Cocky when powered up
							SamusDialogue(s, 
							"How convenient. Since I'm still here... ", 
							"Let's tie up some ... loose ends.", 
							"SAMPRE", 2, 0)
						else 
							SamusDialogue(s, "I've seen enough.     ", nil, "SAMSAD", 2, 19)
						end				
					elseif t.nextbox == 18
						SamusDialogue(s, 
						"I will not leave this planet to its", 
						"cruel fate. Someone must defend it. ", 
						"SAMDEF", 2, 0)
					elseif t.nextbox == 19
						SamusDialogue(s, 
						"Who knows what'll become of this world. ", 
						"...but it won't belong to one man. ", "SAMDEF", 2, 0)	
					elseif t.nextbox == 22 --ERZ
						SamusDialogue(s, 
						"Infiltrate the core and obliterate it! ", 
						"That'll end this. Permanently. ",
						"SAMDEF", 2, 0)
					elseif t.nextbox == 23
						SamusDialogue(s, 
						"As long as I'm alive, there's hope. I won't", 
						"simply watch this world fall to ruin. ", 
						"SAMDEF", 2, 0)	
					elseif t.nextbox == 500 --BCZ
						SamusDialogue(s, "\x82 !!", nil, "SAMDEF", 2, 0)
					end
				elseif t.customnextbox 
				
				--Custom dialogue trees! Allows for continuous custom text conversations.
				--Use CTRL+F in this Lua file and look for "gamemap == 11" to get an idea how to use this.
				
					t.customnextboxready = true
					t.noscale = true
					
				else --No more boxes? Then setup the dialogue ending animation	 					
					t.goodbyedialogue = 12
					t.customnextbox = 0
					if (t.textboxstyle != 5)
						S_StartSound(nil, sfx_ssmenb, p)
					end
				end
			end
		end
		
	--AAAAND END THE DIALOGUE THINKER!!
	
		if t.goodbyedialogue
			t.goodbyedialogue = $-1
			t.endoffset = $+FRACUNIT
			if (t.textboxtrns != FF_TRANS90)
				t.textboxtrns = $+FRACUNIT
			end
			if (t.textboxscale > 5000)
				t.textboxscale = $-5000
			end
			if not t.goodbyedialogue
				t.active = false --That's it, we're done.
			end
		end
	end
end

local function OtherTutorials(t,s)
	if (t.missiles or t.beams or t.supermissiles or t.beamcombo or t.gravitysuit1 or t.gravitysuit2 or t.scanvisor
	or t.screwattack or t.bombs or t.hyperbeam)
		return true --There's more
	end return false --Nothing left!
end
local function SwitchTutorialBox(t,s)
	t.textboxflash = FF_TRANS90
	t.textboxtrns = FF_TRANS90
	t.textboxtrns2 = FF_TRANS90
	t.goodbyedialogue = 0
	t.active = true
end
--Check if that's the end of the tutorials or if there's more...
rawset(_G, "EndSamusTutorial", function(t, s, item)
	local totaldone = 0
			
	if t.lockoncomplete and not t.lockon
		totaldone = $+1
	elseif t.lockon
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.beamscomplete and not t.beams
		totaldone = $+1
	elseif t.beams
		SwitchTutorialBox(t,s)
		return
	end

	if t.monitorhuntcomplete and not t.monitorhunt
		totaldone = $+1
	elseif t.monitorhunt
		SwitchTutorialBox(t,s)
		return
	end

	if t.chargebeamcomplete and not t.chargebeam
		totaldone = $+1
	elseif t.chargebeam
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.missilescomplete and not t.missiles
		totaldone = $+1
	elseif t.missiles
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.supermissilescomplete and not t.supermissiles
		totaldone = $+1
	elseif t.supermissiles
		SwitchTutorialBox(t,s)
		return
	end

	if t.beamcombocomplete and not t.beamcombo
		totaldone = $+1
	elseif t.beamcombo
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.gravitysuit1complete and not t.gravitysuit1
		totaldone = $+1
	elseif t.gravitysuit1
		SwitchTutorialBox(t,s)
		return
	end	
	
	if t.gravitysuit2complete and not t.gravitysuit2
		totaldone = $+1
	elseif t.gravitysuit2
		SwitchTutorialBox(t,s)
		return
	end

	if t.scanvisorcomplete and not t.scanvisor
		totaldone = $+1
	elseif t.scanvisor
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.screwattackcomplete and not t.screwattack
		totaldone = $+1
	elseif t.screwattack
		SwitchTutorialBox(t,s)
		return
	end	

	if t.bombscomplete and not t.bombs
		totaldone = $+1
	elseif t.bombs
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.pwcomplete and not t.pw
		totaldone = $+1
	elseif t.pw
		SwitchTutorialBox(t,s)
		return
	end	
	
	if t.spiderballcomplete and not t.spiderball
		totaldone = $+1
	elseif t.spiderball
		SwitchTutorialBox(t,s)
		return
	end
	
	if t.hyperbeamcomplete and not t.hyperbeam
		totaldone = $+1
	elseif t.hyperbeam
		SwitchTutorialBox(t,s)
		return
	end	
	
	if not (OtherTutorials(t,s) and t.active)
		t.goodbyedialogue = 12
	end
end)


SAM.RunSamusTutorial = function(s,p) --Mobjthinker extension
	if p.nosamustutorials
	or p.sam_saveselect --Everything else has priority over tutorials.
		s.player.samustutorial.dontrender = 1
		return false --
	end
	local t = s.player.samustutorial
	if p.mo.samusdialogue and p.mo.samusdialogue.active
		t.textboxscale = 356
		t.textboxtrns = FF_TRANS90
		return --
	end
	if t.dontrender
		t.dontrender = 0
		t.textboxscale = 356
		t.textboxtrns = FF_TRANS90
	end

	if not YouAreSamus(s) or p.nosamustutorials or
	(t.beams and not p.sam_powerbeamequip) or
	(t.missiles and not p.sammissiles) or
	(t.supermissiles and not p.samsupermissiles) or
	(t.beamcombo and not (p.sammissiles and p.sammissiles > 14)) or
	(t.gravitysuit1 and not p.samspbs) or
	(t.scanvisor and not (p.sam_scanvisor or gametype ~= GT_COOP)) or
	(t.screwattack and not p.sam_screwattack) or
	(t.bombs and not p.sam_bombs) or
	(t.pw and not p.sampw) or
	(t.spiderball and not p.sam_spiderball) or
	(t.hyperbeam and not p.sam_hyperbeam)
		t.dontrender = 1 return --I have failed Amperbee-sama
	end
			
	if not t.goodbyedialogue
		if t.textboxflash
			t.textboxflash = $-FRACUNIT
		end
		if t.textboxscale < FRACUNIT --Gradually expand.
			t.textboxscale = $+5000
		elseif t.textboxtrns2
			t.textboxtrns2 = $-FRACUNIT
		end
		if t.textboxtrns
			t.textboxtrns = $-FRACUNIT
		end				
	else	
		--END THE TUTORIAL THINKER?
	
		t.goodbyedialogue = $-1
		if (t.textboxtrns2 != FF_TRANS90)
			t.textboxtrns2 = $+FRACUNIT
		end
		if (t.textboxtrns != FF_TRANS90)
			t.textboxtrns = $+FRACUNIT
		end
		if (t.textboxscale > 5000)
			t.textboxscale = $-5000
		end
		if not t.goodbyedialogue
			t.active = false
		end
	end
	if p.exiting
	and not s.sam_tutdismiss --Sometimes things don't go as planned.
		s.sam_tutdismiss = true
		SamusTutorial(s, "beams", true)
		SamusTutorial(s, "missiles", true)
		SamusTutorial(s, "supermissiles", true)
		SamusTutorial(s, "beamcombo", true)
		SamusTutorial(s, "variasuit", true)
		SamusTutorial(s, "gravitysuit", true)
		SamusTutorial(s, "scanvisor", true)
		SamusTutorial(s, "screwattack", true)
		SamusTutorial(s, "bombs", true)
		SamusTutorial(s, "pw", true)
		SamusTutorial(s, "spiderball", true)
		SamusTutorial(s, "hyperbeam", true)			
	end
end