@behindthemusictree/app-kit-ui 24.0.1 → 26.1.0
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/dist/{chunk-BPCFNBFO.js → chunk-KPWV4LEJ.js} +163 -75
- package/dist/chunk-KPWV4LEJ.js.map +1 -0
- package/dist/genre-tree/index.cjs +180 -92
- package/dist/genre-tree/index.cjs.map +1 -1
- package/dist/genre-tree/index.d.ts +21 -5
- package/dist/genre-tree/index.js +1 -1
- package/dist/index.cjs +180 -92
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/package.json +4 -4
- package/dist/chunk-BPCFNBFO.js.map +0 -1
package/dist/index.cjs
CHANGED
|
@@ -471,8 +471,9 @@ function AuthCallbackHandler({ renderStatus, ...options }) {
|
|
|
471
471
|
|
|
472
472
|
// src/genre-tree/GenreTreeView.tsx
|
|
473
473
|
var import_react10 = require("react");
|
|
474
|
+
var import_react_query3 = require("@tanstack/react-query");
|
|
474
475
|
var import_lucide_react12 = require("lucide-react");
|
|
475
|
-
var
|
|
476
|
+
var import_ui17 = require("@behindthemusictree/ui");
|
|
476
477
|
var import_genre_tree_view4 = require("@behindthemusictree/genre-tree-view");
|
|
477
478
|
var import_genre_tree17 = require("@behindthemusictree/app-kit/genre-tree");
|
|
478
479
|
var import_genre_tree18 = require("@behindthemusictree/app-kit/genre-tree");
|
|
@@ -964,6 +965,11 @@ var import_genre_tree_view2 = require("@behindthemusictree/genre-tree-view");
|
|
|
964
965
|
var import_player4 = require("@behindthemusictree/app-kit/player");
|
|
965
966
|
var import_popup4 = require("@behindthemusictree/app-kit/popup");
|
|
966
967
|
var import_transport7 = require("@behindthemusictree/app-kit/transport");
|
|
968
|
+
|
|
969
|
+
// src/genre-tree/playlist-tree/size-metric.ts
|
|
970
|
+
var genrePlaylistSize = (genrePlaylist, metric) => metric === "views" ? genrePlaylist.viewsCount : genrePlaylist.tracksCount;
|
|
971
|
+
|
|
972
|
+
// src/genre-tree/playlist-tree/TreeWheel.tsx
|
|
967
973
|
var import_track_noun5 = require("@behindthemusictree/app-kit/track-noun");
|
|
968
974
|
var import_jsx_runtime17 = require("react/jsx-runtime");
|
|
969
975
|
function GenrePlaylistTreeWheel({
|
|
@@ -984,6 +990,9 @@ function GenrePlaylistTreeWheel({
|
|
|
984
990
|
allowWheelRotation,
|
|
985
991
|
showToolbar,
|
|
986
992
|
controlsOrientation,
|
|
993
|
+
sizeMetric = "songs",
|
|
994
|
+
floatingControlsLeading,
|
|
995
|
+
busy,
|
|
987
996
|
defaultViewport,
|
|
988
997
|
onViewportChange,
|
|
989
998
|
playback,
|
|
@@ -999,12 +1008,12 @@ function GenrePlaylistTreeWheel({
|
|
|
999
1008
|
id: genrePlaylist.uuid,
|
|
1000
1009
|
parentId: genrePlaylist.parent?.uuid ?? null,
|
|
1001
1010
|
name: genrePlaylist.name,
|
|
1002
|
-
itemCount: genrePlaylist
|
|
1011
|
+
itemCount: genrePlaylistSize(genrePlaylist, sizeMetric),
|
|
1003
1012
|
actionable: Boolean(genrePlaylist.criteria),
|
|
1004
1013
|
side: genrePlaylist.criteria?.side ?? void 0,
|
|
1005
1014
|
wikidataId: genrePlaylist.criteria?.wikidataId ?? null
|
|
1006
1015
|
})),
|
|
1007
|
-
[genrePlaylists]
|
|
1016
|
+
[genrePlaylists, sizeMetric]
|
|
1008
1017
|
);
|
|
1009
1018
|
const handlePlayPause = (0, import_react5.useCallback)(
|
|
1010
1019
|
(nodeId) => {
|
|
@@ -1056,7 +1065,7 @@ function GenrePlaylistTreeWheel({
|
|
|
1056
1065
|
{
|
|
1057
1066
|
className,
|
|
1058
1067
|
nodes,
|
|
1059
|
-
itemCountLabel: `${(0, import_track_noun5.capitalize)(trackNoun.singular)} count`,
|
|
1068
|
+
itemCountLabel: sizeMetric === "views" ? "Views" : `${(0, import_track_noun5.capitalize)(trackNoun.singular)} count`,
|
|
1060
1069
|
playingNodeId,
|
|
1061
1070
|
playState: isPlaying ? "playing" : "paused",
|
|
1062
1071
|
onPlayPause: handlePlayPause,
|
|
@@ -1074,6 +1083,8 @@ function GenrePlaylistTreeWheel({
|
|
|
1074
1083
|
allowWheelRotation,
|
|
1075
1084
|
showToolbar,
|
|
1076
1085
|
controlsOrientation,
|
|
1086
|
+
floatingControlsLeading,
|
|
1087
|
+
busy,
|
|
1077
1088
|
defaultViewport,
|
|
1078
1089
|
onViewportChange,
|
|
1079
1090
|
...infoPanelCuration,
|
|
@@ -1107,6 +1118,9 @@ function GenrePlaylistTreeWheelRadialPopCore(props) {
|
|
|
1107
1118
|
allowWheelRotation,
|
|
1108
1119
|
showToolbar,
|
|
1109
1120
|
controlsOrientation,
|
|
1121
|
+
sizeMetric = "songs",
|
|
1122
|
+
floatingControlsLeading,
|
|
1123
|
+
busy,
|
|
1110
1124
|
outline = false,
|
|
1111
1125
|
defaultViewport,
|
|
1112
1126
|
onViewportChange,
|
|
@@ -1114,10 +1128,6 @@ function GenrePlaylistTreeWheelRadialPopCore(props) {
|
|
|
1114
1128
|
} = props;
|
|
1115
1129
|
const focus = props;
|
|
1116
1130
|
const infoPanelCuration = {
|
|
1117
|
-
editMode: props.editMode,
|
|
1118
|
-
onEditModeChange: props.onEditModeChange,
|
|
1119
|
-
renderTitleEditor: props.renderTitleEditor,
|
|
1120
|
-
renderParentsEditor: props.renderParentsEditor,
|
|
1121
1131
|
renderDangerZone: props.renderDangerZone,
|
|
1122
1132
|
expanded: props.expanded,
|
|
1123
1133
|
onExpandedChange: props.onExpandedChange,
|
|
@@ -1134,14 +1144,15 @@ function GenrePlaylistTreeWheelRadialPopCore(props) {
|
|
|
1134
1144
|
id: genrePlaylist.uuid,
|
|
1135
1145
|
parentId: genrePlaylist.parent?.uuid ?? null,
|
|
1136
1146
|
name: genrePlaylist.name,
|
|
1137
|
-
itemCount: genrePlaylist
|
|
1147
|
+
itemCount: genrePlaylistSize(genrePlaylist, sizeMetric),
|
|
1138
1148
|
actionable: Boolean(genrePlaylist.criteria),
|
|
1139
1149
|
detached: !genrePlaylist.criteria,
|
|
1140
1150
|
side: genrePlaylist.criteria?.side ?? void 0,
|
|
1141
1151
|
wikidataId: genrePlaylist.criteria?.wikidataId ?? null,
|
|
1142
|
-
umbrella: genrePlaylist.isUmbrella
|
|
1152
|
+
umbrella: genrePlaylist.isUmbrella,
|
|
1153
|
+
scene: genrePlaylist.scene ?? void 0
|
|
1143
1154
|
})),
|
|
1144
|
-
[genrePlaylists]
|
|
1155
|
+
[genrePlaylists, sizeMetric]
|
|
1145
1156
|
);
|
|
1146
1157
|
const handlePlayPause = (0, import_react6.useCallback)(
|
|
1147
1158
|
(nodeId) => {
|
|
@@ -1183,7 +1194,7 @@ function GenrePlaylistTreeWheelRadialPopCore(props) {
|
|
|
1183
1194
|
const treeProps = {
|
|
1184
1195
|
className,
|
|
1185
1196
|
nodes,
|
|
1186
|
-
itemCountLabel: `${(0, import_track_noun6.capitalize)(trackNoun.singular)} count`,
|
|
1197
|
+
itemCountLabel: sizeMetric === "views" ? "Views" : `${(0, import_track_noun6.capitalize)(trackNoun.singular)} count`,
|
|
1187
1198
|
playingNodeId,
|
|
1188
1199
|
playState: isPlaying ? "playing" : "paused",
|
|
1189
1200
|
onPlayPause: handlePlayPause,
|
|
@@ -1208,6 +1219,8 @@ function GenrePlaylistTreeWheelRadialPopCore(props) {
|
|
|
1208
1219
|
...treeProps,
|
|
1209
1220
|
allowWheelRotation,
|
|
1210
1221
|
controlsOrientation,
|
|
1222
|
+
floatingControlsLeading,
|
|
1223
|
+
busy,
|
|
1211
1224
|
defaultViewport,
|
|
1212
1225
|
onViewportChange,
|
|
1213
1226
|
...focus.onFocusGenreChange ? { focusNodeId: focus.focusGenreUuid, onFocusChange: focus.onFocusGenreChange } : { focusNodeId: void 0, onFocusChange: void 0 }
|
|
@@ -1273,6 +1286,7 @@ function GenreSearch({
|
|
|
1273
1286
|
});
|
|
1274
1287
|
const extraItems = query !== "" && query !== selectedName ? extraResults?.items ?? [] : [];
|
|
1275
1288
|
const label = extraResults ? "Search" : "Search a genre";
|
|
1289
|
+
const loading = query !== "" && query !== selectedName && (extraResults?.loading ?? false);
|
|
1276
1290
|
const showList = results.length > 0 || extraItems.length > 0;
|
|
1277
1291
|
const heading = "px-3 pt-2 pb-1 text-xs font-medium uppercase text-[var(--color-text-muted)]";
|
|
1278
1292
|
return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "genre-search relative w-[calc(var(--layout-detail-panel-w,25.5rem)-2*var(--layout-panel-inset,1rem))] shrink-0", children: [
|
|
@@ -1298,11 +1312,34 @@ function GenreSearch({
|
|
|
1298
1312
|
},
|
|
1299
1313
|
placeholder: placeholder ?? `${label}\u2026`,
|
|
1300
1314
|
"aria-label": label,
|
|
1315
|
+
"aria-busy": loading,
|
|
1301
1316
|
className: "h-[var(--layout-search-h,3rem)] pl-6 pr-20 text-base transition-[padding] duration-200 ease-out motion-reduce:transition-none bg-[var(--color-surface)] border-[var(--color-border)] rounded-full shadow-md"
|
|
1302
1317
|
}
|
|
1303
1318
|
),
|
|
1304
1319
|
/* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "absolute right-3 top-1/2 flex items-center -translate-y-1/2", children: [
|
|
1305
|
-
/* @__PURE__ */ (0, import_jsx_runtime20.
|
|
1320
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
|
|
1321
|
+
"span",
|
|
1322
|
+
{
|
|
1323
|
+
"data-loading": loading,
|
|
1324
|
+
className: "relative p-2 text-[var(--color-text-muted)] pointer-events-none",
|
|
1325
|
+
children: [
|
|
1326
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
1327
|
+
import_lucide_react7.Search,
|
|
1328
|
+
{
|
|
1329
|
+
"aria-hidden": "true",
|
|
1330
|
+
className: `w-6 h-6 transition-opacity duration-200 motion-reduce:transition-none ${loading ? "opacity-0" : ""}`
|
|
1331
|
+
}
|
|
1332
|
+
),
|
|
1333
|
+
/* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
1334
|
+
import_lucide_react7.LoaderCircle,
|
|
1335
|
+
{
|
|
1336
|
+
"aria-hidden": "true",
|
|
1337
|
+
className: `absolute inset-2 w-6 h-6 transition-opacity duration-200 motion-reduce:transition-none ${loading ? "opacity-100 delay-300 animate-spin motion-reduce:animate-none" : "opacity-0"}`
|
|
1338
|
+
}
|
|
1339
|
+
)
|
|
1340
|
+
]
|
|
1341
|
+
}
|
|
1342
|
+
),
|
|
1306
1343
|
canClear && /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
|
|
1307
1344
|
"button",
|
|
1308
1345
|
{
|
|
@@ -1485,13 +1522,28 @@ function ChangeParentPopup({
|
|
|
1485
1522
|
genrePlaylists,
|
|
1486
1523
|
scope,
|
|
1487
1524
|
getBackendBaseUrl,
|
|
1488
|
-
onClose
|
|
1525
|
+
onClose,
|
|
1526
|
+
onParentChanged
|
|
1489
1527
|
}) {
|
|
1490
1528
|
const { mutate, isPending, formErrors } = (0, import_genre_tree11.useUpdateGenre)(scope, getBackendBaseUrl);
|
|
1491
1529
|
const candidates = (0, import_react8.useMemo)(
|
|
1492
1530
|
() => (0, import_genre_tree11.getReparentCandidates)(genrePlaylists, genrePlaylist.uuid),
|
|
1493
1531
|
[genrePlaylists, genrePlaylist.uuid]
|
|
1494
1532
|
);
|
|
1533
|
+
const handleSelect = (newParent) => {
|
|
1534
|
+
const genre = genrePlaylist.criteria.uuid;
|
|
1535
|
+
const parentPlaylistUuid = genrePlaylist.parent?.uuid;
|
|
1536
|
+
const from = parentPlaylistUuid ? genrePlaylists.find(({ uuid }) => uuid === parentPlaylistUuid)?.criteria?.uuid ?? null : null;
|
|
1537
|
+
mutate(
|
|
1538
|
+
{ uuid: genre, data: { parent: newParent.criteria.uuid } },
|
|
1539
|
+
{
|
|
1540
|
+
onSuccess: () => {
|
|
1541
|
+
onClose();
|
|
1542
|
+
onParentChanged?.({ genre, from, to: newParent.criteria.uuid });
|
|
1543
|
+
}
|
|
1544
|
+
}
|
|
1545
|
+
);
|
|
1546
|
+
};
|
|
1495
1547
|
(0, import_react8.useEffect)(() => {
|
|
1496
1548
|
const handleKeyDown = (event) => {
|
|
1497
1549
|
if (event.key === "Escape") onClose();
|
|
@@ -1508,7 +1560,7 @@ function ChangeParentPopup({
|
|
|
1508
1560
|
GenreSearch,
|
|
1509
1561
|
{
|
|
1510
1562
|
genrePlaylists: candidates,
|
|
1511
|
-
onSelect:
|
|
1563
|
+
onSelect: handleSelect,
|
|
1512
1564
|
placeholder: "Search a new parent\u2026"
|
|
1513
1565
|
}
|
|
1514
1566
|
) }),
|
|
@@ -1939,8 +1991,30 @@ function useArtistPanel({
|
|
|
1939
1991
|
}
|
|
1940
1992
|
}
|
|
1941
1993
|
|
|
1942
|
-
// src/genre-tree/
|
|
1994
|
+
// src/genre-tree/SizeMetricToggle.tsx
|
|
1995
|
+
var import_md2 = require("react-icons/md");
|
|
1996
|
+
var import_ui16 = require("@behindthemusictree/ui");
|
|
1943
1997
|
var import_jsx_runtime33 = require("react/jsx-runtime");
|
|
1998
|
+
function SizeMetricToggle({
|
|
1999
|
+
value,
|
|
2000
|
+
onChange
|
|
2001
|
+
}) {
|
|
2002
|
+
return /* @__PURE__ */ (0, import_jsx_runtime33.jsx)(
|
|
2003
|
+
import_ui16.SegmentedControl,
|
|
2004
|
+
{
|
|
2005
|
+
"aria-label": "Size nodes by",
|
|
2006
|
+
value,
|
|
2007
|
+
onChange,
|
|
2008
|
+
options: [
|
|
2009
|
+
{ value: "songs", label: /* @__PURE__ */ (0, import_jsx_runtime33.jsx)(import_md2.MdMusicNote, { size: 18, "aria-hidden": true }), "aria-label": "Size by songs", title: "Node size by song count" },
|
|
2010
|
+
{ value: "views", label: /* @__PURE__ */ (0, import_jsx_runtime33.jsx)(import_md2.MdVisibility, { size: 18, "aria-hidden": true }), "aria-label": "Size by views", title: "Node size by song views" }
|
|
2011
|
+
]
|
|
2012
|
+
}
|
|
2013
|
+
);
|
|
2014
|
+
}
|
|
2015
|
+
|
|
2016
|
+
// src/genre-tree/GenreTreeView.tsx
|
|
2017
|
+
var import_jsx_runtime34 = require("react/jsx-runtime");
|
|
1944
2018
|
var PREVIOUS_BUTTON_CSS = `
|
|
1945
2019
|
.genre-tree-view .search-overlay .gtv-info-panel-previous { display: none; }
|
|
1946
2020
|
.genre-tree-view:has(.search-overlay .gtv-info-panel-previous) .genre-search input { padding-left: 2.75rem; }
|
|
@@ -1962,7 +2036,7 @@ function GenreNodeActionBand({ genrePlaylist, scope, playback, ...bandProps }) {
|
|
|
1962
2036
|
console.error("Failed to load genre playlist tracks:", error);
|
|
1963
2037
|
});
|
|
1964
2038
|
};
|
|
1965
|
-
return /* @__PURE__ */ (0,
|
|
2039
|
+
return /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
1966
2040
|
GenreActionBand,
|
|
1967
2041
|
{
|
|
1968
2042
|
...bandProps,
|
|
@@ -1977,6 +2051,7 @@ function GenreTreeView({
|
|
|
1977
2051
|
scope,
|
|
1978
2052
|
handleGenreCreationAction,
|
|
1979
2053
|
handleGenreRenameAction,
|
|
2054
|
+
onParentChanged,
|
|
1980
2055
|
getBackendBaseUrl,
|
|
1981
2056
|
additionalActions,
|
|
1982
2057
|
viewMode: controlledViewMode,
|
|
@@ -1992,6 +2067,8 @@ function GenreTreeView({
|
|
|
1992
2067
|
criteriaOverviewSchema,
|
|
1993
2068
|
renderGenreDetailExtras,
|
|
1994
2069
|
controlsOrientation = "horizontal",
|
|
2070
|
+
sizeMetric: controlledSizeMetric,
|
|
2071
|
+
onSizeMetricChange,
|
|
1995
2072
|
renderArtistLink,
|
|
1996
2073
|
artistUuid: controlledArtistUuid,
|
|
1997
2074
|
onArtistUuidChange,
|
|
@@ -2005,10 +2082,6 @@ function GenreTreeView({
|
|
|
2005
2082
|
renderSongLeading,
|
|
2006
2083
|
renderSongActions,
|
|
2007
2084
|
renderTracksToolbar,
|
|
2008
|
-
editMode,
|
|
2009
|
-
onEditModeChange,
|
|
2010
|
-
renderTitleEditor,
|
|
2011
|
-
renderParentsEditor,
|
|
2012
2085
|
renderDangerZone,
|
|
2013
2086
|
expanded,
|
|
2014
2087
|
onExpandedChange,
|
|
@@ -2021,12 +2094,20 @@ function GenreTreeView({
|
|
|
2021
2094
|
const [internalArtistUuid, setInternalArtistUuid] = (0, import_react10.useState)(null);
|
|
2022
2095
|
const isArtistControlled = controlledArtistUuid !== void 0;
|
|
2023
2096
|
const artistUuid = isArtistControlled ? controlledArtistUuid : internalArtistUuid;
|
|
2097
|
+
const [internalSizeMetric, setInternalSizeMetric] = (0, import_react10.useState)("songs");
|
|
2098
|
+
const sizeMetric = controlledSizeMetric ?? internalSizeMetric;
|
|
2099
|
+
const deferredSizeMetric = (0, import_react10.useDeferredValue)(sizeMetric);
|
|
2100
|
+
const changeSizeMetric = (metric) => {
|
|
2101
|
+
if (controlledSizeMetric === void 0) setInternalSizeMetric(metric);
|
|
2102
|
+
onSizeMetricChange?.(metric);
|
|
2103
|
+
};
|
|
2024
2104
|
const changeArtist = (uuid) => {
|
|
2025
2105
|
if (!isArtistControlled) setInternalArtistUuid(uuid);
|
|
2026
2106
|
onArtistUuidChange?.(uuid);
|
|
2027
2107
|
};
|
|
2028
2108
|
const {
|
|
2029
2109
|
isLoading,
|
|
2110
|
+
isFetching: isTreeFetching,
|
|
2030
2111
|
genrePlaylistByNodeId,
|
|
2031
2112
|
visibleGenrePlaylists,
|
|
2032
2113
|
groupedGenrePlaylistsByRoot,
|
|
@@ -2051,6 +2132,8 @@ function GenreTreeView({
|
|
|
2051
2132
|
criteriaOverviewSchema,
|
|
2052
2133
|
artistUuid
|
|
2053
2134
|
});
|
|
2135
|
+
const isGenreUpdating = (0, import_react_query3.useIsMutating)({ mutationKey: import_genre_tree18.genreUpdateMutationKey }) > 0;
|
|
2136
|
+
const busy = deferredSizeMetric !== sizeMetric || isTreeFetching || isGenreUpdating;
|
|
2054
2137
|
const artistResult = (0, import_genre_tree18.useArtist)(artistUuid, artistSearchBaseUrl ?? getBackendBaseUrl);
|
|
2055
2138
|
const filterArtistName = artistResult.status === "success" ? artistResult.artist.name : null;
|
|
2056
2139
|
const filterArtist = (0, import_react10.useMemo)(
|
|
@@ -2067,7 +2150,7 @@ function GenreTreeView({
|
|
|
2067
2150
|
const artistPanel = useArtistPanel({
|
|
2068
2151
|
uuid: artistUuid,
|
|
2069
2152
|
getBackendBaseUrl: artistBaseUrl,
|
|
2070
|
-
renderArtistLink: renderArtistLink ?? ((artist) => artist.isSpecialPurpose ? artist.name : /* @__PURE__ */ (0,
|
|
2153
|
+
renderArtistLink: renderArtistLink ?? ((artist) => artist.isSpecialPurpose ? artist.name : /* @__PURE__ */ (0, import_jsx_runtime34.jsx)("button", { type: "button", onClick: () => openArtist(artist.uuid), className: "hover:underline", children: artist.name })),
|
|
2071
2154
|
expanded: controlledArtistExpanded ?? (artistUuid !== null && expandedArtistUuid === artistUuid),
|
|
2072
2155
|
onExpandedChange: (on) => {
|
|
2073
2156
|
if (controlledArtistExpanded === void 0) setExpandedArtistUuid(on ? artistUuid : null);
|
|
@@ -2105,10 +2188,6 @@ function GenreTreeView({
|
|
|
2105
2188
|
const detailExpanded = detailOverlay ? !!detailOverlay.expanded : isExpanded;
|
|
2106
2189
|
const onDetailExpandedChange = detailOverlay ? detailOverlay.onExpandedChange : changeExpanded;
|
|
2107
2190
|
const infoPanelCuration = {
|
|
2108
|
-
editMode,
|
|
2109
|
-
onEditModeChange,
|
|
2110
|
-
renderTitleEditor,
|
|
2111
|
-
renderParentsEditor,
|
|
2112
2191
|
renderDangerZone,
|
|
2113
2192
|
expanded: placement === "regions" ? isExpanded : expanded,
|
|
2114
2193
|
onExpandedChange: placement === "regions" ? changeExpanded : onExpandedChange,
|
|
@@ -2130,15 +2209,15 @@ function GenreTreeView({
|
|
|
2130
2209
|
label: "Artists",
|
|
2131
2210
|
items: artistSearchResult.artists.map((artist) => ({
|
|
2132
2211
|
key: artist.uuid,
|
|
2133
|
-
content: /* @__PURE__ */ (0,
|
|
2134
|
-
/* @__PURE__ */ (0,
|
|
2212
|
+
content: /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)(import_jsx_runtime34.Fragment, { children: [
|
|
2213
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsxs)("span", { className: "block truncate font-medium", children: [
|
|
2135
2214
|
artist.name,
|
|
2136
|
-
artist.disambiguation && /* @__PURE__ */ (0,
|
|
2215
|
+
artist.disambiguation && /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)("span", { className: "font-normal text-[var(--color-neutral-500)]", children: [
|
|
2137
2216
|
" \xB7 ",
|
|
2138
2217
|
artist.disambiguation
|
|
2139
2218
|
] })
|
|
2140
2219
|
] }),
|
|
2141
|
-
artist.matchedAlias && /* @__PURE__ */ (0,
|
|
2220
|
+
artist.matchedAlias && /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)("span", { className: "block truncate text-xs text-[var(--color-neutral-500)]", children: [
|
|
2142
2221
|
"also known as ",
|
|
2143
2222
|
artist.matchedAlias
|
|
2144
2223
|
] })
|
|
@@ -2148,7 +2227,8 @@ function GenreTreeView({
|
|
|
2148
2227
|
onArtistSelect?.(artist);
|
|
2149
2228
|
}
|
|
2150
2229
|
})),
|
|
2151
|
-
status: artistSearchResult.isError ? "Search failed" : artistSearchResult.settled && artistSearchResult.artists.length === 0 ? "No artists found" : ""
|
|
2230
|
+
status: artistSearchResult.isError ? "Search failed" : artistSearchResult.settled && artistSearchResult.artists.length === 0 ? "No artists found" : "",
|
|
2231
|
+
loading: artistSearchResult.pending
|
|
2152
2232
|
} : void 0;
|
|
2153
2233
|
const handleSelectedNodeChange = (node) => {
|
|
2154
2234
|
selectNode(node);
|
|
@@ -2169,15 +2249,15 @@ function GenreTreeView({
|
|
|
2169
2249
|
(node, { toolbar, ancestors, family }) => {
|
|
2170
2250
|
const genrePlaylist = genrePlaylistByNodeId.get(node.id);
|
|
2171
2251
|
const criteria = genrePlaylist?.criteria;
|
|
2172
|
-
if (!genrePlaylist || !criteria) return { primary: /* @__PURE__ */ (0,
|
|
2252
|
+
if (!genrePlaylist || !criteria) return { primary: /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)(import_jsx_runtime34.Fragment, { children: [
|
|
2173
2253
|
toolbar,
|
|
2174
2254
|
family
|
|
2175
2255
|
] }), aside: ancestors };
|
|
2176
2256
|
const genreUuid = criteria.uuid;
|
|
2177
2257
|
return {
|
|
2178
|
-
primary: /* @__PURE__ */ (0,
|
|
2258
|
+
primary: /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)(import_jsx_runtime34.Fragment, { children: [
|
|
2179
2259
|
toolbar,
|
|
2180
|
-
/* @__PURE__ */ (0,
|
|
2260
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2181
2261
|
GenreNodeActionBand,
|
|
2182
2262
|
{
|
|
2183
2263
|
node,
|
|
@@ -2187,14 +2267,15 @@ function GenreTreeView({
|
|
|
2187
2267
|
onAddChild: readOnly ? void 0 : () => handleGenreCreationAction(criteria),
|
|
2188
2268
|
onRename: readOnly ? void 0 : () => handleGenreRenameAction(criteria),
|
|
2189
2269
|
onChangeParent: readOnly ? void 0 : () => showPopup(
|
|
2190
|
-
/* @__PURE__ */ (0,
|
|
2270
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2191
2271
|
ChangeParentPopup,
|
|
2192
2272
|
{
|
|
2193
2273
|
genrePlaylist: { ...genrePlaylist, criteria },
|
|
2194
2274
|
genrePlaylists: visibleGenrePlaylists,
|
|
2195
2275
|
scope,
|
|
2196
2276
|
getBackendBaseUrl,
|
|
2197
|
-
onClose: hidePopup
|
|
2277
|
+
onClose: hidePopup,
|
|
2278
|
+
onParentChanged
|
|
2198
2279
|
}
|
|
2199
2280
|
)
|
|
2200
2281
|
),
|
|
@@ -2202,7 +2283,7 @@ function GenreTreeView({
|
|
|
2202
2283
|
playback
|
|
2203
2284
|
}
|
|
2204
2285
|
),
|
|
2205
|
-
/* @__PURE__ */ (0,
|
|
2286
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2206
2287
|
GenreDetailExtras,
|
|
2207
2288
|
{
|
|
2208
2289
|
family,
|
|
@@ -2234,6 +2315,7 @@ function GenreTreeView({
|
|
|
2234
2315
|
handleGenreRenameAction,
|
|
2235
2316
|
showPopup,
|
|
2236
2317
|
hidePopup,
|
|
2318
|
+
onParentChanged,
|
|
2237
2319
|
visibleGenrePlaylists,
|
|
2238
2320
|
playback,
|
|
2239
2321
|
filterArtist,
|
|
@@ -2251,7 +2333,7 @@ function GenreTreeView({
|
|
|
2251
2333
|
);
|
|
2252
2334
|
const isRotationControlled = controlledAllowWheelRotation !== void 0;
|
|
2253
2335
|
const allowWheelRotation = controlledAllowWheelRotation ?? internalAllowWheelRotation;
|
|
2254
|
-
const detailTab = placement === "regions" && (selectedNodeId || detailOverlay) ? /* @__PURE__ */ (0,
|
|
2336
|
+
const detailTab = placement === "regions" && (selectedNodeId || detailOverlay) ? /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2255
2337
|
PanelEdgeTab,
|
|
2256
2338
|
{
|
|
2257
2339
|
side: "left",
|
|
@@ -2259,8 +2341,8 @@ function GenreTreeView({
|
|
|
2259
2341
|
center: detailExpanded ? null : isCollapsed ? { label: "Show panel", onClick: () => changeCollapsed(false) } : onDetailExpandedChange ? { label: "Extend panel", onClick: () => onDetailExpandedChange(true) } : null
|
|
2260
2342
|
}
|
|
2261
2343
|
) : null;
|
|
2262
|
-
const actions = /* @__PURE__ */ (0,
|
|
2263
|
-
!isLoading && /* @__PURE__ */ (0,
|
|
2344
|
+
const actions = /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)(import_jsx_runtime34.Fragment, { children: [
|
|
2345
|
+
!isLoading && /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2264
2346
|
GenreSearch,
|
|
2265
2347
|
{
|
|
2266
2348
|
genrePlaylists: visibleGenrePlaylists,
|
|
@@ -2272,8 +2354,8 @@ function GenreTreeView({
|
|
|
2272
2354
|
extraResults: artistExtraResults
|
|
2273
2355
|
}
|
|
2274
2356
|
),
|
|
2275
|
-
!isLoading && filterArtist && /* @__PURE__ */ (0,
|
|
2276
|
-
/* @__PURE__ */ (0,
|
|
2357
|
+
!isLoading && filterArtist && /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)("span", { className: "inline-flex items-center overflow-hidden rounded-full bg-[var(--color-neutral-100)] text-sm", children: [
|
|
2358
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2277
2359
|
"button",
|
|
2278
2360
|
{
|
|
2279
2361
|
type: "button",
|
|
@@ -2285,7 +2367,7 @@ function GenreTreeView({
|
|
|
2285
2367
|
children: filterArtist.name
|
|
2286
2368
|
}
|
|
2287
2369
|
),
|
|
2288
|
-
/* @__PURE__ */ (0,
|
|
2370
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2289
2371
|
"button",
|
|
2290
2372
|
{
|
|
2291
2373
|
type: "button",
|
|
@@ -2296,8 +2378,8 @@ function GenreTreeView({
|
|
|
2296
2378
|
}
|
|
2297
2379
|
)
|
|
2298
2380
|
] }),
|
|
2299
|
-
!isLoading && !isControlled && /* @__PURE__ */ (0,
|
|
2300
|
-
|
|
2381
|
+
!isLoading && !isControlled && /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2382
|
+
import_ui17.SegmentedControl,
|
|
2301
2383
|
{
|
|
2302
2384
|
"aria-label": "Tree view mode",
|
|
2303
2385
|
value: viewMode,
|
|
@@ -2310,14 +2392,14 @@ function GenreTreeView({
|
|
|
2310
2392
|
]
|
|
2311
2393
|
}
|
|
2312
2394
|
),
|
|
2313
|
-
!isLoading && showDisplayOptions && /* @__PURE__ */ (0,
|
|
2395
|
+
!isLoading && showDisplayOptions && /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2314
2396
|
"div",
|
|
2315
2397
|
{
|
|
2316
2398
|
className: "flex items-center gap-1",
|
|
2317
2399
|
role: "group",
|
|
2318
2400
|
"aria-label": "Tree display options",
|
|
2319
|
-
children: !isRotationControlled && viewMode !== "stacked" && viewMode !== "outline" && /* @__PURE__ */ (0,
|
|
2320
|
-
|
|
2401
|
+
children: !isRotationControlled && viewMode !== "stacked" && viewMode !== "outline" && /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2402
|
+
import_ui17.Button,
|
|
2321
2403
|
{
|
|
2322
2404
|
variant: allowWheelRotation ? "default" : "outline",
|
|
2323
2405
|
size: "sm",
|
|
@@ -2327,8 +2409,8 @@ function GenreTreeView({
|
|
|
2327
2409
|
)
|
|
2328
2410
|
}
|
|
2329
2411
|
),
|
|
2330
|
-
!isLoading && !readOnly && showAddRoot && /* @__PURE__ */ (0,
|
|
2331
|
-
|
|
2412
|
+
!isLoading && !readOnly && showAddRoot && /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2413
|
+
import_ui17.IconTextButton,
|
|
2332
2414
|
{
|
|
2333
2415
|
icon: import_lucide_react12.Plus,
|
|
2334
2416
|
text: "Add root",
|
|
@@ -2336,33 +2418,33 @@ function GenreTreeView({
|
|
|
2336
2418
|
}
|
|
2337
2419
|
)
|
|
2338
2420
|
] });
|
|
2339
|
-
return /* @__PURE__ */ (0,
|
|
2421
|
+
return /* @__PURE__ */ (0, import_jsx_runtime34.jsxs)(
|
|
2340
2422
|
"div",
|
|
2341
2423
|
{
|
|
2342
2424
|
ref: rootRef,
|
|
2343
2425
|
className: ["genre-tree-view relative flex flex-col h-full", placement === "regions" && REGIONS_CLASS, className].filter(Boolean).join(" "),
|
|
2344
2426
|
children: [
|
|
2345
|
-
/* @__PURE__ */ (0,
|
|
2346
|
-
/* @__PURE__ */ (0,
|
|
2427
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)("style", { children: PREVIOUS_BUTTON_CSS }),
|
|
2428
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2347
2429
|
"div",
|
|
2348
2430
|
{
|
|
2349
2431
|
className: `actions-container absolute z-30 flex items-center gap-2 ${placement === "regions" ? "left-[calc(var(--layout-gutter)+var(--layout-panel-inset))] top-[calc(var(--layout-gutter)+var(--layout-panel-inset))]" : "left-5 top-5"}`,
|
|
2350
2432
|
children: actions
|
|
2351
2433
|
}
|
|
2352
2434
|
),
|
|
2353
|
-
detailTab && /* @__PURE__ */ (0,
|
|
2435
|
+
detailTab && /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2354
2436
|
"div",
|
|
2355
2437
|
{
|
|
2356
2438
|
className: `absolute top-1/2 z-30 -translate-y-1/2 transition-[opacity,visibility] duration-150 ease-out ${isTreeReady ? "opacity-100" : "pointer-events-none invisible opacity-0"} ${detailExpanded ? "right-[calc(var(--layout-center-right)-var(--layout-edge-tab-w))]" : isCollapsed ? "left-0" : "left-[calc(var(--layout-gutter)+var(--layout-left-w))]"}`,
|
|
2357
2439
|
children: detailTab
|
|
2358
2440
|
}
|
|
2359
2441
|
),
|
|
2360
|
-
/* @__PURE__ */ (0,
|
|
2442
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "content-container flex-1 min-h-0 flex flex-row gap-4", children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "tree-view-container flex-1 min-w-0 flex flex-col h-full", children: isLoading ? /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(import_genre_tree_view4.GenreTreeViewSkeleton, { viewMode }) : viewMode === "wheel" ? (
|
|
2361
2443
|
// The info panel's top edge aligns with the tree's; the search bar floats `--layout-panel-inset` below it,
|
|
2362
2444
|
// and the header inset (the bar's height plus that inset) extends the header's fill behind the bar,
|
|
2363
2445
|
// Google Maps style; the 8px bottom padding mirrors the inset above the bar, and the hidden title's height is zeroed.
|
|
2364
2446
|
// The panel's own Zoom in button is hidden: the search bar carries it.
|
|
2365
|
-
/* @__PURE__ */ (0,
|
|
2447
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "tree-container search-overlay relative flex-1 w-full min-h-0 [--gtv-info-panel-header-inset:calc(var(--layout-search-h,2.5rem)+var(--layout-panel-inset,0.5rem))] [&_.gtv-info-panel-header]:pb-2 [&_.gtv-info-panel-title--hidden]:h-0 [&_.gtv-toolbar]:hidden", children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(GenreTreeWheelHandoff, { skeleton: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(import_genre_tree_view4.GenreTreeWheelSkeleton, {}), onRevealedChange: setIsWheelRevealed, children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2366
2448
|
GenrePlaylistTreeWheel,
|
|
2367
2449
|
{
|
|
2368
2450
|
scope,
|
|
@@ -2380,6 +2462,9 @@ function GenreTreeView({
|
|
|
2380
2462
|
readOnly,
|
|
2381
2463
|
allowWheelRotation,
|
|
2382
2464
|
controlsOrientation,
|
|
2465
|
+
sizeMetric: filterArtist ? "songs" : deferredSizeMetric,
|
|
2466
|
+
busy,
|
|
2467
|
+
floatingControlsLeading: filterArtist ? void 0 : /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(SizeMetricToggle, { value: sizeMetric, onChange: changeSizeMetric }),
|
|
2383
2468
|
defaultViewport,
|
|
2384
2469
|
onViewportChange,
|
|
2385
2470
|
...infoPanelCuration
|
|
@@ -2387,7 +2472,7 @@ function GenreTreeView({
|
|
|
2387
2472
|
) }) })
|
|
2388
2473
|
) : viewMode === "pop-core" ? (
|
|
2389
2474
|
// Same as the wheel: the header inset extends its fill behind the floating search bar, Google Maps style.
|
|
2390
|
-
/* @__PURE__ */ (0,
|
|
2475
|
+
/* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "tree-container search-overlay relative flex-1 w-full min-h-0 [--gtv-info-panel-header-inset:calc(var(--layout-search-h,2.5rem)+var(--layout-panel-inset,0.5rem))] [&_.gtv-info-panel-header]:pb-2 [&_.gtv-info-panel-title--hidden]:h-0 [&_.gtv-toolbar]:hidden [&_.gtv-info-panel-zoom-in]:hidden", children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(GenreTreeWheelHandoff, { skeleton: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(import_genre_tree_view4.GenreTreeWheelSkeleton, {}), onRevealedChange: setIsWheelRevealed, children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2391
2476
|
GenrePlaylistTreeWheelRadialPopCore,
|
|
2392
2477
|
{
|
|
2393
2478
|
scope,
|
|
@@ -2405,13 +2490,16 @@ function GenreTreeView({
|
|
|
2405
2490
|
readOnly,
|
|
2406
2491
|
allowWheelRotation,
|
|
2407
2492
|
controlsOrientation,
|
|
2493
|
+
sizeMetric: filterArtist ? "songs" : deferredSizeMetric,
|
|
2494
|
+
busy,
|
|
2495
|
+
floatingControlsLeading: filterArtist ? void 0 : /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(SizeMetricToggle, { value: sizeMetric, onChange: changeSizeMetric }),
|
|
2408
2496
|
defaultViewport,
|
|
2409
2497
|
onViewportChange,
|
|
2410
2498
|
...infoPanelCuration,
|
|
2411
2499
|
...focus
|
|
2412
2500
|
}
|
|
2413
2501
|
) }) })
|
|
2414
|
-
) : viewMode === "outline" ? /* @__PURE__ */ (0,
|
|
2502
|
+
) : viewMode === "outline" ? /* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "tree-container flex-1 min-h-0 w-full overflow-y-auto relative [--gtv-info-panel-header-inset:calc(var(--layout-search-h,2.5rem)+var(--layout-panel-inset,0.5rem)+0.75rem)] [&_.gtv-toolbar]:hidden", children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2415
2503
|
GenrePlaylistTreeWheelRadialPopCore,
|
|
2416
2504
|
{
|
|
2417
2505
|
outline: true,
|
|
@@ -2430,13 +2518,13 @@ function GenreTreeView({
|
|
|
2430
2518
|
readOnly,
|
|
2431
2519
|
...infoPanelCuration
|
|
2432
2520
|
}
|
|
2433
|
-
) }) : /* @__PURE__ */ (0,
|
|
2521
|
+
) }) : /* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "tree-container relative flex flex-col gap-4 w-full pt-14 overflow-x-auto overflow-y-auto text-[var(--color-text)] [&_.gtv-toolbar]:hidden", children: Object.entries(groupedGenrePlaylistsByRoot).map(
|
|
2434
2522
|
([uuid, genrePlaylistTreePerRoot], rootIndex) => {
|
|
2435
|
-
return /* @__PURE__ */ (0,
|
|
2523
|
+
return /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2436
2524
|
"div",
|
|
2437
2525
|
{
|
|
2438
2526
|
className: "tree-per-root-container relative shrink-0 h-[28rem] mt-2 mr-16 p-2 bg-[var(--color-neutral-100)] rounded-lg",
|
|
2439
|
-
children: /* @__PURE__ */ (0,
|
|
2527
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)("div", { className: "graph-container relative z-10 h-full", children: /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
|
|
2440
2528
|
GenrePlaylistTreePerRoot,
|
|
2441
2529
|
{
|
|
2442
2530
|
scope,
|
|
@@ -2480,7 +2568,7 @@ var import_genre_tree19 = require("@behindthemusictree/app-kit/genre-tree");
|
|
|
2480
2568
|
var import_genre_tree20 = require("@behindthemusictree/app-kit/genre-tree");
|
|
2481
2569
|
var import_genre_tree21 = require("@behindthemusictree/app-kit/genre-tree");
|
|
2482
2570
|
var import_track_noun7 = require("@behindthemusictree/app-kit/track-noun");
|
|
2483
|
-
var
|
|
2571
|
+
var import_jsx_runtime35 = require("react/jsx-runtime");
|
|
2484
2572
|
function TrackListSidebar({
|
|
2485
2573
|
className = "",
|
|
2486
2574
|
renderDuration,
|
|
@@ -2505,7 +2593,7 @@ function TrackListSidebar({
|
|
|
2505
2593
|
}, [hasMore, loadMore]);
|
|
2506
2594
|
const { hideTrackListSidebar } = (0, import_genre_tree20.useTrackListSidebarVisibility)();
|
|
2507
2595
|
const positionClasses = layout === "inline" ? "relative w-full flex h-full flex-col" : "fixed right-0 w-[50rem]";
|
|
2508
|
-
return trackList ? /* @__PURE__ */ (0,
|
|
2596
|
+
return trackList ? /* @__PURE__ */ (0, import_jsx_runtime35.jsxs)(
|
|
2509
2597
|
"div",
|
|
2510
2598
|
{
|
|
2511
2599
|
"data-theme": "dark",
|
|
@@ -2515,16 +2603,16 @@ function TrackListSidebar({
|
|
|
2515
2603
|
/* Match player height exactly */
|
|
2516
2604
|
} : void 0,
|
|
2517
2605
|
children: [
|
|
2518
|
-
/* @__PURE__ */ (0,
|
|
2519
|
-
/* @__PURE__ */ (0,
|
|
2520
|
-
/* @__PURE__ */ (0,
|
|
2521
|
-
/* @__PURE__ */ (0,
|
|
2606
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsxs)("div", { className: "header flex h-16 px-4 py-2 text-[var(--color-text)]", children: [
|
|
2607
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsxs)("div", { className: "origin flex text-xl ", children: [
|
|
2608
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsx)("div", { className: "from h-auto flex flex-col justify-center items-center mr-2", children: "From" }),
|
|
2609
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsx)("div", { className: "name-container flex flex-col justify-center items-center text-[var(--color-text)] font-bold pr-2 max-w-[27.5rem]", children: /* @__PURE__ */ (0, import_jsx_runtime35.jsx)("div", { className: "name max-w-full truncate", children: trackList.origin.label }) })
|
|
2522
2610
|
] }),
|
|
2523
|
-
/* @__PURE__ */ (0,
|
|
2611
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsxs)("div", { className: "info flex flex-col justify-center items-center pt-1 mr-2 text-[var(--color-text-muted)]", children: [
|
|
2524
2612
|
trackList.origin.type === import_genre_tree21.TrackListOriginType.GENRE_PLAYLIST ? "\u2022 Genre playlist \u2022 " : trackList.origin.type === import_genre_tree21.TrackListOriginType.ARTIST ? "\u2022 Artist \u2022 " : `\u2022 ${trackNoun.singular} playlist \u2022 `,
|
|
2525
2613
|
`${trackList.total} ${trackList.total > 1 ? trackNoun.plural : trackNoun.singular} \u2022`
|
|
2526
2614
|
] }),
|
|
2527
|
-
/* @__PURE__ */ (0,
|
|
2615
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsx)(
|
|
2528
2616
|
"button",
|
|
2529
2617
|
{
|
|
2530
2618
|
type: "button",
|
|
@@ -2535,12 +2623,12 @@ function TrackListSidebar({
|
|
|
2535
2623
|
}
|
|
2536
2624
|
)
|
|
2537
2625
|
] }),
|
|
2538
|
-
/* @__PURE__ */ (0,
|
|
2626
|
+
/* @__PURE__ */ (0, import_jsx_runtime35.jsxs)(
|
|
2539
2627
|
"ul",
|
|
2540
2628
|
{
|
|
2541
2629
|
className: layout === "inline" ? "track-list flex-1 min-h-0 overflow-auto list-none p-0 m-0" : "track-list overflow-auto max-h-[calc(100vh-63.5px-79px-56px-3.5px)] list-none p-0 m-0",
|
|
2542
2630
|
children: [
|
|
2543
|
-
trackList.tracks.map((track, index) => /* @__PURE__ */ (0,
|
|
2631
|
+
trackList.tracks.map((track, index) => /* @__PURE__ */ (0, import_jsx_runtime35.jsx)("li", { children: /* @__PURE__ */ (0, import_jsx_runtime35.jsx)(
|
|
2544
2632
|
TrackItem,
|
|
2545
2633
|
{
|
|
2546
2634
|
track,
|
|
@@ -2550,7 +2638,7 @@ function TrackListSidebar({
|
|
|
2550
2638
|
renderArtistLink
|
|
2551
2639
|
}
|
|
2552
2640
|
) }, track.uuid)),
|
|
2553
|
-
hasMore && /* @__PURE__ */ (0,
|
|
2641
|
+
hasMore && /* @__PURE__ */ (0, import_jsx_runtime35.jsx)("li", { ref: loadMoreSentinelRef, "aria-hidden": "true", className: "h-px" })
|
|
2554
2642
|
]
|
|
2555
2643
|
}
|
|
2556
2644
|
)
|
|
@@ -2565,7 +2653,7 @@ var import_lucide_react13 = require("lucide-react");
|
|
|
2565
2653
|
var import_tailwind_merge2 = require("tailwind-merge");
|
|
2566
2654
|
var import_player11 = require("@behindthemusictree/app-kit/player");
|
|
2567
2655
|
var import_genre_tree22 = require("@behindthemusictree/app-kit/genre-tree");
|
|
2568
|
-
var
|
|
2656
|
+
var import_jsx_runtime36 = require("react/jsx-runtime");
|
|
2569
2657
|
var PANEL_ID = "player-panel";
|
|
2570
2658
|
var iconButtonClassName = "flex h-6 w-6 shrink-0 items-center justify-center p-0 rounded-md hover:bg-white/10";
|
|
2571
2659
|
var DEFAULT_EXTENDED_WIDTH = "calc(100vw - var(--layout-center-left) - var(--layout-gutter))";
|
|
@@ -2595,7 +2683,7 @@ function PlayerPanel({
|
|
|
2595
2683
|
label: "Extend song list panel",
|
|
2596
2684
|
onClick: () => setIsExtendRequested(true)
|
|
2597
2685
|
};
|
|
2598
|
-
return /* @__PURE__ */ (0,
|
|
2686
|
+
return /* @__PURE__ */ (0, import_jsx_runtime36.jsxs)(
|
|
2599
2687
|
"div",
|
|
2600
2688
|
{
|
|
2601
2689
|
id: PANEL_ID,
|
|
@@ -2608,7 +2696,7 @@ function PlayerPanel({
|
|
|
2608
2696
|
),
|
|
2609
2697
|
style: isExtended ? { width: extendedWidth } : void 0,
|
|
2610
2698
|
children: [
|
|
2611
|
-
/* @__PURE__ */ (0,
|
|
2699
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsx)(
|
|
2612
2700
|
PanelEdgeTab,
|
|
2613
2701
|
{
|
|
2614
2702
|
side: "right",
|
|
@@ -2618,7 +2706,7 @@ function PlayerPanel({
|
|
|
2618
2706
|
className: "absolute right-full top-1/2 -translate-y-1/2"
|
|
2619
2707
|
}
|
|
2620
2708
|
),
|
|
2621
|
-
/* @__PURE__ */ (0,
|
|
2709
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsxs)(
|
|
2622
2710
|
"div",
|
|
2623
2711
|
{
|
|
2624
2712
|
className: (0, import_tailwind_merge2.twMerge)(
|
|
@@ -2626,26 +2714,26 @@ function PlayerPanel({
|
|
|
2626
2714
|
isExtended ? "flex-row" : "flex-col"
|
|
2627
2715
|
),
|
|
2628
2716
|
children: [
|
|
2629
|
-
/* @__PURE__ */ (0,
|
|
2630
|
-
/* @__PURE__ */ (0,
|
|
2631
|
-
/* @__PURE__ */ (0,
|
|
2632
|
-
/* @__PURE__ */ (0,
|
|
2717
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsxs)("div", { className: "flex w-[var(--layout-right-w)] shrink-0 flex-col", children: [
|
|
2718
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsxs)("div", { className: "flex shrink-0 items-center justify-between gap-2 border-b border-zinc-800 p-2", children: [
|
|
2719
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsx)("span", { className: "min-w-0 truncate text-sm font-semibold", children: playerTrackObject?.track?.title }),
|
|
2720
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsx)("div", { className: "flex shrink-0 items-center gap-1", children: /* @__PURE__ */ (0, import_jsx_runtime36.jsx)(
|
|
2633
2721
|
"button",
|
|
2634
2722
|
{
|
|
2635
2723
|
type: "button",
|
|
2636
2724
|
onClick: onClose,
|
|
2637
2725
|
className: iconButtonClassName,
|
|
2638
2726
|
"aria-label": "Close player",
|
|
2639
|
-
children: /* @__PURE__ */ (0,
|
|
2727
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime36.jsx)(import_lucide_react13.X, { size: 16 })
|
|
2640
2728
|
}
|
|
2641
2729
|
) })
|
|
2642
2730
|
] }),
|
|
2643
|
-
/* @__PURE__ */ (0,
|
|
2644
|
-
/* @__PURE__ */ (0,
|
|
2645
|
-
playerTrackObject?.loadError && /* @__PURE__ */ (0,
|
|
2731
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsxs)("div", { className: "relative w-full shrink-0", children: [
|
|
2732
|
+
/* @__PURE__ */ (0, import_jsx_runtime36.jsx)(import_player11.PlayerVideoSurface, { className: "aspect-video w-full bg-black" }),
|
|
2733
|
+
playerTrackObject?.loadError && /* @__PURE__ */ (0, import_jsx_runtime36.jsx)("span", { className: "absolute bottom-2 left-2 right-2 text-xs text-red-400", children: playerTrackObject.loadError })
|
|
2646
2734
|
] })
|
|
2647
2735
|
] }),
|
|
2648
|
-
isTrackListSidebarVisible && /* @__PURE__ */ (0,
|
|
2736
|
+
isTrackListSidebarVisible && /* @__PURE__ */ (0, import_jsx_runtime36.jsx)(
|
|
2649
2737
|
TrackListSidebar,
|
|
2650
2738
|
{
|
|
2651
2739
|
layout: "inline",
|
|
@@ -2668,11 +2756,11 @@ function PlayerPanel({
|
|
|
2668
2756
|
var import_uuid = require("uuid");
|
|
2669
2757
|
var import_ai = require("react-icons/ai");
|
|
2670
2758
|
var import_genre_tree23 = require("@behindthemusictree/app-kit/genre-tree");
|
|
2671
|
-
var
|
|
2759
|
+
var import_jsx_runtime37 = require("react/jsx-runtime");
|
|
2672
2760
|
function Rating({ rating, handleChange }) {
|
|
2673
2761
|
const instanceId = (0, import_uuid.v4)();
|
|
2674
|
-
return /* @__PURE__ */ (0,
|
|
2675
|
-
/* @__PURE__ */ (0,
|
|
2762
|
+
return /* @__PURE__ */ (0, import_jsx_runtime37.jsx)("div", { className: "flex items-center", children: [...Array(6)].map((_, i) => /* @__PURE__ */ (0, import_jsx_runtime37.jsxs)("div", { className: `relative ${i === 0 ? "mr-4" : "mr-1"}`, children: [
|
|
2763
|
+
/* @__PURE__ */ (0, import_jsx_runtime37.jsx)(
|
|
2676
2764
|
"input",
|
|
2677
2765
|
{
|
|
2678
2766
|
id: `star-${instanceId}-${i}`,
|
|
@@ -2684,16 +2772,16 @@ function Rating({ rating, handleChange }) {
|
|
|
2684
2772
|
onChange: handleChange
|
|
2685
2773
|
}
|
|
2686
2774
|
),
|
|
2687
|
-
/* @__PURE__ */ (0,
|
|
2688
|
-
/* @__PURE__ */ (0,
|
|
2775
|
+
/* @__PURE__ */ (0, import_jsx_runtime37.jsx)("label", { htmlFor: `star-${instanceId}-${i}`, className: "cursor-pointer", children: i === 0 ? /* @__PURE__ */ (0, import_jsx_runtime37.jsxs)("div", { className: "flex", children: [
|
|
2776
|
+
/* @__PURE__ */ (0, import_jsx_runtime37.jsx)(
|
|
2689
2777
|
import_ai.AiOutlineStar,
|
|
2690
2778
|
{
|
|
2691
2779
|
className: `w-7 h-7 absolute top-0 left-0 ${rating === import_genre_tree23.FORM_RATING_NULL_VALUE ? "text-[var(--color-accent-rating)]" : "text-[var(--color-text-muted)]"}`
|
|
2692
2780
|
}
|
|
2693
2781
|
),
|
|
2694
|
-
/* @__PURE__ */ (0,
|
|
2782
|
+
/* @__PURE__ */ (0, import_jsx_runtime37.jsx)("span", { className: "flex-grow w-8" }),
|
|
2695
2783
|
" "
|
|
2696
|
-
] }) : /* @__PURE__ */ (0,
|
|
2784
|
+
] }) : /* @__PURE__ */ (0, import_jsx_runtime37.jsx)(
|
|
2697
2785
|
import_ai.AiFillStar,
|
|
2698
2786
|
{
|
|
2699
2787
|
className: `w-7 h-7 absolute top-0 left-0 ${(rating ?? -1) >= i ? "text-[var(--color-accent-rating)]" : "text-[var(--color-text-muted)]"}`
|