@deque/cauldron-react 6.6.1-canary.db04cb91 → 6.7.0-canary.099092f1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,36 @@
1
+ 'use strict';
2
+
3
+ var React = require('react');
4
+
5
+ function _interopNamespace(e) {
6
+ if (e && e.__esModule) return e;
7
+ var n = Object.create(null);
8
+ if (e) {
9
+ Object.keys(e).forEach(function (k) {
10
+ if (k !== 'default') {
11
+ var d = Object.getOwnPropertyDescriptor(e, k);
12
+ Object.defineProperty(n, k, d.get ? d : {
13
+ enumerable: true,
14
+ get: function () { return e[k]; }
15
+ });
16
+ }
17
+ });
18
+ }
19
+ n["default"] = e;
20
+ return Object.freeze(n);
21
+ }
22
+
23
+ var React__namespace = /*#__PURE__*/_interopNamespace(React);
24
+
25
+ var _path;
26
+ function _extends() { _extends = Object.assign ? Object.assign.bind() : function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; return _extends.apply(this, arguments); }
27
+ const SvgBrokenImage = props => /*#__PURE__*/React__namespace.createElement("svg", _extends({
28
+ viewBox: "0 0 24 24",
29
+ fill: "currentColor",
30
+ height: 24,
31
+ width: 24
32
+ }, props), _path || (_path = /*#__PURE__*/React__namespace.createElement("path", {
33
+ d: "M22.154 0H1.846c-.49 0-.96.23-1.305.639C.195 1.049 0 1.603 0 2.182v19.636c0 .579.195 1.134.54 1.543.347.41.817.639 1.306.639h7.385a.831.831 0 0 0 .54-.206c.157-.134.274-.323.335-.54l1.712-6.065 4.22-1.994a.935.935 0 0 0 .31-.242c.088-.105.158-.23.205-.366l1.687-4.984 5.132-2.023a.952.952 0 0 0 .455-.398A1.23 1.23 0 0 0 24 6.545V2.182c0-.579-.195-1.134-.54-1.543C23.112.229 22.642 0 22.153 0ZM10.2 16.019l-1.636 5.8H1.846V18l6-7.09 3.51 4.147-.625.293a.933.933 0 0 0-.327.266c-.092.115-.16.253-.203.403Zm11.953-10.26-4.907 1.933a.908.908 0 0 0-.342.242 1.117 1.117 0 0 0-.224.388l-1.698 5.021-1.762.839-4.07-4.81c-.346-.409-.815-.638-1.305-.638s-.959.23-1.305.638l-4.695 5.542V2.182h20.308v3.577Zm1.463 4.5a.852.852 0 0 0-.4-.194.789.789 0 0 0-.432.044l-2.746 1.082a.908.908 0 0 0-.341.241 1.117 1.117 0 0 0-.224.388l-1.652 4.878-4.127 1.951a.934.934 0 0 0-.328.265 1.146 1.146 0 0 0-.204.403l-.916 3.246a1.28 1.28 0 0 0-.037.51c.021.17.078.333.163.474.086.14.198.254.329.333.13.079.274.12.42.12h9.032c.49 0 .96-.23 1.305-.639.346-.41.541-.964.541-1.543V11.145c0-.173-.035-.343-.101-.497a1.062 1.062 0 0 0-.282-.388v-.001Zm-1.463 11.56h-7.75l.374-1.33 4.098-1.937a.936.936 0 0 0 .31-.242c.088-.104.158-.229.204-.366l1.639-4.842 1.125-.443v9.16Z"
34
+ })));
35
+
36
+ exports["default"] = SvgBrokenImage;
package/lib/cauldron.css CHANGED
@@ -39,6 +39,12 @@
39
39
  }
40
40
  }
41
41
 
42
+ a.Button--primary,
43
+ a.Button--secondary,
44
+ a.Button--thin {
45
+ font-weight: var(--font-weight-medium);
46
+ }
47
+
42
48
  a.Button--primary,
43
49
  a.Button--secondary {
44
50
  text-decoration: none;
@@ -0,0 +1,8 @@
1
+ import React from 'react';
2
+ import { ContentNode } from '../../types';
3
+ declare const BottomSheet: React.ForwardRefExoticComponent<{
4
+ label: ContentNode;
5
+ closeButtonText?: ContentNode | undefined;
6
+ open?: boolean | undefined;
7
+ } & React.HTMLAttributes<HTMLDivElement> & Pick<import("../Drawer").DrawerProps<HTMLElement> & React.RefAttributes<HTMLDivElement>, "open" | "onClose" | "portal" | "focusOptions"> & React.RefAttributes<HTMLDivElement>>;
8
+ export default BottomSheet;
@@ -4,23 +4,7 @@ export interface ClickOutsideListenerProps<T extends HTMLElement = HTMLElement>
4
4
  onClickOutside: (e: MouseEvent | TouchEvent) => void;
5
5
  mouseEvent?: 'mousedown' | 'click' | 'mouseup' | false;
6
6
  touchEvent?: 'touchstart' | 'touchend' | false;
7
- target?: T;
8
- }
9
- export default class ClickOutsideListener extends React.Component<ClickOutsideListenerProps> {
10
- static displayName: string;
11
- static defaultProps: {
12
- mouseEvent: string;
13
- touchEvent: string;
14
- };
15
- private nodeRef;
16
- handleEvent: (event: MouseEvent | TouchEvent) => void;
17
- componentDidMount(): void;
18
- componentDidUpdate(prevProps: ClickOutsideListenerProps): void;
19
- componentWillUnmount(): void;
20
- private attachEventListeners;
21
- private removeEventListeners;
22
- resolveRef: (node: HTMLElement) => void;
23
- render(): React.FunctionComponentElement<{
24
- ref: (node: HTMLElement) => void;
25
- }> | null;
7
+ target?: T | React.RefObject<T> | React.MutableRefObject<T>;
26
8
  }
