Tài liệu này mô tả cách tìm khách sạn, nhà hàng hoặc trạm xăng dọc theo một tuyến đường đã lên kế hoạch. Bạn sẽ tìm hiểu cách sử dụng API Tuyến đường để lấy một tuyến đường đa tuyến và sử dụng tuyến đường đó với yêu cầu Tìm kiếm dọc theo tuyến đường (SAR) của API Địa điểm. Ngoài ra, bạn sẽ tìm hiểu cách nhận được kết quả tốt nhất bằng cách đặt điểm xuất phát tìm kiếm dọc theo tuyến đường, ví dụ: 2 giờ sau khi bắt đầu chuyến đi.
Routes API
Để tìm kiếm các địa điểm dọc theo tuyến đường, chúng ta sẽ sử dụng Routes API. Dữ liệu tuyến đường từ phản hồi của API Tuyến đường là một loạt toạ độ LatLong từ điểm xuất phát đến điểm đến. Dữ liệu tuyến đường chứa các chặng và bước đi theo mạng lưới đường.
Các tuyến đường cũng được trả về dưới dạng đường đa tuyến được mã hoá. Bạn sẽ truyền đường đa tuyến này dưới dạng tham số đầu vào cho yêu cầu SAR. Mã hoá đường đa tuyến là một thuật toán nén có tổn hao cho phép bạn lưu trữ một loạt toạ độ dưới dạng một chuỗi duy nhất. Bạn không bắt buộc phải lấy đường đa tuyến từ API Tuyến đường. Bạn có thể tự tạo dữ liệu, nhưng đối với mục đích của ví dụ này, Routes API là một cách nhanh chóng và chắc chắn để lấy dữ liệu cần thiết.
Trong hướng dẫn này, chúng ta sử dụng tuyến đường từ London (-37.8167,144.9619) đến Manchester (-37.8155, 144.9663)
Tuyến trong ví dụ: London đến Manchester
Bước 1: Lấy tuyến đường từ Routes API
Để nhận một tuyến đường từ Routes API, bạn cần cung cấp các thông tin sau:
- Vị trí điểm xuất phát và điểm đến
- Phương tiện đi lại (lái xe, đi bộ, v.v.)
- Điểm trung gian bất kỳ (không bắt buộc)
- Mọi lựa chọn ưu tiên (tránh trạm thu phí, tránh đường cao tốc, v.v.)
- Lựa chọn ưu tiên định tuyến có tính đến lưu lượng truy cập sẽ cung cấp cho bạn thông tin ước tính chính xác nhất, nhưng đây là thao tác tính toán nặng hơn và do đó làm tăng độ trễ của phản hồi.
{"origin":{
"location": {
"latLng":{
"latitude": -37.8167,
"longitude": 144.9619
}
}
},
"destination":{
"location": {
"latLng":{
"latitude":-37.8155,
"longitude": 144.9663
}
}
},
"routingPreference":"TRAFFIC_AWARE",
"travelMode":"DRIVE"
}
Khi thực hiện lệnh gọi, hãy nhớ thêm trường "encodedPolyline" vào mặt nạ trường tiêu đề.
headers = {
"Content-Type": "application/json",
"X-Goog-FieldMask": "routes.distanceMeters,routes.duration,routes.legs,routes.polyline.encodedPolyline"
}
Tài liệu đầy đủ có các ví dụ về cách lấy tuyến đường và lấy đa tuyến đường.
Sau khi bạn cung cấp thông tin này trong yêu cầu, Routes API sẽ trả về một đối tượng tuyến đường. Đối tượng tuyến đường sẽ chứa các thông tin sau:
- Tổng quãng đường của tuyến đường
- Tổng thời lượng của tuyến đường
- Các chặng và bước của tuyến đường
- Hình nhiều đường được mã hoá của tuyến đường, chặng và bước.
{
"routes": [
{
"legs": [
{
"distanceMeters": 321799,
"duration": "15401s",
"staticDuration": "14518s",
"polyline": {
"encodedPolyline": "y_kyH`_XOr@q@xKGnBBZ|AlGPj@Y^k@^MEqAfAQLK?eI … <rest of content removed for readability>"
},
"startLocation": {
"latLng": {
"latitude": 51.507334500000006,
"longitude": -0.1280107
}
},
"endLocation": {
"latLng": {
"latitude": 53.4808513,
"longitude": -2.2425864
}
},
"steps": [
{
"distanceMeters": 320,
"staticDuration": "82s",
"polyline": {
"encodedPolyline": "y_kyH`_XOr@q@xKGnBBZ|AlG"
},
"startLocation": {
"latLng": {
"latitude": 51.507334500000006,
"longitude": -0.1280107
}
},
"endLocation": {
"latLng": {
"latitude": 51.507207,
"longitude": -0.1323681
}
},
"navigationInstruction": {
"maneuver": "DEPART",
"instructions": "Head northwest on Trafalgar Sq/A4 toward Spring Gardens\nContinue to follow A4\nLeaving toll zone\nEntering toll zone\nLeaving toll zone in 210m at Haymarket"
},
"localizedValues": {
"distance": {
"text": "0.3 km"
},
"staticDuration": {
"text": "1 min"
}
},
# rest of the response removed for readability
Bước 2: Yêu cầu Tìm kiếm dọc theo tuyến đường
Tìm kiếm bằng văn bản của API Địa điểm có yêu cầu Tìm kiếm dọc theo tuyến đường cho phép bạn tìm kiếm các địa điểm dọc theo một tuyến đường. Để thực hiện yêu cầu Tìm kiếm dọc theo tuyến đường, bạn cần cung cấp những thông tin tối thiểu sau:
- Mặt nạ trường của các trường được trả về trong phản hồi
- Khoá API hợp lệ cho API đã bật trong Google Cloud Console
- Chuỗi văn bản tìm kiếm cho biết những địa điểm bạn đang tìm kiếm, ví dụ: "nhà hàng chay cay"
- Đường đa tuyến được mã hoá của tuyến đường, được truy xuất từ lệnh gọi API Routes trước đó
- URL cho điểm cuối API Tìm kiếm văn bản về địa điểm
import requests
url = 'https://places.googleapis.com/v1/places:searchText'
api_key = 'YOUR_API_KEY' # Replace with your actual API key
route_polyline = 'YOUR_ROUTE_POLYLINE' # Replace with your encoded route polyline
headers = {
'Content-Type': 'application/json',
'X-Goog-Api-Key': api_key,
'X-Goog-FieldMask': 'places.displayName,places.formattedAddress,places.priceLevel'
}
data = {
"textQuery":
"Spicy Vegetarian Food",
"searchAlongRouteParameters": {
"polyline": {
"encodedPolyline": route_polyline
}
}
}
response = requests.post(url, headers=headers, json=data)
Dữ liệu yêu cầu mẫu
Yêu cầu Tìm kiếm dọc theo tuyến đường sẽ trả về danh sách các địa điểm nằm dọc theo tuyến đường. Dưới đây là một phần ngắn của dữ liệu mẫu. Bạn có thể giới hạn độ dài của phản hồi bằng cách đặt số lượng thông số kết quả tối đa và thêm các trường khác, tất nhiên là làm tăng lượng dữ liệu nhận được. Để biết thêm thông tin chi tiết về phản hồi của API Địa điểm, hãy xem tài liệu.
{
"places": [
{
"formattedAddress": "33 Haymarket, London SW1Y 4HA, UK",
"displayName": {
"text": "xxx",
"languageCode": "en"
}
},
{
"formattedAddress": "224 Piccadilly, London W1J 9HP, UK",
"priceLevel": "PRICE_LEVEL_MODERATE",
"displayName": {
"text": "yyy",
"languageCode": "en"
}
},
{
"formattedAddress": "63 Neal St, London WC2H 9PJ, UK",
"displayName": {
"text": "zzz",
"languageCode": "en"
}
},
Dữ liệu phản hồi mẫu
Tóm tắt tuyến đường và thời gian đi đường vòng
Việc chỉ tìm thấy các vị trí là rất tuyệt, nhưng bạn cũng nên thêm thông tin về thời gian cần thiết để đến các vị trí này. SAR trong tính năng Tìm kiếm văn bản của API Địa điểm cũng có thể trả về trường tóm tắt tuyến đường chứa cả thời lượng và quãng đường di chuyển. Trường dữ liệu tóm tắt định tuyến là một phần tử con của thư mục gốc phản hồi, vì vậy, bạn không được đưa tiền tố "places." vào mặt nạ trường.
'X-Goog-FieldMask': 'places.displayName,places.formattedAddress,places.priceLevel,routingSummaries'
Để nhận thông tin tóm tắt, bạn cũng phải cung cấp tham số vị trí gốc cho nội dung tìm kiếm được dùng để tính toán.
"routingParameters": {
"origin": {
"latitude": -37.8167,
"longitude": 144.9619
}
}
Khi bạn nhận được phản hồi, phản hồi đó sẽ có một phần mới với tóm tắt định tuyến chứa đoạn có thời lượng và quãng đường tính bằng mét.
"routingSummaries": [
{
"legs": [
{
"duration": "662s",
"distanceMeters": 3093
}
]
},
Tiếp theo, chúng ta sẽ xem cách xác định vị trí bắt đầu tìm kiếm dọc theo tuyến đường.
Bước 3: Nhận thông tin vị trí 2 giờ dọc theo tuyến đường
Hãy cân nhắc một trường hợp sử dụng thông thường, trong đó người lái xe muốn tìm nhà hàng không phải ở đầu tuyến đường, mà ở phía xa hơn. Trong ví dụ của chúng tôi, chuyến đi từ London đến Manchester mất khoảng 4 giờ. Người lái xe muốn tìm một nhà hàng cách 2 giờ theo tuyến đường. Yêu cầu này sẽ cho chúng ta thời lượng là 120 phút * 60 giây = 7200 giây.
Trong phản hồi của Routes API, chúng ta có thời lượng của mỗi chặng trong tuyến đường và từng bước của một chặng. Hãy nhớ thêm trường "legs" vào mặt nạ trường trong yêu cầu của bạn. Lặp lại các chặng và bước cho đến khi thời lượng tích luỹ đạt đến giới hạn 2 giờ hoặc 7200 giây. Sau đó, chúng ta đã tìm thấy chặng và bước cần đặt làm nguồn gốc của yêu cầu SAR
Để đẩy nhanh công việc, bạn nên thử thư viện đường đa tuyến cho Python. Bạn có thể sử dụng hàm này để lấy toạ độ từ trường dữ liệu "polyline.endodedPolyLine".
Chạy các lệnh sau trong dòng lệnh môi trường.
> pip install polyline
import requests
import polyline
# We've covered getting a Routes API response earlier,
data = response.json()
# Extract the first route and its encoded polyline
route = data["routes"][0]
polyline_points = polyline.decode(route["polyline"]["encodedPolyline"])
# Calculate total duration of the route in seconds
total_duration_seconds = route["duration"]
# Calculate the desired time offset in seconds, 2h = 120 minutes * 60
desired_time_offset_seconds = time_offset_minutes * 60
# Iterate through the legs and steps to find the point at the desired time offset
elapsed_time_seconds = 0
for leg in route["legs"]:
for step in leg["steps"]:
step_duration_seconds = step["staticDuration"]
# Check if the desired time offset falls within this step, remove last "s" from string and convert to int
second_value = int(step_duration_seconds[:-1])
if elapsed_time_seconds + second_value >= desired_time_offset_seconds:
# Interpolate to find the exact point within the step
fraction_of_step = (desired_time_offset_seconds - elapsed_time_seconds) / second_value
step_polyline_points = polyline.decode(step["polyline"]["encodedPolyline"])
index = int(len(step_polyline_points) * fraction_of_step)
return step_polyline_points[index]
elapsed_time_seconds += second_value
# If the point is not found (e.g., time offset exceeds route duration)
return None
Bây giờ, chúng ta đã tìm thấy vị trí trên tuyến đường cách điểm xuất phát 2 giờ, chúng ta có thể sử dụng vị trí đó trong yêu cầu. Bạn chỉ cần thêm vĩ độ và kinh độ vào tham số "origin" (gốc), tham số này lại là một phần của tham số "routingParameters". Bạn nên sử dụng trường dữ liệu "routingSummaries" mà chúng ta đã đề cập trước đó. Bạn cũng có thể thêm các tham số khác như chế độ đi lại và hướng dẫn để tránh đường thu phí nếu muốn.
"routingParameters": {
"origin": {
"latitude": xx.xxxx,
"longitude": yy.yyyy
},
"travelMode":"DRIVE",
"routeModifiers": {
"avoidTolls": true
}
}
Ví dụ về kết quả (biểu tượng ô tô được thêm để cho biết nguồn gốc tìm kiếm).
Như bạn có thể thấy trong hình ảnh, API trả về các địa điểm thiên về cuối tuyến đường, kết quả bắt đầu từ giữa chuyến đi. Tính năng tìm kiếm này vẫn được hỗ trợ bằng cùng một dữ liệu trên Nền tảng Google Maps, trong đó có tính đến mức độ liên quan của địa điểm và khoảng cách cùng với các yếu tố khác.
Lời kết
Trong hướng dẫn này, chúng ta đã tìm hiểu cách kết hợp hai API của Google Maps Platform là Routes và Places để lên kế hoạch cho một chuyến đi và tìm địa điểm ăn uống sau 2 giờ di chuyển. Bạn cần thực hiện các bước sau để lấy một đường đa tuyến được mã hoá chứa toạ độ vĩ độ và kinh độ cho từng bước trên đường đi, đồng thời đặt nguồn yêu cầu Tìm kiếm dọc theo tuyến đường để có được kết quả tốt nhất.
Tính năng này bổ sung một công cụ mới mạnh mẽ cho tính năng tìm kiếm bằng văn bản và tìm kiếm địa điểm lân cận hiện có trong API Địa điểm. Tiếp theo, bạn nên thêm các dịch vụ vị trí để có thể sử dụng vị trí của người lái xe làm điểm xuất phát nhằm tìm nguồn gốc tìm kiếm tối ưu. Ngoài ra, tính năng này sẽ hoạt động hoàn hảo cùng với trợ lý thoại trong ô tô, nơi bạn có thể nói ra các lựa chọn ăn uống mà mình muốn.
Thao tác tiếp theo
- Thử các ví dụ trong tài liệu.
- Để lại ý kiến phản hồi.
Tài liệu đọc thêm được đề xuất:
Người đóng góp
Google duy trì tài liệu này. Tác giả ban đầu của bài viết này là những người đóng góp sau.
Tác giả chính: Mikko Toivanen | Kỹ sư giải pháp Nền tảng Google Maps