/src/libreoffice/svtools/source/misc/langhelp.cxx
Line | Count | Source |
1 | | /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ |
2 | | /* |
3 | | * This file is part of the LibreOffice project. |
4 | | * |
5 | | * This Source Code Form is subject to the terms of the Mozilla Public |
6 | | * License, v. 2.0. If a copy of the MPL was not distributed with this |
7 | | * file, You can obtain one at http://mozilla.org/MPL/2.0/. |
8 | | */ |
9 | | |
10 | | #include <sal/config.h> |
11 | | |
12 | | #include <string_view> |
13 | | |
14 | | #include <comphelper/sequence.hxx> |
15 | | #include <i18nlangtag/languagetag.hxx> |
16 | | #include <i18nlangtag/mslangid.hxx> |
17 | | #include <officecfg/Office/Common.hxx> |
18 | | #include <officecfg/System.hxx> |
19 | | #include <o3tl/string_view.hxx> |
20 | | #include <org/freedesktop/PackageKit/SyncDbusSessionHelper.hpp> |
21 | | #include <rtl/ustring.hxx> |
22 | | #include <svtools/langhelp.hxx> |
23 | | #include <comphelper/diagnose_ex.hxx> |
24 | | #include <vcl/idle.hxx> |
25 | | #include <vcl/svapp.hxx> |
26 | | #include <vcl/settings.hxx> |
27 | | #include <config_langs.h> |
28 | | #include <config_vendor.h> |
29 | | |
30 | | void localizeWebserviceURI( OUString& rURI ) |
31 | 0 | { |
32 | 0 | OUString aLang = Application::GetSettings().GetUILanguageTag().getLanguage(); |
33 | 0 | if ( aLang.equalsIgnoreAsciiCase("pt") |
34 | 0 | && Application::GetSettings().GetUILanguageTag().getCountry().equalsIgnoreAsciiCase("br") ) |
35 | 0 | { |
36 | 0 | aLang = "pt-br"; |
37 | 0 | } |
38 | 0 | if ( aLang.equalsIgnoreAsciiCase("zh") ) |
39 | 0 | { |
40 | 0 | if ( Application::GetSettings().GetUILanguageTag().getCountry().equalsIgnoreAsciiCase("cn") ) |
41 | 0 | aLang = "zh-cn"; |
42 | 0 | if ( Application::GetSettings().GetUILanguageTag().getCountry().equalsIgnoreAsciiCase("tw") ) |
43 | 0 | aLang = "zh-tw"; |
44 | 0 | } |
45 | |
|
46 | 0 | rURI += aLang; |
47 | 0 | } |
48 | | |
49 | | OUString getInstalledLocaleForLanguage(css::uno::Sequence<OUString> const & installed, OUString const & locale) |
50 | 0 | { |
51 | 0 | if (locale.isEmpty()) |
52 | 0 | return OUString(); // do not attempt to resolve anything |
53 | | |
54 | 0 | if (comphelper::findValue(installed, locale) != -1) |
55 | 0 | return locale; |
56 | | |
57 | 0 | std::vector<OUString> fallbacks(LanguageTag(locale).getFallbackStrings(false)); |
58 | 0 | auto pf = std::find_if(fallbacks.begin(), fallbacks.end(), |
59 | 0 | [&installed](const OUString& rf) { return comphelper::findValue(installed, rf) != -1; }); |
60 | 0 | if (pf != fallbacks.end()) |
61 | 0 | return *pf; |
62 | 0 | return OUString(); |
63 | 0 | } |
64 | | |
65 | | static std::unique_ptr<Idle> xLangpackInstaller; |
66 | | |
67 | | namespace { |
68 | | |
69 | | class InstallLangpack : public Idle |
70 | | { |
71 | | std::vector<OUString> m_aPackages; |
72 | | public: |
73 | | explicit InstallLangpack(std::vector<OUString>&& rPackages) |
74 | 0 | : Idle("install langpack") |
75 | 0 | , m_aPackages(std::move(rPackages)) |
76 | 0 | { |
77 | 0 | SetPriority(TaskPriority::LOWEST); |
78 | 0 | } |
79 | | |
80 | | virtual void Invoke() override |
81 | 0 | { |
82 | 0 | vcl::Window* pTopWindow = Application::GetActiveTopWindow(); |
83 | 0 | if (!pTopWindow) |
84 | 0 | pTopWindow = Application::GetFirstTopLevelWindow(); |
85 | 0 | if (!pTopWindow) |
86 | 0 | { |
87 | 0 | Start(); |
88 | 0 | return; |
89 | 0 | } |
90 | 0 | try |
91 | 0 | { |
92 | 0 | using namespace org::freedesktop::PackageKit; |
93 | 0 | css::uno::Reference<XSyncDbusSessionHelper> xSyncDbusSessionHelper(SyncDbusSessionHelper::create(comphelper::getProcessComponentContext())); |
94 | 0 | xSyncDbusSessionHelper->InstallPackageNames(comphelper::containerToSequence(m_aPackages), OUString()); |
95 | 0 | } |
96 | 0 | catch (const css::uno::Exception&) |
97 | 0 | { |
98 | 0 | TOOLS_INFO_EXCEPTION("svl", "trying to install a LibreOffice langpack"); |
99 | 0 | } |
100 | 0 | xLangpackInstaller.reset(); |
101 | 0 | } |
102 | | }; |
103 | | |
104 | | } |
105 | | |
106 | | OUString getInstalledLocaleForSystemUILanguage(const css::uno::Sequence<OUString>& rLocaleElementNames, bool bRequestInstallIfMissing, const OUString& rPreferredLocale) |
107 | 0 | { |
108 | 0 | OUString wantedLocale(rPreferredLocale); |
109 | 0 | if (wantedLocale.isEmpty()) |
110 | 0 | wantedLocale = officecfg::System::L10N::UILocale::get(); |
111 | |
|
112 | 0 | OUString locale = getInstalledLocaleForLanguage(rLocaleElementNames, wantedLocale); |
113 | 0 | if (bRequestInstallIfMissing && locale.isEmpty() && !wantedLocale.isEmpty() && !Application::IsHeadlessModeEnabled() && |
114 | 0 | officecfg::Office::Common::PackageKit::EnableLangpackInstallation::get()) |
115 | 0 | { |
116 | 0 | LanguageTag aWantedTag(wantedLocale); |
117 | 0 | if (aWantedTag.getLanguage() != "en") |
118 | 0 | { |
119 | | // Get the list of langpacks that this build was configured to include |
120 | 0 | std::vector<OUString> aPackages; |
121 | 0 | static constexpr std::u16string_view sAvailableLocales(u"" WITH_LANG); |
122 | 0 | std::vector<OUString> aAvailable; |
123 | 0 | sal_Int32 nIndex = 0; |
124 | 0 | do |
125 | 0 | { |
126 | 0 | aAvailable.emplace_back(o3tl::getToken(sAvailableLocales, 0, ' ', nIndex)); |
127 | 0 | } |
128 | 0 | while (nIndex >= 0); |
129 | | // See which one matches the desired ui locale |
130 | 0 | OUString install = getInstalledLocaleForLanguage(comphelper::containerToSequence(aAvailable), wantedLocale); |
131 | 0 | if (!install.isEmpty() && install != "en-US") |
132 | 0 | { |
133 | 0 | std::string_view sVendor(OOO_VENDOR); |
134 | 0 | if (sVendor == "Red Hat, Inc." || sVendor == "The Fedora Project") |
135 | 0 | { |
136 | | // langpack is the typical Fedora/RHEL naming convention |
137 | 0 | LanguageType eType = aWantedTag.getLanguageType(); |
138 | 0 | if (MsLangId::isSimplifiedChinese(eType)) |
139 | 0 | aPackages.emplace_back("libreoffice-langpack-zh-Hans"); |
140 | 0 | else if (MsLangId::isTraditionalChinese(eType)) |
141 | 0 | aPackages.emplace_back("libreoffice-langpack-zh-Hant"); |
142 | 0 | else if (install == "pt") |
143 | 0 | aPackages.emplace_back("libreoffice-langpack-pt-PT"); |
144 | 0 | else |
145 | 0 | aPackages.emplace_back("libreoffice-langpack-" + install); |
146 | 0 | } |
147 | 0 | else if (sVendor == "The Document Foundation/Debian" || sVendor == "The Document Foundation, Debian and Ubuntu") |
148 | 0 | { |
149 | | // l10n is the typical Debian/Ubuntu naming convention |
150 | 0 | aPackages.emplace_back("libreoffice-l10n-" + install); |
151 | 0 | } |
152 | 0 | } |
153 | 0 | if (!aPackages.empty()) |
154 | 0 | { |
155 | 0 | xLangpackInstaller.reset(new InstallLangpack(std::move(aPackages))); |
156 | 0 | xLangpackInstaller->Start(); |
157 | 0 | } |
158 | 0 | } |
159 | 0 | } |
160 | 0 | if (locale.isEmpty()) |
161 | 0 | locale = getInstalledLocaleForLanguage(rLocaleElementNames, u"en-US"_ustr); |
162 | 0 | if (locale.isEmpty() && rLocaleElementNames.hasElements()) |
163 | 0 | locale = rLocaleElementNames[0]; |
164 | 0 | return locale; |
165 | 0 | } |
166 | | |
167 | | /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |