More robust Demolitionist Menu item use/drop handling.

This commit is contained in:
Mari the Deer 2025-01-25 14:18:42 +01:00
commit f90c16b36d
5 changed files with 199 additions and 179 deletions

View file

@ -1,8 +1,6 @@
// event processing
extend Class SWWMHandler
{
// for menu events
transient Array<MenuTransaction> checklist;
// for the compact hud
transient int WeaponFlash[10];
// weapon selector
@ -214,6 +212,91 @@ extend Class SWWMHandler
bar.cummspandn = 120+40*int(Log10(clamp(bar.cummscoredn,1,999999999)));
bar.cummflashdn = 15;
}
else if ( e.Name ~== "swwmitemused" )
{
// report back to kbase menu that the item got (or did not get) used
int uid = e.Args[0];
bool rslt = e.Args[1];
bool usedup = e.Args[2];
let kbase = DemolitionistMenu(Menu.GetCurrentMenu());
if ( kbase ) kbase.ItemUsed(uid,rslt,usedup);
}
else if ( e.Name ~== "swwmitemdropped" )
{
// report back to kbase menu that the item got (or did not get) dropped
int uid = e.Args[0];
bool rslt = e.Args[1];
bool usedup = e.Args[2];
let kbase = DemolitionistMenu(Menu.GetCurrentMenu());
if ( kbase ) kbase.ItemDropped(uid,rslt,usedup);
}
}
override void NetworkCommandProcess( NetworkCommand cmd )
{
if ( cmd.Command == 'swwmuseitem' )
{
// kbase menu wants us to use a specific item
int uid = cmd.ReadInt();
int pid = cmd.ReadInt();
uint iid = cmd.ReadInt();
let p = players[pid];
let i = Inventory(GetNetworkEntity(iid));
if ( (i.Owner != p.mo) )
ThrowAbortException("swwmuseitem: attempted to use item '%s' not owned by player '%s'",i.GetTag(),p.GetUserName());
bool rslt = p.mo.UseInventory(i);
let w = Weapon(i);
if ( w )
{
rslt = (p.PendingWeapon==Weapon(i));
// dual wield gun support
if ( (i is 'SWWMWeapon') && (p.PendingWeapon==Weapon(i).SisterWeapon) )
rslt = true;
}
else if ( (i is 'Key') || (i is 'SWWMCollectible') ) rslt = true;
SendInterfaceEvent(pid,"swwmitemused",uid,rslt,(!i||(i.Amount<=0)));
}
else if ( cmd.Command == 'swwmdropitem' )
{
// kbase menu wants us to drop a specific item
int uid = cmd.ReadInt();
int pid = cmd.ReadInt();
uint iid = cmd.ReadInt();
let p = players[pid];
let i = Inventory(GetNetworkEntity(iid));
if ( (i.Owner != p.mo) )
ThrowAbortException("swwmdropitem: attempted to drop item '%s' not owned by player '%s'",i.GetTag(),p.GetUserName());
int amt = i.default.Amount;
// if it's an ammo, check the largest unit givable
if ( i is 'MagAmmo' )
{
foreach ( cls:AllActorClasses )
{
let a = (Class<MagAmmo>)(cls);
if ( !a || (a.GetParentClass() != i.GetClass()) || (GetDefaultByType(a).Amount < amt) ) continue;
amt = GetDefaultByType(a).Amount;
}
}
else if ( i is 'Ammo' )
{
foreach ( cls:AllActorClasses )
{
let a = (Class<Ammo>)(cls);
if ( !a || (a.GetParentClass() != i.GetClass()) || (GetDefaultByType(a).Amount < amt) ) continue;
amt = GetDefaultByType(a).Amount;
}
}
if ( amt > i.Amount ) amt = i.Amount;
let drop = p.mo.DropInventory(i,amt);
// randomize movement direction so multiple drops don't get bunched together
if ( drop )
{
Vector2 vel2d = drop.vel.xy;
drop.vel.xy = Actor.RotateVector(vel2d,FRandom[Junk](-15,15));
drop.vel.xy *= FRandom[Junk](.9,1.1);
}
SendInterfaceEvent(pid,"swwmitemdropped",uid,!!drop,(!i||(i.Amount<=0)));
}
}
override void NetworkProcess( ConsoleEvent e )
@ -466,79 +549,6 @@ extend Class SWWMHandler
let idx = l.FindEntry(e.Name.Mid(17));
l.MarkRead(idx);
}
else if ( e.Name.Left(12) ~== "swwmuseitem." )
{
Class<Inventory> item = e.Name.Mid(12);
if ( !item ) return;
let i = players[e.Args[0]].mo.FindInventory(item);
if ( !i ) return;
bool rslt = players[e.Args[0]].mo.UseInventory(i);
if ( e.Args[0] == consoleplayer )
{
let t = new("MenuTransaction");
t.uid = e.Args[1];
t.type = MenuTransaction.TT_ITEMUSE;
let w = (Class<Weapon>)(item);
if ( w )
{
t.result = (players[e.Args[0]].PendingWeapon==Weapon(i));
// dual wield gun support
if ( (i is 'SWWMWeapon') && (players[e.Args[0]].PendingWeapon==Weapon(i).SisterWeapon) )
t.result = true;
}
else if ( (i is 'Key') || (i is 'SWWMCollectible') ) t.result = true;
else t.result = rslt;
t.used = item;
t.usedup = (!i||(i.Amount<=0));
checklist.Push(t);
}
}
else if ( e.Name.Left(13) ~== "swwmdropitem." )
{
Class<Inventory> item = e.Name.Mid(13);
if ( !item ) return;
let i = players[e.Args[0]].mo.FindInventory(item);
if ( !i ) return;
int amt = i.default.Amount;
// if it's an ammo, check the largest unit givable
if ( i is 'Ammo' )
{
foreach ( cls:AllActorClasses )
{
let a = (Class<Ammo>)(cls);
if ( !a || (a.GetParentClass() != item) || (GetDefaultByType(a).Amount < amt) ) continue;
amt = GetDefaultByType(a).Amount;
}
}
if ( i is 'MagAmmo' )
{
foreach ( cls:AllActorClasses )
{
let a = (Class<MagAmmo>)(cls);
if ( !a || (a.GetParentClass() != item) || (GetDefaultByType(a).Amount < amt) ) continue;
amt = GetDefaultByType(a).Amount;
}
}
if ( amt > i.Amount ) amt = i.Amount;
let drop = players[e.Args[0]].mo.DropInventory(i,amt);
// randomize movement direction so multiple drops don't get bunched together
if ( drop )
{
Vector2 vel2d = drop.vel.xy;
drop.vel.xy = Actor.RotateVector(vel2d,FRandom[Junk](-15,15));
drop.vel.xy *= FRandom[Junk](.9,1.1);
}
if ( e.Args[0] == consoleplayer )
{
let t = new("MenuTransaction");
t.uid = e.Args[1];
t.type = MenuTransaction.TT_ITEMDROP;
t.used = item;
t.result = drop;
t.usedup = (!i||(i.Amount<=0));
checklist.Push(t);
}
}
else if ( e.Name ~== "swwmkoraxline" )
{
if ( consoleplayer != e.Args[1] ) return;
@ -579,21 +589,6 @@ extend Class SWWMHandler
Console.PrintfEx(PRINT_CHAT,"\cx%s\cx: %s\c-",players[e.Args[0]].GetUserName(),txt);
}
}
else if ( e.Name ~== "swwmcleartransaction" )
{
if ( e.Args[1] != consoleplayer ) return;
for ( int i=0; i<checklist.Size(); i++ )
{
if ( checklist[i].uid != e.Args[0] ) continue;
checklist.Delete(i);
i--;
}
}
else if ( e.Name ~== "swwmclearalltransactions" )
{
if ( e.Args[0] != consoleplayer ) return;
checklist.Clear();
}
else if ( e.Name ~== "swwmstorepuzzlecnt" )
{
let s = SWWMStats.Find(players[e.Args[0]]);