ROOT logo
// @(#)root/base:$Id: TQCommand.cxx 25128 2008-08-12 17:59:19Z pcanal $
// Author: Valeriy Onuchin 04/27/2004

/*************************************************************************
 * Copyright (C) 1995-2001, Rene Brun and Fons Rademakers.               *
 * All rights reserved.                                                  *
 *                                                                       *
 * For the licensing terms see $ROOTSYS/LICENSE.                         *
 * For the list of contributors see $ROOTSYS/README/CREDITS.             *
 *************************************************************************/

//////////////////////////////////////////////////////////////////////////
//                                                                      //
// The Command design pattern is based on the idea, that all editing    //
// in an application is done by creating instances of command objects.  //
// Command objects apply changes to the edited object and then are      //
// stored  on a command stack. Furthermore, each command knows how to   //
// undo its changes to bring the edited object back to its previous     //
// state. As long as the application only uses command objects to       //
// change the state of the edited object, it is possible to undo        //
// a sequence of commands by traversing the command stack downwards and //
// calling the "undo" method of each command in turn. It is also        //
// possible to redo a sequence of commands by traversing the command    //
// stack upwards and calling the "redo" method of each command.         //
//                                                                      //
//                                                                      //
// Examples:                                                            //
//                                                                      //
// 1. Create a new command                                              //
//                                                                      //
// TQCommand *com = new TQCommand("TH1", hpx, "SetFillColor(Color_t)"   //
//                                "SetFillColor(Color_t)");             //
//                                                                      //
// 1st parameter - the name of class                                    //
// 2nd parameter - object                                               //
// 3rd parameter - the name of do/redo method                           //
// 4th parameter - the name of undo method                              //
//                                                                      //
// Since redo,undo methods are the same, undo name can be omitted, e.g. //
//                                                                      //
// TQCommand *com = new TQCommand("TH1", hpx, "SetFillColor(Color_t)"); //
//                                                                      //
// For objects derived from TObject class name can be omitted, e.g.     //
//                                                                      //
//    TQCommand *com = new TQCommand(hpx, "SetFillColor(Color_t)");     //
//                                                                      //
// 2. Setting undo, redo parameters.                                    //
//                                                                      //
//    Color_t old_color = hpx->GetFillColor();                          //
//    Color_t new_color = 4;  // blue color                             //
//                                                                      //
//    com->SetRedoArgs(1, new_color);                                   //
//    com->SetUndoArgs(1, old_color);                                   //
//                                                                      //
// 1st argument - the number of undo, redo parameters                   //
// the other arguments - undo, redo values                              //
//                                                                      //
// Since the number of undo,redo parameters is the same one can use     //
//                                                                      //
//    com->SetArgs(1, new_color, old_color);                            //
//                                                                      //
// 3. Undo, redo method execution                                       //
//                                                                      //
//    com->Redo(); // execute redo method                               //
//    com->Undo(); // execute undo method                               //
//                                                                      //
// 4. Merged commands                                                   //
//                                                                      //
// It possible to group several commands together so an end user        //
// can undo and redo them with one command.                             //
//                                                                      //
//    TQCommand *update = new TQCommand(gPad, "Modified()");            //
//    com->Add(update);                                                 //
//                                                                      //
// 5. Macro commands                                                    //
//                                                                      //
// "Merging" allows to create macro commands, e.g.                      //
//                                                                      //
//    TQCommand *macro = new TQCommand("my macro");                     //
//    macro->Add(com1);                                                 //
//    macro->Add(com2);                                                 //
//    ...                                                               //
//                                                                      //
// During Redo operation commands composing macro command are executed  //
// sequentially in direct  order (first in first out). During Undo,     //
// they are executed in reverse order (last in first out).              //
//                                                                      //
// 6. Undo manager.                                                     //
//                                                                      //
// TQUndoManager is recorder of undo and redo operations. This is       //
// command history list which can be traversed backwards and upwards    //
// performing undo and redo operations.                                 //
// To register command TQUndoManager::Add(TObject*) method is used.     //
//                                                                      //
//    TQUndoManager *history = new TQUndoManager();                     //
//    history->Add(com);                                                //
//                                                                      //
// TQUndoManager::Add automatically invokes execution of command's      //
// Redo method.                                                         //
//                                                                      //
// Use TQUndoManager::Undo to undo commands in  history list.           //
// Redo is Undo for undo action. Use TQUndoManager::Redo method for that//
//                                                                      //
//////////////////////////////////////////////////////////////////////////

#include "Varargs.h"
#include "TQCommand.h"
#include "TQConnection.h"
#include "TDataType.h"
#include "stdarg.h"
#include "TROOT.h"

ClassImp(TQCommand)
ClassImp(TQUndoManager)

static TQCommand *gActiveCommand = 0;

//////////////////////// auxilary private functions ////////////////////////////
//______________________________________________________________________________
static char *ResolveTypes(const char *method)
{
   // Resolve any typedefs in the method signature. For example:
   // func(Float_t,Int_t) becomes func(float,int).
   // The returned string must be deleted by the user.

   if (!method || !*method) return 0;

   char *str = new char[strlen(method)+1];
   if (str) strcpy(str, method);

   TString res;

   char *s = strtok(str, "(");
   res = s;
   res += "(";

   Bool_t first = kTRUE;
   while ((s = strtok(0, ",)"))) {
      char *s1, s2 = 0;
      if ((s1 = strchr(s, '*'))) {
         *s1 = 0;
         s2  = '*';
      }
      if (!s1 && (s1 = strchr(s, '&'))) {
         *s1 = 0;
         s2  = '&';
      }
      TDataType *dt = gROOT->GetType(s);
      if (s1) *s1 = s2;
      if (!first) res += ",";
      if (dt) {
         res += dt->GetFullTypeName();
         if (s1) res += s1;
      } else
         res += s;
      first = kFALSE;
   }

   res += ")";

   delete [] str;
   str = new char[res.Length()+1];
   strcpy(str, res.Data());

   return str;
}

//______________________________________________________________________________
static char *CompressName(const char *method_name)
{
   // Removes "const" words and blanks from full (with prototype)
   // method name.
   //
   //  Example: CompressName(" Draw(const char *, const char *,
   //                               Option_t * , Int_t , Int_t)")
   //
   // Returns the string "Draw(char*,char*,char*,int,int)"
   // The returned string must be deleted by the user.

   if (!method_name || !*method_name) return 0;

   char *str = new char[strlen(method_name)+1];
   if (str) strcpy(str, method_name);

   char *tmp = str;

   // substitute "const" with white spaces
   while ((tmp = strstr(tmp,"const"))) {
      for (int i = 0; i < 5; i++) *(tmp+i) = ' ';
   }

   tmp = str;
   char *s;
   s = str;

   Bool_t quote = kFALSE;
   while (*tmp) {
      if (*tmp == '\"')
         quote = quote ? kFALSE : kTRUE;
      if (*tmp != ' ' || quote)
         *s++ = *tmp;
      tmp++;
   }
   *s = '\0';

   s = ResolveTypes(str);

   delete [] str;

   return s;
}

////////////////////////////////////////////////////////////////////////////////
//______________________________________________________________________________
void TQCommand::Init(const char *clname, void *obj, const char *redo, const char *undo)
{
   // common protected method used in several constructors

   char *credo = CompressName(redo);
   char *cundo = CompressName(undo);

   fNRargs = fNUargs = -1;
   fNewDelete = kFALSE;
   fObject = obj;

   fRedo = redo ? new TQConnection(clname, obj, credo) : 0;
   fUndo = undo ? new TQConnection(clname, obj, cundo) : fRedo;

   fRedoArgs = 0;
   fUndoArgs = 0;
   fStatus = 0;
   fState = 0;

   delete [] credo;
   delete [] cundo;

   if (!obj && !redo && !undo) { // macros
      fName = clname;
   }
}

//______________________________________________________________________________
TQCommand::TQCommand(const char *clname, void *obj, const char *redo,
                     const char *undo) : TList(), TQObject()
{
   // Constructor.
   //
   //   Input parameters:
   //     1. clname - class name.
   //     2. obj - an object
   //     3. redo - method or function to do/redo operation
   //     4. undo - method or function to undo operation
   //
   // Comments:
   //    - if either clname or obj is NULL that means that redo/undo is function
   //    - to specify default arguments for redo/undo method/function
   //       '=' must precede to argument value.
   //
   //  Example:
   //    TQCommand("TPad", gPad, "SetEditable(=kTRUE)", "SetEditable(=kFALSE)");
   //
   //    - undo method can be same as redo one. In that case undo parameter
   //       can be omitted.
   //
   //  Example:
   //    TQCommand("TPad", gPad, "SetFillStyle(Style_t)");

   Init(clname, obj, redo, undo);
}

