mirror of
https://github.com/ZDoom/gzdoom-gles.git
synced 2024-11-11 07:12:16 +00:00
This commit is contained in:
commit
5c5b6a55d5
7 changed files with 83 additions and 37 deletions
|
@ -78,6 +78,7 @@
|
|||
#include "menu/menu.h"
|
||||
#include "intermission/intermission.h"
|
||||
#include "g_levellocals.h"
|
||||
#include "events.h"
|
||||
|
||||
// MACROS ------------------------------------------------------------------
|
||||
|
||||
|
@ -331,6 +332,8 @@ static void MarkRoot()
|
|||
DThinker::MarkRoots();
|
||||
FCanvasTextureInfo::Mark();
|
||||
Mark(DACSThinker::ActiveThinker);
|
||||
Mark(E_FirstEventHandler);
|
||||
Mark(E_LastEventHandler);
|
||||
for (auto &s : level.sectorPortals)
|
||||
{
|
||||
Mark(s.mSkybox);
|
||||
|
|
|
@ -37,32 +37,42 @@ bool E_RegisterHandler(DStaticEventHandler* handler)
|
|||
// 2. MyHandler3->2:
|
||||
// E_FirstEventHandler = MyHandler2, E_LastEventHandler = MyHandler3
|
||||
|
||||
// (Yes, all those write barriers here are really needed!)
|
||||
if (before != nullptr)
|
||||
{
|
||||
// if before is not null, link it before the existing handler.
|
||||
// note that before can be first handler, check for this.
|
||||
handler->next = before;
|
||||
GC::WriteBarrier(handler, before);
|
||||
handler->prev = before->prev;
|
||||
GC::WriteBarrier(handler, before->prev);
|
||||
before->prev = handler;
|
||||
GC::WriteBarrier(before, handler);
|
||||
if (before == E_FirstEventHandler)
|
||||
{
|
||||
E_FirstEventHandler = handler;
|
||||
GC::WriteBarrier(handler);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// so if before is null, it means add last.
|
||||
// it can also mean that we have no handlers at all yet.
|
||||
handler->prev = E_LastEventHandler;
|
||||
GC::WriteBarrier(handler, E_LastEventHandler);
|
||||
handler->next = nullptr;
|
||||
if (E_FirstEventHandler == nullptr)
|
||||
E_FirstEventHandler = handler;
|
||||
if (E_FirstEventHandler == nullptr) E_FirstEventHandler = handler;
|
||||
E_LastEventHandler = handler;
|
||||
GC::WriteBarrier(handler);
|
||||
if (handler->prev != nullptr)
|
||||
{
|
||||
handler->prev->next = handler;
|
||||
GC::WriteBarrier(handler->prev, handler);
|
||||
}
|
||||
}
|
||||
|
||||
if (handler->IsStatic())
|
||||
{
|
||||
handler->ObjectFlags |= OF_Fixed;
|
||||
handler->ObjectFlags |= OF_Transient;
|
||||
}
|
||||
|
||||
|
@ -80,16 +90,28 @@ bool E_UnregisterHandler(DStaticEventHandler* handler)
|
|||
|
||||
// link out of normal list
|
||||
if (handler->prev)
|
||||
{
|
||||
handler->prev->next = handler->next;
|
||||
GC::WriteBarrier(handler->prev, handler->next);
|
||||
}
|
||||
if (handler->next)
|
||||
{
|
||||
handler->next->prev = handler->prev;
|
||||
GC::WriteBarrier(handler->next, handler->prev);
|
||||
}
|
||||
if (handler == E_FirstEventHandler)
|
||||
{
|
||||
E_FirstEventHandler = handler->next;
|
||||
GC::WriteBarrier(handler->next);
|
||||
}
|
||||
if (handler == E_LastEventHandler)
|
||||
{
|
||||
E_LastEventHandler = handler->prev;
|
||||
GC::WriteBarrier(handler->prev);
|
||||
}
|
||||
if (handler->IsStatic())
|
||||
{
|
||||
handler->ObjectFlags &= ~(OF_Fixed|OF_Transient);
|
||||
handler->ObjectFlags &= ~OF_Transient;
|
||||
handler->Destroy();
|
||||
}
|
||||
return true;
|
||||
|
|
|
@ -77,6 +77,7 @@ void E_SerializeEvents(FSerializer& arc);
|
|||
class DStaticEventHandler : public DObject // make it a part of normal GC process
|
||||
{
|
||||
DECLARE_CLASS(DStaticEventHandler, DObject)
|
||||
HAS_OBJECT_POINTERS
|
||||
public:
|
||||
DStaticEventHandler()
|
||||
{
|
||||
|
@ -99,6 +100,7 @@ public:
|
|||
void Serialize(FSerializer& arc) override
|
||||
{
|
||||
Super::Serialize(arc);
|
||||
/*
|
||||
if (arc.isReading())
|
||||
{
|
||||
Printf("DStaticEventHandler::Serialize: reading object %s\n", GetClass()->TypeName.GetChars());
|
||||
|
@ -107,6 +109,7 @@ public:
|
|||
{
|
||||
Printf("DStaticEventHandler::Serialize: store object %s\n", GetClass()->TypeName.GetChars());
|
||||
}
|
||||
*/
|
||||
|
||||
arc("Order", Order);
|
||||
arc("IsUiProcessor", IsUiProcessor);
|
||||
|
@ -155,6 +158,7 @@ public:
|
|||
bool IsStatic() override { return false; }
|
||||
};
|
||||
extern DStaticEventHandler* E_FirstEventHandler;
|
||||
extern DStaticEventHandler* E_LastEventHandler;
|
||||
|
||||
// we cannot call this DEvent because in ZScript, 'event' is a keyword
|
||||
class DBaseEvent : public DObject
|
||||
|
|
|
@ -496,7 +496,7 @@ DEFINE_ACTION_FUNCTION(DMenu, SetMenu)
|
|||
{
|
||||
PARAM_PROLOGUE;
|
||||
PARAM_NAME(menu);
|
||||
PARAM_INT(mparam);
|
||||
PARAM_INT_DEF(mparam);
|
||||
M_SetMenu(menu, mparam);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -267,7 +267,7 @@ DEFINE_ACTION_FUNCTION(DMenu, StartMessage)
|
|||
{
|
||||
PARAM_PROLOGUE;
|
||||
PARAM_STRING(msg);
|
||||
PARAM_INT(mode);
|
||||
PARAM_INT_DEF(mode);
|
||||
PARAM_NAME_DEF(action);
|
||||
M_StartMessage(msg, mode, action);
|
||||
return 0;
|
||||
|
|
|
@ -107,6 +107,7 @@ class SightCheck
|
|||
bool P_SightCheckLine (line_t *ld);
|
||||
int P_SightBlockLinesIterator (int x, int y);
|
||||
bool P_SightTraverseIntercepts ();
|
||||
bool LineBlocksSight(line_t *ld);
|
||||
|
||||
public:
|
||||
bool P_SightPathTraverse ();
|
||||
|
@ -211,7 +212,14 @@ bool SightCheck::PTR_SightTraverse (intercept_t *in)
|
|||
|
||||
double trX = Trace.x + Trace.dx * in->frac;
|
||||
double trY = Trace.y + Trace.dy * in->frac;
|
||||
P_SightOpening (open, li, trX, trY);
|
||||
|
||||
P_SightOpening(open, li, trX, trY);
|
||||
if (LineBlocksSight(in->d.line))
|
||||
{
|
||||
// This may not skip P_SightOpening, but only reduce the open range to 0.
|
||||
open.range = 0;
|
||||
open.bottom = open.top;
|
||||
}
|
||||
|
||||
FLinePortal *lport = li->getPortal();
|
||||
|
||||
|
@ -362,6 +370,42 @@ bool SightCheck::PTR_SightTraverse (intercept_t *in)
|
|||
}
|
||||
|
||||
|
||||
// performs trivial visibility checks.
|
||||
bool SightCheck::LineBlocksSight(line_t *ld)
|
||||
{
|
||||
// try to early out the check
|
||||
if (!ld->backsector || !(ld->flags & ML_TWOSIDED) || (ld->flags & ML_BLOCKSIGHT))
|
||||
return true; // stop checking
|
||||
|
||||
// [RH] don't see past block everything lines
|
||||
if (ld->flags & ML_BLOCKEVERYTHING)
|
||||
{
|
||||
if (!(Flags & SF_SEEPASTBLOCKEVERYTHING))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
// Pretend the other side is invisible if this is not an impact line
|
||||
// that runs a script on the current map. Used to prevent monsters
|
||||
// from trying to attack through a block everything line unless
|
||||
// there's a chance their attack will make it nonblocking.
|
||||
if (!(Flags & SF_SEEPASTSHOOTABLELINES))
|
||||
{
|
||||
if (!(ld->activation & SPAC_Impact))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
if (ld->special != ACS_Execute && ld->special != ACS_ExecuteAlways)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
if (ld->args[1] != 0 && ld->args[1] != level.levelnum)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/*
|
||||
==================
|
||||
|
@ -392,36 +436,9 @@ bool SightCheck::P_SightCheckLine (line_t *ld)
|
|||
return true; // line isn't crossed
|
||||
}
|
||||
|
||||
// try to early out the check
|
||||
if (!ld->backsector || !(ld->flags & ML_TWOSIDED) || (ld->flags & ML_BLOCKSIGHT))
|
||||
return false; // stop checking
|
||||
|
||||
// [RH] don't see past block everything lines
|
||||
if (ld->flags & ML_BLOCKEVERYTHING)
|
||||
if (!portalfound) // when portals come into play, the quick-outs here may not be performed
|
||||
{
|
||||
if (!(Flags & SF_SEEPASTBLOCKEVERYTHING))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
// Pretend the other side is invisible if this is not an impact line
|
||||
// that runs a script on the current map. Used to prevent monsters
|
||||
// from trying to attack through a block everything line unless
|
||||
// there's a chance their attack will make it nonblocking.
|
||||
if (!(Flags & SF_SEEPASTSHOOTABLELINES))
|
||||
{
|
||||
if (!(ld->activation & SPAC_Impact))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (ld->special != ACS_Execute && ld->special != ACS_ExecuteAlways)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (ld->args[1] != 0 && ld->args[1] != level.levelnum)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
if (LineBlocksSight(ld)) return false;
|
||||
}
|
||||
|
||||
sightcounts[3]++;
|
||||
|
|
|
@ -788,7 +788,7 @@ class Actor : Thinker native
|
|||
native void A_SpawnDebris(class<Actor> spawntype, bool transfer_translation = false, double mult_h = 1, double mult_v = 1);
|
||||
native void A_SpawnParticle(color color1, int flags = 0, int lifetime = 35, double size = 1, double angle = 0, double xoff = 0, double yoff = 0, double zoff = 0, double velx = 0, double vely = 0, double velz = 0, double accelx = 0, double accely = 0, double accelz = 0, double startalphaf = 1, double fadestepf = -1, double sizestep = 0);
|
||||
native void A_ExtChase(bool usemelee, bool usemissile, bool playactive = true, bool nightmarefast = false);
|
||||
native void A_DropInventory(class<Inventory> itemtype, int amount);
|
||||
native void A_DropInventory(class<Inventory> itemtype, int amount = -1);
|
||||
native void A_SetBlend(color color1, double alpha, int tics, color color2 = 0);
|
||||
deprecated native void A_ChangeFlag(string flagname, bool value);
|
||||
native void A_ChangeCountFlags(int kill = FLAG_NO_CHANGE, int item = FLAG_NO_CHANGE, int secret = FLAG_NO_CHANGE);
|
||||
|
|
Loading…
Reference in a new issue