export const settings = {
  title: 'Settings',
  language: 'Language',
  languageEn: 'English',
  languageDe: 'Deutsch',
  languageEs: 'Español',
  languageFr: 'Français',
  languageNl: 'Nederlands',
  languageNb: 'Norsk',
  languageRu: 'Русский',
  languageZh: '中文',
  languageRo: 'Română',
  font: 'Font',
  fontHintOpenDyslexic: 'Dyslexia-friendly · no Chinese support',
  theme: 'Theme',
  appearance: 'Appearance',
  servers: 'Servers',
  serverName: 'Server Name',
  serverUrl: 'Server URL',
  serverUrlPlaceholder: '192.168.1.100:4533 or https://music.example.com',
  serverAlternateUrl: 'Second address (optional)',
  serverAlternateUrlPlaceholderPublic: 'https://music.example.com',
  serverAlternateUrlPlaceholderLocal: '192.168.1.100:4533',
  serverAlternateUrlHintAddPublic: 'You can add a public address for access outside your home network.',
  serverAlternateUrlHintAddLocal: 'You can add a local address for faster connection at home.',
  serverBothLanError: 'Both addresses are local — keep one or add a public address.',
  dualAddressVerifying: 'Checking that both addresses point at the same server…',
  dualAddressMismatch: 'The two addresses point at different servers. Check spelling and try again.',
  dualAddressInsufficient: 'Could not confirm both addresses are the same server. Remove one address to continue.',
  dualAddressUnreachable: 'Could not reach {{host}}. Check the address and your network, then try again.',
  urlRemigrationTitle: 'Move your library data?',
  urlRemigrationMessage: 'Changing the address will move all library, analysis, and cover-cache data from {{oldKey}} to {{newKey}}. This cannot be undone.',
  urlRemigrationConfirm: 'Move data',
  urlRemigrationProgress: 'Moving library data…',
  urlRemigrationFailureInspect: 'Could not check what would be moved. Try again, or open the debug log.',
  urlRemigrationFailureRun: 'Moving the library data failed. Your saved data is unchanged — try again.',
  urlRemigrationFailureCoverRename: 'Library data was moved, but cover files could not be renamed. Covers will rebuild on next access.',
  shareUsesLocalUrl: 'Use local address in share links',
  shareUsesLocalUrlDesc: 'Affects Orbit invites and library shares. Default: public address.',
  serverUsername: 'Username',
  serverPassword: 'Password',
  addServer: 'Add Server',
  addServerTitle: 'Add New Server',
  editServer: 'Edit',
  editServerTitle: 'Edit Server',
  useServer: 'Use',
  deleteServer: 'Delete',
  noServers: 'No servers saved.',
  serverActive: 'Active',
  serverVersionUnknown: 'Server version unknown',
  confirmDeleteServer: 'Delete server "{{name}}"?',
  confirmDeleteServerLibrary: 'Also delete this server\'s local library index? Click Cancel to keep the cached copy for offline use.',
  serverConnecting: 'Connecting…',
  serverConnected: 'Connected!',
  serverFailed: 'Connection failed.',
  testBtn: 'Test Connection',
  testingBtn: 'Testing…',
  serverCompatible: 'Built for Navidrome. Other Subsonic-compatible servers (Gonic, Airsonic, …) may work with reduced functionality, since Psysonic uses many Navidrome-specific API endpoints.',
  userMgmtTitle: 'User Management',
  userMgmtDesc: 'Manage users on this server. Requires admin privileges.',
  userMgmtNoAdmin: 'You need admin privileges to manage users on this server.',
  userMgmtLoadError: 'Failed to load users.',
  userMgmtLoadFriendly: 'Server didn\'t answer — this is usually a one-off.',
  userMgmtRetry: 'Retry',
  userMgmtEmpty: 'No users found.',
  userMgmtYouBadge: 'You',
  userMgmtAdminBadge: 'Admin',
  userMgmtAddUser: 'Add User',
  userMgmtAddUserTitle: 'Add New User',
  userMgmtEditUserTitle: 'Edit User',
  userMgmtUsername: 'Username',
  userMgmtName: 'Display Name',
  userMgmtEmail: 'Email',
  userMgmtPassword: 'Password',
  userMgmtPasswordEditHint: 'Enter a new password to update it.',
  userMgmtRoleAdmin: 'Admin',
  userMgmtLibraries: 'Libraries',
  userMgmtLibrariesAdminHint: 'Admin users automatically have access to all libraries.',
  userMgmtLibrariesEmpty: 'No libraries available on this server.',
  userMgmtLibrariesValidation: 'Select at least one library.',
  userMgmtLibrariesUpdateError: 'User saved, but library assignment failed',
  userMgmtNoLibraries: 'No libraries assigned',
  userMgmtNeverSeen: 'Never',
  userMgmtSave: 'Save',
  userMgmtCancel: 'Cancel',
  userMgmtDelete: 'Delete',
  userMgmtEdit: 'Edit',
  userMgmtConfirmDelete: 'Delete user "{{username}}"? This cannot be undone.',
  userMgmtCreateError: 'Failed to create user.',
  userMgmtUpdateError: 'Failed to update user.',
  userMgmtDeleteError: 'Failed to delete user.',
  userMgmtCreated: 'User created.',
  userMgmtUpdated: 'User updated.',
  userMgmtDeleted: 'User deleted.',
  userMgmtValidationMissing: 'Username, display name and password are required.',
  userMgmtValidationMissingIdentity: 'Username and display name are required.',
  userMgmtMagicStringGenerate: 'Generate magic string',
  userMgmtSaveAndMagicString: 'Save and get magic string',
  userMgmtMagicStringPasswordNavHint:
    'Navidrome will save this password for the user. If it differs from the current one, the server will update the login password.',
  userMgmtMagicStringPlaintextWarning:
    'Share the magic string carefully: it contains an unencrypted password (encoding is not encryption). Anyone with the full string can sign in as this user.',
  userMgmtMagicStringCopied: 'Magic string copied to clipboard.',
  userMgmtMagicStringCopyFailed: 'Could not copy to clipboard.',
  userMgmtMagicStringLoginFailed: 'Password check failed — credentials could not be verified.',
  userMgmtMagicStringModalTitle: 'Generate magic string',
  userMgmtMagicStringModalDesc: 'Enter the Subsonic password for "{{username}}". It is included in the copied magic string.',
  userMgmtMagicStringModalConfirm: 'Copy string',
  audiomuseTitle: 'AudioMuse-AI (Navidrome)',
  audiomuseBadge: 'AudioMuse-AI',
  audiomuseDesc:
    'Turn on if this server has the <pluginLink>AudioMuse-AI Navidrome plugin</pluginLink> configured. Enables Instant Mix from tracks and uses server-side similar artists instead of Last.fm on artist pages.',
  audiomuseStatusActive: 'Active',
  audiomuseStatusChecking: 'Checking…',
  audiomuseStatusNotDetected: 'Not detected',
  audiomuseStatusProbeFailed: 'Probe failed',
  audiomuseIssueHint:
    'Instant Mix failed recently — check the Navidrome plugin and AudioMuse API. Similar artists fall back to Last.fm when the server returns none.',
  connected: 'Connected',
  failed: 'Failed',
  eqTitle: 'Equalizer',
  eqEnabled: 'Enable Equalizer',
  eqPreset: 'Preset',
  eqPresetCustom: 'Custom',
  eqPresetBuiltin: 'Built-in Presets',
  eqPresetCustomGroup: 'My Presets',
  eqSavePreset: 'Save as Preset',
  eqPresetName: 'Preset name…',
  eqDeletePreset: 'Delete preset',
  eqResetBands: 'Reset to Flat',
  eqPreGain: 'Pre-gain',
  eqResetPreGain: 'Reset pre-gain',
  eqAutoEqTitle: 'AutoEQ Headphone Lookup',
  eqAutoEqPlaceholder: 'Search headphone / IEM model…',
  eqAutoEqSearching: 'Searching…',
  eqAutoEqNoResults: 'No results found',
  eqAutoEqError: 'Search failed',
  eqAutoEqRateLimit: 'GitHub rate limit reached — try again in a minute',
  eqAutoEqFetchError: 'Failed to fetch EQ profile',
  behavior: 'App Behavior',
  groupTray: 'Tray',
  groupLinuxRendering: 'Linux rendering',
  groupClock: 'Clock',
  groupDisplay: 'Display',
  groupWindow: 'Window',
  cacheTitle: 'Max. Storage Size',
  cacheDesc: 'In-browser cache for cover art and artist images (IndexedDB). Oldest entries are removed automatically when space runs low.',
  cacheUsedImages: 'Images:',
  cacheUsedOffline: 'Offline tracks:',
  cacheUsedHot: 'Size on disk:',
  hotCacheTrackCount: 'Tracks in cache:',
  cacheMaxLabel: 'Max. size',
  imageCacheScopeLabel: 'Scope',
  imageCacheSubTitle: 'In-browser previews',
  coverDiskCacheSubTitle: 'On-disk cover cache',
  coverCacheStrategyTitle: 'Cover art cache',
  coverCacheStrategyDesc: 'You can choose a strategy for each server: Lazy — load covers as needed; Aggressive — load as needed plus extra background preloading.',
  coverCacheStrategyLabel: 'Strategy',
  coverCacheStrategyServerLabel: 'Server',
  coverCacheStrategyProgressLabel: 'Cache',
  coverCacheStrategyActionsLabel: 'Actions',
  coverCacheStrategyLazy: 'Lazy',
  coverCacheStrategyLazyDesc: 'Loads covers only when they are needed.',
  coverCacheStrategyAggressive: 'Aggressive',
  coverCacheStrategyAggressiveDesc: 'Lazy behaviour plus extra background preloading.',
  coverCacheStrategyDiskUsage: 'On disk: {{size}}',
  coverCacheStrategyProgressValue: '{{percent}}% ({{done}}/{{total}}) · {{size}}',
  coverCacheStrategyClearAction: 'Clear cover cache',
  coverCacheStrategyClearTitle: 'Clear cover cache?',
  coverCacheStrategyClearDesc: 'Remove all cached cover images for {{server}}. They will be re-downloaded when needed.',
  coverCacheStrategyClearConfirm: 'Clear',
  coverCacheStrategyClearCancel: 'Cancel',
  coverCacheStrategyClearSuccess: 'Cover cache cleared for this server.',
  coverCacheStrategyClearError: 'Failed to clear cover cache.',
  coverCacheStrategyServerRemoved: 'removed server',
  cacheClearBtn: 'Clear Cache',
  cacheClearWarning: 'Clears all cached cover and artist images from in-browser storage. They will be re-downloaded when needed.',
  cacheClearConfirm: 'Clear image cache',
  cacheClearCancel: 'Cancel',
  waveformCacheCleared: 'Waveform cache cleared ({{count}} rows).',
  waveformCacheClearFailed: 'Failed to clear waveform cache.',
  storageTabTitle: 'Offline & cache',
  mediaDirTitle: 'Media folder',
  mediaDirDesc: 'Root folder for local playback. Offline library uses library/; queue prefetch uses cache/.',
  mediaDirDefault: 'Default (App Data)',
  mediaDirChange: 'Change folder',
  mediaDirClear: 'Reset to default',
  mediaDirHint: 'New downloads use this location. Existing files stay at their original paths until removed.',
  offlineStorageTitle: 'Offline library storage',
  offlineDirTitle: 'Offline Library (In-App)',
  offlineDirDesc: 'Storage location for tracks you make available offline within Psysonic.',
  offlineDirDefault: 'Default (App Data)',
  offlineDirChange: 'Change Directory',
  offlineDirClear: 'Reset to Default',
  offlineDirHint: 'New downloads will use this location. Existing downloads remain at their original path.',
  hotCacheTitle: 'Hot playback cache',
  hotCacheDisclaimer: 'Preloads upcoming queue tracks and keeps previous ones. When enabled, uses disk space and network.',
  hotCacheDirDefault: 'Default (App Data)',
  hotCacheDirChange: 'Change folder',
  hotCacheDirClear: 'Reset to default',
  hotCacheDirHint: 'Changing the folder resets the in-app index; files already on disk stay where they are until you remove them.',
  hotCacheEnabled: 'Enable hot playback cache',
  hotCacheMaxMb: 'Maximum cache size',
  hotCacheDebounce: 'Queue change debounce',
  hotCacheDebounceImmediate: 'Immediate',
  hotCacheDebounceSeconds: '{{n}} s',
  hotCacheClearBtn: 'Clear hot cache',
  audioOutputDevice: 'Audio Output Device',
  audioOutputDeviceDesc: 'Select which audio device Psysonic plays through. Changes take effect immediately and restart the current track.',
  audioOutputDeviceDefault: 'System Default',
  audioOutputDeviceRefresh: 'Refresh device list',
  audioOutputDeviceOsDefaultNow: 'current system output',
  audioOutputDeviceListError: 'Could not load the audio device list.',
  audioOutputDeviceNotInCurrentList: 'not in current list',
  audioOutputDeviceMacNotice: 'On macOS, playback currently always follows the system output device for technical reasons. Change the target via System Settings → Sound or the speaker icon in the menu bar. Background: CoreAudio triggers a microphone-permission prompt when opening a non-default stream — we avoid it by always using the system default.',
  hiResTitle: 'Native Hi-Res Playback',
  hiResEnabled: 'Enable native hi-res playback',
  hiResDesc: "Plays each track at its original sample rate instead of resampling everything to 44.1 kHz, switching the audio device to match the file (88.2 kHz and up). Enable only if your hardware and network reliably handle high sample rates.",
  showArtistImages: 'Show Artist Images',
  showArtistImagesDesc: 'Load and display artist images in the Artists overview. Disabled by default to reduce server disk I/O and network load on large libraries.',
  showOrbitTrigger: 'Show "Orbit" in the header',
  showOrbitTriggerDesc: 'The top-bar trigger for starting or joining a shared listening session. Hide it if you don\'t use Orbit — you can turn it back on here.',
  showTrayIcon: 'Show Tray Icon',
  showTrayIconDesc: 'Display the Psysonic icon in the system notification area / menu bar.',
  minimizeToTray: 'Minimize to Tray',
  minimizeToTrayDesc: 'When closing the window, keep Psysonic running in the system tray instead of quitting.',
  clockFormat: 'Clock Format',
  clockFormatDesc: 'Wall-clock display used by the queue ETA and the sleep-timer preview.',
  clockFormatAuto: 'Auto (system locale)',
  clockFormatTwentyFour: '24-hour',
  clockFormatTwelve: '12-hour (AM/PM)',
  preloadMiniPlayer: 'Preload mini player',
  preloadMiniPlayerDesc: 'Build the mini player window in the background at app start so it shows content instantly on first open. Uses a little extra memory.',
  discordRichPresence: 'Discord Rich Presence',
  discordRichPresenceDesc: 'Show the currently playing track on your Discord profile. Requires Discord to be running.',
  discordRichPresenceNotice: 'Heads up: this is Psysonic\'s built-in Discord Rich Presence. If you\'d rather use the official Navidrome Discord Rich Presence plugin, leave this switched off and enable "Show in Now Playing" further down this page instead.',
  useCustomTitlebar: 'Custom title bar',
  useCustomTitlebarDesc: 'Replace the system title bar with a built-in one that matches the app theme. Disable to use the native GNOME/GTK title bar.',
  windowButtonStyle: 'Window buttons',
  windowButtonStyleDesc: 'Pick the look of the minimize, maximize and close buttons.',
  windowButtonsDots: 'Dots',
  windowButtonsDotsGlyph: 'Dots + icons',
  windowButtonsFlat: 'Flat',
  windowButtonsPill: 'Pill',
  windowButtonsOutline: 'Outline',
  windowButtonsGlyph: 'Minimal',
  showMinimizeButton: 'Show minimize button',
  showMinimizeButtonDesc: 'Turn off to show only the maximize and close buttons.',
  linuxWebkitSmoothScroll: 'Smooth wheel (Linux)',
  linuxWebkitSmoothScrollDesc: 'On: inertial scroll. Off: line-by-line, GTK-style.',
  linuxWebkitInputForceRepaint: 'Repaint inputs on focus (Linux)',
  linuxWebkitInputForceRepaintDesc: 'Workaround for WebKitGTK 2.50.x where text fields freeze when clicked. Search icons flicker briefly on focus.',
  linuxWaylandTextRender: 'Wayland text rendering (Linux)',
  linuxWaylandTextRenderDesc:
    'Font smoothing in the UI updates immediately. WebKit hardware acceleration (sharp / GPU presets) is saved and applied on the next app start — changing it live can freeze WebKitGTK on some setups.',
  linuxWaylandTextRenderBalanced: 'Balanced',
  linuxWaylandTextRenderSharp: 'Sharp (CPU-friendly)',
  linuxWaylandTextRenderGpu: 'GPU-first',
  linuxWaylandTextRenderMinimal: 'Minimal (default CSS smoothing)',
  discordCoverTitle: 'Cover art source',
  discordCoverDesc: 'Where the album artwork on your Discord profile comes from.',
  discordCoverNone: 'None (app icon only)',
  discordCoverServer: 'Server (via album info)',
  discordCoverApple: 'Apple Music',
  discordOptions: 'Advanced Discord options',
  discordTemplates: 'Custom text templates',
  discordTemplatesDesc: 'Customize what information is shown on your Discord profile. Variables: {title}, {artist}, {album}',
  discordTemplateDetails: 'Primary line (details)',
  discordTemplateState: 'Secondary line (state)',
  discordTemplateLargeText: 'Album tooltip (largeText)',
  discordTemplateName: 'User list line (name)',
  nowPlayingEnabled: 'Show in Now Playing',
  nowPlayingEnabledDesc: 'Broadcast your currently playing track to the server\'s live listener view. Disable to stop sending playback data.',
  nowPlayingPluginNote: 'Required when using the official Navidrome Discord Rich Presence plugin.',
  enableBandsintown: 'Bandsintown tour dates',
  enableBandsintownDesc: 'Show upcoming concerts for the current artist in the Info tab. Data is fetched from the public Bandsintown API.',
  lyricsServerFirst: 'Prefer server lyrics',
  lyricsServerFirstDesc: 'Check server-provided lyrics (embedded tags, sidecar files) before querying LRCLIB. Disable to use LRCLIB first.',
  enableNeteaselyrics: 'Netease Cloud Music lyrics',
  enableNeteaselyricsDesc: 'Use Netease Cloud Music as a last-resort lyrics source when server and LRCLIB both return nothing. Best coverage for Asian and international music.',
  lyricsSourcesTitle: 'Lyrics Sources',
  lyricsSourcesDesc: 'Choose which sources to query for lyrics and in what order. Drag to reorder. Disabled sources are skipped entirely.',
  lyricsSourceServer: 'Server',
  lyricsSourceLrclib: 'LRCLIB',
  lyricsSourceNetease: 'Netease Cloud Music',
  lyricsYouLyPlus: 'YouLyPlus (Karaoke)',
  lyricsYouLyPlusDesc: 'Word-by-word sync from a community backend (Apple Music, Spotify, Musixmatch, QQ). Tried first; the enabled sources below act as fallback.',
  lyricsSourcesFallbackHint: 'Used as fallback when YouLyPlus finds nothing. Drag to reorder.',
  lyricsSourcesPrimaryHint: 'Tried in order. Drag to reorder. All off = lyrics disabled.',
  lyricsStaticOnly: 'Show lyrics as static text only',
  lyricsStaticOnlyDesc: 'Render synced lyrics without auto-scroll and without word highlighting.',
  downloadsTitle: 'ZIP Export & Archiving',
  downloadsFolderDesc: 'Destination folder for albums you download as a ZIP file to your computer.',
  downloadsDefault: 'Default Downloads Folder',
  pickFolder: 'Select',
  pickFolderTitle: 'Select Download Folder',
  clearFolder: 'Clear download folder',
  logout: 'Logout',
  aboutTitle: 'About Psysonic',
  aboutDesc: 'A modern desktop music player built for Navidrome. Uses the Subsonic API plus Navidrome-specific extensions. Built on Tauri v2 with a native Rust audio engine — lightweight and fast, yet packed with features: waveform seekbar, synchronized lyrics, Last.fm integration, 10-band EQ, crossfade, gapless playback, Replay Gain, genre browsing, and a large library of themes.',
  aboutLicense: 'License',
  aboutLicenseText: 'GNU GPL v3 — free to use, modify, and distribute under the same license.',
  aboutRepo: 'Source Code on GitHub',
  aboutVersion: 'Version',
  aboutBuiltWith: 'Built with Tauri · React · TypeScript · Rust/rodio',
  aboutMaintainersLabel: 'Maintainers',
  aboutReleaseNotesLabel: 'Release notes',
  aboutReleaseNotesLink: "Open this version's what's-new",
  aboutContributorsLabel: 'Contributors',
  showChangelogOnUpdate: "Show 'What's New' on update",
  showChangelogOnUpdateDesc: "Show a discreet changelog banner above Now Playing after an update. Click opens the release notes; X dismisses it.",
  libraryGridMaxColumnsTitle: 'Library card grids',
  libraryGridMaxColumnsPerfHint: 'Higher values pack more tiles per row and can increase layout and painting work—noticeable on very large libraries or slower devices.',
  libraryGridMaxColumnsRangeLabel: 'Maximum columns ({{min}}–{{max}})',
  libraryGridMaxColumnsDesc: 'Applies to album, artist, playlist, radio, offline, and other card-based library views. Lower values use larger tiles and are usually easier on the CPU.',
  libraryIndexTitle: 'Local library index (preview)',
  libraryIndexDesc: 'Keep a local copy of each server\'s track database so browsing and search stay fast and work offline. Initial sync runs for every configured server; offline servers are retried automatically.',
  libraryIndexDeltaHint: 'Background delta sync checks bound servers every 30 seconds and runs when due — typically every 5–45 minutes depending on library size and load.',
  libraryIndexEnable: 'Enable local library index',
  libraryIndexEnableAllDesc: 'Index and sync all configured servers in the background.',
  libraryIndexNoServer: 'Add a server first.',
  libraryIndexServerListTitle: 'Indexed servers',
  libraryIndexAllExcluded: 'All servers are excluded from sync. Re-enable the index or add a server.',
  libraryIndexServerOffline: 'Server offline — sync deferred',
  libraryIndexServerSyncing: 'Syncing…',
  libraryIndexFullResync: 'Full resync',
  libraryIndexDeltaSync: 'Delta sync',
  libraryIndexExcludeServer: 'Exclude from sync',
  libraryIndexExcludingServer: 'Excluding…',
  libraryIndexExcludedTitle: 'Excluded from sync',
  libraryIndexIncludeServer: 'Include again',
  libraryIndexIncludingServer: 'Including…',
  libraryIndexStatus: 'Status',
  libraryIndexStatusIdle: 'Idle',
  libraryIndexStatusProbing: 'Checking server…',
  libraryIndexStatusInitial: 'Initial sync…',
  libraryIndexStatusReady: 'Ready ({{count}} tracks)',
  libraryIndexStatusError: 'Error — see logs',
  libraryIndexProgressIngest: 'Indexed {{count}} tracks…',
  libraryIndexProgressVerify: 'Verified {{checked}} ({{deleted}} removed)',
  libraryIndexSyncNow: 'Sync now',
  libraryIndexVerify: 'Verify library integrity',
  libraryIndexCancel: 'Cancel',
  libraryIndexAutoReconcile: 'Auto-reconcile on count drop',
  libraryIndexAutoReconcileDesc: 'Automatically check for removed tracks when the server reports fewer than expected.',
  libraryIndexSyncError: 'Library sync failed: {{error}}',
  libraryIndexBindError: 'Could not enable index: {{error}}',
  analyticsStrategyTitle: 'Analytics strategies',
  analyticsStrategyDesc: 'Choose the analysis style for the library.',
  analyticsStrategyLabel: 'Strategy',
  analyticsStrategyLazy: 'Lazy',
  analyticsStrategyLazyDesc: 'Analyze only when tracks play or enter the hot/offline cache — minimal CPU and network use.',
  analyticsStrategyAdvanced: 'Aggressive',
  analyticsStrategyAdvancedDesc: 'More aggressive background scan. Once finished, you get BPM for every track plus instant loudness + waveform loads.',
  analyticsStrategyPriorityTitle: 'Analysis priority (always enforced)',
  analyticsStrategyPriorityHigh: '1 — Currently playing: download + analyze first (playback bytes, loudness backfill, or HTTP when needed).',
  analyticsStrategyPriorityMiddle: '2 — Up next: the next ~5 queue tracks and hot-cache neighbours — analyze from cached/downloaded bytes when possible; HTTP backfill only on miss.',
  analyticsStrategyPriorityLow: '3 — Library batch (Aggressive only): automatic background queue at the tail; refilled by watermark (~3× workers) without waiting for an empty queue.',
  analyticsStrategyServerLabel: 'Server',
  analyticsStrategyProgressLabel: 'Analysis progress:',
  analyticsStrategyProgressValue: '{{percent}}% ({{done}}/{{total}})',
  analyticsStrategyActionsLabel: 'Actions',
  analyticsStrategyParallelismLabel: 'Parallel workers',
  analyticsStrategyParallelismValue: '{{n}} threads',
  analyticsStrategyParallelismDesc: 'How many tracks to download and analyze at once (HTTP + CPU). Higher values speed up library catch-up but use more network and CPU.',
  analyticsStrategyAdvancedWarning: 'Aggressive uses more CPU and network bandwidth while the library batch runs in the background.',
  analyticsStrategyServerRemoved: 'Removed server',
  analyticsStrategyClearAction: 'Clear analysis',
  analyticsStrategyClearTitle: 'Clear analysis?',
  analyticsStrategyClearDesc: 'Clearing analysis for {{server}} removes cached waveforms and loudness. Re-adding this server later may require long re-indexing.',
  analyticsStrategyClearCancel: 'Cancel',
  analyticsStrategyClearConfirm: 'Clear analysis',
  analyticsStrategyClearSuccess: 'Analysis cleared for the removed server.',
  analyticsStrategyClearError: 'Failed to clear analysis for the removed server.',
  analyticsStrategyProgressEmptyAfterFailed: '100% (0/0, blocked by failed tracks)',
  analyticsFailedTracksOpenTitle: 'Failed tracks: {{count}}',
  analyticsFailedTracksTitle: 'Failed analysis tracks — {{server}}',
  analyticsFailedTracksDesc: 'These tracks repeatedly failed decode/enrichment and are excluded from automatic background analysis.',
  analyticsFailedTracksLoading: 'Loading failed track list…',
  analyticsFailedTracksEmpty: 'No failed tracks for this server.',
  analyticsFailedTracksClose: 'Close',
  analyticsFailedTracksExport: 'Export list',
  analyticsFailedTracksExportSuccess: 'Failed track list exported ({{count}}).',
  analyticsFailedTracksExportError: 'Could not export failed track list.',
  analyticsFailedTracksRescan: 'Rescan failed tracks',
  analyticsFailedTracksRescanSuccess: 'Rescan scheduled for {{count}} failed tracks.',
  analyticsFailedTracksRescanError: 'Could not rescan failed tracks.',
  analyticsFailedTracksLoadError: 'Could not load failed tracks.',
  randomMixTitle: 'Random Mix Blacklist',
  luckyMixMenuTitle: 'Show Lucky Mix in menu',
  luckyMixMenuDesc: 'Enables Lucky Mix in Build a Mix and as a separate menu item when split navigation is on. Visible only when AudioMuse is enabled on the active server.',
  randomMixBlacklistTitle: 'Custom Filter Keywords',
  randomMixBlacklistDesc: 'Songs are excluded when any keyword matches their genre, title, album, or artist (active when the checkbox above is on).',
  randomMixBlacklistPlaceholder: 'Add keyword…',
  randomMixBlacklistAdd: 'Add',
  randomMixBlacklistEmpty: 'No custom keywords added yet.',
  randomMixHardcodedTitle: 'Built-in keywords (active when checkbox is on)',
  tabAudio: 'Audio',
  tabStorage: 'Offline & Cache',
  tabAppearance: 'Appearance',
  tabThemes: 'Themes',
  themesYourThemesTitle: 'Your Themes',
  themesCvdTooltip: 'Colour-blind safe — deuteranopia, protanopia, tritanopia',
  themeAnimationWarning: 'This theme uses animations that may raise CPU usage on your setup (Nvidia/Linux or compositing off).',
  themeStoreTitle: 'Theme Store',
  themeStoreSubmitText: 'Made your own theme? Share it with the community — more info in the themes repository.',
  themeStoreSubmitLink: 'Open the themes repository',
  themeStoreNetworkNotice: 'The Theme Store loads its catalogue and previews from GitHub. No personal data is sent.',
  themeStoreStatsNotice: 'Last-changed dates refresh once a day (around 04:17 UTC).',
  themeStoreSearchPlaceholder: 'Search themes…',
  themeStoreFilterMode: 'Filter by mode',
  themeStoreModeAll: 'All',
  themeStoreModeDark: 'Dark',
  themeStoreModeLight: 'Light',
  themeStoreRefresh: 'Refresh',
  themeStoreLoading: 'Loading themes…',
  themeStoreError: 'Could not load the theme store. Check your connection.',
  themeStoreRetry: 'Retry',
  themeStoreOfflineTitle: 'The Theme Store is offline',
  themeStoreEmpty: 'No themes match your filters.',
  themeStoreActive: 'Active',
  themeStoreEnlarge: 'Enlarge preview',
  themeStoreSortNewest: 'Newest',
  themeStoreSortName: 'Alphabetical',
  themeStoreAnimAll: 'All',
  themeStoreAnimAnimated: 'Animated',
  themeStoreAnimStatic: 'Static',
  themeStoreByAuthor: 'by {{author}}',
  themeStoreLastChanged: 'Last changed',
  themeMigrationNoticeTitle: 'Theme moved to the Store',
  themeMigrationNoticeBody: '{{themes}} is no longer bundled with the app. You can reinstall it from the Theme Store (Settings → Themes), or pick another theme.',
  themeMigrationNoticeOpen: 'Open Theme Store',
  themeStoreOffline: 'Showing the last cached catalogue — you appear to be offline.',
  themeStoreInstall: 'Install',
  themeStoreInstalling: 'Installing…',
  themeStoreApply: 'Apply',
  themeStoreUpdate: 'Update',
  themeStoreUpdating: 'Updating…',
  themeStoreUninstall: 'Uninstall',
  themeStoreInstallFailed: 'Install failed',
  themeStorePagePrev: 'Previous page',
  themeStorePageNext: 'Next page',
  themeStorePageStatus: 'Page {{page}} of {{total}}',
  themeImportTitle: 'Import a theme',
  themeImportButton: 'Import theme…',
  themeImporting: 'Importing…',
  themeImportHint: 'Load a theme packaged as a .zip (manifest.json + theme.css).',
  themeImportSuccess: '"{{name}}" imported.',
  themeImportErrorTitle: 'This theme could not be imported',
  themeImportErrorBody: "It doesn't match the Psysonic theme format. It may have been made for a different version, or the file is incomplete — check that you picked the right .zip, or ask the theme's author.",
  themeImportErrorDetails: 'Technical details',
  themeImportConfirmTitle: 'Install theme?',
  themeImportConfirmBody: 'Install "{{name}}" by {{author}}?',
  themeImportConfirmRisk: "Imported themes aren't reviewed — only install themes you trust.",
  tabLibrary: 'Library',
  tabServers: 'Servers',
  tabLyrics: 'Lyrics',
  tabPersonalisation: 'Personalisation',
  tabIntegrations: 'Integrations',
  inputKeybindingsTitle: 'Keyboard shortcuts',
  aboutContributorsCount_one: '{{count}} contribution',
  aboutContributorsCount_other: '{{count}} contributions',
  searchPlaceholder: 'Search settings…',
  searchNoResults: 'No settings match your search.',
  integrationsPrivacyTitle: 'Privacy notice',
  integrationsPrivacyBody: 'All integrations on this tab are <strong>opt-in</strong> and send data to external services or to your Navidrome server when enabled. Last.fm receives your listening history, Discord shows the currently playing track in your profile, Bandsintown is queried per artist to fetch tour dates, and the Now-Playing share publishes your current track to other users of your Navidrome server. If you don\'t want any of this, simply leave the corresponding section disabled.',
  homeCustomizerTitle: 'Mainstage',
  queueModeTitle: 'Queue Display Mode',
  queueModeQueueSub: 'Show only upcoming tracks. The current track stays in the header and leaves the list once it has played.',
  queueModePlaylistSub: 'Keep the whole queue in the list with the current track highlighted at the top; played tracks stay.',
  queueModeTimelineSub: 'Center the current track, with played history above and upcoming tracks (in shuffle order) below.',
  queueToolbarTitle: 'Queue Toolbar',
  queueToolbarReset: 'Reset to default',
  queueToolbarSeparator: 'Separator',
  sidebarTitle: 'Sidebar',
  sidebarReset: 'Reset to default',
  artistLayoutTitle: 'Artist page sections',
  artistLayoutDesc: 'Drag to reorder, toggle to hide individual sections of the artist page. Sections without data are skipped automatically.',
  artistLayoutReset: 'Reset to default',
  artistLayoutBio: 'Artist biography',
  artistLayoutTopTracks: 'Top tracks',
  artistLayoutSimilar: 'Similar artists',
  artistLayoutAlbums: 'Albums',
  artistLayoutFeatured: 'Also featured on',
  playlistLayoutTitle: 'Playlist page layout',
  playlistLayoutDesc: 'Show or hide individual elements on the playlist page.',
  playlistLayoutReset: 'Reset to default',
  playerBarTitle: 'Player bar',
  playerBarReset: 'Reset to default',
  playerBarStarRating: 'Star rating',
  playerBarFavorite: 'Favorite (heart)',
  playerBarLastfmLove: 'Love button',
  playerBarPlaybackRate: 'Playback speed',
  playerBarEqualizer: 'Equalizer',
  playerBarMiniPlayer: 'Mini player',
  playbackRateTitle: 'Playback speed',
  playbackRateEnabled: 'Enable playback speed',
  playbackRateEnabledDesc: 'Change speed globally for all tracks. Not applied to radio or previews.',
  playbackRateStrategy: 'Strategy',
  playbackRateStrategySpeed: 'Speed',
  playbackRateStrategyVarispeed: 'Varispeed',
  playbackRateStrategyVarispeedSemitones: 'Semitones',
  playbackRateStrategyPreserve: 'Pitch shift',
  playbackRateStrategySpeedTip: 'Changes tempo; pitch is corrected automatically.',
  playbackRateStrategyVarispeedTip: 'Speed and pitch move together, like tape. Pitch follows speed: 12 × log2(speed).',
  playbackRateStrategyVarispeedSemitonesTip: 'Varispeed dialled directly in semitones. Speed = 2^(st/12).',
  playbackRateStrategyPreserveTip: 'Adjustable tempo plus a manual pitch offset (±12 st).',
  playbackRateSpeed: 'Speed',
  playbackRatePitch: 'Pitch',
  playbackRateDerivedPitch: 'Pitch shift from speed: {{value}}',
  playbackRateDerivedSpeed: 'Speed from semitones: {{value}}',
  playbackRateFineStep: 'Fine adjustment',
  playbackRateFineStepDesc: 'Smaller slider steps: 0.01× for speed and 0.01 st for pitch.',
  playbackRateAutoPitch: 'Pitch is corrected automatically.',
  playbackRateHint: 'Speed keeps pitch natural. Varispeed changes pitch with speed. Varispeed (semitones) sets that pitch change directly in semitones. Pitch shift adds a manual offset. Uses more CPU than varispeed. Not for radio, previews, or Orbit.',
  playbackRateNeutral: 'At 1.0× with no pitch offset, playback is normal.',
  playbackRateOrbitPaused: 'Not applied during Orbit sessions — playback stays at 1.0× for sync.',
  playbackRateOrbitPausedShort: 'Orbit: 1.0× for sync.',
  advancedMode: 'Advanced',
  advancedModeTooltip: 'Show advanced options across all Settings tabs. Community contributions that do not necessarily reflect the design philosophy of the Psysonic maintainers.',
  advancedBadge: 'Advanced',
  sidebarDrag: 'Drag to reorder',
  sidebarFixed: 'Always visible',
  nowPlayingTopTitle: 'Now Playing at top',
  nowPlayingTopDesc: 'Pin the "Now Playing" entry to the top of the sidebar instead of the bottom.',
  randomNavSplitTitle: 'Split Mix navigation',
  randomNavSplitDesc: 'Show "Random Mix", "Random Albums", and "Lucky Mix" as separate sidebar entries instead of the "Build a Mix" hub.',
  tabInput: 'Input',
  tabUsers: 'Users',
  tabSystem: 'System',
  loggingTitle: 'Logging',
  loggingModeDesc: 'Controls backend log verbosity in the terminal.',
  loggingModeOff: 'Off',
  loggingModeNormal: 'Normal',
  loggingModeDebug: 'Debug',
  loggingExport: 'Export logs',
  loggingExportSuccess: 'Logs exported ({{count}} lines).',
  loggingExportError: 'Could not export logs.',
  ratingsSectionTitle: 'Ratings',
  ratingsSkipStarTitle: 'Skip for 1 star',
  ratingsSkipStarDesc:
    'After several skips in a row, set the track to 1★. Only for tracks not yet rated.',
  ratingsSkipStarThresholdLabel: 'Skips',
  ratingsMixFilterTitle: 'Filter by rating',
  ratingsMixFilterDesc:
    'Filter low-rated items in {{mix}} and {{albums}}. Click the selected star again to turn off the threshold.',
  ratingsMixMinSong: 'Songs',
  ratingsMixMinAlbum: 'Albums',
  ratingsMixMinArtist: 'Artists',
  ratingsMixMinThresholdAria: 'Minimum stars: {{label}}',
  backupTitle: 'Backup & Restore',
  backupExport: 'Export settings',
  backupExportDesc: 'Saves all settings, server profiles, Last.fm config, theme, EQ and keybindings to a .psybkp file. Passwords are stored in plaintext — keep the file secure.',
  backupImport: 'Import settings',
  backupImportDesc: 'Restores settings from a .psybkp file. The app will reload after import.',
  backupImportConfirm: 'This will overwrite all current settings. Continue?',
  backupImportAny: 'Import backup',
  backupImportAnyConfirm: 'Import selected backup file and apply its contents (settings, library databases, or full). Continue?',
  backupSuccess: 'Backup saved',
  backupImportSuccess: 'Settings restored — reloading…',
  backupImportError: 'Invalid or corrupted backup file.',
  backupModeFull: 'Full',
  backupModeLibrary: 'Library databases',
  backupModeConfig: 'Config',
  backupFullDesc: 'Archives settings and library databases into one backup file.',
  backupFullExport: 'Export full backup',
  backupFullImport: 'Import full backup',
  backupFullImportConfirm: 'This will overwrite settings, replace current library databases, and move them to .bak. Continue?',
  backupFullExportSuccess: 'Full backup exported.',
  backupFullImportSuccess: 'Full backup imported — reloading…',
  backupFullImportError: 'Could not import full backup.',
  backupLibraryExport: 'Export databases',
  backupLibraryExportDesc: 'Creates a compressed archive with clean SQLite snapshots of library databases.',
  backupLibraryImport: 'Import databases',
  backupLibraryImportDesc: 'Restores library databases from an archive file. Current databases are moved to .bak before switch.',
  backupLibraryImportConfirm: 'This will replace current library databases and move them to .bak. Continue?',
  backupLibraryExportSuccess: 'Databases backup exported.',
  backupLibraryImportSuccess: 'Databases backup imported.',
  backupLibraryImportError: 'Could not import databases backup.',
  backupOverlayExportTitle: 'Creating backup…',
  backupOverlayImportTitle: 'Restoring backup…',
  backupOverlayHint: 'You can keep the window open while we process files. Input is temporarily locked.',
  shortcutsReset: 'Reset to defaults',
  shortcutListening: 'Press a key…',
  shortcutUnbound: '—',
  globalShortcutsTitle: 'Global Shortcuts',
  globalShortcutsNote: 'Work system-wide even when Psysonic is in the background. Requires Ctrl, Alt, or Super as a modifier.',
  shortcutClear: 'Clear',
  shortcutPlayPause: 'Play / Pause',
  shortcutNext: 'Next track',
  shortcutPrev: 'Previous track',
  shortcutVolumeUp: 'Volume up',
  shortcutVolumeDown: 'Volume down',
  shortcutSeekForward: 'Seek forward 10s',
  shortcutSeekBackward: 'Seek backward 10s',
  shortcutToggleQueue: 'Toggle queue',
  shortcutOpenFolderBrowser: 'Open {{folderBrowser}}',
  shortcutFullscreenPlayer: 'Fullscreen player',
  shortcutNativeFullscreen: 'Native fullscreen',
  shortcutOpenMiniPlayer: 'Open mini player',
  shortcutStartSearch: 'Start a search',
  shortcutStartAdvancedSearch: 'Start an advanced search',
  shortcutToggleSidebar: 'Toggle Sidebar',
  shortcutMuteSound: 'Mute sound',
  shortcutToggleEqualizer: 'Open / Toggle Equalizer',
  shortcutToggleRepeat: 'Toggle Repeat',
  shortcutOpenNowPlaying: 'Open "Now Playing"',
  shortcutShowLyrics: 'Show Lyrics',
  shortcutFavoriteCurrentTrack: 'Add current track to favorites',
  shortcutOpenHelp: 'Help',
  playbackTitle: 'Playback',
  replayGain: 'Replay Gain',
  replayGainDesc: 'Normalize track volume using ReplayGain metadata',
  replayGainMode: 'Mode',
  replayGainAuto: 'Auto',
  replayGainAutoDesc: 'Picks album gain when neighbouring queue tracks are from the same album, otherwise track gain.',
  replayGainTrack: 'Track',
  replayGainAlbum: 'Album',
  replayGainPreGain: 'Pre-Gain (tagged files)',
  replayGainPreGainDesc: 'Universal boost added on top of every ReplayGain calculation. Use to compensate if your library feels too quiet overall.',
  replayGainFallback: 'Fallback (untagged / radio)',
  replayGainFallbackDesc: 'Applied to tracks (and radio streams) that have no ReplayGain tags at all, so untagged content does not pop louder than the rest.',
  normalization: 'Normalization',
  normalizationDesc: 'Even out perceived loudness across tracks, albums and radio.',
  normalizationOff: 'Off',
  normalizationReplayGain: 'ReplayGain',
  normalizationLufs: 'LUFS',
  loudnessTargetLufs: 'Target LUFS',
  loudnessTargetLufsDesc: 'Reference loudness all tracks are matched to. Lower numbers = louder output. Streaming services typically sit around -14 LUFS.',
  loudnessPreAnalysisAttenuation: 'Pre-analysis attenuation',
  loudnessPreAnalysisAttenuationDesc:
    'Extra quieting until loudness for this track is saved. Streaming then uses rough guesses, not a full measurement. 0 dB = off; lower = quieter. The number on the right is the effective dB for your current target.',
  loudnessPreAnalysisAttenuationRef: 'Effective {{eff}} dB with target {{tgt}} LUFS.',
  loudnessPreAnalysisAttenuationReset: 'Reset to default',
  loudnessFirstPlayNote:
    'First play of a brand-new track may briefly drift in volume while it is being measured. The next play uses the cached measurement and is rock-solid. Upcoming queue tracks are usually pre-analysed during the previous song, so this rarely happens in practice.',
  crossfade: 'Crossfade',
  crossfadeSecs: '{{n}} s',
  autoDj: 'AutoDJ',
  autoDjDesc: 'No fixed duration — AutoDJ follows the actual audio, blending real fade-outs and intros instead of a set number of seconds. For reliable results, enable the Hot playback cache.',
  autodjSmoothSkip: 'Smooth skip',
  autodjSmoothSkipDesc: 'When you skip to the next or previous track while playing, blend into it with the same AutoDJ rules (overlap length, intro trim) from your current position instead of an abrupt cut. Works best when the next track is already buffered.',
  gapless: 'Gapless Playback',
  transitionsTitle: 'Track transitions',
  transitionsDesc: 'How consecutive tracks blend together. Only one mode can be active at a time.',
  transitionOff: 'Off',
  queueBehaviourTitle: 'Queue behaviour',
  preservePlayNextOrder: 'Preserve "Play Next" order',
  preservePlayNextOrderDesc: 'Newly added Play Next items queue up behind earlier ones instead of jumping in front.',
  trackPreviewsTitle: 'Track Previews',
  trackPreviewsToggle: 'Enable track previews',
  trackPreviewsDesc: 'Show inline Play and Preview buttons in tracklists for a quick mid-song sample.',
  trackPreviewStart: 'Start position',
  trackPreviewStartDesc: 'How far into the track the preview starts (% of track length).',
  trackPreviewDuration: 'Duration',
  trackPreviewDurationDesc: 'How long each preview plays before it stops.',
  trackPreviewDurationSecs: '{{n}} s',
  trackPreviewLocationsTitle: 'Where previews appear',
  trackPreviewLocationsDesc: 'Pick which lists show inline preview buttons.',
  trackPreviewLocation_suggestions: 'In playlist suggestions',
  trackPreviewLocation_albums: 'In album tracklists',
  trackPreviewLocation_playlists: 'In playlists',
  trackPreviewLocation_favorites: 'In favorites',
  trackPreviewLocation_artist: 'In artist top tracks',
  trackPreviewLocation_randomMix: 'In Random Mix',
  nextTrackBufferingTitle: 'Buffering',
  infiniteQueue: 'Infinite Queue',
  infiniteQueueDesc: 'Automatically append random tracks when the queue runs out',
  experimental: 'Experimental',
  sidebarLyricsStyle: 'Lyrics scroll style',
  sidebarLyricsStyleClassic: 'Classic',
  sidebarLyricsStyleClassicDesc: 'Scroll active line to center.',
  sidebarLyricsStyleApple: 'Apple Music-like',
  sidebarLyricsStyleAppleDesc: 'Active line anchors near the top with smooth spring transitions.',
  seekbarStyle: 'Seekbar Style',
  seekbarStyleDesc: 'Choose the look of the player seek bar',
  seekbarTruewave: 'Truewave',
  seekbarPseudowave: 'Pseudowave',
  seekbarLinedot: 'Line & Dot',
  seekbarBar: 'Bar',
  seekbarThick: 'Thick Bar',
  seekbarSegmented: 'Segmented',
  seekbarNeon: 'Neon Glow',
  seekbarPulsewave: 'Pulse Wave',
  seekbarParticletrail: 'Particle Trail',
  seekbarLiquidfill: 'Liquid Fill',
  seekbarRetrotape: 'Retro Tape',
  themeSchedulerTitle: 'Auto-Switch Theme',
  themeSchedulerEnable: 'Enable Theme Scheduler',
  themeSchedulerEnableSub: 'Automatically switch between two themes based on the time of day',
  themeSchedulerDayTheme: 'Day Theme',
  themeSchedulerDayStart: 'Day Starts At',
  themeSchedulerNightTheme: 'Night Theme',
  themeSchedulerNightStart: 'Night Starts At',
  themeSchedulerActiveHint: 'Theme Scheduler is active - theme changes are managed automatically.',
  visualOptionsTitle: 'Visual Options',
  coverArtBackground: 'Cover Art Background',
  coverArtBackgroundSub: 'Show blurred cover art as background in album/playlist headers',
  playlistCoverPhoto: 'Playlist Cover Photo',
  playlistCoverPhotoSub: 'Show cover photo grid in playlist detail view',
  showBitrate: 'Show Bitrate',
  showBitrateSub: 'Display audio bitrate in track listings',
  floatingPlayerBar: 'Floating Player Bar',
  floatingPlayerBarSub: 'Keep the player bar floating above content',
  uiScaleTitle: 'Interface Scale',
  uiScaleLabel: 'Zoom',
};
