diff --git a/src/audio_provider_vs.cpp b/src/audio_provider_vs.cpp index b41b46773..49b3c7e06 100644 --- a/src/audio_provider_vs.cpp +++ b/src/audio_provider_vs.cpp @@ -61,7 +61,7 @@ VapoursynthAudioProvider::VapoursynthAudioProvider(agi::fs::path const& filename throw VapoursynthError("Error creating script API"); } vs.GetScriptAPI()->evalSetWorkingDir(script, 1); - if (OpenScriptOrVideo(vs.GetScriptAPI(), script, filename, OPT_GET("Provider/Audio/VapourSynth/Default Script")->GetString())) { + if (OpenScriptOrVideo(vs.GetAPI(), vs.GetScriptAPI(), script, filename, OPT_GET("Provider/Audio/VapourSynth/Default Script")->GetString())) { std::string msg = agi::format("Error executing VapourSynth script: %s", vs.GetScriptAPI()->getError(script)); vs.GetScriptAPI()->freeScript(script); throw VapoursynthError(msg); diff --git a/src/vapoursynth_common.cpp b/src/vapoursynth_common.cpp index 52614528c..83070111f 100644 --- a/src/vapoursynth_common.cpp +++ b/src/vapoursynth_common.cpp @@ -17,21 +17,43 @@ #ifdef WITH_VAPOURSYNTH #include "vapoursynth_common.h" +#include "vapoursynth_wrap.h" #include "options.h" #include +#include #include -int OpenScriptOrVideo(const VSSCRIPTAPI *api, VSScript *script, agi::fs::path const& filename, std::string default_script) { +void SetStringVar(const VSAPI *api, VSMap *map, std::string variable, std::string value) { + if (api->mapSetData(map, variable.c_str(), value.c_str(), -1, dtUtf8, 1)) + throw VapoursynthError("Failed to set VSMap entry"); +} + +int OpenScriptOrVideo(const VSAPI *api, const VSSCRIPTAPI *sapi, VSScript *script, agi::fs::path const& filename, std::string default_script) { int result; if (agi::fs::HasExtension(filename, "py") || agi::fs::HasExtension(filename, "vpy")) { - result = api->evaluateFile(script, filename.string().c_str()); + result = sapi->evaluateFile(script, filename.string().c_str()); } else { - std::string fname = filename.string(); - boost::replace_all(fname, "\\", "\\\\"); - boost::replace_all(fname, "'", "\\'"); - std::string vscript = "filename = '" + fname + "'\n" + default_script; - result = api->evaluateBuffer(script, vscript.c_str(), "aegisub"); + VSMap *map = api->createMap(); + if (map == nullptr) + throw VapoursynthError("Failed to create VSMap for script info"); + + SetStringVar(api, map, "filename", filename.string()); + for (std::string dir : { "data", "dictionary", "local", "script", "temp", "user", }) + // Don't include ?audio and ?video in here since these only hold the paths to the previous audio/video files. + SetStringVar(api, map, "__aegi_" + dir, config::path->Decode("?" + dir).string()); + + if (sapi->setVariables(script, map)) + throw VapoursynthError("Failed to set script info variables"); + + api->freeMap(map); + + std::string vscript; + vscript += "import sys\n"; + vscript += "sys.path.append(f'{__aegi_data}/automation/vapoursynth')\n"; + vscript += "sys.path.append(f'{__aegi_user}/automation/vapoursynth')\n"; + vscript += default_script; + result = sapi->evaluateBuffer(script, vscript.c_str(), "aegisub"); } return result; } diff --git a/src/vapoursynth_common.h b/src/vapoursynth_common.h index 06479e45e..2f03b4e7b 100644 --- a/src/vapoursynth_common.h +++ b/src/vapoursynth_common.h @@ -19,6 +19,6 @@ #include -int OpenScriptOrVideo(const VSSCRIPTAPI *api, VSScript *script, agi::fs::path const& filename, std::string default_script); +int OpenScriptOrVideo(const VSAPI *api, const VSSCRIPTAPI *sapi, VSScript *script, agi::fs::path const& filename, std::string default_script); #endif // WITH_VAPOURSYNTH diff --git a/src/video_provider_vs.cpp b/src/video_provider_vs.cpp index bde0f9a70..7b0d29449 100644 --- a/src/video_provider_vs.cpp +++ b/src/video_provider_vs.cpp @@ -116,7 +116,7 @@ VapoursynthVideoProvider::VapoursynthVideoProvider(agi::fs::path const& filename throw VapoursynthError("Error creating script API"); } vs.GetScriptAPI()->evalSetWorkingDir(script, 1); - if (OpenScriptOrVideo(vs.GetScriptAPI(), script, filename, OPT_GET("Provider/Video/VapourSynth/Default Script")->GetString())) { + if (OpenScriptOrVideo(vs.GetAPI(), vs.GetScriptAPI(), script, filename, OPT_GET("Provider/Video/VapourSynth/Default Script")->GetString())) { std::string msg = agi::format("Error executing VapourSynth script: %s", vs.GetScriptAPI()->getError(script)); vs.GetScriptAPI()->freeScript(script); throw VapoursynthError(msg);