- Joined
- Jun 1, 2007
- Messages
- 98
Well, I'm making a simple system for use with a map I'm making.
My problem is that if I set a projectile to collide, it will never move. Here is my code so far:
Basically, when I set the 'collides' boolean in the projectile_glaive struct to false, it works fine but if i set it to true then movement stops and collision doesn't occur either. I get no errors with the collision code. Here it is (if you can't be bothered to look through all of that and find it) :
Example map included in the thread. Try changing the collides boolean and you'll see what I mean.
Edit:
Fixed. Forgot to do set g = CreateGroup()
My problem is that if I set a projectile to collide, it will never move. Here is my code so far:
JASS:
//========================PROJECTILE SYSTEM CORE=======================//
library PSCore
globals
private timer PSUpdate = CreateTimer()
private integer PSCount = 0
private projectile array PSArray
private integer PSDummy = 'e000'
constant real PSUpdateInterval = 0.04
private real MAX_X
private real MAX_Y
private real MIN_X
private real MIN_Y
private boolexpr filter
endglobals
private function PSFilter takes nothing returns boolean
return true
endfunction
private function PSMain takes nothing returns boolean
local projectile p
local integer i = 1
local real cX
local real cY
local unit u
local group g
loop
exitwhen i > PSCount
set p = PSArray[ i ]
if (p.x > MAX_X) or (p.y > MAX_Y) or (p.x < MIN_X) or (p.y < MIN_Y) then
call p.destroy()
return false
endif
if p.data.moves then // Movement
set p.x = p.x + p.data.speed * Cos( p.data.dir ) //Already dealing with radians not degrees.
set p.y = p.y + p.data.speed * Sin( p.data.dir )
call SetUnitPosition( p.dummy, p.x, p.y )
endif
if p.data.collides then //Collision
//Thanks to HINDYHat for this nice way of looping through a group.
call GroupEnumUnitsInRange( g, p.x, p.y, p.data.radius, filter )
call GroupRemoveUnit( g, p.dummy )
call GroupRemoveUnit( g, p.owner )
loop
set u = FirstOfGroup( g )
exitwhen u == null
call p.data.Collide( u )
call GroupRemoveUnit( g, u )
endloop
call DestroyGroup( g )
set g = null
set u = null
endif
call p.data.Think() //Thinking!
set i = i + 1
endloop
return true
endfunction
interface pdata
real radius = 0.0
real speed = 0.0
real dir = 0.0
real height = 0.0
string model = ""
boolean moves = false
boolean collides = false
boolean bounces = false
projectile parent
method Think takes nothing returns nothing defaults nothing
method Collide takes unit c returns nothing defaults nothing
method Start takes nothing returns nothing defaults nothing
method End takes nothing returns nothing defaults nothing
endinterface
struct projectile
pdata data
integer id
real x
real y
unit dummy
unit owner
effect ef
static method create takes pdata data, unit owner, real x, real y returns projectile
local projectile p = projectile.allocate()
set p.data = data
set p.owner = owner
set p.x = x
set p.y = y
set p.dummy = CreateUnit( GetOwningPlayer(owner), PSDummy, x, y, data.dir )
set p.ef = AddSpecialEffectTarget( data.model, p.dummy, "origin" )
call SetUnitFlyHeight( p.dummy, data.height, 1000 )
set PSCount = PSCount + 1
set p.id = PSCount
set PSArray[PSCount] = p
debug call BJDebugMsg( "Projectile created with model: " + data.model + "[" + I2S( PSCount ) + "]" )
//Timer stuff
if PSCount == 1 then
call TimerStart( PSUpdate, PSUpdateInterval, true, function PSMain )
endif
return p
endmethod
method onDestroy takes nothing returns nothing
local integer i = .id + 1
call DestroyEffect( .ef )
call RemoveUnit( .dummy )
set .dummy = null
set .ef = null
call .data.destroy()
//Updating the projectile stack.
loop
exitwhen i > PSCount
set PSArray[ i ].id = i - 1
set PSArray[ i-1 ] = PSArray[ i ]
set i = i + 1
endloop
set PSCount = PSCount - 1
if PSCount == 0 then
call PauseTimer( PSUpdate )
endif
endmethod
endstruct
function InitTrig_PSCore takes nothing returns nothing
set MAX_X = GetRectMaxX( bj_mapInitialPlayableArea ) - 10
set MAX_Y = GetRectMaxY( bj_mapInitialPlayableArea ) - 10
set MIN_X = GetRectMinX( bj_mapInitialPlayableArea ) + 10
set MIN_Y = GetRectMinY( bj_mapInitialPlayableArea ) + 10
set filter = Filter(function PSFilter)
endfunction
endlibrary
//=====================================================================//
JASS:
library PSTypes requires PSCore
struct projectile_glaive extends pdata
real radius = 64.0
real speed = 20.0
real height = 60.0
string model = "Abilities\\Weapons\\SentinelMissile\\SentinelMissile.mdl"
boolean moves = true
boolean collides = false
boolean bounces = true
static method create takes nothing returns projectile_glaive
return projectile_glaive.allocate()
endmethod
method Collide takes unit u returns nothing
debug call BJDebugMsg( "Glaive collided with unit." )
endmethod
endstruct
endlibrary
Basically, when I set the 'collides' boolean in the projectile_glaive struct to false, it works fine but if i set it to true then movement stops and collision doesn't occur either. I get no errors with the collision code. Here it is (if you can't be bothered to look through all of that and find it) :
JASS:
if p.data.collides then //Collision
//Thanks to HINDYHat for this nice way of looping through a group.
call GroupEnumUnitsInRange( g, p.x, p.y, p.data.radius, filter )
call GroupRemoveUnit( g, p.dummy )
call GroupRemoveUnit( g, p.owner )
loop
set u = FirstOfGroup( g )
exitwhen u == null
call p.data.Collide( u )
call GroupRemoveUnit( g, u )
endloop
call DestroyGroup( g )
set g = null
set u = null
endif
Example map included in the thread. Try changing the collides boolean and you'll see what I mean.
Edit:
Fixed. Forgot to do set g = CreateGroup()
Attachments
Last edited: