解读ASP.NET 5 & MVC6系列(16):自定义View视图文件查找逻辑
之前MVC5和之前的版本中,我们要想对View文件的路径进行控制的话,则必须要对IViewEngine
接口的FindPartialView
或FindView
方法进行重写,所有的视图引擎都继承于该IViewEngine
接口,比如默认的RazorViewEngine
。但新版本MVC6中,对视图文件的路径方式却不太一样了,目前有两种方式,一种是通过RazorViewEngine
,另外一种是通过新特性IViewLocationExpander
接口。
通过RazorViewEngine来控制View路径
在新版的RazorViewEngine
中,该类提供了两个虚属性(AreaViewLocationFormats
和ViewLocationFormats
),可以用于重写控制,而不必再对FindPartialView
或FindView
方法进行重写,示例如下:
public class ThemeViewEngine : RazorViewEngine
{
public ThemeViewEngine(IRazorPageFactory pageFactory,
IRazorViewFactory viewFactory,
IViewLocationExpanderProvider viewLocationExpanderProvider,
IViewLocationCache viewLocationCache)
: base(pageFactory,
viewFactory,
viewLocationExpanderProvider,
viewLocationCache)
{
}
public override IEnumerable<string> AreaViewLocationFormats
{
get
{
var value = new Random().Next(0, 1);
var theme = value == 0 ? "Theme1" : "Theme2"; // 可通过其它条件,设置皮肤的种类
return base.AreaViewLocationFormats.Select(f => f.Replace("/Views/", "/Views/" + theme + "/"));
}
}
public override IEnumerable<string> ViewLocationFormats
{
get
{
var value = new Random().Next(0, 1);
var theme = value == 0 ? "Theme1" : "Theme2"; // 可通过其它条件,设置皮肤的种类
return base.ViewLocationFormats.Select(f => f.Replace("/Views/", "/Views/" + theme + "/"));
}
}
}
然后,通过修改MVcOptions的实例属性ViewEngines即可完成对视图引擎的替换,代码如下:
services.AddMvc().Configure<MvcOptions>(options =>
{
options.ViewEngines.Clear();
options.ViewEngines.Add(typeof(ThemeViewEngine));
});
这样,系统在查找视图文件的时候,就会按照新注册的ThemeViewEngine
的逻辑来执行。
通过IViewLocationExpander来控制View路径
在MVC6中,微软还提供了另外一种新的方式来控制View文件的路径,那就是IViewLocationExpander
接口,通过实现该接口即可实现自定义逻辑,并且也可以使用相关的上下文对象。示例如下:
public class ThemeViewLocationExpander : IViewLocationExpander
{
public void PopulateValues(ViewLocationExpanderContext context)
{
var value = new Random().Next(0, 1);
var theme = value == 0 ? "Theme1" : "Theme2";
context.Values["theme"] = theme;
}
public virtual IEnumerable<string> ExpandViewLocations(ViewLocationExpanderContext context,
IEnumerable<string> viewLocations)
{
return viewLocations.Select(f => f.Replace("/Views/", "/Views/" + context.Values["theme"] + "/"));
}
}
在上述自定义的IViewLocationExpander
中,实现了2个方法分别是PopulateValues
和ExpandViewLocations
,PopulateValues
方法可以让我们想ViewLocationExpanderContext
上下文中添加响应的键值对以便后续使用,通过,我们可以利用通过该上下文对象,来查找ActionContext
和HttpContext
对象,以便利用这些对象做响应的判断操作;而ExpandViewLocations
方法,只会在没有View缓存或在View缓存里找不到对应key的View文件时才会调用该方法,在该方法内,我们可以动态返回视图的位置。
最后,我们在Startup.cs
里通过修改RazorViewEngineOptions
实例对象的ViewLocationExpanders
属性,来实现注册目的,代码如下:
services.Configure<RazorViewEngineOptions>(options =>
{
options.ViewLocationExpanders.Add(typeof(ThemViewLocationExpander));
});
同步与推荐
本文已同步至目录索引:解读ASP.NET 5 & MVC6系列
解读ASP.NET 5 & MVC6系列(16):自定义View视图文件查找逻辑的更多相关文章
- 解读ASP.NET 5 & MVC6系列
本系列的大部分内容来自于微软源码的阅读和网络,大部分测试代码都是基于VS RC版本进行测试的. 解读ASP.NET 5 & MVC6系列(1):ASP.NET 5简介 解读ASP.NET 5 ...
- 解读ASP.NET 5 & MVC6 ---- 系列文章
本系列的大部分内容来自于微软源码的阅读和网络,大部分测试代码都是基于VS RC版本进行测试的. 解读ASP.NET 5 & MVC6系列(1):ASP.NET 5简介 解读ASP.NET 5 ...
- 解读ASP.NET 5 & MVC6系列(15):MvcOptions配置
程序模型处理 IApplicationModelConvention 在MvcOptions的实例对象上,有一个ApplicationModelConventions属性(类型是:List<IA ...
- 解读ASP.NET 5 & MVC6系列(14):View Component
在之前的MVC中,我们经常需要类似一种小部件的功能,通常我们都是使用Partial View来实现,因为MVC中没有类似Web Forms中的WebControl的功能.但在MVC6中,这一功能得到了 ...
- 解读ASP.NET 5 & MVC6系列(13):TagHelper
在新版的MVC6中,微软提供了强大的TagHelper功能,以便让我们摆脱如下的臃肿代码: @Html.LabelFor(model => model.FullName) @Html.EditF ...
- 解读ASP.NET 5 & MVC6系列(12):基于Lamda表达式的强类型Routing实现
前面的深入理解Routing章节,我们讲到了在MVC中,除了使用默认的ASP.NET 5的路由注册方式,还可以使用基于Attribute的特性(Route和HttpXXX系列方法)来定义.本章,我们将 ...
- 解读ASP.NET 5 & MVC6系列(11):Routing路由
新版Routing功能介绍 在ASP.NET 5和MVC6中,Routing功能被全部重写了,虽然用法有些类似,但和之前的Routing原理完全不太一样了,该Routing框架不仅可以支持MVC和We ...
- 解读ASP.NET 5 & MVC6系列(10):Controller与Action
我们知道在MVC5和之前的版本,两个框架的生命周期是不一样的,在新版MVC6中,MVC Controller/Web API Controller已经合二为一了,本章我们主要讲解Controller和 ...
- 解读ASP.NET 5 & MVC6系列(8):Session与Caching
在之前的版本中,Session存在于System.Web中,新版ASP.NET 5中由于不在依赖于System.Web.dll库了,所以相应的,Session也就成了ASP.NET 5中一个可配置的模 ...
随机推荐
- shell 带签名请求,yii 处理带签名的请求
处理请求 class TestController extends Controller { public function init() { if(!YII_ENV_DEV){ throw new ...
- JavaWeb_day04搜索_乱码_路径_转发重定向_cookie
本文为博主辛苦总结,希望自己以后返回来看的时候理解更深刻,也希望可以起到帮助初学者的作用. 转载请注明 出自 : luogg的博客园 谢谢配合! 搜索功能 DAO层都是一些数据库的增删改查操作 Ser ...
- Servlet3.0的异步
servlet之前的操作同时同步的,就是按照这样的一个流程来走的: 1.请求根据一个路径路由到一个servlet中, 2.servlet获取一系列的参数 3.执行一系列的逻辑(花费时间所占的比重也更大 ...
- 数据结构:栈 顺序表方法和单链表方法(python版)
#!/usr/bin/env python # -*- coding:utf-8 -*- class StackUnderflow(ValueError): pass #链表节点 class Node ...
- javaweb
关于java,作为一个初学者,作为一个即将跨入其中的钻研者,我觉得我很必要好好地升入其中认真学习每一个环节
- springmvc配置文件web.xml详解各方总结(转载)
Spring分为多个文件进行分别的配置,其中在servlet-name中如果没有指定init-param属性,那么系统自动寻找的spring配置文件为[servlet-name]-servlet.xm ...
- jQuery中iframe的操作
今天遇到一个问题:怎样实现点击一个按钮,在当前的页面上新增加一个小窗口,展示一个图片信息? 如图: 点击之前: 单击之后: 分析:要使新增的小窗口不影响父页面,我们这里采用iframe的框架的技术. ...
- LinQ to SQL用法详解
LinQ是指集成化查询语言,通过映射将数据库内的表名变为C#的类名,将列名作为属性名,将表的关系作为类的成员对象.O--M--R O-Object对象(李昌辉)R-Relation关系M-Mappin ...
- cookie存储对象信息
最近看到某公司某项目中用于保存多个城市信息到cookie中的方法,该方法的逻辑是按时间顺序记录最近访问过的三个城市的名字及id,逻辑包插入与含排重.插入与排重的代码如下: 1 2 3 4 5 6 7 ...
- 使用AxisHelper帮助理解View and Data API中的坐标系统
大家使用View and Data API做三维模型开发,必然首先要理解View and Data API的坐标系统,即XYZ三个轴向分别是怎么定义的.Three.js里面提供了一个AxisHelpe ...