2

http://ivaynberg.github.com/select2/#infinite与えられた例はあまり説明されておらず、それらの結果を生成するためにバックエンドで何が起こっているのかわかりません。

編集: クエリから限られた量の行を返すように cfc を変更しました。のajaxから呼び出されることを期待して、合計行数も追加しましたdata.total

CFC:

<cffunction name="GetClientsByName"
    access="remote"
    returntype="string"
    output="true"
    hint="get clients from search term">

    <cfargument name="name" type="string" required="yes">
    <cfargument name="page" type="numeric">
    <cfargument name="page_limit" type="numeric">

    <cfset var start = (arguments.page * arguments.page_limit) - arguments.page_limit + 1>
    <cfset var end = start + arguments.page_limit>

    <cfset var util = createObject("component", "/surveymanagement/JSONUtil")>
    <cfset var results = arrayNew(1)>
    <cfset var elem = "">
    <cfset var total = "">

    <cfquery name="GetClientsByName" datasource="#application.dsn#">
        SELECT client_id, client_name
        FROM Clients
        WHERE client_name LIKE <cfqueryparam cfsqltype="cf_sql_varchar" value="%#arguments.name#%">
        ORDER BY client_name
    </cfquery>

    <cfset total = structNew()>
    <cfset total["total"] = GetClientsByName.RecordCount>

    <cfloop query="GetClientsByName" startrow="#start#" endrow="#end#">
        <cfset elem = structNew()>
        <cfset elem["id"] = GetClientsByName.client_id>
        <cfset elem["text"] = GetClientsByName.client_name>
        <cfset arrayAppend(results, elem)>
    </cfloop>

    <cfset arrayAppend(results, total)>

    <cfcontent type="application/json" reset="true"><cfoutput>#util.serializeJSON(results)#</cfoutput><cfabort />
</cffunction>

cfarguments page と page_limit を使用して SQL を変更する必要があると思いますが、どうすればよいかわかりません。ページごとに返される行を制限してから、次のページの行を追加するにはどうすればよいですか?

js:

$(".select").select2({
    allowClear: true,
    blurOnChange: true,
    openOnEnter: false,
    ajax: {
        url: "/surveymanagement/admin/client.cfc",
        dataType: 'json',
        quietMillis: 100,
        data: function (term, page) {
            return {
                method: "GetClientsByName",
                name: term,
                page_limit: 10,
                page: page
            };
        },
        results: function (data, page) {
            var more = (page * 10) < data.total;

            return { results: data, more: more };
        }
    }
});

また、誰かが select2 に無限スクロールを組み込む方法についてのチュートリアルを見つけてくれるとうれしいです。

私の問題はresultsajax呼び出しのセクションにあると思いますが、よくわかりません。

4

1 に答える 1

2

サーバ側

バックエンド ページは、次の 2 つの値を含む JSON 構造を返す必要があります。

  • 見つかった合計レコード
  • 結果 (つまり、構造体の配列)

デフォルトでは、プラグインは結果構造に と の 2 つのキーが含まれていることを想定してい"id"ます"text"。(技術的には、別のキー名を使用できます。ただし、別の名前を使用する場合は、カスタム関数をコーディングして結果をフォーマットする必要があります。つまりformatResult、 およびformatSelection.)

サンプル:

     {"clients":[{"text":"client name ABC","id":112}],"total":1}

コード:

    <cffunction name="getClientsByName" access="remote" returntype="string" output="false">
        <cfargument name="name" type="string" required="yes">
        <cfargument name="page" type="numeric" required="true">
        <cfargument name="page_limit" type="numeric" default="10">

        <cfset var startRow = (arguments.page * arguments.page_limit) - arguments.page_limit + 1>
        <cfset var endRow = startRow + arguments.page_limit>

        <cfset var util = createObject("component", "test.jsonUtil")>
        <cfset var getClientsByName = "">
        <cfset var results = structNew()>
        <cfset var clients = arrayNew(1)>
        <cfset var elem = "">

        ... run db query ....

        <!--- use default keys: "id" and "text" --->  
        <cfloop query="getClientsByName" startRow="#startRow#" endRow="#endRow#">
            <cfset elem = structNew()>
            <cfset elem["id"] = getClientsByName.client_id>
            <cfset elem["text"] = getClientsByName.client_name>
            <cfset arrayAppend(clients, elem)>
        </cfloop>

         <!--- package the results into a structure --->  
        <cfset results["total"] = getClientsByName.recordCount>
        <cfset results["clients"] = clients>

        <cfcontent type="application/json" reset="true">
        <cfoutput>#util.serializeJSON(results)#</cfoutput><cfabort />
    </cffunction>

クライアント側

JavaScript を少し調整するだけです。は構造体であるためdata、結果を含むキーの名前を追加する必要があります。つまり、

          return { results: data.clients, more: more };

... それ以外の

          return { results: data, more: more };

最適化:

そうは言っても、現在のコードは、リクエストごとにテーブル全体を取得するため、非効率的です。データベース側でページネーションを行う方が効率的です。したがって、データベースは一度に 10 を超えるレコードを返すことはありません。正確な構文はデータベース固有です。

(ところで、SQL の多くはベンダーによって異なります。そのため、質問にクエリが含まれる場合は、データベースの種類とバージョンをタグに含めることをお勧めします :)

于 2013-03-02T06:05:55.033 に答える