Impostazione degli eventi indirizzati come gestiti e gestione delle classiMarking Routed Events as Handled, and Class Handling

I gestori per un evento indirizzato possono contrassegnare l'evento come gestito all'interno dei dati dell'evento.Handlers for a routed event can mark the event handled within the event data. La gestione dell'evento abbrevia efficacemente la route.Handling the event will effectively shorten the route. La gestione delle classi è un concetto di programmazione supportato dagli eventi indirizzati.Class handling is a programming concept that is supported by routed events. Un gestore classi ha l'opportunità di gestire un evento indirizzato specifico a livello di classe con un gestore richiamato prima di qualsiasi gestore istanze in qualsiasi istanza di classe.A class handler has the opportunity to handle a particular routed event at a class level with a handler that is invoked before any instance handler on any instance of the class.

PrerequisitesPrerequisites

Questo argomento elabora i concetti introdotti in Cenni preliminari sugli eventi indirizzati.This topic elaborates on concepts introduced in the Routed Events Overview.

Quando contrassegnare eventi come gestitiWhen to Mark Events as Handled

Quando si imposta il Handled valore true della proprietà su nei dati dell'evento per un evento indirizzato, questo viene definito "contrassegno dell'evento gestito".When you set the value of the Handled property to true in the event data for a routed event, this is referred to as "marking the event handled". Non esiste una regola assoluta riguardo a quando contrassegnare gli eventi indirizzati come gestiti, né per un autore di applicazioni né per un autore di controlli che risponde a eventi indirizzati esistenti o implementa nuovi eventi indirizzati.There is no absolute rule for when you should mark routed events as handled, either as an application author, or as a control author who responds to existing routed events or implements new routed events. Per la maggior parte, il concetto di "gestito" come riportato nei dati dell'evento indirizzato deve essere utilizzato come protocollo WPFWPF limitato per le risposte dell'applicazione ai vari eventi indirizzati esposti nelle API e per tutti gli eventi indirizzati personalizzati.For the most part, the concept of "handled" as carried in the routed event's event data should be used as a limited protocol for your own application's responses to the various routed events exposed in WPFWPF APIs as well as for any custom routed events. Un altro modo di considerare il concetto di "gestito" è che in genere è necessario contrassegnare un evento indirizzato come gestito se il codice ha risposto all'evento indirizzato in modo significativo e relativamente completo.Another way to consider the "handled" issue is that you should generally mark a routed event handled if your code responded to the routed event in a significant and relatively complete way. In genere, deve essere presente una sola risposta significativa che richiede implementazioni del gestore separate per qualsiasi singola occorrenza di un evento indirizzato.Typically, there should not be more than one significant response that requires separate handler implementations for any single routed event occurrence. Se sono necessarie più risposte, il codice richiesto deve essere implementato tramite logica dell'applicazione concatenata a un singolo gestore, anziché usare il sistema degli eventi indirizzati per l'inoltro.If more responses are needed, then the necessary code should be implemented through application logic that is chained within a single handler rather than by using the routed event system for forwarding. Anche il concetto di "significativo" è soggettivo e dipende dall'applicazione o dal codice.The concept of what is "significant" is also subjective, and depends on your application or code. Come indicazione generale, ecco alcuni esempi di "risposta significativa": impostazione dello stato attivo, modifica dello stato pubblico, impostazione delle proprietà che influiscono sulla rappresentazione visiva e generazione di altri nuovi eventi.As general guidance, some "significant response" examples include: setting focus, modifying public state, setting properties that affect the visual representation, and raising other new events. Ecco inoltre alcuni esempi di risposte non significative: modifica dello stato privato (senza alcun impatto visivo o sulla rappresentazione programmatica), registrazione di eventi o esame degli argomenti di un evento e scelta di non rispondervi.Examples of nonsignificant responses include: modifying private state (with no visual impact, or programmatic representation), logging of events, or looking at arguments of an event and choosing not to respond to it.

Il comportamento del sistema di eventi indirizzati rafforza questo modello di "risposta significativa" per XAMLXAML l'utilizzo AddHandler dello stato gestito di un evento indirizzato, perché i gestori aggiunti o la firma comune di non vengono richiamati in risposta a un evento indirizzato in cui i dati dell'evento sono già contrassegnati come gestiti.The routed event system behavior reinforces this "significant response" model for using handled state of a routed event, because handlers added in XAMLXAML or the common signature of AddHandler are not invoked in response to a routed event where the event data is already marked handled. È necessario eseguire l'operazione aggiuntiva handledEventsToo di aggiuntaAddHandler(RoutedEvent, Delegate, Boolean)di un gestore con la versione del parametro ( ) per gestire gli eventi indirizzati contrassegnati come gestiti dai partecipanti precedenti nella route dell'evento.You must go through the extra effort of adding a handler with the handledEventsToo parameter version (AddHandler(RoutedEvent, Delegate, Boolean)) in order to handle routed events that are marked handled by earlier participants in the event route.

In alcuni casi, i controlli stessi contrassegnano determinati eventi indirizzati come gestiti.In some circumstances, controls themselves mark certain routed events as handled. Un evento indirizzato gestito rappresenta una decisione da parte degli autori di controlli WPFWPF in base alla quale le azioni del controllo in risposta all'evento indirizzato sono significative o complete come parte dell'implementazione del controllo e che l'evento non richiede gestione aggiuntiva.A handled routed event represents a decision by WPFWPF control authors that the control's actions in response to the routed event are significant or complete as part of the control implementation, and the event needs no further handling. Questo avviene in genere aggiungendo un gestore classi per un evento oppure eseguendo l'override di uno dei metodi virtuali del gestore classi presenti in una classe base.Usually this is done by adding a class handler for an event, or by overriding one of the class handler virtuals that exist on a base class. Se necessario, è comunque possibile trovare soluzioni alternative per questa gestione degli eventi. Vedere Soluzioni alternative all'eliminazione di eventi da parte dei controlli più avanti in questo argomento.You can still work around this event handling if necessary; see Working Around Event Suppression by Controls later in this topic.

Eventi "Preview" (Tunneling) e eventi di bubbling e gestione degli eventi"Preview" (Tunneling) Events vs. Bubbling Events, and Event Handling

Gli eventi indirizzati di anteprima sono eventi che seguono una route di tunneling attraverso l'albero degli elementi.Preview routed events are events that follow a tunneling route through the element tree. Il termine "anteprima" usato nella convenzione di denominazione è indicativo del principio generale per gli eventi di input in base al quale gli eventi indirizzati (di tunneling) di anteprima vengono generati prima dell'evento indirizzato di bubbling equivalente.The "Preview" expressed in the naming convention is indicative of the general principle for input events that preview (tunneling) routed events are raised prior to the equivalent bubbling routed event. Inoltre, gli eventi indirizzati di input dotati di una coppia di tunneling e bubbling hanno una logica di gestione distinta.Also, input routed events that have a tunneling and bubbling pair have a distinct handling logic. Se l'evento indirizzato di tunneling/anteprima viene contrassegnato come gestito da un listener di eventi, l'evento indirizzato di bubbling verrà contrassegnato come gestito anche prima che qualsiasi listener dell'evento indirizzato di bubbling lo riceva.If the tunneling/preview routed event is marked as handled by an event listener, then the bubbling routed event will be marked handled even before any listeners of the bubbling routed event receive it. Gli eventi indirizzati di tunneling e bubbling sono tecnicamente eventi separati, ma condividono intenzionalmente la stessa istanza dei dati degli eventi per permettere questo comportamento.The tunneling and bubbling routed events are technically separate events, but they deliberately share the same instance of event data to enable this behavior.

La connessione tra gli eventi indirizzati di tunneling e bubbling viene eseguita tramite l'implementazione interna del modo in cui ogni classe WPFWPF specifica genera i propri eventi indirizzati dichiarati e questo avviene per gli eventi indirizzati di input associati.The connection between the tunneling and bubbling routed events is accomplished by the internal implementation of how any given WPFWPF class raises its own declared routed events, and this is true of the paired input routed events. Tuttavia, se questa implementazione a livello di classe non esiste, non vi è alcuna connessione tra un evento indirizzato di tunneling e un evento indirizzato di bubbling che condividono lo schema di denominazione: senza questa implementazione, i due eventi indirizzati sono completamente separati e non vengono generati in sequenza né condividono i dati degli eventi.But unless this class-level implementation exists, there is no connection between a tunneling routed event and a bubbling routed event that share the naming scheme: without such implementation they would be two entirely separate routed events and would not be raised in sequence or share event data.

