Implement modals across create flow
This commit is contained in:
@@ -16,23 +16,18 @@ import { useCreateFlowMdUp } from "../../hooks/useCreateFlowMdUp";
|
||||
import { CreateFlowHeaderLockup } from "../../components/CreateFlowHeaderLockup";
|
||||
import CardStack from "../../../components/utility/CardStack";
|
||||
import Create from "../../../components/modals/Create";
|
||||
import TextArea from "../../../components/controls/TextArea";
|
||||
import InlineTextButton from "../../../components/buttons/InlineTextButton";
|
||||
import { CreateFlowStepShell } from "../../components/CreateFlowStepShell";
|
||||
import {
|
||||
CREATE_FLOW_CARD_STACK_AREA_MAX_CLASS,
|
||||
CREATE_FLOW_MD_UP_COLUMN_MAX_CLASS,
|
||||
} from "../../components/createFlowLayoutTokens";
|
||||
import ModalTextAreaField from "../../components/ModalTextAreaField";
|
||||
|
||||
const IN_PERSON_CARD_ID = "in-person-meetings";
|
||||
const SIGNAL_CARD_ID = "signal";
|
||||
const VIDEO_MEETINGS_CARD_ID = "video-meetings";
|
||||
|
||||
const ADD_PLATFORM_CARD_IDS = [
|
||||
IN_PERSON_CARD_ID,
|
||||
SIGNAL_CARD_ID,
|
||||
VIDEO_MEETINGS_CARD_ID,
|
||||
] as const;
|
||||
|
||||
const SECTION_FIELDS = [
|
||||
"corePrinciple",
|
||||
"logisticsAdmin",
|
||||
@@ -50,40 +45,6 @@ const COMMUNICATION_CARD_ORDER = [
|
||||
"7",
|
||||
] as const;
|
||||
|
||||
function CreateModalSection({
|
||||
title,
|
||||
value: _value,
|
||||
onChange,
|
||||
}: {
|
||||
title: string;
|
||||
value: string;
|
||||
onChange: (_value: string) => void;
|
||||
}) {
|
||||
return (
|
||||
<div className="flex flex-col gap-2">
|
||||
<div className="flex items-center gap-2">
|
||||
<h3 className="text-sm font-semibold leading-tight text-[var(--color-content-default-primary)]">
|
||||
{title}
|
||||
</h3>
|
||||
<span
|
||||
className="flex h-4 w-4 shrink-0 items-center justify-center rounded-full border border-[var(--color-content-invert-brand-secondary)] bg-transparent text-[10px] font-medium leading-none text-[var(--color-content-invert-brand-secondary)]"
|
||||
aria-hidden
|
||||
>
|
||||
?
|
||||
</span>
|
||||
</div>
|
||||
<TextArea
|
||||
formHeader={false}
|
||||
value={_value}
|
||||
onChange={(e) => onChange(e.target.value)}
|
||||
size="large"
|
||||
rows={6}
|
||||
appearance="embedded"
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
function AddPlatformModalContent({
|
||||
platformCardId,
|
||||
}: {
|
||||
@@ -92,15 +53,15 @@ function AddPlatformModalContent({
|
||||
const { markCreateFlowInteraction } = useCreateFlow();
|
||||
const m = useMessages();
|
||||
const comm = m.create.communication;
|
||||
const modal = comm.modals[platformCardId as keyof typeof comm.modals];
|
||||
const defaults =
|
||||
modal && "sections" in modal
|
||||
? modal.sections
|
||||
: {
|
||||
corePrinciple: "",
|
||||
logisticsAdmin: "",
|
||||
codeOfConduct: "",
|
||||
};
|
||||
const modal =
|
||||
platformCardId in comm.modals
|
||||
? comm.modals[platformCardId as keyof typeof comm.modals]
|
||||
: null;
|
||||
const defaults = modal?.sections ?? {
|
||||
corePrinciple: "",
|
||||
logisticsAdmin: "",
|
||||
codeOfConduct: "",
|
||||
};
|
||||
|
||||
const [sectionValues, setSectionValues] = useState<
|
||||
Record<SectionField, string>
|
||||
@@ -118,14 +79,13 @@ function AddPlatformModalContent({
|
||||
[markCreateFlowInteraction],
|
||||
);
|
||||
|
||||
if (!modal || !("sections" in modal)) return null;
|
||||
|
||||
return (
|
||||
<div className="flex flex-col gap-6">
|
||||
{SECTION_FIELDS.map((field) => (
|
||||
<CreateModalSection
|
||||
<ModalTextAreaField
|
||||
key={field}
|
||||
title={comm.sectionHeadings[field]}
|
||||
label={comm.sectionHeadings[field]}
|
||||
rows={6}
|
||||
value={sectionValues[field]}
|
||||
onChange={(v) => updateSection(field, v)}
|
||||
/>
|
||||
@@ -134,13 +94,6 @@ function AddPlatformModalContent({
|
||||
);
|
||||
}
|
||||
|
||||
function isAddPlatformCard(cardId: string | null): boolean {
|
||||
return (
|
||||
cardId !== null &&
|
||||
(ADD_PLATFORM_CARD_IDS as readonly string[]).includes(cardId)
|
||||
);
|
||||
}
|
||||
|
||||
export function CommunicationMethodsScreen() {
|
||||
const m = useMessages();
|
||||
const comm = m.create.communication;
|
||||
@@ -180,42 +133,55 @@ export function CommunicationMethodsScreen() {
|
||||
) : (
|
||||
<>
|
||||
{comm.page.compactDescriptionBefore}
|
||||
<button
|
||||
type="button"
|
||||
className="cursor-pointer border-none bg-transparent p-0 font-inherit text-[length:inherit] leading-[inherit] text-[var(--color-content-default-tertiary)] underline decoration-solid underline-offset-2 hover:opacity-90 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--color-border-invert-primary)]"
|
||||
<InlineTextButton
|
||||
onClick={() => {
|
||||
markCreateFlowInteraction();
|
||||
setExpanded(true);
|
||||
}}
|
||||
>
|
||||
{comm.page.compactDescriptionLinkLabel}
|
||||
</button>
|
||||
</InlineTextButton>
|
||||
{comm.page.compactDescriptionAfter}
|
||||
</>
|
||||
);
|
||||
|
||||
const modalConfig =
|
||||
pendingCardId && pendingCardId in comm.modals
|
||||
? (() => {
|
||||
const modal =
|
||||
comm.modals[pendingCardId as keyof typeof comm.modals];
|
||||
return {
|
||||
title: modal.title,
|
||||
description: modal.description,
|
||||
nextButtonText: comm.addPlatform.nextButtonText,
|
||||
showBackButton: false as const,
|
||||
currentStep: undefined,
|
||||
totalSteps: undefined,
|
||||
};
|
||||
})()
|
||||
: {
|
||||
title: comm.confirmModal.title,
|
||||
description: comm.confirmModal.description,
|
||||
nextButtonText: comm.confirmModal.nextButtonText,
|
||||
showBackButton: false as const,
|
||||
currentStep: undefined,
|
||||
totalSteps: undefined,
|
||||
};
|
||||
const modalConfig = (() => {
|
||||
if (!pendingCardId) {
|
||||
return {
|
||||
title: comm.confirmModal.title,
|
||||
description: comm.confirmModal.description,
|
||||
nextButtonText: comm.confirmModal.nextButtonText,
|
||||
showBackButton: false as const,
|
||||
currentStep: undefined,
|
||||
totalSteps: undefined,
|
||||
};
|
||||
}
|
||||
|
||||
if (pendingCardId in comm.modals) {
|
||||
const modal = comm.modals[pendingCardId as keyof typeof comm.modals];
|
||||
return {
|
||||
title: modal.title,
|
||||
description: modal.description,
|
||||
nextButtonText: comm.addPlatform.nextButtonText,
|
||||
showBackButton: false as const,
|
||||
currentStep: undefined,
|
||||
totalSteps: undefined,
|
||||
};
|
||||
}
|
||||
|
||||
const cardRow =
|
||||
pendingCardId in comm.cards
|
||||
? comm.cards[pendingCardId as keyof typeof comm.cards]
|
||||
: null;
|
||||
return {
|
||||
title: cardRow?.label ?? comm.confirmModal.title,
|
||||
description: cardRow?.supportText ?? comm.confirmModal.description,
|
||||
nextButtonText: comm.addPlatform.nextButtonText,
|
||||
showBackButton: false as const,
|
||||
currentStep: undefined,
|
||||
totalSteps: undefined,
|
||||
};
|
||||
})();
|
||||
|
||||
const handleCardClick = useCallback(
|
||||
(id: string) => {
|
||||
@@ -286,8 +252,9 @@ export function CommunicationMethodsScreen() {
|
||||
showBackButton={modalConfig.showBackButton}
|
||||
currentStep={modalConfig.currentStep}
|
||||
totalSteps={modalConfig.totalSteps}
|
||||
backdropVariant="loginYellow"
|
||||
>
|
||||
{isAddPlatformCard(pendingCardId) && pendingCardId ? (
|
||||
{pendingCardId ? (
|
||||
<AddPlatformModalContent
|
||||
key={pendingCardId}
|
||||
platformCardId={pendingCardId}
|
||||
|
||||
Reference in New Issue
Block a user