mirror of
https://github.com/anatolykopyl/movieroom-front.git
synced 2026-03-26 12:55:20 +00:00
Direct file upload
This commit is contained in:
@@ -1,5 +1,18 @@
|
|||||||
import api from '@/api/index';
|
import api from '@/api/index';
|
||||||
|
|
||||||
export default (magnet:String) => api.post('/room', {
|
export default (movie: String | File) => {
|
||||||
magnet,
|
if (typeof movie === 'string') {
|
||||||
}).then((response) => response.data);
|
return api.post('/roomMagnet', {
|
||||||
|
magnet: movie,
|
||||||
|
}).then((response) => response.data);
|
||||||
|
}
|
||||||
|
|
||||||
|
const formData = new FormData();
|
||||||
|
formData.append('file', movie as Blob);
|
||||||
|
|
||||||
|
return api.post('/roomFile', formData, {
|
||||||
|
headers: {
|
||||||
|
'Content-Type': 'multipart/form-data',
|
||||||
|
},
|
||||||
|
}).then((response) => response.data);
|
||||||
|
};
|
||||||
|
|||||||
39
src/components/Spinner.vue
Normal file
39
src/components/Spinner.vue
Normal file
@@ -0,0 +1,39 @@
|
|||||||
|
<template>
|
||||||
|
<svg class="spinner" viewBox="0 0 50 50">
|
||||||
|
<circle class="path" cx="25" cy="25" r="20" fill="none" stroke-width="5"></circle>
|
||||||
|
</svg>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style lang="scss" scoped>
|
||||||
|
.spinner {
|
||||||
|
animation: rotate 2s linear infinite;
|
||||||
|
|
||||||
|
& .path {
|
||||||
|
stroke: currentColor;
|
||||||
|
stroke-linecap: round;
|
||||||
|
animation: dash 1.5s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes rotate {
|
||||||
|
100% {
|
||||||
|
transform: rotate(360deg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes dash {
|
||||||
|
0% {
|
||||||
|
stroke-dasharray: 1, 150;
|
||||||
|
stroke-dashoffset: 0;
|
||||||
|
}
|
||||||
|
50% {
|
||||||
|
stroke-dasharray: 90, 150;
|
||||||
|
stroke-dashoffset: -35;
|
||||||
|
}
|
||||||
|
100% {
|
||||||
|
stroke-dasharray: 90, 150;
|
||||||
|
stroke-dashoffset: -124;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
export interface Room {
|
export interface Room {
|
||||||
id: string;
|
id: string;
|
||||||
magnet: string;
|
magnet?: string;
|
||||||
createdAt: Date;
|
createdAt: Date;
|
||||||
movie?: string;
|
movie?: string;
|
||||||
filename?: string;
|
filename?: string;
|
||||||
|
|||||||
@@ -12,13 +12,13 @@ html, body {
|
|||||||
height: 100%;
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
button, input[type="text"], textarea {
|
button, input[type="text"], input[type="file"], textarea {
|
||||||
padding: 8px 12px;
|
padding: 8px 12px;
|
||||||
background: none;
|
background: none;
|
||||||
border: 1px solid black;
|
border: 1px solid black;
|
||||||
}
|
}
|
||||||
|
|
||||||
button, a {
|
button, a, input[type="file"] {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -28,4 +28,14 @@ h1 {
|
|||||||
|
|
||||||
h2 {
|
h2 {
|
||||||
font-size: 24px;
|
font-size: 24px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.secondary {
|
||||||
|
color: #818181;
|
||||||
|
}
|
||||||
|
|
||||||
|
::file-selector-button {
|
||||||
|
background: none;
|
||||||
|
border: 1px solid black;
|
||||||
|
font-family: 'EB Garamond', serif;
|
||||||
}
|
}
|
||||||
@@ -1,16 +1,29 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="home">
|
<div class="home">
|
||||||
<form @submit.prevent>
|
<form @submit.prevent>
|
||||||
|
<input
|
||||||
|
type="file"
|
||||||
|
placeholder="file"
|
||||||
|
@change="handleFile"
|
||||||
|
accept="video/mp4"
|
||||||
|
>
|
||||||
|
|
||||||
|
<div class="secondary">or</div>
|
||||||
|
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
v-model="magnet"
|
v-model="magnet"
|
||||||
placeholder="magnet link"
|
placeholder="magnet link"
|
||||||
>
|
>
|
||||||
<button
|
|
||||||
@click="submit"
|
<div class="submit">
|
||||||
>
|
<button
|
||||||
create room
|
@click="submit"
|
||||||
</button>
|
>
|
||||||
|
create room
|
||||||
|
</button>
|
||||||
|
<Spinner v-if="waiting" class="spinner" />
|
||||||
|
</div>
|
||||||
</form>
|
</form>
|
||||||
<a href="https://nutbread.github.io/t2m/">convert .torrent file to a magnet link</a>
|
<a href="https://nutbread.github.io/t2m/">convert .torrent file to a magnet link</a>
|
||||||
</div>
|
</div>
|
||||||
@@ -19,21 +32,40 @@
|
|||||||
<script lang="ts">
|
<script lang="ts">
|
||||||
import { defineComponent } from 'vue';
|
import { defineComponent } from 'vue';
|
||||||
import createRoom from '@/api/createRoom';
|
import createRoom from '@/api/createRoom';
|
||||||
|
import Spinner from '@/components/Spinner.vue';
|
||||||
|
|
||||||
import { Room } from '@/interfaces';
|
import { Room } from '@/interfaces';
|
||||||
|
|
||||||
export default defineComponent({
|
export default defineComponent({
|
||||||
name: 'Home',
|
name: 'Home',
|
||||||
|
components: {
|
||||||
|
Spinner,
|
||||||
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
magnet: '',
|
magnet: '',
|
||||||
|
file: undefined as File | undefined,
|
||||||
|
waiting: false,
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
async submit() {
|
async submit() {
|
||||||
const room: Room = await createRoom(this.magnet);
|
this.waiting = true;
|
||||||
|
let room: Room;
|
||||||
|
if (this.file) {
|
||||||
|
room = await createRoom(this.file);
|
||||||
|
} else {
|
||||||
|
room = await createRoom(this.magnet);
|
||||||
|
}
|
||||||
|
this.waiting = false;
|
||||||
this.$router.push({ name: 'Room', params: { id: room.id } });
|
this.$router.push({ name: 'Room', params: { id: room.id } });
|
||||||
},
|
},
|
||||||
|
handleFile(event: Event) {
|
||||||
|
const element = (event.target as HTMLInputElement);
|
||||||
|
if (element.files) {
|
||||||
|
[this.file] = element.files;
|
||||||
|
}
|
||||||
|
},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
@@ -43,7 +75,26 @@ form {
|
|||||||
margin-bottom: 32px;
|
margin-bottom: 32px;
|
||||||
|
|
||||||
> * {
|
> * {
|
||||||
margin: 0 8px;
|
display: block;
|
||||||
|
margin: 8px 0;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.submit {
|
||||||
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
|
||||||
|
button {
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.spinner {
|
||||||
|
position: absolute;
|
||||||
|
right: -48px;
|
||||||
|
width: 32px;
|
||||||
|
height: 32px;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
@@ -63,8 +63,10 @@ export default defineComponent({
|
|||||||
clearInterval(this.positionInterval);
|
clearInterval(this.positionInterval);
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
onDownloaded() {
|
async onDownloaded() {
|
||||||
this.room.downloaded = true;
|
if (!this.room.downloaded) {
|
||||||
|
this.room = await getRoom(this.id);
|
||||||
|
}
|
||||||
this.$nextTick(() => {
|
this.$nextTick(() => {
|
||||||
const element = this.$refs.video as HTMLVideoElement;
|
const element = this.$refs.video as HTMLVideoElement;
|
||||||
this.positionInterval = setInterval(async () => {
|
this.positionInterval = setInterval(async () => {
|
||||||
|
|||||||
Reference in New Issue
Block a user