94 votes

Django Admin affiche une image à partir d'un champ d'images

Si je peux afficher une image téléchargée dans list_display, est-il possible de le faire sur la page par modèle (comme dans la page que vous obtenez pour changer un modèle) ?

Un exemple rapide de modèle serait :

Class Model1(models.Model):
    image = models.ImageField(upload_to=directory)

L'administration par défaut affiche l'url de l'image téléchargée mais pas l'image elle-même.

Gracias.

138voto

Michael C. O'Connor Points 4462

Bien sûr. Dans votre classe de modèle, ajoutez une méthode comme :

def image_tag(self):
    from django.utils.html import escape
    return u'<img src="%s" />' % escape(<URL to the image>)
image_tag.short_description = 'Image'
image_tag.allow_tags = True

et dans votre admin.py ajouter :

fields = ( 'image_tag', )
readonly_fields = ('image_tag',)

à votre ModelAdmin . Si vous souhaitez restreindre la possibilité de modifier le champ de l'image, veillez à l'ajouter à la liste de contrôle de l'utilisateur. exclude attribut.

Note : Avec Django 1.8 et 'image_tag' uniquement dans readonly_fields, il ne s'affiche pas. Avec 'image_tag' uniquement dans les champs, il a donné une erreur de champ inconnu. Il faut qu'il soit à la fois dans les champs et dans readonly_fields pour qu'il s'affiche correctement.

108voto

palamunder Points 1071

En plus de la réponse de Michael C. O'Connor

Notez que depuis Django v.1.9 (mis à jour - testé et fonctionnant jusqu'à Django 3.0)

image_tag.allow_tags = True

est déprécié et vous devez utiliser format_html(), format_html_join(), ou mark_safe() à la place.

Ainsi, si vous stockez vos fichiers téléchargés dans votre dossier public /directory, votre code devrait ressembler à ceci :

from django.utils.html import mark_safe

    Class Model1(models.Model):
        image = models.ImageField(upload_to=directory)

        def image_tag(self):
            return mark_safe('<img src="/directory/%s" width="150" height="150" />' % (self.image))

        image_tag.short_description = 'Image'

et dans votre admin.py ajouter :

fields = ['image_tag']
readonly_fields = ['image_tag']

68voto

Serj Points 748

Cela peut être fait dans l'administration sans modifier le modèle.

from django.utils.html import format_html

@admin.register(Model1) 
class Model1Admin(admin.ModelAdmin):

    def image_tag(self, obj):
        return format_html('<img src="{}" />'.format(obj.image.url))

    image_tag.short_description = 'Image'

    list_display = ['image_tag',]

20voto

Venkat Kotra Points 2697

Pour Django 1.9 Pour afficher une image au lieu du chemin d'accès au fichier dans les pages d'édition, l'utilisation d'ImageWidget est une bonne façon de le faire.

from django.contrib.admin.widgets import AdminFileWidget
from django.utils.translation import ugettext as _
from django.utils.safestring import mark_safe
from django.contrib import admin

class AdminImageWidget(AdminFileWidget):
    def render(self, name, value, attrs=None):
        output = []
        if value and getattr(value, "url", None):
            image_url = value.url
            file_name = str(value)
            output.append(u' <a href="%s" target="_blank"><img src="%s" alt="%s" /></a> %s ' % \
                          (image_url, image_url, file_name, _('Change:')))
        output.append(super(AdminFileWidget, self).render(name, value, attrs))
        return mark_safe(u''.join(output))

class ImageWidgetAdmin(admin.ModelAdmin):
    image_fields = []

    def formfield_for_dbfield(self, db_field, **kwargs):
        if db_field.name in self.image_fields:
            request = kwargs.pop("request", None)
            kwargs['widget'] = AdminImageWidget
            return db_field.formfield(**kwargs)
        return super(ImageWidgetAdmin, self).formfield_for_dbfield(db_field, **kwargs)

Utilisation :

class IndividualBirdAdmin(ImageWidgetAdmin):
    image_fields = ['thumbNail', 'detailImage']

Les images s'afficheront pour les champs, thumbNail y detailImage

16voto

Risadinha Points 1254

Avec django-imagekit vous pouvez ajouter n'importe quelle image comme ceci :

from imagekit.admin import AdminThumbnail

@register(Fancy)
class FancyAdmin(ModelAdmin):
    list_display = ['name', 'image_display']
    image_display = AdminThumbnail(image_field='image')
    image_display.short_description = 'Image'

    readonly_fields = ['image_display']  # this is for the change form

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X