ui.datepicker.js 17.8 KB
Newer Older
Hzp_D's avatar
Hzp_D 已提交
1 2 3 4
'use strict';

var $ = require('jquery');
var UI = require('./core');
Hzp_D's avatar
Hzp_D 已提交
5
var $doc = $(document);
Hzp_D's avatar
Hzp_D 已提交
6 7 8 9 10 11 12

/**
 * bootstrap-datepicker.js
 * @via http://www.eyecon.ro/bootstrap-datepicker
 * @license http://www.apache.org/licenses/LICENSE-2.0
 */
var Datepicker = function(element, options) {
Hzp_D's avatar
Hzp_D 已提交
13
  this.$element = $(element);
14
  this.options = $.extend({}, Datepicker.DEFAULTS, options);
Hzp_D's avatar
Hzp_D 已提交
15
  this.format = DPGlobal.parseFormat(this.options.format);
16

17
  this.$element.data('date', this.options.date);
Hzp_D's avatar
Hzp_D 已提交
18 19 20
  this.language = this.getLocale(this.options.locale);
  this.theme = this.options.theme;
  this.$picker = $(DPGlobal.template)
Hzp_D's avatar
Hzp_D 已提交
21 22 23 24 25 26
                  .appendTo('body')
                  .on({
                    click: $.proxy(this.click, this)
                    // mousedown: $.proxy(this.mousedown, this)
                  });

Hzp_D's avatar
Hzp_D 已提交
27 28 29
  this.isInput = this.$element.is('input');
  this.component = this.$element.is('.am-datepicker-date') ?
                     this.$element.find('.am-datepicker-add-on') : false;
Hzp_D's avatar
Hzp_D 已提交
30
  if (this.isInput) {
Hzp_D's avatar
Hzp_D 已提交
31
    this.$element.on({
Hzp_D's avatar
Hzp_D 已提交
32
      'click.datepicker.amui': $.proxy(this.open, this),
Hzp_D's avatar
Hzp_D 已提交
33
      // blur: $.proxy(this.close, this),
Hzp_D's avatar
Hzp_D 已提交
34
      'keyup.datepicker.amui': $.proxy(this.update, this)
Hzp_D's avatar
Hzp_D 已提交
35 36 37
    });
  } else {
    if (this.component) {
Hzp_D's avatar
Hzp_D 已提交
38
      this.component.on('click.datepicker.amui', $.proxy(this.open, this));
Hzp_D's avatar
Hzp_D 已提交
39
    } else {
Hzp_D's avatar
Hzp_D 已提交
40
      this.$element.on('click.datepicker.amui', $.proxy(this.open, this));
Hzp_D's avatar
Hzp_D 已提交
41 42 43
    }
  }

Hzp_D's avatar
Hzp_D 已提交
44
  this.minViewMode = this.options.minViewMode;
Hzp_D's avatar
Hzp_D 已提交
45 46 47 48 49 50 51 52 53 54 55 56 57 58 59

  if (typeof this.minViewMode === 'string') {
    switch (this.minViewMode) {
      case 'months':
        this.minViewMode = 1;
        break;
      case 'years':
        this.minViewMode = 2;
        break;
      default:
        this.minViewMode = 0;
        break;
    }
  }

Hzp_D's avatar
Hzp_D 已提交
60
  this.viewMode = this.options.viewMode;
Hzp_D's avatar
Hzp_D 已提交
61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76

  if (typeof this.viewMode === 'string') {
    switch (this.viewMode) {
      case 'months':
        this.viewMode = 1;
        break;
      case 'years':
        this.viewMode = 2;
        break;
      default:
        this.viewMode = 0;
        break;
    }
  }

  this.startViewMode = this.viewMode;
Hzp_D's avatar
Hzp_D 已提交
77
  this.weekStart = this.options.weekStart;
Hzp_D's avatar
Hzp_D 已提交
78
  this.weekEnd = this.weekStart === 0 ? 6 : this.weekStart - 1;
Hzp_D's avatar
Hzp_D 已提交
79
  this.onRender = this.options.onRender;
Hzp_D's avatar
Hzp_D 已提交
80

Hzp_D's avatar
Hzp_D 已提交
81
  this.addTheme();
Hzp_D's avatar
Hzp_D 已提交
82 83 84 85 86 87 88 89 90
  this.fillDow();
  this.fillMonths();
  this.update();
  this.showMode();
};

