Pillow: Is it possible to use colored Whatsapp/Facebook emoji?

Created on 10 Sep 2018  ·  22Comments  ·  Source: python-pillow/Pillow

What did you do?

from PIL import Image, ImageDraw, ImageFont
import textwrap

astr = ''' 👩‍⚕️: H👩‍'''
para = textwrap.wrap(astr, width=40)

MAX_W, MAX_H = 400, 100 + 30 * len(para)
im = Image.new('RGB', (MAX_W, MAX_H), (0, 45, 0, 0))
draw = ImageDraw.Draw(im)
font = ImageFont.truetype('DejaVuSans.ttf', size=18)

current_h, pad = 50, 10
for line in para:
    w, h = draw.textsize(line, font=font)
    draw.text(((MAX_W - w) / 2, current_h), line, font=font)
    current_h += h + pad
im.save('test.png')

What did you expect to happen?

Is it possible to show colored Whatsapp oder Facebook Emoji?

What actually happened?

For the woman emoji i only get a white rect.

What versions of Pillow and Python are you using?

Pillow 3.1.2
Python 3.5.2

Enhancement Question

Most helpful comment

Pillow 8.0.0 has now been released, adding support for CBDT and COLR fonts.
FreeType (and hence also Pillow) does not yet support SBIX or SVG fonts.
To enable color support, use draw.text(..., embedded_color=True).

All 22 comments

I think this is not implemented. But have somebody ideas to do a workaround? For example to tranform the emoji to a image and open the image and render it in text.
http://www.unicode.org/emoji/charts/full-emoji-list.html
https://github.com/carpedm20/emoji

A workaround is to call something like ImageMagick to create an image of the emoji, then open that.

For example, https://stackoverflow.com/a/52131155/724176

this does not work under linux

Does this still happen?

How about when using a Noto font?

Noto Emoji gives black and white emojis, and Noto Color Emoji fails to load with OSError: invalid pixel size. I'm using Pillow 7.0.0 on Ubuntu.

Noto Emoji gives black and white emojis, and Noto Color Emoji fails to load with OSError: invalid pixel size. I'm using Pillow 7.0.0 on Ubuntu.

This error is due to a freetype limitation. Bitmap fonts don't support scaling with freetype, so you must specify a valid size, which is 109 for Noto Color Emoji.

Additionally, freetype must be built with libpng to support this font (png bitmaps). However, due to #960, bitmap fonts will not work with Pillow at all. And even if they did, you would get a grayscale version of the emojis, because Pillow only returns one channel from the C layer font functions.

Note: I am working on improving some of this, I just need to write some tests to submit a PR.

it looks like FreeType 2.10.0 adds support for COLR/CPAL tables, which Noto Color Emoji uses for scalable color emoji glyphs. could this be taken advantage of to add support for this type of emoji font to Pillow?

@boringcactus I've got it partially implemented, but it is not PR ready. I'm not sure when I'll have time to work on it, but it will be either next week or a few weeks later.

@boringcactus I've got it partially implemented, but it is not PR ready. I'm not sure when I'll have time to work on it, but it will be either next week or a few weeks later.

_cough_

I ended up working on #4724 first 😄 and postponed this until that gets merged to avoid merge conflicts. Thinking about it again, I don't think these two actually conflict too badly, so perhaps I can submit this soon as well. I'm hoping both of these can be included in version 8.0.0 planned for release in 6 weeks.

Ah thanks, if you have the patch could you send it to me? I can implement it locally

See my branch https://github.com/nulano/Pillow/compare/06ba0838...nulano:ft-color. IIRC it should work, but there are some extra unnecessary changes that should be removed, and parts of it can be simplified, before submitting it as a PR. Please treat it as a WIP, the API will likely change in the final version.

Hey, can you send me a compiled version for windows?

I've re-triggered the GHA run, you can get wheels there: https://github.com/nulano/Pillow/actions/runs/232647949

I'm dumb, how do I install it with that?

Not dumb, it's not so obvious! :)

If you click dist"-ft-color" under Artifacts it'll download a zip file.

Extract that, and then pip install filename.whl, where filename.whl is the one that closest matches your system (e.g. cp38 for Python 3.8).

Hey, thank you so much, the new version installed correctly
However, it seems that fonts with color don't work, can you tell me what is wrong with this code?

# -*- coding: utf-8 -*-
from PIL import Image
from PIL import ImageFont
from PIL import ImageDraw

import os

im = Image.open('purple.png')
draw = ImageDraw.Draw(im)
font = ImageFont.truetype('seguiemj.ttf', 64, encoding = 'unic')
textToDraw = u'😀'
print(textToDraw)
draw.text((20,20), textToDraw, (255,255,255), font=font)
im.show()

For backwards compatibility you have enable color support using draw.text(..., embedded_color=True). This parameter might be renamed in the final version.

POG IT WORKS thank you so much man

Also, is there a way to have a secondary font for mission glyphs? like many fonts don't have emoji and ideally I want to support them still

Also, is there a way to have a secondary font for mission glyphs? like many fonts don't have emoji and ideally I want to support them still

See #4808. Edit: fix link typo.

The best you can do for now is use unicodedata.category to break up text into "spans" each rendered separately with their own font. You can use font.getsize(...)[0] or draw.textsize(...)[0] as the horizontal offset between spans for now (#4724 proposes adding a faster and more precise font.getlength(...)). You will also have to handle linebreaks yourself, see draw.multiline_text for inspiration.

Pillow 8.0.0 has now been released, adding support for CBDT and COLR fonts.
FreeType (and hence also Pillow) does not yet support SBIX or SVG fonts.
To enable color support, use draw.text(..., embedded_color=True).

Was this page helpful?
0 / 5 - 0 ratings