feat: configuration page with default lisp forms.
This commit is contained in:
parent
396384fd71
commit
4537a3aee3
6 changed files with 42 additions and 42 deletions
|
@ -2,8 +2,19 @@ using MediaBrowser.Model.Plugins;
|
||||||
|
|
||||||
namespace Jellyfin.Plugin.SmartPlaylist {
|
namespace Jellyfin.Plugin.SmartPlaylist {
|
||||||
public class PluginConfiguration : BasePluginConfiguration {
|
public class PluginConfiguration : BasePluginConfiguration {
|
||||||
public PluginConfiguration(
|
public PluginConfiguration() {
|
||||||
) {
|
InitialProgram = """
|
||||||
}
|
(begin
|
||||||
|
(define lower (lambda (s) (invoke s "ToLower" nil)))
|
||||||
|
(define is-genre (lambda (g g-list) (any (lambda (x) (invoke (lower x) "Contains" (list (lower g)))) g-list)))
|
||||||
|
(define is-genre-exact (lambda (g g-list) (find g g-list)))
|
||||||
|
(define genre-list (lambda nil (let (_g (getitems item "Genres")) (if (null _g) nil (car _g)))))
|
||||||
|
(define is-favorite (lambda nil (invoke item "IsFavoriteOrLiked" (list user)))))
|
||||||
|
|
||||||
|
|
||||||
|
(define is-favourite is-favorite)
|
||||||
|
""";
|
||||||
|
}
|
||||||
|
public string InitialProgram { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -98,6 +98,11 @@ namespace Jellyfin.Plugin.SmartPlaylist.ScheduledTasks {
|
||||||
Expression expression = new Parser(StringTokenStream.generate(smartPlaylist.Program)).parse();
|
Expression expression = new Parser(StringTokenStream.generate(smartPlaylist.Program)).parse();
|
||||||
Executor executor = new Executor(new DefaultEnvironment());
|
Executor executor = new Executor(new DefaultEnvironment());
|
||||||
executor.environment.Set("user", new Lisp_Object(user));
|
executor.environment.Set("user", new Lisp_Object(user));
|
||||||
|
if (Plugin.Instance is not null) {
|
||||||
|
executor.eval(Plugin.Instance.Configuration.InitialProgram);
|
||||||
|
} else {
|
||||||
|
throw new ApplicationException("Plugin Instance is not yet initialized");
|
||||||
|
}
|
||||||
foreach (var i in items) {
|
foreach (var i in items) {
|
||||||
executor.environment.Set("item", new Lisp_Object(i));
|
executor.environment.Set("item", new Lisp_Object(i));
|
||||||
var r = executor.eval(expression);
|
var r = executor.eval(expression);
|
||||||
|
|
|
@ -41,7 +41,7 @@ namespace Jellyfin.Plugin.SmartPlaylist {
|
||||||
|
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class SmartPlaylistDto : ISerializable {
|
public class SmartPlaylistDto : ISerializable {
|
||||||
private static string DEFAULT_PROGRAM = "(begin (invoke item 'IsFavoriteOrLiked' (user)))";
|
private static string DEFAULT_PROGRAM = "(begin (invoke item \"IsFavoriteOrLiked\" (list user)))";
|
||||||
public SmartPlaylistId Id { get; set; }
|
public SmartPlaylistId Id { get; set; }
|
||||||
public SmartPlaylistLinkDto[] Playlists { get; set; }
|
public SmartPlaylistLinkDto[] Playlists { get; set; }
|
||||||
public string Name { get; set; }
|
public string Name { get; set; }
|
||||||
|
|
|
@ -20,9 +20,12 @@ namespace Jellyfin.Plugin.SmartPlaylist {
|
||||||
{
|
{
|
||||||
throw new ApplicationException("");
|
throw new ApplicationException("");
|
||||||
}
|
}
|
||||||
if (dto.Id == Path.GetFileNameWithoutExtension(filename)) {
|
if (dto.Id != Path.GetFileNameWithoutExtension(filename)) {
|
||||||
dto.Id = Path.GetFileNameWithoutExtension(filename);
|
dto.Id = Path.GetFileNameWithoutExtension(filename);
|
||||||
}
|
}
|
||||||
|
if (dto.Name != Path.GetFileNameWithoutExtension(filename)) {
|
||||||
|
dto.Name = Path.GetFileNameWithoutExtension(filename);
|
||||||
|
}
|
||||||
if (dto.Filename != filename) {
|
if (dto.Filename != filename) {
|
||||||
dto.Filename = filename;
|
dto.Filename = filename;
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,32 +5,14 @@
|
||||||
<title>Template</title>
|
<title>Template</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<div id="TemplateConfigPage" data-role="page" class="page type-interior pluginConfigurationPage" data-require="emby-input,emby-button,emby-select,emby-checkbox">
|
<div id="SmartPlaylistConfigPage" data-role="page" class="page type-interior pluginConfigurationPage" data-require="emby-input,emby-button,emby-select,emby-checkbox">
|
||||||
<div data-role="content">
|
<div data-role="content">
|
||||||
<div class="content-primary">
|
<div class="content-primary">
|
||||||
<form id="TemplateConfigForm">
|
<form id="SmartPlaylistConfigForm">
|
||||||
<div class="selectContainer">
|
|
||||||
<label class="selectLabel" for="Options">Several Options</label>
|
|
||||||
<select is="emby-select" id="Options" name="Options" class="emby-select-withcolor emby-select">
|
|
||||||
<option id="optOneOption" value="OneOption">One Option</option>
|
|
||||||
<option id="optAnotherOption" value="AnotherOption">Another Option</option>
|
|
||||||
</select>
|
|
||||||
</div>
|
|
||||||
<div class="inputContainer">
|
<div class="inputContainer">
|
||||||
<label class="inputLabel inputLabelUnfocused" for="AnInteger">An Integer</label>
|
<label class="inputLabel inputLabelUnfocused" for="InitialProgram">Initial Program</label>
|
||||||
<input id="AnInteger" name="AnInteger" type="number" is="emby-input" min="0" />
|
<div class="fieldDescription">A program which can set up the environment</div>
|
||||||
<div class="fieldDescription">A Description</div>
|
<input id="InitialProgram" name="InitialProgram" type="text" is="emby-input" />
|
||||||
</div>
|
|
||||||
<div class="checkboxContainer checkboxContainer-withDescription">
|
|
||||||
<label class="emby-checkbox-label">
|
|
||||||
<input id="TrueFalseSetting" name="TrueFalseCheckBox" type="checkbox" is="emby-checkbox" />
|
|
||||||
<span>A Checkbox</span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
<div class="inputContainer">
|
|
||||||
<label class="inputLabel inputLabelUnfocused" for="AString">A String</label>
|
|
||||||
<input id="AString" name="AString" type="text" is="emby-input" />
|
|
||||||
<div class="fieldDescription">Another Description</div>
|
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<button is="emby-button" type="submit" class="raised button-submit block emby-button">
|
<button is="emby-button" type="submit" class="raised button-submit block emby-button">
|
||||||
|
@ -41,31 +23,25 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
var TemplateConfig = {
|
var SmartPlaylistConfig = {
|
||||||
pluginUniqueId: 'dd2326e3-4d3e-4bfc-80e6-28502c1131df'
|
pluginUniqueId: 'dd2326e3-4d3e-4bfc-80e6-28502c1131df'
|
||||||
};
|
};
|
||||||
|
|
||||||
document.querySelector('#TemplateConfigPage')
|
document.querySelector('#SmartPlaylistConfigPage')
|
||||||
.addEventListener('pageshow', function() {
|
.addEventListener('pageshow', function() {
|
||||||
Dashboard.showLoadingMsg();
|
Dashboard.showLoadingMsg();
|
||||||
ApiClient.getPluginConfiguration(TemplateConfig.pluginUniqueId).then(function (config) {
|
ApiClient.getPluginConfiguration(SmartPlaylistConfig.pluginUniqueId).then(function (config) {
|
||||||
document.querySelector('#Options').value = config.Options;
|
document.querySelector('#InitialProgram').value = config.InitialProgram;
|
||||||
document.querySelector('#AnInteger').value = config.AnInteger;
|
|
||||||
document.querySelector('#TrueFalseSetting').checked = config.TrueFalseSetting;
|
|
||||||
document.querySelector('#AString').value = config.AString;
|
|
||||||
Dashboard.hideLoadingMsg();
|
Dashboard.hideLoadingMsg();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
document.querySelector('#TemplateConfigForm')
|
document.querySelector('#SmartPlaylistConfigForm')
|
||||||
.addEventListener('submit', function(e) {
|
.addEventListener('submit', function(e) {
|
||||||
Dashboard.showLoadingMsg();
|
Dashboard.showLoadingMsg();
|
||||||
ApiClient.getPluginConfiguration(TemplateConfig.pluginUniqueId).then(function (config) {
|
ApiClient.getPluginConfiguration(SmartPlaylistConfig.pluginUniqueId).then(function (config) {
|
||||||
config.Options = document.querySelector('#Options').value;
|
config.InitialProgram = document.querySelector('#InitialProgram').value;
|
||||||
config.AnInteger = document.querySelector('#AnInteger').value;
|
ApiClient.updatePluginConfiguration(SmartPlaylistConfig.pluginUniqueId, config).then(function (result) {
|
||||||
config.TrueFalseSetting = document.querySelector('#TrueFalseSetting').checked;
|
|
||||||
config.AString = document.querySelector('#AString').value;
|
|
||||||
ApiClient.updatePluginConfiguration(TemplateConfig.pluginUniqueId, config).then(function (result) {
|
|
||||||
Dashboard.processPluginConfigurationUpdateResult(result);
|
Dashboard.processPluginConfigurationUpdateResult(result);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net8.0</TargetFramework>
|
<TargetFramework>net8.0</TargetFramework>
|
||||||
<RootNamespace>jellyfin_smart_playlist</RootNamespace>
|
<RootNamespace>Jellyfin.Plugin.SmartPlaylist</RootNamespace>
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
<Version>0.1.1.0</Version>
|
<Version>0.1.1.0</Version>
|
||||||
|
@ -14,4 +14,9 @@
|
||||||
<PackageReference Include="YamlDotNet" Version="16.1.3" />
|
<PackageReference Include="YamlDotNet" Version="16.1.3" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<None Remove="configPage.html"/>
|
||||||
|
<EmbeddedResource Include="configPage.html"/>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
|
|
Loading…
Reference in a new issue