Ureader.com  
Microsoft software help and Community
   home   |   control panel login   |   archive   |  
 
DotNet
acad.assignment.mngr
academic
adonet
aspnet
aspnet.announcements
aspnet.build.controls
aspnet.caching
aspnet.datagridcontrol
aspnet.mobile
aspnet.security
aspnet.webcontrols
aspnet.webservices
clr
compactframework
component_services
datatools
distributed_apps
drawing
faqs
framework
framework.wmi
general
internationalization
interop
languages.csharp
languages.jscript
languages.vb
languages.vb.controls
languages.vb.data
languages.vb.upgrade
languages.vc
languages.vc.libraries
myservices
odbcnet
performance
remoting
scripting
sdk
security
setup
vjsharp
vsa
webservi.enhancements
webservices
windowsforms
windowsforms.controls
winforms.databinding
winforms.designtime
xml
  
 
date: Mon, 30 Jun 2008 12:12:45 +0300,    group: microsoft.public.dotnet.framework.aspnet.buildingcontrols        back       


Click event does not fire - IPostBackEventHandler ?   
Hi all,

I am developing a container control like a standard Div with a template 
property called Content.
Unfortunately, although the button implements the IPostBackEventHandler 
interface (since it is the standard Button control)  it's click event does 
not fire.

I am almost running crazy. I don't understand the problem. Could you please 
help?


Here is my code for my custom container:

using System;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.HtmlControls;
using System.ComponentModel;

namespace MyCustomControlLibrary {

 [ParseChildren(true)]
 [PersistChildren(false)]
 public class MyDiv: WebControl {

  private Control container = null;

  protected override HtmlTextWriterTag TagKey {
   get {
    return HtmlTextWriterTag.Div;
   }
  }

  [DefaultValue(null)]
  [Browsable(false)]
  [TemplateInstance(TemplateInstance.Single)]
  [PersistenceMode(PersistenceMode.InnerProperty)]
  [NotifyParentProperty(true)]
  public ITemplate Content {
   get;
   set;
  }

  protected override void OnInit(EventArgs e) {
       if (Content != null) {
            container = new HtmlGenericControl("div");
            container.ID = ClientID + "_Content";
            Content.InstantiateIn(container);
       }
  }

  protected override void CreateChildControls() {
       base.CreateChildControls();

       if (container != null) {
            Controls.Add(container);
       }
  }
 }
}


Here is a sample ASPX page that uses MyDiv:

<%@ Page Debug="true" Language="C#" AutoEventWireup="true" 
CodeBehind="Default.aspx.cs" Inherits="MyTestWebApplication._Default" %>
<%@ Register Assembly="MyCustomControlLibrary" 
Namespace="MyCustomControlLibrary"  TagPrefix="mcc" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>Untitled Page</title>
</head>
<body>
    <form id="form1" runat="server">
    <mcc:MyDiv ID="MyDiv1" runat="server">
        <Content>
            <asp:Button ID="Button1" runat="server" Text="Button" 
OnClick="Button1_Click" />
        </Content>
    </mcc:MyDiv>
    </form>
</body>
</html>
date: Mon, 30 Jun 2008 12:12:45 +0300   author:   Ahmet Gunes

Re: Click event does not fire - IPostBackEventHandler ?   
Hi Ahmet

I guess your Control have to implement "INamingContainer" to garant
unique IDs and the Access from the ASP.NET-Engine.

Try this :)

