Еще один вопрос о пользовательских событиях Flex в компонентах - PullRequest
1 голос
/ 04 февраля 2011

Кажется, я не могу заставить одно из самых основных применений событий работать во Flex 4. Я следовал нескольким учебникам и смотрел везде. Из того, что я могу сказать, я все делаю правильно, поэтому где-то должна быть какая-то глупая ошибка.

У меня есть основной файл приложения, который содержит кнопку. При нажатии на кнопку запускается пользовательское событие, которое я хочу, чтобы мой слушатель в моем дочернем компоненте перехватывал. Событие стреляет. Слушатель события дочернего компонента НЕ перехватывает это событие. Понятия не имею, почему. Настраиваемое событие копируется из учебника Adobe (минус пользовательское пространство имен и комментарии).

Основное применение

<?xml version="1.0" encoding="utf-8"?>
<s:WindowedApplication xmlns:fx="http://ns.adobe.com/mxml/2009" 
                       xmlns:s="library://ns.adobe.com/flex/spark" 
                       xmlns:mx="library://ns.adobe.com/flex/mx"
                       applicationComplete="init()" xmlns:local="*">
    <fx:Metadata>
        [Event(name="enableChanged", type="EnableChangeEvent")]
    </fx:Metadata>

    <fx:Script>
        <![CDATA[
            import EnableChangeEvent;
            import TestComponent;

            private function doDispatchEvent(event:MouseEvent):void {
                if(dispatchEvent(new EnableChangeEvent(EnableChangeEvent.ENABLE_CHANGED, true)))
                {
                    statusLabel.text = "Event was dispatched";
                }
            }

            public function init():void {
                myButton.addEventListener(MouseEvent.CLICK, doDispatchEvent);
            }
        ]]>
    </fx:Script>

    <s:Button x="95" y="83" label="Button" id="myButton" />
    <s:Label x="230" y="83" text="" id="statusLabel" />
    <local:TestComponent x="95" y="150" width="300" height="400" />
</s:WindowedApplication>

Дочерний компонент (тест)

<?xml version="1.0" encoding="utf-8"?>
<s:Group xmlns:fx="http://ns.adobe.com/mxml/2009" 
         xmlns:s="library://ns.adobe.com/flex/spark" 
         xmlns:mx="library://ns.adobe.com/flex/mx"
         width="100%" height="100%"
         initialize="init();">

    <fx:Script>
        <![CDATA[
            import EnableChangeEvent;

            private function doFinalAction(event:EnableChangeEvent):void {
                myLabel.text = "Custom Event Recieved";
            }

            private function init():void {
                addEventListener(EnableChangeEvent.ENABLE_CHANGED, doFinalAction);
            }
        ]]>
    </fx:Script>

    <s:Label width="300" height="50" text="Should change on click" id="myLabel" />
</s:Group>

Пользовательское событие (от Adobe)

package {
    import flash.events.Event;

    public class EnableChangeEvent extends Event
    {
        public function EnableChangeEvent(type:String, isEnabled:Boolean=false) {
            super(type);
            this.isEnabled = isEnabled;
        }

        public static const ENABLE_CHANGED:String = "enableChanged";
        public var isEnabled:Boolean;

        override public function clone():Event {
            return new EnableChangeEvent(type, isEnabled);
        }
    }
}

Ответы [ 3 ]

2 голосов
/ 04 февраля 2011

Тимофей Давыдик, ответь правильно.Поскольку объект Application отправляет событие, если вы хотите, чтобы ваш объект TestComponent его перехватил, вы должны добавить прослушиватель к ссылке на объект Application изнутри вашего TestComponent.Вы можете использовать наследуемое свойство TestComponent объекта "parentApplication", чтобы получить ссылку на Application object`.

Изменить следующий код в TestComponent.mxml:

private function init():void 
{     
    this.parentApplication.addEventListener(EnableChangeEvent.ENABLE_CHANGED, doFinalAction);  

}// end function 

[ОБНОВЛЕНИЕ]

Лично я чувствую, что вы используете неправильные способы использования событий, поэтому я создал аналогичное приложение flex, чтобы продемонстрировать, как использовать события в flex.

Main.mxml

<?xml version="1.0" encoding="utf-8"?>

<s:WindowedApplication xmlns:fx="http://ns.adobe.com/mxml/2009" 
                       xmlns:s="library://ns.adobe.com/flex/spark" 
                       xmlns:mx="library://ns.adobe.com/flex/mx"
                       xmlns:components="components.*"
                       xmlns:events="events.*"
                       applicationComplete="init()">

    <fx:Script>
        <![CDATA[

            import events.EnableChangeEvent;

            public function init():void
            {     
                label1.text = "Application Complete!";

            }// end function

            private function onTestButtonEnableChanged(e:EnableChangeEvent):void
            {                     
                label2.text = "Enabled = " + e.isEnabled;   

            }// end function

        ]]>
    </fx:Script>

    <s:layout>
        <s:VerticalLayout horizontalAlign="center" paddingTop="50" />
    </s:layout>

    <components:TestButton id="testButton" label="CLICK!" enableChanged="onTestButtonEnableChanged(event)"  />
    <s:Label id="label1"/> 
    <s:Label id="label2"/>

</s:WindowedApplication>

TestButton.mxml

<?xml version="1.0" encoding="utf-8"?>

<s:Button xmlns:fx="http://ns.adobe.com/mxml/2009" 
          xmlns:s="library://ns.adobe.com/flex/spark" 
          xmlns:mx="library://ns.adobe.com/flex/mx"
          click="onClick()">

    <fx:Metadata>
        [Event(name="enableChanged", type="events.EnableChangeEvent")]
    </fx:Metadata>

    <fx:Script>

        <![CDATA[

            import events.EnableChangeEvent

            private var isEnabled:Boolean;

            private function onClick():void
            {
                isEnabled = !isEnabled;

                dispatchEvent(new EnableChangeEvent(EnableChangeEvent.ENABLE_CHANGED, isEnabled));

            }// end function

        ]]>

    </fx:Script>

</s:Button>

Основное различие между приложениями состоит в том, что объект Button, в данном случае объект TestButton, отправляет EnableChangeEvent событие при нажатии.При отправке события мы можем проанализировать логическое значение для свойства _isEnabled из TestButton для события.До этого значение инвертируется с помощью строки isEnabled = !isEnabled.Теперь мы можем использовать обработку события, используя объявление mxml объекта TestButton с атрибутом xml enableChanged.

Также вместо того, чтобы следовать учебным пособиям, вы можете попробовать книгу, подобную той, которую я читаю.Она называется «Adobe Flash Builder 4 и Flex 4 Bible» Дэвида Гасснера, которую вы можете получить в виде книги в мягкой обложке или книги для своего разжигания.

1 голос
/ 04 февраля 2011

@ Taurayi правильно, но чтобы получить текущий код, работающий только с одним изменением, отредактируйте init компонента Test следующим образом:

private function init():void 
{ 
     FlexGlobals.topLevelApplication.addEventListener(EnableChangeEvent.ENABLE_CHANGED, doFinalAction);
}
0 голосов
/ 04 февраля 2011

Ваш объект приложения отправляет пользовательское событие.Почему вы ожидаете, что ваша группа "поймает" это событие?Не будетПользовательские события не имеют ни фазы захвата, ни пузырьков.Таким образом, только слушатели, добавленные к вашему объекту приложения, будут слушать это событие.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...