Qt編寫地圖之實(shí)現(xiàn)覆蓋物坐標(biāo)和搜索
一、前言
地圖應(yīng)用中有時(shí)候需要開(kāi)啟懸浮工具欄,用戶可以直接在地圖上繪制矩形、多邊形、圓形、線條等,于是需要提供一個(gè)函數(shù)接口,能夠獲取到用戶繪制的這些圖形形狀對(duì)應(yīng)的信息。比如坐標(biāo)點(diǎn)、圓形的中心點(diǎn)和半徑、所有圖形的路徑Path坐標(biāo)點(diǎn)集合,這些信息都是以經(jīng)緯度坐標(biāo)的形式。一般封裝的類似功能的js函數(shù)一般有三種要求,第一種傳入空值則表示找出所有覆蓋物,第二種傳入類型則找出所有該類型的覆蓋物比如矩形,第三種傳入對(duì)象名稱則找出符合該名稱的。從一堆覆蓋物中找到符合指定類型的覆蓋物,這個(gè)對(duì)于初學(xué)者是難點(diǎn),可以通過(guò)map.getOverlays()拿到所有的覆蓋物,最開(kāi)始我想的策略是如何拿到對(duì)應(yīng)一個(gè)覆蓋物的類型,后面發(fā)現(xiàn)toString()可以獲取到[object Marker] [object Circle] [object Overlay]字樣,于是針對(duì)這個(gè)去過(guò)濾類型,后面發(fā)現(xiàn)js通用關(guān)鍵字instanceof也可以實(shí)現(xiàn)這個(gè)功能,比如if (overlay instanceof BMap.Circle)就可以判斷當(dāng)前覆蓋物是否是圓形。
地圖模塊中很多個(gè)地方都用到了將getPath函數(shù)獲取到的路徑轉(zhuǎn)換成坐標(biāo)點(diǎn)集合字符串傳出去,比如發(fā)給Qt程序處理,所以封裝了一個(gè)通用的轉(zhuǎn)換函數(shù),專門將路徑轉(zhuǎn)成字符串的坐標(biāo)點(diǎn)集合,經(jīng)度和緯度之間用英文逗號(hào) , 隔開(kāi),做個(gè)坐標(biāo)之間用英文分號(hào) ; 隔開(kāi),多個(gè)不同的參數(shù)值用英文豎杠 | 隔開(kāi),這個(gè)統(tǒng)一的規(guī)則在所有函數(shù)和交互中都通用。比如在早期的webkit內(nèi)核的瀏覽器控件中,就無(wú)法將數(shù)組的數(shù)組傳出來(lái),于是就要轉(zhuǎn)成萬(wàn)能的字符串組合數(shù)據(jù)。
二、功能特點(diǎn)
1 省市區(qū)域地圖封裝類功能特點(diǎn)
- 同時(shí)支持閃爍點(diǎn)圖、遷徙圖、區(qū)域地圖、世界地圖、儀表盤等。
- 可以設(shè)置標(biāo)題、提示信息、背景顏色、文字顏色、線條顏色、區(qū)域顏色等各種顏色。
- 可設(shè)置城市的名稱、值、經(jīng)緯度 集合。
- 可設(shè)置地圖的放大倍數(shù)、是否允許鼠標(biāo)滾輪縮放。
- 內(nèi)置世界地圖、全國(guó)地圖、省份地圖、地區(qū)地圖,可以精確到縣,所有地圖全部離線使用。
- 內(nèi)置了各省市json數(shù)據(jù)文件轉(zhuǎn)js文件功能,如有數(shù)據(jù)更新自行轉(zhuǎn)換即可,支持單個(gè)文件轉(zhuǎn)換和一鍵轉(zhuǎn)換所有文件。
- 內(nèi)置了從json文件或者js文件獲取該區(qū)域的所有名稱和經(jīng)緯度信息集合的功能,可以通過(guò)該方法獲取到信息用來(lái)顯示。
- 依賴瀏覽器組件顯示地圖,提供的demo支持webkit/webengine/miniblink/ie 多種方式加載網(wǎng)頁(yè)。
- 采用miniblink瀏覽器內(nèi)核打通了Qt5.6及后續(xù)版本+mingw編譯器缺少瀏覽器模塊的遺憾,使得整個(gè)項(xiàng)目支持所有Qt版本,親測(cè)4.7到6.2等任意版本。
- 閃爍點(diǎn)遷徙圖等設(shè)置的點(diǎn)支持單獨(dú)設(shè)置顏色。
- 提供接口直接獲取點(diǎn)擊的點(diǎn)相關(guān)信息,方便程序聯(lián)動(dòng)處理。
- 拓展性極強(qiáng),可以依葫蘆畫瓢自行增加各種精美的echarts組件,做出牛逼的效果。
- 內(nèi)置的儀表盤組件提供交互功能,demo演示中包含了對(duì)應(yīng)的代碼。
- 函數(shù)接口友好和統(tǒng)一,使用簡(jiǎn)單方便,就一個(gè)類。
- 支持任意Qt版本、任意系統(tǒng)、任意編譯器。
2 百度地圖封裝類功能特點(diǎn)
- 同時(shí)支持在線地圖和離線地圖兩種模式。
- 同時(shí)支持webkit內(nèi)核、webengine內(nèi)核、miniblink內(nèi)核、IE內(nèi)核。
- 支持設(shè)置多個(gè)標(biāo)注點(diǎn),信息包括名稱、地址、經(jīng)緯度。
- 可設(shè)置地圖是否可單擊、拖動(dòng)、鼠標(biāo)滾輪縮放。
- 可設(shè)置協(xié)議版本、秘鑰、主題樣式、中心坐標(biāo)、中心城市、地理編碼位置等。
- 可設(shè)置地圖縮放比例和級(jí)別,縮略圖、比例尺、路況信息等控件的可見(jiàn)。
- 支持地圖交互,比如鼠標(biāo)按下獲取對(duì)應(yīng)位置的經(jīng)緯度。
- 支持查詢路線,可設(shè)置起點(diǎn)位置、終點(diǎn)位置、路線模式、路線方式、路線方案(最少時(shí)間、最少換乘、最少步行、不乘地鐵、最短距離、避開(kāi)高速)。
- 可顯示點(diǎn)線面工具,可直接在地圖上劃線、點(diǎn)、矩形、圓形等。
- 可設(shè)置行政區(qū)劃,指定某個(gè)城市區(qū)域繪制圖層,在線地圖自動(dòng)輸出行政區(qū)劃邊界點(diǎn)集合到j(luò)s文件給離線地圖使用。
- 可靜態(tài)或者動(dòng)態(tài)添加多個(gè)覆蓋物。支持點(diǎn)、折線、多邊形、矩形、圓形、弧線、點(diǎn)聚合等。
- 提供函數(shù)接口處理經(jīng)緯度解析成地址和地址解析成經(jīng)緯度坐標(biāo)。
- 提供的demo直接可以單獨(dú)選點(diǎn)執(zhí)行對(duì)應(yīng)的處理比如路線查詢。
- 可以拿到路線查詢到的點(diǎn)坐標(biāo)信息集合,比如用于機(jī)器人坐標(biāo)導(dǎo)航等。
- 封裝了豐富的函數(shù)比如刪除指定點(diǎn)和所有點(diǎn),刪除指定覆蓋物和所有覆蓋物等。
- 標(biāo)注點(diǎn)彈框信息可以自定義內(nèi)容,標(biāo)準(zhǔn)html格式。
- 標(biāo)注點(diǎn)單擊事件可選 0-不處理 1-自己彈框 2-發(fā)送信號(hào)。
- 標(biāo)注點(diǎn)可設(shè)置動(dòng)畫效果 0-不處理 1-跳動(dòng) 2-墜落
- 標(biāo)注點(diǎn)可設(shè)置本地圖片文件等。
- 函數(shù)接口友好和統(tǒng)一,使用簡(jiǎn)單方便,就一個(gè)類。
- 支持js動(dòng)態(tài)交互添加點(diǎn)、刪除點(diǎn)、清空點(diǎn)、重置點(diǎn),不需要刷新頁(yè)面。
- 支持任意Qt版本、任意系統(tǒng)、任意編譯器。
3 離線地圖下載類功能特點(diǎn)
- 多線程同步下載多級(jí)別瓦片地圖,不卡界面。
- 內(nèi)置多個(gè)離線地圖下載請(qǐng)求地址,自動(dòng)隨機(jī)選擇一個(gè)發(fā)送請(qǐng)求。
- 下載地圖類型同時(shí)支持街道圖和衛(wèi)星圖。
- 自動(dòng)計(jì)算可視區(qū)域或者行政區(qū)域的下載瓦片數(shù)量。
- 下載的級(jí)別可以自定義范圍和選擇。
- 每個(gè)瓦片下載完成都發(fā)送信號(hào)通知,參數(shù)包括下載用時(shí)。
- 可設(shè)置下載最大超時(shí)時(shí)間,超過(guò)了則丟棄跳到下一個(gè)下載任務(wù)。
- 實(shí)時(shí)顯示下載進(jìn)度,以及當(dāng)前級(jí)別已經(jīng)下載的瓦片數(shù)和總瓦片數(shù)。
- 下載過(guò)程中可以停止下載,下載完成自動(dòng)統(tǒng)計(jì)總用時(shí)。
- 內(nèi)置經(jīng)緯度和屏幕坐標(biāo)互相轉(zhuǎn)換函數(shù)。
- 目前支持百度地圖,其他地圖比如谷歌地圖、騰訊地圖、高德地圖可以定制。
- 函數(shù)接口友好和統(tǒng)一,使用簡(jiǎn)單方便,就一個(gè)類。
- 支持任意Qt版本、任意系統(tǒng)、任意編譯器。
4 省市輪廓下載類功能特點(diǎn)
- 定時(shí)器排隊(duì)下載省市輪廓圖點(diǎn)坐標(biāo)集合存儲(chǔ)到JS文件。
- 支持一個(gè)行政區(qū)域多個(gè)不規(guī)則區(qū)域下載。
- 自動(dòng)計(jì)算行政區(qū)域的下載輪廓數(shù)量。
- 可精確選擇省份、市區(qū)、縣城,也可直接輸入行政區(qū)域的名稱。
- 可以設(shè)置下載間隔、隨時(shí)開(kāi)始下載和停止下載。
- 提供編輯邊界功能,可以直接在地圖上編輯好不規(guī)則區(qū)域的點(diǎn)集合,然后獲取邊界點(diǎn)集合數(shù)據(jù),這個(gè)可以用來(lái)自己繪制區(qū)域拿到數(shù)據(jù),比如某個(gè)鄉(xiāng)鎮(zhèn)甚至某個(gè)小區(qū)的行政區(qū)域數(shù)據(jù),很牛逼。
三、體驗(yàn)地址
體驗(yàn)地址:https://pan.baidu.com/s/15ZKAlptW-rDcNq8zlzdYLg 提取碼:uyes 文件名:bin_map.zip
國(guó)內(nèi)站點(diǎn):https://gitee.com/feiyangqingyun
國(guó)際站點(diǎn):https://github.com/feiyangqingyun
四、效果圖
五、相關(guān)代碼
void MapBaiDu::addLocalSearch(QStringList &list) { //全局搜索對(duì)象 結(jié)果可選顯示在地圖中還是異步通知 #if 1 list << QString(" var searchOptions = {renderOptions:{map: map}};"); #else list << QString(" var searchOptions = {"); list << QString(" onSearchComplete: function(results) {"); list << QString(" if (local.getStatus() != BMAP_STATUS_SUCCESS) {"); list << QString(" return;"); list << QString(" }"); list << QString(" var result = [];"); list << QString(" var count = results.getCurrentNumPois();"); list << QString(" for (var i = 0; i < count; ++i) {"); list << QString(" var poi = results.getPoi(i);"); list << QString(" var point = poi.point.lng + ',' + poi.point.lat;"); list << QString(" result.push(point + ';' + poi.title + ';' + poi.address + ';' + poi.url);"); list << QString(" }"); list << QString(" receiveData('searchresult', result.join('|'));"); list << QString(" }"); list << QString(" };"); #endif list << QString(" var local = new %1.LocalSearch(map, searchOptions);").arg(mapFlag); list << QString(" local.setSearchCompleteCallback(function(results) {"); list << QString(" "); list << QString(" });"); //通用搜索方法 //text: 搜索的關(guān)鍵字 支持多個(gè)可以用 | 隔開(kāi) list << QString(" function search(text) {"); list << QString(" var texts = text.split('|');"); list << QString(" local.search(texts);"); list << QString(" }"); //矩形區(qū)域搜索 list << QString(" function searchInBounds(text, start, end) {"); list << QString(" var texts = text.split('|');"); list << QString(" if (!start || !end) {"); list << QString(" local.searchInBounds(texts, map.getBounds());"); list << QString(" return;"); list << QString(" }"); list << QString(" var bs = new %1.Bounds(getPoint(start), getPoint(end));").arg(mapFlag); list << QString(" local.searchInBounds(texts, bs);"); list << QString(" }"); //圓形區(qū)域搜索 list << QString(" function searchNearby(text, center, radius) {"); list << QString(" var texts = text.split('|');"); list << QString(" local.searchNearby(texts, getPoint(center), radius);"); list << QString(" }"); } void MapBaiDu::getOverlayInfo(QStringList &list) { //獲取覆蓋物信息 type = Marker Polyline 等 list << QString(" function getOverlayInfo(type) {"); list << QString(" var allOverlay = map.getOverlays();"); list << QString(" var count = allOverlay.length;"); list << QString(" for (var i = 0; i < count; ++i) {"); list << QString(" var overlay = allOverlay[i];"); //過(guò)濾不可見(jiàn)的 list << QString(" if (!overlay.isVisible()) {"); list << QString(" continue;"); list << QString(" }"); //拿到覆蓋物類型對(duì)應(yīng)字符串 toString() 以后的值是 [object Marker] [object Circle] [object Overlay] list << QString(" var objType = overlay.toString();"); list << QString(" objType = objType.substr(8, objType.length - 9);"); //過(guò)濾標(biāo)注點(diǎn)和懸停工具 list << QString(" if (objType == 'Marker' || objType == 'Overlay') {"); list << QString(" continue;"); list << QString(" }"); //如果指定了覆蓋物類型則過(guò)濾掉不符合類型的 list << QString(" if (type.length > 0 && objType != type) {"); list << QString(" continue;"); list << QString(" }"); list << QString(" var path = overlay.getPath();"); list << QString(" var points = getPathPoints(path);"); //不同類型的有不同的信息 下面演示的是另外一種過(guò)濾方法 instanceof list << QString(" var info = objType;"); list << QString(" if (overlay instanceof %1.Circle) {").arg(mapFlag); list << QString(" var center = overlay.getCenter();"); list << QString(" var point = center.lng + ',' + center.lat;"); list << QString(" var radius = overlay.getRadius();"); list << QString(" info = objType + '|' + point + '|' + radius + '|' + points.join(';')"); list << QString(" } else {"); list << QString(" info = objType + '|' + points.join(';')"); list << QString(" }"); list << QString(" receiveData('overlayinfo', info);"); list << QString(" }"); list << QString(" }"); }
到此這篇關(guān)于Qt編寫地圖之實(shí)現(xiàn)覆蓋物坐標(biāo)和搜索的文章就介紹到這了,更多相關(guān)Qt地圖覆蓋物坐標(biāo)搜索內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
C++實(shí)現(xiàn)LeetCode(50.求x的n次方)
這篇文章主要介紹了C++實(shí)現(xiàn)LeetCode(50.求x的n次方),本篇文章通過(guò)簡(jiǎn)要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下2021-07-07C語(yǔ)言實(shí)現(xiàn)數(shù)組的循環(huán)移位的方法示例
這篇文章主要介紹了C語(yǔ)言實(shí)現(xiàn)數(shù)組的循環(huán)移位的方法示例,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2019-08-08C++ 類中有虛函數(shù)(虛函數(shù)表)時(shí) 內(nèi)存分布詳解
下面小編就為大家?guī)?lái)一篇C++ 類中有虛函數(shù)(虛函數(shù)表)時(shí) 內(nèi)存分布詳解。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2016-12-12C語(yǔ)言的數(shù)字游戲算法效率問(wèn)題探討實(shí)例
這篇文章主要介紹了C語(yǔ)言的數(shù)字游戲算法效率問(wèn)題探討實(shí)例,需要的朋友可以參考下2014-04-04關(guān)于C/C++中static關(guān)鍵字的作用總結(jié)
以下是對(duì)C/C++中static關(guān)鍵字的作用進(jìn)行了總結(jié)介紹,需要的朋友可以過(guò)來(lái)參考下2013-09-09C語(yǔ)言標(biāo)準(zhǔn)庫(kù)<math.h>和<setjmp.h>的實(shí)現(xiàn)
本文主要介紹了C語(yǔ)言標(biāo)準(zhǔn)庫(kù)<math.h>和<setjmp.h>的實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2023-11-11vc中float與DWORD的互想轉(zhuǎn)換實(shí)現(xiàn)代碼
這篇文章主要介紹了vc中float與DWORD的互想轉(zhuǎn)換實(shí)現(xiàn)代碼,需要的朋友可以參考下2017-06-06C++ String部分成員模擬實(shí)現(xiàn)流程詳解
我們先不直接實(shí)現(xiàn)完整版的string,先實(shí)現(xiàn)簡(jiǎn)易版的string部分成員來(lái)基本了解下它的框架,以及以后來(lái)學(xué)習(xí)深淺拷貝的問(wèn)題。這樣有循序漸進(jìn)的過(guò)程嘛2022-08-08