2022-11-16 10:08:09 +01:00
|
|
|
import * as React from 'react';
|
2022-12-27 10:59:36 +01:00
|
|
|
import { useEffect, useState } from 'react';
|
2022-10-28 17:13:41 +02:00
|
|
|
import { SubmitHandler, useForm, useWatch } from 'react-hook-form';
|
|
|
|
import { Machine } from '../../models/machine';
|
|
|
|
import MachineAPI from '../../api/machine';
|
|
|
|
import { useTranslation } from 'react-i18next';
|
|
|
|
import { FormInput } from '../form/form-input';
|
|
|
|
import { FormImageUpload } from '../form/form-image-upload';
|
|
|
|
import { IApplication } from '../../models/application';
|
|
|
|
import { Loader } from '../base/loader';
|
|
|
|
import { react2angular } from 'react2angular';
|
|
|
|
import { ErrorBoundary } from '../base/error-boundary';
|
|
|
|
import { FormRichText } from '../form/form-rich-text';
|
|
|
|
import { FormSwitch } from '../form/form-switch';
|
2022-11-03 11:46:30 +01:00
|
|
|
import { FormMultiFileUpload } from '../form/form-multi-file-upload';
|
|
|
|
import { FabButton } from '../base/fab-button';
|
2022-11-10 16:14:49 +01:00
|
|
|
import { AdvancedAccountingForm } from '../accounting/advanced-accounting-form';
|
2022-12-16 18:43:38 +01:00
|
|
|
import { FormSelect } from '../form/form-select';
|
|
|
|
import { SelectOption } from '../../models/select';
|
|
|
|
import MachineCategoryAPI from '../../api/machine-category';
|
2023-01-16 12:28:53 +01:00
|
|
|
import SettingAPI from '../../api/setting';
|
2022-12-16 18:43:38 +01:00
|
|
|
import { MachineCategory } from '../../models/machine-category';
|
2023-01-16 12:28:53 +01:00
|
|
|
import { FabAlert } from '../base/fab-alert';
|
2022-10-28 17:13:41 +02:00
|
|
|
|
|
|
|
declare const Application: IApplication;
|
|
|
|
|
|
|
|
interface MachineFormProps {
|
|
|
|
action: 'create' | 'update',
|
|
|
|
machine?: Machine,
|
|
|
|
onError: (message: string) => void,
|
|
|
|
onSuccess: (message: string) => void,
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Form to edit or create machines
|
|
|
|
*/
|
|
|
|
export const MachineForm: React.FC<MachineFormProps> = ({ action, machine, onError, onSuccess }) => {
|
|
|
|
const { handleSubmit, register, control, setValue, formState } = useForm<Machine>({ defaultValues: { ...machine } });
|
|
|
|
const output = useWatch<Machine>({ control });
|
|
|
|
const { t } = useTranslation('admin');
|
|
|
|
|
2022-12-16 18:43:38 +01:00
|
|
|
const [machineCategories, setMachineCategories] = useState<Array<MachineCategory>>([]);
|
2023-01-16 12:28:53 +01:00
|
|
|
const [isActiveAccounting, setIsActiveAccounting] = useState<boolean>(false);
|
2022-12-16 18:43:38 +01:00
|
|
|
|
|
|
|
// retrieve the full list of machine categories on component mount
|
2023-01-16 12:28:53 +01:00
|
|
|
// check advanced accounting activation
|
2022-12-16 18:43:38 +01:00
|
|
|
useEffect(() => {
|
|
|
|
MachineCategoryAPI.index()
|
|
|
|
.then(data => setMachineCategories(data))
|
|
|
|
.catch(e => onError(e));
|
2023-01-16 12:28:53 +01:00
|
|
|
SettingAPI.get('advanced_accounting').then(res => setIsActiveAccounting(res.value === 'true')).catch(onError);
|
2022-12-16 18:43:38 +01:00
|
|
|
}, []);
|
|
|
|
|
2022-10-28 17:13:41 +02:00
|
|
|
/**
|
|
|
|
* Callback triggered when the user validates the machine form: handle create or update
|
|
|
|
*/
|
|
|
|
const onSubmit: SubmitHandler<Machine> = (data: Machine) => {
|
2022-11-07 16:54:26 +01:00
|
|
|
MachineAPI[action](data).then((res) => {
|
2022-10-28 17:13:41 +02:00
|
|
|
onSuccess(t(`app.admin.machine_form.${action}_success`));
|
2022-11-07 16:54:26 +01:00
|
|
|
window.location.href = `/#!/machines/${res.slug}`;
|
2022-10-28 17:13:41 +02:00
|
|
|
}).catch(error => {
|
|
|
|
onError(error);
|
|
|
|
});
|
|
|
|
};
|
|
|
|
|
2023-01-23 12:05:02 +01:00
|
|
|
/**
|
|
|
|
* Callack triggered when the user changes the 'reservable' status of the machine:
|
|
|
|
* A reservable machine cannot be disabled
|
|
|
|
*/
|
|
|
|
const onReservableToggled = (reservable: boolean) => {
|
|
|
|
if (reservable) {
|
|
|
|
setValue('disabled', false);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Callack triggered when the user changes the 'disabled' status of the machine:
|
|
|
|
* A disabled machine cannot be reservable
|
|
|
|
*/
|
|
|
|
const onDisabledToggled = (disabled: boolean) => {
|
|
|
|
if (disabled) {
|
|
|
|
setValue('reservable', false);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2022-12-16 18:43:38 +01:00
|
|
|
/**
|
|
|
|
* Convert all machine categories to the select format
|
|
|
|
*/
|
|
|
|
const buildOptions = (): Array<SelectOption<number>> => {
|
|
|
|
return machineCategories.map(t => {
|
|
|
|
return { value: t.id, label: t.name };
|
|
|
|
});
|
|
|
|
};
|
|
|
|
|
2022-10-28 17:13:41 +02:00
|
|
|
return (
|
2023-01-16 12:28:53 +01:00
|
|
|
<div className="machine-form">
|
|
|
|
<header>
|
|
|
|
<h2>{t('app.admin.machine_form.ACTION_title', { ACTION: action })}</h2>
|
|
|
|
<FabButton onClick={handleSubmit(onSubmit)} className="fab-button save-btn is-main">
|
|
|
|
{t('app.admin.machine_form.save')}
|
|
|
|
</FabButton>
|
|
|
|
</header>
|
|
|
|
<form className="machine-form-content" onSubmit={handleSubmit(onSubmit)}>
|
|
|
|
{action === 'create' &&
|
|
|
|
<FabAlert level='warning'>
|
|
|
|
{t('app.admin.machine_form.watch_out_when_creating_a_new_machine_its_prices_are_initialized_at_0_for_all_subscriptions')} {t('app.admin.machine_form.consider_changing_them_before_creating_any_reservation_slot')}
|
|
|
|
</FabAlert>
|
|
|
|
}
|
|
|
|
<section>
|
|
|
|
<header>
|
|
|
|
<p className="title">{t('app.admin.machine_form.description')}</p>
|
|
|
|
</header>
|
|
|
|
<div className="content">
|
|
|
|
<FormInput register={register} id="name"
|
2022-10-28 17:13:41 +02:00
|
|
|
formState={formState}
|
|
|
|
rules={{ required: true }}
|
2023-01-16 12:28:53 +01:00
|
|
|
label={t('app.admin.machine_form.name')} />
|
|
|
|
<FormImageUpload setValue={setValue}
|
|
|
|
register={register}
|
|
|
|
control={control}
|
|
|
|
formState={formState}
|
|
|
|
rules={{ required: true }}
|
|
|
|
id="machine_image_attributes"
|
|
|
|
accept="image/*"
|
|
|
|
defaultImage={output.machine_image_attributes}
|
|
|
|
label={t('app.admin.machine_form.illustration')} />
|
|
|
|
<FormRichText control={control}
|
|
|
|
id="description"
|
|
|
|
rules={{ required: true }}
|
2023-01-25 11:05:16 +01:00
|
|
|
formState={formState}
|
2023-01-16 12:28:53 +01:00
|
|
|
label={t('app.admin.machine_form.description')}
|
|
|
|
limit={null}
|
|
|
|
heading bulletList blockquote link image video />
|
|
|
|
<FormRichText control={control}
|
|
|
|
id="spec"
|
|
|
|
rules={{ required: true }}
|
2023-01-25 11:05:16 +01:00
|
|
|
formState={formState}
|
2023-01-16 12:28:53 +01:00
|
|
|
label={t('app.admin.machine_form.technical_specifications')}
|
|
|
|
limit={null}
|
|
|
|
heading bulletList link />
|
|
|
|
<FormSelect options={buildOptions()}
|
|
|
|
control={control}
|
|
|
|
id="machine_category_id"
|
|
|
|
formState={formState}
|
|
|
|
label={t('app.admin.machine_form.category')} />
|
|
|
|
</div>
|
|
|
|
</section>
|
2022-11-03 11:46:30 +01:00
|
|
|
|
2023-01-16 12:28:53 +01:00
|
|
|
<section>
|
|
|
|
<header>
|
|
|
|
<p className="title">{t('app.admin.machine_form.attachments')}</p>
|
|
|
|
</header>
|
|
|
|
<div className="content">
|
|
|
|
<div className='form-item-header machine-files-header'>
|
|
|
|
<p>{t('app.admin.machine_form.attached_files_pdf')}</p>
|
|
|
|
</div>
|
|
|
|
<FormMultiFileUpload setValue={setValue}
|
|
|
|
addButtonLabel={t('app.admin.machine_form.add_an_attachment')}
|
|
|
|
control={control}
|
|
|
|
accept="application/pdf"
|
|
|
|
register={register}
|
|
|
|
id="machine_files_attributes"
|
|
|
|
className="machine-files" />
|
|
|
|
</div>
|
|
|
|
</section>
|
|
|
|
|
|
|
|
<section>
|
|
|
|
<header>
|
|
|
|
<p className="title">{t('app.admin.machine_form.settings')}</p>
|
|
|
|
</header>
|
|
|
|
<div className="content">
|
|
|
|
<FormSwitch control={control}
|
|
|
|
id="reservable"
|
|
|
|
label={t('app.admin.machine_form.reservable')}
|
2023-01-23 12:05:02 +01:00
|
|
|
onChange={onReservableToggled}
|
2023-01-16 12:28:53 +01:00
|
|
|
tooltip={t('app.admin.machine_form.reservable_help')}
|
|
|
|
defaultValue={true} />
|
|
|
|
<FormSwitch control={control}
|
|
|
|
id="disabled"
|
2023-01-23 12:05:02 +01:00
|
|
|
onChange={onDisabledToggled}
|
2023-01-16 12:28:53 +01:00
|
|
|
label={t('app.admin.machine_form.disable_machine')}
|
|
|
|
tooltip={t('app.admin.machine_form.disabled_help')} />
|
|
|
|
</div>
|
|
|
|
</section>
|
|
|
|
|
|
|
|
{isActiveAccounting &&
|
|
|
|
<section>
|
|
|
|
<AdvancedAccountingForm register={register} onError={onError} />
|
|
|
|
</section>
|
|
|
|
}
|
|
|
|
</form>
|
|
|
|
</div>
|
2022-10-28 17:13:41 +02:00
|
|
|
);
|
|
|
|
};
|
|
|
|
|
|
|
|
const MachineFormWrapper: React.FC<MachineFormProps> = (props) => {
|
|
|
|
return (
|
|
|
|
<Loader>
|
|
|
|
<ErrorBoundary>
|
|
|
|
<MachineForm {...props} />
|
|
|
|
</ErrorBoundary>
|
|
|
|
</Loader>
|
|
|
|
);
|
|
|
|
};
|
|
|
|
|
|
|
|
Application.Components.component('machineForm', react2angular(MachineFormWrapper, ['action', 'machine', 'onError', 'onSuccess']));
|