【问题标题】:KnockoutJS Not Populating $root observable inside the "With" Binding ContextKnockoutJS 没有在“With”绑定上下文中填充 $root observable
【发布时间】:2014-03-26 07:22:08
【问题描述】:

我已经搜索并搜索了一个答案,所以希望我没有在任何地方重复这个。

我正在使用 ASP .NET MVC5,将 KnockoutJS 作为我的 ORM。

由于某种原因,当我尝试使用 $root 绑定上下文(一旦在“with”绑定上下文中)引用回 ViewModel 时,DOM 中没有填充数据

with 绑定上下文是在普通的 mvc 视图剃须刀页面中声明的,但是我在加载到主视图的局部视图中使用 $root 绑定上下文。

有没有人遇到过这样的问题或者可以发现我的错误?我将在下面粘贴我的 viewmodel 和 html 代码。

视图模型

var ProfileViewModel = function () {
    var self = this;
    this.Member = ko.observable(); - With Binding to this
    this.SocialNetworks = ko.observableArray();
    this.Skills = ko.observableArray();
    this.SkillsFilter = ko.observable(""); - Trying to access these from root
    this.FilteredSkills = ko.observableArray();
    this.References = ko.observableArray();
    this.Has = function (has_what) {
        if (has_what) {
            if (has_what.length > 0) {
                return true;
            } else {
                return false;
            }
        }

        return false;
    };

    $.getJSON("/doitgrad/api/member/CameronPearce91", function (allData) {
        self.Member(new DoItGrad.Objects.Member(allData, true));
        self.FilteredSkills = ko.computed(function () {
            return ko.utils.arrayFilter(self.Skills(), function (item) {
                var filter = self.SkillsFilter(),
                    doesnthaveskill = (jQuery.inArray(item, self.Member().details.skills()) == -1),
                    containsfiltertext = (item.title().indexOf(filter) > -1);

                if (filter != "") {
                    return (doesnthaveskill && containsfiltertext);
                } else {
                    return doesnthaveskill;
                }
            });
        });
    })

    $.getJSON("/doitgrad/api/skill/", function (allData) {
        var mappedSkills = $.map(allData, function (item) { return new DoItGrad.Objects.Skill(item); });
        self.Skills(mappedSkills);
    });
}

var model = new ProfileViewModel();
ko.applyBindings(model);

MVC 视图

<section id="profile-details" data-bind="with: Member">
<section id="profile-cover">
    <!-- ko if: details.images.cover() == null -->
        <img src="/DoitGrad/Content/images/Profile/default_cover.jpg">
    <!-- /ko -->
    <!-- ko ifnot: details.images.cover() == null --><!-- /ko -->
    <section class="change-cover">Change cover photo</section>
    <section id="profile-picture">
        <!-- ko if: details.images.profile() == null -->
            <img src="/DoitGrad/Content/images/Profile/default_avatar.png">
        <!-- /ko -->
        <!-- ko ifnot: details.images.profile() == null --><!-- /ko -->

        <h2 id="profile-name" data-bind="text: title">Cameron Pearce</h2>
        <section id="profile-username" data-bind="text: details.username">CameronPearce91</section>
    </section>
</section>
<section id="profile-wrapper">
    <section id="profile-about" data-bind="text: description">Since I have been at uni, I believe I have achieved a lot. I took a year out of my studies to do a work placement year with Xerox based in Welwyn Garden City, primarily focusing on developing C# Web Applications on the MVC framework. It was the best thing I could have done for my career I believe, I have certainly learnt a lot.</section>

@Html.Partial("partialname")

局部视图

<section class="profile-detail-holder">
    <section class="add" data-form="addSkill">+</section>
    <h2 class="profile-detail-header">Skill Wall</h2>
    <ul id="profile-skillwall" data-bind="foreach: details.skills()"></ul>
</section>

<section class="dialog-form" data-form="addSkill">
    <section class="form-cover grey"></section>
    <section class="form-content">
        <section class="form-wrap">
            <section class="form-close">x</section>
            <header class="form-header">Add Skill</header>
            <section class="form-body">
                <form id="dig-member-addskill" class="area" method="post" action="#">
                    <input type="text" data-bind="text: $root.SkillsFilter" placeholder="Filter list of skills..." class="ui-textbox"></input>
                    <ul data-bind="foreach: $root.FilteredSkills"></ul>
                    <section class="ui-button submit">
                        <input type="submit" value="Add">
                    </section>
                </form>
            </section>
        </section>
    </section>
</section>

如果有人需要更多信息,请随时询问。

【问题讨论】:

  • 您可以在“with”绑定中使用
    显示 $root 包含的内容
  • 好的,刚刚试过,observableArray FilteredSkills 似乎没有填充任何东西?但是,如果我在控制台中引用模型,它会填充数据......有什么想法吗?

标签: javascript asp.net-mvc knockout.js


【解决方案1】:

我想我已经发现了,而且很简单:

<input type="text" data-bind="text: $root.SkillsFilter" placeholder="Filter list of skills..." class="ui-textbox"></input>

您正在输入字段上使用文本绑定,因此更新输入不会更改可观察对象。改用值绑定:

<input type="text" data-bind="value: $root.SkillsFilter" placeholder="Filter list of skills..." class="ui-textbox"></input>

【讨论】:

  • 这对文本框很有效!我在使用可观察数组“FilteredSkills”填充无序列表时遇到问题。我已经将 $root 转换为 json 并且模型在 observable 数组中没有任何数据,但是如果我使用 chrome 控制台引用它,它会填充正确的数据...
  • 如何显示列表?您的 ul 元素为空
    • 抱歉忘记在问题中添加标记:
    • 我认为这是因为您在 getJSON 回调中重新定义了 FilteredSkills。您应该立即使用 computedObservable 定义,而不是一开始就将其定义为 observableArray。
    • 谢谢大家,最后,我用一个空的成员对象初始化了Member observable,然后将过滤后的技能计算为observable 声明回视图模型的根。
    猜你喜欢
    • 1970-01-01
    • 2013-06-22
    • 1970-01-01
    • 1970-01-01
    • 2012-07-22
    • 1970-01-01
    • 1970-01-01
    • 2015-01-20
    • 2012-04-07
    相关资源
    最近更新 更多