mirror of
https://github.com/OTCv8/otclientv8.git
synced 2025-10-20 14:43:27 +02:00
Updated to OTCv8 3.1 rev 112
This commit is contained in:
@@ -1,105 +0,0 @@
|
||||
AlarmsWindow < MainWindow
|
||||
!text: tr('Alarms')
|
||||
size: 270 200
|
||||
@onEscape: self:hide()
|
||||
|
||||
BotSwitch
|
||||
id: playerAttack
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: parent.top
|
||||
text-align: center
|
||||
text: Player Attack
|
||||
|
||||
BotSwitch
|
||||
id: playerDetected
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.horizontalCenter
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 4
|
||||
text-align: center
|
||||
text: Player Detected
|
||||
|
||||
CheckBox
|
||||
id: playerDetectedLogout
|
||||
anchors.top: playerDetected.top
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
margin-left: 4
|
||||
text: Logout
|
||||
|
||||
BotSwitch
|
||||
id: creatureDetected
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: playerDetected.bottom
|
||||
margin-top: 4
|
||||
text-align: center
|
||||
text: Creature Detected
|
||||
|
||||
BotSwitch
|
||||
id: healthBelow
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.horizontalCenter
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Health < 50%
|
||||
|
||||
HorizontalScrollBar
|
||||
id: healthValue
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
anchors.top: healthBelow.top
|
||||
margin-left: 3
|
||||
margin-top: 2
|
||||
minimum: 1
|
||||
maximum: 100
|
||||
step: 1
|
||||
|
||||
BotSwitch
|
||||
id: manaBelow
|
||||
anchors.left: parent.left
|
||||
anchors.top: healthBelow.bottom
|
||||
anchors.right: parent.horizontalCenter
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Mana < 50%
|
||||
|
||||
HorizontalScrollBar
|
||||
id: manaValue
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
anchors.top: manaBelow.top
|
||||
margin-left: 3
|
||||
margin-top: 2
|
||||
minimum: 1
|
||||
maximum: 100
|
||||
step: 1
|
||||
|
||||
BotSwitch
|
||||
id: privateMessage
|
||||
anchors.left: parent.left
|
||||
anchors.top: manaBelow.bottom
|
||||
anchors.right: parent.right
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Private Message
|
||||
|
||||
HorizontalSeparator
|
||||
id: separator
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: closeButton.top
|
||||
margin-bottom: 8
|
||||
|
||||
Button
|
||||
id: closeButton
|
||||
!text: tr('Close')
|
||||
font: cipsoftFont
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
size: 45 21
|
||||
margin-top: 15
|
||||
margin-right: 5
|
@@ -1,437 +0,0 @@
|
||||
setDefaultTab("Main")
|
||||
-- first, the variables
|
||||
local launchTime = now
|
||||
local startExp = exp()
|
||||
local dmgTable = {}
|
||||
local healTable = {}
|
||||
local expTable = {}
|
||||
local totalDmg = 0
|
||||
local totalHeal = 0
|
||||
local dmgDistribution = {}
|
||||
local first = "-"
|
||||
local second = "-"
|
||||
local third = "-"
|
||||
local bestHit = 0
|
||||
local bestHeal = 0
|
||||
local lootedItems = {}
|
||||
local useData = {}
|
||||
local usedItems ={}
|
||||
|
||||
local resetSessionData = function()
|
||||
launchTime = now
|
||||
startExp = exp()
|
||||
dmgTable = {}
|
||||
healTable = {}
|
||||
expTable = {}
|
||||
totalDmg = 0
|
||||
totalHeal = 0
|
||||
dmgDistribution = {}
|
||||
first = "-"
|
||||
second = "-"
|
||||
third = "-"
|
||||
bestHit = 0
|
||||
bestHeal = 0
|
||||
lootedItems = {}
|
||||
useData = {}
|
||||
usedItems ={}
|
||||
refreshLoot()
|
||||
refreshWaste()
|
||||
end
|
||||
|
||||
function format_thousand(v)
|
||||
if not v then return 0 end
|
||||
local s = string.format("%d", math.floor(v))
|
||||
local pos = string.len(s) % 3
|
||||
if pos == 0 then pos = 3 end
|
||||
return string.sub(s, 1, pos)
|
||||
.. string.gsub(string.sub(s, pos+1), "(...)", ".%1")
|
||||
end
|
||||
|
||||
local expGained = function()
|
||||
return exp() - startExp
|
||||
end
|
||||
local expLeft = function()
|
||||
local level = lvl()+1
|
||||
return math.floor((50*level*level*level)/3 - 100*level*level + (850*level)/3 - 200) - exp()
|
||||
end
|
||||
|
||||
local niceTimeFormat = function(v) -- v in seconds
|
||||
local hours = string.format("%02.f", math.floor(v/3600))
|
||||
local mins = string.format("%02.f", math.floor(v/60 - (hours*60)))
|
||||
return hours .. ":" .. mins .. "h"
|
||||
end
|
||||
local uptime
|
||||
local sessionTime = function()
|
||||
uptime = math.floor((now - launchTime)/1000)
|
||||
return niceTimeFormat(uptime)
|
||||
end
|
||||
sessionTime()
|
||||
|
||||
local expPerHour = function(calculation)
|
||||
local r = 0
|
||||
if #expTable > 0 then
|
||||
r = exp() - expTable[1]
|
||||
else
|
||||
return "-"
|
||||
end
|
||||
|
||||
if uptime < 15*60 then
|
||||
r = math.ceil((r/uptime)*60*60)
|
||||
else
|
||||
r = math.ceil(r*8)
|
||||
end
|
||||
if calculation then
|
||||
return r
|
||||
else
|
||||
return format_thousand(r)
|
||||
end
|
||||
end
|
||||
|
||||
local timeToLevel = function()
|
||||
local t = 0
|
||||
if expPerHour(true) == 0 or expPerHour() == "-" then
|
||||
return "-"
|
||||
else
|
||||
t = expLeft()/expPerHour(true)
|
||||
return niceTimeFormat(math.ceil(t*60*60))
|
||||
end
|
||||
end
|
||||
|
||||
local sumT = function(t)
|
||||
local s = 0
|
||||
for i,v in pairs(t) do
|
||||
s = s + v.d
|
||||
end
|
||||
return s
|
||||
end
|
||||
|
||||
local valueInSeconds = function(t)
|
||||
local d = 0
|
||||
local time = 0
|
||||
if #t > 0 then
|
||||
for i, v in ipairs(t) do
|
||||
if now - v.t <= 3000 then
|
||||
if time == 0 then
|
||||
time = v.t
|
||||
end
|
||||
d = d + v.d
|
||||
else
|
||||
table.remove(t, 1)
|
||||
end
|
||||
end
|
||||
end
|
||||
return math.ceil(d/((now-time)/1000))
|
||||
end
|
||||
|
||||
local regex = "You lose ([0-9]*) hitpoints due to an attack by ([a-z]*) ([a-z A-z-]*)"
|
||||
onTextMessage(function(mode, text)
|
||||
if mode == 21 then -- damage dealt
|
||||
totalDmg = totalDmg + getFirstNumberInText(text)
|
||||
table.insert(dmgTable, {d = getFirstNumberInText(text), t = now})
|
||||
if getFirstNumberInText(text) > bestHit then
|
||||
bestHit = getFirstNumberInText(text)
|
||||
end
|
||||
end
|
||||
if mode == 23 then -- healing
|
||||
totalHeal = totalHeal + getFirstNumberInText(text)
|
||||
table.insert(healTable, {d = getFirstNumberInText(text), t = now})
|
||||
if getFirstNumberInText(text) > bestHeal then
|
||||
bestHeal = getFirstNumberInText(text)
|
||||
end
|
||||
end
|
||||
|
||||
-- damage distribution part
|
||||
if text:find("You lose") then
|
||||
local data = regexMatch(text, regex)[1]
|
||||
if data then
|
||||
local monster = data[4]
|
||||
local val = data[2]
|
||||
table.insert(dmgDistribution, {v=val,m=monster,t=now})
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
|
||||
-- tables maintance
|
||||
macro(500, function()
|
||||
local dmgFinal = {}
|
||||
local labelTable = {}
|
||||
local dmgSum = 0
|
||||
table.insert(expTable, exp())
|
||||
if #expTable > 15*60 then
|
||||
for i,v in pairs(expTable) do
|
||||
if i == 1 then
|
||||
table.remove(expTable, i)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
for i,v in pairs(dmgDistribution) do
|
||||
if now - v.t > 60*1000*10 then
|
||||
table.remove(dmgDistribution, i)
|
||||
else
|
||||
dmgSum = dmgSum + v.v
|
||||
if not dmgFinal[v.m] then
|
||||
dmgFinal[v.m] = v.v
|
||||
else
|
||||
dmgFinal[v.m] = dmgFinal[v.m] + v.v
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if not dmgFinal[1] then
|
||||
first = "-"
|
||||
end
|
||||
if not dmgFinal[2] then
|
||||
second = "-"
|
||||
end
|
||||
if not dmgFinal[3] then
|
||||
third = "-"
|
||||
end
|
||||
|
||||
local iter = 0
|
||||
for k,v in pairs(dmgFinal) do
|
||||
table.insert(labelTable, {m=k, d=tonumber(v)})
|
||||
end
|
||||
|
||||
table.sort(labelTable, function(a,b) return a.d > b.d end)
|
||||
|
||||
for i,v in pairs(labelTable) do
|
||||
local label = v.m .. ": " .. math.floor((v.d/dmgSum)*100) .. "%"
|
||||
if i == 1 then
|
||||
first = label
|
||||
elseif i == 2 then
|
||||
second = label
|
||||
elseif i == 3 then
|
||||
third = label
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
-- visuals
|
||||
UI.Separator()
|
||||
local main = UI.createWidget("MainAnalyzer")
|
||||
local ui = UI.createWidget("HuntingAnalyzer")
|
||||
local ui2 = UI.createWidget("LootAnalyzer")
|
||||
ui:hide()
|
||||
ui2:hide()
|
||||
|
||||
function refreshLoot()
|
||||
for i, child in pairs(ui2.List:getChildren()) do
|
||||
child:destroy()
|
||||
end
|
||||
|
||||
for k,v in pairs(lootedItems) do
|
||||
local label = g_ui.createWidget("LootItemLabel", ui2.List)
|
||||
label:setText(v .. "x " .. k)
|
||||
end
|
||||
end
|
||||
|
||||
function refreshWaste()
|
||||
for i, child in pairs(ui2.supplyList:getChildren()) do
|
||||
child:destroy()
|
||||
end
|
||||
|
||||
for k,v in pairs(usedItems) do
|
||||
local label = g_ui.createWidget("LootItemLabel", ui2.supplyList)
|
||||
label:setText(v .. "x " .. k)
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
-- loot analyzer
|
||||
-- adding
|
||||
local containers = CaveBot.GetLootContainers()
|
||||
local lastCap = freecap()
|
||||
onAddItem(function(container, slot, item, oldItem)
|
||||
if not table.find(containers, container:getContainerItem():getId()) then return end
|
||||
if isInPz() then return end
|
||||
if slot > 0 then return end
|
||||
if freecap() >= lastCap then return end
|
||||
local name = item:getId() == 3031 and "gold coin" or item:getId() == 3035 and "platinum coin" or item:getId() == 3043 and "crystal coin" or item:getMarketData().name
|
||||
|
||||
if not lootedItems[name] then
|
||||
lootedItems[name] = item:getCount()
|
||||
else
|
||||
lootedItems[name] = lootedItems[name] + item:getCount()
|
||||
end
|
||||
refreshLoot()
|
||||
end)
|
||||
|
||||
onContainerUpdateItem(function(container, slot, item, oldItem)
|
||||
if not table.find(containers, container:getContainerItem():getId()) then return end
|
||||
if not oldItem then return end
|
||||
if isInPz() then return end
|
||||
if freecap() == lastCap then return end
|
||||
|
||||
local name = item:getId() == 3031 and "gold coin" or item:getId() == 3035 and "platinum coin" or item:getId() == 3043 and "crystal coin" or item:getMarketData().name
|
||||
local amount = item:getCount() - oldItem:getCount()
|
||||
|
||||
if not lootedItems[name] then
|
||||
lootedItems[name] = amount
|
||||
else
|
||||
lootedItems[name] = lootedItems[name] + amount
|
||||
end
|
||||
refreshLoot()
|
||||
end)
|
||||
|
||||
-- waste
|
||||
local regex3 = [[\d ([a-z A-Z]*)s...]]
|
||||
useData = {}
|
||||
usedItems = {}
|
||||
onTextMessage(function(mode, text)
|
||||
text = text:lower()
|
||||
if not text:find("using one of") then return end
|
||||
|
||||
local amount = getFirstNumberInText(text)
|
||||
local re = regexMatch(text, regex3)
|
||||
local name = re[1][2]
|
||||
|
||||
if not useData[name] then
|
||||
useData[name] = amount
|
||||
else
|
||||
if math.abs(useData[name]-amount) == 1 then
|
||||
useData[name] = amount
|
||||
if not usedItems[name] then
|
||||
usedItems[name] = 1
|
||||
else
|
||||
usedItems[name] = usedItems[name] + 1
|
||||
end
|
||||
end
|
||||
end
|
||||
refreshWaste()
|
||||
end)
|
||||
|
||||
function toggleBetween()
|
||||
if ui:isVisible() then
|
||||
ui:hide()
|
||||
ui2:show()
|
||||
main.change:setText("Hunt")
|
||||
else
|
||||
ui:show()
|
||||
ui2:hide()
|
||||
main.change:setText("Loot")
|
||||
end
|
||||
end
|
||||
|
||||
function hideAll()
|
||||
if not ui:isVisible() and not ui2:isVisible() then
|
||||
ui:show()
|
||||
ui2:hide()
|
||||
else
|
||||
ui:hide()
|
||||
ui2:hide()
|
||||
end
|
||||
end
|
||||
|
||||
main.reset.onClick = function(widget)
|
||||
resetSessionData()
|
||||
end
|
||||
main.toggle.onClick = function(widget)
|
||||
hideAll()
|
||||
end
|
||||
main.change.onClick = function(widget)
|
||||
toggleBetween()
|
||||
end
|
||||
|
||||
function hourVal(v)
|
||||
return (v/uptime)*3600
|
||||
end
|
||||
|
||||
local lootWorth
|
||||
local wasteWorth
|
||||
local balance
|
||||
local balanceDesc
|
||||
local hourDesc
|
||||
local desc
|
||||
local hour
|
||||
|
||||
|
||||
function bottingStats()
|
||||
lootWorth = 0
|
||||
wasteWorth = 0
|
||||
for k, v in pairs(lootedItems) do
|
||||
if LootItems[k] then
|
||||
lootWorth = lootWorth + (LootItems[k]*v)
|
||||
end
|
||||
end
|
||||
for k, v in pairs(usedItems) do
|
||||
if LootItems[k] then
|
||||
wasteWorth = wasteWorth + (LootItems[k]*v)
|
||||
end
|
||||
end
|
||||
balance = lootWorth - wasteWorth
|
||||
|
||||
return lootWorth, wasteWorth, balance
|
||||
end
|
||||
|
||||
function bottingLabels(lootWorth, wasteWorth, balance)
|
||||
balanceDesc = nil
|
||||
hourDesc = nil
|
||||
desc = nil
|
||||
|
||||
if balance >= 1000000 or balance <= -1000000 then
|
||||
desc = balance / 1000000
|
||||
balanceDesc = math.floor(desc) .. "." .. math.floor(desc * 10) % 10 .. "kk"
|
||||
elseif balance >= 1000 or balance <= -1000 then
|
||||
desc = balance / 1000
|
||||
balanceDesc = math.floor(desc) .. "." .. math.floor(desc * 10) % 10 .."k"
|
||||
else
|
||||
balanceDesc = balance .. "gp"
|
||||
end
|
||||
|
||||
hour = hourVal(balance)
|
||||
if hour >= 1000000 or hour <= -1000000 then
|
||||
desc = balance / 1000000
|
||||
hourDesc = math.floor(hourVal(desc)) .. "." .. math.floor(hourVal(desc) * 10) % 10 .. "kk/h"
|
||||
elseif hour >= 1000 or hour <= -1000 then
|
||||
desc = balance / 1000
|
||||
hourDesc = math.floor(hourVal(desc)) .. "." .. math.floor(hourVal(desc) * 10) % 10 .. "k/h"
|
||||
else
|
||||
hourDesc = math.floor(hourVal(balance)) .. "gp/h"
|
||||
end
|
||||
|
||||
return balanceDesc, hourDesc
|
||||
end
|
||||
|
||||
function reportStats()
|
||||
local lootWorth, wasteWorth, balance = bottingStats()
|
||||
local balanceDesc, hourDesc = bottingLabels(lootWorth, wasteWorth, balance)
|
||||
|
||||
local a, b, c
|
||||
|
||||
a = "Session Time: " .. sessionTime() .. ", Exp Gained: " .. format_thousand(expGained()) .. ", Exp/h: " .. expPerHour()
|
||||
b = " | Balance: " .. balanceDesc .. " (" .. hourDesc .. ")"
|
||||
c = a..b
|
||||
|
||||
return c
|
||||
end
|
||||
|
||||
macro(500, function()
|
||||
local lootWorth, wasteWorth, balance = bottingStats()
|
||||
local balanceDesc, hourDesc = bottingLabels(lootWorth, wasteWorth, balance)
|
||||
-- hunting
|
||||
ui.one:setText(sessionTime())
|
||||
ui.two:setText(format_thousand(expGained()))
|
||||
ui.three:setText(expPerHour())
|
||||
ui.four:setText(timeToLevel())
|
||||
ui.five:setText(format_thousand(burstDamageValue()))
|
||||
ui.six:setText(format_thousand(totalDmg))
|
||||
ui.seven:setText(format_thousand(valueInSeconds(dmgTable)))
|
||||
ui.eight:setText(format_thousand(bestHit))
|
||||
ui.nine:setText(format_thousand(totalHeal))
|
||||
ui.ten:setText(format_thousand(valueInSeconds(healTable)))
|
||||
ui.eleven:setText(format_thousand(bestHeal))
|
||||
ui.dOne:setText(first)
|
||||
ui.dTwo:setText(second)
|
||||
ui.dThree:setText(third)
|
||||
|
||||
-- loot
|
||||
ui2.loot:setText(format_thousand(lootWorth))
|
||||
ui2.lootHour:setText(format_thousand(hourVal(lootWorth)))
|
||||
ui2.supplies:setText(format_thousand(wasteWorth))
|
||||
ui2.suppliesHour:setText(format_thousand(hourVal(wasteWorth)))
|
||||
ui.balance:setColor(balance >= 0 and "green" or "red")
|
||||
ui.balance:setText(balanceDesc .. " (" .. hourDesc .. ")")
|
||||
end)
|
||||
|
@@ -1,367 +0,0 @@
|
||||
LootItemLabel < Label
|
||||
opacity: 0.87
|
||||
text-offset: 2 0
|
||||
focusable: false
|
||||
height: 16
|
||||
|
||||
MainAnalyzer < Panel
|
||||
height: 45
|
||||
padding: 4
|
||||
|
||||
BotButton
|
||||
id: toggle
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
text: Session Analyzer
|
||||
|
||||
BotButton
|
||||
id: reset
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 4
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.horizontalCenter
|
||||
margin-right: 2
|
||||
text: Reset
|
||||
|
||||
BotButton
|
||||
id: change
|
||||
anchors.top: toggle.bottom
|
||||
margin-top: 4
|
||||
anchors.left: parent.horizontalCenter
|
||||
margin-left: 2
|
||||
anchors.right: toggle.right
|
||||
text-align: center
|
||||
text: Loot
|
||||
|
||||
HuntingAnalyzer < Panel
|
||||
height: 275
|
||||
padding: 5
|
||||
|
||||
Label
|
||||
id: SessionLabel
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text: Session:
|
||||
|
||||
Label
|
||||
id: XpGainLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: XP Gain:
|
||||
|
||||
Label
|
||||
id: XpHourLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: XP/h:
|
||||
|
||||
Label
|
||||
id: NextLevelLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: Next Level:
|
||||
|
||||
Label
|
||||
id: BalanceLabel
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
anchors.left: parent.left
|
||||
text: Balance
|
||||
|
||||
Label
|
||||
id: BurstDamageLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: Burst Damage:
|
||||
|
||||
Label
|
||||
id: DamageDealtLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: Damage Dealt:
|
||||
|
||||
Label
|
||||
id: DPSLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: DPS:
|
||||
|
||||
Label
|
||||
id: BestHitLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: Best Hit:
|
||||
|
||||
Label
|
||||
id: HealingDoneLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: Healing Done:
|
||||
|
||||
Label
|
||||
id: HPSLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: HPS:
|
||||
|
||||
Label
|
||||
id: BestHealLabel
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-top: 5
|
||||
text: Best Heal:
|
||||
|
||||
Label
|
||||
id: one
|
||||
anchors.right: parent.right
|
||||
anchors.verticalCenter: SessionLabel.verticalCenter
|
||||
text-align: right
|
||||
text: 00:00h
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: two
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: three
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: -
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: four
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: -
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: balance
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
text: 0
|
||||
text-align: right
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: five
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: six
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: -
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: seven
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: eight
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: nine
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: ten
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: eleven
|
||||
anchors.right: parent.right
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
text-align: right
|
||||
text: 0
|
||||
width: 150
|
||||
|
||||
HorizontalSeparator
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
|
||||
Label
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
text-align: center
|
||||
text: Damage Distribution
|
||||
|
||||
Label
|
||||
id: dOne
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
text-align: center
|
||||
text: -
|
||||
|
||||
Label
|
||||
id: dTwo
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
text-align: center
|
||||
text: -
|
||||
|
||||
Label
|
||||
id: dThree
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
text-align: center
|
||||
text: -
|
||||
|
||||
LootAnalyzer < Panel
|
||||
height: 275
|
||||
padding: 4
|
||||
|
||||
Label
|
||||
id: first
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text: Supplies
|
||||
|
||||
Label
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
anchors.left: parent.left
|
||||
text: Supplies/h
|
||||
|
||||
TextList
|
||||
id: supplyList
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
height: 50
|
||||
vertical-scrollbar: supplyListScrollBar
|
||||
|
||||
Label
|
||||
id: second
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
anchors.left: parent.left
|
||||
text: Loot
|
||||
|
||||
Label
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 5
|
||||
anchors.left: parent.left
|
||||
text: Loot/h
|
||||
|
||||
Label
|
||||
id: supplies
|
||||
anchors.top: parent.top
|
||||
anchors.right: parent.right
|
||||
width: 150
|
||||
text: 0
|
||||
text-align: right
|
||||
|
||||
Label
|
||||
id: suppliesHour
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
text: 0
|
||||
text-align: right
|
||||
width: 150
|
||||
|
||||
Label
|
||||
id: loot
|
||||
anchors.top: second.top
|
||||
anchors.right: parent.right
|
||||
width: 150
|
||||
text: 0
|
||||
text-align: right
|
||||
|
||||
Label
|
||||
id: lootHour
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.right
|
||||
margin-top: 5
|
||||
text: 0
|
||||
text-align: right
|
||||
width: 150
|
||||
|
||||
TextList
|
||||
id: List
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
height: 120
|
||||
vertical-scrollbar: ListScrollBar
|
||||
|
||||
VerticalScrollBar
|
||||
id: ListScrollBar
|
||||
anchors.top: List.top
|
||||
anchors.bottom: List.bottom
|
||||
anchors.right: List.right
|
||||
step: 14
|
||||
pixels-scroll: true
|
||||
|
||||
VerticalScrollBar
|
||||
id: supplyListScrollBar
|
||||
anchors.top: supplyList.top
|
||||
anchors.bottom: supplyList.bottom
|
||||
anchors.right: supplyList.right
|
||||
step: 14
|
||||
pixels-scroll: true
|
@@ -167,7 +167,7 @@ CaveBot.registerAction("goto", "green", function(value, retries, prev)
|
||||
return true -- already at position
|
||||
end
|
||||
-- check if there's a path to that place, ignore creatures and fields
|
||||
local path = findPath(playerPos, pos, maxDist, { ignoreNonPathable = true, precision = 1, ignoreCreatures = true })
|
||||
local path = findPath(playerPos, pos, maxDist, { ignoreNonPathable = true, precision = 1, ignoreCreatures = true, allowUnseen = true, allowOnlyVisibleTiles = false })
|
||||
if not path then
|
||||
return false -- there's no way
|
||||
end
|
||||
@@ -206,7 +206,7 @@ CaveBot.registerAction("goto", "green", function(value, retries, prev)
|
||||
end
|
||||
|
||||
-- try to find path, don't ignore creatures, ignore fields
|
||||
if CaveBot.walkTo(pos, maxDist, { ignoreNonPathable = true }) then
|
||||
if CaveBot.walkTo(pos, maxDist, { ignoreNonPathable = true, allowUnseen = true, allowOnlyVisibleTiles = false }) then
|
||||
return "retry"
|
||||
end
|
||||
|
||||
@@ -216,7 +216,7 @@ CaveBot.registerAction("goto", "green", function(value, retries, prev)
|
||||
if stairs then
|
||||
precison = 0
|
||||
end
|
||||
if CaveBot.walkTo(pos, 50, { ignoreNonPathable = true, precision = precison }) then
|
||||
if CaveBot.walkTo(pos, 50, { ignoreNonPathable = true, precision = precison, allowUnseen = true, allowOnlyVisibleTiles = false }) then
|
||||
return "retry"
|
||||
end
|
||||
end
|
||||
@@ -230,7 +230,7 @@ CaveBot.registerAction("goto", "green", function(value, retries, prev)
|
||||
end
|
||||
|
||||
-- everything else failed, try to walk ignoring creatures, maybe will work
|
||||
CaveBot.walkTo(pos, maxDist, { ignoreNonPathable = true, precision = 1, ignoreCreatures = true })
|
||||
CaveBot.walkTo(pos, maxDist, { ignoreNonPathable = true, precision = 1, ignoreCreatures = true, allowUnseen = true, allowOnlyVisibleTiles = false })
|
||||
return "retry"
|
||||
end)
|
||||
|
@@ -30,7 +30,7 @@ cavebotMacro = macro(20, function()
|
||||
end
|
||||
|
||||
if CaveBot.doWalking() then
|
||||
return -- executing walking
|
||||
return -- executing walking3
|
||||
end
|
||||
|
||||
local actions = ui.list:getChildCount()
|
||||
@@ -185,6 +185,20 @@ CaveBot.setOff = function(val)
|
||||
config.setOff()
|
||||
end
|
||||
|
||||
CaveBot.getCurrentProfile = function()
|
||||
return storage._configs.cavebot_configs.selected
|
||||
end
|
||||
|
||||
local botConfigName = modules.game_bot.contentsPanel.config:getCurrentOption().text
|
||||
CaveBot.setCurrentProfile = function(name)
|
||||
if not g_resources.fileExists("/bot/"..botConfigName.."/cavebot_configs/"..name..".cfg") then
|
||||
return warn("there is no cavebot profile with that name!")
|
||||
end
|
||||
CaveBot.setOff()
|
||||
storage._configs.cavebot_configs.selected = name
|
||||
CaveBot.setOn()
|
||||
end
|
||||
|
||||
CaveBot.delay = function(value)
|
||||
cavebotMacro.delay = math.max(cavebotMacro.delay or 0, now + value)
|
||||
end
|
@@ -1,13 +1,11 @@
|
||||
CaveBot.Extensions.Depositor = {}
|
||||
|
||||
--local variables
|
||||
local closedContainers = false
|
||||
local reopenedContainers = false
|
||||
local destination = nil
|
||||
local lootTable = nil
|
||||
local reopenedContainers = false
|
||||
|
||||
local function resetCache()
|
||||
closedContainers = false
|
||||
reopenedContainers = false
|
||||
destination = nil
|
||||
lootTable = nil
|
||||
@@ -41,21 +39,11 @@ CaveBot.Extensions.Depositor.setup = function()
|
||||
|
||||
-- backpacks etc
|
||||
if value:lower() == "yes" then
|
||||
-- reopening backpacks
|
||||
if not reopenedContainers then
|
||||
if not closedContainers then
|
||||
if not CaveBot.CloseLootContainer() then
|
||||
return "retry"
|
||||
else
|
||||
closedContainers = true
|
||||
end
|
||||
else
|
||||
if not CaveBot.OpenLootContainer() then
|
||||
return "retry"
|
||||
else
|
||||
reopenedContainers = true
|
||||
end
|
||||
end
|
||||
CaveBot.CloseAllLootContainers()
|
||||
delay(3000)
|
||||
reopenedContainers = true
|
||||
return "retry"
|
||||
end
|
||||
-- open next backpacks if no more loot
|
||||
if not CaveBot.HasLootItems() then
|
||||
@@ -70,12 +58,14 @@ CaveBot.Extensions.Depositor.setup = function()
|
||||
return "retry"
|
||||
end
|
||||
end
|
||||
-- couldn't find next container, so we done
|
||||
print("CaveBot[Depositor]: all items stashed, no backpack to open next, proceeding")
|
||||
resetCache()
|
||||
return true
|
||||
end
|
||||
end
|
||||
-- couldn't find next container, so we done
|
||||
print("CaveBot[Depositor]: all items stashed, no backpack to open next, proceeding")
|
||||
CaveBot.CloseAllLootContainers()
|
||||
delay(3000)
|
||||
resetCache()
|
||||
return true
|
||||
end
|
||||
end
|
||||
|
@@ -35,7 +35,7 @@ end
|
||||
]])
|
||||
|
||||
addExampleFunction("Check for stamina and imbues", [[
|
||||
if stamina() < 900 or player:getSkillLevel(11) ~= 100 then CaveBot.setOff() return false else return true end
|
||||
if stamina() < 900 or player:getSkillLevel(11) == 0 then CaveBot.setOff() return false else return true end
|
||||
]])
|
||||
|
||||
addExampleFunction("buy 200 mana potion from npc Eryn", [[
|
||||
@@ -105,4 +105,10 @@ addExampleFunction("Logout", [[
|
||||
g_game.safeLogout()
|
||||
delay(1000)
|
||||
return "retry"
|
||||
]])
|
||||
|
||||
addExampleFunction("Close Loot Containers", [[
|
||||
CaveBot.CloseAllLootContainers()
|
||||
delay(3000)
|
||||
return true
|
||||
]])
|
@@ -5,6 +5,7 @@ local lureMax = 0
|
||||
local anchorPosition = nil
|
||||
local lastCall = now
|
||||
local delayFrom = nil
|
||||
local dynamicLureDelay = false
|
||||
|
||||
function getWalkableTilesCount(position)
|
||||
local count = 0
|
||||
@@ -140,6 +141,7 @@ TargetBot.Creature.walk = function(creature, config, targets)
|
||||
lureMax = config.lureMax
|
||||
end
|
||||
|
||||
dynamicLureDelay = config.dynamicLureDelay
|
||||
delayFrom = config.delayFrom
|
||||
|
||||
-- luring
|
||||
@@ -185,6 +187,7 @@ TargetBot.Creature.walk = function(creature, config, targets)
|
||||
end
|
||||
end
|
||||
|
||||
--target only movement
|
||||
if config.avoidAttacks then
|
||||
local diffx = cpos.x - pos.x
|
||||
local diffy = cpos.y - pos.y
|
||||
@@ -235,6 +238,6 @@ onPlayerPositionChange(function(newPos, oldPos)
|
||||
if not lureMax then return end
|
||||
if storage.TargetBotDelayWhenPlayer then return end
|
||||
|
||||
if targetCount < (delayFrom or lureMax/2) or not target() then return end
|
||||
if dynamicLureDelay and targetCount < (delayFrom or lureMax/2) or not target() then return end
|
||||
CaveBot.delay(delayValue or 0)
|
||||
end)
|
@@ -203,6 +203,20 @@ TargetBot.setOff = function(val)
|
||||
config.setOff()
|
||||
end
|
||||
|
||||
TargetBot.getCurrentProfile = function()
|
||||
return storage._configs.targetbot_configs.selected
|
||||
end
|
||||
|
||||
local botConfigName = modules.game_bot.contentsPanel.config:getCurrentOption().text
|
||||
TargetBot.setCurrentProfile = function(name)
|
||||
if not g_resources.fileExists("/bot/"..botConfigName.."/targetbot_configs/"..name..".json") then
|
||||
return warn("there is no targetbot profile with that name!")
|
||||
end
|
||||
TargetBot.setOff()
|
||||
storage._configs.targetbot_configs.selected = name
|
||||
TargetBot.setOn()
|
||||
end
|
||||
|
||||
TargetBot.delay = function(value)
|
||||
targetbotMacro.delay = now + value
|
||||
end
|
@@ -1075,7 +1075,7 @@ function getBestTileByPattern(pattern, minHp, maxHp, safePattern, monsterNamesTa
|
||||
for i, tile in pairs(tiles) do
|
||||
local tPos = tile:getPosition()
|
||||
local distance = distanceFromPlayer(tPos)
|
||||
if tile:canShoot() and tile:isWalkable() and (not safePattern or distance < 4) then
|
||||
if tile:canShoot() and tile:isWalkable() and distance < 4 then
|
||||
local amount = getMonstersInArea(2, tPos, pattern, minHp, maxHp, safePattern, monsterNamesTable)
|
||||
if amount > targetTile.amount then
|
||||
targetTile = {amount=amount,pos=tPos}
|
||||
@@ -1161,7 +1161,7 @@ macro(100, function()
|
||||
if entry.enabled and manapercent() >= entry.mana then
|
||||
if (entry.spell and canCast(entry.spell, not currentSettings.ignoreMana, not currentSettings.Cooldown)) or (entry.itemId > 100 and (not currentSettings.Visible or findItem(entry.itemId))) then
|
||||
-- first PVP scenario
|
||||
if currentSettings.pvpMode and target():getHealthPercent() >= entry.minHp and target():getHealthPercent() <= entry.maxHp then
|
||||
if currentSettings.pvpMode and target():getHealthPercent() >= entry.minHp and target():getHealthPercent() <= entry.maxHp and target():canShoot() then
|
||||
if entry.category == 2 then
|
||||
return warn("[AttackBot] Area Runes cannot be used in PVP situation!")
|
||||
else
|
||||
@@ -1186,7 +1186,7 @@ macro(100, function()
|
||||
local anchorParam = (pattern == 2 or pattern == 6 or pattern == 7 or pattern > 9) and player or pos()
|
||||
local safe = currentSettings.PvpSafe and spellPatterns[pCat][entry.pattern][2] or false
|
||||
local monsterAmount = pCat ~= 8 and getMonstersInArea(entry.category, anchorParam, spellPatterns[pCat][entry.pattern][1], entry.minHp, entry.maxHp, safe, entry.monsters)
|
||||
if (pattern ~= 8 and (entry.orMore and monsterAmount >= entry.count or not entry.orMore and monsterAmount == entry.count)) or pattern == 8 and bestSide >= entry.count then
|
||||
if (pattern ~= 8 and (entry.orMore and monsterAmount >= entry.count or not entry.orMore and monsterAmount == entry.count)) or (pattern == 8 and bestSide >= entry.count and (not currentSettings.PvpSafe or getPlayers(2) == 0)) then
|
||||
return executeAttackBotAction(entry.category, attackData, entry.cooldown)
|
||||
end
|
||||
elseif entry.category == 2 then
|
@@ -235,7 +235,7 @@ Panel
|
||||
elseif config.cureElectrify and mana() >= config.electrifyCost and isEnergized() then say("exana vis")
|
||||
end
|
||||
end
|
||||
if (not config.ignoreInPz or not isInPz()) and config.holdUtura and mana() >= config.uturaCost and not hasPartyBuff() then say(config.uturaType)
|
||||
if (not config.ignoreInPz or not isInPz()) and config.holdUtura and mana() >= config.uturaCost and canCast(config.uturaType) and hppercent() < 90 then say(config.uturaType)
|
||||
elseif (not config.ignoreInPz or not isInPz()) and config.holdUtana and mana() >= config.utanaCost and (not utanaCast or (now - utanaCast > 120000)) then say("utana vid") utanaCast = now
|
||||
end
|
||||
end)
|
@@ -441,19 +441,19 @@ end
|
||||
|
||||
onContainerOpen(function(container, previousContainer)
|
||||
if renameContui.title:isOn() then
|
||||
if not container.window then return end
|
||||
local containerWindow = container.window
|
||||
if not previousContainer then
|
||||
if not container.window then return end
|
||||
containerWindow = container.window
|
||||
containerWindow:setContentHeight(34)
|
||||
local storageVal = config.list
|
||||
if storageVal and #storageVal > 0 then
|
||||
for _, entry in pairs(storageVal) do
|
||||
if entry.enabled and string.find(container:getContainerItem():getId(), entry.item) then
|
||||
if entry.min then
|
||||
containerWindow:minimize()
|
||||
end
|
||||
containerWindow:setText(entry.value)
|
||||
end
|
||||
local storageVal = config.list
|
||||
if storageVal and #storageVal > 0 then
|
||||
for _, entry in pairs(storageVal) do
|
||||
if entry.enabled and string.find(container:getContainerItem():getId(), entry.item) then
|
||||
if entry.min then
|
||||
containerWindow:minimize()
|
||||
end
|
||||
containerWindow:setText(entry.value)
|
||||
end
|
||||
end
|
||||
end
|
||||
@@ -476,7 +476,7 @@ local function properTable(t)
|
||||
return r
|
||||
end
|
||||
|
||||
macro(100, function()
|
||||
macro(500, function()
|
||||
if not config.sort and not config.purse then return end
|
||||
|
||||
local storageVal = config.list
|
||||
@@ -522,5 +522,5 @@ macro(100, function()
|
||||
if config.purse and config.forceOpen and not getContainerByItem(23396) then
|
||||
return use(getPurse())
|
||||
end
|
||||
delay(900)
|
||||
delay(1500)
|
||||
end)
|
@@ -1,3 +1,6 @@
|
||||
local standBySpells = false
|
||||
local standByItems = false
|
||||
|
||||
setDefaultTab("HP")
|
||||
healPanelName = "healbot"
|
||||
local ui = setupUI([[
|
||||
@@ -222,10 +225,14 @@ if rootWidget then
|
||||
local label = UI.createWidget("SpellEntry", healWindow.spells.spellList)
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
label.enabled.onClick = function(widget)
|
||||
standBySpells = false
|
||||
standByItems = false
|
||||
entry.enabled = not entry.enabled
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
end
|
||||
label.remove.onClick = function(widget)
|
||||
standBySpells = false
|
||||
standByItems = false
|
||||
table.removevalue(currentSettings.spellTable, entry)
|
||||
reindexTable(currentSettings.spellTable)
|
||||
label:destroy()
|
||||
@@ -245,10 +252,14 @@ if rootWidget then
|
||||
local label = UI.createWidget("SpellEntry", healWindow.items.itemList)
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
label.enabled.onClick = function(widget)
|
||||
standBySpells = false
|
||||
standByItems = false
|
||||
entry.enabled = not entry.enabled
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
end
|
||||
label.remove.onClick = function(widget)
|
||||
standBySpells = false
|
||||
standByItems = false
|
||||
table.removevalue(currentSettings.itemTable, entry)
|
||||
reindexTable(currentSettings.itemTable)
|
||||
label:destroy()
|
||||
@@ -414,6 +425,8 @@ if rootWidget then
|
||||
healWindow.spells.spellValue:setText('')
|
||||
healWindow.spells.manaCost:setText('')
|
||||
end
|
||||
standBySpells = false
|
||||
standByItems = false
|
||||
refreshSpells()
|
||||
end
|
||||
|
||||
@@ -455,6 +468,8 @@ if rootWidget then
|
||||
|
||||
if id > 100 then
|
||||
table.insert(currentSettings.itemTable, {index = #currentSettings.itemTable+1,item = id, sign = equasion, origin = source, value = trigger, enabled = true})
|
||||
standBySpells = false
|
||||
standByItems = false
|
||||
refreshItems()
|
||||
healWindow.items.itemId:setItemId(0)
|
||||
healWindow.items.itemValue:setText('')
|
||||
@@ -554,9 +569,6 @@ if rootWidget then
|
||||
end
|
||||
|
||||
-- spells
|
||||
local lastMana = mana()
|
||||
local standBySpells = false
|
||||
local iterationsSpells = 0
|
||||
macro(100, function()
|
||||
if standBySpells then return end
|
||||
if not currentSettings.enabled or modules.game_cooldown.isGroupCooldownIconActive(2) or #currentSettings.spellTable == 0 then return end
|
||||
@@ -625,7 +637,6 @@ macro(100, function()
|
||||
end)
|
||||
|
||||
-- items
|
||||
local standByItems = false
|
||||
macro(100, function()
|
||||
if standByItems then return end
|
||||
if not currentSettings.enabled or #currentSettings.itemTable == 0 then return end
|
@@ -34,10 +34,15 @@ if not storage[panelName] then
|
||||
healthValue = 40,
|
||||
manaBelow = false,
|
||||
manaValue = 50,
|
||||
privateMessage = false
|
||||
privateMessage = false,
|
||||
ignoreFriends = true,
|
||||
warnBoss = false,
|
||||
bossName = '[B]'
|
||||
}
|
||||
end
|
||||
|
||||
|
||||
|
||||
local config = storage[panelName]
|
||||
|
||||
ui.title:setOn(config.enabled)
|
||||
@@ -46,6 +51,10 @@ config.enabled = not config.enabled
|
||||
widget:setOn(config.enabled)
|
||||
end
|
||||
|
||||
-- new var's validation
|
||||
config.messageText = config.messageText or ""
|
||||
config.bossName = config.bossName or ""
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
alarmsWindow = UI.createWindow('AlarmsWindow', rootWidget)
|
||||
@@ -109,11 +118,57 @@ if rootWidget then
|
||||
widget:setOn(config.privateMessage)
|
||||
end
|
||||
|
||||
alarmsWindow.ignoreFriends:setOn(config.ignoreFriends)
|
||||
alarmsWindow.ignoreFriends.onClick = function(widget)
|
||||
config.ignoreFriends = not config.ignoreFriends
|
||||
widget:setOn(config.ignoreFriends)
|
||||
end
|
||||
|
||||
alarmsWindow.warnBoss:setOn(config.warnBoss)
|
||||
alarmsWindow.warnBoss.onClick = function(widget)
|
||||
config.warnBoss = not config.warnBoss
|
||||
widget:setOn(config.warnBoss)
|
||||
end
|
||||
|
||||
alarmsWindow.bossName:setText(config.bossName)
|
||||
alarmsWindow.bossName.onTextChange = function(widget, text)
|
||||
config.bossName = text
|
||||
end
|
||||
|
||||
alarmsWindow.warnMessage:setOn(config.warnMessage)
|
||||
alarmsWindow.warnMessage.onClick = function(widget)
|
||||
config.warnMessage = not config.warnMessage
|
||||
widget:setOn(config.warnMessage)
|
||||
end
|
||||
|
||||
alarmsWindow.messageText:setText(config.messageText)
|
||||
alarmsWindow.messageText.onTextChange = function(widget, text)
|
||||
config.messageText = text
|
||||
end
|
||||
|
||||
local pName = player:getName()
|
||||
onTextMessage(function(mode, text)
|
||||
if config.enabled and config.playerAttack and mode == 16 and string.match(text, "hitpoints due to an attack") and not string.match(text, "hitpoints due to an attack by a ") then
|
||||
if config.enabled and config.playerAttack and string.match(text, "hitpoints due to an attack") and not string.match(text, "hitpoints due to an attack by a ") then
|
||||
playSound("/sounds/Player_Attack.ogg")
|
||||
g_window.setTitle(pName .. " - Player Detected!")
|
||||
g_window.setTitle(pName .. " - Player Attacks!")
|
||||
return
|
||||
end
|
||||
|
||||
if config.warnMessage and config.messageText:len() > 0 then
|
||||
text = text:lower()
|
||||
local parts = string.split(config.messageText, ",")
|
||||
for i=1,#parts do
|
||||
local part = parts[i]
|
||||
part = part:trim()
|
||||
part = part:lower()
|
||||
|
||||
if text:find(part) then
|
||||
delay(1500)
|
||||
playSound(g_resources.fileExists("/sounds/Special_Message.ogg") and "/sounds/Special_Message.ogg" or "/sounds/Private_Message.ogg")
|
||||
g_window.setTitle(pName .. " - Special Message Detected: "..part)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
@@ -121,14 +176,15 @@ if rootWidget then
|
||||
if not config.enabled then
|
||||
return
|
||||
end
|
||||
local specs = getSpectators()
|
||||
if config.playerDetected then
|
||||
for _, spec in ipairs(getSpectators()) do
|
||||
for _, spec in ipairs(specs) do
|
||||
if spec:isPlayer() and spec:getName() ~= name() then
|
||||
specPos = spec:getPosition()
|
||||
if math.max(math.abs(posx()-specPos.x), math.abs(posy()-specPos.y)) <= 8 then
|
||||
local specPos = spec:getPosition()
|
||||
if (not config.ignoreFriends or not isFriend(spec)) and math.max(math.abs(posx()-specPos.x), math.abs(posy()-specPos.y)) <= 8 then
|
||||
playSound("/sounds/Player_Detected.ogg")
|
||||
delay(1500)
|
||||
g_window.setTitle(pName .. " - Player Detected!")
|
||||
g_window.setTitle(pName .. " - Player Detected! "..spec:getName())
|
||||
if config.playerDetectedLogout then
|
||||
modules.game_interface.tryLogout(false)
|
||||
end
|
||||
@@ -139,24 +195,53 @@ if rootWidget then
|
||||
end
|
||||
|
||||
if config.creatureDetected then
|
||||
for _, spec in ipairs(getSpectators()) do
|
||||
if not spec:isPlayer()then
|
||||
specPos = spec:getPosition()
|
||||
for _, spec in ipairs(specs) do
|
||||
if not spec:isPlayer() then
|
||||
local specPos = spec:getPosition()
|
||||
if math.max(math.abs(posx()-specPos.x), math.abs(posy()-specPos.y)) <= 8 then
|
||||
playSound("/sounds/Creature_Detected.ogg")
|
||||
delay(1500)
|
||||
g_window.setTitle(pName .. " - Creature Detected! ")
|
||||
g_window.setTitle(pName .. " - Creature Detected! "..spec:getName())
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if config.warnBoss then
|
||||
-- experimental, but since we check only names i think the best way would be to combine all spec's names into one string and then check it to avoid multiple loops
|
||||
if config.bossName:len() > 0 then
|
||||
local names = string.split(config.bossName, ",")
|
||||
local combinedString = ""
|
||||
for _, spec in ipairs(specs) do
|
||||
local specPos = spec:getPosition()
|
||||
if math.max(math.abs(posx() - specPos.x), math.abs(posy() - specPos.y)) <= 8 then
|
||||
local name = spec:getName():lower()
|
||||
-- add special sign between names to avoid unwanted combining mistakes
|
||||
combinedString = combinedString .."&"..name
|
||||
end
|
||||
end
|
||||
for i=1,#names do
|
||||
local name = names[i]
|
||||
name = name:trim()
|
||||
name = name:lower()
|
||||
|
||||
if combinedString:find(name) then
|
||||
playSound(g_resources.fileExists("/sounds/Special_Creature.ogg") and "/sounds/Special_Creature.ogg" or "/sounds/Creature_Detected.ogg")
|
||||
delay(1500)
|
||||
g_window.setTitle(pName .. " - Special Creature Detected: "..name)
|
||||
return
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if config.healthBelow then
|
||||
if hppercent() <= config.healthValue then
|
||||
playSound("/sounds/Low_Health.ogg")
|
||||
g_window.setTitle(pName .. " - Low Health!")
|
||||
delay(1500)
|
||||
g_window.setTitle(pName .. " - Low Health! only: "..hppercent().."%")
|
||||
return
|
||||
end
|
||||
end
|
||||
@@ -164,8 +249,8 @@ if rootWidget then
|
||||
if config.manaBelow then
|
||||
if manapercent() <= config.manaValue then
|
||||
playSound("/sounds/Low_Mana.ogg")
|
||||
g_window.setTitle(pName .. " - Low Mana!")
|
||||
delay(1500)
|
||||
g_window.setTitle(pName .. " - Low Mana! only: "..manapercent().."%")
|
||||
return
|
||||
end
|
||||
end
|
||||
@@ -174,7 +259,7 @@ if rootWidget then
|
||||
onTalk(function(name, level, mode, text, channelId, pos)
|
||||
if mode == 4 and config.enabled and config.privateMessage then
|
||||
playSound("/sounds/Private_Message.ogg")
|
||||
g_window.setTitle(pName .. " - Private Message")
|
||||
g_window.setTitle(pName .. " - Private Message from: " .. name)
|
||||
return
|
||||
end
|
||||
end)
|
181
modules/game_bot/default_configs/vBot_4.0/vBot/alarms.otui
Normal file
181
modules/game_bot/default_configs/vBot_4.0/vBot/alarms.otui
Normal file
@@ -0,0 +1,181 @@
|
||||
AlarmsWindow < MainWindow
|
||||
!text: tr('Alarms')
|
||||
size: 300 280
|
||||
@onEscape: self:hide()
|
||||
|
||||
BotSwitch
|
||||
id: playerAttack
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: parent.top
|
||||
text-align: center
|
||||
text: Player Attack
|
||||
!tooltip: tr('Alerts when attacked by player.')
|
||||
|
||||
BotSwitch
|
||||
id: playerDetected
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.horizontalCenter
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 4
|
||||
text-align: center
|
||||
text: Player Detected
|
||||
!tooltip: tr('Alerts when a player is detected on screen.')
|
||||
|
||||
CheckBox
|
||||
id: playerDetectedLogout
|
||||
anchors.top: playerDetected.top
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
margin-top: 3
|
||||
margin-left: 4
|
||||
text: Logout
|
||||
!tooltip: tr('Attempts to logout when a player is detected on screen.')
|
||||
|
||||
BotSwitch
|
||||
id: ignoreFriends
|
||||
anchors.left: parent.left
|
||||
anchors.top: playerDetected.bottom
|
||||
anchors.right: parent.right
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Ignore Friends
|
||||
!tooltip: tr('Player detection alerts will ignore friends.')
|
||||
|
||||
HorizontalSeparator
|
||||
id: sepPlayer
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 4
|
||||
|
||||
BotSwitch
|
||||
id: creatureDetected
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: sepPlayer.bottom
|
||||
margin-top: 4
|
||||
text-align: center
|
||||
text: Creature Detected
|
||||
!tooltip: tr('Alerts when a creature is detected on screen.')
|
||||
|
||||
BotSwitch
|
||||
id: warnBoss
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.horizontalCenter
|
||||
text-align: center
|
||||
margin-top: 5
|
||||
text: Creature Name
|
||||
!tooltip: tr('Alerts when a creature/npc with name is detected on screen. \n eg: Benjamin or [boss] would detect a creature with [boss] in name. \n You can add many examples, just separate them by comma.')
|
||||
|
||||
BotTextEdit
|
||||
id: bossName
|
||||
anchors.left: prev.right
|
||||
margin-left: 4
|
||||
anchors.top: prev.top
|
||||
anchors.right: parent.right
|
||||
margin-top: 1
|
||||
height: 17
|
||||
font: terminus-10px
|
||||
|
||||
HorizontalSeparator
|
||||
id: sepCreature
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 4
|
||||
|
||||
BotSwitch
|
||||
id: healthBelow
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.horizontalCenter
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Health < 50%
|
||||
|
||||
HorizontalScrollBar
|
||||
id: healthValue
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
anchors.top: healthBelow.top
|
||||
margin-left: 3
|
||||
margin-top: 2
|
||||
minimum: 1
|
||||
maximum: 100
|
||||
step: 1
|
||||
|
||||
BotSwitch
|
||||
id: manaBelow
|
||||
anchors.left: parent.left
|
||||
anchors.top: healthBelow.bottom
|
||||
anchors.right: parent.horizontalCenter
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Mana < 50%
|
||||
|
||||
HorizontalScrollBar
|
||||
id: manaValue
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
anchors.top: manaBelow.top
|
||||
margin-left: 3
|
||||
margin-top: 2
|
||||
minimum: 1
|
||||
maximum: 100
|
||||
step: 1
|
||||
|
||||
HorizontalSeparator
|
||||
id: sepMessages
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 4
|
||||
|
||||
BotSwitch
|
||||
id: privateMessage
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.right
|
||||
text-align: center
|
||||
margin-top: 4
|
||||
text: Private Message
|
||||
!tooltip: tr('Alerts when recieving a private message.')
|
||||
|
||||
BotSwitch
|
||||
id: warnMessage
|
||||
anchors.left: parent.left
|
||||
anchors.top: prev.bottom
|
||||
anchors.right: parent.horizontalCenter
|
||||
text-align: center
|
||||
margin-top: 5
|
||||
text: Message Alert
|
||||
!tooltip: tr('Alerts when players receive a message that contains given part. \n Eg. event - will trigger alert whenever a message with word event appears. \n You can give many examples, just separate them by comma.')
|
||||
|
||||
BotTextEdit
|
||||
id: messageText
|
||||
anchors.left: prev.right
|
||||
margin-left: 4
|
||||
anchors.top: prev.top
|
||||
anchors.right: parent.right
|
||||
margin-top: 1
|
||||
height: 17
|
||||
font: terminus-10px
|
||||
|
||||
HorizontalSeparator
|
||||
id: separator
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: closeButton.top
|
||||
margin-bottom: 8
|
||||
|
||||
Button
|
||||
id: closeButton
|
||||
!text: tr('Close')
|
||||
font: cipsoftFont
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
size: 45 21
|
||||
margin-top: 15
|
||||
margin-right: 5
|
1083
modules/game_bot/default_configs/vBot_4.0/vBot/analyzer.lua
Normal file
1083
modules/game_bot/default_configs/vBot_4.0/vBot/analyzer.lua
Normal file
File diff suppressed because it is too large
Load Diff
267
modules/game_bot/default_configs/vBot_4.0/vBot/analyzer.otui
Normal file
267
modules/game_bot/default_configs/vBot_4.0/vBot/analyzer.otui
Normal file
@@ -0,0 +1,267 @@
|
||||
AnalyzerPriceLabel < Label
|
||||
background-color: alpha
|
||||
text-offset: 2 0
|
||||
focusable: true
|
||||
height: 16
|
||||
|
||||
$focus:
|
||||
background-color: #00000055
|
||||
|
||||
Button
|
||||
id: remove
|
||||
!text: tr('x')
|
||||
anchors.right: parent.right
|
||||
margin-right: 15
|
||||
width: 15
|
||||
height: 15
|
||||
|
||||
AnalyzerItemsPanel < Panel
|
||||
height: 0
|
||||
|
||||
Panel
|
||||
id: List
|
||||
anchors.fill: parent
|
||||
margin-top: 3
|
||||
padding: 2
|
||||
layout:
|
||||
type: grid
|
||||
cell-size: 32 32
|
||||
cell-spacing: 3
|
||||
num-columns: 5
|
||||
|
||||
AnalyzerLootItem < UIItem
|
||||
opacity: 0.87
|
||||
height: 37
|
||||
margin-left: 1
|
||||
virtual: true
|
||||
background-color: alpha
|
||||
|
||||
Label
|
||||
id: count
|
||||
font: verdana-11px-rounded
|
||||
color: white
|
||||
opacity: 0.87
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
margin-right: 2
|
||||
text-align: right
|
||||
text: 0
|
||||
|
||||
AnalyzerGraph < UIGraph
|
||||
height: 140
|
||||
capacity: 400
|
||||
line-width: 1
|
||||
color: red
|
||||
margin-top: 5
|
||||
margin-left: 5
|
||||
margin-right: 5
|
||||
background-color: #383636
|
||||
padding: 5
|
||||
font: verdana-11px-rounded
|
||||
image-source: /images/ui/graph_background
|
||||
|
||||
AnalyzerProgressBar < ProgressBar
|
||||
background-color: green
|
||||
height: 5
|
||||
margin-top: 3
|
||||
phantom: false
|
||||
margin-left: 3
|
||||
margin-right: 3
|
||||
border: 1 black
|
||||
|
||||
AnalyzerButton < Button
|
||||
height: 22
|
||||
margin-bottom: 2
|
||||
font: verdana-11px-rounded
|
||||
text-offset: 0 4
|
||||
|
||||
MainAnalyzerWindow < MiniWindow
|
||||
id: MainAnalyzerWindow
|
||||
text: Analytics Selector
|
||||
height: 200
|
||||
icon: /images/topbuttons/analyzers
|
||||
|
||||
MiniWindowContents
|
||||
padding-left: 5
|
||||
padding-right: 5
|
||||
padding-top: 5
|
||||
layout: verticalBox
|
||||
|
||||
AnalyzerButton
|
||||
id: HuntingAnalyzer
|
||||
text: Hunting Analyzer
|
||||
|
||||
AnalyzerButton
|
||||
id: LootAnalyzer
|
||||
text: Loot Analyzer
|
||||
|
||||
AnalyzerButton
|
||||
id: SupplyAnalyzer
|
||||
text: Supply Analyzer
|
||||
|
||||
AnalyzerButton
|
||||
id: ImpactAnalyzer
|
||||
text: Impact Analyzer
|
||||
|
||||
AnalyzerButton
|
||||
id: XPAnalyzer
|
||||
text: XP Analyzer
|
||||
|
||||
AnalyzerButton
|
||||
id: Settings
|
||||
text: Features & Settings
|
||||
color: #FABD02
|
||||
|
||||
AnalyzerButton
|
||||
id: ResetSession
|
||||
text: Reset Session
|
||||
color: #FF0000
|
||||
|
||||
HuntingAnalyzer < MiniWindow
|
||||
id: HuntingAnalyzerWindow
|
||||
text: Hunt Analyzer
|
||||
icon: /images/topbuttons/analyzers
|
||||
|
||||
MiniWindowContents
|
||||
padding-top: 3
|
||||
layout: verticalBox
|
||||
|
||||
LootAnalyzer < MiniWindow
|
||||
id: LootAnalyzerWindow
|
||||
text: Loot Analyzer
|
||||
icon: /images/topbuttons/analyzers
|
||||
|
||||
MiniWindowContents
|
||||
padding-top: 3
|
||||
layout: verticalBox
|
||||
|
||||
SupplyAnalyzer < MiniWindow
|
||||
id: SupplyAnalyzerWindow
|
||||
text: Supply Analyzer
|
||||
icon: /images/topbuttons/analyzers
|
||||
|
||||
MiniWindowContents
|
||||
padding-top: 3
|
||||
layout: verticalBox
|
||||
|
||||
ImpactAnalyzer < MiniWindow
|
||||
id: ImpactAnalyzerWindow
|
||||
text: Impact Analyzer
|
||||
icon: /images/topbuttons/analyzers
|
||||
|
||||
MiniWindowContents
|
||||
padding-top: 3
|
||||
layout: verticalBox
|
||||
|
||||
XPAnalyzer < MiniWindow
|
||||
id: XPAnalyzerWindow
|
||||
text: XP Analyzer
|
||||
height: 150
|
||||
icon: /images/topbuttons/analyzers
|
||||
|
||||
MiniWindowContents
|
||||
padding-top: 3
|
||||
layout: verticalBox
|
||||
|
||||
|
||||
FeaturesWindow < MainWindow
|
||||
id: FeaturesWindow
|
||||
size: 250 370
|
||||
padding: 15
|
||||
text: Analyzers Features
|
||||
@onEscape: self:hide()
|
||||
|
||||
TextList
|
||||
id: CustomPrices
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 10
|
||||
padding: 1
|
||||
height: 220
|
||||
vertical-scrollbar: CustomPricesScrollBar
|
||||
|
||||
VerticalScrollBar
|
||||
id: CustomPricesScrollBar
|
||||
anchors.top: CustomPrices.top
|
||||
anchors.bottom: CustomPrices.bottom
|
||||
anchors.right: CustomPrices.right
|
||||
step: 14
|
||||
pixels-scroll: true
|
||||
|
||||
BotItem
|
||||
id: ID
|
||||
anchors.left: CustomPrices.left
|
||||
anchors.top: CustomPrices.bottom
|
||||
margin-top: 5
|
||||
|
||||
SpinBox
|
||||
id: NewPrice
|
||||
anchors.left: prev.right
|
||||
margin-left: 5
|
||||
anchors.verticalCenter: prev.verticalCenter
|
||||
width: 100
|
||||
minimum: 0
|
||||
maximum: 1000000000
|
||||
step: 1
|
||||
text-align: center
|
||||
focusable: true
|
||||
|
||||
Button
|
||||
id: addItem
|
||||
anchors.left: prev.right
|
||||
margin-left: 5
|
||||
anchors.verticalCenter: prev.verticalCenter
|
||||
anchors.right: CustomPrices.right
|
||||
text: Add
|
||||
font: verdana-11px-rounded
|
||||
|
||||
HorizontalSeparator
|
||||
anchors.left: ID.right
|
||||
margin-left: 5
|
||||
anchors.right: CustomPrices.right
|
||||
anchors.verticalCenter: ID.top
|
||||
|
||||
HorizontalSeparator
|
||||
id: secondSeparator
|
||||
anchors.left: ID.right
|
||||
margin-left: 5
|
||||
anchors.right: CustomPrices.right
|
||||
anchors.bottom: ID.bottom
|
||||
|
||||
BotSwitch
|
||||
id: LootChannel
|
||||
anchors.left: CustomPrices.left
|
||||
anchors.right: parent.horizontalCenter
|
||||
margin-right: 2
|
||||
anchors.top: prev.top
|
||||
margin-top: 20
|
||||
text: Loot Channel
|
||||
font: verdana-11px-rounded
|
||||
|
||||
BotSwitch
|
||||
id: RarityFrames
|
||||
anchors.left: parent.horizontalCenter
|
||||
margin-left: 2
|
||||
anchors.right: CustomPrices.right
|
||||
anchors.top: secondSeparator.top
|
||||
margin-top: 20
|
||||
text: Rarity Frames
|
||||
font: verdana-11px-rounded
|
||||
|
||||
HorizontalSeparator
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: closeButton.top
|
||||
margin-bottom: 8
|
||||
|
||||
Button
|
||||
id: closeButton
|
||||
!text: tr('Close')
|
||||
font: cipsoftFont
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
size: 45 21
|
||||
margin-top: 15
|
||||
margin-right: 5
|
@@ -2,7 +2,7 @@
|
||||
Configs for modules
|
||||
Based on Kondrah storage method
|
||||
--]]
|
||||
configName = modules.game_bot.contentsPanel.config:getCurrentOption().text
|
||||
local configName = modules.game_bot.contentsPanel.config:getCurrentOption().text
|
||||
|
||||
-- make vBot config dir
|
||||
if not g_resources.directoryExists("/bot/".. configName .."/vBot_configs/") then
|
@@ -1,7 +1,7 @@
|
||||
setDefaultTab("Main")
|
||||
|
||||
-- securing storage namespace
|
||||
panelName = "extras"
|
||||
local panelName = "extras"
|
||||
if not storage[panelName] then
|
||||
storage[panelName] = {}
|
||||
end
|
||||
@@ -346,12 +346,22 @@ end
|
||||
|
||||
addCheckBox("bless", "Buy bless at login", true, rightPanel)
|
||||
if true then
|
||||
local blessed = false
|
||||
onTextMessage(function(mode,text)
|
||||
if not settings.bless then return end
|
||||
|
||||
text = text:lower()
|
||||
|
||||
if text == "you already have all blessings." then
|
||||
blessed = true
|
||||
end
|
||||
end)
|
||||
if settings.bless then
|
||||
if player:getBlessings() == 0 then
|
||||
say("!bless")
|
||||
schedule(2000, function()
|
||||
if g_game.getClientVersion() > 1000 then
|
||||
if player:getBlessings() == 0 then
|
||||
if not blessed and player:getBlessings() == 0 then
|
||||
warn("!! Blessings not bought !!")
|
||||
end
|
||||
end
|
||||
@@ -394,11 +404,12 @@ addCheckBox("holdMwall", "Hold MW/WG", true, rightPanel)
|
||||
addTextEdit("holdMwHot", "Magic Wall Hotkey: ", "F5", rightPanel)
|
||||
addTextEdit("holdWgHot", "Wild Growth Hotkey: ", "F6", rightPanel)
|
||||
if true then
|
||||
|
||||
local hold = 0
|
||||
local mwHot
|
||||
local wgHot
|
||||
|
||||
local candidates = {}
|
||||
|
||||
local m = macro(20, function()
|
||||
mwHot = settings.holdMwHot
|
||||
wgHot = settings.holdWgHot
|
||||
@@ -406,14 +417,19 @@ if true then
|
||||
if not settings.holdMwall then return end
|
||||
if #candidates == 0 then return end
|
||||
|
||||
for i, tile in pairs(candidates) do
|
||||
for i, pos in pairs(candidates) do
|
||||
local tile = g_map.getTile(pos)
|
||||
if tile then
|
||||
if tile:getText():len() == 0 then
|
||||
table.remove(candidates, i)
|
||||
table.remove(candidates, i)
|
||||
end
|
||||
local rune = tile:getText() == "HOLD MW" and 3180 or tile:getText() == "HOLD WG" and 3156
|
||||
if tile:canShoot() and not isInPz() and tile:isWalkable() and tile:getTopUseThing():getId() ~= 2130 then
|
||||
if math.abs(player:getPosition().x-tile:getPosition().x) < 8 and math.abs(player:getPosition().y-tile:getPosition().y) < 6 then
|
||||
return useWith(rune, tile:getTopUseThing())
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
@@ -421,9 +437,11 @@ if true then
|
||||
if not settings.holdMwall then return end
|
||||
if thing:getId() ~= 2129 then return end
|
||||
if tile:getText():find("HOLD") then
|
||||
table.insert(candidates, tile)
|
||||
table.insert(candidates, tile:getPosition())
|
||||
local rune = tile:getText() == "HOLD MW" and 3180 or tile:getText() == "HOLD WG" and 3156
|
||||
useWith(rune, tile:getTopUseThing())
|
||||
if math.abs(player:getPosition().x-tile:getPosition().x) < 8 and math.abs(player:getPosition().y-tile:getPosition().y) < 6 then
|
||||
return useWith(rune, tile:getTopUseThing())
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
@@ -436,13 +454,13 @@ if true then
|
||||
end
|
||||
end)
|
||||
|
||||
onKeyPress(function(keys)
|
||||
onKeyDown(function(keys)
|
||||
local wsadWalking = modules.game_walking.wsadWalking
|
||||
if not wsadWalking then return end
|
||||
if not settings.holdMwall then return end
|
||||
if m.isOff() then return end
|
||||
if keys ~= mwHot and keys ~= wgHot then return end
|
||||
|
||||
hold = now
|
||||
|
||||
local tile = getTileUnderCursor()
|
||||
if not tile then return end
|
||||
@@ -455,7 +473,25 @@ if true then
|
||||
else
|
||||
tile:setText("HOLD WG")
|
||||
end
|
||||
table.insert(candidates, tile)
|
||||
table.insert(candidates, tile:getPosition())
|
||||
end
|
||||
end)
|
||||
|
||||
onKeyPress(function(keys)
|
||||
local wsadWalking = modules.game_walking.wsadWalking
|
||||
if not wsadWalking then return end
|
||||
if not settings.holdMwall then return end
|
||||
if m.isOff() then return end
|
||||
if keys ~= mwHot and keys ~= wgHot then return end
|
||||
|
||||
if (hold - now) < -1000 then
|
||||
candidates = {}
|
||||
for i, tile in ipairs(g_map.getTiles(posz())) do
|
||||
local text = tile:getText()
|
||||
if text:find("HOLD") then
|
||||
tile:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
end
|
||||
@@ -490,7 +526,7 @@ if true then
|
||||
end
|
||||
end)
|
||||
|
||||
local regex = [[You see ([a-z 'A-z-]*) \(Level ([0-9]*)\)]]
|
||||
local regex = [[You see ([a-z 'A-z-]*) \(Level ([0-9]*)\)((?:.)* of the ([\w ]*),|)]]
|
||||
onTextMessage(function(mode, text)
|
||||
if not settings.checkPlayer then return end
|
||||
|
||||
@@ -498,6 +534,12 @@ if true then
|
||||
if #re ~= 0 then
|
||||
local name = re[1][2]
|
||||
local level = re[1][3]
|
||||
local guild = re[1][5] or ""
|
||||
|
||||
if guild:len() > 10 then
|
||||
guild = guild:sub(1,10) -- change to proper (last) values
|
||||
guild = guild.."..."
|
||||
end
|
||||
local voc
|
||||
if text:lower():find("sorcerer") then
|
||||
voc = "MS"
|
||||
@@ -510,11 +552,43 @@ if true then
|
||||
end
|
||||
local creature = getCreatureByName(name)
|
||||
if creature then
|
||||
creature:setText(level..voc)
|
||||
creature:setText("\n"..level..voc.."\n"..guild)
|
||||
end
|
||||
if found and now - found < 500 then
|
||||
modules.game_textmessage.clearMessages()
|
||||
end
|
||||
end
|
||||
end)
|
||||
end
|
||||
|
||||
addCheckBox("title", "Open Next Loot Container", true, leftPanel)
|
||||
local function openNextLootContainer()
|
||||
local containers = getContainers()
|
||||
local lootCotaniersIds = CaveBot.GetLootContainers()
|
||||
|
||||
for i, container in ipairs(containers) do
|
||||
local cId = container:getContainerItem():getId()
|
||||
if containerIsFull(container) then
|
||||
if table.find(lootCotaniersIds, cId) then
|
||||
for _, item in ipairs(container:getItems()) do
|
||||
if item:getId() == cId then
|
||||
return g_game.open(item, container)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
if true then
|
||||
onContainerOpen(function(container, previousContainer)
|
||||
schedule(100, function()
|
||||
openNextLootContainer()
|
||||
end)
|
||||
end)
|
||||
|
||||
onAddItem(function(container, slot, item, oldItem)
|
||||
schedule(100, function()
|
||||
openNextLootContainer()
|
||||
end)
|
||||
end)
|
||||
end
|
@@ -930,7 +930,7 @@ LootItems = {
|
||||
["sickle"] = 3,
|
||||
["sight of surrender's eye"] = 3000,
|
||||
["signet ring"] = 480000,
|
||||
["silencer claws"] = 390,
|
||||
["silencer claws"] = 25000,
|
||||
["silencer resonating chamber"] = 600,
|
||||
["silken bookmark"] = 1300,
|
||||
["silkweaver bow"] = 12000,
|
||||
@@ -1263,5 +1263,99 @@ LootItems = {
|
||||
["energy wall rune"] = 85,
|
||||
["energy bomb rune"] = 203,
|
||||
["sudden death rune"] = 135,
|
||||
["paralyse rune"] = 700
|
||||
["paralyse rune"] = 700,
|
||||
|
||||
["envenomed arrow"] = 12,
|
||||
["flaming arrow"] = 5,
|
||||
["flash arrow"] = 5,
|
||||
["onyx arrow"] = 7,
|
||||
["poison arrow"] = 1,
|
||||
["shiver arrow"] = 5,
|
||||
["simple arrow"] = 2,
|
||||
["sniper arrow"] = 5,
|
||||
["tarsal arrow"] = 6,
|
||||
["arrow"] = 3,
|
||||
["burst arrow"] = 0,
|
||||
["crystalline arrow"] = 20,
|
||||
["diamond arrow"] = 100,
|
||||
["earth arrow"] = 5,
|
||||
["infernal bolt"] = 12,
|
||||
["piercing bolt"] = 5,
|
||||
["power bolt"] = 7,
|
||||
["prismatic bolt"] = 20,
|
||||
["spectral bolt"] = 70,
|
||||
["vortex bolt"] = 6,
|
||||
["bolt"] = 4,
|
||||
["drill bolt"] = 12,
|
||||
}
|
||||
|
||||
WasteItems = {
|
||||
-- supplies
|
||||
["mana potion"] = 268,
|
||||
["strong mana potion"] = 237,
|
||||
["great mana potion"] = 238,
|
||||
["ultimate mana potion"] = 23373,
|
||||
["health potion"] = 266,
|
||||
["strong health potion"] = 236,
|
||||
["great health potion"] = 239,
|
||||
["ultimate health potion"] = 7643,
|
||||
["supreme health potion"] = 23375,
|
||||
["great spirit potion"] = 7642,
|
||||
["ultimate spirit potion"] = 23374,
|
||||
-- ammo
|
||||
["envenomed arrow"] = 16143,
|
||||
["flaming arrow"] = 763,
|
||||
["flash arrow"] = 761,
|
||||
["onyx arrow"] = 7365,
|
||||
["poison arrow"] = 3448,
|
||||
["shiver arrow"] = 762,
|
||||
["simple arrow"] = 21470,
|
||||
["sniper arrow"] = 7364,
|
||||
["tarsal arrow"] = 14251,
|
||||
["arrow"] = 3447,
|
||||
["burst arrow"] = 3449,
|
||||
["crystalline arrow"] = 15793,
|
||||
["diamond arrow"] = 35901,
|
||||
["earth arrow"] = 774,
|
||||
["infernal bolt"] = 6528,
|
||||
["piercing bolt"] = 7363,
|
||||
["power bolt"] = 3450,
|
||||
["prismatic bolt"] = 16141,
|
||||
["spectral bolt"] = 35902,
|
||||
["vortex bolt"] = 14252,
|
||||
["bolt"] = 3446,
|
||||
["drill bolt"] = 16142,
|
||||
-- runes
|
||||
["cure poison rune"] = 3153,
|
||||
["poison field rune"] = 3172,
|
||||
["fire field rune"] = 3188,
|
||||
["intense healing rune"] = 3152,
|
||||
["destroy field rune"] = 3148,
|
||||
["energy field rune"] = 3164,
|
||||
["stalagmite rune"] = 3179,
|
||||
["heavy magic missile rune"] = 3198,
|
||||
["disintegrate rune"] = 3197,
|
||||
["ultimate healing rune"] = 3160,
|
||||
["poison bomb rune"] = 3173,
|
||||
["animate death rune"] = 3203,
|
||||
["chameleon rune"] = 3178,
|
||||
["fireball rune"] = 3189,
|
||||
["holy missile rune"] = 3182,
|
||||
["icicle rune"] = 3158,
|
||||
["stone shower rune"] = 3175,
|
||||
["thunderstorm rune"] = 3202,
|
||||
["avalanche rune"] = 3161,
|
||||
["great fireball rune"] = 3191,
|
||||
["convince creature rune"] = 3177,
|
||||
["fire bomb rune"] = 3192,
|
||||
["poison wall rune"] = 3176,
|
||||
["explosion rune"] = 3200,
|
||||
["fire wall rune"] = 3190,
|
||||
["soulfire rune"] = 3195,
|
||||
["wild growth rune"] = 3156,
|
||||
["magic wall rune"] = 3180,
|
||||
["energy wall rune"] = 3166,
|
||||
["energy bomb rune"] = 3149,
|
||||
["sudden death rune"] = 3155,
|
||||
["paralyse rune"] = 3165
|
||||
}
|
@@ -1,3 +1,3 @@
|
||||
UI.Label("vBot v3.45 \n Vithrax#5814")
|
||||
UI.Label("vBot v4.0 \n Vithrax#5814")
|
||||
UI.Button("Official OTCv8 Discord!", function() g_platform.openUrl("https://discord.gg/yhqBE4A") end)
|
||||
UI.Separator()
|
@@ -167,6 +167,19 @@ function CaveBot.CloseLootContainer()
|
||||
return true
|
||||
end
|
||||
|
||||
function CaveBot.CloseAllLootContainers()
|
||||
local containers = CaveBot.GetLootContainers()
|
||||
|
||||
for i, container in pairs(getContainers()) do
|
||||
local containerId = container:getContainerItem():getId()
|
||||
if table.find(containers, containerId) then
|
||||
g_game.close(container)
|
||||
end
|
||||
end
|
||||
|
||||
return true
|
||||
end
|
||||
|
||||
--- Opens any loot container that isn't already opened.
|
||||
-- @return void or boolean
|
||||
function CaveBot.OpenLootContainer()
|
||||
@@ -436,7 +449,6 @@ function CaveBot.WithdrawItem(id, amount, fromDepot, destination)
|
||||
destination = getContainerByName(destination)
|
||||
end
|
||||
local itemCount = itemAmount(id)
|
||||
test()
|
||||
local depot
|
||||
for i, container in pairs(getContainers()) do
|
||||
if container:getName():lower():find("depot box") or container:getName():lower():find("your inbox") then
|
@@ -1,3 +1,4 @@
|
||||
---@diagnostic disable: undefined-global
|
||||
setDefaultTab("Main")
|
||||
|
||||
local panelName = "pushmax"
|
||||
@@ -93,22 +94,22 @@ local customMwall = config.mwallBlockId
|
||||
local key = config.pushMaxKey
|
||||
local enabled = config.enabled
|
||||
local fieldTable = {2118, 105, 2122}
|
||||
local cleanTile = nil
|
||||
|
||||
-- scripts
|
||||
|
||||
local targetTile
|
||||
local pushTarget
|
||||
local targetid
|
||||
|
||||
local resetData = function()
|
||||
for i, tile in pairs(g_map.getTiles(posz())) do
|
||||
if tile:getText() == "TARGET" or tile:getText() == "DEST" then
|
||||
if tile:getText() == "TARGET" or tile:getText() == "DEST" or tile:getText() == "CLEAR" then
|
||||
tile:setText('')
|
||||
end
|
||||
end
|
||||
pushTarget = nil
|
||||
targetTile = nil
|
||||
targetId = nil
|
||||
cleanTile = nil
|
||||
end
|
||||
|
||||
local getCreatureById = function(id)
|
||||
@@ -139,9 +140,11 @@ local isOk = function(a,b)
|
||||
end
|
||||
|
||||
-- to mark
|
||||
local hold = 0
|
||||
onKeyDown(function(keys)
|
||||
if not enabled then return end
|
||||
if keys ~= key then return end
|
||||
hold = now
|
||||
local tile = getTileUnderCursor()
|
||||
if not tile then return end
|
||||
if pushTarget and targetTile then
|
||||
@@ -151,7 +154,6 @@ onKeyDown(function(keys)
|
||||
local creature = tile:getCreatures()[1]
|
||||
if not pushTarget and creature then
|
||||
pushTarget = creature
|
||||
targetId = creature:getId()
|
||||
if pushTarget then
|
||||
tile:setText('TARGET')
|
||||
pushTarget:setMarked('#00FF00')
|
||||
@@ -167,6 +169,24 @@ onKeyDown(function(keys)
|
||||
end
|
||||
end)
|
||||
|
||||
-- mark tile to throw anything from it
|
||||
onKeyPress(function(keys)
|
||||
if not enabled then return end
|
||||
if keys ~= key then return end
|
||||
local tile = getTileUnderCursor()
|
||||
if not tile then return end
|
||||
|
||||
if (hold - now) < -2500 then
|
||||
if cleanTile and tile ~= cleanTile then
|
||||
resetData()
|
||||
elseif not cleanTile then
|
||||
cleanTile = tile
|
||||
tile:setText("CLEAR")
|
||||
end
|
||||
end
|
||||
hold = 0
|
||||
end)
|
||||
|
||||
onCreaturePositionChange(function(creature, newPos, oldPos)
|
||||
if not enabled then return end
|
||||
if creature == player then
|
||||
@@ -178,42 +198,93 @@ onCreaturePositionChange(function(creature, newPos, oldPos)
|
||||
end
|
||||
end)
|
||||
|
||||
macro(20, function()
|
||||
macro(50, function()
|
||||
if not enabled then return end
|
||||
if not pushTarget or not targetTile then return end
|
||||
tilePos = targetTile:getPosition()
|
||||
targetPos = pushTarget:getPosition()
|
||||
if not isOk(tilePos,targetPos) then return end
|
||||
|
||||
local tileOfTarget = g_map.getTile(targetPos)
|
||||
|
||||
if not targetTile:isWalkable() then
|
||||
local topThing = targetTile:getTopUseThing():getId()
|
||||
if topThing == 2129 or topThing == 2130 or topThing == customMwall then
|
||||
if targetTile:getTimer() < pushDelay+500 then
|
||||
vBot.isUsing = true
|
||||
schedule(pushDelay+700, function()
|
||||
vBot.isUsing = false
|
||||
end)
|
||||
end
|
||||
if targetTile:getTimer() > pushDelay then
|
||||
return
|
||||
end
|
||||
else
|
||||
return resetData()
|
||||
end
|
||||
end
|
||||
|
||||
if not tileOfTarget:getTopUseThing():isNotMoveable() then
|
||||
return useWith(rune, pushTarget)
|
||||
end
|
||||
if isNotOk(fieldTable, targetTile) then
|
||||
if targetTile:canShoot() then
|
||||
return useWith(3148, targetTile:getTopUseThing())
|
||||
else
|
||||
if cleanTile then
|
||||
local tilePos = cleanTile:getPosition()
|
||||
local pPos = player:getPosition()
|
||||
if not isOk(tilePos, pPos) then
|
||||
resetData()
|
||||
return
|
||||
end
|
||||
|
||||
if not cleanTile:hasCreature() then return end
|
||||
local tiles = getNearTiles(tilePos)
|
||||
local destTile
|
||||
local forbidden = {}
|
||||
-- unfortunately double loop
|
||||
for i, tile in pairs(tiles) do
|
||||
local minimapColor = g_map.getMinimapColor(tile:getPosition())
|
||||
local stairs = (minimapColor >= 210 and minimapColor <= 213)
|
||||
if stairs then
|
||||
table.insert(forbidden, tile:getPosition())
|
||||
end
|
||||
end
|
||||
for i, tile in pairs(tiles) do
|
||||
local minimapColor = g_map.getMinimapColor(tile:getPosition())
|
||||
local stairs = (minimapColor >= 210 and minimapColor <= 213)
|
||||
if tile:isWalkable() and not isNotOk(fieldTable, tile) and not tile:hasCreature() and not stairs then
|
||||
local tooClose = false
|
||||
if #forbidden ~= 0 then
|
||||
for i=1,#forbidden do
|
||||
local pos = forbidden[i]
|
||||
if isOk(pos, tile:getPosition()) then
|
||||
tooClose = true
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if not tooClose then
|
||||
destTile = tile
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if not destTile then return end
|
||||
local parcel = cleanTile:getCreatures()[1]
|
||||
if parcel then
|
||||
test()
|
||||
g_game.move(parcel,destTile:getPosition())
|
||||
delay(2000)
|
||||
end
|
||||
else
|
||||
if not pushTarget or not targetTile then return end
|
||||
local tilePos = targetTile:getPosition()
|
||||
local targetPos = pushTarget:getPosition()
|
||||
if not isOk(tilePos,targetPos) then return end
|
||||
|
||||
local tileOfTarget = g_map.getTile(targetPos)
|
||||
|
||||
if not targetTile:isWalkable() then
|
||||
local topThing = targetTile:getTopUseThing():getId()
|
||||
if topThing == 2129 or topThing == 2130 or topThing == customMwall then
|
||||
if targetTile:getTimer() < pushDelay+500 then
|
||||
vBot.isUsing = true
|
||||
schedule(pushDelay+700, function()
|
||||
vBot.isUsing = false
|
||||
end)
|
||||
end
|
||||
if targetTile:getTimer() > pushDelay then
|
||||
return
|
||||
end
|
||||
else
|
||||
return resetData()
|
||||
end
|
||||
end
|
||||
|
||||
if not tileOfTarget:getTopUseThing():isNotMoveable() and targetTile:getTimer() < pushDelay+500 then
|
||||
return useWith(rune, pushTarget)
|
||||
end
|
||||
if isNotOk(fieldTable, targetTile) then
|
||||
if targetTile:canShoot() then
|
||||
return useWith(3148, targetTile:getTopUseThing())
|
||||
else
|
||||
return
|
||||
end
|
||||
end
|
||||
g_game.move(pushTarget,tilePos)
|
||||
delay(2000)
|
||||
end
|
||||
g_game.move(pushTarget,tilePos)
|
||||
delay(2000)
|
||||
end)
|
@@ -1,10 +1,5 @@
|
||||
-- Author: Vithrax
|
||||
-- contains mostly basic function shortcuts and code shorteners
|
||||
-- burst damage calculation, for function burstDamageValue()
|
||||
-- sums monster hits on a span of last 3seconds
|
||||
-- if last message was more than 3s ago then clears the table
|
||||
|
||||
|
||||
|
||||
-- initial global variables declaration
|
||||
vBot = {} -- global namespace for bot variables
|
||||
@@ -12,7 +7,7 @@ vBot.BotServerMembers = {}
|
||||
vBot.standTime = now
|
||||
vBot.isUsingPotion = false
|
||||
vBot.isUsing = false
|
||||
|
||||
vBot.customCooldowns = {}
|
||||
|
||||
-- scripts / functions
|
||||
onPlayerPositionChange(function(x,y)
|
||||
@@ -282,18 +277,56 @@ end
|
||||
-- exctracts data about spell from gamelib SpellInfo table
|
||||
-- returns table
|
||||
-- ie:['Spell Name'] = {id, words, exhaustion, premium, type, icon, mana, level, soul, group, vocations}
|
||||
-- cooldown detection module
|
||||
local lastPhrase = ""
|
||||
onTalk(function(name, level, mode, text, channelId, pos)
|
||||
if name == player:getName() then
|
||||
lastPhrase = text:lower()
|
||||
end
|
||||
end)
|
||||
|
||||
if onSpellCooldown and onGroupSpellCooldown then
|
||||
onSpellCooldown(function(iconId, duration)
|
||||
schedule(5, function()
|
||||
if not vBot.customCooldowns[lastPhrase] then
|
||||
vBot.customCooldowns[lastPhrase] = {id = iconId}
|
||||
end
|
||||
end)
|
||||
end)
|
||||
|
||||
onGroupSpellCooldown(function(iconId, duration)
|
||||
schedule(10, function()
|
||||
if vBot.customCooldowns[lastPhrase] then
|
||||
vBot.customCooldowns[lastPhrase] = {id = vBot.customCooldowns[lastPhrase].id, group = {[iconId] = duration}}
|
||||
end
|
||||
end)
|
||||
end)
|
||||
else
|
||||
warn("Outdated OTClient! update to newest version to take benefits from all scripts!")
|
||||
end
|
||||
function getSpellData(spell)
|
||||
if not spell then return false end
|
||||
spell = spell:lower()
|
||||
local t = nil
|
||||
local c = nil
|
||||
for k, v in pairs(Spells) do
|
||||
if v.words == spell then
|
||||
t = k
|
||||
break
|
||||
end
|
||||
end
|
||||
if not t then
|
||||
for k, v in pairs(vBot.customCooldowns) do
|
||||
if k == spell then
|
||||
c = {id = v.id, mana = 1, level = 1, group = v.group}
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if t then
|
||||
return Spells[t]
|
||||
elseif c then
|
||||
return c
|
||||
else
|
||||
return false
|
||||
end
|
||||
@@ -819,7 +852,7 @@ end
|
||||
-- self explanatory
|
||||
-- use along with delay, it will only call action
|
||||
function useOnGroundItem(a, b)
|
||||
if not id then return false end
|
||||
if not b then return false end
|
||||
local item = findItem(a)
|
||||
if not item then return false end
|
||||
|
||||
@@ -989,7 +1022,6 @@ function getContainerByItem(id, notFull)
|
||||
end
|
||||
|
||||
-- [[ ready to use getSpectators patterns ]] --
|
||||
|
||||
LargeUeArea = [[
|
||||
0000001000000
|
||||
0000011100000
|
@@ -1,7 +0,0 @@
|
||||
-- main tab
|
||||
UI.Label("Vithrax CFG v1.3 \n \n Scripting Service: \n Vithrax#5814")
|
||||
|
||||
UI.Separator()
|
||||
|
||||
|
||||
|
@@ -1,147 +0,0 @@
|
||||
setDefaultTab("Main")
|
||||
|
||||
BotPanelName = "BOTserver"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 18
|
||||
|
||||
Button
|
||||
id: botServer
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
text-align: center
|
||||
height: 18
|
||||
!text: tr('BotServer')
|
||||
]])
|
||||
ui:setId(BotPanelName)
|
||||
|
||||
if not storage[BotPanelName] then
|
||||
storage[BotPanelName] = {
|
||||
manaInfo = true,
|
||||
mwallInfo = true
|
||||
}
|
||||
end
|
||||
|
||||
if not storage.BotServerChannel then
|
||||
storage.BotServerChannel = tostring(math.random(1000000000000,9999999999999))
|
||||
end
|
||||
|
||||
local channel = tostring(storage.BotServerChannel)
|
||||
BotServer.init(name(), channel)
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
botServerWindow = g_ui.createWidget('BotServerWindow', rootWidget)
|
||||
botServerWindow:hide()
|
||||
|
||||
|
||||
botServerWindow.Data.Channel:setText(storage.BotServerChannel)
|
||||
botServerWindow.Data.Channel.onTextChange = function(widget, text)
|
||||
storage.BotServerChannel = text
|
||||
end
|
||||
|
||||
botServerWindow.Data.Random.onClick = function(widget)
|
||||
storage.BotServerChannel = tostring(math.random(1000000000000,9999999999999))
|
||||
botServerWindow.Data.Channel:setText(storage.BotServerChannel)
|
||||
end
|
||||
|
||||
botServerWindow.Features.Feature1:setOn(storage[BotPanelName].manaInfo)
|
||||
botServerWindow.Features.Feature1.onClick = function(widget)
|
||||
storage[BotPanelName].manaInfo = not storage[BotPanelName].manaInfo
|
||||
widget:setOn(storage[BotPanelName].manaInfo)
|
||||
end
|
||||
|
||||
botServerWindow.Features.Feature2:setOn(storage[BotPanelName].mwallInfo)
|
||||
botServerWindow.Features.Feature2.onClick = function(widget)
|
||||
storage[BotPanelName].mwallInfo = not storage[BotPanelName].mwallInfo
|
||||
widget:setOn(storage[BotPanelName].mwallInfo)
|
||||
end
|
||||
end
|
||||
|
||||
function updateStatusText()
|
||||
if BotServer._websocket then
|
||||
botServerWindow.Data.ServerStatus:setText("CONNECTED")
|
||||
if serverCount then
|
||||
botServerWindow.Data.Participants:setText(#serverCount)
|
||||
end
|
||||
else
|
||||
botServerWindow.Data.ServerStatus:setText("DISCONNECTED")
|
||||
botServerWindow.Data.Participants:setText("-")
|
||||
end
|
||||
end
|
||||
|
||||
macro(2000, function()
|
||||
if BotServer._websocket then
|
||||
BotServer.send("list")
|
||||
end
|
||||
updateStatusText()
|
||||
end)
|
||||
|
||||
local regex = [["(.*?)"]]
|
||||
BotServer.listen("list", function(name, data)
|
||||
serverCount = regexMatch(json.encode(data), regex)
|
||||
storage.serverMembers = json.encode(data)
|
||||
end)
|
||||
|
||||
ui.botServer.onClick = function(widget)
|
||||
botServerWindow:show()
|
||||
botServerWindow:raise()
|
||||
botServerWindow:focus()
|
||||
end
|
||||
|
||||
botServerWindow.closeButton.onClick = function(widget)
|
||||
botServerWindow:hide()
|
||||
end
|
||||
|
||||
|
||||
-- scripts
|
||||
|
||||
storage[BotPanelName].mwalls = {}
|
||||
BotServer.listen("mwall", function(name, message)
|
||||
if storage[BotPanelName].mwallInfo then
|
||||
if not storage[BotPanelName].mwalls[message["pos"]] or storage[BotPanelName].mwalls[message["pos"]] < now then
|
||||
storage[BotPanelName].mwalls[message["pos"]] = now + message["duration"] - 150 -- 150 is latency correction
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
BotServer.listen("mana", function(name, message)
|
||||
if storage[BotPanelName].manaInfo then
|
||||
local creature = getPlayerByName(name)
|
||||
if creature then
|
||||
creature:setManaPercent(message["mana"])
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
onAddThing(function(tile, thing)
|
||||
if storage[BotPanelName].mwallInfo then
|
||||
if thing:isItem() and thing:getId() == 2129 then
|
||||
local pos = tile:getPosition().x .. "," .. tile:getPosition().y .. "," .. tile:getPosition().z
|
||||
if not storage[BotPanelName].mwalls[pos] or storage[BotPanelName].mwalls[pos] < now then
|
||||
storage[BotPanelName].mwalls[pos] = now + 20000
|
||||
BotServer.send("mwall", {pos=pos, duration=20000})
|
||||
end
|
||||
tile:setTimer(storage[BotPanelName].mwalls[pos] - now)
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
local lastMana = 0
|
||||
macro(100, function()
|
||||
if storage[BotPanelName].manaInfo then
|
||||
if manapercent() ~= lastMana then
|
||||
lastMana = manapercent()
|
||||
BotServer.send("mana", {mana=lastMana})
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
addSeparator()
|
@@ -1,178 +0,0 @@
|
||||
alarmsPanelName = "alarms"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 19
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text-align: center
|
||||
width: 130
|
||||
!text: tr('Alarms')
|
||||
|
||||
Button
|
||||
id: alerts
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
anchors.right: parent.right
|
||||
margin-left: 3
|
||||
height: 17
|
||||
text: Edit
|
||||
|
||||
]])
|
||||
ui:setId(alarmsPanelName)
|
||||
|
||||
if not storage[alarmsPanelName] then
|
||||
storage[alarmsPanelName] = {
|
||||
enabled = false,
|
||||
playerAttack = false,
|
||||
playerDetected = false,
|
||||
playerDetectedLogout = false,
|
||||
creatureDetected = false,
|
||||
healthBelow = false,
|
||||
healthValue = 40,
|
||||
manaBelow = false,
|
||||
manaValue = 50,
|
||||
privateMessage = false
|
||||
}
|
||||
end
|
||||
|
||||
ui.title:setOn(storage[alarmsPanelName].enabled)
|
||||
ui.title.onClick = function(widget)
|
||||
storage[alarmsPanelName].enabled = not storage[alarmsPanelName].enabled
|
||||
widget:setOn(storage[alarmsPanelName].enabled)
|
||||
end
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
alarmsWindow = g_ui.createWidget('AlarmsWindow', rootWidget)
|
||||
alarmsWindow:hide()
|
||||
|
||||
alarmsWindow.closeButton.onClick = function(widget)
|
||||
alarmsWindow:hide()
|
||||
end
|
||||
|
||||
alarmsWindow.playerAttack:setOn(storage[alarmsPanelName].playerAttack)
|
||||
alarmsWindow.playerAttack.onClick = function(widget)
|
||||
storage[alarmsPanelName].playerAttack = not storage[alarmsPanelName].playerAttack
|
||||
widget:setOn(storage[alarmsPanelName].playerAttack)
|
||||
end
|
||||
|
||||
alarmsWindow.playerDetected:setOn(storage[alarmsPanelName].playerDetected)
|
||||
alarmsWindow.playerDetected.onClick = function(widget)
|
||||
storage[alarmsPanelName].playerDetected = not storage[alarmsPanelName].playerDetected
|
||||
widget:setOn(storage[alarmsPanelName].playerDetected)
|
||||
end
|
||||
|
||||
alarmsWindow.playerDetectedLogout:setChecked(storage[alarmsPanelName].playerDetectedLogout)
|
||||
alarmsWindow.playerDetectedLogout.onClick = function(widget)
|
||||
storage[alarmsPanelName].playerDetectedLogout = not storage[alarmsPanelName].playerDetectedLogout
|
||||
widget:setChecked(storage[alarmsPanelName].playerDetectedLogout)
|
||||
end
|
||||
|
||||
alarmsWindow.creatureDetected:setOn(storage[alarmsPanelName].creatureDetected)
|
||||
alarmsWindow.creatureDetected.onClick = function(widget)
|
||||
storage[alarmsPanelName].creatureDetected = not storage[alarmsPanelName].creatureDetected
|
||||
widget:setOn(storage[alarmsPanelName].creatureDetected)
|
||||
end
|
||||
|
||||
alarmsWindow.healthBelow:setOn(storage[alarmsPanelName].healthBelow)
|
||||
alarmsWindow.healthBelow.onClick = function(widget)
|
||||
storage[alarmsPanelName].healthBelow = not storage[alarmsPanelName].healthBelow
|
||||
widget:setOn(storage[alarmsPanelName].healthBelow)
|
||||
end
|
||||
|
||||
alarmsWindow.healthValue.onValueChange = function(scroll, value)
|
||||
storage[alarmsPanelName].healthValue = value
|
||||
alarmsWindow.healthBelow:setText("Health < " .. storage[alarmsPanelName].healthValue .. "%")
|
||||
end
|
||||
alarmsWindow.healthValue:setValue(storage[alarmsPanelName].healthValue)
|
||||
|
||||
alarmsWindow.manaBelow:setOn(storage[alarmsPanelName].manaBelow)
|
||||
alarmsWindow.manaBelow.onClick = function(widget)
|
||||
storage[alarmsPanelName].manaBelow = not storage[alarmsPanelName].manaBelow
|
||||
widget:setOn(storage[alarmsPanelName].manaBelow)
|
||||
end
|
||||
|
||||
alarmsWindow.manaValue.onValueChange = function(scroll, value)
|
||||
storage[alarmsPanelName].manaValue = value
|
||||
alarmsWindow.manaBelow:setText("Mana < " .. storage[alarmsPanelName].manaValue .. "%")
|
||||
end
|
||||
alarmsWindow.manaValue:setValue(storage[alarmsPanelName].manaValue)
|
||||
|
||||
alarmsWindow.privateMessage:setOn(storage[alarmsPanelName].privateMessage)
|
||||
alarmsWindow.privateMessage.onClick = function(widget)
|
||||
storage[alarmsPanelName].privateMessage = not storage[alarmsPanelName].privateMessage
|
||||
widget:setOn(storage[alarmsPanelName].privateMessage)
|
||||
end
|
||||
|
||||
onTextMessage(function(mode, text)
|
||||
if storage[alarmsPanelName].enabled and storage[alarmsPanelName].playerAttack and mode == 16 and string.match(text, "hitpoints due to an attack") and not string.match(text, "hitpoints due to an attack by a ") then
|
||||
playSound("/sounds/Player_Attack.ogg")
|
||||
end
|
||||
end)
|
||||
|
||||
macro(100, function()
|
||||
if not storage[alarmsPanelName].enabled then
|
||||
return
|
||||
end
|
||||
if storage[alarmsPanelName].playerDetected then
|
||||
for _, spec in ipairs(getSpectators()) do
|
||||
if spec:isPlayer() and spec:getName() ~= name() then
|
||||
specPos = spec:getPosition()
|
||||
if math.max(math.abs(posx()-specPos.x), math.abs(posy()-specPos.y)) <= 8 then
|
||||
playSound("/sounds/Player_Detected.ogg")
|
||||
delay(1500)
|
||||
if storage[alarmsPanelName].playerDetectedLogout then
|
||||
modules.game_interface.tryLogout(false)
|
||||
end
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if storage[alarmsPanelName].creatureDetected then
|
||||
for _, spec in ipairs(getSpectators()) do
|
||||
if not spec:isPlayer()then
|
||||
specPos = spec:getPosition()
|
||||
if math.max(math.abs(posx()-specPos.x), math.abs(posy()-specPos.y)) <= 8 then
|
||||
playSound("/sounds/Creature_Detected.ogg")
|
||||
delay(1500)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if storage[alarmsPanelName].healthBelow then
|
||||
if hppercent() <= storage[alarmsPanelName].healthValue then
|
||||
playSound("/sounds/Low_Health.ogg")
|
||||
delay(1500)
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
if storage[alarmsPanelName].manaBelow then
|
||||
if manapercent() <= storage[alarmsPanelName].manaValue then
|
||||
playSound("/sounds/Low_Mana.ogg")
|
||||
delay(1500)
|
||||
return
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
onTalk(function(name, level, mode, text, channelId, pos)
|
||||
if mode == 4 and storage[alarmsPanelName].enabled and storage[alarmsPanelName].privateMessage then
|
||||
playSound("/sounds/Private_Message.ogg")
|
||||
return
|
||||
end
|
||||
end)
|
||||
end
|
||||
|
||||
ui.alerts.onClick = function(widget)
|
||||
alarmsWindow:show()
|
||||
alarmsWindow:raise()
|
||||
alarmsWindow:focus()
|
||||
end
|
@@ -1,440 +0,0 @@
|
||||
ComboPanelName = "combobot"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 19
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text-align: center
|
||||
width: 130
|
||||
!text: tr('ComboBot')
|
||||
|
||||
Button
|
||||
id: combos
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
anchors.right: parent.right
|
||||
margin-left: 3
|
||||
height: 17
|
||||
text: Setup
|
||||
|
||||
]])
|
||||
ui:setId(ComboPanelName)
|
||||
|
||||
if not storage[ComboPanelName] then
|
||||
storage[ComboPanelName] = {
|
||||
enabled = false,
|
||||
onSayEnabled = false,
|
||||
onShootEnabled = false,
|
||||
onCastEnabled = false,
|
||||
followLeaderEnabled = false,
|
||||
attackLeaderTargetEnabled = false,
|
||||
attackSpellEnabled = false,
|
||||
attackItemToggle = false,
|
||||
sayLeader = "",
|
||||
shootLeader = "",
|
||||
castLeader = "",
|
||||
sayPhrase = "",
|
||||
spell = "",
|
||||
serverLeader = "",
|
||||
item = 3155,
|
||||
attack = "",
|
||||
follow = "",
|
||||
commandsEnabled = true,
|
||||
serverEnabled = false,
|
||||
serverLeaderTarget = false,
|
||||
serverTriggers = true
|
||||
}
|
||||
end
|
||||
|
||||
ui.title:setOn(storage[ComboPanelName].enabled)
|
||||
ui.title.onClick = function(widget)
|
||||
storage[ComboPanelName].enabled = not storage[ComboPanelName].enabled
|
||||
widget:setOn(storage[ComboPanelName].enabled)
|
||||
end
|
||||
|
||||
ui.combos.onClick = function(widget)
|
||||
comboWindow:show()
|
||||
comboWindow:raise()
|
||||
comboWindow:focus()
|
||||
end
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
comboWindow = g_ui.createWidget('ComboWindow', rootWidget)
|
||||
comboWindow:hide()
|
||||
|
||||
-- bot item
|
||||
|
||||
comboWindow.actions.attackItem:setItemId(storage[ComboPanelName].item)
|
||||
comboWindow.actions.attackItem.onItemChange = function(widget)
|
||||
storage[ComboPanelName].item = widget:getItemId()
|
||||
end
|
||||
|
||||
-- switches
|
||||
|
||||
comboWindow.actions.commandsToggle:setOn(storage[ComboPanelName].commandsEnabled)
|
||||
comboWindow.actions.commandsToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].commandsEnabled = not storage[ComboPanelName].commandsEnabled
|
||||
widget:setOn(storage[ComboPanelName].commandsEnabled)
|
||||
end
|
||||
|
||||
comboWindow.server.botServerToggle:setOn(storage[ComboPanelName].serverEnabled)
|
||||
comboWindow.server.botServerToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].serverEnabled = not storage[ComboPanelName].serverEnabled
|
||||
widget:setOn(storage[ComboPanelName].serverEnabled)
|
||||
end
|
||||
|
||||
comboWindow.server.Triggers:setOn(storage[ComboPanelName].serverTriggers)
|
||||
comboWindow.server.Triggers.onClick = function(widget)
|
||||
storage[ComboPanelName].serverTriggers = not storage[ComboPanelName].serverTriggers
|
||||
widget:setOn(storage[ComboPanelName].serverTriggers)
|
||||
end
|
||||
|
||||
comboWindow.server.targetServerLeaderToggle:setOn(storage[ComboPanelName].serverLeaderTarget)
|
||||
comboWindow.server.targetServerLeaderToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].serverLeaderTarget = not storage[ComboPanelName].serverLeaderTarget
|
||||
widget:setOn(storage[ComboPanelName].serverLeaderTarget)
|
||||
end
|
||||
|
||||
-- buttons
|
||||
comboWindow.closeButton.onClick = function(widget)
|
||||
comboWindow:hide()
|
||||
end
|
||||
|
||||
-- combo boxes
|
||||
|
||||
comboWindow.actions.followLeader:setOption(storage[ComboPanelName].follow)
|
||||
comboWindow.actions.followLeader.onOptionChange = function(widget)
|
||||
storage[ComboPanelName].follow = widget:getCurrentOption().text
|
||||
end
|
||||
|
||||
comboWindow.actions.attackLeaderTarget:setOption(storage[ComboPanelName].attack)
|
||||
comboWindow.actions.attackLeaderTarget.onOptionChange = function(widget)
|
||||
storage[ComboPanelName].attack = widget:getCurrentOption().text
|
||||
end
|
||||
|
||||
-- checkboxes
|
||||
comboWindow.trigger.onSayToggle:setChecked(storage[ComboPanelName].onSayEnabled)
|
||||
comboWindow.trigger.onSayToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].onSayEnabled = not storage[ComboPanelName].onSayEnabled
|
||||
widget:setChecked(storage[ComboPanelName].onSayEnabled)
|
||||
end
|
||||
|
||||
comboWindow.trigger.onShootToggle:setChecked(storage[ComboPanelName].onShootEnabled)
|
||||
comboWindow.trigger.onShootToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].onShootEnabled = not storage[ComboPanelName].onShootEnabled
|
||||
widget:setChecked(storage[ComboPanelName].onShootEnabled)
|
||||
end
|
||||
|
||||
comboWindow.trigger.onCastToggle:setChecked(storage[ComboPanelName].onCastEnabled)
|
||||
comboWindow.trigger.onCastToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].onCastEnabled = not storage[ComboPanelName].onCastEnabled
|
||||
widget:setChecked(storage[ComboPanelName].onCastEnabled)
|
||||
end
|
||||
|
||||
comboWindow.actions.followLeaderToggle:setChecked(storage[ComboPanelName].followLeaderEnabled)
|
||||
comboWindow.actions.followLeaderToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].followLeaderEnabled = not storage[ComboPanelName].followLeaderEnabled
|
||||
widget:setChecked(storage[ComboPanelName].followLeaderEnabled)
|
||||
end
|
||||
|
||||
comboWindow.actions.attackLeaderTargetToggle:setChecked(storage[ComboPanelName].attackLeaderTargetEnabled)
|
||||
comboWindow.actions.attackLeaderTargetToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].attackLeaderTargetEnabled = not storage[ComboPanelName].attackLeaderTargetEnabled
|
||||
widget:setChecked(storage[ComboPanelName].attackLeaderTargetEnabled)
|
||||
end
|
||||
|
||||
comboWindow.actions.attackSpellToggle:setChecked(storage[ComboPanelName].attackSpellEnabled)
|
||||
comboWindow.actions.attackSpellToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].attackSpellEnabled = not storage[ComboPanelName].attackSpellEnabled
|
||||
widget:setChecked(storage[ComboPanelName].attackSpellEnabled)
|
||||
end
|
||||
|
||||
comboWindow.actions.attackItemToggle:setChecked(storage[ComboPanelName].attackItemEnabled)
|
||||
comboWindow.actions.attackItemToggle.onClick = function(widget)
|
||||
storage[ComboPanelName].attackItemEnabled = not storage[ComboPanelName].attackItemEnabled
|
||||
widget:setChecked(storage[ComboPanelName].attackItemEnabled)
|
||||
end
|
||||
|
||||
-- text edits
|
||||
comboWindow.trigger.onSayLeader:setText(storage[ComboPanelName].sayLeader)
|
||||
comboWindow.trigger.onSayLeader.onTextChange = function(widget, text)
|
||||
storage[ComboPanelName].sayLeader = text
|
||||
end
|
||||
|
||||
comboWindow.trigger.onShootLeader:setText(storage[ComboPanelName].shootLeader)
|
||||
comboWindow.trigger.onShootLeader.onTextChange = function(widget, text)
|
||||
storage[ComboPanelName].shootLeader = text
|
||||
end
|
||||
|
||||
comboWindow.trigger.onCastLeader:setText(storage[ComboPanelName].castLeader)
|
||||
comboWindow.trigger.onCastLeader.onTextChange = function(widget, text)
|
||||
storage[ComboPanelName].castLeader = text
|
||||
end
|
||||
|
||||
comboWindow.trigger.onSayPhrase:setText(storage[ComboPanelName].sayPhrase)
|
||||
comboWindow.trigger.onSayPhrase.onTextChange = function(widget, text)
|
||||
storage[ComboPanelName].sayPhrase = text
|
||||
end
|
||||
|
||||
comboWindow.actions.attackSpell:setText(storage[ComboPanelName].spell)
|
||||
comboWindow.actions.attackSpell.onTextChange = function(widget, text)
|
||||
storage[ComboPanelName].spell = text
|
||||
end
|
||||
|
||||
comboWindow.server.botServerLeader:setText(storage[ComboPanelName].serverLeader)
|
||||
comboWindow.server.botServerLeader.onTextChange = function(widget, text)
|
||||
storage[ComboPanelName].serverLeader = text
|
||||
end
|
||||
end
|
||||
|
||||
-- bot server
|
||||
-- [[ join party made by Frosty ]] --
|
||||
|
||||
local shouldCloseWindow = false
|
||||
local firstInvitee = true
|
||||
local isInComboTeam = false
|
||||
macro(10, function()
|
||||
if shouldCloseWindow and storage[ComboPanelName].serverEnabled and storage[ComboPanelName].enabled then
|
||||
local channelsWindow = modules.game_console.channelsWindow
|
||||
if channelsWindow then
|
||||
local child = channelsWindow:getChildById("buttonCancel")
|
||||
if child then
|
||||
child:onClick()
|
||||
shouldCloseWindow = false
|
||||
isInComboTeam = true
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
comboWindow.server.partyButton.onClick = function(widget)
|
||||
if storage[ComboPanelName].serverEnabled and storage[ComboPanelName].enabled then
|
||||
if storage[ComboPanelName].serverLeader:len() > 0 and storage.BotServerChannel:len() > 0 then
|
||||
talkPrivate(storage[ComboPanelName].serverLeader, "request invite " .. storage.BotServerChannel)
|
||||
else
|
||||
error("Request failed. Lack of data.")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
onTextMessage(function(mode, text)
|
||||
if storage[ComboPanelName].serverEnabled and storage[ComboPanelName].enabled then
|
||||
if mode == 20 then
|
||||
if string.find(text, "invited you to") then
|
||||
local regex = "[a-zA-Z]*"
|
||||
local regexData = regexMatch(text, regex)
|
||||
if regexData[1][1]:lower() == storage[ComboPanelName].serverLeader:lower() then
|
||||
local leader = getCreatureByName(regexData[1][1])
|
||||
if leader then
|
||||
g_game.partyJoin(leader:getId())
|
||||
g_game.requestChannels()
|
||||
g_game.joinChannel(1)
|
||||
shouldCloseWindow = true
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
onTalk(function(name, level, mode, text, channelId, pos)
|
||||
if storage[ComboPanelName].serverEnabled and storage[ComboPanelName].enabled then
|
||||
if mode == 4 then
|
||||
if string.find(text, "request invite") then
|
||||
local access = string.match(text, "%d.*")
|
||||
if access and access == storage.BotServerChannel then
|
||||
local minion = getCreatureByName(name)
|
||||
if minion then
|
||||
g_game.partyInvite(minion:getId())
|
||||
if firstInvitee then
|
||||
g_game.requestChannels()
|
||||
g_game.joinChannel(1)
|
||||
shouldCloseWindow = true
|
||||
firstInvitee = false
|
||||
end
|
||||
end
|
||||
else
|
||||
talkPrivate(name, "Incorrect access key!")
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
-- [[ End of Frosty's Code ]] --
|
||||
if storage[ComboPanelName].enabled and storage[ComboPanelName].enabled then
|
||||
if name:lower() == storage[ComboPanelName].sayLeader:lower() and string.find(text, storage[ComboPanelName].sayPhrase) and storage[ComboPanelName].onSayEnabled then
|
||||
startCombo = true
|
||||
end
|
||||
if (storage[ComboPanelName].castLeader and name:lower() == storage[ComboPanelName].castLeader:lower()) and isAttSpell(text) and storage[ComboPanelName].onCastEnabled then
|
||||
startCombo = true
|
||||
end
|
||||
end
|
||||
if storage[ComboPanelName].enabled and storage[ComboPanelName].commandsEnabled and (storage[ComboPanelName].shootLeader and name:lower() == storage[ComboPanelName].shootLeader:lower()) or (storage[ComboPanelName].sayLeader and name:lower() == storage[ComboPanelName].sayLeader:lower()) or (storage[ComboPanelName].castLeader and name:lower() == storage[ComboPanelName].castLeader:lower()) then
|
||||
if string.find(text, "ue") then
|
||||
say(storage[ComboPanelName].spell)
|
||||
elseif string.find(text, "sd") then
|
||||
local params = string.split(text, ",")
|
||||
if #params == 2 then
|
||||
local target = params[2]:trim()
|
||||
if getCreatureByName(target) then
|
||||
useWith(3155, getCreatureByName(target))
|
||||
end
|
||||
end
|
||||
elseif string.find(text, "att") then
|
||||
local attParams = string.split(text, ",")
|
||||
if #attParams == 2 then
|
||||
local atTarget = attParams[2]:trim()
|
||||
if getCreatureByName(atTarget) and storage[ComboPanelName].attack == "COMMAND TARGET" then
|
||||
g_game.attack(getCreatureByName(atTarget))
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
if isAttSpell(text) and storage[ComboPanelName].enabled and storage[ComboPanelName].serverEnabled then
|
||||
BotServer.send("trigger", "start")
|
||||
end
|
||||
end)
|
||||
|
||||
onMissle(function(missle)
|
||||
if storage[ComboPanelName].enabled and storage[ComboPanelName].onShootEnabled then
|
||||
if not storage[ComboPanelName].shootLeader or storage[ComboPanelName].shootLeader:len() == 0 then
|
||||
return
|
||||
end
|
||||
local src = missle:getSource()
|
||||
if src.z ~= posz() then
|
||||
return
|
||||
end
|
||||
local from = g_map.getTile(src)
|
||||
local to = g_map.getTile(missle:getDestination())
|
||||
if not from or not to then
|
||||
return
|
||||
end
|
||||
local fromCreatures = from:getCreatures()
|
||||
local toCreatures = to:getCreatures()
|
||||
if #fromCreatures ~= 1 or #toCreatures ~= 1 then
|
||||
return
|
||||
end
|
||||
local c1 = fromCreatures[1]
|
||||
local t1 = toCreatures[1]
|
||||
leaderTarget = t1
|
||||
if c1:getName():lower() == storage[ComboPanelName].shootLeader:lower() then
|
||||
if storage[ComboPanelName].attackItemEnabled and storage[ComboPanelName].item and storage[ComboPanelName].item > 100 and findItem(storage[ComboPanelName].item) then
|
||||
useWith(storage[ComboPanelName].item, t1)
|
||||
end
|
||||
if storage[ComboPanelName].attackSpellEnabled and storage[ComboPanelName].spell:len() > 1 then
|
||||
say(storage[ComboPanelName].spell)
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
macro(10, function()
|
||||
if not storage[ComboPanelName].enabled or not storage[ComboPanelName].attackLeaderTargetEnabled then return end
|
||||
if leaderTarget and storage[ComboPanelName].attack == "LEADER TARGET" then
|
||||
if not getTarget() or (getTarget() and getTarget():getName() ~= leaderTarget:getName()) then
|
||||
g_game.attack(leaderTarget)
|
||||
end
|
||||
end
|
||||
if storage[ComboPanelName].enabled and storage[ComboPanelName].serverEnabled and storage[ComboPanelName].attack == "SERVER LEADER TARGET" and serverTarget then
|
||||
if serverTarget and not getTarget() or (getTarget() and getTarget():getname() ~= serverTarget)
|
||||
then
|
||||
g_game.attack(serverTarget)
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
|
||||
local toFollow
|
||||
local toFollowPos = {}
|
||||
|
||||
macro(100, function()
|
||||
toFollow = nil
|
||||
if not storage[ComboPanelName].enabled or not storage[ComboPanelName].followLeaderEnabled then return end
|
||||
if leaderTarget and storage[ComboPanelName].follow == "LEADER TARGET" and leaderTarget:isPlayer() then
|
||||
toFollow = leaderTarget:getName()
|
||||
elseif storage[ComboPanelName].follow == "SERVER LEADER TARGET" and storage[ComboPanelName].serverLeader:len() ~= 0 then
|
||||
toFollow = serverTarget
|
||||
elseif storage[ComboPanelName].follow == "SERVER LEADER" and storage[ComboPanelName].serverLeader:len() ~= 0 then
|
||||
toFollow = storage[ComboPanelName].serverLeader
|
||||
elseif storage[ComboPanelName].follow == "LEADER" then
|
||||
if storage[ComboPanelName].onSayEnabled and storage[ComboPanelName].sayLeader:len() ~= 0 then
|
||||
toFollow = storage[ComboPanelName].sayLeader
|
||||
elseif storage[ComboPanelName].onCastEnabled and storage[ComboPanelName].castLeader:len() ~= 0 then
|
||||
toFollow = storage[ComboPanelName].castLeader
|
||||
elseif storage[ComboPanelName].onShootEnabled and storage[ComboPanelName].shootLeader:len() ~= 0 then
|
||||
toFollow = storage[ComboPanelName].shootLeader
|
||||
end
|
||||
end
|
||||
if not toFollow then return end
|
||||
local target = getCreatureByName(toFollow)
|
||||
if target then
|
||||
local tpos = target:getPosition()
|
||||
toFollowPos[tpos.z] = tpos
|
||||
end
|
||||
if player:isWalking() then return end
|
||||
local p = toFollowPos[posz()]
|
||||
if not p then return end
|
||||
if CaveBot.walkTo(p, 20, {ignoreNonPathable=true, precision=1, ignoreStairs=false}) then
|
||||
delay(100)
|
||||
end
|
||||
end)
|
||||
|
||||
onCreaturePositionChange(function(creature, oldPos, newPos)
|
||||
if creature:getName() == toFollow and newPos then
|
||||
toFollowPos[newPos.z] = newPos
|
||||
end
|
||||
end)
|
||||
|
||||
local timeout = now
|
||||
macro(10, function()
|
||||
if storage[ComboPanelName].enabled and startCombo then
|
||||
if storage[ComboPanelName].attackItemEnabled and storage[ComboPanelName].item and storage[ComboPanelName].item > 100 and findItem(storage[ComboPanelName].item) then
|
||||
useWith(storage[ComboPanelName].item, getTarget())
|
||||
end
|
||||
if storage[ComboPanelName].attackSpellEnabled and storage[ComboPanelName].spell:len() > 1 then
|
||||
say(storage[ComboPanelName].spell)
|
||||
end
|
||||
startCombo = false
|
||||
end
|
||||
-- attack part / server
|
||||
if BotServer._websocket and storage[ComboPanelName].enabled and storage[ComboPanelName].serverEnabled then
|
||||
if target() and now - timeout > 500 then
|
||||
targetPos = target():getName()
|
||||
BotServer.send("target", targetPos)
|
||||
timeout = now
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
onUseWith(function(pos, itemId, target, subType)
|
||||
if BotServer._websocket and itemId == 3155 then
|
||||
BotServer.send("useWith", target:getPosition())
|
||||
end
|
||||
end)
|
||||
|
||||
if BotServer._websocket and storage[ComboPanelName].enabled and storage[ComboPanelName].serverEnabled then
|
||||
BotServer.listen("trigger", function(name, message)
|
||||
if message == "start" and name:lower() ~= player:getName():lower() and name:lower() == storage[ComboPanelName].serverLeader:lower() and storage[ComboPanelName].serverTriggers then
|
||||
startCombo = true
|
||||
end
|
||||
end)
|
||||
BotServer.listen("target", function(name, message)
|
||||
if name:lower() ~= player:getName():lower() and name:lower() == storage[ComboPanelName].serverLeader:lower() then
|
||||
if not target() or target():getName() == getCreatureByName(message) then
|
||||
if storage[ComboPanelName].serverLeaderTarget then
|
||||
serverTarget = getCreatureByName(message)
|
||||
g_game.attack(getCreatureByName(message))
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
BotServer.listen("useWith", function(name, message)
|
||||
local tile = g_map.getTile(message)
|
||||
if storage[ComboPanelName].serverTriggers and name:lower() ~= player:getName():lower() and name:lower() == storage[ComboPanelName].serverLeader:lower() and storage[ComboPanelName].attackItemEnabled and storage[ComboPanelName].item and findItem(storage[ComboPanelName].item) then
|
||||
useWith(storage[ComboPanelName].item, tile:getTopUseThing())
|
||||
end
|
||||
end)
|
||||
end
|
@@ -1,187 +0,0 @@
|
||||
setDefaultTab("Main")
|
||||
|
||||
pushPanelName = "pushmax"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 19
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text-align: center
|
||||
width: 130
|
||||
!text: tr('PUSHMAX')
|
||||
|
||||
Button
|
||||
id: push
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
anchors.right: parent.right
|
||||
margin-left: 3
|
||||
height: 17
|
||||
text: Setup
|
||||
|
||||
]])
|
||||
ui:setId(pushPanelName)
|
||||
|
||||
if not storage[pushPanelName] then
|
||||
storage[pushPanelName] = {
|
||||
enabled = true,
|
||||
pushDelay = 1060,
|
||||
pushMaxRuneId = 3188,
|
||||
mwallBlockId = 2128,
|
||||
pushMaxKey = "PageUp"
|
||||
}
|
||||
end
|
||||
|
||||
ui.title:setOn(storage[pushPanelName].enabled)
|
||||
ui.title.onClick = function(widget)
|
||||
storage[pushPanelName].enabled = not storage[pushPanelName].enabled
|
||||
widget:setOn(storage[pushPanelName].enabled)
|
||||
end
|
||||
|
||||
ui.push.onClick = function(widget)
|
||||
pushWindow:show()
|
||||
pushWindow:raise()
|
||||
pushWindow:focus()
|
||||
end
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
pushWindow = g_ui.createWidget('PushMaxWindow', rootWidget)
|
||||
pushWindow:hide()
|
||||
|
||||
pushWindow.closeButton.onClick = function(widget)
|
||||
pushWindow:hide()
|
||||
end
|
||||
|
||||
local updateDelayText = function()
|
||||
pushWindow.delayText:setText("Push Delay: ".. storage[pushPanelName].pushDelay)
|
||||
end
|
||||
updateDelayText()
|
||||
pushWindow.delay.onValueChange = function(scroll, value)
|
||||
storage[pushPanelName].pushDelay = value
|
||||
updateDelayText()
|
||||
end
|
||||
pushWindow.delay:setValue(storage[pushPanelName].pushDelay)
|
||||
|
||||
pushWindow.runeId.onItemChange = function(widget)
|
||||
storage[pushPanelName].pushMaxRuneId = widget:getItemId()
|
||||
end
|
||||
pushWindow.runeId:setItemId(storage[pushPanelName].pushMaxRuneId)
|
||||
pushWindow.mwallId.onItemChange = function(widget)
|
||||
storage[pushPanelName].mwallBlockId = widget:getItemId()
|
||||
end
|
||||
pushWindow.mwallId:setItemId(storage[pushPanelName].mwallBlockId)
|
||||
|
||||
pushWindow.hotkey.onTextChange = function(widget, text)
|
||||
storage[pushPanelName].pushMaxKey = text
|
||||
end
|
||||
pushWindow.hotkey:setText(storage[pushPanelName].pushMaxKey)
|
||||
end
|
||||
|
||||
|
||||
function matchPosition(curX, curY, destX, destY)
|
||||
return (curX == destX and curY == destY)
|
||||
end
|
||||
|
||||
local target
|
||||
local targetTile
|
||||
local targetOldPos
|
||||
macro(10, function()
|
||||
if not storage[pushPanelName].enabled then return end
|
||||
if target and targetTile then
|
||||
if not matchPosition(target:getPosition().x, target:getPosition().y, targetTile:getPosition().x, targetTile:getPosition().y) then
|
||||
local tile = g_map.getTile(target:getPosition())
|
||||
targetOldPos = tile:getPosition()
|
||||
if tile then
|
||||
if tile:getTopUseThing():isPickupable() or not tile:getTopUseThing():isNotMoveable() then
|
||||
useWith(tonumber(storage[pushPanelName].pushMaxRuneId), target)
|
||||
delay(10)
|
||||
end
|
||||
if targetTile:getTopThing():getId() == 2129 or targetTile:getTopThing():getId() == 2130 or targetTile:getTopThing():getId() == tonumber(storage[pushPanelName].mwallBlockId) then
|
||||
if targetTile:getTimer() <= tonumber(storage[pushPanelName].pushDelay) then
|
||||
info("now")
|
||||
g_game.move(target, targetTile:getPosition())
|
||||
tile:setText("")
|
||||
targetTile:setText("")
|
||||
target = nil
|
||||
targetTile = nil
|
||||
end
|
||||
else
|
||||
g_game.move(target, targetTile:getPosition())
|
||||
delay(1250)
|
||||
end
|
||||
end
|
||||
else
|
||||
if targetOldPos then
|
||||
local tile = g_map.getTile(targetOldPos)
|
||||
if tile then
|
||||
tile:setText("")
|
||||
targetTile:setText("")
|
||||
end
|
||||
end
|
||||
target = nil
|
||||
targetTile = nil
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
local resetTimer = now
|
||||
onKeyDown(function(keys)
|
||||
if not storage[pushPanelName].enabled then return end
|
||||
if keys == storage[pushPanelName].pushMaxKey and resetTimer == 0 then
|
||||
if not target then
|
||||
local tile = getTileUnderCursor()
|
||||
if tile and getDistanceBetween(pos(), tile:getPosition()) <= 1 then
|
||||
if tile:getCreatures()[1] then
|
||||
target = tile:getCreatures()[1]
|
||||
tile:setText("PUSH TARGET")
|
||||
end
|
||||
end
|
||||
else
|
||||
local tile = getTileUnderCursor()
|
||||
if tile and not tile:getCreatures()[1] then
|
||||
targetTile = tile
|
||||
tile:setText("DESTINATION")
|
||||
end
|
||||
end
|
||||
resetTimer = now
|
||||
end
|
||||
end)
|
||||
|
||||
|
||||
onKeyPress(function(keys)
|
||||
if not storage[pushPanelName].enabled then return end
|
||||
if keys == storage.pushMaxKey and (resetTimer - now) < -10 then
|
||||
for _, tile in ipairs(g_map.getTiles(posz())) do
|
||||
if getDistanceBetween(pos(), tile:getPosition()) < 3 then
|
||||
if tile:getText() ~= "" then
|
||||
tile:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
target = nil
|
||||
targetTile = nil
|
||||
resetTimer = 0
|
||||
else
|
||||
resetTimer = 0
|
||||
end
|
||||
end)
|
||||
|
||||
onCreaturePositionChange(function(creature, newPos, oldPos)
|
||||
if target and storage[pushPanelName].enabled then
|
||||
if creature:getName() == target:getName() then
|
||||
target = nil
|
||||
targetTile = nil
|
||||
for _, tile in ipairs(g_map.getTiles(posz())) do
|
||||
if getDistanceBetween(pos(), tile:getPosition()) < 3 then
|
||||
if tile:getText() ~= "" then
|
||||
tile:setText("")
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
@@ -1,415 +0,0 @@
|
||||
setDefaultTab("HP")
|
||||
storage.lootStatus = ""
|
||||
healPanelName = "healbot"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 19
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text-align: center
|
||||
width: 130
|
||||
!text: tr('HealBot')
|
||||
|
||||
Button
|
||||
id: combos
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
anchors.right: parent.right
|
||||
margin-left: 3
|
||||
height: 17
|
||||
text: Setup
|
||||
|
||||
]])
|
||||
ui:setId(healPanelName)
|
||||
|
||||
if not storage[healPanelName] or not storage[healPanelName].spellTable or not storage[healPanelName].itemTable then
|
||||
storage[healPanelName] = {
|
||||
enabled = false,
|
||||
spellTable = {},
|
||||
itemTable = {}
|
||||
}
|
||||
end
|
||||
|
||||
ui.title:setOn(storage[healPanelName].enabled)
|
||||
ui.title.onClick = function(widget)
|
||||
storage[healPanelName].enabled = not storage[healPanelName].enabled
|
||||
widget:setOn(storage[healPanelName].enabled)
|
||||
end
|
||||
|
||||
ui.combos.onClick = function(widget)
|
||||
healWindow:show()
|
||||
healWindow:raise()
|
||||
healWindow:focus()
|
||||
end
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
healWindow = g_ui.createWidget('HealWindow', rootWidget)
|
||||
healWindow:hide()
|
||||
|
||||
local refreshSpells = function()
|
||||
if storage[healPanelName].spellTable and #storage[healPanelName].spellTable > 0 then
|
||||
for i, child in pairs(healWindow.spells.spellList:getChildren()) do
|
||||
child:destroy()
|
||||
end
|
||||
for _, entry in pairs(storage[healPanelName].spellTable) do
|
||||
local label = g_ui.createWidget("SpellEntry", healWindow.spells.spellList)
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
label.enabled.onClick = function(widget)
|
||||
entry.enabled = not entry.enabled
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
end
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[healPanelName].spellTable, entry)
|
||||
reindexTable(storage[healPanelName].spellTable)
|
||||
label:destroy()
|
||||
end
|
||||
label:setText("(MP>" .. entry.cost .. ") " .. entry.origin .. entry.sign .. entry.value .. ":" .. entry.spell)
|
||||
end
|
||||
end
|
||||
end
|
||||
refreshSpells()
|
||||
|
||||
local refreshItems = function()
|
||||
if storage[healPanelName].itemTable and #storage[healPanelName].itemTable > 0 then
|
||||
for i, child in pairs(healWindow.items.itemList:getChildren()) do
|
||||
child:destroy()
|
||||
end
|
||||
for _, entry in pairs(storage[healPanelName].itemTable) do
|
||||
local label = g_ui.createWidget("SpellEntry", healWindow.items.itemList)
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
label.enabled.onClick = function(widget)
|
||||
entry.enabled = not entry.enabled
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
end
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[healPanelName].itemTable, entry)
|
||||
reindexTable(storage[healPanelName].itemTable)
|
||||
label:destroy()
|
||||
end
|
||||
label:setText(entry.origin .. entry.sign .. entry.value .. ":" .. entry.item)
|
||||
end
|
||||
end
|
||||
end
|
||||
refreshItems()
|
||||
|
||||
healWindow.spells.MoveUp.onClick = function(widget)
|
||||
local input = healWindow.spells.spellList:getFocusedChild()
|
||||
if not input then return end
|
||||
local index = healWindow.spells.spellList:getChildIndex(input)
|
||||
if index < 2 then return end
|
||||
|
||||
local move
|
||||
if storage[healPanelName].spellTable and #storage[healPanelName].spellTable > 0 then
|
||||
for _, entry in pairs(storage[healPanelName].spellTable) do
|
||||
if entry.index == index -1 then
|
||||
move = entry
|
||||
end
|
||||
if entry.index == index then
|
||||
move.index = index
|
||||
entry.index = index -1
|
||||
end
|
||||
end
|
||||
end
|
||||
table.sort(storage[healPanelName].spellTable, function(a,b) return a.index < b.index end)
|
||||
|
||||
healWindow.spells.spellList:moveChildToIndex(input, index - 1)
|
||||
healWindow.spells.spellList:ensureChildVisible(input)
|
||||
end
|
||||
|
||||
healWindow.spells.MoveDown.onClick = function(widget)
|
||||
local input = healWindow.spells.spellList:getFocusedChild()
|
||||
if not input then return end
|
||||
local index = healWindow.spells.spellList:getChildIndex(input)
|
||||
if index >= healWindow.spells.spellList:getChildCount() then return end
|
||||
|
||||
local move
|
||||
local move2
|
||||
if storage[healPanelName].spellTable and #storage[healPanelName].spellTable > 0 then
|
||||
for _, entry in pairs(storage[healPanelName].spellTable) do
|
||||
if entry.index == index +1 then
|
||||
move = entry
|
||||
end
|
||||
if entry.index == index then
|
||||
move2 = entry
|
||||
end
|
||||
end
|
||||
if move and move2 then
|
||||
move.index = index
|
||||
move2.index = index + 1
|
||||
end
|
||||
end
|
||||
table.sort(storage[healPanelName].spellTable, function(a,b) return a.index < b.index end)
|
||||
|
||||
healWindow.spells.spellList:moveChildToIndex(input, index + 1)
|
||||
healWindow.spells.spellList:ensureChildVisible(input)
|
||||
end
|
||||
|
||||
healWindow.items.MoveUp.onClick = function(widget)
|
||||
local input = healWindow.items.itemList:getFocusedChild()
|
||||
if not input then return end
|
||||
local index = healWindow.items.itemList:getChildIndex(input)
|
||||
if index < 2 then return end
|
||||
|
||||
local move
|
||||
if storage[healPanelName].itemTable and #storage[healPanelName].itemTable > 0 then
|
||||
for _, entry in pairs(storage[healPanelName].itemTable) do
|
||||
if entry.index == index -1 then
|
||||
move = entry
|
||||
end
|
||||
if entry.index == index then
|
||||
move.index = index
|
||||
entry.index = index - 1
|
||||
end
|
||||
end
|
||||
end
|
||||
table.sort(storage[healPanelName].itemTable, function(a,b) return a.index < b.index end)
|
||||
|
||||
healWindow.items.itemList:moveChildToIndex(input, index - 1)
|
||||
healWindow.items.itemList:ensureChildVisible(input)
|
||||
end
|
||||
|
||||
healWindow.items.MoveDown.onClick = function(widget)
|
||||
local input = healWindow.items.itemList:getFocusedChild()
|
||||
if not input then return end
|
||||
local index = healWindow.items.itemList:getChildIndex(input)
|
||||
if index >= healWindow.items.itemList:getChildCount() then return end
|
||||
|
||||
local move
|
||||
local move2
|
||||
if storage[healPanelName].itemTable and #storage[healPanelName].itemTable > 0 then
|
||||
for _, entry in pairs(storage[healPanelName].itemTable) do
|
||||
if entry.index == index +1 then
|
||||
move = entry
|
||||
end
|
||||
if entry.index == index then
|
||||
move2 = entry
|
||||
end
|
||||
end
|
||||
if move and move2 then
|
||||
move.index = index
|
||||
move2.index = index + 1
|
||||
end
|
||||
end
|
||||
table.sort(storage[healPanelName].itemTable, function(a,b) return a.index < b.index end)
|
||||
|
||||
healWindow.items.itemList:moveChildToIndex(input, index + 1)
|
||||
healWindow.items.itemList:ensureChildVisible(input)
|
||||
end
|
||||
|
||||
healWindow.spells.addSpell.onClick = function(widget)
|
||||
|
||||
local spellFormula = healWindow.spells.spellFormula:getText():trim()
|
||||
local manaCost = tonumber(healWindow.spells.manaCost:getText())
|
||||
local spellTrigger = tonumber(healWindow.spells.spellValue:getText())
|
||||
local spellSource = healWindow.spells.spellSource:getCurrentOption().text
|
||||
local spellEquasion = healWindow.spells.spellCondition:getCurrentOption().text
|
||||
local source
|
||||
local equasion
|
||||
|
||||
if not manaCost then
|
||||
warn("HealBot: incorrect mana cost value!")
|
||||
healWindow.spells.spellFormula:setText('')
|
||||
healWindow.spells.spellValue:setText('')
|
||||
healWindow.spells.manaCost:setText('')
|
||||
return
|
||||
end
|
||||
if not spellTrigger then
|
||||
warn("HealBot: incorrect condition value!")
|
||||
healWindow.spells.spellFormula:setText('')
|
||||
healWindow.spells.spellValue:setText('')
|
||||
healWindow.spells.manaCost:setText('')
|
||||
return
|
||||
end
|
||||
|
||||
if spellSource == "Current Mana" then
|
||||
source = "MP"
|
||||
elseif spellSource == "Current Health" then
|
||||
source = "HP"
|
||||
elseif spellSource == "Mana Percent" then
|
||||
source = "MP%"
|
||||
else
|
||||
source = "HP%"
|
||||
end
|
||||
|
||||
if spellEquasion == "Above" then
|
||||
equasion = ">"
|
||||
elseif spellEquasion == "Below" then
|
||||
equasion = "<"
|
||||
else
|
||||
equasion = "="
|
||||
end
|
||||
|
||||
if spellFormula:len() > 0 then
|
||||
table.insert(storage[healPanelName].spellTable, {index = #storage[healPanelName].spellTable+1, spell = spellFormula, sign = equasion, origin = source, cost = manaCost, value = spellTrigger, enabled = true})
|
||||
healWindow.spells.spellFormula:setText('')
|
||||
healWindow.spells.spellValue:setText('')
|
||||
healWindow.spells.manaCost:setText('')
|
||||
end
|
||||
refreshSpells()
|
||||
end
|
||||
|
||||
healWindow.items.addItem.onClick = function(widget)
|
||||
|
||||
local id = healWindow.items.itemId:getItemId()
|
||||
local trigger = tonumber(healWindow.items.itemValue:getText())
|
||||
local src = healWindow.items.itemSource:getCurrentOption().text
|
||||
local eq = healWindow.items.itemCondition:getCurrentOption().text
|
||||
local source
|
||||
local equasion
|
||||
|
||||
if not trigger then
|
||||
warn("HealBot: incorrect trigger value!")
|
||||
healWindow.items.itemId:setItemId(0)
|
||||
healWindow.items.itemValue:setText('')
|
||||
return
|
||||
end
|
||||
|
||||
if src == "Current Mana" then
|
||||
source = "MP"
|
||||
elseif src == "Current Health" then
|
||||
source = "HP"
|
||||
elseif src == "Mana Percent" then
|
||||
source = "MP%"
|
||||
else
|
||||
source = "HP%"
|
||||
end
|
||||
|
||||
if eq == "Above" then
|
||||
equasion = ">"
|
||||
elseif eq == "Below" then
|
||||
equasion = "<"
|
||||
else
|
||||
equasion = "="
|
||||
end
|
||||
|
||||
if id > 100 then
|
||||
table.insert(storage[healPanelName].itemTable, {index = #storage[healPanelName].itemTable+1,item = id, sign = equasion, origin = source, value = trigger, enabled = true})
|
||||
refreshItems()
|
||||
healWindow.items.itemId:setItemId(0)
|
||||
healWindow.items.itemValue:setText('')
|
||||
end
|
||||
end
|
||||
|
||||
healWindow.closeButton.onClick = function(widget)
|
||||
healWindow:hide()
|
||||
end
|
||||
end
|
||||
|
||||
-- spells
|
||||
macro(100, function()
|
||||
if not storage[healPanelName].enabled or modules.game_cooldown.isGroupCooldownIconActive(2) or #storage[healPanelName].spellTable == 0 then return end
|
||||
|
||||
for _, entry in pairs(storage[healPanelName].spellTable) do
|
||||
if canCast(entry.spell) and entry.enabled then
|
||||
if entry.origin == "HP%" then
|
||||
if entry.sign == "=" and hppercent() == entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == ">" and hppercent() >= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == "<" and hppercent() <= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
end
|
||||
elseif entry.origin == "HP" then
|
||||
if entry.sign == "=" and hp() == entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == ">" and hp() >= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == "<" and hp() <= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
end
|
||||
elseif entry.origin == "MP%" then
|
||||
if entry.sign == "=" and manapercent() == entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == ">" and manapercent() >= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == "<" and manapercent() <= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
end
|
||||
elseif entry.origin == "MP" then
|
||||
if entry.sign == "=" and mana() == entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == ">" and mana() >= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
elseif entry.sign == "<" and mana() <= entry.value then
|
||||
say(entry.spell)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
-- items
|
||||
macro(500, function()
|
||||
if TargetBot.isOff() then storage.lootStatus = "" end
|
||||
if not storage[healPanelName].enabled or storage.isUsing or #storage[healPanelName].itemTable == 0 then return end
|
||||
|
||||
if storage.lootStatus:len() > 0 then
|
||||
delay(500)
|
||||
end
|
||||
for _, entry in pairs(storage[healPanelName].itemTable) do
|
||||
local item = findItem(entry.item)
|
||||
if item and entry.enabled then
|
||||
if entry.origin == "HP%" then
|
||||
if entry.sign == "=" and hppercent() == entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == ">" and hppercent() >= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == "<" and hppercent() <= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
end
|
||||
elseif entry.origin == "HP" then
|
||||
if entry.sign == "=" and hp() == tonumberentry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == ">" and hp() >= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == "<" and hp() <= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
end
|
||||
elseif entry.origin == "MP%" then
|
||||
if entry.sign == "=" and manapercent() == entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == ">" and manapercent() >= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == "<" and manapercent() <= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
end
|
||||
elseif entry.origin == "MP" then
|
||||
if entry.sign == "=" and mana() == entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == ">" and mana() >= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
elseif entry.sign == "<" and mana() <= entry.value then
|
||||
useWith(entry.item, player)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
@@ -1,124 +0,0 @@
|
||||
setDefaultTab("Main")
|
||||
local panelName = "advancedFriendHealer"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 19
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text-align: center
|
||||
width: 130
|
||||
!text: tr('Friend Healer')
|
||||
|
||||
Button
|
||||
id: editList
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
anchors.right: parent.right
|
||||
margin-left: 3
|
||||
height: 17
|
||||
text: Setup
|
||||
|
||||
]], parent)
|
||||
ui:setId(panelName)
|
||||
|
||||
if not storage[panelName] then
|
||||
storage[panelName] = {
|
||||
minMana = 60,
|
||||
minFriendHp = 40,
|
||||
spellName = "exura sio",
|
||||
spellHeal = true,
|
||||
distance = 8,
|
||||
itemHeal = true,
|
||||
id = 3160
|
||||
}
|
||||
end
|
||||
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
sioListWindow = g_ui.createWidget('SioListWindow', rootWidget)
|
||||
sioListWindow:hide()
|
||||
|
||||
ui.title:setOn(storage[panelName].enabled)
|
||||
sioListWindow.spell:setOn(storage[panelName].spellHeal)
|
||||
sioListWindow.item:setOn(storage[panelName].itemHeal)
|
||||
|
||||
ui.title.onClick = function(widget)
|
||||
storage[panelName].enabled = not storage[panelName].enabled
|
||||
widget:setOn(storage[panelName].enabled)
|
||||
end
|
||||
|
||||
ui.editList.onClick = function(widget)
|
||||
sioListWindow:show()
|
||||
sioListWindow:raise()
|
||||
sioListWindow:focus()
|
||||
end
|
||||
sioListWindow.spell.onClick = function(widget)
|
||||
storage[panelName].spellHeal = not storage[panelName].spellHeal
|
||||
widget:setOn(storage[panelName].spellHeal)
|
||||
end
|
||||
sioListWindow.item.onClick = function(widget)
|
||||
storage[panelName].itemHeal = not storage[panelName].itemHeal
|
||||
widget:setOn(storage[panelName].itemHeal)
|
||||
end
|
||||
sioListWindow.closeButton.onClick = function(widget)
|
||||
sioListWindow:hide()
|
||||
end
|
||||
sioListWindow.spellName.onTextChange = function(widget, text)
|
||||
storage[panelName].spellName = text
|
||||
end
|
||||
local updateMinManaText = function()
|
||||
sioListWindow.manaInfo:setText("Minimum Mana >= " .. storage[panelName].minMana .. "%")
|
||||
end
|
||||
local updateFriendHpText = function()
|
||||
sioListWindow.friendHp:setText("Heal Friend Below " .. storage[panelName].minFriendHp .. "% hp")
|
||||
end
|
||||
local updateDistanceText = function()
|
||||
sioListWindow.distText:setText("Max Distance: " .. storage[panelName].distance)
|
||||
end
|
||||
sioListWindow.Distance.onValueChange = function(scroll, value)
|
||||
storage[panelName].distance = value
|
||||
updateDistanceText()
|
||||
end
|
||||
updateDistanceText()
|
||||
sioListWindow.minMana.onValueChange = function(scroll, value)
|
||||
storage[panelName].minMana = value
|
||||
updateMinManaText()
|
||||
end
|
||||
sioListWindow.minFriendHp.onValueChange = function(scroll, value)
|
||||
storage[panelName].minFriendHp = value
|
||||
|
||||
updateFriendHpText()
|
||||
end
|
||||
sioListWindow.itemId:setItemId(storage[panelName].id)
|
||||
sioListWindow.itemId.onItemChange = function(widget)
|
||||
storage[panelName].id = widget:getItemId()
|
||||
end
|
||||
sioListWindow.spellName:setText(storage[panelName].spellName)
|
||||
sioListWindow.minMana:setValue(storage[panelName].minMana)
|
||||
sioListWindow.minFriendHp:setValue(storage[panelName].minFriendHp)
|
||||
sioListWindow.Distance:setValue(storage[panelName].distance)
|
||||
|
||||
local healItem
|
||||
macro(200, function()
|
||||
if storage[panelName].enabled and storage[panelName].spellName:len() > 0 and manapercent() > storage[panelName].minMana then
|
||||
for _, spec in ipairs(getSpectators()) do
|
||||
if not spec:isLocalPlayer() then
|
||||
if spec:isPlayer() and storage[panelName].minFriendHp >= spec:getHealthPercent() and isFriend(spec:getName()) then
|
||||
if storage[panelName].spellHeal then
|
||||
saySpell(storage[panelName].spellName .. ' "' .. spec:getName(), 100)
|
||||
return
|
||||
end
|
||||
healItem = findItem(storage[panelName].id)
|
||||
if storage[panelName].itemHeal and distanceFromPlayer(spec:getPosition()) <= storage[panelName].distance and healItem then
|
||||
useWith(storage[panelName].id, spec)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
||||
addSeparator()
|
@@ -1,150 +0,0 @@
|
||||
local listPanelName = "playerList"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 18
|
||||
|
||||
Button
|
||||
id: editList
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
height: 18
|
||||
text: Player Lists
|
||||
]], parent)
|
||||
ui:setId(listPanelName)
|
||||
|
||||
if not storage[listPanelName] then
|
||||
storage[listPanelName] = {
|
||||
enemyList = {},
|
||||
friendList = {},
|
||||
groupMembers = true,
|
||||
outfits = false,
|
||||
marks = false
|
||||
}
|
||||
end
|
||||
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
playerListWindow = g_ui.createWidget('PlayerListsWindow', rootWidget)
|
||||
playerListWindow:hide()
|
||||
|
||||
playerListWindow.Members:setOn(storage[listPanelName].groupMembers)
|
||||
playerListWindow.Members.onClick = function(widget)
|
||||
storage[listPanelName].groupMembers = not storage[listPanelName].groupMembers
|
||||
widget:setOn(storage[listPanelName].groupMembers)
|
||||
end
|
||||
playerListWindow.Outfit:setOn(storage[listPanelName].outfits)
|
||||
playerListWindow.Outfit.onClick = function(widget)
|
||||
storage[listPanelName].outfits = not storage[listPanelName].outfits
|
||||
widget:setOn(storage[listPanelName].outfits)
|
||||
end
|
||||
playerListWindow.Marks:setOn(storage[listPanelName].marks)
|
||||
playerListWindow.Marks.onClick = function(widget)
|
||||
storage[listPanelName].marks = not storage[listPanelName].marks
|
||||
widget:setOn(storage[listPanelName].marks)
|
||||
end
|
||||
|
||||
if storage[listPanelName].enemyList and #storage[listPanelName].enemyList > 0 then
|
||||
for _, name in ipairs(storage[listPanelName].enemyList) do
|
||||
local label = g_ui.createWidget("PlayerName", playerListWindow.EnemyList)
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[listPanelName].enemyList, label:getText())
|
||||
label:destroy()
|
||||
end
|
||||
label:setText(name)
|
||||
end
|
||||
end
|
||||
|
||||
playerListWindow.AddFriend.onClick = function(widget)
|
||||
local friendName = playerListWindow.FriendName:getText()
|
||||
if friendName:len() > 0 and not table.contains(storage[listPanelName].enemyList, friendName, true) then
|
||||
table.insert(storage[listPanelName].enemyList, friendName)
|
||||
local label = g_ui.createWidget("PlayerName", playerListWindow.EnemyList)
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[listPanelName].enemyList, label:getText())
|
||||
label:destroy()
|
||||
end
|
||||
label:setText(friendName)
|
||||
playerListWindow.FriendName:setText('')
|
||||
end
|
||||
end
|
||||
|
||||
if storage[listPanelName].friendList and #storage[listPanelName].friendList > 0 then
|
||||
for _, name in ipairs(storage[listPanelName].friendList) do
|
||||
local label = g_ui.createWidget("PlayerName", playerListWindow.FriendList)
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[listPanelName].friendList, label:getText())
|
||||
label:destroy()
|
||||
end
|
||||
label:setText(name)
|
||||
end
|
||||
end
|
||||
|
||||
playerListWindow.AddFriend.onClick = function(widget)
|
||||
local friendName = playerListWindow.FriendName:getText()
|
||||
if friendName:len() > 0 and not table.contains(storage[listPanelName].friendList, friendName, true) then
|
||||
table.insert(storage[listPanelName].friendList, friendName)
|
||||
local label = g_ui.createWidget("PlayerName", playerListWindow.FriendList)
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[listPanelName].friendList, label:getText())
|
||||
label:destroy()
|
||||
end
|
||||
label:setText(friendName)
|
||||
playerListWindow.FriendName:setText('')
|
||||
end
|
||||
end
|
||||
|
||||
playerListWindow.AddEnemy.onClick = function(widget)
|
||||
local enemyName = playerListWindow.EnemyName:getText()
|
||||
if enemyName:len() > 0 and not table.contains(storage[listPanelName].enemyList, enemyName, true) then
|
||||
table.insert(storage[listPanelName].enemyList, enemyName)
|
||||
local label = g_ui.createWidget("PlayerName", playerListWindow.EnemyList)
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[listPanelName].enemyList, label:getText())
|
||||
label:destroy()
|
||||
end
|
||||
label:setText(enemyName)
|
||||
playerListWindow.EnemyName:setText('')
|
||||
end
|
||||
end
|
||||
|
||||
ui.editList.onClick = function(widget)
|
||||
playerListWindow:show()
|
||||
playerListWindow:raise()
|
||||
playerListWindow:focus()
|
||||
end
|
||||
playerListWindow.closeButton.onClick = function(widget)
|
||||
playerListWindow:hide()
|
||||
end
|
||||
|
||||
function refreshStatus()
|
||||
for _, spec in ipairs(getSpectators()) do
|
||||
if spec:isPlayer() and not spec:isLocalPlayer() then
|
||||
if storage[listPanelName].outfits then
|
||||
specOutfit = spec:getOutfit()
|
||||
if isEnemy(spec:getName()) then
|
||||
specOutfit.head = 112
|
||||
specOutfit.body = 112
|
||||
specOutfit.legs = 112
|
||||
specOutfit.feet = 112
|
||||
spec:setOutfit(specOutfit)
|
||||
elseif isFriend(spec:getName()) then
|
||||
specOutfit.head = 88
|
||||
specOutfit.body = 88
|
||||
specOutfit.legs = 88
|
||||
specOutfit.feet = 88
|
||||
spec:setOutfit(specOutfit)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
refreshStatus()
|
||||
|
||||
onCreatureAppear(function(creature)
|
||||
if creature:isPlayer() then
|
||||
refreshStatus()
|
||||
end
|
||||
end)
|
||||
|
||||
addSeparator()
|
@@ -1,764 +0,0 @@
|
||||
-- if you want to change tab, in line below insert: setDefaultTab("tab name")
|
||||
|
||||
attackPanelName = "attackbot"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 38
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
text-align: center
|
||||
width: 130
|
||||
!text: tr('AttackBot')
|
||||
|
||||
Button
|
||||
id: settings
|
||||
anchors.top: prev.top
|
||||
anchors.left: prev.right
|
||||
anchors.right: parent.right
|
||||
margin-left: 3
|
||||
height: 17
|
||||
text: Setup
|
||||
|
||||
Button
|
||||
id: mode
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.horizontalCenter
|
||||
text: Mode: PVP
|
||||
margin-right: 2
|
||||
margin-top: 4
|
||||
font: cipsoftFont
|
||||
height: 17
|
||||
|
||||
Button
|
||||
id: safe
|
||||
anchors.top: settings.bottom
|
||||
anchors.left: parent.horizontalCenter
|
||||
anchors.right: parent.right
|
||||
text: PVP Safe
|
||||
margin-left: 2
|
||||
margin-top: 4
|
||||
height: 17
|
||||
font:cipsoftFont
|
||||
]])
|
||||
ui:setId(attackPanelName)
|
||||
|
||||
local i = 1
|
||||
local j = 1
|
||||
local k = 1
|
||||
local pvpDedicated = false
|
||||
local item = false
|
||||
|
||||
if not storage[attackPanelName] or not storage[attackPanelName].attackTable then
|
||||
storage[attackPanelName] = {
|
||||
pvpMode = false,
|
||||
pvpSafe = true,
|
||||
enabled = false,
|
||||
attackTable = {},
|
||||
ignoreMana = true
|
||||
}
|
||||
end
|
||||
|
||||
local categories = {
|
||||
"Select Category",
|
||||
"Area Spell (exevo mas san, exevo gran mas flam etc.)",
|
||||
"Adjacent (exori, exori gran)",
|
||||
"Front Sweep (exori min)",
|
||||
"Wave (exevo tera hur, exevo gran vis lux)",
|
||||
"Targeted Spell (exori ico, exori flam etc.)",
|
||||
"Targeted Rune (sudden death, heavy magic missle etc.)",
|
||||
"Area Rune (great fireball, avalanche etc.)",
|
||||
"Empowerment (utito tempo)"
|
||||
}
|
||||
|
||||
local labels = {
|
||||
"",
|
||||
"Area Spell",
|
||||
"Adjacent",
|
||||
"Front Sweep",
|
||||
"Wave",
|
||||
"Targeted Spell",
|
||||
"Targeted Rune",
|
||||
"Area Rune",
|
||||
"Buff"
|
||||
}
|
||||
|
||||
local range = {
|
||||
"Select Range",
|
||||
"Range: 1",
|
||||
"Range: 2",
|
||||
"Range: 3",
|
||||
"Range: 4",
|
||||
"Range: 5",
|
||||
"Range: 6",
|
||||
"Range: 7",
|
||||
"Range: 8",
|
||||
"Range: 9"
|
||||
}
|
||||
|
||||
local pattern = {
|
||||
"Pattern",
|
||||
"Single (exori frigo, SD)",
|
||||
"Large AOE (mas tera)",
|
||||
"Medium AOE (mas frigo)",
|
||||
"Small AOE (mas san)",
|
||||
"Large Wave (tera hur)",
|
||||
"Medium Wave (frigo hur)",
|
||||
"Small Wave (gran frigo hur)",
|
||||
"Beam (exevo vis lux)",
|
||||
"Adjacent (exori)",
|
||||
"Area Rune (GFB, AVA)",
|
||||
"Empowerment"
|
||||
}
|
||||
|
||||
local updateModeText = function()
|
||||
local text
|
||||
if storage[attackPanelName].pvpMode then
|
||||
text = "PVP"
|
||||
ui.mode:setColor("yellow")
|
||||
else
|
||||
text = "HUNT"
|
||||
ui.mode:setColor("green")
|
||||
end
|
||||
ui.mode:setText("MODE: " .. text)
|
||||
end
|
||||
updateModeText()
|
||||
|
||||
local updatePvpColor = function()
|
||||
if storage[attackPanelName].pvpSafe then
|
||||
ui.safe:setColor("green")
|
||||
else
|
||||
ui.safe:setColor("white")
|
||||
end
|
||||
end
|
||||
updatePvpColor()
|
||||
|
||||
ui.title:setOn(storage[attackPanelName].enabled)
|
||||
ui.title.onClick = function(widget)
|
||||
storage[attackPanelName].enabled = not storage[attackPanelName].enabled
|
||||
widget:setOn(storage[attackPanelName].enabled)
|
||||
end
|
||||
|
||||
ui.mode.onClick = function(widget)
|
||||
storage[attackPanelName].pvpMode = not storage[attackPanelName].pvpMode
|
||||
updateModeText()
|
||||
end
|
||||
|
||||
ui.safe.onClick = function(widget)
|
||||
storage[attackPanelName].pvpSafe = not storage[attackPanelName].pvpSafe
|
||||
updatePvpColor()
|
||||
end
|
||||
|
||||
ui.settings.onClick = function(widget)
|
||||
attackWindow:show()
|
||||
attackWindow:raise()
|
||||
attackWindow:focus()
|
||||
end
|
||||
|
||||
rootWidget = g_ui.getRootWidget()
|
||||
if rootWidget then
|
||||
attackWindow = g_ui.createWidget('AttackWindow', rootWidget)
|
||||
attackWindow:hide()
|
||||
|
||||
-- functions
|
||||
local updateCategoryText = function()
|
||||
attackWindow.category:setText(categories[i])
|
||||
end
|
||||
updateCategoryText()
|
||||
local updateParameter1Text = function()
|
||||
attackWindow.parameter1:setText(pattern[k])
|
||||
end
|
||||
updateParameter1Text()
|
||||
local updateParameter2Text = function()
|
||||
attackWindow.parameter2:setText(range[j])
|
||||
end
|
||||
updateParameter2Text()
|
||||
|
||||
-- checkbox
|
||||
attackWindow.pvpSpell.onClick = function(widget)
|
||||
pvpDedicated = not pvpDedicated
|
||||
attackWindow.pvpSpell:setChecked(pvpDedicated)
|
||||
end
|
||||
attackWindow.IgnoreMana:setChecked(storage[attackPanelName].ignoreMana)
|
||||
attackWindow.IgnoreMana.onClick = function(widget)
|
||||
storage[attackPanelName].ignoreMana = not storage[attackPanelName].ignoreMana
|
||||
attackWindow.IgnoreMana:setChecked(storage[attackPanelName].ignoreMana)
|
||||
end
|
||||
|
||||
--buttons
|
||||
attackWindow.CloseButton.onClick = function(widget)
|
||||
attackWindow:hide()
|
||||
end
|
||||
|
||||
local inputTypeToggle = function()
|
||||
if attackWindow.category:getText():lower():find("rune") then
|
||||
item = true
|
||||
attackWindow.spellFormula:setText("")
|
||||
attackWindow.spellFormula:hide()
|
||||
attackWindow.spellDescription:hide()
|
||||
attackWindow.itemId:show()
|
||||
attackWindow.itemDescription:show()
|
||||
else
|
||||
item = false
|
||||
attackWindow.itemId:setItemId(0)
|
||||
attackWindow.itemId:hide()
|
||||
attackWindow.itemDescription:hide()
|
||||
attackWindow.spellFormula:show()
|
||||
attackWindow.spellDescription:show()
|
||||
end
|
||||
end
|
||||
inputTypeToggle()
|
||||
|
||||
attackWindow.categoryNext.onClick = function(widget)
|
||||
if i == #categories then
|
||||
i = 1
|
||||
else
|
||||
i = i + 1
|
||||
end
|
||||
updateCategoryText()
|
||||
inputTypeToggle()
|
||||
end
|
||||
|
||||
attackWindow.categoryPrev.onClick = function(widget)
|
||||
if i == 1 then
|
||||
i = #categories
|
||||
else
|
||||
i = i - 1
|
||||
end
|
||||
updateCategoryText()
|
||||
inputTypeToggle()
|
||||
end
|
||||
|
||||
attackWindow.parameter1Next.onClick = function(widget)
|
||||
if k == #pattern then
|
||||
k = 1
|
||||
else
|
||||
k = k + 1
|
||||
end
|
||||
updateParameter1Text()
|
||||
end
|
||||
|
||||
attackWindow.parameter1Prev.onClick = function(widget)
|
||||
if k == 1 then
|
||||
k = #pattern
|
||||
else
|
||||
k = k - 1
|
||||
end
|
||||
updateParameter1Text()
|
||||
end
|
||||
|
||||
attackWindow.parameter2Next.onClick = function(widget)
|
||||
if j == #range then
|
||||
j = 1
|
||||
else
|
||||
j = j + 1
|
||||
end
|
||||
updateParameter2Text()
|
||||
end
|
||||
|
||||
attackWindow.parameter2Prev.onClick = function(widget)
|
||||
if j == 1 then
|
||||
j = #range
|
||||
else
|
||||
j = j - 1
|
||||
end
|
||||
updateParameter2Text()
|
||||
end
|
||||
|
||||
local validVal = function(v)
|
||||
if type(v) ~= "number" then
|
||||
local val = tonumber(v)
|
||||
if not val then return false end
|
||||
end
|
||||
if v >= 0 and v < 101 then
|
||||
return true
|
||||
else
|
||||
return false
|
||||
end
|
||||
end
|
||||
|
||||
local clearValues = function()
|
||||
attackWindow.spellFormula:setText("")
|
||||
attackWindow.minMana:setText("")
|
||||
attackWindow.minMonsters:setText("")
|
||||
attackWindow.itemId:setItemId(0)
|
||||
pvpDedicated = false
|
||||
item = false
|
||||
attackWindow.pvpSpell:setChecked(false)
|
||||
i = 1
|
||||
j = 1
|
||||
k = 1
|
||||
updateParameter1Text()
|
||||
updateParameter2Text()
|
||||
updateCategoryText()
|
||||
inputTypeToggle()
|
||||
end
|
||||
|
||||
local refreshAttacks = function()
|
||||
if storage[attackPanelName].attackTable and #storage[attackPanelName].attackTable > 0 then
|
||||
for i, child in pairs(attackWindow.attackList:getChildren()) do
|
||||
child:destroy()
|
||||
end
|
||||
for _, entry in pairs(storage[attackPanelName].attackTable) do
|
||||
local label = g_ui.createWidget("AttackEntry", attackWindow.attackList)
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
label.enabled.onClick = function(widget)
|
||||
entry.enabled = not entry.enabled
|
||||
label.enabled:setChecked(entry.enabled)
|
||||
end
|
||||
label.remove.onClick = function(widget)
|
||||
table.removevalue(storage[attackPanelName].attackTable, entry)
|
||||
reindexTable(storage[attackPanelName].attackTable)
|
||||
label:destroy()
|
||||
end
|
||||
if entry.pvp then
|
||||
label:setText("(" .. entry.manaCost .. "% MP) " .. labels[entry.category] .. ": " .. entry.attack .. " (Range: ".. entry.dist .. ")")
|
||||
label:setColor("yellow")
|
||||
else
|
||||
label:setText("(" .. entry.manaCost .. "% MP & mob >= " .. entry.minMonsters .. ") " .. labels[entry.category] .. ": " .. entry.attack .. " (Range: ".. entry.dist .. ")")
|
||||
label:setColor("green")
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
refreshAttacks()
|
||||
|
||||
attackWindow.MoveUp.onClick = function(widget)
|
||||
local input = attackWindow.attackList:getFocusedChild()
|
||||
if not input then return end
|
||||
local index = attackWindow.attackList:getChildIndex(input)
|
||||
if index < 2 then return end
|
||||
|
||||
local move
|
||||
if storage[attackPanelName].attackTable and #storage[attackPanelName].attackTable > 0 then
|
||||
for _, entry in pairs(storage[attackPanelName].attackTable) do
|
||||
if entry.index == index -1 then
|
||||
move = entry
|
||||
end
|
||||
if entry.index == index then
|
||||
move.index = index
|
||||
entry.index = index -1
|
||||
end
|
||||
end
|
||||
end
|
||||
table.sort(storage[attackPanelName].attackTable, function(a,b) return a.index < b.index end)
|
||||
|
||||
attackWindow.attackList:moveChildToIndex(input, index - 1)
|
||||
attackWindow.attackList:ensureChildVisible(input)
|
||||
end
|
||||
|
||||
attackWindow.MoveDown.onClick = function(widget)
|
||||
local input = attackWindow.attackList:getFocusedChild()
|
||||
if not input then return end
|
||||
local index = attackWindow.attackList:getChildIndex(input)
|
||||
if index >= attackWindow.attackList:getChildCount() then return end
|
||||
|
||||
local move
|
||||
local move2
|
||||
if storage[attackPanelName].attackTable and #storage[attackPanelName].attackTable > 0 then
|
||||
for _, entry in pairs(storage[attackPanelName].attackTable) do
|
||||
if entry.index == index +1 then
|
||||
move = entry
|
||||
end
|
||||
if entry.index == index then
|
||||
move2 = entry
|
||||
end
|
||||
end
|
||||
if move and move2 then
|
||||
move.index = index
|
||||
move2.index = index + 1
|
||||
end
|
||||
end
|
||||
table.sort(storage[attackPanelName].attackTable, function(a,b) return a.index < b.index end)
|
||||
|
||||
attackWindow.attackList:moveChildToIndex(input, index + 1)
|
||||
attackWindow.attackList:ensureChildVisible(input)
|
||||
end
|
||||
|
||||
attackWindow.addButton.onClick = function(widget)
|
||||
local val
|
||||
if (item and attackWindow.itemId:getItemId() <= 100) or (not item and attackWindow.spellFormula:getText():len() == 0) then
|
||||
warn("AttackBot: missing spell or item id!")
|
||||
elseif not tonumber(attackWindow.minMana:getText()) or not validVal(tonumber(attackWindow.minMana:getText())) then
|
||||
warn("AttackBot: Mana Values incorrect! it has to be number from between 1 and 100")
|
||||
elseif not tonumber(attackWindow.minMonsters:getText()) or not validVal(tonumber(attackWindow.minMonsters:getText())) then
|
||||
warn("AttackBot: Monsters Count incorrect! it has to be number higher than 0")
|
||||
elseif i == 1 or j == 1 or k == 1 then
|
||||
warn("AttackBot: Categories not changed! You need to be more precise")
|
||||
else
|
||||
if item then
|
||||
val = attackWindow.itemId:getItemId()
|
||||
else
|
||||
val = attackWindow.spellFormula:getText()
|
||||
end
|
||||
table.insert(storage[attackPanelName].attackTable, {index = #storage[attackPanelName].attackTable+1, attack = val, manaCost = tonumber(attackWindow.minMana:getText()), minMonsters = tonumber(attackWindow.minMonsters:getText()), pvp = pvpDedicated, dist = j-1, model = k, category = i, enabled = true})
|
||||
refreshAttacks()
|
||||
clearValues()
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- executor
|
||||
-- table example (attack = 3155, manaCost = 50(%), minMonsters = 5, pvp = true, dist = 3, model = 6, category = 3)
|
||||
-- i = category
|
||||
-- j = range
|
||||
-- k = pattern - covered
|
||||
|
||||
local patterns = {
|
||||
"",
|
||||
"",
|
||||
[[
|
||||
0000001000000
|
||||
0000011100000
|
||||
0000111110000
|
||||
0001111111000
|
||||
0011111111100
|
||||
0111111111110
|
||||
1111111111111
|
||||
0111111111110
|
||||
0011111111100
|
||||
0001111111000
|
||||
0000111110000
|
||||
0000011100000
|
||||
0000001000000
|
||||
]],
|
||||
[[
|
||||
00000100000
|
||||
00011111000
|
||||
00111111100
|
||||
01111111110
|
||||
01111111110
|
||||
11111111111
|
||||
01111111110
|
||||
01111111110
|
||||
00111111100
|
||||
00001110000
|
||||
00000100000
|
||||
]],
|
||||
[[
|
||||
0011100
|
||||
0111110
|
||||
1111111
|
||||
1111111
|
||||
1111111
|
||||
0111110
|
||||
0011100
|
||||
]],
|
||||
[[
|
||||
0000NNN0000
|
||||
0000NNN0000
|
||||
0000NNN0000
|
||||
00000N00000
|
||||
WWW00N00EEE
|
||||
WWWWW0EEEEE
|
||||
WWW00S00EEE
|
||||
00000S00000
|
||||
0000SSS0000
|
||||
0000SSS0000
|
||||
0000SSS0000
|
||||
]],
|
||||
[[
|
||||
000NNNNN000
|
||||
000NNNNN000
|
||||
0000NNN0000
|
||||
WW00NNN00EE
|
||||
WWWW0N0EEEE
|
||||
WWWWW0EEEEE
|
||||
WWWW0S0EEEE
|
||||
WW00SSS00EE
|
||||
0000SSS0000
|
||||
000SSSSS000
|
||||
000SSSSS000
|
||||
]],
|
||||
[[
|
||||
00NNN00
|
||||
00NNN00
|
||||
WW0N0EE
|
||||
WWW0EEE
|
||||
WW0S0EE
|
||||
00SSS00
|
||||
00SSS00
|
||||
]],
|
||||
[[
|
||||
0000000N0000000
|
||||
0000000N0000000
|
||||
0000000N0000000
|
||||
0000000N0000000
|
||||
0000000N0000000
|
||||
0000000N0000000
|
||||
0000000N0000000
|
||||
WWWWWWW0EEEEEEE
|
||||
0000000S0000000
|
||||
0000000S0000000
|
||||
0000000S0000000
|
||||
0000000S0000000
|
||||
0000000S0000000
|
||||
0000000S0000000
|
||||
0000000S0000000
|
||||
]],
|
||||
"",
|
||||
""
|
||||
}
|
||||
|
||||
local safePatterns = {
|
||||
"",
|
||||
"",
|
||||
[[
|
||||
000000010000000
|
||||
000000111000000
|
||||
000001111100000
|
||||
000011111110000
|
||||
000111111111000
|
||||
001111111111100
|
||||
011111111111110
|
||||
111111111111111
|
||||
011111111111110
|
||||
001111111111100
|
||||
000111111111000
|
||||
000011111110000
|
||||
000001111100000
|
||||
000000111000000
|
||||
000000010000000
|
||||
]],
|
||||
[[
|
||||
0000011100000
|
||||
0000111110000
|
||||
0001111111000
|
||||
0011111111100
|
||||
0111111111110
|
||||
0111111111110
|
||||
1111111111111
|
||||
0111111111110
|
||||
0111111111110
|
||||
0011111111100
|
||||
0001111111000
|
||||
0000111110000
|
||||
0000011100000
|
||||
]],
|
||||
[[
|
||||
000111000
|
||||
001111100
|
||||
011111110
|
||||
111111111
|
||||
111111111
|
||||
111111111
|
||||
011111110
|
||||
001111100
|
||||
000111000
|
||||
]],
|
||||
[[
|
||||
0000NNNNN0000
|
||||
0000NNNNN0000
|
||||
0000NNNNN0000
|
||||
0000NNNNN0000
|
||||
WWWW0NNN0EEEE
|
||||
WWWWWNNNEEEEE
|
||||
WWWWWW0EEEEEE
|
||||
WWWWWSSSEEEEE
|
||||
WWWW0SSS0EEEE
|
||||
0000SSSSS0000
|
||||
0000SSSSS0000
|
||||
0000SSSSS0000
|
||||
0000SSSSS0000
|
||||
]],
|
||||
[[
|
||||
000NNNNNNN000
|
||||
000NNNNNNN000
|
||||
000NNNNNNN000
|
||||
WWWWNNNNNEEEE
|
||||
WWWWNNNNNEEEE
|
||||
WWWWWNNNEEEEE
|
||||
WWWWWW0EEEEEE
|
||||
WWWWWSSSEEEEE
|
||||
WWWWSSSSSEEEE
|
||||
WWWWSSSSSEEEE
|
||||
000SSSSSSS000
|
||||
000SSSSSSS000
|
||||
000SSSSSSS000
|
||||
]],
|
||||
[[
|
||||
00NNNNN00
|
||||
00NNNNN00
|
||||
WWNNNNNEE
|
||||
WWWWNEEEE
|
||||
WWWW0EEEE
|
||||
WWWWSEEEE
|
||||
WWSSSSSEE
|
||||
00SSSSS00
|
||||
00SSSSS00
|
||||
]],
|
||||
[[
|
||||
0000000NNN0000000
|
||||
0000000NNN0000000
|
||||
0000000NNN0000000
|
||||
0000000NNN0000000
|
||||
0000000NNN0000000
|
||||
0000000NNN0000000
|
||||
0000000NNN0000000
|
||||
WWWWWWWNNNEEEEEEE
|
||||
WWWWWWWW0EEEEEEEE
|
||||
WWWWWWWSSSEEEEEEE
|
||||
0000000SSS0000000
|
||||
0000000SSS0000000
|
||||
0000000SSS0000000
|
||||
0000000SSS0000000
|
||||
0000000SSS0000000
|
||||
0000000SSS0000000
|
||||
0000000SSS0000000
|
||||
]],
|
||||
"",
|
||||
""
|
||||
}
|
||||
|
||||
local posN = [[
|
||||
111
|
||||
000
|
||||
000
|
||||
]]
|
||||
local posE = [[
|
||||
001
|
||||
001
|
||||
001
|
||||
]]
|
||||
local posS = [[
|
||||
000
|
||||
000
|
||||
111
|
||||
]]
|
||||
local posW = [[
|
||||
100
|
||||
100
|
||||
100
|
||||
]]
|
||||
|
||||
local bestTile
|
||||
macro(100, function()
|
||||
if not storage[attackPanelName].enabled then return end
|
||||
if #storage[attackPanelName].attackTable == 0 or isInPz() or not target() or modules.game_cooldown.isGroupCooldownIconActive(1) then return end
|
||||
|
||||
local monstersN = 0
|
||||
local monstersE = 0
|
||||
local monstersS = 0
|
||||
local monstersW = 0
|
||||
|
||||
monstersN = getCreaturesInArea(pos(), posN, 2)
|
||||
monstersE = getCreaturesInArea(pos(), posE, 2)
|
||||
monstersS = getCreaturesInArea(pos(), posS, 2)
|
||||
monstersW = getCreaturesInArea(pos(), posW, 2)
|
||||
|
||||
local posTable = {monstersE, monstersN, monstersS, monstersW}
|
||||
local bestSide = 0
|
||||
local bestDir
|
||||
|
||||
-- pulling out the biggest number
|
||||
for i, v in pairs(posTable) do
|
||||
if v > bestSide then
|
||||
bestSide = v
|
||||
end
|
||||
end
|
||||
|
||||
-- associate biggest number with turn direction
|
||||
if monstersN == bestSide then bestDir = 0
|
||||
elseif monstersE == bestSide then bestDir = 1
|
||||
elseif monstersS == bestSide then bestDir = 2
|
||||
elseif monstersW == bestSide then bestDir = 3
|
||||
end
|
||||
|
||||
if player:getDirection() ~= bestDir and bestSide > 0 then
|
||||
turn(bestDir)
|
||||
end
|
||||
|
||||
for _, entry in pairs(storage[attackPanelName].attackTable) do
|
||||
if entry.enabled then
|
||||
if (type(entry.attack) == "string" and canCast(entry.attack, not storage[attackPanelName].ignoreMana)) or (type(entry.attack) == "number" and findItem(entry.attack)) then
|
||||
if manapercent() >= entry.manaCost and distanceFromPlayer(target():getPosition()) <= entry.dist then
|
||||
if storage[attackPanelName].pvpMode then
|
||||
if entry.pvp then
|
||||
if type(entry.attack) == "string" and target():canShoot() then
|
||||
say(entry.attack)
|
||||
return
|
||||
else
|
||||
if not storage.isUsing and target():canShoot() then
|
||||
useWith(entry.attack, target())
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
else
|
||||
if entry.category == 6 or entry.category == 7 then
|
||||
if getMonsters(4) >= entry.minMonsters then
|
||||
if type(entry.attack) == "number" then
|
||||
if not storage.isUsing then
|
||||
useWith(entry.attack, target())
|
||||
return
|
||||
end
|
||||
else
|
||||
say(entry.attack)
|
||||
return
|
||||
end
|
||||
end
|
||||
else
|
||||
if killsToRs() > 2 then
|
||||
if entry.category == 8 then
|
||||
bestTile = getBestTileByPatern(patterns[5], 2, entry.dist, storage[attackPanelName].pvpSafe)
|
||||
end
|
||||
if entry.category == 4 and (not storage[attackPanelName].pvpSafe or isSafe(2, false)) and bestSide >= entry.minMonsters then
|
||||
say(entry.attack)
|
||||
return
|
||||
elseif entry.category == 3 and (not storage[attackPanelName].pvpSafe or isSafe(2, false)) and getMonsters(1) >= entry.minMonsters then
|
||||
say(entry.attack)
|
||||
return
|
||||
elseif entry.category == 5 and getCreaturesInArea(player, patterns[entry.model], 2) >= entry.minMonsters and (not storage[attackPanelName].pvpSafe or getCreaturesInArea(player, safePatterns[entry.model], 3) == 0) then
|
||||
say(entry.attack)
|
||||
return
|
||||
elseif entry.category == 2 and getCreaturesInArea(pos(), patterns[entry.model], 2) >= entry.minMonsters and (not storage[attackPanelName].pvpSafe or getCreaturesInArea(pos(), safePatterns[entry.model], 3) == 0) then
|
||||
say(entry.attack)
|
||||
return
|
||||
elseif entry.category == 8 and bestTile and bestTile.count >= entry.minMonsters then
|
||||
if not storage.isUsing then
|
||||
useWith(entry.attack, bestTile.pos:getTopUseThing())
|
||||
end
|
||||
return
|
||||
elseif entry.category == 9 and not isBuffed() and getMonsters(entry.dist) >= entry.minMonsters then
|
||||
say(entry.attack)
|
||||
return
|
||||
else
|
||||
if entry.category == 6 or entry.category == 7 then
|
||||
if getMonsters(4) >= entry.minMonsters then
|
||||
if type(entry.attack) == "number" then
|
||||
if not storage.isUsing then
|
||||
useWith(entry.attack, target())
|
||||
return
|
||||
end
|
||||
else
|
||||
say(entry.attack)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
else
|
||||
if entry.category == 6 or entry.category == 7 then
|
||||
if getMonsters(4) >= entry.minMonsters then
|
||||
if type(entry.attack) == "number" then
|
||||
if not storage.isUsing then
|
||||
useWith(entry.attack, target())
|
||||
return
|
||||
end
|
||||
else
|
||||
say(entry.attack)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end)
|
@@ -1,242 +0,0 @@
|
||||
AttackEntry < Label
|
||||
background-color: alpha
|
||||
text-offset: 18 0
|
||||
focusable: true
|
||||
height: 16
|
||||
|
||||
CheckBox
|
||||
id: enabled
|
||||
anchors.left: parent.left
|
||||
anchors.verticalCenter: parent.verticalCenter
|
||||
width: 15
|
||||
height: 15
|
||||
margin-top: 2
|
||||
margin-left: 3
|
||||
|
||||
$focus:
|
||||
background-color: #00000055
|
||||
|
||||
Button
|
||||
id: remove
|
||||
!text: tr('x')
|
||||
anchors.right: parent.right
|
||||
margin-right: 15
|
||||
width: 15
|
||||
height: 15
|
||||
|
||||
AttackWindow < MainWindow
|
||||
!text: tr('AttackBot')
|
||||
size: 520 350
|
||||
@onEscape: self:hide()
|
||||
|
||||
TextList
|
||||
id: attackList
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
anchors.top: parent.top
|
||||
padding: 1
|
||||
size: 500 150
|
||||
margin-left: 3
|
||||
margin-top: 3
|
||||
margin-left: 3
|
||||
vertical-scrollbar: attackListScrollBar
|
||||
|
||||
VerticalScrollBar
|
||||
id: attackListScrollBar
|
||||
anchors.top: attackList.top
|
||||
anchors.bottom: attackList.bottom
|
||||
anchors.right: attackList.right
|
||||
step: 14
|
||||
pixels-scroll: true
|
||||
|
||||
Label
|
||||
id: category
|
||||
anchors.top: attackList.bottom
|
||||
anchors.left: attackList.left
|
||||
anchors.right: attackList.right
|
||||
text-align: center
|
||||
margin-top: 5
|
||||
image-source: /images/ui/panel_flat
|
||||
image-border: 5
|
||||
height: 21
|
||||
margin-left: 25
|
||||
margin-right: 25
|
||||
|
||||
NextButton
|
||||
id: categoryNext
|
||||
anchors.left: category.right
|
||||
anchors.verticalCenter: category.verticalCenter
|
||||
margin-left: 10
|
||||
|
||||
PreviousButton
|
||||
id: categoryPrev
|
||||
anchors.right: category.left
|
||||
anchors.verticalCenter: category.verticalCenter
|
||||
margin-right: 10
|
||||
|
||||
Label
|
||||
id: parameter1
|
||||
anchors.top: category.bottom
|
||||
anchors.left: category.left
|
||||
anchors.right: category.horizontalCenter
|
||||
margin-top: 5
|
||||
margin-right: 25
|
||||
height: 21
|
||||
text-align: center
|
||||
image-source: /images/ui/panel_flat
|
||||
image-border: 5
|
||||
|
||||
NextButton
|
||||
id: parameter1Next
|
||||
anchors.left: parameter1.right
|
||||
anchors.verticalCenter: parameter1.verticalCenter
|
||||
margin-left: 10
|
||||
|
||||
PreviousButton
|
||||
id: parameter1Prev
|
||||
anchors.right: parameter1.left
|
||||
anchors.verticalCenter: parameter1.verticalCenter
|
||||
margin-right: 10
|
||||
|
||||
Label
|
||||
id: parameter2
|
||||
anchors.top: category.bottom
|
||||
anchors.left: category.horizontalCenter
|
||||
anchors.right: category.right
|
||||
margin-top: 5
|
||||
margin-left: 25
|
||||
height: 21
|
||||
text-align: center
|
||||
image-source: /images/ui/panel_flat
|
||||
image-border: 5
|
||||
|
||||
NextButton
|
||||
id: parameter2Next
|
||||
anchors.left: parameter2.right
|
||||
anchors.verticalCenter: parameter2.verticalCenter
|
||||
margin-left: 10
|
||||
|
||||
PreviousButton
|
||||
id: parameter2Prev
|
||||
anchors.right: parameter2.left
|
||||
anchors.verticalCenter: parameter2.verticalCenter
|
||||
margin-right: 10
|
||||
|
||||
TextEdit
|
||||
id: spellFormula
|
||||
anchors.left: parent.left
|
||||
anchors.top: parameter2Prev.bottom
|
||||
margin-top: 27
|
||||
margin-left: 5
|
||||
width: 200
|
||||
|
||||
Label
|
||||
id: spellDescription
|
||||
anchors.left: prev.left
|
||||
anchors.right: prev.right
|
||||
anchors.bottom: prev.top
|
||||
margin-bottom: 2
|
||||
text-align: center
|
||||
text: Insert Spell Formula Below
|
||||
|
||||
BotItem
|
||||
id: itemId
|
||||
anchors.left: parent.left
|
||||
anchors.top: parameter2Prev.bottom
|
||||
margin-top: 20
|
||||
margin-left: 5
|
||||
|
||||
Label
|
||||
id: itemDescription
|
||||
anchors.left: itemId.right
|
||||
margin-left: 5
|
||||
anchors.verticalCenter: itemId.verticalCenter
|
||||
text: < insert id or drag item here
|
||||
|
||||
Label
|
||||
anchors.left: parameter2Prev.left
|
||||
anchors.top: parameter2Prev.bottom
|
||||
margin-top: 10
|
||||
text-align: center
|
||||
text: Min Monsters:
|
||||
|
||||
TextEdit
|
||||
id: minMonsters
|
||||
anchors.left: prev.right
|
||||
anchors.verticalCenter: prev.verticalCenter
|
||||
margin-left: 5
|
||||
width: 30
|
||||
|
||||
Label
|
||||
anchors.left: parameter2Prev.left
|
||||
anchors.top: prev.bottom
|
||||
margin-top: 10
|
||||
text-align: center
|
||||
text: Min Mana%:
|
||||
|
||||
TextEdit
|
||||
id: minMana
|
||||
anchors.left: minMonsters.left
|
||||
anchors.verticalCenter: prev.verticalCenter
|
||||
width: 30
|
||||
|
||||
CheckBox
|
||||
id: pvpSpell
|
||||
anchors.right: minMana.right
|
||||
anchors.top: minMana.bottom
|
||||
width: 100
|
||||
margin-left: 30
|
||||
margin-top: 6
|
||||
text: Spell for PVP
|
||||
|
||||
Button
|
||||
id: addButton
|
||||
anchors.right: CloseButton.right
|
||||
anchors.bottom: BottomSeparator.top
|
||||
text-align: center
|
||||
text: Add
|
||||
margin-bottom: 10
|
||||
size: 80 20
|
||||
margin-right: 15
|
||||
|
||||
Button
|
||||
id: MoveUp
|
||||
anchors.right: prev.right
|
||||
anchors.bottom: prev.top
|
||||
size: 80 20
|
||||
text: Move Up
|
||||
margin-bottom: 2
|
||||
|
||||
Button
|
||||
id: MoveDown
|
||||
anchors.right: prev.right
|
||||
anchors.bottom: prev.top
|
||||
size: 80 20
|
||||
text: Move Down
|
||||
text-align: center
|
||||
margin-bottom: 2
|
||||
|
||||
CheckBox
|
||||
id: IgnoreMana
|
||||
anchors.verticalCenter: CloseButton.verticalCenter
|
||||
anchors.left: parent.left
|
||||
margin-left: 5
|
||||
width: 250
|
||||
text: Check RL Tibia mana cost
|
||||
|
||||
HorizontalSeparator
|
||||
id: BottomSeparator
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: CloseButton.top
|
||||
margin-bottom: 8
|
||||
|
||||
Button
|
||||
id: CloseButton
|
||||
!text: tr('Close')
|
||||
font: cipsoftFont
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
size: 45 21
|
||||
margin-top: 15
|
||||
margin-right: 5
|
@@ -1,145 +0,0 @@
|
||||
BotServerData < Panel
|
||||
size: 340 70
|
||||
image-source: /images/ui/window
|
||||
image-border: 6
|
||||
padding: 3
|
||||
|
||||
Label
|
||||
id: label
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
text-align: center
|
||||
!text: tr("BotServer Data")
|
||||
|
||||
Label
|
||||
id: label
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
margin-top: 23
|
||||
text-align: center
|
||||
text: Channel Name:
|
||||
margin-left: 6
|
||||
|
||||
TextEdit
|
||||
id: Channel
|
||||
anchors.top: parent.top
|
||||
anchors.left: prev.right
|
||||
margin-top: 20
|
||||
width: 150
|
||||
margin-left: 5
|
||||
text-align: center
|
||||
|
||||
Button
|
||||
id: Random
|
||||
anchors.left: prev.right
|
||||
anchors.top: prev.top
|
||||
anchors.right: parent.right
|
||||
text-align: center
|
||||
text: Randomize
|
||||
margin-left: 6
|
||||
margin-right: 6
|
||||
|
||||
Label
|
||||
id: label
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: parent.bottom
|
||||
margin-left: 6
|
||||
margin-bottom: 4
|
||||
text-align: center
|
||||
text: Status:
|
||||
|
||||
BotLabel
|
||||
id: ServerStatus
|
||||
anchors.left: prev.right
|
||||
anchors.bottom: parent.bottom
|
||||
margin-left: 10
|
||||
margin-bottom: 4
|
||||
text-align: center
|
||||
text: CONNECTED
|
||||
|
||||
BotLabel
|
||||
id: Participants
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
margin-right: 8
|
||||
margin-bottom: 4
|
||||
text-align: center
|
||||
|
||||
Label
|
||||
id: label
|
||||
anchors.right: Participants.left
|
||||
anchors.bottom: parent.bottom
|
||||
margin-right: 10
|
||||
margin-bottom: 4
|
||||
text-align: center
|
||||
text: Members:
|
||||
|
||||
FeaturePanel < Panel
|
||||
size: 340 150
|
||||
image-source: /images/ui/panel_flat
|
||||
image-border: 5
|
||||
padding: 3
|
||||
|
||||
Label
|
||||
id: title
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
text-align: center
|
||||
text: Features
|
||||
|
||||
HorizontalSeparator
|
||||
id: sep
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
anchors.right: parent.right
|
||||
margin-top: 2
|
||||
|
||||
BotSwitch
|
||||
id: Feature1
|
||||
anchors.top: prev.bottom
|
||||
anchors.left: parent.left
|
||||
margin-left: 3
|
||||
margin-top: 5
|
||||
text: Mana info
|
||||
|
||||
BotSwitch
|
||||
id: Feature2
|
||||
anchors.top: sep.bottom
|
||||
anchors.left: prev.right
|
||||
margin-top: 5
|
||||
margin-left: 5
|
||||
text: MWall info
|
||||
|
||||
BotServerWindow < MainWindow
|
||||
!text: tr('BotServer')
|
||||
size: 370 310
|
||||
@onEscape: self:hide()
|
||||
|
||||
BotServerData
|
||||
id: Data
|
||||
anchors.top: parent.top
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
|
||||
FeaturePanel
|
||||
id: Features
|
||||
anchors.top: prev.bottom
|
||||
anchors.horizontalCenter: parent.horizontalCenter
|
||||
margin-top: 10
|
||||
|
||||
HorizontalSeparator
|
||||
id: separator
|
||||
anchors.right: parent.right
|
||||
anchors.left: parent.left
|
||||
anchors.bottom: closeButton.top
|
||||
margin-bottom: 8
|
||||
|
||||
Button
|
||||
id: closeButton
|
||||
!text: tr('Close')
|
||||
font: cipsoftFont
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: parent.bottom
|
||||
size: 45 21
|
||||
margin-top: 15
|
||||
margin-right: 5
|
@@ -1,76 +0,0 @@
|
||||
setDefaultTab("Tools")
|
||||
UI.Label("-- [[ ANTI PUSH Panel ]] --")
|
||||
addSeparator()
|
||||
local panelName = "castle"
|
||||
local ui = setupUI([[
|
||||
Panel
|
||||
height: 40
|
||||
|
||||
BotItem
|
||||
id: item
|
||||
anchors.top: parent.top
|
||||
anchors.left: parent.left
|
||||
margin-top: 2
|
||||
|
||||
BotSwitch
|
||||
id: skip
|
||||
anchors.top: parent.top
|
||||
anchors.left: item.right
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: item.verticalCenter
|
||||
text-align: center
|
||||
!text: tr('Skip Tiles Near Target')
|
||||
margin-left: 2
|
||||
|
||||
BotSwitch
|
||||
id: title
|
||||
anchors.top: item.verticalCenter
|
||||
anchors.left: item.right
|
||||
anchors.right: parent.right
|
||||
anchors.bottom: item.bottom
|
||||
text-align: center
|
||||
!text: tr('Drop Items Around')
|
||||
margin-left: 2
|
||||
|
||||
]], parent)
|
||||
ui:setId(panelName)
|
||||
|
||||
if not storage[panelName] then
|
||||
storage[panelName] = {
|
||||
id = 2983,
|
||||
around = false,
|
||||
enabled = false
|
||||
}
|
||||
end
|
||||
|
||||
ui.skip:setOn(storage[panelName].around)
|
||||
ui.skip.onClick = function(widget)
|
||||
storage[panelName].around = not storage[panelName].around
|
||||
widget:setOn(storage[panelName].around)
|
||||
end
|
||||
ui.title:setOn(storage[panelName].enabled)
|
||||
ui.title.onClick = function(widget)
|
||||
storage[panelName].enabled = not storage[panelName].enabled
|
||||
widget:setOn(storage[panelName].enabled)
|
||||
end
|
||||
|
||||
ui.item:setItemId(storage[panelName].id)
|
||||
ui.item.onItemChange = function(widget)
|
||||
storage[panelName].id = widget:getItemId()
|
||||
end
|
||||
|
||||
|
||||
macro(175, function()
|
||||
if storage[panelName].enabled then
|
||||
local blockItem = findItem(storage[panelName].id)
|
||||
for _, tile in pairs(g_map.getTiles(posz())) do
|
||||
if distanceFromPlayer(tile:getPosition()) == 1 and tile:isWalkable() and tile:getTopUseThing():getId() ~= storage[panelName].id and (not storage[panelName].around or not target() or (target() and getDistanceBetween(targetPos(), tile:getPosition() > 1))) then
|
||||
g_game.move(blockItem, tile:getPosition())
|
||||
return
|
||||
end
|
||||
end
|
||||
storage[panelName].enabled = false
|
||||
ui.title:setOn(storage[panelName].enabled)
|
||||
end
|
||||
end)
|
||||
addSeparator()
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user