freeslot("MT_CARRYCATS")
freeslot("S_CARRYCATS")
freeslot("SPR_CCAT")

//SFX
freeslot("sfx_catcar")
sfxinfo[sfx_catcar].caption = "Picked up CAT"
freeslot("sfx_cattrw")
sfxinfo[sfx_cattrw].caption = "Thrown CAT"
freeslot("sfx_catkil")
sfxinfo[sfx_catkil].caption = "HOLY CRAP"


local function givecat(p)
p.cat = 0
p.catbonus = 0
p.handsdown = 100
p.handsdir = 1
p.disablehands = 0
if p.maxcat == nil
p.maxcat = 5
end
if p.catskin == nil
p.catskin = 1
end
p.throwcat = 1
if p.save1 != nil
A_applyabilities(p)
end
p.catwarning = 0
if p == consoleplayer
if p.mo.valid
P_SpawnMobj(p.mo.x, p.mo.y, p.mo.z, MT_CARRYCATS)
end
end
end

addHook("PlayerSpawn", givecat)

local function handshud(p)
if p.handsdir == 1
if p.handsdown > 0 
p.handsdown = $ - 10
if p.handsdown < 0
p.handsdown = 0
end
end
elseif p.handsdir == 0
if p.handsdown > 0 
p.handsdown = $ + 10
if p.handsdown > 200
p.disablehands = 1
end
end
end
end

addHook("PlayerThink", handshud)

local function winwithcat()
local p = consoleplayer
if p != nil
if (p.pflags & PF_FINISHED)
if p.cat == 0
if P_PlayerTouchingSectorSpecialFlag(p, 128) then
p.exiting = 0
p.catwarning = 1
p.pflags = $ & ~PF_FINISHED
p.pflags = $ & ~PF_STASIS
p.pflags = $ & ~PF_JUMPSTASIS
p.pflags = $ & ~PF_FULLSTASIS
end
end
if p.cat != 0
p.throwcat = 0
p.catwarning = 0
p.beginX = nil
if p.catbonus == 0
p.catbonus = 1
P_AddPlayerScore(p, 10000)
end
end
end
end
end

addHook("PreThinkFrame", winwithcat)

local function catthinker(mobj)
if mobj.owner != nil
mobj.momx = 0
mobj.momy = 0
P_SetOrigin(mobj, mobj.owner.mo.x, mobj.owner.mo.y, mobj.owner.mo.z + 3*FRACUNIT)
mobj.flags = $ | MF_NOCLIP
mobj.flags = $ | MF_NOGRAVITY
P_InstaThrust(mobj, mobj.owner.mo.angle, 1*FRACUNIT)
end
if mobj.throwtime > 0
mobj.owner = nil
mobj.throwtime = mobj.throwtime - 1
end
if mobj.owner != nil and mobj.owner.cat == 0
mobj.owner = nil
end
end

addHook("MobjThinker", catthinker, MT_CARRYCATS)

local function catspawn(mobj)
mobj.throwtime = 0
mobj.owner = nil
end

addHook("MobjSpawn", catspawn, MT_CARRYCATS)

local function throwcat(p)
if p.cat != 0
A_throwingcat(p, 20*FRACUNIT)
S_StartSound(p.mo, sfx_cattrw)
end
end

addHook("SpinSpecial", throwcat)

local function throwabable(mobj, mot)
if mot.type != MT_PLAYER and mot.type != MT_CARRYCATS
if mobj.owner == nil
if (mot.flags & MF_ENEMY) or (mot.flags & MF_PAIN) or (mot.flags & MF_FIRE) or (mot.flags & MF_SHOOTABLE)
if mobj.momx != 0 or mobj.momy != 0 or mobj.momz != 0
P_KillMobj(mot)
S_StartSound(mobj, sfx_catkil)
elseif mobj.momx == 0 and mobj.momy == 0 and mobj.momz == 0
P_RemoveMobj(mobj)
end
end
end
end
end

addHook("MobjMoveCollide", throwabable, MT_CARRYCATS)
addHook("MobjCollide", throwabable, MT_CARRYCATS)

local function catdrop(mobj, infl, src, dmg, dmgtype)
local p = consoleplayer
local otp = secondarydisplayplayer
if mobj != p.mo
if mobj == otp.mo and splitscreen
p = otp
end
end
if mobj == p.mo
if p.cat != nil
if p.powers[pw_invulnerability] == 0 and p.powers[pw_flashing] == 0 and p.powers[pw_super] == 0 and p.powers[pw_shield] == SH_NONE
A_throwingcat(p, 10*FRACUNIT)
S_StartSound(p.mo, sfx_cattrw)
end
end
end
end

