将 C# 模型从视图传递到 Javascript

Pass C# Model from View to Javascript

本文关键字:Javascript 视图 模型      更新时间:2023-09-26

我正在将这个视图模型传递给我的视图:

  public class DashboardViewModel
  {
    public List<UserTask> UserTasks {get; set;}
    public List<WorkItem> WorkItems {get; set;}
  }    

从视图中,我像这样迭代工作项:

 @foreach (var item in Model.WorkItems)
 {
    @item.Name
    @item.HoursLogged
    <button value="@item">UPDATE</button>
 }

当我单击按钮时,jQuery函数正在打开一个模态。

我需要将项目传递给模态才能显示所有项目信息。

这是javascript函数:

$(buttonEl).click(function () {
   //code to open modal
   var item = this.value;
});

在"this.value"中传递的值不是一个对象,而是一个带有工作项命名空间的字符串。

我也尝试过使用内联点击功能:

<button onclick="openModal('@item')">UPDATE</button>

但结果相同。

知道吗?

我通常用它来从MVC翻译成javascript!

@Html.Raw(Json.Encode(item))

我使用以下命令将从 Razor 视图中的控制器传递的模型对象转换为 JavaScript 中的 JSON 对象。

<script>
    let jsonData = @Html.Raw(Json.Serialize(Model))
    console.log(jsonData)
</script>
视图中

的@item会将项目打印为普通字符串(项目。ToString())。我认为您想要的是将字符串解析为 Javascript 对象,对吧?

一种方法是在模型中实现一个方法,如 JSON.stringify()。该方法可以将 C# 模型解析为 JSON 字符串:

{
 "Name" : "Scott",
 "HoursLogged" : "2"
}

然后,您可以使用 JSON.parse() 将字符串解析为 View 中的 JSON 对象。在这种情况下,您可以使用 JSON 对象。一些想法:

C#:

public class Item
{
 public string Name { get; set; }
 public int HoursLogged { get; set; }
 public string ToJsonString()
 {
  return "{" + "'"Name'":" + Name + ",HoursLogged:" + HoursLogged + "}";
 }
}

.JS:

var jsonStr = '@item.ToJsonString()';
var jsonObj = JSON.parse(jsonStr);
console.log(jsonObj.Name);
console.log(jsonObj.HoursLogged);

还可以使用牛顿来串化 C# 模型。

您应该存储用于循环到 javascript 变量的数据,并在单击按钮时查询该变量。在按钮的数据属性上保留一个唯一标识符,以便稍后使用。由于它是一个数组,您可以简单地使用与 (js) 数组索引匹配的计数器变量。

@{ var counter = 0;}
@foreach (var item in Model.WorkItems)
 {
    @item.Name
    <button class="updateBtns" data-index="@counter">UPDATE</button>
    counter++;
 }

在同一个 Razor 视图中,有这个 JavaScript,你将Model.WorkItems集合序列化为 JavaScript 数组并将其存储在变量中。

<script>
  $(function() { 
     var dataArr = @Html.Raw(Newtonsoft.Json.JsonConvert.SerializeObject(Model.WorkItems));
      $(".updateBtns").click(function (e) {
          e.preventDefault();
          var selectedItem = dataArr[$(this).data("index")];
          console.log(selectedItem);
      });    
  });    
</script>

您可能应该退后几步以了解这里发生了什么。 Web 请求实际上只是一堆字符串,MVC .net 做了一些事情来尝试简化从使用对象到直接字符串的过渡,但正如你所看到的,它不能做所有事情。 因此,要点是,您在页面上呈现时要处理事物,就好像它们都是字符串一样。

话虽如此,有很多方法可以解决这个问题。 如前所述,您可以将所有工作项对象转换为 javascript 对象,并将它们从 javascript 数组中拉出。 或者我个人喜欢做的是简单地让按钮包含对象的 id,然后执行 ajax 调用以从服务器获取最新数据。

后端:

[HttpPost]
public string GetWorkItemById(int id)
{
//get or create WorkItem here
WorkItem workItem = new WorkItem(id);
workItem.Name = "Foobar";
workItem.HoursLogged = "127001";
return Newtonsoft.Json.JsonConvert.SerializeObject(workItem);
}

前端:

    $(buttonEl).click(function () {    
    var id = this.value; //assuming you store the id in the button's value
    $.ajax({
          type: "POST",
          url: "@(Url.Action("GetWorkItemById"))",
          data: ({
                    Id:id
                 }),
          success: success,
          dataType: dataType, 
          success: function(result){
                var name = result.Name; // Foobar
                var hoursLogged = result.HoursLogged; // 127001
                //populate text fields using jquery
          }
        })
    });