diff --git a/android/app/src/main/assets/public/blah/en-us.json b/android/app/src/main/assets/public/blah/en-us.json index 33f4e976..f6640451 100644 --- a/android/app/src/main/assets/public/blah/en-us.json +++ b/android/app/src/main/assets/public/blah/en-us.json @@ -36,5 +36,13 @@ "passwords.not.match": "Passwords do not match", "password.cant.empty": "Password cannot be empty", "username.cant.empty": "Username cannot be empty", - "bad.request": "Bad request" + "bad.request": "Bad request", + + "letters": "letters", + "numbers": "numbers", + "underscores": "underscores", + + "loading.connecting": "Connecting...", + "loading.loading": "Loading...", + "loading.done": "Ready!" } \ No newline at end of file diff --git a/android/app/src/main/assets/public/index.html b/android/app/src/main/assets/public/index.html index 41dc0412..a2f4078c 100644 --- a/android/app/src/main/assets/public/index.html +++ b/android/app/src/main/assets/public/index.html @@ -8,97 +8,119 @@ - - - - - - -
- - - - - -
-
- - - - Home - - - - - - - - - Splash - - +
- Welcome to Miarven -

First Larpix client. v1.0

+

-
-
- - + +
+ + + + + + + + + + + +
+
+ + + + + + + + + + +
+ + + + Home + + + + + + + + + Splash + + +
+ + Welcome to Miarven +

First Larpix client. v1.0