Per altre informazioni su come implementare coppie di eventi indirizzati di input di tunneling/bubbling in una classe personalizzata, vedere Creare un evento indirizzato personalizzato.For more information about how to implement tunnel/bubble input routed event pairs in a custom class, see Create a Custom Routed Event.

Gestori classi e gestori istanzeClass Handlers and Instance Handlers

Gli eventi indirizzati considerano due tipi diversi di listener per l'evento: listener di classi e listener di istanze.Routed events consider two different types of listeners to the event: class listeners and instance listeners. I listener di classi esistono EventManager perchéRegisterClassHandleri tipi hanno chiamato una particolare API , , nel costruttore statico o hanno eletto un metodo virtuale del gestore di classi da una classe base dell'elemento.Class listeners exist because types have called a particular EventManager API ,RegisterClassHandler, in their static constructor, or have overridden a class handler virtual method from an element base class. I listener di istanze sono istanze/elementi di classe particolari in cui uno AddHandlero più gestori sono stati associati per l'evento indirizzato da una chiamata a .Instance listeners are particular class instances/elements where one or more handlers have been attached for that routed event by a call to AddHandler. Gli WPFWPF eventi indirizzati AddHandler esistenti effettuano chiamate come parte del{} wrapper{} di eventi CLR (Common Language Runtime) aggiungere e rimuovere implementazioni dell'evento, che è anche il modo in cui è abilitato il semplice XAMLXAML meccanismo di associazione dei gestori eventi tramite una sintassi degli attributi.Existing WPFWPF routed events make calls to AddHandler as part of the common language runtime (CLR) event wrapper add{} and remove{} implementations of the event, which is also how the simple XAMLXAML mechanism of attaching event handlers via an attribute syntax is enabled. Pertanto, XAMLXAML anche l'utilizzo semplice AddHandler equivale in ultima analisi a una chiamata.Therefore even the simple XAMLXAML usage ultimately equates to an AddHandler call.

Gli elementi all'interno dell'albero visuale vengono controllati per individuare le eventuali implementazioni di gestori registrati.Elements within the visual tree are checked for registered handler implementations. I gestori vengono potenzialmente richiamati lungo la route, nell'ordine ereditato nel tipo della strategia di routing per l'evento indirizzato specifico.Handlers are potentially invoked throughout the route, in the order that is inherent in the type of the routing strategy for that routed event. Ad esempio, gli eventi indirizzati di bubbling richiameranno prima di tutto i gestori collegati allo stesso elemento che ha generato l'evento indirizzato.For instance, bubbling routed events will first invoke those handlers that are attached to the same element that raised the routed event. L'evento indirizzato viene propagato al successivo elemento padre e così via fino a raggiungere l'elemento radice dell'applicazione.Then the routed event "bubbles" to the next parent element and so on until the application root element is reached.

Dal punto di vista dell'elemento radice in una route di bubbling, se la gestione delle classi o qualsiasi elemento più vicino all'origine dell'evento indirizzato richiama gestori che contrassegnano gli argomenti dell'evento come gestiti, i gestori negli elementi radice non vengono richiamati e la route dell'evento viene abbreviata in modo efficace prima di raggiungere l'elemento radice.From the perspective of the root element in a bubbling route, if class handling or any element closer to the source of the routed event invoke handlers that mark the event arguments as being handled, then handlers on the root elements are not invoked, and the event route is effectively shortened before reaching that root element. Tuttavia, la route non viene completamente interrotta, perché è possibile aggiungere gestori con una speciale condizione in base alla quale devono comunque essere richiamati, anche se un gestore classi o un gestore istanze ha contrassegnato l'evento indirizzato come gestito.However, the route is not completely halted, because handlers can be added using a special conditional that they should still be invoked, even if a class handler or instance handler has marked the routed event as handled. Questo comportamento viene descritto in Aggiunta di gestori istanze generati anche se gli eventi sono contrassegnati come gestiti più avanti in questo argomento.This is explained in Adding Instance Handlers That Are Raised Even When Events Are Marked Handled, later in this topic.

