121 lines
3.8 KiB
Python
121 lines
3.8 KiB
Python
|
|
from pypdf import PdfReader, PdfWriter, PageObject
|
||
|
|
from pypdf.annotations import Link
|
||
|
|
from reportlab.pdfgen import canvas
|
||
|
|
from reportlab.lib.pagesizes import letter
|
||
|
|
from PIL import Image
|
||
|
|
import io
|
||
|
|
|
||
|
|
|
||
|
|
def image_to_page(image_path: str,
|
||
|
|
x_position: int, y_position: int,
|
||
|
|
desired_width: int, desired_height: int) -> PageObject:
|
||
|
|
image_pdf = io.BytesIO()
|
||
|
|
c = canvas.Canvas(image_pdf, pagesize=letter)
|
||
|
|
c.drawImage(image_path, x_position, y_position,
|
||
|
|
width=desired_width, height=desired_height)
|
||
|
|
c.save()
|
||
|
|
image_pdf.seek(0)
|
||
|
|
return PdfReader(image_pdf).pages[0]
|
||
|
|
|
||
|
|
|
||
|
|
class Stamp:
|
||
|
|
|
||
|
|
def __init__(self,
|
||
|
|
image_path: str,
|
||
|
|
x_position: int, y_position: int,
|
||
|
|
desired_width: int, desired_height: int) -> None:
|
||
|
|
self._image_page = image_to_page(
|
||
|
|
image_path, x_position, y_position, desired_width, desired_height)
|
||
|
|
self._bounding_box = (x_position, y_position, x_position +
|
||
|
|
desired_width - 1,
|
||
|
|
y_position + desired_height - 1)
|
||
|
|
|
||
|
|
def stamp(self, page: PageObject) -> None:
|
||
|
|
page.merge_page(self._image_page)
|
||
|
|
|
||
|
|
def add_link(self, writer: PdfWriter, i: int, j: int):
|
||
|
|
annotation = Link(rect=self._bounding_box, target_page_index=j)
|
||
|
|
writer.add_annotation(page_number=i, annotation=annotation)
|
||
|
|
|
||
|
|
|
||
|
|
def main() -> None:
|
||
|
|
|
||
|
|
writer = PdfWriter()
|
||
|
|
|
||
|
|
# Add a title page and "how to play"
|
||
|
|
writer.add_page(image_to_page("grayscale-1.png", 25, 25, 550, 990))
|
||
|
|
writer.add_page(
|
||
|
|
PdfReader("Fairy tale puzzle book interior PRINT_VERSION.pdf").pages[0])
|
||
|
|
|
||
|
|
# Next, add the stamps to all puzzle pages
|
||
|
|
reader = PdfReader("Fairy tale puzzle book interior PRINT_VERSION.pdf")
|
||
|
|
stamp = Stamp("link_text.png", 495, 15, 100, 50)
|
||
|
|
back_arrows = [
|
||
|
|
Stamp("back.png", 278, 388, 20, 20),
|
||
|
|
Stamp("back.png", 490, 388, 20, 20),
|
||
|
|
Stamp("back.png", 278, 124, 20, 20),
|
||
|
|
Stamp("back.png", 490, 124, 20, 20)
|
||
|
|
]
|
||
|
|
|
||
|
|
# Add pages and merge the image to the specified page
|
||
|
|
skips = [0, 1, 23]
|
||
|
|
for i, page in enumerate(reader.pages):
|
||
|
|
if i in skips:
|
||
|
|
continue
|
||
|
|
if i < 22:
|
||
|
|
stamp.stamp(page)
|
||
|
|
elif i > 22:
|
||
|
|
for a in back_arrows:
|
||
|
|
a.stamp(page)
|
||
|
|
writer.add_page(page)
|
||
|
|
|
||
|
|
# Add forward and back annotations
|
||
|
|
for i in range(2, 22):
|
||
|
|
stamp.add_link(writer, i, 23 + (i - 2) // 4)
|
||
|
|
for i in range(23, 28):
|
||
|
|
offset = 4 * (i - 23) + 2
|
||
|
|
for j in range(4):
|
||
|
|
back_arrows[j].add_link(writer, i, offset + j)
|
||
|
|
|
||
|
|
# Add bookmarks
|
||
|
|
writer.add_outline_item("Cover", 0)
|
||
|
|
writer.add_outline_item("How to play", 1)
|
||
|
|
parent = writer.add_outline_item("Puzzles", 2)
|
||
|
|
for i, n in enumerate([
|
||
|
|
"Cinderella",
|
||
|
|
"Snow white",
|
||
|
|
"The emperor's new clothes",
|
||
|
|
"The Bremen town musicians",
|
||
|
|
"Little red riding hood",
|
||
|
|
"The three little pigs",
|
||
|
|
"The princcess and the pea",
|
||
|
|
"The ugly duckling",
|
||
|
|
"The little mermaid",
|
||
|
|
"Rumplestiltskin",
|
||
|
|
"Sleeping beauty",
|
||
|
|
"Hansel and Gretel",
|
||
|
|
"Rapunzel",
|
||
|
|
"The magic pen",
|
||
|
|
"The talking animals",
|
||
|
|
"Goldilocks and the three bears",
|
||
|
|
"The gingerbread man",
|
||
|
|
"The tortoise and the hare",
|
||
|
|
"Jack and the beanstalk",
|
||
|
|
"The frog prince",
|
||
|
|
]):
|
||
|
|
writer.add_outline_item(n, i + 2, parent)
|
||
|
|
writer.add_outline_item("Solution", 22)
|
||
|
|
|
||
|
|
# Add copyright page
|
||
|
|
writer.add_page(PdfReader('copyright.pdf').pages[0])
|
||
|
|
writer.add_outline_item("Copyright", len(writer.pages) - 1)
|
||
|
|
|
||
|
|
# Write the output
|
||
|
|
with open("Fairy tale puzzle book interior.pdf", "wb") as output_file:
|
||
|
|
writer.write(output_file)
|
||
|
|
print("DONE")
|
||
|
|
|
||
|
|
|
||
|
|
if __name__ == '__main__':
|
||
|
|
main()
|