Заметки за декабрь 2009 года

Модули в YUI3

Первая приятная особенность, с которой приходится столкнуться при работе с YUI3, это модульность и динамическая загрузка этих модулей.

Создать модуль можно, например, на основе следующего кода:

YUI.add("mymodule", function(Y) {
    Y.MyModule = function() {
        // конструктор
    };
});

В дальнейшем он используется так:

YUI().use("mymodule", function (Y) {
    var o = new Y.MyModule();
});

Основная задача шаблона — это изолировать модуль и подключать его к экземпляру YUI (переменная Y в YUI.add и YUI.use) только при необходимости.

При создании экземпляра YUI можно указать в конфигурации атрибуты для динамической загрузки нашего модуля и нужных ему зависимостей.

YUI({
    modules: {
        "mymodule":{
            // полный путь к файлу
            fullpath:"mymodule.js",
            // зависимости модуля
            requires: ["dd", "widget"]
        }
    }
}).use("mymodule", function () {
    // код приложения
});

Указав необходимые модулю зависимости (requires) мы тем самым позволяем загрузчику оптимизировать список файлов, которые требуется загрузить и минимизировать число HTTP подключений.

Так же эти зависимости нужно указать в YUI.add

YUI.add("mymodule", function(Y) {
    Y.MyModule = function() {
        // конструктор
    };
}, "1.0", {requires: ["dd", "widget"], use: ["dd", "widget"]});

Данные, которые передаются при объявлении, указывают на то, что требуется для работы модуля, когда он загружен и используется в методе YUI.use. Так код модуль может быть явно подключен на странице.

Оставте свой комментарий

Выбор диапазона дат с помощью jQuery UI Datepicker

Для очередного проекта понадобился виджет для выбора даты. Очевидным, по крайней мере для меня, решением было jQuery UI Datepicker. Но когда позже понадобилось выбирать не одну дату, а диапазон, я попал в тупик. В API не было ни какого упоминания о такой возможности. Поисковики все как один выдавали какие-то «самоделки» далеко не первой свежести.

Копнув глубже исходники Datepicker, я все-таки обнаружил возможность выбора диапазона. Реализуется все логика через событие «onSelect».

У экземпляра Datepicker есть флаг stayOpen. Если его установить внутри события, то календарь не закроется после клика, а занесет выбранную дату в поле rangeStart и позволит выбрать еще дату. Когда будет выбран конец диапазона, нужно сбросить флаг stayOpen и обновить содержимое текстового поля.

Внимание! Плагин актуален только для jQuery UI 1.7.x. Для последних версий нужно использовать другую редакцию этого плагина.

(function ($) {

  $.fn.daterange = function () {
    // опции
    var opts = $.extend({
      "dateFormat": "dd.mm.yy",
      "changeMonth": false,
      "changeYear": false,
      "numberOfMonths": 2,
      "rangeSeparator": "-"
    }, arguments[0] || {}, {
      // обработчики событий datepicker
      // закрытие
      "onClose": function (dateText, inst) {
        if ($.isFunction(opts.callback)) {
          opts.callback.apply(this, arguments);
        }
      },
      // выбор даты
      "onSelect": function (dateText, inst) {
        var textStart;
          if (!inst.rangeStart) {
            inst.stayOpen = true;
          } else {
            inst.stayOpen = false;
            textStart = $.datepicker.formatDate(opts.dateFormat, inst.rangeStart);
            if (textStart !== dateText) {
              $(this).val(textStart + " " +
                opts.rangeSeparator + " " + dateText);
            }
          }
      }
    });

    return this.each(function () {
      var input = $(this);
      if (input.is("input")) {
        input.datepicker(opts);
      }
    });
  };

}(jQuery));

Еще одно событие, которое может пригодиться, это «onClose». Оно будет сгенерировано в момент закрытия календаря. В плагине я просто делегирую все исполнение внешнему обработчику, но на практике мне удобно было добавить туда больше функционала.

Плагин может быть проинициализирован любыми параметрами, которые используются в Datepicker. Так как обработчик события «onClose» переопределяется, то вместо него используется поле callback.

Второе дыхание

Обновлено 2013-06-19

Для последних версий jQuery UI вместо stayOpen нужно использовать флаг inline. Однако это только запретит календарю закрыться. Нужно ещё позаботиться о сохранении первой выбранной даты.

(function ($) {

  $.fn.daterange = function () {
    // опции
    var opts = $.extend({
      "dateFormat": "dd.mm.yy",
      "changeMonth": false,
      "changeYear": false,
      "numberOfMonths": 2,
      "rangeSeparator": "-"
    }, arguments[0] || {}, {
      // обработчики событий datepicker
      // закрытие
      "onClose": function (dateText, inst) {
        if ($.isFunction(opts.callback)) {
          opts.callback.apply(this, arguments);
        }
      },
      // выбор даты
      "onSelect": function (dateText, inst) {
        var textStart;
          if (!inst.rangeStart) {
            inst.inline = true;
            inst.rangeStart = dateText;
          } else {
            inst.inline = false;
            textStart = inst.rangeStart;
            if (textStart !== dateText) {
              $(this).val(textStart + " " +
                opts.rangeSeparator + " " + dateText);
              inst.rangeStart = null;
            }
          }
      }
    });

    return this.each(function () {
      var input = $(this);
      if (input.is("input")) {
        input.datepicker(opts);
      }
    });
  };

}(jQuery));
Комментарии к заметке: 20