From 01ea291cd5ddf6b08589cce0e9584170d17df53a Mon Sep 17 00:00:00 2001 From: Gabriel Reitz Giannattasio Date: Mon, 23 Apr 2012 11:58:08 -0300 Subject: [PATCH 1/8] Added encapsuled executation, and format method nows supported in prototype mode --- js/date-format.js | 606 +++++++++++++++++++++++----------------------- 1 file changed, 308 insertions(+), 298 deletions(-) diff --git a/js/date-format.js b/js/date-format.js index 9fea332..502fac0 100644 --- a/js/date-format.js +++ b/js/date-format.js @@ -20,301 +20,311 @@ * Dual licensed under the MIT and GPL licenses. * ---------------------------------------------------------------------------- */ - -// extend the Javascript Date class with the "format" static function which will format -// the provided date object using the provided format string -Date.format = function (date, format) -{ - // get the helper functions object - var formatLogic = Date.formatLogic; - - // check if the AM/PM option is used - var isAmPm = (format.indexOf("a") !== -1) || (format.indexOf("A") !== -1); - - // prepare all the parts of the date that can be used in the format - var parts = []; - parts['d'] = date.getDate(); - parts['dd'] = formatLogic.pad(parts['d'], 2); - parts['ddd'] = formatLogic.i18n.shortDayNames[date.getDay()]; - parts['dddd'] = formatLogic.i18n.dayNames[date.getDay()]; - parts['M'] = date.getMonth() + 1; - parts['MM'] = formatLogic.pad(parts['M'], 2); - parts['MMM'] = formatLogic.i18n.shortMonthNames[parts['M'] - 1]; - parts['MMMM'] = formatLogic.i18n.monthNames[parts['M'] - 1]; - parts['yyyy'] = date.getFullYear(); - parts['yyy'] = formatLogic.pad(parts['yyyy'], 2) + 'y'; - parts['yy'] = formatLogic.pad(parts['yyyy'], 2); - parts['y'] = 'y'; - parts['H'] = date.getHours(); - parts['hh'] = formatLogic.pad(isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H'], 2); - parts['h'] = isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H']; - parts['HH'] = formatLogic.pad(parts['H'], 2); - parts['m'] = date.getMinutes(); - parts['mm'] = formatLogic.pad(parts['m'], 2); - parts['s'] = date.getSeconds(); - parts['ss'] = formatLogic.pad(parts['s'], 2); - parts['z'] = date.getMilliseconds(); - parts['zz'] = parts['z'] + 'z'; - parts['zzz'] = formatLogic.pad(parts['z'], 3); - parts['ap'] = parts['H'] < 12 ? 'am' : 'pm'; - parts['a'] = parts['H'] < 12 ? 'am' : 'pm'; - parts['AP'] = parts['H'] < 12 ? 'AM' : 'PM'; - parts['A'] = parts['H'] < 12 ? 'AM' : 'PM'; - - // parse the input format, char by char - var i = 0; - var output = ""; - var token = ""; - while (i < format.length) - { - token = format.charAt(i); - - while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) - { - token += format.charAt(++i); - } - - if (parts[token] !== undefined) - { - output += parts[token]; - } - else - { - output += token; - } - - i++; - } - - // return the parsed result - return output; -}; - -// this is the format logic helper object that contains the helper functions -// and the internationalization settings that can be overridden -Date.formatLogic = -{ - // left-pad the provided number with zeros - pad: function (value, digits) - { - var max = 1; - var zeros = ""; - - if(digits < 1) - { - return ""; - } - - for(var i = 0; i < digits; i++) - { - max *= 10; - zeros += "0"; - } - - var output = value; - - output = zeros + value; - output = output.substring(output.length - digits); - - return output; - }, - - // convert the 24 hour style value to a 12 hour style value - convertTo12Hour: function (value) - { - return value % 12 === 0 ? 12 : value % 12; - }, - - // internationalization settings - i18n: - { - dayNames: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'], - shortDayNames: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'], - monthNames: ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'], - shortMonthNames: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'] - } -}; - -// add a member "format" function which will return the string representation -// of the current object formatted using the provided format string -Date.prototype.toFormattedString = function (format) -{ - return Date.format(this, format); -}; - -// extend the Javascript Date class with the "parseFormatted" static function which -// will parse the provided string, using the provided format into a valid date object -Date.parseFormatted = function (value, format) -{ - var output = new Date(2000, 0, 1); - var parts = []; - parts['d'] = '([0-9][0-9]?)'; - parts['dd'] = '([0-9][0-9])'; -// parts['ddd'] = NOT SUPPORTED; -// parts['dddd'] = NOT SUPPORTED; - parts['M'] = '([0-9][0-9]?)'; - parts['MM'] = '([0-9][0-9])'; -// parts['MMM'] = NOT SUPPORTED; -// parts['MMMM'] = NOT SUPPORTED; - parts['yyyy'] = '([0-9][0-9][0-9][0-9])'; - parts['yyy'] = '([0-9][0-9])[y]'; - parts['yy'] = '([0-9][0-9])'; - parts['H'] = '([0-9][0-9]?)'; - parts['hh'] = '([0-9][0-9])'; - parts['h'] = '([0-9][0-9]?)'; - parts['HH'] = '([0-9][0-9])'; - parts['m'] = '([0-9][0-9]?)'; - parts['mm'] = '([0-9][0-9])'; - parts['s'] = '([0-9][0-9]?)'; - parts['ss'] = '([0-9][0-9])'; - parts['z'] = '([0-9][0-9]?[0-9]?)'; - parts['zz'] = '([0-9][0-9]?[0-9]?)[z]'; - parts['zzz'] = '([0-9][0-9][0-9])'; - parts['ap'] = '([ap][m])'; - parts['a'] = '([ap][m])'; - parts['AP'] = '([AP][M])'; - parts['A'] = '([AP][M])'; - - var _ = Date.parseLogic; - - // parse the input format, char by char - var i = 0; - var regex = ""; - var outputs = new Array(""); - var token = ""; - - // parse the format to get the extraction regex - while (i < format.length) - { - token = format.charAt(i); - while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) - { - token += format.charAt(++i); - } - - if (parts[token] !== undefined) - { - regex += parts[token]; - outputs[outputs.length] = token; - } - else - { - regex += token; - } - - i++; - } - - // extract matches - var r = new RegExp(regex); - var matches = value.match(r); - - if(matches === undefined || matches.length !== outputs.length) - { - return undefined; - } - - // parse each match and update the output date object - for(i = 0; i < outputs.length; i++) - { - if(outputs[i] !== '') - { - switch(outputs[i]) - { - case 'yyyy': - case 'yyy': - output.setYear(_.parseInt(matches[i])); - break; - - case 'yy': - output.setYear(2000 + _.parseInt(matches[i])); - break; - - case 'MM': - case 'M': - output.setMonth(_.parseInt(matches[i]) - 1); - break; - - case 'dd': - case 'd': - output.setDate(_.parseInt(matches[i])); - break; - - case 'hh': - case 'h': - case 'HH': - case 'H': - output.setHours(_.parseInt(matches[i])); - break; - - case 'mm': - case 'm': - output.setMinutes(_.parseInt(matches[i])); - break; - - case 'ss': - case 's': - output.setSeconds(_.parseInt(matches[i])); - break; - - case 'zzz': - case 'zz': - case 'z': - output.setMilliseconds(_.parseInt(matches[i])); - break; - - case 'AP': - case 'A': - case 'ap': - case 'a': - if((matches[i] === 'PM' || matches[i] === 'pm') && (output.getHours() < 12)) - { - output.setHours(output.getHours() + 12); - } - - if((matches[i] === 'AM' || matches[i] === 'am') && (output.getHours() === 12)) - { - output.setHours(0); - } - break; - } - } - } - - return output; -}; - -// this is the parse logic helper object that contains the helper functions -Date.parseLogic = -{ - unpad: function (value) - { - var output = value; - - while(output.length > 1) - { - if(output[0] === '0') - { - output = output.substring(1, output.length); - } - else - { - break; - } - } - - return output; - }, - parseInt: function (value) - { - return parseInt(this.unpad(value), 10); - } -}; - -// add a member "from" function which will return the date object, created -// from the provided string and the format -Date.prototype.fromFormattedString = function(value, format) -{ - this.setTime(Date.parseFormatted(value, format).getTime()); - return this; -}; +(function() { + // extend the Javascript Date class with the "format" static function which will format + // the provided date object using the provided format string + Date.format = function (date, format) + { + if(!(date instanceof Date)) { + format = date; + date = this; + if(!(date instanceof Date)) throw 'Invalid use of format'; + } + + // get the helper functions object + var formatLogic = Date.formatLogic; + + // check if the AM/PM option is used + var isAmPm = (format.indexOf("a") !== -1) || (format.indexOf("A") !== -1); + + // prepare all the parts of the date that can be used in the format + var parts = []; + parts['d'] = date.getDate(); + parts['dd'] = formatLogic.pad(parts['d'], 2); + parts['ddd'] = formatLogic.i18n.shortDayNames[date.getDay()]; + parts['dddd'] = formatLogic.i18n.dayNames[date.getDay()]; + parts['M'] = date.getMonth() + 1; + parts['MM'] = formatLogic.pad(parts['M'], 2); + parts['MMM'] = formatLogic.i18n.shortMonthNames[parts['M'] - 1]; + parts['MMMM'] = formatLogic.i18n.monthNames[parts['M'] - 1]; + parts['yyyy'] = date.getFullYear(); + parts['yyy'] = formatLogic.pad(parts['yyyy'], 2) + 'y'; + parts['yy'] = formatLogic.pad(parts['yyyy'], 2); + parts['y'] = 'y'; + parts['H'] = date.getHours(); + parts['hh'] = formatLogic.pad(isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H'], 2); + parts['h'] = isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H']; + parts['HH'] = formatLogic.pad(parts['H'], 2); + parts['m'] = date.getMinutes(); + parts['mm'] = formatLogic.pad(parts['m'], 2); + parts['s'] = date.getSeconds(); + parts['ss'] = formatLogic.pad(parts['s'], 2); + parts['z'] = date.getMilliseconds(); + parts['zz'] = parts['z'] + 'z'; + parts['zzz'] = formatLogic.pad(parts['z'], 3); + parts['ap'] = parts['H'] < 12 ? 'am' : 'pm'; + parts['a'] = parts['H'] < 12 ? 'am' : 'pm'; + parts['AP'] = parts['H'] < 12 ? 'AM' : 'PM'; + parts['A'] = parts['H'] < 12 ? 'AM' : 'PM'; + + // parse the input format, char by char + var i = 0; + var output = ""; + var token = ""; + while (i < format.length) + { + token = format.charAt(i); + + while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) + { + token += format.charAt(++i); + } + + if (parts[token] !== undefined) + { + output += parts[token]; + } + else + { + output += token; + } + + i++; + } + + // return the parsed result + return output; + }; + + // this is the format logic helper object that contains the helper functions + // and the internationalization settings that can be overridden + Date.formatLogic = + { + // left-pad the provided number with zeros + pad: function (value, digits) + { + var max = 1; + var zeros = ""; + + if(digits < 1) + { + return ""; + } + + for(var i = 0; i < digits; i++) + { + max *= 10; + zeros += "0"; + } + + var output = value; + + output = zeros + value; + output = output.substring(output.length - digits); + + return output; + }, + + // convert the 24 hour style value to a 12 hour style value + convertTo12Hour: function (value) + { + return value % 12 === 0 ? 12 : value % 12; + }, + + // internationalization settings + i18n: + { + dayNames: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'], + shortDayNames: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'], + monthNames: ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'], + shortMonthNames: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'] + } + }; + + // add a member "format" function which will return the string representation + // of the current object formatted using the provided format string + Date.prototype.toFormattedString = function (format) + { + return Date.format(this, format); + }; + + Date.prototype.format = Date.format; + + // extend the Javascript Date class with the "parseFormatted" static function which + // will parse the provided string, using the provided format into a valid date object + Date.parseFormatted = function (value, format) + { + var output = new Date(2000, 0, 1); + var parts = []; + parts['d'] = '([0-9][0-9]?)'; + parts['dd'] = '([0-9][0-9])'; + // parts['ddd'] = NOT SUPPORTED; + // parts['dddd'] = NOT SUPPORTED; + parts['M'] = '([0-9][0-9]?)'; + parts['MM'] = '([0-9][0-9])'; + // parts['MMM'] = NOT SUPPORTED; + // parts['MMMM'] = NOT SUPPORTED; + parts['yyyy'] = '([0-9][0-9][0-9][0-9])'; + parts['yyy'] = '([0-9][0-9])[y]'; + parts['yy'] = '([0-9][0-9])'; + parts['H'] = '([0-9][0-9]?)'; + parts['hh'] = '([0-9][0-9])'; + parts['h'] = '([0-9][0-9]?)'; + parts['HH'] = '([0-9][0-9])'; + parts['m'] = '([0-9][0-9]?)'; + parts['mm'] = '([0-9][0-9])'; + parts['s'] = '([0-9][0-9]?)'; + parts['ss'] = '([0-9][0-9])'; + parts['z'] = '([0-9][0-9]?[0-9]?)'; + parts['zz'] = '([0-9][0-9]?[0-9]?)[z]'; + parts['zzz'] = '([0-9][0-9][0-9])'; + parts['ap'] = '([ap][m])'; + parts['a'] = '([ap][m])'; + parts['AP'] = '([AP][M])'; + parts['A'] = '([AP][M])'; + + var _ = Date.parseLogic; + + // parse the input format, char by char + var i = 0; + var regex = ""; + var outputs = new Array(""); + var token = ""; + + // parse the format to get the extraction regex + while (i < format.length) + { + token = format.charAt(i); + while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) + { + token += format.charAt(++i); + } + + if (parts[token] !== undefined) + { + regex += parts[token]; + outputs[outputs.length] = token; + } + else + { + regex += token; + } + + i++; + } + + // extract matches + var r = new RegExp(regex); + var matches = value.match(r); + + if(matches === undefined || matches.length !== outputs.length) + { + return undefined; + } + + // parse each match and update the output date object + for(i = 0; i < outputs.length; i++) + { + if(outputs[i] !== '') + { + switch(outputs[i]) + { + case 'yyyy': + case 'yyy': + output.setYear(_.parseInt(matches[i])); + break; + + case 'yy': + output.setYear(2000 + _.parseInt(matches[i])); + break; + + case 'MM': + case 'M': + output.setMonth(_.parseInt(matches[i]) - 1); + break; + + case 'dd': + case 'd': + output.setDate(_.parseInt(matches[i])); + break; + + case 'hh': + case 'h': + case 'HH': + case 'H': + output.setHours(_.parseInt(matches[i])); + break; + + case 'mm': + case 'm': + output.setMinutes(_.parseInt(matches[i])); + break; + + case 'ss': + case 's': + output.setSeconds(_.parseInt(matches[i])); + break; + + case 'zzz': + case 'zz': + case 'z': + output.setMilliseconds(_.parseInt(matches[i])); + break; + + case 'AP': + case 'A': + case 'ap': + case 'a': + if((matches[i] === 'PM' || matches[i] === 'pm') && (output.getHours() < 12)) + { + output.setHours(output.getHours() + 12); + } + + if((matches[i] === 'AM' || matches[i] === 'am') && (output.getHours() === 12)) + { + output.setHours(0); + } + break; + } + } + } + + return output; + }; + + // this is the parse logic helper object that contains the helper functions + Date.parseLogic = + { + unpad: function (value) + { + var output = value; + + while(output.length > 1) + { + if(output[0] === '0') + { + output = output.substring(1, output.length); + } + else + { + break; + } + } + + return output; + }, + parseInt: function (value) + { + return parseInt(this.unpad(value), 10); + } + }; + + // add a member "from" function which will return the date object, created + // from the provided string and the format + Date.prototype.fromFormattedString = function(value, format) + { + this.setTime(Date.parseFormatted(value, format).getTime()); + return this; + }; + +})(); From 63188464dc1987e1deae51ddd5732cdfb33df365 Mon Sep 17 00:00:00 2001 From: Gabriel Reitz Giannattasio Date: Mon, 23 Apr 2012 12:48:27 -0300 Subject: [PATCH 2/8] Code cleanup --- js/date-format.js | 189 ++++++++++++++++++++++------------------------ 1 file changed, 90 insertions(+), 99 deletions(-) diff --git a/js/date-format.js b/js/date-format.js index 502fac0..a80e8a2 100644 --- a/js/date-format.js +++ b/js/date-format.js @@ -32,68 +32,65 @@ } // get the helper functions object - var formatLogic = Date.formatLogic; - - // check if the AM/PM option is used - var isAmPm = (format.indexOf("a") !== -1) || (format.indexOf("A") !== -1); - - // prepare all the parts of the date that can be used in the format - var parts = []; - parts['d'] = date.getDate(); - parts['dd'] = formatLogic.pad(parts['d'], 2); - parts['ddd'] = formatLogic.i18n.shortDayNames[date.getDay()]; - parts['dddd'] = formatLogic.i18n.dayNames[date.getDay()]; - parts['M'] = date.getMonth() + 1; - parts['MM'] = formatLogic.pad(parts['M'], 2); - parts['MMM'] = formatLogic.i18n.shortMonthNames[parts['M'] - 1]; - parts['MMMM'] = formatLogic.i18n.monthNames[parts['M'] - 1]; - parts['yyyy'] = date.getFullYear(); - parts['yyy'] = formatLogic.pad(parts['yyyy'], 2) + 'y'; - parts['yy'] = formatLogic.pad(parts['yyyy'], 2); - parts['y'] = 'y'; - parts['H'] = date.getHours(); - parts['hh'] = formatLogic.pad(isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H'], 2); - parts['h'] = isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H']; - parts['HH'] = formatLogic.pad(parts['H'], 2); - parts['m'] = date.getMinutes(); - parts['mm'] = formatLogic.pad(parts['m'], 2); - parts['s'] = date.getSeconds(); - parts['ss'] = formatLogic.pad(parts['s'], 2); - parts['z'] = date.getMilliseconds(); - parts['zz'] = parts['z'] + 'z'; - parts['zzz'] = formatLogic.pad(parts['z'], 3); - parts['ap'] = parts['H'] < 12 ? 'am' : 'pm'; - parts['a'] = parts['H'] < 12 ? 'am' : 'pm'; - parts['AP'] = parts['H'] < 12 ? 'AM' : 'PM'; - parts['A'] = parts['H'] < 12 ? 'AM' : 'PM'; - - // parse the input format, char by char - var i = 0; - var output = ""; - var token = ""; - while (i < format.length) - { - token = format.charAt(i); - - while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) - { - token += format.charAt(++i); - } - - if (parts[token] !== undefined) - { - output += parts[token]; - } - else - { - output += token; - } - - i++; - } + var formatLogic = Date.formatLogic; + + // check if the AM/PM option is used + var isAmPm = format.toLowerCase().indexOf("a") !== -1; + + // prepare all the parts of the date that can be used in the format + var parts = {}; + parts['d'] = date.getDate(); + parts['dd'] = formatLogic.pad(parts['d'], 2); + parts['ddd'] = formatLogic.i18n.shortDayNames[date.getDay()]; + parts['dddd'] = formatLogic.i18n.dayNames[date.getDay()]; + parts['M'] = date.getMonth() + 1; + parts['MM'] = formatLogic.pad(parts['M'], 2); + parts['MMM'] = formatLogic.i18n.shortMonthNames[parts['M'] - 1]; + parts['MMMM'] = formatLogic.i18n.monthNames[parts['M'] - 1]; + parts['yyyy'] = date.getFullYear(); + parts['yyy'] = formatLogic.pad(parts['yyyy'], 2) + 'y'; + parts['yy'] = formatLogic.pad(parts['yyyy'], 2); + parts['y'] = 'y'; + parts['H'] = date.getHours(); + parts['hh'] = formatLogic.pad(isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H'], 2); + parts['h'] = isAmPm ? formatLogic.convertTo12Hour(parts['H']) : parts['H']; + parts['HH'] = formatLogic.pad(parts['H'], 2); + parts['m'] = date.getMinutes(); + parts['mm'] = formatLogic.pad(parts['m'], 2); + parts['s'] = date.getSeconds(); + parts['ss'] = formatLogic.pad(parts['s'], 2); + parts['z'] = date.getMilliseconds(); + parts['zz'] = parts['z'] + 'z'; + parts['zzz'] = formatLogic.pad(parts['z'], 3); + parts['ap'] = parts['H'] < 12 ? 'am' : 'pm'; + parts['a'] = parts['H'] < 12 ? 'am' : 'pm'; + parts['AP'] = parts['H'] < 12 ? 'AM' : 'PM'; + parts['A'] = parts['H'] < 12 ? 'AM' : 'PM'; + + // parse the input format, char by char + var output = ""; + var token = ""; + for(var i = 0; i < format.length; i++) + { + token = format.charAt(i); + + while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) + { + token += format.charAt(++i); + } + + if (parts[token] !== undefined) + { + output += parts[token]; + } + else + { + output += token; + } + } - // return the parsed result - return output; + // return the parsed result + return output; }; // this is the format logic helper object that contains the helper functions @@ -143,11 +140,7 @@ // add a member "format" function which will return the string representation // of the current object formatted using the provided format string - Date.prototype.toFormattedString = function (format) - { - return Date.format(this, format); - }; - + Date.prototype.toFormattedString = Date.format; // Deprecated Date.prototype.format = Date.format; // extend the Javascript Date class with the "parseFormatted" static function which @@ -155,44 +148,44 @@ Date.parseFormatted = function (value, format) { var output = new Date(2000, 0, 1); - var parts = []; - parts['d'] = '([0-9][0-9]?)'; - parts['dd'] = '([0-9][0-9])'; - // parts['ddd'] = NOT SUPPORTED; - // parts['dddd'] = NOT SUPPORTED; - parts['M'] = '([0-9][0-9]?)'; - parts['MM'] = '([0-9][0-9])'; - // parts['MMM'] = NOT SUPPORTED; - // parts['MMMM'] = NOT SUPPORTED; - parts['yyyy'] = '([0-9][0-9][0-9][0-9])'; - parts['yyy'] = '([0-9][0-9])[y]'; - parts['yy'] = '([0-9][0-9])'; - parts['H'] = '([0-9][0-9]?)'; - parts['hh'] = '([0-9][0-9])'; - parts['h'] = '([0-9][0-9]?)'; - parts['HH'] = '([0-9][0-9])'; - parts['m'] = '([0-9][0-9]?)'; - parts['mm'] = '([0-9][0-9])'; - parts['s'] = '([0-9][0-9]?)'; - parts['ss'] = '([0-9][0-9])'; - parts['z'] = '([0-9][0-9]?[0-9]?)'; - parts['zz'] = '([0-9][0-9]?[0-9]?)[z]'; - parts['zzz'] = '([0-9][0-9][0-9])'; - parts['ap'] = '([ap][m])'; - parts['a'] = '([ap][m])'; - parts['AP'] = '([AP][M])'; - parts['A'] = '([AP][M])'; + var parts = { + 'd': '([0-9][0-9]?)', + 'dd': '([0-9][0-9])', +// 'ddd': 'NOT SUPPORTED', +// 'dddd': 'NOT SUPPORTED', + 'M': '([0-9][0-9]?)', + 'MM': '([0-9][0-9])', +// 'MMM': 'NOT SUPPORTED', +// 'MMMM': 'NOT SUPPORTED', + 'yyyy': '([0-9][0-9][0-9][0-9])', + 'yyy': '([0-9][0-9])[y]', + 'yy': '([0-9][0-9])', + 'H': '([0-9][0-9]?)', + 'hh': '([0-9][0-9])', + 'h': '([0-9][0-9]?)', + 'HH': '([0-9][0-9])', + 'm': '([0-9][0-9]?)', + 'mm': '([0-9][0-9])', + 's': '([0-9][0-9]?)', + 'ss': '([0-9][0-9])', + 'z': '([0-9][0-9]?[0-9]?)', + 'zz': '([0-9][0-9]?[0-9]?)[z]', + 'zzz': '([0-9][0-9][0-9])', + 'ap': '([ap][m])', + 'a': '([ap][m])', + 'AP': '([AP][M])', + 'A': '([AP][M])' + }; var _ = Date.parseLogic; // parse the input format, char by char - var i = 0; var regex = ""; - var outputs = new Array(""); + var outputs = []; var token = ""; // parse the format to get the extraction regex - while (i < format.length) + for (var i=0; i < format.length; i++) { token = format.charAt(i); while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) @@ -203,14 +196,12 @@ if (parts[token] !== undefined) { regex += parts[token]; - outputs[outputs.length] = token; + outputs.push(token); } else { regex += token; } - - i++; } // extract matches From b394ff2952c434a69d6ba3501013faa7361bb77b Mon Sep 17 00:00:00 2001 From: gartz Date: Mon, 23 Apr 2012 18:37:15 -0300 Subject: [PATCH 3/8] Fix reverse from format --- js/date-format.js | 72 +++++++++++++++++++++++------------------------ 1 file changed, 35 insertions(+), 37 deletions(-) diff --git a/js/date-format.js b/js/date-format.js index a80e8a2..e5ee34d 100644 --- a/js/date-format.js +++ b/js/date-format.js @@ -97,45 +97,42 @@ // and the internationalization settings that can be overridden Date.formatLogic = { - // left-pad the provided number with zeros - pad: function (value, digits) - { - var max = 1; - var zeros = ""; - - if(digits < 1) - { - return ""; - } - - for(var i = 0; i < digits; i++) - { - max *= 10; - zeros += "0"; - } - - var output = value; - - output = zeros + value; - output = output.substring(output.length - digits); + // left-pad the provided number with zeros + pad: function (value, digits) + { + var max = 1; + var zeros = ""; + + if(digits < 1) return ""; + + for(var i = 0; i < digits; i++) + { + max *= 10; + zeros += "0"; + } - return output; - }, + var output = value; + + output = zeros + value; + output = output.substring(output.length - digits); + + return output; + }, - // convert the 24 hour style value to a 12 hour style value - convertTo12Hour: function (value) - { - return value % 12 === 0 ? 12 : value % 12; - }, + // convert the 24 hour style value to a 12 hour style value + convertTo12Hour: function (value) + { + return value % 12 === 0 ? 12 : value % 12; + }, - // internationalization settings - i18n: - { - dayNames: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'], - shortDayNames: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'], - monthNames: ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'], - shortMonthNames: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'] - } + // internationalization settings + i18n: + { + dayNames: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'], + shortDayNames: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'], + monthNames: ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'], + shortMonthNames: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'] + } }; // add a member "format" function which will return the string representation @@ -207,10 +204,11 @@ // extract matches var r = new RegExp(regex); var matches = value.match(r); + matches.shift(); if(matches === undefined || matches.length !== outputs.length) { - return undefined; + return; } // parse each match and update the output date object From dc6e1d1c1992ce1ba9d474c18eb57dd2b5dd86d0 Mon Sep 17 00:00:00 2001 From: gartz Date: Mon, 23 Apr 2012 18:46:38 -0300 Subject: [PATCH 4/8] Code cleanup --- js/date-format.js | 132 ++++++++++++++++++++++------------------------ 1 file changed, 64 insertions(+), 68 deletions(-) diff --git a/js/date-format.js b/js/date-format.js index e5ee34d..56c7b07 100644 --- a/js/date-format.js +++ b/js/date-format.js @@ -190,7 +190,7 @@ token += format.charAt(++i); } - if (parts[token] !== undefined) + if (parts[token]) { regex += parts[token]; outputs.push(token); @@ -204,78 +204,74 @@ // extract matches var r = new RegExp(regex); var matches = value.match(r); + //Remove first match that is equals value matches.shift(); - - if(matches === undefined || matches.length !== outputs.length) - { - return; - } + + if(!matches || matches.length !== outputs.length) + throw 'Matches length exception'; // parse each match and update the output date object for(i = 0; i < outputs.length; i++) { - if(outputs[i] !== '') - { - switch(outputs[i]) - { - case 'yyyy': - case 'yyy': - output.setYear(_.parseInt(matches[i])); - break; - - case 'yy': - output.setYear(2000 + _.parseInt(matches[i])); - break; - - case 'MM': - case 'M': - output.setMonth(_.parseInt(matches[i]) - 1); - break; - - case 'dd': - case 'd': - output.setDate(_.parseInt(matches[i])); - break; - - case 'hh': - case 'h': - case 'HH': - case 'H': - output.setHours(_.parseInt(matches[i])); - break; - - case 'mm': - case 'm': - output.setMinutes(_.parseInt(matches[i])); - break; - - case 'ss': - case 's': - output.setSeconds(_.parseInt(matches[i])); - break; - - case 'zzz': - case 'zz': - case 'z': - output.setMilliseconds(_.parseInt(matches[i])); - break; - - case 'AP': - case 'A': - case 'ap': - case 'a': - if((matches[i] === 'PM' || matches[i] === 'pm') && (output.getHours() < 12)) - { - output.setHours(output.getHours() + 12); - } - - if((matches[i] === 'AM' || matches[i] === 'am') && (output.getHours() === 12)) - { - output.setHours(0); - } - break; - } - } + switch(outputs[i]) + { + case 'yyyy': + case 'yyy': + output.setYear(_.parseInt(matches[i])); + break; + + case 'yy': + output.setYear(2000 + _.parseInt(matches[i])); + break; + + case 'MM': + case 'M': + output.setMonth(_.parseInt(matches[i]) - 1); + break; + + case 'dd': + case 'd': + output.setDate(_.parseInt(matches[i])); + break; + + case 'hh': + case 'h': + case 'HH': + case 'H': + output.setHours(_.parseInt(matches[i])); + break; + + case 'mm': + case 'm': + output.setMinutes(_.parseInt(matches[i])); + break; + + case 'ss': + case 's': + output.setSeconds(_.parseInt(matches[i])); + break; + + case 'zzz': + case 'zz': + case 'z': + output.setMilliseconds(_.parseInt(matches[i])); + break; + + case 'AP': + case 'A': + case 'ap': + case 'a': + if((matches[i].toLowerCase() === 'pm') && (output.getHours() < 12)) + { + output.setHours(output.getHours() + 12); + } + + if((matches[i].toLowerCase() === 'am') && (output.getHours() === 12)) + { + output.setHours(0); + } + break; + } } return output; From c3ec91b0bdc096fe365fe9058f8c576d4231f7f0 Mon Sep 17 00:00:00 2001 From: gartz Date: Mon, 23 Apr 2012 19:27:46 -0300 Subject: [PATCH 5/8] Removed useless parseLogic --- js/date-format.js | 47 ++++++++++------------------------------------- 1 file changed, 10 insertions(+), 37 deletions(-) diff --git a/js/date-format.js b/js/date-format.js index 56c7b07..f084363 100644 --- a/js/date-format.js +++ b/js/date-format.js @@ -172,9 +172,9 @@ 'a': '([ap][m])', 'AP': '([AP][M])', 'A': '([AP][M])' - }; + }; - var _ = Date.parseLogic; + function toInt(v) { return parseInt(v, 10); } // parse the input format, char by char var regex = ""; @@ -217,44 +217,44 @@ { case 'yyyy': case 'yyy': - output.setYear(_.parseInt(matches[i])); + output.setYear(toInt(matches[i])); break; case 'yy': - output.setYear(2000 + _.parseInt(matches[i])); + output.setYear(2000 + toInt(matches[i])); break; case 'MM': case 'M': - output.setMonth(_.parseInt(matches[i]) - 1); + output.setMonth(toInt(matches[i]) - 1); break; case 'dd': case 'd': - output.setDate(_.parseInt(matches[i])); + output.setDate(toInt(matches[i])); break; case 'hh': case 'h': case 'HH': case 'H': - output.setHours(_.parseInt(matches[i])); + output.setHours(toInt(matches[i])); break; case 'mm': case 'm': - output.setMinutes(_.parseInt(matches[i])); + output.setMinutes(toInt(matches[i])); break; case 'ss': case 's': - output.setSeconds(_.parseInt(matches[i])); + output.setSeconds(toInt(matches[i])); break; case 'zzz': case 'zz': case 'z': - output.setMilliseconds(_.parseInt(matches[i])); + output.setMilliseconds(toInt(matches[i])); break; case 'AP': @@ -277,33 +277,6 @@ return output; }; - // this is the parse logic helper object that contains the helper functions - Date.parseLogic = - { - unpad: function (value) - { - var output = value; - - while(output.length > 1) - { - if(output[0] === '0') - { - output = output.substring(1, output.length); - } - else - { - break; - } - } - - return output; - }, - parseInt: function (value) - { - return parseInt(this.unpad(value), 10); - } - }; - // add a member "from" function which will return the date object, created // from the provided string and the format Date.prototype.fromFormattedString = function(value, format) From 45dbbf70f135e4ab8dce76fce85e69cb73af1058 Mon Sep 17 00:00:00 2001 From: gartz Date: Tue, 24 Jul 2012 14:02:09 -0300 Subject: [PATCH 6/8] Identation --- js/date-format.js | 64 +++++++++++++++++++++++------------------------ 1 file changed, 32 insertions(+), 32 deletions(-) diff --git a/js/date-format.js b/js/date-format.js index f084363..1f81559 100644 --- a/js/date-format.js +++ b/js/date-format.js @@ -4,13 +4,13 @@ * Version: 0.9.11 * Date: 2012-04-12 * Description: In lack of decent formatting ability of Javascript Date object, - * I have created this "patch" for the Date object which will add - * "Date.format(dateObject, format)" static function, and the + * I have created this "patch" for the Date object which will add + * "Date.format(dateObject, format)" static function, and the * "dateObject.toFormattedString(format)" member function. - * Along with the formatting abilities, I have also added the + * Along with the formatting abilities, I have also added the * following functions for parsing dates: * "Date.parseFormatted(value, format)" - static function - * "dateObject.fromFormattedString(value, format)" - member + * "dateObject.fromFormattedString(value, format)" - member * function * Author: Miljenko Barbir * Author URL: http://miljenkobarbir.com/ @@ -30,13 +30,13 @@ date = this; if(!(date instanceof Date)) throw 'Invalid use of format'; } - + // get the helper functions object var formatLogic = Date.formatLogic; - + // check if the AM/PM option is used var isAmPm = format.toLowerCase().indexOf("a") !== -1; - + // prepare all the parts of the date that can be used in the format var parts = {}; parts['d'] = date.getDate(); @@ -66,19 +66,19 @@ parts['a'] = parts['H'] < 12 ? 'am' : 'pm'; parts['AP'] = parts['H'] < 12 ? 'AM' : 'PM'; parts['A'] = parts['H'] < 12 ? 'AM' : 'PM'; - + // parse the input format, char by char var output = ""; var token = ""; for(var i = 0; i < format.length; i++) { token = format.charAt(i); - + while((i + 1 < format.length) && parts[token + format.charAt(i + 1)] !== undefined) { token += format.charAt(++i); } - + if (parts[token] !== undefined) { output += parts[token]; @@ -88,43 +88,43 @@ output += token; } } - + // return the parsed result return output; }; - + // this is the format logic helper object that contains the helper functions // and the internationalization settings that can be overridden - Date.formatLogic = + Date.formatLogic = { // left-pad the provided number with zeros pad: function (value, digits) { var max = 1; var zeros = ""; - + if(digits < 1) return ""; - + for(var i = 0; i < digits; i++) { max *= 10; zeros += "0"; } - + var output = value; - + output = zeros + value; output = output.substring(output.length - digits); - + return output; }, - + // convert the 24 hour style value to a 12 hour style value convertTo12Hour: function (value) { return value % 12 === 0 ? 12 : value % 12; }, - + // internationalization settings i18n: { @@ -134,12 +134,12 @@ shortMonthNames: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'] } }; - + // add a member "format" function which will return the string representation // of the current object formatted using the provided format string Date.prototype.toFormattedString = Date.format; // Deprecated Date.prototype.format = Date.format; - + // extend the Javascript Date class with the "parseFormatted" static function which // will parse the provided string, using the provided format into a valid date object Date.parseFormatted = function (value, format) @@ -173,14 +173,14 @@ 'AP': '([AP][M])', 'A': '([AP][M])' }; - + function toInt(v) { return parseInt(v, 10); } - + // parse the input format, char by char var regex = ""; var outputs = []; var token = ""; - + // parse the format to get the extraction regex for (var i=0; i < format.length; i++) { @@ -189,7 +189,7 @@ { token += format.charAt(++i); } - + if (parts[token]) { regex += parts[token]; @@ -200,16 +200,16 @@ regex += token; } } - + // extract matches var r = new RegExp(regex); var matches = value.match(r); //Remove first match that is equals value matches.shift(); - - if(!matches || matches.length !== outputs.length) + + if(!matches || matches.length !== outputs.length) throw 'Matches length exception'; - + // parse each match and update the output date object for(i = 0; i < outputs.length; i++) { @@ -273,10 +273,10 @@ break; } } - + return output; }; - + // add a member "from" function which will return the date object, created // from the provided string and the format Date.prototype.fromFormattedString = function(value, format) From 964bd14ff2a31a0928137cfe886613d39165fa8a Mon Sep 17 00:00:00 2001 From: "Gabriel R. Giannattasio" Date: Mon, 4 Nov 2013 12:05:36 -0200 Subject: [PATCH 7/8] Added NPM install support --- package.json | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 package.json diff --git a/package.json b/package.json new file mode 100644 index 0000000..543a0c1 --- /dev/null +++ b/package.json @@ -0,0 +1,22 @@ +{ + "name": "js-date-format", + "version": "0.9.12", + "description": "A patch for JavaScript Date object which adds the format functionality when converting to string", + "main": "js/date-format.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "repository": { + "type": "git", + "url": "https://github.com/barbir/js-date-format.git" + }, + "keywords": [ + "date" + ], + "author": "Miljenko Barbir", + "license": "MIT & GPL", + "bugs": { + "url": "https://github.com/barbir/js-date-format/issues" + }, + "homepage": "https://github.com/barbir/js-date-format" +} From 285aaa48c02aec0f1e866b85f3e211cad21a4176 Mon Sep 17 00:00:00 2001 From: "Gabriel R. Giannattasio" Date: Mon, 4 Nov 2013 12:07:51 -0200 Subject: [PATCH 8/8] Updated readme version --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index f525ba7..bca5897 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -Javascript Date Format Patch 0.9.11 +Javascript Date Format Patch 0.9.12 ================================================================================================ About