From d856dc5c627ca4ba16a059bfff52996a42b47b63 Mon Sep 17 00:00:00 2001 From: daniele-mng Date: Mon, 24 Jun 2024 11:34:58 +0200 Subject: [PATCH] Add: opensight date picker --- src/gmp/commands/wizard.js | 2 +- src/gmp/models/event.js | 6 +- .../form/{datepicker.jsx => DatePicker.jsx} | 87 +--- .../performance/startendtimeselection.jsx | 193 +++------ src/web/pages/schedules/dialog.jsx | 118 ++---- src/web/wizard/advancedtaskwizard.jsx | 393 +++++++++--------- src/web/wizard/modifytaskwizard.jsx | 55 ++- 7 files changed, 336 insertions(+), 518 deletions(-) rename src/web/components/form/{datepicker.jsx => DatePicker.jsx} (50%) diff --git a/src/gmp/commands/wizard.js b/src/gmp/commands/wizard.js index 8935cf6e08..ab1f887fda 100644 --- a/src/gmp/commands/wizard.js +++ b/src/gmp/commands/wizard.js @@ -190,7 +190,7 @@ class WizardCommand extends HttpCommand { event_data_quick_task_fields, ); - event_data['event_data:start_day'] = start_date.day(); + event_data['event_data:start_day'] = start_date.date(); event_data['event_data:start_month'] = start_date.month() + 1; event_data['event_data:start_year'] = start_date.year(); diff --git a/src/gmp/models/event.js b/src/gmp/models/event.js index c5cf54048b..592d85f64a 100644 --- a/src/gmp/models/event.js +++ b/src/gmp/models/event.js @@ -254,13 +254,14 @@ class Event { startDate, summary, weekdays, + isUseUTC = true, }, timezone, ) { const event = new ical.Event(); event.uid = uuid(); - event.startDate = ical.Time.fromJSDate(startDate.toDate(), true); + event.startDate = ical.Time.fromJSDate(startDate.toDate(), isUseUTC); if (isDefined(duration)) { const eventDuration = new ical.Duration(); @@ -317,7 +318,8 @@ class Event { } get duration() { - return createDuration({...this.event.duration}); + const {weeks, ...durationWithoutWeeks} = this.event.duration; + return createDuration(durationWithoutWeeks); } get durationInSeconds() { diff --git a/src/web/components/form/datepicker.jsx b/src/web/components/form/DatePicker.jsx similarity index 50% rename from src/web/components/form/datepicker.jsx rename to src/web/components/form/DatePicker.jsx index 4820690a81..c30c892ccf 100644 --- a/src/web/components/form/datepicker.jsx +++ b/src/web/components/form/DatePicker.jsx @@ -17,93 +17,48 @@ */ import React, {useCallback} from 'react'; -import styled from 'styled-components'; - -import DatePicker from 'react-datepicker'; - -import _ from 'gmp/locale'; - -import {getLocale} from 'gmp/locale/lang'; +import {DateTimePicker} from '@greenbone/opensight-ui-components'; import {isDefined} from 'gmp/utils/identity'; import date from 'gmp/models/date'; -import PropTypes from 'web/utils/proptypes'; - -import Theme from 'web/utils/theme'; - -import CalendarIcon from 'web/components/icon/calendaricon'; - -import 'react-datepicker/dist/react-datepicker.css'; - -const StyledCalendarIcon = styled(CalendarIcon)` - margin-left: 5px; - :hover { - cursor: ${props => (props.disabled ? 'not-allowed ' : 'pointer')}; - } -`; - -const StyledDiv = styled.div` - display: flex; - margin-right: 5px; - width: ${props => props.width}; - color: ${props => (props.disabled ? Theme.lightGray : undefined)}; -`; - -// InputField must be a Class to work correctly with Datepicker :-/ -// eslint-disable-next-line react/prefer-stateless-function -class InputField extends React.Component { - render() { - const {disabled, onClick, value, width = 'auto', ...props} = this.props; - - return ( - - {value} - - - ); - } -} +import {getLocale} from 'gmp/locale/lang'; -InputField.propTypes = { - disabled: PropTypes.bool, - value: PropTypes.string, - width: PropTypes.string, - onClick: PropTypes.func, -}; +import PropTypes from 'web/utils/proptypes'; const DatePickerComponent = ({ disabled, - timezone, - minDate = date().tz(timezone), + minDate = date(), name, - width, - value = date().tz(timezone), + width = '100%', + value = date(), onChange, - ...restProps + label = '', }) => { const handleChange = useCallback( newValue => { if (isDefined(onChange)) { - onChange(date(newValue).tz(timezone), name); + const valueToPass = date(newValue); + onChange(valueToPass, name); } }, - [name, onChange, timezone], + [name, onChange], ); + return ( - } + locale={getLocale()} + value={value.toDate()} + onChange={handleChange} minDate={ minDate === false || !isDefined(minDate) ? undefined : minDate.toDate() } maxDate={date().add(3, 'years').toDate()} - selected={value.toDate()} - todayButton={_('Today')} - locale={getLocale()} - onChange={handleChange} + style={{width}} + withSeconds={false} + label={label} /> ); }; @@ -111,13 +66,11 @@ const DatePickerComponent = ({ DatePickerComponent.propTypes = { disabled: PropTypes.bool, minDate: PropTypes.oneOfType([PropTypes.date, PropTypes.oneOf([false])]), - name: PropTypes.string, - timezone: PropTypes.string.isRequired, + name: PropTypes.arrayOf(PropTypes.string), value: PropTypes.date.isRequired, width: PropTypes.string, onChange: PropTypes.func, + label: PropTypes.string, }; export default DatePickerComponent; - -// vim: set ts=2 sw=2 tw=80: diff --git a/src/web/pages/performance/startendtimeselection.jsx b/src/web/pages/performance/startendtimeselection.jsx index 62619abd6c..1ed8fa4aa6 100644 --- a/src/web/pages/performance/startendtimeselection.jsx +++ b/src/web/pages/performance/startendtimeselection.jsx @@ -15,151 +15,82 @@ * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see . */ -import React from 'react'; +import {useState, useEffect} from 'react'; import _ from 'gmp/locale'; -import {isDefined} from 'gmp/utils/identity'; - import PropTypes from 'web/utils/proptypes'; import Button from 'web/components/form/button'; -import Datepicker from 'web/components/form/datepicker'; +import DatePicker from 'web/components/form/DatePicker'; import FormGroup from 'web/components/form/formgroup'; -import Spinner from 'web/components/form/spinner'; import Column from 'web/components/layout/column'; import Row from 'web/components/layout/row'; -class StartTimeSelection extends React.Component { - constructor(...args) { - super(...args); - - const {startDate, endDate} = this.props; - - this.state = { - startDate, - startHour: startDate.hour(), - startMinute: startDate.minute(), - endDate, - endHour: endDate.hour(), - endMinute: endDate.minute(), - }; - - this.handleValueChange = this.handleValueChange.bind(this); - this.handleUpdate = this.handleUpdate.bind(this); - } - - static getDerivedStateFromProps(props, state) { - const {startDate, endDate} = props; - - if ( - (isDefined(startDate) && startDate !== state.prevStartDate) || - (isDefined(endDate) && props.endDate !== state.prevEndDate) - ) { - return { - startDate, - endDate, - endHour: endDate.hour(), - endMinute: endDate.minute(), - prevStartDate: startDate, - prevEndDate: endDate, - startHour: startDate.hour(), - startMinute: startDate.minute(), - }; +const StartTimeSelection = props => { + const { + startDate: initialStartDate, + endDate: initialEndDate, + timezone, + onChanged, + } = props; + const [startDate, setStartDate] = useState(initialStartDate); + const [endDate, setEndDate] = useState(initialEndDate); + + useEffect(() => { + setStartDate(initialStartDate); + setEndDate(initialEndDate); + }, [initialStartDate, initialEndDate]); + + const handleValueChange = (value, name) => { + if (name === 'startDate') { + setStartDate(value); + } else if (name === 'endDate') { + setEndDate(value); } - return null; - } - - handleValueChange(value, name) { - this.setState({[name]: value}); - } - - handleUpdate() { - const {onChanged} = this.props; - const {startDate, endDate, startHour, startMinute, endHour, endMinute} = - this.state; + }; + const handleUpdate = () => { onChanged({ - startDate: startDate.clone().hour(startHour).minute(startMinute), - endDate: endDate.clone().hour(endHour).minute(endMinute), + startDate: startDate.clone(), + endDate: endDate.clone(), }); - } - - render() { - const {timezone} = this.props; - const {endDate, startDate, startHour, startMinute, endHour, endMinute} = - this.state; - return ( - - - {timezone} - - - - {' '} - h - {' '} - m - - - - - {' '} - h - {' '} - m - - - - - - - ); - } -} + }; + + return ( + + + {timezone} + + + + + + + + + + + + + + ); +}; StartTimeSelection.propTypes = { endDate: PropTypes.date.isRequired, @@ -169,5 +100,3 @@ StartTimeSelection.propTypes = { }; export default StartTimeSelection; - -// vim: set ts=2 sw=2 tw=80: diff --git a/src/web/pages/schedules/dialog.jsx b/src/web/pages/schedules/dialog.jsx index 2548ad100c..d1430f9174 100644 --- a/src/web/pages/schedules/dialog.jsx +++ b/src/web/pages/schedules/dialog.jsx @@ -31,7 +31,8 @@ import Select from 'web/components/form/select'; import Spinner from 'web/components/form/spinner'; import FormGroup from 'web/components/form/formgroup'; import TextField from 'web/components/form/textfield'; -import DatePicker from 'web/components/form/datepicker'; +import DatePicker from 'web/components/form/DatePicker'; + import TimeZoneSelect from 'web/components/form/timezoneselect'; import CheckBox from 'web/components/form/checkbox'; import Radio from 'web/components/form/radio'; @@ -203,48 +204,32 @@ const ScheduleDialog = ({ ? undefined : isDefined(endDate) && createDuration(endDate.diff(startDate)); - const handleStartHoursChange = value => { - setStartDate(startDate => startDate.hours(value)); // eslint-disable-line no-shadow - }; - - const handleStartMinutesChange = value => { - setStartDate(startDate => startDate.minutes(value)); // eslint-disable-line no-shadow - }; - const handleNowButtonClick = () => { setStartDate(date().tz(timezone)); }; - const handleEndHoursChange = value => { - setEndDate(endDate => endDate.hours(value)); // eslint-disable-line no-shadow - }; - - const handleEndMinutesChange = value => { - setEndDate(endDate => endDate.minutes(value)); // eslint-disable-line no-shadow - }; - const handleTimezoneChange = value => { - setEndDate(endDate => endDate.tz(value)); // eslint-disable-line no-shadow - setStartDate(startDate => startDate.tz(value)); // eslint-disable-line no-shadow + setEndDate(endDate => endDate.tz(value)); + setStartDate(startDate => startDate.tz(value)); setTimezone(value); }; const handleSave = ({ - comment, // eslint-disable-line no-shadow - endDate, // eslint-disable-line no-shadow - endOpen = false, // eslint-disable-line no-shadow - freq, // eslint-disable-line no-shadow - id, // eslint-disable-line no-shadow - interval, // eslint-disable-line no-shadow - monthdays, // eslint-disable-line no-shadow - monthly, // eslint-disable-line no-shadow - monthlyDay, // eslint-disable-line no-shadow - monthlyNth, // eslint-disable-line no-shadow - name, // eslint-disable-line no-shadow - recurrenceType, // eslint-disable-line no-shadow - startDate, // eslint-disable-line no-shadow - timezone, // eslint-disable-line no-shadow - weekdays, // eslint-disable-line no-shadow + comment, + endDate, + endOpen = false, + freq, + id, + interval, + monthdays, + monthly, + monthlyDay, + monthlyNth, + name, + recurrenceType, + startDate, + timezone, + weekdays, }) => { if (!isDefined(onSave)) { return Promise.resolve(); @@ -322,6 +307,7 @@ const ScheduleDialog = ({ // when name is just numbers. summary: `${name}`, startDate, + isUseUTC: false, }, timezone, ); @@ -390,36 +376,16 @@ const ScheduleDialog = ({ /> - - - - - h - - m - -