From af4831dd8ad2df0b25a64ae3529a20b921e26c7c Mon Sep 17 00:00:00 2001 From: Hsieh Chin Fan Date: Tue, 8 Oct 2024 16:47:29 +0800 Subject: refactor: move addAnchorByEvent into dumbyUtils --- src/dumbyUtils.mjs | 40 +++++++++++++++++++++++++++++++++++----- src/editor.mjs | 53 +++++++++++++++++++++++------------------------------ 2 files changed, 58 insertions(+), 35 deletions(-) (limited to 'src') diff --git a/src/dumbyUtils.mjs b/src/dumbyUtils.mjs index 95bb3dd..be45139 100644 --- a/src/dumbyUtils.mjs +++ b/src/dumbyUtils.mjs @@ -6,7 +6,7 @@ import { insideWindow, insideParent } from './utils' * * @param {Boolean} reverse -- focus previous map */ -export function focusNextMap (reverse = false) { +export function focusNextMap(reverse = false) { const renderedList = this.utils.renderedMaps() const index = renderedList.findIndex(e => e.classList.contains('focus')) const nextIndex = (index + (reverse ? -1 : 1)) % renderedList.length @@ -21,7 +21,7 @@ export function focusNextMap (reverse = false) { * * @param {Boolean} reverse -- focus previous block */ -export function focusNextBlock (reverse = false) { +export function focusNextBlock(reverse = false) { const blocks = this.blocks.filter(b => b.checkVisibility({ contentVisibilityAuto: true, @@ -56,7 +56,7 @@ export const scrollToBlock = block => { /** * focusDelay. Delay of throttle, value changes by cases */ -export function focusDelay () { +export function focusDelay() { return window.window.getComputedStyle(this.showcase).display === 'none' ? 50 : 300 } @@ -65,7 +65,7 @@ export function focusDelay () { * * @param {Boolean} reverse -- Switch to previous one */ -export function switchToNextLayout (reverse = false) { +export function switchToNextLayout(reverse = false) { const layouts = this.layouts const currentLayoutName = this.container.getAttribute('data-layout') const currentIndex = layouts.map(l => l.name).indexOf(currentLayoutName) @@ -81,7 +81,7 @@ export function switchToNextLayout (reverse = false) { /** * removeBlockFocus. */ -export function removeBlockFocus () { +export function removeBlockFocus() { this.blocks.forEach(b => b.classList.remove('focus')) } @@ -243,3 +243,33 @@ const isAnchorVisible = anchor => { const mapContainer = anchor.closest('.mapclay') return insideWindow(anchor) && insideParent(anchor, mapContainer) } + +export const addAnchorByEvent = ({ + event, + map, + validateAnchorName = () => true +}) => { + const rect = map.getBoundingClientRect() + const [x, y] = map.renderer + .unproject([event.x - rect.left, event.y - rect.top]) + .map(coord => Number(coord.toFixed(7))) + + let prompt + let anchorName + + do { + prompt = prompt ? 'Anchor name exists' : 'Name this anchor' + anchorName = window.prompt(prompt, `${x}, ${y}`) + } + while (anchorName !== null && !validateAnchorName(anchorName)) + if (anchorName === null) return + + const link = `geo:${y},${x}?xy=${x},${y}&id=${map.id} "${anchorName}"` + map.renderer.addMarker({ + xy: [x, y], + title: `${map.id}@${x}, ${y}`, + type: 'circle', + }) + + return { ref: anchorName, link } +} diff --git a/src/editor.mjs b/src/editor.mjs index 499d42b..1c444eb 100644 --- a/src/editor.mjs +++ b/src/editor.mjs @@ -4,6 +4,7 @@ import { markdown2HTML, generateMaps } from './dumbymap' import { defaultAliases, parseConfigsFromYaml } from 'mapclay' import * as menuItem from './MenuItem' import { shiftByWindow } from './utils.mjs' +import { addAnchorByEvent } from './dumbyUtils.mjs' // Set up Containers {{{ @@ -47,7 +48,7 @@ const toggleEditing = () => { // Content values for editor const defaultContent = -`
+ `
> Hello My Friend! This is DumbyMap! @@ -441,30 +442,21 @@ const menuForEditor = (event, menu) => { if (map) { const item = new menuItem.Item({ text: 'Add Anchor', - onclick: () => { - const rect = map.getBoundingClientRect() - const [x, y] = map.renderer - .unproject([event.x - rect.left, event.y - rect.top]) - .map(coord => coord.toFixed(7)) - - let prompt - let anchorName - - do { - prompt = prompt ? 'Anchor name exists' : 'Name this anchor' - anchorName = window.prompt(prompt, `${x}, ${y}`) - } - while (anchorName !== null && refLinks.find(({ ref }) => ref === anchorName)) - if (anchorName === null) return + onclick: (event) => { + const validateAnchorName = anchorName => + !refLinks.find(obj => obj.ref === anchorName) + const { ref, link } = addAnchorByEvent({ + event, + map, + validateAnchorName + }) - const link = `geo:${y},${x}?xy=${x},${y}&id=${map.id} "${anchorName}"` + let refLinkString = `\n[${ref}]: ${link}` const lastLineIsRefLink = cm.getLine(cm.lastLine()).match(refLinkPattern) - cm.replaceRange( - `${lastLineIsRefLink ? '' : '\n'}\n[${anchorName}]: ${link}`, - { line: Infinity } - ) - refLinks = getRefLinks() - map.renderer.addMarker({ xy: [Number(x), Number(y)], title: `${map.id}@${x},${y}`, type: 'circle' }) + if (lastLineIsRefLink) refLinkString = '\n' + refLinkString + cm.replaceRange(refLinkString, { line: Infinity }) + + refLinks.push({ ref, link }) } }) menu.insertBefore(item, menu.firstChild) @@ -802,13 +794,13 @@ const getSuggestions = anchor => { return rendererSuggestions.length === 0 ? [] : [ - ...rendererSuggestions, - new menuItem.Item({ - innerHTML: 'More...', - className: ['suggestion'], - onclick: () => window.open('https://github.com/outdoorsafetylab/mapclay#renderer', '_blank') - }) - ] + ...rendererSuggestions, + new menuItem.Item({ + innerHTML: 'More...', + className: ['suggestion'], + onclick: () => window.open('https://github.com/outdoorsafetylab/mapclay#renderer', '_blank') + }) + ] } return [] } @@ -1076,4 +1068,5 @@ document.addEventListener('selectionchange', () => { cm.setSelection({ ...anchor, ch: anchor.ch - content.length }, anchor) } }) + // vim: sw=2 ts=2 foldmethod=marker foldmarker={{{,}}} -- cgit v1.2.3-70-g09d2