diff --git a/profile/public/nsIProfileInternal.idl b/profile/public/nsIProfileInternal.idl index 9601d431b82..694464e8e06 100755 --- a/profile/public/nsIProfileInternal.idl +++ b/profile/public/nsIProfileInternal.idl @@ -79,12 +79,18 @@ interface nsIProfileInternal : nsIProfile { in wstring regOption); [noscript] string isRegStringSet(in wstring profileName); + void createNewProfileWithLocales(in wstring profileName, + in wstring nativeProfileDir, + in wstring UILocale, + in wstring contentLocale, + in boolean useExistingDir); /** * The remaining methods are deprecated. DO NOT USE THEM. */ boolean isCurrentProfileAvailable(); [noscript] void getCurrentProfileDir(out nsIFile profileDir); + }; #endif /* nsIProfileInternal_h__ */ diff --git a/profile/resources/content/createProfileWizard.js b/profile/resources/content/createProfileWizard.js index 0c675dfeeab..6898af758d3 100644 --- a/profile/resources/content/createProfileWizard.js +++ b/profile/resources/content/createProfileWizard.js @@ -80,25 +80,6 @@ function onCancel() } } -function selectLocale(langcode) -{ - try { - var chromeRegistry = Components.classes["@mozilla.org/chrome/chrome-registry;1"].getService(); - if ( chromeRegistry ) { - chromeRegistry = chromeRegistry.QueryInterface( Components.interfaces.nsIChromeRegistry ); - } - //var old_lang = chromeRegistry.getSelectedLocale("navigator"); - //dump("\n --> createPrifleWizard.j sold_lang=" + old_lang + "--\n"); - chromeRegistry.selectLocale(langcode, true); - dump("\n --> createPrifleWizard.js langcode=" + langcode + "--\n"); - } - catch(e) { - dump("\n--> createPrifleWizard.js: selectLocale() failed!\n"); - return false; - } - return true; -} - function onFinish() { @@ -118,12 +99,6 @@ function onFinish() proceed = processCreateProfileData(profName, profDir, profLang, profRegion); if( proceed ) { - - //select locale region - if (profRegion) { - selectLocale(profRegion); - } - if( window.opener ) { window.opener.CreateProfile(profName, profDir); } @@ -191,7 +166,7 @@ function processCreateProfileData( aProfName, aProfDir, langcode, regioncode) useExistingDir = true; dump("*** going to create a new profile called " + aProfName + " in folder: " + aProfDir + "\n"); - profile.createNewProfile(aProfName, aProfDir, langcode, useExistingDir); + profile.createNewProfileWithLocales(aProfName, aProfDir, langcode, regioncode, useExistingDir); return true; } diff --git a/profile/src/nsProfile.cpp b/profile/src/nsProfile.cpp index f75b67f18d0..4f99e2a106d 100644 --- a/profile/src/nsProfile.cpp +++ b/profile/src/nsProfile.cpp @@ -102,7 +102,8 @@ #define INSTALLER_CMD_LINE_ARG "-installer" #define CREATE_PROFILE_CMD_LINE_ARG "-CreateProfile" #define PROFILE_CMD_LINE_ARG "-P" -#define LANG_CMD_LINE_ARG "-lang" +#define UILOCALE_CMD_LINE_ARG "-UILocale" +#define CONTENTLOCALE_CMD_LINE_ARG "-contentLocale" #define PREF_CONFIRM_AUTOMIGRATION "profile.confirm_automigration" #define SHRIMP_PREF "shrimp.startup.enable" @@ -127,6 +128,7 @@ const char* kDefaultOpenWindowParams = "centerscreen,chrome,modal,titlebar"; #define DEBUG_profile_verbose 1 #endif + // ProfileAccess varaible (gProfileDataAccess) to access registry operations // gDataAccessInstCount is used to keep track of instance count to activate // destructor at the right time (count == 0) @@ -134,8 +136,8 @@ static nsProfileAccess* gProfileDataAccess = nsnull; static PRInt32 gInstanceCount = 0; // Profile database to remember which profile has been -// created with UI lang on profileManager -static nsHashtable *gLangProfiles = nsnull; +// created with UILocale and contentLocale on profileManager +static nsHashtable *gLocaleProfiles = nsnull; // Atoms for file locations static nsIAtom* sApp_PrefsDirectory50 = nsnull; @@ -248,13 +250,14 @@ nsProfile::nsProfile() mDiskSpaceErrorQuitCalled = PR_FALSE; mCurrentProfileAvailable = PR_FALSE; - mIsLangSpecified = PR_FALSE; + mIsUILocaleSpecified = PR_FALSE; + mIsContentLocaleSpecified = PR_FALSE; if (gInstanceCount++ == 0) { gProfileDataAccess = new nsProfileAccess(); - gLangProfiles = new nsHashtable(); + gLocaleProfiles = new nsHashtable(); // Make our directory atoms @@ -303,7 +306,7 @@ nsProfile::~nsProfile() delete gProfileDataAccess; - delete gLangProfiles; + delete gLocaleProfiles; NS_IF_RELEASE(sApp_PrefsDirectory50); NS_IF_RELEASE(sApp_PreferencesFile50); @@ -383,11 +386,13 @@ nsProfile::StartupWithArgs(nsICmdLineService *cmdLineArgs, PRBool canInteract) if (NS_FAILED(rv)) return rv; } - // check UI language is specified on profileManager, otherwise, - // when -lang option is specified, install the ui language + // check UILocale is specified on profileManager, otherwise, + // when -UILocale option is specified, install the UILocale - // -lang is not specified - if (mIsLangSpecified == PR_FALSE) return NS_OK; + // -UILocale or -contentLocale is not specified + if (mIsUILocaleSpecified == PR_FALSE && mIsContentLocaleSpecified == PR_FALSE) { + return NS_OK; + } nsCOMPtr profileDir; @@ -398,29 +403,52 @@ nsProfile::StartupWithArgs(nsICmdLineService *cmdLineArgs, PRBool canInteract) rv = profileDir->GetPath(getter_Copies(pathBuf)); if (NS_FAILED(rv)) return rv; - // -lang has been specified, but - // user has selected UI language and region for this profile + // -UILocale or -contentLocale has been specified, but + // user has selected UILocale and contentLocale for this profile // on profileManager - // We should use the language + // We should not set here nsCStringKey key((const char *)pathBuf); - if ((int)gLangProfiles->Get(&key) == PR_TRUE) { + if ((int)gLocaleProfiles->Get(&key) == PR_TRUE) { +#ifdef DEBUG_profile_verbose + printf(" already set UILocale and contentLocale: %s\n", NS_STATIC_CAST(const char*, pathBuf)); + printf(" will not install locale\n"); +#endif return NS_OK; } - gLangProfiles->Remove(&key); + gLocaleProfiles->Remove(&key); - // Install UI language to the profile - const PRUnichar* langcode = mLangName.GetUnicode() ; - if (langcode && nsCRT::strlen(langcode) != 0) { - nsCOMPtr chromeRegistry = do_GetService(kChromeRegistryCID, - &rv); - if (NS_SUCCEEDED(rv)) { - nsFileSpec fileSpec((const char *)pathBuf); - nsFileURL fileURL(fileSpec); - const char* fileStr = fileURL.GetURLString(); - rv = chromeRegistry->SelectLocaleForProfile(langcode, - NS_ConvertUTF8toUCS2(fileStr).get()); - if (NS_FAILED(rv)) return rv; - } + nsCOMPtr chromeRegistry = do_GetService(kChromeRegistryCID, &rv); + if (NS_FAILED(rv)) return rv; + + // Install to the profile + nsFileSpec fileSpec((const char *)pathBuf); + nsFileURL fileURL(fileSpec); + const char* fileStr = fileURL.GetURLString(); + + // NEED TO FIX: when current UILocale and contentLocale are same with specified locales, + // we shouldn't install them again here. But chromeRegistry->GetSelectedLocale() doesn't + // work here properly. It always returns global and global-region of default not current + // profile + const PRUnichar* uilocale = mUILocaleName.GetUnicode() ; + if (uilocale && uilocale[0]) { +#ifdef DEBUG_profile_verbose + nsCAutoString temp1; temp1.AssignWithConversion(uilocale); + printf(" install new UILocaleName: %s\n", NS_STATIC_CAST(const char*, temp1)); +#endif + rv = chromeRegistry->SelectLocaleForProfile(uilocale, + NS_ConvertUTF8toUCS2(fileStr).get()); + if (NS_FAILED(rv)) return rv; + } + + const PRUnichar* contentlocale = mContentLocaleName.GetUnicode() ; + if (contentlocale && contentlocale[0]) { +#ifdef DEBUG_profile_verbose + nsCAutoString temp2; temp2.AssignWithConversion(contentlocale); + printf(" install new mContentLocaleName: %s\n", NS_STATIC_CAST(const char*, temp2)); +#endif + rv = chromeRegistry->SelectLocaleForProfile(contentlocale, + NS_ConvertUTF8toUCS2(fileStr).get()); + if (NS_FAILED(rv)) return rv; } #ifdef DEBUG_profile_verbose @@ -620,23 +648,23 @@ nsProfile::ProcessArgs(nsICmdLineService *cmdLineArgs, #endif // check for command line arguments for profile manager - // -lang command - rv = cmdLineArgs->GetCmdLineValue(LANG_CMD_LINE_ARG, getter_Copies(cmdResult)); + // -UILocale command + rv = cmdLineArgs->GetCmdLineValue(UILOCALE_CMD_LINE_ARG, getter_Copies(cmdResult)); if (NS_SUCCEEDED(rv)) { if (cmdResult) { - mIsLangSpecified = PR_TRUE; - mLangName.AssignWithConversion(cmdResult); + mIsUILocaleSpecified = PR_TRUE; + mUILocaleName.AssignWithConversion(cmdResult); + } + } - // update global locale if possible - // (in case when user-*.rdf can be updated) - // profilemanager will be invoked in the UI language - nsresult rv = NS_OK; - nsCOMPtr chromeRegistry = - do_GetService(kChromeRegistryCID, &rv); - if (NS_SUCCEEDED(rv)) { - rv = chromeRegistry->SelectLocale(mLangName.GetUnicode(), PR_FALSE); - } + // -contentLocale command + rv = cmdLineArgs->GetCmdLineValue(CONTENTLOCALE_CMD_LINE_ARG, getter_Copies(cmdResult)); + if (NS_SUCCEEDED(rv)) + { + if (cmdResult) { + mIsContentLocaleSpecified = PR_TRUE; + mContentLocaleName.AssignWithConversion(cmdResult); } } @@ -1278,12 +1306,12 @@ nsresult nsProfile::SetProfileDir(const PRUnichar *profileName, nsIFile *profile return rv; } - -// Creates a new profile +// Creates a new profile with UILocale and contentLocale NS_IMETHODIMP -nsProfile::CreateNewProfile(const PRUnichar* profileName, +nsProfile::CreateNewProfileWithLocales(const PRUnichar* profileName, const PRUnichar* nativeProfileDir, - const PRUnichar* langcode, + const PRUnichar* aUILocale, + const PRUnichar* aContentLocale, PRBool useExistingDir) { NS_ENSURE_ARG_POINTER(profileName); @@ -1292,7 +1320,7 @@ nsProfile::CreateNewProfile(const PRUnichar* profileName, #if defined(DEBUG_profile) { - printf("ProfileManager : CreateNewProfile\n"); + printf("ProfileManager : CreateNewProfileWithLocales\n"); nsCAutoString temp1; temp1.AssignWithConversion(profileName); printf("Profile Name: %s\n", NS_STATIC_CAST(const char*, temp1)); @@ -1370,34 +1398,97 @@ nsProfile::CreateNewProfile(const PRUnichar* profileName, rv = NS_GetSpecialDirectory(NS_APP_PROFILE_DEFAULTS_NLOC_50_DIR, getter_AddRefs(profDefaultsDir)); if (NS_FAILED(rv)) return rv; - if (langcode && nsCRT::strlen(langcode) != 0) { - // caller prefers locale subdir - nsCOMPtr locProfDefaultsDir; - rv = profDefaultsDir->Clone(getter_AddRefs(locProfDefaultsDir)); - if (NS_FAILED(rv)) return rv; - - locProfDefaultsDir->AppendUnicode(langcode); - rv = locProfDefaultsDir->Exists(&exists); - if (NS_SUCCEEDED(rv) && exists) { - profDefaultsDir = locProfDefaultsDir; // transfers ownership + nsCOMPtr chromeRegistry = do_GetService(kChromeRegistryCID, &rv); + if (NS_SUCCEEDED(rv)) { + + const PRUnichar* uiLocale = aUILocale; + const PRUnichar* contentLocale = aContentLocale; + nsXPIDLString currentUILocaleName; + nsXPIDLString currentContentLocaleName; + + // When aUILocale == null or aContentLocale == null, set those from default values + // which are from default or from command line options + + // This fallback is for CreateNewProfile() of CreateDefaultProfile() and ProcessArgs() + // Those functions call CreateNewProfile(locale=null). We should consider default values + // or specified values of locales for CreateDefaultProfile() and ProcessArgs(). + + // We can get preferred UILocale and contentLocale (specified -UILocale and -contentLocale) + // by GetSelectedLocale() which is done in nsAppRunner.cpp::InstallGlobalLocale() + + if (!aUILocale || !aUILocale[0]) { + rv = chromeRegistry->GetSelectedLocale(NS_LITERAL_STRING("global").get(), + getter_Copies(currentUILocaleName)); + if (NS_SUCCEEDED(rv)) { + uiLocale = currentUILocaleName.get(); + } } - nsCOMPtr chromeRegistry = do_GetService(kChromeRegistryCID, &rv); - if (NS_SUCCEEDED(rv)) { - nsXPIDLCString pathBuf; - rv = profileDir->GetPath(getter_Copies(pathBuf)); - NS_ENSURE_SUCCESS(rv, rv); - nsFileSpec fileSpec((const char *)pathBuf); - nsFileURL fileURL(fileSpec); - const char* fileStr = fileURL.GetURLString(); - rv = chromeRegistry->SelectLocaleForProfile(langcode, + if (!aContentLocale || !aContentLocale[0]) { + rv = chromeRegistry->GetSelectedLocale(NS_LITERAL_STRING("global-region").get(), + getter_Copies(currentContentLocaleName)); + if (NS_SUCCEEDED(rv)) { + contentLocale = currentContentLocaleName.get(); + } + } + +#if defined(DEBUG_profile_verbose) + nsCAutoString temp1; temp1.AssignWithConversion(uiLocale); + printf(" uiLocale=%s\n", NS_STATIC_CAST(const char*, temp1)); + + nsCAutoString temp2; temp2.AssignWithConversion(contentLocale); + printf(" contentLocale=%s\n", NS_STATIC_CAST(const char*, temp2)); +#endif + + nsXPIDLCString pathBuf; + rv = profileDir->GetPath(getter_Copies(pathBuf)); + NS_ENSURE_SUCCESS(rv, rv); + nsFileSpec fileSpec((const char *)pathBuf); + nsFileURL fileURL(fileSpec); + const char* fileStr = fileURL.GetURLString(); + + if (uiLocale && uiLocale[0]) { + rv = chromeRegistry->SelectLocaleForProfile(uiLocale, NS_ConvertUTF8toUCS2(fileStr).get()); - // Remeber which profile has been created with UI language + // Remember which profile has been created with the UILocale // didn't use gProfileDataAccess because just needed one time - nsCStringKey key((const char *)pathBuf); - gLangProfiles->Put(&key, (void*)PR_TRUE); + if (NS_SUCCEEDED(rv)) { + nsCStringKey key((const char *)pathBuf); + gLocaleProfiles->Put(&key, (void*)PR_TRUE); + } + } + + if (contentLocale && contentLocale[0]) { + // caller prefers locale subdir + nsCOMPtr locProfDefaultsDir; + rv = profDefaultsDir->Clone(getter_AddRefs(locProfDefaultsDir)); + if (NS_FAILED(rv)) return rv; + + locProfDefaultsDir->AppendUnicode(contentLocale); + rv = locProfDefaultsDir->Exists(&exists); + if (NS_SUCCEEDED(rv) && exists) { + profDefaultsDir = locProfDefaultsDir; // transfers ownership +#if defined(DEBUG_profile_verbose) + nsXPIDLString profilePath; + rv = profDefaultsDir->GetUnicodePath(getter_Copies(profilePath)); + if (NS_SUCCEEDED(rv)) { + nsCAutoString temp5; temp5.AssignWithConversion(profilePath); + printf(" profDefaultsDir is set to: %s\n", NS_STATIC_CAST(const char*, temp5)); + } +#endif + } + + rv = chromeRegistry->SelectLocaleForProfile(contentLocale, + NS_ConvertUTF8toUCS2(fileStr).get()); + // Remember which profile has been created with the UILocale + // didn't use gProfileDataAccess because just needed one time + if (NS_SUCCEEDED(rv)) { + nsCStringKey key((const char *)pathBuf); + gLocaleProfiles->Put(&key, (void*)PR_TRUE); + } } } + // Copy contents from defaults folder. rv = profDefaultsDir->Exists(&exists); if (NS_SUCCEEDED(rv) && exists && (!useExistingDir)) @@ -1412,6 +1503,20 @@ nsProfile::CreateNewProfile(const PRUnichar* profileName, } +// Rename a old profile to new profile. +// Copies all the keys from old profile to new profile. + +// Creates a new profile +NS_IMETHODIMP +nsProfile::CreateNewProfile(const PRUnichar* profileName, + const PRUnichar* nativeProfileDir, + const PRUnichar* langcode, + PRBool useExistingDir) +{ + return CreateNewProfileWithLocales(profileName,nativeProfileDir,langcode,nsnull,useExistingDir); +} + + // Rename a old profile to new profile. // Copies all the keys from old profile to new profile. // Deletes the old profile from the registry diff --git a/profile/src/nsProfile.h b/profile/src/nsProfile.h index 78a42a0dbbd..3f9b71dffd7 100644 --- a/profile/src/nsProfile.h +++ b/profile/src/nsProfile.h @@ -75,8 +75,11 @@ private: PRBool mCurrentProfileAvailable; - PRBool mIsLangSpecified; - nsAutoString mLangName; + PRBool mIsUILocaleSpecified; + nsAutoString mUILocaleName; + + PRBool mIsContentLocaleSpecified; + nsAutoString mContentLocaleName; public: nsProfile(); diff --git a/xpfe/bootstrap/nsAppRunner.cpp b/xpfe/bootstrap/nsAppRunner.cpp index 48a7378ef25..f4b669e4b7b 100644 --- a/xpfe/bootstrap/nsAppRunner.cpp +++ b/xpfe/bootstrap/nsAppRunner.cpp @@ -92,6 +92,10 @@ static NS_DEFINE_CID(kWindowMediatorCID, NS_WINDOWMEDIATOR_CID); static NS_DEFINE_CID(kIProcessCID, NS_PROCESS_CID); +static NS_DEFINE_CID(kChromeRegistryCID, NS_CHROMEREGISTRY_CID); + +#define UILOCALE_CMD_LINE_ARG "-UILocale" +#define CONTENTLOCALE_CMD_LINE_ARG "-contentLocale" extern "C" void ShowOSAlert(char* aMessage); @@ -132,6 +136,9 @@ static struct MacInitializer { MacInitializer() { InitializeMacToolbox(); } } gI // Initialize profile services for both standalone and regular profiles static nsresult InitializeProfileService(nsICmdLineService *cmdLineArgs); +// Install global locale if possible +static nsresult InstallGlobalLocale(nsICmdLineService *cmdLineArgs); + class stTSMCloser { public: @@ -769,6 +776,35 @@ static nsresult Ensure1Window( nsICmdLineService* cmdLineArgs) return rv; } +// update global locale if possible (in case when user-*.rdf can be updated) +// so that any apps after this can be invoked in the UILocale and contentLocale +static nsresult InstallGlobalLocale(nsICmdLineService *cmdLineArgs) +{ + nsresult rv = NS_OK; + nsCOMPtr chromeRegistry = do_GetService(kChromeRegistryCID, &rv); + if (NS_SUCCEEDED(rv)) { + nsXPIDLCString cmdUI; + rv = cmdLineArgs->GetCmdLineValue(UILOCALE_CMD_LINE_ARG, getter_Copies(cmdUI)); + if (NS_SUCCEEDED(rv)){ + if (cmdUI) { + nsAutoString UILocaleName; + UILocaleName.AssignWithConversion(cmdUI); + rv = chromeRegistry->SelectLocale(UILocaleName.GetUnicode(), PR_FALSE); + } + } + nsXPIDLCString cmdContent; + rv = cmdLineArgs->GetCmdLineValue(CONTENTLOCALE_CMD_LINE_ARG, getter_Copies(cmdContent)); + if (NS_SUCCEEDED(rv)){ + if (cmdContent) { + nsAutoString ContentLocaleName; + ContentLocaleName.AssignWithConversion(cmdContent); + rv = chromeRegistry->SelectLocale(ContentLocaleName.GetUnicode(), PR_FALSE); + } + } + } + return NS_OK; +} + // Do the righe thing to provide locations depending on whether an // application is standalone or not static nsresult InitializeProfileService(nsICmdLineService *cmdLineArgs) @@ -1000,7 +1036,6 @@ static nsresult main1(int argc, char* argv[], nsISupports *nativeApp ) // _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_CHECK_ALWAYS_DF); #endif - #ifndef XP_MAC // Unbuffer debug output (necessary for automated QA performance scripts). setbuf( stdout, 0 ); @@ -1078,6 +1113,10 @@ static nsresult main1(int argc, char* argv[], nsISupports *nativeApp ) return rv; } + rv = InstallGlobalLocale(cmdLineArgs); + if(NS_FAILED(rv)) + return rv; + nsCOMPtr appShell(do_GetService(kAppShellServiceCID, &rv)); NS_ASSERTION(NS_SUCCEEDED(rv), "failed to get the appshell service"); @@ -1220,7 +1259,8 @@ static void DumpHelp(char *appname) printf("%s-ProfileWizard%sStart with profile wizard.\n",HELP_SPACER_1,HELP_SPACER_2); printf("%s-ProfileManager%sStart with profile manager.\n",HELP_SPACER_1,HELP_SPACER_2); printf("%s-SelectProfile%sStart with profile selection dialog.\n",HELP_SPACER_1,HELP_SPACER_2); - printf("%s-lang %sStart with resources.\n",HELP_SPACER_1,HELP_SPACER_2); + printf("%s-UILocale %sStart with resources as UI Locale.\n",HELP_SPACER_1,HELP_SPACER_2); + printf("%s-contentLocale %sStart with resources as content Locale.\n",HELP_SPACER_1,HELP_SPACER_2); #ifdef XP_WIN32 printf("%s-console%sStart Mozilla with a debugging console.\n",HELP_SPACER_1,HELP_SPACER_2); #endif