::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:
class Io.Stream.Public  public Gilda:  Utilities for text files

 type Stream.In   &Read from a string or file.
   is                       &Read from a string as a Stream.
    - Source    string,     &The source string.
    - In   = 0  word,       &Initially 0 for closed; else one-based string index.
    - Mark = 0  word,       &A saved index.  See MARK.INDEX, REPLACE.SCAN.VALUE, MACRO.PARAMETER
      File,                          &File Id when reading from a file.
      Open => $File`Open             :NYI:   Open => AT(@File.Id) \/ In ~= 0

import Reader(Stream.In)
:
:...............................................................................


::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:
method READER..Reader..Stream.In:  Initializes a Reader.

change Reader..Stream.In
:
:  EXCEPTIONS:  The file containing Root does not exist.
:               The file containing Root is already open.
:...............................................................................
:
method OPEN..Reader..Stream.In:  Opens a file for reading and initializes READER.

  exit Reader..Stream.In

 entry Source    string   :Source file OS path or a source string.
:
:...............................................................................
:
method OPEN.TEXT..Reader..Stream.In:  Opens a file for reading and initializes READER.

  exit Reader..Stream.In

 entry Source    string   :Source string.
:
:...............................................................................
:
method CLOSE..Reader..Stream.In:  Close a file that is open for reading with Read.Ch.

change Reader..Stream.In
:
:  Note:  Read will automatically close a file at Eof.  This method only
:         needs to be called when a file is partially read.
:..............................................................................
:
method LINE..Reader..Stream.In:  Reads the rest of a line from a string.

change Reader..Stream.In

  exit Line    string,       &Remainder of the current line.
       Next    byte          :First character of the next line.
:
:...............................................................................
:
method NEXT..Reader..Stream.In:  Reads the current and next characters from a file.

change Reader..Stream.In

  exit C       byte,       &The current character.
       Next    byte        :The next character.

precondition
   $Next ~= Peof;             ERROR:  Attempt to read characters past EOF.
.
: Exit: C = ( C* Eol )* Eof Peof+
:
: Assert:  The file, Read.Id, is not open for sequential input.
:          Attempt to read past end of file.  If the assertion is not
:          invoked, the PEOF character will be returned in C and Next.
:...............................................................................
:
method REPLACE..Reader..Stream.In:  Replace the last token scanned with another.

change Reader..Stream.In

 entry Mark        word,     &Index to the first character to replace.
       Value = ""  string    :The replacement value.
:
: Usage:  OPEN    Stream.In
:         MARK    Stream.In, Mark;          Save the beginning of this token.
:         SCREEN  Stream.In, TOken, Emit;   Read in one or more tokens.
:         REPLACE Stream.In, Mark, Value;   Replace the tokens.
:         SCREEN  Stream.In, TOken, Emit;   Read the first token in the replaced value.
:...............................................................................



::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:
method CLOSE..Stream.In:  Clears the string; sets closed status (optional).

change Stream.In
:
:...............................................................................
:
method DRAIN..Stream.In:  Clears the string; sets closed status (optional).

change Stream.In
:
:...............................................................................
:
method LINE..Stream.In:  Reads the next line from a file.

change Stream.In

  exit Line  string
:
:...............................................................................
:
method MARK..Stream.In:  Mark the beginning of a token while scanning a string.

change Stream.In        :Stream opened for string reads.

  exit Mark    word     :Save this index and pass it to Replace.
                        :On a file read -Eof is returned (not allowed).
:
:...............................................................................
:
method NEXT..Stream.In:  Reads the current from a line of text.

change Stream.In

  exit C      byte   :Next character (0 extended); Eol; Eof; Peof; 0 (closed).
:
:  Exit: C -> (<c>* <delimiters> )* Eof Peof
:...............................................................................
:
method OPEN..Stream.In:  Initialize reading from a single text line or file.

  exit Stream.In

 entry Source    string,     &Line of text or a relative file OS path.
       Text = 0  Bit         :0 - Source is a file path; 1 - a text string.
:
:  The text is raw.  The contents does not impact the status.
:...............................................................................
:
method REPLACE..Stream.In:  Replace a segment of text with another.

change Stream.In             :Stream opened for string reads and marked.

 entry Mark        word,     &Index to the first character to replace.
       Value = ""  string    :The replacement value.
:
: swap = $;      Swap into a file.
: OPEN.STREAM.STRING  $, value;     Open a text string read.
:...............................................................................
:
method SEEK..Stream.In:  Position within the line.

change Stream.In       :Open stream.

 entry Index  word     :Zero-based index into the stream data.

precondition
   Index;                 ERROR:  Seek index is zero.
.
:...............................................................................
:
method STATUS..Stream.In:  Status of the next string read.

 entry Stream.In          :An open or closed stream.

  exit Status   byte      :I/O status; 0 if closed.
:
:...............................................................................



::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
:
method OPEN..Stream..string:  Initialize reading from a single text line.

  exit Stream..string

 entry Source    string,   &Line of text to read.
       Text = 0  Bit       :Ingnored; included for stream.in compatability.
:
:  The text is raw.  The contents does not impact the status.
:  The Text parameter should always be 1.  We could check this???
:...............................................................................
:
method CLOSE..Stream..string:  Clears the string; sets closed status (optional).

change Stream..string
:
:...............................................................................
:
method DRAIN..Stream..string:  Clears the string; sets closed status (optional).

change Stream..string
:
:...............................................................................
:
method LINE..Stream..string:  Reads the rest of a line from a string.

change Stream..string

  exit Line  string
:
: This returns all of the line and does not stop at embedded CR/LF delimiters???
:...............................................................................
:
method MARK..Stream..string:  Mark the beginning of a token while scanning a string.

change Stream..string

  exit Mark    word :Save this index and pass it to Replace.
:
:...............................................................................
:
method NEXT..Stream..string:  Reads the current from a line of text.

change Stream..string

  exit C      byte      :Next character (0 extended); Eof; Peof; 0 (closed).
:
: Exit:  Returns the next character or 0 if the stream is closed.
:...............................................................................
:
method REPLACE..Stream..string:  Replace a substring being read with another.

change Stream..string

 entry Mark        word,   &Index to the first character to replace.
       Value = ""  string  :The replacement value.
:
: Usage:  MARK    Stream.In, Mark;          Save the beginning of this token.
:         SCREEN  Stream.In, Token, Emit;   Read in one or more tokens.
:         REPLACE Stream.In, Mark, Value;   Replace the tokens.
:         SCREEN  Stream.In, Token, Emit;   Read the first token in the replaced value.
:...............................................................................
:
method SEEK..Stream..string:  Position within the line.

change Stream..string

 entry Index  word       :Zero-based index into the string.
:
:...............................................................................
:
method STATUS..Stream..string:  Status of the next string read.

 entry Stream..string

  exit Status  byte     :Stream status; 0 if closed.
:
:...............................................................................


end