--Copyright © 2013, Byrthnoth --All rights reserved. --Redistribution and use in source and binary forms, with or without --modification, are permitted provided that the following conditions are met: -- * Redistributions of source code must retain the above copyright -- notice, this list of conditions and the following disclaimer. -- * Redistributions in binary form must reproduce the above copyright -- notice, this list of conditions and the following disclaimer in the -- documentation and/or other materials provided with the distribution. -- * Neither the name of nor the -- names of its contributors may be used to endorse or promote products -- derived from this software without specific prior written permission. --THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND --ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED --WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE --DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY --DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES --(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; --LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND --ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT --(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS --SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. function nf(field,subfield) if field ~= nil then return field[subfield] else return nil end end function flip(p1,p1t,p2,p2t,cond) return p2,p2t,p1,p1t,not cond end function colconv(str,key) -- Used in the options_load() function local out local strnum = tonumber(str) if strnum >= 256 and strnum < 509 then strnum = strnum - 254 if strnum == 4 then strnum = 3 end --color 258 can bug chatlog out = string.char(0x1E,strnum) elseif strnum >0 then out = string.char(0x1F,strnum) elseif strnum == 0 then out = rcol else print('You have an invalid color '..key) out = string.char(0x1F,1) end return out end function color_it(to_color,color) if not color and debugging then windower.add_to_chat(8,'Color was invalid.') end if not color or color == 0 then return to_color end if to_color then local colarr = string.split(to_color,' ') colarr.n = nil return color..table.concat(colarr,rcol..' '..color)..rcol end end function conjunctions(pre,post,target_count,current) if current < target_count or commamode then pre = pre..', ' else if oxford and target_count >2 then pre = pre..',' end pre = pre..' and ' end return pre..post end function fieldsearch(message) local fieldarr = {} string.gsub(message,'{(.-)}', function(a) fieldarr[a] = true end) return fieldarr end function check_filter(actor,target,category,msg) -- This determines whether the message should be displayed or filtered -- Returns true (don't filter) or false (filter), boolean if not actor.filter or not target.filter then return false end if not filter[actor.filter] and debugging then windower.add_to_chat(8,'Battlemod - Filter Not Recognized: '..tostring(actor.filter)) end local filtertab = (filter[actor.filter] and filter[actor.filter][target.filter]) or filter[actor.filter] if filtertab['all'] or category == 1 and filtertab['melee'] or category == 2 and filtertab['ranged'] or category == 12 and filtertab['ranged'] or category == 5 and filtertab['items'] or category == 9 and filtertab['uses'] or nf(res.action_messages[msg],'color')=='D' and filtertab['damage'] or nf(res.action_messages[msg],'color')=='M' and filtertab['misses'] or nf(res.action_messages[msg],'color')=='H' and filtertab['healing'] or (msg == 43 or msg == 326) and filtertab['readies'] or (msg == 3 or msg==327) and filtertab['casting'] then return false end return true end function actor_noun(msg) if msg then msg = msg :gsub('${actor}', 'The ${actor}') end return msg end function plural_actor(msg, msg_id) if msg then if msg_id == 6 then msg = msg:gsub('${actor} defeats ', '${actor} defeat ') elseif msg_id == 9 then msg = msg:gsub('${actor} attains ', '${actor} attain ') elseif msg_id == 10 then msg = msg:gsub('${actor} loses ', '${actor} lose ') elseif msg_id == 11 then msg = msg:gsub('${actor} falls ', '${actor} fall ') elseif msg_id == 19 then msg = msg:gsub('${actor} calls ' , '${actor} call ') elseif msg_id == 35 then msg = msg:gsub('${actor} lacks ' , '${actor} lack ') elseif msg_id == 67 then msg = msg:gsub('${actor} scores ' , '${actor} score ') elseif msg_id == 124 then msg = msg:gsub('${actor} achieves ' , '${actor} achieve ') elseif msg_id == 129 then msg = msg:gsub('${actor} mugs ' , '${actor} mug ') elseif msg_id == 244 then msg = msg:gsub('${actor} fails ' , '${actor} fail ') elseif msg_id == 311 then msg = msg:gsub('${actor} covers ' , '${actor} cover ') elseif msg_id == 315 then msg = msg:gsub('${actor} already has ' , '${actor} already have ') elseif msg_id ==411 then msg = msg :gsub('${actor} attempts ' , '${actor} attempt ') :gsub(' but lacks ' , ' but lack ') elseif msg_id == 536 then msg = msg:gsub('${actor} takes ' , '${actor} take ') elseif msg_id == 563 then msg = msg:gsub('${actor} destroys ' , '${actor} destroy ') elseif msg_id == 772 then msg = msg:gsub('${actor} stands ', '${actor} stand ') elseif replacements_map.actor.hits:contains(msg_id) then msg = msg:gsub('${actor} hits ', '${actor} hit ') elseif replacements_map.actor.misses:contains(msg_id) then msg = msg:gsub('${actor} misses ' , '${actor} miss ') elseif replacements_map.actor.starts:contains(msg_id) then msg = msg:gsub('${actor} starts ', '${actor} start ') elseif replacements_map.actor.casts:contains(msg_id) then msg = msg:gsub('${actor} casts ', '${actor} cast ') if msg_id == 83 then msg = msg:gsub('${actor} successfully removes ' , '${actor} successfully remove ') elseif msg_id == 572 or msg_id == 642 then msg = msg:gsub('${actor} absorbs ' , '${actor} absorb ') end elseif replacements_map.actor.readies:contains(msg_id) then msg = msg:gsub('${actor} readies ' , '${actor} ready ') elseif replacements_map.actor.recovers:contains(msg_id) then msg = msg:gsub('${actor} recovers ' , '${actor} recover ') elseif replacements_map.actor.gains:contains(msg_id) then msg = msg:gsub('${actor} gains ', '${actor} gain ') elseif replacements_map.actor.apos:contains(msg_id) then msg = msg:gsub('${actor}\'s ', '${actor}\' ') if msg_id == 33 then msg = msg:gsub('${actor} takes ' , '${actor} take ') elseif msg_id == 606 then msg = msg:gsub('${actor} recovers ' , '${actor} recover ') elseif msg_id == 799 then msg = msg:gsub('${actor} is ' , '${actor} are ') end elseif replacements_map.actor.uses:contains(msg_id) then msg = msg:gsub('${actor} uses ' , '${actor} use ') if msg_id == 122 then msg = msg:gsub('${actor} recovers ' , '${actor} recover ') elseif msg_id == 123 then msg = msg:gsub('${actor} successfully removes ' , '${actor} successfully remove ') elseif msg_id == 126 or msg_id == 136 or msg_id == 528 then msg = msg:gsub('${actor}\'s ', '${actor}\' ') elseif msg_id == 137 or msg_id == 153 then msg = msg:gsub('${actor} fails ' , '${actor} fail ') elseif msg_id == 139 then msg = msg:gsub(' but finds nothing' , ' but find nothing') elseif msg_id == 140 then msg = msg:gsub(' and finds a ${item2}' , ' and find a ${item2}') elseif msg_id == 158 then msg = msg:gsub('${ability}, but misses' , '${ability}, but miss') elseif msg_id == 585 then msg = msg:gsub('${actor} is ' , '${actor} are ') elseif msg_id == 674 then msg = msg:gsub(' and finds ${number}' , ' and find ${number}') elseif msg_id == 780 then msg = msg:gsub('${actor} takes ' , '${actor} take ') elseif replacements_map.actor.steals:contains(msg_id) then msg = msg:gsub('${actor} steals ' , '${actor} steal ') elseif replacements_map.actor.butmissestarget:contains(msg_id) then msg = msg:gsub(' but misses ${target}' , ' but miss ${target}') end elseif replacements_map.actor.is:contains(msg_id) then msg = msg:gsub('${actor} is ' , '${actor} are ') elseif replacements_map.actor.learns:contains(msg_id) then msg = msg:gsub('${actor} learns ' , '${actor} learn ') elseif replacements_map.actor.has:contains(msg_id) then msg = msg:gsub('${actor} has ' , '${actor} have ') elseif replacements_map.actor.obtains:contains(msg_id) then msg = msg:gsub('${actor} obtains ' , '${actor} obtain ') elseif replacements_map.actor.does:contains(msg_id) then msg = msg:gsub('${actor} does ' , '${actor} do ') elseif replacements_map.actor.leads:contains(msg_id) then msg = msg:gsub('${actor} leads ' , '${actor} lead ') elseif replacements_map.actor.eats:contains(msg_id) then msg = msg:gsub('${actor} eats ' , '${actor} eat ') if msg_id == 604 then msg = msg:gsub(' but finds nothing' , ' but find nothing') end elseif replacements_map.actor.earns:contains(msg_id) then msg = msg:gsub('${actor} earns ' , '${actor} earn ') end end return msg end function plural_target(msg, msg_id) if msg then if msg_id == 282 then msg = msg:gsub('${target} evades', '${target} evade') elseif msg_id == 359 then msg = msg:gsub('${target} narrowly escapes ', '${target} narrowly escape ') elseif msg_id == 419 then msg = msg:gsub('${target} learns ', '${target} learn ') elseif msg_id == 671 then msg = msg:gsub('${target} now has ', '${target} now have ') elseif msg_id == 764 then msg = msg:gsub('${target} feels ', '${target} feel ') elseif replacements_map.target.takes:contains(msg_id) then msg = msg:gsub('${target} takes ', '${target} take ') if msg_id == 197 then msg = msg:gsub('${target} resists', '${target} resist') end elseif replacements_map.target.is:contains(msg_id) then msg = msg:gsub('${target} is ', '${target} are ') elseif replacements_map.target.recovers:contains(msg_id) then msg = msg:gsub('${target} recovers ', '${target} recover ') elseif replacements_map.target.apos:contains(msg_id) then --coincidence in 439 and 440 msg = msg:gsub('${target}\'s ', targets_condensed and '${target} ' or '${target}\' ') if msg_id == 439 or msg_id == 440 then msg = msg:gsub('${target} regains ', '${target} regain ') end elseif replacements_map.target.falls:contains(msg_id) then msg = msg:gsub('${target} falls ', '${target} fall ') elseif replacements_map.target.uses:contains(msg_id) then msg = msg:gsub('${target} uses ', '${target} use ') elseif replacements_map.target.resists:contains(msg_id) then msg = msg:gsub('${target} resists', '${target} resist') elseif replacements_map.target.vanishes:contains(msg_id) then msg = msg:gsub('${target} vanishes', '${target} vanish') elseif replacements_map.target.receives:contains(msg_id) then msg = msg:gsub('${target} receives ', '${target} receive ') elseif replacements_map.target.seems:contains(msg_id) then msg = msg:gsub('${target} seems ${skill}', '${target} seem ${skill}') if msg_id ~= 174 then msg = msg:gsub('${lb}It seems to have ', '${lb}They seem to have ') end elseif replacements_map.target.gains:contains(msg_id) then msg = msg:gsub('${target} gains ', '${target} gain ') elseif replacements_map.target.regains:contains(msg_id) then msg = msg:gsub('${target} regains ', '${target} regain ') elseif replacements_map.target.obtains:contains(msg_id) then msg = msg:gsub('${target} obtains ', '${target} obtain ') elseif replacements_map.target.loses:contains(msg_id) then msg = msg:gsub('${target} loses ', '${target} lose ') elseif replacements_map.target.was:contains(msg_id) then msg = msg:gsub('${target} was ', '${target} were ') elseif replacements_map.target.has:contains(msg_id) then msg = msg:gsub('${target} has ', '${target} have ') elseif replacements_map.target.compresists:contains(msg_id) then msg = msg:gsub('${target} completely resists ', '${target} completely resist ') end end return msg end function clean_msg(msg, msg_id) if msg then msg = msg :gsub(' The ', ' the ') :gsub(': the ', ': The ') :gsub('! the ', '! The ') if replacements_map.the.point:contains(msg_id) then msg = msg:gsub('%. the ', '. The ') end end return msg end function grammatical_number_fix(msg, number, msg_id) if msg then if number == 1 then if replacements_map.number.points:contains(msg_id) then msg = msg:gsub(' points', ' point') elseif msg_id == 411 then msg = msg:gsub('${number} Ballista Points', '${number} Ballista Point') elseif msg_id == 589 then msg = msg:gsub('healed of ${number} status ailments', 'healed of ${number} status ailment') elseif msg_id == 778 then msg = msg:gsub('magical effects from', 'magical effect from') end else if replacements_map.number.absorbs:contains(msg_id) then msg = msg:gsub(' absorbs', ' absorb') elseif msg_id == 133 then msg = msg:gsub(' Petra', ' Petras') elseif replacements_map.number.attributes:contains(msg_id) then msg = msg:gsub('attributes is', 'attributes are') elseif replacements_map.number.status:contains(msg_id) then msg = msg:gsub('status effect is', 'status effects are') elseif msg_id == 557 then msg = msg:gsub('piece', 'pieces') elseif msg_id == 560 then msg = msg:gsub('Finishing move now ', 'Finishing moves now ') end if replacements_map.number.disappears:contains(msg_id) then msg = msg:gsub('disappears', 'disappear') end end end return msg end function item_article_fix(id,id2,msg) if id then if string.gmatch(msg, ' a ${item}') then local article = res.items_grammar[id] and res.items_grammar[id].article if article == 1 then msg = string.gsub(msg,' a ${item}',' an ${item}') end end end if id2 then if string.gmatch(msg, ' a ${item2}') then local article = res.items_grammar[id2] and res.items_grammar[id2].article if article == 1 then msg = string.gsub(msg,' a ${item2}',' an ${item2}') end end end return msg end function add_item_article(id) local article = '' local article_type = res.items_grammar[id] and res.items_grammar[id].article or nil if id then if article_type == 2 then article = 'pair of ' elseif article_type == 3 then article = 'suit of ' end end return article end function send_delayed_message(color,msg) local message = msg :gsub('${count}', item_quantity.count) windower.add_to_chat(color,message) item_quantity.id = 0 item_quantity.count = '' parse_quantity = false end