mirror of
https://github.com/cpvalente/ontime.git
synced 2026-08-19 14:14:17 +00:00
Feat/delays (#96)
* feat/delays allow negative delays * feat/delays recover expand all * feat/delays refact: icons import * feat/delays refact: upgrade chakra * feat/delays version bump
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
import { Draggable } from 'react-beautiful-dnd';
|
||||
import { FiMoreVertical } from 'react-icons/fi';
|
||||
import { FiMoreVertical } from '@react-icons/all-files/fi/FiMoreVertical';
|
||||
import DeleteIconBtn from 'common/components/buttons/DeleteIconBtn';
|
||||
import ActionButtons from '../list/ActionButtons';
|
||||
import style from './BlockBlock.module.scss';
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { Draggable } from 'react-beautiful-dnd';
|
||||
import { FiMoreVertical } from 'react-icons/fi';
|
||||
import { FiMoreVertical } from '@react-icons/all-files/fi/FiMoreVertical';
|
||||
import { millisToMinutes } from 'common/utils/dateConfig';
|
||||
import ActionButtons from '../list/ActionButtons';
|
||||
import DeleteIconBtn from 'common/components/buttons/DeleteIconBtn';
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import Icon from '@chakra-ui/icon';
|
||||
import { FiChevronUp, FiMoreVertical } from 'react-icons/fi';
|
||||
import { FiChevronUp } from '@react-icons/all-files/fi/FiChevronUp';
|
||||
import { FiMoreVertical } from '@react-icons/all-files/fi/FiMoreVertical';
|
||||
import { useMemo } from 'react';
|
||||
import { Draggable } from 'react-beautiful-dnd';
|
||||
import EventTimes from 'common/components/eventTimes/EventTimes';
|
||||
@@ -28,12 +29,12 @@ const ExpandedBlock = (props) => {
|
||||
return (
|
||||
<>
|
||||
<span className={style.drag} {...provided.dragHandleProps}>
|
||||
<FiMoreVertical />
|
||||
<FiMoreVertical />
|
||||
</span>
|
||||
|
||||
<div className={style.indicators}>
|
||||
<span className={next ? style.next : style.nextDisabled}>Next</span>
|
||||
{delayValue != null && <span className={style.delayValue}>+ {delayValue}</span>}
|
||||
{delayValue != null && <span className={style.delayValue}>{delayValue}</span>}
|
||||
</div>
|
||||
<div className={style.timeExpanded}>
|
||||
<EventTimesVertical
|
||||
@@ -93,7 +94,7 @@ ExpandedBlock.propTypes = {
|
||||
eventIndex: PropTypes.number.isRequired,
|
||||
next: PropTypes.bool.isRequired,
|
||||
delay: PropTypes.number,
|
||||
delayValue: PropTypes.number,
|
||||
delayValue: PropTypes.string,
|
||||
previousEnd: PropTypes.number.isRequired,
|
||||
actionHandler: PropTypes.func.isRequired,
|
||||
};
|
||||
@@ -104,12 +105,12 @@ const CollapsedBlock = (props) => {
|
||||
return (
|
||||
<>
|
||||
<span className={style.drag} {...provided.dragHandleProps}>
|
||||
<FiMoreVertical />
|
||||
<FiMoreVertical />
|
||||
</span>
|
||||
|
||||
<div className={style.indicators}>
|
||||
<span className={next ? style.next : style.nextDisabled}>Next</span>
|
||||
{delayValue != null && <span className={style.delayValue}>+ {delayValue}</span>}
|
||||
{delayValue != null && <span className={style.delayValue}>{delayValue}</span>}
|
||||
</div>
|
||||
<EventTimes
|
||||
actionHandler={actionHandler}
|
||||
@@ -140,7 +141,7 @@ CollapsedBlock.propTypes = {
|
||||
data: PropTypes.object.isRequired,
|
||||
next: PropTypes.bool.isRequired,
|
||||
delay: PropTypes.any,
|
||||
delayValue: PropTypes.any,
|
||||
delayValue: PropTypes.string,
|
||||
previousEnd: PropTypes.number.isRequired,
|
||||
actionHandler: PropTypes.func.isRequired,
|
||||
};
|
||||
@@ -155,8 +156,10 @@ export default function EventBlock(props) {
|
||||
const classSelect = `${style.event} ${isCollapsed} ${isSelected}`;
|
||||
|
||||
// Calculate delay in min
|
||||
const delayValue = delay > 0 ? millisToMinutes(delay) : null;
|
||||
|
||||
let delayValue = null;
|
||||
if (delay != null && delay !== 0) {
|
||||
delayValue = `${delay >= 0 ? '+' : '-'} ${millisToMinutes(Math.abs(delay))}`;
|
||||
}
|
||||
const handleCollapse = (isCollapsed) => {
|
||||
setCollapsed({ [data.id]: isCollapsed });
|
||||
};
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
import { Menu, MenuButton, MenuItem, MenuList } from '@chakra-ui/menu';
|
||||
import { IconButton } from '@chakra-ui/button';
|
||||
import { FiClock, FiMinusCircle, FiPlus } from 'react-icons/fi';
|
||||
import { FiClock } from '@react-icons/all-files/fi/FiClock';
|
||||
import { FiMinusCircle } from '@react-icons/all-files/fi/FiMinusCircle';
|
||||
import { FiPlus } from '@react-icons/all-files/fi/FiPlus';
|
||||
import { Tooltip } from '@chakra-ui/tooltip';
|
||||
|
||||
export default function ActionButtons(props) {
|
||||
@@ -26,19 +28,11 @@ export default function ActionButtons(props) {
|
||||
/>
|
||||
</Tooltip>
|
||||
<MenuList style={menuStyle}>
|
||||
<MenuItem
|
||||
icon={<FiPlus />}
|
||||
onClick={() => actionHandler('event')}
|
||||
isDisabled={!showAdd}
|
||||
>
|
||||
<MenuItem icon={<FiPlus />} onClick={() => actionHandler('event')} isDisabled={!showAdd}>
|
||||
Add Event after
|
||||
</MenuItem>
|
||||
|
||||
<MenuItem
|
||||
icon={<FiClock />}
|
||||
onClick={() => actionHandler('delay')}
|
||||
isDisabled={!showDelay}
|
||||
>
|
||||
<MenuItem icon={<FiClock />} onClick={() => actionHandler('delay')} isDisabled={!showDelay}>
|
||||
Add Delay after
|
||||
</MenuItem>
|
||||
<MenuItem
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import DelayBlock from '../DelayBlock/DelayBlock';
|
||||
import BlockBlock from '../BlockBlock/BlockBlock';
|
||||
import EventBlock from '../EventBlock/EventBlock';
|
||||
import { memo, useContext } from 'react';
|
||||
import { memo, useCallback, useContext } from 'react';
|
||||
import { LoggingContext } from '../../../app/context/LoggingContext';
|
||||
import { LocalEventSettingsContext } from '../../../app/context/LocalEventSettingsContext';
|
||||
|
||||
@@ -33,52 +33,55 @@ const EventListItem = (props) => {
|
||||
const { starTimeIsLastEnd, defaultPublic } = useContext(LocalEventSettingsContext);
|
||||
|
||||
// Create / delete new events
|
||||
const actionHandler = (action, payload) => {
|
||||
switch (action) {
|
||||
case 'event':
|
||||
eventsHandler(
|
||||
'add',
|
||||
{
|
||||
type: 'event',
|
||||
order: index + 1,
|
||||
isPublic: defaultPublic,
|
||||
},
|
||||
{ startIsLastEnd: starTimeIsLastEnd ? index : undefined }
|
||||
);
|
||||
break;
|
||||
case 'delay':
|
||||
eventsHandler('add', { type: 'delay', order: index + 1 });
|
||||
break;
|
||||
case 'block':
|
||||
eventsHandler('add', { type: 'block', order: index + 1 });
|
||||
break;
|
||||
case 'delete':
|
||||
eventsHandler('delete', data.id);
|
||||
break;
|
||||
case 'update':
|
||||
// Handles and filters update requests
|
||||
const { field, value } = payload;
|
||||
if (field === 'durationOverride') {
|
||||
// duration defines timeEnd
|
||||
let end = (data.timeStart += value);
|
||||
const newData = { id: data.id, timeEnd: end };
|
||||
const actionHandler = useCallback(
|
||||
(action, payload) => {
|
||||
switch (action) {
|
||||
case 'event':
|
||||
eventsHandler(
|
||||
'add',
|
||||
{
|
||||
type: 'event',
|
||||
order: index + 1,
|
||||
isPublic: defaultPublic,
|
||||
},
|
||||
{ startIsLastEnd: starTimeIsLastEnd ? index : undefined }
|
||||
);
|
||||
break;
|
||||
case 'delay':
|
||||
eventsHandler('add', { type: 'delay', order: index + 1 });
|
||||
break;
|
||||
case 'block':
|
||||
eventsHandler('add', { type: 'block', order: index + 1 });
|
||||
break;
|
||||
case 'delete':
|
||||
eventsHandler('delete', data.id);
|
||||
break;
|
||||
case 'update':
|
||||
// Handles and filters update requests
|
||||
const { field, value } = payload;
|
||||
if (field === 'durationOverride') {
|
||||
// duration defines timeEnd
|
||||
let end = (data.timeStart += value);
|
||||
const newData = { id: data.id, timeEnd: end };
|
||||
|
||||
// request update in parent
|
||||
eventsHandler('patch', newData);
|
||||
} else if (field in data) {
|
||||
// create object with new field
|
||||
const newData = { id: data.id, [field]: value };
|
||||
// request update in parent
|
||||
eventsHandler('patch', newData);
|
||||
} else if (field in data) {
|
||||
// create object with new field
|
||||
const newData = { id: data.id, [field]: value };
|
||||
|
||||
// request update in parent
|
||||
eventsHandler('patch', newData);
|
||||
} else {
|
||||
emitError(`Unknown field: ${field}`);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
};
|
||||
// request update in parent
|
||||
eventsHandler('patch', newData);
|
||||
} else {
|
||||
emitError(`Unknown field: ${field}`);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
},
|
||||
[data, defaultPublic, emitError, eventsHandler, index, starTimeIsLastEnd]
|
||||
);
|
||||
|
||||
switch (type) {
|
||||
case 'event':
|
||||
|
||||
Reference in New Issue
Block a user