self.bottom_cm = bottom_cm
self.right_cm = right_cm
self.top_cm = top_cm
+ self._calc_measures()
+
+ def _calc_measures(self) -> None:
self.left = float(self.left_cm) * POINTS_PER_CM
self.bottom = float(self.bottom_cm) * POINTS_PER_CM
self.right = float(self.right_cm) * POINTS_PER_CM
"What's left of A4_WIDTH after applying height croppings."
return A4_HEIGHT - self.bottom - self.top
- def make_mirror(
- self
- ) -> 'PageCrop':
- 'Return PageCrop of swapped .left and .right.'
- return PageCrop(left_cm=self.right_cm,
- bottom_cm=self.bottom_cm,
- right_cm=self.left_cm,
- top_cm=self.top_cm)
+ def add(
+ self,
+ to_add: Self,
+ mirror=False
+ ) -> None:
+ 'Add other crop to own measures, mirror left and right if demanded.'
+ self.left_cm += to_add.right_cm if mirror else to_add.left_cm
+ self.bottom_cm += to_add.bottom_cm
+ self.right_cm += to_add.left_cm if mirror else to_add.right_cm
+ self.top_cm += to_add.top_cm
+ self._calc_measures()
class Nup4Geometry:
max_y = max(page.box['top'] for page in pages)
zooms = (A4_WIDTH / max_x, A4_HEIGHT / max_y)
offsets = {'tx': 0.0, 'ty': 0.0}
- if zooms[0] < zooms[1]:
+ zoom_by_x = zooms[0] < zooms[1]
+ if zoom_by_x:
zoom = zooms[0]
offsets['ty'] = (A4_HEIGHT - max_y * zoom) / 2
else:
zoom = zooms[1]
offsets['tx'] = (A4_WIDTH - max_x * zoom) / 2
+ zoom_offset = 0.01 + offsets['tx'] / POINTS_PER_CM
+ zoom_crop = PageCrop(
+ left_cm=0 if zoom_by_x else zoom_offset,
+ right_cm=0 if zoom_by_x else zoom_offset,
+ bottom_cm=zoom_offset if zoom_by_x else 0,
+ top_cm=zoom_offset if zoom_by_x else 0)
for page in pages:
page.scale(zoom)
page.translate(**offsets)
if (rotation := page.rotation()):
page.rotate(360 - rotation)
page.set_box(0, 0, A4_HEIGHT, A4_WIDTH)
+ page.crop.add(zoom_crop)
def collect_page_croppings(
print(f'{prefix}: to pages {idx_start + 1}:{idx_after} '
f'applying crop: {page_crop.format_in_cm}{suffix}')
for idx in range(idx_start, idx_after):
- pages[idx].crop = (page_crop.make_mirror()
- if (args_symmetry and idx % 2)
- else page_crop)
+ pages[idx].crop.add(page_crop, args_symmetry and idx % 2)
elif args_keep_mediabox:
for page in pages:
- page.crop = PageCrop(
- page.box['left'] / POINTS_PER_CM,
- page.box['bottom'] / POINTS_PER_CM,
- (0.01 + A4_WIDTH - page.box['right']) / POINTS_PER_CM,
- (0.01 + A4_HEIGHT - page.box['top']) / POINTS_PER_CM)
- if args_symmetry and not idx % 2:
- page.crop = page.crop.make_mirror()
+ page.crop.add(
+ PageCrop(
+ page.box['left'] / POINTS_PER_CM,
+ page.box['bottom'] / POINTS_PER_CM,
+ (0.01 + A4_WIDTH - page.box['right']) / POINTS_PER_CM,
+ (0.01 + A4_HEIGHT - page.box['top']) / POINTS_PER_CM),
+ args_symmetry and not idx % 2)
def build_single_pages_output(