diff options
Diffstat (limited to 'src/components/settings_modal')
5 files changed, 201 insertions, 119 deletions
diff --git a/src/components/settings_modal/tabs/appearance_tab.js b/src/components/settings_modal/tabs/appearance_tab.js index 4f988508..10de0397 100644 --- a/src/components/settings_modal/tabs/appearance_tab.js +++ b/src/components/settings_modal/tabs/appearance_tab.js @@ -6,6 +6,18 @@ import UnitSetting, { defaultHorizontalUnits } from '../helpers/unit_setting.vue import FontControl from 'src/components/font_control/font_control.vue' +import { normalizeThemeData } from 'src/modules/interface' + +import { + getThemes +} from 'src/services/style_setter/style_setter.js' +import { convertTheme2To3 } from 'src/services/theme_data/theme2_to_theme3.js' +import { init } from 'src/services/theme_data/theme_data_3.service.js' +import { + getCssRules, + getScopedVersion +} from 'src/services/theme_data/css_utils.js' + import SharedComputedObject from '../helpers/shared_computed_object.js' import ProfileSettingIndicator from '../helpers/profile_setting_indicator.vue' import { library } from '@fortawesome/fontawesome-svg-core' @@ -13,6 +25,8 @@ import { faGlobe } from '@fortawesome/free-solid-svg-icons' +import Preview from './theme_tab/preview.vue' + library.add( faGlobe ) @@ -20,6 +34,7 @@ library.add( const AppearanceTab = { data () { return { + availableStyles: [], thirdColumnModeOptions: ['none', 'notifications', 'postform'].map(mode => ({ key: mode, value: mode, @@ -44,7 +59,32 @@ const AppearanceTab = { FloatSetting, UnitSetting, ProfileSettingIndicator, - FontControl + FontControl, + Preview + }, + created () { + const self = this + + getThemes() + .then((promises) => { + return Promise.all( + Object.entries(promises) + .map(([k, v]) => v.then(res => [k, res])) + ) + }) + .then(themes => themes.reduce((acc, [k, v]) => { + if (v) { + return { + ...acc, + [k]: v + } + } else { + return acc + } + }, {})) + .then((themesComplete) => { + self.availableStyles = themesComplete + }) }, computed: { horizontalUnits () { @@ -77,6 +117,25 @@ const AppearanceTab = { } }, ...SharedComputedObject() + }, + methods: { + previewTheme (input) { + const style = normalizeThemeData(input) + const x = 2 + if (x === 1) return + const theme2 = convertTheme2To3(style) + const theme3 = init({ + inputRuleset: theme2, + ultimateBackgroundColor: '#000000', + liteMode: true, + onlyNormalState: true + }) + + return getScopedVersion( + getCssRules(theme3.eager), + '#theme-preview-' + (input.name || input[0]).replace(/ /g, '_') + ).join('\n') + } } } diff --git a/src/components/settings_modal/tabs/appearance_tab.vue b/src/components/settings_modal/tabs/appearance_tab.vue index 85084e29..2488720d 100644 --- a/src/components/settings_modal/tabs/appearance_tab.vue +++ b/src/components/settings_modal/tabs/appearance_tab.vue @@ -1,6 +1,22 @@ <template> <div :label="$t('settings.general')"> <div class="setting-item"> + <h2>{{ $t('settings.theme') }}</h2> + <ul class="theme-list"> + <li + v-for="style in availableStyles" + :key="style.name || style[0]" + class="theme-preview" + > + <h6>{{ style[0] || style.name }}</h6> + <!-- eslint-disable vue/no-v-text-v-html-on-component --> + <component :is="'style'" v-html="previewTheme(style)"/> + <!-- eslint-enable vue/no-v-text-v-html-on-component --> + <preview :id="'theme-preview-' + (style[0] || style.name).replace(/ /g,'_')"/> + </li> + </ul> + </div> + <div class="setting-item"> <h2>{{ $t('settings.scale_and_layout') }}</h2> <ul class="setting-list"> <li> @@ -231,4 +247,18 @@ margin-bottom: 0.5em; margin-top: 0.5em; } + +.theme-list { + list-style: none; + display: flex; + flex-wrap: wrap; +} + +.theme-preview { + width: 10rem; + + .preview-container { + zoom: 0.33; + } +} </style> diff --git a/src/components/settings_modal/tabs/theme_tab/preview.vue b/src/components/settings_modal/tabs/theme_tab/preview.vue index 1837620f..7ec34afd 100644 --- a/src/components/settings_modal/tabs/theme_tab/preview.vue +++ b/src/components/settings_modal/tabs/theme_tab/preview.vue @@ -139,6 +139,108 @@ export default {} <style lang="scss"> .preview-container { position: relative; + border-top: 1px dashed; + border-bottom: 1px dashed; + border-color: var(--border); + margin: 1em 0; + padding: 1em; + background-color: var(--wallpaper); + background-image: var(--body-background-image); + background-size: cover; + background-position: 50% 50%; + + .theme-preview-content { + padding: 20px; + } + + .dummy { + .post { + font-family: var(--postFont); + display: flex; + + .content { + flex: 1; + + h4 { + margin-bottom: 0.25em; + } + + .icons { + margin-top: 0.5em; + display: flex; + + i { + margin-right: 1em; + } + } + } + } + + .after-post { + margin-top: 1em; + display: flex; + align-items: center; + } + + .avatar, + .avatar-alt { + background: + linear-gradient( + 135deg, + #b8e1fc 0%, + #a9d2f3 10%, + #90bae4 25%, + #90bcea 37%, + #90bff0 50%, + #6ba8e5 51%, + #a2daf5 83%, + #bdf3fd 100% + ); + color: black; + font-family: sans-serif; + text-align: center; + margin-right: 1em; + } + + .avatar-alt { + flex: 0 auto; + margin-left: 28px; + font-size: 12px; + min-width: 20px; + min-height: 20px; + line-height: 20px; + } + + .avatar { + flex: 0 auto; + width: 48px; + height: 48px; + font-size: 14px; + line-height: 48px; + } + + .actions { + display: flex; + align-items: baseline; + + .checkbox { + display: inline-flex; + align-items: baseline; + margin-right: 1em; + flex: 1; + } + } + + .separator { + margin: 1em; + border-bottom: 1px solid; + border-color: var(--border); + } + + .btn { + min-width: 3em; + } + } } .underlay-preview { @@ -148,4 +250,4 @@ export default {} left: 10px; right: 10px; } -</style> + </style> diff --git a/src/components/settings_modal/tabs/theme_tab/theme_tab.js b/src/components/settings_modal/tabs/theme_tab/theme_tab.js index 8d025ea4..a19550d1 100644 --- a/src/components/settings_modal/tabs/theme_tab/theme_tab.js +++ b/src/components/settings_modal/tabs/theme_tab/theme_tab.js @@ -30,7 +30,10 @@ import { import { convertTheme2To3 } from 'src/services/theme_data/theme2_to_theme3.js' import { init } from 'src/services/theme_data/theme_data_3.service.js' -import { getCssRules } from 'src/services/theme_data/css_utils.js' +import { + getCssRules, + getScopedVersion +} from 'src/services/theme_data/css_utils.js' import ColorInput from 'src/components/color_input/color_input.vue' import RangeInput from 'src/components/range_input/range_input.vue' @@ -703,17 +706,10 @@ export default { liteMode: true }) - this.themeV3Preview = getCssRules(theme3.eager) - .map(x => { - if (x.startsWith('html')) { - return x.replace('html', '#theme-preview') - } else if (x.startsWith('#content')) { - return x.replace('#content', '#theme-preview') - } else { - return '#theme-preview > ' + x - } - }) - .join('\n') + this.themeV3Preview = getScopedVersion( + getCssRules(theme3.eager), + '#theme-preview' + ).join('\n') } }, watch: { diff --git a/src/components/settings_modal/tabs/theme_tab/theme_tab.scss b/src/components/settings_modal/tabs/theme_tab/theme_tab.scss index 4cb37c1e..3ae8864c 100644 --- a/src/components/settings_modal/tabs/theme_tab/theme_tab.scss +++ b/src/components/settings_modal/tabs/theme_tab/theme_tab.scss @@ -161,107 +161,6 @@ } } - .preview-container { - border-top: 1px dashed; - border-bottom: 1px dashed; - border-color: var(--border); - margin: 1em 0; - padding: 1em; - background-color: var(--wallpaper); - background-image: var(--body-background-image); - background-size: cover; - background-position: 50% 50%; - - .dummy { - .post { - font-family: var(--postFont); - display: flex; - - .content { - flex: 1; - - h4 { - margin-bottom: 0.25em; - } - - .icons { - margin-top: 0.5em; - display: flex; - - i { - margin-right: 1em; - } - } - } - } - - .after-post { - margin-top: 1em; - display: flex; - align-items: center; - } - - .avatar, - .avatar-alt { - background: - linear-gradient( - 135deg, - #b8e1fc 0%, - #a9d2f3 10%, - #90bae4 25%, - #90bcea 37%, - #90bff0 50%, - #6ba8e5 51%, - #a2daf5 83%, - #bdf3fd 100% - ); - color: black; - font-family: sans-serif; - text-align: center; - margin-right: 1em; - } - - .avatar-alt { - flex: 0 auto; - margin-left: 28px; - font-size: 12px; - min-width: 20px; - min-height: 20px; - line-height: 20px; - } - - .avatar { - flex: 0 auto; - width: 48px; - height: 48px; - font-size: 14px; - line-height: 48px; - } - - .actions { - display: flex; - align-items: baseline; - - .checkbox { - display: inline-flex; - align-items: baseline; - margin-right: 1em; - flex: 1; - } - } - - .separator { - margin: 1em; - border-bottom: 1px solid; - border-color: var(--border); - } - - .btn { - min-width: 3em; - } - } - } - .radius-item { flex-basis: auto; } @@ -314,10 +213,6 @@ max-width: 50em; } - .theme-preview-content { - padding: 20px; - } - .theme-warning { display: flex; align-items: baseline; |
