Add kumos.
This commit is contained in:
parent
8a2c269d26
commit
964bd2e808
18 changed files with 427 additions and 23 deletions
|
|
@ -1,5 +1,5 @@
|
||||||
{
|
{
|
||||||
"lastFetched": "2026-07-05T21:48:17.927Z",
|
"lastFetched": "2026-07-05T22:01:02.267Z",
|
||||||
"posts": [
|
"posts": [
|
||||||
{
|
{
|
||||||
"date": "2026-07-03T01:51:37.604Z",
|
"date": "2026-07-03T01:51:37.604Z",
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,7 @@ import readingTime from 'eleventy-plugin-reading-time';
|
||||||
|
|
||||||
// import i18n from "./_data/i18n.js";
|
// import i18n from "./_data/i18n.js";
|
||||||
|
|
||||||
const production = (process.env.GITHUB_ACTIONS || process.env.FORGEJO_ACTIONS);
|
const production = (process.env.GITHUB_ACTIONS || process.env.FORGEJO_ACTIONS || process.env.IS_PRODUCTION);
|
||||||
console.log("Production:", production ? "true" : "false");
|
console.log("Production:", production ? "true" : "false");
|
||||||
|
|
||||||
export default function (eleventyConfig) {
|
export default function (eleventyConfig) {
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,7 @@
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"build": "npx @11ty/eleventy",
|
"build": "npx @11ty/eleventy",
|
||||||
"serve": "npx @11ty/eleventy --serve",
|
"serve": "npx @11ty/eleventy --serve",
|
||||||
|
"production": "IS_PRODUCTION=true npx @11ty/eleventy --serve",
|
||||||
"test": "echo \"Error: no test specified\" && exit 1"
|
"test": "echo \"Error: no test specified\" && exit 1"
|
||||||
},
|
},
|
||||||
"keywords": [],
|
"keywords": [],
|
||||||
|
|
|
||||||
|
|
@ -113,7 +113,8 @@ module.exports = {
|
||||||
sfxCheckboxAlt: "Sound effects",
|
sfxCheckboxAlt: "Sound effects",
|
||||||
videoArtworkAlt: "Video artwork",
|
videoArtworkAlt: "Video artwork",
|
||||||
songSelectAlt: "Song selector",
|
songSelectAlt: "Song selector",
|
||||||
guestbookWarning: "Load guestbook widget? You're subject to <a href='https://iframe.chat/tos.html'>Chattable's terms of service</a>."
|
guestbookWarning: "Load guestbook widget? You're subject to <a href='https://iframe.chat/tos.html'>Chattable's terms of service</a>.",
|
||||||
|
dontAskAgain: "Don't ask again"
|
||||||
},
|
},
|
||||||
pt: {
|
pt: {
|
||||||
language: "português",
|
language: "português",
|
||||||
|
|
@ -202,6 +203,7 @@ module.exports = {
|
||||||
sfxCheckboxAlt: "Efeitos sonoros",
|
sfxCheckboxAlt: "Efeitos sonoros",
|
||||||
videoArtworkAlt: "Capa do vídeo",
|
videoArtworkAlt: "Capa do vídeo",
|
||||||
songSelectAlt: "Seletor de música",
|
songSelectAlt: "Seletor de música",
|
||||||
guestbookWarning: "Carregar o guestbook? Você estará sujeito aos <a href='https://iframe.chat/tos.html'>termos de uso do Chattable</a>."
|
guestbookWarning: "Carregar o guestbook? Você estará sujeito aos <a href='https://iframe.chat/tos.html'>termos de uso do Chattable</a>.",
|
||||||
|
dontAskAgain: "Não pergunte novamente"
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
<script src="https://iframe.chat/scripts/main.min.js"></script>
|
<script src="https://iframe.chat/scripts/main.min.js"></script>
|
||||||
<iframe src="{{ ('/' ~ langKey ~ '/guestbook') | url }}" id="chattable"></iframe>
|
<iframe src="{{ ('/' ~ langKey ~ '/iframe/guestbook') | url }}" id="chattable"></iframe>
|
||||||
<script>
|
<script>
|
||||||
chattable.initialize({
|
chattable.initialize({
|
||||||
theme: "moderno"
|
theme: "moderno"
|
||||||
|
|
|
||||||
|
|
@ -1,14 +0,0 @@
|
||||||
---
|
|
||||||
pagination:
|
|
||||||
data: i18n
|
|
||||||
size: 1
|
|
||||||
alias: langKey
|
|
||||||
permalink: "/{{ langKey }}/guestbook/index.html"
|
|
||||||
layout: iframe.njk
|
|
||||||
title: Adrian Victor:Guestbook
|
|
||||||
headerLink: social
|
|
||||||
---
|
|
||||||
<main>
|
|
||||||
<p>{{ i18n[langKey].guestbookWarning | safe }}</p>
|
|
||||||
<button id="guestbookConfirmButton" onClick="window.location.href = 'https://iframe.chat/embed?chat=17048300'" style="margin-top: auto;">Load</button>
|
|
||||||
</main>
|
|
||||||
28
site/iframe/guestbook.njk
Normal file
28
site/iframe/guestbook.njk
Normal file
|
|
@ -0,0 +1,28 @@
|
||||||
|
---
|
||||||
|
pagination:
|
||||||
|
data: i18n
|
||||||
|
size: 1
|
||||||
|
alias: langKey
|
||||||
|
permalink: "/{{ langKey }}/iframe/guestbook/index.html"
|
||||||
|
layout: iframe.njk
|
||||||
|
title: Adrian Victor:Guestbook
|
||||||
|
headerLink: social
|
||||||
|
---
|
||||||
|
<script defer>
|
||||||
|
if (localStorage.getItem("autoLoadGuestBook") == "true") {
|
||||||
|
window.location.href = 'https://iframe.chat/embed?chat=17048300';
|
||||||
|
}
|
||||||
|
|
||||||
|
function loadGuestbook() {
|
||||||
|
const askAgain = document.querySelector("#dontAskAgain").value;
|
||||||
|
if (askAgain) {
|
||||||
|
localStorage.setItem("autoLoadGuestbook", true);
|
||||||
|
}
|
||||||
|
window.location.href = 'https://iframe.chat/embed?chat=17048300';
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
<main>
|
||||||
|
<p>{{ i18n[langKey].guestbookWarning | safe }}</p>
|
||||||
|
<label><input id="dontAskAgain" type="checkbox" style="margin-right: .4em;">{{ i18n[langKey].dontAskAgain }}</label>
|
||||||
|
<div style="margin-top: 1em;"><button id="guestbookConfirmButton" style="margin-top: auto;" onclick="loadGuestbook()">Load</button></div>
|
||||||
|
</main>
|
||||||
3
site/misc/kumaos/en.json
Normal file
3
site/misc/kumaos/en.json
Normal file
|
|
@ -0,0 +1,3 @@
|
||||||
|
{
|
||||||
|
"pageDescription": "Operating system written in JS."
|
||||||
|
}
|
||||||
29
site/misc/kumaos/index.njk
Normal file
29
site/misc/kumaos/index.njk
Normal file
|
|
@ -0,0 +1,29 @@
|
||||||
|
---
|
||||||
|
layout: text.njk
|
||||||
|
pagination:
|
||||||
|
data: languages
|
||||||
|
size: 1
|
||||||
|
alias: langKey
|
||||||
|
pageTitle: KumaOS
|
||||||
|
---
|
||||||
|
{% from "macros.njk" import i88x31 with context %}
|
||||||
|
|
||||||
|
<script type="module" src="{{ '/static/kumos/kernel.mjs' | url }}" defer></script>
|
||||||
|
<script type="module" src="{{ '/static/kumos/shell.mjs' | url }}" defer></script>
|
||||||
|
<script type="module" src="{{ '/static/kumos/guestbook.mjs' | url }}" defer></script>
|
||||||
|
<script type="module" src="{{ '/static/kumos/browser.mjs' | url }}" defer></script>
|
||||||
|
<script type="module" src="{{ '/static/kumos/apps.mjs' | url }}" defer></script>
|
||||||
|
<script type="module" src="{{ '/static/kumos/taskmanager.mjs' | url }}" defer></script>
|
||||||
|
<main>
|
||||||
|
<!-- <script src="https://iframe.chat/scripts/main.min.js"></script> -->
|
||||||
|
<!-- <div class="window" id="guestbookWindow">
|
||||||
|
<div class="windowHeader" id="guestbookWindowHeader">
|
||||||
|
<p>Guestbook</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<script>
|
||||||
|
chattable.initialize({
|
||||||
|
theme: "moderno"
|
||||||
|
});
|
||||||
|
</script> -->
|
||||||
|
</main>
|
||||||
3
site/misc/kumaos/pt.json
Normal file
3
site/misc/kumaos/pt.json
Normal file
|
|
@ -0,0 +1,3 @@
|
||||||
|
{
|
||||||
|
"pageDescription": "Sistema operacional em JS."
|
||||||
|
}
|
||||||
29
static/kumos/apps.mjs
Normal file
29
static/kumos/apps.mjs
Normal file
|
|
@ -0,0 +1,29 @@
|
||||||
|
import { Application, Window, promoteWindow, registerApplication, getScreenRoot, getApplications } from "./kernel.mjs";
|
||||||
|
|
||||||
|
const app = new Application('apps', (p) => {
|
||||||
|
const w = new Window();
|
||||||
|
w.setTitle("App list");
|
||||||
|
w.content.style.padding = "1rem";
|
||||||
|
|
||||||
|
const list = document.createElement("ul");
|
||||||
|
getApplications().forEach(app => {
|
||||||
|
const item = document.createElement("li");
|
||||||
|
const link = document.createElement("a");
|
||||||
|
link.innerText = app.name;
|
||||||
|
link.addEventListener('click', () => app.fn());
|
||||||
|
item.appendChild(link);
|
||||||
|
list.appendChild(item);
|
||||||
|
})
|
||||||
|
|
||||||
|
w.content.appendChild(list);
|
||||||
|
|
||||||
|
w.close.addEventListener('click', () => {
|
||||||
|
p.detach();
|
||||||
|
w.destroy();
|
||||||
|
});
|
||||||
|
|
||||||
|
getScreenRoot().appendChild(w.window);
|
||||||
|
promoteWindow(w);
|
||||||
|
})
|
||||||
|
|
||||||
|
registerApplication(app);
|
||||||
32
static/kumos/browser.mjs
Normal file
32
static/kumos/browser.mjs
Normal file
|
|
@ -0,0 +1,32 @@
|
||||||
|
import { Application, Window, promoteWindow, registerApplication, getScreenRoot } from "./kernel.mjs";
|
||||||
|
|
||||||
|
const app = new Application('browser', (p) => {
|
||||||
|
const w = new Window();
|
||||||
|
w.setTitle("Web browser");
|
||||||
|
const iframe = document.createElement("iframe");
|
||||||
|
iframe.src = "https://adrianvic.github.io";
|
||||||
|
iframe.style.height = "100%";
|
||||||
|
const searchBar = document.createElement("div");
|
||||||
|
searchBar.style.display = "flex";
|
||||||
|
const search = document.createElement("input");
|
||||||
|
search.style.width = "100%";
|
||||||
|
const searchButton = document.createElement("button");
|
||||||
|
searchBar.appendChild(search);
|
||||||
|
searchBar.appendChild(searchButton);
|
||||||
|
search.type = "text";
|
||||||
|
iframe.addEventListener('load', () => search.value = iframe.src);
|
||||||
|
searchButton.innerText = "go";
|
||||||
|
searchButton.addEventListener('click', () => iframe.src = search.value);
|
||||||
|
w.content.appendChild(searchBar);
|
||||||
|
w.content.appendChild(iframe);
|
||||||
|
|
||||||
|
getScreenRoot().appendChild(w.window);
|
||||||
|
promoteWindow(w);
|
||||||
|
|
||||||
|
w.close.addEventListener('click', () => {
|
||||||
|
p.detach();
|
||||||
|
w.destroy();
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
registerApplication(app);
|
||||||
38
static/kumos/guestbook.mjs
Normal file
38
static/kumos/guestbook.mjs
Normal file
|
|
@ -0,0 +1,38 @@
|
||||||
|
import { Application, Window, promoteWindow, registerApplication, getScreenRoot, getProcList } from "./kernel.mjs";
|
||||||
|
import { notify } from "./shell.mjs";
|
||||||
|
|
||||||
|
function draw(p) {
|
||||||
|
const w = new Window();
|
||||||
|
w.setTitle("Guestbook");
|
||||||
|
w.content.innerHTML = `
|
||||||
|
<script src="https://iframe.chat/scripts/main.min.js"></script>
|
||||||
|
<iframe class="windowContent" src="https://iframe.chat/embed?chat=17048300" id="chattable"></iframe>
|
||||||
|
<script>chattable.initialize({ theme: "moderno" });</script>
|
||||||
|
`
|
||||||
|
|
||||||
|
getScreenRoot().appendChild(w.window);
|
||||||
|
promoteWindow(w);
|
||||||
|
|
||||||
|
w.close.addEventListener('click', () => {
|
||||||
|
p.detach();
|
||||||
|
w.destroy();
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
function main(p) {
|
||||||
|
let running = false;
|
||||||
|
getProcList().forEach(proc => {
|
||||||
|
if (proc.name == 'guestbook' && proc != p) {
|
||||||
|
notify("Guestbook", "Guestbook is already running!")
|
||||||
|
p.detach();
|
||||||
|
running = true;
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
if (!running) {
|
||||||
|
draw(p);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const app = new Application('guestbook', main);
|
||||||
|
registerApplication(app);
|
||||||
125
static/kumos/kernel.mjs
Normal file
125
static/kumos/kernel.mjs
Normal file
|
|
@ -0,0 +1,125 @@
|
||||||
|
const language = "en";
|
||||||
|
const procList = [];
|
||||||
|
|
||||||
|
export class Process {
|
||||||
|
constructor(app) {
|
||||||
|
this.pid = procList.length == 0 ? 0 : procList[procList.length - 1].pid + 1;
|
||||||
|
this.name = app.name;
|
||||||
|
procList.push(this);
|
||||||
|
app.fn(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
detach() {
|
||||||
|
procList.splice(procList.indexOf(this), 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export class Application {
|
||||||
|
constructor(name, fn) {
|
||||||
|
this.fn = fn;
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export class Window {
|
||||||
|
constructor() {
|
||||||
|
// Window
|
||||||
|
const w = document.createElement("div");
|
||||||
|
w.classList.add("window");
|
||||||
|
this.window = w;
|
||||||
|
|
||||||
|
// Header
|
||||||
|
const h = document.createElement("div");
|
||||||
|
h.classList.add("windowHeader");
|
||||||
|
this.header = h;
|
||||||
|
|
||||||
|
// Title
|
||||||
|
const title = document.createElement("p");
|
||||||
|
title.classList.add("windowHeaderTitle");
|
||||||
|
this.title = title;
|
||||||
|
|
||||||
|
// Close button
|
||||||
|
const close = document.createElement("button");
|
||||||
|
close.innerText = "close";
|
||||||
|
close.classList.add("windowHeaderButton");
|
||||||
|
close.classList.add("windowHeaderButtonClose");
|
||||||
|
this.close = close;
|
||||||
|
|
||||||
|
// Content
|
||||||
|
const c = document.createElement("div");
|
||||||
|
c.classList.add("windowContent");
|
||||||
|
this.content = c;
|
||||||
|
|
||||||
|
// Building
|
||||||
|
h.appendChild(title);
|
||||||
|
h.appendChild(close);
|
||||||
|
w.appendChild(h);
|
||||||
|
w.appendChild(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
setTitle(title) {
|
||||||
|
this.title.innerText = title;
|
||||||
|
}
|
||||||
|
|
||||||
|
destroy() {
|
||||||
|
this.window.remove();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function promoteWindow(window) {
|
||||||
|
const header = window.header;
|
||||||
|
const elmnt = window.window;
|
||||||
|
|
||||||
|
header.style.cursor = 'move';
|
||||||
|
|
||||||
|
header.onmousedown = (e) => {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
|
let pos3 = e.clientX;
|
||||||
|
let pos4 = e.clientY;
|
||||||
|
|
||||||
|
const startTop = elmnt.offsetTop;
|
||||||
|
const startLeft = elmnt.offsetLeft;
|
||||||
|
|
||||||
|
document.onmouseup = closeDragElement;
|
||||||
|
document.onmousemove = elementDrag;
|
||||||
|
|
||||||
|
function elementDrag(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
const pos1 = pos3 - e.clientX;
|
||||||
|
const pos2 = pos4 - e.clientY;
|
||||||
|
pos3 = e.clientX;
|
||||||
|
pos4 = e.clientY;
|
||||||
|
|
||||||
|
elmnt.style.top = (elmnt.offsetTop - pos2) + "px";
|
||||||
|
elmnt.style.left = (elmnt.offsetLeft - pos1) + "px";
|
||||||
|
}
|
||||||
|
|
||||||
|
function closeDragElement() {
|
||||||
|
document.onmouseup = null;
|
||||||
|
document.onmousemove = null;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getScreenRoot() {
|
||||||
|
return document.querySelector('body');
|
||||||
|
}
|
||||||
|
|
||||||
|
const applications = [];
|
||||||
|
|
||||||
|
export function getApplications() {
|
||||||
|
return applications;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function registerApplication(application) {
|
||||||
|
applications.push(application);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getLanguage() {
|
||||||
|
return language;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getProcList() {
|
||||||
|
return procList;
|
||||||
|
}
|
||||||
36
static/kumos/shell.mjs
Normal file
36
static/kumos/shell.mjs
Normal file
|
|
@ -0,0 +1,36 @@
|
||||||
|
import { getScreenRoot, getApplications, Process } from "./kernel.mjs";
|
||||||
|
import { showNotification } from "../scripts/notification.js";
|
||||||
|
|
||||||
|
export function notify(title, text, time) {
|
||||||
|
showNotification(title, text, time);
|
||||||
|
}
|
||||||
|
|
||||||
|
function runApp(name) {
|
||||||
|
let launched = false;
|
||||||
|
getApplications().forEach(app => {
|
||||||
|
if (app.name == name) {
|
||||||
|
new Process(app);
|
||||||
|
launched = true;
|
||||||
|
}
|
||||||
|
})
|
||||||
|
if (!launched) alert("Not found.");
|
||||||
|
}
|
||||||
|
|
||||||
|
function createShell() {
|
||||||
|
const bar = document.createElement('div');
|
||||||
|
bar.classList.add("kumosBar");
|
||||||
|
|
||||||
|
const run = document.createElement('input');
|
||||||
|
const runButton = document.createElement('button');
|
||||||
|
run.type = "text";
|
||||||
|
runButton.innerText = "Run";
|
||||||
|
runButton.id = "kumosBarRunButton"
|
||||||
|
runButton.addEventListener('click', () => runApp(run.value));
|
||||||
|
bar.appendChild(run);
|
||||||
|
bar.appendChild(runButton);
|
||||||
|
|
||||||
|
getScreenRoot().appendChild(bar);
|
||||||
|
}
|
||||||
|
|
||||||
|
createShell();
|
||||||
|
showNotification("KumOS Shell", "Welcome to KumOS, everything is work-in-progress! Try running apps to see available packages.", 10000);
|
||||||
34
static/kumos/taskmanager.mjs
Normal file
34
static/kumos/taskmanager.mjs
Normal file
|
|
@ -0,0 +1,34 @@
|
||||||
|
import { Application, Window, promoteWindow, registerApplication, getScreenRoot, getProcList } from "./kernel.mjs";
|
||||||
|
|
||||||
|
const app = new Application('task', (p) => {
|
||||||
|
function update() {
|
||||||
|
w.content.innerHTML = ``;
|
||||||
|
const list = document.createElement("ul");
|
||||||
|
getProcList().forEach(proc => {
|
||||||
|
const item = document.createElement("li");
|
||||||
|
const link = document.createElement("a");
|
||||||
|
link.innerText = `${proc.pid} -> ${proc.name}`;
|
||||||
|
item.appendChild(link);
|
||||||
|
list.appendChild(item);
|
||||||
|
})
|
||||||
|
|
||||||
|
w.content.appendChild(list);
|
||||||
|
}
|
||||||
|
|
||||||
|
const w = new Window();
|
||||||
|
w.setTitle("Task Manager");
|
||||||
|
w.content.style.padding = "1rem";
|
||||||
|
|
||||||
|
const task = setInterval(update, 100);
|
||||||
|
|
||||||
|
w.close.addEventListener('click', () => {
|
||||||
|
clearInterval(task);
|
||||||
|
p.detach();
|
||||||
|
w.destroy();
|
||||||
|
});
|
||||||
|
|
||||||
|
getScreenRoot().appendChild(w.window);
|
||||||
|
promoteWindow(w);
|
||||||
|
})
|
||||||
|
|
||||||
|
registerApplication(app);
|
||||||
|
|
@ -1169,10 +1169,68 @@ header div:first-child {
|
||||||
|
|
||||||
.iframe {
|
.iframe {
|
||||||
padding: 1rem;
|
padding: 1rem;
|
||||||
|
font-size: medium;
|
||||||
}
|
}
|
||||||
|
|
||||||
.iframe p {
|
/* KumOS */
|
||||||
font-size: medium;
|
|
||||||
|
.window {
|
||||||
|
position: absolute;
|
||||||
|
z-index: 9;
|
||||||
|
/* background-color: #f1f1f1; */
|
||||||
|
width: 300px;
|
||||||
|
height: 300px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
resize: both;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
.windowHeader {
|
||||||
|
padding: 10px;
|
||||||
|
cursor: move;
|
||||||
|
z-index: 10;
|
||||||
|
background-color: rgba(0, 0, 0, 0.6);
|
||||||
|
color: #fff;
|
||||||
|
flex: 0 0 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.windowContent {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
flex: 1 1 auto;
|
||||||
|
border: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.windowContent {
|
||||||
|
overflow: hidden;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
background-color: black;
|
||||||
|
}
|
||||||
|
|
||||||
|
.windowHeader {
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
|
.windowHeaderTitle {
|
||||||
|
margin: 0px;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.kumosBar {
|
||||||
|
position: fixed;
|
||||||
|
left: 0;
|
||||||
|
bottom: 0;
|
||||||
|
width: 100%;
|
||||||
|
background-color: var(--theme-color);
|
||||||
|
padding: .4em;
|
||||||
|
display: flex;
|
||||||
|
gap: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.kumosBar * {
|
||||||
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Animations */
|
/* Animations */
|
||||||
|
|
|
||||||
|
|
@ -3,7 +3,7 @@ import { registerElementHint } from "./tips.js";
|
||||||
const notificationBox = document.createElement('div');
|
const notificationBox = document.createElement('div');
|
||||||
notificationBox.classList.add('notificationBox');
|
notificationBox.classList.add('notificationBox');
|
||||||
|
|
||||||
export async function showNotification(title, subtitle, time, hint) {
|
export async function showNotification(title, subtitle, time = 5000, hint) {
|
||||||
if (!hint) {
|
if (!hint) {
|
||||||
hint = headeri18n.notificationDefaultHint;
|
hint = headeri18n.notificationDefaultHint;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue