wisp
 
(Arne Babenhauserheide)
2016-07-19: wisp-guile.w: Enable continuing lines started with a colon. API limited-multiline-colon-parens

wisp-guile.w: Enable continuing lines started with a colon. API CHANGE.

diff --git a/wisp-guile.w b/wisp-guile.w
--- a/wisp-guile.w
+++ b/wisp-guile.w
@@ -470,54 +470,54 @@ Also unescape \\: to :.
                                 . : string-append lastletter processed
                             ; else check for " : ": That adds a new inline bracket
                             ; support : at the beginning of a line, too.
-                          : or (equal? " : "  lastupto3) (equal? ": " lastupto3)
-                                ; replace the last 2 chars with "(" and note
-                                ; that we need an additional closing bracket
-                                ; at the end.
-                                linebracketizer instring inbrackets : + 1 bracketstoadd 
+                          : or (equal? " : "  lastupto3)
+                            ; replace the last 2 chars with "(" and note
+                            ; that we need an additional closing bracket
+                            ; at the end.
+                            linebracketizer instring inbrackets : + 1 bracketstoadd 
                                     string-append (string-drop-right unprocessed 2) 
                                     string-append "(" processed
-                                ; turn " ' (" into " '(", do not modify unprocessed, except to shorten it!
-                                ; same for ` , #' #` #, #,@,
+                            ; turn " ' (" into " '(", do not modify unprocessed, except to shorten it!
+                            ; same for ` , #' #` #, #,@,
                           : and (string-prefix? "(" processed) : equal? " ' " lastupto3
-                                    ; leave out the second space
-                                    linebracketizer instring inbrackets bracketstoadd 
-                                        . (string-append (string-drop-right unprocessed 2) "'")
-                                        . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 2) "'")
+                                . processed
                           : and (string-prefix? "(" processed) : equal? " , " lastupto3
-                                    ; leave out the second space
-                                    linebracketizer instring inbrackets bracketstoadd 
-                                        . (string-append (string-drop-right unprocessed 2) ",")
-                                        . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 2) ",")
+                                . processed
                           : and (string-prefix? "(" processed) : equal? " ` " lastupto3
-                                        ; leave out the second space
-                                        linebracketizer instring inbrackets bracketstoadd 
-                                            . (string-append (string-drop-right unprocessed 2) "`")
-                                            . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 2) "`")
+                                . processed
                           : and (string-prefix? "(" processed) : equal? " #` " lastupto4
-                                        ; leave out the second space
-                                        linebracketizer instring inbrackets bracketstoadd 
-                                            . (string-append (string-drop-right unprocessed 3) "#`")
-                                            . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 3) "#`")
+                                . processed
                           : and (string-prefix? "(" processed) : equal? " #' " lastupto4
-                                        ; leave out the second space
-                                        linebracketizer instring inbrackets bracketstoadd 
-                                            . (string-append (string-drop-right unprocessed 3) "#'")
-                                            . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 3) "#'")
+                                . processed
                           : and (string-prefix? "(" processed) : equal? " #, " lastupto4
-                                        ; leave out the second space
-                                        linebracketizer instring inbrackets bracketstoadd 
-                                            . (string-append (string-drop-right unprocessed 3) "#,")
-                                            . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 3) "#,")
+                                . processed
                           : and (string-prefix? "(" processed) : equal? " #,@, " lastupto6
-                                        ; leave out the second space
-                                        linebracketizer instring inbrackets bracketstoadd 
-                                            . (string-append (string-drop-right unprocessed 5) "#,@,")
-                                            . processed
+                            ; leave out the second space
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-append (string-drop-right unprocessed 5) "#,@,")
+                                . processed
                           else ; just go on
-                                        linebracketizer instring inbrackets bracketstoadd 
-                                            . (string-drop-right unprocessed 1)
-                                            . (string-append lastletter processed)
+                            linebracketizer instring inbrackets bracketstoadd 
+                                . (string-drop-right unprocessed 1)
+                                . (string-append lastletter processed)
                         
 
 define : last-indent levels
@@ -569,6 +569,14 @@ The line *must* have a whitespace after 
                                line-comment line
                          else
                            loop : cdr paren-prefixes
+
+define : line-add-starting-brackets-multiple line number
+     . "Add multiple starting brackets."
+     if : = 0 number
+        . line
+        line-add-starting-brackets-multiple
+          line-add-starting-bracket line
+          - number 1
        
 define : line-add-closing-brackets line number
     . "Add a closing bracket to the line."
@@ -584,16 +592,18 @@ define : line-indent-brackets-to-close l
     ; adjust the levels until the highest indentation level is equal
     ; to the indentation of the next line. Then check for
     ; continuation.
-    let closer : (bracketstoclose 0) (rest levels)
-        let : : highest-level : list-ref rest 0
-            ; finish-condition
-            if : = line-indent highest-level
-                if prev-continues
-                    . bracketstoclose
-                    + 1 bracketstoclose
-                if : > line-indent highest-level
-                    closer (- bracketstoclose 1) : append (list line-indent) rest 
-                    closer (+ bracketstoclose 1) : list-tail rest 1
+    ; we need real start of the line, not the imaginary start of the code
+    let : : line-indent : inexact->exact : real-part line-indent
+      let closer : (bracketstoclose 0) (rest levels)
+          let : : highest-level : list-ref rest 0
+              ; finish-condition
+              if : = line-indent highest-level
+                  if prev-continues
+                      . bracketstoclose
+                      + 1 bracketstoclose
+                  if : > line-indent highest-level
+                      closer (- bracketstoclose 1) : append (list line-indent) rest
+                      closer (+ bracketstoclose 1) : list-tail rest 1
 
 
 define : line-indent-brackets-to-open line-indent levels line-continues prev-continues
@@ -604,13 +614,15 @@ define : line-indent-brackets-to-open li
 
 define : line-indent-levels-adjust levels next-indent
        . "Add or remove levels so the highest remaining level matches next-indent."
-       let adjuster : (lev levels)
-           let : : highest-level : list-ref lev 0
-               if : = next-indent highest-level
-                   . lev
-                   if : > next-indent highest-level
-                       append (list next-indent) lev
-                       adjuster : list-tail lev 1
+       ; take the imaginary levels into account
+       let : : next-indent : inexact->exact : + (real-part next-indent) (imag-part next-indent)
+         let adjuster : (lev levels)
+             let : : highest-level : list-ref lev 0
+                 if : = next-indent highest-level
+                     . lev
+                     if : > next-indent highest-level
+                         append (list next-indent) lev
+                         adjuster : list-tail lev 1
 
 define : line-drop-continuation-dot line
        let : : content : line-content line
@@ -619,7 +631,26 @@ define : line-drop-continuation-dot line
                if : line-continues? line
                    string-drop content 2
                    . content
-               line-comment line 
+               line-comment line
+
+define : line-drop-leading-colon line
+       let* 
+           : content : line-content line
+             indent : line-indent line
+             addindent
+               if : >= 1 : string-length content
+                  . #f
+                  string-index content
+                               λ (x) : not : equal? #\space x
+                               . 1
+           list
+               if addindent
+                  + indent : * addindent 0+1i ; add imaginary indentation
+                  . indent
+               if addindent
+                  string-drop content addindent
+                  . content
+               line-comment line
 
 define : wisp2lisp-parse lisp prev lines
     . "Parse the body of the wisp-code."
@@ -648,13 +679,27 @@ define : wisp2lisp-parse lisp prev lines
                           final-line : equal? #f : line-content next
                           bracketstocloseprev : if (line-empty-code? pre) 0 : line-indent-brackets-to-close next-indent levels next-continues pre-continues
                           bracketstoopennext : line-indent-brackets-to-open next-indent levels next-continues pre-continues
-                          newnext : if final-line next : if (> bracketstoopennext 0) (line-add-starting-bracket next) next
                           newpre : line-drop-continuation-dot : line-add-closing-brackets pre bracketstocloseprev
-                          newlevels : line-indent-levels-adjust levels next-indent
-                        bracketizer newlevels newnext 
-                            if final-line unprocessed : list-tail unprocessed 1
-                            append processed (list newpre) whitespace
-                            list
+                        let de-colonizer
+                            : next next
+                              levels : line-indent-levels-adjust levels next-indent
+                              addcolonbrackets 0
+                            if
+                                 and
+                                     not final-line
+                                     not : line-empty-code? next
+                                     string-prefix? ": " : string-trim-right (line-content next) #\space
+                                 de-colonizer
+                                     line-drop-leading-colon next
+                                     line-indent-levels-adjust levels : line-indent : line-drop-leading-colon next
+                                     + 1 addcolonbrackets
+                                 let : : next : line-add-starting-brackets-multiple next addcolonbrackets
+                                     bracketizer levels
+                                         if final-line next
+                                            if (> bracketstoopennext 0) (line-add-starting-bracket next) next
+                                         if final-line unprocessed : list-tail unprocessed 1
+                                         append processed (list newpre) whitespace
+                                         list
 
 
 define : wisp2lisp-initial-comments lisp prev lines
@@ -798,7 +843,9 @@ define : join-lisp-lines lisp-lines
                  : next : list-ref unprocessed 0
                    nextstring 
                        string-append
-                           xsubstring " " 0 : line-indent next
+                           xsubstring " " 0
+                               inexact->exact
+                                   real-part : line-indent next
                            ; here we re-add all necessary linebreakswe get rid 
                            unescape-linebreaks : line-content next
                            if : equal? "" : line-comment next 
diff --git a/wisp-scheme.w b/wisp-scheme.w
--- a/wisp-scheme.w
+++ b/wisp-scheme.w
@@ -372,7 +372,7 @@ define : line-code-replace-inline-colons
          ; format #t "replace inline colons for line ~A\n" line
          let loop
            : processed '()
-              unprocessed line
+             unprocessed line
            cond
              : null? unprocessed
                ; format #t "inline-colons processed line: ~A\n" processed
@@ -638,35 +638,35 @@ define : wisp-replace-paren-quotation-re
          quoted lists."
          match code
              : 'REPR-QUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'quote : map wisp-replace-paren-quotation-repr a
+               list 'quote : map wisp-replace-paren-quotation-repr a
              : a ... 'REPR-QUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd b ; this is the quoted empty list 
-                append
+               append
                         map wisp-replace-paren-quotation-repr a
                         list : list 'quote : map wisp-replace-paren-quotation-repr b
              : 'REPR-QUASIQUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd 'REPR-UNQUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'quasiquote : list 'unquote : map wisp-replace-paren-quotation-repr a
+               list 'quasiquote : list 'unquote : map wisp-replace-paren-quotation-repr a
              : 'REPR-UNQUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'unquote : map wisp-replace-paren-quotation-repr a
+               list 'unquote : map wisp-replace-paren-quotation-repr a
              : a ... 'REPR-UNQUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd b 
-                append
+               append
                         map wisp-replace-paren-quotation-repr a
                         list : list 'unquote : map wisp-replace-paren-quotation-repr b
              : 'REPR-QUASIQUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'quasiquote : map wisp-replace-paren-quotation-repr a
+               list 'quasiquote : map wisp-replace-paren-quotation-repr a
              : a ... 'REPR-QUASIQUOTE-e749c73d-c826-47e2-a798-c16c13cb89dd b ; this is the quoted empty list 
-                append
+               append
                         map wisp-replace-paren-quotation-repr a
                         list : list 'quasiquote : map wisp-replace-paren-quotation-repr b
              : 'REPR-UNQUOTESPLICING-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'unquote-splicing : map wisp-replace-paren-quotation-repr a
+               list 'unquote-splicing : map wisp-replace-paren-quotation-repr a
              : 'REPR-SYNTAX-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'syntax : map wisp-replace-paren-quotation-repr a
+               list 'syntax : map wisp-replace-paren-quotation-repr a
              : 'REPR-UNSYNTAX-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'unsyntax : map wisp-replace-paren-quotation-repr a
+               list 'unsyntax : map wisp-replace-paren-quotation-repr a
              : 'REPR-QUASISYNTAX-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'quasisyntax : map wisp-replace-paren-quotation-repr a
+               list 'quasisyntax : map wisp-replace-paren-quotation-repr a
              : 'REPR-UNSYNTAXSPLICING-e749c73d-c826-47e2-a798-c16c13cb89dd a ...
-                list 'unsyntax-splicing : map wisp-replace-paren-quotation-repr a
+               list 'unsyntax-splicing : map wisp-replace-paren-quotation-repr a
              : a ...
                map wisp-replace-paren-quotation-repr a
              a