Skip to content

Instantly share code, notes, and snippets.

@nickgammon
Created April 13, 2025 03:03
Show Gist options
  • Select an option

  • Save nickgammon/96702410f6dd44d6517e19498e477c76 to your computer and use it in GitHub Desktop.

Select an option

Save nickgammon/96702410f6dd44d6517e19498e477c76 to your computer and use it in GitHub Desktop.
MUSHclient plugin for showing game text in boxes on the screen with optional cooldowns

Show text in boxes with a cooldown for MUSHclient

This is a standalone plugin that lets you display pure text in small boxes, with an optional cooldown timeout.

Installation

Save the files Cooldown_Text.xml and Cooldown_Text.lua in your MUSHclient plugins directory (usually (install location)/worlds/plugins )

Making a text box

You can have a text box with or without a timeout. Each text box has a name (it can be anything, eg. "fireball") and then the text you want in the box (that you see). If you use the same name twice it will replace the previous box, if you use a different name then you will get extra boxes (one per name).

You add boxes to the screen with CallPlugin like this:

CallPlugin ("2f103c42b3356ee1bcac384b" , "MakeWindow" , "fireball", "Fireball Spell", 30 )

What that does is call MakeWindow inside the plugin, creates a box name "fireball" and puts the text "Fireball Spell" into the box. It has a timeout of 30 seconds in this example. It will automatically count down every second.

What you see is:

Fireball Spell (wait) 30s

Each second the time on the right counts down. If it is longer than a minute then the time is shown in minutes (eg. 25m) or hours, days, or weeks even.

When the 30 seconds are up the window changes to:

Fireball Spell (ready)

Another example:

CallPlugin ("2f103c42b3356ee1bcac384b" , "MakeWindow" , "rez", "Resurrection", 30 * 60 )

That would show "Resurrection" counting down for 30 minutes (30 times 60 seconds).

You can have a box without a timeout:

CallPlugin ("2f103c42b3356ee1bcac384b" , "MakeWindow" , "quest", "You have active quests")

Removing a text box

You can remove a box:

CallPlugin ("2f103c42b3356ee1bcac384b" , "RemoveWindow" , "quest")

How to activate the windows based on game events

It's up to you to activate these windows by detecting game events with triggers or aliases.

("2f103c42b3356ee1bcac384b" is the plugin ID of the plugin, see Cooldown_Text.xml).

require "commas" -- for convert_time
MARGIN = 10 -- pixels
font_id = "fn"
FONT_NAME = "Sans" -- input font name
active_windows = { } -- our windows
-- redraw all active window, one under the other
function ShowWindows ()
top = 5 -- starting Y position
-- for each window
for name, details in pairs (active_windows) do
contents = details.contents
-- for windows with a cooldown indicate if it is ready or you have to wait
if details.cooldown then
if details.cooldown <= 0 then
contents = contents .. " (ready)"
else
contents = contents .. " (wait) " .. convert_time (details.cooldown)
end -- if ready or waiting
end -- if it has a cooldown
win = GetPluginID () .. "_" .. name
-- make window so I can grab the font info
WindowCreate (win, 0, 0, 1, 1, miniwin.pos_top_right, miniwin.create_absolute_location, 0)
WindowFont (win, font_id, FONT_NAME, 12, false, false, false, false, 0, 0) -- normal
font_height = WindowFontInfo (win, font_id, 1) -- height
-- calculate window size
window_height = font_height + MARGIN
window_width = WindowTextWidth (win, font_id, contents) + MARGIN
-- work out left of window (output window width - size of window)
left = GetInfo (281) - window_width - 5 -- position on right, slightly in from edge
-- make window correct size and location
WindowCreate (win, left, top, window_width, window_height,
miniwin.pos_top_right, miniwin.create_absolute_location, ColourNameToRGB ("white"))
-- blank the window
WindowRectOp (win, miniwin.rect_draw_edge, 0, 0, 0, 0,
miniwin.rect_edge_raised, miniwin.rect_edge_at_all + miniwin.rect_option_softer_buttons)
-- add the text
WindowText (win, font_id, contents, MARGIN / 2, MARGIN / 2, 0, 0, ColourNameToRGB ("black"))
-- show the window
WindowShow (win, true)
-- next window is further down
top = top + window_height + 5
end -- for each window
end -- ShowWindows
-- add a notification window
function MakeWindow (name, contents, cooldown)
active_windows [name] = { contents = contents, cooldown = cooldown }
ShowWindows()
end -- MakeWindow
-- call this to remove a notification window
function RemoveWindow (name)
active_windows [name] = nil
win = GetPluginID () .. "_" .. name
WindowDelete (win)
ShowWindows()
end -- RemoveWindow
-- called every second on a timer
function handle_cooldowns ()
for name, details in pairs (active_windows) do
if details.cooldown then
details.cooldown = details.cooldown - 1 -- one less second
if details.cooldown < 1 then
details.cooldown = 0
end -- if time is up
end -- if has a cooldown
end -- for each window
ShowWindows()
end -- function handle_cooldowns
-- remove the windows when we disconnect
function OnPluginDisconnect()
for name, details in pairs (active_windows) do
RemoveWindow (name)
end -- for each window
end -- OnPluginDisconnect
<?xml version="1.0" encoding="iso-8859-1"?>
<!DOCTYPE muclient>
<muclient>
<plugin
name="Cooldown_Text"
author="Nick Gammon"
id="2f103c42b3356ee1bcac384b"
language="Lua"
purpose="Shows cooldowns in a miniwindow"
save_state="y"
date_written="2025-04-08 11:50:44"
requires="5.06"
version="1.0"
>
</plugin>
<!-- Timers -->
<timers>
<timer
script="handle_cooldowns"
enabled="y" second="1.00"
active_closed="y" >
</timer>
</timers>
<!-- Script -->
<script>
dofile (GetPluginInfo (GetPluginID (), 20) .. "Cooldown_Text.lua")
</script>
</muclient>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment