Folium with Mapbox layer blank - maps

I am trying to use Folium with a Mapbox layer and it keeps failing with an error: ValueError: You must pass an API key if using Cloudmade or non-default Mapbox tiles. I am passing it an API key however.
mapbox_api_key = r"pk.eyJ1Ijoi ... " #the whole key is long, assigned by Mapbox
Map = folium.Map(location=[centroid.geometry.y, centroid.geometry.x],
zoom_start=8,
tiles = "Mapbox",
API_key = mapbox_api_key)
Map.save("map.html")
This returns a blank map. What am I doing wrong?

Related

Updating folium coordinates on callback in dash app

I am trying to update the coordinates of a folium map rendered by a Dash App on a callback (which is running inside a Flask App). The callback selectively renders different layers on a map - the issue is that the zoom and center coordinates are not persisted when the map is updated. The map is rendered as html and injected as in iframe into the app.
Addendum: Not a professional programmer, have only been trying my hand at this for the past six months.
I have tried three approaches:
JS API call client-side to flask route. I ended up realizing this had too much overhead (plus couldn't identify user to update the proper coordinates).
Encoding the coordinates and zoom in the URL. The URL changes as expected from this js snippet:
map_layer.on("mouseup zoomend", function(){
var coordinates = map_layer.getCenter();
var lat = coordinates.lat
var lon = coordinates.lng
var zoom = map_layer.getZoom();
parent.history.replaceState({}, '', `/app/layer?&lat=${lat}&lon=${lon}&zoom=${zoom}`);
// const ON_CHANGE = '_dashprivate_historychange';
// window.dispatchEvent(new CustomEvent(ON_CHANGE));
// parent.window.dispatchEvent(new CustomEvent(ON_CHANGE));
console.log("success");
The commented-out code also tries to dispatch a CustomEvent to dash to try and update it's history - not really clear what's happening there - just tried to emulate this approach.
The right URL is not passed on to the callback however. So despite the url changing on the browser, it's not being sent back with the updated query variables. If I refresh the page and actively send the URL, than the right URL is passed on, but that's not the kind of behavior I'm looking for - I would like for it to change with no active reloading of the page:
#layer.callback(
Output("map", "srcDoc"),
-- other inputs --,
Input('url', 'href') #tried State as well
)
def update_output_src(href):
print(href)
-- other code --
return map.get_root().render()
Using a hidden DIV to store the coordinates. The div content changes as expected from this js snippet:
map_layer.on("mouseup zoomend", function(){
var coordinates = map_layer.getCenter();
var lat = coordinates.lat
var lon = coordinates.lng
var zoom = map_layer.getZoom();
var latstore = parent.document.getElementById('latstore');
latstore.textContent = lat; #trying different approaches in what's changed to see if dash callback captures it.
var lonstore = parent.document.getElementById('lonstore');
lonstore.innerText = lon;
var zoomstore = parent.document.getElementById('zoomstore');
zoomstore.innerHTML = zoom;
console.log("success");
But again I am not able to capture the stored coordinates when the input is triggered.
#layer.callback(
Output("map", "srcDoc"),
-- other inputs --,
State('latstore', 'children'),
State('lonstore', 'children'),
State('zoomstore', 'children'),
)
def update_output_src(latstore, lonstore, zoomstore):
print(latstore, lonstore, zoomstor)
-- other code --
return map.get_root().render()
Any help or pointer in the right direction for approaches 2 or 3 would be super useful. I have been struggling with this for 3-4 days now and I'm out of ideas.

mxCodec doesn't decode xml correctly

I integrated mxGraph(mxgraph npm package) in my react app, so when I trying to load graph using xml, I am getting an error in console
TypeError: geo.clone is not a function
The same I am doing in single html file and it's working.
I investigated and found that the mxCell in react app is different from the html one.
In case of HTML there is filled geometry prop instead of react(check screens below)
Сan someone help me to decode xml correctly?
Decoded mxCell from single HTML console: https://monosnap.com/file/yAHAi29zFGFpauqU2RtDcvmfPpZ0YJ
Decoded mxCell from React app console: https://monosnap.com/file/0XxPwyEracX7hMCnMHckAmI8Rl6OEh
Source code from React component:
const graph = new mx.mxGraph(this.automationRef.current)
new mx.mxRubberband(graph);
const xml = '<root>...</root>';
const doc = mx.mxUtils.parseXml(xml);
const codec = new mxCodec(doc);
let elt = doc.documentElement.firstChild;
const cells = [];
while (elt != null){
const cell = codec.decodeCell(elt)
cells.push(cell);
graph.refresh();
elt = elt.nextSibling;
}
graph.addCells(cells);
Found the issue.
Here's the solution:
https://github.com/jgraph/mxgraph/issues/301#issuecomment-514284868
Quote:
you should add
window['mxGraphModel'] = mxGraphModel;
window['mxGeometry'] = mxGeometry;
before
let doc = mxUtils.parseXml(xml);
let codec = new mxCodec(doc);
codec.decode(doc.documentElement, graph.getModel());'
I found that the decode method resolve xml need windows param
End quote

How to draw map using new Lat Lng in ionic

I am passing proper latitude and longitude to the map but it shows old map, having old lat lng. I know I am doing something wrong in this, but I can't figure out it. My project in ionic framework and for map I am using this plugin map plugin
This my html code
<div style="width:100%;height:200px" id="mapDisplay"></div>
This my angularJS code
var getLat = $scope.dealer.lat;
var getLng = $scope.dealer.lng;
var address = $scope.dealer.address;
var mapDiv = document.getElementById("mapDisplay");
const myGeoLocation = new plugin.google.maps.LatLng(getLat,getLng);
var map = plugin.google.maps.Map.getMap(mapDiv, {
'camera': {
'latLng': myGeoLocation,
'zoom': 15
}
});
map.addEventListener(plugin.google.maps.event.MAP_READY, function() {
map.addMarker({
'position': myGeoLocation,
'title': address
}, function(marker) {
marker.showInfoWindow();
});
});
From the docs of the map plugin you are using
This plugin generates only one map instance using the Map.getMap()
method. In general, you may want to create multiple maps, but this
plugin doesn't allow it.
So your plugin.google.maps.Map.getMap is only grabbing the existing instance, not creating a new one and the plugin.google.maps.event.MAP_READY is only fired once, the first time. However looking at the source code it looks like the instance exposes a remove method which you can use to destroy the existing instance and create a new one with the new sets of coordinates when the callback is called, e.g: map.remove(function() { /** reset map coordinates **/ }
** Extra **
If you just need to display a map with a set of coordinates you can do it using the native app by passing lat/lon to the $cordovaInAppBrowser plugin. As an example for iOS and Android you'd have the following:
iOS
$cordovaInAppBrowser.open('maps://?q=<latitude>,<longitude>', '_system');
Android
$cordovaInAppBrowser.open('geo:0,0?q=<latitude>,<longitude>', '_system');
And finally you need to enable the geo uri in your config.xml like so:
<allow-intent href="geo:*" />
The plugin doesn't allow to create multiple maps instance More detail.
But you can achieve this by using this code
var map = plugin.google.maps.Map.getMap(div);
map.clear();
map.off();
map.trigger("test");
map.addEventListener(plugin.google.maps.event.MAP_READY);

Cannot access Google Geocoding API response object

my first message :)
well, i am trying to write a weather Spa with angular.
as part of the model , i need to grab the location Lat and Lon so im using google geocoding api.
after using $resource.get i am successfully getting the object from google but cant access it.
here is my code :
weatherApp.controller('forecastController'['$scope','location','$resource',function($scope,location,$resource){
$scope.toGoogle = location.toGoogle;
$scope.resource = $resource('http://maps.googleapis.com/maps/api/geocode/json?');
$scope.georesult = $scope.resource.get({address:$scope.toGoogle,Key:"somekey"})
console.log(angular.fromJson($scope.georesult));
}]);
$scope.toGoogle is just a var holding the address which needs to be translated into x and y
the thing is - i am getting a response with the object i was expected, but when i am trying to access it with:
console.log(angular.fromJson($scope.georesult.results[0].geometry.location.lat));
I am getting "TypeError: Cannot read property '0' of undefined"
(Please note that i have already transformed the Json into regular object with Angular.fromJson);
Any suggestions ? thanks in advance.

Yelp API key not working in Sencha Architect demo code

I am using the tutorial here : http://docs.sencha.com/architect/3/tutorials/first_mobile_application.html#The_Controller
getBusinesses: function(location, callback) {
// Note: Obtain a Yelp API key by registering (for free)
// with Yelp at http://www.yelp.com/developers/getting_started/api_overview
// (in this app, we use the Review Search API v1.0)
var store = Ext.data.StoreManager.lookup('BusinessStore'),
yelpKey = '', // Enter your Yelp API key here
url = 'http://api.yelp.com/business_review_search' +
'?ywsid=' + yelpKey +
'&term=Bars' +
'&lat=' + location.coords.latitude +
'&long=' + location.coords.longitude;
store.getProxy().setUrl(url);
store.load(function() {
callback(store);
});
}
I applied for an API key on Yelp and got the following:
I am not sure which one to use. The tutorial code has placeholder for one single key as in the code above
The completed app shows error: Uncaught TypeError: Cannot read property 'setStore' of undefined at:
me.getBusinesses(location, function (store) {
// Bind data to the list and display it
me.getDataList().setStore(store);
You need the API v1.0 key.
getDataList() returns undefined because the View does not exist. You may have forgotten to name the List view in the ListContainer, see "List View - Step 4". Also, the function name is derived from whatever you set the reference to in *"The Controller - Step 7". Naming it datalist will make the function getDatalist(), whereas naming it dataList will make it getDataList(). Note the capital "L".
Hope this helps others running into the problem.

Resources