Skip to content

Commit

Permalink
feat(filterpreset): Implement loading/saving filter presets
Browse files Browse the repository at this point in the history
commit 3f6636a
Author: Alkorith <[email protected]>
Date:   Mon Sep 11 11:25:05 2023 -0500

    feat(filterpreset): Implement loading/saving filter presets

commit 9872554
Author: Alkorith <[email protected]>
Date:   Mon Sep 11 11:30:53 2023 -0500

    chore(filterpresets): Add lunajson dependency
  • Loading branch information
Alkorith committed Sep 12, 2023
1 parent 15eabb1 commit 1a5e97b
Show file tree
Hide file tree
Showing 12 changed files with 1,075 additions and 2 deletions.
63 changes: 63 additions & 0 deletions Themes/Rebirth/BGAnimations/playerInfoFrame/searchfilter.lua
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
local filterpreset = require('filterpreset')

local ratios = {
Width = 782 / 1920,
Height = 971 / 1080,
Expand Down Expand Up @@ -55,6 +57,9 @@ local translations = {
Results = THEME:GetString("SearchFilter", "Results"),
Reset = THEME:GetString("SearchFilter", "Reset"),
Apply = THEME:GetString("SearchFilter", "Apply"),
SaveToDefaultPreset = THEME:GetString("FilterPreset", "SaveToDefaultPreset"),
ExportPresetToFile = THEME:GetString("FilterPreset", "ExportPresetToFile"),
SaveFilterPresetPrompt = THEME:GetString("FilterPreset", "SaveFilterPresetPrompt"),
}

local visibleframeX = SCREEN_WIDTH - actuals.Width
Expand Down Expand Up @@ -1170,6 +1175,60 @@ local function lowerSection()
end
}

t[#t+1] = filterMiscLine(9) .. {
Name = "SaveLine",
InitCommand = function(self)
self:settext(translations["SaveToDefaultPreset"])
end,
MouseOverCommand = onHover,
MouseOutCommand = onUnHover,
MouseDownCommand = function(self)
filterpreset.save_preset("default", PLAYER_1)
end
}


t[#t+1] = filterMiscLine(10) .. {
Name = "ExportLine",
InitCommand = function(self)
self:settext(translations["ExportPresetToFile"])
end,
MouseOverCommand = onHover,
MouseOutCommand = onUnHover,
MouseDownCommand = function(self)
local redir = SCREENMAN:get_input_redirected(PLAYER_1)
local function off()
if redir then
SCREENMAN:set_input_redirected(PLAYER_1, false)
end
end
local function on()
if redir then
SCREENMAN:set_input_redirected(PLAYER_1, true)
end
end
off()

askForInputStringWithFunction(
translations["SaveFilterPresetPrompt"],
32,
false,
function(answer)
-- success if the answer isnt blank
if answer:gsub("^%s*(.-)%s*$", "%1") ~= "" then
filterpreset.save_preset(answer)
else
on()
end
end,
function() return true, "" end,
function()
on()
end
)
end
}

return t
end

