const updatesContainer = document.getElementById("updates-container");
let updates = [];
let quotes = [];

let callback = (entries) => {
	entries.forEach((entry) => {
		entry.target.innerHTML = highlight(
			quotes[entry.target.getAttribute("data-quote")],
			entry.intersectionRatio
		);
	});
};

// Threshold Callback

let threshold = [];
for (let i = 0; i <= 1.0; i += 0.01) {
	threshold.push(i);
}

let observer = new IntersectionObserver(callback, {
	rootMargin: "100% 0% -25% 0%",
	threshold: threshold,
});

// Karaoke highlight

function highlight(text, offset) {
	let scrollCursor = text.length * offset;
	return (
		'<span class="highlight">' +
		text.slice(0, scrollCursor) +
		"</span>" +
		text.slice(scrollCursor)
	);
}

// Fetc the updates from the array in updates.json
// Each element of the array is structured like this:
//
// {
//     "date": "October the 21st, 2021",
//     "title": "2nd hand lifeboat script",
//     "text": "Labore eiusmod labore pariatur elit nostrud ut magna cupidatat minim amet deserunt cillum id. Lorem consectetur incididunt anim sit do eu minim nisi id.",
//     "quote": "Lorem elit magna esse reprehenderit fugiat labore est veniam ipsum labore est voluptate do."
//	   "media": {
//         "type": "video",
//         "src": "./assets/test-js.mp4",
//         "alt": "An excerpt from 'When did software gone wrong?' highlighted progressively as in karaoke",
//         "caption": "In every karaoke there are at least 2 voices: a text and a choir"
//     }
// }
//
// Title, Text, Quote and Media are not mandatory.
// If some are not present, the createUpdate function will skip them
//
// Note that the Date is required, but its format is up to the user
//
// All the media elements require an alt description.
// This is for accessibility. It's a really good practice to provide quality alt text
// and we must pay attention to this.

fetch("./updates.json")
	.then((response) => response.json())
	.then((data) => {
		updates = [...data.updates.reverse()];
		populateContents();
	});

function populateContents() {
	updates.forEach((update) => createUpdate(update));
}

function createUpdate(update) {
	let card = document.createElement("div");
	card.classList.add("update");

	// QUOTE

	if (update.quote) {
		let quote = document.createElement("blockquote");
		quote.innerHTML = update.quote;
		quote.setAttribute("data-quote", quotes.length);
		quotes.push(update.quote);
		card.appendChild(quote);
		observer.observe(quote);
	}

	// LOG
	let log = document.createElement("div");
	log.classList.add("log");

	// DATE
	let date = document.createElement("div");
	date.classList.add("date");
	date.innerHTML = update.date;
	log.appendChild(date);

	// TITLE, if present
	if (update.title) {
		let title = document.createElement("h3");
		title.classList.add("title");
		title.innerHTML = update.title;
		log.appendChild(title);
	}

	// MEDIA CONTENTS, if present
	if (update.media) {
		let media;
		// IMAGE
		if (update.media.type == "img") {
			media = document.createElement("media");
			media.classList.add("media");

			let img = document.createElement("img");
			img.src = update.media.src;
			img.alt = update.media.alt;
			media.appendChild(img);

			if (update.media.caption) {
				let caption = document.createElement("figcaption");
				caption.innerHTML = update.media.caption;
				media.appendChild(caption);
			}
		}
		// VIDEO
		if (update.media.type == "video") {
			media = document.createElement("div");
			media.classList.add("media");

			let video = document.createElement("video");
			video.src = update.media.src;
			video.alt = update.media.alt;
			video.setAttribute("autoplay", true);
			video.setAttribute("loop", true);
			media.appendChild(video);

			if (update.media.caption) {
				let caption = document.createElement("p");
				caption.classList.add("caption");
				caption.innerHTML = update.media.caption;
				media.appendChild(caption);
			}
		}
		log.appendChild(media);
	}

	// TEXT, if present
	if (update.text) {
		let text = document.createElement("p");
		text.classList.add("text");
		text.innerHTML = update.text;
		log.appendChild(text);
	}

	card.appendChild(log);
	updatesContainer.appendChild(card);
}
