Refactor ruler out of measure tool
This commit is contained in:
parent
cef4844ea9
commit
e5747235b4
69
src/components/konva/Ruler.tsx
Normal file
69
src/components/konva/Ruler.tsx
Normal file
@ -0,0 +1,69 @@
|
||||
import { Group, Label, Line, Tag, Text } from "react-konva";
|
||||
|
||||
import { useGridStrokeWidth } from "../../contexts/GridContext";
|
||||
import {
|
||||
useDebouncedStageScale,
|
||||
useMapHeight,
|
||||
useMapWidth,
|
||||
} from "../../contexts/MapInteractionContext";
|
||||
|
||||
import { scaleAndFlattenPoints } from "../../helpers/konva";
|
||||
import Vector2 from "../../helpers/Vector2";
|
||||
|
||||
import { GridScale } from "../../types/Grid";
|
||||
|
||||
type RulerProps = {
|
||||
points: Vector2[];
|
||||
scale: GridScale;
|
||||
length: number;
|
||||
};
|
||||
|
||||
function Ruler({ points, scale, length }: RulerProps) {
|
||||
const stageScale = useDebouncedStageScale();
|
||||
const mapWidth = useMapWidth();
|
||||
const mapHeight = useMapHeight();
|
||||
const mapSize = new Vector2(mapWidth, mapHeight);
|
||||
|
||||
const gridStrokeWidth = useGridStrokeWidth();
|
||||
|
||||
const linePoints = scaleAndFlattenPoints(points, mapSize);
|
||||
|
||||
const lineCenter = Vector2.multiply(Vector2.centroid(points), mapSize);
|
||||
|
||||
return (
|
||||
<Group>
|
||||
<Line
|
||||
points={linePoints}
|
||||
strokeWidth={1.5 * gridStrokeWidth}
|
||||
stroke="hsla(230, 25%, 18%, 0.8)"
|
||||
lineCap="round"
|
||||
/>
|
||||
<Line
|
||||
points={linePoints}
|
||||
strokeWidth={0.25 * gridStrokeWidth}
|
||||
stroke="white"
|
||||
lineCap="round"
|
||||
/>
|
||||
<Label
|
||||
x={lineCenter.x}
|
||||
y={lineCenter.y}
|
||||
offsetX={26}
|
||||
offsetY={26}
|
||||
scaleX={1 / stageScale}
|
||||
scaleY={1 / stageScale}
|
||||
>
|
||||
<Tag fill="hsla(230, 25%, 18%, 0.8)" cornerRadius={4} />
|
||||
<Text
|
||||
text={`${(length * scale.multiplier).toFixed(scale.digits)}${
|
||||
scale.unit
|
||||
}`}
|
||||
fill="white"
|
||||
fontSize={24}
|
||||
padding={4}
|
||||
/>
|
||||
</Label>
|
||||
</Group>
|
||||
);
|
||||
}
|
||||
|
||||
export default Ruler;
|
@ -1,18 +1,12 @@
|
||||
import { useState, useEffect } from "react";
|
||||
import { Group, Line, Text, Label, Tag } from "react-konva";
|
||||
import { Group } from "react-konva";
|
||||
|
||||
import {
|
||||
useDebouncedStageScale,
|
||||
useMapWidth,
|
||||
useMapHeight,
|
||||
useInteractionEmitter,
|
||||
} from "../../contexts/MapInteractionContext";
|
||||
import { useInteractionEmitter } from "../../contexts/MapInteractionContext";
|
||||
import { useMapStage } from "../../contexts/MapStageContext";
|
||||
import {
|
||||
useGrid,
|
||||
useGridCellPixelSize,
|
||||
useGridCellNormalizedSize,
|
||||
useGridStrokeWidth,
|
||||
useGridOffset,
|
||||
} from "../../contexts/GridContext";
|
||||
|
||||
@ -24,6 +18,8 @@ import Vector2 from "../../helpers/Vector2";
|
||||
import { getRelativePointerPosition } from "../../helpers/konva";
|
||||
import { parseGridScale, gridDistance } from "../../helpers/grid";
|
||||
|
||||
import Ruler from "../konva/Ruler";
|
||||
|
||||
import useGridSnapping from "../../hooks/useGridSnapping";
|
||||
import { Map } from "../../types/Map";
|
||||
import { PointsData } from "../../types/Drawing";
|
||||
@ -36,15 +32,11 @@ type MapMeasureProps = {
|
||||
type MeasureData = { length: number; points: Vector2[] };
|
||||
|
||||
function MeasureTool({ map, active }: MapMeasureProps) {
|
||||
const stageScale = useDebouncedStageScale();
|
||||
const mapWidth = useMapWidth();
|
||||
const mapHeight = useMapHeight();
|
||||
const interactionEmitter = useInteractionEmitter();
|
||||
|
||||
const grid = useGrid();
|
||||
const gridCellNormalizedSize = useGridCellNormalizedSize();
|
||||
const gridCellPixelSize = useGridCellPixelSize();
|
||||
const gridStrokeWidth = useGridStrokeWidth();
|
||||
const gridOffset = useGridOffset();
|
||||
|
||||
const mapStageRef = useMapStage();
|
||||
@ -147,58 +139,17 @@ function MeasureTool({ map, active }: MapMeasureProps) {
|
||||
};
|
||||
});
|
||||
|
||||
function renderShape(shapeData: MeasureData) {
|
||||
const linePoints = shapeData.points.reduce(
|
||||
(acc: number[], point) => [
|
||||
...acc,
|
||||
point.x * mapWidth,
|
||||
point.y * mapHeight,
|
||||
],
|
||||
[]
|
||||
);
|
||||
|
||||
const lineCenter = Vector2.multiply(
|
||||
Vector2.divide(Vector2.add(shapeData.points[0], shapeData.points[1]), 2),
|
||||
{ x: mapWidth, y: mapHeight }
|
||||
);
|
||||
|
||||
return (
|
||||
<Group>
|
||||
<Line
|
||||
points={linePoints}
|
||||
strokeWidth={1.5 * gridStrokeWidth}
|
||||
stroke="hsla(230, 25%, 18%, 0.8)"
|
||||
lineCap="round"
|
||||
return (
|
||||
<Group>
|
||||
{drawingShapeData && (
|
||||
<Ruler
|
||||
points={drawingShapeData.points}
|
||||
scale={gridScale}
|
||||
length={drawingShapeData.length}
|
||||
/>
|
||||
<Line
|
||||
points={linePoints}
|
||||
strokeWidth={0.25 * gridStrokeWidth}
|
||||
stroke="white"
|
||||
lineCap="round"
|
||||
/>
|
||||
<Label
|
||||
x={lineCenter.x}
|
||||
y={lineCenter.y}
|
||||
offsetX={26}
|
||||
offsetY={26}
|
||||
scaleX={1 / stageScale}
|
||||
scaleY={1 / stageScale}
|
||||
>
|
||||
<Tag fill="hsla(230, 25%, 18%, 0.8)" cornerRadius={4} />
|
||||
<Text
|
||||
text={`${(shapeData.length * gridScale.multiplier).toFixed(
|
||||
gridScale.digits
|
||||
)}${gridScale.unit}`}
|
||||
fill="white"
|
||||
fontSize={24}
|
||||
padding={4}
|
||||
/>
|
||||
</Label>
|
||||
</Group>
|
||||
);
|
||||
}
|
||||
|
||||
return <Group>{drawingShapeData && renderShape(drawingShapeData)}</Group>;
|
||||
)}
|
||||
</Group>
|
||||
);
|
||||
}
|
||||
|
||||
export default MeasureTool;
|
||||
|
Loading…
x
Reference in New Issue
Block a user