Django:m2m选择缩略图

时间:2018-01-11 03:27:46

标签: python django django-models django-forms

我是Django开发的新手,并尝试使用我的作品和博客来构建自己的网站。

我网站的投资组合部分包含的帖子包含可变数量的图片,可用作缩略图。

在Django admin中,我希望能够在选择表单中看到每个图像的缩略图。 Django的filter_horizo​​ntal与我正在寻找的非常接近,但它无法显示图像的缩略图

无论如何,涉及的模型看起来像这样:

class Image(models.Model):
    original = models.ImageField(upload_to='images')
    medium = ...
    thumbnail = ...

class Project(models.Model):
    title = models.CharField(max_length=100)
    images = models.ManyToManyField(Image, blank=True)
    description = RichTextField(max_length=1000)
    content = RichTextField()

This是我想要实现的模型。

我一直在阅读有关Forms,ModelForms和Widgets的文档,但我不完全确定如何将它们拼凑在一起,或者我是否完全看错了。任何帮助都会非常感激,即使它只是指向我正确的方向。

1 个答案:

答案 0 :(得分:0)

我花了一些时间来提出这个问题。问题是,抓取小部件很难。我的解决方案由两部分组成。

首先我改变相关ImageModel的 str 表示以返回image_url

class ArticleImage(ImportModel, ImageModel):
    image = models.ImageField(help_text='Artikelbild')
                           related_name='images', null=True, blank=True)

    def __str__(self):
        return self.image.url

然后我覆盖我的管理表格 init 方法以返回网址(如果您不想显示已保存的所有图片,也可以在此处过滤)

def __init__(self, *args, **kwargs):
    super(ArticleRelatedImageForm, self).__init__(*args, **kwargs)
    images = []

    article_related_images = ArticleImage.objects.all()

    for image in article_related_images:
        images.append(
            (image.pk, mark_safe('%s' % image.image.url))
        )

    self.fields['images'].choices = images

最后,魔法发生在我的base.html中。我从External Libraries / site-packages / django / contrib / admin / templates / admin / base.html复制文件,并在文件底部添加我自己的jQuery Magic:

<script>src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

jQuery('.related-widget-wrapper').bind("DOMNodeInserted", function () {
    jQuery('#id_images_from option').each(function () {
        jQuery(this).attr('style', 'background: url(' + jQuery(this).text() + '); height:100px; width:200px; ' +
            'background-repeat: no-repeat; background-size:contain; margin: 5px; background-position: center;' +
            'color:rgba(0,0,0,0);');
    });
    jQuery('#id_images_to option').each(function () {
        jQuery(this).attr('style', 'background: url(' + jQuery(this).text() + '); height:100px; width:200px; ' +
            'background-repeat: no-repeat; background-size:contain; margin: 5px; background-position: center;' +
            'color:rgba(0,0,0,0);');
    });
});

只要加载过滤器水平,选择列表&#39; id_images就会变为id_images_from和id_images_to。此方法检测何时发生这种情况,并呈现缩略图。它还可以检测何时选择或取消选择图像或添加新图像。

这只会为您提供列表中心的缩略图,而不是标题。我用color属性使标题不可见,但我认为这可能是你的开始。

这个解决方案肯定不是完美的,因为我是初学者,但我希望它仍能帮到你一点点。对我来说它工作正常。

干杯,Codebeat。