Reputation: 9013
I have a standard ASP.NET MVC application, with Layout page and many views. For example, for some users (depend on their properties or by another reason) I want to show something (i.e. additional menu).
Layout page:
@if (Request.IsAuthenticated && User.IsInRole("Admin"))
{
<li class="dropdown">
<a aria-expanded="false" class="dropdown-toggle" role="button" href="#" data-toggle="dropdown">Admin <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">
<li>@Html.ActionLink("Users", "Index", "User")</li>
/* ............ */
</ul>
</li>
}
else if (SomeParameter == "SomeValue") // I WANT TO HAVE THIS VARIABLE FOR ALL PAGES
{
/* ............ */
}
How to implement it? Of course, I can:
add to each controller method:
protected override void Initialize(System.Web.Routing.RequestContext requestContext)
{
base.Initialize(requestContext);
ViewTag.SomeParameter = "SomeValue";
}
This method is bad also, especially if we have 10+ controllers, views of these controllers use this Layout.
Which approach is good?
Upvotes: 0
Views: 104
Reputation: 12410
Implement a base viewmodel. Have all relevant viewmodels inherit from the base. Specify the layout's model as the base viewmodel. I'll use a boolean but you can use a string.
ViewModel
public class BaseViewModel
{
public bool CanSeeSecondaryMenu {get;set;}
}
Layout
@model Web.BaseViewModel
...
else if (Model.CanSeeSecondaryMenu) // I WANT TO HAVE THIS VARIABLE FOR ALL PAGES
{
/* ............ */
}
Action
public ActionResult Index()
{
var model = new InheritedFromBaseViewModel { CanSeeSecondaryMenu = //Set via logic };
return View(model);
}
If you want to generalize the logic for setting this boolean value you can create a base controller, have all relevant controllers inherit from it, and override the OnActionExecuting
method
public abstract class BaseController : Controller
{
protected bool CanSeeSecondaryMenu { get; set; }
protected override void OnActionExecuting(ActionExecutingContext filterContext)
{
base.OnActionExecuting(filterContext);
CanSeeSecondaryMenu = //Set via logic
}
}
Then the Index action would change to this...
public ActionResult Index()
{
var model = new InheritedFromBaseViewModel { CanSeeSecondaryMenu = CanSeeSecondaryMenu };
return View(model);
}
Upvotes: 2