]> git.sur5r.net Git - contagged/blob - js/date-formatting.js
interactive note adding
[contagged] / js / date-formatting.js
1 /*
2  * A Javascript date chooser.
3  * Copyright (C) 2004 Baron Schwartz <baron at sequent dot org>
4  * 
5  * This program is free software; you can redistribute it and/or modify it under
6  * the terms of the GNU General Public License as published by the Free Software
7  * Foundation; either version 2 of the License, or (at your option) any later
8  * version.
9  * 
10  * This program is distributed in the hope that it will be useful, but WITHOUT
11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
12  * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
13  * details.
14  * 
15  * You should have received a copy of the GNU General Public License along with
16  * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
17  * Place, Suite 330, Boston, MA 02111-1307  USA
18  */
19
20 Date.formatFunctions = {count:0};
21
22 Date.prototype.dateFormat = function(format) {
23     if (Date.formatFunctions[format] == null) {
24         Date.createNewFormat(format);
25     }
26     var func = Date.formatFunctions[format];
27     return eval("this." + func + "();");
28 }
29
30 Date.createNewFormat = function(format) {
31     var funcName = "format" + Date.formatFunctions.count++;
32     Date.formatFunctions[format] = funcName;
33     var code = "Date.prototype." + funcName + " = function(){return ";
34     var special = false;
35     var char = '';
36     for (var i = 0; i < format.length; ++i) {
37         char = format.charAt(i);
38         if (!special && char == "\\") {
39             special = true;
40         }
41         else if (special) {
42             special = false;
43             code += "'" + String.escape(char) + "' + ";
44         }
45         else {
46             code += Date.getFormatCode(char);
47         }
48     }
49     eval(code.substring(0, code.length - 3) + ";}");
50 }
51
52 Date.getFormatCode = function(character) {
53     switch (character) {
54     case "d":
55         return "String.leftPad(this.getDate(), 2, '0') + ";
56     case "D":
57         return "Date.dayNames[this.getDay()].substring(0, 3) + ";
58     case "j":
59         return "this.getDate() + ";
60     case "l":
61         return "Date.dayNames[this.getDay()] + ";
62     case "S":
63         return "this.getSuffix() + ";
64     case "w":
65         return "this.getDay() + ";
66     case "z":
67         return "this.getDayOfYear() + ";
68     case "W":
69         return "this.getWeekOfYear() + ";
70     case "F":
71         return "Date.monthNames[this.getMonth()] + ";
72     case "m":
73         return "String.leftPad(this.getMonth() + 1, 2, '0') + ";
74     case "M":
75         return "Date.monthNames[this.getMonth()].substring(0, 3) + ";
76     case "n":
77         return "(this.getMonth() + 1) + ";
78     case "t":
79         return "this.getDaysInMonth() + ";
80     case "L":
81         return "(this.isLeapYear() ? 1 : 0) + ";
82     case "Y":
83         return "this.getFullYear() + ";
84     case "y":
85         return "('' + this.getFullYear()).substring(2, 4) + ";
86     case "a":
87         return "(this.getHours() < 12 ? 'am' : 'pm') + ";
88     case "A":
89         return "(this.getHours() < 12 ? 'AM' : 'PM') + ";
90     case "g":
91         return "((this.getHours() %12) ? this.getHours() % 12 : 12) + ";
92     case "G":
93         return "this.getHours() + ";
94     case "h":
95         return "String.leftPad((this.getHours() %12) ? this.getHours() % 12 : 12, 2, '0') + ";
96     case "H":
97         return "String.leftPad(this.getHours(), 2, '0') + ";
98     case "i":
99         return "String.leftPad(this.getMinutes(), 2, '0') + ";
100     case "s":
101         return "String.leftPad(this.getSeconds(), 2, '0') + ";
102     case "O":
103         return "this.getGMTOffset() + ";
104     case "T":
105         return "this.getTimezone() + ";
106     case "Z":
107         return "(this.getTimezoneOffset() * -60) + ";
108     default:
109         return "'" + String.escape(character) + "' + ";
110     }
111 }
112
113 Date.prototype.getTimezone = function() {
114     return this.toString().replace(
115         /^.*? ([A-Z]{3}) [0-9]{4}.*$/, "$1").replace(
116         /^.*?\(([A-Z])[a-z]+ ([A-Z])[a-z]+ ([A-Z])[a-z]+\)$/, "$1$2$3");
117 }
118
119 Date.prototype.getGMTOffset = function() {
120     return (this.getTimezoneOffset() > 0 ? "-" : "+")
121         + String.leftPad(Math.floor(this.getTimezoneOffset() / 60), 2, "0")
122         + String.leftPad(this.getTimezoneOffset() % 60, 2, "0");
123 }
124
125 Date.prototype.getDayOfYear = function() {
126     var num = 0;
127     Date.daysInMonth[1] = this.isLeapYear() ? 29 : 28;
128     for (var i = 0; i < this.getMonth(); ++i) {
129         num += Date.daysInMonth[i];
130     }
131     return num + this.getDate() - 1;
132 }
133
134 Date.prototype.getWeekOfYear = function() {
135     // Skip to Thursday of this week
136     var now = this.getDayOfYear() + (4 - this.getDay());
137     // Find the first Thursday of the year
138     var jan1 = new Date(this.getFullYear(), 0, 1);
139     var then = (7 - jan1.getDay() + 4);
140     document.write(then);
141     return String.leftPad(((now - then) / 7) + 1, 2, "0");
142 }
143
144 Date.prototype.isLeapYear = function() {
145     var year = this.getFullYear();
146     return ((year & 3) == 0 && (year % 100 || (year % 400 == 0 && year)));
147 }
148
149 Date.prototype.getFirstDayOfMonth = function() {
150     var day = (this.getDay() - (this.getDate() - 1)) % 7;
151     return (day < 0) ? (day + 7) : day;
152 }
153
154 Date.prototype.getLastDayOfMonth = function() {
155     var day = (this.getDay() + (Date.daysInMonth[this.getMonth()] - this.getDate())) % 7;
156     return (day < 0) ? (day + 7) : day;
157 }
158
159 Date.prototype.getDaysInMonth = function() {
160     Date.daysInMonth[1] = this.isLeapYear() ? 29 : 28;
161     return Date.daysInMonth[this.getMonth()];
162 }
163
164 Date.prototype.getSuffix = function() {
165     switch (this.getDate()) {
166         case 1:
167         case 21:
168         case 31:
169             return "st";
170         case 2:
171         case 22:
172             return "nd";
173         case 3:
174         case 23:
175             return "rd";
176         default:
177             return "th";
178     }
179 }
180
181 String.escape = function(string) {
182     return string.replace(/('|\\)/g, "\\$1");
183 }
184
185 String.leftPad = function (val, size, char) {
186     var result = new String(val);
187     if (char == null) {
188         char = " ";
189     }
190     while (result.length < size) {
191         result = char + result;
192     }
193     return result;
194 }
195
196 Date.daysInMonth = [31,28,31,30,31,30,31,31,30,31,30,31];
197 Date.monthNames =
198    ["January",
199     "February",
200     "March",
201     "April",
202     "May",
203     "June",
204     "July",
205     "August",
206     "September",
207     "October",
208     "November",
209     "December"];
210 Date.dayNames =
211    ["Sunday",
212     "Monday",
213     "Tuesday",
214     "Wednesday",
215     "Thursday",
216     "Friday",
217     "Saturday"];
218 Date.patterns = {
219     ISO8601LongPattern:"Y-m-d H:i:s",
220     ISO8601ShortPattern:"Y-m-d",
221     ShortDatePattern: "n/j/Y",
222     LongDatePattern: "l, F d, Y",
223     FullDateTimePattern: "l, F d, Y g:i:s A",
224     MonthDayPattern: "F d",
225     ShortTimePattern: "g:i A",
226     LongTimePattern: "g:i:s A",
227     SortableDateTimePattern: "Y-m-d\\TH:i:s",
228     UniversalSortableDateTimePattern: "Y-m-d H:i:sO",
229     YearMonthPattern: "F, Y"};
230
231 Date.parseIsoDate = function(dateString) {
232     var result = new Date();
233     var re = /^(\d\d\d\d)-(\d\d)-(\d\d)( (\d\d):(\d\d):(\d\d))?$/;
234     var match = dateString.match(re);
235     if (match != null) {
236         if (match[5] != null && match[5] != '') {
237             result = new Date(
238                 parseInt(match[1], 10),
239                 parseInt(match[2], 10) - 1,
240                 parseInt(match[3], 10),
241                 parseInt(match[5], 10),
242                 parseInt(match[6], 10),
243                 parseInt(match[7], 10));
244         }
245         else {
246             result = new Date(
247                 parseInt(match[1], 10),
248                 parseInt(match[2], 10) - 1,
249                 parseInt(match[3], 10));
250         }
251     }
252     return result;
253 }