width / 3 }}
on:swipeStart={onSwipeStart}
diff --git a/src/lib/util/functions.test.ts b/src/lib/util/functions.test.ts
new file mode 100644
index 0000000..a4e0028
--- /dev/null
+++ b/src/lib/util/functions.test.ts
@@ -0,0 +1,62 @@
+import { test, expect } from "vitest";
+import { arrMoveMulti } from "./functions";
+
+const ARR = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
+test.each([
+ {
+ name: "single fwd",
+ positions: [1],
+ target: 3,
+ result: [0, 2, 1, 3, 4, 5, 6, 7, 8, 9],
+ offset: -1,
+ },
+ {
+ name: "range fwd",
+ positions: [1, 2, 3],
+ target: 7,
+ result: [0, 4, 5, 6, 1, 2, 3, 7, 8, 9],
+ offset: -3,
+ },
+ {
+ name: "range+single fwd",
+ positions: [1, 2, 3, 7],
+ target: 9,
+ result: [0, 4, 5, 6, 8, 1, 2, 3, 7, 9],
+ offset: -4,
+ },
+ {
+ name: "single bck",
+ positions: [8],
+ target: 1,
+ result: [0, 8, 1, 2, 3, 4, 5, 6, 7, 9],
+ offset: 0,
+ },
+ {
+ name: "range bck",
+ positions: [6, 7, 8],
+ target: 1,
+ result: [0, 6, 7, 8, 1, 2, 3, 4, 5, 9],
+ offset: 0,
+ },
+ {
+ name: "range+single bck",
+ positions: [8, 3, 6, 7],
+ target: 1,
+ result: [0, 3, 6, 7, 8, 1, 2, 4, 5, 9],
+ offset: 0,
+ },
+ {
+ name: "range inside", // no items get moved
+ positions: [2, 3, 4, 5],
+ target: 4,
+ result: ARR,
+ offset: -2,
+ },
+])("arrMoveMulti $name", ({ positions, target, result, offset }) => {
+ const arr = [...ARR];
+
+ const o = arrMoveMulti(arr, positions, target);
+
+ expect(arr).toStrictEqual(result);
+ expect(o).toBe(offset);
+});
diff --git a/src/lib/util/functions.ts b/src/lib/util/functions.ts
index 877a336..20a309c 100644
--- a/src/lib/util/functions.ts
+++ b/src/lib/util/functions.ts
@@ -236,8 +236,12 @@ export function arrMove
(arr: T[], oldIndex: number, newIndex: number) {
arr.splice(newIndex > oldIndex ? newIndex - 1 : newIndex, 0, ...items);
}
-export function arrMoveMulti(arr: T[], positions: number[], target: number) {
- positions.sort();
+/** Move a list of items in an array to the target position.
+ *
+ * Returns the offset of the move operation
+ * (the number of positions the items were shifted to the right) */
+export function arrMoveMulti(arr: T[], positions: number[], target: number): number {
+ positions.sort((a, b) => a - b);
const toInsert = [];
let offset = 0;
@@ -247,33 +251,8 @@ export function arrMoveMulti(arr: T[], positions: number[], target: number) {
}
toInsert.reverse();
arr.splice(target + offset, 0, ...toInsert);
-}
-export function arrMoveMulti2(
- arr: T[],
- positions: number[],
- target: number
-): { array: T[]; offset: number } {
- const a1 = [],
- spliced = [];
- const pset = new Set(positions);
-
- let offset = 0;
-
- for (let i = positions.length - 1; i >= 0; i--) {
- if (target > positions[i]) offset--;
- }
-
- for (let i = 0; i < arr.length; i++) {
- if (pset.has(i)) {
- spliced.push(arr[i]);
- } else {
- a1.push(arr[i]);
- }
- }
-
- a1.splice(target + offset, 0, ...spliced);
- return { array: a1, offset };
+ return offset;
}
export function setCookie(cName: string, cValue: string, expDays: number) {
diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte
index 97c5a2a..ed9ab96 100644
--- a/src/routes/+layout.svelte
+++ b/src/routes/+layout.svelte
@@ -25,12 +25,13 @@
headerColor,
} from "$lib/stores/layout";
import { clamp, getEventCoords } from "$lib/util/functions";
- import { WIDTH_SMALL } from "$lib/util/constants";
+ import { WIDTH_PHONE, WIDTH_SMALL } from "$lib/util/constants";
- import Menubar from "$lib/components/nav/Navbar.svelte";
+ import Navbar from "$lib/components/nav/Navbar.svelte";
import Playerbar from "$lib/components/player/Playerbar.svelte";
import DummyText from "$lib/components/ui/DummyText.svelte";
import NavbarMobile from "$lib/components/nav/NavbarMobile.svelte";
+ import NavbarMobileLandscape from "$lib/components/nav/NavbarMobileLandscape.svelte";
import PlayerbarMobile from "$lib/components/player/PlayerbarMobile.svelte";
import FixedHeader from "$lib/components/header/FixedHeader.svelte";
@@ -53,8 +54,10 @@
let queuebarElm: HTMLElement;
let queuebarResizing = false;
+ let mobileLandscape = false;
+ $: mobileLandscape = $screenHeight < WIDTH_PHONE && $screenWidth > WIDTH_PHONE;
let showNavbar = false;
- $: showNavbar = $screenWidth >= WIDTH_SMALL;
+ $: showNavbar = $screenWidth >= WIDTH_SMALL && !mobileLandscape;
let showQueue = false;
$: showQueue = showNavbar && $clientState.showQueue;
@@ -168,7 +171,8 @@
-
+
+
+ {:else if mobileLandscape}
+
{/if}
{#if showQueue}
@@ -214,15 +222,15 @@
{/if}
- {#if !showNavbar}
-
+ {#if !showNavbar && !mobileLandscape}
+
{/if}
{/if}
@@ -242,6 +250,10 @@
"main-content" calc(100vh - 3rem)
"player" 3rem / 1fr;
}
+
+ &.mobile-landscape {
+ grid-template: "main-content" 100vh;
+ }
}
#main-content {
@@ -253,6 +265,10 @@
);
}
+ .mobile-landscape > #main-content {
+ grid-template: "sidebar main" 1fr/10rem 1fr;
+ }
+
main {
grid-area: main;
diff --git a/src/routes/playlist/[id]/+page.svelte b/src/routes/playlist/[id]/+page.svelte
index d6b9ff8..58a578b 100644
--- a/src/routes/playlist/[id]/+page.svelte
+++ b/src/routes/playlist/[id]/+page.svelte
@@ -3,7 +3,7 @@
import type { PageData } from "./$types";
import { searchTerm } from "$lib/stores/layout";
- import { userLink, arrMoveMulti, arrMoveMulti2 } from "$lib/util/functions";
+ import { userLink } from "$lib/util/functions";
import { ListView, type MoveData } from "$lib/util/types";
import { testPlaylist } from "$lib/util/testdata";
// import testPlaylist from "$lib/util/testdata/playlist_5K_conv.json";