- Joined
- Jul 10, 2007
- Messages
- 6,306
Bit Streams
---------------------------------------------
Officially tested to *8000* different timers on a 128 bit stream with 0 lag going in increments starting from 1 bit!
News Count: 2
News Data: 8-27-09 at 9:48pm PST
-News-
Build 1 of the new build is released.
What is going to be changed?
A way to attach data to timers =).
A way to split streams up from the main stream without a loss in speed.
Is this hella fast?
It depends... because everything runs on the main stream, the more variety in timers you have, the more laggy it gets because the main stream has to handle more. If you have 8000 of the fastest possible timer, it'd be faster than 8000 dif timers that are all like 100 seconds (fastest possible might run 32 times a second).
So how will this change?
I'm going to split the main stream into two stream types, these being fast and slow.
What will this do?
It will make timers that won't fire for awhile run only once every once and awhile instead of every time, so instead of every bit, it'll run every 32 bits or something : D.
Will this be faster?
Yes... it should be much faster when I think about it .
So, I split up the streams for the most epic optimization stuff ever!
Maximum Optimization To Smallest Bit Timer-
The smallest bit timer runs on the actual main stream timer making it as fast as a single standard timer o-o, 0 extras.
Small Timers have extra optimization-
With the introduction of the 2 stream types, those being the big stream and the small stream, the small timers that always run on the small stream have various elements that they don't do, meaning that they run faster =). These elements have to do with swapping between the big stream and the small stream. What does this mean? You can go smaller without the performance hit.
Big Timers have extra optimization-
Big timers run on a combo of the big and small streams. The big streams don't run as often (once a second). This means that the main stream doesn't have to process as much code making the entire thing run smoother. When a big timer has less than 1 second left (less, not less than or equal to), it swaps to the small stream, carries out the rest of its time, and then goes back to the big stream. You the user don't have to worry about anything.
Maintain Accuracy, Speed, and Performance on your smallest timers, your small timers, and your big timers =).
Does this run as fast and as well as KT2?
I really don't know. I guess someone will have to test it. My only advice is that the best way to stress test this is by creating "unique" timers. Creating a bundle of the same timer will not add anything to the main stream... you have to create as many smaller streams as possible ^_^. This also has a limit of 8191 unique streams and from there 8191 unique pieces of code. Why? It uses arrays : D.
What is next?
Data Attachment
Syncing to and Desyncing from streams
Getting a code's life
Setting a code's life
Forced release of a stream and regular release of a stream (clear it out and release it or release if empty)
Forced release of Code and regular release of code (release now or release on next run)
Further optimizations? =p
Demo-
Copy this somewhere into the map and hit test map to see a small demonstration of this system.
JASS:
scope Test initializer Initialization
globals
private integer stream
endglobals
private function HelloWorld takes nothing returns nothing
call DisplayTextToPlayer(GetLocalPlayer(), 0, 0, "Hello World!"))
call BS_ReleaseCode(stream)
endfunction
private function Initialization takes nothing returns nothing
set stream = BS_StreamCode(1.25, function HelloWorld)
endfunction
endscope
System-
JASS:
/*Utility Information
//===================================================================
Name: Bit Streams
Version: 3.4
Author: Nestharus
Settings:
*///===================================================================
//! textmacro BS_BIT_RATE
private constant integer BIT_RATE = 128
//! endtextmacro
//! textmacro BS_BIT_MAX
private constant real BIT_MAX = 1
//! endtextmacro
/*//===================================================================
Description:
Stream: [url]http://en.wikipedia.org/wiki/Stream_(computing[/url])
This runs on a single Stream (timer) that creates various sub streams. The timer
is split into 3 primary streams. When a sub steam on one of the primary streams is
ready to run, its trigger is fired and all the actions on it go off. The actions are
split into two parts. The first part is internal. It is very small and simply prepares
the data for the second part. It also lets the system know exactly what piece of code is
running. The second part is the user part.
The only task a main stream does is go through everything on its stream and increment
it by its interval. While it's doing this, it checks to see if anything has reached its
timeout period or if it needs to move to the opposite stream.
Primary Stream: The primary stream starts the 3 main streams, these being the small stream,
the big stream, and the cleanup stream. The primary stream also increasing the game
time interval and the current bit. A bit is like a clock and it tells the streams
exactly what bit they are on. The primary stream will only run main streams if they
have data on them.
Small Stream: The small stream runs on small interval timers. When a big interval
timer has less than a big stream interval left, it swaps to the small stream
to finish off and then swaps back to the big stream. The small stream interval
is that of the BIT_RATE. The BIT_RATE is how many times per second the small stream
runs. Things have an interval of less than one second stay on the small stream. Things
that have the same interval as the small stream get added to the actual small stream.
Big Stream: The big stream runs bigger intervals. The big stream usually runs once
every second, but this can vary depending on the bitrate. A bitrate of more than one
should have an interval of 1 second on the big stream. A bitrate of one should have an
interval of 2 on the big stream. An bitrate of less than one should have an interval
of BIT*BIT.
Cleanup Stream: This stream rummages through a cleanup array after everything else is
done running. This means that when code is released, it is not cleaned up immediately. If
it were cleaned up immediately, the stream that it would be running on would be fractured.
So, what makes this system better than other systems that do around the same thing?
More features and an easier to use interface
Dynamic optimizations (streams going from big to small to big, always small staying small
and always big staying big), streams only run when they have something in them, and well,
the cleanup of course. This can actually run 8000 different streams on my laptop with a 128
bitrate with 0 lag starting at 1 bit and ending at 8000 bits and it can run just about as
well as plain timers when running single streams. There are so many optimizations in this, all
of them dynamic, there is just too much to explain o-o.
There are 3 main types of data associated with a piece of code that is streamed in.
1.The first is the codeId, which is returned when it is sent in. Worried about having to keep track of it?
No problem, the codeId is accessible whenever the code runs.
2. The next is the data attached to the code, which is optional of course and can be changed at any time.
3. The final is the life of the code (how many times it should run). This life can of course be changed
and the current age of the code can always be retrieved.
So, do you have to do anything strange like with KT2? Do you need to say true here and false there and return
a boolean? Nope. You just run your everyday function in like you would a normal timer and BS does the rest. It
does use trigger conditions, so don't worry, it just converts the code you send into it into condition form.
Requirements: None
Installation: NA
Variables:
-BIT_RATE
How many times per second the stream runs. The bigger the bit rate,
the more accurate your timers can be. 128 is a good value and 64 is
safe.
-BIT_MAX
Suggest 1 for a bit rate of anything higher than one, BIT+BIT for
1, and BIT*BIT for anything lower than 1.
-Main Functions:
Functions:
------------------------------------------------------------------
-BS_StreamCode(interval, code) returns integer
Streamlines code and returns an id of the code
local integer myStreamedCode = BS_StreamCode(1, function Hello)
-BS_ReleaseCode(codeId) returns nothing
Will take code out of a stream
call BS_ReleaseCode(myStreamedCode)
-BS_GET_STREAM_TIME(codeId) returns real
Takes a code id value and returns the interval of the stream it is
running on.
local real timeout = BS_GET_STREAM_TIME(myStreamedCode)
-BS_GET_STREAM(codeId) returns integer
Takes a code id value and returns the stream id that it is running
on
local integer stream = BS_GET_STREAM(myStreamedCode)
-BS_GET_ELAPSED_GAME_TIME() returns real
Will return the current elapsed game time.
local real gameTime = GetElapsedGameTime()
-BS_GET_DATA() returns integer
Will return data for the current running code
-BS_UpdataData(data) returns nothing
Will set the data for the current running code
-BS_GET_CURRENT_CODE() returns integer
Will return the current running code
-BS_GET_CURRENT_STREAM() returns integer
Will return the current running stream
-BS_GET_CODE_AGE() returns integer
Will return how many times the code has run
-BS_GET_CODE_LIFE() returns itneger
Will return how many times the code can run before being released
-BS_SetCodeLife(codeId, life)
sets the life of the code
-BS_SetCurrentCodeLife(life)
sets the life of the current running code
-BS_StreamCodeData(interval, code, data) returns integer
Streamlines code and attaches data to it.
-BS_StreamCodeLife(interval, code, life) returns integer
Streamlines code and sets its life
-BS_StreamCodeCombo(interval, code, data, life) returns integer
Streamlines code and attaches data to it and sets its life
------------------------------------------------------------------*/
//===================================================================
library BS initializer Initialization
globals
//! runtextmacro BS_BIT_RATE()
private constant integer BIT_SIZE = BIT_RATE*BIT_RATE
private constant real BIT = 1./BIT_RATE
//! runtextmacro BS_BIT_MAX()
private real array bits
private integer array bitIds
private integer bitIdIndex = -1
private boolean array streamExists
private real array bitTable
private integer array streamCodeCount
private real gameSeconds = 0
private real currentBit = 0
private integer currentStream = 0
private integer currentRunningCode = 0
private trigger array streams
private triggercondition array codeStreams
private boolexpr array codes
private integer codeStreamsIndex = 0
private integer array codeStreamsQueu
private integer codeStreamsQueuIndex = 0
private integer array codeStreamId
private real array codeStream
private real array codeStreamProcess
private boolean array streamHasRun
private integer array smallStreamStack
private integer array smallStreamStackR
private integer array bigStreamStack
private integer array bigStreamStackR
private integer smallStreamStackIndex = 0
private integer bigStreamStackIndex = 0
private integer specialBigStreamStackIndex = 0
private real array bitFired
private integer array lastCode
private integer array nextCode
private integer array firstCode
private integer array currentCode
private integer array codeStack
private integer array codeStackQueu
private integer codeStackQueuIndex = 0
private integer array codePointToStack
private integer codeStackIndex = 0
private integer array codeStackLoop
private boolexpr setupCodeData
private boolexpr specialSetupCodeData
private boolexpr specialSetupCodeDataBig
private integer array codeData
private integer array toBeReleased
private integer toBeReleasedIndex = 0
private integer array codeAge
private integer array codeLife
private trigger cleanup = CreateTrigger()
private trigger stream = CreateTrigger()
private trigger bigStream = CreateTrigger()
private event streamEvent = TriggerRegisterTimerEvent(stream, BIT, true)
private boolexpr releaseCode
endglobals
private function AddStreamToBigStack takes integer id returns nothing
set bigStreamStackIndex = bigStreamStackIndex + 1
set bigStreamStack[bigStreamStackIndex] = id
set bigStreamStackR[id] = bigStreamStackIndex
endfunction
private function AddStreamToSmallStack takes integer id returns nothing
set smallStreamStackIndex = smallStreamStackIndex + 1
set smallStreamStack[smallStreamStackIndex] = id
set smallStreamStackR[id] = smallStreamStackIndex
endfunction
private function RemoveStreamFromBigStack takes integer id returns nothing
set bigStreamStack[bigStreamStackR[id]] = bigStreamStack[bigStreamStackIndex]
set bigStreamStackR[bigStreamStack[bigStreamStackIndex]] = bigStreamStackR[id]
set bigStreamStackR[id] = 0
set bigStreamStackIndex = bigStreamStackIndex - 1
endfunction
private function RemoveStreamFromSmallStack takes integer id returns nothing
set smallStreamStack[smallStreamStackR[id]] = smallStreamStack[smallStreamStackIndex]
set smallStreamStackR[smallStreamStack[smallStreamStackIndex]] = smallStreamStackR[id]
set smallStreamStackR[id] = 0
set smallStreamStackIndex = smallStreamStackIndex - 1
endfunction
private constant function BIG_STREAM takes real currentTime, real time returns boolean
return (time-currentTime >= 1)
endfunction
private constant function IN_BIG_STREAM_STACK takes integer id returns boolean
return (bigStreamStackR[id] > 0)
endfunction
private constant function IN_SMALL_STREAM_STACK takes integer id returns boolean
return (smallStreamStackR[id] > 0)
endfunction
private function AddStreamToStack takes integer id, real currentTime, real time returns nothing
if (time != currentTime) then
if BIG_STREAM(currentTime, time) then
if not IN_BIG_STREAM_STACK(id) then
if IN_SMALL_STREAM_STACK(id) then
call RemoveStreamFromSmallStack(id)
endif
call AddStreamToBigStack(id)
endif
elseif not IN_SMALL_STREAM_STACK(id) then
if IN_BIG_STREAM_STACK(id) then
call RemoveStreamFromBigStack(id)
endif
call AddStreamToSmallStack(id)
endif
endif
endfunction
private function RemoveStreamFromStack takes integer id, real currentTime, real time returns nothing
if BIG_STREAM(currentTime, time) then
if IN_BIG_STREAM_STACK(id) then
call RemoveStreamFromBigStack(id)
endif
elseif IN_SMALL_STREAM_STACK(id) then
call RemoveStreamFromSmallStack(id)
endif
endfunction
private function SetupStream takes integer id, real time returns nothing
set bitIdIndex = bitIdIndex + 1
set bitIds[bitIdIndex] = id
set bitTable[id] = time
set streamExists[id] = true
endfunction
private function CreateStream takes integer id, real time returns nothing
set streams[id] = CreateTrigger()
call SetupStream(id, time)
endfunction
private constant function GET_BIT_SIZE takes real time returns real
return time/BIT
endfunction
private function Time2Id takes real time returns integer
return R2I(GET_BIT_SIZE(time)-R2I(GET_BIT_SIZE(time)/8191)*8191)
endfunction
private function FindTime takes integer id, real time returns integer
loop
exitwhen bitTable[id] == time or bitTable[id] == 0
set id = id + 1
endloop
return id
endfunction
private function GetStreamId takes real time returns integer
local integer id = FindTime(Time2Id(time), time)
if not streamExists[id] then
call CreateStream(id, time)
endif
return id
endfunction
private function GetCodeId takes nothing returns integer
if codeStreamsQueuIndex == 0 then
set codeStreamsIndex = codeStreamsIndex + 1
return codeStreamsIndex
endif
set codeStreamsQueuIndex = codeStreamsQueuIndex - 1
return codeStreamsQueu[codeStreamsQueuIndex+1]
endfunction
private function StreamIntervalCode takes integer codeId, real time, boolexpr c returns triggercondition
local integer id = GetStreamId(time)
call AddStreamToStack(id, 0, time)
set codeStreamId[codeId] = id
set streamCodeCount[id] = streamCodeCount[id]+1
set codes[codeId] = And(setupCodeData, c)
return TriggerAddCondition(streams[id], codes[codeId])
endfunction
public constant function GET_STREAM_TIME takes integer codeId returns real
return codeStream[codeId]
endfunction
public constant function GET_STREAM takes integer codeId returns integer
return codeStreamId[codeId]
endfunction
private function ConvertTime takes real time returns real
local real convertedTime
local integer roundedTime
if time > BIT then
set convertedTime = time/BIT
set roundedTime = R2I(convertedTime)
return (R2I(convertedTime-roundedTime+BIT_MAX-.001)+roundedTime)*BIT
endif
return BIT
endfunction
private function GetCodeStream takes real time, boolexpr c, integer codeId returns triggercondition
if time == BIT then
set codeStreamId[codeId] = 1
set codes[codeId] = And(specialSetupCodeData, c)
return TriggerAddCondition(stream, codes[codeId])
elseif time == BIT_MAX then
set codeStreamId[codeId] = 2
set specialBigStreamStackIndex = specialBigStreamStackIndex + 1
set codes[codeId] = And(specialSetupCodeDataBig, c)
return TriggerAddCondition(bigStream, codes[codeId])
endif
return StreamIntervalCode(codeId, time, c)
endfunction
private constant function CHECK_NEXT_CODE takes integer id returns boolean
return (nextCode[codeStackLoop[id]] > 0)
endfunction
private function NextCode takes integer id returns integer
local integer result = codeStackLoop[id]
if CHECK_NEXT_CODE(id) then
set codeStackLoop[id] = nextCode[codeStackLoop[id]]
elseif not CHECK_NEXT_CODE(id) then
set codeStackLoop[id] = firstCode[id]
endif
return codeStack[result]
endfunction
private function AddToCodeStackQueu takes integer stack returns nothing
set codeStackQueuIndex = codeStackQueuIndex + 1
set codeStackQueu[codeStackQueuIndex] = stack
endfunction
private function RemoveCodeFromStack takes integer id, integer stack returns integer
local integer recycled = currentCode[id]
if stack < currentCode[id] then
set codeStack[stack] = codeStack[currentCode[id]]
set codePointToStack[codeStack[stack]] = stack
endif
set nextCode[lastCode[currentCode[id]]] = 0
set lastCode[currentCode[id]] = 0
set currentCode[id] = currentCode[id] - 1
return recycled
endfunction
private function RemoveCode takes integer id, integer codeId returns nothing
call AddToCodeStackQueu(RemoveCodeFromStack(id, codePointToStack[codeId]))
set codePointToStack[codeId] = 0
endfunction
private function CodeStackIndex takes integer id returns integer
if codeStackQueuIndex > 0 then
set codeStackQueuIndex = codeStackQueuIndex - 1
return codeStackQueu[codeStackQueuIndex+1]
endif
return 0
endfunction
private function GetCodeStackIndex takes integer id returns integer
local integer instancedIndex = CodeStackIndex(id)
if instancedIndex == 0 then
set codeStackIndex = codeStackIndex + 1
return codeStackIndex
endif
return instancedIndex
endfunction
private function NewCode takes integer id returns integer
local integer instancedIndex = GetCodeStackIndex(id)
set lastCode[instancedIndex] = nextCode[lastCode[currentCode[id]]]
set nextCode[lastCode[instancedIndex]] = instancedIndex
set currentCode[id] = instancedIndex
return instancedIndex
endfunction
private function StreamCodeList takes integer codeId, integer id returns nothing
local integer instancedIndex
if currentCode[id] > 0 then
set instancedIndex = NewCode(id)
else
set instancedIndex = GetCodeStackIndex(id)
set firstCode[id] = instancedIndex
set currentCode[id] = instancedIndex
set lastCode[currentCode[id]] = instancedIndex
set nextCode[currentCode[id]] = instancedIndex
set codeStackLoop[id] = firstCode[id]
endif
set codeStack[instancedIndex] = codeId
set codePointToStack[codeId] = instancedIndex
endfunction
public constant function GET_DATA takes nothing returns integer
return codeData[currentRunningCode]
endfunction
public constant function GET_CURRENT_CODE takes nothing returns integer
return currentRunningCode
endfunction
public constant function GET_CURRENT_STREAM takes nothing returns integer
return currentStream
endfunction
public function UpdateData takes integer data returns nothing
set codeData[currentRunningCode] = data
endfunction
public function ReleaseCode takes integer codeId returns nothing
set toBeReleasedIndex = toBeReleasedIndex + 1
set toBeReleased[toBeReleasedIndex] = codeId
endfunction
private function IncCodeAge takes integer currentRunningCode returns boolean
set codeAge[currentRunningCode] = codeAge[currentRunningCode] + 1
return (codeLife[currentRunningCode] > 0 and codeAge[currentRunningCode] >= codeLife[currentRunningCode])
endfunction
private function SetupCodeData takes nothing returns boolean
set currentRunningCode = NextCode(currentStream)
if IncCodeAge(currentRunningCode) then
call ReleaseCode(currentRunningCode)
endif
return true
endfunction
private function SpecialSetupCodeData takes nothing returns boolean
set currentStream = 1
call SetupCodeData()
return true
endfunction
private function SpecialSetupCodeDataBig takes nothing returns boolean
set currentStream = 2
call SetupCodeData()
return true
endfunction
public constant function GET_CODE_AGE takes nothing returns integer
return codeAge[currentRunningCode]
endfunction
public constant function GET_CODE_LIFE takes nothing returns integer
return codeLife[currentRunningCode]
endfunction
private function ReleaseCodeLife takes integer codeId, integer life returns boolean
if life < 0 then
set codeLife[codeId] = codeAge[codeId]
return true
endif
return false
endfunction
public function SetCodeLife takes integer codeId, integer life returns nothing
if not ReleaseCodeLife(codeId, life) then
set codeLife[codeId] = life
endif
endfunction
public function SetCurrentCodeLife takes integer life returns nothing
call SetCodeLife(currentRunningCode, life)
endfunction
public function CatchCode takes nothing returns boolean
local real time
local integer id
local integer codeId
loop
exitwhen toBeReleasedIndex == 0
set codeId = toBeReleased[toBeReleasedIndex]
set toBeReleasedIndex = toBeReleasedIndex - 1
set time = GET_STREAM_TIME(codeId)
if time >= BIT then
set id = GET_STREAM(codeId)
call RemoveCode(id, codeId)
if time == BIT then
call TriggerRemoveCondition(stream, codeStreams[codeId])
elseif time == BIT_MAX then
set specialBigStreamStackIndex = specialBigStreamStackIndex - 1
call TriggerRemoveCondition(bigStream, codeStreams[codeId])
else
call TriggerRemoveCondition(streams[id], codeStreams[codeId])
set streamCodeCount[id] = streamCodeCount[id] - 1
if streamCodeCount[id] == 0 then
set codeStackLoop[id] = firstCode[id]
call RemoveStreamFromStack(id, codeStreamProcess[id], bitTable[id])
endif
endif
call DestroyBoolExpr(codes[codeId])
set codeStreams[codeId] = null
set codes[codeId] = null
set codeStreamsQueuIndex = codeStreamsQueuIndex + 1
set codeStreamsQueu[codeStreamsQueuIndex] = codeId
endif
endloop
return true
endfunction
private function RunBigStream takes integer id returns nothing
if (codeStreamProcess[bigStreamStack[id]] == bitTable[bigStreamStack[id]]) then
set codeStreamProcess[bigStreamStack[id]] = 0
set currentStream = bigStreamStack[id]
set bitFired[bigStreamStack[id]] = currentBit
call TriggerEvaluate(streams[bigStreamStack[id]])
endif
endfunction
private function RunSmallStream takes integer id returns nothing
if (codeStreamProcess[smallStreamStack[id]] == bitTable[smallStreamStack[id]]) then
set codeStreamProcess[smallStreamStack[id]] = 0
set currentStream = smallStreamStack[id]
set bitFired[smallStreamStack[id]] = currentBit
call TriggerEvaluate(streams[smallStreamStack[id]])
endif
endfunction
private function IncBigStreamProcess takes integer id, real increase returns nothing
set codeStreamProcess[bigStreamStack[id]] = codeStreamProcess[bigStreamStack[id]] + increase
endfunction
private function IncSmallStreamProcess takes integer id returns nothing
set codeStreamProcess[smallStreamStack[id]] = codeStreamProcess[smallStreamStack[id]] + BIT
endfunction
private function StreamAddToSmallStack takes integer i returns nothing
call AddStreamToStack(smallStreamStack[i], codeStreamProcess[smallStreamStack[i]], bitTable[smallStreamStack[i]])
endfunction
private function StreamAddToBigStack takes integer i returns nothing
call AddStreamToStack(bigStreamStack[i], codeStreamProcess[bigStreamStack[i]], bitTable[bigStreamStack[i]])
endfunction
private function SmallStream takes nothing returns boolean
local integer i = 1
local integer end = smallStreamStackIndex
loop
exitwhen i > end
call IncSmallStreamProcess(i)
call RunSmallStream(i)
if bitTable[smallStreamStack[i]] >= BIT_MAX then
set streamHasRun[smallStreamStack[i]] = true
call StreamAddToSmallStack(i)
endif
set i = i + 1
endloop
return true
endfunction
private function BigStream takes nothing returns boolean
local integer i = 1
local integer end = bigStreamStackIndex
loop
exitwhen i > end
if not streamHasRun[bigStreamStack[i]] then
call IncBigStreamProcess(i, BIT_MAX)
call RunBigStream(i)
call StreamAddToBigStack(i)
elseif bitTable[bigStreamStack[i]] > 1 then
call IncBigStreamProcess(i, (BIT_MAX-bitFired[bigStreamStack[i]]))
call RunBigStream(i)
set streamHasRun[bigStreamStack[i]] = false
call StreamAddToBigStack(i)
else
set streamHasRun[bigStreamStack[i]] = false
endif
set i = i + 1
endloop
return true
endfunction
public constant function GET_ELAPSED_GAME_TIME takes nothing returns real
return currentBit + gameSeconds
endfunction
private constant function BIG_STREAM_CHECK takes nothing returns boolean
return (currentBit == BIT_MAX)
endfunction
private function Stream takes nothing returns boolean
if BIG_STREAM_CHECK() then
set gameSeconds = gameSeconds + BIT_MAX
endif
set currentBit = currentBit - R2I(currentBit) + BIT
if smallStreamStackIndex > 0 then
call SmallStream()
endif
if BIG_STREAM_CHECK() then
if bigStreamStackIndex > 0 or specialBigStreamStackIndex > 0 then
call TriggerEvaluate(bigStream)
endif
endif
if toBeReleasedIndex > 0 then
call TriggerEvaluate(cleanup)
endif
return true
endfunction
private function ClearCodeData takes integer codeId returns nothing
set codeData[codeId] = 0
set codeAge[codeId] = 0
set codeLife[codeId] = 0
endfunction
private function AddCodeToStream takes real time, code c returns integer
local integer codeId = GetCodeId()
set time = ConvertTime(time)
set codeStream[codeId] = time
set codeStreams[codeId] = GetCodeStream(time, Condition(c), codeId)
call StreamCodeList(codeId, codeStreamId[codeId])
return codeId
endfunction
public function StreamCode takes real time, code c returns integer
local integer codeId = AddCodeToStream(time, c)
call ClearCodeData(codeId)
return codeId
endfunction
public function StreamCodeData takes real time, code c, integer data returns integer
local integer codeId = StreamCode(time, c)
set codeData[codeId] = data
return codeId
endfunction
public function StreamCodeLife takes real time, code c, integer life returns integer
local integer codeId = StreamCode(time, c)
set codeLife[codeId] = life
return codeId
endfunction
public function StreamCodeCombo takes real time, code c, integer data, integer life returns integer
local integer codeId = StreamCode(time, c)
set codeData[codeId] = data
set codeLife[codeId] = life
return codeId
endfunction
private function Initialization takes nothing returns nothing
call TriggerAddCondition(bigStream, Condition(function BigStream))
call TriggerAddCondition(stream, Condition(function Stream))
set setupCodeData = Condition(function SetupCodeData)
set specialSetupCodeData = Condition(function SpecialSetupCodeData)
set specialSetupCodeDataBig = Condition(function SpecialSetupCodeDataBig)
call TriggerAddCondition(cleanup, Condition(function CatchCode))
set bitTable[1] = BIT
set bitTable[2] = BIT_MAX
endfunction
endlibrary
Last edited: