(x: number, y: number)
| 485 | // ─── Text Tool ──────────────────────────────────────────────── |
| 486 | |
| 487 | function showAnnotationTextInput(x: number, y: number): void { |
| 488 | if (annotationTextInput) { |
| 489 | annotationTextInput.remove(); |
| 490 | annotationTextInput = null; |
| 491 | } |
| 492 | if (!annotationOverlay || !annotationCanvas) return; |
| 493 | |
| 494 | const canvasRect = annotationCanvas.getBoundingClientRect(); |
| 495 | |
| 496 | const input = document.createElement('input'); |
| 497 | input.type = 'text'; |
| 498 | input.placeholder = 'Type text...'; |
| 499 | input.style.cssText = ` |
| 500 | position: fixed; |
| 501 | top: ${canvasRect.top + y}px; |
| 502 | left: ${canvasRect.left + x}px; |
| 503 | background: rgba(24, 24, 27, 0.9); |
| 504 | border: 1px solid #3f3f46; |
| 505 | border-radius: 4px; |
| 506 | color: ${annotationColor}; |
| 507 | font-size: 16px; |
| 508 | font-weight: 600; |
| 509 | font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif; |
| 510 | padding: 4px 8px; |
| 511 | outline: none; |
| 512 | z-index: 1000000; |
| 513 | min-width: 120px; |
| 514 | `; |
| 515 | |
| 516 | const textColor = annotationColor; |
| 517 | const textX = x; |
| 518 | const textY = y; |
| 519 | |
| 520 | input.addEventListener('keydown', (e) => { |
| 521 | if (e.key === 'Enter') { |
| 522 | const text = input.value.trim(); |
| 523 | if (text && annotationCtx && annotationCanvas) { |
| 524 | // Save undo snapshot |
| 525 | const snapshot = annotationCtx.getImageData(0, 0, annotationCanvas.width, annotationCanvas.height); |
| 526 | annotationSnapshots.push(snapshot); |
| 527 | |
| 528 | annotationCtx.fillStyle = textColor; |
| 529 | annotationCtx.font = '600 16px -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif'; |
| 530 | annotationCtx.fillText(text, textX, textY + 16); |
| 531 | } |
| 532 | input.remove(); |
| 533 | annotationTextInput = null; |
| 534 | } |
| 535 | if (e.key === 'Escape') { |
| 536 | input.remove(); |
| 537 | annotationTextInput = null; |
| 538 | } |
| 539 | }); |
| 540 | |
| 541 | annotationOverlay.appendChild(input); |
| 542 | annotationTextInput = input; |
| 543 | input.focus(); |
| 544 | } |
no outgoing calls
no test coverage detected