• 🏆 Texturing Contest #33 is OPEN! Contestants must re-texture a SD unit model found in-game (Warcraft 3 Classic), recreating the unit into a peaceful NPC version. 🔗Click here to enter!

Problem with importing xe

Status
Not open for further replies.
Level 2
Joined
Apr 29, 2013
Messages
21
Hello everyone,

I've a little problem. I want to make some missile spells for my Project, but when I want to import "xeefx", JassHelper tells me "librarys can't require scopes". I only figured out that this error doesn't occur when I delete the requirement "optional xedummy". But even then a new Error occurs: "function destroy redefined". I have the fitting JassHelper Version that is needed to import xe and I've also followed the instructions step by step.

Thanks in advance for help.
 
Last edited:
Level 2
Joined
Apr 29, 2013
Messages
21
Maybe I've wrote a bit bad. You seem to not understand what I mean^^
or I'm too stupid too understand you^^

I want to implement the system "xe" with wich you can make custom missiles or effect etc. But when I import this system xebasic compiles well, but xeefx won't compile correctly even when I follow the instructions step by step. So why it doesn't compile was my question. I'll post the code. I simply don't understand cuz there is no thread about such a problem that it don't work in my case.
JASS:
library xebasic
//**************************************************************************
//
// xebasic 0.4
// =======
// XE_DUMMY_UNITID : Rawcode of the dummy unit in your map. It should
//                   use the dummy.mdx model, so remember to import it as
//                   well, just use copy&paste to copy the dummy from the
//                   xe map to yours, then change the rawcode.
//
// XE_HEIGHT_ENABLER: Medivh's raven form ability, you may need to change
//                    this rawcode to another spell that morphs into a flier
//                    in case you modified medivh's spell in your map.
//
// XE_TREE_RECOGNITION: The ancients' Eat tree ability, same as with medivh
//                      raven form, you might have to change it.
//
// XE_ANIMATION_PERIOD: The global period of animation used by whatever
//                      timer that depends on it, if you put a low value
//                      the movement will look good but it may hurt your
//                      performance, if instead you use a high value it
//                      will not lag but will be fast.
//
// XE_MAX_COLLISION_SIZE: The maximum unit collision size in your map, if
//                        you got a unit bigger than 197.0 it would be
//                        a good idea to update this constant, since some
//                        enums will not find it. Likewise, if none of
//                        your units can go bellow X and X is much smaller
//                        than 197.0, it would be a good idea to update
//                        as well, since it will improve the performance
//                        those enums.
//
// Notice you probably don't have to update this library, unless I specify
// there are new constants which would be unlikely. 
//
//**************************************************************************

//===========================================================================
globals
   constant integer XE_DUMMY_UNITID       = 'e000'
   constant integer XE_HEIGHT_ENABLER     = 'Amrf'
   constant integer XE_TREE_RECOGNITION   = 'Aeat'
   constant real    XE_ANIMATION_PERIOD   =  0.025
   constant real    XE_MAX_COLLISION_SIZE =  197.0
endglobals

endlibrary

thats xebasic, however compiles well.

JASS:
library xedummy requires xebasic
//******************************************************************************
// xedummy 0.9
// ------
// For all your xe dummy recycling needs.
//
//******************************************************************************

//==============================================================================
    globals
        // The number of different angles at which the dummy units will be stored.
        private constant integer ANGLE_RESOLUTION = 12

        // The total number of xe dummy units that will be preloaded on map initialization.
        private constant integer INITIAL_DUMMY_COUNT  = 36
    
        // Don't allow to keep more than DUMMY_STACK_LIMIT inactive dummy units.
        private constant integer DUMMY_STACK_LIMIT    = 240
    endglobals

// END OF CALIBRATION SECTION
// ================================================================

    private keyword xedummy
    private struct recycleQueue extends array
        recycleQueue next
        recycleQueue prev

        real angle

        integer size
        xedummy first
        xedummy last
        static method onInit takes nothing returns nothing
            local integer i=0
            loop
                exitwhen i==ANGLE_RESOLUTION
                set i=i+1
                set recycleQueue(i).prev=recycleQueue(i-1)
                set recycleQueue(i).next=recycleQueue(i+1)
                set recycleQueue(i).angle=(i-0.5)*(360.0/ANGLE_RESOLUTION)
            endloop
            set recycleQueue(1).prev=recycleQueue(i)
            set recycleQueue(i).next=recycleQueue(1)
        endmethod

        static method get takes real angle returns recycleQueue
            return recycleQueue(R2I(angle/360.0*ANGLE_RESOLUTION)+1)
        endmethod
    endstruct

