image-annotation-drawer 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md ADDED
@@ -0,0 +1,59 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
+ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
+
8
+ ## [Unreleased]
9
+
10
+ ### Added - 标注选中与移动功能
11
+
12
+ - **选中功能**:
13
+ - 点击标注即可选中(青色虚线边框 + 四个角控制点)
14
+ - 支持矩形和多边形标注的选中
15
+ - 碰撞检测(点在矩形内、射线法检测点在多边形内)
16
+ - 支持负宽高矩形的检测(从右下往左上画的情况)
17
+ - **移动功能**:
18
+ - 拖拽选中的标注即可移动位置
19
+ - 实时渲染,流畅体验
20
+ - **快捷操作**:
21
+ - Delete / Backspace - 删除选中的标注
22
+ - ESC - 取消选中
23
+ - 点击空白处 - 取消选中
24
+ - 切换绘制模式自动取消选中
25
+ - **新增 API**:
26
+ - `selectAnnotation(index)` - 选中指定索引的标注
27
+ - `deselectAnnotation()` - 取消选中
28
+ - `getSelectedAnnotation()` - 获取当前选中的标注
29
+ - `deleteSelectedAnnotation()` - 删除选中的标注
30
+ - `moveSelectedAnnotation(dx, dy)` - 移动选中的标注
31
+
32
+ ### Improved - 文本标注易用性优化
33
+
34
+ - **默认空文本**:添加文本标注时默认为空字符串,不再是"双击编辑文字"
35
+ - **视觉优化**:
36
+ - 圆角背景 + 阴影效果
37
+ - 编辑状态青色发光边框
38
+ - 选中时半透明背景高亮
39
+ - 输入框美观样式(圆角、阴影、占位符)
40
+ - **快捷操作**:
41
+ - Enter - 完成编辑
42
+ - ESC - 取消编辑,恢复原状
43
+ - Delete(文本为空时)- 删除标注
44
+ - **智能删除**:清空文本后确认,自动删除标注
45
+ - **自适应输入框**:输入时自动调整宽度适应内容
46
+ - **自动选中文本**:进入编辑模式时自动选中文本,方便直接替换
47
+
48
+ ## [1.0.0] - 2024-03-05
49
+
50
+ ### Added
51
+ - Initial release
52
+ - Support for rectangle annotations
53
+ - Support for polygon annotations
54
+ - Support for text annotations
55
+ - Zoom and pan functionality
56
+ - Undo operation (Ctrl+Z)
57
+ - Export annotated images
58
+ - Keyboard shortcuts
59
+ - TypeScript support
@@ -0,0 +1,147 @@
1
+ # Contributing to Image Annotation Drawer
2
+
3
+ 感谢你对 Image Annotation Drawer 的兴趣!我们欢迎各种形式的贡献。
4
+
5
+ ## 如何贡献
6
+
7
+ ### 报告问题
8
+
9
+ 如果你发现了 bug 或有功能建议,请通过 [GitHub Issues](https://github.com/KangLinDDD/ADrawer/issues) 提交。\n
10
+ 提交问题时请包含:
11
+ - 问题的清晰描述
12
+ - 复现步骤
13
+ - 期望行为 vs 实际行为
14
+ - 浏览器环境和版本
15
+ - 如果有截图会更好
16
+
17
+ ### 提交代码
18
+
19
+ 1. **Fork 仓库**
20
+ ```bash
21
+ # 点击 GitHub 上的 Fork 按钮
22
+ ```
23
+
24
+ 2. **克隆你的 Fork**
25
+ ```bash
26
+ git clone https://github.com/YOUR_USERNAME/ADrawer.git
27
+ cd ADrawer
28
+ ```
29
+
30
+ 3. **创建分支**
31
+ ```bash
32
+ git checkout -b feature/your-feature-name
33
+ # 或
34
+ git checkout -b fix/your-bug-fix
35
+ ```
36
+
37
+ 4. **安装依赖并开发**
38
+ ```bash
39
+ npm install
40
+ npm run dev
41
+ ```
42
+
43
+ 5. **确保代码质量**
44
+ ```bash
45
+ npm run lint
46
+ npm test
47
+ npm run build
48
+ ```
49
+
50
+ 6. **提交更改**
51
+ ```bash
52
+ git add .
53
+ git commit -m "feat: add some feature"
54
+ ```
55
+
56
+ 7. **推送到你的 Fork**
57
+ ```bash
58
+ git push origin feature/your-feature-name
59
+ ```
60
+
61
+ 8. **创建 Pull Request**
62
+ - 访问 https://github.com/KangLinDDD/ADrawer/pulls
63
+ - 点击 "New Pull Request"
64
+ - 选择你的分支
65
+
66
+ ## 提交规范
67
+
68
+ 我们使用 [Conventional Commits](https://www.conventionalcommits.org/) 规范:
69
+
70
+ - `feat:` 新功能
71
+ - `fix:` Bug 修复
72
+ - `docs:` 文档更新
73
+ - `style:` 代码格式(不影响功能的更改)
74
+ - `refactor:` 代码重构
75
+ - `test:` 测试相关
76
+ - `chore:` 构建过程或辅助工具的变动
77
+
78
+ 示例:
79
+ ```bash
80
+ git commit -m "feat: add polygon vertex deletion"
81
+ git commit -m "fix: correct text annotation vertical alignment"
82
+ git commit -m "docs: update API reference for selection"
83
+ ```
84
+
85
+ ## 开发指南
86
+
87
+ ### 项目结构
88
+
89
+ ```
90
+ src/
91
+ ├── index.ts # 主入口
92
+ ├── modules/
93
+ │ ├── types.ts # 类型定义
94
+ │ ├── viewport.ts # 视口管理
95
+ │ ├── annotations.ts # 标注管理
96
+ │ ├── text-annotation.ts # 文本标注
97
+ │ ├── renderer.ts # 渲染器
98
+ │ ├── events.ts # 事件处理
99
+ │ └── utils.ts # 工具函数
100
+ __tests__/ # 测试文件
101
+ examples/ # 示例
102
+ ```
103
+
104
+ ### 代码风格
105
+
106
+ - 使用 TypeScript
107
+ - 2 空格缩进
108
+ - 单引号
109
+ - 分号必需
110
+ - 尾随逗号
111
+
112
+ ### 测试
113
+
114
+ - 新功能需要添加测试
115
+ - 所有测试必须通过
116
+ - 测试覆盖率应保持在合理水平
117
+
118
+ 运行测试:
119
+ ```bash
120
+ npm test # 运行所有测试
121
+ npm run test:watch # 监视模式
122
+ npm run test:coverage # 生成覆盖率报告
123
+ ```
124
+
125
+ ## 发布流程
126
+
127
+ 维护者使用以下流程发布新版本:
128
+
129
+ 1. 更新 `CHANGELOG.md`
130
+ 2. 更新版本号:`npm version patch|minor|major`
131
+ 3. 推送到 GitHub:`git push && git push --tags`
132
+ 4. 创建 Release,CI 会自动发布到 npm
133
+
134
+ ## 行为准则
135
+
136
+ - 保持友好和尊重
137
+ - 欢迎新手,耐心解答问题
138
+ - 专注于技术讨论
139
+ - 接受不同的观点和经验
140
+
141
+ ## 获取帮助
142
+
143
+ - 查看 [README](./README.md) 和 [文档](https://kanglinddd.github.io/ADrawer/)
144
+ - 在 [GitHub Discussions](https://github.com/KangLinDDD/ADrawer/discussions) 提问
145
+ - 加入我们的社区
146
+
147
+ 再次感谢你的贡献!
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,291 @@
1
+ # Image Annotation Drawer
2
+
3
+ > A lightweight, dependency-free image annotation library for the web
4
+
5
+ [English](./README.md) | [中文](./README.zh-CN.md)
6
+
7
+ [![npm version](https://badge.fury.io/js/image-annotation-drawer.svg)](https://www.npmjs.com/package/image-annotation-drawer)
8
+ [![Build Status](https://github.com/KangLinDDD/ADrawer/workflows/Test/badge.svg)](https://github.com/KangLinDDD/ADrawer/actions)
9
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
10
+
11
+ ## Features
12
+
13
+ - 🎨 **Multiple Annotation Types**: Rectangle, Polygon, Text annotations
14
+ - 🔍 **Viewport Operations**: Mouse wheel zoom, drag to pan
15
+ - 🎯 **Selection & Editing**: Select, move, resize, delete annotations
16
+ - 🎨 **Independent Styling**: Each annotation can have its own style
17
+ - ↩️ **Undo/Redo**: Support for withdrawing operations
18
+ - 💾 **Export**: Export annotated images in original or current view
19
+ - ⌨️ **Keyboard Shortcuts**: Space to reset view, ESC to cancel, Delete to remove
20
+ - 📱 **TypeScript**: Full type support
21
+ - 🪶 **Zero Dependencies**: Lightweight, no external dependencies
22
+
23
+ ## Installation
24
+
25
+ ```bash
26
+ npm install image-annotation-drawer
27
+ ```
28
+
29
+ ```bash
30
+ yarn add image-annotation-drawer
31
+ ```
32
+
33
+ ```bash
34
+ pnpm add image-annotation-drawer
35
+ ```
36
+
37
+ ## Quick Start
38
+
39
+ ### Basic Usage
40
+
41
+ ```typescript
42
+ import Drawer from 'image-annotation-drawer';
43
+
44
+ // Initialize
45
+ const drawer = new Drawer({
46
+ id: 'container', // Container element ID
47
+ drawType: 'rect', // Default draw type: 'rect' | 'polygon' | 'drag' | 'text' | ''
48
+ useEvents: true, // Enable mouse/keyboard events
49
+ });
50
+
51
+ // Load image
52
+ drawer.drawImage('https://example.com/image.jpg');
53
+
54
+ // Add text annotation programmatically
55
+ drawer.addTextAnnotation(100, 100, 'Hello World');
56
+
57
+ // Get all annotations
58
+ const annotations = drawer.getAnnotations();
59
+ const textAnnotations = drawer.getTextAnnotations();
60
+
61
+ // Export
62
+ drawer.exportAnnotationImage().then(base64 => {
63
+ console.log(base64); // data:image/jpeg;base64,...
64
+ });
65
+ ```
66
+
67
+ ### HTML Setup
68
+
69
+ ```html
70
+ <div id="container" style="width: 800px; height: 600px;"></div>
71
+ ```
72
+
73
+ ## API Reference
74
+
75
+ ### Constructor Options
76
+
77
+ ```typescript
78
+ interface DrawerOptions {
79
+ id: string; // Container element ID (required)
80
+ drawType?: DrawType; // Default draw type
81
+ useEvents?: boolean; // Enable events (default: true)
82
+ annotationColor?: string | ColorConfig; // Annotation colors
83
+ lineStyle?: LineStyle; // Line style: 'solid' | 'dashed' | 'dotted'
84
+ vertexStyle?: Partial<VertexStyle>; // Vertex style
85
+ textStyle?: Partial<TextStyle>; // Text style
86
+ }
87
+ ```
88
+
89
+ ### Draw Types
90
+
91
+ | Type | Description |
92
+ |------|-------------|
93
+ | `'rect'` | Draw rectangles |
94
+ | `'polygon'` | Draw polygons (click to add points, double-click to finish) |
95
+ | `'drag'` | Drag to pan the image |
96
+ | `'text'` | Click to add text annotations |
97
+ | `''` | Default mode (selection) |
98
+
99
+ ### Methods
100
+
101
+ #### Draw Type
102
+ ```typescript
103
+ drawer.setDrawType('rect'); // Switch draw type
104
+ ```
105
+
106
+ #### Image
107
+ ```typescript
108
+ drawer.drawImage('image.jpg'); // Load image
109
+ drawer.changeScale(true); // Zoom in
110
+ drawer.changeScale(false); // Zoom out
111
+ ```
112
+
113
+ #### Annotations
114
+ ```typescript
115
+ // Text annotations
116
+ drawer.addTextAnnotation(x, y, text);
117
+ drawer.updateTextAnnotation(index, text);
118
+ drawer.moveTextAnnotation(index, x, y);
119
+ drawer.removeTextAnnotation(index);
120
+ drawer.clearTextAnnotations();
121
+
122
+ // Selection
123
+ drawer.selectAnnotation(index);
124
+ drawer.deselectAnnotation();
125
+ drawer.deleteSelectedAnnotation();
126
+ drawer.moveSelectedAnnotation(dx, dy);
127
+
128
+ // Get data
129
+ const annotations = drawer.getAnnotations();
130
+ const textAnnotations = drawer.getTextAnnotations();
131
+ const selected = drawer.getSelectedAnnotation();
132
+ ```
133
+
134
+ #### Styling
135
+ ```typescript
136
+ // Annotation colors
137
+ drawer.setAnnotationColor('#FF0000');
138
+ drawer.setAnnotationColor({
139
+ rect: '#FF0000',
140
+ polygon: '#00FF00',
141
+ default: '#0000FF'
142
+ });
143
+
144
+ // Line style
145
+ drawer.setLineStyle('dashed'); // 'solid' | 'dashed' | 'dotted'
146
+
147
+ // Vertex style
148
+ drawer.setVertexStyle({
149
+ size: 8,
150
+ fillColor: '#FF0000',
151
+ strokeColor: '#FFFFFF',
152
+ strokeWidth: 2,
153
+ shape: 'circle' // 'circle' | 'square' | 'diamond'
154
+ });
155
+
156
+ // Text style
157
+ drawer.setTextStyle({
158
+ font: '16px Arial',
159
+ color: '#FFD700',
160
+ backgroundColor: 'rgba(0,0,0,0.6)',
161
+ padding: 6
162
+ });
163
+
164
+ // Update selected annotation's style
165
+ drawer.updateSelectedAnnotationStyle();
166
+ ```
167
+
168
+ #### Export
169
+ ```typescript
170
+ // Export original size
171
+ drawer.exportAnnotationImage().then(base64 => { ... });
172
+
173
+ // Export current view
174
+ drawer.exportCurrentViewImage().then(base64 => { ... });
175
+
176
+ // Convert to File
177
+ const file = drawer.base64ToFile(base64, 'annotation.jpg');
178
+ ```
179
+
180
+ #### Clear & Undo
181
+ ```typescript
182
+ drawer.clear(); // Clear all, set draw type to ''
183
+ drawer.clear('rect'); // Clear all, set draw type to 'rect'
184
+ drawer.clearCanvas(); // Clear everything including image
185
+ drawer.clearAnnotations(); // Clear annotations only, keep image
186
+ drawer.withdraw(); // Undo last operation
187
+ ```
188
+
189
+ #### Destroy
190
+ ```typescript
191
+ drawer.destroy(); // Clean up resources
192
+ ```
193
+
194
+ ### Keyboard Shortcuts
195
+
196
+ | Key | Action |
197
+ |-----|--------|
198
+ | `Space` | Reset view to initial state |
199
+ | `ESC` | Cancel current drawing / deselect |
200
+ | `Delete` / `Backspace` | Delete selected annotation |
201
+ | `Ctrl+Z` | Undo delete (for text annotations) |
202
+
203
+ ## Advanced Usage
204
+
205
+ ### Custom Styles Per Annotation
206
+
207
+ ```typescript
208
+ // Set global style for new annotations
209
+ drawer.setAnnotationColor('#00FF00');
210
+ drawer.setLineStyle('dashed');
211
+
212
+ // Add annotation - it will use current global style
213
+ drawer.setDrawType('rect');
214
+ // ... draw rectangle ...
215
+
216
+ // Change style - only affects future annotations
217
+ drawer.setAnnotationColor('#FF0000');
218
+ drawer.setLineStyle('solid');
219
+
220
+ // To update existing annotation's style:
221
+ drawer.selectAnnotation(0);
222
+ drawer.setAnnotationColor('#0000FF');
223
+ drawer.updateSelectedAnnotationStyle(); // Save style to selected annotation
224
+ ```
225
+
226
+ ### Event Handling
227
+
228
+ ```typescript
229
+ // Disable default events and handle manually
230
+ const drawer = new Drawer({
231
+ id: 'container',
232
+ useEvents: false // Disable default event binding
233
+ });
234
+
235
+ // Add events manually when needed
236
+ drawer.addEventListeners();
237
+ ```
238
+
239
+ ### TypeScript Support
240
+
241
+ ```typescript
242
+ import Drawer, {
243
+ Rect,
244
+ Polygon,
245
+ TextAnnotation,
246
+ DrawerOptions,
247
+ VertexStyle
248
+ } from 'image-annotation-drawer';
249
+
250
+ const options: DrawerOptions = {
251
+ id: 'container',
252
+ drawType: 'rect',
253
+ vertexStyle: {
254
+ size: 10,
255
+ shape: 'diamond'
256
+ } as Partial<VertexStyle>
257
+ };
258
+
259
+ const drawer = new Drawer(options);
260
+ ```
261
+
262
+ ## Browser Support
263
+
264
+ - Chrome 60+
265
+ - Firefox 60+
266
+ - Safari 12+
267
+ - Edge 79+
268
+
269
+ ## Examples
270
+
271
+ - **Live Demo (English)**: https://kanglinddd.github.io/ADrawer/
272
+ - **在线演示 (中文)**: https://kanglinddd.github.io/ADrawer/zh.html
273
+ - **Source**: See the `examples/` directory for complete working examples.
274
+
275
+ ## Contributing
276
+
277
+ Contributions are welcome! Please feel free to submit a Pull Request.
278
+
279
+ 1. Fork the repository (https://github.com/KangLinDDD/ADrawer/fork)
280
+ 2. Create your feature branch (`git checkout -b feature/AmazingFeature`)
281
+ 3. Commit your changes (`git commit -m 'Add some AmazingFeature'`)
282
+ 4. Push to the branch (`git push origin feature/AmazingFeature`)
283
+ 5. Open a Pull Request (https://github.com/KangLinDDD/ADrawer/pulls)
284
+
285
+ ## License
286
+
287
+ This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
288
+
289
+ ## Changelog
290
+
291
+ See [CHANGELOG.md](CHANGELOG.md) for version history.