Browse Source

Done?

webui
Stian Aune 5 years ago
parent
commit
042130f11c
  1. 3
      webui/src/App.js
  2. 53
      webui/src/Components/Bridge.jsx
  3. 23
      webui/src/Components/BridgeLight.jsx
  4. 25
      webui/src/Components/Bridges.jsx
  5. 94
      webui/src/Components/Modals/BridgeModal.jsx
  6. 18
      webui/src/Components/Pages/AdminPage.jsx
  7. 99
      webui/src/Hooks/bridge.js
  8. 42
      webui/src/Hooks/lights.js

3
webui/src/App.js

@ -10,8 +10,10 @@ import IndexPage from "./Components/Pages/IndexPage";
import GroupPage from "./Components/Pages/GroupPage";
import Loading from "./Components/Loading";
import LightPage from "./Components/Pages/LightPage";
import AdminPage from "./Components/Pages/AdminPage";
export default function App() {
const [hasStarted, setHasStarted] = useState(false);
const {isLoggedIn, isChecked, verify} = useAuth();
@ -34,6 +36,7 @@ export default function App() {
<Route exact path="/" component={IndexPage}/>
<Route exact path="/lights" component={LightPage}/>
<Route exact path="/groups" component={GroupPage}/>
<Route exact path="/admin" component={AdminPage}/>
</>
)}
</Container>

53
webui/src/Components/Bridge.jsx

@ -0,0 +1,53 @@
import React, {useState} from "react";
import {Button, Card, CardBody, CardFooter, CardHeader} from "reactstrap";
import useBridges from "../Hooks/bridge";
import BridgeModal from "./Modals/BridgeModal";
import useLights from "../Hooks/lights";
import Loading from "./Loading";
import BridgeLight from "./BridgeLight";
function Bridge({addr, driver, id, name}) {
const {forgetBridge, discoverLights} = useBridges();
const {lightsByBridge} = useLights();
const [modal, setModal] = useState(false);
function edit() {
setModal(true);
}
function unEdit() {
setModal(false);
}
function forget() {
if (window.confirm(`Vil du virkelig glemme bruen "${name}"?`)) {
forgetBridge(id);
}
}
function discover() {
discoverLights(id);
}
const lights = lightsByBridge(id);
const hasLights = lights !== null;
return (
<Card className="mt-3">
<CardHeader>{name} ({driver}, {addr})</CardHeader>
<CardBody>
{hasLights ? lights.map(l => <BridgeLight key={l.id} {...l} />) : <Loading/>}
</CardBody>
<CardFooter>
<Button color="info" onClick={discover}>Oppdag lys</Button>
{" "}
<Button color="secondary" onClick={edit}>Endre</Button>
{" "}
<Button color="danger" onClick={forget}>Glem</Button>
</CardFooter>
{modal && <BridgeModal bridge={{addr, driver, id, name}} onCancel={unEdit} />}
</Card>
);
}
export default Bridge;

23
webui/src/Components/BridgeLight.jsx

@ -0,0 +1,23 @@
import React, {useState} from "react";
import {Button, FormGroup} from "reactstrap";
import useBridges from "../Hooks/bridge";
function BridgeLight({ id, bridgeId, name }) {
const [waiting, setWaiting] = useState(false);
const {forgetLight} = useBridges();
function forget() {
setWaiting(true);
forgetLight(bridgeId, id);
}
return (
<FormGroup>
<Button color="danger" size="sm" disabled={waiting} onClick={forget}>Glem</Button>
{" "}
{name}
</FormGroup>
);
}
export default BridgeLight;

25
webui/src/Components/Bridges.jsx

@ -0,0 +1,25 @@
import React, {useState} from "react";
import useBridges from "../Hooks/bridge";
import Bridge from "./Bridge";
import {Button, FormGroup} from "reactstrap";
import BridgeModal from "./Modals/BridgeModal";
function Bridges() {
const [modal, setModal] = useState(false);
const {bridges} = useBridges();
if (bridges === null) {
return <></>;
}
return (
<div>
{bridges.map(bridge => <Bridge key={bridge.id} {...bridge} />)}
<FormGroup className="free-buttons">
<Button color="success" onClick={() => setModal(true)} >Søk etter bru</Button>
</FormGroup>
{modal && <BridgeModal onCancel={() => setModal(false)}/> }
</div>
);
}
export default Bridges;

94
webui/src/Components/Modals/BridgeModal.jsx

