JavaScript、GIS等知识点合集
一、文字溢出出现,以省略号显示不完全部分
deviceNames = val.deviceTypeName.substring(0, 11) + "...";
二、

点击设备的时候,今天发现点击不了
floor_g2map.on('click', function (button, shift, screenX, screenY, mapX, mapY, handle) {
let elementLayerArea = elementLayer.hitTest(screenX, screenY);
// 触发火警点位周围资源事件
if(elementLayerArea){
alert(1)
}
});
floor_g2map.on("mousemove", function(button, shift, screenX, screenY, mapX, mapY, handle) {
var obj = elementLayer.hitTest(screenX, screenY);
if(obj) {
$("#map").css("cursor", "pointer");
} else {
$("#map").css("cursor", "default");
}
})
这俩缺一不可。
解释:如果页面打开之后,鼠标不拖动图纸,那么是可以点击弹出弹框的,但是,一旦拖动了图纸,那么就点击弹不出弹框了,这个时候加上下面的mousemove方法就可以了,不管怎么拖动,点击设备图标都是可以打开弹框的。
补充:主要还不是这个问题,而是定时器的问题,改成下面这样就行了。
1 mounted: function () { 2 /*clearTimeout(initMapTimer); 3 let _this=this; 4 initMapTimer = setTimeout(function () { 5 _this.initMap(); 6 },1500)*/ 7 let _this=this; 8 _this.$nextTick(function(){ 9 _this.initMap(); 10 }) 11 }
三、websocket插件使用
具体看以下代码:
//依赖引入的websocket插件,然后直接 new SockJs(socket服务地址)即可。 <script src="http://cdn.bootcss.com/stomp.js/2.3.3/stomp.min.js"></script> <script src="https://cdn.bootcss.com/sockjs-client/1.1.4/sockjs.min.js"></script> var stompClient = null; var clearTimeOut; var auuTimer; var myAudio = document.getElementById("myAudio"); $(function () { var orgObj = JSON.parse(localStorage.getItem('yygl_orgObj')); connect(orgObj.orgCode); }); function connect(subTopic) { var _url = forent_url.webSocketUrl + '/ws'; var socket = new SockJS(_url); stompClient = Stomp.over(socket); stompClient.connect({}, function connectCallback(frame) { // 订阅 /topic/* 订阅模式,可以同时订阅多个主题 stompClient.subscribe('/topic/' + subTopic, function (response) { if (response.body) { if (clearTimeOut && auuTimer) { clearTimeout(clearTimeOut); } if (auuTimer) { clearTimeout(auuTimer); } $(".cs-popup-content").css("display", "block"); $(".cs-popup-content").slideDown(); myAudio.currentTime = 0; myAudio.play(); myAudio.loop = "loop"; auuTimer = setTimeout(function () { myAudio.loop = ""; }, 9500) var _response = JSON.parse(response.body); var _resIcon = ''; if (_response.alarmStatus == '1') { _resIcon = '<i class="diskicon-horn"></i> ' } else if (_response.alarmStatus == '2') { _resIcon = '<i class="diskicon-notice"></i> ' } $(".cs-popup-panel").prepend('<p class="cs-popup-default p-word" title="' + _response.alarmText + '" >' + _resIcon + _response.alarmText + '<i class="diskicon-close btn-remove-item"></i></p >') clearTimeOut = setTimeout(function () { $(".cs-popup-content").slideUp(); $(".cs-popup-panel").html(""); myAudio.currentTime = 0; myAudio.pause(); }, 60000) } }); }, function errorCallBack(error) { // 连接失败时(服务器响应 ERROR 帧)的回调方法 console.log('stompWebSocket connect failed'); setTimeout(function () { var orgObj = JSON.parse(localStorage.getItem('yygl_orgObj')); connect(orgObj.orgCode); }, 120000); } ); stompClient.heartbeat.outgoing = 300000; stompClient.heartbeat.incoming = 0; //客户端不从服务端接收心跳包 /** * @MessageMapping("/sendMsg") 消息服务端Controller方法 * stompClient.send("sendMsg",{},"Hello, STOMP"); */ }
注:举例webSocketUrl可能的服务地址:http://112.27.198.15:9832/webcall,subTopic:这里取的是用户的id
延伸:即时通讯聊天框
原理:获取用户输入的文字或者图片,作为参数调取接口,响应发送成功,此时接口返回一个websocket数据,通过websocket,获取刚刚发送的数据,push到所有的聊天记录里面,即可实现即时聊天
html代码如下:
<div class="work-group"> <div class="chatTt">沟通群</div> <div id="chatCont"> <div class="battleGroup" ref="chatCont"> <div v-for="(item, index) in AllMessage" :key="index"> <div class="chatin" v-show='item.workerId !== mySelf'> <!-- 会议成员 --> <p class="time">{{item.weekDay}} {{item.sendTime}}</p> <img :src="getPhotoSrc(item.photoUrl)" class="img"> <em>{{item.workerName}}</em> <span v-if="item.content">{{item.content}}</span> <div class="imgShow" v-if="item.attachUrl"> <img :src="getSrc(item.attachUrl)" style="width: 113px; margin-top: 10px;border-radius: 5px"> </div> </div> <div class="chatout" v-show='item.workerId === mySelf'> <!-- 自己--> <p class="time">{{item.weekDay}} {{item.sendTime}}</p> <img :src="getPhotoSrc(item.photoUrl)" class="img"> <em>{{item.workerName}}</em> <span v-if="item.content">{{item.content}}</span> <div class="imgShow" v-if="item.attachUrl"> <img :src="getSrc(item.attachUrl)" style="width: 113px; margin-top: 10px; border-radius: 5px"> </div> </div> </div> </div> <div class="enterContent"> <div class="hold-All"> <input type="file" name="fileToUpload" id="fileToUpload" @change="fileSelected()" style="display:none;"> <i class="btn-upload" @click="uploadFile"></i> </div> <gs-el-input type="textarea" placeholder="请输入内容" v-model="textarea2"></gs-el-input> <gs-el-button type="primary" @click="submitBtn()" class="submit">发送</gs-el-button> </div> </div> </div>
js代码如下:
define(['vue'], function (Vue) { var _searchInit = function () { var app; app = new Vue({ el: '#serviceManagementLookForm', data: { url: '', textarea2: '', mySelf: {}, socket:null, stompClient:null, AllMessage: [], // 会上所有历史消息 taskInfo:{}, workerList:[], leaderList:[], responsibleList:[], requestList:[], eventList:[], userSocketId:'' }, methods: { fileSelected (file) { var fileObj = document.getElementById("fileToUpload").files[0]; this.submitBtn(fileObj); }, // 上传文件 uploadFile () { document.getElementById("fileToUpload").click(); }, // 判断当前时间是今天或者昨天 testDay(testTime){ var today = new Date(); var yesterday = new Date(today.valueOf() - 1000 * 60 * 60 * 24); var testYear = new Date(testTime).getFullYear(); var testMonth = new Date(testTime).getMonth(); var testDate = new Date(testTime).getDate(); if (yesterday.getFullYear() === testYear && yesterday.getMonth() === testMonth && yesterday.getDate() === testDate) { // 昨天 return 1; }else if (today.getFullYear() === testYear && today.getMonth() === testMonth && today.getDate() === testDate) { // 今天 return 2; } else { return 3; } }, // 获取会商所有消息 getAllMessage () { var that = this; jQuery.ajax({ url: api.zbglUrl + '/chat/queryChatRecordList', type: "post", data: { "taskId":$("#taskId").val() }, success: function (res) { if (res.code === 'success') { that.AllMessage = res.data; that.scrollHeight(); }else{ GS.$Message.warning(res["message"]); } } }); }, // connect connect(subTopic) { var that = this; that.mySelf = that.userSocketId; // 实例化socket var url = api.zbglSocketUrl; this.socket = new SockJS(`${url}`); this.stompClient = Stomp.over(this.socket); that.stompClient.connect({}, function connectCallback(frame) { // 订阅 /topic/* 订阅模式,可以同时订阅多个主题 that.stompClient.subscribe('/topic/'+ subTopic, function (response) { if(response.body){ var _response = JSON.parse(response.body); console.log(response.body,"_response"); _response.msgBody.forEach(function(item,index){ var _showTime = ''; var _createTime = item.createTime || new Date(item.creatTime).valueOf(); var whichDay = that.testDay(_createTime); switch (whichDay) { case 1: _showTime = "昨天 "+item.sendTime; break; case 2: _showTime = "今天 "+item.sendTime; break; default: _showTime = new Date(_createTime + 8 * 3600 * 1000).toJSON().replace(/T/g, ' ').substring(0, 19); break; } if(item.taskId === $("#taskId").val()){ that.AllMessage.push({ attachUrl:item.attachUrl, chatId: "", photoUrl:item.photoUrl, content: item.content, creatTime: item.creatTime, orderType: item.orderType, position: item.position, sendTime: item.sendTime, taskId: item.taskId, weekDay: item.weekDay, workerId:item.workerId, workerName: item.workerName, sendDate: _showTime, }) } }) } }); }, function errorCallBack(error) { // 连接失败时(服务器响应 ERROR 帧)的回调方法 console.log('stompWebSocket connect failed'); setTimeout(function(){ // var orgObj=JSON.parse(localStorage.getItem('yygl_orgObj')); // connect(orgObj.orgCode); connect(that.userSocketId); },120000); } ); that.stompClient.heartbeat.outgoing = 300000; that.stompClient.heartbeat.incoming = 0; //客户端不从服务端接收心跳包 }, // 发送消息 submitBtn (fileObj) { console.log(fileObj,"fileObj") var that = this; if(!that.textarea2 && !fileObj){ GS.$Message.warning("不能发送空白信息!"); return false; } if(that.textarea2){ jQuery.ajax({ url: api.zbglUrl + '/chat/addChatRecord', type: "post", data: { "content":that.textarea2, "orderType":"1", "taskId":$("#taskId").val(), "workerId":that.userSocketId }, success: function (res) { if (res.code === 'success') { that.$nextTick(() => { that.scrollHeight(); that.textarea2 = ''; }) }else{ GS.$Message.warning(res["message"]); } } }); }else if(fileObj){ console.log(fileObj,"fileObj") var form = new FormData(); form.append('chatFile', fileObj); form.append('taskId', $("#taskId").val()); form.append('content', that.textarea2); form.append('orderType','1'); form.append('workerId',that.userSocketId); jQuery.ajax({ url: api.zbglUrl + '/chat/addChatRecord', type: "post", data: form, processData: false, contentType: false, success: function (res) { if (res.code === 'success') { that.$nextTick(() => { that.scrollHeight(); that.textarea2 = ''; }) }else{ GS.$Message.warning(res["message"]); } } }); } }, scrollHeight () { this.$refs.chatCont.scrollTop = this.$refs.chatCont.scrollHeight; }, getSrc (item) { return api.zbglPicUrl + item; }, getPhotoSrc (item) { return api.zbglUrl + item; }, getData(){ var that = this; jQuery.ajax({ url: api.zbglUrl + '/securityTask/queryPlanDetail', type: "post", data: { "taskId":$("#taskId").val() }, success: function (res) { if (res.code === 'success') { that.eventList = res.data.eventList; that.requestList = res.data.requestList; that.taskInfo = res.data.taskInfo; res.data.workerList.forEach(function(item){ if(item.positionType == "1"){ that.leaderList.push(item); }else if(item.positionType == "3"){ that.workerList.push(item); }else if(item.positionType == "2"){ that.responsibleList.push(item); } }) }else{ GS.$Message.warning(res["message"]); } } }); } }, mounted: function () { var that = this; this.getData(); this.userSocketId = api.userSocketId; if (typeof callback === 'function') callback(); this.url = ""; // this.url = ApiConfig.apiHost + ApiConfig.service.screenImages; setTimeout(() => { that.connect(that.userSocketId); that.getAllMessage(); }, 1000) } }); //取消 返回列表页 $('#serviceManagementLookForm .reviewback').on('click', function () { //聊天记录已读取 jQuery.ajax({ url: api.zbglUrl + '/chat/updateChatMsgStatus', type: "post", data: { "taskId":$("#taskId").val(), "workerId":api.userSocketId }, success: function (res) { if (res.code === 'success') { }else{ GS.$Message.warning(res["message"]); } } }); $('#page').load(pathName + '/page/pages/ServiceSecurity/ServiceManagement/main.html', function () {}); }); window.onbeforeunload= function(event) { //聊天记录已读取 jQuery.ajax({ url: api.zbglUrl + '/chat/updateChatMsgStatus', type: "post", data: { "taskId":$("#taskId").val(), "workerId":api.userSocketId }, success: function (res) { if (res.code === 'success') { }else{ GS.$Message.warning(res["message"]); } } }); } } return { searchInit: _searchInit } });
四、原生websocket使用
具体看以下代码:
connect: function () { var that = this; var websocket = null; //判断当前浏览器是否支持WebSocket if('WebSocket' in window){ //连接WebSocket节点 //websocket = new WebSocket("ws://172.19.14.29:9888/ws/doorDevice/001"); websocket = new WebSocket(BASE_URL.webSocketUrl); } else{ alert('Not support websocket') } //连接发生错误的回调方法 websocket.onerror = function(){ setMessageInnerHTML("error"); }; //连接成功建立的回调方法 websocket.onopen = function(event){ heartCheck.reset().start(); // 成功建立连接后,重置心跳检测 setMessageInnerHTML("open"); } //接收到消息的回调方法 websocket.onmessage = function(event){ heartCheck.reset().start(); // 如果获取到消息,说明连接是正常的,重置心跳检测 setMessageInnerHTML(event.data); if(event.data.indexOf("deviceStatus")!=-1){ var results = JSON.parse(event.data); if(results.deviceStatus != 0){ $.ajax({ type: "post", url: BASE_URL.url + "/device/getCurrentDeviceInfo", data:{ sn:results.sn }, dataType: "json", success(ret) { if(ret) { var code = ret["code"]; if(code == "success") { // 播放声音 var audioPlay = function () { if (clearTimeOut && auuTimer) { clearTimeout(clearTimeOut); } if (auuTimer) { clearTimeout(auuTimer); } myAudio.currentTime = 0; myAudio.play(); myAudio.loop = "loop"; auuTimer = setTimeout(function () { myAudio.loop = ""; }, 9500); clearTimeOut = setTimeout(function () { myAudio.currentTime = 0; myAudio.pause(); }, 60000); }; // 播放声音 audioPlay(); $("#v-overall-popup").show(); var data = ret["data"]; that.deviceInfo = data.coverDevice; var state = data.coverDevice.deviceStatus; switch(state) { case 0: state = 'Normal' break; case 1: state = 'Opened' break; case 2: state = 'slanted' break; case 3: state = 'Leaked' break; } var mapX = parseFloat(data.coverDevice.mapX).toFixed(6); var mapY = parseFloat(data.coverDevice.mapY).toFixed(6); var GPSlocation = mapX + "," + mapY; $("#pop-id").html(data.coverDevice.deviceName); $("#pop-status").html(state); $("#pop-location").html(GPSlocation); $("#pop-time").html(data.coverDevice.updateTime); sidelettop.getList(); sideleftcenter.trendecharts(); siderightbot.getTableData(); window._initEnterpriseData(); clearTimeout(noticeTimer); var noticeTimer = setTimeout(function(){ $("#v-overall-popup").hide(); },10000) } } }, error(err) { sidelettop.getList(); sideleftcenter.trendecharts(); siderightbot.getTableData(); window._initEnterpriseData(); } }); }else{ window._initEnterpriseData(); sidelettop.getList(); sideleftcenter.trendecharts(); siderightbot.getTableData(); } } } //连接关闭的回调方法 websocket.onclose = function(){ setMessageInnerHTML("close"); } //监听窗口关闭事件,当窗口关闭时,主动去关闭websocket连接,防止连接还没断开就关闭窗口,server端会抛异常。 window.onbeforeunload = function(){ websocket.close(); } //将消息显示在网页上 function setMessageInnerHTML(innerHTML){ console.log(innerHTML,"innerHTML") } //关闭连接 function closeWebSocket(){ websocket.close(); } //发送消息 function send(){ var message = document.getElementById('text').value; websocket.send(message); } // 心跳检测, 每隔一段时间检测连接状态,如果处于连接中,就向server端主动发送消息,来重置server端与客户端的最大连接时间,如果已经断开了,发起重连。 var heartCheck = { timeout: 30000, serverTimeoutObj: null, reset: function(){ clearTimeout(this.serverTimeoutObj); return this; }, start: function(){ var self = this; this.serverTimeoutObj = setInterval(function(){ if(websocket.readyState == 1){ console.log("连接状态,发送消息保持连接"); websocket.send("time tick from:" + localStorage.getItem("localIpAddr")); heartCheck.reset().start(); // 如果获取到消息,说明连接是正常的,重置心跳检测 }else{ console.log("断开状态,尝试重连"); App.connect(); } }, this.timeout) } } },
五、点击的时候发现图标不显示

var point = new _self.gs2.geom.Point({ x : parseFloat(mapX), y : parseFloat(mapY), spatialReference: g2.geom.SpatialReference.EPSG3857 }); var _elements = []; var pictureMarker = new _self.gs2.syms.Picturemarkersymbol({ source: 'data:image/png;base64,iVBOg==', width: 32, height: 32, offsetX: 16, offsetY: 16, }); var element = new _self.gs2.ele.Element({ geometry : point, symbol : pictureMarker, }); _elements.push(element) _self.selectLayer.addElements(_elements);
解决方法:定义了数组 _elements,然后将生成的点element push到了 _elements,再addElements到点位图层selectLayer即可显示
心得:注意是addElements,是复数s,说明add的是多个,故要求是一个数组,单个的add不进去
六、标点功能以及切换楼层撒点
// 清除所有图层及事件及点位方法
clearLayersAndEvents: function() { var that = this; var arr = that.ZS.MONITOR.floor_g2map.getLayers(); for (var i = 0; i < arr.length; i++) { that.ZS.MONITOR.floor_g2map.removeLayer(arr[i]); i--; } that.ZS.MONITOR.floor_g2map.un("click"); that.ZS.MONITOR.floor_g2map.un("mousemove"); },
//清除当前点位图层上的所有点,即下图中的绿色点位所在的图层,保证点击楼层切换的时候,会清除然后重新加载
this.ZS.MONITOR.deviceLayer && this.ZS.MONITOR.deviceLayer.clear();
//清除矢量图纸图层,即下图蓝色框框所在的图层,保证点击楼层切换的时候,会清除然后重新加载
this.ZS.MONITOR.wfsLayer && this.ZS.MONITOR.wfsLayer.clear();
P.S. 切换楼层或者搜索的时候,需要清除之前的所有点,然后重新撒点

七、

浙公网安备 33010602011771号