# 点位图绘制 **Repository Path**: lengxiaoxu/point-map-drawing ## Basic Information - **Project Name**: 点位图绘制 - **Description**: 专注于点位图绘制的开源项目,提供高效、精准的绘图工具和丰富的图形库,适用于地图标注、设计布局等多种场景。 - **Primary Language**: TypeScript - **License**: Apache-2.0 - **Default Branch**: main - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2025-11-07 - **Last Updated**: 2026-07-16 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # 点位图绘制器 (PointMap Drawer) 一个基于 React + Konva 的点位图绘制工具,支持在 WebView 环境中使用,提供画笔绘制和图形绘制功能。 ## 📋 项目作用 点位图绘制器是一个轻量级的 Canvas 绘制组件,主要用于: - **点位图绘制**:支持在画布上绘制点位图,适用于地图标注、示意图绘制等场景 - **画笔工具**:提供自由画笔绘制功能,支持自定义颜色和粗细 - **图形工具**:支持绘制正方形、三角形、五角星、菱形等基础图形 - **WebView 集成**:专为 WebView 环境设计,支持 React Native WebView 和浏览器 iframe 集成 - **数据导出**:支持导出为 base64 格式的图片数据 ## 🛠 技术栈 - **运行环境**: Node.js >= 20.19.0 或 >= 22.12.0 - **框架**: React 19.1.1 - **语言**: TypeScript 5.9.3 - **构建工具**: Vite 7.1.7 - **Canvas 库**: Konva 10.0.8 + react-konva 19.2.0 - **代码规范**: ESLint + TypeScript ESLint ### 核心依赖 ```json { "react": "^19.1.1", "react-dom": "^19.1.1", "konva": "^10.0.8", "react-konva": "^19.2.0" } ``` ## 🔌 项目接口 ### 通信方式 项目支持两种通信方式: 1. **postMessage**(推荐):适用于 React Native WebView 和浏览器 iframe 2. **window.pointMapBridge**(备选):适用于浏览器同源环境 ### 消息类型 #### 父窗口 → WebView(请求消息) | 消息类型 | 说明 | Payload 格式 | | ----------------- | ------------ | -------------------------------------------------------- | | `SET_CANVAS_SIZE` | 设置画布尺寸 | `{ width: number, height: number }` | | `SET_TOOL` | 设置工具 | `'pen' \| 'square' \| 'triangle' \| 'star' \| 'diamond'` | | `SET_BRUSH_COLOR` | 设置画笔颜色 | `string` (颜色值,如 `"#204cff"`) | | `SET_BRUSH_SIZE` | 设置画笔大小 | `number` (2-10) | | `LOAD_SNAPSHOT` | 加载快照数据 | `{ lines: LineRecord[], shapes: ShapeRecord[] }` | | `UNDO` | 撤销操作 | 无 | | `CLEAR` | 清空画布 | 无 | | `EXPORT_IMAGE` | 导出图片 | 无(返回响应消息) | | `GET_STATUS` | 获取状态 | 无(返回响应消息) | | `GET_SNAPSHOT` | 获取快照 | 无(返回响应消息) | #### WebView → 父窗口(响应消息) | 消息类型 | 说明 | Payload 格式 | | ----------------------- | ------------ | --------------------------------------------------------------------------------------------------------------- | | `EXPORT_IMAGE_RESPONSE` | 导出图片响应 | `{ dataUrl: string, width: number, height: number }` | | `GET_STATUS_RESPONSE` | 获取状态响应 | `{ hasContent: boolean, canUndo: boolean, activeTool: Tool, viewScale: number, width: number, height: number }` | | `GET_SNAPSHOT_RESPONSE` | 获取快照响应 | `{ lines: LineRecord[], shapes: ShapeRecord[] }` | ### 消息格式 ```typescript interface PointMapMessage { type: MessageType; payload?: any; requestId?: string; // 可选,用于匹配请求和响应 } ``` ### window.pointMapBridge 接口 ```typescript interface PointMapBridge { setTool: (tool: Tool) => void; setBrushColor: (color: string) => void; setBrushSize: (size: number) => void; loadSnapshot: (snapshot: Snapshot | null | undefined) => void; undo: () => void; clear: () => void; setCanvasSize: (width: number, height: number) => void; exportImage: () => ExportImageResult | Promise | null; getStatus: () => { hasContent; canUndo; activeTool; viewScale; width; height; }; getSnapshot: () => Snapshot; onExport?: (payload: ExportImageResult) => void; } ``` ## 📐 规范 ### 代码规范 - 使用 TypeScript 严格模式 - 遵循 ESLint 规则 - 组件使用函数式组件 + Hooks - 样式使用 CSS Modules ### 文件结构 ``` src/pages/PointMapDrawer/ ├── components/ # UI 组件 │ ├── BottomSheet/ # 底部设置面板 │ ├── CanvasArea/ # 画布区域 │ ├── ToolPanel/ # 工具面板 │ ├── TopBar/ # 顶部工具栏 │ └── ZoomIndicator/ # 缩放指示器 ├── hooks/ # 自定义 Hooks │ ├── useBridge.ts # WebView 通信 │ ├── useCanvas.ts # 画布操作 │ ├── useDrawing.ts # 绘制逻辑 │ ├── useHistory.ts # 历史记录 │ ├── useShapes.ts # 图形操作 │ └── useViewport.ts # 视口管理 ├── utils/ # 工具函数 │ ├── messageHandler.ts # 消息处理 │ ├── pathSimplifier.ts # 路径简化 │ └── shapeFactory.ts # 图形工厂 ├── constants.ts # 常量定义 ├── types.ts # 类型定义 └── PointMapDrawerPage.tsx # 主页面 ``` ### 常量配置 ```typescript // 画布默认尺寸 DEFAULT_CANVAS_WIDTH = 750; DEFAULT_CANVAS_HEIGHT = 1334; // 画笔大小选项 BRUSH_SIZES = [2, 4, 6, 10]; // 画笔颜色选项 BRUSH_COLORS = ["#204cff", "#ff6b6b", "#00b894", "#ffb341", "#222428"]; // 图形大小选项 SHAPE_SIZES = [40, 60, 80, 100, 120]; // 缩放范围 SCALE_RANGE = { min: 0.4, max: 3 }; ``` ## 🚀 具体用法 ### 环境要求 - **Node.js**: >= 20.19.0 或 >= 22.12.0(Vite 7.1.7 要求) - **包管理器**: npm、pnpm 或 yarn > 💡 **提示**: 使用 `node --version` 检查当前 Node.js 版本。如果版本不符合要求,请使用 [nvm](https://github.com/nvm-sh/nvm) 或 [fnm](https://github.com/Schniz/fnm) 切换 Node.js 版本。 ### 安装依赖 ```bash npm install # 或 pnpm install ``` ### 开发运行 ```bash npm run dev # 或 pnpm dev ``` ### 构建生产版本 ```bash npm run build # 或 pnpm build ``` ### React Native WebView 集成 ```typescript import { WebView } from "react-native-webview"; import { useRef } from "react"; const PointMapScreen = () => { const webviewRef = useRef(null); // 设置画布尺寸 const setCanvasSize = (width: number, height: number) => { webviewRef.current?.postMessage( JSON.stringify({ type: "SET_CANVAS_SIZE", payload: { width, height }, }) ); }; // 设置工具 const setTool = ( tool: "pen" | "square" | "triangle" | "star" | "diamond" ) => { webviewRef.current?.postMessage( JSON.stringify({ type: "SET_TOOL", payload: tool, }) ); }; // 设置画笔颜色 const setBrushColor = (color: string) => { webviewRef.current?.postMessage( JSON.stringify({ type: "SET_BRUSH_COLOR", payload: color, }) ); }; // 导出图片 const exportImage = () => { webviewRef.current?.postMessage( JSON.stringify({ type: "EXPORT_IMAGE", }) ); }; // 监听 WebView 消息 const handleMessage = (event: any) => { try { const message = JSON.parse(event.nativeEvent.data); if (message.type === "EXPORT_IMAGE_RESPONSE") { const { dataUrl, width, height } = message.payload; console.log("图片导出成功:", dataUrl); // 处理图片数据 } else if (message.type === "GET_STATUS_RESPONSE") { console.log("状态:", message.payload); } } catch (error) { console.error("解析消息失败:", error); } }; return ( ); }; ``` ### 浏览器 iframe 集成 ```html 点位图绘制器 ``` ### 使用 window.pointMapBridge(浏览器同源环境) ```javascript // 等待 bridge 初始化 function waitForBridge(callback) { if (window.pointMapBridge) { callback(window.pointMapBridge); } else { setTimeout(() => waitForBridge(callback), 100); } } waitForBridge((bridge) => { // 设置画布尺寸 bridge.setCanvasSize(750, 1334); // 设置工具 bridge.setTool("pen"); // 设置画笔颜色 bridge.setBrushColor("#204cff"); // 设置画笔大小 bridge.setBrushSize(6); // 监听导出事件 bridge.onExport = (result) => { console.log("图片导出:", result.dataUrl); }; // 导出图片 bridge.exportImage(); // 获取状态 const status = bridge.getStatus(); console.log("状态:", status); // 获取快照 const snapshot = bridge.getSnapshot(); console.log("快照:", snapshot); // 加载快照 bridge.loadSnapshot(snapshot); // 撤销 bridge.undo(); // 清空 bridge.clear(); }); ``` ## 📝 功能特性 - ✅ 画笔绘制:支持自由绘制,自动路径简化 - ✅ 图形绘制:支持正方形、三角形、五角星、菱形 - ✅ 图形编辑:支持拖拽、旋转、缩放 - ✅ 撤销功能:支持操作历史记录和撤销 - ✅ 清空功能:一键清空画布 - ✅ 保存导出:导出为 base64 格式图片 - ✅ 画布适配:自动适应屏幕尺寸 - ✅ 缩放功能:支持鼠标滚轮和手势缩放 - ✅ 响应式设计:适配移动端和桌面端 - ✅ WebView 通信:支持 React Native 和浏览器环境 ## 📄 License MIT