To implement IPostBackEventHandler doesnt make any Sense for
that control and your case, because _that_ Control isnt`t a 
PostBackEventHandler.

-- 
Gruss, Peter Bucher
Microsoft MVP - Visual Developer ASP / ASP.NET, Switzerland
http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community
http://www.aspnetzone.de/blogs/peterbucher/ - Auf den Spuren von .NET
date: Mon, 30 Jun 2008 12:54:03 +0200   author:   Peter Bucher [MVP]

Re: Click event does not fire - IPostBackEventHandler ?   
Thanks Peter,

Actually I have already tried implementing INamingContainer and it worked. 
:)
I also found another way that also worked:

Replace the following lines

container = new HtmlGenericControl("div");
container.ID = ClientID + "_Content";
Content.InstantiateIn(container);
with

Content.InstantiateIn(this);

and remove the override of CreateChildControls.

But I didn't like these solutions since I need to call those content with 
the same ids in the client code.
When INamingContainer is implemented the ids of the content controls are 
changed.
My control is actually much more complicated and needs some inner container.

Actually, I saw a sample code at http://www.coolite.com which achieves this 
without implementing INamingContainer.
If you wish, you may download the community edition as a Zip file and check 
the ContentPanel control.
It does not implement INamingContainer in any way.

Thanks,

Ahmet


"Peter Bucher [MVP]" , haber iletisinde sunlari 
yazdi:upagn%23p2IHA.5832@TK2MSFTNGP02.phx.gbl...
> Hi Ahmet
>
> I guess your Control have to implement "INamingContainer" to garant
> unique IDs and the Access from the ASP.NET-Engine.
>
> Try this :)
>
> To implement IPostBackEventHandler doesnt make any Sense for
> that control and your case, because _that_ Control isnt`t a 
> PostBackEventHandler.
>
> -- 
> Gruss, Peter Bucher
> Microsoft MVP - Visual Developer ASP / ASP.NET, Switzerland
> http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community
> http://www.aspnetzone.de/blogs/peterbucher/ - Auf den Spuren von .NET
date: Mon, 30 Jun 2008 14:21:52 +0300   author:   Ahmet Gunes

Re: Click event does not fire - IPostBackEventHandler ?   
Hi Ahmed

> I also found another way that also worked:
>
> Replace the following lines
>
> container = new HtmlGenericControl("div");
> container.ID = ClientID + "_Content";
> Content.InstantiateIn(container);
> with
>
> Content.InstantiateIn(this);
Here you do manually what ASP.NET does if INamingContainer is implemented.
And like you guess, thats not a good solution.

Whats the Problem with implementing INamingContainer?

> Actually, I saw a sample code at http://www.coolite.com which achieves 
> this without implementing INamingContainer.
> If you wish, you may download the community edition as a Zip file and 
> check the ContentPanel control.
> It does not implement INamingContainer in any way.
I looked short at that Code, but doesent see the Reason - its way to 
complicated, IMO.

-- 
Gruss, Peter Bucher
Microsoft MVP - Visual Developer ASP / ASP.NET, Switzerland
http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community
http://www.aspnetzone.de/blogs/peterbucher/ - Auf den Spuren von .NET
date: Tue, 1 Jul 2008 11:44:48 +0200   author:   Peter Bucher [MVP]

Re: Click event does not fire - IPostBackEventHandler ?   
Hi Peter,

First of all, my container is actually a custom web control which does not 
output begin/end tags.
To simplify things, I just put a sample div control.
Therefore, I think my solution is not the same as implementing 
INamingContainer.

Now let me give you an example:
Assume the containing panel is named "pnl01", and my button control is 
"btn01".
When I implement INamingContainer, the name and id of the button becomes 
"pnl01$btn01" and "pnl01_btn01", respectively.
But for simplicity purposes I need to call the button as "btn01" in the 
client-side script.

Next, since those containers can be nested as many times as the page 
developer wishes, when you put pnl01 inside pnl02 then the name of the 
button becomes "pnl02$pnl01$btn01" which makes client-side scripting a 
tedious task. In addition, those new names adds to the total bytes sent to 
the client since there will be many textbox, dropdownlist or button controls 
in the form.

Another question: Is there any way to override the default behaviour of 
implementing INamingContainer?


Thanks,


