summaryrefslogtreecommitdiffstats
path: root/player/lua/osc.lua
diff options
context:
space:
mode:
Diffstat (limited to 'player/lua/osc.lua')
-rw-r--r--player/lua/osc.lua276
1 files changed, 178 insertions, 98 deletions
diff --git a/player/lua/osc.lua b/player/lua/osc.lua
index ff7d9120ed..643f32faaf 100644
--- a/player/lua/osc.lua
+++ b/player/lua/osc.lua
@@ -12,8 +12,8 @@ local utils = require 'mp.utils'
local user_opts = {
showwindowed = true, -- show OSC when windowed?
showfullscreen = true, -- show OSC when fullscreen?
- scalewindowed = 1.5, -- scaling of the controller when windowed
- scalefullscreen = 1.5, -- scaling of the controller when fullscreen
+ scalewindowed = 1, -- scaling of the controller when windowed
+ scalefullscreen = 1, -- scaling of the controller when fullscreen
scaleforcedwindow = 2, -- scaling when rendered on a forced window
vidscale = true, -- scale the controller with the video?
valign = 0.8, -- vertical alignment, -1 (top) to 1 (bottom)
@@ -25,14 +25,15 @@ local user_opts = {
-- mouse movement. enforced non-negative for the
-- user, but internally negative is "always-on".
fadeduration = 200, -- duration of fade out in ms, 0 = no fade
- deadzonesize = 1, -- size of deadzone
+ deadzonesize = 0.5, -- size of deadzone
minmousemove = 0, -- minimum amount of pixels the mouse has to
-- move between ticks to make the OSC show up
iamaprogrammer = false, -- use native mpv values and disable OSC
-- internal track list management (and some
-- functions that depend on it)
layout = "bottombar",
- seekbarstyle = "bar", -- slider (diamond marker) or bar (fill)
+ seekbarstyle = "bar", -- slider (diamond marker), knob (circle
+ -- marker with guide), or bar (fill)
tooltipborder = 1, -- border of tooltip in bottom/topbar
timetotal = false, -- display total time instead of remaining time?
timems = false, -- display timecodes with milliseconds?
@@ -59,15 +60,20 @@ local osc_param = { -- calculated by osc_init()
local osc_styles = {
bigButtons = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs50\\fnmpv-osd-symbols}",
smallButtonsL = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs19\\fnmpv-osd-symbols}",
- smallButtonsLlabel = "{\\fs20\\fn" .. mp.get_property("options/osd-font") .. "}",
+ smallButtonsLlabel = "{\\fscx105\\fscy105\\fn" .. mp.get_property("options/osd-font") .. "}",
smallButtonsR = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs30\\fnmpv-osd-symbols}",
topButtons = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs12\\fnmpv-osd-symbols}",
elementDown = "{\\1c&H999999}",
timecodes = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs20}",
- vidtitle = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs12}",
- timePos = "{\\blur0\\bord".. user_opts.tooltipborder .."\\1c&HFFFFFF\\3c&H000000\\1a&H00\\3a&H88\\fs20}",
+ vidtitle = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs12\\q2}",
box = "{\\rDefault\\blur0\\bord1\\1c&H000000\\3c&HFFFFFF}",
+
+ topButtonsBar = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs18\\fnmpv-osd-symbols}",
+ smallButtonsBar = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs28\\fnmpv-osd-symbols}",
+ timecodesBar = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs27}",
+ timePosBar = "{\\blur0\\bord".. user_opts.tooltipborder .."\\1c&HFFFFFF\\3c&H000000\\fs30}",
+ vidtitleBar = "{\\blur0\\bord0\\1c&HFFFFFF\\3c&HFFFFFF\\fs18\\q2}",
}
-- internal states, do not touch
@@ -395,7 +401,8 @@ function prepare_elements()
local foV = slider_lo.border + slider_lo.gap
-- calculate positions of min and max points
- if (slider_lo.stype == "slider") then
+ if (slider_lo.stype == "slider") or
+ (slider_lo.stype == "knob") then
element.slider.min.ele_pos = elem_geo.h / 2
element.slider.max.ele_pos = elem_geo.w - (elem_geo.h / 2)
@@ -557,9 +564,11 @@ function render_elements(master_ass)
local foV = slider_lo.border + slider_lo.gap
local foH = 0
- if (slider_lo.stype == "slider") then
+ if (slider_lo.stype == "slider") or
+ (slider_lo.stype == "knob") then
foH = elem_geo.h / 2
elseif (slider_lo.stype == "bar") then
+ foV = foV + 1
foH = slider_lo.border + slider_lo.gap
end
@@ -575,6 +584,11 @@ function render_elements(master_ass)
elem_ass:line_to(xp+(innerH/2), (innerH/2)+foV)
elem_ass:line_to(xp, (innerH)+foV)
elem_ass:line_to(xp-(innerH/2), (innerH/2)+foV)
+ elseif (slider_lo.stype == "knob") then
+ elem_ass:rect_cw(xp, (9*innerH/20)+foV, elem_geo.w - foH, (11*innerH/20)+foV)
+ elem_ass:rect_cw(foH, (3*innerH/8)+foV, xp, (5*innerH/8)+foV)
+ elem_ass:round_rect_cw(xp - innerH/2, foV, xp + innerH/2,
+ foV + innerH, innerH/2.0)
end
end
@@ -619,6 +633,18 @@ function render_elements(master_ass)
elem_ass:pos(tx, ty)
elem_ass:an(an)
elem_ass:append(slider_lo.tooltip_style)
+
+ --alpha
+ local ar = slider_lo.alpha
+ if not (state.animation == nil) then
+ ar = {}
+ for ai, av in pairs(slider_lo.alpha) do
+ ar[ai] = mult_alpha(av, state.animation)
+ end
+ end
+ elem_ass:append(string.format("{\\1a&H%X&\\2a&H%X&\\3a&H%X&\\4a&H%X&}",
+ ar[1], ar[2], ar[3], ar[4]))
+
elem_ass:append(tooltiplabel)
end
@@ -651,47 +677,44 @@ end
-- Message display
--
+-- pos is 1 based
function limited_list(prop, pos)
- local fs = tonumber(mp.get_property('options/osd-font-size'))
- local max_items = math.ceil(720 / fs)
-
local proplist = mp.get_property_native(prop, {})
local count = #proplist
- if (count == 0) then
+ if count == 0 then
return count, proplist
end
- local min, max = 0, count
- local temp = {}
- if (count > max_items - 1) then
- local extra = math.ceil(max_items / 2) - 1
- min = pos - extra
- max = pos + extra
- if (pos < extra) then
- max = max + math.abs(min)
- min = 0
- end
+
+ local fs = tonumber(mp.get_property('options/osd-font-size'))
+ local max = math.ceil(720 / fs)
+ if max % 2 == 0 then
+ max = max - 1
end
+ local delta = math.ceil(max / 2) - 1
+ local begi = math.max(math.min(pos - delta, count - max + 1), 1)
+ local endi = math.min(begi + max - 1, count)
- for i=min+1, max do
+ local reslist = {}
+ for i=begi, endi do
local item = proplist[i]
- item.current = (i-1 == pos) and true or nil
- table.insert(temp, item)
+ item.current = (i == pos) and true or nil
+ table.insert(reslist, item)
end
- return count, temp
+ return count, reslist
end
function get_playlist()
- local pos = mp.get_property_number('playlist-pos')
+ local pos = mp.get_property_number('playlist-pos', 0) + 1
local count, limlist = limited_list('playlist', pos)
- if (count == 0) then
- return "Empty playlist."
+ if count == 0 then
+ return 'Empty playlist.'
end
- local message = string.format('Playlist: (%d/%d):\n', pos + 1, count)
+ local message = string.format('Playlist [%d/%d]:\n', pos, count)
for i, v in ipairs(limlist) do
local title = v.title
local _, filename = utils.split_path(v.filename)
- if (title == nil) then
+ if title == nil then
title = filename
end
message = string.format('%s %s %s\n', message,
@@ -701,18 +724,18 @@ function get_playlist()
end
function get_chapterlist()
- local pos = mp.get_property_number('chapter')
+ local pos = mp.get_property_number('chapter', 0) + 1
local count, limlist = limited_list('chapter-list', pos)
- if (count == 0) then
- return "No chapters."
+ if count == 0 then
+ return 'No chapters.'
end
- local message = string.format('Chapters: (%d/%d):\n', pos + 1, count)
+ local message = string.format('Chapters [%d/%d]:\n', pos, count)
for i, v in ipairs(limlist) do
local time = mp.format_time(v.time)
local title = v.title
- if (title == nil) then
- title = string.format('Chapter %02d', i + 1)
+ if title == nil then
+ title = string.format('Chapter %02d', i)
end
message = string.format('%s[%s] %s %s\n', message, time,
(v.current and '●' or '○'), title)
@@ -829,6 +852,7 @@ function add_layout(name)
adjust_tooltip = true,
tooltip_style = "",
tooltip_an = 2,
+ alpha = {[1] = 0, [2] = 255, [3] = 88, [4] = 255},
}
elseif (elements[name].type == "box") then
elements[name].layout.box = {radius = 0}
@@ -991,6 +1015,9 @@ layouts["box"] = function ()
lo.style = osc_styles.timecodes
lo.slider.tooltip_style = osc_styles.vidtitle
lo.slider.stype = user_opts["seekbarstyle"]
+ if lo.slider.stype == "knob" then
+ lo.slider.border = 0
+ end
--
-- Timecodes + Cache
@@ -1077,7 +1104,9 @@ layouts["slimbox"] = function ()
lo.style = osc_styles.box
lo.alpha[1] = user_opts.boxalpha
lo.alpha[3] = 0
- lo.box.radius = osc_geo.r
+ if not (user_opts["seekbarstyle"] == "bar") then
+ lo.box.radius = osc_geo.r
+ end
lo = add_layout("seekbar")
@@ -1123,16 +1152,28 @@ end
layouts["bottombar"] = function()
local osc_geo = {
x = -2,
- y = osc_param.playresy - 36 - user_opts.barmargin,
+ y = osc_param.playresy - 54 - user_opts.barmargin,
an = 7,
w = osc_param.playresx + 4,
- h = 38,
+ h = 56,
}
- local padX = 6
- local padY = 2
- local line1 = osc_geo.y + 6 + padY
- local line2 = osc_geo.y + 24 + padY
+ local padX = 9
+ local padY = 3
+ local buttonW = 27
+ local tcW = (state.tc_ms) and 150 or 105
+ local tsW = 90
+ local minW = (buttonW + padX)*3 + (tcW + padX)*4 + (tsW + padX)*2
+
+ if ((osc_param.display_aspect > 0) and (osc_param.playresx < minW)) then
+ osc_param.playresy = minW / osc_param.display_aspect
+ osc_param.playresx = osc_param.playresy * osc_param.display_aspect
+ osc_geo.y = osc_param.playresy - 54 - user_opts.barmargin
+ osc_geo.w = osc_param.playresx + 4
+ end
+
+ local line1 = osc_geo.y + 9 + padY
+ local line2 = osc_geo.y + 36 + padY
osc_param.areas = {}
@@ -1159,77 +1200,82 @@ layouts["bottombar"] = function()
-- Playlist prev/next
geo = { x = osc_geo.x + padX, y = line1,
- an = 4, w = 12, h = 12 - padY }
+ an = 4, w = 18, h = 18 - padY }
lo = add_layout("pl_prev")
lo.geometry = geo
- lo.style = osc_styles.topButtons
+ lo.style = osc_styles.topButtonsBar
geo = { x = geo.x + geo.w + padX, y = geo.y, an = geo.an, w = geo.w, h = geo.h }
lo = add_layout("pl_next")
lo.geometry = geo
- lo.style = osc_styles.topButtons
+ lo.style = osc_styles.topButtonsBar
- -- Title
- geo = { x = geo.x + geo.w + padX, y = geo.y, an = geo.an,
- w = 1000, h = geo.h }
- lo = add_layout("title")
- lo.geometry = geo
- lo.style = osc_styles.vidtitle
+ local t_l = geo.x + geo.w + padX
-- Cache
geo = { x = osc_geo.x + osc_geo.w - padX, y = geo.y,
- an = 6, w = 100, h = geo.h }
+ an = 6, w = 150, h = geo.h }
lo = add_layout("cache")
lo.geometry = geo
- lo.style = osc_styles.vidtitle
+ lo.style = osc_styles.vidtitleBar
+
+ local t_r = geo.x - geo.w - padX*2
+
+ -- Title
+ geo = { x = t_l, y = geo.y, an = 4,
+ w = t_r - t_l, h = geo.h }
+ lo = add_layout("title")
+ lo.geometry = geo
+ lo.style = osc_styles.vidtitleBar
+ lo.button.maxchars = math.floor(geo.w/7)
-- Playback control buttons
geo = { x = osc_geo.x + padX, y = line2, an = 4,
- w = 18, h = 24 - padY*2}
+ w = buttonW, h = 36 - padY*2}
lo = add_layout("playpause")
lo.geometry = geo
- lo.style = osc_styles.smallButtonsL
+ lo.style = osc_styles.smallButtonsBar
geo = { x = geo.x + geo.w + padX, y = geo.y, an = geo.an, w = geo.w, h = geo.h }
lo = add_layout("ch_prev")
lo.geometry = geo
- lo.style = osc_styles.smallButtonsL
+ lo.style = osc_styles.smallButtonsBar
geo = { x = geo.x + geo.w + padX, y = geo.y, an = geo.an, w = geo.w, h = geo.h }
lo = add_layout("ch_next")
lo.geometry = geo
- lo.style = osc_styles.smallButtonsL
-
+ lo.style = osc_styles.smallButtonsBar
-- Left timecode
- geo = { x = geo.x + geo.w + padX + 100, y = geo.y, an = 6, w = 100, h = geo.h }
+ geo = { x = geo.x + geo.w + padX + tcW, y = geo.y, an = 6,
+ w = tcW, h = geo.h }
lo = add_layout("tc_left")
lo.geometry = geo
- lo.style = osc_styles.timecodes
+ lo.style = osc_styles.timecodesBar
local sb_l = geo.x + padX
-- Track selection buttons
geo = { x = osc_geo.x + osc_geo.w - padX, y = geo.y, an = geo.an,
- w = 60, h = geo.h }
+ w = tsW, h = geo.h }
lo = add_layout("cy_sub")
lo.geometry = geo
- lo.style = osc_styles.smallButtonsL
+ lo.style = osc_styles.smallButtonsBar
geo = { x = geo.x - geo.w - padX, y = geo.y, an = geo.an, w = geo.w, h = geo.h }
lo = add_layout("cy_audio")
lo.geometry = geo
- lo.style = osc_styles.smallButtonsL
+ lo.style = osc_styles.smallButtonsBar
-- Right timecode
- geo = { x = geo.x - geo.w - padX - 100, y = geo.y, an = 4,
- w = 100, h = geo.h }
+ geo = { x = geo.x - geo.w - padX - tcW, y = geo.y, an = 4,
+ w = tcW, h = geo.h }
lo = add_layout("tc_right")
lo.geometry = geo
- lo.style = osc_styles.timecodes
+ lo.style = osc_styles.timecodesBar
local sb_r = geo.x - padX
@@ -1242,7 +1288,7 @@ layouts["bottombar"] = function()
lo.geometry = geo
lo.layer = 15
- lo.style = osc_styles.timecodes
+ lo.style = osc_styles.timecodesBar
lo.alpha[1] =
math.min(255, user_opts.boxalpha + (255 - user_opts.boxalpha)*0.8)
@@ -1250,7 +1296,7 @@ layouts["bottombar"] = function()
lo.geometry = geo
lo.style = osc_styles.timecodes
lo.slider.border = 0
- lo.slider.tooltip_style = osc_styles.timePos
+ lo.slider.tooltip_style = osc_styles.timePosBar
lo.slider.tooltip_an = 5
lo.slider.stype = user_opts["seekbarstyle"]
end
@@ -1258,16 +1304,28 @@ end
layouts["topbar"] = function()
local osc_geo = {
x = -2,
- y = 36 + user_opts.barmargin,
+ y = 54 + user_opts.barmargin,
an = 1,
w = osc_param.playresx + 4,
- h = 38,
+ h = 56,
}
- local padX = 6
- local padY = 2
- local line1 = osc_geo.y - 24 - padY
- local line2 = osc_geo.y - 6 - padY
+ local padX = 9
+ local padY = 3
+ local buttonW = 27
+ local tcW = (state.tc_ms) and 150 or 105
+ local tsW = 90
+ local minW = (buttonW + padX)*3 + (tcW + padX)*4 + (tsW + padX)*2
+
+ if ((osc_param.display_aspect > 0) and (osc_param.playresx < minW)) then
+ osc_param.playresy = minW / osc_param.display_aspect
+ osc_param.playresx = osc_param.playresy * osc_param.display_aspect
+ osc_geo.y = 54 + user_opts.barmargin
+ osc_geo.w = osc_param.playresx + 4
+ end
+
+ local line1 = osc_geo.y - 36 - padY
+ local line2 = osc_geo.y - 9 - padY
osc_param.areas = {}
@@ -1295,7 +1353,7 @@ layouts["topbar"] = function()
-- Playback control buttons
geo = { x = osc_geo.x + padX, y = line1, an = 4,
- w = 18, h = 24 - padY*2 }
+ w = buttonW, h = 36 - padY*2 }
lo = add_layout("playpause")
lo.geometry = geo
lo.style = osc_styles.smallButtonsL
@@ -1312,8 +1370,8 @@ layouts["topbar"] = function()
-- Left timecode
- geo = { x = geo.x + geo.w + padX + 100, y = geo.y, an = 6,
- w = 100, h = geo.h }
+ geo = { x = geo.x + geo.w + padX + tcW, y = geo.y, an = 6,
+ w = tcW, h = geo.h }
lo = add_layout("tc_left")
lo.geometry = geo
lo.style = osc_styles.timecodes
@@ -1323,7 +1381,7 @@ layouts["topbar"] = function()
-- Track selection buttons
geo = { x = osc_geo.x + osc_geo.w - padX, y = geo.y, an = geo.an,
- w = 60, h = geo.h }
+ w = tsW, h = geo.h }
lo = add_layout("cy_sub")
lo.geometry = geo
lo.style = osc_styles.smallButtonsL
@@ -1335,8 +1393,8 @@ layouts["topbar"] = function()
-- Right timecode
- geo = { x = geo.x - geo.w - padX - 100, y = geo.y, an = 4,
- w = 100, h = geo.h }
+ geo = { x = geo.x - geo.w - padX - tcW, y = geo.y, an = 4,
+ w = tcW, h = geo.h }
lo = add_layout("tc_right")
lo.geometry = geo
lo.style = osc_styles.timecodes
@@ -1359,13 +1417,13 @@ layouts["topbar"] = function()
lo.geometry = geo
lo.style = osc_styles.timecodes
lo.slider.border = 0
- lo.slider.tooltip_style = osc_styles.timePos
+ lo.slider.tooltip_style = osc_styles.timePosBar
lo.slider.stype = user_opts["seekbarstyle"]
lo.slider.tooltip_an = 5
-- Playlist prev/next
- geo = { x = osc_geo.x + padX, y = line2, an = 4, w = 12, h = 12 - padY }
+ geo = { x = osc_geo.x + padX, y = line2, an = 4, w = 18, h = 18 - padY }
lo = add_layout("pl_prev")
lo.geometry = geo
lo.style = osc_styles.topButtons
@@ -1375,19 +1433,24 @@ layouts["topbar"] = function()
lo.geometry = geo
lo.style = osc_styles.topButtons
- -- Title
- geo = { x = geo.x + geo.w + padX, y = geo.y, an = geo.an,
- w = 1000, h = geo.h }
- lo = add_layout("title")
- lo.geometry = geo
- lo.style = osc_styles.vidtitle
+ local t_l = geo.x + geo.w + padX
-- Cache
- geo = { x = osc_geo.x + osc_geo.w - padX, y = geo.y, an = 6,
- w = 100, h = geo.h }
+ geo = { x = osc_geo.x + osc_geo.w - padX, y = geo.y,
+ an = 6, w = 150, h = geo.h }
lo = add_layout("cache")
lo.geometry = geo
lo.style = osc_styles.vidtitle
+
+ local t_r = geo.x - geo.w - padX*2
+
+ -- Title
+ geo = { x = t_l, y = geo.y, an = 4,
+ w = t_r - t_l, h = geo.h }
+ lo = add_layout("title")
+ lo.geometry = geo
+ lo.style = osc_styles.vidtitle
+ lo.button.maxchars = math.floor(geo.w/7)
end
-- Validate string type user options
@@ -1398,7 +1461,8 @@ function validate_user_opts()
end
if user_opts.seekbarstyle ~= "slider" and
- user_opts.seekbarstyle ~= "bar" then
+ user_opts.seekbarstyle ~= "bar" and
+ user_opts.seekbarstyle ~= "knob" then
msg.warn("Invalid setting \"" .. user_opts.seekbarstyle
.. "\" for seekbarstyle")
user_opts.seekbarstyle = "slider"
@@ -1683,8 +1747,10 @@ function osc_init()
return (mp.get_property_osd("playback-time"))
end
end
- ne.eventresponder["mouse_btn0_up"] =
- function () state.tc_ms = not state.tc_ms end
+ ne.eventresponder["mouse_btn0_up"] = function ()
+ state.tc_ms = not state.tc_ms
+ request_init()
+ end
-- tc_right (total/remaining time)
ne = new_element("tc_right", "button")
@@ -2004,7 +2070,8 @@ function process_event(source, what)
if n == 0 then
--click on background (does not work)
- elseif n > 0 and not (elements[n].eventresponder[source .. "_" .. what] == nil) then
+ elseif n > 0 and not (n > #elements) and
+ not (elements[n].eventresponder[source .. "_" .. what] == nil) then
if mouse_hit(elements[n]) then
elements[n].eventresponder[source .. "_" .. what](elements[n])
@@ -2036,7 +2103,7 @@ function process_event(source, what)
local n = state.active_element
- if not (elements[n].eventresponder == nil) then
+ if not (n > #elements) and not (elements[n].eventresponder == nil) then
if not (elements[n].eventresponder[source] == nil) then
elements[n].eventresponder[source](elements[n])
end
@@ -2127,6 +2194,19 @@ mp.register_event("tracks-changed", request_init)
mp.observe_property("playlist", nil, request_init)
mp.register_script_message("osc-message", show_message)
+mp.register_script_message("osc-chapterlist", function(dur)
+ show_message(get_chapterlist(), dur)
+end)
+mp.register_script_message("osc-playlist", function(dur)
+ show_message(get_playlist(), dur)
+end)
+mp.register_script_message("osc-tracklist", function(dur)
+ local msg = {}
+ for k,v in pairs(nicetypes) do
+ table.insert(msg, get_tracklist(k))
+ end
+ show_message(table.concat(msg, '\n\n'), dur)
+end)
mp.observe_property("fullscreen", "bool",
function(name, val)