Web Dev Solutions

Catalin Mititiuc

From 694f2dbb242e88cf0696223aa057e8c749539c1c Mon Sep 17 00:00:00 2001 From: Catalin Mititiuc Date: Fri, 29 Mar 2024 12:30:20 -0700 Subject: Add adjustment debug panel --- index.html | 70 ++++++++++++++++++++++++++++++++++++++------------------ index.js | 77 ++++++++++++++++++++++++++++++++++++++++++++++++++++---------- style.css | 60 ++++++++++++++++++++++++++++++++---------------- 3 files changed, 153 insertions(+), 54 deletions(-) diff --git a/index.html b/index.html index 1f1a914..5fb6303 100644 --- a/index.html +++ b/index.html @@ -101,34 +101,60 @@

- - - - - - - - - - - - - +
+
+ hex +
+ + + + +
+
+
+ grid +
+ + + + +
+
+
+ map2 +
+ + + + +
+
+
+ map3 +
+ + + + +
+
+
+ + - - - * + + + + - - - - - - + + + + diff --git a/index.js b/index.js index 1289035..72804fa 100644 --- a/index.js +++ b/index.js @@ -65,7 +65,8 @@ let getPointCoords = (x, y) => { let svgns = "http://www.w3.org/2000/svg", svg = document.querySelector('svg'), - map = document.querySelector('rect#map'); + map = document.querySelector('rect#map'), + hex = document.getElementById('point'); const { x: VIEWBOX_X, y: VIEWBOX_Y, width: VIEWBOX_WIDTH, height: VIEWBOX_HEIGHT } = svg.viewBox.baseVal; @@ -75,6 +76,8 @@ const COLUMN_COUNT = 33, HORZ_POINT_DISTANCE = 1.005, VERT_POINT_DISTANCE = Math.sqrt(3) * HORZ_POINT_DISTANCE / 2, ALTERNATING_OFFSET = HORZ_POINT_DISTANCE / 2, + CIRCUMRADIUS = Math.max(...[...new Set(Object.values(hex.points).flatMap(({x, y}) => [x, y]))]), + INRADIUS = CIRCUMRADIUS * Math.sqrt(3) / 2, [X_OFFSET, Y_OFFSET] = [0.25, 0.45], [COLUMNS, ROWS] = [COLUMN_COUNT, ROW_COUNT].map(n => [...Array(n).keys()]), POINTS = ROWS.map(y => COLUMNS.map(x => [x, y])); @@ -85,14 +88,62 @@ const FIRING_ARC_SIZE = { 'large': Math.atan((21 * HORZ_POINT_DISTANCE) / (6 * VERT_POINT_DISTANCE)) } +const settingsPanel = document.getElementById('panel'); + +Object.values(settingsPanel.querySelectorAll('fieldset')).forEach(fieldset => { + const target = document.getElementById(fieldset.name); + const transform = window.getComputedStyle(target).transform.match(/-?\d+\.?\d*/g); + const inputs = fieldset.querySelectorAll('input'); + + if (transform) { + const [scaleX, skewX, skewY, scaleY, translateX, translateY] = + transform.map(n => parseFloat(n)); + + const cosScale = Math.sqrt(scaleX**2 + skewY**2); + const sinScale = Math.sqrt(scaleY**2 + skewX**2); + + let values = { + scale: Math.round((sinScale + cosScale) / 2 * 10) / 10, + translateX: translateX, + translateY: translateY, + rotate: Math.round(radToDeg((Math.acos(scaleX / cosScale) + Math.asin(skewX / sinScale)) / 2) * 10) / 10 + } + + inputs.forEach(input => input.value = values[input.name]); + } + + inputs.forEach(input => { + input.addEventListener('pointerenter', e => e.target.focus()); + + input.addEventListener('input', e => { + let { scale, translateX, translateY, rotate} = Object.values(inputs).reduce((acc, input) => { + acc[input.name] = input.value; + return acc; + }, {}); + + let transform = `translate(${translateX}px, ${translateY}px) rotate(${rotate}deg) scale(${scale}) ` + target.style.transform = transform; + }); + + input.addEventListener('pointerleave', () => document.activeElement.blur()); + }); +}); + +const pointsGroup = document.getElementById('points'); + POINTS.forEach((row, index) => row.forEach(([x, y]) => { - var cx = x * HORZ_POINT_DISTANCE + X_OFFSET + (isEven(index) ? ALTERNATING_OFFSET : 0), - cy = y * HORZ_POINT_DISTANCE * VERT_POINT_DISTANCE + Y_OFFSET, + // var cx = x * HORZ_POINT_DISTANCE + X_OFFSET + (isEven(index) ? ALTERNATING_OFFSET : 0), + // cy = y * HORZ_POINT_DISTANCE * VERT_POINT_DISTANCE + Y_OFFSET, + // var cx = x * Math.sqrt(3) + X_OFFSET + (isEven(index) ? INRADIUS : 0), + var cx = x * INRADIUS * 2 + (isEven(index) ? INRADIUS : 0), + cy = y * 3 / 2 * CIRCUMRADIUS, point = document.createElementNS(svgns, 'use'); point.setAttributeNS(null, 'href', `#point`); - point.setAttributeNS(null, 'x', `${cx}in`); - point.setAttributeNS(null, 'y', `${cy}in`); + point.setAttributeNS(null, 'x', `${toFixed(cx)}`); + point.setAttributeNS(null, 'y', `${toFixed(cy)}`); + // point.setAttributeNS(null, 'x', `${cx}`); + // point.setAttributeNS(null, 'y', `${cy}`); point.dataset.x = x; point.dataset.y = y; @@ -147,6 +198,8 @@ POINTS.forEach((row, index) => row.forEach(([x, y]) => { let {troopNumber, troopAllegiance} = selectedSoldier.dataset, selector = troopSelector(troopNumber, troopAllegiance), source = document.querySelector(`circle.counter${selector}`), + + // TODO: use isEqualNode() method instead sourceAndTargetAreNotTheSame = [ troopNumber != e.target.dataset.troopNumber, troopAllegiance != e.target.dataset.troopAllegiance @@ -185,7 +238,7 @@ POINTS.forEach((row, index) => row.forEach(([x, y]) => { point.addEventListener('mouseout', e => e.target.removeAttribute('class')); - svg.appendChild(point); + pointsGroup.appendChild(point); })); map.addEventListener('mousemove', e => { @@ -390,11 +443,11 @@ svg.addEventListener('wheel', e => { let widthChange = (1 - ((svgP.x - x) / width)) * widthDelta; let heightChange = (1 - ((svgP.y - y) / height)) * heightDelta; - let newX = e.deltaY < 0 ? x + xChange : x - xChange; - let newWidth = e.deltaY < 0 ? width - xChange - widthChange : width + xChange + widthChange; + let newX = parseInt(e.deltaY < 0 ? x + xChange : x - xChange); + let newWidth = parseInt(e.deltaY < 0 ? width - xChange - widthChange : width + xChange + widthChange); - let newY = e.deltaY < 0 ? y + yChange : y - yChange; - let newHeight = e.deltaY < 0 ? height - yChange - heightChange : height + yChange + heightChange; + let newY = parseInt(e.deltaY < 0 ? y + yChange : y - yChange); + let newHeight = parseInt(e.deltaY < 0 ? height - yChange - heightChange : height + yChange + heightChange); // console.log('VIEWBOX_X', 'VIEWBOX_Y', VIEWBOX_X, VIEWBOX_Y); // console.log('VIEWBOX_WIDTH', 'VIEWBOX_HEIGHT', VIEWBOX_WIDTH, VIEWBOX_HEIGHT); @@ -446,8 +499,8 @@ svg.addEventListener('pointerdown', e => { ctm = svg.getScreenCTM().inverse(); const [svgStartPt, svgMovePt] = [startPt, movePt].map(p => p.matrixTransform(ctm)), - moveX = svgStartPt.x - svgMovePt.x + x, - moveY = svgStartPt.y - svgMovePt.y + y; + moveX = parseInt(svgStartPt.x - svgMovePt.x + x), + moveY = parseInt(svgStartPt.y - svgMovePt.y + y); svg.setAttributeNS(null, 'viewBox', `${moveX} ${moveY} ${width} ${height}`); } diff --git a/style.css b/style.css index c53f289..67c99ba 100644 --- a/style.css +++ b/style.css @@ -19,11 +19,12 @@ svg text { } div#content { + display: flex; + /* display: none; */ border-left: 1px solid gray; flex-basis: 0; /* overflow: scroll; */ max-height: 100vh; - display: flex; flex-direction: column; /* padding: 2px; */ } @@ -71,10 +72,10 @@ div#content { margin-bottom: 0; } -circle#point { +svg > defs > #point { fill: transparent; - stroke: black; - stroke-width: 2px; + stroke: red; + stroke-width: 1px; } use[href="#point"] { @@ -85,6 +86,41 @@ use[href="#point"].active { opacity: 1; } +g#points { + transform: translate(19px, 31px) scale(4); +} + +#background { + fill: #bacae3; +} + +#map2 { + transform: rotate(0.1deg); +} + +#map3 { + transform: rotate(0.1deg); +} + +image.map-scans { + /* transform: scale(1.39, 1.407) rotate(0.07deg); */ + /* opacity: 0.33; */ +} + +#panel { + display: none; + position: absolute; + right: 0; + background-color: white; + border: 1px solid black; + padding: 2px; +} + +#panel fieldset label { + display: block; + text-align: right; +} + circle.counter { stroke: transparent; stroke-width: 0.5in; @@ -135,10 +171,6 @@ line.firing-arc { opacity: 0.1; } -line.ruler { - stroke-width: 0.25in; -} - .sight-line { stroke: black; stroke-width: 3px; @@ -156,11 +188,6 @@ image#img1 { /* opacity: 0.33; */ } -image.map-scans { - transform: scale(1.39, 1.407) rotate(0.07deg); - /* opacity: 0.33; */ -} - .wall { fill: none; stroke: red; @@ -168,13 +195,6 @@ image.map-scans { opacity: 0.7; } -#hex { - opacity: 0.2; - /* stroke: black; - stroke-opacity: 0.2; */ - transform: scale(0.26) translate(-2in, -2in); -} - #asterisk { font-size: 30; } -- cgit v1.2.3