Monday, August 10, 2009

Steps for making a .net site multilingual

  1. in web.config file [add this (under system.web)]

<globalization requestEncoding="utf-8" responseEncoding="utf-8"/>

            <xhtmlConformance mode="Legacy"/> 

  1. Create a resource file under ‘app_globalresources’ folder in your website.
    The resx file will have Name -> Value ->Type -> Comments fields. Fill all the words and their respective values. The name of the first resource file (in base language english) should be same as website name. e.g. mysite.resx 
  1. Copy the file and paste in the same folder and rename ‘copy of mysite.resx’ to ‘mysite.<culture>.resx.
    where culture is language for which resource file is required. E.g. For deutsch language I’ll rename it to mysite.de-de.aspx. Then in the file, change the value field as per the language and save.
    Similarly create resource files for other languages if required.

E.g.

In English (Base resource file)
Name – Name
City – City

 

In deutsch resource file
Name – Naam
City - Cite 

  1. Open Visual Studio 2005 Command Prompt -> Go to your project folder where you have created your resx files. 
  1. Create the resources files of the same .resx files by typing following command
    resgen mysite.resx mysite.resources
    resgen mysite.de-de.resx mysite.de-de.resources
    This will create resources files in the same folder 
  1. Convert these resources file into .dll for each resource file.
    For this perform following steps:
    al /embed:mysite.resources,mysite.resources /out:mysite.dll
    al /embed:mysite.de-de.resources,mysite.de-de.resources /out:mysite.resources.dll /c:de-de

Substitute the code for the culture into which you are localizing for de-de. Remember that the /c: tag is the culture specifier.

After the DLLs are in the right locations (/bin and /bin/de-de in the above samples), the resources can be retrieved appropriately. Note that everything gets shadow-copied by assembly cache and thus is replaceable, avoiding potential locking scenarios.

 

            So,
            you will place mysite.dll in \bin folder and
            create folders for each language named with <culture> and place its respective mysite.resources.dll inside it. 

  1. Then, Create a global.asax file in your site which should have:

    <%@ Application Language="VB" %>

<%@ Import Namespace="system.resources" %>

<%@ Import Namespace="system.IO" %>

<%@ Import Namespace="system.web" %>

<%@ Import Namespace="system.web.sessionstate" %>

<%@ Import Namespace="system.Threading" %>

<%@ Import Namespace="System.Web.HttpApplication" %>

<%@ Import Namespace="system.globalization" %>

<%@ Import Namespace="system.web.ui.page" %>

<%@ Import Namespace="system.web" %>

<%@ Import Namespace="system.web.sessionstate" %>

 

<script runat="server"> 

    Sub Application_Start(ByVal sender As Object, ByVal e As EventArgs)              
        ' Code that runs on application startup       
    End Sub

    Public Sub Application_AcquireRequestState(ByVal sender As Object, ByVal e As EventArgs)
        If Not System.Web.HttpContext.Current.Session Is Nothing Then
            If Session("lng") IsNot Nothing Then
                Dim currentCulture As String = DirectCast(Session("lng"), String)

                If [String].Compare(currentCulture, System.Threading.Thread.CurrentThread.CurrentCulture.ToString(), StringComparison.OrdinalIgnoreCase) <> 0 Then

                    Try

                        System.Threading.Thread.CurrentThread.CurrentCulture = System.Globalization.CultureInfo.CreateSpecificCulture(currentCulture)

                    Catch

                        System.Threading.Thread.CurrentThread.CurrentCulture = New System.Globalization.CultureInfo("en-us")

                    End Try

                    System.Threading.Thread.CurrentThread.CurrentUICulture = System.Threading.Thread.CurrentThread.CurrentCulture

                End If

            End If

        End If     

    End Sub   

 

    Sub Application_BeginRequest(ByVal sender As Object, ByVal e As EventArgs)

        ' Fires at the beginning of each request

        Try

            Thread.CurrentThread.CurrentCulture = New CultureInfo(Request.UserLanguages(1))

        Catch ex As Exception

            ' provide fallback for not supported languages.

            Thread.CurrentThread.CurrentCulture = New CultureInfo("en-US")

        End Try

 

        Thread.CurrentThread.CurrentUICulture = Thread.CurrentThread.CurrentCulture

    End Sub   

 

    Sub Application_End(ByVal sender As Object, ByVal e As EventArgs)

        ' Code that runs on application shutdown

    End Sub       

 

    Sub Application_Error(ByVal sender As Object, ByVal e As EventArgs)

        ' Code that runs when an unhandled error occurs

    End Sub 

 

    Sub Session_Start(ByVal sender As Object, ByVal e As EventArgs)

        ' Code that runs when a new session is started

    End Sub 

 

    Sub Session_End(ByVal sender As Object, ByVal e As EventArgs)

        ' Code that runs when a session ends.

        ' Note: The Session_End event is raised only when the sessionstate mode

        ' is set to InProc in the Web.config file. If session mode is set to StateServer

        ' or SQLServer, the event is not raised.

    End Sub     

 

</script> 

  1. In your app_code folder, create a class like this,

 

Imports Microsoft.VisualBasic

Imports System.Resources

Public Module test

    Public a As Reflection.Assembly = Reflection.Assembly.Load("mysite")

    Public rm As ResourceManager = New ResourceManager("mysite", a)

End Module

  1. Now in your site, pass the culture as parameter e.g. somepage.aspx?lang=de-de.
    If you see, in pt. 7, we had mentioned the default culture as English-United States. If someone language required is deutsch, then the resource of deutsch culture should be initiated based on which the page will be displayed which is explained in next point. 

on somepage.aspx.vb, add the following
Imports System.Globalization

Imports System.Threading

Imports System.Resources

Imports System.IO

Imports System.Reflection

and then, in page_load

Response.Write("<P>Lang = " & Request.QueryString("lang") & "</P>")

        If Request.QueryString("lang") <> "" Then

            Dim SelectedCulture As String = Request.QueryString("lang")

            Thread.CurrentThread.CurrentCulture = New CultureInfo(SelectedCulture)

            Thread.CurrentThread.CurrentUICulture = New CultureInfo(SelectedCulture)

        End If

 

Note: rm is defined in the module mentioned in pt. 8, so it doesnot require the re declaration in the page.

 

Now anything can be called on the page from the respective resource as:
label1.text=rm.GetString(“Name”)

Label2.text=rm.GetString(“City”)

 

This will display the respective (initiated selected culture) value against the called string.

 

 THAT’S IT!

 

HAPPY MULTILINGUALING!!!!

 

No comments:

Post a Comment