2009-07-24 3 views
2

J'ai un composant personnalisé composé d'un contrôle sélectionnable (bouton radio) et d'une entrée de texte. Je veux effectuer une certaine logique en réponse aux événements de changement de ces deux contrôles, mais après cela, je veux tout ce qui est enregistré sur le gestionnaire de changement du composant composite pour avoir une modification pour gérer les événements aussi bien. Le problème est, lorsque je réexpédier les événements la cible de l'événement a changé pour mon composant personnalisé , perdant la cible de l'événement d'origine.La propagation d'événements Flex 3 sur un composant personnalisé composite?

Voici mon composant personnalisé:

<?xml version="1.0" encoding="utf-8"?> 
<mx:HBox xmlns:mx="http://www.adobe.com/2006/mxml" label="{[email protected]}" data="{[email protected]()}"> 

    <mx:Script> 
     <![CDATA[ 
      import mx.controls.RadioButtonGroup; 
      [Bindable] 
      public var selected: Boolean; 
      [Bindable] 
      public var text: String; 
      [Bindable] 
      public var listItem: XML; 
      [Bindable] 
      public var group: RadioButtonGroup; 

      private function onSelectionChange(event: Event): void { 
       selected = event.target.selected; 
       dispatchEvent(event); 
      } 

      private function onTextChange(event: Event): void { 
       text = event.target.text; 
       dispatchEvent(event); 
      } 
     ]]> 
    </mx:Script> 

    <mx:RadioButton group="{group}" label="{label}" selected="{selected}" change="onSelectionChange(event)"/> 
    <mx:TextInput width="100%" 
        maxChars="{[email protected]}" 
        enabled="{selected}" 
        visible="{listItem.hasOwnProperty('specify')}" 
        includeInLayout="{visible}" 
        change="onTextChange(event)"/> 
</mx:HBox> 

Dans le gestionnaire d'événements qui reçoit changer les événements de cette composante, je vois que event.target est une instance de SpecifyRadioButton, pas le TextInput ou RadioButton, comme je J'attends. Comment devrais-je propager l'événement pour obtenir ce que je veux ici?

Getting event [Event type="change" bubbles=false cancelable=false eventPhase=2] 
from question0.tabSurvey.questionForm.questionContainer.Single94.VBox95.SpecifyRadioButton111 

Répondre

3

Au lieu de réexpédition l'événement d'origine, créez un nouvel événement et passer l'événement d'origine comme une propriété origEvent. Le nouvel événement que les commandes SpecifyRadioButton distribuent peut être une classe d'événements personnalisée qui étend Event, ou vous pouvez être paresseux et utiliser simplement mx.events.DynamicEvent.

Exemple:

import mx.events.DynamicEvent; 

private function onSelectionChange(event: Event): void { 
    selected = event.target.selected; 
    var newEvent:DynamicEvent = new DynamicEvent(Event.CHANGE); 
    newEvent.origEvent = event; 
    dispatchEvent(newEvent); 
} 

Ensuite, dans vos gestionnaires pour l'événement SpecifyRadioButton.change, la référence de la propriété event.origEvent.

2

Il est logique que la cible de l'événement soit SpecifyRadioButton, car c'est ce qui répartit l'événement. L'événement "change" du composant TextInput est configuré pour ne pas augmenter, ce qui signifie qu'il peut être écouté par les écouteurs dans le même composant que lui, mais nulle part ailleurs. Si vous voulez que l'événement de changement augmente, vous allez devoir étendre la classe TextInput (ou utiliser quelque chose de chouette comme Mate).

package { 

    import flash.events.Event; 
    import mx.controls.TextInput; 

    public class CarbonatedTextInput extends TextInput { 
     public function CarbonatedTextInput() { 
      super(); 
      addEventListener(Event.CHANGE, forceBubbles); 
     } 

     /* 
      We have to remove the event listener before we 
      dispatch the new event (with bubbles!) because 
      otherwise our listener in the constructor would 
      catch us and put us in an endless loop... 
      resulting in a **STACK OVERFLOW** 
     */ 
     protected function forceBubbles(e:Event):void { 
      removeEventListener(Event.CHANGE, forceBubbles); 
      dispatchEvent(new Event(Event.CHANGE, true)); 
      addEventListener(Event.CHANGE, forceBubbles); 
     } 
    } 
} 
Questions connexes