2012-04-06 99 views
19

我在其中一个应用中使用了django.contrib.adminDjango admin inline

我的模型:

class Gallery(models.Model): 
    location = models.ForeignKey(Location) 
    date = models.CharField(max_length = 15) 

class Image(models.Model): 
    gallery = models.ForeignKey(Gallery) 
    name = models.CharField(max_length=35) 
    image = ImageField(upload_to='songs') 

admin.py

class ImageInline(admin.StackedInline): 
    model   = Image 

class GalleryAdmin(admin.ModelAdmin): 
    inlines = [ ImageInline, ] 

在管理部分我现在能够创建一个画廊,并在同一页上添加图片。默认情况下,django显示三种图片上传形式。我怎样才能改变它只有一个?

回答

24

额外= 0

class GalleryImageInline(admin.TabularInline): 
    """ 
    Gallery Image inline 
    """ 
    fieldsets = (
     (
      None, 
      { 
       'fields': ('name', 'image',) 
      } 
     ), 
    ) 

    model = Image 
    extra = 0 


class GalleryAdmin(admin.ModelAdmin): 
    """ 
    Case Study Admin 
    """ 
    fieldsets = (
     (
      None, 
      { 
       'fields': ('location', 'date',) 
      } 
     ), 
    ) 

    inlines = (GalleryImageInline,) 
    list_display = ['location', 'date'] 
    list_filter = ['location', ] 

,在我看来,对于具有图像的直列是有用的,你需要实际显示图像内嵌(所以定制覆盖图像小工具):

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

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) 

      # defining the size 
      size='100x100' 
      x, y = [int(x) for x in size.split('x')] 
      try : 
       # defining the filename and the miniature filename 
       filehead, filetail = os.path.split(value.path) 
       basename, format = os.path.splitext(filetail) 
       miniature   = basename + '_' + size + format 
       filename   = value.path 
       miniature_filename = os.path.join(filehead, miniature) 
       filehead, filetail = os.path.split(value.url) 
       miniature_url  = filehead + '/' + miniature 

       # make sure that the thumbnail is a version of the current original sized image 
       if os.path.exists(miniature_filename) and os.path.getmtime(filename) > os.path.getmtime(miniature_filename): 
        os.unlink(miniature_filename) 

       # if the image wasn't already resized, resize it 
       if not os.path.exists(miniature_filename): 
        image = Image.open(filename) 
        image.thumbnail([x, y], Image.ANTIALIAS) 
        try: 
         image.save(miniature_filename, image.format, quality=100, optimize=1) 
        except: 
         image.save(miniature_filename, image.format, quality=100) 

       output.append(u' <div><a href="%s" target="_blank"><img src="%s" alt="%s" /></a></div> %s ' % \ 
       (miniature_url, miniature_url, miniature_filename, _('Change:'))) 
      except: 
       pass 
     output.append(super(AdminFileWidget, self).render(name, value, attrs)) 
     return mark_safe(u''.join(output)) 

注:这确实有些resizey的东西,你可以不喜欢 - 所以你可能需要重写自己的小部件的大小缩放部分。

,那么你将需要重写控件在内嵌的形式:

class GalleryImageForm(forms.ModelForm): 
    """ 
    Image Admin Form 
    """ 
    class Meta: 
     model = Image 
     widgets = { 
      'image' : AdminImageWidget, 
     } 

class GalleryImageInline(admin.TabularInline): 
    ... 
    form = GalleryImageForm 
    ... 

和你结束了这样的somethig(这是另一个项目的一部分,有一堆额外的东西) : screenshot of the image admin inline

5

在情况下,如果你使用sorl-thumbnails,widget是这样的:

from django.contrib.admin.widgets import AdminFileWidget 
from django.utils.safestring import mark_safe 
from sorl import thumbnail 


class AdminImageWidget(AdminFileWidget): 
    def render(self, name, value, attrs=None): 
     output = [] 
     if value and getattr(value, "url", None): 
      t = thumbnail.get_thumbnail(value,'100x100') 
      output.append('<img src="{}">'.format(t.url)) 
     output.append(super(AdminFileWidget, self).render(name, value, attrs)) 
     return mark_safe(u''.join(output)) 


class GalleryImageForm(forms.ModelForm): 
    """ 
    Image Admin Form 
    """ 
    class Meta: 
     model = Image 
     widgets = { 
      'image' : AdminImageWidget, 
     } 

class GalleryImageInline(admin.TabularInline): 
    ... 
    form = GalleryImageForm 
    ...