diff --git a/docs/changelog.md b/docs/changelog.md index aa1a7b72b..2132a9f54 100644 --- a/docs/changelog.md +++ b/docs/changelog.md @@ -20,7 +20,7 @@ [#846](https://github.com/iodide-project/pyodide/pull/846) - Updated to emscripten 1.38.34 [#480](https://github.com/iodide-project/pyodide/pull/480) -- New packages: freesasa, lxml, python-sat, traits, astropy +- New packages: freesasa, lxml, python-sat, traits, astropy, pillow - Updated packages: numpy 1.15.4, pandas 1.0.5 among others. - Updated default `--ldflags` argument to `pyodide_build` scripts to equal what pyodide actually uses. diff --git a/packages/pillow/meta.yaml b/packages/pillow/meta.yaml new file mode 100644 index 000000000..39e6f43dd --- /dev/null +++ b/packages/pillow/meta.yaml @@ -0,0 +1,19 @@ +package: + name: pillow + version: 8.0.1 +source: + sha256: 11c5c6e9b02c9dac08af04f093eb5a2f84857df70a7d4a6a6ad461aca803fb9e + url: https://files.pythonhosted.org/packages/2b/06/93bf1626ef36815010e971a5ce90f49919d84ab5d2fa310329f843a74bc1/Pillow-8.0.1.tar.gz + + patches: + - patches/setitup.patch + extras: + - + - src/setup.cfg + - ./setup.cfg +build: + cflags: -s USE_ZLIB=1 -s USE_LIBJPEG=1 -s USE_FREETYPE=1 + ldflags: -L ../../../../emsdk/emsdk/.emscripten_cache/asmjs/ ../../../../emsdk/emsdk/.emscripten_cache/asmjs/libjpeg.bc +test: + imports: + - PIL diff --git a/packages/pillow/patches/setitup.patch b/packages/pillow/patches/setitup.patch new file mode 100644 index 000000000..6e34ef5cc --- /dev/null +++ b/packages/pillow/patches/setitup.patch @@ -0,0 +1,45 @@ +--- a/setup.py 2020-10-22 16:27:16.000000000 +0200 ++++ b/setup.py 2020-12-15 08:43:30.000000000 +0100 +@@ -557,7 +557,9 @@ + + if feature.want("zlib"): + _dbg("Looking for zlib") +- if _find_include_file(self, "zlib.h"): ++ if "PYODIDE_PACKAGE_ABI" in os.environ: ++ feature.zlib = "z" ++ elif _find_include_file(self, "zlib.h"): + if _find_library_file(self, "z"): + feature.zlib = "z" + elif sys.platform == "win32" and _find_library_file(self, "zlib"): +@@ -565,7 +567,9 @@ + + if feature.want("jpeg"): + _dbg("Looking for jpeg") +- if _find_include_file(self, "jpeglib.h"): ++ if "PYODIDE_PACKAGE_ABI" in os.environ: ++ feature.jpeg = "jpeg" ++ elif _find_include_file(self, "jpeglib.h"): + if _find_library_file(self, "jpeg"): + feature.jpeg = "jpeg" + elif sys.platform == "win32" and _find_library_file(self, "libjpeg"): +@@ -631,7 +635,9 @@ + + if feature.want("freetype"): + _dbg("Looking for freetype") +- if _find_library_file(self, "freetype"): ++ if "PYODIDE_PACKAGE_ABI" in os.environ: ++ feature.freetype = "freetype" ++ elif _find_library_file(self, "freetype"): + # look for freetype2 include files + freetype_version = 0 + for subdir in self.compiler.include_dirs: +@@ -704,7 +710,8 @@ + libs = self.add_imaging_libs.split() + defs = [] + if feature.jpeg: +- libs.append(feature.jpeg) ++ if not "PYODIDE_PACKAGE_ABI" in os.environ: ++ libs.append(feature.jpeg) + defs.append(("HAVE_LIBJPEG", None)) + if feature.jpeg2000: + libs.append(feature.jpeg2000) diff --git a/packages/pillow/src/setup.cfg b/packages/pillow/src/setup.cfg new file mode 100644 index 000000000..bbff20855 --- /dev/null +++ b/packages/pillow/src/setup.cfg @@ -0,0 +1,12 @@ +[build_ext] +disable-platform-guessing=True +enable-zlib=True +enable-jpeg=True +enable-freetype=True +disable-lcms=True +disable-tiff=True +disable-xcb=True +disable-webp=True +disable-webpmux=True +disable-jpeg2000=True +disable-imagequant=True diff --git a/packages/pillow/test_pillow.py b/packages/pillow/test_pillow.py new file mode 100644 index 000000000..de313f9b6 --- /dev/null +++ b/packages/pillow/test_pillow.py @@ -0,0 +1,24 @@ +def test_pillow(selenium): + selenium.load_package("pillow") + selenium.run( + r""" +from PIL import Image, ImageDraw, ImageOps +import io + +img=Image.new('RGB',(4,4),color=(0,0,0)) +ctx=ImageDraw.Draw(img) +ctx.line([0,0,3,0,3,3,0,3,0,0],(255,0,0),1) +img.putpixel((1,1),(0,255,0)) +img.putpixel((2,2),(0,0,255)) +img=ImageOps.flip(img) +assert img.tobytes() == b'\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\x00\x00\x00\x00\x00\xff\xff\x00\x00\xff\x00\x00\x00\xff\x00\x00\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00' +byio=io.BytesIO() +img.save(byio,format='PNG') +assert byio.getvalue() == b'\x89PNG\r\n\x1a\n\x00\x00\x00\rIHDR\x00\x00\x00\x04\x00\x00\x00\x04\x08\x02\x00\x00\x00&\x93\t)\x00\x00\x00\x1cIDATx\x9cc\xfc\xcf\x80\x04`\x9c\xff\xff\x19\x18\x98`\x02\x8c\x0c\x0c\x0c\x8c\xc8\xca\x00\xb5\x05\x06\x00\xcbi8B\x00\x00\x00\x00IEND\xaeB`\x82' +img=Image.open(byio) +assert img.tobytes() == b'\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\x00\x00\x00\x00\x00\xff\xff\x00\x00\xff\x00\x00\x00\xff\x00\x00\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00\xff\x00\x00' +asjpg=io.BytesIO() +img.save(asjpg,format='JPEG') +img=Image.open(asjpg) + """ + )