Celebrate National IT Professionals Day with 3 months of free Premium Membership. Use Code ITDAY17

x
?
Solved

ScriptManager.RegisterClientScriptBlock duplicates JavaScript on Async PostBack (ASP.NET AJAX)

Posted on 2008-06-13
8
Medium Priority
?
8,171 Views
Last Modified: 2013-11-26
I am creating a UserControl of the Yahoo Calendar for use in Microsoft ASP.NET AJAX and am close to completion at this point. However two bugs remain. The one I need some assistance on is regarding the ScriptManager.RegisterClientScriptBlock.

When the user control is used on a site and is not initialized immediately on the page, but is started instead on the page after the postback (or if the control is turned on/off, it may be a later postback and not the immediate one), so you would use the ScriptManager.RegisterClientScriptBlock to add the JavaScript to the script manager. And at this time, this works quite well. However, what doesn't work, is that I have no way of preventing this from stopping once it is turned on and the script multiplies, so many instances of the object are the displayed on the page.

This can be seen at http://www.gmitravelinc.com/yahoo/

All visible controls immediately seen are intialized and are working properly. Click "Test" and "Date 5" will be added to the page asynchronosly within the group. Click the button, now labeled "Testing!" and both "Date 6" and "Date 5", part of a similar control type, will begin to reproduce on the page.

