@primer/react
Version:
An implementation of GitHub's Primer Design System using React
551 lines (545 loc) • 16.3 kB
JavaScript
'use strict';
var reactCompilerRuntime = require('react-compiler-runtime');
var React = require('react');
var styled = require('styled-components');
var styledSystem = require('styled-system');
var constants = require('../constants.js');
var sx = require('../sx.js');
var getGlobalFocusStyles = require('../internal/utils/getGlobalFocusStyles.js');
var _VisuallyHidden = require('../_VisuallyHidden.js');
var useSafeTimeout = require('../hooks/useSafeTimeout.js');
var jsxRuntime = require('react/jsx-runtime');
var useProvidedStateOrCreate = require('../hooks/useProvidedStateOrCreate.js');
var useId = require('../hooks/useId.js');
var Box = require('../Box/Box.js');
var AriaStatus = require('../live-region/AriaStatus.js');
var Spinner = require('../Spinner/Spinner.js');
var Text = require('../Text/Text.js');
function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
var React__default = /*#__PURE__*/_interopDefault(React);
var styled__default = /*#__PURE__*/_interopDefault(styled);
const TRANSITION_DURATION = '80ms';
const EASE_OUT_QUAD_CURVE = 'cubic-bezier(0.5, 1, 0.89, 1)';
const sizeVariants = styledSystem.variant({
prop: 'size',
variants: {
small: {
height: '24px',
width: '48px'
}
}
});
const CircleIcon = t0 => {
const $ = reactCompilerRuntime.c(4);
const {
size
} = t0;
const t1 = size === "small" ? "12" : "16";
const t2 = size === "small" ? "12" : "16";
let t3;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t3 = /*#__PURE__*/jsxRuntime.jsx("path", {
fillRule: "evenodd",
d: "M8 12.5a4.5 4.5 0 1 0 0-9 4.5 4.5 0 0 0 0 9ZM8 14A6 6 0 1 0 8 2a6 6 0 0 0 0 12Z"
});
$[0] = t3;
} else {
t3 = $[0];
}
let t4;
if ($[1] !== t1 || $[2] !== t2) {
t4 = /*#__PURE__*/jsxRuntime.jsx("svg", {
"aria-hidden": "true",
width: t1,
height: t2,
viewBox: "0 0 16 16",
fill: "currentColor",
xmlns: "http://www.w3.org/2000/svg",
children: t3
});
$[1] = t1;
$[2] = t2;
$[3] = t4;
} else {
t4 = $[3];
}
return t4;
};
const LineIcon = t0 => {
const $ = reactCompilerRuntime.c(4);
const {
size
} = t0;
const t1 = size === "small" ? "12" : "16";
const t2 = size === "small" ? "12" : "16";
let t3;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t3 = /*#__PURE__*/jsxRuntime.jsx("path", {
fillRule: "evenodd",
d: "M8 2a.75.75 0 0 1 .75.75v11.5a.75.75 0 0 1-1.5 0V2.75A.75.75 0 0 1 8 2Z"
});
$[0] = t3;
} else {
t3 = $[0];
}
let t4;
if ($[1] !== t1 || $[2] !== t2) {
t4 = /*#__PURE__*/jsxRuntime.jsx("svg", {
"aria-hidden": "true",
width: t1,
height: t2,
viewBox: "0 0 16 16",
fill: "currentColor",
xmlns: "http://www.w3.org/2000/svg",
children: t3
});
$[1] = t1;
$[2] = t2;
$[3] = t4;
} else {
t4 = $[3];
}
return t4;
};
const SwitchButton = styled__default.default.button.withConfig({
displayName: "ToggleSwitch__SwitchButton",
componentId: "sc-e6gszy-0"
})(["vertical-align:middle;cursor:pointer;user-select:none;appearance:none;text-decoration:none;padding:0;transition-property:background-color,border-color;transition-duration:", ";transition-timing-function:", ";border-radius:", ";border-style:solid;border-width:1px;display:block;height:32px;width:64px;position:relative;overflow:hidden;", ";@media (pointer:coarse){&:before{content:'';position:absolute;left:0;right:0;transform:translateY(-50%);top:50%;min-height:44px;}}@media (prefers-reduced-motion){transition:none;*{transition:none;}}&:hover:not(:disabled):not([aria-disabled='true']),&:focus:focus-visible{background-color:", ";}&:active,&:active:focus-visible{background-color:", ";}", " ", " ", ""], TRANSITION_DURATION, EASE_OUT_QUAD_CURVE, constants.get('radii.2'), getGlobalFocusStyles('3px'), constants.get('colors.switchTrack.hoverBg'), constants.get('colors.switchTrack.activeBg'), props => {
if (props['aria-disabled']) {
return styled.css(["@media (forced-colors:active){border-color:GrayText;}background-color:", ";border-color:transparent;cursor:not-allowed;transition-property:none;"], constants.get('colors.switchTrack.disabledBg'));
}
if (props.checked) {
return styled.css(["background-color:", ";border-color:var(--control-checked-borderColor-rest,transparent);&:hover:not(:disabled):not([aria-disabled='true']),&:focus:focus-visible{background-color:", ";}&:active,&:active:focus-visible{background-color:", ";}"], constants.get('colors.switchTrack.checked.bg'), constants.get('colors.switchTrack.checked.hoverBg'), constants.get('colors.switchTrack.checked.activeBg'));
} else {
return styled.css(["background-color:", ";border-color:var(--controlTrack-borderColor-rest,transparent);&:active{background-color:", ";}"], constants.get('colors.switchTrack.bg'), constants.get('colors.switchTrack.activeBg'));
}
}, sx.default, sizeVariants);
const ToggleKnob = styled__default.default.div.withConfig({
displayName: "ToggleSwitch__ToggleKnob",
componentId: "sc-e6gszy-1"
})(["background-color:", ";border-width:1px;border-style:solid;border-color:", ";border-radius:calc(", " - 1px);width:50%;position:absolute;top:0;bottom:0;transition-property:transform;transition-duration:", ";transition-timing-function:", ";transform:", ";z-index:1;@media (prefers-reduced-motion){transition:none;}", ""], constants.get('colors.switchKnob.bg'), props => props['aria-disabled'] ? constants.get('colors.switchTrack.disabledBg') : constants.get('colors.switchKnob.border'), constants.get('radii.2'), TRANSITION_DURATION, EASE_OUT_QUAD_CURVE, props => `translateX(${props.checked ? '100%' : '0px'})`, props => {
if (props['aria-disabled']) {
return styled.css(["@media (forced-colors:active){color:GrayText;}border-color:", ";"], constants.get('colors.switchTrack.disabledBg'));
}
if (props.checked) {
return styled.css(["border-color:", ";"], constants.get('colors.switchKnob.checked.border'));
}
});
const hiddenTextStyles = {
visibility: 'hidden',
height: 0
};
const ToggleSwitch = /*#__PURE__*/React__default.default.forwardRef(function ToggleSwitch(props, ref) {
const $ = reactCompilerRuntime.c(94);
let ariaDescribedby;
let ariaLabelledby;
let checked;
let defaultChecked;
let disabled;
let loading;
let onChange;
let onClick;
let rest;
let sxProp;
let t0;
let t1;
let t2;
let t3;
let t4;
if ($[0] !== props) {
({
"aria-labelledby": ariaLabelledby,
"aria-describedby": ariaDescribedby,
defaultChecked,
disabled,
loading,
checked,
onChange,
onClick,
buttonType: t0,
size: t1,
statusLabelPosition: t2,
loadingLabelDelay: t3,
loadingLabel: t4,
sx: sxProp,
...rest
} = props);
$[0] = props;
$[1] = ariaDescribedby;
$[2] = ariaLabelledby;
$[3] = checked;
$[4] = defaultChecked;
$[5] = disabled;
$[6] = loading;
$[7] = onChange;
$[8] = onClick;
$[9] = rest;
$[10] = sxProp;
$[11] = t0;
$[12] = t1;
$[13] = t2;
$[14] = t3;
$[15] = t4;
} else {
ariaDescribedby = $[1];
ariaLabelledby = $[2];
checked = $[3];
defaultChecked = $[4];
disabled = $[5];
loading = $[6];
onChange = $[7];
onClick = $[8];
rest = $[9];
sxProp = $[10];
t0 = $[11];
t1 = $[12];
t2 = $[13];
t3 = $[14];
t4 = $[15];
}
const buttonType = t0 === undefined ? "button" : t0;
const size = t1 === undefined ? "medium" : t1;
const statusLabelPosition = t2 === undefined ? "start" : t2;
const loadingLabelDelay = t3 === undefined ? 2000 : t3;
const loadingLabel = t4 === undefined ? "Loading" : t4;
const isControlled = typeof checked !== "undefined";
const [isOn, setIsOn] = useProvidedStateOrCreate.useProvidedStateOrCreate(checked, onChange, Boolean(defaultChecked));
const acceptsInteraction = !disabled && !loading;
const [isLoadingLabelVisible, setIsLoadingLabelVisible] = React__default.default.useState(false);
const loadingLabelId = useId.useId("loadingLabel");
const {
safeSetTimeout
} = useSafeTimeout();
let t5;
if ($[16] !== disabled || $[17] !== isControlled || $[18] !== isOn || $[19] !== loading || $[20] !== onClick || $[21] !== setIsOn) {
t5 = e => {
if (disabled || loading) {
return;
}
if (!isControlled) {
setIsOn(!isOn);
}
onClick && onClick(e);
};
$[16] = disabled;
$[17] = isControlled;
$[18] = isOn;
$[19] = loading;
$[20] = onClick;
$[21] = setIsOn;
$[22] = t5;
} else {
t5 = $[22];
}
const handleToggleClick = t5;
let t6;
let t7;
if ($[23] !== checked || $[24] !== disabled || $[25] !== isControlled || $[26] !== onChange) {
t6 = () => {
if (onChange && isControlled && !disabled) {
onChange(Boolean(checked));
}
};
t7 = [onChange, checked, isControlled, disabled];
$[23] = checked;
$[24] = disabled;
$[25] = isControlled;
$[26] = onChange;
$[27] = t6;
$[28] = t7;
} else {
t6 = $[27];
t7 = $[28];
}
React.useEffect(t6, t7);
let t8;
let t9;
if ($[29] !== isLoadingLabelVisible || $[30] !== loading || $[31] !== loadingLabelDelay || $[32] !== safeSetTimeout) {
t8 = () => {
if (!loading && isLoadingLabelVisible) {
setIsLoadingLabelVisible(false);
} else {
if (loading && !isLoadingLabelVisible) {
safeSetTimeout(() => {
setIsLoadingLabelVisible(true);
}, loadingLabelDelay);
}
}
};
t9 = [loading, isLoadingLabelVisible, loadingLabelDelay, safeSetTimeout];
$[29] = isLoadingLabelVisible;
$[30] = loading;
$[31] = loadingLabelDelay;
$[32] = safeSetTimeout;
$[33] = t8;
$[34] = t9;
} else {
t8 = $[33];
t9 = $[34];
}
React.useEffect(t8, t9);
let switchButtonDescribedBy = loadingLabelId;
if (ariaDescribedby) {
switchButtonDescribedBy = `${switchButtonDescribedBy} ${ariaDescribedby}`;
}
const t10 = statusLabelPosition === "start" ? "row" : "row-reverse";
const t11 = isLoadingLabelVisible && loadingLabel;
let t12;
if ($[35] !== loadingLabelId || $[36] !== t11) {
t12 = /*#__PURE__*/jsxRuntime.jsx(_VisuallyHidden, {
children: /*#__PURE__*/jsxRuntime.jsx(AriaStatus.AriaStatus, {
announceOnShow: true,
id: loadingLabelId,
children: t11
})
});
$[35] = loadingLabelId;
$[36] = t11;
$[37] = t12;
} else {
t12 = $[37];
}
let t13;
if ($[38] !== loading) {
t13 = loading ? /*#__PURE__*/jsxRuntime.jsx(Spinner, {
size: "small",
srText: null
}) : null;
$[38] = loading;
$[39] = t13;
} else {
t13 = $[39];
}
const t14 = acceptsInteraction ? "fg.default" : "fg.muted";
const t15 = size === "small" ? 0 : 1;
const t16 = acceptsInteraction ? "pointer" : "not-allowed";
let t17;
if ($[40] !== t16) {
t17 = {
position: "relative",
cursor: t16
};
$[40] = t16;
$[41] = t17;
} else {
t17 = $[41];
}
const t18 = isOn ? null : hiddenTextStyles;
let t19;
if ($[42] !== t18) {
t19 = /*#__PURE__*/jsxRuntime.jsx(Box, {
textAlign: "right",
sx: t18,
children: "On"
});
$[42] = t18;
$[43] = t19;
} else {
t19 = $[43];
}
const t20 = isOn ? hiddenTextStyles : null;
let t21;
if ($[44] !== t20) {
t21 = /*#__PURE__*/jsxRuntime.jsx(Box, {
textAlign: "right",
sx: t20,
children: "Off"
});
$[44] = t20;
$[45] = t21;
} else {
t21 = $[45];
}
let t22;
if ($[46] !== handleToggleClick || $[47] !== t14 || $[48] !== t15 || $[49] !== t17 || $[50] !== t19 || $[51] !== t21) {
t22 = /*#__PURE__*/jsxRuntime.jsxs(Text, {
color: t14,
fontSize: t15,
mx: 2,
"aria-hidden": "true",
sx: t17,
onClick: handleToggleClick,
children: [t19, t21]
});
$[46] = handleToggleClick;
$[47] = t14;
$[48] = t15;
$[49] = t17;
$[50] = t19;
$[51] = t21;
$[52] = t22;
} else {
t22 = $[52];
}
const t23 = isLoadingLabelVisible || ariaDescribedby ? switchButtonDescribedBy : undefined;
const t24 = !acceptsInteraction;
const t25 = acceptsInteraction ? "switchTrack.checked.fg" : "switchTrack.checked.disabledFg";
const t26 = `translateX(${isOn ? "0" : "-100%"})`;
let t27;
if ($[53] !== t26) {
t27 = {
transform: t26,
transitionProperty: "transform",
transitionDuration: TRANSITION_DURATION
};
$[53] = t26;
$[54] = t27;
} else {
t27 = $[54];
}
let t28;
if ($[55] !== size) {
t28 = /*#__PURE__*/jsxRuntime.jsx(LineIcon, {
size: size
});
$[55] = size;
$[56] = t28;
} else {
t28 = $[56];
}
let t29;
if ($[57] !== t25 || $[58] !== t27 || $[59] !== t28) {
t29 = /*#__PURE__*/jsxRuntime.jsx(Box, {
flexGrow: 1,
flexShrink: 0,
flexBasis: "50%",
color: t25,
lineHeight: "0",
sx: t27,
children: t28
});
$[57] = t25;
$[58] = t27;
$[59] = t28;
$[60] = t29;
} else {
t29 = $[60];
}
const t30 = acceptsInteraction ? "switchTrack.fg" : "switchTrack.disabledFg";
const t31 = `translateX(${isOn ? "100%" : "0"})`;
let t32;
if ($[61] !== t31) {
t32 = {
transform: t31,
transitionProperty: "transform",
transitionDuration: TRANSITION_DURATION
};
$[61] = t31;
$[62] = t32;
} else {
t32 = $[62];
}
let t33;
if ($[63] !== size) {
t33 = /*#__PURE__*/jsxRuntime.jsx(CircleIcon, {
size: size
});
$[63] = size;
$[64] = t33;
} else {
t33 = $[64];
}
let t34;
if ($[65] !== t30 || $[66] !== t32 || $[67] !== t33) {
t34 = /*#__PURE__*/jsxRuntime.jsx(Box, {
flexGrow: 1,
flexShrink: 0,
flexBasis: "50%",
color: t30,
lineHeight: "0",
sx: t32,
children: t33
});
$[65] = t30;
$[66] = t32;
$[67] = t33;
$[68] = t34;
} else {
t34 = $[68];
}
let t35;
if ($[69] !== t29 || $[70] !== t34) {
t35 = /*#__PURE__*/jsxRuntime.jsxs(Box, {
"aria-hidden": "true",
display: "flex",
alignItems: "center",
width: "100%",
height: "100%",
overflow: "hidden",
children: [t29, t34]
});
$[69] = t29;
$[70] = t34;
$[71] = t35;
} else {
t35 = $[71];
}
const t36 = !acceptsInteraction;
let t37;
if ($[72] !== isOn || $[73] !== t36) {
t37 = /*#__PURE__*/jsxRuntime.jsx(ToggleKnob, {
"aria-hidden": "true",
"aria-disabled": t36,
checked: isOn
});
$[72] = isOn;
$[73] = t36;
$[74] = t37;
} else {
t37 = $[74];
}
let t38;
if ($[75] !== ariaLabelledby || $[76] !== buttonType || $[77] !== handleToggleClick || $[78] !== isOn || $[79] !== ref || $[80] !== size || $[81] !== t23 || $[82] !== t24 || $[83] !== t35 || $[84] !== t37) {
t38 = /*#__PURE__*/jsxRuntime.jsxs(SwitchButton, {
ref: ref,
type: buttonType,
onClick: handleToggleClick,
"aria-labelledby": ariaLabelledby,
"aria-describedby": t23,
"aria-pressed": isOn,
checked: isOn,
size: size,
"aria-disabled": t24,
children: [t35, t37]
});
$[75] = ariaLabelledby;
$[76] = buttonType;
$[77] = handleToggleClick;
$[78] = isOn;
$[79] = ref;
$[80] = size;
$[81] = t23;
$[82] = t24;
$[83] = t35;
$[84] = t37;
$[85] = t38;
} else {
t38 = $[85];
}
let t39;
if ($[86] !== rest || $[87] !== sxProp || $[88] !== t10 || $[89] !== t12 || $[90] !== t13 || $[91] !== t22 || $[92] !== t38) {
t39 = /*#__PURE__*/jsxRuntime.jsxs(Box, {
display: "inline-flex",
alignItems: "center",
flexDirection: t10,
sx: sxProp,
...rest,
children: [t12, t13, t22, t38]
});
$[86] = rest;
$[87] = sxProp;
$[88] = t10;
$[89] = t12;
$[90] = t13;
$[91] = t22;
$[92] = t38;
$[93] = t39;
} else {
t39 = $[93];
}
return t39;
});
if (process.env.NODE_ENV !== "production") {
ToggleSwitch.displayName = 'ToggleSwitch';
}
module.exports = ToggleSwitch;