import React from 'react';
import { connect } from 'react-redux';

import remove from 'lodash/remove';
import map from 'lodash/map';
import some from 'lodash/some';
import filter from 'lodash/filter';
import isArray from 'lodash/isArray';

import Immutable from 'immutable';
import classnames from 'classnames';

import SymbolAutocompleteMulti from '../../search/SymbolAutocompleteMulti';
import { fetchSources, fetchChannels } from 'actions/filters';
import { changeFilter } from 'actions/feeds';
import { channelService } from '../../../services';
import { applyFiltersToTags, applyTagsToFilters } from 'utils/feeds';
import { isPopout } from 'utils/popouts';

import Tabs from 'components/ui/Tabs';
import Tab from 'components/ui/Tab';
import Badge from 'components/ui/Badge';
import FilterTags from 'components/ui/modal/FilterTags';

class FeedToolbar extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      tags: [],
      showFilters: false
    };
  }

  componentDidMount() {
    const { dispatch } = this.props;
    dispatch(fetchSources());
    dispatch(fetchChannels());
  }

  componentWillReceiveProps(nextProps) {
    this.setState({tags: applyFiltersToTags(nextProps.filters, this.state.tags)});
  }

  onAddSymbol(sym, index) {
    const sList = applyFiltersToTags(this.props.filters);
    sList.splice(index, 0, sym);
    this.searchChange(sList);
  }
  onAddMultiSymbol(syms, index) {
    let sList = applyFiltersToTags(this.props.filters);
    sList = sList.concat(syms);
    this.searchChange(sList);
  }
  onRemoveSymbol(sym, index) {
    const sList = applyFiltersToTags(this.props.filters);
    remove(sList, sym);
    this.searchChange(sList);
  }

  setPopoutTitle() {
    const { sources, channels, filters } = this.props;

    const channelNames = [];
    const allChannels = channels.items.toArray();
    for (const selected of filters.channels) {
      for (const channel of allChannels) {
        if (selected === channel.id) {
          channelNames.push(channel.name);
          continue;
        }
      }
    }
    const sourceNames = map(this.props.filters.contentType, (ct) => channelService.sourceIdToName(ct));
    const watchlistNames = map(this.props.watchlists, 'name');
    const title = [...channelNames, ...sourceNames, ...watchlistNames].join(' + ');
    document.title = title;
  }

  searchChange(tags) {
    changeFilter(this.props.widgetId, applyTagsToFilters(tags, this.props.filters), isPopout());
  }

  toggleFilter() {
    this.setState({showFilters: !this.state.showFilters});
  }

  clearAllFilters(input) {
    const selectedIndex = input.state.selectedIndex;
    const TabsComponent = input.props.children[selectedIndex].props;
    const label = TabsComponent.label;
    const selectedTab = TabsComponent.children.props;
    // console.log(label + ' before', this, selectedTab.selected);
    this.props.filters[selectedTab.filterType] = [];
    // console.log(label + ' after', this, selectedTab.selected);
  }

  filtersBackgroundClick(e) {
    if (e.target === this.refs.filtersBackground) {
      this.toggleFilter();
    }
  }

  totalFilters() {
    const { filters } = this.props;
    const numCategories = filters.channels.length;
    const numSources = filters.contentType.length;
    const numWatchlists = filters.watchlists.length;
    const length = numCategories + numSources + numWatchlists;

    return this.renderBadge(length);
  }

  numberSelected(selected) {
    const length = selected.length;

    return this.renderBadge(length);
  }

  renderBadge(length) {
    return length > 0 ? (<Badge number={length} />) : '';
  }

  renderFilterMenu() {
    const { channels, dispatch, filters, sources, watchlists, widgetId } = this.props;

    function onChangeHelper(type, values) {
      let selected = values;
      if (some(selected, isArray)) {
        let allSelected = new Immutable.Set();
        for (const array of selected) {
          for (const value of array) {
            allSelected = allSelected.add(value);
          }
        }
        selected = allSelected.toJS();
      }
      changeFilter(widgetId, Object.assign({}, filters, {key: selected}), isPopout());
    }

    if (this.state.showFilters) {
      return (
        <div className="WidgetModal" ref="filtersBackground" onClick={(e) => this.filtersBackgroundClick(e)}>
          <div className="WidgetModal-box">

            <div className="WidgetModal-header">
              Click on filters to apply them to your newsfeed
              <i className="bzpro-icon-close" onClick={() => this.toggleFilter()}></i>
            </div>

            <Tabs ref="Tabs">
              <Tab label={'categories'} badge={this.numberSelected(filters.channels)}>
                <FilterTags
                  filterType={'channels'}
                  getName={(channel) => channel.name}
                  onChange={(selected) => onChangeHelper('channels', selected)}
                  selected={filters.channels}
                  sources={channels.items.toJS()}
                />
              </Tab>
              <Tab label={'sources'} badge={this.numberSelected(filters.contentType)}>
                <FilterTags /* TODO change all references to 'contentType' to 'sources' */
                  filterType={'contentType'}
                  getName={(source) => channelService.sourceIdToName(source.id) /* TODO Change to .name */}
                  onChange={(selected) => onChangeHelper('contentType', selected)}
                  selected={filters.contentType}
                  sources={sources.contentTypes.toJS()}
                />
              </Tab>
              <Tab label={'watchlists'} badge={this.numberSelected(filters.watchlists)}>
                <FilterTags
                  filterType={'watchlists'}
                  getName={(watchlist) => watchlist.name}
                  onChange={(selected) => onChangeHelper('watchlists', selected)}
                  selected={filters.watchlists}
                  sources={watchlists}
                />
              </Tab>
            </Tabs>

            <div className="FilterTags-footer">
              {/* <button onClick={() => this.clearAllFilters(this.refs.Tabs)}>clear all</button> */}
              {/* <button onClick={() => this.clearAllFilters(this.refs.Tabs)}>select all</button> */}
              <button className="Button Button--blue" onClick={() => this.toggleFilter()}>Done</button>
            </div>
          </div>
        </div>
      );
    }
  }

  render() {
    if (isPopout()) { this.setPopoutTitle(); }

    return (
      <div>
        <div className="WidgetSearch WidgetSearch--newsfeed" ref="bar">
          <SymbolAutocompleteMulti
            symbols={this.state.tags}
            onAddSymbol={(data, index) => this.onAddSymbol(data, index)}
            onAddMultiSymbol={(data, index) => this.onAddMultiSymbol(data, index)}
            onRemoveSymbol={(data, index) => this.onRemoveSymbol(data, index)}
            multiPlaceholder="Search by symbol or keyword..."
            allowKeywords
          />
          <button className="WidgetSearch-btn WidgetSearch-btn--text" onClick={() => this.toggleFilter()}>Filters {this.totalFilters()}</button>
        </div>
        {this.renderFilterMenu()}
      </div>
    );
  }
}

FeedToolbar.propTypes = {
  channels: React.PropTypes.object.isRequired,
  dispatch: React.PropTypes.func.isRequired,
  filters: React.PropTypes.object,
  sources: React.PropTypes.object.isRequired,
  watchlists: React.PropTypes.object.isRequired,
  widgetId: React.PropTypes.number
};

function mapStateToProps(state) {
  return {
    sources: state.sources,
    channels: state.channels,
    watchlists: state.watchlists.watchlists.toJS()
  };
}

export default connect(mapStateToProps)(FeedToolbar);
