Fixed content tabs stealing keyboard access to search

This commit is contained in:
squidfunk 2021-10-10 23:13:40 +02:00
parent 77c62c9b55
commit 03ff04b339
10 changed files with 32 additions and 22 deletions

View File

@ -44,5 +44,5 @@
* Copyright(c) 2015 Tiancheng "Timothy" Gu
* MIT Licensed
*/"use strict";var be=/["'&<>]/;ne.exports=we;function we(t){var e=""+t,r=be.exec(e);if(!r)return e;var n,i="",s=0,o=0;for(s=r.index;s<e.length;s++){switch(e.charCodeAt(s)){case 34:n="&quot;";break;case 38:n="&amp;";break;case 39:n="&#39;";break;case 60:n="&lt;";break;case 62:n="&gt;";break;default:continue}o!==s&&(i+=e.substring(o,s)),o=s+1,i+=n}return o!==s?i+e.substring(o,s):i}});var le=W(re());var ie=W(H());function se(t){let e=new Map,r=new Set;for(let n of t){let[i,s]=n.location.split("#"),o=n.location,a=n.title,u=(0,ie.default)(n.text).replace(/\s+(?=[,.:;!?])/g,"").replace(/\s+/g," ");if(s){let c=e.get(i);r.has(c)?e.set(o,{location:o,title:a,text:u,parent:c}):(c.title=n.title,c.text=u,r.add(c))}else e.set(o,{location:o,title:a,text:u})}return e}var oe=W(H());function ae(t,e){let r=new RegExp(t.separator,"img"),n=(i,s,o)=>`${s}<mark data-md-highlight>${o}</mark>`;return i=>{i=i.replace(/[\s*+\-:~^]+/g," ").trim();let s=new RegExp(`(^|${t.separator})(${i.replace(/[|\\{}()[\]^$+*?.-]/g,"\\$&").replace(r,"|")})`,"img");return o=>(e?(0,oe.default)(o):o).replace(s,n).replace(/<\/mark>(\s+)<mark[^>]*>/img,"$1")}}function ue(t){let e=new lunr.Query(["title","text"]);return new lunr.QueryParser(t,e).parse(),e.clauses}function ce(t,e){let r=new Set(t),n={};for(let i=0;i<e.length;i++)for(let s of r)e[i].startsWith(s.term)&&(n[s.term]=!0,r.delete(s));for(let i of r)n[i.term]=!1;return n}function Le(t,e){let[r,n]=[new Set(t),new Set(e)];return[...new Set([...r].filter(i=>!n.has(i)))]}var q=class{constructor({config:e,docs:r,index:n,options:i}){this.options=i,this.documents=se(r),this.highlight=ae(e,!1),lunr.tokenizer.separator=new RegExp(e.separator),typeof n=="undefined"?this.index=lunr(function(){e.lang.length===1&&e.lang[0]!=="en"?this.use(lunr[e.lang[0]]):e.lang.length>1&&this.use(lunr.multiLanguage(...e.lang));let s=Le(["trimmer","stopWordFilter","stemmer"],i.pipeline);for(let o of e.lang.map(a=>a==="en"?lunr:lunr[a]))for(let a of s)this.pipeline.remove(o[a]),this.searchPipeline.remove(o[a]);this.ref("location"),this.field("title",{boost:1e3}),this.field("text");for(let o of r)this.add(o)}):this.index=lunr.Index.load(n)}search(e){if(e)try{let r=this.highlight(e),n=ue(e).filter(o=>o.presence!==lunr.Query.presence.PROHIBITED),i=this.index.search(`${e}*`).reduce((o,{ref:a,score:u,matchData:c})=>{let h=this.documents.get(a);if(typeof h!="undefined"){let{location:y,title:g,text:b,parent:v}=h,Q=ce(n,Object.keys(c.metadata)),f=+!v+ +Object.values(Q).every(p=>p);o.push({location:y,title:r(g),text:r(b),score:u*(1+f),terms:Q})}return o},[]).sort((o,a)=>a.score-o.score).reduce((o,a)=>{let u=this.documents.get(a.location);if(typeof u!="undefined"){let c="parent"in u?u.parent.location:u.location;o.set(c,[...o.get(c)||[],a])}return o},new Map),s;if(this.options.suggestions){let o=this.index.query(a=>{for(let u of n)a.term(u.term,{fields:["title"],presence:lunr.Query.presence.REQUIRED,wildcard:lunr.Query.wildcard.TRAILING})});s=o.length?Object.keys(o[0].matchData.metadata):[]}return Z({items:[...i.values()]},typeof s!="undefined"&&{suggestions:s})}catch(r){console.warn(`Invalid query: ${e} \u2013 see https://bit.ly/2s3ChXG`)}return{items:[]}}};var T;(function(i){i[i.SETUP=0]="SETUP",i[i.READY=1]="READY",i[i.QUERY=2]="QUERY",i[i.RESULT=3]="RESULT"})(T||(T={}));var Y;function Ee(t){return U(this,null,function*(){let e="../lunr";if(typeof parent!="undefined"&&"IFrameWorker"in parent){let n=document.querySelector("script[src]"),[i]=n.src.split("/worker");e=e.replace("..",i)}let r=[];for(let n of t.lang){switch(n){case"ja":r.push(`${e}/tinyseg.js`);break;case"hi":case"th":r.push(`${e}/wordcut.js`);break}n!=="en"&&r.push(`${e}/min/lunr.${n}.min.js`)}t.lang.length>1&&r.push(`${e}/min/lunr.multi.min.js`),r.length&&(yield importScripts(`${e}/min/lunr.stemmer.support.min.js`,...r))})}function ke(t){return U(this,null,function*(){switch(t.type){case T.SETUP:return yield Ee(t.data.config),Y=new q(t.data),{type:T.READY};case T.QUERY:return{type:T.RESULT,data:Y?Y.search(t.data):{items:[]}};default:throw new TypeError("Invalid message type")}})}self.lunr=le.default;addEventListener("message",t=>U(void 0,null,function*(){postMessage(yield ke(t.data))}));})();
//# sourceMappingURL=search.e99e714c.min.js.map
//# sourceMappingURL=search.8397ff9e.min.js.map

View File

@ -198,7 +198,7 @@
"base": base_url,
"features": features,
"translations": {},
"search": "assets/javascripts/workers/search.e99e714c.min.js" | url,
"search": "assets/javascripts/workers/search.8397ff9e.min.js" | url,
"version": config.extra.version or None
} -%}
{%- set translations = app.translations -%}
@ -225,7 +225,7 @@
</script>
{% endblock %}
{% block scripts %}
<script src="{{ 'assets/javascripts/bundle.bc35569b.min.js' | url }}"></script>
<script src="{{ 'assets/javascripts/bundle.801e7afd.min.js' | url }}"></script>
{% for path in config["extra_javascript"] %}
<script src="{{ path | url }}"></script>
{% endfor %}