//______________________________________________________________________________
TQCommand::TQCommand(TObject *obj, const char *redo, const char *undo) :
           TList(), TQObject()
{
   // Constructor.
   //
   //   Input parameters:
   //     1. obj - an object
   //     2. redo - method or function to do/redo operation
   //     3. undo - method or function to undo operation
   //
   // Comments:
   //    - to specify default arguments for redo/undo method/function
   //       '=' must precede to argument value.
   //
   //  Example:
   //    TQCommand(gPad, "SetEditable(=kTRUE)", "SetEditable(=kFALSE)");
   //
   //    - undo method can be same as redo one. In that case "undo"
   //       can parameter be omitted.
   //
   //  Example:
   //    TQCommand(gPad, "SetFillStyle(Style_t)");

   if (obj) Init(obj->ClassName(), obj, redo, undo);
   else Init(0, 0, redo, undo);
}

//______________________________________________________________________________
TQCommand::TQCommand(const TQCommand &com) : TList(), TQObject()
{
   // Copy constructor.
   
   fRedo = new TQConnection(*(com.fRedo));
   fUndo = new TQConnection(*(com.fUndo));
   
   fRedoArgs = 0;
   fUndoArgs = 0;
   fNRargs = com.fNRargs;
   fNUargs = com.fNUargs;
   
   if (fNRargs > 0) {
      fRedoArgs = new Long_t[fNRargs];
      for (int i = 0; i< fNRargs; i++) {
         fRedoArgs[i] = com.fRedoArgs[i];
      }
   }
   if (fNUargs > 0) {
      fUndoArgs = new Long_t[fNUargs];
      for (int i = 0; i < fNUargs; i++) {
         fUndoArgs[i] = com.fUndoArgs[i];
      }
   }
   fStatus = com.fStatus;
   fNewDelete = com.fNewDelete;
   fName = com.fName;
   fTitle = com.fTitle;
   fObject = com.fObject;
   fState = com.fState;
   
   // copy merged commands
   TIter next(&com);
   TQCommand *obj;
   while ((obj = (TQCommand*)next())) {
      TList::Add(new TQCommand(*obj));
   }
}

//______________________________________________________________________________
TQCommand::~TQCommand()
{
   // dtor.

   if (fRedo != fUndo) delete fUndo;

   delete fRedo;
   delete fRedoArgs;
   delete fUndoArgs;

   Delete();
}

//______________________________________________________________________________
TQCommand *TQCommand::GetCommand()
{
   // Return a command which is doing redo/undo action.
   //
   // This static method allows to set undo parameters dynamically, i.e.
   // during execution of Redo function.
   //
   // Example:
   //    For redo actions like TGTextEdit::DelChar() it is not possible to
   //    know ahead what character will be deleted.
   //    To set arguments for undo action ( e.g. TGTextEdit::InsChar(char)),
   //    one needs to call TQCommand::SetUndoArgs(1, character) from
   //    inside of TGTextEdit::DelChar() method, i.e.
   //
   //    TQCommand::GetCommand()->SetUndoArgs(1, somechar);

   return gActiveCommand;
}

//______________________________________________________________________________
void TQCommand::Delete(Option_t *opt)
{
   // If "opt" is not zero delete every merged command which option string is
   // equal to "opt". If "opt" is zero - delete all merged commands.

   if (!opt) {
      TList::Delete();
      return;
   }

   TObjLink *lnk = fFirst;
   TObjLink *sav;

   while (lnk) {
      sav = lnk->Next();
      TString ostr = lnk->GetOption();
      if (ostr.Contains(opt)) {   // remove command
         delete lnk->GetObject();
         Remove(lnk);
      }
      lnk = sav;
   }
}

//______________________________________________________________________________
Bool_t TQCommand::CanMerge(TQCommand *) const
{
   // Two commands can be merged if they can be composed into
   // a single command (Macro command).
   //
   // To allow merging commands user might override this function.

   return (!fRedo && !fUndo);
}

//______________________________________________________________________________
void TQCommand::Merge(TQCommand *c)
{
   // Add command to the list of merged commands.
   // This make it possible to group complex actions together so an end user
   // can undo and redo them with one command. Execution of TQUndoManager::Undo(),
   // TQUndoManager::Redo() methods only invokes the top level command as a whole.
   //
   // Merge method is analogous to logical join operation.
   //
   // Note:  Merge method invokes redo action.

   Add(c, "merge");
}

//______________________________________________________________________________
void TQCommand::Add(TObject *obj, Option_t *opt)
{
   // Add command to the list of merged commands.
   //
   // Option string can contain substrings:
   //  "compress" - try to compress input command
   //  "radd" - execute redo action of input command
   //  "uadd" - execute undo action of input command

   if (!obj->InheritsFrom(TQCommand::Class())) return;

   TQCommand *o = (TQCommand *)obj;
   TQCommand *c = (TQCommand *)Last();
   TString ostr = opt;

   if (c) {
      if (c->CanCompress(o) || (c->IsEqual(o) && ostr.Contains("compress"))) {
         c->Compress(o);
         return;
      }
   }
   TList::AddLast(o, opt);
   if (o->CanRedo() && ostr.Contains("radd")) o->Redo();
   if (o->CanUndo() && ostr.Contains("uadd")) o->Undo();
}

//______________________________________________________________________________
Bool_t TQCommand::CanCompress(TQCommand *c) const
{
   // By default, commands can be compressed if they are:
   //
   //  - equal
   //  - setter commands
   //
   // More complicated commands might want to override this function.

   return (IsEqual(c) && IsSetter());
}

//______________________________________________________________________________
void TQCommand::Compress(TQCommand *c)
{
   // Compress command. Compression is analogous to arithmetic "addition operation".
   //
   // Note:
   //    - The compressed command will be deleted.
   //    - Execution Compress method invokes Redo action with new redo arguments
   //      inheritied from compressed command.
   //
   // More complicated commands might want to override this function.

   for (int i = 0; i < fNRargs; i++) {
      fRedoArgs[i] = c->fRedoArgs[i];
   }
   Redo();
   fStatus--;   //do not change the state of command
   delete c;
}

//______________________________________________________________________________
Bool_t TQCommand::IsEqual(const TObject* obj) const
{
   // Equal comparison. The commands are equal if they are
   // applied to the same object and have the same Redo/Undo actions
   //
   // More complicated commands might want to override this function.

   if (!obj->InheritsFrom(TQCommand::Class())) return kFALSE;
   TQCommand *c = (TQCommand *)obj;
   if (!fRedo || !fUndo || (c->GetObject() != fObject)) return kFALSE;

   TString cname = fRedo->GetClassName();
   TString rname = fRedo->GetName();

   return ((cname == c->GetRedo()->GetClassName()) &&
           (rname == c->GetRedo()->GetName()));
}

//______________________________________________________________________________
Bool_t TQCommand::IsSetter() const
{
   // Returns kTRUE is command if Redo is the same as Undo function
   // and is the setter action.
   //
   // By default, all functions with names like "SetXXX" or "setXXX"
   // considered as setters. Another type of setters are Move, Resize operations
   //
   // More complicated commands might want to override this function.

   TString redo = GetRedoName();
   TString undo = GetUndoName();

   if (!redo || !undo || (redo != undo)) return kFALSE;

   return (redo.BeginsWith("Set") ||
           redo.BeginsWith("set") ||
           redo.BeginsWith("Move") ||
           redo.BeginsWith("move") ||
           redo.BeginsWith("Resize") ||
           redo.BeginsWith("resize"));
}

//______________________________________________________________________________
void TQCommand::SetArgs(Int_t narg, ...)
{
   // Set do/redo and undo parameters. The format is
   //    SetArgs(number_of_params, redo_params, undo_params)
   //
   // Example:
   //     move_command->SetArgs(2, 100, 100, 200, 200);
   //      2 params, (100,100) - do/redo position, (200,200) - undo position

   if (narg < 0) {
      return;
   } else if (!narg) {  // no arguments
      fNRargs = fNUargs = narg;
      return;
   }

   va_list ap;
   va_start(ap, narg);

   if (fNRargs != narg ) {
      delete fRedoArgs;
   }
   fRedoArgs = new Long_t[narg];

   if (fNUargs != narg ) {
      delete fUndoArgs;
   }
   fUndoArgs = new Long_t[narg];

   fNRargs = fNUargs = narg;

   Int_t i;
   for (i = 0; i < fNRargs; i++) {
      fRedoArgs[i] = va_arg(ap, Long_t);
   }
   for (i = 0; i < fNUargs; i++) {
      fUndoArgs[i] = va_arg(ap, Long_t);
   }
   va_end(ap);
}

//______________________________________________________________________________
void TQCommand::SetRedoArgs(Int_t narg, ...)
{
   // Set redo parameters. The format is
   //    SetRedoArgs(number_of_params, params)
   //
   // Example:
   //     move_command->SetRedoArgs(2, 100, 100);

   if (narg < 0) {
      return;
   } else if (!narg) {  // no arguments
      fNRargs = 0;
      return;
   }

   va_list ap;
   va_start(ap, narg);

   if (fNRargs != narg ) {
      delete fRedoArgs;
   }
   fRedoArgs = new Long_t[narg];

   fNRargs = narg;

   for (int i = 0; i < fNRargs; i++) {
      fRedoArgs[i] = va_arg(ap, Long_t);
   }
   va_end(ap);
}

