From: phertmuller
Subject: Standard output formatting control
Date: 
Message-ID: <1149844430.367073.234450@i40g2000cwc.googlegroups.com>
Hi all

My question is so simple (I guess) but I couldn't find help googleing.
I'd like to print something (like a counter) to the standard output,
and I'd like to fix the place where the item has to appear into the
screen. For example, if I want to print the status of a counter, like

(do ((x 0 (1+ x))
       ((equal x 3))
   (format t "x"))

This produces

0
1
2

How can I do to get these numbers in the same position ? (So, after
printing 0, clean the output, and print the 1 in the same position).

Thanks for your help
Peter

From: Lars Rune Nøstdal
Subject: Re: Standard output formatting control
Date: 
Message-ID: <1149845205.539501.303990@i40g2000cwc.googlegroups.com>
phertmuller wrote:
> Hi all
>
> My question is so simple (I guess) but I couldn't find help googleing.
> I'd like to print something (like a counter) to the standard output,
> and I'd like to fix the place where the item has to appear into the
> screen. For example, if I want to print the status of a counter, like
>
> (do ((x 0 (1+ x))
>        ((equal x 3))
>    (format t "x"))
>
> This produces
>
> 0
> 1
> 2
>
> How can I do to get these numbers in the same position ? (So, after
> printing 0, clean the output, and print the 1 in the same position).

You do _not_ want stuff like that to happen inside your Lisp
development-environment. You should instead use something external to
display output and read input from the user, like for instance `ltk' (
http://www.peter-herth.de/ltk/ ) or maybe something from any of these
links:

  http://www.cliki.net/Graphics%20Toolkit
  http://www.cliki.net/GTK%20binding

..or you could even output HTML for display on a web-page.

-- 
Lars Rune Nøstdal
http://lars.nostdal.org/
From: Lars Rune Nøstdal
Subject: Re: Standard output formatting control
Date: 
Message-ID: <1149845284.409149.158120@f6g2000cwb.googlegroups.com>
..or maybe you want http://www.cliki.net/sb-screen

-- 
Lars Rune Nøstdal
http://lars.nostdal.org/
From: Rob Warnock
Subject: Re: Standard output formatting control
Date: 
Message-ID: <NKWdnedmHL9RlBfZnZ2dnUVZ_qidnZ2d@speakeasy.net>
Lars Rune N�stdal <···········@gmail.com> wrote:
+---------------
| ..or maybe you want http://www.cliki.net/sb-screen
+---------------

Or, if you need something simpler(?), http://www.cliki.net/CL-Ncurses


-Rob

-----
Rob Warnock			<····@rpw3.org>
627 26th Avenue			<URL:http://rpw3.org/>
San Mateo, CA 94403		(650)572-2607
From: Pascal Bourguignon
Subject: Re: Standard output formatting control
Date: 
Message-ID: <877j3q3bkk.fsf@thalassa.informatimago.com>
"phertmuller" <···········@gmail.com> writes:
> My question is so simple (I guess) but I couldn't find help googleing.
> I'd like to print something (like a counter) to the standard output,
> and I'd like to fix the place where the item has to appear into the
> screen. For example, if I want to print the status of a counter, like
>
> (do ((x 0 (1+ x))
>        ((equal x 3))
>    (format t "x"))
>
> This produces
>
> 0
> 1
> 2
>
> How can I do to get these numbers in the same position ? (So, after
> printing 0, clean the output, and print the 1 in the same position).

To do this kind of thing, you have to drive the terminal.  That is,
each class of terminal understand its own protocol, special sequences
of bytes that it interprets as commands to move cursor and do some
other kind of things (change color, or other character attribute,
define zones ("windows"), move characters or lines, etc).

On a unix system, there's databases of terminal descriptions mapping
such functions to the byte sequences to be sent to the terminal:
termcap (older) or terminfo (newer).  The terminal used is indicated
by the TERM environment variable.  So you could get the content of
this variables, and read the termcap or terminfo files to collect the
byte sequences to send to move the cursor at a given position.


Or, you could use the curses (or ncurses) unix library which does that
for you.  There's the cl-curses Common Lisp package that implement the
FFI to the curses unix library.




If you use clisp, you can also use the clisp specific SCREEN package:
http://clisp.cons.org/impnotes/screen.html

(screen:with-window
  (loop for x from 0 below 3 
        do (screen:set-window-cursor-position screen:*window* 4 10)
           (format screen:*window* "~4D" x)
           (sleep 1)))




Now, if you just want a quick-and-dirty solution, you can use the
Carriage Return ASCII code, in most terminal it will move the cursor
at the beginning of the line without advancing to the next line:

(loop for x from 0 below 3
      do (format t "~C~4D" (code-char 13) x) 
         (sleep 1)) 

(it even does the right thing in emacs inferior-lisp buffers, which is
not the case of screen and other curses libraries).



Or you could use directly the byte sequences understood by your terminal.
For example, if you know your terminal understands ECMA-048 (ie. ISO6429),
then you could use:

http://darcs.informatimago.com/local/darcs/public/lisp/common-lisp/ecma048.lisp

(asdf:oos 'asdf:load-op :com.informatimago.common-lisp)
(shadow '(ed))
(use-package  :com.informatimago.common-lisp.ecma048)
(generate-all-functions :compile t :verbose t :export t
                        :8-bit nil :print t :result-type 'string)
(loop for x from 0 below 3
      initially (ed 2)
      do (cup 4 10) 
         (sgr (+ x 31))
         (format t "~4D" x) 
         (sleep 1)
      finally (cup 22 0))


-- 
__Pascal Bourguignon__                     http://www.informatimago.com/

ATTENTION: Despite any other listing of product contents found
herein, the consumer is advised that, in actuality, this product
consists of 99.9999999999% empty space.
From: Rob Warnock
Subject: Re: Standard output formatting control
Date: 
Message-ID: <bsmdnVjs0qi2kRfZnZ2dneKdnZydnZ2d@speakeasy.net>
Pascal Bourguignon  <···@informatimago.com> wrote:
+---------------
| "phertmuller" <···········@gmail.com> writes:
| > How can I do to get these numbers in the same position ? (So, after
| > printing 0, clean the output, and print the 1 in the same position).
...
| Now, if you just want a quick-and-dirty solution, you can use the
| Carriage Return ASCII code, in most terminal it will move the cursor
| at the beginning of the line without advancing to the next line:
| 
| (loop for x from 0 below 3
|       do (format t "~C~4D" (code-char 13) x) 
|          (sleep 1)) 
+---------------

In many Common Lisps, especially on Unix/Linux, formatted output
is not automatically flushed from buffers by a #\Return, only by
a #\LineFeed, so to get this to work as expected you will need to
add a (FORCE-OUTPUT) before the (SLEEP 1) [and similarly with the
CUP example later]:

     (loop for x from 0 below 3
	   do (format t "~C~4D" (code-char 13) x) 
	      (force-output)
	      (sleep 1)) 


-Rob

-----
Rob Warnock			<····@rpw3.org>
627 26th Avenue			<URL:http://rpw3.org/>
San Mateo, CA 94403		(650)572-2607
From: Thomas F. Burdick
Subject: Re: Standard output formatting control
Date: 
Message-ID: <xcv4pyt9uf4.fsf@conquest.OCF.Berkeley.EDU>
····@rpw3.org (Rob Warnock) writes:

> Pascal Bourguignon  <···@informatimago.com> wrote:
> +---------------
> | "phertmuller" <···········@gmail.com> writes:
> | > How can I do to get these numbers in the same position ? (So, after
> | > printing 0, clean the output, and print the 1 in the same position).
> ...
> | Now, if you just want a quick-and-dirty solution, you can use the
> | Carriage Return ASCII code, in most terminal it will move the cursor
> | at the beginning of the line without advancing to the next line:
> | 
> | (loop for x from 0 below 3
> |       do (format t "~C~4D" (code-char 13) x) 
> |          (sleep 1)) 
> +---------------
> 
> In many Common Lisps, especially on Unix/Linux, formatted output
> is not automatically flushed from buffers by a #\Return, only by
> a #\LineFeed, so to get this to work as expected you will need to
> add a (FORCE-OUTPUT) before the (SLEEP 1) [and similarly with the
> CUP example later]:

I'm not sure how exactly FORCE-OUTPUT became the favorite
recommendation of c.l.lisp denizens, but it's a bad thing to recommend
to a newbie.  To the extent that FORCE-OUTPUT and FINISH-OUTPUT
differ, it's rare that you actually want the behavior of FORCE-OUTPUT.
When writing a server application, just before going back into your
listening loop -- that's the only time that pops to mind where you
want to start flushing buffers but not wait for the process to complete.
From: Rob Warnock
Subject: Re: Standard output formatting control
Date: 
Message-ID: <-ZmdnWNy14u3MBfZnZ2dnUVZ_sKdnZ2d@speakeasy.net>
Thomas F. Burdick <···@conquest.OCF.Berkeley.EDU> wrote:
+---------------
| ····@rpw3.org (Rob Warnock) writes:
| > In many Common Lisps, especially on Unix/Linux, formatted output
| > is not automatically flushed from buffers by a #\Return, only by
| > a #\LineFeed, so to get this to work as expected you will need to
| > add a (FORCE-OUTPUT) before the (SLEEP 1) [and similarly with the
| > CUP example later]:
| 
| I'm not sure how exactly FORCE-OUTPUT became the favorite
| recommendation of c.l.lisp denizens, but it's a bad thing
| to recommend to a newbie.
+---------------

I respectfully disagree.

+---------------
| To the extent that FORCE-OUTPUT and FINISH-OUTPUT differ, it's
| rare that you actually want the behavior of FORCE-OUTPUT. When
| writing a server application, just before going back into your
| listening loop -- that's the only time that pops to mind where you
| want to start flushing buffers but not wait for the process to complete.
+---------------

In a multi-threaded application FINISH-OUTPUT can (in theory) cause
the current thread to *block* until the output has round-tripped
to the ultimate consumer, which can be a *long* time if there's an
international network delay in the path [and/or the network implemen-
tation is using "delayed ACKs" for efficiency, which most modern stacks
*do* by default!]. FORCE-OUTPUT, by contrast, will start the buffered
data moving [so that the user on the far end of the connection *will*
see it, eventually] but will not block the thread and/or the application.

And conversely, actually getting FINISH-OUTPUT to satisfy its
contract -- "ensure that any buffered output sent to output-stream
has reached its destination" -- can be *VERY* hard in a networked
environment, e.g., with TCP, which normally gives you no user-visible
way of knowing that the data has "reached its destination". [Yes, the
*kernel* stack can find that out, by looking at the ACK count, in the
TCB PCB, but that information is not normally made available to users.]

Or for disk files, FINISH-OUTPUT's contract, taken literally, would
say that when it returns the bits are actually physically on the disk,
secure from (say) a power outage or reboot or crash. This is *not*
likely to be the case unless the entire system from the Lisp app
down through the operating system and out through the disk drive
itself are cooperating to create such "stable storage". Good luck!

As a result, I feel that FORCE-OUTPUT, whose weaker contract is
both more "reliable" [in the sense of being likely to be satisfied
across a wide variety of I/O channels] and also closest to the
C language's "fflush()" [which newbies will likely be used to],
is the one to use -- and to suggest -- by default.

Said another way, yes, FORCE-OUTPUT does not make as strong a
promise as FINISH-OUTPUT, but it is more likely to *fulfill*
its contract!


-Rob

p.s. In CMUCL, FINISH-OUTPUT & FORCE-OUTPUT are identical on
an FD-STREAM [any stream mapped to a Unix file descriptor].
It would be interesting to know for which implementations
they are actually different.

-----
Rob Warnock			<····@rpw3.org>
627 26th Avenue			<URL:http://rpw3.org/>
San Mateo, CA 94403		(650)572-2607
From: Matthias Buelow
Subject: Re: Standard output formatting control
Date: 
Message-ID: <878xo6bkod.fsf@graendal.mkbuelow.net>
"phertmuller" <···········@gmail.com> writes:

>My question is so simple (I guess) but I couldn't find help googleing.
>I'd like to print something (like a counter) to the standard output,
>and I'd like to fix the place where the item has to appear into the
>screen. For example, if I want to print the status of a counter, like
>
>(do ((x 0 (1+ x))
>       ((equal x 3))
>   (format t "x"))
>
>This produces
>
>0
>1
>2
>
>How can I do to get these numbers in the same position ? (So, after
>printing 0, clean the output, and print the 1 in the same position).


Here the (corrected) snippet produces: xxx


(do ((x 0 (1+ x)))
       ((equal x 3))
   (format t "x"))


You probably meant "(format t "~A~%" x)".

[note that you also forgot one closing ) in the first line]

But to your question, the general answer, on Unix, is to output ^H
(backspace) and then overwrite the previously printed stuff, like, for
example:

(format t "aaaa^H^H^H^Hxxxx")
xxxx

(the ^H are literal backspaces in this example)

This also works in any ANSI terminal.

mkb.
From: Thomas A. Russ
Subject: Re: Standard output formatting control
Date: 
Message-ID: <ymiac8maq9j.fsf@sevak.isi.edu>
Matthias Buelow <···@incubus.de> writes:

> "phertmuller" <···········@gmail.com> writes:
> 
> >My question is so simple (I guess) but I couldn't find help googleing.
> >I'd like to print something (like a counter) to the standard output,
> >and I'd like to fix the place where the item has to appear into the
> >screen. For example, if I want to print the status of a counter, like
...
> >How can I do to get these numbers in the same position ? (So, after
> >printing 0, clean the output, and print the 1 in the same position).
> 
> (do ((x 0 (1+ x)))
>        ((equal x 3))
>    (format t "x"))
> 
> 
> You probably meant "(format t "~A~%" x)".
> 
> [note that you also forgot one closing ) in the first line]

Generally you can't do that with FORMAT, since it is really more
stream-oriented than terminal-oriented.  So there isn't really a notion
of a screen, that has a randomly addressable place.

If you don't care about other things that are on the screen (or if you
can reproduce them), you can try the ~| [vertical bar] format directive,
but even if this solves your problem, there will likely be flickering on
the update.  Vertical bar should output a page separator character, and
on many terminals this will clear the display.

The real answer, as other have pointed out, is to use a real graphics or
terminal environment.  This will have to be some Common Lisp extension
or 3rd party code.

-- 
Thomas A. Russ,  USC/Information Sciences Institute
From: Tim X
Subject: Re: Standard output formatting control
Date: 
Message-ID: <87bqt1k2t8.fsf@tiger.rapttech.com.au>
"phertmuller" <···········@gmail.com> writes:

> Hi all
>
> My question is so simple (I guess) but I couldn't find help googleing.
> I'd like to print something (like a counter) to the standard output,
> and I'd like to fix the place where the item has to appear into the
> screen. For example, if I want to print the status of a counter, like
>
> (do ((x 0 (1+ x))
>        ((equal x 3))
>    (format t "x"))
>
> This produces
>
> 0
> 1
> 2
>
> How can I do to get these numbers in the same position ? (So, after
> printing 0, clean the output, and print the 1 in the same position).
>
> Thanks for your help
> Peter
>

You would need to make sure your output is not going to the repl to
avoid getting 'odd' behavior, but ....

There is no straight-forward way to do this in CL. You either have to
use an add on package for some sort of GUI front end like ltk etc or
use low level control in your output terminal like ansi control
sequences.

My very first and rather badly written lisp program (pre CL) was a
"Game of Life" implementation which used the control codes for an old
VT100 to manage the movement of the cursor on the screen and
write/erase various 'cells'. 

From memory, these VT100 control codes were a subset of the codes that
eventually made up the ANSI terminal control codes, which I beleive is
what colour LS uses. So, on an xterm which has VT100 support (most
do), you should be able to use the ANSI escape code to manipulate the
cursor and have your counter print in the same location. 

Another approach would be to use something like a CL interface to
ncursors or similar text based UI library. 

Tim
-- 
tcross (at) rapttech dot com dot au