tln devlog [2.56/3] – Setting up a Photologue image manager

This series of articles loosely documents design choices and implementation issues I met during the making of the tln website. I learnt a few lessons along my improvised 9-week schedule, and I thought I could share them with fellow first-timers. I guess some technical points might also be of interest to more experimented developers.

Indenting HTML properly

At the beginning of week 5, I felt idle and manic enough to try serving properly indented HTML code. Django tags are powerful tools for templates, but they often leave unsightly linebreaks and whitespaces all over. This seemed feasible by way of a middleware utility, which would be ran right before serving the code. Indentation logic was to be carried out by the Beautiful Soup library.

While this appeared to work at first, unfortunately Beautiful Soup puts inline elements on their own code lines, which can lead to unwanted behaviour at browser rendering, like always displaying a whitespace character between a link (inline <a> element) and a subsequent punctuation mark. Despite improvements, I could never completely fix it. So maybe don't waste your time like I did, and don't expect serving properly indented HTML code, at least with Django.

Customizing the Photologue image management application

After I'd had three days of rest (I played NaissanceE, which I found to be a mindblowing exploration game), I began working on the third section of the website, dedicated to displaying pictures. Photologue seemed like the most natural application to go to for managing images and galleries. The application would later enable me to embed pictures in blog articles.

Removing useless URLs and overriding default templates worked the same as with the Zinnia application. I extended the Gallery model to hold separate English and French descriptions; Django's development server backtracing made registering this custom model quite easy.

I wasn't sure yet about how I'd protect my pictures. Seeing as I'm no wealthy heiress (though one could say I'm decadent enough for the job), I might want to try selling some of them in the future, so I don't want other people making money off it. Then, I couldn't bear applying watermarks. I can't see the point of going discreet about them, and on the other side, I find noticeable watermarks to usually ruin my appreciation. I could also make a point out of believing that I'm no owner of my art; I mostly happened to witness and seize some collective transcendental good.

Anyway. I settled on displaying pictures with lesser resolution than the original ones, so that I should remain able to print better pictures than whatever one could get out of the website contents. On uploading an image, Photologue creates cached versions of different sizes. New image sizes can be defined from the admin panel. I added a 1920x1080 (maximum) resolution which allows for nice detailed displays inside most common desktop screens.

Displaying a photo gallery

Regarding the full-screen presentation of the pictures, for a while I thought about using Bootstrap Carousel, mostly because I wanted to get some Bootstrap experience. But this plugin didn't seem responsive enough, so I dropped the idea. Then I turned to slick, allegedly 'the last carousel you'll ever need'. Except, I spent several hours trying to make elementary features work, then I looked up slick's creator on Twitter and he seemed like a fresh-out-of-college 40-something obnoxious jerk, so I threw away a day's work and decided I'd start anew with FlexSlider on the next day.

As it happens, FlexSlider is great for displaying series of pictures, with smooth animation and seamless responsiveness. Plus, the team behind does not look morally reprehensible. Apparently, setting it up was so fast I barely mentioned it in my journal. My only regret here was that FlexSlider requires jQuery, which up this point I'd made a case not to use. Consider using jQuery as little as possible. Most tasks can be carried out from vanilla JS with few additional lines, and you'll probably be better handling fundamental functions rather than calling magical, unknowable wrappers.

The only issue I encountered was related to CSS box max-sizing dynamics. Indeed, setting a screen-agnostic, percentage maximum height to the picture required that the containing block height be explicitly set. However, the picture+caption container dimensions should also be regulated by a percentage maximum height. Eventually I set out to compute explicit dimensions with JavaScript at page load, and on window resize events. I can't say I find this satisfying, but it required little code and it has no visible impact on browser rendering performance.

A few days later, I wrote the descriptions for the two initial galleries, négatifs and silhouettes, starting with the French versions then loosely translating them to English. In truth, carefully finding the right words was a painstaking exercise which took me a whole day —there's a reason why I turned to pictures as a conduct for art in the first place. Nonetheless, I too often encountered art pieces which left me clueless, and I think my work asks for a patience which unfortunately eludes most Internet browsing, so giving minimal context seemed essential here.


In parallel, I was making several improvements to multiple parts of the website:

  • factoring the common parts of blog.css and photos.css into a global main.css;

  • writing a cross-application navigation menu to a global template;

  • designing a dropdown submenu for the photo galleries;

  • adding and editing initial blog articles;

  • enabling slug-only short article URLs —the simpler the URLs, the happier the users;

  • linking the movie screenings I attended to their related oeuvre page;

  • replacing the oeuvre identifier URLs with readable slugs, while avoiding homonyms;

  • and tirelessly fixing CSS details everywhere...