It’s officially Day 85, and I’ve transitioned from the terminal back into the world of graphical interfaces. What started as a "simple" assignment to build a functional clone of a tool like Watermarkly quickly spiraled into a deep dive into Abstract Base Classes and complex coordinate mapping.
Building on the architectural lessons of the past few weeks, I wanted to see how far I could push ttkbootstrap. It’s a library that transforms the often-dated look of Tkinter into a professional, modern workspace. It turns out that with the right mix of dual 320px sidebars and high-DPI scaling, you can make a desktop app feel less like a hobby project and more like a production-ready suite.
Then there’s the "brain" of the operation: the Layering Engine. I decided to treat every watermark as an independent object rather than just drawing pixels onto a canvas. It provided an incredibly elegant way to handle state. By using abstraction, I created a system where the main interface doesn't need to know if it's handling a logo or a string of text; it just tells the "Layer" to render itself.
The project wasn't without its "teeth-grinding" hurdles. I insisted on a professional Drag and Drop experience, which led me into the world of pywindnd. I spent hours in a "refactor loop," relocating code and debugging Circular Imports that triggered as the app's complexity exploded. It sent me down a rabbit hole of dynamic resource pathing and _MEIPASS logic to ensure that the app ran smoothly.
I also took the opportunity to streamline the Tiling Logic. By integrating a custom coordinate calculator, I managed to offload the heavy lifting of placement. It handles the "padding" and "margin" math—ensuring text watermarks don't sit flush against the edge—in a fraction of the code I would have written with manual loops.
Right now, the app is a polished Windows-only experience with a robust history stack. I’m already looking toward the next revision: a Batch Processing engine. The goal is to build a system that doesn't just watermark one image, but processes an entire directory with a single click.