Jquery Knockout.js-每5秒用新值更新一次页面

Jquery Knockout.js-每5秒用新值更新一次页面,jquery,asp.net-mvc,knockout.js,asp.net-web-api,Jquery,Asp.net Mvc,Knockout.js,Asp.net Web Api,我正在研究使用MVC Web API的knockout.js,我正在尝试创建一个Hello World页面,该页面每5秒更新一次时间。它是每5秒进行一次呼叫,我可以在我的控制器(断点)中看到这一点,但屏幕上仍然没有显示任何内容 更新: 我一直在研究这个问题,现在我已经确定我正在从服务器获取数据,每5秒向控制器发出一次调用,并且它正在返回我需要的JSON(警报显示了这一点),但是页面上的span元素上仍然没有显示任何内容 我实际上需要使用映射功能,因为我正在开发一个更大的网站,该网站有一个具有50

我正在研究使用MVC Web API的knockout.js,我正在尝试创建一个Hello World页面,该页面每5秒更新一次时间。它是每5秒进行一次呼叫,我可以在我的控制器(断点)中看到这一点,但屏幕上仍然没有显示任何内容

更新: 我一直在研究这个问题,现在我已经确定我正在从服务器获取数据,每5秒向控制器发出一次调用,并且它正在返回我需要的JSON(警报显示了这一点),但是页面上的span元素上仍然没有显示任何内容

我实际上需要使用映射功能,因为我正在开发一个更大的网站,该网站有一个具有50多个属性的模型,并且不特别想在viewmodel中逐一查看和映射它们

我在下面包含了我的代码

<span data-bind="text: TimeString"></span>

<script type="text/javascript">
    var viewModel;
var getUpdates = setInterval(function () {
    $.getJSON(
        "/Values/Get", {},
        function (model) {
            alert(model.TimeString);
            ko.mapping.fromJS(model, viewModel);
        });
}, 5000);

$(document).ready(
    function () {
        $.getJSON(
            "/Values/Get", {},
            function (model) {
                var viewModel = ko.mapping.fromJS(model);
                alert(model.TimeString);
                ko.applyBindings(viewModel);
            });
    });

function bindViewModel(model) {
    ko.applyBindings(model);
}
如果你遵守规则,就不会太难了。在第一次调用服务器时,请执行以下操作:

var viewModel = ko.mapping.fromJS(model);
ko.applyBindings(viewModel);
您正在使用JS对象应用绑定(如果我正确读取,getJSON将返回JS对象,而不是JSON字符串)

之后,在重复功能中,执行以下操作:

ko.mapping.fromJS(model, viewModel);
从文件中:

  • 对象的所有属性都转换为可观察的属性。如果更新会改变值,它会更新可观察值
  • 数组被转换为可观察数组。如果更新将更改项目的数量,它将执行适当的添加/删除操作 行动。它还将努力保持订单与原始订单相同 JavaScript数组

您不需要替换完整的视图模型,而是可以更新从Ajax请求返回的属性,如下所示:

$(function() {
    var vm = {
        TimeDT: ko.observable(),
        TimeString: ko.observable()
    };

    function updateValues() {    
        $.getJSON("/Values/Get").done(function(data) {
            vm.TimeDT(data.TimeDT);
            vm.TimeString(data.TimeString);
        });
    }

    ko.applyBindings(vm);

    updateValues();
    setInterval(updateValues, 5000);
});

您可以在这里看到一个我在JSFIDLE中制作的声明。

免责声明:我与Ben一起工作

代码中有几个问题,第一个是缺少一些javascript引用,第二个是每当计时器循环通过时,viewModel对象总是为null

您需要从下载knockout映射Javascript文件,将其命名为knockout.mapping-latest.js并将其保存在Scripts目录中。然后确保添加了对jquery和knockout.js的引用

更新的Razor视图如下所示:

<div id="body">

    <span data-bind='text: TimeString'></span>

    <script src="~/Scripts/jquery-1.8.2.js" type="text/javascript"></script>
    <script src="~/Scripts/knockout-2.2.0.debug.js" type="text/javascript"></script>
    <script src="~/Scripts/knockout.mapping-latest.js" type="text/javascript"></script>
    <script type="text/javascript">
        var viewModel;
        var getUpdates = setInterval(function () {
            $.getJSON(
                "/Values/Get", {},
                function (model) {
                    //alert(model.TimeString);
                    ko.mapping.fromJS(model, viewModel);
                });
        }, 5000);

        var viewModelSet = false;

        $(document).ready(
            function () {
                $.getJSON(
                    "/Values/Get", {},
                    function (model) {
                        viewModel = ko.mapping.fromJS(model);
                        ko.applyBindings(viewModel);
                    });
            });

        function bindViewModel(model) {
            ko.applyBindings(model);
        }
    </script>    

</div>

var模型;
var getUpdates=setInterval(函数(){
$.getJSON(
“/Values/Get”,{},
功能(模型){
//警报(model.TimeString);
fromJS(model,viewModel);
});
}, 5000);
var viewModelSet=false;
$(文件)。准备好了吗(
函数(){
$.getJSON(
“/Values/Get”,{},
功能(模型){
viewModel=ko.mapping.fromJS(模型);
应用绑定(视图模型);
});
});
函数bindViewModel(模型){
ko.应用绑定(模型);
}

只需补充一点,类中的公共字段通常是不允许的,在ViewModel中,HelloWorldModel实例不会从代码中的任何其他地方访问,只能从该类中访问,因此它可以是私有的。如果它是从其他地方访问的,最好的做法是保持它的隐私,并通过一个属性公开它。更多信息。

绑定中的
数据是什么?是定制的吗?或者你的意思是
?updateFromJSON从哪里来?在文档中,它声明了
ko.mapping.fromJS(数据,视图模型)
您应该在最初的AJAX调用中使用映射插件,而不仅仅是每5秒重复一次的插件。他确实不需要完全替换viewmodel。但是有了这个解决方案,你又可以自己完成所有的工作了。KO mapping插件的好处在于它可以为您做到这一点。第一次(创建viewmodel时),以及以后要更新viewmodel时。它将为您更新所有可观测数据(使用
ko.mapping.fromJS(model,viewModel);
)。当你有几个可观察的属性,当你随着时间增加属性时,这是很有趣的。是的,我也同意你的观点。在这种情况下,我将使他当前的ViewModel成为更复杂(组合?)的ViewModel的属性。我给出的答案对于简单的场景是有效的,比如Ben在他的例子中给出的场景。
<div id="body">

    <span data-bind='text: TimeString'></span>

    <script src="~/Scripts/jquery-1.8.2.js" type="text/javascript"></script>
    <script src="~/Scripts/knockout-2.2.0.debug.js" type="text/javascript"></script>
    <script src="~/Scripts/knockout.mapping-latest.js" type="text/javascript"></script>
    <script type="text/javascript">
        var viewModel;
        var getUpdates = setInterval(function () {
            $.getJSON(
                "/Values/Get", {},
                function (model) {
                    //alert(model.TimeString);
                    ko.mapping.fromJS(model, viewModel);
                });
        }, 5000);

        var viewModelSet = false;

        $(document).ready(
            function () {
                $.getJSON(
                    "/Values/Get", {},
                    function (model) {
                        viewModel = ko.mapping.fromJS(model);
                        ko.applyBindings(viewModel);
                    });
            });

        function bindViewModel(model) {
            ko.applyBindings(model);
        }
    </script>    

</div>