| <?xml version="1.0" encoding="UTF-8"?> |
| <!-- |
| Licensed to the Apache Software Foundation (ASF) under one or more |
| contributor license agreements. See the NOTICE file distributed with |
| this work for additional information regarding copyright ownership. |
| The ASF licenses this file to You under the Apache License, Version 2.0 |
| (the "License"); you may not use this file except in compliance with |
| the License. You may obtain a copy of the License at |
| |
| http://www.apache.org/licenses/LICENSE-2.0 |
| |
| Unless required by applicable law or agreed to in writing, software |
| distributed under the License is distributed on an "AS IS" BASIS, |
| WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| See the License for the specific language governing permissions and |
| limitations under the License. |
| --> |
| <!DOCTYPE html |
| PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> |
| <html lang="en-us" xml:lang="en-us"> |
| <head> |
| <meta name="DC.Type" content="topic"/> |
| <meta name="DC.Title" content="Events"/> |
| <meta name="DC.Format" content="XHTML"/> |
| <meta name="DC.Identifier" content="WS2db454920e96a9e51e63e3d11c0bf69084-7ee9_verapache"/> |
| <title>Events</title> |
| </head> |
| <body id="WS2db454920e96a9e51e63e3d11c0bf69084-7ee9_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7ee9_verapache"><!-- --></a> |
| |
| <div> |
| <p>One of the most important parts of your Flex application |
| is handling events by using controls and ActionScript.</p> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fff_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fff_verapache"><!-- --></a> |
| <h2 class="topictitle2">About Flex events</h2> |
| |
| |
| <div> |
| <p>Events |
| let a developer know when something happens within an application. They |
| can be generated by user devices, such as the mouse and keyboard, |
| or other external input, such as the return of a web service call. |
| Events are also triggered when changes happen in the appearance |
| or life cycle of a component, such as the creation or destruction |
| of a component or when the component is resized.</p> |
| |
| <p>Any user interaction with your application can generate events. |
| Events can also occur without any direct user interaction, such |
| as when data finishes loading from a server or when an attached |
| camera becomes active. You can "handle" these events in your code |
| by adding an event handler. <em>Event handlers</em> are the functions |
| or methods that you write to respond to specific events. They are |
| also sometimes referred to as <em>event listeners</em>. </p> |
| |
| <p>The Flex event model is based on the Document Object Model (DOM) |
| Level 3 events model. Although Flex does not adhere specifically |
| to the DOM standard, the implementations are very similar. The event |
| model in Flex comprises the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html" target="_blank">Event</a> object |
| and its subclasses, and the event dispatching model. For a quick start |
| in using events in Flex, see the sample code in <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cdf_verapache">Using |
| events</a>.</p> |
| |
| <p>Components generate and dispatch events and <em>consume</em> (listen |
| to) other events. An object that requires information about another |
| object's events registers a listener with that object. When an event |
| occurs, the object dispatches the event to all registered listeners |
| by calling a function that was requested during registration. To |
| receive multiple events from the same object, you must register |
| your listener for each event.</p> |
| |
| <p>Components have built-in events that you can handle in ActionScript |
| blocks in your MXML applications. You can also take advantage of |
| the Flex event system's dispatcher-listener model to define your |
| own event listeners outside of your applications, and define which |
| methods of your custom listeners will listen to certain events. |
| You can register listeners with the target object so that when the target |
| object dispatches an event, the listeners get called.</p> |
| |
| <p>All visual objects, including Flex controls and containers, are |
| subclasses of the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/display/DisplayObject.html" target="_blank">DisplayObject</a> class. |
| They are in a tree of visible objects that make up your application. |
| The root of the tree is the Stage. Below that is the SystemManager |
| object, and then the Application object. Child containers and components |
| are leaf nodes of the tree. That tree is known as the <em>display list</em>. |
| An object on the display list is analogous to a node in the DOM |
| hierarchical structure. The terms <em>display list object</em> and <em>node</em> are |
| used interchangeably. </p> |
| |
| <p>For information about each component's events, see the component's description |
| in <a href="flx_controls_ctr.html#WS2db454920e96a9e51e63e3d11c0bf69084-7ff8_verapache">UI |
| Controls</a> or the control's entry in <em> |
| <a href="https://flex.apache.org/asdoc/" target="_blank">ActionScript 3.0 Reference for Apache Flex</a></em>. </p> |
| |
| <p>For a detailed description of a component's startup life cycle, |
| including major events in that life cycle, see <a href="flx_ascomponents_advanced_asa.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cdd_verapache">Create |
| advanced MX visual components in ActionScript</a>.</p> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache"><!-- --></a> |
| <h3 class="topictitle3">About the event flow</h3> |
| |
| |
| <div> |
| <p>You can instruct any container or control to listen for |
| events dispatched by another container or control. When Adobe<sup>®</sup> Flash<sup>®</sup> Player |
| dispatches an Event object, that Event object makes a roundtrip |
| journey from the root of the display list to the target node, checking |
| each node for registered listeners. The <em>target node</em> is the |
| node in the display list where the event occurred. For example, |
| if a user clicks a Button control named Child1, Flash Player dispatches |
| an Event object with Child1 defined as the target node.</p> |
| |
| <p>The event flow |
| is conceptually divided into three parts: the capturing phase, the targeting |
| phase, and the bubbling phase, as briefly described next. For more information |
| about the event flow, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cdb_verapache">Event |
| propagation</a>.</p> |
| |
| <div class="section" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fdd_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fdd_verapache"><!-- --></a><h4 class="sectiontitle">About |
| the capturing phase</h4> |
| |
| <p>The |
| first part of the event flow is called the <em>capturing phase</em>. |
| This phase comprises all of the nodes from the root node to the |
| parent of the target node. During this phase, Flash Player examines |
| each node, starting with the root, to see if it has a listener registered |
| to handle the event. If it does, Flash Player sets the appropriate values |
| of the Event object and then calls that listener. Flash Player stops |
| after it reaches the target node's parent and calls any listeners |
| registered on the parent. For more information, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cde_verapache">Capturing |
| phase</a>.</p> |
| |
| </div> |
| |
| <div class="section" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7ff1_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7ff1_verapache"><!-- --></a><h4 class="sectiontitle">About |
| the targeting phase</h4> |
| |
| <p>The |
| second part of the event flow, the <em>targeting phase</em>, consists |
| solely of the target node. Flash Player sets the appropriate values |
| on the Event object, checks the target node for registered event |
| listeners, and then calls those listeners. For more information, |
| see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7ccf_verapache">Targeting |
| phase</a>.</p> |
| |
| </div> |
| |
| <div class="section" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fee_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe1_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fee_verapache"><!-- --></a><h4 class="sectiontitle">About |
| the bubbling phase</h4> |
| |
| <p>The |
| third part of the event flow, the <em>bubbling phase</em>, comprises |
| all of the nodes from the target node's parent to the root node. |
| Starting with the target node's parent, Flash Player sets the appropriate |
| values on the Event object and then calls event listeners on each |
| of these nodes. Flash Player stops after calling any listeners on |
| the root node. For more information about the bubbling phase, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cce_verapache">Bubbling |
| phase</a>.</p> |
| |
| </div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ffe_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ffe_verapache"><!-- --></a> |
| <h3 class="topictitle3">About the Event class</h3> |
| |
| |
| <div> |
| <p>The <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html" target="_blank">Event</a> |
| class |
| is an ActionScript class with properties that contain information about |
| the event that occurred. An Event object is an implicitly created |
| object, similar to the request and response objects in a JavaServer |
| Page (JSP) that are implicitly created by the application server.</p> |
| |
| <p>Flex creates an Event object each time an event is dispatched. |
| You can use the Event object inside an event listener to access |
| details about the event that was dispatched, or about the component |
| that dispatched the event. Passing an Event object to, and using |
| it in, an event listener is optional. However, if you want to access |
| the Event object's properties inside your event listeners, you must |
| pass the Event object to the listener. </p> |
| |
| <p>Flex creates only one Event object when an event is dispatched. |
| During the bubbling and capturing phases, Flex changes the values |
| on the Event object as it moves up or down the display list, rather |
| than creating a new Event object for each node.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe4_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe4_verapache"><!-- --></a> |
| <h3 class="topictitle3">About event subclasses</h3> |
| |
| |
| <div> |
| <p>There are many classes that extend the flash.events.Event |
| class. These classes are defined mostly in the following packages:</p> |
| |
| <ul> |
| <li> |
| <p>spark.events.*</p> |
| |
| </li> |
| |
| <li> |
| <p>mx.events.*</p> |
| |
| </li> |
| |
| <li> |
| <p>flash.events.*</p> |
| |
| </li> |
| |
| </ul> |
| |
| <p>The mx.events package defines event classes that are specific |
| to most Flex controls, including the DataGridEvent, DragEvent, and |
| ColorPickerEvent. The spark.events package defines event classes |
| that are specific to a few Spark controls, including the TextOperationEvent |
| and VideoEvent. The flash.events package describes events that are |
| not unique to Flex but are instead defined by Flash Player. These |
| event classes include <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/MouseEvent.html" target="_blank">MouseEvent</a>, <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/DataEvent.html" target="_blank">DataEvent</a>, |
| and <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/TextEvent.html" target="_blank">TextEvent</a>. All |
| of these events are commonly used in applications.</p> |
| |
| <p>In addition to these packages, some packages also define their |
| own event objects: for example, mx.messaging.events.ChannelEvent |
| and mx.logging.LogEvent.</p> |
| |
| <p>Child classes of the Event class have additional properties and |
| methods that may be unique to them. In some cases, you will want |
| to use a more specific event type rather than the generic Event |
| object so that you can access these unique properties or methods. |
| For example, the LogEvent class has a <samp class="codeph">getLevelString()</samp> method |
| that the Event class does not.</p> |
| |
| <p>For information on using Event subclasses, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7ce0_verapache">Using |
| event subclasses</a>.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe5_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe5_verapache"><!-- --></a> |
| <h3 class="topictitle3">About the EventDispatcher class</h3> |
| |
| |
| <div> |
| <p>Every object in the display list can trace its class inheritance |
| back to the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/display/DisplayObject.html" target="_blank">DisplayObject</a> class. |
| The DisplayObject class, in turn, inherits from the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/EventDispatcher.html" target="_blank">EventDispatcher</a> class. |
| The EventDispatcher class is a base class that provides important |
| event model functionality for every object on the display list. |
| Because the DisplayObject class inherits from the EventDispatcher |
| class, any object on the display list has access to the methods |
| of the EventDispatcher class.</p> |
| |
| <p>This is significant because every item on the display list can |
| participate fully in the event model. Every object on the display |
| list can use its <samp class="codeph">addEventListener()</samp> method—inherited |
| from the EventDispatcher class—to listen for a particular event, |
| but only if the listening object is part of the event flow for that |
| event.</p> |
| |
| <p>Although the name EventDispatcher seems to imply that this class's |
| main purpose is to send (or dispatch) Event objects, the methods |
| of this class are used much more frequently to register event listeners, |
| check for event listeners, and remove event listeners.</p> |
| |
| <p>The EventDispatcher class implements the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/IEventDispatcher.html" target="_blank">IEventDispatcher</a> interface. |
| This allows developers who create custom classes that cannot inherit |
| from EventDispatcher or one of its subclasses to implement the IEventDispatcher |
| interface to gain access to its methods. </p> |
| |
| <p>The <samp class="codeph">addEventListener()</samp> method is the most commonly |
| used method of this class. You use it to register your event listeners. |
| For information on using the <samp class="codeph">addEventListener()</samp> method, |
| see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache">Using |
| the addEventListener() method</a>.</p> |
| |
| <p>Advanced programmers use the <samp class="codeph">dispatchEvent()</samp> method |
| to manually dispatch an event or to send a custom Event object into |
| the event flow. For more information, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7ce1_verapache">Manually |
| dispatching events</a>.</p> |
| |
| <p>Several other methods of the EventDispatcher class provide useful |
| information about the existence of event listeners. The <samp class="codeph">hasEventListener()</samp> method returns <samp class="codeph">true</samp> if |
| an event listener is found for that specific event type on a particular |
| display list object. The <samp class="codeph">willTrigger()</samp> method checks |
| for event listeners on a particular display list object, but it |
| also checks for listeners on all of that display list object's ancestors |
| for all phases of the event flow. The method returns <samp class="codeph">true</samp> if |
| it finds one.</p> |
| |
| </div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cdf_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cdf_verapache"><!-- --></a> |
| <h2 class="topictitle2">Using events</h2> |
| |
| |
| <div> |
| <p>Using events in Flex is a two-step process. First, you |
| write a function or class method, known as an <em>event listener</em> or <em>event handler</em>, that |
| responds to events. The function often accesses the properties of |
| the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html" target="_blank">Event</a> object |
| or some other settings of the application state. The signature of |
| this function usually includes an argument that specifies the event |
| type being passed in.</p> |
| |
| <p>The |
| following example shows a simple event listener function that reports |
| when a control triggers the event that it is listening for:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/SimpleEventHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp();"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function initApp():void { |
| b1.addEventListener(MouseEvent.CLICK, myEventHandler); |
| } |
| |
| private function myEventHandler(event:Event):void { |
| Alert.show("An event occurred."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| </s:Application></pre> |
| |
| <p>As you can see in this example, you also register that function |
| or class method with a display list object by using the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/EventDispatcher.html#addEventListener()" target="_blank">addEventListener()</a> method.</p> |
| |
| <p>Most Flex controls simplify listener registration by letting |
| you specify the listener inside the MXML tag. For example, instead |
| of using the <samp class="codeph">addEventListener()</samp> method to specify |
| a listener function for the Button control's <samp class="codeph">click</samp> event, |
| you specify it in the <samp class="codeph">click</samp> attribute of the <samp class="codeph"><mx:Button></samp> tag:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/SimplerEventHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myEventHandler(event:Event):void { |
| Alert.show("An event occurred."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="myEventHandler(event)"/> |
| |
| </s:Application></pre> |
| |
| <p>This is equivalent to the <samp class="codeph">addEventListener()</samp> method |
| in the previous code example. However, it is best practice to use |
| the <samp class="codeph">addEventListener()</samp> method. This method gives |
| you greater control over the event by letting you configure the |
| priority and capturing settings, and use event constants. In addition, |
| if you use <samp class="codeph">addEventListener()</samp> to add an event handler, |
| you can use <samp class="codeph">removeEventListener()</samp> to remove the |
| handler when you no longer need it. If you add an event handler |
| inline, you cannot call <samp class="codeph">removeEventListener()</samp> on |
| that handler.</p> |
| |
| <p>Each time a control generates an event, Flex creates an Event |
| object that contains information about that event, including the |
| type of event and a reference to the dispatching control. To use |
| the Event object, you specify it as a parameter in the event handler |
| function, as the following example shows:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/EventTypeHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myEventHandler(e:Event):void { |
| Alert.show("An event of type '" + e.type + "' occurred."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="myEventHandler(event)"/> |
| |
| </s:Application></pre> |
| |
| <p>If you want to access the Event object in an event handler that |
| was triggered by an inline event, you must add the <samp class="codeph">event</samp> keyword |
| inside the MXML tag so that Flex explicitly passes it to the handler, |
| as in the following:</p> |
| |
| <pre class="codeblock"> <mx:Button id="b1" label="Click Me" click="myEventHandler(event)"/></pre> |
| |
| <p>You are not required to use the Event object in a handler function. |
| The following example creates two event handler functions and registers |
| them with the events of a ComboBox control. The first event handler, <samp class="codeph">openEvt()</samp>, |
| takes no arguments. The second event handler, <samp class="codeph">changeEvt()</samp>, |
| takes the Event object as an argument and uses this object to access |
| the <samp class="codeph">value</samp> and <samp class="codeph">selectedIndex</samp> of the |
| ComboBox control that triggered the event.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/MultipleEventHandlers.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| private function openEvt():void { |
| forChange.text=""; |
| } |
| |
| private function changeEvt(e:Event):void { |
| forChange.text = |
| "Value: " + e.currentTarget.selectedItem + "\n" + |
| "Index: " + e.currentTarget.selectedIndex; |
| } |
| ]]></fx:Script> |
| |
| <s:ComboBox open="openEvt()" change="changeEvt(event)"> |
| <s:dataProvider> |
| <s:ArrayList> |
| <fx:String>AK</fx:String> |
| <fx:String>AL</fx:String> |
| <fx:String>AR</fx:String> |
| </s:ArrayList> |
| </s:dataProvider> |
| </s:ComboBox> |
| |
| <s:TextArea id="forChange" width="150" height="100"/> |
| |
| </s:Application></pre> |
| |
| <p>This example shows accessing the <samp class="codeph">target</samp> property |
| of the Event object. For more information, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cd1_verapache">Accessing |
| the currentTarget property</a>.</p> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff0_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff0_verapache"><!-- --></a> |
| <h3 class="topictitle3">Specifying the Event object</h3> |
| |
| |
| <div> |
| <p>You specify the object in a listener function's signature |
| as type Event, as the following example shows:</p> |
| |
| <pre class="codeblock"> function myEventListener(e:Event):void { ... }</pre> |
| |
| <p>However, if you want to access properties that are specific to |
| the type of event that was dispatched, you must instead specify |
| a more specific event type, such as ToolTipEvent or KeyboardEvent, |
| as the following example shows:</p> |
| |
| <pre class="codeblock"> import mx.events.ToolTip |
| function myEventListener(e:ToolTipEvent):void { ... }</pre> |
| |
| <p>In some cases, you must import the event's class in your ActionScript |
| block.</p> |
| |
| <p>Most objects have specific events that are associated with them, |
| and most of them can dispatch more than one type of event. </p> |
| |
| <p>If you declare an event of type Event, you can cast it to a more |
| specific type to access its event-specific properties. For more |
| information, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7ce0_verapache">Using |
| event subclasses</a>.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd1_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd1_verapache"><!-- --></a> |
| <h3 class="topictitle3">Accessing the currentTarget property</h3> |
| |
| |
| <div> |
| <p>Event objects include a reference to the |
| instance of the dispatching component (or <em>target</em>), which |
| means that you can access all the properties and methods of that |
| instance in an event listener. The following example accesses the <samp class="codeph">id</samp> of |
| the Button control that triggered the event:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/AccessingCurrentTarget.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myEventHandler(e:Event):void { |
| Alert.show("The button '" + e.currentTarget.id + "' was clicked."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="myEventHandler(event)"/> |
| |
| </s:Application></pre> |
| |
| <p>You can access members of the <samp class="codeph">currentTarget</samp>. |
| If you do not cast the current target to a specific type, the compiler |
| assumes that it is of type Object. Objects can have any property |
| or method because the Object type is dynamic in ActionScript. Therefore, |
| when accessing methods and properties of the <samp class="codeph">currentTarget</samp>, |
| it is best practice to cast <samp class="codeph">currentTarget</samp> to whatever |
| class you anticipate will dispatch that event. This gives you strong |
| type checking at compile time, and helps avoid the risk of throwing |
| a run-time error.</p> |
| |
| <p>The following example casts the current target to a TextInput |
| class before calling the <samp class="codeph">selectRange()</samp> method, |
| but does not cast it before trying to set the <samp class="codeph">tmesis</samp> property. |
| The <samp class="codeph">tmesis</samp> property does not exist on the TextInput |
| class. This illustrates that you will get a run-time error but not |
| a compile-time error when you try to access members that don't exist, |
| unless you cast <samp class="codeph">currentTarget</samp> to a specific type |
| so that type checking can occur:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/InvokingOnCurrentTarget.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| width="500"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.core.UIComponent; |
| |
| private function tiHandler(e:Event):void { |
| /* |
| The following enforces type checking: |
| */ |
| TextInput(e.currentTarget).selectRange(0,3); |
| |
| /* |
| The following throws a run-time error but not a compile-time error: |
| e.currentTarget.tmesis = 4; |
| */ |
| |
| /* |
| ... unless you cast it to the expected type like the following. Then |
| the compiler throws an error. |
| TextInput(e.currentTarget).tmesis = 4; |
| */ |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:TextInput id="ti1" click="tiHandler(event)" |
| text="When you click on this control, the first three characters are selected." |
| width="400"/> |
| |
| </s:Application></pre> |
| |
| <p>You could also cast <samp class="codeph">currentTarget</samp> to UIComponent |
| or some other more general class that still has methods of display |
| objects. That way, if you don't know exactly which control will |
| dispatch an event, at least you can ensure there is some type checking.</p> |
| |
| <p>You can also access methods and properties of the <samp class="codeph">target</samp> property, |
| which contains a reference to the current node in the display list. |
| For more information, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cd3_verapache">About |
| the target and currentTarget properties</a>.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ffb_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ffb_verapache"><!-- --></a> |
| <h3 class="topictitle3">Registering event handlers</h3> |
| |
| |
| <div> |
| <p>There |
| are several strategies that you can employ when you register event handlers |
| with your Flex controls:</p> |
| |
| <ol> |
| <li> |
| <p>Define an event handler inline. This binds a call to |
| the handler function to the control that triggers the event.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/SimplerEventHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myEventHandler(event:Event):void { |
| Alert.show("An event occurred."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="myEventHandler(event)"/> |
| |
| </s:Application></pre> |
| |
| <p>In this example, whenever the |
| user clicks the Button control, Flex calls the <samp class="codeph">myClickHandler()</samp> function.</p> |
| |
| <p>For |
| more information on defining event handlers inline, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cd5_verapache">Defining |
| event listeners inline</a>.</p> |
| |
| </li> |
| |
| <li> |
| <p>Use the <samp class="codeph">addEventListener()</samp> method, as follows:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/SimpleEventHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp();"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function initApp():void { |
| b1.addEventListener(MouseEvent.CLICK, myEventHandler); |
| } |
| |
| private function myEventHandler(event:Event):void { |
| Alert.show("An event occurred."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| </s:Application></pre> |
| |
| <p>As with the previous example, |
| whenever the user clicks the Button control, Flex calls the <samp class="codeph">myClickHandler()</samp> handler |
| function. However, registering your event handlers using this method |
| provides more flexibility. You can register multiple components |
| with this event handler, add multiple handlers to a single component, |
| or remove the handler. For more information, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache">Using |
| the addEventListener() method</a>.</p> |
| |
| </li> |
| |
| <li> |
| <p>Create an event handler class and register components to |
| use the class for event handling. This approach to event handling |
| promotes code reuse and lets you centralize event handling outside |
| your MXML files. For more information on creating custom event handler |
| classes, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cd2_verapache">Creating |
| event handler classes</a>.</p> |
| |
| </li> |
| |
| </ol> |
| |
| </div> |
| |
| <div class="nested3" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd5_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd5_verapache"><!-- --></a> |
| <h4 class="topictitle4">Defining event listeners inline</h4> |
| |
| |
| <div> |
| <p>The |
| simplest method of defining event handlers in applications is to |
| point to a handler function in the component's MXML tag. To do this, |
| you add any of the component's events as a tag attribute followed |
| by an ActionScript statement or function call.</p> |
| |
| <p>You add an event handler inline using the following syntax:</p> |
| |
| <pre class="codeblock"> <s:<em>tag_name</em> <em>event_name</em>="<em>handler_function</em>"/></pre> |
| |
| <p>For example, to listen for a Button control's <samp class="codeph">click</samp> event, |
| you add a statement in the <samp class="codeph"><mx:Button></samp> tag's <samp class="codeph">click</samp> attribute. |
| If you add a function, you define that function in an ActionScript |
| block. The following example defines the <samp class="codeph">submitForm()</samp> function |
| as the handler for the Button control's <samp class="codeph">click</samp> event:</p> |
| |
| <pre class="codeblock"> <fx:Script><![CDATA[ |
| function submitForm():void { |
| // Do something. |
| } |
| ]]></fx:Script> |
| <s:Button label="Submit" click="submitForm();"/></pre> |
| |
| <p>Event handlers can include any valid ActionScript code, including |
| code that calls global functions or sets a component property to |
| the return value. The following example calls the <samp class="codeph">trace()</samp> global |
| function:</p> |
| |
| <pre class="codeblock"> <s:Button label="Get Ver" click="trace('The button was clicked');"/></pre> |
| |
| <p>There is one special parameter that you can pass in an inline |
| event handler definition: the <samp class="codeph">event</samp> parameter. |
| If you add the <samp class="codeph">event</samp> keyword as a parameter, Flex |
| passes the Event object and inside the handler function, you can |
| then access all the properties of the Event object. </p> |
| |
| <p>The following example passes the Event object to the <samp class="codeph">submitForm()</samp> handler function |
| and specifies it as type MouseEvent:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/MouseEventHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myEventHandler(event:MouseEvent):void { |
| // Do something with the MouseEvent object. |
| Alert.show("An event of type '" + event.type + "' occurred."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="myEventHandler(event)"/> |
| |
| </s:Application></pre> |
| |
| <p>It is best practice to include the <samp class="codeph">event</samp> keyword |
| when you define all inline event listeners and to specify the most |
| stringent Event object type in the resulting listener function (for |
| example, specify MouseEvent instead of Event).</p> |
| |
| <p>You can use the Event object to access a reference to the target |
| object (the object that dispatched the event), the type of event |
| (for example, <samp class="codeph">click</samp>), or other relevant properties, |
| such as the row number and value in a list-based control. You can |
| also use the Event object to access methods and properties of the |
| target component, or the component that dispatched the event.</p> |
| |
| <p>Although you will most often pass the entire Event object to |
| an event listener, you can just pass individual properties, as the |
| following example shows:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/PropertyHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myEventHandler(s:String):void { |
| Alert.show("Current Target: " + s); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="myEventHandler(event.currentTarget.id)"/> |
| |
| </s:Application></pre> |
| |
| <p>Registering an event listener inline provides less flexibility |
| than using the <samp class="codeph">addEventListener()</samp> method to register |
| event listeners. The drawbacks are that you cannot set the <samp class="codeph">useCapture</samp> or <samp class="codeph">priority</samp> properties |
| on the Event object and that you cannot remove the listener once |
| you add it.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested3" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache"><!-- --></a> |
| <h4 class="topictitle4">Using the addEventListener() method</h4> |
| |
| |
| <div> |
| <p>The <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/EventDispatcher.html#addEventListener()" target="_blank">addEventListener()</a> method |
| lets you register event listener functions with the specified control |
| or object. The following example adds the <samp class="codeph">myClickListener()</samp> function |
| to the b1 instance of a Button control. When the user clicks b1, |
| Flex calls the <samp class="codeph">myClickListener()</samp> method:</p> |
| |
| <pre class="codeblock"> b1.addEventListener(MouseEvent.CLICK, myClickListener);</pre> |
| |
| <p>The <samp class="codeph">addEventListener()</samp> method has the following |
| signature:</p> |
| |
| <pre class="codeblock"> <em>componentInstance</em>.addEventListener( |
| <em>event_type</em>:String, |
| <em>event_listener</em>:Function, |
| <em>use_capture</em>:Boolean, |
| <em>priority</em>:int, |
| <em>weakRef</em>:Boolean |
| )</pre> |
| |
| <p>The <samp class="codeph"> |
| <em>event_type</em> |
| </samp> argument is the kind of |
| event that this component dispatches. This can be either the event |
| type String (for example, "click" or "mouseOut") or the event type |
| static constant (such as <samp class="codeph">MouseEvent.CLICK</samp> or <samp class="codeph">MouseEvent.MOUSE_OUT</samp>). |
| This argument is required.</p> |
| |
| <p>The constants provide an easy way to refer to specific event |
| types. You should use these constants instead of the strings that |
| they represent. If you misspell a constant name in your code, the |
| compiler catches the mistake. If you instead use strings and make |
| a typographical error, it can be harder to debug and could lead to |
| unexpected behavior.</p> |
| |
| <p>You should use the constants wherever possible. For example, |
| when you are testing to see whether an Event object is of a certain |
| type, use the following code:</p> |
| |
| <pre class="codeblock"> if (myEventObject.type == MouseEvent.CLICK) {/* your code here */}</pre> |
| |
| <p>Do not use the following code:</p> |
| |
| <pre class="codeblock"> if (myEventObject.type == "click") {/* your code here */}</pre> |
| |
| <p>The <em>event_listener</em> argument is the function that handles |
| the event. This argument is required.</p> |
| |
| <p>The <samp class="codeph"> |
| <em>use_capture</em> |
| </samp> parameter of the <samp class="codeph">addEventListener()</samp> method |
| lets you control the phase in the event flow in which your listener |
| will be active. It sets the value of the <samp class="codeph">useCapture</samp> property |
| of the Event object. If <samp class="codeph">useCapture</samp> is set to <samp class="codeph">true</samp>, |
| your listener is active during the capturing phase of the event |
| flow. If <samp class="codeph">useCapture</samp> is set to <samp class="codeph">false</samp>, |
| your listener is active during the targeting and bubbling phases |
| of the event flow, but not during the capturing phase. The default |
| value is determined by the type of event, but is <samp class="codeph">false</samp> in |
| most cases. </p> |
| |
| <p>To listen for an event during all phases of the event flow, you |
| must call <samp class="codeph">addEventListener()</samp> twice, once with the <samp class="codeph">useCapture</samp> parameter |
| set to <samp class="codeph">true</samp>, and again with <samp class="codeph"> |
| <em>use_capture</em> |
| </samp> set |
| to <samp class="codeph">false</samp>. This argument is optional. For more information, |
| see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cde_verapache">Capturing |
| phase</a>.</p> |
| |
| <p>The <em>priority</em> parameter sets the priority for that event |
| listener. The higher the number, the sooner that event handler executes |
| relative to other event listeners for the same event. Event listeners |
| with the same priority are executed in the order that they were |
| added. This parameter sets the <samp class="codeph">priority</samp> property |
| of the Event object. The default value is 0, but you can set it |
| to negative or positive integer values. If several event listeners |
| are added without priorities, the earlier a listener is added, the |
| sooner it is executed. For more information on setting priorities, |
| see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cda_verapache">Event |
| priorities</a>.</p> |
| |
| <p>The <em>weakRef</em> parameter provides you with some control over |
| memory resources for listeners. A strong reference (when <samp class="codeph">weakRef</samp> is <samp class="codeph">false</samp>) |
| prevents the listener from being garbage collected. A weak reference |
| (when <samp class="codeph">weakRef</samp> is <samp class="codeph">true</samp>) does not. |
| The default value is <samp class="codeph">false</samp>.</p> |
| |
| <p>When you add a listener function and that function is invoked, |
| Flex implicitly creates an Event object for you and passes it to |
| the listener function. You must declare the Event object in the |
| signature of your listener function. </p> |
| |
| <p>If you add an event listener by using the <samp class="codeph">addEventListener()</samp> method, |
| you are required to declare an event object as a parameter of the <samp class="codeph"> |
| <em>listener_function</em> |
| </samp>, |
| as the following example shows:</p> |
| |
| <pre class="codeblock"> b1.addEventListener(MouseEvent.CLICK, performAction);</pre> |
| |
| <p>In the listener function, you declare the Event object as a parameter, |
| as follows:</p> |
| |
| <pre class="codeblock"> public function performAction(e:MouseEvent):void { |
| ... |
| }</pre> |
| |
| <p>The following example defines a new handler function <samp class="codeph">myClickListener()</samp>. It |
| then registers the <samp class="codeph">click</samp> event of the Button control |
| with that handler. When the user clicks the button, Flex calls the <samp class="codeph">myClickHandler()</samp> function.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/AddEventListenerExample.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="createListener()"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| private function createListener():void { |
| b1.addEventListener(MouseEvent.CLICK, myClickHandler, false, 0); |
| } |
| |
| private function myClickHandler(e:MouseEvent):void { |
| Alert.show("The button was clicked."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button label="Click Me" id="b1"/> |
| |
| </s:Application></pre> |
| |
| <div class="section" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7feb_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7feb_verapache"><!-- --></a><h5 class="sectiontitle">Using |
| addEventListener() inside an MXML tag</h5> |
| |
| <p>You can add event listeners with |
| the <samp class="codeph">addEventListener()</samp> method inline with the component |
| definition. The following Button control definition adds the call |
| to the <samp class="codeph">addEventListener()</samp> method inline with the |
| Button control's <samp class="codeph">initialize</samp> property:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/CallingAddEventListenerInline.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function myClickHandler(event:Event):void { |
| Alert.show("The button was clicked."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id='b1' |
| label="Click Me" |
| initialize='b1.addEventListener(MouseEvent.CLICK, myClickHandler, false, 1);' |
| /> |
| |
| </s:Application></pre> |
| |
| <p>This is the equivalent of defining |
| the event handler inline. However, defining a handler by using the <samp class="codeph">addEventListener()</samp> method |
| rather than setting <samp class="codeph">click="</samp> |
| <em> |
| <samp class="codeph">handler_function</samp> |
| </em> |
| <samp class="codeph">"</samp> lets |
| you set the value of the <samp class="codeph">useCapture</samp> and <samp class="codeph">priority</samp> properties |
| of the Event object. Furthermore, you cannot remove a handler added |
| inline, but when you use the <samp class="codeph">addEventListener()</samp> method to |
| add a handler, you can call the <samp class="codeph">removeEventListener()</samp> method |
| to remove that handler.</p> |
| |
| </div> |
| |
| <div class="section" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fdc_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fdc_verapache"><!-- --></a><h5 class="sectiontitle">Using |
| nested inner functions as event listeners</h5> |
| |
| <p>Rather |
| than passing the name of an event listener function to the <samp class="codeph">addEventListener()</samp> method, |
| you can define an inner function (also known as a closure). </p> |
| |
| <p>In |
| the following example, the nested inner function is called when |
| the button is clicked:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/AddingInnerFunctionListener.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp()"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function initApp():void { |
| b1.addEventListener("click", |
| function(e:Event):void { |
| Alert.show("The button was clicked."); |
| } |
| ); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id='b1' label="Click Me"/> |
| |
| </s:Application></pre> |
| |
| <p>Function closures are created |
| any time a function is executed apart from an object or a class. |
| They retain the scope in which they were defined. This creates interesting |
| results when a function is passed as an argument or a return value into |
| a different scope. </p> |
| |
| <p>For example, the following code creates |
| two functions: <samp class="codeph">foo()</samp>, which returns a nested function |
| named <samp class="codeph">rectArea()</samp> that calculates the area of a |
| rectangle, and <samp class="codeph">bar()</samp>, which calls <samp class="codeph">foo()</samp> and |
| stores the returned function closure in a variable named <samp class="codeph">myProduct</samp>. |
| Even though the <samp class="codeph">bar()</samp> function defines its own |
| local variable <samp class="codeph">x</samp> (with a value of 2), when the |
| function closure <samp class="codeph">myProduct()</samp> is called, it retains |
| the variable <samp class="codeph">x</samp> (with a value of 40) defined in |
| function <samp class="codeph">foo()</samp>. The <samp class="codeph">bar()</samp> function |
| therefore returns the product of the numbers in the TextInput controls, |
| rather than 8.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/FunctionReturnsFunction.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="foo()"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| [Bindable] |
| private var answer:String; |
| |
| private function foo():Function { |
| var x:int = int(ti1.text); |
| function rectArea(y:int):int { // function closure defined |
| return x * y; |
| } |
| return rectArea; |
| } |
| |
| private function bar():void { |
| var x:int = 2; // ignored |
| var y:int = 4; // ignored |
| var myProduct:Function = foo(); |
| answer = myProduct(int(ti2.text)); // function closure called |
| } |
| |
| ]]> |
| </fx:Script> |
| |
| <s:Form width="107"> |
| <s:FormItem label="X"> |
| <s:TextInput id="ti1" text="10" width="37" textAlign="right"/> |
| </s:FormItem> |
| <s:FormItem label="Y" width="71"> |
| <s:TextInput id="ti2" text="20" width="38" textAlign="right"/> |
| </s:FormItem> |
| <s:Label id="label1" text="{answer}" width="71" textAlign="right"/> |
| </s:Form> |
| |
| <s:Button id='b1' label="Compute Product" click="bar()"/> |
| |
| </s:Application></pre> |
| |
| <p>If the listener that you pass |
| to <samp class="codeph">addEventListener()</samp> method is a nested inner |
| function, you should not pass <samp class="codeph">true</samp> for the <samp class="codeph">useWeakReference</samp> argument. |
| For example:</p> |
| |
| <pre class="codeblock"> addEventListener("anyEvent", |
| function(e:Event) { /* My listener function. */ }, |
| false, 0, true);</pre> |
| |
| <p>In this example, passing <samp class="codeph">true</samp> as |
| the last argument can lead to unexpected results. To Flex, an inner |
| function is actually an object, and can be freed by the garbage |
| collector. If you set the value of the <samp class="codeph">useWeakReference</samp> argument |
| to <samp class="codeph">true</samp>, as shown in the previous example, there |
| are no persistent references at all to the inner function. The next |
| time the garbage collector runs, it might free the function, and |
| the function will not be called when the event is triggered.</p> |
| |
| <p>If |
| there are other references to the inner function (for example, if |
| you saved it in another variable), the garbage collector will not |
| free it.</p> |
| |
| <p>Regular class-level member functions are not subject |
| to garbage collection; as a result, you can set the value of the <samp class="codeph">useWeakReference</samp> argument |
| to <samp class="codeph">true</samp> and they will not be garbage collected.</p> |
| |
| </div> |
| |
| <div class="section" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fe2_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd9_verapache__WS2db454920e96a9e51e63e3d11c0bf64a29-7fe2_verapache"><!-- --></a><h5 class="sectiontitle">Removing |
| event handlers</h5> |
| |
| <p>It |
| is a good idea to remove any handlers that will no longer be used. |
| This removes references to objects so that they can be targeted |
| for garbage collection. You can use the <samp class="codeph">removeEventListener()</samp> method |
| to remove an event handler that you no longer need. All components |
| that can call <samp class="codeph">addEventListener()</samp> can also call |
| the <samp class="codeph">removeEventListener()</samp> method. The syntax for |
| the <samp class="codeph">removeEventListener()</samp> method is as follows:</p> |
| |
| <pre class="codeblock"> <em>componentInstance</em>.removeEventListener(<em>event_type</em>:String, <em>listener_function</em>:Function, <em>use_capture</em>:Boolean)</pre> |
| |
| <p>For |
| example, consider the following code:</p> |
| |
| <pre class="codeblock"> myButton.removeEventListener(MouseEvent.CLICK, myClickHandler);</pre> |
| |
| <p>The <em>event_type</em> and <em>listener_function</em> parameters |
| are required. These are the same as the required parameters for |
| the <samp class="codeph">addEventListener()</samp> method.</p> |
| |
| <p>The <em>use_capture</em> parameter |
| is also identical to the parameter used in the <samp class="codeph">addEventListener()</samp> method. |
| Recall that you can listen for events during all event phases by |
| calling <samp class="codeph">addEventListener()</samp> twice: once with <em>use_capture</em> set |
| to <samp class="codeph">true</samp>, and again with it set to <samp class="codeph">false</samp>. |
| To remove both event listeners, you must call <samp class="codeph">removeEventListener()</samp> twice: |
| once with <em>use_capture</em> set to <samp class="codeph">true</samp>, and again |
| with it set to <samp class="codeph">false</samp>.</p> |
| |
| <p>You can remove only |
| event listeners that you added with the <samp class="codeph">addEventListener()</samp> method |
| in an ActionScript block. You cannot remove an event listener that |
| was defined in the MXML tag, even if it was registered using a call |
| to the <samp class="codeph">addEventListener()</samp> method that was made |
| inside a tag attribute. </p> |
| |
| <p>The following sample application |
| shows what type of handler can be removed and what type cannot:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/RemoveEventListenerExample.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="createHandler(event)"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function createHandler(e:Event):void { |
| b1.addEventListener(MouseEvent.CLICK, myClickHandler); |
| } |
| |
| private function removeMyHandlers(e:Event):void { |
| /* Remove listener for b1's click event because it was added |
| with the addEventListener() method. */ |
| b1.removeEventListener(MouseEvent.CLICK, myClickHandler); |
| |
| /* Does NOT remove the listener for b2's click event because it |
| was added inline in an MXML tag. */ |
| b2.removeEventListener(MouseEvent.CLICK, myClickHandler); |
| } |
| |
| private function myClickHandler(e:Event):void { |
| Alert.show("The button was clicked."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| <s:Button label="Click Me Too" id="b2" click="myClickHandler(event)"/> |
| <s:Button label="Remove Event Listeners" id="b3" click="removeMyHandlers(event)"/> |
| |
| </s:Application></pre> |
| |
| </div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested3" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd2_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd2_verapache"><!-- --></a> |
| <h4 class="topictitle4">Creating event handler classes</h4> |
| |
| |
| <div> |
| <p>You |
| can create an external class file and use the methods of this class |
| as event handlers. Objects themselves cannot be event handlers, |
| but methods of an object can be. By defining one class that handles |
| all your event handlers, you can use the same event handling logic |
| across applications, which can make your MXML applications more |
| readable and maintainable.</p> |
| |
| <p>To create a class that handles events, you usually import the |
| flash.events.Event class. You also usually write an empty constructor. |
| The following ActionScript class file calls the Alert control's <samp class="codeph">show()</samp> method |
| whenever it handles an event with the <samp class="codeph">handleAllEvents()</samp> method:</p> |
| |
| <pre class="codeblock">// events/MyEventHandler.as |
| |
| package { // Empty package. |
| |
| import flash.events.Event; |
| import mx.controls.Alert; |
| |
| public class MyEventHandler { |
| public function MyEventHandler() { |
| // Empty constructor. |
| } |
| |
| public function handleAllEvents(event:Event):void { |
| Alert.show("Some event happened."); |
| } |
| } |
| }</pre> |
| |
| <p>In your MXML file, you declare a new instance of MyEventHandler |
| and use the <samp class="codeph">addEventListener()</samp> method to register |
| its <samp class="codeph">handleAllEvents()</samp> method as a handler to the |
| Button control's <samp class="codeph">click</samp> event, as the following example |
| shows:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/CustomHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="createHandler()"> |
| |
| <fx:Script> |
| <![CDATA[ |
| private var myListener:MyEventHandler = new MyEventHandler(); |
| |
| private function createHandler():void { |
| b1.addEventListener(MouseEvent.CLICK, myListener.handleAllEvents); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button label="Submit" id="b1"/> |
| |
| </s:Application></pre> |
| |
| <p>The best approach is to define the event handler's method as |
| static. When you make the event handler method static, you are not |
| required to instantiate the class inside your MXML application. |
| The following <samp class="codeph">createHandler()</samp> function registers |
| the <samp class="codeph">handleAllEvents()</samp> method as an event handler without |
| instantiating the MyStaticEventHandler class:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/CustomHandlerStatic.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="createHandler()"> |
| |
| <fx:Script> |
| <![CDATA[ |
| private function createHandler():void { |
| b1.addEventListener(MouseEvent.CLICK, MyStaticEventHandler.handleAllEvents); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button label="Submit" id="b1"/> |
| |
| </s:Application></pre> |
| |
| <p>In the class file, you just add the <samp class="codeph">static</samp> keyword |
| to the method signature:</p> |
| |
| <pre class="codeblock">// events/MyStaticEventHandler.as |
| |
| package { // Empty package. |
| |
| import flash.events.Event; |
| import mx.controls.Alert; |
| |
| public class MyStaticEventHandler { |
| public function MyStaticEventHandler() { |
| // Empty constructor. |
| } |
| |
| public static function handleAllEvents(event:Event):void { |
| Alert.show("Some event happened."); |
| } |
| } |
| }</pre> |
| |
| <p>Store your event listener class in a directory in your source |
| path. You can also store your ActionScript class in the same directory |
| as your MXML file, although it is not recommended.</p> |
| |
| </div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fdf_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fdf_verapache"><!-- --></a> |
| <h3 class="topictitle3">Defining multiple listeners for |
| a single event</h3> |
| |
| |
| <div> |
| <p>You can define multiple event handler functions for a single |
| event in two ways. When defining events inside MXML tags, you separate |
| each new handler function with a semicolon. The following example |
| adds the <samp class="codeph">submitForm()</samp> and <samp class="codeph">debugMessage()</samp> functions |
| as handlers of the <samp class="codeph">click</samp> event:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/MultipleEventHandlersInline.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| [Bindable] |
| private var s:String = ""; |
| |
| private function submitForm(e:Event):void { |
| // Handle event here. |
| s += "The submitForm() method was called. "; |
| } |
| private function debugMessage(e:Event):void { |
| // Handle event here. |
| s += "The debugMessage() method was called. "; |
| } |
| ]]></fx:Script> |
| |
| <s:Button id="b1" |
| label="Do Both Actions" |
| click='submitForm(event); debugMessage(event);' |
| /> |
| <s:Label id="l1" text="{s}"/> |
| |
| <s:Button id="b2" label="Reset" click="s='';"/> |
| |
| </s:Application></pre> |
| |
| <p>For events added with the <samp class="codeph">addEventListener()</samp> method, |
| you can add any number of handlers with additional calls to the <samp class="codeph">addEventListener()</samp> method. |
| Each call adds a handler function that you want to register to the specified |
| object. The following example registers the <samp class="codeph">submitForm()</samp> and <samp class="codeph">debugMessage()</samp> handler |
| functions with b1's <samp class="codeph">click</samp> event:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/MultipleEventHandlersAS.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="createHandlers(event)"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| [Bindable] |
| private var s:String = ""; |
| |
| public function createHandlers(e:Event):void { |
| b1.addEventListener(MouseEvent.CLICK, submitForm); |
| b1.addEventListener(MouseEvent.CLICK, debugMessage); |
| } |
| |
| private function submitForm(e:Event):void { |
| // Handle event here. |
| s += "The submitForm() method was called. "; |
| |
| } |
| |
| private function debugMessage(e:Event):void { |
| // Handle event here. |
| s += "The debugMessage() method was called. "; |
| } |
| |
| ]]></fx:Script> |
| |
| <s:Button id="b1" label="Do Both Actions"/> |
| |
| <s:Label id="l1" text="{s}"/> |
| |
| <s:Button id="b2" label="Reset" click="s='';"/> |
| |
| </s:Application></pre> |
| |
| <p>You can mix the methods of adding event handlers to any component; |
| alternatively, you can add handlers inline and with the <samp class="codeph">addEventListener()</samp> method. |
| The following example adds a <samp class="codeph">click</samp> event handler |
| inline for the Button control, which calls the <samp class="codeph">performAction()</samp> method. |
| It then conditionally adds a second <samp class="codeph">click</samp> handler |
| to call the <samp class="codeph">logAction()</samp> method, depending on the |
| state of the CheckBox control.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/ConditionalHandlers.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="initApp(event)"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function initApp(e:Event):void { |
| cb1.addEventListener(MouseEvent.CLICK, handleCheckBoxChange); |
| b1.addEventListener(MouseEvent.CLICK, logAction); |
| } |
| |
| private function handleCheckBoxChange(e:Event):void { |
| if (cb1.selected) { |
| b1.addEventListener(MouseEvent.CLICK, logAction); |
| ta1.text += "Added log listener." + "\n"; |
| } else { |
| b1.removeEventListener(MouseEvent.CLICK, logAction); |
| ta1.text += "Removed log listener." + "\n"; |
| } |
| } |
| |
| private function performAction(e:Event):void { |
| Alert.show("You performed the action."); |
| } |
| |
| private function logAction(e:Event):void { |
| ta1.text += "Action performed: " + e.type + ".\n"; |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button label="Perform Action" id="b1" click="performAction(event)"/> |
| <s:CheckBox id="cb1" label="Log?" selected="true"/> |
| <s:TextArea id="ta1" height="200" width="300"/> |
| |
| </s:Application></pre> |
| |
| <p>You can set the order in which event listeners are called by |
| using the <samp class="codeph">priority</samp> parameter of the <samp class="codeph">addEventListener()</samp> method. |
| You cannot set a priority for a listener function if you added the |
| event listener using MXML inline. For more information on setting |
| priorities, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cda_verapache">Event |
| priorities</a>.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fde_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fde_verapache"><!-- --></a> |
| <h3 class="topictitle3">Registering a single listener with |
| multiple components</h3> |
| |
| |
| <div> |
| <p>You can register the same listener function with any number |
| of events of the same component, or events of different components. |
| The following example registers a single listener function, <samp class="codeph">submitForm()</samp>, |
| with two different buttons:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/OneHandlerTwoComponentsInline.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function submitForm(e:Event):void { |
| // Handle event here. |
| Alert.show("Current Target: " + e.currentTarget.id); |
| } |
| |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" |
| label="Click Me" |
| click="submitForm(event)"/> |
| |
| <s:Button id="b2" |
| label="Click Me, Too" |
| click="submitForm(event)"/> |
| |
| </s:Application></pre> |
| |
| <p>When |
| you use the <samp class="codeph">addEventListener()</samp> method to register |
| a single listener to handle the events of multiple components, you |
| must use a separate call to the <samp class="codeph">addEventListener()</samp> method |
| for each instance, as the following example shows: </p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/OneHandlerTwoComponentsAS.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="createHandlers(event)"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| public function createHandlers(e:Event):void { |
| b1.addEventListener(MouseEvent.CLICK, submitForm); |
| b2.addEventListener(MouseEvent.CLICK, submitForm); |
| } |
| |
| private function submitForm(e:Event):void { |
| // Handle event here. |
| Alert.show("Current Target: " + e.currentTarget.id); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| <s:Button id="b2" label="Click Me, Too"/> |
| |
| </s:Application></pre> |
| |
| <p>When doing this, you should add logic to the event listener that |
| processes the type of event. The event target (or object that dispatched |
| the event) is added to the Event object for you. No matter what |
| triggered the event, you can conditionalize the event processing |
| based on the <samp class="codeph">target</samp> or <samp class="codeph">type</samp> properties |
| of the Event object. Flex adds these two properties to all Event |
| objects.</p> |
| |
| <p>The following example registers a single listener function (<samp class="codeph">myEventHandler()</samp>) |
| to the <samp class="codeph">click</samp> event of a Button control and the <samp class="codeph">click</samp> event |
| of a CheckBox control. To detect what type of object called the |
| event listener, the listener checks the <samp class="codeph">className</samp> property |
| of the target in the Event object in a <samp class="codeph">case</samp> statement.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/ConditionalTargetHandler.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp()"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| public function initApp():void { |
| button1.addEventListener(MouseEvent.CLICK, myEventHandler); |
| cb1.addEventListener(MouseEvent.CLICK, myEventHandler); |
| } |
| |
| public function myEventHandler(event:Event):void { |
| switch (event.currentTarget.className) { |
| case "Button": |
| // Process Button click. |
| Alert.show("You clicked the Button control."); |
| break; |
| case "CheckBox": |
| // Process CheckBox click. |
| Alert.show("You clicked the CheckBox control."); |
| break; |
| } |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button label="Click Me" id="button1"/> |
| <s:CheckBox label="Select Me" id="cb1"/> |
| |
| </s:Application></pre> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff7_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff7_verapache"><!-- --></a> |
| <h3 class="topictitle3">Passing additional parameters to |
| listener functions</h3> |
| |
| |
| <div> |
| <p>You can pass additional parameters to listener functions |
| depending on how you add the listeners. If you add a listener with |
| the <samp class="codeph">addEventListener()</samp> method, you cannot pass |
| any additional parameters to the listener function by arbitrarily |
| adding new parameters to the function signature. The default listener function |
| can declare only a single argument, the Event object (or one of |
| its subclasses).</p> |
| |
| <p>For example, the following code throws an error because the <samp class="codeph">clickListener()</samp> method |
| expects two arguments:</p> |
| |
| <pre class="codeblock"> <fx:Script> |
| public function addListeners():void { |
| b1.addEventListener(MouseEvent.CLICK,clickListener); |
| } |
| public function clickListener(e:MouseEvent, a:String):void { ... } |
| </fx:Script> |
| <mx:Button id="b1"/></pre> |
| |
| <p>Because the second parameter of the <samp class="codeph">addEventListener()</samp> method |
| is a function, you can define that function and pass the event object |
| plus any additional parameters through to a different handler. The |
| following example creates a new function in the <samp class="codeph">addEventListener()</samp> method, |
| add two parameters to the new handler's call, and then handles all |
| of the parameters in the <samp class="codeph">myClickListener()</samp> method.</p> |
| |
| <pre class="codeblock"><?xml version="1.0" encoding="utf-8"?> |
| <!-- events/CustomListenerFunction.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp(event)"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| private var specialParam1:String; |
| private var specialParam2:String = "42"; |
| |
| private function initApp(e:Event):void { |
| assignSpecialParam(e); |
| |
| /* Change the value of specialParam whenever the user changes it |
| in the TextInput and clicks the button. */ |
| ti1.addEventListener("focusOut", assignSpecialParam); |
| |
| /* Define the pass-through method in the addEventListener() method call. |
| You can add any number of parameters, as long as teh target method's |
| signature agrees. */ |
| myButton.addEventListener(MouseEvent.CLICK, function (e:MouseEvent):void { |
| myClickListener(e, specialParam1, specialParam2); |
| } |
| ); |
| } |
| |
| private function assignSpecialParam(e:Event):void { |
| specialParam1 = ti1.text; |
| } |
| |
| /* This method acts as the event listener, and it has any |
| number of parameters that we defined in the addEventListener() call. */ |
| private function myClickListener(e:MouseEvent, s1:String, s2:String) : void { |
| myButton.label = s1 + " " + s2; |
| } |
| ]]> |
| </fx:Script> |
| <s:Button id="myButton" label="Click Me"/> |
| <s:TextInput id="ti1" text="Enter a custom String here." width="250"/> |
| |
| </s:Application></pre> |
| |
| <p>Another approach to passing additional parameters to the listener |
| function is to define them in the listener function and then call |
| the final method with those parameters. If you define an event listener |
| inline (inside the MXML tag), you can add any number of parameters |
| as long as the listener function's signature agrees with that number |
| of parameters. </p> |
| |
| <p>The following example passes a string and the Event object to |
| the <samp class="codeph">runMove()</samp> method:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/MultipleHandlerParametersInline.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| public function runMove(dir:String, e:Event):void { |
| if (dir == "up") { |
| moveableButton.y = moveableButton.y - 5; |
| } else if (dir == "down") { |
| moveableButton.y = moveableButton.y + 5; |
| } else if (dir == "left") { |
| moveableButton.x = moveableButton.x - 5; |
| } else if (dir == "right") { |
| moveableButton.x = moveableButton.x + 5; |
| } |
| } |
| ]]> |
| </fx:Script> |
| |
| <mx:Canvas height="100%" width="100%"> |
| <s:Button id="moveableButton" |
| label="{moveableButton.x.toString()},{moveableButton.y.toString()}" |
| x="75" |
| y="100" |
| width="80" |
| /> |
| </mx:Canvas> |
| |
| <s:VGroup horizontalAlign="center"> |
| <s:Button id="b1" |
| label="Up" |
| click='runMove("up",event);' |
| width="75"/> |
| <s:HGroup horizontalAlign="center"> |
| <mx:Button id="b2" |
| label="Left" |
| click='runMove("left",event);' |
| width="75"/> |
| <s:Button id="b3" |
| label="Right" |
| click='runMove("right",event);' |
| width="75"/> |
| </s:HGroup> |
| <s:Button id="b4" |
| label="Down" |
| click='runMove("down",event);' |
| width="75"/> |
| </s:VGroup> |
| |
| </s:Application></pre> |
| |
| </div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf69084-7ce1_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7ce1_verapache"><!-- --></a> |
| <h2 class="topictitle2">Manually dispatching events</h2> |
| |
| |
| <div> |
| <p>You can manually dispatch events using a component instance's <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/EventDispatcher.html#dispatchEvent()" target="_blank">dispatchEvent()</a> method. |
| All components that extend <a href="https://flex.apache.org/asdoc/mx/core/UIComponent.html" target="_blank">UIComponent</a> have |
| this method. The method is inherited from the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/EventDispatcher.html" target="_blank">EventDispatcher</a> class, |
| which UIComponent extends.</p> |
| |
| <p>The syntax for the <samp class="codeph">dispatchEvent()</samp> method |
| is as follows:</p> |
| |
| <pre class="codeblock"> objectInstance.dispatchEvent(event:Event):Boolean</pre> |
| |
| <p>When dispatching an event, you must create a new Event object. |
| The syntax for the Event object constructor is as follows:</p> |
| |
| <pre class="codeblock"> Event(<em>event_type</em>:String, <em>bubbles</em>:Boolean, <em>cancelable</em>:Boolean)</pre> |
| |
| <p>The <em>event_type</em> parameter is the <samp class="codeph">type</samp> property |
| of the Event object. The <em>bubbles</em> and <em>cancelable</em> parameters |
| are optional and both default to <samp class="codeph">false</samp>. For information |
| on bubbling and capturing, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7cdb_verapache">Event |
| propagation</a>.</p> |
| |
| <p>You can use the <samp class="codeph">dispatchEvent()</samp> method to dispatch |
| any event you want, not just a custom event. You can dispatch a |
| Button control's <samp class="codeph">click</samp> event, even though the user |
| did not click a Button control, as in the following example:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/DispatchEventExample.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="createListener(event);"> |
| |
| <fx:Script><![CDATA[ |
| import mx.controls.Alert; |
| private function createListener(e:Event):void { |
| b1.addEventListener(MouseEvent.MOUSE_OVER, myEventHandler); |
| b1.addEventListener(MouseEvent.CLICK, myClickHandler); |
| } |
| |
| private function myEventHandler(e:Event):void { |
| var result:Boolean = b1.dispatchEvent(new MouseEvent(MouseEvent.CLICK, true, false)); |
| } |
| |
| private function myClickHandler(e:Event):void { |
| Alert.show("The event dispatched by the MOUSE_OVER was of type '" + e.type + "'."); |
| } |
| ]]></fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| </s:Application></pre> |
| |
| <p>You can also manually dispatch an event in an MXML tag. In the |
| following example, moving the mouse pointer over the button triggers |
| the button's <samp class="codeph">click</samp> event:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/DispatchEventExampleInline.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="createListener(event);"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function createListener(e:Event):void { |
| b1.addEventListener(MouseEvent.CLICK, myClickHandler); |
| } |
| |
| private function myClickHandler(e:Event):void { |
| Alert.show("The event dispatched by the MOUSE_OVER was of type '" + e.type + "'."); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" |
| label="Click Me" |
| mouseOver="b1.dispatchEvent(new MouseEvent(MouseEvent.CLICK, true, false));" |
| /> |
| |
| </s:Application></pre> |
| |
| <p>Your application is not required to handle the newly dispatched |
| event. If you trigger an event that has no listeners, Flex ignores |
| the event.</p> |
| |
| <p>You can set properties of the Event object in ActionScript, but |
| you cannot add new properties because the object is not dynamic. |
| The following example intercepts a <samp class="codeph">click</samp> event. |
| It then creates a new MouseEvent object and dispatches it as a <samp class="codeph">doubleClick</samp> event. |
| In addition, it sets the value of the <samp class="codeph">shiftKey</samp> property |
| of the MouseEvent object to <samp class="codeph">true</samp>, to simulate a |
| Shift-click on the keyboard. </p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/DispatchCustomizedEvent.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="addListeners()"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| private function customLogEvent(e:MouseEvent):void { |
| l1.text = String(e.currentTarget.id); |
| l2.text = String(e.type); |
| l3.text = String(e.shiftKey); |
| |
| // Remove current listener to avoid recursion. |
| e.currentTarget.removeEventListener("doubleClick", customLogEvent); |
| } |
| |
| private function handleEvent(e:MouseEvent):void { |
| // Add new handler for custom event about to be dispatched. |
| e.currentTarget.addEventListener("doubleClick", customLogEvent); |
| |
| // Create new event object. |
| var mev:MouseEvent = new MouseEvent("doubleClick"); |
| |
| // Customize event object. |
| mev.shiftKey = true; |
| |
| // Dispatch custom event. |
| e.currentTarget.dispatchEvent(mev); |
| } |
| |
| private function addListeners():void { |
| b1.addEventListener("click",handleEvent); |
| b2.addEventListener("click",handleEvent); |
| } |
| |
| ]]></fx:Script> |
| |
| <s:Button id="b1" label="Click Me (b1)"/> |
| <s:Button id="b2" label="Click Me (b2)"/> |
| |
| <s:Form> |
| <s:FormItem label="Current Target:"> |
| <s:Label id="l1"/> |
| </s:FormItem> |
| <s:FormItem label="Event Type:"> |
| <s:Label id="l2"/> |
| </s:FormItem> |
| <s:FormItem label="Shift Key Pressed:"> |
| <s:Label id="l3"/> |
| </s:FormItem> |
| </s:Form> |
| |
| </s:Application></pre> |
| |
| <p>If you want to add custom properties to an Event object, you |
| must extend the Event object and define the new properties in your |
| own custom class. You can then manually dispatch your custom events |
| with the <samp class="codeph">dispatchEvent()</samp> method, as you would any |
| event.</p> |
| |
| <p>If you create a custom ActionScript class that dispatches its |
| own events but does not extend UIComponent, you can extend the flash.events.EventDispatcher |
| class to get access to the <samp class="codeph">addEventListener()</samp>, <samp class="codeph">removeEventListener()</samp>, and <samp class="codeph">dispatchEvent()</samp> methods.</p> |
| |
| <p>To make your code more efficient, you can check to see if the |
| intended target of a dispatched event is listening for the event. |
| If it is not, then there is no reason to dispatch the event. This |
| is especially true if the event bubbles because that means many |
| calls will be made by the system while it searches for a target. |
| You can check by using the <samp class="codeph">hasEventListner()</samp> and <samp class="codeph">willTrigger()</samp> methods.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cdb_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cdb_verapache"><!-- --></a> |
| <h2 class="topictitle2">Event propagation</h2> |
| |
| |
| <div> |
| <p>When events are triggered, there are three phases in which |
| Flex checks whether there are event listeners. These phases occur |
| in the following order: </p> |
| |
| <ul> |
| <li> |
| <p>Capturing</p> |
| |
| </li> |
| |
| <li> |
| <p>Targeting</p> |
| |
| </li> |
| |
| <li> |
| <p>Bubbling</p> |
| |
| </li> |
| |
| </ul> |
| |
| <p>During each of these phases, the nodes have a chance to react |
| to the event. For example, assume the user clicks a Button control |
| that is inside a VBox container. During the capturing phase, Flex |
| checks the Application object and the VBox for listeners to handle |
| the event. Flex then triggers the Button's listeners in the target phase. |
| In the bubbling phase, the VBox and then the Application are again |
| given a chance to handle the event but now in the reverse order |
| from the order in which they were checked in the capturing phase.</p> |
| |
| <p>In ActionScript 3.0, you can register event listeners on a target |
| node and on any node along the event flow. Not all events, however, |
| participate in all three phases of the event flow. Some types of |
| events are dispatched directly to the target node and participate |
| in neither the capturing nor the bubbling phases. All events can be |
| captured unless they are dispatched from the top node.</p> |
| |
| <p>Other events may target objects that are not on the display list, |
| such as events dispatched to an instance of the Socket class. These |
| event objects flow directly to the target node, without participating |
| in the capturing or bubbling phases. You can also cancel an event |
| as it flows through the event model so that even though it was supposed |
| to continue to the other phases, you stopped it from doing so. You |
| can do this only if the <samp class="codeph">cancelable</samp> property is |
| set to <samp class="codeph">true</samp>.</p> |
| |
| <p>Capturing and bubbling happen as the Event object moves from |
| node to node in the display list: parent-to-child for capturing |
| and child-to-parent for bubbling. This process has nothing to do |
| with the inheritance hierarchy. Only <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/display/DisplayObject.html" target="_blank">DisplayObject</a> objects |
| (visual objects such as containers and controls) can have a capturing |
| phase and a bubbling phase in addition to the targeting phase. </p> |
| |
| <p>Mouse events and keyboard events are among those that bubble. |
| Any event can be captured, but no DisplayObject objects listen during |
| the capturing phase unless you explicitly instruct them to do so. |
| In other words, capturing is disabled by default.</p> |
| |
| <p>When a faceless event dispatcher, such as a Validator, dispatches |
| an event, there is only a targeting phase, because there is no visual |
| display list for the Event object to capture or bubble through.</p> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cd3_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cd3_verapache"><!-- --></a> |
| <h3 class="topictitle3">About the target and currentTarget |
| properties</h3> |
| |
| |
| <div> |
| <p>Every <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html" target="_blank">Event</a> object |
| has a <samp class="codeph">target</samp> and a <samp class="codeph">currentTarget</samp> property |
| that help you to keep track of where it is in the process of propagation. |
| The <samp class="codeph">target</samp> property refers to the dispatcher of |
| the event. The <samp class="codeph">currentTarget</samp> property refers to |
| the current node that is being examined for event listeners.</p> |
| |
| <p>When you handle a mouse event such as <samp class="codeph">MouseEvent.CLICK</samp> by |
| writing a listener on some component, the <samp class="codeph">event.target</samp> property |
| does not necessarily refer to that component; it is often a subcomponent, |
| such as the Button control's UITextField, that defines the label.</p> |
| |
| <p>When Flash Player or Adobe<sup>®</sup> AIR™ dispatches an event, it dispatches the |
| event from the frontmost object under the mouse. Because children |
| are in front of parents, that means the player or AIR might dispatch |
| the event from an internal subcomponent, such as the UITextField |
| of a Button.</p> |
| |
| <p>The <samp class="codeph">event.target</samp> property is set to the object |
| that dispatched the event (in this case, UITextField), not the object |
| that is being listened to (in most cases, you have a Button control |
| listen for a <samp class="codeph">click</samp> event). </p> |
| |
| <p>MouseEvent events bubble up the parent chain, and can be handled |
| on any ancestor. As the event bubbles, the value of the <samp class="codeph">event.target</samp> property |
| stays the same (UITextField), but the value of the <samp class="codeph">event.currentTarget</samp> property is |
| set at each level to be the ancestor that is handling the event. |
| Eventually, the <samp class="codeph">currentTarget</samp> will be Button, at |
| which time the Button control's event listener will handle the event. |
| For this reason, you should use the <samp class="codeph">event.currentTarget</samp> property |
| rather than the <samp class="codeph">event.target</samp> property; for example:</p> |
| |
| <pre class="codeblock"> <mx:Button label="OK" click="trace(event.currentTarget.label)"/></pre> |
| |
| <p>In this case, in the Button event's click event listener, the <samp class="codeph">event.currentTarget</samp> property |
| always refers to the Button, while <samp class="codeph">event.target</samp> might |
| be either the Button or its UITextField, depending on where on the |
| Button control the user clicked.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cde_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cde_verapache"><!-- --></a> |
| <h3 class="topictitle3">Capturing phase</h3> |
| |
| |
| <div> |
| <p>In the capturing phase, Flex examines an event target's |
| ancestors in the display list to see which ones are registered as |
| a listener for the event. Flex starts with the root ancestor and |
| continues down the display list to the direct ancestor of the target. |
| In most cases, the root ancestors are the Stage, then the SystemManager, and |
| then the Application object.</p> |
| |
| <p>For example, if you have an application with a Panel container |
| that contains a TitleWindow container, which in turn contains a |
| Button control, the structure appears as follows:</p> |
| |
| <pre class="codeblock"> Application |
| Panel |
| TitleWindow |
| Button</pre> |
| |
| <p>If your listener is on the <samp class="codeph">click</samp> event of the |
| Button control, the following steps occur during the capturing phase |
| if capturing is enabled:</p> |
| |
| <ol> |
| <li> |
| <p>Check the Application container for click event listeners.</p> |
| |
| </li> |
| |
| <li> |
| <p>Check the Panel container for click event listeners.</p> |
| |
| </li> |
| |
| <li> |
| <p>Check the TitleWindow container for click event listeners.</p> |
| |
| </li> |
| |
| </ol> |
| |
| <p>During the capturing phase, Flex changes the value of the <samp class="codeph">currentTarget</samp> property |
| on the Event object to match the current node whose listener is |
| being called. The <samp class="codeph">target</samp> property continues to |
| refer to the dispatcher of the event.</p> |
| |
| <p>By default, no container listens during the capturing phase. |
| The default value of the <em>use_capture</em> argument is <samp class="codeph">false</samp>. |
| The only way to add a listener during this phase is to pass <samp class="codeph">true</samp> for |
| the <em>use_capture</em> argument when calling the <samp class="codeph">addEventListener()</samp> method, |
| as the following example shows:</p> |
| |
| <pre class="codeblock"> myPanel.addEventListener(MouseEvent.MOUSE_DOWN, clickHandler, true);</pre> |
| |
| <p>If you add an event listener inline with MXML, Flex sets this |
| argument to <samp class="codeph">false</samp>; you cannot override it.</p> |
| |
| <p>If you set the <em>use_capture</em> argument to <samp class="codeph">true</samp>—in |
| other words, if an event is propagated through the capturing phase—the |
| event can still bubble, but capture phase listeners will not react |
| to it. If you want your event to traverse both the capturing and |
| bubbling phases, you must call <samp class="codeph">addEventListener()</samp> twice: |
| once with <em>use_capture</em> set to <samp class="codeph">true</samp>, and then |
| again with <em>use_capture</em> set to <samp class="codeph">false</samp>. </p> |
| |
| <p>The capturing phase is very rarely used, and it can also be computationally intensive. |
| By contrast, bubbling is much more common.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf69084-7ccf_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7ccf_verapache"><!-- --></a> |
| <h3 class="topictitle3">Targeting phase</h3> |
| |
| |
| <div> |
| <p>In the targeting phase, Flex invokes the event dispatcher's |
| listeners. No other nodes on the display list are examined for event |
| listeners. The values of the <samp class="codeph">currentTarget</samp> and |
| the <samp class="codeph">target</samp> properties on the Event object during |
| the targeting phase are the same.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cce_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cce_verapache"><!-- --></a> |
| <h3 class="topictitle3">Bubbling phase</h3> |
| |
| |
| <div> |
| <p>In the bubbling phase, Flex examines an event's ancestors |
| for event listeners. Flex starts with the dispatcher's immediate |
| ancestor and continues up the display list to the root ancestor. |
| This is the reverse of the capturing phase.</p> |
| |
| <p>For example, if you have an application with a Panel container |
| that contains a TitleWindow container that contains a Button control, |
| the structure appears as follows:</p> |
| |
| <pre class="codeblock"> Application |
| Panel |
| TitleWindow |
| Button</pre> |
| |
| <p>If your listener is on the <samp class="codeph">click</samp> event of the |
| Button control, the following steps occur during the bubble phase |
| if bubbling is enabled:</p> |
| |
| <ol> |
| <li> |
| <p>Check the TitleWindow container for click event listeners.</p> |
| |
| </li> |
| |
| <li> |
| <p>Check the Panel container for click event listeners.</p> |
| |
| </li> |
| |
| <li> |
| <p>Check the Application container for click event listeners.</p> |
| |
| </li> |
| |
| </ol> |
| |
| <p>An event only bubbles if its <samp class="codeph">bubbles</samp> property |
| is set to <samp class="codeph">true</samp>. Mouse events and keyboard events |
| are among those that bubble; it is less common for higher-level events |
| that are dispatched by Flex to bubble. Events that can be bubbled |
| include <samp class="codeph">change</samp>, <samp class="codeph">click</samp>, <samp class="codeph">doubleClick</samp>, <samp class="codeph">keyDown</samp>, <samp class="codeph">keyUp</samp>, <samp class="codeph">mouseDown</samp>, |
| and <samp class="codeph">mouseUp</samp>. To determine whether an event bubbles, |
| see the event's entry in the <em> |
| <a href="https://flex.apache.org/asdoc/" target="_blank">ActionScript 3.0 Reference for Apache Flex</a></em>.</p> |
| |
| <p>During the bubbling phase, Flex changes the value of the <samp class="codeph">currentTarget</samp> property |
| on the Event object to match the current node whose listener is |
| being called. The <samp class="codeph">target</samp> property continues to |
| refer to the dispatcher of the event.</p> |
| |
| <p>When Flex invokes an event listener, the Event object might have |
| actually been dispatched by an object deeper in the display list. |
| The object that originally dispatched the event is the <samp class="codeph">target</samp>. |
| The object that the event is currently bubbling through is the <samp class="codeph">currentTarget</samp>. |
| So, you should generally use the <samp class="codeph">currentTarget</samp> property |
| instead of the <samp class="codeph">target</samp> property when referring to the |
| current object in your event listeners.</p> |
| |
| <p>If you set the <samp class="codeph">useCapture</samp> property to <samp class="codeph">true</samp>—in |
| other words, if an event is propagated through the capturing phase—then |
| it does not bubble, regardless of its default bubbling behavior. |
| If you want your event to traverse both the capturing and bubbling |
| phases, you must call <samp class="codeph">addEventListener()</samp> twice: once |
| with <samp class="codeph">useCapture</samp> set to <samp class="codeph">true</samp>, and |
| then again with <samp class="codeph">useCapture</samp> set to <samp class="codeph">false</samp>.</p> |
| |
| <p>An event only bubbles up the parent's chain of ancestors in the |
| display list. Siblings, such as two Button controls inside the same |
| container, do not intercept each other's events. </p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe9_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe9_verapache"><!-- --></a> |
| <h3 class="topictitle3">Detecting the event phase</h3> |
| |
| |
| <div> |
| <p>You can determine what phase you are in by using the Event |
| object's <samp class="codeph">eventPhase</samp> property. This property contains |
| an integer that represents one of the following constants:</p> |
| |
| <ul> |
| <li> |
| <p>1 — Capturing phase (<samp class="codeph">CAPTURING_PHASE</samp>)</p> |
| |
| </li> |
| |
| <li> |
| <p>2 — Targeting phase (<samp class="codeph">AT_TARGET</samp>)</p> |
| |
| </li> |
| |
| <li> |
| <p>3 — Bubbling phase (<samp class="codeph">BUBBLING_PHASE</samp>)</p> |
| |
| </li> |
| |
| </ul> |
| |
| <p>The following example displays the current phase and information |
| about the current target:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/DisplayCurrentTargetInfo.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <fx:Script><![CDATA[ |
| import mx.controls.Alert; |
| |
| private function showInfo(e:MouseEvent):void { |
| Alert.show("Phase: " + e.eventPhase + "\n" + |
| "ID: " + e.currentTarget.id + "\n" + |
| "Label: " + e.currentTarget.label + "\n" + |
| "Font Size: " + e.currentTarget.getStyle("fontSize"), "Current Target Info"); |
| } |
| ]]></fx:Script> |
| |
| <s:Button id="b1" label="Click Me" click="showInfo(event)"/> |
| |
| </s:Application></pre> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ffa_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ffa_verapache"><!-- --></a> |
| <h3 class="topictitle3">Stopping propagation</h3> |
| |
| |
| <div> |
| <p>During any phase, you can stop the traversal of the display |
| list by calling one of the following methods on the Event object:</p> |
| |
| <ul> |
| <li> |
| <p> |
| <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html#stopPropagation()" target="_blank">stopPropagation()</a> |
| </p> |
| |
| </li> |
| |
| <li> |
| <p> |
| <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html#stopImmediatePropagation()" target="_blank">stopImmediatePropagation()</a> |
| </p> |
| |
| </li> |
| |
| </ul> |
| |
| <p>You can call either the event's <samp class="codeph">stopPropagation()</samp> method |
| or the <samp class="codeph">stopImmediatePropagation()</samp> method to prevent |
| an Event object from continuing on its way through the event flow. |
| The two methods are nearly identical and differ only in whether |
| the current node's remaining event listeners are allowed to execute. |
| The <samp class="codeph">stopPropagation()</samp> method prevents the Event object |
| from moving on to the next node, but only after any other event |
| listeners on the current node are allowed to execute. </p> |
| |
| <p>The <samp class="codeph">stopImmediatePropagation()</samp> method also prevents |
| the Event objects from moving on to the next node, but it does not |
| allow any other event listeners on the current node to execute. </p> |
| |
| <p>The following example creates a <a href="https://flex.apache.org/asdoc/mx/containers/TitleWindow.html" target="_blank">TitleWindow</a> container |
| inside a Panel container. Both containers are registered to listen |
| for a <samp class="codeph">mouseDown</samp> event. As a result, if you click |
| on the TitleWindow container, the <samp class="codeph">showAlert()</samp> method |
| is called twice unless you add a call to the <samp class="codeph">stopImmediatePropagation()</samp> method, |
| as the following example shows:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/StoppingPropagation.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="init(event);"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| import flash.events.MouseEvent; |
| import flash.events.Event; |
| |
| public function init(e:Event):void { |
| p1.addEventListener(MouseEvent.MOUSE_DOWN, showAlert); |
| tw1.addEventListener(MouseEvent.MOUSE_DOWN, showAlert); |
| tw1.addEventListener(Event.CLOSE, closeWindow); |
| |
| p2.addEventListener(MouseEvent.MOUSE_DOWN, showAlertWithoutStoppingPropagation); |
| tw2.addEventListener(MouseEvent.MOUSE_DOWN, showAlertWithoutStoppingPropagation); |
| tw2.addEventListener(Event.CLOSE, closeWindow); |
| } |
| |
| public function showAlert(e:Event):void { |
| Alert.show("Alert!\n" + "Current Target: " + e.currentTarget + "\n" + |
| "Phase: " + e.eventPhase); |
| e.stopImmediatePropagation(); |
| } |
| |
| public function showAlertWithoutStoppingPropagation(e:Event):void { |
| Alert.show("Alert!\n" + "Current Target: " + e.currentTarget + "\n" + |
| "Phase: " + e.eventPhase); |
| } |
| |
| public function closeWindow(e:Event):void { |
| p1.removeChild(tw1); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Panel id="p1" title="Stops Propagation"> |
| <mx:TitleWindow id="tw1" |
| width="300" |
| height="100" |
| showCloseButton="true" |
| title="Title Window 1"> |
| <s:Button label="Click Me"/> |
| <s:TextArea id="ta1"/> |
| </mx:TitleWindow> |
| </s:Panel> |
| |
| <s:Panel id="p2" title="Does Not Stop Propagation"> |
| <mx:TitleWindow id="tw2" |
| width="300" |
| height="100" |
| showCloseButton="true" |
| title="Title Window 2"> |
| <s:Button label="Click Me"/> |
| <s:TextArea id="ta2"/> |
| </mx:TitleWindow> |
| </s:Panel> |
| |
| </s:Application></pre> |
| |
| <div class="note"><span class="notetitle">Note:</span> A call to either the <samp class="codeph">Event.stopPropogation()</samp> or |
| the <samp class="codeph"> Event.stopImmediatePropogation()</samp> methods does |
| not prevent default behavior from occurring.</div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff2_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff2_verapache"><!-- --></a> |
| <h3 class="topictitle3">Event examples</h3> |
| |
| |
| <div> |
| <p>In the following example, the parent container's click |
| handler disables the target control after the target handles the |
| event. It shows that you can reuse the logic of a single listener |
| (click the HGroup container) for multiple events (all the clicks).</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/NestedHandlers.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| public function disableControl(event:MouseEvent):void { |
| // Use this same logic for all events. |
| event.currentTarget.enabled = false; |
| } |
| |
| public function doSomething(event:MouseEvent):void { |
| b1.label = "clicked"; |
| ta1.text += "Something happened."; |
| } |
| |
| public function doSomethingElse(event:MouseEvent):void { |
| b2.label = "clicked"; |
| ta1.text += "Something happened again."; |
| } |
| ]]></fx:Script> |
| |
| <s:HGroup id="hb1" height="200" click="disableControl(event)"> |
| <s:Button id='b1' label="Click Me" click="doSomething(event)"/> |
| <s:Button id='b2' label="Click Me" click="doSomethingElse(event)"/> |
| <s:TextArea id="ta1"/> |
| </s:HGroup> |
| |
| <s:Button id="resetButton" |
| label="Reset" |
| click="hb1.enabled=true;b1.enabled=true;b2.enabled=true;b1.label='Click Me';b2.label='Click Me';"/> |
| |
| </s:Application></pre> |
| |
| <p>By having a single listener on a parent control instead of many |
| listeners (one on each child control), you can reduce your code |
| size and make your applications more efficient. Reducing the number |
| of calls to the <samp class="codeph">addEventListener()</samp> method potentially |
| reduces application startup time and memory usage.</p> |
| |
| <p>The following example registers an event handler for the Panel |
| container, rather than registering a listener for each link. All |
| children of the Panel container inherit this event handler. Since |
| Flex invokes the handler on a bubbled event, you use the <samp class="codeph">target</samp> property |
| rather than the <samp class="codeph">currentTarget</samp> property. In this handler, |
| the <samp class="codeph">currentTarget</samp> property would refer to the Panel |
| control, whereas the <samp class="codeph">target</samp> property refers to |
| the LinkButton control, which has the label that you want.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/SingleRegisterHandler.mxml --> |
| <s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="createLinkHandler();"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| private function linkHandler(event:MouseEvent):void { |
| try { |
| var url:URLRequest = new URLRequest("http://finance.google.com/finance?q=" + |
| event.target.label); |
| navigateToURL(url); |
| } catch (e:Error) { |
| /** |
| * Do nothing; just want to catch the error that occurs when a user clicks on |
| * the Panel and not one of the LinkButtons. |
| **/ |
| } |
| } |
| private function createLinkHandler():void { |
| p1.addEventListener(MouseEvent.CLICK,linkHandler); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Panel id="p1" title="Click on a stock ticker symbol"> |
| <s:layout> |
| <s:HorizontalLayout/> |
| </s:layout> |
| <mx:LinkButton label="ADBE"/> |
| <mx:LinkButton label="GE"/> |
| <mx:LinkButton label="IBM"/> |
| <mx:LinkButton label="INTC"/> |
| </s:Panel> |
| </s:Application></pre> |
| |
| </div> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf69084-7cda_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7cda_verapache"><!-- --></a> |
| <h2 class="topictitle2">Event priorities</h2> |
| |
| |
| <div> |
| <p>You can |
| register any number of event listeners with a single event. Flex |
| registers event listeners in the order in which the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/EventDispatcher.html#addEventListener()" target="_blank">addEventListener()</a> methods |
| are called. Flex then typically calls the listener functions when |
| the event occurs in the order in which they were registered. However, |
| if you register some event listeners inline and some with the <samp class="codeph">addEventListener()</samp> method, |
| the order in which the listeners are called for a single event can |
| be unpredictable.</p> |
| |
| <p>You can change the order in which Flex calls event listeners |
| by using the <em>priority</em> parameter of the <samp class="codeph">addEventListener()</samp> method. |
| It is the fourth argument of the <samp class="codeph">addEventListener()</samp> method. </p> |
| |
| <p>Flex calls event listeners in priority order, from highest to |
| lowest. The highest priority event is called first. In the following |
| example, Flex calls the <samp class="codeph">verifyInputData()</samp> method |
| before the <samp class="codeph">saveInputData()</samp> function. The <samp class="codeph">verifyInputData()</samp> method |
| has the highest priority. The last method to be called is <samp class="codeph">returnResult()</samp> because |
| the value of its <samp class="codeph">priority</samp> parameter is lowest.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/ShowEventPriorities.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp()"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| private function returnResult(e:Event):void { |
| ta1.text += "returnResult() method called last (priority 1)\n"; |
| } |
| |
| private function verifyInputData(e:Event):void { |
| ta1.text += "verifyInputData() method called first (priority 3)\n"; |
| } |
| |
| private function saveInputData(e:Event):void { |
| ta1.text += "saveInputData() method called second (priority 2)\n"; |
| } |
| |
| private function initApp():void { |
| b1.addEventListener(MouseEvent.CLICK, returnResult, false, 1); |
| b1.addEventListener(MouseEvent.CLICK, saveInputData, false, 2); |
| b1.addEventListener(MouseEvent.CLICK, verifyInputData, false, 3); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| <s:TextArea id="ta1" height="200" width="300"/> |
| |
| </s:Application></pre> |
| |
| <p>You can set the event priority to any valid integer, positive |
| or negative. The default value is 0. If multiple listeners have |
| the same priority, Flex typically calls them in the order in which |
| they were registered, although the order is not guaranteed.</p> |
| |
| <p>If you want to change the priority of an event listener once |
| the event listener has already been defined, you must remove the |
| listener by calling the <samp class="codeph">removeEventListener()</samp> method. |
| You add the event again with the new priority.</p> |
| |
| <p>The <em>priority</em> parameter of the <samp class="codeph">addEventListener()</samp> method |
| is not an official part of the DOM Level 3 events model. ActionScript |
| 3.0 provides it so that programmers can be more flexible when organizing |
| their event listeners. </p> |
| |
| <p>If your listeners rely on a specific order of execution, you |
| can call one listener function from within another, or dispatch |
| a new event from within the first event listener. For more information |
| on manually dispatching events, see <a href="flx_events_ev.html#WS2db454920e96a9e51e63e3d11c0bf69084-7ce1_verapache">Manually dispatching |
| events</a>.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf69084-7ce0_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf69084-7ce0_verapache"><!-- --></a> |
| <h2 class="topictitle2">Using event subclasses</h2> |
| |
| |
| <div> |
| <p>Depending |
| on the event type, the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/Event.html" target="_blank">Event</a> object |
| can have a wide range of properties. These properties are based |
| on those defined in the W3C specification <a href="https://www.w3.org/TR/DOM-Level-3-Events/" target="_blank">http://www.w3.org/TR/DOM-Level-3-Events/</a>), |
| but Flex does not implement all of these.</p> |
| |
| <p>When you declare an Event object in a listener function, you |
| can declare it of type Event, or you can specify a subclass of the |
| Event object. In the following example, you specify the event object |
| as type <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/MouseEvent.html" target="_blank">MouseEvent</a>:</p> |
| |
| <pre class="codeblock"> public function performAction(e:MouseEvent):void { |
| ... |
| }</pre> |
| |
| <p>Most controls generate an object that is of a specific event |
| type; for example, a mouse click generates an object of type MouseEvent. |
| By specifying a more specific event type, you can access specific |
| properties without having to cast the Event object to something |
| else. In addition, some subclasses of the Event object have methods |
| that are unique to them. For example, the LogEvent has a <samp class="codeph">getLevelString()</samp> method, |
| which returns the log level as a String. The generic Event object |
| does not have this method.</p> |
| |
| <p>An event object that you define at run time can be a subclass |
| of the compile-time type. You can access the event-specific properties |
| inside an event listener even if you did not declare the specific |
| event type, as long as you cast the Event object to a specific type. |
| In the following example, the function defines the object type as |
| Event. However, inside the function, in order to access the <samp class="codeph">localX</samp> and <samp class="codeph">localY</samp> properties, |
| which are specific to the MouseEvent class, you must cast the Event |
| object to be of type MouseEvent.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/AccessEventSpecificProperties.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="addListeners()"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| |
| private function customLogEvent(e:Event):void { |
| var a:MouseEvent = MouseEvent(e); |
| Alert.show("Y: " + a.localY + "\n" + "X: " + a.localX); |
| } |
| |
| private function addListeners():void { |
| b1.addEventListener(MouseEvent.CLICK, customLogEvent); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| </s:Application></pre> |
| |
| <p>If you declare the Event object as a specific type, you are not |
| required to cast that object in the handler, as the following example |
| shows:</p> |
| |
| <pre class="codeblock"> private function customLogEvent(e:MouseEvent):void { ... }</pre> |
| |
| <p>In the previous example, you can also cast the Event object for |
| only the property access, using the syntax shown in the following |
| example:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/SinglePropertyAccess.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| initialize="addListeners()"> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.controls.Alert; |
| private function customLogEvent(e:Event):void { |
| Alert.show("Y: " + MouseEvent(e).localY + "\n" + "X: " + MouseEvent(e).localX); |
| } |
| |
| private function addListeners():void { |
| b1.addEventListener(MouseEvent.CLICK, customLogEvent); |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:Button id="b1" label="Click Me"/> |
| |
| </s:Application></pre> |
| |
| <p>This approach can use less memory and system resources, but it |
| is best to declare the event's type as specifically as possible.</p> |
| |
| <p>Each of the Event object's subclasses provides additional properties |
| and event types that are unique to that category of events. The |
| MouseEvent class defines several event types related to that input |
| device, including the <samp class="codeph">CLICK</samp>, <samp class="codeph">DOUBLE_CLICK</samp>, <samp class="codeph">MOUSE_DOWN</samp>, |
| and <samp class="codeph">MOUSE_UP</samp> event types. </p> |
| |
| <p>For a list of types for each Event subclass, see the subclass's |
| entry in <em> |
| <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/" target="_blank">ActionScript 3.0 Reference for the Adobe |
| Flash Platform</a> |
| </em>.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested1" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fdb_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fdb_verapache"><!-- --></a> |
| <h2 class="topictitle2">About keyboard events</h2> |
| |
| |
| <div> |
| <p>It |
| is common for applications to respond to a key or series of keys |
| and perform some action—for example, Control+q to quit the application. |
| While Flash Player supports all the basic functionality of key combinations |
| from the underlying operating system, it also lets you override |
| or trap any key or combination of keys to perform a custom action.</p> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fef_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fef_verapache"><!-- --></a> |
| <h3 class="topictitle3">Handling keyboard events</h3> |
| |
| |
| <div> |
| <p>In some cases, you want to trap keys globally, meaning |
| no matter where the user is in the application, their keystrokes |
| are recognized by the application and the action is performed. Flex |
| recognizes global keyboard events whether the user is hovering over |
| a button or the focus is inside a TextInput control. </p> |
| |
| <p>A common way to handle global key presses is to create a listener |
| for the <samp class="codeph">KeyboardEvent.KEY_DOWN</samp> or <samp class="codeph">KeyboardEvent.KEY_UP</samp> event |
| on the application. Listeners on the application container are triggered |
| every time a key is pressed, regardless of where the focus is (as |
| long as the focus is in the application on not in the browser controls |
| or outside of the browser). Inside the handler, you can examine |
| the key code or the character code using the <samp class="codeph">charCode</samp> and <samp class="codeph">keyCode</samp> properties |
| of the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/KeyboardEvent.html" target="_blank">KeyboardEvent</a> class, |
| as the following example shows:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/TrapAllKeys.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp();"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.core.FlexGlobals; |
| |
| private function initApp():void { |
| FlexGlobals.topLevelApplication.addEventListener(KeyboardEvent.KEY_UP, keyHandler); |
| } |
| |
| private function keyHandler(event:KeyboardEvent):void { |
| t1.text = event.keyCode + "/" + event.charCode; |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:TextInput id="myTextInput"/> |
| |
| <s:Label id="t1"/> |
| |
| </s:Application></pre> |
| |
| <p>To run this example, you must first set the focus to something |
| inside the application, such as the TextInput control, by clicking |
| on it.</p> |
| |
| <p>Because any class that extends UIComponent dispatches the <samp class="codeph">keyUp</samp> and <samp class="codeph">keyDown</samp> events, |
| you can also trap keys pressed when the focus is on an individual |
| component.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fed_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fed_verapache"><!-- --></a> |
| <h3 class="topictitle3">Understanding the keyCode and charCode |
| properties</h3> |
| |
| |
| <div> |
| <p>You |
| can access the <samp class="codeph">keyCode</samp> and <samp class="codeph">charCode</samp> properties |
| to determine what key was pressed and trigger other actions as a |
| result. The <samp class="codeph">keyCode</samp> property is a numeric value |
| that corresponds to the value of a key on the keyboard. The <samp class="codeph">charCode</samp> property |
| is the numeric value of that key in the current character set (the |
| default character set is UTF-8, which supports ASCII). The primary |
| difference between the key code and character values is that a key |
| code value represents a particular key on the keyboard (the 1 on |
| a keypad is different than the 1 in the top row, but the 1 on the |
| keyboard and the key that generates the ! are the same key), and |
| the character value represents a particular character (the <em>R</em> and <em>r</em> characters are |
| different).</p> |
| |
| <p>The mappings between keys and key codes are device and operating |
| system dependent. ASCII values, on the other hand, are available |
| in the ActionScript documentation.</p> |
| |
| <p>The following example shows the character and key code values |
| for the keys you press. When you run this example, you must be sure |
| to put the focus in the application before beginning.</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- charts/ShowCharAndKeyCodes.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="init()" |
| width="650"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| import flash.events.KeyboardEvent; |
| |
| private function init():void { |
| ti1.setFocus(); |
| this.addEventListener(KeyboardEvent.KEY_DOWN, trapKeys); |
| } |
| |
| private function trapKeys(e:KeyboardEvent):void { |
| ta1.text = String(e.toString()); |
| |
| l1.text = numToChar(e.charCode) + " (" + String(e.charCode) + ")"; |
| l2.text = numToChar(e.keyCode) + " (" + String(e.keyCode) + ")"; |
| } |
| |
| private function numToChar(num:int):String { |
| if (num > 47 && num < 58) { |
| var strNums:String = "0123456789"; |
| return strNums.charAt(num - 48); |
| } else if (num > 64 && num < 91) { |
| var strCaps:String = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; |
| return strCaps.charAt(num - 65); |
| } else if (num > 96 && num < 123) { |
| var strLow:String = "abcdefghijklmnopqrstuvwxyz"; |
| return strLow.charAt(num - 97); |
| } else { |
| return num.toString(); |
| } |
| } |
| ]]></fx:Script> |
| |
| <s:TextInput width="50%" id="ti1"/> |
| |
| <s:Panel id="mainPanel" width="100%" height="100%"> |
| <s:Form> |
| <s:FormItem label="Char (Code)"> |
| <s:Label id="l1"/> |
| </s:FormItem> |
| <s:FormItem label="Key (Code)"> |
| <s:Label id="l2"/> |
| </s:FormItem> |
| <s:FormItem label="Key Event"> |
| <s:TextArea id="ta1" width="500" height="200" editable="false"/> |
| </s:FormItem> |
| </s:Form> |
| </s:Panel> |
| |
| </s:Application></pre> |
| |
| <p>You can listen for specific keys or combinations of keys by using |
| a conditional operator in the KeyboardEvent handler. The following |
| example listens for the combination of the Shift key plus the q |
| key and prompts the user to close the browser window if they press |
| those keys at the same time:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/TrapQKey.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp();"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script> |
| <![CDATA[ |
| import mx.core.FlexGlobals; |
| |
| private function initApp():void { |
| FlexGlobals.topLevelApplication.addEventListener(KeyboardEvent.KEY_UP,keyHandler); |
| |
| // Set the focus somewhere inside the application. |
| ta1.setFocus(); |
| } |
| |
| //This function quits the application if the user presses Shift+Q. |
| private function keyHandler(event:KeyboardEvent):void { |
| var bShiftPressed:Boolean = event.shiftKey; |
| if (bShiftPressed) { |
| var curKeyCode:int = event.keyCode; |
| if (curKeyCode == 81) { // 81 is the keycode value for the Q key |
| |
| /* Quit the application by closing the browser using JavaScript. |
| This may not work in all browsers. */ |
| var url:URLRequest = new |
| URLRequest("javascript:window.close()"); |
| navigateToURL(url,"_self"); |
| } |
| } |
| } |
| ]]> |
| </fx:Script> |
| |
| <s:TextArea id="ta1" text="Focus here so that Shift+Q will quit the browser."/> |
| |
| </s:Application></pre> |
| |
| <p>Notice that this application must have focus when you run it |
| in a browser so that the application can capture keyboard events.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe8_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7fe8_verapache"><!-- --></a> |
| <h3 class="topictitle3">Understanding KeyboardEvent precedence</h3> |
| |
| |
| <div> |
| <p>If you define <samp class="codeph">keyUp</samp> or <samp class="codeph">keyDown</samp> event |
| listeners for both a control and its parent, you will notice that |
| the keyboard event is dispatched for each component because the |
| event bubbles. The only difference is that the <samp class="codeph">currentTarget</samp> property |
| of the KeyboardEvent object is changed.</p> |
| |
| <p>In the following example, the application, the <samp class="codeph">my_vgroup</samp> container, |
| and the <samp class="codeph">my_textinput</samp> control all dispatch <samp class="codeph">keyUp</samp> events |
| to the <samp class="codeph">keyHandler()</samp> event listener function:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/KeyboardEventPrecedence.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp();" |
| width="650"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| import mx.core.FlexGlobals; |
| |
| private function initApp():void { |
| FlexGlobals.topLevelApplication.addEventListener(KeyboardEvent.KEY_UP, keyHandler); |
| my_vgroup.addEventListener(KeyboardEvent.KEY_UP, keyHandler); |
| my_textinput.addEventListener(KeyboardEvent.KEY_UP, keyHandler); |
| |
| // Set the focus somewhere inside the application. |
| my_textinput.setFocus(); |
| } |
| |
| private function keyHandler(event:KeyboardEvent):void { |
| ta1.text += event.target + "(" + event.currentTarget + "): " + |
| event.keyCode + "/" + event.charCode + "\n"; |
| } |
| ]]></fx:Script> |
| |
| <s:VGroup id="my_vgroup"> |
| <s:TextInput id="my_textinput"/> |
| </s:VGroup> |
| |
| <s:TextArea id="ta1" height="300" width="550"/> |
| |
| </s:Application></pre> |
| |
| <p>When you examine the output, you will notice that the <samp class="codeph">target</samp> property |
| of the <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/KeyboardEvent.html" target="_blank">KeyboardEvent</a> object |
| stays the same because it refers to the original dispatcher of the |
| event (in this case, my_textinput). But the <samp class="codeph">currentTarget</samp> property changes |
| depending on what the current node is during the bubbling (in this case, |
| it changes from my_textinput to my_vgroup to the application itself).</p> |
| |
| <p>The order of calls to the event listener is determined by the |
| object hierarchy and not the order in which the <samp class="codeph">addEventListener()</samp> methods |
| were called. Child controls dispatch events before their parents. |
| In this example, for each key pressed, the TextInput control dispatches |
| the event first, the VGroup container next, and finally the application.</p> |
| |
| <p>When handling a key or key combination that the underlying operating |
| system or browser recognizes, the operating system or browser generally |
| processes the event first. For example, in Microsoft Internet Explorer, |
| pressing Control+w closes the browser window. If you trap that combination |
| in your application, Internet Explorer users never know it, because |
| the browser closes before the ActiveX Flash Player has a chance |
| to react to the event.</p> |
| |
| </div> |
| |
| </div> |
| |
| <div class="nested2" id="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff8_verapache"><a name="WS2db454920e96a9e51e63e3d11c0bf64a29-7ff8_verapache"><!-- --></a> |
| <h3 class="topictitle3">Handling keyboard-related mouse |
| events</h3> |
| |
| |
| <div> |
| <p>The <a href="https://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/events/MouseEvent.html" target="_blank">MouseEvent</a> class |
| and all MouseEvent subclasses (such as ChartItemEvent, DragEvent, |
| and LegendMouseEvent) have the following properties that you can use |
| to determine if a specific key was held down when the event occurred:</p> |
| |
| |
| <div class="tablenoborder"><table cellpadding="4" cellspacing="0" summary="" frame="border" border="1" rules="all"> |
| |
| |
| <thead align="left"> |
| <tr> |
| <th class="cellrowborder" valign="top" width="NaN%" id="d206409e2827"> |
| <p>Property</p> |
| |
| </th> |
| |
| <th class="cellrowborder" valign="top" width="NaN%" id="d206409e2833"> |
| <p>Description</p> |
| |
| </th> |
| |
| </tr> |
| |
| </thead> |
| |
| <tbody> |
| <tr> |
| <td class="cellrowborder" valign="top" width="NaN%" headers="d206409e2827 "> |
| <p> |
| <samp class="codeph">altKey</samp> |
| </p> |
| |
| </td> |
| |
| <td class="cellrowborder" valign="top" width="NaN%" headers="d206409e2833 "> |
| <p>Is set to <samp class="codeph">true</samp> if the Alt |
| key was held down when the user pressed the mouse button; otherwise, <samp class="codeph">false</samp>.</p> |
| |
| </td> |
| |
| </tr> |
| |
| <tr> |
| <td class="cellrowborder" valign="top" width="NaN%" headers="d206409e2827 "> |
| <p> |
| <samp class="codeph">ctrlKey</samp> |
| </p> |
| |
| </td> |
| |
| <td class="cellrowborder" valign="top" width="NaN%" headers="d206409e2833 "> |
| <p>Is set to <samp class="codeph">true</samp> if the Control |
| key was held down when the user pressed mouse button; otherwise, <samp class="codeph">false</samp>.</p> |
| |
| </td> |
| |
| </tr> |
| |
| <tr> |
| <td class="cellrowborder" valign="top" width="NaN%" headers="d206409e2827 "> |
| <p> |
| <samp class="codeph">shiftKey</samp> |
| </p> |
| |
| </td> |
| |
| <td class="cellrowborder" valign="top" width="NaN%" headers="d206409e2833 "> |
| <p>Is set to <samp class="codeph">true</samp> if the Shift |
| key was held down when the user pressed mouse button; otherwise, <samp class="codeph">false</samp>.</p> |
| |
| </td> |
| |
| </tr> |
| |
| </tbody> |
| |
| </table> |
| </div> |
| |
| <p>The following example deletes Button controls, based on whether |
| the user holds down the Shift key while pressing the mouse button:</p> |
| |
| <pre class="codeblock"><?xml version="1.0"?> |
| <!-- events/DetectingShiftClicks.mxml --> |
| <s:Application |
| xmlns:fx="http://ns.adobe.com/mxml/2009" |
| xmlns:mx="library://ns.adobe.com/flex/mx" |
| xmlns:s="library://ns.adobe.com/flex/spark" |
| creationComplete="initApp();"> |
| |
| <s:layout> |
| <s:VerticalLayout/> |
| </s:layout> |
| |
| <fx:Script><![CDATA[ |
| import spark.components.Button; |
| |
| private function initApp():void { |
| var b1:Button = new Button(); |
| b1.label = "Button 1"; |
| |
| var b2:Button = new Button(); |
| b2.label = "Button 2"; |
| b1.addEventListener(MouseEvent.CLICK, removeButtons); |
| b2.addEventListener(MouseEvent.CLICK, removeButtons); |
| |
| vg1.addElement(b1); |
| vg1.addElement(b2); |
| } |
| |
| private function removeButtons(event:MouseEvent):void { |
| if (event.shiftKey) { |
| vg1.removeElement(Button(event.currentTarget)); |
| } else { |
| event.currentTarget.toolTip = "Shift+click to remove this button."; |
| } |
| } |
| ]]></fx:Script> |
| |
| <s:VGroup id="vg1"/> |
| |
| <s:Button id="resetButton" label="Reset" click="initApp();"/> |
| |
| </s:Application></pre> |
| |
| <p/> |
| |
| </div> |
| |
| </div> |
| |
| <div> |
| <p><strong>Navigation</strong></p> |
| <p><a href="index.html">Using Flex</a> » <a href="flx_p1_gettingstarted.html">Getting Started</a></p> |
| </div> |
| |
| <p>Adobe, Adobe AIR, Adobe Flash Platform and Adobe Flash Player are either registered trademarks or trademarks of Adobe Systems Incorporated in the United States and/or other countries and are used by permission from Adobe. No other license to the Adobe trademarks are granted.</p> |
| </div> |
| |
| |
| </body> |
| </html> |