I am trying to convert the output of pyBarcode to a PIL Image file without first saving an image. First off, pyBarcode generates an image file like such:
>>> import barcode
>>> from barcode.writer import ImageWriter
>>> ean = barcode.get_barcode('ean', '123456789102', writer=ImageWriter())
>>> filename = ean.save('ean13')
>>> filename
u'ean13.png'
As you can see above, I don't want the image to be actually saved on my filesystem because I want the output to be processed into a PIL Image. So I did some modifications:
i = StringIO()
ean = barcode.get_barcode('ean', '123456789102', writer=ImageWriter())
ean.write(i)
Now I have a StringIO file object and I want to PIL to "read" it and convert it to a PIL Image file. I wanted to use Image.new
or Image.frombuffer
but both these functions required me to enter a size...can't the size be determined from the barcode StringIO data? Image.open
states this in their documentation:
You can use either a string (representing the filename) or a file object. In the latter case, the file object must implement read, seek and tell methods, and be opened in binary mode
Isn't a StringIO instance a file object as well? How do I open it as a binary file?
Image.open(i, 'rb')
>>> Image.open(i, 'rb')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/home/mark/.virtualenvs/barcode/local/lib/python2.7/site-packages/PIL/Image.py", line 1947, in open
raise ValueError("bad mode")
ValueError: bad mode
I'm sure I'm pretty close to the answer I just need someone's guidance. Thanks in advance guys!
save() Saves this image under the given filename. If no format is specified, the format to use is determined from the filename extension, if possible. Keyword options can be used to provide additional instructions to the writer.
Modes. The mode of an image is a string which defines the type and depth of a pixel in the image. Each pixel uses the full range of the bit depth.
StringIO
objects are file objects.
However, if you are using the cStringIO
module (the C-optimized version of the StringIO
module) then do note that once you ceate an emptyStringIO
instance, it is optimized for writing only, and you cannot use it as in input file, and vice-versa. Simply reinitialize it in that case:
i = StringIO(i.getvalue()) # create a cStringIO.StringO instance for a cStringIO.StringI instance.
For the python version (the StringIO
module), simply seek to the start again:
i.seek(0)
You do not need to specify a file mode for the Image.open()
call; unless i
is a string it'll be ignored in any case:
img = Image.open(i)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With