web-dev-qa-db-fra.com

Ajout d'un sous-répertoire au dossier "View / Shared" dans ASP.Net MVC et appel de la vue

Je développe actuellement un site utilisant ASP.Net MVC3 avec Razor. Dans le dossier "View/Shared", je veux ajouter un sous-dossier appelé "Partials" où je peux placer toutes mes vues partielles (pour mieux organiser le site.

Je peux le faire sans problème tant que je fais toujours référence au dossier "Partials" lors de l'appel des vues (à l'aide de Razor):

@Html.Partial("Partials/{ViewName}")

Ma question est de savoir s'il existe un moyen d'ajouter le dossier "Partials" à la liste que .Net parcourt lors de la recherche d'une vue, de cette façon je peux appeler ma vue sans avoir à référencer le dossier "Partials", comme ceci:

@Html.Partial("{ViewName}")

Merci pour l'aide!

48
lamarant

Résolu cela. Pour ajouter le sous-répertoire "Shared/Partials" que j'ai créé à la liste des emplacements recherchés lorsque vous essayez de localiser une vue partielle dans Razor en utilisant:

@Html.Partial("{NameOfView}")

Créez d'abord un moteur de vue avec RazorViewEngine comme classe de base et ajoutez vos emplacements de vue comme suit. Encore une fois, je voulais stocker toutes mes vues partielles dans un sous-répertoire "Partiels" que j'ai créé dans le répertoire "Vues/Partagé" par défaut créé par MVC.

public class RDDBViewEngine : RazorViewEngine
{
    private static readonly string[] NewPartialViewFormats = 
    { 
        "~/Views/{1}/Partials/{0}.cshtml",
        "~/Views/Shared/Partials/{0}.cshtml"
    };

    public RDDBViewEngine()
    {
        base.PartialViewLocationFormats = base.PartialViewLocationFormats.Union(NewPartialViewFormats).ToArray();
    }       

}

Notez que {1} dans le format d'emplacement est le nom du contrôleur et {0} est le nom de la vue.

Ajoutez ensuite ce moteur de vue à la collection MVC ViewEngines.Engines dans la méthode Application_Start () dans votre global.asax:

ViewEngines.Engines.Add(new RDDBViewEngine()); 
65
lamarant

Merci pour vos réponses. Cela a organisé mon dossier partagé, mais pourquoi créez-vous un nouveau type de moteur de vue? Je viens de créer un nouveau RazorViewEngine, de le définir PartialViewLocationFormats et de l'ajouter à la liste de ViewEngines.

ViewEngines.Engines.Add(new RazorViewEngine
{
    PartialViewLocationFormats = new string[]
    {
        "~/Views/{1}/Partials/{0}.cshtml",
        "~/Views/Shared/Partials/{0}.cshtml"
    }
});
28
David Cabiness

C'est bien de personnaliser le moteur de vue, mais si vous voulez juste avoir un sous-dossier por partiel, vous n'en avez pas besoin autant ...

Utilisez simplement le chemin complet de la vue partielle, comme pour la vue de mise en page:

@Html.Partial("/Views/Shared/Partial/myPartial.cshtml")

J'espère que cela aide quelqu'un ...

16
repeatdomiau

J'ai mis à jour l'excellente réponse de lamarant pour inclure les zones:

public class RDDBViewEngine : RazorViewEngine
{
    private static readonly string[] NewPartialViewFormats =
    {
        "~/Views/{1}/Partials/{0}.cshtml",
        "~/Views/Shared/Partials/{0}.cshtml"
    };

    private static List<string> AreaRegistrations;

    public RDDBViewEngine()
    {
        AreaRegistrations = new List<string>();

        BuildAreaRegistrations();

        base.PartialViewLocationFormats = base.PartialViewLocationFormats.Union(NewPartialViewFormats).ToArray();
        base.PartialViewLocationFormats = base.PartialViewLocationFormats.Union(areaRegistrations).ToArray();
    }

    private static void BuildAreaRegistrations()
    {
        string[] areaNames = RouteTable.Routes.OfType<Route>()
            .Where(d => d.DataTokens != null && d.DataTokens.ContainsKey("area"))
            .Select(r => r.DataTokens["area"].ToString()).ToArray();

        foreach (string areaName in areaNames)
        {
            AreaRegistrations.Add("~/Areas/" + areaName + "/Views/Shared/Partials/{0}.cshtml");
            AreaRegistrations.Add("~/Areas/" + areaName + "/Views/{1}/Partials/{0}.cshtml");
        }
    }
}

N'oubliez pas d'inclure dans le démarrage de votre candidature:

public class MvcApplication : System.Web.HttpApplication
{

    protected void Application_Start()
    {
        ...

        ViewEngines.Engines.Add(new RDDBViewEngine()); 
    }
}
6
mcfea

Si vous faites cela dans ASP.NET Core, allez simplement dans la classe Startup, sous la méthode ConfigureServices, et mettez

services.AddMvc()
    .AddRazorOptions(opt => {
        opt.ViewLocationFormats.Add("/Views/{1}/Partials/{0}.cshtml");
        opt.ViewLocationFormats.Add("/Views/Shared/Partials/{0}.cshtml");
    });
6
saluce

Vous pouvez également mettre à jour les formats de vue partielle de l'emplacement du moteur RazorViewEngine enregistré. Placez le code ci-dessous dans Application_Start dans Global.asax.

 RazorViewEngine razorEngine = ViewEngines.Engines.OfType<RazorViewEngine>().FirstOrDefault();
        if (razorEngine != null)
        {
            string[] newPartialViewFormats = new[] { 
                    "~/Views/{1}/Partials/{0}.cshtml",
                    "~/Views/Shared/Partials/{0}.cshtml"
            };
            razorEngine.PartialViewLocationFormats =
                razorEngine.PartialViewLocationFormats.Union(newPartialViewFormats).ToArray();
        }
5
SridharVenkat

Vous pouvez créer enregistrer votre propre moteur de vue qui dérive du moteur de vue que vous utilisez (Webforms/Razor) et spécifier les emplacements souhaités dans le constructeur ou simplement les ajouter à la liste des emplacements déjà existants:

this.PartialViewLocationFormats = viewLocations;

Ensuite, au démarrage de l'application, vous ajouteriez votre moteur de vue comme suit: ViewEngines.Engines.Add(new MyViewEngineWithPartialPath());

1
Joe Cartano