dates_array = require('./dates_array.coffee')
_ = require('lodash')
filters = require('../../common/js/filters.coffee')
bench = require('../../common/js/bench.coffee')
moment = require('moment')
# {direct: {prices: {date: price, date2: price2, … }, max: 4000}, return: ...}

column_percent = (price, max_price) ->
  if price and max_price and max_price > 0
    _.min([Math.round(((price or 0)/ max_price) * 100), 100])
  else
    60

column_state = (column_date, selected_date, price) ->
  if column_date == selected_date
    'calendar-bar-current'
  else if price == null or price == undefined
    'calendar-bar-unknown'
  else
    ''

format_rank = (num) ->
  if num >= 1000000000
    return (num / 1000000000).toFixed(1).replace(/\.0$/, '') + 'мм'
  if num >= 1000000
    return (num / 1000000).toFixed(1).replace(/\.0$/, '') + 'м'
  if num >= 1000
    return (num / 1000).toFixed(1).replace(/\.0$/, '') + 'к'
  num

present_columns = (prices_info, selected_day) ->
  week_days = __('datepicker.days')
  week_days.unshift(week_days[week_days.length - 1])
  columns = []
  max_price = normalize_max_price(prices_info.max)
  for [date_str, week_day] in dates_array()
    columns.push({
      date: date_str
      height: column_percent(prices_info.prices[date_str], max_price)
      price: prices_info.prices[date_str] || ''
      day: +date_str.split('-')[2]
      state_class: column_state(date_str, selected_day, prices_info.prices[date_str])
      weekend_class: if week_day == 0 or week_day == 6 then 'calendar-day-weekend' else ''
      week_day_name:  week_days[week_day].toLowerCase()
    })
  columns

format_price = (value, rate) ->
  price_in_currency = Math.round(value / rate)
  filters.split_price(price_in_currency)

format_date = (date) ->
  moment(date, 'YYYY-MM-DD').format('D MMM YYYY')

normalize_max_price = (price) ->
  price_str = Math.ceil(price * 1.3).toString()

  digit_count = if price_str.length < 3 then 1 else 2

  first_digits = parseInt(price_str.substring(0, digit_count), 10)
  multiplier = Math.pow(10, price_str.length - digit_count)

  (first_digits + 1) * multiplier

calculate_shift = (start_date) ->
  one_row_width = 30 #px
  days_diff = moment(start_date, 'YYYY-MM-DD').diff(moment().startOf('day'), 'days')
  days_diff * one_row_width

capitalize_first_letter = (string) -> string.charAt(0).toUpperCase() + string.slice(1)

calculate_months = (start_date_str) ->
  month_translations = __('datepicker.months')
  start_date = moment(start_date_str, 'YYYY-MM-DD')
  end_date = moment(start_date).add(13, 'days')
  result =
    left_month: capitalize_first_letter(month_translations[start_date.month() + 1])
    right_month: capitalize_first_letter(month_translations[end_date.month() + 1])

  if start_date.month() == end_date.month()
    result.month_state = 'state-0'
  else
    result.month_state = "state-#{moment(start_date).endOf('month').startOf('day').diff(start_date, 'days') + 1}"

  result

retreive_cities = (segment) ->
  origin_name: segment.origin_name or segment.origin
  destination_name: segment.destination_name or segment.destination

left_arrow_class = (start_date) ->
  if moment().format('YYYY-MM-DD') == start_date then 'arrow-inactive' else ''

right_arrow_class = (start_date) ->
  cal_last_day = moment().startOf('day').add(365, 'days')
  view_last_day = moment(start_date, 'YYYY-MM-DD').add(13, 'days')
  if cal_last_day.isSame(view_last_day) then 'arrow-inactive' else ''

module.exports = (dictionaries) ->
  adapt_total: (price) ->
    if price
      price: format_price(price, dictionaries.currencies[dictionaries.currency])
      currency: dictionaries.currency
    else
      false

  adapt_hover: ({direct_date, return_date}, price) ->
    result =
      price: if price then format_price(price, dictionaries.currencies[dictionaries.currency]) else '?'
      button_text: if price then 'Найти' else 'Узнать цену'

    if direct_date
      result.depart_date = format_date(direct_date)

    if return_date
      result.return_date = {value: format_date(return_date)}

    result.total = @adapt_total(price)
    result.no_total = !result.total # For temple :/

    result

  adapt: bench('min price presenter', (direction_info, selected_days, start_days) ->
    price = direction_info.direct?.prices[selected_days.direct] or direction_info.return?.prices[selected_days.return]
    result = {
      rows: []
      depart_date: format_date(selected_days.direct)
      button_text: if price then 'Найти' else 'Узнать цену'
    }

    result.return_date = if selected_days.return? then {'value': format_date(selected_days.return)} else false

    # Selected does not change on hover (original dates not formated for display)
    result.selected =
      price: price || ''
      depart_date: selected_days.direct
      return_date: selected_days.return || '' # Temple likes empty strings instead of null or false in attributes

    # For total price block display
    result.total = @adapt_total(price)
    result.no_total = !result.total # For temple :/

    for direction, prices_info of direction_info

      {month_state, left_month, right_month} = calculate_months(start_days[direction])
      {origin_name, destination_name} = retreive_cities(dictionaries.search_params.segments[{'direct': 0, 'return' : 1}[direction]])
      max_price = Math.round(prices_info.max / dictionaries.currencies[dictionaries.currency])
      normalized_max_price = normalize_max_price(max_price)
      result.rows.push({
        origin_name: origin_name
        destination_name: destination_name
        direction: direction
        columns: present_columns(prices_info, selected_days[direction])
        normalize_max: format_rank(normalized_max_price)
        normalize_mid: format_rank(normalized_max_price / 2.0)
        shift: calculate_shift(start_days[direction])
        month_state: month_state
        left_month: left_month
        right_month: right_month
        left_arrow_class: left_arrow_class(start_days[direction])
        right_arrow_class: right_arrow_class(start_days[direction])
      })
    result
  )
