| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173 |
- module.exports = function(eleventyConfig) {
- const fs = require('fs');
- const path = require('path');
- const exifParser = require("exif-parser");
- // add my css file from the root folder
- eleventyConfig.addPassthroughCopy("bundle.css");
- eleventyConfig.addPassthroughCopy("img");
- eleventyConfig.addPassthroughCopy({ "_data/images": "photos" });
- // This line was to make sure my post.md weren't processed as Liquid,
- // permitting this post here
- eleventyConfig.setTemplateFormats(["md", "njk", "html"]);
- eleventyConfig.addGlobalData("site.author", "unakt");
- // Double with the .eleventyignore file, but just in case
- eleventyConfig.ignores.add("/_drafts/**");
- eleventyConfig.ignores.add("/README.md");
- eleventyConfig.addLayoutAlias("post", "post.njk");
- eleventyConfig.addCollection("postlist", function(collectionApi) {
- return collectionApi.getFilteredByGlob("./posts/*.md");
- });
- // Custom collection for mini images
- // It scans the ./src/_data/images/ folder for jpg files
- // and groups them by their parent folder name
- // Each image object contains its path, album name, and last modified date
- // ========================================================
- eleventyConfig.addCollection("miniImages", function(collectionApi) {
- const files = [];
- const baseDir = "./_data/images/";
- // Recursive function to find all images
- const getFiles = (dir) => {
- if (!fs.existsSync(dir)) return; // Safety check
- fs.readdirSync(dir).forEach(file => {
- const fullPath = path.join(dir, file);
- if (fs.statSync(fullPath).isDirectory()) {
- getFiles(fullPath);
- } else if (file.endsWith(".jpg") ||
- file.endsWith(".jpeg") ||
- file.endsWith(".png") ||
- file.endsWith(".gif") ||
- file.endsWith(".webp")) {
- // .jpg an others extensions might be case sensitive on some systems !!
-
- // READ EXIF DATA
- let exifDate = null;
- try {
- const buffer = fs.readFileSync(fullPath);
- const parser = exifParser.create(buffer);
- const result = parser.parse();
-
- // Grab Exif Date of photo taken (if exists)
- if (result.tags.DateTimeOriginal) {
- exifDate = new Date(result.tags.DateTimeOriginal * 1000);
- }
-
- exifData = {
- model: result.tags.Model || "Unknown",
- lens: result.tags.LensModel || "Unknown",
- focalLength: result.tags.FocalLength ? `${result.tags.FocalLength}` : "N/A",
- fNumber: result.tags.FNumber ? `f/${result.tags.FNumber}` : "N/A",
- exposure: result.tags.ExposureTime ? `1/${Math.round(1/result.tags.ExposureTime)}s` : "N/A",
- iso: result.tags.ISO || "N/A"
- };
- } catch (e) {
- console.error(`Skipping ${file}: No valid EXIF date found.`);
- }
- // END READ EXIF DATA
- // BEFORE =============
- const relativePath = path.relative("./_data/images", fullPath).replace(/\\/g, "/");
- //const pathParts = relativePath.split(path.sep).slice(0, -1); // Make Breadcrumb
- // ====================
- // Only add real photos with EXIF date
- if (exifDate) {
- files.push({
- fullPath: fullPath, // We need this for the calculation below
- //webPath: fullPath.replace("src/", "/"),
- date: exifDate,
- path: "/photos/" + relativePath,
- folderPath: path.relative(baseDir, path.dirname(fullPath)),
- exif: exifData,
- });
- }
- }
- });
- };
- getFiles(baseDir);
-
- // Group them by album name
- const grouped = {};
- // This here ? or just before return grouped ?
- files.sort((a, b) => a.date - b.date);
- files.forEach(f => {
- const relFolder = path.relative(baseDir, path.dirname(f.fullPath));
- if (!grouped[relFolder]) {
- grouped[relFolder] = {
- images: [],
- subfolders: [],
- breadcrumbArray: relFolder === "" ? [] : relFolder.split(path.sep)
- //path: folderPath.split(path.sep) // Normalize to forward slashes
- };
- }
- grouped[relFolder].images.push(f);
- });
- // Second pass to link parents to children subfolders
- for (const parentPath in grouped) {
- for (const potentialChild in grouped) {
- const parentParts = parentPath === "" ? [] : parentPath.split(path.sep);
- const childParts = potentialChild.split(path.sep);
- // Is the child exactly one level deeper than the parent?
- if (potentialChild.startsWith(parentPath) &&
- childParts.length === parentParts.length + 1 &&
- parentPath !== potentialChild) {
- grouped[parentPath].subfolders.push(potentialChild);
- }
- }
- }
- return grouped;
- });
- // ========================================================
- eleventyConfig.addCollection("allPhotos", function(collectionApi) {
- //const grouped = collectionApi.getFilteredByTag("miniImages"); // This won't work since miniImages isn't a tag
- // Instead, use the logic we already built:
- const miniImages = collectionApi.getAll()[0].data.collections.miniImages;
-
- return Object.values(miniImages).flatMap(album => album.images);
- });
- // Date filter to format dates as YYYY-MM-DD
- //eleventyConfig.addFilter("date", function(dateObj, format = "YYYY-MM-DD") {
- // const d = new Date(dateObj);
- // return d.toISOString().split('T')[0]; // Returns YYYY-MM-DD
- // });
- //eleventyConfig.addFilter("date", function(dateObj) {
- // const d = new Date(dateObj);
- //
- // Check if the date is actually valid
- // if (isNaN(d.getTime())) {
- // console.warn("Skipping invalid date for a file. Value received:", dateObj);
- // return "Date Unknown";
- // }
- // return d.toISOString().split('T')[0];
- //});
- return {
- // Ok idk this prevent markdown from being processed?
- markdownTemplateEngine: false,
- dir: {
- input: "./",
- output: "_site",
- layouts: "layouts",
- includes: "includes"
- }
- };
- };
|