A un livello più profondo rispetto a quello della route degli eventi esistono potenzialmente anche più gestori classi che agiscono su qualsiasi istanza specifica di una classe.At a deeper level than the event route, there are also potentially multiple class handlers acting on any given instance of a class. Questo avviene perché il modello di gestione delle classi per eventi indirizzati permette a tutte le possibili classi in una gerarchia di classi di registrare ciascuna il proprio gestore classi per ogni evento indirizzato.This is because the class handling model for routed events enables all possible classes in a class hierarchy to each register its own class handler for each routed event. Ogni gestore classi viene aggiunto a un archivio interno e quando viene creata la route degli eventi per un'applicazione, i gestori classi vengono tutti aggiunti alla route.Each class handler is added to an internal store, and when the event route for an application is constructed, the class handlers are all added to the event route. I gestori classi vengono aggiunti alla route in modo che venga richiamato per primo il gestore della classe più derivata, richiamando quindi i gestori classi da ogni classe base successiva.Class handlers are added to the route such that the most-derived class handler is invoked first, and class handlers from each successive base class are invoked next. In genere i gestori classi non sono registrati in modo da rispondere anche a eventi indirizzati già contrassegnati come gestiti.Generally, class handlers are not registered such that they also respond to routed events that were already marked handled. Di conseguenza, questo meccanismo di gestione delle classi permette di scegliere tra due opzioni:Therefore, this class handling mechanism enables one of two choices:

  • Le classi derivate possono completare la gestione delle classi ereditata dalla classe base aggiungendo un gestore che non contrassegna l'evento indirizzato come gestito, perché il gestore della classe base verrà richiamato in un momento successivo al gestore delle classi derivate.Derived classes can supplement the class handling that is inherited from the base class by adding a handler that does not mark the routed event handled, because the base class handler will be invoked sometime after the derived class handler.

  • Le classi derivate possono sostituire la gestione delle classi dalla classe base tramite l'aggiunta di un gestore classi che contrassegna l'evento indirizzato come gestito.Derived classes can replace the class handling from the base class by adding a class handler that marks the routed event handled. È necessario usare questo approccio con cautela, perché potrebbe modificare la progettazione dei controlli di base desiderata, ad esempio in aree come l'aspetto visivo, la logica di stato, la gestione degli input e la gestione dei comandi.You should be cautious with this approach, because it will potentially change the intended base control design in areas such as visual appearance, state logic, input handling, and command handling.

Gestione delle classi degli eventi indirizzati tramite classi di base dei controlliClass Handling of Routed Events by Control Base Classes

Nel nodo di ogni elemento specifico in una route di eventi i listener di classi possono rispondere all'evento indirizzato prima di qualsiasi listener di istanze per l'elemento.On each given element node in an event route, class listeners have the opportunity to respond to the routed event before any instance listener on the element can. Per questo motivo, i gestori classi vengono usati talvolta per eliminare gli eventi indirizzati che l'implementazione di una determinata classe di controlli non desidera propagare ulteriormente oppure per fornire una gestione speciale dell'evento indirizzato che è una caratteristica della classe.For this reason, class handlers are sometimes used to suppress routed events that a particular control class implementation does not wish to propagate further, or to provide special handling of that routed event that is a feature of the class. Ad esempio, una classe potrebbe generare il proprio evento specifico della classe che contiene più specifiche sul significato di una certa condizione di input utente nel contesto di una determinata classe.For instance, a class might raise its own class-specific event that contains more specifics about what some user input condition means in the context of that particular class. L'implementazione della classe potrebbe quindi contrassegnare come gestito l'evento indirizzato più generale.The class implementation might then mark the more general routed event as handled. I gestori di classi vengono in genere aggiunti in modo che non vengano richiamati per gli eventi RegisterClassHandler(Type, RoutedEvent, Delegate, Boolean) indirizzati in cui i dati degli eventi condivisi sono già stati contrassegnati come gestiti, ma per i casi atipici è presente anche una firma che registra i gestori di classi da richiamare anche quando gli eventi indirizzati sono contrassegnati come gestiti.Class handlers are typically added such that they are not invoked for routed events where shared event data was already marked handled, but for atypical cases there is also a RegisterClassHandler(Type, RoutedEvent, Delegate, Boolean) signature that registers class handlers to invoke even when routed events are marked handled.

Metodi virtuali dei gestori classiClass Handler Virtuals

