"Re-raising" custom events in .NET (in this case, ASP.NET)

I am working on an ASP.NET page using VB.NET and I have this hierarchy:

Page A
- Manage web users 1
- Web User Management A
- web user control B
- Manage C Web Users

I need to raise an event from the web user control B that page A will receive (the event flow will be web user control B → web user control 1 → page A).

So far, my only approach has been this: 1) Add a custom event declaration for both Web User Control B and Web User Control 1 and just RaiseEvent twice until it reaches page A (this seems ugly and it doesn't me especially like it).

My other idea was to create a custom event class that would be created from some magic base class Event and create an instance of it in both Web User Control B and Web User Control 1, but this turned out to be fruitless because I cannot find any base event classes (perhaps b / c they are not any, since this is a keyword, not a class name).

Any help would be appreciated! Thanks and happy coding!

+3
source share
4 answers

You can use the BubbleEvent concept for this. BubbleEvent raises the management hierarchy until someone can handle it. GridView and Repeater controls do this with their Row / ItemCommand events.

You can implement it in WebUserControl1, turning it into a standard event for the page (for example, GridView):

Class UserControl1 ' Parent Protected Override Function OnBubbleEvent(sender as Object, e as EventArgs) as Boolean Dim c as CommandEventArgs = TryCast(e, CommandEventArgs) If c IsNot Nothing Then RaiseEvent ItemEvent(sender, c) Return True ' Cancel the bubbling, so it doesn't go up any further in the hierarchy End If Return False ' Couldn't handle, so let it bubble End Function Public Event ItemEvent as EventHandler(Of CommandEventArgs) End Class Class UserControlB ' Child Protected Sub OnClicked(e as EventArgs) ' Raise a direct event for any handlers attached directly RaiseEvent Clicked(Me, e) ' And raise a bubble event for parent control RaiseBubbleEvent(Me, New CommandEventArgs("Clicked", Nothing)) End Sub Protected Sub OnMoved(e as EventArgs) ' Raise a direct event for any handlers attached directly RaiseEvent Moved(Me, e) ' And raise a bubble event for parent control RaiseBubbleEvent(Me, New CommandEventArgs("Moved", Nothing)) End Sub End Class Class PageA Sub UserControl1_ItemEvent(sender as Object, e as CommandEventArgs) Handles UserControl1.ItemEvent Response.Write(sender.GetType().Name & " was " & e.CommandName) End Sub End Class 

Or do it right on the page. UserControlB (Child) is the same as above, and UserControl1 (Parent) does not need to do anything - by default OnBubbleEvent returns False, so the event bubbles up:

 Class PageA Protected Override Function OnBubbleEvent(sender as Object, e as EventArgs) as Boolean If sender Is UserControlB Then Dim c as CommandEventArgs = TryCast(e, CommandEventArgs) If c IsNot Nothing Then Response.Write(sender.GetType().Name & " was " & c.CommandName) Else Response.Write(sender.GetType().Name & " raised an event, with " & e.GetType().Name & " args) End If Return True ' Cancel the bubbling, so it doesn't go up any further in the hierarchy End If Return False ' Not handled End Function End Class 

If your initial event comes from a server control (e.g. Button.Click), then it will be encoded to raise the bubble event already - so UserControlB (Child) does not need to do anything to get this parent. You just need to call RaiseBubbleEvent for any of your custom events or if you somehow transform EventArg.

+4
source

The real question here is the actual action in Web UserControl B that should notify this, OR, is WebUserControl1 responsible for some processing before notifying the page.

If each step of the chain has a specific action, your method of raising two events is the right one. If this happens so that the event just needs to be notified to everyone, you will want to look at the various subscription methods for communication.

+1
source

Create the assembly (or namespace) referenced by everything. Create the interface using the necessary methods. Create a class that manages the objects that implemented the interface.

Does page A implement the Have Page interface? Registration with the manager class in step 3 Now Web UserControl B can raise this event by retrieving the page from the manager and calling a method on the interface that raises the event you need.

You avoid tightly linking the page with the webcontrol because you use the interface.

You will probably find that you will have several interfaces for different areas of your project. For example, in my CAM project, I have an interface for the settings user interface, form input interface, and cut user interface. On our website we have different categories of products that use different interfaces. (Software, machines, services, etc.).

+1
source

You can create an open method on Page A that is called from Web User Control B instead of raising an event throughout the control tree.

This would not be my first choice, as it will lead to a tight connection between these classes, but I hope it solves your problem.

Page example:

 Public Partial Class TestPage Inherits Page Public Sub PerformAction() 'Whatever needs to be done on Page A End Sub End Class 

User Management Example:

 Public Partial Class TestControl Inherits UserControl Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load 'This will call the Page, obviously this will only 'work when the control is on TestPage CType(Page, TestPage).PerformAction() End Sub End Class 
0
source

All Articles