Files
kjvstudy.org/kjvstudy_org/templates/study_guide_detail.html
T
kennethreitz 8546e58713 Add TOC to study guides and new Spirits & Demons guide
- Add table of contents navigation to study guide detail pages
- New study guide covering biblical teaching on demons and spiritual warfare:
  - The Reality of Evil Spirits
  - Satan: The Adversary
  - Demon Possession in the Gospels (Legion, etc.)
  - Christ's Victory Over Demons
  - Spiritual Warfare
  - Testing the Spirits
  - Demons' Final Doom

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-25 22:41:10 -05:00

174 lines
6.3 KiB
HTML

{% extends "base.html" %}
{% block title %}{{ guide.title }} - Bible Study Guide - KJV Bible{% endblock %}
{% block og_type %}article{% endblock %}
{% block og_title %}{{ guide.title }} - Bible Study Guide{% endblock %}
{% block og_description %}{{ guide.description }}{% endblock %}
{% block structured_data %}
<script type="application/ld+json">
{
"@context": "https://schema.org",
"@type": "Article",
"headline": {{ guide.title | tojson }},
"description": {{ guide.description | tojson }},
"author": {
"@type": "Organization",
"name": "KJV Study"
},
"publisher": {
"@type": "Organization",
"name": "KJV Study",
"url": "https://kjvstudy.org"
},
"mainEntityOfPage": {
"@type": "WebPage",
"@id": "https://kjvstudy.org{{ request.url.path }}"
},
"about": {
"@type": "Thing",
"name": "Bible Study"
}
}
</script>
{% endblock %}
{% block head %}
<script>
document.addEventListener('DOMContentLoaded', function() {
// Function to link verse references in text
function linkVerseReferences(element) {
if (!element) return;
// Get all text nodes
const walker = document.createTreeWalker(element, NodeFilter.SHOW_TEXT, null, false);
const textNodes = [];
let node;
while (node = walker.nextNode()) {
textNodes.push(node);
}
textNodes.forEach(function(textNode) {
let text = textNode.textContent;
let changed = false;
// First, handle comma-separated verse lists like "Psalms 7:17, 9:2, 18:13"
// Pattern: Book chapter:verse, chapter:verse, chapter:verse...
text = text.replace(/\b(\d?\s?[A-Z][a-z]+(?:\s+[A-Z][a-z]+)?)\s+((?:\d+:\d+(?:-\d+)?(?:\s*,\s*)?)+)/g, function(match, book, verseList) {
book = book.trim();
// Check if this is actually a comma-separated list
if (!verseList.includes(',')) {
// Single verse, will be handled by the next regex
return match;
}
changed = true;
// Split by comma and process each verse reference
var verses = verseList.split(/\s*,\s*/);
var links = verses.map(function(verseRef) {
verseRef = verseRef.trim();
var parts = verseRef.match(/^(\d+):(\d+)(?:-(\d+))?$/);
if (parts) {
var chapter = parts[1];
var verseStart = parts[2];
var verseEnd = parts[3];
if (verseEnd) {
return '<a href="/book/' + book + '/chapter/' + chapter + '#verse-' + verseStart + '-' + verseEnd + '">' + book + ' ' + chapter + ':' + verseStart + '-' + verseEnd + '</a>';
} else {
return '<a href="/book/' + book + '/chapter/' + chapter + '/verse/' + verseStart + '">' + book + ' ' + chapter + ':' + verseStart + '</a>';
}
}
return verseRef;
});
return links.join(', ');
});
// Then handle individual verse references like "John 3:16" or "Romans 8:28-29"
// This regex handles book names with optional numbers and spaces
text = text.replace(/\b(\d?\s?[A-Z][a-z]+(?:\s+[A-Z][a-z]+)?)\s+(\d+):(\d+)(?:-(\d+))?\b/g, function(match, book, chapter, verseStart, verseEnd) {
changed = true;
book = book.trim();
if (verseEnd) {
return '<a href="/book/' + book + '/chapter/' + chapter + '#verse-' + verseStart + '-' + verseEnd + '">' + match + '</a>';
} else {
return '<a href="/book/' + book + '/chapter/' + chapter + '/verse/' + verseStart + '">' + match + '</a>';
}
});
// Handle chapter-only references like "Psalm 2" or "Genesis 1"
// Must come after verse references to avoid double-matching
text = text.replace(/\b(Psalm|Genesis|Exodus|Isaiah|Daniel|Revelation|Matthew|Mark|Luke|John|Romans|Hebrews|Proverbs|Ecclesiastes|Job)\s+(\d+)\b(?!:)/g, function(match, book, chapter) {
changed = true;
return '<a href="/book/' + book + '/chapter/' + chapter + '">' + match + '</a>';
});
if (changed) {
const span = document.createElement('span');
span.innerHTML = text;
textNode.parentNode.replaceChild(span, textNode);
// Replace the span's children with its contents
while (span.firstChild) {
span.parentNode.insertBefore(span.firstChild, span);
}
span.parentNode.removeChild(span);
}
});
}
// Link verse references in all section content paragraphs
document.querySelectorAll('section p').forEach(function(paragraph) {
// Skip paragraphs that are just margin toggle labels
if (!paragraph.querySelector('.margin-toggle')) {
linkVerseReferences(paragraph);
}
});
});
</script>
{% endblock %}
{% block content %}
<h1>{{ guide.title }}</h1>
<p class="subtitle">{{ guide.description }}</p>
<nav class="toc">
<h2>Contents</h2>
<ul>
{% for section in guide.sections %}
<li><a href="#section-{{ loop.index }}">{{ section.title }}</a></li>
{% endfor %}
</ul>
</nav>
{% for section in guide.sections %}
{% set section_index = loop.index %}
<section id="section-{{ section_index }}">
<h2>{{ section.title }}</h2>
{% for verse_data in section.verse_texts %}
<p>
<label for="mn-s{{ section_index }}-v{{ loop.index }}" class="margin-toggle"></label>
<input type="checkbox" id="mn-s{{ section_index }}-v{{ loop.index }}" class="margin-toggle"/>
<span class="marginnote">
<strong><a href="{{ verse_data.url }}">{{ verse_data.reference }}</a></strong><br/>
<em>{{ verse_data.text }}</em>
</span>
</p>
{% endfor %}
<p>{{ section.content | format_lists | safe }}</p>
</section>
{% endfor %}
<nav>
<p>
<a href="/study-guides">← Study Guides</a> |
<a href="/">Home</a>
</p>
</nav>
{% endblock %}