]> git.localhorst.tv Git - alttp.git/blob - resources/js/components/episodes/ApplyForm.js
events overview
[alttp.git] / resources / js / components / episodes / ApplyForm.js
1 import { withFormik } from 'formik';
2 import PropTypes from 'prop-types';
3 import React from 'react';
4 import { Button, Col, Form, Modal, Row } from 'react-bootstrap';
5 import { useTranslation } from 'react-i18next';
6
7 import DialogEpisode from './DialogEpisode';
8 import laravelErrorsToFormik from '../../helpers/laravelErrorsToFormik';
9 import { applicableChannels } from '../../helpers/permissions';
10 import { withUser } from '../../helpers/UserContext';
11
12 const ApplyForm = ({
13         as,
14         episode,
15         errors,
16         handleBlur,
17         handleChange,
18         handleSubmit,
19         onCancel,
20         touched,
21         user,
22         values,
23 }) => {
24         const { t } = useTranslation();
25
26         const available_channels = React.useMemo(() => {
27                 return applicableChannels(user, episode, as);
28         }, [as, episode, user]);
29
30         return <Form noValidate onSubmit={handleSubmit}>
31                 <Modal.Body>
32                         <DialogEpisode episode={episode} />
33                         <Form.Group controlId="apply.role">
34                                 <Form.Label>{t('episodes.applyDialog.signUpAs')}</Form.Label>
35                                 <Form.Control
36                                         plaintext
37                                         readOnly
38                                         value={t(`crew.roles.${as}`)}
39                                 />
40                         </Form.Group>
41                         <Form.Group controlId="apply.channel_id">
42                                 <Form.Label>{t('episodes.channel')}</Form.Label>
43                                 <Form.Select
44                                         isInvalid={!!(touched.channel_id && errors.channel_id)}
45                                         name="channel_id"
46                                         onBlur={handleBlur}
47                                         onChange={handleChange}
48                                         value={values.channel_id || 0}
49                                 >
50                                         <option disabled value={0}>{t('general.pleaseSelect')}</option>
51                                         {available_channels.map(c =>
52                                                 <option key={c.id} value={c.id}>
53                                                         {c.title}
54                                                 </option>
55                                         )}
56                                 </Form.Select>
57                                 {touched.channel_id && errors.channel_id ?
58                                         <Form.Control.Feedback type="invalid">
59                                                 {t(errors.channel_id)}
60                                         </Form.Control.Feedback>
61                                 : null}
62                         </Form.Group>
63                 </Modal.Body>
64                 <Modal.Footer>
65                         {onCancel ?
66                                 <Button onClick={onCancel} variant="secondary">
67                                         {t('button.cancel')}
68                                 </Button>
69                         : null}
70                         <Button type="submit" variant="primary">
71                                 {t('button.submit')}
72                         </Button>
73                 </Modal.Footer>
74         </Form>;
75 };
76
77 ApplyForm.propTypes = {
78         episode: PropTypes.shape({
79         }),
80         errors: PropTypes.shape({
81                 channel_id: PropTypes.string,
82         }),
83         handleBlur: PropTypes.func,
84         handleChange: PropTypes.func,
85         handleSubmit: PropTypes.func,
86         onCancel: PropTypes.func,
87         touched: PropTypes.shape({
88                 channel_id: PropTypes.bool,
89         }),
90         user: PropTypes.shape({
91         }),
92         values: PropTypes.shape({
93                 channel_id: PropTypes.number,
94         }),
95 };
96
97 export default withUser(withFormik({
98         displayName: 'ApplyForm',
99         enableReinitialize: true,
100         handleSubmit: async (values, actions) => {
101                 const { setErrors } = actions;
102                 const { onSubmit } = actions.props;
103                 try {
104                         await onSubmit(values);
105                 } catch (e) {
106                         if (e.response && e.response.data && e.response.data.errors) {
107                                 setErrors(laravelErrorsToFormik(e.response.data.errors));
108                         }
109                 }
110         },
111         mapPropsToValues: ({ as, episode, user }) => {
112                 const channels = applicableChannels(user, episode, as);
113                 return {
114                         as,
115                         channel_id: channels.length ? channels[0].id : 0,
116                         episode_id: episode ? episode.id : 0,
117                 };
118         },
119 })(ApplyForm));