Giter Club home page Giter Club logo

jekyll-toc's Introduction

jekyll-toc

CI Gem Version Code Climate Test Coverage

Table of Contents

Installation

Add jekyll-toc plugin in your site's Gemfile, and run bundle install.

gem 'jekyll-toc'

Add jekyll-toc to the gems: section in your site's _config.yml.

plugins:
  - jekyll-toc

Set toc: true in posts for which you want the TOC to appear.

---
layout: post
title: "Welcome to Jekyll!"
toc: true
---

Usage

There are three Liquid filters, which can be applied to HTML content, e.g. the Liquid variable content available in Jekyll's templates.

Basic Usage

toc filter

Add the toc filter to your site's {{ content }} (e.g. _layouts/post.html).

{{ content | toc }}

This filter places the TOC directly above the content.

Advanced Usage

If you'd like separated TOC and content, you can use {% toc %} tag (or toc_only filter) and inject_anchors filter.

{% toc %} tag / toc_only filter

Generates the TOC itself as described below. Mostly useful in cases where the TOC should not be placed immediately above the content but at some other place of the page, i.e. an aside.

<div>
  <div id="table-of-contents">
    {% toc %}
  </div>
  <div id="markdown-content">
    {{ content }}
  </div>
</div>

⚠️ {% toc %} Tag Limitation

{% toc %} works only for Jekyll Posts and Jekyll Collections. If you'd like to use {% toc %} except posts or collections, please use toc_only filter as described below.

<div>
  <div id="table-of-contents">
    {{ content | toc_only }}
  </div>
  <div id="markdown-content">
    {{ content | inject_anchors }}
  </div>
</div>

inject_anchors filter

Injects HTML anchors into the content without actually outputting the TOC itself. They are of the form:

<a class="anchor" href="#heading1-1" aria-hidden="true">
  <span class="octicon octicon-link"></span>
</a>

This is only useful when the TOC itself should be placed at some other location with the toc_only filter.

Generated HTML

jekyll-toc generates an unordered list by default. The HTML output is as follows.

<ul id="toc" class="section-nav">
  <li class="toc-entry toc-h1"><a href="#heading1">Heading.1</a>
    <ul>
      <li class="toc-entry toc-h2"><a href="#heading1-1">Heading.1-1</a></li>
      <li class="toc-entry toc-h2"><a href="#heading1-2">Heading.1-2</a></li>
    </ul>
  </li>
  <li class="toc-entry toc-h1"><a href="#heading2">Heading.2</a>
    <ul>
      <li class="toc-entry toc-h2"><a href="#heading2-1">Heading.2-1</a>
        <ul>
          <li class="toc-entry toc-h3"><a href="#heading2-1-1">Heading.2-1-1</a></li>
          <li class="toc-entry toc-h3"><a href="#heading2-1-2">Heading.2-1-2</a></li>
        </ul>
      </li>
      <li class="toc-entry toc-h2"><a href="#heading2-2">Heading.2-2</a></li>
    </ul>
  </li>
</ul>

screenshot

Customization

jekyll-toc is customizable on _config.yml.

Default Configuration

# _config.yml
toc:
  min_level: 1
  max_level: 6
  ordered_list: false
  no_toc_section_class: no_toc_section
  list_id: toc
  list_class: section-nav
  sublist_class: ''
  item_class: toc-entry
  item_prefix: toc-

TOC levels

# _config.yml
toc:
  min_level: 2 # default: 1
  max_level: 5 # default: 6

The default heading range is from <h1> to <h6>.

Enable TOC by default

You can enable TOC by default with Front Matter Defaults:

# _config.yml
defaults:
  - scope:
      path: ""
    values:
      toc: true

Skip TOC

The heading is ignored in the toc by adding no_toc class.

<h1>h1</h1>
<h1 class="no_toc">This heading is ignored in the TOC</h1>
<h2>h2</h2>

Skip TOC Sectionally

The headings are ignored inside the element which has no_toc_section class.

<h1>h1</h1>
<div class="no_toc_section">
  <h2>This heading is ignored in the TOC</h2>
  <h3>This heading is ignored in the TOC</h3>
</div>
<h4>h4</h4>

Which would result in only the <h1> & <h4> within the example being included in the TOC.

The class can be configured on _config.yml:

# _config.yml
toc:
  no_toc_section_class: exclude # default: no_toc_section

Configuring multiple classes are allowed:

# _config.yml
toc:
  no_toc_section_class:
    - no_toc_section
    - exclude
    - your_custom_skip_class_name