Datepicker.prototype = {
  constructor: Datepicker,

Hzp_D's avatar
Hzp_D 已提交
91 92 93 94 95
  open: function(e) {
    this.$picker.show();
    this.height = this.component ?
        this.component.outerHeight() : this.$element.outerHeight();

Hzp_D's avatar
Hzp_D 已提交
96
    this.place();
Hzp_D's avatar
Hzp_D 已提交
97
    $(window).on('resize.datepicker.amui', $.proxy(this.place, this));
Hzp_D's avatar
Hzp_D 已提交
98 99 100 101 102
    if (e) {
      e.stopPropagation();
      e.preventDefault();
    }
    var that = this;
Hzp_D's avatar
Hzp_D 已提交
103
    $(document).on('click.datepicker.amui', function(ev) {
104
      if ($(ev.target).closest('.am-datepicker').length === 0) {
Hzp_D's avatar
Hzp_D 已提交
105
        that.close();
Hzp_D's avatar
Hzp_D 已提交
106 107
      }
    });
Hzp_D's avatar
Hzp_D 已提交
108 109
    this.$element.trigger({
      type: 'open',
Hzp_D's avatar
Hzp_D 已提交
110 111 112 113
      date: this.date
    });
  },

Hzp_D's avatar
Hzp_D 已提交
114 115
  close: function() {
    this.$picker.hide();
Hzp_D's avatar
Hzp_D 已提交
116
    $(window).off('resize.datepicker.amui', this.place);
Hzp_D's avatar
Hzp_D 已提交
117 118 119
    this.viewMode = this.startViewMode;
    this.showMode();
    if (!this.isInput) {
Hzp_D's avatar
Hzp_D 已提交
120
      $(document).off('click.datepicker.amui', this.close);
Hzp_D's avatar
Hzp_D 已提交
121 122
    }
    // this.set();
Hzp_D's avatar
Hzp_D 已提交
123 124
    this.$element.trigger({
      type: 'close',
Hzp_D's avatar
Hzp_D 已提交
125 126 127 128 129 130 131 132
      date: this.date
    });
  },

  set: function() {
    var formated = DPGlobal.formatDate(this.date, this.format);
    if (!this.isInput) {
      if (this.component) {
Hzp_D's avatar
Hzp_D 已提交
133
        this.$element.find('input').prop('value', formated);
Hzp_D's avatar
Hzp_D 已提交
134
      }
135
      this.$element.data('date', formated);
Hzp_D's avatar
Hzp_D 已提交
136
    } else {
Hzp_D's avatar
Hzp_D 已提交
137
      this.$element.prop('value', formated);
Hzp_D's avatar
Hzp_D 已提交
138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155
    }
  },

  setValue: function(newDate) {
    if (typeof newDate === 'string') {
      this.date = DPGlobal.parseDate(newDate, this.format);
    } else {
      this.date = new Date(newDate);
    }
    this.set();

    this.viewDate = new Date(this.date.getFullYear(),
                  this.date.getMonth(), 1, 0, 0, 0, 0);

    this.fill();
  },

  place: function() {
Hzp_D's avatar
Hzp_D 已提交
156
    var offset = this.component ?
Hzp_D's avatar
Hzp_D 已提交
157
                 this.component.offset() : this.$element.offset();
Hzp_D's avatar
Hzp_D 已提交
158
    var $width = this.component ?
Hzp_D's avatar
Hzp_D 已提交
159
        this.component.width() : this.$element.width();
Hzp_D's avatar
Hzp_D 已提交
160 161 162 163
    var top = offset.top + this.height;
    var left = offset.left;
    var right = $doc.width() - offset.left - $width;
    var isOutView = this.isOutView();
Hzp_D's avatar
Hzp_D 已提交
164 165
    this.$picker.removeClass('am-datepicker-right');
    this.$picker.removeClass('am-datepicker-up');
Hzp_D's avatar
Hzp_D 已提交
166 167
    if ($doc.width() > 640) {
      if (isOutView.outRight) {
Hzp_D's avatar
Hzp_D 已提交
168 169
        this.$picker.addClass('am-datepicker-right');
        this.$picker.css({
Hzp_D's avatar
Hzp_D 已提交
170 171 172 173
          top: top,
          left: 'auto',
          right: right
        });
174
        return;
Hzp_D's avatar
Hzp_D 已提交
175 176
      }
      if (isOutView.outBottom) {
Hzp_D's avatar
Hzp_D 已提交
177 178
        this.$picker.addClass('am-datepicker-up');
        top = offset.top - this.$picker.outerHeight(true);
Hzp_D's avatar
Hzp_D 已提交
179 180 181 182
      }
    } else {
      left = 0;
    }
Hzp_D's avatar
Hzp_D 已提交
183
    this.$picker.css({
Hzp_D's avatar
Hzp_D 已提交
184 185
      top: top,
      left: left
Hzp_D's avatar
Hzp_D 已提交
186 187 188 189 190
    });
  },

  update: function(newDate) {
    this.date = DPGlobal.parseDate(
Hzp_D's avatar
Hzp_D 已提交
191
            typeof newDate === 'string' ? newDate : (this.isInput ?
192
                this.$element.prop('value') : this.$element.data('date')),
Hzp_D's avatar
Hzp_D 已提交
193 194 195 196 197 198 199 200 201 202 203
        this.format
    );
    this.viewDate = new Date(this.date.getFullYear(),
        this.date.getMonth(), 1, 0, 0, 0, 0);
    this.fill();
  },

  fillDow: function() {
    var dowCnt = this.weekStart;
    var html = '<tr>';
    while (dowCnt < this.weekStart + 7) {
Hzp_D's avatar
Hzp_D 已提交
204 205 206
      html += '<th class="am-datepicker-dow">' +
          Datepicker.locales[this.language].daysMin[(dowCnt++) % 7] +
          '</th>';
Hzp_D's avatar
Hzp_D 已提交
207 208
    }
    html += '</tr>';
Hzp_D's avatar
Hzp_D 已提交
209
    this.$picker.find('.am-datepicker-days thead').append(html);
Hzp_D's avatar
Hzp_D 已提交
210 211 212 213 214 215
  },

  fillMonths: function() {
    var html = '';
    var i = 0;
    while (i < 12) {
Hzp_D's avatar
Hzp_D 已提交
216 217
      html += '<span class="am-datepicker-month">' +
          Datepicker.locales[this.language].monthsShort[i++] + '</span>';
Hzp_D's avatar
Hzp_D 已提交
218
    }
Hzp_D's avatar
Hzp_D 已提交
219
    this.$picker.find('.am-datepicker-months td').append(html);
Hzp_D's avatar
Hzp_D 已提交
220 221 222 223 224 225 226 227 228
  },

  fill: function() {
    var d = new Date(this.viewDate);
    var year = d.getFullYear();
    var month = d.getMonth();
    var currentDate = this.date.valueOf();

    var prevMonth = new Date(year, month - 1, 28, 0, 0, 0, 0);
Hzp_D's avatar
Hzp_D 已提交
229 230 231 232 233
    var day = DPGlobal
        .getDaysInMonth(prevMonth.getFullYear(), prevMonth.getMonth());

    var daysSelect = this.$picker
        .find('.am-datepicker-days .am-datepicker-select');
Hzp_D's avatar
Hzp_D 已提交
234

Hzp_D's avatar
Hzp_D 已提交
235
    if (this.language === 'zh_CN') {
Hzp_D's avatar
Hzp_D 已提交
236 237
      daysSelect.text(year + Datepicker.locales[this.language].year[0] +
          ' ' + Datepicker.locales[this.language].months[month]);
Hzp_D's avatar
Hzp_D 已提交
238
    } else {
Hzp_D's avatar
Hzp_D 已提交
239 240
      daysSelect.text(Datepicker.locales[this.language].months[month] +
          ' ' + year);
Hzp_D's avatar
Hzp_D 已提交
241 242 243 244 245 246 247 248 249 250
    }

    prevMonth.setDate(day);
    prevMonth.setDate(day - (prevMonth.getDay() - this.weekStart + 7) % 7);

    var nextMonth = new Date(prevMonth);
    nextMonth.setDate(nextMonth.getDate() + 42);
    nextMonth = nextMonth.valueOf();
    var html = [];

Hzp_D's avatar
Hzp_D 已提交
251 252 253
    var className;
    var prevY;
    var prevM;
Hzp_D's avatar
Hzp_D 已提交
254 255 256 257 258

    while (prevMonth.valueOf() < nextMonth) {
      if (prevMonth.getDay() === this.weekStart) {
        html.push('<tr>');
      }
M
Minwe 已提交
259
      className = this.onRender(prevMonth);
Hzp_D's avatar
Hzp_D 已提交
260 261 262
      prevY = prevMonth.getFullYear();
      prevM = prevMonth.getMonth();
      if ((prevM < month &&  prevY === year) ||  prevY < year) {
M
Minwe 已提交
263
        className += ' am-datepicker-old';
Hzp_D's avatar
Hzp_D 已提交
264
      } else if ((prevM > month && prevY === year) || prevY > year) {
M
Minwe 已提交
265
        className += ' am-datepicker-new';
Hzp_D's avatar
Hzp_D 已提交
266 267
      }
      if (prevMonth.valueOf() === currentDate) {
M
Minwe 已提交
268
        className += ' am-active';
Hzp_D's avatar
Hzp_D 已提交
269
      }
Hzp_D's avatar
Hzp_D 已提交
270 271 272
      html.push('<td class="am-datepicker-day ' +
          className + '">' + prevMonth.getDate() + '</td>');

Hzp_D's avatar
Hzp_D 已提交
273 274 275 276 277 278 279
      if (prevMonth.getDay() === this.weekEnd) {
        html.push('</tr>');
      }
      prevMonth.setDate(prevMonth.getDate() + 1);

    }

Hzp_D's avatar
Hzp_D 已提交
280 281 282
    this.$picker.find('.am-datepicker-days tbody')
        .empty().append(html.join(''));

Hzp_D's avatar
Hzp_D 已提交
283 284
    var currentYear = this.date.getFullYear();

Hzp_D's avatar
Hzp_D 已提交
285
    var months = this.$picker.find('.am-datepicker-months')
Hzp_D's avatar
Hzp_D 已提交
286 287 288 289 290 291 292 293 294 295 296
        .find('.am-datepicker-select')
        .text(year);
    months = months.end()
              .find('span').removeClass('am-active');

    if (currentYear === year) {
      months.eq(this.date.getMonth()).addClass('am-active');
    }

    html = '';
    year = parseInt(year / 10, 10) * 10;
Hzp_D's avatar
Hzp_D 已提交
297
    var yearCont = this.$picker
Hzp_D's avatar
Hzp_D 已提交
298 299 300 301 302 303 304 305
        .find('.am-datepicker-years')
        .find('.am-datepicker-select')
        .text(year + '-' + (year + 9))
        .end()
        .find('td');

    year -= 1;
    for (var i = -1; i < 11; i++) {
Hzp_D's avatar
Hzp_D 已提交
306 307 308
      html += '<span class="' +
          (i === -1 || i === 10 ? ' am-datepicker-old' : '') +
          (currentYear === year ? ' am-active' : '') + '">' + year + '</span>';
Hzp_D's avatar
Hzp_D 已提交
309 310 311 312 313 314 315 316 317
      year += 1;
    }
    yearCont.html(html);

  },

  click: function(event) {
    event.stopPropagation();
    event.preventDefault();
Hzp_D's avatar
Hzp_D 已提交
318 319
    var month;
    var year;
Hzp_D's avatar
Hzp_D 已提交
320 321 322 323 324 325 326 327 328 329 330 331 332

    var target = $(event.target).closest('span, td, th');
    if (target.length === 1) {
      switch (target[0].nodeName.toLowerCase()) {
        case 'th':
          switch (target[0].className) {
            case 'am-datepicker-switch':
              this.showMode(1);
              break;
            case 'am-datepicker-prev':
            case 'am-datepicker-next':
              this.viewDate['set' + DPGlobal.modes[this.viewMode].navFnc].call(
                  this.viewDate,
Hzp_D's avatar
Hzp_D 已提交
333 334 335 336 337
                      this.viewDate
                          ['get' + DPGlobal.modes[this.viewMode].navFnc]
                          .call(this.viewDate) +
                      DPGlobal.modes[this.viewMode].navStep *
                      (target[0].className === 'am-datepicker-prev' ? -1 : 1)
Hzp_D's avatar
Hzp_D 已提交
338 339 340 341 342 343 344 345
              );
              this.fill();
              this.set();
              break;
          }
          break;
        case 'span':
          if (target.is('.am-datepicker-month')) {
Hzp_D's avatar
Hzp_D 已提交
346
            month = target.parent().find('span').index(target);
Hzp_D's avatar
Hzp_D 已提交
347 348
            this.viewDate.setMonth(month);
          } else {
Hzp_D's avatar
Hzp_D 已提交
349
            year = parseInt(target.text(), 10) || 0;
Hzp_D's avatar
Hzp_D 已提交
350 351 352 353
            this.viewDate.setFullYear(year);
          }
          if (this.viewMode !== 0) {
            this.date = new Date(this.viewDate);
Hzp_D's avatar
Hzp_D 已提交
354
            this.$element.trigger({
Hzp_D's avatar
Hzp_D 已提交
355
              type: 'changeDate.datepicker.amui',
Hzp_D's avatar
Hzp_D 已提交
356 357 358 359 360 361 362 363 364 365 366
              date: this.date,
              viewMode: DPGlobal.modes[this.viewMode].clsName
            });
          }
          this.showMode(-1);
          this.fill();
          this.set();
          break;
        case 'td':
          if (target.is('.am-datepicker-day') && !target.is('.am-disabled')) {
            var day = parseInt(target.text(), 10) || 1;
Hzp_D's avatar
Hzp_D 已提交
367
            month = this.viewDate.getMonth();
Hzp_D's avatar
Hzp_D 已提交
368 369 370 371 372
            if (target.is('.am-datepicker-old')) {
              month -= 1;
            } else if (target.is('.am-datepicker-new')) {
              month += 1;
            }
Hzp_D's avatar
Hzp_D 已提交
373
            year = this.viewDate.getFullYear();
Hzp_D's avatar
Hzp_D 已提交
374 375 376 377
            this.date = new Date(year, month, day, 0, 0, 0, 0);
            this.viewDate = new Date(year, month, Math.min(28, day), 0,0,0,0);
            this.fill();
            this.set();
Hzp_D's avatar
Hzp_D 已提交
378
            this.$element.trigger({
Hzp_D's avatar
Hzp_D 已提交
379
              type: 'changeDate.datepicker.amui',
Hzp_D's avatar
Hzp_D 已提交
380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399
              date: this.date,
              viewMode: DPGlobal.modes[this.viewMode].clsName
            });
          }
          break;
      }
    }
  },

  mousedown: function(event) {
    event.stopPropagation();
    event.preventDefault();
  },

  showMode: function(dir) {
    if (dir) {
      this.viewMode = Math.max(this.minViewMode,
          Math.min(2, this.viewMode + dir));
    }

Hzp_D's avatar
Hzp_D 已提交
400
    this.$picker
Hzp_D's avatar
Hzp_D 已提交
401 402 403 404
        .find('>div')
        .hide()
        .filter('.am-datepicker-' + DPGlobal.modes[this.viewMode].clsName)
        .show();
Hzp_D's avatar
Hzp_D 已提交
405 406 407 408
  },

  isOutView: function() {
    var offset = this.component ?
Hzp_D's avatar
Hzp_D 已提交
409
        this.component.offset() : this.$element.offset();
Hzp_D's avatar
Hzp_D 已提交
410 411 412 413
    var isOutView = {
      outRight: false,
      outBottom: false
    };
Hzp_D's avatar
Hzp_D 已提交
414
    var $picker = this.$picker;
Hzp_D's avatar
Hzp_D 已提交
415
    var width = offset.left + $picker.outerWidth(true);
Hzp_D's avatar
Hzp_D 已提交
416 417
    var height = offset.top + $picker.outerHeight(true) +
        this.$element.innerHeight();
Hzp_D's avatar
Hzp_D 已提交
418 419 420 421 422 423 424 425 426 427

    if (width > $doc.width()) {
      isOutView.outRight = true;
    }
    if (height > $doc.height()) {
      isOutView.outBottom = true;
    }
    return isOutView;
  },

M
Minwe 已提交
428 429 430 431 432
  getLocale: function(locale) {
    if (!locale) {
      locale = navigator.language && navigator.language.split('-');
      locale[1] = locale[1].toUpperCase();
      locale = locale.join('_');
Hzp_D's avatar
Hzp_D 已提交
433
    }
M
Minwe 已提交
434 435 436 437 438

    if (!Datepicker.locales[locale]) {
      locale = 'en_US';
    }
    return locale;
Hzp_D's avatar
Hzp_D 已提交
439 440 441 442
  },

  addTheme: function() {
    if (this.theme) {
Hzp_D's avatar
Hzp_D 已提交
443
      this.$picker.addClass('am-datepicker-' + this.theme);
Hzp_D's avatar
Hzp_D 已提交
444
    }
Hzp_D's avatar
Hzp_D 已提交
445 446 447 448
  }
};

