This is the code that runs https://bandolier.learnjsthehardway.com/ for you to review. It uses the https://git.learnjsthehardway.com/learn-javascript-the-hard-way/bandolier-template to create the documentation for the project.
https://bandolier.learnjsthehardway.com/
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
139 lines
3.5 KiB
139 lines
3.5 KiB
2 years ago
|
<script>
|
||
|
import wt from '$/client/wt.js';
|
||
|
import { onMount, onDestroy } from 'svelte';
|
||
|
import { defer, random_numbers } from '$/client/helpers.js';
|
||
|
import { inject_remote } from "./Source.svelte";
|
||
|
import Spinner from './Spinner.svelte';
|
||
|
import ProgressMeter from './ProgressMeter.svelte';
|
||
|
import { log } from "$/client/logging.js";
|
||
|
|
||
|
export let media;
|
||
|
// whether to add a download link to download the video
|
||
|
export let aspect_ratio = "16/9";
|
||
|
export let autoplay = false;
|
||
|
export let muted = false;
|
||
|
export let controls = true;
|
||
|
|
||
|
let video_ready = false;
|
||
|
let video_done = false;
|
||
|
let progress = 0;
|
||
|
let peers = 0;
|
||
|
let up_rate = 0;
|
||
|
let down_rate = 0;
|
||
|
let time_remaining = 0;
|
||
|
let activated = false;
|
||
|
let loading_promise = defer("wt loading promise");
|
||
|
|
||
|
class VideoEvents extends wt.WTEvents {
|
||
|
done() {
|
||
|
video_done = true;
|
||
|
}
|
||
|
|
||
|
videoReady(file) {
|
||
|
super.videoReady(file);
|
||
|
video_ready = true;
|
||
|
|
||
|
this.intervalId = setInterval(() => {
|
||
|
down_rate = (this.torrent.downloadSpeed / 1024 / 1024).toFixed(2);
|
||
|
up_rate = (this.torrent.uploadSpeed / 1024 / 1024).toFixed(2);
|
||
|
time_remaining = (this.torrent.timeRemaining / 1000).toFixed(0);
|
||
|
peers = this.torrent.numPeers;
|
||
|
}, 1000);
|
||
|
}
|
||
|
|
||
|
download_available(url) {
|
||
|
media.download_url = url;
|
||
|
}
|
||
|
|
||
|
download(bytes) {
|
||
|
let count = Math.floor(this.torrent.progress * 100);
|
||
|
|
||
|
// don't want to overload svelte with tons of updates, it kind of eats it
|
||
|
if(count % 2 == 0 || count % 5 == 0) {
|
||
|
progress = count;
|
||
|
peers = this.torrent.numPeers;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
wire(wire) {
|
||
|
log.debug("wire", wire);
|
||
|
peers = this.torrent.numPeers;
|
||
|
}
|
||
|
|
||
|
noPeers(announceType) {
|
||
|
log.debug("announce", announceType);
|
||
|
peers = this.torrent.numPeers;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
onDestroy(() => {
|
||
|
if(activated) wt.remove(media)
|
||
|
});
|
||
|
|
||
|
|
||
|
const load_media = async () => {
|
||
|
if(await wt.fetch_torrent_file(media)) {
|
||
|
await inject_remote(document, "/js/webtorrent.js", () => {
|
||
|
// generate a temporary target for the loader div
|
||
|
media.target_id = random_numbers(1)[0];
|
||
|
wt.load(media, new VideoEvents(media, {autoplay, controls, muted}));
|
||
|
activated = true;
|
||
|
loading_promise.resolve();
|
||
|
});
|
||
|
} else {
|
||
|
log.debug("Failure loading torrent file.");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
onMount(async () => {
|
||
|
// BUG: this "guard" is here because svelte will load this component
|
||
|
// twice when its inside an await block. First time it loads it but
|
||
|
// doesn't set any properties, then the second time it sets the properties.
|
||
|
if(media && media.torrent_url) {
|
||
|
await load_media();
|
||
|
}
|
||
|
});
|
||
|
</script>
|
||
|
|
||
|
<style>
|
||
|
video {
|
||
|
width: 100%;
|
||
|
}
|
||
|
|
||
|
card {
|
||
|
min-width: unset;
|
||
|
box-shadow: unset;
|
||
|
border-radius: unset;
|
||
|
border: unset;
|
||
|
max-height: calc(95vh - var(--fixed-header-height));
|
||
|
}
|
||
|
|
||
|
card top {
|
||
|
max-height: calc(95vh - var(--fixed-header-height));
|
||
|
}
|
||
|
|
||
|
card bottom {
|
||
|
padding: 0px;
|
||
|
}
|
||
|
</style>
|
||
|
|
||
|
{#await loading_promise}
|
||
|
<Spinner color="var(--value4)" aspect_ratio="16/9" />
|
||
|
{:then}
|
||
|
<card data-testid="video-torrent-body">
|
||
|
<top style="--aspect-ratio: { aspect_ratio };">
|
||
|
<video id="append-{media.target_id}"
|
||
|
muted={muted}
|
||
|
autoplay={autoplay}
|
||
|
controls={ controls}
|
||
|
preload={ media.preload }
|
||
|
poster={media.poster}>
|
||
|
</video>
|
||
|
</top>
|
||
|
|
||
|
<bottom>
|
||
|
<ProgressMeter percent={ progress } show_percent={ false } />
|
||
|
</bottom>
|
||
|
</card>
|
||
|
{/await}
|