mirror of
https://github.com/jesseduffield/lazygit.git
synced 2026-10-27 23:50:17 -05:00
Show the diff view's narrow selection bar on the right edge too
This is an improvement for users who use a side-by-side diff renderer on a very large screen; in this scenario it was hard to see which hunk on the right side was selected.
This commit is contained in:
1 parent
a5bf29e092
commit
96f93ec79d
2 files changed
+37
-9
No files matched your search
+13
-9
@@ -174,9 +174,11 @@ type View struct {
|
||||
HighlightInactive bool
|
||||
|
||||
// If SelectedLineColorWidth is greater than zero, a highlighted line is painted
|
||||
// in the selection colors on that many columns at its left edge only, rather
|
||||
// than across its whole width, leaving the line's own colors to show through.
|
||||
// For content that conveys meaning by color of its own.
|
||||
// in the selection colors on that many columns at its left and right edges only,
|
||||
// rather than across its whole width, leaving the line's own colors to show
|
||||
// through. For content that conveys meaning by color of its own. A double-width
|
||||
// character that reaches into these columns is painted whole, so the colored part
|
||||
// can be a column wider.
|
||||
SelectedLineColorWidth int
|
||||
|
||||
// InclusionGutterMarker is the glyph the inclusion gutter draws on a marked line
|
||||
@@ -936,8 +938,8 @@ func (v *View) InclusionGutterWidthWhenShown() int {
|
||||
|
||||
// setCharacter sets a character (grapheme cluster) at the given point relative to the view. It applies
|
||||
// the specified colors, taking into account if the cell must be highlighted. Also, it checks if the
|
||||
// position is valid.
|
||||
func (v *View) setCharacter(x, y int, ch string, fgColor, bgColor Attribute, isWindowFocused bool) {
|
||||
// position is valid. width is the number of columns the character takes up.
|
||||
func (v *View) setCharacter(x, y int, ch string, width int, fgColor, bgColor Attribute, isWindowFocused bool) {
|
||||
maxX, maxY := v.Size()
|
||||
if x < 0 || x >= maxX || y < 0 || y >= maxY {
|
||||
return
|
||||
@@ -957,7 +959,8 @@ func (v *View) setCharacter(x, y int, ch string, fgColor, bgColor Attribute, isW
|
||||
}
|
||||
|
||||
colorWidth := v.SelectedLineColorWidth
|
||||
if y >= rangeSelectStart && y <= rangeSelectEnd && (colorWidth == 0 || x < colorWidth) {
|
||||
if y >= rangeSelectStart && y <= rangeSelectEnd &&
|
||||
(colorWidth == 0 || x < colorWidth || x+width > v.InnerWidth()-colorWidth) {
|
||||
fgColor = applySelTextColor(fgColor, v.SelTextColor)
|
||||
if v.HighlightInactive || !isWindowFocused {
|
||||
bgColor = (bgColor & AttrStyleBits) | v.InactiveViewSelBgColor
|
||||
@@ -1869,10 +1872,11 @@ func (v *View) draw(isWindowFocused bool) {
|
||||
// content begins after it. The blanks go through setCharacter like everything
|
||||
// else, so that a selection reaching the left edge covers the gutter too.
|
||||
for gx := range gutterWidth {
|
||||
v.setCharacter(gx, y, " ", v.FgColor, v.BgColor, isWindowFocused)
|
||||
v.setCharacter(gx, y, " ", 1, v.FgColor, v.BgColor, isWindowFocused)
|
||||
}
|
||||
if gutterWidth > 0 && vline.linesY < len(v.inclusionGutterMarks) && v.inclusionGutterMarks[vline.linesY] {
|
||||
v.setCharacter(0, y, v.InclusionGutterMarker, v.InclusionGutterMarkerColor, v.BgColor, isWindowFocused)
|
||||
v.setCharacter(0, y, v.InclusionGutterMarker, uniseg.StringWidth(v.InclusionGutterMarker),
|
||||
v.InclusionGutterMarkerColor, v.BgColor, isWindowFocused)
|
||||
}
|
||||
|
||||
// x tracks the current x position in the view, and cellIdx tracks the
|
||||
@@ -1925,7 +1929,7 @@ func (v *View) draw(isWindowFocused bool) {
|
||||
fgColor |= AttrUnderline
|
||||
}
|
||||
|
||||
v.setCharacter(x, y, c.chr, fgColor, bgColor, isWindowFocused)
|
||||
v.setCharacter(x, y, c.chr, c.width, fgColor, bgColor, isWindowFocused)
|
||||
|
||||
x += c.width
|
||||
cellIdx++
|
||||
|
||||
@@ -1139,6 +1139,30 @@ func TestLineFlashReversesTheSelectionBarWithoutChangingSelection(t *testing.T)
|
||||
assert.False(t, style.HasReverse(), "clearing should remove the flash")
|
||||
}
|
||||
|
||||
// The selection bar on the right edge covers a double-width character that reaches
|
||||
// into it, like the bar on the left edge does.
|
||||
func TestSelectionBarOnTheRightEdgeCoversADoubleWidthCharacter(t *testing.T) {
|
||||
WithSimulationScreen(t, 14, 6)
|
||||
|
||||
v := NewView("name", 0, 0, 11, 5, OutputNormal) // InnerWidth 10
|
||||
v.Highlight = true
|
||||
v.SelBgColor = ColorBlue
|
||||
v.SelectedLineColorWidth = 2
|
||||
|
||||
// に takes view columns 7 and 8, and the bar the last two, 8 and 9.
|
||||
v.writeString("abcdefgにj\n")
|
||||
v.draw(true)
|
||||
|
||||
// The frame puts view column x at screen column x+1.
|
||||
highlighted := func(x int) bool {
|
||||
_, style, _ := Screen.Get(x+1, 1)
|
||||
return style.GetBackground() != tcell.ColorDefault
|
||||
}
|
||||
assert.False(t, highlighted(6))
|
||||
assert.True(t, highlighted(7), "に reaches into the bar")
|
||||
assert.True(t, highlighted(9))
|
||||
}
|
||||
|
||||
// Resizing a view throws away the wrapping of its content and wraps it again for
|
||||
// the new width, which moves every line of it to a different view line. The
|
||||
// positions into the view count view lines, so they all have to come along.
|
||||
|
||||
Reference in new issue
Block a user