JQuery UI Datepicker теряет фокус при выборе даты с помощью мыши

Я использую JQuery UI с DatePicker, и когда пользователь вкладывает в поле, они соответственно получают всплывающий календарь.

  1. Пользовательские вкладки (через клавишу на поле
  2. Пользователь выбирает дату щелчком мыши
  3. Пользовательские вкладки
  4. Tabindex начинается сначала (в начале формы)

Вот код. (Может также быть установлен индекс вкладки)

<input type="text" name="demo" />
<input type="text" class="date" />

Код jquery:

$(".date").datepicker();

Любые предложения о том, как я мог бы решить эту проблему (бонус к кратчайшему решению)?

9 ответов

Решение

Подписаться на onClose или onSelect событие:

$("#someinput").datepicker(
{
    // other options goes here
    onSelect: function ()
    {
        // The "this" keyword refers to the input (in this case: #someinput)
        this.focus();
    }
});

Или в случае onClose:

$("#someinput").datepicker(
{
    onClose: function ()
    {
        this.focus();
    }
});

См. Обсуждение этой проблемы на http://bugs.jqueryui.com/ticket/7266 с решением по адресу http://jsfiddle.net/lankarden/9FtnW/

Спасибо за предложение Джефф, я изменил вашу функцию onSelect, чтобы использовать фильтр атрибутов для извлечения только элементов с tabindex, заданным параметром "nexttab".

$(function(){
  $(".date").datepicker({
      onSelect: function(){
          currenttab = $(el).attr("tabindex");
          nexttab = currenttab * 1 + 1;
          $("[tabindex='" + nexttab + "']").focus();
      }
  });
});

PS: Если в вашем коде не указаны табличные индексы, как я раньше не делал, просто добавьте следующий код:

$('input, select').each(function(i, val){
    $(this).attr('tabindex', i + 1);
});

Подобно подходу Джимми, но это устанавливает фокус на значок календаря (при условии, что ваш календарь использует значок), я нашел этот способ более подходящим, когда у меня было несколько сборщиков дат рядом друг с другом.

Установите параметры даты по умолчанию, чтобы они устанавливали фокус на значок при закрытии всплывающего окна календаря:

    $(".date").datepicker({
        onClose: function() {
            $(this).next('a').focus(); 
        }
    });

Добавьте метку к значку календаря, чтобы он был фокусируемым:

    $(".date").each(function() {
        $($(this).next('img')).wrap($("<A/>").attr("href","#"));
    });

Если вы действительно не заботитесь о порядке вкладок, то есть, если он не назначен, чтобы он следовал за ходом страницы, вы можете сделать что-то вроде этого.

jQuery('.date').datepicker({
    'onSelect': function(){
        $(this).nextAll('input, button, textarea, a').filter(':first').focus();
    }
});

Он работает в предположении, что когда пользователь выбирает дату, он заканчивает работу с этим полем и переходит к следующему, поэтому он просто выбирает следующее поле.

Я добавил пустой тег href рядом с элементом управления вводом datepicker и сосредоточился на нем в обработчике события onClose. Это решило мою проблему смещения фокуса полностью вверх страницы, когда календарь был закрыт. Я использую этот тег href для отображения сообщений об ошибках; поэтому он служит для меня двум целям.

Я также должен был решить эту проблему и обнаружил, что данные ответы не совсем то, что я искал. Вот что я сделал.

В блоге упоминается функция jQuery, которая позволит вам выбрать следующий элемент формы на экране. Я импортировал это в свой проект и назвал его onClose в диалоге выбора даты.

В случае, если ссылка не работает, вот функция

$.fn.focusNextInputField = function() {
    return this.each(function() {
        var fields = $(this).parents('form:eq(0),body').find('button,input,textarea,select');
        var index = fields.index( this );
        if ( index > -1 && ( index + 1 ) < fields.length ) {
            fields.eq( index + 1 ).focus();
        }
        return false;
    });
};

Тогда просто назвал это onClose of datepicker

$(this).datepicker({
    onClose: function () {
       $(this).focusNextInputField();
    }
});

Надеюсь, это поможет будущим посетителям.

Мне удалось переместить фокус на следующее поле ввода после нажатия клавиши ввода (которая по умолчанию выбирает текущую дату) или при нажатии на дату в календаре с помощью этой кнопки.

$(".jqDateField").datepicker('option', {
    dateFormat: 'mm/dd/y', onClose: function () {
        $(':input:eq(' + ($(':input').index(this) + 1) + ')').focus();
    }
});

Это может потребоваться для установки фокуса на следующий текстовый ввод, если у вас есть кнопка выбора или кнопка "путь"

$(':input[type="text"]:eq(' + ($(':input[type="text"]').index(this) + 1) + ')')

Сосредоточение его на одной и той же рамке в конечном итоге вызывает всплывающее окно выбора даты, и мы действительно хотим, чтобы он перешел к следующему полю. Вот разработанное решение:

  1. Требует, чтобы атрибут tabindex был установлен на ваших полях.
  2. Это приведение от строки к int в JavaScript (* 1).
  3. Это фактически перемещает выбранное поле к следующему элементу вместо текущего фокуса

    $(function(){
      $(".date").datepicker({
          onSelect: function(){
              currenttab = $(this).attr("tabindex");
              nexttab = currenttab * 1 + 1;
              $(":input").each(function(){
                  if ($(this).attr("tabindex") == nexttab)
                     $(this).focus();
              });
      }
      });
    });
    

Любые предложения по улучшению этой техники приветствуются.

Вы, вероятно, можете использовать onClose событие для возврата фокуса на ваш ввод при закрытии DatePicker, как this ссылается на соответствующее поле ввода в этом обратном вызове. Например:

$('.date').datepicker({
   onClose: function() { this.focus(); }
});
Другие вопросы по тегам