<html>
<head>
<title>待ち合わせMAP</title>
<meta charset="UTF-8">
<link rel="stylesheet" href="https://unpkg.com/leaflet/dist/leaflet.css" />
<style>
body { font-family: sans-serif; text-align: center; }
#map { height: 500px; width: 90%; margin: 20px auto; border: 2px solid #aaa; }
button { padding: 10px 20px; font-size: 16px; margin-top: 10px; }
#nearest { font-size: 18px; margin-top: 15px; color: #333; font-weight: bold; }
</style>
</head>
<body>
<h1>現在地と近くの駅を表示</h1>
<button onclick="getLocation()">現在地を取得して表示</button>
<div id="map"></div>
<p id="nearest"></p> <!-- ★ここに最寄り駅を表示 -->
<script src="https://unpkg.com/leaflet/dist/leaflet.js"></script>
<script>
let map = L.map('map').setView([35.6812, 139.7671], 13); // 初期位置:東京駅
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
attribution: '© OpenStreetMap contributors'
}).addTo(map);
function getLocation() {
if (navigator.geolocation) {
navigator.geolocation.getCurrentPosition(showPosition, showError);
} else {
alert("このブラウザでは位置情報が使えません。");
}
}
function showPosition(position) {
const lat = position.coords.latitude;
const lon = position.coords.longitude;
map.setView([lat, lon], 15);
// 現在地マーカー
L.marker([lat, lon]).addTo(map)
.bindPopup("📍 あなたの現在地").openPopup();
searchStations(lat, lon, 2000); // 最初は2kmで検索
}
// ★ 駅検索関数
function searchStations(lat, lon, radius) {
const overpassUrl = `https://overpass-api.de/api/interpreter?data=[out:json];node["railway"="station"](around:${radius},${lat},${lon});out;`;
fetch(overpassUrl)
.then(response => response.json())
.then(data => {
if (data.elements.length === 0 && radius < 10000) {
console.log(`駅が見つかりません。範囲を広げます: ${radius}m → ${radius * 2}m`);
searchStations(lat, lon, radius * 2);
return;
}
if (data.elements.length === 0) {
document.getElementById("nearest").textContent = "10km以内に駅が見つかりませんでした。";
return;
}
// 駅マーカーを追加
data.elements.forEach(station => {
const name = station.tags.name || "駅名不明";
const sLat = station.lat;
const sLon = station.lon;
L.marker([sLat, sLon]).addTo(map)
.bindPopup(`🚉 ${name}`);
});
// ★ 最寄り駅を特定
const nearest = findNearestStation(lat, lon, data.elements);
if (nearest) {
const nearestName = nearest.tags.name || "駅名不明";
document.getElementById("nearest").textContent =
`現在地から近い駅は「${nearestName}駅」です!`;
}
})
.catch(err => {
console.error(err);
alert("駅情報の取得に失敗しました。");
});
}
// ★ 最寄り駅を探す関数(距離を計算)
function findNearestStation(lat, lon, stations) {
let nearest = null;
let minDistance = Infinity;
stations.forEach(station => {
const sLat = station.lat;
const sLon = station.lon;
const distance = getDistance(lat, lon, sLat, sLon);
if (distance < minDistance) {
minDistance = distance;
nearest = station;
}
});
return nearest;
}
// ★ 2点間の距離をメートルで返す(Haversine formula)
function getDistance(lat1, lon1, lat2, lon2) {
const R = 6371000; // 地球の半径 (m)
const dLat = (lat2 - lat1) * Math.PI / 180;
const dLon = (lon2 - lon1) * Math.PI / 180;
const a =
Math.sin(dLat / 2) * Math.sin(dLat / 2) +
Math.cos(lat1 * Math.PI / 180) *
Math.cos(lat2 * Math.PI / 180) *
Math.sin(dLon / 2) * Math.sin(dLon / 2);
const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
return R * c;
}
function showError(error) {
alert("位置情報を取得できませんでした: " + error.message);
}
</script>
</body>
</html>