@vestra-player/sdk 1.5.8 → 1.5.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +39 -0
- package/README.md +4 -1
- package/bin/vestra-plugin.mjs +170 -7
- package/dist/commands.d.ts +7 -4
- package/dist/i18n-tools.d.ts +67 -0
- package/dist/i18n-tools.js +787 -0
- package/dist/i18n.d.ts +222 -0
- package/dist/i18n.js +972 -0
- package/dist/player-runtime.d.ts +2 -0
- package/dist/player-runtime.js +2 -0
- package/dist/plugin/appearance.js +27 -1
- package/dist/plugin/bindings.js +1 -0
- package/dist/plugin/commands.js +24 -4
- package/dist/plugin/index.js +9 -1
- package/dist/plugin/language.d.ts +8 -0
- package/dist/plugin/language.js +79 -0
- package/dist/plugin/osd.d.ts +11 -0
- package/dist/plugin/osd.js +64 -9
- package/dist/plugin/packages.js +10 -0
- package/dist/plugin/runtime.d.ts +3 -1
- package/dist/plugin/runtime.js +6 -0
- package/dist/plugin/scope.d.ts +1 -0
- package/dist/plugin/scope.js +2 -0
- package/dist/plugin/subtitles.js +9 -1
- package/dist/plugin/testing.d.ts +184 -5
- package/dist/plugin/testing.js +459 -67
- package/dist/plugin/timeline.js +3 -1
- package/dist/plugin/types.d.ts +523 -54
- package/dist/plugin/ui.js +29 -10
- package/dist/plugin/values.d.ts +55 -0
- package/dist/plugin/values.js +117 -0
- package/dist/plugin/window.d.ts +2 -0
- package/dist/plugin/window.js +4 -0
- package/dist/source-resolvers.d.ts +0 -1
- package/dist/source-resolvers.js +9 -1
- package/dist/subtitles.d.ts +3 -1
- package/dist/wire.d.ts +38 -6
- package/dist/wire.js +13 -2
- package/llms-full.txt +646 -58
- package/llms.txt +44 -40
- package/package.json +1 -1
- package/slint/vestra/markdown.slint +5 -5
- package/slint/vestra/widgets.slint +4 -4
package/dist/plugin/types.d.ts
CHANGED
|
@@ -73,11 +73,11 @@ export interface Disposable {
|
|
|
73
73
|
* | `timeout` | A time limit ran out (`openStream` start-up, `tools.run`, `system.*` after 10 s). |
|
|
74
74
|
* | `stream`, `device` | `openStream`: the producer failed / the audio device is not ready. |
|
|
75
75
|
* | `backend-uncertain` | The player's backend blocked a filter stage; call `retry()`. |
|
|
76
|
-
* | `limit` | A player-wide limit was reached (for example the number of commands). |
|
|
76
|
+
* | `limit` | A player-wide limit was reached (for example the number of commands), a property value is over the limits of {@link PropValue}, or a request is longer than the player's 1 MiB message. |
|
|
77
77
|
* | `reserved` | {@link Packages.validate}, {@link PackageCandidate.install}: the id is `vestra` or starts with `vestra.` (any case), which only the player's built-in plugins use (player 0.4.1). |
|
|
78
78
|
* | `versionMismatch` | The package needs a newer player (`minPlayerVersion`) or another `apiVersion`. |
|
|
79
79
|
* | `ui-prepare` | The player could not prepare a mounted panel or a settings page (its Slint file does not compile, a bound property is not declared, or another plugin's panel holds the slot); `message` has the diagnostics. |
|
|
80
|
-
* | `ui` | The player could not apply a property to a tool window or a settings page, or could not build the Options window (a property the Slint file does not declare, a value of the wrong type); `message` has Slint's reason. |
|
|
80
|
+
* | `ui` | The player could not apply a property to a tool window or a settings page, or could not build the Options window (a property the Slint file does not declare, a value of the wrong type); `message` has Slint's reason. Also reported to {@link Scope.onError} without a request: a callback whose arguments the player could not convert, a property it could not show again when it rebuilt a view (an image file removed since). |
|
|
81
81
|
* | `host` | Any other failure inside the player; `message` is the player's reason. |
|
|
82
82
|
* | `disabled` | The plugin is being stopped; pending requests fail with it. |
|
|
83
83
|
* | `unknown`, `rejected`, `expired` | After a transport problem the SDK could not confirm the outcome (does not happen in normal operation). |
|
|
@@ -224,8 +224,10 @@ export interface Scope extends Disposable {
|
|
|
224
224
|
readonly timeline: Timeline;
|
|
225
225
|
/** Files dropped on the video area, by extension (`ui.drop`). */
|
|
226
226
|
readonly drops: Drops;
|
|
227
|
-
/** The player's palette. */
|
|
227
|
+
/** The player's palette and the saved interface language. */
|
|
228
228
|
readonly appearance: Appearance;
|
|
229
|
+
/** The interface language of this run (read-only). */
|
|
230
|
+
readonly i18n: I18n;
|
|
229
231
|
/** Pages in the player's options window (`ui.settings`). */
|
|
230
232
|
readonly settings: Settings;
|
|
231
233
|
/**
|
|
@@ -339,8 +341,11 @@ export interface CommandState {
|
|
|
339
341
|
checked: boolean | null;
|
|
340
342
|
/** Shown as busy; like `enabled: false`, the player does not call `run`. Default false. */
|
|
341
343
|
busy: boolean;
|
|
342
|
-
/**
|
|
343
|
-
|
|
344
|
+
/**
|
|
345
|
+
* Shown when the command is disabled or busy: English source text the
|
|
346
|
+
* player translates, or a {@link Text} (SDK 1.5.11).
|
|
347
|
+
*/
|
|
348
|
+
reason: TextValue | null;
|
|
344
349
|
}
|
|
345
350
|
/**
|
|
346
351
|
* A value, or a function the SDK re-evaluates on every update pass (see
|
|
@@ -360,9 +365,9 @@ export interface CommandState {
|
|
|
360
365
|
export type Bindable<T> = T | (() => T);
|
|
361
366
|
/**
|
|
362
367
|
* A built-in top-level menu of the player, named in a command path as
|
|
363
|
-
* `@<id>` (see {@link CommandOptions.path}): Open
|
|
364
|
-
* Subtitles
|
|
365
|
-
*
|
|
368
|
+
* `@<id>` or by its English key (see {@link CommandOptions.path}): Open,
|
|
369
|
+
* Playback, Subtitles, Video, Audio, Screen, Settings. The list is
|
|
370
|
+
* `MENU_IDS` in `@vestra-player/sdk/testing`.
|
|
366
371
|
*/
|
|
367
372
|
export type MenuId = "open" | "playback" | "subtitles" | "video" | "audio" | "screen" | "settings";
|
|
368
373
|
/**
|
|
@@ -379,7 +384,7 @@ export type MenuId = "open" | "playback" | "subtitles" | "video" | "audio" | "sc
|
|
|
379
384
|
* ({@link MenuId}) sit at fixed orders, whatever is inside them: Open 110,
|
|
380
385
|
* Playback 200, Subtitles 300, Video 400, Audio 500, Screen 710, Settings
|
|
381
386
|
* 830 (player 0.3.0). This holds whether the path names the menu by id
|
|
382
|
-
* (`["@video", "Blur"]`) or by its
|
|
387
|
+
* (`["@video", "Blur"]`) or by its key (`["Video", "Blur"]`), so a plugin's
|
|
383
388
|
* item never moves the player's menu. Directly inside a built-in menu,
|
|
384
389
|
* `order` 0 (the default) sorts after every other order: an item without
|
|
385
390
|
* `order` goes at the end, after the player's own items (which all use 100
|
|
@@ -402,22 +407,43 @@ export interface CommandOptions {
|
|
|
402
407
|
* one segment is a top-level item. Omit it for a command that is not in the
|
|
403
408
|
* main menu (bindings and panel menus only); `title` is then required.
|
|
404
409
|
*
|
|
405
|
-
* Segments are
|
|
406
|
-
*
|
|
407
|
-
*
|
|
408
|
-
*
|
|
409
|
-
*
|
|
410
|
-
*
|
|
411
|
-
*
|
|
410
|
+
* Segments are English source text, and menus merge by them: commands
|
|
411
|
+
* of different plugins with the same leading segments share a submenu.
|
|
412
|
+
* The player shows each segment and the title in the interface language
|
|
413
|
+
* from the declaring plugin's catalog (`locales/<lang>.po`, see the
|
|
414
|
+
* [i18n guide](../../docs/how-to/i18n.md)); the player's own menus
|
|
415
|
+
* (Open, Playback, Subtitles, Video, Audio, Screen, Settings, and
|
|
416
|
+
* Playback ▸ Speed, Playback ▸ Seek) always show the player's words.
|
|
417
|
+
* A built-in menu can also be named by its id, `@` plus a {@link MenuId}:
|
|
418
|
+
* `@open`, `@playback`, `@subtitles`, `@video`, `@audio`, `@screen` or
|
|
419
|
+
* `@settings`. Only the first segment is read as an id; an unknown id, or
|
|
420
|
+
* an id with nothing after it, fails with `invalid`. Players up to 0.4.2
|
|
421
|
+
* titled their menus in Chinese (视频…): there `["Video", "Blur"]` is a
|
|
422
|
+
* menu of its own, so plugins for those players write `@video`; player
|
|
423
|
+
* 0.4.3 still accepts the old Chinese titles of its own menus.
|
|
424
|
+
*
|
|
425
|
+
* A segment that mixes words with data (a track number, a count) is a
|
|
426
|
+
* {@link Text} (SDK 1.5.11, player 0.4.3): `plugin.i18n.text("Track {}
|
|
427
|
+
* ({})", [n, codec])`. The menu shows it translated and filled in; it
|
|
428
|
+
* merges by its English rendering ("Track 2 (opus)").
|
|
412
429
|
*
|
|
413
430
|
* @example
|
|
414
431
|
* ```ts
|
|
415
432
|
* plugin.commands.add({ id: "blur", path: ["@video", "Blur"], run: toggle });
|
|
433
|
+
* const { text } = plugin.i18n;
|
|
434
|
+
* plugin.commands.add({
|
|
435
|
+
* id: "track-2",
|
|
436
|
+
* path: ["@audio", "Audio Track", text("Track {} ({})", [2, "opus"])],
|
|
437
|
+
* run: select,
|
|
438
|
+
* });
|
|
416
439
|
* ```
|
|
417
440
|
*/
|
|
418
|
-
path?: string[];
|
|
419
|
-
/**
|
|
420
|
-
|
|
441
|
+
path?: (string | Text)[];
|
|
442
|
+
/**
|
|
443
|
+
* Menu label (English source text, shown translated, or a {@link Text});
|
|
444
|
+
* defaults to the last path segment.
|
|
445
|
+
*/
|
|
446
|
+
title?: string | Text;
|
|
421
447
|
/**
|
|
422
448
|
* Sibling order in the menu, ascending (integer, default 0). A submenu sits
|
|
423
449
|
* where its first command sits, except a built-in menu, which keeps its
|
|
@@ -463,8 +489,11 @@ export interface CommandOptions {
|
|
|
463
489
|
checked?: Bindable<boolean | null>;
|
|
464
490
|
/** Busy state (default false); the player does not call `run` while busy. */
|
|
465
491
|
busy?: Bindable<boolean>;
|
|
466
|
-
/**
|
|
467
|
-
|
|
492
|
+
/**
|
|
493
|
+
* Why the command is disabled or busy (shown to the user): English
|
|
494
|
+
* source text, or a {@link Text} for one with data in it (SDK 1.5.11).
|
|
495
|
+
*/
|
|
496
|
+
reason?: Bindable<TextValue | null>;
|
|
468
497
|
/**
|
|
469
498
|
* Run the command (menu item, binding, panel menu or
|
|
470
499
|
* `host.command(id).run()` in tests). It may return a promise; errors
|
|
@@ -631,15 +660,31 @@ export interface MarkdownOptions {
|
|
|
631
660
|
* is refused (Slint treats `_` and `-` as the same, so use camelCase or
|
|
632
661
|
* kebab-case).
|
|
633
662
|
*
|
|
663
|
+
* A {@link Text} or {@link TextList} goes where the Slint type is `string`,
|
|
664
|
+
* at any depth (SDK 1.5.11, player 0.4.3): the player shows it translated
|
|
665
|
+
* with the plugin's catalog, so a `[string]` model (a ComboBox) can mix
|
|
666
|
+
* words and data. The limits below count it as the string it becomes.
|
|
667
|
+
*
|
|
634
668
|
* A {@link MarkdownRef} goes where the Slint type is `[MarkdownBlock]`: the
|
|
635
669
|
* whole value, or a field at any depth (SDK 1.5.4; older players refuse a
|
|
636
670
|
* nested one). An {@link ImageRef} only as the whole value: nested in an
|
|
637
671
|
* array or object it is `invalid`.
|
|
638
672
|
*
|
|
639
|
-
* Limits per value
|
|
640
|
-
*
|
|
641
|
-
*
|
|
642
|
-
*
|
|
673
|
+
* Limits per value (`UI_VALUE_LIMITS` in `@vestra-player/sdk/testing`,
|
|
674
|
+
* player 0.4.3; older players: 4096 values and 1024 rows): nesting depth 8,
|
|
675
|
+
* 16384 values in total (every array, object, string, number, boolean and
|
|
676
|
+
* null counts, the value itself included; a document is one), 4096 rows
|
|
677
|
+
* per array, 64 KiB per string or field name and 1 MiB of text in total,
|
|
678
|
+
* field names and the text of its Markdown documents included (256 KB per
|
|
679
|
+
* document). A list of rows with 8 fields is 9 values per row, so about
|
|
680
|
+
* 1800 rows fit. The whole request must also fit the player's 1 MiB
|
|
681
|
+
* message. A value over a limit is refused with code `limit` and the
|
|
682
|
+
* property keeps what it showed (see {@link View.set}); `TestHost` refuses
|
|
683
|
+
* it the same way.
|
|
684
|
+
*
|
|
685
|
+
* The limits bound the work of one write, not the size of your data: for
|
|
686
|
+
* a list that can grow without bound, send the rows near the view and the
|
|
687
|
+
* row count, and move that window as the user scrolls.
|
|
643
688
|
*
|
|
644
689
|
* @since 1.0.0
|
|
645
690
|
* @category UI
|
|
@@ -659,7 +704,7 @@ export type PropValue = PropData | ImageRef;
|
|
|
659
704
|
* @since 1.5.4
|
|
660
705
|
* @category UI
|
|
661
706
|
*/
|
|
662
|
-
export type PropData = null | boolean | number | string | MarkdownRef | PropData[] | {
|
|
707
|
+
export type PropData = null | boolean | number | string | MarkdownRef | Text | TextList | PropData[] | {
|
|
663
708
|
[key: string]: PropData;
|
|
664
709
|
};
|
|
665
710
|
/**
|
|
@@ -902,7 +947,13 @@ export interface View {
|
|
|
902
947
|
* the next update pass replaces the set value with the bound one.
|
|
903
948
|
*
|
|
904
949
|
* Never throws. A write that fails is retried with back-off and reported
|
|
905
|
-
* to {@link Scope.onError}
|
|
950
|
+
* to {@link Scope.onError} (the first failure of a run of failures; the
|
|
951
|
+
* message names the property). A value over the limits of
|
|
952
|
+
* {@link PropValue} fails with `limit`. As an initial property (written
|
|
953
|
+
* while the view is not open) it makes {@link Window.show} reject; a
|
|
954
|
+
* panel or settings page still opens without it (the property keeps its
|
|
955
|
+
* default) and the failure goes to the plugin's `onError` (player 0.4.3;
|
|
956
|
+
* older players left it out silently).
|
|
906
957
|
*
|
|
907
958
|
* @capability That of the view: `ui.window`, `ui.mount` or `ui.settings`.
|
|
908
959
|
*
|
|
@@ -935,7 +986,9 @@ export interface View {
|
|
|
935
986
|
* run. A view can have several bindings; when two return the same name,
|
|
936
987
|
* the one bound later wins.
|
|
937
988
|
*
|
|
938
|
-
* Never throws. Writes that fail are not repeated until the value
|
|
989
|
+
* Never throws. Writes that fail are not repeated until the value
|
|
990
|
+
* changes, and are reported to {@link Scope.onError} like a failed
|
|
991
|
+
* {@link View.set} (a value over the limits of {@link PropValue}: `limit`).
|
|
939
992
|
*
|
|
940
993
|
* @capability That of the view: `ui.window`, `ui.mount` or `ui.settings`.
|
|
941
994
|
*
|
|
@@ -1940,6 +1993,330 @@ export interface Appearance {
|
|
|
1940
1993
|
* @since 1.0.0
|
|
1941
1994
|
*/
|
|
1942
1995
|
set(theme: ThemeId): Promise<void>;
|
|
1996
|
+
/**
|
|
1997
|
+
* The saved interface language: `"system"` (follow the system's
|
|
1998
|
+
* languages, the default) or a {@link Locale}.
|
|
1999
|
+
*
|
|
2000
|
+
* @remarks
|
|
2001
|
+
* This is the choice for the next start. The language of this run is
|
|
2002
|
+
* {@link I18n.locale} and never changes while the player runs. Read before
|
|
2003
|
+
* activation; with `events` it follows other plugins' changes, without it
|
|
2004
|
+
* only this plugin's own. Players before 0.4.3 report `"system"`.
|
|
2005
|
+
*
|
|
2006
|
+
* @since 1.5.9
|
|
2007
|
+
*/
|
|
2008
|
+
readonly language: LanguagePreference;
|
|
2009
|
+
/**
|
|
2010
|
+
* Save the interface language for the next start.
|
|
2011
|
+
*
|
|
2012
|
+
* @remarks
|
|
2013
|
+
* The player keeps the choice in its interface state; the language
|
|
2014
|
+
* changes when the player starts again (tell the user, for example "Takes
|
|
2015
|
+
* effect after restart"). Every plugin with `events` hears the change in
|
|
2016
|
+
* {@link Appearance.language}.
|
|
2017
|
+
*
|
|
2018
|
+
* @capability ui.theme
|
|
2019
|
+
* @player 0.4.3
|
|
2020
|
+
*
|
|
2021
|
+
* @param language - `"system"` or a {@link Locale}.
|
|
2022
|
+
* @returns Resolves once the player saved it; {@link Appearance.language}
|
|
2023
|
+
* has the new value.
|
|
2024
|
+
*
|
|
2025
|
+
* @throws `invalid` (rejects) `language` is not `"system"` or a {@link Locale}.
|
|
2026
|
+
* @throws `capability` (rejects) The manifest does not declare `ui.theme`.
|
|
2027
|
+
* @throws `unsupported` (rejects) A player before 0.4.3.
|
|
2028
|
+
*
|
|
2029
|
+
* @example
|
|
2030
|
+
* ```ts
|
|
2031
|
+
* await plugin.appearance.setLanguage("de");
|
|
2032
|
+
* await plugin.osd.show("Takes effect after restart");
|
|
2033
|
+
* ```
|
|
2034
|
+
*
|
|
2035
|
+
* @since 1.5.9
|
|
2036
|
+
*/
|
|
2037
|
+
setLanguage(language: LanguagePreference): Promise<void>;
|
|
2038
|
+
}
|
|
2039
|
+
/**
|
|
2040
|
+
* An interface language of the player: English (`en`, the source language
|
|
2041
|
+
* of every plugin text) or a translation. The list is `LOCALES` in
|
|
2042
|
+
* `@vestra-player/sdk/testing`.
|
|
2043
|
+
*
|
|
2044
|
+
* @remarks
|
|
2045
|
+
* Simplified Chinese is `zh-Hans`. There is no Traditional Chinese: a
|
|
2046
|
+
* system set to Traditional Chinese (Taiwan, Hong Kong, Macao) gets English.
|
|
2047
|
+
*
|
|
2048
|
+
* @since 1.5.9
|
|
2049
|
+
* @category UI
|
|
2050
|
+
*/
|
|
2051
|
+
export type Locale = "en" | "zh-Hans" | "ja" | "ko" | "de" | "fr" | "es";
|
|
2052
|
+
/**
|
|
2053
|
+
* The saved interface language ({@link Appearance.language}): follow the
|
|
2054
|
+
* system, or one {@link Locale}.
|
|
2055
|
+
*
|
|
2056
|
+
* @since 1.5.9
|
|
2057
|
+
* @category UI
|
|
2058
|
+
*/
|
|
2059
|
+
export type LanguagePreference = "system" | Locale;
|
|
2060
|
+
/**
|
|
2061
|
+
* Arguments of a template sentence ({@link Osd.show},
|
|
2062
|
+
* {@link OsdPanel.set}, {@link ConfirmOptions.args}, {@link I18n.text}): an
|
|
2063
|
+
* array for `{}` and `{0}`, `{1}` placeholders, or an object for `{name}`
|
|
2064
|
+
* placeholders. At most 16. Strings and finite numbers are data, shown as
|
|
2065
|
+
* they are (whole numbers without a fraction); a {@link Text} or
|
|
2066
|
+
* {@link TextList} argument (SDK 1.5.11, player 0.4.3) is translated too,
|
|
2067
|
+
* so a sentence can be built from translated parts.
|
|
2068
|
+
*
|
|
2069
|
+
* @since 1.5.9
|
|
2070
|
+
* @category UI
|
|
2071
|
+
*/
|
|
2072
|
+
export type TemplateArgs = readonly TextArg[] | Readonly<Record<string, TextArg>>;
|
|
2073
|
+
/**
|
|
2074
|
+
* A text the player translates with the plugin's catalog and fills in:
|
|
2075
|
+
* English source text with its arguments. Made by {@link I18n.text}; plain
|
|
2076
|
+
* data, not a translation (the plugin never sees the translated string).
|
|
2077
|
+
*
|
|
2078
|
+
* @remarks
|
|
2079
|
+
* Accepted wherever the player shows a plugin's text: command titles, path
|
|
2080
|
+
* segments and reasons, {@link Osd.show} and {@link OsdPanel.set} (as the
|
|
2081
|
+
* text or an argument), the texts of {@link Dialogs.confirm}, file dialog
|
|
2082
|
+
* titles and `saveFile`'s `fileName`, and property values where Slint
|
|
2083
|
+
* expects a `string` (at any depth: a `[string]` model, a struct field).
|
|
2084
|
+
* Nested in another text's arguments it is translated too. Requires player
|
|
2085
|
+
* 0.4.3. Limits: `TEXT_LIMITS` in `@vestra-player/sdk/testing`.
|
|
2086
|
+
*
|
|
2087
|
+
* The wire form `{ $vestraText, args }` is what the player reads; write it
|
|
2088
|
+
* with {@link I18n.text}, so that `vestra-plugin i18n extract` finds the
|
|
2089
|
+
* source text.
|
|
2090
|
+
*
|
|
2091
|
+
* @since 1.5.11
|
|
2092
|
+
* @category UI
|
|
2093
|
+
*/
|
|
2094
|
+
export interface Text {
|
|
2095
|
+
/** The English source text: a template with `{}`, `{0}` or `{name}`. */
|
|
2096
|
+
readonly $vestraText: string;
|
|
2097
|
+
/** Values for its placeholders. */
|
|
2098
|
+
readonly args?: TemplateArgs;
|
|
2099
|
+
}
|
|
2100
|
+
/**
|
|
2101
|
+
* Values joined the way the interface language joins them ("a, b" in
|
|
2102
|
+
* English, "a、b" in Chinese). Made by {@link I18n.list}; accepted where a
|
|
2103
|
+
* {@link Text} is.
|
|
2104
|
+
*
|
|
2105
|
+
* @since 1.5.11
|
|
2106
|
+
* @category UI
|
|
2107
|
+
*/
|
|
2108
|
+
export interface TextList {
|
|
2109
|
+
/** The items: data, or texts the player translates. */
|
|
2110
|
+
readonly $vestraList: readonly TextArg[];
|
|
2111
|
+
/** How they are joined; `"list"` by default. */
|
|
2112
|
+
readonly style?: ListStyle;
|
|
2113
|
+
}
|
|
2114
|
+
/**
|
|
2115
|
+
* How a {@link TextList} is joined, per interface language:
|
|
2116
|
+
*
|
|
2117
|
+
* | style | English | 简体中文 | 日本語 |
|
|
2118
|
+
* | --- | --- | --- | --- |
|
|
2119
|
+
* | `list` (enumeration) | `, ` | `、` | `、` |
|
|
2120
|
+
* | `clauses` (parts of one sentence) | `, ` | `,` | `、` |
|
|
2121
|
+
* | `semicolons` | `; ` | `;` | `;` |
|
|
2122
|
+
* | `sentences` (no final full stop) | `. ` | `。` | `。` |
|
|
2123
|
+
* | `lines` | line break | line break | line break |
|
|
2124
|
+
*
|
|
2125
|
+
* Korean, German and Spanish join as English; French puts a narrow space
|
|
2126
|
+
* before `;`.
|
|
2127
|
+
*
|
|
2128
|
+
* @since 1.5.11
|
|
2129
|
+
* @category UI
|
|
2130
|
+
*/
|
|
2131
|
+
export type ListStyle = "list" | "clauses" | "semicolons" | "sentences" | "lines";
|
|
2132
|
+
/**
|
|
2133
|
+
* An argument of a template: data (a string or a finite number, shown as it
|
|
2134
|
+
* is) or a {@link Text} or {@link TextList} (translated).
|
|
2135
|
+
*
|
|
2136
|
+
* @since 1.5.11
|
|
2137
|
+
* @category UI
|
|
2138
|
+
*/
|
|
2139
|
+
export type TextArg = string | number | Text | TextList;
|
|
2140
|
+
/**
|
|
2141
|
+
* A text the player shows: English source text (translated as a whole), a
|
|
2142
|
+
* {@link Text} or a {@link TextList}.
|
|
2143
|
+
*
|
|
2144
|
+
* @since 1.5.11
|
|
2145
|
+
* @category UI
|
|
2146
|
+
*/
|
|
2147
|
+
export type TextValue = string | Text | TextList;
|
|
2148
|
+
/**
|
|
2149
|
+
* The interface language of this run. `plugin.i18n`.
|
|
2150
|
+
*
|
|
2151
|
+
* @remarks
|
|
2152
|
+
* Plugins write no translation code. Every user-visible text is English
|
|
2153
|
+
* source text in one of three places, and the player translates it with
|
|
2154
|
+
* the plugin's own catalog (`locales/<lang>.po`, compiled into the package
|
|
2155
|
+
* by `vestra-plugin build`):
|
|
2156
|
+
*
|
|
2157
|
+
* 1. declarations: command titles and paths, settings page and panel
|
|
2158
|
+
* titles, the manifest's `name`, `punchline`, `description` and `tags`;
|
|
2159
|
+
* 2. Slint: `@tr("…")` in the plugin's `.slint` files;
|
|
2160
|
+
* 3. sentences the plugin hands the player: {@link Osd.show},
|
|
2161
|
+
* {@link OsdPanel.set} and {@link Dialogs.confirm} take a template and
|
|
2162
|
+
* its arguments (`osd.show("Speed {}×", [rate])`), never a sentence
|
|
2163
|
+
* composed in TypeScript.
|
|
2164
|
+
*
|
|
2165
|
+
* Where words and data cannot be separated that way (a menu item with a
|
|
2166
|
+
* number, a `[string]` model, a sentence made of translated parts), the
|
|
2167
|
+
* plugin passes a text value ({@link I18n.text}, {@link I18n.list}; SDK
|
|
2168
|
+
* 1.5.11): data the player translates, never a translated string.
|
|
2169
|
+
*
|
|
2170
|
+
* The language is fixed when the player starts: {@link I18n.locale} never
|
|
2171
|
+
* changes during a run. Read it for what is not text, such as the order of
|
|
2172
|
+
* names or a date format. `vestra-plugin i18n extract` collects the texts
|
|
2173
|
+
* into `locales/messages.pot`; see the
|
|
2174
|
+
* [i18n guide](../../docs/how-to/i18n.md).
|
|
2175
|
+
*
|
|
2176
|
+
* @capability None.
|
|
2177
|
+
*
|
|
2178
|
+
* @example Format a date the way the interface language writes it
|
|
2179
|
+
* ```ts
|
|
2180
|
+
* const day = new Date().toLocaleDateString(plugin.i18n.locale);
|
|
2181
|
+
* await plugin.osd.show("Today is {}", [day]);
|
|
2182
|
+
* ```
|
|
2183
|
+
*
|
|
2184
|
+
* @since 1.5.9
|
|
2185
|
+
* @category UI
|
|
2186
|
+
*/
|
|
2187
|
+
export interface I18n {
|
|
2188
|
+
/**
|
|
2189
|
+
* The interface language of this run, chosen at start-up from the saved
|
|
2190
|
+
* {@link Appearance.language} or the system's languages; English when
|
|
2191
|
+
* neither names a {@link Locale}. Players before 0.4.3 report `"en"`.
|
|
2192
|
+
*/
|
|
2193
|
+
readonly locale: Locale;
|
|
2194
|
+
/**
|
|
2195
|
+
* A text that mixes words with data, for the player to translate: the
|
|
2196
|
+
* English source text (a template) and its arguments. It returns a plain
|
|
2197
|
+
* {@link Text} value, not a translation; pass it where the player shows
|
|
2198
|
+
* text (see {@link Text}) and the player shows it translated with this
|
|
2199
|
+
* plugin's catalog. `vestra-plugin i18n extract` collects `source` from
|
|
2200
|
+
* every call, so write it as a literal (or a conditional of literals, or
|
|
2201
|
+
* an `as const` table entry).
|
|
2202
|
+
*
|
|
2203
|
+
* Arguments are data unless they are texts themselves, so a sentence can
|
|
2204
|
+
* be built from translated parts without composing it in TypeScript.
|
|
2205
|
+
* `text` does not use `this`: `const { text, list } = plugin.i18n` works.
|
|
2206
|
+
*
|
|
2207
|
+
* @param source - English source text; `{}`, `{0}` or `{name}` for the
|
|
2208
|
+
* arguments, `{{` and `}}` for braces.
|
|
2209
|
+
* @param args - Values for its placeholders.
|
|
2210
|
+
* @throws `invalid` A malformed or over-limit value (`TEXT_LIMITS`).
|
|
2211
|
+
*
|
|
2212
|
+
* @example A ComboBox model with fixed words and data
|
|
2213
|
+
* ```ts
|
|
2214
|
+
* const { text } = plugin.i18n;
|
|
2215
|
+
* const picker = plugin.windows.create("ui/clip.slint");
|
|
2216
|
+
* const tracks = [{ id: 7, title: "en" }];
|
|
2217
|
+
* picker.set({
|
|
2218
|
+
* labels: [text("No Audio"), ...tracks.map((t) => text("Track {} · {}", [t.id, t.title]))],
|
|
2219
|
+
* });
|
|
2220
|
+
* ```
|
|
2221
|
+
*
|
|
2222
|
+
* @example A message built from translated parts
|
|
2223
|
+
* ```ts
|
|
2224
|
+
* await plugin.osd.show("Download failed: {}", [plugin.i18n.text("Connection timed out")]);
|
|
2225
|
+
* ```
|
|
2226
|
+
*
|
|
2227
|
+
* @capability None.
|
|
2228
|
+
*
|
|
2229
|
+
* @since 1.5.11
|
|
2230
|
+
*/
|
|
2231
|
+
text(source: string, args?: TemplateArgs): Text;
|
|
2232
|
+
/**
|
|
2233
|
+
* Items joined the way the interface language joins them (see
|
|
2234
|
+
* {@link ListStyle}): `list(["a.glsl", "b.glsl"])` shows "a.glsl, b.glsl"
|
|
2235
|
+
* in English and "a.glsl、b.glsl" in Chinese. Items are data, or texts the
|
|
2236
|
+
* player translates. Accepted where a {@link Text} is.
|
|
2237
|
+
*
|
|
2238
|
+
* @param items - At most 256.
|
|
2239
|
+
* @param style - `"list"` by default.
|
|
2240
|
+
* @throws `invalid` A malformed or over-limit value.
|
|
2241
|
+
*
|
|
2242
|
+
* @example
|
|
2243
|
+
* ```ts
|
|
2244
|
+
* const missing = ["a.glsl", "b.glsl"];
|
|
2245
|
+
* await plugin.osd.show("Removed missing shaders: {}", [plugin.i18n.list(missing)]);
|
|
2246
|
+
* ```
|
|
2247
|
+
*
|
|
2248
|
+
* @capability None.
|
|
2249
|
+
*
|
|
2250
|
+
* @since 1.5.11
|
|
2251
|
+
*/
|
|
2252
|
+
list(items: readonly TextArg[], style?: ListStyle): TextList;
|
|
2253
|
+
/**
|
|
2254
|
+
* An `Error` whose words the player shows translated: throw it where the
|
|
2255
|
+
* player shows a plugin's failure to the user, such as from a
|
|
2256
|
+
* file or web resolver's `resolve` ({@link FileResolverOptions}, {@link WebResolverOptions}) (also when a stream
|
|
2257
|
+
* fails while it starts). The player shows `text` translated with this
|
|
2258
|
+
* plugin's catalog (as `player.state.error` and the failure message);
|
|
2259
|
+
* `message` is the English rendering, for logs and older players.
|
|
2260
|
+
* Elsewhere it is an ordinary `Error`.
|
|
2261
|
+
*
|
|
2262
|
+
* @param source - English source text, as {@link I18n.text}'s.
|
|
2263
|
+
* @param args - Values for its placeholders.
|
|
2264
|
+
* @throws `invalid` A malformed or over-limit value.
|
|
2265
|
+
*
|
|
2266
|
+
* @example
|
|
2267
|
+
* ```ts
|
|
2268
|
+
* plugin.resolvers.add({
|
|
2269
|
+
* id: "nes",
|
|
2270
|
+
* extensions: ["nes"],
|
|
2271
|
+
* async resolve() {
|
|
2272
|
+
* throw plugin.i18n.error("The ROM file was not found.");
|
|
2273
|
+
* },
|
|
2274
|
+
* });
|
|
2275
|
+
* ```
|
|
2276
|
+
*
|
|
2277
|
+
* @capability None.
|
|
2278
|
+
*
|
|
2279
|
+
* @since 1.5.11
|
|
2280
|
+
*/
|
|
2281
|
+
error(source: string, args?: TemplateArgs): TextError;
|
|
2282
|
+
/**
|
|
2283
|
+
* The string a text shows in this run's language, for text that leaves
|
|
2284
|
+
* the player: what the plugin copies to the clipboard or writes to a file
|
|
2285
|
+
* ("Copy info", "Save as…"). Translated with this plugin's catalog (a
|
|
2286
|
+
* string as a whole, a {@link Text} or {@link TextList} with its
|
|
2287
|
+
* arguments), the way the player would show it.
|
|
2288
|
+
*
|
|
2289
|
+
* Only for text leaving the player. Never use it for the interface (a
|
|
2290
|
+
* window, the menu, the OSD, a dialog): pass the value itself there, so
|
|
2291
|
+
* the player translates it and `vestra-plugin i18n check` can see the
|
|
2292
|
+
* sentence is whole.
|
|
2293
|
+
*
|
|
2294
|
+
* @param value - Source text, or a text value.
|
|
2295
|
+
* @returns The translated string.
|
|
2296
|
+
* @throws `invalid` A malformed value.
|
|
2297
|
+
*
|
|
2298
|
+
* @example
|
|
2299
|
+
* ```ts
|
|
2300
|
+
* const { text, list, resolve } = plugin.i18n;
|
|
2301
|
+
* const lines = list([text("Version {}", ["1.0"]), text("Cores: {}", [8])], "lines");
|
|
2302
|
+
* await plugin.clipboard.writeText(resolve(lines));
|
|
2303
|
+
* ```
|
|
2304
|
+
*
|
|
2305
|
+
* @capability None.
|
|
2306
|
+
*
|
|
2307
|
+
* @since 1.5.11
|
|
2308
|
+
*/
|
|
2309
|
+
resolve(value: TextValue): string;
|
|
2310
|
+
}
|
|
2311
|
+
/**
|
|
2312
|
+
* An `Error` the player shows translated ({@link I18n.error}).
|
|
2313
|
+
*
|
|
2314
|
+
* @since 1.5.11
|
|
2315
|
+
* @category UI
|
|
2316
|
+
*/
|
|
2317
|
+
export interface TextError extends Error {
|
|
2318
|
+
/** What the player shows. */
|
|
2319
|
+
readonly text: Text;
|
|
1943
2320
|
}
|
|
1944
2321
|
/**
|
|
1945
2322
|
* The categories of the Options window. The tree shows them in this order:
|
|
@@ -2352,6 +2729,9 @@ export interface TimelineLayer extends Disposable {
|
|
|
2352
2729
|
* Replace the layer (last write wins; `[]` clears it). At most 1000 marks,
|
|
2353
2730
|
* titles ≤ 100 characters, times within the media. Failures go to `onError`;
|
|
2354
2731
|
* with `ifCurrent`, a write for another source is dropped silently.
|
|
2732
|
+
* A title is data (a chapter's or bookmark's own name), or a {@link Text}
|
|
2733
|
+
* the player translates (`text("Chapter {}", [n])`, SDK 1.5.11); other
|
|
2734
|
+
* plugins read the shown string.
|
|
2355
2735
|
*
|
|
2356
2736
|
* @example
|
|
2357
2737
|
* ```ts
|
|
@@ -2366,7 +2746,7 @@ export interface TimelineLayer extends Disposable {
|
|
|
2366
2746
|
set(marks: {
|
|
2367
2747
|
time: number;
|
|
2368
2748
|
kind: MarkKind;
|
|
2369
|
-
title?: string;
|
|
2749
|
+
title?: string | Text;
|
|
2370
2750
|
}[], options?: {
|
|
2371
2751
|
ifCurrent?: PlayerState;
|
|
2372
2752
|
}): void;
|
|
@@ -2560,17 +2940,17 @@ export interface DisplayInfo {
|
|
|
2560
2940
|
*/
|
|
2561
2941
|
export interface ConfirmOptions {
|
|
2562
2942
|
/** The question, shown in bold; 1–200 characters. */
|
|
2563
|
-
message:
|
|
2943
|
+
message: TextValue;
|
|
2564
2944
|
/** More text under the message; at most 2000 characters. */
|
|
2565
|
-
detail?:
|
|
2945
|
+
detail?: TextValue;
|
|
2566
2946
|
/** The confirm button's text (the default button: Enter picks it); 1–40 characters. */
|
|
2567
|
-
confirm:
|
|
2947
|
+
confirm: TextValue;
|
|
2568
2948
|
/**
|
|
2569
2949
|
* The cancel button's text (Escape picks it); 1–40 characters.
|
|
2570
2950
|
*
|
|
2571
2951
|
* @defaultValue "Cancel", in the player's language
|
|
2572
2952
|
*/
|
|
2573
|
-
cancel?:
|
|
2953
|
+
cancel?: TextValue;
|
|
2574
2954
|
/**
|
|
2575
2955
|
* Mark the confirm button as destructive: red text on macOS, a warning
|
|
2576
2956
|
* icon on Windows.
|
|
@@ -2579,7 +2959,19 @@ export interface ConfirmOptions {
|
|
|
2579
2959
|
*/
|
|
2580
2960
|
destructive?: boolean;
|
|
2581
2961
|
/** A checkbox under the text, such as "Don't ask again"; 1–40 characters. */
|
|
2582
|
-
checkbox?:
|
|
2962
|
+
checkbox?: TextValue;
|
|
2963
|
+
/**
|
|
2964
|
+
* Values for the placeholders of `message` and `detail` (player 0.4.3).
|
|
2965
|
+
* Any of the texts may instead be a {@link Text} (SDK 1.5.11), which
|
|
2966
|
+
* carries its own arguments; `args` only fills the string ones.
|
|
2967
|
+
* Every text of the dialog is English source text that the player shows
|
|
2968
|
+
* translated from the plugin's catalog; `message` and `detail` are
|
|
2969
|
+
* templates like {@link Osd.show}'s. The length limits apply to the shown
|
|
2970
|
+
* text.
|
|
2971
|
+
*
|
|
2972
|
+
* @since 1.5.9
|
|
2973
|
+
*/
|
|
2974
|
+
args?: TemplateArgs;
|
|
2583
2975
|
}
|
|
2584
2976
|
/**
|
|
2585
2977
|
* The system's own dialogs: a confirmation alert and the open and save file
|
|
@@ -2690,8 +3082,8 @@ export interface Dialogs {
|
|
|
2690
3082
|
* @since 1.0.0
|
|
2691
3083
|
*/
|
|
2692
3084
|
openFile(options?: {
|
|
2693
|
-
/** The dialog's title, at most 256 bytes. */
|
|
2694
|
-
title?:
|
|
3085
|
+
/** The dialog's title (English source text or a {@link Text}), at most 256 bytes. */
|
|
3086
|
+
title?: TextValue;
|
|
2695
3087
|
}): Promise<string | null>;
|
|
2696
3088
|
/**
|
|
2697
3089
|
* Ask the user for one or more files to open.
|
|
@@ -2715,8 +3107,8 @@ export interface Dialogs {
|
|
|
2715
3107
|
* @since 1.0.0
|
|
2716
3108
|
*/
|
|
2717
3109
|
openFiles(options?: {
|
|
2718
|
-
/** The dialog's title, at most 256 bytes. */
|
|
2719
|
-
title?:
|
|
3110
|
+
/** The dialog's title (English source text or a {@link Text}), at most 256 bytes. */
|
|
3111
|
+
title?: TextValue;
|
|
2720
3112
|
}): Promise<string[]>;
|
|
2721
3113
|
/**
|
|
2722
3114
|
* Ask the user for a folder.
|
|
@@ -2740,8 +3132,8 @@ export interface Dialogs {
|
|
|
2740
3132
|
* @since 1.0.0
|
|
2741
3133
|
*/
|
|
2742
3134
|
openDirectory(options?: {
|
|
2743
|
-
/** The dialog's title, at most 256 bytes. */
|
|
2744
|
-
title?:
|
|
3135
|
+
/** The dialog's title (English source text or a {@link Text}), at most 256 bytes. */
|
|
3136
|
+
title?: TextValue;
|
|
2745
3137
|
}): Promise<string | null>;
|
|
2746
3138
|
/**
|
|
2747
3139
|
* Ask the user where to save a file.
|
|
@@ -2771,10 +3163,15 @@ export interface Dialogs {
|
|
|
2771
3163
|
* @since 1.0.0
|
|
2772
3164
|
*/
|
|
2773
3165
|
saveFile(options?: {
|
|
2774
|
-
/** The dialog's title, at most 256 bytes. */
|
|
2775
|
-
title?:
|
|
2776
|
-
/**
|
|
2777
|
-
|
|
3166
|
+
/** The dialog's title (English source text or a {@link Text}), at most 256 bytes. */
|
|
3167
|
+
title?: TextValue;
|
|
3168
|
+
/**
|
|
3169
|
+
* The proposed file name: a plain name, at most 256 bytes. A string is
|
|
3170
|
+
* data (not translated); a {@link Text} (SDK 1.5.11) is shown
|
|
3171
|
+
* translated, `text("Playlist.m3u8")` (a `/` or `\\` in a translation
|
|
3172
|
+
* becomes `-`).
|
|
3173
|
+
*/
|
|
3174
|
+
fileName?: TextValue;
|
|
2778
3175
|
}): Promise<string | null>;
|
|
2779
3176
|
}
|
|
2780
3177
|
/** One audio track of the current media ({@link PlayerState.audioTracks}). */
|
|
@@ -3349,18 +3746,38 @@ export interface OsdPanel extends Disposable {
|
|
|
3349
3746
|
* @capability ui.osd
|
|
3350
3747
|
*
|
|
3351
3748
|
* @param text - The text, with `\n` between lines: at most 32 lines and
|
|
3352
|
-
* 4096 bytes. `null` hides the block.
|
|
3749
|
+
* 4096 bytes once translated and formatted. `null` hides the block. A
|
|
3750
|
+
* template, like {@link Osd.show}'s.
|
|
3751
|
+
* @param args - Values for its placeholders (player 0.4.3); `null` or
|
|
3752
|
+
* omitted for none.
|
|
3753
|
+
* @param options - `maxColumns`: cut long lines (SDK 1.5.11).
|
|
3353
3754
|
*
|
|
3354
3755
|
* @example
|
|
3355
3756
|
* ```ts
|
|
3356
3757
|
* const info = plugin.osd.panel();
|
|
3357
|
-
* info.set("A:
|
|
3758
|
+
* info.set("A: {} s\nB: {} s", ["12.0", "18.5"]);
|
|
3358
3759
|
* info.set(null); // hide it
|
|
3359
3760
|
* ```
|
|
3360
3761
|
*
|
|
3361
3762
|
* @since 1.0.0
|
|
3362
3763
|
*/
|
|
3363
|
-
set(text:
|
|
3764
|
+
set(text: TextValue | null, args?: TemplateArgs | null, options?: OsdPanelOptions): void;
|
|
3765
|
+
}
|
|
3766
|
+
/**
|
|
3767
|
+
* Options of {@link OsdPanel.set}.
|
|
3768
|
+
*
|
|
3769
|
+
* @since 1.5.11
|
|
3770
|
+
* @category UI
|
|
3771
|
+
*/
|
|
3772
|
+
export interface OsdPanelOptions {
|
|
3773
|
+
/**
|
|
3774
|
+
* Cut every line longer than this many columns, after translation and
|
|
3775
|
+
* formatting, ending it with `…`: a wide character (Chinese, Japanese,
|
|
3776
|
+
* Korean, full-width forms) is two columns, a combining mark none, any
|
|
3777
|
+
* other one. An integer from 8 to 1000 (player 0.4.3; older players show
|
|
3778
|
+
* whole lines). Measure the video area to choose it.
|
|
3779
|
+
*/
|
|
3780
|
+
maxColumns?: number;
|
|
3364
3781
|
}
|
|
3365
3782
|
/**
|
|
3366
3783
|
* Text the player draws over the video: short messages and an information
|
|
@@ -3398,24 +3815,38 @@ export interface Osd {
|
|
|
3398
3815
|
* Replaces the message on screen, whichever plugin showed it. A message
|
|
3399
3816
|
* that is on screen when the plugin stops still disappears on time.
|
|
3400
3817
|
*
|
|
3818
|
+
* The text is a template in English: the player shows its translation
|
|
3819
|
+
* from the plugin's catalog, with the placeholders (`{}`, `{0}`, `{name}`;
|
|
3820
|
+
* `{{` and `}}` for braces) filled from `args`. Without `args` the text
|
|
3821
|
+
* shows as it is (braces included). Untranslated, the English template is
|
|
3822
|
+
* formatted. Never compose the sentence in TypeScript
|
|
3823
|
+
* (`` `Speed ${rate}×` ``): translators can only translate whole templates.
|
|
3824
|
+
* An argument that is itself words is a {@link Text} (SDK 1.5.11), and a
|
|
3825
|
+
* message made of a varying number of parts is a {@link TextList} of
|
|
3826
|
+
* texts; `text` may also be a `Text` (then without `args`).
|
|
3827
|
+
*
|
|
3401
3828
|
* @capability ui.osd
|
|
3402
3829
|
*
|
|
3403
|
-
* @param text - 1–200 characters
|
|
3830
|
+
* @param text - The template, 1–200 characters once translated and
|
|
3831
|
+
* formatted; line breaks become spaces.
|
|
3832
|
+
* @param args - Values for its placeholders (player 0.4.3; older players
|
|
3833
|
+
* show the template as it is).
|
|
3404
3834
|
* @returns Resolves once the message is on screen.
|
|
3405
3835
|
*
|
|
3406
|
-
* @throws `invalid` (rejects)
|
|
3407
|
-
* than 200 characters.
|
|
3836
|
+
* @throws `invalid` (rejects) The shown text is empty, only white space,
|
|
3837
|
+
* or longer than 200 characters, or `args` is not a {@link TemplateArgs}.
|
|
3408
3838
|
* @throws `unavailable` (rejects) The player runs without a user interface.
|
|
3409
3839
|
* @throws `capability` (rejects) The manifest does not declare `ui.osd`.
|
|
3410
3840
|
*
|
|
3411
3841
|
* @example
|
|
3412
3842
|
* ```ts
|
|
3413
3843
|
* await plugin.osd.show("Bookmark added");
|
|
3844
|
+
* await plugin.osd.show("Speed {}×", [plugin.player.state.rate]);
|
|
3414
3845
|
* ```
|
|
3415
3846
|
*
|
|
3416
3847
|
* @since 1.0.0
|
|
3417
3848
|
*/
|
|
3418
|
-
show(text:
|
|
3849
|
+
show(text: TextValue, args?: TemplateArgs): Promise<void>;
|
|
3419
3850
|
/**
|
|
3420
3851
|
* Create this plugin's information block.
|
|
3421
3852
|
*
|
|
@@ -3720,7 +4151,9 @@ export interface Subtitles {
|
|
|
3720
4151
|
/**
|
|
3721
4152
|
* Upload a subtitle file's bytes (UTF-8 SRT, or ASS/SSA with
|
|
3722
4153
|
* `format: "ass"`) for the current source; select it unless
|
|
3723
|
-
* `select: "none"`. `title` (1–200 characters) names the track
|
|
4154
|
+
* `select: "none"`. `title` (1–200 characters) names the track: data, or
|
|
4155
|
+
* a {@link Text} the player translates (`text("{} · {}", [text("Simplified
|
|
4156
|
+
* Chinese"), file])`, SDK 1.5.11). Aborting
|
|
3724
4157
|
* `signal` before the commit discards the upload (rejects with AbortError);
|
|
3725
4158
|
* once the commit was sent it completes.
|
|
3726
4159
|
*
|
|
@@ -3730,7 +4163,7 @@ export interface Subtitles {
|
|
|
3730
4163
|
*/
|
|
3731
4164
|
load(bytes: Uint8Array, options?: SubtitleConditional & {
|
|
3732
4165
|
format?: "srt" | "ass";
|
|
3733
|
-
title?: string;
|
|
4166
|
+
title?: string | Text;
|
|
3734
4167
|
select?: "primary" | "secondary" | "none";
|
|
3735
4168
|
signal?: AbortSignal;
|
|
3736
4169
|
}): Promise<SubtitleTrack>;
|
|
@@ -4207,6 +4640,30 @@ export interface PluginInfo {
|
|
|
4207
4640
|
* @since 1.5.2
|
|
4208
4641
|
*/
|
|
4209
4642
|
warnings?: readonly PluginWarning[];
|
|
4643
|
+
/**
|
|
4644
|
+
* The manifest's display texts in the interface language, translated
|
|
4645
|
+
* with that package's catalog; absent from players before 0.4.3 (read
|
|
4646
|
+
* `manifest.json` there).
|
|
4647
|
+
*
|
|
4648
|
+
* @since 1.5.9
|
|
4649
|
+
*/
|
|
4650
|
+
display?: PluginDisplay;
|
|
4651
|
+
}
|
|
4652
|
+
/**
|
|
4653
|
+
* {@link PluginInfo.display}: a package's `name`, `punchline`,
|
|
4654
|
+
* `description` and `tags` as the player shows them.
|
|
4655
|
+
*
|
|
4656
|
+
* @since 1.5.9
|
|
4657
|
+
*/
|
|
4658
|
+
export interface PluginDisplay {
|
|
4659
|
+
/** `name`, translated; `null` when the manifest has none. */
|
|
4660
|
+
readonly name: string | null;
|
|
4661
|
+
/** `punchline`, translated; `null` when the manifest has none. */
|
|
4662
|
+
readonly punchline: string | null;
|
|
4663
|
+
/** `description`, translated; `null` when the manifest has none. */
|
|
4664
|
+
readonly description: string | null;
|
|
4665
|
+
/** `tags`, each translated. */
|
|
4666
|
+
readonly tags: readonly string[];
|
|
4210
4667
|
}
|
|
4211
4668
|
/**
|
|
4212
4669
|
* One refusal in {@link PluginInfo.warnings}.
|
|
@@ -4293,8 +4750,20 @@ export interface BindingRef {
|
|
|
4293
4750
|
export interface BindingInfo extends BindingRef {
|
|
4294
4751
|
/** Menu title. */
|
|
4295
4752
|
title: string;
|
|
4296
|
-
/** Menu path; `null` for a command outside the menu. */
|
|
4753
|
+
/** Menu path as shown; `null` for a command outside the menu. */
|
|
4297
4754
|
path: string[] | null;
|
|
4755
|
+
/**
|
|
4756
|
+
* The menu path's keys: the English text menus merge by, the same in
|
|
4757
|
+
* every interface language (`["Playback", "Seek", "Back 5 s"]`; a
|
|
4758
|
+
* built-in menu by its key, `"Video"`, also when declared as `@video`).
|
|
4759
|
+
* `null` for a command outside the menu, and from players before 0.4.3.
|
|
4760
|
+
* Find a command by where it is in the menu with this, not with `path`.
|
|
4761
|
+
* Always set by `list()`; optional so that test fakes written for older
|
|
4762
|
+
* SDKs still type-check.
|
|
4763
|
+
*
|
|
4764
|
+
* @since 1.5.11
|
|
4765
|
+
*/
|
|
4766
|
+
key?: string[] | null;
|
|
4298
4767
|
/** Global, or only while the plugin's panel has focus. */
|
|
4299
4768
|
scope: "global" | "panel";
|
|
4300
4769
|
/** The command's own bindings. */
|