| GNU gettext for Delphi, C++ Builder and Kylix 1.2 beta | ||
|---|---|---|
| <<< Previous | Action | Next >>> |
When you create a database application, there will be a lot of component properties that you don't want to be translated when using Translatecomponent(). Typically, the field names, table names and even database names of a database have meaningful translations, and the translation file from the translator may include translations for field names. Also, SQL statements should not be translated. They will get extracted, but if the translator modifies them, it would most likely break your program if this translation would be applied.
Therefore, it is very important, that you consult the appendix called How to handle specific classes> to see what ignores you should add to your application. Make sure that these ignores are executed before the first call to TranslateComponent(). The list in that appendix may not be complete - especially not if you use database components that are not mentioned. Therefore you must have a look at your components and make sure, that all properties, that should not be translated, have a corresponding TP_GlobalIgnoreClassProperty() call.
Delphi is very good for creating a single-language database application, fast, if the application only needs one language. A typical single-language application uses field names that are easily understood, like "Name", "Address" etc. Let's assume that you use a query component with an SQL statement like this:
select * from customer order by Name |
In this case, the name of the Name field of the customer table will propagate through all components, will become the column heading of a TDBGrid etc. Your grid column for names will read "Name". This is desired in an English language application, but absolutely not in all other languages.
The solution is to modify the .DisplayLabel property of the TField components, that your dataset possesses. Every TDataset descendant has a .Fields[] property that refers to the fields in the dataset, and all these field components are descendants of TField, which has the TField.DisplayLabel property.
Delphi provides two ways to modify this DisplayLabel property: At runtime and at design time, which leads to two different ways of handling the localization of it.
The runtime assignment solution is to assign a displaylabel at runtime like this:
procedure TForm1.Query1AfterOpen(DataSet: TDataSet);
begin
Dataset.FieldByName('Name').DisplayLabel:=_('Name');
end; |
This way, the field names are always the same in the database and the entire application, but the user will see a localized name. This works for all dataset type components, including table components, TClientDataset etc.
Creating design-time DisplayLabel properties goes like this:
Double-click the dataset component. This brings up the field list window.
Click with your right mouse button on the field list window and choose "Add all fields". This requires your dataset to be able to actually fetch data from the database at design time, but will add all the fields of the dataset to the field list window.
Make sure that the form (or datamodule) that the dataset component is on, is translated using TranslateComponent() before the dataset is opened. This means that the dataset needs to be closed by default, and that you have to open the dataset at runtime using .Open or .Active:=True.
By doing this, the field names will be present in the DFM files, and will therefore be extracted for the translator to be translated. Now, TranslateComponent() will translate the TField.DisplayLabel values:
procedure TForm1.FormCreate(Sender: TObject); begin TranslateComponent (self); Query.Open; end; |
Sometimes it is very handy to have field names translated to something else than what you put into the .DisplayLabel property. For instance, you may want to have a short version for exported ASCII files, another version for exporting XML files, one version for reports, and again another version for the .DisplayLabel property.
This is easily done by using several po files (which is the same as multiple text domains). The part of your program that writes a column header to an ascii file might look like this:
write (mytextfile,dgettext('fieldnames',myfield.FieldName)); |
This will find the field name in the fieldnames.mo file and output the translation. The fieldnames.po template can be written by hand (using notepad), or sometimes be extracted from a datamodule. Often, the number of field names is so low that the quickest solution is to write the po file by hand.
| <<< Previous | Home | Next >>> |
| Plural forms | Up | Translation repositories |