Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix: Input handling for Windows to prevent first key loss #1180

Open
wants to merge 4 commits into
base: main
Choose a base branch
from

Conversation

Denish3436
Copy link

This PR solve issue #1167

Copy link
Member

@aymanbagabas aymanbagabas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @Denish3436. Thank you for the PR. Could you please make sure you use LF line endings instead of CRLF?

Copy link
Member

@aymanbagabas aymanbagabas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, could you please fix the lint issues

@aymanbagabas
Copy link
Member

aymanbagabas commented Oct 21, 2024

@Denish3436 I've tried reproducing the bug with your example from #1167. The bug still happens even with this patch. However, using the v2-exp branch with the following patch seems to resolve the issue on v2. Still digging and trying to figure out why this happens on main.

diff --git a/cancelreader_windows.go b/cancelreader_windows.go
index 4aa5a75..a1a49c9 100644
--- a/cancelreader_windows.go
+++ b/cancelreader_windows.go
@@ -10,6 +10,7 @@ import (
 	"sync"
 	"time"
 
+	xwindows "github.com/charmbracelet/x/windows"
 	"github.com/muesli/cancelreader"
 	"golang.org/x/sys/windows"
 )
@@ -47,6 +48,10 @@ func newCancelreader(r io.Reader) (cancelreader.CancelReader, error) {
 		return fallback(r)
 	}
 
+	if err := xwindows.FlushConsoleInputBuffer(conin); err != nil {
+		return fallback(r)
+	}
+
 	originalMode, err := prepareConsole(conin,
 		windows.ENABLE_MOUSE_INPUT,
 		windows.ENABLE_WINDOW_INPUT,

The example i'm using

package main

import (
	"fmt"

	"github.com/charmbracelet/bubbles/v2/cursor"
	"github.com/charmbracelet/bubbles/v2/textinput"
	tea "github.com/charmbracelet/bubbletea/v2"
)

func Input(prompt, value string) {
	ti := textinput.New()
	ti.Prompt = prompt
	ti.Focus()
	p := tea.NewProgram(inputModel{textInput: ti})
	p.Run()
}

type inputModel struct {
	textInput textinput.Model
	quitting  bool
}

func (m inputModel) Init() (tea.Model, tea.Cmd) {
	return m, nil
}

func (m inputModel) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
	var cmd tea.Cmd

	switch msg := msg.(type) {
	case tea.KeyMsg:
		switch msg.String() {
		case "enter":
			m.textInput.Cursor.SetMode(cursor.CursorHide)
			m.quitting = true
			return m, tea.Quit
		}
	}
	m.textInput, cmd = m.textInput.Update(msg)
	return m, cmd
}

func (m inputModel) View() string {
	str := m.textInput.View()
	if m.quitting {
		return str + "\n"
	}
	return str
}

func main() {
	for i := 0; i < 2; i++ {
		Input(fmt.Sprintf("Test %d: ", i), "default")
	}
}

@aymanbagabas
Copy link
Member

I've opened #1192 to fix this issue in v2.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants