chore: add strict-boolean-expressions rule (#27852)
## Description Add `@typescript-eslint/strict-boolean-expressions` eslint rule for packages.
This commit is contained in:
parent
e32e51b2fe
commit
22e10c6fdb
|
|
@ -3,6 +3,12 @@
|
||||||
"$schema": "http://json.schemastore.org/eslintrc",
|
"$schema": "http://json.schemastore.org/eslintrc",
|
||||||
"root": true,
|
"root": true,
|
||||||
"parser": "@typescript-eslint/parser",
|
"parser": "@typescript-eslint/parser",
|
||||||
|
"ignorePatterns": [
|
||||||
|
"jest.config.js",
|
||||||
|
"jest.setup.ts",
|
||||||
|
"rollup.config.js",
|
||||||
|
".eslintrc.js"
|
||||||
|
],
|
||||||
"plugins": [
|
"plugins": [
|
||||||
"react",
|
"react",
|
||||||
"@typescript-eslint",
|
"@typescript-eslint",
|
||||||
|
|
@ -25,9 +31,11 @@
|
||||||
"sourceType": "module", // Allows for the use of imports
|
"sourceType": "module", // Allows for the use of imports
|
||||||
"ecmaFeatures": {
|
"ecmaFeatures": {
|
||||||
"jsx": true // Allows for the parsing of JSX
|
"jsx": true // Allows for the parsing of JSX
|
||||||
}
|
},
|
||||||
|
"project": "./tsconfig.json"
|
||||||
},
|
},
|
||||||
"rules": {
|
"rules": {
|
||||||
|
"@typescript-eslint/strict-boolean-expressions": "error",
|
||||||
"@typescript-eslint/no-explicit-any": "error",
|
"@typescript-eslint/no-explicit-any": "error",
|
||||||
"@typescript-eslint/no-unused-vars": "error",
|
"@typescript-eslint/no-unused-vars": "error",
|
||||||
"jest/no-focused-tests": "error",
|
"jest/no-focused-tests": "error",
|
||||||
|
|
|
||||||
|
|
@ -13,6 +13,7 @@ const baseNoRestrictedImports =
|
||||||
const eslintConfig = {
|
const eslintConfig = {
|
||||||
extends: ["./.eslintrc.base.json"],
|
extends: ["./.eslintrc.base.json"],
|
||||||
rules: {
|
rules: {
|
||||||
|
"@typescript-eslint/strict-boolean-expressions": "off",
|
||||||
"@typescript-eslint/no-explicit-any": "off",
|
"@typescript-eslint/no-explicit-any": "off",
|
||||||
"react/display-name": "off",
|
"react/display-name": "off",
|
||||||
"react/prop-types": "off",
|
"react/prop-types": "off",
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
{
|
{
|
||||||
"src/**/*.{js,ts,tsx}": ["npx eslint --fix"],
|
"src/**/*.{js,ts,tsx}": ["npx eslint --fix"],
|
||||||
"src/**/*.{js,ts,tsx,css,md,json}": ["npx prettier --write"],
|
"src/**/*.{js,ts,tsx,css,md,json}": ["npx prettier --write"],
|
||||||
"cypress/**/*.{js,ts}": ["npx eslint --fix"],
|
"cypress/**/*.{js,ts}": ["cd ./cypress && npx eslint -c .eslintrc.json --fix"],
|
||||||
"cypress/**/*.{js,ts,json}": ["npx prettier --write"],
|
"cypress/**/*.{js,ts,json}": ["npx prettier --write"],
|
||||||
"packages/**/*.{js,ts,tsx}": ["npx eslint --fix"],
|
"packages/**/*.{js,ts,tsx}": ["npx eslint --fix"],
|
||||||
"packages/**/*.{js,ts,tsx,css,mdx,json}": ["npx prettier --write"]
|
"packages/**/*.{js,ts,tsx,css,mdx,json}": ["npx prettier --write"]
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,11 @@
|
||||||
{
|
{
|
||||||
"extends": ["../.eslintrc.base.json"],
|
"extends": ["../.eslintrc.base.json"],
|
||||||
|
"ignorePatterns": ["locators", "fixtures"],
|
||||||
"env": {
|
"env": {
|
||||||
"cypress/globals": true
|
"cypress/globals": true
|
||||||
},
|
},
|
||||||
"rules": {
|
"rules": {
|
||||||
|
"@typescript-eslint/strict-boolean-expressions": "off",
|
||||||
"@typescript-eslint/no-array-constructor": "off",
|
"@typescript-eslint/no-array-constructor": "off",
|
||||||
"@typescript-eslint/no-namespace": "off",
|
"@typescript-eslint/no-namespace": "off",
|
||||||
"@typescript-eslint/no-unused-vars": "off",
|
"@typescript-eslint/no-unused-vars": "off",
|
||||||
|
|
|
||||||
|
|
@ -32,5 +32,5 @@
|
||||||
"noFallthroughCasesInSwitch": true,
|
"noFallthroughCasesInSwitch": true,
|
||||||
"types": ["cypress", "node", "cypress-tags", "cypress-real-events"]
|
"types": ["cypress", "node", "cypress-tags", "cypress-real-events"]
|
||||||
},
|
},
|
||||||
"include": ["/**/*.ts", "../packages/rts/src/version.js"]
|
"include": ["./", "../packages/rts/src/version.js"]
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -34,7 +34,7 @@
|
||||||
"generate:widget": "plop --plopfile generators/index.js",
|
"generate:widget": "plop --plopfile generators/index.js",
|
||||||
"postinstall": "node cypress/apply-patches.js && yarn init-husky",
|
"postinstall": "node cypress/apply-patches.js && yarn init-husky",
|
||||||
"storybook": "yarn workspace @design-system/storybook storybook",
|
"storybook": "yarn workspace @design-system/storybook storybook",
|
||||||
"lint": "eslint --cache --ext .js,.ts,.tsx ./src && eslint --cache --ext .js,.ts ./cypress",
|
"lint": "eslint --cache ./src && cd ./cypress && eslint -c .eslintrc.json --cache ./",
|
||||||
"g:lint": "cd $INIT_CWD && eslint --cache .",
|
"g:lint": "cd $INIT_CWD && eslint --cache .",
|
||||||
"lint:ci": "yarn workspaces foreach -ptv run lint",
|
"lint:ci": "yarn workspaces foreach -ptv run lint",
|
||||||
"prettier": "prettier --check ./src && prettier --check ./cypress",
|
"prettier": "prettier --check ./src && prettier --check ./cypress",
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@
|
||||||
"extends": ["../../.eslintrc.base.json"],
|
"extends": ["../../.eslintrc.base.json"],
|
||||||
"ignorePatterns": ["build"],
|
"ignorePatterns": ["build"],
|
||||||
"rules": {
|
"rules": {
|
||||||
|
"@typescript-eslint/strict-boolean-expressions": "off",
|
||||||
"@typescript-eslint/no-explicit-any": "off"
|
"@typescript-eslint/no-explicit-any": "off"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,13 @@ export type ButtonRef = React.Ref<HTMLButtonElement>;
|
||||||
type ButtonRefObject = React.RefObject<HTMLButtonElement>;
|
type ButtonRefObject = React.RefObject<HTMLButtonElement>;
|
||||||
|
|
||||||
const _Button = (props: ButtonProps, ref: ButtonRef) => {
|
const _Button = (props: ButtonProps, ref: ButtonRef) => {
|
||||||
const { autoFocus, children, className, draggable, isDisabled } = props;
|
const {
|
||||||
|
autoFocus,
|
||||||
|
children,
|
||||||
|
className,
|
||||||
|
draggable = false,
|
||||||
|
isDisabled = false,
|
||||||
|
} = props;
|
||||||
const { hoverProps, isHovered } = useHover({ isDisabled });
|
const { hoverProps, isHovered } = useHover({ isDisabled });
|
||||||
const { focusProps, isFocusVisible } = useFocusRing({ autoFocus });
|
const { focusProps, isFocusVisible } = useFocusRing({ autoFocus });
|
||||||
const { buttonProps, isPressed } = useButton(props, ref as ButtonRefObject);
|
const { buttonProps, isPressed } = useButton(props, ref as ButtonRefObject);
|
||||||
|
|
@ -28,8 +34,8 @@ const _Button = (props: ButtonProps, ref: ButtonRef) => {
|
||||||
return (
|
return (
|
||||||
<button
|
<button
|
||||||
{...mergeProps(buttonProps, hoverProps, focusProps)}
|
{...mergeProps(buttonProps, hoverProps, focusProps)}
|
||||||
aria-busy={props["aria-busy"] ? true : undefined}
|
aria-busy={props["aria-busy"] ?? undefined}
|
||||||
aria-disabled={props["aria-disabled"] ? true : undefined}
|
aria-disabled={props["aria-disabled"] ?? undefined}
|
||||||
className={className}
|
className={className}
|
||||||
data-active={isPressed ? "" : undefined}
|
data-active={isPressed ? "" : undefined}
|
||||||
data-disabled={isDisabled ? "" : undefined}
|
data-disabled={isDisabled ? "" : undefined}
|
||||||
|
|
|
||||||
|
|
@ -51,7 +51,7 @@ const _Checkbox = (props: CheckboxProps, ref: CheckboxRef) => {
|
||||||
const context = useContext(CheckboxGroupContext) as CheckboxGroupContextType;
|
const context = useContext(CheckboxGroupContext) as CheckboxGroupContextType;
|
||||||
const isDisabled = isDisabledProp || context?.isDisabled;
|
const isDisabled = isDisabledProp || context?.isDisabled;
|
||||||
const { hoverProps, isHovered } = useHover({ isDisabled });
|
const { hoverProps, isHovered } = useHover({ isDisabled });
|
||||||
const { inputProps } = context?.state
|
const { inputProps } = Boolean(context?.state)
|
||||||
? // eslint-disable-next-line react-hooks/rules-of-hooks
|
? // eslint-disable-next-line react-hooks/rules-of-hooks
|
||||||
useCheckboxGroupItem(
|
useCheckboxGroupItem(
|
||||||
{
|
{
|
||||||
|
|
@ -74,7 +74,7 @@ const _Checkbox = (props: CheckboxProps, ref: CheckboxRef) => {
|
||||||
|
|
||||||
const dataState = isIndeterminate
|
const dataState = isIndeterminate
|
||||||
? "indeterminate"
|
? "indeterminate"
|
||||||
: inputProps.checked
|
: Boolean(inputProps.checked)
|
||||||
? "checked"
|
? "checked"
|
||||||
: "unchecked";
|
: "unchecked";
|
||||||
|
|
||||||
|
|
@ -82,7 +82,7 @@ const _Checkbox = (props: CheckboxProps, ref: CheckboxRef) => {
|
||||||
<label
|
<label
|
||||||
{...hoverProps}
|
{...hoverProps}
|
||||||
className={className}
|
className={className}
|
||||||
data-disabled={isDisabled ? "" : undefined}
|
data-disabled={Boolean(isDisabled) ? "" : undefined}
|
||||||
data-focused={isFocusVisible ? "" : undefined}
|
data-focused={isFocusVisible ? "" : undefined}
|
||||||
data-hovered={isHovered ? "" : undefined}
|
data-hovered={isHovered ? "" : undefined}
|
||||||
data-invalid={validationState === "invalid" ? "" : undefined}
|
data-invalid={validationState === "invalid" ? "" : undefined}
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,12 @@ export interface CheckboxGroupProps
|
||||||
}
|
}
|
||||||
|
|
||||||
const _CheckboxGroup = (props: CheckboxGroupProps, ref: CheckboxGroupRef) => {
|
const _CheckboxGroup = (props: CheckboxGroupProps, ref: CheckboxGroupRef) => {
|
||||||
const { children, className, isDisabled, orientation = "vertical" } = props;
|
const {
|
||||||
|
children,
|
||||||
|
className,
|
||||||
|
isDisabled = false,
|
||||||
|
orientation = "vertical",
|
||||||
|
} = props;
|
||||||
const domRef = useDOMRef(ref);
|
const domRef = useDOMRef(ref);
|
||||||
const state = useCheckboxGroupState(props);
|
const state = useCheckboxGroupState(props);
|
||||||
const { descriptionProps, errorMessageProps, groupProps, labelProps } =
|
const { descriptionProps, errorMessageProps, groupProps, labelProps } =
|
||||||
|
|
@ -38,7 +43,7 @@ const _CheckboxGroup = (props: CheckboxGroupProps, ref: CheckboxGroupRef) => {
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
{...groupProps}
|
{...groupProps}
|
||||||
data-disabled={props.isDisabled ? "" : undefined}
|
data-disabled={isDisabled ? "" : undefined}
|
||||||
data-field-group=""
|
data-field-group=""
|
||||||
data-orientation={orientation}
|
data-orientation={orientation}
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ function _HelpText(props: HelpTextProps, ref: DOMRef<HTMLDivElement>) {
|
||||||
validationState,
|
validationState,
|
||||||
} = props;
|
} = props;
|
||||||
const domRef = useDOMRef(ref);
|
const domRef = useDOMRef(ref);
|
||||||
const isErrorMessage = errorMessage && validationState === "invalid";
|
const isErrorMessage = Boolean(errorMessage) && validationState === "invalid";
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div ref={domRef}>
|
<div ref={domRef}>
|
||||||
|
|
|
||||||
|
|
@ -27,7 +27,7 @@ const _Field = (props: FieldProps, ref: FieldRef) => {
|
||||||
elementType,
|
elementType,
|
||||||
errorMessage,
|
errorMessage,
|
||||||
errorMessageProps = {},
|
errorMessageProps = {},
|
||||||
isDisabled,
|
isDisabled = false,
|
||||||
label,
|
label,
|
||||||
labelProps,
|
labelProps,
|
||||||
validationState,
|
validationState,
|
||||||
|
|
@ -39,7 +39,8 @@ const _Field = (props: FieldProps, ref: FieldRef) => {
|
||||||
fieldType = "field",
|
fieldType = "field",
|
||||||
} = props;
|
} = props;
|
||||||
const hasHelpText =
|
const hasHelpText =
|
||||||
!!description || (errorMessage && validationState === "invalid");
|
Boolean(description) ||
|
||||||
|
(Boolean(errorMessage) && validationState === "invalid");
|
||||||
|
|
||||||
const renderHelpText = () => {
|
const renderHelpText = () => {
|
||||||
return (
|
return (
|
||||||
|
|
@ -56,12 +57,12 @@ const _Field = (props: FieldProps, ref: FieldRef) => {
|
||||||
|
|
||||||
const labelAndContextualHelp = (
|
const labelAndContextualHelp = (
|
||||||
<div data-field-label-wrapper="">
|
<div data-field-label-wrapper="">
|
||||||
{label && (
|
{Boolean(label) && (
|
||||||
<Label {...labelProps} elementType={elementType}>
|
<Label {...labelProps} elementType={elementType}>
|
||||||
{label}
|
{label}
|
||||||
</Label>
|
</Label>
|
||||||
)}
|
)}
|
||||||
{label && contextualHelp}
|
{Boolean(label) && contextualHelp}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ function _HelpText(props: HelpTextProps, ref: DOMRef<HTMLDivElement>) {
|
||||||
validationState,
|
validationState,
|
||||||
} = props;
|
} = props;
|
||||||
const domRef = useDOMRef(ref);
|
const domRef = useDOMRef(ref);
|
||||||
const isErrorMessage = errorMessage && validationState === "invalid";
|
const isErrorMessage = Boolean(errorMessage) && validationState === "invalid";
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div ref={domRef}>
|
<div ref={domRef}>
|
||||||
|
|
|
||||||
|
|
@ -30,7 +30,9 @@ const _Label = (props: LabelProps, ref: DOMRef<HTMLLabelElement>) => {
|
||||||
<ElementType
|
<ElementType
|
||||||
data-field-label=""
|
data-field-label=""
|
||||||
{...filterDOMProps(otherProps)}
|
{...filterDOMProps(otherProps)}
|
||||||
htmlFor={ElementType === "label" ? labelFor || htmlFor : undefined}
|
htmlFor={
|
||||||
|
ElementType === "label" ? Boolean(labelFor) || htmlFor : undefined
|
||||||
|
}
|
||||||
onClick={onClick}
|
onClick={onClick}
|
||||||
ref={domRef}
|
ref={domRef}
|
||||||
>
|
>
|
||||||
|
|
|
||||||
|
|
@ -21,13 +21,11 @@ export function Icon(props: IconProps) {
|
||||||
...otherProps
|
...otherProps
|
||||||
} = props;
|
} = props;
|
||||||
|
|
||||||
const ariaHidden = !ariaHiddenProp ? undefined : ariaHiddenProp;
|
|
||||||
|
|
||||||
return React.cloneElement(children, {
|
return React.cloneElement(children, {
|
||||||
...filterDOMProps(otherProps),
|
...filterDOMProps(otherProps),
|
||||||
focusable: "false",
|
focusable: "false",
|
||||||
"aria-label": ariaLabel,
|
"aria-label": ariaLabel,
|
||||||
"aria-hidden": ariaLabel ? ariaHidden || undefined : true,
|
"aria-hidden": Boolean(ariaLabel) ? ariaHiddenProp ?? undefined : true,
|
||||||
role,
|
role,
|
||||||
"data-icon": "",
|
"data-icon": "",
|
||||||
className,
|
className,
|
||||||
|
|
|
||||||
|
|
@ -50,7 +50,7 @@ const _Radio = (props: RadioProps, ref: RadioRef) => {
|
||||||
<label
|
<label
|
||||||
{...hoverProps}
|
{...hoverProps}
|
||||||
className={className}
|
className={className}
|
||||||
data-disabled={isDisabled ? "" : undefined}
|
data-disabled={Boolean(isDisabled) ? "" : undefined}
|
||||||
data-focused={isFocusVisible ? "" : undefined}
|
data-focused={isFocusVisible ? "" : undefined}
|
||||||
data-hovered={isHovered ? "" : undefined}
|
data-hovered={isHovered ? "" : undefined}
|
||||||
data-invalid={validationState === "invalid" ? "" : undefined}
|
data-invalid={validationState === "invalid" ? "" : undefined}
|
||||||
|
|
|
||||||
|
|
@ -44,7 +44,7 @@ const _Switch = (props: SwitchProps, ref: SwitchRef) => {
|
||||||
const context = useContext(CheckboxGroupContext) as CheckboxGroupContextType;
|
const context = useContext(CheckboxGroupContext) as CheckboxGroupContextType;
|
||||||
const isDisabled = isDisabledProp || context?.isDisabled;
|
const isDisabled = isDisabledProp || context?.isDisabled;
|
||||||
const { hoverProps, isHovered } = useHover({ isDisabled });
|
const { hoverProps, isHovered } = useHover({ isDisabled });
|
||||||
const { inputProps } = context?.state
|
const { inputProps } = Boolean(context?.state)
|
||||||
? // eslint-disable-next-line react-hooks/rules-of-hooks
|
? // eslint-disable-next-line react-hooks/rules-of-hooks
|
||||||
useCheckboxGroupItem(
|
useCheckboxGroupItem(
|
||||||
{
|
{
|
||||||
|
|
@ -65,13 +65,13 @@ const _Switch = (props: SwitchProps, ref: SwitchRef) => {
|
||||||
: // eslint-disable-next-line react-hooks/rules-of-hooks
|
: // eslint-disable-next-line react-hooks/rules-of-hooks
|
||||||
useSwitch(props, state, inputRef);
|
useSwitch(props, state, inputRef);
|
||||||
|
|
||||||
const dataState = inputProps.checked ? "checked" : "unchecked";
|
const dataState = Boolean(inputProps.checked) ? "checked" : "unchecked";
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<label
|
<label
|
||||||
{...hoverProps}
|
{...hoverProps}
|
||||||
className={className}
|
className={className}
|
||||||
data-disabled={isDisabled ? "" : undefined}
|
data-disabled={Boolean(isDisabled) ? "" : undefined}
|
||||||
data-focused={isFocusVisible ? "" : undefined}
|
data-focused={isFocusVisible ? "" : undefined}
|
||||||
data-hovered={isHovered ? "" : undefined}
|
data-hovered={isHovered ? "" : undefined}
|
||||||
data-invalid={validationState === "invalid" ? "" : undefined}
|
data-invalid={validationState === "invalid" ? "" : undefined}
|
||||||
|
|
|
||||||
|
|
@ -32,7 +32,7 @@ function TextArea(props: TextAreaProps, ref: TextAreaRef) {
|
||||||
const onHeightChange = useCallback(() => {
|
const onHeightChange = useCallback(() => {
|
||||||
// Quiet textareas always grow based on their text content.
|
// Quiet textareas always grow based on their text content.
|
||||||
// Standard textareas also grow by default, unless an explicit height is set.
|
// Standard textareas also grow by default, unless an explicit height is set.
|
||||||
if (!props.height && inputRef.current) {
|
if (props.height == null && inputRef.current) {
|
||||||
const input = inputRef.current;
|
const input = inputRef.current;
|
||||||
const prevAlignment = input.style.alignSelf;
|
const prevAlignment = input.style.alignSelf;
|
||||||
const prevOverflow = input.style.overflow;
|
const prevOverflow = input.style.overflow;
|
||||||
|
|
@ -60,7 +60,7 @@ function TextArea(props: TextAreaProps, ref: TextAreaRef) {
|
||||||
}
|
}
|
||||||
}, [onHeightChange, inputValue, inputRef.current]);
|
}, [onHeightChange, inputValue, inputRef.current]);
|
||||||
|
|
||||||
if (props.placeholder) {
|
if (props.placeholder != null) {
|
||||||
// eslint-disable-next-line no-console
|
// eslint-disable-next-line no-console
|
||||||
console.warn(
|
console.warn(
|
||||||
"Placeholders are deprecated due to accessibility issues. Please use help text instead. See the docs for details: https://react-spectrum.adobe.com/react-spectrum/TextArea.html#help-text",
|
"Placeholders are deprecated due to accessibility issues. Please use help text instead. See the docs for details: https://react-spectrum.adobe.com/react-spectrum/TextArea.html#help-text",
|
||||||
|
|
|
||||||
|
|
@ -1 +0,0 @@
|
||||||
export * from "./src";
|
|
||||||
|
|
@ -14,7 +14,7 @@ function TextInput(props: TextInputProps, ref: TextInputRef) {
|
||||||
const { descriptionProps, errorMessageProps, inputProps, labelProps } =
|
const { descriptionProps, errorMessageProps, inputProps, labelProps } =
|
||||||
useTextField(rest, inputRef);
|
useTextField(rest, inputRef);
|
||||||
|
|
||||||
if (props.placeholder) {
|
if (props.placeholder != null) {
|
||||||
// eslint-disable-next-line no-console
|
// eslint-disable-next-line no-console
|
||||||
console.warn(
|
console.warn(
|
||||||
"Placeholders are deprecated due to accessibility issues. Please use help text instead. See the docs for details: https://react-spectrum.adobe.com/react-spectrum/TextField.html#help-text",
|
"Placeholders are deprecated due to accessibility issues. Please use help text instead. See the docs for details: https://react-spectrum.adobe.com/react-spectrum/TextField.html#help-text",
|
||||||
|
|
|
||||||
|
|
@ -17,10 +17,10 @@ function TextInputBase(props: TextInputBaseProps, ref: Ref<HTMLDivElement>) {
|
||||||
inputClassName,
|
inputClassName,
|
||||||
inputProps,
|
inputProps,
|
||||||
inputRef: userInputRef,
|
inputRef: userInputRef,
|
||||||
isDisabled,
|
isDisabled = false,
|
||||||
isLoading,
|
isLoading = false,
|
||||||
labelProps,
|
labelProps,
|
||||||
multiLine,
|
multiLine = false,
|
||||||
onBlur,
|
onBlur,
|
||||||
onFocus,
|
onFocus,
|
||||||
startIcon,
|
startIcon,
|
||||||
|
|
@ -32,8 +32,10 @@ function TextInputBase(props: TextInputBaseProps, ref: Ref<HTMLDivElement>) {
|
||||||
const defaultInputRef = useRef<HTMLInputElement | HTMLTextAreaElement>(null);
|
const defaultInputRef = useRef<HTMLInputElement | HTMLTextAreaElement>(null);
|
||||||
const inputRef = userInputRef || defaultInputRef;
|
const inputRef = userInputRef || defaultInputRef;
|
||||||
|
|
||||||
const ElementType: React.ElementType = multiLine ? "textarea" : "input";
|
const ElementType: React.ElementType = Boolean(multiLine)
|
||||||
const isInvalid = validationState === "invalid" && !isDisabled;
|
? "textarea"
|
||||||
|
: "input";
|
||||||
|
const isInvalid = validationState === "invalid" && !Boolean(isDisabled);
|
||||||
|
|
||||||
const { focusProps, isFocusVisible } = useFocusRing({
|
const { focusProps, isFocusVisible } = useFocusRing({
|
||||||
isTextInput: true,
|
isTextInput: true,
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@ const _TooltipTrigger = (
|
||||||
"data-state": context.open ? "open" : "closed",
|
"data-state": context.open ? "open" : "closed",
|
||||||
// when the trigger is disabled, we want to make sure that the tooltip is
|
// when the trigger is disabled, we want to make sure that the tooltip is
|
||||||
// accessible with keyboard but visually disabled only
|
// accessible with keyboard but visually disabled only
|
||||||
visuallyDisabled: children.props.isDisabled ? true : undefined,
|
visuallyDisabled: Boolean(children.props.isDisabled) ? true : undefined,
|
||||||
}),
|
}),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -56,7 +56,7 @@ export function useTheme(props: UseThemeProps = {}) {
|
||||||
}, [colorMode]);
|
}, [colorMode]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (borderRadius) {
|
if (borderRadius != null) {
|
||||||
tokensAccessor.updateBorderRadius({
|
tokensAccessor.updateBorderRadius({
|
||||||
1: borderRadius,
|
1: borderRadius,
|
||||||
});
|
});
|
||||||
|
|
@ -71,7 +71,7 @@ export function useTheme(props: UseThemeProps = {}) {
|
||||||
}, [borderRadius]);
|
}, [borderRadius]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (seedColor) {
|
if (seedColor != null) {
|
||||||
let color;
|
let color;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
@ -107,7 +107,7 @@ export function useTheme(props: UseThemeProps = {}) {
|
||||||
}, [fontFamily]);
|
}, [fontFamily]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (rootUnitRatioProp) {
|
if (rootUnitRatioProp != null) {
|
||||||
setRootUnitRatio(rootUnitRatioProp);
|
setRootUnitRatio(rootUnitRatioProp);
|
||||||
}
|
}
|
||||||
}, [rootUnitRatioProp]);
|
}, [rootUnitRatioProp]);
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@ export const cssRule = (tokens: Theme) => {
|
||||||
let styles = "";
|
let styles = "";
|
||||||
|
|
||||||
Object.values(tokens).forEach((token) => {
|
Object.values(tokens).forEach((token) => {
|
||||||
if (!token) return;
|
if (token == null) return;
|
||||||
|
|
||||||
Object.keys(token).forEach((key) => {
|
Object.keys(token).forEach((key) => {
|
||||||
//@ts-expect-error: type mismatch
|
//@ts-expect-error: type mismatch
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
{
|
{
|
||||||
"extends": ["../../../.eslintrc.base.json"],
|
"extends": ["../../../.eslintrc.base.json"],
|
||||||
"rules": {
|
"rules": {
|
||||||
|
"@typescript-eslint/strict-boolean-expressions": "off",
|
||||||
"@typescript-eslint/no-explicit-any": "off",
|
"@typescript-eslint/no-explicit-any": "off",
|
||||||
"react/display-name": "off"
|
"react/display-name": "off"
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -20,12 +20,13 @@ const _Button = (props: ButtonProps, ref: HeadlessButtonRef) => {
|
||||||
color = "accent",
|
color = "accent",
|
||||||
icon: Icon,
|
icon: Icon,
|
||||||
iconPosition = "start",
|
iconPosition = "start",
|
||||||
isLoading,
|
isDisabled = false,
|
||||||
|
isLoading = false,
|
||||||
loadingText = "Loading...",
|
loadingText = "Loading...",
|
||||||
// eslint-disable-next-line -- TODO add onKeyUp when the bug is fixed https://github.com/adobe/react-spectrum/issues/4350
|
// eslint-disable-next-line -- TODO add onKeyUp when the bug is fixed https://github.com/adobe/react-spectrum/issues/4350
|
||||||
onKeyUp,
|
onKeyUp,
|
||||||
variant = "filled",
|
variant = "filled",
|
||||||
visuallyDisabled,
|
visuallyDisabled = false,
|
||||||
...rest
|
...rest
|
||||||
} = props;
|
} = props;
|
||||||
const { visuallyHiddenProps } = useVisuallyHidden();
|
const { visuallyHiddenProps } = useVisuallyHidden();
|
||||||
|
|
@ -39,7 +40,7 @@ const _Button = (props: ButtonProps, ref: HeadlessButtonRef) => {
|
||||||
<Icon />
|
<Icon />
|
||||||
</HeadlessIcon>
|
</HeadlessIcon>
|
||||||
)}
|
)}
|
||||||
{children && (
|
{Boolean(children) && (
|
||||||
<Text fontWeight={600} lineClamp={1} textAlign="center">
|
<Text fontWeight={600} lineClamp={1} textAlign="center">
|
||||||
{children}
|
{children}
|
||||||
</Text>
|
</Text>
|
||||||
|
|
@ -58,7 +59,7 @@ const _Button = (props: ButtonProps, ref: HeadlessButtonRef) => {
|
||||||
<HeadlessButton
|
<HeadlessButton
|
||||||
aria-busy={isLoading ? true : undefined}
|
aria-busy={isLoading ? true : undefined}
|
||||||
aria-disabled={
|
aria-disabled={
|
||||||
visuallyDisabled || isLoading || props.isDisabled ? true : undefined
|
visuallyDisabled || isLoading || isDisabled ? true : undefined
|
||||||
}
|
}
|
||||||
className={clsx(styles.button, getTypographyClassName("body"))}
|
className={clsx(styles.button, getTypographyClassName("body"))}
|
||||||
data-button=""
|
data-button=""
|
||||||
|
|
@ -67,6 +68,7 @@ const _Button = (props: ButtonProps, ref: HeadlessButtonRef) => {
|
||||||
data-loading={isLoading ? "" : undefined}
|
data-loading={isLoading ? "" : undefined}
|
||||||
data-variant={variant}
|
data-variant={variant}
|
||||||
draggable
|
draggable
|
||||||
|
isDisabled={isDisabled}
|
||||||
ref={ref}
|
ref={ref}
|
||||||
{...rest}
|
{...rest}
|
||||||
>
|
>
|
||||||
|
|
@ -83,9 +85,10 @@ export const Button = forwardRef(_Button);
|
||||||
* when the button is visually disabled
|
* when the button is visually disabled
|
||||||
*/
|
*/
|
||||||
const useVisuallyDisabled = (props: ButtonProps) => {
|
const useVisuallyDisabled = (props: ButtonProps) => {
|
||||||
|
const { isLoading = false, visuallyDisabled = false } = props;
|
||||||
let computedProps = props;
|
let computedProps = props;
|
||||||
|
|
||||||
if (props.visuallyDisabled || props.isLoading) {
|
if (visuallyDisabled || isLoading) {
|
||||||
computedProps = {
|
computedProps = {
|
||||||
...props,
|
...props,
|
||||||
isDisabled: false,
|
isDisabled: false,
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const _Checkbox = (props: CheckboxProps, ref: HeadlessCheckboxRef) => {
|
||||||
inlineLabelStyles["inline-label"],
|
inlineLabelStyles["inline-label"],
|
||||||
)}
|
)}
|
||||||
>
|
>
|
||||||
{children && <Text>{children}</Text>}
|
{Boolean(children) && <Text>{children}</Text>}
|
||||||
</HeadlessCheckbox>
|
</HeadlessCheckbox>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -18,10 +18,10 @@ const _CheckboxGroup = (
|
||||||
ref: HeadlessCheckboxGroupRef,
|
ref: HeadlessCheckboxGroupRef,
|
||||||
) => {
|
) => {
|
||||||
const { errorMessage, label, ...rest } = props;
|
const { errorMessage, label, ...rest } = props;
|
||||||
const wrappedErrorMessage = errorMessage && (
|
const wrappedErrorMessage = Boolean(errorMessage) && (
|
||||||
<Text variant="footnote">{errorMessage}</Text>
|
<Text variant="footnote">{errorMessage}</Text>
|
||||||
);
|
);
|
||||||
const wrappedLabel = label && <Text>{label}</Text>;
|
const wrappedLabel = Boolean(label) && <Text>{label}</Text>;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<HeadlessCheckboxGroup
|
<HeadlessCheckboxGroup
|
||||||
|
|
|
||||||
|
|
@ -141,5 +141,5 @@ const cssVarValue = (value: CssVarValues) => {
|
||||||
};
|
};
|
||||||
|
|
||||||
const hiddenValue = (value: FlexCssProps["isHidden"]) => {
|
const hiddenValue = (value: FlexCssProps["isHidden"]) => {
|
||||||
return value ? "none" : "flex";
|
return Boolean(value) ? "none" : "flex";
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,2 +0,0 @@
|
||||||
export { IconButton } from "./IconButton";
|
|
||||||
export type { IconButtonProps } from "./IconButton";
|
|
||||||
|
|
@ -23,7 +23,7 @@ const _Radio = (props: RadioProps, ref: HeadlessRadioRef) => {
|
||||||
ref={ref}
|
ref={ref}
|
||||||
{...rest}
|
{...rest}
|
||||||
>
|
>
|
||||||
{children && <Text>{children}</Text>}
|
{Boolean(children) && <Text>{children}</Text>}
|
||||||
</HeadlessRadio>
|
</HeadlessRadio>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -15,8 +15,10 @@ export interface RadioGroupProps extends HeadlessRadioGroupProps {
|
||||||
|
|
||||||
const _RadioGroup = (props: RadioGroupProps, ref: HeadlessRadioGroupRef) => {
|
const _RadioGroup = (props: RadioGroupProps, ref: HeadlessRadioGroupRef) => {
|
||||||
const { errorMessage, label, ...rest } = props;
|
const { errorMessage, label, ...rest } = props;
|
||||||
const wrappedErrorMessage = errorMessage && <Text>{errorMessage}</Text>;
|
const wrappedErrorMessage = Boolean(errorMessage) && (
|
||||||
const wrappedLabel = label && <Text>{label}</Text>;
|
<Text>{errorMessage}</Text>
|
||||||
|
);
|
||||||
|
const wrappedLabel = Boolean(label) && <Text>{label}</Text>;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<HeadlessRadioGroup
|
<HeadlessRadioGroup
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ const _Switch = (props: SwitchProps, ref: HeadlessSwitchRef) => {
|
||||||
ref={ref}
|
ref={ref}
|
||||||
{...rest}
|
{...rest}
|
||||||
>
|
>
|
||||||
{children && <Text>{children}</Text>}
|
{Boolean(children) && <Text>{children}</Text>}
|
||||||
</HeadlessSwitch>
|
</HeadlessSwitch>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ const _Text = (props: TextProps, ref: Ref<HTMLParagraphElement>) => {
|
||||||
|
|
||||||
const getFontWeight = (
|
const getFontWeight = (
|
||||||
fontWeight?: keyof typeof TYPOGRAPHY_FONT_WEIGHTS,
|
fontWeight?: keyof typeof TYPOGRAPHY_FONT_WEIGHTS,
|
||||||
isBold?: boolean,
|
isBold = false,
|
||||||
) => {
|
) => {
|
||||||
if (fontWeight) return fontWeight;
|
if (fontWeight) return fontWeight;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -34,7 +34,7 @@ const _TextArea = (props: TextAreaProps, ref: HeadlessTextAreaRef) => {
|
||||||
...rest
|
...rest
|
||||||
} = props;
|
} = props;
|
||||||
|
|
||||||
const wrappedLabel = label && (
|
const wrappedLabel = Boolean(label) && (
|
||||||
<Label
|
<Label
|
||||||
includeNecessityIndicatorInAccessibilityName={
|
includeNecessityIndicatorInAccessibilityName={
|
||||||
includeNecessityIndicatorInAccessibilityName
|
includeNecessityIndicatorInAccessibilityName
|
||||||
|
|
@ -45,10 +45,10 @@ const _TextArea = (props: TextAreaProps, ref: HeadlessTextAreaRef) => {
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
const wrappedDescription = description && (
|
const wrappedDescription = Boolean(description) && (
|
||||||
<Text variant="footnote">{description}</Text>
|
<Text variant="footnote">{description}</Text>
|
||||||
);
|
);
|
||||||
const wrappedErrorMessage = errorMessage && (
|
const wrappedErrorMessage = Boolean(errorMessage) && (
|
||||||
<Text variant="footnote">{errorMessage}</Text>
|
<Text variant="footnote">{errorMessage}</Text>
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,2 +0,0 @@
|
||||||
export { TextArea } from "./TextArea";
|
|
||||||
export type { TextAreaProps } from "./TextArea";
|
|
||||||
|
|
@ -8,7 +8,7 @@ export type LabelProps = TextInputProps;
|
||||||
const _Label = (props: LabelProps) => {
|
const _Label = (props: LabelProps) => {
|
||||||
const {
|
const {
|
||||||
includeNecessityIndicatorInAccessibilityName,
|
includeNecessityIndicatorInAccessibilityName,
|
||||||
isRequired,
|
isRequired = false,
|
||||||
label,
|
label,
|
||||||
necessityIndicator = "icon",
|
necessityIndicator = "icon",
|
||||||
} = props;
|
} = props;
|
||||||
|
|
@ -16,7 +16,9 @@ const _Label = (props: LabelProps) => {
|
||||||
const icon = (
|
const icon = (
|
||||||
<span
|
<span
|
||||||
aria-label={
|
aria-label={
|
||||||
includeNecessityIndicatorInAccessibilityName ? "(required)" : undefined
|
Boolean(includeNecessityIndicatorInAccessibilityName)
|
||||||
|
? "(required)"
|
||||||
|
: undefined
|
||||||
}
|
}
|
||||||
data-field-necessity-indicator-icon=""
|
data-field-necessity-indicator-icon=""
|
||||||
>
|
>
|
||||||
|
|
@ -36,7 +38,7 @@ const _Label = (props: LabelProps) => {
|
||||||
{necessityIndicator === "label" && (
|
{necessityIndicator === "label" && (
|
||||||
<span
|
<span
|
||||||
aria-hidden={
|
aria-hidden={
|
||||||
!includeNecessityIndicatorInAccessibilityName
|
includeNecessityIndicatorInAccessibilityName == null
|
||||||
? isRequired
|
? isRequired
|
||||||
: undefined
|
: undefined
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -38,6 +38,7 @@ const _TextInput = (props: TextInputProps, ref: HeadlessTextInputRef) => {
|
||||||
endIcon,
|
endIcon,
|
||||||
errorMessage,
|
errorMessage,
|
||||||
includeNecessityIndicatorInAccessibilityName,
|
includeNecessityIndicatorInAccessibilityName,
|
||||||
|
isLoading = false,
|
||||||
isRequired,
|
isRequired,
|
||||||
label,
|
label,
|
||||||
loaderPosition = "auto",
|
loaderPosition = "auto",
|
||||||
|
|
@ -48,7 +49,7 @@ const _TextInput = (props: TextInputProps, ref: HeadlessTextInputRef) => {
|
||||||
} = props;
|
} = props;
|
||||||
const [showPassword, togglePassword] = useState(false);
|
const [showPassword, togglePassword] = useState(false);
|
||||||
|
|
||||||
const wrappedLabel = label && (
|
const wrappedLabel = Boolean(label) && (
|
||||||
<Label
|
<Label
|
||||||
includeNecessityIndicatorInAccessibilityName={
|
includeNecessityIndicatorInAccessibilityName={
|
||||||
includeNecessityIndicatorInAccessibilityName
|
includeNecessityIndicatorInAccessibilityName
|
||||||
|
|
@ -59,15 +60,15 @@ const _TextInput = (props: TextInputProps, ref: HeadlessTextInputRef) => {
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
const contextualHelp = label && contextualHelpProp && (
|
const contextualHelp = Boolean(label) && Boolean(contextualHelpProp) && (
|
||||||
<ContextualHelp contextualHelp={contextualHelpProp} />
|
<ContextualHelp contextualHelp={contextualHelpProp} />
|
||||||
);
|
);
|
||||||
|
|
||||||
const wrappedDescription = description && (
|
const wrappedDescription = Boolean(description) && (
|
||||||
<Text variant="footnote">{description}</Text>
|
<Text variant="footnote">{description}</Text>
|
||||||
);
|
);
|
||||||
|
|
||||||
const wrappedErrorMessage = errorMessage && (
|
const wrappedErrorMessage = Boolean(errorMessage) && (
|
||||||
<Text variant="footnote">{errorMessage}</Text>
|
<Text variant="footnote">{errorMessage}</Text>
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
@ -77,9 +78,9 @@ const _TextInput = (props: TextInputProps, ref: HeadlessTextInputRef) => {
|
||||||
|
|
||||||
const renderStartIcon = () => {
|
const renderStartIcon = () => {
|
||||||
const showLoadingIndicator =
|
const showLoadingIndicator =
|
||||||
props.isLoading &&
|
isLoading &&
|
||||||
(loaderPosition === "start" ||
|
(loaderPosition === "start" ||
|
||||||
Boolean(startIcon && loaderPosition !== "end"));
|
(Boolean(startIcon) && loaderPosition !== "end"));
|
||||||
|
|
||||||
if (!showLoadingIndicator) return startIcon;
|
if (!showLoadingIndicator) return startIcon;
|
||||||
|
|
||||||
|
|
@ -101,9 +102,9 @@ const _TextInput = (props: TextInputProps, ref: HeadlessTextInputRef) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
const showLoadingIndicator =
|
const showLoadingIndicator =
|
||||||
props.isLoading &&
|
isLoading &&
|
||||||
(loaderPosition === "end" ||
|
(loaderPosition === "end" ||
|
||||||
Boolean(loaderPosition === "auto" && !startIcon));
|
Boolean(loaderPosition === "auto" && Boolean(startIcon)));
|
||||||
|
|
||||||
if (!showLoadingIndicator) return endIcon;
|
if (!showLoadingIndicator) return endIcon;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,7 @@ export type TooltipProps = {
|
||||||
export function Tooltip(props: TooltipProps) {
|
export function Tooltip(props: TooltipProps) {
|
||||||
const { children, tooltip, ...rest } = props;
|
const { children, tooltip, ...rest } = props;
|
||||||
|
|
||||||
if (!tooltip) return children;
|
if (tooltip == null) return children;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<TooltipRoot {...rest}>
|
<TooltipRoot {...rest}>
|
||||||
|
|
|
||||||
|
|
@ -174,10 +174,10 @@ export const ColorGrid = (props: any) => {
|
||||||
>
|
>
|
||||||
<button
|
<button
|
||||||
className={styles["color-grid"]}
|
className={styles["color-grid"]}
|
||||||
data-active={isActive ? "" : undefined}
|
data-active={Boolean(isActive) ? "" : undefined}
|
||||||
data-disabled={isDisabled ? "" : undefined}
|
data-disabled={Boolean(isDisabled) ? "" : undefined}
|
||||||
data-focused={isFocused ? "" : undefined}
|
data-focused={Boolean(isFocused) ? "" : undefined}
|
||||||
data-hovered={isHovered ? "" : undefined}
|
data-hovered={Boolean(isHovered) ? "" : undefined}
|
||||||
data-variant={variant}
|
data-variant={variant}
|
||||||
>
|
>
|
||||||
<Text lineClamp={2} textAlign="center" variant="footnote">
|
<Text lineClamp={2} textAlign="center" variant="footnote">
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,8 @@
|
||||||
{
|
{
|
||||||
"extends": ["../../.eslintrc.base.json"],
|
"extends": ["../../.eslintrc.base.json"],
|
||||||
"ignorePatterns": ["dist"],
|
"ignorePatterns": ["dist", "server.test.ts"],
|
||||||
"rules": {
|
"rules": {
|
||||||
|
"@typescript-eslint/strict-boolean-expressions": "off",
|
||||||
"@typescript-eslint/no-explicit-any": "off"
|
"@typescript-eslint/no-explicit-any": "off"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user