I need to use the mentioned 3rd party datepicker and it throws an exception when an invalid date it entered. The author only exposes one event, which is fired when a successful parse takes place. How, in ASP.NET could I catch this error and do something about it, like set a label's text?
There are a couple of approaches you can take here, personally I would replace the default event handler for the TextChanged event via inheritance.
The code assigns one via during the setup and unfortunately textbox is a private member
textBox.TextChanged += new EventHandler(OnSelectedDateChanged);
which is declared as
protected virtual void OnSelectedDateChanged(object sender, EventArgs e)
So we can inherit SlimeeLibrary.DatePicker
public class EnhancedDatePicker : SlimeeLibrary.DatePicker
and then override the EventHandler raising a new parse error event.
public event EventHandler OnDateParseError;
protected override void OnSelectedDateChanged(object sender, EventArgs e)
{
try
{
base.OnSelectedDateChanged(sender, e);
}
catch (FormatException fe)
{
OnDateParseError(sender, e);
}
}
Hope that helps. I haven't checked it but have examined the code for slimees control, but don't want to setup a code project account to download it sorry. You'll obviously need to change your ASP.NET usercontrol references to use the new class.
Related
I've got a bit of an issue with creating a new control based on ASP.NET's ImageButton control. Everything works as expected, except for the click handler that is being hooked up in the control's OnInit override. Basically, clicking the custom image button just refreshes the page, never hitting the handler.
Now, I know this is something stupid I've done or just not understood, but I can't for the life of me figure this out. All the articles, questions and forum posts I've found on event handling issues for controls is for child controls, rather than ones that inherit from existing control types and have their own predefined handlers.
The following code is what I've written:
public class WebPaymentButton : ImageButton
{
public string DisabledImageUrl { get; set; }
public string TermsAcceptClass { get; set; }
protected override void OnPreRender(EventArgs e)
{
Page.ClientScript.RegisterClientScriptResource(typeof (WebPaymentButton), "PaymentModule.Scripts.WebPaymentButtonScript.js");
}
protected override void OnInit(EventArgs e)
{
CssClass = "WebPaymentButton";
if (!string.IsNullOrWhiteSpace(TermsAcceptClass))
{
Attributes["data-TermsClass"] = TermsAcceptClass;
}
if (!string.IsNullOrWhiteSpace(DisabledImageUrl))
{
Attributes["data-DisabledImageUrl"] = ResolveUrl(DisabledImageUrl);
}
Click += WebPaymentButton_Click;
base.OnInit(e);
}
private void WebPaymentButton_Click(object sender, ImageClickEventArgs e)
{
HttpContext.Current.Response.Redirect("http://dummy_payment_page_in_place_of_code", true);
}
}
I've tried hooking the handler up in the OnLoad and also switching it to run after the base.OnInit/OnLoad calls. Nothing has solved the handler issue. Can anyone point me in the right direction?
In case it helps, here is the markup for the button on the page:
<pm:WebPaymentButton runat="server" ImageUrl="~/pay-now.png" DisabledImageUrl="~/not-pay-now.png" TermsAcceptClass="TermsCheckbox" ID="MainPayButton" />
Have you tried overriding the OnClick event handler instead of hooking up to a new event handler?
Remove the Click += WebPaymentButton_Click line from OnInit and remove the WebPaymentButton_Click function, then add the following code to your class instead:
protected override void OnClick(ImageClickEventArgs e)
{
base.OnClick(e);
HttpContext.Current.Response.Redirect("http://dummy_payment_page_in_place_of_code", true);
}
I have C# Web Application that has an aspx page hosting a user control (Review.ascx). Inside that user control there are 5 more user controls, one of which has a public event (Review_Summary.ascx). The problem is no matter what i do I cannot get the event wired up in the parent ascx control (Review.ascx).
Here is what I have in the child control (Review_Summary.ascx)
public event EventHandler forwardStatusChanged;
#region methods
protected void btnForward_Click(object sender, EventArgs e)
{
if (btnForward.Text == "Return")
{
if (forwardStatusChanged != null)
{
forwardStatusChanged(sender, e);
}
removeForward();
}
}
In the parent control (Review.ascx) I have this
public void initReview(string EmployeeNumber)
{
RevSummary.forwardStatusChanged += new EventHandler(RevSummary_forwardStatusChanged);
<more code here>
}
protected void RevSummary_forwardStatusChanged(object sender, EventArgs e)
{
lblReadOnly.Visible = false;
}
RevSummary is the ID of the child control in the parent control. InitReveiw is a method that is called by the aspx page in its Page_Load event.
I get no errors on compile or at runtime. But when I click the button the forwardStatusChanged event is null. The "removeForward()" method that is called after that executes properly. So that fact that the event is always null leads me to believe that the wire up in the parent control is not working. However, I am sure it is executing becasue all of the code after that executes.
How can I figure out why this event is not wiring up?
Where is initReview being called from? Are you sure it's being called because the only reason this happens is that the event handler wasn't truly setup. I've never found a reason other than this, the several times I did this myself.
HTH.
Let's say I have a base page class with a Page_load() event handler and I also have a Page_load() event handler in the derived page class. I realised you don't have to wrote vitual or override keyword and compiler does not detect error. Why is this? And why is is base class version executed?
Those are just events.
To override, you need to use the OnLoad method available on Control.
Try overriding the event firing method and call your own. I can't explain why it's not complaining about both but I know they are added to the event, and hence are both in the queue to be executed.
protected override void OnLoad(EventArgs e)
{
this.Page_Load(this, e);
}
The method you are overriding here doesn't do anything fancy except execute all event handlers in the queue. See the snippet from Reflector below:
protected internal virtual void OnLoad(EventArgs e)
{
if (this.HasEvents())
{
EventHandler handler = this._occasionalFields.Events[EventLoad] as EventHandler;
if (handler != null)
{
handler(this, e);
}
}
}
I was wrong. There was indeed a warning about shadowing a parent class method, but it was just a warning, not an error.
I need to test a condition in several ASPX code-behind files and, in some cases, would like to completely bypass the normal page load process so that the corresponding ASPX page is not loaded. Intead, I'd like to send a custom response to the browser that's written from a code-behind method.
Does anyone know where to start- what method(s) in the page lifecycle to override and the best technique to ensure that my custom Response.Write is sent to the browser while the normal ASPX page content is suppressed?
Thanks.
Probably the easiest way to do it - use Page_Load().
protected void Page_Load(object sender, EventArgs e)
{
bool customResponse = true;
if (customResponse)
{
Response.Write("I am sending a custom response");
Response.End(); //this is what keeps it from continuing on...
}
}
The "easy" way to do it, with Response.End() is terrible for performance, throwing an exception which terminates the thread.
http://blogs.msdn.com/b/tmarq/archive/2009/06/25/correct-use-of-system-web-httpresponse-redirect.aspx
http://weblogs.asp.net/hajan/archive/2010/09/26/why-not-to-use-httpresponse-close-and-httpresponse-end.aspx
I had the same question and solved it this way. It's a two-step process: First call HttpApplication.CompleteRequest() and exit your processing. Next override Render() so that the base method is not called. The example code then becomes:
bool customResponse = true;
protected void Page_Load(object sender, EventArgs e)
{
if (customResponse)
{
Response.Write("I am sending a custom response");
this.Context.ApplicationInstance.CompleteRequest();
return; // Bypass normal processing.
}
// Normal processing...
}
protected override void Render(HtmlTextWriter writer)
{
if (!customResponse)
base.Render(writer); // Then write the page as usual.
}
It really depends what you're responding to, is it a posted Form field, authentication info etc...?
The method shown using Page_Load will work, but anything before that point in the page lifecycle will also execute.
I can easily understand how to use custom events in pure C# code, but how can I do pass in custom event arguments on asp:button click?
I've tried all sorts of things (defining new event args, new delegates, etc etc) but I have had no luck.
Is there a tutorial of how to do this with the standard asp controls?
As long as your EventArgs inherit from System.EventArgs you will be able to pass them. Then, once inside your event handler, you can cast the event to the proper subtype.
Here is an example:
using System;
class Program
{
static event EventHandler Foo;
static void Main()
{
// Here is cast the EventArgs to FooEventArgs
Foo += (o,e) => Console.WriteLine(((FooEventArgs)e).Number);
// Notice that I am passing a "FooEventArgs" instance
// even though the delegate signature for "EventHandler"
// specifies "EventArgs". Polymorphism in action. :)
Foo(null, new FooEventArgs { Number = 1 });
}
}
class FooEventArgs : EventArgs
{
public int Number { get; set; }
}
I know that you are working with existing control delegates so unfortunately this kind of casting is neccessary. Keep in mind though that there is a EventHandler<T> where T : EventArgs delegate in .NET 2.0 and greater that will allow you to do what I have done above without casting.
I don't believe there is a way to do this without creating your own controls. However, I sometimes use the commandagument and commandname properties on a button to provide additional information
I don't thinks you can. The Button itself will be calling the Click event with it's own EventArgs object, and unfortunately you can't hijack that call. You can however use closures:
protected void Page_Load(object sender, EventArgs e)
{
int number = 1;
button.Click += (o, args) => Response.Write("Expression:"+number++);
number = 10;
button.Click += delegate(object o, EventArgs args) { Response.Write("Anonymous:"+number); };
}
By the way the output for this is Expression:10Anonymous:11 Understanding why this is the output is a big step into understanding closures! Even though number is out of scope when Click Event is handled, it is not destroyed because both of the defined event handler's have references to the it. So it and it's value will be maintained until it is no longer needed. I know that's not the most technical explanation of closures, but should give you an idea of what they are.