How to apply filters to images with Python
Tags: python, programming, opensource, showdev
Published: 2021-12-22 00:01:44

A few weeks ago, we received a new ticket: *“Users want to be able to apply filters to their pictures”*, yes, something like Instagram does. We immediately thought about the Lightroom API, but after some research, we came to the conclusion that it doesn’t quite meet our needs. We were searching for something like a library, where we can just load the image, apply the filters and then save the new image with the filters applied, since we couldn’t find it we decided to build one.

## FImage
**[FImage](https://github.com/jordandjp/fimage "FImage")** is a Python module to apply and create multiple filters to images, it exposes an API that you can use for applying the different color transformations to the images. It works by converting the image to an RGB matrix and applying different math formulas to it. We used [NumPy](https://numpy.org/ "NumPy") for all the matrix operations since it is faster and optimized, and [Pillow](https://pillow.readthedocs.io/en/stable/ "Pillow") for handling the loading and saving of the images.

## How to use it?
First, we need to install it, for this you need to be using Python 3.6 or greater to be able to use **FImage**.

```python
pip install fimage
```

And for these examples, I’m gonna use this picture to apply it filters:

![my_picture.jpg](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/fjk44oa9ycowudgaf6fb.jpg)
 


### Applying a simple filter
Create a file `app.py` with:

```python
from fimage import FImage
from fimage.filters import Sepia


def main():
    # replace 'my_picture.jpg' with the path to your image
    image = FImage('my_picture.jpg')

    # apply the Sepia filter to the image
    image.apply(Sepia(90))

    # save the image with the applied filter
    image.save('my_picture_sepia.jpg')


if __name__ == "__main__":
    main()

```

Now, just run it :
```python
python app.py
```

And this is how the new image `my_picture_sepia.jpg` looks like after the filter was applied.
![my_picture_sepia.jpg](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/hjf09bxcipgbbjwuw9jv.jpg)
 

### Applying multiple filters 
**FImage** offers more filters besides the Sepia one, even you can combine multiples filters to give a better look to your picture.

Modify the file `app.py` to import more filters from FImage

```python
from fimage import FImage
from fimage.filters import Contrast, Brightness, Saturation


def main():
    image = FImage('my_picture.jpg')

    # apply the mutiple filters to the image
    image.apply(
        Saturation(20),
        Contrast(25),
        Brightness(15)
    )

    # save the image with the applied filter
    image.save('my_picture_mixed.jpg')


if __name__ == "__main__":
    main()
```

We run it by
```python
python app.py
```

And our new `my_picture_mixed.jpg` looks like
![my_picture_mixed.jpg](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/5i3tn210bvuyf8z7lqff.jpg)
 

The order in which the filters are passed to the `apply` function matters, this is because the filters are applied sequentially, so the next filter will be applied over the resultant image from the previous one.

### Presets
Presets are just the combinations of multiple filters with already defined adjustment values.

Let’s change our `app.py` one more time to use the Presets

```python
from fimage import FImage
from fimage.presets import SinCity


def main():
    # replace 'my_picture.jpg' with the path to your image
    image = FImage('my_picture.jpg')

    # apply the SinCity preset to the image
    image.apply(SinCity())

    # save the image with the applied preset
    image.save('my_picture_sincity.jpg')


if __name__ == "__main__":
    main()
```

After we run it, we get our new `my_picture_sincity.jpg`
![my_picture_sincity.jpg](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/v7e1azi4djosxguuq4r3.jpg)
 

### Custom Presets
If you like the look your picture got after testing different filters and want to store this combination for applying it to more pictures, you can create your own Preset by just extending the `Preset` Class and specifying these filters and their adjust values in it.

In our `app.py` let’s do

```python
from fimage import FImage
from fimage.presets import Preset
from fimage.filters import Contrast, Brightness, Saturation


# Create my custom preset and specify the filters to apply
class MyOwnPreset(Preset):
    transformations = [
        Contrast(30),
        Saturation(50),
        Brightness(10),
    ]


def main():
    # replace 'my_picture.jpg' with the path to your image
    image = FImage('my_picture.jpg')

    # apply MyOwnPreset to the image
    image.apply(MyOwnPreset())

    # save the image with the applied preset
    image.save('my_picture_custom.jpg')


if __name__ == "__main__":
    main()
```

The new `my_picture_custom.jpg`

![my_picture_custom.jpg](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mus16gejayn3a4i4ev1o.jpg)
 

This is basic usage of **FImage**, we are still developing it, and it would be really great any feedback or contribution you have.

[GitHub Repo](https://github.com/jordandjp/fimage "Github Repo")

You can follow me on [Twitter](https://www.twitter.com/juanbenitezdev) and [GitHub](https://www.github.com/juanbenitezdev) to be up to date with all my projects and content.