System Anachrons Move & Spawn Systems

Anachron

New Member
Reaction score
53
(Yes, I am that Anachron from Hiveworkshop.com)

Anachrons Move System
JASS:

//WayPoint:
public static method create takes real bX, real bY, real tX, real tY, real tR returns WayPoint
public method moveUnit takes unit u returns nothing

//Way:
public static method create takes nothing returns thistype
private static method addWay takes thistype wy returns nothing
private static method removeWay takes thistype wy returns nothing
public method addWayPoint takes WayPoint wp returns nothing
public method removeWayPoint takes WayPoint wp returns nothing
public method addUnit takes unit u, integer curPos returns nothing
public method removeUnit takes unit u returns nothing
public method moveUnit takes unit u, integer curPos returns nothing
public method moveNext takes unit u, integer curPos returns nothing
public method getNearestWP takes unit u returns integer

JASS:

//:******************************************************************************
//: Anachrons Move System
//: by dhk_undead_lord / aka Anachron
//: version 1.05
//:
//:
//: ABOUT:
//: This system has been thought to be able to easily
//: create and manage spawn ways of troops.
//: Top priority is the automatic movement control,
//: such as high customizeability for users.
//:
//: WHAT YOU NEED:
//: You need JassNewGenPack to use this vJASS system.
//: (Download it here: <a href="http://www.wc3c.net/showthread.php?goto=newpost&amp;t=90999" target="_blank" class="link link--external" rel="nofollow ugc noopener">http://www.wc3c.net/showthread.php?goto=newpost&amp;t=90999</a>)
//:
//: STEPS TO IMPORT:
//: I.) Copy this code.
//: II.) Paste it into the head of your map.
//: (Therefor go to the Trigger Editor, select the mapname and paste
//: into the area on the right)
//: III.) Save your map!
//: (With File - Save Map (S) or control + S. DO NOT SAVE WITH SAVE AS!)
//: IV.) You got it! You imported the system.
//:
//: To make sure this system works, you should try a few tests!
//:
//: METHODS
//:
//: &gt;WayPoint.create takes real baseX, real baseY, real targX, real targY, real targRadius
//: Constructor of WayPoints.
//:
//: &gt;WayPoint.moveUnit takes unit u
//: Move any unit to the target of this waypoint!
//:
//: &gt;Way.create takes boolean scCon, boolean stCon, boolean hdCon returns Way
//: Create a new Way, say whether orders should recast attack/move or not.
//:
//: &gt;Way.addWayPoint takes WayPoint wp returns nothing
//: Add a waypoint to the system! Horray, another patrol point.
//:
//: &gt;Way.addUnit takes unit u returns nothing
//: Adds an unit to the way. Automaticly moves to the first waypoint.
//:
//: &gt;Way.removeUnit takes unit u returns nothing
//: Remove a unit from the way system.
//:
//: &gt;Way.moveUnit takes unit u, integer curPos returns nothing
//: Move the unit u to the waypoint curPos&#039;s position
//:
//: &gt;Way.moveNext takes unit u, integer curPos returns nothing
//: Sets the new wayPoint for the unit u
//:
//: &gt;Way.getNearestWP takes unit u returns integer
//: A very nice function to find the nearest waypoint of an unit.
//: Is perfect for Revive spells were you need to reregister,
//: because with this function its pretty easy to get the correct waypoint.
//:
//: Thanks for downloading and using my system!
//:
//: Please don&#039;t forget to give credits to me (dhk_undead_lord / Aka Anachron)
//:
//:******************************************************************************
library AnaMoveSys initializer init
    //==========================================================================
    // %CUSTOMIZATION AREA%: Feel free to change anything to what you need!
    //==========================================================================
    globals
        //: %Default Values%
        //: Basicly the radius the unit has to be to
        //: get ordered to the next waypoint.
        private constant real TARGET_TOLERANCE = 192.
        //: Sets whether the unit should move again
        //: after it casted a spell.
        private constant boolean SPELLCAST_CONTINUE = true
        //: Sets whether the unit should move again
        //: after it used stop command.
        private constant boolean STOP_CONTINUE = true
        //: Sets whether the unit should move again
        //: after it used the hold position command.
        private constant boolean HOLDPOSITION_CONTINUE = false
        //: Sets whether death units will automaticly
        //: removed by the system.
        //: WARNING: THIS IS HIGLY RECOMMENDED!
        //: TO ADD UNITS (LIKE REVIVE) USE THE addUnit()
        //: METHOD!
        private constant boolean DEATH_REMOVES = true

        //: %Hashtable Storage%
        //: Sets which key is for the unit ID
        private constant integer KEY_UNIT = 0
        //: Sets which key is for the way ID
        private constant integer KEY_WAY = 1
        //: Sets which key is for the current
        //: waypoint ID.
        private constant integer KEY_CURPOS = 2

        //: %Order Ids%
        private constant string ORDER_STOP = &quot;stop&quot;
        private constant string ORDER_HOLDPOSITION = &quot;position&quot;
        private constant string ORDER_ATTACKMOVE = &quot;attack&quot;

        //: %Timers%
        private constant timer MOVE_TIMER = CreateTimer()
        private constant real MOVE_INT = 0.75

        //: %Saving%
        private hashtable UNIT_DATA = InitHashtable()
        private group MOVING_UNITS = CreateGroup()
    endglobals

    //: %Conditions of reordering the units
    //: Here you can define the conditions,
    //: such as owner controlling and other
    //: useful filters.
    public function globalCheck takes nothing returns boolean
        return LoadWidgetHandle(UNIT_DATA, GetHandleId(GetTriggerUnit()), KEY_UNIT) != null
    endfunction

    public function checkSpellcast takes nothing returns boolean
        return globalCheck()
    endfunction

    public function checkStopOrder takes nothing returns boolean
        return globalCheck() and GetIssuedOrderId() == OrderId(ORDER_STOP)
    endfunction

    public function checkHoldOrder takes nothing returns boolean
        return globalCheck() and GetIssuedOrderId() == OrderId(ORDER_HOLDPOSITION)
    endfunction

    //==========================================================================
    //: %DO NOT CHANGE THIS UNLIKE YOU KNOW WHAT YOU ARE DOING%
    //==========================================================================

    public function reOrderUnit takes nothing returns nothing
        local integer unitID = 0
        local integer wayID = 0
        local integer curPos = 0

        if IsUnitInGroup(GetTriggerUnit(), MOVING_UNITS) then
            set unitID = GetHandleId(GetTriggerUnit())
            set wayID = LoadInteger(UNIT_DATA, unitID, KEY_WAY)
            set curPos = LoadInteger(UNIT_DATA, unitID, KEY_CURPOS)
            debug call BJDebugMsg(&quot;!AoSMoveSys] |NOTICE| &lt;Way[&quot; + I2S(wayID) + &quot;]&gt; &lt;Reorder unit &quot; + I2S(unitID) + &quot;&gt;&quot;)
            call Way.instances[wayID].moveUnit(GetTriggerUnit(), curPos)
        endif
    endfunction

    public function checkUnregister takes nothing returns boolean
        return GetOwningPlayer(GetTriggerUnit()) == Player(0)
    endfunction

    public function unregisterUnit takes nothing returns nothing
        local integer wayID = LoadInteger(UNIT_DATA, GetHandleId(GetTriggerUnit()), KEY_WAY)

        call Way.instances[wayID].removeUnit(GetTriggerUnit())
    endfunction

    struct WayPoint
        real baseX = 0.
        real baseY = 0.

        real targX = 0.
        real targY = 0.
        real targRadius = 0.

        integer ID = 0

        //: =================================
        //: CREATE NEW INSTANCES
        //: =================================
        public static method create takes real bX, real bY, real tX, real tY, real tR returns WayPoint
            local thistype wp = thistype.allocate()
                set wp.baseX = bX
                set wp.baseY = bY
                set wp.targX = tX
                set wp.targY = tY
                set wp.targRadius = tR
            return wp
        endmethod
        //: =================================

        //: =================================
        //: Move the unit to the target loc
        //: =================================
        public method moveUnit takes unit u returns nothing
            call IssuePointOrder(u, ORDER_ATTACKMOVE, .targX, .targY)
        endmethod
        //: =================================
    endstruct

    struct Way
        group units = CreateGroup()

        integer ID = 0
        static Way array instances[8191]
        static integer index = 0

        integer curwpID = 0
        WayPoint array wayPoints[128]

        //: Saves the triggers for the
        //: auto remove functions.
        //: -&gt; spellcast?
        static trigger scTrig = CreateTrigger()
        //: -&gt; stop?
        static trigger stTrig = CreateTrigger()
        //: -&gt; hold position?
        static trigger hpTrig = CreateTrigger()

        //: This unregisters unit which die
        static trigger deathTrig = CreateTrigger()

        //: =================================
        //: CREATE NEW INSTANCES
        //: =================================
        public static method create takes nothing returns thistype
            local thistype wy = thistype.allocate()
                call thistype.addWay(wy)
            return wy
        endmethod
        //: =================================

        //: =================================
        //: Add and remove ways to the system
        //: =================================
        private static method addWay takes thistype wy returns nothing
            set wy.ID = thistype.index
            set thistype.instances[thistype.index] = wy
            set thistype.index = thistype.index + 1
        endmethod

        private static method removeWay takes thistype wy returns nothing
            set thistype.instances[wy.ID] = thistype.instances[thistype.index]
            set thistype.index = thistype.index - 1
        endmethod
        //: =================================

        //: ====================================
        //: Add and remove Way Point to the way
        //: ====================================
        public method addWayPoint takes WayPoint wp returns nothing
            set wp.ID = .curwpID
            set .wayPoints[.curwpID] = wp
            set .curwpID = .curwpID + 1
        endmethod

        public method removeWayPoint takes WayPoint wp returns nothing
            set .wayPoints[wp.ID] = .wayPoints[.curwpID]
            set .curwpID = .curwpID - 1
        endmethod
        //: ====================================

        //: ====================================
        //: Add and remove units to the way
        //: ====================================
        public method addUnit takes unit u, integer curPos returns nothing
            if not(IsUnitInGroup(u, .units)) then
                call SaveWidgetHandle(UNIT_DATA, GetHandleId(u), KEY_UNIT, u)
                call SaveInteger(UNIT_DATA, GetHandleId(u), KEY_WAY, .ID)
                call SaveInteger(UNIT_DATA, GetHandleId(u), KEY_CURPOS, curPos)

                call GroupAddUnit(.units, u)
                call GroupAddUnit(MOVING_UNITS, u)

                call .moveUnit(u, curPos)
            else
                debug call BJDebugMsg(&quot;!AoSMoveSys] |ERROR| &lt;Way[&quot; + I2S(.ID) + &quot;]&gt; &lt;addUnit: UNIT ALREADY REGISTERED!&gt;&quot;)
            endif
        endmethod

        public method removeUnit takes unit u returns nothing
            call FlushChildHashtable(UNIT_DATA, GetHandleId(u))
            call GroupRemoveUnit(.units, u)
            call GroupRemoveUnit(MOVING_UNITS, u)
            debug call BJDebugMsg(&quot;!AoSMoveSys] |NOTICE| &lt;Way[&quot; + I2S(.ID) + &quot;]&gt; &lt;removeUnit: UNIT HAS BEEN REMOVED!&gt;&quot;)
        endmethod
        //: ====================================

        //: ====================================
        //: Move an unit to the target
        //: ====================================
        public method moveUnit takes unit u, integer curPos returns nothing
            call .wayPoints[curPos].moveUnit(u)
        endmethod

        public method moveNext takes unit u, integer curPos returns nothing
            set curPos = curPos + 1
            if curPos &lt; .curwpID then
                //: %Save data and move unit%
                call SaveInteger(UNIT_DATA, GetHandleId(u), KEY_CURPOS, curPos)
                call .moveUnit(u, curPos)
            else
                call .removeUnit(u)
            endif
        endmethod
        //: ====================================

        //: ====================================
        //: Additional Methods for users
        //: ====================================
        public method getNearestWP takes unit u returns integer
            local integer foundWP = -1
            local WayPoint wp = 0
            local integer i = 0
            local real tmpDist = 0.
            //: !Do NOT change this
            local real dist = 100000000.

            loop
                exitwhen i &gt;= .curwpID

                // %Compare the distances%
                set tmpDist = SquareRoot(GetUnitX(u) * wp.targX + GetUnitY(u) * wp.targY)
                if tmpDist &lt;= dist then
                    set foundWP = i
                    set dist = tmpDist
                endif

                set i = i + 1
            endloop

            return foundWP
        endmethod
        //: ====================================

        //: ====================================
        //: Desctrutor Method
        //: ====================================
        private method onDestroy takes nothing returns nothing
            local integer i = 0

            loop
                exitwhen i &gt;= .curwpID

                call .wayPoints<i>.destroy()

                set i = i + 1
            endloop

            call thistype.removeWay(this)
        endmethod
        //: ====================================
    endstruct

    private struct MoveOrders

        //: =================================
        //: CHECK ALL WAYS FOR SPAWNING
        //: =================================
        static method checkWays takes nothing returns nothing
            local Way wy = 0
            local WayPoint wp = 0
            local integer i = 0

            local unit u = null
            local group g = CreateGroup()
            local integer unitID = 0
            local integer wpID = 0

            local real dx = 0.
            local real dy = 0.
            local real dist = 0.

            loop
                exitwhen i &gt;= Way.index

                //----------------
                //: %Reset Data%
                //----------------
                set u = null
                call GroupClear(g)
                set wy = 0
                set wp = 0
                set unitID = 0
                //----------------

                set wy = Way.instances<i>
                call GroupAddGroup(wy.units, g)

                loop
                    set u = FirstOfGroup(g)
                    exitwhen u == null

                    //-----------------------
                    // %Get unit data%
                    //-----------------------
                    set unitID = GetHandleId(u)
                    set wpID = LoadInteger(UNIT_DATA, unitID, KEY_CURPOS)
                    set wp = wy.wayPoints[wpID]

                    //: Check whether the unit is in the range of
                    //: her checkpoint
                    set dx = GetUnitX(u) - wp.targX
                    set dy = GetUnitY(u) - wp.targY
                    set dist = SquareRoot(dx * dx + dy * dy)
                    if dist &lt;= wp.targRadius then
                        call wy.moveNext(u, wpID)
                        debug call BJDebugMsg(&quot;!AoSMoveSys] |NOTICE| &lt;Way[&quot; + I2S(wy.ID) + &quot;]&gt; &lt;Unit &quot; + I2S(GetHandleId(u)) + &quot; reached target&gt;&quot;)
                    endif

                    call GroupRemoveUnit(g, u)
                endloop

                set i = i + 1
            endloop

            call GroupClear(g)
            set u = null
            set g = null
        endmethod
        //: =================================
    endstruct

    private function init takes nothing returns nothing
        local integer i = 0
        call TimerStart(MOVE_TIMER, MOVE_INT, true, function MoveOrders.checkWays)

        if SPELLCAST_CONTINUE then
            call TriggerAddAction(Way.scTrig, function reOrderUnit)
            call TriggerAddCondition(Way.scTrig, Condition(function checkSpellcast))
            set i = 0
            loop
                exitwhen i &gt; 15
                call TriggerRegisterPlayerUnitEvent(Way.scTrig, Player(i), EVENT_PLAYER_UNIT_SPELL_ENDCAST, null)
                set i = i + 1
            endloop
        endif

        if STOP_CONTINUE then
            call TriggerAddAction(Way.stTrig, function reOrderUnit)
            call TriggerAddCondition(Way.stTrig, Condition(function checkStopOrder))
            set i = 0
            loop
                exitwhen i &gt; 15
                call TriggerRegisterPlayerUnitEvent(Way.scTrig, Player(i), EVENT_PLAYER_UNIT_ISSUED_ORDER, null)
                set i = i + 1
            endloop
        endif

        if HOLDPOSITION_CONTINUE then
            call TriggerAddAction(Way.hpTrig, function reOrderUnit)
            call TriggerAddCondition(Way.hpTrig, Condition(function checkHoldOrder))
            set i = 0
            loop
                exitwhen i &gt; 15
                call TriggerRegisterPlayerUnitEvent(Way.hpTrig, Player(i), EVENT_PLAYER_UNIT_ISSUED_ORDER, null)
                set i = i + 1
            endloop
        endif

        if DEATH_REMOVES then
            call TriggerAddAction(Way.deathTrig, function unregisterUnit)
            call TriggerAddCondition(Way.deathTrig, Condition(function checkUnregister))
            set i = 0
            loop
                exitwhen i &gt; 15
                call TriggerRegisterPlayerUnitEvent(Way.deathTrig, Player(i), EVENT_PLAYER_UNIT_DEATH, null)
                set i = i + 1
            endloop
        endif
    endfunction

