|
Note: Wait! Stop! You do not need to copy this actor's code into your project! Here's why:
- This actor is already defined in GZDoom, there's no reason to define it again.
- In fact, trying to define an actor with the same name will cause an error (because it already exists).
- If you want to make your own version of this actor, use inheritance.
- Definitions for existing actors are put on the wiki for reference purpose only.
|
Custom bridge
|
Actor type
|
Bridge
|
Game
|
(ZDoom)
|
DoomEd Number
|
9991
|
Class Name
|
CustomBridge
|
Classes: CustomBridge
→Bridge
→ZBridge
CustomBridge can be used to create either a Doom-style or Hexen-style invisible bridge, and can also further customize the appearance and behavior of the rotating "bridge balls" when used as a Hexen-style bridge.
When placed in a map, the bridge's arguments control its appearance and behavior, as follows:
- Arg 1: Bridge radius, in mapunits
- Arg 2: Bridge height, in mapunits
- Arg 3: Number of bridge balls to display.
- Arg 4: Rotation speed and direction of bridge balls. 0 uses Hexen's default. Values from 1-128 rotate counterclockwise, while values from 129-255 go clockwise. For example:
- 0: Hexen default
- 11: 15° / second
- 21: 30° / second
- 32: 45° / second
- 64: 90° / second
- 128: 180° / second
- 192: -90° / second
- 223: -45° / second
- 233: -30° / second
- 244: -15° / second
- Arg 5: Rotation radius of bridge balls, in bridge radius %. 0 is Hexen-default (15 units regardless of bridge radius)
Note: When inheriting from this actor in ZScript or Decorate, you can redefine the Spawn state to change the way the bridge behaves as a Doom-format bridge (Arg 3 set to 0), or the See state to alter the way it behaves as a Hexen bridge. This can be used, for example, to change which actors are spawned instead of the bridge balls.
|
Note: The ZScript definition below is for reference and may be different in the current version of GZDoom.The most up-to-date version of this code can be found on GZDoom GitHub.
|
class CustomBridge : Actor
{
const ORBIT_RADIUS = 15;
default
{
+SOLID
+NOGRAVITY
+NOLIFTDROP
+ACTLIKEBRIDGE
Radius 32;
Height 2;
RenderStyle "None";
}
states
{
Spawn:
TLGL ABCDE 3 Bright;
Loop;
See:
TLGL A 2;
TLGL A 2 A_BridgeInit;
TLGL A -1;
Stop;
Death:
TLGL A 2;
TLGL A 300;
Stop;
}
override void BeginPlay ()
{
if (args[2]) // Hexen bridge if there are balls
{
SetState(SeeState);
A_SetSize(args[0] ? args[0] : 32, args[1] ? args[1] : 2);
}
else // No balls? Then a Doom bridge.
{
A_SetSize(args[0] ? args[0] : 36, args[1] ? args[1] : 4);
A_SetRenderStyle(1., STYLE_Normal);
}
}
override void OnDestroy()
{
// Hexen originally just set a flag to make the bridge balls remove themselves in A_BridgeOrbit.
// But this is not safe with custom bridge balls that do not necessarily call that function.
// So the best course of action is to look for all bridge balls here and destroy them ourselves.
let it = ThinkerIterator.Create("Actor");
Actor thing;
while ((thing = Actor(it.Next())))
{
if (thing.target == self)
{
thing.Destroy();
}
}
Super.OnDestroy();
}
void A_BridgeInit(class<Actor> balltype = "BridgeBall")
{
if (balltype == NULL)
{
balltype = "BridgeBall";
}
double startangle = random[orbit]() * (360./256.);
// Spawn triad into world -- may be more than a triad now.
int ballcount = args[2]==0 ? 3 : args[2];
for (int i = 0; i < ballcount; i++)
{
Actor ball = Spawn(balltype, Pos, ALLOW_REPLACE);
ball.Angle = startangle + (45./32) * (256/ballcount) * i;
ball.target = self;
double rotationradius = ORBIT_RADIUS;
if (args[4]) rotationradius = (args[4] * radius) / 100;
ball.SetOrigin(Vec3Angle(rotationradius, ball.Angle, 0), true);
ball.floorz = floorz;
ball.ceilingz = ceilingz;
}
}
}
ACTOR CustomBridge native
{
+SOLID
+NOGRAVITY
+NOLIFTDROP
+ACTLIKEBRIDGE
Radius 32
Height 2
RenderStyle None
action native A_BridgeInit(class<Actor> balltype = "BridgeBall");
States
{
Spawn:
TLGL ABCDE 3 Bright
Loop
See:
TLGL A 2
TLGL A 2 A_BridgeInit
TLGL A -1
Stop
Death:
TLGL A 2
TLGL A 300
Stop
}
}