Files
pos-system/microservices/.agent/skills/pencil-design/references/MCP_TOOLS.md
Ho Ngoc Hai 76d75c753b Migrate
2026-05-23 18:37:02 +07:00

6.6 KiB

MCP Pencil Tools Reference / Tham Chiếu MCP Pencil

Note

MCP Pencil cho phép tương tác realtime với Pencil editor thông qua các tools. Yêu cầu: Có file .pen đang mở trong Pencil editor.

Khi Nào Dùng MCP vs Build Scripts

Tác vụ MCP Pencil Build Scripts
Thiết kế UI realtime Dùng MCP
Xem screenshot get_screenshot
Lấy style guide get_style_guide
Build library từ Atomic scripts/build.py
Merge nhiều files scripts/build.py -m
Extract components scripts/extract-atomic.py

Tools Overview

1. Document Management

Tool Mục đích
open_document Mở file .pen hoặc tạo mới ("new")
get_editor_state Lấy state hiện tại: file đang mở, selection, components
get_variables Đọc design tokens (colors, spacing, typography)
set_variables Cập nhật design tokens

2. Design Operations

Tool Mục đích
batch_design Insert/Update/Replace/Copy/Move/Delete nodes
batch_get Đọc nodes theo ID hoặc search patterns
snapshot_layout Kiểm tra layout structure, tìm overlapping
find_empty_space_on_canvas Tìm vị trí trống để đặt frame mới

3. Guidelines & Inspiration

Tool Mục đích
get_guidelines Lấy hướng dẫn theo topic: design-system, landing-page, table, code, tailwind
get_style_guide_tags Liệt kê tags có sẵn cho style guide
get_style_guide Lấy style guide theo tags hoặc tên

4. Verification

Tool Mục đích
get_screenshot Chụp screenshot node để verify

5. Batch Operations

Tool Mục đích
search_all_unique_properties Tìm all unique values của properties
replace_all_matching_properties Thay thế properties matching

batch_design Operations

Operations trong batch_design dùng syntax đặc biệt:

// Insert (I) - Thêm node mới
binding=I(parent, {type: "frame", layout: "vertical", ...})

// Update (U) - Cập nhật properties (KHÔNG dùng cho children)
U(nodeId, {content: "New text", fill: "$--foreground"})
U(instanceId+"/childId", {content: "Override text"})

// Replace (R) - Thay thế node hoàn toàn (dùng cho slot content)
newNode=R(instanceId+"/slotId", {type: "text", content: "Custom"})

// Copy (C) - Copy node (tạo ref nếu reusable)
copiedNode=C(sourceId, parent, {positionDirection: "right", positionPadding: 100})

// Move (M) - Di chuyển node
M(nodeId, newParent, index)

// Delete (D) - Xóa node
D(nodeId)

// Generate Image (G) - Tạo image fill cho frame/rectangle
G(nodeId, "ai", "modern office workspace")  // AI generated
G(nodeId, "stock", "coffee shop interior")  // Stock photo

Quy Tắc Quan Trọng

Important

  • Mỗi I, C, R PHẢI có binding name
  • Dùng instanceId+"/childId" để override descendants
  • KHÔNG dùng U() cho descendants của node vừa Copy - dùng descendants trong Copy operation
  • Max 25 operations mỗi batch_design call

Workflow Chuẩn

1. Khởi Đầu

get_editor_state(include_schema: true)
→ Xác định file, selection, reusable components

2. Lấy Context

get_guidelines("design-system")  // Hoặc "landing-page"
get_variables()                   // Design tokens
batch_get(patterns: [{reusable: true}], readDepth: 2)  // Components

3. Thiết Kế

// Tạo placeholder frame trước
batch_design(`
screen=I(document, {type: "frame", placeholder: true, ...})
`)

// Thêm content
batch_design(`
sidebar=I("screenId", {type: "ref", ref: "SidebarComp"})
content=I("screenId", {type: "frame", ...})
...
`)

// Xóa placeholder khi xong
batch_design(`U("screenId", {placeholder: false})`)

4. Verify

get_screenshot(nodeId: "screenId")
→ Kiểm tra visual output

Ví Dụ: Dashboard Screen

// Batch 1: Structure
screen=I(document, {type: "frame", name: "Dashboard", layout: "horizontal", width: 1440, height: 900, fill: "$--background", placeholder: true})
sidebar=I(screen, {type: "ref", ref: "SidebarComp", height: "fill_container"})
main=I(screen, {type: "frame", layout: "vertical", width: "fill_container", height: "fill_container", padding: 32, gap: 24})

// Batch 2: Sidebar items
item1=I(sidebar+"/contentSlot", {type: "ref", ref: "SidebarItem", descendants: {"labelId": {content: "Dashboard"}}})
item2=I(sidebar+"/contentSlot", {type: "ref", ref: "SidebarItem", descendants: {"labelId": {content: "Users"}}})

// Batch 3: Main content
header=I("mainId", {type: "frame", layout: "horizontal", width: "fill_container", justifyContent: "space_between"})
title=I(header, {type: "text", content: "Dashboard", fontSize: 24, fontWeight: "600", fill: "$--foreground"})
cards=I("mainId", {type: "frame", layout: "horizontal", gap: 16})
card1=I(cards, {type: "ref", ref: "CardComp", width: "fill_container"})
card2=I(cards, {type: "ref", ref: "CardComp", width: "fill_container"})

// Batch 4: Finalize
U("screenId", {placeholder: false})

Common Patterns

Override Component Text

button=I(container, {type: "ref", ref: "ButtonComp"})
U(button+"/labelText", {content: "Submit"})

Replace Slot Content

card=I(container, {type: "ref", ref: "CardComp"})
customContent=R(card+"/contentSlot", {type: "frame", layout: "vertical", gap: 8, children: [
  {type: "text", content: "Custom Title", fontSize: 18},
  {type: "text", content: "Description", fontSize: 14}
]})

Add Image to Frame

heroFrame=I(container, {type: "frame", width: 600, height: 400})
G(heroFrame, "ai", "modern tech office, bright, professional")

Find Empty Space

find_empty_space_on_canvas(width: 1440, height: 900, padding: 100, direction: "right")
 Trả về {x, y} cho vị trí trống

Troubleshooting

Vấn đề Giải pháp
"A file needs to be open" Dùng open_document trước
Update descendants fail Dùng path: instanceId+"/childId"
Copy descendants fail Dùng descendants trong Copy, KHÔNG Update riêng
Nodes overlap Dùng find_empty_space_on_canvas
Layout broken Kiểm tra snapshot_layout(problemsOnly: true)