Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update position.lua #1386

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions changelog.txt
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ Template for new versions:
## Fixes
- `advtools`: fix dfhack-added conversation options not appearing in the ask whereabouts conversation tree
- `gui/rename`: fix error when changing the language of a unit's name
- `position`: support for adv mode look cursor

## Misc Improvements
- `assign-preferences`: new ``--show`` option to display the preferences of the selected unit
Expand Down
2 changes: 1 addition & 1 deletion docs/position.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ position
This tool reports the current date, clock time, month, season, and historical
era. It also reports the keyboard cursor position (or just the z-level if no
active cursor), window size, and mouse location on the screen. If a site is
loaded, it prints the world coordinates of the site. If not, it prints the world
loaded, it prints the world coordinates of the site. It also prints the world
coordinates of the adventurer (if applicable).

Can also be used to copy the current keyboard cursor position for later use.
Expand Down
172 changes: 111 additions & 61 deletions position.lua
Original file line number Diff line number Diff line change
@@ -1,20 +1,36 @@
-- Report cursor and mouse position, along with other info.
--@ module = true

local cursor = df.global.cursor
local args = {...}
if #args > 0 then --Copy keyboard cursor to clipboard
if #args > 1 then
qerror('Too many arguments!')
elseif args[1] ~= '-c' and args[1] ~= '--copy' then
qerror('Invalid argument "'..args[1]..'"!')
elseif cursor.x < 0 then
qerror('No keyboard cursor!')
local argparse = require('argparse')

local function parse_args(args)
local opts = {}
local positionals = argparse.processArgsGetopt(args,
{
{'c', 'copy', handler=function() opts.copy = true end},
})

if #positionals > 0 then
qerror('Too many positionals!')
end

dfhack.internal.setClipboardTextCp437(('%d,%d,%d'):format(cursor.x, cursor.y, cursor.z))
return
return opts
end

function get_active_cursor() --Return active fort/adv cursor or nil
if dfhack.world.isAdventureMode() then
local look = df.global.game.main_interface.adventure.look
if look.open and look.cursor:isValid() then
return look.cursor --Note: This is a df.coord
end
elseif df.global.cursor.x >= 0 then
return df.global.cursor
end
return nil --Not active
end
Comment on lines +20 to 30
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This can be replaced with guidm.getCursorPos() after DFHack/dfhack#5230 merges.


