先看效果
PHP代码
<?php
namespace kds_addons\edata\controller;
use think\addons\Controller;
use think\Db;
class Maps extends Controller
{
// 经纬度计算面积
function calculate_area($points)
{
$totalArea = 0;
$numPoints = count($points);
if ($numPoints > 2) {
for ($i = 0; $i < $numPoints; $i++) {
$j = ($i + 1) % $numPoints;
$x1 = $points[$i]["lng"];
$y1 = $points[$i]["lat"];
$x2 = $points[$j]["lng"];
$y2 = $points[$j]["lat"];
$totalArea += deg2rad($x2 - $x1) * (2 + sin(deg2rad($y1)) + sin(deg2rad($y2)));
}
$totalArea *= 6378137 * 6378137 / 2;
}
return abs($totalArea);
}
// 地图设置
public function set_pi()
{
$times = time();
$id = intval(input("id"));
$this->assign("id", $id);
if (request()->isPost()) {
$l2_json = trim(input("l2_json"));
// dump($l2_json);
$l2_json = htmlspecialchars_decode($l2_json);
// $l2_json = stripslashes($l2_json);
$l2_arr = json_decode($l2_json, true);
// dump($l2_arr);
Db::name("land_l2")->where("land_id", $id)->delete(); //删除数据
$datas_ia = [];
foreach ($l2_arr as $key => &$value) {
// dump($value);
$value["land_id"] = $id;
$value["create_time"] = $times;
ksort($value); //数组按键名排序
$datas_ia[] = $value;
}
$datas_ia = array_values($datas_ia); //只保留数组中的value
Db::name("land_l2")->insertAll($datas_ia); //插入多条数据
// 计算中心
// 经度
$lng_sum = Db::name("land_l2")->where("land_id", $id)->sum("lng");
$lng_nu = Db::name("land_l2")->where("land_id", $id)->count("lng");
$datas["lng"] = $lng_sum / $lng_nu;
// 纬度
$lat_sum = Db::name("land_l2")->where("land_id", $id)->sum("lat");
$lat_nu = Db::name("land_l2")->where("land_id", $id)->count("lat");
$datas["lat"] = $lat_sum / $lat_nu;
// 计算面积
$lists_l2 = Db::name("land_l2")->field(["lng", "lat"])->where("land_id", $id)->select();
$area = $this->calculate_area($lists_l2);
$datas["area_m2"] = $area;
$datas["area_gq2"] = $area / 10000; //平方米转换为平方公顷
$datas["not_gp2"] = $area / 10000; //平方米转换为平方公顷
// 更新数据
Db::name("land")->where("id", $id)->update($datas);
$res = [];
$res["code"] = 0;
return json($res);
}
// 获取所有标记点
$lists = Db::name("land_l2")
->field(["lng", "lat"])
->where("land_id", $id)
->order("id asc")
->select();
$this->assign("lists", $lists);
// 获取中心坐标
$first = reset($lists);
$this->assign("lng", $first["lng"]);
$this->assign("lat", $first["lat"]);
// return $this->fetch();
return $this->fetch(request()->action() . "_qq");
}
// 地图查看
public function se_pi()
{
$id = intval(input("id"));
$this->assign("id", $id);
// 获取所有标记点
$lists = Db::name("land_l2")
->field(["lng", "lat"])
->where("land_id", $id)
->order("id asc")
->select();
$this->assign("lists", $lists);
// 获取中心坐标
$first = reset($lists);
$this->assign("lng", $first["lng"]);
$this->assign("lat", $first["lat"]);
// return $this->fetch();
return $this->fetch(request()->action() . "_qq");
}
}
选点
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<meta name="renderer"
content="webkit">
<meta http-equiv="X-UA-Compatible"
content="IE=edge,chrome=1">
<meta name="viewport"
content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=0">
<link rel="stylesheet"
href="/yunqikds_static/iconfont/iconfont.css">
<script src="/yunqikds_static/iconfont/iconfont.js"></script>
<link rel="stylesheet"
href="/yunqikds_static/layuiadmin/layui/css/layui.css"
media="all">
<script src="/yunqikds_static/layuiadmin/layui/layui.js"></script>
<script src="/yunqikds_static/js/jquery-1.10.2.min.js"></script>
</head>
<style type="text/css">
html,
body {
height: 100%;
margin: 0px;
padding: 0px;
}
#container {
width: 100%;
height: 100%;
}
</style>
<style type="text/css">
ul li {
list-style: none;
}
.drawing-panel {
z-index: 9999;
position: fixed;
bottom: 3.5rem;
margin-left: 3rem;
padding: 1rem 1rem;
border-radius: .25rem;
background-color: #fff;
box-shadow: 0 2px 6px 0 rgba(27, 142, 236, 0.5);
}
.btn {
width: 150px;
height: 30px;
float: left;
background-color: #fff;
color: rgba(27, 142, 236, 1);
font-size: 14px;
border: 1px solid rgba(27, 142, 236, 1);
border-radius: 5px;
margin: 0 5px;
text-align: center;
line-height: 30px;
}
.btn:hover {
background-color: rgba(27, 142, 236, 0.8);
color: #fff;
}
</style>
<body>
<div id="container"></div>
<ul class="drawing-panel">
<li class="btn"
onclick="map_tog()">切换</li>
</ul>
<script charset="utf-8"
src="https://map.qq.com/api/gljs?v=1.exp&key=OB4BZ-D4W3U-B7VVO-4PJWW-6TKDJ-WPB77&libraries=geometry"></script>
<script type="text/javascript">
$(function () {
layui.use([
"layer",
], function () {
layer = layui.layer;
});
});
var is_add = true; //解决单击添加和删除冲突的问题
var is_point = ""; //解决多次删除的问题
// 初始化地图
var c_pi = new TMap.LatLng(parseFloat(`{$lat?$lat:"36.6171"}`), parseFloat(`{$lng?$lng:"101.7782"}`)); //中心点
var map = new TMap.Map("container", {
center: c_pi,
doubleClickZoom: false, //设置是否可以双击放大
zoom: 16,
baseMap: {
type: "satellite", //卫星底图
// type: "vector", //矢量底图
},
});
map.setDoubleClickZoom(false); //设置是否可以双击放大
map.removeControl(TMap.constants.DEFAULT_CONTROL_ID.SCALE); //移除腾讯地图比例尺
map.removeControl(TMap.constants.DEFAULT_CONTROL_ID.ROTATION); //移除腾讯地图旋转控件
map.removeControl(TMap.constants.DEFAULT_CONTROL_ID.ZOOM); //移除腾讯地图缩放控件
// 创建MultiMarker对象
var multi_marker = new TMap.MultiMarker({
map: map,
styles: {
"my_styles": new TMap.MarkerStyle({
strokeColor: "#fff",
size: 24,
strokeWidth: 3,
}),
},
});
// 添加标记点
function p_add(lat, lng, i = null) {
lat = parseFloat(lat);
lng = parseFloat(lng);
var datas = {
position: new TMap.LatLng(lat, lng),
};
if (i) {
// console.log(i);
datas.content = i;
datas.styleId = "my_styles";
}
var marker = multi_marker.add(datas);
is_point = "";
marker.on("click", function (evt) {
// console.log(evt);
if (!evt.geometry) {
return false;
}
var points = JSON.stringify(evt.point);
if (is_point == points) {
return false;
}
is_point = points;
multi_marker.remove(evt.geometry.id);
is_add = false;
setTimeout(function () {
is_add = true;
}, 1);
});
}
`{volist name="lists" id="vo"}`;
p_add(`{$vo.lat}`, `{$vo.lng}`, `{$i}`);
`{/volist}`;
// 监听点击事件添加marker
map.on("click", function (evt) {
// console.log(evt);
if (is_add) {
p_add(evt.latLng.lat, evt.latLng.lng);
}
});
// 切换地图类型
function map_tog() {
if (map.getBaseMap().type != "satellite") {
map.setBaseMap({
type: "satellite", //卫星底图
});
} else {
map.setBaseMap({
type: "vector", //矢量底图
});
}
}
// 保存标记标记点
function map_save() {
var l2_marker = [];
// 获取经纬度
var arr_marker = multi_marker.getGeometries();
// console.log(arr_marker);
$.each(arr_marker, function (key, vo) {
// console.log(vo);
l2_marker.push({
lat: vo.position.lat,
lng: vo.position.lng,
});
});
// console.log(l2_marker);
l2_marker = JSON.stringify(l2_marker);
$.post("", {
id: "{$id}",
l2_json: l2_marker,
}, function (params) {
if (params.code == 0) {
layer.msg("标记成功");
} else {
layer.msg("标记失败");
}
}, "json");
}
</script>
</body>
</html>
效果查看
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<meta name="renderer"
content="webkit">
<meta http-equiv="X-UA-Compatible"
content="IE=edge,chrome=1">
<meta name="viewport"
content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=0">
<link rel="stylesheet"
href="/yunqikds_static/iconfont/iconfont.css">
<script src="/yunqikds_static/iconfont/iconfont.js"></script>
<link rel="stylesheet"
href="/yunqikds_static/layuiadmin/layui/css/layui.css"
media="all">
<script src="/yunqikds_static/layuiadmin/layui/layui.js"></script>
<script src="/yunqikds_static/js/jquery-1.10.2.min.js"></script>
</head>
<style type="text/css">
html,
body {
height: 100%;
margin: 0px;
padding: 0px;
}
#container {
width: 100%;
height: 100%;
}
</style>
<style type="text/css">
ul li {
list-style: none;
}
.drawing-panel {
z-index: 9999;
position: fixed;
bottom: 3.5rem;
margin-left: 3rem;
padding: 1rem 1rem;
border-radius: .25rem;
background-color: #fff;
box-shadow: 0 2px 6px 0 rgba(27, 142, 236, 0.5);
}
.btn {
width: 150px;
height: 30px;
float: left;
background-color: #fff;
color: rgba(27, 142, 236, 1);
font-size: 14px;
border: 1px solid rgba(27, 142, 236, 1);
border-radius: 5px;
margin: 0 5px;
text-align: center;
line-height: 30px;
}
.btn:hover {
background-color: rgba(27, 142, 236, 0.8);
color: #fff;
}
</style>
<body>
<div id="container"></div>
<ul class="drawing-panel">
<li class="btn"
onclick="map_tog()">切换</li>
</ul>
<script charset="utf-8"
src="https://map.qq.com/api/gljs?v=1.exp&key=OB4BZ-D4W3U-B7VVO-4PJWW-6TKDJ-WPB77&libraries=geometry"></script>
<script type="text/javascript">
$(function () {
layui.use([
"layer",
], function () {
layer = layui.layer;
});
});
// 初始化地图
var c_pi = new TMap.LatLng(parseFloat(`{$lat?$lat:"36.6171"}`), parseFloat(`{$lng?$lng:"101.7782"}`)); //中心点
var map = new TMap.Map("container", {
center: c_pi,
doubleClickZoom: false, //设置是否可以双击放大
zoom: 16,
baseMap: {
type: "satellite", //卫星底图
// type: "vector", //矢量底图
},
});
map.setDoubleClickZoom(false); //设置是否可以双击放大
map.removeControl(TMap.constants.DEFAULT_CONTROL_ID.SCALE); //移除腾讯地图比例尺
map.removeControl(TMap.constants.DEFAULT_CONTROL_ID.ROTATION); //移除腾讯地图旋转控件
map.removeControl(TMap.constants.DEFAULT_CONTROL_ID.ZOOM); //移除腾讯地图缩放控件
var polygon_path = [];
`{volist name="lists" id="vo"}`;
polygon_path.push(new TMap.LatLng(parseFloat(`{$vo.lat}`), parseFloat(`{$vo.lng}`)));
`{/volist}`;
// console.log(polygon_path);
var polygon1 = new TMap.MultiPolygon({
map, // 显示多边形图层的底图
styles: { // 多边形的相关样式
polygon1: new TMap.PolygonStyle({
color: "rgba(0,0,0,0)", // 面填充色
showBorder: true, // 是否显示拔起面的边线
borderColor: "#295BFF", // 边线颜色
borderWidth: 3, // 边线宽度
// borderDashArray: [5, 5], // 虚线数组
}),
},
geometries: [{
id: "polygon1", // 多边形图形数据的标志信息
styleId: "polygon1", // 样式id
paths: polygon_path, // 多边形的位置信息
}],
});
// 获取面积
var area = TMap.geometry.computeArea(polygon_path);
console.log(area);
// 切换地图类型
function map_tog() {
if (map.getBaseMap().type != "satellite") {
map.setBaseMap({
type: "satellite", //卫星底图
});
} else {
map.setBaseMap({
type: "vector", //矢量底图
});
}
}
</script>
</body>
</html>