much progress on layout the foundations of the Friendship page in the front, also refactored some code to reuse displaying a users profile info
This commit is contained in:
@@ -50,6 +50,7 @@ export class UsersController {
|
|||||||
@Get('search')
|
@Get('search')
|
||||||
findOneByUsername(@Query('username') username: string, @Req() req) {
|
findOneByUsername(@Query('username') username: string, @Req() req) {
|
||||||
const user : User = req.user;
|
const user : User = req.user;
|
||||||
|
console.log('searching for user' + user.username);
|
||||||
return this.usersService.findOneByUsername(user.id.toString(),username);
|
return this.usersService.findOneByUsername(user.id.toString(),username);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,112 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
|
||||||
|
import { onMount } from 'svelte';
|
||||||
|
|
||||||
|
import { location } from 'svelte-spa-router';
|
||||||
|
import GenerateUserDisplay from './GenerateUserDisplay.svelte';
|
||||||
|
|
||||||
|
// using location won't work cuz i do a fetch but i don't change the page fragment, so means nothing to location...
|
||||||
|
|
||||||
|
// this is how you access /:first for example
|
||||||
|
// export let params = {}
|
||||||
|
// <p>Your name is: <b>{params.first}</b> <b>{#if params.last}{params.last}{/if}</b></p>
|
||||||
|
|
||||||
|
// If i export these vars, maybe as an nice tidy object, i could pass whatever i like to them
|
||||||
|
// The current user, some other user, whatever, and thus reuse this Componente for the user and their friends or whatever
|
||||||
|
// will have to coordinate with Back, will know more once the Game stats are in the back
|
||||||
|
// wait maybe this won't work, cuz like it's still going through a route, i would have to update a Store Var each time...
|
||||||
|
// not sure if that's what i want...
|
||||||
|
|
||||||
|
|
||||||
|
// maybe the rank is determined dynamically just in the front based on win loss ratio or something no one cares about
|
||||||
|
// why bother storing that shit in the back...
|
||||||
|
// maybe i need a Rank.svelte component
|
||||||
|
// ohhh i could make above a certain rank glitter! like that CSS tutorial showed me!
|
||||||
|
|
||||||
|
export let aUsername;
|
||||||
|
|
||||||
|
let user;
|
||||||
|
let rank = '';
|
||||||
|
let avatar;
|
||||||
|
|
||||||
|
// i think i don't need to do this once i sort out the {wrap} conditions: in theory i could pass values to the Route
|
||||||
|
// once the async authentication check is done
|
||||||
|
onMount( async() => {
|
||||||
|
console.log('Display aUser username: '+ aUsername)
|
||||||
|
// http://transcendance:8080/api/v2/user?username=NomDuUserATrouver
|
||||||
|
user = await fetch(`http://transcendance:8080/api/v2/user?username=${aUsername}`)
|
||||||
|
.then( (x) => x.json() );
|
||||||
|
|
||||||
|
console.log('Display a user: ' + user.username)
|
||||||
|
|
||||||
|
|
||||||
|
// console.log('profile display did my fetch')
|
||||||
|
// should i be updating the userStore or is that unnecessary?
|
||||||
|
|
||||||
|
if (user.loseGame > user.winGame) {
|
||||||
|
rank = 'Bitch Ass Loser!'
|
||||||
|
} else if (user.loseGame === user.winGame) {
|
||||||
|
rank = 'Fine i guess...'
|
||||||
|
} else {
|
||||||
|
rank = 'Yea you da Boss!'
|
||||||
|
}
|
||||||
|
|
||||||
|
await fetch("http://transcendance:8080/api/v2/user/avatar", {method: "GET"})
|
||||||
|
.then(response => {return response.blob()})
|
||||||
|
.then(data => {
|
||||||
|
const url = URL.createObjectURL(data);
|
||||||
|
avatar = url;
|
||||||
|
});
|
||||||
|
|
||||||
|
// tmp
|
||||||
|
// console.log('mounted Profile Display')
|
||||||
|
// console.log(user);
|
||||||
|
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
// Glittery Stars and such for Rank
|
||||||
|
|
||||||
|
let index = 0, interval = 1000;
|
||||||
|
|
||||||
|
const rand = (min, max) =>
|
||||||
|
Math.floor(Math.random() * (max - min + 1)) + min;
|
||||||
|
|
||||||
|
// it's unhappy that "star" isn't typeset, no idea what to do about it...
|
||||||
|
const animate = (star) => {
|
||||||
|
// the if seems to have fixed the type issue
|
||||||
|
if (star) {
|
||||||
|
star.style.setProperty("--star-left", `${rand(-10, 100)}%`);
|
||||||
|
star.style.setProperty("--star-top", `${rand(-40, 80)}%`);
|
||||||
|
|
||||||
|
star.style.animation = "none";
|
||||||
|
star.offsetHeight;
|
||||||
|
star.style.animation = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// This is the part i invented, it was kinda a fucking nightmare...
|
||||||
|
let stars = [];
|
||||||
|
|
||||||
|
for (let i = 0; i < 3; i++) {
|
||||||
|
setTimeout(() => {
|
||||||
|
animate(stars[i]);
|
||||||
|
|
||||||
|
setInterval(() => animate(stars[i]), 1000);
|
||||||
|
}, index++ * (interval / 3))
|
||||||
|
}
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
{#if user !== undefined}
|
||||||
|
<GenerateUserDisplay {user}/>
|
||||||
|
{:else}
|
||||||
|
<h2>Sorry</h2>
|
||||||
|
<div>Failed to load user {aUsername}</div>
|
||||||
|
{/if}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<style>
|
||||||
|
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,305 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
|
||||||
|
import { onMount } from 'svelte';
|
||||||
|
|
||||||
|
import { location } from 'svelte-spa-router';
|
||||||
|
// this is how you access /:first for example
|
||||||
|
// export let params = {}
|
||||||
|
// <p>Your name is: <b>{params.first}</b> <b>{#if params.last}{params.last}{/if}</b></p>
|
||||||
|
|
||||||
|
// If i export these vars, maybe as an nice tidy object, i could pass whatever i like to them
|
||||||
|
// The current user, some other user, whatever, and thus reuse this Componente for the user and their friends or whatever
|
||||||
|
// will have to coordinate with Back, will know more once the Game stats are in the back
|
||||||
|
// wait maybe this won't work, cuz like it's still going through a route, i would have to update a Store Var each time...
|
||||||
|
// not sure if that's what i want...
|
||||||
|
|
||||||
|
|
||||||
|
// maybe the rank is determined dynamically just in the front based on win loss ratio or something no one cares about
|
||||||
|
// why bother storing that shit in the back...
|
||||||
|
// maybe i need a Rank.svelte component
|
||||||
|
// ohhh i could make above a certain rank glitter! like that CSS tutorial showed me!
|
||||||
|
|
||||||
|
let user;
|
||||||
|
let rank = '';
|
||||||
|
let avatar;
|
||||||
|
|
||||||
|
// i think i don't need to do this once i sort out the {wrap} conditions: in theory i could pass values to the Route
|
||||||
|
// once the async authentication check is done
|
||||||
|
onMount( async() => {
|
||||||
|
// console.log('mounting profile display')
|
||||||
|
user = await fetch('http://transcendance:8080/api/v2/user')
|
||||||
|
.then( (x) => x.json() );
|
||||||
|
|
||||||
|
// console.log('profile display did my fetch')
|
||||||
|
// should i be updating the userStore or is that unnecessary?
|
||||||
|
|
||||||
|
if (user.loseGame > user.winGame) {
|
||||||
|
rank = 'Bitch Ass Loser!'
|
||||||
|
} else if (user.loseGame === user.winGame) {
|
||||||
|
rank = 'Fine i guess...'
|
||||||
|
} else {
|
||||||
|
rank = 'Yea you da Boss!'
|
||||||
|
}
|
||||||
|
|
||||||
|
await fetch("http://transcendance:8080/api/v2/user/avatar", {method: "GET"})
|
||||||
|
.then(response => {return response.blob()})
|
||||||
|
.then(data => {
|
||||||
|
const url = URL.createObjectURL(data);
|
||||||
|
avatar = url;
|
||||||
|
});
|
||||||
|
|
||||||
|
// tmp
|
||||||
|
// console.log('mounted Profile Display')
|
||||||
|
// console.log(user);
|
||||||
|
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
// Glittery Stars and such for Rank
|
||||||
|
|
||||||
|
let index = 0, interval = 1000;
|
||||||
|
|
||||||
|
const rand = (min, max) =>
|
||||||
|
Math.floor(Math.random() * (max - min + 1)) + min;
|
||||||
|
|
||||||
|
// it's unhappy that "star" isn't typeset, no idea what to do about it...
|
||||||
|
const animate = (star) => {
|
||||||
|
// the if seems to have fixed the type issue
|
||||||
|
if (star) {
|
||||||
|
star.style.setProperty("--star-left", `${rand(-10, 100)}%`);
|
||||||
|
star.style.setProperty("--star-top", `${rand(-40, 80)}%`);
|
||||||
|
|
||||||
|
star.style.animation = "none";
|
||||||
|
star.offsetHeight;
|
||||||
|
star.style.animation = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// This is the part i invented, it was kinda a fucking nightmare...
|
||||||
|
let stars = [];
|
||||||
|
|
||||||
|
for (let i = 0; i < 3; i++) {
|
||||||
|
setTimeout(() => {
|
||||||
|
animate(stars[i]);
|
||||||
|
|
||||||
|
setInterval(() => animate(stars[i]), 1000);
|
||||||
|
}, index++ * (interval / 3))
|
||||||
|
}
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<!-- is this if excessive? -->
|
||||||
|
<div class="outer">
|
||||||
|
{#if user !== undefined}
|
||||||
|
<main>
|
||||||
|
<!-- <img class="icon" src="img/default_user_icon.png" alt="default user icon"> -->
|
||||||
|
<!-- <img class="icon" src="{user.image_url}" alt="default user icon"> -->
|
||||||
|
<img class="avatar" src="{avatar}" alt="default user icon">
|
||||||
|
<div class="username">{user.username}</div>
|
||||||
|
<div class="rank">Rank:
|
||||||
|
<span class="glitter">
|
||||||
|
<span bind:this={stars[0]} class="glitter-star">
|
||||||
|
<svg viewBox="0 0 512 512">
|
||||||
|
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
||||||
|
</svg>
|
||||||
|
</span>
|
||||||
|
<span bind:this={stars[1]} class="glitter-star">
|
||||||
|
<svg viewBox="0 0 512 512">
|
||||||
|
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
||||||
|
</svg>
|
||||||
|
</span>
|
||||||
|
<span bind:this={stars[2]} class="glitter-star">
|
||||||
|
<svg viewBox="0 0 512 512">
|
||||||
|
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
||||||
|
</svg>
|
||||||
|
</span>
|
||||||
|
<span class="glitter-text">{rank}</span>
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
<section class="main-stats">
|
||||||
|
<h4>Match Statistics</h4>
|
||||||
|
<p>Total: {user.stats.totalGame}</p>
|
||||||
|
<p>Victories: {user.stats.winGame}</p>
|
||||||
|
<p>Losses: {user.stats.loseGame}</p>
|
||||||
|
<p>Draws: {user.stats.drawGame}</p>
|
||||||
|
</section>
|
||||||
|
</main>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
<div>testing when there's tons of stuff</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<style>
|
||||||
|
|
||||||
|
div.outer{
|
||||||
|
max-width: 960px;
|
||||||
|
margin: 40px auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* The main part */
|
||||||
|
main{
|
||||||
|
max-width: 960px;
|
||||||
|
margin: 40px auto;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Normal CSS stuff */
|
||||||
|
.avatar{
|
||||||
|
max-width: 150px;
|
||||||
|
/* padding: 5px; */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* The variable rich section */
|
||||||
|
section.main-stats{
|
||||||
|
max-width: 600px;
|
||||||
|
margin: 40px auto;
|
||||||
|
text-align: center;
|
||||||
|
/* i think i want to use a grid? */
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: repeat(3, 1fr);
|
||||||
|
/* not sure about this, maybe top should be larger? */
|
||||||
|
grid-template-rows: repeat(3, 1fr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* the stuff in the grid*/
|
||||||
|
section.main-stats h4{
|
||||||
|
grid-column: 1 / span 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.username{
|
||||||
|
font-size: 1.5em;
|
||||||
|
font-weight: bold;
|
||||||
|
padding-bottom: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.rank {
|
||||||
|
/* color: black; */
|
||||||
|
font-size: 1.2em;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Glittery Star Stuff */
|
||||||
|
|
||||||
|
|
||||||
|
:root {
|
||||||
|
--purple: rgb(123, 31, 162);
|
||||||
|
--violet: rgb(103, 58, 183);
|
||||||
|
--pink: rgb(244, 143, 177);
|
||||||
|
/* make shit gold? */
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes background-pan {
|
||||||
|
from {
|
||||||
|
background-position: 0% center;
|
||||||
|
}
|
||||||
|
|
||||||
|
to {
|
||||||
|
background-position: -200% center;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes scale {
|
||||||
|
from, to {
|
||||||
|
transform: scale(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
50% {
|
||||||
|
transform: scale(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes rotate {
|
||||||
|
from {
|
||||||
|
transform: rotate(0deg);
|
||||||
|
}
|
||||||
|
|
||||||
|
to {
|
||||||
|
transform: rotate(180deg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
div > .glitter {
|
||||||
|
display: inline-block;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-star {
|
||||||
|
--size: clamp(20px, 1.5vw, 30px);
|
||||||
|
|
||||||
|
animation: scale 700ms ease forwards;
|
||||||
|
display: block;
|
||||||
|
height: var(--size);
|
||||||
|
left: var(--star-left);
|
||||||
|
position: absolute;
|
||||||
|
top: var(--star-top);
|
||||||
|
width: var(--size);
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-star > svg {
|
||||||
|
animation: rotate 1000ms linear infinite;
|
||||||
|
display: block;
|
||||||
|
opacity: 0.7;
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-star > svg > path {
|
||||||
|
fill: var(--violet);
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-text {
|
||||||
|
animation: background-pan 3s linear infinite;
|
||||||
|
/* background-image: linear-gradient( */
|
||||||
|
background: linear-gradient(
|
||||||
|
to right,
|
||||||
|
var(--purple),
|
||||||
|
var(--violet),
|
||||||
|
var(--pink),
|
||||||
|
var(--purple)
|
||||||
|
);
|
||||||
|
background-size: 200%;
|
||||||
|
|
||||||
|
/* Keep these for Safari and chrome */
|
||||||
|
-webkit-background-clip: text;
|
||||||
|
-webkit-text-fill-color: transparent;
|
||||||
|
|
||||||
|
/* These are for Firefox */
|
||||||
|
background-clip: text;
|
||||||
|
color: transparent;
|
||||||
|
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
||||||
@@ -1,129 +1,32 @@
|
|||||||
<script lang="ts">
|
<script lang="ts">
|
||||||
|
|
||||||
import { onMount } from 'svelte';
|
import { onMount } from 'svelte';
|
||||||
|
import GenerateUserDisplay from '../../pieces/GenerateUserDisplay.svelte';
|
||||||
import { location } from 'svelte-spa-router';
|
|
||||||
// this is how you access /:first for example
|
|
||||||
// export let params = {}
|
|
||||||
// <p>Your name is: <b>{params.first}</b> <b>{#if params.last}{params.last}{/if}</b></p>
|
|
||||||
|
|
||||||
// If i export these vars, maybe as an nice tidy object, i could pass whatever i like to them
|
|
||||||
// The current user, some other user, whatever, and thus reuse this Componente for the user and their friends or whatever
|
|
||||||
// will have to coordinate with Back, will know more once the Game stats are in the back
|
|
||||||
// wait maybe this won't work, cuz like it's still going through a route, i would have to update a Store Var each time...
|
|
||||||
// not sure if that's what i want...
|
|
||||||
|
|
||||||
|
|
||||||
// maybe the rank is determined dynamically just in the front based on win loss ratio or something no one cares about
|
|
||||||
// why bother storing that shit in the back...
|
|
||||||
// maybe i need a Rank.svelte component
|
|
||||||
// ohhh i could make above a certain rank glitter! like that CSS tutorial showed me!
|
|
||||||
|
|
||||||
let user;
|
let user;
|
||||||
let rank = '';
|
|
||||||
let avatar;
|
|
||||||
|
|
||||||
// i think i don't need to do this once i sort out the {wrap} conditions: in theory i could pass values to the Route
|
|
||||||
// once the async authentication check is done
|
|
||||||
onMount( async() => {
|
onMount( async() => {
|
||||||
// console.log('mounting profile display')
|
// console.log('mounting profile display')
|
||||||
user = await fetch('http://transcendance:8080/api/v2/user')
|
user = await fetch('http://transcendance:8080/api/v2/user')
|
||||||
.then( (x) => x.json() );
|
.then( (x) => x.json() );
|
||||||
|
|
||||||
// console.log('profile display did my fetch')
|
|
||||||
// should i be updating the userStore or is that unnecessary?
|
|
||||||
|
|
||||||
if (user.loseGame > user.winGame) {
|
|
||||||
rank = 'Bitch Ass Loser!'
|
|
||||||
} else if (user.loseGame === user.winGame) {
|
|
||||||
rank = 'Fine i guess...'
|
|
||||||
} else {
|
|
||||||
rank = 'Yea you da Boss!'
|
|
||||||
}
|
|
||||||
|
|
||||||
await fetch("http://transcendance:8080/api/v2/user/avatar", {method: "GET"})
|
|
||||||
.then(response => {return response.blob()})
|
|
||||||
.then(data => {
|
|
||||||
const url = URL.createObjectURL(data);
|
|
||||||
avatar = url;
|
|
||||||
});
|
|
||||||
|
|
||||||
// tmp
|
|
||||||
// console.log('mounted Profile Display')
|
|
||||||
// console.log(user);
|
|
||||||
|
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
// Glittery Stars and such for Rank
|
|
||||||
|
|
||||||
let index = 0, interval = 1000;
|
|
||||||
|
|
||||||
const rand = (min, max) =>
|
|
||||||
Math.floor(Math.random() * (max - min + 1)) + min;
|
|
||||||
|
|
||||||
// it's unhappy that "star" isn't typeset, no idea what to do about it...
|
|
||||||
const animate = (star) => {
|
|
||||||
// the if seems to have fixed the type issue
|
|
||||||
if (star) {
|
|
||||||
star.style.setProperty("--star-left", `${rand(-10, 100)}%`);
|
|
||||||
star.style.setProperty("--star-top", `${rand(-40, 80)}%`);
|
|
||||||
|
|
||||||
star.style.animation = "none";
|
|
||||||
star.offsetHeight;
|
|
||||||
star.style.animation = "";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// This is the part i invented, it was kinda a fucking nightmare...
|
|
||||||
let stars = [];
|
|
||||||
|
|
||||||
for (let i = 0; i < 3; i++) {
|
|
||||||
setTimeout(() => {
|
|
||||||
animate(stars[i]);
|
|
||||||
|
|
||||||
setInterval(() => animate(stars[i]), 1000);
|
|
||||||
}, index++ * (interval / 3))
|
|
||||||
}
|
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<!-- is this if excessive? -->
|
<!-- is this if excessive? -->
|
||||||
|
<div class="outer">
|
||||||
|
<!-- OHHHH i could use #await instead of if and have an nice loading page! -->
|
||||||
{#if user !== undefined}
|
{#if user !== undefined}
|
||||||
<main>
|
<GenerateUserDisplay {user} primary={true}/>
|
||||||
<!-- <img class="icon" src="img/default_user_icon.png" alt="default user icon"> -->
|
{:else}
|
||||||
<!-- <img class="icon" src="{user.image_url}" alt="default user icon"> -->
|
<!-- might be unnecessary since you can't access the page without fetching the user -->
|
||||||
<img class="avatar" src="{avatar}" alt="default user icon">
|
<h2>Sorry</h2>
|
||||||
<div class="username">{user.username}</div>
|
<div>Failed to load current</div>
|
||||||
<div class="rank">Rank:
|
|
||||||
<span class="glitter">
|
|
||||||
<span bind:this={stars[0]} class="glitter-star">
|
|
||||||
<svg viewBox="0 0 512 512">
|
|
||||||
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
|
||||||
</svg>
|
|
||||||
</span>
|
|
||||||
<span bind:this={stars[1]} class="glitter-star">
|
|
||||||
<svg viewBox="0 0 512 512">
|
|
||||||
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
|
||||||
</svg>
|
|
||||||
</span>
|
|
||||||
<span bind:this={stars[2]} class="glitter-star">
|
|
||||||
<svg viewBox="0 0 512 512">
|
|
||||||
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
|
||||||
</svg>
|
|
||||||
</span>
|
|
||||||
<span class="glitter-text">{rank}</span>
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
<section class="main-stats">
|
|
||||||
<h4>Match Statistics</h4>
|
|
||||||
<p>Total: {user.stats.totalGame}</p>
|
|
||||||
<p>Victories: {user.stats.winGame}</p>
|
|
||||||
<p>Losses: {user.stats.loseGame}</p>
|
|
||||||
<p>Draws: {user.stats.drawGame}</p>
|
|
||||||
</section>
|
|
||||||
</main>
|
|
||||||
{/if}
|
{/if}
|
||||||
|
</div>
|
||||||
|
|
||||||
<div>testing when there's tons of stuff</div>
|
<div>testing when there's tons of stuff</div>
|
||||||
<div>testing when there's tons of stuff</div>
|
<div>testing when there's tons of stuff</div>
|
||||||
@@ -161,6 +64,11 @@
|
|||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
|
||||||
|
div.outer{
|
||||||
|
max-width: 960px;
|
||||||
|
margin: 40px auto;
|
||||||
|
}
|
||||||
|
|
||||||
/* The main part */
|
/* The main part */
|
||||||
main{
|
main{
|
||||||
max-width: 960px;
|
max-width: 960px;
|
||||||
|
|||||||
@@ -2,6 +2,26 @@
|
|||||||
|
|
||||||
import { onMount } from "svelte";
|
import { onMount } from "svelte";
|
||||||
import Button from "../../pieces/Button.svelte";
|
import Button from "../../pieces/Button.svelte";
|
||||||
|
import DisplayAUser from "../../pieces/DisplayAUser.svelte";
|
||||||
|
|
||||||
|
// Ok so i need to test all the paths Cherif has made but a major one doesn't work yet...
|
||||||
|
// in the mean time, i need to make some other stuff look nice
|
||||||
|
// what do i want?
|
||||||
|
|
||||||
|
/*
|
||||||
|
Ideas
|
||||||
|
- a list of all users and if they're active
|
||||||
|
could be a list of friends and if they're active but i can't see that yet
|
||||||
|
- I click on a thing and it lets me see all the users and i get a button that lets me add them
|
||||||
|
- would that be like a serachable list of all users?
|
||||||
|
- am i skipping optimization? i mean for now yes, but like
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
let errors = {friendRequest: '',};
|
let errors = {friendRequest: '',};
|
||||||
let set = {friendUsername: '', friendId: Number}
|
let set = {friendUsername: '', friendId: Number}
|
||||||
@@ -9,8 +29,9 @@
|
|||||||
let user;
|
let user;
|
||||||
let myFriends;
|
let myFriends;
|
||||||
let requestsMade, requestsRecieved;
|
let requestsMade, requestsRecieved;
|
||||||
// http://transcendance:8080/api/v2/network/received the ones you have recieved
|
let allUsers;
|
||||||
// http://transcendance:8080/api/v2/network/pending the ones you have sent
|
let allFriends;
|
||||||
|
let userToDisplay;
|
||||||
|
|
||||||
|
|
||||||
onMount( async() => {
|
onMount( async() => {
|
||||||
@@ -42,16 +63,23 @@
|
|||||||
console.log('Requests received ');
|
console.log('Requests received ');
|
||||||
console.log(requestsRecieved);
|
console.log(requestsRecieved);
|
||||||
|
|
||||||
|
allUsers = await fetch('http://transcendance:8080/api/v2/user/all')
|
||||||
|
.then( x => x.json() );
|
||||||
|
console.log('got all users ' + allUsers)
|
||||||
|
|
||||||
|
allFriends = await fetch('http://transcendance:8080/api/v2/network/myfriends')
|
||||||
|
.then( x => x.json() );
|
||||||
|
console.log('got all friends ' + allFriends)
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
let allUsers;
|
|
||||||
const displayAllUsers = async() => {
|
const displayAllUsers = async() => {
|
||||||
allUsers = await fetch('http://transcendance:8080/api/v2/user/all')
|
allUsers = await fetch('http://transcendance:8080/api/v2/user/all')
|
||||||
.then( x => x.json() );
|
.then( x => x.json() );
|
||||||
console.log('got all users ' + allUsers)
|
console.log('got all users ' + allUsers)
|
||||||
};
|
};
|
||||||
|
|
||||||
let allFriends;
|
|
||||||
const displayAllFriends = async() => {
|
const displayAllFriends = async() => {
|
||||||
allFriends = await fetch('http://transcendance:8080/api/v2/network/myfriends')
|
allFriends = await fetch('http://transcendance:8080/api/v2/network/myfriends')
|
||||||
.then( x => x.json() );
|
.then( x => x.json() );
|
||||||
@@ -112,78 +140,140 @@
|
|||||||
.then (x => console.log({...x}));
|
.then (x => console.log({...x}));
|
||||||
|
|
||||||
// should i then update requtestsMade with another fetch?
|
// should i then update requtestsMade with another fetch?
|
||||||
|
// maybe also check if the request went through?
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// body: JSON.stringify({
|
|
||||||
// "requesterUsername": user.username,
|
|
||||||
// "addresseeUsername": set.friendUsername,
|
|
||||||
// "status": r
|
|
||||||
|
|
||||||
// "requesterId": user.username,
|
|
||||||
// "addresseeId": set.friendUsername,
|
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<h1>Friendship page</h1>
|
|
||||||
|
|
||||||
{#if user && user.username}
|
<!-- svelte-ignore a11y-click-events-have-key-events -->
|
||||||
<div>You are {user.username}</div>
|
<div class="top-grid">
|
||||||
|
|
||||||
|
<div class="all-users-sidebar">
|
||||||
|
<h3>All Users</h3>
|
||||||
|
{#if allUsers === undefined}
|
||||||
|
<div class="error">Failed to load all users</div>
|
||||||
|
{:else}
|
||||||
|
<!-- problem, i can't use user.id since Cherif doesn't want to expost that to the front...
|
||||||
|
is there something else i could use? -->
|
||||||
|
{#each allUsers as aUser }
|
||||||
|
<!-- <div class="a-user" on:click={() => displayAUser(aUser.username)}>{aUser.username}</div> -->
|
||||||
|
<div class="a-user" on:click={() => userToDisplay = aUser.username}>{aUser.username}</div>
|
||||||
|
<!-- i could make an indicator component? like green for connected or something?
|
||||||
|
i could use words but color them?
|
||||||
|
i could make it so if they're in a game -->
|
||||||
|
<div class="status a-user">{aUser.status}</div>
|
||||||
|
<br>
|
||||||
|
{/each}
|
||||||
{/if}
|
{/if}
|
||||||
|
|
||||||
<!-- <div>My friends obj</div> -->
|
</div>
|
||||||
<!-- <div>{myFriends}</div> -->
|
|
||||||
<!-- <br> -->
|
|
||||||
<Button on:click={displayAllUsers}>Get All Users</Button>
|
|
||||||
|
<!-- <h1>Friendship page</h1> -->
|
||||||
|
|
||||||
|
<div class="main-display">
|
||||||
|
|
||||||
|
<h1>Main Display</h1>
|
||||||
|
|
||||||
|
<!-- use an #await here too? -->
|
||||||
|
<!-- you can do better, like an on load sort of thing -->
|
||||||
|
{#if userToDisplay !== undefined}
|
||||||
|
<DisplayAUser aUsername={userToDisplay}/>
|
||||||
|
{/if}
|
||||||
|
|
||||||
|
<!-- {#if user && user.username}
|
||||||
|
<div>You are {user.username}</div>
|
||||||
|
{/if} -->
|
||||||
|
|
||||||
|
<!-- <Button on:click={displayAllUsers}>Get All Users</Button>
|
||||||
{#if allUsers !== undefined}
|
{#if allUsers !== undefined}
|
||||||
{#each allUsers as user}
|
{#each allUsers as user}
|
||||||
<div>{user.username}</div>
|
<div>{user.username}</div>
|
||||||
{/each}
|
{/each}
|
||||||
{/if}
|
{/if}
|
||||||
|
|
||||||
<br>
|
<br> -->
|
||||||
|
|
||||||
<Button on:click={displayAllFriends}>Get All Friends</Button>
|
<!-- <Button on:click={displayAllFriends}>Get All Friends</Button>
|
||||||
{#if allFriends !== undefined}
|
{#if allFriends !== undefined}
|
||||||
<div>{allFriends}</div>
|
<div>{allFriends}</div>
|
||||||
{#each allFriends as friend}
|
{#each allFriends as friend}
|
||||||
<div>{friend}{friend.username}</div>
|
<div>{friend}{friend.username}</div>
|
||||||
{/each}
|
{/each}
|
||||||
{/if}
|
{/if} -->
|
||||||
|
|
||||||
<br>
|
<!-- <br>
|
||||||
|
|
||||||
<div>Make a Friend!</div>
|
<div>Make a Friend!</div>
|
||||||
<form on:submit|preventDefault={() => friendUserByUsername(set.friendUsername)}>
|
<form on:submit|preventDefault={() => friendUserByUsername(set.friendUsername)}>
|
||||||
<input type="text" placeholder="friend's username" bind:value={set.friendUsername}>
|
<input type="text" placeholder="friend's username" bind:value={set.friendUsername}>
|
||||||
<div class="error">{errors.friendRequest}</div>
|
<div class="error">{errors.friendRequest}</div>
|
||||||
<Button type="secondary">Send Friend Request</Button>
|
<Button type="secondary">Send Friend Request</Button>
|
||||||
</form>
|
</form> -->
|
||||||
|
|
||||||
<br> <br>
|
<!-- <br> <br> -->
|
||||||
<!-- here i want to list all the requests you and have an accept and a decline button -->
|
<!-- here i want to list all the requests you and have an accept and a decline button -->
|
||||||
|
|
||||||
<!-- {#each requestsRecieved as request} -->
|
<!-- {#each requestsRecieved as request} -->
|
||||||
|
|
||||||
<br> <br>
|
<!-- <br> <br> -->
|
||||||
<!-- I want to list all the requests made by this user -->
|
<!-- I want to list all the requests made by this user -->
|
||||||
|
|
||||||
<Button on:click={displayRequestsMade}>Display Requests Made</Button>
|
<!-- <Button on:click={displayRequestsMade}>Display Requests Made</Button>
|
||||||
|
|
||||||
{#if requestsMade !== undefined}
|
{#if requestsMade !== undefined}
|
||||||
{#each requestsMade as requestMade}
|
{#each requestsMade as requestMade}
|
||||||
<div>{requestMade}</div>
|
<div>{requestMade}</div>
|
||||||
{/each}
|
{/each}
|
||||||
{/if}
|
{/if} -->
|
||||||
|
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
|
||||||
|
/* ok so i want a 12 column grid with a sidebar */
|
||||||
|
|
||||||
|
div.top-grid{
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: repeat(12, 1fr);
|
||||||
|
/* max-height: calc(100vh - 30vh); */
|
||||||
|
height: 85vh;
|
||||||
|
/* margin: 0; */
|
||||||
|
}
|
||||||
|
|
||||||
|
div.all-users-sidebar{
|
||||||
|
grid-column: 1 / span 2;
|
||||||
|
background: white;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.a-user{
|
||||||
|
/* yea i mean that seems fine... */
|
||||||
|
display: inline-block;
|
||||||
|
/* somehting about the buttons too, smaller ? */
|
||||||
|
}
|
||||||
|
div.status{
|
||||||
|
font-size: 0.6em;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
/* selector attributes to get only divs with .a-user */
|
||||||
|
/* you gotta be careful with Svelte cuz it tacks classes on to the end of basically all elems! */
|
||||||
|
div[class^="a-user"]:hover{
|
||||||
|
text-decoration: underline;
|
||||||
|
font-weight: bold;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.main-display{
|
||||||
|
grid-column: 3 / span 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
.error{
|
.error{
|
||||||
font-size: 0.8em;
|
font-size: 0.8em;
|
||||||
font-weight: bold;
|
font-weight: bold;
|
||||||
|
|||||||
@@ -28,10 +28,11 @@
|
|||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
|
||||||
div {
|
/* this doesn't work, fucks up all my sub routes */
|
||||||
|
/* div {
|
||||||
max-width: 960px;
|
max-width: 960px;
|
||||||
margin: 40px auto;
|
margin: 40px auto;
|
||||||
}
|
} */
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,33 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
|
||||||
|
import { onMount } from 'svelte';
|
||||||
|
import GenerateUserDisplay from './GenerateUserDisplay.svelte';
|
||||||
|
|
||||||
|
export let aUsername;
|
||||||
|
let user;
|
||||||
|
|
||||||
|
onMount( async() => {
|
||||||
|
console.log('Display aUser username: '+ aUsername)
|
||||||
|
// http://transcendance:8080/api/v2/user?username=NomDuUserATrouver
|
||||||
|
user = await fetch(`http://transcendance:8080/api/v2/user?username=${aUsername}`)
|
||||||
|
.then( (x) => x.json() );
|
||||||
|
|
||||||
|
console.log('Display a user: ' + user.username)
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
<!-- OHHHH i could use #await instead of if and have an nice loading page! -->
|
||||||
|
{#if user !== undefined}
|
||||||
|
<GenerateUserDisplay {user} primary={true}/>
|
||||||
|
{:else}
|
||||||
|
<h2>Sorry</h2>
|
||||||
|
<div>Failed to load user {aUsername}</div>
|
||||||
|
{/if}
|
||||||
|
|
||||||
|
|
||||||
|
<style>
|
||||||
|
|
||||||
|
</style>
|
||||||
@@ -0,0 +1,251 @@
|
|||||||
|
<script lang="ts">
|
||||||
|
|
||||||
|
import { onMount } from 'svelte';
|
||||||
|
|
||||||
|
export let user;
|
||||||
|
export let primary;
|
||||||
|
let rank = '';
|
||||||
|
let avatar;
|
||||||
|
|
||||||
|
|
||||||
|
onMount( async() => {
|
||||||
|
// using this for now cuz for some reason there is yet to be a way to fet another person's avatar
|
||||||
|
if (primary) {
|
||||||
|
await fetch("http://transcendance:8080/api/v2/user/avatar", {method: "GET"})
|
||||||
|
.then(response => {return response.blob()})
|
||||||
|
.then(data => {
|
||||||
|
const url = URL.createObjectURL(data);
|
||||||
|
avatar = url;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
// tmp
|
||||||
|
// console.log('mounted Profile Display')
|
||||||
|
// console.log(user);
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
if (user.loseGame > user.winGame) {
|
||||||
|
rank = 'Bitch Ass Loser!'
|
||||||
|
} else if (user.loseGame === user.winGame) {
|
||||||
|
rank = 'Fine i guess...'
|
||||||
|
} else {
|
||||||
|
rank = 'Yea you da Boss!'
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Glittery Stars and such for Rank
|
||||||
|
|
||||||
|
let index = 0, interval = 1000;
|
||||||
|
|
||||||
|
const rand = (min, max) =>
|
||||||
|
Math.floor(Math.random() * (max - min + 1)) + min;
|
||||||
|
|
||||||
|
// it's unhappy that "star" isn't typeset, no idea what to do about it...
|
||||||
|
const animate = (star) => {
|
||||||
|
// the if seems to have fixed the type issue
|
||||||
|
if (star) {
|
||||||
|
star.style.setProperty("--star-left", `${rand(-10, 100)}%`);
|
||||||
|
star.style.setProperty("--star-top", `${rand(-40, 80)}%`);
|
||||||
|
|
||||||
|
star.style.animation = "none";
|
||||||
|
star.offsetHeight;
|
||||||
|
star.style.animation = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// This is the part i invented, it was kinda a fucking nightmare...
|
||||||
|
let stars = [];
|
||||||
|
|
||||||
|
for (let i = 0; i < 3; i++) {
|
||||||
|
setTimeout(() => {
|
||||||
|
animate(stars[i]);
|
||||||
|
|
||||||
|
setInterval(() => animate(stars[i]), 1000);
|
||||||
|
}, index++ * (interval / 3))
|
||||||
|
}
|
||||||
|
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<!-- is this if excessive? -->
|
||||||
|
<div class="outer">
|
||||||
|
{#if user !== undefined}
|
||||||
|
<main>
|
||||||
|
<!-- <img class="icon" src="img/default_user_icon.png" alt="default user icon"> -->
|
||||||
|
<!-- <img class="icon" src="{user.image_url}" alt="default user icon"> -->
|
||||||
|
<img class="avatar" src="{avatar}" alt="default user icon">
|
||||||
|
<div class="username">{user.username}</div>
|
||||||
|
<div class="rank">Rank:
|
||||||
|
<span class="glitter">
|
||||||
|
<span bind:this={stars[0]} class="glitter-star">
|
||||||
|
<svg viewBox="0 0 512 512">
|
||||||
|
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
||||||
|
</svg>
|
||||||
|
</span>
|
||||||
|
<span bind:this={stars[1]} class="glitter-star">
|
||||||
|
<svg viewBox="0 0 512 512">
|
||||||
|
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
||||||
|
</svg>
|
||||||
|
</span>
|
||||||
|
<span bind:this={stars[2]} class="glitter-star">
|
||||||
|
<svg viewBox="0 0 512 512">
|
||||||
|
<path d="M512 255.1c0 11.34-7.406 20.86-18.44 23.64l-171.3 42.78l-42.78 171.1C276.7 504.6 267.2 512 255.9 512s-20.84-7.406-23.62-18.44l-42.66-171.2L18.47 279.6C7.406 276.8 0 267.3 0 255.1c0-11.34 7.406-20.83 18.44-23.61l171.2-42.78l42.78-171.1C235.2 7.406 244.7 0 256 0s20.84 7.406 23.62 18.44l42.78 171.2l171.2 42.78C504.6 235.2 512 244.6 512 255.1z" />
|
||||||
|
</svg>
|
||||||
|
</span>
|
||||||
|
<span class="glitter-text">{rank}</span>
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
<section class="main-stats">
|
||||||
|
<h4>Match Statistics</h4>
|
||||||
|
<p>Total: {user.stats.totalGame}</p>
|
||||||
|
<p>Victories: {user.stats.winGame}</p>
|
||||||
|
<p>Losses: {user.stats.loseGame}</p>
|
||||||
|
<p>Draws: {user.stats.drawGame}</p>
|
||||||
|
</section>
|
||||||
|
</main>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<style>
|
||||||
|
|
||||||
|
div.outer{
|
||||||
|
max-width: 960px;
|
||||||
|
margin: 40px auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* The main part */
|
||||||
|
main{
|
||||||
|
max-width: 960px;
|
||||||
|
margin: 40px auto;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Normal CSS stuff */
|
||||||
|
.avatar{
|
||||||
|
max-width: 150px;
|
||||||
|
/* padding: 5px; */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* The variable rich section */
|
||||||
|
section.main-stats{
|
||||||
|
max-width: 600px;
|
||||||
|
margin: 40px auto;
|
||||||
|
text-align: center;
|
||||||
|
/* i think i want to use a grid? */
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: repeat(3, 1fr);
|
||||||
|
/* not sure about this, maybe top should be larger? */
|
||||||
|
grid-template-rows: repeat(3, 1fr);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* the stuff in the grid*/
|
||||||
|
section.main-stats h4{
|
||||||
|
grid-column: 1 / span 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.username{
|
||||||
|
font-size: 1.5em;
|
||||||
|
font-weight: bold;
|
||||||
|
padding-bottom: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.rank {
|
||||||
|
/* color: black; */
|
||||||
|
font-size: 1.2em;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Glittery Star Stuff */
|
||||||
|
|
||||||
|
|
||||||
|
:root {
|
||||||
|
--purple: rgb(123, 31, 162);
|
||||||
|
--violet: rgb(103, 58, 183);
|
||||||
|
--pink: rgb(244, 143, 177);
|
||||||
|
/* make shit gold? */
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes background-pan {
|
||||||
|
from {
|
||||||
|
background-position: 0% center;
|
||||||
|
}
|
||||||
|
|
||||||
|
to {
|
||||||
|
background-position: -200% center;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes scale {
|
||||||
|
from, to {
|
||||||
|
transform: scale(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
50% {
|
||||||
|
transform: scale(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes rotate {
|
||||||
|
from {
|
||||||
|
transform: rotate(0deg);
|
||||||
|
}
|
||||||
|
|
||||||
|
to {
|
||||||
|
transform: rotate(180deg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
div > .glitter {
|
||||||
|
display: inline-block;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-star {
|
||||||
|
--size: clamp(20px, 1.5vw, 30px);
|
||||||
|
|
||||||
|
animation: scale 700ms ease forwards;
|
||||||
|
display: block;
|
||||||
|
height: var(--size);
|
||||||
|
left: var(--star-left);
|
||||||
|
position: absolute;
|
||||||
|
top: var(--star-top);
|
||||||
|
width: var(--size);
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-star > svg {
|
||||||
|
animation: rotate 1000ms linear infinite;
|
||||||
|
display: block;
|
||||||
|
opacity: 0.7;
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-star > svg > path {
|
||||||
|
fill: var(--violet);
|
||||||
|
}
|
||||||
|
|
||||||
|
div > .glitter > .glitter-text {
|
||||||
|
animation: background-pan 3s linear infinite;
|
||||||
|
/* background-image: linear-gradient( */
|
||||||
|
background: linear-gradient(
|
||||||
|
to right,
|
||||||
|
var(--purple),
|
||||||
|
var(--violet),
|
||||||
|
var(--pink),
|
||||||
|
var(--purple)
|
||||||
|
);
|
||||||
|
background-size: 200%;
|
||||||
|
|
||||||
|
/* Keep these for Safari and chrome */
|
||||||
|
-webkit-background-clip: text;
|
||||||
|
-webkit-text-fill-color: transparent;
|
||||||
|
|
||||||
|
/* These are for Firefox */
|
||||||
|
background-clip: text;
|
||||||
|
color: transparent;
|
||||||
|
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
||||||
Reference in New Issue
Block a user