endlibrary
</i></i>


Example
JASS:

scope example initializer init

    private function init takes nothing returns nothing
        local WayPoint wp = 0
        local Way wy = 0
        local unit u = CreateUnit(Player(0), &#039;hmpr&#039;, 800., -1200., 270.)

        call FogModifierStart(CreateFogModifierRect(Player(0), FOG_OF_WAR_VISIBLE, bj_mapInitialPlayableArea , false, false))

        //: Instaciate a new way
        set wy = Way.create()
        //: Add a new waypoint
        call wy.addWayPoint(WayPoint.create(800., -1200., -900., -1125., 192.))
        call wy.addWayPoint(WayPoint.create(-900., -1125., -860., -110., 192.))
        call wy.addWayPoint(WayPoint.create(-860., -110., 0., 0., 192.))
        //: Add a unit to the way, starting at waypoint 0.
        call wy.addUnit(u, 0)
    endfunction

endscope


Anachrons Spawns System
Spawn System:
JASS:

//UnitSpawn:
public static method create takes integer unitId, integer amount, onUnitSpawn onUnitSp, string effPath returns UnitSpawn
public method spawn takes player p, real posX, real posY returns nothing

//GroupSpawn:
public static method create takes real baseX, real baseY, real d returns thistype
public method addUnitSpawn takes UnitSpawn us returns nothing
public method removeUnitSpawn takes UnitSpawn us returns nothing
public method spawnUnits takes player p returns nothing

//Wave:
public static method create takes real i, player own returns thistype
public method addGroupSpawn takes GroupSpawn gs returns nothing
public method removeGroupSpawn takes GroupSpawn gs returns nothing
public method spawnUnitGroup takes integer i returns nothing

//WaveCheck
public static method checkSpawn takes nothing returns nothing
public static method addWave takes Wave w, integer times returns nothing
public static method removeWave takes Wave w returns nothing

JASS:

//:******************************************************************************
//: Anachrons Spawn System
//: by dhk_undead_lord / aka Anachron
//: version 1.05
//: BETA
//:
//: ABOUT:
//: This system has been made for easily create
//: and manage grouped spawns such as in DotA or
//: AotZ. Could also be very useful in Tower Defenses,
//: TAG maps and/or all other map genres with interval
//: spawning, such as Enfo, Castle Defenses etc.
//:
//: WHAT YOU NEED:
//: You need JassNewGenPack to use this vJASS system.
//: (Download it here: <a href="http://www.wc3c.net/showthread.php?goto=newpost&amp;t=90999" target="_blank" class="link link--external" rel="nofollow ugc noopener">http://www.wc3c.net/showthread.php?goto=newpost&amp;t=90999</a>)
//:
//: STEPS TO IMPORT:
//: I.) Copy this code.
//: II.) Paste it into the head of your map.
//: (Therefor go to the Trigger Editor, select the mapname and paste
//: into the area on the right)
//: III.) Save your map!
//: (With File - Save Map (S) or control + S. DO NOT SAVE WITH SAVE AS!)
//: IV.) You got it! You imported the system.
//:
//: To make sure this system works, you should try a few tests!
//:
//: METHODS
//:
//: SharedObjects:
//: This is a small library for GroupSpawns and unitsspawns so
//: you can easily manage conditional spawning and function calls
//: at actual spawning.
//:
//:
//:
//:
//:
//:
//: Thanks for downloading and using my system!
//:
//: Please don&#039;t forget to give credits to me (dhk_undead_lord / Aka Anachron)
//:
//:******************************************************************************
library AnaSpawnSys initializer init

    //==========================================================================
    // %CUSTOMIZATION AREA%: Feel free to change anything to what you need!
    //==========================================================================
    globals
        //: %Default Values%
        //: Check whether wanting to create units in each other
        //: on creation or not. This prevents the bug that units
        //: spawn out of area when to much units are into, or
        //: simple the pathing is off.
        private constant boolean CREATION_ZEROCOLLISION = true

        //: %Timers%
        private constant timer WAVE_TIMER = CreateTimer()
        private constant real WAVE_INT = 0.25
    endglobals

    //==========================================================================
    //: %DO NOT CHANGE THIS UNLIKE YOU KNOW WHAT YOU ARE DOING%
    //==========================================================================

    //: =================================
    //: Small Interface for Spawns
    //: =================================
    function interface onSpawn takes nothing returns nothing
    function interface onCheck takes nothing returns boolean
    function interface onUnitSpawn takes unit u returns nothing

    private function returnTrue takes nothing returns boolean
        return true
    endfunction

    struct SharedObjects
        onSpawn spawnCall = 0
        onCheck checkCall = 0
        boolean isSetSpawn = false
        boolean isSetCheck = false

        public method setOnSpawnCall takes onSpawn onS returns nothing
            set .spawnCall = onS
            set .isSetSpawn = true
        endmethod

        public method runOnSpawnCall takes nothing returns nothing
            if .isSetSpawn then
                call .spawnCall.execute()
            endif
        endmethod

        public method setOnSpawnCheck takes onCheck onC returns nothing
            set .checkCall = onC
            set .isSetCheck = true
        endmethod

        public method runOnSpawnCheck takes nothing returns boolean
            if .isSetCheck then
                return .checkCall.evaluate()
            endif
            return true
        endmethod
    endstruct
    //: =================================

    struct UnitSpawn extends SharedObjects
        integer ID = 0

        integer unitID = &#039;0000&#039;
        integer amount = 0

        string sfxPath = &quot;&quot;

        onUnitSpawn onUnitSpawnCall = 0

        public static method create takes integer unitId, integer amount, onUnitSpawn onUnitSp, string effPath returns UnitSpawn
            local thistype us = thistype.allocate()
                set us.unitID = unitId
                set us.amount = amount
                set us.onUnitSpawnCall = onUnitSp
                set us.sfxPath = effPath
            return us
        endmethod

        public method spawn takes player p, real posX, real posY returns nothing
            local integer i = 0
            local integer i2 = .amount
            local unit u = null

            if .runOnSpawnCheck() then
                call .runOnSpawnCall()

                loop
                    exitwhen i &gt;= i2

                    set u = CreateUnit(p, .unitID, posX, posY, 270)
                    if .sfxPath != &quot;&quot; then
                        call DestroyEffect(AddSpecialEffect(.sfxPath, GetUnitX(u), GetUnitY(u)))
                    endif

                    if CREATION_ZEROCOLLISION then
                        call SetUnitPathing(u, false)
                        call SetUnitX(u, posX)
                        call SetUnitY(u, posY)
                        call SetUnitPathing(u, true)
                    endif

                    if .onUnitSpawnCall != 0 then
                        call .onUnitSpawnCall.execute(u)
                    endif

                    set i = i + 1
                endloop
            endif

            set u = null
        endmethod
    endstruct

    struct GroupSpawn extends SharedObjects
        integer ID = 0
        real delay = 0

        real baseX = 0.
        real baseY = 0.

        UnitSpawn array unitSpawns[64]
        integer index = 0

        //: =================================
        //: CREATE NEW INSTANCES
        //: =================================
        public static method create takes real baseX, real baseY, real d returns thistype
            local thistype usg = thistype.allocate()
                set usg.baseX = baseX
                set usg.baseY = baseY
                set usg.delay = d
            return usg
        endmethod
        //: =================================

        //: =================================
        //: Add and remove UnitSpawns
        //: =================================
        public method addUnitSpawn takes UnitSpawn us returns nothing
            set us.ID = .index
            set .unitSpawns[.index] = us
            set .index = .index + 1
        endmethod

        public method removeUnitSpawn takes UnitSpawn us returns nothing
            set .unitSpawns[us.ID] = .unitSpawns[.index]
            set .index = .index - 1
        endmethod
        //: =================================

        //: =================================
        //: Spawn UnitSpawn-objects.
        //: =================================
        public method spawnUnits takes player p returns nothing
            local integer i = 0
            local UnitSpawn us = 0

            if .runOnSpawnCheck() then
                call .runOnSpawnCall()

                loop
                    exitwhen i &gt;= .index
                    set us = .unitSpawns<i>
                    call us.spawn(p, .baseX, .baseY)
                    set i = i + 1
                endloop
            endif
        endmethod
        //: =================================

        //: ====================================
        //: Desctrutor Method
        //: ====================================
        private method onDestroy takes nothing returns nothing
            local integer i = 0

            loop
                exitwhen i &gt;= .index

                call .unitSpawns<i>.destroy()

                set i = i + 1
            endloop
        endmethod
        //: ====================================
    endstruct


    struct Wave
        GroupSpawn array groupSpawns[64]
        integer groupIndex = 0

        player owner = null
        real interval = 0.

        integer ID = 0

        //: =================================
        //: CREATE NEW INSTANCES
        //: =================================
        public static method create takes real i, player own returns thistype
            local thistype usg = thistype.allocate()
                set usg.interval = i
                set usg.owner = own
            return usg
        endmethod
        //: =================================

        //: =================================
        //: Add and remove GroupSpawns
        //: =================================
        public method addGroupSpawn takes GroupSpawn gs returns nothing
            set gs.ID = .groupIndex
            set .groupSpawns[.groupIndex] = gs
            set .groupIndex = .groupIndex + 1
        endmethod

        public method removeGroupSpawn takes GroupSpawn gs returns nothing
            set .groupSpawns[gs.ID] = .groupSpawns[.groupIndex]
            set .groupIndex = .groupIndex - 1
        endmethod
        //: =================================

        public method spawnUnitGroup takes integer i returns nothing
            call .groupSpawns<i>.spawnUnits(.owner)
        endmethod

        //: ====================================
        //: Desctrutor Method
        //: ====================================
        private method onDestroy takes nothing returns nothing
            local integer i = 0

            loop
                exitwhen i &gt;= .groupIndex

                call .groupSpawns<i>.destroy()

                set i = i + 1
            endloop
        endmethod
        //: ====================================
    endstruct

    struct WaveStack
        static Wave array toSpawn[8191]
        static integer index = 0

        // %Data of the Waves%
        static real array waitTime[8191]
        static real array groupDelay[8191]
        static integer array curGroup[8191]
        static boolean array isPermanent[8191]
        static integer array spawnTimes[8191]

        //: =================================
        //: CHECK ALL WAYS AND ALL UNITS
        //: =================================
        public static method checkSpawn takes nothing returns nothing
            local integer i = 0
            local Wave w = 0

            loop
                exitwhen i &gt;= thistype.index
                set w = thistype.toSpawn<i>

                //: We don&#039;t have to wait so we
                //: can check what should happen after the wave has to
                //: be spammed.
                if thistype.waitTime<i> &lt;= 0. then
                    if thistype.groupDelay<i> &gt; 0. then
                       set thistype.groupDelay<i> = thistype.groupDelay<i> - WAVE_INT
                    endif

                    debug call BJDebugMsg(&quot;!AoSSpawnSys] |NOTICE| &lt;Wave[&quot; + I2S(i) + &quot;]&gt; &lt;CHECKING FOR SPAWNING!&gt;&quot;)
                    //: If the group has no delay we can call the spawn
                    if thistype.groupDelay<i> &lt;= 0. then
                        debug call BJDebugMsg(&quot;!AoSSpawnSys] |NOTICE| &lt;Wave[&quot; + I2S(i) + &quot;]&gt; &lt;SPAWN GROUP &quot; + I2S(thistype.curGroup<i>) + &quot;!&gt;&quot;)
                        call w.spawnUnitGroup(thistype.curGroup<i>)

                        if thistype.curGroup<i> &lt; w.groupIndex - 1 then
                            set thistype.curGroup<i> = thistype.curGroup<i> + 1
                        else
                            set thistype.curGroup<i> = 0
                            set thistype.waitTime<i> = w.interval
                            debug call BJDebugMsg(&quot;!AoSSpawnSys] |NOTICE| &lt;Wave[&quot; + I2S(i) + &quot;]&gt; &lt;RESET GROUPS!&gt;&quot;)
                        endif

                        set thistype.groupDelay<i> = w.groupSpawns[thistype.curGroup<i>].delay
                    endif

                    //: If we have no permanent wave reduce its amount.
                    //: If required delete the wave from the stack.
                    if not thistype.isPermanent<i> then
                        debug call BJDebugMsg(&quot;!AoSSpawnSys] |NOTICE| &lt;Wave[&quot; + I2S(i) + &quot;]&gt; &lt;DELETING THE WAVE!&gt;&quot;)
                        set thistype.spawnTimes<i> = thistype.spawnTimes<i> - 1
                        if thistype.spawnTimes<i> &lt;= 0 then
                            call thistype.removeWave(w)
                            set i = i - 1
                        endif
                    endif
                else
                    //: If we have to wait decrease time
                    set thistype.waitTime<i> = thistype.waitTime<i> - WAVE_INT
                endif

                set i = i + 1
            endloop
        endmethod
        //: =================================

        //: =================================
        //: Add and remove Waves
        //: =================================
        public static method addWave takes Wave w, integer times returns nothing
            local integer i = thistype.index

            set w.ID = i
            set thistype.toSpawn<i> = w

            // %Init Wave%
            set thistype.waitTime<i> = w.interval
            set thistype.curGroup<i> = 0
            set thistype.groupDelay<i> = w.groupSpawns[0].delay
            set thistype.spawnTimes<i> = times
            if times == 0 then
                set thistype.isPermanent<i> = true
            else
                set thistype.isPermanent<i> = false
            endif

            set thistype.index = thistype.index + 1
        endmethod

        public static method removeWave takes Wave w returns nothing
            local integer i = w.ID

            set thistype.toSpawn<i> = thistype.toSpawn[thistype.index]
            set thistype.curGroup<i> = thistype.curGroup[thistype.index]
            set thistype.groupDelay<i> = thistype.groupDelay[thistype.index]
            set thistype.isPermanent<i> = thistype.isPermanent[thistype.index]
            set thistype.spawnTimes<i> = thistype.spawnTimes[thistype.index]

            set thistype.index = thistype.index - 1
        endmethod
        //: =================================
    endstruct

    public function init takes nothing returns nothing
        call TimerStart(WAVE_TIMER, WAVE_INT, true, function WaveStack.checkSpawn)
    endfunction

