Question

I am adding Globalization to a C# MVC 5 web application. in most views I use Resources and it works great. For views with a lot of customization I want to seperate the views, each for different language. I followed Brian Reiter post. I add the Globalization forlder under Views, the ISO 639-1 two-letter macro-language code, and the Home folder and Index view for the specific langague.

I understand that I need to modify the mechnisem that renders the views to take into account the client's locale. in Brian's post it is demonstrated on web forms and in my solution I don't seem to have the same WebFormViewEngine as in his example.

I will appriciate if you could direct me to how should I extand the mvc view engine so the correct view will be rendered depending the locale.

Thanks.

Was it helpful?

Solution

This how I fixed my project:

  1. added a class that will extand the RazorViewEngine (inherit from it).

I used the code in Brian Reiter post (link above) with slight changes (from WebFormsViewEngine to RazorViewEngine, my apps culture cookie and the extraction of the two letter languge from the culture):

using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Web.Mvc; using System.Text.RegularExpressions; using System.IO; using LeadsWize.Helpers; using System.Globalization;

namespace System.Web.Mvc { public class GlobalizationViewEngine : RazorViewEngine { protected override IView CreatePartialView(ControllerContext controllerContext, string partialPath) { partialPath = GlobalizeViewPath(controllerContext, partialPath); return new RazorView(controllerContext, partialPath, null, false, FileExtensions, ViewPageActivator); }

    protected override IView CreateView(ControllerContext controllerContext, string viewPath, string masterPath)
    {
        viewPath = GlobalizeViewPath(controllerContext, viewPath);
        return base.CreateView(controllerContext, viewPath, masterPath);
    }

    private static string GlobalizeViewPath(ControllerContext controllerContext, string viewPath)
    {
        var request = controllerContext.HttpContext.Request;
        string cultureName = null;
        HttpCookie cultureCookie = request.Cookies["_culture"];
        if (cultureCookie != null)
            cultureName = cultureCookie.Value;
        else
            cultureName = request.UserLanguages != null && request.UserLanguages.Length > 0 ?
                    request.UserLanguages[0] :  // obtain it from HTTP header AcceptLanguages
                    null;
        // Validate culture name
        cultureName = CultureHelper.GetImplementedCulture(cultureName); // This is safe
        var lang = (CultureInfo.CreateSpecificCulture(cultureName)).TwoLetterISOLanguageName; // this is to extract the two languge letters from the culture
        if (lang != null &&
            !string.IsNullOrEmpty(lang) &&
            !string.Equals(lang, "en", StringComparison.InvariantCultureIgnoreCase))
        {
            string localizedViewPath = Regex.Replace(
                viewPath,
                "^~/Views/",
                string.Format("~/Views/Globalization/{0}/",
                lang
                ));
            if (File.Exists(request.MapPath(localizedViewPath)))
            { viewPath = localizedViewPath; }
        }
        return viewPath;
    }
}

}

  1. added there two lines in the Application_Stat in Global.asxs.cs

        ViewEngines.Engines.Clear();
        ViewEngines.Engines.Add(new GlobalizationViewEngine()); //this is our customized extended view engine to support the globaliztion in view folder Globalization.
    

** please note that the folders arangemnet for the globalized view files are exactly in the same hierarchy as in Brian's post.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top