Skip to content

Commit

Permalink
Fix gutter overwriting other split pane
Browse files Browse the repository at this point in the history
When we resize a split pane to a very small width, so that the gutter
does not fit in the pane, it overwrites the sibling split pane.

To fix it, clean up the calculation of gutter width, buffer width and
scrollbar width, so that they add up exactly to the window width, and
ensure that we don't draw the gutter beyond this calculated gutter
width (gutterOffset).

As a bonus, this also fixes the crash zyedidia#3052 (observed when resizing a
split pane to a very small width, if wordwrap is enabled), by ensuring
that bufWidth is never negative.

[*] By the gutter we mean of course gutter + diffgutter + ruler.
  • Loading branch information
dmaluka committed Dec 3, 2023
1 parent d8e9d61 commit 614401a
Showing 1 changed file with 26 additions and 14 deletions.
40 changes: 26 additions & 14 deletions internal/display/bufwindow.go
Original file line number Diff line number Diff line change
Expand Up @@ -146,12 +146,18 @@ func (w *BufWindow) updateDisplayInfo() {
w.gutterOffset += w.maxLineNumLength + 1
}

prevBufWidth := w.bufWidth
scrollbarWidth := 0
if w.Buf.Settings["scrollbar"].(bool) && w.Buf.LinesNum() > w.Height && w.Width > 0 {
scrollbarWidth = 1
}

w.bufWidth = w.Width - w.gutterOffset
if w.Buf.Settings["scrollbar"].(bool) && w.Buf.LinesNum() > w.Height {
w.bufWidth--
if w.gutterOffset > w.Width {
w.gutterOffset = w.Width
}
w.gutterOffset -= scrollbarWidth

prevBufWidth := w.bufWidth
w.bufWidth = w.Width - w.gutterOffset - scrollbarWidth

if w.bufWidth != prevBufWidth && w.Buf.Settings["softwrap"].(bool) {
for _, c := range w.Buf.GetCursors() {
Expand Down Expand Up @@ -277,13 +283,17 @@ func (w *BufWindow) drawGutter(vloc *buffer.Loc, bloc *buffer.Loc) {
break
}
}
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, char, nil, s)
vloc.X++
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, char, nil, s)
vloc.X++
for i := 0; i < 2 && vloc.X < w.gutterOffset; i++ {
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, char, nil, s)
vloc.X++
}
}

func (w *BufWindow) drawDiffGutter(backgroundStyle tcell.Style, softwrapped bool, vloc *buffer.Loc, bloc *buffer.Loc) {
if vloc.X >= w.gutterOffset {
return
}

symbol := ' '
styleName := ""

Expand Down Expand Up @@ -319,26 +329,28 @@ func (w *BufWindow) drawLineNum(lineNumStyle tcell.Style, softwrapped bool, vloc
} else {
lineInt = bloc.Y - cursorLine
}
lineNum := strconv.Itoa(util.Abs(lineInt))
lineNum := []rune(strconv.Itoa(util.Abs(lineInt)))

// Write the spaces before the line number if necessary
for i := 0; i < w.maxLineNumLength-len(lineNum); i++ {
for i := 0; i < w.maxLineNumLength-len(lineNum) && vloc.X < w.gutterOffset; i++ {
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, ' ', nil, lineNumStyle)
vloc.X++
}
// Write the actual line number
for _, ch := range lineNum {
for i := 0; i < len(lineNum) && vloc.X < w.gutterOffset; i++ {
if softwrapped {
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, ' ', nil, lineNumStyle)
} else {
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, ch, nil, lineNumStyle)
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, lineNum[i], nil, lineNumStyle)
}
vloc.X++
}

// Write the extra space
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, ' ', nil, lineNumStyle)
vloc.X++
if vloc.X < w.gutterOffset {
screen.SetContent(w.X+vloc.X, w.Y+vloc.Y, ' ', nil, lineNumStyle)
vloc.X++
}
}

// getStyle returns the highlight style for the given character position
Expand Down

0 comments on commit 614401a

Please sign in to comment.