You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1397 lines
39 KiB

<?xml version="1.0" encoding="iso-8859-1"?>
<!DOCTYPE muclient>
<!-- Saved on Saturday, December 29, 2018, 1:32 PM -->
<!-- MuClient version 5.06-pre -->
<!-- Plugin "atlas" generated by Plugin Wizard -->
<muclient>
<plugin
name="atlas"
author="Durel"
id="b16d151337abc0f39a22a37c"
language="Lua"
purpose="Titan L3 assistant"
save_state="y"
date_written="2018-12-29 1:32:52"
requires="5.06"
version="1.0"
>
<description trim="y">
<![CDATA[
The "atlas" plugin simplifies movement and mapping of Titan Level 3.
]]>
</description>
</plugin>
<!-- Get our standard constants -->
<include name="constants.lua"/>
<!-- Triggers -->
<triggers>
<trigger
enabled="y"
expand_variables="y"
keep_evaluating="y"
ignore_case="y"
match="^\(Group\) (.*):[ ]+.(marco|dirs|path)[\?]?([ ]+[0-9]+)?[ ]*.$"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.marcoDetect(Trim("%1"), Trim("%3"))</send>
</trigger>
<trigger
enabled="y"
expand_variables="y"
keep_evaluating="y"
ignore_case="y"
match="^({repop})?The Mountain rumbles as the Titans rise again.$"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.repopDetect()</send>
</trigger>
</triggers>
<!-- Aliases -->
<aliases>
<alias
match="^[ ]*atlas[ ]+path[ ]+([^ ]+)[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.pathSet("%1")</send>
</alias>
<alias
match="^[ ]*atlas[ ]+display[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.pathDisplay()</send>
</alias>
<alias
match="^[ ]*atlas[ ]+default[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.pathSet(atlas.defaultPath)</send>
</alias>
<alias
match="^[ ]*atlas[ ]+moat[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.pathSet(atlas.moatPath)</send>
</alias>
<alias
match="^[ ]*atlas[ ]+master[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.pathSet(atlas.masterPath)</send>
</alias>
<alias
match="^[ ]*atlas[ ]+next([ ]+[^ ]+)?[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.next(Trim("%1"))</send>
</alias>
<alias
match="^[ ]*atlas[ ]+exit([ ]+[^ ]+)?[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.exit(Trim("%1"))</send>
</alias>
<alias
match="^[ ]*atlas[ ]+portal([ ]+[^ ]+)?[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.portal(Trim("%1"))</send>
</alias>
<alias
match="^[ ]*atlas[ ]+safe([ ]+[^ ]+)?[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.safe(Trim("%1"))</send>
</alias>
<alias
match="^[ ]*atlas[ ]+report([ ]+[^ ]+)?[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.report(nil, Trim("%1"), nil)</send>
</alias>
<alias
match="^[ ]*atlas[ ]+marco[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.marco()</send>
</alias>
<alias
match="^[ ]*atlas[ ]+polo[ ]+(on|off)[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.poloSet("%1")</send>
</alias>
<alias
match="^[ ]*atlas[ ]+command([ ]+.*)?$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.cmdSet("%1")</send>
</alias>
<alias
match="^[ ]*atlas[ ]+version[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.version()</send>
</alias>
<alias
match="^[ ]*atlas[ ]+route[ ]+([0-9]+)[ ]+([0-9]+)[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.route("%1", "%2")</send>
</alias>
<alias
match="^[ ]*atlas[ ]+commlog[ ]+(on|off)[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.commlogSet("%1")</send>
</alias>
<alias
match="^[ ]*atlas[ ]+exploder[ ]+(on|off)[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.exploderSet("%1")</send>
</alias>
<alias
match="^[ ]*atlas[ ]+zarconis[ ]+(on|off)[ ]*$"
enabled="y"
regexp="y"
send_to="12"
sequence="100"
>
<send>atlas.zarconisSet("%1")</send>
</alias>
<alias
match="^[ ]*atlas(|[ ]+.*)$"
enabled="y"
regexp="y"
send_to="12"
sequence="1000"
>
<send>atlas.help()</send>
</alias>
</aliases>
<!-- Variables -->
<!-- Script -->
<script>
<![CDATA[
--[[
----------------------------------------------------------------------------------------------------------
Table of Contents
----------------------------------------------------------------------------------------------------------
Dependencies and Globals
------------------------
MUSH callbacks
--------------
function OnPluginInstall()
function OnPluginClose()
function OnPluginConnect()
function OnPluginDisconnect()
function OnPluginEnable()
function OnPluginDisable()
function OnPluginBroadcast(msg, id, name, text)
Plugin init/de-init
-------------------
function atlas.init()
function atlas.fini()
Path options
------------
function atlas.pathSet(path)
function atlas.pathGet()
function atlas.pathDisplay()
function atlas.pathApply(userPath)
Movement options
----------------
function atlas.next(fromRoom)
function atlas.exit(fromRoom)
function atlas.portal(fromRoom)
function atlas.safe(fromRoom)
function atlas.move()
Routing and reporting functions
-------------------------------
function atlas.report(startRoom, userChannel, requestor)
function atlas.marco()
function atlas.marcoDetect(caller, roomId)
function atlas.poloSet(enable)
function atlas.poloGet()
function atlas.route(startRoom, endRoom)
function atlas.shortestPath(startRoom, endRoom)
function atlas.safestPath(startRoom, endRoom)
function atlas.findPath(startRoom, endRoom, currentRooms, roomsToAvoid)
function atlas.repopDetect()
function atlas.unexploredReset()
function atlas.unexploredUpdate()
Advanced options
----------------
function atlas.cmdSet(commands)
function atlas.cmdGet()
function atlas.commlogSet(enable)
function atlas.commlogGet()
function atlas.exploderSet(enable)
function atlas.exploderGet()
function atlas.exploderInit()
function atlas.exploderAim(target)
function atlas.zarconisSet(enable)
function atlas.zarconisGet()
function atlas.zarconisInit()
function atlas.zarconisGive()
function atlas.zarconisReceive()
Plugin info
-----------
function atlas.version()
function atlas.help()
Core helper functions
---------------------
function atlas.printFormat(msg)
function atlas.printColors(msg)
function atlas.print(msg)
function atlas.error(msg)
function atlas.getRoom()
function atlas.getRoomId()
function atlas.roomIdToRoom(roomId)
function atlas.getName()
function atlas.inCombat()
function atlas.commLog(msg)
function atlas.isWordInString(word, field)
--]]
----------------------------------------------------------------------------------------------------------
-- Dependencies
----------------------------------------------------------------------------------------------------------
require "gmcphelper"
require "wait"
require "check"
require "tprint"
dofile(GetInfo(60) .. "aardwolf_colors.lua")
----------------------------------------------------------------------------------------------------------
-- Global vars and tables
----------------------------------------------------------------------------------------------------------
atlas = {}
atlas.name = "ATLAS"
atlas.ver = "1.0.0"
atlas.defaultPath = "seedsdsdwwwwdnueeeedwwwwundee"
atlas.moatPath = "swwdsdnendnwndswwwwnun"
atlas.masterPath = "seedsdsdwwwwdnueeeedwxuwwwundee"
atlas.rooms = {}
atlas.rooms[0] = { r = 38310, w = -1, e = -1, s = 3, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[1] = { r = 38302, w = -1, e = 2, s = 6, n = -1, u = 25, d = 5, x = nil }
atlas.rooms[2] = { r = 38301, w = 1, e = 3, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[3] = { r = 38285, w = 2, e = 4, s = 8, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[4] = { r = 38286, w = 3, e = 5, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[5] = { r = 38293, w = 4, e = -1, s = 10, n = -1, u = 1, d = 23, x = nil }
atlas.rooms[6] = { r = 38303, w = -1, e = 7, s = -1, n = 1, u = 26, d = 11, x = nil }
atlas.rooms[7] = { r = 38300, w = 6, e = 8, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[8] = { r = 38284, w = 7, e = 9, s = -1, n = 3, u = -1, d = 13, x = nil }
atlas.rooms[9] = { r = 38287, w = 8, e = 10, s = -1, n = -1, u = -1, d = -1, x = {29, "open vault; d; get band; keep band"} } -- IN
atlas.rooms[10] = { r = 38292, w = 9, e = -1, s = -1, n = 5, u = 15, d = 24, x = nil }
atlas.rooms[11] = { r = 38304, w = -1, e = 12, s = 16, n = -1, u = 6, d = 27, x = nil }
atlas.rooms[12] = { r = 38299, w = 11, e = 13, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[13] = { r = 38283, w = 12, e = 14, s = 18, n = -1, u = 8, d = -1, x = nil }
atlas.rooms[14] = { r = 38288, w = 13, e = 15, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[15] = { r = 38291, w = 14, e = -1, s = 20, n = -1, u = 21, d = 10, x = nil }
atlas.rooms[16] = { r = 38305, w = -1, e = 17, s = -1, n = 11, u = 20, d = 28, x = nil }
atlas.rooms[17] = { r = 38298, w = 16, e = 18, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[18] = { r = 38282, w = 17, e = 19, s = -1, n = 13, u = -1, d = -1, x = nil }
atlas.rooms[19] = { r = 38289, w = 18, e = 20, s = -1, n = -1, u = -1, d = -1, x = nil }
atlas.rooms[20] = { r = 38290, w = 19, e = -1, s = -1, n = 15, u = 22, d = 16, x = nil }
atlas.rooms[21] = { r = 38296, w = -1, e = -1, s = 22, n = -1, u = 24, d = 15, x = {30, "open door; e"} } -- IN
atlas.rooms[22] = { r = 38297, w = -1, e = 25, s = 23, n = 21, u = -1, d = 20, x = nil }
atlas.rooms[23] = { r = 38294, w = -1, e = 28, s = 24, n = 22, u = 5, d = -1, x = nil }
atlas.rooms[24] = { r = 38295, w = -1, e = -1, s = -1, n = 23, u = 10, d = 21, x = nil }
atlas.rooms[25] = { r = 38309, w = 22, e = -1, s = 26, n = -1, u = 28, d = 1, x = nil }
atlas.rooms[26] = { r = 38308, w = -1, e = -1, s = -1, n = 25, u = 27, d = 6, x = {31, "open door; w"} } -- IN
atlas.rooms[27] = { r = 38307, w = -1, e = -1, s = 28, n = -1, u = 11, d = 26, x = nil }
atlas.rooms[28] = { r = 38306, w = 23, e = -1, s = -1, n = 27, u = 16, d = 25, x = nil }
atlas.rooms[29] = { r = 38313, w = -1, e = -1, s = -1, n = -1, u = 9, d = -1, x = nil }
atlas.rooms[30] = { r = 38312, w = -1, e = -1, s = -1, n = -1, u = -1, d = -1, x = {21, "open door; w"} } -- OUT
atlas.rooms[31] = { r = 38311, w = -1, e = -1, s = -1, n = -1, u = -1, d = -1, x = {26, "open door; e"} } -- OUT
atlas.minRoom = 38282
atlas.maxRoom = 38313
----------------------------------------------------------------------------------------------------------
-- MUSH callbacks and hooks
----------------------------------------------------------------------------------------------------------
function OnPluginInstall()
atlas.init()
end -- OnPluginInstall
function OnPluginClose()
atlas.fini()
end -- OnPluginClose
function OnPluginConnect()
--atlas.print("OnPluginConnect!")
end -- OnPluginConnect
function OnPluginDisconnect()
--atlas.print("OnPluginDisconnect!")
end -- OnPluginDisconnect
function OnPluginEnable()
--atlas.print("OnPluginEnable!")
atlas.print("@GENABLED@W")
end -- OnPluginEnable
function OnPluginDisable()
--atlas.print("OnPluginDisable!")
atlas.print("@RENABLED@W")
end -- OnPluginDisable
function OnPluginBroadcast(msg, id, name, text)
if id == "3e7dedbe37e44942dd46d264" then -- message from the GMCP Handler
if (text == "room.info") then
atlas.unexploredUpdate(true)
end
end
end
----------------------------------------------------------------------------------------------------------
-- Plugin init/de-init
----------------------------------------------------------------------------------------------------------
function atlas.init()
-- Display the helpfile when the plugin loads
atlas.help()
atlas.currentArea = ""
atlas.pathApply()
atlas.unexploredReset()
atlas.exploderInit()
atlas.zarconisInit()
end -- atlas.init
function atlas.fini()
-- placeholder for now...
end -- atlas.fini
----------------------------------------------------------------------------------------------------------
-- Path definition and display functions
----------------------------------------------------------------------------------------------------------
function atlas.pathSet(path)
if (path == nil) or (path == "") then
atlas.error("atlas.pathSet: missing path")
else
if (atlas.pathApply(path) == 0) then
SetVariable("path", path)
end -- if
end -- if
end -- atlas.pathSet
function atlas.pathGet()
local path = GetVariable("path") or ""
if (path == "") then
path = atlas.defaultPath
atlas.pathSet(path)
end -- if
return path
end -- atlas.pathGet
function atlas.pathDisplay()
local path = atlas.pathGet()
if (path == nil) or (path == "") then
atlas.error("atlas.pathDisplay: missing path")
else
atlas.print("Current path = \"@C" .. path .. "@w\"")
atlas.print("Auto command = \"@C" .. (atlas.cmdGet() or "") .. "@w\"")
end -- if
end -- atlas.pathDisplay
function atlas.pathApply(userPath)
local path
if (userPath == nil) or (userPath == "") then
path = atlas.pathGet()
else
path = userPath
end -- if
if (path == nil) or (path == "") then
atlas.error("atlas.pathApply: missing path")
return 1
end -- if
atlas.print("Applying path " .. path)
atlas.nextDir = {}
local currentRoom = 0
for dir in path:gmatch("%a") do
if (dir ~= "w") and (dir ~= "e") and
(dir ~= "s") and (dir ~= "n") and
(dir ~= "u") and (dir ~= "d") and
(dir ~= "x") then
atlas.error("atlas.pathApply: attempted to apply direction other than w,e,s,n,u,d,x")
return 1
end -- if
local entry = atlas.rooms[currentRoom]
if (entry == nil) or (entry.r == nil) or (entry.r == "") then
atlas.error("atlas.pathApply: invalid path \"" .. path .. "\"")
return 1
end -- if
if (atlas.nextDir[currentRoom] == nil) then
atlas.nextDir[currentRoom] = { index = 1, dirTable = {} }
end -- if
-- Determine what to send to the mud to move to the next room
if (dir == "x") then
-- Some rooms have special custom exits
table.insert(atlas.nextDir[currentRoom].dirTable, entry.x[2])
currentRoom = entry.x[1]
else
table.insert(atlas.nextDir[currentRoom].dirTable, dir)
currentRoom = atlas.rooms[currentRoom][dir]
end -- if
end -- for
return 0
end -- atlas.pathApply
----------------------------------------------------------------------------------------------------------
-- Movement options
----------------------------------------------------------------------------------------------------------
function atlas.next(fromRoom)
local room = -1
local roomId = -1
if (fromRoom ~= nil) and (fromRoom ~= "") then
room = tonumber(fromRoom or "") or -1
if (atlas.rooms[room] ~= nil) and (atlas.rooms[room].r ~= nil) then
roomId = atlas.rooms[room].r
end -- if
else
room, roomId = atlas.getRoom()
end -- if
if (atlas.nextDir == nil) then
atlas.pathApply()
end -- if
local dir = nil
local roomEntry = atlas.nextDir[room]
if (roomEntry ~= nil) then
dir = roomEntry.dirTable[roomEntry.index]
if (roomEntry.index >= #roomEntry.dirTable) then
roomEntry.index = 1
else
roomEntry.index = roomEntry.index + 1
end -- if
end -- if
if (dir == nil) or (dir == "") then
atlas.error("atlas.next: current room [@c" .. roomId .. "@w/@C" .. room ..
"@w] is not included in path")
return
end -- if
atlas.print("@GNEXT@w: Room [@c" .. roomId .. "@w/@C" .. room .. "@w] @W--> " .. dir .. "@w")
local cmds = atlas.cmdGet() or ""
if (cmds ~= nil) and (cmds ~= "") then
Execute(cmds)
end -- if
Execute(dir)
end -- atlas.next
function atlas.exit(startRoom)
return atlas.move("EXIT", startRoom, 3)
end -- atlas.exit
function atlas.portal(startRoom)
return atlas.move("PORTAL", startRoom, 18)
end -- atlas.exit
function atlas.safe(startRoom)
if (startRoom == nil) or (startRoom == "") then
startRoom, roomId = atlas.getRoom()
end -- if
-- Find the shortest routes to the three safe rooms
local vaultPath = atlas.shortestPath(startRoom, 29) or ""
local door1Path = atlas.shortestPath(startRoom, 30) or ""
local door2Path = atlas.shortestPath(startRoom, 31) or ""
-- Determine which safe room is closest
local vaultLen = string.len(vaultPath)
local door1Len = string.len(door1Path)
local door2Len = string.len(door2Path)
local endRoom = 0
local fullPath = ""
if (vaultLen <= door1Len) and (vaultLen <= door2Len) then
endRoom = 29
fullPath = vaultPath
elseif (door1Len <= door2Len) then
endRoom = 30
fullPath = door1Path
else
endRoom = 31
fullPath = door2Path
end -- if
if (fullPath ~= "") then
atlas.print("Moving toward safe room " .. endRoom .. ", path=\"" .. fullPath .. "\"")
atlas.move("SAFE", startRoom, endRoom)
end -- if
end -- atlas.safe
function atlas.move(desc, src, dst)
local room = tonumber(src or "") or -1
local roomId = -1
local descFmt = (desc or "NONE")
local dstFmt = tonumber(dst or "") or -1
-- If the user specified a starting room (for testing), use it. Otherwise, use the current
-- room reported by gmcp as the starting room.
if (room ~= -1) then
if (atlas.rooms[room] ~= nil) and (atlas.rooms[room].r ~= nil) then
roomId = atlas.rooms[room].r
end -- if
else
room, roomId = atlas.getRoom()
end -- if
local route = atlas.shortestPath(room, dstFmt)
local dir
if (route ~= nil) and (route ~= "") then
dir = string.sub(route, 1, 1)
if (dir == "x") then
dir = atlas.rooms[room].x[2]
end -- if
elseif (room == dstFmt) then
atlas.print("You are already at the \"" .. descFmt .. "\" room")
return
else
atlas.error("atlas.move: could not find route from [@c" .. roomId .. "@w/@C" .. room ..
"@w] to " .. descFmt .. " at room " .. dstFmt)
return
end -- if
atlas.print("@G" .. descFmt .. "@w: Room [@c" .. roomId .. "@w/@C" .. room .. "@w] @W--> " .. dir .. "@w")
local cmds = atlas.cmdGet() or ""
if (cmds ~= nil) and (cmds ~= "") then
Execute(cmds)
end -- if
Execute(dir)
end -- atlas.move
----------------------------------------------------------------------------------------------------------
-- Routing and reporting functions
----------------------------------------------------------------------------------------------------------
atlas.channel = "gtell"
function atlas.report(startRoom, userChannel, requestor)
local room, roomId = atlas.getRoom()
local start = 0
if (startRoom ~= nil) then
start = tonumber(startRoom or "") or -1
end -- if
local shortestPath = atlas.shortestPath(start, room)
local safestPath = atlas.safestPath(start, room)
-- It is possible that there are multiple different paths that have the same length as the shortest
-- path (we simply stick with the first one we find). As a result, it is possible that our "safest"
-- path is the same length as our "shortest" path but uses different directions. In this case, we
-- change our shortest path to be the safest path since they are they same length and the safest
-- path is...well...safer.
if (safestPath ~= nil) and (safestPath ~= "") and
(shortestPath ~= nil) and (shortestPath ~= "") and
(string.len(safestPath) <= string.len(shortestPath)) then
shortestPath = safestPath
end -- if
local prefix = "@w" .. (requestor or "Salkin") .. " to [@c" .. roomId .. "@w/@C" .. room .. "@w]: "
local msg = ""
if (room == start) then
--msg = prefix .. "@WYou are already in the room!@w"
elseif (shortestPath == nil) or (shortestPath == "") then
msg = prefix .. "@RNo route found@w"
elseif (shortestPath == safestPath) then
msg = prefix .. "@G" .. shortestPath .. " @g(shortest and safest)@w"
elseif (safestPath == nil) or (safestPath == "") then
msg = prefix .. "@Y" .. shortestPath .. " @y(shortest but @Rnot safe@y)@w"
else
msg = prefix .. "@Y" .. shortestPath .. " @y(shortest)@w, @G" .. safestPath .. " @g(safest)@w"
end -- if
local channel = userChannel
if (channel == nil) or (channel == "") then
channel = atlas.channel
end -- if
if (msg ~= nil) and (msg ~= "") then
Execute(channel .. " " .. msg)
end -- if
end -- atlas.report
function atlas.marco()
local room, roomId = atlas.getRoom()
Execute(atlas.channel .. " marco " .. (roomId or "nil"))
end -- atlas.marco
function atlas.marcoDetect(caller, roomId)
-- Don't reply if an automated reply isn't enabled
local poloEnable = atlas.poloGet()
if (poloEnable ~= "on") then
return
end -- if
-- Don't reply if we aren't in titan L3
local currentRoom, currentRoomId = atlas.getRoom()
if (currentRoom == nil) or (currentRoom == "") or (currentRoom == -1) then
return
end -- if
-- Don't reply to your own marco requests
local userName, pretitle = atlas.getName()
local fullName = (pretitle or "") .. (userName or "")
if (caller == fullName) then
--atlas.print("Skipping polo for own request")
return
end -- if
local requestor
local room = -1
if (roomId == nil) or (roomId == "") then
room = 0
else
room = atlas.roomIdToRoom(tonumber(roomId or ""))
requestor = caller -- Report directions relative to the caller (if one exists)
end -- if
--atlas.print("Detected request for path from room " .. room)
atlas.report(room, nil, requestor)
end -- atlas.marcoDetect
function atlas.poloSet(enable)
if (enable ~= "on") and (enable ~= "off") then
atlas.error("atlas.poloSet: invalid polo mode \"" .. (enable or "nil") .. "\"")
return
end -- if
SetVariable("poloState", enable)
local msg
if (enable == "on") then
msg = "@GENABLED@w"
else
msg = "@RDISABLED@w"
end -- if
atlas.print("Automated path reporting is " .. msg)
end -- atlas.poloSet
function atlas.poloGet()
return (GetVariable("poloState") or "")
end -- atlas.poloGet
function atlas.route(startRoom, endRoom)
local shortestPath = atlas.shortestPath(startRoom, endRoom)
local safestPath = atlas.safestPath(startRoom, endRoom)
atlas.print("atlas.route: " .. (startRoom or "nil") .. " to " .. (endRoom or "nil") .. ": shortest=" ..
(shortestPath or "None") .. ", safest=" .. (safestPath or "None"))
end -- atlas.route
function atlas.shortestPath(startRoom, endRoom)
return atlas.findPath(startRoom, endRoom, nil, "")
end -- atlas.shortestPath
function atlas.safestPath(startRoom, endRoom)
local unexploredRooms = ""
for room,entry in pairs(atlas.rooms) do
if (entry.isExplored == nil) or (entry.isExplored == false) then
unexploredRooms = unexploredRooms .. " " .. room
end -- if
end -- for
--atlas.print("atlas.safestPath: " .. (startRoom or "nil") .. " to " .. (endRoom or "nil") ..
-- " avoiding rooms \"" .. unexploredRooms .. "\"")
return atlas.findPath(startRoom, endRoom, nil, unexploredRooms)
end -- atlas.safestPath
-- We use "roomsToAvoid" to detect cycles (don't want to run in circles) and to also pass
-- in unexplored rooms to find routes that only include rooms we have seen since the last
-- repop.
function atlas.findPath(startRoom, endRoom, currentPath, roomsToAvoid)
local src = tonumber(startRoom or "") or -1
local dst = tonumber(endRoom or "") or -1
local shortestPath = nil
local maxDepth = 10
--atlas.print("src=" .. src .. ", dst=" .. dst .. ", roomsToAvoid=\"" .. (roomsToAvoid or "nil") .. "\"")
-- Prune it so that we don't search forever (relatively speaking)
if (currentPath ~= nil) and (string.len(currentPath) > maxDepth) then
return nil
end -- if
if (src == -1) or (dst == -1) then
atlas.error("atlas.findPath: invalid source or destination room")
return nil
end -- if
if (src == dst) then
--atlas.print("Found valid path at \"" .. (currentPath or "nil") .. "\"")
return currentPath
end -- if
local dirList = "w e s n u d x"
for dir in dirList:gmatch("%S+") do
--atlas.print("dir=\"" .. dir .. "\", nextDir=\"" .. (atlas.rooms[src][dir] or "nil"))
if (atlas.rooms[src] ~= nil) then
local nextRoom
if (dir == "x") then
if (atlas.rooms[src].x == nil) then
nextRoom = -1
else
nextRoom = atlas.rooms[src].x[1]
end -- if
else
nextRoom = atlas.rooms[src][dir] or -1
end -- if
if (nextRoom ~= -1) and (not atlas.isWordInString(string.format("%d", nextRoom), roomsToAvoid)) then
local updatedPath = (currentPath or "") .. dir
local updatedRoomsHit = (roomsToAvoid or "") .. " " .. nextRoom
local path = atlas.findPath(nextRoom, dst, updatedPath, updatedRoomsHit)
if (path ~= nil) and ((shortestPath == nil) or (string.len(path) < string.len(shortestPath))) then
--atlas.print("Update shortest path: \"" .. (shortestPath or "nil") .. "\" to \"" .. path .. "\"")
shortestPath = path
end -- if
end -- if
end -- if
end -- for
if (shortestPath ~= nil) then
--atlas.print("atlas.findPath: start=" .. src .. ", end=" .. dst .. ", shortest=" .. shortestPath)
end -- if
return shortestPath
end -- atlas.findPath
function atlas.repopDetect()
atlas.print("Titan repopped!")
atlas.unexploredReset()
end -- atlas.repopDetect
function atlas.unexploredReset()
for room,entry in pairs(atlas.rooms) do
atlas.rooms[room].isExplored = false
end -- for
atlas.rooms[0].isExplored = true -- First room is always safe
-- If you are in titan, make sure your current room is marked as explored
atlas.unexploredUpdate(false)
end -- atlas.unexploredReset
function atlas.unexploredUpdate(doAreaCheck)
local roomInfo = gmcp("room.info")
if (roomInfo == nil) then
return
end -- if
-- Reset our unexplored rooms each time we enter titan (it may have repopped while we were gone)
if (doAreaCheck) then
local area = roomInfo.zone
if (area ~= atlas.currentArea) then
if (area == "titan") then
-- We just entered titan so clean out any previous explored rooms
atlas.unexploredReset()
end -- if
atlas.currentArea = area
end -- if
end -- if
-- If we just explored one of the rooms in titan, update the unexplored list accordingly
local roomId = tonumber(roomInfo.num or "") or -1
if (roomId >= atlas.minRoom) and (roomId <= atlas.maxRoom) then
for i, entry in pairs(atlas.rooms) do
if (entry.r == roomId) then
entry.isExplored = true
--atlas.print("Explored room " .. roomId)
break
end -- if
end -- for
end -- if
end -- atlas.unexploredUpdate
----------------------------------------------------------------------------------------------------------
-- Advanced options
----------------------------------------------------------------------------------------------------------
function atlas.cmdSet(commands)
local preMoveCommands = Trim(commands or "")
SetVariable("atlasPreMoveCommands", preMoveCommands)
atlas.print("Set commands to: \"@C" .. preMoveCommands .. "@w\"")
end -- atlas.cmdSet
function atlas.cmdGet()
local commands = GetVariable("atlasPreMoveCommands") or ""
return commands
end -- atlas.cmdGet
function atlas.commlogSet(enable)
if (enable ~= "on") and (enable ~= "off") then
atlas.error("atlas.commlogSet: invalid commlog mode \"" .. (enable or "nil") .. "\"")
return
end -- if
SetVariable("commlogState", enable)
local msg
if (enable == "on") then
msg = "@GENABLED@w"
else
msg = "@RDISABLED@w"
end -- if
atlas.print("Mirroring to communication log is " .. msg)
end -- atlas.commlog
function atlas.commlogGet()
return (GetVariable("commlogState") or "")
end -- atlas.commlogGet
function atlas.exploderSet(enable)
if (enable ~= "on") and (enable ~= "off") then
atlas.error("atlas.exploderSet: invalid exploder mode \"" .. (enable or "nil") .. "\"")
return
end -- if
SetVariable("exploderState", enable)
local msg
if (enable == "on") then
msg = "@GENABLED@w"
EnableTrigger(atlasExploderTrigName, true)
else
msg = "@RDISABLED@w"
EnableTrigger(atlasExploderTrigName, false)
end -- if
atlas.print("Auto-targeting exploders is " .. msg)
end -- atlas.exploderSet
function atlas.exploderGet()
return (GetVariable("exploderState") or "")
end -- atlas.exploderGet
atlasExploderTrigName = "atlasExploderTrigger"
atlasSiegeLine = "This Titan has morphed into a massive siege weapon for the upcoming assault."
atlasEnergyLine = "Your entire body tingles and instruments begin going haywire near this Titan."
function atlas.exploderInit()
AddTriggerEx(atlasExploderTrigName,
"^(\\(.*\\) )*(" .. atlasSiegeLine .. "|" .. atlasEnergyLine .. ")$",
"atlas.exploderAim(\"%2\")",
trigger_flag.RegularExpression + trigger_flag.Replace,
custom_colour.NoChange, 0, "", "", sendto.script, 0)
if (atlas.exploderGet() == "on") then
EnableTrigger(atlasExploderTrigName, true)
end -- if
end -- atlas.exploderInit
function atlas.exploderAim(line)
local target = ""
if (line == atlasSiegeLine) then
target = "siege"
elseif (line == atlasEnergyLine) then
target = "energy"
else
atlas.error("atlas.exploderAim: Invalid target line \"" .. (line or "nil") .. "\"")
end -- if
--atlas.print("Aiming for target \"" .. (target or "nil") .. "\"")
if (target ~= nil) and (target ~= "") then
Execute("aim " .. target)
end -- if
end -- atlas.exploderAim
function atlas.zarconisSet(enable)
if (enable ~= "on") and (enable ~= "off") then
atlas.error("atlas.zarconisSet: invalid zarconis mode \"" .. (enable or "nil") .. "\"")
return
end -- if
SetVariable("zarconisState", enable)
local msg
if (enable == "on") then
msg = "@GENABLED@w"
EnableTrigger(atlasZarconisGiveTrigName, true)
EnableTrigger(atlasZarconisReceiveTrigName, true)
else
msg = "@RDISABLED@w"
EnableTrigger(atlasZarconisGiveTrigName, false)
EnableTrigger(atlasZarconisReceiveTrigName, false)
end -- if
atlas.print("Zarconis letter delivery is " .. msg)
end -- atlas.zarconis
function atlas.zarconisGet()
return (GetVariable("zarconisState") or "")
end -- atlas.zarconisGet
atlasZarconisGiveTrigName = "atlasZarconisGiveTrigger"
atlasZarconisReceiveTrigName = "atlasZarconisReceiveTrigger"
function atlas.zarconisInit()
-- As the "Titan" dies, the illusion fades to reveal Zarconis!
AddTriggerEx(atlasZarconisGiveTrigName,
"^As the \"Titan\" dies, the illusion fades to reveal Zarconis!$",
"atlas.zarconisGive()",
trigger_flag.RegularExpression + trigger_flag.Replace,
custom_colour.NoChange, 0, "", "", sendto.script, 0)
-- Zarconis of the Abyss says, "Thank you, I've been waiting anxiously for that letter. Update our records in the Vault, you'll need this key."
AddTriggerEx(atlasZarconisReceiveTrigName,
"^Zarconis of the Abyss says, \"Thank you, I've been waiting anxiously for that letter. Update our records in the Vault, you'll need this key\\.\"$",
"atlas.zarconisReceive()",
trigger_flag.RegularExpression + trigger_flag.Replace,
custom_colour.NoChange, 0, "", "", sendto.script, 0)
if (atlas.zarconisGet() == "on") then
EnableTrigger(atlasZarconisGiveTrigName, true)
EnableTrigger(atlasZarconisReceiveTrigName, true)
end -- if
end -- atlas.zarconisInit
function atlas.zarconisGive()
atlas.print("Delivering letter to zarconis@w")
Execute("unkeep letter")
Execute("give letter zarconis")
end -- atlas.zarconisGive
function atlas.zarconisReceive()
atlas.print("Received master key from Zarconis@w")
Execute("keep master")
-- Disable lettery deliver once we receive a master key
atlas.zarconisSet("off")
end -- atlas.zarconisReceive
----------------------------------------------------------------------------------------------------------
-- Plugin information
----------------------------------------------------------------------------------------------------------
function atlas.version()
atlas.print("Version: " .. atlas.ver)
end -- atlas.version
function atlas.help()
atlas.printColors([[
@x039------------------------------------------------------------------------------------------@w
@x039ATLAS: Automated Titan Level 3 Assistant@w
@x039------------------------------------------------------------------------------------------@w
@cPath options@w
@watlas @Wpath [dirs] @x173-- Set path through L3 (e.g., seedsds...)@w
@watlas @Wdefault @x173-- Set path to default value@w
@watlas @Wmoat @x173-- Set path to create a 9-room moat around the entrance@w
@watlas @Wmaster @x173-- Add vault room to default path (requires master key)@w
@watlas @Wdisplay @x173-- Print the current path through L3 and any auto-commands@w
@cMovement options@w
@watlas @Wnext @x173-- Move to the next room in the current path@w
@watlas @Wexit @x173-- Move to the next room toward the exit@w
@watlas @Wportal @x173-- Move to the next room toward the portal@w
@watlas @Wsafe @x173-- Move to the closest hidden nopk room (requires master key)@w
@cRequest and report directions@w
@watlas @Wreport @x173-- Report shortest path from L3 start to your current room@w
@watlas @Wmarco @x173-- Request a path from your room to a groupmate's location@w
@watlas @Wpolo [on|off] @x173-- Automatic reply when someone requests your location@w
@cAdvanced options@w
@watlas @Wcommand @x173-- Set pre-movement command(s) (e.g., "spellup;; quaff duff")@w
@watlas @Wcommlog [on|off] @x173-- Mirror atlas messages to the commlog (handy with L3 spam!)@w
@watlas @Wexploder [on|off] @x173-- Automatically target exploder titans@w
@watlas @Wzarconis [on|off] @x173-- Deliver letter to Zarconis (turns off after delivery)
@cPlugin info@w
@watlas @Wversion @x173-- Report the current version of this plugin@w
@watlas @Whelp @x173-- Display the usage you're reading right now...@w
@x039------------------------------------------------------------------------------------------@w
]])
end -- atlas.help
----------------------------------------------------------------------------------------------------------
-- Core helper functions
----------------------------------------------------------------------------------------------------------
function atlas.printFormat(msg)
local formattedMsg = ""
if (msg ~= nil) and (msg ~= "") then
local outerColor = "@x105"
local innerColor = "@x39"
formattedMsg = outerColor .. "[" .. innerColor .. atlas.name .. outerColor .. "]@w " .. msg .. "@w"
end -- if
return formattedMsg
end -- atlas.printFormat
function atlas.printColors(msg)
print(AnsiNote(stylesToANSI(ColoursToStyles(msg))))
end -- atlas.printColors
function atlas.print(msg)
if (msg ~= nil) and (msg ~= "") then
local formattedMsg = atlas.printFormat(msg)
atlas.printColors(formattedMsg)
-- If the user wants us to mirror messages to the commlog, do it :)
local commlogState = atlas.commlogGet()
if (commlogState == "on") then
atlas.commLog(formattedMsg)
end -- if
end -- if
end -- atlas.print()
function atlas.error(msg)
if (msg ~= nil) and (msg ~= "") then
atlas.print("@RERROR@w " .. msg)
end -- if
end -- atlas.error
function atlas.getRoom()
local roomId = tonumber(atlas.getRoomId() or "") or -1
local room = atlas.roomIdToRoom(roomId) or -1
return room, roomId
end -- atlas.getRoom()
function atlas.getRoomId()
return gmcp("room.info.num")
end -- atlas.getRoomId()
function atlas.roomIdToRoom(roomId)
local roomIdNum = tonumber(roomId or "") or -1
local room = -1
for r, entry in pairs(atlas.rooms) do
if (entry.r == roomIdNum) then
room = r
break
end -- if
end -- for
return room
end -- atlas.roomIdToRoom
function atlas.getName()
local name = ""
local pretitle = ""
local char = gmcp("char.base")
if (char ~= nil) then
name = (char.name or "nil")
pretitle = (char.pretitle or "nil")
end -- if
return name, pretitle
end -- atlas.getName
function atlas.inCombat()
local inCombat = false
local charStatus = gmcp("char.status")
if (charStatus ~= nil) and (charStatus.state == "8") then
inCombat = true
end -- if
return inCombat
end -- atlas.inCombat
function atlas.commLog(msg)
local clPlugin = "b555825a4a5700c35fa80780"
local clFunction = "storeFromOutside"
if (msg == nil) or (msg == "") then
print("atlas.commLog: Missing message parameter")
return error_code.eBadParameter
end -- if
local retval = CallPlugin(clPlugin, clFunction, msg)
if (retval == error_code.eNoSuchPlugin) then
print("atlas.commLog: target plugin does not exist")
elseif (retval == error_code.ePluginDisabled) then
print("atlas.commLog: target plugin is disabled")
elseif (retval == error_code.eNoSuchRoutine) then
print("atlas.commLog: target routine does not exist")
elseif (retval == error_code.eErrorCallingPluginRoutine) then
print("atlas.commLog: error calling plugin routine")
elseif (retval ~= error_code.eOK) then
print("atlas.commLog: Unknown return value from CallPlugin: " .. (retval or "nil"))
end -- if
return retval
end -- atlas.commLog
function atlas.isWordInString(word, field)
if (word == nil) or (word == "") or (field == nil) or (field == "") then
return false
end -- if
for element in field:gmatch("%S+") do
if (string.lower(word) == string.lower(element)) then
return true
end -- if
end -- for
return false
end -- atlas.isWordInString
]]>
</script>
<!-- Plugin help -->
<aliases>
<alias
script="OnHelp"
match="atlas:help"
enabled="y"
>
</alias>
</aliases>
<script>
<![CDATA[
function OnHelp ()
world.Note (world.GetPluginInfo (world.GetPluginID (), 3))
end
]]>
</script>
</muclient>