2011-09-09 7 views
2

私はjquery UIオートコンプリートウィジェットをajaxで使用しています。jquery ui autocompleteは、ajaxが返すときにフォーカスがない場合、閉じるオプションメニューを表示しません。

背景:

autoComp.focus(function() { $(this).autocomplete("search", "");}

は、しかし、これは次のような効果を生成します:ユーザーが自動補完に焦点を当て、何も入力せずにオプションを取得することができるようにするためには、私はフォーカスイベントを使用する場合ユーザーがクリックすると、ajaxリクエストが送信されます。応答を待つ間、ユーザーは他の場所をクリックし、オートコンプリートが不鮮明になります。しかし、応答が返されるとすぐに、オートコンプリートにはフォーカスがないのに、オプションメニューがポップアウトされます。それを離れさせるために、ユーザーは一度内側をクリックして、オートコンプリートの外側をもう一度クリックしなければなりません。これはちょっと面倒です。

どのように私はこれを防止するのですか?

EDIT:要素のIDを知っている別のメディエータ関数を構築することで、これを非常に醜い方法で解決しました。この関数はIDを持つajax関数を呼び出し、成功すると要素のフォーカスをチェックし、それは集中していません。それはかなり醜いです、私はまだ選択肢を探しています。

EDIT#2:Wlliamが示唆したように試みましたが、まだ動作しません。xhrは不鮮明なときは定義されていません。 thisキーワードに何らかの問題があります。オートコンプリートの外にgetTags関数を書くと、それは意味が異なりますか?

this.autocomplete = $('.tab#'+this.id+' #tags').autocomplete({ 
    minLength: 0, 
    autoFocus: true, 
    source: getTags, 
    select: function(e, obj) { 
     tab_id = $(this).parents('.tab').attr('id'); 
     tabs[tab_id].addTag(obj.item.label, obj.item.id, false); 
     $(this).blur(); // This is done so that the options menu won't pop up again. 
     return false; // This is done so that the value will not stay in the input box after selection. 
    }, 
    open: function() {}, 
    close: function() {} 
}); 
$('.tab#'+this.id+' #tags').focus(function() { 
    $(this).autocomplete("search", ""); 
}); 
$('.tab#'+this.id+' #tags').blur(function() { 
    console.log('blurring'); 
    var xhr = $(this).data('xhr'); // This comes out undefined... :(
    if (xhr) { 
     xhr.abort(); 
    }; 
    $(this).removeClass('ui-autocomplete-loading'); 
}); 

、これはソースキーワードにコピーgetTags機能である:

 function getTags(request, response) 
     { 
      console.log('Getting tags.'); 
      $(this).data('xhr', $.ajax({ 
       url: '/rpc', 
       dataType: 'json', 
       data: { 
        action: 'GetLabels', 
        arg0: JSON.stringify(request.term) 
       }, 
       success: function(data) { 
        console.log('Tags arrived:'); 
        tags = []; 
        for (i in data) { 
         a = {} 
         a.id = data[i]['key']; 
         a.label = data[i]['name']; 
         tags.push(a); 
        } 
        response(tags); 
       } 
      })); 
      console.log($(this).data('xhr')); 
     } 

答えて

4

私はあなたがAJAXリクエストを中止するために、sourceのコールバックオプションを使用する必要があると思います。オートコンプリートウィジェットの概要からの引用: テキスト現在値を参照する「という用語」と呼ばれる単一のプロパティと、

  • 要求オブジェクト:

    コールバックは2つの引数を取得します入力。たとえば、 ユーザーが都市のフィールドに「new yo」と入力した場合、オートコンプリートの用語は となり、「new yo」になります。

  • 応答コールバック。応答コールバック。応答コールバックでは、単一の引数に、ユーザーに示唆するデータを に含めることが必要です。このデータは、提供された用語である に基づいてフィルタリングされ、簡単なローカルデータ( ラベル/値/両方のプロパティを持つString-ArrayまたはObject-Array)の場合には、 のいずれかの形式になります。要求中にエラーを処理するために、カスタムの ソースコールバックを提供する場合は重要です。エラーが発生した場合でも常に 応答コールバックを呼び出す必要があります。この は、ウィジェットが常に正しい状態であることを保証します。あなたのケースでは

、それはおそらく、次のようなものを見てみましょう:

$("#autoComp").autocomplete({ 
    source: function(request, response) { 
     var searchString = request.term; 

     // ajax call to remote server, perhaps filtered with searchString 
     $(this).data('xhr', $.ajax({ 
      ... 
      success: function(data) { 
       ... 
       // pass back the data filtered by searchString 
       response(filteredList); 
      } 
     })); 
    }, 
    minLength: 0, 
    focus: function() { 
     $(this).autocomplete("search"); 
    } 
}) 
// cancel the request when user click away from the input box 
.blur(function() { 
    var xhr = $(this).data('xhr'); 
    if (xhr) xhr.abort(); 
}); 
+0

jqueryオブジェクトに関連付けられたデータを格納できることは知られていなかったので、これは良い考えです。しかし、オートコンプリートの読み込みクラスでは、読み込みアニメーションが実行されています。私があなたのやり方をするならば、クラスを自分で取り除く必要がありますか?それは問題なのだろうか? – Uri

+0

「オートコンプリート・ロード・クラスが実行しているロード・アニメーション」とはどういう意味ですか?コールバックをソースとして使用すると柔軟性が増すため、アニメーションの提供に支障はないと思います。いくつかのコードであなたの答えを更新できますか? –

+0

オートコンプリートは、読み込み中の指示を追加するために使用できる「ui-autocomplete-loading」クラス(読み込み中)を自動的に追加します。 ajaxが返されると、これは自動的に削除されます。あなたがそれを打ち切るなら、別のコード行でそれを削除しなければならないと思いますよね? – Uri

1

私はOpen eventを使用してこの問題を回避ました。ドロップダウンが開いたときに入力にフォーカスがない場合は、単に閉じます。

$("#autoComp").autocomplete({ 
    open: function() { 
    if ($(this).is(':not(:focus)')) { 
     $(this).autocomplete('close'); 
    } 
    }, 
    source: function(request, response) { 
    ... 
    } 
}); 
関連する問題