'use strict';

Object.defineProperty(exports, '__esModule', { value: true });

var _rollupPluginBabelHelpers = require('../../../_virtual/_rollupPluginBabelHelpers.js');

var getColumnsFromFormat = function getColumnsFromFormat(format, multiplicityMinutes, multiplicitySeconds) {
  var parts = format.split(':');
  var columns = [];
  parts.forEach(function (part) {
    switch (part) {
      case 'HH':
        columns.push({
          type: 'hours',
          values: range(24),
          format: 'HH'
        });
        break;
      case 'mm':
        columns.push({
          type: 'minutes',
          values: range(60, 2, multiplicityMinutes !== null && multiplicityMinutes !== void 0 ? multiplicityMinutes : 1),
          format: 'mm'
        });
        break;
      case 'ss':
        columns.push({
          type: 'seconds',
          values: range(60, 2, multiplicitySeconds !== null && multiplicitySeconds !== void 0 ? multiplicitySeconds : 1),
          format: 'ss'
        });
        break;
    }
  });
  return columns;
};
var parseTimeString = function parseTimeString(timeString, format) {
  var timeParts = timeString.split(':');
  var formatParts = format.split(':');
  var result = {
    hh: null,
    mm: null,
    ss: null
  };
  formatParts.forEach(function (part, index) {
    var value = timeParts[index] ? parseInt(timeParts[index], 10) : null;
    switch (part) {
      case 'HH':
        result.hh = value;
        break;
      case 'mm':
        result.mm = value;
        break;
      case 'ss':
        result.ss = value;
        break;
    }
  });
  return result;
};
var buildTimeString = function buildTimeString(timeValues, format) {
  var formatParts = format.split(':');
  return formatParts.map(function (part) {
    switch (part) {
      case 'HH':
        return timeValues.hh !== null ? timeValues.hh.toString().padStart(2, '0') : '00';
      case 'mm':
        return timeValues.mm !== null ? timeValues.mm.toString().padStart(2, '0') : '00';
      case 'ss':
        return timeValues.ss !== null ? timeValues.ss.toString().padStart(2, '0') : '00';
      default:
        return '00';
    }
  }).join(':');
};
var isTimeDisabled = function isTimeDisabled(timeValues, min, max, format) {
  if (!min && !max) return false;
  if (timeValues.hh === null || timeValues.mm === null || timeValues.ss === null) {
    return false;
  }
  var totalSeconds = timeValues.hh * 3600 + timeValues.mm * 60 + timeValues.ss;
  var minSeconds = 0;
  var maxSeconds = 23 * 3600 + 59 * 60 + 59;
  if (min) {
    if (min instanceof Date) {
      minSeconds = min.getHours() * 3600 + min.getMinutes() * 60 + min.getSeconds();
    } else {
      var minTime = parseTimeString(min, format !== null && format !== void 0 ? format : 'HH:mm:ss');
      minSeconds = (minTime.hh || 0) * 3600 + (minTime.mm || 0) * 60 + (minTime.ss || 0);
    }
  }
  if (max) {
    if (max instanceof Date) {
      maxSeconds = max.getHours() * 3600 + max.getMinutes() * 60 + max.getSeconds();
    } else {
      var maxTime = parseTimeString(max, format !== null && format !== void 0 ? format : 'HH:mm:ss');
      maxSeconds = (maxTime.hh || 0) * 3600 + (maxTime.mm || 0) * 60 + (maxTime.ss || 0);
    }
  }
  return totalSeconds < minSeconds || totalSeconds > maxSeconds;
};
var range = function range(number) {
  var padLength = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 2;
  var step = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 1;
  if (step > number) step = number;
  return Array.from({
    length: Math.ceil(number / step)
  }, function (_, i) {
    return (i * step).toString().padStart(padLength, '0');
  });
};
var roundToMultiplicity = function roundToMultiplicity(value, step) {
  if (!step || step <= 1) return value;
  return Math.round(value / step) * step;
};

/**
 * Разбирает границу времени (min/max) в объект TimeValues.
 * Принимает строку в формате HH:mm / HH:mm:ss или объект Date.
 */
var parseTimeBoundary = function parseTimeBoundary(val, format) {
  if (!val) {
    return null;
  }
  if (val instanceof Date) {
    return {
      hh: val.getHours(),
      mm: val.getMinutes(),
      ss: val.getSeconds()
    };
  }
  return parseTimeString(val, format);
};

/**
 * Переводит TimeValues в количество секунд с начала суток.
 * null-значения трактуются как 0.
 */
var toTotalSeconds = function toTotalSeconds(timeValues) {
  var _timeValues$hh, _timeValues$mm, _timeValues$ss;
  return ((_timeValues$hh = timeValues.hh) !== null && _timeValues$hh !== void 0 ? _timeValues$hh : 0) * 3600 + ((_timeValues$mm = timeValues.mm) !== null && _timeValues$mm !== void 0 ? _timeValues$mm : 0) * 60 + ((_timeValues$ss = timeValues.ss) !== null && _timeValues$ss !== void 0 ? _timeValues$ss : 0);
};

