{"version":3,"file":"Field.cjs","sources":["../../../../src/components/Forms/Field.tsx"],"sourcesContent":["import { css, cx } from '@emotion/css';\nimport { useId, type HTMLAttributes } from 'react';\nimport * as React from 'react';\n\nimport { type GrafanaTheme2 } from '@grafana/data';\n\nimport { useStyles2 } from '../../themes/ThemeContext';\nimport { getChildId } from '../../utils/reactUtils';\n\nimport { FieldContext } from './FieldContext';\nimport { FieldValidationMessage } from './FieldValidationMessage';\nimport { Label, getLabelStyles } from './Label';\nimport { RadioButtonGroup } from './RadioButtonGroup/RadioButtonGroup';\n\ntype ChildProps = Record<string, unknown>;\n\nexport interface FieldProps extends HTMLAttributes<HTMLElement> {\n  /** Form input element, i.e Input or Switch */\n  children: React.ReactElement<ChildProps>;\n  /** Label for the field */\n  label?: React.ReactNode;\n  /** Description of the field */\n  description?: React.ReactNode;\n  /** Indicates if field is in invalid state */\n  invalid?: boolean;\n  /** Indicates if field is in loading state */\n  loading?: boolean;\n  /** Indicates if field is disabled */\n  disabled?: boolean;\n  /** Indicates if field is required */\n  required?: boolean;\n  /** Error message to display */\n  error?: React.ReactNode;\n  /** Indicates horizontal layout of the field */\n  horizontal?: boolean;\n  /** make validation message overflow horizontally. Prevents pushing out adjacent inline components */\n  validationMessageHorizontalOverflow?: boolean;\n  /** Whether to use a <fieldset> + <legend> for rendering the label. Only use for RadioButtonGroup */\n  useFieldset?: boolean;\n\n  className?: string;\n  /**\n   *  A unique id that associates the label of the Field component with the control with the unique id.\n   *  If the `htmlFor` property is missing the `htmlFor` will be inferred from the `id` or `inputId` property of the first child.\n   *  https://developer.mozilla.org/en-US/docs/Web/HTML/Element/label#attr-for\n   */\n  htmlFor?: string;\n  /** Remove the bottom margin */\n  noMargin?: boolean;\n}\n\n/**\n * Field is the basic component for rendering form elements together with labels and description.\n *\n * https://developers.grafana.com/ui/latest/index.html?path=/docs/forms-field--docs\n */\nexport const Field = React.forwardRef<HTMLDivElement, FieldProps>(\n  (\n    {\n      label: labelProp,\n      description,\n      horizontal,\n      invalid,\n      loading,\n      disabled,\n      required,\n      error,\n      children,\n      className,\n      validationMessageHorizontalOverflow,\n      htmlFor,\n      noMargin,\n      useFieldset: useFieldsetProp,\n      ...otherProps\n    }: FieldProps,\n    ref\n  ) => {\n    const styles = useStyles2(getFieldStyles, noMargin);\n    const labelStyles = useStyles2(getLabelStyles);\n    const useFieldset = useFieldsetProp ?? children.type === RadioButtonGroup;\n    const label = typeof labelProp === 'string' ? `${labelProp}${required ? ' *' : ''}` : labelProp;\n    const fieldId = useId();\n    const errorId = useId();\n    const inputId = htmlFor ?? getChildId(children) ?? fieldId;\n\n    let labelElement = label;\n\n    if (useFieldset) {\n      if (typeof label === 'string') {\n        labelElement = (\n          <legend className={labelStyles.label}>\n            <div className={labelStyles.labelContent}>{label}</div>\n            {description && <span className={labelStyles.description}>{description}</span>}\n          </legend>\n        );\n      } else {\n        labelElement = <legend className={labelStyles.label}>{label}</legend>;\n      }\n    } else if (typeof label === 'string') {\n      labelElement = (\n        <Label htmlFor={inputId} description={description}>\n          {label}\n        </Label>\n      );\n    }\n\n    // @deprecated — passing props via children is discouraged and will be removed at some point, use FieldContext instead\n    const childProps: ChildProps = deleteUndefinedProps({ invalid, disabled, loading });\n    if (invalid && error) {\n      // this should probably use aria-errormessage, but seems like voiceover still doesn't support that...\n      childProps['aria-describedby'] = errorId;\n    }\n    const Wrapper = useFieldset ? 'fieldset' : 'div';\n    return (\n      <FieldContext.Provider\n        value={{\n          id: inputId,\n          invalid,\n          disabled,\n          loading,\n          'aria-describedby': invalid && error ? errorId : undefined,\n        }}\n      >\n        <Wrapper className={cx(styles.field, horizontal && styles.fieldHorizontal, className)} {...otherProps}>\n          {labelElement}\n          <div>\n            <div ref={ref}>\n              {React.cloneElement(children, children.type !== React.Fragment ? childProps : undefined)}\n            </div>\n            {invalid && error && !horizontal && (\n              <div\n                className={cx(styles.fieldValidationWrapper, {\n                  [styles.validationMessageHorizontalOverflow]: !!validationMessageHorizontalOverflow,\n                })}\n              >\n                <FieldValidationMessage id={errorId}>{error}</FieldValidationMessage>\n              </div>\n            )}\n          </div>\n\n          {invalid && error && horizontal && (\n            <div\n              className={cx(styles.fieldValidationWrapper, styles.fieldValidationWrapperHorizontal, {\n                [styles.validationMessageHorizontalOverflow]: !!validationMessageHorizontalOverflow,\n              })}\n            >\n              <FieldValidationMessage id={errorId}>{error}</FieldValidationMessage>\n            </div>\n          )}\n        </Wrapper>\n      </FieldContext.Provider>\n    );\n  }\n);\n\nField.displayName = 'Field';\n\nfunction deleteUndefinedProps<T extends Object>(obj: T): Partial<T> {\n  for (const key in obj) {\n    if (obj[key] === undefined) {\n      delete obj[key];\n    }\n  }\n\n  return obj;\n}\n\nconst getFieldStyles = (theme: GrafanaTheme2, noMargin?: boolean) => ({\n  field: css({\n    display: 'flex',\n    flexDirection: 'column',\n    marginBottom: theme.spacing(noMargin ? 0 : 2),\n  }),\n  fieldHorizontal: css({\n    flexDirection: 'row',\n    justifyContent: 'space-between',\n    flexWrap: 'wrap',\n  }),\n  fieldValidationWrapper: css({\n    marginTop: theme.spacing(0.5),\n  }),\n  fieldValidationWrapperHorizontal: css({\n    flex: '1 1 100%',\n  }),\n  validationMessageHorizontalOverflow: css({\n    width: 0,\n    overflowX: 'visible',\n\n    '& > *': {\n      whiteSpace: 'nowrap',\n    },\n  }),\n});\n"],"names":["React","useStyles2","getLabelStyles","RadioButtonGroup","useId","getChildId","jsxs","jsx","Label","FieldContext","cx","FieldValidationMessage","css"],"mappings":"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"}