import { Modal, ModalCustom, Tabs, Tab, Badge, useToast, Checkbox } from '@ocv-web/ui' import { categoryMap, certaintyMap, weaCertaintyMap, eventCodes, eventResponseMap, severityMap, weaSeverityMap, urgencyMap, weaUrgencyMap, weaHandlingMap, NotificationFormData, } from '../../config' import React from 'react' import { DetailMap } from '../DetailTabs/DetailMap' import { useNotificationMutation, useNotificationsMutation, } from '../../api/notifications' import { useTemplateMutation, useTemplatesMutation } from '../../api/templates' import { useParams } from 'react-router-dom' import { OCVRouteParams } from '../../../core/types' import { useUserSelection } from '../../../core/context/UserSelectionContext' import { useUser } from '../../../administration/api/users' export interface SubmissionModalProps { show: boolean showAction: () => void formData: NotificationFormData templateEdit: boolean template: boolean newNotification: boolean setSubmitStatus?: React.Dispatch<React.SetStateAction<string>> } const alertMapping = { GeoPhysical: 'Geo', Meteorological: 'Met', Safety: 'Safety', Security: 'Security', Rescue: 'Rescue', Fire: 'Fire', Health: 'Health', 'Environmental (Env)': 'Env', Transport: 'Transport', 'Infrastructure (Infra)': 'Infra', CBRNE: 'CBRNE', Other: 'Other', } export const SubmissionModal: React.FC<SubmissionModalProps> = ({ show, showAction, formData, templateEdit, template, setSubmitStatus, newNotification, }) => { const { id } = useParams<OCVRouteParams>() const [disabled, toggleDisabled] = React.useState(true) const { userEmail } = useUserSelection() const { data } = useUser(userEmail) const userName = data?.Results[0]?.Name const [selectedTab, setTabSelected] = React.useState(0) const [mutate] = useNotificationsMutation() const [mutatePatch] = useNotificationMutation(id) const [templateMutate] = useTemplatesMutation() const [mutateTemplatePatch] = useTemplateMutation(id) const { dispatch } = useToast() const handleTabChange = React.useCallback( newSelectedTab => setTabSelected(newSelectedTab), [] ) const localStorageData = JSON.parse(localStorage.getItem('formObject')) React.useEffect(() => { console.log(template) }, [template]) const handleSend = () => { if (localStorageData && Object.keys(localStorageData).length > 0) { localStorage.setItem('formObject', JSON.stringify({})) window.location.reload() } if (template === true) { try { templateMutate({ Name: formData.Title, Type: formData.Type, <<<<<<< HEAD CreatedBy: { Name: userName, Email: userEmail }, ======= CreatedBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Template: { Title: formData.Title, Description: formData.Description, Type: formData.Type, Locations: JSON.parse(formData.Locations), <<<<<<< HEAD SentBy: { Name: userName, Email: userEmail }, ======= SentBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Groups: [formData.Groups], IPAWSInfo: { DisseminationChannels: { EAS: formData.EAS, WEA: formData.WEA, NWEM: formData.NWEM, }, Instructions: formData.Instructions, Severity: formData.Severity, Urgency: formData.Urgency, Certainty: formData.Certainty, AlertCategory: formData.AlertCategory, EventCode: formData.EventCode, EventResponse: formData.EventResponse, CountyFIPS: parseInt(formData.CountyFIPS), WEAShortText: formData.WEAShortText, WEALongText: formData.WEALongText, WEAHandling: formData.WEAHandling, WEASpanish: formData.WEASpanish, WEAShortTextSpanish: formData.WEAShortTextSpanish, WEALongTextSpanish: formData.WEALongTextSpanish, IPAWSKey: formData.IPAWSKey, }, Expires: { Hours: formData.ExpiresInHours, Minutes: formData.ExpiresInMinutes, }, SchedulingInfo: { Schedule: formData.ScheduleNotification, Hide: formData.ScheduleHide, SendDate: formData.ScheduleDate, HideDate: formData.ScheduleHideDate, Recurring: formData.ScheduleRecurring, Frequency: formData.Frequency, }, SocialMedia: { Instagram: formData.Instagram, Facebook: formData.Facebook, Twitter: formData.Twitter, }, FeatureToOpen: formData.FeatureToOpen, <<<<<<< HEAD LastUpdated: new Date().toLocaleString(), ======= Response: { body: { alertId: '', sender: '', sentOn: '', }, }, >>>>>>> master }, }) dispatch({ type: 'add', payload: { title: 'Template Added Successfully.', status: 'success', message: 'You successfully added this Template.', }, }) setSubmitStatus && setSubmitStatus('success') showAction() } catch { dispatch({ type: 'add', payload: { title: 'Adding Template Failed.', status: 'error', message: 'You failed to add this Template.', }, }) setSubmitStatus && setSubmitStatus('failed') showAction() } } else if (formData.IPAWSTemplate === true) { try { mutate({ Title: formData.Title, Description: formData.Description, Type: formData.Type, Locations: JSON.parse(formData.Locations), <<<<<<< HEAD SentBy: { Name: userName, Email: userEmail }, ======= SentBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Groups: [formData.Groups], IPAWSInfo: { DisseminationChannels: { EAS: formData.EAS, WEA: formData.WEA, NWEM: formData.NWEM, }, Instructions: formData.Instructions, Severity: formData.Severity, Urgency: formData.Urgency, Certainty: formData.Certainty, AlertCategory: formData.AlertCategory, EventCode: formData.EventCode, EventResponse: formData.EventResponse, CountyFIPS: parseInt(formData.CountyFIPS), WEAShortText: formData.WEAShortText, WEALongText: formData.WEALongText, WEAHandling: formData.WEAHandling, WEASpanish: formData.WEASpanish, WEAShortTextSpanish: formData.WEAShortTextSpanish, WEALongTextSpanish: formData.WEALongTextSpanish, IPAWSKey: formData.IPAWSKey, }, Expires: { Hours: formData.ExpiresInHours, Minutes: formData.ExpiresInMinutes }, SchedulingInfo: { Schedule: formData.ScheduleNotification, Hide: formData.ScheduleHide, SendDate: formData.ScheduleDate, HideDate: formData.ScheduleHideDate, Recurring: formData.ScheduleRecurring, Frequency: formData.Frequency, }, SocialMedia: { Instagram: formData.Instagram, Facebook: formData.Facebook, Twitter: formData.Twitter, }, FeatureToOpen: formData.FeatureToOpen, <<<<<<< HEAD LastUpdated: new Date().toLocaleString(), ======= Response: { body: { alertId: '', sender: '', sentOn: '', }, }, >>>>>>> master }).then(() => { templateMutate({ Name: formData.Title, Type: formData.Type, <<<<<<< HEAD CreatedBy: { Name: userName, Email: userEmail }, ======= CreatedBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Template: { Title: formData.Title, Description: formData.Description, Type: formData.Type, Locations: JSON.parse(formData.Locations), <<<<<<< HEAD SentBy: { Name: userName, Email: userEmail }, ======= SentBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Groups: [formData.Groups], IPAWSInfo: { DisseminationChannels: { EAS: formData.EAS, WEA: formData.WEA, NWEM: formData.NWEM, }, Instructions: formData.Instructions, Severity: formData.Severity, Urgency: formData.Urgency, Certainty: formData.Certainty, AlertCategory: formData.AlertCategory, EventCode: formData.EventCode, EventResponse: formData.EventResponse, CountyFIPS: parseInt(formData.CountyFIPS), WEAShortText: formData.WEAShortText, WEALongText: formData.WEALongText, WEAHandling: formData.WEAHandling, WEASpanish: formData.WEASpanish, WEAShortTextSpanish: formData.WEAShortTextSpanish, WEALongTextSpanish: formData.WEALongTextSpanish, IPAWSKey: formData.IPAWSKey, }, Expires: { Hours: formData.ExpiresInHours, Minutes: formData.ExpiresInMinutes, }, SchedulingInfo: { Schedule: formData.ScheduleNotification, Hide: formData.ScheduleHide, SendDate: formData.ScheduleDate, HideDate: formData.ScheduleHideDate, Recurring: formData.ScheduleRecurring, Frequency: formData.Frequency, }, SocialMedia: { Instagram: formData.Instagram, Facebook: formData.Facebook, Twitter: formData.Twitter, }, FeatureToOpen: formData.FeatureToOpen, <<<<<<< HEAD LastUpdated: new Date().toLocaleString(), ======= Response: { body: { alertId: '', sender: '', sentOn: '', }, }, >>>>>>> master }, }) }) dispatch({ type: 'add', payload: { title: 'Notification Sent Successfully.', status: 'success', message: 'You successfully sent this MAXX Notification.', }, }) setSubmitStatus && setSubmitStatus('success') showAction() } catch { dispatch({ type: 'add', payload: { title: 'Sending Notification Failed.', status: 'error', message: 'You failed to send this MAXX Notification.', }, }) setSubmitStatus && setSubmitStatus('failed') showAction() } } else { try { mutate({ Title: formData.Title, Description: formData.Description, Type: formData.Type, Locations: JSON.parse(formData.Locations), <<<<<<< HEAD SentBy: { Name: userName, Email: userEmail }, ======= SentBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Groups: [formData.Groups], IPAWSInfo: { DisseminationChannels: { EAS: formData.EAS, WEA: formData.WEA, NWEM: formData.NWEM, }, Instructions: formData.Instructions, Severity: formData.Severity, Urgency: formData.Urgency, Certainty: formData.Certainty, AlertCategory: formData.AlertCategory, EventCode: formData.EventCode, EventResponse: formData.EventResponse, CountyFIPS: parseInt(formData.CountyFIPS), WEAShortText: formData.WEAShortText, WEALongText: formData.WEALongText, WEAHandling: formData.WEAHandling, WEASpanish: formData.WEASpanish, WEAShortTextSpanish: formData.WEAShortTextSpanish, WEALongTextSpanish: formData.WEALongTextSpanish, IPAWSKey: formData.IPAWSKey, }, Expires: { Hours: formData.ExpiresInHours, Minutes: formData.ExpiresInMinutes }, SchedulingInfo: { Schedule: formData.ScheduleNotification, Hide: formData.ScheduleHide, SendDate: formData.ScheduleDate, HideDate: formData.ScheduleHideDate, Recurring: formData.ScheduleRecurring, Frequency: formData.Frequency, }, SocialMedia: { Instagram: formData.Instagram, Facebook: formData.Facebook, Twitter: formData.Twitter, }, FeatureToOpen: formData.FeatureToOpen, <<<<<<< HEAD LastUpdated: new Date().toLocaleString(), ======= Response: { body: { alertId: '', sender: '', sentOn: '', }, }, >>>>>>> master }) dispatch({ type: 'add', payload: { title: 'Notification Sent Successfully.', status: 'success', message: 'You successfully sent this MAXX Notification.', }, }) setSubmitStatus && setSubmitStatus('success') showAction() } catch { dispatch({ type: 'add', payload: { title: 'Sending Notification Failed.', status: 'error', message: 'You failed to send this MAXX Notification.', }, }) setSubmitStatus && setSubmitStatus('failed') showAction() } } } const handleNotificationUpdate = () => { try { mutatePatch({ Title: formData.Title, Description: formData.Description, Type: formData.Type, Locations: JSON.parse(formData.Locations), <<<<<<< HEAD SentBy: { Name: userName, Email: userEmail }, ======= SentBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Groups: [formData.Groups], IPAWSInfo: { DisseminationChannels: { EAS: formData.EAS, WEA: formData.WEA, NWEM: formData.NWEM, }, Instructions: formData.Instructions, Severity: formData.Severity, Urgency: formData.Urgency, Certainty: formData.Certainty, AlertCategory: formData.AlertCategory, EventCode: formData.EventCode, EventResponse: formData.EventResponse, CountyFIPS: parseInt(formData.CountyFIPS), WEAShortText: formData.WEAShortText, WEALongText: formData.WEALongText, WEAHandling: formData.WEAHandling, WEASpanish: formData.WEASpanish, WEAShortTextSpanish: formData.WEAShortTextSpanish, WEALongTextSpanish: formData.WEALongTextSpanish, IPAWSKey: formData.IPAWSKey, }, Expires: { Hours: formData.ExpiresInHours, Minutes: formData.ExpiresInMinutes }, SchedulingInfo: { Schedule: formData.ScheduleNotification, Hide: formData.ScheduleHide, SendDate: formData.ScheduleDate, HideDate: formData.ScheduleHideDate, Recurring: formData.ScheduleRecurring, Frequency: formData.Frequency, }, SocialMedia: { Instagram: formData.Instagram, Facebook: formData.Facebook, Twitter: formData.Twitter, }, FeatureToOpen: formData.FeatureToOpen, <<<<<<< HEAD LastUpdated: new Date().toLocaleString(), ======= Response: { body: { alertId: '', sender: '', sentOn: '', }, }, >>>>>>> master }) dispatch({ type: 'add', payload: { title: 'Notification Updated Successfully.', status: 'success', message: 'You successfully updated this MAXX Notification.', }, }) showAction() } catch { dispatch({ type: 'add', payload: { title: 'Updating Notification Failed.', status: 'error', message: 'You failed to update this MAXX Notification.', }, }) showAction() } } const handleTemplatePatch = () => { try { mutateTemplatePatch({ Name: formData.Title, Type: formData.Type, <<<<<<< HEAD CreatedBy: { Name: userName, Email: userEmail }, ======= CreatedBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Template: { Title: formData.Title, Description: formData.Description, Type: formData.Type, Locations: JSON.parse(formData.Locations), <<<<<<< HEAD SentBy: { Name: userName, Email: userEmail }, ======= SentBy: { Name: 'Rob Beaty', Email: 'rob@myocv.com' }, >>>>>>> master Groups: [formData.Groups], IPAWSInfo: { DisseminationChannels: { EAS: formData.EAS, WEA: formData.WEA, NWEM: formData.NWEM, }, Instructions: formData.Instructions, Severity: formData.Severity, Urgency: formData.Urgency, Certainty: formData.Certainty, AlertCategory: formData.AlertCategory, EventCode: formData.EventCode, EventResponse: formData.EventResponse, CountyFIPS: parseInt(formData.CountyFIPS), WEAShortText: formData.WEAShortText, WEALongText: formData.WEALongText, WEAHandling: formData.WEAHandling, WEASpanish: formData.WEASpanish, WEAShortTextSpanish: formData.WEAShortTextSpanish, WEALongTextSpanish: formData.WEALongTextSpanish, IPAWSKey: formData.IPAWSKey, }, Expires: { Hours: formData.ExpiresInHours, Minutes: formData.ExpiresInMinutes, }, SchedulingInfo: { Schedule: formData.ScheduleNotification, Hide: formData.ScheduleHide, SendDate: formData.ScheduleDate, HideDate: formData.ScheduleHideDate, Recurring: formData.ScheduleRecurring, Frequency: formData.Frequency, }, SocialMedia: { Instagram: formData.Instagram, Facebook: formData.Facebook, Twitter: formData.Twitter, }, FeatureToOpen: formData.FeatureToOpen, <<<<<<< HEAD LastUpdated: new Date().toLocaleString(), ======= Response: { body: { alertId: '', sender: '', sentOn: '', }, }, >>>>>>> master }, }) showAction() dispatch({ type: 'add', payload: { title: 'Template Updated Successfully.', status: 'success', message: 'You successfully updated this Template.', }, }) } catch { dispatch({ type: 'add', payload: { title: 'Updating Template Failed.', status: 'error', message: 'You failed to update this Template.', }, }) showAction() } } const disseminationChannels = [] if (formData.EAS) disseminationChannels.push('EAS') if (formData.WEA) disseminationChannels.push('WEA/CMAS') if (formData.NWEM) disseminationChannels.push('NWEM') return ( show && ( <Modal disabled={disabled} buttons width="xxl" buttonColor={disabled ? 'gray' : 'green'} show={show} onCancel={() => showAction()} onClick={ templateEdit ? handleTemplatePatch : newNotification ? handleSend : handleNotificationUpdate } buttonTitle="Send Notification" > <ModalCustom> <div className="flex-1 overflow-y-hidden"> <div className="h-full py-8 xl:py-10"> <div className="flex flex-col px-2 mx-auto sm:px-6 lg:px-8 xl:h-full"> <div className="xl:col-span-2 xl:pr-8"> {formData.IPAWSKey === 'Test' ? ( <div className="flex flex-col h-10 rounded-md mb-4 space-x-0 space-y-4 md:flex-row md:space-x-4 md:space-y-0 bg-green-600"> <p className="pl-px text-2xl"> IPAWS Environment: {formData.IPAWSKey} - Lab </p> </div> ) : ( <div className="flex flex-col h-10 rounded-md mb-4 space-x-0 space-y-4 md:flex-row md:space-x-4 md:space-y-0 bg-red-600"> <p className="pl-px text-2xl"> IPAWS Environment: {formData.IPAWSKey} - WARNING LIVE ENVIRONMENT </p> </div> )} <h2 className="font-semibold text-gray-300 ">Headline (Title)</h2> <h1 className="text-2xl font-bold text-gray-900 dark:text-gray-50"> {formData.Title ? formData.Title : 'No Value Provided'} </h1> <div className="py-3 xl:pt-3 xl:pb-0"> <Tabs selected={selectedTab} onSelect={handleTabChange}> <Tab title="General"> <div className="grid grid-cols-1 overflow-y-auto xl:grid-cols-3 xl:gap-4"> <div className="col-span-1 pt-4 xl:col-span-3"> <h2 className="text-lg font-semibold text-gray-200"> Description </h2> <div className="mb-8 prose dark:text-gray-200 max-w-none"> <p> {formData.Description ? formData.Description : 'No Value Provided'} </p> </div> </div> <div className=""> <h2 className="font-semibold text-gray-200 ">County FIPS</h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData['CountyFIPS'] ? formData['CountyFIPS'] : 'No Value Provided'} </p> </div> </div> <div className=""> <h2 className="font-semibold text-gray-200 ">Expires in: </h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData.ExpiresInHours + ' Hour(s), ' + formData.ExpiresInMinutes + ' Minute(s)'} </p> </div> </div> {formData.WEA && ( <> <div className="py-4"> <h2 className="font-semibold text-gray-300 "> WEA Short Text </h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData.WEAShortText ? formData.WEAShortText : 'No Value Provided'} </p> </div> </div> <div className="py-4"> <h2 className="font-semibold text-gray-200 "> WEA Long Text </h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData.WEALongText ? formData.WEALongText : 'No Value Provided'} </p> </div> </div> {formData.WEASpanish && ( <> <div className="py-4"> <h2 className="font-semibold text-gray-200 "> WEA Short Text (Spanish) </h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData.WEAShortTextSpanish ? formData.WEAShortTextSpanish : 'No Value Provided'} </p> </div> </div> <div className="py-4"> <h2 className="font-semibold text-gray-200 "> WEA Long Text (Spanish) </h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData.WEALongTextSpanish ? formData.WEALongTextSpanish : 'No Value Provided'} </p> </div> </div> </> )} </> )} </div> </Tab> {formData.Type === 'IPAWS' && ( <Tab title="IPAWS"> <div className="h-auto overflow-y-auto"> <div className="grid grid-cols-3 py-4 border-gray-200 gap-y-6"> <div className="col-span-3"> <h2 className="text-sm font-semibold text-gray-300"> Instructions </h2> <div className="prose dark:text-gray-200 max-w-none"> <p> {formData.Instructions ? formData.Instructions : 'No Value Provided'} </p> </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Distribution Channels </h2> <div className="prose dark:text-gray-200 max-w-none"> <p>{disseminationChannels.join(', ')}</p> </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Event Code </h2> <div className="prose dark:text-gray-200 max-w-none"> <p>{eventCodes[formData['EventCode']]?.name}</p> </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Event Response </h2> <div className="m-1"> <Badge color={ eventResponseMap[formData['EventResponse']]?.color } > {eventResponseMap[formData['EventResponse']]?.name} </Badge> </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Alert Category </h2> <div className="m-1"> <Badge color={categoryMap[formData['AlertCategory']]?.color} > {categoryMap[formData['AlertCategory']]?.name} </Badge> </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Severity </h2> <div className="m-1"> {formData.WEA ? ( <Badge color={weaSeverityMap[formData.Severity]?.color} > {weaSeverityMap[formData.Severity]?.name} </Badge> ) : ( <Badge color={severityMap[formData.Severity]?.color}> {severityMap[formData.Severity]?.name} </Badge> )} </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Urgency </h2> <div className="m-1"> {formData.WEA ? ( <Badge color={weaUrgencyMap[formData.Urgency]?.color}> {weaUrgencyMap[formData.Urgency]?.name} </Badge> ) : ( <Badge color={urgencyMap[formData.Urgency]?.color}> {urgencyMap[formData.Urgency]?.name} </Badge> )} </div> </div> <div> <h2 className="text-sm font-semibold text-gray-300"> Certainty </h2> <div className="m-1"> {formData.WEA ? ( <Badge color={weaCertaintyMap[formData.Certainty]?.color} > {weaCertaintyMap[formData.Certainty]?.name} </Badge> ) : ( <Badge color={certaintyMap[formData.Certainty]?.color} > {certaintyMap[formData.Certainty]?.name} </Badge> )} </div> </div> {formData['WEA Handling'] && ( <div> <h2 className="text-sm font-semibold text-gray-300"> WEA Handling </h2> <div className="m-1"> <Badge color={ weaHandlingMap[formData['WEAHandling']]?.color } > {weaHandlingMap[formData['WEAHandling']]?.name} </Badge> </div> </div> )} </div> </div> </Tab> )} <Tab title="Locations"> <DetailMap locations={JSON.parse(formData.Locations)} /> </Tab> </Tabs> </div> </div> </div> </div> </div> </ModalCustom> <div className="px-6 py-6 bg-gray-200 dark:bg-gray-800 sm:px-6 "> <h2 className="text-lg font-semibold text-red-400"> You are sending as {userName}. </h2> <Checkbox onChange={() => toggleDisabled(false)}> I, {userName}, by checking this box do hereby accept responsibility for sending out this notification in ensuring public safety and emergency preparedness. </Checkbox> </div> </Modal> ) ) } export default SubmissionModal
Preview:
downloadDownload PNG
downloadDownload JPEG
downloadDownload SVG
Tip: You can change the style, width & colours of the snippet with the inspect tool before clicking Download!
Click to optimize width for Twitter