Jquery 在多个页面上实现一个小部件Durandal 2.0
我试图在多个屏幕上使用单个小部件。然而,我遇到了一个问题,当我在另一个页面上加载这个小部件的第二个实例,然后尝试在第一个页面上再次使用第一个小部件时,这个小部件内的选项卡不再导航(引导活动类确实切换到正确的选项卡,只是内容没有切换) 经过一段时间的调试,我意识到当我尝试在不工作的小部件中导航时,实际上是在“工作”小部件上导航选项卡。似乎2个视图和1个视图模型通信不正常。我认为这是因为Durandal认为它是这个小部件的第二个实例(不知道如何正确区分两者) 我使用的是BootstrapV3.0.1选项卡,我已经浏览并制作了小部件中的所有选项卡ID,这些ID特定于加载此小部件的每个页面 可悲的是,我没有想法,也不知道如何解决这个问题。非常感谢能提供的任何帮助 是否有某种方法可以指定一个小部件不具有CachedView?下面代码中的绑定不起作用 小部件实现:Jquery 在多个页面上实现一个小部件Durandal 2.0,jquery,twitter-bootstrap-3,durandal-2.0,Jquery,Twitter Bootstrap 3,Durandal 2.0,我试图在多个屏幕上使用单个小部件。然而,我遇到了一个问题,当我在另一个页面上加载这个小部件的第二个实例,然后尝试在第一个页面上再次使用第一个小部件时,这个小部件内的选项卡不再导航(引导活动类确实切换到正确的选项卡,只是内容没有切换) 经过一段时间的调试,我意识到当我尝试在不工作的小部件中导航时,实际上是在“工作”小部件上导航选项卡。似乎2个视图和1个视图模型通信不正常。我认为这是因为Durandal认为它是这个小部件的第二个实例(不知道如何正确区分两者) 我使用的是BootstrapV3.0.1
Page 1:
<div class="modal fade" id="id1" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div data-bind="widget: {kind: 'productDetails', options: productDetailsWidgetOptions, cacheViews:false }"></div>
</div>
</div>
</div>
Page 2:
<div class="modal fade" id="id2" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div data-bind="widget: { kind: 'productDetails', options: productDetailsWidgetOptions, cacheViews:false }"></div>
</div>
</div>
</div>
我试图更改代码以返回一个函数,使其不成为单例函数。这给了我完全相同的结果,还有什么我可能遗漏或做得不正确的吗
var vm = function(){
//#region Durandal's callbacks
this.activate = activate;
this.attached = attached;
this.deactivate = deactivate;
this.canDeactivate = canDeactivate;
//#endregion
//#region Properties
this.title = title;
this.name = name;
this.productCode = productCode;
this.description = description;
//#endregion
//#region Commands
this.saveProductDetailsCommand = saveProductDetailsCommand;
this.cancelProductDetailsCommand = cancelProductDetailsCommand;
//#endregion
};
return vm;
确保在小部件的viewModel中返回构造函数。如果您返回的是对象文本,那么您创建的是单例模块,而不是基于实例的模块。请发布您的viewModel代码,以便我可以看到您如何设置小部件的viewModel [编辑]
var vm = function(){
//#region Properties
this.title = title;
this.name = name;
this.productCode = productCode;
this.description = description;
//#endregion
//#region Commands
this.saveProductDetailsCommand = saveProductDetailsCommand;
this.cancelProductDetailsCommand = cancelProductDetailsCommand;
//#endregion
};
vm.prototype.activate = function () {}
vm.prototype.attached = function () {}
vm.prototype.compositionComplete = function () {}
vm.prototype.detached = function () {}
vm.prototype.deactivate = function () {}
vm.prototype.canDeactivate = function () {}
return vm;
另外,不要忘记封闭的定义和函数。因此,全文如下:
define(['knockout'],
function(ko) {
var vm = function(){
//#region Properties
this.title = title;
this.name = name;
this.productCode = productCode;
this.description = description;
//#endregion
//#region Commands
this.saveProductDetailsCommand = saveProductDetailsCommand;
this.cancelProductDetailsCommand = cancelProductDetailsCommand;
//#endregion
};
vm.prototype.activate = function () {}
vm.prototype.attached = function () {}
vm.prototype.compositionComplete = function () {}
vm.prototype.detached = function () {}
vm.prototype.deactivate = function () {}
vm.prototype.canDeactivate = function () {}
return vm;
}
其他要点:
- 对viewModel使用比“vm”更具描述性的名称。如果您正在编写一个菜单小部件,请使用Pascal case将其命名为MenuWidget,并用此名称替换“vm”。这将使调试更加容易
- 确保将在视图中显示和更新的属性是可忽略的可观察属性(例如,将
this.name=name;
更改为this.name=ko.observable(name);
- 最好是在
activate
处理程序中初始化观测值,而不是在构造函数中(至少使用Durandal)
同意这一“诊断”。这是一个完美的例子,说明需要构造函数,因为您需要多个“实例”,而不是多次调用的单个实例。我以前返回了一个对象。我更改了小部件以返回一个函数,但仍然得到了相同的结果。代码张贴在它上面,这是我的最新编辑。@treemedus问题是您需要放置激活
,附加
,停用
,以及canDeactivate
在原型上,这样Durandal就可以找到它们。另外,它们需要是函数。请参阅我答案的编辑。@EricTaylor每个回调都是如上所述创建的函数。我已将Durandal回调移到原型上,但仍然得到相同的结果。是否将vm更改为函数创建基于实例的小部件要做的主要事情是什么?因为似乎仍在创建一个单例。@Treemendus不,更改名称只是表面上的。请确保清除缓存并刷新。现在没有理由认为它不起作用。我有几十个小部件,没有问题。也许你可以压缩你的代码并修改它e通过DropBox或其他基于云的存储解决方案提供。我很乐意看一看。
define(['knockout'],
function(ko) {
var vm = function(){
//#region Properties
this.title = title;
this.name = name;
this.productCode = productCode;
this.description = description;
//#endregion
//#region Commands
this.saveProductDetailsCommand = saveProductDetailsCommand;
this.cancelProductDetailsCommand = cancelProductDetailsCommand;
//#endregion
};
vm.prototype.activate = function () {}
vm.prototype.attached = function () {}
vm.prototype.compositionComplete = function () {}
vm.prototype.detached = function () {}
vm.prototype.deactivate = function () {}
vm.prototype.canDeactivate = function () {}
return vm;
}