Datepicker.DEFAULTS = {
M
Minwe 已提交
449 450
  locale: 'zh_CN',
  format: 'yyyy-mm-dd',
Hzp_D's avatar
Hzp_D 已提交
451 452
  weekStart: 0,
  viewMode: 0,
Hzp_D's avatar
Hzp_D 已提交
453 454
  minViewMode: 0,
  date: '',
455 456 457 458
  theme: '',
  onRender: function(date) {
    return '';
  }
Hzp_D's avatar
Hzp_D 已提交
459 460
};

Hzp_D's avatar
Hzp_D 已提交
461 462 463 464
// Datepicker locales

Datepicker.locales = {
  en_US: {
Hzp_D's avatar
Hzp_D 已提交
465 466 467 468 469 470 471 472 473 474 475
    days: ['Sunday', 'Monday', 'Tuesday', 'Wednesday',
      'Thursday', 'Friday', 'Saturday'],

    daysShort: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'],
    daysMin: ['Su', 'Mo', 'Tu', 'We', 'Th', 'Fr', 'Sa'],

    months: ['January', 'February', 'March', 'April', 'May', 'June',
      'July', 'August', 'September', 'October', 'November', 'December'],

    monthsShort: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun',
      'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec']
Hzp_D's avatar
Hzp_D 已提交
476
  },
