package editor import ( "pad/internal/ui" ) // State holds all application state owned by the logic goroutine. type State struct { PixelWidth int // raw pixel width from Gio ConfigEvent PixelHeight int // raw pixel height from Gio ConfigEvent scale float32 Elems []ui.Element } func NewState() *State { return &State{scale: 1.0} } func (s *State) SetScale(scale float32) { s.scale = scale } func (s *State) Scale() float32 { return s.scale } // layout converts stored pixel dimensions to Dp using the current scale // and computes the element tree. Called only when a frame is needed. func (s *State) layout() []ui.Element { dpW := ui.ToDp(ui.Px(s.PixelWidth), s.scale) dpH := ui.ToDp(ui.Px(s.PixelHeight), s.scale) s.Elems = EditorLayout(dpW, dpH) return s.Elems } // EditorLayout computes the element tree for the editor page. func EditorLayout(screenWidth, screenHeight ui.Dp) []ui.Element { margin := ui.Dp(10) // --- Top bar: filename on row 1, icons on row 2 --- statusBarRegion := ui.Region{ X: margin, Y: margin, W: screenWidth - margin*2, H: ui.Dp(52), } statusBarW := statusBarRegion.W statusBar := ui.NewContainer( statusBarRegion, ui.Color{R: 230, G: 230, B: 230, A: 255}, []ui.Element{ // Row 1: filename ui.NewLabel("a very long file name that probably will eventually need to be truncated.txt", 14, ui.Region{X: 0, Y: ui.Dp(2), W: statusBarW, H: ui.Dp(20)}, ui.AlignStart), // Row 2: cut, copy, paste icons ui.NewIcon("cut", ui.Region{X: ui.Dp(0), Y: ui.Dp(28), W: ui.IconSize, H: ui.IconSize}, 0), ui.NewIcon("copy", ui.Region{X: ui.Dp(48), Y: ui.Dp(28), W: ui.IconSize, H: ui.IconSize}, 0), ui.NewIcon("paste", ui.Region{X: ui.Dp(96), Y: ui.Dp(28), W: ui.IconSize, H: ui.IconSize}, 0), }, ) // --- Bottom bar --- bottomBarHeight := ui.BottomBarHeight bottomBarY := screenHeight - margin - bottomBarHeight bottomBarRegion := ui.Region{ X: margin, Y: bottomBarY, W: screenWidth - margin*2, H: bottomBarHeight, } bottomBarW := bottomBarRegion.W bottomBar := ui.NewContainer( bottomBarRegion, ui.Color{R: 230, G: 230, B: 230, A: 255}, []ui.Element{ ui.NewLabel("Ln 47, Col 12", 12, ui.Region{X: 0, Y: ui.Dp(2), W: bottomBarW, H: ui.Dp(20)}, ui.AlignStart), ui.NewLabel("1024 / 50000", 12, ui.Region{X: 0, Y: ui.Dp(2), W: bottomBarW, H: ui.Dp(20)}, ui.AlignCenter), ui.NewLabel("Wrap: On", 12, ui.Region{X: 0, Y: ui.Dp(2), W: bottomBarW, H: ui.Dp(20)}, ui.AlignEnd), }, ) return []ui.Element{statusBar, bottomBar} }