Only show one tippy at a time (#24648)

Because our tippy instances have an `interactiveBorder`, it's possible
to bring up two instances at once, which is undesirable.

<img width="256" alt="Screenshot 2023-05-10 at 23 03 04"
src="https://github.com/go-gitea/gitea/assets/115237/3a9a1775-78c1-46d4-a8a5-503ab7dca0d8">

Prevent this by keeping track of visible tippy instances and hiding
others when one is shown. Tippy also has the [singleton
addon](https://atomiks.github.io/tippyjs/v6/addons/#singleton) for the
same purpose, but it's unsuitable to us because we don't init all
tooltips at once.
This commit is contained in:
silverwind 2023-05-11 07:40:54 +02:00 committed by GitHub
parent 3d9ed62f4a
commit bcd0733a64
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 14 additions and 0 deletions

View File

@ -1,5 +1,7 @@
import tippy from 'tippy.js'; import tippy from 'tippy.js';
const visibleInstances = new Set();
export function createTippy(target, opts = {}) { export function createTippy(target, opts = {}) {
const instance = tippy(target, { const instance = tippy(target, {
appendTo: document.body, appendTo: document.body,
@ -9,6 +11,18 @@ export function createTippy(target, opts = {}) {
interactiveBorder: 20, interactiveBorder: 20,
ignoreAttributes: true, ignoreAttributes: true,
maxWidth: 500, // increase over default 350px maxWidth: 500, // increase over default 350px
onHide: (instance) => {
visibleInstances.delete(instance);
},
onDestroy: (instance) => {
visibleInstances.delete(instance);
},
onShow: (instance) => {
for (const visibleInstance of visibleInstances) {
visibleInstance.hide(); // hide other instances
}
visibleInstances.add(instance);
},
arrow: `<svg width="16" height="7"><path d="m0 7 8-7 8 7Z" class="tippy-svg-arrow-outer"/><path d="m0 8 8-7 8 7Z" class="tippy-svg-arrow-inner"/></svg>`, arrow: `<svg width="16" height="7"><path d="m0 7 8-7 8 7Z" class="tippy-svg-arrow-outer"/><path d="m0 8 8-7 8 7Z" class="tippy-svg-arrow-inner"/></svg>`,
...(opts?.role && {theme: opts.role}), ...(opts?.role && {theme: opts.role}),
...opts, ...opts,