fix: track both SVG units and screen pixels for zoom and dampening

The previous commit broke cursor dampening and magnifier triggers by
using SVG units for everything. We need both measurements:

- **SVG units** (0-1010): Accurate zoom calculation
- **Screen pixels**: Cursor dampening and magnifier triggers

Changes:
- Track detectedSmallestSize (SVG units) for zoom calculation
- Track detectedSmallestScreenSize (screen pixels) for dampening
- Use screen pixels for getMovementMultiplier() (expects <1px, <5px, <15px)
- Use screen pixels for hasSmallRegion trigger (<15px)
- Debug logging now shows both values

Example for Gibraltar:
- SVG size: 0.08 units → 1000x zoom
- Screen size: 0.08px → 3% cursor speed (ultra precision)

This restores cursor dampening behavior while keeping accurate
SVG-based zoom calculations.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Thomas Hallock 2025-11-19 10:50:37 -06:00
parent 0dcaabb8a5
commit d72f309bad
1 changed files with 14 additions and 10 deletions

View File

@ -757,7 +757,8 @@ export function MapRenderer({
let regionsInBox = 0 let regionsInBox = 0
let hasSmallRegion = false let hasSmallRegion = false
let totalRegionArea = 0 let totalRegionArea = 0
let detectedSmallestSize = Infinity let detectedSmallestSize = Infinity // SVG units for zoom calculation
let detectedSmallestScreenSize = Infinity // Screen pixels for dampening
const detectedRegions: string[] = [] const detectedRegions: string[] = []
let regionUnderCursor: string | null = null let regionUnderCursor: string | null = null
let smallestDistanceToCenter = Infinity let smallestDistanceToCenter = Infinity
@ -826,13 +827,15 @@ export function MapRenderer({
} }
// Track region sizes for adaptive zoom and dampening // Track region sizes for adaptive zoom and dampening
// Use SVG path bounding box (from viewBox coordinates) for more accurate sizing // - SVG units (from viewBox) for accurate zoom calculation
// getBoundingClientRect() gives axis-aligned boxes which are too large for irregular shapes // - Screen pixels (from getBoundingClientRect) for cursor dampening
const svgBBox = calculateBoundingBox(region.path) const svgBBox = calculateBoundingBox(region.path)
const svgSize = Math.min(svgBBox.width, svgBBox.height) const svgSize = Math.min(svgBBox.width, svgBBox.height)
const screenSize = Math.min(pixelWidth, pixelHeight)
totalRegionArea += pixelArea totalRegionArea += pixelArea
detectedSmallestSize = Math.min(detectedSmallestSize, svgSize) detectedSmallestSize = Math.min(detectedSmallestSize, svgSize)
detectedSmallestScreenSize = Math.min(detectedSmallestScreenSize, screenSize)
} }
}) })
@ -843,9 +846,9 @@ export function MapRenderer({
// Show magnifier if: 7+ regions in detection box OR any region smaller than 15px // Show magnifier if: 7+ regions in detection box OR any region smaller than 15px
const shouldShow = regionsInBox >= 7 || hasSmallRegion const shouldShow = regionsInBox >= 7 || hasSmallRegion
// Update smallest region size for adaptive cursor dampening // Update smallest region size for adaptive cursor dampening (use screen pixels)
if (shouldShow && detectedSmallestSize !== Infinity) { if (shouldShow && detectedSmallestScreenSize !== Infinity) {
setSmallestRegionSize(detectedSmallestSize) setSmallestRegionSize(detectedSmallestScreenSize)
} else { } else {
setSmallestRegionSize(Infinity) setSmallestRegionSize(Infinity)
} }
@ -856,17 +859,18 @@ export function MapRenderer({
setHoveredRegion(regionUnderCursor) setHoveredRegion(regionUnderCursor)
} }
// Debug logging - ONLY for Gibraltar or ultra-small regions (< 2px) // Debug logging - ONLY for Gibraltar or ultra-small regions
const hasGibraltar = detectedRegions.includes('gi') const hasGibraltar = detectedRegions.includes('gi')
if (hasGibraltar || detectedSmallestSize < 2) { if (hasGibraltar || detectedSmallestSize < 5) {
console.log( console.log(
`[Magnifier] ${hasGibraltar ? '🎯 GIBRALTAR DETECTED' : '🔍 Tiny region'} Detection:`, `[Magnifier] ${hasGibraltar ? '🎯 GIBRALTAR DETECTED' : '🔍 Tiny region'} Detection:`,
{ {
detectedRegionIds: detectedRegions, detectedRegionIds: detectedRegions,
regionsInBox, regionsInBox,
smallestSize: detectedSmallestSize.toFixed(2) + 'px', smallestSvgSize: detectedSmallestSize.toFixed(4) + ' SVG units',
smallestScreenSize: detectedSmallestScreenSize.toFixed(2) + 'px',
shouldShow, shouldShow,
movementMultiplier: getMovementMultiplier(detectedSmallestSize).toFixed(2), movementMultiplier: getMovementMultiplier(detectedSmallestScreenSize).toFixed(2),
} }
) )
} }