mirror of https://github.com/chzyer/readline.git
Prefill user input (#101)
* Using a fillable stdin reader * Adding some documentation to the new features
This commit is contained in:
parent
af545c8af6
commit
9cc74fe5ad
18
readline.go
18
readline.go
|
@ -55,6 +55,7 @@ type Config struct {
|
||||||
FuncGetWidth func() int
|
FuncGetWidth func() int
|
||||||
|
|
||||||
Stdin io.Reader
|
Stdin io.Reader
|
||||||
|
StdinWriter io.Writer
|
||||||
Stdout io.Writer
|
Stdout io.Writer
|
||||||
Stderr io.Writer
|
Stderr io.Writer
|
||||||
|
|
||||||
|
@ -97,6 +98,9 @@ func (c *Config) Init() error {
|
||||||
if c.Stdin == nil {
|
if c.Stdin == nil {
|
||||||
c.Stdin = NewCancelableStdin(Stdin)
|
c.Stdin = NewCancelableStdin(Stdin)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
c.Stdin, c.StdinWriter = NewFillableStdin(c.Stdin)
|
||||||
|
|
||||||
if c.Stdout == nil {
|
if c.Stdout == nil {
|
||||||
c.Stdout = Stdout
|
c.Stdout = Stdout
|
||||||
}
|
}
|
||||||
|
@ -281,6 +285,20 @@ func (i *Instance) Write(b []byte) (int, error) {
|
||||||
return i.Stdout().Write(b)
|
return i.Stdout().Write(b)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// WriteStdin prefill the next Stdin fetch
|
||||||
|
// Next time you call ReadLine() this value will be writen before the user input
|
||||||
|
// ie :
|
||||||
|
// i := readline.New()
|
||||||
|
// i.WriteStdin([]byte("test"))
|
||||||
|
// _, _= i.Readline()
|
||||||
|
//
|
||||||
|
// gives
|
||||||
|
//
|
||||||
|
// > test[cursor]
|
||||||
|
func (i *Instance) WriteStdin(val []byte) (int, error) {
|
||||||
|
return i.Terminal.WriteStdin(val)
|
||||||
|
}
|
||||||
|
|
||||||
func (i *Instance) SetConfig(cfg *Config) *Config {
|
func (i *Instance) SetConfig(cfg *Config) *Config {
|
||||||
if i.Config == cfg {
|
if i.Config == cfg {
|
||||||
return cfg
|
return cfg
|
||||||
|
|
57
std.go
57
std.go
|
@ -131,3 +131,60 @@ func (c *CancelableStdin) Close() error {
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// FillableStdin is a stdin reader which can prepend some data before
|
||||||
|
// reading into the real stdin
|
||||||
|
type FillableStdin struct {
|
||||||
|
sync.Mutex
|
||||||
|
stdin io.Reader
|
||||||
|
stdinBuffer io.Reader
|
||||||
|
buf []byte
|
||||||
|
bufErr error
|
||||||
|
}
|
||||||
|
|
||||||
|
// NewFillableStdin gives you FillableStdin
|
||||||
|
func NewFillableStdin(stdin io.Reader) (io.Reader, io.Writer) {
|
||||||
|
|
||||||
|
r, w := io.Pipe()
|
||||||
|
s := &FillableStdin{
|
||||||
|
stdinBuffer: r,
|
||||||
|
stdin: stdin,
|
||||||
|
}
|
||||||
|
s.ioloop()
|
||||||
|
return s, w
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *FillableStdin) ioloop() {
|
||||||
|
go func() {
|
||||||
|
for {
|
||||||
|
bufR := make([]byte, 100)
|
||||||
|
var n int
|
||||||
|
n, s.bufErr = s.stdinBuffer.Read(bufR)
|
||||||
|
s.Lock()
|
||||||
|
s.buf = append(s.buf, bufR[:n]...)
|
||||||
|
s.Unlock()
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
}
|
||||||
|
|
||||||
|
// Read will read from the local buffer and if no data, read from stdin
|
||||||
|
func (s *FillableStdin) Read(p []byte) (n int, err error) {
|
||||||
|
s.Lock()
|
||||||
|
i := len(s.buf)
|
||||||
|
if len(p) < i {
|
||||||
|
i = len(p)
|
||||||
|
}
|
||||||
|
if i > 0 {
|
||||||
|
n := copy(p, s.buf)
|
||||||
|
s.buf = s.buf[:0]
|
||||||
|
cerr := s.bufErr
|
||||||
|
s.bufErr = nil
|
||||||
|
s.Unlock()
|
||||||
|
return n, cerr
|
||||||
|
}
|
||||||
|
s.Unlock()
|
||||||
|
|
||||||
|
return s.stdin.Read(p)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
|
@ -65,6 +65,12 @@ func (t *Terminal) Write(b []byte) (int, error) {
|
||||||
return t.cfg.Stdout.Write(b)
|
return t.cfg.Stdout.Write(b)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// WriteStdin prefill the next Stdin fetch
|
||||||
|
// Next time you call ReadLine() this value will be writen before the user input
|
||||||
|
func (t *Terminal) WriteStdin(b []byte) (int, error) {
|
||||||
|
return t.cfg.StdinWriter.Write(b)
|
||||||
|
}
|
||||||
|
|
||||||
type termSize struct {
|
type termSize struct {
|
||||||
left int
|
left int
|
||||||
top int
|
top int
|
||||||
|
|
Loading…
Reference in New Issue