Start work on faces panel

This commit is contained in:
Kovid Goyal
2024-05-13 12:10:47 +05:30
parent 9cfd920e11
commit 802ed976a9
4 changed files with 118 additions and 22 deletions

View File

@@ -0,0 +1,69 @@
package choose_fonts
import (
"fmt"
"kitty/tools/tui/loop"
"kitty/tools/utils"
)
var _ = fmt.Print
type faces struct {
handler *handler
family string
settings struct {
font_family, bold_font, italic_font, bold_italic_font string
}
}
func (self *faces) draw_screen() (err error) {
self.handler.lp.SetCursorVisible(false)
sz, _ := self.handler.lp.ScreenSize()
lines := []string{self.handler.format_title(self.family, 0), ""}
_, _, str := self.handler.render_lines.InRectangle(lines, 0, 0, int(sz.WidthCells), int(sz.HeightCells), &self.handler.mouse_state, self.on_click)
self.handler.lp.QueueWriteString(str)
return
}
func (self *faces) initialize(h *handler) (err error) {
self.handler = h
return
}
func (self *faces) on_wakeup() error {
return self.handler.draw_screen()
}
func (self *faces) on_click(id string) (err error) {
return
}
func (self *faces) on_key_event(event *loop.KeyEvent) (err error) {
if event.MatchesPressOrRepeat("esc") {
event.Handled = true
self.handler.current_pane = &self.handler.listing
return self.handler.draw_screen()
}
return
}
func (self *faces) on_text(text string, from_key_event bool, in_bracketed_paste bool) (err error) {
return
}
func (self *faces) on_enter(family string) error {
if family != "" {
self.family = family
r := self.handler.listing.resolved_faces_from_kitty_conf
d := func(conf ResolvedFace, setting *string, defval string) {
*setting = utils.IfElse(family == conf.Family, conf.Spec, defval)
}
d(r.Font_family, &self.settings.font_family, family)
d(r.Bold_font, &self.settings.bold_font, "auto")
d(r.Italic_font, &self.settings.italic_font, "auto")
d(r.Bold_italic_font, &self.settings.bold_italic_font, "auto")
}
self.handler.current_pane = self
return self.handler.draw_screen()
}

View File