Expand Down Expand Up @@ -1218,4 +1277,8 @@ t[#t+1] = Def.Quad {
t[#t+1] = upperSection()
t[#t+1] = lowerSection()

-- Load default preset if it exists. We should only be setting the values once
-- at startup. Subsequent calls should not occur.
filterpreset.load_preset("default", false, PLAYER_1)

return t
7 changes: 6 additions & 1 deletion Themes/Rebirth/Languages/en.ini
Original file line number Diff line number Diff line change
Expand Up @@ -627,6 +627,11 @@ Results=Matches
Reset=Reset
Apply=Apply
[FilterPreset]
ExportPresetToFile=Export
SaveFilterPresetPrompt=Enter filter preset file name:
SaveToDefaultPreset=Save
[Settings]
NothingBound=none
CurrentlyBinding=Currently Binding
Expand Down Expand Up @@ -1021,4 +1026,4 @@ Bm_Double7=14K+2
Maniax_Single=4K
Maniax_Double=8K
Pnm_Five=5K
Pnm_Nine=9K
Pnm_Nine=9K
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
local filterpreset = require('filterpreset')

local numbershers = {"1", "2", "3", "4", "5", "6", "7", "8", "9", "0"}
local frameX = 10
local frameY = 45
Expand Down Expand Up @@ -99,6 +101,9 @@ local translated_info = {
MaxRate = THEME:GetString("TabFilter", "MaxRate"),
Title = THEME:GetString("TabFilter", "Title"),
MinRate = THEME:GetString("TabFilter", "MinRate"),
ExportFilterToFile = THEME:GetString("FilterPreset", "ExportFilterToFile"),
SaveFilterPresetPrompt = THEME:GetString("FilterPreset", "SaveFilterPresetPrompt"),
SaveToDefaultFilterPreset = THEME:GetString("FilterPreset", "SaveToDefaultFilterPreset"),
}

local f = Def.ActorFrame {
Expand Down Expand Up @@ -433,6 +438,81 @@ local f = Def.ActorFrame {
ResetFilterMessageCommand = function(self)
self:queuecommand("Set")
end
},
--[[
-- FIXME: Hot Reloading does not work (yet). You would need to leave the
-- song select menu, then go back in for the filter to apply.
UIElements.TextToolTip(1, 1, "Common Large") ..{
InitCommand = function(self)
self:xy(10, 175 + spacingY * -2)
self:zoom(textzoom)
self:halign(0)
self:diffuse(getMainColor("positive"))
self:settext(translated_info["LoadFilterPreset"])
end,
MouseOverCommand = function(self)
self:diffusealpha(hoverAlpha)
end,
MouseOutCommand = function(self)
self:diffusealpha(1)
end,
MouseDownCommand = function(self, params)
if params.event == "DeviceButton_left mouse button" and active then
easyInputStringWithParams(
translated_info["LoadFilterPresetPrompt"],
32,
false,
filterpreset.load_preset,
true
)
end
end
},
--]]
UIElements.TextToolTip(1, 1, "Common Large") ..{
InitCommand = function(self)
self:xy(frameX + frameWidth / 2 + 100, 175 + spacingY * 7)
self:zoom(textzoom)
self:halign(0)
self:settext(translated_info["SaveToDefaultFilterPreset"])
self:diffuse(getMainColor("positive"))
end,
MouseOverCommand = function(self)
self:diffusealpha(hoverAlpha)
end,
MouseOutCommand = function(self)
self:diffusealpha(1)
end,
MouseDownCommand = function(self, params)
if params.event == "DeviceButton_left mouse button" and active then
filterpreset.save_preset("default", PLAYER_1)
end
end
},
UIElements.TextToolTip(1, 1, "Common Large") ..{
InitCommand = function(self)
self:xy(frameX + frameWidth / 2 + 100, 175 + spacingY * 8)
self:zoom(textzoom)
self:halign(0)
self:diffuse(getMainColor("positive"))
self:settext("Export")
end,
MouseOverCommand = function(self)
self:diffusealpha(hoverAlpha)
end,
MouseOutCommand = function(self)
self:diffusealpha(1)
end,
MouseDownCommand = function(self, params)
if params.event == "DeviceButton_left mouse button" and active then
easyInputStringWithFunction(
THEME:GetString("FilterPreset", "SaveFilterPresetPrompt"),
32,
false,
filterpreset.save_preset
)
end
end
}
}

Expand Down Expand Up @@ -648,9 +728,14 @@ f[#f + 1] = UIElements.TextButton(1, 1, "Common Large") .. {
end
end,
}
]]
--]]

