diff --git a/size-plugin.json b/size-plugin.json index 7253210..cf8612f 100644 --- a/size-plugin.json +++ b/size-plugin.json @@ -1 +1 @@ -[{"timestamp":1646924506348,"files":[{"filename":"index.html","previous":487,"size":487,"diff":0},{"filename":"bundle.45d14.css","previous":1691,"size":1691,"diff":0},{"filename":"bundle.*****.js","previous":12153,"size":14680,"diff":2527},{"filename":"polyfills.*****.js","previous":2288,"size":2288,"diff":0}]},{"timestamp":1646755354217,"files":[{"filename":"bundle.*****.esm.js","previous":9839,"size":0,"diff":-9839},{"filename":"polyfills.*****.esm.js","previous":2187,"size":0,"diff":-2187},{"filename":"sw.js","previous":10597,"size":0,"diff":-10597},{"filename":"sw-esm.js","previous":10603,"size":0,"diff":-10603},{"filename":"polyfills.058fb.js","previous":2288,"size":0,"diff":-2288},{"filename":"index.html","previous":521,"size":487,"diff":-34},{"filename":"200.html","previous":521,"size":0,"diff":-521},{"filename":"bundle.45d14.css","previous":1691,"size":1691,"diff":0},{"filename":"bundle.caa2d.js","previous":12219,"size":0,"diff":-12219},{"filename":"bundle.*****.js","previous":0,"size":12153,"diff":12153},{"filename":"polyfills.*****.js","previous":0,"size":2288,"diff":2288}]},{"timestamp":1646755194517,"files":[{"filename":"bundle.2a54a.css","previous":1709,"size":0,"diff":-1709},{"filename":"bundle.*****.esm.js","previous":9842,"size":9839,"diff":-3},{"filename":"polyfills.*****.esm.js","previous":2187,"size":2187,"diff":0},{"filename":"sw.js","previous":10595,"size":10597,"diff":2},{"filename":"sw-esm.js","previous":10600,"size":10603,"diff":3},{"filename":"polyfills.058fb.js","previous":2288,"size":2288,"diff":0},{"filename":"index.html","previous":536,"size":521,"diff":-15},{"filename":"200.html","previous":536,"size":521,"diff":-15},{"filename":"bundle.3030b.js","previous":12224,"size":0,"diff":-12224},{"filename":"bundle.45d14.css","previous":0,"size":1691,"diff":1691},{"filename":"bundle.caa2d.js","previous":0,"size":12219,"diff":12219}]},{"timestamp":1646755054393,"files":[{"filename":"bundle.2a54a.css","previous":1709,"size":1709,"diff":0},{"filename":"bundle.*****.esm.js","previous":9856,"size":9842,"diff":-14},{"filename":"polyfills.*****.esm.js","previous":2187,"size":2187,"diff":0},{"filename":"sw.js","previous":10599,"size":10595,"diff":-4},{"filename":"sw-esm.js","previous":10603,"size":10600,"diff":-3},{"filename":"bundle.1a7a6.js","previous":11947,"size":0,"diff":-11947},{"filename":"polyfills.058fb.js","previous":2288,"size":2288,"diff":0},{"filename":"index.html","previous":536,"size":536,"diff":0},{"filename":"200.html","previous":536,"size":536,"diff":0},{"filename":"bundle.3030b.js","previous":0,"size":12224,"diff":12224}]},{"timestamp":1646751614979,"files":[{"filename":"bundle.2a54a.css","previous":0,"size":1709,"diff":1709},{"filename":"bundle.*****.esm.js","previous":0,"size":9856,"diff":9856},{"filename":"polyfills.*****.esm.js","previous":0,"size":2187,"diff":2187},{"filename":"sw.js","previous":0,"size":10599,"diff":10599},{"filename":"sw-esm.js","previous":0,"size":10603,"diff":10603},{"filename":"bundle.1a7a6.js","previous":0,"size":11947,"diff":11947},{"filename":"polyfills.058fb.js","previous":0,"size":2288,"diff":2288},{"filename":"index.html","previous":0,"size":536,"diff":536},{"filename":"200.html","previous":0,"size":536,"diff":536}]}] +[{"timestamp":1646927116411,"files":[{"filename":"index.html","previous":487,"size":487,"diff":0},{"filename":"bundle.45d14.css","previous":1691,"size":1691,"diff":0},{"filename":"bundle.*****.js","previous":14680,"size":14692,"diff":12},{"filename":"polyfills.*****.js","previous":2288,"size":2288,"diff":0}]},{"timestamp":1646924506348,"files":[{"filename":"index.html","previous":487,"size":487,"diff":0},{"filename":"bundle.45d14.css","previous":1691,"size":1691,"diff":0},{"filename":"bundle.*****.js","previous":12153,"size":14680,"diff":2527},{"filename":"polyfills.*****.js","previous":2288,"size":2288,"diff":0}]},{"timestamp":1646755354217,"files":[{"filename":"bundle.*****.esm.js","previous":9839,"size":0,"diff":-9839},{"filename":"polyfills.*****.esm.js","previous":2187,"size":0,"diff":-2187},{"filename":"sw.js","previous":10597,"size":0,"diff":-10597},{"filename":"sw-esm.js","previous":10603,"size":0,"diff":-10603},{"filename":"polyfills.058fb.js","previous":2288,"size":0,"diff":-2288},{"filename":"index.html","previous":521,"size":487,"diff":-34},{"filename":"200.html","previous":521,"size":0,"diff":-521},{"filename":"bundle.45d14.css","previous":1691,"size":1691,"diff":0},{"filename":"bundle.caa2d.js","previous":12219,"size":0,"diff":-12219},{"filename":"bundle.*****.js","previous":0,"size":12153,"diff":12153},{"filename":"polyfills.*****.js","previous":0,"size":2288,"diff":2288}]},{"timestamp":1646755194517,"files":[{"filename":"bundle.2a54a.css","previous":1709,"size":0,"diff":-1709},{"filename":"bundle.*****.esm.js","previous":9842,"size":9839,"diff":-3},{"filename":"polyfills.*****.esm.js","previous":2187,"size":2187,"diff":0},{"filename":"sw.js","previous":10595,"size":10597,"diff":2},{"filename":"sw-esm.js","previous":10600,"size":10603,"diff":3},{"filename":"polyfills.058fb.js","previous":2288,"size":2288,"diff":0},{"filename":"index.html","previous":536,"size":521,"diff":-15},{"filename":"200.html","previous":536,"size":521,"diff":-15},{"filename":"bundle.3030b.js","previous":12224,"size":0,"diff":-12224},{"filename":"bundle.45d14.css","previous":0,"size":1691,"diff":1691},{"filename":"bundle.caa2d.js","previous":0,"size":12219,"diff":12219}]},{"timestamp":1646755054393,"files":[{"filename":"bundle.2a54a.css","previous":1709,"size":1709,"diff":0},{"filename":"bundle.*****.esm.js","previous":9856,"size":9842,"diff":-14},{"filename":"polyfills.*****.esm.js","previous":2187,"size":2187,"diff":0},{"filename":"sw.js","previous":10599,"size":10595,"diff":-4},{"filename":"sw-esm.js","previous":10603,"size":10600,"diff":-3},{"filename":"bundle.1a7a6.js","previous":11947,"size":0,"diff":-11947},{"filename":"polyfills.058fb.js","previous":2288,"size":2288,"diff":0},{"filename":"index.html","previous":536,"size":536,"diff":0},{"filename":"200.html","previous":536,"size":536,"diff":0},{"filename":"bundle.3030b.js","previous":0,"size":12224,"diff":12224}]},{"timestamp":1646751614979,"files":[{"filename":"bundle.2a54a.css","previous":0,"size":1709,"diff":1709},{"filename":"bundle.*****.esm.js","previous":0,"size":9856,"diff":9856},{"filename":"polyfills.*****.esm.js","previous":0,"size":2187,"diff":2187},{"filename":"sw.js","previous":0,"size":10599,"diff":10599},{"filename":"sw-esm.js","previous":0,"size":10603,"diff":10603},{"filename":"bundle.1a7a6.js","previous":0,"size":11947,"diff":11947},{"filename":"polyfills.058fb.js","previous":0,"size":2288,"diff":2288},{"filename":"index.html","previous":0,"size":536,"diff":536},{"filename":"200.html","previous":0,"size":536,"diff":536}]}] diff --git a/src/api/index.js b/src/api/index.js index 8fd7050..f0f904d 100644 --- a/src/api/index.js +++ b/src/api/index.js @@ -1,40 +1,70 @@ const server = 'http://192.168.4.22' -async function login(username,password){ +async function login(username, password) { let formData = new FormData(); - formData.append('username',username) - formData.append('password',password); - formData.append('action','login'); - const resp = await fetch(`${server}/api/auth`,{method: 'POST',mode: 'cors',body:formData }).then(resp=>resp.text()) + formData.append('username', username) + formData.append('password', password); + formData.append('action', 'login'); + const resp = fetch(`${server}/api/auth`, { method: 'POST', mode: 'cors', body: formData }).then(resp => resp.text()); return resp; } -function logout(){ - return 'DUMMYTOKEN'; +async function logout(token) { + let formData = new FormData() + formData.append('token', token); + formData.append('action', 'logout'); + const resp = fetch(`${server}/api/auth`, { method: 'POST', mode: 'cors', body: formData }).then(resp => resp.text()); + return resp; } -function checkAuth(token){ - return token==='DUMMYTOKEN'; +function checkAuth(token) { + return token === 'DUMMYTOKEN'; } -async function fetchdb(token='azif7eqCl5'){ +async function fetchdb(token = 'azif7eqCl5') { //fetch(`${server}/api/userdb`).then() //let xmlHttp = new XMLHttpRequest(); //xmlHttp.open( "GET", `${server}/api/userdb`, false ); // false for synchronous request //xmlHttp.send( null ); - const resp = await fetch(`${server}/api/userdb`,{method: 'GET',mode: 'cors',headers:{Authentification:token}}) - .then(resp=>resp.text()).then(text=>parsedb(text)) + const resp = await fetch(`${server}/api/userdb`, { method: 'GET', mode: 'cors', headers: { Authentification: token } }) + .then(resp => resp.text()).then(text => parsedb(text)) return resp; - + } -function parsedb(raw){ - - let lines = raw.split('\n'); - let users = []; - lines.map((l,line)=>{ - let [uid, first_name, last_name, rfid_uid, user_pin, active] = l.split([';']); - users.push({ line, uid, first_name, last_name, rfid_uid, user_pin, enabled: active[0]==='1' }); - }); - return users; - +function createCsvTable(userdb) { + let res = ''; + let first = true; + for (let u of userdb) { + if (first) + first = false; + + res += `${!first && '\n'}${u.uid},${u.first_name},${u.last_name},${u.rfid_uid},${u.user_pin},${u.enabled ? '1' : '0'}`; + } + return res; } -const publicfunctions = {login, logout, checkAuth, parsedb, fetchdb}; -export default {...publicfunctions} -export {login, logout, checkAuth, parsedb} \ No newline at end of file +async function updateUser(token, user) { + const resp = await fetch(`${server}/api/user/`, { method: 'POST', body: JSON.stringify(user), mode: 'cors', headers: { Authentification: token } }) + .then(resp => resp.json()); + return resp; +} +async function deleteUser(token, user) { + const resp = await fetch(`${server}/api/user/${user.uid}`, { method: 'DELETE', body: JSON.stringify(user), mode: 'cors', headers: { Authentification: token } }) + .then(resp => resp.json()); + return resp; +} +async function createUser(token, user) { + const resp = await fetch(`${server}/api/user/`, { method: 'PUT', body: JSON.stringify(user), mode: 'cors', headers: { Authentification: token } }) + .then(resp => resp.json()); + return resp; +} +function parsedb(raw) { + + let lines = raw.split('\n'); + let users = []; + lines.map((l, line) => { + let [uid, first_name, last_name, rfid_uid, user_pin, enabled] = l.split([';']); + users.push({ line, uid, first_name, last_name, rfid_uid, user_pin, enabled: enabled[0] === '1' }); + }); + return users; + +} +const publicfunctions = { login, logout, checkAuth, parsedb,fetchdb, createCsvTable, updateUser, deleteUser, createUser }; +export default { ...publicfunctions } +export { login, logout, checkAuth, parsedb,fetchdb, createCsvTable, updateUser, deleteUser, createUser } \ No newline at end of file diff --git a/src/components/app.js b/src/components/app.js index 44be02e..0203297 100644 --- a/src/components/app.js +++ b/src/components/app.js @@ -8,12 +8,13 @@ import { AppStateProvider, UserTableProvider, menuReducer, sessionReducer, userT function App() { // useReducer const menu = useReducer(menuReducer, false); - const session = useReducer(sessionReducer, { active: false }); + const session = useReducer(sessionReducer, { active:true ,token: "0t6BF94Y92" }); const [usertable, userreducer] = useReducer(userTableReducer, []); this.menu_items = [ { text: "Übersicht", path: "/" }, - { text: "Benutzer", path: "/users" }, + { text: "Benutzer anlegen", path: "/newuser" }, + { text: "Benutzer verwalten", path: "/users" }, { text: "System", path: "/system" }, { text: "Abmelden", path: "/logout" } ] @@ -28,7 +29,7 @@ function App() {
-
+
{!menu[0] && @@ -39,7 +40,8 @@ function App() { - + +
Error 404
diff --git a/src/components/header/index.jsx b/src/components/header/index.jsx index 611e167..0673a48 100644 --- a/src/components/header/index.jsx +++ b/src/components/header/index.jsx @@ -1,13 +1,13 @@ import { useContext } from 'preact/hooks'; import AppState from '../../store/AppState'; -const Header = () => { +const Header = ({title}) => { let { menu, session } = useContext(AppState); let [menu_shown, toggle_menu] = menu; let [sessiondata] = session; return (
-

Login

+

{title}

{ sessiondata.active &&(
toggle_menu('toggle')}>
diff --git a/src/route/edituser/index.js b/src/route/edituser/index.js index 27397fa..0b824a6 100644 --- a/src/route/edituser/index.js +++ b/src/route/edituser/index.js @@ -1,36 +1,55 @@ -import {h} from 'preact'; -import { useContext, useState } from 'preact/hooks'; +import { h } from 'preact'; +import { useContext, useEffect, useState } from 'preact/hooks'; import { route } from 'preact-router'; -import { UserTable } from "../../store"; -function EditUser({userid}){ +import AppState, { UserTable } from "../../store"; +import api from '../../api' +function EditUser({ userid }) { + let [sessiondata,] = useContext(AppState).session; const { usertable, userreducer } = useContext(UserTable); - let user = usertable.find(u=>u.uid===userid) - const [formdata, formchange] = useState(user?user:{}); - const onChange=(e)=>{ + + const [formdata, formchange] = useState({}); + const onChange = (e) => { console.log(e); - if(e.target.type==='checkbox') - formchange({...formdata, [e.target.id]:e.target.checked}) + if (e.target.type === 'checkbox') + formchange({ ...formdata, [e.target.id]: e.target.checked }) else - formchange({...formdata, [e.target.id]:e.target.value}) + formchange({ ...formdata, [e.target.id]: e.target.value }) } - const onSubmit=(e)=>{ + useEffect(()=>{ + let user = userid !== undefined?usertable.find(u => u.uid === userid):undefined; + if(user!==undefined){ + formchange(user); + } + },[userid]); + const onSubmit = (e) => { e.preventDefault(); - userreducer({type:'update', user: formdata}) + console.log(api); + if(formdata.line!==undefined){ + api.updateUser(sessiondata.token, formdata).then(r => { + userreducer({ type: 'update', user: r }) + }); + }else{ + api.createUser(sessiondata.token, formdata).then(r => { + userreducer({ type: 'create', user: r }) + }); + } + route('/users'); } - const Input = ({id, type='text', label, disabled})=>(
) - return( + const Input = ({ id, type = 'text', label, disabled }) => (
) + return (
-

Benutzer Bearbeiten

-
- - - - - - - Speichern -
+

{formdata.line != undefined ? "Benutzer Bearbeiten" : "Neuer Benutzer"}

+
+ + + + + + +
Speichern
+ +
) } diff --git a/src/route/home/index.js b/src/route/home/index.js index b42343f..a8eca83 100644 --- a/src/route/home/index.js +++ b/src/route/home/index.js @@ -1,10 +1,29 @@ import { h } from 'preact'; +import { Link } from 'preact-router'; +import { useContext, useState } from 'preact/hooks'; +import AppState from '../../store/AppState'; -function Home() {return( -
-

Home

-

This is the Home component.

-
-); +function Home() { + let [sessiondata, ] = useContext(AppState).session; + return ( +
+
+

Startseite

+

Willkommen zurück {sessiondata.username}

+
+

Status

+
    +
  • Aktiv seit: 12.01.2022
  • +
+
+
+

Hier können Sie den Türöffner manuell aktivieren.

+ +

Um Benutzer anzulegen, öffnen sie das Menü und tippen auf Benutzer anlegen

+
+
+ +
+ ); } export default Home; diff --git a/src/route/login/index.jsx b/src/route/login/index.jsx index 35b9b41..57ace70 100644 --- a/src/route/login/index.jsx +++ b/src/route/login/index.jsx @@ -1,19 +1,19 @@ import { h } from 'preact'; import { route } from 'preact-router'; -import { useContext,useState } from 'preact/hooks'; +import { useContext, useState } from 'preact/hooks'; import AppState from '../../store/AppState'; import Breadcrumbs from '../../components/breadcrumbs'; import api from '../../api' function Login() { - let [sessiondata, setsession]= useContext(AppState).session; + let [sessiondata, setsession] = useContext(AppState).session; const [val, set] = useState({ username: '', password: '', error: null }); const navigation = ["Login"]; - if(sessiondata.active) + if (sessiondata.active) route('/', true); function onSubmit(e) { e.preventDefault(); - api.login(val.username, val.password).then(token=>{ - if (token!='failed!') { + api.login(val.username, val.password).then(token => { + if (token != 'failed!') { let newsession = { type: 'start', username: val.username, @@ -24,31 +24,32 @@ function Login() { else { set({ ...val, error: "user" }); } - set({ username: '', password: '' }); + set({ username: '', password: '' }); }) } return (
+
+

Anmeldung

+

Bitte melden Sie sich mit ihren Nutzerdaten an.

+ {val.error !== null && Fehler: Ungültige Anmeldedaten.} +
- -

- Bitte melden Sie sich mit ihren Nutzerdaten an. + +

+ set({ ...val, username: e.target.value })} value={val.username} /> + +
+
+ set({ ...val, password: e.target.value })} value={val.password} /> + +
+
-

- {val.error !== null && Fehler: Ungültige Anmeldedaten.} -
- set({ ...val, username: e.target.value })} value={val.username} /> - -
-
- set({ ...val, password: e.target.value })} value={val.password} /> - -
- - -
+ +
); diff --git a/src/route/logout/index.jsx b/src/route/logout/index.jsx index b1cb469..3423c1d 100644 --- a/src/route/logout/index.jsx +++ b/src/route/logout/index.jsx @@ -1,29 +1,38 @@ import { h } from 'preact'; import { Link } from 'preact-router'; -import { useContext } from 'preact/hooks'; +import { useContext, useState } from 'preact/hooks'; import AppState from '../../store/AppState'; import { Breadcrumbs } from '../../components'; - +import api from '../../api' function Logout() { const navigation = ["Logout"]; + let [text, settext] = useState(''); let [sessiondata, setsession] = useContext(AppState).session; this.shouldComponentUpdate = function () { console.log('functional component vs closures'); } if (sessiondata.active) { + api.logout(sessiondata.token).then((r) => r === 'success' ? settext('Sitzung beendet.') : settext('Sitzung war bereits nicht mehr vorhanden.')); setsession({ type: 'end' }) } + return (
+
+

+ Erfolgreich abgemeldet: +

+

+ {text}
+ Erneut Anmelden +

+ +
-

- Erfolgreich abgemeldet. - Erneut Anmelden -

); diff --git a/src/route/system/index.jsx b/src/route/system/index.jsx index 2f37926..5aa174c 100644 --- a/src/route/system/index.jsx +++ b/src/route/system/index.jsx @@ -4,44 +4,45 @@ import { h } from 'preact'; function System() { return ( -
-

System

-

WiFi Setup

-
-
-
- - -
-
- - -
-
-

Admin User

-
-
-
- - -
-
- - -
-
-

Datenbank Backup


-
-
-

Backup einspielen

- - -
-

Backup herunterladen

- -
- +
+
+

System

+

WiFi Setup

+
+
+
+ + +
+
+ + +
+
+

Admin User

+
+
+
+ + +
+
+ + +
+
+

Datenbank Backup


+
+
+

Backup einspielen

+ + +
+

Backup herunterladen

+ +
-
) +
+
) } export default System \ No newline at end of file diff --git a/src/route/users/index.jsx b/src/route/users/index.jsx index ec2843d..df57d3d 100644 --- a/src/route/users/index.jsx +++ b/src/route/users/index.jsx @@ -7,7 +7,7 @@ import AppState, { UserTable } from "../../store"; function Users({ pageid }) { const [viewstate, setview] = useState({ limit: 100, page: 1, pages: null }) const { usertable, userreducer } = useContext(UserTable); - let [sessiondata, setsession] = useContext(AppState).session; + let [sessiondata,] = useContext(AppState).session; const setPage = (e) => { e.preventDefault(); console.log(e) @@ -19,13 +19,13 @@ function Users({ pageid }) { useEffect(() => { if (usertable === undefined) - console.log("TOKEN"); - console.log(sessiondata.token); - api.fetchdb(sessiondata.token).then(imported => { - let action = { type: 'import', imported }; - userreducer(action); - }); - },[sessiondata]); + console.log("TOKEN"); + console.log(sessiondata.token); + api.fetchdb(sessiondata.token).then(imported => { + let action = { type: 'import', imported }; + userreducer(action); + }); + }, [sessiondata]); useEffect(() => { setview({ ...viewstate, pages: Math.ceil(usertable.length / viewstate.limit) }); @@ -36,11 +36,14 @@ function Users({ pageid }) { setview({ ...viewstate, page: pageid }) }, [pageid]) const deleteUser = (user) => { - let action = { - type: 'delete', - user - } - userreducer(action) + api.deleteUser(sessiondata.token,user).then(r=>{ + let action = { + type: 'delete', + user, r + } + userreducer(action) + }) + } const calculateView = () => { let start = viewstate.limit * (viewstate.page - 1); @@ -55,10 +58,13 @@ function Users({ pageid }) { return (
-
Suche: Limit:
+
+
Suche: Limit:
+
+
); diff --git a/src/store/reducers.js b/src/store/reducers.js index b363d5e..6875cba 100644 --- a/src/store/reducers.js +++ b/src/store/reducers.js @@ -23,7 +23,7 @@ export const userTableReducer = (state, action) => { let newstate = []; let newindex = 0; state.forEach((u, i) => { - if (user.uid && u.uid !== user.uid|| user.line && i !== user.line ) + if (user.uid && u.uid != user.uid|| user.line && i != user.line ) newstate.push({ ...u, line: newindex++ }) return newstate; }, []); @@ -32,7 +32,7 @@ export const userTableReducer = (state, action) => { case 'update': { let newstate = []; state.forEach((u, i) => { - if (user.uid && u.uid === user.uid || user.line && i === user.line) + if (user.uid && u.uid == user.uid || user.line && i == user.line) newstate.push(user); else newstate.push(u); diff --git a/src/style/_breadcrumbs.sass b/src/style/_breadcrumbs.sass index afa8a49..b7d77f0 100644 --- a/src/style/_breadcrumbs.sass +++ b/src/style/_breadcrumbs.sass @@ -5,7 +5,7 @@ background: #eee box-shadow: inset 0 0 .3em #ccc, 0 0 .5em #ddd padding: .3em - margin: 0 + margin: 0 .5em border: 0.05em solid #fff border-radius: .3em list-style-type: none diff --git a/src/style/_button.sass b/src/style/_button.sass new file mode 100644 index 0000000..abddc1d --- /dev/null +++ b/src/style/_button.sass @@ -0,0 +1,46 @@ +@mixin default + z-index: 1 + margin: 1em + padding: 0.5em + text-align: center + display: inline-block + position: relative + color: #333 + font-weight: bold + text-decoration: none + border: solid 1px #999 + border-radius: .2rem + input[type=submit] + display: block + background: none + width: 100% + border: none + border-radius: none + font-size: 2em + transition: all ease-in-out 100ms + + &::before + z-index: -1 + border-radius: .2rem + position: absolute + top: 0 + right: 0 + content: '' + background: transparent + width: 0% + height: 100% + transition: all ease-in-out 250ms + &:hover + color: #fff + input[type=submit] + background: #333 + color: #fff + border-radius: .3rem + &::before + top: 0 + left: 0 + right: auto + content: '' + background: #333 + width: 100% + height: 100% diff --git a/src/style/_input.sass b/src/style/_input.sass new file mode 100644 index 0000000..b5c58b5 --- /dev/null +++ b/src/style/_input.sass @@ -0,0 +1,37 @@ +@mixin textfield + position: relative + display: inline-block + margin: 0 .25em 1em .25em + background: #fafafa + border-radius: .3em + border-bottom: 1px solid #ccc + &:hover + background: #fff + input + display: block + background: none + width: 100% + border-radius: none + outline: none + border: none + font-size: 1em + padding: 0.7em + + label + user-select: none + position: absolute + top: 0.15em + left: 0.25em + font-size: .7em + cursor: text + transition: 250ms all + + &::placeholder + color: transparent + + &:placeholder-shown + label + color: grey + position: absolute + padding: .7em + top: 0em + left: 0em + font-size: 1em \ No newline at end of file diff --git a/src/style/_login.sass b/src/style/_login.sass index d8de6ff..aeac739 100644 --- a/src/style/_login.sass +++ b/src/style/_login.sass @@ -1,40 +1,13 @@ -@mixin text-input - position: relative - input - display: block - width: 100% - border-radius: none - outline: none - border: none - font-size: 1.5em - padding: .7em - + label - position: absolute - top: 0 - left: 0 - cursor: text - transition: 250ms all - - &::placeholder - color: transparent - &:placeholder-shown + label - color: grey - font-size: 1.5em - position: absolute - padding: .7em - +@use 'input' @mixin login-form - padding: 1em + width: 100% margin: 0 auto display: flex flex-direction: column .input-box - @include text-input + @include input.textfield + font-size: 1.5em p font-size: 2em - input[type=submit] - border: none - border-radius: none - font-size: 2em diff --git a/src/style/_menu.sass b/src/style/_menu.sass index 10c6574..1d8a805 100644 --- a/src/style/_menu.sass +++ b/src/style/_menu.sass @@ -15,10 +15,13 @@ color: #666 //text-shadow: 0 0 .2em #000 width: 100% + transition: all ease-in-out 150ms //background: #ccc &:hover - background: #bbb - color: #333 + padding-left: .5em + background: #888 + color: #fff + text-shadow: 0 0 1em #fff &::after top: 100% left: 0 @@ -27,5 +30,5 @@ position: absolute width: 100% height: .1em - background: #8a8080 + background: #ccc //border-bottom-left-radius: 2em 1em \ No newline at end of file diff --git a/src/style/_pageselector.sass b/src/style/_pageselector.sass index d9307b1..8562461 100644 --- a/src/style/_pageselector.sass +++ b/src/style/_pageselector.sass @@ -1,16 +1,22 @@ @mixin pageselector text-align: center //background-color: #ccc - margin: 1em + margin: 2em ul list-style: none justify-content: center margin: 0 padding: 0 display: flex + flex-wrap: wrap li a + display: inline-flex text-decoration: none font-weight: bold + min-width: 2rem + min-height: 2rem + justify-content: center + align-items: center padding: .2em .5em margin: .3em border-radius: .3em @@ -23,4 +29,4 @@ &:hover color: #333 background: #fff - border: .1em solid #ccc \ No newline at end of file + border: .1em solid #444 diff --git a/src/style/style.sass b/src/style/style.sass index dc2822b..9a0419f 100644 --- a/src/style/style.sass +++ b/src/style/style.sass @@ -4,9 +4,12 @@ @use 'breadcrumbs' @use 'pageselector' @use 'footer' +@use 'button' +@use 'input' * - + //border: 1px dotted red box-sizing: border-box + html font-family: Helvetica, sans-serif font-size: 16px @@ -30,11 +33,12 @@ body position: fixed top: 0em width: 100% + max-width: 100vw height: 4rem display: flex flex-direction: column - justify-content: flex-end - padding: .5em 0 + justify-content: center + padding: 0.5em .5em margin: 0 0 0 0 background: linear-gradient(#9e9e9e 0% , #d1d1d1 100%) box-shadow: 0 0 .2em #444 @@ -49,6 +53,7 @@ body .container width: clamp(5ch, 100%,75ch) margin: 0 auto + .breadcrumb @include breadcrumbs.breadcrumbs @@ -73,6 +78,7 @@ body display: flex flex-direction: row background: #eee + margin: 0 0.5em padding: .5em 0 border-radius: .3em &:not(:last-child) @@ -131,4 +137,27 @@ body background-image: url("../assets/icons/edit-icon3.svg") footer - @include footer.footer \ No newline at end of file + @include footer.footer + +.contentbox + display: flex + flex-wrap: wrap + flex-direction: column + align-content: stretch + padding: 1em + margin: 1em 0.5em + border: 1px solid #fff + background: #f4f4f4 + box-shadow: 0 0 .5em #ddd, inset 0 0 1em #fff + border-radius: .5em + h2 + margin: 0 + display: flex + flex-break: after + flex-basis: 100% +.button + @include button.default + +.textbox + @include input.textfield + font-size: 1.5em