Skip to content

Commit

Permalink
Merge pull request #18 from albarji/bugfix/alpha
Browse files Browse the repository at this point in the history
Solves #17
  • Loading branch information
albarji authored Nov 23, 2017
2 parents 28901be + d277fae commit a78399a
Show file tree
Hide file tree
Showing 7 changed files with 55 additions and 36 deletions.
28 changes: 13 additions & 15 deletions neuralstyle/imagemagick.py
Original file line number Diff line number Diff line change
@@ -1,28 +1,19 @@
# Convenience functions to perform Image Magicks
from subprocess import run, PIPE
from glob import glob
from tempfile import TemporaryDirectory
from neuralstyle.utils import filename


def convert(origin, dest):
"""Transforms the format of an image in a file, by creating a new file with the new format
If the input file has several layers, they are flattened.
"""
command = "convert " + origin + " -flatten " + dest
run(command, shell=True)
"""Transforms the format of an image in a file, by creating a new file with the new format"""
if ismultilayer(origin):
raise ValueError("Cannot operate with multilayer images")
run("convert %s %s" % (origin, dest), shell=True)


def shape(imfile):
"""Returns the shape of an image file
If the input file has several layers, it is flattened before computing the shape.
"""
tmpdir = TemporaryDirectory()
tmpname = tmpdir.name + "/" + "image.png"
convert(imfile, tmpname)
result = run("convert " + tmpname + ' -format "%w %h" info:', shell=True, check=True, stdout=PIPE)
"""Returns the shape of an image file"""
result = run("convert " + imfile + ' -format "%w %h" info:', shell=True, check=True, stdout=PIPE)
return [int(x) for x in result.stdout.decode("utf-8").split(" ")]


Expand Down Expand Up @@ -90,6 +81,8 @@ def composite(imfiles, outname):

def extractalpha(imfile, rgbfile, alphafile):
"""Decomposes an image file into the RGB channels and the alpha channel, saving both as separate image files"""
if ismultilayer(imfile):
raise ValueError("Cannot operate with multilayer images")
# Alpha channel extraction
command = "convert -alpha extract %s %s" % (imfile, alphafile)
run(command, shell=True, check=True)
Expand Down Expand Up @@ -119,3 +112,8 @@ def equalimages(imfile1, imfile2):
if result.returncode == 2:
raise IOError("Error while calling imagemagick compare method")
return result.returncode == 0


def ismultilayer(imfile):
"""Returns whether an image file contains multiple layers"""
return len(shape(imfile)) > 2
52 changes: 42 additions & 10 deletions tests/algorithms_tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,18 @@
STYLES = "/app/entrypoint/tests/styles/"


def assertalldifferent(pattern, expected=None):
"""Asserts that all images that follow a given glob pattern have different contents
An expected number of images can also be provided to be checked.
"""
files = glob(pattern)
if expected is not None:
assert len(files) == expected
for f1, f2 in zip(files, files[1:]):
assert not equalimages(f1, f2)


def test_styletransfer_gatys():
"""Style transfer works without error for the Gatys algorithm"""
tmpdir = TemporaryDirectory()
Expand Down Expand Up @@ -79,11 +91,7 @@ def test_styletransfer_ss():
tmpdir = TemporaryDirectory()
styletransfer([CONTENTS + img], [STYLES + "cubism.jpg"], tmpdir.name, alg=alg, size=100,
stylescales=stylescales)
files = glob(tmpdir.name + "/" + filename(img) + "*cubism*")
# Check correct number of generated images, and that they are different
assert len(files) == len(stylescales)
for f1, f2 in zip(files, files[1:]):
assert not equalimages(f1, f2)
assertalldifferent(tmpdir.name + "/" + filename(img) + "*cubism*", len(stylescales))


def test_styletransfer_sw():
Expand All @@ -94,11 +102,7 @@ def test_styletransfer_sw():
tmpdir = TemporaryDirectory()
styletransfer([CONTENTS + img], [STYLES + "cubism.jpg"], tmpdir.name, alg=alg, size=100,
weights=styleweights)
files = glob(tmpdir.name + "/" + filename(img) + "*cubism*")
# Check correct number of generated images, and that they are different
assert len(files) == len(styleweights)
for f1, f2 in zip(files, files[1:]):
assert not equalimages(f1, f2)
assertalldifferent(tmpdir.name + "/" + filename(img) + "*cubism*", len(styleweights))


def test_neuraltile():
Expand All @@ -124,3 +128,31 @@ def test_formatpsd():
tmpdir = TemporaryDirectory()
styletransfer(contents, [STYLES + "cubism.jpg"], tmpdir.name, alg="chen-schmidt-inverse")
assert len(glob(tmpdir.name + "/*cubism*")) == 1


def test_alpha():
"""Transformation of images with an alpha channel preserve transparency"""
tmpdir = TemporaryDirectory()
# Transform image with alpha
styletransfer([CONTENTS + "dockersmallalpha.png"], [STYLES + "cubism.jpg"], tmpdir.name, alg="chen-schmidt-inverse")
assert len(glob(tmpdir.name + "/*dockersmallalpha_cubism*")) == 1
# Transform image without alpha
styletransfer([CONTENTS + "dockersmall.png"], [STYLES + "cubism.jpg"], tmpdir.name, alg="chen-schmidt-inverse")
assert len(glob(tmpdir.name + "/*dockersmall_cubism*")) == 1
# Check correct that generated image are different
assertalldifferent(tmpdir.name + "/*cubism*")


def test_alpha_tiling():
"""Transformation of images with an alpha channel preserve transparency, even when a tiling strategy is used"""
tmpdir = TemporaryDirectory()
# Transform image with alpha
styletransfer([CONTENTS + "dockersmallalpha.png"], [STYLES + "cubism.jpg"], tmpdir.name, alg="chen-schmidt-inverse",
maxtilesize=150)
assert len(glob(tmpdir.name + "/*dockersmallalpha_cubism*")) == 1
# Transform image without alpha
styletransfer([CONTENTS + "dockersmall.png"], [STYLES + "cubism.jpg"], tmpdir.name, alg="chen-schmidt-inverse",
maxtilesize=150)
assert len(glob(tmpdir.name + "/*dockersmall_cubism*")) == 1
# Check correct that generated image are different
assertalldifferent(tmpdir.name + "/*cubism*")
Binary file added tests/contents/dockersmallalpha.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added tests/contents/marbles.tga
Binary file not shown.
Binary file added tests/contents/oldtelephone.psd
Binary file not shown.
Binary file added tests/contents/tgasample.tga
Binary file not shown.
11 changes: 0 additions & 11 deletions tests/imagemagick_tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,17 +47,6 @@ def test_convert_nolayers():
assert shape(outname) == shape(content)


def test_convert_layers():
"""Convert a single image with layers works as expected"""
for content in [CONTENTS + f for f in ["oldtelephone.psd"]]:
for ext in [".png", ".jpg", ".psd", ".tga"]:
tmpdir = TemporaryDirectory()
outname = tmpdir.name + "/" + "output" + ext
convert(content, outname)
assert len(glob(tmpdir.name + "/" + filename(outname) + ext)) == 1
assert shape(outname) == shape(content)


def test_resize_keepproportions():
"""Resizing an image without changing proportions works correctly"""
tmpdir = TemporaryDirectory()
Expand Down

0 comments on commit a78399a

Please sign in to comment.