I have built a website based on the Jekyll code for the website for Apache Buildr. The Buildr website automatically generates a table of contents for each page based on the headers in the textile
format files.
For example, you write a page using textile marking out the headings like so . .
h2(#why). Why are we doing this?
BLah blah balh etc ..
h2(#something). Some other header
BLah blah balh etc ..
Then in the default HTML you have some code that pipes the content into something called toc
and then you put the contents afterward. For example ...
<div id='content'>
<h1 id='{{ page.title | downcase | replace(' ', '_') }}'>{{ page.title }}</h1>
{{ content | toc }}
{{ content }}
</div>
On the Apache site they get the desired results (the toc is shown followed by the contents). However, on my site, the contents are rendered twice. No table of contents is generated.
Furthermore, if I clone the Apache Buildr project directly from github and run jekyll --server
in the doc
folder of that project, then no table of contents is generated either.
What am I missing?
I emailed the Buildr developer mailing list and someone told me to look here for inspiration. Turns out that the relevant code snippet is ...
module TocFilter
def toc(input)
output = "<ol class=\"toc\">"
input.scan(/<(h2)(?:>|\s+(.*?)>)([^<]*)<\/\1\s*>/mi).each do |entry|
id = (entry[1][/^id=(['"])(.*)\1$/, 2] rescue nil)
title = entry[2].gsub(/<(\w*).*?>(.*?)<\/\1\s*>/m, '\2').strip
if id
output << %{<li><a href="##{id}">#{title}</a></li>}
else
output << %{<li>#{title}</li>}
end
end
output << '</ol>'
output
end
end
Liquid::Template.register_filter(TocFilter)
Make a folder in the source folder of your site called _plugins
and then paste this code into a file called TocFilter.rb
within that folder.
It works!!
Where is toc defined? It isn't listed as one of the standard liquid filters or jekyll extensions, so likely you are missing a plugin.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With