mirror of
https://github.com/jesseduffield/lazygit.git
synced 2026-09-10 07:36:27 -04:00
Draw embedded views as one focused unit
A view can only be drawn with the focused frame and title colors while it is the current view, but a panel made of an outer view and an editable field embedded in it has to look focused as a whole, whichever of the two the keyboard is pointed at. Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
9e98b3d2f3
commit
f9ec7adb61
|
|
@ -1615,6 +1615,20 @@ func (g *Gui) ForceFlushViewsContentOnly(views []*View) error {
|
|||
return g.flushContentOnly(views)
|
||||
}
|
||||
|
||||
// hasFocus reports whether a view is drawn as focused. Views that are embedded
|
||||
// in one another (see View.ParentView) form a single unit, so they are all drawn
|
||||
// as focused while any one of them is the current view.
|
||||
func (g *Gui) hasFocus(v *View) bool {
|
||||
return g.currentView != nil && outermostView(v) == outermostView(g.currentView)
|
||||
}
|
||||
|
||||
func outermostView(v *View) *View {
|
||||
for v.ParentView != nil {
|
||||
v = v.ParentView
|
||||
}
|
||||
return v
|
||||
}
|
||||
|
||||
// draw manages the cursor and calls the draw function of a view.
|
||||
func (g *Gui) draw(v *View) error {
|
||||
if !v.Visible || v.y1 < v.y0 || v.x1 < v.x0 {
|
||||
|
|
@ -1639,7 +1653,7 @@ func (g *Gui) draw(v *View) error {
|
|||
|
||||
if v.Frame {
|
||||
var fgColor, bgColor, frameColor Attribute
|
||||
if g.Highlight && v == g.currentView && g.IsFocused() {
|
||||
if g.Highlight && g.hasFocus(v) && g.IsFocused() {
|
||||
fgColor = g.SelFgColor
|
||||
bgColor = g.SelBgColor
|
||||
frameColor = g.SelFrameColor
|
||||
|
|
|
|||
|
|
@ -56,6 +56,26 @@ func TestFirstMatchingKeybindingOfParentViewWins(t *testing.T) {
|
|||
assert.Equal(t, []string{"first"}, pressed)
|
||||
}
|
||||
|
||||
func TestEmbeddedViewsAreFocusedTogether(t *testing.T) {
|
||||
g := newTestGui(t)
|
||||
parent, child := setupParentAndChildView(t, g)
|
||||
sibling, _ := g.SetView("sibling", 0, 12, 20, 14, 0)
|
||||
sibling.ParentView = parent
|
||||
unrelated, _ := g.SetView("unrelated", 30, 0, 50, 10, 0)
|
||||
|
||||
assert.True(t, g.hasFocus(child))
|
||||
assert.True(t, g.hasFocus(parent))
|
||||
assert.True(t, g.hasFocus(sibling))
|
||||
assert.False(t, g.hasFocus(unrelated))
|
||||
|
||||
_, err := g.SetCurrentView(unrelated.Name())
|
||||
assert.NoError(t, err)
|
||||
|
||||
assert.True(t, g.hasFocus(unrelated))
|
||||
assert.False(t, g.hasFocus(parent))
|
||||
assert.False(t, g.hasFocus(child))
|
||||
}
|
||||
|
||||
func TestPrintableKeysGoToTheFieldBeingTypedIn(t *testing.T) {
|
||||
for _, test := range []struct {
|
||||
name string
|
||||
|
|
|
|||
|
|
@ -210,7 +210,9 @@ type View struct {
|
|||
// Overlaps describes which edges are overlapping with another view's edges
|
||||
Overlaps byte
|
||||
|
||||
// ParentView is the view which catches events bubbled up from the given view if there's no matching handler
|
||||
// ParentView is the view which catches events bubbled up from the given view if there's no matching handler.
|
||||
// Views related this way are also drawn as a single focused unit: while one of
|
||||
// them is the current view, they all get the focused frame and title colors.
|
||||
ParentView *View
|
||||
|
||||
searcher *searcher
|
||||
|
|
|
|||
Loading…
Reference in a new issue