I am trying to manage Google Maps Api in order to work within Flask.
However it doesn't give any error, but it doesn't render the map itself.
It work perfectly on simple .html however Flask is having problem rendering map.js file itself
map.js
// Initiation of marker for Google Maps Api
function initMap() {
var map = new google.maps.Map(document.getElementById("map"), {
zoom: 8,
center: {
lat: 52.857500,
lng: -8.987437
}
});
var labels = "ABCDEFGHIJKLMONPQRSTUVWXYZ";
var locations = [{
lat: 52.857500,
lng: -8.987437
}];
var markers = locations.map(function(location, i) {
return new google.maps.Marker({
position: location,
label: labels[i % labels.length]
});
});
var markerCluster = new MarkerClusterer(map, markers, {
imagePath: 'https://developers.google.com/maps/documentation/javascript/examples/markerclusterer/m'
});
}
Flask Code
{% extends 'base.html' %}
{% block content %}
<!-- content -->
<div class="section no-pad-bot" id="index-banner">
<div class="container">
<br><br>
<div class="row center"></div>
<h2 class="header center black-text">How to approach our office ? </h2>
<div class="row center">
<h5 class="header col s12 light">85 Aughanteeroe<br> Gort Road <br> Ennis <br> Co. Clare<br>V95 CXV2<br>Ireland</h5>
</div>
<div class="row center" id="map">
<br>
</div>
</div>
</div>
<script src="https://developers.google.com/maps/documentation/javascript/examples/markerclusterer/markerclusterer.js"></script>
<script async defer src="https://maps.googleapis.com/maps/api/js?key=AIzaSyCef1gneSCdkePrWnkXROPQUynW490rnd4&callback=initMap"></script>
<script src="{{url_for('static', filename='js/map.js')}}"></script>
Related
i have list of lat long stored in db $order->customers->location_url and (location_url = 31.5952599,74.3526989 have data in this form) using foreach loop i am trying to print all markers on map in model but when i click to button it shows blank screen check screen shot even doesnot start map
here is my code that i am using to show map
html
<button class="btn-sm" type="button" data-toggle="modal" onclick ='initialize();' data-target="#map-modal-points">Show All Points</button>
model
<div class="modal fade" id="map-modal-points" tabindex="-1" role="dialog" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title">All Shops</h5>
<button class="close" type="button" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
<div class="modal-body">
<div id="map_canvas" style="height: 400px"></div>
</div>
<div class="modal-footer">
<button class="btn btn-secondary">Close</button>
</div>
</div>
</div>
</div>
java script
<script type="text/javascript" src="https://www.google.com/jsapi"></script>
<script>
function initialize() {
var locations = [
#foreach ($orders as $order)
[ {{ $order->customers->location_url }} ]
#endforeach
];
var map = new google.maps.Map(document.getElementById('map_canvas'), {
zoom: 10,
center: new google.maps.LatLng(-33.92, 151.25),
mapTypeId: google.maps.MapTypeId.ROADMAP
});
var infowindow = new google.maps.InfoWindow();
var marker, i;
for (i = 0; i < locations.length; i++) {
marker = new google.maps.Marker({
position: new google.maps.LatLng(locations[i]),
map: map
});
google.maps.event.addListener(marker, 'click', (function(marker, i) {
return function() {
infowindow.setContent(locations[i][0]);
infowindow.open(map, marker);
}
})(marker, i));
}
}
</script>
i am using this code to print map Laravel and google maps : foreach latitude/longitude show marker or map
is there any other way i can print all markers ? or what mistake i am making in it?
Currently the code uses Vue.js to manage the inputs and post requests and is using JavaScript to handle things like Google Map functionality.
The issue is that when we wrap a div id around all the current HTML on a page so the Vue.js functionality works, it results in the Google Map code in a JavaScript file to run incorrectly and loads the page with no map. As soon as the Vue.js id (adminVenueVue) is removed the map works fine.
When trying to debug the issue it seems that the function that is responsible for updating the map doesn't run all the way through and stops when a listener function is created as no following code would run after. Below shows this function if you need more code please tell me.
function initCreateUpdateVenue() {
var mapCenter = new google.maps.LatLng({
lat: 54.445886,
lng: -3.435974
});
var marker, london = {
lat: 52.41,
lng: -1.69
};
var ZoomLevel = 5;
map = new google.maps.Map(document.getElementsByName('googleMap')[0], {
zoom: ZoomLevel,
center: mapCenter,
mapTypeId: google.maps.MapTypeId.ROADMAP
});
map.setZoom(5);
var input = (document.getElementsByName("autocomplete")[0]);
var options = {
componentRestrictions: {
country: "uk"
}
};
var autocomplete = new google.maps.places.Autocomplete(input, options);
autocomplete.bindTo('bounds', map);
autocomplete.addListener('place_changed', function() {
var element = document.getElementsByName("autocomplete")[0];
//remove any errors
element.classList.remove("is-invalid");
var place = autocomplete.getPlace();
if (!place.geometry) {
return;
}
populate_hidden_fields(place);
set_venue_detail_fields(place);
populate_fields(place.address_components);
set_map_location();
});
}
Here is the HTML code (the Google Map code is at the bottom)
<div id="adminVenueVue">
<div class="row">
<div class="col-lg-12 ">
<div class="row">
<div class="col-lg-12 ui-sortable-disabled">
<div class="panel">
<div class="panel-heading disable-draggable">Administrator Controls</div>
<div class="panel-body">
#include('venue.components.admin_controls', ['submitButtonText' => 'Add Type'])
</div>
</div>
</div>
</div>
<div class="row">
<div class="col-lg-12 ui-sortable-disabled">
<div class="panel">
<div class="panel-heading disable-draggable">Start by finding your address</div>
<div class="panel-body">
#include('venue.components.autocomplete-form', ['submitButtonText' => 'Add Type'])
</div>
</div>
</div>
</div>
<div class="row">
<div class="col-lg-6 ui-sortable-disabled">
<div class="panel">
<div class="panel-heading disable-draggable">Venue Details</div>
<div class="panel-body" style="padding-bottom: 16px;">
#include('venue.components.venue-details', ['submitButtonText' => 'Add Type'])
</div>
</div>
</div>
<div class="col-lg-6 ui-sortable-disabled">
<div class="panel">
<div class="panel-heading disable-draggable ">Address Details</div>
<div class="panel-body">
#include('venue.components.form', ['submitButtonText' => 'Submit Venue'])
</div>
</div>
</div>
</div>
</div>
</div>
<div class="row">
<div class="col-lg-12 ui-sortable-disabled">
<div class="panel">
<div class="panel-heading disable-draggable">Map</div>
<div class="panel-body">
<div id="googleMap" name="googleMap" class="width-full" style="height: 500px;"></div>
</div>
</div>
</div>
</div>
</div>
I recommend using the Vue google map component (vue2-google-maps).
Follow this example code:
<body>
<div id="root">
<google-map :center="{lat: 1.38, lng: 103.8}" :zoom="12" style="width: 100%; height: 500px">
<ground-overlay source="./overlay.png" :bounds="{
north: 1.502,
south: 1.185,
east: 104.0262,
west: 103.5998,
}" :opacity="0.5">
</ground-overlay>
</google-map>
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.0/vue.js"></script>
<script src="vue-google-maps.js"></script>
<script>
Vue.use(VueGoogleMaps, {
load: {
key: 'AIzaSyBzlLYISGjL_ovJwAehh6ydhB56fCCpPQw',
v: '3.26',
},
// Demonstrating how we can customize the name of the components
installComponents: false,
});
document.addEventListener('DOMContentLoaded', function() {
Vue.component('google-map', VueGoogleMaps.Map);
Vue.component('ground-overlay', VueGoogleMaps.MapElementFactory({
mappedProps: {
'opacity': {}
},
props: {
'source': {type: String},
'bounds': {type: Object},
},
events: ['click', 'dblclick'],
name: 'groundOverlay',
ctr: () => google.maps.GroundOverlay,
ctrArgs: (options, {source, bounds}) => [source, bounds, options],
}));
new Vue({
el: '#root',
data: {
place: '',
},
});
});
</script>
</body>
Or, if you're using webpack and Vue file components, follow the instructions bellow.
First install it : npm install vue2-google-maps
Then register it in main.js file
import Vue from 'vue'
import * as VueGoogleMaps from 'vue2-google-maps'
Vue.use(VueGoogleMaps, {
load: {
key: 'YOUR_API_TOKEN',
libraries: 'places', // This is required if you use the Autocomplete plugin
}
})
So, you can use it like a component:
<GmapMap
:center="{lat:10, lng:10}"
:zoom="7"
map-type-id="terrain"
style="width: 500px; height: 300px"
>
<GmapMarker
:key="index"
v-for="(m, index) in markers"
:position="m.position"
:clickable="true"
:draggable="true"
#click="center=m.position"
/>
</GmapMap>
More at:
https://www.npmjs.com/package/vue2-google-maps
https://github.com/xkjyeah/vue-google-maps/blob/no-deferred-ready/examples/overlay.html
https://alligator.io/vuejs/vue-google-maps/ (tutorial)
Hello guys i am creating a form that works really well but when i want to set the localisation of the place but now i have to set it manually (with latitude and logitude), so i create a map with dragable marker and when i drag the marker the value lat and lng changes (in the console) but now i want to set it in the form (because the values are changing but not save) and i would like to change vlaues of latitude and longitude when i change the position of mark (so i want to set latitude with the value lat and longitude with the value lng)
My form html (in twig with symfony) :
{% extends 'base.html.twig' %}
{% block body %}
<!-- Left and right buttons -->
<div class="col-8 mx-auto">
<br/><br/><br/><br/>
<div class="card">
<div class="card-header header-elements-inline">
<h6 class="card-title">Create a place</h6>
</div>
<br/>
<div class="card-body">
{{ form_start(form) }}
<div class="form-group">
<label for="form_username">Content :</label>
{{ form_widget(form.content) }}
</div>
<div class="form-group">
<label for="form_username">Title:</label>
{{ form_widget(form.title) }}
</div>
<div class="form-group">
<label for="form_username">Theme:</label>
{{ form_widget(form.theme) }}
</div>
<div class="form-group">
<label for="form_username">Max users:</label>
{{ form_widget(form.maxUser) }}
</div>
<div class="form-group">
<label for="form_username">timeLenght:</label>
{{ form_widget(form.timeLength) }}
</div>
<div class="form-group">
<label for="form_username">Longitude:</label>
{{ form_widget(form.longitude) }}
</div>
<div class="form-group">
<label for="form_username">Latitude:</label>
{{ form_widget(form.latitude) }}
</div>
<div class="card px-3">
<br/>
<!-- Basic map -->
<div class="map-container" id="map_marker_simple"></div>
{% block javascripts_map %}
{% endblock %}
<br/>
<!-- /basic map -->
</div>
<!-- /custom handle -->
</div>
<div class="d-flex justify-content-end align-items-center">
<button type="submit" class="btn bg-blue" id="create">Submit<i class="icon-paperplane ml-2"></i></button>
</div>
{{ form_end(form) }}
</div>
</div>
</div>
<!-- /left and right buttons -->
{% endblock %}
and my part js of the form :
{% extends 'admin/user/new_place.html.twig' %}
{% block javascripts_map %}
<script type="text/javascript">
/* -------------------------------------------------------------------
-----------
*
* # Basic markers
*
* Specific JS code additions for maps_google_markers.html page
*
* ---------------------------------------------------------------------------- */
// Setup module
// ------------------------------
var GoogleMapMarkerBasic = function() {
//
// Setup module components
//
// Line chart
var _googleMapMarkerBasic = function() {
if (typeof google == 'undefined') {
console.warn('Warning - Google Maps library is not
loaded.');
return;
}
// Setup map
function initialize() {
// Define map element
var map_marker_simple_element =
document.getElementById('map_marker_simple');
// Set coordinates
var myLatlng = new google.maps.LatLng(('{{ place.latitude
}}'), ('{{ place.longitude }}'));
// Options
var mapOptions = {
zoom: 10,
center: myLatlng
};
// Apply options
var map = new google.maps.Map(map_marker_simple_element, mapOptions);
var contentString = 'Marker';
// Add info window
var infowindow = new google.maps.InfoWindow({
content: contentString
});
// Add marker
var marker = new google.maps.Marker({
position: myLatlng,
map: map,
draggable: true,
title: ('{{ place.title }}'),
animation: google.maps.Animation.DROP
});
marker.addListener('drag', function() {
infowindow.open(map,marker);
var lat = marker.getPosition().lat();
var lng = marker.getPosition().lng();
console.log(lat, lng)
});
// Attach click event
};
// Initialize map on window load
google.maps.event.addDomListener(window, 'load', initialize);
};
return {
init: function() {
_googleMapMarkerBasic();
}
}
}();
// Initialize module
// ------------------------------
document.addEventListener('DOMContentLoaded', function() {
GoogleMapMarkerBasic.init();
});
</script>
{% endblock %}
This is the view of the form :
Thx for all that will try to answer :)
All you have to do is to change the latitude and longitude input value through javascript.
Vanilla javascript:
document.getElementById("your_latitude_field").value = marker.getPosition().lat();
document.getElementById("your_longitude_field").value = marker.getPosition().lng();
JQuery:
$("#your_latitude_field").val(marker.getPosition().lat());
$("#your_longitude_field").val(marker.getPosition().lng());
I'm working on learning Angular with Google maps and having difficulty rendering a map within a div controlled by an ng-if directive.
For my application, I would like the map render upon receiving the coordinates from the $scope.location function. I would then click on a button and invoke $scope.myRide in order to place a marker on the map. However, what is happening is that the map does not render until I click on the button.
The coordinates within $scope.map are serve as placeholders until the actual coordinates are received from $scope.location.
Any assistance will be greatly appreciated :)
angular.module('MapView',[])
.config(function($stateProvider){
$stateProvider
// the state will go on the html that you want route the user.
.state('mapView', {
url: '/mapView',
templateUrl: 'app/mapView/mapView.html',
controller: function($scope){
$scope.map = { center: { latitude: 38, longitude: -122 }, zoom: 15 };
$scope.output = document.getElementById("loc");
$scope.maker = {};
$scope.coords = {};
$scope.mockUsers = [{username: 'young', mess: 'I need a ride at 9am'},{username: 'young', mess: 'I need a ride at 9am'}, {username: 'young', mess: 'I need a ride at 9am'}]
$scope.location = function(){
if (!navigator.geolocation){
output.innerHTML = "<p>Geolocation is not supported by your browser</p>";
return;
}
navigator.geolocation.getCurrentPosition(function(position){
console.log('current position',position.coords)
$scope.map.center.latitude = position.coords.latitude;
$scope.coords.lat = position.coords.latitude; //added this
$scope.map.center.longitude = position.coords.longitude;
$scope.coords.lon = true; // added this
}, function(){
$scope.output.innerHTML = "Unable to retrieve your location";
});
}()
$scope.myRide = function(){
$scope.maker.latitude = $scope.map.center.latitude;
$scope.maker.longitude = $scope.map.center.longitude;
}
},
controllerAs: 'LoginCtrl'
});
})
The following is the HTML:
<div ui-sref='mapView' >
<div ng-show = "coords.lon == true">Hello</div>
<div id="loc"></div>
<div id="mapDiv" ng-if="coords.lon">
<ui-gmap-google-map center='map.center' zoom='map.zoom' maker=>
<ui-gmap-marker coords="maker" icon="icon" idkey="1"></ui-gmap-marker>
</ui-gmap-google-map>
</div>
<div class="btn-Center">
<button class="btn btn-danger" ng-click='myRide()' >Ride</button>
</div>
<div id="mapUsers">
<div class="clear" ng-repeat='user in mockUsers'>
<div class="mapUserImg">
<img class="img-responsive" src="http://falconbus.in/images/site/user_icon.png">
</div>
<h1> {{ user.username }} </h1>
<p> {{ user.mess}} </p>
</div>
</div>
</div>
I have some recomendations,
1) for debugging you can install the chrome extension ng-inspector in there you can view what value you have in center and zoom when you are in the html side, check if the data have sense.
2) i thing you use angular-google-maps from angular-ui if is true, you have two errors,
<div id="mapDiv" ng-if="coords.lon">
<ui-gmap-google-map center='map.center' zoom='map.zoom' **maker=**>
<ui-gmap-marker coords="maker" **icon="icon"** idkey="1"></ui-gmap-marker>
</ui-gmap-google-map>
marker empty is not necesesary and icon do are inside to options like the example in the official website.
<div id="map_canvas" ng-controller="mainCtrl">
<ui-gmap-google-map center="map.center" zoom="map.zoom" draggable="true" options="options">
<ui-gmap-marker coords="marker.coords" options="marker.options" events="marker.events" idkey="marker.id">
</ui-gmap-marker>
</ui-gmap-google-map>
<div ng-cloak>
<ul>
<li>coords update ctr: {{coordsUpdates}}</li>
<li>dynamic move ctr: {{dynamicMoveCtr}}</li>
</ul>
</div>
3) in the anglar-google-maps website you can use Edit in Plnkr for made some first test to familiarize with this directives
[<script src="~/Scripts/app/Home.js"></script>
<div class="container">
<div class="row">
<div class="col-md-12">
<h1>AngularJS Examples</h1>
<div ng-app="myApp" style="width:400px;">
<div ng-controller="homeController">
<table class="table table-striped table-bordered">
<tbody>
<tr>
<td>Person Name:</td>
<td>
<input type="text" ng-model="Person.personName" />
</td>
</tr>
<tr>
<td>Person Age:</td>
<td>
<input type="text" ng-model="Person.personAge" />
</td>
</tr>
<tr>
<td colspan="2" align="center">
<div class="alert alert-info" ng-if="Person.personAge < 18">
Person Age must be <strong>above 18 years.</strong>
</div>
<div class="alert alert-success" ng-if="Person.personAge >= 18 && Person.personAge <= 100">
<strong>Valid Age.</strong>
</div>
<div ng-if="Person.personAge > 100" class="alert alert-warning">
Person Age must be <strong> between 18 and 100.</strong>
</div>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
</div>
learn from c-sharpcorner.com
I noticed that upon receiving the coordinates, If I click anywhere on the page the map will load. I thus modified the js file to simulate a click, and it works. Although this works for my application, I'm still not sure what the root issue of the problem is. Any assistance would be greatly appreciated.
This is the function I modified by adding a .click() :
$scope.location = function(){
if (!navigator.geolocation){
output.innerHTML = "<p>Geolocation is not supported by your browser</p>";
return;
}
navigator.geolocation.getCurrentPosition(function(position){
console.log('current position',position.coords)
$scope.map.center.latitude = position.coords.latitude;
$scope.coords.lat = position.coords.latitude; //added this
$scope.map.center.longitude = position.coords.longitude;
$scope.coords = true; // added this
document.getElementById('loc').click();
}, function(){
$scope.output.innerHTML = "Unable to retrieve your location";
});
}()
I'm trying to put two buttons underneath my google maps canvas(One of which is a dropdown button). Without the buttons markup, the Google Maps loads fine. When I add the buttons code, the map disappears. The map element and the buttons are all within the same container and columns, but on different rows.
<div class="container-fluid pushdown">
<div class="row">
<div class="col-md-2"></div>
<div class="col-md-8"><div class="map" id="map"></div></div>
<div class="col-md-2"></div>
</div>
<div class="row">
<div class="col-md-2"></div>
<div class="col-md-8">
<div id="controls">
<button class="btn btn-default btn-lg dropdown-toggle location"type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
Select<span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li><input type="checkbox" class="Check" name="traders[]" value="1"/><label class="CheckText">Trader1</label></li>
<li><input type="checkbox" class="traderCheck" name="traders[]" /><label class="traderCheckText">Trader2</label></li>
</ul>
<button onclick="location.href = 'search.html';" type="button" class="btn btn-default btn-lg" id="searchButton">Search <span class="glyphicon glyphicon-search"></span></button>
</div>
</div>
<div class="col-md-2"></div>
</div>
</div>
And the JS:
function initMap() {
var map = new google.maps.Map(document.getElementById('map'), {
center: {lat: -34.397, lng: 150.644},
zoom: 16,
disableDefaultUI: true
});
var marker = new google.maps.Marker({
position: {lat: -34.397, lng: 150.644},
draggable:true
});
// Try HTML5 geolocation.
if (navigator.geolocation) {
navigator.geolocation.getCurrentPosition(function(position) {
var pos = {
lat: position.coords.latitude,
lng: position.coords.longitude
};
map.setCenter(pos);
marker.setPosition(pos);
marker.setMap(map);
}, function() {
handleLocationError(true, infoWindow, map.getCenter());
});
} else {
// Browser doesn't support Geolocation
handleLocationError(false, infoWindow, map.getCenter());
}
}
function handleLocationError(browserHasGeolocation, infoWindow, pos) {
infoWindow.setPosition(pos);
infoWindow.setContent(browserHasGeolocation ?
'Error: The Geolocation service failed.' :
'Error: Your browser doesn\'t support geolocation.');
}
The map element CSS:
.map {
width: 100%;
height: 500px;
background-color: blue;
}
Also, I tried it with just the 3 columns on the second row(without the button elements) and the map disappeared . This means my problem is with Bootstrap.
Try this way .
function initMap() {
var map = new google.maps.Map(document.getElementById('map'), {
center: {lat: -34.397, lng: 150.644},
zoom: 16,
disableDefaultUI: true
});
var marker = new google.maps.Marker({
position: {lat: -34.397, lng: 150.644},
draggable:true
});
// Try HTML5 geolocation.
if (navigator.geolocation) {
navigator.geolocation.getCurrentPosition(function(position) {
var pos = {
lat: position.coords.latitude,
lng: position.coords.longitude
};
map.setCenter(pos);
marker.setPosition(pos);
marker.setMap(map);
}, function() {
handleLocationError(true, infoWindow, map.getCenter());
});
} else {
// Browser doesn't support Geolocation
handleLocationError(false, infoWindow, map.getCenter());
}
}
function handleLocationError(browserHasGeolocation, infoWindow, pos) {
infoWindow.setPosition(pos);
infoWindow.setContent(browserHasGeolocation ?
'Error: The Geolocation service failed.' :
'Error: Your browser doesn\'t support geolocation.');
}
</script>
<script src="https://maps.googleapis.com/maps/api/js?key=AIzaSyCrwOEvG-QIFrYPBCwRVTvXvSuzcnz38Xs&signed_in=true&callback=initMap"
async defer>
</script>
.map{
width: 100%;
height: 500px;
background-color: blue;
}
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js"></script>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap-theme.min.css" rel="stylesheet"/>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css" rel="stylesheet"/>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div class="container-fluid pushdown">
<div class="row">
<div class="col-md-2"></div>
<div class="col-md-8"><div class="map" id="map"></div></div>
<div class="col-md-2"></div>
</div>
<div class="row">
<div class="col-md-2"></div>
<div class="col-md-8">
<div id="controls">
<button class="btn btn-default btn-lg dropdown-toggle location"type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
Select<span class="caret"></span>
</button>
<ul class="dropdown-menu">
<li>
<input type="checkbox" class="Check" name="traders[]" value="1"/>
<label class="CheckText">Trader1</label></li>
<li>
<input type="checkbox" class="traderCheck" name="traders[]" />
<label class="traderCheckText">Trader2</label></li>
</ul>
<button onclick="location.href = 'search.html';" type="button" class="btn btn-default btn-lg" id="searchButton">Search <span class="glyphicon glyphicon-search"></span></button>
</div>
</div>
<div class="col-md-2"></div>