First full run through successful with v2.0.0 official, with write support. #90

This commit is contained in:
John Evans 2013-07-29 09:54:04 -04:00
commit c2a94b92f1
7 changed files with 95 additions and 3 deletions

View file

@ -34,6 +34,14 @@ from .lib import _openjpeg as _opj
from .lib import _openjp2 as _opj2
from .lib import c
# Need to known if openjp2 library is the officially release v2.0.0 or not.
_OPENJP2_IS_OFFICIAL_V2 = False
if _opj2.OPENJP2 is not None:
if _opj2.version() == '2.0.0':
if not hasattr(_opj2.OPENJP2,
'opj_stream_create_default_file_stream_v3'):
_OPENJP2_IS_OFFICIAL_V2 = True
_COLORSPACE_MAP = {'rgb': _opj2.CLRSPC_SRGB,
'gray': _opj2.CLRSPC_GRAY,
'grey': _opj2.CLRSPC_GRAY,
@ -371,6 +379,13 @@ class Jp2k(Jp2kBox):
raise IOError(msg)
numrows, numcols, num_comps = img_array.shape
if _OPENJP2_IS_OFFICIAL_V2:
if img_array.shape[2] != 1 and img_array.shape[2] != 3:
msg = "Writing images is restricted to single-channel "
msg += "greyscale images or three-channel RGB images when "
msg += "the OpenJPEG library version is the official 2.0.0 "
msg += "release."
raise IOError(msg)
if colorspace is None:
if img_array.shape[2] == 1 or img_array.shape[2] == 2:
@ -449,11 +464,24 @@ class Jp2k(Jp2kBox):
_opj2.set_warning_handler(codec, _WARNING_CALLBACK)
_opj2.set_error_handler(codec, _ERROR_CALLBACK)
_opj2.setup_encoder(codec, cparams, image)
strm = _opj2.stream_create_default_file_stream_v3(self.filename, False)
if hasattr(_opj2.OPENJP2, 'opj_stream_create_default_file_stream_v3'):
strm = _opj2.stream_create_default_file_stream_v3(self.filename,
False)
else:
fptr = c.fopen(self.filename, 'wb')
strm = _opj2.stream_create_default_file_stream(fptr, False)
_opj2.start_compress(codec, image, strm)
_opj2.encode(codec, strm)
_opj2.end_compress(codec, strm)
_opj2.stream_destroy_v3(strm)
if hasattr(_opj2.OPENJP2, 'opj_stream_create_default_file_stream_v3'):
_opj2.stream_destroy_v3(strm)
else:
_opj2.stream_destroy(strm)
c.fclose(fptr)
_opj2.destroy_codec(codec)
_opj2.image_destroy(image)

View file

@ -5,6 +5,7 @@ Wraps individual functions in openjp2 library.
# pylint: disable=C0302,R0903
import ctypes
import sys
from .config import glymur_config
OPENJP2, OPENJPEG = glymur_config()
@ -1382,3 +1383,13 @@ def set_error_message(msg):
"""The openjpeg error handler has recorded an error message."""
global ERROR_MSG_LST
ERROR_MSG_LST.append(msg)
def version():
"""Wrapper for opj_version library routine."""
OPENJP2.opj_version.restype = ctypes.c_char_p
library_version = OPENJP2.opj_version()
if sys.hexversion >= 0x03000000:
return library_version.decode('utf-8')
else:
return library_version

View file

@ -16,10 +16,15 @@ import numpy as np
import glymur
OPENJP2_IS_V2_OFFICIAL=False
if glymur.lib.openjp2.OPENJP2 is not None:
if not hasattr(glymur.lib.openjp2.OPENJP2, 'opj_stream_create_default_file_stream_v3'):
OPENJP2_IS_V2_OFFICIAL=True
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
@unittest.skipIf(glymur.lib._openjp2.OPENJP2 is None,
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL, "API followed here specific to V2.0+")
class TestOpenJP2(unittest.TestCase):
def setUp(self):

View file

@ -3,6 +3,13 @@ import sys
import numpy as np
import glymur
OPENJP2_IS_V2_OFFICIAL=False
if glymur.lib.openjp2.OPENJP2 is not None:
if not hasattr(glymur.lib.openjp2.OPENJP2, 'opj_stream_create_default_file_stream_v3'):
OPENJP2_IS_V2_OFFICIAL=True
def mse(amat, bmat):
"""Mean Square Error"""

View file

@ -19,6 +19,8 @@ from glymur.jp2box import *
from glymur.core import COLOR, OPACITY
from glymur.core import RED, GREEN, BLUE, GREY, WHOLE_IMAGE
from .fixtures import OPENJP2_IS_V2_OFFICIAL
try:
format_corpus_data_root = os.environ['FORMAT_CORPUS_DATA_ROOT']
except KeyError:
@ -34,6 +36,8 @@ def load_tests(loader, tests, ignore):
return tests
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Requires v2.0.0+ in order to run.")
@unittest.skipIf(os.name == "nt", "Temporary file issue on window.")
@unittest.skipIf(glymur.lib.openjp2.OPENJP2 is None,
"Missing openjp2 library.")

View file

@ -26,6 +26,8 @@ import glymur
from glymur import Jp2k
from glymur.lib import openjp2 as opj2
from .fixtures import OPENJP2_IS_V2_OFFICIAL
try:
data_root = os.environ['OPJ_DATA_ROOT']
except KeyError:
@ -477,6 +479,8 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[1].colorspace,
glymur.core.GREYSCALE)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Does not seem to work on official v2.0.0 release.")
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_grey_with_extra_component(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
@ -501,6 +505,8 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[1].colorspace,
glymur.core.GREYSCALE)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Does not seem to work on official v2.0.0 release.")
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_rgb_with_extra_component(self):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
@ -512,6 +518,17 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(j.box[2].box[0].num_components, 4)
self.assertEqual(j.box[2].box[1].colorspace, glymur.core.SRGB)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL is False,
"Test is specific for v2.0.0 release")
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
def test_extra_components_on_v2_official(self):
# Extra components seems to require 2.0+. Verify that we error out.
with self.assertRaises(IOError):
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
j = Jp2k(tfile.name, 'wb')
data = np.zeros((128, 128, 4), dtype=np.uint8)
j.write(data)
def test_specify_ycc(self):
# We don't support writing YCC at the moment.
with tempfile.NamedTemporaryFile(suffix='.jp2') as tfile:
@ -655,6 +672,8 @@ class TestJp2k(unittest.TestCase):
self.assertEqual(jasoc.box[3].box[1].box_id, 'xml ')
@unittest.skipIf(os.name == "nt", "NamedTemporaryFile issue on windows")
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Segfault on official v2.0.0 release.")
def test_openjpeg_library_message(self):
# Verify the error message produced by the openjpeg library.
# This will confirm that the error callback mechanism is working.
@ -675,6 +694,8 @@ class TestJp2k(unittest.TestCase):
tfile.write(data[3186:])
tfile.flush()
import shutil
shutil.copyfile(tfile.name, '/home/jevans/tmp/a.jp2')
with warnings.catch_warnings():
warnings.simplefilter("ignore")
j = Jp2k(tfile.name)