Alcuni elementi, in particolare UIElementgli elementi di base, ad esempio*, espongono metodi virtuali vuoti "On-Event" e "OnPreview Event" che corrispondono al relativo elenco di eventi indirizzati pubblici.Some elements, particularly the base elements such as UIElement, expose empty "On*Event" and "OnPreview*Event" virtual methods that correspond to their list of public routed events. È possibile eseguire l'override di questi metodi virtuali per implementare un gestore classi per l'evento indirizzato.These virtual methods can be overridden to implement a class handler for that routed event. Le classi degli elementi di base registrano questi metodi RegisterClassHandler(Type, RoutedEvent, Delegate, Boolean) virtuali come gestore di classi per ogni evento indirizzato di questo tipo utilizzando come descritto in precedenza.The base element classes register these virtual methods as their class handler for each such routed event using RegisterClassHandler(Type, RoutedEvent, Delegate, Boolean) as described earlier. I metodi virtuali On*Event semplificano notevolmente l'implementazione della gestione delle classi per gli eventi indirizzati pertinenti, senza richiedere attività di inizializzazione speciali nei costruttori statici per ogni tipo.The On*Event virtual methods make it much simpler to implement class handling for the relevant routed events, without requiring special initialization in static constructors for each type. Ad esempio, è possibile aggiungere DragEnter la UIElement gestione della classe OnDragEnter per l'evento in qualsiasi classe derivata eseguendo l'override del metodo virtuale.For instance, you can add class handling for the DragEnter event in any UIElement derived class by overriding the OnDragEnter virtual method. All'interno dell'override è possibile gestire l'evento indirizzato, generare altri eventi, avviare una logica specifica della classe che può modificare le proprietà degli elementi nelle istanze o scegliere qualsiasi combinazione di queste azioni.Within the override, you could handle the routed event, raise other events, initiate class-specific logic that might change element properties on instances, or any combination of those actions. È in genere consigliabile chiamare l'implementazione base in questi override, anche se si contrassegna l'evento come gestito.You should generally call the base implementation in such overrides even if you mark the event handled. La chiamata dell'implementazione base è fortemente consigliata perché il metodo virtuale è incluso nella classe base.Calling the base implementation is strongly recommended because the virtual method is on the base class. Il modello virtuale protetto standard costituito dalla chiamata delle implementazioni base da ogni metodo virtuale essenzialmente sostituisce ed eguaglia un meccanismo simile che è nativo per la gestione delle classi degli eventi indirizzati, in cui i gestori classi per tutte le classi in una gerarchia di classi vengono chiamati in qualsiasi istanza specifica, a partire dal gestore della classe più derivata e continuando fino al gestore della classe base.The standard protected virtual pattern of calling the base implementations from each virtual essentially replaces and parallels a similar mechanism that is native to routed event class handling, whereby class handlers for all classes in a class hierarchy are called on any given instance, starting with the most-derived class' handler and continuing to the base class handler. È necessario omettere la chiamata dell'implementazione base solo se la classe prevede un requisito intenzionale relativo alla modifica della logica di gestione delle classi base.You should only omit the base implementation call if your class has a deliberate requirement to change the base class handling logic. Se si chiamerà l'implementazione base prima o dopo l'override del codice dipende dalla natura dell'implementazione.Whether you call the base implementation before or after your overriding code will depend on the nature of your implementation.

Gestione delle classi degli eventi di inputInput Event Class Handling

I metodi virtuali dei gestori classi vengono tutti registrati in modo da essere richiamati solo in presenza di dati degli eventi condivisi che non sono già stati contrassegnati come gestiti.The class handler virtual methods are all registered such that they are only invoked in cases where any shared event data are not already marked handled. Inoltre, solo per gli eventi di input, le versioni di tunneling e bubbling vengono normalmente generate in sequenza e condividono i dati degli eventi.Also, for the input events uniquely, the tunneling and bubbling versions typically are raised in sequence and share event data. Di conseguenza, per una specifica coppia di gestori classi di eventi di input in cui uno corrisponde alla versione di tunneling e l'altro alla versione di bubbling, si potrebbe non voler contrassegnare immediatamente l'evento come gestito.This entails that for a given pair of class handlers of input events where one is the tunneling version and the other is the bubbling version, you may not want to mark the event handled immediately. Se si implementa il metodo virtuale della gestione delle classi di tunneling per contrassegnare l'evento come gestito, si impedirà al gestore classi di bubbling di essere richiamato, oltre a impedire la chiamata dei gestori istanze normalmente registrati per l'evento di tunneling o di bubbling.If you implement the tunneling class handling virtual method to mark the event handled, that will prevent the bubbling class handler from being invoked (as well as preventing any normally registered instance handlers for either the tunneling or bubbling event from being invoked).

