【Web前端问题】请教一个问题, 百度地图的javascript api 能否用触摸方式动态画一个圆或者矩形?

如题,请教下解决思路。

回答:

我自己实现了一下,可以自己在百度地图上随便画图形,基本原理就是,监听touch事件,touchMove,保存当前的经纬度,转化为pixel坐标,重复绘制线段,当touchEnd时,绘制矩形图形。最后会连接首位2点,并判断矩形是否有效,同时如果在画得过程中已经有闭合图形,则终止画图。

演示地址,需要使用手机浏览测试:
需要使用手机浏览

JS 实现代码:

var app = app || {};

app.BM = {

map: false,

init: function() {

// 百度地图API功能

this.map = new BMap.Map("allmap"); // 创建Map实例

this.map.centerAndZoom(new BMap.Point(116.404, 39.915), 11); // 初始化地图,设置中心点坐标和地图级别

this.map.addControl(new BMap.MapTypeControl()); //添加地图类型控件

this.map.setCurrentCity("北京"); // 设置地图显示的城市 此项是必须设置的

this.map.enableScrollWheelZoom(); //开启鼠标滚轮缩放

this.map.enableDragging();

}

};

// 电子围栏

// @todo 数据交互部分

app.Fence = {

cache_points: [], // 缓存折线数据,取消操作时,重新画图。

polyline:false, // 百度折线覆盖物

points: [], // 折线数据 [H,H,H,...] H{lat:"",lng:""}

coordinate: [], // 像素数据 [P,P,...] P{x:"",y:""}

cur_point: false,

cur_pixel: false,

isOver: false, // 围栏是否已经完成

cross_at: false, // 相交的点索引

state: 0, // 界面状态 0 待设定状态, 1 开始设定, 2 设定完成

polygon: false, // 完成后的栏栅覆盖物

polylineOption: {strokeColor:"blue", strokeWeight:4, strokeOpacity:0.5},

init: function() {

app.BM.init();

this.initClickEvent();

},

initClickEvent: function() {

// 设定或取消

document.getElementById('action').addEventListener('click', this.clickSettingHandler, false);

// 确定或重新设定事件监听

document.getElementById('setok').addEventListener('click', this.setOKHandler, false);

document.getElementById('reset').addEventListener('click', this.resetHandler, false);

},

clickSettingHandler: function(){

if (app.Fence.state == 0)

{

app.Fence.initTouchEvent();

if (app.Fence.polygon){

app.BM.map.removeOverlay(app.Fence.polygon);

}

app.Fence.resetData();

app.Fence.state = 1;

app.Fence.setElementHidden('fence_show');

app.Fence.setElementDisplay('fence_begin_draw');

document.getElementById('action').innerHTML = "取消";

} else {

app.Fence.removeTouchEvent();

if (app.Fence.polyline) {

app.BM.map.removeOverlay(app.Fence.polyline);

}

app.Fence.resetData();

app.Fence.state = 0;

if (app.Fence.cache_points) {

app.Fence.polygon = new BMap.Polygon(app.Fence.cache_points, app.Fence.polylineOption);

app.BM.map.addOverlay(app.Fence.polygon);

}

app.Fence.setElementDisplay('fence_show');

app.Fence.setElementHidden('fence_begin_draw');

document.getElementById('action').innerHTML = "设定";

}

},

finishDrawing: function(){

app.Fence.state = 2;

// 画图完成后立即清除移动

app.Fence.removeTouchEvent();

app.Fence.setElementHidden('fence_begin_draw');

app.Fence.setElementDisplay('fence_end_draw');

},

drawPolygon: function(){

app.BM.map.removeOverlay(app.Fence.polyline);

app.Fence.polygon = new BMap.Polygon(app.Fence.points, app.Fence.polylineOption);

app.BM.map.addOverlay(app.Fence.polygon);

},

removeClickEvent: function(){

document.getElementById('setok').removeEventListener('click', app.Fence.setOKHandler, false);

document.getElementById('reset').removeEventListener('click', app.Fence.resetHandler, false);

},

setOKHandler: function(){

app.Fence.state = 0;

// 最后画一个多边形polygon

app.Fence.drawPolygon();

app.Fence.setElementDisplay('fence_show');

app.Fence.setElementHidden('fence_end_draw');

document.getElementById('action').innerHTML = "设定";

document.getElementById('setting_state').innerHTML = "电子栏栅设定成功";

// 缓存数据

app.Fence.cache_points = app.Fence.points;

// @todo 同步数据到服务器

},

// 不满意,重新画图

resetHandler: function(){

app.Fence.state = 1;

app.BM.map.removeOverlay(app.Fence.polyline);

app.Fence.resetData();

app.Fence.initTouchEvent();

app.Fence.setElementHidden('fence_end_draw');

app.Fence.setElementDisplay('fence_begin_draw');

},

// 触摸事件 @important 开始画图时init 画完图后remove

initTouchEvent: function(){

app.BM.map.addEventListener("touchstart", app.Fence.touchStartHandler, false);

app.BM.map.addEventListener("touchend", app.Fence.touchEndHandler, false);

app.BM.map.addEventListener("touchmove", app.Fence.touchMoveHandler, false);

},

removeTouchEvent: function(){

app.BM.map.removeEventListener("touchstart", app.Fence.touchStartHandler, false);

app.BM.map.removeEventListener("touchend", app.Fence.touchEndHandler, false);

app.BM.map.removeEventListener("touchmove", app.Fence.touchMoveHandler, false);

},

touchStartHandler: function(){

app.BM.map.disableDragging();

app.Bm.map.disableScrollWheelZoom();

},

touchEndHandler: function(){

// 正确的画完图形

if (app.Fence.isOver){

app.Fence.finishDrawing();

} else {

if (!app.Fence.finalCheckIsCrossed())

{

var last = app.Fence.points.length - 1;

app.Fence.polyline = new BMap.Polyline([app.Fence.points[0], app.Fence.points[last]], app.Fence.polylineOption); //创建多边形

app.BM.map.addOverlay(app.Fence.polyline);

app.Fence.finishDrawing();

}

else

{

alert("电子栏栅设定错误,请重新设定!");

app.BM.map.removeOverlay(app.Fence.polyline);

app.Fence.resetData();

app.Fence.state = 1;

app.Fence.setElementHidden('fence_end_draw');

app.Fence.setElementDisplay('fence_begin_draw');

}

}

app.BM.map.enableDragging();

app.BM.map.enableScrollWheelZoom();

},

touchMoveHandler: function(e){

app.Fence.cur_point = e.point;

app.Fence.cur_pixel = e.pixel;

app.Fence.points.push(e.point);

app.Fence.coordinate.push(e.pixel);

if (app.Fence.checkIsCrossed())

{

app.Fence.redrawPolyline();

app.Fence.isOver = true;

}

else

{

if (!app.Fence.isOver) app.Fence.redraw();

}

},

checkIsCrossed: function(){

var last = app.Fence.coordinate.length - 1;

for (var i = 1; i < last - 2; i++)

{

if (last > 5 && app.Fence.intersect(app.Fence.coordinate[last-1], app.Fence.coordinate[last], app.Fence.coordinate[i-1], app.Fence.coordinate[i]))

{

app.Fence.cross_at = i;

return true;

}

}

return false;

},

finalCheckIsCrossed: function(){

var last = app.Fence.coordinate.length - 1;

for (var i = 2; i < last - 2; i++)

{

if (app.Fence.intersect(app.Fence.coordinate[i-1], app.Fence.coordinate[i], app.Fence.coordinate[0], app.Fence.coordinate[last]))

{

return true;

}

}

return false;

},

redrawPolyline: function(){

app.Fence.points.splice(0, app.Fence.cross_at);

// 重画图形

if (app.Fence.polyline) {

app.BM.map.removeOverlay(app.Fence.polyline);

}

if (app.Fence.points)

{

app.Fence.polyline = new BMap.Polyline(app.Fence.points, app.Fence.polylineOption); //创建多边形

app.BM.map.addOverlay(app.Fence.polyline); //增加多边形

var last = app.Fence.points.length -1 ;

app.Fence.polyline = new BMap.Polyline([app.Fence.points[0], app.Fence.points[last]], app.Fence.polylineOption); //创建多边形

app.BM.map.addOverlay(app.Fence.polyline);

}

},

redraw: function(){

if (app.Fence.polyline) {

app.BM.map.removeOverlay(app.Fence.polyline);

}

if (app.Fence.points)

{

app.Fence.polyline = new BMap.Polyline(app.Fence.points, app.Fence.polylineOption); //创建多边形

app.BM.map.addOverlay(app.Fence.polyline); //增加多边形

}

},

/* 叉积 判断2条线段是否相交 */

mult: function(a, b, c) {

return (a.x-c.x)*(b.y-c.y)-(b.x-c.x)*(a.y-c.y);

},

/* pa, pb为一条线段两端点 pc, pd为另一条线段的两端点 相交返回true, 不相交返回false*/

intersect: function(pa, pb, pc, pd) {

if ( Math.max(pa.x, pb.x)<Math.min(pc.x, pd.x) )

{

return false;

}

if ( Math.max(pa.y, pb.y)<Math.min(pc.y, pd.y) )

{

return false;

}

if ( Math.max(pc.x, pd.x)<Math.min(pa.x, pb.x) )

{

return false;

}

if ( Math.max(pc.y, pd.y)<Math.min(pa.y, pb.y) )

{

return false;

}

if ( app.Fence.mult(pc, pb, pa)*app.Fence.mult(pb, pd, pa)<0 )

{

return false;

}

if ( app.Fence.mult(pa, pd, pc)*app.Fence.mult(pd, pb, pc)<0 )

{

return false;

}

return true;

},

resetData: function(){

app.Fence.polyline = false;

app.Fence.points = [];

app.Fence.coordinate = [];

app.Fence.isOver = false;

app.Fence.cur_point = false;

app.Fence.cur_pixel = false;

app.Fence.polygon = false;

},

setElementDisplay:function(id){

document.getElementById(id).style.display = "block";

},

setElementHidden: function(id){

document.getElementById(id).style.display = "none";

}

};

回答:

触摸时获取触摸点的经纬度,然后调用api里画圆的方法画圆

回答:

http://developer.baidu.com/map/reference/index.phptitle=Class:%E8%A6%8...百度地图API的Circle类画圆

以上是 【Web前端问题】请教一个问题, 百度地图的javascript api 能否用触摸方式动态画一个圆或者矩形? 的全部内容, 来源链接: utcz.com/a/137573.html

回到顶部