// REMFMT.S
//
// This is a MultiEdit 6.  10 macro to reformat a block of C++ or 
// assembly-language comments.  It is designed to work with a block of 
// comments that is by itself.  It will NOT work with comments that are 
// appended to the end of statement lines.
//
// The comment token ("//" in C++, or ";" in assembly language) must be 
// followed by at least one space.  If you like to butt the text right up 
// against the comment token, this macro won't work for you.
//
// A comment block must be followed by a blank line or by a line with 
// only a comment token on it.
//
// I don't use tabs, so I would be surprised if this macro works with a 
// file that contains tabs.
//
// If the macro reformats your entire block of comments to a single line, 
// go into your Other/Install/Filename-Extentions and set the right 
// margin to something like 74 or whatever you like.
//
// Donated to the public domain by:
//
//   Wayne Conrad, Phoenix Control Systems
//   CIS 71754,2053


macro RemFmt
{

  // Mark the beginning of an "undoable" thing.

  Push_Undo;

  // We'll update the screen when we're done, thank you.

  Refresh = False;

  // If this is an empty line, don't do anything.

  Goto_Col (1);
  Forward_Till_Not (' ');
  if (!AT_EOL)
    {

    // Block marking off

    Block_Off;

    // Remember where we started.

    First_Word;
    int FirstCol  = C_Col;
    int FirstLine = C_Line;

    // Remember the insert mode

    int OldInsertMode = Insert_Mode;

    // Grab a copy of the comment token.

    str CommentToken = Get_Word (' ');

    // Find the first line that is blank or that has only a comment 
    // token.

    int Done = False;
    while (!Done)
      {
      First_Word;
      str Token = Get_Word (' ');
      Forward_Till_Not (' ');
      if ( (Token == CommentToken) && !AT_EOL)
        Down;
      else
        Done = True;
      };

    // Now skip blank comment lines.

    int Done = False;
    while (!Done)
      {
      First_Word;
      str Token = Get_Word (' ');
      Forward_Till_Not (' ');
      if ( (Token == CommentToken) && AT_EOL)
        Down;
      else
        Done = True;
      }

    // Now we know the range of stuff to reformat.

    int LastLine = C_Line - 1;

    // Line up the comments tokens.

    for (int LineNum = FirstLine; LineNum <= LastLine; LineNum++)
      {
      Goto_Line (LineNum);
      First_Word;
      while (C_Col < FirstCol)
        Text (' ');
      if (C_Col > FirstCol)
        {
        Goto_Col (1);
        Del_Chars (FirstCol);
        }
      }

    // For each line, replace the comment token with spaces.

    Insert_Mode = False;
    for (int LineNum = FirstLine; LineNum <= LastLine; LineNum++)
      {
      Goto_Line (LineNum);
      Block_Off;
        First_Word;
      str Blanks;
      Pad_Str (Blanks, Length (CommentToken), ' ');
      Text (Blanks);
      Delete_Block;
      }

    // Mark the first line for which we should NOT replace the comment 
    // tokens.

    Down;
    Mark_Pos;

    // Reformat.

    Goto_Line (FirstLine);
    Run_Macro ('TEXT^REFORMAT');

    // Put the comment tokens back in.

    Goto_Mark;
    LastLine = C_Line - 1;
    for (int LineNum = FirstLine; LineNum <= LastLine; LineNum++)
      {
      Goto_Line (LineNum);
      Goto_Col (FirstCol);
      Text (CommentToken);
      }

    // Position for the next reformat.

    Down;
    Goto_Col (1);

    // Restore the insert mode.

    Insert_Mode = OldInsertMode;

    }

  // Mark the end of an undoable thing.

  Pop_Undo;

  // Refresh the screen.

  Refresh = True;

}