Quando la gestione delle classi in un nodo è completa, vengono presi in considerazione i listener di istanze.Once class handling on a node is complete, the instance listeners are considered.

Aggiunta di gestori istanze generati anche se gli eventi sono contrassegnati come gestitiAdding Instance Handlers That Are Raised Even When Events Are Marked Handled

Il AddHandler metodo fornisce un particolare overload che consente di aggiungere gestori che verranno richiamati dal sistema di eventi ogni volta che un evento raggiunge l'elemento di gestione nella route, anche se un altro gestore ha già modificato i dati dell'evento per contrassegnare l'evento come gestito.The AddHandler method supplies a particular overload that allows you to add handlers that will be invoked by the event system whenever an event reaches the handling element in the route, even if some other handler has already adjusted the event data to mark that event as handled. Questo non è il comportamento più comune.This is not typically done. In genere, i gestori possono essere scritti in modo da modificare tutte le aree del codice dell'applicazione che potrebbero essere influenzate da un evento, indipendentemente dal punto in cui questo è stato gestito nell'albero degli elementi, anche nei casi in cui si desiderano più risultati finali.Generally, handlers can be written to adjust all areas of application code that might be influenced by an event, regardless of where it was handled in an element tree, even if multiple end results are desired. Inoltre, in genere, un solo elemento deve rispondere all'evento e la logica dell'applicazione appropriata è già stata applicata.Also, typically there is really only one element that needs to respond to that event, and the appropriate application logic had already happened. Tuttavia, è disponibile l'overload handledEventsToo per i casi eccezionali in cui un altro elemento in un albero di elementi o in una composizione di controlli ha già contrassegnato un evento come gestito, ma altri elementi in posizione superiore o inferiore nell'albero degli elementi (a seconda della route) vogliono comunque che i rispettivi gestori vengano richiamati.But the handledEventsToo overload is available for the exceptional cases where some other element in an element tree or control compositing has already marked an event as handled, but other elements either higher or lower in the element tree (depending on route) still wish to have their own handlers invoked.

Quando contrassegnare eventi gestiti come non gestitiWhen to Mark Handled Events as Unhandled

In genere, gli eventi indirizzati contrassegnati come gestiti non devono essere contrassegnati come non gestiti (Handled impostati su false) anche dai gestori che agiscono su handledEventsToo.Generally, routed events that are marked handled should not be marked unhandled (Handled set back to false) even by handlers that act on handledEventsToo. Tuttavia, alcuni eventi di input hanno rappresentazioni di eventi di alto livello e di livello inferiore che possono sovrapporsi quando l'evento di alto livello viene visualizzato in una posizione nell'albero e quello di basso livello viene visualizzato in un'altra posizione.However, some input events have high-level and lower-level event representations that can overlap when the high-level event is seen at one position in the tree and the low-level event at another position. Si consideri, ad esempio, il caso in cui un TextInput elemento figlio è in ascolto di un KeyDownevento chiave di alto livello, ad esempio mentre un elemento padre è in ascolto di un evento di basso livello, ad esempio .For instance, consider the case where a child element listens to a high-level key event such as TextInput while a parent element listens to a low-level event such as KeyDown. Se l'elemento padre gestisce l'evento di basso livello, l'evento di livello superiore può essere eliminato anche nell'elemento figlio che dovrebbe avere la prima opportunità di gestire l'evento.If the parent element handles the low-level event, the higher-level event can be suppressed even in the child element that intuitively should have first opportunity to handle the event.

In queste situazioni può essere necessario aggiungere gestori sia agli elementi padre sia agli elementi figlio per l'evento di basso livello.In these situations it may be necessary to add handlers to both parent elements and child elements for the low-level event. L'implementazione del gestore dell'elemento figlio può contrassegnare l'evento di basso livello come gestito, ma l'implementazione del gestore dell'elemento padre lo imposterebbe di nuovo come non gestito per permettere ad altri elementi di livello superiore nell'albero (nonché all'evento di alto livello) di rispondere.The child element handler implementation can mark the low-level event as handled, but the parent element handler implementation would set it unhandled again so that further elements up the tree (as well as the high-level event) can have the opportunity to respond. Questa situazione dovrebbe essere piuttosto rara.This situation is should be fairly rare.

