fix(viewport): properly truncate to size (#228)

There are many "interesting" cases:

- logical content is wider than display width (long lines).
  In this case, we truncate.
- logical content is smaller than display height (fewer lines
  than visible).
  In this case, we pad with empty lines up to the specified height.
- logical content is higher than display height (more lines than
  visible).
  In this case, we truncate.

- style specifies a width wider than the display width.
  In this case, we ignore the style width and
  fit in the display width.
- style specifies a height higher than the display height.
  Same as width, we ignore the style and fit in the display height.
- style specifies a narrower width or smaller height than the display.
  In this case we obey the style.
This commit is contained in:
Raphael 'kena' Poss 2022-09-02 21:50:33 +02:00 committed by GitHub
parent 09e1f00349
commit 278edd1c2b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -350,10 +350,23 @@ func (m Model) View() string {
return strings.Repeat("\n", max(0, m.Height-1))
}
return m.Style.Copy().
Width(m.Width - m.Style.GetHorizontalFrameSize()).
Height(m.Height - m.Style.GetVerticalFrameSize()).
w, h := m.Width, m.Height
if sw := m.Style.GetWidth(); sw != 0 {
w = min(w, sw)
}
if sh := m.Style.GetHeight(); sh != 0 {
h = min(h, sh)
}
contentWidth := w - m.Style.GetHorizontalFrameSize()
contentHeight := h - m.Style.GetVerticalFrameSize()
contents := lipgloss.NewStyle().
Height(contentHeight). // pad to height.
MaxHeight(contentHeight). // truncate height if taller.
MaxWidth(contentWidth). // truncate width.
Render(strings.Join(m.visibleLines(), "\n"))
return m.Style.Copy().
UnsetWidth().UnsetHeight(). // Style size already applied in contents.
Render(contents)
}
func clamp(v, low, high int) int {