Warcraft 3 documentation
vJASS & Zinc Documentation
For the latest documentation about how it works vJASS and Zinc language layers for Warcraft III, please follow these links:
Jasshelper documentation - Zinc documentation - WC3 Optimizer documentation

Advanced Streak System v5.1.1.0 No New Posts Warcraft III Spells and Systems

Started by
Magtheridon96

0 Members and 1 Guest are viewing this topic.

Rating

Average Score - 5 / 5

« Created: June 08, 2017, 02:46:15 PM by moyack »

Advanced Streak System v5.1.1.0
on: June 25, 2013, 07:11:38 PM
Categories: System, vJASS
Rating: 5
Warcraft III Spell resource
« Created: February 02, 2018, 10:33:55 PM by moyack »

Related Topics or Resources



by

by

by

This is an advanced and dynamic streak system that supports:
- Killing Streaks
- Multikills
- Player Assists

You can have up to 8190 types of streaks.
You can add a whole new streak to the game anytime you want.

I'm not supporting AIDS or Damage for your own good...
Problem /bro/?

The code doesn't fit in here, so here's the documentation instead:
Now it can be posted totally :D ~moyack

Code: jass
  1. /*******************************************************************
  2. *       _   ___  ___
  3. *      /_\ / __|/ __|
  4. *     / _ \\__ \\__ \
  5. *    /_/ \_|___//___/
  6. *    v5.1.1.0
  7. *    By Magtheridon96
  8. *
  9. *    - This is an advanced player streak system.
  10. *       - Features:
  11. *           - Kill Streaks
  12. *           - Multikills
  13. *           - Assists
  14. *           - Combo-breaker
  15. *           - Streak/Multikill/Combo-breaker sounds
  16. *           - Texttags for Gold Gaining/Losing after each kill
  17. *           - Storage for total kills, deaths, assists, suicides,
  18. *             denies, streaks, multikills, streaks of any type,
  19. *             multikills of any type and combobreakers.
  20. *           - Events for everything except assists
  21. *           - Useful Event-responses
  22. *       - It is:
  23. *           - Dynamic
  24. *           - Easy to Use
  25. *           - Easy to Configure
  26. *           - Very Configurable
  27. *
  28. *       - It also supports a lot of systems.
  29. *         AutoIndex was not supported because the only damage detection
  30. *         systems that were written based on it were far too troublesome.
  31. *
  32. *   Requirements:
  33. *   -------------
  34. *
  35. *       - A Damage Detection System.
  36. *         Supports:
  37. *               - DamageEvent   By Nestharus        (hiveworkshop.com/forums/jass-resources-412/snippet-damageevent-186829/)
  38. *               - Damage        By Jesus4Lyf        (thehelper.net/forums/showthread.php/131287-Damage)
  39. *               - Damage        By Dirac            (thehelper.net/forums/showthread.php/168144-Damage-Struct)
  40. *
  41. *       - A Unit Indexer.
  42. *         Supports:
  43. *               - UnitIndexer   By Nestharus        (hiveworkshop.com/forums/jass-resources-412/system-unit-indexer-172090/)
  44. *               - AIDS          By Jesus4Lyf        (thehelper.net/forums/showthread.php/130752-Advanced-Indexing-Data-Storage)
  45. *
  46. *       - A Sound System.
  47. *         Supports:
  48. *               - SoundTools    By Magtheridon96    (hiveworkshop.com/forums/jass-resources-412/system-soundtools-207308/)
  49. *               - SoundUtils    By Rising_Dusk      (wc3c.net/showthread.php?t=107433)
  50. *
  51. *       - An Event Handler.
  52. *         Supports:
  53. *               - Event         By Nestharus        (hiveworkshop.com/forums/jass-resources-412/snippet-event-186555/)
  54. *               - Event         By Jesus4Lyf        (thehelper.net/forums/showthread.php/126846-Event)
  55. *
  56. *       - Table By Bribe
  57. *           - hiveworkshop.com/forums/jass-resources-412/snippet-new-table-188084/
  58. *
  59. *       - TimerUtils By Vexorian
  60. *           - wc3c.net/showthread.php?t=101322
  61. *
  62. *       Optional:
  63. *       ---------
  64. *
  65. *           - RegisterPlayerUnitEvent By Magtheridon96
  66. *               - hiveworkshop.com/forums/jass-resources-412/snippet-registerplayerunitevent-203338/
  67. *
  68. *   Configurable Functions:
  69. *   -----------------------
  70. *
  71. *       - function GetBounty           takes integer killerPlayerId, integer dyingPlayerId, unit killingUnit, unit dyingUnit                                                 returns integer
  72. *       - function GetLostGold         takes integer killerPlayerId, integer dyingPlayerId, unit killingUnit, unit dyingUnit, integer killingBounty                          returns integer
  73. *       - function GetAssistGold       takes integer killerPlayerId, integer dyingPlayerId, unit killingUnit, unit dyingUnit, integer killingBounty, integer numberAssisters returns integer
  74. *
  75. *       - function KillingPlayerFilter takes integer playerId                                                                                                                returns boolean
  76. *       - function AssistPlayerFilter  takes integer playerId                                                                                                                returns boolean
  77. *       - function DyingPlayerFilter   takes integer playerId                                                                                                                returns boolean
  78. *
  79. *       - function GetFirstbloodString takes string killingName                                                                                                              returns string
  80. *       - function GetKillString       takes string killingName, string dyingName, string bounty                                                                             returns string
  81. *       - function GetEndString        takes string killingName, string dyingName, string streak, string bounty                                                              returns string
  82. *
  83. *       - function GetSuicideString    takes integer killingPlayerId, string killingName                                                                                     returns string
  84. *       - function GetDenialString     takes integer killingPlayerId, string killingName, integer dyingPlayerId, string dyingName                                            returns string
  85. *
  86. *   How To Import:
  87. *   --------------
  88. *
  89. *       1- The first thing you need to do is import the required systems and set them up.
  90. *          This system supports DamageEvent by Nestharus, Damage by Jesus4Lyf and Damage
  91. *          by Dirac. In the Demo map, DamageEvent and all of the systems it uses including
  92. *          UnitIndexer are enabled. To import all the needed scripts, just copy and paste
  93. *          whatever is not disabled.
  94. *
  95. *          There are some systems that require more than just simple copying and pasting
  96. *          though. UnitIndexer requires you to import the Undefend-based ability and configure
  97. *          the ability Id in the globals of the code.
  98. *
  99. *       2- Now that all your systems are implemeted, you should configure this system.
  100. *          After this documentation, there is a globals block. You need to configure it
  101. *          based on the systems you implemented/are using.
  102. *
  103. *       3- Now, you need to configure the rest of the globals and functions to your liking.
  104. *
  105. *       4- Read the 'Setup' section of this documentation to understand how to configure
  106. *          and create streaks and multikills. You will need to define the streaks and
  107. *          multikills you want, else you will have fatal errors.
  108. *
  109. *       5- Test this system. If certain errors occur during initialization, the system
  110. *          will notify you and exit Warcraft III.
  111. *
  112. *   Setup:
  113. *   ------
  114. *
  115. *       - You will face fatal errors if you do not setup this system.
  116. *       - It is very important that you read these.
  117. *       
  118. *       Streaks:
  119. *       --------
  120. *
  121. *           - The first thing you need to do is set the minimum streak index:
  122. *
  123. *               call StreakSystem.setMinimumStreak(3)
  124. *
  125. *           - This means that 3 kills will give you the first streak.
  126. *           - Now, we need to start creating the streaks.
  127. *           - We will call the function newStreak like this:
  128. *
  129. *               call StreakSystem.newStreak("haxxor spree", "is on a haxxor spree", "war3mapImported\\HaxxingSpree.mp3", 2489)
  130. *
  131. *           - The first parameter is the name of this spree. This string will be
  132. *             used for the text that is displayed when a player ends a streak.
  133. *           - The second parameter is the string snippet that is displayed when
  134. *             a player achieves a certain streak. It is concatenated with the name
  135. *             of the player of course.
  136. *           - The third parameter is the filepath of the sound that is played
  137. *             when a player achieves a certain streak.
  138. *           - The fourth parameter is the duration of the sound in milliseconds.
  139. *
  140. *       Multikills:
  141. *       -----------
  142. *
  143. *           - With this setup, there is no catch. You would start calling newMultikill
  144. *             immediately.
  145. *
  146. *               call StreakSystem.newMultikill("got a Triple Kill!", "war3mapImported\\tripleKIll.wav", 1991)
  147. *
  148. *           - The first parameter is the string snippet that is displayed when
  149. *             a player achieves a certain multikill. It is concatenated with the
  150. *             name of the player of course.
  151. *           - The second parameter is the filepath of the sound that is played
  152. *             when a player achieves a certain streak.
  153. *           - The third parameter is the duration of the sound in milliseconds.
  154. *
  155. *       Firstblood:
  156. *       -----------
  157. *
  158. *           - The only thing that can be configured externally is the firstblood sound.
  159. *           - The firstblood string can be configured using the configurable function
  160. *             mentioned above: GetFirstbloodString
  161. *
  162. *               call StreakSystem.setFirstBloodSound("war3mapImported\\firstblood.wav", 1230)
  163. *
  164. *           - The first parameter is the filepath of the sound that is played
  165. *             when a player achieves firstblood.
  166. *           - The second parameter is the duration of the sound in milliseconds.
  167. *
  168. *       Combobreaker:
  169. *       -------------
  170. *
  171. *           - To configure the combo-breaker sound, we use the following function:
  172. *
  173. *               call StreakSystem.setComboBreakerSound("war3mapImported\\combobreaker.wav", 2102)
  174. *
  175. *           - The first parameter is the filepath of the sound that is played
  176. *             when a player breakes a combo.
  177. *           - The second parameter is the duration of the sound in milliseconds.
  178. *
  179. *   Event Responses:
  180. *   ----------------
  181. *
  182. *       - StreakSystem.getKillingUnitId()
  183. *       - StreakSystem.getKillingUnit()
  184. *       - StreakSystem.getDyingUnitId()
  185. *       - StreakSystem.getDyingUnit()
  186. *       - StreakSystem.getKillingPlayerId()
  187. *       - StreakSystem.getKillingPlayer()
  188. *       - StreakSystem.getDyingPlayerId()
  189. *       - StreakSystem.getDyingPlayer()
  190. *           - For: FIRSTBLOOD, STREAK, END_STREAK, MULTIKILL, COMBO_BREAKER, SUICIDE, DENIAL
  191. *           - These can be used inside END_MULTIKILL if DEATH_END_MULTI is set to true. They will only
  192. *             return valid data if a unit dies and loses a multikill.
  193. *           - Warning: Calling StreakSystem.getKillingPlayer() or StreakSystem.getDyingPlayer() inside
  194. *             a function registered to END_MULTIKILL will crash the game if the multikill simply faded.
  195. *             Use the Id counterparts instead.
  196. *
  197. *       - StreakSystem.getEndedMultikill()
  198. *       - StreakSystem.getMultikillLoserId()
  199. *       - StreakSystem.getMultikillLoser()
  200. *           - For: END_MULTIKILL
  201. *
  202. *       - StreakSystem.getAchievedStreak()
  203. *           - For: STREAK
  204. *       - StreakSystem.getEndedStreak()
  205. *           - For: END_STREAK
  206. *       - StreakSystem.getAchievedMultikill()
  207. *           - For: MULTIKILL
  208. *       - StreakSystem.getComboBroken()
  209. *           - For: COMBO_BREAKER
  210. *
  211. *   API:
  212. *   ----
  213. *
  214. *       - struct StreakSystem extends array
  215. *
  216. *           - static boolean enabled
  217. *               - Tells whether the system is enabled or not.
  218. *           - static boolean firstblood
  219. *               - Tells whether firstblood was taken or not.
  220. *
  221. *           - static Event FIRSTBLOOD
  222. *               - This event fires when a hero takes firstblood
  223. *           - static Event STREAK
  224. *               - This event fires when a hero is on a streak
  225. *           - static Event MULTIKILL
  226. *               - This event fires when a hero gets a multikill
  227. *           - static Event END_STREAK
  228. *               - This event fires when a streak is ended
  229. *           - static Event END_MULTIKILL
  230. *               - This event fires when a multikill is no longer valid
  231. *           - static Event COMBO_BREAKER
  232. *               - This event fires when a hero gets a combo-breaker
  233. *           - static Event SUICIDE
  234. *               - This event fires when a hero kills himself
  235. *           - static Event DENIAL
  236. *               - This event fires when a hero kills his own ally
  237. *
  238. *           - static method newStreak takes string streakName, string streakDisplay, string soundPath, integer duration returns nothing
  239. *           - static method newMultikill takes string text, string soundPath, integer duration returns nothing
  240. *               - These two functions create a streak-type and a multikill-type. The duration is in milliseconds.
  241. *               - Since it is not very clear what the arguments should be, here is an example:
  242. *                   - call StreakSystem.newStreak("killing spree", "is on a killing spree!", "war3mapImported\\KillingSpree.mp3", 2489)
  243. *                   - call StreakSystem.newMultikill("is on a Rampage!!!", "war3mapImported\\Rampage.wav", 1991)
  244. *               - As you can see, the function newStreak takes the name of the streak, then the form of the
  245. *                 streak message, then the path of the streak sound and finally, the duration of the streak
  246. *                 sound in milliseconds. The newMultikill function takes the form of the multikill message,
  247. *                 then the path of the multikill sound and finally, the duration of that sound in milliseconds.
  248. *
  249. *           - static method setFirstBloodSound takes string path, integer duration returns nothing
  250. *           - static method setComboBreakerSound takes string path, integer duration returns nothing
  251. *               - These two functions are used to configure the sounds that are played when a player gets
  252. *                 firstblood/a combo-breaker.
  253. *
  254. *           - static method setMinimumStreak takes integer i returns nothing
  255. *               - This sets the minimum streak value.
  256. *
  257. *           - static method setColor takes integer playerId, string color returns nothing
  258. *               - This function reconfigures the player color used in the system.
  259. *                 Player colors are already configured by default, but you may
  260. *                 need this just in case player colors change in-game.
  261. *
  262. *           - static method getKillingUnitId takes nothing returns UnitIndex
  263. *           - static method getKillingUnit takes nothing returns unit
  264. *           - static method getDyingUnitId takes nothing returns UnitIndex
  265. *           - static method getDyingUnit takes nothing returns unit
  266. *           - static method getKillingPlayerId takes nothing returns integer
  267. *           - static method getKillingPlayer takes nothing returns player
  268. *           - static method getDyingPlayerId takes nothing returns integer
  269. *           - static method getDyingPlayer takes nothing returns player
  270. *               - These functions retrieve the killing players and units and the
  271. *                 dying units and players for event responses.
  272. *
  273. *           - static method getAchievedStreak takes nothing returns integer
  274. *           - static method getEndedStreak takes nothing returns integer
  275. *           - static method getAchievedMultikill takes nothing returns integer
  276. *           - static method getEndedMultikill takes nothing returns integer
  277. *           - static method getMultikillLoserId takes nothing returns integer
  278. *           - static method getMultikillLoser takes nothing returns player
  279. *           - static method getComboBroken takes nothing returns integer
  280. *               - These functions retrieve the streak and multikill data for
  281. *                 for event responses.
  282. *           
  283. *           - static method getKills takes player whichPlayer returns integer
  284. *           - static method getDeaths takes player whichPlayer returns integer
  285. *           - static method getDenies takes player whichPlayer returns integer
  286. *           - static method getSuicides takes player whichPlayer returns integer
  287. *           - static method getAssists takes player whichPlayer returns integer
  288. *           - static method getStreaks takes player whichPlayer returns integer
  289. *           - static method getMultikills takes player whichPlayer returns integer
  290. *           - static method getCombobreakers takes player whichPlayer returns integer
  291. *           - static method getMultikillsOfType takes player whichPlayer returns integer
  292. *           - static method getStreaksOfType takes player whichPlayer returns integer
  293. *               - These functions are used to get the total stats of a player.
  294. *
  295. *           - static method getKillsById takes integer playerId returns integer
  296. *           - static method getDeathsById takes integer playerId returns integer
  297. *           - static method getDeniesById takes integer playerId returns integer
  298. *           - static method getSuicidesById takes integer playerId returns integer
  299. *           - static method getAssistsById takes integer playerId returns integer
  300. *           - static method getStreaksById takes integer playerId returns integer
  301. *           - static method getMultikillsById takes integer playerId returns integer
  302. *           - static method getCombobreakersById takes integer playerId returns integer
  303. *           - static method getMultikillsOfTypeById takes integer playerId returns integer
  304. *           - static method getStreaksOfTypeById takes integer playerId returns integer
  305. *               - These functions are used to get the total stats of a player given his Id.
  306. *
  307. *           - static method getCurrentStreak takes player p returns integer
  308. *           - static method getCurrentMultikill takes player p returns integer
  309. *               - These functions are used to get the current streak of a player
  310. *                 or his current multikills.
  311. *
  312. *           - static method getCurrentStreakById takes integer playerId returns integer
  313. *           - static method getCurrentMultikillById takes integer playerId returns integer
  314. *               - These functions are used to get the current streak of a player
  315. *                 or his current multikills given his Id.
  316. *
  317. *           - static method resetStreak takes integer playerId returns nothing
  318. *           - static method resetStreaks takes nothing returns nothing
  319. *               - These functions are used to either reset the streak of one or all players.
  320. *
  321. *           - static method resetAssist takes integer unitId returns nothing
  322. *           - static method resetAssists takes nothing returns nothing
  323. *               - These functions are used to either reset the streak associated with one or all units.
  324. *
  325. *           - static method operator goldGain takes nothing returns boolean
  326. *           - static method operator goldGain= takes boolean b returns nothing
  327. *           - static method operator goldLoss takes nothing returns boolean
  328. *           - static method operator goldLoss= takes boolean b returns nothing
  329. *               - Management of KillingPlayer-Goldgain and DyingPlayer-Goldloss.
  330. *
  331. *           - static method operator bountyBase takes nothing returns integer
  332. *           - static method operator bountyBase= takes integer i returns nothing
  333. *           - static method operator bountyIncrement takes nothing returns integer
  334. *           - static method operator bountyIncrement= takes integer i returns nothing
  335. *               - Management of Bounty Formula.
  336. *
  337. *******************************************************************/
  338. library ASS requires optional DamageEvent, optional Damage, optional UnitIndexer, optional AIDS, optional SoundTools, optional SoundUtils, Table, optional RegisterPlayerUnitEvent, TimerUtils, Event
  339.  
  340.     /*
  341.     *   Configuration
  342.     */
  343.     globals
  344.         /*
  345.         *   Whether you have Event by Nestharus or Jesus4Lyf is unknown to me.
  346.         *   Hence, I put up this boolean for configuration. If you are using
  347.         *   Damage and thus AIDS and Event by Jesus4Lyf, then set this to false.
  348.         */
  349.         private constant boolean EVENT_BY_NESTHARUS = true
  350.         /*
  351.         *   Whether you have Damage by Jesus4Lyf or Dirac is unknown to me.
  352.         *   Hence, I put up this boolean for configuration.
  353.         */
  354.         private constant boolean DAMAGE_BY_JESUS4LYF = false
  355.     endglobals
  356.    
  357.     /*
  358.     *   System Configuration
  359.     */
  360.     globals
  361.         // Max interval between Multikills (seconds)
  362.         private constant    real            MULTI_TIME              = 10
  363.         // Multikill Update Interval (seconds)
  364.         private constant    real            MULTI_UPDATE            = 1
  365.         // Are sounds 3D?
  366.         private constant    boolean         S3D                     = false
  367.         // Firstblood bonus
  368.         private constant    integer         FIRST_GOLD              = 200
  369.         // Duration of the text messages
  370.         private constant    real            TEXT_DURATION           = 8.00
  371.         // Interval between streak and multikill sounds
  372.         private constant    real            INTERVAL                = 0.50
  373.         // Assist Decay time (seconds)
  374.         private constant    real            ASSIST_DECAY            = 45
  375.         // Assist Update Interval (seconds)
  376.         private constant    real            ASSIST_UPDATE           = 1
  377.         // Can the heroes of leavers get streaks?
  378.         private constant    boolean         LEAVER_HEROES           = true
  379.         // Leavers can assist?
  380.         private constant    boolean         LEAVER_CAN_ASSIST       = true
  381.         // Initial Gold base
  382.         private             integer         baseGold                = 210
  383.         // Gold increment according to formulas
  384.         private             integer         goldIncrement           = 10
  385.         // Do you lose gold when you die?
  386.         private             boolean         loseGold                = true
  387.         // Do you gain gold when you kill?
  388.         private             boolean         gainGold                = true
  389.         // Do you want floating texts?
  390.         private constant    boolean         TEXTTAGS                = true
  391.         // Texttag configuration: Age
  392.         private constant    real            TEXTTAG_AGE             = 2.
  393.         // Texttag configuration: Fade-point
  394.         private constant    real            TEXTTAG_FADE            = 1.5
  395.         // Texttag configuration: Size
  396.         private constant    real            TEXTTAG_SIZE            = 0.024
  397.         // Texttag configuration: Velocity X
  398.         private constant    real            TEXTTAG_X               = 0.
  399.         // Texttag configuration: Velocity Y
  400.         private constant    real            TEXTTAG_Y               = 0.0355
  401.         // Give gold to assisters?
  402.         private constant    boolean         ASSIST_GOLD             = true
  403.         // Does Suicide end a streak?
  404.         private constant    boolean         SUICIDE_ENDS            = true
  405.         // When you deny a hero, do you get a kill?
  406.         private constant    boolean         DENIES_COUNT_KILLS      = false
  407.         // When you get denied, do you get a death?
  408.         private constant    boolean         DENIES_COUNT_DEATHS     = false
  409.         // Does suicide count as a death?
  410.         private constant    boolean         SUICIDE_DEATH           = true
  411.         // Does a Death end a multikill?
  412.         private constant    boolean         DEATH_END_MULTI         = false
  413.         // Do you want to have the Combo-breaker message and sound feature?
  414.         private constant    boolean         COMBO_BREAKER           = true
  415.         // Minimum Streak to end to get a Combo-breaker
  416.         private constant    integer         COMBO_BREAKER_MIN       = 3
  417.         // Should the suicide event fire before the end streak event? Or after?
  418.         // This is only important if SUICIDE_ENDS is set to true.
  419.         private constant    boolean         SUICIDE_FIRE_FIRST      = true
  420.     endglobals
  421.    
  422.     private keyword Streak
  423.     private keyword Multikill
  424.    
  425.     private function GetBounty takes integer killingId, integer dyingId, unit killingUnit, unit dyingUnit returns integer
  426.         return baseGold + goldIncrement * Streak[dyingId] + goldIncrement * Streak[killingId]
  427.     endfunction
  428.    
  429.     private function GetLostGold takes integer killingId, integer dyingId, unit killingUnit, unit dyingUnit, integer gold returns integer
  430.         return gold / 3
  431.     endfunction
  432.    
  433.     private function GetAssistGold takes integer killingId, integer dyingId, unit killingUnit, unit dyingUnit, integer gold, integer numberAssisters returns integer
  434.         return gold / numberAssisters
  435.     endfunction
  436.    
  437.     private function KillingPlayerFilter takes integer playerId returns boolean
  438.         return playerId < 12
  439.     endfunction
  440.    
  441.     private function AssistPlayerFilter takes integer playerId returns boolean
  442.         return playerId < 12
  443.     endfunction
  444.    
  445.     private function DyingPlayerFilter takes integer playerId returns boolean
  446.         return playerId < 12
  447.     endfunction
  448.    
  449.     private function StreakPlayerFilter takes integer playerId returns boolean
  450.         return playerId < 12
  451.     endfunction
  452.    
  453.     private function MultikillPlayerFilter takes integer playerId returns boolean
  454.         return playerId < 12
  455.     endfunction
  456.    
  457.     private function CombobreakerPlayerFilter takes integer playerId returns boolean
  458.         return playerId < 12
  459.     endfunction
  460.    
  461.     private function GetFirstbloodString takes string killingName returns string
  462.         return killingName + " just drew |cffff0000firstblood|r!"
  463.     endfunction
  464.    
  465.     private function GetKillString takes string killingName, string dyingName, string bounty returns string
  466.         return killingName + " pwned " + dyingName + "'s head for |cffffcc00" + bounty + "|r gold."
  467.     endfunction
  468.    
  469.     private function GetEndString takes string killingName, string dyingName, string streak, string bounty returns string
  470.         return dyingName + streak + " streak has been ended by " + killingName + " for |cffffcc00" + bounty + "|r gold."
  471.     endfunction
  472.    
  473.     private function GetSuicideString takes string dyingName returns string
  474.         return dyingName + "|r has killed himself!"
  475.     endfunction
  476.    
  477.     private function GetDenialString takes string killingName, string dyingName returns string
  478.         return killingName + "|r has denied his ally " + dyingName + "|r!"
  479.     endfunction
  480.    
  481.     private module Init
  482.         private static method onInit takes nothing returns nothing
  483.             /*
  484.             *   Player color strings configuration.
  485.             */
  486.             set thistype.colors[0]  = "|cffff0303"
  487.             set thistype.colors[1]  = "|cff0042ff"
  488.             set thistype.colors[2]  = "|cff1ce6b9"
  489.             set thistype.colors[3]  = "|cff540081"
  490.             set thistype.colors[4]  = "|cfffffc01"
  491.             set thistype.colors[5]  = "|cfffeba0e"
  492.             set thistype.colors[6]  = "|cff20c000"
  493.             set thistype.colors[7]  = "|cffe55bb0"
  494.             set thistype.colors[8]  = "|cff959697"
  495.             set thistype.colors[9]  = "|cff7ebff1"
  496.             set thistype.colors[10] = "|cff106246"
  497.             set thistype.colors[11] = "|cff4e2a04"
  498.         endmethod
  499.     endmodule
  500.    
  501.     /*
  502.     *   Configuration Ends Here
  503.     */
  504.    
  505.     private struct PlayerActive extends array
  506.         private static boolean array playerOff
  507.         static method operator [] takes integer i returns boolean
  508.             return not playerOff[i]
  509.         endmethod
  510.         private static method run takes nothing returns boolean
  511.             set playerOff[GetPlayerId(GetTriggerPlayer())] = true
  512.             return false
  513.         endmethod
  514.         private static method onInit takes nothing returns nothing
  515.             local trigger t = CreateTrigger()
  516.             local integer i = 15
  517.             loop
  518.                 call TriggerRegisterPlayerEvent(t, Player(i), EVENT_PLAYER_LEAVE)
  519.                 exitwhen i == 0
  520.                 set i = i - 1
  521.             endloop
  522.             call TriggerAddCondition(t, Condition(function thistype.run))
  523.             set t = null
  524.         endmethod
  525.     endstruct
  526.    
  527.     private module InitEventHandler
  528.         private static method onInit takes nothing returns nothing
  529.             set FIRSTBLOOD = Event.create()
  530.             set STREAK = Event.create()
  531.             set MULTIKILL = Event.create()
  532.             set END_STREAK = Event.create()
  533.             set END_MULTIKILL = Event.create()
  534.             set COMBO_BREAKER = Event.create()
  535.             set SUICIDE = Event.create()
  536.             set DENIAL = Event.create()
  537.         endmethod
  538.     endmodule
  539.    
  540.     private struct EventHandler extends array
  541.         readonly static Event FIRSTBLOOD
  542.         readonly static Event STREAK
  543.         readonly static Event MULTIKILL
  544.         readonly static Event END_STREAK
  545.         readonly static Event END_MULTIKILL
  546.         readonly static Event COMBO_BREAKER
  547.         readonly static Event SUICIDE
  548.         readonly static Event DENIAL
  549.        
  550.         static integer killingUnitId = 0
  551.         static integer dyingUnitId = 0
  552.         static integer killingPlayerId = 0
  553.         static integer dyingPlayerId = 0
  554.         static integer streakAchieved = 0
  555.         static integer streakEnded = 0
  556.         static integer multikillAchieved = 0
  557.         static integer multikillEnded = 0
  558.         static integer multikillLoserId = 0
  559.         static integer comboBroken = 0
  560.         static unit dyingUnit = null
  561.         static unit killingUnit = null
  562.        
  563.         implement InitEventHandler
  564.     endstruct
  565.    
  566.     private struct Multikill extends array
  567.         private static integer array value
  568.         private static real array counters
  569.        
  570.         method operator multikill takes nothing returns integer
  571.             return value[this]
  572.         endmethod
  573.        
  574.         method operator multikill= takes integer i returns nothing
  575.             set value[this] = i
  576.         endmethod
  577.        
  578.         method operator counter takes nothing returns real
  579.             return counters[this]
  580.         endmethod
  581.        
  582.         method operator counter= takes real r returns nothing
  583.             set counters[this] = r
  584.         endmethod
  585.        
  586.         static method reset takes integer this returns nothing
  587.             set value[this] = 0
  588.             set counters[this] = 0
  589.         endmethod
  590.        
  591.         static method resetAll takes nothing returns nothing
  592.             local integer i = 15
  593.             loop
  594.                 call reset(i)
  595.                 exitwhen i == 0
  596.                 set i = i - 1
  597.             endloop
  598.         endmethod
  599.        
  600.         private static method updateMulti takes nothing returns nothing
  601.             local integer index = 15
  602.             loop
  603.                 set counters[index] = counters[index] - MULTI_UPDATE
  604.                
  605.                 if counters[index] <= 0 then
  606.                     /*
  607.                     *   Cache Event Response Data and Fire Event.
  608.                     */
  609.                     set EventHandler.multikillLoserId = index
  610.                     set EventHandler.multikillEnded = value[index]
  611.                     set value[index] = 0
  612.                    
  613.                     set EventHandler.killingUnitId = 0
  614.                     set EventHandler.dyingUnitId = 0
  615.                     set EventHandler.killingUnit = null
  616.                     set EventHandler.dyingUnit = null
  617.                     set EventHandler.killingPlayerId = -1
  618.                     set EventHandler.dyingPlayerId = -1
  619.                    
  620.                     call EventHandler.END_MULTIKILL.fire()
  621.                 endif
  622.                
  623.                 exitwhen index == 0
  624.                 set index = index - 1
  625.             endloop
  626.         endmethod
  627.        
  628.         private static method onInit takes nothing returns nothing
  629.             call TimerStart(CreateTimer(), MULTI_UPDATE, true, function thistype.updateMulti)
  630.         endmethod
  631.     endstruct
  632.    
  633.     private struct Streak extends array
  634.         private static integer array value
  635.        
  636.         static method operator [] takes integer i returns integer
  637.             return value[i]
  638.         endmethod
  639.        
  640.         static method operator []= takes integer i, integer v returns nothing
  641.             set value[i] = v
  642.         endmethod
  643.        
  644.         static method reset takes integer i returns nothing
  645.             set value[i] = 0
  646.         endmethod
  647.        
  648.         static method resetAll takes nothing returns nothing
  649.             local integer i = 15
  650.             loop
  651.                 call reset(i)
  652.                 exitwhen i == 0
  653.                 set i = i - 1
  654.             endloop
  655.         endmethod
  656.     endstruct
  657.    
  658.     private function Exit takes nothing returns nothing
  659.         loop
  660.             call ExecuteFunc(Exit.name)
  661.         endloop
  662.     endfunction
  663.    
  664.     private struct Assist extends array
  665.         private static Table array counters
  666.         private static Table array assisting
  667.        
  668.         private static integer array count
  669.         private static integer array next
  670.         private static integer array prev
  671.         private static boolean array inList
  672.         private static boolean array allocated
  673.        
  674.         static method operator [] takes integer i returns thistype
  675.             return i
  676.         endmethod
  677.        
  678.         method operator [] takes integer i returns boolean
  679.             return assisting[this].boolean[i]
  680.         endmethod
  681.        
  682.         method operator []= takes integer i, boolean b returns nothing
  683.             set assisting[this].boolean[i] = b
  684.         endmethod
  685.        
  686.         method operator counter takes nothing returns integer
  687.             return counters[this]
  688.         endmethod
  689.        
  690.         method operator counter= takes integer i returns nothing
  691.             set counters[this] = i
  692.         endmethod
  693.        
  694.         method operator number takes nothing returns integer
  695.             return count[this]
  696.         endmethod
  697.        
  698.         method operator number= takes integer i returns nothing
  699.             set count[this] = i
  700.         endmethod
  701.        
  702.         static method reset takes integer unitId returns nothing
  703.             /*
  704.             *   Set the number of assisting players to 0,
  705.             *   and flush all the data in the tables.
  706.             */
  707.             set count[unitId] = 0
  708.             call assisting[unitId].flush()
  709.             call counters[unitId].flush()
  710.         endmethod
  711.        
  712.         static method resetAll takes nothing returns nothing
  713.             local integer this = next[0]
  714.             loop
  715.                 exitwhen this == 0
  716.                 call reset(this)
  717.                 set this = next[this]
  718.             endloop
  719.         endmethod
  720.        
  721.         static if not LIBRARY_UnitIndexer and not LIBRARY_AIDS then
  722.             private static unit crashThread
  723.             private static integer crashThreadInt
  724.         endif
  725.        
  726.         private static method getIndexed takes nothing returns unit
  727.             static if LIBRARY_UnitIndexer then
  728.                 return GetIndexedUnit()
  729.             elseif LIBRARY_AIDS then
  730.                 return AIDS_GetEnteringIndexUnit()
  731.             else
  732.                 return crashThread
  733.             endif
  734.         endmethod
  735.        
  736.         private static method getIndexedId takes nothing returns integer
  737.             static if LIBRARY_UnitIndexer then
  738.                 return GetIndexedUnitId()
  739.             elseif LIBRARY_AIDS then
  740.                 return AIDS_GetIndexOfEnteringUnitAllocated()
  741.             else
  742.                 return crashThreadInt
  743.             endif
  744.         endmethod
  745.        
  746.         private static method getDeindexed takes nothing returns unit
  747.             static if LIBRARY_UnitIndexer then
  748.                 return GetIndexedUnit()
  749.             elseif LIBRARY_AIDS then
  750.                 return GetIndexUnit(AIDS_GetDecayingIndex())
  751.             else
  752.                 return crashThread
  753.             endif
  754.         endmethod
  755.        
  756.         private static method getDeindexedId takes nothing returns integer
  757.             static if LIBRARY_UnitIndexer then
  758.                 return GetIndexedUnitId()
  759.             elseif LIBRARY_AIDS then
  760.                 return AIDS_GetDecayingIndex()
  761.             else
  762.                 return crashThreadInt
  763.             endif
  764.         endmethod
  765.        
  766.         private static method index takes nothing returns boolean
  767.             if IsUnitType(getIndexed(), UNIT_TYPE_HERO) then
  768.                 /*
  769.                 *   Make sure tables are initialized
  770.                 */
  771.                 if counters[getIndexedId()] == 0 then
  772.                     set counters[getIndexedId()] = Table.create()
  773.                     set assisting[getIndexedId()] = Table.create()
  774.                 endif
  775.                 set allocated[getIndexedId()] = true
  776.             endif
  777.             return false
  778.         endmethod
  779.        
  780.         private static method deindex takes nothing returns boolean
  781.             if IsUnitType(getDeindexed(), UNIT_TYPE_HERO) then
  782.                 /*
  783.                 *   Reset data
  784.                 */
  785.                 set count[getDeindexedId()] = 0
  786.                 call counters[getDeindexedId()].flush()
  787.                 call assisting[getDeindexedId()].flush()
  788.                 set allocated[getDeindexedId()] = false
  789.             endif
  790.             return false
  791.         endmethod
  792.        
  793.         private static integer damageTargetId = 0
  794.         private static integer damageSourceId = 0
  795.         private static unit damageTarget = null
  796.        
  797.         private static method filter takes player p, integer id returns boolean
  798.             static if LEAVER_CAN_ASSIST then
  799.                 return allocated[damageTargetId] and AssistPlayerFilter(id) and damageSourceId != 0 and (not assisting[damageTargetId].boolean[id]) and IsUnitEnemy(damageTarget, p) and damageSourceId != damageTargetId
  800.             else
  801.                 return allocated[damageTargetId] and AssistPlayerFilter(id) and damageSourceId != 0 and (not assisting[damageTargetId].boolean[id]) and IsUnitEnemy(damageTarget, p) and damageSourceId != damageTargetId and PlayerActive[id]
  802.             endif
  803.         endmethod
  804.        
  805.         private static method onDamage takes nothing returns boolean
  806.             local integer id
  807.             local player p
  808.            
  809.             /*
  810.             *   Data configuration based on system implemented.
  811.             */
  812.             static if LIBRARY_DamageEvent then
  813.                 set p = GetOwningPlayer(DamageEvent.source)
  814.                 set id = GetPlayerId(p)
  815.                 set damageTarget = DamageEvent.target
  816.                 set damageTargetId = DamageEvent.targetId
  817.                 set damageSourceId = DamageEvent.sourceId
  818.             elseif LIBRARY_Damage then
  819.                 static if DAMAGE_BY_JESUS4LYF then
  820.                     set p = GetOwningPlayer(GetEventDamageSource())
  821.                     set id = GetPlayerId(p)
  822.                     set damageTarget = GetTriggerUnit()
  823.                     set damageTargetId = GetUnitId(damageTarget)
  824.                     set damageSourceId = GetUnitId(GetEventDamageSource())
  825.                 else
  826.                     set p = GetOwningPlayer(Damage.source)
  827.                     set id = GetPlayerId(p)
  828.                     set damageTarget = Damage.target
  829.                     set damageTargetId = Damage.targetId
  830.                     set damageSourceId = Damage.sourceId
  831.                 endif
  832.             endif
  833.            
  834.             if filter(p, id) then
  835.                
  836.                 /*
  837.                 *   If the target is not in the list, we add him.
  838.                 */
  839.                 if not inList[damageTargetId] then
  840.                     set inList[damageTargetId] = true
  841.                     set next[damageTargetId] = 0
  842.                     set prev[damageTargetId] = prev[0]
  843.                     set next[prev[0]] = damageTargetId
  844.                     set prev[0] = damageTargetId
  845.                 endif
  846.                
  847.                 /*
  848.                 *   Mark player as assisting, increase assister count and reset assist counter
  849.                 */
  850.                 set assisting[damageTargetId].boolean[id] = true
  851.                 set count[damageTargetId] = count[damageTargetId] + 1
  852.                 set counters[damageTargetId].real[id] = ASSIST_DECAY
  853.             endif
  854.            
  855.             set p = null
  856.             return false
  857.         endmethod
  858.        
  859.         private static method updateAssist takes nothing returns nothing
  860.             local integer assist = next[0]
  861.             local integer index = 15
  862.             local real n = 0
  863.             loop
  864.                 exitwhen assist == 0
  865.                 loop
  866.                     if assisting[assist].boolean[index] then
  867.                         set n = counters[assist].real[index] - ASSIST_UPDATE
  868.                         set counters[assist].real[index] = n
  869.                        
  870.                         if n <= 0 then
  871.                             /*
  872.                             *   Mark the player as not assisting, decrease
  873.                             *   the assisting player count, and check if we
  874.                             *   can remove the target from the assists list
  875.                             */
  876.                             set assisting[assist].boolean[index] = false
  877.                             set count[assist] = count[assist] - 1
  878.                             if count[assist] == 0 then
  879.                                 set prev[next[assist]] = prev[assist]
  880.                                 set next[prev[assist]] = next[assist]
  881.                                 set inList[assist] = false
  882.                             endif
  883.                         endif
  884.                     endif
  885.                    
  886.                     exitwhen index == 0
  887.                     set index = index - 1
  888.                 endloop
  889.                 set index = 15
  890.                 set assist = next[assist]
  891.             endloop
  892.         endmethod
  893.        
  894.         private static method onInit takes nothing returns nothing
  895.             static if LIBRARY_Damage then
  896.                 local trigger t = CreateTrigger()
  897.             endif
  898.             static if LIBRARY_UnitIndexer then
  899.                 call RegisterUnitIndexEvent(Condition(function thistype.index), UnitIndexer.INDEX)
  900.                 call RegisterUnitIndexEvent(Condition(function thistype.deindex), UnitIndexer.DEINDEX)
  901.             elseif LIBRARY_AIDS then
  902.                 call AIDS_RegisterOnEnterAllocated(Condition(function thistype.index))
  903.                 call AIDS_RegisterOnDeallocate(Condition(function thistype.deindex))
  904.             else
  905.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "ERROR: NO UNIT INDEXING SYSTEM FOUND.")
  906.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "SHUTING DOWN IN: 5")
  907.                 call TriggerSleepAction(1)
  908.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "4")
  909.                 call TriggerSleepAction(1)
  910.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "3")
  911.                 call TriggerSleepAction(1)
  912.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "2")
  913.                 call TriggerSleepAction(1)
  914.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "1")
  915.                 call TriggerSleepAction(1)
  916.                 call Exit()
  917.             endif
  918.            
  919.             static if LIBRARY_DamageEvent then
  920.                 call DamageEvent.ANY.register(Condition(function thistype.onDamage), 0)
  921.             elseif LIBRARY_Damage then
  922.                 static if DAMAGE_BY_JESUS4LYF then
  923.                     call Damage_RegisterEvent(t)
  924.                     call TriggerAddCondition(t, Condition(function thistype.onDamage))
  925.                     set t = null
  926.                 else
  927.                     call RegisterGlobalDamage(function thistype.onDamage)
  928.                 endif
  929.             else
  930.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "ERROR: NO DAMAGE DETECTING SYSTEM FOUND.")
  931.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "SHUTING DOWN IN: 5")
  932.                 call TriggerSleepAction(1)
  933.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "4")
  934.                 call TriggerSleepAction(1)
  935.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "3")
  936.                 call TriggerSleepAction(1)
  937.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "2")
  938.                 call TriggerSleepAction(1)
  939.                 call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "1")
  940.                 call TriggerSleepAction(1)
  941.                 call Exit()
  942.             endif
  943.            
  944.             call TimerStart(CreateTimer(), ASSIST_UPDATE, true, function thistype.updateAssist)
  945.         endmethod
  946.     endstruct
  947.    
  948.     private struct MessageHandler extends array
  949.         private static string queue = ""
  950.        
  951.         static method print takes string s returns nothing
  952.             call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, TEXT_DURATION, s)
  953.         endmethod
  954.        
  955.         static method enqueue takes string s returns nothing
  956.             set queue = queue + s + "\n"
  957.         endmethod
  958.        
  959.         static method printQueue takes nothing returns nothing
  960.             call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, TEXT_DURATION, queue)
  961.         endmethod
  962.        
  963.         static method clearQueue takes nothing returns nothing
  964.             set queue = ""
  965.         endmethod
  966.     endstruct
  967.    
  968.     static if TEXTTAGS then
  969.         private struct TextTagHandler extends array
  970.             private static method createText takes player p, real cameraCenter, string s returns nothing
  971.                 local texttag tag = CreateTextTag()
  972.                 call SetTextTagText(tag, s, TEXTTAG_SIZE)
  973.                 call SetTextTagPos(tag, GetCameraEyePositionX(), GetCameraEyePositionY() + cameraCenter, 16.0)
  974.                 call SetTextTagVelocity(tag, TEXTTAG_X, TEXTTAG_Y)
  975.                 call SetTextTagVisibility(tag, GetLocalPlayer() == p)
  976.                 call SetTextTagFadepoint(tag, TEXTTAG_FADE)
  977.                 call SetTextTagLifespan(tag, TEXTTAG_AGE)
  978.                 call SetTextTagPermanent(tag, false)
  979.                 set tag = null
  980.             endmethod
  981.            
  982.             static method plus takes player p, real cameraCenter, string s returns nothing
  983.                 call createText(p, cameraCenter, "|cffffcc00+" + s)
  984.             endmethod
  985.            
  986.             static method minus takes player p, real cameraCenter, string s returns nothing
  987.                 call createText(p, cameraCenter, "|cffff0000-" + s)
  988.             endmethod
  989.         endstruct
  990.     endif
  991.    
  992.     private struct PlayerStatHandler extends array
  993.         static integer array kills
  994.         static integer array deaths
  995.         static integer array assists
  996.         static integer array denies
  997.         static integer array suicides
  998.        
  999.         static integer array streaks
  1000.         static integer array multikills
  1001.         static integer array combobreakers
  1002.        
  1003.         static Table array streakTypes
  1004.         static Table array multikillTypes
  1005.        
  1006.         private static method onInit takes nothing returns nothing
  1007.             local integer i = 15
  1008.             loop
  1009.                 set streakTypes[i] = Table.create()
  1010.                 set multikillTypes[i] = Table.create()
  1011.                 exitwhen i == 0
  1012.                 set i = i - 1
  1013.             endloop
  1014.         endmethod
  1015.     endstruct
  1016.    
  1017.     struct StreakSystem extends array
  1018.         private static integer maxStreak = 0
  1019.         private static integer minStreak = 0
  1020.         private static integer maxMultikill = 1
  1021.        
  1022.         static if LIBRARY_SoundTools then
  1023.             private static Sound firstSound
  1024.             private static Sound comboBreaker
  1025.            
  1026.             private static Sound array sounds
  1027.             private static Sound array multiSound
  1028.         elseif LIBRARY_SoundUtils then
  1029.             private static integer firstSound
  1030.             private static integer comboBreaker
  1031.            
  1032.             private static integer array sounds
  1033.             private static integer array multiSound
  1034.         endif
  1035.        
  1036.         private static string array strings
  1037.         private static string array multiString
  1038.         private static string array endString
  1039.         private static string array colors
  1040.        
  1041.         static boolean firstblood = false
  1042.         static boolean enabled = true
  1043.        
  1044.         private static key cacheKey
  1045.         private static Table cache = cacheKey
  1046.        
  1047.         /*
  1048.         *   Event Response Get Functions
  1049.         */
  1050.         static method getKillingUnitId takes nothing returns integer
  1051.             return EventHandler.killingUnitId
  1052.         endmethod
  1053.         static method getKillingUnit takes nothing returns unit
  1054.             return EventHandler.killingUnit
  1055.         endmethod
  1056.         static method getDyingUnitId takes nothing returns integer
  1057.             return EventHandler.dyingUnitId
  1058.         endmethod
  1059.         static method getDyingUnit takes nothing returns unit
  1060.             return EventHandler.dyingUnit
  1061.         endmethod
  1062.         static method getKillingPlayerId takes nothing returns integer
  1063.             return EventHandler.killingPlayerId
  1064.         endmethod
  1065.         static method getKillingPlayer takes nothing returns player
  1066.             return Player(EventHandler.killingPlayerId)
  1067.         endmethod
  1068.         static method getDyingPlayerId takes nothing returns integer
  1069.             return EventHandler.dyingPlayerId
  1070.         endmethod
  1071.         static method getDyingPlayer takes nothing returns player
  1072.             return Player(EventHandler.dyingPlayerId)
  1073.         endmethod
  1074.         static method getAchievedStreak takes nothing returns integer
  1075.             return EventHandler.streakAchieved
  1076.         endmethod
  1077.         static method getEndedStreak takes nothing returns integer
  1078.             return EventHandler.streakEnded
  1079.         endmethod
  1080.         static method getAchievedMultikill takes nothing returns integer
  1081.             return EventHandler.multikillAchieved
  1082.         endmethod
  1083.         static method getEndedMultikill takes nothing returns integer
  1084.             return EventHandler.multikillEnded
  1085.         endmethod
  1086.         static method getMultikillLoserId takes nothing returns integer
  1087.             return EventHandler.multikillLoserId
  1088.         endmethod
  1089.         static method getMultikillLoser takes nothing returns player
  1090.             return Player(EventHandler.multikillLoserId)
  1091.         endmethod
  1092.         static method getComboBroken takes nothing returns integer
  1093.             return EventHandler.comboBroken
  1094.         endmethod
  1095.        
  1096.         /*
  1097.         *   Event registration functions
  1098.         */
  1099.         static if EVENT_BY_NESTHARUS then
  1100.             static method registerFirstbloodEvent takes code c returns nothing
  1101.                 call EventHandler.FIRSTBLOOD.register(Filter(c))
  1102.                 return
  1103.             endmethod
  1104.             static method registerStreakEvent takes code c returns nothing
  1105.                 call EventHandler.STREAK.register(Filter(c))
  1106.                 return
  1107.             endmethod
  1108.             static method registerMultikillEvent takes code c returns nothing
  1109.                 call EventHandler.MULTIKILL.register(Filter(c))
  1110.                 return
  1111.             endmethod
  1112.             static method registerStreakEndEvent takes code c returns nothing
  1113.                 call EventHandler.END_STREAK.register(Filter(c))
  1114.                 return
  1115.             endmethod
  1116.             static method registerMultikillEndEvent takes code c returns nothing
  1117.                 call EventHandler.END_MULTIKILL.register(Filter(c))
  1118.                 return
  1119.             endmethod
  1120.             static method registerCombobreakerEvent takes code c returns nothing
  1121.                 call EventHandler.COMBO_BREAKER.register(Filter(c))
  1122.                 return
  1123.             endmethod
  1124.             static method registerSuicideEvent takes code c returns nothing
  1125.                 call EventHandler.SUICIDE.register(Filter(c))
  1126.                 return
  1127.             endmethod
  1128.             static method registerDenialEvent takes code c returns nothing
  1129.                 call EventHandler.DENIAL.register(Filter(c))
  1130.                 return
  1131.             endmethod
  1132.         else
  1133.             static method registerFirstbloodEvent takes trigger t returns nothing
  1134.                 call EventHandler.FIRSTBLOOD.register(t)
  1135.             endmethod
  1136.             static method registerStreakEvent takes trigger t returns nothing
  1137.                 call EventHandler.STREAK.register(t)
  1138.             endmethod
  1139.             static method registerMultikillEvent takes trigger t returns nothing
  1140.                 call EventHandler.MULTIKILL.register(t)
  1141.             endmethod
  1142.             static method registerStreakEndEvent takes trigger t returns nothing
  1143.                 call EventHandler.END_STREAK.register(t)
  1144.             endmethod
  1145.             static method registerMultikillEndEvent takes trigger t returns nothing
  1146.                 call EventHandler.END_MULTIKILL.register(t)
  1147.             endmethod
  1148.             static method registerCombobreakerEvent takes trigger t returns nothing
  1149.                 call EventHandler.COMBO_BREAKER.register(t)
  1150.             endmethod
  1151.             static method registerSuicideEvent takes trigger t returns nothing
  1152.                 call EventHandler.SUICIDE.register(t)
  1153.             endmethod
  1154.             static method registerDenialEvent takes trigger t returns nothing
  1155.                 call EventHandler.DENIAL.register(t)
  1156.             endmethod
  1157.         endif
  1158.        
  1159.         /*
  1160.         *   API Get Total Stat Functions
  1161.         */
  1162.         static method getKills takes player p returns integer
  1163.             return PlayerStatHandler.kills[GetPlayerId(p)]
  1164.         endmethod
  1165.         static method getDeaths takes player p returns integer
  1166.             return PlayerStatHandler.deaths[GetPlayerId(p)]
  1167.         endmethod
  1168.         static method getDenies takes player p returns integer
  1169.             return PlayerStatHandler.denies[GetPlayerId(p)]
  1170.         endmethod
  1171.         static method getSuicides takes player p returns integer
  1172.             return PlayerStatHandler.suicides[GetPlayerId(p)]
  1173.         endmethod
  1174.         static method getAssists takes player p returns integer
  1175.             return PlayerStatHandler.assists[GetPlayerId(p)]
  1176.         endmethod
  1177.         static method getStreaks takes player p returns integer
  1178.             return PlayerStatHandler.streaks[GetPlayerId(p)]
  1179.         endmethod
  1180.         static method getMultikills takes player p returns integer
  1181.             return PlayerStatHandler.multikills[GetPlayerId(p)]
  1182.         endmethod
  1183.         static method getCombobreakers takes player p returns integer
  1184.             return PlayerStatHandler.combobreakers[GetPlayerId(p)]
  1185.         endmethod
  1186.         static method getStreaksOfType takes player p, integer typ returns integer
  1187.             return PlayerStatHandler.streakTypes[GetPlayerId(p)][typ]
  1188.         endmethod
  1189.         static method getMultikillsOfType takes player p, integer typ returns integer
  1190.             return PlayerStatHandler.multikillTypes[GetPlayerId(p)][typ]
  1191.         endmethod
  1192.        
  1193.         static method getCurrentStreak takes player p returns integer
  1194.             return Streak[GetPlayerId(p)]
  1195.         endmethod
  1196.         static method getCurrentMultikill takes player p returns integer
  1197.             return Multikill(GetPlayerId(p)).multikill
  1198.         endmethod
  1199.        
  1200.         /*
  1201.         *   API Get Total Stat ById Functions
  1202.         */
  1203.         static method getKillsById takes integer id returns integer
  1204.             return PlayerStatHandler.kills[id]
  1205.         endmethod
  1206.         static method getDeathsById takes integer id returns integer
  1207.             return PlayerStatHandler.deaths[id]
  1208.         endmethod
  1209.         static method getDeniesById takes integer id returns integer
  1210.             return PlayerStatHandler.denies[id]
  1211.         endmethod
  1212.         static method getSuicidesById takes integer id returns integer
  1213.             return PlayerStatHandler.suicides[id]
  1214.         endmethod
  1215.         static method getAssistsById takes integer id returns integer
  1216.             return PlayerStatHandler.assists[id]
  1217.         endmethod
  1218.         static method getStreaksById takes integer id returns integer
  1219.             return PlayerStatHandler.streaks[id]
  1220.         endmethod
  1221.         static method getMultikillsById takes integer id returns integer
  1222.             return PlayerStatHandler.multikills[id]
  1223.         endmethod
  1224.         static method getCombobreakersById takes integer id returns integer
  1225.             return PlayerStatHandler.combobreakers[id]
  1226.         endmethod
  1227.         static method getStreaksOfTypeById takes integer id, integer typ returns integer
  1228.             return PlayerStatHandler.streakTypes[id][typ]
  1229.         endmethod
  1230.         static method getMultikillsOfTypeById takes integer id, integer typ returns integer
  1231.             return PlayerStatHandler.multikillTypes[id][typ]
  1232.         endmethod
  1233.        
  1234.         static method getCurrentStreakById takes integer id returns integer
  1235.             return Streak[id]
  1236.         endmethod
  1237.         static method getCurrentMultikillById takes integer id returns integer
  1238.             return Multikill(id).multikill
  1239.         endmethod
  1240.        
  1241.         /*
  1242.         *   Streak and Multikill Create Functions
  1243.         */
  1244.         static method newStreak takes string streakName, string streakDisplay, string soundPath, integer duration returns nothing
  1245.             set maxStreak = maxStreak + 1
  1246.            
  1247.             set strings[maxStreak] = " " + streakDisplay
  1248.             set endString[maxStreak] = "'s " + streakName
  1249.            
  1250.             static if LIBRARY_SoundTools then
  1251.                 set sounds[maxStreak] = NewSound(soundPath, duration, false, S3D)
  1252.             elseif LIBRARY_SoundUtils then
  1253.                 set sounds[maxStreak] = DefineSound(soundPath, duration, false, S3D)
  1254.             endif
  1255.         endmethod
  1256.        
  1257.         static method newMultikill takes string text, string soundPath, integer duration returns nothing
  1258.             set maxMultikill = maxMultikill + 1
  1259.             set multiString[maxMultikill] = " " + text
  1260.             static if LIBRARY_SoundTools then
  1261.                 set multiSound[maxMultikill] = NewSound(soundPath, duration, false, S3D)
  1262.             elseif LIBRARY_SoundUtils then
  1263.                 set multiSound[maxMultikill] = DefineSound(soundPath, duration, false, S3D)
  1264.             endif
  1265.         endmethod
  1266.        
  1267.         static method setMinimumStreak takes integer i returns nothing
  1268.             set minStreak = i
  1269.             set maxStreak = i - 1
  1270.         endmethod
  1271.        
  1272.         static method setFirstBloodSound takes string path, integer duration returns nothing
  1273.             static if LIBRARY_SoundTools then
  1274.                 set firstSound = NewSound(path, duration, false, S3D)
  1275.             elseif LIBRARY_SoundUtils then
  1276.                 set firstSound = DefineSound(path, duration, false, S3D)
  1277.             endif
  1278.         endmethod
  1279.        
  1280.         static method setComboBreakerSound takes string path, integer duration returns nothing
  1281.             static if LIBRARY_SoundTools then
  1282.                 set comboBreaker = NewSound(path, duration, false, S3D)
  1283.             elseif LIBRARY_SoundUtils then
  1284.                 set comboBreaker = DefineSound(path, duration, false, S3D)
  1285.             endif
  1286.         endmethod
  1287.        
  1288.         /*
  1289.         *   Color Configuration
  1290.         */
  1291.         static method setColor takes integer playerId, string color returns nothing
  1292.             set thistype.colors[playerId] = color
  1293.         endmethod
  1294.        
  1295.         /*
  1296.         *   Gold Gain/Loss Control
  1297.         */
  1298.         static method operator goldGain takes nothing returns boolean
  1299.             return gainGold
  1300.         endmethod
  1301.         static method operator goldGain= takes boolean b returns nothing
  1302.             set gainGold = b
  1303.         endmethod
  1304.         static method operator goldLoss takes nothing returns boolean
  1305.             return loseGold
  1306.         endmethod
  1307.         static method operator goldLoss= takes boolean b returns nothing
  1308.             set loseGold = b
  1309.         endmethod
  1310.        
  1311.         /*
  1312.         *   Bounty Formula Control
  1313.         */
  1314.         static method operator bountyBase takes nothing returns integer
  1315.             return baseGold
  1316.         endmethod
  1317.         static method operator bountyBase= takes integer v returns nothing
  1318.             set baseGold = v
  1319.         endmethod
  1320.         static method operator bountyIncrement takes nothing returns integer
  1321.             return goldIncrement
  1322.         endmethod
  1323.         static method operator bountyIncrement= takes integer v returns nothing
  1324.             set goldIncrement = v
  1325.         endmethod
  1326.        
  1327.         /*
  1328.         *   Streak Functions
  1329.         */
  1330.         static method resetStreak takes integer playerId returns nothing
  1331.             call Streak.reset(playerId)
  1332.         endmethod
  1333.         static method resetAllStreaks takes nothing returns nothing
  1334.             call Streak.resetAll()
  1335.         endmethod
  1336.        
  1337.         /*
  1338.         *   Multikill Functions
  1339.         */
  1340.         static method resetMultikill takes integer playerId returns nothing
  1341.             call Multikill.reset(playerId)
  1342.         endmethod
  1343.         static method resetAllMultikills takes nothing returns nothing
  1344.             call Multikill.resetAll()
  1345.         endmethod
  1346.        
  1347.         /*
  1348.         *   Assist Functions
  1349.         */
  1350.         static method resetAssist takes integer unitId returns nothing
  1351.             call Assist.reset(unitId)
  1352.         endmethod
  1353.         static method resetAllAssists takes nothing returns nothing
  1354.             call Assist.resetAll()
  1355.         endmethod
  1356.        
  1357.         /*
  1358.         *   Simple wrapper for gold gaining.
  1359.         */
  1360.         private static method addGold takes player p, integer amount returns nothing
  1361.         endmethod
  1362.        
  1363.         private static method doMulti takes nothing returns nothing
  1364.             local timer tmr = GetExpiredTimer()
  1365.             local integer handleId = GetHandleId(tmr)
  1366.             local integer multi = GetTimerData(tmr)
  1367.            
  1368.             /*
  1369.             *   Make sure the multikill is greater than 1 and still valid
  1370.             */
  1371.             if cache.real[handleId] > 0 and multi > 1 then
  1372.            
  1373.                 /*
  1374.                 *   Checking if the multikill is greater than the maximum multikill,
  1375.                 *   then displaying the correct message and playing the correct sound
  1376.                 */
  1377.                 if multi > maxMultikill then
  1378.                     call MessageHandler.print(cache.string[handleId] + multiString[maxMultikill])
  1379.                     call RunSound(multiSound[maxMultikill])
  1380.                 else
  1381.                     call MessageHandler.print(cache.string[handleId] + multiString[multi])
  1382.                     call RunSound(multiSound[multi])
  1383.                 endif
  1384.             endif
  1385.            
  1386.             call ReleaseTimer(tmr)
  1387.             set tmr = null
  1388.         endmethod
  1389.        
  1390.         private static method onDeath takes nothing returns nothing
  1391.             /*
  1392.             *   These variables are for storing basic data like the killing unit,
  1393.             *   the dying unit, the killing player, etc...
  1394.             */
  1395.             local unit dyingUnit
  1396.             local unit killingUnit
  1397.             local player dyingPlayer
  1398.             local player killingPlayer
  1399.             local integer dyingId
  1400.             local integer killingId
  1401.            
  1402.             /*
  1403.             *   Local variables that will be needed later.
  1404.             */
  1405.             local integer index = 0
  1406.             local integer bounty
  1407.             local integer unitIdDying
  1408.             local integer unitIdKilling
  1409.             local integer timerId
  1410.             local string assistString = ""
  1411.             local string killingName
  1412.             local string dyingName
  1413.             local player tempPlayer
  1414.             local timer delayTimer
  1415.            
  1416.             /*
  1417.             *   These locals will only be declared if TEXTTAGS is set to true.
  1418.             */
  1419.             static if TEXTTAGS then
  1420.                 local integer assistGold
  1421.                 local integer lostGold
  1422.                 local texttag tag
  1423.                 local real cameraCenter
  1424.             endif
  1425.            
  1426.             /*
  1427.             *   Make sure the dying unit is a hero and the system is enabled
  1428.             */
  1429.             if enabled and IsUnitType(GetTriggerUnit(), UNIT_TYPE_HERO) then
  1430.            
  1431.                 set dyingUnit = GetTriggerUnit()
  1432.                 set killingUnit = GetKillingUnit()
  1433.                 set dyingPlayer = GetTriggerPlayer()
  1434.                 set killingPlayer = GetOwningPlayer(killingUnit)
  1435.                 set killingId = GetPlayerId(killingPlayer)
  1436.                 set dyingId = GetPlayerId(dyingPlayer)
  1437.                
  1438.                 if KillingPlayerFilter(killingId) and DyingPlayerFilter(dyingId) and killingUnit != null and killingPlayer != null then
  1439.                     static if LEAVER_STREAK then
  1440.                         /*
  1441.                         *   Check if the player has left.
  1442.                         */
  1443.                         if not PlayerActive[killingId] then
  1444.                             set dyingUnit = null
  1445.                             set killingUnit = null
  1446.                             set dyingPlayer = null
  1447.                             set killingPlayer = null
  1448.                             return
  1449.                         endif
  1450.                     endif
  1451.                    
  1452.                     /*
  1453.                     *   Check if the killing player and the dying player are allies.
  1454.                     */
  1455.                     if IsPlayerAlly(killingPlayer, dyingPlayer) then
  1456.                        
  1457.                         call resetAssist(GetUnitUserData(dyingUnit))
  1458.                        
  1459.                         if killingPlayer != dyingPlayer then
  1460.                             /*
  1461.                             *   Total Stat Incrementation
  1462.                             */
  1463.                             set PlayerStatHandler.denies[killingId] = PlayerStatHandler.denies[killingId] + 1
  1464.                             static if DENIES_COUNT_DEATHS then
  1465.                                 set PlayerStatHandler.deaths[dyingId] = PlayerStatHandler.deaths[dyingId] + 1
  1466.                             endif
  1467.                             static if DENIES_COUNT_KILLS then
  1468.                                 set PlayerStatHandler.kills[killingId] = PlayerStatHandler.kills[killingId] + 1
  1469.                             endif
  1470.                            
  1471.                             /*
  1472.                             *   We print the allied-player-denial message.
  1473.                             */
  1474.                             call MessageHandler.print(GetDenialString(colors[killingId] + GetPlayerName(killingPlayer), colors[dyingId] + GetPlayerName(dyingPlayer)))
  1475.                            
  1476.                             /*
  1477.                             *   We store the event data responses and fire the event.
  1478.                             */
  1479.                             set EventHandler.killingUnitId = GetUnitUserData(killingUnit)
  1480.                             set EventHandler.killingUnit = killingUnit
  1481.                             set EventHandler.killingPlayerId = killingId
  1482.                             set EventHandler.dyingUnitId = GetUnitUserData(dyingUnit)
  1483.                             set EventHandler.dyingUnit = dyingUnit
  1484.                             set EventHandler.dyingPlayerId = dyingId
  1485.                             call EventHandler.DENIAL.fire()
  1486.                         else
  1487.                             /*
  1488.                             *   Total Stat Incrementations
  1489.                             */
  1490.                             set PlayerStatHandler.suicides[killingId] = PlayerStatHandler.suicides[killingId] + 1
  1491.                             static if SUICIDE_DEATH then
  1492.                                 set PlayerStatHandler.deaths[dyingId] = PlayerStatHandler.deaths[dyingId] + 1
  1493.                             endif
  1494.                            
  1495.                             /*
  1496.                             *   We print the suicide message.
  1497.                             */
  1498.                             call MessageHandler.print(GetSuicideString(colors[killingId] + GetPlayerName(dyingPlayer)))
  1499.                            
  1500.                             /*
  1501.                             *   We store the event data responses.
  1502.                             */
  1503.                             set EventHandler.killingUnitId = GetUnitUserData(killingUnit)
  1504.                             set EventHandler.killingUnit = killingUnit
  1505.                             set EventHandler.killingPlayerId = killingId
  1506.                             set EventHandler.dyingUnitId = EventHandler.killingUnitId
  1507.                             set EventHandler.dyingUnit = EventHandler.killingUnit
  1508.                             set EventHandler.dyingPlayerId = killingId
  1509.                            
  1510.                             static if SUICIDE_ENDS then
  1511.                                 /*
  1512.                                 *   Cache event data and reset streak
  1513.                                 */
  1514.                                 set EventHandler.streakEnded = Streak[killingId]
  1515.                                 set Streak[killingId] = 0
  1516.                             endif
  1517.                            
  1518.                             /*
  1519.                             *   Fire suicide and streak-end
  1520.                             */
  1521.                             static if SUICIDE_FIRE_FIRST then
  1522.                                 call EventHandler.SUICIDE.fire()
  1523.                                 static if SUICIDE_ENDS then
  1524.                                     call EventHandler.END_STREAK.fire()
  1525.                                 endif
  1526.                             else
  1527.                                 static if SUICIDE_ENDS then
  1528.                                     call EventHandler.END_STREAK.fire()
  1529.                                 endif
  1530.                                 call EventHandler.SUICIDE.fire()
  1531.                             endif
  1532.                         endif
  1533.                        
  1534.                         /*
  1535.                         *   Null all the locals and return.
  1536.                         */
  1537.                         set dyingUnit = null
  1538.                         set killingUnit = null
  1539.                         set dyingPlayer = null
  1540.                         set killingPlayer = null
  1541.                         return
  1542.                     endif
  1543.                    
  1544.                     /*
  1545.                     *   Increase kills of killing player and deaths of dying player
  1546.                     */
  1547.                     set PlayerStatHandler.kills[killingId] = PlayerStatHandler.kills[killingId] + 1
  1548.                     set PlayerStatHandler.deaths[dyingId] = PlayerStatHandler.deaths[dyingId] + 1
  1549.                    
  1550.                     /*
  1551.                     *   Increase streak of killing player and reset multikill counter
  1552.                     */
  1553.                     set Streak[killingId] = Streak[killingId] + 1
  1554.                     set Multikill(killingId).counter = MULTI_TIME
  1555.                    
  1556.                     set unitIdDying = GetUnitUserData(dyingUnit)
  1557.                     set unitIdKilling = GetUnitUserData(killingUnit)
  1558.                    
  1559.                     /*
  1560.                     *   Event response data
  1561.                     */
  1562.                     set EventHandler.killingUnitId = unitIdKilling
  1563.                     set EventHandler.dyingUnitId = unitIdDying
  1564.                     set EventHandler.killingUnit = killingUnit
  1565.                     set EventHandler.dyingUnit = dyingUnit
  1566.                     set EventHandler.killingPlayerId = killingId
  1567.                     set EventHandler.dyingPlayerId = dyingId
  1568.                    
  1569.                     static if DEATH_END_MULTI then
  1570.                         /*
  1571.                         *   Cache event data, reset multikills of dying player and fire event
  1572.                         */
  1573.                         set EventHandler.multikillEnded = Multikill(dyingId).multikill
  1574.                         set EventHandler.multikillLoserId = dyingId
  1575.                        
  1576.                         set Multikill(dyingId).multikill = 0
  1577.                         set Multikill(dyingId).counter = 0
  1578.                        
  1579.                         call EventHandler.END_MULTIKILL.fire()
  1580.                     endif
  1581.                    
  1582.                     /*
  1583.                     *   The bounty of the killing player.
  1584.                     */
  1585.                     set bounty = GetBounty(killingId, dyingId, killingUnit, dyingUnit)
  1586.                    
  1587.                     /*
  1588.                     *   Get the colored names of the killing player and dying player.
  1589.                     */
  1590.                     set killingName = colors[killingId] + GetPlayerName(killingPlayer) + "|r"
  1591.                     set dyingName = colors[dyingId] + GetPlayerName(dyingPlayer) + "|r"
  1592.                    
  1593.                     static if TEXTTAGS then
  1594.                         set assistGold = 0
  1595.                         set lostGold = 0
  1596.                         /*
  1597.                         *   We are dividing the camera distance by 2 to be used while placing the texttag
  1598.                         *   at the center of the screen for the player. This will be equal to half the length of
  1599.                         *   your field of view. Interesting, ey?
  1600.                         */
  1601.                         set cameraCenter = GetCameraField(CAMERA_FIELD_TARGET_DISTANCE) / 2
  1602.                     endif
  1603.                    
  1604.                     /*
  1605.                     *   If the number of assisters is one, it means that only the killing player fought the unit.
  1606.                     *   If the number of assisters is greater than one, there is at least one assister, so:
  1607.                     */
  1608.                     if Assist[unitIdDying].number > 1 then
  1609.                    
  1610.                         set assistString = " Assists: "
  1611.                        
  1612.                         /*
  1613.                         *   We loop through all the players
  1614.                         */
  1615.                         loop
  1616.                             set tempPlayer = Player(index)
  1617.                            
  1618.                             /*
  1619.                             *   Check if the player is an enemy to the dying player and if he assisted in the kill.
  1620.                             */
  1621.                             if Assist[unitIdDying][index] and index != killingId and index != dyingId and PlayerActive[index] then
  1622.                                
  1623.                                 /*
  1624.                                 *   Add player name to assist string and increase total assists
  1625.                                 */
  1626.                                 set assistString = assistString + colors[index] + GetPlayerName(tempPlayer) + "|r/"
  1627.                                 set PlayerStatHandler.assists[index] = PlayerStatHandler.assists[index] + 1
  1628.                                
  1629.                                 static if ASSIST_GOLD then
  1630.                                     static if TEXTTAGS then
  1631.                                         /*
  1632.                                         *   Give assisting player gold and create texttag
  1633.                                         */
  1634.                                         set assistGold = GetAssistGold(killingId, dyingId, killingUnit, dyingUnit, bounty, Assist[unitIdDying].number)
  1635.                                         call addGold(tempPlayer, assistGold)
  1636.                                         call TextTagHandler.plus(tempPlayer, cameraCenter, I2S(assistGold))
  1637.                                     else
  1638.                                         /*
  1639.                                         *   Give assisting player gold
  1640.                                         */
  1641.                                         call addGold(tempPlayer, GetAssistGold(killingId, dyingId, killingUnit, dyingUnit, bounty, Assist[unitIdDying].number))
  1642.                                     endif
  1643.                                 endif
  1644.                             endif
  1645.                            
  1646.                             exitwhen index == 15
  1647.                             set index = index + 1
  1648.                         endloop
  1649.                        
  1650.                         /*
  1651.                         *   Adjust assist string.
  1652.                         */
  1653.                         set assistString = SubString(assistString, 0, StringLength(assistString) - 1)
  1654.                     endif
  1655.                    
  1656.                     call Assist.reset(unitIdDying)
  1657.                    
  1658.                     /*
  1659.                     *   If bounty-gain is enabled, give gold to the
  1660.                     *   player and create a texttag if that feature
  1661.                     *   is selected.
  1662.                     */
  1663.                     if gainGold then
  1664.                         call addGold(killingPlayer, bounty)
  1665.                         static if TEXTTAGS then
  1666.                             call TextTagHandler.plus(killingPlayer, cameraCenter, I2S(bounty))
  1667.                         endif
  1668.                     endif
  1669.                    
  1670.                     /*
  1671.                     *   If gold-loss is enabled, we remove gold from the player
  1672.                     *   and create a texttag if the feature is selected.
  1673.                     */
  1674.                     if loseGold then
  1675.                         static if TEXTTAGS then
  1676.                             set lostGold = GetLostGold(killingId, dyingId, killingUnit, dyingUnit, bounty)
  1677.                             call addGold(dyingPlayer, -lostGold)
  1678.                             call TextTagHandler.minus(dyingPlayer, cameraCenter, I2S(lostGold))
  1679.                         else
  1680.                             call addGold(dyingPlayer, -(GetLostGold(killingId, dyingId, killingUnit, dyingUnit, bounty)))
  1681.                         endif
  1682.                     endif
  1683.                    
  1684.                     if firstblood then
  1685.                        
  1686.                         /*
  1687.                         *   Evaluate dying player streak
  1688.                         */
  1689.                         if Streak[dyingId] >= minStreak and Streak[dyingId] <= maxStreak then
  1690.                             call MessageHandler.enqueue(GetEndString(killingName, dyingName, endString[Streak[dyingId]], I2S(bounty)) + assistString)
  1691.                             set EventHandler.streakEnded = Streak[dyingId]
  1692.                             call EventHandler.END_STREAK.fire()
  1693.                            
  1694.                             /*
  1695.                             *   Combobreaker evaluation
  1696.                             */
  1697.                             if Streak[dyingId] >= COMBO_BREAKER_MIN then
  1698.                                 set PlayerStatHandler.combobreakers[killingId] = PlayerStatHandler.combobreakers[killingId] + 1
  1699.                                 call RunSound(comboBreaker)
  1700.                                 set EventHandler.comboBroken = Streak[dyingId]
  1701.                                 call EventHandler.COMBO_BREAKER.fire()
  1702.                             endif
  1703.                         elseif Streak[dyingId] > maxStreak then
  1704.                             /*
  1705.                             *   Display End Streak Message and fire event
  1706.                             */
  1707.                             call MessageHandler.enqueue(GetEndString(killingName, dyingName, endString[maxStreak], I2S(bounty)) + assistString)
  1708.                             set EventHandler.streakEnded = maxStreak
  1709.                             call EventHandler.END_STREAK.fire()
  1710.                            
  1711.                             /*
  1712.                             *   Run combo breaker sound, increase total combo breakers and fire event
  1713.                             */
  1714.                             set PlayerStatHandler.combobreakers[killingId] = PlayerStatHandler.combobreakers[killingId] + 1
  1715.                             call RunSound(comboBreaker)
  1716.                             set EventHandler.comboBroken = Streak[dyingId]
  1717.                             call EventHandler.COMBO_BREAKER.fire()
  1718.                         else
  1719.                             /*
  1720.                             *   Display Ordinary Kill Message
  1721.                             */
  1722.                             call MessageHandler.enqueue(GetKillString(killingName, dyingName, I2S(bounty)) + assistString)
  1723.                         endif
  1724.                        
  1725.                         /*
  1726.                         *   Evaluate killing player streak
  1727.                         */
  1728.                         if Streak[killingId] >= minStreak and Streak[killingId] <= maxStreak then
  1729.                             call MessageHandler.enqueue(killingName + strings[Streak[killingId]])
  1730.                             call RunSound(sounds[Streak[killingId]])
  1731.                            
  1732.                             /*
  1733.                             *   Smart Algorithm for streak/streak-type tracking
  1734.                             */
  1735.                             if Streak[killingId] == minStreak then
  1736.                                 set PlayerStatHandler.streaks[killingId] = PlayerStatHandler.streaks[killingId] + 1
  1737.                             else
  1738.                                 set PlayerStatHandler.streakTypes[killingId][Streak[killingId] - 1] = PlayerStatHandler.streakTypes[killingId][Streak[killingId] - 1] - 1
  1739.                             endif
  1740.                            
  1741.                             /*
  1742.                             *   Increase the number of streak types for player and fire event
  1743.                             */
  1744.                             set PlayerStatHandler.streakTypes[killingId][Streak[killingId]] = PlayerStatHandler.streakTypes[killingId][Streak[killingId]] + 1
  1745.                             set EventHandler.streakAchieved = Streak[killingId]
  1746.                             call EventHandler.STREAK.fire()
  1747.                         elseif Streak[killingId] > maxStreak then
  1748.                        
  1749.                             /*
  1750.                             *   We display the streak message of the maximum streak value because
  1751.                             *   the streak of the killing player is too large and we play the streak sound.
  1752.                             */
  1753.                             call MessageHandler.enqueue(killingName + strings[maxStreak])
  1754.                             call RunSound(sounds[maxStreak])
  1755.                            
  1756.                             /*
  1757.                             *   Store the achieved streak and fire the Streak event
  1758.                             */
  1759.                             set EventHandler.streakAchieved = maxStreak
  1760.                             call EventHandler.STREAK.fire()
  1761.                         endif
  1762.                     else
  1763.                         /*
  1764.                         *   Register firstblood as taken, display messages, give gold, play sound and fire event
  1765.                         */
  1766.                         set firstblood = true
  1767.                        
  1768.                         call MessageHandler.enqueue(GetKillString(killingName, dyingName, I2S(bounty)) + assistString)
  1769.                         call MessageHandler.enqueue(GetFirstbloodString(killingName))
  1770.                        
  1771.                         call RunSound(firstSound)
  1772.                         call addGold(killingPlayer, FIRST_GOLD)
  1773.                         call EventHandler.FIRSTBLOOD.fire()
  1774.                        
  1775.                         static if TEXTTAGS then
  1776.                             call TextTagHandler.plus(killingPlayer, cameraCenter - 35., I2S(FIRST_GOLD))
  1777.                         endif
  1778.                     endif
  1779.                    
  1780.                     /*
  1781.                     *   Increase current multikills by 1 and reset dying player streak
  1782.                     */
  1783.                     set Multikill[killingId].multikill = Multikill[killingId].multikill + 1
  1784.                     set Streak[dyingId] = 0
  1785.                    
  1786.                     /*
  1787.                     *   Evaluation of killing player multikills
  1788.                     */
  1789.                     if Multikill[killingId].multikill > 1 then
  1790.                         /*
  1791.                         *   Create a timer and store multikill data in it to display
  1792.                         *   multikill message after a delay
  1793.                         */
  1794.                         set delayTimer = NewTimerEx(Multikill[killingId].multikill)
  1795.                         set timerId = GetHandleId(delayTimer)
  1796.                         set cache.real[timerId] = Multikill[killingId].counter
  1797.                         set cache.string[timerId] = killingName
  1798.                         call TimerStart(delayTimer, INTERVAL, false, function thistype.doMulti)
  1799.                        
  1800.                         /*
  1801.                         *   Smart Algorithm for multikill/multikill-type detection
  1802.                         */
  1803.                         if Multikill[killingId].multikill == 2 then
  1804.                             set PlayerStatHandler.multikills[killingId] = PlayerStatHandler.multikills[killingId] + 1
  1805.                         elseif Multikill[killingId].multikill <= maxMultikill then
  1806.                             set PlayerStatHandler.multikillTypes[killingId][Multikill[killingId].multikill - 1] = PlayerStatHandler.multikillTypes[killingId][Multikill[killingId].multikill - 1] - 1
  1807.                         endif
  1808.                        
  1809.                         /*
  1810.                         *   Increase number of multikill types and fire event
  1811.                         */
  1812.                         set PlayerStatHandler.multikillTypes[killingId][Multikill[killingId].multikill] = PlayerStatHandler.multikillTypes[killingId][Multikill[killingId].multikill] + 1
  1813.                         set EventHandler.multikillAchieved = Multikill[killingId].multikill
  1814.                         call EventHandler.MULTIKILL.fire()
  1815.                     endif
  1816.                    
  1817.                     /*
  1818.                     *   Print all enqueued strings and clear queue
  1819.                     */
  1820.                     call MessageHandler.printQueue()
  1821.                     call MessageHandler.clearQueue()
  1822.                    
  1823.                     /*
  1824.                     *   Null data
  1825.                     */
  1826.                     set tempPlayer = null
  1827.                     set delayTimer = null
  1828.                 endif
  1829.                
  1830.                 /*
  1831.                 *   Null data
  1832.                 */
  1833.                 set dyingUnit = null
  1834.                 set killingUnit = null
  1835.                 set dyingPlayer = null
  1836.                 set killingPlayer = null
  1837.             endif
  1838.         endmethod
  1839.        
  1840.         implement Init
  1841.        
  1842.         private static method onInit takes nothing returns nothing
  1843.             static if LIBRARY_RegisterPlayerUnitEvent then
  1844.                 call RegisterPlayerUnitEvent(EVENT_PLAYER_UNIT_DEATH, function thistype.onDeath)
  1845.             else
  1846.                 local trigger t = CreateTrigger()
  1847.                 local code c = function thistype.onDeath
  1848.                 call TriggerAddCondition(t, Condition(c))
  1849.                 set t = null
  1850.             endif
  1851.         endmethod
  1852.     endstruct
  1853.    
  1854. endlibrary

