-
Notifications
You must be signed in to change notification settings - Fork 48
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: Ignore touch on more interactive elements #1678
feat: Ignore touch on more interactive elements #1678
Conversation
@StarScape Looks great, thank you! I wonder if we should re-use While we're at it, maybe we should factor out an |
bee244c
to
472280e
Compare
@birtles All great points! I've done what you suggested. Note I just modified the previous commit rather than creating another one—this is a simple enough change I don't think it warrants 2 commits in the history. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks! Looks great.
src/utils/dom-utils.ts
Outdated
export function isInteractiveElement(elem: Element) { | ||
return ( | ||
elem.tagName === 'A' || | ||
elem.tagName === 'BUTTON' || | ||
elem.tagName === 'INPUT' || | ||
elem.tagName === 'TEXTAREA' || | ||
elem.tagName === 'SELECT' || | ||
elem.tagName === 'DATALIST' || | ||
elem.tagName === 'OPTGROUP' || | ||
elem.tagName === 'OPTION' || | ||
isContentEditableNode(elem) | ||
); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit: If we make this take Node | null
like many of the other functions in this file the call site will become a lot simpler.
export function isInteractiveElement(elem: Element) { | |
return ( | |
elem.tagName === 'A' || | |
elem.tagName === 'BUTTON' || | |
elem.tagName === 'INPUT' || | |
elem.tagName === 'TEXTAREA' || | |
elem.tagName === 'SELECT' || | |
elem.tagName === 'DATALIST' || | |
elem.tagName === 'OPTGROUP' || | |
elem.tagName === 'OPTION' || | |
isContentEditableNode(elem) | |
); | |
export function isInteractiveElement(elem: Node | null) { | |
return ( | |
isElement(elem) && | |
(elem.tagName === 'A' || | |
elem.tagName === 'BUTTON' || | |
elem.tagName === 'INPUT' || | |
elem.tagName === 'TEXTAREA' || | |
elem.tagName === 'SELECT' || | |
elem.tagName === 'DATALIST' || | |
elem.tagName === 'OPTGROUP' || | |
elem.tagName === 'OPTION' || | |
isContentEditableNode(elem)) | |
); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, agreed. Though I think we'll want to move the isContentEditableNode
call up to, since, AFAIK, the event target could still be a non-element Node, like a text node, inside of a content editable. I think we'd still want to prevent a tap in those cases.
Though now that I type it out, I'm not sure if the browser will ever have text nodes as event targets?
src/content/content.ts
Outdated
possibleTargetElem != null && | ||
possibleTargetElem.nodeType === Node.ELEMENT_NODE && | ||
isInteractiveElement(possibleTargetElem) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
With the suggestion below, I think this will become just:
possibleTargetElem != null && | |
possibleTargetElem.nodeType === Node.ELEMENT_NODE && | |
isInteractiveElement(possibleTargetElem) | |
isInteractiveElement(possibleTargetElem) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yep! One addition I missed previously: I have to do a type guard to with instanceof Node
to make the call type check. As far as I can tell that's the only way to refine the EventTarget interface into Node
in a type safe way (I could be wrong about that, I'm no TypeScript expert). My previous code with the as
assertion wasn't actually safe, whoops 😬 .
The instanceof
usage does lose the cross-frame capability, though. Not sure if that matters for particular this listener?
Thank you! Yep, I agree. |
472280e
to
455d21d
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Perfect! Thank you!
Fixes #1654. Added in every interactive element I could think of, including contenteditable.