f
This commit is contained in:
215
MPV/LUA/main.lua
215
MPV/LUA/main.lua
@@ -52,6 +52,7 @@ local _sleep_timer = nil
|
||||
local PIPELINE_REQ_PROP = 'user-data/medeia-pipeline-request'
|
||||
local PIPELINE_RESP_PROP = 'user-data/medeia-pipeline-response'
|
||||
local PIPELINE_READY_PROP = 'user-data/medeia-pipeline-ready'
|
||||
local CURRENT_WEB_URL_PROP = 'user-data/medeia-current-web-url'
|
||||
|
||||
-- Dedicated Lua log: write directly to logs.db database for unified logging
|
||||
-- Fallback to stderr if database unavailable
|
||||
@@ -1885,6 +1886,21 @@ function FileState.new()
|
||||
}, FileState)
|
||||
end
|
||||
|
||||
function FileState:set_url(url)
|
||||
local normalized = trim(tostring(url or ''))
|
||||
if normalized == '' then
|
||||
self.url = nil
|
||||
self.formats = nil
|
||||
self.formats_table = nil
|
||||
return
|
||||
end
|
||||
if self.url ~= normalized then
|
||||
self.url = normalized
|
||||
self.formats = nil
|
||||
self.formats_table = nil
|
||||
end
|
||||
end
|
||||
|
||||
function FileState:has_formats()
|
||||
return type(self.formats) == 'table'
|
||||
and type(self.formats.rows) == 'table'
|
||||
@@ -1892,7 +1908,7 @@ function FileState:has_formats()
|
||||
end
|
||||
|
||||
function FileState:set_formats(url, tbl)
|
||||
self.url = url
|
||||
self:set_url(url)
|
||||
self.formats = tbl
|
||||
self.formats_table = tbl
|
||||
end
|
||||
@@ -1903,6 +1919,7 @@ M.file = M.file or FileState.new()
|
||||
local _formats_cache = {}
|
||||
local _formats_inflight = {}
|
||||
local _formats_waiters = {}
|
||||
local _get_cached_formats_table
|
||||
|
||||
local _ipc_async_busy = false
|
||||
local _ipc_async_queue = {}
|
||||
@@ -1983,6 +2000,70 @@ local function _is_ytdlp_url(u)
|
||||
return false
|
||||
end
|
||||
|
||||
local function _set_current_web_url(url)
|
||||
local normalized = trim(tostring(url or ''))
|
||||
if normalized ~= '' and _is_http_url(normalized) then
|
||||
pcall(mp.set_property, CURRENT_WEB_URL_PROP, normalized)
|
||||
if type(M.file) == 'table' and M.file.set_url then
|
||||
M.file:set_url(normalized)
|
||||
end
|
||||
return normalized
|
||||
end
|
||||
pcall(mp.set_property, CURRENT_WEB_URL_PROP, '')
|
||||
if type(M.file) == 'table' and M.file.set_url then
|
||||
M.file:set_url(nil)
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
local function _get_current_web_url()
|
||||
local current = trim(tostring(mp.get_property(CURRENT_WEB_URL_PROP) or ''))
|
||||
if current ~= '' and _is_http_url(current) then
|
||||
return current
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
local function _current_url_for_web_actions()
|
||||
local current = _get_current_web_url()
|
||||
if current and current ~= '' then
|
||||
return current
|
||||
end
|
||||
local target = _current_target()
|
||||
if not target or target == '' then
|
||||
return nil
|
||||
end
|
||||
return tostring(target)
|
||||
end
|
||||
|
||||
local function _sync_current_web_url_from_playback()
|
||||
local target = _current_target()
|
||||
local target_str = trim(tostring(target or ''))
|
||||
if target_str ~= '' and _extract_store_hash(target_str) then
|
||||
_set_current_web_url(nil)
|
||||
return
|
||||
end
|
||||
if target_str ~= '' and _is_http_url(target_str) and _is_ytdlp_url(target_str) then
|
||||
_set_current_web_url(target_str)
|
||||
return
|
||||
end
|
||||
|
||||
local current = _get_current_web_url()
|
||||
if current and current ~= '' then
|
||||
local raw = mp.get_property_native('ytdl-raw-info')
|
||||
if type(raw) == 'table' then
|
||||
if type(M.file) == 'table' and M.file.set_url then
|
||||
M.file:set_url(current)
|
||||
end
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
if target_str == '' or not _is_http_url(target_str) then
|
||||
_set_current_web_url(nil)
|
||||
end
|
||||
end
|
||||
|
||||
local function _cache_formats_for_url(url, tbl)
|
||||
if type(url) ~= 'string' or url == '' then
|
||||
return
|
||||
@@ -2000,7 +2081,7 @@ local function _cache_formats_for_url(url, tbl)
|
||||
end
|
||||
end
|
||||
|
||||
local function _get_cached_formats_table(url)
|
||||
_get_cached_formats_table = function(url)
|
||||
if type(url) ~= 'string' or url == '' then
|
||||
return nil
|
||||
end
|
||||
@@ -2111,8 +2192,13 @@ local function _prefetch_formats_for_url(url)
|
||||
if url == '' or not _is_http_url(url) then
|
||||
return
|
||||
end
|
||||
_set_current_web_url(url)
|
||||
if type(M.file) == 'table' then
|
||||
M.file.url = url
|
||||
if M.file.set_url then
|
||||
M.file:set_url(url)
|
||||
else
|
||||
M.file.url = url
|
||||
end
|
||||
if M.file.fetch_formats then
|
||||
M.file:fetch_formats(nil)
|
||||
end
|
||||
@@ -2307,8 +2393,11 @@ local function _apply_ytdl_format_and_reload(url, fmt)
|
||||
local pos = mp.get_property_number('time-pos')
|
||||
local paused = mp.get_property_native('pause') and true or false
|
||||
|
||||
_lua_log('change-format: setting options/ytdl-format=' .. tostring(fmt))
|
||||
_lua_log('change-format: setting ytdl format=' .. tostring(fmt))
|
||||
_set_current_web_url(url)
|
||||
pcall(mp.set_property, 'options/ytdl-format', tostring(fmt))
|
||||
pcall(mp.set_property, 'file-local-options/ytdl-format', tostring(fmt))
|
||||
pcall(mp.set_property, 'ytdl-format', tostring(fmt))
|
||||
|
||||
if pos and pos > 0 then
|
||||
mp.commandv('loadfile', url, 'replace', 'start=' .. tostring(pos))
|
||||
@@ -2322,7 +2411,7 @@ local function _apply_ytdl_format_and_reload(url, fmt)
|
||||
end
|
||||
|
||||
local function _start_download_flow_for_current()
|
||||
local target = _current_target()
|
||||
local target = _current_url_for_web_actions() or _current_target()
|
||||
if not target or target == '' then
|
||||
mp.osd_message('No current item', 2)
|
||||
return
|
||||
@@ -2371,7 +2460,7 @@ mp.register_script_message('medios-download-current', function()
|
||||
end)
|
||||
|
||||
mp.register_script_message('medios-change-format-current', function()
|
||||
local target = _current_target()
|
||||
local target = _current_url_for_web_actions() or _current_target()
|
||||
if not target or target == '' then
|
||||
mp.osd_message('No current item', 2)
|
||||
return
|
||||
@@ -2384,15 +2473,22 @@ mp.register_script_message('medios-change-format-current', function()
|
||||
end
|
||||
|
||||
local url = tostring(target)
|
||||
_set_current_web_url(url)
|
||||
|
||||
-- Ensure file state is tracking the current URL.
|
||||
if type(M.file) == 'table' then
|
||||
M.file.url = url
|
||||
if M.file.set_url then
|
||||
M.file:set_url(url)
|
||||
else
|
||||
M.file.url = url
|
||||
end
|
||||
end
|
||||
|
||||
-- If formats were already prefetched for this URL, open instantly.
|
||||
local cached_tbl = nil
|
||||
if type(M.file) == 'table' and type(M.file.formats) == 'table' then
|
||||
if type(M.file) == 'table'
|
||||
and M.file.url == url
|
||||
and type(M.file.formats) == 'table' then
|
||||
cached_tbl = M.file.formats
|
||||
else
|
||||
cached_tbl = _get_cached_formats_table(url)
|
||||
@@ -2506,7 +2602,8 @@ end)
|
||||
|
||||
-- Prefetch formats for yt-dlp-supported URLs on load so Change Format is instant.
|
||||
mp.register_event('file-loaded', function()
|
||||
local target = _current_target()
|
||||
_sync_current_web_url_from_playback()
|
||||
local target = _current_url_for_web_actions() or _current_target()
|
||||
if not target or target == '' then
|
||||
return
|
||||
end
|
||||
@@ -3188,6 +3285,7 @@ mp.register_script_message('medios-load-url-event', function(json)
|
||||
mp.osd_message('Loading URL...', 1)
|
||||
_log_all('INFO', 'Load URL started: ' .. url)
|
||||
_lua_log('[LOAD-URL] Starting to load: ' .. url)
|
||||
_set_current_web_url(url)
|
||||
|
||||
local function close_menu()
|
||||
_lua_log('[LOAD-URL] Closing menu')
|
||||
@@ -3199,16 +3297,21 @@ mp.register_script_message('medios-load-url-event', function(json)
|
||||
end
|
||||
end
|
||||
|
||||
-- Close the URL prompt immediately once the user submits. Playback may still
|
||||
-- take time to resolve, but the modal should not stay stuck on screen.
|
||||
close_menu()
|
||||
|
||||
-- First, always try direct loadfile. This is the fastest path.
|
||||
local can_direct = _url_can_direct_load(url)
|
||||
local prefer_direct = can_direct or _is_ytdlp_url(url)
|
||||
_lua_log('[LOAD-URL] Checking if URL can be loaded directly: ' .. tostring(can_direct))
|
||||
_lua_log('[LOAD-URL] Prefer direct load: ' .. tostring(prefer_direct))
|
||||
|
||||
local direct_ok, direct_loaded = _try_direct_loadfile(url, false)
|
||||
local direct_ok, direct_loaded = _try_direct_loadfile(url, prefer_direct)
|
||||
if direct_ok and direct_loaded then
|
||||
_lua_log('[LOAD-URL] Direct loadfile command sent successfully (forced)')
|
||||
_log_all('INFO', 'Load URL succeeded via direct load')
|
||||
mp.osd_message('URL loaded', 2)
|
||||
close_menu()
|
||||
return
|
||||
end
|
||||
if direct_ok then
|
||||
@@ -3223,6 +3326,47 @@ mp.register_script_message('medios-load-url-event', function(json)
|
||||
local helper_ready = ensure_pipeline_helper_running()
|
||||
_lua_log('[LOAD-URL] Pipeline helper ready: ' .. tostring(helper_ready))
|
||||
|
||||
local function start_pipeline_load()
|
||||
-- Use pipeline to download/prepare the URL
|
||||
local pipeline_cmd = '.mpv -url ' .. quote_pipeline_arg(url) .. ' -play'
|
||||
_lua_log('[LOAD-URL] Sending to pipeline: ' .. pipeline_cmd)
|
||||
_lua_log('[LOAD-URL] Pipeline helper ready: ' .. tostring(_is_pipeline_helper_ready()))
|
||||
|
||||
local timeout_timer = nil
|
||||
timeout_timer = mp.add_timeout(5, function()
|
||||
if timeout_timer then
|
||||
mp.osd_message('Still loading... (helper may be resolving URL)', 2)
|
||||
_log_all('WARN', 'Load URL still processing after 5 seconds')
|
||||
_lua_log('[LOAD-URL] Timeout message shown (helper still processing)')
|
||||
end
|
||||
end)
|
||||
|
||||
M.run_pipeline(pipeline_cmd, nil, function(resp, err)
|
||||
if timeout_timer then
|
||||
timeout_timer:kill()
|
||||
timeout_timer = nil
|
||||
end
|
||||
|
||||
_lua_log('[LOAD-URL] Pipeline callback received: resp=' .. tostring(resp) .. ', err=' .. tostring(err))
|
||||
if err then
|
||||
_lua_log('[LOAD-URL] Pipeline error: ' .. tostring(err))
|
||||
_log_all('ERROR', 'Load URL pipeline failed: ' .. tostring(err))
|
||||
mp.osd_message('Load URL failed: ' .. tostring(err), 3)
|
||||
return
|
||||
end
|
||||
_lua_log('[LOAD-URL] URL loaded successfully')
|
||||
_log_all('INFO', 'Load URL succeeded')
|
||||
mp.osd_message('URL loaded', 2)
|
||||
|
||||
if _is_ytdlp_url(url) then
|
||||
_lua_log('[LOAD-URL] URL is yt-dlp compatible, prefetching formats in background')
|
||||
mp.add_timeout(0.5, function()
|
||||
_prefetch_formats_for_url(url)
|
||||
end)
|
||||
end
|
||||
end)
|
||||
end
|
||||
|
||||
if not helper_ready then
|
||||
_lua_log('[LOAD-URL] Pipeline helper not available, attempting to start...')
|
||||
_log_all('WARN', 'Pipeline helper not running, attempting auto-start')
|
||||
@@ -3231,62 +3375,19 @@ mp.register_script_message('medios-load-url-event', function(json)
|
||||
-- Attempt to start the helper asynchronously
|
||||
attempt_start_pipeline_helper_async(function(success)
|
||||
if success then
|
||||
_lua_log('[LOAD-URL] Helper started successfully, retry Load URL from menu')
|
||||
_lua_log('[LOAD-URL] Helper started successfully, continuing load')
|
||||
_log_all('INFO', 'Pipeline helper started successfully')
|
||||
mp.osd_message('Helper started! Try Load URL again', 2)
|
||||
start_pipeline_load()
|
||||
else
|
||||
_lua_log('[LOAD-URL] Failed to start helper')
|
||||
_log_all('ERROR', 'Failed to start pipeline helper')
|
||||
mp.osd_message('Could not start pipeline helper', 3)
|
||||
end
|
||||
close_menu()
|
||||
end)
|
||||
return
|
||||
end
|
||||
|
||||
-- Use pipeline to download/prepare the URL
|
||||
local pipeline_cmd = '.mpv -url ' .. quote_pipeline_arg(url) .. ' -play'
|
||||
_lua_log('[LOAD-URL] Sending to pipeline: ' .. pipeline_cmd)
|
||||
_lua_log('[LOAD-URL] Pipeline helper ready: ' .. tostring(_is_pipeline_helper_ready()))
|
||||
|
||||
-- Add a timeout message after a delay to give user feedback
|
||||
local timeout_timer = nil
|
||||
timeout_timer = mp.add_timeout(5, function()
|
||||
if timeout_timer then
|
||||
mp.osd_message('Still loading... (helper may be resolving URL)', 2)
|
||||
_log_all('WARN', 'Load URL still processing after 5 seconds')
|
||||
_lua_log('[LOAD-URL] Timeout message shown (helper still processing)')
|
||||
end
|
||||
end)
|
||||
|
||||
M.run_pipeline(pipeline_cmd, nil, function(resp, err)
|
||||
if timeout_timer then
|
||||
timeout_timer:kill()
|
||||
timeout_timer = nil
|
||||
end
|
||||
|
||||
_lua_log('[LOAD-URL] Pipeline callback received: resp=' .. tostring(resp) .. ', err=' .. tostring(err))
|
||||
if err then
|
||||
_lua_log('[LOAD-URL] Pipeline error: ' .. tostring(err))
|
||||
_log_all('ERROR', 'Load URL pipeline failed: ' .. tostring(err))
|
||||
mp.osd_message('Load URL failed: ' .. tostring(err), 3)
|
||||
close_menu()
|
||||
return
|
||||
end
|
||||
_lua_log('[LOAD-URL] URL loaded successfully')
|
||||
_log_all('INFO', 'Load URL succeeded')
|
||||
mp.osd_message('URL loaded', 2)
|
||||
|
||||
-- Prefetch formats for yt-dlp URLs so "Change Format" menu is instant
|
||||
if _is_ytdlp_url(url) then
|
||||
_lua_log('[LOAD-URL] URL is yt-dlp compatible, prefetching formats in background')
|
||||
mp.add_timeout(0.5, function()
|
||||
_prefetch_formats_for_url(url)
|
||||
end)
|
||||
end
|
||||
|
||||
close_menu()
|
||||
end)
|
||||
start_pipeline_load()
|
||||
end)
|
||||
|
||||
-- Menu integration with UOSC
|
||||
|
||||
Reference in New Issue
Block a user