Eliminazione intenzionale di eventi di input per la composizione dei controlliDeliberately Suppressing Input Events for Control Compositing

Lo scenario principale in cui viene usata la gestione delle classi per eventi indirizzati riguarda gli eventi di input e i controlli compositi.The main scenario where class handling of routed events is used is for input events and composited controls. Un controllo composito è per definizione composto da più controlli pratici o classi base di controlli.A composited control is by definition composed of multiple practical controls or control base classes. Spesso l'autore del controllo desidera comporre in modo uniforme tutti i possibili eventi di input che possono essere generati da ognuno dei sottocomponenti, per segnalare l'intero controllo come singola origine evento.Often the author of the control wishes to amalgamate all of the possible input events that each of the subcomponents might raise, in order to report the entire control as the singular event source. In alcuni casi, l'autore del controllo potrebbe desiderare di eliminare interamente gli eventi dai componenti oppure sostituire un evento definito da un componente che contiene più informazioni o implica un comportamento più specifico.In some cases the control author might wish to suppress the events from components entirely, or substitute a component-defined event that carries more information or implies a more specific behavior. L'esempio canonico che è immediatamente visibile Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF) Button a qualsiasi autore di componenti è come un gestisce Click qualsiasi evento del mouse che alla fine si risolverà nell'evento intuitivo che tutti i pulsanti hanno: un evento.The canonical example that is immediately visible to any component author is how a Windows Presentation Foundation (WPF)Windows Presentation Foundation (WPF) Button handles any mouse event that will eventually resolve to the intuitive event that all buttons have: a Click event.

La Button classeButtonBasebase ( Control ) deriva da FrameworkElement quale UIElementa sua volta deriva da e , e UIElement gran parte dell'infrastruttura di eventi necessaria per l'elaborazione dell'input di controllo è disponibile a livello.The Button base class (ButtonBase) derives from Control which in turn derives from FrameworkElement and UIElement, and much of the event infrastructure needed for control input processing is available at the UIElement level. In particolare, UIElement elabora Mouse eventi generali che gestiscono l'hit testing per il cursore del mouse all'interno dei limiti e fornisce eventi distinti per le azioni più comuni dei pulsanti, ad MouseLeftButtonDownesempio .In particular, UIElement processes general Mouse events that handle hit testing for the mouse cursor within its bounds, and provides distinct events for the most common button actions, such as MouseLeftButtonDown. UIElementfornisce inoltre un OnMouseLeftButtonDown virtuale vuoto come MouseLeftButtonDowngestore ButtonBase di classi preregistrato per e ne esegue l'override.UIElement also provides an empty virtual OnMouseLeftButtonDown as the preregistered class handler for MouseLeftButtonDown, and ButtonBase overrides it. Analogamente, ButtonBase utilizza i MouseLeftButtonUpgestori di classi per .Similarly, ButtonBase uses class handlers for MouseLeftButtonUp. Negli override, a cui vengono passati i dati RoutedEventArgs dell'evento, Handled le trueimplementazioni contrassegnano tale istanza come gestita impostando su , e gli stessi dati dell'evento è ciò che continua lungo il resto della route ad altri gestori di classi e anche ai gestori di istanze o ai gestori di eventi.In the overrides, which are passed the event data, the implementations mark that RoutedEventArgs instance as handled by setting Handled to true, and that same event data is what continues along the remainder of the route to other class handlers and also to instance handlers or event setters. Inoltre, OnMouseLeftButtonUp la sostituzione genererà l'evento. ClickAlso, the OnMouseLeftButtonUp override will next raise the Click event. Il risultato finale per la MouseLeftButtonDown maggior MouseLeftButtonUp parte dei listener sarà Clickche gli eventi e "scompaiono" e vengono sostituiti da , un evento che ha più significato perché è noto che questo evento ha avuto origine da un pulsante vero e non da qualche pezzo composito del pulsante o da un altro elemento interamente.The end result for most listeners will be that the MouseLeftButtonDown and MouseLeftButtonUp events "disappear" and are replaced instead by Click, an event that holds more meaning because it is known that this event originated from a true button and not some composite piece of the button or from some other element entirely.

Soluzioni alternative all'eliminazione di eventi da parte dei controlliWorking Around Event Suppression by Controls

A volte questo comportamento di eliminazione di eventi all'interno di singoli controlli può interferire con alcune intenzioni più generali della logica di gestione degli eventi per l'applicazione.Sometimes this event suppression behavior within individual controls can interfere with some more general intentions of event handling logic for your application. Ad esempio, se per qualche motivo MouseLeftButtonDown l'applicazione dispone di un gestore che si trova MouseLeftButtonDown all'elemento radice dell'applicazione, si noterà che qualsiasi clic del mouse su un pulsante non richiamerebbe o MouseLeftButtonUp gestori a livello di radice.For instance, if for some reason your application had a handler for MouseLeftButtonDown located at the application root element, you would notice that any mouse click on a button would not invoke MouseLeftButtonDown or MouseLeftButtonUp handlers at the root level. L'evento stesso è stato effettivamente propagato. Come già detto, le route degli eventi non vengono davvero completate, ma il sistema degli eventi indirizzati ne modifica il comportamento di chiamata del gestore dopo che gli eventi sono stati contrassegnati come gestiti.The event itself actually did bubble up (again, event routes are not truly ended, but the routed event system changes their handler invocation behavior after being marked handled). Quando l'evento indirizzato ha ButtonBase raggiunto MouseLeftButtonDown il pulsante, la gestione Click della classe ha contrassegnato l'oggetto gestito perché desiderava sostituire l'evento con più significato.When the routed event reached the button, the ButtonBase class handling marked the MouseLeftButtonDown handled because it wished to substitute the Click event with more meaning. Pertanto, MouseLeftButtonDown qualsiasi gestore standard più in alto nella route non verrà richiamato.Therefore, any standard MouseLeftButtonDown handler further up the route would not be invoked. Esistono due tecniche che è possibile usare per garantire che i gestori vengano richiamati in questo caso.There are two techniques you can use to ensure that your handlers would be invoked in this circumstance.

La prima tecnica consiste nell'aggiungere handledEventsToo deliberatamente il gestore utilizzando la firma di AddHandler(RoutedEvent, Delegate, Boolean).The first technique is to deliberately add the handler using the handledEventsToo signature of AddHandler(RoutedEvent, Delegate, Boolean). Una limitazione di questo approccio è che la tecnica di collegamento di un gestore eventi è possibile solo dal codice, non dal markup.A limitation of this approach is that this technique for attaching an event handler is only possible from code, not from markup. La semplice sintassi per specificare il nome del gestore eventi come valore di attributo dell'evento tramite Extensible Application Markup Language (XAML)Extensible Application Markup Language (XAML) non permette questo comportamento.The simple syntax of specifying the event handler name as an event attribute value via Extensible Application Markup Language (XAML)Extensible Application Markup Language (XAML) does not enable that behavior.

La seconda tecnica può essere usata solo per gli eventi di input, le cui versioni di tunneling e bubbling dell'evento indirizzato sono associate.The second technique works only for input events, where the tunneling and bubbling versions of the routed event are paired. Per questi eventi indirizzati, è invece possibile aggiungere gestori all'evento indirizzato di anteprima/tunneling equivalente.For these routed events, you can add handlers to the preview/tunneling equivalent routed event instead. Poiché l'evento indirizzato percorre tramite tunneling la route a partire dalla radice, il codice di gestione delle classi del pulsante non lo intercetta, presumendo che il gestore di anteprima sia stato collegato a livello di un elemento predecessore nell'albero degli elementi dell'applicazione.That routed event will tunnel through the route starting from the root, so the button class handling code would not intercept it, presuming that you attached the Preview handler at some ancestor element level in the application's element tree. Se si usa questo approccio, contrassegnare con cautela qualsiasi evento di anteprima come gestito.If you use this approach, be cautious about marking any Preview event handled. Per l'esempio PreviewMouseLeftButtonDown fornito con la gestione dell'elemento radice, se l'evento è stato contrassegnato come Handled nell'implementazione del gestore, l'evento Click vermente eliminato sarebbe.For the example given with PreviewMouseLeftButtonDown being handled at the root element, if you marked the event as Handled in the handler implementation, you would actually suppress the Click event. Questo non è un comportamento consigliato.That is typically not desirable behavior.

Vedere ancheSee also