Click here to Skip to main content
15,867,308 members
Articles / Web Development / ASP.NET

Disable an ASP.NET Button Control During Postback with an AJAX Loading Background Image

Rate me:
Please Sign up or sign in to vote.
4.44/5 (15 votes)
15 Nov 2009CPOL3 min read 132.8K   1.2K   58   25
An article on how to disable a button control during postback.

Introduction

There are times when our applications might take an extra few seconds to respond to a click event. Some users might get impatient and click on the button more than once. We can easily avoid this type of situation by disabling the submit button during postback on the page by using a client-side script. In this article, I will share with everyone how to:

  1. Disable a button during postback with or without a validation control.
  2. Change button text value during postback.
  3. Include an AJAX loading background image during postback.
  4. How to avoid the 'Page_IsValid is undefined' JavaScript error.

Using the Code

Before we begin, allow me to show you the structure of my project. You are welcome to download this demo.

Project Structure

Demo 1 – Without Validation Control

Here is the content of Jscript.js:

JavaScript
function disableBtn(btnID, newText) {

    var btn = document.getElementById(btnID);
        setTimeout("setImage('"+btnID+"')", 10);
        btn.disabled = true;
        btn.value = newText;
}

function setImage(btnID) {
    var btn = document.getElementById(btnID);
    btn.style.background = 'url(12501270608.gif)';
}

Here is part of the Default.aspx page content:

HTML
<table>        
         <tr>
            <td>
            <td>
                 <asp:button id="btnOne" tabIndex="0" 
                    Runat="server" Text="Submit"
                    onclick="btnOne_Click" 
                    OnClientClick="disableBtn(this.id, 'Submitting...')" 
                    UseSubmitBehavior="false" />               
            </td>
        </tr>
        <tr>
            <td colspan="2">
                <asp:Label ID="Label3" 
                  runat="server" Text=""></td>
        </tr>
   </table>

<script type="text/javascript" src="JScript.js"></script>

In the Default.aspx page, I have a Button and a Label control. Let's take a closer look at the button attributes.

  • OnClientClick="disableBtn(this.id, 'Submitting...')" - Calls the JavaScript function by passing in the button ID and the new text value that I want it to display on click.
  • UseSubmitBehavior="false" - Indicates that the button control should use the ASP.NET postback mechanism instead of the client browser's submit mechanism (UseSubmitBehavior property).

For testing, I included these lines in default.aspx.cs:

C#
protected void btnOne_Click(object sender, EventArgs e)
{
    Thread.Sleep(2000);
    Label3.Text = DateTime.Now.ToLongTimeString();
}

Here is how the button will look like when someone clicks on it:

Demo 1 click

Demo 1 Output

Demo 2 – With Validation Control

Here is the output from Default2.aspx:

Demo 2 aspx Page

Oops... The button is still disabled after it failed the validation process. Let's modify the JavaScript to fix this problem.

Demo 2 aspx Page Onclick

Here is the content of the new JavaScript file with comments – Jscript2.js:

JavaScript
function ResetToDefault(btn, oldValue) {
    btn.disabled = false;
    btn.value = oldValue;
}
//browser properties
var Browser = {
    Version: function() {
        var version = 999;
        if (navigator.appVersion.indexOf("MSIE") != -1) {
            version = parseFloat(navigator.appVersion.split("MSIE")[1]);
            return version;
        }
    },
    Name: navigator.appName,
    isIE: function() {
        if (navigator.appVersion.indexOf("MSIE") != -1) {
            return true;
        }
        return false;
    }
};

//Handle Page_Validators is not defined error
//http://www.velocityreviews.com/forums/t88987-pagevalidators-error.html
function HasPageValidators() {
    var hasValidators = false;
    try {
        if (Page_Validators.length > 0) {
            hasValidators = true;
        }
    }
    catch (error) { }

    return hasValidators;
}

