Skip to content
Snippets Groups Projects
  • Matt Wang's avatar
    2495d3e6
    refactor: modularize site components (#1058) · 2495d3e6
    Matt Wang authored
    Hi everyone, this is a large refactoring PR that looks to **modularize site components** following the discussion in #959. At the top-level, it:
    
    - moves icons, the sidebar, header (navbar, search, aux links), footer, and mermaid components of the `default` layout into their own `_includes`
    - creates a new `minimal` layout that does not render the header or sidebar as a proof-of-concept for the composability of components
    - documents all existing and new layouts (including vendor code) in the "Customization" section 
    
    An important goal of this PR is for it to be **just code motion and flexibility**: there should be **zero impact** on the average end user that only consumes the `default` theme.
    
    The next few sections go in-depth on each of the listed changes.
    
    ### new components
    
    The `default` layout contains a "list" of all relevant components. Importantly, some of these components have sub-components:
    
    - the header is split into the search bar, custom code, and aux links
    - the icons include imports different icon components, some of which are conditionally imported by feature guards
    
    There are also candidates for future splits and joins:
    
    - the sidebar could be split into navigation, collections, external link, and header/footer code
    - the "search footer" could be joined with other search code, which would make it easier to "include search" in one go; *however, this is a markup change*
    - @kevinlin1 has pointed out that there is some leakage between the sidebar (which computes parents/grandparents) and the breadcrumbs (which needs them to render). He's graciously added a bandaid fix to `minimal` (which does not render the sidebar). However, in the long term, we should either:
        - calculate this in a parent and pass the information to both components
        - change how this works entirely (which may happen with multi-level navigation)
    
    @pdmosses has done a great job outlining this and more in his [Modular Layouts test site](https://pdmosses.github.io/modular-layouts/docs/main/).
    
    ### minimal layout
    
    Based on @kevinlin1's use-case in just-the-class (see: his [Winter 2023 CSE 373 site](https://courses.cs.washington.edu/courses/cse373/23wi/)), we've created a first-class `minimal` layout that does not render the sidebar or header.
    
    In a [comment](https://github.com/just-the-docs/just-the-docs/pull/1058#discussion_r1057015039), Kevin has indicated that we can re-add the search bar in the minimal layout; however, it seems like this would be a code change. I think we should punt this to a future issue/PR.
    
    @pdmosses has also discussed the confusion of `minimal` as a layout and its meaning in inheritance. I've added a note in documentation to clarify the (lack of) inheritance relationship.
    
    ### documentation
    
    I've written documentation in the "Customization" page / [Custom layouts and includes](https://deploy-preview-1058--just-the-docs.netlify.app/docs/customization/#custom-layouts-and-includes) section explaining:
    
    - generally, that we use includes/layouts (and pointing to docs)
    - the `default` layout and its constituent components (with a warning about name collisions)
    - creating alternative layouts with `minimal` as an example
    - the inheritance chain of layouts and the vendor layouts that we consume
    
    I've also created (and linked to) a [minimal layout test](https://deploy-preview-1058--just-the-docs.netlify.app/docs/minimal-test/) that is currently a copy of the markdown kitchen sink but with the minimal layout. I think there's room to improve this in the future.
    
    ### future work
    
    I think there's a lot we can do. Let me break this into various sections.
    
    Potential follow-ups before `v0.4.0`:
    
    - re-including search in `minimal` (anticipating a minor code change)
    - fixing the leakage of parent/grandparent information between the sidebar and breadcrumbs (anticipating no end-user code change, but good to evaluate separately and discuss)
    - heavily document this in the migration guide (#1059) and in our RC4 release docs
    - improve semantic markup for components (ex `main`, `nav`)
    
    Related work in later minor versions:
    
    - split up components into smaller components
    - allow users to easily customize new layouts using frontmatter (see @kevinlin1's [comment in #959](https://github.com/just-the-docs/just-the-docs/issues/959#issuecomment-1249755249))
    
    Related work for `v1.0` (i.e. a major breaking change):
    
    - rename and better categorize existing includes
        - standardizing the "custom" includes
        - moving other components to the `components/` folder (ex `head`, `nav`)
        - potentially: less confusing naming for various components
    - potentially separate the search and header as components, so that they are completely independent 
    
    Tangentially related work:
    
    - more flexible grid (see @JPrevost's [comment in this PR thread](https://github.com/just-the-docs/just-the-docs/pull/1058#issuecomment-1363314610))
    - a formal [feature model](https://en.wikipedia.org/wiki/Feature_model) of JTD, documenting feature dependence (see @pdmosses's [comment in this PR thread](https://github.com/just-the-docs/just-the-docs/pull/1058#issuecomment-1365414023))
    - better annotate new features (motivated by writing these docs)
        - we should add "New" to new features :) 
        - we should note when a feature was introduced (I think this is a core part of most software documentation)
        - we should annotate things that are "Advanced" in so far as the average Just the Docs user will not use them / they require significant Jekyll knowledge
    
    
    --- 
    
    Closes #959.
    refactor: modularize site components (#1058)
    Matt Wang authored
    Hi everyone, this is a large refactoring PR that looks to **modularize site components** following the discussion in #959. At the top-level, it:
    
    - moves icons, the sidebar, header (navbar, search, aux links), footer, and mermaid components of the `default` layout into their own `_includes`
    - creates a new `minimal` layout that does not render the header or sidebar as a proof-of-concept for the composability of components
    - documents all existing and new layouts (including vendor code) in the "Customization" section 
    
    An important goal of this PR is for it to be **just code motion and flexibility**: there should be **zero impact** on the average end user that only consumes the `default` theme.
    
    The next few sections go in-depth on each of the listed changes.
    
    ### new components
    
    The `default` layout contains a "list" of all relevant components. Importantly, some of these components have sub-components:
    
    - the header is split into the search bar, custom code, and aux links
    - the icons include imports different icon components, some of which are conditionally imported by feature guards
    
    There are also candidates for future splits and joins:
    
    - the sidebar could be split into navigation, collections, external link, and header/footer code
    - the "search footer" could be joined with other search code, which would make it easier to "include search" in one go; *however, this is a markup change*
    - @kevinlin1 has pointed out that there is some leakage between the sidebar (which computes parents/grandparents) and the breadcrumbs (which needs them to render). He's graciously added a bandaid fix to `minimal` (which does not render the sidebar). However, in the long term, we should either:
        - calculate this in a parent and pass the information to both components
        - change how this works entirely (which may happen with multi-level navigation)
    
    @pdmosses has done a great job outlining this and more in his [Modular Layouts test site](https://pdmosses.github.io/modular-layouts/docs/main/).
    
    ### minimal layout
    
    Based on @kevinlin1's use-case in just-the-class (see: his [Winter 2023 CSE 373 site](https://courses.cs.washington.edu/courses/cse373/23wi/)), we've created a first-class `minimal` layout that does not render the sidebar or header.
    
    In a [comment](https://github.com/just-the-docs/just-the-docs/pull/1058#discussion_r1057015039), Kevin has indicated that we can re-add the search bar in the minimal layout; however, it seems like this would be a code change. I think we should punt this to a future issue/PR.
    
    @pdmosses has also discussed the confusion of `minimal` as a layout and its meaning in inheritance. I've added a note in documentation to clarify the (lack of) inheritance relationship.
    
    ### documentation
    
    I've written documentation in the "Customization" page / [Custom layouts and includes](https://deploy-preview-1058--just-the-docs.netlify.app/docs/customization/#custom-layouts-and-includes) section explaining:
    
    - generally, that we use includes/layouts (and pointing to docs)
    - the `default` layout and its constituent components (with a warning about name collisions)
    - creating alternative layouts with `minimal` as an example
    - the inheritance chain of layouts and the vendor layouts that we consume
    
    I've also created (and linked to) a [minimal layout test](https://deploy-preview-1058--just-the-docs.netlify.app/docs/minimal-test/) that is currently a copy of the markdown kitchen sink but with the minimal layout. I think there's room to improve this in the future.
    
    ### future work
    
    I think there's a lot we can do. Let me break this into various sections.
    
    Potential follow-ups before `v0.4.0`:
    
    - re-including search in `minimal` (anticipating a minor code change)
    - fixing the leakage of parent/grandparent information between the sidebar and breadcrumbs (anticipating no end-user code change, but good to evaluate separately and discuss)
    - heavily document this in the migration guide (#1059) and in our RC4 release docs
    - improve semantic markup for components (ex `main`, `nav`)
    
    Related work in later minor versions:
    
    - split up components into smaller components
    - allow users to easily customize new layouts using frontmatter (see @kevinlin1's [comment in #959](https://github.com/just-the-docs/just-the-docs/issues/959#issuecomment-1249755249))
    
    Related work for `v1.0` (i.e. a major breaking change):
    
    - rename and better categorize existing includes
        - standardizing the "custom" includes
        - moving other components to the `components/` folder (ex `head`, `nav`)
        - potentially: less confusing naming for various components
    - potentially separate the search and header as components, so that they are completely independent 
    
    Tangentially related work:
    
    - more flexible grid (see @JPrevost's [comment in this PR thread](https://github.com/just-the-docs/just-the-docs/pull/1058#issuecomment-1363314610))
    - a formal [feature model](https://en.wikipedia.org/wiki/Feature_model) of JTD, documenting feature dependence (see @pdmosses's [comment in this PR thread](https://github.com/just-the-docs/just-the-docs/pull/1058#issuecomment-1365414023))
    - better annotate new features (motivated by writing these docs)
        - we should add "New" to new features :) 
        - we should note when a feature was introduced (I think this is a core part of most software documentation)
        - we should annotate things that are "Advanced" in so far as the average Just the Docs user will not use them / they require significant Jekyll knowledge
    
    
    --- 
    
    Closes #959.
customization.md 12.75 KiB
layout: default
title: Customization
nav_order: 6

Customization

{: .no_toc }

Table of contents

{: .no_toc .text-delta }

  1. TOC {:toc}

Color schemes

{: .d-inline-block }

New {: .label .label-green }

Just the Docs supports two color schemes: light (default), and dark.

To enable a color scheme, set the color_scheme parameter in your site's _config.yml file:

Example

{: .no_toc }

# Color scheme supports "light" (default) and "dark"
color_scheme: dark

Preview dark color scheme

Custom schemes

Define a custom scheme

You can add custom schemes. If you want to add a scheme named foo (can be any name) just add a file _sass/color_schemes/foo.scss (replace foo by your scheme name) where you override theme variables to change colors, fonts, spacing, etc.

{: .note } Since the default color scheme is light, your custom scheme is implicitly based on the variable settings used by the light scheme.

If you want your custom scheme to be based on the dark scheme, you need to start your file with the following line:

@import "./color_schemes/dark";

You can define custom schemes based on other custom schemes in the same way.

Available variables are listed in the _variables.scss file.

For example, to change the link color from the purple default to blue, include the following inside your scheme file:

Example

{: .no_toc }

$link-color: $blue-000;

Keep in mind that changing a variable will not automatically change the value of other variables that depend on it. For example, the default link color ($link-color) is set to $purple-000. However, redefining $purple-000 in a custom color scheme will not automatically change $link-color to match it. Instead, each variable that relies on previously-cascaded values must be manually reimplemented by copying the dependent rules from _variables.scss — in this case, rewriting $link-color: $purple-000;.

Note: Editing the variables directly in _sass/support/variables.scss is not recommended and can cause other dependencies to fail. Please use scheme files.

Use a custom scheme

To use the custom color scheme, only set the color_scheme parameter in your site's _config.yml file:

color_scheme: foo

Switchable custom scheme

If you want to be able to change the scheme dynamically, for example via javascript, just add a file assets/css/just-the-docs-foo.scss (replace foo by your scheme name) with the following content:

{% raw %} --- --- {% include css/just-the-docs.scss.liquid color_scheme="foo" %} {% endraw %}

This allows you to switch the scheme via the following javascript.

jtd.setTheme("foo")

Override and completely custom styles

For styles that aren't defined as variables, you may want to modify specific CSS classes. Additionally, you may want to add completely custom CSS specific to your content. To do this, put your styles in the file _sass/custom/custom.scss. This will allow for all overrides to be kept in a single file, and for any upstream changes to still be applied.

For example, if you'd like to add your own styles for printing a page, you could add the following styles.

Example

{: .no_toc }

// Print-only styles.
@media print {
  .side-bar,
  .page-header {
    display: none;
  }
  .main-content {
    max-width: auto;
    margin: 1em;
  }
}

Override includes

You can customize the theme by overriding any of the custom Jekyll includes files that it provides.

To do this, create an _includes directory and make a copy of the specific file you wish to modify. The content in this file will override the theme defaults. You can learn more about this process in the Jekyll docs for Overriding theme defaults.

Just the Docs provides the following custom includes files:

Custom TOC Heading

_includes/toc_heading_custom.html

If the page has any child pages, and has_toc is not set to false, this content appears as a heading above the auto-generating list of child pages after the page's content.

Example

{: .no_toc }

To change the default TOC heading to "Contents", create _includes/toc_heading_custom.html and add:

<h2 class="text-delta">Contents</h2>

The (optional) text-delta class makes the heading appear as Contents{:.text-delta} .

Custom Footer

_includes/footer_custom.html

This content appears at the bottom of every page's main content. More info for this include can be found in the Configuration - Footer content.

Custom Head

_includes/head_custom.html

Any HTML added to this file will be inserted before the closing <head> tag. This might include additional <meta>, <link>, or <script> tags.

The <head> tag automatically includes a link to an existing favicon if you set favicon_ico to the corresponding path in your configuration, or if the path to the favicon is /favicon.ico.

Custom Header

_includes/header_custom.html

Content added to this file appears at the top of every page's main content between the site search and auxiliary links if they are enabled. If search_enabled were set to false and aux_links were removed, the content of header_custom.html would occupy the space at the top of every page.

Custom Nav Footer

_includes/nav_footer_custom.html

Any content added to this file will appear at the bottom left of the page below the site's navigation. By default an attribution to Just the Docs is displayed which reads, This site uses Just the Docs, a documentation theme for Jekyll..

Custom Search Placeholder

_includes/search_placeholder_custom.html

Content added to this file will replace the default placeholder text in the search bar (and its aria-label), after stripping HTML and leading/trailing whitespace. By default, the content of the include is:

{% raw %}

Search {{site.title}}

{% endraw %}

Override this file to render a custom placeholder. One common use-case is internationalization; for example,

{% raw %}

Chercher notre site

{% endraw %}

would make the placeholder text "Chercher notre site". Liquid code (including Jekyll variables) is also supported.

Custom layouts and includes

{: .d-inline-block }

New (v0.4.0) {: .label .label-green }

Advanced {: .label .label-yellow }

Just the Docs uses Jekyll's powerful layouts and includes features to generate and compose various elements of the site. Jekyll users and developers can extend or replace existing layouts and includes to customize the entire site layout.

Default layout and includable components

The default layout is inherited by most of the "out-of-the-box" pages provided by Just the Docs. It composes various re-usable components of the site, including the sidebar, navbar, footer, breadcrumbs, and various imports. Most users who create new pages or layouts will inherit from default.

Here is a simplified code example of what it looks like:

{% raw %}

<!-- a simplified version of _layouts/default.html -->
<html>
{% include head.html %}
<body>
  {% include icons/icons.html %}
  {% include components/sidebar.html %}
  {% include components/header.html %}
  {% include components/breadcrumbs.html %}

  {% if site.heading_anchors != false %}
    {% include vendor/anchor_headings.html html=content ... %}
  {% else %}
    {{ content }}
  {% endif %}

  {% if page.has_children == true and page.has_toc != false %}
    {% include components/children_nav.html %}
  {% endif %}

  {% include components/footer.html %}

  {% if site.search_enabled != false %}
    {% include components/search_footer.html %}
  {% endif %}

  {% if site.mermaid %}
    {% include components/mermaid.html %}
  {% endif %}
</body>
</html>

{% endraw %}

Component summary

{: .no_toc }

{: .warning } Defining a new _includes with the same name as any of these components will significantly change the existing layout. Please proceed with caution when adjusting them.

To briefly summarize each component:

  • _includes/head.html is the entire <head> tag for the site; this imports stylesheets, various JavaScript files (ex: analytics, mermaid, search, and Just the Docs code), and SEO / meta information.
  • _includes/icons/icons.html imports all SVG icons that are used throughout the site. Some, such as those relating to search or code snippet copying, are only loaded when those features are enabled.
  • _includes/components/sidebar.html renders the sidebar, containing the site header, navigation links, external links, collections, and nav footer.
  • _includes/components/header.html renders the navigation header, containing the search bar, custom header, and aux links
  • _includes/components/breadcrumbs.html renders the breadcrumbs feature
  • vendor/anchor_headings.html is a local copy of Vladimir Jimenez's jekyll-anchor-headings snippet
  • _includes/components/children_nav.html renders a list of nav links to child pages on parent pages
  • _includes/components/footer.html renders the bottom-of-page footer
  • _includes/components/search_footer.html renders DOM elements that are necessary for the search bar to work
  • _includes/components/mermaid.html initializes mermaid if the feature is enabled

Each of these components can be overridden individually using the same process described in the Override includes section. In particular, the granularity of components should allow users to replace certain components (such as the sidebar) without having to adjust the rest of the code.

Future versions may subdivide components further; we guarantee that we will only place them in folders (ex components/, icons/, or a new js/) to avoid top-level namespace collisions.

Alternative layouts and example (minimal)

Users can develop custom layouts that compose, omit, or add components differently. We provide one first-class example titled minimal, inspired by Kevin Lin's work in just-the-class. This minimal layout does not render the sidebar, header, or search. To see an example, visit the minimal layout test page.

Here is a simplified code example of what it looks like:

{% raw %}

<!-- a simplified version of _layouts/minimal.html -->
<html>
{% include head.html %}
<body>
  {% include icons/icons.html %}
  {% comment %} Bandaid fix for breadcrumbs here! {% endcomment %}
  {% include components/breadcrumbs.html %}

  {% if site.heading_anchors != false %}
    {% include vendor/anchor_headings.html html=content ... %}
  {% else %}
    {{ content }}
  {% endif %}

  {% if page.has_children == true and page.has_toc != false %}
    {% include components/children_nav.html %}
  {% endif %}

  {% include components/footer.html %}

  {% if site.mermaid %}
    {% include components/mermaid.html %}
  {% endif %}
</body>
</html>

{% endraw %}

This layout is packaged in Just the Docs. Users can indicate this alternative layout in page front matter:

{% raw %}

---
layout: minimal
title: Minimal layout test
---

{% endraw %}

Similarly, users and developers can create other alternative layouts using Just the Docs' reusable includable components.

Default layout and inheritance chain