Skip to content

Commit

Permalink
Merge pull request #28 from Joery-M/16-sl-ui-make-panels-generic-and-…
Browse files Browse the repository at this point in the history
…configurable

16 sl UI make panels generic and configurable
  • Loading branch information
Joery-M authored May 5, 2024
2 parents 9a1ae7c + 3e5443c commit cea51ee
Show file tree
Hide file tree
Showing 23 changed files with 620 additions and 328 deletions.
8 changes: 4 additions & 4 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,10 +28,10 @@
],
"devDependencies": {
"@vitejs/plugin-vue": "^5.0.4",
"@vitest/browser": "^1.5.3",
"@vitest/ui": "^1.5.3",
"vite": "^5.2.10",
"vitest": "^1.5.3",
"@vitest/browser": "^1.6.0",
"@vitest/ui": "^1.6.0",
"vite": "^5.2.11",
"vitest": "^1.6.0",
"vue": "^3.4.26"
}
}
10 changes: 5 additions & 5 deletions packages/darkroom/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,14 +40,14 @@
},
"devDependencies": {
"@types/path-browserify": "^1.0.2",
"@vitest/browser": "^1.5.3",
"@vitest/ui": "^1.5.3",
"@vitest/browser": "^1.6.0",
"@vitest/ui": "^1.6.0",
"playwright": "^1.43.1",
"rimraf": "^5.0.5",
"typescript": "^5.4.5",
"vite": "^5.2.10",
"vite-plugin-dts": "^3.9.0",
"vitest": "^1.5.3"
"vite": "^5.2.11",
"vite-plugin-dts": "^3.9.1",
"vitest": "^1.6.0"
},
"optionalDependencies": {
"@codemirror/lang-javascript": "^6.2.2",
Expand Down
9 changes: 3 additions & 6 deletions packages/safelight/package.json
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
{
"name": "safelight",
"name": "@safelight/safelight",
"version": "1.0.0",
"description": "A extensible, browser based, video editor",
"private": true,
Expand Down Expand Up @@ -28,11 +28,9 @@
"@vueuse/integrations": "^10.9.0",
"@vueuse/math": "^10.9.0",
"@vueuse/rxjs": "^10.9.0",
"change-case": "^5.4.4",
"dexie": "^3.2.7",
"fuzzysearch": "^1.0.3",
"hash-wasm": "^4.11.0",
"lodash": "^4.17.21",
"luxon": "^3.4.4",
"mime-matcher": "^1.0.5",
"monaco-editor": "^0.46.0",
Expand All @@ -46,7 +44,6 @@
},
"devDependencies": {
"@babel/types": "^7.24.5",
"@iconify-json/ph": "^1.1.12",
"@tsconfig/node20": "^20.1.4",
"@types/dom-webcodecs": "^0.1.11",
"@types/fuzzysearch": "^1.0.2",
Expand All @@ -73,14 +70,14 @@
"strip-ansi": "^7.1.0",
"tailwindcss": "^3.4.3",
"ts-node-dev": "^2.0.0",
"tsx": "^4.8.2",
"tsx": "^4.9.1",
"typescript": "^5.4.5",
"typescript-eslint": "^7.8.0",
"unplugin-auto-import": "^0.17.5",
"unplugin-turbo-console": "^1.8.6",
"unplugin-vue-components": "^0.26.0",
"unplugin-vue-router": "^0.8.6",
"vite": "^5.2.10",
"vite": "^5.2.11",
"vite-plugin-mkcert": "^1.17.5",
"vue-tsc": "^2.0.16"
}
Expand Down
21 changes: 5 additions & 16 deletions packages/safelight/src/components/Editor/Library/Library.vue
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
<template>
<DataView
:value="sortedAndFiltered"
scrollable
scroll-height="400px"
class="flex h-full flex-col"
data-key="id"
:pt="{
header: {
class: 'p-1'
},
content: {
style: 'flex: 1;'
style: 'flex-shrink: 1; min-height: 0;'
},
emptyMessage: {
style: 'height: 100%;'
Expand Down Expand Up @@ -59,24 +57,17 @@
</template>
<template #list="{ items }: { items: Media[] }">
<div
class="grid-nogutter grid h-full select-none"
class="grid-nogutter grid h-full select-none overflow-y-auto"
role="grid"
style="
grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
grid-template-rows: min-content;
"
@dblclick.self="fileDialogOpenDblClick"
>
<div
v-for="item in items"
:key="item.id"
role="gridcell"
class="border-round m-1 flex min-h-32 select-text flex-col rounded-md border-solid border-white/10"
style="border-width: 1px"
:aria-label="item.name.value"
>
<template v-for="item in items" :key="item.id">
<LibraryItem :item="item" />
</div>
</template>
</div>
</template>
<template #empty>
Expand Down Expand Up @@ -173,8 +164,6 @@ function sortAndFilter() {
return item1.duration.value - item2.duration.value;
case 'File type':
return collator.compare(ext1, ext2);
case 'Media type':
return collator.compare(item1.type.toString(), item1.type.toString());
default:
return collator.compare(item1.name.value, item2.name.value);
}
Expand All @@ -189,5 +178,5 @@ function fileDialogOpenDblClick(event: MouseEvent) {
fileDialog.open();
}
type sortOptions = 'Name' | 'Duration' | 'File type' | 'Media type';
type sortOptions = 'Name' | 'Duration' | 'File type';
</script>
111 changes: 76 additions & 35 deletions packages/safelight/src/components/Editor/Library/LibraryItem.vue
Original file line number Diff line number Diff line change
@@ -1,40 +1,69 @@
<template>
<div
class="bg-checkerboard flex aspect-video w-full items-center justify-center overflow-clip rounded-t-md"
role="gridcell"
class="border-round m-1 flex min-h-44 select-text flex-col rounded-md border-solid border-white/10"
style="border-width: 1px"
:aria-label="item.name.value"
>
<img
v-if="$props.item.previewImage.value"
class="overflow-none max-h-full max-w-full"
:aria-label="'Preview image for ' + $props.item.name.value"
:src="$props.item.previewImage.value"
/>
<Skeleton
v-else
class="max-h-full max-w-full rounded-none rounded-t-md"
height="100%"
width="100%"
/>
</div>
<div class="flex items-center gap-1 px-1">
<p
v-tooltip.bottom="{ value: $props.item.name.value, showDelay: 500 }"
class="flex-1 overflow-x-hidden overflow-ellipsis whitespace-nowrap text-base"
<div
class="bg-checkerboard relative flex aspect-video w-full items-center justify-center overflow-clip rounded-t-md"
>
{{ $props.item.name.value }}
</p>
<Button
title="Options"
text
rounded
severity="secondary"
aria-haspopup="true"
aria-controls="library_item_menu"
@click="overlay?.show"
>
<template #icon>
<PhDotsThreeVertical size="20" />
</template>
</Button>
<img
v-if="item.previewImage.value"
class="overflow-none max-h-full max-w-full"
:aria-label="'Preview image for ' + item.name.value"
:src="item.previewImage.value"
/>
<Skeleton
v-else
class="max-h-full max-w-full rounded-none rounded-t-md"
height="100%"
width="100%"
/>
<div class="mediaType">
<PhVideoCamera
v-if="item.isOfType(MediaType.Video)"
weight="bold"
aria-label="Media has video"
/>
<PhSpeakerHigh
v-if="item.isOfType(MediaType.Audio)"
weight="bold"
aria-label="Media has audio"
/>
<PhSubtitles
v-if="item.isOfType(MediaType.Text)"
weight="bold"
aria-label="Media has subtitles"
/>
<PhImage
v-if="item.isOfType(MediaType.Image)"
weight="bold"
aria-label="Media is an image"
/>
</div>
</div>
<div class="flex items-center gap-1 px-1">
<p
v-tooltip.bottom="{ value: item.name.value, showDelay: 500 }"
class="line-clamp-2 flex-1 text-base"
>
{{ item.name.value }}
</p>
<Button
title="Options"
text
rounded
severity="secondary"
aria-haspopup="true"
aria-controls="library_item_menu"
@click="overlay?.toggle"
>
<template #icon>
<PhDotsThreeVertical size="20" />
</template>
</Button>
</div>
</div>
<OverlayPanel
id="library_item_menu"
Expand Down Expand Up @@ -78,9 +107,9 @@
</OverlayPanel>
</template>
<script setup lang="ts">
import { PhTrash, type PhDotsThreeVertical } from '@phosphor-icons/vue';
import { ProjectFeatures } from '@safelight/shared/base/Project';
import type Media from '@safelight/shared/Media/Media';
import { MediaType } from '@safelight/shared/Media/Media';
import type Menu from 'primevue/menu';
import type { MenuItem } from 'primevue/menuitem';
import type OverlayPanel from 'primevue/overlaypanel';
Expand All @@ -107,10 +136,22 @@ const alertt = (text: string) => window.alert(text);
const overlay = ref<OverlayPanel>();
</script>

<style lang="scss">
<style lang="scss" scoped>
.bg-checkerboard {
/* This is beautifully simple
https://stackoverflow.com/a/65129916 */
background: repeating-conic-gradient(#ffffff0a 0% 25%, transparent 0% 50%) 50% / 20px 20px;
}
.mediaType {
@apply left-0 top-0 h-full w-full gap-2 p-2;
position: absolute;
display: flex;
justify-content: end;
align-items: end;
background: radial-gradient(circle at 100% 100%, rgba(0, 0, 0, 0.4) 0%, transparent 50%);
}
</style>
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<template>
<SLTimeline :items="items" />
<SLTimeline class="h-full" :items="items" />
</template>

<script setup lang="ts">
Expand Down
5 changes: 5 additions & 0 deletions packages/safelight/src/components/Panels/EmptyPanel.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<template>
<div style="flex: 1; display: grid; place-items: center">
<p>No page</p>
</div>
</template>
5 changes: 5 additions & 0 deletions packages/safelight/src/components/Panels/LoadingPanel.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<template>
<div class="grid h-full w-full place-content-center">
<PhCircleNotch class="animate-spin" aria-label="Loading" size="48" />
</div>
</template>
48 changes: 48 additions & 0 deletions packages/safelight/src/components/Panels/PanelContainer.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
<template>
<Splitter
:layout="config.splitDirection"
:pt="{
root: {
style: 'min-height: 0; height: 100%; border-radius: 0;'
}
}"
@resize="clearSelection"
@resizestart="dragStart"
@resizeend="dragEnd"
>
<SplitterPanel v-for="(split, i) in config.split" :key="i" :min-size="5">
<PanelContainer v-if="'splitDirection' in split" :config="split" />
<PanelGroup v-else :config="split" />
</SplitterPanel>
</Splitter>
</template>

<script setup lang="ts">
import type { PanelSplitConfig } from './injection';
defineProps<{
config: PanelSplitConfig;
}>();
// Save the selection range for when the drag ends
// Could just remove the ranges when dragging, but this is nicer IMO
let originalSelection: Range[] = [];
function dragStart() {
originalSelection = [];
for (let index = 0; index < (getSelection()?.rangeCount ?? 0); index++) {
const element = getSelection()?.getRangeAt(index);
if (element) {
originalSelection.push(element);
}
}
}
function dragEnd() {
originalSelection.forEach((range) => {
getSelection()?.addRange(range);
});
}
function clearSelection() {
getSelection()?.removeAllRanges();
}
</script>
Loading

0 comments on commit cea51ee

Please sign in to comment.