Hzp_D's avatar
Hzp_D 已提交
477
  zh_CN: {
Hzp_D's avatar
Hzp_D 已提交
478 479 480 481 482 483 484 485 486
    days: ['星期日', '星期一', '星期二', '星期三', '星期四', '星期五', '星期六'],
    daysShort: ['周日', '周一', '周二', '周三', '周四', '周五', '周六'],
    daysMin: ['', '', '', '', '', '', ''],

    months: ['一月', '二月', '三月', '四月', '五月', '六月', '七月',
      '八月', '九月', '十月', '十一月', '十二月'],

    monthsShort: ['一月', '二月', '三月', '四月', '五月', '六月',
      '七月', '八月', '九月', '十月', '十一月', '十二月'],
Hzp_D's avatar
Hzp_D 已提交
487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509
    year: ['']
  }
};

var DPGlobal = {
  modes: [
    {
      clsName: 'days',
      navFnc: 'Month',
      navStep: 1
    },
    {
      clsName: 'months',
      navFnc: 'FullYear',
      navStep: 1
    },
    {
      clsName: 'years',
      navFnc: 'FullYear',
      navStep: 10
    }
  ],
  isLeapYear: function(year) {
510
    return (((year % 4 === 0) && (year % 100 !== 0)) || (year % 400 === 0));
Hzp_D's avatar
Hzp_D 已提交
511 512
  },
  getDaysInMonth: function(year, month) {
Hzp_D's avatar
Hzp_D 已提交
513 514
    return [31, (DPGlobal.isLeapYear(year) ? 29 : 28),
      31, 30, 31, 30, 31, 31, 30, 31, 30, 31][month];
Hzp_D's avatar
Hzp_D 已提交
515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530
  },
  parseFormat: function(format) {
    var separator = format.match(/[.\/\-\s].*?/);
    var parts = format.split(/\W+/);

    if (!separator || !parts || parts.length === 0) {
      throw new Error('Invalid date format.');
    }
    return {
      separator: separator,
      parts: parts
    };
  },
  parseDate: function(date, format) {
    var parts = date.split(format.separator);
    var val;
Hzp_D's avatar
Hzp_D 已提交
531
    date = new Date();
Hzp_D's avatar
Hzp_D 已提交
532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576

    date.setHours(0);
    date.setMinutes(0);
    date.setSeconds(0);
    date.setMilliseconds(0);

    if (parts.length === format.parts.length) {
      var year = date.getFullYear();
      var day = date.getDate();
      var month = date.getMonth();

      for (var i = 0, cnt = format.parts.length; i < cnt; i++) {
        val = parseInt(parts[i], 10) || 1;
        switch (format.parts[i]) {
          case 'dd':
          case 'd':
            day = val;
            date.setDate(val);
            break;
          case 'mm':
          case 'm':
            month = val - 1;
            date.setMonth(val - 1);
            break;
          case 'yy':
            year = 2000 + val;
            date.setFullYear(2000 + val);
            break;
          case 'yyyy':
            year = val;
            date.setFullYear(val);
            break;
        }
      }
      date = new Date(year, month, day, 0, 0, 0);
    }
    return date;
  },
  formatDate: function(date, format) {
    var val = {
      d: date.getDate(),
      m: date.getMonth() + 1,
      yy: date.getFullYear().toString().substring(2),
      yyyy: date.getFullYear()
    };
Hzp_D's avatar
Hzp_D 已提交
577
    var dateArray = [];
Hzp_D's avatar
Hzp_D 已提交
578 579 580 581 582

    val.dd = (val.d < 10 ? '0' : '') + val.d;
    val.mm = (val.m < 10 ? '0' : '') + val.m;

    for (var i = 0, cnt = format.parts.length; i < cnt; i++) {
Hzp_D's avatar
Hzp_D 已提交
583
      dateArray.push(val[format.parts[i]]);
Hzp_D's avatar
Hzp_D 已提交
584
    }
Hzp_D's avatar
Hzp_D 已提交
585
    return dateArray.join(format.separator);
Hzp_D's avatar
Hzp_D 已提交
586 587 588
  },
  headTemplate: '<thead>' +
      '<tr class="am-datepicker-header">' +
Hzp_D's avatar
Hzp_D 已提交
589 590 591 592 593 594
      '<th class="am-datepicker-prev">' +
      '<i class="am-datepicker-prev-icon"></i></th>' +
      '<th colspan="5" class="am-datepicker-switch">' +
      '<div class="am-datepicker-select"></div></th>' +
      '<th class="am-datepicker-next"><i class="am-datepicker-next-icon"></i>' +
      '</th></tr></thead>',
Hzp_D's avatar
Hzp_D 已提交
595 596 597
  contTemplate: '<tbody><tr><td colspan="7"></td></tr></tbody>'
};

