Javascript Knockoutjs中的子视图模型
认识得好 我正在玩Knockoutjs,目标是拥有一个ViewModel,它控制多个子ViewModel。这样做是为了更好地控制视图本身,并防止将视图的各个部分放到自己的小地方。下面的代码应该解释我的想法: ApplicationViewModelJavascript Knockoutjs中的子视图模型,javascript,knockout.js,Javascript,Knockout.js,认识得好 我正在玩Knockoutjs,目标是拥有一个ViewModel,它控制多个子ViewModel。这样做是为了更好地控制视图本身,并防止将视图的各个部分放到自己的小地方。下面的代码应该解释我的想法: ApplicationViewModel ApplicationViewModel = function () { var self = this; // Context (for laziness' sake, no separate VM) self.activeProject = k
ApplicationViewModel = function () {
var self = this;
// Context (for laziness' sake, no separate VM)
self.activeProject = ko.observable();
// States
self.projectsLoaded = ko.observable(false);
// State-change events
// Let application know that loading of projects has been called
self.projectsLoaded.subscribe(function (newValue) {
if (newValue === true) {
console.log('Projects have loaded');
} else {
console.log('Projects have not loaded');
}
});
// Let application know that selection of a project has happened
self.activeProject.subscribe(function (newValue) {
if (newValue != null) {
// Notify other viewmodels that a project has been (successfully loaded)
// Use hook-pattern to hook into this event
} else {
// Notify something went wrong- present user with a notification
// Application stops processes that are project-dependant
}
});
self.ProjectViewModel = new ProjectViewModel();
};
ProjectViewModel = function () {
var self = this;
self.projects = ko.observableArray();
self.loadProjects = function () {
// Business logic to retrieve projects, think AJAX
var placeHolderProjects = [];
// Find projects somewhere and load them up!
// If something went wrong, notify parent
if (placeHolderProjects.length > 0) {
self.projects(placeHolderProjects);
$root.projectsLoaded(true);
} else {
$root.projectsLoaded(false);
}
};
self.selectProject = function (projectId) {
if (!projectId) {
$.parent.activeProject = null;
return;
}
// Fetch data for project, stuff like membershipId
var loadProjectResult = magicalLoadFunction(projectId);
if (loadProjectsResult === true) {
$root.activeProject(projectId);
} else {
$root.activeProject(projectId);
}
// Exit
return;
}
/********** Constructor logic
****************************/
self.loadProjects();
};
项目视图模型
ApplicationViewModel = function () {
var self = this;
// Context (for laziness' sake, no separate VM)
self.activeProject = ko.observable();
// States
self.projectsLoaded = ko.observable(false);
// State-change events
// Let application know that loading of projects has been called
self.projectsLoaded.subscribe(function (newValue) {
if (newValue === true) {
console.log('Projects have loaded');
} else {
console.log('Projects have not loaded');
}
});
// Let application know that selection of a project has happened
self.activeProject.subscribe(function (newValue) {
if (newValue != null) {
// Notify other viewmodels that a project has been (successfully loaded)
// Use hook-pattern to hook into this event
} else {
// Notify something went wrong- present user with a notification
// Application stops processes that are project-dependant
}
});
self.ProjectViewModel = new ProjectViewModel();
};
ProjectViewModel = function () {
var self = this;
self.projects = ko.observableArray();
self.loadProjects = function () {
// Business logic to retrieve projects, think AJAX
var placeHolderProjects = [];
// Find projects somewhere and load them up!
// If something went wrong, notify parent
if (placeHolderProjects.length > 0) {
self.projects(placeHolderProjects);
$root.projectsLoaded(true);
} else {
$root.projectsLoaded(false);
}
};
self.selectProject = function (projectId) {
if (!projectId) {
$.parent.activeProject = null;
return;
}
// Fetch data for project, stuff like membershipId
var loadProjectResult = magicalLoadFunction(projectId);
if (loadProjectsResult === true) {
$root.activeProject(projectId);
} else {
$root.activeProject(projectId);
}
// Exit
return;
}
/********** Constructor logic
****************************/
self.loadProjects();
};
因此,基本上,我要寻找的是:
-从viewmodels中各自的子/父属性控制父/子属性
我也在研究AngularJS,但我真的想先让它在KnockoutJS中工作:)直接的问题是,我无法让$root/$parent工作。我将ApplicationViewModel绑定到$(document).ready()处理程序中,不确定是否还必须将子viewmodels绑定到视图。我已将ApplicationViewModel绑定到body元素
感谢您的阅读,可能还有您的回答/帮助我上路:)由@jansommer提供的答案证明是成功的 我更改了以下行(将其作为参数添加): 这就是我们所需要的
谢谢 您的ProjectViewModel可以接受一个参数,例如“parent”,当您从ApplicationViewModel实例化它时,您可以使用
self.ProjectViewModel=new ProjectViewModel(this)
进行实例化。但是最好让您的子视图模型公开父视图可以使用的函数或观察对象,这样子视图模型就不必知道它的父视图。这通常会使代码更清晰,但您的用例可能会有所不同。@JanSommer:谢谢您的建议,我正在尝试。至于公开函数/可观察对象,在我的这个测试用例之前,我通常是这样做的。