- Joined
- Apr 5, 2011
- Messages
- 245
Libraries:
- Curves
- Fly
FAQ
Q: WTF?
A: Every object's movement in 3-dimensional space can be represented as a composition of XY (surface) and Z (height) movement.
Most custom maps XY movement is nothing more than simple linear trajectory with constant movespeed. Jump is an obvious example, where specific Z coordinates form parabola. Same maps don't have flying units realistically interact with each other and require those parabolas just as visual.
Meanwhile our sense of continuity is about 0.025 sec, we are less sensitive to rate of trajectory, so smooth trajectory and right amount of points, connected linearly, look almost same for us. Thus, speed can be updated every 0.1 sec, or 0.2 sec, or even bigger, which depends on situation (the faster is movement the less must be frequency).
Relatively small amount of points, required to satisfy our senses, makes wise to use constant set of points for geometrically similar curves.
Curves library is meant to put normalized curves, which can be easily scaled then.
Example:
Normalized = {0, 0.75, 1, 0.75, 0} (parabola)
Scaled (x400) = {0, 300, 400, 300, 0} (parabola)
Movement algorithm is made so it uses rate of curve, to minimize input data, some inner calculations and opens door for composite Z movement from different sources (by summing up all rates).
Example:
Curve = {0, 0.75, 1, 0.75, 0}
Rate of curve = {0.75, 0.25, -0.25, -0.75}
Q: How can I do my curve?
A: Very easy:
-=- Library Curves -=-
-=- Library Fly -=-
Example of usage:
It makes unit fly for 2 seconds with 300 height at maximum
XY movement is done separately
Added:
Btw, if you see some memory leak, point me please
- Curves
- Fly
FAQ
Q: WTF?
A: Every object's movement in 3-dimensional space can be represented as a composition of XY (surface) and Z (height) movement.
Most custom maps XY movement is nothing more than simple linear trajectory with constant movespeed. Jump is an obvious example, where specific Z coordinates form parabola. Same maps don't have flying units realistically interact with each other and require those parabolas just as visual.
Meanwhile our sense of continuity is about 0.025 sec, we are less sensitive to rate of trajectory, so smooth trajectory and right amount of points, connected linearly, look almost same for us. Thus, speed can be updated every 0.1 sec, or 0.2 sec, or even bigger, which depends on situation (the faster is movement the less must be frequency).
Relatively small amount of points, required to satisfy our senses, makes wise to use constant set of points for geometrically similar curves.
Curves library is meant to put normalized curves, which can be easily scaled then.
Example:
Normalized = {0, 0.75, 1, 0.75, 0} (parabola)
Scaled (x400) = {0, 300, 400, 300, 0} (parabola)
Movement algorithm is made so it uses rate of curve, to minimize input data, some inner calculations and opens door for composite Z movement from different sources (by summing up all rates).
Example:
Curve = {0, 0.75, 1, 0.75, 0}
Rate of curve = {0.75, 0.25, -0.25, -0.75}
Q: How can I do my curve?
A: Very easy:
//-=-=-=- Settings -=-=-=-
//! textmacro CURVES
constant integer CURVE_TRAJECTORY_1 = 0 //Array address of curve data
constant integer CURVE_TRAJECTORY_2 = 5 //Array address of curve data
...
//! endtextmacro
//! textmacro CURVES_DATA
//CURVE_TRAJECTORY_1
set DATA[0] = 4 //Amount of points
set DATA[1] = .75
set DATA[2] = .25
set DATA[3] = -.25
set DATA[4] = -.75
//CURVE_TRAJECTORY_2
set DATA[5] = 6 //Amount of points
...
//! endtextmacro
//-=-=-=--=-=-=-=-=-=-=-=-
-=- Library Curves -=-
JASS:
//-=-=-=-=--=-=-=-=-=-=-=-
//-=-=-=-] Curves [-=-=-=-
//-=-=-=-=-=-=-=--=-=-=-=-
library Curves
//-=-=-=- Settings -=-=-=-
//! textmacro CURVES
constant integer CURVE_PARABOLA = 0
constant integer CURVE_PARABOLA5_RATE = 6
constant integer CURVE_PARABOLA7_RATE = 11
//! endtextmacro
//! textmacro CURVES_DATA
//CURVE_PARABOLA5
set DATA[0] = 5
set DATA[1] = 0
set DATA[2] = .75
set DATA[3] = 1
set DATA[4] = .75
set DATA[5] = 0
//CURVE_PARABOLA5_RATE
set DATA[6] = 4
set DATA[7] = .75
set DATA[8] = .25
set DATA[9] = -.25
set DATA[10] = -.75
//CURVE_PARABOLA7_RATE
set DATA[11] = 6
set DATA[12] = .6
set DATA[13] = .3
set DATA[14] = .1
set DATA[15] = -.1
set DATA[16] = -.3
set DATA[17] = -.6
//! endtextmacro
//-=-=-=--=-=-=-=-=-=-=-=-
globals
//! runtextmacro CURVES()
endglobals
struct CURVES extends array
readonly static real array DATA
private static method onInit takes nothing returns nothing
//! runtextmacro CURVES_DATA()
endmethod
endstruct
endlibrary
-=- Library Fly -=-
JASS:
//-=-=-=-=-=-=-=-=-=-=-
//-=-=-=-] Fly [-=-=-=-
//-=-=-=-=-=-=-=-=-=-=-
library Fly requires Curves, Support
globals
private integer I = 0
private unit array Unit
private timer array Timer
private integer array Curve
private real array Scale
private real array Speed
private integer array Node
private real array Height
endglobals
private function Refresh takes nothing returns nothing
set Support.workTimer = GetExpiredTimer()
set Support.workInteger = I
loop
if Support.workTimer == Timer[Support.workInteger] then
set Node[Support.workInteger] = Node[Support.workInteger] + 1
set Support.workReal = CURVES.DATA[Curve[Support.workInteger] + Node[Support.workInteger]]
set Height[Support.workInteger] = Height[Support.workInteger] + Scale[Support.workInteger] * Support.workReal
if Support.workReal < 0 then
set Support.workReal = -Speed[Support.workInteger] * Support.workReal
else
set Support.workReal = Speed[Support.workInteger] * Support.workReal
endif
call SetUnitFlyHeight(Unit[Support.workInteger], GetUnitDefaultFlyHeight(Unit[Support.workInteger]) + Height[Support.workInteger], Support.workReal)
if Node[Support.workInteger] == CURVES.DATA[Curve[Support.workInteger]] then
if Support.workInteger == I then
set Unit[Support.workInteger] = null
else
set Unit[Support.workInteger] = Unit[I]
set Timer[Support.workInteger] = Timer[I]
set Curve[Support.workInteger] = Curve[I]
set Scale[Support.workInteger] = Scale[I]
set Speed[Support.workInteger] = Speed[I]
set Node[Support.workInteger] = Node[I]
set Height[Support.workInteger] = Height[I]
set Unit[I] = null
set Timer[I] = Support.workTimer
endif
call PauseTimer(Support.workTimer)
set I = I - 1
endif
return
endif
set Support.workInteger = Support.workInteger - 1
endloop
endfunction
function UnitFly takes unit u, integer curve, real height, real time returns nothing
set I = I + 1
set Unit[I] = u
if Timer[I] == null then
set Timer[I] = CreateTimer()
endif
call TimerStart(Timer[I], time / CURVES.DATA[curve], true, function Refresh)
set Curve[I] = curve
set Scale[I] = height
set Speed[I] = height * CURVES.DATA[curve] / time
set Node[I] = 1
set Height[I] = height * CURVES.DATA[curve + 1]
call SetUnitFlyHeight(u, GetUnitDefaultFlyHeight(u) + Height[I], Speed[I] * CURVES.DATA[curve + 1])
endfunction
endlibrary
Example of usage:
JASS:
call UnitFly(GetTriggerUnit(), CURVE_PARABOLA7_RATE, 300, 2)
XY movement is done separately
Added:
Btw, if you see some memory leak, point me please
Last edited: