about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
authorbptato <nincsnevem662@gmail.com>2023-09-26 16:11:07 +0200
committerbptato <nincsnevem662@gmail.com>2023-09-26 16:11:07 +0200
commitee17e946c53e6ca807dea2df04f8f2b9eedd754f (patch)
tree3cfccd5f9cf382d2a73cd12925bb86dba82acc1a /src
parent463499131a1b4ca41fea56030f77f4794cdca071 (diff)
downloadchawan-ee17e946c53e6ca807dea2df04f8f2b9eedd754f.tar.gz
pager: show character sequence inputs on status line
pretty useful I think
Diffstat (limited to 'src')
-rw-r--r--src/local/client.nim48
-rw-r--r--src/local/pager.nim27
2 files changed, 44 insertions, 31 deletions
diff --git a/src/local/client.nim b/src/local/client.nim
index 815d1efb..5a02d2a8 100644
--- a/src/local/client.nim
+++ b/src/local/client.nim
@@ -58,14 +58,11 @@ type
     fdmap: Table[int, Container]
     feednext: bool
     forkserver: ForkServer
-    notnum: bool # has a non-numeric character been input already?
     jsctx: JSContext
     jsrt: JSRuntime
     loader: FileLoader
     mainproc: Pid
     pager {.jsget.}: Pager
-    precnum: int32 # current number prefix (when vi-numeric-prefix is true)
-    s: string # current input buffer
     selector: Selector[int]
     timeouts: TimeoutState
 
@@ -207,22 +204,21 @@ proc evalAction(client: Client, action: string, arg0: int32) =
 const MaxPrecNum = 100000000
 
 proc handleCommandInput(client: Client, c: char) =
-  if client.config.input.vi_numeric_prefix and not client.notnum:
-    if client.precnum != 0 and c == '0' or c in '1' .. '9':
-      if client.precnum < MaxPrecNum: # better ignore than eval...
-        client.precnum *= 10
-        client.precnum += cast[int32](decValue(c))
+  if client.config.input.vi_numeric_prefix and not client.pager.notnum:
+    if client.pager.precnum != 0 and c == '0' or c in '1' .. '9':
+      if client.pager.precnum < MaxPrecNum: # better ignore than eval...
+        client.pager.precnum *= 10
+        client.pager.precnum += cast[int32](decValue(c))
       return
     else:
-      client.notnum = true
-  client.s &= c
-  let action = getNormalAction(client.config, client.s)
-  client.evalAction(action, client.precnum)
+      client.pager.notnum = true
+  client.pager.inputBuffer &= c
+  let action = getNormalAction(client.config, client.pager.inputBuffer)
+  client.evalAction(action, client.pager.precnum)
   if not client.feedNext:
-    client.precnum = 0
-    client.notnum = false
+    client.pager.precnum = 0
+    client.pager.notnum = false
     client.handlePagerEvents()
-    client.pager.refreshStatusMsg()
 
 proc input(client: Client) =
   client.pager.term.restoreStdin()
@@ -236,17 +232,17 @@ proc input(client: Client) =
         client.pager.fulfillAsk(false)
         client.runJSJobs()
     elif client.pager.lineedit.isSome:
-      client.s &= c
+      client.pager.inputBuffer &= c
       let edit = client.pager.lineedit.get
       if edit.escNext:
         edit.escNext = false
-        if edit.write(client.s, client.pager.term.cs):
-          client.s = ""
+        if edit.write(client.pager.inputBuffer, client.pager.term.cs):
+          client.pager.inputBuffer = ""
       else:
-        let action = getLinedAction(client.config, client.s)
+        let action = getLinedAction(client.config, client.pager.inputBuffer)
         if action == "":
-          if edit.write(client.s, client.pager.term.cs):
-            client.s = ""
+          if edit.write(client.pager.inputBuffer, client.pager.term.cs):
+            client.pager.inputBuffer = ""
           else:
             client.feedNext = true
         elif not client.feednext:
@@ -255,12 +251,18 @@ proc input(client: Client) =
           client.pager.updateReadLine()
     else:
       client.handleCommandInput(c)
+      if not client.feednext:
+        client.pager.inputBuffer = ""
+        client.pager.refreshStatusMsg()
+        break
+      client.pager.refreshStatusMsg()
+      client.pager.draw()
     if not client.feednext:
