Qt編寫地圖綜合應用14-離線地圖下載


一、前言

網上其實有很多各種各樣的離線地圖下載器,大部分都是要收費的,免費的要么是限制了下載的瓦片數量或者級別,要么是下載的瓦片圖打上了水印,看起來很難看,由於經常需要用到離線地圖,擺脫這個限制,特意花了點時間重新研究了瓦片地圖的原理,做了個離線地圖下載器,其實瓦片地圖下載沒有那么復雜,其實就是從開放的幾個服務器地址組建要請求的瓦片地圖的地址,發送請求以后會自動將圖片返回給你,你只需要拿到圖片數據保存成圖片即可。

瓦片地圖下載流程步驟如下:

  1. 獲取可視區域或者行政區域的范圍
  2. 拿到區域的左下角右上角經緯度坐標
  3. 根據層級數計算對應層級的瓦片數
  4. 自動生成下載瓦片地圖的地址並發出請求
  5. 解析收到的數據保存成圖片
  6. 更新對應界面的下載數量和進度
  7. 可選擇對應保存的目錄、全選層級、中途停止下載等
  8. 可選擇是下載街道圖還是衛星圖等

二、功能特點

  1. 多線程同步下載多級別瓦片地圖,不卡界面。
  2. 內置多個離線地圖下載請求地址,自動隨機選擇一個發送請求。
  3. 下載地圖類型同時支持街道圖和衛星圖。
  4. 自動計算可視區域或者行政區域的下載瓦片數量。
  5. 下載的級別可以自定義范圍和選擇。
  6. 每個瓦片下載完成都發送信號通知,參數包括下載用時。
  7. 可設置下載最大超時時間,超過了則丟棄跳到下一個下載任務。
  8. 實時顯示下載進度,以及當前級別已經下載的瓦片數和總瓦片數。
  9. 下載過程中可以停止下載,下載完成自動統計總用時。
  10. 內置經緯度和屏幕坐標互相轉換函數。
  11. 目前支持百度地圖,其他地圖比如谷歌地圖、騰訊地圖、高德地圖可以定制。
  12. 函數接口友好和統一,使用簡單方便,就一個類。
  13. 支持任意Qt版本、任意系統、任意編譯器。

三、體驗地址

  1. 體驗地址:https://pan.baidu.com/s/1ZxG-oyUKe286LPMPxOrO2A 提取碼:o05q 名稱:bin_map.zip
  2. 國內站點:https://gitee.com/feiyangqingyun
  3. 國際站點:https://github.com/feiyangqingyun
  4. 個人主頁:https://blog.csdn.net/feiyangqingyun
  5. 知乎主頁:https://www.zhihu.com/people/feiyangqingyun/

四、效果圖

五、相關代碼

void MapDownload::download(const QString &url, const QString &dirName, const QString &fileName, int zoom)
{
    if (url.isEmpty()) {
        return;
    }

    //啟動計時
    QTime time;
    time.start();

    //先判斷文件夾是否存在,不存在則新建
    QDir dir(dirName);
    if (!dir.exists()) {
        dir.mkpath(dirName);
    }

    //局部的事件循環,不卡主界面
    QEventLoop eventLoop;
    QNetworkReply *reply = manager->get(QNetworkRequest(QUrl(url)));
    connect(reply, SIGNAL(finished()), &eventLoop, SLOT(quit()));

    //設置下載超時
    QTimer timer;
    connect(&timer, SIGNAL(timeout()), &eventLoop, SLOT(quit()));
    timer.setSingleShot(true);
    timer.start(timeout);
    eventLoop.exec();

    bool error = false;
    if (reply->bytesAvailable() > 0 && reply->error() == QNetworkReply::NoError) {
        //讀取所有數據保存成文件
        QByteArray data = reply->readAll();
        QFile file(dirName + fileName);
        if (file.open(QFile::WriteOnly | QFile::Truncate)) {
            file.write(data);
            file.close();
        }
    } else {
        //可以自行增加下載失敗的統計
        error = true;
        qDebug() << TIMEMS << "下載出錯" << reply->errorString();
    }

    int useTime = time.elapsed();
    emit finsh(url, fileName, zoom, useTime, error);
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM