Compare commits

..

23 Commits

Author SHA1 Message Date
jeffvli a137de612a fix crossfade settings to update player store 2025-11-06 20:30:33 -08:00
jeffvli ae9a8e6d08 move mpv initialization into player implementation 2025-11-06 20:24:01 -08:00
jeffvli 9c3053608d re-add conditional render to ReactPlayer components which causes crossfade error 2025-11-06 20:23:22 -08:00
jeffvli d6ea97fa2a move remote init into hook 2025-11-06 18:59:42 -08:00
jeffvli 578b00fe3d lint 2025-11-06 18:42:43 -08:00
jeffvli f43f696f54 fix ipc in remote hook 2025-11-06 18:42:43 -08:00
jeffvli 4a81d7b249 add useRemote to playerbar 2025-11-06 18:42:43 -08:00
jeffvli 88fbc22923 add new player remote hook 2025-11-06 18:42:43 -08:00
jeffvli daef3b31fe add subscribers for player repeat and shuffle 2025-11-06 18:42:43 -08:00
jeffvli 7142017c26 support offset for player skip 2025-11-06 18:42:43 -08:00
jeffvli f30a466fb2 re-implement mpv with new player 2025-11-06 18:42:43 -08:00
jeffvli f2e3e7a74e add volume wheel 2025-11-06 18:42:43 -08:00
jeffvli 83efd6e8c5 refactor windowbar to prevent unnecessary renders 2025-11-06 18:42:43 -08:00
jeffvli 515496ab85 re-implement playerbar controls 2025-11-06 18:42:43 -08:00
jeffvli 16b99ef597 add usePlayer hook 2025-11-06 18:39:09 -08:00
jeffvli b607c57f59 rename internal types in domain models 2025-11-06 18:39:09 -08:00
jeffvli 9f0a8f2bae begin implementing player context 2025-11-06 18:39:09 -08:00
jeffvli 0e384a6302 reorganize 2025-11-06 18:39:09 -08:00
jeffvli 0c7cec9f4f fix table row styles listener 2025-11-06 18:39:09 -08:00
jeffvli f30a706eef rework player events to use properties object instead of flat value 2025-11-06 18:39:09 -08:00
jeffvli a980a8de0b add new web player implementation 2025-11-06 18:39:09 -08:00
jeffvli 9abda23a4a temporarily remove old player implementations to prevent broken app 2025-11-06 18:39:09 -08:00
jeffvli 4e3a3742a5 rework player store and add global player context 2025-11-06 18:38:32 -08:00
1044 changed files with 34829 additions and 112021 deletions
-1
View File
@@ -5,7 +5,6 @@
*.jpeg binary
*.ico binary
*.icns binary
*.webp binary
*.eot binary
*.otf binary
*.ttf binary
-189
View File
@@ -1,189 +0,0 @@
# Alpha builds published to Cloudflare R2 with date versioning (e.g. 1.0.0-alpha-20260205).
# Required repo secrets: R2_ACCESS_KEY_ID, R2_SECRET_ACCESS_KEY (from R2 API token in Cloudflare dashboard).
name: Publish Alpha
on:
workflow_dispatch:
inputs:
version:
description: 'Semantic version number (e.g., 1.0.0) - alpha suffix will be added automatically'
required: false
type: string
schedule:
# Run at 3:00 AM PST daily (11:00 UTC; PST = UTC-8)
- cron: '0 11 * * *'
jobs:
check-new-commits:
runs-on: ubuntu-latest
outputs:
has_new_commits: ${{ steps.manual.outputs.has_new_commits || steps.check.outputs['has-new-commits'] }}
steps:
- name: Set has new commits (manual trigger)
id: manual
if: github.event_name == 'workflow_dispatch'
run: echo "has_new_commits=true" >> "$GITHUB_OUTPUT"
- name: Check for new commits (24 hr interval)
id: check
if: github.event_name != 'workflow_dispatch'
uses: adriangl/check-new-commits-action@v1
with:
token: ${{ secrets.GITHUB_TOKEN }}
seconds: 86400
prepare:
needs: check-new-commits
if: needs.check-new-commits.outputs.has_new_commits == 'true'
runs-on: ubuntu-latest
outputs:
version: ${{ steps.version.outputs.version }}
steps:
- name: Checkout git repo
uses: actions/checkout@v6
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
with:
version: 10
- name: Install dependencies
run: pnpm install
- name: Set date-based alpha version
id: version
shell: pwsh
run: |
$inputVersion = "${{ github.event.inputs.version }}"
Write-Host "Input version: $inputVersion"
if ($inputVersion -eq "" -or $inputVersion -eq "null") {
# No input version provided (scheduled run or manual without input), auto-increment patch version
Write-Host "No version provided, auto-incrementing patch version..."
$currentVersion = (Get-Content package.json | ConvertFrom-Json).version
Write-Host "Current version: $currentVersion"
$cleanVersion = $currentVersion -replace '-.*$', ''
$versionParts = $cleanVersion.Split('.')
if ($versionParts.Length -ne 3) {
Write-Error "Current version format is invalid: $cleanVersion"
exit 1
}
$major = [int]$versionParts[0]
$minor = [int]$versionParts[1]
$patch = [int]$versionParts[2]
$newPatch = $patch + 1
$inputVersion = "$major.$minor.$newPatch"
Write-Host "Auto-generated version: $inputVersion"
} else {
# Validate semantic version format (major.minor.patch)
$versionPattern = '^\d+\.\d+\.\d+$'
if ($inputVersion -notmatch $versionPattern) {
Write-Error "Invalid version format. Expected semantic version (e.g., 1.0.0), got: $inputVersion"
exit 1
}
}
# Date in YYYYMMDD (PST / America/Los_Angeles)
$pst = [TimeZoneInfo]::FindSystemTimeZoneById('America/Los_Angeles')
$dateInPst = [TimeZoneInfo]::ConvertTimeFromUtc([DateTime]::UtcNow, $pst)
$dateStr = $dateInPst.ToString("yyyyMMdd")
$alphaVersion = "$inputVersion-alpha-$dateStr"
Write-Host "Alpha version: $alphaVersion"
# Update package.json
$packageJson = Get-Content package.json | ConvertFrom-Json
$packageJson.version = $alphaVersion
$packageJson | ConvertTo-Json -Depth 10 | Set-Content package.json
echo "version=$alphaVersion" >> $env:GITHUB_OUTPUT
cleanup:
needs: prepare
runs-on: ubuntu-latest
env:
AWS_ACCESS_KEY_ID: ${{ secrets.R2_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.R2_SECRET_ACCESS_KEY }}
R2_ENDPOINT_URL: ${{ secrets.R2_ENDPOINT_URL }}
steps:
- name: Delete all objects in R2 bucket
run: |
aws s3 rm s3://feishin-nightly --recursive --endpoint-url $R2_ENDPOINT_URL
publish:
needs: [prepare, cleanup]
runs-on: ${{ matrix.os }}
env:
AWS_ACCESS_KEY_ID: ${{ secrets.R2_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.R2_SECRET_ACCESS_KEY }}
strategy:
matrix:
os: [windows-latest, macos-latest, ubuntu-latest]
steps:
- name: Checkout git repo
uses: actions/checkout@v6
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
with:
version: 10
- name: Install dependencies
run: pnpm install
- name: Set version from prepare job
shell: pwsh
run: |
$version = "${{ needs.prepare.outputs.version }}"
Write-Host "Setting version: $version"
$packageJson = Get-Content package.json | ConvertFrom-Json
$packageJson.version = $version
$packageJson | ConvertTo-Json -Depth 10 | Set-Content package.json
- name: Build and Publish to R2 (Windows)
if: matrix.os == 'windows-latest'
uses: nick-invision/retry@v3.0.2
with:
timeout_minutes: 30
max_attempts: 3
retry_on: error
command: |
pnpm run publish:win:alpha
on_retry_command: pnpm cache delete
- name: Build and Publish to R2 (macOS)
if: matrix.os == 'macos-latest'
uses: nick-invision/retry@v3.0.2
with:
timeout_minutes: 30
max_attempts: 3
retry_on: error
command: |
pnpm run publish:mac:alpha
on_retry_command: pnpm cache delete
- name: Build and Publish to R2 (Linux)
if: matrix.os == 'ubuntu-latest'
uses: nick-invision/retry@v3.0.2
with:
timeout_minutes: 30
max_attempts: 3
retry_on: error
command: |
pnpm run publish:linux:alpha
on_retry_command: pnpm cache delete
- name: Build and Publish to R2 (Linux ARM64)
if: matrix.os == 'ubuntu-latest'
uses: nick-invision/retry@v3.0.2
with:
timeout_minutes: 30
max_attempts: 3
retry_on: error
command: |
pnpm run publish:linux-arm64:alpha
on_retry_command: pnpm cache delete
+12 -12
View File
@@ -15,12 +15,12 @@ jobs:
version: ${{ steps.version.outputs.version }}
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
@@ -119,12 +119,12 @@ jobs:
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
@@ -146,7 +146,7 @@ jobs:
if: matrix.os == 'windows-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -159,7 +159,7 @@ jobs:
if: matrix.os == 'macos-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -172,7 +172,7 @@ jobs:
if: matrix.os == 'ubuntu-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -185,7 +185,7 @@ jobs:
if: matrix.os == 'ubuntu-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -199,7 +199,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Edit release with commits and title
shell: pwsh
@@ -346,7 +346,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Delete existing prereleases
shell: pwsh
+1 -1
View File
@@ -20,7 +20,7 @@ jobs:
packages: write
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Log in to the Container registry
uses: docker/login-action@65b78e6e13532edd9afa3aa52ac7964289d1a9c1
with:
+1 -1
View File
@@ -15,7 +15,7 @@ jobs:
packages: write
steps:
- name: Checkout repository
uses: actions/checkout@v6
uses: actions/checkout@v4
- name: Log in to the Container registry
uses: docker/login-action@65b78e6e13532edd9afa3aa52ac7964289d1a9c1
with:
+5 -5
View File
@@ -12,12 +12,12 @@ jobs:
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
@@ -25,7 +25,7 @@ jobs:
- name: Build and Publish releases
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -37,7 +37,7 @@ jobs:
- name: Build and Publish releases (arm64)
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
+4 -4
View File
@@ -12,12 +12,12 @@ jobs:
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
@@ -25,7 +25,7 @@ jobs:
- name: Build and Publish releases
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
+9 -28
View File
@@ -1,31 +1,12 @@
name: Publish (PR)
on:
workflow_dispatch:
pull_request:
branches:
- development
paths:
- 'src/**'
- 'electron-builder*.yml'
jobs:
wait-for-lint:
if: github.event_name == 'pull_request'
runs-on: ubuntu-latest
steps:
- name: Wait for Test workflow to complete
uses: lewagon/wait-on-check-action@v1.4.1
with:
ref: ${{ github.event.pull_request.head.sha }}
check-name: 'lint'
repo-token: ${{ secrets.GITHUB_TOKEN }}
wait-interval: 10
allowed-conclusions: success
publish:
needs: wait-for-lint
if: always() && (needs.wait-for-lint.result == 'success' || needs.wait-for-lint.result == 'skipped')
runs-on: ${{ matrix.os }}
strategy:
@@ -34,19 +15,19 @@ jobs:
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v3
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
- name: Build for Windows
if: ${{ matrix.os == 'windows-latest' }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -56,7 +37,7 @@ jobs:
- name: Build for Linux
if: ${{ matrix.os == 'ubuntu-latest' }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -66,7 +47,7 @@ jobs:
- name: Build for MacOS
if: ${{ matrix.os == 'macos-latest' }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -92,21 +73,21 @@ jobs:
- name: Upload Windows Binaries
if: ${{ matrix.os == 'windows-latest' }}
uses: actions/upload-artifact@v7
uses: actions/upload-artifact@v4
with:
name: windows-binaries
path: dist/windows-binaries.zip
- name: Upload Linux Binaries
if: ${{ matrix.os == 'ubuntu-latest' }}
uses: actions/upload-artifact@v7
uses: actions/upload-artifact@v4
with:
name: linux-binaries
path: dist/linux-binaries.zip
- name: Upload MacOS Binaries
if: ${{ matrix.os == 'macos-latest' }}
uses: actions/upload-artifact@v7
uses: actions/upload-artifact@v4
with:
name: macos-binaries
path: dist/macos-binaries.zip
+4 -4
View File
@@ -12,12 +12,12 @@ jobs:
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
@@ -25,7 +25,7 @@ jobs:
- name: Build and Publish releases
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
+2 -1
View File
@@ -16,5 +16,6 @@ jobs:
- uses: vedantmgoyal9/winget-releaser@main
with:
identifier: jeffvli.Feishin
installers-regex: 'Feishin-*-win-(x64|arm64)\.exe'
installers-regex: 'Feishin-*-win-x64\.exe'
token: ${{ secrets.WINGET_ACC_TOKEN }}
+7 -7
View File
@@ -12,12 +12,12 @@ jobs:
steps:
- name: Checkout git repo
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
@@ -26,7 +26,7 @@ jobs:
if: matrix.os == 'windows-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -39,7 +39,7 @@ jobs:
if: matrix.os == 'macos-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -52,7 +52,7 @@ jobs:
if: matrix.os == 'ubuntu-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
@@ -65,7 +65,7 @@ jobs:
if: matrix.os == 'ubuntu-latest'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
uses: nick-invision/retry@v3.0.2
uses: nick-invision/retry@v2.8.2
with:
timeout_minutes: 30
max_attempts: 3
+3 -3
View File
@@ -8,12 +8,12 @@ jobs:
steps:
- name: Check out Git repository
uses: actions/checkout@v6
uses: actions/checkout@v1
- name: Install Node.js and PNPM
uses: pnpm/action-setup@v4
uses: pnpm/action-setup@v4.1.0
with:
version: 10
version: 9
- name: Install dependencies
run: pnpm install
+1
View File
@@ -1 +1,2 @@
legacy-peer-deps=true
only-built-dependencies=electron,esbuild
+4 -5
View File
@@ -14,7 +14,9 @@
".eslintignore": "ignore"
},
"eslint.validate": ["typescript", "typescriptreact"],
"eslint.workingDirectories": [{ "directory": "./", "changeProcessCWD": true }],
"eslint.workingDirectories": [
{ "directory": "./", "changeProcessCWD": true },
],
"typescript.tsserver.experimental.enableProjectDiagnostics": false,
"editor.codeActionsOnSave": {
"source.fixAll.eslint": "explicit",
@@ -48,10 +50,7 @@
"typescript.preferences.autoImportFileExcludePatterns": [
"@mantine/core",
"@mantine/modals",
"@mantine/dates",
"@mantine/hooks",
"@mantine/form",
"@radix-ui/react-context-menu"
"@mantine/dates"
],
"[typescriptreact]": { "editor.defaultFormatter": "esbenp.prettier-vscode" },
"typescript.format.insertSpaceAfterOpeningAndBeforeClosingTemplateStringBraces": true,
+5 -7
View File
@@ -1,5 +1,5 @@
# --- Builder stage
FROM node:23-alpine AS builder
FROM node:23-alpine as builder
WORKDIR /app
# Copy package.json first to cache node_modules
@@ -14,14 +14,12 @@ COPY . .
RUN pnpm run build:web
# --- Production stage
FROM nginxinc/nginx-unprivileged:alpine-slim
FROM nginx:alpine-slim
COPY --chown=nginx:nginx --from=builder /app/out/web /usr/share/nginx/html
COPY --chown=nginx:nginx ./settings.js.template /etc/nginx/templates/settings.js.template
COPY --chown=nginx:nginx ng.conf.template /etc/nginx/templates/default.conf.template
ENV SERVER_LOCK=false SERVER_NAME="" SERVER_TYPE="" SERVER_URL="" REMOTE_URL=""
ENV LEGACY_AUTHENTICATION="" ANALYTICS_DISABLED="" PUBLIC_PATH="/"
COPY ./settings.js.template /etc/nginx/templates/settings.js.template
COPY ng.conf.template /etc/nginx/templates/default.conf.template
ENV PUBLIC_PATH="/"
EXPOSE 9180
CMD ["nginx", "-g", "daemon off;"]
+12 -21
View File
@@ -43,7 +43,7 @@ Rewrite of [Sonixd](https://github.com/jeffvli/sonixd).
## Screenshots
<a href="./media/preview_full_screen_player.png"><img src="./media/preview_full_screen_player.png" width="49.5%"/></a> <a href="./media/preview_album_artist_detail.png"><img src="./media/preview_album_artist_detail.png" width="49.5%"/></a> <a href="./media/preview_album_detail.png"><img src="./media/preview_album_detail.png" width="49.5%"/></a> <a href="./media/preview_smart_playlist.png"><img src="./media/preview_smart_playlist.png" width="49.5%"/></a>
<a href="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_full_screen_player.png"><img src="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_full_screen_player.png" width="49.5%"/></a> <a href="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_album_artist_detail.png"><img src="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_album_artist_detail.png" width="49.5%"/></a> <a href="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_album_detail.png"><img src="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_album_detail.png" width="49.5%"/></a> <a href="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_smart_playlist.png"><img src="https://raw.githubusercontent.com/jeffvli/feishin/development/media/preview_smart_playlist.png" width="49.5%"/></a>
## Getting Started
@@ -62,21 +62,18 @@ For media keys to work, you will be prompted to allow Feishin to be a Trusted Ac
We provide a small install script to download the latest `.AppImage`, make it executable, and also download the icons required by Desktop Environments. Finally, it generates a `.desktop` file to add Feishin to your Application Launcher.
Simply run the installer like this:
```sh
dir=/your/application/directory
curl 'https://raw.githubusercontent.com/jeffvli/feishin/refs/heads/development/install-feishin-appimage' | sh -s -- "$dir"
```
The script also has an option to add launch arguments to run Feishin in native Wayland mode. Note that this is experimental in Electron and therefore not officially supported. If you want to use it, run this instead:
```sh
dir=/your/application/directory
curl 'https://raw.githubusercontent.com/jeffvli/feishin/refs/heads/development/install-feishin-appimage' | sh -s -- "$dir" wayland-native
```
It also provides a simple uninstall routine, removing the downloaded files:
```sh
dir=/your/application/directory
curl 'https://raw.githubusercontent.com/jeffvli/feishin/refs/heads/development/install-feishin-appimage' | sh -s -- "$dir" remove
@@ -101,25 +98,25 @@ docker run --name feishin -p 9180:9180 feishin
#### Docker Compose
To install via Docker Compose, use the following snippet. This also works on Portainer.
To install via Docker Compose use the following snippit. This also works on Portainer.
```yaml
services:
feishin:
container_name: feishin
image: 'ghcr.io/jeffvli/feishin:latest'
restart: unless-stopped
environment:
- SERVER_NAME=jellyfin # pre-defined server name
- SERVER_NAME=jellyfin # pre defined server name
- SERVER_LOCK=true # When true AND name/type/url are set, only username/password can be toggled
- SERVER_TYPE=jellyfin # the allowed types are: jellyfin, navidrome, subsonic. These values are case insensitive
- SERVER_URL= # http://address:port or https://address:port
- REMOTE_URL= # http://address or https://address
- LEGACY_AUTHENTICATION=false # When SERVER_LOCK is true, sets the legacy (plaintext) authentication flag for Subsonic/OpenSubsonic servers
- ANALYTICS_DISABLED=true # Set to true to disable Umami analytics tracking
- SERVER_TYPE=jellyfin # navidrome also works
- SERVER_URL= # http://address:port
- PUID=1000
- PGID=1000
- UMASK=002
- TZ=America/Los_Angeles
ports:
- 9180:9180
# Alternatively, to restrict to only localhost, - 127.0.0.1:9180:8190
restart: unless-stopped
```
### Configuration
@@ -129,17 +126,11 @@ services:
2. After restarting the app, you will be prompted to select a server. Click the `Open menu` button and select `Manage servers`. Click the `Add server` button in the popup and fill out all applicable details. You will need to enter the full URL to your server, including the protocol and port if applicable (e.g. `https://navidrome.my-server.com` or `http://192.168.0.1:4533`).
- **Navidrome** - For the best experience, select "Save password" when creating the server and configure the `SessionTimeout` setting in your Navidrome config to a larger value (e.g. 72h).
- **Linux users** - The default password store uses `libsecret`. `kwallet4/5/6` are also supported, but must be explicitly set in Settings > Window > Passwords/secret store.
- **Linux users** - The default password store uses `libsecret`. `kwallet4/5/6` are also supported, but must be explicitly set in Settings > Window > Passwords/secret score.
3. _Optional_ - If you want to host Feishin on a subpath (not `/`), then pass in the following environment variable: `PUBLIC_PATH=PATH`. For example, to host on `/feishin`, pass in `PUBLIC_PATH=/feishin`.
4. _Optional_ - To hard code the server url, pass the following environment variables: `SERVER_NAME`, `SERVER_TYPE` (one of `jellyfin` or `navidrome` or `subsonic`), `SERVER_URL`. To prevent users from changing these settings, pass `SERVER_LOCK=true`. This can only be set if all three of the previous values are set. When `SERVER_LOCK=true`, you can also set `LEGACY_AUTHENTICATION=true` or `LEGACY_AUTHENTICATION=false` to configure the legacy authentication flag for the server (only applicable for Subsonic/OpenSubsonic servers).
5. _Optional_ - If your server uses a separate public-facing URL than what integrating applications use internally to communicate with your server, such as a separate Navidrome `ShareURL`, set `REMOTE_URL` to said public-facing URL.
6. _Optional_ - To disable Umami analytics tracking in the Docker/web version, set the environment variable `ANALYTICS_DISABLED=true`. When enabled, the analytics script will not be loaded and all tracking will be disabled.
7. _Optional_ - App settings (theme, language, sidebar options, etc.) can be overridden with environment variables on first run. The variables use the `FS_` prefix (e.g. `FS_GENERAL_THEME=defaultDark`, `FS_GENERAL_LANGUAGE=de`). See [the settings environment variable documentation](docs/ENV_SETTINGS.md) for the full list.
4. _Optional_ - To hard code the server url, pass the following environment variables: `SERVER_NAME`, `SERVER_TYPE` (one of `jellyfin` or `navidrome`), `SERVER_URL`. To prevent users from changing these settings, pass `SERVER_LOCK=true`. This can only be set if all three of the previous values are set.
## FAQ
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.

Before

Width:  |  Height:  |  Size: 73 KiB

After

Width:  |  Height:  |  Size: 154 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.4 KiB

After

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 651 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 14 KiB

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.5 KiB

After

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 48 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.1 KiB

After

Width:  |  Height:  |  Size: 2.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 277 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 447 B

Binary file not shown.
Binary file not shown.

Before

Width:  |  Height:  |  Size: 422 KiB

After

Width:  |  Height:  |  Size: 176 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 48 KiB

+7 -10
View File
@@ -1,16 +1,13 @@
version: '3.5'
services:
feishin:
container_name: feishin
image: "ghcr.io/jeffvli/feishin:latest"
image: ghcr.io/jeffvli/feishin:latest
restart: unless-stopped
environment:
- SERVER_NAME=jellyfin # pre-defined server name
- SERVER_LOCK=false # When true AND name/type/url are set, only username/password can be toggled
- SERVER_TYPE=jellyfin # the allowed types are: jellyfin, navidrome, subsonic. These values are case insensitive
- SERVER_URL=http://localhost:8096 # http://address:port or https://address:port
# - REMOTE_URL=http://share.localhost # Used for compatibility with external functionality, such as custom sharing URLs on Navidrome
- LEGACY_AUTHENTICATION=false # When SERVER_LOCK is true, sets the legacyauth flag for server authentication (true or false)
- ANALYTICS_DISABLED=false # Set to true to disable Umami analytics tracking
ports:
- 9180:9180
# Alternatively, to restrict to only localhost, - 127.0.0.1:9180:8190
environment:
- SERVER_NAME=jellyfin # pre defined server name
- SERVER_LOCK=true # When true AND name/type/url are set, only username/password can be toggled
- SERVER_TYPE=jellyfin # navidrome also works
- SERVER_URL= # http://address:port
-126
View File
@@ -1,126 +0,0 @@
# Environment variables for settings (web / Docker)
These variables override app settings **on first run** when no persisted settings exist. They are injected via `settings.js` (from `settings.js.template`) and only apply to the **web** build.
**Format:** All values are strings; booleans use `true`/`false`, numbers are numeric strings. Leave unset or empty to use the default.
---
## General
| Setting | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `general.accent` | `rgb(53, 116, 252)` | `FS_GENERAL_ACCENT` | CSS `rgb(r, g, b)` string (e.g. `rgb(53, 116, 252)`). Invalid values are ignored. |
| `general.albumBackground` | `false` | `FS_GENERAL_ALBUM_BACKGROUND` | `true` / `false` — Show album background image. |
| `general.albumBackgroundBlur` | `3` | `FS_GENERAL_ALBUM_BACKGROUND_BLUR` | Blur amount for album background (number). |
| `general.artistBackground` | `true` | `FS_GENERAL_ARTIST_BACKGROUND` | `true` / `false` — Show artist background image. |
| `general.artistBackgroundBlur` | `3` | `FS_GENERAL_ARTIST_BACKGROUND_BLUR` | Blur amount for artist background (number). |
| `general.blurExplicitImages` | `false` | `FS_GENERAL_BLUR_EXPLICIT_IMAGES` | `true` / `false` — Blur explicit images. |
| `general.combinedLyricsAndVisualizer` | `false` | `FS_GENERAL_COMBINED_LYRICS_AND_VISUALIZER` | `true` / `false` — Combine lyrics and visualizer panel. |
| `general.enableGridMultiSelect` | `false` | `FS_GENERAL_ENABLE_GRID_MULTI_SELECT` | `true` / `false` — Enable multi-select in grid views. |
| `general.externalLinks` | `true` | `FS_GENERAL_EXTERNAL_LINKS` | `true` / `false` — Show external links in UI. |
| `general.followCurrentSong` | `true` | `FS_GENERAL_FOLLOW_CURRENT_SONG` | `true` / `false` — Follow current song in list. |
| `general.followSystemTheme` | `false` | `FS_GENERAL_FOLLOW_SYSTEM_THEME` | `true` / `false` — Use OS light/dark preference. |
| `general.homeFeature` | `true` | `FS_GENERAL_HOME_FEATURE` | `true` / `false` — Show home featured carousel. |
| `general.homeFeatureStyle` | `single` | `FS_GENERAL_HOME_FEATURE_STYLE` | `multiple` / `single` — Home featured carousel style. |
| `general.language` | `en` | `FS_GENERAL_LANGUAGE` | UI language code (e.g. `en`, `de`, `fr`). |
| `general.theme` | `defaultDark` | `FS_GENERAL_THEME` | One of: `ayuDark`, `ayuLight`, `catppuccinLatte`, `catppuccinMocha`, `defaultDark`, `defaultLight`, `dracula`, `githubDark`, `githubLight`, `glassyDark`, `gruvboxDark`, `gruvboxLight`, `highContrastDark`, `highContrastLight`, `materialDark`, `materialLight`, `monokai`, `nightOwl`, `nord`, `oneDark`, `rosePine`, `rosePineDawn`, `rosePineMoon`, `shadesOfPurple`, `solarizedDark`, `solarizedLight`, `tokyoNight`, `vscodeDarkPlus`, `vscodeLightPlus`. |
| `general.themeDark` | `defaultDark` | `FS_GENERAL_THEME_DARK` | Same as theme (used when system is dark). |
| `general.themeLight` | `defaultLight` | `FS_GENERAL_THEME_LIGHT` | Same as theme (used when system is light). |
| `general.lastfmApiKey` | *(empty)* | `FS_GENERAL_LASTFM_API_KEY` | Last.fm API key. |
| `general.lastFM` | `true` | `FS_GENERAL_LAST_FM` | `true` / `false` — Enable Last.fm. |
| `general.musicBrainz` | `true` | `FS_GENERAL_MUSIC_BRAINZ` | `true` / `false` — MusicBrainz links. |
| `general.nativeAspectRatio` | `false` | `FS_GENERAL_NATIVE_ASPECT_RATIO` | `true` / `false` — Use native cover art aspect ratio. |
| `general.pathReplace` | *(empty)* | `FS_GENERAL_PATH_REPLACE` | Path pattern to replace (e.g. server path in Docker). |
| `general.pathReplaceWith` | *(empty)* | `FS_GENERAL_PATH_REPLACE_WITH` | Replacement path. |
| `general.playerbarOpenDrawer` | `false` | `FS_GENERAL_PLAYERBAR_OPEN_DRAWER` | `true` / `false` — Open queue/lyrics as drawer from player bar. |
| `general.primaryShade` | `6` | `FS_GENERAL_PRIMARY_SHADE` | Mantine primary shade 09 (number). |
| `general.resume` | `true` | `FS_GENERAL_RESUME` | `true` / `false` — Resume playback on load. |
| `general.showLyricsInSidebar` | `true` | `FS_GENERAL_SHOW_LYRICS_IN_SIDEBAR` | `true` / `false` — Show lyrics in sidebar. |
| `general.showRatings` | `true` | `FS_GENERAL_SHOW_RATINGS` | `true` / `false` — Show star ratings. |
| `general.showVisualizerInSidebar` | `true` | `FS_GENERAL_SHOW_VISUALIZER_IN_SIDEBAR` | `true` / `false` — Show visualizer in sidebar. |
| `general.sidebarCollapsedNavigation` | `true` | `FS_GENERAL_SIDEBAR_COLLAPSED_NAVIGATION` | `true` / `false` — Start with collapsed sidebar nav. |
| `general.sidebarCollapseShared` | `false` | `FS_GENERAL_SIDEBAR_COLLAPSE_SHARED` | `true` / `false` — Share sidebar collapse state. |
| `general.sidebarPlaylistList` | `true` | `FS_GENERAL_SIDEBAR_PLAYLIST_LIST` | `true` / `false` — Show playlist list in sidebar. |
| `general.sidebarPlaylistSorting` | `false` | `FS_GENERAL_SIDEBAR_PLAYLIST_SORTING` | `true` / `false` — Enable playlist sorting in sidebar. |
| `general.sideQueueType` | `sideQueue` | `FS_GENERAL_SIDE_QUEUE_TYPE` | `sideDrawerQueue` / `sideQueue` — Side play queue style. |
| `general.useThemeAccentColor` | `false` | `FS_GENERAL_USE_THEME_ACCENT_COLOR` | `true` / `false` — Use themes accent color instead of custom. |
| `general.useThemePrimaryShade` | `true` | `FS_GENERAL_USE_THEME_PRIMARY_SHADE` | `true` / `false` — Use themes primary shade. |
| `general.zoomFactor` | `100` | `FS_GENERAL_ZOOM_FACTOR` | UI zoom percentage (number). |
---
## Playback
| Setting path | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `playback.mediaSession` | `false` | `FS_PLAYBACK_MEDIA_SESSION` | `true` / `false` — Media Session API (e.g. browser/media keys). |
| `playback.webAudio` | `true` | `FS_PLAYBACK_WEB_AUDIO` | `true` / `false` — Use Web Audio for playback. |
| `playback.audioFadeOnStatusChange` | `true` | `FS_PLAYBACK_AUDIO_FADE_ON_STATUS_CHANGE` | `true` / `false` — Fade on play/pause. |
| `playback.preservePitch` | `true` | `FS_PLAYBACK_PRESERVE_PITCH` | `true` / `false` — Preserve pitch when changing speed. |
| `playback.scrobble.enabled` | `true` | `FS_PLAYBACK_SCROBBLE_ENABLED` | `true` / `false` — Enable scrobbling. |
| `playback.scrobble.notify` | `false` | `FS_PLAYBACK_SCROBBLE_NOTIFY` | `true` / `false` — Scrobble notifications. |
| `playback.scrobble.scrobbleAtDuration` | `240` | `FS_PLAYBACK_SCROBBLE_AT_DURATION` | Seconds of playback before scrobble. |
| `playback.scrobble.scrobbleAtPercentage` | `75` | `FS_PLAYBACK_SCROBBLE_AT_PERCENTAGE` | Percentage of track before scrobble. |
| `playback.transcode.enabled` | `false` | `FS_PLAYBACK_TRANSCODE_ENABLED` | `true` / `false` — Enable transcoding. |
---
## Discord
| Setting path | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `discord.enabled` | `false` | `FS_DISCORD_ENABLED` | `true` / `false` — Discord rich presence. |
| `discord.clientId` | *(built-in)* | `FS_DISCORD_CLIENT_ID` | Custom Discord application ID. |
| `discord.displayType` | `feishin` | `FS_DISCORD_DISPLAY_TYPE` | `artist` / `feishin` / `song`. |
| `discord.linkType` | `none` | `FS_DISCORD_LINK_TYPE` | `last_fm` / `musicbrainz` / `musicbrainz_last_fm` / `none`. |
| `discord.showAsListening` | `false` | `FS_DISCORD_SHOW_AS_LISTENING` | `true` / `false`. |
| `discord.showPaused` | `true` | `FS_DISCORD_SHOW_PAUSED` | `true` / `false` — Show paused state. |
| `discord.showServerImage` | `false` | `FS_DISCORD_SHOW_SERVER_IMAGE` | `true` / `false`. |
| `discord.showStateIcon` | `true` | `FS_DISCORD_SHOW_STATE_ICON` | `true` / `false`. |
---
## Lyrics
| Setting path | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `lyrics.fetch` | `true` | `FS_LYRICS_FETCH` | `true` / `false` — Fetch lyrics. |
| `lyrics.follow` | `true` | `FS_LYRICS_FOLLOW` | `true` / `false` — Follow current line. |
| `lyrics.delayMs` | `0` | `FS_LYRICS_DELAY_MS` | Sync delay in milliseconds. |
| `lyrics.preferLocalLyrics` | `true` | `FS_LYRICS_PREFER_LOCAL` | `true` / `false` — Prefer local lyric files. |
| `lyrics.showMatch` | `true` | `FS_LYRICS_SHOW_MATCH` | `true` / `false`. |
| `lyrics.showProvider` | `true` | `FS_LYRICS_SHOW_PROVIDER` | `true` / `false`. |
| `lyrics.enableAutoTranslation` | `false` | `FS_LYRICS_ENABLE_AUTO_TRANSLATION` | `true` / `false`. |
| `lyrics.translationApiKey` | *(empty)* | `FS_LYRICS_TRANSLATION_API_KEY` | API key for lyric translation. |
| `lyrics.translationTargetLanguage` | `en` | `FS_LYRICS_TRANSLATION_TARGET_LANGUAGE` | Target language code. |
| `lyrics.alignment` | `center` | `FS_LYRICS_ALIGNMENT` | `center` / `left` / `right`. |
---
## Auto DJ
| Setting path | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `autoDJ.enabled` | `false` | `FS_AUTO_DJ_ENABLED` | `true` / `false`. |
| `autoDJ.itemCount` | `5` | `FS_AUTO_DJ_ITEM_COUNT` | Number of items to add. |
| `autoDJ.timing` | `1` | `FS_AUTO_DJ_TIMING` | Timing value (number). |
---
## CSS
| Setting path | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `css.content` | *(empty)* | `FS_CSS_CONTENT` | Custom CSS string (sanitized like in-app custom CSS). Set `FS_CSS_ENABLED=true` to apply. |
| `css.enabled` | `false` | `FS_CSS_ENABLED` | `true` / `false` — Enable custom CSS. |
---
## Font
| Setting path | Default | Env variable | Available values / Description |
|-------------|---------|--------------|--------------------------------|
| `font.type` | `builtIn` | `FS_FONT_TYPE` | `builtIn` / `system` / `custom`. |
| `font.builtIn` | `Inter` | `FS_FONT_BUILT_IN` | Built-in font name. |
| `font.system` | *(empty)* | `FS_FONT_SYSTEM` | System font name (when type is `system`). |
-72
View File
@@ -1,72 +0,0 @@
appId: org.jeffvli.feishin
productName: Feishin
artifactName: ${productName}-${version}-${os}-${arch}.${ext}
electronVersion: 39.4.0
directories:
buildResources: assets
files:
- 'out/**/*'
- 'package.json'
extraResources:
- assets/**
asarUnpack:
- resources/**
win:
target:
- target: zip
arch:
- x64
- arm64
- target: nsis
arch:
- x64
- arm64
icon: assets/icons/icon.ico
nsis:
allowToChangeInstallationDirectory: true
oneClick: false
shortcutName: ${productName}
uninstallDisplayName: ${productName}
createDesktopShortcut: always
mac:
target:
- target: dmg
arch:
- arm64
- x64
- target: zip
arch:
- arm64
- x64
icon: assets/icons/icon.icns
type: distribution
hardenedRuntime: false
identity: "-"
gatekeeperAssess: false
notarize: false
dmg:
contents: [{ x: 130, y: 220 }, { x: 410, y: 220, type: link, path: /Applications }]
linux:
target:
- AppImage
- deb
- tar.xz
category: AudioVideo;Audio;Player
icon: assets/icons/icon.png
artifactName: ${productName}-${os}-${arch}.${ext}
toolsets:
appimage: "1.0.2"
npmRebuild: false
publish:
provider: s3
bucket: feishin-nightly
channel: alpha
endpoint: https://065f090c64de2dc707dd70ac72db9669.r2.cloudflarestorage.com
+11 -24
View File
@@ -1,7 +1,7 @@
appId: org.jeffvli.feishin
productName: Feishin
artifactName: ${productName}-${version}-${os}-${arch}.${ext}
electronVersion: 39.4.0
electronVersion: 38.5.0
directories:
buildResources: assets
files:
@@ -13,15 +13,9 @@ asarUnpack:
- resources/**
win:
target:
- target: zip
arch:
- x64
- arm64
- target: nsis
arch:
- x64
- arm64
icon: assets/icons/icon.ico
- zip
- nsis
icon: assets/icons/icon.png
nsis:
allowToChangeInstallationDirectory: true
@@ -32,18 +26,15 @@ nsis:
mac:
target:
- target: dmg
arch:
- arm64
- x64
- target: zip
arch:
- arm64
- x64
target: default
arch:
- arm64
- x64
icon: assets/icons/icon.icns
type: distribution
hardenedRuntime: false
identity: "-"
hardenedRuntime: true
entitlements: assets/entitlements.mac.plist
entitlementsInherit: assets/entitlements.mac.plist
gatekeeperAssess: false
notarize: false
@@ -53,15 +44,11 @@ dmg:
linux:
target:
- AppImage
- deb
- tar.xz
category: AudioVideo;Audio;Player
icon: assets/icons/icon.png
artifactName: ${productName}-${os}-${arch}.${ext}
toolsets:
appimage: "1.0.2"
npmRebuild: false
publish:
provider: github
+11 -25
View File
@@ -1,7 +1,7 @@
appId: org.jeffvli.feishin
productName: Feishin
artifactName: ${productName}-${version}-${os}-${arch}.${ext}
electronVersion: 39.4.0
electronVersion: 38.5.0
directories:
buildResources: assets
files:
@@ -13,15 +13,9 @@ asarUnpack:
- resources/**
win:
target:
- target: zip
arch:
- x64
- arm64
- target: nsis
arch:
- x64
- arm64
icon: assets/icons/icon.ico
- zip
- nsis
icon: assets/icons/icon.png
nsis:
allowToChangeInstallationDirectory: true
@@ -32,18 +26,15 @@ nsis:
mac:
target:
- target: dmg
arch:
- arm64
- x64
- target: zip
arch:
- arm64
- x64
target: default
arch:
- arm64
- x64
icon: assets/icons/icon.icns
type: distribution
hardenedRuntime: false
identity: "-"
hardenedRuntime: true
entitlements: assets/entitlements.mac.plist
entitlementsInherit: assets/entitlements.mac.plist
gatekeeperAssess: false
notarize: false
@@ -53,17 +44,12 @@ dmg:
linux:
target:
- AppImage
- deb
- tar.xz
category: AudioVideo;Audio;Player
icon: assets/icons/icon.png
artifactName: ${productName}-${os}-${arch}.${ext}
toolsets:
appimage: "1.0.2"
npmRebuild: false
afterAllArtifactBuild: scripts/after-all-artifact-build.mjs
publish:
provider: github
owner: jeffvli
-13
View File
@@ -6,7 +6,6 @@ import dynamicImportPlugin from 'vite-plugin-dynamic-import';
import { ViteEjsPlugin } from 'vite-plugin-ejs';
const currentOSEnv = process.platform;
const electronRendererTarget = 'chrome87';
const config: UserConfig = {
main: {
@@ -37,9 +36,6 @@ const config: UserConfig = {
},
},
preload: {
build: {
sourcemap: true,
},
plugins: [externalizeDepsPlugin()],
resolve: {
alias: {
@@ -49,15 +45,6 @@ const config: UserConfig = {
},
},
renderer: {
build: {
cssMinify: 'esbuild',
minify: 'esbuild',
modulePreload: {
polyfill: false,
},
sourcemap: true,
target: electronRendererTarget,
},
css: {
modules: {
generateScopedName: 'fs-[name]-[local]',
-2
View File
@@ -43,8 +43,6 @@ export default tseslint.config(
'no-unused-vars': 'off',
'no-use-before-define': 'off',
quotes: ['error', 'single'],
'react-hooks/refs': 'off',
'react-hooks/set-state-in-effect': 'off',
'react-refresh/only-export-components': 'off',
'react/display-name': 'off',
semi: ['error', 'always'],
Binary file not shown.
Binary file not shown.

After

Width:  |  Height:  |  Size: 118 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 81 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 77 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 214 KiB

BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.

After

Width:  |  Height:  |  Size: 101 KiB

-104
View File
@@ -1,104 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
width="512"
height="512"
viewBox="0 0 512 512"
version="1.1"
id="svg1"
xml:space="preserve"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg"><defs
id="defs1"><linearGradient
id="linearGradient1"><stop
style="stop-color:#dfdfdf;stop-opacity:1;"
offset="0"
id="stop1" /><stop
style="stop-color:#ffffff;stop-opacity:1;"
offset="1"
id="stop2" /></linearGradient><filter
style="color-interpolation-filters:sRGB"
id="filter249"
x="-0.61395349"
y="-0.61395349"
width="2.227907"
height="2.5069767"><feFlood
result="flood"
in="SourceGraphic"
flood-opacity="0.498039"
flood-color="rgb(0,0,0)"
id="feFlood247" /><feGaussianBlur
result="blur"
in="SourceGraphic"
stdDeviation="1.000000"
id="feGaussianBlur247" /><feOffset
result="offset"
in="blur"
dx="0.000000"
dy="2"
id="feOffset247" /><feComposite
result="comp1"
operator="in"
in="flood"
in2="offset"
id="feComposite248" /><feComposite
result="fbSourceGraphic"
operator="over"
in="SourceGraphic"
id="feComposite249"
in2="comp1" /><feColorMatrix
result="fbSourceGraphicAlpha"
in="fbSourceGraphic"
values="0 0 0 -1 0 0 0 0 -1 0 0 0 0 -1 0 0 0 0 1 0"
id="feColorMatrix122" /><feFlood
id="feFlood122"
result="flood"
in="fbSourceGraphic"
flood-opacity="0.196078"
flood-color="rgb(0,0,0)" /><feGaussianBlur
id="feGaussianBlur122"
result="blur"
in="fbSourceGraphic"
stdDeviation="10.000000" /><feOffset
id="feOffset122"
result="offset"
in="blur"
dx="0.000000"
dy="10.000000" /><feComposite
id="feComposite122"
result="comp1"
operator="in"
in="flood"
in2="offset" /><feComposite
id="feComposite123"
result="comp2"
operator="over"
in="fbSourceGraphic"
in2="comp1" /></filter><linearGradient
xlink:href="#linearGradient1"
id="linearGradient2"
x1="256"
y1="0"
x2="256"
y2="512"
gradientUnits="userSpaceOnUse" /></defs><g
id="layer1"
style="display:inline"><circle
style="display:inline;fill:url(#linearGradient2);stroke-width:25;stroke-linecap:round;stroke-linejoin:round;paint-order:markers fill stroke"
id="background"
cx="256"
cy="256"
r="256" /><circle
style="opacity:1;fill:#000000;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:2.19597;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers fill stroke;filter:url(#filter249)"
id="dot"
cx="256"
cy="240.31155"
r="21.5" /><path
id="bottom"
style="opacity:1;fill:#000000;fill-opacity:1;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter249)"
d="M 220.84961,277.95117 183.5,315.59961 219.5,351.69922 239.5,332 c 0,0 5.85615,-6.19922 16.5,-6.19922 10.64385,0 16.5,6.19922 16.5,6.19922 l 20,19.69922 36,-36.09961 -37.34961,-37.64844 A 51.5,51.5 0 0 1 256,291.8125 51.5,51.5 0 0 1 220.84961,277.95117 Z" /><path
id="main"
style="display:inline;opacity:1;fill:#000000;fill-opacity:1;stroke-width:2.2;stroke-linecap:round;stroke-linejoin:round;paint-order:markers fill stroke;filter:url(#filter249)"
d="m 256,145.40039 c -7.11895,0 -13.56326,2.88552 -18.22852,7.55078 L 66.96875,323.46875 C 62.354158,328.08334 59.5,334.45837 59.5,341.5 c 0,14.08326 11.416739,25.5 25.5,25.5 7.04163,0 13.41666,-2.85416 18.03125,-7.46875 L 206.92578,255.93359 A 51.5,51.5 0 0 1 204.5,240.3125 a 51.5,51.5 0 0 1 51.5,-51.5 51.5,51.5 0 0 1 51.5,51.5 51.5,51.5 0 0 1 -2.42578,15.62109 L 408.96875,359.53125 C 413.58334,364.14585 419.95837,367 427,367 c 14.08326,0 25.5,-11.41674 25.5,-25.5 0,-7.04163 -2.85415,-13.41666 -7.46875,-18.03125 L 274.22852,152.95117 C 269.56326,148.2859 263.11895,145.40039 256,145.40039 Z" /></g></svg>

Before

Width:  |  Height:  |  Size: 4.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 733 KiB

After

Width:  |  Height:  |  Size: 644 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 371 KiB

After

Width:  |  Height:  |  Size: 186 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 869 KiB

After

Width:  |  Height:  |  Size: 465 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 49 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 990 KiB

After

Width:  |  Height:  |  Size: 887 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 356 KiB

After

Width:  |  Height:  |  Size: 396 KiB

-3
View File
@@ -1,6 +1,5 @@
server {
listen 9180;
listen [::]:9180;
sendfile on;
default_type application/octet-stream;
@@ -20,11 +19,9 @@ server {
location ${PUBLIC_PATH}settings.js {
alias /etc/nginx/conf.d/settings.js;
add_header Cache-Control "no-store";
}
location ${PUBLIC_PATH}/settings.js {
alias /etc/nginx/conf.d/settings.js;
add_header Cache-Control "no-store";
}
}
+83 -89
View File
@@ -1,6 +1,6 @@
{
"name": "feishin",
"version": "1.9.0",
"version": "0.21.2",
"description": "A modern self-hosted music player.",
"keywords": [
"subsonic",
@@ -16,12 +16,11 @@
"license": "GPL-3.0",
"author": {
"name": "jeffvli",
"email": "feishin@users.noreply.github.com",
"url": "https://github.com/jeffvli/"
},
"main": "./out/main/index.js",
"scripts": {
"build": "pnpm run build:electron && pnpm run build:remote",
"build": "pnpm run typecheck && pnpm run build:electron && pnpm run build:remote",
"build:electron": "electron-vite build",
"build:remote": "vite build --config remote.vite.config.ts",
"build:web": "vite build --config web.vite.config.ts",
@@ -30,7 +29,7 @@
"dev:watch": "electron-vite dev --watch",
"i18next": "i18next -c src/i18n/i18next-parser.config.js",
"postinstall": "electron-builder install-app-deps",
"lint": "pnpm run typecheck && pnpm run lint-code && pnpm run lint-styles",
"lint": "pnpm run lint-code && pnpm run lint-styles",
"lint-code": "eslint --max-warnings=0 --cache .",
"lint-code:fix": "eslint --cache --fix .",
"lint-styles": "stylelint --max-warnings=0 'src/**/*.{css,scss}'",
@@ -44,22 +43,14 @@
"package:mac": "pnpm run build && electron-builder --mac",
"package:mac:pr": "pnpm run build && electron-builder --mac --publish never",
"package:win": "pnpm run build && electron-builder --win",
"package:win-arm64:pr": "pnpm run build && electron-builder --win --arm64 --publish never",
"package:win:pr": "pnpm run build && electron-builder --win --publish never",
"publish:linux": "pnpm run build && electron-builder --publish always --linux",
"publish:linux-arm64": "pnpm run build && electron-builder --publish always --linux --arm64",
"publish:linux-arm64:alpha": "pnpm run build && electron-builder --config electron-builder-alpha.yml --publish always --linux --arm64",
"publish:linux-arm64:beta": "pnpm run build && electron-builder --config electron-builder-beta.yml --publish always --linux --arm64",
"publish:linux:alpha": "pnpm run build && electron-builder --config electron-builder-alpha.yml --publish always --linux",
"publish:linux:beta": "pnpm run build && electron-builder --config electron-builder-beta.yml --publish always --linux",
"publish:mac": "pnpm run build && electron-builder --publish always --mac",
"publish:mac:alpha": "pnpm run build && electron-builder --config electron-builder-alpha.yml --publish always --mac",
"publish:mac:beta": "pnpm run build && electron-builder --config electron-builder-beta.yml --publish always --mac",
"publish:win": "pnpm run build && electron-builder --publish always --win",
"publish:win-arm64": "pnpm run build && electron-builder --publish always --win --arm64",
"publish:win-arm64:alpha": "pnpm run build && electron-builder --config electron-builder-alpha.yml --publish always --win --arm64",
"publish:win-arm64:beta": "pnpm run build && electron-builder --config electron-builder-beta.yml --publish always --win --arm64",
"publish:win:alpha": "pnpm run build && electron-builder --config electron-builder-alpha.yml --publish always --win",
"publish:win:beta": "pnpm run build && electron-builder --config electron-builder-beta.yml --publish always --win",
"start": "electron-vite preview",
"typecheck": "pnpm run typecheck:node && pnpm run typecheck:web",
@@ -69,73 +60,75 @@
"postversion": "node ./scripts/update-app-stream.mjs"
},
"dependencies": {
"@atlaskit/pragmatic-drag-and-drop": "1.7.7",
"@atlaskit/pragmatic-drag-and-drop-auto-scroll": "^2.1.2",
"@atlaskit/pragmatic-drag-and-drop-hitbox": "^1.1.0",
"@ag-grid-community/client-side-row-model": "^28.2.1",
"@ag-grid-community/core": "^28.2.1",
"@ag-grid-community/infinite-row-model": "^28.2.1",
"@ag-grid-community/react": "^28.2.1",
"@ag-grid-community/styles": "^28.2.1",
"@atlaskit/pragmatic-drag-and-drop": "1.4.0",
"@atlaskit/pragmatic-drag-and-drop-auto-scroll": "^2.1.0",
"@atlaskit/pragmatic-drag-and-drop-hitbox": "^1.0.3",
"@electron-toolkit/preload": "^3.0.1",
"@electron-toolkit/utils": "^4.0.0",
"@mantine/colors-generator": "^8.3.8",
"@mantine/core": "^8.3.8",
"@mantine/dates": "^8.3.8",
"@mantine/form": "^8.3.8",
"@mantine/hooks": "^8.3.8",
"@mantine/modals": "^8.3.8",
"@mantine/notifications": "^8.3.8",
"@radix-ui/react-context-menu": "^2.2.16",
"@tanstack/react-query": "^5.90.9",
"@tanstack/react-query-devtools": "^5.90.2",
"@tanstack/react-query-persist-client": "^5.90.11",
"@ts-rest/core": "^3.52.1",
"@wavesurfer/react": "^1.0.11",
"@mantine/colors-generator": "^8.2.8",
"@mantine/core": "^8.2.8",
"@mantine/dates": "^8.2.8",
"@mantine/form": "^8.2.8",
"@mantine/hooks": "^8.2.8",
"@mantine/modals": "^8.2.8",
"@mantine/notifications": "^8.2.8",
"@tanstack/react-query": "^5.89.0",
"@tanstack/react-query-devtools": "^5.89.0",
"@tanstack/react-query-persist-client": "^5.89.0",
"@ts-rest/core": "^3.23.0",
"@xhayper/discord-rpc": "^1.3.0",
"audiomotion-analyzer": "^4.5.1",
"axios": "^1.13.5",
"butterchurn": "^3.0.0-beta.5",
"butterchurn-presets": "^3.0.0-beta.4",
"cheerio": "^1.1.2",
"clsx": "^2.1.1",
"cmdk": "^1.1.1",
"dayjs": "^1.11.19",
"dompurify": "^3.3.0",
"audiomotion-analyzer": "^4.5.0",
"auto-text-size": "^0.2.3",
"axios": "^1.12.0",
"cheerio": "^1.0.0",
"clsx": "^2.0.0",
"cmdk": "^0.2.0",
"dayjs": "^1.11.6",
"dompurify": "^3.1.6",
"electron-debug": "^3.2.0",
"electron-localshortcut": "^3.2.1",
"electron-log": "^5.4.3",
"electron-store": "^8.2.0",
"electron-updater": "^6.6.2",
"fast-average-color": "^9.5.0",
"fast-xml-parser": "^5.3.6",
"format-duration": "^3.0.2",
"fuse.js": "^7.1.0",
"i18next": "^25.6.2",
"icecast-metadata-stats": "^0.1.12",
"idb-keyval": "^6.2.2",
"immer": "^10.2.0",
"electron-log": "^5.1.1",
"electron-store": "^8.1.0",
"electron-updater": "^6.3.9",
"fast-average-color": "^9.3.0",
"fast-xml-parser": "^5.3.0",
"format-duration": "^2.0.0",
"fuse.js": "^6.6.2",
"i18next": "^21.10.0",
"idb-keyval": "^6.2.1",
"immer": "^9.0.21",
"is-electron": "^2.2.2",
"lodash": "^4.17.23",
"lodash": "^4.17.21",
"md5": "^2.3.0",
"motion": "^12.23.24",
"memoize-one": "^6.0.0",
"motion": "^12.18.1",
"mpris-service": "^2.1.2",
"nanoid": "^3.3.11",
"nanoid": "^3.3.3",
"node-mpv": "github:jeffvli/Node-MPV#32b4d64395289ad710c41d481d2707a7acfc228f",
"nuqs": "^2.7.1",
"overlayscrollbars": "^2.11.1",
"overlayscrollbars-react": "^0.5.6",
"qs": "^6.14.2",
"qs": "^6.14.0",
"react": "^19.1.0",
"react-call": "^1.8.1",
"react-dom": "^19.1.0",
"react-error-boundary": "^5.0.0",
"react-i18next": "^16.3.3",
"react-error-boundary": "^3.1.4",
"react-i18next": "^11.18.6",
"react-icons": "^5.5.0",
"react-player": "^2.16.0",
"react-router": "^7.13.1",
"react-split-pane": "^3.0.4",
"react-virtualized-auto-sizer": "^1.0.26",
"react-window": "1.8.11",
"react-window-v2": "npm:react-window@^2.2.3",
"react-image": "^4.1.0",
"react-loading-skeleton": "^3.5.0",
"react-player": "^2.11.0",
"react-router": "^6.16.0",
"react-router-dom": "^6.16.0",
"react-virtualized-auto-sizer": "^1.0.17",
"react-window": "^1.8.9",
"react-window-infinite-loader": "^1.0.9",
"semver": "^7.5.4",
"string-to-color": "^2.2.2",
"wavesurfer.js": "^7.11.1",
"swiper": "^9.3.1",
"use-sync-external-store": "^1.5.0",
"ws": "^8.18.2",
"zod": "^3.22.3",
"zustand": "^5.0.5"
@@ -143,44 +136,45 @@
"devDependencies": {
"@electron-toolkit/eslint-config-prettier": "^3.0.0",
"@electron-toolkit/eslint-config-ts": "^3.0.0",
"@electron-toolkit/tsconfig": "^2.0.0",
"@electron-toolkit/tsconfig": "^1.0.1",
"@types/electron-localshortcut": "^3.1.0",
"@types/lodash": "^4.17.18",
"@types/md5": "^2.3.5",
"@types/node": "^24.10.1",
"@types/react": "^19.2.5",
"@types/react-dom": "^19.2.3",
"@types/react-window": "^1.8.8",
"@types/node": "^22.15.32",
"@types/react": "^18.3.23",
"@types/react-dom": "^18.3.7",
"@types/react-window": "^1.8.5",
"@types/react-window-infinite-loader": "^1.0.6",
"@types/source-map-support": "^0.5.10",
"@types/ws": "^8.18.1",
"@vitejs/plugin-react": "^5.1.1",
"concurrently": "^9.2.1",
"cross-env": "^10.1.0",
"electron": "^39.4.0",
"electron-builder": "^26.8.2",
"electron-devtools-installer": "^4.0.0",
"electron-vite": "^4.0.1",
"@vitejs/plugin-react": "^4.3.4",
"concurrently": "^7.1.0",
"cross-env": "^7.0.3",
"electron": "^38.5.0",
"electron-builder": "^26.0.12",
"electron-devtools-installer": "^3.2.0",
"electron-vite": "^3.1.0",
"eslint": "^9.24.0",
"eslint-plugin-perfectionist": "^4.13.0",
"eslint-plugin-prettier": "^5.4.0",
"eslint-plugin-react": "^7.37.5",
"eslint-plugin-react-hooks": "^7.0.1",
"eslint-plugin-react-refresh": "^0.4.24",
"i18next-parser": "^9.3.0",
"postcss-preset-mantine": "^1.18.0",
"postcss-simple-vars": "^7.0.1",
"prettier": "^3.6.2",
"prettier-plugin-packagejson": "^2.5.19",
"stylelint": "^16.25.0",
"stylelint-config-css-modules": "^4.5.1",
"stylelint-config-recess-order": "^7.4.0",
"stylelint-config-standard": "^39.0.1",
"eslint-plugin-react-hooks": "^5.2.0",
"eslint-plugin-react-refresh": "^0.4.19",
"i18next-parser": "^9.0.2",
"postcss-preset-mantine": "^1.17.0",
"prettier": "^3.5.3",
"prettier-plugin-packagejson": "^2.5.14",
"sass-embedded": "^1.89.0",
"stylelint": "^16.14.1",
"stylelint-config-css-modules": "^4.4.0",
"stylelint-config-recess-order": "^7.1.0",
"stylelint-config-standard": "^38.0.0",
"typescript": "^5.8.3",
"vite": "^7.2.2",
"vite": "^6.4.1",
"vite-plugin-conditional-import": "^0.1.7",
"vite-plugin-dynamic-import": "^1.6.0",
"vite-plugin-ejs": "^1.7.0",
"vite-plugin-pwa": "^1.1.0"
"vite-plugin-pwa": "^1.0.3"
},
"pnpm": {
"onlyBuiltDependencies": [
+2399 -2705
View File
File diff suppressed because it is too large Load Diff
-11
View File
@@ -1,16 +1,5 @@
module.exports = {
plugins: {
'postcss-preset-mantine': {},
'postcss-simple-vars': {
variables: {
'mantine-breakpoint-2xl': '120em',
'mantine-breakpoint-3xl': '160em',
'mantine-breakpoint-lg': '75em',
'mantine-breakpoint-md': '62em',
'mantine-breakpoint-sm': '48em',
'mantine-breakpoint-xl': '88em',
'mantine-breakpoint-xs': '36em',
},
},
},
};
-3
View File
@@ -7,9 +7,7 @@ import { version } from './package.json';
export default defineConfig({
build: {
cssMinify: 'esbuild',
emptyOutDir: true,
minify: 'esbuild',
outDir: path.resolve(__dirname, './out/remote'),
rollupOptions: {
input: {
@@ -23,7 +21,6 @@ export default defineConfig({
assetFileNames: '[name].[ext]',
chunkFileNames: '[name].js',
entryFileNames: '[name].js',
sourcemapExcludeSources: false,
},
},
sourcemap: true,
Binary file not shown.

Before

Width:  |  Height:  |  Size: 32 KiB

After

Width:  |  Height:  |  Size: 48 KiB

-45
View File
@@ -1,45 +0,0 @@
import { execSync } from 'child_process';
import path from 'path';
import { fileURLToPath } from 'url';
const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename);
/**
* Electron-builder afterAllArtifactBuild hook
* Runs the app stream update script only for Linux builds
* Returns the metainfo file path to be included in published artifacts
*/
// This is not a typescript file, and is called by electron-builder, so we cannot use typescript features here.
// eslint-disable-next-line @typescript-eslint/explicit-function-return-type
export default async function afterAllArtifactBuild(buildResult) {
// Check if this build includes Linux as a target
const isLinux = Array.from(buildResult.platformToTargets.keys()).some(
(platform) => platform.name === 'linux',
);
if (isLinux) {
const updateScriptPath = path.join(__dirname, 'update-app-stream.mjs');
const projectRoot = path.resolve(__dirname, '..');
const metainfoFile = path.resolve(projectRoot, 'org.jeffvli.feishin.metainfo.xml');
console.log('Running app stream update for Linux build...');
try {
execSync(`node ${updateScriptPath} --replace-if-version-missing`, {
cwd: projectRoot,
stdio: 'inherit',
});
// Return the metainfo file to be included in published artifacts
return [metainfoFile];
} catch (error) {
console.error('Failed to update app stream:', error.message);
throw error;
}
}
// Return empty array if not a Linux build
return [];
}
+11 -32
View File
@@ -3,51 +3,30 @@ import fs from 'fs';
import path from 'path';
const args = process.argv.slice(2);
// Parse flags and positional arguments
const flags = args.filter((arg) => arg.startsWith('--'));
const positionalArgs = args.filter((arg) => !arg.startsWith('--'));
const replaceIfVersionMissing = flags.includes('--replace-if-version-missing');
if (positionalArgs.length > 3) {
console.error(
'Usage: node update-app-stream.js [package-file] [date] [metainfo-file] [--replace-if-version-missing]',
);
if (args.length > 3) {
console.error('Usage: node update-app-stream.js [package-file] [date] [metainfo-file]');
process.exit(1);
}
const packageFile = positionalArgs[0] || path.resolve(process.cwd(), 'package.json');
const packageFile = args[0] || path.resolve(process.cwd(), 'package.json');
const packageContent = fs.readFileSync(packageFile, 'utf8');
const packageJson = JSON.parse(packageContent);
const version = packageJson.version;
const time = Math.floor((Date.parse(positionalArgs[1]) || Date.now()) / 1000);
const metainfoFile =
positionalArgs[2] || path.resolve(process.cwd(), 'org.jeffvli.feishin.metainfo.xml');
const time = Math.floor((Date.parse(args[1]) || Date.now()) / 1000);
const metainfoFile = args[2] || path.resolve(process.cwd(), 'org.jeffvli.feishin.metainfo.xml');
const parser = new XMLParser({ ignoreAttributes: false });
const metainfoContent = fs.readFileSync(metainfoFile, 'utf8');
const metainfo = parser.parse(metainfoContent);
const newRelease = {
'@_date': new Date(time * 1000).toISOString().split('T')[0],
'@_type': version.includes('-') ? 'development' : 'stable',
'@_version': version,
};
if (replaceIfVersionMissing) {
// Replace all releases with only the current version
metainfo.component.releases.release = [newRelease];
} else {
// Default behavior: add new release if it doesn't exist
const releaseExists =
metainfo.component.releases.release.findIndex(
(release) => release['@_version'] === version,
) !== -1;
if (!releaseExists) {
metainfo.component.releases.release.unshift(newRelease);
}
if (!metainfo.component.releases.release.find((release) => release['@_version'] === version)) {
metainfo.component.releases.release.unshift({
'@_date': new Date(time * 1000).toISOString().split('T')[0],
'@_type': version.includes('-') ? 'development' : 'stable',
'@_version': version,
});
}
const builder = new XMLBuilder({ format: true, ignoreAttributes: false, indentBy: ' ' });
+1 -87
View File
@@ -1,87 +1 @@
"use strict";
window.SERVER_URL = "${SERVER_URL}";
window.REMOTE_URL = "${REMOTE_URL}";
window.SERVER_NAME = "${SERVER_NAME}";
window.SERVER_TYPE = "${SERVER_TYPE}";
window.SERVER_LOCK = "${SERVER_LOCK}";
window.LEGACY_AUTHENTICATION = "${LEGACY_AUTHENTICATION}";
window.ANALYTICS_DISABLED = "${ANALYTICS_DISABLED}";
window.FS_GENERAL_ACCENT = "${FS_GENERAL_ACCENT}";
window.FS_GENERAL_ALBUM_BACKGROUND = "${FS_GENERAL_ALBUM_BACKGROUND}";
window.FS_GENERAL_ALBUM_BACKGROUND_BLUR = "${FS_GENERAL_ALBUM_BACKGROUND_BLUR}";
window.FS_GENERAL_ARTIST_BACKGROUND = "${FS_GENERAL_ARTIST_BACKGROUND}";
window.FS_GENERAL_ARTIST_BACKGROUND_BLUR = "${FS_GENERAL_ARTIST_BACKGROUND_BLUR}";
window.FS_GENERAL_BLUR_EXPLICIT_IMAGES = "${FS_GENERAL_BLUR_EXPLICIT_IMAGES}";
window.FS_GENERAL_COMBINED_LYRICS_AND_VISUALIZER = "${FS_GENERAL_COMBINED_LYRICS_AND_VISUALIZER}";
window.FS_GENERAL_ENABLE_GRID_MULTI_SELECT = "${FS_GENERAL_ENABLE_GRID_MULTI_SELECT}";
window.FS_GENERAL_EXTERNAL_LINKS = "${FS_GENERAL_EXTERNAL_LINKS}";
window.FS_GENERAL_FOLLOW_CURRENT_SONG = "${FS_GENERAL_FOLLOW_CURRENT_SONG}";
window.FS_GENERAL_FOLLOW_SYSTEM_THEME = "${FS_GENERAL_FOLLOW_SYSTEM_THEME}";
window.FS_GENERAL_HOME_FEATURE = "${FS_GENERAL_HOME_FEATURE}";
window.FS_GENERAL_HOME_FEATURE_STYLE = "${FS_GENERAL_HOME_FEATURE_STYLE}";
window.FS_GENERAL_LANGUAGE = "${FS_GENERAL_LANGUAGE}";
window.FS_GENERAL_LAST_FM = "${FS_GENERAL_LAST_FM}";
window.FS_GENERAL_LASTFM_API_KEY = "${FS_GENERAL_LASTFM_API_KEY}";
window.FS_GENERAL_MUSIC_BRAINZ = "${FS_GENERAL_MUSIC_BRAINZ}";
window.FS_GENERAL_NATIVE_ASPECT_RATIO = "${FS_GENERAL_NATIVE_ASPECT_RATIO}";
window.FS_GENERAL_PATH_REPLACE = "${FS_GENERAL_PATH_REPLACE}";
window.FS_GENERAL_PATH_REPLACE_WITH = "${FS_GENERAL_PATH_REPLACE_WITH}";
window.FS_GENERAL_PLAYERBAR_OPEN_DRAWER = "${FS_GENERAL_PLAYERBAR_OPEN_DRAWER}";
window.FS_GENERAL_PRIMARY_SHADE = "${FS_GENERAL_PRIMARY_SHADE}";
window.FS_GENERAL_RESUME = "${FS_GENERAL_RESUME}";
window.FS_GENERAL_SHOW_LYRICS_IN_SIDEBAR = "${FS_GENERAL_SHOW_LYRICS_IN_SIDEBAR}";
window.FS_GENERAL_SHOW_RATINGS = "${FS_GENERAL_SHOW_RATINGS}";
window.FS_GENERAL_SHOW_VISUALIZER_IN_SIDEBAR = "${FS_GENERAL_SHOW_VISUALIZER_IN_SIDEBAR}";
window.FS_GENERAL_SIDEBAR_COLLAPSED_NAVIGATION = "${FS_GENERAL_SIDEBAR_COLLAPSED_NAVIGATION}";
window.FS_GENERAL_SIDEBAR_COLLAPSE_SHARED = "${FS_GENERAL_SIDEBAR_COLLAPSE_SHARED}";
window.FS_GENERAL_SIDEBAR_PLAYLIST_LIST = "${FS_GENERAL_SIDEBAR_PLAYLIST_LIST}";
window.FS_GENERAL_SIDEBAR_PLAYLIST_SORTING = "${FS_GENERAL_SIDEBAR_PLAYLIST_SORTING}";
window.FS_GENERAL_SIDE_QUEUE_TYPE = "${FS_GENERAL_SIDE_QUEUE_TYPE}";
window.FS_GENERAL_THEME = "${FS_GENERAL_THEME}";
window.FS_GENERAL_THEME_DARK = "${FS_GENERAL_THEME_DARK}";
window.FS_GENERAL_THEME_LIGHT = "${FS_GENERAL_THEME_LIGHT}";
window.FS_GENERAL_USE_THEME_ACCENT_COLOR = "${FS_GENERAL_USE_THEME_ACCENT_COLOR}";
window.FS_GENERAL_USE_THEME_PRIMARY_SHADE = "${FS_GENERAL_USE_THEME_PRIMARY_SHADE}";
window.FS_GENERAL_ZOOM_FACTOR = "${FS_GENERAL_ZOOM_FACTOR}";
window.FS_PLAYBACK_MEDIA_SESSION = "${FS_PLAYBACK_MEDIA_SESSION}";
window.FS_PLAYBACK_WEB_AUDIO = "${FS_PLAYBACK_WEB_AUDIO}";
window.FS_PLAYBACK_AUDIO_FADE_ON_STATUS_CHANGE = "${FS_PLAYBACK_AUDIO_FADE_ON_STATUS_CHANGE}";
window.FS_PLAYBACK_PRESERVE_PITCH = "${FS_PLAYBACK_PRESERVE_PITCH}";
window.FS_PLAYBACK_SCROBBLE_ENABLED = "${FS_PLAYBACK_SCROBBLE_ENABLED}";
window.FS_PLAYBACK_SCROBBLE_NOTIFY = "${FS_PLAYBACK_SCROBBLE_NOTIFY}";
window.FS_PLAYBACK_SCROBBLE_AT_DURATION = "${FS_PLAYBACK_SCROBBLE_AT_DURATION}";
window.FS_PLAYBACK_SCROBBLE_AT_PERCENTAGE = "${FS_PLAYBACK_SCROBBLE_AT_PERCENTAGE}";
window.FS_PLAYBACK_TRANSCODE_ENABLED = "${FS_PLAYBACK_TRANSCODE_ENABLED}";
window.FS_DISCORD_ENABLED = "${FS_DISCORD_ENABLED}";
window.FS_DISCORD_CLIENT_ID = "${FS_DISCORD_CLIENT_ID}";
window.FS_DISCORD_DISPLAY_TYPE = "${FS_DISCORD_DISPLAY_TYPE}";
window.FS_DISCORD_LINK_TYPE = "${FS_DISCORD_LINK_TYPE}";
window.FS_DISCORD_SHOW_AS_LISTENING = "${FS_DISCORD_SHOW_AS_LISTENING}";
window.FS_DISCORD_SHOW_PAUSED = "${FS_DISCORD_SHOW_PAUSED}";
window.FS_DISCORD_SHOW_SERVER_IMAGE = "${FS_DISCORD_SHOW_SERVER_IMAGE}";
window.FS_DISCORD_SHOW_STATE_ICON = "${FS_DISCORD_SHOW_STATE_ICON}";
window.FS_LYRICS_FETCH = "${FS_LYRICS_FETCH}";
window.FS_LYRICS_FOLLOW = "${FS_LYRICS_FOLLOW}";
window.FS_LYRICS_DELAY_MS = "${FS_LYRICS_DELAY_MS}";
window.FS_LYRICS_PREFER_LOCAL = "${FS_LYRICS_PREFER_LOCAL}";
window.FS_LYRICS_SHOW_MATCH = "${FS_LYRICS_SHOW_MATCH}";
window.FS_LYRICS_SHOW_PROVIDER = "${FS_LYRICS_SHOW_PROVIDER}";
window.FS_LYRICS_ENABLE_AUTO_TRANSLATION = "${FS_LYRICS_ENABLE_AUTO_TRANSLATION}";
window.FS_LYRICS_TRANSLATION_API_KEY = "${FS_LYRICS_TRANSLATION_API_KEY}";
window.FS_LYRICS_TRANSLATION_TARGET_LANGUAGE = "${FS_LYRICS_TRANSLATION_TARGET_LANGUAGE}";
window.FS_LYRICS_ALIGNMENT = "${FS_LYRICS_ALIGNMENT}";
window.FS_AUTO_DJ_ENABLED = "${FS_AUTO_DJ_ENABLED}";
window.FS_AUTO_DJ_ITEM_COUNT = "${FS_AUTO_DJ_ITEM_COUNT}";
window.FS_AUTO_DJ_TIMING = "${FS_AUTO_DJ_TIMING}";
window.FS_CSS_CONTENT = "${FS_CSS_CONTENT}";
window.FS_CSS_ENABLED = "${FS_CSS_ENABLED}";
window.FS_FONT_TYPE = "${FS_FONT_TYPE}";
window.FS_FONT_BUILT_IN = "${FS_FONT_BUILT_IN}";
window.FS_FONT_SYSTEM = "${FS_FONT_SYSTEM}";
"use strict";window.SERVER_URL="${SERVER_URL}";window.SERVER_NAME="${SERVER_NAME}";window.SERVER_TYPE="${SERVER_TYPE}";window.SERVER_LOCK=${SERVER_LOCK};
+2 -7
View File
@@ -1,4 +1,4 @@
import { PostProcessorModule, TOptions } from 'i18next';
import { PostProcessorModule, StringMap, TOptions } from 'i18next';
import i18n from 'i18next';
import { initReactI18next } from 'react-i18next';
@@ -207,12 +207,7 @@ const ignoreSentenceCaseLanguages = ['de'];
const sentenceCasePostProcessor: PostProcessorModule = {
name: 'sentenceCase',
process: (
value: string,
_key: string,
_options: TOptions<Record<string, string>>,
translator: any,
) => {
process: (value: string, _key: string, _options: TOptions<StringMap>, translator: any) => {
const sentences = value.split('. ');
return sentences
+12 -23
View File
@@ -1,33 +1,27 @@
{
"action": {
"addToFavorites": "إضافة الى $t(entity.favorite, {\"count\": 2})",
"addToPlaylist": "إضافة الى $t(entity.playlist, {\"count\": 1})",
"addToFavorites": "إضافة الى $t(entity.favorite_other)",
"addToPlaylist": "إضافة الى $t(entity.playlist_one)",
"clearQueue": "مسح قائمة الإنتظار",
"createPlaylist": "إنشاء $t(entity.playlist, {\"count\": 1})",
"deletePlaylist": "حذف $t(entity.playlist, {\"count\": 1})",
"createPlaylist": "إنشاء $t(entity.playlist_one)",
"deletePlaylist": "حذف $t(entity.playlist_one)",
"deselectAll": "إلغاء تحديد الكل",
"editPlaylist": "تعديل $t(entity.playlist, {\"count\": 1})",
"editPlaylist": "تعديل $t(entity.playlist_one)",
"goToPage": "اذهب الى صفحة",
"moveToNext": "الذهاب الى التالي",
"moveToBottom": "الذهاب الى الأسفل",
"moveToTop": "الذهاب الى الأعلى",
"refresh": "$t(common.refresh)",
"removeFromFavorites": "حذف من $t(entity.favorite, {\"count\": 2})",
"removeFromPlaylist": "حذف من $t(entity.playlist, {\"count\": 1})",
"removeFromFavorites": "حذف من $t(entity.favorite_other)",
"removeFromPlaylist": "حذف من $t(entity.playlist_one)",
"removeFromQueue": "حذف من قائمة الإنتظار",
"setRating": "تحديد التقييم",
"toggleSmartPlaylistEditor": "تشغيل / إطفاء وضع التعديل لـ $t(entity.smartPlaylist)",
"viewPlaylists": "إظهار $t(entity.playlist, {\"count\": 2})",
"viewPlaylists": "إظهار $t(entity.playlist_other)",
"openIn": {
"lastfm": "فتح في Last.fm",
"musicbrainz": "فتح في MusicBrainz"
},
"addOrRemoveFromSelection": "إضافة أو إزالة من الإختيارات",
"selectRangeOfItems": "اختر مجموعة من العناصر",
"goToCurrent": "الانتقال إلى العنصر الحالي",
"createRadioStation": "يخلق $t(entity.radioStation, {\"count\": 1})",
"deleteRadioStation": "يمسح $t(entity.radioStation, {\"count\": 1})",
"selectAll": "تحديد الكل"
}
},
"common": {
"action_zero": "عملية",
@@ -65,7 +59,7 @@
"configure": "تعديل",
"confirm": "تأكيد",
"create": "إنشاء",
"currentSong": "$t(entity.track, {\"count\": 1}) الحالي",
"currentSong": "$t(entity.track_one) الحالي",
"decrease": "تنقيص",
"delete": "حذف",
"descending": "تنازلي",
@@ -108,7 +102,7 @@
"path": "المسار",
"playerMustBePaused": "يجب إيقاف المشغل",
"preview": "معاينة",
"previousSong": "$t(entity.track, {\"count\": 1}) السابق",
"previousSong": "$t(entity.track_one) السابق",
"quit": "خروج",
"random": "عشوائي",
"rating": "التقييم",
@@ -123,12 +117,7 @@
"saveAndReplace": "حفظ واستبدال",
"saveAs": "حفظ بإسم",
"search": "بحث",
"setting_zero": "إعداد",
"setting_one": "",
"setting_two": "",
"setting_few": "",
"setting_many": "",
"setting_other": "",
"setting": "إعداد",
"share": "نشر",
"size": "حجم",
"sortOrder": "الترتيب",
+109 -581
View File
@@ -2,55 +2,46 @@
"page": {
"sidebar": {
"myLibrary": "La meva llibreria",
"albumArtists": "$t(entity.albumArtist, {\"count\": 2})",
"albums": "$t(entity.album, {\"count\": 2})",
"artists": "$t(entity.artist, {\"count\": 2})",
"folders": "$t(entity.folder, {\"count\": 2})",
"genres": "$t(entity.genre, {\"count\": 2})",
"albumArtists": "$t(entity.albumArtist_other)",
"albums": "$t(entity.album_other)",
"artists": "$t(entity.artist_other)",
"folders": "$t(entity.folder_other)",
"genres": "$t(entity.genre_other)",
"home": "$t(common.home)",
"playlists": "$t(entity.playlist, {\"count\": 2})",
"playlists": "$t(entity.playlist_other)",
"search": "$t(common.search)",
"settings": "$t(common.setting, {\"count\": 2})",
"tracks": "$t(entity.track, {\"count\": 2})",
"nowPlaying": "s'està reproduint",
"shared": "$t(entity.playlist, {\"count\": 2}) compartides",
"favorites": "$t(entity.favorite, {\"count\": 2})",
"radio": "$t(entity.radioStation, {\"count\": 2})",
"collections": "col·leccions"
"settings": "$t(common.setting_other)",
"tracks": "$t(entity.track_other)",
"nowPlaying": "ara sona",
"shared": "$t(entity.playlist_other) compartida"
},
"albumArtistDetail": {
"relatedArtists": "$t(entity.artist, {\"count\": 2}) similars",
"viewAllTracks": "mostra totes les $t(entity.track, {\"count\": 2})",
"relatedArtists": "$t(entity.artist_other) similars",
"viewAllTracks": "veure totes les $t(entity.track_other)",
"about": "Sobre {{artist}}",
"appearsOn": "apareix a",
"recentReleases": "Llançaments recents",
"viewDiscography": "Mosta la discografia",
"topSongs": "millors cançons",
"topSongsFrom": "les millors cançons de {{title}}",
"viewAll": "mostra-ho tot",
"groupingTypeAll": "tots els tipus de llançaments",
"groupingTypePrimary": "tipus principals de llançament",
"favoriteSongs": "Cançons preferides",
"topSongsCommunity": "comunitat",
"topSongsPersonal": "personal",
"favoriteSongsFrom": "cançons preferides de {{title}}"
"viewAll": "mostra-ho tot"
},
"albumArtistList": {
"title": "$t(entity.albumArtist, {\"count\": 2})"
"title": "$t(entity.albumArtist_other)"
},
"albumDetail": {
"moreFromArtist": "més d'aquest $t(entity.artist, {\"count\": 1})",
"moreFromArtist": "més d'aquest $t(entity.artist_one)",
"moreFromGeneric": "més de {{item}}",
"released": "publicat"
},
"albumList": {
"title": "$t(entity.album, {\"count\": 2})",
"title": "$t(entity.album_other)",
"artistAlbums": "àlbums de {{artist}}",
"genreAlbums": "\"{{genre}}\" $t(entity.album, {\"count\": 2})"
"genreAlbums": "\"{{genre}}\" $t(entity.album_other)"
},
"appMenu": {
"quit": "$t(common.quit)",
"settings": "$t(common.setting, {\"count\": 2})",
"settings": "$t(common.setting_other)",
"goBack": "torna enrere",
"goForward": "avança",
"collapseSidebar": "replega la barra lateral",
@@ -60,11 +51,7 @@
"version": "versió {{version}}",
"openBrowserDevtools": "obre les eines de desenvolupament del navegador",
"privateModeOff": "desactiva el mode privat",
"privateModeOn": "activa el mode privat",
"commandPalette": "obre la paleta d'ordres",
"selectMusicFolder": "selecciona una carpeta de música",
"noMusicFolder": "no s'ha seleccionat cap carpeta de música",
"multipleMusicFolders": "{{count}} carpetes de música seleccionades"
"privateModeOn": "activa el mode privat"
},
"contextMenu": {
"addFavorite": "$t(action.addToFavorites)",
@@ -89,15 +76,13 @@
"showDetails": "informació",
"numberSelected": "{{count}} seleccionat",
"shareItem": "comparteix l'element",
"goToAlbumArtist": "Ves a $t(entity.albumArtist, {\"count\": 1})",
"goToAlbum": "ves a $t(entity.album, {\"count\": 1})",
"moveItems": "$t(action.moveItems)",
"goTo": "ves a"
"goToAlbumArtist": "Ves a $t(entity.albumArtist_one)",
"goToAlbum": "ves a $t(entity.album_one)"
},
"genreList": {
"title": "$t(entity.genre, {\"count\": 2})",
"showAlbums": "mostra $t(entity.album, {\"count\": 2}) de $t(entity.genre, {\"count\": 1})",
"showTracks": "mostra $t(entity.track, {\"count\": 2}) de $t(entity.genre, {\"count\": 1})"
"title": "$t(entity.genre_other)",
"showAlbums": "mostra $t(entity.album_other) $t(entity.genre_one)",
"showTracks": "mostra $t(entity.track_other) $t(entity.genre_one)"
},
"home": {
"title": "$t(common.home)",
@@ -105,16 +90,15 @@
"newlyAdded": "afegits recentment",
"mostPlayed": "els més reproduïts",
"recentlyPlayed": "reproduït recentment",
"recentlyReleased": "estrenat fa poc",
"genres": "$t(entity.genre, {\"count\": 2})"
"recentlyReleased": "estrenat fa poc"
},
"playlistList": {
"title": "$t(entity.playlist, {\"count\": 2})"
"title": "$t(entity.playlist_other)"
},
"trackList": {
"title": "$t(entity.track, {\"count\": 2})",
"title": "$t(entity.track_other)",
"artistTracks": "pistes de {{artist}}",
"genreTracks": "$t(entity.track, {\"count\": 2}) \"{{genre}}\""
"genreTracks": "\"{{genre}}\" $t(entity.track_other)"
},
"manageServers": {
"username": "nom d'usuari",
@@ -152,25 +136,7 @@
"generalTab": "general",
"hotkeysTab": "tecles d'accés ràpid",
"playbackTab": "reproducció",
"windowTab": "finestra",
"analytics": "analítiques",
"updates": "actualitza",
"cache": "memòria cau",
"application": "aplicació",
"queryBuilder": "constructor de consultes",
"theme": "tema",
"controls": "controls",
"sidebar": "barra lateral",
"remote": "remot",
"exportImport": "importa/exporta",
"scrobble": "scrobble",
"audio": "àudio",
"lyrics": "lletra",
"transcoding": "transcodificació",
"discord": "discord",
"logger": "registres",
"playerFilters": "filtres de reproducció",
"lyricsDisplay": "mostra la lletra"
"windowTab": "finestra"
},
"globalSearch": {
"commands": {
@@ -187,28 +153,6 @@
},
"playlist": {
"reorder": "el reordenament només s'activa quan s'ordena per id"
},
"favorites": {
"title": "$t(entity.favorite, {\"count\": 2})"
},
"folderList": {
"title": "$t(entity.folder, {\"count\": 2})"
},
"radioList": {
"title": "emissores de ràdio"
},
"windowBar": {
"paused": "(en pausa) ",
"privateMode": "(mode privat)"
},
"collections": {
"overrideExisting": "sobreescriu existents",
"saveAsCollection": "desa com a col·lecció"
},
"releasenotes": {
"commitsSinceStable": "commits des de {{stable}}",
"noNewCommits": "no hi ha hagut commits en aquest període",
"noStableReleaseToCompare": "no hi ha actualitzacions disponibles amb les quals comparar"
}
},
"common": {
@@ -280,9 +224,9 @@
"action_other": "accions",
"newVersion": "s'ha instal·lat una nova versió ({{version}})",
"viewReleaseNotes": "veure les notes de la versió",
"currentSong": "$t(entity.track, {\"count\": 1}) actual",
"currentSong": "$t(entity.track_one) actual",
"limit": "límit",
"previousSong": "$t(entity.track, {\"count\": 1}) anterior",
"previousSong": "$t(entity.track_one) anterior",
"trackNumber": "pista",
"albumGain": "guany de l'àlbum",
"albumPeak": "pic de l'àlbum",
@@ -306,9 +250,7 @@
"playerMustBePaused": "cal pausar el reproductor",
"restartRequired": "cal reiniciar",
"sampleRate": "freqüència de mostreig",
"setting_one": "configuració",
"setting_many": "configuracions",
"setting_other": "configuracions",
"setting": "configuració",
"trackGain": "guany de pista",
"trackPeak": "pic de pista",
"gap": "espera",
@@ -318,25 +260,7 @@
"private": "privat",
"public": "públic",
"recordLabel": "segell discogràfic",
"releaseType": "tipus de llançament",
"doNotShowAgain": "no tornis a mostrar això",
"view": "mostra",
"externalLinks": "enllaços externs",
"faster": "més ràpid",
"noFilters": "cap filtre configurat",
"slower": "més lent",
"sort": "ordre",
"gridRows": "files de la quadrícula",
"tableColumns": "columnes de la taula",
"itemsMore": "{{count}} més",
"countSelected": "{{count}} seleccionats",
"retry": "reintenta",
"example": "exemple",
"mood": "estat d'ànim",
"filter_single": "senzill",
"filter_multiple": "multi",
"rename": "reanomena",
"newVersionAvailable": "hi ha una nova versió disponible"
"releaseType": "tipus de llançament"
},
"entity": {
"album_one": "àlbum",
@@ -363,7 +287,7 @@
"playlistWithCount_one": "{{count}} llista de reproducció",
"playlistWithCount_many": "{{count}} llistes de reproducció",
"playlistWithCount_other": "{{count}} llistes de reproducció",
"smartPlaylist": "$t(entity.playlist, {\"count\": 1}) intel·ligent",
"smartPlaylist": "$t(entity.playlist_one) intel·ligent",
"play_one": "{{count}} reproducció",
"play_many": "{{count}} reproduccions",
"play_other": "{{count}} reproduccions",
@@ -390,44 +314,37 @@
"song_other": "cançons",
"favorite_one": "preferit",
"favorite_many": "preferits",
"favorite_other": "preferits",
"radioStation_one": "emissora de ràdio",
"radioStation_many": "emissores de ràdio",
"radioStation_other": "emissores de ràdio",
"radioStationWithCount_one": "{{count}} emissora de ràdio",
"radioStationWithCount_many": "{{count}} emissores de ràdio",
"radioStationWithCount_other": "{{count}} emissores de ràdio"
"favorite_other": "preferits"
},
"form": {
"addToPlaylist": {
"input_playlists": "$t(entity.playlist, {\"count\": 2})",
"title": "afegir a una $t(entity.playlist, {\"count\": 1})",
"input_playlists": "$t(entity.playlist_other)",
"title": "afegir a una $t(entity.playlist_one)",
"input_skipDuplicates": "salta't els duplicats",
"success": "s'ha afegit $t(entity.trackWithCount, {\"count\": {{message}} }) a $t(entity.playlistWithCount, {\"count\": {{numOfPlaylists}} })",
"create": "crea $t(entity.playlist, {\"count\": 1}) {{playlist}}",
"searchOrCreate": "cerca $t(entity.playlist, {\"count\": 2}) o escriu per crear-ne una de nova"
"create": "crea $t(entity.playlist_one) {{playlist}}",
"searchOrCreate": "cerca $t(entity.playlist_other) o tipus per crear-ne un de nou"
},
"createPlaylist": {
"input_description": "$t(common.description)",
"input_name": "$t(common.name)",
"input_owner": "$t(common.owner)",
"success": "$t(entity.playlist, {\"count\": 1}) s'ha creat amb èxit",
"title": "crea una $t(entity.playlist, {\"count\": 1})",
"success": "$t(entity.playlist_one) s'ha creat amb èxit",
"title": "crear una $t(entity.playlist_one)",
"input_public": "públic"
},
"deletePlaylist": {
"success": "$t(entity.playlist, {\"count\": 1}) s'ha eliminat amb èxit",
"title": "elimina la $t(entity.playlist, {\"count\": 1})",
"input_confirm": "escriviu el nom de la $t(entity.playlist, {\"count\": 1}) per confirmar"
"success": "$t(entity.playlist_one) s'ha eliminat amb èxit",
"title": "elimina la $t(entity.playlist_one)",
"input_confirm": "escriviu el nom de la $t(entity.playlist_one) per confirmar"
},
"editPlaylist": {
"success": "$t(entity.playlist, {\"count\": 1}) s'ha actualitzat amb èxit",
"title": "editar la $t(entity.playlist, {\"count\": 1})",
"publicJellyfinNote": "Per algun motiu, Jellyfin no exposa si una llista de reproducció és pública o no. Si voleu que es mantingui pública, seleccioneu la següent entrada",
"editNote": "es recomana no editar manualment les llistes de reproducció grans. segur que accepteu el risc de perdre dades si sobreescriviu la llista de reproducció existent?"
"success": "$t(entity.playlist_one) s'ha actualitzat amb èxit",
"title": "editar la $t(entity.playlist_one)",
"publicJellyfinNote": "Per algun motiu, Jellyfin no exposa si una llista de reproducció és pública o no. Si voleu que es mantingui pública, seleccioneu la següent entrada"
},
"lyricSearch": {
"input_artist": "$t(entity.artist, {\"count\": 1})",
"input_artist": "$t(entity.artist_one)",
"input_name": "$t(common.name)",
"title": "cerca de lletres"
},
@@ -444,10 +361,7 @@
"success": "servidor afegit correctament",
"title": "afegeix un servidor",
"input_preferInstantMix": "prefereix el mix instantani",
"input_preferInstantMixDescription": "utilitza només el mix instantani per obtenir cançons similars. útil si teniu complements que modifiquin aquest comportament",
"input_preferRemoteUrl": "prefereix l'url públic",
"input_remoteUrl": "url públic",
"input_remoteUrlPlaceholder": "opcional: url públic per característiques externes"
"input_preferInstantMixDescription": "utilitza només el mix instantani per obtenir cançons similars. útil si teniu complements que modifiquin aquest comportament"
},
"shareItem": {
"description": "descripció",
@@ -455,9 +369,7 @@
"setExpiration": "estableix expiració",
"success": "s'ha copiat l'enllaç de compartició al porta-retalls (o feu clic aquí per obrir-lo)",
"expireInvalid": "la data d'expiració ha de ser al futur",
"createFailed": "no s'ha pogut crear el recurs compartit (està habilitat, l'ús compartit?)",
"copyToClipboard": "Copiar al porta-retalls: Ctrl+C, Enter",
"successMustClick": "Compartició creada correctament. Feu clic aquí per obrir-la."
"createFailed": "no s'ha pogut crear el recurs compartit (està habilitat, l'ús compartit?)"
},
"updateServer": {
"success": "s'ha actualitzat el servidor amb èxit",
@@ -466,58 +378,24 @@
"queryEditor": {
"title": "editor de consultes",
"input_optionMatchAll": "coincidències totals",
"input_optionMatchAny": "coincidències parcials",
"addRuleGroup": "afegeix el grup de regles",
"removeRuleGroup": "elimina el grup de regles",
"resetToDefault": "reestableix als valors predeterminats",
"clearFilters": "neteja els filtres"
"input_optionMatchAny": "coincidències parcials"
},
"privateMode": {
"enabled": "mode privat actiu; l'estat de reproducció ara està ocult d'integracions externes",
"disabled": "mode privat inactiu; l'estat de reproducció ara és visible per les integracions externes",
"title": "mode privat"
},
"largeFetchConfirmation": {
"title": "afegeix elements a la cua",
"description": "Aquesta acció afegirà tots els elements a la vista filtrada actual"
},
"shuffleAll": {
"title": "reprodueix a l'atzar",
"input_genre": "$t(entity.genre, {\"count\": 1})",
"input_limit": "quantes cançons?",
"input_minYear": "de l'any",
"input_maxYear": "fins a l'any",
"input_played": "reprodueix el filtre",
"input_played_optionAll": "totes les pistes",
"input_played_optionUnplayed": "només les pistes sense reproduir",
"input_played_optionPlayed": "només les pistes reproduïdes"
},
"createRadioStation": {
"success": "emissora de ràdio creada amb èxit",
"title": "crea una emissora de ràdio",
"input_homepageUrl": "URL de la pàgina d'inici",
"input_name": "nom",
"input_streamUrl": "URL de transmissió"
},
"saveQueue": {
"success": "cua de reproducció desada al servidor"
},
"lyricsExport": {
"export": "exporta la lletra",
"input_synced": "exporta la lletra sincronitzada",
"input_offset": "$t(setting.lyricOffset)"
}
},
"action": {
"addToFavorites": "afegeix a $t(entity.favorite, {\"count\": 2})",
"addToPlaylist": "afegeix a $t(entity.playlist, {\"count\": 1})",
"createPlaylist": "crea $t(entity.playlist, {\"count\": 1})",
"deletePlaylist": "elimina la $t(entity.playlist, {\"count\": 1})",
"editPlaylist": "edita $t(entity.playlist, {\"count\": 1})",
"addToFavorites": "afegir als $t(entity.favorite_other)",
"addToPlaylist": "afegir a $t(entity.playlist_one)",
"createPlaylist": "crear $t(entity.playlist_one)",
"deletePlaylist": "elimina la $t(entity.playlist_one)",
"editPlaylist": "edita la $t(entity.playlist_one)",
"refresh": "$t(common.refresh)",
"removeFromFavorites": "elimina dels $t(entity.favorite, {\"count\": 2})",
"removeFromPlaylist": "elimina de $t(entity.playlist, {\"count\": 1})",
"clearQueue": "buida la cua",
"removeFromFavorites": "elimina dels $t(entity.favorite_other)",
"removeFromPlaylist": "elimina de $t(entity.playlist_one)",
"clearQueue": "buidar la cua",
"removeFromQueue": "treure de la cua",
"goToPage": "anar a la pàgina",
"openIn": {
@@ -525,29 +403,12 @@
"musicbrainz": "Obrir a MusicBrainz"
},
"deselectAll": "deselecciona-ho tot",
"viewPlaylists": "veure $t(entity.playlist, {\"count\": 2})",
"viewPlaylists": "veure$t(entity.playlist_other)",
"moveToNext": "passar al següent",
"moveToBottom": "anar al final",
"moveToTop": "anar al principi",
"setRating": "Qualifica",
"toggleSmartPlaylistEditor": "canvia l'editor $t(entity.smartPlaylist)",
"downloadStarted": "s'ha iniciat la descàrrega de {{count}} elements",
"moveUp": "mou amunt",
"moveDown": "mou avall",
"holdToMoveToTop": "mantingueu premut per moure al capdamunt",
"holdToMoveToBottom": "mantingueu premut per moure al capdavall",
"moveItems": "mou elements",
"shuffle": "mescla",
"shuffleAll": "mescla-ho tot",
"shuffleSelected": "mescla els seleccionats",
"viewMore": "mostra'n més",
"createRadioStation": "crea $t(entity.radioStation, {\"count\": 1})",
"deleteRadioStation": "elimina $t(entity.radioStation, {\"count\": 1})",
"addOrRemoveFromSelection": "afegeix o elimina de la selecció",
"selectRangeOfItems": "selecciona un interval d'elements",
"selectAll": "selecciona-ho tot",
"openApplicationDirectory": "obre el directori de l'aplicació",
"goToCurrent": "anar a l'element actual"
"toggleSmartPlaylistEditor": "canvia l'editor $t(entity.smartPlaylist)"
},
"setting": {
"language_description": "estableix l'idioma de l'aplicació ($t(common.restartRequired))",
@@ -555,14 +416,15 @@
"playButtonBehavior_optionAddNext": "$t(player.addNext)",
"playButtonBehavior_optionPlay": "$t(player.play)",
"playButtonBehavior_optionPlayShuffled": "$t(player.shuffle)",
"replayGainMode_optionAlbum": "$t(entity.album, {\"count\": 1})",
"replayGainMode_optionAlbum": "$t(entity.album_one)",
"replayGainMode_optionNone": "$t(common.none)",
"replayGainMode_optionTrack": "$t(entity.track, {\"count\": 1})",
"replayGainMode_optionTrack": "$t(entity.track_one)",
"font": "tipus de lletra",
"fontType": "selecció de tipus de lletra",
"fontType_optionBuiltIn": "tipus de lletra integrats",
"fontType_optionCustom": "tipus de lletra personalitzats",
"fontType_optionSystem": "tipus de lletra del sistema",
"disableAutomaticUpdates": "desactivar les actualitzacions automàtiques",
"disableLibraryUpdateOnStartup": "desactiva la comprovació de noves versions a l'inici",
"homeConfiguration": "configuració de la pàgina d'inici",
"sidebarConfiguration": "configuració de la barra lateral",
@@ -572,7 +434,7 @@
"sidePlayQueueStyle_optionAttached": "unida",
"sidePlayQueueStyle_optionDetached": "separada",
"audioDevice": "dispositiu d'àudio",
"audioDevice_description": "seleccioneu el dispositiu d'àudio que voleu utilitzar per a la reproducció",
"audioDevice_description": "seleccioneu el dispositiu d'àudio que voleu utilitzar per a la reproducció (només pel reproductor web)",
"audioPlayer": "reproductor d'àudio",
"audioPlayer_description": "seleccioneu el reproductor d'àudio que voleu utilitzar per a la reproducció",
"sidebarConfiguration_description": "selecciona els elements i l'ordre en què apareixen a la barra lateral",
@@ -618,9 +480,9 @@
"customFontPath_description": "estableix la ruta a una font personalitzada per utilitzar-la a l'aplicació",
"discordApplicationId": "id d'aplicació de {{discord}}",
"discordApplicationId_description": "l'id d'aplicació per l'estat d'activitat de {{discord}} (per defecte, {{defaultId}})",
"discordPausedStatus": "mostra l'estat d'activitat quan està en pausa",
"discordPausedStatus": "mosta l'estat d'activitat quan està en pausa",
"discordPausedStatus_description": "si està activat, l'estat es mostrarà quan el reproductor estigui pausat",
"discordIdleStatus": "mosta l'estat d'activitat quan està inactiu",
"discordIdleStatus": "mosta l'estat d'activitat en inactivitat",
"discordIdleStatus_description": "si està activat, s'actualitzarà l'estat mentre el reproductor estigui inactiu",
"discordListening": "mosta l'estat com escoltant",
"discordListening_description": "mosta l'estat com escoltant en comptes de jugant",
@@ -628,10 +490,14 @@
"discordServeImage": "serveix imatges de {{discord}} des del servidor",
"discordServeImage_description": "comparteix la caràtula per l'estat d'activitat de {{discord}} des del servidor; només disponible per Jellyfin i Navidrome. {{discord}} fa ser un bot per trobar les imatges, de manera que el vostre servidor ha de ser visible per l'internet públic",
"discordUpdateInterval": "interval d'actualització de l'estat d'activitat de {{discord}}",
"doubleClickBehavior": "posa en cua totes les pistes cercades en fer doble clic",
"doubleClickBehavior_description": "si està actiu, totes les pistes coincidents en una cerca de pistes es posaran a la cua. altrament, només la que seleccioneu s'afegirà a la cua",
"externalLinks": "mostra enllaços externs",
"externalLinks_description": "permet mostrar enllaços externs (Last.fm, MusicBrainz) a les pàgines d'artista/àlbum",
"exitToTray": "surt a la safata",
"exitToTray_description": "en sortir de l'aplicació, minimitza-la a la safa del sistema",
"floatingQueueArea": "mostra la zona flotant de la cua",
"floatingQueueArea_description": "mostra una icona flotant al costat dret de la pantalla per veure la cua de reproducció",
"followLyric": "segueix la lletra actual",
"followLyric_description": "desplaça la lletra a la posició de reproducció actual",
"preferLocalLyrics": "prefereix les lletres locals",
@@ -641,6 +507,8 @@
"gaplessAudio": "àudio sense pauses",
"gaplessAudio_description": "estableix la configuració d'àudio sense pauses per mpv",
"gaplessAudio_optionWeak": "feble (recomanat)",
"genreBehavior": "comportament predeterminat per les pàgines de gènere",
"genreBehavior_description": "determina si clicar sobre un gènere obre per defecte la llista de pistes o d'àlbums",
"globalMediaHotkeys": "tecles de drecera globals",
"globalMediaHotkeys_description": "activa o desactiva l'ús de les tecles multimèdia del sistema per controlar la reproducció",
"homeConfiguration_description": "configura quins objectes es mostren, i en quin ordre, a la pàgina d'inici",
@@ -686,7 +554,7 @@
"lyricFetch": "extreu la lletra d'internet",
"lyricFetch_description": "extreu la lletra de diverses fonts d'internet",
"lyricFetchProvider": "proveïdors de lletres",
"lyricFetchProvider_description": "selecciona els proveïdors de lletres",
"lyricFetchProvider_description": "selecciona els proveïdors de lletres. l'ordre en què apareixen és l'ordre en què es consultaran",
"lyricOffset": "desfasament de la lletra (ms)",
"lyricOffset_description": "desplaça la lletra els mil·lisegons especificats",
"minimizeToTray": "minimitza a la safata",
@@ -710,6 +578,8 @@
"playbackStyle_optionNormal": "normal",
"playButtonBehavior": "comportament del botó de reproducció",
"playButtonBehavior_description": "estableix el comportament predeterminat del botó de reproducció quan s'afegeixen cançons a la cua",
"playerAlbumArtResolution": "resolució de la caràtula de l'àlbum al reproductor",
"playerAlbumArtResolution_description": "la resolució de la previsualització gran de la caràtula al reproductor. si és més alta, serà més nítida, però es carregarà més lent. el valor predeterminat 0 vol dir automàtic",
"playerbarOpenDrawer": "activa el reproductor en pantalla completa",
"playerbarOpenDrawer_description": "permet fer clic a la barra de reproducció per obrir el reproductor de pantalla completa",
"remotePassword": "contrasenya del servidor de control remot",
@@ -792,9 +662,9 @@
"releaseChannel_optionLatest": "última versió",
"releaseChannel_optionBeta": "beta",
"releaseChannel": "canal de versions",
"releaseChannel_description": "trieu entre versions estables i beta o alfa (diàries) per les actualitzacions automàtiques",
"releaseChannel_description": "tria entre versions estables i versions beta per les actualitzacions automàtiques",
"mediaSession": "activa Media Session",
"mediaSession_description": "activa la integració amb Media Session per mostrar els controls multimèdia i les metadades a l'indicador de volum del sistema i la pantalla de bloqueig",
"mediaSession_description": "activa la integració amb Windows Media Session per mostrar els controls multimèdia i les metadades a l'indicador de volum del sistema i la pantalla de bloqueig (només per Windows)",
"crossfadeStyle": "estil de fosa encadenada",
"discordRichPresence": "estat d'activitat de {{discord}}",
"enableAutoTranslation_description": "activa la traducció automàtica en carregar la lletra",
@@ -809,118 +679,17 @@
"exportImportSettings_importSuccess": "la configuració s'ha importat correctament!",
"exportImportSettings_notValidJSON": "el fitxer que heu seleccionat no és un JSON vàlid",
"exportImportSettings_offendingKeyError": "\"{{offendingKey}}\" és incorrecte: {{reason}}",
"language": "llengua",
"notify": "activa les notificacions de cançons",
"notify_description": "mostra notificacions quan la cançó actual canviï",
"transcode": "activa la transcodificació",
"autoDJ": "DJ automàtic",
"autoDJ_description": "afegeix cançons similars a la cua automàticament",
"autoDJ_itemCount": "número d'elements",
"autoDJ_itemCount_description": "el nombre d'elements que s'intenten afegir a la cua quan el DJ automàtic està activat",
"autoDJ_timing": "temps",
"autoDJ_timing_description": "el nombre de cançons que han de quedar a la cua per activar el DJ automàtic",
"analyticsDisable": "Desactiva les analítiques basades en l'ús",
"analyticsDisable_description": "S'envien dades d'ús anonimitzades al desenvolupador per ajudar a millorar l'aplicació",
"followCurrentSong_description": "desplaça automàticament la cua de reproducció a la cançó en reproducció",
"followCurrentSong": "segueix la cançó actual",
"logLevel": "nivell de registre",
"logLevel_description": "estableix el nivell mínim de registre que s'ha de mostrar. debug mostra tots els missatges, error mostra només els errors",
"logLevel_optionDebug": "debug",
"logLevel_optionError": "error",
"logLevel_optionInfo": "info",
"logLevel_optionWarn": "avís",
"playerFilters": "filtra les cançons de la cua",
"playerFilters_description": "evita afegir cançons a la cua segons els següents criteris",
"playerbarSlider": "barra lliscadora de reproducció",
"playerbarSlider_description": "la forma d'ona no es recomana si utilitzeu una connexió d'internet lenta o mesurada",
"playerbarSliderType_optionSlider": "lliscador",
"playerbarSliderType_optionWaveform": "forma d'ona",
"playerbarWaveformAlign": "alineament de la forma d'ona",
"playerbarWaveformAlign_optionTop": "superior",
"playerbarWaveformAlign_optionCenter": "centrat",
"playerbarWaveformAlign_optionBottom": "inferior",
"playerbarWaveformBarWidth": "amplada de la forma d'ona",
"playerbarWaveformGap": "buits de la forma d'ona",
"playerbarWaveformRadius": "radi de la forma d'ona",
"showLyricsInSidebar_description": "s'afegirà un tauler a la cua de reproducció que mostra la lletra",
"showLyricsInSidebar": "mostra la lletra a la barra lateral del reproductor",
"showVisualizerInSidebar_description": "s'afegirà un tauler a la barra lateral de reproducció que mostra el visualitzador",
"showVisualizerInSidebar": "mostra el visualitzador a la barra laterla de reproducció",
"audioFadeOnStatusChange": "fosa d'àudio en canviar d'estat",
"audioFadeOnStatusChange_description": "activa la fosa de sortida i entrada en reproduir o pausar",
"queryBuilder": "constructor de consultes",
"queryBuilderCustomFields_inputLabel": "discogràfica",
"queryBuilderCustomFields_inputTag": "etiqueta",
"queryBuilderCustomFields": "camps personalitzats",
"queryBuilderCustomFields_description": "afegeix camps personalitzats pel constructor de consultes",
"useThemeAccentColor": "fes servir el color d'accent del tema",
"useThemeAccentColor_description": "fes servir el color primari definit pel tema seleccionat en comptes del color d'accent personalitzat",
"artistRadioCount_description": "estableix el número de cançons per cercar per la ràdio d'artista i pista",
"artistRadioCount": "recompte de ràdios d'artista o pista",
"imageResolution": "resolució d'imatge",
"imageResolution_description": "la resolució per les imatges que s'utilitzen a l'aplicació. un valor de 0 equival a la resolució nativa de la imatge",
"imageResolution_optionTable": "taula",
"imageResolution_optionItemCard": "targeta d'element",
"imageResolution_optionSidebar": "tauler lateral",
"imageResolution_optionHeader": "encapçalament",
"imageResolution_optionFullScreenPlayer": "reproductor de pantalla completa",
"showRatings_description": "controla si es mostren les estrelles de valoració a la interfície",
"showRatings": "mostra la valoració d'estrelles",
"combinedLyricsAndVisualizer_description": "combina la lletra i el visualitzador en un sol tauler",
"combinedLyricsAndVisualizer": "combina la lletra i el visualitzador al tauler lateral del reproductor",
"artistReleaseTypeConfiguration": "configuració de tipus de llançament d'artista",
"artistReleaseTypeConfiguration_description": "configura quins llançaments es mostren, i en quin ordre, a la pàgina d'artista de l'àlbum",
"hotkey_listNavigateToPage": "navega per la llista fins a la pàgina de l'element",
"hotkey_listPlayDefault": "reprodueix llista",
"hotkey_listPlayLast": "reprodueix la llista al final",
"hotkey_listPlayNext": "reprodueix la llista a continuació",
"hotkey_listPlayNow": "reprodueix la llista ara",
"mpvExtraParameters": "paràmetres addicionals d'mpv",
"mpvExtraParameters_description": "arguments addicionals per l'mpv",
"pathReplace": "substitució de la ruta de l'arxiu",
"pathReplace_description": "substitueix la ruta d'arxiu predeterminada del servidor",
"pathReplace_optionRemovePrefix": "elimina el prefix",
"pathReplace_optionAddPrefix": "afegeix prefix",
"homeFeatureStyle_description": "controla l'estil del carrusel de destacats de l'inici",
"homeFeatureStyle": "estil del carrusel de destacats de l'inici",
"homeFeatureStyle_optionMultiple": "múltiple",
"homeFeatureStyle_optionSingle": "simple",
"enableGridMultiSelect": "activa la selecció múltiple de quadrícula",
"enableGridMultiSelect_description": "quan està activada, podeu seleccionar més d'un element en la vista de quadrícula; si feu clic en la imatge d'un element de la quadrícula, accedireu a la pàgina de l'element",
"sidebarPlaylistSorting_description": "permet ordenar manualment les llistes de reproducció a la barra lateral arrossegant amb el ratolí en comptes de seguir l'ordre predeterminat del servidor",
"sidebarPlaylistSorting": "ordenació de llistes de reproducció de la barra lateral",
"sidebarPlaylistListFilterRegex_description": "amaga les llistes de reproducció de la barra lateral que coincideixin amb aquesta expressió regular",
"sidebarPlaylistListFilterRegex_placeholder": "ex. ^Mescla diària.*",
"sidebarPlaylistListFilterRegex": "regex pel filtre de llistes",
"analyticsEnable": "envia analítiques basades en l'ús",
"analyticsEnable_description": "s'envien dades d'ús anonimitzades al desenvolupar per ajudar a millorar l'aplicació",
"automaticUpdates": "actualitzacions automàtiques",
"automaticUpdates_description": "cerca i instal·la actualitzacions automàticament",
"releaseChannel_optionAlpha": "alfa (diària)",
"blurExplicitImages": "desenfoca imatges explícites",
"blurExplicitImages_description": "les caràtules d'àlbums i cançons marcades com a explícites quedaran desenfocades",
"discordStateIcon": "mostra la icona de reproducció",
"discordStateIcon_description": "mostra una petita icona de reproducció a l'estat d'activitat. l'icona de pausa es mostra quan \"mostra l'estat d'activitat quan està en pausa\" està activat",
"autosave": "desa automàticament la cua de reproducció",
"autosave_description": "activa el desament automàtic de la cua de reproducció al teu servidor. això només és possible quan s'utilitza Navidrome/Subsonic i no es pot tenir una cua de reproducció mixta.",
"autosaveCount": "freqüència de desament de cua de reproducció automàtica",
"autosaveCount_description": "quants canvis de pista abans que es desi la cua. 1 (mínim) significa cada canvi de cançó",
"useThemePrimaryShade": "utilitza l'ombra primària del tema",
"useThemePrimaryShade_description": "utilitza el to primari definit al tema seleccionat per a les variants de color primari",
"primaryShade": "ombra primària",
"primaryShade_description": "substitueix el to primari (09) utilitzat per a botons, enllaços i altres elements de color primari",
"playerItemConfiguration_description": "configurar quins elements es mostren i en quin ordre al reproductor de pantalla completa",
"playerItemConfiguration": "configuració d'elements del jugador"
"language": "llengua"
},
"table": {
"column": {
"albumCount": "$t(entity.album, {\"count\": 2})",
"artist": "$t(entity.artist, {\"count\": 1})",
"channels": "$t(common.channel, {\"count\": 2})",
"albumCount": "$t(entity.album_other)",
"artist": "$t(entity.artist_one)",
"channels": "$t(common.channel_other)",
"codec": "$t(common.codec)",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"size": "$t(common.size)",
"songCount": "$t(entity.track, {\"count\": 2})",
"songCount": "$t(entity.track_other)",
"releaseYear": "any",
"playCount": "reproduccions",
"releaseDate": "data de llançament",
@@ -937,10 +706,7 @@
"lastPlayed": "última reproducció",
"path": "ruta",
"rating": "qualificació",
"title": "títol",
"bitDepth": "$t(common.bitDepth)",
"sampleRate": "$t(common.sampleRate)",
"owner": "propietari"
"title": "títol"
},
"config": {
"general": {
@@ -951,49 +717,27 @@
"displayType": "tipus de visualització",
"itemGap": "espai entre elements (px)",
"itemSize": "mida dels elements (px)",
"tableColumns": "columnes de la taula",
"advancedSettings": "opcions avançades",
"autosize": "dimensions automàtiques",
"moveUp": "mou amunt",
"moveDown": "mou avall",
"pinToLeft": "ancora a l'esquerra",
"pinToRight": "ancora a la dreta",
"alignLeft": "alinea a l'esquerra",
"alignCenter": "alinea al centre",
"alignRight": "alinea a la dreta",
"itemsPerRow": "elements per fila",
"size_default": "predeterminat",
"size_compact": "compacte",
"size_large": "gran",
"pagination": "paginació",
"pagination_itemsPerPage": "elements per pàgina",
"pagination_infinite": "infinita",
"pagination_paginate": "paginada",
"alternateRowColors": "colors de fila alternants",
"horizontalBorders": "vores de fila",
"rowHoverHighlight": "ressalta en passar el cursor per la fila",
"verticalBorders": "vores de columna",
"showHeader": "mostra l'encapçalament"
"tableColumns": "columnes de la taula"
},
"label": {
"actions": "$t(common.action, {\"count\": 2})",
"album": "$t(entity.album, {\"count\": 1})",
"albumArtist": "$t(entity.albumArtist, {\"count\": 1})",
"artist": "$t(entity.artist, {\"count\": 1})",
"actions": "$t(common.action_other)",
"album": "$t(entity.album_one)",
"albumArtist": "$t(entity.albumArtist_one)",
"artist": "$t(entity.artist_one)",
"biography": "$t(common.biography)",
"bitrate": "$t(common.bitrate)",
"bpm": "$t(common.bpm)",
"channels": "$t(common.channel, {\"count\": 2})",
"channels": "$t(common.channel_other)",
"codec": "$t(common.codec)",
"duration": "$t(common.duration)",
"favorite": "$t(common.favorite)",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"note": "$t(common.note)",
"owner": "$t(common.owner)",
"path": "$t(common.path)",
"rating": "$t(common.rating)",
"size": "$t(common.size)",
"songCount": "$t(entity.track, {\"count\": 2})",
"songCount": "$t(entity.track_other)",
"title": "$t(common.title)",
"year": "$t(common.year)",
"playCount": "compte de reproduccions",
@@ -1003,21 +747,14 @@
"discNumber": "número de disc",
"lastPlayed": "última reproducció",
"rowIndex": "índex de files",
"titleCombined": "$t(common.title) (combinat)",
"albumCount": "$t(entity.album, {\"count\": 2})",
"bitDepth": "$t(common.bitDepth)",
"genreBadge": "$t(entity.genre, {\"count\": 1}) (insígnies)",
"image": "imatge",
"sampleRate": "$t(common.sampleRate)",
"composer": "compositor",
"titleArtist": "$t(common.title) (artista)",
"albumGroup": "grup d'àlbums"
"titleCombined": "$t(common.title) (combinat)"
},
"view": {
"table": "taula",
"card": "targeta",
"grid": "quadrícula",
"list": "llista",
"detail": "detall"
"poster": "pòster"
}
}
},
@@ -1025,17 +762,17 @@
"fromYear": "des de l'any",
"releaseYear": "any de llançament",
"toYear": "fins a l'any",
"album": "$t(entity.album, {\"count\": 1})",
"albumArtist": "$t(entity.albumArtist, {\"count\": 1})",
"artist": "$t(entity.artist, {\"count\": 1})",
"album": "$t(entity.album_one)",
"albumArtist": "$t(entity.albumArtist_one)",
"artist": "$t(entity.artist_one)",
"biography": "biografia",
"bitrate": "taxa de bits",
"bpm": "bpm",
"channels": "$t(common.channel, {\"count\": 2})",
"channels": "$t(common.channel_other)",
"comment": "comentari",
"disc": "disc",
"duration": "durada",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"id": "identificador",
"name": "nom",
"note": "nota",
@@ -1054,7 +791,7 @@
"recentlyAdded": "afegit recentment",
"recentlyPlayed": "reproduït recentment",
"recentlyUpdated": "actualitzat recentment",
"albumCount": "nombre de $t(entity.album, {\"count\": 2})",
"albumCount": "nombre de $t(entity.album_other)",
"favorited": "preferits",
"isCompilation": "és una compilació",
"isFavorited": "és un preferit",
@@ -1064,10 +801,7 @@
"lastPlayed": "última reproducció",
"path": "ruta",
"songCount": "nombre de cançons",
"explicitStatus": "$t(common.explicitStatus)",
"sortName": "ordena per nom",
"matchAnd": "i",
"matchOr": "o"
"explicitStatus": "$t(common.explicitStatus)"
},
"player": {
"muted": "silenciat",
@@ -1082,10 +816,10 @@
"playSimilarSongs": "reproduir cançons similars",
"repeat_off": "repetició desactivada",
"repeat_all": "repetició",
"shuffle": "reprodueix (mesclat)",
"shuffle": "reproducció aleatòria",
"shuffle_off": "reproducció aleatòria desactivada",
"addLast": "al final",
"addNext": "a continuació",
"addLast": "afegeix al final",
"addNext": "afegeix a continuació",
"favorite": "marcar com a preferida",
"mute": "silencia",
"next": "següent",
@@ -1100,25 +834,7 @@
"skip_forward": "salta endavant",
"toggleFullscreenPlayer": "activa el reproductor de pantalla completa",
"unfavorite": "elimina de preferits",
"pause": "pausa",
"addLastShuffled": "al final (mesclat)",
"addNextShuffled": "a continuació (mesclat)",
"holdToShuffle": "mantén premut per mesclar",
"lyrics": "lletra",
"restoreQueueFromServer": "restaura la cua del servidor",
"saveQueueToServer": "desa la cua al servidor",
"artistRadio": "ràdio de l'artista",
"trackRadio": "ràdio de la pista",
"sleepTimer": "temporitzador d'adormir",
"sleepTimer_endOfSong": "final de la cançó actual",
"sleepTimer_minutes": "{{count}} min",
"sleepTimer_hours": "{{count}} h",
"sleepTimer_custom": "personalitzat",
"sleepTimer_off": "apagat",
"sleepTimer_timeRemaining": "queden {{time}}",
"sleepTimer_setCustom": "configura el temporitzador",
"sleepTimer_cancel": "cancel·la el temporitzador",
"albumRadio": "ràdio d'àlbums"
"pause": "pausa"
},
"error": {
"credentialsRequired": "credencials requerides",
@@ -1144,19 +860,11 @@
"notificationDenied": "s'han negat els permisos per enviar notificacions. aquesta opció no té cap efecte",
"playbackError": "hi ha hagut un error en intentar reproduir el mitjà",
"remoteDisableError": "hi ha hagut un error en intentar $t(common.disable) el servidor remot",
"endpointNotImplementedError": "el punt final {{endpoint}} no està implementat per {{serverType}}",
"multipleServerSaveQueueError": "la cua de reproducció té una o més cançons que no són del servidor actual, cosa que no és compatible",
"saveQueueFailed": "error en desar la cua",
"settingsSyncError": "hi ha discrepàncies entre la configuració del renderitzador i el procés principal. reinicieu l'aplicació per aplicar els canvis",
"noNetwork": "servidor no disponible",
"noNetworkDescription": "no s'ha pogut connectar amb el servidor",
"invalidJson": "JSON invàlid",
"serverLockSingleServer": "només es permet un servidor quan el servidor està bloquejat",
"playbackPausedDueToError": "la reproducció s'ha pausat a causa d'un error"
"endpointNotImplementedError": "el punt final {{endpoint}} no està implementat per {{serverType}}"
},
"releaseType": {
"primary": {
"album": "$t(entity.album, {\"count\": 1})",
"album": "$t(entity.album_one)",
"broadcast": "emissió",
"ep": "EP",
"other": "altres",
@@ -1181,185 +889,5 @@
"error_oneFileOnly": "Seleccioneu un sol fitxer",
"error_readingFile": "hi ha hagut un error en llegir el fitxer: {{errorMessage}}",
"mainText": "deixeu anar un fitxer aquí"
},
"filterOperator": {
"after": "és posterior",
"afterDate": "és posterior a (data)",
"before": "és anterior",
"beforeDate": "és anterior a (data)",
"contains": "conté",
"endsWith": "acaba en",
"inPlaylist": "és a",
"inTheLast": "és a l'últim",
"inTheRange": "és entre",
"inTheRangeDate": "és entre (data)",
"is": "és",
"isNot": "no és",
"isGreaterThan": "és més gran que",
"isLessThan": "és més petit que",
"matchesRegex": "coincideix amb l'expressió regular",
"notContains": "no conté",
"notInPlaylist": "no és a",
"notInTheLast": "no és a l'últim",
"startsWith": "comença amb"
},
"queryBuilder": {
"standardTags": "etiquetes estàndard",
"customTags": "etiquetes personalitzades"
},
"datetime": {
"minuteShort": "min",
"secondShort": "s",
"hourShort": "h",
"dayShort": "d"
},
"visualizer": {
"visualizerType": "tipus de visualitzador",
"cyclePresets": "opcions preconfigurades",
"cycleTime": "duració d'un cicle (segons)",
"includeAllPresets": "inclou totes les opcions predeterminades",
"ignoredPresets": "ignora les opcions predeterminades",
"selectedPresets": "opcions predeterminades seleccionades",
"randomizeNextPreset": "tria la següent opcions predeterminada a l'atzar",
"blendTime": "duració de la mescla",
"presets": "opcions predeterminades",
"selectPreset": "selecciona una opció predeterminada",
"applyPreset": "aplica l'opció predeterminada",
"saveAsPreset": "desa com a opció predeterminada",
"updatePreset": "actualitza l'opció predeterminada",
"copyConfiguration": "copia la configuració",
"pasteConfiguration": "enganxa la configuració",
"pasteConfigurationPlaceholder": "enganxa la configuració JSON aquí...",
"pasteFromClipboard": "enganxa des del portaretalls",
"applyConfiguration": "aplica la configuració",
"configCopied": "configuració copiada al portaretalls",
"configCopyFailed": "error en copiar la configuració",
"configPasted": "configuració aplicada correctament",
"configPasteFailed": "Error en aplicar la configuració. Reviseu-ne el format.",
"configPasteReadFailed": "Error en llegir del portaretalls",
"presetName": "Nom de l'opció predeterminada",
"presetNamePlaceholder": "Escriviu el nom de l'opció predeterminada",
"general": "General",
"mode": "Mode",
"mode1To8": "Mode 1 - 8",
"mode10": "Mode 10",
"barSpace": "Espai entre barres",
"lineWidth": "Amplitud de línia",
"fillAlpha": "Omplir alfa",
"channelLayout": "Disseny del canal",
"maxFPS": "FPS màxims",
"opacity": "Opacitat",
"customGradients": "Degradats personalitzats",
"addCustomGradient": "Afegeix un degradat personalitzat",
"gradientName": "Nom del degradat",
"gradientNamePlaceholder": "Nom del degradat",
"vertical": "Vertical",
"horizontal": "Horitzontal",
"colorStops": "Parades de color",
"addColor": "Afegeix el color",
"position": "Posició",
"level": "Nivell",
"remove": "Elimina",
"custom": "Personalitzat",
"builtIn": "Integrat",
"colors": "Colors",
"colorMode": "Mode de color",
"gradient": "Degradat",
"gradientLeft": "Esquerra del degradat",
"gradientRight": "Dreta del degradat",
"fft": "FFT",
"fftSize": "Mida del FFT",
"smoothing": "Suavitzador",
"frequencyRangeAndScaling": "Escala i rang de freqüència",
"minimumFrequency": "Freqüència mínima",
"maximumFrequency": "Freqüència màxima",
"frequencyScale": "Escala de freqüència",
"sensitivity": "Sensibilitat",
"weightingFilter": "Filtre de pes",
"minimumDecibels": "Decibels mínims",
"maximumDecibels": "Decibels màxims",
"linearAmplitude": "Amplitud lineal",
"linearBoost": "Augment lineal",
"peakBehavior": "Comportament del pic",
"showPeaks": "Mostra els pics",
"fadePeaks": "Pics de fosa",
"peakLine": "Línea del pic",
"gravity": "Gravetat",
"peakFadeTime": "Temps de fosa del pic (ms)",
"peakHoldTime": "Temps d'espera del pic (ms)",
"radialSpectrum": "Espectre radial",
"radial": "Radial",
"radialInvert": "Invertir el radial",
"spinSpeed": "Velocitat de gir",
"radius": "Radi",
"reflexMirror": "Mirall del reflex",
"reflexFit": "Ajustament del reflex",
"reflexRatio": "Proporció del reflex",
"reflexAlpha": "Alfa del reflex",
"reflexBrightness": "Brillantor del reflex",
"mirror": "Mirall",
"miscellaneousSettings": "Configuració miscel·lànea",
"alphaBars": "Barres alfa",
"ansiBands": "Bandes ANSI",
"ledBars": "Barres LED",
"trueLeds": "LEDs reals",
"lumiBars": "Barres Lumi",
"outlineBars": "Barres de vora",
"roundBars": "Barres arrodonides",
"lowResolution": "Baixa resolució",
"splitGradient": "Degradat dividit",
"showFPS": "Mostra els FPS",
"showScaleX": "Mostra l'escala X",
"noteLabels": "Etiquetes de nota",
"showScaleY": "Mostra l'escala Y",
"options": {
"colorMode": {
"gradient": "Degradat",
"barIndex": "Índex de barra",
"barLevel": "Nivell de barra"
},
"gradient": {
"classic": "Classic",
"prism": "Prisme",
"rainbow": "Arc de Sant Martí",
"steelblue": "Blau d'acer",
"orangered": "Vermell ataronjat"
},
"channelLayout": {
"single": "Únic",
"dualCombined": "Dual-Combinat",
"dualHorizontal": "Dual-Horitzontal",
"dualVertical": "Dual-Vertical"
},
"frequencyScale": {
"bark": "Escala Bark",
"linear": "Escala Lineal",
"log": "Escala logarítmica",
"mel": "Escala Mel",
"none": "Cap"
},
"weightingFilter": {
"none": "Cap",
"a": "A",
"b": "B",
"c": "C",
"d": "D",
"z": "Z"
},
"mode": {
"0": "[0] Freqüències discretes",
"1": "[1] 1/24a octava / 240 bandes",
"2": "[2] 1/12a octava / 120 bandes",
"3": "[3] 1/8a octava / 80 bandes",
"4": "[4] 1/6a octava / 60 bandes",
"5": "[5] 1/4a octava / 40 bandes",
"6": "[6] 1/3a octava / 30 bandes",
"7": "[7] Mitja octava / 20 bandes",
"8": "[8] Octava completa / 10 bandes",
"10": "[10] Línia / Gràfic d'àrea"
}
},
"pasteGradient": "enganxa degradat",
"pasteGradientPlaceholder": "enganxa el degradat JSON aquí..."
}
}
+116 -588
View File
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+167 -703
View File
File diff suppressed because it is too large Load Diff
+96 -565
View File
File diff suppressed because it is too large Load Diff
+121 -593
View File
File diff suppressed because it is too large Load Diff
+91 -416
View File
@@ -1,39 +1,27 @@
{
"action": {
"deselectAll": "deshautatu dena",
"editPlaylist": "editatu $t(entity.playlist, {\"count\": 1})",
"editPlaylist": "editatu $t(entity.playlist_one)",
"goToPage": "joan orrira",
"moveToNext": "mugitu hurrengora",
"moveToBottom": "mugitu behera",
"moveToTop": "mugitu gora",
"refresh": "$t(common.refresh)",
"removeFromFavorites": "kendu gogokoetatik",
"removeFromPlaylist": "kendu $t(entity.playlist, {\"count\": 1})-(e)tik",
"removeFromFavorites": "kendu $t(entity.favorite_other)-(e)tik",
"removeFromPlaylist": "kendu $t(entity.playlist_one)-(e)tik",
"removeFromQueue": "kendu ilaratik",
"setRating": "ezarri balorazioa",
"toggleSmartPlaylistEditor": "txandakatu $t(entity.smartPlaylist) editorea",
"viewPlaylists": "ikusi $t(entity.playlist, {\"count\": 2})",
"viewPlaylists": "ikusi $t(entity.playlist_other)",
"openIn": {
"lastfm": "Ireki Last.fm-n",
"musicbrainz": "Ireki MusicBrainz-en"
},
"clearQueue": "garbitu ilara",
"createPlaylist": "sortu $t(entity.playlist, {\"count\": 1})",
"deletePlaylist": "ezabatu $t(entity.playlist, {\"count\": 1})",
"addToFavorites": "gehitu gogokoetara",
"addToPlaylist": "gehitu $t(entity.playlist, {\"count\": 1})ra",
"createRadioStation": "sortu $t(entity.radioStation, {\"count\": 1})",
"deleteRadioStation": "ezabatu $t(entity.radioStation, {\"count\": 1})",
"viewMore": "ikusi gehiago",
"shuffle": "nahastu",
"selectAll": "aukeratu guztiak",
"downloadStarted": "{{count}} elementuren deskarga hasi da",
"addOrRemoveFromSelection": "gehitu edo kendu hautapenetik",
"selectRangeOfItems": "aukeratu elementu sorta bat",
"shuffleAll": "nahastu dena",
"shuffleSelected": "nahastu aukeratutak",
"moveItems": "elementuak mugitu",
"openApplicationDirectory": "ireki aplikazioaren direktorioa"
"createPlaylist": "sortu $t(entity.playlist_one)",
"deletePlaylist": "ezabatu $t(entity.playlist_one)",
"addToFavorites": "gehitu $t(entity.favorite_other)-(e)ra",
"addToPlaylist": "gehitu $t(entity.playlist_one)-(e)ra"
},
"common": {
"add": "gehitu",
@@ -50,7 +38,7 @@
"configure": "konfiguratu",
"confirm": "berretsi",
"create": "sortu",
"currentSong": "uneko $t(entity.track, {\"count\": 1})",
"currentSong": "uneko $t(entity.track_one)",
"decrease": "gutxitu",
"delete": "ezabatu",
"descending": "beheranzkoa",
@@ -67,8 +55,7 @@
"filter_other": "iragazkiak",
"filters": "iragazkiak",
"forceRestartRequired": "berreabiarazi aldaketak aplikatzeko... itxi notifikazioa berreabiarazteko",
"setting_one": "ezarpenak",
"setting_other": "",
"setting": "ezarpena",
"share": "partekatu",
"action_one": "ekintza",
"action_other": "ekintzak",
@@ -104,7 +91,7 @@
"path": "bidea",
"playerMustBePaused": "erreproduzitzailea pausatuta egon behar da",
"preview": "aurrebista",
"previousSong": "aurreko $t(entity.track, {\"count\": 1})",
"previousSong": "aurreko $t(entity.track_one)",
"quit": "irten",
"random": "ausazkoa",
"rating": "balorazioa",
@@ -137,20 +124,7 @@
"clean": "garbia",
"private": "pribatua",
"public": "publikoa",
"releaseType": "argitalpen mota",
"countSelected": "{{count}} hautatuta",
"view": "ikuspegia",
"externalLinks": "kanpoko estekak",
"faster": "azkarrago",
"noFilters": "ez dago iragazkirik konfiguratuta",
"retry": "saiatu berriro",
"slower": "motelago",
"itemsMore": "{{count}} gehiago",
"sort": "ordenatu",
"recordLabel": "diskoetxea",
"example": "adibidea",
"tableColumns": "taulako zutabeak",
"doNotShowAgain": "ez erakutsi hau berriro"
"releaseType": "argitalpen mota"
},
"player": {
"repeat": "errepikatu",
@@ -177,53 +151,35 @@
"queue_remove": "kendu hautatutakoak",
"repeat_all": "errepikatu dena",
"repeat_off": "errepikapena desgaituta",
"shuffle": "erreproduzitu (ausaz)",
"shuffle": "erreproduzitu ausaz",
"shuffle_off": "auza desgaituta",
"skip_back": "saltatu atzeraka",
"skip_forward": "saltatu aurreraka",
"toggleFullscreenPlayer": "txandakatu pantaila osoko erreproduzitzailea",
"viewQueue": "ikusi ilara",
"playbackFetchCancel": "honek denbora pixka bat behar du... itxi jakinarazpena bertan behera uzteko",
"lyrics": "letrak",
"restoreQueueFromServer": "berrezarri ilara zerbitzaritik",
"saveQueueToServer": "gorde ilara zerbitzarira",
"addLastShuffled": "azkena (ausaz)",
"addNextShuffled": "hurrengoa (ausaz)",
"artistRadio": "artista irratia",
"trackRadio": "pista irratia"
"playbackFetchCancel": "honek denbora pixka bat behar du... itxi jakinarazpena bertan behera uzteko"
},
"table": {
"config": {
"view": {
"table": "taula",
"list": "zerrenda",
"grid": "sareta"
"card": "txartela",
"grid": "sareta",
"poster": "kartela"
},
"general": {
"gap": "$t(common.gap)",
"size": "$t(common.size)",
"tableColumns": "taula zutabeak",
"itemSize": "elementuaren tamaina (px)",
"followCurrentSong": "jarraitu uneko abestia",
"size_default": "lehenetsia",
"advancedSettings": "ezarpen aurreratuak",
"autoFitColumns": "zutabeak automatikoki doitu",
"pinToLeft": "ezkerrera finkatu",
"pinToRight": "eskuinera finkatu",
"alignLeft": "ezkerrean lerrokatu",
"alignCenter": "lerrokatu erdian",
"alignRight": "eskuinean lerrokatu",
"itemGap": "elementuen arteko tartea (px)",
"itemsPerRow": "elementuak errenkada bakoitzeko",
"size_large": "handia",
"pagination_itemsPerPage": "elementuak orrialde bakoitzeko",
"pagination_infinite": "infinitua"
"followCurrentSong": "jarraitu uneko abestia"
},
"label": {
"actions": "$t(common.action_other)",
"album": "$t(entity.album, {\"count\": 1})",
"albumArtist": "$t(entity.albumArtist, {\"count\": 1})",
"artist": "$t(entity.artist, {\"count\": 1})",
"album": "$t(entity.album_one)",
"albumArtist": "$t(entity.albumArtist_one)",
"artist": "$t(entity.artist_one)",
"biography": "$t(common.biography)",
"bitrate": "$t(common.bitrate)",
"bpm": "$t(common.bpm)",
@@ -231,13 +187,13 @@
"codec": "$t(common.codec)",
"duration": "$t(common.duration)",
"favorite": "$t(common.favorite)",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"note": "$t(common.note)",
"owner": "$t(common.owner)",
"path": "$t(common.path)",
"rating": "$t(common.rating)",
"size": "$t(common.size)",
"songCount": "$t(entity.track, {\"count\": 2})",
"songCount": "$t(entity.track_other)",
"title": "$t(common.title)",
"year": "$t(common.year)",
"titleCombined": "$t(common.title) (batuta)",
@@ -245,29 +201,25 @@
"playCount": "erreprodukzio kopurua",
"lastPlayed": "azken aldiz entzunda",
"discNumber": "disko zenbakia",
"dateAdded": "gehitze data",
"albumCount": "$t(entity.album, {\"count\": 2})",
"image": "irudia",
"bitDepth": "$t(common.bitDepth)",
"sampleRate": "$t(common.sampleRate)"
"dateAdded": "gehitze data"
}
},
"column": {
"album": "albuma",
"albumCount": "$t(entity.album, {\"count\": 2})",
"artist": "$t(entity.artist, {\"count\": 1})",
"albumCount": "$t(entity.album_other)",
"artist": "$t(entity.artist_one)",
"biography": "biografia",
"bitrate": "bit-emaria",
"channels": "$t(common.channel_other)",
"codec": "$t(common.codec)",
"discNumber": "diskoa",
"favorite": "gogokoa",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"path": "bidea",
"rating": "balorazioa",
"releaseYear": "urtea",
"size": "$t(common.size)",
"songCount": "$t(entity.track, {\"count\": 2})",
"songCount": "$t(entity.track_other)",
"title": "tituloa",
"trackNumber": "pista",
"bpm": "bpm",
@@ -276,10 +228,7 @@
"releaseDate": "argitalpen data",
"lastPlayed": "azken aldiz entzundakoa",
"dateAdded": "gehitutako data",
"albumArtist": "albumeko artista",
"owner": "jabea",
"bitDepth": "$t(common.bitDepth)",
"sampleRate": "$t(common.sampleRate)"
"albumArtist": "albumeko artista"
}
},
"entity": {
@@ -311,17 +260,13 @@
"play_other": "{{count}} erreprodukzio",
"playlistWithCount_one": "erreprodukzio-zerrenda {{count}}",
"playlistWithCount_other": "{{count}} erreprodukzio-zerrenda",
"smartPlaylist": "$t(entity.playlist, {\"count\": 1}) adimentsua",
"smartPlaylist": "$t(entity.playlist_one) adimentsua",
"track_one": "pista",
"track_other": "pistak",
"song_one": "abestia",
"song_other": "abestiak",
"trackWithCount_one": "pista {{count}}",
"trackWithCount_other": "{{count}} pista",
"radioStation_one": "irrati-katea",
"radioStation_other": "irrati-kateak",
"radioStationWithCount_one": "irrati-kate {{count}}",
"radioStationWithCount_other": "{{count}} irrati-kate"
"trackWithCount_other": "{{count}} pista"
},
"error": {
"apiRouteError": "ezin izan da eskaera bideratu",
@@ -347,11 +292,7 @@
"badAlbum": "Orrialde hau ikusten ari zara abesti hau album batekoa ez delako. Ziurrenik arazo hau ikusten ari zara zure musika karpetaren goiko mailan abesti bat baduzu. Jellyfinek abestiak karpeta batean badaude taldekatzen ditu bakarrik",
"loginRateError": "Saioa hasteko saiakera gehiegi egin dira, saiatu berriro segundo batzuk barru",
"notificationDenied": "jakinarazpenetarako baimenak ukatu dira. Ezarpen honek ez du eraginik",
"systemFontError": "errore bat gertatu da sistemaren letra-tipoak lortzen saiatzean",
"noNetwork": "zerbitzaria ez dago erabilgarri",
"noNetworkDescription": "ezin izan da zerbitzari honetara konektatu",
"saveQueueFailed": "huts egin du ilara gordetzean",
"multipleServerSaveQueueError": "erreprodukzio-ilarak zerbitzarikoak ez diren abesti bat edo gehiago ditu. hau ez da onartzen"
"systemFontError": "errore bat gertatu da sistemaren letra-tipoak lortzen saiatzean"
},
"filter": {
"disc": "diskoa",
@@ -365,19 +306,19 @@
"random": "ausazkoa",
"rating": "balorazioa",
"trackNumber": "pista",
"album": "$t(entity.album, {\"count\": 1})",
"albumArtist": "$t(entity.albumArtist, {\"count\": 1})",
"artist": "$t(entity.artist, {\"count\": 1})",
"album": "$t(entity.album_one)",
"albumArtist": "$t(entity.albumArtist_one)",
"artist": "$t(entity.artist_one)",
"biography": "biografia",
"bitrate": "bit-emaria",
"bpm": "bpm-ak",
"channels": "$t(common.channel_other)",
"comment": "iruzkina",
"favorited": "gogoko gisa markatua",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"search": "bilatu",
"title": "tituloa",
"albumCount": "$t(entity.album, {\"count\": 2}) kopurua",
"albumCount": "$t(entity.album_other) kopurua",
"communityRating": "komunitatearen balorazioa",
"criticRating": "kritikarien balorazioa",
"dateAdded": "gehitutako data",
@@ -404,9 +345,9 @@
"playbackStyle_optionNormal": "normala",
"playButtonBehavior_optionPlay": "$t(player.play)",
"playButtonBehavior_optionPlayShuffled": "$t(player.shuffle)",
"replayGainMode_optionAlbum": "$t(entity.album, {\"count\": 1})",
"replayGainMode_optionAlbum": "$t(entity.album_one)",
"replayGainMode_optionNone": "$t(common.none)",
"replayGainMode_optionTrack": "$t(entity.track, {\"count\": 1})",
"replayGainMode_optionTrack": "$t(entity.track_one)",
"font": "letra-tipoa",
"hotkey_playbackStop": "gelditu",
"buttonSize_description": "erreproduzitzailearen barrako botoien tamaina",
@@ -419,6 +360,7 @@
"customCss": "css pertsonalizatua",
"customFontPath": "letra-tipo pertsonalizatuaren bidea",
"customFontPath_description": "aplikazioan erabiliko den letra-tipo pertsonalizatuaren bidea ezartzen du",
"disableAutomaticUpdates": "desgaitu eguneratze automatikoak",
"discordApplicationId": "{{discord}} aplikazioaren IDa",
"followLyric": "jarraitu uneko letra",
"font_description": "aplikazioan erabiliko den letra-tipoa ezartzen du",
@@ -506,6 +448,7 @@
"discordDisplayType_description": "zure egoeran entzuten ari zarena aldatzen du",
"discordLinkType": "{{discord}} egoera estekak",
"fontType_description": "barneko letra-tipoa feishinek eskaintzen dituen letra-tipoetako bat aukeratzen du. sistemaren letra-tipoa zure sistema eragileak eskaintzen duen edozein letra-tipo hautatzeko aukera ematen dizu. pertsonalizatua zure letra-tipoa eskaintzeko aukera ematen dizu",
"genreBehavior": "genero orriaren portaera lehenetsia",
"homeConfiguration_description": "konfiguratu zein elementu erakusten diren hasierako orrian eta zein ordenatan",
"homeFeature": "etxeko karrusela nabarmendua",
"homeFeature_description": "hasierako orrian karrusel nabarmen handia erakutsi behar den ala ez kontrolatzen du",
@@ -553,6 +496,7 @@
"accentColor": "azentu-kolorea",
"clearCache_description": "feishinen 'garbiketa gogorra'. feishinen katxea garbitzeaz gain, hustu nabigatzailearen katxea (gordetako irudiak eta bestelako aktiboak). zerbitzari-kredentzialak eta ezarpenak gorde egiten dira",
"clearQueryCache_description": "feishinen 'garbiketa ahula'. honek erreprodukzio-zerrendak eta pisten metadatuak freskatuko ditu eta gordetako letrak berrezarriko ditu. ezarpenak, zerbitzari-kredentzialak eta katxetutako irudiak gorde egiten dira",
"doubleClickBehavior": "jarri ilaran bilatutako pista guztiak klik bikoitza egitean",
"exitToTray_description": "irten aplikaziotik sistemaren erretilura",
"followLyric_description": "mugitu letra uneko erreprodukzio-posiziora",
"preferLocalLyrics": "nahiago izan letra lokalak",
@@ -579,8 +523,10 @@
"playbackStyle_description": "aukeratu audio erreproduzitzailearentzat erabiliko den erreprodukzio estiloa",
"playButtonBehavior": "erreprodukzio botoiaren portaera",
"playButtonBehavior_description": "ezartzen du erreprodukzio botoiaren portaera lehenetsia abestiak ilaran gehitzean",
"playerAlbumArtResolution": "erreproduzitzailearen albumaren arte-azalaren erresoluzioa",
"gaplessAudio": "hutsune gabeko audioa",
"gaplessAudio_description": "ezartzen du hutsunik gabeko audio ezarpena mpv-rako",
"genreBehavior_description": "genero batean klik egiteak abestien edo albumen zerrendan lehenespenez irekitzen den zehazten du",
"passwordStore": "pasahitzak/biltegi sekretua",
"playerbarOpenDrawer": "txandakatu erreproduzitzailearen barra pantaila osora",
"playerbarOpenDrawer_description": "aukera ematen du erreproduzitzailearen barran klik egiteak pantaila osoko erreproduzitzailea irekitzeko",
@@ -588,94 +534,11 @@
"customCss_description": "css eduki pertsonalizatua. Oharra: edukia eta urruneko URLak debekatutako propietateak dira. Zure edukiaren aurrebista erakusten da behean. Ezarri ez dituzun eremu gehigarriak daude garbiketa dela eta",
"enableRemote": "gaitu urruneko kontrol zerbitzaria",
"enableRemote_description": "urruneko kontrol zerbitzariari beste gailu batzuei aplikazioa kontrolatzeko aukera ematen dio",
"doubleClickBehavior_description": "egia bada, bilaketa batean bat datozen pista guztiak ilaran jarriko dira. bestela, klikatutakoak bakarrik jarriko dira ilaran",
"imageAspectRatio_description": "gaituta badago, azaleko artea jatorrizko aspektu-erlazioa erabiliz erakutsiko da. 1:1 ez den arterako, gainerako espazioa hutsik egongo da",
"crossfadeStyle": "crossfade estiloa",
"discordRichPresence": "{{discord}}-en jarduera-egoera",
"enableAutoTranslation": "gaitu itzulpen automatikoa",
"exportImportSettings_control_exportText": "esportatu ezarpenak",
"exportImportSettings_control_importText": "inportatu ezarpenak",
"exportImportSettings_control_title": "inportatu / esportatu ezarpenak",
"exportImportSettings_importBtn": "inportatu ezarpenak",
"exportImportSettings_importModalTitle": "inportatu feishin ezarpenak",
"autoDJ_itemCount": "elementu kopurua",
"language": "hizkuntza",
"queryBuilderCustomFields_inputTag": "etiketa",
"logLevel_optionError": "errore bat",
"logLevel_optionInfo": "informazioa",
"imageResolution_optionTable": "taula",
"imageResolution_optionSidebar": "alboko barra",
"replayGainClipping": "{{ReplayGain}} mozketa",
"replayGainFallback": "{{ReplayGain}} ordezko aukera",
"trayEnabled": "erakutsi erretilua",
"artistReleaseTypeConfiguration": "artistaren argitalpen motaren konfigurazioa",
"artistReleaseTypeConfiguration_description": "konfiguratu zein argitalpen mota erakusten diren, eta zein ordenatan, albumaren artistaren orrian",
"useThemeAccentColor": "erabili gaiaren azentu-kolorea",
"useThemeAccentColor_description": "erabili hautatutako gaian definitutako kolore nagusia azentu-kolore pertsonalizatuaren ordez",
"showRatings": "erakutsi izarren balorazioak",
"showRatings_description": "izarren balorazioen funtzioa interfazean agertzen den ala ez kontrolatzen du",
"imageResolution": "irudiaren erresoluzioa",
"imageResolution_description": "aplikazioan erabilitako irudien erresoluzioa. 0 balioa erabiliz gero, jatorrizko irudiaren erresoluzioa erabiliko da lehenespenez",
"followCurrentSong_description": "automatikoki korritu erreprodukzio-ilara uneko abestira",
"followCurrentSong": "jarraitu uneko abestia",
"lyricOffset_description": "letra zehaztutako milisegundo kopuruarekin desplazatu",
"lyricOffset": "letraren desplazamendua (ms)",
"mpvExtraParameters": "mpv parametro gehigarriak",
"mpvExtraParameters_description": "mpv-ri pasatzeko argumentu gehigarriak",
"notify": "abestien jakinarazpenak gaitu",
"notify_description": "erakutsi jakinarazpenak uneko abestia aldatzean",
"pathReplace": "fitxategiaren bidearen ordezkapena",
"pathReplace_description": "ordezkatu zure zerbitzariaren fitxategi-bide lehenetsia",
"pathReplace_optionRemovePrefix": "kendu aurrizkia",
"pathReplace_optionAddPrefix": "gehitu aurrizkia",
"passwordStore_description": "zein pasahitz/sekretu biltegi erabili. aldatu hau pasahitzak gordetzeko arazoak badituzu",
"playerFilters": "Iragazi ilarako abestiak",
"sidePlayQueueStyle_description": "alboko erreprodukzio-ilararen estiloa ezartzen du",
"mediaSession_description": "Windows Media Session integrazioa gaitzen du, multimedia kontrolak eta metadatuak sistemaren bolumenaren gainjartzean eta blokeo pantailan bistaratuz (Windows bakarrik)",
"sidePlayQueueStyle": "alboko erreprodukzio-ilarako estiloa",
"skipPlaylistPage": "saltatu erreprodukzio-zerrenda orria",
"startMinimized_description": "abiarazi aplikazioa sistemaren erretiluan",
"startMinimized": "hasi minimizatuta",
"transcode": "gaitu transkodetzea",
"transcode_description": "formatu ezberdinetara transkodetzea ahalbidetzen du",
"transcodeBitrate_description": "transkodetzeko bit-emaria hautatzen du. 0k zerbitzariari aukeratzen uzten diola esan nahi du",
"transcodeBitrate": "transkodetzeko bit-emaria",
"transcodeFormat_description": "transkodetzeko formatua hautatzen du. utzi hutsik zerbitzariak erabaki dezan",
"transcodeFormat": "transkodetzeko formatua",
"queryBuilderCustomFields_inputLabel": "etiketa",
"autoDJ": "DJ automatikoa",
"autoDJ_description": "automatikoki gehitu antzeko abestiak ilaran",
"autoDJ_itemCount_description": "DJ automatikoa gaituta dagoenean ilaran gehitzen saiatu diren elementuen kopurua",
"autoDJ_timing_description": "DJ automatikoa aktibatu aurretik ilaran geratzen diren abestien kopurua",
"analyticsDisable": "Erabileran oinarritutako analisiei uko egin",
"analyticsDisable_description": "Erabilera-datu anonimoak garatzaileari bidaltzen zaizkio aplikazioa hobetzen laguntzeko",
"contextMenu_description": "elementu batean eskuineko botoiarekin klik egitean menuan agertzen diren elementuak ezkutatzeko aukera ematen dizu. hautatuta ez dauden elementuak ezkutatuta egongo dira",
"enableAutoTranslation_description": "Gaitu itzulpena automatikoki letra kargatzen denean",
"exportImportSettings_control_description": "JSON bidez ezarpenak esportatu eta inportatu",
"exportImportSettings_destructiveWarning": "Ezarpenak inportatzea arriskutsua da, mesedez, berrikusi goikoa beheko \"inportatu\" klikatu aurretik!",
"exportImportSettings_importSuccess": "ezarpenak behar bezala inportatu dira!",
"exportImportSettings_offendingKeyError": "\"{{offendingKey}}\" okerra da - {{reason}}",
"hotkey_listPlayDefault": "zerrenda erreproduzitu",
"hotkey_listPlayLast": "zerrenda erreproduzitu amaieran",
"hotkey_listPlayNow": "zerrenda erreproduzitu orain",
"logLevel": "erregistro maila",
"logLevel_description": "Bistaratzeko erregistroen gutxieneko maila ezartzen du. Debug-ek erregistro guztiak erakusten ditu, «erroreak» erroreak bakarrik erakusten ditu",
"logLevel_optionDebug": "arazketa",
"playerFilters_description": "saltatu abestiak ilaran gehitzea irizpide hauen arabera",
"artistRadioCount_description": "artista eta abestien irratian bilatu beharreko abesti kopurua ezartzen du",
"artistRadioCount": "artista/abesti irratiko kopurua",
"imageResolution_optionItemCard": "elementu txartela",
"imageResolution_optionHeader": "goiburua",
"imageResolution_optionFullScreenPlayer": "pantaila osoko erreproduzitzailea",
"showVisualizerInSidebar": "erakutsi bistaratzailea erreproduzitzailearen alboko barran",
"combinedLyricsAndVisualizer_description": "konbinatu letrak eta bistaratzailea panel berean",
"combinedLyricsAndVisualizer": "konbinatu letrak eta bistaratzailea erreproduzitzailearen alboko barran",
"preventSleepOnPlayback_description": "saihestu pantaila lotan jartzea musika erreproduzitzen ari den bitartean",
"remotePassword_description": "urruneko kontrol zerbitzariaren pasahitza ezartzen du. Kredentzial hauek modu ez-seguruan transferitzen dira lehenespenez, beraz, axola ez zaizun pasahitz bakarra erabili beharko zenuke",
"remotePassword": "urruneko kontrol zerbitzariaren pasahitza",
"remotePort_description": "urruneko kontrol zerbitzariaren portua ezartzen du",
"remotePort": "urruneko kontrol zerbitzariaren ataka",
"remoteUsername_description": "urruneko kontrol zerbitzariaren erabiltzaile-izena ezartzen du. Erabiltzaile-izena eta pasahitza hutsik badaude, autentifikazioa desgaituta egongo da",
"remoteUsername": "urruneko kontrol zerbitzariaren erabiltzaile-izena"
"enableAutoTranslation": "gaitu itzulpen automatikoa"
},
"form": {
"addServer": {
@@ -691,27 +554,26 @@
"input_legacyAuthentication": "gaitu zaharkitutako autentifikazioa",
"success": "zerbitzaria behar bezala gehitu da",
"input_preferInstantMix": "nahiago izan berehalako nahasketa",
"input_preferInstantMixDescription": "erabili berehalako nahasketa soilik antzeko abestiak lortzeko. erabilgarria portaera hau aldatzen duten pluginak badituzu",
"input_remoteUrl": "URL publikoa"
"input_preferInstantMixDescription": "erabili berehalako nahasketa soilik antzeko abestiak lortzeko. erabilgarria portaera hau aldatzen duten pluginak badituzu"
},
"addToPlaylist": {
"input_playlists": "$t(entity.playlist, {\"count\": 2})",
"input_playlists": "$t(entity.playlist_other)",
"success": "$t(entity.trackWithCount, {\"count\": {{message}} }) gehitu da $t(entity.playlistWithCount, {\"count\": {{numOfPlaylists}} })-ra",
"input_skipDuplicates": "saltatu bikoiztuak",
"title": "gehitu $t(entity.playlist, {\"count\": 1})-(a)ri",
"create": "sortu $t(entity.playlist, {\"count\": 1}) {{playlist}}",
"searchOrCreate": "bilatu $t(entity.playlist, {\"count\": 2}) edo idatzi berri bat sortzeko"
"title": "gehitu $t(entity.playlist_one)-(a)ri",
"create": "sortu $t(entity.playlist_one) {{playlist}}",
"searchOrCreate": "bilatu $t(entity.playlist_other) edo idatzi berri bat sortzeko"
},
"createPlaylist": {
"input_description": "$t(common.description)",
"input_name": "$t(common.name)",
"input_owner": "$t(common.owner)",
"input_public": "publikoa",
"title": "$t(entity.playlist, {\"count\": 1}) sortu",
"success": "$t(entity.playlist, {\"count\": 1}) behar bezala sortu da"
"title": "$t(entity.playlist_one) sortu",
"success": "$t(entity.playlist_one) behar bezala sortu da"
},
"lyricSearch": {
"input_artist": "$t(entity.artist, {\"count\": 1})",
"input_artist": "$t(entity.artist_one)",
"input_name": "$t(common.name)",
"title": "letra bilatu"
},
@@ -724,22 +586,19 @@
"createFailed": "partekatzea sortzeak huts egin du (partekatzea gaituta al dago?)"
},
"deletePlaylist": {
"success": "$t(entity.playlist, {\"count\": 1}) behar bezala ezabatu da",
"title": "$t(entity.playlist, {\"count\": 1}) ezabatu",
"input_confirm": "idatzi $t(entity.playlist, {\"count\": 1})-(a)ren izena berresteko"
"success": "$t(entity.playlist_one) behar bezala ezabatu da",
"title": "$t(entity.playlist_one) ezabatu",
"input_confirm": "idatzi $t(entity.playlist_one)-(a)ren izena berresteko"
},
"editPlaylist": {
"success": "$t(entity.playlist, {\"count\": 1}) behar bezala eguneratu da",
"title": "$t(entity.playlist, {\"count\": 1}) editatu",
"publicJellyfinNote": "Arrazoiren batengatik, Jellyfin ez du erakusten erreprodukzio-zerrendak publikoak diren edo ez. Hau publiko izaten jarraitzea nahi baduzu, hautatu sarrera hau",
"editNote": "ez da gomendatzen eskuzko edizioak egitea erreprodukzio-zerrenda handietarako. ziur zaude onartzen duzula lehendik dagoen erreprodukzio-zerrenda gainidazteagatik datuak galtzeko arriskua?"
"success": "$t(entity.playlist_one) behar bezala eguneratu da",
"title": "$t(entity.playlist_one) editatu",
"publicJellyfinNote": "Arrazoiren batengatik, Jellyfin ez du erakusten erreprodukzio-zerrendak publikoak diren edo ez. Hau publiko izaten jarraitzea nahi baduzu, hautatu sarrera hau"
},
"queryEditor": {
"title": "kontsulta editorea",
"input_optionMatchAll": "guztiak bat etorri",
"input_optionMatchAny": "edozeinekin bat etorri",
"resetToDefault": "lehenetsitako egoerara berrezarri",
"clearFilters": "garbitu iragazkiak"
"input_optionMatchAny": "edozeinekin bat etorri"
},
"updateServer": {
"success": "zerbitzaria behar bezala eguneratu da",
@@ -749,50 +608,25 @@
"title": "modu pribatua",
"enabled": "modu pribatua gaituta, erreprodukzio egoera kanpoko integrazioetatik ezkutatuta dago orain",
"disabled": "modu pribatua desgaituta, erreprodukzio egoera ikusgai dago orain gaitutako kanpoko integrazioentzat"
},
"largeFetchConfirmation": {
"title": "gehitu elementuak ilaran"
},
"createRadioStation": {
"input_homepageUrl": "hasierako orriaren URLa",
"input_name": "izena",
"title": "irrati-katea sortu",
"success": "irrati-katea behar bezala sortu da"
},
"lyricsExport": {
"export": "esportatu letrak",
"input_synced": "esportatu sinkronizatutako letrak",
"input_offset": "$t(setting.lyricOffset)"
},
"shuffleAll": {
"input_genre": "$t(entity.genre, {\"count\": 1})",
"title": "ausaz erreproduzitu",
"input_limit": "zenbat abesti?",
"input_played_optionAll": "pista guztiak",
"input_played_optionUnplayed": "erreproduzitu gabeko pistak bakarrik",
"input_played_optionPlayed": "erreproduzitutako pistak bakarrik"
},
"saveQueue": {
"success": "erreprodukzio-ilara zerbitzarian gordeta"
}
},
"page": {
"albumArtistList": {
"title": "$t(entity.albumArtist, {\"count\": 2})"
"title": "$t(entity.albumArtist_other)"
},
"albumDetail": {
"released": "argitaratuta",
"moreFromArtist": "$t(entity.artist, {\"count\": 1}) honetatik gehiago",
"moreFromArtist": "$t(entity.artist_one) honetatik gehiago",
"moreFromGeneric": "{{item}}-(e)tik gehiago"
},
"albumList": {
"title": "$t(entity.album, {\"count\": 2})",
"genreAlbums": "\"{{genre}}\" $t(entity.album, {\"count\": 2})",
"title": "$t(entity.album_other)",
"genreAlbums": "\"{{genre}}\" $t(entity.album_other)",
"artistAlbums": "{{artist}}-(a)ren albumak"
},
"appMenu": {
"quit": "$t(common.quit)",
"settings": "$t(common.setting, {\"count\": 2})",
"settings": "$t(common.setting_other)",
"collapseSidebar": "tolestu alboko barra",
"expandSidebar": "zabaldu alboko barra",
"goBack": "atzera",
@@ -802,11 +636,7 @@
"privateModeOn": "aktibatu modu pribatua",
"selectServer": "aukeratu zerbitzaria",
"version": "bertsioa {{version}}",
"openBrowserDevtools": "ireki nabigatzailearen garapen tresnak",
"commandPalette": "ireki komando-paleta",
"noMusicFolder": "ez da musika karpetarik hautatu",
"selectMusicFolder": "aukeratu musika karpeta",
"multipleMusicFolders": "{{count}} musika karpeta aukeratuta"
"openBrowserDevtools": "ireki nabigatzailearen garapen tresnak"
},
"manageServers": {
"url": "URLa",
@@ -838,10 +668,9 @@
"playShuffled": "$t(player.shuffle)",
"numberSelected": "{{count}} hautatuta",
"shareItem": "partekatu elementua",
"goToAlbum": "joan $t(entity.album, {\"count\": 1})-(e)ra",
"goToAlbum": "joan $t(entity.album_one)-(e)ra",
"goToAlbumArtist": "joan albumera",
"showDetails": "informazioa lortu",
"moveItems": "$t(action.moveItems)"
"showDetails": "informazioa lortu"
},
"fullscreenPlayer": {
"config": {
@@ -867,9 +696,9 @@
"noLyrics": "ez da letrarik aurkitu"
},
"genreList": {
"title": "$t(entity.genre, {\"count\": 2})",
"showAlbums": "erakutsi $t(entity.genre, {\"count\": 1}) $t(entity.album, {\"count\": 2})",
"showTracks": "erakutsi $t(entity.genre, {\"count\": 1}) $t(entity.track, {\"count\": 2})"
"title": "$t(entity.genre_other)",
"showAlbums": "erakutsi $t(entity.genre_one) $t(entity.album_other)",
"showTracks": "erakutsi $t(entity.genre_one) $t(entity.track_other)"
},
"globalSearch": {
"title": "komandoak",
@@ -885,68 +714,48 @@
"newlyAdded": "azken aldian gehitutako argitalpenak",
"recentlyPlayed": "azken aldian entzundakoak",
"recentlyReleased": "azken aldian argitaratutak",
"explore": "arakatu zure liburutegitik",
"genres": "$t(entity.genre, {\"count\": 2})"
"explore": "arakatu zure liburutegitik"
},
"playlistList": {
"title": "$t(entity.playlist, {\"count\": 2})"
"title": "$t(entity.playlist_other)"
},
"setting": {
"advanced": "aurreratua",
"generalTab": "orokorra",
"playbackTab": "erreprodukzioa",
"windowTab": "leihoa",
"hotkeysTab": "laster-teklak",
"cache": "katxea",
"application": "aplikazioa",
"theme": "gaia",
"sidebar": "alboko barra",
"exportImport": "inportatu/esportatu",
"scrobble": "scrobble",
"audio": "audioa",
"lyrics": "letrak",
"discord": "discord",
"playerFilters": "erreproduzitzailearen iragazkiak",
"updates": "eguneraketa",
"queryBuilder": "kontsulta-sortzailea",
"controls": "kontrolak",
"remote": "urrunekoa",
"lyricsDisplay": "erakutsi letrak"
"hotkeysTab": "laster-teklak"
},
"sidebar": {
"albumArtists": "$t(entity.albumArtist, {\"count\": 2})",
"albums": "$t(entity.album, {\"count\": 2})",
"artists": "$t(entity.artist, {\"count\": 2})",
"folders": "$t(entity.folder, {\"count\": 2})",
"genres": "$t(entity.genre, {\"count\": 2})",
"albumArtists": "$t(entity.albumArtist_other)",
"albums": "$t(entity.album_other)",
"artists": "$t(entity.artist_other)",
"folders": "$t(entity.folder_other)",
"genres": "$t(entity.genre_other)",
"home": "$t(common.home)",
"playlists": "$t(entity.playlist, {\"count\": 2})",
"playlists": "$t(entity.playlist_other)",
"search": "$t(common.search)",
"settings": "$t(common.setting, {\"count\": 2})",
"tracks": "$t(entity.track, {\"count\": 2})",
"settings": "$t(common.setting_other)",
"tracks": "$t(entity.track_other)",
"myLibrary": "nire liburutegia",
"nowPlaying": "orain erreproduzitzen",
"shared": "partekatutako $t(entity.playlist, {\"count\": 2})",
"favorites": "$t(entity.favorite, {\"count\": 2})",
"radio": "$t(entity.radioStation, {\"count\": 2})"
"shared": "partekatutako $t(entity.playlist_other)"
},
"trackList": {
"title": "$t(entity.track, {\"count\": 2})",
"genreTracks": "\"{{genre}}\" $t(entity.track, {\"count\": 2})",
"title": "$t(entity.track_other)",
"genreTracks": "\"{{genre}}\" $t(entity.track_other)",
"artistTracks": "{{artist}}-(r)en abestiak"
},
"albumArtistDetail": {
"about": "{{artist}}-(r)i buruz",
"relatedArtists": "erlazionatutako $t(entity.artist, {\"count\": 2})",
"relatedArtists": "erlazionatutako $t(entity.artist_other)",
"topSongs": "abesti nagusiak",
"topSongsFrom": "{{title}}-(a)ren abesti nagusiak",
"viewAll": "ikusi guztiak",
"viewAllTracks": "ikusi $t(entity.track, {\"count\": 2}) guztiak",
"viewAllTracks": "ikusi $t(entity.track_other) guztiak",
"appearsOn": "agertzen da hemen",
"recentReleases": "azken argitalpenak",
"viewDiscography": "ikusi diskografia",
"groupingTypeAll": "argitalpen mota guztiak",
"groupingTypePrimary": "argitalpen mota nagusiak"
"viewDiscography": "ikusi diskografia"
},
"itemDetail": {
"copyPath": "kopiatu bidea arbelean",
@@ -955,148 +764,14 @@
},
"playlist": {
"reorder": "berrantolaketa IDaren arabera ordenatzean bakarrik gaituta dago"
},
"folderList": {
"title": "$t(entity.folder, {\"count\": 2})"
},
"favorites": {
"title": "$t(entity.favorite, {\"count\": 2})"
},
"radioList": {
"title": "irrati-kateak"
}
},
"releaseType": {
"primary": {
"album": "$t(entity.album, {\"count\": 1})",
"other": "bestelakoa",
"ep": "ep"
"album": "$t(entity.album_one)"
},
"secondary": {
"compilation": "konpilazioa",
"audiobook": "audioliburua",
"interview": "elkarrizketa",
"remix": "nahasketa",
"djMix": "dj nahasketa"
"compilation": "konpilazioa"
}
},
"datetime": {
"minuteShort": "m",
"secondShort": "s",
"hourShort": "h",
"dayShort": "d"
},
"queryBuilder": {
"customTags": "etiketa pertsonalizatutak",
"standardTags": "etiketa estandarrak"
},
"filterOperator": {
"is": "da",
"contains": "dauka",
"notContains": "ez dauka",
"startsWith": "honekin hasten da",
"endsWith": "honekin amaitzen da",
"isNot": "ez da"
},
"visualizer": {
"general": "Orokorra",
"mode": "Modua",
"vertical": "Bertikala",
"horizontal": "Horizontala",
"position": "Posizioa",
"level": "Maila",
"remove": "Kendu",
"custom": "Pertsonalizatua",
"builtIn": "Barneratua",
"colors": "Koloreak",
"gradient": "Gradientea",
"fft": "FFT",
"sensitivity": "Sentikortasuna",
"smoothing": "Leuntzea",
"gravity": "Grabitatea",
"radial": "Erradiala",
"radius": "Erradioa",
"mirror": "Ispilua",
"options": {
"colorMode": {
"gradient": "Gradientea",
"barIndex": "Barra-indizea",
"barLevel": "Barra-maila"
},
"gradient": {
"classic": "Klasikoa",
"prism": "Prisma",
"rainbow": "Ostadarra",
"orangered": "Laranja-gorria"
},
"weightingFilter": {
"none": "Bat ere ez",
"a": "A",
"b": "B",
"c": "C",
"d": "D",
"z": "Z"
},
"mode": {
"0": "[0] Maiztasun Diskretuak",
"1": "[1] 1/24 oktaba / 240 banda",
"2": "[2] 1/12 oktaba / 120 banda",
"3": "[3] 1/8 oktaba / 80 banda",
"4": "[4] 1/6ko oktaba / 60 banda",
"5": "[5] 1/4 oktaba / 40 banda",
"6": "[6] 1/3 oktaba / 30 banda",
"7": "[7] Oktaba erdi / 20 banda",
"8": "[8] Oktaba osoa / 10 banda",
"10": "[10] Lerroa / Azalera grafikoa"
},
"frequencyScale": {
"none": "Bat ere ez",
"linear": "Eskala Lineala",
"bark": "Bark Eskala",
"mel": "Mel Eskala"
}
},
"opacity": "Opakotasuna",
"minimumFrequency": "Gutxieneko Maiztasuna",
"maximumFrequency": "Gehienezko Maiztasuna",
"frequencyScale": "Maiztasun Eskala",
"weightingFilter": "Ponderazio-iragazkia",
"minimumDecibels": "Gutxieneko Dezibelioak",
"maximumDecibels": "Gehienezko Dezibelioak",
"linearAmplitude": "Anplitude Lineala",
"linearBoost": "Bultzada Lineala",
"showPeaks": "Erakutsi Gailurrak",
"configCopied": "Konfigurazioa arbelean kopiatu da",
"configCopyFailed": "Konfigurazioa kopiatzeak huts egin du",
"configPasted": "Konfigurazioa behar bezala aplikatu da",
"configPasteFailed": "Konfigurazioa aplikatzeak huts egin du. Mesedez, egiaztatu formatua.",
"configPasteReadFailed": "Arbelatik irakurtzeak huts egin du",
"colorMode": "Kolore Modua",
"fftSize": "FFT tamaina",
"frequencyRangeAndScaling": "Maiztasun-tartea eta eskalatzea",
"showScaleY": "Erakutsi Y Eskala",
"pasteGradientPlaceholder": "Itsatsi JSON gradientea hemen...",
"pasteGradient": "Itsatsi Gradientea",
"addColor": "Gehitu Kolorea",
"colorStops": "Kolore Geldialdiak",
"gradientNamePlaceholder": "Gradientearen Izena",
"gradientName": "Gradientearen Izena",
"addCustomGradient": "Gehitu Gradiente Pertsonalizatua",
"customGradients": "Gradiente Pertsonalizatuak",
"maxFPS": "FPS maximoak",
"channelLayout": "Kanalaren Diseinua",
"lineWidth": "Lerroaren Zabalera",
"presetNamePlaceholder": "Sartu aurrezarpenaren izena",
"presetName": "Aurrezarpenaren Izena",
"applyConfiguration": "Aplikatu konfigurazioa",
"pasteFromClipboard": "Itsatsi Arbeletik",
"pasteConfigurationPlaceholder": "Itsatsi JSON konfigurazioa hemen...",
"pasteConfiguration": "Itsatsi Konfigurazioa",
"copyConfiguration": "Kopiatu Konfigurazioa",
"updatePreset": "Aurrezarpena Eguneratu",
"saveAsPreset": "Aurrezarpen gisa gorde",
"applyPreset": "Aurrezarpena Aplikatu",
"selectPreset": "Aukeratu Aurrezarpena",
"presets": "Aurrezarpenak"
}
}
+58 -55
View File
@@ -33,23 +33,23 @@
"muted": "بی‌صدا"
},
"action": {
"editPlaylist": "ویرایش $t(entity.playlist, {\"count\": 1})",
"editPlaylist": "ویرایش $t(entity.playlist_one)",
"goToPage": "برو به صفحهٔ",
"moveToTop": "انتقال به بالا",
"clearQueue": "خالی کردن صف",
"addToFavorites": "افزودن به $t(entity.favorite, {\"count\": 2})",
"addToPlaylist": "افزودن به $t(entity.playlist, {\"count\": 1})",
"createPlaylist": "ساخت $t(entity.playlist, {\"count\": 1})",
"removeFromPlaylist": "حذف از $t(entity.playlist, {\"count\": 1})",
"viewPlaylists": "نمایش $t(entity.playlist, {\"count\": 2})",
"addToFavorites": "افزودن به $t(entity.favorite_other)",
"addToPlaylist": "افزودن به $t(entity.playlist_one)",
"createPlaylist": "ساخت $t(entity.playlist_one)",
"removeFromPlaylist": "حذف از $t(entity.playlist_one)",
"viewPlaylists": "نمایش $t(entity.playlist_other)",
"refresh": "$t(common.refresh)",
"deletePlaylist": "حذف $t(entity.playlist, {\"count\": 1})",
"deletePlaylist": "حذف $t(entity.playlist_one)",
"removeFromQueue": "حذف از صف",
"deselectAll": "لغو انتخاب همه",
"moveToBottom": "انتقال به پایین",
"setRating": "تعیین امتیاز",
"toggleSmartPlaylistEditor": "تغییر ویرایشگر $t(entity.smartPlaylist)",
"removeFromFavorites": "حذف از $t(entity.favorite, {\"count\": 2})",
"removeFromFavorites": "حذف از $t(entity.favorite_other)",
"openIn": {
"lastfm": "باز کردن در Last.fm",
"musicbrainz": "باز کردن در MusicBranz"
@@ -76,15 +76,16 @@
"hotkey_volumeDown": "کم کردن صدا",
"audioPlayer_description": "پخش‌کنندهٔ صدا را برای پخش انتخاب کنید",
"hotkey_globalSearch": "جست و جوی سراسری",
"disableAutomaticUpdates": "غیرفعال کردن به‌‌روزرسانی خودکار",
"exitToTray_description": "خروج از اپلیکیشن به system tray",
"replayGainMode_optionAlbum": "$t(entity.album, {\"count\": 1})",
"replayGainMode_optionAlbum": "$t(entity.album_one)",
"discordUpdateInterval_description": "فاصلهٔ بین هر به روزرسانی به ثانیه (حداقل ۱۵ ثانیه)",
"audioExclusiveMode": "حالت اختصاصی صدا",
"remotePassword": "رمز عبور کنترل از راه دور",
"language_description": "زبان اپلیکیشن را معین می‌کند $t(common.restartRequired)",
"hotkey_rate3": "امتیاز ۳ ستاره",
"font": "قلم",
"replayGainMode_optionTrack": "$t(entity.track, {\"count\": 1})",
"replayGainMode_optionTrack": "$t(entity.track_one)",
"hotkey_toggleFullScreenPlayer": "تغییر به پخش‌کنندهٔ تمام‌صفحه",
"hotkey_localSearch": "جست و جو در صفحه",
"hotkey_toggleQueue": "تغییر صف",
@@ -185,7 +186,7 @@
"left": "چپ",
"save": "ذخیره",
"right": "راست",
"currentSong": "فعلی $t(entity.track, {\"count\": 1})",
"currentSong": "فعلی $t(entity.track_one)",
"collapse": "بستن",
"trackNumber": "قطعه",
"descending": "نزولی",
@@ -238,7 +239,7 @@
"none": "هیچ",
"menu": "منو",
"restartRequired": "راه‌اندازی دوباره لازم است",
"previousSong": "$t(entity.track, {\"count\": 1}) پیشین",
"previousSong": "$t(entity.track_one) پیشین",
"noResultsFromQuery": "جست‌وجو نتیجه‌ای نداشت",
"quit": "خروج",
"expand": "گسترش",
@@ -255,8 +256,7 @@
"albumPeak": "اوج آلبوم",
"mbid": "شناسه‌ی MusicBrainz",
"reload": "بارگذاری مجدد",
"setting_one": "پیکربندی",
"setting_other": "",
"setting": "پیکربندی",
"trackGain": "گین قطعه",
"trackPeak": "اوج قطعه",
"translation": "ترجمه",
@@ -301,16 +301,16 @@
"rating": "امتیاز",
"search": "جست‌وجو",
"bitrate": "بیت‌ریت",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"recentlyAdded": "به تازگی افزوده شده",
"note": "توجه",
"name": "نام",
"dateAdded": "تاریخ افزوده شدن",
"releaseDate": "تاریخ انتشار",
"albumCount": "$t(entity.album, {\"count\": 2}) عدد",
"albumCount": "$t(entity.album_other) عدد",
"path": "مسیر",
"favorited": "موردعلاقه",
"albumArtist": "$t(entity.albumArtist, {\"count\": 1})",
"albumArtist": "$t(entity.albumArtist_one)",
"isRecentlyPlayed": "به تازگی پخش شده است",
"isFavorited": "موردعلاقه است",
"bpm": "bpm",
@@ -319,7 +319,7 @@
"disc": "دیسک",
"biography": "زندگی‌نامه",
"songCount": "تعداد ترانه",
"artist": "$t(entity.artist, {\"count\": 1})",
"artist": "$t(entity.artist_one)",
"duration": "مدت",
"isPublic": "عمومی است",
"random": "تصادفی",
@@ -327,23 +327,23 @@
"toYear": "تا سال",
"fromYear": "از سال",
"criticRating": "امتیاز منتقدین",
"album": "$t(entity.album, {\"count\": 1})",
"album": "$t(entity.album_one)",
"trackNumber": "قطعه",
"communityRating": "رتبه بندی جامعه",
"isCompilation": "مخلوط است"
},
"form": {
"deletePlaylist": {
"title": "حذف $t(entity.playlist, {\"count\": 1})",
"success": "$t(entity.playlist, {\"count\": 1}) حذف شد",
"input_confirm": "برای تایید، نام $t(entity.playlist, {\"count\": 1}) را وارد کنید"
"title": "حذف $t(entity.playlist_one)",
"success": "$t(entity.playlist_one) حذف شد",
"input_confirm": "برای تایید، نام $t(entity.playlist_one) را وارد کنید"
},
"createPlaylist": {
"input_description": "$t(common.description)",
"title": "ساخت $t(entity.playlist, {\"count\": 1})",
"title": "ساخت $t(entity.playlist_one)",
"input_public": "عمومی",
"input_name": "$t(common.name)",
"success": "$t(entity.playlist, {\"count\": 1}) ساخته شد",
"success": "$t(entity.playlist_one) ساخته شد",
"input_owner": "$t(common.owner)"
},
"addServer": {
@@ -360,19 +360,19 @@
"ignoreSsl": "نادیده گرفتن ssl ($t(common.restartRequired))"
},
"addToPlaylist": {
"success": "$t(entity.song, {\"count\": 2}) به {{numOfPlaylists}}$t(entity.playlist, {\"count\": 2}) افزوده شد",
"title": "افزودن به $t(entity.playlist, {\"count\": 1})",
"input_playlists": "$t(entity.playlist, {\"count\": 2})",
"success": "$t(entity.song_other) به {{numOfPlaylists}}$t(entity.playlist_other) افزوده شد",
"title": "افزودن به $t(entity.playlist_one)",
"input_playlists": "$t(entity.playlist_other)",
"input_skipDuplicates": "پرش از تکراری‌ها"
},
"lyricSearch": {
"input_name": "$t(common.name)",
"input_artist": "$t(entity.artist, {\"count\": 1})",
"input_artist": "$t(entity.artist_one)",
"title": "جست‌وجو در متن شعر"
},
"editPlaylist": {
"title": "ویرایش $t(entity.playlist, {\"count\": 1})",
"success": "$t(entity.playlist, {\"count\": 1}) با موفقیت بروزرسانی شد",
"title": "ویرایش $t(entity.playlist_one)",
"success": "$t(entity.playlist_one) با موفقیت بروزرسانی شد",
"publicJellyfinNote": "جلی‌فین به دلیلی این‌که فهرست پخش عمومی‌ست یا خصوصی را فاش نمی‌کند. اگر می‌خواهید این عمومی باقی بماند، لطفاٌ ورودی پیش‌رو را منتخب داشته باشید"
},
"queryEditor": {
@@ -417,7 +417,7 @@
"artistWithCount_other": "{{count}} هنرمند",
"folder_one": "پوشه",
"folder_other": "پوشه‌ها",
"smartPlaylist": "$t(entity.playlist, {\"count\": 1}) هوشمند",
"smartPlaylist": "$t(entity.playlist_one) هوشمند",
"album_one": "آلبوم",
"album_other": "آلبوم‌ها",
"genreWithCount_one": "{{count}} ژانر",
@@ -431,12 +431,12 @@
},
"page": {
"albumList": {
"title": "$t(entity.album, {\"count\": 2})",
"title": "$t(entity.album_other)",
"artistAlbums": "آلبوم‌های {{artist}}",
"genreAlbums": "\"{{genre}}\" $t(entity.album, {\"count\": 2})"
"genreAlbums": "\"{{genre}}\" $t(entity.album_other)"
},
"appMenu": {
"settings": "$t(common.setting, {\"count\": 2})",
"settings": "$t(common.setting_other)",
"selectServer": "گزینش سرویس‌دهنده",
"expandSidebar": "گسترش نوار کناری",
"collapseSidebar": "فروکش نوار کناری",
@@ -451,11 +451,11 @@
"appearsOn": "مشاهده می‌شود در",
"about": "درباره‌ی {{artist}}",
"recentReleases": "عرضه‌های اخیر",
"viewAllTracks": "نمایش همه‌ی $t(entity.track, {\"count\": 2})",
"viewAllTracks": "نمایش همه‌ی $t(entity.track_other)",
"topSongsFrom": "قطعه‌های برتر از {{title}}",
"viewAll": "نمایش همه",
"viewDiscography": "نمایش کاتالوگ",
"relatedArtists": "$t(entity.artist, {\"count\": 2}) مربوطه",
"relatedArtists": "$t(entity.artist_other) مربوطه",
"topSongs": "قطعه‌های برتر"
},
"contextMenu": {
@@ -523,21 +523,21 @@
"playbackTab": "پخش"
},
"sidebar": {
"genres": "$t(entity.genre, {\"count\": 2})",
"playlists": "$t(entity.playlist, {\"count\": 2})",
"genres": "$t(entity.genre_other)",
"playlists": "$t(entity.playlist_other)",
"search": "$t(common.search)",
"albumArtists": "$t(entity.albumArtist, {\"count\": 2})",
"albums": "$t(entity.album, {\"count\": 2})",
"folders": "$t(entity.folder, {\"count\": 2})",
"artists": "$t(entity.artist, {\"count\": 2})",
"albumArtists": "$t(entity.albumArtist_other)",
"albums": "$t(entity.album_other)",
"folders": "$t(entity.folder_other)",
"artists": "$t(entity.artist_other)",
"home": "$t(common.home)",
"nowPlaying": "پخش کنونی",
"tracks": "$t(entity.track, {\"count\": 2})",
"settings": "$t(common.setting, {\"count\": 2})",
"shared": "$t(entity.playlist, {\"count\": 2}) اشتراک‌گذاری شده"
"tracks": "$t(entity.track_other)",
"settings": "$t(common.setting_other)",
"shared": "$t(entity.playlist_other) اشتراک‌گذاری شده"
},
"albumDetail": {
"moreFromArtist": "موارد بیشتر از این $t(entity.artist, {\"count\": 1})",
"moreFromArtist": "موارد بیشتر از این $t(entity.artist_one)",
"moreFromGeneric": "موارد بیشتر از {{item}}",
"released": "عرضه شده"
},
@@ -550,9 +550,9 @@
"editServerDetailsTooltip": "ویرایش ریزگان سرویس‌دهنده"
},
"genreList": {
"showAlbums": "نمایش $t(entity.genre, {\"count\": 1}) $t(entity.album, {\"count\": 2})",
"title": "$t(entity.genre, {\"count\": 2})",
"showTracks": "نمایش $t(entity.genre, {\"count\": 1}) $t(entity.track, {\"count\": 2})"
"showAlbums": "نمایش $t(entity.genre_one) $t(entity.album_other)",
"title": "$t(entity.genre_other)",
"showTracks": "نمایش $t(entity.genre_one) $t(entity.track_other)"
},
"globalSearch": {
"commands": {
@@ -563,15 +563,15 @@
"title": "فرمان‌ها"
},
"playlistList": {
"title": "$t(entity.playlist, {\"count\": 2})"
"title": "$t(entity.playlist_other)"
},
"trackList": {
"title": "$t(entity.track, {\"count\": 2})",
"title": "$t(entity.track_other)",
"artistTracks": "قطعه‌های {{artist}}",
"genreTracks": "$t(entity.track, {\"count\": 2}) \"{{genre}}\""
"genreTracks": "$t(entity.track_other) \"{{genre}}\""
},
"albumArtistList": {
"title": "$t(entity.albumArtist, {\"count\": 2})"
"title": "$t(entity.albumArtist_other)"
},
"itemDetail": {
"copyPath": "کپی کردن مسیر در کلیپ‌بورد",
@@ -584,11 +584,11 @@
"size": "$t(common.size)",
"lastPlayed": "آخرین بار پخش شده",
"discNumber": "دیسک",
"songCount": "$t(entity.track, {\"count\": 2})",
"songCount": "$t(entity.track_other)",
"title": "عنوان",
"trackNumber": "قطعه",
"favorite": "مورد علاقه",
"genre": "$t(entity.genre, {\"count\": 1})",
"genre": "$t(entity.genre_one)",
"comment": "دیدگاه",
"playCount": "تعداد پخش",
"rating": "امتیاز",
@@ -608,6 +608,9 @@
"gap": "$t(common.gap)",
"itemGap": "فاصله‌ی آیتم (px)"
},
"view": {
"card": "کارت"
},
"label": {
"playCount": "تعداد پخش",
"dateAdded": "تاریخ افزوده شدن",

Some files were not shown because too many files have changed in this diff Show More