2016-01-23 99 views
3

我在Django模板內部使用jQuery腳本來呈現Google地圖。目標是在地圖上繪製多個標記。我試過兩件事:如何將jQuery變量設置爲django模板變量

  1. 將jQuery var設置爲一個Django模板變量,我在views.py中定義了一個列表。在這種情況下無法產生任何標記。只是一張空白的地圖。

    var markers = {{marker_list}};

    我打印marker_list頁面確認,這是這在我的最後一次測試上:marker_list = [ '清邁公園',21.0333,21.0333],[ '胡志明墓',21.036666667,21.036666667]

  2. 使用jQuery腳本中的模板標籤創建for循環,並使用模板變量構建列表。使用此功能,即使列表中有多個位置,也只會繪製一個標記(請參閱上面的marker_list)。

    {%,例如在查詢集%}

    變種標記= [ [{{instance.place_id}},{{instance.place_lat}},{{instance.place_long}}] ];

    {%ENDFOR%}

完整代碼如下表示嘗試2#。請注意,JavaScript中的「var markers」需要列表。即var標記= [[name1,latitude1,longitude1],[name2,latitude2,longitude2]]。

任何幫助將不勝感激。我既是Django又是Javascript n00b。

views.py

def places_map(request):  
if request.user.is_authenticated(): 
    queryset = AddLink.objects.filter(user=request.user) 
    marker_list = [] 

    for instance in queryset: 
     name = str(instance.location) 
     latitude = float(instance.place_lat) 
     longitude = float(instance.place_lat) 
     marker_list += [[name, latitude, longitude]] 

    context = { 
     "queryset": queryset, 
     "marker_list": marker_list 
    } 

    return render(request, "places_map.html", context) 
else: 
    raise Http404("You must be logged in to view places.") 

places_map.html

{% extends "base.html" %} 
{% load crispy_forms_tags %} 
{% load staticfiles %} 

<style> 
{% block style %} 

#map_wrapper { 
    height: 400px; 
} 

#map_canvas { 
    width: 100%; 
    height: 100%; 
} 

{% endblock style %} 
</style> 

{% block content %} 

<div class='row' align='center'> 
    <h1 id="places-title">Map</h1> 

    {% if queryset %} 
     <!-- removed -->  
    {% endif %} 
</div> 

<div id="map_wrapper"> 
    <div id="map_canvas" class="mapping"></div> 
</div> 

<!-- For testing --> 
{{ marker_list }} 

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script> 

<script> 
// Script from http://wrightshq.com/playground/placing-multiple-markers-on-a-google-map-using-api-3/ 

jQuery(function($) { 
    // Asynchronously Load the map API 
    var script = document.createElement('script'); 
    script.src = "http://maps.googleapis.com/maps/api/js?sensor=false&callback=initialize"; 
    document.body.appendChild(script); 
}); 

function initialize() { 
    var map; 
    var bounds = new google.maps.LatLngBounds(); 
    var mapOptions = { 
     mapTypeId: 'roadmap' 
    }; 

    // Display a map on the page 
    map = new google.maps.Map(document.getElementById("map_canvas"), mapOptions); 
    map.setTilt(45); 

    // Multiple Markers 

    {% for instance in queryset %} 
    var markers = [ 
     // ['London Eye, London', 51.503454,-0.119562], 
     // ['Palace of Westminster, London', 51.499633,-0.124755], 
     // ['Ministry of Sound', 51.498231,-0.118468], 
     [{{ instance.place_id }}, {{ instance.place_lat }}, {{ instance.place_long }}] 
     ]; 
    {% endfor %} 

    // Info Window Content 
    var infoWindowContent = [ 
     ['<div class="info_content">' + 
     '<h3>London Eye</h3>' + 
     '<p>The London Eye is a giant...</p>' +  '</div>'], 
     ['<div class="info_content">' + 
     '<h3>Palace of Westminster</h3>' + 
     '<p>The Palace of Westminster is the...</p>' + 
     '</div>'], 
     ['<div class="info_content">' + 
     '<h3>Ministry of Sound</h3>' + 
     '<p>Nice place.</p>' + 
     '</div>'] 
    ]; 

    // Display multiple markers on a map 
    var infoWindow = new google.maps.InfoWindow(), marker, i; 

    // Loop through our array of markers & place each one on the map 
    for(i = 0; i < markers.length; i++) { 
     var position = new google.maps.LatLng(markers[i][1], markers[i][2], markers[i][3]); 
     bounds.extend(position); 
     marker = new google.maps.Marker({ 
      position: position, 
      map: map, 
      title: markers[i][0] 
     }); 

     // Allow each marker to have an info window  
     google.maps.event.addListener(marker, 'click', (function(marker, i) { 
      return function() { 
       infoWindow.setContent(infoWindowContent[i][0]); 
       infoWindow.open(map, marker); 
      } 
     })(marker, i)); 

     // Automatically center the map fitting all markers on the screen 
     map.fitBounds(bounds); 
    } 

    // Override our map zoom level once our fitBounds function runs (Make sure it only runs once) 
    var boundsListener = google.maps.event.addListener((map), 'bounds_changed', function(event) { 
     this.setZoom(14); 
     google.maps.event.removeListener(boundsListener); 
    }); 

} 

</script> 

{% endblock content %} 

回答

2

您應該爲此使用JSON。

context = { 
    "queryset": queryset, 
    "marker_list": json.dumps(marker_list) 
} 

,並在您的模板,使用safe過濾器,以便Django不逃避符號:

var markers = {{ marker_list|safe }} 
+0

完全忘了安全(深夜)......我會留下我的答案,因爲我確定有某些原因需要在某個時候使用這種方式,但實際上這個答案更正確。 – Sayse

+0

這工作完美,謝謝! – msarlo

1

這樣做{{ marker_list }}你剛剛結束了一個字符串,這顯然是沒有好,我的解決方案通常與去是定義一個空白數組然後附加到它

var markers = []; 
{% for instance in queryset %}  
markers.append([{{ instance.place_id }}, {{ instance.place_lat }}, {{ instance.place_long }}]);  
{% endfor %} 

當然,你可以在for循環之後關閉數組,這可能會產生jslint錯誤,儘管它也可以工作。

var markers = [ 
{% for instance in queryset %}  
[{{ instance.place_id }}, {{ instance.place_lat }}, {{ instance.place_long }}],  
{% endfor %} 
]; 
+1

您的解決方案的工作(第二個),雖然@DanielRossman答案是簡單的,所以我選擇那個。這對我的學習仍然有幫助,所以謝謝! – msarlo