我有以下代码
var content = document.getElementById('popup-content');
var center = ol.proj.transform([44.6753, 25.7136], 'EPSG:4326', 'EPSG:3857'); //initial position of map
// ol.proj.fromLonLat([44.6753, 25.7136])
var view = new ol.View({
center: center,
zoom: 6
}); // {"unique_id": "Riyadh", "lat": 24.7136, "lon": 46.6753, "speed": 1}
//raster layer on map
var OSMBaseLayer = new ol.layer.Tile({
source: new ol.source.OSM()
});
straitSource = new ol.source.Vector({ wrapX: true });
var clusterLayer = new ol.layer.Vector({
source: new ol.source.Cluster({
source: straitSource,
distance: 40
})
});
map = new ol.Map({
layers: [OSMBaseLayer, clusterLayer],
target: 'map',
view: view,
controls: [new ol.control.FullScreen(), new ol.control.Zoom()]
});
var icon = new ol.style.Icon({
anchor: [0.5, 0.5], // Default value is the icon center.
scale: 0.3,
color: '#ffcd46',
crossOrigin: 'anonymous',
src: 'http://127.0.0.1:8081/static/img/truck128.png'
});
var iconStyle = new ol.style.Style({
image: icon
});
var styleCache = {};
clusterLayer.setStyle(function(feature) {
var size = feature.get('features').length;
if (size == 1 && map.getView().getZoom() > 16) { // size == 1 && resolution < map.getView.getResolutionForZoom(6)
// if a cluster of one show the normal icon
return iconStyle
} else {
// otherwise show the number of features
var style = styleCache[size];
if (!style) {
style = new ol.style.Style({
image: new ol.style.Circle({
radius: 10,
stroke: new ol.style.Stroke({
color: '#fff'
}),
fill: new ol.style.Fill({
color: '#3399CC'
})
}),
text: new ol.style.Text({
text: size.toString(),
fill: new ol.style.Fill({
color: '#fff'
})
})
});
styleCache[size] = style;
}
return style;
}
});
// Popup showing the position the user clicked
var container = document.getElementById('popup');
var popup = new ol.Overlay({
element: container,
autoPan: true,
autoPanAnimation: {
duration: 1000
}
});
/* Add a pointermove handler to the map to render the popup.*/
map.on('click', function (evt) { // 'pointermove'
var cluster = map.forEachFeatureAtPixel(evt.pixel, function (feat) {
return feat;
},{
// restrict to the cluster layer
layerFilter: function(layer) {
return (layer === clusterLayer);
}
});
if (cluster && map.getView().getZoom() > 16) {
map.addOverlay(popup);
var coordinate = evt.coordinate; //default projection is EPSG:3857 you may want to use ol.proj.transform
// list all the features in the cluster
content.innerHTML = '';
cluster.get('features').forEach(function(feature) {
content.innerHTML += (feature.get('desc') + '<br>');
});
popup.setPosition(coordinate);
} else {
popup.setPosition(undefined);
}
});
我希望能够根据达到的条件更改图标来源,例如:
if(obj.free_op) {/* use green truck icon*/}
else { /* use red truck icon */} }
更新
获得答案后的完整代码是问题,这是根据收到的最新更新为所有用户定义free
或busy
的图标:
map initiation
:
<script>
var content = document.getElementById('popup-content');
var center = ol.proj.transform([44.6753, 25.7136], 'EPSG:4326', 'EPSG:3857'); /
// ol.proj.fromLonLat([44.6753, 25.7136])
var view = new ol.View({
center: center,
zoom: 6
});
//raster layer on map
var OSMBaseLayer = new ol.layer.Tile({
source: new ol.source.OSM()
});
straitSource = new ol.source.Vector({ wrapX: true });
var clusterLayer = new ol.layer.Vector({
source: new ol.source.Cluster({
source: straitSource,
distance: 40
})
});
map = new ol.Map({
layers: [OSMBaseLayer, clusterLayer],
target: 'map',
view: view,
controls: [new ol.control.FullScreen(), new ol.control.Zoom()]
});
var container = document.getElementById('popup');
var popup = new ol.Overlay({
element: container,
autoPan: true,
autoPanAnimation: {
duration: 1000
}
});
/* Add a pointermove handler to the map to render the popup.*/
map.on('click', function (evt) { // 'pointermove'
var cluster = map.forEachFeatureAtPixel(evt.pixel, function (feat) {
return feat;
},{
// restrict to the cluster layer
layerFilter: function(layer) {
return (layer === clusterLayer);
}
});
if (cluster && map.getView().getZoom() > 13) {
map.addOverlay(popup);
var coordinate = evt.coordinate; //default projection is EPSG:3857 you may want to use ol.proj.transform
// list all the features in the cluster
content.innerHTML = '';
cluster.get('features').forEach(function(feature) {
content.innerHTML += (feature.get('desc') + '<br>');
});
popup.setPosition(coordinate);
} else {
popup.setPosition(undefined);
}
});
const list = document.querySelector('#menuList');
const searchBar = document.forms['search-truck'].querySelector('input');
searchBar.addEventListener('keyup', function(e){
const trucks = Array.from(list.getElementsByTagName('li'));
const term = e.target.value.toLowerCase();
trucks.forEach(function(truck){
const title = truck.textContent.toLowerCase();
if(title.includes(term)){
truck.style.display = 'inline-block';
}
else {
truck.style.display = 'none';
}
})
})
function arrayRemove(arr, value) {
return arr.filter(function(ele){
return ele != value;
});
}
</script>
Socket handling
<script>
var socket = new WebSocket("ws://127.0.0.1:8080/ws");
var menuList = document.querySelector('#menuList');
var devices = []; // new Array();
var markers = {}; // new Object();
socket.onopen = function (event) {}
socket.onoclose = function (event) {}
socket.onerror = function (error) {
console.log('Error ${error.message}')
}
socket.onmessage = function (event) {
console.log(event.data)
var messages = document.getElementById("messages");
messages.innerHTML += event.data;
var obj = JSON.parse(event.data);
// console.log(obj);
var device = obj.unique_id;
var data=[{"Lon":19.455128,"Lat":41.310575}];
var li = document.createElement('li');
// li.textContent = obj.unique_id; // .innerHTML
li.appendChild(document.createTextNode(obj.unique_id));
li.id = obj.unique_id;
const trucks = Array.from(list.getElementsByTagName('li'));
let found = trucks.findIndex((e) => e.id == obj.unique_id);
if (found === -1) {
li.setAttribute("lon", obj.lon);
li.setAttribute("lat", obj.lat);
menuList.appendChild(li);
} else {
const index = trucks.findIndex((e) => e.id === li.id);
trucks[index].setAttribute("lon", obj.lon);
trucks[index].setAttribute("lat", obj.lat);
}
menuList.addEventListener("click", function(e) {
if (e.target && e.target.matches("li")) {
var lon = Number(e.target.getAttribute('lon'));
var lat = Number(e.target.getAttribute('lat'));
view.animate({center: new ol.proj.fromLonLat([lon, lat])}, {zoom: 15.1});
}
});
if(obj.free_op) {console.log('obj.free_op 1: '+obj.free_op)}
else {console.log('obj.free_op 2: '+obj.free_op)}
var stdStyle = new ol.style.Style({
image: new ol.style.Icon({
anchor: [0.5, 0.5], // Default value is the icon center.
scale: 0.3, // resize imge
crossOrigin: 'anonymous',
src: 'http://127.0.0.1:8081/static/img/man_human-128.png'
})
});
var freeStyle = new ol.style.Style({
image: new ol.style.Icon({
anchor: [0.5, 0.5], // Default value is the icon center.
scale: 0.3, // resize imge
color: '#49fc82', // green
crossOrigin: 'anonymous',
src: 'http://127.0.0.1:8081/static/img/man_human-128.png'
})
});
var busyStyle = new ol.style.Style({
image: new ol.style.Icon({
anchor: [0.5, 0.5], // Default value is the icon center.
scale: 0.3,
color: '#ff704d', // busy
crossOrigin: 'anonymous',
src: 'http://127.0.0.1:8081/static/img/man_human-128.png'
})
});
var styleCache = {};
clusterLayer.setStyle(function(feature) {
var size = feature.get('features').length;
if (size == 1 && map.getView().getZoom() > 13) {
if (obj.free_op) { return freeStyle; }
else { return busyStyle; }
} else {
var style = styleCache[size];
if (!style) {
style = new ol.style.Style({
image: new ol.style.Circle({
radius: 10,
stroke: new ol.style.Stroke({
color: '#fff'
}),
fill: new ol.style.Fill({
color: '#3399CC'
})
}),
text: new ol.style.Text({
text: size.toString(),
fill: new ol.style.Fill({
color: '#fff'
})
})
});
styleCache[size] = style;
}
return style;
}
});
var desc = `Person/Vehicle: <h5>` + obj.unique_id + `<h5>
<form id="task_form" action="/" method="post" accept-charset="utf-8">
<input type="hidden" name="status" value='New'>
<input type="hidden" name="command" value='Task'>
<input type="hidden" name="truck_id" value=` + obj.unique_id + `>
Task: <input type="text" name="task"><br>
Details: <textarea name="details" rows="4" cols="50"></textarea><br>
Customer Name: <input type="text" name="customer"><br>
Mobile: <input type="number" name="mobile"><br>
Address: <br>
<input type="number" name="lon" placeholder="longitude">
<input type="number" name="lat" placeholder="latitude"><br>
<textarea name="address" placeholder="Address details/notes" rows="4" cols="50"></textarea><br>
Schedule: <input type="date" name="datePicker" value= "2019-01-01"
min="2019-01-01" max="2020-12-31">
<input type="time" name="timePicker" value="00:00"><br><br><br>
</form>
<button onclick="handleFormSubmit(document.forms['task_form'], '/')">Login</button>
`
var iconFeature = new ol.Feature({
geometry: new ol.geom.Point(ol.proj.transform([obj.lon, obj.lat], 'EPSG:4326', 'EPSG:3857')),
type: 'Point',
desc: desc
});
iconFeature.setStyle(stdStyle);
if(!devices.includes(device)) {
devices.push(device);
var coordinates = [obj.lon, obj.lat];
markers[device]= iconFeature;
straitSource.addFeature(iconFeature);
} else {
// devices = devices.filter(function(value, index, arr){ return value != device; });
straitSource.removeFeature(markers[device]);
straitSource.addFeature(iconFeature);
markers[device]= iconFeature;
}
};
</script>
答案 0 :(得分:2)
ol.style.Icon
没有setSrc
方法,因此您需要为每个源创建一个。然后根据需要在ol.style.Style
中进行设置:
if (size == 1 && map.getView().getZoom() > 16) { // size == 1 && resolution < map.getView.getResolutionForZoom(6)
// if a cluster of one show the normal icon
iconStyle.setImage(obj.free_op ? greenIcon : redIcon);
return iconStyle
} else { }
或为每个图标创建完整的ol.style.Style
,然后在样式函数中返回相应的图标:
if (size == 1 && map.getView().getZoom() > 16) { // size == 1 && resolution < map.getView.getResolutionForZoom(6)
// if a cluster of one show the normal icon
if (obj.free_op) { return greenIconStyle; }
else { return redIconStyle; }
} else { }
完整代码如下所示:
var greenIconStyle = new ol.style.Style({
image: new ol.style.Icon({
anchor: [0.5, 0.5],
scale: 0.3,
color: '#ffcd46',
crossOrigin: 'anonymous',
src: 'http://127.0.0.1:8081/static/img/greenIcon.png'
})
});
var redIconStyle = new ol.style.Style({
image: new ol.style.Icon({
anchor: [0.5, 0.5],
scale: 0.3,
color: '#ffcd46',
crossOrigin: 'anonymous',
src: 'http://127.0.0.1:8081/static/img/redIconStyle.png'
})
});
if (size == 1 && map.getView().getZoom() > 16) {
if (obj.free_op) { return greenIconStyle; }
else { return redIconStyle; }
} else {
}
iconFeature.setStyle( obj.free_op ? greenIconStyle : redIconStyle)
更新 您需要将卡车的free_op值设置为功能属性
var iconFeature = new ol.Feature({
geometry: new ol.geom.Point(ol.proj.transform([obj.lon, obj.lat], 'EPSG:4326', 'EPSG:3857')),
type: 'Point',
desc: desc,
free_op: obj.free_op
});
并在样式功能中对其进行测试
clusterLayer.setStyle(function(feature) {
var features = feature.get('features');
var size = features.length;
if (size == 1 && map.getView().getZoom() > 13) {
if (features[0].get('free_op')) { return freeStyle; }
else { return busyStyle; }
} else { }