Click here to Skip to main content
Click here to Skip to main content

Atlas: ModalUpdateProgress - An UpdateProgress Control in Modal Popup Style

By , 26 Jun 2007
 

Sample Image - ModalUpdateProgress.jpg

Introduction

ASP.NET AJAX has a cool UpdateProgress control that provides a visual indicator while one or more of the UpdatePanel controls are being updated. However, it will be much more useful if all other elements on the page could be disabled when the UpdateProgress is shown. This led me to build the ModalUpdateProgress control in which the UpdateProgress will act as a modal popup.

How UpdateProgress Control Works

If you open up System.Web.Extensions.dll using reflector, you will be able to look up how UpdateProgress control works. Simply put, it implements IScriptControl's two methods GetScriptDescriptors() and GetScriptReferences(). According to the AJAX documentation, GetScriptDescriptors() returns a list of components, behaviors, and client controls required for the UpdateProgress control's client functionality; and GetScriptReferences() returns a list of client script library dependencies for the UpdateProgress control. In GetScriptDescriptors(), the UpdateProgress control registers a ScriptControlDescriptor with type name Sys.UI._UpdateProgress, which is a class available in MicrosoftAjaxWebForms.js (MicrosoftAjaxWebForms.js is one of the ASP.NET AJAX client script libraries, embedded in the System.Web.Extensions.dll). It is pretty straightforward to understand the logic in Sys.UI._UpdateProgress by looking into the debug version of MicrosoftAjaxWebForms.js.

Building the ModalUpdateProgress Control

First, we derive ModalUpdateProgress from UpdateProgress so that we can reuse its existing properties and interface. Then we need to override the two methods GetScriptDescriptors() and GetScriptReferences(), and implement the client-side script component. We will name the client script component as Sys.UI._ModalUpdateProgress, which in turn will be a sub class of Sys.UI._UpdateProgress.

The following is the detail implementation of GetScriptDescriptors() and GetScriptReferences():

/// <summary>
/// Gets the script descriptors.
/// </summary>
/// <returns>A list of components, behaviors, and 
/// client controls required
/// for the ModalUpdateProgress control's client functionality
/// </returns>
protected override IEnumerable<ScriptDescriptor> GetScriptDescriptors()
{
  if (((this.Page != null) && this.ScriptManager
      .SupportsPartialRendering) && this.Visible)
  {
    ScriptControlDescriptor desc = new ScriptControlDescriptor(
       "Sys.UI._ModalUpdateProgress", this.ClientID);
    string updatePanelClientID = null;
    if (!string.IsNullOrEmpty(this.AssociatedUpdatePanelID))
    {
        UpdatePanel panel = this.NamingContainer.FindControl(this
            .AssociatedUpdatePanelID) as UpdatePanel;
        if (panel == null)
        {
            panel = this.Page.FindControl(this
               .AssociatedUpdatePanelID) as UpdatePanel;
        }

        if (panel == null)
        {
            throw new InvalidOperationException(string.Format(
                CultureInfo.InvariantCulture, "No UpdatePanel 
                found for AssociatedUpdatePanelID '{0}'.",
                new object[] { this.AssociatedUpdatePanelID }));
        }

        updatePanelClientID = panel.ClientID;
    }

    string backgroundCssClass = null;
    string cancelControlID = null;
    if (!string.IsNullOrEmpty(this._backgroundCssClass))
    {
        backgroundCssClass = this._backgroundCssClass;
    }

    if (!string.IsNullOrEmpty(this._cancelControlID))
    {
        cancelControlID = this._cancelControlID;
    }

    desc.AddProperty("associatedUpdatePanelId", updatePanelClientID);
    desc.AddProperty("dynamicLayout", this.DynamicLayout);
    desc.AddProperty("displayAfter", this.DisplayAfter);
    desc.AddProperty("backgroundCssClass", backgroundCssClass);
    desc.AddProperty("cancelControlID", cancelControlID);
    yield return desc;
  }
}

/// <summary>
/// Gets the script references.
/// </summary>
/// <returns>A list of client script library dependencies for the control.
/// </returns>
protected override IEnumerable<ScriptReference> GetScriptReferences()
{
    yield return new ScriptReference("AjaxControls.ModalUpdateProgress.js", "
    AjaxControls");
}

Both methods return IEnumerable's that will be later handled by ScriptManager.

To implement the client-side script component Sys.UI._ModalUpdateProgress, we can borrow scripts from the ModalPopup control available in the AJAX Control Toolkit. In order to get the script to work for the control, I have to make some minor tweakings, which won't be discussed here. For those who are interested, please look into the ModalUpdateProgress.js in the source for detailed implementation.

How to Use

Just like the UpdateProgress control, you can use the ProgressTemplate property to customize your progress indicator in ModalUpdateProgress.

The ModalUpdateProgress control has an extra property BackgroundCssClass which is used to set the CSS class for the background when the control is displayed. In addition, the ProgressTemplate can include a button that the user can click on to cancel the update in progress. In order for the cancel button to work, you should specify the CancelControlID property using the button ID in the ProgressTemplate.

The following shows an example of adding the ModalUpdateProgress to the page:

<asp:ModalUpdateProgress ID="ModalUpdateProgress1" DisplayAfter="0"
        runat="server" BackgroundCssClass="modalBackground">
 <ProgressTemplate>
  <div class="modalPopup">
     Loading <img src="indicator.gif" align="middle" />
  </div>
 </ProgressTemplate>
</asp:ModalUpdateProgress>

To see how it works, please check out the demo website I have included in the download. The ModalUpdateProgress control supports all the features that UpdateProgress has, including associating the ModalUpdateProgress with an UpdatePanel.

The control passed testing under IE6/7 and Firefox 2.0. Please leave your comments here if you find any problems.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

About the Author

Ting Huang
United States United States
Member
Currently playing Wii...Just love it!

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
You must Sign In to use this message board.
Search this forum  
    Spacing  Noise  Layout  Per page   
QuestionAssembly does not allow partially trusted callersmembershalan9924 Sep '08 - 3:31 
Hi,
 
was wondering if anyone incurred this problem. The application im developing is to be hosted on a medium trust environment. Im developing in VS2005 on vista, so I changed my local trust settings to medium, and got the Security Exception error.
 
I see that the assembly is signed with an snk, but why am I still getting this error? Should I add the APTCA attribute to the "ModalUpdateProgress.cs" class? and if so, how?
 
Much thanx
AnswerRe: Assembly does not allow partially trusted callersmemberMember 43434843 Jun '09 - 18:31 
Put [assembly: AllowPartiallyTrustedCallers()]
 
in the assembly.cs file.
 
And it works in medium trust.
GeneralRe: Assembly does not allow partially trusted callersmemberlogicaldna15 Jun '09 - 21:06 
I have got a similar issue, If I change the trust level to medium, project wont compile, I have added a line as per you suggestions, but does not work in medium trust level.
I have also used permcal tool to check what permissions are required but could not understand part of it.
 
Here is output xml for permcal tool
http://flexdna.com/downloads/SurveyDNA.web.survey.dll.PermCalc.xml[^]
 
If I know what code is causing the permissions request I can get rid of the same to make it work on medium trust level
 
Thanks
QuestionWhich ajax library are you using here?memberefinkelb25 Jul '08 - 5:41 
Hello,
I was wondering which .dll are you using for this feature.
Why it doesn´t work if I use the "normal" common ajax library? Is this one some "special" dll that includes the control modalUpdateProgress?
As you can see I am confused about this.
Thanks.
GeneralModalpopup does not display.....memberKamalmostofi2 Jul '08 - 2:07 
Hi,
You have done a great job and made the life easy. Thanks.
However, it does not work for my project. I have pages that have contentwrapper and all my controls are inside this wrapper. (updatepanel.... etc).
The modalpopup does not show.
But, when I use your control in a very simple page, it works.
 
Can you advice please?
 
Thanks,
Kam
GeneralProblem with ModalPopupmemberadlionelC10 Jun '08 - 6:05 
Hi,
 
I'm facing a very weird problem with your very usefull control:
 
I'm using Modal Popup extender from the "standard" MS Ajax ToolKit called from server with the Show Method
 
Thoses modal popup are encapsulated within UpdatePanels so as to avoid page flickering during internal postbacks (I manually call the Show Method during postback as Modal Popup doesn't show automatically on postback)
 
Once I've added your ModalUpdateProgress in my page sometimes my page is randomly not refreshed on postback
 
When I'm attaching Visual Studio debugger with a breakpoint just before my show statement, I'm breaking as expected and stranger the page is refreshed as expected too! As soon as I'm stopping debugging the problem comes back
 
I've no problem using standard MS UpdateProgress
 
Here is my progress template :
 
<table bgcolor="#FFFFFF" border="0" cellspacing="0" cellpadding="0">
<tr>
<td>Please wait...</td>
</tr>
</table>
 
(very simple as you can see)
 
Moreover it seems that a higher update progress display delay reduces the problem (but it still exists)
 
Have you any ideas?
 
Lionel
QuestionPossible to show modal progress bar over multiple frame document?memberbjames029 May '08 - 11:47 
I have a very UI intensive application and without an intelligent way to ask the user to wait ,they often execute code in one frame while another frame is doing it's thing.
 
Is it possible to use this control to disable the whole page (every frame) until loading is finished?
 
Thanks again and great article.
GeneralProblem in firefox and safarimemberIsmail Mayat2 May '08 - 6:12 
Hello,
 
i am using this excellent control in a project. In an update panel i have 3 buttons they are used to vote for different aspects on an object. When you click on button the modal popup appears the code writes to db then disables button you just clicked. It all works fine in ie7. However in Firefox and safari you click first button all works as expected. When you click on second or third button you get javascript error "The state information for this page is invalid and might be corrupted"
 
Any ideas?
 
Thanks
 
Ismail Mayat

GeneralGreat JobmemberSunny Gurnani21 Apr '08 - 8:40 
Good Great Job Smile | :)
GeneralHandler was not added through the Sys.UI.DomEvent.addHandler method.memberVictor M. Bello A.4 Apr '08 - 6:33 
Hello, i'm having a problem, i'm using this control on one of my forms and i'm having an issue when clicking through a couple of buttons, when i hit a button in particular i get this error
 
Message: Sys.InvalidOperationException: Handler was not added through the Sys.UI.DomEvent.addHandler method.
Line: 3559
Char: 48
Code: 0
 
And sometimes the "Processing..." panel i have that locks everything while processing just stays there.
 
Any suggestions?
 
Thanks.
GeneralRe: Handler was not added through the Sys.UI.DomEvent.addHandler method.memberVictor M. Bello A.4 Apr '08 - 6:40 
I followed SamEB's suggestion and that appears to have fixed my problem.
 
I added this line
this._windowHandlersAttached = false;
and it worked great.
 
Thanks.
<------------------------>
 
SamEB's message
 
Hi,
 
I was getting an Invalid SysOperation error when I added a delay to the display of the popup (to prevent screen flash on fast updates).
 
Fixed it by adding the following line to the detach popup:
 

function Sys$UI$_ModalUpdateProgress$_detachPopup() {
if (this._windowHandlersAttached) {
if (this._scrollHandler) {
$removeHandler(window, 'scroll', this._scrollHandler);
}
if (this._resizeHandler) {
$removeHandler(window, 'resize', this._resizeHandler);
}
<!-- ADDED LINE - handlers no longer attached -->
this._windowHandlersAttached = false;
}
}
GeneralRe: Handler was not added through the Sys.UI.DomEvent.addHandler method.memberDPLyonnais8 May '08 - 8:22 
Nice!! This was it, finally found the rigth solution. Thanks SamEB
GeneralGood, thanks!!!memberkeenth4 Apr '08 - 3:59 
This is what I have been looking for, thanks man!!!
GeneralThank you!membershalan9918 Mar '08 - 22:53 
Beautiful piece of work! well done and thank you for making this available! Big Grin | :-D
Generalproblems with step 1membererkki22211 Feb '08 - 2:37 
Nice stuff, it is just what I need but I am having a problems with step 1. When i open .dll file with Reflector, it shows
References and Resources. Where can I find the stuff what I need to edit? I have never done anything like this before. thanks in advance!
Generalupdating controls inside a modal update progressmemberarcb31 Jan '08 - 8:18 
I want to have a % done readout in the modalupdateprogress control. I tried adding an update panel, label and a timer inside the progresstemplate, with the timer calling a page method that updated the label and the update panel set to update on the timer tick, but i can't work out how to reference the label in the codebehind, as visual studio can't find the controls inside the modalupdateprogress, and findcontrol can't find them either... Any ideas, or do i have to delve into the code for modalupdateprogress and add this funtionality?
 
Thanks, Ben
GeneralRuns on the first try!!! Thanks a lot !!!memberTony Montana29 Jan '08 - 18:36 
Cool program!!! we need this kind of stuff!! thanks buddy.. Blush | :O
GeneralProblem Firefox Vs. IE7memberMember 332403725 Jan '08 - 12:00 
That excellent work ...
 
However, I have a question ... Posted control in a MasterPage but it works perfectly in Firefox, but when I am going to run on IE7 shows me control in the upper left corner of the page and does not show the style of the fund ... (ModalProgressGreyBackground), you help?
AnswerRe: Problem Firefox Vs. IE7memberTing Huang25 Jan '08 - 14:18 
make sure you have doctype on your page.
GeneralRe: Problem Firefox Vs. IE7memberpanzerdivisionmarkus31 Jan '08 - 23:54 
I have the same problem. What doctype should I use?
 
Right now I have this doctype:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
 
and this in the html tag:
 
<html xmlns="http://www.w3.org/1999/xhtml" >
AnswerRe: Problem Firefox Vs. IE7memberpanzerdivisionmarkus31 Jan '08 - 23:57 
Found it...
 
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
GeneralRe: Problem Firefox Vs. IE7memberChajon28 Mar '08 - 8:23 
Thank you SO much. I have looked for the resolution to this problem everywhere. I'm greatly indebted. Big Grin | :-D
QuestionProblem with contentplaceholders?memberarcb15 Jan '08 - 14:45 
Hi,
 
I have been using this control for a while, and it is great! The only problem i have is when the update panel has a contentplaceholder in it. The background element positions its top and left to match the top and left of the contentplaceholder, rather than the page...
 
Has anyone else seen this, and is there a fix?
 
Thanks in advance,
 
Ben
AnswerRe: Problem with contentplaceholders?memberarcb16 Jan '08 - 10:24 
Don't worry, i was just putting things in the wrong place,it's fixed now.
 
--ben
GeneralGreat job!memberbrinsky7 Jan '08 - 0:22 
I'm very impressed, well done.. it saved me a lot of time and had me interested in making my own controls.
 
Thanks again,
b

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Permalink | Advertise | Privacy | Mobile
Web03 | 2.6.130516.1 | Last Updated 26 Jun 2007
Article Copyright 2006 by Ting Huang
Everything else Copyright © CodeProject, 1999-2013
Terms of Use
Layout: fixed | fluid