From 7080321cb94c401037c361a57838aac6fe4a3bca Mon Sep 17 00:00:00 2001 From: MrMelon54 Date: Sun, 14 Jan 2024 18:33:53 +0000 Subject: [PATCH] Old code --- buffer.go | 59 ++++++++++++++++++++++++++++++++++++++++++++++ cell-attributes.go | 18 ++++++++++++++ cell.go | 14 +++++++++++ line.go | 32 +++++++++++++++++++++++++ line_test.go | 23 ++++++++++++++++++ measured-rune.go | 6 +++++ modes.go | 33 ++++++++++++++++++++++++++ position.go | 5 ++++ voidterm.go | 27 +++++++++++++++++++++ 9 files changed, 217 insertions(+) create mode 100644 buffer.go create mode 100644 cell-attributes.go create mode 100644 cell.go create mode 100644 line.go create mode 100644 line_test.go create mode 100644 measured-rune.go create mode 100644 modes.go create mode 100644 position.go create mode 100644 voidterm.go diff --git a/buffer.go b/buffer.go new file mode 100644 index 0000000..177e035 --- /dev/null +++ b/buffer.go @@ -0,0 +1,59 @@ +package voidterm + +import ( + "io" + "sync/atomic" +) + +type Buffer struct { + lines []Line + cursor Position + + inputStream io.Reader + + width, height atomic.Uint64 + + done chan struct{} + updateBuffer chan struct{} +} + +func NewBuffer(width, height uint64, input io.Reader) *Buffer { + v := &Buffer{ + lines: make([]Line, 0), + cursor: Position{0, 0}, + inputStream: input, + done: make(chan struct{}), + updateBuffer: make(chan struct{}), + } + v.width.Store(width) + v.height.Store(height) + return v +} + +func (v *Buffer) renderBuffer() [][]Cell { + width := v.width.Load() + height := v.height.Load() + buf := make([][]Cell, height) + y := v.height.Load() - 1 + lineIdx := len(v.lines) - 1 + for _, i := range v.lines { + w := i.Wrap(width) + for _, j := range w { + buf[y] = j + y++ + } + } + return nil +} + +var specialChars = map[rune]func(t *Buffer){ + 0x07: handleOutputBell, + 0x08: handleOutputBackspace, + '\n': handleOutputLineFeed, + '\v': handleOutputLineFeed, + '\f': handleOutputLineFeed, + '\r': handleOutputCarriageReturn, + '\t': handleOutputTab, + 0x0e: handleShiftOut, // handle switch to G1 character set + 0x0f: handleShiftIn, // handle switch to G0 character set +} diff --git a/cell-attributes.go b/cell-attributes.go new file mode 100644 index 0000000..59d7b15 --- /dev/null +++ b/cell-attributes.go @@ -0,0 +1,18 @@ +package voidterm + +import ( + "image/color" +) + +type CellAttributes struct { + fg color.Color + bg color.Color + bold bool + italic bool + dim bool + underline bool + strikethrough bool + blink bool + inverse bool + hidden bool +} diff --git a/cell.go b/cell.go new file mode 100644 index 0000000..e8e26ba --- /dev/null +++ b/cell.go @@ -0,0 +1,14 @@ +package voidterm + +type Cell struct { + r MeasuredRune + attr CellAttributes +} + +func (c *Cell) Attr() CellAttributes { + return c.attr +} + +func (c *Cell) Rune() MeasuredRune { + return c.r +} diff --git a/line.go b/line.go new file mode 100644 index 0000000..488f110 --- /dev/null +++ b/line.go @@ -0,0 +1,32 @@ +package voidterm + +type Line struct { + wrapped bool + cells []Cell +} + +func LineFromRunes(runes []rune, style CellAttributes) Line { + l := make(Line, len(runes)) + for i, r := range runes { + l[i] = Cell{ + r: r, + s: style, + } + } + return l +} + +func (l Line) Wrap(width uint64) WrappedLine { + if uint64(len(l)) <= width { + return WrappedLine{l} + } + a := l + w := make(WrappedLine, 0, 1+uint64(len(l)-1)/width) + for uint64(len(a)) > width { + w = append(w, a[:width]) + a = a[width:] + } + return w +} + +type WrappedLine []Line diff --git a/line_test.go b/line_test.go new file mode 100644 index 0000000..9b56511 --- /dev/null +++ b/line_test.go @@ -0,0 +1,23 @@ +package voidterm + +import ( + "github.com/stretchr/testify/assert" + "testing" +) + +func TestLine_Wrap(t *testing.T) { + t.Run("too wide", func(t *testing.T) { + l := LineFromRunes([]rune("Hello world!"), CellAttributes{}).Wrap(16) + assert.Equal(t, WrappedLine{ + LineFromRunes([]rune("Hello world!"), CellAttributes{}), + }, l) + }) + t.Run("too thin", func(t *testing.T) { + l := LineFromRunes([]rune("Hello world!"), CellAttributes{}).Wrap(4) + assert.Equal(t, WrappedLine{ + LineFromRunes([]rune("Hell"), CellAttributes{}), + LineFromRunes([]rune("o wo"), CellAttributes{}), + LineFromRunes([]rune("rld!"), CellAttributes{}), + }, l) + }) +} diff --git a/measured-rune.go b/measured-rune.go new file mode 100644 index 0000000..924b620 --- /dev/null +++ b/measured-rune.go @@ -0,0 +1,6 @@ +package voidterm + +type MeasuredRune struct { + Rune rune + Width int +} diff --git a/modes.go b/modes.go new file mode 100644 index 0000000..6be1e81 --- /dev/null +++ b/modes.go @@ -0,0 +1,33 @@ +package voidterm + +type Modes struct { + ShowCursor bool + ApplicationCursorKeys bool + BlinkingCursor bool + ReplaceMode bool + OriginMode bool + LineFeedMode bool + ScreenMode bool + AutoWrap bool + SixelScrolling bool + BracketedPasteMode bool +} + +type MouseMode uint +type MouseExtMode uint + +const ( + MouseModeNone MouseMode = iota + MouseModeX10 + MouseModeVT200 + MouseModeVT200Highlight + MouseModeButtonEvent + MouseModeAnyEvent +) + +const ( + MouseExtNone MouseExtMode = iota + MouseExtUTF + MouseExtSGR + MouseExtURXVT +) diff --git a/position.go b/position.go new file mode 100644 index 0000000..76f8766 --- /dev/null +++ b/position.go @@ -0,0 +1,5 @@ +package voidterm + +type Position struct { + X, Y int +} diff --git a/voidterm.go b/voidterm.go new file mode 100644 index 0000000..3ae8f4c --- /dev/null +++ b/voidterm.go @@ -0,0 +1,27 @@ +package voidterm + +import ( + "os" + "sync" +) + +const ( + MainBuffer uint8 = 0 + AltBuffer uint8 = 1 + InternalBuffer uint8 = 2 +) + +type VoidTerm struct { + mu sync.Mutex + pty *os.File + updateChan chan struct{} + processChan chan MeasuredRune + closeChan chan struct{} + buffers []*Buffer + activeBuffer *Buffer + mouseMode MouseMode + mouseExtMode MouseExtMode + running bool + shell string + initialCommand string +}