More thinngeijidjioashdisa
This commit is contained in:
parent
34a8e1d120
commit
1991fd8f02
@ -10,7 +10,7 @@
|
|||||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/katex.min.css" integrity="sha384-GvrOXuhMATgEsSwCs4smul74iXGOixntILdUW9XmUC6+HX0sLNAK3q71HotJqlAn" crossorigin="anonymous">
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/katex.min.css" integrity="sha384-GvrOXuhMATgEsSwCs4smul74iXGOixntILdUW9XmUC6+HX0sLNAK3q71HotJqlAn" crossorigin="anonymous">
|
||||||
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.js" integrity="sha384-XjKyOOlGwcjNTAIQHIpgOno0Hl1YQqzUOEleOLALmuqehneUG+vnGctmUb0ZY0l8" crossorigin="anonymous"></script>
|
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.js" integrity="sha384-XjKyOOlGwcjNTAIQHIpgOno0Hl1YQqzUOEleOLALmuqehneUG+vnGctmUb0ZY0l8" crossorigin="anonymous"></script>
|
||||||
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/contrib/auto-render.min.js" integrity="sha384-+VBxd3r6XgURycqtZ117nYw44OOcIax56Z4dCRWbxyPt0Koah1uHoK0o4+/RRE05" crossorigin="anonymous"></script>
|
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/contrib/auto-render.min.js" integrity="sha384-+VBxd3r6XgURycqtZ117nYw44OOcIax56Z4dCRWbxyPt0Koah1uHoK0o4+/RRE05" crossorigin="anonymous"></script>
|
||||||
<title>Aran blog</title>
|
<title>Dragonroll</title>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<div id="app"></div>
|
<div id="app"></div>
|
||||||
|
BIN
client/public/sounds/click.wav
Normal file
BIN
client/public/sounds/click.wav
Normal file
Binary file not shown.
BIN
client/public/sounds/close.wav
Normal file
BIN
client/public/sounds/close.wav
Normal file
Binary file not shown.
BIN
client/public/sounds/roll1.wav
Normal file
BIN
client/public/sounds/roll1.wav
Normal file
Binary file not shown.
BIN
client/public/sounds/roll2.wav
Normal file
BIN
client/public/sounds/roll2.wav
Normal file
Binary file not shown.
BIN
client/public/sounds/snap.wav
Normal file
BIN
client/public/sounds/snap.wav
Normal file
Binary file not shown.
@ -45,6 +45,21 @@ a {
|
|||||||
margin: 4.25px;
|
margin: 4.25px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.buttons-row {
|
||||||
|
width: 100%;
|
||||||
|
padding-right: 10px;
|
||||||
|
padding-left: 10px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.button-row {
|
||||||
|
margin-left: 5px;
|
||||||
|
margin-right: 5px;
|
||||||
|
flex-grow: 1;
|
||||||
|
}
|
||||||
|
|
||||||
hr {
|
hr {
|
||||||
border: 0;
|
border: 0;
|
||||||
height: 1px;
|
height: 1px;
|
||||||
@ -89,7 +104,8 @@ input[type=text]:focus, input[type=password]:focus, input[type=email]:focus {
|
|||||||
button {
|
button {
|
||||||
margin-top: 5px;
|
margin-top: 5px;
|
||||||
margin-bottom: 5px;
|
margin-bottom: 5px;
|
||||||
padding: 18px;
|
|
||||||
|
padding: 14px;
|
||||||
font-size: 15px;
|
font-size: 15px;
|
||||||
border-radius: 6px;
|
border-radius: 6px;
|
||||||
outline: none;
|
outline: none;
|
||||||
|
12
client/src/services/Dragonroll.js
Normal file
12
client/src/services/Dragonroll.js
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
import { ClearAll, ClearWindow, CreateWindow } from './Windows';
|
||||||
|
|
||||||
|
function DisplayCampaign(data){
|
||||||
|
ClearAll();
|
||||||
|
CreateWindow('campaign_preview', {
|
||||||
|
title: data.name
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
export {
|
||||||
|
DisplayCampaign
|
||||||
|
};
|
@ -7,9 +7,66 @@ const windows = {
|
|||||||
main_menu: ref([]),
|
main_menu: ref([]),
|
||||||
edit_profile: ref([]),
|
edit_profile: ref([]),
|
||||||
account_settings: ref([]),
|
account_settings: ref([]),
|
||||||
db_window: ref([])
|
db_window: ref([]),
|
||||||
|
campaign_list: ref([]),
|
||||||
|
new_campaign: ref([]),
|
||||||
|
join_campaign: ref([]),
|
||||||
|
campaign_preview: ref([])
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const defValues = {
|
||||||
|
'login': {
|
||||||
|
id: 'login',
|
||||||
|
title: 'Login'
|
||||||
|
},
|
||||||
|
'register': {
|
||||||
|
id: 'register',
|
||||||
|
title: 'Register'
|
||||||
|
},
|
||||||
|
'main_menu': {
|
||||||
|
id: 'main_menu',
|
||||||
|
title: "DragonRoll"
|
||||||
|
},
|
||||||
|
'edit_profile': {
|
||||||
|
id: 'edit_profile',
|
||||||
|
title: "Edit Profile",
|
||||||
|
close: true
|
||||||
|
},
|
||||||
|
'account_settings': {
|
||||||
|
id: 'account_settings',
|
||||||
|
title: "Dragonroll settings",
|
||||||
|
close: true
|
||||||
|
},
|
||||||
|
'campaign_list': {
|
||||||
|
id: 'campaign_list',
|
||||||
|
title: 'Campaigns',
|
||||||
|
back: () => {
|
||||||
|
ClearWindow('campaign_list');
|
||||||
|
CreateWindow('main_menu');
|
||||||
|
}
|
||||||
|
},
|
||||||
|
'new_campaign': {
|
||||||
|
id: 'new_campaign',
|
||||||
|
title: 'Create campaign',
|
||||||
|
parent: 'campaign_list',
|
||||||
|
close: true
|
||||||
|
},
|
||||||
|
'join_campaign': {
|
||||||
|
id: 'join_campaign',
|
||||||
|
title: 'Join campaign',
|
||||||
|
parent: 'campaign_list',
|
||||||
|
close: true
|
||||||
|
},
|
||||||
|
'campaign_preview': {
|
||||||
|
id: 'campaign_preview',
|
||||||
|
title: "Campaign Preview",
|
||||||
|
back: () => {
|
||||||
|
ClearWindow('campaign_preview');
|
||||||
|
CreateWindow('campaign_list')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const reload = ref(0);
|
const reload = ref(0);
|
||||||
|
|
||||||
let ReloadRef = () => { return reload };
|
let ReloadRef = () => { return reload };
|
||||||
@ -107,35 +164,57 @@ function ResetPosition(id, pos){
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
function CreateWindow(data){
|
function CreateWindow(type, data = {}){
|
||||||
if(windows[data.type] === undefined){
|
let finalData = {...{type}, ...defValues[type], ...data}
|
||||||
console.error("Window type " + data.type + " is not defined!");
|
|
||||||
|
console.log(finalData);
|
||||||
|
|
||||||
|
if(windows[finalData.type] === undefined){
|
||||||
|
console.error("Window type " + finalData.type + " is not defined!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let contains = false;
|
let contains = false;
|
||||||
for (let i = 0; i < windows[data.type].length; i++) {
|
for (let i = 0; i < windows[finalData.type].value.length; i++) {
|
||||||
if(windows[data.type][i].id == data.id){
|
if(windows[finalData.type].value[i].id == finalData.id){
|
||||||
contains = true;
|
contains = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!contains) {
|
if(!contains) {
|
||||||
windows[data.type].value.push(data);
|
windows[finalData.type].value.push(finalData);
|
||||||
// reload.value += 1;
|
// reload.value += 1;
|
||||||
|
|
||||||
setTimeout(() => SetOnTop(data.id), 0);
|
setTimeout(() => SetOnTop(finalData.id), 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function CreateChildWindow(parentId, type, data = {}){
|
||||||
|
let finalData = {...{type}, ...defValues[type], ...data}
|
||||||
|
|
||||||
|
let parent = GetWindowWithId(parentId);
|
||||||
|
if(parent.children) parent.children.push(finalData.id);
|
||||||
|
else parent.children = [finalData.id];
|
||||||
|
CreateWindow(type, data);
|
||||||
|
}
|
||||||
|
|
||||||
|
function ClearAll(){
|
||||||
|
Object.keys(windows).forEach((key) => {
|
||||||
|
windows[key].value = [];
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
function ClearWindows(data){
|
function ClearWindows(data){
|
||||||
windows[data.type].value = [];
|
for (let i = 0; i < windows[data.type].value.length; i++) {
|
||||||
|
ClearWindow(windows[data.type].value[i].id);
|
||||||
|
}
|
||||||
// reload.value += 1;
|
// reload.value += 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
function ClearWindow(id){
|
function ClearWindow(id){
|
||||||
let win = GetWindowWithId(id);
|
let win = GetWindowWithId(id);
|
||||||
|
if(!win) return;
|
||||||
|
if(win.children) for(let i = 0; i < win.children.length; i++) ClearWindow(win.children[i]);
|
||||||
windows[win.type].value = windows[win.type].value.filter((e) => {return e.id !== id});
|
windows[win.type].value = windows[win.type].value.filter((e) => {return e.id !== id});
|
||||||
// reload.value += 1;
|
// reload.value += 1;
|
||||||
}
|
}
|
||||||
@ -174,7 +253,9 @@ export {
|
|||||||
ReloadRef,
|
ReloadRef,
|
||||||
ClearWindows,
|
ClearWindows,
|
||||||
CreateWindow,
|
CreateWindow,
|
||||||
|
CreateChildWindow,
|
||||||
GetWindowWithId,
|
GetWindowWithId,
|
||||||
SaveWindowPos,
|
SaveWindowPos,
|
||||||
ClearWindow
|
ClearWindow,
|
||||||
|
ClearAll
|
||||||
}
|
}
|
@ -9,18 +9,10 @@ import { CreateWindow } from '@/services/Windows'
|
|||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
if(GetUser()){
|
if(GetUser()){
|
||||||
CreateWindow({
|
CreateWindow('main_menu')
|
||||||
type: "main_menu",
|
|
||||||
id: "main_menu",
|
|
||||||
title: "Dragonroll"
|
|
||||||
})
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
CreateWindow({
|
CreateWindow('login');
|
||||||
type: "login",
|
|
||||||
id: "login",
|
|
||||||
title: "Login"
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -1,83 +0,0 @@
|
|||||||
<script setup>
|
|
||||||
import ErrorMessage from '@/components/partials/ErrorMessage.vue'
|
|
||||||
|
|
||||||
import { ref } from 'vue';
|
|
||||||
import Api from '@/services/Api.js'
|
|
||||||
import { useRouter, RouterLink } from 'vue-router'
|
|
||||||
|
|
||||||
const email = ref("");
|
|
||||||
const name = ref("");
|
|
||||||
const username = ref("");
|
|
||||||
const password = ref("");
|
|
||||||
const confirmPassword = ref("");
|
|
||||||
|
|
||||||
const errorMessage = ref("");
|
|
||||||
const router = useRouter();
|
|
||||||
|
|
||||||
function register(){
|
|
||||||
|
|
||||||
if(password.value != confirmPassword.value){
|
|
||||||
errorMessage.value = "Les contrasenyes no coincideixen";
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
Api().post('/user/register',
|
|
||||||
{
|
|
||||||
name: name.value,
|
|
||||||
username: username.value,
|
|
||||||
email: email.value,
|
|
||||||
password: password.value,
|
|
||||||
}).then((response) => {
|
|
||||||
const data = response.data;
|
|
||||||
|
|
||||||
if(data.error){
|
|
||||||
errorMessage.value = data.msg;
|
|
||||||
} else {
|
|
||||||
errorMessage.value = "";
|
|
||||||
conso
|
|
||||||
}
|
|
||||||
}).catch((error) => {
|
|
||||||
console.log(error);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<template>
|
|
||||||
<h1 class="title">Registra't</h1>
|
|
||||||
|
|
||||||
<ErrorMessage v-if="errorMessage">{{ errorMessage }}</ErrorMessage>
|
|
||||||
|
|
||||||
<form v-on:submit.prevent="register">
|
|
||||||
<div class="form-field">
|
|
||||||
<label for="name">Nom i cognoms</label>
|
|
||||||
<input id="name-field" type="text" placeholder="Aran Roig" name="name" v-model="name" autocomplete="off" >
|
|
||||||
</div>
|
|
||||||
<div class="form-field">
|
|
||||||
<label for="email">Correu electrònic</label>
|
|
||||||
<input id="email-field" type="email" placeholder="correu@electronic.net" name="email" v-model="email" autocomplete="off" >
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-field">
|
|
||||||
<label for="username">Nom d'usuari</label>
|
|
||||||
<input id="username-field" type="text" placeholder="Introdueix un nom d'usuari..." name="username" v-model="username" autocomplete="off" >
|
|
||||||
</div>
|
|
||||||
<div class="form-field">
|
|
||||||
<label for="password">Contrasenya</label>
|
|
||||||
<input id="password-field" type="password" placeholder="Introdueix una contrasenya..." name="password" v-model="password" autocomplete="off" >
|
|
||||||
</div>
|
|
||||||
<div class="form-field">
|
|
||||||
<label for="confirm-password">Confirma la teva contrasenya</label>
|
|
||||||
<input id="confirm-password-field" type="password" placeholder="Repeteix la contrasenya..." name="confirm-password" v-model="confirmPassword" autocomplete="off" >
|
|
||||||
</div>
|
|
||||||
<div class="form-field">
|
|
||||||
<button class="btn-primary">Registrar</button>
|
|
||||||
</div>
|
|
||||||
</form>
|
|
||||||
<p class="centered">Ja tens un compte? <RouterLink to="/login" class="underline">Inicia sessió</RouterLink></p>
|
|
||||||
</template>
|
|
||||||
|
|
||||||
|
|
||||||
<style scoped>
|
|
||||||
|
|
||||||
</style>
|
|
@ -11,6 +11,10 @@ import AccountSettingsWindow from '../windows/AccountSettingsWindow.vue'
|
|||||||
|
|
||||||
import { Windows, ReloadRef } from '@/services/Windows';
|
import { Windows, ReloadRef } from '@/services/Windows';
|
||||||
import DbWindow from '../windows/database/DbWindow.vue'
|
import DbWindow from '../windows/database/DbWindow.vue'
|
||||||
|
import CampaignListWindow from '../windows/campaigns/CampaignListWindow.vue'
|
||||||
|
import NewCampaignWindow from '../windows/campaigns/NewCampaignWindow.vue'
|
||||||
|
import JoinCampaignWindow from '../windows/campaigns/JoinCampaignWindow.vue'
|
||||||
|
import CampaignPreviewWindow from '@/views/windows/campaigns/CampaignPreviewWindow.vue'
|
||||||
|
|
||||||
// Gestionem ventanas
|
// Gestionem ventanas
|
||||||
const reload = ReloadRef();
|
const reload = ReloadRef();
|
||||||
@ -24,6 +28,10 @@ const main_menu = windows.main_menu;
|
|||||||
const edit_profile = windows.edit_profile;
|
const edit_profile = windows.edit_profile;
|
||||||
const account_settings = windows.account_settings;
|
const account_settings = windows.account_settings;
|
||||||
const db_window = windows.db_window;
|
const db_window = windows.db_window;
|
||||||
|
const campaign_list = windows.campaign_list;
|
||||||
|
const new_campaign = windows.new_campaign;
|
||||||
|
const join_campaign = windows.join_campaign;
|
||||||
|
const campaign_preview = windows.campaign_preview;
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@ -36,6 +44,10 @@ const db_window = windows.db_window;
|
|||||||
<EditProfileWindow v-for="win in edit_profile" :key="win.id" :data="win"></EditProfileWindow>
|
<EditProfileWindow v-for="win in edit_profile" :key="win.id" :data="win"></EditProfileWindow>
|
||||||
<AccountSettingsWindow v-for="win in account_settings" :key="win.id" :data="win"></AccountSettingsWindow>
|
<AccountSettingsWindow v-for="win in account_settings" :key="win.id" :data="win"></AccountSettingsWindow>
|
||||||
<DbWindow v-for="win in db_window" :key="win.id" :data="win"></DbWindow>
|
<DbWindow v-for="win in db_window" :key="win.id" :data="win"></DbWindow>
|
||||||
|
<CampaignListWindow v-for="win in campaign_list" :key="win.id" :data="win"></CampaignListWindow>
|
||||||
|
<NewCampaignWindow v-for="win in new_campaign" :key="win.id" :data="win"></NewCampaignWindow>
|
||||||
|
<JoinCampaignWindow v-for="win in join_campaign" :key="win.id" :data="win"></JoinCampaignWindow>
|
||||||
|
<CampaignPreviewWindow v-for="win in campaign_preview" :key="win.id" :data="win"></CampaignPreviewWindow>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
75
client/src/views/partials/CampaignEntry.vue
Normal file
75
client/src/views/partials/CampaignEntry.vue
Normal file
@ -0,0 +1,75 @@
|
|||||||
|
<script setup>
|
||||||
|
|
||||||
|
import { onMounted, ref } from 'vue';
|
||||||
|
|
||||||
|
import Api from '@/services/Api'
|
||||||
|
import { DisplayCampaign } from '@/services/Dragonroll'
|
||||||
|
|
||||||
|
const props = defineProps(['data']);
|
||||||
|
const data = props.data;
|
||||||
|
|
||||||
|
const title = ref("");
|
||||||
|
const last_session = ref("");
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
console.log(data);
|
||||||
|
title.value = data.name;
|
||||||
|
last_session.value = new Date(data.last_opened).toISOString().slice(0, 10);
|
||||||
|
console.log(title);
|
||||||
|
});
|
||||||
|
|
||||||
|
function ViewCampaign(){
|
||||||
|
DisplayCampaign(data);
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="campaign-entry-container">
|
||||||
|
<div class="main-campaign-entry-container-inner">
|
||||||
|
<img class="campaign-icon" src="img/def-avatar.jpg" draggable="false">
|
||||||
|
<div class="campaign-info">
|
||||||
|
<b>{{ title }}</b><br>Last session: <span>{{ last_session }}</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="campaign-user-actions">
|
||||||
|
<button class="btn-primary button-small sound-click" v-on:click.prevent="ViewCampaign">View</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.button-small {
|
||||||
|
height: 32px;
|
||||||
|
padding: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.campaign-entry-container {
|
||||||
|
background-color: var(--color-background-softer);
|
||||||
|
width: 100%;
|
||||||
|
user-select: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.main-campaign-entry-container-inner {
|
||||||
|
padding: 10px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.campaign-info {
|
||||||
|
text-align: left;
|
||||||
|
margin-left: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.campaign-icon {
|
||||||
|
width: 40px;
|
||||||
|
height: 40px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.campaign-user-actions {
|
||||||
|
margin-left: auto;
|
||||||
|
}
|
||||||
|
</style>
|
@ -10,7 +10,7 @@ import Api from '@/services/Api'
|
|||||||
import url from '@/services/BackendURL'
|
import url from '@/services/BackendURL'
|
||||||
|
|
||||||
import useEmitter from '@/services/Emitter';
|
import useEmitter from '@/services/Emitter';
|
||||||
import { ClearWindows, CreateWindow } from '../../services/Windows';
|
import { ClearWindows, CreateWindow, CreateChildWindow } from '../../services/Windows';
|
||||||
const emitter = useEmitter();
|
const emitter = useEmitter();
|
||||||
|
|
||||||
const username = ref("");
|
const username = ref("");
|
||||||
@ -26,30 +26,16 @@ function retrieveAvatar(){
|
|||||||
function LogOut(){
|
function LogOut(){
|
||||||
LogoutUser();
|
LogoutUser();
|
||||||
|
|
||||||
ClearWindows({type: "main_menu", title: "Dragonroll"});
|
ClearWindows({type: "main_menu"});
|
||||||
CreateWindow({
|
CreateWindow('login');
|
||||||
type: "login",
|
|
||||||
id: "login",
|
|
||||||
title: "Login"
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function EditProfile(){
|
function EditProfile(){
|
||||||
CreateWindow({
|
CreateChildWindow('main_menu', 'edit_profile');
|
||||||
type: "edit_profile",
|
|
||||||
id: "edit_profile",
|
|
||||||
title: "Edit Profile",
|
|
||||||
close: true
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function EditSettings(){
|
function EditSettings(){
|
||||||
CreateWindow({
|
CreateChildWindow('main_menu', 'account_settings');
|
||||||
type: "account_settings",
|
|
||||||
id: "account_settings",
|
|
||||||
title: "Dragonroll settings",
|
|
||||||
close: true
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
@ -92,9 +78,9 @@ onMounted(() => {
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="main-user-actions">
|
<div class="main-user-actions">
|
||||||
<button class="btn-primary button-small" v-on:click.prevent="EditProfile">Edit profile</button>
|
<button class="btn-primary button-small sound-click" v-on:click.prevent="EditProfile">Edit profile</button>
|
||||||
<button class="btn-primary button-small" v-on:click.prevent="EditSettings">Settings</button>
|
<button class="btn-primary button-small sound-click" v-on:click.prevent="EditSettings">Settings</button>
|
||||||
<button class="btn-primary button-small" v-on:click.prevent="LogOut">Log out</button>
|
<button class="btn-primary button-small sound-click" v-on:click.prevent="LogOut">Log out</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
<script setup>
|
<script setup>
|
||||||
import { ref } from 'vue';
|
import { onMounted, ref } from 'vue';
|
||||||
import { GetWindowWithId } from '@/services/Windows';
|
import { GetWindowWithId } from '@/services/Windows';
|
||||||
import { ClearWindow } from '../../services/Windows';
|
import { ClearWindow } from '../../services/Windows';
|
||||||
|
|
||||||
@ -24,15 +24,33 @@ function setupHandle() {
|
|||||||
hasBack.value = true;
|
hasBack.value = true;
|
||||||
backFunction = win.back;
|
backFunction = win.back;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Setup sounds
|
||||||
|
let currentWindowId = "window-wrapper-" + id;
|
||||||
|
let currentWindow = document.getElementById(currentWindowId);
|
||||||
|
let soundClicks = currentWindow.getElementsByClassName("sound-click");
|
||||||
|
|
||||||
|
|
||||||
|
for (let i = 0; i < soundClicks.length; i++) {
|
||||||
|
soundClicks[i].addEventListener("click", async (event) => {
|
||||||
|
const audio = new Audio('/sounds/snap.wav');
|
||||||
|
audio.type = "audio/wav"
|
||||||
|
audio.play();
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function CloseButton(){
|
function CloseButton(){
|
||||||
|
const audio = new Audio('/sounds/close.wav');
|
||||||
|
audio.type = "audio/wav"
|
||||||
|
audio.play();
|
||||||
ClearWindow(id)
|
ClearWindow(id)
|
||||||
}
|
}
|
||||||
|
|
||||||
defineExpose({
|
defineExpose({
|
||||||
setupHandle
|
setupHandle
|
||||||
})
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
@ -32,7 +32,7 @@ onMounted(() => {
|
|||||||
successMessage.value = success;
|
successMessage.value = success;
|
||||||
|
|
||||||
SetupHandle(id, handle);
|
SetupHandle(id, handle);
|
||||||
SetSize(id, {x: 700, y: 630});
|
SetSize(id, {x: 450, y: 480});
|
||||||
ResetPosition(id, "center");
|
ResetPosition(id, "center");
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -62,20 +62,12 @@ function login(){
|
|||||||
|
|
||||||
function ShowRegister(){
|
function ShowRegister(){
|
||||||
ClearWindows({type: "login"});
|
ClearWindows({type: "login"});
|
||||||
CreateWindow({
|
CreateWindow('register');
|
||||||
type: "register",
|
|
||||||
id: "register",
|
|
||||||
title: "Register"
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function ShowMainMenu(){
|
function ShowMainMenu(){
|
||||||
ClearWindows({type: "login"});
|
ClearWindows({type: "login"});
|
||||||
CreateWindow({
|
CreateWindow('main_menu');
|
||||||
type: "main_menu",
|
|
||||||
id: "main_menu",
|
|
||||||
title: "Dragonroll"
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
@ -97,7 +89,7 @@ function ShowMainMenu(){
|
|||||||
<input id="password-field" type="password" placeholder="Enter your password..." name="password" v-model="password" autocomplete="off" >
|
<input id="password-field" type="password" placeholder="Enter your password..." name="password" v-model="password" autocomplete="off" >
|
||||||
</div>
|
</div>
|
||||||
<div class="form-field">
|
<div class="form-field">
|
||||||
<button class="btn-primary">Log in</button>
|
<button class="btn-primary sound-click">Log in</button>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
@ -116,8 +108,6 @@ p {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.window-wrapper {
|
.window-wrapper {
|
||||||
min-width: 700px;
|
|
||||||
min-height: 630px;
|
|
||||||
user-select: none;
|
user-select: none;
|
||||||
|
|
||||||
display: flex;
|
display: flex;
|
||||||
@ -125,17 +115,22 @@ p {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.splash-image {
|
.splash-image {
|
||||||
width: 600px;
|
width: 400px;
|
||||||
height: 250px;
|
}
|
||||||
|
|
||||||
|
form {
|
||||||
|
padding-left: 30px;
|
||||||
|
padding-right: 30px;
|
||||||
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
.form-field {
|
.form-field {
|
||||||
padding: 10px;
|
width: 100%;
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: left;
|
align-items: left;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
justify-content: left;
|
justify-content: left;
|
||||||
width: 600px;
|
padding-top: 10px;
|
||||||
}
|
}
|
||||||
|
|
||||||
label {
|
label {
|
||||||
|
@ -24,10 +24,12 @@ let title = data.title;
|
|||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
SetupHandle(id, handle);
|
SetupHandle(id, handle);
|
||||||
SetSize(id, {x: 500, y: 600});
|
SetSize(id, {x: 500, y: 540});
|
||||||
ResetPosition(id, "center", emitter);
|
ResetPosition(id, "center", emitter);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// ???
|
||||||
|
/*
|
||||||
function OpenDatabase(){
|
function OpenDatabase(){
|
||||||
ClearWindow(id);
|
ClearWindow(id);
|
||||||
CreateWindow({
|
CreateWindow({
|
||||||
@ -44,13 +46,11 @@ function OpenDatabase(){
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
function OpenJoinCampaign(){
|
function OpenCampaigns(){
|
||||||
ClearWindow(id);
|
|
||||||
}
|
|
||||||
|
|
||||||
function OpenMyCampaigns(){
|
|
||||||
ClearWindow(id);
|
ClearWindow(id);
|
||||||
|
CreateWindow('campaign_list');
|
||||||
}
|
}
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
@ -65,12 +65,11 @@ function OpenMyCampaigns(){
|
|||||||
<h1>Main Menu</h1>
|
<h1>Main Menu</h1>
|
||||||
|
|
||||||
<div class="button-container">
|
<div class="button-container">
|
||||||
<button class="btn-primary button-expand" v-on:click="OpenMyCampaigns">My campaings</button>
|
<button class="btn-primary button-expand sound-click" v-on:click="OpenCampaigns">Campaigns</button>
|
||||||
<button class="btn-primary button-expand" v-on:click="OpenJoinCampaign">Join existing campaign</button>
|
|
||||||
<hr>
|
<hr>
|
||||||
<button class="btn-primary button-expand" v-on:click="OpenCollection">Your Collection</button>
|
<button class="btn-primary button-expand sound-click" v-on:click="OpenCollection">Your Collection</button>
|
||||||
<button class="btn-primary button-expand" v-on:click="OpenLibrary">The Cosmic Library</button>
|
<button class="btn-primary button-expand sound-click" v-on:click="OpenLibrary">The Cosmic Library</button>
|
||||||
<button class="btn-primary button-expand" v-on:click="OpenLibrary">Book Anvil</button>
|
<button class="btn-primary button-expand sound-click" v-on:click="OpenLibrary">Book Anvil</button>
|
||||||
</div>
|
</div>
|
||||||
<VersionRender></VersionRender>
|
<VersionRender></VersionRender>
|
||||||
</div>
|
</div>
|
||||||
|
@ -29,7 +29,7 @@ let title = data.title;
|
|||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
SetupHandle(id, handle);
|
SetupHandle(id, handle);
|
||||||
SetSize(id, {x: 700, y: 630});
|
SetSize(id, {x: 450, y: 780});
|
||||||
ResetPosition(id, "center");
|
ResetPosition(id, "center");
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -65,12 +65,7 @@ function register(){
|
|||||||
|
|
||||||
function ShowLogin(msg){
|
function ShowLogin(msg){
|
||||||
ClearWindows({type: "register"});
|
ClearWindows({type: "register"});
|
||||||
CreateWindow({
|
CreateWindow('login', {success: msg});
|
||||||
type: "login",
|
|
||||||
id: "login",
|
|
||||||
title: "Login",
|
|
||||||
success: msg
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
@ -106,7 +101,7 @@ function ShowLogin(msg){
|
|||||||
<input id="confirm-password-field" type="password" placeholder="Enter again your password..." name="confirm-password" v-model="confirmPassword" autocomplete="off" >
|
<input id="confirm-password-field" type="password" placeholder="Enter again your password..." name="confirm-password" v-model="confirmPassword" autocomplete="off" >
|
||||||
</div>
|
</div>
|
||||||
<div class="form-field">
|
<div class="form-field">
|
||||||
<button class="btn-primary">Register</button>
|
<button class="btn-primary sound-click">Register</button>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
@ -126,17 +121,11 @@ p {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.window-wrapper {
|
.window-wrapper {
|
||||||
min-width: 700px;
|
|
||||||
min-height: 630px;
|
|
||||||
|
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.window-content {
|
.window-content {
|
||||||
overflow: auto;
|
|
||||||
min-width: 700px;
|
|
||||||
|
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
@ -144,8 +133,7 @@ p {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.splash-image {
|
.splash-image {
|
||||||
width: 600px;
|
width: 400px;
|
||||||
height: 250px;
|
|
||||||
user-select: none;
|
user-select: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -155,7 +143,10 @@ p {
|
|||||||
align-items: left;
|
align-items: left;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
justify-content: left;
|
justify-content: left;
|
||||||
width: 600px;
|
}
|
||||||
|
|
||||||
|
form {
|
||||||
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
label {
|
label {
|
||||||
|
135
client/src/views/windows/campaigns/CampaignListWindow.vue
Normal file
135
client/src/views/windows/campaigns/CampaignListWindow.vue
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
<script setup>
|
||||||
|
import { onMounted, onUpdated, ref } from 'vue';
|
||||||
|
import { SetupHandle, SetSize, SetPosition, ResetPosition } from '@/services/Windows';
|
||||||
|
|
||||||
|
import WindowHandle from '@/views/partials/WindowHandle.vue';
|
||||||
|
import { CreateWindow, CreateChildWindow } from '../../../services/Windows';
|
||||||
|
|
||||||
|
import Api from '@/services/Api.js'
|
||||||
|
import CampaignEntry from '../../partials/CampaignEntry.vue';
|
||||||
|
|
||||||
|
const handle = ref(null);
|
||||||
|
|
||||||
|
const props = defineProps(['data']);
|
||||||
|
const data = props.data;
|
||||||
|
|
||||||
|
const myCampaigns = ref([]);
|
||||||
|
const otherCampaigns = ref([]);
|
||||||
|
|
||||||
|
let id = data.id;
|
||||||
|
onMounted(() => {
|
||||||
|
SetupHandle(id, handle);
|
||||||
|
SetSize(id, {x: 500, y: 680});
|
||||||
|
ResetPosition(id, "center");
|
||||||
|
|
||||||
|
RefreshCampaigns();
|
||||||
|
});
|
||||||
|
|
||||||
|
function CreateCampaign(){
|
||||||
|
CreateChildWindow(id, 'new_campaign');
|
||||||
|
}
|
||||||
|
|
||||||
|
function JoinCampaign(){
|
||||||
|
CreateChildWindow(id, 'join_campaign')
|
||||||
|
}
|
||||||
|
|
||||||
|
function RefreshCampaigns(){
|
||||||
|
Api().get('/campaign/list').then((response) => {
|
||||||
|
response.data.forEach((camp) => {
|
||||||
|
if(camp.is_dm) {
|
||||||
|
myCampaigns.value.push(camp.campaign);
|
||||||
|
} else {
|
||||||
|
otherCampaigns.value.push(camp.campaign);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="window-wrapper" :id="'window-wrapper-' + id">
|
||||||
|
<WindowHandle :window="id" ref="handle"></WindowHandle>
|
||||||
|
|
||||||
|
<div class="window-body">
|
||||||
|
<!-- Body -->
|
||||||
|
<div class="campaign-list-container">
|
||||||
|
<div class="window-second-header">
|
||||||
|
<h2>Your campaigns</h2>
|
||||||
|
|
||||||
|
<div class="campaign-list">
|
||||||
|
<CampaignEntry v-for="camp in myCampaigns" :key="camp._id" :data="camp"></CampaignEntry>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="window-second-header">
|
||||||
|
<h2>Other campaigns</h2>
|
||||||
|
<div class="campaign-list">
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="buttons-row">
|
||||||
|
<button class="btn-primary button-row sound-click" v-on:click.prevent="CreateCampaign">Create campaign</button>
|
||||||
|
<button class="btn-primary button-row sound-click" v-on:click.prevent="JoinCampaign">Join campaign</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
|
||||||
|
<style scoped lang="scss">
|
||||||
|
|
||||||
|
.campaign-list {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
.campaign-list-container {
|
||||||
|
height: 100%;
|
||||||
|
overflow: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.window-wrapper {
|
||||||
|
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.window-second-header {
|
||||||
|
width: 100%;
|
||||||
|
h2 {
|
||||||
|
font-family: MrEavesRemake;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.buttons-row {
|
||||||
|
margin-top: auto;
|
||||||
|
margin-bottom: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-field {
|
||||||
|
padding: 10px;
|
||||||
|
display: flex;
|
||||||
|
align-items: left;
|
||||||
|
flex-direction: column;
|
||||||
|
justify-content: left;
|
||||||
|
width: 600px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.window-body {
|
||||||
|
max-height: 660px;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
label {
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
58
client/src/views/windows/campaigns/CampaignPreviewWindow.vue
Normal file
58
client/src/views/windows/campaigns/CampaignPreviewWindow.vue
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
<script setup>
|
||||||
|
import { onMounted, onUpdated, ref } from 'vue';
|
||||||
|
import { SetupHandle, SetSize, SetPosition, ResetPosition } from '@/services/Windows';
|
||||||
|
|
||||||
|
import WindowHandle from '@/views/partials/WindowHandle.vue';
|
||||||
|
|
||||||
|
const handle = ref(null);
|
||||||
|
|
||||||
|
const props = defineProps(['data']);
|
||||||
|
const data = props.data;
|
||||||
|
|
||||||
|
let id = data.id;
|
||||||
|
onMounted(() => {
|
||||||
|
SetupHandle(id, handle);
|
||||||
|
SetSize(id, {x: 500, y: 380});
|
||||||
|
ResetPosition(id, "center");
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="window-wrapper" :id="'window-wrapper-' + id">
|
||||||
|
<WindowHandle :window="id" ref="handle"></WindowHandle>
|
||||||
|
|
||||||
|
<!-- Body -->
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.window-wrapper {
|
||||||
|
min-width: 700px;
|
||||||
|
min-height: 630px;
|
||||||
|
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.splash-image {
|
||||||
|
width: 600px;
|
||||||
|
height: 250px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-field {
|
||||||
|
padding: 10px;
|
||||||
|
display: flex;
|
||||||
|
align-items: left;
|
||||||
|
flex-direction: column;
|
||||||
|
justify-content: left;
|
||||||
|
width: 600px;
|
||||||
|
}
|
||||||
|
|
||||||
|
label {
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
73
client/src/views/windows/campaigns/JoinCampaignWindow.vue
Normal file
73
client/src/views/windows/campaigns/JoinCampaignWindow.vue
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
<script setup>
|
||||||
|
import { onMounted, onUpdated, ref } from 'vue';
|
||||||
|
import { SetupHandle, SetSize, SetPosition, ResetPosition } from '@/services/Windows';
|
||||||
|
|
||||||
|
import WindowHandle from '@/views/partials/WindowHandle.vue';
|
||||||
|
|
||||||
|
const handle = ref(null);
|
||||||
|
|
||||||
|
const props = defineProps(['data']);
|
||||||
|
const data = props.data;
|
||||||
|
|
||||||
|
const code = ref("");
|
||||||
|
|
||||||
|
let id = data.id;
|
||||||
|
onMounted(() => {
|
||||||
|
SetupHandle(id, handle);
|
||||||
|
SetSize(id, {x: 300, y: 150});
|
||||||
|
ResetPosition(id, "center");
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="window-wrapper" :id="'window-wrapper-' + id">
|
||||||
|
<WindowHandle :window="id" ref="handle"></WindowHandle>
|
||||||
|
|
||||||
|
<!-- Body -->
|
||||||
|
<form v-on:submit.prevent="JoinCampaign">
|
||||||
|
<div class="form-field">
|
||||||
|
<input id="username-field" type="text" placeholder="Enter campaign code..." name="code" v-model="code" autocomplete="off" >
|
||||||
|
</div>
|
||||||
|
<div class="form-field">
|
||||||
|
<button class="btn-primary sound-click">Join</button>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
|
||||||
|
<style scoped lang="scss">
|
||||||
|
.window-wrapper {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.window-second-header {
|
||||||
|
width: 100%;
|
||||||
|
h2 {
|
||||||
|
font-family: MrEavesRemake;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
form {
|
||||||
|
width: 100%;
|
||||||
|
padding-top: 10px;
|
||||||
|
padding-left: 10px;
|
||||||
|
padding-right: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-field {
|
||||||
|
padding: 2px;
|
||||||
|
display: flex;
|
||||||
|
align-items: left;
|
||||||
|
flex-direction: column;
|
||||||
|
justify-content: left;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
label {
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
84
client/src/views/windows/campaigns/NewCampaignWindow.vue
Normal file
84
client/src/views/windows/campaigns/NewCampaignWindow.vue
Normal file
@ -0,0 +1,84 @@
|
|||||||
|
<script setup>
|
||||||
|
import { onMounted, onUpdated, ref } from 'vue';
|
||||||
|
import { SetupHandle, SetSize, SetPosition, ResetPosition } from '@/services/Windows';
|
||||||
|
|
||||||
|
import WindowHandle from '@/views/partials/WindowHandle.vue';
|
||||||
|
|
||||||
|
import Api from '@/services/Api.js'
|
||||||
|
|
||||||
|
const handle = ref(null);
|
||||||
|
|
||||||
|
const props = defineProps(['data']);
|
||||||
|
const data = props.data;
|
||||||
|
|
||||||
|
const campaignName = ref("");
|
||||||
|
|
||||||
|
let id = data.id;
|
||||||
|
onMounted(() => {
|
||||||
|
SetupHandle(id, handle);
|
||||||
|
SetSize(id, {x: 300, y: 150});
|
||||||
|
ResetPosition(id, "center");
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
function NewCampaign(){
|
||||||
|
Api().post('/campaign/create', {
|
||||||
|
name: campaignName.value
|
||||||
|
}).then((response) => {
|
||||||
|
console.log(response);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<div class="window-wrapper" :id="'window-wrapper-' + id">
|
||||||
|
<WindowHandle :window="id" ref="handle"></WindowHandle>
|
||||||
|
|
||||||
|
<!-- Body -->
|
||||||
|
<form v-on:submit.prevent="NewCampaign">
|
||||||
|
<div class="form-field">
|
||||||
|
<input id="username-field" type="text" placeholder="Enter campaign name..." name="campaignName" v-model="campaignName" autocomplete="off" >
|
||||||
|
</div>
|
||||||
|
<div class="form-field">
|
||||||
|
<button class="btn-primary sound-click">Create</button>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
|
||||||
|
<style scoped lang="scss">
|
||||||
|
.window-wrapper {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.window-second-header {
|
||||||
|
width: 100%;
|
||||||
|
h2 {
|
||||||
|
font-family: MrEavesRemake;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
form {
|
||||||
|
width: 100%;
|
||||||
|
padding-top: 10px;
|
||||||
|
padding-left: 10px;
|
||||||
|
padding-right: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.form-field {
|
||||||
|
padding: 2px;
|
||||||
|
display: flex;
|
||||||
|
align-items: left;
|
||||||
|
flex-direction: column;
|
||||||
|
justify-content: left;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
label {
|
||||||
|
text-align: left;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
23
server/models/Campaign.js
Normal file
23
server/models/Campaign.js
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
const mongoose = require("mongoose");
|
||||||
|
const Schema = mongoose.Schema;
|
||||||
|
|
||||||
|
const CampaignSchema = new Schema({
|
||||||
|
name: {type: String, required: true},
|
||||||
|
creation_date: { type: Date, default: Date.now},
|
||||||
|
last_opened: { type: Date, default: Date.now},
|
||||||
|
invite_code: { type: String, unique: true },
|
||||||
|
image: { type: String }
|
||||||
|
});
|
||||||
|
|
||||||
|
CampaignSchema.statics.generateInvite = function() {
|
||||||
|
let possible = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTVWXYZ0123456789";
|
||||||
|
let cod = '';
|
||||||
|
|
||||||
|
for (let i = 0; i < 32; i++) {
|
||||||
|
cod += possible.charAt(Math.floor(Math.random() * possible.length));
|
||||||
|
}
|
||||||
|
|
||||||
|
return cod;
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = mongoose.model('Campaign', CampaignSchema);
|
10
server/models/CampaignUser.js
Normal file
10
server/models/CampaignUser.js
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
const mongoose = require("mongoose")
|
||||||
|
const Schema = mongoose.Schema;
|
||||||
|
|
||||||
|
const CampaignUserSchema = new Schema({
|
||||||
|
user: {type: mongoose.Types.ObjectId, ref: "User"},
|
||||||
|
campaign: {type: mongoose.Types.ObjectId, ref: "Campaign"},
|
||||||
|
is_dm: {type: Boolean, default: false}
|
||||||
|
});
|
||||||
|
|
||||||
|
module.exports = mongoose.model('CampaignUser', CampaignUserSchema);
|
56
server/routes/campaign.js
Normal file
56
server/routes/campaign.js
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
const express = require('express');
|
||||||
|
const router = express.Router();
|
||||||
|
|
||||||
|
const passport = require('passport');
|
||||||
|
const rateLimitMiddleware = require("../config/rate-limiter");
|
||||||
|
|
||||||
|
const Campaign = require("../models/Campaign");
|
||||||
|
const CampaignUser = require("../models/CampaignUser");
|
||||||
|
|
||||||
|
const upload = require("../config/storage");
|
||||||
|
|
||||||
|
/*
|
||||||
|
router.post('/register', passport.authenticate('jwt', {session: false}), rateLimitMiddleware, (req, res) => {
|
||||||
|
});
|
||||||
|
*/
|
||||||
|
|
||||||
|
router.post('/create', passport.authenticate('jwt', {session: false}), rateLimitMiddleware, (req, res) => {
|
||||||
|
let {
|
||||||
|
name
|
||||||
|
} = req.body;
|
||||||
|
|
||||||
|
if(!(name)){
|
||||||
|
res.json({
|
||||||
|
status: "error",
|
||||||
|
msg: "params"
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create the campaign
|
||||||
|
let campaign = new Campaign({name});
|
||||||
|
campaign.invite_code = Campaign.generateInvite();
|
||||||
|
|
||||||
|
campaign.save().then(campaign => {
|
||||||
|
// Create relation with our user and set him as dm
|
||||||
|
let campaignUser = new CampaignUser({
|
||||||
|
user: req.user,
|
||||||
|
campaign,
|
||||||
|
is_dm: true
|
||||||
|
});
|
||||||
|
|
||||||
|
campaignUser.save().then(campaignUser => {
|
||||||
|
res.json(campaign);
|
||||||
|
return
|
||||||
|
}).catch((err) => {res.json({status: "error", msg: "internal"})});
|
||||||
|
}).catch((err) => {res.json({status: "error", msg: "internal"})});
|
||||||
|
});
|
||||||
|
|
||||||
|
router.get('/list', passport.authenticate('jwt', {session: false}), (req, res) => {
|
||||||
|
CampaignUser.find({user: req.user}).populate("campaign").then((data) => {
|
||||||
|
res.json(data);
|
||||||
|
return;
|
||||||
|
}).catch((err) => res.json({status: "error", msg: "internal"}));
|
||||||
|
});
|
||||||
|
|
||||||
|
module.exports = router;
|
@ -54,6 +54,7 @@ app.use(cors());
|
|||||||
|
|
||||||
// Routes (/ només)
|
// Routes (/ només)
|
||||||
app.use('/user', require('./routes/user'));
|
app.use('/user', require('./routes/user'));
|
||||||
|
app.use('/campaign', require('./routes/campaign'));
|
||||||
|
|
||||||
// app.use('/users', require('./routes/users'));
|
// app.use('/users', require('./routes/users'));
|
||||||
app.listen(PORT, () => {
|
app.listen(PORT, () => {
|
||||||
|
Loading…
Reference in New Issue
Block a user