add per-pane display ownership

This commit is contained in:
2026-05-27 14:30:47 +01:00
parent 63cb8a4388
commit 6d15626e05
9 changed files with 333 additions and 36 deletions

View File

@@ -134,6 +134,8 @@ type netClient struct {
mu sync.Mutex
focusedID string
paneSize protocol.Size
ownerView bool
chrome chromeModel
renderer *viewportRenderer
palette *clientCommandPrompt
@@ -287,10 +289,13 @@ func (c *netClient) handleFrame(f protocol.Frame) error {
}
c.mu.Lock()
c.focusedID = msg.PaneID
c.renderer = newViewportRenderer(c.layout)
c.paneSize = msg.Size
c.ownerView = msg.DisplayOwner
c.renderer = newViewportRenderer(c.renderLayoutLocked(msg.Size))
renderer := c.renderer
c.mu.Unlock()
c.clearViewport()
c.drawChrome()
c.writeWrapped(renderer.Render(msg.Bytes))
case protocol.FramePaneChunk:
msg, err := protocol.Decode[protocol.PaneChunk](f)
@@ -300,6 +305,11 @@ func (c *netClient) handleFrame(f protocol.Frame) error {
c.mu.Lock()
focused := c.focusedID
renderer := c.renderer
c.paneSize = msg.Size
c.ownerView = msg.DisplayOwner
if renderer != nil && (msg.Size.Cols != 0 || msg.Size.Rows != 0) {
renderer.SetLayout(c.renderLayoutLocked(msg.Size))
}
c.mu.Unlock()
if msg.PaneID == focused && renderer != nil {
c.writeWrapped(renderer.Render(msg.Bytes))
@@ -508,7 +518,7 @@ func (c *netClient) resize(cols, rows uint16) error {
c.mu.Lock()
c.layout = newTerminalLayout(cols, rows)
if c.renderer != nil {
c.renderer.SetLayout(c.layout)
c.renderer.SetLayout(c.renderLayoutLocked(c.paneSize))
}
size := protocol.Size{Cols: c.layout.childCols(), Rows: c.layout.childRows()}
c.mu.Unlock()
@@ -519,6 +529,17 @@ func (c *netClient) resize(cols, rows uint16) error {
return c.t.Send(f)
}
func (c *netClient) renderLayoutLocked(size protocol.Size) terminalLayout {
l := c.layout
if size.Cols != 0 && size.Cols < l.mainCols {
l.mainCols = size.Cols
}
if size.Rows != 0 && size.Rows < l.mainRows {
l.mainRows = size.Rows
}
return l
}
func (c *netClient) enterScreen() {
_, _ = c.out.Write([]byte("\x1b[?1049h\x1b[H\x1b[2J\x1b[?25h\x1b[?1000h\x1b[?1006h"))
c.installScrollRegion()
@@ -589,6 +610,13 @@ func (c *netClient) drawChrome() {
if model.FocusedID != "" {
status = fmt.Sprintf("%s · %s", model.FocusedID, status)
}
c.mu.Lock()
size := c.paneSize
ownerView := c.ownerView
c.mu.Unlock()
if model.FocusedID != "" && !ownerView && size.Cols != 0 && size.Rows != 0 {
status = fmt.Sprintf("viewing at owner size %dx%d · %s", size.Cols, size.Rows, status)
}
if prompt != nil {
status = "command: " + string(prompt.buf)
}