与Kendo复杂对象的模型绑定问题

时间:2013-12-24 23:43:59

标签: kendo-ui kendo-grid kendo-asp.net-mvc

我的问题与此Model binding issues with Kendo objects with complex child properties非常相似。唯一的区别是我在对象中有另一个级别。

我的模特是:

Public Person 
{
   public int Id {get;set;}
   public string Name {get;set;}
   public IEnumerable<Course> Courses {get;set;}
}

public Course 
{
   public int Id {get;set;}
   public string Description {get;set;}
   public IEnumerable<Schedule> Schedules {get;set;}
}

Public Schedule 
{
   public DateTime Init {get;set;}
   public DateTime End {get;set;} 
}

此模型绑定到KendoGrid。一切都运行良好,但是当我发布模型时,Init和End属性总是为空。

在Ajax数据源中:

.Update(update => update.Action("Update", "Controller").Data("serialize"))
.Create(create => create.Action("Create", "Controller").Data("serialize"))

   <script>
        function serialize(data) {
           for (var property in data) {
            if ($.isArray(data[property])) {
                serializeArray(property, data[property], data);
            }
        }
    };

    function serializeArray(prefix, array, result) {
    for (var i = 0; i < array.length; i++) {
        if ($.isPlainObject(array[i])) {
            for (var property in array[i]) {
                result[prefix + "[" + i + "]." + property] = array[i][property];
            }
        }
        else {
            result[prefix + "[" + i + "]"] = array[i];
        }
    }
}
    </script>

发送列表计划的属性我需要做些什么?

1 个答案:

答案 0 :(得分:1)

我还查看了他们的serializeArray解决方案,但是在我拥有3级对象的情况下它对我不起作用。我可以解决这个问题,但后来我不想编写递归代码。我使用的解决方案非常简单,并且与我遇到的问题保持一致。它非常易读。

我绝对希望剑道能够为他们的网格开箱即用,但是当我提出支持问题时他们就这么说了。

“在这种情况下,您需要将值作为附加数据发送,因为内置过滤不支持集合值。要格式化数据以使其受模型绑定器的约束,您应该遵循我之前的回复中的指南(对象的点符号和数组的索引器)“

这是我的C#ViewModels

   //relates to one control value (for e.g. one entry in multi-select)
    public class FormUnitFilter
    {
        public string Operator { get; set; }
        public string Field { get; set; }
        public string Value { get; set; }
        public List<string> ValueList { get; set; }
    }

    //relates to a set of filters in a combined set (for e.g. the whole multi-select or a radiobutton or date control which appears in a single panel)
    public class FormSetFilter
    {
        public List<FormUnitFilter> Filters { get; set; }
        public string LogicalOperator { get; set; }
    }

    //relates to the whole set of filters present on the screen (for e.g. the filters across different panels)
    public class FormWholeFilter
    {
        public List<FormSetFilter> Filters { get; set; }
        public string LogicalOperator { get; set; }
    }

这是我的js函数,它将这个json模型转换为MVC控制器动作参数识别的类型。

function buildFilterCriteria() {
    var data = {};
    if (modelObj) {
        //reset the filters
        modelObj.FormWholeFilter.Filters.length = 0;

        //Assign FormWholeFilter data (outermost object)
        data["FormWholeFilter.LogicalOperator"] = modelObj.FormWholeFilter.LogicalOperator;
        //now iterate the filters inside FormWholeFilter (1st inner object)
        for (var setIndex = 0; setIndex < modelObj.FormWholeFilter.Filters.length; setIndex++) {
            var setFilter = modelObj.FormWholeFilter.Filters[setIndex];

            data["FormWholeFilter.Filters[" + setIndex + "].LogicalOperator"] = setFilter.LogicalOperator;

            //now iterate the filters inside FormSetFilter (2nd inner object)
            for (var unitIndex = 0; unitIndex < setFilter.Filters.length; unitIndex++) {
                var unitFilter = setFilter.Filters[unitIndex];

                data["FormWholeFilter.Filters[" + setIndex + "].Filters[" + unitIndex + "].Operator"] = unitFilter.Operator;
                data["FormWholeFilter.Filters[" + setIndex + "].Filters[" + unitIndex + "].Field"] = unitFilter.Field;
                data["FormWholeFilter.Filters[" + setIndex + "].Filters[" + unitIndex + "].Value"] = unitFilter.Value;

                if (unitFilter.ValueList)
                    for (var valIndex = 0; valIndex < unitFilter.ValueList.length; valIndex++) {
                        data["FormWholeFilter.Filters[" + setIndex + "].Filters[" + unitIndex + "].ValueList[" + valIndex + "]"] = unitFilter.ValueList[valIndex];
                    }
            }
        }
    }

    return modelObj && data;
}

这是我的控制器动作方法,它采用了Kendo网格数据源请求和我从JavaScript传递的FormWholeFilter。

    public JsonResult ProcessFilters([DataSourceRequest] DataSourceRequest request, FormWholeFilter formWholeFilter)
            {
//Method body
}

另外,当我第一次加载页面时,我已经将modelObj分配给FormWholeFilter空白json,这就是为什么我可以在buildFilterCriteria方法中使用这个变量:

var modelObj;
$(document).ready(function () {
    modelObj = $.parseJSON('@Html.Raw(Json.Encode(@Model))');
});