jQuery Validation - 一个 asp.net 表单上的多个提交按钮,不同的验证组?
Posted
技术标签:
【中文标题】jQuery Validation - 一个 asp.net 表单上的多个提交按钮,不同的验证组?【英文标题】:jQuery Validation - Multiple submit buttons on one asp.net form, different validation groups? 【发布时间】:2010-12-08 20:14:14 【问题描述】:我有一个带有登录部分和注册部分的 asp.net 表单。有两个提交按钮对应于相应的部分,登录或注册。我正在使用 jquery 验证,但是我找不到像使用普通 asp.net 验证那样指定验证组的方法。当我点击注册按钮时,现在它要求填写登录字段。有人对此有任何想法吗?谢谢!
【问题讨论】:
【参考方案1】:我猜你正在使用这个验证插件:JQuery Validation。该插件使用表单标记作为验证组,因此要完成您想要的操作,您需要根据用户按下的按钮删除规则。此外,您需要为验证失败然后用户决定单击另一个按钮的情况添加规则。
这是一个例子:
$(document).ready(function()
$("#form").validate(
invalidHandler: addRules
);
addRules();
$("#submit1").click(function()
$(".group2").each(function()
$(this).rules("remove");
);
);
$("#submit2").click(function()
$(".group1").each(function()
$(this).rules("remove");
);
);
);
var addRules = function()
$("#input1").rules("add", required:true);
$("#input2").rules("add", required:true);
这种方法允许您为每个输入添加一个类属性(group1 或 group2),作为验证组。
【讨论】:
要是这么简单就好了。在 asp.net 中,您可能只有一个 @Jataro 你知道如何为一个提交按钮禁用 jquery 验证吗?我的表单上有两个提交按钮:提交和取消。我需要禁用“取消”按钮的验证。【参考方案2】:您可以使用以下库,而不必编写特定于页面的代码来解决此问题:
https://github.com/bbraithwaite/JQueryValidationForWebForms
NB 源代码在下方,但 Github 链接将始终具有最新的源代码。
它位于 jQuery Validation Framework 之上,并通过使用类名作为约定来抽象出这个问题。
您注册验证事件的方式与 jQuery 验证相同(只是名称不同):
$(function()
$("#aspForm").validateWebForm();
);
.ASPX 示例
具有两个验证组的基本 .aspx 示例可能如下所示。您只需包装每个逻辑部分并给它一个“form”类名,并在应该触发验证事件的操作上添加类“submit”:
<fieldset class="form">
<div class="something">
<ul></ul>
</div>
<legend>Sign Up</legend>
<p>
<asp:Label ID="uiFirstName" runat="server" AssociatedControlID="uxFirstName" Text="First name:"></asp:Label>
<asp:TextBox ID="uxFirstName" runat="server" CssClass="required"></asp:TextBox>
</p>
<p>
<asp:Button ID="uxRegister" runat="server" Text="Sign Up" CssClass="submit signup" />
<asp:Button ID="uxCancelRegister" runat="server" Text="Cancel" />
</p>
</fieldset>
<fieldset class="form">
<legend>Login</legend>
<p>
<asp:Label ID="uiUserName" runat="server" AssociatedControlID="uxUserName" Text="User name:"></asp:Label>
<asp:TextBox ID="uxUserName" runat="server" CssClass="required email"></asp:TextBox>
</p>
<p>
<asp:Button ID="uxLogin" runat="server" Text="Login" CssClass="submit login" />
<asp:Button ID="uxCancelSignUp" runat="server" Text="Cancel" />
</p>
</fieldset>
源代码
(function ($)
$.extend($.fn,
validateWebForm: function (options)
var form = $(this[0]),
formExists = (form.length) && form.is('form');
if (formExists)
if (!options)
options = ;
// stop the validation from firing on the form submit
options.onsubmit = false;
// wire up the default jquery validation event to the form
this.validate(options);
// Select any input[type=text] elements within a validation group
// and attach keydown handlers to all of them.
$('.form :text').keydown(function (event)
// Only execute validation if the key pressed was enter.
if (event.keyCode == 13)
$(event.currentTarget).closest(".form").find(".submit").click();
);
// find the submit buttons and override the click event
form.getSumbitControls().click(this.validateAndSubmit);
return this;
return undefined;
,
getSumbitControls: function ()
return $(this).find('.form .submit');
,
getValidationContainer: function (submitControl)
return $(submitControl).closest('.form');
,
validateAndSubmit: function (event)
// Ascend from the button that triggered this click event
// until we find a container element flagged with
// .validationGroup and store a reference to that element.
var group = $(this).getValidationContainer(event.currentTarget),
isValid = true;
// Descending from that .form element, find any input
// elements within it, iterate over them, and run validation on
// each of them.
group.find(':input').each(function (i, item)
if (!$(item).valid())
isValid = false;
);
// If any fields failed validation, prevent the button's click
// event from triggering form submission.
if (!isValid)
event.preventDefault();
);
)(jQuery);
Nuget 用户
PM> 安装包 JQuery.Validation.WebForms
这是从阅读 Dave Ward 的以下帖子演变而来的:
http://encosia.com/asp-net-webforms-validation-groups-with-jquery-validation/
【讨论】:
【参考方案3】:您始终可以使用一些简单的 jquery/javascript 来删除 asp 按钮 OnClientClick 上的“validate[required]”类,然后将其重新添加到其他按钮 OnClientClick 上,这比更改验证引擎文件或替换它们更容易。这方面的一个例子是:
<div id="Login">
<asp:TextBox ID="txtUser" runat="server" CssClass="validate[required]"></asp:TextBox>
<asp:TextBox ID="txtPass" runat="server" CssClass="validate[required]"></asp:TextBox>
<asp:Button ID="btnLogin" runat="server" OnClientClick="disableReg();" OnClick="btnLogin_Click" />
</div>
<div id="Register">
<asp:TextBox ID="txtName" runat="server" CssClass="validate[required]"></asp:TextBox>
<asp:TextBox ID="txtEmail" runat="server" CssClass="validate[required]"></asp:TextBox>
<asp:Button ID="btnReg" runat="server" OnClientClick="disableLogin();" OnClick="btnReg_Click" />
</div>
javascript 将是:
function disableReg()
$('#<%=txtName.ClientID%>').removeClass("validate[required]");
$('#<%=txtEmail.ClientID%>').removeClass("validate[required]");
$('#<%=txtUser.ClientID%>').addClass("validate[required]");
$('#<%=txtPass.ClientID%>').addClass("validate[required]");
return true;
function disableLogin()
$('#<%=txtUser.ClientID%>').removeClass("validate[required]");
$('#<%=txtPass.ClientID%>').removeClass("validate[required]");
$('#<%=txtName.ClientID%>').addClass("validate[required]");
$('#<%=txtEmail.ClientID%>').addClass("validate[required]");
return true;
【讨论】:
【参考方案4】:跟踪验证对象并直接删除/替换规则。适用于 v1.13.0
var validation = $('#form1').validate(); //Keep track of validation object
//Rule set 1
var validationRulesLogin =
headerEmail:
required: true,
email: true
,
headerPassword: "required"
;
var validationMessagesLogin =
headerEmail:
required: "Please enter your email address.",
email: "Not a valid email address."
,
headerPassword: "Please enter your password."
;
//Rule set 2
var validationRulesSignup =
signupEmail:
required: true,
email: true
,
signupPassword: "required",
signupPassword2:
equalTo: "#phBody_txtNewPassword"
;
var validationMessagesSignup =
signupEmail:
required: "Please enter your email address.",
email: "Not a valid email address."
,
signupPassword: "Please enter your password.",
signupPassword2: "Passwords are not the same."
;
//Toggle rule sets on form focus, button click or other event.
function validatingLoginForm()
validation.resetForm();
validation.settings.rules = validationRulesLogin;
validation.settings.messages = validationMessagesLogin;
function validationSignupForm()
validation.resetForm();
validation.settings.rules = validationRulesSignup;
validation.settings.messages = validationMessagesSignup;
【讨论】:
【参考方案5】:如果您使用不显眼的 jquery 验证,或者您可以使用这个:
$(document).ready(function ()
var formValidator = $("form").validate();
$("#btnLogin").click(function ()
formValidator.settings.ignore = "#registerSection *";
);
$("#btnRegister").click(function ()
formValidator.settings.ignore = "#loginSection *";
);
);
【讨论】:
【参考方案6】:通过将特殊的 CSS 类名称附加到代表服务器端验证控件的 html 元素上,使 ASP.NET 服务器验证逻辑可用于客户端/jQuery。
生成的 CSS 类名称将代表验证组。因此,例如,某些文本框将被标记为一个验证组的类名,而其他文本框将被标记为不同的验证组。
例如,在页面 PreRender 处理程序中或在渲染页面之前编写并调用此 C# 函数,以便为服务器控件注入特殊的 CSS。
/// <summary>
/// Makes the server validation logic knowledge available to the client side
/// by appending css class names to validators and html elements being validated.
/// The generated css classes can be targeted by jQuery in the DOM.
/// </summary>
/// <param name="cssPrefixValidator">prefix string for validator css names</param>
/// <param name="cssPrefixTarget">prefix string for target element css names</param>
/// <remarks>
/// The css prefix arguments to this function help distinguish between what is a
/// validation control and what is an html element being targeted by said validation control.
/// </remarks>
///
void TagValidationWithCss(string cssPrefixValidator, string cssPrefixTarget)
List<string> valClasses = new List<string>();
List<string> targetClasses = new List<string>();
// iterate over validator server controls
foreach (BaseValidator val in Page.Validators)
// keep a unique list of generated validator css class names
string classnameVal = cssPrefixValidator + val.ValidationGroup;
if (!valClasses.Contains(classnameVal))
valClasses.Add(classnameVal);
// ..and mark the validator element with the generated css class name
val.CssClass += (string.IsNullOrEmpty(val.CssClass) ? "" : " ") + classnameVal;
// keep a unique list of generated target element css class names
string classnameTarg = cssPrefixTarget + val.ValidationGroup;
if (!targetClasses.Contains(classnameTarg))
targetClasses.Add(classnameTarg);
// ..and mark the target element with the generated css class name
Control target = FindControl(val.ControlToValidate);
if (target is HtmlControl)
((HtmlControl)target).Attributes["class"] += (string.IsNullOrEmpty(val.CssClass) ? "" : " ") + classnameTarg;
else if (target is WebControl)
((WebControl)target).CssClass += (string.IsNullOrEmpty(val.CssClass) ? "" : " ") + classnameTarg;
// output client script having array of validator css names representing validation groups
string jscriptVal = string.Format("<script>window['1'] = ['0'];</script>", string.Join("','", valClasses.ToArray()), cssPrefixValidator);
ClientScript.RegisterStartupScript(this.GetType(), "val", jscriptVal);
//output client script having array of html element class names representing validation groups
string jscriptTarg = string.Format("<script>window['1'] = ['0'];</script>", string.Join("','", targetClasses.ToArray()), cssPrefixTarget);
ClientScript.RegisterStartupScript(this.GetType(), "targ", jscriptTarg);
该函数在服务端Page中调用:
protected override void OnPreRender(EventArgs e)
base.OnPreRender(e);
TagValidationWithCss("validator-", "target-");
ASPX 页面的声明性语法可能有两个部分,如下所示:
<div>
Login Section
<asp:TextBox ValidationGroup="vg1" ID="TextBox1" runat="server"></asp:TextBox><asp:TextBox
ValidationGroup="vg1" ID="Textbox2" runat="server"></asp:TextBox><asp:Button ID="Button1"
ValidationGroup="vg1" runat="server" Text="Button" />
<asp:RequiredFieldValidator ID="RequiredFieldValidator3" runat="server" ControlToValidate="TextBox1"
ErrorMessage="RequiredFieldValidator" ValidationGroup="vg1"></asp:RequiredFieldValidator>
<asp:RequiredFieldValidator ID="RequiredFieldValidator4" runat="server" ControlToValidate="Textbox2"
ErrorMessage="RequiredFieldValidator" ValidationGroup="vg1"></asp:RequiredFieldValidator>
<hr />
Registration Section
<asp:TextBox ValidationGroup="vg2" ID="TextBox4" runat="server"></asp:TextBox><asp:TextBox
ValidationGroup="vg2" ID="Textbox5" runat="server"></asp:TextBox><asp:Button ID="Button3"
ValidationGroup="vg2" runat="server" Text="Button" />
</div>
现在转到渲染页面查看结果.....
页面 HTML 源代码包含一组生成的 CSS 名称表示验证组,一组用于验证器 (validator-),另一组用于验证目标 (target-)
<script>window['validator-'] = ['validator-vg1','validator-vg2'];</script>
<script>window['target-'] = ['target-vg1','target-vg2'];</script>
这些 CSS 名称也会呈现在 html 元素上。注意此处文本框上的“target-vg1”CSS 类,代表验证组 #1。文本框代表页面上的登录屏幕/界面(两个 UI 部分之一):
<input name="TextBox1" type="text" id="TextBox1" class=" target-vg1" /><input name="Textbox2" type="text" id="Textbox2" class=" target-vg1" /><input type="submit" name="Button1" value="Button" onclick="javascript:WebForm_DoPostBackWithOptions(new WebForm_PostBackOptions("Button1", "", true, "vg1", "", false, false))" id="Button1" />
第二组文本框位于同一个 ASP.NET 页面(在同一个 ASP.NET 表单中),代表用户注册屏幕/界面(第二个 UI 部分)。请注意,这些文本框通过 css 类使用名为“target-vg2”的不同验证组进行标记。
<input name="TextBox4" type="text" id="TextBox4" class=" target-vg2" /><input name="Textbox5" type="text" id="Textbox5" class=" target-vg2" /><input type="submit" name="Button3" value="Button" onclick="javascript:WebForm_DoPostBackWithOptions(new WebForm_PostBackOptions("Button3", "", true, "vg2", "", false, false))" id="Button3" />
因此,我们将特殊的 Css 名称注入到 ASP.NET 流中,而不会中断或破坏它。
最终,这个专门的输出允许您针对它编写自定义脚本(即使用 jQuery)来获取那些特殊的 CSS 类名称并区分客户端的验证组。
这个简单的示例会提醒客户端验证组的名称,以证明它们被看到和知道。哇!
<script>
// Tell the CSS names of the available validation groups assigned to target elements.
var strGroups = 'css validation groups are: ' + window['target-'].join(', ');
alert(strGroups);
</script>
jQuery 也可以用来定位特殊的 css 类。
这并不涵盖所有情况。它可能真的出去吃午饭,但做起来很有趣。服务器端和客户端代码需要根据个人或项目的喜好进行调整。
(您还希望依靠这样一个事实,即较新的浏览器可以使用“class”属性将多个 CSS 类应用于一个元素,方法是使用空格分隔类名,例如 - class="vg1 animated bright myclass your class"。这允许生成的 css 类名将附加在现有类名之后而不覆盖它们。)
【讨论】:
方式方式太复杂了。我什至不想为如此简单但不需要复杂的东西考虑服务器端代码。以上是关于jQuery Validation - 一个 asp.net 表单上的多个提交按钮,不同的验证组?的主要内容,如果未能解决你的问题,请参考以下文章