All files / app/components Selectable.tsx

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86                            16x         16x               16x     16x     16x       16x           75x       105x             105x                         75x 8x 8x     8x   8x     75x       75x        
import React from 'react';
import { style } from 'app/styles';
import { TestProps } from 'app/interfaces';
 
export interface MenuItemProps {
  // The children are the menu content
  children: string | JSX.Element | JSX.Element[];
  onClick: (evt, value?) => void;
  onDoubleClick?: (evt, value?) => void;
  value?: any;
  style?: string | object;
  disabled?: boolean;
  selected?: boolean;
}
const initialState = {
  isHovering: false,
};
type MenuItemState = Readonly<typeof initialState>;
 
const containerStyle = {
  _extends: ['normalText'],
  padding: 5,
  // this keeps the card from moving on hover, but
  // won't show a border regardless of background color
  // when not hovering
  border: '1px solid transparent',
};
const hoverContainerStyle = {
  _extends: [containerStyle, 'selectable'],
};
const disabledContainerStyle = {
  _extends: [containerStyle, 'disabledText'],
};
const selectedContainerStyle = {
  _extends: [containerStyle, 'selected'],
};
 
const DOUBLE_CLICK_DELAY_MS = 500;
 
export class Selectable extends React.Component<
  MenuItemProps & TestProps,
  MenuItemState
> {
  readonly state: MenuItemState = initialState;
  private lastClick: number;
 
  render() {
    const outerStyle = this.props.disabled
      ? disabledContainerStyle
      : this.props.selected
        ? selectedContainerStyle
        : this.state.isHovering
          ? hoverContainerStyle
          : containerStyle;
    return (
      <div
        style={style(outerStyle, this.props.style)}
        onClick={this.onClick}
        onMouseOver={this.onMouseOver}
        onMouseLeave={this.onMouseLeave}
        data-testid={this.props.testId}
      >
        {this.props.children}
      </div>
    );
  }
 
  private onClick = evt => {
    const now = Date.now();
    Iif (this.lastClick && now - this.lastClick <= DOUBLE_CLICK_DELAY_MS) {
      this.props.onDoubleClick(evt, this.props.value);
    } else {
      this.props.onClick(evt, this.props.value);
    }
    this.lastClick = now;
  };
 
  private onMouseOver = () => {
    this.setState({ isHovering: true });
  };
 
  private onMouseLeave = () => {
    this.setState({ isHovering: false });
  };
}