diff --git a/packages/client-next/src/components/CanvasMeta.tsx b/packages/client-next/src/components/CanvasMeta.tsx
index 8be4e9f..126cd63 100644
--- a/packages/client-next/src/components/CanvasMeta.tsx
+++ b/packages/client-next/src/components/CanvasMeta.tsx
@@ -8,7 +8,7 @@ import {
import { useAppContext } from "../contexts/AppContext";
export const CanvasMeta = () => {
- const { canvasPosition } = useAppContext();
+ const { canvasPosition, cursorPosition } = useAppContext();
const { isOpen, onOpen, onOpenChange } = useDisclosure();
return (
@@ -19,6 +19,14 @@ export const CanvasMeta = () => {
+ {cursorPosition && (
+ <>
+ {" "}
+
+ (Cursor: {cursorPosition.x}, {cursorPosition.y})
+
+ >
+ )}
)}
diff --git a/packages/client-next/src/components/CanvasWrapper.tsx b/packages/client-next/src/components/CanvasWrapper.tsx
index 2f6d276..2db2dda 100644
--- a/packages/client-next/src/components/CanvasWrapper.tsx
+++ b/packages/client-next/src/components/CanvasWrapper.tsx
@@ -5,7 +5,7 @@ import { PanZoomWrapper } from "@sc07-canvas/lib/src/renderer";
import { RendererContext } from "@sc07-canvas/lib/src/renderer/RendererContext";
import { ViewportMoveEvent } from "@sc07-canvas/lib/src/renderer/PanZoom";
import throttle from "lodash.throttle";
-import { ICanvasPosition } from "../types";
+import { ICanvasPosition, IPosition } from "../types";
import { Routes } from "../lib/routes";
export const CanvasWrapper = () => {
@@ -21,7 +21,7 @@ export const CanvasWrapper = () => {
const CanvasInner = () => {
const canvasRef = createRef();
- const { config, setCanvasPosition } = useAppContext();
+ const { config, setCanvasPosition, setCursorPosition } = useAppContext();
const PanZoom = useContext(RendererContext);
// const { centerView } = useControls();
@@ -45,11 +45,26 @@ const CanvasInner = () => {
window.location.replace(Routes.canvas(canvasPosition));
}, 1000);
+ const handleCursorPos = (pos: IPosition) => {
+ if (
+ pos.x < 0 ||
+ pos.y < 0 ||
+ pos.x > config.canvas.size[0] ||
+ pos.y > config.canvas.size[1]
+ ) {
+ setCursorPosition();
+ } else {
+ setCursorPosition(pos);
+ }
+ };
+
PanZoom.addListener("viewportMove", handleViewportMove);
+ canvasInstance.on("cursorPos", handleCursorPos);
return () => {
canvasInstance.destroy();
PanZoom.removeListener("viewportMove", handleViewportMove);
+ canvasInstance.off("cursorPos", handleCursorPos);
};
}, [PanZoom, canvasRef, config, setCanvasPosition]);
diff --git a/packages/client-next/src/components/Pallete.tsx b/packages/client-next/src/components/Pallete.tsx
index d068ae5..518c74b 100644
--- a/packages/client-next/src/components/Pallete.tsx
+++ b/packages/client-next/src/components/Pallete.tsx
@@ -13,7 +13,7 @@ export const Pallete = () => {
useEffect(() => {
if (!Canvas.instance) return;
- Canvas.instance.emit("pallete", pallete);
+ Canvas.instance.updatePallete(pallete);
}, [pallete]);
return (
diff --git a/packages/client-next/src/contexts/AppContext.tsx b/packages/client-next/src/contexts/AppContext.tsx
index 05bfc4c..a3d4300 100644
--- a/packages/client-next/src/contexts/AppContext.tsx
+++ b/packages/client-next/src/contexts/AppContext.tsx
@@ -5,7 +5,12 @@ import {
useEffect,
useState,
} from "react";
-import { ClientConfig, IAppContext, ICanvasPosition } from "../types";
+import {
+ ClientConfig,
+ IAppContext,
+ ICanvasPosition,
+ IPosition,
+} from "../types";
import { AuthSession } from "@sc07-canvas/lib/src/net";
import Network from "../lib/network";
@@ -17,6 +22,7 @@ export const AppContext = ({ children }: PropsWithChildren) => {
const [config, setConfig] = useState(undefined as any);
const [auth, setAuth] = useState();
const [canvasPosition, setCanvasPosition] = useState();
+ const [cursorPosition, setCursorPosition] = useState();
useEffect(() => {
function handleConfig(config: ClientConfig) {
@@ -41,7 +47,14 @@ export const AppContext = ({ children }: PropsWithChildren) => {
return (
{config ? children : "Loading..."}
diff --git a/packages/client-next/src/lib/canvas.ts b/packages/client-next/src/lib/canvas.ts
index 6acc916..d8a4add 100644
--- a/packages/client-next/src/lib/canvas.ts
+++ b/packages/client-next/src/lib/canvas.ts
@@ -1,5 +1,5 @@
import EventEmitter from "eventemitter3";
-import { ClientConfig, IPalleteContext, Pixel } from "../types";
+import { ClientConfig, IPalleteContext, IPosition, Pixel } from "../types";
import Network from "./network";
import {
ClickEvent,
@@ -7,7 +7,17 @@ import {
PanZoom,
} from "@sc07-canvas/lib/src/renderer/PanZoom";
-export class Canvas extends EventEmitter {
+interface CanvasEvents {
+ /**
+ * Cursor canvas position
+ * (-1, -1) is not on canvas
+ * @param position Canvas position
+ * @returns
+ */
+ cursorPos: (position: IPosition) => void;
+}
+
+export class Canvas extends EventEmitter {
static instance: Canvas | undefined;
private _destroy = false;
@@ -41,8 +51,6 @@ export class Canvas extends EventEmitter {
this.PanZoom.addListener("hover", this.handleMouseMove.bind(this));
this.PanZoom.addListener("click", this.handleMouseDown.bind(this));
- this.on("pallete", this.updatePallete.bind(this));
-
Network.waitFor("canvas").then(([pixels]) => this.handleBatch(pixels));
this.draw();
@@ -77,6 +85,8 @@ export class Canvas extends EventEmitter {
this.cursor.x = -1;
this.cursor.y = -1;
}
+
+ this.emit("cursorPos", this.cursor);
}
handleBatch(pixels: string[]) {
@@ -92,7 +102,7 @@ export class Canvas extends EventEmitter {
});
}
- handlePixel({ x, y, color, ...pixel }: Pixel) {
+ handlePixel({ x, y, color }: Pixel) {
this.pixels[x + "_" + y] = {
color,
type: "full",
diff --git a/packages/client-next/src/style.scss b/packages/client-next/src/style.scss
index faba6f0..ff5cba8 100644
--- a/packages/client-next/src/style.scss
+++ b/packages/client-next/src/style.scss
@@ -94,6 +94,10 @@ header#main-header {
display: flex;
flex-direction: column;
+
+ .canvas-meta--cursor-pos {
+ font-style: italic;
+ }
}
main {
diff --git a/packages/client-next/src/types.ts b/packages/client-next/src/types.ts
index dc27411..1bcdde4 100644
--- a/packages/client-next/src/types.ts
+++ b/packages/client-next/src/types.ts
@@ -20,6 +20,8 @@ export interface IAppContext {
user?: AuthSession;
canvasPosition?: ICanvasPosition;
setCanvasPosition: (v: ICanvasPosition) => void;
+ cursorPosition?: IPosition;
+ setCursorPosition: (v?: IPosition) => void;
}
export interface IPalleteContext {
@@ -32,6 +34,11 @@ export interface ICanvasPosition {
zoom: number;
}
+export interface IPosition {
+ x: number;
+ y: number;
+}
+
// other
export type Pixel = {