Added note menu and note text
This commit is contained in:
parent
927c596b04
commit
a3ae3471e8
@ -19,6 +19,7 @@ import TokenMenu from "../token/TokenMenu";
|
|||||||
import TokenDragOverlay from "../token/TokenDragOverlay";
|
import TokenDragOverlay from "../token/TokenDragOverlay";
|
||||||
|
|
||||||
import { drawActionsToShapes } from "../../helpers/drawing";
|
import { drawActionsToShapes } from "../../helpers/drawing";
|
||||||
|
import MapNoteMenu from "./MapNoteMenu";
|
||||||
|
|
||||||
function Map({
|
function Map({
|
||||||
map,
|
map,
|
||||||
@ -33,7 +34,7 @@ function Map({
|
|||||||
onFogDraw,
|
onFogDraw,
|
||||||
onFogDrawUndo,
|
onFogDrawUndo,
|
||||||
onFogDrawRedo,
|
onFogDrawRedo,
|
||||||
onMapNoteAdd,
|
onMapNoteChange,
|
||||||
allowMapDrawing,
|
allowMapDrawing,
|
||||||
allowFogDrawing,
|
allowFogDrawing,
|
||||||
allowMapChange,
|
allowMapChange,
|
||||||
@ -351,15 +352,35 @@ function Map({
|
|||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
|
const [isNoteMenuOpen, setIsNoteMenuOpen] = useState(false);
|
||||||
|
const [noteMenuOptions, setNoteMenuOptions] = useState({});
|
||||||
|
function handleNoteMenuOpen(noteId, noteNode) {
|
||||||
|
setNoteMenuOptions({ noteId, noteNode });
|
||||||
|
setIsNoteMenuOpen(true);
|
||||||
|
}
|
||||||
|
|
||||||
const mapNotes = (
|
const mapNotes = (
|
||||||
<MapNotes
|
<MapNotes
|
||||||
map={map}
|
map={map}
|
||||||
active={selectedToolId === "note"}
|
active={selectedToolId === "note"}
|
||||||
gridSize={gridSizeNormalized}
|
gridSize={gridSizeNormalized}
|
||||||
selectedToolSettings={settings[selectedToolId]}
|
selectedToolSettings={settings[selectedToolId]}
|
||||||
onNoteAdd={onMapNoteAdd}
|
onNoteAdd={onMapNoteChange}
|
||||||
|
onNoteChange={onMapNoteChange}
|
||||||
// TODO: Sort by last modified
|
// TODO: Sort by last modified
|
||||||
notes={mapState ? Object.values(mapState.notes) : []}
|
notes={mapState ? Object.values(mapState.notes) : []}
|
||||||
|
onNoteMenuOpen={handleNoteMenuOpen}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
|
||||||
|
const noteMenu = (
|
||||||
|
<MapNoteMenu
|
||||||
|
isOpen={isNoteMenuOpen}
|
||||||
|
onRequestClose={() => setIsNoteMenuOpen(false)}
|
||||||
|
onNoteChange={onMapNoteChange}
|
||||||
|
note={mapState && mapState.notes[noteMenuOptions.noteId]}
|
||||||
|
noteNode={noteMenuOptions.noteNode}
|
||||||
|
map={map}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -370,6 +391,7 @@ function Map({
|
|||||||
<>
|
<>
|
||||||
{mapControls}
|
{mapControls}
|
||||||
{tokenMenu}
|
{tokenMenu}
|
||||||
|
{noteMenu}
|
||||||
{tokenDragOverlay}
|
{tokenDragOverlay}
|
||||||
<MapLoadingOverlay />
|
<MapLoadingOverlay />
|
||||||
</>
|
</>
|
||||||
|
@ -1,29 +1,139 @@
|
|||||||
import React, { useContext } from "react";
|
import React, { useContext, useEffect, useState, useRef } from "react";
|
||||||
import { Group, Rect } from "react-konva";
|
import { Group, Rect, Text } from "react-konva";
|
||||||
|
|
||||||
|
import AuthContext from "../../contexts/AuthContext";
|
||||||
import MapInteractionContext from "../../contexts/MapInteractionContext";
|
import MapInteractionContext from "../../contexts/MapInteractionContext";
|
||||||
|
|
||||||
function MapNote({ note, map }) {
|
import * as Vector2 from "../../helpers/vector2";
|
||||||
|
import colors from "../../helpers/colors";
|
||||||
|
|
||||||
|
const snappingThreshold = 1 / 5;
|
||||||
|
const textPadding = 4;
|
||||||
|
|
||||||
|
function MapNote({ note, map, onNoteChange, onNoteMenuOpen, draggable }) {
|
||||||
|
const { userId } = useContext(AuthContext);
|
||||||
const { mapWidth, mapHeight } = useContext(MapInteractionContext);
|
const { mapWidth, mapHeight } = useContext(MapInteractionContext);
|
||||||
|
|
||||||
const noteWidth = map && (mapWidth / map.grid.size.x) * note.size;
|
const noteWidth = map && (mapWidth / map.grid.size.x) * note.size;
|
||||||
const noteHeight = map && (mapHeight / map.grid.size.y) * note.size;
|
const noteHeight = map && (mapHeight / map.grid.size.y) * note.size;
|
||||||
|
|
||||||
|
function handleClick(event) {
|
||||||
|
if (draggable) {
|
||||||
|
const noteNode = event.target;
|
||||||
|
onNoteMenuOpen && onNoteMenuOpen(note.id, noteNode);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleDragMove(event) {
|
||||||
|
const noteGroup = event.target;
|
||||||
|
// Snap to corners of grid
|
||||||
|
if (map.snapToGrid) {
|
||||||
|
const offset = Vector2.multiply(map.grid.inset.topLeft, {
|
||||||
|
x: mapWidth,
|
||||||
|
y: mapHeight,
|
||||||
|
});
|
||||||
|
const position = {
|
||||||
|
x: noteGroup.x() + noteGroup.width() / 2,
|
||||||
|
y: noteGroup.y() + noteGroup.height() / 2,
|
||||||
|
};
|
||||||
|
const gridSize = {
|
||||||
|
x:
|
||||||
|
(mapWidth *
|
||||||
|
(map.grid.inset.bottomRight.x - map.grid.inset.topLeft.x)) /
|
||||||
|
map.grid.size.x,
|
||||||
|
y:
|
||||||
|
(mapHeight *
|
||||||
|
(map.grid.inset.bottomRight.y - map.grid.inset.topLeft.y)) /
|
||||||
|
map.grid.size.y,
|
||||||
|
};
|
||||||
|
// Transform into offset space, round, then transform back
|
||||||
|
const gridSnap = Vector2.add(
|
||||||
|
Vector2.roundTo(Vector2.subtract(position, offset), gridSize),
|
||||||
|
offset
|
||||||
|
);
|
||||||
|
const gridDistance = Vector2.length(Vector2.subtract(gridSnap, position));
|
||||||
|
const minGrid = Vector2.min(gridSize);
|
||||||
|
if (gridDistance < minGrid * snappingThreshold) {
|
||||||
|
noteGroup.x(gridSnap.x - noteGroup.width() / 2);
|
||||||
|
noteGroup.y(gridSnap.y - noteGroup.height() / 2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleDragEnd(event) {
|
||||||
|
const noteGroup = event.target;
|
||||||
|
onNoteChange &&
|
||||||
|
onNoteChange({
|
||||||
|
...note,
|
||||||
|
x: noteGroup.x() / mapWidth,
|
||||||
|
y: noteGroup.y() / mapHeight,
|
||||||
|
lastModifiedBy: userId,
|
||||||
|
lastModified: Date.now(),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
const [fontSize, setFontSize] = useState(1);
|
||||||
|
useEffect(() => {
|
||||||
|
const text = textRef.current;
|
||||||
|
function findFontSize() {
|
||||||
|
// Create an array from 4 to 18 scaled to the note size
|
||||||
|
const sizes = Array.from(
|
||||||
|
{ length: 14 * note.size },
|
||||||
|
(_, i) => i + 4 * note.size
|
||||||
|
);
|
||||||
|
|
||||||
|
return sizes.reduce((prev, curr) => {
|
||||||
|
text.fontSize(curr);
|
||||||
|
const width = text.getTextWidth() + textPadding * 2;
|
||||||
|
if (width < noteWidth) {
|
||||||
|
return curr;
|
||||||
|
} else {
|
||||||
|
return prev;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
setFontSize(findFontSize());
|
||||||
|
}, [note, noteWidth]);
|
||||||
|
|
||||||
|
const textRef = useRef();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Group>
|
<Group
|
||||||
|
onClick={handleClick}
|
||||||
|
onTap={handleClick}
|
||||||
|
x={note.x * mapWidth}
|
||||||
|
y={note.y * mapHeight}
|
||||||
|
width={noteWidth}
|
||||||
|
height={noteHeight}
|
||||||
|
offsetX={noteWidth / 2}
|
||||||
|
offsetY={noteHeight / 2}
|
||||||
|
draggable={draggable}
|
||||||
|
onDragEnd={handleDragEnd}
|
||||||
|
onDragMove={handleDragMove}
|
||||||
|
>
|
||||||
<Rect
|
<Rect
|
||||||
x={note.x * mapWidth}
|
|
||||||
y={note.y * mapHeight}
|
|
||||||
width={noteWidth}
|
width={noteWidth}
|
||||||
height={noteHeight}
|
height={noteHeight}
|
||||||
offsetX={noteWidth / 2}
|
|
||||||
offsetY={noteHeight / 2}
|
|
||||||
fill="white"
|
|
||||||
shadowColor="rgba(0, 0, 0, 0.16)"
|
shadowColor="rgba(0, 0, 0, 0.16)"
|
||||||
shadowOffset={{ x: 0, y: 3 }}
|
shadowOffset={{ x: 0, y: 3 }}
|
||||||
shadowBlur={6}
|
shadowBlur={6}
|
||||||
cornerRadius={1}
|
cornerRadius={0.25}
|
||||||
|
fill={colors[note.color]}
|
||||||
/>
|
/>
|
||||||
|
<Text
|
||||||
|
text={note.text}
|
||||||
|
fill="black"
|
||||||
|
align="center"
|
||||||
|
verticalAlign="middle"
|
||||||
|
padding={textPadding}
|
||||||
|
fontSize={fontSize}
|
||||||
|
wrap="word"
|
||||||
|
width={noteWidth}
|
||||||
|
height={noteHeight}
|
||||||
|
/>
|
||||||
|
{/* Use an invisible text block to work out text sizing */}
|
||||||
|
<Text visible={false} ref={textRef} text={note.text} wrap="none" />
|
||||||
</Group>
|
</Group>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
216
src/components/map/MapNoteMenu.js
Normal file
216
src/components/map/MapNoteMenu.js
Normal file
@ -0,0 +1,216 @@
|
|||||||
|
import React, { useEffect, useState, useContext } from "react";
|
||||||
|
import { Box, Input, Slider, Flex, Text, IconButton } from "theme-ui";
|
||||||
|
|
||||||
|
import MapMenu from "../map/MapMenu";
|
||||||
|
|
||||||
|
import colors, { colorOptions } from "../../helpers/colors";
|
||||||
|
|
||||||
|
import usePrevious from "../../helpers/usePrevious";
|
||||||
|
|
||||||
|
import LockIcon from "../../icons/TokenLockIcon";
|
||||||
|
import UnlockIcon from "../../icons/TokenUnlockIcon";
|
||||||
|
import ShowIcon from "../../icons/TokenShowIcon";
|
||||||
|
import HideIcon from "../../icons/TokenHideIcon";
|
||||||
|
|
||||||
|
import AuthContext from "../../contexts/AuthContext";
|
||||||
|
|
||||||
|
const defaultNoteMaxSize = 6;
|
||||||
|
|
||||||
|
function MapNoteMenu({
|
||||||
|
isOpen,
|
||||||
|
onRequestClose,
|
||||||
|
note,
|
||||||
|
noteNode,
|
||||||
|
onNoteChange,
|
||||||
|
map,
|
||||||
|
}) {
|
||||||
|
const { userId } = useContext(AuthContext);
|
||||||
|
|
||||||
|
const wasOpen = usePrevious(isOpen);
|
||||||
|
|
||||||
|
const [noteMaxSize, setNoteMaxSize] = useState(defaultNoteMaxSize);
|
||||||
|
const [menuLeft, setMenuLeft] = useState(0);
|
||||||
|
const [menuTop, setMenuTop] = useState(0);
|
||||||
|
useEffect(() => {
|
||||||
|
if (isOpen && !wasOpen && note) {
|
||||||
|
setNoteMaxSize(Math.max(note.size, defaultNoteMaxSize));
|
||||||
|
// Update menu position
|
||||||
|
if (noteNode) {
|
||||||
|
const nodeRect = noteNode.getClientRect();
|
||||||
|
const mapElement = document.querySelector(".map");
|
||||||
|
const mapRect = mapElement.getBoundingClientRect();
|
||||||
|
|
||||||
|
// Center X for the menu which is 156px wide
|
||||||
|
setMenuLeft(mapRect.left + nodeRect.x + nodeRect.width / 2 - 156 / 2);
|
||||||
|
// Y 12px from the bottom
|
||||||
|
setMenuTop(mapRect.top + nodeRect.y + nodeRect.height + 12);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}, [isOpen, note, wasOpen, noteNode]);
|
||||||
|
|
||||||
|
function handleTextChange(event) {
|
||||||
|
const text = event.target.value;
|
||||||
|
note && onNoteChange({ ...note, text: text });
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleColorChange(color) {
|
||||||
|
if (!note) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
onNoteChange({ ...note, color: color });
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleSizeChange(event) {
|
||||||
|
const newSize = parseInt(event.target.value);
|
||||||
|
note && onNoteChange({ ...note, size: newSize });
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleVisibleChange() {
|
||||||
|
note && onNoteChange({ ...note, visible: !note.visible });
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleLockChange() {
|
||||||
|
note && onNoteChange({ ...note, locked: !note.locked });
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleModalContent(node) {
|
||||||
|
if (node) {
|
||||||
|
// Focus input
|
||||||
|
const tokenLabelInput = node.querySelector("#changeNoteText");
|
||||||
|
tokenLabelInput.focus();
|
||||||
|
tokenLabelInput.select();
|
||||||
|
|
||||||
|
// Ensure menu is in bounds
|
||||||
|
const nodeRect = node.getBoundingClientRect();
|
||||||
|
const mapElement = document.querySelector(".map");
|
||||||
|
const mapRect = mapElement.getBoundingClientRect();
|
||||||
|
setMenuLeft((prevLeft) =>
|
||||||
|
Math.min(
|
||||||
|
mapRect.right - nodeRect.width,
|
||||||
|
Math.max(mapRect.left, prevLeft)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
setMenuTop((prevTop) =>
|
||||||
|
Math.min(mapRect.bottom - nodeRect.height, prevTop)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<MapMenu
|
||||||
|
isOpen={isOpen}
|
||||||
|
onRequestClose={onRequestClose}
|
||||||
|
top={`${menuTop}px`}
|
||||||
|
left={`${menuLeft}px`}
|
||||||
|
onModalContent={handleModalContent}
|
||||||
|
>
|
||||||
|
<Box sx={{ width: "156px" }} p={1}>
|
||||||
|
<Flex
|
||||||
|
as="form"
|
||||||
|
onSubmit={(e) => {
|
||||||
|
e.preventDefault();
|
||||||
|
onRequestClose();
|
||||||
|
}}
|
||||||
|
sx={{ alignItems: "center" }}
|
||||||
|
>
|
||||||
|
<Text
|
||||||
|
as="label"
|
||||||
|
variant="body2"
|
||||||
|
sx={{ width: "45%", fontSize: "16px" }}
|
||||||
|
p={1}
|
||||||
|
>
|
||||||
|
Label:
|
||||||
|
</Text>
|
||||||
|
<Input
|
||||||
|
id="changeNoteText"
|
||||||
|
onChange={handleTextChange}
|
||||||
|
value={(note && note.text) || ""}
|
||||||
|
sx={{
|
||||||
|
padding: "4px",
|
||||||
|
border: "none",
|
||||||
|
":focus": {
|
||||||
|
outline: "none",
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
autoComplete="off"
|
||||||
|
/>
|
||||||
|
</Flex>
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
display: "flex",
|
||||||
|
flexWrap: "wrap",
|
||||||
|
justifyContent: "space-between",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{colorOptions.map((color) => (
|
||||||
|
<Box
|
||||||
|
key={color}
|
||||||
|
sx={{
|
||||||
|
width: "16.66%",
|
||||||
|
paddingTop: "16.66%",
|
||||||
|
borderRadius: "50%",
|
||||||
|
transform: "scale(0.75)",
|
||||||
|
backgroundColor: colors[color],
|
||||||
|
cursor: "pointer",
|
||||||
|
}}
|
||||||
|
onClick={() => handleColorChange(color)}
|
||||||
|
aria-label={`Note label Color ${color}`}
|
||||||
|
>
|
||||||
|
{note && note.color === color && (
|
||||||
|
<Box
|
||||||
|
sx={{
|
||||||
|
width: "100%",
|
||||||
|
height: "100%",
|
||||||
|
border: "2px solid white",
|
||||||
|
position: "absolute",
|
||||||
|
top: 0,
|
||||||
|
borderRadius: "50%",
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
)}
|
||||||
|
</Box>
|
||||||
|
))}
|
||||||
|
</Box>
|
||||||
|
<Flex sx={{ alignItems: "center" }}>
|
||||||
|
<Text
|
||||||
|
as="label"
|
||||||
|
variant="body2"
|
||||||
|
sx={{ width: "40%", fontSize: "16px" }}
|
||||||
|
p={1}
|
||||||
|
>
|
||||||
|
Size:
|
||||||
|
</Text>
|
||||||
|
<Slider
|
||||||
|
value={(note && note.size) || 1}
|
||||||
|
onChange={handleSizeChange}
|
||||||
|
step={1}
|
||||||
|
min={1}
|
||||||
|
max={noteMaxSize}
|
||||||
|
mr={1}
|
||||||
|
/>
|
||||||
|
</Flex>
|
||||||
|
{/* Only show hide and lock token actions to map owners */}
|
||||||
|
{map && map.owner === userId && (
|
||||||
|
<Flex sx={{ alignItems: "center", justifyContent: "space-around" }}>
|
||||||
|
<IconButton
|
||||||
|
onClick={handleVisibleChange}
|
||||||
|
title={note && note.visible ? "Hide Note" : "Show Note"}
|
||||||
|
aria-label={note && note.visible ? "Hide Note" : "Show Note"}
|
||||||
|
>
|
||||||
|
{note && note.visible ? <ShowIcon /> : <HideIcon />}
|
||||||
|
</IconButton>
|
||||||
|
<IconButton
|
||||||
|
onClick={handleLockChange}
|
||||||
|
title={note && note.locked ? "Unlock Note" : "Lock Note"}
|
||||||
|
aria-label={note && note.locked ? "Unlock Note" : "Lock Note"}
|
||||||
|
>
|
||||||
|
{note && note.locked ? <LockIcon /> : <UnlockIcon />}
|
||||||
|
</IconButton>
|
||||||
|
</Flex>
|
||||||
|
)}
|
||||||
|
</Box>
|
||||||
|
</MapMenu>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export default MapNoteMenu;
|
@ -1,4 +1,4 @@
|
|||||||
import React, { useContext, useState, useEffect } from "react";
|
import React, { useContext, useState, useEffect, useRef } from "react";
|
||||||
import shortid from "shortid";
|
import shortid from "shortid";
|
||||||
import { Group } from "react-konva";
|
import { Group } from "react-konva";
|
||||||
|
|
||||||
@ -19,7 +19,9 @@ function MapNotes({
|
|||||||
active,
|
active,
|
||||||
gridSize,
|
gridSize,
|
||||||
onNoteAdd,
|
onNoteAdd,
|
||||||
|
onNoteChange,
|
||||||
notes,
|
notes,
|
||||||
|
onNoteMenuOpen,
|
||||||
}) {
|
}) {
|
||||||
const { interactionEmitter } = useContext(MapInteractionContext);
|
const { interactionEmitter } = useContext(MapInteractionContext);
|
||||||
const { userId } = useContext(AuthContext);
|
const { userId } = useContext(AuthContext);
|
||||||
@ -27,6 +29,8 @@ function MapNotes({
|
|||||||
const [isBrushDown, setIsBrushDown] = useState(false);
|
const [isBrushDown, setIsBrushDown] = useState(false);
|
||||||
const [noteData, setNoteData] = useState(null);
|
const [noteData, setNoteData] = useState(null);
|
||||||
|
|
||||||
|
const creatingNoteRef = useRef();
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (!active) {
|
if (!active) {
|
||||||
return;
|
return;
|
||||||
@ -46,33 +50,41 @@ function MapNotes({
|
|||||||
}
|
}
|
||||||
|
|
||||||
function handleBrushDown() {
|
function handleBrushDown() {
|
||||||
const brushPosition = getBrushPosition();
|
if (selectedToolSettings.type === "add") {
|
||||||
setNoteData({
|
const brushPosition = getBrushPosition();
|
||||||
x: brushPosition.x,
|
setNoteData({
|
||||||
y: brushPosition.y,
|
x: brushPosition.x,
|
||||||
size: defaultNoteSize,
|
y: brushPosition.y,
|
||||||
text: "",
|
size: defaultNoteSize,
|
||||||
id: shortid.generate(),
|
text: "",
|
||||||
lastModified: Date.now(),
|
id: shortid.generate(),
|
||||||
lastModifiedBy: userId,
|
lastModified: Date.now(),
|
||||||
visible: true,
|
lastModifiedBy: userId,
|
||||||
locked: false,
|
visible: true,
|
||||||
});
|
locked: false,
|
||||||
setIsBrushDown(true);
|
color: "yellow",
|
||||||
|
});
|
||||||
|
setIsBrushDown(true);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function handleBrushMove() {
|
function handleBrushMove() {
|
||||||
const brushPosition = getBrushPosition();
|
if (selectedToolSettings.type === "add") {
|
||||||
setNoteData((prev) => ({
|
const brushPosition = getBrushPosition();
|
||||||
...prev,
|
setNoteData((prev) => ({
|
||||||
x: brushPosition.x,
|
...prev,
|
||||||
y: brushPosition.y,
|
x: brushPosition.x,
|
||||||
}));
|
y: brushPosition.y,
|
||||||
setIsBrushDown(true);
|
}));
|
||||||
|
setIsBrushDown(true);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function handleBrushUp() {
|
function handleBrushUp() {
|
||||||
onNoteAdd(noteData);
|
if (selectedToolSettings.type === "add") {
|
||||||
|
onNoteAdd(noteData);
|
||||||
|
onNoteMenuOpen(noteData.id, creatingNoteRef.current);
|
||||||
|
}
|
||||||
setNoteData(null);
|
setNoteData(null);
|
||||||
setIsBrushDown(false);
|
setIsBrushDown(false);
|
||||||
}
|
}
|
||||||
@ -91,9 +103,20 @@ function MapNotes({
|
|||||||
return (
|
return (
|
||||||
<Group>
|
<Group>
|
||||||
{notes.map((note) => (
|
{notes.map((note) => (
|
||||||
<MapNote note={note} map={map} key={note.id} />
|
<MapNote
|
||||||
|
note={note}
|
||||||
|
map={map}
|
||||||
|
key={note.id}
|
||||||
|
onNoteMenuOpen={onNoteMenuOpen}
|
||||||
|
draggable={active && selectedToolSettings.type === "move"}
|
||||||
|
onNoteChange={onNoteChange}
|
||||||
|
/>
|
||||||
))}
|
))}
|
||||||
{isBrushDown && noteData && <MapNote note={noteData} map={map} />}
|
<Group ref={creatingNoteRef}>
|
||||||
|
{isBrushDown && noteData && (
|
||||||
|
<MapNote note={noteData} map={map} draggable={false} />
|
||||||
|
)}
|
||||||
|
</Group>
|
||||||
</Group>
|
</Group>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -167,7 +167,7 @@ function NetworkedMapAndTokens({ session }) {
|
|||||||
session.send("mapFogIndex", index);
|
session.send("mapFogIndex", index);
|
||||||
}
|
}
|
||||||
|
|
||||||
function handleNoteAdd(note) {
|
function handleNoteChange(note) {
|
||||||
setCurrentMapState((prevMapState) => ({
|
setCurrentMapState((prevMapState) => ({
|
||||||
...prevMapState,
|
...prevMapState,
|
||||||
notes: {
|
notes: {
|
||||||
@ -175,7 +175,7 @@ function NetworkedMapAndTokens({ session }) {
|
|||||||
[note.id]: note,
|
[note.id]: note,
|
||||||
},
|
},
|
||||||
}));
|
}));
|
||||||
session.send("mapNoteAdd", note);
|
session.send("mapNoteChange", note);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -406,7 +406,7 @@ function NetworkedMapAndTokens({ session }) {
|
|||||||
fogDrawActionIndex: data,
|
fogDrawActionIndex: data,
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
if (id === "mapNoteAdd" && currentMapState) {
|
if (id === "mapNoteChange" && currentMapState) {
|
||||||
setCurrentMapState((prevMapState) => ({
|
setCurrentMapState((prevMapState) => ({
|
||||||
...prevMapState,
|
...prevMapState,
|
||||||
notes: {
|
notes: {
|
||||||
@ -480,7 +480,7 @@ function NetworkedMapAndTokens({ session }) {
|
|||||||
onFogDraw={handleFogDraw}
|
onFogDraw={handleFogDraw}
|
||||||
onFogDrawUndo={handleFogDrawUndo}
|
onFogDrawUndo={handleFogDrawUndo}
|
||||||
onFogDrawRedo={handleFogDrawRedo}
|
onFogDrawRedo={handleFogDrawRedo}
|
||||||
onMapNoteAdd={handleNoteAdd}
|
onMapNoteChange={handleNoteChange}
|
||||||
allowMapDrawing={canEditMapDrawing}
|
allowMapDrawing={canEditMapDrawing}
|
||||||
allowFogDrawing={canEditFogDrawing}
|
allowFogDrawing={canEditFogDrawing}
|
||||||
allowMapChange={canChangeMap}
|
allowMapChange={canChangeMap}
|
||||||
|
Loading…
Reference in New Issue
Block a user