Bind View Into _Layout File In MVC Using Razor Engine

Introduction

In this session, we will briefly discuss how to bind View.cshtml DOM content into _Layout.cshtml using Razor Engine.

Razor Engine is a free Microsoft tool that you can download from NuGet Package Manager. It contains the collection of methods and properties. We have an option to bind one View into another using “@Model.Parameter”.

  1. <!DOCTYPE html>  
  2. <html>  
  3. <head>  
  4.     <meta name="viewport" content="width=device-width" />  
  5. </head>  
  6. <body>  
  7.     <table class="menu">  
  8.         <tr>  
  9.             <td><h1>Report Header</h1></td>  
  10.             <td></td>  
  11.         </tr>  
  12.     </table>  
  13.     @Model.DynamicView  
  14. </body>  
  15. </html>  

The above code is a structure where we will insert a set of code from another View using _Layout.cshtml.

Create Home Controller

Here, we have created the Home Controller and Action Method called as Generate. Create the View for the method.

Create new View

Right-click on the method, select “Add View”. A new popup window will appear. Click “OK”.
  1. public class HomeController : Controller  
  2. {  
  3. public ActionResult Generate()  
  4.         {  
  5.             return View();  
  6.         }  
  7.   
  8. }  

Create Generate.cshtml in View

Create the View from the Controller. Here, I have created the View called Generate.cshtml.

You can see that I have included the button click event to call Razor Engine method.

  1. @{  
  2.     ViewBag.Title = "Generate";  
  3.     Layout = "~/Views/Shared/_Layout.cshtml";  
  4. }  
  5.   
  6. <h2>PDF Templates</h2><br />  
  7.   
  8. <div>  
  9.     @Html.ActionLink("Template 1""GenerateReport""HOME"new { @class = "btn btn-primary" }) <b>View Name: PDF</b>  
  10. </div>  
  11.   
  12. <div>  
  13. </div>  

RouteConfig.cs

Change the “Route Configuration” in class file to redirect your current controller at run-time.

  1. public class RouteConfig  
  2. {  
  3.   public static void RegisterRoutes(RouteCollection routes)  
  4.   {  
  5.      routes.IgnoreRoute("{resource}.axd/{*pathInfo}");  
  6.      routes.MapRoute(  
  7.      name: "Default",  
  8.      url: "{controller}/{action}/{id}",  
  9.      defaults: new { controller = "Home", action = "Generate", id = UrlParameter.Optional });  
  10.    }  
  11.  }  

For example, change your own control name in the “controller” attribute and change the “action”.

Create _LayoutReport.cshtml in Shared View

The _Layout.cshtml file has been created for the report and it is named as _LayoutReport.cshtml.

In the below code, we have mentioned the Model property called “@Model.MyView”. This is used to bind the View into _Layout file using Razor Engine in C#.

  1. <!DOCTYPE html>  
  2. <html>  
  3. <head>  
  4.     <meta name="viewport" content="width=device-width" />  
  5.     <style type="text/css">  
  6.         .menu {  
  7.             background-color: #8383ff;  
  8.             color: white;  
  9.             width: 100%;  
  10.             height: 100px;  
  11.         }  
  12.   
  13.         td {  
  14.             width: 30%;  
  15.             padding-left: 15px;  
  16.         }  
  17.     </style>  
  18. </head>  
  19. <body>  
  20.     <table class="menu">  
  21.         <tr>  
  22.             <td>  
  23.                  
  24.             </td>  
  25.             <td><h1>Report Header</h1></td>  
  26.             <td></td>  
  27.         </tr>  
  28.     </table>  
  29.     @Model.MyView  
  30. </body>  
  31. </html>  

Create PDFSummary.cshtml View

Here is my own template that is used to show the content along with the input model.

  1. <h4>Number</h4>  
  2. <table cellpadding="10" cellspacing="10">  
  3.     <tr>  
  4.         <td>Project Number: </td>  
  5.         <td>@Model.ProjectNumber</td>  
  6.     </tr>  
  7.     <tr>  
  8.         <td>Project Name:</td>  
  9.         <td>@Model.ProjectName</td>  
  10.     </tr>  
  11.     <tr>  
  12.         <td>Element Number:</td>  
  13.         <td>@Model.ElementNumber</td>  
  14.     </tr>  
  15.     <tr>  
  16.         <td>Element Name:</td>  
  17.         <td>@Model.ElementName</td>  
  18.     </tr>  
  19. </table>  
  20. @if (Model.IsShowContent)  
  21. {  
  22.     <a href="https://www.google.co.in/">Click Here</a>  
  23. }  

We have included the Boolean operation to enable/disable the content in page. For example, if the “Model.IsShowContent” is “True”, you will see the content on page else it won’t appear.

