197 Commits
Author SHA1 Message Date
austinried 8f64cfcbca bump version 2023-05-08 06:39:17 +09:00
austinried 1edb2c13da update todo 2023-05-08 06:37:10 +09:00
austinried 7f83204b24 don't pass all ids as params
instead, only pass ids to delete and chunk those by the param limit
2023-05-07 13:56:05 +09:00
austinried 0fe52494d0 update todo 2023-05-07 13:54:56 +09:00
Daniel Playfair Cal 56dbcde3b4 add autofill hints for source page 2023-05-07 13:54:26 +09:00
austinried 8fbc5e6ce4 add artist radio 2023-05-07 13:28:15 +09:00
austinried 979a4b7c73 add plaintext password option
fixes #161
2023-05-06 17:56:03 +09:00
josé m 7b1da24748 Translated using Weblate (Galician)
Currently translated at 100.0% (92 of 92 strings)

Co-authored-by: josé m <correoxm@disroot.org>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/gl/
Translation: Subtracks/subtracks
2023-05-06 09:11:25 +09:00
Sacelo 7014aa85d1 Translated using Weblate (Spanish)
Currently translated at 77.1% (71 of 92 strings)

Co-authored-by: Sacelo <rion020806@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/es/
Translation: Subtracks/subtracks
2023-05-06 09:11:25 +09:00
雨杉叶 abab674322 Translated using Weblate (Chinese (Simplified))
Currently translated at 88.0% (81 of 92 strings)

Co-authored-by: 雨杉叶 <yushaye@outlook.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/zh_Hans/
Translation: Subtracks/subtracks
2023-05-06 09:11:25 +09:00
daniel-225 498bb22a69 Translated using Weblate (German)
Currently translated at 75.0% (69 of 92 strings)

Co-authored-by: daniel-225 <dsoukup@outlook.de>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/
Translation: Subtracks/subtracks
2023-05-06 09:11:25 +09:00
austinried 11fe43a750 add server info fields 2023-04-28 21:59:33 +09:00
austinried 2a60a7306c use english as last fallback locale
fixes #160
2023-04-28 21:45:59 +09:00
austinried ad12a7e15d don't use build number in version 2023-04-28 16:04:59 +09:00
austinried 1c5fea2dd4 Update README.md 2023-04-28 13:22:23 +09:00
austinried 90ac4dc59b fix weblate multiple language issue 2023-04-28 13:13:07 +09:00
austinried 11e50946d2 build on tags 2023-04-28 12:58:49 +09:00
austinried abd0bcd4b9 setup workflows for main 2023-04-28 12:26:02 +09:00
austinried c3c957d527 create .env file first 2023-04-28 12:26:02 +09:00
austinried f415d8a98f rename workflow 2023-04-28 12:26:02 +09:00
austinried 963c15636c aab build, release signing
clean up analyze issues
2023-04-28 12:26:02 +09:00
austinried 7562d93113 get version? 2023-04-28 12:26:02 +09:00
austinried aae58bc5ee use a valid .env file from example 2023-04-28 12:26:02 +09:00
austinried 5be08c16d5 please grab artifact 2023-04-28 12:26:02 +09:00
austinried 0f29b757ee forgot .env file 2023-04-28 12:26:02 +09:00
austinried 49b8d2c423 signing config & build apk 2023-04-28 12:26:02 +09:00
austinried f0f812e66a v2 2023-04-28 12:26:02 +09:00
mohammed_9456 35b037f66c Better README 2023-04-27 18:08:38 +09:00
Roman 985995d45d Translated using Weblate (Czech)
Currently translated at 82.0% (55 of 67 strings)

Translated using Weblate (Czech)

Currently translated at 1.4% (1 of 67 strings)

Added translation using Weblate (Czech)

Co-authored-by: Roman <peposik.r@seznam.cz>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/cs/
Translation: Subtracks/subtracks
2023-03-24 09:07:53 +09:00
Burak Orcun OZKABLAN cb786d6360 Translated using Weblate (Turkish)
Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: Burak Orcun OZKABLAN <borcunozkablan@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/tr/
Translation: Subtracks/subtracks
2023-03-24 09:07:53 +09:00
Mohammed 89416a9017 Translated using Weblate (Arabic)
Currently translated at 97.0% (65 of 67 strings)

Added translation using Weblate (Arabic)

Co-authored-by: Mohammed <lym0991903165@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ar/
Translation: Subtracks/subtracks
2023-03-24 09:07:53 +09:00
jazzyjabroni 6aa8df7d9a Translated using Weblate (Danish)
Currently translated at 82.0% (55 of 67 strings)

Translated using Weblate (Danish)

Currently translated at 77.6% (52 of 67 strings)

Co-authored-by: jazzyjabroni <lordcarmack@tuta.io>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/da/
Translation: Subtracks/subtracks
2023-03-24 09:07:53 +09:00
Maite Guix 16f9f8c54d Translated using Weblate (Catalan)
Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: Maite Guix <maite.guix@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ca/
Translation: Subtracks/subtracks
2023-03-24 09:07:53 +09:00
mariobros 2b041580de Translated using Weblate (Punjabi)
Currently translated at 100.0% (67 of 67 strings)

Translated using Weblate (Punjabi)

Currently translated at 71.6% (48 of 67 strings)

Co-authored-by: mariobros <damanjitsingh96@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/pa/
Translation: Subtracks/subtracks
2023-03-24 09:07:53 +09:00
Nikita Epifanov 9de0984553 Translated using Weblate (Russian)
Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: Nikita Epifanov <nikgreens@protonmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ru/
Translation: Subtracks/subtracks
2022-07-12 16:12:23 +09:00
M-Kedzior 4a73c0ba17 Translated using Weblate (Polish)
Currently translated at 100.0% (67 of 67 strings)

Added translation using Weblate (Polish)

Co-authored-by: M-Kedzior <marcin.kedzior@protonmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/pl/
Translation: Subtracks/subtracks
2022-07-12 16:12:23 +09:00
Joel Calado 3d1d226c43 Translated using Weblate (Portuguese)
Currently translated at 100.0% (67 of 67 strings)

Translated using Weblate (Portuguese)

Currently translated at 11.9% (8 of 67 strings)

Added translation using Weblate (Portuguese)

Co-authored-by: Joel Calado <joelcalado@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/pt/
Translation: Subtracks/subtracks
2022-07-04 10:14:43 +09:00
Xosé M ccead686aa Translated using Weblate (Galician)
Currently translated at 100.0% (67 of 67 strings)

Added translation using Weblate (Galician)

Co-authored-by: Xosé M <xosem@disroot.org>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/gl/
Translation: Subtracks/subtracks
2022-06-28 14:01:35 +09:00
Clyhtsuriva 1f57cc503c Translated using Weblate (French)
Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: Clyhtsuriva <aimeric@adjutor.xyz>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/
Translation: Subtracks/subtracks
2022-06-20 19:06:26 +09:00
austinried 24f9fddae0 Create PRIVACY.md 2022-06-20 19:01:25 +09:00
Maite Guix e4875b10de Translated using Weblate (Catalan)
Currently translated at 98.5% (66 of 67 strings)

Co-authored-by: Maite Guix <maite.guix@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ca/
Translation: Subtracks/subtracks
2022-06-20 18:17:46 +09:00
mariobros 48f1a4ca3a Translated using Weblate (Punjabi)
Currently translated at 70.1% (47 of 67 strings)

Translated using Weblate (Punjabi)

Currently translated at 47.7% (32 of 67 strings)