CSS Styling

The toc can be modified with CSS. The sample CSS is the following.

.section-nav {
  background-color: #fff;
  margin: 5px 0;
  padding: 10px 30px;
  border: 1px solid #e8e8e8;
  border-radius: 3px;
}

screenshot

Each TOC li entry has two CSS classes for further styling. The general toc-entry is applied to all li elements in the ul.section-nav.

Depending on the heading level each specific entry refers to, it has a second CSS class toc-XX, where XX is the HTML heading tag name. For example, the TOC entry linking to a heading <h1>...</h1> (a single # in Markdown) will get the CSS class toc-h1.

Custom CSS Class and ID

You can apply custom CSS classes to the generated <ul> and <li> tags.

# _config.yml
toc:
  list_id: my-toc-id # Default: "toc"
  list_class: my-list-class # Default: "section-nav"
  sublist_class: my-sublist-class # Default: no class for sublists
  item_class: my-item-class # Default: "toc-entry"
  item_prefix: item- # Default: "toc-":

Using Unordered/Ordered lists

By default the table of contents will be generated as an unordered list via <ul></ul> tags. This can be configured to use ordered lists instead <ol></ol>. This can be configured in _config.yml:

# _config.yml
toc:
  ordered_list: true # default is false

In order to change the list type, use the list-style-type css property. Add a class to the sublist_class configuration to append it to the ol tags so that you can add the list-style-type property.

Example

# _config.yml
toc:
  ordered_list: true
  list_class: my-list-class
  sublist_class: my-sublist-class
.my-list-class {
  list-style-type: upper-alpha;
}

.my-sublist-class: {
  list-style-type: lower-alpha;
}

This will produce:

screenshot

Alternative Tools

jekyll-toc's People

Contributors

antgel avatar chalin avatar defusion avatar dependabot[bot] avatar endrift avatar jfredrickson avatar kitlawes avatar mtasaka avatar torbjoernk avatar toshimaru avatar voxik avatar xhmikosr avatar zsyed91 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar

jekyll-toc's Issues

New {% toc %} tag only available in posts and collections

Hello,
The new tag scheme disturbs the layout of my site since I have TOC content in asides for contents other that posts and collections in my sites. Could you please advise me some workaround for this? Apart from this, thanks for jekyll-toc, Toshimaru, this is a very handy addition!
Frédéric Salard-Deschandol, from Nice, France

inject_anchors customization feature

I think it would be great to give user an opportunity to customize injected anchors, for example by adding toc-injected-anchors.html template to _includes directory, the content of which will override default string.

Allow specifying headers to ignore

In our use case we never want the following to be included in the TOC:

<h2>foo</h2>

<h3>bar</h3>

<div class="bd-example">
  <p>text</p>
  <h4>header</h4> <!-- we need to ignore this -->
</div>

<h3>bar</h3>

No more id attribute in all <a > tags

Updating from jekyll-toc 0.4.0 to 13.1.0, I found the following issue: id attribute missing in all <a> tags inside <h> tags
generated by 0.4.0
<h2><a id="historique-du-site-depuis-1970" class="anchor" href="#historique-du-site-depuis-1970" aria-hidden="true"><span class="octicon octicon-link"></span></a>Historique du site depuis 1970</h2>

generated by 13.1.0
<h2><a class="anchor" href="#historique-du-site-depuis-1970" aria-hidden="true"><span class="octicon octicon-link"></span></a>Historique du site depuis 1970</h2>

How to solve this issue ?

`ignore_within` doesn't seem to work

Hi.

So I tried the new version with our Bootstrap docs with version 0.7.1 and it doesn't seem to work...

toc:
  ignore_within:    ".bd-example"
  min_level:        2
  max_level:        4
<div class="bd-example">
<div class="alert alert-success" role="alert">
  <h4 class="alert-heading">Well done!</h4>
  <p>Aww yeah, you successfully read this important alert message. This example text is going to run a bit longer so that you can see how spacing within an alert works with this kind of content.</p>
  <hr>
  <p class="mb-0">Whenever you need to, be sure to use margin utilities to keep things nice and tidy.</p>
</div>
</div>

I also tried bd-example which doesn't seem to work either. I'm still getting Well done! in ToC.

PR: twbs/bootstrap#27417
Live preview: https://deploy-preview-27417--twbs-bootstrap4.netlify.com/docs/4.1/components/alerts/

Allow specifying custom class names

It would be great if one could set custom class names to replace section-nav & toc-entry, as well as a custom prefix to replace toc-h. This would allow integrating it into existing sites easily, re-using existing CSS classes.

I'm thinking something like the following set in the _config.yml:

toc:
  list_class: list
  item_class: item
  item_prefix: level_

Resulting in:

<ul class="list">
  <li class="item level_1"><a href="#heading1">Heading.1</a></li>
  <li class="item level_2"><a href="#heading2-1">Heading.2-1</a></li>
</ul>

I'm happy to submit a pull request if this is within scope.

<ul> elements are empty for nested toc entries

Using v0.3.0, I'm trying to generate a toc from h2 and h3 entries. When I try, I get an empty <ul> element in the place where the h3 entries should be found. For example:

<ul class="section-nav nav" style="opacity: 1;">
  <li class="toc-entry toc-h2"><a href="#what-are-structural-directives">What are structural directives?</a></li>
  <li class="toc-entry toc-h2"><a href="#ngif-case-study">NgIf case study</a>
    <ul>

    </ul>
  </li>
...

Notice the empty nested <ul>. My CSS is like this:

.toc-entry.toc-h2,
.toc-entry.toc-h3 {}
.toc-entry.toc-h1,
.toc-entry.toc-h4,
.toc-entry.toc-h5,
.toc-entry.toc-h6,
.no_toc {
 display: none;
}

cc @kwalrath

`inject-anchors` injects invalid HTML

imject-anchors is injectiong invalid html with duplicate IDs.
the code heading one generates

<h1 id="header-one"><a id="header-one" class="anchor" href="#header-one" aria-hidden="true"><span class="octicon octicon-link"></span></a>Header one</h1>

and that is invalid HTML as it contains duplicate IDs. This is poor practice and may cause errors in some browsers.

Configuration based on minimum number of items to show ToC

Thinking it might be useful to set a config (likely managed at _config.yml) around only outputting the ToC when there are two or more items that would be output. It seems the best way to manage that today is disabling the ToC on those specific pages and enabling it once ya have more headers used.

Does not work with GitHub Pages

When I develop locally with bundle exec jekyll serve, everything works like it should. When I push my changes to GitHub, however, there's no TOC in my posts.

Missing URL-Encoding of ids or anchor elements

I have in my TOC the German word "Datenschutzerklärung" (engl. Privacy) with an ä inside.

When I create the TOC the href or the anchor are getting #datenschutzerkl%C3%A4rung

<a class="anchor" href="#datenschutzerkl%C3%A4rung" aria-hidden="true"><span class="octicon octicon-link"></span></a>

In the url bar of my browser I see https://example.com/#datenschutzerklärung.

To harmonize the results and be secure for other special chars, I would suggest to use url_encode for the ID-Element and the Anchor-Link.

Rubocop should ignore the package folders

Current:

AllCops:
  TargetRubyVersion: 2.4
  Exclude:
    - "*.gemspec"
    - "gemfiles/*"
    - Rakefile
    - Gemfile

Should be:

AllCops:
  TargetRubyVersion: 2.4
  Exclude:
    - "*.gemspec"
    - "gemfiles/*"
    - gems/**/*
    - node_modules/**/*
    - vendor/bundle/**/*
    - Rakefile
    - Gemfile

Feature Request: allow filters on toc tag

{% toc %} currently only renders the TOC based off of the {{ content }} var. I've run into scenarios where I needed to template in additional headings and metadata-generated content before or after the content as boilerplate HTML, that would still be nice to have in a table of contents. I'm supposing it might look like:

{%- capture key_concepts_heading -%}<h2>Key Concepts</h2>{% endcapture -%}
{%- capture license_heading -%}<h2>License</h2>{% endcapture -%}

{% toc | prepend: key_concepts_heading | append: license_heading %}

...
{{ key_concepts_heading }}
{{ page.key_concepts }}
{{ content }}
{{ license_heading }}
{{ page.license }}

place toc perticuler position in a post

Hi

I am new to Jekyll blogging, I don't wat add toc on top of the page, instead of after some line of text in a post I want to add toc, could you please let me know how to do this?

Option to move id to injected anchor

So I'm trying to fix an issue where sticky headers overlap/cover headings when navigating using the ToC.
Would an option, when using the inject_anchors option, to move the id from the containing header into the injected anchor be possible?

Breaks kramdown footnotes

For some reason, when the toc was included, the footnote anchor links were not working on any browser.

Renders content twice

When clicking a header, sometimes it would render the content of the post a second time.

Using `toc_only` and `inject_anchors` Filters

Hi;

The plugin is working pretty fine in the basic mode, but I couldn't make it work in the advanced mode using toc_only and inject_anchors filters. I probably have missed something. Could you please guide me how to use it in a custom location in a layout/page?

Thanks in advance.

Vahid

Customize automatically generated TOC on jekyll

In _config.yml I have the following setting that ensures that only h2 elements show up in the automatically generated table of contents.
toc:
min_level: 2 # default: 1
max_level: 2 # default: 6

This works fine, but on some pages, I would like to include h3 elements in the toc as well. So I want to change the max_level to 3 in a particular case. Is this possible? I want to change max_level value dynamically from the template code. Please help

TOC on GitHub Pages

The plugin works fine locally, but when I push the website to the GitHub pages, it doesn't work there. Is there any way to make it work on GitHub beside producing a static version of the website in gh-pages branch and pushing that to the GitHub?

Thanks a lot. :-)