-      client.s = ""
+      client.pager.inputBuffer = ""
       break
     else:
       client.feednext = false
-  client.s = ""
+  client.pager.inputBuffer = ""
 
 proc setTimeout[T: JSValue|string](client: Client, handler: T,
     timeout = 0i32): int32 {.jsfunc.} =
diff --git a/src/local/pager.nim b/src/local/pager.nim
index dce66505..79511f86 100644
--- a/src/local/pager.nim
+++ b/src/local/pager.nim
@@ -52,12 +52,13 @@ type
     askcursor: int
     askpromise*: Promise[bool]
     askprompt: string
-    commandMode* {.jsget.}: bool
+    commandMode {.jsget.}: bool
     config: Config
     container*: Container
     cookiejars: Table[string, CookieJar]
     display: FixedGrid
     forkserver: ForkServer
+    inputBuffer*: string # currently uninterpreted characters
     iregex: Result[Regex, string]
     isearchpromise: EmptyPromise
     lineedit*: Option[LineEdit]
@@ -66,8 +67,10 @@ type
     mailcap: Mailcap
     mainproc: Pid
     mimeTypes: MimeTypes
+    notnum*: bool # has a non-numeric character been input already?
     numload*: int
     omnirules: seq[OmniRule]
+    precnum*: int32 # current number prefix (when vi-numeric-prefix is true)
     procmap*: Table[Pid, Container]
     proxy: URL
     redraw*: bool
@@ -196,6 +199,7 @@ proc alert*(pager: Pager, msg: string)
 
 proc newPager*(config: Config, attrs: WindowAttributes,
     forkserver: ForkServer, mainproc: Pid, ctx: JSContext): Pager =
+  let (mailcap, errs) = config.getMailcap()
   let pager = Pager(
     config: config,
     display: newFixedGrid(attrs.width, attrs.height - 1),
@@ -206,10 +210,9 @@ proc newPager*(config: Config, attrs: WindowAttributes,
     siteconf: config.getSiteConfig(ctx),
     statusgrid: newFixedGrid(attrs.width),
     term: newTerminal(stdout, config, attrs),
-    mimeTypes: config.getMimeTypes()
+    mimeTypes: config.getMimeTypes(),
+    mailcap: mailcap
   )
-  let (mcap, errs) = config.getMailcap()
-  pager.mailcap = mcap
   for err in errs:
     pager.alert("Error reading mailcap: " & err)
   return pager
@@ -249,7 +252,7 @@ proc writeStatusMessage(pager: Pager, str: string,
     return i
   for r in str.runes:
     let pi = i
-    i += r.twidth(i)
+    i += r.width()
     if i >= e:
       if i >= pager.statusgrid.width:
         i = pi
@@ -258,7 +261,9 @@ proc writeStatusMessage(pager: Pager, str: string,
       inc i
       break
     if r.isControlChar():
-      pager.statusgrid[pi].str = "^" & getControlLetter(char(r))
+      pager.statusgrid[pi].str = "^"
+      pager.statusgrid[pi + 1].str = $getControlLetter(char(r))
+      pager.statusgrid[pi + 1].format = format
     else:
       pager.statusgrid[pi].str = $r
     pager.statusgrid[pi].format = format
@@ -275,7 +280,13 @@ proc refreshStatusMsg*(pager: Pager) =
   if container == nil: return
   if pager.tty == nil: return
   if pager.askpromise != nil: return
-  if container.loadinfo != "":
+  if pager.precnum != 0:
+    pager.writeStatusMessage($pager.precnum)
+    if pager.inputBuffer != "":
+      pager.writeStatusMessage(pager.inputBuffer)
+  elif pager.inputBuffer != "":
+    pager.writeStatusMessage(pager.inputBuffer)
+  elif container.loadinfo != "":
     pager.alerton = false
     pager.writeStatusMessage(container.loadinfo)
   elif pager.alerts.len > 0:
@@ -302,7 +313,7 @@ proc refreshStatusMsg*(pager: Pager) =
 
 # Call refreshStatusMsg if no alert is being displayed on the screen.
 proc showAlerts*(pager: Pager) =
-  if not pager.alerton:
+  if not pager.alerton and pager.inputBuffer == "" and pager.precnum == 0:
     pager.refreshStatusMsg()
 
 proc drawBuffer*(pager: Pager, container: Container, ostream: Stream) =