+
+
+
+ +
\ No newline at end of file diff --git a/android/app/src/main/assets/public/login/index.html b/android/app/src/main/assets/public/login/index.html index c844e976..aec3363c 100644 --- a/android/app/src/main/assets/public/login/index.html +++ b/android/app/src/main/assets/public/login/index.html @@ -478,6 +478,5 @@ } } - loginHostChanged(); \ No newline at end of file diff --git a/android/app/src/main/assets/public/main.js b/android/app/src/main/assets/public/main.js index f046bf40..c07412cc 100644 --- a/android/app/src/main/assets/public/main.js +++ b/android/app/src/main/assets/public/main.js @@ -24,7 +24,7 @@ var url = `${prot}//${window.location.hostname}/_larpix`; var params = new URLSearchParams(window.location.search); try { - + var loadingStatus = document.getElementById("loadingstatus"); var collapseDmsBtn = document.getElementById("collapse-dms"); var collapseGroupsBtn = document.getElementById("collapse-groups"); @@ -49,6 +49,21 @@ try { var roomContentBar = roomContent.children[0]; + var roomTopBar = document.getElementsByTagName("roomtopbar")[1]; + + var sidebarProfile = document.getElementById("sidebar-profile"); + var sidebarProfileButton = sidebarProfile.children.item(1); + var sidebarProfileIndicator = sidebarProfile.children.item(0); + + var sidebarPfp = sidebarProfileButton.children.item(0); + + + var sidebarInbox = document.getElementById("sidebar-inbox"); + var sidebarInboxButton = sidebarInbox.children.item(1); + var sidebarInboxIndicator = sidebarInbox.children.item(0); + + + } catch (e) { } @@ -439,6 +454,103 @@ async function hashSHA3_512(input) { return hashHex; } +//placeholder pfp +function getInitials(name) { + const cleanName = (name || "").trim(); + + //name empty + if (!cleanName) return ""; + + const parts = cleanName.split(/\s+/); + + //at least 2 words + if (parts.length >= 2) { + const firstInitial = parts[0][0]; + const secondInitial = parts[parts.length - 1][0]; //from last word + return (firstInitial + secondInitial).toUpperCase(); + } + + //only 1 word with 1 letter + const word = parts[0]; + if (word.length === 1) { + return word.toUpperCase(); + } + + //1 word at least 2 letters + return word.substring(0, 2).toUpperCase(); +} +function stringToColor(str) { + let hash = 0; + for (let i = 0; i < str.length; i++) { + hash = str.charCodeAt(i) + ((hash << 5) - hash); + } + const h = Math.abs(hash) % 360; + const s = 50; + const l = 65; + + return `hsl(${h}, ${s}%, ${l}%)`; +} +function createAvatarSvg(name, size = 512) { + const initials = getInitials(name); + const color = stringToColor(name); + + const svg = ` + + + + ${initials} + + + `.trim(); + return `data:image/svg+xml;utf8,${encodeURIComponent(svg)}`; +} + +async function getAvatarUrl(username) +{ + try { + let pfpUrl = `${url}/user/storage/public/getentry?u=${username}&e=larp.profile.pfp`; + if ((await fetchAsync(pfpUrl)) == "") + { + throw Error(); + } + return pfpUrl; + } + catch (e) { + return createAvatarSvg(username); + } +} + +function updateLoadingStatus(message) { + loadingStatus.innerHTML = processBlah(message); +} + +async function loadingFadeOut() { + let loadingScreen = document.querySelector("loading"); + let mainScreen = document.querySelector("main"); + + mainScreen.style.transform = "scale(0.85)"; + mainScreen.style.opacity = "0"; + + loadingScreen.style.transform = "scale(0.85)"; + loadingScreen.style.opacity = "0"; + await delay(200); + loadingScreen.style.display = "none"; + mainScreen.style.display = ""; + await delay(200); + mainScreen.style.transform = ""; + mainScreen.style.opacity = ""; + + +} + + var blah; async function initBlahs() { @@ -457,6 +569,10 @@ async function initBlahs() { function processBlah(blahmessage) { try { + if (!blahmessage.includes(":")) { + blahmessage = `:${blahmessage}`; + } + let split = blahmessage.split(":"); let values = []; try { @@ -468,10 +584,9 @@ function processBlah(blahmessage) { let valueslist = ""; for (let i = 0; i < values.length; i++) { - let value = values[i]; - valueslist+=`${values[i]}, `; - processBlah(value); - + let value = processBlah(values[i]); + valueslist+=`${value}, `; + message = message.replaceAll(`{${i}}`, value); } valueslist = valueslist.slice(0, -2); @@ -479,7 +594,6 @@ function processBlah(blahmessage) { message = message.replaceAll('{all}', valueslist); } - return message; } catch (e) @@ -505,6 +619,8 @@ async function mainJS() { if (localStorage.getItem('lang') != null) { lang = localStorage.getItem('lang'); } + + await start(); } username = localStorage.getItem('username'); password = localStorage.getItem('password'); @@ -518,7 +634,14 @@ collapseGroupsBtn.addEventListener("click", () => { collapseGroupsBtn.classList.toggle("collapsed"); }); -addDmBtn.addEventListener("click", () => { +addDmBtn.addEventListener("click", async () => { + roomContentMain.style.transform = "scale(0.85)"; + roomContentMain.style.opacity = "0"; + await delay(200); + + roomTopBar.innerHTML = "Invite to dm"; + roomDetailsBar.style.display = "none"; + roomContentMain.innerHTML = `
@@ -528,7 +651,7 @@ addDmBtn.addEventListener("click", () => {
- +
- ` + `; + roomContentMain.style.transform = ""; + roomContentMain.style.opacity = ""; }); -addGroupBtn.addEventListener("click", () => { - +addGroupBtn.addEventListener("click", async () => { + roomContentMain.style.transform = "scale(0.85)"; + roomContentMain.style.opacity = "0"; + await delay(200); + + roomTopBar.innerHTML = "Create group"; + roomDetailsBar.style.display = "none"; + + roomContentMain.innerHTML = + ` +
+ + Create Group +

Create a private, encrypted group

+
+
+ + +
+
+ +
+
+ `; + roomContentMain.style.transform = ""; + roomContentMain.style.opacity = ""; }); @@ -557,3 +708,55 @@ sidebarAddButton.addEventListener("mouseleave", () => { sidebarAddIndicator.classList.remove("hover"); }); +sidebarProfileButton.addEventListener("mouseenter", () => { + sidebarProfileIndicator.classList.add("hover"); +}); +sidebarProfileButton.addEventListener("mouseleave", () => { + sidebarProfileIndicator.classList.remove("hover"); +}); + +sidebarInboxButton.addEventListener("mouseenter", () => { + sidebarInboxIndicator.classList.add("hover"); +}); +sidebarInboxButton.addEventListener("mouseleave", () => { + sidebarInboxIndicator.classList.remove("hover"); +}); + + +function gotoSideProfilePopup() { + +} +function gotoInbox() { + +} +async function gotoCreateSpace() { + roomContentMain.style.transform = "scale(0.85)"; + roomContentMain.style.opacity = "0"; + await delay(200); + + roomTopBar.innerHTML = "Create space"; + roomDetailsBar.style.display = "none"; + roomContentMain.innerHTML = + ` +
+ + Create Space +

Create a space for your community

+
+
+ + +
+
+ +
+
+ `; + roomContentMain.style.transform = ""; + roomContentMain.style.opacity = ""; +} +function gotoHome() { + +} diff --git a/android/app/src/main/assets/public/style.css b/android/app/src/main/assets/public/style.css index 663eea28..03d3858c 100644 --- a/android/app/src/main/assets/public/style.css +++ b/android/app/src/main/assets/public/style.css @@ -40,9 +40,16 @@ html { body { padding-top: env(safe-area-inset-top); background-color: var(--main-bg-color); + overflow: hidden; +} +main, loading, body { display: flex; height: 100dvh; - overflow: hidden; +} +loading { + justify-content: center; + align-items: center; + width: 100%; } * { font-size: 1rem; @@ -68,6 +75,11 @@ button, input { align-items: center; justify-content: flex-start; border: var(--border-width) solid var(--light-border-color); + + backface-visibility: hidden; + transform: translateZ(0); + will-change: transform; + transform-origin: center center; } input { padding-left: calc(var(--button-margin) * 2); @@ -120,11 +132,16 @@ indicator.active { height: var(--icon-button-height); width: var(--icon-button-height); justify-content: center; + overflow: hidden; } .icon-button svg { width: var(--icon-button-size); height: var(--icon-button-size); } +.icon-button img { + width: calc(var(--icon-button-height) - (var(--border-width) * 2)); + height: calc(var(--icon-button-height) - (var(--border-width) * 2)); +} button:hover, input:hover { background-color: rgba(255, 255, 255, 0.1); } @@ -340,4 +357,9 @@ herotitle { .submit-button:hover { background-color: rgba(255, 255, 255, 0.5); +} + + +.bottom-element { + margin-top: auto; } \ No newline at end of file diff --git a/electron/assets/icon.png b/electron/assets/icon.png index eaeb16da..6132e963 100644 Binary files a/electron/assets/icon.png and b/electron/assets/icon.png differ diff --git a/icons/icon.png b/icons/icon.png index eaeb16da..6132e963 100644 Binary files a/icons/icon.png and b/icons/icon.png differ diff --git a/webroot/blah/en-us.json b/webroot/blah/en-us.json index 33f4e976..f6640451 100644 --- a/webroot/blah/en-us.json +++ b/webroot/blah/en-us.json @@ -36,5 +36,13 @@ "passwords.not.match": "Passwords do not match", "password.cant.empty": "Password cannot be empty", "username.cant.empty": "Username cannot be empty", - "bad.request": "Bad request" + "bad.request": "Bad request", + + "letters": "letters", + "numbers": "numbers", + "underscores": "underscores", + + "loading.connecting": "Connecting...", + "loading.loading": "Loading...", + "loading.done": "Ready!" } \ No newline at end of file diff --git a/webroot/index.html b/webroot/index.html index 4f7e103f..a2f4078c 100644 --- a/webroot/index.html +++ b/webroot/index.html @@ -8,104 +8,119 @@ - - - - - - -
- - - - - -
- - - - - -
- - - - Home - - - - - - - - - Splash - - +
- Welcome to Miarven -

First Larpix client. v1.0

+

-
-
- - + +
+ + + + + + + + + + + +
+
+ + + + + + + + + + +
+ + + + Home + + + + + + + + + Splash + + +
+ + Welcome to Miarven +

First Larpix client. v1.0

+
+
+
+ +
\ No newline at end of file diff --git a/webroot/login/index.html b/webroot/login/index.html index c844e976..aec3363c 100644 --- a/webroot/login/index.html +++ b/webroot/login/index.html @@ -478,6 +478,5 @@ } } - loginHostChanged(); \ No newline at end of file diff --git a/webroot/main.js b/webroot/main.js index c7572d02..c07412cc 100644 --- a/webroot/main.js +++ b/webroot/main.js @@ -24,7 +24,7 @@ var url = `${prot}//${window.location.hostname}/_larpix`; var params = new URLSearchParams(window.location.search); try { - + var loadingStatus = document.getElementById("loadingstatus"); var collapseDmsBtn = document.getElementById("collapse-dms"); var collapseGroupsBtn = document.getElementById("collapse-groups"); @@ -54,7 +54,10 @@ try { var sidebarProfile = document.getElementById("sidebar-profile"); var sidebarProfileButton = sidebarProfile.children.item(1); var sidebarProfileIndicator = sidebarProfile.children.item(0); - + + var sidebarPfp = sidebarProfileButton.children.item(0); + + var sidebarInbox = document.getElementById("sidebar-inbox"); var sidebarInboxButton = sidebarInbox.children.item(1); var sidebarInboxIndicator = sidebarInbox.children.item(0); @@ -451,6 +454,103 @@ async function hashSHA3_512(input) { return hashHex; } +//placeholder pfp +function getInitials(name) { + const cleanName = (name || "").trim(); + + //name empty + if (!cleanName) return ""; + + const parts = cleanName.split(/\s+/); + + //at least 2 words + if (parts.length >= 2) { + const firstInitial = parts[0][0]; + const secondInitial = parts[parts.length - 1][0]; //from last word + return (firstInitial + secondInitial).toUpperCase(); + } + + //only 1 word with 1 letter + const word = parts[0]; + if (word.length === 1) { + return word.toUpperCase(); + } + + //1 word at least 2 letters + return word.substring(0, 2).toUpperCase(); +} +function stringToColor(str) { + let hash = 0; + for (let i = 0; i < str.length; i++) { + hash = str.charCodeAt(i) + ((hash << 5) - hash); + } + const h = Math.abs(hash) % 360; + const s = 50; + const l = 65; + + return `hsl(${h}, ${s}%, ${l}%)`; +} +function createAvatarSvg(name, size = 512) { + const initials = getInitials(name); + const color = stringToColor(name); + + const svg = ` + + + + ${initials} + + + `.trim(); + return `data:image/svg+xml;utf8,${encodeURIComponent(svg)}`; +} + +async function getAvatarUrl(username) +{ + try { + let pfpUrl = `${url}/user/storage/public/getentry?u=${username}&e=larp.profile.pfp`; + if ((await fetchAsync(pfpUrl)) == "") + { + throw Error(); + } + return pfpUrl; + } + catch (e) { + return createAvatarSvg(username); + } +} + +function updateLoadingStatus(message) { + loadingStatus.innerHTML = processBlah(message); +} + +async function loadingFadeOut() { + let loadingScreen = document.querySelector("loading"); + let mainScreen = document.querySelector("main"); + + mainScreen.style.transform = "scale(0.85)"; + mainScreen.style.opacity = "0"; + + loadingScreen.style.transform = "scale(0.85)"; + loadingScreen.style.opacity = "0"; + await delay(200); + loadingScreen.style.display = "none"; + mainScreen.style.display = ""; + await delay(200); + mainScreen.style.transform = ""; + mainScreen.style.opacity = ""; + + +} + + var blah; async function initBlahs() { @@ -469,6 +569,10 @@ async function initBlahs() { function processBlah(blahmessage) { try { + if (!blahmessage.includes(":")) { + blahmessage = `:${blahmessage}`; + } + let split = blahmessage.split(":"); let values = []; try { @@ -480,10 +584,9 @@ function processBlah(blahmessage) { let valueslist = ""; for (let i = 0; i < values.length; i++) { - let value = values[i]; - valueslist+=`${values[i]}, `; - processBlah(value); - + let value = processBlah(values[i]); + valueslist+=`${value}, `; + message = message.replaceAll(`{${i}}`, value); } valueslist = valueslist.slice(0, -2); @@ -491,7 +594,6 @@ function processBlah(blahmessage) { message = message.replaceAll('{all}', valueslist); } - return message; } catch (e) @@ -517,6 +619,8 @@ async function mainJS() { if (localStorage.getItem('lang') != null) { lang = localStorage.getItem('lang'); } + + await start(); } username = localStorage.getItem('username'); password = localStorage.getItem('password'); @@ -530,9 +634,14 @@ collapseGroupsBtn.addEventListener("click", () => { collapseGroupsBtn.classList.toggle("collapsed"); }); -addDmBtn.addEventListener("click", () => { +addDmBtn.addEventListener("click", async () => { + roomContentMain.style.transform = "scale(0.85)"; + roomContentMain.style.opacity = "0"; + await delay(200); + roomTopBar.innerHTML = "Invite to dm"; roomDetailsBar.style.display = "none"; + roomContentMain.innerHTML = `
@@ -551,10 +660,17 @@ addDmBtn.addEventListener("click", () => {
`; + roomContentMain.style.transform = ""; + roomContentMain.style.opacity = ""; }); -addGroupBtn.addEventListener("click", () => { +addGroupBtn.addEventListener("click", async () => { + roomContentMain.style.transform = "scale(0.85)"; + roomContentMain.style.opacity = "0"; + await delay(200); + roomTopBar.innerHTML = "Create group"; roomDetailsBar.style.display = "none"; + roomContentMain.innerHTML = `
@@ -573,6 +689,8 @@ addGroupBtn.addEventListener("click", () => {
`; + roomContentMain.style.transform = ""; + roomContentMain.style.opacity = ""; }); @@ -608,7 +726,14 @@ sidebarInboxButton.addEventListener("mouseleave", () => { function gotoSideProfilePopup() { } -function gotoCreateSpace() { +function gotoInbox() { + +} +async function gotoCreateSpace() { + roomContentMain.style.transform = "scale(0.85)"; + roomContentMain.style.opacity = "0"; + await delay(200); + roomTopBar.innerHTML = "Create space"; roomDetailsBar.style.display = "none"; roomContentMain.innerHTML = @@ -629,6 +754,8 @@ function gotoCreateSpace() { `; + roomContentMain.style.transform = ""; + roomContentMain.style.opacity = ""; } function gotoHome() { diff --git a/webroot/pfpexamp.png b/webroot/pfpexamp.png deleted file mode 100644 index 416243bb..00000000 Binary files a/webroot/pfpexamp.png and /dev/null differ diff --git a/webroot/style.css b/webroot/style.css index 934879a8..03d3858c 100644 --- a/webroot/style.css +++ b/webroot/style.css @@ -40,9 +40,16 @@ html { body { padding-top: env(safe-area-inset-top); background-color: var(--main-bg-color); + overflow: hidden; +} +main, loading, body { display: flex; height: 100dvh; - overflow: hidden; +} +loading { + justify-content: center; + align-items: center; + width: 100%; } * { font-size: 1rem;