You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
57 lines
2.2 KiB
57 lines
2.2 KiB
const maxValueMonth = [31, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
|
|
const formatOrder = ['yyyy', 'yy', 'mm', 'dd', 'HH', 'MM', 'SS']
|
|
export default function createAutoCorrectedDatePipe(dateFormat = 'mm dd yyyy', {
|
|
minYear = 1,
|
|
maxYear = 9999
|
|
} = {}) {
|
|
const dateFormatArray = dateFormat
|
|
.split(/[^dmyHMS]+/)
|
|
.sort((a, b) => formatOrder.indexOf(a) - formatOrder.indexOf(b))
|
|
return function(conformedValue) {
|
|
const indexesOfPipedChars = []
|
|
const maxValue = {'dd': 31, 'mm': 12, 'yy': 99, 'yyyy': maxYear, 'HH': 23, 'MM': 59, 'SS': 59}
|
|
const minValue = {'dd': 1, 'mm': 1, 'yy': 0, 'yyyy': minYear, 'HH': 0, 'MM': 0, 'SS': 0}
|
|
const conformedValueArr = conformedValue.split('')
|
|
|
|
// Check first digit
|
|
dateFormatArray.forEach((format) => {
|
|
const position = dateFormat.indexOf(format)
|
|
const maxFirstDigit = parseInt(maxValue[format].toString().substr(0, 1), 10)
|
|
|
|
if (parseInt(conformedValueArr[position], 10) > maxFirstDigit) {
|
|
conformedValueArr[position + 1] = conformedValueArr[position]
|
|
conformedValueArr[position] = 0
|
|
indexesOfPipedChars.push(position)
|
|
}
|
|
})
|
|
|
|
// Check for invalid date
|
|
let month = 0
|
|
const isInvalid = dateFormatArray.some((format) => {
|
|
const position = dateFormat.indexOf(format)
|
|
const length = format.length
|
|
const textValue = conformedValue.substr(position, length).replace(/\D/g, '')
|
|
const value = parseInt(textValue, 10)
|
|
if (format === 'mm') {
|
|
month = value || 0
|
|
}
|
|
const maxValueForFormat = format === 'dd' ? maxValueMonth[month] : maxValue[format]
|
|
if (format === 'yyyy' && (minYear !== 1 || maxYear !== 9999)) {
|
|
const scopedMaxValue = parseInt(maxValue[format].toString().substring(0, textValue.length), 10)
|
|
const scopedMinValue = parseInt(minValue[format].toString().substring(0, textValue.length), 10)
|
|
return value < scopedMinValue || value > scopedMaxValue
|
|
}
|
|
return value > maxValueForFormat || (textValue.length === length && value < minValue[format])
|
|
})
|
|
|
|
if (isInvalid) {
|
|
return false
|
|
}
|
|
|
|
return {
|
|
value: conformedValueArr.join(''),
|
|
indexesOfPipedChars
|
|
}
|
|
}
|
|
}
|