/**
 * Прижимает время к нижней границе (min) с учётом кратности.
 *
 *  1. При выборе часа корректируем минуты до ближайшей кратной ≥ min.mm.
 *     Если кратная ≥ 60 — оставляем как есть; isTimeDisabled отклонит клик.
 *  2. Если итоговое время всё ещё < min — корректируем секунды до ближайшей кратной ≥ min.ss.
 *     При переполнении секунд (clamped ≥ 60) переходим на следующую кратную минуту с ss=0.
 *     Если и nextMM ≥ 60 — isTimeDisabled отклонит клик.
 */
var clampTimeToMin = function clampTimeToMin(timeValues, minParsed, column, activeFormat) {
  var _minParsed$ss, _result$mm;
  var multiplicityMinutes = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : 1;
  var multiplicitySeconds = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : 1;
  var result = _rollupPluginBabelHelpers.objectSpread2({}, timeValues);

  /**
   * Корректируем минуты (только при выборе часа)
   */
  if (column === 'hours' && activeFormat.includes('mm')) {
    var _minParsed$mm;
    var clamped = Math.ceil(((_minParsed$mm = minParsed.mm) !== null && _minParsed$mm !== void 0 ? _minParsed$mm : 0) / multiplicityMinutes) * multiplicityMinutes;
    if (clamped < 60) {
      result.mm = clamped;
    }
  }

  /**
   * Корректируем секунды
   */
  if (!activeFormat.includes('ss') || toTotalSeconds(result) >= toTotalSeconds(minParsed)) {
    return result;
  }
  var clampedSS = Math.ceil(((_minParsed$ss = minParsed.ss) !== null && _minParsed$ss !== void 0 ? _minParsed$ss : 0) / multiplicitySeconds) * multiplicitySeconds;
  if (clampedSS < 60) {
    result.ss = clampedSS;
    return result;
  }

  /**
   * Переполнение секунд: переходим на следующую кратную минуту, ss → 0
   */
  var nextMM = ((_result$mm = result.mm) !== null && _result$mm !== void 0 ? _result$mm : 0) + multiplicityMinutes;
  if (nextMM < 60) {
    result.mm = nextMM;
    result.ss = 0;
  }
  return result;
};

/**
 * Прижимает время к верхней границе (max) с учётом кратности.
 *
 *  1. При выборе часа корректируем минуты до ближайшей кратной ≤ max.mm.
 *  2. Если итоговое время всё ещё > max — корректируем секунды до ближайшей кратной ≤ max.ss.
 */
var clampTimeToMax = function clampTimeToMax(timeValues, maxParsed, column, activeFormat) {
  var _maxParsed$ss;
  var multiplicityMinutes = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : 1;
  var multiplicitySeconds = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : 1;
  var result = _rollupPluginBabelHelpers.objectSpread2({}, timeValues);

  /**
   * Корректируем минуты (только при выборе часа)
   */
  if (column === 'hours' && activeFormat.includes('mm')) {
    var _maxParsed$mm;
    result.mm = Math.floor(((_maxParsed$mm = maxParsed.mm) !== null && _maxParsed$mm !== void 0 ? _maxParsed$mm : 0) / multiplicityMinutes) * multiplicityMinutes;
  }

  /**
   * Корректируем секунды
   */
  if (!activeFormat.includes('ss') || toTotalSeconds(result) <= toTotalSeconds(maxParsed)) {
    return result;
  }
  result.ss = Math.floor(((_maxParsed$ss = maxParsed.ss) !== null && _maxParsed$ss !== void 0 ? _maxParsed$ss : 0) / multiplicitySeconds) * multiplicitySeconds;
  return result;
};
var animateScrollTo = function animateScrollTo(element, targetScrollTop) {
  var duration = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 300;
  var startScrollTop = element.scrollTop;
  var distance = targetScrollTop - startScrollTop;
  var startTime = null;
  var animate = function animate(currentTime) {
    if (!startTime) startTime = currentTime;
    var timeElapsed = currentTime - startTime;
    var progress = Math.min(timeElapsed / duration, 1);
    var easeOut = function easeOut(t) {
      return 1 - Math.pow(1 - t, 3);
    };
    var scrollPosition = startScrollTop + distance * easeOut(progress);
    element.scrollTop = scrollPosition;
    if (timeElapsed < duration) {
      requestAnimationFrame(animate);
    }
  };
  requestAnimationFrame(animate);
};

exports.animateScrollTo = animateScrollTo;
exports.buildTimeString = buildTimeString;
exports.clampTimeToMax = clampTimeToMax;
exports.clampTimeToMin = clampTimeToMin;
exports.getColumnsFromFormat = getColumnsFromFormat;
exports.isTimeDisabled = isTimeDisabled;
exports.parseTimeBoundary = parseTimeBoundary;
exports.parseTimeString = parseTimeString;
exports.range = range;
exports.roundToMultiplicity = roundToMultiplicity;
exports.toTotalSeconds = toTotalSeconds;
