Merge pull request #8737 from tk0miya/8510_html_logo_url

Allow user to use url to reference html logo & favicon
This commit is contained in:
Takeshi KOMIYA 2021-01-24 14:40:56 +09:00 committed by GitHub
commit 0e6a2a9ebd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
11 changed files with 101 additions and 25 deletions

View File

@ -38,6 +38,7 @@ Incompatible changes
Deprecated Deprecated
---------- ----------
* ``favicon`` and ``logo`` variable in HTML templates
* ``sphinx.directives.patches.CSVTable`` * ``sphinx.directives.patches.CSVTable``
* ``sphinx.directives.patches.ListTable`` * ``sphinx.directives.patches.ListTable``
* ``sphinx.directives.patches.RSTTable`` * ``sphinx.directives.patches.RSTTable``
@ -53,6 +54,8 @@ Features added
the location where the object is defined the location where the object is defined
* #7784: i18n: The alt text for image is translated by default (without * #7784: i18n: The alt text for image is translated by default (without
:confval:`gettext_additional_targets` setting) :confval:`gettext_additional_targets` setting)
* #2018: html: :confval:`html_favicon` and :confval:`html_logo` now accept URL
for the image
* #8070: html search: Support searching for 2characters word * #8070: html search: Support searching for 2characters word
* #7830: Add debug logs for change detection of sources and templates * #7830: Add debug logs for change detection of sources and templates
* #8201: Emit a warning if toctree contains duplicated entries * #8201: Emit a warning if toctree contains duplicated entries

View File

@ -26,6 +26,16 @@ The following is a list of deprecated interfaces.
- (will be) Removed - (will be) Removed
- Alternatives - Alternatives
* - ``favicon`` variable in HTML templates
- 4.0
- TBD
- ``favicon_url``
* - ``logo`` variable in HTML templates
- 4.0
- TBD
- ``logo_url``
* - ``sphinx.directives.patches.CSVTable`` * - ``sphinx.directives.patches.CSVTable``
- 4.0 - 4.0
- 6.0 - 6.0

View File

@ -274,7 +274,19 @@ in the future.
.. data:: favicon .. data:: favicon
The path to the HTML favicon in the static path, or ``''``. The path to the HTML favicon in the static path, or URL to the favicon, or
``''``.
.. deprecated:: 4.0
Recommend to use ``favicon_url`` instead.
.. data:: favicon_url
The relative path to the HTML favicon image from the current document, or
URL to the favicon, or ``''``.
.. versionadded:: 4.0
.. data:: file_suffix .. data:: file_suffix
@ -297,7 +309,19 @@ in the future.
.. data:: logo .. data:: logo
The path to the HTML logo image in the static path, or ``''``. The path to the HTML logo image in the static path, or URL to the logo, or
``''``.
.. deprecated:: 4.0
Recommend to use ``logo_url`` instead.
.. data:: logo_url
The relative path to the HTML logo image from the current document, or URL
to the logo, or ``''``.
.. versionadded:: 4.0
.. data:: master_doc .. data:: master_doc

View File

@ -987,26 +987,32 @@ that use Sphinx's HTMLWriter class.
.. confval:: html_logo .. confval:: html_logo
If given, this must be the name of an image file (path relative to the If given, this must be the name of an image file (path relative to the
:term:`configuration directory`) that is the logo of the docs. It is placed :term:`configuration directory`) that is the logo of the docs, or URL that
at the top of the sidebar; its width should therefore not exceed 200 pixels. points an image file for the logo. It is placed at the top of the sidebar;
Default: ``None``. its width should therefore not exceed 200 pixels. Default: ``None``.
.. versionadded:: 0.4.1 .. versionadded:: 0.4.1
The image file will be copied to the ``_static`` directory of the output The image file will be copied to the ``_static`` directory of the output
HTML, but only if the file does not already exist there. HTML, but only if the file does not already exist there.
.. versionchanged:: 4.0
Also accepts the URL for the logo file.
.. confval:: html_favicon .. confval:: html_favicon
If given, this must be the name of an image file (path relative to the If given, this must be the name of an image file (path relative to the
:term:`configuration directory`) that is the favicon of the docs. Modern :term:`configuration directory`) that is the favicon of the docs, or URL that
browsers use this as the icon for tabs, windows and bookmarks. It should points an image file for the favicon. Modern browsers use this as the icon
be a Windows-style icon file (``.ico``), which is 16x16 or 32x32 for tabs, windows and bookmarks. It should be a Windows-style icon file
pixels large. Default: ``None``. (``.ico``), which is 16x16 or 32x32 pixels large. Default: ``None``.
.. versionadded:: 0.4 .. versionadded:: 0.4
The image file will be copied to the ``_static`` directory of the output The image file will be copied to the ``_static`` directory of the output
HTML, but only if the file does not already exist there. HTML, but only if the file does not already exist there.
.. versionchanged:: 4.0
Also accepts the URL for the favicon.
.. confval:: html_css_files .. confval:: html_css_files
A list of CSS files. The entry must be a *filename* string or a tuple A list of CSS files. The entry must be a *filename* string or a tuple