How do I change my code to prevent this?
String stringScript = String.Empty;
stringScript = @"
<script type=""text/javascript"" id=""" + this.ClientID + @"Script"">
var prm = Sys.WebForms.PageRequestManager.getInstance();
prm.add_initializeRequest(initializeRequest);
prm.add_pageLoaded(pageLoaded);
var _postBackElement;
 
function initializeRequest(sender, e)
{
   if (prm.get_isInAsyncPostBack())
   {
      e.set_cancel(true);
   }
   _postBackElement = e.get_postBackElement();
}
 
function pageLoaded(sender, e)
{
   YAHOO.util.Event.onDOMReady(function ()
   {
";
					if (boolReadOnly)
					{
						stringScript += @"
      document.getElementById(""" + stringTargetControlID + @""").readOnly = true;
";
					}
					stringScript += @"
      function onButtonClick()
      {
         oCalendarMenu.setBody(""&#32;"");
         oCalendarMenu.body.id = """ + this.ClientID + @"calendarcontainer"";
         oCalendarMenu.render(this.get(""container""));
         oCalendarMenu.align();
         var oCalendar = new YAHOO.widget.Calendar(""" + this.ClientID + @"buttoncalendar"", oCalendarMenu.body.id);
";
					if (boolNavigation)
					{
						stringScript += @"
         oCalendar.cfg.setProperty(""navigator"", true);
";
					}
					if (!String.IsNullOrEmpty(stringMinDate))
					{
						stringScript += @"
         oCalendar.cfg.setProperty(""mindate"", """ + stringMinDate + @""");
";
					}
					if (!String.IsNullOrEmpty(stringMaxDate))
					{
						stringScript += @"
         oCalendar.cfg.setProperty(""maxdate"", """ + stringMaxDate + @""");
";
					}
					if (!String.IsNullOrEmpty(stringPageDate))
					{
						stringScript += @"
         oCalendar.cfg.setProperty(""pagedate"", """ + stringPageDate + @""");
";
					}
					if (!String.IsNullOrEmpty(stringHightlight))
					{
						stringScript += @"
         oCalendar.addRenderer(""" + stringHightlight + @""", oCalendar.renderCellStyleHighlight1);
";
					}
					if (!String.IsNullOrEmpty(stringSoldOut))
					{
						stringScript += @"
         oCalendar.addRenderer(""" + stringSoldOut + @""", oCalendar.renderBodyCellRestricted);
";
					}
					stringScript += @"
         var stDate = document.getElementById(""" + stringTargetControlID + @""");
         if (stDate.value != """")
         {
            oCalendar.select(stDate.value);
            var selectedDates = oCalendar.getSelectedDates();
            if (selectedDates.length > 0)
            {
               var firstDate = selectedDates[0];
               oCalendar.cfg.setProperty(""pagedate"", (firstDate.getMonth()+1) + ""/"" + firstDate.getFullYear());
            }
         }
         oCalendar.render();
         oCalendar.changePageEvent.subscribe(function ()
         {
            window.setTimeout(function ()
            {
               oCalendarMenu.show();
            }, 0);
         });
         oCalendar.selectEvent.subscribe(function (p_sType, p_aArgs)
         {
            var aDate;
            if (p_aArgs)
            {
               aDate = p_aArgs[0][0];
               YAHOO.util.Dom.get(""" + stringTargetControlID + @""").value = aDate[1] + ""/"" + aDate[2] + ""/"" + aDate[0];
            }
            oCalendarMenu.hide();
         });
         this.unsubscribe(""click"", onButtonClick);
      }
      var oCalendarMenu = new YAHOO.widget.Overlay(""" + this.ClientID + @"calendarmenu"");
      var oButton = new YAHOO.widget.Button({type: ""menu"", 
                                             id: """ + this.ClientID + @"calendarpicker"", 
                                             label: ""Choose A Date"", 
                                             menu: oCalendarMenu, 
                                             container: """ + this.ClientID + @"datefields"" });
      oButton.on(""click"", onButtonClick);
   });
}
</script>
";
					writer.Write(@"
        <span id=""" + this.ClientID + @"datefields"">
" + stringScript + @"
        </span>
");
 
if (IsPostBack)
{
	ScriptManager.RegisterClientScriptBlock(Page, typeof(YahooCalendar), this.ClientID + "ScriptA", stringScript, false);
}

Open in new window

0
Comment
Question by:gmitravel
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 3
  • 3
8 Comments
 
LVL 13

Expert Comment

by:joechina
ID: 21822155
Have you tried to remove the following:
writer.Write(@"
        <span id=""" + this.ClientID + @"datefields"">
" + stringScript + @"
        </span>


0
 

Author Comment

by:gmitravel
ID: 21822295
It won't initialize without it.

If you comment that out and write either:

if (IsPostBack)
{
      ScriptManager.RegisterClientScriptBlock(Page, typeof(YahooCalendar), this.ClientID + "ScriptA", stringScript, false);
}

or just:

ScriptManager.RegisterClientScriptBlock(Page, typeof(YahooCalendar), this.ClientID + "ScriptA", stringScript, false);

It will not add the script to the file.
0
 
LVL 13

Expert Comment

by:joechina
ID: 21824631
Which event do you put the code?
0
Interactive Way of Training for the AWS CSA Exam

An interactive way of learning that will help you visualize core concepts so that you can be more effective when taking your AWS certification exam.  Built for students by a student to help them understand the concepts that they are being taught.

 
LVL 13

Expert Comment

by:joechina
ID: 21824656
How about this:
if (IsPostBack)
{
      ScriptManager.RegisterClientScriptBlock(Page, typeof(YahooCalendar), this.ClientID + "ScriptA", stringScript, false);
}
else
{
writer.Write(@"
        <span id=""" + this.ClientID + @"datefields"">
" + stringScript + @"
        </span>
");

}
0
 

Author Comment

by:gmitravel
ID: 21824751
In the "if...else" statement the control initializes when the page opens. When you postback the control is gone, again because the writer has not written the <span> statement.

Here is how the code is set in the aspx file:

<yui:YahooCalendar ID="Calendar6" Type="TextBox" TargetControlID="Calendar6Date" Navigation="false" MinDate="8/8/2008" MaxDate="8/19/2008" PageDate="8/2008" Highlight="8/8/2008-8/9/2008,8/11/2008" SoldOut="8/10/2008,8/12/2008,8/13/2008" runat="server" />

It's a control (yahoocalendar.cs) that is compiled into a dll file, etc. That's where the writer writes the code, inline in that place -- it replaces that with the YUI inline script to function the calendar control. The code I initially provided is from the protected override void Render(HtmlTextWriter writer) function in the control.
0
 

Accepted Solution

by:
gmitravel earned 0 total points
ID: 21948579
Add this line of JavaScript code to the bottom of the script and you've cleaned out the problem....

prm.dispose();
Note.... it has to be at the bottom......

      var oButton = new YAHOO.widget.Button({type: ""menu"", 
                                             id: """ + this.ClientID + @"calendarpicker"", 
                                             label: ""Choose A Date"", 
                                             menu: oCalendarMenu, 
                                             container: """ + this.ClientID + @"datefields"" });
      oButton.on(""click"", onButtonClick);
   });
prm.dispose();
}
</script>

Open in new window

0

Featured Post

What is SQL Server and how does it work?

The purpose of this paper is to provide you background on SQL Server. It’s your self-study guide for learning fundamentals. It includes both the history of SQL and its technical basics. Concepts and definitions will form the solid foundation of your future DBA expertise.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

This article is for Object-Oriented Programming (OOP) beginners. An Interface contains declarations of events, indexers, methods and/or properties. Any class which implements the Interface should provide the concrete implementation for each Inter…
Wouldn’t it be nice if you could test whether an element is contained in an array by using a Contains method just like the one available on List objects? Wouldn’t it be good if you could write code like this? (CODE) In .NET 3.5, this is possible…
Monitoring a network: how to monitor network services and why? Michael Kulchisky, MCSE, MCSA, MCP, VTSP, VSP, CCSP outlines the philosophy behind service monitoring and why a handshake validation is critical in network monitoring. Software utilized …
In this video you will find out how to export Office 365 mailboxes using the built in eDiscovery tool. Bear in mind that although this method might be useful in some cases, using PST files as Office 365 backup is troublesome in a long run (more on t…

730 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question