我正在尝试使用MVC方法来使用原始JS组件。
但是,通过以下设置,我无法根据模型更新视图。
一切顺利,直到代码到达视图构造函数为止。在那里,必须根据模型中指定的值(通过控制器推送)来更新视图。
我确实获得了价值。但是,HTML模板未更新。
现在,以下代码示例显示了许多样板代码。这是获得功能正常的示例所必需的。痛点似乎主要在TestView
类中。
// unrelated helper function
const stringToHTMLCollection = function(string) {
const template = document.createElement('template');
string = string.trim(); // Never return a text node of whitespace as the result
template.innerHTML = string;
return template.content.children;
}
class TestModel {
constructor(data) {
this._firstValue = data.first;
}
get firstValue() {
return this._firstValue;
}
}
class TestController {
constructor(model) {
this.model = model;
}
get firstValue() {
return this.model.firstValue;
}
}
class TestView {
static htmlString() {
return `<div>
<ul>
<li id="first-list-item">0</li>
<li>0</li>
</ul>
</div>`
}
constructor(controller) {
this.controller = controller;
this.testView = TestView.htmlString();
this.list = stringToHTMLCollection(this.testView)[0];
this.listItems = this.list.getElementsByTagName('li');
this.init();
}
init() {
// this is going well, output: 100
console.log(this.controller.firstValue);
Object.entries(this.listItems).forEach(([key, price]) => {
if (price.id === 'first-list-item') {
price.innerHTML = this.controller.firstValue;
}
});
// this is going well, output element with innerText of 100
console.log(this.listItems[0]);
}
renderInto(targetNode) {
if(!targetNode) return;
targetNode.insertAdjacentHTML('beforeend', this.testView);
}
}
const resultElement = document.getElementById('result');
function testComponent(pricing) {
const testModel = new TestModel(pricing),
testController = new TestController(testModel);
return new TestView(testController);
}
const pricing = {
first: 100,
second: 200
}
testComponent(pricing).renderInto(result);
<div id="result"></div>
答案 0 :(得分:0)
嗯,我想stringToHTMLCollection实际上创建了一个新实例。在构造函数中使用它作为定义,然后在init解决它之后将其返回。
示例:
// unrelated helper function
const stringToHTMLCollection = function(string) {
const template = document.createElement('template');
string = string.trim(); // Never return a text node of whitespace as the result
template.innerHTML = string;
return template.content.children;
}
class TestModel {
constructor(data) {
this._firstValue = data.first;
}
get firstValue() {
return this._firstValue;
}
}
class TestController {
constructor(model) {
this.model = model;
}
get firstValue() {
return this.model.firstValue;
}
}
class TestView {
static htmlString() {
return `<div>
<ul>
<li id="first-list-item">0</li>
<li>0</li>
</ul>
</div>`
}
constructor(controller) {
this.controller = controller;
this.testView = TestView.htmlString();
this.html = stringToHTMLCollection(this.testView);
this.list = this.html[0];
this.listItems = this.list.getElementsByTagName('li');
this.init();
}
init() {
// this is going well, output: 100
console.log(this.controller.firstValue);
Object.entries(this.listItems).forEach(([key, price]) => {
if (price.id === 'first-list-item') {
price.innerHTML = this.controller.firstValue;
}
});
// this is going well, output element with innerText of 100
console.log(this.listItems[0]);
}
renderInto(targetNode) {
if(!targetNode) return;
targetNode.insertAdjacentElement('beforeend', this.html[0]);
}
}
const resultElement = document.getElementById('result');
function testComponent(pricing) {
const testModel = new TestModel(pricing),
testController = new TestController(testModel);
return new TestView(testController);
}
const pricing = {
first: 100,
second: 200
}
testComponent(pricing).renderInto(result);
<div id="result"></div>