diff --git a/assets/js/settings.ts b/assets/js/settings.ts index 9ff6b17f..e4ab8927 100644 --- a/assets/js/settings.ts +++ b/assets/js/settings.ts @@ -11,8 +11,9 @@ export function setupSettings() { if (!$('#js-setting-table')) return; const localCheckboxes = $$('[data-tab="local"] input[type="checkbox"]'); - const themeSelect = assertNotNull($('#user_theme')); - const styleSheet = assertNotNull($('head link[rel="stylesheet"]')); + const themeSelect = assertNotNull($('#user_theme_name')); + const themeColorSelect = assertNotNull($('#user_theme_color')); + const styleSheet = assertNotNull($('#js-theme-stylesheet')); // Local settings localCheckboxes.forEach(checkbox => { @@ -22,9 +23,13 @@ export function setupSettings() { }); // Theme preview - if (themeSelect) { - themeSelect.addEventListener('change', () => { - styleSheet.href = assertNotUndefined(themeSelect.options[themeSelect.selectedIndex].dataset.themePath); - }); - } + const themePreviewCallback = () => { + const themeName = assertNotUndefined(themeSelect.options[themeSelect.selectedIndex].value); + const themeColor = assertNotUndefined(themeColorSelect.options[themeColorSelect.selectedIndex].value); + + styleSheet.href = `/css/${themeName}-${themeColor}.css`; + }; + + themeSelect.addEventListener('change', themePreviewCallback); + themeColorSelect.addEventListener('change', themePreviewCallback); } diff --git a/lib/philomena/users/user.ex b/lib/philomena/users/user.ex index 57c78580..8bb2f693 100644 --- a/lib/philomena/users/user.ex +++ b/lib/philomena/users/user.ex @@ -357,7 +357,7 @@ defmodule Philomena.Users.User do |> TagList.propagate_tag_list(:watched_tag_list, :watched_tag_ids) |> validate_inclusion( :theme, - ~W(dark-blue dark-red dark-green dark-purple dark-pink dark-yellow dark-cyan dark-grey light-blue light-red light-green light-purple light-pink light-yellow light-cyan light-grey) + ~W(dark-red dark-orange dark-yellow dark-blue dark-green dark-purple dark-cyan dark-pink dark-silver light-red light-orange light-yellow light-blue light-green light-purple light-cyan light-pink light-silver) ) |> validate_inclusion(:images_per_page, 1..50) |> validate_inclusion(:comments_per_page, 1..100) diff --git a/lib/philomena_web/controllers/setting_controller.ex b/lib/philomena_web/controllers/setting_controller.ex index 09c3496a..f7928bf9 100644 --- a/lib/philomena_web/controllers/setting_controller.ex +++ b/lib/philomena_web/controllers/setting_controller.ex @@ -9,6 +9,7 @@ defmodule PhilomenaWeb.SettingController do def edit(conn, _params) do changeset = (conn.assigns.current_user || %User{}) + |> assign_theme() |> TagList.assign_tag_list(:watched_tag_ids, :watched_tag_list) |> Users.change_user() @@ -57,13 +58,21 @@ defmodule PhilomenaWeb.SettingController do ) end - defp determine_theme(%{"theme" => "light", "light_theme" => name} = attrs) when name != nil, - do: Map.replace(attrs, "theme", name) + defp assign_theme(%{theme: theme} = user) do + [theme_name, theme_color] = String.split(theme, "-") - defp determine_theme(%{"dark_theme" => name} = attrs) when name != nil, - do: Map.replace(attrs, "theme", name) + user + |> Map.put(:theme_name, theme_name) + |> Map.put(:theme_color, theme_color) + end - defp determine_theme(attrs), do: Map.replace(attrs, "theme", "dark-blue") + defp assign_theme(_), do: assign_theme(%{theme: "dark-blue"}) + + defp determine_theme(%{"theme_name" => name, "theme_color" => color} = attrs) + when name != nil and color != nil, + do: Map.put(attrs, "theme", "#{name}-#{color}") + + defp determine_theme(attrs), do: Map.put(attrs, "theme", "dark-blue") defp maybe_update_user(conn, nil, _user_params), do: {:ok, conn} diff --git a/lib/philomena_web/templates/layout/app.html.slime b/lib/philomena_web/templates/layout/app.html.slime index f0805313..2ca353fe 100644 --- a/lib/philomena_web/templates/layout/app.html.slime +++ b/lib/philomena_web/templates/layout/app.html.slime @@ -13,9 +13,9 @@ html lang="en" =<> site_name() link rel="preconnect" href="https://#{cdn_host()}" link rel="stylesheet" href=~p"/css/application.css" - link rel="stylesheet" href=stylesheet_path(@conn, @current_user) + link#js-theme-stylesheet rel="stylesheet" href=stylesheet_path(@conn, @current_user) = if is_nil(@current_user) do - link rel="stylesheet" href=light_stylesheet_path(@conn) media="(prefers-color-scheme: light)" + link#js-theme-stylesheet rel="stylesheet" href=light_stylesheet_path(@conn) media="(prefers-color-scheme: light)" link rel="icon" href=~p"/favicon.ico" type="image/x-icon" link rel="icon" href=~p"/favicon.svg" type="image/svg+xml" link rel="search" type="application/opensearchdescription+xml" title="Derpibooru" href="/opensearch.xml" diff --git a/lib/philomena_web/templates/setting/edit.html.slime b/lib/philomena_web/templates/setting/edit.html.slime index aa10ae2d..524ee17c 100644 --- a/lib/philomena_web/templates/setting/edit.html.slime +++ b/lib/philomena_web/templates/setting/edit.html.slime @@ -83,22 +83,16 @@ h1 Content Settings ' For 1080p monitors, try 24. .field label Theme - select.input#js-theme-selector name="user[theme]" id="user_theme" - option value="dark" Dark - option value="light" Light + .with-error + => select f, :theme_name, themes(), class: "input" + = error_tag f, :theme_name .fieldlabel: i General appearance of the theme - .field#js-theme-dark + .field label Theme color .with-error - => select f, :dark_theme, theme_options(), class: "input" - = error_tag f, :dark_theme + => select f, :theme_color, theme_colors(), class: "input" + = error_tag f, :theme_color .fieldlabel: i Color of the theme, don't forget to save settings to apply the theme - .field.hidden#js-theme-light - label Theme color - .with-error - => select f, :light_theme, light_theme_options(), class: "input" - = error_tag f, :light_theme - .fieldlabel: i Preview themes by selecting one from the dropdown. Saving sets the currently selected theme. .field => label f, :scale_large_images .with-error diff --git a/lib/philomena_web/views/layout_view.ex b/lib/philomena_web/views/layout_view.ex index b30a0d8c..db166710 100644 --- a/lib/philomena_web/views/layout_view.ex +++ b/lib/philomena_web/views/layout_view.ex @@ -71,22 +71,24 @@ defmodule PhilomenaWeb.LayoutView do def stylesheet_path(conn, %{theme: theme}) when theme in [ - "dark-blue", "dark-red", + "dark-orange", + "dark-yellow", + "dark-blue", "dark-green", "dark-purple", - "dark-pink", - "dark-yellow", "dark-cyan", - "dark-grey", - "light-blue", + "dark-pink", + "dark-silver", "light-red", + "light-orange", + "light-yellow", + "light-blue", "light-green", "light-purple", - "light-pink", - "light-yellow", "light-cyan", - "light-grey" + "light-pink", + "light-silver" ], do: static_path(conn, "/css/#{theme}.css") diff --git a/lib/philomena_web/views/setting_view.ex b/lib/philomena_web/views/setting_view.ex index a9eb68cd..63030bb2 100644 --- a/lib/philomena_web/views/setting_view.ex +++ b/lib/philomena_web/views/setting_view.ex @@ -1,103 +1,24 @@ defmodule PhilomenaWeb.SettingView do use PhilomenaWeb, :view - def theme_options do + def themes do [ - [ - key: "Red", - value: "dark-red", - data: [theme_path: ~p"/css/dark-red.css"] - ], - [ - key: "Orange", - value: "dark-orange", - data: [theme_path: ~p"/css/dark-orange.css"] - ], - [ - key: "Yellow", - value: "dark-yellow", - data: [theme_path: ~p"/css/dark-yellow.css"] - ], - [ - key: "Green", - value: "dark-green", - data: [theme_path: ~p"/css/dark-green.css"] - ], - [ - key: "Blue", - value: "dark-blue", - data: [theme_path: ~p"/css/dark-blue.css"] - ], - [ - key: "Purple", - value: "dark-purple", - data: [theme_path: ~p"/css/dark-purple.css"] - ], - [ - key: "Cyan", - value: "dark-cyan", - data: [theme_path: ~p"/css/dark-cyan.css"] - ], - [ - key: "Pink", - value: "dark-pink", - data: [theme_path: ~p"/css/dark-pink.css"] - ], - [ - key: "Grey", - value: "dark-grey", - data: [theme_path: ~p"/css/dark-grey.css"] - ] + Dark: "dark", + Light: "light" ] end - def light_theme_options do + def theme_colors do [ - [ - key: "Red", - value: "light-red", - data: [theme_path: ~p"/css/light-red.css"] - ], - [ - key: "Orange", - value: "light-orange", - data: [theme_path: ~p"/css/light-orange.css"] - ], - [ - key: "Yellow", - value: "light-yellow", - data: [theme_path: ~p"/css/light-yellow.css"] - ], - [ - key: "Green", - value: "light-green", - data: [theme_path: ~p"/css/light-green.css"] - ], - [ - key: "Blue", - value: "light-blue", - data: [theme_path: ~p"/css/light-blue.css"] - ], - [ - key: "Purple", - value: "light-purple", - data: [theme_path: ~p"/css/light-purple.css"] - ], - [ - key: "Cyan", - value: "light-cyan", - data: [theme_path: ~p"/css/light-cyan.css"] - ], - [ - key: "Pink", - value: "light-pink", - data: [theme_path: ~p"/css/light-pink.css"] - ], - [ - key: "Grey", - value: "light-grey", - data: [theme_path: ~p"/css/light-grey.css"] - ] + Red: "red", + Orange: "orange", + Yellow: "yellow", + Green: "green", + Blue: "blue", + Purple: "purple", + Cyan: "cyan", + Pink: "pink", + "Silver/Charcoal": "silver" ] end