diff --git a/themes/dracula/assets/dracula.png b/themes/dracula/assets/dracula.png new file mode 100644 index 0000000..19bf67e Binary files /dev/null and b/themes/dracula/assets/dracula.png differ diff --git a/themes/dracula/css/DRACULA b/themes/dracula/css/DRACULA new file mode 100644 index 0000000..dcaf6d7 --- /dev/null +++ b/themes/dracula/css/DRACULA @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2016 Dracula Theme + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/themes/dracula/css/style.css b/themes/dracula/css/style.css new file mode 100644 index 0000000..429de2f --- /dev/null +++ b/themes/dracula/css/style.css @@ -0,0 +1,546 @@ +:root { + + --bg0: #282A36; + --bg1: #44475A; + --bg2: #585C74; + --bg3: #666e99; + + --alt0: #6272A4; + --alt1: #7A88B3; + + --fg0: #F8F8F2; + --fg1: #EAEAE0; + --fg2: #DEDED2; + + --cyan: #8BE9fD; + --green: #50FA7B; + --orange: #FFb86C; + --pink: #FF79C6; + --purple: #BD93F9; + --red: #FF5555; + --yellow: #F1FA8C; + + --animation-duration: 300ms; +} + +/* High DPI */ + +@media screen and (min-width: 3000px) and (min-height: 1200px) { + html { + zoom: 2.0; + } +} + +/* Basic */ + +html { + height: 100vh; + width: 100vw; + background-color: black; + font-size: 16px; +} +html * { + font-family: system-ui; + font-size: 16px; + transition: var(--animation-duration); + color: var(--fg0); +} + +body { + height: 100vh; + width: 100vw; + margin: 0; + overflow-x: hidden; + background-color: var(--bg0); +} + +.hide { + opacity: 0; + visibility: hidden; + max-height: 0; + max-width: 0; + display: none; +} + +/* Scrollbar */ + +::-webkit-scrollbar { + width: 6px; +} +::-webkit-scrollbar-thumb { + background-color: var(--fg2); +} +::-webkit-scrollbar-thumb:hover { + background-color: var(--fg0); +} + +/* Background */ + +#background { + height: 100vh; + width: 100vw; + position: absolute; + + background-color: var(--bg0); +} + +#background img { + width: inherit; + height: inherit; + object-fit: cover; + object-position: center; +} + +#bg-cover { + backdrop-filter: blur(4px); + position: absolute; + height: inherit; + width: inherit; +} + +#screen { + height: 100vh; + width: 100vw; + position: relative; + display: flex; + align-items: center; + justify-content: center; +} + +#cover { + height: 100vh; + width: 100vw; + position: absolute; + z-index: 10; + transition: var(--animation-duration); + + display: flex; + align-items: center; + justify-content: center; + + background-color: #282A36aa; + backdrop-filter: blur(5px); +} +#cover > #message { + font-size: 4em; + font-weight: bold; + cursor: default; +} + +/* Login form */ + +#login-wrapper { + position: relative; + background: var(--bg1); + border-radius: 2px; + max-height: 90vh; + width: 30em; + box-sizing: border-box; + transition: var(--animation-duration); + + /*display: flex;*/ + /*justify-content: center;*/ + /*align-items: flex-start;*/ +} +body.success #login-wrapper { + background-color: #79d28f; +} +body.failed #login-wrapper { + background-color: #dd7878; +} + +#login-wrapper-box { + display: flex; + justify-content: center; + align-items: center; + padding: 1.8em 3em; + height: 8em; +} + +#login-form { + display: flex; + align-items: center; + justify-content: space-around; + flex-direction: column; + height: 10em; + max-width: fit-content; +} + +input { + background-color: var(--bg2); + color: var(--fg0); + border: 0; + border-radius: 2px; + padding: 1em; + margin: 0.5em; + font-size: inherit; + font-family: inherit; +} +input:focus, input:focus-visible { + border: 0; + outline: auto var(--fg0); +} +:focus { + outline: auto var(--fg0) !important; +} + +#pass-form.hide { + visibility: hidden; + max-height: initial; + max-width: initial; + display: flex; +} + +#input-password { + box-shadow: 0 2px var(--cyan); + box-sizing: border-box; + margin: 0; +} + +#input-username { + box-sizing: border-box; + width: 100%; + margin: 0; + box-shadow: 0 2px var(--orange); +} + +::placeholder { + color: var(--fg2); +} + +#pass-wrapper { + display: flex; + width: 100%; + flex-direction: row; +} + +#user-wrapper { + display: flex; + width: 100%; + flex-direction: row; + position: relative; +} + +#submit-button { + background-color: #72bece; +} +#submit-button:hover, #submit-button:focus { + background-color: var(--purple); +} + +#users-button-wrapper { + display: flex; + flex-direction: column; +} + +#users-button { + background-color: var(--orange); + height: 100%; +} +#users-button:hover, #users-button:focus { + background-color: var(--red); +} + +#users-dropdown { + height: 0; +} + +#users-dropdown .dropdown { + background-color: var(--bg2); + right: 0; + z-index: 2; +} +#users-dropdown .dropdown button:hover, #users-dropdown .dropdown button:focus { + background-color: var(--orange); +} + +/* Time and date */ + +#time-date { + position: absolute; + display: flex; + flex-direction: column; + align-items: center; + background-color: transparent; + transition: var(--animation-duration); + overflow: hidden; + cursor: pointer; +} + +#time-date:hover, #time-date:focus { + filter: drop-shadow(2px 2px 6px black); + /*animation-name: shake;*/ + animation-duration: 1s; + animation-direction: normal; + animation-iteration-count: 1; + animation-timing-function: ease-in-out; +} +#time-date:hover *, #time-date:focus * { + /*color: var(--cyan);*/ +} +#time-date.hide { + display: flex; + max-height: initial; + max-width: initial; + opacity: 0; +} + +#time-label { + font-size: 4em; + margin: 0; +} + +/* Buttons */ +button { + /*color: var(--fg0);*/ + border: 0; + /*font-size: inherit;*/ + /*font-family: inherit;*/ +} + +.button { + background: var(--purple); + border: 0; + padding: 0.5em; + font-size: inherit; + cursor: pointer; + border-radius: 2px; + transition: var(--animation-duration); +} + +.button-group { + background: var(--purple); + border: 0; + padding: 0; + font-size: inherit; + border-radius: 2px; + transition: var(--animation-duration); +} +.button-group > * { + background-color: transparent; + cursor: pointer; + padding: 0.5em 0.8em; + transition: inherit; +} +.button-group > *:hover, .button-group > *:focus { + background-color: var(--orange); +} + +/* Auth message */ + +#auth-message { + position: absolute; + font-size: 4em; + font-weight: bold; +} +#auth-message.hide { + display: block; + max-width: initial; + max-height: initial; +} + +/* Bottom bar */ +#bottom-bar { + background-color: #585c7480; + backdrop-filter: blur(10px); + width: -webkit-fill-available; + min-height: 2em; + + display: flex; + align-items: stretch; + padding: 0.5em; +} +#bottom-bar * { + font-weight: bold; +} + +#bottom-bar .button { + display: flex; + align-items: center; + padding: 0.5em 0.75em; +} + +#sessions-button { + background-color: var(--bg3); +} +#sessions-button > span { + margin-left: 0.3em; +} + +#sessions-button:hover, #sessions-button:focus { + background-color: var(--purple); +} + +#sessions-dropdown { + max-height: 25vh; +} + +#bottom-right { + background-color: var(--bg3); + margin-left: auto; + display: flex; +} + +/* Top bar */ +#top-bar { + background-color: transparent; + width: -webkit-fill-available; + min-height: 2em; + padding: 1em; + padding-bottom: 0; + font-weight: bold; + + transition: var(--animation-duration); + + display: flex; + align-items: center; + justify-content: center; +} +#bottom-bar.hide, #top-bar.hide { + min-height: 0; + max-height: 0; + max-width: initial; + display: flex; + overflow: hidden; + padding: 0; + margin: 0; + opacity: 0; +} + +/* Panel */ + +#panel-button { + position: absolute; + top: 0; + right: 0; + margin: 1em; + + background-color: var(--bg1); +} +#panel-button:hover, #panel-button:focus { + background-color: var(--green); +} + +.panel { + position: fixed; + width: 350px; + height: -webkit-fill-available; + background: var(--bg2); + right: 0; + + display: flex; + flex-direction: row; + flex-wrap: wrap; + justify-content: space-between; + align-content: flex-start; + padding: 1.5em; + + overflow-y: auto; + overflow-x: hidden; +} + +.panel.hide { + transform: translateX(100%); + display: flex; + visibility: hidden; + opacity: 100%; + max-width: 100vw; + max-height: 100vh; +} + +.panel .image { + display: flex; + flex-direction: column; + width: 48%; + background-color: transparent; + margin-top: 1em; + padding: 0; + cursor: pointer; + border-color: var(--fg0); + border-width: 1px; + border-style: solid; + border-radius: 0; +} + +.panel .image > img { + background-color: var(--alt1); + width: -webkit-fill-available; + max-height: 200px; + object-fit: cover; + filter: brightness(0.8); +} +.panel .image:hover, .panel .image:focus { + filter: drop-shadow(2px 2px 6px black); +} +.panel .image:hover > img, .panel .image:focus > img { + filter: brightness(1); +} + +.panel h3 { + width: 80%; + margin-top: 0; + margin-bottom: 0; + font-size: 1.2em; + align-self: center; +} + +#close-panel-button { + background-color: var(--alt1); + height: fit-content; + align-self: center; +} +#close-panel-button:hover, #close-panel-button:focus { + background-color: var(--red); +} + +/* Dropdown */ +.dropdown { + position: absolute; + background-color: var(--bg2); + min-width: 8em; + max-height: 60vh; + overflow-y: auto; + margin: 0; + padding: 0; + transition: var(--animation-duration); +} +.dropdown button { + background-color: transparent; + color: var(--fg0); + padding: 0.8em; + width: -webkit-fill-available; + cursor: pointer; +} +.dropdown button:hover, .dropdown button:focus { + background-color: var(--purple); +} + +.dropdown li { + text-decoration: none; + display: block; +} + +.dropdown.hide { + visibility: hidden; + opacity: 100%; + display: block; + max-height: 0 !important; + overflow-y: hidden; +} + +/* Animations */ + +@keyframes shake { + 0% { + transform: rotateZ(0deg); + } + 25% { + transform: rotateZ(10deg); + } + 75% { + transform: rotateZ(-10deg); + } + 100% { + transform: rotateZ(0deg); + } +} diff --git a/themes/dracula/index.html b/themes/dracula/index.html new file mode 100644 index 0000000..d257ad1 --- /dev/null +++ b/themes/dracula/index.html @@ -0,0 +1,135 @@ + + + + + + Dracula theme + + + + + + + + + +
+
+ +
+ +
+
+
+ +
+ +
+ +
+ Welcome! +
+ +
+ + +
+ +
+
+
+ + +
+ +
+ +
+
+ +
+ +
+ + +
+ +
+
+ +
+ +
+
+ + +
+ +
+ + + + + + + +
+ +
+ +
+ + + + + +
+ + + + + + + + + diff --git a/themes/dracula/js/accounts.js b/themes/dracula/js/accounts.js new file mode 100644 index 0000000..4d84b69 --- /dev/null +++ b/themes/dracula/js/accounts.js @@ -0,0 +1,89 @@ +class Accounts { + constructor() { + this._localStorage = window.localStorage + this._userWrapper = document.querySelector("#user-wrapper") + this._accountsList = document.querySelector("#users-dropdown") + this._accountsButton = document.querySelector("#users-button") + this._defaultUser = null + this._usersObject = null + this._init() + } + + getDefaultUserName() { + return this._defaultUser.username + } + + _setAccountDefault() { + let input = this._userWrapper.querySelector("input") + if (this._defaultUser.username != "") { + //input.classList.add("hide") + input.value = this._defaultUser.username + } else { + input.value = "" + } + if (this._usersObject.length > 0) { + this._accountsButton.classList.remove("hide") + } + } + + _updateOnStartup() { + var username = "" + if (this._usersObject.length > 0) { + username = this._localStorage.getItem("defaultUser") || this._usersObject[0].username + } + var user = this._usersObject.find((val) => {return val.username === username}) + if (user === undefined) { + this._defaultUser = {username: "", display_name: ""} + } else { + this._defaultUser = user + } + this._setAccountDefault() + } + + _setAccountList() { + var dropdown = this._accountsList.querySelector(".dropdown") + dropdown.innerHTML = "" + + for (let i = 0; i < this._usersObject.length; i++) { + var name = this._usersObject[i].display_name + var li = document.createElement("li") + var button = document.createElement("button") + button.type = "button" + button.innerText = name + button.addEventListener("click", () => { + this._updateDefaults(this._usersObject[i]) + this._setAccountDefault() + //authenticate.startAuthentication() + }) + + li.appendChild(button) + dropdown.appendChild(li) + } + } + + _setButton() { + var dropdown = this._accountsList.querySelector(".dropdown") + document.querySelector("#screen").addEventListener("click", (ev) => { + if (ev.target == this._accountsButton || ev.target.parentElement == this._accountsButton) { + dropdown.classList.toggle("hide") + } else + if (ev.target != this._accountsList && ev.target.closest(".dropdown") == null) { + dropdown.classList.add("hide") + } + }) + } + + _updateDefaults(userObject) { + if (!userObject) return + this._defaultUser = userObject + + this._localStorage.setItem("defaultUser", this._defaultUser.username) + } + + _init() { + this._usersObject = lightdm.users + this._updateOnStartup() + this._setAccountList() + this._setButton() + } +} diff --git a/themes/dracula/js/authenticate.js b/themes/dracula/js/authenticate.js new file mode 100644 index 0000000..318032a --- /dev/null +++ b/themes/dracula/js/authenticate.js @@ -0,0 +1,112 @@ +class Authenticate { + constructor() { + this._form = document.querySelector("#login-form") + this._username = "" + this._password = "" + this._init() + } + + _setForm() { + this._form.addEventListener("submit", (ev) => { + ev.preventDefault() + var inputs = this._form.querySelectorAll("input") + var data = getArrayForm(inputs) + if (!data) return false + this._username = data.username + this._password = data.password + this._respond() + }) + } + + _respond() { + let inputUser = document.querySelector("#input-username") + let inputPass = document.querySelector("#input-password") + inputUser.blur(); inputUser.disabled = true; + inputPass.blur(); inputPass.disabled = true; + + lightdm.cancel_authentication() + lightdm.authenticate(String(this._username)) + lightdm.respond(this._password) + } + + _showMessage(msg) { + let message = document.querySelector("#auth-message") + message.innerText = msg + message.classList.remove("hide") + } + + _hideMessage() { + let message = document.querySelector("#auth-message") + message.classList.add("hide") + } + + async _authentication_done() { + let body = document.querySelector("body") + body.classList.add("success") + + this._showMessage("Welcome!") + + let form = document.querySelector("#pass-form") + let topbar = document.querySelector("#top-bar") + let bottombar = document.querySelector("#bottom-bar") + form.style.transition = "0ms" + form.classList.add("hide") + topbar.classList.add("hide") + bottombar.classList.add("hide") + + await wait(1000) + let defSession = String(sessions.getDefaultSession()) + document.querySelector("body").style.opacity = 0 + + await wait(1000) + console.log("Session started with", defSession) + lightdm.start_session(defSession) + } + + async _authentication_failed() { + lightdm.cancel_authentication() + let body = document.querySelector("body") + body.classList.add("failed") + + this._showMessage("Try again") + + let form = document.querySelector("#pass-form") + let topbar = document.querySelector("#top-bar") + let bottombar = document.querySelector("#bottom-bar") + form.style.transition = "0ms" + form.classList.add("hide") + topbar.classList.add("hide") + bottombar.classList.add("hide") + + await wait(1500) + + this._hideMessage() + form.style.transition = "" + form.classList.remove("hide") + topbar.classList.remove("hide") + bottombar.classList.remove("hide") + + let inputUser = document.querySelector("#input-username") + let inputPass = document.querySelector("#input-password") + inputUser.blur(); inputUser.disabled = false; + inputPass.blur(); inputPass.disabled = false; + inputPass.value = "" + + body.classList.remove("failed") + } + + _setAuthentication_done() { + window.authentication_done = () => { + if (lightdm.is_authenticated) { + this._authentication_done() + } else { + this._authentication_failed() + } + } + } + + _init() { + this._setForm() + this._setAuthentication_done() + } +} diff --git a/themes/dracula/js/debug.js b/themes/dracula/js/debug.js new file mode 100644 index 0000000..49e047c --- /dev/null +++ b/themes/dracula/js/debug.js @@ -0,0 +1,155 @@ +class Debug { + constructor() { + this._debugPass = "tepes" + this._init() + } + + _init() { + console.log("DEBUG") + + if (!window.greeter_config) { + window.greeter_config = { + greeter: { + debug_mode: true, + }, + branding: { + background_images_dir: "", + } + } + } + + if (!window.theme_utils) { + window.theme_utils = {} + window.theme_utils.dirlist = function(path, mode, callback) { + var result = [] + callback(result) + }; + window.theme_utils.bind_this = function(context) {return context} + } + + if (!window.lightdm) { + window.lightdm = {} + } + + var local_lightdm = { + default_password: "tepes", + is_authenticated: false, + authentication_user: null, + default_session: "awesome", + can_suspend: true, + can_hibernate: true, + can_shutdown: true, + can_restart: true, + can_access_battery: true, + can_access_brightness: true, + sessions: [ + { + name: "awesome wm", + key: "awesome" + }, + { + name: "Ubuntu", + key: "ubuntu" + }, + { + name: "i3wm", + key: "i3" + }, + { + name: "bspwm", + key: "bspwm" + } + ], + users: [ + { + display_name: "Vlad Tepes", + username: "dracula", + image: "" + }, + { + display_name: "Trevor Belmont", + username: "treffy", + image: "" + }, + { + display_name: "Sypha Belnades", + username: "speaker", + image: "" + } + ], + languages: [ + { + name: 'American English', + code: 'en_US.utf8' + } + ], + language: 'American English', + authenticate: username => { + console.log(`Starting authentication with user: "${username}"`) + }, + cancel_authentication: () => { + console.log(`Authentication cancelled`) + }, + respond: async (password) => { + console.log(`Password provided: "${password}"`) + if (password == this._debugPass) { + lightdm.is_authenticated = true + } else { + await wait(2000) + } + authentication_done() + }, + start_session: session => { + alert(`Logged with session: "${session}"`) + location.reload() + }, + shutdown: () => { + console.log("System is shutting down...") + setTimeout(() => location.reload(), 2000) + }, + restart: () => { + console.log("System is rebooting...") + setTimeout(() => location.reload(), 2000) + }, + hibernate: () => { + console.log("System is hibernating") + setTimeout(() => location.reload(), 2000) + }, + suspend: () => { + console.log("System is suspending") + setTimeout(() => location.reload(), 2000) + }, + batteryData: { + name: "Battery 0", + level: 85, + state: "Discharging" + }, + batteryUpdate: () => { + console.log("Battery updated") + }, + brightness: 50, + brightnessSet: (quantity) => { + lightdm.brightness = quantity + }, + brightnessIncrease: (quantity) => { + lightdm.brightness += quantity + if (lightdm.brightness > 100) lightdm.brightness = 100 + }, + brightnessDecrease: (quantity) => { + lightdm.brightness -= quantity + if (lightdm.brightness < 0) lightdm.brightness = 0 + } + } + + if (lightdm.mock == undefined) { + window.lightdm = {} + Object.assign(window.lightdm, local_lightdm) + } else { + Object.keys(local_lightdm).forEach((key) => { + var realKey = `_${key}` + lightdm[realKey] = local_lightdm[key] + }) + } + + } +} diff --git a/themes/dracula/js/index.js b/themes/dracula/js/index.js new file mode 100644 index 0000000..e985072 --- /dev/null +++ b/themes/dracula/js/index.js @@ -0,0 +1,130 @@ + +function getArrayForm(inputs) { + if (!inputs) return false + var data = {} + inputs.forEach((x) => { + data[x.name] = x.value + }) + return data +} + +async function wait(ms) { + return new Promise( resolve => { + setTimeout(() => { + resolve() + }, ms) + }) +} + + +async function initGreeter() { + + if (greeter_config.greeter.debug_mode) { + debug = new Debug() + } + + lightdm.authentication_complete?.connect(() => authentication_done()) + + lightdm.brightness_update?.connect(() => brightness._updateData()) + + accounts = new Accounts() + + sessions = new Sessions() + + authenticate = new Authenticate() + + sidebar = new Sidebar() + + //power = new Power() + + //battery = new Battery() + + //brightness = new Brightness() + +} + +window.addEventListener("GreeterReady", initGreeter) + +//const panel_button = document.querySelector("#panel-button") +//const close_panel_button = document.querySelector("#close-panel-button") +const panel = document.querySelector(".panel") +const screen = document.querySelector("#screen") + +const sessions_button = document.querySelector("#sessions-button") +const sessions_dropdown = document.querySelector("#sessions-dropdown") + +const time_date_button = document.querySelector("#time-date") +const pass_form = document.querySelector("#pass-form") + +//screen.addEventListener("click", (ev) => { + //if (ev.target == panel_button || ev.target.parentElement == panel_button) { + //panel.classList.toggle("hide") + //panel_button.blur() + //wait(100).then(() => {close_panel_button.focus()}) + //} else + //if (ev.target != panel && ev.target.closest(".panel") == null) { + //panel.classList.add("hide") + //} + + //if (ev.target == close_panel_button || ev.target.parentElement == close_panel_button) { + //panel.classList.toggle("hide") + //panel_button.focus() + //} + + //if (ev.target == sessions_button || ev.target.parentElement == sessions_button) { + //sessions_dropdown.classList.toggle("hide") + //} else + //if (ev.target != sessions_dropdown && ev.target.closest(".dropdown") == null) { + //sessions_dropdown.classList.add("hide") + //} +//}) + +async function toggleTimeDate() { + time_date_button.blur() + pass_form.blur() + if (time_date_button.classList.contains("hide")) { + pass_form.classList.add("hide") + await wait(300) + time_date_button.classList.remove("hide") + await wait(100) + time_date_button.focus() + } else { + time_date_button.classList.add("hide") + await wait(300) + pass_form.classList.remove("hide") + } +} + +time_date_button.addEventListener("click", async (ev) => { + toggleTimeDate() +}) + +pass_form.addEventListener("keydown", (ev) => { + if (ev.keyCode == 27) { + toggleTimeDate() + } +}) + +//sessions_dropdown.addEventListener("keydown", (ev) => { + //if (ev.keyCode == 27) { + //sessions_dropdown.classList.toggle("hide") + //sessions_button.focus() + //} +//}) + +//panel.addEventListener("keydown", (ev) => { + //if (ev.keyCode == 27) { + //panel.classList.toggle("hide") + //panel_button.focus() + //} +//}) + +//const time_label = document.querySelector("#time-label") +//const date_label = document.querySelector("#date-label") + +//function updateTimeDate() { + //time_label.innerText = theme_utils.get_current_localized_time() + //date_label.innerText = theme_utils.get_current_localized_date() +//} + +//setInterval(updateTimeDate, 1000) diff --git a/themes/dracula/js/sessions.js b/themes/dracula/js/sessions.js new file mode 100644 index 0000000..9ae0d8a --- /dev/null +++ b/themes/dracula/js/sessions.js @@ -0,0 +1,91 @@ +class Sessions { + constructor() { + this._localStorage = window.localStorage + this._sessionsButton = document.querySelector("#sessions-button") + this._sessionList = document.querySelector("#sessions-dropdown") + this._sessionLabel = document.querySelector("#sessions-button > .text") + this._defaultSession = null + this._sessionsObject = null + this._init() + } + + getDefaultSession() { + return this._defaultSession.key + } + + _setSessionDefault() { + this._sessionLabel.innerText = this._defaultSession.name + } + + _updateOnStartup() { + var key = this._localStorage.getItem("defaultSession") || this._sessionsObject[0].key || lightdm.default_session + + var session = this._sessionsObject.find((val) => {return val.key === key}) + if (session === undefined) { + // This should never happen + this._defaultSession = {key: "awesome", name: "Awesome WM"} + } else { + this._defaultSession = session + } + this._setSessionDefault() + } + + _updateDefaults(sessionObj) { + if (!sessionObj) return + this._defaultSession = sessionObj + this._localStorage.setItem("defaultSession", this._defaultSession.key) + } + + _setSessionList() { + var dropdown = this._sessionList + dropdown.innerHTML = "" + for (let i = 0; i < this._sessionsObject.length; i++) { + var name = this._sessionsObject[i].name + var li = document.createElement("li") + var button = document.createElement("button") + button.innerText = name + button.addEventListener("click", () => { + this._updateDefaults(this._sessionsObject[i]) + this._setSessionDefault() + }) + + li.appendChild(button) + dropdown.appendChild(li) + } + } + + _setKeydown() { + var dropdown = this._sessionList + dropdown.addEventListener("keydown", (ev) => { + if (ev.keyCode == 27) { + sessions_dropdown.classList.add("hide") + this._sessionsButton.focus() + } + }) + } + + _setButton() { + var dropdown = this._sessionList + document.querySelector("#screen").addEventListener("click", (ev) => { + if (ev.target == this._sessionsButton || ev.target.parentElement == this._sessionsButton) { + dropdown.classList.toggle("hide") + } else + if (ev.target != this._sessionList && ev.target.closest(".dropdown") == null) { + dropdown.classList.add("hide") + } + }) + document.querySelector("#screen").addEventListener("focusin", (ev) => { + if (!dropdown.contains(document.activeElement) && document.activeElement != this._sessionsButton) { + dropdown.classList.add("hide") + } + }) + } + + _init() { + this._sessionsObject = lightdm.sessions + this._updateOnStartup() + this._setSessionList() + this._setButton() + this._setKeydown() + } +} diff --git a/themes/dracula/js/sidebar.js b/themes/dracula/js/sidebar.js new file mode 100644 index 0000000..5bc95a3 --- /dev/null +++ b/themes/dracula/js/sidebar.js @@ -0,0 +1,65 @@ +class Sidebar { + constructor() { + this._sidebar = document.querySelector("#sidebar") + this._sidebarButton = document.querySelector("#panel-button") + this._closeButton = document.querySelector("#close-panel-button") + this._visible = false + this._init() + } + + showSidebar() { + this._sidebar.classList.remove("hide") + wait(100).then(() => {this._closeButton.focus()}) + this._visible = true + } + + hideSidebar() { + this._sidebar.classList.add("hide") + this._sidebarButton.focus() + this._visible = false + } + + toggleSidebar() { + if (this._visible) { + this.hideSidebar() + } else { + this.showSidebar() + } + } + + _setKeydown() { + this._sidebar.addEventListener("keydown", (ev) => { + if (ev.keyCode == 27) { + this.hideSidebar() + } + }) + } + + _setSidebar() { + document.querySelector("#screen").addEventListener("click", (ev) => { + if (ev.target == this._sidebarButton || ev.target.parentElement == this._sidebarButton) { + this.toggleSidebar() + } else + if (ev.target != this._sidebar && ev.target.closest(".panel") == null) { + this._sidebar.classList.add("hide") + this._visible = false + } + + if (ev.target == this._closeButton || ev.target.parentElement == this._closeButton) { + this.hideSidebar() + } + }) + + document.querySelector("#screen").addEventListener("focusin", (ev) => { + if (!this._sidebar.contains(document.activeElement)) { + this._sidebar.classList.add("hide") + this._visible = false + } + }) + } + + _init() { + this._setSidebar() + this._setKeydown() + } +}