Added support for focusable code blocks on overflow

This commit is contained in:
squidfunk 2020-05-16 15:08:39 +02:00
parent 900c113e59
commit c6e2e3a780
8 changed files with 85 additions and 6 deletions

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -1,6 +1,6 @@
{ {
"assets/javascripts/bundle.js": "assets/javascripts/bundle.4e2bfc5d.min.js", "assets/javascripts/bundle.js": "assets/javascripts/bundle.ff925e8b.min.js",
"assets/javascripts/bundle.js.map": "assets/javascripts/bundle.4e2bfc5d.min.js.map", "assets/javascripts/bundle.js.map": "assets/javascripts/bundle.ff925e8b.min.js.map",
"assets/javascripts/vendor.js": "assets/javascripts/vendor.809e24aa.min.js", "assets/javascripts/vendor.js": "assets/javascripts/vendor.809e24aa.min.js",
"assets/javascripts/vendor.js.map": "assets/javascripts/vendor.809e24aa.min.js.map", "assets/javascripts/vendor.js.map": "assets/javascripts/vendor.809e24aa.min.js.map",
"assets/javascripts/worker/search.js": "assets/javascripts/worker/search.f6ebf1dc.min.js", "assets/javascripts/worker/search.js": "assets/javascripts/worker/search.f6ebf1dc.min.js",

View File

@ -179,7 +179,7 @@
</div> </div>
{% block scripts %} {% block scripts %}
<script src="{{ 'assets/javascripts/vendor.809e24aa.min.js' | url }}"></script> <script src="{{ 'assets/javascripts/vendor.809e24aa.min.js' | url }}"></script>
<script src="{{ 'assets/javascripts/bundle.4e2bfc5d.min.js' | url }}"></script> <script src="{{ 'assets/javascripts/bundle.ff925e8b.min.js' | url }}"></script>
{%- set translations = {} -%} {%- set translations = {} -%}
{%- for key in [ {%- for key in [
"clipboard.copy", "clipboard.copy",

View File

@ -86,6 +86,7 @@ import {
SearchIndex SearchIndex
} from "integrations" } from "integrations"
import { import {
patchCodeBlocks,
patchTables, patchTables,
patchDetails, patchDetails,
patchScrollfix, patchScrollfix,
@ -178,6 +179,7 @@ export function initialize(config: unknown) {
const keyboard$ = setupKeyboard() const keyboard$ = setupKeyboard()
patchCodeBlocks({ document$, viewport$ })
patchDetails({ document$, hash$ }) patchDetails({ document$, hash$ })
patchScripts({ document$ }) patchScripts({ document$ })
patchSource({ document$ }) patchSource({ document$ })

View File

@ -0,0 +1,76 @@
/*
* Copyright (c) 2016-2020 Martin Donath <martin.donath@squidfunk.com>
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to
* deal in the Software without restriction, including without limitation the
* rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
* sell copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
* IN THE SOFTWARE.
*/
import { Observable, combineLatest } from "rxjs"
import { distinctUntilKeyChanged, map } from "rxjs/operators"
import { Viewport, getElements } from "browser"
/* ----------------------------------------------------------------------------
* Helper types
* ------------------------------------------------------------------------- */
/**
* Mount options
*/
interface MountOptions {
document$: Observable<Document> /* Document observable */
viewport$: Observable<Viewport> /* Viewport observable */
}
/* ----------------------------------------------------------------------------
* Functions
* ------------------------------------------------------------------------- */
/**
* Patch all `code` elements
*
* This function will make overflowing code blocks focusable via keyboard, so
* they can be scrolled without a mouse.
*
* @param options - Options
*/
export function patchCodeBlocks(
{ document$, viewport$ }: MountOptions
): void {
const els$ = document$
.pipe(
map(() => getElements<HTMLTableElement>("pre > code"))
)
/* Observe viewport size only */
const size$ = viewport$
.pipe(
distinctUntilKeyChanged("size")
)
/* Make overflowing elements focusable */
combineLatest([els$, size$])
.subscribe(([els]) => {
for (const el of els) {
if (el.scrollWidth > el.clientWidth)
el.setAttribute("tabindex", "0")
else
el.removeAttribute("tabindex")
}
})
}

View File

@ -20,6 +20,7 @@
* IN THE SOFTWARE. * IN THE SOFTWARE.
*/ */
export * from "./code"
export * from "./details" export * from "./details"
export * from "./script" export * from "./script"
export * from "./scrollfix" export * from "./scrollfix"