CEC-381 Install messages and update styling (#76)
* Styling * Handle install messages * Update progress * Display download and install status
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@@ -75,8 +75,12 @@ const SendCommand = ({ vins }) => {
|
|||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={classes.form}>
|
<div className={`${classes.form}`} style={{ marginTop: 20 }}>
|
||||||
<FormControl className={classes.formControlInline} variant="outlined">
|
<FormControl
|
||||||
|
className={classes.formControlInline}
|
||||||
|
variant="outlined"
|
||||||
|
size="small"
|
||||||
|
>
|
||||||
<InputLabel htmlFor="send-command" style={{ backgroundColor: "White" }}>
|
<InputLabel htmlFor="send-command" style={{ backgroundColor: "White" }}>
|
||||||
Command
|
Command
|
||||||
</InputLabel>
|
</InputLabel>
|
||||||
@@ -97,7 +101,11 @@ const SendCommand = ({ vins }) => {
|
|||||||
))}
|
))}
|
||||||
</Select>
|
</Select>
|
||||||
</FormControl>
|
</FormControl>
|
||||||
<FormControl className={classes.formControlInline} variant="outlined">
|
<FormControl
|
||||||
|
className={classes.formControlInline}
|
||||||
|
variant="outlined"
|
||||||
|
size="small"
|
||||||
|
>
|
||||||
<InputLabel
|
<InputLabel
|
||||||
htmlFor="send-parameter"
|
htmlFor="send-parameter"
|
||||||
style={{ backgroundColor: "White" }}
|
style={{ backgroundColor: "White" }}
|
||||||
@@ -127,6 +135,7 @@ const SendCommand = ({ vins }) => {
|
|||||||
aria-label="send command"
|
aria-label="send command"
|
||||||
component="span"
|
component="span"
|
||||||
onClick={clickHandler}
|
onClick={clickHandler}
|
||||||
|
size="small"
|
||||||
disabled={busy || vins.length === 0}
|
disabled={busy || vins.length === 0}
|
||||||
>
|
>
|
||||||
<SendIcon fontSize="large" />
|
<SendIcon fontSize="large" />
|
||||||
|
|||||||
@@ -56,16 +56,18 @@ const MainForm = () => {
|
|||||||
return (
|
return (
|
||||||
<div className={classes.paper} style={{ height: 700, width: "100%" }}>
|
<div className={classes.paper} style={{ height: 700, width: "100%" }}>
|
||||||
<Grid container className={classes.root} spacing={2}>
|
<Grid container className={classes.root} spacing={2}>
|
||||||
<Grid item md={6}>
|
<Grid item md={4} style={{ textAlign: "justify" }}>
|
||||||
<Link to="/vehicle-add" className={classes.labelInline}>
|
<Link to="/vehicle-add">
|
||||||
<AddCircleIcon fontSize="large" />
|
<AddCircleIcon fontSize="large" />
|
||||||
</Link>
|
</Link>
|
||||||
<SearchField classes={classes} onSearch={handleSearch} />
|
|
||||||
<div
|
<div
|
||||||
className={classes.labelInline}
|
className={classes.labelInline}
|
||||||
>{`${selected.length} Selected`}</div>
|
>{`${selected.length} Selected`}</div>
|
||||||
</Grid>
|
</Grid>
|
||||||
<Grid item md={6} style={{ textAlign: "right" }}>
|
<Grid item md={4} style={{ textAlign: "center" }}>
|
||||||
|
<SearchField classes={classes} onSearch={handleSearch} />
|
||||||
|
</Grid>
|
||||||
|
<Grid item md={4} style={{ textAlign: "right" }}>
|
||||||
<SendCommand vins={selected} style={{ display: "flex" }} />
|
<SendCommand vins={selected} style={{ display: "flex" }} />
|
||||||
</Grid>
|
</Grid>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
|||||||
@@ -76,10 +76,20 @@ export const CarUpdatesProvider = ({ children }) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const applyProgressStatus = (item, status) => {
|
const applyProgressStatus = (item, status) => {
|
||||||
if (status.msg === "package_download_complete") {
|
if (
|
||||||
delete item.progress;
|
status.msg === "package_download_start" ||
|
||||||
|
status.msg === "download_start"
|
||||||
|
) {
|
||||||
|
item.progress = 1;
|
||||||
|
item.status = "downloading";
|
||||||
|
} else if (status.msg === "package_download_complete") {
|
||||||
item.status = "downloaded";
|
item.status = "downloaded";
|
||||||
} else if (status.msg === "downloading" && status.package_total > 0) {
|
} else if (
|
||||||
|
status.msg === "downloading" &&
|
||||||
|
status.package_current &&
|
||||||
|
status.package_total &&
|
||||||
|
status.package_total > 0
|
||||||
|
) {
|
||||||
let progress = Math.floor(
|
let progress = Math.floor(
|
||||||
(100 * status.package_current) / status.package_total
|
(100 * status.package_current) / status.package_total
|
||||||
);
|
);
|
||||||
@@ -88,8 +98,23 @@ export const CarUpdatesProvider = ({ children }) => {
|
|||||||
item.status = `downloading ${progress}%`;
|
item.status = `downloading ${progress}%`;
|
||||||
} else if (status.error > 0 || status.msg === "download_error") {
|
} else if (status.error > 0 || status.msg === "download_error") {
|
||||||
item.status = "download error";
|
item.status = "download error";
|
||||||
|
} else if (status.msg === "package_install_start") {
|
||||||
|
item.progress = 1;
|
||||||
|
item.status = "installing";
|
||||||
|
} else if (
|
||||||
|
status.msg === "installing" &&
|
||||||
|
status.installed &&
|
||||||
|
status.total_files &&
|
||||||
|
status.total_files > 0
|
||||||
|
) {
|
||||||
|
let progress = Math.floor((100 * status.installed) / status.total_files);
|
||||||
|
item.progress = progress;
|
||||||
|
item.status = `installing ${progress}%`;
|
||||||
|
} else if (status.msg === "package_install_complete") {
|
||||||
|
item.status = "installed";
|
||||||
} else {
|
} else {
|
||||||
item.status = "downloading";
|
delete item.progress;
|
||||||
|
item.status = status.msg;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -97,8 +122,8 @@ export const CarUpdatesProvider = ({ children }) => {
|
|||||||
let items = JSON.parse(JSON.stringify(carUpdates));
|
let items = JSON.parse(JSON.stringify(carUpdates));
|
||||||
|
|
||||||
statuses.forEach((status) => {
|
statuses.forEach((status) => {
|
||||||
let item = items.find((item) => status.id === item.id);
|
let item = items.find((item) => status.car_update_id === item.id);
|
||||||
if (!item || status.id === 0) return;
|
if (!item || status.car_update_id === 0) return;
|
||||||
applyProgressStatus(item, status);
|
applyProgressStatus(item, status);
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -113,7 +138,7 @@ export const CarUpdatesProvider = ({ children }) => {
|
|||||||
try {
|
try {
|
||||||
setBusy(true);
|
setBusy(true);
|
||||||
const carupdateids = carUpdates.reduce((accum, update) => {
|
const carupdateids = carUpdates.reduce((accum, update) => {
|
||||||
if (update.status !== "downloaded") accum.push(update.id);
|
if (update.status !== "installed") accum.push(update.id);
|
||||||
return accum;
|
return accum;
|
||||||
}, []);
|
}, []);
|
||||||
if (carupdateids.length === 0) return;
|
if (carupdateids.length === 0) return;
|
||||||
|
|||||||
@@ -52,7 +52,9 @@ export default function MenuDrawer({ children }) {
|
|||||||
paper: classes.drawerPaper,
|
paper: classes.drawerPaper,
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<div className={classes.drawerHeader}>
|
<div
|
||||||
|
className={`${classes.drawerHeader} ${classes.drawerHeaderLogo}`}
|
||||||
|
>
|
||||||
<img
|
<img
|
||||||
src={logo}
|
src={logo}
|
||||||
alt="Fisker Admin Portal"
|
alt="Fisker Admin Portal"
|
||||||
|
|||||||
@@ -126,17 +126,18 @@ const MainForm = () => {
|
|||||||
<form className={classes.form} noValidate action="{onSubmit}">
|
<form className={classes.form} noValidate action="{onSubmit}">
|
||||||
<Typography variant="body2">Created {createDate}.</Typography>
|
<Typography variant="body2">Created {createDate}.</Typography>
|
||||||
<Grid container className={classes.root} spacing={2}>
|
<Grid container className={classes.root} spacing={2}>
|
||||||
<Grid item md={10}>
|
<Grid item md={2}>
|
||||||
<SearchField classes={classes} onSearch={handleSearch} />
|
|
||||||
<div
|
<div
|
||||||
className={classes.labelInline}
|
className={classes.labelInline}
|
||||||
>{`${selected.length} Selected`}</div>
|
>{`${selected.length} Selected`}</div>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
<Grid item md={8} style={{ textAlign: "center" }}>
|
||||||
|
<SearchField classes={classes} onSearch={handleSearch} />
|
||||||
|
</Grid>
|
||||||
<Grid item md={2} style={{ textAlign: "right" }}>
|
<Grid item md={2} style={{ textAlign: "right" }}>
|
||||||
<Button
|
<Button
|
||||||
type="submit"
|
type="submit"
|
||||||
disabled={busy || selected.length === 0}
|
disabled={busy || selected.length === 0}
|
||||||
fullWidth
|
|
||||||
variant="contained"
|
variant="contained"
|
||||||
color="primary"
|
color="primary"
|
||||||
className={classes.formControl}
|
className={classes.formControl}
|
||||||
|
|||||||
@@ -1,13 +1,13 @@
|
|||||||
import React, { useEffect, useState } from "react";
|
import React, { useEffect, useState } from "react";
|
||||||
import { Link } from "react-router-dom";
|
import { Link } from "react-router-dom";
|
||||||
import {
|
import {
|
||||||
|
Grid,
|
||||||
Table,
|
Table,
|
||||||
TableBody,
|
TableBody,
|
||||||
TableCell,
|
TableCell,
|
||||||
TableFooter,
|
TableFooter,
|
||||||
TablePagination,
|
TablePagination,
|
||||||
TableRow,
|
TableRow,
|
||||||
Toolbar,
|
|
||||||
Tooltip,
|
Tooltip,
|
||||||
} from "@material-ui/core";
|
} from "@material-ui/core";
|
||||||
import AddCircleIcon from "@material-ui/icons/AddCircle";
|
import AddCircleIcon from "@material-ui/icons/AddCircle";
|
||||||
@@ -185,12 +185,17 @@ const MainForm = () => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={classes.paper} style={{ height: 700, width: "100%" }}>
|
<div className={classes.paper} style={{ height: 700, width: "100%" }}>
|
||||||
<Toolbar className={classes.tableToolbar}>
|
<Grid container className={classes.root} spacing={2}>
|
||||||
|
<Grid item md={4} style={{ textAlign: "justify" }}>
|
||||||
<Link to="/package-create" className={classes.labelInline}>
|
<Link to="/package-create" className={classes.labelInline}>
|
||||||
<AddCircleIcon fontSize="large" />
|
<AddCircleIcon fontSize="large" />
|
||||||
</Link>
|
</Link>
|
||||||
|
</Grid>
|
||||||
|
<Grid item md={4} style={{ textAlign: "center" }}>
|
||||||
<SearchField classes={classes} onSearch={handleSearch} />
|
<SearchField classes={classes} onSearch={handleSearch} />
|
||||||
</Toolbar>
|
</Grid>
|
||||||
|
<Grid item md={4} style={{ textAlign: "right" }}></Grid>
|
||||||
|
</Grid>
|
||||||
<Table>
|
<Table>
|
||||||
<TableHeaderSortable
|
<TableHeaderSortable
|
||||||
classes={classes}
|
classes={classes}
|
||||||
|
|||||||
@@ -45,7 +45,7 @@ const useStyles = makeStyles((theme) => ({
|
|||||||
},
|
},
|
||||||
labelInline: {
|
labelInline: {
|
||||||
fontSize: "1.25em",
|
fontSize: "1.25em",
|
||||||
margin: theme.spacing(2, 1, 1),
|
margin: theme.spacing(4, 1, 1),
|
||||||
display: "inline-flex",
|
display: "inline-flex",
|
||||||
boxSizing: "border-box",
|
boxSizing: "border-box",
|
||||||
verticalAlign: "bottom",
|
verticalAlign: "bottom",
|
||||||
@@ -77,6 +77,8 @@ const useStyles = makeStyles((theme) => ({
|
|||||||
easing: theme.transitions.easing.sharp,
|
easing: theme.transitions.easing.sharp,
|
||||||
duration: theme.transitions.duration.leavingScreen,
|
duration: theme.transitions.duration.leavingScreen,
|
||||||
}),
|
}),
|
||||||
|
color: "black",
|
||||||
|
backgroundColor: "white",
|
||||||
},
|
},
|
||||||
appBarShift: {
|
appBarShift: {
|
||||||
width: `calc(100% - ${DRAWER_WIDTH}px)`,
|
width: `calc(100% - ${DRAWER_WIDTH}px)`,
|
||||||
@@ -107,6 +109,9 @@ const useStyles = makeStyles((theme) => ({
|
|||||||
...theme.mixins.toolbar,
|
...theme.mixins.toolbar,
|
||||||
justifyContent: "flex-start",
|
justifyContent: "flex-start",
|
||||||
},
|
},
|
||||||
|
drawerHeaderLogo: {
|
||||||
|
backgroundColor: "#3f51b5",
|
||||||
|
},
|
||||||
content: {
|
content: {
|
||||||
flexGrow: 1,
|
flexGrow: 1,
|
||||||
padding: theme.spacing(3),
|
padding: theme.spacing(3),
|
||||||
|
|||||||
Reference in New Issue
Block a user