【问题标题】:Open mvc view in new window from controller从控制器在新窗口中打开 mvc 视图
【发布时间】:2013-01-24 19:55:21
【问题描述】:

有什么方法可以在新窗口中通过控制器操作打开视图?

public ActionResult NewWindow()
{
    // some code
    return View();
}

如何让 NewWindow.cshtml 视图在新的浏览器选项卡中打开?

我知道如何通过视图中的链接执行此操作 - 这不是问题所在。有没有人从 controller action 想出办法来做到这一点?

【问题讨论】:

    标签: asp.net-mvc-4


    【解决方案1】:

    这不能在控制器本身内完成,而是从您的视图中完成。在我看来,您有两种选择:

    1. 使用“_blank”属性装饰您的链接(使用 HTML 助手和直接 HMTL 语法的示例)

      • @Html.ActionLink("linkText", "Action", new {controller="Controller"}, new {target="_blank"})
      • <a href="@Url.Action("Action", "Controller")" target="_blank">Link Text</a>
    2. 使用Javascript打开一个新窗口

      window.open("Link URL")

    【讨论】:

    • 如果我想通过链接在新窗口中打开视图,我会使用它:@Html.ActionLink("linkText", "Action", "Controller", new { target="_blank" }. 还没有测试过将控制器作为对象 routeValue 传递,你为什么会这样做?但这不是问题。你确实回答了原始问题,尽管“无法完成”,所以我将其标记为答案。跨度>
    • @Joe - 这只是我使用的 Html.ActionLink 重载中的选择,它具有以下签名 - Html.ActionLink(string linkText, string Action, object routeValues, object htmlAttributes) - 但它只是个人选择,您可以使用任何您希望接受 htmlAttributes 参数的重载。
    • 有没有办法为新窗口定义尺寸? (使用剃须刀)
    • @barnes - 我知道如何让弹出窗口达到一定大小的唯一方法是通过 javascript。原因:大多数其他时间,浏览器决定如何处理窗口。 JavaScript 是整个 Web 应用程序堆栈中唯一可以实际操作客户端浏览器的部分。
    • 这就是你指的LINK。如果您知道更好的方法,请分享。
    【解决方案2】:

    您也可以在表单中使用 Tommy 的方法:

    @using (Html.BeginForm("Action", "Controller", FormMethod.Get, new { target = "_blank" }))
    {
    //code
    }
    

    【讨论】:

    • 在我找到的所有可能的解决方案中,我认为这是最好的。它是最简单的,因为它使用了 MVC 框架。
    • 默认提交操作是发布并提交以进行最终操作。我们如何发布表单以启动部分视图(因此在单独的窗口中)以避免主窗口数据丢失。简单的场景就像主表单提交是提交在客户端临时保存的 n 个文件,用户选择并预览第一个。但用户可能会预览某个文件,但仍未提交表单。在这种情况下,用户可能需要在新选项卡中查看该文件。那么我们如何才能为具有不同视图的表单提供两种 POST 方法。
    • 如果您知道请求应始终在新窗口中打开(仅),则此方法效果很好。如果您可能在操作方法(典型的 POST 操作)中检测到服务器端的错误,那么您不希望返回的视图位于新选项卡中……您想使用“返回视图(模型)”而是将错误添加到 ModelState 中。如果您的表单使用 POST 请求类型,请小心新窗口...
    • AKS - 使用单个 POST,但向您的模型添加一个标识符,以便您的回发操作可以检测到您打算做什么,例如一个 SelectedAction 枚举(或 bool 或 ....)。结合 GET 和 POST 操作方法是一种很好的做法,即使回发本身可能会重定向到其他操作。
    【解决方案3】:

    你问错问题了。代码隐藏(控制器)与前端的工作无关。事实上,这就是 MVC 的优势——您可以将代码/概念与视图分开。

    如果您希望某个动作在新窗口中打开,那么指向该动作的链接需要告诉浏览器在单击时打开一个新窗口。

    一个伪例子:<a href="NewWindow" target="_new">Click Me</a>

    仅此而已。设置指向该操作的链接目标。

    【讨论】:

    • POST 控制器方法的视图代码是什么,例如来自视图传递表单对象等的提交操作?上面的动作默认是 GET。
    • 如果你必须用一个帖子来做,那么你会做一个<form method="post" action="url" target="_new"> 再次,这是一个前端解决方案,与后端无关。
    【解决方案4】:

    是的,你可以做一些棘手的工作来模拟你想要的:

    1) 通过 ajax 从视图中调用您的控制器。 2)返回您的视图

    3) 在 $.ajax 请求的 success(或者 error!错误对我有用!)部分使用类似以下内容:

    $("#imgPrint").click(function () {
            $.ajax({
                url: ...,
                type: 'POST', dataType: 'json',
                data: $("#frm").serialize(),
                success: function (data, textStatus, jqXHR) {
                    //Here it is:
                    //Gets the model state
                    var isValid = '@Html.Raw(Json.Encode(ViewData.ModelState.IsValid))'; 
                    // checks that model is valid                    
                    if (isValid == 'true') {
                        //open new tab or window - according to configs of browser
                        var w = window.open();
                        //put what controller gave in the new tab or win 
                        $(w.document.body).html(jqXHR.responseText);
                    }
                    $("#imgSpinner1").hide();
                },
                error: function (jqXHR, textStatus, errorThrown) {
                    // And here it is for error section. 
                    //Pay attention to different order of 
                    //parameters of success and error sections!
                    var isValid = '@Html.Raw(Json.Encode(ViewData.ModelState.IsValid))';                    
                    if (isValid == 'true') {
                        var w = window.open();
                        $(w.document.body).html(jqXHR.responseText);
                    }
                    $("#imgSpinner1").hide();
                },
                beforeSend: function () { $("#imgSpinner1").show(); },
                complete: function () { $("#imgSpinner1").hide(); }
            });            
        });      
    

    【讨论】:

      【解决方案5】:

      可以如下使用

      public ActionResult NewWindow()
      {
          return Content("<script>window.open('{url}','_blank')</script>");
      }
      

      【讨论】:

        【解决方案6】:
        @Html.ActionLink("linkText", "Action", new {controller="Controller"}, new {target="_blank",@class="edit"})
        
           script below will open the action view url in a new window
        
        <script type="text/javascript">
            $(function (){
                $('a.edit').click(function () {
                    var url = $(this).attr('href');
                    window.open(url, "popupWindow", "width=600,height=800,scrollbars=yes");
                    });
                    return false;
                });   
        </script>
        

        【讨论】:

          【解决方案7】:

          假设“NewWindow.cshtml”在您的“Home”文件夹中,我已经看到您可以在哪里执行此类操作:

          string url = "/Home/NewWindow";
          return JavaScript(string.Format("window.open('{0}', '_blank', 'left=100,top=100,width=500,height=500,toolbar=no,resizable=no,scrollable=yes');", url));
          

          return Content("/Home/NewWindow");
          

          如果您只想在选项卡中打开视图,您可以使用 JavaScript 点击事件来呈现您的部分视图。这将是 NewWindow.cshtml 的控制器方法:

          public ActionResult DisplayNewWindow(NewWindowModel nwm) {
              // build model list based on its properties & values
              nwm.Name = "John Doe";
              nwm.Address = "123 Main Street";
              return PartialView("NewWindow", nwm);
          }
          

          你在页面上的标记是这样的:

          <input type="button" id="btnNewWin" value="Open Window" />
          <div id="newWinResults" />
          

          还有 JavaScript(需要 jQuery):

          var url = '@Url.Action("NewWindow", "Home")';
          $('btnNewWin').on('click', function() {
              var model = "{ 'Name': 'Jane Doe', 'Address': '555 Main Street' }"; // you must build your JSON you intend to pass into the "NewWindowModel" manually
              $('#newWinResults').load(url, model); // may need to do JSON.stringify(model)
          });
          

          请注意,此 JSON 将覆盖上述 C# 函数中的内容。我把它放在那里只是为了演示如何对值进行硬编码。

          (改编自Rendering partial view on button click in ASP.NET MVC

          【讨论】:

            【解决方案8】:

            我在我的控制器中分配了 javascript:

            model.linkCode = "window.open('https://www.yahoo.com', '_blank')";
            

            在我看来:

            @section Scripts{
                <script @Html.CspScriptNonce()>
            
                $(function () {
            
                    @if (!String.IsNullOrEmpty(Model.linkCode))
                    {
                        WriteLiteral(Model.linkCode);
                    }
                });
            

            这会打开一个带有链接的新标签,然后转到它。

            有趣的是,在本地运行它会使用弹出窗口拦截器,但似乎在服务器上运行良好。

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2018-08-13
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 2011-12-09
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多