@ -0,0 +1,94 @@
import React, {useState} from "react";
import {Button, Col, Form, FormGroup, Input, Label, Modal, ModalBody, ModalFooter, ModalHeader} from "reactstrap";
import useBridges from "../../Hooks/bridge";
import Loading from "../Loading";
function BridgeModal({onCancel, bridge = null}) {
const {addBridge, editBridge} = useBridges();
const edit = bridge !== null;
const [name, setName] = useState(edit ? bridge.name : "");
const [driver, setDriver] = useState(edit ? bridge.driver : "");
const [addr, setAddr] = useState(edit ? bridge.addr : "");
const [waiting, setWaiting] = useState(false);
function onConfirm() {
if (edit) {
editBridge(bridge.id, name);
} else {
setWaiting(true);
addBridge(name, driver, addr, (result) => {
if (!result) {
alert("Noe gikk galt");
}
setWaiting(false);
onCancel();
});
}
}
return (
<Modal isOpen={true}>
<ModalHeader>{edit ? "Bruegenskaper" : "Ny bru"}</ModalHeader>
<ModalBody>
{waiting ? (
<Loading/>
) : (
<Form>
<FormGroup row>
<Label sm={3} for="text-name">
Navn:
</Label>
<Col sm={9}>
<Input type="text"
id="text-name"
name="name"
value={name}
onChange={e => setName(e.target.value)}
/>
</Col>
</FormGroup>
<FormGroup row>
<Label sm={3} for="text-driver">
Driver:
</Label>
<Col sm={9}>
<Input type="text"
id="text-driver"
name="driver"
value={driver}
onChange={e => setDriver(e.target.value)}
disabled={edit}
/>
</Col>
</FormGroup>
<FormGroup row>
<Label sm={3} for="text-name">
Adresse:
</Label>
<Col sm={9}>
<Input type="text"
id="text-addr"
name="addr"
value={addr}
onChange={e => setAddr(e.target.value)}
disabled={edit}
/>
</Col>
</FormGroup>
</Form>
)}
</ModalBody>
<ModalFooter>
<Button color="primary" disabled={waiting} onClick={onConfirm}>Bekreft</Button>
{" "}
<Button color="secondary" disabled={waiting} onClick={onCancel}>Avbryt</Button>
</ModalFooter>
</Modal>
);
}
export default BridgeModal;

18
webui/src/Components/Pages/AdminPage.jsx

@ -0,0 +1,18 @@
import React from "react";
import Bridges from "../Bridges";
import useAuth from "../../Hooks/auth";
function AdminPage() {
const {user} = useAuth();
if (user.name === "Admin") {
return <></>;
}
return (
<div>
<Bridges/>
</div>
);
}
export default AdminPage;

99
webui/src/Hooks/bridge.js

@ -0,0 +1,99 @@
import {setGlobal, useGlobal} from "reactn";
import {useEffect} from "react";
import {fetchDelete, fetchGet, fetchPatch, fetchPost} from "../Helpers/fetcher";
import useLights from "./lights";
setGlobal({
bridges: null,
});
function useBridges() {
const [bridges, setBridges] = useGlobal("bridges");
const {reloadLights} = useLights();
function reloadBridges() {
setBridges(null);
fetchGet("/bridge/").then(({error, data}) => {
if (error !== null) {
console.error(error);
return;
}
setBridges(data);
});
}
useEffect(() => {
if (bridges === null) {
reloadBridges();
}
}, []);
function bridge(id) {
if (bridges === null) {
return null;
}
return bridges.find(b => b.id === id);
}
function forgetBridge(id) {
fetchDelete(`/bridge/${id}`).then(({data, error}) => {
if (error !== null) {
console.error(error);
}
reloadBridges();
});
}
function forgetLight(bridgeId, lightId) {
fetchDelete(`/bridge/${bridgeId}/light/${lightId}`).then(({data, error}) => {
if (error !== null) {
console.error(error);
}
reloadBridges();
});
}
function addBridge(name, driver, addr, callback = null) {
fetchPost("/bridge/", {name, driver, addr}).then(({error}) => {
if (error !== null) {
console.error(error);
}
if (callback !== null) {
callback(error === null);
}
reloadBridges();
});
}
function editBridge(id, name) {
fetchPatch(`/bridge/${id}`, {name}).then(({error}) => {
if (error !== null) {
console.error(error);
}
reloadBridges();
});
}
function discoverLights(id) {
fetchPost(`/bridge/${id}/discover`).then(({error}) => {
if (error !== null) {
console.error(error);
}
reloadLights();
reloadBridges();
});
}
return {bridges, bridge, forgetBridge, addBridge, editBridge, forgetLight, discoverLights};
}
export default useBridges;

42
webui/src/Hooks/lights.js

@ -0,0 +1,42 @@
import {setGlobal, useGlobal} from "reactn";
import {fetchGet} from "../Helpers/fetcher";
import {useEffect} from "react";
setGlobal({
lights: null,
});
function useLights() {
const [lights, setLights] = useGlobal("lights");
function reloadLights() {
setLights(null);
fetchGet("/light/").then(({error, data}) => {
if (error !== null) {
console.error(error);
return;
}
setLights(data);
});
}
useEffect(() => {
if (lights === null) {
reloadLights();
}
}, []);
function lightsByBridge(bridgeId) {
if (lights === null) {
return null;
}
return lights.filter(light => light.bridgeId === bridgeId);
}
return {lights, lightsByBridge, reloadLights};
}
export default useLights;
Loading…
Cancel
Save