Added basic persistance to notes

This commit is contained in:
Mitchell McCaffrey 2020-11-03 17:15:39 +11:00
parent 84af4c5845
commit 6c1d952855
5 changed files with 107 additions and 26 deletions

View File

@ -33,6 +33,7 @@ function Map({
onFogDraw,
onFogDrawUndo,
onFogDrawRedo,
onMapNoteAdd,
allowMapDrawing,
allowFogDrawing,
allowMapChange,
@ -356,6 +357,9 @@ function Map({
active={selectedToolId === "note"}
gridSize={gridSizeNormalized}
selectedToolSettings={settings[selectedToolId]}
onNoteAdd={onMapNoteAdd}
// TODO: Sort by last modified
notes={mapState ? Object.values(mapState.notes) : []}
/>
);

View File

@ -0,0 +1,31 @@
import React, { useContext } from "react";
import { Group, Rect } from "react-konva";
import MapInteractionContext from "../../contexts/MapInteractionContext";
function MapNote({ note, map }) {
const { mapWidth, mapHeight } = useContext(MapInteractionContext);
const noteWidth = map && (mapWidth / map.grid.size.x) * note.size;
const noteHeight = map && (mapHeight / map.grid.size.y) * note.size;
return (
<Group>
<Rect
x={note.x * mapWidth}
y={note.y * mapHeight}
width={noteWidth}
height={noteHeight}
offsetX={noteWidth / 2}
offsetY={noteHeight / 2}
fill="white"
shadowColor="rgba(0, 0, 0, 0.16)"
shadowOffset={{ x: 0, y: 3 }}
shadowBlur={6}
cornerRadius={1}
/>
</Group>
);
}
export default MapNote;

View File

@ -1,21 +1,31 @@
import React, { useContext, useState, useEffect } from "react";
import { Group, Rect } from "react-konva";
import shortid from "shortid";
import { Group } from "react-konva";
import MapInteractionContext from "../../contexts/MapInteractionContext";
import MapStageContext from "../../contexts/MapStageContext";
import AuthContext from "../../contexts/AuthContext";
import { getBrushPositionForTool } from "../../helpers/drawing";
import { getRelativePointerPositionNormalized } from "../../helpers/konva";
import MapNote from "./MapNote";
const defaultNoteSize = 2;
function MapNotes({ map, selectedToolSettings, active, gridSize }) {
const { mapWidth, mapHeight, interactionEmitter } = useContext(
MapInteractionContext
);
function MapNotes({
map,
selectedToolSettings,
active,
gridSize,
onNoteAdd,
notes,
}) {
const { interactionEmitter } = useContext(MapInteractionContext);
const { userId } = useContext(AuthContext);
const mapStageRef = useContext(MapStageContext);
const [isBrushDown, setIsBrushDown] = useState(false);
const [brushPosition, setBrushPosition] = useState({ x: 0, y: 0 });
const [noteData, setNoteData] = useState(null);
useEffect(() => {
if (!active) {
@ -36,17 +46,34 @@ function MapNotes({ map, selectedToolSettings, active, gridSize }) {
}
function handleBrushDown() {
setBrushPosition(getBrushPosition());
const brushPosition = getBrushPosition();
setNoteData({
x: brushPosition.x,
y: brushPosition.y,
size: defaultNoteSize,
text: "",
id: shortid.generate(),
lastModified: Date.now(),
lastModifiedBy: userId,
visible: true,
locked: false,
});
setIsBrushDown(true);
}
function handleBrushMove() {
setBrushPosition(getBrushPosition());
const brushPosition = getBrushPosition();
setNoteData((prev) => ({
...prev,
x: brushPosition.x,
y: brushPosition.y,
}));
setIsBrushDown(true);
}
function handleBrushUp() {
setBrushPosition({ x: 0, y: 0 });
onNoteAdd(noteData);
setNoteData(null);
setIsBrushDown(false);
}
@ -61,25 +88,12 @@ function MapNotes({ map, selectedToolSettings, active, gridSize }) {
};
});
const noteWidth = map && (mapWidth / map.grid.size.x) * defaultNoteSize;
const noteHeight = map && (mapHeight / map.grid.size.y) * defaultNoteSize;
return (
<Group>
{isBrushDown && (
<Rect
x={brushPosition.x * mapWidth}
y={brushPosition.y * mapHeight}
width={noteWidth}
height={noteHeight}
offsetX={noteWidth / 2}
offsetY={noteHeight / 2}
fill="white"
shadowColor="rgba(0, 0, 0, 0.16)"
shadowOffset={{ x: 0, y: 3 }}
shadowBlur={6}
/>
)}
{notes.map((note) => (
<MapNote note={note} map={map} key={note.id} />
))}
{isBrushDown && noteData && <MapNote note={noteData} map={map} />}
</Group>
);
}

View File

@ -268,6 +268,17 @@ function loadVersions(db) {
token.height = tokenSizes[token.id].height;
});
});
// v1.7.0 - Added note tool
db.version(16)
.stores({})
.upgrade((tx) => {
return tx
.table("states")
.toCollection()
.modify((state) => {
state.notes = {};
});
});
}
// Get the dexie database used in DatabaseContext

View File

@ -167,6 +167,17 @@ function NetworkedMapAndTokens({ session }) {
session.send("mapFogIndex", index);
}
function handleNoteAdd(note) {
setCurrentMapState((prevMapState) => ({
...prevMapState,
notes: {
...prevMapState.notes,
[note.id]: note,
},
}));
session.send("mapNoteAdd", note);
}
/**
* Token state
*/
@ -395,6 +406,15 @@ function NetworkedMapAndTokens({ session }) {
fogDrawActionIndex: data,
}));
}
if (id === "mapNoteAdd" && currentMapState) {
setCurrentMapState((prevMapState) => ({
...prevMapState,
notes: {
...prevMapState.notes,
[data.id]: data,
},
}));
}
}
function handlePeerDataProgress({ id, total, count }) {
@ -460,6 +480,7 @@ function NetworkedMapAndTokens({ session }) {
onFogDraw={handleFogDraw}
onFogDrawUndo={handleFogDrawUndo}
onFogDrawRedo={handleFogDrawRedo}
onMapNoteAdd={handleNoteAdd}
allowMapDrawing={canEditMapDrawing}
allowFogDrawing={canEditFogDrawing}
allowMapChange={canChangeMap}