|
|
@@ -0,0 +1,136 @@
|
|
|
+// package screen -- объект экрана
|
|
|
+package screen
|
|
|
+
|
|
|
+import (
|
|
|
+ "fmt"
|
|
|
+
|
|
|
+ "github.com/gdamore/tcell"
|
|
|
+
|
|
|
+ "p78git.ddns.net/svi/libtui/alias"
|
|
|
+ "p78git.ddns.net/svi/libtui/line_cell/cell"
|
|
|
+ "p78git.ddns.net/svi/libtui/pos"
|
|
|
+
|
|
|
+ // "p78git.ddns.net/svi/libtui/screen/win_debug"
|
|
|
+ "p78git.ddns.net/svi/libtui/size"
|
|
|
+ "p78git.ddns.net/svi/libtui/types"
|
|
|
+)
|
|
|
+
|
|
|
+// Screen -- объект экрана
|
|
|
+type Screen struct {
|
|
|
+ app types.IKernel
|
|
|
+ scr tcell.Screen // Библиотечный экран
|
|
|
+ size types.ISize // Размер экрана
|
|
|
+ posShift types.IPos // Смещение начала координат
|
|
|
+}
|
|
|
+
|
|
|
+// NewScreen -- возвращаетновый экран
|
|
|
+func NewScreen(app types.IKernel) (*Screen, error) {
|
|
|
+ if app == nil {
|
|
|
+ return nil, fmt.Errorf("NewScreen(): IApp==nil")
|
|
|
+ }
|
|
|
+ scr, err := tcell.NewScreen()
|
|
|
+ if err != nil {
|
|
|
+ return nil, fmt.Errorf("NewScreen(): in create tcell.Screen, err=\n\t%w", err)
|
|
|
+ }
|
|
|
+ sf := &Screen{
|
|
|
+ app: app,
|
|
|
+ scr: scr,
|
|
|
+ size: size.NewSize(),
|
|
|
+ posShift: pos.NewPos(),
|
|
|
+ }
|
|
|
+ return sf, nil
|
|
|
+}
|
|
|
+
|
|
|
+// Run -- запускает экран в работу
|
|
|
+func (sf *Screen) Run() error {
|
|
|
+ defer func() {
|
|
|
+ sf.scr.Fini()
|
|
|
+ sf.app.CancelApp()
|
|
|
+ }()
|
|
|
+ if err := sf.scr.Init(); err != nil {
|
|
|
+ return fmt.Errorf("Screen.Run(): in init tcell.Screen, err=\n\t%w", err)
|
|
|
+ }
|
|
|
+ sf.scr.EnableMouse()
|
|
|
+ sf.scr.HideCursor()
|
|
|
+ sf.setGeomShift()
|
|
|
+ sf.Clear()
|
|
|
+ sf.Draw() // sf.scr.Show() // Обновить экран
|
|
|
+ for { // Главный цикл работы
|
|
|
+ event := sf.scr.PollEvent() // Получить событие
|
|
|
+ // Process event
|
|
|
+ switch ev := event.(type) {
|
|
|
+ case *tcell.EventResize:
|
|
|
+ sf.scr.Sync()
|
|
|
+ x, y := ev.Size()
|
|
|
+ sf.size.Set(alias.SizeX(x), alias.SizeY(y))
|
|
|
+ case *tcell.EventKey:
|
|
|
+ if ev.Key() == tcell.KeyCtrlQ { // ev.Key() == tcell.KeyEscape
|
|
|
+ return nil
|
|
|
+ }
|
|
|
+ if ev.Key() == tcell.KeyCtrlD { // Показать отладочную информацию
|
|
|
+ // if sf.screen.WinDebug().IsVisible() { // Переключение состояния показа окна отладки
|
|
|
+ // sf.screen.WinDebug().Hide()
|
|
|
+ // } else {
|
|
|
+ // sf.screen.WinDebug().Show()
|
|
|
+ // }
|
|
|
+ }
|
|
|
+ case *tcell.EventMouse: // Мышка подвинулась
|
|
|
+ x, y := ev.Position()
|
|
|
+ sf.app.Cursor().SetPos(alias.PosX(x), alias.PosY(y))
|
|
|
+ }
|
|
|
+ sf.Draw()
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+// setGeomShift -- устанавливает геометрическое начало координат
|
|
|
+func (sf *Screen) setGeomShift() {
|
|
|
+ _, sizeY := sf.scr.Size()
|
|
|
+ // Сдвигает по вертикали координату вниз
|
|
|
+ sf.posShift.Set(0, alias.PosY(sizeY))
|
|
|
+}
|
|
|
+
|
|
|
+// Size -- возвращает размер экрана
|
|
|
+func (sf *Screen) Size() (alias.SizeX, alias.SizeY) {
|
|
|
+ return sf.size.Get()
|
|
|
+}
|
|
|
+
|
|
|
+// WinDebug -- возвращает объект окна отладки экрана
|
|
|
+// func (sf *Screen) WinDebug() types.IWinDebug {
|
|
|
+// return sf.winDebug
|
|
|
+// }
|
|
|
+
|
|
|
+// Resize -- изменяет размер экрана
|
|
|
+func (sf *Screen) Resize(x alias.SizeX, y alias.SizeY) {
|
|
|
+ sf.size.Set(x, y)
|
|
|
+}
|
|
|
+
|
|
|
+// GetCell -- возвращает ячейку по указанному знакоместу
|
|
|
+func (sf *Screen) GetCell(posX alias.PosX, posY alias.PosY) types.ICell {
|
|
|
+ rune_, _, style, _ := sf.scr.GetContent(int(posX), int(posY))
|
|
|
+ cell := cell.NewCell()
|
|
|
+ cell.SetLit(alias.Lit(rune_))
|
|
|
+ cell.SetStyle(alias.Style(style))
|
|
|
+ return cell
|
|
|
+}
|
|
|
+
|
|
|
+// SetCell -- устанавливает ячейку на экран
|
|
|
+func (sf *Screen) SetCell(cell types.ICell) {
|
|
|
+ x, y := cell.Pos()
|
|
|
+ style := cell.Style()
|
|
|
+ lit := cell.Lit()
|
|
|
+ sf.scr.SetCell(int(x), int(y), tcell.Style(style), rune(lit))
|
|
|
+}
|
|
|
+
|
|
|
+// Draw -- отрисовка экранасебя по требованию
|
|
|
+func (sf *Screen) Draw() {
|
|
|
+ sf.scr.Clear()
|
|
|
+ // sf.winDebug.Draw()
|
|
|
+ // sf.cursor.Draw()
|
|
|
+ sf.scr.Show() // Обновить экран
|
|
|
+
|
|
|
+}
|
|
|
+
|
|
|
+// Clear -- очистка экрана
|
|
|
+func (sf *Screen) Clear() {
|
|
|
+ sf.scr.Clear() // Зачистить экран перед началом работы
|
|
|
+}
|