mirror of
https://github.com/immich-app/immich.git
synced 2025-12-19 01:11:07 +03:00
* feat(web,a11y): slider accessibility improvements * add perceivable focus outline * label all sliders for screen readers * chore: add IDs to all settings sliders * chore: add comment to id prop * fix: switch to using CSS to add outlines * fix: reactive sliderId * fix: bring back the slot * fix: add aria-describedby for the subtitle * fix: cleanup css because disabled slider cannot be focused * fix: add border to the slider when focus is visible --------- Co-authored-by: Alex Tran <alex.tran1502@gmail.com>
89 lines
3.8 KiB
Svelte
89 lines
3.8 KiB
Svelte
<script lang="ts">
|
|
import { Colorspace, type SystemConfigDto } from '@immich/sdk';
|
|
import { isEqual } from 'lodash-es';
|
|
import { createEventDispatcher } from 'svelte';
|
|
import { fade } from 'svelte/transition';
|
|
import type { SettingsEventType } from '../admin-settings';
|
|
import SettingSelect from '$lib/components/shared-components/settings/setting-select.svelte';
|
|
|
|
import SettingSwitch from '$lib/components/shared-components/settings/setting-switch.svelte';
|
|
import SettingButtonsRow from '$lib/components/shared-components/settings/setting-buttons-row.svelte';
|
|
import SettingInputField, {
|
|
SettingInputFieldType,
|
|
} from '$lib/components/shared-components/settings/setting-input-field.svelte';
|
|
|
|
export let savedConfig: SystemConfigDto;
|
|
export let defaultConfig: SystemConfigDto;
|
|
export let config: SystemConfigDto; // this is the config that is being edited
|
|
export let disabled = false;
|
|
|
|
const dispatch = createEventDispatcher<SettingsEventType>();
|
|
</script>
|
|
|
|
<div>
|
|
<div in:fade={{ duration: 500 }}>
|
|
<form autocomplete="off" on:submit|preventDefault>
|
|
<div class="ml-4 mt-4 flex flex-col gap-4">
|
|
<SettingSelect
|
|
label="THUMBNAIL RESOLUTION"
|
|
desc="Used when viewing groups of photos (main timeline, album view, etc.). Higher resolutions can preserve more detail but take longer to encode, have larger file sizes, and can reduce app responsiveness."
|
|
number
|
|
bind:value={config.image.thumbnailSize}
|
|
options={[
|
|
{ value: 1080, text: '1080p' },
|
|
{ value: 720, text: '720p' },
|
|
{ value: 480, text: '480p' },
|
|
{ value: 250, text: '250p' },
|
|
{ value: 200, text: '200p' },
|
|
]}
|
|
name="resolution"
|
|
isEdited={config.image.thumbnailSize !== savedConfig.image.thumbnailSize}
|
|
{disabled}
|
|
/>
|
|
|
|
<SettingSelect
|
|
label="PREVIEW RESOLUTION"
|
|
desc="Used when viewing a single photo and for machine learning. Higher resolutions can preserve more detail but take longer to encode, have larger file sizes, and can reduce app responsiveness."
|
|
number
|
|
bind:value={config.image.previewSize}
|
|
options={[
|
|
{ value: 2160, text: '4K' },
|
|
{ value: 1440, text: '1440p' },
|
|
{ value: 1080, text: '1080p' },
|
|
{ value: 720, text: '720p' },
|
|
]}
|
|
name="resolution"
|
|
isEdited={config.image.previewSize !== savedConfig.image.previewSize}
|
|
{disabled}
|
|
/>
|
|
|
|
<SettingInputField
|
|
inputType={SettingInputFieldType.NUMBER}
|
|
label="QUALITY"
|
|
desc="Image quality from 1-100. Higher is better for quality but produces larger files."
|
|
bind:value={config.image.quality}
|
|
isEdited={config.image.quality !== savedConfig.image.quality}
|
|
/>
|
|
|
|
<SettingSwitch
|
|
id="prefer-wide-gamut"
|
|
title="PREFER WIDE GAMUT"
|
|
subtitle="Use Display P3 for thumbnails. This better preserves the vibrance of images with wide colorspaces, but images may appear differently on old devices with an old browser version. sRGB images are kept as sRGB to avoid color shifts."
|
|
checked={config.image.colorspace === Colorspace.P3}
|
|
on:toggle={(e) => (config.image.colorspace = e.detail ? Colorspace.P3 : Colorspace.Srgb)}
|
|
isEdited={config.image.colorspace !== savedConfig.image.colorspace}
|
|
/>
|
|
</div>
|
|
|
|
<div class="ml-4">
|
|
<SettingButtonsRow
|
|
on:reset={({ detail }) => dispatch('reset', { ...detail, configKeys: ['image'] })}
|
|
on:save={() => dispatch('save', { image: config.image })}
|
|
showResetToDefault={!isEqual(savedConfig, defaultConfig)}
|
|
{disabled}
|
|
/>
|
|
</div>
|
|
</form>
|
|
</div>
|
|
</div>
|