diff --git a/met-web/src/components/engagement/form/RichEditorStyles.css b/met-web/src/components/common/RichTextEditor/RichEditorStyles.css similarity index 100% rename from met-web/src/components/engagement/form/RichEditorStyles.css rename to met-web/src/components/common/RichTextEditor/RichEditorStyles.css diff --git a/met-web/src/components/engagement/form/RichTextEditor.tsx b/met-web/src/components/common/RichTextEditor/index.tsx similarity index 76% rename from met-web/src/components/engagement/form/RichTextEditor.tsx rename to met-web/src/components/common/RichTextEditor/index.tsx index 6fd447c52..8ffe7f395 100644 --- a/met-web/src/components/engagement/form/RichTextEditor.tsx +++ b/met-web/src/components/common/RichTextEditor/index.tsx @@ -1,10 +1,11 @@ import React, { useEffect } from 'react'; -import { EditorState, ContentState, convertFromHTML, convertFromRaw, convertToRaw } from 'draft-js'; +import { EditorState, convertToRaw } from 'draft-js'; import { Editor } from 'react-draft-wysiwyg'; import { FormControl, FormHelperText } from '@mui/material'; -import { MetPaper } from '../../common'; import 'react-draft-wysiwyg/dist/react-draft-wysiwyg.css'; import './RichEditorStyles.css'; +import { getEditorStateFromHtml, getEditorStateFromRaw } from './utils'; +import { MetPaper } from '..'; const RichTextEditor = ({ setRawText = (_rawText: string) => { @@ -20,30 +21,17 @@ const RichTextEditor = ({ }) => { const getStateFromInitialValue = () => { if (initialRawEditorState) { - setEditorState(getEditorState(initialRawEditorState)); + setEditorState(getEditorStateFromRaw(initialRawEditorState)); return; } if (initialHTMLText) { - const blocksFromHTML = convertFromHTML(initialHTMLText); - const contentState = ContentState.createFromBlockArray( - blocksFromHTML.contentBlocks, - blocksFromHTML.entityMap, - ); - setEditorState(EditorState.createWithContent(contentState)); - return; - } - }; - - const getEditorState = (rawTextToConvert: string) => { - if (!rawTextToConvert) { - return EditorState.createEmpty(); + const contentState = getEditorStateFromHtml(initialHTMLText); + setEditorState(contentState); } - const rawContentFromStore = convertFromRaw(JSON.parse(rawTextToConvert)); - return EditorState.createWithContent(rawContentFromStore); }; - const [editorState, setEditorState] = React.useState(getEditorState(initialRawEditorState)); + const [editorState, setEditorState] = React.useState(getEditorStateFromRaw(initialRawEditorState)); const handleChange = (newEditorState: EditorState) => { const plainText = newEditorState.getCurrentContent().getPlainText(); diff --git a/met-web/src/components/common/RichTextEditor/utils.ts b/met-web/src/components/common/RichTextEditor/utils.ts new file mode 100644 index 000000000..9a87d60d6 --- /dev/null +++ b/met-web/src/components/common/RichTextEditor/utils.ts @@ -0,0 +1,17 @@ +import { ContentState, EditorState, convertFromHTML, convertFromRaw } from 'draft-js'; + +// For draft-js to convert raw text to editor state +export const getEditorStateFromRaw = (rawTextToConvert: string) => { + if (!rawTextToConvert) { + return EditorState.createEmpty(); + } + const rawContentFromStore = convertFromRaw(JSON.parse(rawTextToConvert)); + return EditorState.createWithContent(rawContentFromStore); +}; + +// For draft-js to convert html to editor state +export const getEditorStateFromHtml = (htmlToConvert: string) => { + const blocksFromHTML = convertFromHTML(htmlToConvert); + const contentState = ContentState.createFromBlockArray(blocksFromHTML.contentBlocks, blocksFromHTML.entityMap); + return EditorState.createWithContent(contentState); +}; diff --git a/met-web/src/components/engagement/form/EngagementFormTabs/EngagementForm.tsx b/met-web/src/components/engagement/form/EngagementFormTabs/EngagementForm.tsx index 2bfe92079..888fd1e51 100644 --- a/met-web/src/components/engagement/form/EngagementFormTabs/EngagementForm.tsx +++ b/met-web/src/components/engagement/form/EngagementFormTabs/EngagementForm.tsx @@ -1,7 +1,6 @@ import React, { useContext, useEffect, useState } from 'react'; import { Typography, Grid, TextField, Stack, Box } from '@mui/material'; import { MetPaper, MetLabel, PrimaryButton, SecondaryButton, MetDescription } from '../../../common'; -import RichTextEditor from '../RichTextEditor'; import { ActionContext } from '../ActionContext'; import ImageUpload from 'components/imageUpload'; import { useNavigate } from 'react-router-dom'; @@ -11,6 +10,7 @@ import { EngagementTabsContext } from './EngagementTabsContext'; import { SUBMISSION_STATUS } from 'constants/engagementStatus'; import DayCalculatorModal from '../DayCalculator'; import { ENGAGEMENT_CROPPER_ASPECT_RATIO, ENGAGMENET_UPLOADER_HEIGHT } from './constants'; +import RichTextEditor from 'components/common/RichTextEditor'; const CREATE = 'create'; const EngagementForm = () => { diff --git a/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyClosedTextInput.tsx b/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyClosedTextInput.tsx index 83335d555..7f2f61e3d 100644 --- a/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyClosedTextInput.tsx +++ b/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyClosedTextInput.tsx @@ -1,6 +1,6 @@ import React, { useContext, useState } from 'react'; import { defaultClosedText } from 'constants/submissionStatusText'; -import RichTextEditor from '../../RichTextEditor'; +import RichTextEditor from 'components/common/RichTextEditor'; import { EngagementTabsContext } from '../EngagementTabsContext'; export const SurveyClosedTextInput = () => { diff --git a/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyOpenTextInput.tsx b/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyOpenTextInput.tsx index f86bfbc57..f8e998546 100644 --- a/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyOpenTextInput.tsx +++ b/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyOpenTextInput.tsx @@ -1,6 +1,6 @@ import React, { useContext, useState } from 'react'; import { defaultOpenText } from 'constants/submissionStatusText'; -import RichTextEditor from '../../RichTextEditor'; +import RichTextEditor from 'components/common/RichTextEditor'; import { EngagementTabsContext } from '../EngagementTabsContext'; export const SurveyOpenTextInput = () => { diff --git a/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyUpcomingTextInput.tsx b/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyUpcomingTextInput.tsx index ee5b45f0f..8e8b6062b 100644 --- a/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyUpcomingTextInput.tsx +++ b/met-web/src/components/engagement/form/EngagementFormTabs/SurveyBlock/SurveyUpcomingTextInput.tsx @@ -1,6 +1,6 @@ import React, { useContext, useState } from 'react'; import { defaultUpcomingText } from 'constants/submissionStatusText'; -import RichTextEditor from '../../RichTextEditor'; +import RichTextEditor from 'components/common/RichTextEditor'; import { EngagementTabsContext } from '../EngagementTabsContext'; export const SurveyUpcomingTextInput = () => { diff --git a/met-web/src/components/engagement/status/index.tsx b/met-web/src/components/engagement/status/index.tsx index 4a18da52a..691a2308f 100644 --- a/met-web/src/components/engagement/status/index.tsx +++ b/met-web/src/components/engagement/status/index.tsx @@ -3,40 +3,62 @@ import { Chip } from '@mui/material'; import { SubmissionStatus } from 'constants/engagementStatus'; const Chip_Font_Weight = { fontWeight: 'bold' }; -const Open = ({ preview }: { preview?: boolean }) => { - return ; +interface ChipParams { + active: boolean; + clickable: boolean; +} +const Open = ({ active, clickable }: ChipParams) => { + return ( + + ); }; -const Closed = ({ preview }: { preview?: boolean }) => { - return ; +const Closed = ({ active, clickable }: ChipParams) => { + return ( + + ); }; -const Upcoming = ({ preview }: { preview?: boolean }) => { +const Upcoming = ({ active, clickable }: ChipParams) => { return ( ); }; export const EngagementStatusChip = ({ submissionStatus, - preview, + active = true, + clickable = false, }: { submissionStatus: SubmissionStatus; - preview?: boolean; + active?: boolean; + clickable?: boolean; }) => { switch (submissionStatus) { case SubmissionStatus.Upcoming: // Engagement is published but submission start date is not due yet. - return ; + return ; case SubmissionStatus.Open: // Engagement is published and open for submission. - return ; + return ; case SubmissionStatus.Closed: // Engagement is published but it's past the submission date. - return ; + return ; default: return null; } diff --git a/met-web/src/components/engagement/view/EngagementBanner.tsx b/met-web/src/components/engagement/view/EngagementBanner.tsx index 1d653c1ec..3cca75695 100644 --- a/met-web/src/components/engagement/view/EngagementBanner.tsx +++ b/met-web/src/components/engagement/view/EngagementBanner.tsx @@ -10,11 +10,12 @@ import { When } from 'react-if'; import EngagementInfoSection from './EngagementInfoSection'; export const EngagementBanner = ({ startSurvey }: EngagementBannerProps) => { - const { isEngagementLoading, savedEngagement } = useContext(ActionContext); + const { isEngagementLoading, savedEngagement, mockStatus } = useContext(ActionContext); const surveyId = savedEngagement.surveys[0]?.id || ''; - const isOpen = savedEngagement.submission_status === SubmissionStatus.Open; const isLoggedIn = useAppSelector((state) => state.user.authentication.authenticated); const isPreview = isLoggedIn; + const currentStatus = isPreview ? mockStatus : savedEngagement.submission_status; + const isOpen = currentStatus === SubmissionStatus.Open; if (isEngagementLoading) { return ; @@ -23,7 +24,7 @@ export const EngagementBanner = ({ startSurvey }: EngagementBannerProps) => { return ( - + Share your thoughts diff --git a/met-web/src/components/engagement/view/EngagementContent.tsx b/met-web/src/components/engagement/view/EngagementContent.tsx index 54673b51d..b1f683ce6 100644 --- a/met-web/src/components/engagement/view/EngagementContent.tsx +++ b/met-web/src/components/engagement/view/EngagementContent.tsx @@ -3,7 +3,7 @@ import { MetPaper } from '../../common'; import { Editor } from 'react-draft-wysiwyg'; import { ActionContext } from './ActionContext'; import { Skeleton } from '@mui/material'; -import { getEditorState } from 'utils'; +import { getEditorStateFromRaw } from 'components/common/RichTextEditor/utils'; export const EngagementContent = () => { const { savedEngagement, isEngagementLoading } = useContext(ActionContext); @@ -16,7 +16,7 @@ export const EngagementContent = () => { return ( - + ); }; diff --git a/met-web/src/components/engagement/view/EngagementInfoSection.tsx b/met-web/src/components/engagement/view/EngagementInfoSection.tsx index 040860ba1..2877e4d43 100644 --- a/met-web/src/components/engagement/view/EngagementInfoSection.tsx +++ b/met-web/src/components/engagement/view/EngagementInfoSection.tsx @@ -3,11 +3,11 @@ import { Grid, Typography, Stack } from '@mui/material'; import { MetHeader1 } from 'components/common'; import { EngagementStatusChip } from '../status'; import { Editor } from 'react-draft-wysiwyg'; -import { getEditorState } from 'utils'; import dayjs from 'dayjs'; import { ActionContext } from './ActionContext'; import { Engagement } from 'models/engagement'; import { useAppSelector } from 'hooks'; +import { getEditorStateFromRaw } from 'components/common/RichTextEditor/utils'; interface EngagementInfoSectionProps { savedEngagement: Engagement; @@ -58,7 +58,7 @@ const EngagementInfoSection = ({ savedEngagement, children }: EngagementInfoSect {name} - + diff --git a/met-web/src/components/engagement/view/PreviewBanner.tsx b/met-web/src/components/engagement/view/PreviewBanner.tsx index 79c645efb..203fd2c9b 100644 --- a/met-web/src/components/engagement/view/PreviewBanner.tsx +++ b/met-web/src/components/engagement/view/PreviewBanner.tsx @@ -154,20 +154,23 @@ export const PreviewBanner = () => { updateMockStatus(SubmissionStatus.Upcoming)}> updateMockStatus(SubmissionStatus.Open)}> updateMockStatus(SubmissionStatus.Closed)}> diff --git a/met-web/src/components/engagement/view/SurveyBlock.tsx b/met-web/src/components/engagement/view/SurveyBlock.tsx index dfe3244af..10f680d90 100644 --- a/met-web/src/components/engagement/view/SurveyBlock.tsx +++ b/met-web/src/components/engagement/view/SurveyBlock.tsx @@ -5,26 +5,21 @@ import { ActionContext } from './ActionContext'; import { SubmissionStatus } from 'constants/engagementStatus'; import { SurveyBlockProps } from './types'; import { useAppSelector } from 'hooks'; -import { If, Then, Else } from 'react-if'; import { submissionStatusArray } from 'constants/submissionStatusText'; import { Editor } from 'react-draft-wysiwyg'; -import { getEditorState } from 'utils'; - -const statusMap = { - 1: 'Upcoming', - 2: 'Open', - 3: 'Closed', -}; +import { getEditorStateFromHtml, getEditorStateFromRaw } from 'components/common/RichTextEditor/utils'; const SurveyBlock = ({ startSurvey }: SurveyBlockProps) => { const { savedEngagement, isEngagementLoading, mockStatus } = useContext(ActionContext); - const isOpen = savedEngagement.submission_status === SubmissionStatus.Open; - const surveyId = savedEngagement.surveys[0]?.id || ''; const isLoggedIn = useAppSelector((state) => state.user.authentication.authenticated); const isPreview = isLoggedIn; + const currentStatus = isPreview ? mockStatus : savedEngagement.submission_status; + const isOpen = currentStatus === SubmissionStatus.Open; + const surveyId = savedEngagement.surveys[0]?.id || ''; const status_block = savedEngagement.status_block; - const status_text = status_block.find((status) => status.survey_status === statusMap[mockStatus])?.block_text; - const isMockStatusClosed = SubmissionStatus.Closed === mockStatus; + const status_text = status_block.find( + (status) => status.survey_status === SubmissionStatus[currentStatus], + )?.block_text; if (isEngagementLoading) { return ; } @@ -33,29 +28,20 @@ const SurveyBlock = ({ startSurvey }: SurveyBlockProps) => { - <> - - - - - -
- - - + Take me to the survey diff --git a/met-web/src/utils/index.ts b/met-web/src/utils/index.ts index 973a7e91b..1ffdae549 100644 --- a/met-web/src/utils/index.ts +++ b/met-web/src/utils/index.ts @@ -1,5 +1,4 @@ import { AxiosResponse } from 'axios'; -import { EditorState, convertFromRaw } from 'draft-js'; export function hasKey(obj: O, key: PropertyKey): key is keyof O { return key in obj; @@ -15,15 +14,6 @@ export function checkEmail(email: string) { return filter.test(email); } -// For draft-js to convert raw text to editor state -export const getEditorState = (rawTextToConvert: string) => { - if (!rawTextToConvert) { - return EditorState.createEmpty(); - } - const rawContentFromStore = convertFromRaw(JSON.parse(rawTextToConvert)); - return EditorState.createWithContent(rawContentFromStore); -}; - export const downloadFile = (response: AxiosResponse, filename: string) => { if (!filename) { throw new Error('Filename must be specified');