Create function in Controller

We have created the function called “GenerateReport()”. This is used to pass the Model from Controller to Razor Engine Method.

  1. public class HomeController : Controller  
  2. {  
  3. public ProjectModel projectModel = new ProjectModel();  
  4.           
  5.         public ActionResult Generate()  
  6.         {  
  7.             return View();  
  8.         }  
  9.   
  10.         public void GenerateReport()  
  11.         {  
  12.             try  
  13.             {  
  14.                 projectModel = projectModel.TempModel("proj1234");  
  15.                 RazorViewEngineFormat.RenderEngineToString(projectModel);  
  16.             }  
  17.             catch (Exception ex)  
  18.             {  
  19.             }  
  20.         }  
  21. }  

In the above function, I have implemented the Controller with the Model data. You can see that we have referred the method called as “TempModel”. The model will fetch a set of data from the database.

Create a new Model

This static method is used to play with data around Razor Engine functionality.

  1. public class ProjectModel  
  2. {  
  3.  
  4.         #region "Public Property"  
  5.   
  6.         /// <summary>  
  7.         /// get/set the Project Number  
  8.         /// </summary>  
  9.         public string ProjectNumber { get; set; }  
  10.   
  11.         /// <summary>  
  12.         /// get/set the Project Name  
  13.         /// </summary>  
  14.         public string ProjectName { get; set; }  
  15.   
  16.         /// <summary>  
  17.         /// get/set the Element Number  
  18.         /// </summary>  
  19.         public string ElementNumber { get; set; }  
  20.   
  21.         /// <summary>  
  22.         /// get/set the Element Name  
  23.         /// </summary>  
  24.         public string ElementName { get; set; }  
  25.   
  26.         /// <summary>  
  27.         /// get/set the Action Content  
  28.         /// </summary>  
  29.         public bool IsShowContent { get; set; }  
  30.  
  31.         #endregion  
  32.  
  33.         #region "Public Method"  
  34.   
  35.         public ProjectModel TempModel(string ProjectID)  
  36.         {  
  37.             ProjectModel projectModel = new ProjectModel();  
  38.             projectModel.ProjectNumber = "prj1254215";  
  39.             projectModel.ProjectName = "Project Audit";  
  40.             projectModel.ElementNumber = "154-154-15454";  
  41.             projectModel.ElementName = "Test element";  
  42.             projectModel.IsShowContent = true;  
  43.             return projectModel;  
  44.         }  
  45.         #endregion  
  46.   
  47.     }  

The above “ProjectModel” class contains Properties and Methods.

Convert Razor Engine ToString

This is the Razor Engine method, which is used to append view.cshtml into _Layout.cshtml file. Make sure, you have included the RazorEngine.dll in NuGet Package Manager.

ASP.NET

  1. public static void RenderEngineToString(object model)  
  2. {  
  3.    try  
  4.    {  
  5.      string emailHtmlBody = string.Empty;  
  6.      GenerateFile generateFile = new GenerateFile();  
  7.      string reportHeader = File.ReadAllText(HttpContext.Current.Server.MapPath("~/Views/Shared/_LayoutReport.cshtml"));  
  8.       HtmlString tableValue = new HtmlString(File.ReadAllText(HttpContext.Current.Server.MapPath("~/Views/Home/PDFSummary.cshtml")));  
  9.        string result = Razor.Parse(reportHeader, new { MyView = tableValue });  
  10.        string htmlCompression = HttpUtility.HtmlDecode(result);  
  11.        using (TemplateService templateService = new TemplateService())  
  12.        {  
  13.          emailHtmlBody = templateService.Parse(htmlCompression, model, nullnull);  
  14.        }  
  15.        generateFile.DownloadPDF(emailHtmlBody.ToString());  
  16.     }  
  17.     catch (Exception ex)  
  18.     {  
  19.   
  20.     }  
  21.  }  

In the above code,

  • Collecting _Layout object model from cshtml and assigned to reportHeader (string property).
  • The View object model content collected from cshtml and assigned to tableValue (HtmlString Property)
  • Using Razor.Parse() method the View content will be concatenated into Layout file.
  • The template service is used to assign the model property value to model attributes.

SCREENSHOT

In the screenshot, I have marked the Model property where we are going to bind the dynamic Views.

ASP.NET

View DOM Object

This is “*.cshtml” file, which contains the collection of tags and parameters.

ASP.NET

 Now, let us bind the below Document Object Model into _Layout.cshtml file.

ASP.NET

Also, the “Template Service” will bind the all model property values into Model attributes through “Parse” model.

OUTPUT

Eventually, the final output looks like below.

ASP.NET

Please leave your comment if you find any issues or want to give feedback on this article.


Similar Articles