Hzp_D's avatar
Hzp_D 已提交
598 599
DPGlobal.template = '<div class="am-datepicker am-datepicker-dropdown">' +
    '<div class="am-datepicker-caret"></div>' +
Hzp_D's avatar
Hzp_D 已提交
600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624
    '<div class="am-datepicker-days">' +
    '<table class="am-datepicker-table">' +
    DPGlobal.headTemplate +
    '<tbody></tbody>' +
    '</table>' +
    '</div>' +
    '<div class="am-datepicker-months">' +
    '<table class="am-datepicker-table">' +
    DPGlobal.headTemplate +
    DPGlobal.contTemplate +
    '</table>' +
    '</div>' +
    '<div class="am-datepicker-years">' +
    '<table class="am-datepicker-table">' +
    DPGlobal.headTemplate +
    DPGlobal.contTemplate +
    '</table>' +
    '</div>' +
    '</div>';

$.fn.datepicker = function(option, val) {
  return this.each(function() {
    var $this = $(this);
    var data = $this.data('amui.datepicker');

625
    var options = $.extend({},
626
      UI.utils.options($this.data('am-datepicker')),
Hzp_D's avatar
Hzp_D 已提交
627 628
            typeof option === 'object' && option);
    if (!data) {
629
      $this.data('amui.datepicker', (data = new Datepicker(this, options)));
Hzp_D's avatar
Hzp_D 已提交
630 631
    }
    if (typeof option === 'string') {
632
      data[option] && data[option](val);
Hzp_D's avatar
Hzp_D 已提交
633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648
    }
  });
};

$.fn.datepicker.Constructor = Datepicker;

// Init code
$(document).on('ready', function(e) {
  $('[data-am-datepicker]').datepicker();
});

$.AMUI.datepicker = Datepicker;

module.exports = Datepicker;

// TODO: 1. 载入动画
Hzp_D's avatar
Hzp_D 已提交
649
//       2. less 优化