5

属性を実装するASP.NETユーザーコントロールがありValidationPropertyます。この属性を使用するRequiredFieldValidatorと、カスタムコントロールにを使用できますが、検証時に、クライアント側のJavaScriptベースの検証を使用するのではなく、完全なポストバックが発生します。

これを防ぎ、カスタムバリデーターを使用せずにクライアント側の検証を有効にする方法はありますか?

これは私のUserControlがどのように見えるかです。

<%@ Control Language="C#" AutoEventWireup="true" CodeBehind="ucBooleanRadio.ascx.cs" Inherits="MyCompany.Web.UserControls.ucBooleanRadio" %>

<div class="BooleanRadio">
    <input runat="server" id="radTrue" type="radio" name="BooleanRadio" value="True" /> Yes
    <input runat="server" id="radFalse" type="radio" name="BooleanRadio" value="False" /> No
</div>

[ValidationProperty("Checked")]
public partial class ucBooleanRadio : System.Web.UI.UserControl
{
    public Nullable<bool> Checked
    {
        get
        {
            if (radTrue.Checked || radFalse.Checked)
                return radTrue.Checked;
            else
                return null;
        }
        set
        {
            radTrue.Checked = value != null ? value.Value : false;
            radFalse.Checked = value != null ? !value.Value : false;                    
        }
    }
}

そして、これはそれがどのように使用されているかです

<uc1:ucBooleanRadio ID="ucAgree" runat="server" />
<asp:RequiredFieldValidator ID="RequiredFieldValidator6" runat="server" CssClass="Validator" Display="Dynamic" ControlToValidate="ucAgree" InitialValue="" ErrorMessage="You must agree to continue."></asp:RequiredFieldValidator>

Page.Validate();
if (Page.IsValid)
{
    //Do stuff
}
4

4 に答える 4

1

単純なクライアント側の検証では、検証する値に対応する名前の入力要素が必要です。あなたの場合にそれがどのように行われるかの例:

<div class="BooleanRadio">
    <% radTrue.Attributes["onclick"] = "document.getElementsByName('" + UniqueID + "')[0].value='+'"; %>
    <input runat="server" id="radTrue" type="radio" name="BooleanRadio" value="True" /> Yes
    <% radFalse.Attributes["onclick"] = "document.getElementsByName('" + UniqueID + "')[0].value='-'"; %>
    <input runat="server" id="radFalse" type="radio" name="BooleanRadio" value="False" /> No
    <input name="<%= UniqueID %>" type="hidden" value="<%= radTrue.Checked? "+" : radFalse.Checked? "-" : "" %>" />
</div>
于 2012-06-21T05:56:15.850 に答える
1

OK、ASP.NETフィールドバリデーターのアーキテクチャをかなり掘り下げて、上記のポスターからいくつかのガイダンスを受け取った後、私はついに解決策を見つけました。

基本的に、上記の答えは、いくつかの変更を除いて正しいです。

まず、非表示のテキストに設定されるIDは、Nameフィールドではなくフィールドにある必要がありIDます。さらに、[非表示]フィールド内に入力されるIDはPage.UniqueID、ではなく、Page.ClientID問題のUserControlのIDである必要があります。

これは、バリデーターを含むページが読み込まれると、ASP.NETフレームワークによって次の関数が呼び出されるためです。

function ValidatorHookupControlID(controlID, val) {
    if (typeof (controlID) != "string") {
        return;
    }
    var ctrl = document.getElementById(controlID); //NOTE THIS LINE
    if ((typeof (ctrl) != "undefined") && (ctrl != null)) {
        ValidatorHookupControl(ctrl, val);
    }
    else {
        val.isvalid = true;
        val.enabled = false;
    }
}

フレームワークが行おうとしているのは、必須フィールドバリデーター(実際には)で設定されてIDいるプロパティと同じコントロールを取得することです。次に、検証関数でこのコントロールを使用します(RequiredField、Compare、Regexなど)。そのようなコントロールが見つかった場合は、バリデーターを有効にし、その値に対して検証を実行します。そうでない場合は、単にバリデーターを無効に設定します。ControlToValidatePage.ClientID

結局、私のコードは次のようになります。

<%@ Control Language="C#" AutoEventWireup="true" CodeBehind="ucBooleanRadio.ascx.cs" Inherits="MyCompany.Web.UserControls.ucBooleanRadio" %>

<input id="<% =this.ClientID %>" type="hidden" value="" />
<asp:RadioButton runat="server" ID="radTrue" Text="Yes" GroupName="radio" />
<asp:RadioButton runat="server" ID="radFalse" Text="No" GroupName="radio" />    

<script language="javascript" type="text/javascript">
    $(function (e) {
        $("#<% =radTrue.ClientID %>").click(function (e) {
            $("#<% =this.ClientID %>").val("true");
        });
        $("#<% =radFalse.ClientID %>").click(function (e) {
            $("#<% =this.ClientID %>").val("false");
        });
    });
</script>

そして、背後にあるコードは変更されていません。うまくいけば、これは同じ問題に遭遇した人に何が起こっているのかという謎のいくつかを説明しています。

于 2012-06-27T03:23:39.740 に答える
1

結局のところ、ASP.NETは要素タグをイベントで気にしません。
検証コードを調べたところ、これが見つかりました

function ValidatorGetValue(id) {
    var control;
    control = document.getElementById(id);
    if (typeof(control.value) == "string") {
        return control.value;
    }
    return ValidatorGetValueRecursive(control);
}

それで

<div class="BooleanRadio" id="<%= ClientID %>" value="<%= radTrue.Checked? "true" : radFalse.Checked? "false" : "" %>">
    <% radTrue.Attributes["onclick"] = "document.getElementById('" + ClientID + "').value='true'"; %>
    <% radFalse.Attributes["onclick"] = "document.getElementById('" + ClientID + "').value='false'"; %>
    <input runat="server" id="radTrue" type="radio" name="BooleanRadio" value="True" /> Yes
    <input runat="server" id="radFalse" type="radio" name="BooleanRadio" value="False" /> No
</div>

実際に機能:\します

<div class="BooleanRadio" id="<%= ClientID %>">
    <input runat="server" id="radTrue" type="radio" name="BooleanRadio" value="True" /> Yes
    <input runat="server" id="radFalse" type="radio" name="BooleanRadio" value="False" /> No
</div>

そして、自動フックするイベントがあります-検証された要素(ClientIDを持つもの)とその子は、検証を自動的に引き起こすように配線されています(ValidatorHookupControlを見てください)。
その結果、次の結果になる可能性があり
ます。1.ユーザーが何かを実行する
2.検証が実行される
3.検証する値が更新される(検証後!)
divに値がある最初の例はこのように動作します。

于 2012-06-27T08:25:13.257 に答える
0

マキシム、私はちょうど同様の問題に取り組んでいます。

JavaScriptは必要ないことがわかりました。バリデーターは、設定されている「値」を探してコントロールを自動的に繰り返し処理します。

HTMLではなくサーバー側のラジオボタンを使用している必要があります

CompositeControlsを使用している場合は、自動的に機能します

Webユーザーコントロール(ascxファイル)を使用している場合、コントロールはIDでラップされないため、次のコードをコントロールに追加する必要があります。

<div id='<%=ClientID %>'>

   Your radio button controls here...

</div>

編集:簡単なサンプルコードをアップロードしました。お役に立てれば! サンプルコード

于 2013-01-08T10:05:38.260 に答える