for i = 1, (#ms.SkillSets + 2) do
f[#f + 1] = CreateFilterInputBox(i)
end

-- Load default preset if it exists. We should only be setting the values once
-- at startup. Subsequent calls should not occur.
filterpreset.load_preset("default", false, PLAYER_1)

return f
7 changes: 7 additions & 0 deletions Themes/Til Death/Languages/en.ini
Original file line number Diff line number Diff line change
Expand Up @@ -572,6 +572,13 @@ Apply=Apply
AND=ALL
OR=ANY

[FilterPreset]
ExportFilterToFile=Export
LoadFilterPreset=Load
LoadFilterPresetPrompt=Enter filter preset file name:
SaveFilterPresetPrompt=Enter filter preset file name:
SaveToDefaultFilterPreset=Save

[TabGoals]
PriorityLong=Priority
PriorityShort=P
Expand Down
7 changes: 7 additions & 0 deletions Themes/_fallback/lib/lua/5.1/filterpreset.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
local load_preset = require("filterpreset.load_preset")
local save_preset = require("filterpreset.save_preset")

return {
load_preset = load_preset,
save_preset = save_preset
}
80 changes: 80 additions & 0 deletions Themes/_fallback/lib/lua/5.1/filterpreset/load_preset.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
local json = require('lunajson')

local first_time_call_guard = true

-- Use default skillset names
local json_filter_categories = DeepCopy(ms.SkillSets)
table.insert(json_filter_categories, "Length")
table.insert(json_filter_categories, "ClearPercent")

local RateKey = "Rate"
local ExclusiveFilterKey = "ExclusiveFilter"
local HighestSkillsetOnlyKey = "HighestSkillsetOnly"
local HighestDifficultyOnlyKey = "HighestDifficultyOnly"

local function load_preset(filename, explicit_call, pn)
explicit_call = explicit_call or false

if not (explicit_call or first_time_call_guard) then return end
if first_time_call_guard then first_time_call_guard = false end

pn = pn or PLAYER_1
filename = filename or "default.json"

local full_path = (
PROFILEMAN:GetProfileDir(pn_to_profile_slot(pn))
.. '/filter_presets/'
.. filename
.. '.json'
)

local file_output = File.Read(full_path)
if not file_output then return end


local data = json.decode(file_output)

for i = 1, #json_filter_categories do
if data[json_filter_categories[i]] then
local setting = data[json_filter_categories[i]]

if setting.min then
FILTERMAN:SetSSFilter(setting.min, i, 0)
end

if setting.max then
FILTERMAN:SetSSFilter(setting.max, i, 1)
end
end
end

if data[RateKey] then
local setting = data[RateKey]

if setting.min then
FILTERMAN:SetMinFilterRate(setting.min)
end

if setting.max then
FILTERMAN:SetMaxFilterRate(setting.max)
end
end

if data[ExclusiveFilterKey] then
FILTERMAN:SetFilterMode(data[ExclusiveFilterKey])
end

if data[HighestSkillsetOnlyKey] then
FILTERMAN:SetHighestSkillsetsOnly(data[HighestSkillsetOnlyKey])
end

if data[HighestDifficultyOnlyKey] then
FILTERMAN:HighestDifficultyOnlyKey(data[HighestDifficultyOnlyKey])
end

if explicit_call then
ms.ok(string.format("Loaded filter preset: %s", full_path))
end
end

return load_preset
44 changes: 44 additions & 0 deletions Themes/_fallback/lib/lua/5.1/filterpreset/save_preset.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
local json = require('lunajson')

-- Use default skillset names
local json_filter_categories = DeepCopy(ms.SkillSets)
table.insert(json_filter_categories, "Length")
table.insert(json_filter_categories, "ClearPercent")

local RateKey = "Rate"
local ExclusiveFilterKey = "ExclusiveFilter"
local HighestSkillsetOnlyKey = "HighestSkillsetOnly"
local HighestDifficultyOnlyKey = "HighestDifficultyOnly"

local function save_preset(filename, pn)
filename = filename or "default"
pn = pn or PLAYER_1

local filter_preset = {
Rate = {
min = math.round(FILTERMAN:GetMinFilterRate(), 1),
max = math.round(FILTERMAN:GetMaxFilterRate(), 1)
},
ExclusiveFilter = FILTERMAN:GetFilterMode(),
HighestSkillsetOnly = FILTERMAN:GetHighestSkillsetsOnly(),
HighestDifficultyOnly = FILTERMAN:GetHighestDifficultyOnly()
}

for i = 1, #json_filter_categories do
filter_preset[json_filter_categories[i]] = {
min = FILTERMAN:GetSSFilter(i, 0),
max = FILTERMAN:GetSSFilter(i, 1)
}
end

local full_path = (
PROFILEMAN:GetProfileDir(pn_to_profile_slot(pn))
.. '/filter_presets/'
.. filename
.. '.json'
)
File.Write(full_path, json.encode(filter_preset))
ms.ok(string.format("Saved file to: %s", full_path))
end

return save_preset
8 changes: 8 additions & 0 deletions lib/lua/5.1/lunajson.lua
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
local newdecoder = require 'lunajson.decoder'
local newencoder = require 'lunajson.encoder'
-- If you need multiple contexts of decoder and/or encoder,
-- you can require lunajson.decoder and/or lunajson.encoder directly.
return {
decode = newdecoder(),
encode = newencoder(),
}
Loading

0 comments on commit 1a5e97b

Please sign in to comment.