//______________________________________________________________________________
void TQCommand::SetUndoArgs(Int_t narg, ...)
{
   // Set undo parameters. The format is
   //    SetUndoArgs(number_of_params, params)
   //
   // Example:
   //     move_command->SetUndoArgs(2, 200, 200);

   if (narg < 0) {
      return;
   } else if (!narg) {  // no arguments
      fNUargs = narg;
      return;
   }

   va_list ap;
   va_start(ap, narg);

   if (fNUargs != narg ) {
      delete fUndoArgs;
   }
   fUndoArgs = new Long_t[narg];

   fNUargs = narg;

   for (int i = 0; i < fNUargs; i++) {
      fUndoArgs[i] = va_arg(ap, Long_t);
   }
   va_end(ap);
}

//______________________________________________________________________________
Bool_t TQCommand::CanRedo() const
{
   // Returns kTRUE if Redo action is possible, kFALSE if it's not.
   // By default, only single sequential redo action is possible.

   return (fStatus <= 0);
}

//______________________________________________________________________________
Bool_t TQCommand::CanUndo() const
{
   // Returns kTRUE if Undo action is possible, kFALSE if it's not.
   // By default, only single tial undo action is possible.

   return (fStatus > 0);
}

//______________________________________________________________________________
void TQCommand::Redo(Option_t *)
{
   // Execute command and then smerged commands

   Bool_t done = kFALSE;
   fState = 1;

   gActiveCommand = this;

   if (fNRargs > 0) {
      if (fRedo) {
         fRedo->ExecuteMethod(fRedoArgs, fNRargs);
         done = kTRUE;
      }
   } else if (!fNRargs) {
      if (fRedo) {
         fRedo->ExecuteMethod();
         done = kTRUE;
      }
   }

   // execute merged commands
   TObjLink *lnk = fFirst;
   while (lnk) {
      TQCommand *c = (TQCommand *)lnk->GetObject();
      c->Redo();
      done = kTRUE;
      lnk = lnk->Next();
   }

   if (done) Emit("Redo()");
   fStatus++;
   fState = 0;
   gActiveCommand = 0;
}

//______________________________________________________________________________
void TQCommand::Undo(Option_t *)
{
   // Unexecute all merged commands and the command.
   // Merged commands are executed in reverse order.

   Bool_t done = kFALSE;
   fState = -1;

   gActiveCommand = this;

   // unexecute merged commands
   TObjLink *lnk = fLast;
   while (lnk) {
      TQCommand *c = (TQCommand *)lnk->GetObject();
      TString opt = lnk->GetOption();
      TObjLink *sav = lnk->Prev();
      c->Undo();
      done = kTRUE;
      if (opt.Contains("remove")) {   // remove  command
         delete lnk->GetObject();
         Remove(lnk);
      }
      lnk = sav;
   }
   if (fNUargs > 0) {
      if (fUndo) {
         fUndo->ExecuteMethod(fUndoArgs, fNUargs);
         done = kTRUE;
      }
   } else if (!fNUargs) {
      if (fUndo) {
         fUndo->ExecuteMethod();
         done = kTRUE;
      }
   }

   if (done) Emit("Undo()");
   fStatus--;
   fState = 0;
   gActiveCommand = 0;
}

//______________________________________________________________________________
const char *TQCommand::GetName() const
{
   // Returns the command name. Default name is "ClassName::RedoName(args)"
   // If list of merged commands is not empty the name is
   // "ClassName::RedoName(args):cname1:cname2 ..."

   const Int_t maxname = 100;

   if (!fName.IsNull()) return fName.Data();

   TString name;

   if (fRedo) {
      if (fRedo->GetClassName()) {
         name = fRedo->GetClassName();
      }
      name += "::";
      name += fRedo->GetName();
   }
   TQCommand *c;
   TObjLink *lnk = fFirst;

   while (lnk && (fName.Length() < maxname)) {
      c = (TQCommand *)lnk->GetObject();
      name += ":";
      name += c->GetName();
      lnk = lnk->Next();
   }

   // trick against "constness"
   TQCommand *m = (TQCommand *)this;
   m->fName = name;

   return name.Data();
}

//______________________________________________________________________________
const char *TQCommand::GetTitle() const
{
   // Returns command description.
   // By default, "ClassName::RedoName(args)_ClassName::UndoName(args)"

   if (!fTitle.IsNull()) return fTitle.Data();

   TString title = GetName();

   if (fUndo) {
      title += "_";
      title += fUndo->GetClassName();
      title += "::";
      if (fUndo->GetName())  title += fUndo->GetName();
   }
   return title.Data();
}

//______________________________________________________________________________
const char *TQCommand::GetRedoName() const
{
   // Returns the name of redo command

   return (fRedo ? fRedo->GetName() : 0);
}

//______________________________________________________________________________
const char *TQCommand::GetUndoName() const
{
   // Returns the name of undo command

   return (fUndo ? fUndo->GetName() : 0);
}

//______________________________________________________________________________
Long_t *TQCommand::GetRedoArgs() const
{
   // Returns a pointer to array of redo arguments

   return fRedoArgs;
}

//______________________________________________________________________________
Long_t *TQCommand::GetUndoArgs() const
{
   // Returns a pointer to array of undo arguments

   return fUndoArgs;
}

//______________________________________________________________________________
Int_t TQCommand::GetNRargs() const
{
   // Returns a number of redo arguments

   return fNRargs;
}

//______________________________________________________________________________
Int_t TQCommand::GetNUargs() const
{
   // Returns a number of undo arguments

   return fNUargs;
}

//______________________________________________________________________________
void *TQCommand::GetObject() const
{
   // Returns an object for which undo redo acions are applied

   return fObject;
}

//______________________________________________________________________________
Int_t TQCommand::GetStatus() const
{
   // Returns a number of sequential undo or redo operations

   return fStatus;
}

//______________________________________________________________________________
Bool_t TQCommand::IsMacro() const
{
   // Returns kTRUE if neither redo nor undo action specified

   return (!fRedo && !fUndo);
}

//______________________________________________________________________________
Bool_t TQCommand::IsUndoing() const
{
   // Undo action is in progress

   return (fState < 0);
}

//______________________________________________________________________________
Bool_t TQCommand::IsRedoing() const
{
   // Redo action is in progress

   return (fState > 0);
}

//______________________________________________________________________________
Bool_t TQCommand::IsExecuting() const
{
   // Returns kTRUE if command execution is in progress

   return fState;
}

//______________________________________________________________________________
void TQCommand::SetName(const char *name)
{
   // Sets name of the command

   fName = name;
}

//______________________________________________________________________________
void TQCommand::SetTitle(const char *title)
{
   // Sets description of the command

   fTitle = title;
}

//______________________________________________________________________________
void TQCommand::ls(Option_t *) const
{
   // ls this command and merged commands

   TString name = GetName();
   printf("%d %s\n", fStatus, name.Data());

   TObjLink *lnk = fFirst;
   while (lnk) {
      printf("\t");
      lnk->GetObject()->ls();
      lnk = lnk->Next();
   }
}

//______________________________________________________________________________
void TQCommand::PrintCollectionHeader(Option_t* /*option*/) const
{
   // Print collection header.

   TROOT::IndentLevel();
   printf("%d %s\n", fStatus, GetName()); 
}

///////////////////////////////////////////////////////////////////////////////
//______________________________________________________________________________
TQUndoManager::TQUndoManager() : TQCommand(0, 0, 0, 0)
{
   // Constructor

   fCursor = 0;
   fLimit = kMaxUInt;   // maximum value for UInt_t
   fLogging = kFALSE;
   fLogBook = 0;
   fCurrent = 0;
}

//______________________________________________________________________________
TQUndoManager::~TQUndoManager()
{
   // Destructor

   Delete();

   if (fLogBook) {
      delete fLogBook;
   }
}

//______________________________________________________________________________
void TQUndoManager::ls(Option_t *option) const
{
   // Lists all commands in stack

   if (!IsEmpty()) {
      TObjLink *lnk = fFirst;
      while (lnk) {
         if (lnk == fCursor) {
            printf("->");
         } else {
            printf("  ");
         }
         TQCommand *com = (TQCommand*)lnk->GetObject();
         com->ls(option);
         lnk = lnk->Next();
      }
   }
}

//______________________________________________________________________________
void TQUndoManager::PrintCollectionEntry(TObject* entry, Option_t* option,
                                         Int_t /*recurse*/) const
{
   // Print collection entry.

   TQCommand *com = (TQCommand*) entry;
   TROOT::IndentLevel();
   if (fCursor && fCursor->GetObject() == entry) {
      printf("->");
   } else {
      printf("  ");
   }
   com->ls(option);
}

