Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Making navbar + a few other sections more modular #355

Merged
merged 20 commits into from
Apr 9, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions docs/_templates/navbar-version.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
v{{ version }}
14 changes: 10 additions & 4 deletions docs/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,9 @@
copyright = "2019, PyData Community"
author = "PyData Community"

# The full version, including alpha/beta/rc tags
release = "0.0.1dev0"
import pydata_sphinx_theme

version = pydata_sphinx_theme.__version__.replace("dev0", "")

# -- General configuration ---------------------------------------------------

Expand All @@ -50,7 +50,7 @@
exclude_patterns = ["_build", "Thumbs.db", ".DS_Store"]

html_sidebars = {
"contributing": ["sidebar-search-bs.html", "custom-template.html"],
"contributing": ["search-field", "custom-template"],
"changelog": [],
}

Expand All @@ -77,9 +77,15 @@
],
"use_edit_page_button": True,
"show_toc_level": 1,
# "navbar_align": "right", # For testing that the navbar items align properly
# "search_bar_position": "navbar", # TODO: Deprecated - remove in future version
# "navbar_align": "left", # [left, content, right] For testing that the navbar items align properly
# "navbar_start": ["navbar-logo", "navbar-version"],
# "navbar_center": ["navbar-nav", "navbar-version"], # Just for testing
# "navbar_end": ["navbar-icon-links", "navbar-version"] # Just for testing
# "footer_items": ["copyright", "sphinx-version", ""]
}