9
+ declare const _default: React.ForwardRefExoticComponent<ClickOutsideListenerProps<HTMLElement> & React.RefAttributes<HTMLElement>>;
10
+ export default _default;
@@ -0,0 +1,15 @@
1
+ import React from 'react';
2
+ export interface DrawerProps<T extends HTMLElement = HTMLElement> extends React.HTMLAttributes<HTMLDivElement> {
3
+ children: React.ReactNode;
4
+ position: 'top' | 'bottom' | 'left' | 'right';
5
+ open?: boolean;
6
+ behavior?: 'modal' | 'non-modal';
7
+ focusOptions?: {
8
+ initialFocus?: T | React.RefObject<T> | React.MutableRefObject<T>;
9
+ returnFocus?: T | React.RefObject<T> | React.MutableRefObject<T>;
10
+ };
11
+ onClose?: () => void;
12
+ portal?: React.RefObject<HTMLElement> | HTMLElement;
13
+ }
14
+ declare const Drawer: React.ForwardRefExoticComponent<DrawerProps<HTMLElement> & React.RefAttributes<HTMLDivElement>>;
15
+ export default Drawer;
@@ -2,6 +2,6 @@
2
2
  * GENERATED CODE. DO NOT EDIT DIRECTLY!
3
3
  */
4
4
  /** IconType represents each valid icon type. */
5
- export type IconType = 'add-user' | 'arrow-circle-up' | 'arrow-circle-down' | 'arrow-circle-left' | 'arrow-circle-right' | 'arrow-up' | 'arrow-down' | 'arrow-left' | 'arrow-right' | 'arrows-alt' | 'bolt' | 'caution' | 'check-circle' | 'check-shield' | 'check-solid' | 'check' | 'checkbox-checked' | 'checkbox-unchecked' | 'chevron-double-up' | 'chevron-double-down' | 'chevron-double-left' | 'chevron-double-right' | 'chevron-up' | 'chevron-down' | 'chevron-left' | 'chevron-right' | 'clipboard' | 'clock' | 'close' | 'code' | 'copy' | 'download' | 'dropper' | 'exchange' | 'export-solid' | 'external-link' | 'eye' | 'filter-solid' | 'filter' | 'flag' | 'gears' | 'github' | 'grid' | 'hamburger-menu' | 'hashtag' | 'highlight' | 'info-circle-alt' | 'info-circle' | 'info-square' | 'kabob' | 'link' | 'linkedin' | 'list' | 'lock' | 'magnifying-glass' | 'menu' | 'minus' | 'new-releases' | 'new' | 'no' | 'pencil' | 'person-running' | 'play' | 'plus' | 'question-circle-alt' | 'question-circle' | 'radio-checked' | 'radio-unchecked' | 'recycle-square' | 'recycle' | 'resend' | 'robot' | 'run-again' | 'save' | 'share-nodes' | 'share' | 'sort-triangle' | 'sort' | 'star' | 'step-back' | 'step-forward' | 'sun' | 'table-sort-ascending' | 'table-sort-descending' | 'tag' | 'target' | 'trash' | 'triangle-up' | 'triangle-down' | 'triangle-left' | 'triangle-right' | 'twitter' | 'upload';
5
+ export type IconType = 'add-user' | 'arrow-circle-up' | 'arrow-circle-down' | 'arrow-circle-left' | 'arrow-circle-right' | 'arrow-up' | 'arrow-down' | 'arrow-left' | 'arrow-right' | 'arrows-alt' | 'bolt' | 'broken-image' | 'caution' | 'check-circle' | 'check-shield' | 'check-solid' | 'check' | 'checkbox-checked' | 'checkbox-unchecked' | 'chevron-double-up' | 'chevron-double-down' | 'chevron-double-left' | 'chevron-double-right' | 'chevron-up' | 'chevron-down' | 'chevron-left' | 'chevron-right' | 'clipboard' | 'clock' | 'close' | 'code' | 'copy' | 'download' | 'dropper' | 'exchange' | 'export-solid' | 'external-link' | 'eye' | 'filter-solid' | 'filter' | 'flag' | 'gears' | 'github' | 'grid' | 'hamburger-menu' | 'hashtag' | 'highlight' | 'images' | 'info-circle-alt' | 'info-circle' | 'info-square' | 'kabob' | 'link' | 'linkedin' | 'list' | 'lock' | 'magnifying-glass' | 'menu' | 'minus' | 'new-releases' | 'new' | 'no' | 'pencil' | 'person-running' | 'play' | 'plus' | 'question-circle-alt' | 'question-circle' | 'radio-checked' | 'radio-unchecked' | 'recycle-square' | 'recycle' | 'resend' | 'robot' | 'run-again' | 'save' | 'share-nodes' | 'share' | 'sort-triangle' | 'sort' | 'star' | 'step-back' | 'step-forward' | 'sun' | 'table-sort-ascending' | 'table-sort-descending' | 'tag' | 'target' | 'trash' | 'triangle-up' | 'triangle-down' | 'triangle-left' | 'triangle-right' | 'twitter' | 'upload';
6
6
  /** iconTypes holds each valid icon type. */
7
7
  export declare const iconTypes: string[];