View File

@ -38,7 +38,7 @@ from sphinx.highlighting import PygmentsBridge
from sphinx.locale import _, __ from sphinx.locale import _, __
from sphinx.search import js_index from sphinx.search import js_index
from sphinx.theming import HTMLThemeFactory from sphinx.theming import HTMLThemeFactory
from sphinx.util import logging, md5, progress_message, status_iterator from sphinx.util import isurl, logging, md5, progress_message, status_iterator
from sphinx.util.docutils import is_html5_writer_available, new_document from sphinx.util.docutils import is_html5_writer_available, new_document
from sphinx.util.fileutil import copy_asset from sphinx.util.fileutil import copy_asset
from sphinx.util.i18n import format_date from sphinx.util.i18n import format_date
@ -792,12 +792,12 @@ class StandaloneHTMLBuilder(Builder):
excluded, context=context, renderer=self.templates, onerror=onerror) excluded, context=context, renderer=self.templates, onerror=onerror)
def copy_html_logo(self) -> None: def copy_html_logo(self) -> None:
if self.config.html_logo: if self.config.html_logo and not isurl(self.config.html_logo):
copy_asset(path.join(self.confdir, self.config.html_logo), copy_asset(path.join(self.confdir, self.config.html_logo),
path.join(self.outdir, '_static')) path.join(self.outdir, '_static'))
def copy_html_favicon(self) -> None: def copy_html_favicon(self) -> None:
if self.config.html_favicon: if self.config.html_favicon and not isurl(self.config.html_favicon):
copy_asset(path.join(self.confdir, self.config.html_favicon), copy_asset(path.join(self.confdir, self.config.html_favicon),
path.join(self.outdir, '_static')) path.join(self.outdir, '_static'))
@ -1155,6 +1155,26 @@ def setup_js_tag_helper(app: Sphinx, pagename: str, templatexname: str,
context['js_tag'] = js_tag context['js_tag'] = js_tag
def setup_resource_paths(app: Sphinx, pagename: str, templatename: str,
context: Dict, doctree: Node) -> None:
"""Set up relative resource paths."""
pathto = context.get('pathto')
# favicon_url
favicon = context.get('favicon')
if not isurl(favicon):
context['favicon_url'] = pathto('_static/' + favicon, resource=True)
else:
context['favicon_url'] = favicon
# logo_url
logo = context.get('logo')
if not isurl(logo):
context['logo_url'] = pathto('_static/' + logo, resource=True)
else:
context['logo_url'] = logo
def validate_math_renderer(app: Sphinx) -> None: def validate_math_renderer(app: Sphinx) -> None:
if app.builder.format != 'html': if app.builder.format != 'html':
return return
@ -1195,14 +1215,18 @@ def validate_html_static_path(app: Sphinx, config: Config) -> None:
def validate_html_logo(app: Sphinx, config: Config) -> None: def validate_html_logo(app: Sphinx, config: Config) -> None:
"""Check html_logo setting.""" """Check html_logo setting."""
if config.html_logo and not path.isfile(path.join(app.confdir, config.html_logo)): if (config.html_logo and
not path.isfile(path.join(app.confdir, config.html_logo)) and
not isurl(config.html_logo)):
logger.warning(__('logo file %r does not exist'), config.html_logo) logger.warning(__('logo file %r does not exist'), config.html_logo)
config.html_logo = None # type: ignore config.html_logo = None # type: ignore
def validate_html_favicon(app: Sphinx, config: Config) -> None: def validate_html_favicon(app: Sphinx, config: Config) -> None:
"""Check html_favicon setting.""" """Check html_favicon setting."""
if config.html_favicon and not path.isfile(path.join(app.confdir, config.html_favicon)): if (config.html_favicon and
not path.isfile(path.join(app.confdir, config.html_favicon)) and
not isurl(config.html_favicon)):
logger.warning(__('favicon file %r does not exist'), config.html_favicon) logger.warning(__('favicon file %r does not exist'), config.html_favicon)
config.html_favicon = None # type: ignore config.html_favicon = None # type: ignore
@ -1288,6 +1312,7 @@ def setup(app: Sphinx) -> Dict[str, Any]:
app.connect('config-inited', validate_html_favicon, priority=800) app.connect('config-inited', validate_html_favicon, priority=800)
app.connect('builder-inited', validate_math_renderer) app.connect('builder-inited', validate_math_renderer)
app.connect('html-page-context', setup_js_tag_helper) app.connect('html-page-context', setup_js_tag_helper)
app.connect('html-page-context', setup_resource_paths)
# load default math renderer # load default math renderer
app.setup_extension('sphinx.ext.mathjax') app.setup_extension('sphinx.ext.mathjax')

View File

@ -13,9 +13,9 @@
{% block header %} {% block header %}
<div class="header-wrapper" role="banner"> <div class="header-wrapper" role="banner">
<div class="header"> <div class="header">
{%- if logo %} {%- if logo_url %}
<p class="logo"><a href="{{ pathto(master_doc)|e }}"> <p class="logo"><a href="{{ pathto(master_doc)|e }}">
<img class="logo" src="{{ pathto('_static/' + logo, 1)|e }}" alt="Logo"/> <img class="logo" src="{{ logo_url|e }}" alt="Logo"/>
</a></p> </a></p>
{%- endif %} {%- endif %}
{%- block headertitle %} {%- block headertitle %}

View File

@ -51,9 +51,9 @@
<div class="sphinxsidebar" role="navigation" aria-label="main navigation"> <div class="sphinxsidebar" role="navigation" aria-label="main navigation">
<div class="sphinxsidebarwrapper"> <div class="sphinxsidebarwrapper">
{%- block sidebarlogo %} {%- block sidebarlogo %}
{%- if logo %} {%- if logo_url %}
<p class="logo"><a href="{{ pathto(master_doc)|e }}"> <p class="logo"><a href="{{ pathto(master_doc)|e }}">
<img class="logo" src="{{ pathto('_static/' + logo, 1)|e }}" alt="Logo"/> <img class="logo" src="{{ logo_url|e }}" alt="Logo"/>
</a></p> </a></p>
{%- endif %} {%- endif %}
{%- endblock %} {%- endblock %}
@ -135,8 +135,8 @@
title="{% trans docstitle=docstitle|e %}Search within {{ docstitle }}{% endtrans %}" title="{% trans docstitle=docstitle|e %}Search within {{ docstitle }}{% endtrans %}"
href="{{ pathto('_static/opensearch.xml', 1) }}"/> href="{{ pathto('_static/opensearch.xml', 1) }}"/>
{%- endif %} {%- endif %}
{%- if favicon %} {%- if favicon_url %}
<link rel="shortcut icon" href="{{ pathto('_static/' + favicon, 1)|e }}"/> <link rel="shortcut icon" href="{{ favicon_url|e }}"/>
{%- endif %} {%- endif %}
{%- endif %} {%- endif %}
{%- block linktags %} {%- block linktags %}

View File

@ -6,8 +6,8 @@
<Url type="text/html" method="get" <Url type="text/html" method="get"
template="{{ use_opensearch }}/{{ pathto('search') }}?q={searchTerms}"/> template="{{ use_opensearch }}/{{ pathto('search') }}?q={searchTerms}"/>
<LongName>{{ docstitle|e }}</LongName> <LongName>{{ docstitle|e }}</LongName>
{%- if favicon %} {%- if favicon_url %}
<Image height="16" width="16" type="image/x-icon">{{ use_opensearch }}/{{ pathto('_static/' + favicon, 1)|e }}</Image> <Image height="16" width="16" type="image/x-icon">{{ use_opensearch }}/{{ favicon_url|e }}</Image>
{%- endif %} {%- endif %}
{% block extra %} {# Put e.g. an <Image> element here. #} {% endblock %} {% block extra %} {# Put e.g. an <Image> element here. #} {% endblock %}
</OpenSearchDescription> </OpenSearchDescription>

View File

@ -36,11 +36,11 @@
{%- block haikuheader %} {%- block haikuheader %}
{%- if theme_full_logo != "false" %} {%- if theme_full_logo != "false" %}
<a href="{{ pathto('index') }}"> <a href="{{ pathto('index') }}">
<img class="logo" src="{{ pathto('_static/' + logo, 1)|e }}" alt="Logo"/> <img class="logo" src="{{ logo_url|e }}" alt="Logo"/>
</a> </a>
{%- else %} {%- else %}
{%- if logo -%} {%- if logo -%}
<img class="rightlogo" src="{{ pathto('_static/' + logo, 1)|e }}" alt="Logo"/> <img class="rightlogo" src="{{ logo_url|e }}" alt="Logo"/>
{%- endif -%} {%- endif -%}
<h1 class="heading"><a href="{{ pathto('index') }}"> <h1 class="heading"><a href="{{ pathto('index') }}">
<span>{{ shorttitle|e }}</span></a></h1> <span>{{ shorttitle|e }}</span></a></h1>

View File

@ -13,7 +13,7 @@
<div class="header" role="banner"> <div class="header" role="banner">
<div class="logo"> <div class="logo">
<a href="{{ pathto(master_doc)|e }}"> <a href="{{ pathto(master_doc)|e }}">
<img class="logo" src="{{ pathto('_static/' + logo, 1)|e }}" alt="Logo"/> <img class="logo" src="{{ pathto(logo, 1)|e }}" alt="Logo"/>
</a> </a>
</div> </div>
</div> </div>

View File

@ -447,6 +447,14 @@ def encode_uri(uri: str) -> str:
return urlunsplit(split) return urlunsplit(split)
def isurl(url: str) -> bool:
"""Check *url* is URL or not."""
if url and '://' in url:
return True
else:
return False
def display_chunk(chunk: Any) -> str: def display_chunk(chunk: Any) -> str:
if isinstance(chunk, (list, tuple)): if isinstance(chunk, (list, tuple)):
if len(chunk) == 1: if len(chunk) == 1: