111 lines
1.7 KiB
Go
111 lines
1.7 KiB
Go
package editor
|
|
|
|
import (
|
|
"unicode/utf8"
|
|
|
|
"tea.kareha.org/cup/termi"
|
|
)
|
|
|
|
func (ed *Editor) LineHeight(line string) int {
|
|
rc := utf8.RuneCountInString(line)
|
|
width := termi.StringWidth(line, rc)
|
|
return 1 + max(width-1, 0)/ed.w
|
|
}
|
|
|
|
func (ed *Editor) DrawBuffer() {
|
|
y := 0
|
|
for i := ed.vrow; i < len(ed.lines); i++ {
|
|
line := ed.Line(i)
|
|
|
|
termi.MoveCursor(0, y)
|
|
termi.Draw(line)
|
|
|
|
y += ed.LineHeight(line)
|
|
if y >= ed.h-1 {
|
|
break
|
|
}
|
|
}
|
|
|
|
for ; y < ed.h-1; y++ {
|
|
termi.MoveCursor(0, y)
|
|
termi.Draw("~")
|
|
}
|
|
}
|
|
|
|
func (ed *Editor) DrawStatus() {
|
|
var m string
|
|
switch ed.mode {
|
|
case ModeCommand:
|
|
m = "vi command"
|
|
case ModeInsert:
|
|
m = "vi insert"
|
|
case ModeSearch:
|
|
m = "vi search"
|
|
case ModePrompt:
|
|
m = "vi prompt"
|
|
default:
|
|
panic("invalid mode")
|
|
}
|
|
|
|
termi.MoveCursor(0, ed.h-1)
|
|
if ed.message != "" {
|
|
termi.EnableInvert()
|
|
termi.Print(ed.message)
|
|
termi.DisableInvert()
|
|
ed.message = ""
|
|
} else {
|
|
termi.Printf("[%s] %s %d,%d %s", ed.parser.Cache(), m, ed.row, ed.col, ed.path)
|
|
}
|
|
}
|
|
|
|
func (ed *Editor) UpdateCursor() {
|
|
// XXX approximation
|
|
width := termi.StringWidth(ed.CurrentLine(), ed.col)
|
|
ed.x = width % ed.w
|
|
dy := width / ed.w
|
|
|
|
if ed.row < ed.vrow {
|
|
ed.vrow = ed.row
|
|
}
|
|
|
|
y := 0
|
|
for i := ed.vrow; i < ed.row; i++ {
|
|
y += ed.LineHeight(ed.lines[i])
|
|
}
|
|
ed.y = y + dy
|
|
|
|
for ed.y >= ed.h-1 {
|
|
ed.vrow++
|
|
|
|
y := 0
|
|
for i := ed.vrow; i < ed.row; i++ {
|
|
y += ed.LineHeight(ed.lines[i])
|
|
}
|
|
ed.y = y + dy
|
|
}
|
|
}
|
|
|
|
func (ed *Editor) Repaint() {
|
|
w, h := termi.Size()
|
|
ed.w = w
|
|
ed.h = h
|
|
|
|
termi.HideCursor()
|
|
|
|
termi.Clear()
|
|
termi.HomeCursor()
|
|
|
|
ed.UpdateCursor()
|
|
|
|
ed.DrawBuffer()
|
|
ed.DrawStatus()
|
|
|
|
termi.MoveCursor(ed.x, ed.y)
|
|
|
|
termi.ShowCursor()
|
|
}
|
|
|
|
func (ed *Editor) Draw() {
|
|
ed.Repaint()
|
|
}
|