Use io.Readers to read files more efficiently
This commit is contained in:
parent
d13f9602ff
commit
eeaac76f5f
9 changed files with 57 additions and 35 deletions
|
@ -1469,7 +1469,7 @@ func (v *View) AddTab(usePlugin bool) bool {
|
|||
return false
|
||||
}
|
||||
|
||||
tab := NewTabFromView(NewView(NewBuffer([]byte{}, "")))
|
||||
tab := NewTabFromView(NewView(NewBuffer(strings.NewReader(""), "")))
|
||||
tab.SetNum(len(tabs))
|
||||
tabs = append(tabs, tab)
|
||||
curTab++
|
||||
|
@ -1529,7 +1529,7 @@ func (v *View) VSplitBinding(usePlugin bool) bool {
|
|||
return false
|
||||
}
|
||||
|
||||
v.VSplit(NewBuffer([]byte{}, ""))
|
||||
v.VSplit(NewBuffer(strings.NewReader(""), ""))
|
||||
|
||||
if usePlugin {
|
||||
return PostActionCall("VSplit", v)
|
||||
|
@ -1543,7 +1543,7 @@ func (v *View) HSplitBinding(usePlugin bool) bool {
|
|||
return false
|
||||
}
|
||||
|
||||
v.HSplit(NewBuffer([]byte{}, ""))
|
||||
v.HSplit(NewBuffer(strings.NewReader(""), ""))
|
||||
|
||||
if usePlugin {
|
||||
return PostActionCall("HSplit", v)
|
||||
|
|
|
@ -3,6 +3,7 @@ package main
|
|||
import (
|
||||
"bytes"
|
||||
"encoding/gob"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"os/exec"
|
||||
|
@ -55,8 +56,12 @@ type SerializedBuffer struct {
|
|||
ModTime time.Time
|
||||
}
|
||||
|
||||
// NewBuffer creates a new buffer from `txt` with path and name `path`
|
||||
func NewBuffer(txt []byte, path string) *Buffer {
|
||||
func NewBufferFromString(text, path string) *Buffer {
|
||||
return NewBuffer(strings.NewReader(text), path)
|
||||
}
|
||||
|
||||
// NewBuffer creates a new buffer from a given reader with a given path
|
||||
func NewBuffer(reader io.Reader, path string) *Buffer {
|
||||
if path != "" {
|
||||
for _, tab := range tabs {
|
||||
for _, view := range tab.views {
|
||||
|
@ -68,7 +73,7 @@ func NewBuffer(txt []byte, path string) *Buffer {
|
|||
}
|
||||
|
||||
b := new(Buffer)
|
||||
b.LineArray = NewLineArray(txt)
|
||||
b.LineArray = NewLineArray(reader)
|
||||
|
||||
b.Settings = DefaultLocalSettings()
|
||||
for k, v := range globalSettings {
|
||||
|
@ -166,6 +171,9 @@ func NewBuffer(txt []byte, path string) *Buffer {
|
|||
|
||||
func (b *Buffer) GetName() string {
|
||||
if b.name == "" {
|
||||
if b.Path == "" {
|
||||
return "No name"
|
||||
}
|
||||
return b.Path
|
||||
}
|
||||
return b.name
|
||||
|
|
|
@ -4,7 +4,6 @@ import (
|
|||
"bytes"
|
||||
"fmt"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"os/exec"
|
||||
"os/signal"
|
||||
|
@ -266,17 +265,18 @@ func Help(args []string) {
|
|||
// If no file is given, it opens an empty buffer in a new split
|
||||
func VSplit(args []string) {
|
||||
if len(args) == 0 {
|
||||
CurView().VSplit(NewBuffer([]byte{}, ""))
|
||||
CurView().VSplit(NewBuffer(strings.NewReader(""), ""))
|
||||
} else {
|
||||
filename := args[0]
|
||||
home, _ := homedir.Dir()
|
||||
filename = strings.Replace(filename, "~", home, 1)
|
||||
file, err := ioutil.ReadFile(filename)
|
||||
file, err := os.Open(filename)
|
||||
defer file.Close()
|
||||
|
||||
var buf *Buffer
|
||||
if err != nil {
|
||||
// File does not exist -- create an empty buffer with that name
|
||||
buf = NewBuffer([]byte{}, filename)
|
||||
buf = NewBuffer(strings.NewReader(""), filename)
|
||||
} else {
|
||||
buf = NewBuffer(file, filename)
|
||||
}
|
||||
|
@ -288,17 +288,18 @@ func VSplit(args []string) {
|
|||
// If no file is given, it opens an empty buffer in a new split
|
||||
func HSplit(args []string) {
|
||||
if len(args) == 0 {
|
||||
CurView().HSplit(NewBuffer([]byte{}, ""))
|
||||
CurView().HSplit(NewBuffer(strings.NewReader(""), ""))
|
||||
} else {
|
||||
filename := args[0]
|
||||
home, _ := homedir.Dir()
|
||||
filename = strings.Replace(filename, "~", home, 1)
|
||||
file, err := ioutil.ReadFile(filename)
|
||||
file, err := os.Open(filename)
|
||||
defer file.Close()
|
||||
|
||||
var buf *Buffer
|
||||
if err != nil {
|
||||
// File does not exist -- create an empty buffer with that name
|
||||
buf = NewBuffer([]byte{}, filename)
|
||||
buf = NewBuffer(strings.NewReader(""), filename)
|
||||
} else {
|
||||
buf = NewBuffer(file, filename)
|
||||
}
|
||||
|
@ -326,7 +327,8 @@ func NewTab(args []string) {
|
|||
filename := args[0]
|
||||
home, _ := homedir.Dir()
|
||||
filename = strings.Replace(filename, "~", home, 1)
|
||||
file, _ := ioutil.ReadFile(filename)
|
||||
file, _ := os.Open(filename)
|
||||
defer file.Close()
|
||||
|
||||
tab := NewTabFromView(NewView(NewBuffer(file, filename)))
|
||||
tab.SetNum(len(tabs))
|
||||
|
|
|
@ -1,7 +1,9 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"bytes"
|
||||
"io"
|
||||
"unicode/utf8"
|
||||
)
|
||||
|
||||
|
@ -33,14 +35,23 @@ type LineArray struct {
|
|||
}
|
||||
|
||||
// NewLineArray returns a new line array from an array of bytes
|
||||
func NewLineArray(text []byte) *LineArray {
|
||||
func NewLineArray(reader io.Reader) *LineArray {
|
||||
la := new(LineArray)
|
||||
// Split the bytes into lines
|
||||
split := bytes.Split(text, []byte("\n"))
|
||||
la.lines = make([][]byte, len(split))
|
||||
for i := range split {
|
||||
la.lines[i] = make([]byte, len(split[i]))
|
||||
copy(la.lines[i], split[i])
|
||||
br := bufio.NewReader(reader)
|
||||
|
||||
i := 0
|
||||
for {
|
||||
data, err := br.ReadBytes('\n')
|
||||
if err != nil {
|
||||
if err == io.EOF {
|
||||
la.lines = append(la.lines, data[:len(data)])
|
||||
}
|
||||
// Last line was read
|
||||
break
|
||||
} else {
|
||||
la.lines = append(la.lines, data[:len(data)-1])
|
||||
}
|
||||
i++
|
||||
}
|
||||
|
||||
return la
|
||||
|
|
|
@ -6,6 +6,7 @@ import (
|
|||
"fmt"
|
||||
"os"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
||||
"github.com/zyedidia/clipboard"
|
||||
"github.com/zyedidia/tcell"
|
||||
|
@ -78,7 +79,7 @@ func (m *Messenger) AddLog(msg string) {
|
|||
|
||||
func (m *Messenger) getBuffer() *Buffer {
|
||||
if m.log == nil {
|
||||
m.log = NewBuffer([]byte{}, "")
|
||||
m.log = NewBuffer(strings.NewReader(""), "")
|
||||
m.log.name = "Log"
|
||||
}
|
||||
return m.log
|
||||
|
|
|
@ -93,9 +93,11 @@ func LoadInput() []*Buffer {
|
|||
filename = flag.Args()[i]
|
||||
|
||||
// Check that the file exists
|
||||
var input *os.File
|
||||
if _, e := os.Stat(filename); e == nil {
|
||||
// If it exists we load it into a buffer
|
||||
input, err = ioutil.ReadFile(filename)
|
||||
input, err = os.Open(filename)
|
||||
defer input.Close()
|
||||
if err != nil {
|
||||
TermMessage(err)
|
||||
continue
|
||||
|
@ -103,6 +105,7 @@ func LoadInput() []*Buffer {
|
|||
}
|
||||
// If the file didn't exist, input will be empty, and we'll open an empty buffer
|
||||
buffers = append(buffers, NewBuffer(input, filename))
|
||||
fmt.Print("\a")
|
||||
}
|
||||
} else if !isatty.IsTerminal(os.Stdin.Fd()) {
|
||||
// Option 2
|
||||
|
@ -113,10 +116,10 @@ func LoadInput() []*Buffer {
|
|||
TermMessage("Error reading from stdin: ", err)
|
||||
input = []byte{}
|
||||
}
|
||||
buffers = append(buffers, NewBuffer(input, filename))
|
||||
buffers = append(buffers, NewBuffer(strings.NewReader(string(input)), filename))
|
||||
} else {
|
||||
// Option 3, just open an empty buffer
|
||||
buffers = append(buffers, NewBuffer(input, filename))
|
||||
buffers = append(buffers, NewBuffer(strings.NewReader(string(input)), filename))
|
||||
}
|
||||
|
||||
return buffers
|
||||
|
@ -335,7 +338,7 @@ func main() {
|
|||
L.SetGlobal("HandleShellCommand", luar.New(L, HandleShellCommand))
|
||||
L.SetGlobal("GetLeadingWhitespace", luar.New(L, GetLeadingWhitespace))
|
||||
L.SetGlobal("MakeCompletion", luar.New(L, MakeCompletion))
|
||||
L.SetGlobal("NewBuffer", luar.New(L, NewBuffer))
|
||||
L.SetGlobal("NewBuffer", luar.New(L, NewBufferFromString))
|
||||
L.SetGlobal("RuneStr", luar.New(L, func(r rune) string {
|
||||
return string(r)
|
||||
}))
|
||||
|
@ -404,6 +407,7 @@ func main() {
|
|||
}()
|
||||
|
||||
for {
|
||||
fmt.Print("\a")
|
||||
// Display everything
|
||||
RedrawAll()
|
||||
|
||||
|
|
|
@ -18,9 +18,6 @@ func (sline *Statusline) Display() {
|
|||
y := sline.view.Height + sline.view.y
|
||||
|
||||
file := sline.view.Buf.GetName()
|
||||
if file == "" {
|
||||
file = "No name"
|
||||
}
|
||||
|
||||
// If the buffer is dirty (has been modified) write a little '+'
|
||||
if sline.view.Buf.IsModified {
|
||||
|
|
|
@ -13,8 +13,6 @@ type Tab struct {
|
|||
views []*View
|
||||
// This is the current view for this tab
|
||||
CurView int
|
||||
// Generally this is the name of the current view's buffer
|
||||
name string
|
||||
|
||||
tree *SplitTree
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
|
@ -242,13 +242,14 @@ func (v *View) OpenBuffer(buf *Buffer) {
|
|||
func (v *View) Open(filename string) {
|
||||
home, _ := homedir.Dir()
|
||||
filename = strings.Replace(filename, "~", home, 1)
|
||||
file, err := ioutil.ReadFile(filename)
|
||||
file, err := os.Open(filename)
|
||||
defer file.Close()
|
||||
|
||||
var buf *Buffer
|
||||
if err != nil {
|
||||
messenger.Message(err.Error())
|
||||
// File does not exist -- create an empty buffer with that name
|
||||
buf = NewBuffer([]byte{}, filename)
|
||||
buf = NewBuffer(strings.NewReader(""), filename)
|
||||
} else {
|
||||
buf = NewBuffer(file, filename)
|
||||
}
|
||||
|
@ -630,7 +631,7 @@ func (v *View) openHelp(helpPage string) {
|
|||
if data, err := FindRuntimeFile(RTHelp, helpPage).Data(); err != nil {
|
||||
TermMessage("Unable to load help text", helpPage, "\n", err)
|
||||
} else {
|
||||
helpBuffer := NewBuffer(data, helpPage+".md")
|
||||
helpBuffer := NewBuffer(strings.NewReader(string(data)), helpPage+".md")
|
||||
helpBuffer.name = "Help"
|
||||
|
||||
if v.Type == vtHelp {
|
||||
|
|
Loading…
Reference in a new issue