Cheers,
Vahid

Invalid HTML

Hey, there.

So, in Bootstrap v4-dev we switched to your plugin.

I notice that the generated HTML is invalid.

See for example https://github.com/twbs/bootstrap/blob/v4-dev/docs/4.0/about/brand.md

The HTML we get is the following, which is invalid:

            <ul class="section-nav">
<ul>
<li class="toc-entry toc-h2"><a href="#contents">Contents</a></li>
<li class="toc-entry toc-h2"><a href="#mark-and-logo">Mark and logo</a></li>
</ul>
<li class="toc-entry toc-h1"><a href="#bootstrap">Bootstrap</a></li>
<li class="toc-entry toc-h1"><a href="#bootstrap-1">Bootstrap</a>
<ul>
<li class="toc-entry toc-h2"><a href="#download-mark">Download mark</a></li>
<li class="toc-entry toc-h2"><a href="#name">Name</a>
<ul>
<li class="toc-entry toc-h3"><a href="#bootstrap-2">Bootstrap</a></li>
<li class="toc-entry toc-h3"><a href="#bootstrap-3">BootStrap</a></li>
<li class="toc-entry toc-h3"><a href="#twitter-bootstrap">Twitter Bootstrap</a></li>
</ul>
</li>
<li class="toc-entry toc-h2"><a href="#colors">Colors</a></li>
</ul>
</li>
</ul>

