Skip to content

Commit

Permalink
Just for fun, yapf-formatting of PIL/*.py
Browse files Browse the repository at this point in the history
And amazingly all tests pass! https://github.com/google/yapf
  • Loading branch information
aclark4life committed Apr 2, 2015
1 parent d754598 commit 3bb6b14
Show file tree
Hide file tree
Showing 82 changed files with 1,654 additions and 2,015 deletions.
18 changes: 6 additions & 12 deletions PIL/BdfFontFile.py
Expand Up @@ -20,7 +20,6 @@
from PIL import Image
from PIL import FontFile


# --------------------------------------------------------------------
# parse X Bitmap Distribution Format (BDF)
# --------------------------------------------------------------------
Expand All @@ -34,11 +33,7 @@
"OT": "Other"
}

bdf_spacing = {
"P": "Proportional",
"M": "Monospaced",
"C": "Cell"
}
bdf_spacing = {"P": "Proportional", "M": "Monospaced", "C": "Cell"}


def bdf_char(f):
Expand All @@ -58,7 +53,7 @@ def bdf_char(f):
if not s or s[:6] == b"BITMAP":
break
i = s.find(b" ")
props[s[:i].decode('ascii')] = s[i+1:-1].decode('ascii')
props[s[:i].decode('ascii')] = s[i + 1:-1].decode('ascii')

# load bitmap
bitmap = []
Expand All @@ -72,7 +67,7 @@ def bdf_char(f):
[x, y, l, d] = [int(p) for p in props["BBX"].split()]
[dx, dy] = [int(p) for p in props["DWIDTH"].split()]

bbox = (dx, dy), (l, -d-y, x+l, -d), (0, 0, x, y)
bbox = (dx, dy), (l, -d - y, x + l, -d), (0, 0, x, y)

try:
im = Image.frombytes("1", (x, y), bitmap, "hex", "1")
Expand All @@ -82,12 +77,11 @@ def bdf_char(f):

return id, int(props["ENCODING"]), bbox, im


##
# Font file plugin for the X11 BDF format.

class BdfFontFile(FontFile.FontFile):

class BdfFontFile(FontFile.FontFile):
def __init__(self, fp):

FontFile.FontFile.__init__(self)
Expand All @@ -104,10 +98,10 @@ def __init__(self, fp):
if not s or s[:13] == b"ENDPROPERTIES":
break
i = s.find(b" ")
props[s[:i].decode('ascii')] = s[i+1:-1].decode('ascii')
props[s[:i].decode('ascii')] = s[i + 1:-1].decode('ascii')
if s[:i] in [b"COMMENT", b"COPYRIGHT"]:
if s.find(b"LogicalFontDescription") < 0:
comments.append(s[i+1:-1].decode('ascii'))
comments.append(s[i + 1:-1].decode('ascii'))

font = props["FONT"].split("-")

Expand Down
152 changes: 97 additions & 55 deletions PIL/BmpImagePlugin.py
Expand Up @@ -23,14 +23,11 @@
# See the README file for information on usage and redistribution.
#


__version__ = "0.7"


from PIL import Image, ImageFile, ImagePalette, _binary
import math


i8 = _binary.i8
i16 = _binary.i16le
i32 = _binary.i32le
Expand Down Expand Up @@ -67,7 +64,14 @@ class BmpImageFile(ImageFile.ImageFile):
format_description = "Windows Bitmap"
format = "BMP"
# --------------------------------------------------- BMP Compression values
COMPRESSIONS = {'RAW': 0, 'RLE8': 1, 'RLE4': 2, 'BITFIELDS': 3, 'JPEG': 4, 'PNG': 5}
COMPRESSIONS = {
'RAW': 0,
'RLE8': 1,
'RLE4': 2,
'BITFIELDS': 3,
'JPEG': 4,
'PNG': 5
}
RAW, RLE8, RLE4, BITFIELDS, JPEG, PNG = 0, 1, 2, 3, 4, 5

def _bitmap(self, header=0, offset=0):
Expand All @@ -76,10 +80,14 @@ def _bitmap(self, header=0, offset=0):
if header:
seek(header)
file_info = dict()
file_info['header_size'] = i32(read(4)) # read bmp header size @offset 14 (this is part of the header size)
file_info['header_size'] = i32(
read(4)
) # read bmp header size @offset 14 (this is part of the header size)
file_info['direction'] = -1
# --------------------- If requested, read header at a specific position
header_data = ImageFile._safe_read(self.fp, file_info['header_size'] - 4) # read the rest of the bmp header, without its size
header_data = ImageFile._safe_read(
self.fp, file_info['header_size'] - 4
) # read the rest of the bmp header, without its size
# --------------------------------------------------- IBM OS/2 Bitmap v1
# ------ This format has different offsets because of width/height types
if file_info['header_size'] == 12:
Expand All @@ -90,59 +98,87 @@ def _bitmap(self, header=0, offset=0):
file_info['compression'] = self.RAW
file_info['palette_padding'] = 3
# ---------------------------------------------- Windows Bitmap v2 to v5
elif file_info['header_size'] in (40, 64, 108, 124): # v3, OS/2 v2, v4, v5
elif file_info['header_size'] in (40, 64, 108,
124): # v3, OS/2 v2, v4, v5
if file_info['header_size'] >= 40: # v3 and OS/2
file_info['y_flip'] = i8(header_data[7]) == 0xff
file_info['direction'] = 1 if file_info['y_flip'] else -1
file_info['width'] = i32(header_data[0:4])
file_info['height'] = i32(header_data[4:8]) if not file_info['y_flip'] else 2**32 - i32(header_data[4:8])
file_info['height'] = i32(header_data[4:8]) if not file_info[
'y_flip'
] else 2 ** 32 - i32(header_data[4:8])
file_info['planes'] = i16(header_data[8:10])
file_info['bits'] = i16(header_data[10:12])
file_info['compression'] = i32(header_data[12:16])
file_info['data_size'] = i32(header_data[16:20]) # byte size of pixel data
file_info['pixels_per_meter'] = (i32(header_data[20:24]), i32(header_data[24:28]))
file_info['data_size'] = i32(header_data[16:20]
) # byte size of pixel data
file_info['pixels_per_meter'] = (i32(header_data[20:24]),
i32(header_data[24:28]))
file_info['colors'] = i32(header_data[28:32])
file_info['palette_padding'] = 4
self.info["dpi"] = tuple(map(lambda x: math.ceil(x / 39.3701), file_info['pixels_per_meter']))
self.info["dpi"] = tuple(map(lambda x: math.ceil(x / 39.3701),
file_info['pixels_per_meter']))
if file_info['compression'] == self.BITFIELDS:
if len(header_data) >= 52:
for idx, mask in enumerate(['r_mask', 'g_mask', 'b_mask', 'a_mask']):
file_info[mask] = i32(header_data[36+idx*4:40+idx*4])
for idx, mask in enumerate(['r_mask', 'g_mask',
'b_mask', 'a_mask']):
file_info[mask] = i32(
header_data[36 + idx * 4:40 + idx * 4])
else:
for mask in ['r_mask', 'g_mask', 'b_mask', 'a_mask']:
file_info[mask] = i32(read(4))
file_info['rgb_mask'] = (file_info['r_mask'], file_info['g_mask'], file_info['b_mask'])
file_info['rgba_mask'] = (file_info['r_mask'], file_info['g_mask'], file_info['b_mask'], file_info['a_mask'])
file_info['rgb_mask'] = (file_info['r_mask'],
file_info['g_mask'],
file_info['b_mask'])
file_info['rgba_mask'] = (
file_info['r_mask'], file_info['g_mask'],
file_info['b_mask'], file_info['a_mask'])
else:
raise IOError("Unsupported BMP header type (%d)" % file_info['header_size'])
raise IOError(
"Unsupported BMP header type (%d)" % file_info['header_size'])
# ------------------ Special case : header is reported 40, which
# ---------------------- is shorter than real size for bpp >= 16
self.size = file_info['width'], file_info['height']
# -------- If color count was not found in the header, compute from bits
file_info['colors'] = file_info['colors'] if file_info.get('colors', 0) else (1 << file_info['bits'])
file_info['colors'] = file_info['colors'] if file_info.get(
'colors', 0) else (1 << file_info['bits'])
# -------------------------------- Check abnormal values for DOS attacks
if file_info['width'] * file_info['height'] > 2**31:
if file_info['width'] * file_info['height'] > 2 ** 31:
raise IOError("Unsupported BMP Size: (%dx%d)" % self.size)
# ----------------------- Check bit depth for unusual unsupported values
self.mode, raw_mode = BIT2MODE.get(file_info['bits'], (None, None))
if self.mode is None:
raise IOError("Unsupported BMP pixel depth (%d)" % file_info['bits'])
raise IOError(
"Unsupported BMP pixel depth (%d)" % file_info['bits'])
# ----------------- Process BMP with Bitfields compression (not palette)
if file_info['compression'] == self.BITFIELDS:
SUPPORTED = {
32: [(0xff0000, 0xff00, 0xff, 0x0), (0xff0000, 0xff00, 0xff, 0xff000000), (0x0, 0x0, 0x0, 0x0)],
24: [(0xff0000, 0xff00, 0xff)],
16: [(0xf800, 0x7e0, 0x1f), (0x7c00, 0x3e0, 0x1f)]}
32: [(0xff0000, 0xff00, 0xff, 0x0),
(0xff0000, 0xff00, 0xff, 0xff000000),
(0x0, 0x0, 0x0, 0x0)],
24: [(0xff0000, 0xff00, 0xff)],
16: [(0xf800, 0x7e0, 0x1f), (0x7c00, 0x3e0, 0x1f)]
}
MASK_MODES = {
(32, (0xff0000, 0xff00, 0xff, 0x0)): "BGRX", (32, (0xff0000, 0xff00, 0xff, 0xff000000)): "BGRA", (32, (0x0, 0x0, 0x0, 0x0)): "BGRA",
(24, (0xff0000, 0xff00, 0xff)): "BGR",
(16, (0xf800, 0x7e0, 0x1f)): "BGR;16", (16, (0x7c00, 0x3e0, 0x1f)): "BGR;15"}
(32, (0xff0000, 0xff00, 0xff, 0x0)): "BGRX",
(32, (0xff0000, 0xff00, 0xff, 0xff000000)): "BGRA",
(32, (0x0, 0x0, 0x0, 0x0)): "BGRA",
(24, (0xff0000, 0xff00, 0xff)): "BGR",
(16, (0xf800, 0x7e0, 0x1f)): "BGR;16",
(16, (0x7c00, 0x3e0, 0x1f)): "BGR;15"
}
if file_info['bits'] in SUPPORTED:
if file_info['bits'] == 32 and file_info['rgba_mask'] in SUPPORTED[file_info['bits']]:
raw_mode = MASK_MODES[(file_info['bits'], file_info['rgba_mask'])]
self.mode = "RGBA" if raw_mode in ("BGRA",) else self.mode
elif file_info['bits'] in (24, 16) and file_info['rgb_mask'] in SUPPORTED[file_info['bits']]:
raw_mode = MASK_MODES[(file_info['bits'], file_info['rgb_mask'])]
if file_info['bits'] == 32 and file_info[
'rgba_mask'
] in SUPPORTED[file_info['bits']]:
raw_mode = MASK_MODES[(file_info['bits'],
file_info['rgba_mask'])]
self.mode = "RGBA" if raw_mode in ("BGRA", ) else self.mode
elif file_info['bits'] in (
24, 16
) and file_info['rgb_mask'] in SUPPORTED[file_info['bits']]:
raw_mode = MASK_MODES[(file_info['bits'],
file_info['rgb_mask'])]
else:
raise IOError("Unsupported BMP bitfields layout")
else:
Expand All @@ -151,20 +187,23 @@ def _bitmap(self, header=0, offset=0):
if file_info['bits'] == 32 and header == 22: # 32-bit .cur offset
raw_mode, self.mode = "BGRA", "RGBA"
else:
raise IOError("Unsupported BMP compression (%d)" % file_info['compression'])
raise IOError(
"Unsupported BMP compression (%d)" % file_info['compression'])
# ---------------- Once the header is processed, process the palette/LUT
if self.mode == "P": # Paletted for 1, 4 and 8 bit images
# ----------------------------------------------------- 1-bit images
if not (0 < file_info['colors'] <= 65536):
raise IOError("Unsupported BMP Palette size (%d)" % file_info['colors'])
raise IOError(
"Unsupported BMP Palette size (%d)" % file_info['colors'])
else:
padding = file_info['palette_padding']
palette = read(padding * file_info['colors'])
greyscale = True
indices = (0, 255) if file_info['colors'] == 2 else list(range(file_info['colors']))
indices = (0, 255) if file_info['colors'] == 2 else list(
range(file_info['colors']))
# ------------------ Check if greyscale and ignore palette if so
for ind, val in enumerate(indices):
rgb = palette[ind*padding:ind*padding + 3]
rgb = palette[ind * padding:ind * padding + 3]
if rgb != o8(val) * 3:
greyscale = False
# -------- If all colors are grey, white or black, ditch palette
Expand All @@ -173,13 +212,16 @@ def _bitmap(self, header=0, offset=0):
raw_mode = self.mode
else:
self.mode = "P"
self.palette = ImagePalette.raw("BGRX" if padding == 4 else "BGR", palette)
self.palette = ImagePalette.raw("BGRX" if padding == 4 else
"BGR", palette)

# ----------------------------- Finally set the tile data for the plugin
self.info['compression'] = file_info['compression']
self.tile = [('raw', (0, 0, file_info['width'], file_info['height']), offset or self.fp.tell(),
(raw_mode, ((file_info['width'] * file_info['bits'] + 31) >> 3) & (~3), file_info['direction'])
)]
self.tile = [('raw', (0, 0, file_info['width'], file_info['height']),
offset or self.fp.tell(),
(raw_mode,
((file_info['width'] * file_info['bits'] + 31) >> 3) &
(~3), file_info['direction']))]

def _open(self):
""" Open file, check magic number and read header """
Expand Down Expand Up @@ -234,30 +276,30 @@ def _save(im, fp, filename, check=0):
# 1 meter == 39.3701 inches
ppm = tuple(map(lambda x: int(x * 39.3701), dpi))

stride = ((im.size[0]*bits+7)//8+3) & (~3)
stride = ((im.size[0] * bits + 7) // 8 + 3) & (~3)
header = 40 # or 64 for OS/2 version 2
offset = 14 + header + colors * 4
image = stride * im.size[1]

# bitmap header
fp.write(b"BM" + # file type (magic)
o32(offset+image) + # file size
o32(0) + # reserved
o32(offset)) # image data offset
fp.write(b"BM" + # file type (magic)
o32(offset + image) + # file size
o32(0) + # reserved
o32(offset)) # image data offset

# bitmap info header
fp.write(o32(header) + # info header size
o32(im.size[0]) + # width
o32(im.size[1]) + # height
o16(1) + # planes
o16(bits) + # depth
o32(0) + # compression (0=uncompressed)
o32(image) + # size of bitmap
fp.write(o32(header) + # info header size
o32(im.size[0]) + # width
o32(im.size[1]) + # height
o16(1) + # planes
o16(bits) + # depth
o32(0) + # compression (0=uncompressed)
o32(image) + # size of bitmap
o32(ppm[0]) + o32(ppm[1]) + # resolution
o32(colors) + # colors used
o32(colors)) # colors important
o32(colors) + # colors used
o32(colors)) # colors important

fp.write(b"\0" * (header - 40)) # padding (for OS/2 format)
fp.write(b"\0" * (header - 40)) # padding (for OS/2 format)

if im.mode == "1":
for i in (0, 255):
Expand All @@ -268,8 +310,8 @@ def _save(im, fp, filename, check=0):
elif im.mode == "P":
fp.write(im.im.getpalette("RGB", "BGRX"))

ImageFile._save(im, fp, [("raw", (0, 0)+im.size, 0,
(rawmode, stride, -1))])
ImageFile._save(im, fp, [("raw", (0, 0) + im.size, 0,
(rawmode, stride, -1))])

#
# --------------------------------------------------------------------
Expand Down
5 changes: 2 additions & 3 deletions PIL/BufrStubImagePlugin.py
Expand Up @@ -13,20 +13,20 @@

_handler = None


##
# Install application-specific BUFR image handler.
#
# @param handler Handler object.


def register_handler(handler):
global _handler
_handler = handler


# --------------------------------------------------------------------
# Image adapter


def _accept(prefix):
return prefix[:4] == b"BUFR" or prefix[:4] == b"ZCZC"

Expand Down Expand Up @@ -62,7 +62,6 @@ def _save(im, fp, filename):
raise IOError("BUFR save handler not installed")
_handler.save(im, fp, filename)


# --------------------------------------------------------------------
# Registry

Expand Down

0 comments on commit 3bb6b14

Please sign in to comment.