Merge commit '2719ce86dc' into scripting
Conflicts: src/info.h src/thingdef/thingdef_codeptr.cpp (until right before the main work for multiple tags.)
This commit is contained in:
commit
8447990889
93 changed files with 1857 additions and 1565 deletions
214
src/p_spec.cpp
214
src/p_spec.cpp
|
|
@ -195,29 +195,48 @@ bool CheckIfExitIsGood (AActor *self, level_info_t *info)
|
|||
// Find the next sector with a specified tag.
|
||||
// Rewritten by Lee Killough to use chained hashing to improve speed
|
||||
|
||||
int P_FindSectorFromTag (int tag, int start)
|
||||
int FSectorTagIterator::Next()
|
||||
{
|
||||
start = start >= 0 ? sectors[start].nexttag :
|
||||
sectors[(unsigned) tag % (unsigned) numsectors].firsttag;
|
||||
while (start >= 0 && sectors[start].tag != tag)
|
||||
int ret;
|
||||
if (searchtag == INT_MIN)
|
||||
{
|
||||
ret = start;
|
||||
start = -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
while (start != -1 && sectors[start].tag != searchtag) start = sectors[start].nexttag;
|
||||
if (start == -1) return -1;
|
||||
ret = start;
|
||||
start = sectors[start].nexttag;
|
||||
return start;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int FSectorTagIterator::NextCompat(bool compat, int start)
|
||||
{
|
||||
if (!compat) return Next();
|
||||
|
||||
for (int i = start + 1; i < numsectors; i++)
|
||||
{
|
||||
if (sectors[i].HasTag(searchtag)) return i;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
// killough 4/16/98: Same thing, only for linedefs
|
||||
|
||||
int P_FindLineFromID (int id, int start)
|
||||
int FLineIdIterator::Next()
|
||||
{
|
||||
start = start >= 0 ? lines[start].nextid :
|
||||
lines[(unsigned) id % (unsigned) numlines].firstid;
|
||||
while (start >= 0 && lines[start].id != id)
|
||||
start = lines[start].nextid;
|
||||
return start;
|
||||
while (start != -1 && lines[start].id != searchtag) start = lines[start].nextid;
|
||||
if (start == -1) return -1;
|
||||
int ret = start;
|
||||
start = lines[start].nextid;
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// P_ActivateLine
|
||||
|
|
@ -260,13 +279,13 @@ bool P_ActivateLine (line_t *line, AActor *mo, int side, int activationType)
|
|||
}
|
||||
// some old WADs use this method to create walls that change the texture when shot.
|
||||
else if (activationType == SPAC_Impact && // only for shootable triggers
|
||||
(level.flags2 & LEVEL2_DUMMYSWITCHES) && // this is only a compatibility setting for an old hack!
|
||||
(level.flags2 & LEVEL2_DUMMYSWITCHES) && // this is only a compatibility setting for an old hack!
|
||||
!repeat && // only non-repeatable triggers
|
||||
(special<Generic_Floor || special>Generic_Crusher) && // not for Boom's generalized linedefs
|
||||
special && // not for lines without a special
|
||||
line->args[0] == line->id && // Safety check: exclude edited UDMF linedefs or ones that don't map the tag to args[0]
|
||||
line->HasId(line->args[0]) && // Safety check: exclude edited UDMF linedefs or ones that don't map the tag to args[0]
|
||||
line->args[0] && // only if there's a tag (which is stored in the first arg)
|
||||
P_FindSectorFromTag (line->args[0], -1) == -1) // only if no sector is tagged to this linedef
|
||||
P_FindFirstSectorFromTag (line->args[0]) == -1) // only if no sector is tagged to this linedef
|
||||
{
|
||||
P_ChangeSwitchTexture (line->sidedef[0], repeat, special);
|
||||
line->special = 0;
|
||||
|
|
@ -657,9 +676,9 @@ static void DoSectorDamage(AActor *actor, sector_t *sec, int amount, FName type,
|
|||
|
||||
void P_SectorDamage(int tag, int amount, FName type, PClassActor *protectClass, int flags)
|
||||
{
|
||||
int secnum = -1;
|
||||
|
||||
while ((secnum = P_FindSectorFromTag (tag, secnum)) >= 0)
|
||||
FSectorTagIterator itr(tag);
|
||||
int secnum;
|
||||
while ((secnum = itr.Next()) >= 0)
|
||||
{
|
||||
AActor *actor, *next;
|
||||
sector_t *sec = §ors[secnum];
|
||||
|
|
@ -884,12 +903,14 @@ DLightTransfer::DLightTransfer (sector_t *srcSec, int target, bool copyFloor)
|
|||
|
||||
if (copyFloor)
|
||||
{
|
||||
for (secnum = -1; (secnum = P_FindSectorFromTag (target, secnum)) >= 0; )
|
||||
FSectorTagIterator itr(target);
|
||||
while ((secnum = itr.Next()) >= 0)
|
||||
sectors[secnum].ChangeFlags(sector_t::floor, 0, PLANEF_ABSLIGHTING);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (secnum = -1; (secnum = P_FindSectorFromTag (target, secnum)) >= 0; )
|
||||
FSectorTagIterator itr(target);
|
||||
while ((secnum = itr.Next()) >= 0)
|
||||
sectors[secnum].ChangeFlags(sector_t::ceiling, 0, PLANEF_ABSLIGHTING);
|
||||
}
|
||||
ChangeStatNum (STAT_LIGHTTRANSFER);
|
||||
|
|
@ -912,12 +933,14 @@ void DLightTransfer::DoTransfer (int level, int target, bool floor)
|
|||
|
||||
if (floor)
|
||||
{
|
||||
for (secnum = -1; (secnum = P_FindSectorFromTag (target, secnum)) >= 0; )
|
||||
FSectorTagIterator itr(target);
|
||||
while ((secnum = itr.Next()) >= 0)
|
||||
sectors[secnum].SetPlaneLight(sector_t::floor, level);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (secnum = -1; (secnum = P_FindSectorFromTag (target, secnum)) >= 0; )
|
||||
FSectorTagIterator itr(target);
|
||||
while ((secnum = itr.Next()) >= 0)
|
||||
sectors[secnum].SetPlaneLight(sector_t::ceiling, level);
|
||||
}
|
||||
}
|
||||
|
|
@ -985,7 +1008,8 @@ DWallLightTransfer::DWallLightTransfer (sector_t *srcSec, int target, BYTE flags
|
|||
wallflags = WALLF_ABSLIGHTING | WALLF_NOFAKECONTRAST;
|
||||
}
|
||||
|
||||
for (linenum = -1; (linenum = P_FindLineFromID (target, linenum)) >= 0; )
|
||||
FLineIdIterator itr(target);
|
||||
while ((linenum = itr.Next()) >= 0)
|
||||
{
|
||||
if (flags & WLF_SIDE1 && lines[linenum].sidedef[0] != NULL)
|
||||
{
|
||||
|
|
@ -1015,7 +1039,8 @@ void DWallLightTransfer::DoTransfer (short lightlevel, int target, BYTE flags)
|
|||
{
|
||||
int linenum;
|
||||
|
||||
for (linenum = -1; (linenum = P_FindLineFromID (target, linenum)) >= 0; )
|
||||
FLineIdIterator itr(target);
|
||||
while ((linenum = itr.Next()) >= 0)
|
||||
{
|
||||
line_t *line = &lines[linenum];
|
||||
|
||||
|
|
@ -1173,7 +1198,9 @@ void P_SpawnPortal(line_t *line, int sectortag, int plane, int alpha)
|
|||
reference->flags |= MF_JUSTATTACKED;
|
||||
anchor->flags |= MF_JUSTATTACKED;
|
||||
|
||||
for (int s=-1; (s = P_FindSectorFromTag(sectortag,s)) >= 0;)
|
||||
int s;
|
||||
FSectorTagIterator itr(sectortag);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
SetPortal(§ors[s], plane, reference, alpha);
|
||||
}
|
||||
|
|
@ -1193,7 +1220,8 @@ void P_SpawnPortal(line_t *line, int sectortag, int plane, int alpha)
|
|||
}
|
||||
else
|
||||
{
|
||||
for (int s=-1; (s = P_FindSectorFromTag(lines[j].args[0],s)) >= 0;)
|
||||
FSectorTagIterator itr(lines[j].args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
SetPortal(§ors[s], plane, reference, alpha);
|
||||
}
|
||||
|
|
@ -1374,38 +1402,41 @@ void P_SpawnSpecials (void)
|
|||
// killough 3/7/98:
|
||||
// support for drawn heights coming from different sector
|
||||
case Transfer_Heights:
|
||||
sec = lines[i].frontsector;
|
||||
if (lines[i].args[1] & 2)
|
||||
{
|
||||
sec->MoreFlags |= SECF_FAKEFLOORONLY;
|
||||
sec = lines[i].frontsector;
|
||||
if (lines[i].args[1] & 2)
|
||||
{
|
||||
sec->MoreFlags |= SECF_FAKEFLOORONLY;
|
||||
}
|
||||
if (lines[i].args[1] & 4)
|
||||
{
|
||||
sec->MoreFlags |= SECF_CLIPFAKEPLANES;
|
||||
}
|
||||
if (lines[i].args[1] & 8)
|
||||
{
|
||||
sec->MoreFlags |= SECF_UNDERWATER;
|
||||
}
|
||||
else if (forcewater)
|
||||
{
|
||||
sec->MoreFlags |= SECF_FORCEDUNDERWATER;
|
||||
}
|
||||
if (lines[i].args[1] & 16)
|
||||
{
|
||||
sec->MoreFlags |= SECF_IGNOREHEIGHTSEC;
|
||||
}
|
||||
if (lines[i].args[1] & 32)
|
||||
{
|
||||
sec->MoreFlags |= SECF_NOFAKELIGHT;
|
||||
}
|
||||
FSectorTagIterator itr(lines[i].args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
sectors[s].heightsec = sec;
|
||||
sec->e->FakeFloor.Sectors.Push(§ors[s]);
|
||||
sectors[s].AdjustFloorClip();
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (lines[i].args[1] & 4)
|
||||
{
|
||||
sec->MoreFlags |= SECF_CLIPFAKEPLANES;
|
||||
}
|
||||
if (lines[i].args[1] & 8)
|
||||
{
|
||||
sec->MoreFlags |= SECF_UNDERWATER;
|
||||
}
|
||||
else if (forcewater)
|
||||
{
|
||||
sec->MoreFlags |= SECF_FORCEDUNDERWATER;
|
||||
}
|
||||
if (lines[i].args[1] & 16)
|
||||
{
|
||||
sec->MoreFlags |= SECF_IGNOREHEIGHTSEC;
|
||||
}
|
||||
if (lines[i].args[1] & 32)
|
||||
{
|
||||
sec->MoreFlags |= SECF_NOFAKELIGHT;
|
||||
}
|
||||
for (s = -1; (s = P_FindSectorFromTag(lines[i].args[0],s)) >= 0;)
|
||||
{
|
||||
sectors[s].heightsec = sec;
|
||||
sec->e->FakeFloor.Sectors.Push(§ors[s]);
|
||||
sectors[s].AdjustFloorClip();
|
||||
}
|
||||
break;
|
||||
|
||||
// killough 3/16/98: Add support for setting
|
||||
// floor lighting independently (e.g. lava)
|
||||
|
|
@ -1458,9 +1489,10 @@ void P_SpawnSpecials (void)
|
|||
{
|
||||
case Init_Gravity:
|
||||
{
|
||||
float grav = ((float)P_AproxDistance (lines[i].dx, lines[i].dy)) / (FRACUNIT * 100.0f);
|
||||
for (s = -1; (s = P_FindSectorFromTag(lines[i].args[0],s)) >= 0;)
|
||||
sectors[s].gravity = grav;
|
||||
float grav = ((float)P_AproxDistance (lines[i].dx, lines[i].dy)) / (FRACUNIT * 100.0f);
|
||||
FSectorTagIterator itr(lines[i].args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
sectors[s].gravity = grav;
|
||||
}
|
||||
break;
|
||||
|
||||
|
|
@ -1470,7 +1502,8 @@ void P_SpawnSpecials (void)
|
|||
case Init_Damage:
|
||||
{
|
||||
int damage = P_AproxDistance (lines[i].dx, lines[i].dy) >> FRACBITS;
|
||||
for (s = -1; (s = P_FindSectorFromTag(lines[i].args[0],s)) >= 0;)
|
||||
FSectorTagIterator itr(lines[i].args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
sectors[s].damage = damage;
|
||||
sectors[s].mod = 0;//MOD_UNKNOWN;
|
||||
|
|
@ -1493,9 +1526,12 @@ void P_SpawnSpecials (void)
|
|||
// or ceiling texture, to distinguish floor and ceiling sky.
|
||||
|
||||
case Init_TransferSky:
|
||||
for (s = -1; (s = P_FindSectorFromTag(lines[i].args[0],s)) >= 0;)
|
||||
sectors[s].sky = (i+1) | PL_SKYFLAT;
|
||||
break;
|
||||
{
|
||||
FSectorTagIterator itr(lines[i].args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
sectors[s].sky = (i + 1) | PL_SKYFLAT;
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
|
@ -1756,7 +1792,7 @@ static void P_SpawnScrollers(void)
|
|||
if (lines[i].special == Sector_CopyScroller)
|
||||
{
|
||||
// don't allow copying the scroller if the sector has the same tag as it would just duplicate it.
|
||||
if (lines[i].args[0] != lines[i].frontsector->tag)
|
||||
if (lines[i].frontsector->HasTag(lines[i].args[0]))
|
||||
{
|
||||
copyscrollers.Push(i);
|
||||
}
|
||||
|
|
@ -1832,25 +1868,29 @@ static void P_SpawnScrollers(void)
|
|||
register int s;
|
||||
|
||||
case Scroll_Ceiling:
|
||||
for (s=-1; (s = P_FindSectorFromTag (l->args[0],s)) >= 0;)
|
||||
{
|
||||
FSectorTagIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
new DScroller (DScroller::sc_ceiling, -dx, dy, control, s, accel);
|
||||
new DScroller(DScroller::sc_ceiling, -dx, dy, control, s, accel);
|
||||
}
|
||||
for(unsigned j = 0;j < copyscrollers.Size(); j++)
|
||||
for (unsigned j = 0; j < copyscrollers.Size(); j++)
|
||||
{
|
||||
line_t *line = &lines[copyscrollers[j]];
|
||||
|
||||
if (line->args[0] == l->args[0] && (line->args[1] & 1))
|
||||
{
|
||||
new DScroller (DScroller::sc_ceiling, -dx, dy, control, int(line->frontsector-sectors), accel);
|
||||
new DScroller(DScroller::sc_ceiling, -dx, dy, control, int(line->frontsector - sectors), accel);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case Scroll_Floor:
|
||||
if (l->args[2] != 1)
|
||||
{ // scroll the floor texture
|
||||
for (s=-1; (s = P_FindSectorFromTag (l->args[0],s)) >= 0;)
|
||||
FSectorTagIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
new DScroller (DScroller::sc_floor, -dx, dy, control, s, accel);
|
||||
}
|
||||
|
|
@ -1867,7 +1907,8 @@ static void P_SpawnScrollers(void)
|
|||
|
||||
if (l->args[2] > 0)
|
||||
{ // carry objects on the floor
|
||||
for (s=-1; (s = P_FindSectorFromTag (l->args[0],s)) >= 0;)
|
||||
FSectorTagIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
new DScroller (DScroller::sc_carry, dx, dy, control, s, accel);
|
||||
}
|
||||
|
|
@ -1886,10 +1927,15 @@ static void P_SpawnScrollers(void)
|
|||
// killough 3/1/98: scroll wall according to linedef
|
||||
// (same direction and speed as scrolling floors)
|
||||
case Scroll_Texture_Model:
|
||||
for (s=-1; (s = P_FindLineFromID (l->args[0],s)) >= 0;)
|
||||
{
|
||||
FLineIdIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
if (s != i)
|
||||
new DScroller (dx, dy, lines+s, control, accel);
|
||||
new DScroller(dx, dy, lines + s, control, accel);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case Scroll_Texture_Offsets:
|
||||
// killough 3/2/98: scroll according to sidedef offsets
|
||||
|
|
@ -2041,7 +2087,8 @@ void P_SetSectorFriction (int tag, int amount, bool alterFlag)
|
|||
// higher friction value actually means 'less friction'.
|
||||
movefactor = FrictionToMoveFactor(friction);
|
||||
|
||||
for (s = -1; (s = P_FindSectorFromTag (tag,s)) >= 0; )
|
||||
FSectorTagIterator itr(tag);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
// killough 8/28/98:
|
||||
//
|
||||
|
|
@ -2153,7 +2200,7 @@ DPusher::DPusher (DPusher::EPusher type, line_t *l, int magnitude, int angle,
|
|||
|
||||
int DPusher::CheckForSectorMatch (EPusher type, int tag)
|
||||
{
|
||||
if (m_Type == type && sectors[m_Affectee].tag == tag)
|
||||
if (m_Type == type && sectors[m_Affectee].HasTag(tag))
|
||||
return m_Affectee;
|
||||
else
|
||||
return -1;
|
||||
|
|
@ -2356,20 +2403,27 @@ static void P_SpawnPushers ()
|
|||
switch (l->special)
|
||||
{
|
||||
case Sector_SetWind: // wind
|
||||
for (s = -1; (s = P_FindSectorFromTag (l->args[0],s)) >= 0 ; )
|
||||
new DPusher (DPusher::p_wind, l->args[3] ? l : NULL, l->args[1], l->args[2], NULL, s);
|
||||
{
|
||||
FSectorTagIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
new DPusher(DPusher::p_wind, l->args[3] ? l : NULL, l->args[1], l->args[2], NULL, s);
|
||||
l->special = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
case Sector_SetCurrent: // current
|
||||
for (s = -1; (s = P_FindSectorFromTag (l->args[0],s)) >= 0 ; )
|
||||
new DPusher (DPusher::p_current, l->args[3] ? l : NULL, l->args[1], l->args[2], NULL, s);
|
||||
{
|
||||
FSectorTagIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
new DPusher(DPusher::p_current, l->args[3] ? l : NULL, l->args[1], l->args[2], NULL, s);
|
||||
l->special = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
case PointPush_SetForce: // push/pull
|
||||
if (l->args[0]) { // [RH] Find thing by sector
|
||||
for (s = -1; (s = P_FindSectorFromTag (l->args[0], s)) >= 0 ; )
|
||||
FSectorTagIterator itr(l->args[0]);
|
||||
while ((s = itr.Next()) >= 0)
|
||||
{
|
||||
AActor *thing = P_GetPushThing (s);
|
||||
if (thing) { // No MT_P* means no effect
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue