ASP Button with Custom Validator - if True fire Javascript AND Code Behind

alright
alright used Ask the Experts™
on
What I want to accomplish: I have a Button and a Checkbox on a page. If the user clicks the button without first checking the box, they receive an alert box and no postback occurs.

If the checkbox is checked and the user clicks the button, the button should be immediately disabled to prevent subsequent clicks (the button sends an email - don't want it being spammed).

The issue: I have a Custom Validator set up to check if the Box is checked. This works great, no check - no post. Check - post and the Button_Click event is fired; however, this only works if I don't include the code to disable the button.

By firing the Javascript code to disable the button, only the Javascript is ran - the code-behind in the _Click event is not ran. Code below.

I've tried placing the Disable code inside an Else{} statement within the ValidateCheck() function. I've tried invoking the Click method of the Button after the Disable javascript is ran via document.getElementById("<%= btnConfirmation.ClientID %>").click();.

Whatever I seem to try I can get one part working but break another. This is rudimentary I'm sure - any help is appreciated. Thx
html:

<asp:Button ID="btnConfirmation" runat="server" Text="Confirm" onclick="btnConfirmation_Click" ValidationGroup="vgConfirmation" />


javascript:

function ValidateChecked(oSrc, args) {
            if (document.getElementById('<%= cbConfirmation.ClientID %>').checked == false) {
                alert("Check the box etc");
                args.IsValid = false;
            }


javascript i'm using to disable the button on checked click:

                var objName = '<%= btnConfirmation.ClientID %>';
                document.getElementById(objName).disabled = true;

Open in new window

Comment
Watch Question

Do more with

Expert Office
EXPERT OFFICE® is a registered trademark of EXPERTS EXCHANGE®
Miguel OzSenior Software Engineer
Top Expert 2009

Commented:
Check:
http://forums.asp.net/t/1324613.aspx/1?How+to+call+javascript+and+C+function+on+HTML+Button+Click
http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.button.onclientclick.aspx

You can define:
this.Button1.Attributes.Add("onClick", "IsChecked()");

Your click code behind will execute only if IsChecked returns true
function IsChecked() {
            if (document.getElementById('<%= cbConfirmation.ClientID %>').checked == false) {
                return false;
            }
            return true;
}    

Author

Commented:
Hi mas_oz2003,

The issue is not with the Validation - that is working great. My code-behind fires no problem when the Checkbox is checked and the Confirm button is clicked. If the Checkbox is not checked and the Confirm button is clicked - the user receives an alert box simply stating they need to Check the box first - no code-behind is fired. The issue is that I want to squeeze in additional client-side script to immediately disable the Confirm button after the Validation returns true, but before the Code-behind firing, in order to prevent the button from being clicked again while the code-behind is being ran (it can take 5-10 seconds to complete).

Commented:
In code behind you can use  CheckBox1.Attributes.Add("onclick", "return false;"); to make it read only or you can make it's disabled property false. CheckBox1.Enabled = False;

on the client side you can do this to hide it:

function hideDiv() {
if (document.getElementById) {
document.getElementById('div').style.visibility = 'hidden';
}

or you can refer to this:
http://stackoverflow.com/questions/5088352/enable-disable-asppanel-and-all-its-control-using-javascript

to disable it using jquery or javascript

Author

Commented:
Sorry, I don't think I am being clear. Full code below, please consider the following.

This works pretty much exactly how I would like it to - Check the box and click Confirm - you will see the Confirm button is immediately disabled while post-back occurs; HOWEVER, the code-behind is not actually being ran [evidenced by inserting breakpoints, or just noting that the label text is never updated].

If the code-behind in the below situation ran my problem would be solved.

Thanks again

[Default.aspx:]

<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
<head runat="server">
    <title>Junk</title>
    <script type="text/javascript">
        function ValidateChecked(oSrc, args) {
            if (document.getElementById('<%= cbConfirmation.ClientID %>').checked == false) {
                alert("Confirmation UNSUCCESSFUL. Check the box above before clicking Confirm.");
                args.IsValid = false;
            }
        }
        function Disable() {
            if (document.getElementById('<%= cbConfirmation.ClientID %>').checked == true) {
                var objName = '<%= btnConfirmation.ClientID %>';
                document.getElementById(objName).disabled = true;
                return true;
            }
        }     
    </script>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <asp:CheckBox ID="cbConfirmation" runat="server" Text="If this is not checked, there will be no post-back." />
        <br />
        <asp:Button ID="btnConfirmation" runat="server" Text="Confirm" OnClientClick="javascript:Disable()"
            OnClick="btnConfirmation_Click" ValidationGroup="vgConfirmation" />
        <br />
        <asp:CustomValidator ID="cvConfirmation" ClientValidationFunction="ValidateChecked"
            runat="server" ErrorMessage="There has been an error with your submission." ValidationGroup="vgConfirmation"></asp:CustomValidator>
        <br />
        <asp:Label ID="lblConfirmation" runat="server" ForeColor="Red"></asp:Label>
    </div>
    </form>
</body>
</html>


[Default.aspx.cs:]

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Collections;

public partial class _Default : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {

    }
    protected void btnConfirmation_Click(object sender, EventArgs e)
    {
        ArrayList a = new ArrayList();
        for (int i = 0; i < 10000; i++)
        {
            for (int j = 0; j < 1000; j++)
            {
                a.Add(i.ToString() + j.ToString());
            }
        }

        lblConfirmation.Text = "Confirmation submitted. Thank you.";
    }
}

Open in new window

Commented:
here you go:

ASPX:

        <asp:CheckBox ID="cbConfirmation" runat="server" 
            Text="If this is not checked, there will be no post-back." 
             />
        <br />
        <asp:Button ID="btnConfirmation" runat="server" Text="Confirm"
            OnClick="btnConfirmation_Click" />
        <br />
        <asp:Label ID="lblConfirmation" runat="server" ForeColor="Red"></asp:Label>

CODEBEHIND:

 protected void Page_Load(object sender, EventArgs e)
        {
            btnConfirmation.Attributes.Add("onclick", GetLockButtonJscript(this.Page, btnConfirmation, "Submit", new ArrayList(), ""));

        }

        protected void btnConfirmation_Click(object sender, EventArgs e)
        {
            if (cbConfirmation.Checked)
            {
                ArrayList a = new ArrayList();
                for (int i = 0; i < 10000; i++)
                {
                    for (int j = 0; j < 1000; j++)
                    {
                        a.Add(i.ToString() + j.ToString());
                    }
                }

                lblConfirmation.Text = "Confirmation submitted. Thank you.";
            }
            else
            {
                this.ClientScript.RegisterStartupScript(this.GetType(), "showAlert", "alert('Confirmation UNSUCCESSFUL. Check the box above before clicking Confirm.');", true);
            }
        }

        public static string GetLockButtonJscript(Page p, Button btn, string disabledText, ArrayList aCol, string customScript)
        {

            disabledText = disabledText == "" ? "Processing..." : disabledText; disabledText = disabledText.Replace("'", "");


            StringBuilder sb = new StringBuilder();

            if (btn.CausesValidation && p.Validators.Count > 0 && btn != null)
            {

                sb.Append("if (typeof(Page_ClientValidate) == 'function') { "); sb.Append("if (Page_ClientValidate('" + btn.ValidationGroup + "') == false) { return false; }} ");
            }

            if (!String.IsNullOrEmpty(customScript))
            {

                sb.Append(customScript);

            }

            PostBackOptions opt = new PostBackOptions(btn, "", "", false, true, true, true, true, btn.ValidationGroup);
            sb.Append(p.ClientScript.GetPostBackEventReference(opt));

            sb.Append(";");
            sb.Append("this.disabled='true';this.value='" + disabledText + "';");

            foreach (Control c in aCol)
            {

                if (c is Button)
                {

                    sb.Append("" + c.UniqueID + ".disabled='true';");
                }

            }

            return sb.ToString();


        }

Open in new window

Do more with

Expert Office
Submit tech questions to Ask the Experts™ at any time to receive solutions, advice, and new ideas from leading industry professionals.

Start 7-Day Free Trial