Co-authored-by: mariobros <damanjitsingh96@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/pa/
Translation: Subtracks/subtracks
2022-06-20 18:17:46 +09:00
dependabot[bot] 0a475c0a0f Bump simple-plist from 1.3.0 to 1.3.1
Bumps [simple-plist](https://github.com/wollardj/simple-plist) from 1.3.0 to 1.3.1.
- [Release notes](https://github.com/wollardj/simple-plist/releases)
- [Commits](https://github.com/wollardj/simple-plist/compare/v1.3.0...v1.3.1)

---
updated-dependencies:
- dependency-name: simple-plist
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-06-06 09:37:26 +09:00
Ali Mürteza Yeşil 1859c5c32d Translated using Weblate (Turkish)
Currently translated at 95.5% (64 of 67 strings)

Added translation using Weblate (Turkish)

Co-authored-by: Ali Mürteza Yeşil <murtezayesil@protonmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/tr/
Translation: Subtracks/subtracks
2022-06-06 08:52:40 +09:00
HeavyDutySoul f159a8fc42 Translated using Weblate (Russian)
Currently translated at 95.5% (64 of 67 strings)

Co-authored-by: HeavyDutySoul <putsli@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ru/
Translation: Subtracks/subtracks
2022-05-07 19:13:31 +09:00
Quyen Truong f700ac9935 Translated using Weblate (Vietnamese)
Currently translated at 100.0% (67 of 67 strings)

Added translation using Weblate (Vietnamese)

Co-authored-by: Quyen Truong <quyent22@cs.washington.edu>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/vi/
Translation: Subtracks/subtracks
2022-05-07 19:13:31 +09:00
ChocolateMoo53 70729bb0e5 Translated using Weblate (Spanish)
Currently translated at 100.0% (67 of 67 strings)

Translated using Weblate (Spanish)

Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: ChocolateMoo53 <rion020806@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/es/
Translation: Subtracks/subtracks
2022-05-07 19:13:31 +09:00
Sargon-Isa 7d5b0d285d Translated using Weblate (German)
Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: Sargon-Isa <Sargon_isa@hotmail.de>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/
Translation: Subtracks/subtracks
2022-05-03 12:07:17 +09:00
ChocolateMoo53 72f53d6d21 Translated using Weblate (Spanish)
Currently translated at 2.9% (2 of 67 strings)

Added translation using Weblate (Spanish)

Co-authored-by: ChocolateMoo53 <rion020806@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/es/
Translation: Subtracks/subtracks
2022-05-03 12:07:17 +09:00
mariobros 5707c93295 Translated using Weblate (Punjabi)
Currently translated at 8.9% (6 of 67 strings)

Added translation using Weblate (Punjabi)

Co-authored-by: mariobros <damanjitsingh96@gmail.com>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/pa/
Translation: Subtracks/subtracks
2022-05-03 12:07:17 +09:00
jazzyjabroni 46a90169a9 Translated using Weblate (Danish)
Currently translated at 74.6% (50 of 67 strings)

Co-authored-by: jazzyjabroni <lordcarmack@tuta.io>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/da/
Translation: Subtracks/subtracks
2022-04-28 18:17:43 +09:00
austinried 27754bd3c3 minor reorg/cleanup 2022-04-28 15:41:45 +09:00
austinried 2bf3e8853d 1.3.0 changelog 2022-04-26 13:19:45 +09:00
austinried e14099472a bump version 1.3.0 2022-04-26 13:17:01 +09:00
austinried ac06e21f37 Update release.yml 2022-04-26 12:53:43 +09:00
austinried 92e2fd93f9 Create release.yml 2022-04-26 12:49:50 +09:00
jazzyjabroni a5ccba69ec Translated using Weblate (Danish)
Currently translated at 59.7% (40 of 67 strings)

Added translation using Weblate (Danish)

Co-authored-by: jazzyjabroni <lordcarmack@tuta.io>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/da/
Translation: Subtracks/subtracks
2022-04-26 11:59:34 +09:00
Sargon-Isa 23eb05a368 Translated using Weblate (German)
Currently translated at 100.0% (67 of 67 strings)

Co-authored-by: Sargon-Isa <Sargon_isa@hotmail.de>
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/
Translation: Subtracks/subtracks
2022-04-26 11:59:34 +09:00
austinried 1f9ee9b462 Merge remote-tracking branch 'weblate/main' into main 2022-04-21 15:01:28 +09:00
Weblate (bot)andHillwah 237b8d2fc6 Translations update from Hosted Weblate (#112)
* Added translation using Weblate (Chinese (Simplified))

* Translated using Weblate (Chinese (Simplified))

Currently translated at 86.5% (58 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/zh_Hans/

* Translated using Weblate (Chinese (Simplified))

Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/zh_Hans/

Co-authored-by: Hillwah <curvycode@gmail.com>
2022-04-21 15:00:36 +09:00
Hillwah 35eada710e Translated using Weblate (Chinese (Simplified))
Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/zh_Hans/
2022-04-21 07:58:39 +02:00
Hillwah 86ef5af6f6 Translated using Weblate (Chinese (Simplified))
Currently translated at 86.5% (58 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/zh_Hans/
2022-04-21 07:58:39 +02:00
Hillwah 76b290c8b3 Added translation using Weblate (Chinese (Simplified)) 2022-04-21 07:58:39 +02:00
austinried a92ad7bfc9 Bugfix/large playlist crash (#111)
* get all song coverArt as they are rendered

doing it all up front was too heavy
temporarily disabled mapping artwork in setQueue, need to fix this

* use cache data for track artwork when available

* fix round art in context menu for songs

* set only the first artwork at play time

then set the rest in the playback service

* handle both cached images and fetching images

* remove commented code

* fix shuffle

fix first thumbnail not being updated on shuffle for now playing background
2022-04-21 14:58:35 +09:00
austinried 1944add558 disable/unmount tabs while clearing image cache 2022-04-21 12:32:01 +09:00
austinried 05e4b46469 fix context menu i18n & view actions 2022-04-21 11:16:28 +09:00
austinried 00652952d8 remove CHECK_LICENSE permission
seems to have been added by react-native-blob-util
2022-04-19 12:55:47 +09:00
retiolus 83864217f9 Translated using Weblate (Catalan)
Currently translated at 89.5% (60 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ca/
2022-04-19 10:30:08 +09:00
retiolus b3ab75699e Added translation using Weblate (Catalan) 2022-04-19 10:30:08 +09:00
Saverio Napolitano 5cde911113 Translated using Weblate (Italian)
Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/it/
2022-04-19 10:30:08 +09:00
Saverio Napolitano 7fda50857f Added translation using Weblate (Italian) 2022-04-19 10:30:08 +09:00
austinried 4ab51ea11a Update issue templates 2022-04-19 10:02:51 +09:00
Austin Riedhammer fcd5c1b167 Translated using Weblate (Japanese)
Currently translated at 28.3% (19 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ja/
2022-04-17 15:06:51 +09:00
austinried 2ccb397164 Merge branch 'main' of github.com:austinried/subtracks into main 2022-04-16 20:20:55 +09:00
Weblate (bot)andSargon 4e3a3133d7 Translations update from Hosted Weblate (#103)
* Translated using Weblate (German)

Currently translated at 97.0% (65 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/

* Translated using Weblate (German)

Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/

Co-authored-by: Sargon <Sargon_isa@hotmail.de>
2022-04-16 20:16:59 +09:00
Sargon 2edd3a73fd Translated using Weblate (German)
Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/
2022-04-16 11:38:38 +02:00
Sargon 4855043cda Translated using Weblate (German)
Currently translated at 97.0% (65 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/
2022-04-16 11:38:38 +02:00
austinried e6e997e4b5 fix plurals falling back to en when no count 2022-04-16 18:38:22 +09:00
austinried c78fc65279 fix empty strings in nb-NO
(i don't know how to pluralize these though, just placeholders)
2022-04-16 18:06:59 +09:00
austinried 52e95dc959 don't use i18n namespaces
there's no need to keep reloading different parts of the object we already cached
2022-04-16 18:06:06 +09:00
austinried b8948fb646 fix norwegian language not being selected
use BCP langauge codes for file names
2022-04-16 17:41:36 +09:00
austinried a91ac29626 Merge remote-tracking branch 'weblate/main' into main 2022-04-16 17:16:19 +09:00
aca677a432 Translations update from Hosted Weblate (#102)
* Added translation using Weblate (German)

* Translated using Weblate (Norwegian Bokmål)

Currently translated at 98.5% (66 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/nb_NO/

* Translated using Weblate (French)

Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* Translated using Weblate (Russian)

Currently translated at 95.5% (64 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ru/

* Translated using Weblate (German)

Currently translated at 94.0% (63 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/

Co-authored-by: Sargon <Sargon_isa@hotmail.de>
Co-authored-by: Allan Nordhøy <epost@anotheragency.no>
Co-authored-by: Clyhtsuriva <aimeric@adjutor.xyz>
Co-authored-by: Nikita Epifanov <nikgreens@protonmail.com>
2022-04-16 17:10:23 +09:00
Sargon 708a404a21 Translated using Weblate (German)
Currently translated at 94.0% (63 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/de/
2022-04-16 10:01:49 +02:00
Nikita Epifanov 7fa861d609 Translated using Weblate (Russian)
Currently translated at 95.5% (64 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ru/
2022-04-16 10:01:49 +02:00
Clyhtsuriva 5a201c783f Translated using Weblate (French)
Currently translated at 100.0% (67 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/
2022-04-16 10:01:49 +02:00
Allan Nordhøy f98ed31475 Translated using Weblate (Norwegian Bokmål)
Currently translated at 98.5% (66 of 67 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/nb_NO/
2022-04-16 10:01:49 +02:00
Sargon 6ebf1d265e Added translation using Weblate (German) 2022-04-16 10:01:49 +02:00
austinried 07c4d14adf don't require build for i18n file PRs 2022-04-16 17:01:39 +09:00
Weblate (bot)andNikita Epifanov 6b1b4c2c4f Added translation using Weblate (Russian) (#101)
Co-authored-by: Nikita Epifanov <nikgreens@protonmail.com>
2022-04-15 22:49:15 +09:00
dependabot[bot] 658d134f64 Bump async from 2.6.3 to 2.6.4 (#100)
Bumps [async](https://github.com/caolan/async) from 2.6.3 to 2.6.4.
- [Release notes](https://github.com/caolan/async/releases)
- [Changelog](https://github.com/caolan/async/blob/v2.6.4/CHANGELOG.md)
- [Commits](https://github.com/caolan/async/compare/v2.6.3...v2.6.4)

---
updated-dependencies:
- dependency-name: async
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-04-15 14:02:22 +09:00
austinried a9dbcfb69d add edit server string i18n
set add/edit header title with i18n
fix albums plural in artist view
2022-04-15 12:55:11 +09:00
860a4cec16 Localization support (#99)
* basic i18n poc

* translate home, filters, tabs

support dot notation in backend for namespaces

* i18n context menu, artist filters, list controls

also nothings here
fix backend not caching fallback

* i18n queue, artist view, search/results

* i18n settings and server view

* Added translation using Weblate (Norwegian Bokmål)

* Translated using Weblate (Norwegian Bokmål)

Currently translated at 100.0% (6 of 6 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/nb_NO/

* Update translation files

Updated by "Cleanup translation files" hook in Weblate.

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/

* Update translation files

Updated by "Cleanup translation files" hook in Weblate.

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/

* Update translation files

Updated by "Cleanup translation files" hook in Weblate.

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/

* fix url escaping

* added some mostly naive text overflow fixes

rewrote filter context menu as a slide in because the old one apparently can't handle dynamic width

* Added translation using Weblate (French)

* Translated using Weblate (French)

Currently translated at 17.4% (11 of 63 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* Translated using Weblate (French)

Currently translated at 19.0% (12 of 63 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* Translated using Weblate (French)

Currently translated at 40.0% (26 of 65 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* add weblate and some pretty badges to readme

* fix link

* Translated using Weblate (French)

Currently translated at 50.7% (33 of 65 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* Translated using Weblate (English)

Currently translated at 100.0% (65 of 65 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/en/

* Translated using Weblate (French)

Currently translated at 90.7% (59 of 65 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* i18n now playing context type

fix overscroll on new filter menu
fix getting default namespace from the i18n backend

* Translated using Weblate (French)

Currently translated at 96.9% (63 of 65 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* Translated using Weblate (French)

Currently translated at 100.0% (66 of 66 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/fr/

* Translated using Weblate (Japanese) (#98)

Currently translated at 7.5% (5 of 66 strings)

Translation: Subtracks/subtracks
Translate-URL: https://hosted.weblate.org/projects/subtracks/subtracks/ja/

Co-authored-by: Austin Riedhammer <austinried@functionkey.xyz>

* little note to remind me why that's there

* update licenses

Co-authored-by: Allan Nordhøy <epost@anotheragency.no>
Co-authored-by: Hosted Weblate <hosted@weblate.org>
Co-authored-by: Clyhtsuriva <aimeric@adjutor.xyz>
2022-04-15 12:11:00 +09:00
austinried 4905f75564 Merge branch 'main' of github.com:austinried/subtracks into main 2022-04-12 10:21:37 +09:00
austinried 6b53d9444d bump version 2022-04-12 10:18:33 +09:00
austinried f39a29159a Fix pausing after playing a few tracks (#94)
we only get this error when playing so we should always keep playing
2022-04-12 09:45:38 +09:00
austinried c1a4b5ede8 restore repeat mode when rebuilding the queue (#93) 2022-04-12 09:45:10 +09:00
austinried d0319eb32d remove ruby stuff for iOS 2022-04-11 15:36:18 +09:00
austinried 9524080d00 move back to api 30 2022-04-11 15:15:57 +09:00
austinried cba32e75b3 downgrade async-storage a bit
some kind of java/jetifier issue in 1.17 that i don't want to deal with
2022-04-11 13:53:11 +09:00
austinried 37d81cb87a update licences 2022-04-11 12:28:33 +09:00
austinried f911688c78 upgade deps
async-storage 1.17.3: required updating sdk to 31, kotlin to 1.6.10
react-native-track-player 2.1.3: added new "android:exported" prop required by API 31
react-native-fs: 2.19.0
2022-04-11 12:14:45 +09:00
austinried bfa6b6f08a upgrade to react-native 0.67.4 2022-04-11 11:07:17 +09:00
austinried 87e83516a1 filter topSongs backup search by artistName 2022-04-11 10:47:51 +09:00
austinried 8196704ccd React Query refactor (#91)
* initial react-query experiments

* use queries for item screens

send the data we do have over routing to prepopulate (album/playlist)
use number for starred because sending Date freaks out react-navigation

* add in equiv. song cover art fix

* reorg, switch artistview over

start mapping song cover art when any are available

* refactor useStar to queries

fix caching for starred items and album cover art

* add hook to reset queries on server change

* refactor search to use query

* fix song cover art setting

* use query for artistInfo

* remove last bits of library state

* cleanup

* use query key factory

already fixed one wrong key...

* require coverart size

* let's try no promise queues on these for now

* image cache uses query

* perf fix for playlist parsing

also use placeholder data so we don't have to deal with staleness

* drill that disabled

also list controls doesn't need its own songs hook/copy

* switch to react-native-blob-util for downloads

slightly slower but allows us to use DownloadManager, which backgrounds downloads so they are no longer corrupted when the app suspends

* add a fake "top songs" based on artist search

then sorted by play count/ratings
artistview should load now even if topSongs fails

* try not to swap between topSongs/search on refetch

set queueContext by song list so the index isn't off if the list changes

* add content type validation for file fetching

also try to speed up existing file return by limiting fs ops

* if the HEAD fails, don't queue the download

* clean up params

* reimpl clear image cache

* precompute contextId

prevents wrong "is playing" when any mismatch between queue and list

* clear images from all servers

use external files dir instead of cache

* fix pressable disabled flicker

don't retry topsongs on failure
try to optimize setqueue and fixcoverart a bit

* wait for queries during clear

* break out fetchExistingFile from fetchFile

allows to tell if file is coming from disk or not
only show placeholder/loading spinner if actually fetching image

* forgot these wouldn't do anything with objects

* remove query cache when switching servers

* add content-disposition extension gathering

add support for progress hook (needs native support still)

* added custom RNBU pkg with progress changes

* fully unmount tabs when server changes

prevents unwanted requests, gives fresh start on switch
fix fixCoverArt not re-rendering in certain cases on search

* use serverId from fetch deps

* fix lint

* update licenses

* just use the whole lodash package

* make using cache buster optional
2022-04-11 09:40:51 +09:00
dependabot[bot] cbd88d0f13 Bump cocoapods-downloader from 1.5.1 to 1.6.3 (#88)
Bumps [cocoapods-downloader](https://github.com/CocoaPods/cocoapods-downloader) from 1.5.1 to 1.6.3.
- [Release notes](https://github.com/CocoaPods/cocoapods-downloader/releases)
- [Changelog](https://github.com/CocoaPods/cocoapods-downloader/blob/master/CHANGELOG.md)
- [Commits](https://github.com/CocoaPods/cocoapods-downloader/compare/1.5.1...1.6.3)

---
updated-dependencies:
- dependency-name: cocoapods-downloader
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-04-06 17:12:10 +09:00
austinried ecb706310b remove react-native-get-random-values (#87)
swap in react-native-uuid, which is a js-only impl of uuid without native requirements
2022-04-06 01:22:05 +09:00
austinried caf544069e switch to useSafeAreaInsets().top (#85)
StatusBar.currentHeight seems just broken on some devices
2022-04-04 12:48:10 +09:00
austinried 8bc4caae78 some files still using old folder names 2022-04-03 10:29:23 +09:00
austinried 5a2ab98af5 repeat v1.1.2 changelog for google play 2022-04-01 10:22:23 +09:00
austinried 3ab9ea9fe8 bump version for google play 2022-04-01 10:19:32 +09:00
austinried b761ad8b84 Release/v1.1.2 (#82)
* add changelog

* increment version
2022-03-28 16:16:48 +09:00
austinried 5169b726ce encode values before using in url (#81) 2022-03-28 15:44:58 +09:00
austinried 41f00ef3f1 update build to main branch
add new ignores
2022-03-28 14:32:08 +09:00
dependabot[bot] abdd1667b7 Bump ansi-regex from 4.1.0 to 4.1.1 (#80)
Bumps [ansi-regex](https://github.com/chalk/ansi-regex) from 4.1.0 to 4.1.1.
- [Release notes](https://github.com/chalk/ansi-regex/releases)
- [Commits](https://github.com/chalk/ansi-regex/compare/v4.1.0...v4.1.1)

---
updated-dependencies:
- dependency-name: ansi-regex
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-03-28 14:21:17 +09:00
dependabot[bot] b6c689ea7e Bump minimist from 1.2.5 to 1.2.6 (#79)
Bumps [minimist](https://github.com/substack/minimist) from 1.2.5 to 1.2.6.
- [Release notes](https://github.com/substack/minimist/releases)
- [Commits](https://github.com/substack/minimist/compare/1.2.5...1.2.6)

---
updated-dependencies:
- dependency-name: minimist
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-03-28 14:21:05 +09:00
dependabot[bot] 2c8bcbcb2f Bump plist from 3.0.4 to 3.0.5 (#78)
Bumps [plist](https://github.com/TooTallNate/node-plist) from 3.0.4 to 3.0.5.
- [Release notes](https://github.com/TooTallNate/node-plist/releases)
- [Changelog](https://github.com/TooTallNate/plist.js/blob/master/History.md)
- [Commits](https://github.com/TooTallNate/node-plist/commits)

---
updated-dependencies:
- dependency-name: plist
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-03-28 14:06:20 +09:00
austinried e412b33d4e run validation before yarn license (#77)
* run validation before yarn license

* attempt to fix CI errors

https://github.com/yarnpkg/yarn/issues/7212
2022-03-28 14:05:49 +09:00
austinried 081251061d Library store refactor (#76)
* start of music store refactor

moving stuff into a state cache
better separate it from view logic

* added paginated list/album list

* reworked fetchAlbumList to remove ui state

refactored home screen to use new method
i broke playing songs somehow, JS thread goes into a loop

* don't reset parts manually, do it all at once

* fixed perf issue related to too many rerenders

rerenders were caused by strict equality check on object/array picks
switched artistInfo to new store
updated zustand and fixed deprecation warnings

* update typescript

and use workspace tsc version for vscode

* remove old artistInfo

* switched to new playlist w/songs

removed more unused stuff

* remove unused + (slightly) rework search

* refactor star

* use only original/large imges for covers/artist

fix view artist from context menu
add loading indicators to song list and artist views (show info we have right away)

* set starred/unstar assuming it works

and correct state on error

* reorg, remove old music slice files

* added back fix for song cover art

* sort artists by localCompare name

* update licenses

* fix now playing background grey bar

* update react-native-gesture-handler

for node-fetch security alert

* fix another gradient height grey bar issue

* update licenses again

* remove thumbnail cache

* rename to remove "Library" from methods

* Revert "remove thumbnail cache"

This reverts commit e0db4931f1.

* use ids for lists, pull state later

* Revert "use only original/large imges for covers/artist"

This reverts commit c9aea9065c.

* deep equal ListItem props for now

this needs a bigger refactor

* use immer as middleware

* refactor api client to use string method

hoping to use this for requestKey/deduping next

* use thumbnails in list items

* Revert "refactor api client to use string method"

This reverts commit 234326135b.

* rename/cleanup

* store servers by id

* get rid of settings selectors

* renames for clarity

remove unused estimateContentLength setting

* remove trackplayer selectors

* fix migration for library filter settings

* fixed shuffle order reporting wrong track/queue

* removed the other selectors

* don't actually need es6/react for our state

* fix slow artist sort on star

localeCompare is too slow for large lists
2022-03-28 13:30:57 +09:00
austinried 09ca4974c5 don't run prepare on yarn install... 2022-03-12 09:24:52 +09:00
austinried d9781f3a47 add build instructions
add yarn script to prepare exoplayer/ffmpeg
2022-02-02 16:03:05 +09:00
austinried ec390f593c Upgrade React Native and deps (#68)
* upgrade RN to 0.67-rc.6
upgrade react-native-reanimated to 2.3.1
debug and release building/working

* update to RN stable 0.67

* yarn upgrade

also use xmldom builtin types

* ignore ndk dir for linting

* upgrade types (RN 0.67 not out yet)

* remove deprecated rule

* actually i like that one, keep for now

* update licenses

* upgrade RN types and use builtin dep

* upgrade RN 0.67.1
2022-01-23 13:36:02 +09:00
austinried 6883a556bf fix boolean 2022-01-12 09:25:45 +09:00
Andrej Shadura 100be96fca Fix autocorrect/autofill in server settings (#59) (#60)
Prevent autocorrection on URLs, disable autoCorrect and
autoCapitalise and set importantForAutofill.
2022-01-11 22:08:42 +09:00
austinried c1e26d23cf reduce api version to lowest currently needed (#53) 2021-12-18 09:50:16 +09:00
austinried 329ef919f7 add .nvmrc for node 14.x 2021-12-15 14:38:15 +09:00
austinried 336e106e01 changelog for 1.1.1 2021-12-15 14:08:37 +09:00
austinried c0f802c27b bump version 1.1.1 2021-12-15 14:05:51 +09:00
austinried da033e697f check if we paused on duck before playing again (#51)
prevents music playing after an alarm or call ends if it wasn't paused by that alarm/call in the first place
2021-12-15 13:59:58 +09:00
austinried 5bb32df16b Create FUNDING.yml 2021-12-13 09:34:22 +09:00
austinried 6cb364531b Release/v1.1.0 (#47)
* bump version for 1.1.0

* add changelog for 1.1.0
2021-12-06 11:05:18 +09:00
austinried 72fa2c765d Trust self-signed user certificates (#46)
* add network config to trust user certificates

* allow clear text traffic again
2021-12-06 10:16:06 +09:00
austinried 0643b6d719 use .view method suffix for 1.14.0 (#45) 2021-12-06 10:05:59 +09:00
dependabot[bot] da79b306b2 Bump tmpl from 1.0.4 to 1.0.5 (#44)
Bumps [tmpl](https://github.com/daaku/nodejs-tmpl) from 1.0.4 to 1.0.5.
- [Release notes](https://github.com/daaku/nodejs-tmpl/releases)
- [Commits](https://github.com/daaku/nodejs-tmpl/commits/v1.0.5)

---
updated-dependencies:
- dependency-name: tmpl
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2021-12-04 15:26:22 +09:00
Theo Salzmannandaustinried 9a6f8b86fc FEATURE: add plain text password toggle to settings (#22)
* FEATURE: add plain text password toggle to settings

* clean up state types, lint, and add migrate

Co-authored-by: austinried <4966622+austinried@users.noreply.github.com>
2021-12-03 15:18:05 +09:00
austinried 37214fcbdc add f-droid badge to readme 2021-09-11 16:40:32 +09:00
austinried eb578fa5e6 use consistent user agent for requests 2021-09-08 15:49:01 +09:00
austinried 51f79ac8ad stop saying my project is html pls 2021-09-08 10:13:54 +09:00
aux4 ddef0fc2c8 Merge pull request #15 from austinried/exoplayer-extension
Build ExoPlayer ffmpeg extension for ALAC playback
2021-09-08 10:06:38 +09:00
austinried dbc72d5259 add ffmpeg license
reworked licenses into a single generated file
2021-09-08 09:32:35 +09:00
austinried f686294aab too many files in here for watchman 2021-09-07 18:37:19 +09:00
austinried 29cdebe424 quiet down wget and unzip
really don't need 5mb of logs every time those run...
2021-09-07 18:32:22 +09:00
austinried ef476552e0 remove gradle wrapper that fails validation 2021-09-07 16:48:49 +09:00
austinried dd0d4d52c1 remove unused exoplayer modules
update licenses
2021-09-07 16:36:12 +09:00
austinried 0c825a3d85 don't lint submodules 2021-09-07 15:44:18 +09:00
austinried 2d07d5f1fa Revert "regen lockfile"
This reverts commit 2dc9e71ab5.
2021-09-07 15:38:52 +09:00
austinried 2dc9e71ab5 regen lockfile 2021-09-07 15:35:10 +09:00
austinried 062b0cadd2 Merge branch 'master' into exoplayer-extension 2021-09-07 15:26:04 +09:00
austinried ad92e6d3ff enable ffmpeg prep for GH builds 2021-09-07 15:23:57 +09:00
austinried 328956d84a bump ram for release builds 2021-09-07 15:23:37 +09:00
austinried 9d58e15b39 build and use ffmpeg extension
pointing at my own repo for RNTP to enable extensions in exoplayer
new prepare script needs to be run to build ffmpeg
2021-09-07 14:40:22 +09:00
austinried 721a42f60f pull in/rely on exoplayer locally 2021-09-07 12:20:52 +09:00
aux4 6a0f5678ec Merge pull request #14 from austinried/dependabot/npm_and_yarn/immer-9.0.6
Bump immer from 9.0.5 to 9.0.6
2021-09-04 15:09:13 +09:00
dependabot[bot] dbfc4172fb Bump immer from 9.0.5 to 9.0.6
Bumps [immer](https://github.com/immerjs/immer) from 9.0.5 to 9.0.6.
- [Release notes](https://github.com/immerjs/immer/releases)
- [Commits](https://github.com/immerjs/immer/compare/v9.0.5...v9.0.6)

---
updated-dependencies:
- dependency-name: immer
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-04 05:46:58 +00:00
austinried 2097a9f7fd remove non-working cast button for now 2021-09-04 14:45:08 +09:00
austinried 3053e2b5c9 add changelog for 1.0.1 2021-09-02 18:01:58 +09:00
austinried 7f1585a6ad bump version 1.0.1 2021-09-02 17:23:38 +09:00
austinried 704edfbaaf remove unused permissions 2021-09-01 18:23:13 +09:00
austinried 5622c007f2 fix text cutting off bottom w/fixed height 2021-09-01 15:11:24 +09:00
austinried 3719a71e0f Merge branch 'master' of github.com:austinried/subtracks 2021-09-01 14:53:10 +09:00
aux4 44fb9a022d update readme coming soon 2021-09-01 10:17:38 +09:00
austinried 45cc51192a Merge branch 'master' of github.com:austinried/subtracks 2021-08-27 15:42:22 +09:00
aux4 d981690ba6 update readme with google play link 2021-08-27 15:41:39 +09:00
austinried 161a621d71 address xmldom security issue
https://github.com/advisories/GHSA-6fc8-4gx4-v693
2021-08-27 13:11:03 +09:00
austinried 7da1afa643 bump version 1.0.0 for release 2021-08-27 11:17:58 +09:00
austinried 77e89fc9e2 add version number to about setion 2021-08-27 09:58:49 +09:00
austinried 36e97cb621 update metadata per google play standards 2021-08-26 16:38:30 +09:00
austinried c539376cc4 add metadata for stores 2021-08-26 16:10:49 +09:00
austinried 0465147a7c bump sdk version for google play 2021-08-26 15:19:03 +09:00
austinried 2e96c61b82 let's do some pre-release builds 2021-08-26 14:38:22 +09:00
austinried 08470aaf00 Merge branch 'master' of github.com:austinried/subtracks 2021-08-26 13:41:38 +09:00
aux4 8ee98327fe update readme 2021-08-26 13:41:07 +09:00
austinried a91f455534 add scripts for bumping versions 2021-08-26 13:33:15 +09:00
austinried ac175d091f ignore html for languages 2021-08-26 12:58:35 +09:00
austinried 872dde4e1c remove bad button style 2021-08-26 12:49:26 +09:00
austinried 23807a3506 update header for better dark mode 2021-08-26 12:48:06 +09:00
austinried a3fda31743 added licenses and webview for them
added link to github page
2021-08-26 12:47:56 +09:00
austinried b8f04e5426 update readme 2021-08-26 08:18:29 +09:00
austinried 46eb293f98 fix net state not being right on startup 2021-08-26 08:17:39 +09:00
austinried 5af187ba48 lint builds 2021-08-26 08:07:32 +09:00
austinried 9847cdb894 fix for search clearing text/not scrolling 2021-08-25 16:32:04 +09:00
austinried fac2b62ec2 improved large album/playlist performance
switched to flatlist for all of those
2021-08-25 16:13:35 +09:00
austinried 81b5bfb56b readme update 2021-08-25 11:26:03 +09:00
austinried 7abf5c0e88 settings wording 2021-08-25 10:43:36 +09:00
austinried ed4a32cba3 remove UI option to disable estimateContentLength 2021-08-25 10:29:59 +09:00
austinried 0778c49b18 Merge branch 'master' of github.com:austinried/subtracks 2021-08-25 10:25:03 +09:00
austinried 3db1d795dc fix player crashing at the end of transcoded track 2021-08-25 10:24:42 +09:00
aux4 07fc618fd2 specify android app in readme 2021-08-24 16:00:21 +09:00
austinried 75da5d16ac Merge branch 'master' of github.com:austinried/subtracks 2021-08-24 15:58:01 +09:00
austinried 1d40ac5b35 stop building on non-app file changes 2021-08-24 15:57:46 +09:00
aux4 6bdd052472 added download badge to readme 2021-08-24 15:52:34 +09:00
austinried 74632eff10 added "get it on" badges" 2021-08-24 15:49:41 +09:00
austinried 3055726fb3 better name/group artifacts 2021-08-24 15:31:22 +09:00
aux4 d10a29b931 fix readme link, add server examples 2021-08-24 14:46:07 +09:00
aux4 75a264ca83 fix readme image formatting 2021-08-24 14:27:27 +09:00
austinried dcd764bd68 add images/features/coming soon to readme 2021-08-24 14:23:00 +09:00
aux4 1a596077fa Merge pull request #1 from austinried/github-actions-test
Use actions to build and sign PRs/releases
2021-08-24 11:27:12 +09:00
22 changed files with 692 additions and 1322 deletions
+99 -33
View File
@@ -22,8 +22,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -55,8 +53,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -66,12 +62,32 @@
], ],
"cs": [ "cs": [
"actionsCancel",
"actionsDelete",
"actionsDownload",
"actionsDownloadCancel",
"actionsDownloadDelete",
"actionsOk",
"controlsShuffle",
"resourcesAlbumCount", "resourcesAlbumCount",
"resourcesArtistCount", "resourcesArtistCount",
"resourcesFilterAlbum",
"resourcesFilterArtist",
"resourcesFilterOwner",
"resourcesFilterYear",
"resourcesPlaylistCount", "resourcesPlaylistCount",
"resourcesSongCount", "resourcesSongCount",
"settingsAboutShareLogs", "resourcesSongListDeleteAllContent",
"settingsAboutChooseLog", "resourcesSongListDeleteAllTitle",
"resourcesSortByAlbum",
"resourcesSortByAlbumCount",
"resourcesSortByTitle",
"resourcesSortByUpdated",
"settingsAboutActionsLicenses",
"settingsAboutActionsProjectHomepage",
"settingsAboutActionsSupport",
"settingsAboutName",
"settingsAboutVersion",
"settingsMusicName", "settingsMusicName",
"settingsMusicOptionsScrobbleDescriptionOff", "settingsMusicOptionsScrobbleDescriptionOff",
"settingsMusicOptionsScrobbleDescriptionOn", "settingsMusicOptionsScrobbleDescriptionOn",
@@ -80,7 +96,12 @@
"settingsNetworkOptionsMinBufferTitle", "settingsNetworkOptionsMinBufferTitle",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn" "settingsNetworkOptionsOfflineModeOn",
"settingsNetworkOptionsStreamFormat",
"settingsNetworkOptionsStreamFormatServerDefault",
"settingsResetActionsClearImageCache",
"settingsResetName",
"settingsServersFieldsName"
], ],
"da": [ "da": [
@@ -112,8 +133,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsMusicOptionsScrobbleDescriptionOff", "settingsMusicOptionsScrobbleDescriptionOff",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
@@ -127,8 +146,29 @@
], ],
"de": [ "de": [
"settingsAboutShareLogs", "actionsDownloadDelete",
"settingsAboutChooseLog" "actionsOk",
"resourcesAlbumCount",
"resourcesArtistCount",
"resourcesFilterAlbum",
"resourcesFilterArtist",
"resourcesFilterOwner",
"resourcesFilterYear",
"resourcesPlaylistCount",
"resourcesSongCount",
"resourcesSongListDeleteAllContent",
"resourcesSongListDeleteAllTitle",
"resourcesSortByAlbum",
"resourcesSortByAlbumCount",
"resourcesSortByTitle",
"resourcesSortByUpdated",
"settingsAboutActionsSupport",
"settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn",
"settingsNetworkOptionsStreamFormat",
"settingsNetworkOptionsStreamFormatServerDefault",
"settingsServersFieldsName"
], ],
"es": [ "es": [
@@ -147,8 +187,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -180,8 +218,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -213,8 +249,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -266,8 +300,6 @@
"settingsAboutActionsLicenses", "settingsAboutActionsLicenses",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutName", "settingsAboutName",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsAboutVersion", "settingsAboutVersion",
"settingsMusicOptionsScrobbleDescriptionOff", "settingsMusicOptionsScrobbleDescriptionOff",
"settingsMusicOptionsScrobbleDescriptionOn", "settingsMusicOptionsScrobbleDescriptionOn",
@@ -324,8 +356,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -357,8 +387,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -390,8 +418,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -401,17 +427,63 @@
], ],
"pt": [ "pt": [
"actionsCancel",
"actionsDelete",
"actionsDownload",
"actionsDownloadCancel",
"actionsDownloadDelete",
"actionsOk",
"controlsShuffle",
"resourcesAlbumCount", "resourcesAlbumCount",
"resourcesArtistCount", "resourcesArtistCount",
"resourcesFilterAlbum",
"resourcesFilterArtist",
"resourcesFilterOwner", "resourcesFilterOwner",
"resourcesFilterYear",
"resourcesPlaylistCount", "resourcesPlaylistCount",
"resourcesSongCount", "resourcesSongCount",
"resourcesSongListDeleteAllContent", "resourcesSongListDeleteAllContent",
"resourcesSongListDeleteAllTitle", "resourcesSongListDeleteAllTitle",
"resourcesSortByAlbum",
"resourcesSortByAlbumCount", "resourcesSortByAlbumCount",
"resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutShareLogs", "settingsAboutActionsSupport",
"settingsAboutChooseLog", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn",
"settingsNetworkOptionsStreamFormat",
"settingsNetworkOptionsStreamFormatServerDefault",
"settingsServersFieldsName"
],
"ru": [
"actionsCancel",
"actionsDelete",
"actionsDownload",
"actionsDownloadCancel",
"actionsDownloadDelete",
"actionsOk",
"controlsShuffle",
"resourcesAlbumCount",
"resourcesArtistCount",
"resourcesFilterAlbum",
"resourcesFilterArtist",
"resourcesFilterOwner",
"resourcesFilterYear",
"resourcesPlaylistCount",
"resourcesSongCount",
"resourcesSongListDeleteAllContent",
"resourcesSongListDeleteAllTitle",
"resourcesSortByAlbum",
"resourcesSortByAlbumCount",
"resourcesSortByTitle",
"resourcesSortByUpdated",
"settingsAboutActionsSupport",
"settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn",
"settingsNetworkOptionsStreamFormat",
"settingsNetworkOptionsStreamFormatServerDefault", "settingsNetworkOptionsStreamFormatServerDefault",
"settingsServersFieldsName" "settingsServersFieldsName"
], ],
@@ -439,8 +511,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -472,8 +542,6 @@
"resourcesSortByTitle", "resourcesSortByTitle",
"resourcesSortByUpdated", "resourcesSortByUpdated",
"settingsAboutActionsSupport", "settingsAboutActionsSupport",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
@@ -488,8 +556,6 @@
"resourcesArtistCount", "resourcesArtistCount",
"resourcesPlaylistCount", "resourcesPlaylistCount",
"resourcesSongCount", "resourcesSongCount",
"settingsAboutShareLogs",
"settingsAboutChooseLog",
"settingsNetworkOptionsOfflineMode", "settingsNetworkOptionsOfflineMode",
"settingsNetworkOptionsOfflineModeOff", "settingsNetworkOptionsOfflineModeOff",
"settingsNetworkOptionsOfflineModeOn", "settingsNetworkOptionsOfflineModeOn",
+1 -8
View File
@@ -4,7 +4,6 @@ import 'package:infinite_scroll_pagination/infinite_scroll_pagination.dart';
import '../services/sync_service.dart'; import '../services/sync_service.dart';
import 'items.dart'; import 'items.dart';
import 'snackbars.dart';
class PagedListQueryView<T> extends HookConsumerWidget { class PagedListQueryView<T> extends HookConsumerWidget {
final PagingController<int, T> pagingController; final PagingController<int, T> pagingController;
@@ -123,13 +122,7 @@ class SyncAllRefresh extends HookConsumerWidget {
@override @override
Widget build(BuildContext context, WidgetRef ref) { Widget build(BuildContext context, WidgetRef ref) {
return RefreshIndicator( return RefreshIndicator(
onRefresh: () async { onRefresh: () => ref.read(syncServiceProvider.notifier).syncAll(),
try {
await ref.read(syncServiceProvider.notifier).syncAll();
} catch (e) {
showErrorSnackbar(context, e.toString());
}
},
child: child, child: child,
); );
} }
-53
View File
@@ -1,16 +1,11 @@
import 'dart:math';
import 'package:auto_route/auto_route.dart'; import 'package:auto_route/auto_route.dart';
import 'package:fast_immutable_collections/fast_immutable_collections.dart'; import 'package:fast_immutable_collections/fast_immutable_collections.dart';
import 'package:flutter/foundation.dart'; import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_gen/gen_l10n/app_localizations.dart'; import 'package:flutter_gen/gen_l10n/app_localizations.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:path/path.dart' as p;
import 'package:share_plus/share_plus.dart';
import 'package:url_launcher/url_launcher.dart'; import 'package:url_launcher/url_launcher.dart';
import '../../log.dart';
import '../../models/support.dart'; import '../../models/support.dart';
import '../../services/settings_service.dart'; import '../../services/settings_service.dart';
import '../../state/init.dart'; import '../../state/init.dart';
@@ -167,54 +162,6 @@ class _About extends HookConsumerWidget {
mode: LaunchMode.externalApplication, mode: LaunchMode.externalApplication,
), ),
), ),
const SizedBox(height: 12),
const _ShareLogsButton(),
],
);
}
}
class _ShareLogsButton extends StatelessWidget {
const _ShareLogsButton();
@override
Widget build(BuildContext context) {
final l = AppLocalizations.of(context);
return Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
OutlinedButton.icon(
icon: const Icon(Icons.share),
label: Text(l.settingsAboutShareLogs),
onPressed: () async {
final files = await logFiles();
if (files.isEmpty) return;
// ignore: use_build_context_synchronously
final value = await showDialog<String>(
context: context,
builder: (context) => MultipleChoiceDialog<String>(
title: l.settingsAboutChooseLog,
current: files.first.path,
options: files
.map((e) => MultiChoiceOption.string(
title: p.basename(e.path),
option: e.path,
))
.toIList(),
),
);
if (value == null) return;
Share.shareXFiles(
[XFile(value, mimeType: 'text/plain')],
subject: 'Logs from subtracks: ${String.fromCharCodes(
List.generate(8, (_) => Random().nextInt(26) + 65),
)}',
);
},
),
], ],
); );
} }
+4 -7
View File
@@ -8,11 +8,9 @@ import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
import '../../database/database.dart'; import '../../database/database.dart';
import '../../log.dart';
import '../../models/settings.dart'; import '../../models/settings.dart';
import '../../services/settings_service.dart'; import '../../services/settings_service.dart';
import '../items.dart'; import '../items.dart';
import '../snackbars.dart';
class SourcePage extends HookConsumerWidget { class SourcePage extends HookConsumerWidget {
final int? id; final int? id;
@@ -46,7 +44,7 @@ class SourcePage extends HookConsumerWidget {
autofillHints: const [AutofillHints.url], autofillHints: const [AutofillHints.url],
required: true, required: true,
validator: (value, label) { validator: (value, label) {
if (!value!.contains(RegExp(r'https?:\/\/'))) { if (Uri.tryParse(value!) == null) {
return '$label must be a valid URL'; return '$label must be a valid URL';
} }
return null; return null;
@@ -66,7 +64,7 @@ class SourcePage extends HookConsumerWidget {
required: true, required: true,
); );
final forcePlaintextPassword = useState(!(source?.useTokenAuth ?? true)); final forcePlaintextPassword = useState(!(source?.useTokenAuth ?? false));
final forcePlaintextSwitch = SwitchListTile( final forcePlaintextSwitch = SwitchListTile(
value: forcePlaintextPassword.value, value: forcePlaintextPassword.value,
title: Text(l.settingsServersOptionsForcePlaintextPasswordTitle), title: Text(l.settingsServersOptionsForcePlaintextPasswordTitle),
@@ -163,9 +161,8 @@ class SourcePage extends HookConsumerWidget {
), ),
); );
} }
} catch (e, st) { } catch (err) {
showErrorSnackbar(context, e.toString()); // TOOD: toast the error or whatever
log.severe('Saving source', e, st);
error = true; error = true;
} finally { } finally {
isSaving.value = false; isSaving.value = false;
-14
View File
@@ -1,14 +0,0 @@
import 'package:flutter/material.dart';
void showErrorSnackbar(BuildContext context, String message) {
final colors = Theme.of(context).colorScheme;
ScaffoldMessenger.of(context).showSnackBar(SnackBar(
content: Text(message, style: TextStyle(color: colors.onErrorContainer)),
backgroundColor: colors.errorContainer,
showCloseIcon: true,
closeIconColor: colors.onErrorContainer,
behavior: SnackBarBehavior.floating,
duration: const Duration(seconds: 10),
));
}
+1 -7
View File
@@ -9,13 +9,11 @@ import 'package:path/path.dart' as p;
import 'package:path_provider/path_provider.dart'; import 'package:path_provider/path_provider.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart'; import 'package:riverpod_annotation/riverpod_annotation.dart';
import '../log.dart';
import '../models/music.dart'; import '../models/music.dart';
import '../models/query.dart'; import '../models/query.dart';
import '../models/settings.dart'; import '../models/settings.dart';
import '../models/support.dart'; import '../models/support.dart';
import 'converters.dart'; import 'converters.dart';
import 'error_logging_database.dart';
part 'database.g.dart'; part 'database.g.dart';
@@ -437,11 +435,7 @@ LazyDatabase _openConnection() {
final dbFolder = await getApplicationDocumentsDirectory(); final dbFolder = await getApplicationDocumentsDirectory();
final file = File(p.join(dbFolder.path, 'subtracks.sqlite')); final file = File(p.join(dbFolder.path, 'subtracks.sqlite'));
// return NativeDatabase.createInBackground(file, logStatements: true); // return NativeDatabase.createInBackground(file, logStatements: true);
return NativeDatabase.createInBackground(file);
return ErrorLoggingDatabase(
NativeDatabase.createInBackground(file),
(e, s) => log.severe('SQL error', e, s),
);
}); });
} }
-94
View File
@@ -1,94 +0,0 @@
import 'dart:async';
import 'package:drift/drift.dart';
import 'package:drift/isolate.dart';
/// https://github.com/simolus3/drift/issues/2326#issuecomment-1445138730
class ErrorLoggingDatabase implements QueryExecutor {
final QueryExecutor inner;
final void Function(Object, StackTrace) onError;
ErrorLoggingDatabase(this.inner, this.onError);
Future<T> _handleErrors<T>(Future<T> Function() body) {
return Future.sync(body)
.onError<DriftWrappedException>((error, stackTrace) {
onError(error, error.trace ?? stackTrace);
throw error;
}).onError<DriftRemoteException>((error, stackTrace) {
onError(error, error.remoteStackTrace ?? stackTrace);
throw error;
});
}
@override
TransactionExecutor beginTransaction() {
return _ErrorLoggingTransactionExecutor(inner.beginTransaction(), onError);
}
@override
Future<void> close() {
return _handleErrors(inner.close);
}
@override
SqlDialect get dialect => inner.dialect;
@override
Future<bool> ensureOpen(QueryExecutorUser user) {
return _handleErrors(() => inner.ensureOpen(user));
}
@override
Future<void> runBatched(BatchedStatements statements) {
return _handleErrors(() => inner.runBatched(statements));
}
@override
Future<void> runCustom(String statement, [List<Object?>? args]) {
return _handleErrors(() => inner.runCustom(statement, args));
}
@override
Future<int> runDelete(String statement, List<Object?> args) {
return _handleErrors(() => inner.runDelete(statement, args));
}
@override
Future<int> runInsert(String statement, List<Object?> args) {
return _handleErrors(() => inner.runInsert(statement, args));
}
@override
Future<List<Map<String, Object?>>> runSelect(
String statement, List<Object?> args) {
return _handleErrors(() => inner.runSelect(statement, args));
}
@override
Future<int> runUpdate(String statement, List<Object?> args) {
return _handleErrors(() => inner.runUpdate(statement, args));
}
}
class _ErrorLoggingTransactionExecutor extends ErrorLoggingDatabase
implements TransactionExecutor {
final TransactionExecutor transaction;
_ErrorLoggingTransactionExecutor(
this.transaction, void Function(Object, StackTrace) onError)
: super(transaction, onError);
@override
Future<void> rollback() {
return _handleErrors(transaction.rollback);
}
@override
Future<void> send() {
return _handleErrors(transaction.send);
}
@override
bool get supportsNestedTransactions => transaction.supportsNestedTransactions;
}
+3 -10
View File
@@ -1,8 +1,7 @@
import 'package:flutter/foundation.dart';
import 'package:http/http.dart'; import 'package:http/http.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart'; import 'package:riverpod_annotation/riverpod_annotation.dart';
import '../log.dart';
part 'client.g.dart'; part 'client.g.dart';
const Map<String, String> subtracksHeaders = { const Map<String, String> subtracksHeaders = {
@@ -15,14 +14,8 @@ class SubtracksHttpClient extends BaseClient {
@override @override
Future<StreamedResponse> send(BaseRequest request) { Future<StreamedResponse> send(BaseRequest request) {
request.headers.addAll(subtracksHeaders); request.headers.addAll(subtracksHeaders);
log.info('${request.method} ${request.url}'); if (kDebugMode) print('${request.method} ${request.url}');
return request.send();
try {
return request.send();
} catch (e, st) {
log.severe('HTTP client: ${request.method} ${request.url}', e, st);
rethrow;
}
} }
} }
+165 -225
View File
@@ -1,226 +1,166 @@
{ {
"actionsStar": "Ohodnotit", "actionsStar": "Ohodnotit",
"@actionsStar": {}, "@actionsStar": {},
"actionsUnstar": "Zrušit hodnocení", "actionsUnstar": "Zrušit hodnocení",
"@actionsUnstar": {}, "@actionsUnstar": {},
"messagesNothingHere": "Zde nic není…", "messagesNothingHere": "Zde nic není…",
"@messagesNothingHere": {}, "@messagesNothingHere": {},
"navigationTabsHome": "Domů", "navigationTabsHome": "Domů",
"@navigationTabsHome": {}, "@navigationTabsHome": {},
"navigationTabsLibrary": "Knihovna", "navigationTabsLibrary": "Knihovna",
"@navigationTabsLibrary": {}, "@navigationTabsLibrary": {},
"navigationTabsSearch": "Hledat", "navigationTabsSearch": "Hledat",
"@navigationTabsSearch": {}, "@navigationTabsSearch": {},
"navigationTabsSettings": "Nastavení", "navigationTabsSettings": "Nastavení",
"@navigationTabsSettings": {}, "@navigationTabsSettings": {},
"resourcesAlbumActionsPlay": "Přehrát album", "resourcesAlbumActionsPlay": "Přehrát album",
"@resourcesAlbumActionsPlay": {}, "@resourcesAlbumActionsPlay": {},
"resourcesAlbumActionsView": "Zobrazit album", "resourcesAlbumActionsView": "Zobrazit album",
"@resourcesAlbumActionsView": {}, "@resourcesAlbumActionsView": {},
"resourcesAlbumListsSort": "Seřadit alba", "resourcesAlbumListsSort": "Seřadit alba",
"@resourcesAlbumListsSort": {}, "@resourcesAlbumListsSort": {},
"resourcesAlbumName": "{count,plural, =1{Album} few{Alba} many{Alba} other{Alba}}", "resourcesAlbumName": "{count,plural, =1{Album} few{Alba} many{Alba} other{Alba}}",
"@resourcesAlbumName": { "@resourcesAlbumName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesArtistActionsView": "Zobrazit umělce", "resourcesArtistActionsView": "Zobrazit umělce",
"@resourcesArtistActionsView": {}, "@resourcesArtistActionsView": {},
"resourcesArtistListsSort": "Seřadit umělce", "resourcesArtistListsSort": "Seřadit umělce",
"@resourcesArtistListsSort": {}, "@resourcesArtistListsSort": {},
"resourcesArtistName": "{count,plural, =1{Umělec} few{Umělci} many{Umělci} other{Umělci}}", "resourcesArtistName": "{count,plural, =1{Umělec} few{Umělci} many{Umělci} other{Umělci}}",
"@resourcesArtistName": { "@resourcesArtistName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesFilterGenre": "Podle žánru", "resourcesFilterGenre": "Podle žánru",
"@resourcesFilterGenre": {}, "@resourcesFilterGenre": {},
"resourcesFilterStarred": "Ohodnocené", "resourcesFilterStarred": "Ohodnocené",
"@resourcesFilterStarred": {}, "@resourcesFilterStarred": {},
"resourcesPlaylistActionsPlay": "Přehrát seznam skladeb", "resourcesPlaylistActionsPlay": "Přehrát seznam skladeb",
"@resourcesPlaylistActionsPlay": {}, "@resourcesPlaylistActionsPlay": {},
"resourcesPlaylistName": "{count,plural, =1{Seznam skladeb} few{Seznamy skladeb} many{Seznamy skladeb} other{Seznamy skladeb}}", "resourcesPlaylistName": "{count,plural, =1{Seznam skladeb} few{Seznamy skladeb} many{Seznamy skladeb} other{Seznamy skladeb}}",
"@resourcesPlaylistName": { "@resourcesPlaylistName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesQueueName": "{count,plural, =1{Fronta} few{Fronty} many{Fronty} other{Fronty}}", "resourcesQueueName": "{count,plural, =1{Fronta} few{Fronty} many{Fronty} other{Fronty}}",
"@resourcesQueueName": { "@resourcesQueueName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesSongListsArtistTopSongs": "Top skladby", "resourcesSongListsArtistTopSongs": "Top skladby",
"@resourcesSongListsArtistTopSongs": {}, "@resourcesSongListsArtistTopSongs": {},
"resourcesSongName": "{count,plural, =1{Skladba} few{Skladby} many{Skladby} other{Skladby}}", "resourcesSongName": "{count,plural, =1{Skladba} few{Skladby} many{Skladby} other{Skladby}}",
"@resourcesSongName": { "@resourcesSongName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesSortByAdded": "Nedávno přidané", "resourcesSortByAdded": "Nedávno přidané",
"@resourcesSortByAdded": {}, "@resourcesSortByAdded": {},
"resourcesSortByArtist": "Umělce", "resourcesSortByArtist": "Podle umělce",
"@resourcesSortByArtist": {}, "@resourcesSortByArtist": {},
"resourcesSortByFrequentlyPlayed": "Často přehrávané", "resourcesSortByFrequentlyPlayed": "Často přehrávané",
"@resourcesSortByFrequentlyPlayed": {}, "@resourcesSortByFrequentlyPlayed": {},
"resourcesSortByName": "Názvu", "resourcesSortByName": "Podle názvu",
"@resourcesSortByName": {}, "@resourcesSortByName": {},
"resourcesSortByRandom": "Náhodně", "resourcesSortByRandom": "Náhodně",
"@resourcesSortByRandom": {}, "@resourcesSortByRandom": {},
"resourcesSortByRecentlyPlayed": "Často přehrávané", "resourcesSortByRecentlyPlayed": "Často přehrávané",
"@resourcesSortByRecentlyPlayed": {}, "@resourcesSortByRecentlyPlayed": {},
"resourcesSortByYear": "Roku", "resourcesSortByYear": "Podle roku",
"@resourcesSortByYear": {}, "@resourcesSortByYear": {},
"searchHeaderTitle": "Hledat: {query}", "searchHeaderTitle": "Hledat: {query}",
"@searchHeaderTitle": { "@searchHeaderTitle": {
"placeholders": { "placeholders": {
"query": { "query": {
"type": "String" "type": "String"
} }
} }
}, },
"searchInputPlaceholder": "Hledat", "searchInputPlaceholder": "Hledat",
"@searchInputPlaceholder": {}, "@searchInputPlaceholder": {},
"searchMoreResults": "Více…", "searchMoreResults": "Více…",
"@searchMoreResults": {}, "@searchMoreResults": {},
"searchNowPlayingContext": "Výsledky hledání", "searchNowPlayingContext": "Výsledky hledání",
"@searchNowPlayingContext": {}, "@searchNowPlayingContext": {},
"settingsNetworkName": "Síť", "settingsNetworkName": "Síť",
"@settingsNetworkName": {}, "@settingsNetworkName": {},
"settingsNetworkOptionsMaxBitrateMobileTitle": "Maximální datový tok (mobil)", "settingsNetworkOptionsMaxBitrateMobileTitle": "Maximální datový tok (mobil)",
"@settingsNetworkOptionsMaxBitrateMobileTitle": {}, "@settingsNetworkOptionsMaxBitrateMobileTitle": {},
"settingsNetworkOptionsMaxBitrateWifiTitle": "Maximální datový tok (Wi-Fi)", "settingsNetworkOptionsMaxBitrateWifiTitle": "Maximální datový tok (Wi-Fi)",
"@settingsNetworkOptionsMaxBitrateWifiTitle": {}, "@settingsNetworkOptionsMaxBitrateWifiTitle": {},
"settingsNetworkValuesKbps": "{value}kbps", "settingsNetworkValuesKbps": "{value}kbps",
"@settingsNetworkValuesKbps": { "@settingsNetworkValuesKbps": {
"placeholders": { "placeholders": {
"value": { "value": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsNetworkValuesSeconds": "{value} sekund", "settingsNetworkValuesSeconds": "{value} sekund",
"@settingsNetworkValuesSeconds": { "@settingsNetworkValuesSeconds": {
"placeholders": { "placeholders": {
"value": { "value": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsNetworkValuesUnlimitedKbps": "Neomezeno", "settingsNetworkValuesUnlimitedKbps": "Neomezeno",
"@settingsNetworkValuesUnlimitedKbps": {}, "@settingsNetworkValuesUnlimitedKbps": {},
"settingsServersActionsAdd": "Přidat server", "settingsServersActionsAdd": "Přidat server",
"@settingsServersActionsAdd": {}, "@settingsServersActionsAdd": {},
"settingsServersActionsDelete": "Odstranit", "settingsServersActionsDelete": "Odstranit",
"@settingsServersActionsDelete": {}, "@settingsServersActionsDelete": {},
"settingsServersActionsEdit": "Upravit server", "settingsServersActionsEdit": "Upravit server",
"@settingsServersActionsEdit": {}, "@settingsServersActionsEdit": {},
"settingsServersActionsSave": "Uložit", "settingsServersActionsSave": "Uložit",
"@settingsServersActionsSave": {}, "@settingsServersActionsSave": {},
"settingsServersActionsTestConnection": "Otestovat spojení", "settingsServersActionsTestConnection": "Otestovat spojení",
"@settingsServersActionsTestConnection": {}, "@settingsServersActionsTestConnection": {},
"settingsServersFieldsAddress": "Adresa", "settingsServersFieldsAddress": "Adresa",
"@settingsServersFieldsAddress": {}, "@settingsServersFieldsAddress": {},
"settingsServersFieldsPassword": "Heslo", "settingsServersFieldsPassword": "Heslo",
"@settingsServersFieldsPassword": {}, "@settingsServersFieldsPassword": {},
"settingsServersFieldsUsername": "Uživ. jméno", "settingsServersFieldsUsername": "Uživ. jméno",
"@settingsServersFieldsUsername": {}, "@settingsServersFieldsUsername": {},
"settingsServersMessagesConnectionFailed": "Připojení k {address} selhalo, zkontrolujte nastavení nebo server", "settingsServersMessagesConnectionFailed": "Připojení k {address} selhalo, zkontrolujte nastavení nebo server",
"@settingsServersMessagesConnectionFailed": { "@settingsServersMessagesConnectionFailed": {
"placeholders": { "placeholders": {
"address": { "address": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsServersMessagesConnectionOk": "Připojení k {address} je OK!", "settingsServersMessagesConnectionOk": "Připojení k {address} je OK!",
"@settingsServersMessagesConnectionOk": { "@settingsServersMessagesConnectionOk": {
"placeholders": { "placeholders": {
"address": { "address": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsServersName": "Servery", "settingsServersName": "Servery",
"@settingsServersName": {}, "@settingsServersName": {},
"settingsServersOptionsForcePlaintextPasswordDescriptionOff": "Posílat heslo jako token + salt", "settingsServersOptionsForcePlaintextPasswordDescriptionOff": "Posílat heslo jako token + salt",
"@settingsServersOptionsForcePlaintextPasswordDescriptionOff": {}, "@settingsServersOptionsForcePlaintextPasswordDescriptionOff": {},
"settingsServersOptionsForcePlaintextPasswordDescriptionOn": "Posílat heslo v prostém textu (zastaralé, ujistěte se, že je vaše připojení zabezpečené!)", "settingsServersOptionsForcePlaintextPasswordDescriptionOn": "Posílat heslo v prostém textu (zastaralé, ujistěte se, že je vaše připojení zabezpečené!)",
"@settingsServersOptionsForcePlaintextPasswordDescriptionOn": {}, "@settingsServersOptionsForcePlaintextPasswordDescriptionOn": {},
"settingsServersOptionsForcePlaintextPasswordTitle": "Vynutit heslo ve formátu prostého textu", "settingsServersOptionsForcePlaintextPasswordTitle": "Vynutit heslo ve formátu prostého textu",
"@settingsServersOptionsForcePlaintextPasswordTitle": {}, "@settingsServersOptionsForcePlaintextPasswordTitle": {}
"actionsDownloadDelete": "Smazat stažené", }
"@actionsDownloadDelete": {},
"actionsOk": "OK",
"@actionsOk": {},
"actionsCancel": "Zrušit",
"@actionsCancel": {},
"actionsDownload": "Stáhnout",
"@actionsDownload": {},
"controlsShuffle": "Náhodně",
"@controlsShuffle": {},
"resourcesFilterAlbum": "Album",
"@resourcesFilterAlbum": {},
"resourcesFilterArtist": "Umělec",
"@resourcesFilterArtist": {},
"resourcesFilterYear": "Rok",
"@resourcesFilterYear": {},
"resourcesFilterOwner": "Majitele",
"@resourcesFilterOwner": {},
"resourcesSongListDeleteAllTitle": "Smazat stažené?",
"@resourcesSongListDeleteAllTitle": {},
"resourcesSongListDeleteAllContent": "Toto odstraní všechny stažené soubory s hudbou.",
"@resourcesSongListDeleteAllContent": {},
"resourcesSortByUpdated": "Naposledy upravené",
"@resourcesSortByUpdated": {},
"resourcesSortByAlbum": "Alba",
"@resourcesSortByAlbum": {},
"resourcesSortByAlbumCount": "Počtu alb",
"@resourcesSortByAlbumCount": {},
"resourcesSortByTitle": "Názvu",
"@resourcesSortByTitle": {},
"settingsAboutActionsLicenses": "Licence",
"@settingsAboutActionsLicenses": {},
"settingsAboutActionsProjectHomepage": "Stránka projektu",
"@settingsAboutActionsProjectHomepage": {},
"settingsAboutActionsSupport": "Podpořit vývojáře 💜",
"@settingsAboutActionsSupport": {},
"settingsAboutVersion": "verze {version}",
"@settingsAboutVersion": {
"placeholders": {
"version": {
"type": "String"
}
}
},
"settingsNetworkOptionsStreamFormat": "Preferovaný formát pro streamování",
"@settingsNetworkOptionsStreamFormat": {},
"settingsNetworkOptionsStreamFormatServerDefault": "Použít nastavení serveru",
"@settingsNetworkOptionsStreamFormatServerDefault": {},
"settingsResetActionsClearImageCache": "Smazat mezipaměť obrázků",
"@settingsResetActionsClearImageCache": {},
"settingsResetName": "Resetovat",
"@settingsResetName": {},
"settingsServersFieldsName": "Jméno",
"@settingsServersFieldsName": {},
"settingsAboutName": "O aplikaci",
"@settingsAboutName": {},
"actionsDownloadCancel": "Zrušit stahování",
"@actionsDownloadCancel": {},
"actionsDelete": "Smazat",
"@actionsDelete": {}
}
+1 -71
View File
@@ -202,75 +202,5 @@
"controlsShuffle": "Zufall", "controlsShuffle": "Zufall",
"@controlsShuffle": {}, "@controlsShuffle": {},
"actionsCancel": "Abbrechen", "actionsCancel": "Abbrechen",
"@actionsCancel": {}, "@actionsCancel": {}
"actionsDownloadDelete": "Heruntergeladene Inhalte löschen",
"@actionsDownloadDelete": {},
"actionsOk": "OK",
"@actionsOk": {},
"resourcesAlbumCount": "{count,plural, =1{{count} Album} other{{count} Alben}}",
"@resourcesAlbumCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesFilterAlbum": "Album",
"@resourcesFilterAlbum": {},
"resourcesArtistCount": "{count,plural, =1{{count} Künstler} other{{count} Künstler}}",
"@resourcesArtistCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesFilterArtist": "Künstler",
"@resourcesFilterArtist": {},
"resourcesFilterOwner": "Besitzer",
"@resourcesFilterOwner": {},
"resourcesFilterYear": "Jahr",
"@resourcesFilterYear": {},
"resourcesPlaylistCount": "{count,plural, =1{{count} Playlist} other{{count} Playlists}}",
"@resourcesPlaylistCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesSongCount": "{count,plural, =1{{count} Song} other{{count} Songs}}",
"@resourcesSongCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesSongListDeleteAllContent": "Hierdurch werden alle heruntergeladenen Inhalte entfernt.",
"@resourcesSongListDeleteAllContent": {},
"resourcesSortByAlbum": "Album",
"@resourcesSortByAlbum": {},
"resourcesSortByAlbumCount": "Albenanzahl",
"@resourcesSortByAlbumCount": {},
"resourcesSortByTitle": "Titel",
"@resourcesSortByTitle": {},
"resourcesSortByUpdated": "Kürzlich hinzugefügt",
"@resourcesSortByUpdated": {},
"settingsAboutActionsSupport": "Den Entwickler unterstützen",
"@settingsAboutActionsSupport": {},
"settingsNetworkOptionsOfflineMode": "Offline Modus",
"@settingsNetworkOptionsOfflineMode": {},
"settingsNetworkOptionsOfflineModeOff": "Nutze das Internet um Musik zu synchronisieren.",
"@settingsNetworkOptionsOfflineModeOff": {},
"settingsNetworkOptionsOfflineModeOn": "Nutze nicht das Internet um Musik zu synchronisieren.",
"@settingsNetworkOptionsOfflineModeOn": {},
"settingsNetworkOptionsStreamFormat": "Bevorzugtes Streaming-Format",
"@settingsNetworkOptionsStreamFormat": {},
"settingsServersFieldsName": "Name",
"@settingsServersFieldsName": {},
"resourcesSongListDeleteAllTitle": "Downloads löschen?",
"@resourcesSongListDeleteAllTitle": {},
"settingsNetworkOptionsStreamFormatServerDefault": "Server-Standard verwenden",
"@settingsNetworkOptionsStreamFormatServerDefault": {}
} }
-4
View File
@@ -173,10 +173,6 @@
"@settingsAboutActionsSupport": {}, "@settingsAboutActionsSupport": {},
"settingsAboutName": "About", "settingsAboutName": "About",
"@settingsAboutName": {}, "@settingsAboutName": {},
"settingsAboutShareLogs": "Share logs",
"@settingsAboutShareLogs": {},
"settingsAboutChooseLog": "Choose a log file",
"@settingsAboutChooseLog": {},
"settingsAboutVersion": "version {version}", "settingsAboutVersion": "version {version}",
"@settingsAboutVersion": { "@settingsAboutVersion": {
"placeholders": { "placeholders": {
+1 -5
View File
@@ -272,9 +272,5 @@
"resourcesSortByTitle": "Título", "resourcesSortByTitle": "Título",
"@resourcesSortByTitle": {}, "@resourcesSortByTitle": {},
"resourcesSortByUpdated": "Actualizado recentemente", "resourcesSortByUpdated": "Actualizado recentemente",
"@resourcesSortByUpdated": {}, "@resourcesSortByUpdated": {}
"settingsAboutShareLogs": "Compartir rexistros",
"@settingsAboutShareLogs": {},
"settingsAboutChooseLog": "Escolle un ficheiro de rexistro",
"@settingsAboutChooseLog": {}
} }
+195 -229
View File
@@ -1,230 +1,196 @@
{ {
"actionsStar": "Favorito", "actionsStar": "Favorito",
"@actionsStar": {}, "@actionsStar": {},
"actionsUnstar": "Remover favorito", "actionsUnstar": "Remover favorito",
"@actionsUnstar": {}, "@actionsUnstar": {},
"messagesNothingHere": "Não existe nada…", "messagesNothingHere": "Não existe nada…",
"@messagesNothingHere": {}, "@messagesNothingHere": {},
"navigationTabsHome": "Início", "navigationTabsHome": "Início",
"@navigationTabsHome": {}, "@navigationTabsHome": {},
"navigationTabsLibrary": "Biblioteca", "navigationTabsLibrary": "Biblioteca",
"@navigationTabsLibrary": {}, "@navigationTabsLibrary": {},
"navigationTabsSearch": "Procurar", "navigationTabsSearch": "Procurar",
"@navigationTabsSearch": {}, "@navigationTabsSearch": {},
"navigationTabsSettings": "Definições", "navigationTabsSettings": "Definições",
"@navigationTabsSettings": {}, "@navigationTabsSettings": {},
"resourcesAlbumActionsPlay": "Tocar Álbum", "resourcesAlbumActionsPlay": "Tocar Álbum",
"@resourcesAlbumActionsPlay": {}, "@resourcesAlbumActionsPlay": {},
"resourcesAlbumActionsView": "Ver Álbum", "resourcesAlbumActionsView": "Ver Álbum",
"@resourcesAlbumActionsView": {}, "@resourcesAlbumActionsView": {},
"resourcesAlbumListsSort": "Ordenar Álbuns", "resourcesAlbumListsSort": "Ordenar Álbuns",
"@resourcesAlbumListsSort": {}, "@resourcesAlbumListsSort": {},
"resourcesAlbumName": "{count,plural, =1{Álbum} other{Álbuns}}", "resourcesAlbumName": "{count,plural, =1{Álbum} other{Álbuns}}",
"@resourcesAlbumName": { "@resourcesAlbumName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesArtistActionsView": "Ver Artista", "resourcesArtistActionsView": "Ver Artista",
"@resourcesArtistActionsView": {}, "@resourcesArtistActionsView": {},
"resourcesArtistListsSort": "Ordenar Artistas", "resourcesArtistListsSort": "Ordenar Artistas",
"@resourcesArtistListsSort": {}, "@resourcesArtistListsSort": {},
"resourcesArtistName": "{count,plural, =1{Artista} other{Artistas}}", "resourcesArtistName": "{count,plural, =1{Artista} other{Artistas}}",
"@resourcesArtistName": { "@resourcesArtistName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesFilterGenre": "Por Género", "resourcesFilterGenre": "Por Género",
"@resourcesFilterGenre": {}, "@resourcesFilterGenre": {},
"resourcesFilterStarred": "Favoritos", "resourcesFilterStarred": "Favoritos",
"@resourcesFilterStarred": {}, "@resourcesFilterStarred": {},
"resourcesPlaylistActionsPlay": "Tocar Playlist", "resourcesPlaylistActionsPlay": "Tocar Playlist",
"@resourcesPlaylistActionsPlay": {}, "@resourcesPlaylistActionsPlay": {},
"resourcesPlaylistName": "{count,plural, =1{Lista} other{Listas}}", "resourcesPlaylistName": "{count,plural, =1{Lista} other{Listas}}",
"@resourcesPlaylistName": { "@resourcesPlaylistName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesQueueName": "{count,plural, =1{Fila} other{Filas}}", "resourcesQueueName": "{count,plural, =1{Fila} other{Filas}}",
"@resourcesQueueName": { "@resourcesQueueName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesSongListsArtistTopSongs": "Top Músicas", "resourcesSongListsArtistTopSongs": "Top Músicas",
"@resourcesSongListsArtistTopSongs": {}, "@resourcesSongListsArtistTopSongs": {},
"resourcesSongName": "{count,plural, =1{Música} other{Músicas}}", "resourcesSongName": "{count,plural, =1{Música} other{Músicas}}",
"@resourcesSongName": { "@resourcesSongName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesSortByAdded": "Adicionado recentemente", "resourcesSortByAdded": "Adicionado recentemente",
"@resourcesSortByAdded": {}, "@resourcesSortByAdded": {},
"resourcesSortByArtist": "Por Artista", "resourcesSortByArtist": "Por Artista",
"@resourcesSortByArtist": {}, "@resourcesSortByArtist": {},
"resourcesSortByFrequentlyPlayed": "Mais Tocado", "resourcesSortByFrequentlyPlayed": "Mais Tocado",
"@resourcesSortByFrequentlyPlayed": {}, "@resourcesSortByFrequentlyPlayed": {},
"resourcesSortByName": "Por Nome", "resourcesSortByName": "Por Nome",
"@resourcesSortByName": {}, "@resourcesSortByName": {},
"resourcesSortByRandom": "Aleatório", "resourcesSortByRandom": "Aleatório",
"@resourcesSortByRandom": {}, "@resourcesSortByRandom": {},
"resourcesSortByRecentlyPlayed": "Ouviu recentemente", "resourcesSortByRecentlyPlayed": "Ouviu recentemente",
"@resourcesSortByRecentlyPlayed": {}, "@resourcesSortByRecentlyPlayed": {},
"resourcesSortByYear": "Por Ano", "resourcesSortByYear": "Por Ano",
"@resourcesSortByYear": {}, "@resourcesSortByYear": {},
"searchHeaderTitle": "Procurar: {query}", "searchHeaderTitle": "Procurar: {query}",
"@searchHeaderTitle": { "@searchHeaderTitle": {
"placeholders": { "placeholders": {
"query": { "query": {
"type": "String" "type": "String"
} }
} }
}, },
"searchInputPlaceholder": "Procurar", "searchInputPlaceholder": "Procurar",
"@searchInputPlaceholder": {}, "@searchInputPlaceholder": {},
"searchMoreResults": "Mais…", "searchMoreResults": "Mais…",
"@searchMoreResults": {}, "@searchMoreResults": {},
"searchNowPlayingContext": "Resultados da Pesquisa", "searchNowPlayingContext": "Resultados da Pesquisa",
"@searchNowPlayingContext": {}, "@searchNowPlayingContext": {},
"settingsAboutActionsLicenses": "Licenças", "settingsAboutActionsLicenses": "Licenças",
"@settingsAboutActionsLicenses": {}, "@settingsAboutActionsLicenses": {},
"settingsAboutActionsProjectHomepage": "Página do Projeto", "settingsAboutActionsProjectHomepage": "Página do Projeto",
"@settingsAboutActionsProjectHomepage": {}, "@settingsAboutActionsProjectHomepage": {},
"settingsAboutName": "Acerca", "settingsAboutName": "Acerca",
"@settingsAboutName": {}, "@settingsAboutName": {},
"settingsAboutVersion": "versão {version}", "settingsAboutVersion": "versão {version}",
"@settingsAboutVersion": { "@settingsAboutVersion": {
"placeholders": { "placeholders": {
"version": { "version": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsMusicName": "Música", "settingsMusicName": "Música",
"@settingsMusicName": {}, "@settingsMusicName": {},
"settingsMusicOptionsScrobbleDescriptionOff": "Não enviar histórico de reproduções por scrobble", "settingsMusicOptionsScrobbleDescriptionOff": "Não enviar histórico de reproduções por scrobble",
"@settingsMusicOptionsScrobbleDescriptionOff": {}, "@settingsMusicOptionsScrobbleDescriptionOff": {},
"settingsMusicOptionsScrobbleDescriptionOn": "Enviar histórico de reproduções por scrobble", "settingsMusicOptionsScrobbleDescriptionOn": "Enviar histórico de reproduções por scrobble",
"@settingsMusicOptionsScrobbleDescriptionOn": {}, "@settingsMusicOptionsScrobbleDescriptionOn": {},
"settingsMusicOptionsScrobbleTitle": "Enviar reproduções por scrobble", "settingsMusicOptionsScrobbleTitle": "Enviar reproduções por scrobble",
"@settingsMusicOptionsScrobbleTitle": {}, "@settingsMusicOptionsScrobbleTitle": {},
"settingsNetworkName": "Rede", "settingsNetworkName": "Rede",
"@settingsNetworkName": {}, "@settingsNetworkName": {},
"settingsNetworkOptionsMaxBitrateMobileTitle": "Bitrate Máximo (móvel)", "settingsNetworkOptionsMaxBitrateMobileTitle": "Bitrate Máximo (móvel)",
"@settingsNetworkOptionsMaxBitrateMobileTitle": {}, "@settingsNetworkOptionsMaxBitrateMobileTitle": {},
"settingsNetworkOptionsMaxBitrateWifiTitle": "Bitrate Máximo (Wi-Fi)", "settingsNetworkOptionsMaxBitrateWifiTitle": "Bitrate Máximo (Wi-Fi)",
"@settingsNetworkOptionsMaxBitrateWifiTitle": {}, "@settingsNetworkOptionsMaxBitrateWifiTitle": {},
"settingsNetworkOptionsMaxBufferTitle": "Tempo de buffer máximo", "settingsNetworkOptionsMaxBufferTitle": "Tempo de buffer máximo",
"@settingsNetworkOptionsMaxBufferTitle": {}, "@settingsNetworkOptionsMaxBufferTitle": {},
"settingsNetworkOptionsMinBufferTitle": "Tempo de buffer mínimo", "settingsNetworkOptionsMinBufferTitle": "Tempo de buffer mínimo",
"@settingsNetworkOptionsMinBufferTitle": {}, "@settingsNetworkOptionsMinBufferTitle": {},
"settingsNetworkValuesKbps": "{value}kbps", "settingsNetworkValuesKbps": "{value}kbps",
"@settingsNetworkValuesKbps": { "@settingsNetworkValuesKbps": {
"placeholders": { "placeholders": {
"value": { "value": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsNetworkValuesSeconds": "{value} segundos", "settingsNetworkValuesSeconds": "{value} segundos",
"@settingsNetworkValuesSeconds": { "@settingsNetworkValuesSeconds": {
"placeholders": { "placeholders": {
"value": { "value": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsNetworkValuesUnlimitedKbps": "Ilimitado", "settingsNetworkValuesUnlimitedKbps": "Ilimitado",
"@settingsNetworkValuesUnlimitedKbps": {}, "@settingsNetworkValuesUnlimitedKbps": {},
"settingsResetActionsClearImageCache": "Limpar cache de Imagens", "settingsResetActionsClearImageCache": "Limpar cache de Imagens",
"@settingsResetActionsClearImageCache": {}, "@settingsResetActionsClearImageCache": {},
"settingsResetName": "Redefinir", "settingsResetName": "Redefinir",
"@settingsResetName": {}, "@settingsResetName": {},
"settingsServersActionsAdd": "Adicionar Servidor", "settingsServersActionsAdd": "Adicionar Servidor",
"@settingsServersActionsAdd": {}, "@settingsServersActionsAdd": {},
"settingsServersActionsDelete": "Apagar", "settingsServersActionsDelete": "Apagar",
"@settingsServersActionsDelete": {}, "@settingsServersActionsDelete": {},
"settingsServersActionsEdit": "Editar Servidor", "settingsServersActionsEdit": "Editar Servidor",
"@settingsServersActionsEdit": {}, "@settingsServersActionsEdit": {},
"settingsServersActionsSave": "Guardar", "settingsServersActionsSave": "Guardar",
"@settingsServersActionsSave": {}, "@settingsServersActionsSave": {},
"settingsServersActionsTestConnection": "Testar Ligação", "settingsServersActionsTestConnection": "Testar Ligação",
"@settingsServersActionsTestConnection": {}, "@settingsServersActionsTestConnection": {},
"settingsServersFieldsAddress": "Endereço", "settingsServersFieldsAddress": "Endereço",
"@settingsServersFieldsAddress": {}, "@settingsServersFieldsAddress": {},
"settingsServersFieldsPassword": "Senha", "settingsServersFieldsPassword": "Senha",
"@settingsServersFieldsPassword": {}, "@settingsServersFieldsPassword": {},
"settingsServersFieldsUsername": "Nome de utilizador", "settingsServersFieldsUsername": "Nome de utilizador",
"@settingsServersFieldsUsername": {}, "@settingsServersFieldsUsername": {},
"settingsServersMessagesConnectionFailed": "Ligação a {address} falhou, verifique definições ou servidor", "settingsServersMessagesConnectionFailed": "Ligação a {address} falhou, verifique definições ou servidor",
"@settingsServersMessagesConnectionFailed": { "@settingsServersMessagesConnectionFailed": {
"placeholders": { "placeholders": {
"address": { "address": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsServersMessagesConnectionOk": "Ligação a {address} OK!", "settingsServersMessagesConnectionOk": "Ligação a {address} OK!",
"@settingsServersMessagesConnectionOk": { "@settingsServersMessagesConnectionOk": {
"placeholders": { "placeholders": {
"address": { "address": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsServersName": "Servidores", "settingsServersName": "Servidores",
"@settingsServersName": {}, "@settingsServersName": {},
"settingsServersOptionsForcePlaintextPasswordDescriptionOff": "Enviar senha como token + sal", "settingsServersOptionsForcePlaintextPasswordDescriptionOff": "Enviar senha como token + sal",
"@settingsServersOptionsForcePlaintextPasswordDescriptionOff": {}, "@settingsServersOptionsForcePlaintextPasswordDescriptionOff": {},
"settingsServersOptionsForcePlaintextPasswordDescriptionOn": "Enviar senha em texto simples (antigo, certifique-se que a sua ligação é segura!)", "settingsServersOptionsForcePlaintextPasswordDescriptionOn": "Enviar senha em texto simples (antigo, certifique-se que a sua ligação é segura!)",
"@settingsServersOptionsForcePlaintextPasswordDescriptionOn": {}, "@settingsServersOptionsForcePlaintextPasswordDescriptionOn": {},
"settingsServersOptionsForcePlaintextPasswordTitle": "Forçar password em texto simples", "settingsServersOptionsForcePlaintextPasswordTitle": "Forçar password em texto simples",
"@settingsServersOptionsForcePlaintextPasswordTitle": {}, "@settingsServersOptionsForcePlaintextPasswordTitle": {}
"actionsCancel": "Cancelar", }
"@actionsCancel": {},
"actionsDelete": "Apagar",
"@actionsDelete": {},
"actionsDownload": "Descarregar",
"@actionsDownload": {},
"actionsDownloadCancel": "Cancelar descarga",
"@actionsDownloadCancel": {},
"actionsDownloadDelete": "Apagar descarga",
"@actionsDownloadDelete": {},
"resourcesFilterAlbum": "Álbum",
"@resourcesFilterAlbum": {},
"resourcesFilterArtist": "Artista",
"@resourcesFilterArtist": {},
"resourcesFilterYear": "Ano",
"@resourcesFilterYear": {},
"resourcesSortByAlbum": "Álbum",
"@resourcesSortByAlbum": {},
"settingsAboutActionsSupport": "Apoie o programador 💜",
"@settingsAboutActionsSupport": {},
"settingsNetworkOptionsOfflineMode": "Modo offline",
"@settingsNetworkOptionsOfflineMode": {},
"settingsNetworkOptionsOfflineModeOff": "Usar a internet para sincronizar música.",
"@settingsNetworkOptionsOfflineModeOff": {},
"settingsNetworkOptionsOfflineModeOn": "Não usar a internet para sincronizar ou tocar música.",
"@settingsNetworkOptionsOfflineModeOn": {},
"settingsNetworkOptionsStreamFormat": "Formato preferido de streaming",
"@settingsNetworkOptionsStreamFormat": {},
"resourcesSortByTitle": "Título",
"@resourcesSortByTitle": {},
"actionsOk": "OK",
"@actionsOk": {},
"controlsShuffle": "Aleatório",
"@controlsShuffle": {}
}
+195 -279
View File
@@ -1,280 +1,196 @@
{ {
"actionsStar": "Избранное", "actionsStar": "Избранное",
"@actionsStar": {}, "@actionsStar": {},
"actionsUnstar": "Убрать из избранного", "actionsUnstar": "Убрать из избранного",
"@actionsUnstar": {}, "@actionsUnstar": {},
"messagesNothingHere": "Здесь ничего нет…", "messagesNothingHere": "Здесь ничего нет…",
"@messagesNothingHere": {}, "@messagesNothingHere": {},
"navigationTabsHome": "Главная", "navigationTabsHome": "Главная",
"@navigationTabsHome": {}, "@navigationTabsHome": {},
"navigationTabsLibrary": "Библиотека", "navigationTabsLibrary": "Библиотека",
"@navigationTabsLibrary": {}, "@navigationTabsLibrary": {},
"navigationTabsSearch": "Поиск", "navigationTabsSearch": "Поиск",
"@navigationTabsSearch": {}, "@navigationTabsSearch": {},
"navigationTabsSettings": "Настройки", "navigationTabsSettings": "Настройки",
"@navigationTabsSettings": {}, "@navigationTabsSettings": {},
"resourcesAlbumActionsPlay": "Воспроизвести альбом", "resourcesAlbumActionsPlay": "Воспроизвести альбом",
"@resourcesAlbumActionsPlay": {}, "@resourcesAlbumActionsPlay": {},
"resourcesAlbumActionsView": "Посмотреть альбом", "resourcesAlbumActionsView": "Посмотреть альбом",
"@resourcesAlbumActionsView": {}, "@resourcesAlbumActionsView": {},
"resourcesAlbumListsSort": "Сортировка альбомов", "resourcesAlbumListsSort": "Сортировка альбомов",
"@resourcesAlbumListsSort": {}, "@resourcesAlbumListsSort": {},
"resourcesAlbumName": "{count,plural, =1{Альбом} few{Альбомы} many{Альбомов} other{Альбомов}}", "resourcesAlbumName": "{count,plural, =1{Альбом} few{Альбомы} many{Альбомов} other{Альбомов}}",
"@resourcesAlbumName": { "@resourcesAlbumName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesArtistActionsView": "Посмотреть исполнителя", "resourcesArtistActionsView": "Посмотреть исполнителя",
"@resourcesArtistActionsView": {}, "@resourcesArtistActionsView": {},
"resourcesArtistListsSort": "Сортировать исполнителей", "resourcesArtistListsSort": "Сортировать исполнителей",
"@resourcesArtistListsSort": {}, "@resourcesArtistListsSort": {},
"resourcesArtistName": "{count,plural, =1{Исполнитель} few{Исполнители} many{Исполнителей} other{Исполнителей}}", "resourcesArtistName": "{count,plural, =1{Исполнитель} few{Исполнители} many{Исполнителей} other{Исполнителей}}",
"@resourcesArtistName": { "@resourcesArtistName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesFilterGenre": "По жанру", "resourcesFilterGenre": "По жанру",
"@resourcesFilterGenre": {}, "@resourcesFilterGenre": {},
"resourcesFilterStarred": "Избранные", "resourcesFilterStarred": "Избранные",
"@resourcesFilterStarred": {}, "@resourcesFilterStarred": {},
"resourcesPlaylistActionsPlay": "Воспроизвести плейлист", "resourcesPlaylistActionsPlay": "Воспроизвести плейлист",
"@resourcesPlaylistActionsPlay": {}, "@resourcesPlaylistActionsPlay": {},
"resourcesPlaylistName": "{count,plural, =1{Плейлист} few{Плейлисты} many{Плейлистов} other{Плейлистов}}", "resourcesPlaylistName": "{count,plural, =1{Плейлист} few{Плейлисты} many{Плейлистов} other{Плейлистов}}",
"@resourcesPlaylistName": { "@resourcesPlaylistName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesQueueName": "{count,plural, =1{Очередь} few{Очереди} many{Очередей} other{Очередей}}", "resourcesQueueName": "{count,plural, =1{Очередь} few{Очереди} many{Очередей} other{Очередей}}",
"@resourcesQueueName": { "@resourcesQueueName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesSongListsArtistTopSongs": "Лучшие треки", "resourcesSongListsArtistTopSongs": "Лучшие треки",
"@resourcesSongListsArtistTopSongs": {}, "@resourcesSongListsArtistTopSongs": {},
"resourcesSongName": "{count,plural, =1{Трек} few{Трека} many{Треков} other{Треков}}", "resourcesSongName": "{count,plural, =1{Трек} few{Трека} many{Треков} other{Треков}}",
"@resourcesSongName": { "@resourcesSongName": {
"placeholders": { "placeholders": {
"count": { "count": {
"type": "int" "type": "int"
} }
} }
}, },
"resourcesSortByAdded": "Недавно добавленные", "resourcesSortByAdded": "Недавно добавленные",
"@resourcesSortByAdded": {}, "@resourcesSortByAdded": {},
"resourcesSortByArtist": "По исполнителям", "resourcesSortByArtist": "По исполнителю",
"@resourcesSortByArtist": {}, "@resourcesSortByArtist": {},
"resourcesSortByFrequentlyPlayed": "Часто проигрываемые", "resourcesSortByFrequentlyPlayed": "Часто проигрываемые",
"@resourcesSortByFrequentlyPlayed": {}, "@resourcesSortByFrequentlyPlayed": {},
"resourcesSortByName": "По имени", "resourcesSortByName": "По имени",
"@resourcesSortByName": {}, "@resourcesSortByName": {},
"resourcesSortByRandom": "Случайно", "resourcesSortByRandom": "Случайно",
"@resourcesSortByRandom": {}, "@resourcesSortByRandom": {},
"resourcesSortByRecentlyPlayed": "Недавно проигранные", "resourcesSortByRecentlyPlayed": "Недавно проигранные",
"@resourcesSortByRecentlyPlayed": {}, "@resourcesSortByRecentlyPlayed": {},
"resourcesSortByYear": "По году", "resourcesSortByYear": "По году",
"@resourcesSortByYear": {}, "@resourcesSortByYear": {},
"searchHeaderTitle": "Поиск: {query}", "searchHeaderTitle": "Поиск: {query}",
"@searchHeaderTitle": { "@searchHeaderTitle": {
"placeholders": { "placeholders": {
"query": { "query": {
"type": "String" "type": "String"
} }
} }
}, },
"searchInputPlaceholder": "Поиск", "searchInputPlaceholder": "Поиск",
"@searchInputPlaceholder": {}, "@searchInputPlaceholder": {},
"searchMoreResults": "Больше…", "searchMoreResults": "Больше…",
"@searchMoreResults": {}, "@searchMoreResults": {},
"searchNowPlayingContext": "Результаты поиска", "searchNowPlayingContext": "Результаты поиска",
"@searchNowPlayingContext": {}, "@searchNowPlayingContext": {},
"settingsAboutActionsLicenses": "Лицензии", "settingsAboutActionsLicenses": "Лицензии",
"@settingsAboutActionsLicenses": {}, "@settingsAboutActionsLicenses": {},
"settingsAboutActionsProjectHomepage": "Сайт проекта", "settingsAboutActionsProjectHomepage": "Сайт проекта",
"@settingsAboutActionsProjectHomepage": {}, "@settingsAboutActionsProjectHomepage": {},
"settingsAboutName": "О Subtracks", "settingsAboutName": "О Subtracks",
"@settingsAboutName": {}, "@settingsAboutName": {},
"settingsAboutVersion": "версия {version}", "settingsAboutVersion": "версия {version}",
"@settingsAboutVersion": { "@settingsAboutVersion": {
"placeholders": { "placeholders": {
"version": { "version": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsMusicName": "Музыка", "settingsMusicName": "Музыка",
"@settingsMusicName": {}, "@settingsMusicName": {},
"settingsMusicOptionsScrobbleDescriptionOff": "Не отправлять историю воспроизведений", "settingsMusicOptionsScrobbleDescriptionOff": "Не отправлять историю воспроизведений",
"@settingsMusicOptionsScrobbleDescriptionOff": {}, "@settingsMusicOptionsScrobbleDescriptionOff": {},
"settingsMusicOptionsScrobbleDescriptionOn": "Скробблинг истории воспроизведения", "settingsMusicOptionsScrobbleDescriptionOn": "Скробблинг истории воспроизведения",
"@settingsMusicOptionsScrobbleDescriptionOn": {}, "@settingsMusicOptionsScrobbleDescriptionOn": {},
"settingsMusicOptionsScrobbleTitle": "Скробблинг", "settingsMusicOptionsScrobbleTitle": "Скробблинг",
"@settingsMusicOptionsScrobbleTitle": {}, "@settingsMusicOptionsScrobbleTitle": {},
"settingsNetworkName": "Сеть", "settingsNetworkName": "Сеть",
"@settingsNetworkName": {}, "@settingsNetworkName": {},
"settingsNetworkOptionsMaxBitrateMobileTitle": "Максимальный битрейт (мобильный интернет)", "settingsNetworkOptionsMaxBitrateMobileTitle": "Максимальный битрейт (мобильный интернет)",
"@settingsNetworkOptionsMaxBitrateMobileTitle": {}, "@settingsNetworkOptionsMaxBitrateMobileTitle": {},
"settingsNetworkOptionsMaxBitrateWifiTitle": "Максимальный битрейт (Wi-Fi)", "settingsNetworkOptionsMaxBitrateWifiTitle": "Максимальный битрейт (Wi-Fi)",
"@settingsNetworkOptionsMaxBitrateWifiTitle": {}, "@settingsNetworkOptionsMaxBitrateWifiTitle": {},
"settingsNetworkOptionsMaxBufferTitle": "Максимальное время буферизации", "settingsNetworkOptionsMaxBufferTitle": "Максимальное время буферизации",
"@settingsNetworkOptionsMaxBufferTitle": {}, "@settingsNetworkOptionsMaxBufferTitle": {},
"settingsNetworkOptionsMinBufferTitle": "Минимальное время буферизации", "settingsNetworkOptionsMinBufferTitle": "Минимальное время буферизации",
"@settingsNetworkOptionsMinBufferTitle": {}, "@settingsNetworkOptionsMinBufferTitle": {},
"settingsNetworkValuesKbps": "{value} кбит/с", "settingsNetworkValuesKbps": "{value} кбит/с",
"@settingsNetworkValuesKbps": { "@settingsNetworkValuesKbps": {
"placeholders": { "placeholders": {
"value": { "value": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsNetworkValuesSeconds": "{value} секунд", "settingsNetworkValuesSeconds": "{value} секунд",
"@settingsNetworkValuesSeconds": { "@settingsNetworkValuesSeconds": {
"placeholders": { "placeholders": {
"value": { "value": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsNetworkValuesUnlimitedKbps": "Без ограничений", "settingsNetworkValuesUnlimitedKbps": "Без ограничений",
"@settingsNetworkValuesUnlimitedKbps": {}, "@settingsNetworkValuesUnlimitedKbps": {},
"settingsResetActionsClearImageCache": "Очистить кэш изображения", "settingsResetActionsClearImageCache": "Очистить кэш изображения",
"@settingsResetActionsClearImageCache": {}, "@settingsResetActionsClearImageCache": {},
"settingsResetName": "Сброс", "settingsResetName": "Сброс",
"@settingsResetName": {}, "@settingsResetName": {},
"settingsServersActionsAdd": "Добавить сервер", "settingsServersActionsAdd": "Добавить сервер",
"@settingsServersActionsAdd": {}, "@settingsServersActionsAdd": {},
"settingsServersActionsDelete": "Удалить", "settingsServersActionsDelete": "Удалить",
"@settingsServersActionsDelete": {}, "@settingsServersActionsDelete": {},
"settingsServersActionsEdit": "Редактировать сервер", "settingsServersActionsEdit": "Редактировать сервер",
"@settingsServersActionsEdit": {}, "@settingsServersActionsEdit": {},
"settingsServersActionsSave": "Сохранить", "settingsServersActionsSave": "Сохранить",
"@settingsServersActionsSave": {}, "@settingsServersActionsSave": {},
"settingsServersActionsTestConnection": "Проверить подключение", "settingsServersActionsTestConnection": "Проверить подключение",
"@settingsServersActionsTestConnection": {}, "@settingsServersActionsTestConnection": {},
"settingsServersFieldsAddress": "Адрес", "settingsServersFieldsAddress": "Адрес",
"@settingsServersFieldsAddress": {}, "@settingsServersFieldsAddress": {},
"settingsServersFieldsPassword": "Пароль", "settingsServersFieldsPassword": "Пароль",
"@settingsServersFieldsPassword": {}, "@settingsServersFieldsPassword": {},
"settingsServersFieldsUsername": "Имя пользователя", "settingsServersFieldsUsername": "Имя пользователя",
"@settingsServersFieldsUsername": {}, "@settingsServersFieldsUsername": {},
"settingsServersMessagesConnectionFailed": "Не удалось подключиться к {address}, проверьте настройки или сервер", "settingsServersMessagesConnectionFailed": "Не удалось подключиться к {address}, проверьте настройки или сервер",
"@settingsServersMessagesConnectionFailed": { "@settingsServersMessagesConnectionFailed": {
"placeholders": { "placeholders": {
"address": { "address": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsServersMessagesConnectionOk": "Подключение к {address} установлено!", "settingsServersMessagesConnectionOk": "Подключение к {address} установлено!",
"@settingsServersMessagesConnectionOk": { "@settingsServersMessagesConnectionOk": {
"placeholders": { "placeholders": {
"address": { "address": {
"type": "String" "type": "String"
} }
} }
}, },
"settingsServersName": "Серверы", "settingsServersName": "Серверы",
"@settingsServersName": {}, "@settingsServersName": {},
"settingsServersOptionsForcePlaintextPasswordDescriptionOff": "Отправить пароль в виде токена", "settingsServersOptionsForcePlaintextPasswordDescriptionOff": "Отправить пароль в виде токена",
"@settingsServersOptionsForcePlaintextPasswordDescriptionOff": {}, "@settingsServersOptionsForcePlaintextPasswordDescriptionOff": {},
"settingsServersOptionsForcePlaintextPasswordDescriptionOn": "Отправить пароль в виде текста (устарело, убедитесь, что ваше соединение безопасно!)", "settingsServersOptionsForcePlaintextPasswordDescriptionOn": "Отправить пароль в виде текста (устарело, убедитесь, что ваше соединение безопасно!)",
"@settingsServersOptionsForcePlaintextPasswordDescriptionOn": {}, "@settingsServersOptionsForcePlaintextPasswordDescriptionOn": {},
"settingsServersOptionsForcePlaintextPasswordTitle": "Принудительно использовать текстовой пароль", "settingsServersOptionsForcePlaintextPasswordTitle": "Принудительно использовать текстовой пароль",
"@settingsServersOptionsForcePlaintextPasswordTitle": {}, "@settingsServersOptionsForcePlaintextPasswordTitle": {}
"settingsAboutShareLogs": "Поделиться журналами", }
"@settingsAboutShareLogs": {},
"settingsAboutChooseLog": "Выбрать файл журнала",
"@settingsAboutChooseLog": {},
"settingsNetworkOptionsStreamFormatServerDefault": "Использовать сервер по умолчанию",
"@settingsNetworkOptionsStreamFormatServerDefault": {},
"actionsDownload": "Скачать",
"@actionsDownload": {},
"actionsDownloadCancel": "Отменить загрузку",
"@actionsDownloadCancel": {},
"actionsCancel": "Отменить",
"@actionsCancel": {},
"resourcesSongCount": "{count,plural, =1{{count} трек} other{{count} треки}}",
"@resourcesSongCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesSortByAlbum": "По альбомам",
"@resourcesSortByAlbum": {},
"resourcesSortByTitle": "По заголовку",
"@resourcesSortByTitle": {},
"resourcesSortByUpdated": "По недавно обновленному",
"@resourcesSortByUpdated": {},
"resourcesSortByAlbumCount": "По количеству альбомов",
"@resourcesSortByAlbumCount": {},
"settingsNetworkOptionsOfflineMode": "Автономный режим",
"@settingsNetworkOptionsOfflineMode": {},
"settingsNetworkOptionsOfflineModeOff": "Использовать интернет для синхронизации музыки.",
"@settingsNetworkOptionsOfflineModeOff": {},
"settingsServersFieldsName": "Имя",
"@settingsServersFieldsName": {},
"actionsDelete": "Удалить",
"@actionsDelete": {},
"actionsDownloadDelete": "Удалить загруженное",
"@actionsDownloadDelete": {},
"actionsOk": "ОК",
"@actionsOk": {},
"controlsShuffle": "Перемешать",
"@controlsShuffle": {},
"resourcesFilterArtist": "По исполнителю",
"@resourcesFilterArtist": {},
"resourcesFilterAlbum": "По альбомам",
"@resourcesFilterAlbum": {},
"resourcesFilterYear": "По годам",
"@resourcesFilterYear": {},
"resourcesFilterOwner": "По владельцу",
"@resourcesFilterOwner": {},
"resourcesSongListDeleteAllContent": "Это удалит все загруженные файлы песен.",
"@resourcesSongListDeleteAllContent": {},
"settingsNetworkOptionsStreamFormat": "Предпочтительный формат потока",
"@settingsNetworkOptionsStreamFormat": {},
"resourcesSongListDeleteAllTitle": "Удалить загрузки?",
"@resourcesSongListDeleteAllTitle": {},
"settingsNetworkOptionsOfflineModeOn": "Не использовать интернет для синхронизации или воспроизведения музыки.",
"@settingsNetworkOptionsOfflineModeOn": {},
"settingsAboutActionsSupport": "Поддержать разработчика",
"@settingsAboutActionsSupport": {},
"resourcesArtistCount": "{count,plural, =1{{count} исполнитель} other{{count} исполнители}}",
"@resourcesArtistCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesPlaylistCount": "{count,plural, =1{{count} плейлист} other{{count} плейлисты}}",
"@resourcesPlaylistCount": {
"placeholders": {
"count": {
"type": "int"
}
}
},
"resourcesAlbumCount": "{count,plural, =1{{count} альбом} other{{count} альбомы}}",
"@resourcesAlbumCount": {
"placeholders": {
"count": {
"type": "int"
}
}
}
}
-209
View File
@@ -1,209 +0,0 @@
// import 'dart:convert';
import 'dart:io';
import 'package:collection/collection.dart';
import 'package:flutter/foundation.dart';
import 'package:logging/logging.dart';
import 'package:path/path.dart' as p;
import 'package:path_provider/path_provider.dart';
class AnsiColor {
/// ANSI Control Sequence Introducer, signals the terminal for new settings.
static const ansiEsc = '\x1B[';
/// Reset all colors and options for current SGRs to terminal defaults.
static const ansiDefault = '${ansiEsc}0m';
final int? fg;
final int? bg;
final bool color;
AnsiColor.none()
: fg = null,
bg = null,
color = false;
AnsiColor.fg(this.fg)
: bg = null,
color = true;
AnsiColor.bg(this.bg)
: fg = null,
color = true;
@override
String toString() {
if (fg != null) {
return '${ansiEsc}38;5;${fg}m';
} else if (bg != null) {
return '${ansiEsc}48;5;${bg}m';
} else {
return '';
}
}
String call(String msg) {
if (color) {
// ignore: unnecessary_brace_in_string_interps
return '${this}$msg$ansiDefault';
} else {
return msg;
}
}
AnsiColor toFg() => AnsiColor.fg(bg);
AnsiColor toBg() => AnsiColor.bg(fg);
/// Defaults the terminal's foreground color without altering the background.
String get resetForeground => color ? '${ansiEsc}39m' : '';
/// Defaults the terminal's background color without altering the foreground.
String get resetBackground => color ? '${ansiEsc}49m' : '';
static int grey(double level) => 232 + (level.clamp(0.0, 1.0) * 23).round();
}
final levelColors = {
Level.FINEST: AnsiColor.fg(AnsiColor.grey(0.5)),
Level.FINER: AnsiColor.fg(AnsiColor.grey(0.5)),
Level.FINE: AnsiColor.fg(AnsiColor.grey(0.5)),
Level.CONFIG: AnsiColor.fg(81),
Level.INFO: AnsiColor.fg(12),
Level.WARNING: AnsiColor.fg(208),
Level.SEVERE: AnsiColor.fg(196),
Level.SHOUT: AnsiColor.fg(199),
};
class LogData {
final String? message;
final Object? data;
const LogData(this.message, this.data);
}
String _format(
LogRecord event, {
bool color = false,
bool time = true,
bool level = true,
bool redact = true,
}) {
var message = '';
if (time) message += '${event.time.toIso8601String()} ';
if (level) message += '${event.level.name} ';
final object = event.object;
if (object is LogData) {
message += '${object.message}';
message += '\n${object.data}';
} else if (object != null) {
message += 'Object';
message += '\n$object';
} else {
message += event.message;
}
if (event.error != null) {
message += '\n${event.error}';
}
if (redact) {
message = _redactUrl(message);
}
if (event.stackTrace != null) {
message += '\n${event.stackTrace}';
}
return color
? message.split('\n').map((e) => levelColors[event.level]!(e)).join('\n')
: message;
}
String _redactUrl(String message) {
if (!_queryReplace('u').hasMatch(message)) {
return message;
}
message = _redactParam(message, 'u');
message = _redactParam(message, 'p');
message = _redactParam(message, 's');
message = _redactParam(message, 't');
return message;
}
RegExp _queryReplace(String key) => RegExp('$key=([^&|\\n|\\t\\s]+)');
String _redactParam(String url, String key) =>
url.replaceAll(_queryReplace(key), '$key=REDACTED');
Future<Directory> logDirectory() async {
return Directory(
p.join((await getApplicationDocumentsDirectory()).path, 'logs'),
);
}
Future<List<File>> logFiles() async {
final dir = await logDirectory();
return dir.listSync().whereType<File>().toList()
..sort(
(a, b) => b.statSync().modified.compareTo(a.statSync().modified),
);
}
File _currentLogFile(String logDir) {
final now = DateTime.now();
return File(p.join(logDir, '${now.year}-${now.month}-${now.day}.txt'));
}
Future<void> _printFile(String event, String logDir) async {
final file = _currentLogFile(logDir);
if (!event.endsWith('\n')) {
event += '\n';
}
await file.writeAsString(event, mode: FileMode.writeOnlyAppend, flush: true);
}
void _printDebug(LogRecord event) {
// ignore: avoid_print
print(_format(event, color: true, time: false, level: false, redact: false));
}
Future<void> _printRelease(LogRecord event, String logDir) async {
await _printFile(
_format(event, color: false, time: true, level: true, redact: true),
logDir,
);
}
final log = Logger('default');
Future<void> initLogging() async {
final dir = (await logDirectory())..create();
final file = _currentLogFile(dir.path);
if (!(await file.exists())) {
await file.create();
}
final files = await logFiles();
if (files.length > 7) {
for (var file in files.slice(7)) {
await file.delete();
}
}
Logger.root.level = kDebugMode ? Level.ALL : Level.INFO;
Logger.root.onRecord.asyncMap((event) async {
if (kDebugMode) {
_printDebug(event);
} else {
await _printRelease(event, dir.path);
}
}).listen((_) {}, cancelOnError: false);
}
-4
View File
@@ -4,7 +4,6 @@ import 'package:stack_trace/stack_trace.dart' as stack_trace;
import 'package:worker_manager/worker_manager.dart'; import 'package:worker_manager/worker_manager.dart';
import 'app/app.dart'; import 'app/app.dart';
import 'log.dart';
void main() async { void main() async {
// TOOD: probably remove before live // TOOD: probably remove before live
@@ -19,8 +18,5 @@ void main() async {
await Executor().warmUp(); await Executor().warmUp();
WidgetsFlutterBinding.ensureInitialized(); WidgetsFlutterBinding.ensureInitialized();
await initLogging();
runApp(const ProviderScope(child: MyApp())); runApp(const ProviderScope(child: MyApp()));
} }
+16 -12
View File
@@ -4,6 +4,7 @@ import 'dart:math';
import 'package:audio_service/audio_service.dart'; import 'package:audio_service/audio_service.dart';
import 'package:collection/collection.dart'; import 'package:collection/collection.dart';
import 'package:drift/drift.dart' show Value; import 'package:drift/drift.dart' show Value;
import 'package:flutter/foundation.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:just_audio/just_audio.dart'; import 'package:just_audio/just_audio.dart';
import 'package:pool/pool.dart'; import 'package:pool/pool.dart';
@@ -13,7 +14,6 @@ import 'package:synchronized/synchronized.dart';
import '../cache/image_cache.dart'; import '../cache/image_cache.dart';
import '../database/database.dart'; import '../database/database.dart';
import '../log.dart';
import '../models/music.dart'; import '../models/music.dart';
import '../models/query.dart'; import '../models/query.dart';
import '../models/support.dart'; import '../models/support.dart';
@@ -122,10 +122,6 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
)); ));
}); });
_player.playbackEventStream.doOnError((e, st) async {
log.warning('playbackEventStream', e, st);
});
shuffleIndicies.listen((value) { shuffleIndicies.listen((value) {
playbackState.add(playbackState.value.copyWith( playbackState.add(playbackState.value.copyWith(
shuffleMode: value != null shuffleMode: value != null
@@ -141,7 +137,7 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
_player.processingStateStream.listen((event) async { _player.processingStateStream.listen((event) async {
if (event == ProcessingState.completed) { if (event == ProcessingState.completed) {
if (_audioSource.length > 0) { if (_audioSource.length > 0) {
log.fine('completed'); yell('completed');
await stop(); await stop();
await seek(Duration.zero); await seek(Duration.zero);
} }
@@ -390,7 +386,7 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
mediaItem.add(slice.current!.mediaItem); mediaItem.add(slice.current!.mediaItem);
queue.add(list.map((e) => e.mediaItem).toList()); queue.add(list.map((e) => e.mediaItem).toList());
log.fine('addAll'); yell('addAll');
await _audioSource.addAll(list.map((e) => e.audioSource).toList()); await _audioSource.addAll(list.map((e) => e.audioSource).toList());
await _player.seek(Duration.zero, index: list.indexOf(slice.current!)); await _player.seek(Duration.zero, index: list.indexOf(slice.current!));
} }
@@ -414,7 +410,7 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
final sourceNeedsPrev = sourceIndex == 0; final sourceNeedsPrev = sourceIndex == 0;
if (sourceNeedsNext && slice.next != null) { if (sourceNeedsNext && slice.next != null) {
log.fine('add'); yell('add');
await _audioSource.add(slice.next!.audioSource); await _audioSource.add(slice.next!.audioSource);
} }
if (sourceNeedsPrev && slice.prev != null) { if (sourceNeedsPrev && slice.prev != null) {
@@ -501,7 +497,7 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
} }
Future<void> _insertFirstAudioSource(AudioSource source) { Future<void> _insertFirstAudioSource(AudioSource source) {
log.fine('insert'); yell('insert');
final wait = _audioSource.insert(0, source); final wait = _audioSource.insert(0, source);
_currentIndexIgnore.add(1); _currentIndexIgnore.add(1);
return wait; return wait;
@@ -509,20 +505,20 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
Future<void> _pruneAudioSources(int keepIndex) async { Future<void> _pruneAudioSources(int keepIndex) async {
if (keepIndex > 0) { if (keepIndex > 0) {
log.fine('removeRange 0'); yell('removeRange 0');
final wait = _audioSource.removeRange(0, keepIndex); final wait = _audioSource.removeRange(0, keepIndex);
_currentIndexIgnore.add(0); _currentIndexIgnore.add(0);
await wait; await wait;
} }
if (_audioSource.length > 1) { if (_audioSource.length > 1) {
log.fine('removeRange 1'); yell('removeRange 1');
await _audioSource.removeRange(1, _audioSource.length); await _audioSource.removeRange(1, _audioSource.length);
} }
} }
Future<void> _clearAudioSource([bool clearMetadata = false]) async { Future<void> _clearAudioSource([bool clearMetadata = false]) async {
// await _player.stop(); // await _player.stop();
log.fine('_clearAudioSource'); yell('_clearAudioSource');
await _audioSource.clear(); await _audioSource.clear();
if (clearMetadata) { if (clearMetadata) {
@@ -701,3 +697,11 @@ class AudioControl extends BaseAudioHandler with QueueHandler, SeekHandler {
} }
} }
} }
void yell(String msg) {
if (kDebugMode) {
print('=================================================================<');
print(msg);
print('=================================================================>');
}
}
-6
View File
@@ -53,8 +53,6 @@ class SettingsService extends _$SettingsService {
ref.read(httpClientProvider), ref.read(httpClientProvider),
); );
await client.test();
final features = IList([ final features = IList([
if (await client.testFeature(SubsonicFeature.emptyQuerySearch)) if (await client.testFeature(SubsonicFeature.emptyQuerySearch))
SubsonicFeature.emptyQuerySearch, SubsonicFeature.emptyQuerySearch,
@@ -68,10 +66,6 @@ class SettingsService extends _$SettingsService {
} }
Future<void> updateSource(SubsonicSettings source) async { Future<void> updateSource(SubsonicSettings source) async {
final client = SubsonicClient(source, ref.read(httpClientProvider));
await client.test();
await _db.updateSource(source); await _db.updateSource(source);
await init(); await init();
} }
+4 -14
View File
@@ -1,8 +1,6 @@
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:rxdart/rxdart.dart';
import '../database/database.dart'; import '../database/database.dart';
import '../log.dart';
import '../state/settings.dart'; import '../state/settings.dart';
abstract class BaseMusicSource { abstract class BaseMusicSource {
@@ -42,33 +40,25 @@ class MusicSource implements BaseMusicSource {
@override @override
Stream<Iterable<AlbumsCompanion>> allAlbums() { Stream<Iterable<AlbumsCompanion>> allAlbums() {
_testOnline(); _testOnline();
return _source return _source.allAlbums();
.allAlbums()
.doOnError((e, st) => log.severe('allAlbums', e, st));
} }
@override @override
Stream<Iterable<ArtistsCompanion>> allArtists() { Stream<Iterable<ArtistsCompanion>> allArtists() {
_testOnline(); _testOnline();
return _source return _source.allArtists();
.allArtists()
.doOnError((e, st) => log.severe('allArtists', e, st));
} }
@override @override
Stream<Iterable<PlaylistWithSongsCompanion>> allPlaylists() { Stream<Iterable<PlaylistWithSongsCompanion>> allPlaylists() {
_testOnline(); _testOnline();
return _source return _source.allPlaylists();
.allPlaylists()
.doOnError((e, st) => log.severe('allPlaylists', e, st));
} }
@override @override
Stream<Iterable<SongsCompanion>> allSongs() { Stream<Iterable<SongsCompanion>> allSongs() {
_testOnline(); _testOnline();
return _source return _source.allSongs();
.allSongs()
.doOnError((e, st) => log.severe('allSongs', e, st));
} }
@override @override
+1 -6
View File
@@ -6,7 +6,6 @@ import 'package:crypto/crypto.dart';
import 'package:http/http.dart'; import 'package:http/http.dart';
import 'package:xml/xml.dart'; import 'package:xml/xml.dart';
import '../../log.dart';
import '../../models/settings.dart'; import '../../models/settings.dart';
import 'xml.dart'; import 'xml.dart';
@@ -90,16 +89,12 @@ class SubsonicClient {
final subsonicResponse = final subsonicResponse =
SubsonicResponse(XmlDocument.parse(utf8.decode(res.bodyBytes))); SubsonicResponse(XmlDocument.parse(utf8.decode(res.bodyBytes)));
if (subsonicResponse.status == Status.failed) { if (subsonicResponse.status == Status.failed) {
final error = SubsonicException(subsonicResponse.xml); throw SubsonicException(subsonicResponse.xml);
log.severe('Subsonic error', error);
throw error;
} }
return subsonicResponse; return subsonicResponse;
} }
Future<void> test() => get('ping');
Future<bool> testFeature(SubsonicFeature feature) async { Future<bool> testFeature(SubsonicFeature feature) async {
switch (feature) { switch (feature) {
case SubsonicFeature.emptyQuerySearch: case SubsonicFeature.emptyQuerySearch:
+5 -29
View File
@@ -290,14 +290,6 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "1.6.3" version: "1.6.3"
cross_file:
dependency: transitive
description:
name: cross_file
sha256: "0b0036e8cccbfbe0555fd83c1d31a6f30b77a96b598b35a5d36dd41f718695e9"
url: "https://pub.dev"
source: hosted
version: "0.3.3+4"
crypto: crypto:
dependency: "direct main" dependency: "direct main"
description: description:
@@ -687,7 +679,7 @@ packages:
source: hosted source: hosted
version: "2.0.1" version: "2.0.1"
logging: logging:
dependency: "direct main" dependency: transitive
description: description:
name: logging name: logging
sha256: "04094f2eb032cbb06c6f6e8d3607edcfcb0455e2bb6cbc010cb01171dcb64e6d" sha256: "04094f2eb032cbb06c6f6e8d3607edcfcb0455e2bb6cbc010cb01171dcb64e6d"
@@ -842,10 +834,10 @@ packages:
dependency: transitive dependency: transitive
description: description:
name: path_provider_windows name: path_provider_windows
sha256: d3f80b32e83ec208ac95253e0cd4d298e104fbc63cb29c5c69edaed43b0c69d6 sha256: f53720498d5a543f9607db4b0e997c4b5438884de25b0f73098cc2671a51b130
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "2.1.6" version: "2.1.5"
pedantic: pedantic:
dependency: transitive dependency: transitive
description: description:
@@ -958,22 +950,6 @@ packages:
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "0.27.7" version: "0.27.7"
share_plus:
dependency: "direct main"
description:
name: share_plus
sha256: "322a1ec9d9fe07e2e2252c098ce93d12dbd06133cc4c00ffe6a4ef505c295c17"
url: "https://pub.dev"
source: hosted
version: "7.0.0"
share_plus_platform_interface:
dependency: transitive
description:
name: share_plus_platform_interface
sha256: "0c6e61471bd71b04a138b8b588fa388e66d8b005e6f2deda63371c5c505a0981"
url: "https://pub.dev"
source: hosted
version: "3.2.1"
shelf: shelf:
dependency: transitive dependency: transitive
description: description:
@@ -1343,10 +1319,10 @@ packages:
dependency: transitive dependency: transitive
description: description:
name: win32 name: win32
sha256: "5a751eddf9db89b3e5f9d50c20ab8612296e4e8db69009788d6c8b060a84191c" sha256: a6f0236dbda0f63aa9a25ad1ff9a9d8a4eaaa5012da0dc59d21afdb1dc361ca4
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "4.1.4" version: "3.1.4"
worker_manager: worker_manager:
dependency: "direct main" dependency: "direct main"
description: description:
+1 -3
View File
@@ -4,7 +4,7 @@ homepage: https://github.com/austinried/subtracks
repository: https://github.com/austinried/subtracks repository: https://github.com/austinried/subtracks
issue_tracker: https://github.com/austinried/subtracks/issues issue_tracker: https://github.com/austinried/subtracks/issues
publish_to: 'none' publish_to: 'none'
version: 2.0.0-alpha.3+12 version: 2.0.0-alpha.2+11
environment: environment:
sdk: '>=2.19.2 <3.0.0' sdk: '>=2.19.2 <3.0.0'
@@ -57,8 +57,6 @@ dependencies:
connectivity_plus: ^3.0.4 connectivity_plus: ^3.0.4
package_info_plus: ^3.1.1 package_info_plus: ^3.1.1
url_launcher: ^6.1.10 url_launcher: ^6.1.10
logging: ^1.1.1
share_plus: ^7.0.0
# https://github.com/dart-lang/intl/issues/522#issuecomment-1469961807 # https://github.com/dart-lang/intl/issues/522#issuecomment-1469961807
dependency_overrides: dependency_overrides: