import classNames from 'classnames';
import React, { PropTypes } from 'react';
import { DragSource, DropTarget } from 'react-dnd';
import { findDOMNode } from 'react-dom';

import KdItemSelected from '../KdItemSelected';
import { ASC } from '../../constants';

const defaultProps = {
  isChickletNone: false,
  isLoading: false,
  hasMainSelector: false,
  autocompleteVisible: false,
  draggable: false,
  direction: ASC,
  renderClearTextboxButton: false,
  chicklets: {
    sortable: true,
    visible: true,
    fullwidth: true,
    buttons: {
      ascDesc: { visible: false },
      info: { visible: false },
    },
    events: {},
    clearAll: { visible: false },
  },
};

const propTypes = {
  theme: PropTypes.oneOfType([
    PropTypes.object,
    PropTypes.func,
  ]).isRequired,
  connectDragSource: PropTypes.func,
  connectDropTarget: PropTypes.func,
  index: PropTypes.number,
  isDragging: PropTypes.bool,
  moveCard: PropTypes.func,
  chicklets: PropTypes.shape({
    sortable: PropTypes.bool,
    visible: PropTypes.bool,
    fullwidth: PropTypes.bool,
    prefix: PropTypes.string,

    buttons: PropTypes.shape({
      ascDesc: PropTypes.shape({ visible: PropTypes.bool }),
      info: PropTypes.shape({ visible: PropTypes.bool }),
    }),

    events: PropTypes.shape({
      onClick: PropTypes.func,
      onClose: PropTypes.func,
    }),

    clearAll: PropTypes.shape({
      visible: PropTypes.bool,
      onClick: PropTypes.func,
    }),
  }),
};

const itemSource = {
  beginDrag({ value, index }) {
    return {
      id: value,
      index,
    };
  },
  endDrag(props) {
    if (props.chicklets.events.onDrop) {
      props.chicklets.events.onDrop();
    }
  },
};

const itemTarget = {
  hover(props, monitor, component) {
    const dragIndex = monitor.getItem().index;
    const hoverIndex = props.index;

    // Don't replace items with themselves
    if (dragIndex === hoverIndex) {
      return;
    }

    // Determine rectangle on screen
    const hoverBoundingRect = findDOMNode(component).getBoundingClientRect();

    // Get vertical middle
    const hoverMiddleY = (hoverBoundingRect.bottom - hoverBoundingRect.top) / 2;

    // Determine mouse position
    const clientOffset = monitor.getClientOffset();

    // Get pixels to the top
    const hoverClientY = clientOffset.y - hoverBoundingRect.top;

    // Dragging downwards
    if (dragIndex < hoverIndex && hoverClientY < hoverMiddleY) {
      return;
    }

    // Dragging upwards
    if (dragIndex > hoverIndex && hoverClientY > hoverMiddleY) {
      return;
    }

    props.moveCard(dragIndex, hoverIndex);
    monitor.getItem().index = hoverIndex;
  },
};

@DropTarget('KdItemSelectedDraggable', itemTarget, connect => ({
  connectDropTarget: connect.dropTarget()
}))

@DragSource('KdItemSelectedDraggable', itemSource, (connect, monitor) => ({
  connectDragSource: connect.dragSource(),
  isDragging: monitor.isDragging()
}))

class KdItemSelectedDraggable extends React.Component {

  render() {
    const { isDragging, connectDragSource, connectDropTarget, theme, chicklets } = this.props;
    const opacity = isDragging ? 0 : 1;
    return connectDragSource(connectDropTarget(
      <div className={
        classNames(
          'c-kd-item-selected-draggable',
          theme['c-kd-item-selected-draggable'],
          { ['c-kd-item-selected-draggable__inline']: chicklets.fullwidth === false },
          { [theme['c-kd-item-selected-draggable__inline']]: chicklets.fullwidth === false },
        )}
        style={{ opacity }}>
        <div className={classNames('c-kd-item-selected-draggable__icon-container', theme['c-kd-item-selected-draggable__icon-container'])}>
          <span className={classNames('c-kd-item-selected-draggable__sort-icon', theme['c-kd-item-selected-draggable__sort-icon'])} />
        </div>
        <KdItemSelected {...this.props} draggable />
      </div>
    ));
  }
}

KdItemSelectedDraggable.propTypes = propTypes;
KdItemSelectedDraggable.defaultProps = defaultProps;

export default KdItemSelectedDraggable;
