一、前言

在现在很多的应用系统中,会提供一个地图模块,地图相关的应用和app也是非常多,最广泛的应用就属于导航,地图基本上分在线的和离线的两种,在线的一般都是实时的,数据也是最新的,速度很快路线很准,缺点是耗费流量,一直需要收发数据,而离线的需要先把地图包和对应的文件下载到本地,直接读取本地的地图数据进行交互。

用Qt做过很多个商业项目,其中有几个涉及到加载地图用于展示设备的分布,之前做的是在线的地图,通过网页的交互来获取和设置数据,最近几年越来越多需要离线地图的需求,离线地图最核心的就是地图数据包,也叫瓦片地图,需要通过下载器下载到本地使用,网上查了下,还非常多公司专门做这个离线瓦片地图的下载器,绝大部分都是收费的。

越来越多的地图服务用到瓦片技术,例如我国实行发布的天地图服务就运用了地图瓦片技术。其实切片之后的地图瓦片是栅格图像,并不具备定位信息,不过切片运用了相关切片算法之后,可以计算出具体定位的位置。例如采用WGS84大地坐标系为空间参考,对地图进行切片,采用一定的切片算法,例如用经纬度步长等比例分割形成地图瓦片,当需要对一个具体地方进行定位时,可以根据经纬度步长来计算具体位置,以此来达到定位的功能。

近期抽空特意将大屏系统中常用的区域地图以及地图功能模块重新封装了下,使得支持在线和离线两种模式,同时支持webkit、webengine、ie 三种方式,支持闪烁点图、迁徙图、区域地图、仪表盘,还带有交互功能。

echart仪表盘带交互demo开源地址:https://gitee.com/feiyangqingyun/QWidgetDemo https://github.com/feiyangqingyun/QWidgetDemo

文件名称:echartgauge

体验地址:https://gitee.com/feiyangqingyun/QWidgetExe https://github.com/feiyangqingyun/QWidgetExe

文件名称:bin_map.zip

二、功能特点

Echarts地图封装类功能特点

  1. 同时支持闪烁点图、迁徙图、区域地图、仪表盘等。
  2. 可以设置标题、提示信息、背景颜色、文字颜色、线条颜色、区域颜色等各种颜色。
  3. 可设置城市的名称、值、经纬度 集合。
  4. 可设置地图的放大倍数、是否允许鼠标滚轮缩放。
  5. 内置世界地图、全国地图、省份地图、地区地图,可以精确到县,所有地图全部离线使用。
  6. 内置了各省市json数据文件转js文件功能,如有数据更新自行转换即可,支持单个文件转换和一键转换所有文件。
  7. 内置了从json文件或者js文件获取该区域的所有名称和经纬度信息集合的功能,可以通过该方法获取到信息用来显示。
  8. 依赖浏览器组件显示地图,提供的demo支持webkit、webengine、ie 三种方式加载网页。
  9. 拓展性极强,可以依葫芦画瓢自行增加各种精美的echarts组件,做出牛逼的效果。
  10. 内置的仪表盘组件提供交互功能,demo演示中包含了对应的代码。
  11. 函数接口友好和统一,使用简单方便,就一个类。
  12. 支持任意Qt版本、任意系统、任意编译器。

百度地图封装类功能特点

  1. 同时支持在线地图和离线地图两种模式。
  2. 同时支持webkit内核、webengine内核、IE内核。
  3. 支持设置多个标注点,信息包括名称、地址、经纬度。
  4. 可设置地图是否可单击、拖动、鼠标滚轮缩放。
  5. 可设置协议版本、秘钥、主题样式、中心坐标、中心城市、地理编码位置等。
  6. 可设置地图缩放比例和级别,缩略图、比例尺、路况信息等控件的可见。
  7. 支持地图交互,比如鼠标按下获取对应位置的经纬度。
  8. 支持查询路线,可设置起点位置、终点位置、路线模式、路线方式、路线方案(最少时间、最少换乘、最少步行、不乘地铁、最短距离、避开高速)。
  9. 可显示点线面工具,可直接在地图上划线、点、矩形、圆形等。
  10. 可设置行政区划,指定某个城市区域绘制图层,在线地图自动输出行政区划边界点集合到js文件给离线地图使用。
  11. 可添加多个覆盖物。支持点、折线、多边形、矩形、圆形、弧线、点聚合等。
  12. 函数接口友好和统一,使用简单方便,就一个类。
  13. 支持任意Qt版本、任意系统、任意编译器。

三、效果图



四、使用代码

void frmEcharts::loadMap()
{
timer->stop(); Echarts::Instance()->reset();
Echarts::Instance()->setHeight(ui->widget->height()); QStringList cityName, cityValue, cityPoint;
cityName << "上海" << "北京" << "成都" << "武汉" << "厦门" << "广州";
cityPoint << "121.48,31.22" << "116.46,39.92" << "104.06,30.67" << "114.31,30.52" << "118.1,24.46" << "113.23,23.16"; Echarts::Instance()->setCityName(cityName);
Echarts::Instance()->setCityPoint(cityPoint);
Echarts::Instance()->setZoom(1.0);
//全国地图是 china 世界地图可以换成 world
Echarts::Instance()->setMapJsName("china");
Echarts::Instance()->setMapAreaName("china"); QString text = ui->cboxType->currentText();
if (text == "闪烁点图") {
cityValue << "250" << "220" << "150" << "180" << "140" << "170";
Echarts::Instance()->setCityValue(cityValue);
} else if (text == "迁徙图") {
cityValue << "1" << "0" << "0" << "0" << "0" << "0";
Echarts::Instance()->setCityValue(cityValue);
} else if (text == "仪表盘") { } else if (text == "区域地图") {
QStringList cityName, cityValue, cityPoint;
QString dirName = ui->cboxDir->currentText();
QString areaName = ui->cboxJson->currentText();
QString jsName = dirName + "/" + areaName; #if 1
//根据文件获取名称+经纬度集合
QString jsonFile = QString("%1/areajson/%2/%3.json").arg(AppPath).arg(dirName).arg(areaName);
QString jsFile = QString("%1/areajs/%2/%3.js").arg(AppPath).arg(dirName).arg(areaName);
//QStringList infos = EchartJs::getInfoFromJson(jsonFile);
QStringList infos = EchartJs::getInfoFromJs(jsFile);
foreach (QString info, infos) {
QStringList list = info.split("|");
cityName << list.at(0);
cityValue << QString("%1").arg((qrand() % 100) + 100);
cityPoint << list.at(1);
}
#else
//固定写死
if (areaName == "上海") {
cityName << "浦东新区" << "闵行区" << "金山区" << "奉贤区" << "嘉定区";
cityValue << "250" << "100" << "200" << "150" << "220";
cityPoint << "121.567706,31.245944" << "121.375972,31.111658" << "121.330736,30.724697" << "121.458472,30.912345" << "121.250333,31.383524";
}
#endif Echarts::Instance()->setCityName(cityName);
Echarts::Instance()->setCityValue(cityValue);
Echarts::Instance()->setCityPoint(cityPoint);
Echarts::Instance()->setMapJsName(jsName);
Echarts::Instance()->setMapAreaName(areaName);
} else if (text == "世界地图") {
QStringList cityName, cityValue, cityPoint;
Echarts::Instance()->setCityName(cityName);
Echarts::Instance()->setCityValue(cityValue);
Echarts::Instance()->setCityPoint(cityPoint);
Echarts::Instance()->setMapJsName("world");
Echarts::Instance()->setMapAreaName("world");
} loadMap(ui->cboxType->currentIndex());
} void frmEcharts::loadMap(int type)
{
QString content;
QString fileName = QString("%1/map_echarts.html").arg(AppPath);
QString url = "file:///" + fileName; //如果采用加载内容方式则需要先设置不存储文件
//在linux上需要用load的方式加载
#ifdef Q_OS_WIN
Echarts::Instance()->setSaveFile(false);
#else
Echarts::Instance()->setSaveFile(true);
#endif Echarts::Instance()->setFileName(fileName);
if (type == 1) {
content = Echarts::Instance()->newChartMove("上海");
} else if (type == 2) {
content = Echarts::Instance()->newChartGauge("完成率", 65);
} else {
content = Echarts::Instance()->newChartPoint();
} //下面为两种方式加载网页,如果内容为空则加载网页文件否则加载内容
//一般为了保密建议加载内容,这样看不到生成的网页文件
if (Echarts::Instance()->getSaveFile()) {
#ifdef webkit
webView->load(QUrl(url));
#elif webengine
webView->load(QUrl(url));
#elif webie
webView->dynamicCall("Navigate(const QString&)", url);
#endif
} else {
QUrl baseUrl(QString("%1/").arg(AppPath));
#ifdef webkit
webView->setHtml(content, baseUrl);
#elif webengine
webView->setHtml(content, baseUrl);
#endif
}
} void frmEcharts::on_btnSaveJs_clicked()
{
QString dirName = ui->cboxDir->currentText();
QString cityName = ui->cboxJson->currentText();
QString jsonFile = QString("%1/areajson/%2/%3.json").arg(AppPath).arg(dirName).arg(cityName);
QString jsFile = QString("%1/areajs/%2/%3.js").arg(AppPath).arg(dirName).arg(cityName);
EchartJs::saveJs(jsonFile, jsFile, cityName);
} void frmEcharts::on_btnSaveAll_clicked()
{
ui->btnSaveJs->setEnabled(false);
ui->btnSaveAll->setEnabled(false);
qApp->processEvents(); QString dirPath = QString("%1/areajson").arg(AppPath);
QDir dir(dirPath);
if (dir.exists()) {
QStringList dirNames = dir.entryList(QDir::Dirs | QDir::NoSymLinks | QDir::NoDotAndDotDot);
ui->progressBar->setValue(0);
ui->progressBar->setRange(0, dirNames.count());
foreach (QString dirName, dirNames) {
QString strPath = QString("%1/areajson/%2").arg(AppPath).arg(dirName);
QDir path(strPath);
if (path.exists()) {
QStringList fileNames = path.entryList(QDir::Files | QDir::NoSymLinks | QDir::NoDotAndDotDot);
foreach (QString fileName, fileNames) {
fileName = fileName.replace(".json", "");
QString jsonFile = QString("%1/areajson/%2/%3.json").arg(AppPath).arg(dirName).arg(fileName);
QString jsFile = QString("%1/areajs/%2/%3.js").arg(AppPath).arg(dirName).arg(fileName);
EchartJs::saveJs(jsonFile, jsFile, fileName);
}
} ui->progressBar->setValue(ui->progressBar->value() + 1);
}
} ui->btnSaveJs->setEnabled(true);
ui->btnSaveAll->setEnabled(true);
} void frmEcharts::on_cboxType_currentIndexChanged(const QString &arg1)
{
if (isVisible()) {
this->loadMap();
}
} void frmEcharts::on_cboxDir_currentIndexChanged(const QString &arg1)
{
//取出目录下的所有文件名称作为市
ui->cboxJson->clear();
QString dirPath = QString("%1/areajson/%2").arg(AppPath).arg(arg1);
QDir dir(dirPath);
if (dir.exists()) {
QStringList fileNames = dir.entryList(QDir::Files | QDir::NoSymLinks | QDir::NoDotAndDotDot);
foreach (QString fileName, fileNames) {
fileName = fileName.replace(".json", "");
ui->cboxJson->addItem(fileName);
}
}
} void frmEcharts::on_cboxJson_currentIndexChanged(const QString &arg1)
{
if (isVisible() && ui->cboxType->currentText() == "区域地图") {
this->loadMap();
}
} void frmEcharts::on_horizontalSlider_valueChanged(int value)
{
if (isVisible() && ui->cboxType->currentText() == "仪表盘") {
QString js = QString("setGaugeValue(%1)").arg(value);
#ifdef webkit
webView->page()->mainFrame()->evaluateJavaScript(js);
#elif webengine
webView->page()->runJavaScript(js);
#endif
}
}

Qt编写百度地图综合应用(在线+离线+区域)的更多相关文章

  1. 【百度地图API】自行获取区域经纬度的工具

    原文:[百度地图API]自行获取区域经纬度的工具 摘要:上一章教大家如何建立自己的行政区域地图.这次为大家提供一个,可视化选择区域,并且能自动生成经纬度代码的工具.工具的源代码完全公开,并且做了详尽的 ...

  2. Qt编写百度离线版人脸识别+比对+活体检测

    在AI技术发展迅猛的今天,很多设备都希望加上人脸识别功能,好像不加上点人脸识别功能感觉不够高大上,都往人脸识别这边靠,手机刷脸解锁,刷脸支付,刷脸开门,刷脸金融,刷脸安防,是不是以后还可以刷脸匹配男女 ...

  3. android 在使用studio 编写百度地图中遇到APP Scode码校验失败 问题

    直接用打包出来的apk查看签名,具体如下: 1) 将apk修改后缀为 .zip文件后解压: 2) 进入解压后的META-INF目录,该目录下会存在文件CERT.RSA 3) 在该目录下打开cmd,输入 ...

  4. 最全面的百度地图JavaScript离线版开发

    转载请注明出处:http://www.cnblogs.com/Joanna-Yan/p/5822231.html 项目要求web版百度地图要离线开发.这里总结下自己的开发过程和经验. 大概需求是:每辆 ...

  5. Qt开发北斗定位系统融合百度地图API及Qt程序打包发布

    Qt开发北斗定位系统融合百度地图API及Qt程序打包发布 1.上位机介绍 最近有个接了一个小型项目,内容很简单,就是解析北斗GPS的串口数据然后输出经纬度,但接过来觉得太简单,就发挥了主观能动性,增加 ...

  6. 【百度地图API】JS版本的常见问题

    1.请问如何将我的店铺标注在百度地图上?我是否可以做区域代理?在百度地图上标注是否免费? 答复: 这里只负责API的技术咨询,不解决任何地图标注问题.在百度地图上标注自己公司,即气泡标注业务.该业务已 ...

  7. 【Android】3.0 第3章 百度地图及其应用--预备知识

    分类:C#.Android.VS2015.百度地图应用: 创建日期:2016-02-04 一.概述 这一章先来点有意思的百度地图应用示例,然后再分章详细介绍用C#开发Android App的各种基本技 ...

  8. 百度地图API相关点

    百度API接口:http://developer.baidu.com/map/jsdemo.htm#a1_1 百度地图API具体解释之地图标注:http://www.cnblogs.com/jz110 ...

  9. 百度地图API和高德地图API资料集锦

    [高德地图API]从零开始学高德JS API(五)路线规划——驾车|公交|步行   [高德地图API]从零开始学高德JS API(四)搜索服务——POI搜索|自动完成|输入提示|行政区域|交叉路口|自 ...

  10. [转]百度地图API详解之地图坐标系统

    博客原文地址:http://www.jiazhengblog.com/blog/2011/07/02/289/ 我们都知道地球是圆的,电脑显示器是平的,要想让位于球面的形状显示在平面的显示器上就必然需 ...