@@ -30,11 +30,12 @@ type FontList struct {
preview_cache_mutex sync.Mutex
}
func (self *FontList) initialize(h *handler) {
func (self *FontList) initialize(h *handler) error {
self.handler = h
self.preview_cache = make(map[preview_cache_key]string)
self.rl = readline.New(h.lp, readline.RlInit{DontMarkPrompts: true, Prompt: "Family: "})
self.variable_data_requested_for = utils.NewSet[string](256)
return nil
}
func (self *FontList) draw_search_bar() {
@@ -58,16 +59,18 @@ func center_string(x string, width int) string {
return strings.Repeat(" ", utils.Max(0, spaces)) + x
}
func (self *handler) format_title(title string, start_x int) string {
sz, _ := self.lp.ScreenSize()
return self.lp.SprintStyled("fg=green bold", center_string(title, int(sz.WidthCells)-start_x))
}
func (self *FontList) draw_family_summary(start_x int, sz loop.ScreenSize) (err error) {
lp := self.handler.lp
family := self.family_list.CurrentFamily()
if family == "" || int(sz.WidthCells) < start_x+2 {
return nil
}
lines := []string{
lp.SprintStyled("fg=green bold", center_string(family, int(sz.WidthCells)-start_x)),
"",
}
lines := []string{self.handler.format_title(family, start_x), ""}
width := int(sz.WidthCells) - start_x - 1
add_line := func(x string) {
lines = append(lines, style.WrapTextAsLines(x, width, style.WrapOptions{})...)
@@ -157,9 +160,10 @@ func (self *FontList) draw_preview(x, y int, sz loop.ScreenSize) (err error) {
return
}
func (self *FontList) on_wakeup() {
func (self *FontList) on_wakeup() error {
self.family_list.UpdateFamilies(utils.StableSortWithKey(utils.Keys(self.fonts), strings.ToLower))
self.family_list.SelectFamily(self.resolved_faces_from_kitty_conf.Font_family.Family)
return self.handler.draw_screen()
}
func (self *FontList) draw_screen() (err error) {
@@ -235,6 +239,14 @@ func (self *FontList) next(delta int, allow_wrapping bool) {
}
func (self *FontList) on_key_event(event *loop.KeyEvent) (err error) {
if event.MatchesPressOrRepeat("enter") {
event.Handled = true
if family := self.family_list.CurrentFamily(); family != "" {
return self.handler.faces.on_enter(family)
}
self.handler.lp.Beep()
return
}
if event.MatchesPressOrRepeat("esc") {
event.Handled = true
if self.rl.AllText() != "" {

View File

@@ -30,6 +30,15 @@ type TextStyle struct {
Background string `json:"background"`
}
type pane interface {
initialize(*handler) error
draw_screen() error
on_wakeup() error
on_key_event(event *loop.KeyEvent) error
on_text(text string, from_key_event bool, in_bracketed_paste bool) error
on_click(id string) error
}
type handler struct {
lp *loop.Loop
state State
@@ -43,6 +52,10 @@ type handler struct {
temp_dir string
listing FontList
faces faces
panes []pane
current_pane pane
}
func (h *handler) set_worker_error(err error) {
@@ -62,7 +75,12 @@ func (h *handler) initialize() (err error) {
h.lp.SetCursorVisible(false)
h.lp.OnQueryResponse = h.on_query_response
h.lp.QueryTerminal("font_size", "dpi_x", "dpi_y", "foreground", "background")
h.listing.initialize(h)
h.panes = []pane{&h.listing, &h.faces}
for _, pane := range h.panes {
if err = pane.initialize(h); err != nil {
return err
}
}
// dont use /tmp as it may be mounted in RAM, Le Sigh
if h.temp_dir, err = os.MkdirTemp(utils.CacheDir(), "kitten-choose-fonts-*"); err != nil {
return
@@ -136,11 +154,10 @@ func (h *handler) draw_screen() (err error) {
h.lp.ClearScreenButNotGraphics()
h.lp.AllowLineWrapping(false)
h.mouse_state.ClearCellRegions()
switch h.state {
case SCANNING_FAMILIES:
if h.current_pane == nil {
h.lp.Println("Scanning system for fonts, please wait...")
case LISTING_FAMILIES:
return h.listing.draw_screen()
} else {
return h.current_pane.draw_screen()
}
return
}
@@ -149,12 +166,10 @@ func (h *handler) on_wakeup() (err error) {
if err = h.get_worker_error(); err != nil {
return
}
switch h.state {
case SCANNING_FAMILIES:
h.state = LISTING_FAMILIES
h.listing.on_wakeup()
if h.current_pane == nil {
h.current_pane = &h.listing
}
return h.draw_screen()
return h.listing.on_wakeup()
}
func (h *handler) on_mouse_event(event *loop.MouseEvent) (err error) {
@@ -179,17 +194,15 @@ func (h *handler) on_key_event(event *loop.KeyEvent) (err error) {
event.Handled = true
return fmt.Errorf("canceled by user")
}
switch h.state {
case LISTING_FAMILIES:
return h.listing.on_key_event(event)
if h.current_pane != nil {
err = h.current_pane.on_key_event(event)
}
return
}
func (h *handler) on_text(text string, from_key_event bool, in_bracketed_paste bool) (err error) {
switch h.state {
case LISTING_FAMILIES:
return h.listing.on_text(text, from_key_event, in_bracketed_paste)
if h.current_pane != nil {
err = h.current_pane.on_text(text, from_key_event, in_bracketed_paste)
}
return
}

View File

@@ -167,3 +167,5 @@ func RuneOffsetsToByteOffsets(text string) func(int) int {
return self.byte_offset
}
}
func Repr(x any) string { return fmt.Sprintf("%#v", x) }