package/lib/images.js ADDED
@@ -0,0 +1,37 @@
1
+ 'use strict';
2
+
3
+ var React = require('react');
4
+
5
+ function _interopNamespace(e) {
6
+ if (e && e.__esModule) return e;
7
+ var n = Object.create(null);
8
+ if (e) {
9
+ Object.keys(e).forEach(function (k) {
10
+ if (k !== 'default') {
11
+ var d = Object.getOwnPropertyDescriptor(e, k);
12
+ Object.defineProperty(n, k, d.get ? d : {
13
+ enumerable: true,
14
+ get: function () { return e[k]; }
15
+ });
16
+ }
17
+ });
18
+ }
19
+ n["default"] = e;
20
+ return Object.freeze(n);
21
+ }
22
+
23
+ var React__namespace = /*#__PURE__*/_interopNamespace(React);
24
+
25
+ var _path;
26
+ function _extends() { _extends = Object.assign ? Object.assign.bind() : function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; return _extends.apply(this, arguments); }
27
+ const SvgImages = props => /*#__PURE__*/React__namespace.createElement("svg", _extends({
28
+ xmlns: "http://www.w3.org/2000/svg",
29
+ viewBox: "0 0 576 512",
30
+ height: 24,
31
+ width: 24
32
+ }, props), _path || (_path = /*#__PURE__*/React__namespace.createElement("path", {
33
+ d: "M160 32c-35.3 0-64 28.7-64 64v224c0 35.3 28.7 64 64 64h352c35.3 0 64-28.7 64-64V96c0-35.3-28.7-64-64-64H160zm236 106.7 96 144c4.9 7.4 5.4 16.8 1.2 24.6S480.9 320 472 320H200c-9.2 0-17.6-5.3-21.6-13.6s-2.9-18.2 2.9-25.4l64-80c4.6-5.7 11.4-9 18.7-9s14.2 3.3 18.7 9l17.3 21.6 56-84c4.5-6.6 12-10.6 20-10.6s15.5 4 20 10.7zM192 128a32 32 0 1 1 64 0 32 32 0 1 1-64 0zm-144-8c0-13.3-10.7-24-24-24S0 106.7 0 120v224c0 75.1 60.9 136 136 136h320c13.3 0 24-10.7 24-24s-10.7-24-24-24H136c-48.6 0-88-39.4-88-88V120z",
34
+ fill: "currentColor"
35
+ })));
36
+
37
+ exports["default"] = SvgImages;
package/lib/index.d.ts CHANGED
@@ -59,6 +59,8 @@ export { default as Popover } from './components/Popover';
59
59
  export { default as Timeline, TimelineItem } from './components/Timeline';
60
60
  export { default as TextEllipsis } from './components/TextEllipsis';
61
61
  export { default as CopyButton } from './components/CopyButton';
62
+ export { default as Drawer } from './components/Drawer';
63
+ export { default as BottomSheet } from './components/BottomSheet';
62
64
  /**
63
65
  * Helpers / Utils
64
66
  */