"Peter Bucher [MVP]" , haber iletisinde sunlari 
yazdi:C0414D71-443D-401F-BBE6-AC623BB634AC@microsoft.com...
> Hi Ahmed
>
>> I also found another way that also worked:
>>
>> Replace the following lines
>>
>> container = new HtmlGenericControl("div");
>> container.ID = ClientID + "_Content";
>> Content.InstantiateIn(container);
>> with
>>
>> Content.InstantiateIn(this);
> Here you do manually what ASP.NET does if INamingContainer is implemented.
> And like you guess, thats not a good solution.
>
> Whats the Problem with implementing INamingContainer?
>
>> Actually, I saw a sample code at http://www.coolite.com which achieves 
>> this without implementing INamingContainer.
>> If you wish, you may download the community edition as a Zip file and 
>> check the ContentPanel control.
>> It does not implement INamingContainer in any way.
> I looked short at that Code, but doesent see the Reason - its way to 
> complicated, IMO.
>
> -- 
> Gruss, Peter Bucher
> Microsoft MVP - Visual Developer ASP / ASP.NET, Switzerland
> http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community
> http://www.aspnetzone.de/blogs/peterbucher/ - Auf den Spuren von .NET
date: Tue, 1 Jul 2008 13:57:37 +0300   author:   Ahmet Gunes

[SOLVED] Re: Click event does not fire - IPostBackEventHandler ?   
Solved at last.

The point that I was missing is the execution order of the events.
In order for a control to raise an event that control should be added to the 
Control tree first.

Hence the following code in the custom container control solved my problem:

protected override void OnInit(EventArgs e) {
    base.OnInit(e);
    if (Content != null) {
        this.EnsureID();
        container = new MyContainer();
        container.ID = this.ID + "_Content";
        Controls.Add(container);
        Content.InstantiateIn(container);
    }
}

Thanks,

Ahmet

"Ahmet Gunes"  wrote in message 
news:%23IkmIl22IHA.4500@TK2MSFTNGP06.phx.gbl...
> Hi Peter,
>
> First of all, my container is actually a custom web control which does not 
> output begin/end tags.
> To simplify things, I just put a sample div control.
> Therefore, I think my solution is not the same as implementing 
> INamingContainer.
>
> Now let me give you an example:
> Assume the containing panel is named "pnl01", and my button control is 
> "btn01".
> When I implement INamingContainer, the name and id of the button becomes 
> "pnl01$btn01" and "pnl01_btn01", respectively.
> But for simplicity purposes I need to call the button as "btn01" in the 
> client-side script.
>
> Next, since those containers can be nested as many times as the page 
> developer wishes, when you put pnl01 inside pnl02 then the name of the 
> button becomes "pnl02$pnl01$btn01" which makes client-side scripting a 
> tedious task. In addition, those new names adds to the total bytes sent to 
> the client since there will be many textbox, dropdownlist or button 
> controls in the form.
>
> Another question: Is there any way to override the default behaviour of 
> implementing INamingContainer?
>
>
> Thanks,
>
>
> "Peter Bucher [MVP]" , haber iletisinde 
> sunlari yazdi:C0414D71-443D-401F-BBE6-AC623BB634AC@microsoft.com...
>> Hi Ahmed
>>
>>> I also found another way that also worked:
>>>
>>> Replace the following lines
>>>
>>> container = new HtmlGenericControl("div");
>>> container.ID = ClientID + "_Content";
>>> Content.InstantiateIn(container);
>>> with
>>>
>>> Content.InstantiateIn(this);
>> Here you do manually what ASP.NET does if INamingContainer is 
>> implemented.
>> And like you guess, thats not a good solution.
>>
>> Whats the Problem with implementing INamingContainer?
>>
>>> Actually, I saw a sample code at http://www.coolite.com which achieves 
>>> this without implementing INamingContainer.
>>> If you wish, you may download the community edition as a Zip file and 
>>> check the ContentPanel control.
>>> It does not implement INamingContainer in any way.
>> I looked short at that Code, but doesent see the Reason - its way to 
>> complicated, IMO.
>>
>> -- 
>> Gruss, Peter Bucher
>> Microsoft MVP - Visual Developer ASP / ASP.NET, Switzerland
>> http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community
>> http://www.aspnetzone.de/blogs/peterbucher/ - Auf den Spuren von .NET
>
>
date: Wed, 2 Jul 2008 01:26:22 +0300   author:   Ahmet Gunes

