Показать сообщение отдельно
Старый 17.04.2012, 23:33
s3dworld вне форума Посмотреть профиль Отправить личное сообщение для s3dworld Найти все сообщения от s3dworld
  № 1  
Ответить с цитированием
s3dworld

Регистрация: Apr 2010
Сообщений: 170
По умолчанию Двойное событие

Всем доброго вечера!

У меня есть базовый класс RenderWindow от которого наследуется любое GUI. Собственно поведение RenderWindow устроено так, что он обрабатывает события мыши и посылает события с типом произошедшего события мыши. Собственно вот как это устроено:

Код AS3:
package d.app.render
{
	import d.app.event.AppEvent;
	import d.app.event.appEvent.WindowAppEvent;
	import flash.display.DisplayObject;
	import flash.events.MouseEvent;
 
	public class RenderWindow extends RenderObject
	{
		public static const RW_TYPE_ROOT							:uint		= 0;
		public static const RW_TYPE_MAIN_MENU						:uint		= 1;
		public static const RW_TYPE_MAIN_MENU_BUTTON				:uint		= 2;
		public static const RW_TYPE_CONTEXT_MENU					:uint		= 3;
		public static const RW_TYPE_CONTEXT_MENU_ITEM				:uint		= 4;
		public static const RW_TYPE_TEXT_BUTTON						:uint		= 5;
 
		protected var rwType:uint=RW_TYPE_ROOT;
		protected var rwIsListener:Boolean=false;
		protected var rwIsDown:Boolean=false;
 
		public function RenderWindow(_type:uint,_name:String,_parent:RenderObject,_display:DisplayObject)
		{
			super(RO_TYPE_WINDOW,_name,_parent,_display);
			rwType=_type;
			mouseEnabled=true;
		}
 
		public final function rwGetType():uint
		{
			return rwType;
		}
 
		public function rwBegin():void
		{
		}
 
		public function rwUpdate():void
		{
		}
 
		public function rwResize():void
		{
		}
 
		public function rwEnd():void
		{
		}
 
		public override function roEnable():Boolean
		{
			if(roIsEnable) return false;
 
			roIsEnable=true;
 
			if(!rwIsListener)
			{
				addEventListener(MouseEvent.MOUSE_OUT,rwOnMouseOut);
				addEventListener(MouseEvent.MOUSE_OVER,rwOnMouseOver);
				addEventListener(MouseEvent.MOUSE_MOVE,rwOnMouseMove);
				addEventListener(MouseEvent.MOUSE_DOWN,rwOnMouseDown);
				addEventListener(MouseEvent.MOUSE_UP,rwOnMouseUp);
			}
 
			rwOnEnable();
			return true;
		}
 
		public override function roDisable():Boolean
		{
			if(!roIsEnable) return false;
 
			if(rwIsListener)
			{
				removeEventListener(MouseEvent.MOUSE_OUT,rwOnMouseOut);
				removeEventListener(MouseEvent.MOUSE_OVER,rwOnMouseOver);
				removeEventListener(MouseEvent.MOUSE_MOVE,rwOnMouseMove);
				removeEventListener(MouseEvent.MOUSE_DOWN,rwOnMouseDown);
				removeEventListener(MouseEvent.MOUSE_UP,rwOnMouseUp);
			}
 
			roIsEnable=false;
			rwOnDisable();
			return true;
		}
 
		protected function rwOnEnable():void
		{
		}
 
		protected function rwOnDisable():void
		{
		}
 
		public override function roLock():Boolean
		{
			if(roIsLock) return false;
			roIsLock=true;
 
			if(!rwIsListener)
			{
				addEventListener(MouseEvent.MOUSE_OUT,rwOnMouseOut);
				addEventListener(MouseEvent.MOUSE_OVER,rwOnMouseOver);
				addEventListener(MouseEvent.MOUSE_MOVE,rwOnMouseMove);
				addEventListener(MouseEvent.MOUSE_DOWN,rwOnMouseDown);
				addEventListener(MouseEvent.MOUSE_UP,rwOnMouseUp);
			}
 
			rwOnLock();
			return true;
		}
 
		public override function roUnlock():Boolean
		{
			if(!roIsLock) return false;
 
			if(rwIsListener)
			{
				removeEventListener(MouseEvent.MOUSE_OUT,rwOnMouseOut);
				removeEventListener(MouseEvent.MOUSE_OVER,rwOnMouseOver);
				removeEventListener(MouseEvent.MOUSE_MOVE,rwOnMouseMove);
				removeEventListener(MouseEvent.MOUSE_DOWN,rwOnMouseDown);
				removeEventListener(MouseEvent.MOUSE_UP,rwOnMouseUp);
			}
 
			roIsLock=false;
			rwOnUnlock();
			return true;
		}
 
		protected function rwOnLock():void
		{
		}
 
		protected function rwOnUnlock():void
		{
		}
 
		protected function rwOnMouseOut(_event:MouseEvent):void
		{
			rwIsDown=false;
			dispatchEvent(new WindowAppEvent(AppEvent.WINDOW_OUT,this));
			rwOnAdditionMouseOut(_event);
		}
 
		protected function rwOnMouseOver(_event:MouseEvent):void
		{
			rwIsDown=false;
			dispatchEvent(new WindowAppEvent(AppEvent.WINDOW_OVER,this));
			rwOnAdditionMouseOver(_event);
		}
 
		protected function rwOnMouseMove(_event:MouseEvent):void
		{
			dispatchEvent(new WindowAppEvent(AppEvent.WINDOW_MOVE,this));
			rwOnAdditionMouseMove(_event);
		}
 
		protected function rwOnMouseDown(_event:MouseEvent):void
		{
			rwIsDown=true;
			dispatchEvent(new WindowAppEvent(AppEvent.WINDOW_DOWN,this));
			rwOnAdditionMouseDown(_event);
		}
 
		protected function rwOnMouseUp(_event:MouseEvent):void
		{
			if(rwIsDown) dispatchEvent(new WindowAppEvent(AppEvent.WINDOW_CLICK,this));
			rwIsDown=false;
			rwOnAdditionMouseUp(_event);
		}
 
		protected function rwOnAdditionMouseOut(_event:MouseEvent):void
		{
		}
 
		protected function rwOnAdditionMouseOver(_event:MouseEvent):void
		{
		}
 
		protected function rwOnAdditionMouseMove(_event:MouseEvent):void
		{
		}
 
		protected function rwOnAdditionMouseDown(_event:MouseEvent):void
		{
		}
 
		protected function rwOnAdditionMouseUp(_event:MouseEvent):void
		{
		}
 
	}
 
}
Любой наследуемый класс может не переопределять полный список методов, а только добавочные методы. Ну и сам класс наследуется от класса RenderObject (а он предоставляет просто общую информацию и никакого поведения не несёт).

И вот я от RenderWindow наследую два класса:

1. GUIMainMenu
2. GUIMenuButton

GUIMenuButton я прикрепляю к GUIMainMenu в контейнер его. И вот в чём ошибка: когда я тыкаю мышкой на GUIMenuButton, у меня вызывается два события:

1. Событие GUIMenuButton
2. Событие GUIMainMenu

Почему так? Ведь GUIMenuButton лежит в GUIMainMenu и перекрывает его. Тогда почему два события происходят?