[haiku-commits] Change in haiku[master]: locale kit: allow creating a catalog without entry_ref

  • From: Gerrit <review@xxxxxxxxxxxxxxxxxxx>
  • To: waddlesplash <waddlesplash@xxxxxxxxx>, haiku-commits@xxxxxxxxxxxxx
  • Date: Wed, 26 Aug 2020 12:17:50 +0000

From Adrien Destugues <pulkomandy@xxxxxxxxx>:

Adrien Destugues has uploaded this change for review. ( 
https://review.haiku-os.org/c/haiku/+/3173 ;)


Change subject: locale kit: allow creating a catalog without entry_ref
......................................................................

locale kit: allow creating a catalog without entry_ref

The catalogs are loaded from separate files, so there is no need to have
an app entry_ref to load them, just a MIME type is enough.

The implementation is a bit simplified: only the default catalog format
is allowed (unlike when loading from entry_ref, where extra catalog
formats can be added in add-ons).

Unrelated cleanup: remove unused code to load catalogs from attributes
of an application. We considered this when designing the locale kit, but
using resources or separate files works better.

Use this in Cortex, where some strings are in a static library, so they
don't have an associated executable or library or add-on to identify
them. The code in Cortex is not complete localization, several parts
should use StringForRate, BStringFormat, etc.
---
M docs/user/locale/Catalog.dox
M headers/os/locale/Catalog.h
M headers/private/locale/DefaultCatalog.h
M headers/private/locale/MutableLocaleRoster.h
M src/apps/cortex/support/MediaString.cpp
M src/kits/locale/Catalog.cpp
M src/kits/locale/DefaultCatalog.cpp
M src/kits/locale/MutableLocaleRoster.cpp
8 files changed, 503 insertions(+), 285 deletions(-)



  git pull ssh://git.haiku-os.org:22/haiku refs/changes/73/3173/1

diff --git a/docs/user/locale/Catalog.dox b/docs/user/locale/Catalog.dox
index fc64a56..7161c06 100644
--- a/docs/user/locale/Catalog.dox
+++ b/docs/user/locale/Catalog.dox
@@ -8,8 +8,8 @@
  *             Oliver Tappe, zooey@xxxxxxxxxxxxxxx
  *
  * Corresponds to:
- *             headers/os/locale/Catalog.h      hrev45083
- *             src/kits/locale/Catalog.cpp      hrev45083
+ *             headers/os/locale/Catalog.h      hrev54533
+ *             src/kits/locale/Catalog.cpp      hrev54533
  */
 

@@ -109,7 +109,8 @@
        different versions of your application, it may be useful to separate 
their
        catalogs.

-       \param catalogOwner entry_ref for which to load a catalog.
+       \param catalogOwner entry_ref or application, add-on or library for 
which
+              to load a catalog.
        \param language The language of the catalog to load. If \c NULL, the 
user
               settings will be used.
        \param fingerprint The fingerprint version-info for the catalog to load.
@@ -121,6 +122,29 @@


 /*!
+       \fn BCatalog::BCatalog(const char* signature, const char* language)
+       \brief Construct a BCatalog object for the given application \a 
signqture.
+
+       If you don't specify a language, the system default list will be used.
+       The language is passed here as a 2 letter ISO code.
+
+       This constructor is used to load catalogs that are not related to an
+       executable or library file (so there is no entry_ref usable to identify 
the
+       catalog). As it uses only the MIME signature, it cannot load catalogs 
from
+       application resources or a catalog file located next to the application.
+       Only the catalogs in the standard system directories 
(data/locale/catalogs)
+       are checked. Moreover, only the default catalog format is available, not
+       custom formats from catalog add-ons.
+
+       \param catalogOwner entry_ref for which to load a catalog.
+       \param language The language of the catalog to load. If \c NULL, the 
user
+              settings will be used.
+
+       \since Haiku R1
+*/
+
+
+/*!
        \fn BCatalog::~BCatalog()
        \brief Destroys the BCatalog object freeing memory used by it.

@@ -269,9 +293,10 @@
                const char* language, uint32 fingerprint)
        \brief Reload the string data.

-       This method reloads the data for the given signature and fingerprint.
+       This method reloads the data for the given file, language and 
fingerprint.

-       \param catalogOwner The \c entry_ref of the catalog that you want to 
load.
+       \param catalogOwner The \c entry_ref of the application, add-on or 
library
+              for which you want to load a catalog.
        \param language The language of the catalog to load. If \c NULL, the 
user
               settings will be used.
        \param fingerprint The fingerprint of the catalog you want to load.
@@ -283,6 +308,23 @@


 /*!
+       \fn status_t BCatalog::SetTo(const char* signature,
+               const char* language, uint32 fingerprint)
+       \brief Reload the string data.
+
+       This method reloads the data for the given signature and language.
+
+       \param signature The MIME signature identifying the catalog to load.
+       \param language The language of the catalog to load. If \c NULL, the 
user
+              settings will be used.
+
+       \returns A status code, \c B_OK on success, \c B_ERROR on error.
+
+       \since Haiku R1
+*/
+
+
+/*!
        \fn status_t BCatalog::InitCheck() const
        \brief Check if the catalog is in a valid and usable state.

diff --git a/headers/os/locale/Catalog.h b/headers/os/locale/Catalog.h
index 7672393..2e16bf8 100644
--- a/headers/os/locale/Catalog.h
+++ b/headers/os/locale/Catalog.h
@@ -24,6 +24,9 @@
                                                                BCatalog(const 
entry_ref& catalogOwner,
                                                                        const 
char* language = NULL,
                                                                        uint32 
fingerprint = 0);
+                                                               BCatalog(const 
char* signature,
+                                                                       const 
char* language = NULL);
+
        virtual                                         ~BCatalog();

                        const char*                     GetString(const char* 
string,
@@ -41,6 +44,8 @@
                        status_t                        SetTo(const entry_ref& 
catalogOwner,
                                                                        const 
char* language = NULL,
                                                                        uint32 
fingerprint = 0);
+                       status_t                        SetTo(const char* 
signature,
+                                                                       const 
char* language = NULL);

                        status_t                        InitCheck() const;
                        int32                           CountItems() const;
diff --git a/headers/private/locale/DefaultCatalog.h 
b/headers/private/locale/DefaultCatalog.h
index 0cfab3f..99fe8b9 100644
--- a/headers/private/locale/DefaultCatalog.h
+++ b/headers/private/locale/DefaultCatalog.h
@@ -37,12 +37,12 @@

                // implementation for editor-interface:
                status_t ReadFromFile(const char *path = NULL);
-               status_t ReadFromAttribute(const entry_ref &appOrAddOnRef);
                status_t ReadFromResource(const entry_ref &appOrAddOnRef);
                status_t WriteToFile(const char *path = NULL);
-               status_t WriteToAttribute(const entry_ref &appOrAddOnRef);
                status_t WriteToResource(const entry_ref &appOrAddOnRef);

+               status_t ReadFromStandardLocations();
+
                status_t SetRawString(const CatKey& key, const char 
*translated);
                void SetSignature(const entry_ref &catalogOwner);

diff --git a/headers/private/locale/MutableLocaleRoster.h 
b/headers/private/locale/MutableLocaleRoster.h
index c4cd209..75a9616 100644
--- a/headers/private/locale/MutableLocaleRoster.h
+++ b/headers/private/locale/MutableLocaleRoster.h
@@ -52,6 +52,8 @@
                        BCatalogData*           LoadCatalog(const entry_ref& 
catalogOwner,
                                                                        const 
char* language = NULL,
                                                                        int32 
fingerprint = 0) const;
+                       BCatalogData*           LoadCatalog(const char* 
signature,
+                                                                       const 
char* language = NULL) const;
                        status_t                        
UnloadCatalog(BCatalogData* catalogData);

                        BCatalogData*           CreateCatalog(const char* type,
diff --git a/src/apps/cortex/support/MediaString.cpp 
b/src/apps/cortex/support/MediaString.cpp
index e156380..8daf1bb 100644
--- a/src/apps/cortex/support/MediaString.cpp
+++ b/src/apps/cortex/support/MediaString.cpp
@@ -38,11 +38,15 @@
 // Support Kit
 #include <String.h>

+#include <Catalog.h>
+
 __USE_CORTEX_NAMESPACE

 #include <Debug.h>
 #define D_METHOD(x) //PRINT (x)

+static BCatalog sCatalog("application/Haiku-cortext-support");
+
 // -------------------------------------------------------- //
 // *** media_node strings (public)
 // -------------------------------------------------------- //
@@ -57,96 +61,96 @@

        if (kinds & B_BUFFER_PRODUCER) {
                if (first) {
-                       list = "Buffer producer";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Buffer 
producer"));
                        first = false;
                }
        }
        if (kinds & B_BUFFER_CONSUMER) {
                if (first) {
-                       list = "Buffer consumer";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Buffer 
consumer"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Buffer consumer";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Buffer 
consumer"));
                }
        }
        if (kinds & B_TIME_SOURCE) {
                if (first) {
-                       list = "Time source";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Time 
source"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Time source";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Time 
source"));
                }
        }
        if (kinds & B_CONTROLLABLE) {
                if (first) {
-                       list = "Controllable";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Controllable"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Controllable";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Controllable"));
                }
        }
        if (kinds & B_FILE_INTERFACE) {
                if (first) {
-                       list = "File interface";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("File 
interface"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "File interface";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("File 
interface"));
                }
        }
        if (kinds & B_ENTITY_INTERFACE) {
                if (first) {
-                       list = "Entity interface";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Entity 
interface"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Entity interface";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Entity 
interface"));
                }
        }
        if (kinds & B_PHYSICAL_INPUT) {
                if (first) {
-                       list = "Physical input";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Physical 
input"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Physical input";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Physical 
input"));
                }
        }
        if (kinds & B_PHYSICAL_OUTPUT) {
                if (first) {
-                       list = "Physical output";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Physical 
output"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Physical output";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Physical 
output"));
                }
        }
        if (kinds & B_SYSTEM_MIXER) {
                if (first) {
-                       list = "System mixer";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("System 
mixer"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "System mixer";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("System 
mixer"));
                }
        }

@@ -162,12 +166,18 @@
        D_METHOD(("MediaString::getStringFor(run_mode)\n"));

        switch (runMode) {
-               case BMediaNode::B_OFFLINE:                             return 
"Offline";
-               case BMediaNode::B_RECORDING:                   return 
"Recording";
-               case BMediaNode::B_DECREASE_PRECISION:  return "Decrease 
precision";
-               case BMediaNode::B_INCREASE_LATENCY:    return "Increase 
latency";
-               case BMediaNode::B_DROP_DATA:                   return "Drop 
data";
-               default:                                                        
        return "(unknown run mode)";
+               case BMediaNode::B_OFFLINE:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Offline"));
+               case BMediaNode::B_RECORDING:
+                       return 
sCatalog.GetString(B_TRANSLATE_MARK("Recording"));
+               case BMediaNode::B_DECREASE_PRECISION:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Decrease 
precision"));
+               case BMediaNode::B_INCREASE_LATENCY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Increase 
latency"));
+               case BMediaNode::B_DROP_DATA:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Drop 
data"));
+               default:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(unknown 
run mode)"));
        }
 }

@@ -181,24 +191,41 @@
        D_METHOD(("MediaString::getStringFor(media_type)\n"));

        switch (type) {
-               case B_MEDIA_NO_TYPE:                   return "Typeless media";
-               case B_MEDIA_UNKNOWN_TYPE:              return "Unknown media 
type";
-               case B_MEDIA_RAW_AUDIO:                 return "Raw audio";
-               case B_MEDIA_RAW_VIDEO:                 return "Raw video";
-               case B_MEDIA_VBL:                               return "Raw 
data from VBL area";
-               case B_MEDIA_TIMECODE:                  return "Timecode";
-               case B_MEDIA_MIDI:                              return "MIDI";
-               case B_MEDIA_TEXT:                              return "Text";
-               case B_MEDIA_HTML:                              return "HTML";
-               case B_MEDIA_MULTISTREAM:               return "Multistream 
media";
-               case B_MEDIA_PARAMETERS:                return "Parameters";
-               case B_MEDIA_ENCODED_AUDIO:             return "Encoded audio";
-               case B_MEDIA_ENCODED_VIDEO:             return "Encoded video";
+               case B_MEDIA_NO_TYPE:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Typeless 
media"));
+               case B_MEDIA_UNKNOWN_TYPE:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Unknown 
media type"));
+               case B_MEDIA_RAW_AUDIO:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Raw 
audio"));
+               case B_MEDIA_RAW_VIDEO:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Raw 
video"));
+               case B_MEDIA_VBL:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Raw data 
from VBL area"));
+               case B_MEDIA_TIMECODE:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Timecode"));
+               case B_MEDIA_MIDI:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("MIDI"));
+               case B_MEDIA_TEXT:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Text"));
+               case B_MEDIA_HTML:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("HTML"));
+               case B_MEDIA_MULTISTREAM:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Multistream 
media"));
+               case B_MEDIA_PARAMETERS:
+                       return 
sCatalog.GetString(B_TRANSLATE_MARK("Parameters"));
+               case B_MEDIA_ENCODED_AUDIO:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Encoded 
audio"));
+               case B_MEDIA_ENCODED_VIDEO:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Encoded 
video"));
                default: {
-                       if (type >= B_MEDIA_FIRST_USER_TYPE)
-                               return "User-defined media type";
-                       if (type >= B_MEDIA_PRIVATE)
-                               return "Private Be media type";
+                       if (type >= B_MEDIA_FIRST_USER_TYPE) {
+                               return sCatalog.GetString(B_TRANSLATE_MARK(
+                                       "User-defined media type"));
+                       }
+                       if (type >= B_MEDIA_PRIVATE) {
+                               return sCatalog.GetString(B_TRANSLATE_MARK(
+                                       "Private Be media type"));
+                       }
                }
        }
        return "Unknown Media Type";
@@ -210,15 +237,24 @@
        D_METHOD(("MediaString::getStringFor(media_format_family)\n"));

        switch (family) {
-               case B_ANY_FORMAT_FAMILY:               return "Any format 
family";
-               case B_BEOS_FORMAT_FAMILY:              return "BeOS format 
family";
-               case B_QUICKTIME_FORMAT_FAMILY: return "QuickTime format 
family";
-               case B_AVI_FORMAT_FAMILY:               return "AVI format 
family";
-               case B_ASF_FORMAT_FAMILY:               return "ASF format 
family";
-               case B_MPEG_FORMAT_FAMILY:              return "MPEG format 
family";
-               case B_WAV_FORMAT_FAMILY:               return "WAV format 
family";
-               case B_AIFF_FORMAT_FAMILY:              return "AIFF format 
family";
-               default:                                                return 
"Miscellaneous format family";
+               case B_ANY_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Any format 
family"));
+               case B_BEOS_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("BeOS format 
family"));
+               case B_QUICKTIME_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("QuickTime 
format family"));
+               case B_AVI_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("AVI format 
family"));
+               case B_ASF_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("ASF format 
family"));
+               case B_MPEG_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("MPEG format 
family"));
+               case B_WAV_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("WAV format 
family"));
+               case B_AIFF_FORMAT_FAMILY:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("AIFF format 
family"));
+               default:
+                       return 
sCatalog.GetString(B_TRANSLATE_MARK("Miscellaneous format family"));
        }
 }

@@ -488,10 +524,11 @@
        BString s;
        if ((source.port != media_source::null.port)
         && (source.id != media_source::null.id)) {
-               s << "Port " << source.port << ", ID " << source.id;
+               s << sCatalog.GetString(B_TRANSLATE_MARK("Port ")) << 
source.port
+                       << sCatalog.GetString(B_TRANSLATE_MARK(", ID ")) << 
source.id;
        }
        else {
-               s = "(none)";
+               s = sCatalog.GetString(B_TRANSLATE_MARK("(none)"));
        }
        return s;
 }
@@ -504,10 +541,11 @@
        BString s;
        if ((destination.port != media_destination::null.port)
         && (destination.id != media_destination::null.id)) {
-               s << "Port " << destination.port << ", ID " << destination.id;
+               s << sCatalog.GetString(B_TRANSLATE_MARK("Port ")) << 
destination.port
+                       << sCatalog.GetString(B_TRANSLATE_MARK(", ID ")) << 
destination.id;
        }
        else {
-               s = "(none)";
+               s = sCatalog.GetString(B_TRANSLATE_MARK("(none)"));
        }
        return s;
 }
@@ -528,25 +566,25 @@

        switch (format) {
                case media_raw_audio_format::B_AUDIO_UCHAR: {
-                       return "8 bit integer";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("8 bit 
integer"));
                }
                case media_raw_audio_format::B_AUDIO_SHORT:     {
-                       return "16 bit integer";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("16 bit 
integer"));
                }
                case media_raw_audio_format::B_AUDIO_FLOAT:     {
-                       return "32 bit float";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
float"));
                }
                case media_raw_audio_format::B_AUDIO_INT: {
                        BString s = "";
                        if (validBits != 
media_multi_audio_format::wildcard.valid_bits)
-                               s << validBits << " bit ";
+                               s << validBits << 
sCatalog.GetString(B_TRANSLATE_MARK(" bit "));
                        else
-                               s << "32 bit ";
-                       s << "integer";
+                               s << sCatalog.GetString(B_TRANSLATE_MARK("32 
bit "));
+                       s << sCatalog.GetString(B_TRANSLATE_MARK("integer"));
                        return s;
                }
                default: {
-                       return "(unknown format)";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(unknown 
format)"));
                }
        }
 }
@@ -561,7 +599,7 @@
        }

        BString s;
-       s << (frameRate / 1000) << " kHz";
+       s << (frameRate / 1000) << sCatalog.GetString(B_TRANSLATE_MARK(" kHz"));
        return s;
 }

@@ -576,14 +614,15 @@
        
        switch (channelCount) {
                case 1: {
-                       return "Mono";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Mono"));
                }
                case 2: {
-                       return "Stereo";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Stereo"));
                }
                default: {
                        BString s = "";
-                       s << channelCount << " Channels";
+                       s << channelCount
+                               << sCatalog.GetString(B_TRANSLATE_MARK(" 
Channels"));
                        return s;
                }
        }
@@ -600,13 +639,13 @@

        switch (byteOrder) {
                case B_MEDIA_BIG_ENDIAN: {
-                       return "Big endian";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Big 
endian"));
                }
                case B_MEDIA_LITTLE_ENDIAN: {
-                       return "Little endian";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Little 
endian"));
                }
                default: {
-                       return "(unknown byte order)";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(unknown 
byte order)"));
                }
        }
 }
@@ -621,7 +660,7 @@
        }

        BString s = "";
-       s << bufferSize << " bytes per buffer";
+       s << bufferSize << sCatalog.GetString(B_TRANSLATE_MARK(" bytes per 
buffer"));
        return s;
 }

@@ -634,202 +673,202 @@

        if (channelMask & B_CHANNEL_LEFT) {
                if (first) {
-                       list = "Left";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Left"));
                        first = false;
                }
        }
        if (channelMask & B_CHANNEL_RIGHT) {
                if (first) {
-                       list = "Right";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Right"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Right";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Right"));
                }
        }
        if (channelMask & B_CHANNEL_CENTER) {
                if (first) {
-                       list = "Center";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Center";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Center"));
                }
        }
        if (channelMask & B_CHANNEL_SUB) {
                if (first) {
-                       list = "Sub";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Sub"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Sub";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Sub"));
                }
        }
        if (channelMask & B_CHANNEL_REARLEFT) {
                if (first) {
-                       list = "Rear-left";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Rear-left"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Rear-left";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Rear-left"));
                }
        }
        if (channelMask & B_CHANNEL_REARRIGHT) {
                if (first) {
-                       list = "Rear-right";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Rear-right"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Rear-right";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Rear-right"));
                }
        }
        if (channelMask & B_CHANNEL_FRONT_LEFT_CENTER) {
                if (first) {
-                       list = "Front-left-center";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Front-left-center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Front-left-center";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Front-left-center"));
                }
        }
        if (channelMask & B_CHANNEL_FRONT_RIGHT_CENTER) {
                if (first) {
-                       list = "Front-right-center";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Front-right-center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Front-right-center";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Front-right-center"));
                }
        }
        if (channelMask & B_CHANNEL_BACK_CENTER) {
                if (first) {
-                       list = "Back-center";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Back-center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Back-center";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Back-center"));
                }
        }
        if (channelMask & B_CHANNEL_SIDE_LEFT) {
                if (first) {
-                       list = "Side-left";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Side-left"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Side-left";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Side-left"));
                }
        }
        if (channelMask & B_CHANNEL_SIDE_RIGHT) {
                if (first) {
-                       list = "Side-right";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Side-right"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Side-right";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Side-right"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_CENTER) {
                if (first) {
-                       list = "Top-center";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-center";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-center"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_FRONT_LEFT) {
                if (first) {
-                       list = "Top-Front-left";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Front-left"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-Front-left";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Front-left"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_FRONT_CENTER) {
                if (first) {
-                       list = "Top-Front-center";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Front-center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-Front-center";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Front-center"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_FRONT_RIGHT) {
                if (first) {
-                       list = "Top-Front-right";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Front-right"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-Front-right";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Front-right"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_BACK_LEFT) {
                if (first) {
-                       list = "Top-Back-left";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Back-left"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-Back-left";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Back-left"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_BACK_CENTER) {
                if (first) {
-                       list = "Top-Back-center";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Back-center"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-Back-center";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Back-center"));
                }
        }
        if (channelMask & B_CHANNEL_TOP_BACK_RIGHT) {
                if (first) {
-                       list = "Top-Back-right";
+                       list = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Back-right"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Top-Back-right";
+                       last = 
sCatalog.GetString(B_TRANSLATE_MARK("Top-Back-right"));
                }
        }
        if (last != "") {
                list << " & " << last;
        }
        if (list == "") {
-               list = "(none)";
+               list = sCatalog.GetString(B_TRANSLATE_MARK("(none)"));
        }

        return list;
@@ -840,10 +879,14 @@
        D_METHOD(("MediaString::forAudioMatrixMask()\n"));

        switch (matrixMask) {
-               case 0:                                                         
        return "(none)";
-               case B_MATRIX_PROLOGIC_LR:                              return 
"ProLogic LR";
-               case B_MATRIX_AMBISONIC_WXYZ:                   return 
"Ambisonic WXYZ";
-               default:                                                        
        return "(unknown matrix mask)";
+               case 0:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(none)"));
+               case B_MATRIX_PROLOGIC_LR:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("ProLogic 
LR"));
+               case B_MATRIX_AMBISONIC_WXYZ:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("Ambisonic 
WXYZ"));
+               default:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(unknown 
matrix mask)"));
        }
 }

@@ -862,7 +905,7 @@
        }

        BString s = "";
-       s << bitRate / 1000.0f << " kb/s";
+       s << bitRate / 1000.0f << sCatalog.GetString(B_TRANSLATE_MARK(" kb/s"));
        return s;
 }

@@ -876,7 +919,7 @@
        }

        BString s = "";
-       s << frameSize << " bytes per frame";
+       s << frameSize << sCatalog.GetString(B_TRANSLATE_MARK(" bytes per 
frame"));
        return s;
 }

@@ -896,51 +939,89 @@

        switch (format) {
                case B_RGB32:
-               case B_RGB32_BIG:               return "32 bit RGB";
+               case B_RGB32_BIG:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
RGB"));
                case B_RGBA32:
-               case B_RGBA32_BIG:              return "32 bit RGBA";
+               case B_RGBA32_BIG:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
RGBA"));
                case B_RGB24:
-               case B_RGB24_BIG:               return "24 bit RGB";
+               case B_RGB24_BIG:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
RGB"));
                case B_RGB16:
-               case B_RGB16_BIG:               return "16 bit RGB";
+               case B_RGB16_BIG:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("16 bit 
RGB"));
                case B_RGB15:
-               case B_RGB15_BIG:               return "15 bit RGB";
+               case B_RGB15_BIG:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("15 bit 
RGB"));
                case B_RGBA15:
-               case B_RGBA15_BIG:              return "15 bit RGBA";
-               case B_CMAP8:                   return "8 bit color-index";
-               case B_GRAY8:                   return "8 bit grayscale-index";
-               case B_GRAY1:                   return "Monochrome";
-               case B_YUV422:                  return "YUV422";
-               case B_YUV411:                  return "YUV411";
-               case B_YUV420:                  return "YUV420";
-               case B_YUV444:                  return "YUV444";
-               case B_YUV9:                    return "YUV9";
-               case B_YUV12:                   return "YUV12";
-               case B_YCbCr422:                return "YCbCr422";
-               case B_YCbCr411:                return "YCbCr411";
-               case B_YCbCr444:                return "YCbCr444";
-               case B_YCbCr420:                return "YCbCr420";
-               case B_UVL24:                   return "24 bit UVL";
-               case B_UVL32:                   return "32 bit UVL";
-               case B_UVLA32:                  return "32 bit UVLA";
-               case B_LAB24:                   return "24 bit LAB";
-               case B_LAB32:                   return "32 bit LAB";
-               case B_LABA32:                  return "32 bit LABA";
-               case B_HSI24:                   return "24 bit HSI";
-               case B_HSI32:                   return "32 bit HSI";
-               case B_HSIA32:                  return "32 bit HSIA";
-               case B_HSV24:                   return "24 bit HSV";
-               case B_HSV32:                   return "32 bit HSV";
-               case B_HSVA32:                  return "32 bit HSVA";
-               case B_HLS24:                   return "24 bit HLS";
-               case B_HLS32:                   return "32 bit HLS";
-               case B_HLSA32:                  return "32 bit HLSA";
-               case B_CMY24:                   return "24 bit CMY";
-               case B_CMY32:                   return "32 bit CMY";
-               case B_CMYA32:                  return "32 bit CMYA";
-               case B_CMYK32:                  return "32 bit CMYK";
+               case B_RGBA15_BIG:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("15 bit 
RGBA"));
+               case B_CMAP8:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("8 bit 
color-index"));
+               case B_GRAY8:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("8 bit 
grayscale-index"));
+               case B_GRAY1:
+                       return 
sCatalog.GetString(B_TRANSLATE_MARK("Monochrome"));
+               case B_YUV422:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YUV422"));
+               case B_YUV411:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YUV411"));
+               case B_YUV420:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YUV420"));
+               case B_YUV444:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YUV444"));
+               case B_YUV9:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YUV9"));
+               case B_YUV12:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YUV12"));
+               case B_YCbCr422:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YCbCr422"));
+               case B_YCbCr411:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YCbCr411"));
+               case B_YCbCr444:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YCbCr444"));
+               case B_YCbCr420:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("YCbCr420"));
+               case B_UVL24:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
UVL"));
+               case B_UVL32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
UVL"));
+               case B_UVLA32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
UVLA"));
+               case B_LAB24:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
LAB"));
+               case B_LAB32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
LAB"));
+               case B_LABA32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
LABA"));
+               case B_HSI24:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
HSI"));
+               case B_HSI32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
HSI"));
+               case B_HSIA32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
HSIA"));
+               case B_HSV24:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
HSV"));
+               case B_HSV32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
HSV"));
+               case B_HSVA32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
HSVA"));
+               case B_HLS24:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
HLS"));
+               case B_HLS32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
HLS"));
+               case B_HLSA32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
HLSA"));
+               case B_CMY24:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("24 bit 
CMY"));
+               case B_CMY32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
CMY"));
+               case B_CMYA32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
CMYA"));
+               case B_CMYK32:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("32 bit 
CMYK"));
                default: {
-                       return "(unknown video format)";
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(unknown 
video format)"));
                }
        }
 }
@@ -973,18 +1054,18 @@

        BString s = "";
        if (interlace == 1) {
-               s << "Non-interlaced ";
+               s << sCatalog.GetString(B_TRANSLATE_MARK("Non-interlaced "));
        }
        else {
-               s << "Interlaced ";
+               s << sCatalog.GetString(B_TRANSLATE_MARK("Interlaced "));
        }
-       s << fieldRate << " Hz";
+       s << fieldRate << sCatalog.GetString(B_TRANSLATE_MARK(" Hz"));
        if ((fieldRate > 49.9) && (fieldRate < 50.1)) {
-               s << " (PAL)";
+               s << sCatalog.GetString(B_TRANSLATE_MARK(" (PAL)"));
        }
        else if (((interlace == 2) && (fieldRate > 59.9) && (fieldRate < 60.0))
                  || ((interlace == 1) && (fieldRate > 29.9) && (fieldRate < 
30.0))) {
-               s << " (NTSC)";
+               s << sCatalog.GetString(B_TRANSLATE_MARK(" (NTSC)"));
        }

        return s;
@@ -1001,13 +1082,16 @@

        switch (orientation) {
                case B_VIDEO_TOP_LEFT_RIGHT: {
-                       return "Top to bottom, left to right";
+                       return sCatalog.GetString(B_TRANSLATE_MARK(
+                               "Top to bottom, left to right"));
                }
                case B_VIDEO_BOTTOM_LEFT_RIGHT: {
-                       return "Bottom to top, left to right";
+                       return sCatalog.GetString(B_TRANSLATE_MARK(
+                               "Bottom to top, left to right"));
                }
                default: {
-                       return "(unkown video orientation)";
+                       return sCatalog.GetString(B_TRANSLATE_MARK(
+                               "(unkown video orientation)"));
                }
        }
 }
@@ -1040,9 +1124,9 @@
                return "*";
        }

-       BString s = "Video data between";
-       s << " line " << firstActive;
-       s << " and " << lastActive;
+       BString s = sCatalog.GetString(B_TRANSLATE_MARK("Video data between"));
+       s << sCatalog.GetString(B_TRANSLATE_MARK(" line ")) << firstActive;
+       s << sCatalog.GetString(B_TRANSLATE_MARK(" and ")) << lastActive;
        return s;
 }

@@ -1056,7 +1140,7 @@
        }

        BString s = "";
-       s << bytesPerRow << " bytes per row";
+       s << bytesPerRow << sCatalog.GetString(B_TRANSLATE_MARK(" bytes per 
row"));
        return s;
 }

@@ -1068,13 +1152,13 @@

        BString s = "";
        if (pixelOffset != media_video_display_info::wildcard.pixel_offset) {
-               s << pixelOffset << " pixels";
+               s << pixelOffset << sCatalog.GetString(B_TRANSLATE_MARK(" 
pixels"));
        }
        if (lineOffset != media_video_display_info::wildcard.line_offset) {
                if (s != "") {
                        s << ", ";
                }
-               s << pixelOffset << " lines";
+               s << pixelOffset << sCatalog.GetString(B_TRANSLATE_MARK(" 
lines"));
        }
        if (s == "") {
                s = "*";
@@ -1095,13 +1179,13 @@

        BString s = "";
        if (avgBitRate != media_encoded_video_format::wildcard.avg_bit_rate) {
-               s << avgBitRate / 1000.0f << " kb/s (avg)";
+               s << avgBitRate / 1000.0f << 
sCatalog.GetString(B_TRANSLATE_MARK(" kb/s (avg)"));
        }
        if (maxBitRate != media_encoded_video_format::wildcard.max_bit_rate) {
                if (s != "") {
                        s << ", ";
                }
-               s << maxBitRate / 1000.0f << " kb/s (max)";
+               s << maxBitRate / 1000.0f << 
sCatalog.GetString(B_TRANSLATE_MARK(" kb/s (max)"));
        }
        if (s == "") {
                s = "*";
@@ -1119,7 +1203,7 @@
        }

        BString s = "";
-       s << frameSize << " bytes per frame";
+       s << frameSize << sCatalog.GetString(B_TRANSLATE_MARK(" bytes per 
frame"));
        return s;
 }

@@ -1131,13 +1215,15 @@

        BString s = "";
        if (forwardHistory != 
media_encoded_video_format::wildcard.forward_history) {
-               s << static_cast<int32>(forwardHistory) << " frames forward";
+               s << static_cast<int32>(forwardHistory)
+                       << sCatalog.GetString(B_TRANSLATE_MARK(" frames 
forward"));
        }
        if (backwardHistory != 
media_encoded_video_format::wildcard.backward_history) {
                if (s != "") {
                        s << ", ";
                }
-               s << static_cast<int32>(backwardHistory) << " frames backward";
+               s << static_cast<int32>(backwardHistory)
+                       << sCatalog.GetString(B_TRANSLATE_MARK(" frames 
backward"));
        }
        if (s == "") {
                s = "*";
@@ -1160,12 +1246,18 @@
        }

        switch (format) {
-               case media_multistream_format::B_VID:           return "BeOS 
video";
-               case media_multistream_format::B_AVI:           return "AVI";
-               case media_multistream_format::B_MPEG1:         return "MPEG1";
-               case media_multistream_format::B_MPEG2:         return "MPEG2";
-               case media_multistream_format::B_QUICKTIME:     return 
"QuickTime";
-               default:                                                        
                return "(unknown multistream format)";
+               case media_multistream_format::B_VID:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("BeOS 
video"));
+               case media_multistream_format::B_AVI:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("AVI"));
+               case media_multistream_format::B_MPEG1:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("MPEG1"));
+               case media_multistream_format::B_MPEG2:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("MPEG2"));
+               case media_multistream_format::B_QUICKTIME:
+                       return 
sCatalog.GetString(B_TRANSLATE_MARK("QuickTime"));
+               default:
+                       return sCatalog.GetString(B_TRANSLATE_MARK("(unknown 
multistream format)"));
        }
 }

@@ -1177,13 +1269,13 @@

        BString s = "";
        if (avgBitRate != media_multistream_format::wildcard.avg_bit_rate) {
-               s << avgBitRate / 1000.0f << " kb/s (avg)";
+               s << avgBitRate / 1000.0f << 
sCatalog.GetString(B_TRANSLATE_MARK(" kb/s (avg)"));
        }
        if (maxBitRate != media_multistream_format::wildcard.max_bit_rate) {
                if (s != "") {
                        s << ", ";
                }
-               s << maxBitRate / 1000.0f << " kb/s (max)";
+               s << maxBitRate / 1000.0f << 
sCatalog.GetString(B_TRANSLATE_MARK(" kb/s (max)"));
        }
        if (s == "") {
                s = "*";
@@ -1199,13 +1291,13 @@

        BString s = "";
        if (avgChunkSize != media_multistream_format::wildcard.avg_chunk_size) {
-               s << avgChunkSize << " bytes (avg)";
+               s << avgChunkSize << sCatalog.GetString(B_TRANSLATE_MARK(" 
bytes (avg)"));
        }
        if (maxChunkSize != media_multistream_format::wildcard.max_chunk_size) {
                if (s != "") {
                        s << ", ";
                }
-               s << maxChunkSize << " bytes (max)";
+               s << maxChunkSize << sCatalog.GetString(B_TRANSLATE_MARK(" 
bytes (max)"));
        }
        if (s == "") {
                s = "*";
@@ -1223,30 +1315,30 @@

        if (flags & media_multistream_format::B_HEADER_HAS_FLAGS) {
                if (first) {
-                       list = "Header has flags";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Header has 
flags"));
                        first = false;
                }
        }
        if (flags & media_multistream_format::B_CLEAN_BUFFERS) {
                if (first) {
-                       list = "Clean buffers";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Clean 
buffers"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Clean buffers";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Clean 
buffers"));
                }
        }
        if (flags & media_multistream_format::B_HOMOGENOUS_BUFFERS) {
                if (first) {
-                       list = "Homogenous buffers";
+                       list = sCatalog.GetString(B_TRANSLATE_MARK("Homogenous 
buffers"));
                        first = false;
                }
                else {
                        if (last != "")
                                list << ", " << last;
-                       last = "Homogenous buffers";
+                       last = sCatalog.GetString(B_TRANSLATE_MARK("Homogenous 
buffers"));
                }
        }

@@ -1254,7 +1346,7 @@
                list << " & " << last;

        if (list == "")
-               list = "(none)";
+               list = sCatalog.GetString(B_TRANSLATE_MARK("(none)"));

        return list;
 }
diff --git a/src/kits/locale/Catalog.cpp b/src/kits/locale/Catalog.cpp
index 25c2104..a5c9041 100644
--- a/src/kits/locale/Catalog.cpp
+++ b/src/kits/locale/Catalog.cpp
@@ -37,6 +37,15 @@
 }


+BCatalog::BCatalog(const char* signature, const char* language)
+       :
+       fCatalogData(NULL),
+       fLock("Catalog")
+{
+       SetTo(signature, language);
+}
+
+
 BCatalog::~BCatalog()
 {
        MutableLocaleRoster::Default()->UnloadCatalog(fCatalogData);
@@ -196,6 +205,21 @@


 status_t
+BCatalog::SetTo(const char* signature, const char* language)
+{
+       BAutolock lock(&fLock);
+       if (!lock.IsLocked())
+               return B_ERROR;
+
+       MutableLocaleRoster::Default()->UnloadCatalog(fCatalogData);
+       fCatalogData = MutableLocaleRoster::Default()->LoadCatalog(signature,
+               language);
+
+       return B_OK;
+}
+
+
+status_t
 BCatalog::InitCheck() const
 {
        BAutolock lock(&fLock);
diff --git a/src/kits/locale/DefaultCatalog.cpp 
b/src/kits/locale/DefaultCatalog.cpp
index d3d240a..d9771e3 100644
--- a/src/kits/locale/DefaultCatalog.cpp
+++ b/src/kits/locale/DefaultCatalog.cpp
@@ -87,30 +87,10 @@
        BPath catalogPath(&appDir, catalogName.String());
        status = ReadFromFile(catalogPath.Path());

-       if (status != B_OK) {
-               // search in data folders
-
-               directory_which which[] = {
-                       B_USER_NONPACKAGED_DATA_DIRECTORY,
-                       B_USER_DATA_DIRECTORY,
-                       B_SYSTEM_NONPACKAGED_DATA_DIRECTORY,
-                       B_SYSTEM_DATA_DIRECTORY
-               };
-
-               for (size_t i = 0; i < sizeof(which) / sizeof(which[0]); i++) {
-                       BPath path;
-                       if (find_directory(which[i], &path) == B_OK) {
-                               BString catalogName(path.Path());
-                               catalogName << "/locale/" << kCatFolder
-                                       << "/" << fSignature
-                                       << "/" << fLanguageName
-                                       << kCatExtension;
-                               status = ReadFromFile(catalogName.String());
-                               if (status == B_OK)
-                                       break;
-                       }
-               }
-       }
+       // search for catalogs in the standard ../data/locale/ directories
+       // (packaged/non-packaged and system/home)
+       if (status != B_OK)
+               status = ReadFromStandardLocations();

        if (status != B_OK) {
                // give lowest priority to catalog embedded as resource in 
application
@@ -188,6 +168,38 @@


 status_t
+DefaultCatalog::ReadFromStandardLocations()
+{
+       // search in data folders
+
+       directory_which which[] = {
+               B_USER_NONPACKAGED_DATA_DIRECTORY,
+               B_USER_DATA_DIRECTORY,
+               B_SYSTEM_NONPACKAGED_DATA_DIRECTORY,
+               B_SYSTEM_DATA_DIRECTORY
+       };
+
+       status_t status = B_ENTRY_NOT_FOUND;
+
+       for (size_t i = 0; i < sizeof(which) / sizeof(which[0]); i++) {
+               BPath path;
+               if (find_directory(which[i], &path) == B_OK) {
+                       BString catalogName(path.Path());
+                       catalogName << "/locale/" << kCatFolder
+                               << "/" << fSignature
+                               << "/" << fLanguageName
+                               << kCatExtension;
+                       status = ReadFromFile(catalogName.String());
+                       if (status == B_OK)
+                               break;
+               }
+       }
+
+       return status;
+}
+
+
+status_t
 DefaultCatalog::ReadFromFile(const char *path)
 {
        if (!path)
@@ -228,40 +240,6 @@
 }


-/*
- * this method is not currently being used, but it may be useful in the 
future...
- */
-status_t
-DefaultCatalog::ReadFromAttribute(const entry_ref &appOrAddOnRef)
-{
-       BNode node;
-       status_t res = node.SetTo(&appOrAddOnRef);
-       if (res != B_OK)
-               return B_ENTRY_NOT_FOUND;
-
-       attr_info attrInfo;
-       res = node.GetAttrInfo(BLocaleRoster::kEmbeddedCatAttr, &attrInfo);
-       if (res != B_OK)
-               return B_NAME_NOT_FOUND;
-       if (attrInfo.type != B_MESSAGE_TYPE)
-               return B_BAD_TYPE;
-
-       size_t size = attrInfo.size;
-       BStackOrHeapArray<char, 0> buf(size);
-       if (!buf.IsValid())
-               return B_NO_MEMORY;
-       res = node.ReadAttr(BLocaleRoster::kEmbeddedCatAttr, B_MESSAGE_TYPE, 0,
-               buf, size);
-       if (res < (ssize_t)size)
-               return res < B_OK ? res : B_BAD_DATA;
-
-       BMemoryIO memIO(buf, size);
-       res = Unflatten(&memIO);
-
-       return res;
-}
-
-
 status_t
 DefaultCatalog::ReadFromResource(const entry_ref &appOrAddOnRef)
 {
@@ -317,36 +295,6 @@
 }


-/*
- * this method is not currently being used, but it may be useful in the
- * future...
- */
-status_t
-DefaultCatalog::WriteToAttribute(const entry_ref &appOrAddOnRef)
-{
-       BNode node;
-       status_t res = node.SetTo(&appOrAddOnRef);
-       if (res != B_OK)
-               return res;
-
-       BMallocIO mallocIO;
-       mallocIO.SetBlockSize(max(fCatMap.Size() * 20, (int32)256));
-               // set a largish block-size in order to avoid reallocs
-       res = Flatten(&mallocIO);
-
-       if (res == B_OK) {
-               ssize_t wsz;
-               wsz = node.WriteAttr(BLocaleRoster::kEmbeddedCatAttr, 
B_MESSAGE_TYPE, 0,
-                       mallocIO.Buffer(), mallocIO.BufferLength());
-               if (wsz < B_OK)
-                       res = wsz;
-               else if (wsz != (ssize_t)mallocIO.BufferLength())
-                       res = B_ERROR;
-       }
-       return res;
-}
-
-
 status_t
 DefaultCatalog::WriteToResource(const entry_ref &appOrAddOnRef)
 {
diff --git a/src/kits/locale/MutableLocaleRoster.cpp 
b/src/kits/locale/MutableLocaleRoster.cpp
index 3ca25e3..03debea 100644
--- a/src/kits/locale/MutableLocaleRoster.cpp
+++ b/src/kits/locale/MutableLocaleRoster.cpp
@@ -16,6 +16,7 @@
 #include <Autolock.h>
 #include <Catalog.h>
 #include <CatalogData.h>
+#include <DefaultCatalog.h>
 #include <Debug.h>
 #include <Entry.h>
 #include <FormattingConventions.h>
@@ -191,7 +192,7 @@
                if (!info->MakeSureItsLoaded() || !info->fInstantiateFunc)
                        continue;
                BMessage languages;
-               if (language)
+               if (language != NULL)
                        // try to load catalogs for the given language:
                        languages.AddString("language", language);
                else
@@ -200,7 +201,8 @@

                BCatalogData* catalog = NULL;
                const char* lang;
-               for (int32 l=0; languages.FindString("language", l, 
&lang)==B_OK; ++l) {
+               for (int32 l=0; languages.FindString("language", l, &lang) == 
B_OK;
+                       ++l) {
                        catalog = info->fInstantiateFunc(catalogOwner, lang, 
fingerprint);
                        if (catalog)
                                info->fLoadedCatalogs.AddItem(catalog);
@@ -212,7 +214,7 @@
                        // to "english"):
                        int32 pos;
                        BString langName(lang);
-                       BCatalogData* currCatalog = catalog;
+                       BCatalogData* currentCatalog = catalog;
                        BCatalogData* nextCatalog = NULL;
                        while ((pos = langName.FindLast('_')) >= 0) {
                                // language is based on parent, so we load 
that, too:
@@ -222,11 +224,11 @@
                                        langName.String(), fingerprint);
                                if (nextCatalog) {
                                        
info->fLoadedCatalogs.AddItem(nextCatalog);
-                                       if(currCatalog)
-                                               
currCatalog->SetNext(nextCatalog);
+                                       if (currentCatalog)
+                                               
currentCatalog->SetNext(nextCatalog);
                                        else
                                                catalog = nextCatalog;
-                                       currCatalog = nextCatalog;
+                                       currentCatalog = nextCatalog;
                                }
                        }
                        if (catalog != NULL)
@@ -240,6 +242,109 @@


 /*
+ * Loads a catalog for the given signature and language.
+ *
+ * Only the default catalog type is searched, and only the standard system
+ * directories.
+ *
+ * If a catalog depends on another language (as 'english-british' depends
+ * on 'english') the dependant catalogs are automatically loaded, too.
+ * So it is perfectly possible that this method returns a catalog-chain
+ * instead of a single catalog.
+ * NULL is returned if no matching catalog could be found.
+ */
+BCatalogData*
+MutableLocaleRoster::LoadCatalog(const char* signature,
+       const char* language) const
+{
+       BAutolock lock(fData->fLock);
+       if (!lock.IsLocked())
+               return NULL;
+
+       BMessage languages;
+       if (language != NULL)
+               // try to load catalogs for the given language:
+               languages.AddString("language", language);
+       else
+               // try to load catalogs for one of the preferred languages:
+               GetPreferredLanguages(&languages);
+
+
+       int32 count = fData->fCatalogAddOnInfos.CountItems();
+       CatalogAddOnInfo* defaultCatalogInfo = NULL;
+       for (int32 i = 0; i < count; ++i) {
+               CatalogAddOnInfo* info = (CatalogAddOnInfo*)
+                       fData->fCatalogAddOnInfos.ItemAt(i);
+               if (info->MakeSureItsLoaded()
+                       && info->fInstantiateFunc
+                               == BPrivate::DefaultCatalog::Instantiate) {
+                       defaultCatalogInfo = info;
+                       break;
+               }
+       }
+
+       if (defaultCatalogInfo == NULL)
+               return NULL;
+
+       BPrivate::DefaultCatalog* catalog = NULL;
+       const char* lang;
+       for (int32 l=0; languages.FindString("language", l, &lang) == B_OK; 
++l) {
+               catalog = new (std::nothrow) BPrivate::DefaultCatalog(NULL, 
signature,
+                       lang);
+               if (catalog == NULL)
+                       continue;
+
+               if (catalog->InitCheck() != B_OK
+                       || catalog->ReadFromStandardLocations() != B_OK) {
+                       delete catalog;
+                       continue;
+               }
+
+               defaultCatalogInfo->fLoadedCatalogs.AddItem(catalog);
+
+               // Chain-load catalogs for languages that depend on
+               // other languages.
+               // The current implementation uses the filename in order to
+               // detect dependencies (parenthood) between languages (it
+               // traverses from "english_british_oxford" to "english_british"
+               // to "english"):
+               int32 pos;
+               BString langName(lang);
+               BCatalogData* currentCatalog = catalog;
+               BPrivate::DefaultCatalog* nextCatalog = NULL;
+               while ((pos = langName.FindLast('_')) >= 0) {
+                       // language is based on parent, so we load that, too:
+                       // (even if the parent catalog was not found)
+                       langName.Truncate(pos);
+                       nextCatalog = new (std::nothrow) 
BPrivate::DefaultCatalog(NULL,
+                               signature, langName.String());
+
+                       if (nextCatalog == NULL)
+                               continue;
+
+                       if (nextCatalog->InitCheck() != B_OK
+                               || nextCatalog->ReadFromStandardLocations() != 
B_OK) {
+                               delete nextCatalog;
+                               continue;
+                       }
+
+                       
defaultCatalogInfo->fLoadedCatalogs.AddItem(nextCatalog);
+
+                       if (currentCatalog != NULL)
+                               currentCatalog->SetNext(nextCatalog);
+                       else
+                               catalog = nextCatalog;
+                       currentCatalog = nextCatalog;
+               }
+               if (catalog != NULL)
+                       return catalog;
+       }
+
+       return NULL;
+}
+
+
+/*
  * unloads the given catalog (or rather: catalog-chain).
  * Every single catalog of the chain will be deleted automatically.
  * Add-ons that have no more current catalogs are unloaded, too.

--
To view, visit https://review.haiku-os.org/c/haiku/+/3173
To unsubscribe, or for help writing mail filters, visit 
https://review.haiku-os.org/settings

Gerrit-Project: haiku
Gerrit-Branch: master
Gerrit-Change-Id: I8801c81d12ed64485daab48f96b823c0334798d8
Gerrit-Change-Number: 3173
Gerrit-PatchSet: 1
Gerrit-Owner: Adrien Destugues <pulkomandy@xxxxxxxxx>
Gerrit-MessageType: newchange

Other related posts: