From 182fb135909e1d132e655e7bc029bc38c24100c0 Mon Sep 17 00:00:00 2001
From: DutchEllie <personal@quenten.nl>
Date: Tue, 19 Apr 2022 22:30:47 +0200
Subject: [PATCH] Added music player beta

---
 src/main.go        |   2 +
 src/music.go       |  51 +++++++++++++++++
 src/musicplayer.go | 136 +++++++++++++++++++++++++++++++++++++++++++++
 src/navbar.go      |   3 +
 4 files changed, 192 insertions(+)
 create mode 100644 src/music.go
 create mode 100644 src/musicplayer.go

diff --git a/src/main.go b/src/main.go
index afc505c..2a09c6b 100644
--- a/src/main.go
+++ b/src/main.go
@@ -20,11 +20,13 @@ func main() {
 	aboutpage := NewAboutPage()
 	galaxiespage := NewGalaxiesPage()
 	undertalePage := NewUndertalePage()
+	musicPage := NewMusicPage()
 	app.Route("/", homepage)
 	app.Route("/about", aboutpage)
 	app.Route("/galaxies", galaxiespage)
 	app.Route("/undertale", undertalePage)
 	app.Route("/blog", NewBlogPage())
+	app.Route("/music", musicPage)
 
 	app.Handle(getHTML, handleGetHTML)
 
diff --git a/src/music.go b/src/music.go
new file mode 100644
index 0000000..0c98f51
--- /dev/null
+++ b/src/music.go
@@ -0,0 +1,51 @@
+// Idea for this page:
+// - Make a navbar on the top for different genres and switch the pages content when clicked
+
+package main
+
+import "github.com/maxence-charriere/go-app/v9/pkg/app"
+
+type MusicPage struct {
+	app.Compo
+}
+
+func NewMusicPage() *MusicPage {
+	return &MusicPage{}
+}
+
+func (f *MusicPage) Render() app.UI {
+	return newPage().
+		Title("Music!").
+		LeftBar(
+			newHTMLBlock().
+				Class("left").
+				Class("leftbarblock").
+				Src("/web/blocks/snippets/bannerpanel.html"),
+		).
+		Main(
+			// Genre navbar above this
+			newUIBlock().
+				Class("right").
+				Class("contentblock").
+				UI(
+					app.Div().
+						Body(
+							app.P().
+								Class("m-t5").
+								Text(`I am quite picky with my music most of the time. I rarely enjoy an entire album of an artist and most artists for me have only a couple amazing songs.
+						My tastes in music are almost exclusively Japanese songs. Vocaloid is how I began and nowadays I listen to all sorts of Japanese music.
+						Here are some of the songs, artists and albums I like the most.`),
+							app.P().
+								Class("p-h3").
+								Style("color", "red").
+								Text("Warning! Player feature still in beta. Stuff can break and design is most certainly not final at all!"),
+							app.P().
+								Text("Just click one of the songs to play it."),
+							app.P().
+								Class("p-h2").
+								Text("Songs"),
+							newMusicPlayer(),
+						),
+				),
+		)
+}
diff --git a/src/musicplayer.go b/src/musicplayer.go
new file mode 100644
index 0000000..6efb9b1
--- /dev/null
+++ b/src/musicplayer.go
@@ -0,0 +1,136 @@
+package main
+
+import (
+	"fmt"
+
+	"github.com/maxence-charriere/go-app/v9/pkg/app"
+)
+
+const (
+	songRepoURL string = "" // URL where the music files are stored. Made a bit like the ApiURL
+)
+
+type song struct {
+	ITitle string
+	IID    string
+	IURL   string
+}
+
+func newSong() *song {
+	return &song{}
+}
+
+func (f *song) Title(v string) *song {
+	f.ITitle = v
+	return f
+}
+
+func (f *song) URL(v string) *song {
+	f.IURL = v
+	return f
+}
+
+func (f *song) ID(v string) *song {
+	f.IID = v
+	return f
+}
+
+type musicPlayer struct {
+	app.Compo
+
+	songs                 map[string](*song)
+	currentlySelectedSong string
+}
+
+func newMusicPlayer() *musicPlayer {
+	return &musicPlayer{
+		songs: make(map[string]*song),
+	}
+}
+
+// On... handlers
+
+func (f *musicPlayer) OnMount(ctx app.Context) {
+	ctx.Handle("switchSong", f.handleSwitchSong)
+	// Statically create all the music.
+	// I am not making a database for this shit lmao
+	// Also do not forget to at least set the currentlySelectedSong to the first one added, or at least make it point somewhere
+	f.songs["ievan-polka"] = newSong().
+		Title("Ievan Polka - Hatsune Miku").
+		URL("https://files.catbox.moe/lh229f.mp3").
+		ID("ievan-polka")
+	f.songs["tokusya-seizon"] = newSong().
+		Title("Tokusya-Seizon Wonder-la-der!! - Amane Kanata").
+		URL("https://music-website.s3.nl-ams.scw.cloud/Tokusya-Seizon%20Wonder-la-der%21%21.mp3").
+		ID("tokusya-seizon")
+
+}
+
+// Action handlers
+
+// Call with a value called "title" to switch to the right song
+func (f *musicPlayer) handleSwitchSong(ctx app.Context, a app.Action) {
+	title, ok := a.Value.(string)
+	if !ok {
+		app.Log("Error calling handleSwitchSong function. Title value was not found")
+		return
+	}
+	v, ok := f.songs[title]
+	if !ok {
+		app.Log("Error getting song. Song with title does not exist")
+		return
+	}
+
+	f.currentlySelectedSong = v.IID
+	f.Update()
+}
+
+func (f *musicPlayer) Render() app.UI {
+	// Don't forget to handle the possibility of no songs having been added and the currentlySelectedSong to be empty
+	if f.currentlySelectedSong == "" {
+		return app.Div().
+			Body(
+				app.Range(f.songs).Map(func(s string) app.UI {
+					return app.Div().
+						Style("border", "solid 1px red").
+						Style("width", "fit-content").
+						Body(
+							app.Span().
+								Style("text-decoration", "underline").
+								Style("width", "fit-content").
+								Text(f.songs[s].ITitle).
+								OnClick(func(ctx app.Context, e app.Event) {
+									ctx.NewActionWithValue("switchSong", f.songs[s].IID)
+								}),
+						)
+				}),
+			)
+	}
+	return app.Div().Body(
+		app.P().
+			Class("p-h3").
+			Text(fmt.Sprintf("Currently playing: %s", f.songs[f.currentlySelectedSong].ITitle)),
+		app.Audio().
+			Src(f.songs[f.currentlySelectedSong].IURL).
+			Controls(true).
+			AutoPlay(true),
+		// Lots of buttons of songs
+		app.Div().
+			Body(
+				app.Range(f.songs).Map(func(s string) app.UI {
+					return app.Div().
+						Style("border", "solid 1px red").
+						Style("width", "fit-content").
+						Body(
+							app.Span().
+								Style("text-decoration", "underline").
+								Style("width", "fit-content").
+								Text(f.songs[s].ITitle).
+								OnClick(func(ctx app.Context, e app.Event) {
+									ctx.NewActionWithValue("switchSong", f.songs[s].IID)
+								}),
+						)
+				}),
+			),
+	)
+}
diff --git a/src/navbar.go b/src/navbar.go
index 4021523..bb15476 100644
--- a/src/navbar.go
+++ b/src/navbar.go
@@ -20,6 +20,9 @@ func (n *navbar) Render() app.UI {
 			app.Li().Body(
 				app.A().Href("/galaxies").Text("Galaxies"),
 			),
+			app.Li().Body(
+				app.A().Href("/music").Text("Music"),
+			),
 			// Disabled for now since there are none anyway
 			app.Li().Body(
 				app.A().Href("/blog").Text("Blog"),