local months = {
local months =
{
'Granite, in early Spring.',
'Slate, in mid Spring.',
'Felsite, in late Spring.',
Expand All @@ -29,68 +45,102 @@ local months = {
'Obsidian, in late Winter.',
}

--Fortress mode counts 1200 ticks per day and 403200 per year
--Adventurer mode counts 86400 ticks to a day and 29030400 ticks per year
--Twelve months per year, 28 days to every month, 336 days per year
function print_time_info()
--Fortress mode counts 1200 ticks per day and 403200 per year
--Adventurer mode counts 86400 ticks to a day and 29030400 ticks per year
--Twelve months per year, 28 days to every month, 336 days per year
local julian_day = df.global.cur_year_tick // 1200 + 1
local month = julian_day // 28 + 1 --days and months are 1-indexed
local day = julian_day % 28

local julian_day = df.global.cur_year_tick // 1200 + 1
local month = julian_day // 28 + 1 --days and months are 1-indexed
local day = julian_day % 28
local time_of_day = df.global.cur_year_tick_advmode // 336
local second = time_of_day % 60
local minute = time_of_day // 60 % 60
local hour = time_of_day // 3600 % 24

local time_of_day = df.global.cur_year_tick_advmode // 336
local second = time_of_day % 60
local minute = time_of_day // 60 % 60
local hour = time_of_day // 3600 % 24
print('Time:')
print((' The time is %02d:%02d:%02d'):format(hour, minute, second))
print((' The date is %03d-%02d-%02d'):format(df.global.cur_year, month, day))
print(' It is the month of '..months[month])

print('Time:')
print((' The time is %02d:%02d:%02d'):format(hour, minute, second))
print((' The date is %03d-%02d-%02d'):format(df.global.cur_year, month, day))
print(' It is the month of '..months[month])
local eras = df.global.world.history.eras
if #eras > 0 then
print(' It is the '..eras[#eras-1].title.name..'.')
end
end

local eras = df.global.world.history.eras
if #eras > 0 then
print(' It is the '..eras[#eras-1].title.name..'.')
function get_adv_region_pos() --Regional coords
if not dfhack.world.getAdventurer() then --Army exists when unit doesn't
local army = df.army.find(df.global.adventure.player_army_id)
if army then
return army.pos.x//48, army.pos.y//48
end
end
local wd = df.global.world.world_data
return wd.midmap_data.adv_region_x, wd.midmap_data.adv_region_y
end

print('Place:')
print(' The z-level is z='..df.global.window_z)
local function print_world_info()
local wd = df.global.world.world_data
local site = dfhack.world.getCurrentSite()
if site then
print((' The current site is at x=%d, y=%d on the %dx%d world map.'):
format(site.pos.x, site.pos.y, wd.world_width, wd.world_height))
end

if cursor.x < 0 then
print(' The keyboard cursor is inactive.')
else
print(' The keyboard cursor is at x='..cursor.x..', y='..cursor.y)
if dfhack.world.isAdventureMode() then
local x, y = get_adv_region_pos()
print((' The adventurer is at x=%d, y=%d on the %dx%d world map.'):
format(x, y, wd.world_width, wd.world_height))
end
end

local x, y = dfhack.screen.getWindowSize()
print(' The window is '..x..' tiles wide and '..y..' tiles high.')
function print_place_info(cursor)
print('Place:')
print(' The z-level is z='..df.global.window_z)

x, y = dfhack.screen.getMousePos()
if x then
print(' The mouse is at x='..x..', y='..y..' within the window.')
local pos = dfhack.gui.getMousePos()
if pos then
print(' The mouse is over map tile x='..pos.x..', y='..pos.y)
if cursor then
local x, y = cursor.x, cursor.y
print((' The keyboard cursor is at x=%d, y=%d (%d+%d, %d+%d)'):
format(x, y, x//16*16, x%16, y//16*16, y%16))
else
print(' The keyboard cursor is inactive.')
end
else
print(' The mouse is not in the DF window.')
end

local wd = df.global.world.world_data
local site = dfhack.world.getCurrentSite()
if site then
print((' The current site is at x=%d, y=%d on the %dx%d world map.'):
format(site.pos.x, site.pos.y, wd.world_width, wd.world_height))
elseif dfhack.world.isAdventureMode() then
x, y = -1, -1
for _,army in ipairs(df.global.world.armies.all) do
if army.flags.player then
x, y = army.pos.x // 48, army.pos.y // 48
break
local x, y = dfhack.screen.getWindowSize()
print(' The window is '..x..' tiles wide and '..y..' tiles high.')

x, y = dfhack.screen.getMousePos()
if x then
print(' The mouse is at x='..x..', y='..y..' within the window.')
local pos = dfhack.gui.getMousePos()
if pos then
print(' The mouse is over map tile x='..pos.x..', y='..pos.y)
end
else
print(' The mouse is not in the DF window.')
end
if x < 0 then
x, y = wd.midmap_data.adv_region_x, wd.midmap_data.adv_region_y

print_world_info()
end

if dfhack_flags.module then
return
end

function main(opts)
local cursor = get_active_cursor()

if opts.copy then --Copy keyboard cursor to clipboard
if not cursor then
qerror('No keyboard cursor!')
end
dfhack.internal.setClipboardTextCp437(('%d,%d,%d'):format(cursor.x, cursor.y, cursor.z))
return --Don't print anything
end
print((' The adventurer is at x=%d, y=%d on the %dx%d world map.'):
format(x, y, wd.world_width, wd.world_height))

print_time_info()
print_place_info(cursor)
end

main(parse_args({...}))