Feel free to comment and rate.
Credit isn't required, but it would be highly appreciated. (Just being humble :D)
« Last Edit: February 02, 2018, 10:35:43 PM by moyack »



Advanced Streak System v4.3.0.0
Reply #1 on: June 25, 2013, 07:14:08 PM

Moved from media section to the new JASS system section. And uber approved for awesomeness!!! YAY


Advanced Streak System v4.3.0.0
Reply #2 on: June 25, 2013, 08:54:56 PM

SO NEAT!! :3 :3
I would like to use this :3 :3
Well, I want DotA hero revive system or Compressed Tavern like something else :3 :3
That's would like cool @..@



 

* Random Spells & Systems

Started by cohadar

Replies: 0
Views: 2044
Codes & Snippets

Started by ashujon

Replies: 0
Views: 2975
Warcraft III Spells and Systems

Started by azlier

Replies: 0
Views: 1789
Codes & Snippets

Started by Magtheridon96

Replies: 0
Views: 2025
Codes & Snippets

Started by moyack

Replies: 6
Views: 19000
Codes & Snippets
Vivir aprendiendo.co - A place for learning stuff, in Spanish   Chaos Realm - The world of Game modders and wc3 addicts   Diplo, a gaming community   Power of Corruption, an altered melee featuring Naga and Demon. Play it now!!!   WC3JASS.com - The JASS Vault + vJASS and Zinc   Jetcraft - A Starcraft II mod   WormTastic Clan (wTc)   Warcraft RESOURCES Reforged: Modelos, mapas, proyectos y mas...