diff --git a/src/ocrmypdf.py b/src/ocrmypdf.py index 0dac1380..68d1591f 100755 --- a/src/ocrmypdf.py +++ b/src/ocrmypdf.py @@ -195,109 +195,6 @@ def clean_pdf( check_call(args_mutool) -FRIENDLY_COLORSPACE = { - '/DeviceGray': 'gray', - '/CalGray': 'gray', - '/DeviceRGB': 'rgb', - '/CalRGB': 'rgb', - '/DeviceCMYK': 'cmyk', - '/Lab': 'lab', - '/ICCBased': 'icc', - '/Indexed': 'index', - '/Separation': 'sep', - '/DeviceN': 'devn', - '/Pattern': '-' -} - -FRIENDLY_ENCODING = { - '/CCITTFaxDecode': 'ccitt', - '/DCTDecode': 'jpeg', - '/JPXDecode': 'jpx', - '/JBIG2Decode': 'jbig2', -} - -FRIENDLY_COMP = { - 'gray': 1, - 'rgb': 3, - 'cmyk': 4, - 'lab': 3, -} - - -def pdf_get_pageinfo(infile, page, width_pt, height_pt): - pageinfo = {} - pageinfo['pageno'] = page - pageinfo['width_inches'] = width_pt / 72.0 - pageinfo['height_inches'] = height_pt / 72.0 - pageinfo['images'] = [] - - p_pdftotext = Popen(['pdftotext', '-f', str(page), '-l', str(page), - '-raw', '-nopgbrk', infile, '-'], - close_fds=True, stdout=PIPE, stderr=PIPE, - universal_newlines=True) - text, _ = p_pdftotext.communicate() - if len(text.strip()) > 0: - pageinfo['has_text'] = True - else: - pageinfo['has_text'] = False - - pdf = pypdf.PdfFileReader(infile) - page = pdf.pages[page - 1] - - if not '/XObject' in page['/Resources']: - # Missing /XObject means no images or possibly corrupt PDF - return pageinfo - - for xobj in page['/Resources']['/XObject']: - # PyPDF2 returns the keys as an iterator - pdfimage = page['/Resources']['/XObject'][xobj] - if pdfimage['/Subtype'] != '/Image': - continue - if '/ImageMask' in pdfimage: - if pdfimage['/ImageMask']: - continue - image = {} - image['width'] = pdfimage['/Width'] - image['height'] = pdfimage['/Height'] - image['bpc'] = pdfimage['/BitsPerComponent'] - if '/Filter' in pdfimage: - filter_ = pdfimage['/Filter'] - if isinstance(filter_, pypdf.generic.ArrayObject): - filter_ = filter_[0] - image['enc'] = FRIENDLY_ENCODING.get(filter_, 'image') - else: - image['enc'] = 'image' - if '/ColorSpace' in pdfimage: - cs = pdfimage['/ColorSpace'] - if isinstance(cs, pypdf.generic.ArrayObject): - cs = cs[0] - image['color'] = FRIENDLY_COLORSPACE.get(cs, '-') - else: - image['color'] = 'jpx' if image['enc'] == 'jpx' else '?' - - image['comp'] = FRIENDLY_COMP.get(image['color'], '?') - image['dpi_w'] = image['width'] / pageinfo['width_inches'] - image['dpi_h'] = image['height'] / pageinfo['height_inches'] - image['dpi'] = (image['dpi_w'] * image['dpi_h']) ** 0.5 - pageinfo['images'].append(image) - - if pageinfo['images']: - xres = max(image['dpi_w'] for image in pageinfo['images']) - yres = max(image['dpi_h'] for image in pageinfo['images']) - pageinfo['xres'], pageinfo['yres'] = xres, yres - pageinfo['width_pixels'] = \ - int(round(xres * pageinfo['width_inches'])) - pageinfo['height_pixels'] = \ - int(round(yres * pageinfo['height_inches'])) - - if options.oversampling_dpi > 0: - rx, ry = options.oversampling_dpi, options.oversampling_dpi - else: - rx, ry = pageinfo['xres'], pageinfo['yres'] - pageinfo['xres_render'], pageinfo['yres_render'] = rx, ry - - return pageinfo - pageno, width_pt, height_pt = map(int, options.page_info.split(' ', 3)) pageinfo = pdf_get_pageinfo(options.input_file, pageno, width_pt, height_pt) diff --git a/src/pageinfo.py b/src/pageinfo.py new file mode 100644 index 00000000..b79c0144 --- /dev/null +++ b/src/pageinfo.py @@ -0,0 +1,112 @@ +#!/usr/bin/env python3 +# + +from subprocess import Popen, PIPE +import PyPDF2 as pypdf + + +FRIENDLY_COLORSPACE = { + '/DeviceGray': 'gray', + '/CalGray': 'gray', + '/DeviceRGB': 'rgb', + '/CalRGB': 'rgb', + '/DeviceCMYK': 'cmyk', + '/Lab': 'lab', + '/ICCBased': 'icc', + '/Indexed': 'index', + '/Separation': 'sep', + '/DeviceN': 'devn', + '/Pattern': '-' +} + +FRIENDLY_ENCODING = { + '/CCITTFaxDecode': 'ccitt', + '/DCTDecode': 'jpeg', + '/JPXDecode': 'jpx', + '/JBIG2Decode': 'jbig2', +} + +FRIENDLY_COMP = { + 'gray': 1, + 'rgb': 3, + 'cmyk': 4, + 'lab': 3, +} + + +def _pdf_get_pageinfo(infile, page: int): + pageinfo = {} + pageinfo['pageno'] = page + pageinfo['images'] = [] + + p_pdftotext = Popen(['pdftotext', '-f', str(page), '-l', str(page), + '-raw', '-nopgbrk', infile, '-'], + close_fds=True, stdout=PIPE, stderr=PIPE, + universal_newlines=True) + text, _ = p_pdftotext.communicate() + if len(text.strip()) > 0: + pageinfo['has_text'] = True + else: + pageinfo['has_text'] = False + + pdf = pypdf.PdfFileReader(infile) + page = pdf.pages[page - 1] + width_pt = page['/MediaBox'][2] - page['/MediaBox'][0] + height_pt = page['/MediaBox'][3] - page['/MediaBox'][1] + pageinfo['width_inches'] = width_pt / 72.0 + pageinfo['height_inches'] = height_pt / 72.0 + + if '/XObject' not in page['/Resources']: + # Missing /XObject means no images or possibly corrupt PDF + return pageinfo + + for xobj in page['/Resources']['/XObject']: + # PyPDF2 returns the keys as an iterator + pdfimage = page['/Resources']['/XObject'][xobj] + if pdfimage['/Subtype'] != '/Image': + continue + if '/ImageMask' in pdfimage: + if pdfimage['/ImageMask']: + continue + image = {} + image['width'] = pdfimage['/Width'] + image['height'] = pdfimage['/Height'] + image['bpc'] = pdfimage['/BitsPerComponent'] + if '/Filter' in pdfimage: + filter_ = pdfimage['/Filter'] + if isinstance(filter_, pypdf.generic.ArrayObject): + filter_ = filter_[0] + image['enc'] = FRIENDLY_ENCODING.get(filter_, 'image') + else: + image['enc'] = 'image' + if '/ColorSpace' in pdfimage: + cs = pdfimage['/ColorSpace'] + if isinstance(cs, pypdf.generic.ArrayObject): + cs = cs[0] + image['color'] = FRIENDLY_COLORSPACE.get(cs, '-') + else: + image['color'] = 'jpx' if image['enc'] == 'jpx' else '?' + + image['comp'] = FRIENDLY_COMP.get(image['color'], '?') + image['dpi_w'] = image['width'] / pageinfo['width_inches'] + image['dpi_h'] = image['height'] / pageinfo['height_inches'] + image['dpi'] = (image['dpi_w'] * image['dpi_h']) ** 0.5 + pageinfo['images'].append(image) + + if pageinfo['images']: + xres = max(image['dpi_w'] for image in pageinfo['images']) + yres = max(image['dpi_h'] for image in pageinfo['images']) + pageinfo['xres'], pageinfo['yres'] = xres, yres + pageinfo['width_pixels'] = \ + int(round(xres * pageinfo['width_inches'])) + pageinfo['height_pixels'] = \ + int(round(yres * pageinfo['height_inches'])) + rx, ry = pageinfo['xres'], pageinfo['yres'] + pageinfo['xres_render'], pageinfo['yres_render'] = rx, ry + + return pageinfo + + +def pdf_get_all_pageinfo(infile): + pdf = pypdf.PdfFileReader(infile) + return [_pdf_get_pageinfo(infile, n) for n in range(pdf.numPages)]