diff --git a/src/fencer.html b/src/fencer.html
index b947ef2..996c9c1 100644
--- a/src/fencer.html
+++ b/src/fencer.html
@@ -410,6 +410,8 @@
Mappings
+
+
diff --git a/src/fencer.js b/src/fencer.js
index 4848f86..7f66066 100644
--- a/src/fencer.js
+++ b/src/fencer.js
@@ -1009,18 +1009,44 @@ function mappingsChanged(mode) {
GLOBAL.svgEl.appendChild(xAxisEl);
GLOBAL.svgEl.appendChild(yAxisEl);
- // draw the grid locations
- gridLocations.forEach((location, l) => {
- const [svgX0, svgY0] = svgCoordsFromAxisCoords(location[0]);
- const [svgX1, svgY1] = svgCoordsFromAxisCoords(location[1]);
-
- // are the input and output equal in this projection? (need to allow for normalization rounding)
- if (!locationsAreEqual(location[0], location[1], visibleAxisIds)) {
- const arrow = svgArrow({x1: svgX0, y1: svgY0, x2: svgX1, y2: svgY1, tipLen: 7, tipWid: 7, strokeWidth: 1, color: "grey"}); // draw an arrow
- GLOBAL.svgEl.append(arrow);
- }
- GLOBAL.svgEl.append(SVG("circle", {cx: svgX0, cy: svgY0, r: 2.5, fill: "grey"})); // draw a dot
- });
+ // draw grid locations as a grid
+ if (Q("#grid-style").value.startsWith("grid-")) {
+ gridLocations.forEach((location, l) => {
+ const xIndex = Math.floor(l / yGraticules.length);
+ const yIndex = l % yGraticules.length;
+ const [x1, y1] = svgCoordsFromAxisCoords(location[1]);
+ if (xIndex < xGraticules.length-1) {
+ const topRight = gridLocations[l+yGraticules.length];
+ if (topRight) {
+ const [x2, y2] = svgCoordsFromAxisCoords(topRight[1]);
+ const hLine = SVG("line", {x1: x1, y1: y1, x2: x2, y2: y2, stroke: "grey"});
+ GLOBAL.svgEl.append(hLine);
+ }
+ }
+ if (yIndex < yGraticules.length-1) {
+ const bottomLeft = gridLocations[l+1];
+ if (bottomLeft) {
+ const [x2, y2] = svgCoordsFromAxisCoords(bottomLeft[1])
+ const vLine = SVG("line", {x1: x1, y1: y1, x2: x2, y2: y2, stroke: "grey"});
+ GLOBAL.svgEl.append(vLine);
+ }
+ }
+ });
+ }
+ // draw grid locations as vectors
+ else {
+ gridLocations.forEach((location, l) => {
+ const [svgX0, svgY0] = svgCoordsFromAxisCoords(location[0]);
+ const [svgX1, svgY1] = svgCoordsFromAxisCoords(location[1]);
+
+ // are the input and output equal in this projection? (need to allow for normalization rounding)
+ if (!locationsAreEqual(location[0], location[1], visibleAxisIds)) {
+ const arrow = svgArrow({x1: svgX0, y1: svgY0, x2: svgX1, y2: svgY1, tipLen: 7, tipWid: 7, strokeWidth: 1, color: "grey"}); // draw an arrow
+ GLOBAL.svgEl.append(arrow);
+ }
+ GLOBAL.svgEl.append(SVG("circle", {cx: svgX0, cy: svgY0, r: 2.5, fill: "grey"})); // draw a dot
+ });
+ }
// draw the instances (including current)
// - draw them early so they are underneath the mappings and current location which need to be dragged
@@ -1194,11 +1220,11 @@ function getGraticulesForAxis(axis) {
graticules.add(Math.floor(v / inc) * inc);
}
}
- else if (Q("#grid-style").value.startsWith("fill-space")) {
+ else if (Q("#grid-style").value.match(/^(fill-space-|grid-)/)) {
let inc = 20; // measured in svg px units
let match;
- if (match = Q("#grid-style").value.match(/^fill-space-(\d+)/)) // e.g. fill-space-20, fill-space-40
- inc = parseInt(match[1]);
+ if (match = Q("#grid-style").value.match(/^(fill-space-|grid-)(\d+)/)) // e.g. fill-space-20, fill-space-40
+ inc = parseInt(match[2]);
for (let val = svgCoordFromAxisCoord(axis.axisId, axis.defaultValue) + inc; axisCoordFromSvgCoord(axis.axisId, val) < axis.maxValue; val += inc) { // get the max side of the axis
graticules.add(axisCoordFromSvgCoord(axis.axisId, val));
}