mirror of
https://github.com/scm-manager/scm-manager.git
synced 2025-11-12 00:15:44 +01:00
Implement new form features
Extends existing functionality, provides new fallbacks for translations and adds capabilities to manage array properties in configurations. Committed-by: Florian Scholdei <florian.scholdei@cloudogu.com> Co-authored-by: Florian Scholdei <florian.scholdei@cloudogu.com>
This commit is contained in:
committed by
SCM-Manager
parent
719f6c4c09
commit
dda52b8400
@@ -24,9 +24,10 @@
|
||||
|
||||
import React, { ComponentProps } from "react";
|
||||
import { Controller, ControllerRenderProps, Path } from "react-hook-form";
|
||||
import classNames from "classnames";
|
||||
import { useScmFormContext } from "../ScmFormContext";
|
||||
import SelectField from "./SelectField";
|
||||
import { useScmFormPathContext } from "../FormPathContext";
|
||||
import { prefixWithoutIndices } from "../helpers";
|
||||
|
||||
type Props<T extends Record<string, unknown>> = Omit<
|
||||
ComponentProps<typeof SelectField>,
|
||||
@@ -42,32 +43,38 @@ function ControlledSelectField<T extends Record<string, unknown>>({
|
||||
label,
|
||||
helpText,
|
||||
rules,
|
||||
className,
|
||||
testId,
|
||||
defaultValue,
|
||||
readOnly,
|
||||
...props
|
||||
}: Props<T>) {
|
||||
const { control, t, readOnly: formReadonly } = useScmFormContext();
|
||||
const labelTranslation = label || t(`${name}.label`) || "";
|
||||
const helpTextTranslation = helpText || t(`${name}.helpText`);
|
||||
const { control, t, readOnly: formReadonly, formId } = useScmFormContext();
|
||||
const formPathPrefix = useScmFormPathContext();
|
||||
const nameWithPrefix = formPathPrefix ? `${formPathPrefix}.${name}` : name;
|
||||
const prefixedNameWithoutIndices = prefixWithoutIndices(nameWithPrefix);
|
||||
const labelTranslation = label || t(`${prefixedNameWithoutIndices}.label`) || "";
|
||||
const helpTextTranslation = helpText || t(`${prefixedNameWithoutIndices}.helpText`);
|
||||
return (
|
||||
<Controller
|
||||
control={control}
|
||||
name={name}
|
||||
name={nameWithPrefix}
|
||||
rules={rules}
|
||||
defaultValue={defaultValue as never}
|
||||
render={({ field, fieldState }) => (
|
||||
<SelectField
|
||||
className={classNames("column", className)}
|
||||
form={formId}
|
||||
readOnly={readOnly ?? formReadonly}
|
||||
required={rules?.required as boolean}
|
||||
{...props}
|
||||
{...field}
|
||||
label={labelTranslation}
|
||||
helpText={helpTextTranslation}
|
||||
error={fieldState.error ? fieldState.error.message || t(`${name}.error.${fieldState.error.type}`) : undefined}
|
||||
testId={testId ?? `select-${name}`}
|
||||
error={
|
||||
fieldState.error
|
||||
? fieldState.error.message || t(`${prefixedNameWithoutIndices}.error.${fieldState.error.type}`)
|
||||
: undefined
|
||||
}
|
||||
testId={testId ?? `select-${nameWithPrefix}`}
|
||||
/>
|
||||
)}
|
||||
/>
|
||||
|
||||
@@ -22,22 +22,32 @@
|
||||
* SOFTWARE.
|
||||
*/
|
||||
|
||||
import React, { InputHTMLAttributes } from "react";
|
||||
import React, { InputHTMLAttributes, Key, OptionHTMLAttributes } from "react";
|
||||
import classNames from "classnames";
|
||||
import { createVariantClass, Variant } from "../variants";
|
||||
import { createAttributesForTesting } from "@scm-manager/ui-components";
|
||||
|
||||
type Props = {
|
||||
variant?: Variant;
|
||||
options?: Array<OptionHTMLAttributes<HTMLOptionElement> & { label: string }>;
|
||||
testId?: string;
|
||||
} & InputHTMLAttributes<HTMLSelectElement>;
|
||||
|
||||
const Select = React.forwardRef<HTMLSelectElement, Props>(({ variant, children, className, testId, ...props }, ref) => (
|
||||
<div className={classNames("select", { "is-multiple": props.multiple }, createVariantClass(variant), className)}>
|
||||
<select ref={ref} {...props} {...createAttributesForTesting(testId)}>
|
||||
{children}
|
||||
</select>
|
||||
</div>
|
||||
));
|
||||
const Select = React.forwardRef<HTMLSelectElement, Props>(
|
||||
({ variant, children, className, options, testId, ...props }, ref) => (
|
||||
<div className={classNames("select", { "is-multiple": props.multiple }, createVariantClass(variant), className)}>
|
||||
<select ref={ref} {...props} {...createAttributesForTesting(testId)}>
|
||||
{options
|
||||
? options.map((option) => (
|
||||
<option {...option} key={option.value as Key}>
|
||||
{option.label}
|
||||
{option.children}
|
||||
</option>
|
||||
))
|
||||
: children}
|
||||
</select>
|
||||
</div>
|
||||
)
|
||||
);
|
||||
|
||||
export default Select;
|
||||
|
||||
Reference in New Issue
Block a user