RE: [SOLVED] Re: Click event does not fire - IPostBackEventHandler ?   
You must implement RegisterRequiresRaiseEvent ( control)
where control implements IPostBackEventHandler. This must be done in the 
control's load event.
Also I must note that 'Only one server control can be registered per page 
request.' (MSDN cited) so only one control from those which implements 
IPostBackEventHandler will run its implemented RaisePostBackEvent(). That 
control will be the last one which registers its instance with 
RegisterRequiresRaiseEvent() from Page class.

"Ahmet Gunes" wrote:

> Solved at last.
> 
> The point that I was missing is the execution order of the events.
> In order for a control to raise an event that control should be added to the 
> Control tree first.
> 
> Hence the following code in the custom container control solved my problem:
> 
> protected override void OnInit(EventArgs e) {
>     base.OnInit(e);
>     if (Content != null) {
>         this.EnsureID();
>         container = new MyContainer();
>         container.ID = this.ID + "_Content";
>         Controls.Add(container);
>         Content.InstantiateIn(container);
>     }
> }
> 
> Thanks,
> 
> Ahmet
> 
> "Ahmet Gunes"  wrote in message 
> news:%23IkmIl22IHA.4500@TK2MSFTNGP06.phx.gbl...
> > Hi Peter,
> >
> > First of all, my container is actually a custom web control which does not 
> > output begin/end tags.
> > To simplify things, I just put a sample div control.
> > Therefore, I think my solution is not the same as implementing 
> > INamingContainer.
> >
> > Now let me give you an example:
> > Assume the containing panel is named "pnl01", and my button control is 
> > "btn01".
> > When I implement INamingContainer, the name and id of the button becomes 
> > "pnl01$btn01" and "pnl01_btn01", respectively.
> > But for simplicity purposes I need to call the button as "btn01" in the 
> > client-side script.
> >
> > Next, since those containers can be nested as many times as the page 
> > developer wishes, when you put pnl01 inside pnl02 then the name of the 
> > button becomes "pnl02$pnl01$btn01" which makes client-side scripting a 
> > tedious task. In addition, those new names adds to the total bytes sent to 
> > the client since there will be many textbox, dropdownlist or button 
> > controls in the form.
> >
> > Another question: Is there any way to override the default behaviour of 
> > implementing INamingContainer?
> >
> >
> > Thanks,
> >
> >
> > "Peter Bucher [MVP]" , haber iletisinde 
> > sunlari yazdi:C0414D71-443D-401F-BBE6-AC623BB634AC@microsoft.com...
> >> Hi Ahmed
> >>
> >>> I also found another way that also worked:
> >>>
> >>> Replace the following lines
> >>>
> >>> container = new HtmlGenericControl("div");
> >>> container.ID = ClientID + "_Content";
> >>> Content.InstantiateIn(container);
> >>> with
> >>>
> >>> Content.InstantiateIn(this);
> >> Here you do manually what ASP.NET does if INamingContainer is 
> >> implemented.
> >> And like you guess, thats not a good solution.
> >>
> >> Whats the Problem with implementing INamingContainer?
> >>
> >>> Actually, I saw a sample code at http://www.coolite.com which achieves 
> >>> this without implementing INamingContainer.
> >>> If you wish, you may download the community edition as a Zip file and 
> >>> check the ContentPanel control.
> >>> It does not implement INamingContainer in any way.
> >> I looked short at that Code, but doesent see the Reason - its way to 
> >> complicated, IMO.
> >>
> >> -- 
> >> Gruss, Peter Bucher
> >> Microsoft MVP - Visual Developer ASP / ASP.NET, Switzerland
> >> http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community
> >> http://www.aspnetzone.de/blogs/peterbucher/ - Auf den Spuren von .NET
> >
> > 
> 
> 
>
date: Tue, 5 Aug 2008 01:27:01 -0700   author:   Ion Lamasanu Ion

Google
 
Web ureader.com


    COPYRIGHT 2007, YARDI TECHNOLOGY LIMITED, ALL RIGHT RESERVE  |   contact us