# -*- coding: utf-8 -*- """量出各页「单位名称文字中心」与「已盖红章中心」的偏差,得出校正量。""" import io import os import sys import fitz import numpy as np sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding="utf-8") HERE = os.path.dirname(os.path.abspath(__file__)) PDF = os.path.join(HERE, "_tmp_inspect", "sealed.pdf") COMPANY = "北京智造易科技有限公司" PAGES = [1, 5, 6, 7, 9, 12, 46, 61, 62, 65, 76, 79, 91] d = fitz.open(PDF) p0 = d[0] print(f"page.rect {p0.rect} mediabox {p0.mediabox} rotation {p0.rotation}") print(f"即 {p0.rect.width / 72 * 25.4:.1f}×{p0.rect.height / 72 * 25.4:.1f} mm\n") print(f"{'页':>4} {'文字中心 x,y':>18} {'红章中心 x,y':>18} " f"{'Δx':>7} {'Δy':>7} {'章直径mm':>9}") for pno in PAGES: pg = d[pno - 1] hits = pg.search_for(COMPANY) # 红章:取红色像素连通范围(整页扫描件页会误判,这些页没有扫描件) pm = pg.get_pixmap(dpi=100) a = np.frombuffer(pm.samples, dtype=np.uint8).reshape(pm.height, pm.width, pm.n) r, g, b = a[..., 0].astype(int), a[..., 1].astype(int), a[..., 2].astype(int) red = (r > 110) & (r - g > 55) & (r - b > 55) ys, xs = np.nonzero(red) if not len(ys) or not hits: print(f"{pno:>4} 未找到(文字 {len(hits)} 处,红像素 {len(ys)})") continue sc = 72 / 100 cx = (xs.min() + xs.max()) / 2 * sc cy = (ys.min() + ys.max()) / 2 * sc dia = (xs.max() - xs.min() + 1) * sc / 72 * 25.4 # 文字命中可能多处,取与红章最近的 best = min(hits, key=lambda rc: abs((rc.y0 + rc.y1) / 2 - cy)) tx, ty = (best.x0 + best.x1) / 2, (best.y0 + best.y1) / 2 print(f"{pno:>4} {tx:8.1f},{ty:8.1f} {cx:8.1f},{cy:8.1f} " f"{cx - tx:+7.1f} {cy - ty:+7.1f} {dia:9.1f}") d.close()