import { useState } from 'react';
import type { FC } from 'react';
import { toast } from 'react-toastify';
import CancelIcon from '@mui/icons-material/Cancel';
import PowerSettingsNewIcon from '@mui/icons-material/PowerSettingsNew';
import WarningIcon from '@mui/icons-material/Warning';
import {
Box,
Button,
Checkbox,
Divider,
Grid,
InputAdornment,
MenuItem,
TextField,
Typography
} from '@mui/material';
import * as SystemApi from 'api/system';
import { useRequest } from 'alova';
import type { ValidateFieldsError } from 'async-validator';
import {
BlockFormControlLabel,
BlockNavigation,
ButtonRow,
FormLoader,
MessageBox,
SectionContent,
ValidatedTextField,
useLayoutTitle
} from 'components';
import RestartMonitor from 'framework/system/RestartMonitor';
import { useI18nContext } from 'i18n/i18n-react';
import { numberValue, updateValueDirty, useRest } from 'utils';
import { validate } from 'validators';
import * as EMSESP from './api';
import { BOARD_PROFILES } from './types';
import type { Settings } from './types';
import { createSettingsValidator } from './validators';
export function boardProfileSelectItems() {
return Object.keys(BOARD_PROFILES).map((code) => (
));
}
const ApplicationSettings: FC = () => {
const {
loadData,
saveData,
saving,
updateDataValue,
data,
origData,
dirtyFlags,
setDirtyFlags,
blocker,
errorMessage,
restartNeeded
} = useRest({
read: EMSESP.readSettings,
update: EMSESP.writeSettings
});
const [restarting, setRestarting] = useState();
const { LL } = useI18nContext();
const updateFormValue = updateValueDirty(
origData,
dirtyFlags,
setDirtyFlags,
updateDataValue
);
const [fieldErrors, setFieldErrors] = useState();
const {
loading: processingBoard,
send: readBoardProfile,
onSuccess: onSuccessBoardProfile
} = useRequest((boardProfile: string) => EMSESP.getBoardProfile(boardProfile), {
immediate: false
});
const { send: restartCommand } = useRequest(SystemApi.restart(), {
immediate: false
});
onSuccessBoardProfile((event) => {
const response = event.data as Settings;
updateDataValue({
...data,
board_profile: response.board_profile,
led_gpio: response.led_gpio,
dallas_gpio: response.dallas_gpio,
rx_gpio: response.rx_gpio,
tx_gpio: response.tx_gpio,
pbutton_gpio: response.pbutton_gpio,
phy_type: response.phy_type,
eth_power: response.eth_power,
eth_phy_addr: response.eth_phy_addr,
eth_clock_mode: response.eth_clock_mode
});
});
const updateBoardProfile = async (board_profile: string) => {
await readBoardProfile(board_profile).catch((error: Error) => {
toast.error(error.message);
});
};
useLayoutTitle(LL.APPLICATION());
const content = () => {
if (!data) {
return ;
}
const validateAndSubmit = async () => {
try {
setFieldErrors(undefined);
await validate(createSettingsValidator(data), data);
} catch (error) {
setFieldErrors(error as ValidateFieldsError);
} finally {
await saveData();
}
};
const changeBoardProfile = (event: React.ChangeEvent) => {
const boardProfile = event.target.value;
updateFormValue(event);
if (boardProfile === 'CUSTOM') {
updateDataValue({
...data,
board_profile: boardProfile
});
} else {
void updateBoardProfile(boardProfile);
}
};
const restart = async () => {
await validateAndSubmit();
await restartCommand().catch((error: Error) => {
toast.error(error.message);
});
setRestarting(true);
};
return (
<>
{LL.INTERFACE_BOARD_PROFILE()}
{LL.BOARD_PROFILE_TEXT()}
{boardProfileSelectItems()}
{data.board_profile === 'CUSTOM' && (
<>
{data.phy_type !== 0 && (
)}
>
)}
{LL.SETTINGS_OF(LL.EMS_BUS(0))}
{LL.GENERAL_OPTIONS()}
{data.led_gpio !== 0 && (
}
label={LL.HIDE_LED()}
disabled={saving}
/>
)}
}
label={LL.ENABLE_TELNET()}
disabled={saving}
/>
}
label={LL.ENABLE_ANALOG()}
disabled={saving}
/>
}
label={LL.CONVERT_FAHRENHEIT()}
disabled={saving}
/>
}
label={LL.BYPASS_TOKEN()}
disabled={saving}
/>
}
label={LL.READONLY()}
disabled={saving}
/>
}
label={LL.UNDERCLOCK_CPU()}
disabled={saving}
/>
}
label={LL.HEATINGOFF()}
disabled={saving}
/>
}
label={LL.REMOTE_TIMEOUT_EN()}
/>
{data.remote_timeout_en && (
{LL.HOURS()}
)
}}
fullWidth
variant="outlined"
value={numberValue(data.remote_timeout)}
type="number"
onChange={updateFormValue}
/>
)}
}
label={LL.ENABLE_SHOWER_TIMER()}
disabled={saving}
/>
}
label={LL.ENABLE_SHOWER_ALERT()}
disabled={!data.shower_timer}
/>
{data.shower_timer && (
{LL.SECONDS()}
)
}}
variant="outlined"
value={numberValue(data.shower_min_duration)}
fullWidth
type="number"
onChange={updateFormValue}
/>
)}
{data.shower_alert && (
<>
{LL.MINUTES()}
)
}}
variant="outlined"
value={numberValue(data.shower_alert_trigger)}
fullWidth
type="number"
onChange={updateFormValue}
disabled={!data.shower_timer}
/>
{LL.SECONDS()}
)
}}
variant="outlined"
value={numberValue(data.shower_alert_coldshot)}
fullWidth
type="number"
onChange={updateFormValue}
disabled={!data.shower_timer}
/>
>
)}
{LL.FORMATTING_OPTIONS()}
{data.dallas_gpio !== 0 && (
<>
{LL.TEMP_SENSORS()}
}
label={LL.ENABLE_PARASITE()}
disabled={saving}
/>
>
)}
{LL.LOGGING()}
}
label={LL.LOG_HEX()}
disabled={saving}
/>
}
label={LL.ENABLE_SYSLOG()}
/>
{data.syslog_enabled && (
{LL.SECONDS()}
)
}}
fullWidth
variant="outlined"
value={numberValue(data.syslog_mark_interval)}
type="number"
onChange={updateFormValue}
margin="normal"
disabled={saving}
/>
)}
{restartNeeded && (
}
variant="contained"
color="error"
onClick={restart}
>
{LL.RESTART()}
)}
{!restartNeeded && dirtyFlags && dirtyFlags.length !== 0 && (
}
disabled={saving}
variant="outlined"
color="primary"
type="submit"
onClick={loadData}
>
{LL.CANCEL()}
}
disabled={saving}
variant="contained"
color="info"
type="submit"
onClick={validateAndSubmit}
>
{LL.APPLY_CHANGES(dirtyFlags.length)}
)}
>
);
};
return (
{blocker ? : null}
{restarting ? : content()}
);
};
export default ApplicationSettings;