UNPKG

8 kBJavaScriptView Raw
1import { __rest } from "tslib";
2import * as React from 'react';
3import { css } from '@patternfly/react-styles';
4import { DropdownContext } from './dropdownConstants';
5import { KEYHANDLER_DIRECTION } from '../../helpers/constants';
6import { preventedEvents } from '../../helpers/util';
7import { Tooltip } from '../Tooltip';
8import styles from '@patternfly/react-styles/css/components/Dropdown/dropdown';
9export class InternalDropdownItem extends React.Component {
10 constructor() {
11 super(...arguments);
12 this.ref = React.createRef();
13 this.additionalRef = React.createRef();
14 this.getInnerNode = (node) => (node && node.childNodes && node.childNodes.length ? node.childNodes[0] : node);
15 this.onKeyDown = (event) => {
16 // Detected key press on this item, notify the menu parent so that the appropriate item can be focused
17 const innerIndex = event.target === this.ref.current ? 0 : 1;
18 if (!this.props.customChild) {
19 event.preventDefault();
20 }
21 if (event.key === 'ArrowUp') {
22 this.props.context.keyHandler(this.props.index, innerIndex, KEYHANDLER_DIRECTION.UP);
23 event.stopPropagation();
24 }
25 else if (event.key === 'ArrowDown') {
26 this.props.context.keyHandler(this.props.index, innerIndex, KEYHANDLER_DIRECTION.DOWN);
27 event.stopPropagation();
28 }
29 else if (event.key === 'ArrowRight') {
30 this.props.context.keyHandler(this.props.index, innerIndex, KEYHANDLER_DIRECTION.RIGHT);
31 event.stopPropagation();
32 }
33 else if (event.key === 'ArrowLeft') {
34 this.props.context.keyHandler(this.props.index, innerIndex, KEYHANDLER_DIRECTION.LEFT);
35 event.stopPropagation();
36 }
37 else if (event.key === 'Enter' || event.key === ' ') {
38 event.target.click();
39 this.props.enterTriggersArrowDown &&
40 this.props.context.keyHandler(this.props.index, innerIndex, KEYHANDLER_DIRECTION.DOWN);
41 }
42 };
43 this.componentRef = (element) => {
44 this.ref.current = element;
45 const { component } = this.props;
46 const ref = component.ref;
47 if (ref) {
48 if (typeof ref === 'function') {
49 ref(element);
50 }
51 else {
52 ref.current = element;
53 }
54 }
55 };
56 }
57 componentDidMount() {
58 const { context, index, isDisabled, role, customChild, autoFocus } = this.props;
59 const customRef = customChild ? this.getInnerNode(this.ref.current) : this.ref.current;
60 context.sendRef(index, [customRef, customChild ? customRef : this.additionalRef.current], isDisabled, role === 'separator');
61 autoFocus && setTimeout(() => customRef.focus());
62 }
63 componentDidUpdate() {
64 const { context, index, isDisabled, role, customChild } = this.props;
65 const customRef = customChild ? this.getInnerNode(this.ref.current) : this.ref.current;
66 context.sendRef(index, [customRef, customChild ? customRef : this.additionalRef.current], isDisabled, role === 'separator');
67 }
68 extendAdditionalChildRef() {
69 const { additionalChild } = this.props;
70 return React.cloneElement(additionalChild, {
71 ref: this.additionalRef
72 });
73 }
74 render() {
75 /* eslint-disable @typescript-eslint/no-unused-vars */
76 const _a = this.props, { className, children, isHovered, context, onClick, component, role, isDisabled, isAriaDisabled, isPlainText, index, href, tooltip, tooltipProps, id, componentID, listItemClassName, additionalChild, customChild, enterTriggersArrowDown, icon, autoFocus, styleChildren, description, inoperableEvents } = _a, additionalProps = __rest(_a, ["className", "children", "isHovered", "context", "onClick", "component", "role", "isDisabled", "isAriaDisabled", "isPlainText", "index", "href", "tooltip", "tooltipProps", "id", "componentID", "listItemClassName", "additionalChild", "customChild", "enterTriggersArrowDown", "icon", "autoFocus", "styleChildren", "description", "inoperableEvents"]);
77 /* eslint-enable @typescript-eslint/no-unused-vars */
78 let classes = css(icon && styles.modifiers.icon, isAriaDisabled && styles.modifiers.ariaDisabled, className);
79 if (component === 'a') {
80 additionalProps['aria-disabled'] = isDisabled || isAriaDisabled;
81 }
82 else if (component === 'button') {
83 additionalProps['aria-disabled'] = isDisabled || isAriaDisabled;
84 additionalProps.type = additionalProps.type || 'button';
85 }
86 const renderWithTooltip = (childNode) => tooltip ? (React.createElement(Tooltip, Object.assign({ content: tooltip }, tooltipProps), childNode)) : (childNode);
87 const renderClonedComponent = (element) => React.cloneElement(element, Object.assign(Object.assign({}, (styleChildren && {
88 className: css(element.props.className, classes)
89 })), (this.props.role !== 'separator' && { ref: this.componentRef })));
90 const renderDefaultComponent = (tag) => {
91 const Component = tag;
92 const componentContent = description ? (React.createElement(React.Fragment, null,
93 React.createElement("div", { className: styles.dropdownMenuItemMain },
94 icon && React.createElement("span", { className: css(styles.dropdownMenuItemIcon) }, icon),
95 children),
96 React.createElement("div", { className: styles.dropdownMenuItemDescription }, description))) : (React.createElement(React.Fragment, null,
97 icon && React.createElement("span", { className: css(styles.dropdownMenuItemIcon) }, icon),
98 children));
99 return (React.createElement(Component, Object.assign({}, additionalProps, (isDisabled || isAriaDisabled ? preventedEvents(inoperableEvents) : null), { href: href, ref: this.ref, className: classes, id: componentID }), componentContent));
100 };
101 return (React.createElement(DropdownContext.Consumer, null, ({ onSelect, itemClass, disabledClass, plainTextClass }) => {
102 if (this.props.role !== 'separator') {
103 classes = css(classes, isDisabled && disabledClass, isPlainText && plainTextClass, itemClass, description && styles.modifiers.description);
104 }
105 if (customChild) {
106 return React.cloneElement(customChild, {
107 ref: this.ref,
108 onKeyDown: this.onKeyDown
109 });
110 }
111 return (React.createElement("li", { className: listItemClassName || null, role: role, onKeyDown: this.onKeyDown, onClick: (event) => {
112 if (!isDisabled && !isAriaDisabled) {
113 onClick(event);
114 onSelect(event);
115 }
116 }, id: id },
117 renderWithTooltip(React.isValidElement(component)
118 ? renderClonedComponent(component)
119 : renderDefaultComponent(component)),
120 additionalChild && this.extendAdditionalChildRef()));
121 }));
122 }
123}
124InternalDropdownItem.displayName = 'InternalDropdownItem';
125InternalDropdownItem.defaultProps = {
126 className: '',
127 isHovered: false,
128 component: 'a',
129 role: 'none',
130 isDisabled: false,
131 isPlainText: false,
132 tooltipProps: {},
133 // eslint-disable-next-line @typescript-eslint/no-unused-vars
134 onClick: (event) => undefined,
135 index: -1,
136 context: {
137 keyHandler: () => { },
138 sendRef: () => { }
139 },
140 enterTriggersArrowDown: false,
141 icon: null,
142 styleChildren: true,
143 description: null,
144 inoperableEvents: ['onClick', 'onKeyPress']
145};
146//# sourceMappingURL=InternalDropdownItem.js.map
\No newline at end of file