I'm working in a windows application. using VB.NET 1.1
I have an empty form, and I want to generate my design in load session (not in form_load event! but in my form's constructor)
So I know I must generate my components in constructor, but I don't know how to generate button events. I mean I haven't any button in design mode, and these are generating in run-time mode. so how I set button events in this session?
And if you have a better solution for run-time design generation, give it to me. thanks ;)
A few things.
You may add controls at practically any point. It can be in the constructor, the Load, in response to another event, or when a custom method is called.
You can wire up events by using AddHandler myButton.Click, AddressOf Button_Click. You'll have to define the Button_Click event handlder and it will need to have the appropriate signature, which for a button click is (sender as object, e as EventArgs).
When in doubt, temporarily add a real control to you form and go to the hidden designer code (MyForm.vDesigner.vb) and see what is generated as a sample. Copy that code and move it into the main populating code. Then delete the control.
Good luck!
Related
I am creating an application which requires dynamically loaded controls (to be precise buttons). These buttons are exactly the same, therefore the problem is not creating controls programatically, but making them work somehow. Each button should open a form, the form is being based on some data from the button. I'd like to have all the buttons use one event handler and open forms accordingly to the data it contains. Is there any way to do so? I don't know the types of these forms yet, therefore I can't use pre-defined "select case" or anything that would limit possibilities.
Another problem is that I would like to have some of the forms (modules) being "installed" independently. Is there any way to make that possible? I believe that could be completed using dlls, but I'm not sure. Is there any information on that, I've been looking for that for a while, but found nothing.
Regarding your first problem: You can create buttons in code; the answers to the following question should be enough to get you started (it's C#, but the principle is the same):
How to add Buttons in WinForm in Runtime?
In a nutshell:
Read your button configuration data from the database (or configuration file or whatever),
add the buttons to your user interface (see above),
use AddHandler to add an event handler to each of the buttons. For example:
AddHandler myButton.Click, Sub(sender, e)
' Do something
End Sub
(Regarding your second question: 1. It is unclear to me what you are asking and 2. you shouldn't ask two questions in the same SO question. I suggest that you open a new SO question for that and try to explain your requirement more clearly.)
Maybe i have not understand well your answer... But for your buttons:
1) Create a custom control, inheriting the Button control, and add the properties used for the creation of your forms.
2) In the Sub referenced by your eventHandler, the first argument is the control (the button) who raises the event, so you can use it's own properties to create your forms...
Adding to Heinzi's post:
Keep a list of the button names you created for use with AddHandler().
This code isn't exactly on point but it shows how the AddHandler() can be used at runtime:
' hook TextChanged/CheckedChanged for dirty logic
Dim chk As CheckBox
Dim rdo As RadioButton
For Each c As Control In FormDataControls
If c.Name.StartsWith("chk") Then
chk = c
AddHandler chk.CheckedChanged, AddressOf SetDirty
ElseIf c.Name.StartsWith("rdo") Then
rdo = c
AddHandler rdo.CheckedChanged, AddressOf SetDirty
Else
AddHandler c.TextChanged, AddressOf SetDirty
End If
Next
FormDataControls is my list of controls to target. In my case I use the Tag property to designate data controls.
If I close a form in vb.net by using .dispose(), do I need to worry about cleaning up any of the elements that were created inside the form (like addHandler, etc) or does disposal clean up everything for me?
Thanks.
Closing a Form (or calling Dispose() on it) will clean up all of the components within that form. This means that any controls added to the form (or its controls, recursively) will automatically clean up.
Event handlers on controls within the form will get cleaned up.
That being said, this will not clean up event handlers which are subscribing to objects not owned by the form. If you used AddHandler to add an event handler to a type outside of the form, it would be a good practice to use RemoveHandler within an override of Form.Dispose(Boolean) to remove this subscription.
I don't know how to put it right, but I have a vb.net winform app in which I want to use a customcontrol so I can re-use the logic on multiple forms. I know how to set values in this control from the parent (using properties in the control). But now I want to call a specifiek function on the parent form. Im my case LoadData() which is a procedure of the parentform. How can I do this?
I know I can reference the parent form by using Me.ParentForm in the usercontrol. But I cannot call the LoadData() procedure in the parentform.
Any help? This is a winforms app, not a ASP.NET app.
T.I.A.
[Edit]
I could solve my problem using this example found right here. This is working fine
First, a UserControl is for reusing GUI logic, so I hope that is what you meant. If you are trying to reuse non-GUI logic you might want to create some stand-alone classes for that.
Second, it is generally bad design to call back up to the parent form in the way you describe because it makes the UserControl less reusable and it creates an overly tight binding between the two. You should, if at all possible, push the data down into the UserControl instead.
If you can find no way for the Form to push the data down (perhaps because it is based upon a UI interaction within the UserControl), you have a couple of other options. The first is to wrap up the data-loading behavior into an object that can be passed to the UserControl during initialization, and the the UserControl can access the LoadData method on it as needed. Another approach is to have the UserControl define a set of Events that can be used to request external data from the form. I like to use the "Query" prefix on these kinds of events. So when a fetch button is tapped on your UserControl, it raises the "QueryData" event, and the form that is handling that event responds by populating a data container of some sort that is part of the custom EventArgs.
Either of these can be expanded upon if you need more assistance.
Upon re-reading the question, I it looks like perhaps my approach is over kill. I was under the impression that the LoadData was a method in the Form that loaded data into the UserControl. If it is just a simple call then focus on the event portion of my answer and ignore the data container portion.
I would add an event to your control and handle it on the form the control is part of.
In your control, put something like this:
Public Event LoadData(ByVal sender As Object, ByVal e As System.EventArgs)
And in your form, you can have something like this:
Private Sub UserControl1_LoadData(sender As Object, e As EventArgs) Handles UserControl1.LoadData
'...Your code here
End Sub
I ma using DevExpress controls (which doesnt matter for this example). I have a lookupEdit control and I never want the EditValue_Changed event to fire. Can I use RemoveHandler to do this? If so can someone give me a code example of doing this? Should I put RemoveHandler in the load event of the user control I am creating? Or does it go in the EditValue_Changed event of the lookupControl?
THIS IS A WINDOWS APP NO POSTBACK....Sorry
You can use RemoveHandler from any event you add to an object within one of your own classes. If the event is defined and being handled within a class you do not have access to, you will not be able to remove its handler events.
It would be instructive to learn where this EditValue_Changed event is firing. If it is firing within your application, then you must have wired it up either in the designer or in the code (which means you should be able to call RemoveHandler without difficulty). If this belongs to a 3rd party library and is auto-configured, you may not have this access.
You can't stop the control from firing the postback, but you can just not wire up an event handler to a control's event. You don't need RemoveHandler to do that; just don't attach to the event... But it seem like the issue is the postback, DevExpress should have a feature in there to fire a client-side event, and keep that all on the client and not have to worry about a server-side postback.
If this doesn't help, could you explain more about the problem?
HTH.
You might be able to subclass the control and override the method(s) that trigger the EditValue_Changed event to fire. If you have access to the source code, find where its being called and if that code can be overridden.
When using Visual Studio (though ideally this can apply to the generic case) and double click on a button I've created, the event handler code that is auto generated uses the following signature:
Protected Sub btnSubmitRequest_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnSubmitRequest.Click
End Sub
Is it best practice to leave the name of this method as is, or should it be renamed to something a little more descriptive, such as SubmitNewEmployeeRequest?
Create another method called SubmitNewEmployeeRequest. In btnSubmitRequest_Click, call SubmitNewEmployeeRequest. That is the most logical separation of duties.
Also, if you change the name of the button in the IDE before creating the handlers, the handlers get better default names. The name of your button would currently be btnSubmitRequest, you could change it to be more specific as btnSubmitNewEmployeeRequest and then generate the handler.
You should name your controls, and keep the naming consistent between the control and handlers.
I would generally name them within the context of usage, that is if your in the
Employee Request form, then the button need only be named SubmitRequest.
Do Stuff to Directory components form, then the button should probably be more descriptive like SubmitNewEmployeeRequest.
Well, personally I leave it so that I can see quickly that it is an event handler, specifically a click event handler. However I would be inclined to just have one line of code there that calls (in this case, your) SubmitNewEmployeeRequest because this may also be called from some context menu as well, or fired in response to some other event.