poi naming fix

This commit is contained in:
Arsentiy Milchakov 2017-04-27 15:29:25 +03:00 committed by r.kuznetsov
parent 8503501a5b
commit ab0718d981
3 changed files with 112 additions and 52 deletions

View file

@ -12,9 +12,9 @@
#include "base/base.hpp"
#include "std/vector.hpp"
#include "std/unordered_map.hpp"
#include "std/utility.hpp"
#include "std/vector.hpp"
namespace
{
@ -25,10 +25,10 @@ int8_t GetIndex(string const & lang)
return StrUtf8::GetLangIndex(lang);
}
unordered_map<int8_t, vector<int8_t>> const kExtendedDeviceLang =
unordered_map<int8_t, vector<int8_t>> const kSimilarToDeviceLanguages =
{
{GetIndex("be"), {GetIndex("be"), GetIndex("ru")}},
{GetIndex("ru"), {GetIndex("ru"), GetIndex("be")}}
{GetIndex("be"), {GetIndex("ru")}},
{GetIndex("ru"), {GetIndex("be")}}
};
void GetMwmLangName(feature::RegionData const & regionData, StringUtf8Multilang const & src, string & out)
@ -94,36 +94,48 @@ bool GetBestName(StringUtf8Multilang const & src, vector<int8_t> const & priorit
return bestIndex < priorityList.size();
}
vector<int8_t> GetExtendedDeviceLanguages(int8_t deviceLang)
vector<int8_t> GetSimilarToDeviceLanguages(int8_t deviceLang)
{
auto const it = kSimilarToDeviceLanguages.find(deviceLang);
if (it != kSimilarToDeviceLanguages.cend())
return it->second;
return {};
}
bool IsNativeLang(feature::RegionData const & regionData, int8_t deviceLang)
{
vector<int8_t> result;
if (regionData.HasLanguage(deviceLang))
return true;
auto const it = kExtendedDeviceLang.find(deviceLang);
if (it != kExtendedDeviceLang.cend())
result = it->second;
else
result.push_back(deviceLang);
for (auto const lang : GetSimilarToDeviceLanguages(deviceLang))
{
if (regionData.HasLanguage(lang))
return true;
}
return result;
return false;
}
vector<int8_t> MakePrimaryNamePriorityList(int8_t deviceLang, bool preferDefault)
{
vector<int8_t> langPriority = {deviceLang};
if (preferDefault)
langPriority.push_back(StrUtf8::kDefaultCode);
auto const similarLangs = GetSimilarToDeviceLanguages(deviceLang);
langPriority.insert(langPriority.cend(), similarLangs.cbegin(), similarLangs.cend());
langPriority.insert(langPriority.cend(), {StrUtf8::kInternationalCode, StrUtf8::kEnglishCode});
return langPriority;
}
void GetReadableNameImpl(feature::RegionData const & regionData, StringUtf8Multilang const & src,
vector<int8_t> deviceLangs, bool preferDefault, bool allowTranslit,
string & out)
int8_t deviceLang, bool preferDefault, bool allowTranslit, string & out)
{
ASSERT(!deviceLangs.empty(), ());
vector<int8_t> langPriority = MakePrimaryNamePriorityList(deviceLang, preferDefault);
if (preferDefault)
{
deviceLangs.insert(deviceLangs.cend(), {StrUtf8::kDefaultCode, StrUtf8::kInternationalCode,
StrUtf8::kEnglishCode});
}
else
{
deviceLangs.insert(deviceLangs.cend(), {StrUtf8::kInternationalCode, StrUtf8::kEnglishCode});
}
if (GetBestName(src, deviceLangs, out))
if (GetBestName(src, langPriority, out))
return;
if (allowTranslit && GetTransliteratedName(regionData, src, out))
@ -288,17 +300,12 @@ void GetPreferredNames(RegionData const & regionData, StringUtf8Multilang const
if (src.IsEmpty())
return;
vector<int8_t> primaryCodes = GetExtendedDeviceLanguages(deviceLang);
// When the language of the user is equal to one of the languages of the MWM
// only single name scheme is used.
for (auto const code : primaryCodes)
{
if (regionData.HasLanguage(code))
return GetReadableNameImpl(regionData, src, move(primaryCodes), true, allowTranslit, primary);
}
// (or similar languages) only single name scheme is used.
if (IsNativeLang(regionData, deviceLang))
return GetReadableNameImpl(regionData, src, deviceLang, true, allowTranslit, primary);
primaryCodes.insert(primaryCodes.cend(), {StrUtf8::kInternationalCode, StrUtf8::kEnglishCode});
vector<int8_t> primaryCodes = MakePrimaryNamePriorityList(deviceLang, false);
if (!GetBestName(src, primaryCodes, primary) && allowTranslit)
GetTransliteratedName(regionData, src, primary);
@ -327,20 +334,10 @@ void GetReadableName(RegionData const & regionData, StringUtf8Multilang const &
if (src.IsEmpty())
return;
vector<int8_t> deviceLangs = GetExtendedDeviceLanguages(deviceLang);
// If MWM contains user's language.
bool preferDefault = false;
for (auto const lang : deviceLangs)
{
if (regionData.HasLanguage(lang))
{
preferDefault = true;
break;
}
}
bool const preferDefault = IsNativeLang(regionData, deviceLang);
GetReadableNameImpl(regionData, src, move(deviceLangs), preferDefault, allowTranslit, out);
GetReadableNameImpl(regionData, src, deviceLang, preferDefault, allowTranslit, out);
}
int8_t GetNameForSearchOnBooking(RegionData const & regionData, StringUtf8Multilang const & src,

View file

@ -15,8 +15,11 @@ namespace feature
/// Get viewport scale to show given feature. Used in search.
int GetFeatureViewportScale(TypesHolder const & types);
/// When the language of the device is equal to one of the languages of the MWM
/// (or similar to device languages) only single name scheme is used. See GetReadableName method.
/// Primary name using priority:
/// - device language name (or extended device languages if provided);
/// - device language name;
/// - similar to device languages if provided;
/// - international name;
/// - english name;
/// - transliterated name (if allowed).
@ -30,17 +33,19 @@ namespace feature
void GetPreferredNames(RegionData const & regionData, StringUtf8Multilang const & src,
int8_t const deviceLang, bool allowTranslit, string & primary, string & secondary);
/// When MWM contains user's language (or extended device languages if provided),
/// When MWM contains user's language (or similar to device languages if provided),
/// the priority is the following:
/// - device language name (or extended device languages if provided);
/// - device language name;
/// - default name;
/// - similar to device languages if provided;
/// - international name;
/// - english name;
/// - transliterated name (if allowed);
/// - country language name.
/// When MWM does not contain user's language (or extended device languages),
/// When MWM does not contain user's language (or similar to device languages),
/// the priority is the following:
/// - device language name (or extended device languages if provided);
/// - device language name;
/// - similar to device languages if provided;
/// - international name;
/// - english name;
/// - transliterated name (if allowed);

View file

@ -193,6 +193,36 @@ UNIT_TEST(GetPrefferedNames)
TEST_EQUAL(primary, "ru name", ());
TEST_EQUAL(secondary, "", ());
}
{
feature::RegionData regionData;
regionData.SetLanguages({"ru"});
int8_t deviceLang = StrUtf8::GetLangIndex("be");
StrUtf8 src;
src.AddString("default", "default name");
src.AddString("int_name", "int name");
src.AddString("en", "en name");
src.AddString("ru", "ru name");
feature::GetPreferredNames(regionData, src, deviceLang, allowTranslit, primary, secondary);
TEST_EQUAL(primary, "default name", ());
TEST_EQUAL(secondary, "", ());
}
{
feature::RegionData regionData;
regionData.SetLanguages({"ru"});
int8_t deviceLang = StrUtf8::GetLangIndex("ru");
StrUtf8 src;
src.AddString("default", "default name");
src.AddString("int_name", "int name");
src.AddString("en", "en name");
src.AddString("be", "be name");
feature::GetPreferredNames(regionData, src, deviceLang, allowTranslit, primary, secondary);
TEST_EQUAL(primary, "default name", ());
TEST_EQUAL(secondary, "", ());
}
}
UNIT_TEST(GetPrefferedNamesLocal)
@ -382,6 +412,34 @@ UNIT_TEST(GetReadableName)
TEST_EQUAL(name, "ru name", ());
}
{
feature::RegionData regionData;
regionData.SetLanguages({"ru"});
int8_t deviceLang = StrUtf8::GetLangIndex("be");
StrUtf8 src;
src.AddString("default", "default name");
src.AddString("int_name", "int name");
src.AddString("en", "en name");
src.AddString("ru", "ru name");
feature::GetReadableName(regionData, src, deviceLang, allowTranslit, name);
TEST_EQUAL(name, "default name", ());
}
{
feature::RegionData regionData;
regionData.SetLanguages({"ru"});
int8_t deviceLang = StrUtf8::GetLangIndex("ru");
StrUtf8 src;
src.AddString("default", "default name");
src.AddString("int_name", "int name");
src.AddString("en", "en name");
src.AddString("be", "be name");
feature::GetReadableName(regionData, src, deviceLang, allowTranslit, name);
TEST_EQUAL(name, "default name", ());
}
}
UNIT_TEST(GetNameForSearchOnBooking)