/CC @mdo @Johann-S

How to enable by default for all pages

Hi! Thanks for the plugin! How is it possible to enable this by default for all pages? Here's a PR where I'm trying to enable this for some pages https://github.com/home-assistant/home-assistant.io/pull/13572/files.

In short:

  1. I'm using {% toc %} since this is applied in an aside.
  2. The pages I'm trying to enable this are defined as collections .
  3. toc: true is defined in the _config.yaml defaults .

Still, the ToC doesn't appear. If I set it explicitly in a page's frontmatter, it works, but I want to avoid that though since there are 1000+ pages this should be applied to.

Any help would be appreciated, thanks!

Can't make it install

When using your step-by-step guide and then try to use the plugin, nothing happens.

I'm not sure if it's the install there never do anything or if it the plugin there is outdated or even if it because I try to use it on a page instead of post.

When I install it nothing happens in the files, is this right? only see a lot of things happens in the Terminal

Followed instructions and toc does not render

I did the walkthrough according to the README

Here is the site: https://joelouthan.github.io/ownCloud/

Here is the repo: https://github.com/joelouthan/ownCloud/tree/master/docs

This is for the default.md in which index.md is using layout: default.

Within my _layouts/default.html

<section> <h1>{{ page.title }}</h1> {{ content | toc }} </section>

And in my index.md, I am using h2.

But it still does not render the toc locally nor on github.

Any thoughts?

Allow multiple classes for `no_toc_section_class`

For example

#### Dealing with specificity

Sometimes contextual classes cannot be applied due to the specificity of another selector. In some cases, a sufficient workaround is to wrap your element's content in a `<div>` with the class.

results in this being included in ToC

https://github.com/twbs/bootstrap/blob/9788baedeadddba9d0bcd4dbaea43d65ece9bcbd/site/_includes/callout.html#L1-L9

Demo: https://twbs-bootstrap4.netlify.com/docs/4.1/utilities/colors/

If I change the header to an h5, since we have max h4, then the header is not included in ToC.

/CC @toshimaru

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.