You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

ContextMenuItem.tsx 3.8KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166
  1. import React, { ReactNode } from 'react';
  2. import { useSelector } from 'react-redux';
  3. import { makeStyles } from 'tss-react/mui';
  4. import { showOverflowDrawer } from '../../../../toolbox/functions.web';
  5. import Icon from '../../../icons/components/Icon';
  6. import { withPixelLineHeight } from '../../../styles/functions.web';
  7. export interface IProps {
  8. /**
  9. * Label used for accessibility.
  10. */
  11. accessibilityLabel: string;
  12. /**
  13. * CSS class name used for custom styles.
  14. */
  15. className?: string;
  16. /**
  17. * Custom icon. If used, the icon prop is ignored.
  18. * Used to allow custom children instead of just the default icons.
  19. */
  20. customIcon?: ReactNode;
  21. /**
  22. * Whether or not the action is disabled.
  23. */
  24. disabled?: boolean;
  25. /**
  26. * Default icon for action.
  27. */
  28. icon?: Function;
  29. /**
  30. * Id of the action container.
  31. */
  32. id?: string;
  33. /**
  34. * Click handler.
  35. */
  36. onClick?: (e?: React.MouseEvent) => void;
  37. /**
  38. * Keydown handler.
  39. */
  40. onKeyDown?: (e?: React.KeyboardEvent) => void;
  41. /**
  42. * Keypress handler.
  43. */
  44. onKeyPress?: (e?: React.KeyboardEvent) => void;
  45. /**
  46. * TestId of the element, if any.
  47. */
  48. testId?: string;
  49. /**
  50. * Action text.
  51. */
  52. text: string;
  53. /**
  54. * Class name for the text.
  55. */
  56. textClassName?: string;
  57. }
  58. const useStyles = makeStyles()(theme => {
  59. return {
  60. contextMenuItem: {
  61. alignItems: 'center',
  62. cursor: 'pointer',
  63. display: 'flex',
  64. minHeight: '40px',
  65. padding: '10px 16px',
  66. boxSizing: 'border-box',
  67. '& > *:not(:last-child)': {
  68. marginRight: theme.spacing(3)
  69. },
  70. '&:hover': {
  71. backgroundColor: theme.palette.ui02
  72. },
  73. '&:active': {
  74. backgroundColor: theme.palette.ui03
  75. },
  76. '&:focus': {
  77. boxShadow: `inset 0 0 0 2px ${theme.palette.action01Hover}`
  78. }
  79. },
  80. contextMenuItemDisabled: {
  81. pointerEvents: 'none'
  82. },
  83. contextMenuItemDrawer: {
  84. padding: '13px 16px'
  85. },
  86. contextMenuItemIcon: {
  87. '& svg': {
  88. fill: theme.palette.icon01
  89. }
  90. },
  91. text: {
  92. ...withPixelLineHeight(theme.typography.bodyShortRegular),
  93. color: theme.palette.text01
  94. },
  95. drawerText: {
  96. ...withPixelLineHeight(theme.typography.bodyShortRegularLarge)
  97. }
  98. };
  99. });
  100. const ContextMenuItem = ({
  101. accessibilityLabel,
  102. className,
  103. customIcon,
  104. disabled,
  105. id,
  106. icon,
  107. onClick,
  108. onKeyDown,
  109. onKeyPress,
  110. testId,
  111. text,
  112. textClassName }: IProps) => {
  113. const { classes: styles, cx } = useStyles();
  114. const _overflowDrawer: boolean = useSelector(showOverflowDrawer);
  115. return (
  116. <div
  117. aria-disabled = { disabled }
  118. aria-label = { accessibilityLabel }
  119. className = { cx(styles.contextMenuItem,
  120. _overflowDrawer && styles.contextMenuItemDrawer,
  121. disabled && styles.contextMenuItemDisabled,
  122. className
  123. ) }
  124. data-testid = { testId }
  125. id = { id }
  126. key = { text }
  127. onClick = { disabled ? undefined : onClick }
  128. onKeyDown = { disabled ? undefined : onKeyDown }
  129. onKeyPress = { disabled ? undefined : onKeyPress }>
  130. {customIcon ? customIcon
  131. : icon && <Icon
  132. className = { styles.contextMenuItemIcon }
  133. size = { 20 }
  134. src = { icon } />}
  135. <span className = { cx(styles.text, textClassName) }>{text}</span>
  136. </div>
  137. );
  138. };
  139. export default ContextMenuItem;