我正在尝试使用autocomplete-light在django中创建一个包含两个相关下拉列表(大陆,国家/地区)的非管理员表单。第一个下拉列表将包含一个大陆列表,第二个下拉列表将包含一个国家列表。一旦用户选择了一个大陆,只有来自该大陆的国家/地区将显示在国家/地区下拉列表中。
我已经能够让两个相关的输入字段正常工作但无法将这些输入字段转换为下拉列表。下面是我正在使用的代码,我希望有人可以帮助解释将依赖输入字段转换为依赖下拉列表所需的内容。我试图在forms.py中应用小部件但没有成功,如果我删除了 来自forms.py的“widgets = autocomplete_light.get_widgets_dict(Locations)”行显示下拉列表,但我放弃了两个列表之间的依赖关系。
#models.py
from django.db import models
from django import forms
import autocomplete_light
class Continent(models.Model):
continent_id = models.BigIntegerField(primary_key=True)
continent_nm = models.CharField(max_length=100, blank=True)
class Meta:
db_table = 'continent'
def __unicode__(self):
#return self.continent_nm
return u'%s %s' % (self.continent_id, self.continent_nm)
class Country(models.Model):
country_id = models.BigIntegerField(primary_key=True)
country_nm = models.CharField(max_length=100, blank=True)
continent = models.ForeignKey(Continent, null=True, blank=True)
class Meta:
db_table = 'country'
def __unicode__(self):
#return self.country_nm
return u'%s %s' % (self.country_nm, self.country_id)
class Locations(models.Model):
continent = models.ForeignKey(Continent)
country = models.ForeignKey(Country)
def __unicode__(self):
return u'%s %s' % (self.continent, self.country)
#forms.py
import autocomplete_light
from django import forms
from insights.models import Locations
class DummyForm(forms.ModelForm):
class Meta:
model = Locations
widgets = autocomplete_light.get_widgets_dict(Locations)
# views.py
from django.shortcuts import render
from django.http import HttpResponse
from insights.forms import DummyForm
def index(request):
form = DummyForm()
context = {'form': form}
return render(request, 'insights/index.html', context)
# autocomplete_light_registry.py
import autocomplete_light
import logging
from insights.models import Continent, Country
class AutocompleContinent(autocomplete_light.AutocompleteModelBase):
search_fields= ('continent_id', 'continent_nm',)
autocomplete_js_attributes={'placeholder': 'continent name ..'}
autocomplete_light.register(Continent, AutocompleContinent)
class AutocompleteCountry(autocomplete_light.AutocompleteModelBase):
autocomplete_js_attributes={'placeholder': 'country name ..'}
search_fields=('country_id', 'country_nm',)
def choices_for_request(self):
q = self.request.GET.get('q', '')
continent_id = self.request.GET.get('continent_id', None)
choices = self.choices.all()
if q:
choices = choices.filter(country_nm__icontains=q)
if continent_id:
choices = choices.filter(continent_id=continent_id)
return self.order_choices(choices)[0:self.limit_choices]
autocomplete_light.register(Country, AutocompleteCountry)
#HTML
<!-- index.html -->
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.9.0/jquery.js" type="text/javascript"></script>
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.0/jquery.min.js"></script>
<script type="text/javascript" src="/static/insights/dependant_autocomplete.js"></script>
{% load staticfiles %}
{% include 'autocomplete_light/static.html' %}
<body>
{% block content %}
<form action='' method='post' enctype='multipart/form-data'>
{{ form.as_p }}
{% csrf_token %}
</form>
{% endblock %}
</body>
$(document).ready(function() {
$('body').on('change','.autocomplete-light-widget select[name$=continent]', function() {
alert('autocomplete dependant');
var continentSelectElement = $(this);
var countrySelectElement = $('#' + $(this).attr('id').replace('continent', 'country'));
var countryWidgetElement = countrySelectElement.parents('.autocomplete-light-widget');
// When the continent select changes
value = $(this).val();
if (value) {
// If value is contains something, add it to autocomplete.data
countryWidgetElement.yourlabsWidget().autocomplete.data = {
'continent_id': value[0],
};
} else {
// If value is empty, empty autocomplete.data
countryWidgetElement.yourlabsWidget().autocomplete.data = {}
}
})
});