Skip to content
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

fix(links): 5539 close link bubble on click outside #5691

Merged
merged 1 commit into from
Apr 17, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 19 additions & 1 deletion cypress/e2e/nodes/Links.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -40,15 +40,33 @@ describe('test link marks', function() {
const link = 'https://nextcloud.com/'
cy.getContent()
.type(`${link}{enter}`)
cy.getContent()
.find(`a[href*="${link}"]`)

cy.getContent()
.type('{upArrow}')

cy.get('.link-view-bubble .widget-default', { timeout: 10000 })
.find('.widget-default--name')
.contains('Nextcloud')
})

it('closes the link bubble when clicking elsewhere', () => {
const link = 'https://nextcloud.com/'
cy.getContent()
.type(`${link}{enter}`)
cy.getContent()
.find(`a[href*="${link}"]`)

cy.getContent()
.type('{upArrow}')
cy.get('.link-view-bubble .widget-default', { timeout: 10000 })
.find('.widget-default--name')
.contains('Nextcloud')

cy.get('[role="dialog"] h2.modal-name').click()

cy.get('.link-view-bubble .widget-default')
.should('not.exist')
})

it('allows to edit a link in the bubble', () => {
Expand Down
57 changes: 37 additions & 20 deletions src/plugins/LinkBubblePluginView.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,13 @@ import LinkBubbleView from '../components/Link/LinkBubbleView.vue'
class LinkBubblePluginView {

#component = null
#editor = null

constructor({ view, options, plugin }) {
this.options = options
this.view = view
this.plugin = plugin
this.#editor = this.options.editor

this.#component = new VueRenderer(LinkBubbleView, {
parent: this.options.parent,
Expand All @@ -19,23 +21,46 @@ class LinkBubblePluginView {
href: null,
},
})
}

addEventListeners() {
this.view.dom.addEventListener('dragstart',
this.closeOnExternalEvents,
)
document.addEventListener('mousedown',
this.closeOnExternalEvents,
)
document.addEventListener('scroll',
this.closeOnExternalEvents,
{ capture: true }
)
}

this.view.dom.addEventListener('dragstart', this.dragOrScrollHandler)
document.addEventListener('scroll', this.dragOrScrollHandler, { capture: true })
removeEventListeners() {
this.view.dom.removeEventListener('dragstart',
this.closeOnExternalEvents,
)
document.removeEventListener('mousedown',
this.closeOnExternalEvents,
)
document.removeEventListener('scroll',
this.closeOnExternalEvents,
{ capture: true }
)
}

dragOrScrollHandler = (event) => {
// Only hide when scrolling on `<div>` (not .e.g. on `<input>`)
if (event.target.nodeName !== 'DIV') {
closeOnExternalEvents = (event) => {
// Only hide when targetting something outside of the popup
if (this.tippy?.popper?.contains(event.target)) {
return
}

// Cypress fires unexpected scroll events, which breaks testing the link bubble
if (window.Cypress) {
if (window.Cypress && event.type === 'scroll') {
return
}

this.hide()
this.#editor.commands.hideLinkBubble()
}

createTooltip() {
Expand Down Expand Up @@ -73,7 +98,10 @@ class LinkBubblePluginView {
if (active?.mark) {
this.updateTooltip(view, active)
} else {
this.hide()
setTimeout(() => {
this.tippy?.hide()
}, 100)
this.removeEventListeners()
}
}

Expand All @@ -92,23 +120,12 @@ class LinkBubblePluginView {
getReferenceClientRect: () => clientRect,
})

this.show()
}

show() {
this.tippy?.show()
}

hide() {
setTimeout(() => {
this.tippy?.hide()
}, 100)
this.addEventListeners()
}

destroy() {
this.tippy?.destroy()
this.view.dom.removeEventListener('dragstart', this.dragOrScrollHandler)
document.removeEventListener('scroll', this.dragOrScrollHandler, { capture: true })
}

}
Expand Down
Loading