14

さまざまな要素が変更されたときにリモートで送信されるフォームがあります。特に検索フィールドでは、フィールド内のテキストがいつ変更されたかを検出するためにキーアップを使用しています。これの問題は、誰かが「chicken」と入力すると、フォームが 7 回送信され、最後の 1 回だけがカウントされることです。

このようなものが良いでしょう

  • キーアップが検出されました - 待機を開始します (1 秒間)

  • 別のキーアップが検出されました - 再起動の待ち時間

  • 待機終了 - 値を取得してフォームを送信

これの独自のバージョンをコーディングする前に (私は本当に小さな js しか持たないバックエンドの男で、すべてに jQuery を使用しています)、これに対する既存のソリューションは既にありますか? それは一般的な要件のようです。jQueryプラグインかな?そうでない場合、これをコーディングする最も簡単で最良の方法は何ですか?

更新 - ダンに追加された現在のコード (以下)

ダン - これは関連している可能性があります。このページで使用している jQuery プラグインの 1 つ (tablesorter) には、このファイル「tablesorter/jquery-latest.js」が必要です。これが含まれていると、コードで以前と同じエラーが発生します。

jQuery("input#search").data("timeout", null) が未定義 http‍://192.168.0.234/javascripts/main.js?1264084467 11行目

異なる jQuery 定義の間に何らかの競合があるのではないでしょうか? (か何か)

$(document).ready(function() {
  //initiate the shadowbox player
//  Shadowbox.init({
//    players:  ['html', 'iframe']
//  });
}); 

jQuery(function(){
  jQuery('input#search')
    .data('timeout', null)
    .keyup(function(){
      jQuery(this).data('timeout', setTimeout(function(){
          var mytext = jQuery('input#search').val();
          submitQuizForm();
          jQuery('input#search').next().html(mytext);
        }, 2000)
     )
     .keydown(function(){
       clearTimeout(jQuery(this).data('timeout'));
     });
    });
});

function submitQuizForm(){
  form = jQuery("#searchQuizzes");
  jQuery.ajax({
    async:true, 
    data:jQuery.param(form.serializeArray()), 
    dataType:'script', 
    type:'get', 
    url:'/millionaire/millionaire_quizzes',
    success: function(msg){ 
     // $("#chooseQuizMainTable").trigger("update"); 
    }
  }); 
  return true;
}
4

5 に答える 5

24

申し訳ありませんが、私はこれをテストしておらず、頭のてっぺんから少し外れていますが、これらの線に沿った何かがうまくいくはずです。2000 を、サーバーのポスト間に必要なミリ秒数に変更します

<input type="text" id="mytextbox" style="border: 1px solid" />
<span></span>

<script language="javascript" type="text/javascript">
    jQuery(function(){
      jQuery('#mytextbox')
        .data('timeout', null)
        .keyup(function(){
            clearTimeout(jQuery(this).data('timeout'));
            jQuery(this).data('timeout', setTimeout(submitQuizForm, 2000));
        });
    });
</script>
于 2010-01-20T13:14:02.147 に答える
7

これがあなたの派手なjquery拡張機能です:

(function($){

$.widget("ui.onDelayedKeyup", {

    _init : function() {
        var self = this;
        $(this.element).keyup(function() {
            if(typeof(window['inputTimeout']) != "undefined"){
                window.clearTimeout(inputTimeout);
            }  
            var handler = self.options.handler;
            window['inputTimeout'] = window.setTimeout(function() {
                handler.call(self.element) }, self.options.delay);
        });
    },
    options: {
        handler: $.noop(),
        delay: 500
    }

});
})(jQuery);

そのようにそれを使用してください:

    $("input.filterField").onDelayedKeyup({
        handler: function() {
            if ($.trim($(this).val()).length > 0) {
                //reload my data store using the filter string.
            }
        }
    });

デフォルトで0.5秒の遅延を行います。

于 2011-05-19T05:16:47.710 に答える
4

更新として、私はこれでうまくいったようです:

function afterDelayedKeyup(selector, action, delay){
  jQuery(selector).keyup(function(){
    if(typeof(window['inputTimeout']) != "undefined"){
      clearTimeout(inputTimeout);
    }  
    inputTimeout = setTimeout(action, delay);
  });
}

次に、問題のページの document.ready ブロックからこれを呼び出します

  afterDelayedKeyup('input#search',"submitQuizForm()",500)

このロジックを使用する新しい jquery イベントを作成するとよいでしょう。たとえば、.delayedKeyup を .keyup と一緒に使用することで、個々のページの document.ready ブロックに対してこのようなことを言うことができます。

  jQuery('input#search').delayedKeyup(function(){
    submitQuizForm();
  });

しかし、このようにjqueryをカスタマイズする方法がわかりません。しかし、それは良い宿題です。

于 2010-01-22T17:36:16.977 に答える
3

よくやった、マックス、とても役に立ちました!より一般的なものにすることで、関数をわずかに改善しました。

function afterDelayedEvent(eventtype, selector, action, delay) {
    $(selector).bind(eventtype, function() {
        if (typeof(window['inputTimeout']) != "undefined") {
            clearTimeout(inputTimeout);
        }
        inputTimeout = setTimeout(action, delay);
    });
}

このようにして、あらゆるタイプのイベントに使用できますが、ここでは keyup がおそらく最も便利です。

于 2010-11-30T08:35:02.163 に答える
0

これは古いことは知っていますが、このようなことを行う方法を探していたときの最初の結果の1つであったため、解決策を共有します. 提供された回答を組み合わせて、必要なものを取得しました。

既存の jQuery イベントと同じように機能するカスタム イベントが必要でした。それにはkeypress+ delete、backspace、enter を使用する必要がありました。

これが私のjQueryプラグインです:

$.fn.typePause = function (dataObject, eventFunc)
    {
        if(typeof dataObject === 'function')
        {
            eventFunc = dataObject;
            dataObject = {};
        }
        if(typeof dataObject.milliseconds === 'undefined')
            dataObject.milliseconds = 500;
        $(this).data('timeout', null)
            .keypress(dataObject, function(e)
            {
                clearTimeout($(this).data('timeout'));
                $(this).data('timeout', setTimeout($.proxy(eventFunc, this, e), dataObject.milliseconds));
            })
            .keyup(dataObject, function(e)
            {
                var code = (e.keyCode ? e.keyCode : e.which);
                if(code == 8 || code == 46 || code == 13)
                    $(this).triggerHandler('keypress',dataObject);
            });
    }

以前$.proxy()はイベントのコンテキストを保持していましたが、パフォーマンスに関しては、これを行うためのより良い方法がある可能性があります。

このプラグインを使用するには、次のようにします。

$('#myElement').typePause(function(e){ /* do stuff */ });

また

$('#myElement').typePause({milliseconds: 500, [other data to pass to event]},function(e){ /* do stuff */ });    
于 2013-08-09T18:30:21.243 に答える