Asp.Net MVC 2.0 动态加载Master Page数据(二)

好的解决方案

  在这节,我们会测试一个替代的并且更好的解决方案来实现从控制器行为传递数据到视图母版页。与在每一个控制器行为添加电影分类相反,我们只添加电影分类到视图数据一次。所有的被视图母版页使用的视图数据都添加到一个应用控制器。

  

ApplicationController类包含在清单4.

清单4 - Controllers\ApplicationController.cs

using System.Linq;
using System.Web.Mvc;
using MvcApplication1.Models;

namespace MvcApplication1.Controllers
{

      public abstract class ApplicationController : Controller
      {

           private MovieDataContext _dataContext = new MovieDataContext();

           public MovieDataContext DataContext
           {
                get { return _dataContext; }
           }

           public ApplicationController()
           {
                ViewData["categories"] = from c in DataContext.MovieCategories
                          select c;
           }
      }
}

清单4里面的ApplicationController三个地方你需要注意。首先,该类继承自System.Web.Mvc.Controller基类。应用控制器是一个控制器类。

  

  第二,ApplicationController类是一个抽象类。一个抽象类是一个具体类必须实现的类。由于ApplicationController是一个抽象类,你不能调用该类里面的任何方法。如果你想直接地调用ApplicationController类,那么你会得到一个资源无法被找到(Resource Cannot Be Found)的错误信息。

  第三,ApplicationController包含了一个添加电影分类到视图数据的构造函数。每一个继承自ApplicationController类的控制器类会自动地调用ApplicationController类的构造函数。无论你何时调用继承自ApplicationController类的控制器的何种行为,电影分类都会被自动地包含在视图数据里。

 

清单5的Movies控制器继承自ApplicationController。

清单5 - Controllers\MoviesController.cs

using System.Linq;
using System.Web.Mvc;

namespace MvcApplication1.Controllers
{

      public class MoviesController : ApplicationController
      {
           /// <summary>
           /// Show list of all movies
           /// </summary>
           public ActionResult Index()
           {
                ViewData["movies"] = from m in DataContext.Movies
                          select m;
                return View();
           }

           /// <summary>
           /// Show list of movies in a category
           /// </summary>
           public ActionResult Details(int id)
           {
                ViewData["movies"] = from m in DataContext.Movies
                          where m.CategoryId == id
                          select m;
                return View();
           }
      }
}

  Movies控制器,就如上一节讨论过的Home控制器,暴露了名叫Index()和Detials()的两个行为方法。注意到母版页显示的电影分类列表既不是由Index()函数也不是由Details()函数添加到。由于Movies控制器继承自ApplicationController,电影分类列表被自动地添加到视图数据。

 

  注意到这个添加视图数据到一个视图母版页的解决方案并没有违法DRY原则。添加电影分类列表到视图数据的代码只存在在一个地方:ApplicationController的构造函数。

总结

  在这篇教程,我们讨论了两种从控制器传递视图数据到视图母版页的方法。首先,我们测试了一个简单,但难以维护的方法。在第一节,我们讨论了怎么样在每一个控制器行为添加视图数据到视图母版页。由于它违反了DIY原则,我们以它不是好的解决方案而结束了讨论。

  接下来,我们测试了一个比较好的策略。与添加视图数据到每一个控制器行为不同,我们只在ApplicationController添加了视图数据。用这种方式的话,你可以避免代码重复。

 

转自:http://hi.baidu.com/aliasmic/blog/item/9bb4c3b5dc5d93798ad4b2ef.html

 

posted @ 2011-03-04 23:20  RyanBell  阅读(694)  评论(0编辑  收藏  举报