11 #ifndef SDK_BASE_STRING_COORDINATES_CONVERSIONS_H_
12 #define SDK_BASE_STRING_COORDINATES_CONVERSIONS_H_
23 namespace conversions {
25 inline SDKUInt32 MulDivUInt32(SDKUInt32 number, SDKUInt32 numerator,
26 SDKUInt32 denominator) {
27 SDKUInt64 intermediate =
static_cast<SDKUInt64
>(number) * numerator;
28 return denominator ? ((intermediate /= denominator) <=
SDK_MAX_UINT32 ?
30 static_cast<SDKUInt32>(intermediate >> 32);
33 inline std::string CoordStrPrintf(
const std::string& format,
34 char* coord_str,
size_t coord_str_size,...) {
37 va_start(dividers, coord_str_size);
39 #if defined(SDK_CC_MSVC)
40 vsprintf_s(coord_str, coord_str_size, format.c_str(), dividers);
42 vsprintf(coord_str, format.c_str(), dividers);
51 const std::string& format,
char positive,
char negative, SDKUInt32 max_value,
52 const SDKUInt32* dividers, SDKUInt32 divider_count) {
55 if (
static_cast<SDKInt32
>(coord) < 0) {
56 coord =
static_cast<SDKUInt32
>(-
static_cast<SDKInt32
>(coord));
60 if (coord > max_value)
63 typedef std::vector<SDKUInt32> Dividers;
64 Dividers dividers_vec(dividers, ÷rs[divider_count]);
67 for (Dividers::const_iterator it = dividers_vec.begin();
68 it != dividers_vec.end(); ++it) {
69 scale = scale *
static_cast<SDKUInt32
>(*it);
72 coord += (0x20000000UL / scale);
76 for (Dividers::iterator it = dividers_vec.begin();
77 it != dividers_vec.end(); ++it) {
78 scale = scale *
static_cast<SDKUInt32
>(*it);
79 SDKUInt32 tmp = MulDivUInt32(coord, scale, 0x40000000UL);
80 coord -= MulDivUInt32(tmp, 0x40000000UL, scale);
84 char coord_str[32] = {0};
85 switch(dividers_vec.size()) {
87 CoordStrPrintf(format, coord_str,
sizeof(coord_str),
88 dividers_vec[0], dividers_vec[1], dividers_vec[2]);
94 char* sign_pos = strchr(coord_str,
'\\');
97 *sign_pos = sign ? positive : negative;
99 return std::string(coord_str);
104 static const char* kLonHemispherePostfix =
"%03u#%02u.%04u\'\\";
105 static const char* kLatHemispherePrefix =
"\\ %02u#%02u.%04u\'";
106 static const char* kLonHemispherePrefix =
"\\ %03u#%02u.%04u\'";
107 static const char* kLatHemispherePostfixSpaced =
"%02u# %02u.%04u\' \\";
108 static const char* kLonHemispherePostfixSpaced =
"%03u# %02u.%04u\' \\";
109 static const char* kLatHemispherePrefixSpaced =
"\\ %02u# %02u.%04u\'";
110 static const char* kLonHemispherePrefixSpaced =
"\\ %03u# %02u.%04u\'";
111 static const SDKUInt32 kDividers[3] = { 90, 60, 10000 };
115 static const char* kLonHemispherePostfix3 =
"%03u#%02u.%03u\'\\";
116 static const char* kLatHemispherePrefix3 =
"\\ %02u#%02u.%03u\'";
117 static const char* kLonHemispherePrefix3 =
"\\ %03u#%02u.%03u\'";
118 static const char* kLatHemispherePostfix3Spaced =
"%02u# %02u.%03u\' \\";
119 static const char* kLonHemispherePostfix3Spaced =
"%03u# %02u.%03u\' \\";
120 static const char* kLatHemispherePrefix3Spaced =
"\\ %02u# %02u.%03u\'";
121 static const char* kLonHemispherePrefix3Spaced =
"\\ %03u# %02u.%03u\'";
122 static const SDKUInt32 kDividers3[3] = { 90, 60, 1000 };
124 static const unsigned char kDegreeSignB = 0xB0;
125 static const std::wstring::value_type kDegreeSignW = 0xB0;
136 sizeof(kDividers)/
sizeof(kDividers[0]));
137 size_t pos = res.find_first_of(
"#");
138 if (pos != std::string::npos) {
139 res[pos] = kDegreeSignB;
148 kLonHemispherePostfix,
153 sizeof(kDividers)/
sizeof(kDividers[0]));
154 size_t pos = res.find_first_of(
"#");
155 if (pos != std::string::npos) {
156 res[pos] = kDegreeSignB;
170 sizeof(kDividers)/
sizeof(kDividers[0]));
172 std::wstring res = std::wstring(ascii.begin(), ascii.end());
173 size_t pos = res.find_first_of(L
"#");
174 if (pos != std::wstring::npos) {
175 res[pos] = kDegreeSignW;
184 kLonHemispherePostfix,
189 sizeof(kDividers)/
sizeof(kDividers[0]));
191 std::wstring res = std::wstring(ascii.begin(), ascii.end());
192 size_t pos = res.find_first_of(L
"#");
193 if (pos != std::wstring::npos) {
194 res[pos] = kDegreeSignW;