// ================================================================

    struct xedummy
        private static group g=CreateGroup()
        private unit u

        // ----------------------------------------------------------------

        private xedummy next
        
        private method queueInsert takes recycleQueue q returns nothing
            call SetUnitFacing(.u, q.angle)

            if q.size==0 then
                set q.first=this
            else
                set q.last.next=this
            endif
            set q.last=this
            set .next=0

            // Recursively check adajcent queues and migrate xedummies as needed.
            if q.size>q.next.size then
                set this=q.first
                set q.first=.next
                call .queueInsert(q.next)
            elseif q.size>q.prev.size then
                set this=q.first
                set q.first=.next
                call .queueInsert(q.prev)
            else
                set q.size=q.size+1
            endif
        endmethod
        
        private static method queueRemove takes recycleQueue q returns xedummy
            // Recursively check adajcent queues and migrate xedummies as needed.
            local xedummy this
            if q.size<q.next.size then
                set this=q.last
                set q.last=.queueRemove(q.next)
                set .next=q.last
                call SetUnitFacing(q.last.u, q.angle)
            elseif q.size<q.prev.size then
                set this=q.last
                set q.last=.queueRemove(q.prev)
                set .next=q.last
                call SetUnitFacing(q.last.u, q.angle)
            else
                set q.size=q.size-1
                if q.size==0 then
                    set q.last=0
                endif
            endif

            set this=q.first
            set q.first=.next
            set .next=0
            return this
        endmethod
    
        // ----------------------------------------------------------------

        private static method create takes unit u returns xedummy
            local xedummy this
            if GetUnitTypeId(u)!=XE_DUMMY_UNITID then
                debug call BJDebugMsg("ReleaseXEDummy error: Method called on a unit of an incorrect type.")
            elseif IsUnitInGroup(u, .g) then
                debug call BJDebugMsg("ReleaseXEDummy error: Method called on an already released unit.")
            else
                set this=.allocate()
                if integer(this)>DUMMY_STACK_LIMIT then
                    call RemoveUnit(u)
                    call .deallocate()
                    return 0
                endif
                set .u=u
                call GroupAddUnit(.g, u)
                call .queueInsert(recycleQueue.get(GetUnitFacing(u)))
                call SetUnitAnimationByIndex(u, 90)
                call SetUnitScale(u, 1, 0, 0)
                call SetUnitVertexColor(u, 255, 255, 255, 255)
                // call ShowUnit(u, false) // Do not hide the unit, it is rather costly and not needed.
                return this
            endif
            return 0
        endmethod

        private method destroy takes nothing returns nothing
            call GroupRemoveUnit(.g, .u)
            call ShowUnit(.u, true) // Show the unit in case it was hidden before being recycled.
            set .u=null
            call .deallocate()
        endmethod
        
        // ----------------------------------------------------------------

        private static unit dummy

        private static method onInit takes nothing returns nothing
            local integer i=INITIAL_DUMMY_COUNT
            local recycleQueue q=recycleQueue(1)
            if i>DUMMY_STACK_LIMIT then
                debug call BJDebugMsg("xedummy error: INITIAL_DUMMY_COUNT can not be larger than DUMMY_STACK_LIMIT.")
                set i=DUMMY_STACK_LIMIT
            endif
            loop
                exitwhen i==0
                set .dummy = CreateUnit(Player(15), XE_DUMMY_UNITID, 0.0,0.0,q.angle)
                call UnitAddAbility(.dummy,XE_HEIGHT_ENABLER)
                call UnitAddAbility(.dummy,'Aloc')
                call UnitRemoveAbility(.dummy,XE_HEIGHT_ENABLER)
                call .create(.dummy)
                set i=i-1
                set q=q.next
            endloop
        endmethod

        // ----------------------------------------------------------------

        static method new takes player p, real x, real y, real face returns unit
            local recycleQueue q
            local xedummy this
            loop
                exitwhen face>0.0
                set face=face+360.0
            endloop
            loop
                exitwhen face<360.0
                set face=face-360.0
            endloop
            set q=recycleQueue.get(face)
            if q.size==0 then
                set .dummy = CreateUnit(p, XE_DUMMY_UNITID, x,y,face)
                call UnitAddAbility(.dummy,XE_HEIGHT_ENABLER)
                call UnitAddAbility(.dummy,'Aloc')
                call UnitRemoveAbility(.dummy,XE_HEIGHT_ENABLER)
                call SetUnitX(.dummy, x)
                call SetUnitY(.dummy, y)
            else
                set this=.queueRemove(q)
                set .dummy=.u
                call .destroy()
                call SetUnitX(.dummy, x)
                call SetUnitY(.dummy, y)
                call SetUnitFacing(.dummy, face)
                call SetUnitOwner(.dummy, p, true)
            endif
            return .dummy
        endmethod

        static method release takes unit u returns nothing
            call .create(u)
        endmethod
    endstruct
    
