找回密码
 立即注册

QQ登录

只需一步,快速开始

沉木主人

初级会员

1

主题

8

帖子

305

积分

初级会员

积分
305
  • 411

    金币

  • 1

    主题

  • 8

    帖子

最新发帖
沉木主人
初级会员   /  发表于:2024-7-26 11:51  /   查看:505  /  回复:2
GPS坐标和百度地图坐标因为坐标系的不同,GPS的经纬度坐标在百度地图中直接定位是不正确的,必须要要转换为百度地图经纬度,才能正确显示。最近有个百度地图定位项目,要将已经取得的大量GPS经纬度在百度地图上定位,还要显示一个动画,并添加一个文字标签。由于数据量比较大,使用循环实现会“卡死”屏幕,效果不佳,故尝试用递归解决,经过几天的努力终于实现了,现将活字格JS源码附上共享。




// 获取map对象,下例Map为页面上百度地图插件单元格名称,
var cell = Forguncy.ForguncyData.pageInfo.pageElementManager.cells.getCellByName("Map");
var map = cell.cellType.map;
map.clearOverlays();//清除百度地图上原来所有覆盖物
// 创建转换器对象convertor
var convertor = new BMap.Convertor();
//通过TEXTJOIN()函数将表格中某列所有数据用“;”号拼接在一起到CoordinateCell2单元格。拼接完格式为: 经度,纬度@标签;经度,纬度@标签;......

// 从CoordinateCell2单元格获取GPS坐标及标签字符串,并按";"分割为坐标对数组。
var coordWithTagString = Forguncy.Page.getCell("CoordinateCell2").getValue() || "";
var coordWithTagPairs = coordWithTagString.split(';');

// 转换函数每次处理的最大点数为10,10为百度地图API里convertor.translate()规定最大转换数
var batchSize = 10;
var respoints = [];
var labels = [];

// 收集所有的GPS点和标签
// GPS经纬度装入respoints数组
// GPS经纬度对应的标签装入labels数组
coordWithTagPairs.forEach(function(pairWithTag) {
    if (pairWithTag) {
        var parts = pairWithTag.split('@');
        if (parts.length === 2) {
            var [longitude, latitude] = parts[0].split(',').map(parseFloat);
            var labelContent = parts[1];
            respoints.push(new BMap.Point(longitude, latitude));
            labels.push(labelContent);
        }
    }
});

// 分批次进行坐标转换
// startIndex: 开始位置
// endIndex: 结束位置
function processBatch(startIndex) {
    var endIndex = Math.min(startIndex + batchSize, respoints.length);
    var batch = respoints.slice(startIndex, endIndex);
    // 截取respoints里大小为10的子数组
   
    convertor.translate(batch, 1, 5, function(data) {
        if (data.status === 0) {
            // 遍历每10个转换完成的点数组data.points[]
            data.points.forEach(function(point, index) {
                var marker = new BMap.Marker(point);
                //var opts = {position: point, offset: new BMap.Size(20,-10)};
                var opts = {offset: new BMap.Size(20,-10)};
                var label = new BMap.Label(labels[startIndex + index], opts);
                // 为marker绑定label并绘制marker
                marker.setLabel(label);
                map.addOverlay(marker);
                //map.addOverlay(label);
                marker.setAnimation(BMAP_ANIMATION_BOUNCE);     // marker跳动动画
            });
        }
        else {
            console.warn("坐标转换失败,状态码:", data.status);
        }

        // 如果还有未处理的批次,继续处理下一批10个
        if (endIndex < respoints.length) {  // if (上次结束的地方小于需要转换的GPS点的总大小)
            processBatch(endIndex);         // 那就从这次结束的地方开始转换下一组10个点, 递归
        }
        else {
            // 所有批次处理完毕后,设置地图中心
            if (respoints.length > 0) {
                // 经度平均值avgLng,纬度平均值avgLat
                var avgLng = respoints.reduce((sum, p) => sum + p.lng, 0) / respoints.length;
                var avgLat = respoints.reduce((sum, p) => sum + p.lat, 0) / respoints.length;
                map.centerAndZoom(new BMap.Point(avgLng, avgLat), 10);
            }
        }
    });
}

// 开始处理第一个批次
processBatch(0);


2 个回复

倒序浏览
VVANVI悬赏达人认证
论坛元老   /  发表于:2024-7-26 16:31:03
沙发
没看出哪里用到了递归!  
回复 使用道具 举报
沉木主人
初级会员   /  发表于:2024-7-26 18:10:47
板凳
本帖最后由 沉木主人 于 2024-7-26 18:26 编辑
VVANVI 发表于 2024-7-26 16:31
没看出哪里用到了递归!

用processBatch(0)函数调用了自身,把一个复杂的问题层层转化为一个小的问题解决,不是递归?那你心中的递归是什么样。拉出来大家看看呗。
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 立即注册
返回顶部