|
|
@ -1,31 +1,81 @@ |
|
|
|
|
|
|
|
import { flatMap } from "lodash"; |
|
|
|
import { observer } from "mobx-react"; |
|
|
|
import { observer } from "mobx-react"; |
|
|
|
|
|
|
|
import * as moment from "moment"; |
|
|
|
import * as React from "react"; |
|
|
|
import * as React from "react"; |
|
|
|
import { Button, Table } from "semantic-ui-react"; |
|
|
|
import { Button, Table } from "semantic-ui-react"; |
|
|
|
|
|
|
|
|
|
|
|
import { Duration } from "@common/Duration"; |
|
|
|
import { Duration } from "@common/Duration"; |
|
|
|
import { Program, Schedule } from "@common/sprinklers"; |
|
|
|
import { Program, Schedule, TimeOfDay, Weekday, DateOfYear, Section } from "@common/sprinklers"; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function timeToString(time: TimeOfDay) { |
|
|
|
|
|
|
|
return moment(time).format("LTS"); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
function formatDateOfYear(day: DateOfYear | null, prefix: string) { |
|
|
|
|
|
|
|
if (day == null) { |
|
|
|
|
|
|
|
return null; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
return prefix + moment(day).format("l"); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
@observer |
|
|
|
@observer |
|
|
|
export class ScheduleView extends React.Component<{ schedule: Schedule }> { |
|
|
|
export class ScheduleView extends React.Component<{ schedule: Schedule }> { |
|
|
|
render() { |
|
|
|
render() { |
|
|
|
|
|
|
|
const { schedule } = this.props; |
|
|
|
|
|
|
|
const times = schedule.times.map((time, i) => timeToString(time)) |
|
|
|
|
|
|
|
.join(", "); |
|
|
|
|
|
|
|
const weekdays = schedule.weekdays.map((weekday) => |
|
|
|
|
|
|
|
Weekday[weekday]).join(", "); |
|
|
|
|
|
|
|
const from = formatDateOfYear(schedule.from, "From "); |
|
|
|
|
|
|
|
const to = formatDateOfYear(schedule.to, "To "); |
|
|
|
return ( |
|
|
|
return ( |
|
|
|
<div>{JSON.stringify(this.props.schedule)}</div> |
|
|
|
<div> |
|
|
|
|
|
|
|
At {times} <br /> |
|
|
|
|
|
|
|
On {weekdays} <br /> |
|
|
|
|
|
|
|
{from} <br /> |
|
|
|
|
|
|
|
{to} |
|
|
|
|
|
|
|
</div> |
|
|
|
); |
|
|
|
); |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
@observer |
|
|
|
@observer |
|
|
|
export default class ProgramTable extends React.Component<{ programs: Program[] }> { |
|
|
|
export default class ProgramTable extends React.Component<{ programs: Program[], sections: Section[] }> { |
|
|
|
private static renderRows(program: Program, i: number): JSX.Element[] | null { |
|
|
|
render() { |
|
|
|
|
|
|
|
const programRows = Array.prototype.concat.apply([], |
|
|
|
|
|
|
|
this.props.programs.map(this.renderRows)); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return ( |
|
|
|
|
|
|
|
<Table celled> |
|
|
|
|
|
|
|
<Table.Header> |
|
|
|
|
|
|
|
<Table.Row> |
|
|
|
|
|
|
|
<Table.HeaderCell colSpan="7">Programs</Table.HeaderCell> |
|
|
|
|
|
|
|
</Table.Row> |
|
|
|
|
|
|
|
<Table.Row> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--number">#</Table.HeaderCell> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--name">Name</Table.HeaderCell> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--running">Running?</Table.HeaderCell> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--enabled">Enabled?</Table.HeaderCell> |
|
|
|
|
|
|
|
</Table.Row> |
|
|
|
|
|
|
|
</Table.Header> |
|
|
|
|
|
|
|
<Table.Body> |
|
|
|
|
|
|
|
{programRows} |
|
|
|
|
|
|
|
</Table.Body> |
|
|
|
|
|
|
|
</Table> |
|
|
|
|
|
|
|
); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private renderRows = (program: Program, i: number): JSX.Element[] | null => { |
|
|
|
if (!program) { |
|
|
|
if (!program) { |
|
|
|
return null; |
|
|
|
return null; |
|
|
|
} |
|
|
|
} |
|
|
|
const { name, running, enabled, schedule, sequence } = program; |
|
|
|
const { name, running, enabled, schedule, sequence } = program; |
|
|
|
const sequenceItems = sequence.map((item, index) => { |
|
|
|
const sequenceItems = flatMap(sequence, (item, index) => { |
|
|
|
|
|
|
|
const section = this.props.sections[item.section]; |
|
|
|
const duration = Duration.fromSeconds(item.duration); |
|
|
|
const duration = Duration.fromSeconds(item.duration); |
|
|
|
return ( |
|
|
|
return [ |
|
|
|
<li key={index}>Section {item.section + 1 + ""} for {duration.toString()}</li> |
|
|
|
<em key={index}>"{section.name}"</em>, ` for ${duration.toString()}, `, |
|
|
|
); |
|
|
|
]; |
|
|
|
}); |
|
|
|
}); |
|
|
|
const cancelOrRun = () => running ? program.cancel() : program.run(); |
|
|
|
const cancelOrRun = () => running ? program.cancel() : program.run(); |
|
|
|
return [( |
|
|
|
return [( |
|
|
@ -34,7 +84,7 @@ export default class ProgramTable extends React.Component<{ programs: Program[] |
|
|
|
<Table.Cell className="program--name">{name}</Table.Cell> |
|
|
|
<Table.Cell className="program--name">{name}</Table.Cell> |
|
|
|
<Table.Cell className="program--running"> |
|
|
|
<Table.Cell className="program--running"> |
|
|
|
{running ? "Running" : "Not running"} |
|
|
|
{running ? "Running" : "Not running"} |
|
|
|
<Button onClick={cancelOrRun}> |
|
|
|
<Button className="program--runningButton" onClick={cancelOrRun}> |
|
|
|
{running ? "Cancel" : "Run"} |
|
|
|
{running ? "Cancel" : "Run"} |
|
|
|
</Button> |
|
|
|
</Button> |
|
|
|
</Table.Cell> |
|
|
|
</Table.Cell> |
|
|
@ -43,36 +93,10 @@ export default class ProgramTable extends React.Component<{ programs: Program[] |
|
|
|
), ( |
|
|
|
), ( |
|
|
|
<Table.Row key={i + .5}> |
|
|
|
<Table.Row key={i + .5}> |
|
|
|
<Table.Cell className="program--sequence" colSpan="4"> |
|
|
|
<Table.Cell className="program--sequence" colSpan="4"> |
|
|
|
<ul> |
|
|
|
<h4>Sequence: </h4> {sequenceItems} |
|
|
|
{sequenceItems} |
|
|
|
<h4>Schedule: </h4> <ScheduleView schedule={schedule} /> |
|
|
|
</ul> |
|
|
|
|
|
|
|
<ScheduleView schedule={schedule} /> |
|
|
|
|
|
|
|
</Table.Cell> |
|
|
|
</Table.Cell> |
|
|
|
</Table.Row> |
|
|
|
</Table.Row> |
|
|
|
)]; |
|
|
|
)]; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
render() { |
|
|
|
|
|
|
|
const programRows = Array.prototype.concat.apply([], |
|
|
|
|
|
|
|
this.props.programs.map(ProgramTable.renderRows)); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return ( |
|
|
|
|
|
|
|
<Table celled> |
|
|
|
|
|
|
|
<Table.Header> |
|
|
|
|
|
|
|
<Table.Row> |
|
|
|
|
|
|
|
<Table.HeaderCell colSpan="7">Programs</Table.HeaderCell> |
|
|
|
|
|
|
|
</Table.Row> |
|
|
|
|
|
|
|
<Table.Row> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--number">#</Table.HeaderCell> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--name">Name</Table.HeaderCell> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--running">Running?</Table.HeaderCell> |
|
|
|
|
|
|
|
<Table.HeaderCell className="program--enabled">Enabled?</Table.HeaderCell> |
|
|
|
|
|
|
|
</Table.Row> |
|
|
|
|
|
|
|
</Table.Header> |
|
|
|
|
|
|
|
<Table.Body> |
|
|
|
|
|
|
|
{programRows} |
|
|
|
|
|
|
|
</Table.Body> |
|
|
|
|
|
|
|
</Table> |
|
|
|
|
|
|
|
); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
} |
|
|
|
} |
|
|
|