Is there a way to bring a block's polygon (and its polylines) to the top layer?
I'm drawing polylines (to form polygons) for blocks in a city. Each block polygon is outlined with white polylines:
block = new google.maps.Polygon({
paths: blockCoordinates,
strokeColor: '#ffffff',
strokeOpacity: 1.0,
strokeWeight: 2,
fillColor: '#ff0000',
fillOpacity: shadeValue
}); }
When I hover over a block, I want the outline to turn black. I currently have this code:
google.maps.event.addListener(flightPath, 'mouseout', function (event) {
this.setOptions({
strokeColor: '#ffffff'
});
});
google.maps.event.addListener(flightPath, 'mouseover', function (event) {
this.setOptions({
strokeColor: '#000000'
});
});
However, it's not working on all the blocks.I think that is because (depending on the order of how the blocks are drawn), sometimes the polylines of other blocks are "above" the current block polylines.
If I set the white polylines to opacity of 0 (and black to an opacity of 1). It works fine but I, of course, don't get the pretty white lines between the blocks.
I had the same problem with several overlapping Polylines. The way I solved this is by initializing the Polyline with a zIndex. For you it should look something like:
block = new google.maps.Polygon({
paths: blockCoordinates,
strokeColor: '#ffffff',
strokeOpacity: 1.0,
strokeWeight: 2,
fillColor: '#ff0000',
fillOpacity: shadeValue,
zIndex: 1
}); }
Now you should able to change the zIndex of the Polylines using your mouseover and mouseout events like this:
google.maps.event.addListener(flightPath, 'mouseout', function (event) {
this.setOptions({
strokeColor: '#ffffff',
zIndex: 1
});
});
google.maps.event.addListener(flightPath, 'mouseover', function (event) {
this.setOptions({
strokeColor: '#000000',
zIndex: 2
});
});
The initialization isn't strictly necessary, but you could run into unexpected behavior if you don't.
Related
I have some code that loops through an array of airline routes and airports placing markers at each airport and drawing polylines between them. The code works and is fine when I have 400 routes. When I expand it to the full ~3500ish routes it grinds to a halt for nearly a minute rendering. Is there any way I can speed this up?
map.fitBounds(bounds);
var flightPath;
var flightPlanCoordinates;
$.each(routes, function(key, route) {
flightPlanCoordinates = [];
flightPlanCoordinates.push( markers[route.origincode].position );
flightPlanCoordinates.push( markers[route.destinationcode].position );
flightPath = new google.maps.Polyline({
path: flightPlanCoordinates,
geodesic: true,
strokeColor: '#004494',
strokeOpacity: 0.2,
strokeWeight: 1
});
flightPath.setMap(map); //commenting this line speeds things back up
google.maps.event.addListener(flightPath, 'mouseover', function (event) {
this.setOptions({
strokeOpacity: 1,
strokeWeight: 2
});
});
google.maps.event.addListener(flightPath, 'mouseout', function (event) {
this.setOptions({
strokeOpacity: 0.2,
strokeWeight: 1
});
});
});
I suggest you to request and decode the direction json data in background before the MapsActivity start. And your can also storage the decode LatLng in SharedPreferencd(eg: 1->(1.12,1.32), 2->(1.32, 2.52)) making it a flow-data instead of storage all date in an array which will cost you many resource and reduce the runnig-speed. At last, take LatLng data from SharedPreferenced and pain them.
When I initiate the map I have this listener:
google.maps.event.addListener(drawingManager, 'overlaycomplete', function(e) {
console.log('value of e');
console.log(e);
polyArray.push(e);
if (e.type != google.maps.drawing.OverlayType.MARKER) {
// Switch back to non-drawing mode after drawing a shape.
drawingManager.setDrawingMode(null);
}
setMapClickEvent(e.overlay, e.type);
setSelection(e.overlay);
});
Immediatly after this declaration I loop through the current rectangles that should be automatically drawn on the map. This is the code:
_.each($scope.currentRactangles, function(arr) {
new google.maps.Rectangle({
strokeColor: '#002288',
strokeOpacity: 0.8,
strokeWeight: 2,
fillColor: '#333322',
fillOpacity: 0.35,
map: map,
editable: true,
bounds: new google.maps.LatLngBounds(
new google.maps.LatLng(arr.upper_lat, arr.upper_lng),
new google.maps.LatLng(arr.lower_lat, arr.lower_lng)
)
});
});
Now, when map is loaded, the existing rectangles (fetched from database) are drawn on the map.
However, the listener never gets triggered.
If I manually draw a rectangle, the I can see in the console "value of e" and the event itself.
My question is: is it possible to trigger the listener when drawing rectangles programmatically?
All this because when I store the rectangles in database, I will store stuff inside the array "polyArray". Which only contains rectangles created manually.
Ok, solution was about storing in the array the newly created rectangles. Basically this snippet:
var tmprect = new google.maps.Rectangle({
strokeColor: '#002288',
strokeOpacity: 0.8,
strokeWeight: 2,
fillColor: '#333322',
fillOpacity: 0.35,
map: map,
editable: true,
bounds: new google.maps.LatLngBounds(
new google.maps.LatLng(arr.upper_lat, arr.upper_lng),
new google.maps.LatLng(arr.lower_lat, arr.lower_lng)
)
});
var newrect = {};
newrect.type = 'rectangle';
newrect.overlay = tmprect;
polyArray.push(newrect);
Even if the rectangles from database didn't generated an event they are now inside the same array that will also contain the rectangles manually drawn. That was enough for me as I only needed a way to store rectangles both from user and the automatically generated.
I am adding areas of interest in google maps using polygons and circles.
In each polygon and circle I'm adding an ID so I can get detailed information about that area if the user clicks on the polygon or circle.
There are cases that two areas overlap. By clicking the common area I'm able to get the ID for the object that is "above" but I have no way to get the ID of the object that lies "below". An example is given below.
Is there a way to get the IDs of overlapping objects?
The code that creates a polygon and a circle is given below.
function drawpolygonExersice(res, ExerciseID){
var points = new Array();
var ptn;
for (var j=0;j<res.length/2;j++)
{ptn = new google.maps.LatLng(res[2*j],res[2*j+1]);
points.push(ptn);}
var polygonExercise = new google.maps.Polygon({
path: points,
geodesic: true,
strokeColor: 'red',
strokeOpacity: 0.8,
strokeWeight: 1,
fillColor: "red",
fillOpacity: 0.20,
ID: ExerciseID, //look up ID
map: map
});
google.maps.event.addListener(polygonExercise, 'click', function(event) {
alert(this.ID);
});
exerciseAreas.push(polygonExercise);
}
function drawcircleExersice(res, ExerciseID) {
var circleExercise = new google.maps.Circle ({
center: new google.maps.LatLng(res[0],res[1]),
radius: res[2] * 1852, //Nautical miles to meters
geodesic: true,
strokeColor: 'red',
strokeOpacity: 0.8,
strokeWeight: 1,
fillColor:'red',
fillOpacity: 0.20,
ID: ExerciseID, //look up ID
map: map
});
google.maps.event.addListener(circleExercise, 'click', function(event) {
alert(this.ID);
});
exerciseAreas.push(circleExercise);
}
The only way I see is to iterate over all shapes and calculate(via geometry-library) if a shape contains the clicked latLng. It shouldn't be a problem with the expected amount of shapes.
For a circle use .computeDistanceBetween(clickedLatLng,circle.getCenter()), when the result is <=circle.getRadius() , the click has been on the circle.
For a polygon use .containsLocation(clickedLatLng,polygon), when it returns true the click has been on the polygon.
Demo: http://jsfiddle.net/doktormolle/qotg0o2x/
I am trying to get a dot like marker for Google Maps using google.maps.SymbolPath.CIRCLE - in which I am successful.
var dotMarkerImage = {
path: google.maps.SymbolPath.CIRCLE,
fillColor: 'blue',
fillOpacity: 0.7,
scale: 7,
strokeColor: '#000',
strokeWeight: 1
};
This successfully results in a blue circle, but I want a circle with a gradient.
Now Google says in Documentation that we can use all CSS3 colors. How do I use fillColor to accept a gradient?
For anyone who is familiar with Leaflet, do you know a way to dynamically change a polygon's color? For example, take a circle defined like this:
window.circle = L.circle([51.508, -0.11], 500, {
color: 'red',
fillColor: '#ffffff',
fillOpacity: 0.5
}).addTo(map);
Then later, after a user clicks a button somewhere on an interface (for example), I want to change the color of the circle like this:
window.circle.options.fillColor = "#dddddd";
The code changes the value for window.circle.options.fillColor, but the change is not reflected by a change to the color of the polygon on the map. I've searched around but haven't found anything. Any ideas?
Thanks.
L.Circle extends L.Path (http://leafletjs.com/reference.html#path), that have method setStyle( <Path options> object ), and you can apply new style as window.circle.setStyle({fillColor: '#dddddd'});
If you are looking for something like this:
const circle = L.circle([lat, lng], {
style: style,
onEachFeature: onEachFeature,
});
These options are available for geoJson data ie: L.geojson()..... :D
So, for polygon .
Try,
circle.setStyle({
color: 'red'
});
I have a set of polygons in my map, this code can change the fillcolor of each polygon dynamically :
// 'file' is a geojson layer
L.geoJSON(file, {
onEachFeature: colorlayer,
style: {
color: "#00008c",
opacity: 0.6,
fillColor: '#333333',
fillOpacity: 0
}
}).addTo(map);
function colorlayer(feature, layer) {
layer.on('mouseover', function (e) {
layer.setStyle({
fillOpacity: 0.4
});
});
layer.on('mouseout', function (e) {
layer.setStyle({
fillOpacity: 0
});
});
}