Пожалуйста, имейте в виду, что я новичок в Django и веб-программировании в целом.
Я пытаюсь сделать что-то, что кажется простым, но я не могу понять:
У меня есть шаблон «Просмотр объекта», который я использую для отображения информации об одном выбранном объекте из базы данных, и я хочу включить график на странице.
models.py:
class MaxExtent(models.Model):
id = models.IntegerField(primary_key=True)
geoName = models.CharField('Geounit name (territories are unique geounits)', max_length=40, null=True)
sovereignty = models.CharField('Sovereign country name', max_length=32, null=True)
lakeName = models.CharField('GLWD Lake name', max_length=50)
areaMax = models.FloatField('Max Extent area (km^2)')
area2000 = models.FloatField('2000 area (km^2)')
area2001 = models.FloatField('2001 area (km^2)')
area2002 = models.FloatField('2002 area (km^2)')
area2003 = models.FloatField('2003 area (km^2)')
area2004 = models.FloatField('2004 area (km^2)')
area2005 = models.FloatField('2005 area (km^2)')
area2006 = models.FloatField('2006 area (km^2)')
centerLat = models.FloatField('Latitude of centroid')
centerLon = models.FloatField('Longitude of centroid')
poly = models.MultiPolygonField()
def __str__(self): # default field for string representation
if self.lakeName:
return "ID {}: {} ({}, {})".format(self.id, self.lakeName, self.centerLon, self.centerLat)
else:
return "ID {}: Not named ({}, {})".format(self.id, self.centerLon, self.centerLat)
views.py:
from django.shortcuts import get_object_or_404, render
from django.forms import ModelForm
from .models import MaxExtent
from .functions import chart_object_areas
# Object viewer
def objectViewer(request, req_id):
waterBody = get_object_or_404(MaxExtent, pk = req_id)
displayFields = [str(f.name) for f in MaxExtent._meta.get_fields()]
class MaxExtentForm(ModelForm):
class Meta:
model = MaxExtent
fields = displayFields
fields = MaxExtentForm(instance=waterBody)
areas = [waterBody.area2000, waterBody.area2001, waterBody.area2002, waterBody.area2003, waterBody.area2004, waterBody.area2005, waterBody.area2006]
years = [yr for yr in range(2000,2007)]
# get the bar plot with best fit line on top
return_chart = chart_object_areas(X = years, Y = areas, waterBody.slope, waterBody.intercept) # UPDATE
context = {'waterBody': waterBody, 'displayFields': fields, 'chart': return_chart} # UPDATE - tried sending object to template
return render(request, 'waterExplorer/objectViewer.html', context)
Я могу показать код шаблона, но не думаю, что это будет полезно.Просто знайте, что он успешно отображает информацию об атрибутах, используя waterBody и displayFields вместе с картой объекта.
Теперь по моему вопросу ...
Я следую учебному пособию здесь , который использует matplotlib для создания диаграммы и визуализации ее в шаблоне.Я пытаюсь создать простую гистограмму, используя информацию из модели (область 2000 - область 2006 как мой Y и год - 2000, 2001, ..., 2006 как X).У меня есть скрипт, который создает этот график на основе информации, полученной из модели (functions.chart_object_area);В настоящее время используется Matplotlib, как в учебнике.Это вызывается в views.py и возвращает объект, который должен быть визуализирован, в соответствии с примером 1 (см. пример и views.py выше)
Однако, как вернуть f.getValue () вдополнение к параметрам waterBody и displayFields?Учебник возвращает диаграмму примерно так:
return HttpResponse(f.getvalue(), content_type="image/png")
Но я возвращаюсь:
context = {'waterBody': waterBody, 'displayFields': form}
Так как мне объединить два, чтобы я мог отобразить график в дополнение к другим вещамУ меня уже есть?
Я использую Django версию 1.11
ОБНОВЛЕНИЕ : я обновил код в views.py, чтобы указать, как я получаю переменные. 'm отправляю в мою функцию диаграммы (см. # ОБНОВЛЕНИЕ) и добавляю сюда функцию chart_object_areas.Я также обновил файл views.py, чтобы показать, что я попытался передать выходной график в шаблон:
functions.py:
import sys
from django.http import HttpResponse
import matplotlib as mpl
mpl.use('Agg') # Required to redirect locally
import matplotlib.pyplot as plt
import numpy as np
from numpy.random import rand
import cStringIO
def chart_object_areas(X, Y, slope, intercept):
plt.ylim(0.0, np.max(Y)+(np.mean(Y)/3))
plt.xlim(np.min(X)-1, np.max(X)+1)
plt.ylabel('Area ($km^2$)')
plt.xlabel('Year')
plt.bar(X, Y)
# plot the best fit line too
fitY = [(slope*x + intercept) for x,d in enumerate(X)]
plt.plot(X, fitY, color='black')
plt.savefig('test-plot.png')
f = cStringIO.StringIO() # redirect per tutorial
plt.savefig(f, format="png", facecolor=(0.95,0.95,0.95))
plt.clf()
return f.getvalue() # per tutorial
Как видите, я сохранил рисунок и подтвердилчто функция является , создающей график.Однако, когда я пытаюсь отобразить его в шаблоне так:
{{ chart | safe }}
Ничего не появляется.Я предполагаю, что это из-за способа, которым я передаю шаблон [в учебнике, он использует content_type = "image / png" при возврате ответа, и я не знаю, как это сделать, так как я отправляю контекст вrender ()].
Опять же, я следую уроку здесь , чтобы научиться использовать matplotlib в Django.