mirror of
https://codeberg.org/comaps/comaps
synced 2025-12-20 05:13:58 +00:00
[core] Support geo-navigation URL
Signed-off-by: x7z4w <x7z4w@noreply.codeberg.org>
This commit is contained in:
@@ -41,6 +41,7 @@ public:
|
|||||||
return &p.second;
|
return &p.second;
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
std::vector<Param> const & GetParams() const { return m_params; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool Parse(std::string const & url);
|
bool Parse(std::string const & url);
|
||||||
|
|||||||
@@ -1,8 +1,19 @@
|
|||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
#include "platform/preferred_languages.hpp"
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "map/mwm_url.hpp"
|
#include "map/mwm_url.hpp"
|
||||||
|
|
||||||
#include "map/api_mark_point.hpp"
|
#include "map/api_mark_point.hpp"
|
||||||
#include "map/bookmark_manager.hpp"
|
#include "map/bookmark_manager.hpp"
|
||||||
#include "map/framework.hpp"
|
#include "map/framework.hpp"
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
#include "map/everywhere_search_params.hpp"
|
||||||
|
#include "map/routing_manager.hpp"
|
||||||
|
#include "map/routing_mark.hpp"
|
||||||
|
|
||||||
|
#include "search/result.hpp"
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "ge0/geo_url_parser.hpp"
|
#include "ge0/geo_url_parser.hpp"
|
||||||
#include "ge0/parser.hpp"
|
#include "ge0/parser.hpp"
|
||||||
@@ -17,8 +28,9 @@
|
|||||||
#include "base/scope_guard.hpp"
|
#include "base/scope_guard.hpp"
|
||||||
#include "base/string_utils.hpp"
|
#include "base/string_utils.hpp"
|
||||||
|
|
||||||
#include <array>
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
#include <tuple>
|
#include <future>
|
||||||
|
#endif
|
||||||
|
|
||||||
namespace url_scheme
|
namespace url_scheme
|
||||||
{
|
{
|
||||||
@@ -238,6 +250,131 @@ ParsedMapApi::UrlType ParsedMapApi::SetUrlAndParse(std::string const & raw)
|
|||||||
UNREACHABLE();
|
UNREACHABLE();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
ParsedMapApi::UrlType ParsedMapApi::ParseGeoNav(std::string const & raw, Framework & fm)
|
||||||
|
{
|
||||||
|
Reset();
|
||||||
|
SCOPE_GUARD(guard, [this]
|
||||||
|
{
|
||||||
|
if (m_requestType == UrlType::Incorrect)
|
||||||
|
Reset();
|
||||||
|
});
|
||||||
|
|
||||||
|
url::Url const url(raw);
|
||||||
|
|
||||||
|
if (url.GetHost() == "place")
|
||||||
|
{
|
||||||
|
auto const latLon = url.GetParamValue("coordinate");
|
||||||
|
auto const addr = url.GetParamValue("address");
|
||||||
|
|
||||||
|
if (latLon)
|
||||||
|
{
|
||||||
|
auto const tokens = strings::Tokenize(*latLon, ",");
|
||||||
|
double lat;
|
||||||
|
double lon;
|
||||||
|
|
||||||
|
if (tokens.size() != 2 || !strings::to_double(tokens[0], lat) || !strings::to_double(tokens[1], lon) ||
|
||||||
|
!mercator::ValidLat(lat) || !mercator::ValidLon(lon))
|
||||||
|
{
|
||||||
|
LOG(LWARNING, ("Invalid lat,lon in", raw));
|
||||||
|
return m_requestType = UrlType::Incorrect;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (addr)
|
||||||
|
{
|
||||||
|
m_searchRequest = SearchRequest();
|
||||||
|
m_searchRequest.m_query = *addr;
|
||||||
|
m_centerLatLon = {lat, lon};
|
||||||
|
return m_requestType = UrlType::Search;
|
||||||
|
}
|
||||||
|
|
||||||
|
else
|
||||||
|
{
|
||||||
|
m_centerLatLon = {lat, lon};
|
||||||
|
m_mapPoints.push_back({lat /* m_lat */, lon /* m_lon */, "" /* m_label */, "" /* m_id */, "" /* m_style */});
|
||||||
|
return m_requestType = UrlType::Map;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
else if (addr)
|
||||||
|
{
|
||||||
|
m_searchRequest = SearchRequest();
|
||||||
|
m_searchRequest.m_query = *addr;
|
||||||
|
return m_requestType = UrlType::Search;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
else if (url.GetHost() == "directions")
|
||||||
|
{
|
||||||
|
auto const source = url.GetParamValue("source");
|
||||||
|
auto const destination = url.GetParamValue("destination");
|
||||||
|
|
||||||
|
if (source)
|
||||||
|
SetRouteMark(*source, fm, RouteMarkType::Finish);
|
||||||
|
|
||||||
|
if (url.GetParamValue("waypoint"))
|
||||||
|
for (auto const & param : url.GetParams())
|
||||||
|
if (param.first == "waypoint")
|
||||||
|
SetRouteMark(param.second, fm, RouteMarkType::Intermediate);
|
||||||
|
|
||||||
|
if (destination)
|
||||||
|
SetRouteMark(*destination, fm, RouteMarkType::Finish);
|
||||||
|
|
||||||
|
if (source || destination)
|
||||||
|
{
|
||||||
|
m_routingType = routing::ToString(routing::GetLastUsedRouter());
|
||||||
|
|
||||||
|
return m_requestType = UrlType::Route;
|
||||||
|
}
|
||||||
|
|
||||||
|
return m_requestType = UrlType::Incorrect;
|
||||||
|
}
|
||||||
|
|
||||||
|
return m_requestType = UrlType::Incorrect;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ParsedMapApi::SetRouteMark(std::string_view const raw, Framework & fm, RouteMarkType const type)
|
||||||
|
{
|
||||||
|
auto const tokens = strings::Tokenize(raw, ",");
|
||||||
|
double lat;
|
||||||
|
double lon;
|
||||||
|
|
||||||
|
if (tokens.size() != 2 || !strings::to_double(tokens[0], lat) || !strings::to_double(tokens[1], lon) ||
|
||||||
|
!mercator::ValidLat(lat) || !mercator::ValidLon(lon))
|
||||||
|
{
|
||||||
|
std::promise<void> signal;
|
||||||
|
std::future<void> future = signal.get_future();
|
||||||
|
|
||||||
|
::search::EverywhereSearchParams params{
|
||||||
|
std::string(raw),
|
||||||
|
languages::GetMostPreferredLang(),
|
||||||
|
{} /* timeout */,
|
||||||
|
false,
|
||||||
|
// m_onResults
|
||||||
|
[this, type = std::move(type), &signal](::search::Results results, std::vector<::search::ProductInfo>)
|
||||||
|
{
|
||||||
|
auto const center = results[0].GetFeatureCenter();
|
||||||
|
RoutePoint p;
|
||||||
|
p.m_type = type;
|
||||||
|
p.m_org = mercator::FromLatLon(mercator::YToLat(center.y), mercator::XToLon(center.x));
|
||||||
|
p.m_name = results[0].GetString();
|
||||||
|
m_routePoints.push_back(p);
|
||||||
|
signal.set_value();
|
||||||
|
}};
|
||||||
|
|
||||||
|
fm.GetSearchAPI().SearchEverywhere(std::move(params));
|
||||||
|
future.wait();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
RoutePoint p;
|
||||||
|
p.m_org = mercator::FromLatLon(lat, lon);
|
||||||
|
p.m_type = type;
|
||||||
|
m_routePoints.push_back(p);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
void ParsedMapApi::ParseMapParam(std::string const & key, std::string const & value, bool & correctOrder)
|
void ParsedMapApi::ParseMapParam(std::string const & key, std::string const & value, bool & correctOrder)
|
||||||
{
|
{
|
||||||
using namespace map;
|
using namespace map;
|
||||||
|
|||||||
@@ -1,5 +1,10 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
#include "map/everywhere_search_params.hpp"
|
||||||
|
#include "map/routing_mark.hpp"
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "geometry/latlon.hpp"
|
#include "geometry/latlon.hpp"
|
||||||
#include "geometry/point2d.hpp"
|
#include "geometry/point2d.hpp"
|
||||||
|
|
||||||
@@ -22,9 +27,20 @@ struct MapPoint
|
|||||||
struct RoutePoint
|
struct RoutePoint
|
||||||
{
|
{
|
||||||
RoutePoint() = default;
|
RoutePoint() = default;
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
RoutePoint(m2::PointD const & org, std::string const & name, RouteMarkType type)
|
||||||
|
: m_org(org)
|
||||||
|
, m_name(name)
|
||||||
|
, m_type(type)
|
||||||
|
{}
|
||||||
|
#else
|
||||||
RoutePoint(m2::PointD const & org, std::string const & name) : m_org(org), m_name(name) {}
|
RoutePoint(m2::PointD const & org, std::string const & name) : m_org(org), m_name(name) {}
|
||||||
|
#endif
|
||||||
m2::PointD m_org = m2::PointD::Zero();
|
m2::PointD m_org = m2::PointD::Zero();
|
||||||
std::string m_name;
|
std::string m_name;
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
RouteMarkType m_type;
|
||||||
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
struct SearchRequest
|
struct SearchRequest
|
||||||
@@ -66,6 +82,9 @@ public:
|
|||||||
explicit ParsedMapApi(std::string const & url) { SetUrlAndParse(url); }
|
explicit ParsedMapApi(std::string const & url) { SetUrlAndParse(url); }
|
||||||
|
|
||||||
UrlType SetUrlAndParse(std::string const & url);
|
UrlType SetUrlAndParse(std::string const & url);
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
UrlType ParseGeoNav(std::string const & raw, Framework & fm);
|
||||||
|
#endif
|
||||||
UrlType GetRequestType() const { return m_requestType; }
|
UrlType GetRequestType() const { return m_requestType; }
|
||||||
std::string const & GetGlobalBackUrl() const { return m_globalBackUrl; }
|
std::string const & GetGlobalBackUrl() const { return m_globalBackUrl; }
|
||||||
std::string const & GetAppName() const { return m_appName; }
|
std::string const & GetAppName() const { return m_appName; }
|
||||||
@@ -123,6 +142,9 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
void ParseMapParam(std::string const & key, std::string const & value, bool & correctOrder);
|
void ParseMapParam(std::string const & key, std::string const & value, bool & correctOrder);
|
||||||
|
#if defined(OMIM_OS_MAC) || defined(OMIM_OS_IPHONE)
|
||||||
|
void SetRouteMark(std::string_view const raw, Framework & fm, RouteMarkType const type);
|
||||||
|
#endif
|
||||||
void ParseRouteParam(std::string const & key, std::string const & value, std::vector<std::string_view> & pattern);
|
void ParseRouteParam(std::string const & key, std::string const & value, std::vector<std::string_view> & pattern);
|
||||||
void ParseSearchParam(std::string const & key, std::string const & value);
|
void ParseSearchParam(std::string const & key, std::string const & value);
|
||||||
void ParseInAppFeatureHighlightParam(std::string const & key, std::string const & value);
|
void ParseInAppFeatureHighlightParam(std::string const & key, std::string const & value);
|
||||||
|
|||||||
@@ -470,10 +470,10 @@ void RoutingManager::OnLocationUpdate(location::GpsInfo const & info)
|
|||||||
RouterType RoutingManager::GetBestRouter(m2::PointD const & startPoint, m2::PointD const & finalPoint) const
|
RouterType RoutingManager::GetBestRouter(m2::PointD const & startPoint, m2::PointD const & finalPoint) const
|
||||||
{
|
{
|
||||||
// todo Implement something more sophisticated here (or delete the method).
|
// todo Implement something more sophisticated here (or delete the method).
|
||||||
return GetLastUsedRouter();
|
return routing::GetLastUsedRouter();
|
||||||
}
|
}
|
||||||
|
|
||||||
RouterType RoutingManager::GetLastUsedRouter() const
|
RouterType routing::GetLastUsedRouter()
|
||||||
{
|
{
|
||||||
string routerTypeStr;
|
string routerTypeStr;
|
||||||
if (!settings::Get(kRouterTypeKey, routerTypeStr))
|
if (!settings::Get(kRouterTypeKey, routerTypeStr))
|
||||||
|
|||||||
@@ -40,6 +40,7 @@ class CountryInfoGetter;
|
|||||||
namespace routing
|
namespace routing
|
||||||
{
|
{
|
||||||
class NumMwmIds;
|
class NumMwmIds;
|
||||||
|
RouterType GetLastUsedRouter();
|
||||||
}
|
}
|
||||||
|
|
||||||
class DataSource;
|
class DataSource;
|
||||||
@@ -172,7 +173,6 @@ public:
|
|||||||
m2::PointD GetRouteEndPoint() const { return m_routingSession.GetEndPoint(); }
|
m2::PointD GetRouteEndPoint() const { return m_routingSession.GetEndPoint(); }
|
||||||
/// Returns the most situable router engine type.
|
/// Returns the most situable router engine type.
|
||||||
routing::RouterType GetBestRouter(m2::PointD const & startPoint, m2::PointD const & finalPoint) const;
|
routing::RouterType GetBestRouter(m2::PointD const & startPoint, m2::PointD const & finalPoint) const;
|
||||||
routing::RouterType GetLastUsedRouter() const;
|
|
||||||
void SetLastUsedRouter(routing::RouterType type);
|
void SetLastUsedRouter(routing::RouterType type);
|
||||||
// Sound notifications for turn instructions.
|
// Sound notifications for turn instructions.
|
||||||
void EnableTurnNotifications(bool enable) { m_routingSession.EnableTurnNotifications(enable); }
|
void EnableTurnNotifications(bool enable) { m_routingSession.EnableTurnNotifications(enable); }
|
||||||
|
|||||||
@@ -579,6 +579,11 @@ std::string GetCurrentMapLanguage()
|
|||||||
return languageCode;
|
return languageCode;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::string GetMostPreferredLang()
|
||||||
|
{
|
||||||
|
return std::string(StringUtf8Multilang::GetLangByCode(GetPreferredLangIndexes()[0]));
|
||||||
|
}
|
||||||
|
|
||||||
std::vector<int8_t> GetPreferredLangIndexes()
|
std::vector<int8_t> GetPreferredLangIndexes()
|
||||||
{
|
{
|
||||||
std::vector<int8_t> langs = {};
|
std::vector<int8_t> langs = {};
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ std::string GetCurrentMapTwine();
|
|||||||
std::string Normalize(std::string_view lang);
|
std::string Normalize(std::string_view lang);
|
||||||
std::string GetCurrentNorm();
|
std::string GetCurrentNorm();
|
||||||
std::string GetCurrentMapLanguage();
|
std::string GetCurrentMapLanguage();
|
||||||
|
std::string GetMostPreferredLang();
|
||||||
std::vector<int8_t> GetPreferredLangIndexes();
|
std::vector<int8_t> GetPreferredLangIndexes();
|
||||||
|
|
||||||
buffer_vector<std::string, 4> const & GetSystemPreferred();
|
buffer_vector<std::string, 4> const & GetSystemPreferred();
|
||||||
|
|||||||
@@ -49,6 +49,13 @@ bool FromString<string>(string const & strIn, string & strOut)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template <>
|
||||||
|
bool FromString<std::string_view>(string const & strIn, std::string_view & strOut)
|
||||||
|
{
|
||||||
|
strOut = strIn;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
namespace impl
|
namespace impl
|
||||||
{
|
{
|
||||||
template <class T, size_t N>
|
template <class T, size_t N>
|
||||||
|
|||||||
@@ -130,12 +130,14 @@ void QuerySaver::Deserialize(string const & data)
|
|||||||
{
|
{
|
||||||
Length localeLength = ReadPrimitiveFromSource<Length>(reader);
|
Length localeLength = ReadPrimitiveFromSource<Length>(reader);
|
||||||
vector<char> locale(localeLength);
|
vector<char> locale(localeLength);
|
||||||
|
if (locale.size() > 0) {
|
||||||
reader.Read(&locale[0], localeLength);
|
reader.Read(&locale[0], localeLength);
|
||||||
Length stringLength = ReadPrimitiveFromSource<Length>(reader);
|
Length stringLength = ReadPrimitiveFromSource<Length>(reader);
|
||||||
vector<char> str(stringLength);
|
vector<char> str(stringLength);
|
||||||
reader.Read(&str[0], stringLength);
|
reader.Read(&str[0], stringLength);
|
||||||
m_topQueries.emplace_back(make_pair(string(&locale[0], localeLength), string(&str[0], stringLength)));
|
m_topQueries.emplace_back(make_pair(string(&locale[0], localeLength), string(&str[0], stringLength)));
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void QuerySaver::Save()
|
void QuerySaver::Save()
|
||||||
|
|||||||
Reference in New Issue
Block a user