- Joined
- Apr 29, 2007
- Messages
- 826
pew pew. A very neat update in my opinion. I again rewrote the whole system to archieve even more configurability and ease the working with it.
It now features 2 struct types, one is called lane and the other is called spawn.
The lane is obviously the way a spawn moves, which still uses rects. (Since you can easily move them within the editor)
A spawn contains the data to spawn units. Each spawn requires one lane, one owner (a player), one unit type, an amount and an interval.
This features in-game changes of everything, means you can replace (or change) the lane, the player, the unit type, the amount and even the interval while the game is running.
You can also get the revertion of any lane (pretty useful for AoS maps, you just have to create half the lanes and get the reversed ones)
The functions featured are:
Enough talked, let's come to the code:
It now features 2 struct types, one is called lane and the other is called spawn.
The lane is obviously the way a spawn moves, which still uses rects. (Since you can easily move them within the editor)
A spawn contains the data to spawn units. Each spawn requires one lane, one owner (a player), one unit type, an amount and an interval.
This features in-game changes of everything, means you can replace (or change) the lane, the player, the unit type, the amount and even the interval while the game is running.
You can also get the revertion of any lane (pretty useful for AoS maps, you just have to create half the lanes and get the reversed ones)
The functions featured are:
- Lane:
-
JASS:
method registerWaypoint takes rect returns nothing method getWaypoint takes integer returns rect method getWaypointX takes integer returns real method getWaypointY takes integer returns real method getWaypointCount takes nothing returns integer method getReversed takes nothing returns Lane method list takes nothing returns nothing
-
- Spawn:
-
JASS:
static method create takes Lane, player, integer id, integer amount, real time returns thistype method startSpawn takes nothing returns nothing method pauseSpawn takes nothing returns nothing method setSpawningUnit takes integer id returns nothing method setSpawnCount takes integer amount returns nothing method setOwner takes player returns nothing method setLane takes Lane returns nothing method setInterval takes real returns nothing
-
Enough talked, let's come to the code:
JASS:
library SpawnAndMove
globals
//Which order get's issued to spawned units
public string ISSUED_ORDER = "attack"
//Distance to check if the unit is near his next waypoint (Set this higher if your rects are big)
private constant real CHECK_DISTANCE = 500.
//Do NOT change
private hashtable hash
endglobals
struct Lane
private integer waypointCount = 0
method registerWaypoint takes rect r returns nothing
call SaveRectHandle(hash, this, this.waypointCount, r)
set this.waypointCount = this.waypointCount + 1
endmethod
method getWaypoint takes integer index returns rect
return LoadRectHandle(hash, this, index)
endmethod
method getWaypointX takes integer index returns real
return GetRectCenterX(LoadRectHandle(hash, this, index))
endmethod
method getWaypointY takes integer index returns real
return GetRectCenterY(LoadRectHandle(hash, this, index))
endmethod
method getWaypointCount takes nothing returns integer
return this.waypointCount
endmethod
method getReversed takes nothing returns thistype
local thistype reversed = thistype.allocate()
local integer i = this.waypointCount-1
loop
call reversed.registerWaypoint(this.getWaypoint(i))
set i = i-1
exitwhen i < 0
endloop
return reversed
endmethod
method list takes nothing returns nothing
local integer i = 0
loop
call BJDebugMsg("Rect in Pos: " + I2S(i))
call BJDebugMsg("---")
call BJDebugMsg("X: " + I2S(R2I(this.getWaypointX(i))))
call BJDebugMsg("X: " + I2S(R2I(this.getWaypointY(i))))
set i = i + 1
exitwhen i >= this.waypointCount
endloop
endmethod
private method onDestroy takes nothing returns nothing
call FlushChildHashtable(hash, this)
endmethod
endstruct
struct Spawn
private player owner
private integer spawned
private integer spawnCount
private real interval
private Lane lane
private timer t
private static trigger onEnter
private region waypoint
private static method onInit takes nothing returns nothing
set hash = InitHashtable()
set thistype.onEnter = CreateTrigger()
endmethod
private static method enter takes nothing returns boolean
local thistype this
local integer cur
local unit u = GetFilterUnit()
if HaveSavedInteger(hash, GetHandleId(u), 0) then
set this = LoadInteger(hash, GetHandleId(u), 1)
set cur = LoadInteger(hash, GetHandleId(u), 0)
if IsUnitInRangeXY(u, LoadReal(hash, GetHandleId(u), 2), LoadReal(hash, GetHandleId(u), 3), CHECK_DISTANCE) then
set cur = cur + 1
if cur >= this.lane.getWaypointCount() then
call FlushChildHashtable(hash, GetHandleId(u))
return false
endif
call SaveInteger(hash, GetHandleId(u), 0, cur)
call SaveReal(hash, GetHandleId(u), 2, this.lane.getWaypointX(cur))
call SaveReal(hash, GetHandleId(u), 3, this.lane.getWaypointY(cur))
call IssuePointOrder(u, ISSUED_ORDER, this.lane.getWaypointX(cur), this.lane.getWaypointY(cur))
endif
endif
set u = null
return false
endmethod
static method create takes Lane l, player p, integer toSpawn, integer count, real time returns thistype
local thistype this = thistype.allocate()
local trigger t = CreateTrigger()
local integer i = 0
set this.lane = l
set this.owner = p
set this.spawned = toSpawn
set this.spawnCount = count
set this.interval = time
set this.t = CreateTimer()
call SaveInteger(hash, GetHandleId(this.t), 0, this)
call TriggerRegisterAnyUnitEventBJ(t, EVENT_PLAYER_UNIT_DEATH)
call TriggerAddCondition(t, Filter(function thistype.flush))
set this.waypoint = CreateRegion()
loop
call RegionAddRect(this.waypoint, l.getWaypoint(i))
set i = i + 1
exitwhen i >= l.getWaypointCount()
endloop
call TriggerRegisterEnterRegion(this.onEnter, this.waypoint, Filter(function thistype.enter))
return this
endmethod
method startSpawn takes nothing returns nothing
call TimerStart(this.t, this.interval, true, function thistype.spawn)
endmethod
method pauseSpawn takes nothing returns nothing
call PauseTimer(this.t)
endmethod
method setSpawningUnit takes integer new returns nothing
set this.spawned = new
endmethod
method setSpawnCount takes integer count returns nothing
set this.spawnCount = count
endmethod
method setOwner takes player new returns nothing
set this.owner = new
endmethod
method setLane takes Lane new returns nothing
local integer i = 0
set this.lane = new
call RemoveRegion(this.waypoint)
set this.waypoint = CreateRegion()
loop
call RegionAddRect(this.waypoint, this.lane.getWaypoint(i))
set i = i + 1
exitwhen i >= this.lane.getWaypointCount()
endloop
call TriggerRegisterEnterRegion(this.onEnter, this.waypoint, Filter(function thistype.enter))
endmethod
method setInterval takes real time returns nothing
call PauseTimer(this.t)
set this.interval = time
call TimerStart(this.t, time, true, function thistype.spawn)
endmethod
private static method spawn takes nothing returns nothing
local thistype this = LoadInteger(hash, GetHandleId(GetExpiredTimer()), 0)
local integer i = 0
local unit u
loop
set u = CreateUnit(this.owner, this.spawned, this.lane.getWaypointX(0), this.lane.getWaypointY(0), 0)
call IssuePointOrder(u, ISSUED_ORDER, this.lane.getWaypointX(1), this.lane.getWaypointY(1))
call SaveInteger(hash, GetHandleId(u), 0, 1)
call SaveInteger(hash, GetHandleId(u), 1, this)
call SaveReal(hash, GetHandleId(u), 2, this.lane.getWaypointX(1))
call SaveReal(hash, GetHandleId(u), 3, this.lane.getWaypointY(1))
set i = i + 1
exitwhen i >= this.spawnCount
endloop
set u = null
endmethod
private static method flush takes nothing returns boolean
if HaveSavedInteger(hash, GetHandleId(GetDyingUnit()), 0) then
call FlushChildHashtable(hash, GetHandleId(GetDyingUnit()))
endif
return false
endmethod
endstruct
endlibrary
Last edited: