Move song page to a request for faster loading

Updated some info
This commit is contained in:
Michał 2023-02-26 19:24:11 +00:00
parent 70ded2c95e
commit 3613f90fa5
7 changed files with 285 additions and 97 deletions

75
app.py
View file

@ -1,11 +1,14 @@
from flask import Flask, render_template, redirect
from flask import Flask, render_template, request, jsonify
from flask_compress import Compress
import requests
import dotenv
from random import choice
import json
import requests
# Getting color palette from album art
import colorthief
LASTFM_API_KEY = dotenv.get_key('./.env', 'LASTFM')
@ -19,18 +22,15 @@ Compress(app)
#
@app.route('/')
def index():
msg = ['This is a test string',
msg = ['Don\'t cry because it\'s over, smile because it happened',
'This could go one of two ways...',
'Gwa Gwa', 'It\'s a UNIX system! I know this!',
'They turned him into a pickle, its the funnies shit I\'ve ever seen',
'Gwa Gwa',
'It\'s a UNIX system! I know this!',
'*internal screaming*',
'Don\'t forget to drink water!',
'Fluffy made this!',
'I wish we were better strangers.',
'If I were you, I\'d run now',
'SILICA GEL "DO NOT EAT".',
'AAAAAAAAAAAAAAAAAAAA',
'The weather is dry',
'Gods die too.',
'Eat hotchip and lie']
@ -47,37 +47,42 @@ def about():
return render_template('about.html')
@app.route('/music')
@app.route('/music', methods=['GET', 'POST'])
def music():
current_tracks = requests.get(
if request.method == 'POST':
current_tracks = requests.get(
f'http://ws.audioscrobbler.com/2.0/?method=user.getrecenttracks&user=Fluffy_Bean_&api_key={LASTFM_API_KEY}&limit=5&format=json')
current_tracks = json.loads(current_tracks.text)
tracks = []
for track in current_tracks['recenttracks']['track']:
nowPlaying = False
if '@attr' in track:
nowPlaying = True
tmp_track = {
'name': track['name'],
'artist': track['artist']['#text'],
'album': track['album']['#text'],
'url': track['url'],
'image': track['image'][2]['#text'],
'nowPlaying': nowPlaying,
}
current_tracks = json.loads(current_tracks.text)
tracks.append(tmp_track)
tracks = []
for track in current_tracks['recenttracks']['track']:
# As django is weird with @attr in json data
# I make a new dict with a bool for nowPlaying
nowPlaying = False
if '@attr' in track:
nowPlaying = True
# Yoink color palette from album art
color_thief = colorthief.ColorThief(requests.get(track['image'][2]['#text'], stream=True).raw)
palette = color_thief.get_palette()
tmp_track = {
'name': track['name'],
'artist': track['artist']['#text'],
'album': track['album']['#text'],
'url': track['url'],
'image': track['image'][2]['#text'],
'nowPlaying': nowPlaying,
'palette': palette[0]
}
tracks.append(tmp_track)
return jsonify(tracks)
return render_template('music.html', tracks=tracks)
@app.route('/blog')
def blog():
return render_template('blog.html')
# GET request
return render_template('music.html')
#
# ERROR HANDLERS

View file

@ -1,3 +1,5 @@
@use 'sass:map'
$black: #101010
$dark: #151515
$grey: #808080
@ -220,26 +222,136 @@ p.subtitle
overflow: hidden
$languages: ("python": #3776AB, "js": #F7DF1E, "html": #E34F26, "css": #1572B6, "sass": #CC6699, "php": #777BB4, "sql": #4479A1, "shell": #89E051, "rust": #CE422B)
$os: ("ubuntu": #E95420, "arch": #1793D1, "proxmox": #E57000, "manjaro": #35BF5C, "windows": #0078D6)
.sub_experiance
padding-left: 0.25rem !important
position: relative
color: $white !important
&::before
content: ''
width: 2px
height: 100%
position: absolute
top: 0
left: 0
background-color: $primary
border-radius: 2px
opacity: 0.5
z-index: -1
@each $lang, $color in $languages
&.#{$lang}
&::before
background-color: $color
@each $os, $color in $os
&.#{$os}
&::before
background-color: $color
&.vbad
&::before
width: 2px
&.bad
&::before
width: 10%
&.ok
&::before
width: 20%
&.good
&::before
width: 40%
&.vgood
&::before
width: 80%
&.excellent
&::before
width: 100%
span
font-size: 0.8rem
@keyframes loader
0%
width: 0
left: 0
30%
width: 100%
left: 0
60%
width: 100%
left: 100%
100%
width: 100%
left: 100%
.loader
margin: 1rem 0
width: 100%
height: 2px
position: relative
background-color: $black
overflow: hidden
&::after
content: ''
margin: 0
padding: 0
width: 0
height: 100%
position: absolute
top: 0
left: 0
background-color: $primary
animation: loader 1s ease-in-out infinite
.music
display: flex
flex-direction: column
gap: 1rem
.track
display: flex
flex-direction: row
gap: 1rem
position: relative
overflow: hidden
.music-image
.track-image
padding: 0px
width: 5rem
height: 5rem
border-radius: 2px
background-color: $black
transition: all 0.3s cubic-bezier(.86,0,.07,1)
img
margin: 0
padding: 0
width: 5rem
height: 5rem
width: 100%
height: 100%
display: block
float: left
@ -247,9 +359,12 @@ p.subtitle
border-radius: 2px
background-color: $dark
opacity: 1
object-fit: cover
.music-info
transition: all 0.2s cubic-bezier(.86,0,.07,1)
.track-info
display: flex
flex-direction: column
//justify-content: space-between
@ -273,10 +388,9 @@ p.subtitle
&:hover
color: $primary
p.music-nowplaying
p.track-nowplaying
color: $primary
@import "buttons"
@import "toast"
@ -292,9 +406,9 @@ p.music-nowplaying
p.subtitle
text-align: center
.music
padding-left: 0.5rem
border-left: 2px solid $primary
.track-image
width: 2px
height: auto
span, img
display: none
img
opacity: 0

View file

@ -7,35 +7,43 @@
</div>
<div class="content">
<h2 data-value="Meeee :3">Meeee :3</h2>
<h2 data-value="Meeeeeee">Meeeeeee</h2>
<p>Hewwo, I'm a 17 year old nerd, who likes to code and tinker with computers!</p>
<p>I'm mostly a frontend developer, with some knowlage of the backend. I also enjoy programming for the hell of it</p>
</div>
<div class="content">
<h2 data-value="Fluffy-Bean">Fluffy-Bean</h2>
<p>Fluffy Bean is a maned wolf, he reflects my personality and is my fursona</p>
<p>Refsheet made by mrHDash</p>
</div>
<img src="{{ url_for('static', filename='images/ref.png') }}" alt="Orange maned wolf sneaking under a yellow sheet" style="opacity:0" onload="fadeOnLoad(this)">
<img src="{{ url_for('static', filename='images/ref.png') }}" alt="Orange maned wolf sneaking under a yellow sheet">
<div class="content">
<h2 data-value="Experiance">Experiance</h2>
<p>
I'm quite well experianced with Python, HTML, CSS/Sass, and Shell Scripting.
And have some experiance with JavaScript, PHP, MySQL and a few other languages
</p>
<h2 data-value="Experiance and Projects">Experiance and Projects</h2>
<p>I'm quite well experianced with Python, HTML, CSS/Sass, and Shell Scripting.And have some experiance with JavaScript, PHP, MySQL and a few other languages</p>
<p>My main operating system has been Linux for about 1.5 years (Arch btw)</p>
<p>Now I have started to learn hardware and been messing around with Pi Picos!</p>
<p>Recently I have started working on a gallery, originally written in PHP for my own use before making it public</p>
<p>It is now written in Python with Flask and is open source! You can find it on <a href="https://github.com/Fluffy-Bean/onlylegs">GitHub</a>. Or on my self hosted instance of <a href="https://git.leggy.dev/Fluffy/onlylegs">Gitea</a>!</p>
</div>
<div class="content">
<h2 data-value="Projects">Projects</h2>
<p>Recently I have started working on a gallery, originally written in PHP for my own use before making it public</p>
<p>
It is now written in Python with Flask and is open source! You can find it on <a href="https://github.com/Fluffy-Bean/onlylegs">GitHub</a>.
Or on my self hosted instance of <a href="https://git.leggy.dev/Fluffy/onlylegs">Gitea</a>!
</p>
<h2 data-value="Languages">Languages</h2>
<p class="sub_experiance python good">Python <span>Good</span></p>
<p class="sub_experiance html vgood">HTML <span>Very Good</span></p>
<p class="sub_experiance css vgood">CSS <span>Very Good</span></p>
<p class="sub_experiance sass vgood">Sass/SCSS <span>Very Good</span></p>
<p class="sub_experiance js bad">JavaScript <span>Meh</span></p>
<p class="sub_experiance php good">PHP <span>Good</span></p>
<p class="sub_experiance sql ok">SQL <span>Ok</span></p>
<p class="sub_experiance shell ok">Shell Scripting <span>Ok</span></p>
<p class="sub_experiance rust vbad">Rust <span>Learning</span></p>
</div>
<div class="content">
<h2 data-value="OS'">OS'</h2>
<p class="sub_experiance ubuntu good">Ubuntu <span>Good</span></p>
<p class="sub_experiance arch vgood">Arch <span>Very Good</span></p>
<p class="sub_experiance proxmox ok">Proxmox <span>Decent</span></p>
<p class="sub_experiance manjaro bad">Manjaro <span>Breaking bad</span></p>
<p class="sub_experiance windows ok">Windows <span>Ok</span></p>
</div>
{% endblock %}

View file

@ -1,9 +0,0 @@
{% extends 'layout.html' %}
{% block nav_blog %}selected{% endblock %}
{% block content %}
<div class="content">
<h1 data-value="Blog">Blog</h1>
<p class="subtitle" data-value="*sound of crickets chirping*">*sound of crickets chirping*</p>
</div>
{% endblock %}

View file

@ -19,5 +19,5 @@
-->
</div>
<img src="{{url_for('static', filename='images/ny.png')}}" style="opacity:0" onload="fadeOnLoad(this)">
<img src="{{url_for('static', filename='images/ny.png')}}">
{% endblock %}

View file

@ -8,18 +8,12 @@
<link rel="icon" href="{{url_for('static', filename='images/taidum.png')}}">
<link rel="stylesheet" href="{{url_for('static', filename='css/style.css')}}">
<script src="{{ url_for('static', filename='js/main.js') }}" defer></script>
<script>
function fadeOnLoad(obj) {
obj.style.transition = "opacity 1s";
obj.style.opacity = 1;
}
</script>
</head>
<body>
<nav>
<a class="{% block nav_home %}{% endblock %}" href="/">Home</a>
<a class="{% block nav_cretura %}{% endblock %}" href="/cretura">Cretura</a>
<a class="{% block nav_about %}{% endblock %}" href="/about">About</a>
<a class="{% block nav_cretura %}{% endblock %}" href="/cretura">Cretura</a>
<span class="spacer"></span>
<a class="{% block nav_music %}{% endblock %}" href="/music">Music</a>
</nav>

View file

@ -2,26 +2,102 @@
{% block nav_music %}selected{% endblock %}
{% block content %}
<h1 data-value="Enslaved-Sound">Enslaved-Sound</h1>
<h1 data-value="Muuuuuuusic">Muuuuuuusic</h1>
{% for track in tracks %}
<div class="music">
<span class="music-image"><img src="{{track.image}}" style="opacity:0" onload="fadeOnLoad(this)"></span>
<div class="music-info">
{% if track.nowPlaying %}
<p class="music-nowplaying">Now Playing:</p>
<a href={{track.url}}>{{track.name}}</a>
<p>by {{track.artist}}</p>
{% else %}
<a href={{track.url}}>{{track.name}}</a>
<p>by {{track.artist}}</p>
<p>on {{track.album}}</p>
{% endif %}
</div>
</div>
{% endfor %}
<div class="music">
<span class="loader"></span>
</div>
<div class="content">
<p>Provided by <a href="http://www.last.fm">Last.fm</a></p>
</div>
<script>
function processMusic(data) {
const music = document.querySelector('.music');
music.innerHTML = '';
data = JSON.parse(data);
Object.entries(data).forEach(([key, value]) => {
// Create track container
const track = document.createElement('div');
track.classList.add('track');
// Create track image container
const trackImage = document.createElement('span');
trackImage.classList.add('track-image');
// UUUUUUUUUGHHHHHHHHHH
trackImage.style.backgroundColor = `rgb(${value.palette[0]}, ${value.palette[1]}, ${value.palette[2]})`;
// Create track image
const trackImageImg = document.createElement('img');
trackImageImg.src = value.image;
trackImage.appendChild(trackImageImg);
// Create track info container
const trackInfo = document.createElement('div');
trackInfo.classList.add('track-info');
// Create track title
const trackTitle = document.createElement('a');
trackTitle.href = value.url;
trackTitle.innerHTML = value.name;
// Create track artist
const trackArtist = document.createElement('p');
trackArtist.innerHTML = 'by ' + value.artist;
// If track is now playing, add now playing text
// Else add album name
if (value.nowPlaying) {
const trackNowPlaying = document.createElement('p');
trackNowPlaying.classList.add('track-nowplaying');
trackNowPlaying.innerHTML = 'Now Playing:';
// Append now playing and track info to track info
trackInfo.appendChild(trackNowPlaying);
trackInfo.appendChild(trackTitle);
trackInfo.appendChild(trackArtist);
} else {
const trackAlbum = document.createElement('p');
trackAlbum.innerHTML = 'on ' + value.album;
// Append track title, artist and album to track info
trackInfo.appendChild(trackTitle);
trackInfo.appendChild(trackArtist);
trackInfo.appendChild(trackAlbum);
}
// Append track image and track info to track
track.appendChild(trackImage);
track.appendChild(trackInfo);
// Append track to music
music.appendChild(track);
});
}
// Make POST request with XHR
let xhr = new XMLHttpRequest();
xhr.open('POST', '/music', true);
xhr.setRequestHeader('Content-Type', 'application/json');
xhr.send(JSON.stringify({}));
// Handle response
xhr.onloadend = function () {
if (xhr.readyState == XMLHttpRequest.DONE) {
// check if no error occurred
if (xhr.status == 200) {
processMusic(xhr.responseText);
} else {
const music = document.querySelector('.music');
music.innerHTML = '<p>Music data could not be loaded :<</p>';
}
} else {
const music = document.querySelector('.music');
music.innerHTML = '<p>Music data could not be loaded :<</p>';
}
};
</script>
{% endblock %}