Some context. I've added inside Page_Load of a class Method1 that generates a repeater and Method2 that generates an array of buttons.
Each button is attached dynamically an event inside Method2.
The buttons will never change, but based on clicking a button the repeated elements should change.
My main problem is/are:
1) when I click a button, the event causes the page to load (Page_Load) which calls Method1, which generates the default repeater, instead of the one associated with my specific event attached to button x from the array of buttons; --> so, I wrapped up Method1 in !isPostBack ... then, nothing happens at all
How would you avoid this? What principles would you use for implementig this?
Attempted so far:
protected void Page_Load(object sender, EventArgs e)
{
if(!IsPostBack)
{
GetItems(1, 2); //default values (first time the page is loaded)
GenerateButtons(10);
}
}
private void GenerateButtons(int c)
{
LinkButton[] x = new LinkButton[c];
for(int i=0; i<c;i++)
{
x[i] = new LinkButton();
x[i].Text = (i+1).ToString();
Panel1.Controls.Add(x[i]);
x[i].OnClientClick += new EventHandler(Button_Click);
}
}
protected void Button_Click(object sender, EventArgs e)
{
Button button = (Button)sender; // Which button was clicked;
GetItems(int.Parse(button.Text)-1, 3); //3 is a constant; first argument is index of button extracted from its caption
}
//clicking a button should load the page invoking GetItems() specific to the button pressed (first argument is its index) and should regenerate the buttons, maybe highlighting in some way the one that was previously pressed.
To help performance, it would also help not to regenerate the buttons after a page was first loaded.
I'm working with ASP.NET and C#.
My main problem is Button_Click is never invoked, probably because the buttons are regenerated when clicking a button so their definitions is recreated, including the buttons' events.
Your Button_Click handler would always be fired before the regeneration, anyway; so this is not the problem.
Your problem, however, lies in your x[i].OnClientClick += ... code.
You need to hook up to the .Click event of the LinkButton to listen to the right event.
Like this:
private void GenerateButtons(int c)
{
LinkButton[] x = new LinkButton[c];
for(int i=0; i<c;i++)
{
x[i] = new LinkButton();
x[i].Text = (i+1).ToString();
Panel1.Controls.Add(x[i]);
x[i].Click += new EventHandler(Button_Click); // Use the 'Click' event
}
}
Hope this helps!
Related
The problem we are having is accessing the click event for a button which is created in the click event of another button i.e. clicking the first button generates a new panel and controls, and we now want the button on this newly created panel to perform an action.
The controls have been declared at the top of the class as follows:
Panel createElementPage = null;
TextBox elementDescription = null;
TextBox elementName = null;
Button continueButton = null;
AuditSystem audit;
Here is an excerpt of the method that generates the new panel, the part that defines the continueButton is written as follows:
public void CE_Click(object sender, EventArgs e)
{
createElementPage.Controls.Add(elementDescription);
continueButton = new Button();
continueButton.Text = "Continue";
continueButton.Location = new Point(700, 500);
continueButton.Size = new Size(100, 50);
createElementPage.Controls.Add(continueButton);
}
We want to access the continueButton's click event handler but the method we have written does not seem to be working. This is what we have so far:
private void continueButton_Click(object sender, EventArgs e)
{
Console.WriteLine(" something");
}
Clicking the button yields no results, and we have tried a few solutions such as implementing a seperate eventHandler method. Does anybody have a fix for this?
You have to actually subscribe to the event:
continueButton.Click += continueButton_Click;
Events need to be told what they should handle. Without that, they won't "listen" to anything.
Friendly note: be careful when adding handlers "on demand" like this (i.e. outside of the designer). It doesn't really apply here (you have a new button each time), but it's fairly easy to accidentally subscribe to a control's event multiple times, and your handler will fire multiple times as a result. It's just nice to be aware of :)
Any idea how I could make a click event create another button with different click event?
I have a WPF app to make using EF. So I'm stuck at the part where I need to press button "Add" which will freeze other buttons and then create another button "Submit" with code for adding data to the table. I have tried some advice from msdn, but it doesn't work. Here is the code (previously in XAML added a button named b1):
public partial class RoutedEventAddRemoveHandler {
void MakeButton(object sender, RoutedEventArgs e)
{
Button b2 = new Button();
b2.Content = "New Button";
// Associate event handler to the button. You can remove the event
// handler using "-=" syntax rather than "+=".
b2.Click += new RoutedEventHandler(Onb2Click);
root.Children.Insert(root.Children.Count, b2);
DockPanel.SetDock(b2, Dock.Top);
text1.Text = "Now click the second button...";
b1.IsEnabled = false;
}
void Onb2Click(object sender, RoutedEventArgs e)
{
text1.Text = "New Button (b2) Was Clicked!!";
}
I even tried the most obvious solution to simply create another button with click event directly in click event.
I would recommend an alternative approach and put the submitbutton in your xaml code right away but make it so that it is invisible and disabled.
Then in the event handler you simply have to make it visible and enable it.
Your event handler that handles the submit, the dynamic creation of the button, hooking it in the form and such can all be avoided and don't have to be done at runtime.
This will result in a lot better readable code and maintainable code than your original approach unless you have a very good reason for it.
I have done the following coding and it is working for me
private void btnAdd_Click(object sender, RoutedEventArgs e)
{
Button oButton = new Button();
oButton.Name = "btnMessage";
oButton.Content = "Message Show";
oButton.Height = 50;
oButton.Width = 50;
oButton.Click += new RoutedEventHandler(oButton_Click);
//root is a stack panel
root.Children.Insert(root.Children.Count, oButton);
DockPanel.SetDock(oButton, Dock.Top);
}
void oButton_Click(object sender, RoutedEventArgs e)
{
MessageBox.Show("Hello World !");
}
i have a problem with user control.
i create it dynamically on my aspx page after clicking on a button:
protected void btnAddRules_Click(object sender, EventArgs e)
{
RuleProperty Control = (RuleProperty)LoadControl("RuleProperty.ascx");
MyPanel.Controls.Add(Control);
}
when i click on a button of my user control, the button event wont fire and the user control will disappear. here is the button event:
protected void btnAdd_Click1(object sender, EventArgs e)
{
WowzaRule rule = GetRuleFromGUI();
RuleList.Add(rule);
//Session["RuleList"] = RuleList;
//List<WowzaRule> test = new List<WowzaRule>();
SaveToXMLFiles(txtdbnum.Text, RuleList);
}
i understand that after pressing the button on mypage the usercontrol is released and if its not created on pag_init or page Load it wont stay, but i need to create it on my button click event and find a way for it not to disapper.
thanks in advance, Daniel
You might have to add an event handler that it can fire the click event and call your delegate
Control.Click += btnAdd_Click1;
Dynamically created controls, once added, have to be on a page on every page load in order to work correctly. What happens in your case:
RuleProperty is added after the button click
Page loads with this control
User clicks on the button within RuleProperty
Control is not added to the control tree during the page load (corresponding code is only in the button click handler, and that button was not clicked)
ASP.NET does not know which control triggered the event, so the event is not processed
To go around this issue you need to add you control on every page loading, for example using some flag stored in ViewState:
protected void Page_Load(object sender, EventArgs e)
{
if (ViewState["AddRuleProperty"] != null && (bool)ViewState["AddRuleProperty"])
{
AddRulePropertyControl();
}
}
protected void btnAddRules_Click(object sender, EventArgs e)
{
AddRulePropertyControl();
ViewState["AddRuleProperty"] = true;
}
private void AddRulePropertyControl()
{
RuleProperty Control = (RuleProperty)LoadControl("RuleProperty.ascx");
MyPanel.Controls.Add(Control);
}
Update.
If you want to remove the control from the page later on in the control's click handler, you need to remove corresponding ViewState key. This is not possible from the control directly, since property Page.ViewState is protected, and also this would have created an unwanted dependency.
What seems as the right way to do this is to subscribe to the very same event from the Page (you might need to make this event visible from the controller) and reset the key in there. Like this:
private void AddRulePropertyControl()
{
RuleProperty Control = (RuleProperty)LoadControl("RuleProperty.ascx");
Control.ButtonClick += RuleProperty_ButtonClick;
MyPanel.Controls.Add(Control);
}
private void RuleProperty_ButtonClick()
{
ViewState["AddRuleProperty"] = false;
}
Please note that event name here is not real, this is just a sketch of what can be done.
I have a button that is created after a user selects a certain value from a dropdown menu, but it is not firing its' EventHandler. Is there something with the Lifecycle, OnInit possibly, that I have to refresh for the handler to fire correctly?
Event fired from DropDownList's OnSelectedIndexChanged
protected void Selected_floor_first(object sender, EventArgs e)
{
Button btn = new Button();
btn.ID = "room_button_1";
btn.Text = "Select";
btn.Click += new EventHandler(room_1_Click);
floor_1_room_overlay.Controls.Add(btn);
}
Handler: (Not Firing)
protected void room_1_Click(object sender, EventArgs e)
{
validation.Text = "You selected a Room";
}
If you must create your button dynamically, create it inside the OnInit() method of the page.
Event handling happens after Page Init. So, the button will have to be created before Page Init, for the events to be handled.
As it is dynamically added, you have to take that code in Page_Init() event that occurs after every postback. otherwise when the postback occurs, there is no room_button_1 in the forms.controls collection and the event is missed. So
add it as it is being added.
after adding set a variable in session to identify that dynamic control has been added
on page_init() check the session variable of step2. if it says yes then create the control you created in step 1.
Instead of repeating the code, it's better if you create a function for button creation and call it from your Select_floor_first() and Page_Init().
The button goes out of scope mate. define it as a private variable otherwise the event wont fire as the button disposed after Selected_floor_first method finishes
private Button btn = new Button();
protected void Selected_floor_first(object sender, EventArgs e)
{
btn.ID = "room_button_1";
btn.Text = "Select";
btn.Click += new EventHandler(room_1_Click);
floor_1_room_overlay.Controls.Add(btn);
}
protected void room_1_Click(object sender, EventArgs e)
{
validation.Text = "You selected a Room";
}
Basically, I have an update panel in which i have a link button, when user clicks on the link button all the contents are cleared and textbox shows up in which user enters something and when user hit enter key, the update panel should be refreshed or gets updated or repopulated with all the contents .
How can I do it ???
The way I am trying to do this is that when event handler of link button is fired, I created a hidden button dynamically and assign it a new event handler which will get fired when user hits enter key.This new dynamic button is created inside link button event handler. In this new button event handler I will repopulate the contents back.
The problem with my way is the event handler of dynamically created button is not fired.
Why ???
Please try to answer in c#.
Thanks in advance.
Regards,
My code #
protected void Submit_Click1(object sender, EventArgs e)
{
Label1.Text = TextBox1.Text + TextBox2.Text + " are sucessfully registered";
Button mento = new Button();
mento.cssclass = "invisible";
mento.Click += new EventHandler(mento_click);
// here this new mento button is attached to update panel
updatepanel1.ContentTemplateContainer.Controls.add(mento);
}
Now the problem is mento_click event handler does not get fired ???
You can catch the enter key, in the textbox?
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
//add event keydown
textBox1.KeyDown += new KeyEventHandler(textBox1_KeyDown);
}
void textBox1_KeyDown(object sender, KeyEventArgs e)
{
switch (e.KeyCode )
{
case Keys.Enter:
//YOur updatecode here:
MessageBox.Show("You press enter");
break;
default:
break;
}
}
}
You have to attach the event on page_init or page_load every time theres a request, or the event wont get hooked up to the control.
you can check out this link to understand why:
http://msdn.microsoft.com/en-us/library/ms178472.aspx
Example
if you want to hook it up on the submit you should do something like:
page_init(object sender, EventArgs e)
{
CreateControls();
}
private void CreateControls()
{
//Create button with event and add to the panel
}
clickEvent(object sender, EventArgs e)
{
updatePanel.Update();
}
That should fire correctly the event. Im sorry i just wrote this on the fly and didnt test it, but i hope it gives you de general idea.
Cheers.
To all of you strugling with postback from buttons in asp.net, I would like to mention an alternative and ancient method of dealing with button-click events.
1) name your dynamically created buttons using a Prefix (like for instance this one: btn_). That way, every button you create will have a name starting with this prefix. For example the first button you create will have the name btn_0. You can achieve this by a routine like this one:
For _counter As Integer = 0 To 3
Dim butt As New Button
' the next 1 line is convenient when programming for the .net 4.0 framework:
butt.ClientIDMode = UI.ClientIDMode.Static
butt.butt.ID = "btn_" & _counter
butt.Text = "someting"
page.controls.add(butt)
next
2) ... and then, to handle it all, you can do it like this in the on_load event of your asp.net page:
If IsPostBack Then
For Each key As String In Request.Form
If InStr(Trim(key), "btn_") > 0 Then
Response.Write(Request.Form(key))
End If
Next
End If