Итак, мои проблемы в том, что я не знаю и нигде не могу найти, как передать аргументы моему eventHandler. Кроме того, я попробовал опубликованный метод Rikudo, но он не работает в IE lt 9.
Ответ 2
Все ваши аргументы, как и вся другая информация о событии, должны храниться внутри самого объекта события. Полностью автономный объект события содержит всю необходимую информацию об этом событии. Значения ваших аргументов обычно устанавливаются при создании нового настраиваемого объекта события (а не при запуске события).
(Все фрагменты примерного кода ниже точно соответствуют всем остальным фрагментам. На самом деле некоторые из примеров могут не иметь большого смысла сами по себе, когда это происходит, относятся к предыдущим фрагментам примера.)
Для ваших собственных аргументов в некоторых случаях вы можете повторно использовать существующие поля (или, возможно, даже добавить новые собственные поля):
var newEvent = ...
newEvent['scrollX'] = your-own-custom-value;
Именно то, как они будут устанавливаться, будет отличаться в зависимости от того, сможете ли вы использовать новый стандартизованный способ HTML5 или должны вернуться к более старой поддержке браузера. (Различные "прокладки", которые добавляют поддержку пользовательских событий даже старым браузерам, которые ничего не предоставляют, здесь не рассматриваются - многие из них предоставят свой собственный довольно уникальный способ установки аргументов.)
В способе HTML5 используется параметр "словарь" (второй) для конструктора объектов, что-то вроде этого:
var newEvent = new CustomEvent('customname', { propertyname : propertyvalue,
anotherpropname : anotherpropvalue,
thirdpropname : thirdpropvalue,
etcpropname : etcpropvalue } );
Соответствующий старый метод будет выглядеть примерно так:
var newEvent = document.createEvent();
newEvent.initEvent('customname', true, true);
newEvent['propertyname'] = propertyvalue;
newEvent['anotherpropname'] = anotherpropvalue;
newEvent['thirdpropname'] = thirdpropvalue;
newEvent['etcpropname'] = etcprovalue;
(В приведенном выше примере также может быть понятнее, что фактически делает конструктор CustomEvent HTML5.)
Использование существующих имен свойств, подобных этому (или создания ваших собственных свойств:-), обычно не рекомендуется, поскольку проблемы с кросс-браузером и проблемы отладки могут быть довольно серьезными. Время от времени это будет необходимо, и оно будет работать, но не полагаться на него как на общую технику. Хотя некоторые типы объектов событий включают определенное именованное свойство, подобные типы объектов событий могут и не быть. Некоторые свойства события могут быть "только для чтения". Объекты событий очень сильно изменяются из одного браузера в другой и даже между версиями браузера. И создание ваших собственных новых свойств может смутить реализацию браузера Javascript.
Вместо этого используйте одно конкретное свойство, которое "зарезервировано" для вашего использования в пользовательских событиях, и ничего больше: detail.
Часто у вас будет несколько аргументов, но для вашего использования есть только одно свойство. Таким образом, обычный подход заключается в том, чтобы всегда приводить все ваши аргументы в один "объект" , что-то вроде этого:
var myargs = { my : 1,
own : getElementById('foo');
args : { X : 32, Y : 53 } };
Способ настройки этой переменной HTML5 будет выглядеть примерно так:
var newEvent = new CustomEvent('customname', { bubbles : true,
cancelable : true,
detail : myargs } );
Более старый интерфейс для выполнения той же самой вещи будет выглядеть примерно так:
var newEvent = document.createEvent();
newEvent.initEvent('customname', true, true);
newEvent['detail'] = myargs;
(Конечно, если вы сильно используете Javasript "литеральный объект" для фигурного скобки, чтобы свести к минимуму вашу типизацию, ваш код может выглядеть немного иначе, чем приведенные выше примеры, которые определяют приоритетность.)
(Два существующих свойства событий, "пузырьки" и "отменяемые" всегда должны быть установлены для каждого события независимо от установки возможных пользовательских аргументов. Если используется новый способ HTML5, они всегда будут отображаться как две дополнительные строки в объект, который является вторым параметром для конструктора CustomEvent. Если используется более старый способ, они будут вторым и третьим параметрами для вызова initEvent (...).
Также предлагаются два разных способа запуска пользовательского события. В новом способе HTML5 используется object.dispatchEvent(newEvent). В более старом способе используется object.fireEvent('customname', newEvent, false). Здесь "объект" означает DOMObject/Element; точно, что (если что-либо) происходит, если "объект" - это нечто, кроме элемента DOM, даже больше зависит от браузера, чем остальная часть этой темы. (Смешивание HTML5-способа и старого способа обычно работает, но может быть запутанным. Еще одним частым источником путаницы является системная функция с именем fireEvent (...), а также определение вашей собственной функции с тем же именем.)
(Существует несколько тайных различий между двумя способами запуска настраиваемого события. Более старый метод fireEvent (...) требует повторного указания имени события, даже если вы уже указали его в initEvent (...), а более старый метод fireEvent (...) не вызывает "действие по умолчанию" [что бы это ни значило].)
С другой стороны, пользовательские аргументы получают доступ одинаково, независимо от того, использовался ли HTML5 или старый метод настройки события. Он будет выглядеть примерно так:
function customhandler(evt) {
alert(evt.detail.own);
Если некоторые из ваших пользовательских значений на самом деле представляют собой объекты, точечная нотация может затянуться так долго, что может выглядеть как опечатка... но это не так. Например:
function customhandler(evt) {
alert(evt.detail.args.X);
Похоже, что некоторые из них могут работать несколько иначе в IE 9 и ниже. Надеемся, что проблемы просто обычные, пытаясь повторно использовать или даже создать свойства объекта события. Если проблемы более распространены, вы можете отправить сообщение "извините:-(" на своем веб-сайте, или вы можете дождаться, когда IE6/7/8/9 умрет, или вы можете попробовать перекрестный браузер, взломать его самостоятельно, или вы может использовать какую-то прокладку/резервную копию. Мне не понятно, лучше ли найти прокладку, которая "выглядит точно так же", как обычный интерфейс, или использовать альтернативный интерфейс, предоставляемый прокладкой для всего (даже если обычный интерфейс доступно).
(Отказ от ответственности: Конечно, я мог ошибаться в отношении некоторых из вышеперечисленных...: -)