8#if defined(Q_CC_GNU_ONLY) && Q_CC_GNU >= 1000
10
11
12
13
14
15
16
17QT_WARNING_DISABLE_GCC(
"-Wfree-nonheap-object")
20#if defined(Q_OS_MACOS)
21# include "private/qcore_mac_p.h"
22# include <CoreFoundation/CoreFoundation.h>
25#include "qplatformdefs.h"
30#include "private/qduplicatetracker_p.h"
37#include <private/qtools_p.h>
38#if QT_CONFIG(datetimeparser)
39#include "private/qdatetimeparser_p.h"
47#if QT_CONFIG(timezone)
48# include "qtimezone.h"
50#include "private/qnumeric_p.h"
51#include "private/qtools_p.h"
53#ifndef QT_NO_SYSTEMLOCALE
57# include <qt_windows.h>
61#include "private/qcalendarbackend_p.h"
62#include "private/qgregoriancalendar_p.h"
63#if QT_CONFIG(timezone) && QT_CONFIG(timezone_locale) && !QT_CONFIG(icu)
64# include "private/qtimezonelocale_p.h"
67#include <q20iterator.h>
71constexpr int QLocale::DefaultTwoDigitBaseYear;
73QT_IMPL_METATYPE_EXTERN_TAGGED(QList<Qt::DayOfWeek>, QList_Qt__DayOfWeek)
74#ifndef QT_NO_SYSTEMLOCALE
75QT_IMPL_METATYPE_EXTERN_TAGGED(QSystemLocale::CurrencyToStringArgument,
76 QSystemLocale__CurrencyToStringArgument)
79using namespace Qt::StringLiterals;
80using namespace QtMiscUtils;
82#ifndef QT_NO_SYSTEMLOCALE
83Q_CONSTINIT
static QSystemLocale *_systemLocale =
nullptr;
84Q_CONSTINIT
static QLocaleData systemLocaleData = {};
87static_assert(ascii_isspace(
' '));
88static_assert(ascii_isspace(
'\t'));
89static_assert(ascii_isspace(
'\n'));
90static_assert(ascii_isspace(
'\v'));
91static_assert(ascii_isspace(
'\f'));
92static_assert(ascii_isspace(
'\r'));
93static_assert(!ascii_isspace(
'\0'));
94static_assert(!ascii_isspace(
'\a'));
95static_assert(!ascii_isspace(
'a'));
96static_assert(!ascii_isspace(
'\177'));
97static_assert(!ascii_isspace(uchar(
'\200')));
98static_assert(!ascii_isspace(uchar(
'\xA0')));
99static_assert(!ascii_isspace(uchar(
'\377')));
102
103
105QT_BEGIN_INCLUDE_NAMESPACE
107QT_END_INCLUDE_NAMESPACE
109QLocale::Language QLocalePrivate::codeToLanguage(QStringView code,
110 QLocale::LanguageCodeTypes codeTypes)
noexcept
112 const auto len = code.size();
113 if (len != 2 && len != 3)
114 return QLocale::AnyLanguage;
116 const char16_t uc1 = code[0].toLower().unicode();
117 const char16_t uc2 = code[1].toLower().unicode();
118 const char16_t uc3 = len > 2 ? code[2].toLower().unicode() : 0;
121 if (uc1 > 0x7F || uc2 > 0x7F || uc3 > 0x7F)
122 return QLocale::AnyLanguage;
124 const AlphaCode codeBuf = {
char(uc1),
char(uc2),
char(uc3) };
126 auto searchCode = [codeBuf](
auto f) {
127 return std::find_if(languageCodeList.begin(), languageCodeList.end(),
128 [=](LanguageCodeEntry i) {
return f(i) == codeBuf; });
131 if (codeTypes.testFlag(QLocale::ISO639Part1) && uc3 == 0) {
132 auto i = searchCode([](LanguageCodeEntry i) {
return i.part1; });
133 if (i != languageCodeList.end())
134 return QLocale::Language(std::distance(languageCodeList.begin(), i));
138 if (codeTypes.testFlag(QLocale::ISO639Part2B)) {
139 auto i = searchCode([](LanguageCodeEntry i) {
return i.part2B; });
140 if (i != languageCodeList.end())
141 return QLocale::Language(std::distance(languageCodeList.begin(), i));
146 if (codeTypes.testFlag(QLocale::ISO639Part2T)
147 && !codeTypes.testFlag(QLocale::ISO639Part3)) {
148 auto i = searchCode([](LanguageCodeEntry i) {
return i.part2T; });
149 if (i != languageCodeList.end())
150 return QLocale::Language(std::distance(languageCodeList.begin(), i));
153 if (codeTypes.testFlag(QLocale::ISO639Part3)) {
154 auto i = searchCode([](LanguageCodeEntry i) {
return i.part3; });
155 if (i != languageCodeList.end())
156 return QLocale::Language(std::distance(languageCodeList.begin(), i));
160 if (codeTypes.testFlag(QLocale::LegacyLanguageCode) && uc3 == 0) {
161 constexpr struct LegacyCodes {
163 QLocale::Language language;
165 { {
'n',
'o'}, QLocale::NorwegianBokmal },
166 { {
't',
'l'}, QLocale::Filipino },
167 { {
's',
'h'}, QLocale::Serbian },
168 { {
'm',
'o'}, QLocale::Romanian },
170 { {
'i',
'w'}, QLocale::Hebrew },
171 { {
'i',
'n'}, QLocale::Indonesian },
172 { {
'j',
'i'}, QLocale::Yiddish },
176 for (
const auto &e : legacyCodes) {
177 if (codeBuf == e.code)
181 return QLocale::AnyLanguage;
186 if (code.size() != 4)
191 const unsigned char c0 = (fixCase ? code[0].toUpper() : code[0]).toLatin1();
192 const unsigned char c1 = (fixCase ? code[1].toLower() : code[1]).toLatin1();
193 const unsigned char c2 = (fixCase ? code[2].toLower() : code[2]).toLatin1();
194 const unsigned char c3 = (fixCase ? code[3].toLower() : code[3]).toLatin1();
196 if (!c0 || !c1 || !c2 || !c3)
199 constexpr qsizetype NumScripts = QLocale::LastScript + 1;
202 for (qsizetype i = 0; i < NumScripts; ++i, c += 4) {
203 if (c0 == c[0] && c1 == c[1] && c2 == c[2] && c3 == c[3])
211 qsizetype index = scriptIndex(code, Qt::CaseInsensitive);
212 return index < 0 ? QLocale::AnyScript : QLocale::Script(index);
217 const auto len = code.size();
218 if (len != 2 && len != 3)
219 return QLocale::AnyTerritory;
221 char16_t uc1 = code[0].toUpper().unicode();
222 char16_t uc2 = code[1].toUpper().unicode();
223 char16_t uc3 = len > 2 ? code[2].toUpper().unicode() : 0;
226 for (; *c != 0; c += 3) {
227 if (uc1 == c[0] && uc2 == c[1] && uc3 == c[2])
228 return QLocale::Territory((c - territory_code_list)/3);
231 return QLocale::AnyTerritory;
235 QLocale::LanguageCodeTypes codeTypes)
237 if (language == QLocale::AnyLanguage || language > QLocale::LastLanguage)
239 if (language == QLocale::C)
244 if (codeTypes.testFlag(QLocale::ISO639Part1) && i
.part1.isValid())
247 if (codeTypes.testFlag(QLocale::ISO639Part2B) && i
.part2B.isValid())
250 if (codeTypes.testFlag(QLocale::ISO639Part2T) && i
.part2T.isValid())
253 if (codeTypes.testFlag(QLocale::ISO639Part3))
261 if (script == QLocale::AnyScript || script > QLocale::LastScript)
264 return {
reinterpret_cast<
const char *>(c), 4};
269 if (territory == QLocale::AnyTerritory || territory > QLocale::LastTerritory)
273 return {
reinterpret_cast<
const char*>(c), c[2] == 0 ? 2 : 3};
283bool operator<(LikelyPair lhs, LikelyPair rhs)
287 const auto compare = [](
int lhs,
int rhs) {
289 const int huge = 0x10000;
290 return (lhs ? lhs : huge) - (rhs ? rhs : huge);
292 const auto &left = lhs.key;
293 const auto &right = rhs.key;
295 if (
int cmp = compare(left.language_id, right.language_id))
297 if (
int cmp = compare(left.territory_id, right.territory_id))
299 return compare(left.script_id, right.script_id) < 0;
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
330
331
332
333
334
335
336
337
338
339
340
341
342
344 auto *pairs =
reinterpret_cast<
const LikelyPair *>(
likely_subtags);
346 LikelyPair sought { *
this };
351 pairs =
std::lower_bound(pairs, afterPairs, sought);
354 for (; pairs < afterPairs && pairs->key.language_id ==
language_id; ++pairs) {
371 pairs =
std::lower_bound(pairs, afterPairs, sought);
374 for (; pairs < afterPairs && pairs->key.territory_id ==
territory_id; ++pairs) {
389 sought.key = QLocaleId { 0,
script_id, 0 };
390 pairs =
std::lower_bound(pairs, afterPairs, sought);
391 if (pairs < afterPairs && pairs->key.script_id ==
script_id) {
392 Q_ASSERT(!pairs->key.language_id && !pairs->key.territory_id);
402 pairs = afterPairs - 1;
403 if (pairs->key.matchesAll()) {
442 if (language_id == QLocale::AnyLanguage)
444 if (language_id == QLocale::C)
445 return QByteArrayLiteral(
"C");
446 Q_ASSERT(language_id <= QLocale::LastLanguage);
447 Q_ASSERT(script_id <= QLocale::LastScript);
448 Q_ASSERT(territory_id <= QLocale::LastTerritory);
454 if (language
.part1.isValid()) {
462 const unsigned char *script =
463 (script_id != QLocale::AnyScript ? script_code_list + 4 * script_id :
nullptr);
464 const unsigned char *country =
465 (territory_id != QLocale::AnyTerritory
466 ? territory_code_list + 3 * territory_id :
nullptr);
467 qsizetype len = langLen + (script ? 4 + 1 : 0) + (country ? (country[2] != 0 ? 3 : 2) + 1 : 0);
469 char *uc = name.data();
471 auto langArray = lang.decode();
473 *uc++ = langArray[0];
474 *uc++ = langArray[1];
476 *uc++ = langArray[2];
497 if (m_data->m_language_id == QLocale::AnyLanguage)
499 if (m_data->m_language_id == QLocale::C)
500 return QByteArrayView(
"en") % separator % QByteArrayView(
"POSIX");
507 qsizetype idx = locale_index[localeId.language_id];
510 if (localeId.language_id && idx == 0)
513 Q_ASSERT(localeId.acceptLanguage(locale_data[idx].m_language_id));
516 if (localeId.acceptScriptTerritory(locale_data[idx].id()))
519 }
while (localeId.acceptLanguage(locale_data[idx].m_language_id));
525bool QLocaleData::allLocaleDataRows(
bool (*check)(qsizetype,
const QLocaleData &))
527 for (qsizetype index = 0; index < locale_data_size; ++index) {
528 if (!(*check)(index, locale_data[index]))
538 Q_PRE(index < locale_data_size);
542#if QT_CONFIG(timezone) && QT_CONFIG(timezone_locale) && !QT_CONFIG(icu)
543namespace QtTimeZoneLocale {
546QList<qsizetype> fallbackLocalesFor(qsizetype index)
550 Q_ASSERT(index < locale_data_size);
551 QList<qsizetype> result = {index};
552 QLocaleId id = locale_data[index].id();
553 if (id.language_id == QLocale::C) {
554 id = { QLocale::English, QLocale::LatinScript, QLocale::UnitedStates };
555 qsizetype it = findLocaleIndexById(id);
556 Q_ASSERT_X(it != -1, Q_FUNC_INFO,
"Missing en_Latn_US from locale data");
557 Q_ASSERT_X(it != index,
558 Q_FUNC_INFO,
"en_Latn_US != C");
562 const QLocaleId base = id;
563 QLocaleId likely = id.withLikelySubtagsAdded();
564 if (likely != base) {
565 qsizetype it = findLocaleIndexById(likely);
566 if (it != -1 && !result.contains(it))
569 if (id.territory_id) {
571 likely = id.withLikelySubtagsAdded();
572 if (likely != base) {
573 qsizetype it = findLocaleIndexById(likely);
574 if (it != -1 && !result.contains(it))
580 likely = id.withLikelySubtagsAdded();
581 if (likely != base) {
582 qsizetype it = findLocaleIndexById(likely);
583 if (it != -1 && !result.contains(it))
600 qsizetype index = findLocaleIndexById(likelyId);
604 tried.push_back(likelyId);
606#define CheckCandidate(id) do {
607 if (!tried.contains(id)) {
608 index = findLocaleIndexById(id);
640 return locale_index[fallback];
645 const std::u16string_view v(name.utf16(), size_t(name.size()));
646 const auto i = v.find_first_of(u"_-.@");
647 if (i == std::string_view::npos)
649 return name.first(qsizetype(i));
655 for (QChar uc : tag) {
656 const char16_t ch = uc.unicode();
657 if (!isAsciiLetterOrNumber(ch))
660 return tag.size() > 0;
664 QStringView *lang, QStringView *script, QStringView *land)
noexcept
667 enum ParserState { NoState, LangState, ScriptState, CountryState };
668 ParserState state = LangState;
669 while (name.size() && state != NoState) {
670 const QStringView tag = findTag(name);
673 name = name.sliced(tag.size());
674 const bool sep = name.size() > 0;
676 name = name.sliced(1);
680 if (tag.size() != 2 && tag.size() != 3)
684 state = sep ? ScriptState : NoState;
690 state = sep ? CountryState : NoState;
705 return state != LangState;
713 if (!qt_splitLocaleName(name, &lang, &script, &land))
714 return { QLocale::C, 0, 0 };
717 if (land.compare(
"POSIX", Qt::CaseInsensitive) == 0)
718 return { QLocale::C, 0, 0 };
720 QLocale::Language langId = QLocalePrivate::codeToLanguage(lang);
721 if (langId == QLocale::AnyLanguage)
722 return { QLocale::C, 0, 0 };
723 return { langId, QLocalePrivate::codeToScript(script), QLocalePrivate::codeToTerritory(land) };
730 Q_ASSERT(format.at(i) == u'\'');
732 if (i == format.size())
734 if (format.at(i).unicode() ==
'\'') {
741 while (i < format.size()) {
742 if (format.at(i).unicode() ==
'\'') {
743 if (format.mid(i + 1).startsWith(u'\'')) {
745 result.append(u'\'');
751 result.append(format.at(i++));
754 if (i < format.size())
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
780 const QChar c = s.front();
782 while (j < s.size() && s.at(j) == c)
787Q_CONSTINIT
static const QLocaleData *default_data =
nullptr;
788Q_CONSTINIT QBasicAtomicInt QLocalePrivate::s_generation = Q_BASIC_ATOMIC_INITIALIZER(0);
792 Q_CONSTINIT
static QLocalePrivate c_locale(locale_data, 0, QLocale::OmitGroupSeparator, 1);
798 return forLanguage == QLocale::C ? QLocale::OmitGroupSeparator : QLocale::DefaultNumberOptions;
803 return defaultNumberOptions(QLocale::Language(forLanguage));
806#ifndef QT_NO_SYSTEMLOCALE
808
809
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831QSystemLocale::QSystemLocale() : next(_systemLocale)
833 _systemLocale =
this;
835 systemLocaleData.m_language_id = 0;
839
840
841
842QSystemLocale::~QSystemLocale()
844 if (_systemLocale ==
this) {
845 _systemLocale = next;
848 systemLocaleData.m_language_id = 0;
850 for (QSystemLocale *p = _systemLocale; p; p = p->next) {
860 return _systemLocale;
865 static QSystemLocale globalInstance;
866 return &globalInstance;
874 const QSystemLocale *sys_locale = systemLocale();
877 sys_locale->query(QSystemLocale::LocaleChanged);
880 systemLocaleData = locale_data[sys_locale->fallbackLocaleIndex()];
882 QVariant res = sys_locale->query(QSystemLocale::LanguageId);
884 systemLocaleData.m_language_id = res.toInt();
885 systemLocaleData.m_script_id = QLocale::AnyScript;
887 res = sys_locale->query(QSystemLocale::TerritoryId);
889 systemLocaleData.m_territory_id = res.toInt();
890 systemLocaleData.m_script_id = QLocale::AnyScript;
892 res = sys_locale->query(QSystemLocale::ScriptId);
894 systemLocaleData.m_script_id = res.toInt();
899 if (default_data == &systemLocaleData)
900 QLocalePrivate::s_generation.fetchAndAddRelaxed(1);
906#ifndef QT_NO_SYSTEMLOCALE
908
909
910
911
912
913
914
916 Q_CONSTINIT
static QLocaleId sysId;
917 bool updated =
false;
919 Q_CONSTINIT
static QBasicMutex systemDataMutex;
920 systemDataMutex.lock();
921 if (systemLocaleData.m_language_id == 0) {
922 updateSystemPrivate();
926 if (sysIndex && (updated || *sysIndex < 0)) {
927 const QLocaleId nowId = systemLocaleData.id();
928 if (sysId != nowId || *sysIndex < 0) {
930 *sysIndex = QLocaleData::findLocaleIndex(nowId);
934 systemDataMutex.unlock();
937 return &systemLocaleData;
947 default_data = systemData();
954#ifndef QT_NO_SYSTEMLOCALE
955 if (data == &systemLocaleData) {
958 return QLocaleData::findLocaleIndex(data->id());
969 Q_ASSERT(locale_index[QLocale::C] == 0);
973#ifndef QT_NO_DATASTREAM
974QDataStream &operator<<(QDataStream &ds,
const QLocale &l)
980QDataStream &
operator>>(QDataStream &ds, QLocale &l)
990 new QLocalePrivate(defaultData(), defaultIndex(),
991 defaultNumberOptions(defaultData()->m_language_id)))
997 const qsizetype index = QLocaleData::findLocaleIndex(QLocaleId::fromName(name));
998 return new QLocalePrivate(QLocaleData::dataForLocaleIndex(index), index,
999 defaultNumberOptions(locale_data[index].m_language_id));
1003 QLocale::Territory territory)
1005 if (language == QLocale::C)
1008 qsizetype index = QLocaleData::findLocaleIndex(QLocaleId { language, script, territory });
1009 const QLocaleData *data = QLocaleData::dataForLocaleIndex(index);
1011 QLocale::NumberOptions numberOptions = QLocale::DefaultNumberOptions;
1014 if (data->m_language_id == QLocale::C) {
1015 if (defaultLocalePrivate.exists())
1016 numberOptions = defaultLocalePrivate->data()->m_numberOptions;
1018 index = defaultIndex();
1026 auto compareWithPrivate = [&loc](
const QLocaleData *data, QLocale::NumberOptions opts)
1028 return loc.d->m_data == data && loc.d->m_numberOptions == opts;
1031 if (lang == QLocale::C)
1034 qsizetype index = QLocaleData::findLocaleIndex(QLocaleId { lang });
1035 const QLocaleData *data = QLocaleData::dataForLocaleIndex(index);
1037 QLocale::NumberOptions numberOptions = QLocale::DefaultNumberOptions;
1040 if (data->m_language_id == QLocale::C) {
1041 if (defaultLocalePrivate.exists())
1042 numberOptions = defaultLocalePrivate->data()->m_numberOptions;
1045 return compareWithPrivate(data, numberOptions);
1048static std::optional<QString>
1051#ifndef QT_NO_SYSTEMLOCALE
1052 if (that != &systemLocaleData)
1053 return std::nullopt;
1055 QVariant v = systemLocale()->query(type);
1056 if (v.metaType() != QMetaType::fromType<QString>())
1057 return std::nullopt;
1059 return v.toString();
1063 return std::nullopt;
1070 if (
auto opt = systemLocaleString(that, type))
1077 return localeString(
this, QSystemLocale::DecimalPoint, decimalSeparator());
1082 return localeString(
this, QSystemLocale::GroupSeparator, groupDelim());
1097 return localeString(
this, QSystemLocale::ZeroDigit, zero());
1102#ifndef QT_NO_SYSTEMLOCALE
1103 if (
this == &systemLocaleData) {
1104 const auto text = systemLocale()->query(QSystemLocale::ZeroDigit).toString();
1105 if (!text.isEmpty()) {
1106 if (text.size() == 1 && !text.at(0).isSurrogate())
1107 return text.at(0).unicode();
1108 if (text.size() == 2 && text.at(0).isHighSurrogate())
1109 return QChar::surrogateToUcs4(text.at(0), text.at(1));
1118 return localeString(
this, QSystemLocale::NegativeSign, minus());
1123 return localeString(
this, QSystemLocale::PositiveSign, plus());
1133#ifndef QT_NO_SYSTEMLOCALE
1134 if (
this == &systemLocaleData) {
1135 QVariant queryResult = systemLocale()->query(QSystemLocale::Grouping);
1136 if (!queryResult.isNull()) {
1139 if (sysGroupSizes.first <= 0)
1140 sysGroupSizes.first = m_grouping_first;
1141 if (sysGroupSizes.higher <= 0)
1142 sysGroupSizes.higher = m_grouping_higher;
1143 if (sysGroupSizes.least <= 0)
1144 sysGroupSizes.least = m_grouping_least;
1145 return sysGroupSizes;
1149 return { m_grouping_first,
1155
1156
1157QLocale::QLocale(QLocalePrivate &dd)
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208QLocale::QLocale(QStringView name)
1209 : d(localePrivateByName(name))
1214
1215
1216
1219
1220
1221
1222
1223
1224
1225
1230 if (!defaultLocalePrivate.isDestroyed()) {
1233 d = *defaultLocalePrivate;
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1249QLocale::QLocale(Language language, Territory territory)
1250 : d(findLocalePrivate(language, AnyScript, territory))
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1273QLocale::QLocale(Language language, Script script, Territory territory)
1274 : d(findLocalePrivate(language, script, territory))
1279
1280
1282QLocale::QLocale(
const QLocale &other)
noexcept =
default;
1285
1286
1293
1294
1295
1297QLocale &QLocale::operator=(
const QLocale &other)
noexcept =
default;
1300
1301
1302
1304bool QLocale::equals(
const QLocale &other)
const noexcept
1306 return d->m_data == other.d->m_data && d->m_numberOptions == other.d->m_numberOptions;
1310
1311
1312
1313
1316
1317
1318
1321 return qHashMulti(seed, key.d->m_data, key.d->m_numberOptions);
1325
1326
1327
1328
1329
1330
1331void QLocale::setNumberOptions(NumberOptions options)
1333 d->m_numberOptions = options;
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346QLocale::NumberOptions QLocale::numberOptions()
const
1348 return d->m_numberOptions;
1352
1353
1354
1355
1356
1357
1358
1361
1362
1363
1364
1365QString QLocale::quoteString(QStringView str, QuotationStyle style)
const
1367#ifndef QT_NO_SYSTEMLOCALE
1368 if (d->m_data == &systemLocaleData) {
1370 if (style == AlternateQuotation)
1371 res = systemLocale()->query(QSystemLocale::StringToAlternateQuotation,
1372 QVariant::fromValue(str));
1373 if (res.isNull() || style == StandardQuotation)
1374 res = systemLocale()->query(QSystemLocale::StringToStandardQuotation,
1375 QVariant::fromValue(str));
1377 return res.toString();
1381 QLocaleData::DataRange start, end;
1382 if (style == StandardQuotation) {
1383 start = d->m_data->quoteStart();
1384 end = d->m_data->quoteEnd();
1386 start = d->m_data->quoteStartAlternate();
1387 end = d->m_data->quoteEndAlternate();
1390 return start.viewData(single_character_data) % str % end.viewData(single_character_data);
1394
1395
1396
1397
1398
1399QString QLocale::createSeparatedList(
const QStringList &list)
const
1402#ifndef QT_NO_SYSTEMLOCALE
1403 if (d->m_data == &systemLocaleData) {
1405 systemLocale()->query(QSystemLocale::ListToSeparatedString, QVariant::fromValue(list));
1408 return res.toString();
1412 const qsizetype size = list.size();
1420 return d->m_data->pairListPattern().getData(
1421 list_pattern_part_data).arg(list.at(0), list.at(1));
1423 QStringView formatStart = d->m_data->startListPattern().viewData(list_pattern_part_data);
1424 QStringView formatMid = d->m_data->midListPattern().viewData(list_pattern_part_data);
1425 QStringView formatEnd = d->m_data->endListPattern().viewData(list_pattern_part_data);
1426 QString result = formatStart.arg(list.at(0), list.at(1));
1427 for (qsizetype i = 2; i < size - 1; ++i)
1428 result = formatMid.arg(result, list.at(i));
1429 result = formatEnd.arg(result, list.at(size - 1));
1434
1435
1436
1437
1438
1439
1440
1441
1442
1443
1444
1445
1447void QLocale::setDefault(
const QLocale &locale)
1449 default_data = locale.d->m_data;
1451 if (defaultLocalePrivate.isDestroyed())
1453 if (!defaultLocalePrivate.exists()) {
1456 Q_ASSERT(defaultLocalePrivate.exists());
1460 *defaultLocalePrivate = locale.d;
1461 QLocalePrivate::s_generation.fetchAndAddRelaxed(1);
1465
1466
1467
1468
1469QLocale::Language QLocale::language()
const
1471 return Language(d->languageId());
1475
1476
1477
1478
1479
1480
1481QLocale::Script QLocale::script()
const
1483 return Script(d->m_data->m_script_id);
1487
1488
1489
1490
1491
1492
1493QLocale::Territory QLocale::territory()
const
1495 return Territory(d->territoryId());
1498#if QT_DEPRECATED_SINCE(6
, 6
)
1500
1501
1502
1503
1504
1505
1506QLocale::Country QLocale::country()
const
1513
1514
1515
1516
1517
1518
1519
1520
1521
1522
1523
1524
1525
1526
1527
1528
1529
1530
1531
1532
1533
1534
1535
1536
1540 qWarning(
"QLocale::%s(): Using non-ASCII separator '%c' (%02x) is unsupported",
1541 method, sep, uint(uchar(sep)));
1545
1546
1547
1548
1549
1550
1551
1552
1553
1554
1555
1556
1557
1558
1559
1560
1561
1562
1564QString QLocale::name(TagSeparator separator)
const
1566 const char sep =
char(separator);
1567 if (uchar(sep) > 0x7f) {
1568 badSeparatorWarning(
"name", sep);
1571 const auto code = d->languageCode();
1572 QLatin1StringView view{code.data()};
1574 Language l = language();
1578 Territory c = territory();
1579 if (c == AnyTerritory)
1582 return view + QLatin1Char(sep) + d->territoryCode();
1585template <
typename T>
static inline
1588 constexpr bool isUnsigned =
std::is_unsigned_v<T>;
1589 using Int64 =
typename std::conditional_t<isUnsigned, quint64, qint64>;
1591 QSimpleParsedNumber<Int64> r{};
1592 if constexpr (isUnsigned)
1593 r = d
->m_data->stringToUnsLongLong(str, 10, d->m_numberOptions);
1595 r = d
->m_data->stringToLongLong(str, 10, d->m_numberOptions);
1600 Int64 val = r.result;
1601 if (T(val) != val) {
1611
1612
1613
1614
1615
1616
1617
1618
1619
1620
1621
1622
1623
1624
1625
1626
1627
1628
1629
1630
1631
1632
1633
1634QString QLocale::bcp47Name(TagSeparator separator)
const
1636 const char sep =
char(separator);
1637 if (uchar(sep) > 0x7f) {
1638 badSeparatorWarning(
"bcp47Name", sep);
1641 return QString::fromLatin1(d->bcp47Name(sep));
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662QString QLocale::languageToCode(Language language, LanguageCodeTypes codeTypes)
1664 const auto code = QLocalePrivate::languageToCode(language, codeTypes);
1665 return QLatin1StringView{code.data()};
1669
1670
1671
1672
1673
1674
1675
1676
1677
1678
1679
1680
1681
1682QLocale::Language QLocale::codeToLanguage(QStringView languageCode,
1683 LanguageCodeTypes codeTypes)
noexcept
1685 return QLocalePrivate::codeToLanguage(languageCode, codeTypes);
1689
1690
1691
1692
1693
1694
1695
1696
1697
1698QString QLocale::territoryToCode(QLocale::Territory territory)
1700 return QLocalePrivate::territoryToCode(territory);
1704
1705
1706
1707
1708
1709
1710
1711
1712
1713QLocale::Territory QLocale::codeToTerritory(QStringView territoryCode)
noexcept
1715 return QLocalePrivate::codeToTerritory(territoryCode);
1718#if QT_DEPRECATED_SINCE(6
, 6
)
1720
1721
1722
1723
1724
1725
1726
1727
1728
1729QString QLocale::countryToCode(Country country)
1731 return territoryToCode(country);
1735
1736
1737
1738
1739
1740
1741
1742
1743
1744QLocale::Country QLocale::codeToCountry(QStringView countryCode)
noexcept
1746 return QLocalePrivate::codeToTerritory(countryCode);
1751
1752
1753
1754
1755
1756
1757
1758
1759QString QLocale::scriptToCode(Script script)
1761 return QLocalePrivate::scriptToCode(script);
1765
1766
1767
1768
1769
1770
1771
1772
1773QLocale::Script QLocale::codeToScript(QStringView scriptCode)
noexcept
1775 return QLocalePrivate::codeToScript(scriptCode);
1779
1780
1781
1782
1784QString QLocale::languageToString(Language language)
1786 if (language > LastLanguage)
1787 return "Unknown"_L1;
1788 return QString::fromUtf8(language_name_list + language_name_index[language]);
1792
1793
1794
1795
1796
1797
1798QString QLocale::territoryToString(Territory territory)
1800 if (territory > LastTerritory)
1801 return "Unknown"_L1;
1802 return QString::fromUtf8(territory_name_list + territory_name_index[territory]);
1805#if QT_DEPRECATED_SINCE(6
, 6
)
1807
1808
1809
1810
1811
1812
1813QString QLocale::countryToString(Country country)
1815 return territoryToString(country);
1820
1821
1822
1823
1824
1825
1826QString QLocale::scriptToString(Script script)
1828 if (script > LastScript)
1829 return "Unknown"_L1;
1830 return QString::fromUtf8(script_name_list + script_name_index[script]);
1834
1835
1836
1837
1838
1839
1840
1841
1842
1843
1844
1845
1846
1849
1850
1851
1852
1853
1854
1855
1856
1857
1858
1859
1860
1861
1864
1865
1866
1867
1868
1869
1870
1871
1872
1873
1874
1875
1878
1879
1880
1881
1882
1883
1884
1885
1886
1887
1888
1889
1892
1893
1894
1895
1896
1897
1898
1899
1900
1901
1902
1903
1904
1905
1908
1909
1910
1911
1912
1913
1914
1915
1916
1917
1918
1919
1920
1921
1922
1925
1926
1927
1928
1929
1930
1931
1932
1933
1934
1935
1936
1939
1940
1941
1942
1943
1944
1945
1946
1947
1948
1949
1950
1951
1952
1955
1956
1957
1958
1959
1960
1961
1962
1963
1964
1965
1966
1967
1968
1971
1972
1973
1974
1975
1976
1977
1978
1979
1980
1981
1982
1983
1984
1985
1986
1987
1988
1991
1992
1993
1994
1995
1996
1997
1998
1999
2000
2001
2002
2003
2005short QLocale::toShort(QStringView s,
bool *ok)
const
2007 return toIntegral_helper<
short>(d, s, ok);
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2025ushort QLocale::toUShort(QStringView s,
bool *ok)
const
2027 return toIntegral_helper<ushort>(d, s, ok);
2031
2032
2033
2034
2035
2036
2037
2038
2039
2040
2041
2042
2043
2045int QLocale::toInt(QStringView s,
bool *ok)
const
2047 return toIntegral_helper<
int>(d, s, ok);
2051
2052
2053
2054
2055
2056
2057
2058
2059
2060
2061
2062
2063
2065uint QLocale::toUInt(QStringView s,
bool *ok)
const
2067 return toIntegral_helper<uint>(d, s, ok);
2071
2072
2073
2074
2075
2076
2077
2078
2079
2080
2081
2082
2084long QLocale::toLong(QStringView s,
bool *ok)
const
2086 return toIntegral_helper<
long>(d, s, ok);
2090
2091
2092
2093
2094
2095
2096
2097
2098
2099
2100
2101
2102
2104ulong QLocale::toULong(QStringView s,
bool *ok)
const
2106 return toIntegral_helper<ulong>(d, s, ok);
2110
2111
2112
2113
2114
2115
2116
2117
2118
2119
2120
2121
2122
2125qlonglong QLocale::toLongLong(QStringView s,
bool *ok)
const
2127 return toIntegral_helper<qlonglong>(d, s, ok);
2131
2132
2133
2134
2135
2136
2137
2138
2139
2140
2141
2142
2143
2144
2146qulonglong QLocale::toULongLong(QStringView s,
bool *ok)
const
2148 return toIntegral_helper<qulonglong>(d, s, ok);
2152
2153
2154
2155
2156
2157
2158
2159
2160
2161
2162
2163
2164
2165
2167float QLocale::toFloat(QStringView s,
bool *ok)
const
2169 return QLocaleData::convertDoubleToFloat(toDouble(s, ok), ok);
2173
2174
2175
2176
2177
2178
2179
2180
2181
2182
2183
2184
2185
2186
2187
2188
2189
2190
2191
2193double QLocale::toDouble(QStringView s,
bool *ok)
const
2195 return d->m_data->stringToDouble(s, ok, d->m_numberOptions);
2199
2200
2201
2202
2204QString QLocale::toString(qlonglong i)
const
2206 int flags = (d->m_numberOptions & OmitGroupSeparator
2207 ? 0 : QLocaleData::GroupDigits);
2209 return d->m_data->longLongToString(i, -1, 10, -1, flags);
2213
2214
2215
2216
2218QString QLocale::toString(qulonglong i)
const
2220 int flags = (d->m_numberOptions & OmitGroupSeparator
2221 ? 0 : QLocaleData::GroupDigits);
2223 return d->m_data->unsLongLongToString(i, -1, 10, -1, flags);
2229 qsizetype count = 0;
2232 [[maybe_unused]]
auto ch = counter
.next();
2238 const QLocale &locale)
2241 if (!(locale.numberOptions() & QLocale::OmitGroupSeparator))
2245 else if (fillChar == U'0')
2257 if (fillChar == U'0') {
2258 Q_ASSERT(fieldWidth < 0);
2259 filler = localeData->zeroDigit();
2261 filler = QString(QChar::fromUcs4(fillChar));
2265 filler = filler.repeated(padding);
2270
2271
2272
2273
2274
2275
2277
2278
2279
2280
2281
2282
2283
2284
2285
2286
2287
2288
2289
2290
2291
2292
2293
2294
2295QString QLocale::toString(qlonglong number,
int fieldWidth,
char32_t fillChar)
const
2297 int absFieldWidth = qAbs(fieldWidth);
2298 int width = (fillChar == U'0') ? absFieldWidth : -1;
2299 unsigned flags = calculateFlags(fieldWidth, fillChar, *
this);
2301 QString result = d->m_data->longLongToString(number, -1, 10, width, flags);
2302 qsizetype padding = absFieldWidth - stringWidth(result);
2305 QString filler = calculateFiller(padding, fillChar, fieldWidth, d->m_data);
2307 result.append(filler);
2309 result.prepend(filler);
2315
2316
2317
2318
2319
2320
2322
2323
2324
2325QString QLocale::toString(qulonglong number,
int fieldWidth,
char32_t fillChar)
const
2327 int absFieldWidth = qAbs(fieldWidth);
2328 int width = (fillChar == U'0') ? absFieldWidth : -1;
2329 unsigned flags = calculateFlags(fieldWidth, fillChar, *
this);
2331 QString result = d->m_data->unsLongLongToString(number, -1, 10, width, flags);
2332 qsizetype padding = absFieldWidth - stringWidth(result);
2335 QString filler = calculateFiller(padding, fillChar, fieldWidth, d->m_data);
2337 result.append(filler);
2339 result.prepend(filler);
2345
2346
2347
2348
2349
2350
2352QString QLocale::toString(QDate date,
const QString &format)
const
2354 return toString(date, qToStringViewIgnoringNull(format));
2358
2359
2360
2361
2362
2363
2365QString QLocale::toString(QTime time,
const QString &format)
const
2367 return toString(time, qToStringViewIgnoringNull(format));
2371
2372
2373
2374
2375
2376
2377
2378
2379
2382
2383
2384
2385
2386
2387
2388
2389
2390QString QLocale::toString(QDate date, QStringView format, QCalendar cal)
const
2392 return cal.dateTimeToString(format, QDateTime(), date, QTime(), *
this);
2396
2397
2398
2399QString QLocale::toString(QDate date, QStringView format)
const
2401 return QCalendar().dateTimeToString(format, QDateTime(), date, QTime(), *
this);
2405
2406
2407
2408
2409
2410
2411
2412
2413
2414QString QLocale::toString(QDate date, FormatType format, QCalendar cal)
const
2416 if (!date.isValid())
2419#ifndef QT_NO_SYSTEMLOCALE
2420 if (cal.isGregorian() && d->m_data == &systemLocaleData) {
2421 QVariant res = systemLocale()->query(format == LongFormat
2422 ? QSystemLocale::DateToStringLong
2423 : QSystemLocale::DateToStringShort,
2426 return res.toString();
2430 QString format_str = dateFormat(format);
2431 return toString(date, format_str, cal);
2435
2436
2437
2438QString QLocale::toString(QDate date, FormatType format)
const
2440 if (!date.isValid())
2443#ifndef QT_NO_SYSTEMLOCALE
2444 if (d->m_data == &systemLocaleData) {
2445 QVariant res = systemLocale()->query(format == LongFormat
2446 ? QSystemLocale::DateToStringLong
2447 : QSystemLocale::DateToStringShort,
2450 return res.toString();
2454 QString format_str = dateFormat(format);
2455 return toString(date, format_str);
2461 while (i < format.size()) {
2462 if (format.at(i).unicode() ==
'\'') {
2463 qt_readEscapedFormatString(format, &i);
2467 if (format.at(i).toLower().unicode() ==
'a')
2476
2477
2478
2479
2480
2481
2482
2483
2484QString QLocale::toString(QTime time, QStringView format)
const
2486 return QCalendar().dateTimeToString(format, QDateTime(), QDate(), time, *
this);
2490
2491
2492
2493
2494
2495
2496
2497
2498QString QLocale::toString(
const QDateTime &dateTime, QStringView format, QCalendar cal)
const
2500 return cal.dateTimeToString(format, dateTime, QDate(), QTime(), *
this);
2504
2505
2506
2507QString QLocale::toString(
const QDateTime &dateTime, QStringView format)
const
2509 return QCalendar().dateTimeToString(format, dateTime, QDate(), QTime(), *
this);
2513
2514
2515
2516
2517
2518
2519
2520
2521
2522QString QLocale::toString(
const QDateTime &dateTime, FormatType format, QCalendar cal)
const
2524 if (!dateTime.isValid())
2527#ifndef QT_NO_SYSTEMLOCALE
2528 if (cal.isGregorian() && d->m_data == &systemLocaleData) {
2529 QVariant res = systemLocale()->query(format == LongFormat
2530 ? QSystemLocale::DateTimeToStringLong
2531 : QSystemLocale::DateTimeToStringShort,
2534 return res.toString();
2538 const QString format_str = dateTimeFormat(format);
2539 return toString(dateTime, format_str, cal);
2543
2544
2545
2546QString QLocale::toString(
const QDateTime &dateTime, FormatType format)
const
2548 if (!dateTime.isValid())
2551#ifndef QT_NO_SYSTEMLOCALE
2552 if (d->m_data == &systemLocaleData) {
2553 QVariant res = systemLocale()->query(format == LongFormat
2554 ? QSystemLocale::DateTimeToStringLong
2555 : QSystemLocale::DateTimeToStringShort,
2558 return res.toString();
2562 const QString format_str = dateTimeFormat(format);
2563 return toString(dateTime, format_str);
2568
2569
2570
2572QString QLocale::toString(QTime time, FormatType format)
const
2574 if (!time.isValid())
2577#ifndef QT_NO_SYSTEMLOCALE
2578 if (d->m_data == &systemLocaleData) {
2579 QVariant res = systemLocale()->query(format == LongFormat
2580 ? QSystemLocale::TimeToStringLong
2581 : QSystemLocale::TimeToStringShort,
2584 return res.toString();
2588 QString format_str = timeFormat(format);
2589 return toString(time, format_str);
2593
2594
2595
2596
2597
2598
2599
2600
2601
2602
2604QString QLocale::dateFormat(FormatType format)
const
2606#ifndef QT_NO_SYSTEMLOCALE
2607 if (d->m_data == &systemLocaleData) {
2608 QVariant res = systemLocale()->query(format == LongFormat
2609 ? QSystemLocale::DateFormatLong
2610 : QSystemLocale::DateFormatShort,
2613 return res.toString();
2617 return (format == LongFormat
2618 ? d->m_data->longDateFormat()
2619 : d->m_data->shortDateFormat()
2620 ).getData(date_format_data);
2624
2625
2626
2627
2628
2629
2630
2631
2632
2633
2635QString QLocale::timeFormat(FormatType format)
const
2637#ifndef QT_NO_SYSTEMLOCALE
2638 if (d->m_data == &systemLocaleData) {
2639 QVariant res = systemLocale()->query(format == LongFormat
2640 ? QSystemLocale::TimeFormatLong
2641 : QSystemLocale::TimeFormatShort,
2644 return res.toString();
2648 return (format == LongFormat
2649 ? d->m_data->longTimeFormat()
2650 : d->m_data->shortTimeFormat()
2651 ).getData(time_format_data);
2655
2656
2657
2658
2659
2660
2661
2662
2663
2664
2666QString QLocale::dateTimeFormat(FormatType format)
const
2668#ifndef QT_NO_SYSTEMLOCALE
2669 if (d->m_data == &systemLocaleData) {
2670 QVariant res = systemLocale()->query(format == LongFormat
2671 ? QSystemLocale::DateTimeFormatLong
2672 : QSystemLocale::DateTimeFormatShort,
2674 if (!res.isNull()) {
2675 return res.toString();
2679 return dateFormat(format) + u' ' + timeFormat(format);
2682#if QT_CONFIG(datestring)
2684
2685
2686
2687
2688
2689
2690
2691
2692
2693
2694
2695
2696
2697
2698QTime QLocale::toTime(
const QString &string, FormatType format)
const
2700 return toTime(string, timeFormat(format));
2704
2705
2706
2707
2708
2709
2710
2711
2712
2713
2714
2715
2716
2717
2718
2719
2720
2721
2722
2723
2724
2725
2726
2727
2728QDate QLocale::toDate(
const QString &string, FormatType format,
int baseYear)
const
2730 return toDate(string, dateFormat(format), baseYear);
2734
2735
2736
2737QDate QLocale::toDate(
const QString &string, FormatType format, QCalendar cal,
int baseYear)
const
2739 return toDate(string, dateFormat(format), cal, baseYear);
2743
2744
2745
2746
2747
2748
2749
2750
2751
2752
2753
2754
2755
2756
2757
2758
2759
2760
2761QDateTime QLocale::toDateTime(
const QString &string, FormatType format,
int baseYear)
const
2763 return toDateTime(string, dateTimeFormat(format), baseYear);
2767
2768
2769
2770QDateTime QLocale::toDateTime(
const QString &string, FormatType format, QCalendar cal,
2773 return toDateTime(string, dateTimeFormat(format), cal, baseYear);
2777
2778
2779
2780
2781
2782
2783
2784
2785
2786
2787
2788
2789
2790
2791QTime QLocale::toTime(
const QString &string,
const QString &format)
const
2794#if QT_CONFIG(datetimeparser)
2795 QDateTimeParser dt(QMetaType::QTime, QDateTimeParser::FromString, QCalendar());
2796 dt.setDefaultLocale(*
this);
2797 if (dt.parseFormat(format))
2798 dt.fromString(string,
nullptr, &time);
2807
2808
2809
2810
2811
2812
2813
2814
2815
2816
2817
2818
2819
2820
2821
2822
2823
2824
2825
2826
2827
2828
2829
2830
2831QDate QLocale::toDate(
const QString &string,
const QString &format,
int baseYear)
const
2833 return toDate(string, format, QCalendar(), baseYear);
2837
2838
2839
2840QDate QLocale::toDate(
const QString &string,
const QString &format, QCalendar cal,
int baseYear)
const
2843#if QT_CONFIG(datetimeparser)
2844 QDateTimeParser dt(QMetaType::QDate, QDateTimeParser::FromString, cal);
2845 dt.setDefaultLocale(*
this);
2846 if (dt.parseFormat(format))
2847 dt.fromString(string, &date,
nullptr, baseYear);
2858
2859
2860
2861
2862
2863
2864
2865
2866
2867
2868
2869
2870
2871
2872
2873
2874
2875
2876
2877
2878
2879
2880QDateTime QLocale::toDateTime(
const QString &string,
const QString &format,
int baseYear)
const
2882 return toDateTime(string, format, QCalendar(), baseYear);
2886
2887
2888
2889QDateTime QLocale::toDateTime(
const QString &string,
const QString &format, QCalendar cal,
2892#if QT_CONFIG(datetimeparser)
2895 QDateTimeParser dt(QMetaType::QDateTime, QDateTimeParser::FromString, cal);
2896 dt.setDefaultLocale(*
this);
2897 if (dt.parseFormat(format) && (dt.fromString(string, &datetime, baseYear)
2898 || !datetime.isValid())) {
2912
2913
2914
2915
2916
2917
2918
2919
2920
2921
2922
2923
2924
2925QString QLocale::decimalPoint()
const
2927 return d->m_data->decimalPoint();
2931
2932
2933
2934
2935
2936
2937
2938
2939
2940
2941
2942
2943
2944QString QLocale::groupSeparator()
const
2946 return d->m_data->groupSeparator();
2950
2951
2952
2953
2954
2955
2956
2957
2958
2959
2960
2961QString QLocale::percent()
const
2963 return d->m_data->percentSign();
2967
2968
2969
2970
2971
2972
2973
2974
2975
2976
2977
2978
2979
2980QString QLocale::zeroDigit()
const
2982 return d->m_data->zeroDigit();
2986
2987
2988
2989
2990
2991
2992
2993
2994
2995
2996
2997QString QLocale::negativeSign()
const
2999 return d->m_data->negativeSign();
3003
3004
3005
3006
3007
3008
3009
3010
3011
3012
3013
3014QString QLocale::positiveSign()
const
3016 return d->m_data->positiveSign();
3020
3021
3022
3023
3024
3025
3026
3027
3028
3029
3030
3031
3032QString QLocale::exponential()
const
3034 return d->m_data->exponentSeparator();
3038
3039
3040
3041
3042
3043
3044
3045
3046
3047
3048
3049
3050
3051
3052
3053
3054
3055
3056
3057
3058
3059
3060
3061
3062
3063
3064
3065
3066
3067
3068
3069
3071QString QLocale::toString(
double f,
char format,
int precision)
const
3073 QLocaleData::DoubleForm form = QLocaleData::DFDecimal;
3074 uint flags = isAsciiUpper(format) ? QLocaleData::CapitalEorX : 0;
3076 switch (QtMiscUtils::toAsciiLower(format)) {
3078 form = QLocaleData::DFDecimal;
3081 form = QLocaleData::DFExponent;
3084 form = QLocaleData::DFSignificantDigits;
3090 if (!(d->m_numberOptions & OmitGroupSeparator))
3091 flags |= QLocaleData::GroupDigits;
3092 if (!(d->m_numberOptions & OmitLeadingZeroInExponent))
3093 flags |= QLocaleData::ZeroPadExponent;
3094 if (d->m_numberOptions & IncludeTrailingZeroesAfterDot)
3095 flags |= QLocaleData::AddTrailingZeroes;
3096 return d->m_data->doubleToString(f, precision, form, -1, flags);
3100
3101
3102
3103
3104
3105
3106
3107
3108
3109
3110
3111
3112
3113
3114
3115QLocale QLocale::c()
noexcept
3117 return QLocale(*c_private());
3121
3122
3123
3124
3125
3126
3127
3128
3129
3130
3131
3132
3134QLocale QLocale::system()
3136 constexpr auto sysData = []() {
3138#ifdef QT_NO_SYSTEMLOCALE
3141 return &systemLocaleData;
3144 Q_CONSTINIT
static QLocalePrivate locale(sysData(), -1, DefaultNumberOptions, 1);
3147 systemData(&locale.m_index);
3148 Q_ASSERT(locale.m_index >= 0 && locale.m_index < locale_data_size);
3149 locale.m_numberOptions = defaultNumberOptions(locale.m_data->m_language_id);
3151 return QLocale(locale);
3155
3156
3157
3158
3159
3160
3161
3162
3163
3164
3165
3166QList<QLocale> QLocale::matchingLocales(Language language, Script script, Territory territory)
3168 QList<QLocale> result;
3170 const QLocaleId filter { language, script, territory };
3171 if (!filter.isValid())
3174 if (language == C) {
3175 result.emplace_back(C);
3179 if (filter.matchesAll())
3180 result.reserve(locale_data_size);
3182 quint16 index = locale_index[language];
3184 while (index < locale_data_size
3185 && filter.acceptLanguage(locale_data[index].m_language_id)) {
3186 const QLocaleId id = locale_data[index].id();
3187 if (filter.acceptScriptTerritory(id)) {
3188 result.append(QLocale(*(id.language_id == C ? c_private()
3189 :
new QLocalePrivate(locale_data + index, index))));
3195 const auto syslocaledata = systemData();
3197 if (filter.acceptLanguage(syslocaledata->m_language_id)) {
3198 const QLocaleId id = syslocaledata->id();
3199 if (filter.acceptScriptTerritory(id))
3200 result.append(system());
3206#if QT_DEPRECATED_SINCE(6
, 6
)
3208
3209
3210
3211
3212
3213
3214
3215
3216
3217QList<QLocale::Country> QLocale::countriesForLanguage(Language language)
3219 const auto locales = matchingLocales(language, AnyScript, AnyCountry);
3220 QList<Country> result;
3221 result.reserve(locales.size());
3222 for (
const auto &locale : locales)
3223 result.append(locale.territory());
3229
3230
3231
3232
3233
3234
3235
3236
3237
3238
3239
3240QString QLocale::monthName(
int month, FormatType type)
const
3242 return QCalendar().monthName(*
this, month, QCalendar::Unspecified, type);
3246
3247
3248
3249
3250
3251
3252
3253
3254
3255
3256QString QLocale::standaloneMonthName(
int month, FormatType type)
const
3258 return QCalendar().standaloneMonthName(*
this, month, QCalendar::Unspecified, type);
3262
3263
3264
3265
3266
3267
3268
3269
3270
3271
3272
3273
3274QString QLocale::dayName(
int day, FormatType type)
const
3276 return QCalendar().weekDayName(*
this, day, type);
3280
3281
3282
3283
3284
3285
3286
3287
3288
3289
3290
3291QString QLocale::standaloneDayName(
int day, FormatType type)
const
3293 return QCalendar().standaloneWeekDayName(*
this, day, type);
3300 const QCalendarLocale *table)
3303 [[maybe_unused]]
const auto sameLocale = [](
const QLocaleData &locale,
3304 const QCalendarLocale &cal) {
3305 return locale.m_language_id == cal.m_language_id
3306 && locale.m_script_id == cal.m_script_id
3307 && locale.m_territory_id == cal.m_territory_id;
3309 const QCalendarLocale &monthly = table[loc->m_index];
3310#ifdef QT_NO_SYSTEMLOCALE
3311 [[maybe_unused]]
constexpr bool isSys =
false;
3313 [[maybe_unused]]
const bool isSys = loc->m_data == &systemLocaleData;
3318 Q_ASSERT(sameLocale(
locale_data[loc->m_index], monthly));
3323
3324
3327 const char16_t *monthsData,
int month,
3328 QLocale::FormatType type)
3331 return range.getListEntry(monthsData, month - 1);
3335
3336
3339 const char16_t *monthsData,
int month,
3340 QLocale::FormatType type)
3343 if (QString name = range.getListEntry(monthsData, month - 1); !name.isEmpty())
3345 return rawMonthName(localeData, monthsData, month, type);
3349
3350
3353 QLocale::FormatType type)
3357 case QLocale::LongFormat:
3358 range = data->longDayNames();
3360 case QLocale::ShortFormat:
3361 range = data->shortDayNames();
3363 case QLocale::NarrowFormat:
3364 range = data->narrowDayNames();
3369 return range.getListEntry(
days_data, day == 7 ? 0 : day);
3373
3374
3377 QLocale::FormatType type)
3381 case QLocale::LongFormat:
3382 range =data->longDayNamesStandalone();
3384 case QLocale::ShortFormat:
3385 range = data->shortDayNamesStandalone();
3387 case QLocale::NarrowFormat:
3388 range = data->narrowDayNamesStandalone();
3393 QString name = range.getListEntry(days_data, day == 7 ? 0 : day);
3395 return rawWeekDayName(data, day, type);
3401QString QCalendarBackend::monthName(
const QLocale &locale,
int month,
int,
3402 QLocale::FormatType format)
const
3404 Q_ASSERT(month >= 1 && month <= maximumMonthsInYear());
3405 return rawMonthName(getMonthDataFor(locale.d, localeMonthIndexData()),
3406 localeMonthData(), month, format);
3409QString QRomanCalendar::monthName(
const QLocale &locale,
int month,
int year,
3410 QLocale::FormatType format)
const
3412#ifndef QT_NO_SYSTEMLOCALE
3413 if (locale.d->m_data == &systemLocaleData) {
3414 Q_ASSERT(month >= 1 && month <= 12);
3415 QSystemLocale::QueryType queryType = QSystemLocale::MonthNameLong;
3417 case QLocale::LongFormat:
3418 queryType = QSystemLocale::MonthNameLong;
3420 case QLocale::ShortFormat:
3421 queryType = QSystemLocale::MonthNameShort;
3423 case QLocale::NarrowFormat:
3424 queryType = QSystemLocale::MonthNameNarrow;
3427 QVariant res = systemLocale()->query(queryType, month);
3429 return res.toString();
3433 return QCalendarBackend::monthName(locale, month, year, format);
3436QString QCalendarBackend::standaloneMonthName(
const QLocale &locale,
int month,
int,
3437 QLocale::FormatType format)
const
3439 Q_ASSERT(month >= 1 && month <= maximumMonthsInYear());
3440 return rawStandaloneMonthName(getMonthDataFor(locale.d, localeMonthIndexData()),
3441 localeMonthData(), month, format);
3444QString QRomanCalendar::standaloneMonthName(
const QLocale &locale,
int month,
int year,
3445 QLocale::FormatType format)
const
3447#ifndef QT_NO_SYSTEMLOCALE
3448 if (locale.d->m_data == &systemLocaleData) {
3449 Q_ASSERT(month >= 1 && month <= 12);
3450 QSystemLocale::QueryType queryType = QSystemLocale::StandaloneMonthNameLong;
3452 case QLocale::LongFormat:
3453 queryType = QSystemLocale::StandaloneMonthNameLong;
3455 case QLocale::ShortFormat:
3456 queryType = QSystemLocale::StandaloneMonthNameShort;
3458 case QLocale::NarrowFormat:
3459 queryType = QSystemLocale::StandaloneMonthNameNarrow;
3462 QVariant res = systemLocale()->query(queryType, month);
3464 return res.toString();
3468 return QCalendarBackend::standaloneMonthName(locale, month, year, format);
3473QString QCalendarBackend::weekDayName(
const QLocale &locale,
int day,
3474 QLocale::FormatType format)
const
3476 if (day < 1 || day > 7)
3479#ifndef QT_NO_SYSTEMLOCALE
3480 if (locale.d->m_data == &systemLocaleData) {
3481 QSystemLocale::QueryType queryType = QSystemLocale::DayNameLong;
3483 case QLocale::LongFormat:
3484 queryType = QSystemLocale::DayNameLong;
3486 case QLocale::ShortFormat:
3487 queryType = QSystemLocale::DayNameShort;
3489 case QLocale::NarrowFormat:
3490 queryType = QSystemLocale::DayNameNarrow;
3493 QVariant res = systemLocale()->query(queryType, day);
3495 return res.toString();
3499 return rawWeekDayName(locale.d->m_data, day, format);
3502QString QCalendarBackend::standaloneWeekDayName(
const QLocale &locale,
int day,
3503 QLocale::FormatType format)
const
3505 if (day < 1 || day > 7)
3508#ifndef QT_NO_SYSTEMLOCALE
3509 if (locale.d->m_data == &systemLocaleData) {
3510 QSystemLocale::QueryType queryType = QSystemLocale::StandaloneDayNameLong;
3512 case QLocale::LongFormat:
3513 queryType = QSystemLocale::StandaloneDayNameLong;
3515 case QLocale::ShortFormat:
3516 queryType = QSystemLocale::StandaloneDayNameShort;
3518 case QLocale::NarrowFormat:
3519 queryType = QSystemLocale::StandaloneDayNameNarrow;
3522 QVariant res = systemLocale()->query(queryType, day);
3524 return res.toString();
3528 return rawStandaloneWeekDayName(locale.d->m_data, day, format);
3534
3535
3536
3537
3538Qt::DayOfWeek QLocale::firstDayOfWeek()
const
3540#ifndef QT_NO_SYSTEMLOCALE
3541 if (d->m_data == &systemLocaleData) {
3542 const auto res = systemLocale()->query(QSystemLocale::FirstDayOfWeek);
3544 return static_cast<Qt::DayOfWeek>(res.toUInt());
3547 return static_cast<Qt::DayOfWeek>(d->m_data->m_first_day_of_week);
3553
3554
3555
3556
3557 struct TerritoryLanguage
3560 quint16 territoryId;
3561 QLocale::MeasurementSystem system;
3564 constexpr TerritoryLanguage ImperialMeasurementSystems[] = {
3565 { QLocale::English, QLocale::UnitedStates, QLocale::ImperialUSSystem },
3566 { QLocale::English, QLocale::UnitedStatesMinorOutlyingIslands, QLocale::ImperialUSSystem },
3567 { QLocale::Spanish, QLocale::UnitedStates, QLocale::ImperialUSSystem },
3568 { QLocale::Hawaiian, QLocale::UnitedStates, QLocale::ImperialUSSystem },
3569 { QLocale::English, QLocale::UnitedKingdom, QLocale::ImperialUKSystem }
3572 for (
const auto &system : ImperialMeasurementSystems) {
3573 if (system.languageId == m_data->m_language_id
3574 && system.territoryId == m_data->m_territory_id) {
3575 return system.system;
3578 return QLocale::MetricSystem;
3582
3583
3584
3585
3586QList<Qt::DayOfWeek> QLocale::weekdays()
const
3588#ifndef QT_NO_SYSTEMLOCALE
3589 if (d->m_data == &systemLocaleData) {
3591 = qvariant_cast<QList<Qt::DayOfWeek> >(systemLocale()->query(QSystemLocale::Weekdays));
3596 QList<Qt::DayOfWeek> weekdays;
3597 quint16 weekendStart = d->m_data->m_weekend_start;
3598 quint16 weekendEnd = d->m_data->m_weekend_end;
3599 for (
int day = Qt::Monday; day <= Qt::Sunday; day++) {
3600 if ((weekendEnd >= weekendStart && (day < weekendStart || day > weekendEnd)) ||
3601 (weekendEnd < weekendStart && (day > weekendEnd && day < weekendStart)))
3602 weekdays <<
static_cast<Qt::DayOfWeek>(day);
3608
3609
3610
3611
3612QLocale::MeasurementSystem QLocale::measurementSystem()
const
3614#ifndef QT_NO_SYSTEMLOCALE
3615 if (d->m_data == &systemLocaleData) {
3616 const auto res = systemLocale()->query(QSystemLocale::MeasurementSystem);
3618 return MeasurementSystem(res.toInt());
3622 return d->measurementSystem();
3626
3627
3628
3629
3630Qt::LayoutDirection QLocale::textDirection()
const
3639 case ImperialAramaicScript:
3640 case InscriptionalPahlaviScript:
3641 case InscriptionalParthianScript:
3642 case KharoshthiScript:
3644 case MandaeanScript:
3645 case ManichaeanScript:
3646 case MendeKikakuiScript:
3647 case MeroiticCursiveScript:
3648 case MeroiticScript:
3649 case NabataeanScript:
3651 case OldHungarianScript:
3652 case OldNorthArabianScript:
3653 case OldSouthArabianScript:
3655 case PalmyreneScript:
3656 case PhoenicianScript:
3657 case PsalterPahlaviScript:
3658 case SamaritanScript:
3661 return Qt::RightToLeft;
3665 return Qt::LeftToRight;
3669
3670
3671
3672
3673
3674
3675
3676
3677
3678
3679
3680
3681
3682
3683QString QLocale::toUpper(
const QString &str)
const
3685#if !defined(QT_BOOTSTRAPPED) && (QT_CONFIG(icu) || defined(Q_OS_WIN) || defined(Q_OS_APPLE))
3687 QString result = d->toUpper(str, &ok);
3692 return str.toUpper();
3696
3697
3698
3699
3700
3701
3702
3703
3704
3705
3706
3707QString QLocale::toLower(
const QString &str)
const
3709#if !defined(QT_BOOTSTRAPPED) && (QT_CONFIG(icu) || defined(Q_OS_WIN) || defined(Q_OS_APPLE))
3711 const QString result = d->toLower(str, &ok);
3716 return str.toLower();
3721
3722
3723
3724
3725
3726
3727
3728QString QLocale::amText()
const
3730#ifndef QT_NO_SYSTEMLOCALE
3731 if (d->m_data == &systemLocaleData) {
3732 auto res = systemLocale()->query(QSystemLocale::AMText).toString();
3737 return d->m_data->anteMeridiem().getData(am_data);
3741
3742
3743
3744
3745
3746
3747
3748QString QLocale::pmText()
const
3750#ifndef QT_NO_SYSTEMLOCALE
3751 if (d->m_data == &systemLocaleData) {
3752 auto res = systemLocale()->query(QSystemLocale::PMText).toString();
3757 return d->m_data->postMeridiem().getData(pm_data);
3763 QStringView tail{text};
3765 if (tail.startsWith(
"UTC"_L1) || tail.startsWith(
"GMT"_L1))
3766 tail = tail.sliced(3);
3769 return (tail.isEmpty()
3774 : std::move(text).right(tail.size())));
3778#if QT_CONFIG(icu) || !(QT_CONFIG(timezone) && QT_CONFIG(timezone_locale))
3779namespace QtTimeZoneLocale {
3783QString zoneOffsetFormat([[maybe_unused]]
const QLocale &locale,
3785 [[maybe_unused]] QLocale::FormatType width,
3786 const QDateTime &when,
3790 Q_ASSERT(width == QLocale::ShortFormat);
3792#if QT_CONFIG(timezone)
3793 locale != QLocale::system()
3794 ? when.timeRepresentation().displayName(when, QTimeZone::OffsetName, locale)
3797 when.toOffsetFromUtc(offsetSeconds).timeZoneAbbreviation();
3799 if (!text.isEmpty())
3800 text = offsetFromAbbreviation(std::move(text));
3810QString QCalendarBackend::dateTimeToString(QStringView format,
const QDateTime &datetime,
3811 QDate dateOnly, QTime timeOnly,
3812 const QLocale &locale)
const
3816 bool formatDate =
false;
3817 bool formatTime =
false;
3818 if (datetime.isValid()) {
3819 date = datetime.date();
3820 time = datetime.time();
3823 }
else if (dateOnly.isValid()) {
3826 }
else if (timeOnly.isValid()) {
3834 int year = 0, month = 0, day = 0;
3836 const auto parts = julianDayToDate(date.toJulianDay());
3837 if (!parts.isValid())
3840 month = parts.month;
3844 auto appendToResult = [&](
int t,
int repeat) {
3845 auto data = locale.d->m_data;
3847 result.append(data->longLongToString(t, -1, 10, repeat, QLocaleData::ZeroPadded));
3849 result.append(data->longLongToString(t));
3852 auto formatType = [](
int repeat) {
3853 return repeat == 3 ? QLocale::ShortFormat : QLocale::LongFormat;
3857 while (i < format.size()) {
3858 if (format.at(i).unicode() ==
'\'') {
3859 result.append(qt_readEscapedFormatString(format, &i));
3863 const QChar c = format.at(i);
3864 qsizetype rep = qt_repeatCount(format.mid(i));
3865 Q_ASSERT(rep < std::numeric_limits<
int>::max());
3866 int repeat =
int(rep);
3869 switch (c.unicode()) {
3874 else if (repeat >= 2)
3879 appendToResult(year, (year < 0) ? 5 : 4);
3882 appendToResult(year % 100, 2);
3893 repeat = qMin(repeat, 4);
3895 appendToResult(month, repeat);
3897 result.append(monthName(locale, month, year, formatType(repeat)));
3902 repeat = qMin(repeat, 4);
3904 appendToResult(day, repeat);
3907 locale.dayName(dayOfWeek(date.toJulianDay()), formatType(repeat)));
3914 if (!used && formatTime) {
3915 switch (c.unicode()) {
3918 repeat = qMin(repeat, 2);
3919 int hour = time.hour();
3920 if (timeFormatContainsAP(format)) {
3926 appendToResult(hour, repeat);
3931 repeat = qMin(repeat, 2);
3932 appendToResult(time.hour(), repeat);
3937 repeat = qMin(repeat, 2);
3938 appendToResult(time.minute(), repeat);
3943 repeat = qMin(repeat, 2);
3944 appendToResult(time.second(), repeat);
3949 QString text = time.hour() < 12 ? locale.amText() : locale.pmText();
3952 if (format.mid(i + 1).startsWith(u'p', Qt::CaseInsensitive))
3954 if (c.unicode() ==
'A' && (repeat == 1 || format.at(i + 1).unicode() ==
'P'))
3955 text = std::move(text).toUpper();
3956 else if (c.unicode() ==
'a' && (repeat == 1 || format.at(i + 1).unicode() ==
'p'))
3957 text = std::move(text).toLower();
3959 result.append(text);
3965 repeat = qMin(repeat, 3);
3969 appendToResult(time.msec(), 3);
3971 const QString zero = locale.zeroDigit();
3972 if (result.endsWith(zero))
3973 result.chop(zero.size());
3974 if (result.endsWith(zero))
3975 result.chop(zero.size());
3980#if QT_VERSION < QT_VERSION_CHECK(7
,0
,0
) && !defined(QT_BOOTSTRAPPED)
3983
3984
3985
3986
3987 qWarning(
"Zone specifiers are only meaningful for a full datetime. "
3988 "Their use in formatting QTime is deprecated and "
3989 "shall be retired in Qt 7.");
3995 enum AbbrType { Long, Offset, Short };
3996 const auto tzAbbr = [locale](
const QDateTime &when, AbbrType type) {
3998 if (type == Offset) {
3999 text = QtTimeZoneLocale::zoneOffsetFormat(locale, locale.d->m_index,
4000 QLocale::ShortFormat,
4001 when, when.offsetFromUtc());
4003 if (!text.isEmpty())
4006#if QT_CONFIG(timezone)
4007 if (type != Short || locale != QLocale::system()) {
4008 QTimeZone::NameType mode =
4009 type == Short ? QTimeZone::ShortName
4010 : type == Long ? QTimeZone::LongName : QTimeZone::OffsetName;
4011 text = when.timeRepresentation().displayName(when, mode, locale);
4012 if (!text.isEmpty())
4018 text = QString::fromLatin1(when.timeZone().id());
4019 if (!text.isEmpty())
4026 text = when.toOffsetFromUtc(when.offsetFromUtc()).timeZoneAbbreviation();
4028 text = when.timeZoneAbbreviation();
4030 text = offsetFromAbbreviation(std::move(text));
4035 repeat = qMin(repeat, 4);
4036#if QT_VERSION < QT_VERSION_CHECK(7
,0
,0
) && !defined(QT_BOOTSTRAPPED)
4038 const QDateTime when = formatDate ? datetime : QDateTime::currentDateTime();
4040 const QDateTime when = datetime;
4045 text = tzAbbr(when, Long);
4049 text = tzAbbr(when, Offset);
4054 text = tzAbbr(when, Short);
4056 if (text.startsWith(
"UTC"_L1) && text.size() == 6)
4060 if (!text.isEmpty())
4061 result.append(text);
4070 result.resize(result.size() + repeat, c);
4080 int width,
unsigned flags)
const
4087 if (precision != QLocale::FloatingPointShortest && precision < 0)
4093 qsizetype bufSize = 1;
4094 if (precision == QLocale::FloatingPointShortest)
4095 bufSize += std::numeric_limits<
double>::max_digits10;
4096 else if (form == DFDecimal && qt_is_finite(d))
4097 bufSize += wholePartSpace(qAbs(d)) + precision;
4099 bufSize += qMax(2, precision) + 1;
4101 QVarLengthArray<
char> buf(bufSize);
4103 bool negative =
false;
4104 qt_doubleToAscii(d, form, precision, buf.data(), bufSize, negative, length, decpt);
4106 const QString prefix = signPrefix(negative && !qIsNull(d), flags);
4110 && (qstrncmp(buf.data(),
"inf", 3) == 0 || qstrncmp(buf.data(),
"nan", 3) == 0)) {
4111 numStr = QString::fromLatin1(buf.data(), length);
4113 const QString zero = zeroDigit();
4114 QString digits = QString::fromLatin1(buf.data(), length);
4118 Q_ASSERT(
std::all_of(buf.cbegin(), buf.cbegin() + length, isAsciiDigit));
4120 }
else if (zero.size() == 2 && zero.at(0).isHighSurrogate()) {
4121 const char32_t zeroUcs4 = QChar::surrogateToUcs4(zero.at(0), zero.at(1));
4123 converted.reserve(2 * digits.size());
4124 for (QChar ch : std::as_const(digits)) {
4125 const char32_t digit = unicodeForDigit(ch.unicode() -
'0', zeroUcs4);
4126 Q_ASSERT(QChar::requiresSurrogates(digit));
4127 converted.append(QChar::highSurrogate(digit));
4128 converted.append(QChar::lowSurrogate(digit));
4130 digits =
std::move(converted);
4132 Q_ASSERT(zero.size() == 1);
4133 Q_ASSERT(!zero.at(0).isSurrogate());
4134 char16_t z = zero.at(0).unicode();
4135 char16_t *
const value =
reinterpret_cast<
char16_t *>(digits.data());
4136 for (qsizetype i = 0; i < digits.size(); ++i)
4137 value[i] = unicodeForDigit(value[i] -
'0', z);
4140 const bool mustMarkDecimal = flags &
ForcePoint;
4145 numStr = exponentForm(
std::move(digits), decpt, precision, PMDecimalDigits,
4146 mustMarkDecimal, minExponentDigits);
4149 numStr = decimalForm(
std::move(digits), decpt, precision, PMDecimalDigits,
4150 mustMarkDecimal, groupDigits);
4157
4158
4159
4160
4161
4162
4163
4164
4166 if (precision == QLocale::FloatingPointShortest) {
4173 int bias = 2 + minExponentDigits;
4175 if (groupDigits && decpt >= grouping
.first + grouping
.least)
4178 if (decpt > 10 && minExponentDigits == 1)
4183 const qsizetype digitCount = digits.size() / zero.size();
4184 if (!mustMarkDecimal) {
4187 if (digitCount <= decpt && digitCount > 1)
4189 else if (digitCount == 1 && decpt <= 0)
4197 useDecimal = (decpt <= 0 ? 1 - decpt <= bias
4198 : decpt <= digitCount ? 0 <= bias : decpt <= digitCount + bias);
4201 Q_ASSERT(precision >= 0);
4202 useDecimal = decpt > -4 && decpt <= (precision ? precision : 1);
4206 ? decimalForm(
std::move(digits), decpt, precision, mode,
4207 mustMarkDecimal, groupDigits)
4208 : exponentForm(
std::move(digits), decpt, precision, mode,
4209 mustMarkDecimal, minExponentDigits);
4216 for (qsizetype i = numStr.size() / zero.size() + prefix.size(); i < width; ++i)
4217 numStr.prepend(zero);
4222 ?
std::move(numStr).toUpper()
4223 :
std::move(numStr).toLower());
4226QString
QLocaleData::decimalForm(QString &&digits,
int decpt,
int precision,
4227 PrecisionMode pm,
bool mustMarkDecimal,
4228 bool groupDigits)
const
4230 const QString zero = zeroDigit();
4231 const auto digitWidth = zero.size();
4232 Q_ASSERT(digitWidth == 1 || digitWidth == 2);
4233 Q_ASSERT(digits.size() % digitWidth == 0);
4238 for (; decpt < 0; ++decpt)
4239 digits.prepend(zero);
4241 for (qsizetype i = digits.size() / digitWidth; i < decpt; ++i)
4242 digits.append(zero);
4246 case PMDecimalDigits:
4247 for (qsizetype i = digits.size() / digitWidth - decpt; i < precision; ++i)
4248 digits.append(zero);
4250 case PMSignificantDigits:
4251 for (qsizetype i = digits.size() / digitWidth; i < precision; ++i)
4252 digits.append(zero);
4254 case PMChopTrailingZeros:
4255 Q_ASSERT(digits.size() / digitWidth <= qMax(decpt, 1) || !digits.endsWith(zero));
4259 if (mustMarkDecimal || decpt < digits.size() / digitWidth)
4260 digits.insert(decpt * digitWidth, decimalPoint());
4264 const QString group = groupSeparator();
4265 qsizetype i = decpt - grouping.least;
4266 if (i >= grouping.first) {
4267 digits.insert(i * digitWidth, group);
4268 while ((i -= grouping.higher) > 0)
4269 digits.insert(i * digitWidth, group);
4274 digits.prepend(zero);
4276 return std::move(digits);
4279QString
QLocaleData::exponentForm(QString &&digits,
int decpt,
int precision,
4280 PrecisionMode pm,
bool mustMarkDecimal,
4281 int minExponentDigits)
const
4283 const QString zero = zeroDigit();
4284 const auto digitWidth = zero.size();
4285 Q_ASSERT(digitWidth == 1 || digitWidth == 2);
4286 Q_ASSERT(digits.size() % digitWidth == 0);
4289 case PMDecimalDigits:
4290 for (qsizetype i = digits.size() / digitWidth; i < precision + 1; ++i)
4291 digits.append(zero);
4293 case PMSignificantDigits:
4294 for (qsizetype i = digits.size() / digitWidth; i < precision; ++i)
4295 digits.append(zero);
4297 case PMChopTrailingZeros:
4298 Q_ASSERT(digits.size() / digitWidth <= 1 || !digits.endsWith(zero));
4302 if (mustMarkDecimal || digits.size() > digitWidth)
4303 digits.insert(digitWidth, decimalPoint());
4305 digits.append(exponentSeparator());
4306 digits.append(longLongToString(decpt - 1, minExponentDigits, 10, -1, AlwaysShowSign));
4308 return std::move(digits);
4311QString
QLocaleData::signPrefix(
bool negative,
unsigned flags)
const
4314 return negativeSign();
4315 if (flags & AlwaysShowSign)
4316 return positiveSign();
4317 if (flags & BlankBeforePositive)
4323 int base,
int width,
unsigned flags)
const
4325 bool negative = n < 0;
4328
4329
4330
4331 QString numStr = qulltoa(negative ? 1u + qulonglong(-(n + 1)) : qulonglong(n),
4334 return applyIntegerFormatting(
std::move(numStr), negative, precision, base, width, flags);
4338 int base,
int width,
unsigned flags)
const
4340 return applyIntegerFormatting(qulltoa(l, base, zeroDigit()),
4341 false, precision, base, width, flags);
4344QString
QLocaleData::applyIntegerFormatting(QString &&numStr,
bool negative,
int precision,
4345 int base,
int width,
unsigned flags)
const
4347 const QString zero = base == 10 ? zeroDigit() :
QStringLiteral(
"0");
4348 const auto digitWidth = zero.size();
4349 const auto digitCount = numStr.size() / digitWidth;
4351 const auto basePrefix = [&] () -> QStringView {
4352 if (flags & ShowBase) {
4353 const bool upper = flags & UppercaseBase;
4355 return upper ? u"0X" : u"0x";
4357 return upper ? u"0B" : u"0b";
4358 if (base == 8 && !numStr.startsWith(zero))
4364 const QString prefix = signPrefix(negative, flags) + basePrefix;
4366 qsizetype usedWidth = digitCount + prefix.size();
4370 const QString group = groupSeparator();
4371 qsizetype i = digitCount - grouping.least;
4372 if (i >= grouping.first) {
4373 numStr.insert(i * digitWidth, group);
4375 while ((i -= grouping.higher) > 0) {
4376 numStr.insert(i * digitWidth, group);
4383 const bool noPrecision = precision == -1;
4387 for (qsizetype i = numStr.size(); i < precision; ++i) {
4388 numStr.prepend(zero);
4395 for (qsizetype i = usedWidth; i < width; ++i)
4396 numStr.prepend(zero);
4399 QString result(flags & CapitalEorX ? std::move(numStr).toUpper() : std::move(numStr));
4401 result.prepend(prefix);
4407#ifndef QT_BUILD_INTERNAL
4411 :
grouping(data->groupSizes()), isC(data == c())
4417 setZero(data->zero().viewData(single_character_data));
4418 group = data->groupDelim().viewData(single_character_data);
4420 minus = data->minus().viewData(single_character_data);
4421 plus = data->plus().viewData(single_character_data);
4422 if (mode != IntegerMode)
4423 decimal = data->decimalSeparator().viewData(single_character_data);
4425 exponent = data->exponential().viewData(single_character_data);
4427 exponentCyrillic = data->m_script_id == QLocale::CyrillicScript;
4429#ifndef QT_NO_SYSTEMLOCALE
4430 if (data == &systemLocaleData) {
4431 const auto getString = [sys = systemLocale()](QSystemLocale::QueryType query) {
4432 return sys->query(query).toString();
4435 sysDecimal = getString(QSystemLocale::DecimalPoint);
4436 if (sysDecimal.size())
4437 decimal = QStringView{sysDecimal};
4439 sysGroup = getString(QSystemLocale::GroupSeparator);
4440 if (sysGroup.size())
4441 group = QStringView{sysGroup};
4442 sysMinus = getString(QSystemLocale::NegativeSign);
4443 if (sysMinus.size())
4444 minus = QStringView{sysMinus};
4445 sysPlus = getString(QSystemLocale::PositiveSign);
4447 plus = QStringView{sysPlus};
4448 setZero(getString(QSystemLocale::ZeroDigit));
4457class NumericTokenizer
4461 static constexpr char lettersInfNaN[] =
"afin";
4462 static constexpr auto matchInfNaN =
QtPrivate::makeCharacterSetMatch<lettersInfNaN>();
4463 const QStringView m_text;
4467 static_assert(
'+' + 1 ==
',' &&
',' + 1 ==
'-' &&
'-' + 1 ==
'.');
4472 : m_text(text), m_guide(guide), m_index(from), m_mode(mode),
4475 Q_ASSERT(m_guide.isValid(mode));
4477 bool done()
const {
return !(m_index < m_text.size()); }
4478 qsizetype index()
const {
return m_index; }
4479 int digitValue(
char32_t digit)
const {
return m_guide.digitValue(digit); }
4480 bool isInfNanChar(
char ch)
const {
return matchInfNaN.matches(ch); }
4482 bool fractionGroupClash()
const
4487 return Q_UNLIKELY(m_mode != QLocaleData::IntegerMode && m_guide.fractionalIsGroup());
4492char NumericTokenizer::nextToken()
4499 const auto asciiLower = [](
unsigned char c) {
return c >=
'A' ? c | 0x20 : c; };
4500 const QStringView tail = m_text.sliced(m_index);
4501 const QChar ch = tail.front();
4502 if (ch == u'\u2212') {
4509 if (Q_LIKELY(ch.unicode() < 256)) {
4510 unsigned char ascii = asciiLower(ch.toLatin1());
4511 if (Q_LIKELY(isAsciiDigit(ascii) || (
'+' <= ascii && ascii <= lastMark)
4522 if (ch.unicode() < 256) {
4524 char ascii = asciiLower(ch.toLatin1());
4525 if (isAsciiDigit(ascii) || ascii ==
'-' || ascii ==
'+'
4534 if (tail.startsWith(m_guide.minus)) {
4535 m_index += m_guide.minus.size();
4538 if (tail.startsWith(m_guide.plus)) {
4539 m_index += m_guide.plus.size();
4542 if (!m_guide.group.isEmpty() && tail.startsWith(m_guide.group)) {
4543 m_index += m_guide.group.size();
4548 if (fractionGroupClash() && tail.indexOf(m_guide.decimal, m_guide.group.size()) == -1)
4553 m_index += m_guide.decimal.size();
4558 m_index += m_guide.exponent.size();
4563 if (m_guide.zeroLen == 1) {
4564 if (!ch.isSurrogate()) {
4565 if (
const int gap = digitValue(
char32_t(ch.unicode())); gap >= 0) {
4569 }
else if (ch.isHighSurrogate() && tail.size() > 1 && tail.at(1).isLowSurrogate()) {
4573 }
else if (ch.isHighSurrogate()) {
4576 if (tail.size() > 1) {
4577 if (
const QChar low = tail.at(1); low.isLowSurrogate()) {
4578 if (
const int gap = digitValue(QChar::surrogateToUcs4(ch, low)); gap >= 0) {
4589 Q_ASSERT(!(ch.isHighSurrogate() && tail.size() > 1 && tail.at(1).isLowSurrogate()));
4592 switch (ch.unicode()) {
4606 if (m_guide.group == u"\u00a0" || m_guide.group == u"\u202f") {
4620 if (m_guide.exponentCyrillic) {
4634
4635
4636
4637
4638
4639
4640
4641
4642
4643
4644
4645
4646
4647
4648
4649
4650
4657 NumericTokenizer tokens(s, NumericData(
this, mode), mode);
4660 enum { Whole, Grouped, Fraction, Exponent, Name } stage = Whole;
4666 bool wantDigits =
true;
4669 bool needHigherGroup =
false;
4670 qsizetype digitsInGroup = 0;
4672 const auto badLeastGroup = [&]() {
4678 if (stage == Grouped) {
4679 Q_ASSERT(!number_options.testFlag(QLocale::RejectGroupSeparator));
4681 if (needHigherGroup)
4684 if (digitsInGroup != grouping.least)
4691 while (!tokens.done()) {
4692 char out = tokens.nextToken();
4700 if (stage > Grouped)
4703 if (tokens.fractionGroupClash() && badLeastGroup()
4704 && digitsInGroup == grouping.higher) {
4710 needHigherGroup =
false;
4714 if (badLeastGroup())
4718 }
else if (out ==
'e') {
4719 if (wantDigits || stage == Name || stage > Fraction)
4722 if (stage < Fraction) {
4724 if (badLeastGroup())
4726 }
else if (number_options.testFlag(QLocale::RejectTrailingZeroesAfterDot)) {
4733 }
else if (out ==
',') {
4739 if (number_options.testFlag(QLocale::RejectGroupSeparator))
4745 if (digitsInGroup == 0
4746 || digitsInGroup > qMax(grouping.first, grouping.higher)) {
4749 Q_ASSERT(!needHigherGroup);
4753 if (grouping.first > digitsInGroup)
4754 needHigherGroup =
true;
4759 if (digitsInGroup != grouping.higher)
4761 needHigherGroup =
false;
4770 }
else if (isAsciiDigit(out)) {
4773 if (out ==
'0' && number_options.testFlag(QLocale::RejectLeadingZeroInExponent)
4774 && stage > Fraction && !tokens.done() && !isAsciiDigit(last)) {
4782 }
else if (stage == Whole && tokens.isInfNanChar(out)) {
4792 result->append(out);
4797 if (!number_options.testFlag(QLocale::RejectGroupSeparator)) {
4799 if (stage < Fraction && badLeastGroup())
4803 if (number_options.testFlag(QLocale::RejectTrailingZeroesAfterDot) && stage == Fraction) {
4814 QLocale::NumberOptions number_options)
const
4817 result.buff.reserve(str.size());
4819 enum { Whole, Fractional, Exponent } state = Whole;
4821 NumericTokenizer tokens(str, NumericData(
this, numMode), numMode);
4824 while (!tokens.done()) {
4825 char c = tokens.nextToken();
4827 if (isAsciiDigit(c)) {
4834 if (decDigits-- == 0)
4838 if (!isAsciiDigit(last)) {
4841 if (c ==
'0' && (number_options & QLocale::RejectLeadingZeroInExponent))
4863 if (last !=
'\0' && !(scientific && last ==
'e'))
4869 if ((number_options & QLocale::RejectGroupSeparator) || state != Whole
4870 || !isAsciiDigit(last)) {
4879 if (!scientific || state == Exponent)
4889 Q_ASSERT(!c || c ==
'a' || c ==
'f' || c ==
'i' || c ==
'n');
4896 result.buff.append(c);
4903 if (last ==
',' || last ==
'-' || last ==
'+' || last ==
'e')
4910 QLocale::NumberOptions number_options)
const
4913 if (!numberToCLocale(str, number_options, DoubleScientificMode, &buff)) {
4918 auto r = qt_asciiToDouble(buff.constData(), buff.size());
4926 QLocale::NumberOptions number_options)
const
4929 if (!numberToCLocale(str, number_options, IntegerMode, &buff))
4932 return bytearrayToLongLong(QByteArrayView(buff), base);
4937 QLocale::NumberOptions number_options)
const
4940 if (!numberToCLocale(str, number_options, IntegerMode, &buff))
4943 return bytearrayToUnsLongLong(QByteArrayView(buff), base);
4951 const qsizetype len = num.size();
4952 if (used < len && num[used] !=
'\0') {
4953 while (used < len && ascii_isspace(num[used]))
4957 if (used < len && num[used] !=
'\0')
4964QSimpleParsedNumber<qint64>
QLocaleData::bytearrayToLongLong(QByteArrayView num,
int base)
4966 auto r = qstrntoll(num.data(), num.size(), base);
4967 if (!checkParsed(num, r.used))
4972QSimpleParsedNumber<quint64>
QLocaleData::bytearrayToUnsLongLong(QByteArrayView num,
int base)
4974 auto r = qstrntoull(num.data(), num.size(), base);
4975 if (!checkParsed(num, r.used))
4981
4982
4983
4984
4985
4986
4987
4988
4989
4990
4993
4994
4995
4996QString QLocale::currencySymbol(CurrencySymbolFormat format)
const
4998#ifndef QT_NO_SYSTEMLOCALE
4999 if (d->m_data == &systemLocaleData) {
5000 auto res = systemLocale()->query(QSystemLocale::CurrencySymbol, format).toString();
5006 case CurrencySymbol:
5007 return d->m_data->currencySymbol().getData(currency_symbol_data);
5008 case CurrencyDisplayName:
5009 return d->m_data->currencyDisplayName().getData(currency_display_name_data);
5010 case CurrencyIsoCode: {
5011 const char *code = d->m_data->m_currency_iso_code;
5012 if (
auto len = qstrnlen(code, 3))
5013 return QString::fromLatin1(code, qsizetype(len));
5021
5022
5023
5024
5025
5026
5027
5028QString QLocale::toCurrencyString(qlonglong value,
const QString &symbol)
const
5030#ifndef QT_NO_SYSTEMLOCALE
5031 if (d->m_data == &systemLocaleData) {
5032 QSystemLocale::CurrencyToStringArgument arg(value, symbol);
5033 auto res = systemLocale()->query(QSystemLocale::CurrencyToString,
5034 QVariant::fromValue(arg)).toString();
5039 QLocaleData::DataRange range = d->m_data->currencyFormatNegative();
5040 if (!range.size || value >= 0)
5041 range = d->m_data->currencyFormat();
5044 QString str = toString(value);
5045 QString sym = symbol.isNull() ? currencySymbol() : symbol;
5047 sym = currencySymbol(CurrencyIsoCode);
5048 return range.viewData(currency_format_data).arg(str, sym);
5052
5053
5054
5055QString QLocale::toCurrencyString(qulonglong value,
const QString &symbol)
const
5057#ifndef QT_NO_SYSTEMLOCALE
5058 if (d->m_data == &systemLocaleData) {
5059 QSystemLocale::CurrencyToStringArgument arg(value, symbol);
5060 auto res = systemLocale()->query(QSystemLocale::CurrencyToString,
5061 QVariant::fromValue(arg)).toString();
5066 QString str = toString(value);
5067 QString sym = symbol.isNull() ? currencySymbol() : symbol;
5069 sym = currencySymbol(CurrencyIsoCode);
5070 return d->m_data->currencyFormat().getData(currency_format_data).arg(str, sym);
5074
5075
5076
5077
5078
5079
5080
5081
5082
5083QString QLocale::toCurrencyString(
double value,
const QString &symbol,
int precision)
const
5085#ifndef QT_NO_SYSTEMLOCALE
5086 if (d->m_data == &systemLocaleData) {
5087 QSystemLocale::CurrencyToStringArgument arg(value, symbol);
5088 auto res = systemLocale()->query(QSystemLocale::CurrencyToString,
5089 QVariant::fromValue(arg)).toString();
5094 QLocaleData::DataRange range = d->m_data->currencyFormatNegative();
5095 if (!range.size || value >= 0)
5096 range = d->m_data->currencyFormat();
5099 QString str = toString(value,
'f', precision == -1 ? d->m_data->m_currency_digits : precision);
5100 QString sym = symbol.isNull() ? currencySymbol() : symbol;
5102 sym = currencySymbol(CurrencyIsoCode);
5103 return range.viewData(currency_format_data).arg(str, sym);
5107
5108
5109
5112
5113
5114
5115
5116
5117
5118
5119
5120
5121
5122
5123
5124
5125
5128
5129
5130
5131
5132
5133
5134
5135
5136
5137
5138
5139
5140
5141
5142
5143QString QLocale::formattedDataSize(qint64 bytes,
int precision, DataSizeFormats format)
const
5145 int power, base = 1000;
5148 }
else if (format & DataSizeBase1000) {
5149 constexpr auto log10_1000 = 3;
5150 power =
int(std::log10(QtPrivate::qUnsignedAbs(bytes))) / log10_1000;
5152 constexpr auto log2_1024 = 10;
5153 power = QtPrivate::log2i(QtPrivate::qUnsignedAbs(bytes)) / log2_1024;
5157 const QString number = power
5158 ? toString(bytes / std::pow(
double(base), power),
'f', qMin(precision, 3 * power))
5163 Q_ASSERT(power <= 6 && power >= 0);
5166 QLocaleData::DataRange range = (format & DataSizeSIQuantifiers)
5167 ? d->m_data->byteAmountSI() : d->m_data->byteAmountIEC();
5168 unit = range.viewListEntry(byte_unit_data, power - 1);
5170 unit = d->m_data->byteCount().viewData(byte_unit_data);
5173 return number + u' ' + unit;
5177
5178
5179
5180
5181
5182
5183
5184
5185
5186
5187
5188
5189
5190
5191
5192
5193
5194
5195
5196
5197
5198
5199
5200
5201
5202
5203
5204
5205
5206
5207
5208
5209
5210
5211
5212
5213
5214
5215
5216
5217
5218
5219QStringList QLocale::uiLanguages(TagSeparator separator)
const
5221 const char sep =
char(separator);
5222 QStringList uiLanguages;
5223 if (uchar(sep) > 0x7f) {
5224 badSeparatorWarning(
"uiLanguages", sep);
5227 QList<QLocaleId> localeIds;
5228#ifdef QT_NO_SYSTEMLOCALE
5229 constexpr bool isSystem =
false;
5231 const bool isSystem = d->m_data == &systemLocaleData;
5233 uiLanguages = systemLocale()->query(QSystemLocale::UILanguages).toStringList();
5234 if (separator != TagSeparator::Dash) {
5236 const QChar join = QLatin1Char(sep);
5237 uiLanguages.replaceInStrings(u"-", QStringView(&join, 1));
5241 for (
const auto &entry : std::as_const(uiLanguages))
5242 localeIds.append(QLocaleId::fromName(entry));
5243 if (localeIds.isEmpty())
5244 localeIds.append(systemLocale()->fallbackLocale().d->m_data->id());
5246
5247
5248
5249
5250
5251
5252
5253 const QString name = QString::fromLatin1(d->m_data->id().name(sep));
5254 if (!name.isEmpty() && language() != C && !uiLanguages.contains(name)) {
5257 const QLocaleId id = d->m_data->id();
5258 const QLocaleId max = id.withLikelySubtagsAdded();
5259 const QLocaleId mine = max.withLikelySubtagsRemoved();
5261 qsizetype lastAlike = uiLanguages.size() - 1;
5263 for (qsizetype i = 0; !seen && i < uiLanguages.size(); ++i) {
5264 const auto its = QLocaleId::fromName(uiLanguages.at(i)).withLikelySubtagsAdded();
5265 seen = its.withLikelySubtagsRemoved() == mine;
5266 if (!seen && its.language_id == max.language_id && its.script_id == max.script_id)
5270 localeIds.insert(lastAlike + 1, id);
5271 uiLanguages.insert(lastAlike + 1, QString::fromLatin1(id.name(sep)));
5277 localeIds.append(d->m_data->id());
5280 for (qsizetype i = localeIds.size(); i-- > 0; ) {
5281 const QLocaleId id = localeIds.at(i);
5282 Q_ASSERT(id.language_id);
5283 if (id.language_id == C) {
5284 if (!uiLanguages.contains(u"C"_s))
5285 uiLanguages.append(u"C"_s);
5291 const QByteArray prior = id.name(sep);
5292 bool faithful =
true;
5293 if (isSystem && i < uiLanguages.size()) {
5295 faithful = uiLanguages.at(i) == QLatin1StringView(prior);
5298 || QLocaleId::fromName(uiLanguages.at(i)).name(sep) == prior);
5303 if (!uiLanguages.contains(QLatin1StringView(prior)))
5304 uiLanguages.append(QString::fromLatin1(prior));
5305 j = uiLanguages.size();
5308 const QLocaleId max = id.withLikelySubtagsAdded();
5309 Q_ASSERT(max.language_id);
5310 Q_ASSERT(max.language_id == id.language_id);
5314 const auto addIfEquivalent = [&j, &uiLanguages, max, sep, &prior, faithful](QLocaleId cid) {
5315 if (cid.withLikelySubtagsAdded() == max) {
5316 if (
const QByteArray name = cid.name(sep); name != prior)
5317 uiLanguages.insert(j, QString::fromLatin1(name));
5323 addIfEquivalent({ max.language_id, 0, 0 });
5326 addIfEquivalent({ max.language_id, max.script_id, 0 });
5327 if (id.script_id && id.script_id != max.script_id)
5328 addIfEquivalent({ id.language_id, id.script_id, 0 });
5330 if (max.territory_id)
5331 addIfEquivalent({ max.language_id, 0, max.territory_id });
5332 if (id.territory_id && id.territory_id != max.territory_id)
5333 addIfEquivalent({ id.language_id, 0, id.territory_id });
5335 if (max.territory_id && max.script_id)
5336 addIfEquivalent(max);
5337 if (max.territory_id && id.script_id && id.script_id != max.script_id)
5338 addIfEquivalent({ id.language_id, id.script_id, max.territory_id });
5339 if (max.script_id && id.territory_id && id.territory_id != max.territory_id)
5340 addIfEquivalent({ id.language_id, max.script_id, id.territory_id });
5341 if (id.territory_id && id.territory_id != max.territory_id
5342 && id.script_id && id.script_id != max.script_id) {
5343 addIfEquivalent(id);
5350 QDuplicateTracker<QString> known(uiLanguages.size());
5351 uiLanguages.removeIf([&](
const QString &s) {
return known.hasSeen(s); });
5355 const QLatin1Char cut(sep);
5356 const auto hasPrefix = [cut](
auto name, QStringView stem) {
5358 return name.startsWith(stem)
5359 && (name.size() == stem.size() || name.at(stem.size()) == cut);
5370 qsizetype afterEquivs = 0;
5371 qsizetype afterTruncs = 0;
5375 for (qsizetype i = 0; i < uiLanguages.size(); ++i >= afterEquivs && (i = afterTruncs)) {
5376 const QString entry = uiLanguages.at(i);
5377 const QLocaleId max = QLocaleId::fromName(entry).withLikelySubtagsAdded();
5379 if (i >= afterEquivs) {
5380 Q_ASSERT(i >= afterTruncs);
5381 afterEquivs = i + 1;
5383 while (afterEquivs < uiLanguages.size()
5384 && QLocaleId::fromName(uiLanguages.at(afterEquivs))
5385 .withLikelySubtagsAdded() == max) {
5389 afterTruncs = afterEquivs;
5391 if (hasPrefix(entry, u"C") || hasPrefix(entry, u"und"))
5393 qsizetype stopAt = uiLanguages.size();
5394 qsizetype at = entry.size();
5395 while ((at = entry.lastIndexOf(cut, at - 1)) > 0) {
5396 QString prefix = entry.first(at);
5400 bool found = known.contains(prefix);
5402
5403
5404
5405
5406
5407
5408
5409
5410
5412 = (QLocaleId::fromName(prefix).withLikelySubtagsAdded().script_id == max.script_id);
5413 for (qsizetype j = afterTruncs; !found && j < stopAt; ++j) {
5414 QString later = uiLanguages.at(j);
5415 if (!later.startsWith(prefix)) {
5416 const QByteArray laterFull =
5417 QLocaleId::fromName(later.replace(cut, u'-')
5418 ).withLikelySubtagsAdded().name(sep);
5420 if (hasPrefix(QLatin1StringView(laterFull), prefix))
5425 Q_ASSERT(later.size() > prefix.size());
5426 if (later.at(prefix.size()) == cut) {
5433 QStringView head{later};
5434 for (qsizetype as = head.lastIndexOf(cut);
5435 !found && as > prefix.size(); as = head.lastIndexOf(cut)) {
5436 head = head.first(as);
5438 for (qsizetype k = j + 1; !seen && k < uiLanguages.size(); ++k)
5439 seen = uiLanguages.at(k) == head;
5448 (
void) known.hasSeen(prefix);
5450 uiLanguages.insert(afterTruncs++, std::move(prefix));
5453 uiLanguages.append(std::move(prefix));
5462
5463
5464
5465
5466
5467
5468
5469
5470
5471
5472QLocale QLocale::collation()
const
5474#ifndef QT_NO_SYSTEMLOCALE
5475 if (d->m_data == &systemLocaleData) {
5476 const auto res = systemLocale()->query(QSystemLocale::Collation).toString();
5478 return QLocale(res);
5485
5486
5487
5488
5489
5490
5491
5492QString QLocale::nativeLanguageName()
const
5494#ifndef QT_NO_SYSTEMLOCALE
5495 if (d->m_data == &systemLocaleData) {
5496 auto res = systemLocale()->query(QSystemLocale::NativeLanguageName).toString();
5501 return d->m_data->endonymLanguage().getData(endonyms_data);
5505
5506
5507
5508
5509
5510
5511
5512QString QLocale::nativeTerritoryName()
const
5514#ifndef QT_NO_SYSTEMLOCALE
5515 if (d->m_data == &systemLocaleData) {
5516 auto res = systemLocale()->query(QSystemLocale::NativeTerritoryName).toString();
5521 return d->m_data->endonymTerritory().getData(endonyms_data);
5524#if QT_DEPRECATED_SINCE(6
, 6
)
5526
5527
5528
5529
5530
5531
5532
5533
5534QString QLocale::nativeCountryName()
const
5536 return nativeTerritoryName();
5540#ifndef QT_NO_DEBUG_STREAM
5543 QDebugStateSaver saver(dbg);
5544 const bool isSys = l == QLocale::system();
5545 dbg.nospace().noquote()
5546 << (isSys ?
"QLocale::system()/* " :
"QLocale(")
5547 << QLocale::languageToString(l.language()) <<
", "
5548 << QLocale::scriptToString(l.script()) <<
", "
5549 << QLocale::territoryToString(l.territory()) << (isSys ?
" */" :
")");
5555#ifndef QT_NO_QOBJECT
5556#include "moc_qlocale.cpp"
const QLocaleData *const m_data
QLocale::MeasurementSystem measurementSystem() const
QByteArray bcp47Name(char separator='-') const
char32_t next(char32_t invalidAs=QChar::ReplacementCharacter)
Combined button and popup list for selecting options.
Q_GLOBAL_STATIC(DefaultRoleNames, qDefaultRoleNames, { { Qt::DisplayRole, "display" }, { Qt::DecorationRole, "decoration" }, { Qt::EditRole, "edit" }, { Qt::ToolTipRole, "toolTip" }, { Qt::StatusTipRole, "statusTip" }, { Qt::WhatsThisRole, "whatsThis" }, }) const QHash< int
static unsigned calculateFlags(int fieldWidth, char32_t fillChar, const QLocale &locale)
static QString calculateFiller(qsizetype padding, char32_t fillChar, qsizetype fieldWidth, const QLocaleData *localeData)
QDebug operator<<(QDebug dbg, const QLocale &l)
static QLocalePrivate * findLocalePrivate(QLocale::Language language, QLocale::Script script, QLocale::Territory territory)
static std::optional< QString > systemLocaleString(const QLocaleData *that, QSystemLocale::QueryType type)
static const QSystemLocale * systemLocale()
static bool checkParsed(QByteArrayView num, qsizetype used)
static QString rawWeekDayName(const QLocaleData *data, const int day, QLocale::FormatType type)
QDataStream & operator>>(QDataStream &ds, QLocale &l)
#define CheckCandidate(id)
static Q_DECL_COLD_FUNCTION void badSeparatorWarning(const char *method, char sep)
static QString rawStandaloneWeekDayName(const QLocaleData *data, const int day, QLocale::FormatType type)
static constexpr QLocale::NumberOptions defaultNumberOptions(QLocale::Language forLanguage)
static QStringView findTag(QStringView name) noexcept
static bool validTag(QStringView tag)
static qsizetype scriptIndex(QStringView code, Qt::CaseSensitivity cs) noexcept
static const QCalendarLocale & getMonthDataFor(const QLocalePrivate *loc, const QCalendarLocale *table)
static T toIntegral_helper(const QLocalePrivate *d, QStringView str, bool *ok)
static bool timeFormatContainsAP(QStringView format)
size_t qHash(const QLocale &key, size_t seed) noexcept
bool comparesEqual(const QLocale &loc, QLocale::Language lang)
static qsizetype findLocaleIndexById(QLocaleId localeId) noexcept
static constexpr qsizetype locale_data_size
static void updateSystemPrivate()
static QString rawMonthName(const QCalendarLocale &localeData, const char16_t *monthsData, int month, QLocale::FormatType type)
static qsizetype stringWidth(QStringView text)
static QLocalePrivate * c_private() noexcept
static const QLocaleData * defaultData()
static QString rawStandaloneMonthName(const QCalendarLocale &localeData, const char16_t *monthsData, int month, QLocale::FormatType type)
static QString localeString(const QLocaleData *that, QSystemLocale::QueryType type, QLocaleData::DataRange range)
static const QLocaleData * systemData(qsizetype *sysIndex=nullptr)
static QString offsetFromAbbreviation(QString &&text)
static qsizetype defaultIndex()
static constexpr char16_t single_character_data[]
static constexpr char16_t days_data[]
static constexpr QLocaleData locale_data[]
static constexpr QLocaleId likely_subtags[]
static constexpr unsigned char territory_code_list[]
static constexpr unsigned char script_code_list[]
bool qt_splitLocaleName(QStringView name, QStringView *lang=nullptr, QStringView *script=nullptr, QStringView *cntry=nullptr) noexcept
qsizetype qt_repeatCount(QStringView s) noexcept
QString qt_readEscapedFormatString(QStringView format, qsizetype *idx)
#define QStringLiteral(str)
char32_t ucsFirst(const char16_t *table) const
const GroupSizes grouping
QString positiveSign() const
QString groupSeparator() const
QSimpleParsedNumber< qint64 > stringToLongLong(QStringView str, int base, QLocale::NumberOptions options) const
Q_AUTOTEST_EXPORT char32_t zeroUcs() const
QString zeroDigit() const
bool numberToCLocale(QStringView s, QLocale::NumberOptions number_options, NumberMode mode, CharBuff *result) const
QString decimalPoint() const
QString doubleToString(double d, int precision=-1, DoubleForm form=DFSignificantDigits, int width=-1, unsigned flags=NoFlags) const
QString listSeparator() const
QString percentSign() const
double stringToDouble(QStringView str, bool *ok, QLocale::NumberOptions options) const
QString longLongToString(qint64 l, int precision=-1, int base=10, int width=-1, unsigned flags=NoFlags) const
QString exponentSeparator() const
QString negativeSign() const
QSimpleParsedNumber< quint64 > stringToUnsLongLong(QStringView str, int base, QLocale::NumberOptions options) const
QString unsLongLongToString(quint64 l, int precision=-1, int base=10, int width=-1, unsigned flags=NoFlags) const
QLocaleId withLikelySubtagsAdded() const noexcept
QLocaleId withLikelySubtagsRemoved() const noexcept
bool operator==(QLocaleId other) const noexcept