.NET Internationalization: The Developers Guide to Building Global Windows and Web Applications

Resource managers retrieve resources. The .NET Framework versions 1.1 and 2.0 include two resource-manager classes, System.Resources.ResourceManager and its descendant, System.ComponentModel.ComponentResourceManager. The former is used in all .NET applications, whereas the latter is typically used only in Visual Studio 2005 Windows Forms applications. We return to the latter in Chapter 4. We create new and exciting resource managers in Chapter 12.

We start by taking a high-level view of how System.Resources.ResourceManager retrieves resources. When an attempt to load a resource entry is made (using ResourceManager.GetString or ResourceManager.GetObject), the Resource Manager looks through its internal cache of resources to see if the request can be supplied from the cache. If not, a ResourceSet is loaded from a resource embedded in an assembly. A ResourceSet is a collection of resource entries and is equivalent to an in-memory copy of a single resx file (you can think of a ResourceSet as a DataTable for resource entries). The ResourceSet is added to the ResourceManager's internal cache. Finally, the ResourceSet is searched for the resource entry that matches the requested key. The ResourceManager class is covered in depth in Chapter 12.

The System.Resources.ResourceManager class retrieves resources either from a resource embedded in an assembly or from stand-alone binary resource files. To retrieve resources from a resource embedded in an assembly, we create a Resource-Manager using the class constructor. To retrieve resources from stand-alone binary resource files, we use the static CreateFileBasedResourceManager method. For the purposes of this example, we focus on the former. To retrieve the string, we need to create a ResourceManager object and call its GetString method. Add a couple of using directives to Form1.cs:

using System.Resources; using System.Reflection;

Add a private field to the Form1 class to hold the ResourceManager:

private ResourceManager resourceManager;

Instantiate the ResourceManager at the beginning of the Form1 constructor:

public Form1() { resourceManager = new ResourceManager( "WindowsApplication1.Form1Resources", Assembly.GetExecutingAssembly()); InitializeComponent(); }

The first parameter to the ResourceManager constructor is the fully qualified name of the resource that we want to retrieve. Recall from the assembly's manifest that the resource was called "WindowsApplication1.Form1Resources.resources." The ResourceManager class adds the ".resources" suffix so that it should not be included in the name passed to the constructor. The second parameter to the ResourceManager constructor is the assembly in which this resource can be found. In this example and most others like it, we are saying that the resource can be found in the assembly that is currently executing: i.e., WindowsApplication1.exe. The ResourceManager class supports three public constructor overloads:

public ResourceManager(string, Assembly); public ResourceManager(string, Assembly, Type); public ResourceManager(Type);

We have just covered the first. The second is a variation on the first and specifies the type to be used to create new ResourceSet objects. The third specifies the Type for which resources should be retrieved. This is also a variation on the first constructor because it uses the Type's Name for the resource name and the type's assembly as the assembly where the resource can be found.

All that remains is for us to retrieve the string using the ResourceManager. Change the original hard-coded line from this:

MessageBox.Show("Insufficient funds for the transfer");

to this:

MessageBox.Show(resourceManager.GetString("InsufficientFunds"));

The ResourceManager.GetString method gets a string from the resource: "InsufficientFunds" is the key of the resource, and GetString returns the value that corresponds to this key.

At this point, we have a localizable application; it is capable of being localized, but it has not yet been localized. There is just the original English text. From the user's point of view, our application is no different from when the text was hard coded.

Категории