From 3bbe5f85aa084e807eba3d380fc077a00af88516 Mon Sep 17 00:00:00 2001 From: Hsieh Chin Fan Date: Fri, 18 Oct 2024 12:21:51 +0800 Subject: refactor: move logic about dragging GeoLink into DumbyUtils --- src/dumbyUtils.mjs | 64 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ src/dumbymap.mjs | 53 +++++--------------------------------------- 2 files changed, 70 insertions(+), 47 deletions(-) (limited to 'src') diff --git a/src/dumbyUtils.mjs b/src/dumbyUtils.mjs index be0da43..b73f5cd 100644 --- a/src/dumbyUtils.mjs +++ b/src/dumbyUtils.mjs @@ -367,3 +367,67 @@ export const setGeoSchemeByCRS = (crs) => (link) => { return link } + +/** + * dragForAnchor. + * + * @param {HTMLElement} container + * @param {Range} range + */ +export const dragForAnchor = (container, range, endOfLeaderLine) => { + // link placeholder when dragging + container.classList.add('dragging-geolink') + const geoLink = document.createElement('a') + geoLink.textContent = range.toString() + geoLink.classList.add('with-leader-line', 'geolink', 'drag') + + // Replace current content with link + const originContent = range.cloneContents() + const resumeContent = () => { + range.deleteContents() + range.insertNode(originContent) + } + range.deleteContents() + range.insertNode(geoLink) + + // Add leader-line + const line = new LeaderLine({ + start: geoLink, + end: endOfLeaderLine, + path: 'magnet', + }) + + const positionObserver = new window.MutationObserver(() => { + line.position() + }) + positionObserver.observe(endOfLeaderLine, { + attributes: true, + attributeFilter: ['style'], + }) + + // Handler for dragend + container.onmouseup = (e) => { + container.classList.remove('dragging-geolink') + container.onmousemove = null + container.onmouseup = null + geoLink.classList.remove('drag') + positionObserver.disconnect() + line.remove() + + const map = document.elementFromPoint(e.clientX, e.clientY) + .closest('.mapclay[data-render="fulfilled"]') + if (!map) { + resumeContent() + return + } + + const marker = addMarkerByPoint({ point: [e.clientX, e.clientY], map }) + if (!marker) { + resumeContent() + return + } + + geoLink.href = `geo:${marker.dataset.xy.split(',').reverse()}` + createGeoLink(geoLink) + } +} diff --git a/src/dumbymap.mjs b/src/dumbymap.mjs index e9cb473..2879319 100644 --- a/src/dumbymap.mjs +++ b/src/dumbymap.mjs @@ -11,7 +11,6 @@ import * as menuItem from './MenuItem' import PlainModal from 'plain-modal' import proj4 from 'proj4' import { register, fromEPSGCode } from 'ol/proj/proj4' -import LeaderLine from 'leader-line' /** CSS Selector for main components */ const mapBlockSelector = 'pre:has(.language-map), .mapclay-container' @@ -606,62 +605,22 @@ export const generateMaps = (container, { const mouseInRange = e.clientX < rect.right && e.clientX > rect.left && e.clientY < rect.bottom && e.clientY > rect.top if (!mouseInRange) return - // link placeholder when dragging - container.classList.add('dragging-geolink') - const geoLink = document.createElement('a') - geoLink.textContent = range.toString() - geoLink.classList.add('with-leader-line', 'geolink', 'drag') - - // Replace current content with link - const originContent = range.cloneContents() - const resumeContent = () => { - range.deleteContents() - range.insertNode(originContent) - } - range.deleteContents() - range.insertNode(geoLink) - - // Add leader-line - const line = new LeaderLine({ - start: geoLink, - end: pointByArrow, - path: 'magnet', - }) + const timer = setTimeout(() => { + utils.dragForAnchor(container, range, pointByArrow) + }, 300) // Update leader-line with mouse move container.onmousemove = (event) => { const rect = container.getBoundingClientRect() pointByArrow.style.left = `${event.clientX - rect.left}px` pointByArrow.style.top = `${event.clientY - rect.top}px` - line.position() - // TODO Scroll dumbymap.htmlHolder when cursor is at upper/lower side } container.onmousemove(e) - - // Handler for dragend - container.onmouseup = (e) => { - container.classList.remove('dragging-geolink') - container.onmousemove = null + container.onmouseup = () => { + clearTimeout(timer) container.onmouseup = null - geoLink.classList.remove('drag') - line.remove() - - const map = document.elementFromPoint(e.clientX, e.clientY) - .closest('.mapclay[data-render="fulfilled"]') - if (!map) { - resumeContent() - return - } - - const marker = utils.addMarkerByPoint({ point: [e.clientX, e.clientY], map }) - if (!marker) { - resumeContent() - return - } - - geoLink.href = `geo:${marker.dataset.xy.split(',').reverse()}` - utils.createGeoLink(geoLink) + container.onmousemove = null } } -- cgit v1.2.3-70-g09d2