- PR -

[ASP.NET/C#]JavaScriptからのポストバックについて

投稿者投稿内容
Jitta
ぬし
会議室デビュー日: 2002/07/05
投稿数: 6267
お住まい・勤務地: 兵庫県・海手
投稿日時: 2004-01-23 16:51
引用:

夏姫☆さんの書き込み (2004-01-23 15:54) より:

 調べていたMSのページValidatorが記載されていたのですが、理解できていませんでした。
 MSの解説は難解だと思えて仕方がありません。


 MSDNを読むのは頭の格闘技です!?知力、体力、時の運(検索にかかる言葉を思いつくか)が必要です??


 で、バリデータですが、「検証対象は適当」なんて書きましたが、よく考えると検証対象コントロールからフォーカスアウトすると検証が行われます。ですから、テキストボックスの方を指定するのが妥当かと思います。
 また、ボタンをクリック(明示的なsubmit)しても検証が行われます。ボタンに検証を引き起こすプロパティがあるので、「このボタンでは検証したくない」ときは、そのプロパティをFalseにしてください。
ほむら
ぬし
会議室デビュー日: 2003/02/28
投稿数: 583
お住まい・勤務地: 東京都
投稿日時: 2004-01-23 16:57
>MSDNを読むのは頭の格闘技です!?知力、体力、時の運(検索にかかる言葉を思いつくか)が必要です??
あとは、リンク切れになっていないことを祈るのみ(涙
taku
ぬし
会議室デビュー日: 2002/11/12
投稿数: 918
お住まい・勤務地: 墨田区→中野区
投稿日時: 2004-01-23 17:07
引用:

夏姫☆さんの書き込み (2004-01-23 15:54) より:
ほむらさん
 確かにおっしゃるとおりですね。
 JSP&Servletの習慣!?で、つい、データチェックはクライアント・サイドでと
 思ってしまいました。
 今回はサーバへのアクセスを必要時のみとしたいので、クライアント・サイドでの
 チェックを採用しますが、サーバ・サイドでのチェックも選択肢のひとつに
 考えたいと思います。


これって、WEB全般の話であって、.NETやJava固有の問題ではないですよね。
一般の消費者に提供するサービスとかだと、
JavaScript等でクライアントでチェックした方が、
サーバーでのチェックより喜ばれたりしますので、
クライアント側でチェックするのかサーバー側でチェックするのかは、
ケースバイケースですよね。
それにクライアントで全てのチェックができるわけではないですしね。
夏姫☆
会議室デビュー日: 2003/12/11
投稿数: 15
投稿日時: 2004-01-26 18:51
こんばんは。
金曜日からCustomValidatorを用いた方法でチャレンジしてみましたが、
どうも思わしくありません。
悩みつづけましたが、原因が分からず困っています。
ご教授いただけたらと思い、再投稿します。

Button1のCausesValidatio="false"に設定しておき、
TextBox1をCustomValidatorの対象に設定します。
そして、TextBox1は未入力、Dropdownlist1は"99"以外を選択して
Button1を押下すると、サーバーエラーが発生しました。

◆エラーメッセージ
Page.IsValid は、評価がなされるまで呼び出せません。
コントロールのイベント ハンドラで、CausesValidation=True 設定で、
または Page.Validate の呼び出しの後で、クエリーされなければ
なりません。
説明 : 現在の Web 要求を実行中に、ハンドルされていない例外が
発生しました。エラーに関する詳細および例外の発生場所については、
スタック トレースを参照してください。

スタック トレース:
[HttpException (0x80004005): Page.IsValid は、評価がなされる
まで呼び出せません。コントロールのイベント ハンドラで、
CausesValidation=True 設定で、または Page.Validate の呼び出しの
後で、クエリーされなければなりません。 ]


Button1のCausesValidatio="true"であれば当然のことながら
チェックは行われず、ポストバックされてしまいます。

MSの解説等ひたすら調べたのですが、行き詰まってしまいました。

現状のソースは↓です。(長くてすみません。)

◆WebForm1.aspx
<HTML>
 <HEAD>
  <title>WebForm1</title>
 </HEAD>
 <body MS_POSITIONING="GridLayout">
  <form id="Form1" method="post" runat="server">
   <h3>入力チェックテスト</h3>
   <asp:label id="Label1" style="Z-INDEX: 103; LEFT: 59px;
    POSITION: absolute; TOP: 139px" runat="server"
    Width="236px"></asp:label>
   <asp:textbox id="TextBox1" style="Z-INDEX: 101;
    LEFT: 55px; POSITION: absolute; TOP: 85px"
    runat="server"></asp:textbox>
   <asp:dropdownlist id="DropDownList1" style="Z-INDEX: 104;
    LEFT: 235px; POSITION: absolute; TOP: 86px" runat="server"
    Width="161px">
   <asp:ListItem Value="" Selected="True">選んでね</asp:ListItem>
    <asp:ListItem Value="1">Value 1</asp:ListItem>
    <asp:ListItem Value="2">Value 2</asp:ListItem>
    <asp:ListItem Value="3">Value 3</asp:ListItem>
    <asp:ListItem Value="99">Value 99</asp:ListItem>
   </asp:dropdownlist>
   <asp:button id="Button1" style="Z-INDEX: 102; LEFT: 442px;
    POSITION: absolute; TOP: 85px" onclick="ValiDateBtn_OnClick"
    runat="server" Width="71px" Text="チェック"></asp:button>
   <asp:customvalidator id="InputCheck" runat="server"
    ControlToValidate="TextBox1"
    ClientValidationFunction="DataCheck"
    ErrorMessage="データが入力されていません" ForeColor="red"
    style="Z-INDEX: 105; LEFT: 57px; POSITION: absolute;
    TOP: 49px"></asp:customvalidator>
  </form>
 </body>
</HTML>
<SCRIPT language="JavaScript">
<!--
 function DataCheck(source, arguments) {
  if ( ( document.Form1.DropDownList1.value != "99" )
   && ( arguments.value == "" ) ) {
    arguments.IsValid = false;
  } else {
    arguments.IsValid = true;
  }
 }
//-->
</SCRIPT>

◆WebForm1.aspx
namespace WebAplTest1
{
 public class WebForm1 : System.Web.UI.Page
 {
  protected System.Web.UI.WebControls.TextBox TextBox1;
  protected System.Web.UI.WebControls.Button Button1;
  protected System.Web.UI.WebControls.CustomValidator InputCheck;
  protected System.Web.UI.WebControls.DropDownList DropDownList1;
  protected System.Web.UI.WebControls.Label Label1;

  private void Page_Load(object sender, System.EventArgs e)
  {
  }

  public void ValiDateBtn_OnClick(object sender, System.EventArgs e)
  {
   if ( Page.IsValid )
   {
    Label1.Text = "Check OK !!";
    Label1.ForeColor = Color.FromName( "Black" );
   }
   else
   {
    // このロジックはとおらないはず
    Label1.Text = "Check Error !!";
    Label1.ForeColor = Color.FromName( "Red" );
   }
  }
 }
}
Jitta
ぬし
会議室デビュー日: 2002/07/05
投稿数: 6267
お住まい・勤務地: 兵庫県・海手
投稿日時: 2004-01-26 20:16
引用:

夏姫☆さんの書き込み (2004-01-26 18:51) より:


Button1のCausesValidation="false"に設定しておき、
TextBox1をCustomValidatorの対象に設定します。

Button1のCausesValidation="true"であれば当然のことながら
チェックは行われず、ポストバックされてしまいます。

◆エラーメッセージ
Page.IsValid は、評価がなされるまで呼び出せません。
コントロールのイベント ハンドラで、CausesValidation=True 設定で、
または Page.Validate の呼び出しの後で、クエリーされなければ
なりません。


 ども、Jitta@行き詰まりモード です。

 夏姫☆さん、逆です。CausesValidation="true"であれば、チェックされるんです。「検証を引き起こす」ですから。falseにすることで、Page.IsValidが「設定されず」、if文で落ちているんですよ。
 あと、クライアントでやっているのですから、サーバ側のコードは実行されていないような?クライアントスクリプトを有効にするか、というプロパティがあるので、それの設定を確認してください。


##あ〜、Windowsサービスのデバッグは待ちが多くて疲れる。。。←行き詰まりモード


追加:
 チェックされていないのではなく、チェックの仕方が間違っています。
 function DataCheck(source, arguments) {
  if ( ( document.Form1.DropDownList1.value != "99" )
   && ( arguments.value == null ) ) {
    arguments.IsValid = false;
  } else {
    arguments.IsValid = true;
  }
 }

 空文字列とnullは違います。あ、length==0にしていると、オブジェクトがない、とかってエラーになりましたか?そうだったら失礼しました。私のがミスってますね。

[ メッセージ編集済み 編集者: Jitta 編集日時 2004-01-26 20:26 ]
夏姫☆
会議室デビュー日: 2003/12/11
投稿数: 15
投稿日時: 2004-01-27 16:08
こんにちは。
Jittaさん、アドバイスありがとうございました。
CustomValidatorで検証することができました。

JavaScriptの記述は

if ( ( document.Form1.DropDownList1.value != 99 )
  && ( arguments.value == "" ) ) {

にしなければ、上手くいきませんでした。


ただ、せっかく動くようになったのですが、検証対象の
コントロールからフォーカスが外れると検証されてしまうのが
ネックになってしまいました。

最初、TextBox1を検証対象にしていましたが、JavaScript内で
チェック条件として使用するDropDownList1を選択する前に
検証が走ってしまい、DropDownList1の値が選択されていないため
意図した動きになりませんでした。
逆に、DropDownList1を検証対象に変更しても、TextBox1に
入力する前に検証されてしまい、これもNGでした。

入力順を固定できないかぎり(ユーザが必ずしもこちらの意図した順序で
入力してくれると思えませんので)、今回のケースはCustomValidatorでは
厳しいのかなと思えてしまいました。

なので、Button1押下時にのみ検証させようとすると、
Button1.Attributes.add( 〜 )でやるしかないのかなと…。

せっかく使えるようになったCustomValidatorでしたが、残念です。
検証のタイミングをフォーカスを外れた場合か、あるトリガーが
与えられた場合(この場合ボタン押下)か、選択できるコントロール
だったら、ちょうど良かったのですが。

「ボタン押下のタイミングで入力チェックしてから
ポストバックする」というのはMS側での意図しない動きなんでしょうか。。。


結局…。
C#なのでButton1.Attributes.add( 〜 )ではなく
Button1.Attributes[ 〜 ] = " 〜 "でしたね。

◆WebForm1.aspxのJavaScript(DropDownList1の初期値を"#"とした)
function DataCheck() {
 if ( document.Form1.DropDownList1.value == "#" )
 {
  alert( "リストを選択してください" );
  return false;
 }
 else if ( ( document.Form1.DropDownList1.value != 99 )
  && ( document.Form1.TextBox1.value == "" ) )
 {
  alert( "条件を入力してください" );
  return false;
 }
 return true;
}

◆WebForm1.aspx.cs
private void Page_Load(object sender, System.EventArgs e)
{
 Button1.Attributes[ "onClick" ] = "return DataCheck()";
}

↑にしました。
せっかくならCustomValidatorでやってみたかったですが、
仕方ないですね。

[ メッセージ編集済み 編集者: 夏姫☆ 編集日時 2004-01-27 17:37 ]
Jitta
ぬし
会議室デビュー日: 2002/07/05
投稿数: 6267
お住まい・勤務地: 兵庫県・海手
投稿日時: 2004-01-27 17:29
引用:

夏姫☆さんの書き込み (2004-01-27 16:08) より:

JavaScriptの記述は

if ( ( document.Form1.DropDownList1.value != 99 )
  && ( arguments.value == "" ) ) {

にしなければ、上手くいきませんでした。


(._.) φ メモメモ

引用:

ただ、せっかく動くようになったのですが、検証対象の
コントロールからフォーカスが外れると検証されてしまうのが
ネックになってしまいました。


 確かに。私も、複数のボタンがあって、ボタンによって使用したい検証コントロールを変えたい!と思って苦労しました。

 で、私がやった方法ですが。
 まず、そのまま実行します。そしてページの「ソースを表示」すると、検証対象の要素にonchangeなどの追加した覚えのない属性が追加されていることがわかります。そこに、検証のための関数名が書かれていますから、それをメモします。
 次に、検証コントロールをDisabledにします(Enableプロパティをfalse)。これで検証が行われません。
 これでは困るので、検証を実行したいトリガで、先ほど書き留めた関数が呼び出されるように、コントロールに属性を追加します。このとき、関数を呼ぶ前後で検証コントロールのEnableプロパティを変更するようにします(trueにしてから検証し、検証が終わるとfalseにする)。

 今回はボタンクリックによるので、Page_loadメソッドないで検証コントロールをdisabledにします。そして、ボタンに属性を追加します。
btnControl.Attribute.Add("onclick", "javascript:validator.enabled=true;FUNC;validator.enabled=false;")
こんな感じ。
ゆうじゅん
ぬし
会議室デビュー日: 2004/01/16
投稿数: 347
投稿日時: 2004-01-27 18:17
こんにちは

function DataCheck(source, arguments) {
 if ( ( document.Form1.DropDownList1.value != "99" )
  && ( document.Form1.TextBox1.value == "" ) ) {
   arguments.IsValid = false;
 } else {
   arguments.IsValid = true;
 }
}

として

CustomValidatorのControlToValidateプロパティを無指定にすれば
submit時にチェックするようになります

スキルアップ/キャリアアップ(JOB@IT)