Recupera il nome della vista corrente in ASP.NET MVC?

Ho una vista parziale (controllo) che viene utilizzata in diverse pagine di visualizzazione e devo passare il nome della vista corrente al controller, quindi se ci sono errori di convalida, posso ridisegnare la vista originale.

Un modo alternativo per farlo sarebbe (nei metodi del controller)

var viewName = "Details"; // or whatever ViewData["viewName"] = viewName; return(View(viewName, customer)); 

e poi nel parziale stesso, renderlo come

 <input type="hidden" name="viewName" value="" /> 

La domanda è: c’è qualche proprietà o syntax che posso usare per recuperarlo direttamente invece di impostarlo dal controller? Ho provato l’ovvio:

 <input type="hidden" name="viewName" value="" /> 

ma questo non funziona. Cosa mi manca qui?

Grazie.

Beh, se non ti dispiace avere il tuo codice legato allo specifico motore di visualizzazione che stai utilizzando, puoi guardare la proprietà WebFormView e WebFormView a WebFormView

 var viewPath = ((WebFormView)ViewContext.View).ViewPath; 

Credo che alla fine otterrai il nome della vista.

EDIT: Haacked è assolutamente azzeccato; per rendere le cose un po ‘più ordinate ho avvolto la logica in un metodo di estensione in questo modo:

 public static class IViewExtensions { public static string GetWebFormViewName(this IView view) { if (view is WebFormView) { string viewUrl = ((WebFormView)view).ViewPath; string viewFileName = viewUrl.Substring(viewUrl.LastIndexOf('/')); string viewFileNameWithoutExtension = Path.GetFileNameWithoutExtension(viewFileName); return (viewFileNameWithoutExtension); } else { throw (new InvalidOperationException("This view is not a WebFormView")); } } } 

che sembra fare esattamente quello che stavo cercando.

Ho avuto lo stesso problema ed è così che l’ho risolto:

 namespace System.Web.Mvc { public static class HtmlHelperExtensions { public static string CurrentViewName(this HtmlHelper html) { return System.IO.Path.GetFileNameWithoutExtension( ((RazorView)html.ViewContext.View).ViewPath ); } } } 

Quindi nella vista:

 var name = Html.CurrentViewName(); 

o semplicemente

 @Html.CurrentViewName() 

Se vuoi solo il nome dell’azione, allora questo farebbe il trucco:

 public static string ViewName(this HtmlHelper html) { return html.ViewContext.RouteData.GetRequiredString("action"); } 

Se vuoi ottenere il nome del file da una vista parziale, sembra funzionare:

 public static class HtmlHelperExtensions { public static string GetViewFileName(this HtmlHelper html, object view) { return @"\\"+ view.GetType().FullName.Replace("ASP._Page_", "").Replace("_cshtml", ".cshtml").Replace("_", @"\\"); } } 

E nella vista parziale, dovresti fare qualcosa del genere:

 var filename = Html.GetViewFileName(this); 

o questo:

 @Html.GetViewFileName(this) 

Si prega di commentare se questo non è un buon approccio – eventuali alternative?

La soluzione più semplice sta usando ViewBag.

 public ActionResult Index() { ViewBag.CurrentView = "Index"; return View(); } 

Nella pagina cshtml

 @{ var viewName = ViewBag.CurrentView; } 

O,

 ((RazorView)ViewContext.View).ViewPath 

Se stai cercando una soluzione per asp.net core puoi usare:

 @System.IO.Path.GetFileNameWithoutExtension(ViewContext.View.Path) 

Ciò restituirà il nome della vista corrente.

Non dovresti usare un metodo di validazione come gli strumenti per la cena Nerd?

In questo modo non hai realmente bisogno di fare tutto questo e puoi solo restituire la vista.

Ho avuto lo stesso problema di recente e il frammento di codice che ho trovato ha risolto il mio problema.

L’unico inconveniente è che Request.UrlReferrer potrebbe essere nullo in alcuni casi. Un po ‘in ritardo ma sembrava funzionare per me e ho coperto tutte le basi di Request.UrlReferrer non essendo nullo.

  if (Request.UrlReferrer != null) { var viewUrl = Request.UrlReferrer.ToString(); var actionResultName = viewUrl.Substring(viewUrl.LastIndexOf('/')); var viewNameWithoutExtension = actionResultName.TrimStart('/'); } 

Ho appena scritto un blog su questo

http://www.antix.co.uk/A-Developers-Blog/Targeting-Pages-with-CSS-in-ASP.NET-MVC

  ///  /// Get a string from the route data ///  public static string RouteString( this ViewContext context, string template) { foreach (var value in context.RouteData.Values) { template = template.Replace(string.Format("{{{0}}}", value.Key.ToLower()), value.Value == null ? string.Empty : value.Value.ToString().ToLower()); } return template; } 

uso

 "> 

EDIT: Sì, questo non ti darà il nome della vista come afferma il primo commento, ti dà il controller e l’azione. Ma lasciandolo qui è prezioso sapere che non è così.