package/lib/index.js CHANGED
@@ -114,6 +114,7 @@ var iconTypes = [
114
114
  'arrow-right',
115
115
  'arrows-alt',
116
116
  'bolt',
117
+ 'broken-image',
117
118
  'caution',
118
119
  'check-circle',
119
120
  'check-shield',
@@ -149,6 +150,7 @@ var iconTypes = [
149
150
  'hamburger-menu',
150
151
  'hashtag',
151
152
  'highlight',
153
+ 'images',
152
154
  'info-circle-alt',
153
155
  'info-circle',
154
156
  'info-square',
@@ -205,6 +207,7 @@ function __variableDynamicImportRuntime0__(path) {
205
207
  case './icons/arrow.svg': return Promise.resolve().then(function () { return require('./arrow.js'); });
206
208
  case './icons/arrows-alt.svg': return Promise.resolve().then(function () { return require('./arrows-alt.js'); });
207
209
  case './icons/bolt.svg': return Promise.resolve().then(function () { return require('./bolt.js'); });
210
+ case './icons/broken-image.svg': return Promise.resolve().then(function () { return require('./broken-image.js'); });
208
211
  case './icons/caution.svg': return Promise.resolve().then(function () { return require('./caution.js'); });
209
212
  case './icons/check-circle.svg': return Promise.resolve().then(function () { return require('./check-circle.js'); });
210
213
  case './icons/check-shield.svg': return Promise.resolve().then(function () { return require('./check-shield.js'); });
@@ -234,6 +237,7 @@ function __variableDynamicImportRuntime0__(path) {
234
237
  case './icons/hamburger-menu.svg': return Promise.resolve().then(function () { return require('./hamburger-menu.js'); });
235
238
  case './icons/hashtag.svg': return Promise.resolve().then(function () { return require('./hashtag.js'); });
236
239
  case './icons/highlight.svg': return Promise.resolve().then(function () { return require('./highlight.js'); });
240
+ case './icons/images.svg': return Promise.resolve().then(function () { return require('./images.js'); });
237
241
  case './icons/info-circle-alt.svg': return Promise.resolve().then(function () { return require('./info-circle-alt.js'); });
238
242
  case './icons/info-circle.svg': return Promise.resolve().then(function () { return require('./info-circle.js'); });
239
243
  case './icons/info-square.svg': return Promise.resolve().then(function () { return require('./info-square.js'); });
@@ -789,74 +793,70 @@ var OptionsMenuWrapper = function (_a) {
789
793
  return (React__default["default"].createElement("div", tslib.__assign({ className: classNames__default["default"]('OptionsMenu', menuAlignment(align), className) }, other)));
790
794
  };
791
795
 
792
- var ClickOutsideListener = /** @class */ (function (_super) {
793
- tslib.__extends(ClickOutsideListener, _super);
794
- function ClickOutsideListener() {
795
- var _this = _super !== null && _super.apply(this, arguments) || this;
796
- _this.handleEvent = function (event) {
797
- var _a = _this, nodeRef = _a.nodeRef, props = _a.props;
798
- var onClickOutside = props.onClickOutside, target = props.target;
799
- if (event.defaultPrevented) {
800
- return;
801
- }
802
- var eventTarget = event.target;
803
- if ((target && !target.contains(eventTarget)) ||
804
- (nodeRef && !nodeRef.contains(eventTarget))) {
805
- onClickOutside(event);
806
- }
807
- };
808
- _this.attachEventListeners = function () {
809
- var _a = _this.props, mouseEvent = _a.mouseEvent, touchEvent = _a.touchEvent;
810
- typeof mouseEvent === 'string' &&
811
- document.addEventListener(mouseEvent, _this.handleEvent);
812
- typeof touchEvent === 'string' &&
813
- document.addEventListener(touchEvent, _this.handleEvent);
814
- };
815
- _this.removeEventListeners = function (mouseEvent, touchEvent) {
816
- typeof mouseEvent === 'string' &&
817
- document.removeEventListener(mouseEvent, _this.handleEvent);
818
- typeof touchEvent === 'string' &&
819
- document.removeEventListener(touchEvent, _this.handleEvent);
820
- };
821
- _this.resolveRef = function (node) {
822
- _this.nodeRef = node;
823
- // If child has its own ref, we want to update
824
- // its ref with the newly cloned node
825
- var ref = _this.props.children.ref;
826
- setRef(ref, node);
827
- };
828
- return _this;
796
+ /**
797
+ * When an element can be passed as a value that is either an element or an
798
+ * elementRef, this will resolve the property down to the resulting element
799
+ */
800
+ function resolveElement(elementOrRef) {
801
+ if (elementOrRef instanceof Element) {
802
+ return elementOrRef;
829
803
  }
830
- ClickOutsideListener.prototype.componentDidMount = function () {
831
- this.attachEventListeners();
832
- };
833
- ClickOutsideListener.prototype.componentDidUpdate = function (prevProps) {
834
- var _a = this.props, mouseEvent = _a.mouseEvent, touchEvent = _a.touchEvent;
835
- if (prevProps.mouseEvent !== mouseEvent ||
836
- prevProps.touchEvent !== touchEvent) {
837
- this.removeEventListeners(prevProps.mouseEvent, prevProps.touchEvent);
838
- this.attachEventListeners();
804
+ if (elementOrRef &&
805
+ typeof elementOrRef === 'object' &&
806
+ 'current' in elementOrRef &&
807
+ elementOrRef.current instanceof Element) {
808
+ return elementOrRef.current;
809
+ }
810
+ return null;
811
+ }
812
+
813
+ function ClickOutsideListener(_a, ref) {
814
+ var children = _a.children, _b = _a.mouseEvent, mouseEvent = _b === void 0 ? 'click' : _b, _c = _a.touchEvent, touchEvent = _c === void 0 ? 'touchend' : _c, target = _a.target, _d = _a.onClickOutside, onClickOutside = _d === void 0 ? function () { return null; } : _d;
815
+ var childElementRef = React.useRef();
816
+ var handleEvent = function (event) {
817
+ if (event.defaultPrevented) {
818
+ return;
819
+ }
820
+ var eventTarget = event.target;
821
+ var elementTarget = resolveElement(target);
822
+ if (target && !(elementTarget === null || elementTarget === void 0 ? void 0 : elementTarget.contains(eventTarget))) {
823
+ onClickOutside(event);
824
+ // If a target is passed in via a prop, we defer to utilizing that
825
+ // target instead of a child element target
826
+ return;
827
+ }
828
+ if (childElementRef.current &&
829
+ !childElementRef.current.contains(eventTarget)) {
830
+ onClickOutside(event);
839
831
  }
840
832
  };
841
- ClickOutsideListener.prototype.componentWillUnmount = function () {
842
- var _a = this.props, mouseEvent = _a.mouseEvent, touchEvent = _a.touchEvent;
843
- this.removeEventListeners(mouseEvent, touchEvent);
844
- };
845
- ClickOutsideListener.prototype.render = function () {
846
- var _a = this, props = _a.props, resolveRef = _a.resolveRef;
847
- return !props.children
848
- ? null
849
- : React__default["default"].cloneElement(props.children, {
850
- ref: resolveRef
851
- });
852
- };
853
- ClickOutsideListener.displayName = 'ClickOutsideListener';
854
- ClickOutsideListener.defaultProps = {
855
- mouseEvent: 'click',
856
- touchEvent: 'touchend'
833
+ var resolveRef = function (node) {
834
+ childElementRef.current = node;
835
+ // Ref for this component should pass-through to the child node
836
+ setRef(ref, node);
837
+ // If child has its own ref, we want to update
838
+ // its ref with the newly cloned node
839
+ var childRef = children.ref;
840
+ setRef(childRef, node);
857
841
  };
858
- return ClickOutsideListener;
859
- }(React__default["default"].Component));
842
+ React.useEffect(function () {
843
+ typeof mouseEvent === 'string' &&
844
+ document.addEventListener(mouseEvent, handleEvent);
845
+ typeof touchEvent === 'string' &&
846
+ document.addEventListener(touchEvent, handleEvent);
847
+ return function () {
848
+ typeof mouseEvent === 'string' &&
849
+ document.removeEventListener(mouseEvent, handleEvent);
850
+ typeof touchEvent === 'string' &&
851
+ document.removeEventListener(touchEvent, handleEvent);
852
+ };
853
+ }, [mouseEvent, touchEvent]);
854
+ return !children
855
+ ? null
856
+ : React__default["default"].cloneElement(children, { ref: resolveRef });
857
+ }
858
+ ClickOutsideListener.displayName = 'ClickOutsideListener';
859
+ var ClickOutsideListener$1 = React__default["default"].forwardRef(ClickOutsideListener);
860
860
 
861
861
  var _a$2 = tslib.__read([38, 40, 9, 13, 32, 27], 6), up = _a$2[0], down$1 = _a$2[1], tab = _a$2[2], enter = _a$2[3], space = _a$2[4], esc = _a$2[5];
862
862
  var OptionsMenuList = /** @class */ (function (_super) {
@@ -962,7 +962,7 @@ var OptionsMenuList = /** @class */ (function (_super) {
962
962
  // Key event is being handled in componentDidMount
963
963
  /* eslint-disable jsx-a11y/click-events-have-key-events */
964
964
  /* eslint-disable jsx-a11y/role-supports-aria-props */
965
- return (React__default["default"].createElement(ClickOutsideListener, { onClickOutside: this.handleClickOutside, mouseEvent: clickOutsideEventActive, touchEvent: clickOutsideEventActive },
965
+ return (React__default["default"].createElement(ClickOutsideListener$1, { onClickOutside: this.handleClickOutside, mouseEvent: clickOutsideEventActive, touchEvent: clickOutsideEventActive },
966
966
  React__default["default"].createElement("ul", tslib.__assign({}, other, { className: classNames__default["default"]('OptionsMenu__list', className), "aria-expanded": show, role: "menu", onClick: handleClick, ref: function (el) {
967
967
  _this.menuRef = el;
968
968
  if (menuRef) {
@@ -1310,7 +1310,7 @@ var SideBar = /** @class */ (function (_super) {
1310
1310
  var _b = this.props, children = _b.children, className = _b.className, show = _b.show; _b.onDismiss; var navProps = _b.navProps, other = tslib.__rest(_b, ["children", "className", "show", "onDismiss", "navProps"]);
1311
1311
  /* eslint-disable jsx-a11y/no-noninteractive-element-interactions */
1312
1312
  return (React__default["default"].createElement(React.Fragment, null,
1313
- React__default["default"].createElement(ClickOutsideListener, { onClickOutside: this.handleClickOutside },
1313
+ React__default["default"].createElement(ClickOutsideListener$1, { onClickOutside: this.handleClickOutside },
1314
1314
  React__default["default"].createElement("nav", tslib.__assign({}, navProps),
1315
1315
  React__default["default"].createElement("ul", tslib.__assign({ className: classNames__default["default"]('SideBar', className, animateClass) }, other, { ref: this.navList, onKeyDown: this.onKeyDown }), children))),
1316
1316
  React__default["default"].createElement(Scrim, { show: !wide && show })));
@@ -1449,7 +1449,7 @@ var Dialog = /** @class */ (function (_super) {
1449
1449
  escapeDeactivates: false,
1450
1450
  fallbackFocus: '.Dialog__heading'
1451
1451
  } },
1452
- React__default["default"].createElement(ClickOutsideListener, { onClickOutside: this.handleClickOutside },
1452
+ React__default["default"].createElement(ClickOutsideListener$1, { onClickOutside: this.handleClickOutside },
1453
1453
  React__default["default"].createElement("div", tslib.__assign({ role: "dialog", className: classNames__default["default"]('Dialog', className, {
1454
1454
  'Dialog--show': show
1455
1455
  }), ref: function (el) {
@@ -1665,6 +1665,46 @@ function hasIdRef(ids, id) {
1665
1665
  return idRefs(ids).has(id);
1666
1666
  }
1667
1667
 
1668
+ var isEscapeKey = function (event) {
1669
+ return event.key === 'Escape' || event.key === 'Esc' || event.keyCode === 27;
1670
+ };
1671
+ /**
1672
+ * When a component needs to implement an escape handler, such as in modal
1673
+ * dialogs, useEscapeKey will handle the events and call the provided callback
1674
+ * handler when an escape key event has been fired.
1675
+ *
1676
+ * @example
1677
+ * useEscapeKey(() => close())
1678
+ */
1679
+ function useEscapeKey(options, dependencies) {
1680
+ if (dependencies === void 0) { dependencies = []; }
1681
+ var callback = options.callback;
1682
+ var event = options.event || 'keyup';
1683
+ var target = resolveElement(options.target) || document.body;
1684
+ var active = typeof options.active === 'boolean' ? options.active : true;
1685
+ React.useEffect(function () {
1686
+ var eventListener = function (event) {
1687
+ if (isEscapeKey(event) &&
1688
+ (options.defaultPrevented ? !event.defaultPrevented : true)) {
1689
+ callback(event);
1690
+ }
1691
+ };
1692
+ if (active) {
1693
+ target === null || target === void 0 ? void 0 : target.addEventListener(event, eventListener, options.capture);
1694
+ }
1695
+ return function () {
1696
+ target === null || target === void 0 ? void 0 : target.removeEventListener(event, eventListener, options.capture);
1697
+ };
1698
+ }, tslib.__spreadArray([
1699
+ active,
1700
+ callback,
1701
+ event,
1702
+ target,
1703
+ options.capture,
1704
+ options.defaultPrevented
1705
+ ], tslib.__read(dependencies), false));
1706
+ }
1707
+
1668
1708
  var TIP_HIDE_DELAY = 100;
1669
1709
  // fires a custom "cauldron:tooltip:show" / "cauldron:tooltip:hide" event
1670
1710
  // to allow projects using cauldron to hook into when a tooltip is shown/hidden
@@ -1753,30 +1793,14 @@ function Tooltip(_a) {
1753
1793
  attributes.popper['data-popper-placement']) ||
1754
1794
  initialPlacement;
1755
1795
  // Only listen to key ups when the tooltip is visible
1756
- React.useEffect(function () {
1757
- var handleEscape = function (event) {
1758
- if (event.key === 'Escape' ||
1759
- event.key === 'Esc' ||
1760
- event.keyCode === 27) {
1761
- event.preventDefault();
1762
- setShowTooltip(false);
1763
- }
1764
- };
1765
- var targetElement = document.body;
1766
- if (showTooltip && typeof showProp !== 'boolean') {
1767
- targetElement.addEventListener('keyup', handleEscape, { capture: true });
1768
- }
1769
- else {
1770
- targetElement.removeEventListener('keyup', handleEscape, {
1771
- capture: true
1772
- });
1773
- }
1774
- return function () {
1775
- targetElement.removeEventListener('keyup', handleEscape, {
1776
- capture: true
1777
- });
1778
- };
1779
- }, [showTooltip, showProp]);
1796
+ useEscapeKey({
1797
+ callback: function (event) {
1798
+ event.preventDefault();
1799
+ setShowTooltip(false);
1800
+ },
1801
+ capture: true,
1802
+ active: showTooltip && typeof showProp !== 'boolean'
1803
+ }, [setShowTooltip]);
1780
1804
  // Handle hover and focus events for the targetElement
1781
1805
  React.useEffect(function () {
1782
1806
  if (typeof showProp !== 'boolean') {
@@ -3292,25 +3316,10 @@ var TwoColumnPanel = React.forwardRef(function (_a, ref) {
3292
3316
  mediaQueryList.removeEventListener('change', listener);
3293
3317
  };
3294
3318
  }, []);
3295
- React.useEffect(function () {
3296
- var handleEscape = function (event) {
3297
- if (event.key === 'Escape' ||
3298
- event.key === 'Esc' ||
3299
- event.keyCode === 27) {
3300
- setCollapsed(true);
3301
- }
3302
- };
3303
- var targetElement = document.body;
3304
- if (isFocusTrap) {
3305
- targetElement.addEventListener('keyup', handleEscape);
3306
- }
3307
- else {
3308
- targetElement.removeEventListener('keyup', handleEscape);
3309
- }
3310
- return function () {
3311
- targetElement.removeEventListener('keyup', handleEscape);
3312
- };
3313
- }, [isFocusTrap]);
3319
+ useEscapeKey({
3320
+ callback: function () { return setCollapsed(true); },
3321
+ active: isFocusTrap
3322
+ }, [setCollapsed]);
3314
3323
  var handleClickOutside = function () {
3315
3324
  if (!isCollapsed && isFocusTrap) {
3316
3325
  setCollapsed(true);
@@ -3326,7 +3335,7 @@ var TwoColumnPanel = React.forwardRef(function (_a, ref) {
3326
3335
  allowOutsideClick: true,
3327
3336
  fallbackFocus: columnLeftRef.current
3328
3337
  }, containerElements: [columnLeftRef.current] }),
3329
- React__default["default"].createElement(ClickOutsideListener, { onClickOutside: handleClickOutside, target: columnLeftRef.current }),
3338
+ React__default["default"].createElement(ClickOutsideListener$1, { onClickOutside: handleClickOutside, target: columnLeftRef.current }),
3330
3339
  isCollapsed ? null : skipLink,
3331
3340
  showPanel ? ColumnLeftComponent : null,
3332
3341
  ColumnRightComponent)));
@@ -3358,8 +3367,8 @@ var iconTypeMap = {
3358
3367
  };
3359
3368
  var Notice = React.forwardRef(function (_a, ref) {
3360
3369
  var _b;
3361
- var _c = _a.type, type = _c === void 0 ? 'info' : _c, title = _a.title, icon = _a.icon, _d = _a.variant, variant = _d === void 0 ? 'default' : _d, children = _a.children, otherProps = tslib.__rest(_a, ["type", "title", "icon", "variant", "children"]);
3362
- return (React__default["default"].createElement("div", tslib.__assign({ className: classNames__default["default"]('Notice', (_b = {},
3370
+ var className = _a.className, _c = _a.type, type = _c === void 0 ? 'info' : _c, title = _a.title, icon = _a.icon, _d = _a.variant, variant = _d === void 0 ? 'default' : _d, children = _a.children, otherProps = tslib.__rest(_a, ["className", "type", "title", "icon", "variant", "children"]);
3371
+ return (React__default["default"].createElement("div", tslib.__assign({ className: classNames__default["default"]('Notice', className, (_b = {},
3363
3372
  _b["Notice--".concat(type)] = type,
3364
3373
  _b["Notice--condensed"] = variant === 'condensed',
3365
3374
  _b)), ref: ref }, otherProps),
@@ -4093,24 +4102,6 @@ var Popover = React.forwardRef(function (_a, ref) {
4093
4102
  }
4094
4103
  targetElement === null || targetElement === void 0 ? void 0 : targetElement.setAttribute('aria-expanded', Boolean(show).toString());
4095
4104
  }, [show, popoverRef.current]);
4096
- React.useEffect(function () {
4097
- var handleEscape = function (event) {
4098
- if (event.key === 'Escape' ||
4099
- event.key === 'Esc' ||
4100
- event.keyCode === 27) {
4101
- handleClosePopover();
4102
- }
4103
- };
4104
- if (show) {
4105
- document.body.addEventListener('keyup', handleEscape);
4106
- }
4107
- else {
4108
- document.body.removeEventListener('keyup', handleEscape);
4109
- }
4110
- return function () {
4111
- document.body.removeEventListener('keyup', handleEscape);
4112
- };
4113
- }, [show]);
4114
4105
  React.useEffect(function () {
4115
4106
  var attrText = targetElement === null || targetElement === void 0 ? void 0 : targetElement.getAttribute('aria-controls');
4116
4107
  var hasPopupAttr = targetElement === null || targetElement === void 0 ? void 0 : targetElement.getAttribute('aria-haspopup');
@@ -4137,13 +4128,17 @@ var Popover = React.forwardRef(function (_a, ref) {
4137
4128
  onClose();
4138
4129
  }
4139
4130
  };
4131
+ useEscapeKey({
4132
+ callback: handleClosePopover,
4133
+ active: show
4134
+ }, [show]);
4140
4135
  if (!show || !isBrowser())
4141
4136
  return null;
4142
4137
  return reactDom.createPortal(React__default["default"].createElement(FocusTrap__default["default"], { focusTrapOptions: {
4143
4138
  allowOutsideClick: true,
4144
4139
  fallbackFocus: '.Popover__borderLeft'
4145
4140
  } },
4146
- React__default["default"].createElement(ClickOutsideListener, { onClickOutside: handleClickOutside },
4141
+ React__default["default"].createElement(ClickOutsideListener$1, { onClickOutside: handleClickOutside },
4147
4142
  React__default["default"].createElement("div", tslib.__assign({ id: id, className: classNames__default["default"]('Popover', "Popover--".concat(placement), className, {
4148
4143
  'Popover--hidden': !show,
4149
4144
  'Popover--prompt': variant === 'prompt'
@@ -4214,6 +4209,133 @@ var TextEllipsis = React__default["default"].forwardRef(function (_a, ref) {
4214
4209
  });
4215
4210
  TextEllipsis.displayName = 'TextEllipsis';
4216
4211
 
4212
+ var Drawer = React.forwardRef(function (_a, ref) {
4213
+ var children = _a.children, className = _a.className, position = _a.position, _b = _a.open, open = _b === void 0 ? false : _b, _c = _a.behavior, behavior = _c === void 0 ? 'modal' : _c, _d = _a.focusOptions, focusOptions = _d === void 0 ? {} : _d, portal = _a.portal, onClose = _a.onClose, style = _a.style, props = tslib.__rest(_a, ["children", "className", "position", "open", "behavior", "focusOptions", "portal", "onClose", "style"]);
4214
+ var drawerRef = useSharedRef(ref);
4215
+ var openRef = React.useRef(!!open);
4216
+ var previousActiveElementRef = React.useRef(null);
4217
+ var focusInitial = focusOptions.initialFocus, focusReturn = focusOptions.returnFocus;
4218
+ var _e = tslib.__read(React.useState(!!open), 2), isTransitioning = _e[0], setIsTransitioning = _e[1];
4219
+ var isModal = behavior === 'modal';
4220
+ var handleClose = React.useCallback(function () {
4221
+ // istanbul ignore next
4222
+ if (open && typeof onClose === 'function') {
4223
+ onClose();
4224
+ }
4225
+ }, [open, onClose]);
4226
+ React.useEffect(function () {
4227
+ // jsdom does not trigger transitionend event
4228
+ // istanbul ignore next
4229
+ var transitionEndHandler = function () { return setIsTransitioning(false); };
4230
+ document.addEventListener('transitionend', transitionEndHandler);
4231
+ return function () {
4232
+ document.removeEventListener('transitionend', transitionEndHandler);
4233
+ };
4234
+ }, [setIsTransitioning]);
4235
+ React.useEffect(function () {
4236
+ if (openRef.current !== open) {
4237
+ setIsTransitioning(true);
4238
+ }
4239
+ openRef.current = open;
4240
+ }, [open, setIsTransitioning]);
4241
+ React.useEffect(function () {
4242
+ if (!isModal) {
4243
+ return;
4244
+ }
4245
+ var isolator = new AriaIsolate(drawerRef.current);
4246
+ if (open) {
4247
+ isolator.activate();
4248
+ }
4249
+ else {
4250
+ isolator.deactivate();
4251
+ }
4252
+ return function () {
4253
+ isolator.deactivate();
4254
+ };
4255
+ }, [isModal, open]);
4256
+ React.useLayoutEffect(function () {
4257
+ var _a, _b, _c;
4258
+ if (open) {
4259
+ previousActiveElementRef.current =
4260
+ document.activeElement;
4261
+ var initialFocusElement = resolveElement(focusInitial);
4262
+ if (initialFocusElement) {
4263
+ initialFocusElement.focus();
4264
+ }
4265
+ else {
4266
+ var focusable = (_a = drawerRef.current) === null || _a === void 0 ? void 0 : _a.querySelector(focusableSelector);
4267
+ if (focusable) {
4268
+ focusable.focus();
4269
+ }
4270
+ else {
4271
+ // fallback focus
4272
+ (_b = drawerRef.current) === null || _b === void 0 ? void 0 : _b.focus();
4273
+ }
4274
+ }
4275
+ }
4276
+ else if (previousActiveElementRef.current) {
4277
+ var returnFocusElement = resolveElement(focusReturn);
4278
+ if (returnFocusElement) {
4279
+ returnFocusElement.focus();
4280
+ }
4281
+ else {
4282
+ // fallback focus
4283
+ (_c = previousActiveElementRef.current) === null || _c === void 0 ? void 0 : _c.focus();
4284
+ }
4285
+ }
4286
+ }, [open, focusInitial, focusReturn]);
4287
+ useEscapeKey({ callback: handleClose, active: open, defaultPrevented: true }, [onClose]);
4288
+ // istanbul ignore next
4289
+ if (!isBrowser()) {
4290
+ return null;
4291
+ }
4292
+ var portalElement = resolveElement(portal);
4293
+ return reactDom.createPortal(React__default["default"].createElement(React__default["default"].Fragment, null,
4294
+ React__default["default"].createElement(ClickOutsideListener$1, { onClickOutside: handleClose, mouseEvent: open ? undefined : false, touchEvent: open ? undefined : false, target: drawerRef },
4295
+ React__default["default"].createElement(FocusTrap__default["default"], { active: !!isModal && !!open, focusTrapOptions: {
4296
+ allowOutsideClick: true,
4297
+ escapeDeactivates: false,
4298
+ clickOutsideDeactivates: false,
4299
+ initialFocus: false,
4300
+ setReturnFocus: false,
4301
+ fallbackFocus: function () { return drawerRef.current; }
4302
+ } },
4303
+ React__default["default"].createElement("div", tslib.__assign({ ref: drawerRef, className: classNames__default["default"](className, 'Drawer', {
4304
+ 'Drawer--open': !!open,
4305
+ 'Drawer--top': position === 'top',
4306
+ 'Drawer--bottom': position === 'bottom',
4307
+ 'Drawer--left': position === 'left',
4308
+ 'Drawer--right': position === 'right'
4309
+ }), "aria-hidden": !open || undefined, style: tslib.__assign({ visibility: !open && !isTransitioning ? 'hidden' : undefined }, style), tabIndex: open ? -1 : undefined }, props), children))),
4310
+ React__default["default"].createElement(Scrim, { show: !!open && !!isModal })), portalElement ||
4311
+ (
4312
+ // eslint-disable-next-line ssr-friendly/no-dom-globals-in-react-fc
4313
+ document === null || document === void 0 ? void 0 : document.body));
4314
+ });
4315
+ Drawer.displayName = 'Drawer';
4316
+
4317
+ var BottomSheet = React.forwardRef(function (_a, ref) {
4318
+ var label = _a.label, children = _a.children, className = _a.className, _b = _a.closeButtonText, closeButtonText = _b === void 0 ? 'Close' : _b, _c = _a.open, open = _c === void 0 ? false : _c, onClose = _a.onClose, focusOptions = _a.focusOptions, props = tslib.__rest(_a, ["label", "children", "className", "closeButtonText", "open", "onClose", "focusOptions"]);
4319
+ var bottomSheetRef = useSharedRef(ref);
4320
+ var _d = tslib.__read(nextId.useId(1, 'bottom-sheet-label'), 1), labelId = _d[0];
4321
+ var handleClose = React.useCallback(function () {
4322
+ // istanbul ignore else
4323
+ if (typeof onClose === 'function') {
4324
+ onClose();
4325
+ }
4326
+ }, [onClose]);
4327
+ return (React__default["default"].createElement(Drawer, tslib.__assign({ open: open, onClose: handleClose, focusOptions: tslib.__assign({ initialFocus: bottomSheetRef }, focusOptions) }, props, { behavior: "modal", position: "bottom" }),
4328
+ React__default["default"].createElement("div", { ref: bottomSheetRef, className: classNames__default["default"]('BottomSheet', className), tabIndex: -1, role: "dialog", "aria-labelledby": labelId },
4329
+ React__default["default"].createElement("div", { className: "BottomSheet__header" },
4330
+ React__default["default"].createElement("div", { id: labelId, className: "BottomSheet__title" }, label),
4331
+ React__default["default"].createElement(IconButton, { icon: "close", label: closeButtonText, "aria-label": "".concat(closeButtonText), onClick: handleClose, tooltipProps: {
4332
+ show: false,
4333
+ association: 'none'
4334
+ } })),
4335
+ React__default["default"].createElement("div", { className: "BottomSheet__contents" }, children))));
4336
+ });
4337
+ BottomSheet.displayName = 'BottomSheet';
4338
+
4217
4339
  var LIGHT_THEME_CLASS = 'cauldron--theme-light';
4218
4340
  var DARK_THEME_CLASS = 'cauldron--theme-dark';
4219
4341
  var ThemeContext = React.createContext({
@@ -4293,12 +4415,13 @@ exports.AlertContent = AlertContent;
4293
4415
  exports.AriaIsolate = AriaIsolate;
4294
4416
  exports.Badge = Badge;
4295
4417
  exports.BadgeLabel = BadgeLabel;
4418
+ exports.BottomSheet = BottomSheet;
4296
4419
  exports.Breadcrumb = Breadcrumb;
4297
4420
  exports.BreadcrumbItem = BreadcrumbItem;
4298
4421
  exports.BreadcrumbLink = BreadcrumbLink;
4299
4422
  exports.Button = Button;
4300
4423
  exports.Checkbox = Checkbox;
4301
- exports.ClickOutsideListener = ClickOutsideListener;
4424
+ exports.ClickOutsideListener = ClickOutsideListener$1;
4302
4425
  exports.Code = Code;
4303
4426
  exports.ColumnGroupHeader = ColumnGroupHeader;
4304
4427
  exports.ColumnHeader = ColumnHeader;
@@ -4316,6 +4439,7 @@ exports.DescriptionTerm = DescriptionTerm;
4316
4439
  exports.Dialog = Dialog;
4317
4440
  exports.DialogContent = DialogContent;
4318
4441
  exports.DialogFooter = DialogFooter;
4442
+ exports.Drawer = Drawer;
4319
4443
  exports.ExpandCollapsePanel = ExpandCollapsePanel;
4320
4444
  exports.FieldWrap = FieldWrap;
4321
4445
  exports.Icon = Icon;
@@ -0,0 +1,6 @@
1
+ import type { RefObject, MutableRefObject } from 'react';
2
+ /**
3
+ * When an element can be passed as a value that is either an element or an
4
+ * elementRef, this will resolve the property down to the resulting element
5
+ */
6
+ export default function resolveElement<T extends Element = Element>(elementOrRef: T | RefObject<T> | MutableRefObject<T> | undefined): T | null;
@@ -0,0 +1,17 @@
1
+ import { type DependencyList } from 'react';
2
+ /**
3
+ * When a component needs to implement an escape handler, such as in modal
4
+ * dialogs, useEscapeKey will handle the events and call the provided callback
5
+ * handler when an escape key event has been fired.
6
+ *
7
+ * @example
8
+ * useEscapeKey(() => close())
9
+ */
10
+ export default function useEscapeKey<T extends HTMLElement = HTMLElement>(options: {
11
+ active?: boolean;
12
+ callback: (event: KeyboardEvent) => void;
13
+ event?: 'keydown' | 'keypress' | 'keyup';
14
+ target?: T | React.RefObject<T> | React.MutableRefObject<T>;
15
+ defaultPrevented?: boolean;
16
+ capture?: boolean;
17
+ }, dependencies?: DependencyList): void;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@deque/cauldron-react",
3
- "version": "6.6.1-canary.db04cb91",
3
+ "version": "6.7.0-canary.099092f1",
4
4
  "license": "MPL-2.0",
5
5
  "description": "Fully accessible react components library for Deque Cauldron",
6
6
  "homepage": "https://cauldron.dequelabs.com/",