endlibrary</i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i>


Example
JASS:

scope example initializer init

    globals
        private Wave array NIGHTELF_WAVES
        private unit array NIGHTELF_STRUCTURES[8191]

        private constant integer ID_LEFTWAVE = 0
        private constant integer ID_CENTERWAVE = 1
        private constant integer ID_RIGHTWAVE = 2
    endglobals

    public function nightelfGroupSpawnCheckLeft takes nothing returns boolean
        return GetUnitState(NIGHTELF_STRUCTURES[ID_LEFTWAVE], UNIT_STATE_LIFE) != 0.
    endfunction

    public function nightelfGroupSpawnCheckCenter takes nothing returns boolean
        return GetUnitState(NIGHTELF_STRUCTURES[ID_CENTERWAVE], UNIT_STATE_LIFE) != 0.
    endfunction

    public function nightelfGroupSpawnCheckRight takes nothing returns boolean
        return GetUnitState(NIGHTELF_STRUCTURES[ID_RIGHTWAVE], UNIT_STATE_LIFE) != 0.
    endfunction

    public function timedLife takes unit u returns nothing
        call UnitApplyTimedLife(u, &#039;0000&#039;, 25.)
    endfunction

    private function init takes nothing returns nothing
        local Wave w = 0
        local GroupSpawn gs = 0
        local UnitSpawn us = 0

        //:**********************************
        //: %LEFT WAVE
        //:**********************************

        //: Instanciate a new wave
        //: spawn every 30 seconds
        //: owner is Player 0. (red)
        set w = Wave.create(5, Player(0))

        //: Instanciate a new GroupSpawn
        //: based on Point(0., 0.)
        //: delay to last group: 0.00
        set gs = GroupSpawn.create(0., 0., 0.)

        //: Add a condition to the group spawn
        //: first parameter = condition
        //: func that returns boolean
        call gs.setOnSpawnCheck(nightelfGroupSpawnCheckLeft)

        //: Create a new unitspawn
        //: type: &#039;efon&#039; (ent)
        //: amount: 1
        //: function to call on construction: nothing = 0
        //: effect-path: &quot;Objects\\Spawnmodels\\NightElf\\EntBirthTarget\\EntBirthTarget.mdl&quot;
        set us = UnitSpawn.create(&#039;efon&#039;, 1, timedLife, &quot;Objects\\Spawnmodels\\NightElf\\EntBirthTarget\\EntBirthTarget.mdl&quot;)

        //: Add the unit spawn to the group
        call gs.addUnitSpawn(us)

        //: Add the groupspawn to the wave
        call w.addGroupSpawn(gs)

        //: Add the wave to the current spawn system
        //: 0 = endless spawning
        call WaveStack.addWave(w, 0)

        set NIGHTELF_WAVES[ID_LEFTWAVE] = w
        set NIGHTELF_STRUCTURES[ID_LEFTWAVE] = CreateUnit(Player(0), &#039;eaow&#039;, -64., -64., 270.)
        //:**********************************
    endfunction

endscope
 

Attachments

  • AMS v1.05.w3x
    28.4 KB · Views: 342
  • ASS v.1.05.w3x
    42.3 KB · Views: 345

Anachron

New Member
Reaction score
53
For what? I don't have that many functions and the example clearly shows all functions which can be used.
 

Anachron

New Member
Reaction score
53
if the example use all, so really don't need, sorry for that
'
Ok dude, here is what it does:
Automaticly reorders units after they make any other action as hold position and move.
(So spellcast, stop, etc)

You can make multiple units spawn for one group.
The to spawn units can have conditions which have to return true.
The spawn group can have conditions aswell.
The wave can be either period or limited.
You can get the nearest waypoint of an unit of a way.
...

This and the like can be made static if's?
Yeah could, when I did this I didn't know about static ifs at all.
 

Laiev

Hey Listen!!
Reaction score
188
You don't understand what i mean, look at the example <by Damage System from Jesus4Lyf>

function Damage_IsPhysical takes nothing returns boolean
function Damage_IsSpell takes nothing returns boolean
function Damage_IsPure takes nothing returns boolean
etc...
 

Anachron

New Member
Reaction score
53
Move System:
JASS:
//WayPoint:
public static method create takes real bX, real bY, real tX, real tY, real tR returns WayPoint
public method moveUnit takes unit u returns nothing

//Way:
public static method create takes nothing returns thistype
private static method addWay takes thistype wy returns nothing
private static method removeWay takes thistype wy returns nothing
public method addWayPoint takes WayPoint wp returns nothing
public method removeWayPoint takes WayPoint wp returns nothing
public method addUnit takes unit u, integer curPos returns nothing
public method removeUnit takes unit u returns nothing
public method moveUnit takes unit u, integer curPos returns nothing
public method moveNext takes unit u, integer curPos returns nothing
public method getNearestWP takes unit u returns integer


Spawn System:
JASS:
//UnitSpawn:
public static method create takes integer unitId, integer amount, onUnitSpawn onUnitSp, string effPath returns UnitSpawn
public method spawn takes player p, real posX, real posY returns nothing

//GroupSpawn:
public static method create takes real baseX, real baseY, real d returns thistype
public method addUnitSpawn takes UnitSpawn us returns nothing
public method removeUnitSpawn takes UnitSpawn us returns nothing
public method spawnUnits takes player p returns nothing

//Wave:
public static method create takes real i, player own returns thistype
public method addGroupSpawn takes GroupSpawn gs returns nothing
public method removeGroupSpawn takes GroupSpawn gs returns nothing
public method spawnUnitGroup takes integer i returns nothing

//WaveCheck
public static method checkSpawn takes nothing returns nothing
public static method addWave takes Wave w, integer times returns nothing
public static method removeWave takes Wave w returns nothing


Good enough?
 

Laiev

Hey Listen!!
Reaction score
188
Maybe a function to units with the collision off, like.. the spawn start with collision off, but then change to on, a boolean to stay collision off

[ljass]public static method create takes integer unitId, integer amount, onUnitSpawn onUnitSp, string effPath, boolean collision returns UnitSpawn[/ljass]
 

Anachron

New Member
Reaction score
53
I have that as a global value
JASS:
globals
        //: %Default Values%
        //: Check whether wanting to create units in each other
        //: on creation or not. This prevents the bug that units
        //: spawn out of area when to much units are into, or
        //: simple the pathing is off.
        private constant boolean CREATION_ZEROCOLLISION = true
 

Laiev

Hey Listen!!
Reaction score
188
I see it, but what i say is to creeps STAY with no collision, not just create part.. understand?
 

Anachron

New Member
Reaction score
53
I want creeps to be able to cast spells ?

EDIT: I mean't will this interfere?
They will be ordered again to attack / move to the waypoint after their spellcast is finally over.

I see it, but what i say is to creeps STAY with no collision, not just create part.. understand?
You can attach an method that does that. Its executed after spawning, when collision is removed.

JASS:
public method setOnSpawnCall takes onSpawn onS returns nothing
 

Laiev

Hey Listen!!
Reaction score
188
<Reviving>
How can i attach an unit to WY from US? (using both, spawn system and move system)
 

Anachron

New Member
Reaction score
53
Do you mean automatically?

JASS:
globals
     private Way wayOne = 0
endglobals

private function yourFunction takes unit u returns nothing
    call wayOne.addUnit(u, 0)
endfunction

private function createSpawnGroups takes nothing returns nothing
   local Wave w = 0
   local GroupSpawn gs = 0
   local UnitSpawn us = 0

   set w = Wave.create(5, Player(0))
   set gs = GroupSpawn.create(0., 0., 0.)

   set us = UnitSpawn.create(&#039;efon&#039;, 1, timedLife, &quot;Objects\\Spawnmodels\\NightElf\\EntBirthTarget\\EntBirthTarget.mdl&quot;)
   set us.onUnitSpawnCall = yourFunction
endfunction

Something like that, then the units are automatically added to the way. Did you understand that?
 

Laiev

Hey Listen!!
Reaction score
188
you point what i want.... but you don't notice a thing...

[ljass]set us.onUnitSpawnCall = yourFunction //<< takes unit?[/ljass]

[ljass]private function yourFunction takes unit u returns nothing[/ljass]

my problem is that.... i don't know how get the unit from spawnunit and attach it to the group of move
 
General chit-chat
Help Users
  • No one is chatting at the moment.
  • The Helper The Helper:
    The bots will show up as users online in the forum software but they do not show up in my stats tracking. I am sure there are bots in the stats but the way alot of the bots treat the site do not show up on the stats
  • Varine Varine:
    I want to build a filtration system for my 3d printer, and that shit is so much more complicated than I thought it would be
  • Varine Varine:
    Apparently ABS emits styrene particulates which can be like .2 micrometers, which idk if the VOC detectors I have can even catch that
  • Varine Varine:
    Anyway I need to get some of those sensors and two air pressure sensors installed before an after the filters, which I need to figure out how to calculate the necessary pressure for and I have yet to find anything that tells me how to actually do that, just the cfm ratings
  • Varine Varine:
    And then I have to set up an arduino board to read those sensors, which I also don't know very much about but I have a whole bunch of crash course things for that
  • Varine Varine:
    These sensors are also a lot more than I thought they would be. Like 5 to 10 each, idk why but I assumed they would be like 2 dollars
  • Varine Varine:
    Another issue I'm learning is that a lot of the air quality sensors don't work at very high ambient temperatures. I'm planning on heating this enclosure to like 60C or so, and that's the upper limit of their functionality
  • Varine Varine:
    Although I don't know if I need to actually actively heat it or just let the plate and hotend bring the ambient temp to whatever it will, but even then I need to figure out an exfiltration for hot air. I think I kind of know what to do but it's still fucking confusing
  • The Helper The Helper:
    Maybe you could find some of that information from AC tech - like how they detect freon and such
  • Varine Varine:
    That's mostly what I've been looking at
  • Varine Varine:
    I don't think I'm dealing with quite the same pressures though, at the very least its a significantly smaller system. For the time being I'm just going to put together a quick scrubby box though and hope it works good enough to not make my house toxic
  • Varine Varine:
    I mean I don't use this enough to pose any significant danger I don't think, but I would still rather not be throwing styrene all over the air
  • The Helper The Helper:
    New dessert added to recipes Southern Pecan Praline Cake https://www.thehelper.net/threads/recipe-southern-pecan-praline-cake.193555/
  • The Helper The Helper:
    Another bot invasion 493 members online most of them bots that do not show up on stats
  • Varine Varine:
    I'm looking at a solid 378 guests, but 3 members. Of which two are me and VSNES. The third is unlisted, which makes me think its a ghost.
    +1
  • The Helper The Helper:
    Some members choose invisibility mode
    +1
  • The Helper The Helper:
    I bitch about Xenforo sometimes but it really is full featured you just have to really know what you are doing to get the most out of it.
  • The Helper The Helper:
    It is just not easy to fix styles and customize but it definitely can be done
  • The Helper The Helper:
    I do know this - xenforo dropped the ball by not keeping the vbulletin reputation comments as a feature. The loss of the Reputation comments data when we switched to Xenforo really was the death knell for the site when it came to all the users that left. I know I missed it so much and I got way less interested in the site when that feature was gone and I run the site.
  • Blackveiled Blackveiled:
    People love rep, lol
    +1
  • The Helper The Helper:
    The recipe today is Sloppy Joe Casserole - one of my faves LOL https://www.thehelper.net/threads/sloppy-joe-casserole-with-manwich.193585/
  • The Helper The Helper:
    Decided to put up a healthier type recipe to mix it up - Honey Garlic Shrimp Stir-Fry https://www.thehelper.net/threads/recipe-honey-garlic-shrimp-stir-fry.193595/
  • The Helper The Helper:
    Here is another comfort food favorite - Million Dollar Casserole - https://www.thehelper.net/threads/recipe-million-dollar-casserole.193614/

      The Helper Discord

      Members online

      No members online now.

      Affiliates

      Hive Workshop NUON Dome World Editor Tutorials

      Network Sponsors

      Apex Steel Pipe - Buys and sells Steel Pipe.
      Top