2012-02-24 11 views
2

私はbackbone.jsを使用していますが、時々fetch()というコレクションを持っています。サブビューが作成される方法(コレクションがループされ、各項目が現在の表に追加された新しい行です)のため、オプション{add: true}を渡したくありません。私が試した1つのことは、テーブル全体を空にして新しい行をすべて作成することですが、スクロールが非常に頻繁に実行されるので(スクロールがテーブルの最後に近づくと)ゆっくりです。それは遅れを開始する。コレクションの古い部分と新しい部分を追跡する

私は追加目的のために新しいコレクションを追跡することができますが、コレクション全体をエンティティとして持つことができます。 1つ目の可能性は、2番目のコレクションを作成して最初のコレクションに追加することですが、どうすればいいか分かりません。

答えて

0

新しいモデルが追加された後でコレクションの現在の長さを追跡することができます。そのモデルをコレクションの終点までレンダリングするオフセットとして使用します。

UPDATE:私は、アンダースコアのドキュメントを見たとき、ちょうどこのことに気づい:http://documentcloud.github.com/underscore/#rest

それはこのない要約すると:

残り _.rest(配列、[インデックス])別名:tail
配列内の残りの要素を返します。そのインデックス以降の配列の値を返すためにインデックスを渡します。

これで、追加アイテムがコレクションに追加されるまでの長さを把握し、それをインデックスとして残りの部分に渡すだけで済みます。

2

新しいモデルの2番目のコレクションを作成することは冗長だと思います。私はあなたのセットアップを想像してみようとしており、ここにいくつかのソリューションのアイデアがあります。

多分あなたがこれを行う方法は、あなたのサブビューを行う方法を変更することです。

fetch()を実行するとコレクションがリセットされ、新しいモデルで作業する必要があるようです。この場合、fetch with {add:true}を使用すると、より良い解決策のように聞こえます。あなたは、あなたのサブビューの作成がループされていると言います、そして、私はあなたがコレクションをリセットするとき、どのようにループし、すべての新しいサブビューを作成する必要が遅くなる可能性が想像します。各モデルに対応するようにサブビューの作成を変更できますか?したがって、コレクションに追加される新しいモデルごとに、サブビューが追加されます。

私はTodo.jsの例のようなものを想像しています。しかし、あなたの問題のコンテキストは、私が見ているものから完全に離れているかもしれません。

EDIT:あなたは我々の議論を1として収集

に追加している新しいモデルにアクセスする方法、私は私がフェッチ成功オプションとパラメータについて考えていたものを確認し、このスレッドを発見しました。

In Backbone.js, after I perform a collection.fetch({'add':true}), how do I get the latest elements retrieved?

EDIT2:フルワーキングバックボーン例

これはOUTPUT(このような何か)である:ここでは

Pokemon Users 

Audino // These are in our initial collection 
Bulbasaur 
Charmander 
Caterpie // These are added to our collection using fetch() 
Butterfree 
Squirtle 

はHTMLです:

<body> 
    <h1>Pokemon Users</h1> 

    <div id="app"> 
     <div id="userList">  
    </div> 
</body> 

ここれますJS:

var User, UserCollection, UserView, AppView; 

// Each User model has 1 attribute name 
User = Backbone.Model.extend({ 
    defaults: { 
     name: "changeMe" 
    } 
}); 

// Our collection of Users 
UserCollection = Backbone.Collection.extend({ 
    model: User, 
    url: 'user' 
}); 

// Initialize our collection (nothing in it right now) 
var myCollection = new UserCollection; 

// Our UserView is each individual view, represented by the user model 
UserView = Backbone.View.extend({ 
    tagName: 'div', 
    className: 'user', 
    render: function() { 
     $(this.el).html(this.model.get("name")); 
     return this; 
    } 
}); 

// AppView is the larger view that contains the sub-views 
AppView = Backbone.View.extend({ 
    el: $('#app'), 
    initialize: function() { 
     // Binding the view to collection add events! <- This is the key 
     myCollection.on('add', this.addOne, this); // on/bind 
    }, 
    addOne: function(user) { 
     var view = new UserView({model:user}); 
     $('#userList').append(view.render().el); 
    } 
}); 

// Initialize the AppView -> Rock and Roll Time 
var myApp = new AppView(); 

// I'm creating 3 new models 
var userA, userB, userC; 
userA = new User(); 
userA.set({name:"Audino"}); 
userB = new User({name:"Bulbasaur"}); 
userC = new User({name:"Charmander"}); 

var userAry = [userA,userB,userC]; 

// I'm adding these models into my collection 
myCollection.add(userAry); 

// When you take a look at the collection now, it only has 3 models 
console.log(myCollection); 

// Now we fetch the other 3 models from the server using {add:true} 
// Try commenting this fetch call out to see the output minus new models 
myCollection.fetch({ 
    add: true, success: function(collection, response) { 
     // Just some extras to illustrate the success callback and args 
     // console.log('collection: '); 
     // console.log(collection); 
     // console.log('response: '); 
     // console.log(response); 
    } 
}); 

// The collection is updated rather than reset - necessary subview changes made 
console.log(myCollection); 

次は、PHPサーバーのコードです - 私は、ルーティングのためのスリムPHPを使用します。

// Returns a JSON Collection 
$app->get('/user', function() use ($app) { 

    $userD = array("name"=>"Caterpie"); 
    $userE = array("name"=>"Butterfree"); 
    $userF = array("name"=>"Squirtle"); 

    $userAry = array(); 
    array_push($userAry, $userD, $userE, $userF); 

    $json = json_encode($userAry); 
    $response = $app->response(); 
    $response['Content-Type'] = 'application/json'; 
    $response->body($json); 
}); 

は、これが通じ仕事が楽しかったです。私は何かを自分で学びました。それが役に立てば幸い! :-)

+0

正しいですが、私の問題は、どのモデルを「新」とするかわからないし、サブビューを追加する必要があることです。 – Matthew

+0

@ryanmarcには解決策があるようです。最後のIDをコレクションに保存してそこから移動することもできます。しかし、バックボーンはこのようなことをする良い方法があると私は伝えています。 ここで考えてみましょう。 fetch()を実行すると、引数として(collection、response)となる成功オプションを渡すことができます。さて、後でチェックする必要がありますが、成功コールバックのコレクション引数は、サーバーから取得する新しいコレクションかもしれません。 (元のコレクションとは対照的に、この新しいコレクションを追加しています。)そうであれば、これは新しいモデルであるかどうかを示す別の方法です。 – jmk2142

+1

成功コールバックに返されたコレクションは、サーバーから返されたすべてのコレクションになります。クエリを開始するようにオフセットして、新しいアイテムだけを返すのであれば、@ storagewarpが何を話しているのかを知ることができます。成功した関数のコールバックでは、取得したコレクションを使用して、それらをビューにレンダリングするように渡します。レンダリングを処理するためにコレクションへの変更イベントに既に頼っている場合は、それを再考するか、別の解決策を検討する必要があります。 (私が下に投稿した代替案のように) – ryanmarc

関連する問題