// ================================================================

    function XE_NewDummyUnit takes player p, real x, real y, real face returns unit
        return xedummy.new( p,x,y,face )
    endfunction

    function XE_ReleaseDummyUnit takes unit u returns nothing
        call xedummy.release( u )
    endfunction

endlibrary

thats xedummy, optional required for xeefx

JASS:
library xefx initializer init requires xebasic, optional xedummy
//**************************************************
// xefx 0.9
// --------
//  Recommended: ARGB (adds ARGBrecolor method)
//  For your movable fx needs
//
//**************************************************

//==================================================
 globals
    private constant integer MAX_INSTANCES = 8190 //change accordingly.

    //Delay in order to show the death animation of the effect correctly when xefx is destroyed.
    //You may need to increase this if you are using effects with longer death animations.
    private constant real    MIN_RECYCLE_DELAY = 4.0

    //The delay does not need to be exact so we do cleanup in batches instead of individually.
    //This determines how often the recycler runs, should be less than MIN_RECYCLE_DELAY.
    private constant real    RECYCLE_INTERVAL = 0.5

    //if this is true and the xedummy library is present, units will be recycled instead of removed.
    private constant boolean RECYCLE_DUMMY_UNITS = true
    
    private timer    recycler
 endglobals

   private struct recyclebin
       unit u

       private recyclebin next=0
       private static recyclebin array list
       private static integer readindex=1
       private static integer writeindex=0
       private static integer count=0

       static method Recycle takes nothing returns nothing
            local recyclebin this = .list[readindex]
            loop
                exitwhen this==0
                static if RECYCLE_DUMMY_UNITS and LIBRARY_xedummy then
                    call XE_ReleaseDummyUnit(this.u)
                else
                    call RemoveUnit(this.u)
                endif
                set this.u=null
                set .count=.count-1
                call this.destroy()
                set this=this.next
            endloop
            set .list[readindex]=0
            set .writeindex=.readindex
            set .readindex=.readindex+1
            if .readindex>R2I(MIN_RECYCLE_DELAY/RECYCLE_INTERVAL+1.0) then
                set .readindex=0
            endif
            if count!=0 then
                call TimerStart(recycler, RECYCLE_INTERVAL, false, function recyclebin.Recycle)
            endif
       endmethod
       
       static method create takes unit u returns recyclebin
           local recyclebin this=recyclebin.allocate()
           if .count==0 then
                call TimerStart(recycler, RECYCLE_INTERVAL, false, function recyclebin.Recycle)
           endif
           set .count=.count+1
           set .u=u
           call SetUnitOwner(u,Player(15),false)
           set .next=.list[.writeindex]
           set .list[.writeindex]=this
           return this
       endmethod
   endstruct



   private function init takes nothing returns nothing
       set recycler=CreateTimer()
   endfunction

   struct xefx[MAX_INSTANCES]
       public integer tag=0
       private unit   dummy
       private effect fx=null
       private real   zang=0.0
       private integer r=255
       private integer g=255
       private integer b=255
       private integer a=255

       private integer abil=0

       static method create takes real x, real y, real facing returns xefx
        local xefx this=xefx.allocate()
           static if RECYCLE_DUMMY_UNITS and LIBRARY_xedummy then
               set this.dummy= XE_NewDummyUnit(Player(15), x,y, facing*bj_RADTODEG)
           else
               set this.dummy= CreateUnit(Player(15), XE_DUMMY_UNITID, x,y, facing*bj_RADTODEG)
               call UnitAddAbility(this.dummy,XE_HEIGHT_ENABLER)
               call UnitAddAbility(this.dummy,'Aloc')
               call UnitRemoveAbility(this.dummy,XE_HEIGHT_ENABLER)
               call SetUnitX(this.dummy,x)
               call SetUnitY(this.dummy,y)
           endif
        return this
       endmethod

       method operator owner takes nothing returns player
           return GetOwningPlayer(this.dummy)
       endmethod

       method operator owner= takes player p returns nothing
           call SetUnitOwner(this.dummy,p,false)
       endmethod

       method operator teamcolor= takes playercolor c returns nothing
           call SetUnitColor(this.dummy,c)
       endmethod

       method operator scale= takes real value returns nothing
           call SetUnitScale(this.dummy,value,value,value)
       endmethod

       //! textmacro XEFX_colorstuff takes colorname, colorvar
       method operator $colorname$ takes nothing returns integer
           return this.$colorvar$
       endmethod
       method operator $colorname$= takes integer value returns nothing
           set this.$colorvar$=value
           call SetUnitVertexColor(this.dummy,this.r,this.g,this.b,this.a)
       endmethod
       //! endtextmacro
       //! runtextmacro XEFX_colorstuff("red","r")
       //! runtextmacro XEFX_colorstuff("green","g")
       //! runtextmacro XEFX_colorstuff("blue","b")
       //! runtextmacro XEFX_colorstuff("alpha","a")

       method recolor takes integer r, integer g , integer b, integer a returns nothing
           set this.r=r
           set this.g=g
           set this.b=b
           set this.a=a
           call SetUnitVertexColor(this.dummy,this.r,this.g,this.b,this.a)
       endmethod

       implement optional ARGBrecolor

       method operator abilityid takes nothing returns integer
           return this.abil
       endmethod

       method operator abilityid= takes integer a returns nothing
           if(this.abil!=0) then
               call UnitRemoveAbility(this.dummy,this.abil)
           endif

           if(a!=0) then
               call UnitAddAbility(this.dummy,a)
           endif
           set this.abil=a
       endmethod
       
       method operator abilityLevel takes nothing returns integer
           return GetUnitAbilityLevel( this.dummy, this.abil)
       endmethod
       
       method operator abilityLevel= takes integer newLevel returns nothing
           call SetUnitAbilityLevel(this.dummy, this.abil, newLevel)
       endmethod

       method flash takes string fx returns nothing
           call DestroyEffect(AddSpecialEffectTarget(fx,this.dummy,"origin"))
       endmethod

       method operator xyangle takes nothing returns real
           return GetUnitFacing(this.dummy)*bj_DEGTORAD
       endmethod
       method operator xyangle= takes real value returns nothing
           call SetUnitFacing(this.dummy,value*bj_RADTODEG)
       endmethod

       method operator zangle takes nothing returns real
           return this.zang
       endmethod

       method operator zangle= takes real value returns nothing
        local integer i=R2I(value*bj_RADTODEG+90.5)
           set this.zang=value
           if(i>=180) then
               set i=179
           elseif(i<0) then
               set i=0
           endif
               
           call SetUnitAnimationByIndex(this.dummy, i  )
       endmethod


       method operator x takes nothing returns real
           return GetUnitX(this.dummy)
       endmethod
       method operator y takes nothing returns real
           return GetUnitY(this.dummy)
       endmethod
       method operator z takes nothing returns real
           return GetUnitFlyHeight(this.dummy)
       endmethod

       method operator z= takes real value returns nothing
           call SetUnitFlyHeight(this.dummy,value,0)
       endmethod

       method operator x= takes real value returns nothing
           call SetUnitX(this.dummy,value)
       endmethod

       method operator y= takes real value returns nothing
           call SetUnitY(this.dummy,value)
       endmethod

       method operator fxpath= takes string newpath returns nothing
           if (this.fx!=null) then
               call DestroyEffect(this.fx)
           endif
           if (newpath=="") then
               set this.fx=null
           else
               set this.fx=AddSpecialEffectTarget(newpath,this.dummy,"origin")
           endif

       endmethod
       
       method hiddenReset takes string newfxpath, real newfacing returns nothing
        local real x = GetUnitX(this.dummy)
        local real y = GetUnitY(this.dummy)
        local real z = this.z
        local real za = this.zangle
        local integer level = this.abilityLevel
           set .fxpath=null
           static if RECYCLE_DUMMY_UNITS and LIBRARY_xedummy then
               if(this.abil!=0) then
                   call UnitRemoveAbility(this.dummy,this.abil)
               endif
               call recyclebin.create(this.dummy)
               set this.dummy=XE_NewDummyUnit(Player(15), x,y, newfacing*bj_RADTODEG)
           else
               call RemoveUnit(this.dummy)
               set this.dummy= CreateUnit(Player(15), XE_DUMMY_UNITID, x,y, newfacing*bj_RADTODEG)
               call UnitAddAbility(this.dummy,XE_HEIGHT_ENABLER)
               call UnitAddAbility(this.dummy,'Aloc')
               call UnitRemoveAbility(this.dummy,XE_HEIGHT_ENABLER)
               call SetUnitX(this.dummy,x)
               call SetUnitY(this.dummy,y)
           endif
           set .fxpath=newfxpath
           if(level != 0) then
               call UnitAddAbility(this.dummy, this.abil) 
               call SetUnitAbilityLevel(this.dummy, this.abil, level)
           endif
           set this.z = z
           set zangle = za
       endmethod


       method destroy takes nothing returns nothing
           if(this.abil!=0) then
               call UnitRemoveAbility(this.dummy,this.abil)
           endif
           if(this.fx!=null) then
               call DestroyEffect(this.fx)
               set this.fx=null
           endif
           call recyclebin.create(this.dummy)
           set this.dummy=null
           call this.deallocate()
       endmethod

       method hiddenDestroy takes nothing returns nothing           
           call ShowUnit(dummy,false)
           call destroy()
       endmethod
       
   endstruct

endlibrary

and this one won't compile correctly.
 
Status
Not open for further replies.
Top