Giter VIP home page Giter VIP logo

django-picture's Introduction

Django Picture

A Django application designed to optimize your image handling process. It aids in the creation of HTML <picture> elements by processing Django images through one or more filters.

django-picture manages different image sizes and types, ensuring that the most appropriate image is served based on the user's device and screen resolution. This improves page load times and also reduces the amount of data that needs to be transferred.

By default, images are generated in a pipeline, out-of-band from the request. When a <picture> is created, processed images that don't already exist are queued for processing (if they haven't been already) and left out of the HTML.

Installation & Configuration

To install django-picture, simply run the following command:

pip install django-picture

Once installed, add picture to your INSTALLED_APPS in your Django settings file:

INSTALLED_APPS = [
    # ...
    "picture",
    # ...
]

Since this uses pyvips, you'll need to have the libvips library installed on your system. In Ubuntu, you can install it with the following command:

sudo apt-get install --no-install-recommends libvips

Usage

There are two ways to use django-picture: through a Python class or through a template filter.

Picture class

The Picture class is used to create a generator for HTML <picture> elements. Here's an example of how to use it:

from picture import Picture
thumb = Picture(width="md")
thumb(profile.photo, alt=f"Profile photo for {{ profile.name }}").as_html()

As you can see, thumb is a Picture instance that is used to generate an HTML <picture> element for the profile.photo image.

In a following section you can see all the different options that you can pass to the Picture class.

A final optional argument when calling a Picture instance is build. This argument specifies whether the image should be processed inline or not. Valid values are:

  • None (default): The image will be processed out-of-band from the request.
  • "base": The base image will be processed inline, but the sources will be processed out-of-band from the request.
  • "all": The base image and the sources will be processed inline.

The {% picture %} tag

The picture template tag is another way to generate an HTML <picture> element.

{% load picture %}
{% picture report.image width="md" alt="" %}

You can also pass a Picture instance to the picture template tag:

{% load picture %}
{% picture report.image thumb alt="" %}

The template tag does not process images inline.

Building images.

Whenever a picture is requested, any missing images will be queued for processing and excluded from the HTML.

To build the images in this queue, you can either:

  • run the process_picture_queue management command (usually in a cron job), or
  • process it in a task using celery or another task runner (probably using the queued_picture signal_).

Options

The Picture class and the picture template tag can be called with the following options.

width

Limit the width of the image. Either use an integer, or one of the following tailwind sizes as a string: "xs", "sm", "md", "lg", "screen-sm", "screen-md", "screen-lg", "screen-xl" or "screen-2xl"

ratio

The aspect ratio of the image to generate.

Use a float representing the ratio (e.g. 4/5) or one of the following strings: "square", "video" (meaning 16/9), "video_vertical", "golden" (using the golden ratio), "golden_vertical".

The default is "video" (16/9).

crop

Whether to crop the image.

The default is True.

Use a boolean, or tuple of two floats, or the comma separated string equivalent. True is replaced with to (0.5, 0.5) meaning the image is cropped from the center. The numbers are percentages of the image size. You can also use the following keywords: tl (top left), tr (top right), bl (bottom left), br (bottom right), and t or b. This will set the percentage to 0 or 100 for the appropriate axis.

If crop is False, the image will be resized so that it will cover the requested ratio but not cropped down. This is useful when you want to handle the cropping in CSS using object-fit.

focal_window

A focal window to zoom in on when shrinking the image. Use a tuple of four floats (or a comma separated string equivalent) where the first pair of percentages is the top left corner and the second pair of percentages is the bottom right corner.

quality

The quality of the image. For example, quality=90 means that the image will be compressed with a quality of 90. The default is 80.

alternatives

A list of alternative versions of the image. Use a dictionary to specify different picture options for each of these alternatives, for example alternatives={"100w": {"width": 100}, "2x": {}}.

The default is ["2x"].

formats

The list of better image formats to ensure are generated and preferentially used. The valid values are "avif" and "webp".

Use a dictionary to specify different picture options for different formats.

The default is {"avif": {"quality": 60}}.

base

A dictionary of options to use for the base fallback image. If provided, this is used in the fallback <img> tag rather than the source image.

The default is {"width": "screen-xl", "crop": False}.

Signals

file_post_save signal

This signal is triggered for each that FileField that was uncommitted when it's model instance is saved.

It can be used to build & pre-queue images for a model instance. For example:

from django.db import models
from django.db.models.fields.files import ImageFieldFile

from my_app.pictures import thumbnail

def generate_images(instance, image, **kwargs):
    """
    Trigger generation of all related `<picture>` images for an uncommitted ImageField
    just before its model is saved.
    """
    if isinstance(image, ImageFieldFile):
        thumbnail(image, build="base")

In your apps.py file, connect this receiver:

from django.apps import AppConfig

from picture.signals import file_post_save

class MyAppConfig(AppConfig):
    name = 'my_app'

    def ready(self):
        from my_app.signals import generate_images

        file_post_save.connect(generate_images)

queued_picture signal

This signal is triggered whenever an image is missing and was not already queued for building.

It can be used to process the queue in a task using celery or another task runner. Here's an example tasks.py:

from picture.management import process_queue

@app.task
def process_picture_queue():
    process_queue()

In your apps apps.py file, connect this receiver:

In your `apps.py` file, connect your `process_picture_queue` function to the `queued_picture` signal to process the queue whenever an image is saved:

```python
from django.apps import AppConfig

from picture.signals import queued_picture

class MyAppConfig(AppConfig):
    name = 'my_app'

    def ready(self):
        from my_app.tasks import process_picture_queue

        queued_picture.connect(process_picture_queue.delay)

django-picture's People

Contributors

smileychris avatar

Watchers

 avatar  avatar

django-picture's Issues

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.