ASP.NET MVC - HybridViewResult (ViewResult /PartialViewResult)
Is it possible to build a hybrid ViewResult that returns in depedency of an AjaxRequest or HttpRequest a PartialViewResult
or ViewResult
?
IsAjaxRequest --> return PartialViewResult !IsAjaxRequest --> return ViewResult
As far as I know my开发者_JAVA技巧 HybridViewResult should derive from ViewResultBase.
But how to implement the FindView method?
Try:
public class HybridViewResult : ActionResult
{
public string ViewName { get; set; }
public HybridViewResult () { }
public HybridViewResult (string viewName ) { this.ViewName = viewName ; }
public override void ExecuteResult(ControllerContext context)
{
if (context == null) throw new ArgumentNullException("context");
var usePartial = ShouldUsePartial();
ActionResult res = GetInnerViewResult(usePartial);
res.ExecuteResult(context);
}
private ActionResult GetInnerViewResult(bool usePartial)
{
var view = ViewName;
ActionResult res;
if(String.IsNullOrEmpty(view)) {
res = usePartial ? new PartialViewResult(view) : new ViewResult(view);
}
else {
res = usePartial ? new PartialViewResult() : new ViewResult();
}
return res;
}
private bool ShouldUsePartial(ControllerContext context) {
return false; //your code that checks if you need to use partial here
}
}
Add any constructor & GetInnerViewResult variations as needed i.e. to pass Model.
This is a slightly more stripped down take on eglasius's answer. I'm actually tackling a similar problem except I need to return a JsonResult.
The (untested) NormalOrAjaxResult simply lets you specify an action result for the non ajax request and one for the ajax request. Because these are ActionResults you can mix up Redirect, View, Partial and Json view results.
public class NormalOrAjaxResult : ActionResult
{
private readonly ActionResult _nonAjaxActionResult;
private readonly ActionResult _ajaxActionResult;
public NormalOrAjaxResult(ActionResult nonAjaxActionResult, ActionResult ajaxActionResult)
{
_nonAjaxActionResult = nonAjaxActionResult;
_ajaxActionResult = ajaxActionResult;
}
public override void ExecuteResult(ControllerContext context)
{
var isAjaxRequest = context.HttpContext.Request["isAjax"];
if (isAjaxRequest != null && isAjaxRequest.ToLower() == "true")
{
_ajaxActionResult.ExecuteResult(context);
} else
{
_nonAjaxActionResult.ExecuteResult(context);
}
}
}
can you not just make 2 different actions in that case? the 'shared' logic you could simply put in a [nonAction]
method?
I know I'm really late to the party here, but these didnt seem quite right to me, so here's my 2 cents:
public class PartialViewConverter : ViewResult
{
public ViewResultBase Res { get; set; }
public PartialViewConverter(ViewResultBase res) { Res = res; }
public override void ExecuteResult(ControllerContext context)
{
Res.ExecuteResult(context);
}
public static ViewResult Convert(ViewResultBase res)
{
return new PartialViewConverter(res);
}
}
With usage:
return PartialViewConverter.Convert(PartialView());
And then in your controller if you override View
protected override ViewResult View(string viewName, string masterName, object model)
{
//Whichever condition you like can go here
if (Request.QueryString["partial"] != null)
return PartialViewConverter.Convert(PartialView(viewName, model));
else
return base.View(viewName, masterName, model);
}
Any action method where you return a view will automatically also return partials when requested:
public ActionResult Index()
{
ViewBag.Message = "Modify this template to jump-start your ASP.NET MVC application.";
//This will return a partial if partial=true is passed in the querystring.
return View();
}
精彩评论