Skip to content
Back to wiki

Author a Ranged Attack

A

Author

Author

Created: Oct 21, 2026Updated: Oct 21, 2026

Table of contents

Author a Ranged Attack

This page builds the smallest ranged shot: one bullet definition, one bullet request, and an ability that calls WaitForBulletEvent, reads UGCS_AttackRequest_Bullet from OptionalObject, and hands it to the bullet component. Predicted bullets own trajectory and presentation only. Gameplay Effects, chain bullets, and emitter follow-ups happen on the server.

Related pages: if the Flow still has no Result, start with Register the First Attack Result. The bullet contract is in Bullet Runtime; request fields are in Attack Definitions and Requests.

Prerequisites

  1. You attached Combat and Bullet components from Attach Combat Components. Hit detection also needs the Trace component. The target Flow already registers a Result from the attribute callback, as in Register the First Attack Result.
  2. The authority already called InitializeAbilitySystem.
  3. You have one FGCS_AttackDefinition row whose TargetEffectClass changes a target attribute.
  4. You have a bullet actor that implements IGCS_BulletInterface. Inheriting AGCS_BulletInstance or AGCS_SphereBulletInstance is enough.

1. Author the bullet definition

Create a Data Table with row type GCS Bullet Definition (FGCS_BulletDefinition):

Field

This page

BulletActorClass

A spawnable class that implements IGCS_BulletInterface; not an abstract class

BulletCount / LaunchAngle / LaunchAngleInterval

One shot, angle 0

InitialSpeed / MaxSpeed

For example 1500, enough to see a trail

AttackDefinition

The existing attack-definition row

TraceDefinitions

At least one hit Trace; these override traces on the bullet instance class

Count, spread, and speed live on the definition, not the request. Leave chain and emitter empty on this page; those spawn on the server only.

2. Fill the bullet request

Create UGCS_AttackRequest_Bullet:

Field

Role

BulletDefinitionHandle

The bullet-definition row from step 1

TargetingSourceType

Aim origin: CameraTowardsFocus, PawnForward, PawnTowardsFocus, WeaponForward, WeaponTowardsFocus, Custom

SourceComponentLookupTagName / SourceSocketName / SourceWeaponSocketName

Needed except for camera-towards-focus; a missing socket falls back to the source location

bRequireTargeting

Turn on when a locked target is required to fire

PawnForward or CameraTowardsFocus is enough here. Custom must override GetTargetingTransform. A weapon origin can also use GCS_GetTargetingStartTransform on the weapon interface.

3. Hand the request to the Task through an Event

In the ranged ability, call WaitForBulletEvent:

  1. Set the Gameplay Event tag to listen for.
  2. bInUseScopedPredictionWindow defaults to true and wraps a local player shot in FScopedPredictionWindow.
  3. When the event fires, the Task reads UGCS_AttackRequest_Bullet from EventData.OptionalObject and passes it to UGCS_BulletSystemComponent.
  4. Success broadcasts OnBulletSpawned; failure broadcasts OnBulletSpawnFailed.

You can store the same request on GCS_ANS_BulletTrace and fire a Gameplay Event with that OptionalObject from the window. The notify is not a runtime launcher either.

ValidateAttackRequest is overridable. The default only checks that the request is valid and BulletDefinitionHandle resolves a row. Fire rate, ammo, and resource legality stay with the project. Do not assume the component rejects those shots.

Expected result

After a locally controlled player fires, the client shows a trail immediately and the Debugger Bullet section lists a predicted Entry. After the server confirms, the Entry is confirmed and a hit applies GE. The predicted client bullet does not change attributes.

Verify

  1. Open the Combat category of Gameplay Debugger and inspect Bullet after one shot: entries, instances, and Pending / Confirmed / LocalPredicted counts.
  2. The predicted bullet has a trail and FX; target attributes do not change.
  3. The server window shows the same Entry and an Attack Result after the hit.
  4. If you configured chain or emitter, follow-up bullets appear only on the server. The client does not spawn its own batch.
  5. Set LogGCS_Bullet to Verbose to see spawn, confirm, or deny.

Common failures

Symptom

Check first

Event arrives, nothing spawns

OptionalObject is UGCS_AttackRequest_Bullet; ValidateAttackRequest did not fail

Trail, no GE

Confirm it is a predicted bullet. No GE on predicted bullets is the contract

Server has no Entry either

The owning client reached server spawn; AI / non-locally-controlled shots spawn authoritatively

BulletActorClass fails to spawn

The class implements IGCS_BulletInterface and is instantiable

Aim is wrong

TargetingSourceType, socket, and tag resolve; a required lock exists when bRequireTargeting is true

Fire rate is unlimited

The default does not check rate or resources. Gate in an overridden ValidateAttackRequest or an Ability Cost

Next

After the ranged loop works, continue with Configure Combo and Weapon. Prediction that disagrees with authority: Debugging and Troubleshooting.