|
|
|||||
Регистрация: Jan 2004
Адрес: На чердаке.
Сообщений: 1,112
|
Перехват и исполнение
Как-то, еще давным-давно в эпоху mx2004, встала задача перехватывать вызов нужных методов каких-либо объектов, без того, чтобы прописывать в них бродкасты.
Набросал такой вот класс: import mx.events.EventDispatcher; import mx.utils.Delegate; // class EventInterceptor { var _targ = new Object(); var _func:Function; var _func_name:String; private var dispatchEvent:Function; public var addEventListener, removeEventListener:Function; var onEvent:Function; // function EventInterceptor() { EventDispatcher.initialize(this); this.addEventListener("onEvent", this); } // public function intercept(obj:Object, func:String):Void { if (_targ && _func) { dismiss(); } _targ = obj; _func_name = func; _func = obj[func]; _targ[func] = Delegate.create(this, executeEvent); } // public function dismiss():Void { _targ[_func_name] = _func; } // private function executeEvent():Void { _func.apply(_targ, arguments); dispatchEvent({type:"onEvent", target:_targ, event:_func_name}); } } Не так давно была тема по динамическому добавлению/удалению действий, к примеру, в onEnterFrame без полного переписывания. Решил поэкспериментировать. К примеру есть на сцене 2 клипа: mc1 и mc2 mc1.move = function() { this._x += 20; }; mc1.onEnterFrame = function() { this.move(); }; EI1 = new EventInterceptor(); EI1.intercept(mc1, "move"); EI1.onEvent = function(evt_obj) { _root.mc2._x += 2; trace("1: "+this+" "+evt_obj.target+" "+evt_obj.event); }; // EI2 = new EventInterceptor(); EI2.intercept(mc1, "move"); EI2.onEvent = function(evt_obj) { _root.mc1._y += 2; trace("2: "+this+" "+evt_obj.target+" "+evt_obj.event); }; // EI3 = new EventInterceptor(); EI3.intercept(mc1, "move"); EI3.onEvent = function(evt_obj) { _root.mc2._y += 2; trace("3: "+this+" "+evt_obj.target+" "+evt_obj.event); }; Экземпляры интерсептора перехватывают вызов метода move, и выполняют свои действия. Все ок. Но. Минусы: 1. Все перехваты осуществляются последовательно, а не независимо. То есть следующий интерсептор перехватывает не mc1.move, как казалось бы, а делегат предыдущего. 2.Вытекает из первой. Если мы удаляем предыдущий перехватчик, то и следующий за ним тоже перестает работать. Вопрос: может кто делал что-то подобное и как-то еще решал такую задачу?
__________________
...Тебе страшно? Мне - нет. |
|
|||||
Et cetera
Регистрация: Sep 2002
Сообщений: 30,784
|
Я долго пытался понять, что ты хочешь сделать и почему нельзя тупо заменить (дать ссылку) move другим методом, а?
|
|
|||||
Регистрация: Jan 2004
Адрес: На чердаке.
Сообщений: 1,112
|
Гм... Наверное привел не очень наглядный пример.
Будем перехватывать не move, а onEnterFrame: EI1.intercept(mc1, "onEnterFrame"); EI2.intercept(mc1, "onEnterFrame"); EI3.intercept(mc1, "onEnterFrame"); Но фактически, повторюсь, каждый последующий экземпляр перехватывает не mc1.onEnterFrame, как мы вроде бы написали, а всего лишь предыдущий по цепочке. Проблемы возникнут, когда мы захотим удалить какое-то действие из onEnterFrame - перестанут работать и все последующие. Вот и любопытно, какие есть соображения по поводу, как эту дрянь переделать так, чтобы перехваты шли независимо, а не последовательно.
__________________
...Тебе страшно? Мне - нет. |
|
|||||
Et cetera
Регистрация: Sep 2002
Сообщений: 30,784
|
А чем не устраивает подписка/отписка методов на события?
Делаешь мувик вещателем, ставишь на onEnterFrame dispatchEvent({type:'onEnterFrame'}), затем добавляешь mc.addEventListener('onEnterFrame',anyMethod1); и т.д. |
|
|||||
Регистрация: Jan 2004
Адрес: На чердаке.
Сообщений: 1,112
|
Вообще в свое время EventInterceptor создавался для других целей, как вспомогательный класс.
Но захотелось попробовать его и в таком аспекте. Тогда и столкнулся с вышеописанной проблемой... Есть соображения, как исхитриться это сделать именно в таком варианте, или же только кардинально другим подходом можно?
__________________
...Тебе страшно? Мне - нет. |
|
|||||
Регистрация: Jan 2004
Адрес: На чердаке.
Сообщений: 1,112
|
Вот. Как раз тогда задача стояла перехватывать вызов любых методов, без инициализации перехватываемых объектов, и вообще любого вмешательства в код извне.
__________________
...Тебе страшно? Мне - нет. |
|
|||||
Регистрация: Jan 2004
Адрес: На чердаке.
Сообщений: 1,112
|
Поясню, почему это нужно было.
Как один из примеров: в контексте той задачи некоторые объекты могли инициализироваться Диспетчером или другим бродкастером уже после того, как требовалось отслеживать вызов их методов. Вторая причина наверное носила скорее принципиальный характер. Перехватывать вызов без вмешательства в код. То есть дописывать бродкасты в каждом методе. А их мог быть не один десяток.
__________________
...Тебе страшно? Мне - нет. |
|
|||||
Et cetera
Регистрация: Sep 2002
Сообщений: 30,784
|
Что мешает переназначить onEnterFrame на другой метод и в нём убирать/добавлять вызываемые методы?
Одновременно выполнить все методы на одном событии невозможно в принципе. |
|
|||||
я бы по-простому сделал :
Object.prototype.addFunc=function(func:String,toAdd:Function){ if(!this._adds){ this._adds=[]; this.naitiveFunc=this[func]; this[func]=function(){ this.naitiveFunc(); for(var i in this._adds)this._adds[i](); } } this._adds.push(toAdd); } mc1.move = function() { this._x += 20; }; mc1.onEnterFrame = function() { this.move(); }; mc1.addFunc("move",function(){ _root.mc2._x += 2; }); mc1.addFunc("move",function(){ _root.mc2._y += 2; }); |
|
|||||
Регистрация: Jan 2004
Адрес: На чердаке.
Сообщений: 1,112
|
to __etc: Да в принципе ничего не мешает
Сделать компромиссное решение с тем, что предложил silin. to silin: про добавление в массив тоже приходила мысля в голову. Правда в этом варианте еще придется отслеживать порядковые номера в массиве, чтобы удалять или перемещать нужные действия. ТОгда как с независимыми экземплярами интерсептора мы уже сразу имеем прямые ссылки на них. Так что действительно, тут придется прибегать к компромиссному решению. Оставаясь в контексте исходной задачи (не меняя исходный код и не делая перехватываемый объект вещателем) вешать на одно событие (или метод) один перехватчик. А уже на onEvent перехватчика - работу по добавлению/удалению действий в массив.
__________________
...Тебе страшно? Мне - нет. |
Часовой пояс GMT +4, время: 02:51. |
|
« Предыдущая тема | Следующая тема » |
Опции темы | |
Опции просмотра | |
|
|