@walkthru-earth/objex 1.3.1 → 1.5.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/LICENSE +5 -0
- package/README.md +28 -20
- package/dist/components/browser/FileTreeSidebar.svelte +32 -17
- package/dist/components/layout/AboutSheet.svelte +5 -2
- package/dist/components/layout/ConnectionDialog.svelte +7 -2
- package/dist/components/layout/SettingsSheet.svelte +238 -0
- package/dist/components/layout/SettingsSheet.svelte.d.ts +6 -0
- package/dist/components/layout/Sidebar.svelte +73 -6
- package/dist/components/layout/Sidebar.svelte.d.ts +4 -1
- package/dist/components/layout/StatusBar.svelte +17 -14
- package/dist/components/layout/TabBar.svelte +4 -4
- package/dist/components/ui/context-menu/context-menu-radio-group.svelte.d.ts +1 -1
- package/dist/components/ui/dropdown-menu/dropdown-menu-checkbox-group.svelte.d.ts +1 -1
- package/dist/components/ui/dropdown-menu/dropdown-menu-radio-group.svelte.d.ts +1 -1
- package/dist/components/ui/input/input.svelte.d.ts +1 -1
- package/dist/components/ui/resizable/index.d.ts +1 -1
- package/dist/components/ui/resizable/index.js +2 -2
- package/dist/components/ui/slider/index.d.ts +3 -0
- package/dist/components/ui/slider/index.js +5 -0
- package/dist/components/ui/slider/range-slider.svelte +94 -0
- package/dist/components/ui/slider/range-slider.svelte.d.ts +21 -0
- package/dist/components/ui/slider/slider.svelte +83 -0
- package/dist/components/ui/slider/slider.svelte.d.ts +7 -0
- package/dist/components/viewers/ArchiveViewer.svelte +140 -113
- package/dist/components/viewers/CodeViewer.svelte +45 -48
- package/dist/components/viewers/CodeViewer.svelte.d.ts +1 -1
- package/dist/components/viewers/CogControls.svelte +338 -184
- package/dist/components/viewers/CogControls.svelte.d.ts +33 -10
- package/dist/components/viewers/CogViewer.svelte +269 -116
- package/dist/components/viewers/CopcViewer.svelte +8 -15
- package/dist/components/viewers/DatabaseViewer.svelte +22 -21
- package/dist/components/viewers/FileInfo.svelte +16 -16
- package/dist/components/viewers/FlatGeobufViewer.svelte +16 -46
- package/dist/components/viewers/GeoParquetMapViewer.svelte +11 -9
- package/dist/components/viewers/GeoParquetMapViewer.svelte.d.ts +1 -1
- package/dist/components/viewers/ImageViewer.svelte +12 -14
- package/dist/components/viewers/LoadProgress.svelte +6 -6
- package/dist/components/viewers/MarkdownViewer.svelte +29 -30
- package/dist/components/viewers/MediaViewer.svelte +13 -14
- package/dist/components/viewers/ModelViewer.svelte +18 -21
- package/dist/components/viewers/MultiCogViewer.svelte +474 -106
- package/dist/components/viewers/MultiCogViewer.svelte.d.ts +1 -1
- package/dist/components/viewers/NotebookViewer.svelte +28 -29
- package/dist/components/viewers/PdfViewer.svelte +24 -33
- package/dist/components/viewers/PmtilesViewer.svelte +13 -15
- package/dist/components/viewers/QueryHistoryPanel.svelte +18 -18
- package/dist/components/viewers/RawViewer.svelte +27 -21
- package/dist/components/viewers/StacMapViewer.svelte +6 -13
- package/dist/components/viewers/StacMosaicViewer.svelte +1764 -410
- package/dist/components/viewers/StacMosaicViewer.svelte.d.ts +1 -1
- package/dist/components/viewers/StacTabViewer.svelte +26 -15
- package/dist/components/viewers/StacTabViewer.svelte.d.ts +1 -1
- package/dist/components/viewers/TableGrid.svelte +38 -34
- package/dist/components/viewers/TableStatusBar.svelte +7 -7
- package/dist/components/viewers/TableToolbar.svelte +10 -9
- package/dist/components/viewers/TableViewer.svelte +47 -30
- package/dist/components/viewers/TableViewer.svelte.d.ts +1 -0
- package/dist/components/viewers/ViewerHeader.svelte +18 -0
- package/dist/components/viewers/ViewerHeader.svelte.d.ts +10 -0
- package/dist/components/viewers/ViewerRouter.svelte +16 -8
- package/dist/components/viewers/ViewerStatus.svelte +19 -0
- package/dist/components/viewers/ViewerStatus.svelte.d.ts +7 -0
- package/dist/components/viewers/ZarrMapViewer.svelte +24 -21
- package/dist/components/viewers/ZarrViewer.svelte +98 -65
- package/dist/components/viewers/cog/ChannelPicker.svelte +83 -0
- package/dist/components/viewers/cog/ChannelPicker.svelte.d.ts +13 -0
- package/dist/components/viewers/cog/PixelInspectorPanel.svelte +87 -0
- package/dist/components/viewers/cog/PixelInspectorPanel.svelte.d.ts +17 -0
- package/dist/components/viewers/cog/buildRgbLayer.d.ts +78 -0
- package/dist/components/viewers/cog/buildRgbLayer.js +176 -0
- package/dist/components/viewers/map/AttributeTable.svelte +7 -7
- package/dist/components/viewers/map/MapContainer.svelte +38 -12
- package/dist/components/viewers/pmtiles/PmtilesArchiveView.svelte +109 -83
- package/dist/components/viewers/pmtiles/PmtilesTileInspector.svelte +16 -16
- package/dist/components/viewers/stac/StacDatetimeBar.svelte +175 -0
- package/dist/components/viewers/stac/StacDatetimeBar.svelte.d.ts +10 -0
- package/dist/components/viewers/stac/StacFilterPanel.svelte +243 -0
- package/dist/components/viewers/stac/StacFilterPanel.svelte.d.ts +14 -0
- package/dist/components/viewers/stac/StacItemInspector.svelte +223 -0
- package/dist/components/viewers/stac/StacItemInspector.svelte.d.ts +10 -0
- package/dist/components/viewers/stac/StacItemStrip.svelte +228 -0
- package/dist/components/viewers/stac/StacItemStrip.svelte.d.ts +12 -0
- package/dist/constants.d.ts +6 -0
- package/dist/constants.js +8 -0
- package/dist/file-icons/index.d.ts +1 -1
- package/dist/file-icons/index.js +1 -1
- package/dist/i18n/ar.js +113 -2
- package/dist/i18n/en.js +113 -2
- package/dist/index.d.ts +2 -28
- package/dist/index.js +7 -23
- package/dist/query/engine.d.ts +10 -0
- package/dist/query/source.js +1 -1
- package/dist/query/stac-source-factory.d.ts +65 -0
- package/dist/query/stac-source-factory.js +77 -0
- package/dist/query/stac-source-parquet.d.ts +135 -0
- package/dist/query/stac-source-parquet.js +468 -0
- package/dist/query/wasm.d.ts +8 -0
- package/dist/query/wasm.js +310 -65
- package/dist/storage/presign.js +3 -2
- package/dist/storage/providers.js +7 -6
- package/dist/stores/config.svelte.d.ts +15 -0
- package/dist/stores/config.svelte.js +46 -0
- package/dist/stores/connections.svelte.d.ts +2 -2
- package/dist/stores/connections.svelte.js +1 -2
- package/dist/stores/files.svelte.d.ts +1 -1
- package/dist/stores/files.svelte.js +1 -1
- package/dist/stores/query-history.svelte.js +1 -1
- package/dist/stores/settings.svelte.d.ts +16 -1
- package/dist/stores/settings.svelte.js +104 -48
- package/dist/stores/tabs.svelte.d.ts +3 -0
- package/dist/stores/tabs.svelte.js +17 -0
- package/dist/utils/cog-histogram.d.ts +121 -0
- package/dist/utils/cog-histogram.js +424 -0
- package/dist/utils/cog.d.ts +177 -20
- package/dist/utils/cog.js +361 -76
- package/dist/utils/colormap-sprite.d.ts +0 -9
- package/dist/utils/colormap-sprite.js +0 -21
- package/dist/utils/deck.d.ts +18 -12
- package/dist/utils/deck.js +15 -7
- package/dist/utils/media-query.svelte.d.ts +14 -0
- package/dist/utils/media-query.svelte.js +29 -0
- package/dist/utils/pmtiles-tile.js +2 -2
- package/dist/utils/signed-url-effect.d.ts +7 -0
- package/dist/utils/signed-url-effect.js +19 -0
- package/dist/utils/{url.d.ts → signed-url.d.ts} +15 -1
- package/dist/utils/{url.js → signed-url.js} +32 -10
- package/dist/utils/url-state.d.ts +36 -0
- package/dist/utils/url-state.js +72 -2
- package/dist/utils/zarr-tab.d.ts +1 -2
- package/dist/utils/zarr-tab.js +1 -2
- package/dist/utils/zarr.d.ts +0 -17
- package/dist/utils/zarr.js +1 -45
- package/package.json +55 -84
- package/dist/components/browser/Breadcrumb.svelte +0 -50
- package/dist/components/browser/Breadcrumb.svelte.d.ts +0 -7
- package/dist/components/browser/CreateFolderDialog.svelte +0 -98
- package/dist/components/browser/CreateFolderDialog.svelte.d.ts +0 -6
- package/dist/components/browser/DeleteConfirmDialog.svelte +0 -90
- package/dist/components/browser/DeleteConfirmDialog.svelte.d.ts +0 -8
- package/dist/components/browser/DropZone.svelte +0 -83
- package/dist/components/browser/DropZone.svelte.d.ts +0 -7
- package/dist/components/browser/FileBrowser.svelte +0 -252
- package/dist/components/browser/FileBrowser.svelte.d.ts +0 -3
- package/dist/components/browser/FileRow.svelte +0 -117
- package/dist/components/browser/FileRow.svelte.d.ts +0 -9
- package/dist/components/browser/RenameDialog.svelte +0 -101
- package/dist/components/browser/RenameDialog.svelte.d.ts +0 -8
- package/dist/components/browser/SearchBar.svelte +0 -40
- package/dist/components/browser/SearchBar.svelte.d.ts +0 -6
- package/dist/components/browser/UploadButton.svelte +0 -65
- package/dist/components/browser/UploadButton.svelte.d.ts +0 -3
- package/dist/query/stac-geoparquet.d.ts +0 -31
- package/dist/query/stac-geoparquet.js +0 -136
- package/dist/utils/clipboard.d.ts +0 -13
- package/dist/utils/clipboard.js +0 -38
- package/dist/utils/cloud-url.d.ts +0 -27
- package/dist/utils/cloud-url.js +0 -61
- package/dist/utils/cog-pure.d.ts +0 -25
- package/dist/utils/cog-pure.js +0 -35
- package/dist/utils/column-types.d.ts +0 -5
- package/dist/utils/column-types.js +0 -137
- package/dist/utils/connection-identity.d.ts +0 -51
- package/dist/utils/connection-identity.js +0 -97
- package/dist/utils/error.d.ts +0 -8
- package/dist/utils/error.js +0 -12
- package/dist/utils/evidence-context.d.ts +0 -22
- package/dist/utils/evidence-context.js +0 -56
- package/dist/utils/export.d.ts +0 -22
- package/dist/utils/export.js +0 -76
- package/dist/utils/file-sort.d.ts +0 -20
- package/dist/utils/file-sort.js +0 -41
- package/dist/utils/format.d.ts +0 -24
- package/dist/utils/format.js +0 -78
- package/dist/utils/geoarrow.d.ts +0 -32
- package/dist/utils/geoarrow.js +0 -672
- package/dist/utils/geometry-type.d.ts +0 -52
- package/dist/utils/geometry-type.js +0 -76
- package/dist/utils/hex.d.ts +0 -10
- package/dist/utils/hex.js +0 -27
- package/dist/utils/host-detection.d.ts +0 -23
- package/dist/utils/host-detection.js +0 -95
- package/dist/utils/local-storage.d.ts +0 -16
- package/dist/utils/local-storage.js +0 -37
- package/dist/utils/markdown-sql.d.ts +0 -30
- package/dist/utils/markdown-sql.js +0 -72
- package/dist/utils/notebook.d.ts +0 -59
- package/dist/utils/notebook.js +0 -211
- package/dist/utils/parquet-metadata.d.ts +0 -64
- package/dist/utils/parquet-metadata.js +0 -262
- package/dist/utils/stac-geoparquet.d.ts +0 -90
- package/dist/utils/stac-geoparquet.js +0 -223
- package/dist/utils/stac-hydrate.d.ts +0 -38
- package/dist/utils/stac-hydrate.js +0 -243
- package/dist/utils/stac.d.ts +0 -136
- package/dist/utils/stac.js +0 -176
- package/dist/utils/storage-url.d.ts +0 -90
- package/dist/utils/storage-url.js +0 -568
- package/dist/utils/wkb.d.ts +0 -43
- package/dist/utils/wkb.js +0 -359
|
@@ -4,13 +4,13 @@ import FileTextIcon from '@lucide/svelte/icons/file-text';
|
|
|
4
4
|
import FolderIcon from '@lucide/svelte/icons/folder';
|
|
5
5
|
import GlobeIcon from '@lucide/svelte/icons/globe';
|
|
6
6
|
import InfoIcon from '@lucide/svelte/icons/info';
|
|
7
|
+
import { formatFileSize } from '@walkthru-earth/objex-utils';
|
|
7
8
|
import { Separator } from '../ui/separator/index.js';
|
|
8
9
|
import { getFileTypeInfo } from '../../file-icons/index.js';
|
|
9
10
|
import { t } from '../../i18n/index.svelte.js';
|
|
10
11
|
import { browser } from '../../stores/browser.svelte.js';
|
|
11
12
|
import { files } from '../../stores/files.svelte.js';
|
|
12
13
|
import { tabs } from '../../stores/tabs.svelte.js';
|
|
13
|
-
import { formatFileSize } from '../../utils/format.js';
|
|
14
14
|
import SafeLockToggle from './SafeLockToggle.svelte';
|
|
15
15
|
|
|
16
16
|
let isBrowsingRemote = $derived(browser.activeConnection !== null);
|
|
@@ -32,29 +32,32 @@ let activeFileInfo = $derived(activeTab ? getFileTypeInfo(activeTab.extension) :
|
|
|
32
32
|
{browser.activeConnection.name}
|
|
33
33
|
</span>
|
|
34
34
|
{#if displayPath}
|
|
35
|
-
<span class="text-muted-foreground/50">/</span>
|
|
36
|
-
<span class="max-w-[200px] truncate" title={displayPath}>{displayPath}</span>
|
|
35
|
+
<span class="hidden text-muted-foreground/50 sm:inline">/</span>
|
|
36
|
+
<span class="hidden max-w-[200px] truncate sm:inline" title={displayPath}>{displayPath}</span>
|
|
37
37
|
{/if}
|
|
38
38
|
<Separator orientation="vertical" class="mx-1.5 h-3.5" />
|
|
39
39
|
{:else if displayPath}
|
|
40
|
-
<FolderIcon class="size-3 shrink-0" />
|
|
41
|
-
<span class="max-w-[300px] truncate" title={displayPath}>{displayPath}</span>
|
|
42
|
-
<Separator orientation="vertical" class="mx-1.5 h-3.5" />
|
|
40
|
+
<FolderIcon class="hidden size-3 shrink-0 sm:block" />
|
|
41
|
+
<span class="hidden max-w-[300px] truncate sm:inline" title={displayPath}>{displayPath}</span>
|
|
42
|
+
<Separator orientation="vertical" class="mx-1.5 hidden h-3.5 sm:block" />
|
|
43
43
|
{/if}
|
|
44
44
|
|
|
45
|
-
<!-- Entry count -->
|
|
45
|
+
<!-- Entry count — hidden on mobile -->
|
|
46
46
|
{#if displayCount > 0}
|
|
47
|
-
<FileTextIcon class="size-3 shrink-0" />
|
|
48
|
-
<span
|
|
49
|
-
|
|
47
|
+
<FileTextIcon class="hidden size-3 shrink-0 sm:block" />
|
|
48
|
+
<span class="hidden sm:inline"
|
|
49
|
+
>{displayCount}
|
|
50
|
+
{displayCount === 1 ? t('statusBar.item') : t('statusBar.items')}</span
|
|
51
|
+
>
|
|
52
|
+
<Separator orientation="vertical" class="mx-1.5 hidden h-3.5 sm:block" />
|
|
50
53
|
{/if}
|
|
51
54
|
|
|
52
|
-
<!-- Active file info -->
|
|
55
|
+
<!-- Active file info: type label hidden on mobile, size kept -->
|
|
53
56
|
{#if activeTab && activeFileInfo}
|
|
54
|
-
<InfoIcon class="size-3 shrink-0" />
|
|
55
|
-
<span>{activeFileInfo.label}</span>
|
|
57
|
+
<InfoIcon class="hidden size-3 shrink-0 sm:block" />
|
|
58
|
+
<span class="hidden sm:inline">{activeFileInfo.label}</span>
|
|
56
59
|
{#if activeTab.size}
|
|
57
|
-
<span class="text-muted-foreground/50">·</span>
|
|
60
|
+
<span class="hidden text-muted-foreground/50 sm:inline">·</span>
|
|
58
61
|
<span>{formatFileSize(activeTab.size)}</span>
|
|
59
62
|
{/if}
|
|
60
63
|
<Separator orientation="vertical" class="mx-1.5 h-3.5" />
|
|
@@ -2,14 +2,14 @@
|
|
|
2
2
|
import DatabaseIcon from '@lucide/svelte/icons/database';
|
|
3
3
|
import FileTextIcon from '@lucide/svelte/icons/file-text';
|
|
4
4
|
import XIcon from '@lucide/svelte/icons/x';
|
|
5
|
+
import { copyToClipboard } from '@walkthru-earth/objex-utils';
|
|
5
6
|
import type { Snippet } from 'svelte';
|
|
6
7
|
import { Button } from '../ui/button/index.js';
|
|
7
8
|
import * as ContextMenu from '../ui/context-menu/index.js';
|
|
8
9
|
import { ScrollArea } from '../ui/scroll-area/index.js';
|
|
9
10
|
import { t } from '../../i18n/index.svelte.js';
|
|
10
11
|
import { tabs } from '../../stores/tabs.svelte.js';
|
|
11
|
-
import {
|
|
12
|
-
import { buildHttpsUrl, buildStorageUrl } from '../../utils/url.js';
|
|
12
|
+
import { buildHttpsUrl, buildStorageUrl } from '../../utils/signed-url.js';
|
|
13
13
|
|
|
14
14
|
let { leading }: { leading?: Snippet } = $props();
|
|
15
15
|
|
|
@@ -60,8 +60,8 @@ async function handleCopy(type: 'https' | 's3', tab: (typeof tabs.items)[0]) {
|
|
|
60
60
|
<Button
|
|
61
61
|
variant="ghost"
|
|
62
62
|
size="icon-sm"
|
|
63
|
-
class="ms-1 size-5 opacity-
|
|
64
|
-
{isActive ? 'opacity-60' : ''}"
|
|
63
|
+
class="ms-1 size-5 opacity-100 transition-opacity sm:opacity-0 sm:group-hover:opacity-100
|
|
64
|
+
{isActive ? 'sm:opacity-60' : ''}"
|
|
65
65
|
onclick={(e: MouseEvent) => handleClose(e, tab.id)}
|
|
66
66
|
aria-label={t('tabBar.closeTab', { name: tab.name })}
|
|
67
67
|
>
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { ContextMenu as ContextMenuPrimitive } from 'bits-ui';
|
|
2
|
-
declare const ContextMenuRadioGroup: import("svelte").Component<ContextMenuPrimitive.RadioGroupProps, {}, "
|
|
2
|
+
declare const ContextMenuRadioGroup: import("svelte").Component<ContextMenuPrimitive.RadioGroupProps, {}, "ref" | "value">;
|
|
3
3
|
type ContextMenuRadioGroup = ReturnType<typeof ContextMenuRadioGroup>;
|
|
4
4
|
export default ContextMenuRadioGroup;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { DropdownMenu as DropdownMenuPrimitive } from 'bits-ui';
|
|
2
|
-
declare const DropdownMenuCheckboxGroup: import("svelte").Component<DropdownMenuPrimitive.CheckboxGroupProps, {}, "
|
|
2
|
+
declare const DropdownMenuCheckboxGroup: import("svelte").Component<DropdownMenuPrimitive.CheckboxGroupProps, {}, "ref" | "value">;
|
|
3
3
|
type DropdownMenuCheckboxGroup = ReturnType<typeof DropdownMenuCheckboxGroup>;
|
|
4
4
|
export default DropdownMenuCheckboxGroup;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { DropdownMenu as DropdownMenuPrimitive } from 'bits-ui';
|
|
2
|
-
declare const DropdownMenuRadioGroup: import("svelte").Component<DropdownMenuPrimitive.RadioGroupProps, {}, "
|
|
2
|
+
declare const DropdownMenuRadioGroup: import("svelte").Component<DropdownMenuPrimitive.RadioGroupProps, {}, "ref" | "value">;
|
|
3
3
|
type DropdownMenuRadioGroup = ReturnType<typeof DropdownMenuRadioGroup>;
|
|
4
4
|
export default DropdownMenuRadioGroup;
|
|
@@ -8,6 +8,6 @@ type Props = WithElementRef<Omit<HTMLInputAttributes, 'type'> & ({
|
|
|
8
8
|
type?: InputType;
|
|
9
9
|
files?: undefined;
|
|
10
10
|
})>;
|
|
11
|
-
declare const Input: import("svelte").Component<Props, {}, "
|
|
11
|
+
declare const Input: import("svelte").Component<Props, {}, "ref" | "value" | "files">;
|
|
12
12
|
type Input = ReturnType<typeof Input>;
|
|
13
13
|
export default Input;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { Pane } from 'paneforge';
|
|
2
2
|
import Handle from './resizable-handle.svelte';
|
|
3
3
|
import PaneGroup from './resizable-pane-group.svelte';
|
|
4
|
-
export {
|
|
4
|
+
export { Handle, Handle as ResizableHandle, Pane as ResizablePane, PaneGroup, PaneGroup as ResizablePaneGroup };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Pane } from 'paneforge';
|
|
2
2
|
import Handle from './resizable-handle.svelte';
|
|
3
3
|
import PaneGroup from './resizable-pane-group.svelte';
|
|
4
|
-
export {
|
|
4
|
+
export { Handle, Handle as ResizableHandle, Pane as ResizablePane, PaneGroup,
|
|
5
5
|
//
|
|
6
|
-
PaneGroup as ResizablePaneGroup
|
|
6
|
+
PaneGroup as ResizablePaneGroup };
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { cn } from '../../../utils.js';
|
|
3
|
+
import Slider from './slider.svelte';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Dual-thumb numeric range slider with optional histogram bars rendered
|
|
7
|
+
* behind the track and a min/max label row beneath. Composes the shadcn
|
|
8
|
+
* `Slider` primitive (bits-ui) so pointer, keyboard, RTL, and a11y
|
|
9
|
+
* behavior come from the primitive instead of being reimplemented.
|
|
10
|
+
*
|
|
11
|
+
* Used by:
|
|
12
|
+
* - StacDatetimeBar / StacFilterPanel (datetime + numeric facets, with histogram)
|
|
13
|
+
* - CogControls (rescale min/max, no histogram, paired number inputs)
|
|
14
|
+
*/
|
|
15
|
+
let {
|
|
16
|
+
value = $bindable<[number, number]>([0, 1]),
|
|
17
|
+
min,
|
|
18
|
+
max,
|
|
19
|
+
step = 1,
|
|
20
|
+
histogram,
|
|
21
|
+
formatLabel,
|
|
22
|
+
loLabel,
|
|
23
|
+
hiLabel,
|
|
24
|
+
class: className,
|
|
25
|
+
disabled = false,
|
|
26
|
+
onValueChange,
|
|
27
|
+
onValueCommit
|
|
28
|
+
}: {
|
|
29
|
+
value?: [number, number];
|
|
30
|
+
min: number;
|
|
31
|
+
max: number;
|
|
32
|
+
step?: number;
|
|
33
|
+
/** Optional bin counts to draw behind the track. */
|
|
34
|
+
histogram?: readonly number[] | null;
|
|
35
|
+
/** Formatter for the default min/max label row. Omit to hide labels. */
|
|
36
|
+
formatLabel?: (n: number) => string;
|
|
37
|
+
/** Override the lower label (takes precedence over `formatLabel(value[0])`). */
|
|
38
|
+
loLabel?: string;
|
|
39
|
+
/** Override the upper label (takes precedence over `formatLabel(value[1])`). */
|
|
40
|
+
hiLabel?: string;
|
|
41
|
+
class?: string;
|
|
42
|
+
disabled?: boolean;
|
|
43
|
+
onValueChange?: (next: [number, number]) => void;
|
|
44
|
+
onValueCommit?: (next: [number, number]) => void;
|
|
45
|
+
} = $props();
|
|
46
|
+
|
|
47
|
+
const histMax = $derived(histogram?.length ? Math.max(1, ...histogram) : 1);
|
|
48
|
+
const showLabels = $derived(Boolean(formatLabel) || loLabel != null || hiLabel != null);
|
|
49
|
+
|
|
50
|
+
function emitChange(next: number[]): void {
|
|
51
|
+
if (next.length >= 2) onValueChange?.([next[0], next[1]]);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
function emitCommit(next: number[]): void {
|
|
55
|
+
if (next.length >= 2) onValueCommit?.([next[0], next[1]]);
|
|
56
|
+
}
|
|
57
|
+
</script>
|
|
58
|
+
|
|
59
|
+
<div class={cn('flex flex-col gap-1.5', className)}>
|
|
60
|
+
<div class="relative px-2">
|
|
61
|
+
{#if histogram && histogram.length > 0}
|
|
62
|
+
<div
|
|
63
|
+
class="pointer-events-none absolute inset-x-2 top-0 flex h-6 items-end gap-px"
|
|
64
|
+
aria-hidden="true"
|
|
65
|
+
>
|
|
66
|
+
{#each histogram as count, i (i)}
|
|
67
|
+
<div
|
|
68
|
+
class="bg-muted-foreground/30 flex-1 rounded-sm"
|
|
69
|
+
style="height: {Math.max(2, (count / histMax) * 100)}%"
|
|
70
|
+
></div>
|
|
71
|
+
{/each}
|
|
72
|
+
</div>
|
|
73
|
+
{/if}
|
|
74
|
+
<Slider
|
|
75
|
+
type="multiple"
|
|
76
|
+
bind:value={value as never}
|
|
77
|
+
{min}
|
|
78
|
+
{max}
|
|
79
|
+
{step}
|
|
80
|
+
{disabled}
|
|
81
|
+
onValueChange={emitChange}
|
|
82
|
+
onValueCommit={emitCommit}
|
|
83
|
+
class={cn(histogram && histogram.length > 0 && 'mt-7')}
|
|
84
|
+
/>
|
|
85
|
+
</div>
|
|
86
|
+
{#if showLabels}
|
|
87
|
+
<div
|
|
88
|
+
class="text-muted-foreground flex items-center justify-between px-2 text-[10px] tabular-nums"
|
|
89
|
+
>
|
|
90
|
+
<span>{loLabel ?? (formatLabel ? formatLabel(value[0]) : '')}</span>
|
|
91
|
+
<span>{hiLabel ?? (formatLabel ? formatLabel(value[1]) : '')}</span>
|
|
92
|
+
</div>
|
|
93
|
+
{/if}
|
|
94
|
+
</div>
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
type $$ComponentProps = {
|
|
2
|
+
value?: [number, number];
|
|
3
|
+
min: number;
|
|
4
|
+
max: number;
|
|
5
|
+
step?: number;
|
|
6
|
+
/** Optional bin counts to draw behind the track. */
|
|
7
|
+
histogram?: readonly number[] | null;
|
|
8
|
+
/** Formatter for the default min/max label row. Omit to hide labels. */
|
|
9
|
+
formatLabel?: (n: number) => string;
|
|
10
|
+
/** Override the lower label (takes precedence over `formatLabel(value[0])`). */
|
|
11
|
+
loLabel?: string;
|
|
12
|
+
/** Override the upper label (takes precedence over `formatLabel(value[1])`). */
|
|
13
|
+
hiLabel?: string;
|
|
14
|
+
class?: string;
|
|
15
|
+
disabled?: boolean;
|
|
16
|
+
onValueChange?: (next: [number, number]) => void;
|
|
17
|
+
onValueCommit?: (next: [number, number]) => void;
|
|
18
|
+
};
|
|
19
|
+
declare const RangeSlider: import("svelte").Component<$$ComponentProps, {}, "value">;
|
|
20
|
+
type RangeSlider = ReturnType<typeof RangeSlider>;
|
|
21
|
+
export default RangeSlider;
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
<script lang="ts" module>
|
|
2
|
+
import { Slider as SliderPrimitive, type WithoutChildrenOrChild } from 'bits-ui';
|
|
3
|
+
|
|
4
|
+
export type SliderProps = WithoutChildrenOrChild<SliderPrimitive.RootProps> & {
|
|
5
|
+
class?: string;
|
|
6
|
+
};
|
|
7
|
+
</script>
|
|
8
|
+
|
|
9
|
+
<script lang="ts">
|
|
10
|
+
import { cn } from '../../../utils.js';
|
|
11
|
+
|
|
12
|
+
let {
|
|
13
|
+
ref = $bindable(null),
|
|
14
|
+
value = $bindable(),
|
|
15
|
+
class: className,
|
|
16
|
+
type,
|
|
17
|
+
...restProps
|
|
18
|
+
}: SliderProps = $props();
|
|
19
|
+
</script>
|
|
20
|
+
|
|
21
|
+
{#if type === 'single'}
|
|
22
|
+
<SliderPrimitive.Root
|
|
23
|
+
bind:ref
|
|
24
|
+
bind:value={value as never}
|
|
25
|
+
type="single"
|
|
26
|
+
data-slot="slider"
|
|
27
|
+
class={cn(
|
|
28
|
+
'relative flex w-full touch-none select-none items-center data-[orientation=vertical]:h-full data-[orientation=vertical]:min-h-44 data-[orientation=vertical]:w-auto data-[orientation=vertical]:flex-col data-[disabled]:opacity-50',
|
|
29
|
+
className
|
|
30
|
+
)}
|
|
31
|
+
{...(restProps as Record<string, unknown>)}
|
|
32
|
+
>
|
|
33
|
+
{#snippet children({ thumbs })}
|
|
34
|
+
<span
|
|
35
|
+
data-slot="slider-track"
|
|
36
|
+
class="bg-muted relative grow overflow-hidden rounded-full data-[orientation=horizontal]:h-1.5 data-[orientation=horizontal]:w-full data-[orientation=vertical]:h-full data-[orientation=vertical]:w-1.5"
|
|
37
|
+
>
|
|
38
|
+
<SliderPrimitive.Range
|
|
39
|
+
data-slot="slider-range"
|
|
40
|
+
class="bg-primary absolute data-[orientation=horizontal]:h-full data-[orientation=vertical]:w-full"
|
|
41
|
+
/>
|
|
42
|
+
</span>
|
|
43
|
+
{#each thumbs as index (index)}
|
|
44
|
+
<SliderPrimitive.Thumb
|
|
45
|
+
{index}
|
|
46
|
+
data-slot="slider-thumb"
|
|
47
|
+
class="border-primary bg-background ring-ring/50 block size-4 shrink-0 cursor-pointer rounded-full border-2 shadow-sm transition-[color,box-shadow] hover:ring-4 focus-visible:ring-4 focus-visible:outline-none disabled:pointer-events-none disabled:opacity-50"
|
|
48
|
+
/>
|
|
49
|
+
{/each}
|
|
50
|
+
{/snippet}
|
|
51
|
+
</SliderPrimitive.Root>
|
|
52
|
+
{:else}
|
|
53
|
+
<SliderPrimitive.Root
|
|
54
|
+
bind:ref
|
|
55
|
+
bind:value={value as never}
|
|
56
|
+
type="multiple"
|
|
57
|
+
data-slot="slider"
|
|
58
|
+
class={cn(
|
|
59
|
+
'relative flex w-full touch-none select-none items-center data-[orientation=vertical]:h-full data-[orientation=vertical]:min-h-44 data-[orientation=vertical]:w-auto data-[orientation=vertical]:flex-col data-[disabled]:opacity-50',
|
|
60
|
+
className
|
|
61
|
+
)}
|
|
62
|
+
{...(restProps as Record<string, unknown>)}
|
|
63
|
+
>
|
|
64
|
+
{#snippet children({ thumbs })}
|
|
65
|
+
<span
|
|
66
|
+
data-slot="slider-track"
|
|
67
|
+
class="bg-muted relative grow overflow-hidden rounded-full data-[orientation=horizontal]:h-1.5 data-[orientation=horizontal]:w-full data-[orientation=vertical]:h-full data-[orientation=vertical]:w-1.5"
|
|
68
|
+
>
|
|
69
|
+
<SliderPrimitive.Range
|
|
70
|
+
data-slot="slider-range"
|
|
71
|
+
class="bg-primary absolute data-[orientation=horizontal]:h-full data-[orientation=vertical]:w-full"
|
|
72
|
+
/>
|
|
73
|
+
</span>
|
|
74
|
+
{#each thumbs as index (index)}
|
|
75
|
+
<SliderPrimitive.Thumb
|
|
76
|
+
{index}
|
|
77
|
+
data-slot="slider-thumb"
|
|
78
|
+
class="border-primary bg-background ring-ring/50 block size-4 shrink-0 cursor-pointer rounded-full border-2 shadow-sm transition-[color,box-shadow] hover:ring-4 focus-visible:ring-4 focus-visible:outline-none disabled:pointer-events-none disabled:opacity-50"
|
|
79
|
+
/>
|
|
80
|
+
{/each}
|
|
81
|
+
{/snippet}
|
|
82
|
+
</SliderPrimitive.Root>
|
|
83
|
+
{/if}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { Slider as SliderPrimitive, type WithoutChildrenOrChild } from 'bits-ui';
|
|
2
|
+
export type SliderProps = WithoutChildrenOrChild<SliderPrimitive.RootProps> & {
|
|
3
|
+
class?: string;
|
|
4
|
+
};
|
|
5
|
+
declare const Slider: import("svelte").Component<SliderProps, {}, "ref" | "value">;
|
|
6
|
+
type Slider = ReturnType<typeof Slider>;
|
|
7
|
+
export default Slider;
|