1
0

dropdownItem.tsx 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110
  1. import React from 'react';
  2. import cls from 'classnames';
  3. import PropTypes from 'prop-types';
  4. import { cssClasses as css, strings } from '@douyinfe/semi-foundation/dropdown/constants';
  5. import DropdownContext from './context';
  6. import BaseComponent from '../_base/baseComponent';
  7. import { IconTick } from '@douyinfe/semi-icons';
  8. import { noop } from 'lodash';
  9. import type { BaseProps } from '../_base/baseComponent';
  10. import type { DropdownContextType } from './context';
  11. export type Type = 'primary' | 'secondary' | 'tertiary' | 'warning' | 'danger';
  12. export interface DropdownItemProps extends BaseProps {
  13. disabled?: boolean;
  14. selected?: boolean;
  15. onClick?: React.MouseEventHandler<HTMLLIElement>;
  16. onMouseEnter?: React.MouseEventHandler<HTMLLIElement>;
  17. onMouseLeave?: React.MouseEventHandler<HTMLLIElement>;
  18. onContextMenu?: React.MouseEventHandler<HTMLLIElement>;
  19. forwardRef?: (ele: HTMLLIElement) => void;
  20. type?: Type;
  21. active?: boolean;
  22. icon?: React.ReactNode;
  23. onKeyDown?: (e: React.KeyboardEvent) => void;
  24. }
  25. const prefixCls = css.PREFIX;
  26. class DropdownItem extends BaseComponent<DropdownItemProps> {
  27. static propTypes = {
  28. children: PropTypes.oneOfType([PropTypes.string, PropTypes.node]),
  29. name: PropTypes.string,
  30. disabled: PropTypes.bool,
  31. selected: PropTypes.bool,
  32. onClick: PropTypes.func,
  33. onMouseEnter: PropTypes.func,
  34. onMouseLeave: PropTypes.func,
  35. onContextMenu: PropTypes.func,
  36. className: PropTypes.string,
  37. style: PropTypes.object,
  38. forwardRef: PropTypes.func,
  39. type: PropTypes.oneOf(strings.ITEM_TYPE),
  40. active: PropTypes.bool,
  41. icon: PropTypes.node
  42. };
  43. static contextType = DropdownContext;
  44. context: DropdownContextType;
  45. static defaultProps = {
  46. disabled: false,
  47. divided: false,
  48. selected: false,
  49. onMouseEnter: noop,
  50. onMouseLeave: noop,
  51. forwardRef: noop,
  52. };
  53. render() {
  54. const { children, disabled, className, forwardRef, style, type, active, icon, onKeyDown } = this.props;
  55. const { showTick } = this.context;
  56. const itemclass = cls(className, {
  57. [`${prefixCls}-item`]: true,
  58. [`${prefixCls}-item-disabled`]: disabled,
  59. [`${prefixCls}-item-withTick`]: showTick,
  60. [`${prefixCls}-item-${type}`]: type,
  61. [`${prefixCls}-item-active`]: active,
  62. });
  63. const events = {};
  64. if (!disabled) {
  65. ['onClick', 'onMouseEnter', 'onMouseLeave', 'onContextMenu'].forEach(eventName => {
  66. events[eventName] = this.props[eventName];
  67. });
  68. }
  69. let tick = null;
  70. switch (true) {
  71. case showTick && active:
  72. tick = <IconTick />;
  73. break;
  74. case showTick && !active:
  75. tick = <IconTick style={{ color: 'transparent' }} />;
  76. break;
  77. default:
  78. tick = null;
  79. break;
  80. }
  81. let iconContent = null;
  82. if (icon) {
  83. iconContent = (
  84. <div className={`${prefixCls}-item-icon`}>
  85. {icon}
  86. </div>
  87. );
  88. }
  89. return (
  90. <li role="menuitem" tabIndex={-1} aria-disabled={disabled} {...events} onKeyDown={onKeyDown} ref={ref => forwardRef(ref)} className={itemclass} style={style}>
  91. {tick}
  92. {iconContent}
  93. {children}
  94. </li>
  95. );
  96. }
  97. }
  98. export default DropdownItem;