feat: 9-position dock grid (4 corners + 4 edges + center)

This commit is contained in:
Hermes Agent committed 2026-09-09 17:54:53 +02:00
1 parent 0aeaf9f831
commit d29654b8d5
2 files changed
+36 -12

No files matched your search

+19 -7
View File
@@ -12,25 +12,37 @@ export default function () {
// Пока не null — позиция пересчитывается при каждом изменении viewport
// (через поллинг, т.к. события viewportchange в API нет), иначе
// canvas-space-точка "уплывает" на экране при смене зума/пана.
let dockedPosition: 'left' | 'right' | 'center' | null = null
let dockedPosition: DockPosition | null = null
// 9 позиций докинга: 4 угла + 4 края + центр.
type DockPosition =
| 'top-left' | 'top-center' | 'top-right'
| 'center-left' | 'center' | 'center-right'
| 'bottom-left' | 'bottom-center' | 'bottom-right'
// Прижать окно к краю видимой области canvas (bounds) в canvas-space.
// ВАЖНО: reposition()/getPosition() и bounds — в canvas-space (единицы документа),
// а figma.ui.resize(width,height) — в ЭКРАННЫХ пикселях. Размер окна в canvas-units =
// width / zoom. Без этого деления при zoom≠100% окно прижимается с ошибкой
// (px-размер вычитается из canvas-ширины → уезжает пропорционально 1/zoom).
function applyDock (position: 'left' | 'right' | 'center', width: number, height: number) {
function applyDock (position: DockPosition, width: number, height: number) {
const b = figma.viewport.bounds
const zoom = figma.viewport.zoom || 1
const wCanvas = width / zoom
const hCanvas = height / zoom
let x = b.x
let y = b.y
if (position === 'right') {
x = b.x + b.width - wCanvas
} else if (position === 'center') {
// По горизонтали
if (position === 'top-center' || position === 'center' || position === 'bottom-center') {
x = b.x + (b.width - wCanvas) / 2
} else if (position === 'top-right' || position === 'center-right' || position === 'bottom-right') {
x = b.x + b.width - wCanvas
}
// По вертикали
if (position === 'center-left' || position === 'center' || position === 'center-right') {
y = b.y + (b.height - hCanvas) / 2
} else if (position === 'bottom-left' || position === 'bottom-center' || position === 'bottom-right') {
y = b.y + b.height - hCanvas
}
figma.ui.reposition(x, y)
}
@@ -77,8 +89,8 @@ export default function () {
}
})
// Эмуляция докинга: прижать окно к краям canvas (left/right/center).
on('DOCK_WINDOW', function (payload: { position: 'left' | 'right' | 'center'; width: number; height: number }) {
// Эмуляция докинга: прижать окно к краям canvas (9 позиций).
on('DOCK_WINDOW', function (payload: { position: DockPosition; width: number; height: number }) {
const { position } = payload
const { width, height } = clampWindowSize(payload)
lastSize = { width, height }
+17 -5
View File
@@ -201,7 +201,13 @@ function Plugin () {
refreshInfo()
}
function dockWindow (position: 'left' | 'right' | 'center') {
// 9 позиций докинга: 4 угла + 4 края + центр.
type DockPosition =
| 'top-left' | 'top-center' | 'top-right'
| 'center-left' | 'center' | 'center-right'
| 'bottom-left' | 'bottom-center' | 'bottom-right'
function dockWindow (position: DockPosition) {
emit('DOCK_WINDOW', {
position,
width: currentWindowSize.width,
@@ -240,10 +246,16 @@ function Plugin () {
</IconButton>
</div>
</div>
<div style={{ display: 'flex', gap: '4px', flexWrap: 'wrap' }}>
<Button onClick={function () { dockWindow('left') }}>◧ Лево</Button>
<Button onClick={function () { dockWindow('center') }}>▣ Центр</Button>
<Button onClick={function () { dockWindow('right') }}>Право ◨</Button>
<div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: '4px' }}>
<Button onClick={function () { dockWindow('top-left') }}>◤</Button>
<Button onClick={function () { dockWindow('top-center') }}>▬</Button>
<Button onClick={function () { dockWindow('top-right') }}>◥</Button>
<Button onClick={function () { dockWindow('center-left') }}>▏</Button>
<Button onClick={function () { dockWindow('center') }}>⊕</Button>
<Button onClick={function () { dockWindow('center-right') }}>▕</Button>
<Button onClick={function () { dockWindow('bottom-left') }}>◣</Button>
<Button onClick={function () { dockWindow('bottom-center') }}>▭</Button>
<Button onClick={function () { dockWindow('bottom-right') }}>◢</Button>
</div>
<div
style={{