首先說明以下代碼適合有前端基礎知識的同學。
以下是css和html部分
<!DOCTYPE html>
<html lang="zh-CN">
? ? <!-- lang是用來申明語言類型,這里申明為中文(zh)中國大陸(CN)
? ? ?補充中文繁體為zh-TW -->
<head>
? ? <meta charset="UTF-8">
? ? <meta name="viewport" content="width=device-width, initial-scale=1.0">
? ? <title>騰訊地圖逆地址解析</title>
? ? <script src="https://map.qq.com/api/gljs?v=1.exp&key=你的key&libraries=service"></script>
? ? <!--接口地址的引入,加 &libraries=service,為了避免location格式錯誤 ?-->
? ? <style>
? ? ? ? :root {
? ? ? ? ? ? /* 在根元素的偽類中自定義了一些顏色,方便后續引用 */
? ? ? ? ? ? /* 放在:root中,是因為它是全局屬性 */
? ? ? ? ? ? --primary: #1a2980;
? ? ? ? ? ? --secondary: #26d0ce;
? ? ? ? ? ? --light: #f8f9ff;
? ? ? ? ? ? --dark: #0f1a5c;
? ? ? ? ? ? --success: #2ecc71;
? ? ? ? ? ? --danger: #e74c3c;
? ? ? ? ? ? --warning: #f39c12;
? ? ? ? }
? ? ? ?
? ? ? ? * {
? ? ? ? ? ? box-sizing: border-box;
? ? ? ? ? ? /* 防止盒子被撐大 */
? ? ? ? ? ? margin: 0;
? ? ? ? ? ? padding: 0;
? ? ? ? ? ? /* 清除默認格式 */
? ? ? ? ? ? font-family: 'Segoe UI', 'Microsoft YaHei', sans-serif;
? ? ? ? }
? ? ? ?
? ? ? ? body {
? ? ? ? ? ? background: linear-gradient(135deg, var(--primary), var(--secondary));
? ? ? ? ? ? /* 漸變背景 */
? ? ? ? ? ? color: #333;
? ? ? ? ? ? min-height: 100vh;
? ? ? ? ? ? padding: 20px;
? ? ? ? ? ? display: flex;
? ? ? ? ? ? justify-content: center;
? ? ? ? ? ? align-items: center;
? ? ? ? }
? ? ? ?
? ? ? ? .container {
? ? ? ? ? ? width: 100%;
? ? ? ? ? ? max-width: 1000px;
? ? ? ? ? ? background: rgba(255, 255, 255, 0.95);
? ? ? ? ? ? border-radius: 16px;
? ? ? ? ? ? box-shadow: 0 12px 40px rgba(0, 0, 0, 0.25);
? ? ? ? ? ? overflow: hidden;
? ? ? ? ? ? display: flex;
? ? ? ? ? ? flex-direction: column;
? ? ? ? }
? ? ? ?
? ? ? ? header {
? ? ? ? ? ? background: var(--primary);
? ? ? ? ? ? /* 自定義引用變量 */
? ? ? ? ? ? background: linear-gradient(90deg, var(--primary), var(--secondary));
? ? ? ? ? ? color: white;
? ? ? ? ? ? padding: 25px;
? ? ? ? ? ? text-align: center;
? ? ? ? ? ? position: relative;
? ? ? ? ? ? overflow: hidden;
? ? ? ? }
? ? ? ?
? ? ? ? header::before {
? ? ? ? ? ? content: "";
? ? ? ? ? ? position: absolute;
? ? ? ? ? ? top: -50px;
? ? ? ? ? ? left: -50px;
? ? ? ? ? ? width: 150px;
? ? ? ? ? ? height: 150px;
? ? ? ? ? ? border-radius: 50%;
? ? ? ? ? ? background: rgba(255, 255, 255, 0.1);
? ? ? ? }
? ? ? ?
? ? ? ? header::after {
? ? ? ? ? ? content: "";
? ? ? ? ? ? position: absolute;
? ? ? ? ? ? bottom: -30px;
? ? ? ? ? ? right: -30px;
? ? ? ? ? ? width: 100px;
? ? ? ? ? ? height: 100px;
? ? ? ? ? ? border-radius: 50%;
? ? ? ? ? ? background: rgba(255, 255, 255, 0.1);
? ? ? ? }
? ? ? ?
? ? ? ? h1 {
? ? ? ? ? ? font-size: 32px;
? ? ? ? ? ? margin-bottom: 10px;
? ? ? ? ? ? position: relative;
? ? ? ? ? ? z-index: 2;
? ? ? ? }
? ? ? ?
? ? ? ? .subtitle {
? ? ? ? ? ? font-size: 17px;
? ? ? ? ? ? opacity: 0.9;
? ? ? ? ? ? position: relative;
? ? ? ? ? ? z-index: 2;
? ? ? ? }
? ? ? ?
? ? ? ? .content {
? ? ? ? ? ? display: flex;
? ? ? ? ? ? flex-wrap: wrap;
? ? ? ? ? ? /* flex-wrap: nowrap | wrap | wrap-reverse;
? ? ? ? ? ? 當一行排不下時,允許換行 */
? ? ? ? ? ? padding: 20px;
? ? ? ? }
? ? ? ?
? ? ? ? .input-section {
? ? ? ? ? ? flex: 1;
? ? ? ? ? ? min-width: 300px;
? ? ? ? ? ? padding: 20px;
? ? ? ? }
? ? ? ?
? ? ? ? .map-section {
? ? ? ? ? ? flex: 1;
? ? ? ? ? ? min-width: 300px;
? ? ? ? ? ? height: 400px;
? ? ? ? ? ? border-radius: 10px;
? ? ? ? ? ? overflow: hidden;
? ? ? ? ? ? background: #f0f0f0;
? ? ? ? ? ? position: relative;
? ? ? ? ? ? box-shadow: 0 4px 15px rgba(0, 0, 0, 0.1);
? ? ? ? }
? ? ? ?
? ? ? ? #map {
? ? ? ? ? ? width: 100%;
? ? ? ? ? ? height: 100%;
? ? ? ? }
? ? ? ?
? ? ? ? .input-group {
? ? ? ? ? ? margin-bottom: 25px;
? ? ? ? }
? ? ? ?
? ? ? ? label {
? ? ? ? ? ? display: block;
? ? ? ? ? ? margin-bottom: 8px;
? ? ? ? ? ? font-weight: 600;
? ? ? ? ? ? color: var(--primary);
? ? ? ? ? ? font-size: 16px;
? ? ? ? }
? ? ? ?
? ? ? ? input {
? ? ? ? ? ? width: 100%;
? ? ? ? ? ? padding: 14px 18px;
? ? ? ? ? ? border: 2px solid #dde4ff;
? ? ? ? ? ? border-radius: 10px;
? ? ? ? ? ? font-size: 17px;
? ? ? ? ? ? transition: all 0.3s;
? ? ? ? ? ? background: #f8f9ff;
? ? ? ? }
? ? ? ?
? ? ? ? input:focus {
? ? ? ? ? ? border-color: var(--primary);
? ? ? ? ? ? outline: none;
? ? ? ? ? ? box-shadow: 0 0 0 3px rgba(26, 41, 128, 0.2);
? ? ? ? }
? ? ? ?
? ? ? ? .button-group {
? ? ? ? ? ? display: flex;
? ? ? ? ? ? gap: 15px;
? ? ? ? ? ? margin-top: 30px;
? ? ? ? }
? ? ? ?
? ? ? ? button {
? ? ? ? ? ? flex: 1;
? ? ? ? ? ? padding: 15px;
? ? ? ? ? ? border: none;
? ? ? ? ? ? border-radius: 10px;
? ? ? ? ? ? font-size: 17px;
? ? ? ? ? ? font-weight: 600;
? ? ? ? ? ? cursor: pointer;
? ? ? ? ? ? transition: all 0.3s;
? ? ? ? ? ? display: flex;
? ? ? ? ? ? align-items: center;
? ? ? ? ? ? justify-content: center;
? ? ? ? ? ? gap: 8px;
? ? ? ? }
? ? ? ?
? ? ? ? button i {
? ? ? ? ? ? font-size: 20px;
? ? ? ? }
? ? ? ?
? ? ? ? #parseBtn {
? ? ? ? ? ? background: var(--primary);
? ? ? ? ? ? color: white;
? ? ? ? }
? ? ? ?
? ? ? ? #getLocationBtn {
? ? ? ? ? ? background: var(--secondary);
? ? ? ? ? ? color: white;
? ? ? ? }
? ? ? ?
? ? ? ? button:hover {
? ? ? ? ? ? transform: translateY(-3px);
? ? ? ? ? ? box-shadow: 0 6px 15px rgba(0, 0, 0, 0.15);
? ? ? ? }
? ? ? ?
? ? ? ? #parseBtn:hover {
? ? ? ? ? ? background: var(--dark);
? ? ? ? }
? ? ? ?
? ? ? ? #getLocationBtn:hover {
? ? ? ? ? ? background: #1db9b7;
? ? ? ? }
? ? ? ?
? ? ? ? .result-section {
? ? ? ? ? ? padding: 25px;
? ? ? ? ? ? background: var(--light);
? ? ? ? ? ? border-radius: 12px;
? ? ? ? ? ? margin-top: 25px;
? ? ? ? ? ? border: 1px solid #e0e7ff;
? ? ? ? ? ? box-shadow: 0 4px 10px rgba(0, 0, 0, 0.05);
? ? ? ? }
? ? ? ?
? ? ? ? .result-title {
? ? ? ? ? ? font-size: 22px;
? ? ? ? ? ? color: var(--primary);
? ? ? ? ? ? margin-bottom: 20px;
? ? ? ? ? ? padding-bottom: 12px;
? ? ? ? ? ? border-bottom: 3px solid var(--primary);
? ? ? ? ? ? display: flex;
? ? ? ? ? ? align-items: center;
? ? ? ? ? ? gap: 10px;
? ? ? ? }
? ? ? ?
? ? ? ? .result-grid {
? ? ? ? ? ? display: grid;
? ? ? ? ? ? grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
? ? ? ? ? ? gap: 20px;
? ? ? ? }
? ? ? ?
? ? ? ? .result-item {
? ? ? ? ? ? background: white;
? ? ? ? ? ? padding: 20px;
? ? ? ? ? ? border-radius: 10px;
? ? ? ? ? ? box-shadow: 0 3px 8px rgba(0, 0, 0, 0.06);
? ? ? ? ? ? border-left: 4px solid var(--primary);
? ? ? ? ? ? transition: transform 0.3s;
? ? ? ? }
? ? ? ?
? ? ? ? .result-item:hover {
? ? ? ? ? ? transform: translateY(-5px);
? ? ? ? }
? ? ? ?
? ? ? ? .result-label {
? ? ? ? ? ? font-size: 15px;
? ? ? ? ? ? color: #666;
? ? ? ? ? ? margin-bottom: 8px;
? ? ? ? ? ? display: flex;
? ? ? ? ? ? align-items: center;
? ? ? ? ? ? gap: 6px;
? ? ? ? }
? ? ? ?
? ? ? ? .result-value {
? ? ? ? ? ? font-size: 19px;
? ? ? ? ? ? font-weight: 700;
? ? ? ? ? ? color: var(--primary);
? ? ? ? ? ? word-break: break-all;
? ? ? ? ? ? /* 用于控制文本換行規則的屬性,可將單詞拆開,避免溢出 */
? ? ? ? }
? ? ? ?
? ? ? ? .address-value {
? ? ? ? ? ? font-size: 22px;
? ? ? ? ? ? color: var(--danger);
? ? ? ? ? ? font-weight: 800;
? ? ? ? }
? ? ? ?
? ? ? ? .loading {
? ? ? ? ? ? text-align: center;
? ? ? ? ? ? padding: 25px;
? ? ? ? ? ? display: none;
? ? ? ? }
? ? ? ?
? ? ? ? .spinner {
? ? ? ? ? ? border: 5px solid rgba(0, 0, 0, 0.1);
? ? ? ? ? ? border-top: 5px solid var(--primary);
? ? ? ? ? ? border-radius: 50%;
? ? ? ? ? ? width: 50px;
? ? ? ? ? ? height: 50px;
? ? ? ? ? ? animation: spin 1s linear infinite;
? ? ? ? ? ? /* animation和@keyframes連用 */
? ? ? ? ? ? margin: 0 auto 20px;
? ? ? ? }
? ? ? ?
? ? ? ? @keyframes spin {
? ? ? ? ? ? /* spin是動畫名稱,用來實現自轉 */
? ? ? ? ? ? 0% { transform: rotate(0deg); }
? ? ? ? ? ? 100% { transform: rotate(360deg); }
? ? ? ? }
? ? ? ?
? ? ? ? .error {
? ? ? ? ? ? color: var(--danger);
? ? ? ? ? ? background: rgba(231, 76, 60, 0.1);
? ? ? ? ? ? padding: 18px;
? ? ? ? ? ? border-radius: 10px;
? ? ? ? ? ? margin-top: 20px;
? ? ? ? ? ? display: none;
? ? ? ? ? ? border-left: 4px solid var(--danger);
? ? ? ? ? ? font-weight: 500;
? ? ? ? }
? ? ? ?
? ? ? ? footer {
? ? ? ? ? ? text-align: center;
? ? ? ? ? ? padding: 20px;
? ? ? ? ? ? color: #666;
? ? ? ? ? ? font-size: 15px;
? ? ? ? ? ? border-top: 1px solid #eee;
? ? ? ? }
? ? ? ? ? ? ? ?
? ? ? ? @media (max-width: 768px) {
? ? ? ? ? ? .content {
? ? ? ? ? ? ? ? flex-direction: column;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? .input-section, .map-section {
? ? ? ? ? ? ? ? width: 100%;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? h1 {
? ? ? ? ? ? ? ? font-size: 28px;
? ? ? ? ? ? }
? ? ? ? }
? ? ? ? /* 響應式設計 */
? ? </style>
? ? <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css">
? ? <!-- Font Awesome 圖標庫 的 CSS 文件地址 -->
? ? ?<!-- 里面提供了大量可自定義圖標 -->
</head>
<body>
? ? <div class="container">
? ? ? ? <header>
? ? ? ? ? ? <h1><i class="fas fa-map-marked-alt"></i> 騰訊地圖逆地址解析</h1>
? ? ? ? ? ? <!-- 這里的i標簽用來包裹字體圖標(如 Font Awesome),成為圖標占位符 -->
? ? ? ? ? ? ?<!-- 一般斜體不用i,用em或者font-style: italic; -->
? ? ? ? ? ? ? <!-- 如果用i除了上面一種情況外,還有就是i標簽包裹的內容語氣或者性質與旁文不同 -->
? ? ? ? ? ? <div class="subtitle">GPS經緯度轉換為詳細地址信息</div>
? ? ? ? </header>
? ? ? ?
? ? ? ? <div class="content">
? ? ? ? ? ? <div class="input-section">
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? <div class="input-group">
? ? ? ? ? ? ? ? ? ? <label for="latitude"><i class="fas fa-latitude"></i> 緯度</label>
? ? ? ? ? ? ? ? ? ? <input type="text" id="latitude" placeholder="例如:39.908823">
? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? <div class="input-group">
? ? ? ? ? ? ? ? ? ? <label for="longitude"><i class="fas fa-longitude"></i> 經度</label>
? ? ? ? ? ? ? ? ? ? <input type="text" id="longitude" placeholder="例如:116.397470">
? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? <div class="button-group">
? ? ? ? ? ? ? ? ? ? <button id="parseBtn"><i class="fas fa-search-location"></i> 解析地址</button>
? ? ? ? ? ? ? ? ? ? <button id="getLocationBtn"><i class="fas fa-location-arrow"></i> 獲取當前位置</button>
? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? <div class="loading" id="loading">
? ? ? ? ? ? ? ? ? ? <div class="spinner"></div>
? ? ? ? ? ? ? ? ? ? <p>正在解析地址信息,請稍候...</p>
? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? <div class="error" id="error">
? ? ? ? ? ? ? ? ? ? <i class="fas fa-exclamation-circle"></i>
? ? ? ? ? ? ? ? ? ? <span id="errorMsg"></span>
? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? <div class="result-section" id="resultSection" style="display: none;">
? ? ? ? ? ? ? ? ? ? <div class="result-title">
? ? ? ? ? ? ? ? ? ? ? ? <i class="fas fa-map-marker-alt"></i>
? ? ? ? ? ? ? ? ? ? ? ? <span>解析結果</span>
? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? <div class="result-grid">
? ? ? ? ? ? ? ? ? ? ? ? <div class="result-item">
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-label"><i class="fas fa-road"></i> 完整地址</div>
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-value address-value" id="fullAddress">-</div>
? ? ? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? ? ? <div class="result-item">
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-label"><i class="fas fa-flag"></i> 國家</div>
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-value" id="nation">-</div>
? ? ? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? ? ? <div class="result-item">
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-label"><i class="fas fa-map"></i> 省份</div>
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-value" id="province">-</div>
? ? ? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? ? ? <div class="result-item">
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-label"><i class="fas fa-city"></i> 城市</div>
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-value" id="city">-</div>
? ? ? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? ? ? <div class="result-item">
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-label"><i class="fas fa-building"></i> 區縣</div>
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-value" id="district">-</div>
? ? ? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? ? ? <div class="result-item">
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-label"><i class="fas fa-street-view"></i> 街道</div>
? ? ? ? ? ? ? ? ? ? ? ? ? ? <div class="result-value" id="street">-</div>
? ? ? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? ? ? </div>
? ? ? ? ? ? </div>
? ? ? ? ? ?
? ? ? ? ? ? <div class="map-section">
? ? ? ? ? ? ? ? <div id="map"></div>
? ? ? ? ? ? </div>
? ? ? ? </div>
? ? ? ?
? ? ? ? <footer>
? ? ? ? ? ? <div>本服務使用騰訊地圖API | 逆地址解析功能</div>
? ? ? ? ? ? <div style="margin-top: 8px; font-size: 13px; color: #888;">
? ? ? ? ? ? ? ? <i class="fas fa-info-circle"></i> 請確保在HTTP/HTTPS協議下使用
? ? ? ? ? ? </div>
? ? ? ? </footer>
? ? </div>
以下是JavaScript部分
? ? <script>
? ? ? ?
? ? ? ?
? ? ? ? // 初始化地圖
? ? ? ? let map;
? ? ? ? let marker;
? ? ? ? let geocoder;
? ? ? ?
? ? ? ? // 頁面加載完成后初始化地圖
? ? ? ? window.onload = function() {
? ? ? ? ? ? // 檢查是否在HTTP/HTTPS協議下運行
? ? ? ? ? ? if (window.location.protocol === 'file:') {
? ? ? ? ? ? ? ? showError('騰訊地圖API不支持在本地文件協議(file://)下使用,請在HTTP/HTTPS協議下運行此頁面');
? ? ? ? ? ? ? ? return;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? // 初始化地圖
? ? ? ? ? ? initMap();
? ? ? ? };
? ? ? ?
? ? ? ? function initMap() {
? ? ? ? ? ? try {
? ? ? ? ? ? ? ? // try捕獲錯誤,無錯則跳過catch
? ? ? ? ? ? ? ? // 默認坐標 - 北京
? ? ? ? ? ? ? ? const center = new TMap.LatLng(39.908823, 116.397470);
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? // 初始化地圖
? ? ? ? ? ? ? ? map = new TMap.Map('map', {
? ? ? ? ? ? ? ? ? ? ?// 騰訊地圖創建地圖實例
? ? ? ? ? ? ? ? ? ? // 格式為map = new TMap.Map(container, options);
? ? ? ? ? ? ? ? ? ? // option除了以下還有rotation,pitch
? ? ? ? ? ? ? ? ? ? center: center,
? ? ? ? ? ? ? ? ? ? zoom: 15,
? ? ? ? ? ? ? ? ? ? // zoom:(3-20)表示地圖的縮放級別,數值越小地圖顯示范圍越大
? ? ? ? ? ? ? ? ? ? viewMode: '2D'
? ? ? ? ? ? ? ? });
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? // 添加標記
? ? ? ? ? ? ? ? marker = new TMap.MultiMarker({
? ? ? ? ? ? ? ? ? ? // 創建多個標記點實例
? ? ? ? ? ? ? ? ? ? map: map,
? ? ? ? ? ? ? ? ? ? // 創建的標記綁在map實例上
? ? ? ? ? ? ? ? ? ? styles: {
? ? ? ? ? ? ? ? ? ? ? ? "marker": new TMap.MarkerStyle({
? ? ? ? ? ? ? ? ? ? ? ? ? ? width: 25,
? ? ? ? ? ? ? ? ? ? ? ? ? ? height: 35,
? ? ? ? ? ? ? ? ? ? ? ? ? ? anchor: {x: 12.5, y: 35},
? ? ? ? ? ? ? ? ? ? ? ? ? ? // 定位點,用于指定標記圖片的哪個點與實際坐標(經緯度)對齊
? ? ? ? ? ? ? ? ? ? ? ? ? ? src: 'https://mapapi.qq.com/web/lbs/javascriptGL/demo/img/marker.png'
? ? ? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? ? ? ? ? })
? ? ? ? ? ? ? ? ? ? },
? ? ? ? ? ? ? ? ? ? geometries: [{
? ? ? ? ? ? ? ? ? ? ? ? id: 'location',
? ? ? ? ? ? ? ? ? ? ? ? styleId: 'marker',
? ? ? ? ? ? ? ? ? ? ? ? position: center
? ? ? ? ? ? ? ? ? ? }]
? ? ? ? ? ? ? ? });
? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? // 初始化地理編碼服務TMap.service.Geocoder()
? ? ? ? ? ? ? ? // 它是騰訊地圖 API 提供的一個服務類,封裝了地理編碼相關的功能
? ? ? ? ? ? ? ? geocoder = new TMap.service.Geocoder();
? ? ? ? ? ? } catch (e) {
? ? ? ? ? ? ? ? // catch處理錯誤
? ? ? ? ? ? ? ? showError(`地圖初始化失敗: ${e.message}`);
? ? ? ? ? ? }
? ? ? ? }
? ? ? ?
? ? ? ? // 獲取DOM元素
? ? ? ? const latitudeInput = document.getElementById('latitude');
? ? ? ? const longitudeInput = document.getElementById('longitude');
? ? ? ? const parseBtn = document.getElementById('parseBtn');
? ? ? ? // 解析地址btn
? ? ? ? const getLocationBtn = document.getElementById('getLocationBtn');
? ? ? ? // 獲取當前地址的btn
? ? ? ? const resultSection = document.getElementById('resultSection');
? ? ? ? // 解析結果
? ? ? ? const loading = document.getElementById('loading');
? ? ? ? const errorElement = document.getElementById('error');
? ? ? ? const errorMsg = document.getElementById('errorMsg');
? ? ? ?
? ? ? ? // 更新結果展示
? ? ? ? function updateResults(data) {
? ? ? ? ? ? document.getElementById('fullAddress').textContent = data.address || '未知';
? ? ? ? ? ? document.getElementById('nation').textContent = data.address_component.nation || '未知';
? ? ? ? ? ? document.getElementById('province').textContent = data.address_component.province || '未知';
? ? ? ? ? ? document.getElementById('city').textContent = data.address_component.city || '未知';
? ? ? ? ? ? document.getElementById('district').textContent = data.address_component.district || '未知';
? ? ? ? ? ? document.getElementById('street').textContent = data.address_component.street || '未知';
? ? ? ? ? ?
? ? ? ? ? ? resultSection.style.display = 'block';
? ? ? ? }
? ? ? ?
? ? ? ? // 顯示錯誤信息
? ? ? ? function showError(message) {
? ? ? ? ? ? errorMsg.textContent = message;
? ? ? ? ? ? errorElement.style.display = 'flex';
? ? ? ? ? ? setTimeout(() => {
? ? ? ? ? ? ? ? errorElement.style.display = 'none';
? ? ? ? ? ? }, 8000);
? ? ? ? }
? ? ? ?
? ? ? ? // 逆地址解析函數
? ? ? ? function reverseGeocode(lat, lng) {
? ? ? ? ? ? // 顯示加載狀態
? ? ? ? ? ? loading.style.display = 'block';
? ? ? ? ? ? resultSection.style.display = 'none';
? ? ? ? ? ? errorElement.style.display = 'none';
? ? ? ? ? ?
? ? ? ? ? ? // 確保地理編碼服務已初始化
? ? ? ? ? ? if (!geocoder) {
? ? ? ? ? ? ? ? try {
? ? ? ? ? ? ? ? ? ? geocoder = new TMap.service.Geocoder();
? ? ? ? ? ? ? ? } catch (e) {
? ? ? ? ? ? ? ? ? ? loading.style.display = 'none';
? ? ? ? ? ? ? ? ? ? showError(`地理編碼服務初始化失敗: ${e.message}`);
? ? ? ? ? ? ? ? ? ? return;
? ? ? ? ? ? ? ? }
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? // 調用逆地址解析
? ? ? ? ? ? geocoder.getAddress({ location: new TMap.LatLng( lat, lng ) })
? ? ? ? ? ? // 接收經緯度地址
? ? ? ? ? ? // getAddress() 是一個異步方法,返回一個 Promise 對象,then() 用于處理請求成功的情況
? ? ? ? ? ? ? ? .then((result) => {
? ? ? ? ? ? ? ? ? ? // 隱藏加載狀態
? ? ? ? ? ? ? ? ? ? loading.style.display = 'none';
? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? ? ? if (result.status === 0) {
? ? ? ? ? ? ? ? ? ? ? ? // status === 0表示解析成功,是騰訊地圖api的規定
? ? ? ? ? ? ? ? ? ? ? ? // 更新結果展示
? ? ? ? ? ? ? ? ? ? ? ? updateResults(result.result);
? ? ? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? ? ? ? ? // 更新地圖位置
? ? ? ? ? ? ? ? ? ? ? ? const newPosition = new TMap.LatLng(lat, lng);
? ? ? ? ? ? ? ? ? ? ? ? map.setCenter(newPosition);
? ? ? ? ? ? ? ? ? ? ? ? marker.setGeometries([{
? ? ? ? ? ? ? ? ? ? ? ? ? ? // 更新標記點
? ? ? ? ? ? ? ? ? ? ? ? ? ? id: 'location',
? ? ? ? ? ? ? ? ? ? ? ? ? ? styleId: 'marker',
? ? ? ? ? ? ? ? ? ? ? ? ? ? position: newPosition
? ? ? ? ? ? ? ? ? ? ? ? }]);
? ? ? ? ? ? ? ? ? ? } else {
? ? ? ? ? ? ? ? ? ? ? ? showError(`解析失敗: ${result.message}`);
? ? ? ? ? ? ? ? ? ? }
? ? ? ? ? ? ? ? })
? ? ? ? ? ? ? ? .catch((error) => {
? ? ? ? ? ? ? ? ? ? loading.style.display = 'none';
? ? ? ? ? ? ? ? ? ? showError(`請求失敗: ${error.message}`);
? ? ? ? ? ? ? ? });
? ? ? ? }
? ? ? ?
? ? ? ? // 解析按鈕點擊事件
? ? ? ? parseBtn.addEventListener('click', () => {
? ? ? ? ? ? const lat = parseFloat(latitudeInput.value.trim());
? ? ? ? ? ? const lng = parseFloat(longitudeInput.value.trim());
? ? ? ? ? ?
? ? ? ? ? ? if (isNaN(lat) || isNaN(lng)) {
? ? ? ? ? ? ? ? showError('請輸入有效的經緯度數值');
? ? ? ? ? ? ? ? return;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? if (lat < -90 || lat > 90) {
? ? ? ? ? ? ? ? showError('緯度范圍應在-90到90之間');
? ? ? ? ? ? ? ? return;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? if (lng < -180 || lng > 180) {
? ? ? ? ? ? ? ? showError('經度范圍應在-180到180之間');
? ? ? ? ? ? ? ? return;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? reverseGeocode(lat, lng);
? ? ? ? });
? ? ? ?
? ? ? ? // 獲取當前位置按鈕點擊事件
? ? ? ? getLocationBtn.addEventListener('click', () => {
? ? ? ? ? ? if (!navigator.geolocation) {
? ? ? ? ? ? ? ? showError('您的瀏覽器不支持地理位置服務');
? ? ? ? ? ? ? ? return;
? ? ? ? ? ? }
? ? ? ? ? ?
? ? ? ? ? ? // 顯示加載狀態
? ? ? ? ? ? loading.style.display = 'block';
? ? ? ? ? ? resultSection.style.display = 'none';
? ? ? ? ? ? errorElement.style.display = 'none';
? ? ? ? ? ?
? ? ? ? ? ? navigator.geolocation.getCurrentPosition(
? ? ? ? ? ? ? ? // 這是瀏覽器提供的 獲取用戶當前地理位置 的 API
? ? ? ? ? ? ? ? // 格式navigator.geolocation.getCurrentPosition(定位成功時執行的回調函數(必填),失敗時的,配置)
? ? ? ? ? ? ? ? (position) => {
? ? ? ? ? ? ? ? ? ? // coords是coordinate的縮寫,用到latitude這些表位置的參數時必須用到它
? ? ? ? ? ? ? ? ? ? const lat = position.coords.latitude;
? ? ? ? ? ? ? ? ? ? const lng = position.coords.longitude;
? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? ? ? // 更新輸入框
? ? ? ? ? ? ? ? ? ? latitudeInput.value = lat.toFixed(6);
? ? ? ? ? ? ? ? ? ? longitudeInput.value = lng.toFixed(6);
? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? ? ? ? ? // 進行逆地址解析
? ? ? ? ? ? ? ? ? ? reverseGeocode(lat, lng);
? ? ? ? ? ? ? ? },
? ? ? ? ? ? ? ? (error) => {
? ? ? ? ? ? ? ? ? ? loading.style.display = 'none';
? ? ? ? ? ? ? ? ? ? let errorMessage;
? ? ? ? ? ? ? ? ? ? switch(error.code) {
? ? ? ? ? ? ? ? ? ? ? ? case error.PERMISSION_DENIED:
? ? ? ? ? ? ? ? ? ? ? ? ? ? errorMessage = "用戶拒絕了位置請求";
? ? ? ? ? ? ? ? ? ? ? ? ? ? break;
? ? ? ? ? ? ? ? ? ? ? ? case error.POSITION_UNAVAILABLE:
? ? ? ? ? ? ? ? ? ? ? ? ? ? errorMessage = "位置信息不可用";
? ? ? ? ? ? ? ? ? ? ? ? ? ? break;
? ? ? ? ? ? ? ? ? ? ? ? case error.TIMEOUT:
? ? ? ? ? ? ? ? ? ? ? ? ? ? errorMessage = "獲取位置超時";
? ? ? ? ? ? ? ? ? ? ? ? ? ? break;
? ? ? ? ? ? ? ? ? ? ? ? default:
? ? ? ? ? ? ? ? ? ? ? ? ? ? errorMessage = "煩死了";
? ? ? ? ? ? ? ? ? ? }
? ? ? ? ? ? ? ? ? ? showError(`獲取位置失敗: ${errorMessage}`);
? ? ? ? ? ? ? ? },
? ? ? ? ? ? ? ? {
? ? ? ? ? ? ? ? ? ? enableHighAccuracy: true,
? ? ? ? ? ? ? ? ? ? // 啟用高精度地位
? ? ? ? ? ? ? ? ? ? timeout: 10000,
? ? ? ? ? ? ? ? ? ? // 超時時間
? ? ? ? ? ? ? ? ? ? maximumAge: 300000
? ? ? ? ? ? ? ? ? ? // 允許緩存位置的最大事件
? ? ? ? ? ? ? ? }
? ? ? ? ? ? );
? ? ? ? });
? ? ? ?
? ? ? ? // 示例坐標(北京天安門)
? ? ? ? // latitudeInput.value = "39.908823";
? ? ? ? // longitudeInput.value = "116.397470";
? ? </script>
</body>
</html>
(編者水平有限,還請大家多多指教)