View File

@ -16,5 +16,5 @@
{% endblock %}
{% block scripts %}
{{ super() }}
<script src="{{ 'overrides/assets/javascripts/bundle.bb368c8a.min.js' | url }}"></script>
<script src="{{ 'overrides/assets/javascripts/bundle.f2c7354c.min.js' | url }}"></script>
{% endblock %}

View File

@ -56,16 +56,26 @@ export interface Keyboard {
* Check whether an element may receive keyboard input
*
* @param el - Element
* @param type - Key type
*
* @returns Test result
*/
function isSusceptibleToKeyboard(el: HTMLElement): boolean {
switch (el.tagName) {
function isSusceptibleToKeyboard(
el: HTMLElement, type: string
): boolean {
switch (el.constructor) {
/* Form elements */
case "INPUT":
case "SELECT":
case "TEXTAREA":
/* Input elements */
case HTMLInputElement:
/* @ts-expect-error - omit unnecessary type cast */
if (el.type === "radio")
return /^Arrow/.test(type)
else
return true
/* Select element and textarea */
case HTMLSelectElement:
case HTMLTextAreaElement:
return true
/* Everything else */
@ -95,11 +105,11 @@ export function watchKeyboard(): Observable<Keyboard> {
ev.stopPropagation()
}
} as Keyboard)),
filter(({ mode }) => {
filter(({ mode, type }) => {
if (mode === "global") {
const active = getActiveElement()
if (typeof active !== "undefined")
return !isSusceptibleToKeyboard(active)
return !isSusceptibleToKeyboard(active, type)
}
return true
}),

View File

@ -163,7 +163,7 @@ export async function handler(
* Worker
* ------------------------------------------------------------------------- */
/* @ts-ignore - expose Lunr.js in global scope, or stemmers will not work */
/* @ts-expect-error - expose Lunr.js in global scope, or stemmers won't work */
self.lunr = lunr
/* Handle messages */