//______________________________________________________________________________
void  TQUndoManager::SetLogging(Bool_t on)
{
   // Start logging. Delete all previous log records
   // Note: logging is not implemented yet

   fLogging = on;

   if (fLogging) {
      if (fLogBook) {
         fLogBook->Delete();
      } else {
         fLogBook = new TList();
      }
   }
}

//______________________________________________________________________________
void TQUndoManager::Add(TObject *obj, Option_t *opt)
{
   // Add command to the stack of commands.
   // Command's redo action will be executed.
   //
   // option string can contain the following substrings:
   //    "merge" - input command will be merged
   //    "compress" - input command will be compressed

   if (!obj->InheritsFrom(TQCommand::Class())) return;

   TQCommand *o = (TQCommand *)obj;
   TQCommand *c;
   Bool_t onredo = fCursor && fCursor->Next();
   TString ostr = onredo ? "1radd" : "0radd"; // execute redo on add
   if (opt) ostr += opt;

   if (fState) { // undo/redo in progress
      c = fCurrent;
      if (c) {
         fCurrent = o;
         c->Add(o, "remove");   // add nested command
      }
      return;
   }

   // delete all commands after cursor position
   if (fCursor && fCursor->Next()) {
      TObjLink *lnk = fCursor->Next();
      TObjLink *sav;
      while (lnk) {
         sav = lnk->Next();
         delete lnk->GetObject();
         Remove(lnk);
         lnk = sav;
      }
   }

   c = GetCursor();
   if (c) {
      if (c->CanCompress(o) || c->CanMerge(o) ||
          ostr.Contains("merge") || ostr.Contains("compress")) {
         fState = 1;
         c->Add(o, ostr.Data());
         fState = 0;
         return;
      }
   }

   TList::AddLast(obj, ostr.Data());
   fCursor = fLast;
   Redo(ostr.Data());

   if ((fSize > 0) && ((UInt_t)fSize > fLimit)) {
      Remove(fFirst);
   }
}

//______________________________________________________________________________
void TQUndoManager::CurrentChanged(TQCommand *c)
{
   // emit signal

   Emit("CurrentChanged(TQCommand*)", (long)c);
}

//______________________________________________________________________________
void TQUndoManager::Undo(Option_t *option)
{
   // Performs undo action. Move cursor position backward in history stack

   Bool_t done = kFALSE;
   if (!CanUndo()) return;

   TQCommand *sav = fCurrent;
   TQCommand *c = (TQCommand*)fCursor->GetObject();

   if (c->CanUndo()) {
      fState = -1;
      fCurrent = c;
      fCurrent->Undo(option);
      fState = 0;
      done = kTRUE;
      fCursor = fCursor->Prev() ? fCursor->Prev() : fFirst;
   } else {
      fCursor = fCursor->Prev();
      fCurrent = (TQCommand*)fCursor->GetObject();
      fState = -1;
      fCurrent->Undo(option);
      fState = 0;
      done = kTRUE;
   }
   if (done && fLogging && fLogBook) {
      fLogBook->Add(new TQCommand(*fCurrent));
   }
   if (sav != fCurrent) CurrentChanged(fCurrent);
}

//______________________________________________________________________________
void TQUndoManager::Redo(Option_t *option)
{
   // Performs redo action. Move cursor position forward in history stack

   Bool_t done = kFALSE;
   if (!CanRedo()) return;

   TQCommand *sav = fCurrent;
   TQCommand *c = (TQCommand*)fCursor->GetObject();

   if (c->CanRedo()) {
      fState = 1;
      fCurrent = c;
      fCurrent->Redo(option);
      fState = 0;
      done = kTRUE;
      fCursor = fCursor->Next() ? fCursor->Next() : fLast;
   } else {
      fCursor = fCursor->Next();
      fCurrent = (TQCommand*)fCursor->GetObject();
      fState = 1;
      fCurrent->Redo(option);
      fState = 0;
      done = kTRUE;
   }
   if (done && fLogging && fLogBook) {
      fLogBook->Add(new TQCommand(*fCurrent));
   }
   if (sav != fCurrent) CurrentChanged(fCurrent);
}

//______________________________________________________________________________
Bool_t TQUndoManager::CanRedo() const
{
   // Returns kTRUE if redo action is possible

   if (!fCursor) return kFALSE;

   TQCommand *c = (TQCommand*)fCursor->GetObject();
   if (c->CanRedo()) return kTRUE;

   c = fCursor->Next() ? (TQCommand*)fCursor->Next()->GetObject() : 0;
   return (c && c->CanRedo());
}

//______________________________________________________________________________
Bool_t TQUndoManager::CanUndo() const
{
   // Returns kTRUE if undo action is possible

   if (!fCursor) return kFALSE;

   TQCommand *c = (TQCommand*)fCursor->GetObject();
   if (c->CanUndo()) return kTRUE;

   c = fCursor->Prev() ? (TQCommand*)fCursor->Prev()->GetObject() : 0;
   return (c && c->CanUndo());
}

//_____________________________________________________________________________
Bool_t TQUndoManager::IsLogging() const
{
   // Returns kTRUE if logging is ON

   return fLogging;
}

//_____________________________________________________________________________
TQCommand *TQUndoManager::GetCurrent() const
{
   // Returns the last executed command

   return fCurrent;
}

//_____________________________________________________________________________
TQCommand *TQUndoManager::GetCursor() const
{
   // Returns a command correspondent to the current cursor position in stack

   return (TQCommand*)(fCursor ? fCursor->GetObject() : 0);
}

//_____________________________________________________________________________
void TQUndoManager::SetLimit(UInt_t limit)
{
   // Returns a maximum number of commands which could be located in stack

   fLimit = limit;
}

//_____________________________________________________________________________
UInt_t TQUndoManager::GetLimit() const
{
   // Returns a maximum number of commands which  could be located in stack

   return fLimit;
}
 TQCommand.cxx:1
 TQCommand.cxx:2
 TQCommand.cxx:3
 TQCommand.cxx:4
 TQCommand.cxx:5
 TQCommand.cxx:6
 TQCommand.cxx:7
 TQCommand.cxx:8
 TQCommand.cxx:9
 TQCommand.cxx:10
 TQCommand.cxx:11
 TQCommand.cxx:12
 TQCommand.cxx:13
 TQCommand.cxx:14
 TQCommand.cxx:15
 TQCommand.cxx:16
 TQCommand.cxx:17
 TQCommand.cxx:18
 TQCommand.cxx:19
 TQCommand.cxx:20
 TQCommand.cxx:21
 TQCommand.cxx:22
 TQCommand.cxx:23
 TQCommand.cxx:24
 TQCommand.cxx:25
 TQCommand.cxx:26
 TQCommand.cxx:27
 TQCommand.cxx:28
 TQCommand.cxx:29
 TQCommand.cxx:30
 TQCommand.cxx:31
 TQCommand.cxx:32
 TQCommand.cxx:33
 TQCommand.cxx:34
 TQCommand.cxx:35
 TQCommand.cxx:36
 TQCommand.cxx:37
 TQCommand.cxx:38
 TQCommand.cxx:39
 TQCommand.cxx:40
 TQCommand.cxx:41
 TQCommand.cxx:42
 TQCommand.cxx:43
 TQCommand.cxx:44
 TQCommand.cxx:45
 TQCommand.cxx:46
 TQCommand.cxx:47
 TQCommand.cxx:48
 TQCommand.cxx:49
 TQCommand.cxx:50
 TQCommand.cxx:51
 TQCommand.cxx:52
 TQCommand.cxx:53
 TQCommand.cxx:54
 TQCommand.cxx:55
 TQCommand.cxx:56
 TQCommand.cxx:57
 TQCommand.cxx:58
 TQCommand.cxx:59
 TQCommand.cxx:60
 TQCommand.cxx:61
 TQCommand.cxx:62
 TQCommand.cxx:63
 TQCommand.cxx:64
 TQCommand.cxx:65
 TQCommand.cxx:66
 TQCommand.cxx:67
 TQCommand.cxx:68
 TQCommand.cxx:69
 TQCommand.cxx:70
 TQCommand.cxx:71
 TQCommand.cxx:72
 TQCommand.cxx:73
 TQCommand.cxx:74
 TQCommand.cxx:75
 TQCommand.cxx:76
 TQCommand.cxx:77
 TQCommand.cxx:78
 TQCommand.cxx:79
 TQCommand.cxx:80
 TQCommand.cxx:81
 TQCommand.cxx:82
 TQCommand.cxx:83
 TQCommand.cxx:84
 TQCommand.cxx:85
 TQCommand.cxx:86
 TQCommand.cxx:87
 TQCommand.cxx:88
 TQCommand.cxx:89
 TQCommand.cxx:90
 TQCommand.cxx:91
 TQCommand.cxx:92
 TQCommand.cxx:93
 TQCommand.cxx:94
 TQCommand.cxx:95
 TQCommand.cxx:96
 TQCommand.cxx:97
 TQCommand.cxx:98
 TQCommand.cxx:99
 TQCommand.cxx:100
 TQCommand.cxx:101
 TQCommand.cxx:102
 TQCommand.cxx:103
 TQCommand.cxx:104
 TQCommand.cxx:105
 TQCommand.cxx:106
 TQCommand.cxx:107
 TQCommand.cxx:108
 TQCommand.cxx:109
 TQCommand.cxx:110
 TQCommand.cxx:111
 TQCommand.cxx:112
 TQCommand.cxx:113
 TQCommand.cxx:114
 TQCommand.cxx:115
 TQCommand.cxx:116
 TQCommand.cxx:117
 TQCommand.cxx:118
 TQCommand.cxx:119
 TQCommand.cxx:120
 TQCommand.cxx:121
 TQCommand.cxx:122
 TQCommand.cxx:123
 TQCommand.cxx:124
 TQCommand.cxx:125
 TQCommand.cxx:126
 TQCommand.cxx:127
 TQCommand.cxx:128
 TQCommand.cxx:129
 TQCommand.cxx:130
 TQCommand.cxx:131
 TQCommand.cxx:132
 TQCommand.cxx:133
 TQCommand.cxx:134
 TQCommand.cxx:135
 TQCommand.cxx:136
 TQCommand.cxx:137
 TQCommand.cxx:138
 TQCommand.cxx:139
 TQCommand.cxx:140
 TQCommand.cxx:141
 TQCommand.cxx:142
 TQCommand.cxx:143
 TQCommand.cxx:144
 TQCommand.cxx:145
 TQCommand.cxx:146
 TQCommand.cxx:147
 TQCommand.cxx:148
 TQCommand.cxx:149
 TQCommand.cxx:150
 TQCommand.cxx:151
 TQCommand.cxx:152
 TQCommand.cxx:153
 TQCommand.cxx:154
 TQCommand.cxx:155
 TQCommand.cxx:156
 TQCommand.cxx:157
 TQCommand.cxx:158
 TQCommand.cxx:159
 TQCommand.cxx:160
 TQCommand.cxx:161
 TQCommand.cxx:162
 TQCommand.cxx:163
 TQCommand.cxx:164
 TQCommand.cxx:165
 TQCommand.cxx:166
 TQCommand.cxx:167
 TQCommand.cxx:168
 TQCommand.cxx:169
 TQCommand.cxx:170
 TQCommand.cxx:171
 TQCommand.cxx:172
 TQCommand.cxx:173
 TQCommand.cxx:174
 TQCommand.cxx:175
 TQCommand.cxx:176
 TQCommand.cxx:177
 TQCommand.cxx:178
 TQCommand.cxx:179
 TQCommand.cxx:180
 TQCommand.cxx:181
 TQCommand.cxx:182
 TQCommand.cxx:183
 TQCommand.cxx:184
 TQCommand.cxx:185
 TQCommand.cxx:186
 TQCommand.cxx:187
 TQCommand.cxx:188
 TQCommand.cxx:189
 TQCommand.cxx:190
 TQCommand.cxx:191
 TQCommand.cxx:192
 TQCommand.cxx:193
 TQCommand.cxx:194
 TQCommand.cxx:195
 TQCommand.cxx:196
 TQCommand.cxx:197
 TQCommand.cxx:198
 TQCommand.cxx:199
 TQCommand.cxx:200
 TQCommand.cxx:201
 TQCommand.cxx:202
 TQCommand.cxx:203
 TQCommand.cxx:204
 TQCommand.cxx:205
 TQCommand.cxx:206
 TQCommand.cxx:207
 TQCommand.cxx:208
 TQCommand.cxx:209
 TQCommand.cxx:210
 TQCommand.cxx:211
 TQCommand.cxx:212
 TQCommand.cxx:213
 TQCommand.cxx:214
 TQCommand.cxx:215
 TQCommand.cxx:216
 TQCommand.cxx:217
 TQCommand.cxx:218
 TQCommand.cxx:219
 TQCommand.cxx:220
 TQCommand.cxx:221
 TQCommand.cxx:222
 TQCommand.cxx:223
 TQCommand.cxx:224
 TQCommand.cxx:225
 TQCommand.cxx:226
 TQCommand.cxx:227
 TQCommand.cxx:228
 TQCommand.cxx:229
 TQCommand.cxx:230
 TQCommand.cxx:231
 TQCommand.cxx:232
 TQCommand.cxx:233
 TQCommand.cxx:234
 TQCommand.cxx:235
 TQCommand.cxx:236
 TQCommand.cxx:237
 TQCommand.cxx:238
 TQCommand.cxx:239
 TQCommand.cxx:240
 TQCommand.cxx:241
 TQCommand.cxx:242
 TQCommand.cxx:243
 TQCommand.cxx:244
 TQCommand.cxx:245
 TQCommand.cxx:246
 TQCommand.cxx:247
 TQCommand.cxx:248
 TQCommand.cxx:249
 TQCommand.cxx:250
 TQCommand.cxx:251
 TQCommand.cxx:252
 TQCommand.cxx:253
 TQCommand.cxx:254
 TQCommand.cxx:255
 TQCommand.cxx:256
 TQCommand.cxx:257
 TQCommand.cxx:258
 TQCommand.cxx:259
 TQCommand.cxx:260
 TQCommand.cxx:261
 TQCommand.cxx:262
 TQCommand.cxx:263
 TQCommand.cxx:264
 TQCommand.cxx:265
 TQCommand.cxx:266
 TQCommand.cxx:267
 TQCommand.cxx:268
 TQCommand.cxx:269
 TQCommand.cxx:270
 TQCommand.cxx:271
 TQCommand.cxx:272
 TQCommand.cxx:273
 TQCommand.cxx:274
 TQCommand.cxx:275
 TQCommand.cxx:276
 TQCommand.cxx:277
 TQCommand.cxx:278
 TQCommand.cxx:279
 TQCommand.cxx:280
 TQCommand.cxx:281
 TQCommand.cxx:282
 TQCommand.cxx:283
 TQCommand.cxx:284
 TQCommand.cxx:285
 TQCommand.cxx:286
 TQCommand.cxx:287
 TQCommand.cxx:288
 TQCommand.cxx:289
 TQCommand.cxx:290
 TQCommand.cxx:291
 TQCommand.cxx:292
 TQCommand.cxx:293
 TQCommand.cxx:294
 TQCommand.cxx:295
 TQCommand.cxx:296
 TQCommand.cxx:297
 TQCommand.cxx:298
 TQCommand.cxx:299
 TQCommand.cxx:300
 TQCommand.cxx:301
 TQCommand.cxx:302
 TQCommand.cxx:303
 TQCommand.cxx:304
 TQCommand.cxx:305
 TQCommand.cxx:306
 TQCommand.cxx:307
 TQCommand.cxx:308
 TQCommand.cxx:309
 TQCommand.cxx:310
 TQCommand.cxx:311
 TQCommand.cxx:312
 TQCommand.cxx:313
 TQCommand.cxx:314
 TQCommand.cxx:315
 TQCommand.cxx:316
 TQCommand.cxx:317
 TQCommand.cxx:318
 TQCommand.cxx:319
 TQCommand.cxx:320
 TQCommand.cxx:321
 TQCommand.cxx:322
 TQCommand.cxx:323
 TQCommand.cxx:324
 TQCommand.cxx:325
 TQCommand.cxx:326
 TQCommand.cxx:327
 TQCommand.cxx:328
 TQCommand.cxx:329
 TQCommand.cxx:330
 TQCommand.cxx:331
 TQCommand.cxx:332
 TQCommand.cxx:333
 TQCommand.cxx:334
 TQCommand.cxx:335
 TQCommand.cxx:336
 TQCommand.cxx:337
 TQCommand.cxx:338
 TQCommand.cxx:339
 TQCommand.cxx:340
 TQCommand.cxx:341
 TQCommand.cxx:342
 TQCommand.cxx:343
 TQCommand.cxx:344
 TQCommand.cxx:345
 TQCommand.cxx:346
 TQCommand.cxx:347
 TQCommand.cxx:348
 TQCommand.cxx:349
 TQCommand.cxx:350
 TQCommand.cxx:351
 TQCommand.cxx:352
 TQCommand.cxx:353
 TQCommand.cxx:354
 TQCommand.cxx:355
 TQCommand.cxx:356
 TQCommand.cxx:357
 TQCommand.cxx:358
 TQCommand.cxx:359
 TQCommand.cxx:360
 TQCommand.cxx:361
 TQCommand.cxx:362
 TQCommand.cxx:363
 TQCommand.cxx:364
 TQCommand.cxx:365
 TQCommand.cxx:366
 TQCommand.cxx:367
 TQCommand.cxx:368
 TQCommand.cxx:369
 TQCommand.cxx:370
 TQCommand.cxx:371
 TQCommand.cxx:372
 TQCommand.cxx:373
 TQCommand.cxx:374
 TQCommand.cxx:375
 TQCommand.cxx:376
 TQCommand.cxx:377
 TQCommand.cxx:378
 TQCommand.cxx:379
 TQCommand.cxx:380
 TQCommand.cxx:381
 TQCommand.cxx:382
 TQCommand.cxx:383
 TQCommand.cxx:384
 TQCommand.cxx:385
 TQCommand.cxx:386
 TQCommand.cxx:387
 TQCommand.cxx:388
 TQCommand.cxx:389
 TQCommand.cxx:390
 TQCommand.cxx:391
 TQCommand.cxx:392
 TQCommand.cxx:393
 TQCommand.cxx:394
 TQCommand.cxx:395
 TQCommand.cxx:396
 TQCommand.cxx:397
 TQCommand.cxx:398
 TQCommand.cxx:399
 TQCommand.cxx:400
 TQCommand.cxx:401
 TQCommand.cxx:402
 TQCommand.cxx:403
 TQCommand.cxx:404
 TQCommand.cxx:405
 TQCommand.cxx:406
 TQCommand.cxx:407
 TQCommand.cxx:408
 TQCommand.cxx:409
 TQCommand.cxx:410
 TQCommand.cxx:411
 TQCommand.cxx:412
 TQCommand.cxx:413
 TQCommand.cxx:414
 TQCommand.cxx:415
 TQCommand.cxx:416
 TQCommand.cxx:417
 TQCommand.cxx:418
 TQCommand.cxx:419
 TQCommand.cxx:420
 TQCommand.cxx:421
 TQCommand.cxx:422
 TQCommand.cxx:423
 TQCommand.cxx:424
 TQCommand.cxx:425
 TQCommand.cxx:426
 TQCommand.cxx:427
 TQCommand.cxx:428
 TQCommand.cxx:429
 TQCommand.cxx:430
 TQCommand.cxx:431
 TQCommand.cxx:432
 TQCommand.cxx:433
 TQCommand.cxx:434
 TQCommand.cxx:435
 TQCommand.cxx:436
 TQCommand.cxx:437
 TQCommand.cxx:438
 TQCommand.cxx:439
 TQCommand.cxx:440
 TQCommand.cxx:441
 TQCommand.cxx:442
 TQCommand.cxx:443
 TQCommand.cxx:444
 TQCommand.cxx:445
 TQCommand.cxx:446
 TQCommand.cxx:447
 TQCommand.cxx:448
 TQCommand.cxx:449
 TQCommand.cxx:450
 TQCommand.cxx:451
 TQCommand.cxx:452
 TQCommand.cxx:453
 TQCommand.cxx:454
 TQCommand.cxx:455
 TQCommand.cxx:456
 TQCommand.cxx:457
 TQCommand.cxx:458
 TQCommand.cxx:459
 TQCommand.cxx:460
 TQCommand.cxx:461
 TQCommand.cxx:462
 TQCommand.cxx:463
 TQCommand.cxx:464
 TQCommand.cxx:465
 TQCommand.cxx:466
 TQCommand.cxx:467
 TQCommand.cxx:468
 TQCommand.cxx:469
 TQCommand.cxx:470
 TQCommand.cxx:471
 TQCommand.cxx:472
 TQCommand.cxx:473
 TQCommand.cxx:474
 TQCommand.cxx:475
 TQCommand.cxx:476
 TQCommand.cxx:477
 TQCommand.cxx:478
 TQCommand.cxx:479
 TQCommand.cxx:480
 TQCommand.cxx:481
 TQCommand.cxx:482
 TQCommand.cxx:483
 TQCommand.cxx:484
 TQCommand.cxx:485
 TQCommand.cxx:486
 TQCommand.cxx:487
 TQCommand.cxx:488
 TQCommand.cxx:489
 TQCommand.cxx:490
 TQCommand.cxx:491
 TQCommand.cxx:492
 TQCommand.cxx:493
 TQCommand.cxx:494
 TQCommand.cxx:495
 TQCommand.cxx:496
 TQCommand.cxx:497
 TQCommand.cxx:498
 TQCommand.cxx:499
 TQCommand.cxx:500
 TQCommand.cxx:501
 TQCommand.cxx:502
 TQCommand.cxx:503
 TQCommand.cxx:504
 TQCommand.cxx:505
 TQCommand.cxx:506
 TQCommand.cxx:507
 TQCommand.cxx:508
 TQCommand.cxx:509
 TQCommand.cxx:510
 TQCommand.cxx:511
 TQCommand.cxx:512
 TQCommand.cxx:513
 TQCommand.cxx:514
 TQCommand.cxx:515
 TQCommand.cxx:516
 TQCommand.cxx:517
 TQCommand.cxx:518
 TQCommand.cxx:519
 TQCommand.cxx:520
 TQCommand.cxx:521
 TQCommand.cxx:522
 TQCommand.cxx:523
 TQCommand.cxx:524
 TQCommand.cxx:525
 TQCommand.cxx:526
 TQCommand.cxx:527
 TQCommand.cxx:528
 TQCommand.cxx:529
 TQCommand.cxx:530
 TQCommand.cxx:531
 TQCommand.cxx:532
 TQCommand.cxx:533
 TQCommand.cxx:534
 TQCommand.cxx:535
 TQCommand.cxx:536
 TQCommand.cxx:537
 TQCommand.cxx:538
 TQCommand.cxx:539
 TQCommand.cxx:540
 TQCommand.cxx:541
 TQCommand.cxx:542
 TQCommand.cxx:543
 TQCommand.cxx:544
 TQCommand.cxx:545
 TQCommand.cxx:546
 TQCommand.cxx:547
 TQCommand.cxx:548
 TQCommand.cxx:549
 TQCommand.cxx:550
 TQCommand.cxx:551
 TQCommand.cxx:552
 TQCommand.cxx:553
 TQCommand.cxx:554
 TQCommand.cxx:555
 TQCommand.cxx:556
 TQCommand.cxx:557
 TQCommand.cxx:558
 TQCommand.cxx:559
 TQCommand.cxx:560
 TQCommand.cxx:561
 TQCommand.cxx:562
 TQCommand.cxx:563
 TQCommand.cxx:564
 TQCommand.cxx:565
 TQCommand.cxx:566
 TQCommand.cxx:567
 TQCommand.cxx:568
 TQCommand.cxx:569
 TQCommand.cxx:570
 TQCommand.cxx:571
 TQCommand.cxx:572
 TQCommand.cxx:573
 TQCommand.cxx:574
 TQCommand.cxx:575
 TQCommand.cxx:576
 TQCommand.cxx:577
 TQCommand.cxx:578
 TQCommand.cxx:579
 TQCommand.cxx:580
 TQCommand.cxx:581
 TQCommand.cxx:582
 TQCommand.cxx:583
 TQCommand.cxx:584
 TQCommand.cxx:585
 TQCommand.cxx:586
 TQCommand.cxx:587
 TQCommand.cxx:588
 TQCommand.cxx:589
 TQCommand.cxx:590
 TQCommand.cxx:591
 TQCommand.cxx:592
 TQCommand.cxx:593
 TQCommand.cxx:594
 TQCommand.cxx:595
 TQCommand.cxx:596
 TQCommand.cxx:597
 TQCommand.cxx:598
 TQCommand.cxx:599
 TQCommand.cxx:600
 TQCommand.cxx:601
 TQCommand.cxx:602
 TQCommand.cxx:603
 TQCommand.cxx:604
 TQCommand.cxx:605
 TQCommand.cxx:606
 TQCommand.cxx:607
 TQCommand.cxx:608
 TQCommand.cxx:609
 TQCommand.cxx:610
 TQCommand.cxx:611
 TQCommand.cxx:612
 TQCommand.cxx:613
 TQCommand.cxx:614
 TQCommand.cxx:615
 TQCommand.cxx:616
 TQCommand.cxx:617
 TQCommand.cxx:618
 TQCommand.cxx:619
 TQCommand.cxx:620
 TQCommand.cxx:621
 TQCommand.cxx:622
 TQCommand.cxx:623
 TQCommand.cxx:624
 TQCommand.cxx:625
 TQCommand.cxx:626
 TQCommand.cxx:627
 TQCommand.cxx:628
 TQCommand.cxx:629
 TQCommand.cxx:630
 TQCommand.cxx:631
 TQCommand.cxx:632
 TQCommand.cxx:633
 TQCommand.cxx:634
 TQCommand.cxx:635
 TQCommand.cxx:636
 TQCommand.cxx:637
 TQCommand.cxx:638
 TQCommand.cxx:639
 TQCommand.cxx:640
 TQCommand.cxx:641
 TQCommand.cxx:642
 TQCommand.cxx:643
 TQCommand.cxx:644
 TQCommand.cxx:645
 TQCommand.cxx:646
 TQCommand.cxx:647
 TQCommand.cxx:648
 TQCommand.cxx:649
 TQCommand.cxx:650
 TQCommand.cxx:651
 TQCommand.cxx:652
 TQCommand.cxx:653
 TQCommand.cxx:654
 TQCommand.cxx:655
 TQCommand.cxx:656
 TQCommand.cxx:657
 TQCommand.cxx:658
 TQCommand.cxx:659
 TQCommand.cxx:660
 TQCommand.cxx:661
 TQCommand.cxx:662
 TQCommand.cxx:663
 TQCommand.cxx:664
 TQCommand.cxx:665
 TQCommand.cxx:666
 TQCommand.cxx:667
 TQCommand.cxx:668
 TQCommand.cxx:669
 TQCommand.cxx:670
 TQCommand.cxx:671
 TQCommand.cxx:672
 TQCommand.cxx:673
 TQCommand.cxx:674
 TQCommand.cxx:675
 TQCommand.cxx:676
 TQCommand.cxx:677
 TQCommand.cxx:678
 TQCommand.cxx:679
 TQCommand.cxx:680
 TQCommand.cxx:681
 TQCommand.cxx:682
 TQCommand.cxx:683
 TQCommand.cxx:684
 TQCommand.cxx:685
 TQCommand.cxx:686
 TQCommand.cxx:687
 TQCommand.cxx:688
 TQCommand.cxx:689
 TQCommand.cxx:690
 TQCommand.cxx:691
 TQCommand.cxx:692
 TQCommand.cxx:693
 TQCommand.cxx:694
 TQCommand.cxx:695
 TQCommand.cxx:696
 TQCommand.cxx:697
 TQCommand.cxx:698
 TQCommand.cxx:699
 TQCommand.cxx:700
 TQCommand.cxx:701
 TQCommand.cxx:702
 TQCommand.cxx:703
 TQCommand.cxx:704
 TQCommand.cxx:705
 TQCommand.cxx:706
 TQCommand.cxx:707
 TQCommand.cxx:708
 TQCommand.cxx:709
 TQCommand.cxx:710
 TQCommand.cxx:711
 TQCommand.cxx:712
 TQCommand.cxx:713
 TQCommand.cxx:714
 TQCommand.cxx:715
 TQCommand.cxx:716
 TQCommand.cxx:717
 TQCommand.cxx:718
 TQCommand.cxx:719
 TQCommand.cxx:720
 TQCommand.cxx:721
 TQCommand.cxx:722
 TQCommand.cxx:723
 TQCommand.cxx:724
 TQCommand.cxx:725
 TQCommand.cxx:726
 TQCommand.cxx:727
 TQCommand.cxx:728
 TQCommand.cxx:729
 TQCommand.cxx:730
 TQCommand.cxx:731
 TQCommand.cxx:732
 TQCommand.cxx:733
 TQCommand.cxx:734
 TQCommand.cxx:735
 TQCommand.cxx:736
 TQCommand.cxx:737
 TQCommand.cxx:738
 TQCommand.cxx:739
 TQCommand.cxx:740
 TQCommand.cxx:741
 TQCommand.cxx:742
 TQCommand.cxx:743
 TQCommand.cxx:744
 TQCommand.cxx:745
 TQCommand.cxx:746
 TQCommand.cxx:747
 TQCommand.cxx:748
 TQCommand.cxx:749
 TQCommand.cxx:750
 TQCommand.cxx:751
 TQCommand.cxx:752
 TQCommand.cxx:753
 TQCommand.cxx:754
 TQCommand.cxx:755
 TQCommand.cxx:756
 TQCommand.cxx:757
 TQCommand.cxx:758
 TQCommand.cxx:759
 TQCommand.cxx:760
 TQCommand.cxx:761
 TQCommand.cxx:762
 TQCommand.cxx:763
 TQCommand.cxx:764
 TQCommand.cxx:765
 TQCommand.cxx:766
 TQCommand.cxx:767
 TQCommand.cxx:768
 TQCommand.cxx:769
 TQCommand.cxx:770
 TQCommand.cxx:771
 TQCommand.cxx:772
 TQCommand.cxx:773
 TQCommand.cxx:774
 TQCommand.cxx:775
 TQCommand.cxx:776
 TQCommand.cxx:777
 TQCommand.cxx:778
 TQCommand.cxx:779
 TQCommand.cxx:780
 TQCommand.cxx:781
 TQCommand.cxx:782
 TQCommand.cxx:783
 TQCommand.cxx:784
 TQCommand.cxx:785
 TQCommand.cxx:786
 TQCommand.cxx:787
 TQCommand.cxx:788
 TQCommand.cxx:789
 TQCommand.cxx:790
 TQCommand.cxx:791
 TQCommand.cxx:792
 TQCommand.cxx:793
 TQCommand.cxx:794
 TQCommand.cxx:795
 TQCommand.cxx:796
 TQCommand.cxx:797
 TQCommand.cxx:798
 TQCommand.cxx:799
 TQCommand.cxx:800
 TQCommand.cxx:801
 TQCommand.cxx:802
 TQCommand.cxx:803
 TQCommand.cxx:804
 TQCommand.cxx:805
 TQCommand.cxx:806
 TQCommand.cxx:807
 TQCommand.cxx:808
 TQCommand.cxx:809
 TQCommand.cxx:810
 TQCommand.cxx:811
 TQCommand.cxx:812
 TQCommand.cxx:813
 TQCommand.cxx:814
 TQCommand.cxx:815
 TQCommand.cxx:816
 TQCommand.cxx:817
 TQCommand.cxx:818
 TQCommand.cxx:819
 TQCommand.cxx:820
 TQCommand.cxx:821
 TQCommand.cxx:822
 TQCommand.cxx:823
 TQCommand.cxx:824
 TQCommand.cxx:825
 TQCommand.cxx:826
 TQCommand.cxx:827
 TQCommand.cxx:828
 TQCommand.cxx:829
 TQCommand.cxx:830
 TQCommand.cxx:831
 TQCommand.cxx:832
 TQCommand.cxx:833
 TQCommand.cxx:834
 TQCommand.cxx:835
 TQCommand.cxx:836
 TQCommand.cxx:837
 TQCommand.cxx:838
 TQCommand.cxx:839
 TQCommand.cxx:840
 TQCommand.cxx:841
 TQCommand.cxx:842
 TQCommand.cxx:843
 TQCommand.cxx:844
 TQCommand.cxx:845
 TQCommand.cxx:846
 TQCommand.cxx:847
 TQCommand.cxx:848
 TQCommand.cxx:849
 TQCommand.cxx:850
 TQCommand.cxx:851
 TQCommand.cxx:852
 TQCommand.cxx:853
 TQCommand.cxx:854
 TQCommand.cxx:855
 TQCommand.cxx:856
 TQCommand.cxx:857
 TQCommand.cxx:858
 TQCommand.cxx:859
 TQCommand.cxx:860
 TQCommand.cxx:861
 TQCommand.cxx:862
 TQCommand.cxx:863
 TQCommand.cxx:864
 TQCommand.cxx:865
 TQCommand.cxx:866
 TQCommand.cxx:867
 TQCommand.cxx:868
 TQCommand.cxx:869
 TQCommand.cxx:870
 TQCommand.cxx:871
 TQCommand.cxx:872
 TQCommand.cxx:873
 TQCommand.cxx:874
 TQCommand.cxx:875
 TQCommand.cxx:876
 TQCommand.cxx:877
 TQCommand.cxx:878
 TQCommand.cxx:879
 TQCommand.cxx:880
 TQCommand.cxx:881
 TQCommand.cxx:882
 TQCommand.cxx:883
 TQCommand.cxx:884
 TQCommand.cxx:885
 TQCommand.cxx:886
 TQCommand.cxx:887
 TQCommand.cxx:888
 TQCommand.cxx:889
 TQCommand.cxx:890
 TQCommand.cxx:891
 TQCommand.cxx:892
 TQCommand.cxx:893
 TQCommand.cxx:894
 TQCommand.cxx:895
 TQCommand.cxx:896
 TQCommand.cxx:897
 TQCommand.cxx:898
 TQCommand.cxx:899
 TQCommand.cxx:900
 TQCommand.cxx:901
 TQCommand.cxx:902
 TQCommand.cxx:903
 TQCommand.cxx:904
 TQCommand.cxx:905
 TQCommand.cxx:906
 TQCommand.cxx:907
 TQCommand.cxx:908
 TQCommand.cxx:909
 TQCommand.cxx:910
 TQCommand.cxx:911
 TQCommand.cxx:912
 TQCommand.cxx:913
 TQCommand.cxx:914
 TQCommand.cxx:915
 TQCommand.cxx:916
 TQCommand.cxx:917
 TQCommand.cxx:918
 TQCommand.cxx:919
 TQCommand.cxx:920
 TQCommand.cxx:921
 TQCommand.cxx:922
 TQCommand.cxx:923
 TQCommand.cxx:924
 TQCommand.cxx:925
 TQCommand.cxx:926
 TQCommand.cxx:927
 TQCommand.cxx:928
 TQCommand.cxx:929
 TQCommand.cxx:930
 TQCommand.cxx:931
 TQCommand.cxx:932
 TQCommand.cxx:933
 TQCommand.cxx:934
 TQCommand.cxx:935
 TQCommand.cxx:936
 TQCommand.cxx:937
 TQCommand.cxx:938
 TQCommand.cxx:939
 TQCommand.cxx:940
 TQCommand.cxx:941
 TQCommand.cxx:942
 TQCommand.cxx:943
 TQCommand.cxx:944
 TQCommand.cxx:945
 TQCommand.cxx:946
 TQCommand.cxx:947
 TQCommand.cxx:948
 TQCommand.cxx:949
 TQCommand.cxx:950
 TQCommand.cxx:951
 TQCommand.cxx:952
 TQCommand.cxx:953
 TQCommand.cxx:954
 TQCommand.cxx:955
 TQCommand.cxx:956
 TQCommand.cxx:957
 TQCommand.cxx:958
 TQCommand.cxx:959
 TQCommand.cxx:960
 TQCommand.cxx:961
 TQCommand.cxx:962
 TQCommand.cxx:963
 TQCommand.cxx:964
 TQCommand.cxx:965
 TQCommand.cxx:966
 TQCommand.cxx:967
 TQCommand.cxx:968
 TQCommand.cxx:969
 TQCommand.cxx:970
 TQCommand.cxx:971
 TQCommand.cxx:972
 TQCommand.cxx:973
 TQCommand.cxx:974
 TQCommand.cxx:975
 TQCommand.cxx:976
 TQCommand.cxx:977
 TQCommand.cxx:978
 TQCommand.cxx:979
 TQCommand.cxx:980
 TQCommand.cxx:981
 TQCommand.cxx:982
 TQCommand.cxx:983
 TQCommand.cxx:984
 TQCommand.cxx:985
 TQCommand.cxx:986
 TQCommand.cxx:987
 TQCommand.cxx:988
 TQCommand.cxx:989
 TQCommand.cxx:990
 TQCommand.cxx:991
 TQCommand.cxx:992
 TQCommand.cxx:993
 TQCommand.cxx:994
 TQCommand.cxx:995
 TQCommand.cxx:996
 TQCommand.cxx:997
 TQCommand.cxx:998
 TQCommand.cxx:999
 TQCommand.cxx:1000
 TQCommand.cxx:1001
 TQCommand.cxx:1002
 TQCommand.cxx:1003
 TQCommand.cxx:1004
 TQCommand.cxx:1005
 TQCommand.cxx:1006
 TQCommand.cxx:1007
 TQCommand.cxx:1008
 TQCommand.cxx:1009
 TQCommand.cxx:1010
 TQCommand.cxx:1011
 TQCommand.cxx:1012
 TQCommand.cxx:1013
 TQCommand.cxx:1014
 TQCommand.cxx:1015
 TQCommand.cxx:1016
 TQCommand.cxx:1017
 TQCommand.cxx:1018
 TQCommand.cxx:1019
 TQCommand.cxx:1020
 TQCommand.cxx:1021
 TQCommand.cxx:1022
 TQCommand.cxx:1023
 TQCommand.cxx:1024
 TQCommand.cxx:1025
 TQCommand.cxx:1026
 TQCommand.cxx:1027
 TQCommand.cxx:1028
 TQCommand.cxx:1029
 TQCommand.cxx:1030
 TQCommand.cxx:1031
 TQCommand.cxx:1032
 TQCommand.cxx:1033
 TQCommand.cxx:1034
 TQCommand.cxx:1035
 TQCommand.cxx:1036
 TQCommand.cxx:1037
 TQCommand.cxx:1038
 TQCommand.cxx:1039
 TQCommand.cxx:1040
 TQCommand.cxx:1041
 TQCommand.cxx:1042
 TQCommand.cxx:1043
 TQCommand.cxx:1044
 TQCommand.cxx:1045
 TQCommand.cxx:1046
 TQCommand.cxx:1047
 TQCommand.cxx:1048
 TQCommand.cxx:1049
 TQCommand.cxx:1050
 TQCommand.cxx:1051
 TQCommand.cxx:1052
 TQCommand.cxx:1053
 TQCommand.cxx:1054
 TQCommand.cxx:1055
 TQCommand.cxx:1056
 TQCommand.cxx:1057
 TQCommand.cxx:1058
 TQCommand.cxx:1059
 TQCommand.cxx:1060
 TQCommand.cxx:1061
 TQCommand.cxx:1062
 TQCommand.cxx:1063
 TQCommand.cxx:1064
 TQCommand.cxx:1065
 TQCommand.cxx:1066
 TQCommand.cxx:1067
 TQCommand.cxx:1068
 TQCommand.cxx:1069
 TQCommand.cxx:1070
 TQCommand.cxx:1071
 TQCommand.cxx:1072
 TQCommand.cxx:1073
 TQCommand.cxx:1074
 TQCommand.cxx:1075
 TQCommand.cxx:1076
 TQCommand.cxx:1077
 TQCommand.cxx:1078
 TQCommand.cxx:1079
 TQCommand.cxx:1080
 TQCommand.cxx:1081
 TQCommand.cxx:1082
 TQCommand.cxx:1083
 TQCommand.cxx:1084
 TQCommand.cxx:1085
 TQCommand.cxx:1086
 TQCommand.cxx:1087
 TQCommand.cxx:1088
 TQCommand.cxx:1089
 TQCommand.cxx:1090
 TQCommand.cxx:1091
 TQCommand.cxx:1092
 TQCommand.cxx:1093
 TQCommand.cxx:1094
 TQCommand.cxx:1095
 TQCommand.cxx:1096
 TQCommand.cxx:1097
 TQCommand.cxx:1098
 TQCommand.cxx:1099
 TQCommand.cxx:1100
 TQCommand.cxx:1101
 TQCommand.cxx:1102
 TQCommand.cxx:1103
 TQCommand.cxx:1104
 TQCommand.cxx:1105
 TQCommand.cxx:1106
 TQCommand.cxx:1107
 TQCommand.cxx:1108
 TQCommand.cxx:1109
 TQCommand.cxx:1110
 TQCommand.cxx:1111
 TQCommand.cxx:1112
 TQCommand.cxx:1113
 TQCommand.cxx:1114
 TQCommand.cxx:1115
 TQCommand.cxx:1116
 TQCommand.cxx:1117
 TQCommand.cxx:1118
 TQCommand.cxx:1119
 TQCommand.cxx:1120
 TQCommand.cxx:1121
 TQCommand.cxx:1122
 TQCommand.cxx:1123
 TQCommand.cxx:1124
 TQCommand.cxx:1125
 TQCommand.cxx:1126
 TQCommand.cxx:1127
 TQCommand.cxx:1128
 TQCommand.cxx:1129
 TQCommand.cxx:1130
 TQCommand.cxx:1131
 TQCommand.cxx:1132
 TQCommand.cxx:1133
 TQCommand.cxx:1134
 TQCommand.cxx:1135
 TQCommand.cxx:1136
 TQCommand.cxx:1137
 TQCommand.cxx:1138
 TQCommand.cxx:1139
 TQCommand.cxx:1140
 TQCommand.cxx:1141
 TQCommand.cxx:1142
 TQCommand.cxx:1143
 TQCommand.cxx:1144
 TQCommand.cxx:1145
 TQCommand.cxx:1146
 TQCommand.cxx:1147
 TQCommand.cxx:1148
 TQCommand.cxx:1149
 TQCommand.cxx:1150
 TQCommand.cxx:1151
 TQCommand.cxx:1152
 TQCommand.cxx:1153
 TQCommand.cxx:1154
 TQCommand.cxx:1155
 TQCommand.cxx:1156
 TQCommand.cxx:1157
 TQCommand.cxx:1158
 TQCommand.cxx:1159
 TQCommand.cxx:1160
 TQCommand.cxx:1161
 TQCommand.cxx:1162
 TQCommand.cxx:1163
 TQCommand.cxx:1164
 TQCommand.cxx:1165
 TQCommand.cxx:1166
 TQCommand.cxx:1167
 TQCommand.cxx:1168
 TQCommand.cxx:1169
 TQCommand.cxx:1170
 TQCommand.cxx:1171
 TQCommand.cxx:1172
 TQCommand.cxx:1173
 TQCommand.cxx:1174
 TQCommand.cxx:1175
 TQCommand.cxx:1176
 TQCommand.cxx:1177
 TQCommand.cxx:1178
 TQCommand.cxx:1179
 TQCommand.cxx:1180
 TQCommand.cxx:1181
 TQCommand.cxx:1182
 TQCommand.cxx:1183
 TQCommand.cxx:1184
 TQCommand.cxx:1185
 TQCommand.cxx:1186
 TQCommand.cxx:1187
 TQCommand.cxx:1188
 TQCommand.cxx:1189
 TQCommand.cxx:1190
 TQCommand.cxx:1191
 TQCommand.cxx:1192
 TQCommand.cxx:1193
 TQCommand.cxx:1194
 TQCommand.cxx:1195
 TQCommand.cxx:1196
 TQCommand.cxx:1197
 TQCommand.cxx:1198
 TQCommand.cxx:1199