Autocompletion for django-tagulous TagField¶
Note that django-tagulous provides autocompletion features. Check them out, if it doesn’t work for you or whatever reason then feel free to use dal_tagulous.
Model example¶
Consider such a model, using django-tagulous to handle tags for a model:
from django.db import models
from tagulous.models import TagField
class TestModel(models.Model):
name = models.CharField(max_length=200)
tags = TagField()
def __str__(self):
return self.name
View example¶
The QuerySet view works here too: we’re relying on Select2 and a QuerySet of Tag objects. However, in django-tagulous, a specific Tag model is made for every instance of the field. So we have to get the Tag model class dynamically:
from dal import autocomplete
class TagAutocomplete(autocomplete.Select2QuerySetView):
def get_queryset(self):
# Get the tag model dynamically
Tag = TestModel.tags.tag_model
# Don't forget to filter out results depending on the visitor !
if not self.request.is_authenticated():
return Tag.objects.none()
qs = Tag.objects.all()
if self.q:
qs = qs.filter(name__istartswith=self.q)
return self.q
Don’t forget to Register the autocomplete view.
Note
For more complex filtering, refer to official documentation for
the QuerySet API
.
Form example¶
As usual, we need a backend-aware widget that will make only selected choices
to render initially, to avoid butchering the database. As we’re using a
QuerySet of Tag and Select2 in its “tag” appearance, we’ll use
TagSelect2
.
Also, we need a field that works with a queryset of tagulous tag, and is able
to update tagulous TagField: TagulousField
.
Finnaly, we can’t use Django’s ModelForm because it django-taggit’s field is
made to be edited in a text input with a comma-separated list of fields, which
isn’t what Select2 supports even in its tag mode. So, we’ll use
FutureModelForm
.
Example:
class TestForm(autocomplete.FutureModelForm):
tags = autocomplete.TagulousField(
required=False,
queryset=TestModel.test.tag_model.objects.all(),
widget=autocomplete.TagSelect2(url='your-view-url-name'),
)
class Meta:
model = TestModel
fields = ('name',)