"use client"; import { useState } from "react"; import { Button, Group, Stack } from "@mantine/core"; import { objectEntries } from "@homarr/common"; import type { WidgetKind } from "@homarr/definitions"; import { zodResolver } from "@homarr/form"; import { createModal, useModalAction } from "@homarr/modals"; import { useI18n } from "@homarr/translation/client"; import { z } from "@homarr/validation"; import { zodErrorMap } from "@homarr/validation/form"; import { widgetImports } from ".."; import { getInputForType } from "../_inputs"; import { FormProvider, useForm } from "../_inputs/form"; import type { BoardItemAdvancedOptions } from "../../../validation/src/shared"; import type { OptionsBuilderResult } from "../options"; import type { IntegrationSelectOption } from "../widget-integration-select"; import { WidgetIntegrationSelect } from "../widget-integration-select"; import { WidgetAdvancedOptionsModal } from "./widget-advanced-options-modal"; export interface WidgetEditModalState { options: Record; integrationIds: string[]; advancedOptions: BoardItemAdvancedOptions; } interface ModalProps { kind: TSort; value: WidgetEditModalState; onSuccessfulEdit: (value: WidgetEditModalState) => void; integrationData: IntegrationSelectOption[]; integrationSupport: boolean; } export const WidgetEditModal = createModal>(({ actions, innerProps }) => { const t = useI18n(); const [advancedOptions, setAdvancedOptions] = useState(innerProps.value.advancedOptions); // Translate the error messages z.setErrorMap(zodErrorMap(t)); const form = useForm({ mode: "controlled", initialValues: innerProps.value, validate: zodResolver( z.object({ options: z.object( objectEntries(widgetImports[innerProps.kind].definition.options).reduce( (acc, [key, value]: [string, { type: string; validate?: z.ZodType }]) => { if (value.validate) { acc[key] = value.type === "multiText" ? z.array(value.validate).optional() : value.validate; } return acc; }, {} as Record>, ), ), integrationIds: z.array(z.string()), advancedOptions: z.object({ customCssClasses: z.array(z.string()), }), }), ), validateInputOnBlur: true, validateInputOnChange: true, }); const { openModal } = useModalAction(WidgetAdvancedOptionsModal); const { definition } = widgetImports[innerProps.kind]; return (
{ innerProps.onSuccessfulEdit({ ...values, advancedOptions, }); actions.closeModal(); })} > {innerProps.integrationSupport && ( )} {Object.entries(definition.options).map(([key, value]: [string, OptionsBuilderResult[string]]) => { const Input = getInputForType(value.type); if ( // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition !Input || // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition value.shouldHide?.( form.values.options as never, innerProps.integrationData .filter(({ id }) => form.values.integrationIds.includes(id)) .map(({ kind }) => kind), ) ) { return null; } return ( ); })}
); }).withOptions({ keepMounted: true, defaultTitle(t) { return t("item.edit.title"); }, size: "lg", });