addHook("ShouldDamage", catdrop, MT_PLAYER)

local function lastbreath(tmobj)
local p = consoleplayer
local otp = secondarydisplayplayer
if tmobj != p.mo
if tmobj == otp.mo and splitscreen
p = otp
end
end
A_applyabilities(p)
end

addHook("MobjDeath", lastbreath, MT_PLAYER)

local function catdamage(mobj, infl, src, dmg, dmgtype)
local p = consoleplayer
local otp = secondarydisplayplayer
if splitscreen then
if otp.mo.valid == true and otp.deadtimer == 0
A_applyabilities(otp)
P_KillMobj(otp.mo)
otp.starpostnum = 0
end
if p.mo.valid == true and p.deadtimer == 0
A_applyabilities(p)
P_KillMobj(p.mo)
p.starpostnum = 0
end
elseif splitscreen == false
if mobj.prevowner.mo.valid == true and mobj.prevowner.deadtimer == 0
A_applyabilities(mobj.prevowner)
mobj.prevowner.starpostnum = 0
P_KillMobj(mobj.prevowner.mo)
end
end
end

addHook("MobjRemoved", catdamage, MT_CARRYCATS)
addHook("MobjDeath", catdamage, MT_CARRYCATS)

local function catpickup(mobj, tmobj)
local p = consoleplayer
local otp = secondarydisplayplayer
if tmobj != p.mo
if tmobj == otp.mo and splitscreen
p = otp
end
end
if tmobj == p.mo
if tmobj.type == MT_PLAYER
if mobj.owner == nil and p.cat == 0 and mobj.throwtime == 0
mobj.owner = p
mobj.prevowner = p
p.cat = mobj
A_saveabilities(p)
p.disablehands = 0
p.handsdir = 1
p.handsdown = 100
S_StartSound(p.mo, sfx_catcar)
end
end
end
return true
end

addHook("TouchSpecial", catpickup, MT_CARRYCATS)

function A_saveabilities(actor)
actor.save1 = actor.charability
actor.save2 = actor.charability2
actor.charability = CA_NONE
actor.charability2 = CA2_NONE
end

function A_applyabilities(actor)
actor.charability = actor.save1
actor.charability2 = actor.save2
end

function A_throwingcat(actor, var1)
if actor.throwcat == 1
actor.cat.throwtime = 20
actor.handsdir = 0
actor.handsdown = 100
actor.cat.flags = $ | MF_SPECIAL
actor.cat.flags = $ & ~MF_NOCLIP
actor.cat.flags = $ & ~MF_NOGRAVITY
P_Thrust(actor.cat, actor.mo.angle, actor.speed + var1)
actor.cat.owner = nil
actor.cat = 0
A_applyabilities(actor)
end
end

function A_catskin(actor, var1)
if actor.cat != 0
if var1 < actor.maxcat
actor.catskin = var1 + 1
actor.cat.frame = var1
end
end
end

local function Catset(p, field)
    if (field ~= nil) then
   A_catskin(p, tonumber(field))
end
end

COM_AddCommand("cat", Catset)


//HUD HANDLING
addHook("HUD", function(v)
local p = consoleplayer
if not camera.chase then
if p.cat != 0
if p.handsdir == 1
v.drawScaled(45*FRACUNIT, FRACUNIT*p.handsdown+100*FRACUNIT, FRACUNIT*2,v.cachePatch("HUD_SONIC"), V_SNAPTOBOTTOM|V_SNAPTORIGHT)
v.drawScaled(65*FRACUNIT, FRACUNIT*p.handsdown+100*FRACUNIT, FRACUNIT*2,v.cachePatch("HUD_CARRY_" + p.catskin), V_SNAPTOBOTTOM|V_SNAPTORIGHT)
end
end
if p.handsdir == 0 and p.disablehands == 0
v.drawScaled(45*FRACUNIT, p.handsdown*FRACUNIT, FRACUNIT*2,v.cachePatch("HUD_SONIC"), V_SNAPTOBOTTOM|V_SNAPTORIGHT)
end
end
if p.catwarning == 1
v.drawString(80, 0, "GET BACK CAT TO FINISH", V_MEDSCALEPATCH|V_REDMAP)
end
end)