All files / src/timepicker util.ts

95.56% Statements 43/45
71.93% Branches 41/57
94.44% Functions 17/18
97.62% Lines 41/42

Press n or j to go to the next uncovered block, b, p or k for the previous block.

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 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130      4x   96x 4x   240x   4x 4x     16x                         4x                           12x               4x   4x 2x 2x 2x   48x     2x         4x   4x 2x 2x 2x       120x         2x           4x   4x 2x 2x 2x       120x         2x                     4x 4x   4x 4x 20x     4x 4x 62x     4x 4x       4x    
import moment, { Moment, isMoment } from "moment";
import { TimePickerProps } from "./TimeProps";
 
const SEQUENCE_24 = Array(24)
  .fill(0)
  .map((_, i) => i);
const SEQUENCE_60 = Array(60)
  .fill(0)
  .map((_, i) => i);
 
const startOfDay = moment().startOf("day");
const endOfDay = moment().endOf("day");
 
export function getHourMinuteSecond(time: Moment) {
  return {
    hour: time.hour(),
    minute: time.minute(),
    second: time.second(),
  };
}
 
/**
 * 解析 format
 * @param format
 */
export function genShowHourMinuteSecond(format: string) {
  // Ref: http://momentjs.com/docs/#/parsing/string-format/
  return {
    showHour:
      format.indexOf("H") > -1 ||
      format.indexOf("h") > -1 ||
      format.indexOf("k") > -1,
    showMinute: format.indexOf("m") > -1,
    showSecond: format.indexOf("s") > -1,
  };
}
 
/**
 * 校验 range
 */
function isValidRange(range): boolean {
  return Array.isArray(range) && (isMoment(range[0]) || isMoment(range[1]));
}
 
/**
 * 获取 disabled 部分
 */
export function getDisabledHours({
  range,
  disabledHours = () => [],
}: Partial<TimePickerProps>) {
  if (isValidRange(range)) {
    const min = getHourMinuteSecond(range[0] || startOfDay);
    const max = getHourMinuteSecond(range[1] || endOfDay);
    return [
      ...disabledHours(),
      ...SEQUENCE_24.filter(i => i < min.hour || i > max.hour),
    ];
  }
  return disabledHours();
}
 
export function getDisabledMinutes(
  hour: number,
  { range, disabledMinutes = () => [] }: Partial<TimePickerProps>
) {
  if (isValidRange(range)) {
    const min = getHourMinuteSecond(range[0] || startOfDay);
    const max = getHourMinuteSecond(range[1] || endOfDay);
    return [
      ...disabledMinutes(hour),
      ...SEQUENCE_60.filter(
        i =>
          (hour === min.hour && i < min.minute) ||
          (hour === max.hour && i > max.minute)
      ),
    ];
  }
  return disabledMinutes(hour);
}
 
export function getDisabledSeconds(
  hour: number,
  minute: number,
  { range, disabledSeconds = () => [] }: Partial<TimePickerProps>
) {
  if (isValidRange(range)) {
    const min = getHourMinuteSecond(range[0] || startOfDay);
    const max = getHourMinuteSecond(range[1] || endOfDay);
    return [
      ...disabledSeconds(hour, minute),
      ...SEQUENCE_60.filter(
        i =>
          (hour === min.hour && minute === min.minute && i < min.second) ||
          (hour === max.hour && minute === max.minute && i > max.second)
      ),
    ];
  }
  return disabledSeconds(hour, minute);
}
 
/**
 * 获取自动调整后的合法值
 */
export function getValidTimeValue(
  value: Moment,
  rangeOptions: Partial<TimePickerProps> = {},
  format: string = "HH:mm:ss"
): Moment {
  const { showHour, showMinute, showSecond } = genShowHourMinuteSecond(format);
  let { hour, minute, second } = getHourMinuteSecond(value || moment(0, "HH"));
 
  const disabledHours = getDisabledHours(rangeOptions);
  if (showHour && disabledHours.includes(hour)) {
    hour = SEQUENCE_24.find(i => !disabledHours.includes(i));
  }
 
  const disabledMinutes = getDisabledMinutes(hour, rangeOptions);
  if (showMinute && disabledMinutes.includes(minute)) {
    minute = SEQUENCE_60.find(i => !disabledMinutes.includes(i));
  }
 
  const disabledSeconds = getDisabledSeconds(hour, minute, rangeOptions);
  Iif (showSecond && disabledSeconds.includes(second)) {
    second = SEQUENCE_60.find(i => !disabledSeconds.includes(i));
  }
 
  return (value || moment()).set({ hour, minute, second });
}