• Razor视图引擎学习


    RazorView:

      RazorView和WebFormView都是继承自:BuildManageCompiledView。RazorView和WebFormView都有其各自对应的一个引擎:RazorViewEngine和WebFormViewEngine,今天咱们不讲WebFormView,主讲RazorView,我们来看看RazorView类型。在Razor引擎下,通过这一类型来表示View。

     1 public class RazorView : BuildManagerCompiledView
     2 {
     3     // Methods
     4     public RazorView(ControllerContext controllerContext, string viewPath, string layoutPath, bool runViewStartPages, IEnumerable<string> viewStartFileExtensions);
     5     public RazorView(ControllerContext controllerContext, string viewPath, string layoutPath, bool runViewStartPages, IEnumerable<string> viewStartFileExtensions, IViewPageActivator viewPageActivator);
     6     protected override void RenderView(ViewContext viewContext, TextWriter writer, object instance);
     7 
     8     // Properties
     9     internal DisplayModeProvider DisplayModeProvider { get; set; }
    10     public string LayoutPath { get; private set; }
    11     public bool RunViewStartPages { get; private set; }
    12     internal StartPageLookupDelegate StartPageLookup { get; set; }
    13     public IEnumerable<string> ViewStartFileExtensions { get; private set; }
    14     internal IVirtualPathFactory VirtualPathFactory { get; set; }
    15 }

    RenderView方法重写了基类BuildManagerCompiledView的方法。 属性LayoutPath表示布局文件的虚拟路径,而RunViewStartPages则表示是否运行ViewSatrt视图

    ,ViewStartFileExtensions属性则表示的是ViewStart文件的后缀。例如:“cshtml”、"vbhtml"。我们再来看看其内部的一个很重要的方法:RenderView.

     1   protected override void RenderView(ViewContext viewContext, TextWriter writer, object instance)
     2     {
     3         if (writer == null)
     4         {
     5             throw new ArgumentNullException("writer");
     6         }
     7         WebViewPage page = instance as WebViewPage;
     8         if (page == null)
     9         {
    10             throw new InvalidOperationException(string.Format(CultureInfo.CurrentCulture, MvcResources.CshtmlView_WrongViewBase, new object[] { base.ViewPath }));
    11         }
    12         page.OverridenLayoutPath = this.LayoutPath;
    13         page.VirtualPath = base.ViewPath;
    14         page.ViewContext = viewContext;
    15         page.ViewData = viewContext.ViewData;
    16         page.InitHelpers();
    17         if (this.VirtualPathFactory != null)
    18         {
    19             page.VirtualPathFactory = this.VirtualPathFactory;
    20         }
    21         if (this.DisplayModeProvider != null)
    22         {
    23             page.DisplayModeProvider = this.DisplayModeProvider;
    24         }
    25         WebPageRenderingBase startPage = null;
    26         if (this.RunViewStartPages)
    27         {
    28             startPage = this.StartPageLookup(page, RazorViewEngine.ViewStartFileName, this.ViewStartFileExtensions);
    29         }
    30         HttpContextBase httpContext = viewContext.HttpContext;
    31         WebPageRenderingBase base4 = null;
    32         object model = null;
    33         page.ExecutePageHierarchy(new WebPageContext(httpContext, base4, model), writer, startPage);
    34     }

    在此方法中,首先是将传过来的object对象转换为一个WebViewPage对象,接着设置WebViewPage对象的page的布局文件路径,视图文件路径,以及ViewContext和ViewData属性。接着执行初始化,对WebViewPage内部的一些属性进行设置,接着判断执行ViewStart页面的情况,得到表示开启页面的WebPageRenderingBase对象。最后执行page对象的ExecutePageHierarchy方法, 运行执行管道的页层次结构。

    来瞧瞧其基类:BuilderManagerCompiledView

     1 public abstract class BuildManagerCompiledView : IView
     2 {
         // Methods11     internal BuildManagerCompiledView(ControllerContext controllerContext, string viewPath, IViewPageActivator viewPageActivator, IDependencyResolver dependencyResolver);
    12     public void Render(ViewContext viewContext, TextWriter writer);
    13     protected abstract void RenderView(ViewContext viewContext, TextWriter writer, object instance);
    14 
    15     // Properties
    16     internal IBuildManager BuildManager { get; set; }
    17     public string ViewPath { get; protected set; }
    18 }

    BuilderManagerCompiledView提供了一个RenderView的抽象方法供子类重写,上面我们已经讲过RenderView方法,可以参考。其中有一个Render方法,我们来看看:

     1 public void Render(ViewContext viewContext, TextWriter writer)
     2 {
     3     if (viewContext == null)
     4     {
     5         throw new ArgumentNullException("viewContext");
     6     }
     7     object instance = null;
     8     Type compiledType = this.BuildManager.GetCompiledType(this.ViewPath);
     9     if (compiledType != null)
    10     {
    11         instance = this.ViewPageActivator.Create(this._controllerContext, compiledType);
    12     }
    13     if (instance == null)
    14     {
    15         throw new InvalidOperationException(string.Format(CultureInfo.CurrentCulture, MvcResources.CshtmlView_ViewCouldNotBeCreated, new object[] { this.ViewPath }));
    16     }
    17     this.RenderView(viewContext, writer, instance);
    18 }

    该方法中,首先是根据虚拟路径获得所在View的类型,然在根据类型和控制器上下文创建对象,这个方法最终还是调用了RenderView方法,将instance对象作为参数带入方法中.

    可能你对BuildManagerCompiledView构造函数也感兴趣,特别是IViewPageActivator和IDependencyResolver。

    1 internal BuildManagerCompiledView(ControllerContext controllerContext, string viewPath, IViewPageActivator viewPageActivator, IDependencyResolver dependencyResolver)
    2 {
    3     this._controllerContext = controllerContext;
    4     this.ViewPath = viewPath;
    5     this.ViewPageActivator = viewPageActivator ?? new BuildManagerViewEngine.DefaultViewPageActivator(dependencyResolver);
    6 }

    看到构造函数结尾对当前ViewPageActivator属性进行赋值的时候,给了一个默认值。看到了吧,当为null的时候,赋了一个DefaultViewPageActivator对象,此时构造函数中传入的参数是dependencyResolver对象。

    Razor视图引擎:

     1 public class RazorViewEngine : BuildManagerViewEngine
     2 {
     3     // Fields
     4     internal static readonly string ViewStartFileName;
     5 
     6     // Methods
     7     static RazorViewEngine();
     8     public RazorViewEngine();
     9     public RazorViewEngine(IViewPageActivator viewPageActivator);
    10     protected override IView CreatePartialView(ControllerContext controllerContext, string partialPath);
    11     protected override IView CreateView(ControllerContext controllerContext, string viewPath, string masterPath);
    12 }

    RazorViewEngine继承自BuildManagerViewEngine,内部通过控制器上下文,重写了基类的CreatePartialView创建分布视图方法和CreateView创建视图方法。构造函数设置了视图的搜寻顺序,如果没有提供,则按照这个顺序进行搜寻。

  • 相关阅读:
    iOSraywenderlich翻译使用MapKit叠加图层
    IOSTableView学习V2.0
    html的<input>标签常用属性
    SQLSqlServer中decimal(numeric )、float 和 real 数据类型的区别[转]
    PhoneGapV1.0
    IOSPlistV1.0
    IOS使用 UITableView 创建表格应用演练(1)——一个简单的表格应用V3.0
    IOSTableView学习V4.0
    IOS从plist文件加载并显示数据
    学习思路
  • 原文地址:https://www.cnblogs.com/yangda/p/2994865.html
Copyright © 2020-2023  润新知