Я хотел бы узнать в JavaScript, какой элемент в настоящее время имеет фокус. Я просматривал DOM и пока не нашел то, что мне нужно. Есть ли способ сделать это и как?
Причина, по которой я искал это:
Я пытаюсь сделать клавиши как стрелки и enter
перемещаться по таблице элементов ввода. Вкладка теперь работает, но вводи, а стрелки не по умолчанию вроде бы. Я настроил часть обработки ключей, но теперь мне нужно выяснить, как переместить фокус в функции обработки событий.
javascript
dom
Тони Петерсон
источник
источник
find-focused-element
пакет: npmjs.com/package/find-focused-elementОтветы:
Используйте
document.activeElement
, это поддерживается во всех основных браузерах.Ранее, если вы пытались выяснить, какое поле формы имеет фокус, вы не могли этого сделать. Чтобы эмулировать обнаружение в старых браузерах, добавьте обработчик события «focus» ко всем полям и запишите последнее сфокусированное поле в переменной. Добавьте обработчик «размытия», чтобы очистить переменную после события размытия для последнего сфокусированного поля.
Если вам нужно удалить,
activeElement
вы можете использовать размытие;document.activeElement.blur()
, Это изменитactiveElement
Tobody
.Ссылки по теме:
источник
activeElement
на самом деле не возвращает сфокусированный элемент. Любой элемент может иметь фокус. Если документ имеет 4 scrolldivs, 0 или 1 из этих div можно прокручивать клавишами со стрелками. Если вы нажмете один, этот div будет сфокусирован. Если вы нажмете за пределами всего, тело сфокусировано. Как вы узнаете, какой скроллдив сфокусирован? jsfiddle.net/rudiedirkx/bC5ke/show (проверьте консоль)div
это Firefox 17, и только при помощи вкладок . Типы элементов, черезdocument.activeElement
которые возвращаются ВСЕ основные браузеры , ограничены элементами, связанными с вводом . Если ни один такой элемент не имеет фокуса, все основные браузеры возвращаютbody
элемент - кроме IE 9, который возвращаетhtml
элемент.document.activeElement
должен быть заключен в a, такtry catch
как при некоторых обстоятельствах он может вызвать исключение (не только IE9 AFAIK). См. Bugs.jquery.com/ticket/13393 и bugs.jqueryui.com/ticket/8443Как сказал JW, вы не можете найти текущий фокусированный элемент, по крайней мере, независимо от браузера. Но если ваше приложение предназначено только для IE (некоторые из них ...), вы можете найти его следующим образом:
РЕДАКТИРОВАТЬ: Похоже, что IE не все не так, в конце концов, это часть проекта HTML5 и, кажется, поддерживается по крайней мере последней версии Chrome, Safari и Firefox.
источник
Если вы можете использовать jQuery, он теперь поддерживает: focus, просто убедитесь, что вы используете версию 1.6+.
Это утверждение даст вам в настоящее время сосредоточенный элемент.
От: Как выбрать элемент, который фокусируется на нем, с помощью jQuery
источник
return elem === document.activeElement && (!document.hasFocus || document.hasFocus()) && !!(elem.type || elem.href || ~elem.tabIndex);
document.activeElement
в настоящее время является частью спецификации рабочего проекта HTML5 , но она может еще не поддерживаться в некоторых не основных / мобильных / старых браузерах. Вы можете вернуться кquerySelector
(если это поддерживается). Также стоит упомянуть, чтоdocument.activeElement
он вернется,document.body
если ни один элемент не сфокусирован, даже если окно браузера не имеет фокуса.Следующий код поможет обойти эту проблему и
querySelector
предоставит немного лучшую поддержку.Кроме того, следует отметить разницу в производительности между этими двумя методами. Запрос к документу с помощью селекторов всегда будет намного медленнее, чем доступ к
activeElement
свойству. Смотрите этот тест jsperf.com .источник
Сам по себе
document.activeElement
может возвращать элемент, если документ не сфокусирован (и, следовательно, ничто в документе не сфокусировано!)Вы можете хотеть такого поведения, или оно может не иметь значения (например, в рамках
keydown
события), но если вам нужно знать, что что-то действительно сфокусировано, вы можете дополнительно проверитьdocument.hasFocus()
.Следующее даст вам сфокусированный элемент, если он есть, или еще
null
.Чтобы проверить, имеет ли конкретный элемент фокус, проще:
Чтобы проверить, сфокусировано ли что-нибудь , еще раз сложнее:
Примечание о надежности : в коде, в котором выполняется проверка,
document.body
иdocument.documentElement
это происходит потому, что некоторые браузеры возвращают один из них илиnull
когда ничего не сфокусировано.Он не учитывает, имел ли
<body>
(или может быть<html>
)tabIndex
атрибут и, таким образом, мог бы быть сфокусирован . Если вы пишете библиотеку или что-то еще и хотите, чтобы она была надежной, вам, вероятно, следует как-то с этим справиться.Вот ( тяжелые воздушные кавычки) «однострочная» версия получения сфокусированного элемента, концептуально более сложная, потому что вы должны знать о коротком замыкании, и вы знаете, что он явно не помещается в одну строку, если вы хочу, чтобы это было читабельно.
Я не буду рекомендовать это. Но если вы 1337 hax0r, idk ... это там.
Вы также можете удалить
|| null
часть, если вы не против получитьfalse
в некоторых случаях. (Вы все еще можете получить,null
еслиdocument.activeElement
естьnull
):Для проверки того, что конкретный элемент сфокусирован, вы также можете использовать события, но этот способ требует настройки (и, возможно, демонтажа), и, что важно, предполагает исходное состояние :
Вы могли бы исправить предположение о начальном состоянии, используя нечетный способ, но тогда вы могли бы просто использовать его вместо этого.
источник
document.activeElement
может по умолчанию к<body>
элементу, если фокусируемые элементы не находятся в фокусе. Кроме того, если элемент сфокусирован, а окно браузера размыто,activeElement
будет продолжать удерживать сфокусированный элемент.Если какой- либо из этих двух видов поведения не является желательным, рассмотрит подход CSS на основе:
document.querySelector( ':focus' )
.источник
querySelector
: stackoverflow.com/a/40873560/2624876Мне понравился подход, используемый Joel S, но я также люблю простоту
document.activeElement
. Я использовал jQuery и объединил их. Старые браузеры, которые не поддерживают,document.activeElement
будут использоватьjQuery.data()
для хранения значения hasFocus. Новые браузеры будут использоватьdocument.activeElement
. Я предполагаю, чтоdocument.activeElement
будет иметь лучшую производительность.источник
$("*:focus")
?Маленький помощник, который я использовал для этих целей в Mootools:
Таким образом, вы можете проверить, имеет ли элемент фокус при
el.hasFocus()
условии, чтоstartFocusTracking()
он был вызван для данного элемента.источник
JQuery поддерживает
:focus
псевдокласс на текущий момент. Если вы ищете его в документации JQuery, отметьте в разделе «Селекторы», где он указывает на документацию CSS W3C . Я тестировал с Chrome, FF и IE 7+. Обратите внимание, что для того, чтобы он работал в IE,<!DOCTYPE...
должен существовать на странице HTML. Вот пример, предполагающий, что вы присвоили идентификатор элементу, который имеет фокус:источник
this.id
вместо$(this).attr('id')
или, по крайней мере (когда у вас уже есть объект jQuery)$(this)[0].id
. Родной Javascript на этом уровне гораздо быстрее и эффективнее. В этом случае может не быть заметным, но в масштабе всей системы вы заметите разницу.Если вы хотите получить объект, который является экземпляром
Element
, вы должны использоватьdocument.activeElement
, но если вы хотите получить объект, который является экземпляромText
, вы должны использоватьdocument.getSelection().focusNode
.Надеюсь поможет.
источник
document.getSelection().focusNode.parentElement
и нажмите Enter. После этогоdocument.activeElement
прошёл и сделал то же самое. ;)document.activeElement
дает<textarea>
то, чтоdocument.getSelection().focusNode
дает то,<td>
что содержит<textarea>
(иdocument.getSelection().focusNode.parentElement
дает<tr>
содержащее<td>
)Element
, вы должны использоватьdocument.activeElement
, но если вы хотите получить объект, который является экземпляромText
, вы должны использоватьdocument.getSelection().focusNode
. Пожалуйста, проверьте это снова. Я надеюсь, что помог.focusNode
не обязательно будет текстовым узлом.Есть потенциальные проблемы с использованием document.activeElement. Рассматривать:
Если пользователь фокусируется на внутреннем div, то document.activeElement все еще ссылается на внешний div. Вы не можете использовать document.activeElement, чтобы определить, какой из внутренних элементов имеет фокус.
Следующая функция обходит это и возвращает сфокусированный узел:
Если вы предпочитаете получить сфокусированный элемент, используйте:
источник
document.activeElement
: внутренние<div>
элементы на самом деле не могут получить фокус, как вы можете видеть визуально, установив:focus
псевдокласс на что-то видимое (пример: jsfiddle.net/4gasa1t2/1 ). То, о чем вы говорите, это то, что из внутренних элементов<div>
содержит выделение или символ каретки, что является отдельной проблемой.Я обнаружил, что следующий фрагмент полезен при попытке определить, какой элемент в данный момент имеет фокус. Скопируйте следующее в консоль вашего браузера, и каждую секунду он будет распечатывать детали текущего элемента, который имеет фокус.
Не стесняйтесь изменять,
console.log
чтобы выйти из системы, чтобы помочь вам точно определить точный элемент, если распечатка всего элемента не поможет вам точно определить элемент.источник
Читая другие ответы и пробуя себя, кажется
document.activeElement
, вы получите элемент, который вам нужен в большинстве браузеров.Если у вас есть браузер, который не поддерживает document.activeElement, если у вас есть jQuery, вы сможете заполнить его на всех событиях фокуса чем-то очень простым, как это (не проверено, поскольку у меня нет браузера, соответствующего этим критериям) ):
источник
Если вы используете jQuery, вы можете использовать это, чтобы узнать, активен ли элемент:
источник
С dojo вы можете использовать dijit.getFocus ()
источник
Просто поместите это здесь, чтобы дать решение, которое я в конечном итоге придумала.
Я создал свойство под названием document.activeInputArea и использовал дополнение HotKeys для jQuery, чтобы перехватывать события клавиатуры для клавиш со стрелками, табуляции и ввода, и я создал обработчик событий для нажатия на элементы ввода.
Затем я настраивал activeInputArea при каждом изменении фокуса, чтобы я мог использовать это свойство, чтобы узнать, где я был.
Хотя это легко испортить, потому что если у вас есть ошибка в системе, а фокус не там, где вы думаете, то восстановить правильную фокусировку очень сложно.
источник