sounds, better files

This commit is contained in:
2024-08-18 19:11:41 +00:00
parent 9ed2f70701
commit 08489ed67b
86 changed files with 4226 additions and 86 deletions

View File

@@ -1,26 +1,46 @@
<template>
<div>
<div style="background-color: white; display: flex; flex-direction: row;gap: 0.5rem;padding: 0.5rem">
<div style="max-width: 32px; height: 32px; overflow: hidden;">
<div style="background-color: white; display: flex; flex-direction: row;gap: 0.5rem;padding: 0.5rem;margin-bottom:0.5rem; color: black">
<FilesAside />
<!-- <div style="max-width: 32px; height: 32px; overflow: hidden;">
<google-cast-launcher style="--disconnected-color: black;" ></google-cast-launcher>
</div>
<button @click="openMapWindow">Open map window</button>
<button @click="onStreamImage">Stream image</button>
<button @click="onStreamImage">Stream image</button> -->
</div>
<fieldset>
<legend>Image settings</legend>
<label>Width</label>
<input type="number" v-model="imageWidth" />
<label>Screen Diameter</label>
<input type="number" v-model="screenDiameterInch" />
<label>Flip <input type="checkbox" v-model="flipped"></label>
<label>Position (X/Y)</label>
<input type="range" min="0" max="100" v-model="positionX" />
<input type="range" min="0" max="100" v-model="positionY" />
<button @click="positionX = 50;positionY = 50">center</button>
</fieldset>
<FileManager @openFile="openFile" />
<FilesAside />
<ScreenManager />
<Tabs
:tabs="[
{label: 'Sounds', key: 'sounds'},
{label: 'Settings', key: 'settings'},
{label: 'Devices', key: 'devices'},
]"
>
<template v-slot:settings>
<fieldset>
<legend>Image settings</legend>
<label>Width</label>
<input type="number" v-model="imageWidth" />
<label>Screen Diameter</label>
<input type="number" v-model="screenDiameterInch" />
<label>Flip <input type="checkbox" v-model="flipped"></label>
<label>Position (X/Y)</label>
<input type="range" min="0" max="100" v-model="positionX" />
<input type="range" min="0" max="100" v-model="positionY" />
<button @click="positionX = 50;positionY = 50">center</button>
</fieldset>
</template>
<template v-slot:devices>
<RemoteDevices />
</template>
<template v-slot:sounds>
<div style="padding: 1rem">
<Soundboard />
</div>
</template>
</Tabs>
</div>
</template>
<script setup lang="ts">
@@ -28,6 +48,12 @@ import FileManager from '../../components/FileManager/FileManager.vue';
import type { FileWithMeta } from '../../model/FileManager';
import {ref, inject, watch} from 'vue';
import {SenderSymbol} from '../../model/injectionSymbols';
import Tabs from '../../components/Tabs.vue';
import {VirtualFile} from '../../model/FileSystem/types';
import ScreenManager from '../../components/ScreenManager/ScreenManager.vue';
import RemoteDevices from '../../components/RemoteDevices/RemoteDevices.vue';
import Soundboard from '../../components/Audio/Soundboard.vue';
import FilesAside from '../../components/Files/FilesAside.vue';
const openedFile = ref<FileWithMeta>()
const sender = inject(SenderSymbol);
@@ -62,13 +88,14 @@ watch(() => [positionX.value, positionY.value, flipped.value], () => {
})
});
function openFile(file: FileWithMeta) {
sender?.sendMessage({
type: 'showFile',
file,
})
imageWidth.value = file.width ?? 20;
openedFile.value = file;
function openFile(file: VirtualFile) {
console.log('openFile', file);
// sender?.sendMessage({
// type: 'showFile',
// file,
// })
// imageWidth.value = file.width ?? 20;
// openedFile.value = file;
}
function openMapWindow() {

View File

@@ -0,0 +1,50 @@
<template>
<div class="debug-window">
<pre v-for="json in lastMessages" :class="{
'debug-window__json': json.source === 'json',
'debug-window__webrtc': json.source === 'webrtc',
}">{{ json.message }}</pre>
</div>
</template>
<script setup lang="ts">
import {computed, ref, inject} from 'vue';
import {Message} from '../../model/Remote/Channels/type';
import { JsonChannelSymbol, WebRtcChannelSymbol } from '../../model/injectionSymbols';
const jsonMessages = ref<{source: 'json' | 'webrtc', message: Message}[]>([]);
const lastMessages = computed(() => [...jsonMessages.value].reverse().slice(0, 10));
console.log(jsonMessages, lastMessages);
const channel = inject(JsonChannelSymbol)!;
const webRTC = inject(WebRtcChannelSymbol)!;
channel.on((message) => {
jsonMessages.value.push({source: 'json', message});
jsonMessages.value = jsonMessages.value.slice(-100);
});
webRTC.on((message) => {
jsonMessages.value.push({source: 'webrtc', message});
jsonMessages.value = jsonMessages.value.slice(-100);
});
</script>
<style>
.debug-window {
position: fixed;
left: 0;
top: 0;
width: 400px;
height: 800px;
background-color: rgba(0, 0, 0, 0.5);
border: 2px solid white;
z-index: 10000;
overflow: hidden;
}
.debug-window__json {
color: cadetblue;
}
.debug-window__webrtc {
color: greenyellow;
}
</style>

View File

@@ -0,0 +1,68 @@
<template>
<Debug />
<canvas ref="canvas" style="max-width: 100%" />
</template>
<script setup lang="ts">
import {inject, ref} from 'vue';
import Debug from './Debug.vue';
import {WebRtcChannelSymbol} from '../../model/injectionSymbols';
import {VirtualFile} from '../../model/FileSystem/types';
const webRtc = inject(WebRtcChannelSymbol)!;
const canvas = ref<HTMLCanvasElement>();
const cachedFiles = new Map<string, Blob>();
const fileToKey = (file: VirtualFile) => `${file.source}:${file.path.join('/')}`;
function sendScreenInfo() {
webRtc.send({
type: 'resolution',
width: window.innerWidth * window.devicePixelRatio,
height: window.innerHeight * window.devicePixelRatio,
});
}
function sendAudioInfo() {
const ac = new AudioContext();
webRtc.send({
type: 'audioInfo',
channels: ac.destination.channelCount,
channelInterpretation: ac.destination.channelInterpretation,
})
}
window.addEventListener('resize', () => {
sendScreenInfo();
});
webRtc.on((message) => {
console.log('webRtc message', message);
if (message.type === 'connected') {
sendScreenInfo();
sendAudioInfo();
} else if (message.type === 'fileTransfered') {
debugger;
const key = fileToKey(message.meta);
cachedFiles.set(key, message.blob);
} else if (message.type === 'showFile') {
debugger;
const key = fileToKey(message.file);
const blob = cachedFiles.get(key);
if (blob) {
const url = URL.createObjectURL(blob);
const img = new Image();
img.onload = () => {
const ctx = canvas.value!.getContext('2d')!;
canvas.value!.width = img.width;
canvas.value!.height = img.height;
ctx.drawImage(img, 0, 0);
}
img.src = url;
}
} else if (message.type === 'transform') {
// canvas.value.style = `max-width: 100%;transform: scale(${message.scale}) translate(${message.x}%, ${message.y}%);transition: transform 100ms;`;
}
});
</script>