History

lua: add a helper for runtime script option changes

A script can use this to easily get runtime updates. (Even if script-opts is sort of clunky.)

wm4 committed 6 years ago

Commit 478a3211 parent db1e28f2 files · +71 −17Browse files

Unified · Split

2 files
  1. DOCS/man/lua.rst +9 −2
  2. player/lua/options.lua +62 −15
DOCS/man/lua.rst+9−2
@@ -566,14 +566,21 @@ command-line. All you have to do is to supply a table with default options to · 565 unmodified lines
566566 the read_options function. The function will overwrite the default values
567567 with values found in the config-file and the command-line (in that order).
568568
569−``options.read_options(table [, identifier])``
569+``options.read_options(table [, identifier [, on_update]])``
570570 A ``table`` with key-value pairs. The type of the default values is
571571 important for converting the values read from the config file or
572572 command-line back. Do not use ``nil`` as a default value!
573573
574574 The ``identifier`` is used to identify the config-file and the command-line
575575 options. These needs to unique to avoid collisions with other scripts.
576− Defaults to ``mp.get_script_name()``.
576+ Defaults to ``mp.get_script_name()`` if the parameter is ``nil`` or missing.
577+
578+ The ``on_update`` parameter enables run-time updates of all matching option
579+ values via the ``script-opts`` option/property. If any of the matching
580+ options changes, the values in the ``table`` (which was originally passed to
581+ the function) are changed, and ``on_update(list)`` is called. ``list`` is
582+ a table where each updated option has a ``list[option_name] = true`` entry.
583+ There is no initial ``on_update()`` call. This never re-reads the config file.
577584
578585
579586 Example implementation::
player/lua/options.lua+62−15
@@ -29,8 +29,17 @@ local function typeconv(desttypeval, val) · 28 unmodified lines
2929 return val
3030 end
3131
32+-- performs a deep-copy of the given option value
33+local function opt_copy(val)
34+ return val -- no tables currently
35+end
36+
37+-- compares the given option values for equality
38+local function opt_equal(val1, val2)
39+ return val1 == val2
40+end
3241
33−local function read_options(options, identifier)
42+local function read_options(options, identifier, on_update)
3443 if identifier == nil then
3544 identifier = mp.get_script_name()
3645 end
@@ -88,24 +97,62 @@ local function read_options(options, identifier) · 51 unmodified lines
8897 end
8998
9099 --parse command-line options
91− for key, val in pairs(mp.get_property_native("options/script-opts")) do
92− local prefix = identifier.."-"
93− if not (string.find(key, prefix, 1, true) == nil) then
94− key = string.sub(key, string.len(prefix)+1)
95−
96− -- match found values with defaults
97− if options[key] == nil then
98− msg.warn("script-opts: unknown key " .. key .. ", ignoring")
99− else
100− local convval = typeconv(options[key], val)
101− if convval == nil then
102− msg.error("script-opts: error converting value '" .. val ..
103− "' for key '" .. key .. "'")
100+ local prefix = identifier.."-"
101+
102+ local option_types = {}
103+ for key, value in pairs(options) do
104+ option_types[key] = opt_copy(value)
105+ end
106+
107+ local function parse_opts(full, options)
108+ local changelist = {}
109+ for key, val in pairs(full) do
110+ if not (string.find(key, prefix, 1, true) == nil) then
111+ key = string.sub(key, string.len(prefix)+1)
112+
113+ -- match found values with defaults
114+ if option_types[key] == nil then
115+ msg.warn("script-opts: unknown key " .. key .. ", ignoring")
104116 else
105− options[key] = convval
117+ local convval = typeconv(option_types[key], val)
118+ if convval == nil then
119+ msg.error("script-opts: error converting value '" .. val ..
120+ "' for key '" .. key .. "'")
121+ else
122+ if not opt_equal(options[key], convval) then
123+ changelist[key] = true
124+ options[key] = convval
125+ end
126+ end
106127 end
107128 end
108129 end
130+ return changelist
131+ end
132+
133+ --initial
134+ parse_opts(mp.get_property_native("options/script-opts"), options)
135+
136+ --runtime updates
137+ if on_update then
138+ -- Current option state, so that we can detect changes, even if the
139+ -- caller messes with the options table.
140+ local cur_opts = {}
141+
142+ for key, value in pairs(options) do
143+ cur_opts[key] = opt_copy(value)
144+ end
145+
146+ mp.observe_property("options/script-opts", "native", function(name, val)
147+ local changelist = parse_opts(val, cur_opts)
148+ for key, _ in pairs(changelist) do
149+ -- copy to user
150+ options[key] = opt_copy(cur_opts[key])
151+ end
152+ if #changelist then
153+ on_update(changelist)
154+ end
155+ end)
109156 end
110157
111158 end

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t