@mskcc/carbon-react
Version:
Carbon react components for the MSKCC DSM
269 lines (259 loc) • 8.51 kB
JavaScript
/**
* MSKCC 2021, 2024
*/
'use strict';
Object.defineProperty(exports, '__esModule', { value: true });
var _rollupPluginBabelHelpers = require('../../_virtual/_rollupPluginBabelHelpers.js');
var cx = require('classnames');
var PropTypes = require('prop-types');
var React = require('react');
var index = require('../Popover/index.js');
var useEvent = require('../../internal/useEvent.js');
var useId = require('../../internal/useId.js');
var usePrefix = require('../../internal/usePrefix.js');
var match = require('../../internal/keyboard/match.js');
var keys = require('../../internal/keyboard/keys.js');
function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; }
var cx__default = /*#__PURE__*/_interopDefaultLegacy(cx);
var PropTypes__default = /*#__PURE__*/_interopDefaultLegacy(PropTypes);
var React__default = /*#__PURE__*/_interopDefaultLegacy(React);
/**
* Used to render the label for a Toggletip
*/
function ToggletipLabel(_ref) {
let {
as: BaseComponent = 'span',
children,
className: customClassName
} = _ref;
const prefix = usePrefix.usePrefix();
const className = cx__default["default"](`${prefix}--toggletip-label`, customClassName);
const BaseComponentAsAny = BaseComponent;
return /*#__PURE__*/React__default["default"].createElement(BaseComponentAsAny, {
className: className
}, children);
}
ToggletipLabel.propTypes = {
/**
* Provide a custom element or component to render the top-level node for the
* component.
*/
as: PropTypes__default["default"].elementType,
/**
* Custom children to be rendered as the content of the label
*/
children: PropTypes__default["default"].node,
/**
* Provide a custom class name to be added to the outermost node in the
* component
*/
className: PropTypes__default["default"].string
};
// Used to coordinate accessibility props between button and content along with
// the actions to open and close the toggletip
const ToggletipContext = /*#__PURE__*/React__default["default"].createContext(undefined);
function useToggletip() {
return React.useContext(ToggletipContext);
}
/**
* Used as a container for the button and content of a toggletip. This component
* is responsible for coordinating between interactions with the button and the
* visibility of the content
*/
function Toggletip(_ref2) {
let {
align,
as,
className: customClassName,
children,
defaultOpen = false
} = _ref2;
const ref = React.useRef(null);
const [open, setOpen] = React.useState(defaultOpen);
const prefix = usePrefix.usePrefix();
const id = useId.useId();
const className = cx__default["default"](`${prefix}--toggletip`, customClassName, {
[`${prefix}--toggletip--open`]: open
});
const actions = {
toggle: () => {
setOpen(!open);
},
close: () => {
setOpen(false);
}
};
const value = {
buttonProps: {
'aria-expanded': open,
'aria-controls': id,
onClick: actions.toggle
},
contentProps: {
id
}
};
const onKeyDown = event => {
if (open && match.match(event, keys.Escape)) {
actions.close();
// If the menu is closed while focus is still inside the menu, it should return to the trigger button (#12922)
const button = ref.current?.children[0];
if (button instanceof HTMLButtonElement) {
button.focus();
}
}
};
const handleBlur = event => {
// Do not close if the menu itself is clicked, should only close on focus out
if (open && event.relatedTarget === null) {
return;
}
if (!event.currentTarget.contains(event.relatedTarget)) {
// The menu should be closed when focus leaves the `Toggletip` (#12922)
actions.close();
}
};
// If the `Toggletip` is the last focusable item in the tab order, it shoudl also close when the browser window loses focus (#12922)
useEvent.useWindowEvent('blur', () => {
if (open) {
actions.close();
}
});
useEvent.useWindowEvent('click', event => {
if (open && ref.current && !ref.current.contains(event.target)) {
actions.close();
}
});
return /*#__PURE__*/React__default["default"].createElement(ToggletipContext.Provider, {
value: value
}, /*#__PURE__*/React__default["default"].createElement(index.Popover, {
align: align,
as: as,
caret: true,
className: className,
dropShadow: false,
highContrast: true,
open: open,
onKeyDown: onKeyDown,
onBlur: handleBlur,
ref: ref
}, children));
}
Toggletip.propTypes = {
/**
* Specify how the toggletip should align with the button
*/
align: PropTypes__default["default"].oneOf(['top', 'top-left', 'top-right', 'bottom', 'bottom-left', 'bottom-right', 'left', 'left-bottom', 'left-top', 'right', 'right-bottom', 'right-top']),
/**
* Provide a custom element or component to render the top-level node for the
* component.
*/
as: PropTypes__default["default"].elementType,
/**
* Custom children to be rendered as the content of the label
*/
children: PropTypes__default["default"].node,
/**
* Provide a custom class name to be added to the outermost node in the
* component
*/
className: PropTypes__default["default"].string,
/**
* Specify if the toggletip should be open by default
*/
defaultOpen: PropTypes__default["default"].bool
};
/**
* `ToggletipButton` controls the visibility of the Toggletip through mouse
* clicks and keyboard interactions.
*/
function ToggletipButton(_ref3) {
let {
children,
className: customClassName,
label = 'Show information'
} = _ref3;
const toggletip = useToggletip();
const prefix = usePrefix.usePrefix();
const className = cx__default["default"](`${prefix}--toggletip-button`, customClassName);
return /*#__PURE__*/React__default["default"].createElement("button", _rollupPluginBabelHelpers["extends"]({}, toggletip?.buttonProps, {
"aria-label": label,
type: "button",
className: className
}), children);
}
ToggletipButton.propTypes = {
/**
* Custom children to be rendered as the content of the label
*/
children: PropTypes__default["default"].node,
/**
* Provide a custom class name to be added to the outermost node in the
* component
*/
className: PropTypes__default["default"].string,
/**
* Provide an accessible label for this button
*/
label: PropTypes__default["default"].string
};
/**
* `ToggletipContent` is a wrapper around `PopoverContent`. It places the
* `children` passed in as a prop inside of `PopoverContent` so that they will
* be rendered inside of the popover for this component.
*/
function ToggletipContent(_ref4) {
let {
children,
className: customClassName
} = _ref4;
const toggletip = useToggletip();
const prefix = usePrefix.usePrefix();
return /*#__PURE__*/React__default["default"].createElement(index.PopoverContent, _rollupPluginBabelHelpers["extends"]({
className: customClassName
}, toggletip?.contentProps), /*#__PURE__*/React__default["default"].createElement("div", {
className: `${prefix}--toggletip-content`
}, children));
}
ToggletipContent.propTypes = {
/**
* Custom children to be rendered as the content of the label
*/
children: PropTypes__default["default"].node,
/**
* Provide a custom class name to be added to the outermost node in the
* component
*/
className: PropTypes__default["default"].string
};
/**
* `ToggletipActions` is a container for one or two actions present at the base
* of a toggletip. It is used for layout of these items.
*/
function ToggletipActions(_ref5) {
let {
children,
className: customClassName
} = _ref5;
const prefix = usePrefix.usePrefix();
const className = cx__default["default"](`${prefix}--toggletip-actions`, customClassName);
return /*#__PURE__*/React__default["default"].createElement("div", {
className: className
}, children);
}
ToggletipActions.propTypes = {
/**
* Custom children to be rendered as the content of the label
*/
children: PropTypes__default["default"].node,
/**
* Provide a custom class name to be added to the outermost node in the
* component
*/
className: PropTypes__default["default"].string
};
exports.Toggletip = Toggletip;
exports.ToggletipActions = ToggletipActions;
exports.ToggletipButton = ToggletipButton;
exports.ToggletipContent = ToggletipContent;
exports.ToggletipLabel = ToggletipLabel;