随机推荐

  1. Machine Learning Week_1 Model and Cost Function 5-8

    目录 2.5 Video: Cost Function Intuition-1 unfamiliar words 2.6 Reading: Cost Function Intuition-1 unfa ...

  2. 《大话设计模式》java实现:第二章-策略模式

    <大话设计模式>java实现:第二章-策略模式 第二章是使用策略模式实现商场收银系统,使收银系统的促销策略可以灵活更改. 1. 原始代码实现: package gof; /* * < ...

  3. 内核源码+vscode+bear+clang实现函数任意跳转,无缝跳转,无缝阅读,无缝开发

    一.准备工作 1.内核源码版本选择 务必有一份能编译通过的<内核源码>,本次选择5.10版本的. #说明:5.10版本的<内核源码>里,在 scripts/clang-tool ...

  4. byte,关于127+1等于多少

    public class Main { public static void main(String[] args) { Integer i1 = 100; Integer i2 = 100; Int ...

  5. Codeforces Round 987 (Div. 2)

    Codeforces Round 987 (Div. 2) 总结 A 常见的套路,将一个序列变为不下降序列所需要改变的值的最小数量,考虑最大能保留多少个,显然是求最长上升子序列,而这题给出的 \(a\ ...

  6. iconfont图标库的使用

    https://www.iconfont.cn/ -- 点击链接进入官网 择自己需要的图标加购物车 点击资源管理->我的项目 选择你需要的项目->下载到本地 将下载的压缩包进行解压,解压后 ...

  7. 2022 GDOI普及组游记

    2022 GDOI普及组游记 注:传送门均为校内网址 day -4 被年级主任集中开会,给我们免了亿堆作业,灌了亿壶鸡汤,宣布了为期一(亿)周的集训开始. day -3 中午一直在复习期中(4.21- ...

  8. 【Spring】IOC核心源码学习(二):容器初始化过程

    接上文 啃啃老菜: Spring IOC核心源码学习(一) ,本文将以 ClassPathXmlApplicationContext 这个容器的实现作为基础,学习容器的初始化过程. ClassPath ...

  9. 使用 Antlr 开发领域语言

    高 尚 (gaoshang1999@163.com), 软件工程师, 中国农业银行软件开发中心 简介: Antlr 是一个基于 Java 开发的功能强大的语言识别工具,Antlr 以其简介的语法和高速 ...

  10. Java语言的动态性支持

    一.脚本语言的支持     JSR 223中规范了在Java虚拟机上运行的脚本语言与Java程序之间的交互方式.JSR 233是JavaSE6的一部分,在Java表中API中的包是javax.scri ...