Backbone 列表视图/渲染列表视图项目
Backbone List View / Rendering List View Items
我是 Backbone.js 的新手。请查看我的代码以了解我在此处引用的内容。我有一个应该显示 'Stock' 模型集合的视图。此视图称为 'StockDashboardView'。此视图需要的每个股票模型都可以用 'StockDashboardItemView' 显示。不过,在每个 StockDashboardItemView 呈现之前,它各自的 Stock Model 需要获取一些数据(请求股票价格),以便 StockDashboardItemView 可以使用这些数据绘制图形。 StockDashboardView 遍历每个股票模型并为每个模型创建一个 StockDashboardItemView。我应该得到 5 个不同的图表,每个图表都有不同的公司数据点。但是所有图表都是相同的,这意味着 5 个 StockDashboardItemView 中的每一个都以某种方式具有相同的模型。我知道我的 fetch/looping 逻辑是错误的,但我不知道如何或为什么。我还尝试获取单个 StockDashboardItemViews 而不是 StockDashboardView(请参阅注释掉的代码)。查看我的 console.log 语句,我看到以下打印语句:(该系列有 5 个模型)。有人可以帮我解决我的逻辑吗?谢谢
------------1--------
------------1--------
------------1--------
------------1--------
------------1--------
------------2--------
------------3--------
------------2--------
------------3--------
------------2--------
------------3--------
------------2--------
------------3--------
------------2--------
------------3--------
window.StockDashboardView = Backbone.View.extend({
initialize: function () {
this.render();
},
render: function () {
var stocks = this.model.models;
var len = stocks.length;
var startPos = (this.options.page - 1) * 8;
var endPos = Math.min(startPos + 8, len);
$(this.el).html('<ul class="thumbnails"></ul>');
for (var i = startPos; i < endPos; i++) {
console.log("----------1--------");
var stock = stocks[i];
stock.set("_id", stocks[i].toJSON()["tickerSymbol"]);
stock.fetch({success: function(model, response, options){
stock.set("data", response);
// set interactivity to false
console.log("-----------2---------");
$('.thumbnails', this.el).append(new StockDashboardItemView({model: stock}).render().el);
}});
}
$(this.el).append(new Paginator({model: this.model, page: this.options.page}).render().el);
return this;
}
});
window.StockDashboardItemView = Backbone.View.extend({
tagName: "li",
initialize: function () {
this.model.bind("change", this.render, this);
this.model.bind("destroy", this.close, this);
},
render: function () {
$(this.el).html(this.template(this.model.toJSON()));
var context = this.$("#chart_div")[0];
var stock = this.model;
stock.set("_id", stock.toJSON()["tickerSymbol"]);
//stock.fetch({success: function(model, response, options){
//stock.set("data", response);
// set interactivity to false
console.log("-----------3---------");
var chart = new TFChart(stock.get("_id"), stock.attributes['data'], context, false, this.$("#chart_div").width(), this.$("#chart_div").height());
return this;
//}});
}
});
在您的 for-loop
中,您使用 stock = stocks[i]
获取每只股票,然后获取它们。
但是,由于.fetch
是async
方法,当它开始执行以呈现股票视图时,您会注意到股票现在指向股票中的最后一项, 所以它只是多次渲染最后一项。
为什么会这样?因为var
使用的是函数作用域,而不是块作用域(在ES6中,有一个let
可以使用块作用域,但是这里有点跑题了),所以所有的.fetch
' s成功回调,当他们想使用stock
时,他们都看到相同的stock
,这将是for循环中最后分配的值,应该是最后一项stocks。
这是一个作用域问题,解决方案是将上下文包装到一个函数中,这样函数的作用域就会为您保留该项目:
render: function () {
var stocks = this.model.models;
var len = stocks.length;
var startPos = (this.options.page - 1) * 8;
var endPos = Math.min(startPos + 8, len);
// Move this.el to here, so the this.el's this won't be a problem.
var thisEl = this.el;
var fetchStock = function(stock) {
stock.set("_id", stocks[i].toJSON()["tickerSymbol"]);
stock.fetch({success: function(model, response, options){
stock.set("data", response);
// set interactivity to false
console.log("-----------2---------");
$('.thumbnails', thisEl).append(new StockDashboardItemView({model: stock}).render().el);
}});
};
$(this.el).html('<ul class="thumbnails"></ul>');
for (var i = startPos; i < endPos; i++) {
console.log("----------1--------");
fetchStock(stocks[i]);
}
$(this.el).append(new Paginator({model: this.model, page: this.options.page}).render().el);
return this;
}
如你所见,现在当我们调用fetchStock
时,它的stock
将引用当前的stocks[i]
,而不会受到后面循环的影响。
我是 Backbone.js 的新手。请查看我的代码以了解我在此处引用的内容。我有一个应该显示 'Stock' 模型集合的视图。此视图称为 'StockDashboardView'。此视图需要的每个股票模型都可以用 'StockDashboardItemView' 显示。不过,在每个 StockDashboardItemView 呈现之前,它各自的 Stock Model 需要获取一些数据(请求股票价格),以便 StockDashboardItemView 可以使用这些数据绘制图形。 StockDashboardView 遍历每个股票模型并为每个模型创建一个 StockDashboardItemView。我应该得到 5 个不同的图表,每个图表都有不同的公司数据点。但是所有图表都是相同的,这意味着 5 个 StockDashboardItemView 中的每一个都以某种方式具有相同的模型。我知道我的 fetch/looping 逻辑是错误的,但我不知道如何或为什么。我还尝试获取单个 StockDashboardItemViews 而不是 StockDashboardView(请参阅注释掉的代码)。查看我的 console.log 语句,我看到以下打印语句:(该系列有 5 个模型)。有人可以帮我解决我的逻辑吗?谢谢
------------1--------
------------1--------
------------1--------
------------1--------
------------1--------
------------2--------
------------3--------
------------2--------
------------3--------
------------2--------
------------3--------
------------2--------
------------3--------
------------2--------
------------3--------
window.StockDashboardView = Backbone.View.extend({
initialize: function () {
this.render();
},
render: function () {
var stocks = this.model.models;
var len = stocks.length;
var startPos = (this.options.page - 1) * 8;
var endPos = Math.min(startPos + 8, len);
$(this.el).html('<ul class="thumbnails"></ul>');
for (var i = startPos; i < endPos; i++) {
console.log("----------1--------");
var stock = stocks[i];
stock.set("_id", stocks[i].toJSON()["tickerSymbol"]);
stock.fetch({success: function(model, response, options){
stock.set("data", response);
// set interactivity to false
console.log("-----------2---------");
$('.thumbnails', this.el).append(new StockDashboardItemView({model: stock}).render().el);
}});
}
$(this.el).append(new Paginator({model: this.model, page: this.options.page}).render().el);
return this;
}
});
window.StockDashboardItemView = Backbone.View.extend({
tagName: "li",
initialize: function () {
this.model.bind("change", this.render, this);
this.model.bind("destroy", this.close, this);
},
render: function () {
$(this.el).html(this.template(this.model.toJSON()));
var context = this.$("#chart_div")[0];
var stock = this.model;
stock.set("_id", stock.toJSON()["tickerSymbol"]);
//stock.fetch({success: function(model, response, options){
//stock.set("data", response);
// set interactivity to false
console.log("-----------3---------");
var chart = new TFChart(stock.get("_id"), stock.attributes['data'], context, false, this.$("#chart_div").width(), this.$("#chart_div").height());
return this;
//}});
}
});
在您的 for-loop
中,您使用 stock = stocks[i]
获取每只股票,然后获取它们。
但是,由于.fetch
是async
方法,当它开始执行以呈现股票视图时,您会注意到股票现在指向股票中的最后一项, 所以它只是多次渲染最后一项。
为什么会这样?因为var
使用的是函数作用域,而不是块作用域(在ES6中,有一个let
可以使用块作用域,但是这里有点跑题了),所以所有的.fetch
' s成功回调,当他们想使用stock
时,他们都看到相同的stock
,这将是for循环中最后分配的值,应该是最后一项stocks。
这是一个作用域问题,解决方案是将上下文包装到一个函数中,这样函数的作用域就会为您保留该项目:
render: function () {
var stocks = this.model.models;
var len = stocks.length;
var startPos = (this.options.page - 1) * 8;
var endPos = Math.min(startPos + 8, len);
// Move this.el to here, so the this.el's this won't be a problem.
var thisEl = this.el;
var fetchStock = function(stock) {
stock.set("_id", stocks[i].toJSON()["tickerSymbol"]);
stock.fetch({success: function(model, response, options){
stock.set("data", response);
// set interactivity to false
console.log("-----------2---------");
$('.thumbnails', thisEl).append(new StockDashboardItemView({model: stock}).render().el);
}});
};
$(this.el).html('<ul class="thumbnails"></ul>');
for (var i = startPos; i < endPos; i++) {
console.log("----------1--------");
fetchStock(stocks[i]);
}
$(this.el).append(new Paginator({model: this.model, page: this.options.page}).render().el);
return this;
}
如你所见,现在当我们调用fetchStock
时,它的stock
将引用当前的stocks[i]
,而不会受到后面循环的影响。