How to track when any child control gains or loses focus in WinForms?

I have a custom Windows Forms control that acts like a panel in that it can contain any number of children. The number and type of child controls are determined at runtime, so I need to work generically without knowing the exact child controls that may or may not be present.

I want to change the background color of my panel depending on whether the panel has focus. So if a child of a panel (or a child of a child of a panel, etc.) takes focus, I want to know this, so I can update the background color for the custom panel. When focus shifts to something that is not in the descendant hierarchy, I also need to know, so I can revert to the original background color.

Control.ContainsFocus is great for telling me if a panel has focus in a child hierarchy, but I need to know when there is a change. At this point, I can only think of the following bad mechanism.

I am connecting to GotFocus / LostFocus for every child and every child of every child, etc. I also have to hook up ControlAdded / ControlRemoved so that I keep in sync with a possible changing child hierarchy. As you can see, this can lead to ALOT event interceptors, and I suspect there should be a simpler approach. Any ideas?

+1


a source to share


2 answers


I am afraid this is the only option. Winforms sometimes has some annoying api holes. I haven't tested, but it wouldn't surprise me if ContainsFocus is just a recursive traversal of the container control's control tree to see if any control has focus.



Having a large number of event handlers is not a big problem, which causes a lot of events that change the elements of the user interface. You can get around this by subclassing the controls that can be added (but I'm not sure if you need to allow all controls, or just a subset) and pass the panel to a control added in such a way that the control itself calls the panel when it gains / loses focus. But it's also a lot of work and the observer-like pattern of having code in a panel is IMHO.

+1


a source


Seems to use the Enter and Leave answer . GotFocus will only be dispatched to the specific control that receives focus, while the Enter event will also be dispatched to the parent (and ancestor) controls that receive the GotFocus event.

from http://msdn.microsoft.com/en-us/library/system.windows.forms.control.leave.aspx



"Enter and Leave events are hierarchical and will cascade and down the parent chain until the appropriate control is reached. For example, suppose you have a Form with two GroupBox controls, and each GroupBox control has one TextBox control When the caret moves from one TextBox to another, the Leave event is for the TextBox and GroupBox, and the Enter event is for the other GroupBox and TextBox.

+6


a source







All Articles