function SetImage(btn) {

    if (btn.type == "image") {
        btn.src = null;
        btn.style.width = '100px';
        btn.style.height = '20px';
        btn.style.backgroundImage = 'url(http://images.ysatech.com/ajax-loader.gif)';
    }
    else {
        //somehow backgroundImage not working with IE 7
        if (Browser.isIE() && Browser.Version() === 7) {
            btn.style.background = 'url(http://images.ysatech.com/ajax-loader.gif)';
        }
        else {
            btn.style.backgroundImage = 'url(http://images.ysatech.com/ajax-loader.gif)';
        }
    }
}

//enable the button and restore the original text value for browsers other than IE
function EnableOnUnload(btn, btnText) {
    if (!Browser.isIE()) {
        window.onunload = function() {
            ResetToDefault(btn, btnText);
        };
    }
}

//check if the validator have any control to validate
function EnableValidator(validator) {
    var controlToValidate = document.getElementById(validator.controltovalidate);

    if (controlToValidate !== null) {
        // alert(controlToValidate.id);
        ValidatorEnable(validator);
        return true;
    }
    ValidatorEnable(validator, false);

    return false;
}

function disableBtn(btnID, newText) {
    var btn = document.getElementById(btnID);
    var oldValue = btn.value;
    btn.disabled = true;
    btn.value = newText;
    
    //if validator control present
    if (HasPageValidators()) {

        Page_IsValid = null;

        //http://sandblogaspnet.blogspot.com/2009/04/calling-validator-controls-from.html
        //double check, if validator not null
        if (Page_Validators !== 'undefined' && Page_Validators !== null) {
            //Looping through the whole validation collection.
            for (var i = 0; i < Page_Validators.length; i++) {

                var validator = Page_Validators[i];

                //check if control to validate is enable 
                if (EnableValidator(validator)) {

                    if (!Page_Validators[i].isvalid) { //if not valid
                        ResetToDefault(btn, oldValue); //break;
                    }
                }
            }

            //   else { //if valid
            var isValidationOk = Page_IsValid;

            alert('isValidationOk ' + isValidationOk);

            EnableOnUnload(btn, btn.value);
            if (isValidationOk !== null) {
                if (isValidationOk) {
                    SetImage(btn);
                    __doPostBack(btnID, '');
                    // break;
                }
                else { //page not valid
                    btn.disabled = false;
                }
            }
            //  }
            
        }
    }
    else { //regular, no validation control present
        // setTimeout("SetImage('" + btn + "')", 5);
        SetImage(btn);
        btn.disabled = true; btn.value = newText;
        EnableOnUnload(btn, btn.value);
    }
}

//disable those validators where controltovalidate = null
function DisableValidators() {
    //this will get rid of the Page_Validators is undefined error
    if (typeof (Page_Validators) === 'undefined')
        return;
        
    if (Page_Validators !== 'undefined' && Page_Validators !== null) {
        for (var i = 0; i < Page_Validators.length; i++) {
            var validator2 = Page_Validators[i];
            var controlToValidate2 = document.getElementById(validator2.controltovalidate);
            if (controlToValidate2 === null) {
                ValidatorEnable(validator2, false);
            }
        }
    }
    return false;
}

window.onload = DisableValidators;

Output from using the new JavaScript (JScript2.js):

Demo 2 OnClick fail Validation

Demo 2 OnClick Pass Validation

Demo 2 After PostBack

Conclusion

The main items in this project were the JavaScript (Jscript2) and the button attributes (OnClientClick, UseSubmitBehavior). I hope someone will find this tutorial useful. If you think I can improve this code, please leave me a feedback and share your thoughts.

Tested on IE 6.0/7.0 and Firefox 3.0.13.

History

  • 08/14/2009 - I found out that, in Firefox, if we hit the button and continue to the next page, and then hit the Back button (or javascript:history(-1);)... the button control is still disabled. I have updated the JavaScript (JScript2). I have not fully tested the new implementation. Please leave me a feedback and share your thoughts.
  • 10/19/2009 - Modified the JavaScript (JScript2) to fix the double validation problem.
  • 11/14/2009 - Fixed the bug mentioned by CodeProject user, prodriguez13. The JavaScript will throw an error when the control to validate is not visible. To remedy this, in the onload event, I have added the DisableValidators function. This function is responsible to disable all the validators with controltovalidate === null.
  • I have received a few requests on getting this script to work with the Image button. I managed to put together a solution for it. Let me know if you find any bugs. Tested on IE 7.0/8.0, FireFox, image would not show on Google Chrome, maybe someone can shed some light on this.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior)
United States United States
I have over 10 years of experience working with Microsoft technologies. I have earned my Microsoft Certified Technology Specialist (MCTS) certification. I'm a highly motivated self-starter with an aptitude for learning new skills quickly.

Comments and Discussions

 
Questiondouble validation problem Pin
Member 106619426-Apr-18 8:28
Member 106619426-Apr-18 8:28 
QuestionAnother Solution Pin
Jayant Sharma12-Jun-12 1:19
Jayant Sharma12-Jun-12 1:19 
AnswerRe: Another Solution Pin
Member 119042525-Sep-19 23:53
Member 119042525-Sep-19 23:53 
QuestionGood Pin
deepthimadhu8-Feb-12 3:22
deepthimadhu8-Feb-12 3:22 
QuestionLink Button Pin
xfair developer28-Jan-12 9:36
xfair developer28-Jan-12 9:36 
GeneralRe: Link Button Pin
Bryian Tan29-Jan-12 15:09
professionalBryian Tan29-Jan-12 15:09 
GeneralMy vote 5 Pin
shaheen_mix16-Dec-11 22:59
shaheen_mix16-Dec-11 22:59 
GeneralRe: My vote 5 Pin
Bryian Tan29-Jan-12 15:09
professionalBryian Tan29-Jan-12 15:09 
GeneralMy vote of 5 Pin
Hua Trung12-Dec-11 14:11
Hua Trung12-Dec-11 14:11 
GeneralRe: My vote of 5 Pin
Bryian Tan29-Jan-12 15:09
professionalBryian Tan29-Jan-12 15:09 
GeneralServer-side code called multiple times when page valid Pin
Alec MacLean22-Jun-10 4:10
Alec MacLean22-Jun-10 4:10 
GeneralRe: Server-side code called multiple times when page valid Pin
Bryian Tan22-Jun-10 17:29
professionalBryian Tan22-Jun-10 17:29 
GeneralA couple of fixes Pin
prodriguez132-Nov-09 2:16
prodriguez132-Nov-09 2:16 
GeneralRe: A couple of fixes Pin
Bryian Tan3-Nov-09 4:34
professionalBryian Tan3-Nov-09 4:34 
QuestionHow to do the same for Image Button! Pin
Member 245269829-Oct-09 22:04
Member 245269829-Oct-09 22:04 
AnswerRe: How to do the same for Image Button! Pin
Bryian Tan30-Oct-09 7:29
professionalBryian Tan30-Oct-09 7:29 
GeneralDouble Validation with Validation Summry Control Pin
Adeel Alvi8-Oct-09 0:01
Adeel Alvi8-Oct-09 0:01 
GeneralRe: Double Validation with Validation Summry Control Pin
Bryian Tan9-Oct-09 17:26
professionalBryian Tan9-Oct-09 17:26 
GeneralRe: Double Validation with Validation Summry Control Pin
Adeel Alvi9-Oct-09 21:09
Adeel Alvi9-Oct-09 21:09 
GeneralRe: Double Validation with Validation Summry Control Pin
Bryian Tan12-Oct-09 8:42
professionalBryian Tan12-Oct-09 8:42 
GeneralI have ImageButton with validation group Pin
dilipsss1-Oct-09 2:00
dilipsss1-Oct-09 2:00 
GeneralRe: I have ImageButton with validation group Pin
Bryian Tan4-Oct-09 18:57
professionalBryian Tan4-Oct-09 18:57 
QuestionDouble Validation Pin
tomsmbox-codeproject24-Aug-09 14:15
tomsmbox-codeproject24-Aug-09 14:15 
AnswerRe: Double Validation Pin
Bryian Tan27-Aug-09 7:01
professionalBryian Tan27-Aug-09 7:01 
GeneralExcellent in its simplicity Pin
Rory van der Berg14-Aug-09 9:31
Rory van der Berg14-Aug-09 9:31 

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

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.