View file

@ -991,6 +991,8 @@ class TestSuite(unittest.TestCase):
data = Jp2k(jfile).read()
self.assertTrue(True)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test known to fail in v2.0.0 official")
def test_NR_DEC_text_GBR_jp2_29_decode(self):
jfile = os.path.join(data_root,
'input/nonregression/text_GBR.jp2')
@ -1007,12 +1009,16 @@ class TestSuite(unittest.TestCase):
data = Jp2k(jfile).read()
self.assertTrue(True)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test known to fail in v2.0.0 official")
def test_NR_DEC_kodak_2layers_lrcp_j2c_31_decode(self):
jfile = os.path.join(data_root,
'input/nonregression/kodak_2layers_lrcp.j2c')
data = Jp2k(jfile).read()
self.assertTrue(True)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test known to fail in v2.0.0 official")
def test_NR_DEC_kodak_2layers_lrcp_j2c_32_decode(self):
jfile = os.path.join(data_root,
'input/nonregression/kodak_2layers_lrcp.j2c')
@ -1025,6 +1031,8 @@ class TestSuite(unittest.TestCase):
data = Jp2k(jfile).read()
self.assertTrue(True)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test known to fail in v2.0.0 official")
def test_NR_DEC_mem_b2ace68c_1381_jp2_34_decode(self):
jfile = os.path.join(data_root,
'input/nonregression/mem-b2ace68c-1381.jp2')
@ -1035,6 +1043,8 @@ class TestSuite(unittest.TestCase):
data = j.read()
self.assertTrue(True)
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test known to fail in v2.0.0 official")
def test_NR_DEC_mem_b2b86b74_2753_jp2_35_decode(self):
jfile = os.path.join(data_root,
'input/nonregression/mem-b2b86b74-2753.jp2')
@ -1050,6 +1060,8 @@ class TestSuite(unittest.TestCase):
with self.assertRaises(IOError):
data = j.read()
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test not in done in v2.0.0 official")
def test_NR_DEC_jp2_36_decode(self):
lst = ('input',
'nonregression',
@ -1088,6 +1100,8 @@ class TestSuite(unittest.TestCase):
with self.assertRaises(RuntimeError):
data = Jp2k(jfile).read()
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test not in done in v2.0.0 official")
@unittest.skipIf(sys.hexversion < 0x03020000,
"Uses features introduced in 3.2.")
def test_NR_DEC_issue188_beach_64bitsbox_jp2_41_decode(self):
@ -1098,6 +1112,8 @@ class TestSuite(unittest.TestCase):
with self.assertWarns(UserWarning) as cw:
data = Jp2k(jfile).read()
@unittest.skipIf(OPENJP2_IS_V2_OFFICIAL,
"Test not in done in v2.0.0 official")
def test_NR_DEC_issue206_image_000_jp2_42_decode(self):
jfile = os.path.join(data_root,
'input/nonregression/issue206_image-000.jp2')