From f32f8fb9dc08adaa8d597470caa3ce0d25e5059a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pawe=C5=82=20Malinowski?= <47485431+malinowskip@users.noreply.github.com> Date: Sun, 7 Nov 2021 21:03:32 +0100 Subject: [PATCH] fix(ToolTip): better toggling logic (#885) * fix(ToolTip): better toggling logic * fix(ToolTip): remove redundant click handler * fix(ToolTip): ensure at most one ToolTip is open at the same time - a click event closes the tooltip if the target is not the tooltip or the tooltip icon. - the event is registered in the capture phase and a `setTimeout` is used to deal with edge cases in which a button is used to toggle the tooltip on or off. --- src/Tooltip/Tooltip.svelte | 28 +++++++++++++++++++++------- 1 file changed, 21 insertions(+), 7 deletions(-) diff --git a/src/Tooltip/Tooltip.svelte b/src/Tooltip/Tooltip.svelte index c1583968..b206c869 100644 --- a/src/Tooltip/Tooltip.svelte +++ b/src/Tooltip/Tooltip.svelte @@ -89,10 +89,19 @@ } } - function openMenu() { + function onFocus() { open = true; } + function onMousedown() { + // determine the desired state before the focus event triggers. + const shouldClose = open; + // ensure changes are scheduled at the end, i.e. after the possible focus event. + setTimeout(() => { + open = shouldClose ? false : true; + }); + } + afterUpdate(() => { if (open) { const button = ref.getBoundingClientRect(); @@ -173,8 +182,13 @@ ref.focus(); } } - - open = false; + } + }}" + on:click|capture="{({ target }) => { + if (open && !ref.contains(target) && !refTooltip.contains(target)) { + setTimeout(() => { + open = false; + }); } }}" /> @@ -190,8 +204,8 @@ bind:this="{refIcon}" {...buttonProps} aria-describedby="{tooltipId}" - on:click|preventDefault|stopPropagation="{openMenu}" - on:focus="{openMenu}" + on:mousedown="{onMousedown}" + on:focus="{onFocus}" on:blur="{onBlur}" on:keydown="{onKeydown}" > @@ -205,8 +219,8 @@ bind:this="{ref}" {...buttonProps} aria-describedby="{tooltipId}" - on:click|preventDefault|stopPropagation="{openMenu}" - on:focus="{openMenu}" + on:mousedown="{onMousedown}" + on:focus="{onFocus}" on:blur="{onBlur}" on:keydown="{onKeydown}" >