El orden de ejecución de los manipuladores de un solo evento no pueden ser controlados a través del comportamiento básico de un built-in evento en sí. Los delegados de Multicast son "bolsas" de manipuladores, y simplemente los agarran uno a la vez. Tenga en cuenta que así es como la mayoría de los desarrolladores esperan que esto funcione, y puede ser peligroso permitir manipuladores de eventos dependientes del pedido. Los manejadores de eventos normalmente no deberían conocerse entre sí, porque si dependen de que se ejecuten antes o después de otro manejador, primero deben saber de la existencia del otro manejador (que viola el ocultamiento de información y varios otros principios de diseño), y segundo, si ese orden cambia, el comportamiento se romperá.
Si entiende todo esto y aún desea controlar el orden de ejecución de los controladores de un evento, lo siguiente lo acercará.
- Cree una colección ordenada de delegados del tipo de controlador de eventos llamado MyHandlers. Este será un sustituto de la implementación MulticastDelegate del evento real.
- Crea un método de controlador "maestro" que realmente se adjuntará al evento integrado, y se repetirá a través de MyHandlers y llamará a cada uno.
- Define algunos medios para agregar y eliminar controladores de la lista. Parte de esto se puede lograr con una "propiedad" de evento personalizado, pero eso solo definirá agregar y eliminar comportamientos, no insertar.
El código podría tener el siguiente aspecto:
private List<EventHandler> MyHandlers = new List<EventHandler>();
private void MasterClickHandler(object sender, EventArgs e)
{
foreach(var handler in MyHandlers)
handler(sender, e);
}
public event EventHandler MyControlButtonClick
{
add { MyHandlers.Add(value); }
remove { MyHandlers.Remove(value); }
}
public void InsertButtonClickHandler(EventHandler handler)
{
MyHandlers.Insert(handler,0); //calling this to add a handler puts the handler up front
}
...
myForm.MyControl.Click += MasterClickHandler;
en cuenta que ya no está adjuntando los controladores que no sean MasterClickHandler al acontecimiento real; no puedes tener tu pastel y comértelo también, anulando y manteniendo el comportamiento básico del evento.Tampoco hay un comportamiento de "inserción" incorporado en la "propiedad" del evento; tienes que definir un método que lo permita. Por último, nunca debe plantear el evento MyControlButtonClick directamente (aunque como su control es el único que puede hacerlo, esto se puede aplicar mediante la inspección del código).
Ahora, al hacer clic en el botón, el evento Click integrado del botón dispara MasterEventHandler, que ejecutará los delegados en MyHandlers en el mismo orden en que se adjuntaron a MyControlButtonClick (con el que se insertó se ejecutó primero, en el reverso orden en que fueron insertados). Si coloca este código en un control de usuario personalizado con el Botón, incluso podría nombrar el evento personalizado en su control Haga clic en, y el control se vería y funcionaría de manera similar al Botón que contiene, excepto que tendría el control adicional sobre la inserción manejadores. La belleza de todo esto es que nada acerca de este código obliga a los consumidores a trabajar con él como algo más que un simple evento de vanilla.
+1 por el buen consejo. –