html_context = {
"github_user": "pandas-dev",
"github_repo": "pydata-sphinx-theme",
Expand Down
55 changes: 45 additions & 10 deletions docs/user_guide/configuring.rst
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ Configure the sidebar
``pydata_sphinx_theme`` provides two new sidebar items by default:

- ``sidebar-nav-bs.html`` - a bootstrap-friendly navigation section
- ``sidebar-search-bs.html`` - a bootstrap-friendly search bar
- ``search-field.html`` - a bootstrap-friendly search bar

By default, this theme's sidebar has these two elements in it. If you'd like to
override this behavior and control the sidebar on a per-page basis, use the
Expand Down Expand Up @@ -229,18 +229,34 @@ and you do not need to specify it if you wish to use the default.
Configure the search bar position
=================================

To modify the position of the search bar, change the following variable in
your configuration file ``conf.py``. Possible options are 'navbar' and 'sidebar'.
To modify the position of the search bar, add the ``search-field.html``
template to your **sidebar**, or to one of the **navbar** positions, depending
on where you want it to be placed.

By default the search bar is positioned in the sidebar since this is more
suitable for large navigation bars.
For example, if you'd like the search field to be in your side-bar, add it to
the sidebar templates like so:

.. code:: python

html_theme_options = {
"search_bar_position": "navbar"
html_sidebars = {
"**": ["search-field.html", "sidebar-nav-bs.html", "sidebar-ethical-ads.html"]
}

If instead you'd like to put the search bar in the top navbar, use the
following configuration:

.. code:: python

html_theme_options = {
"navbar_end": ["navbar-icon-links.html", "search-field.html"]
}


.. note::

By default the search bar is positioned in the sidebar since this is more
suitable for large navigation bars.

Configure the search bar text
=============================

Expand Down Expand Up @@ -332,10 +348,10 @@ use this pattern:
For information about configuring the sidebar's contents, see :ref:`configure-sidebar`.


Configure navbar menu item alignment
====================================
Configure the navbar center alignment
=====================================

By default, the navigation bar menu items will align with the content on your
By default, the navigation bar center area will align with the content on your
page. This equals the following default configuration:

.. code-block:: python
Expand Down Expand Up @@ -366,3 +382,22 @@ If you'd like these items to snap to the right of the page, use this configurati
"navbar_align": "right"
...
}


Adding ethical advertisements to your sidebar in ReadTheDocs
============================================================

If you're hosting your documentation on ReadTheDocs, you should consider
adding an explicit placement for their **ethical advertisements**. These are
non-tracking advertisements from ethical companies, and they help ReadTheDocs
sustain themselves and their free service.

Ethical advertisements are added to your sidebar by default. To ensure they are
there if you manually update your sidebar, ensure that the ``sidebar-ethical-ads.html``
template is added to your list. For example:

.. code:: python

html_sidebars = {
"**": ["search-field.html", "sidebar-nav-bs.html", "sidebar-ethical-ads.html"]
}
1 change: 1 addition & 0 deletions docs/user_guide/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,5 @@ User Guide

install
configuring
sections
customizing
146 changes: 146 additions & 0 deletions docs/user_guide/sections.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
====================================
Add/Remove items from theme sections
====================================

There are a few major theme sections that you can customize to add/remove
components, or add your own components. Each section is configured with a
list of *html templates* - these are snippets of HTML that are inserted into
the section by Sphinx.

You can choose which templates show up in each section, as well as the order in
which they appear. This page describes the major areas that you can customize.

.. note::

When configuring templates in each section, you may omit the ``.html``
suffix after each template if you wish.

The navbar items
================
choldgraf marked this conversation as resolved.
Show resolved Hide resolved

The navbar is at the top of the page, and is broken up into three sections.
Each section is configured in ``conf.py`` with the following configuration:

- Left section: ``html_theme_options['navbar_start']``
- Middle menu: ``html_theme_options['navbar_center']``
- Right section: ``html_theme_options['navbar_end']``

By default, the following configuration is used:

.. code-block:: python

html_theme_options = {
...
"navbar_start": ["navbar-logo"],
"navbar_center": ["navbar-nav"],
"navbar_end": ["navbar-icon-links"]
...
}

The left sidebar
================

The left sidebar is just to the left of a page's main content.
Configuring it is a bit different from configuring the other sections, because
configuring the sidebar is natively supported in Sphinx, via the ``html_sidebars``
configuration variable.

For the left sidebar only, you can configure templates so that they only show
up on certain pages. You do so via a configuration like so in ``conf.py``:
choldgraf marked this conversation as resolved.
Show resolved Hide resolved

.. code-block:: python

html_sidebars = {
"<page_pattern>": ["list", "of", "templates"]
}

Any pages that match ``<page_pattern>`` will have their respective templates
inserted. You can also ``*`` to do ``glob``-style matching, and may use ``**``
to match all pages.

By default, it has the following configuration:

.. code-block:: python

html_sidebars = {
"**": ["search-field", "sidebar-nav-bs", "sidebar-ethical-ads"]
}


The right in-page sidebar
=========================

The in-page sidebar is just to the right of a page's main content, and is
configured in ``conf.py`` with ``html_theme_options['page_sidebar_items']``.

By default, it has the following templates:

.. code-block:: python

html_theme_options = {
...
"page_sidebar_items": ["page-toc", "edit-this-page"],
...
}

The footer
==========

The footer is just below a page's main content, and is configured in ``conf.py``
with ``html_theme_options['footer_items']``.

By default, it has the following templates:

.. code-block:: python

html_theme_options = {
...
"footer_items": ["copyright", "sphinx-version"],
...
}

A list of built-in templates you can insert into sections
=========================================================

Below is a list of build-in templates that you can insert into any section.
Note that some of them may have CSS rules that assume a specific section (and
will be named accordingly).

- ``icon-links.html``
- ``search-field.html``
- ``copyright.html``
- ``edit-this-page.html``
- ``last-updated.html``
- ``navbar-icon-links.html``
- ``navbar-logo.html``
- ``navbar-nav.html``
- ``page-toc.html``
- ``sidebar-ethical-ads.html``
- ``sidebar-nav-bs.html``
- ``sphinx-version.html``

Add your own HTML templates to theme sections
=============================================

If you'd like to add your own custom template to any of these sections, you
could do so with the following steps:

1. Create an HTML file in a folder called ``_templates``. For example, if
you wanted to display the version of your documentation using a Jinja
template, you could create a file: ``_templates/version.html`` and put the
following in it:

.. code-block:: html

<!-- This will display the version of the docs -->
{{ version }}

1. Now add the file to your menu items for one of the sections above. For example:

.. code-block:: python

html_theme_options = {
...
"navbar_start": ["navbar-logo", "version"],
...
}
41 changes: 41 additions & 0 deletions pydata_sphinx_theme/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import os

from sphinx.errors import ExtensionError
from sphinx.util import logging
from sphinx.environment.adapters.toctree import TocTree
from sphinx import addnodes

Expand All @@ -13,6 +14,44 @@

__version__ = "0.5.3dev0"

logger = logging.getLogger(__name__)


def update_config(app, env):
theme_options = app.config["html_theme_options"]
if theme_options.get("search_bar_position") == "navbar":
logger.warn(
(
"Deprecated config `search_bar_position` used."
"Use `search-field.html` in `navbar_end` template list instead."
)
)


def update_templates(app, pagename, templatename, context, doctree):
"""Update template names for page build."""
template_sections = [
"theme_navbar_start",
"theme_navbar_center",
"theme_navbar_end",
"theme_footer_items",
"theme_page_sidebar_items",
"sidebars",
]

for section in template_sections:
if context.get(section):
# Break apart `,` separated strings so we can use , in the defaults
if isinstance(context.get(section), str):
context[section] = [
ii.strip() for ii in context.get(section).split(",")
]

# Add `.html` to templates with no suffix
for ii, template in enumerate(context.get(section)):
if not os.path.splitext(template)[1]:
context[section][ii] = template + ".html"


def add_toctree_functions(app, pagename, templatename, context, doctree):
"""Add functions so Jinja templates can add toctree objects."""
Expand Down Expand Up @@ -440,8 +479,10 @@ def setup(app):
# our custom HTML builder
app.set_translator("readthedocs", BootstrapHTML5Translator, override=True)
app.set_translator("readthedocsdirhtml", BootstrapHTML5Translator, override=True)
app.connect("env-updated", update_config)
app.connect("html-page-context", setup_edit_url)
app.connect("html-page-context", add_toctree_functions)
app.connect("html-page-context", update_templates)

# Update templates for sidebar
pkgdir = os.path.abspath(os.path.dirname(__file__))
Expand Down
7 changes: 7 additions & 0 deletions pydata_sphinx_theme/_templates/copyright.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<p class="copyright">
{%- if hasdoc('copyright') %}
{% trans path=pathto('copyright'), copyright=copyright|e %}&copy; <a href="{{ path }}">Copyright</a> {{ copyright }}.{% endtrans %}<br/>
{%- else %}
{% trans copyright=copyright|e %}&copy; Copyright {{ copyright }}.{% endtrans %}<br/>
{%- endif %}
</p>
3 changes: 3 additions & 0 deletions pydata_sphinx_theme/_templates/last-updated.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<p class="last-updated">
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The original had a if last_updated, should that be kept?

Copy link
Collaborator Author

@choldgraf choldgraf Apr 9, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was thinking that people could just provide this in the footer config if they wished, rather than using the Sphinx feature flag. Does that make sense?

I've added a docs section with a list of templates that can be inserted in. This isn't super descriptive, but I think should help people know what they can put in here. Does that work?

{% trans last_updated=last_updated|e %}Last updated on {{ last_updated }}.{% endtrans %}<br/>
</p>
3 changes: 3 additions & 0 deletions pydata_sphinx_theme/_templates/navbar-icon-links.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{%- block icon_links -%}
{%- include "icon-links.html" with context -%}
{%- endblock %}
19 changes: 19 additions & 0 deletions pydata_sphinx_theme/_templates/navbar-logo.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
{% if logo %}
{% if not theme_logo_link %}
<a class="navbar-brand" href="{{ pathto(master_doc) }}">
<img src="{{ pathto('_static/' + logo, 1) }}" class="logo" alt="logo">
</a>
{% elif theme_logo_link[:4] == 'http' %}
<a class="navbar-brand" href="{{ theme_logo_link }}">
<img src="{{ pathto('_static/' + logo, 1) }}" class="logo" alt="logo">
</a>
{% else %}
<a class="navbar-brand" href="{{ pathto(theme_logo_link) }}">
<img src="{{ pathto('_static/' + logo, 1) }}" class="logo" alt="logo">
</a>
{% endif %}
{% else %}
<a class="navbar-brand" href="{{ pathto(master_doc) }}">
<p class="title">{{ project }}</p>
</a>
{% endif %}
8 changes: 8 additions & 0 deletions pydata_sphinx_theme/_templates/navbar-nav.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<ul id="navbar-main-elements" class="navbar-nav">
{{ generate_nav_html("navbar", maxdepth=1, collapse=True, includehidden=True, titles_only=True) }}
{% for external_link in theme_external_links %}
<li class="nav-item">
<a class="nav-link nav-external" href="{{ external_link.url }}">{{ external_link.name }}<i class="fas fa-external-link-alt"></i></a>
</li>
{% endfor %}
</ul>
Loading