UNPKG

@yamada-ui/toggle

Version:

Yamada UI toggle component

1 lines 8.41 kB
{"version":3,"sources":["../src/toggle.tsx"],"sourcesContent":["import type {\n ComponentArgs,\n CSSUIObject,\n HTMLUIProps,\n ThemeProps,\n} from \"@yamada-ui/core\"\nimport type { ForwardedRef, ReactElement, RefAttributes } from \"react\"\nimport {\n forwardRef,\n omitThemeProps,\n ui,\n useComponentMultiStyle,\n} from \"@yamada-ui/core\"\nimport { Ripple, useRipple } from \"@yamada-ui/ripple\"\nimport { useControllableState } from \"@yamada-ui/use-controllable-state\"\nimport {\n cx,\n dataAttr,\n handlerAll,\n isArray,\n isUndefined,\n} from \"@yamada-ui/utils\"\nimport { useMemo } from \"react\"\nimport { useToggleGroup } from \"./toggle-group\"\n\ninterface ToggleOptions<Y extends number | string = string> {\n /**\n * If `true`, the toggle button is represented as active.\n *\n * @default false\n */\n active?: boolean\n /**\n *If `true`, the toggle button will be initially selected.\n *\n @default false\n\n @deprecated Use `defaultSelected` instead.\n */\n defaultIsSelected?: boolean\n /**\n *If `true`, the toggle button will be initially selected.\n *\n @default false\n */\n defaultSelected?: boolean\n /**\n * If `true`, the toggle button will be disabled.\n *\n * @default false\n */\n disabled?: boolean\n /**\n * If `true`, disable ripple effects when pressing a element.\n *\n * @default false\n */\n disableRipple?: boolean\n /**\n * If true, the toggle button is full rounded. Else, it'll be slightly round.\n *\n * @default false\n */\n fullRounded?: boolean\n /**\n * The icon to be used in the button.\n */\n icon?: ReactElement\n /**\n * If `true`, the toggle button is represented as active.\n *\n * @default false\n *\n * @deprecated Use `active` instead.\n */\n isActive?: boolean\n /**\n * If `true`, the toggle button will be disabled.\n *\n * @default false\n *\n * @deprecated Use `disabled` instead.\n */\n isDisabled?: boolean\n /**\n * If `true`, the toggle button will be readonly.\n *\n * @default false\n *\n * @deprecated Use `readOnly` instead.\n */\n isReadOnly?: boolean\n /**\n * If true, the toggle button is full rounded. Else, it'll be slightly round.\n *\n * @default false\n *\n * @deprecated Use `fullRounded` instead.\n */\n isRounded?: boolean\n /**\n * If `true`, the toggle button will be selected.\n *\n * @deprecated Use `selected` instead.\n */\n isSelected?: boolean\n /**\n * If `true`, the toggle button will be readonly.\n *\n * @default false\n */\n readOnly?: boolean\n /**\n * If `true`, the toggle button will be selected.\n */\n selected?: boolean\n /**\n * The value of the toggle button.\n */\n value?: Y\n /**\n * The callback invoked when selected state changes.\n */\n onChange?: (selected: boolean) => void\n}\n\nexport interface ToggleProps<Y extends number | string = string>\n extends Omit<HTMLUIProps<\"button\">, \"onChange\" | \"value\">,\n ThemeProps<\"Toggle\">,\n ToggleOptions<Y> {}\n\n/**\n * `Toggle` is a two-state button that can be either on or off.\n *\n * @see Docs https://yamada-ui.com/components/forms/toggle\n */\nexport const Toggle = forwardRef(\n <Y extends number | string = string>(\n props: ToggleProps<Y>,\n ref: ForwardedRef<HTMLButtonElement>,\n ) => {\n const {\n controlled: controlled,\n disabled: groupDisabled,\n readOnly: groupReadOnly,\n value: groupValue,\n onChange: onChangeGroup,\n ...group\n } = useToggleGroup() ?? {}\n const [styles, mergedProps] = useComponentMultiStyle(\"Toggle\", {\n ...group,\n isDisabled: groupDisabled,\n isReadOnly: groupReadOnly,\n ...props,\n })\n const {\n className,\n isActive,\n active = isActive,\n children,\n defaultIsSelected = false,\n defaultSelected = defaultIsSelected,\n isDisabled = groupDisabled,\n disabled = isDisabled,\n disableRipple,\n isRounded,\n fullRounded = isRounded,\n icon,\n isReadOnly = groupReadOnly,\n isSelected,\n readOnly = isReadOnly,\n selected: selectedProp = isSelected,\n value,\n onChange,\n ...rest\n } = omitThemeProps(mergedProps)\n const [selected, setSelected] = useControllableState({\n defaultValue: defaultSelected,\n value: selectedProp,\n onChange,\n })\n\n if (controlled && isUndefined(value)) {\n console.warn(`Toggle: value is required. Please set the value.`)\n }\n\n const multi = isArray(groupValue)\n const included = multi\n ? groupValue.includes(value ?? \"\")\n : value === groupValue\n const trulySelected = controlled ? included : selected\n const { onPointerDown, ...rippleProps } = useRipple({\n ...rest,\n disabled: disableRipple || disabled,\n })\n\n const onClick = () => {\n setSelected((prev) => !prev)\n onChangeGroup?.(value)\n }\n\n const css: CSSUIObject = useMemo(\n () => ({\n alignItems: \"center\",\n appearance: \"none\",\n display: \"inline-flex\",\n gap: \"fallback(2, 0.5rem)\",\n justifyContent: \"center\",\n outline: \"none\",\n overflow: \"hidden\",\n pointerEvents: readOnly ? \"none\" : \"auto\",\n position: \"relative\",\n userSelect: \"none\",\n verticalAlign: \"middle\",\n ...styles,\n ...(fullRounded ? { borderRadius: \"fallback(full, 9999px)\" } : {}),\n }),\n [fullRounded, styles, readOnly],\n )\n\n return (\n <ui.button\n ref={ref}\n type=\"button\"\n className={cx(\"ui-toggle\", className)}\n aria-pressed={trulySelected}\n data-active={dataAttr(active)}\n data-readonly={dataAttr(readOnly)}\n data-selected={dataAttr(trulySelected)}\n disabled={disabled}\n tabIndex={readOnly ? -1 : 0}\n __css={css}\n {...rest}\n onClick={handlerAll(rest.onClick, onClick)}\n onPointerDown={onPointerDown}\n >\n {children || icon}\n\n <Ripple {...rippleProps} />\n </ui.button>\n )\n },\n) as {\n <Y extends number | string = string>(\n props: RefAttributes<HTMLButtonElement> & ToggleProps<Y>,\n ): ReactElement\n} & ComponentArgs\n\nToggle.displayName = \"Toggle\"\nToggle.__ui__ = \"Toggle\"\n"],"mappings":";;;;;;AAOA;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AACP,SAAS,QAAQ,iBAAiB;AAClC,SAAS,4BAA4B;AACrC;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AACP,SAAS,eAAe;AAuMlB,SAiBE,KAjBF;AArFC,IAAM,SAAS;AAAA,EACpB,CACE,OACA,QACG;AA5IP;AA6II,UAAM;AAAA,MACJ;AAAA,MACA,UAAU;AAAA,MACV,UAAU;AAAA,MACV,OAAO;AAAA,MACP,UAAU;AAAA,MACV,GAAG;AAAA,IACL,KAAI,oBAAe,MAAf,YAAoB,CAAC;AACzB,UAAM,CAAC,QAAQ,WAAW,IAAI,uBAAuB,UAAU;AAAA,MAC7D,GAAG;AAAA,MACH,YAAY;AAAA,MACZ,YAAY;AAAA,MACZ,GAAG;AAAA,IACL,CAAC;AACD,UAAM;AAAA,MACJ;AAAA,MACA;AAAA,MACA,SAAS;AAAA,MACT;AAAA,MACA,oBAAoB;AAAA,MACpB,kBAAkB;AAAA,MAClB,aAAa;AAAA,MACb,WAAW;AAAA,MACX;AAAA,MACA;AAAA,MACA,cAAc;AAAA,MACd;AAAA,MACA,aAAa;AAAA,MACb;AAAA,MACA,WAAW;AAAA,MACX,UAAU,eAAe;AAAA,MACzB;AAAA,MACA;AAAA,MACA,GAAG;AAAA,IACL,IAAI,eAAe,WAAW;AAC9B,UAAM,CAAC,UAAU,WAAW,IAAI,qBAAqB;AAAA,MACnD,cAAc;AAAA,MACd,OAAO;AAAA,MACP;AAAA,IACF,CAAC;AAED,QAAI,cAAc,YAAY,KAAK,GAAG;AACpC,cAAQ,KAAK,kDAAkD;AAAA,IACjE;AAEA,UAAM,QAAQ,QAAQ,UAAU;AAChC,UAAM,WAAW,QACb,WAAW,SAAS,wBAAS,EAAE,IAC/B,UAAU;AACd,UAAM,gBAAgB,aAAa,WAAW;AAC9C,UAAM,EAAE,eAAe,GAAG,YAAY,IAAI,UAAU;AAAA,MAClD,GAAG;AAAA,MACH,UAAU,iBAAiB;AAAA,IAC7B,CAAC;AAED,UAAM,UAAU,MAAM;AACpB,kBAAY,CAAC,SAAS,CAAC,IAAI;AAC3B,qDAAgB;AAAA,IAClB;AAEA,UAAM,MAAmB;AAAA,MACvB,OAAO;AAAA,QACL,YAAY;AAAA,QACZ,YAAY;AAAA,QACZ,SAAS;AAAA,QACT,KAAK;AAAA,QACL,gBAAgB;AAAA,QAChB,SAAS;AAAA,QACT,UAAU;AAAA,QACV,eAAe,WAAW,SAAS;AAAA,QACnC,UAAU;AAAA,QACV,YAAY;AAAA,QACZ,eAAe;AAAA,QACf,GAAG;AAAA,QACH,GAAI,cAAc,EAAE,cAAc,yBAAyB,IAAI,CAAC;AAAA,MAClE;AAAA,MACA,CAAC,aAAa,QAAQ,QAAQ;AAAA,IAChC;AAEA,WACE;AAAA,MAAC,GAAG;AAAA,MAAH;AAAA,QACC;AAAA,QACA,MAAK;AAAA,QACL,WAAW,GAAG,aAAa,SAAS;AAAA,QACpC,gBAAc;AAAA,QACd,eAAa,SAAS,MAAM;AAAA,QAC5B,iBAAe,SAAS,QAAQ;AAAA,QAChC,iBAAe,SAAS,aAAa;AAAA,QACrC;AAAA,QACA,UAAU,WAAW,KAAK;AAAA,QAC1B,OAAO;AAAA,QACN,GAAG;AAAA,QACJ,SAAS,WAAW,KAAK,SAAS,OAAO;AAAA,QACzC;AAAA,QAEC;AAAA,sBAAY;AAAA,UAEb,oBAAC,UAAQ,GAAG,aAAa;AAAA;AAAA;AAAA,IAC3B;AAAA,EAEJ;AACF;AAMA,OAAO,cAAc;AACrB,OAAO,SAAS;","names":[]}