'
'Class description:
'
!short:Menu class structure:
Class Menu:
~~~~~~~~~~~~
Makes all the main menu functions.

Common use:
~~~~~~~~~~~
It is as example used in DEMO1.prg and DEMO2.prg.

Zdrojovy text triedy Menu je v subore C_Menu.prg
Source code is in C_Menu.prg.

!seealso: c_md.ngo:MD c_view.ngo:View c_dbf.ngo:Dbf c_color.ngo:Color ob_class.ngo:"Class hierarchy"

!short:~~~~~~~~~~~~~~~~~~~~~
!short:create class Menu
!short:  export:
!short:  var Color   //m->Color:Menu
^BMenu:Color^N: public: character
  Menu color definition.

!short:  var Data    //{}
^BMenu:Data^N: read-only: array
  N-dimensional array for storing of the objects of the class MD,
  it describes the whole menu structure.

!short:  var Block   //{}
^BMenu:Block^N: read-only: array
  Onedimensional array for storing of the code blocks, which are
  to be processed when user selects a menu action.

!short:  var Avail   //{}
^BMenu:Avail^N: read-only: array
  Onedimensional array storing the logical value true or false about the
  selectability of the menu item.

!short:  var HotKeys //{}
^BMenu:HotKeys^N: read-only: array
  Acclerator array, here are the "hot keys" stored for speeding up the
  menu items selection. It structure is:
  HotKeys:={}
  AAdd( HotKeys, {nKey,nIdx} )
  ...
  Where:
  nKey is InKey hot key code.
  nIdx is the Menu:Block pointer to desired action.

!short:  var Idx     //1
^BMenu:Idx^N: read-only: numeric
  The last selected item of the top menu level (bar pointer).

!short:  var NewTask //nil
^BMenu:NewTask^N: public: object_of_task
  Selects the next task for the Esc user exit. This instvar variable
  should content the class Task object or its successor. If there is
  no need to start a special task the instvar variable NewTask can be nil.

!short:  method New=MenuNew          //o:New() --> self
^BMenu:New()^N: public: return self
  Object is filled with the default values.

!short:  method Init=MenuInit        //o:Init() --> true
^BMenu:Init()^N: public: return true
  The menu object initialization and (may) the opened files reindex
  (only if it is need, i.e. if previous running copy of the program
  was be crashed).

!short:  method Password=MenuPassword//o:Password(SelfID) --> true
^BMenu:Password(SelfID)^N: public: return true
  Enables the password change. If the user has supervisor rights, he can
  change all paswords. He can add the name, password and rights for the
  next user or delete the user.

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~
  ^USelfID^N: numeric
   Pointer to object of class MD for recursive restart of this method.

!short:  method AddBar=MenuAddBar    //o:AddBar(cName,bAction,bPreBlock,bPostBlock) --> true
^BMenu:AddBar(cName,bAction,bPreBlock,bPostBlock)^N: public: return true
  Next item to bar line of the menu (the top line) is added. For every item
  is created a hot key after the character marked with ~ prefix.

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~~
  ^UcName^N: character: no default
   Menu item name

  ^UbAction^N: code_block: default is the submenu for this item
   The code block, if not defined, the submenu for this bar item is created,
   if defined it represents the action processed when this item is selected.

  ^UbPreBlock^N: code_block: default is {||true}
   The code block, processedd before entering this item.

  ^UbPostBlock^N: code_block: default is {||true}
   The code block processed imediately after leaving the item.

!short:  method AddMenu=MenuAddMenu  //o:AddMenu(cName,nHotKey,bPreBlock,bPostBlock) --> true
^BMenu:AddMenu(cName,nHotKey,bPreBlock,bPostBlock)^N: public: return true
  The current menu is appended with the next submenu item.

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~~
  ^UcName^N: character: no default
   Menu item name.

  ^UnHotKey^N: numeric: no default
   It is InKey() key code, representing the "hot key" for this menu item.
   If not set the hot key is not created.

  ^UbPreBlock^N: code_block: default is {||true}
   The code block, processed before entering this item.

  ^UbPostBlock^N: code_block: default is {||true}
   The code block processed imediately after leaving the item.

!short:  method AddItem=MenuAddItem  //o:AddItem(cName,bAction,nHotKey,bPreBlock,bPostBlock) --> true
^BMenu:AddItem(cName,bAction,nHotKey,bPreBlock,bPostBlock)^N:
  public: return true
  The current menu is appended with the next item, representing the action
  to be done when selecting this menu item.

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~~
  ^UcName^N: character: no default
   Menu item name

  ^UbAction^N: code_block: no default
   The code block processed as the action when selecting this menu item.
   As parameter becomes the pointer to MD structure, which is the menu item
   stored in.

  ^UnHotKey^N: numeric: no default
   It is InKey() key code, representing the "hot key" for this menu item.
   If not set the hot key is not created.

  ^UbPreBlock^N: code_block: default je {||true}
   The code block, processed before entering this item.

  ^UbPostBlock^N: code_block: default je {||true}
   The code block processed imediately after leaving the item.

!short:  method AddCheck=MenuAddCheck//o:AddCheck(cName,bAction,nHotKey,bPreBlock,bPostBlock) --> true
^BMenu:AddCheck(cName,bAction,nHotKey,bPreBlock,bPostBlock)^N:
  public: return true
  The same as AddItem, but operates as switch, not as the common menu item.
  The bAction prameter is a Get/Set block for reading the switch value (when
  used without the parameters), or for setting the value of the switch (when
  using the new value as the parameter)

!short:  method AddView=MenuAddView  //o:AddView(cName,cWinName,oV,nHotK,nVk,nEk,nGk,nLk,nIk,nFk,nRk,nMk) --> true
^BMenu:AddView(cName,cWinName,oV,nHotKey,nVk,nEk,nGk,nIk,nFk,nRk,nMk)^N:
  public: return true
  The menu is appended with a complex menu structure dealing the single
  View object.

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~
  ^UcName^N: character: no default
   Menu item name

  ^UcWinName^N: character: no default
   Displayed object window title.

  ^UoV^N: object_of_view: no default
   The view object.

  ^UnHotKey^N: numeric: no default
   InKey() code of hot key for this view object.

  ^UnVk^N: numeric: no default
   InKey() code of hot key for the item "View" of this view object.

  ^UnEk^N: numeric: no default
   InKey() code of hot key for the item "Edit" of this view object.

  ^UnGk^N: numeric: no default
   InKey() code of hot key for the item "Goto" of this view object.

  ^UnIk^N: numeric: no default
   InKey() code of hot key for the item "Index" of this view object.

  ^UnFk^N: numeric: no default
   InKey() code of hot key for the item "Filter" of this view object.

  ^UnRk^N: numeric: no default
   InKey() code of hot key for the item "Report" of this view object.

  ^UnMk^N: numeric: no default
   InKey() code of hot key for the item "Modify" of this view object.

!short:  method PopSubLevel=MenuPopSubLevel   //o:PopSubLevel() --> true
^BMenu:PopSubLevel()^N: public: return true
  This method use when you want in generated menu structure to return one
  level up and to continue there in appending the menu items.

!short:  method DisableItem=MenuDisableItem   //o:DisableItem(nItemID,lSubMenu) --> true
^BMenu:DisableItem(nItemID,lSubMenu)^N: public: return true
  The menu item (pointed to with the nItemID pointer) selection is disabled.
  All code blocks are passed to nItemID, which is the offset to internal
  table of flags which indicates the recursive entering of the menu item.

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~~
  ^UnItemID^N: numeric: no default
   Menu item pointer.

  ^UlSubMenu^N: logical: default is true
   If true, disabled are all items below the current item (it can have
   submenu selectable by hot key). If false, only the current item is
   selected.

!short:  method EnableItem=MenuEnableItem     //o:EnableItem(nItemID,lSubMenu) --> true
^BMenu:EnableItem(nItemID,lSubMenu)^N: public: return true
  The same as Menu:DisableItem(), but instead of disabling the item it is
  enabled.

!short:  method GetMD=MenuGetMD               //o:GetMD(nItemID) --> object_of_MD
^BMenu:GetMD(nItemID)^N: public: return object_of_MD
  The current menu item identifier is searched for its data structure
  (the class MD object).

!short:  method GetParentMD=MenuGetParentMD   //o:GetParentMD(nItemID) --> object_of_MD
^BMenu:GetParentMD(nItemID)^N: public: return object_of_MD
  The same as Menu:GetMD(), but the parent data structure is searched.

!short:  method Process=MenuProcess           //o:Process() --> true
^BMenu:Process()^N: public: return true
  The main program body, can be finished only by processing of the method
  Menu:Done().

!short:  method BarEntry=MenuBarEntry         //o:BarEntry(aAccelerators) --> true
^BMenu:BarEntry(aAccelerators)^N: private: return true
  Internal method processed by the menu. aAccelerators is the array of
  InKey() codes, for speeding up the user access to the required menu item.
  The every processing of this method takes the first item, which is inserted
  as the key to the keyboard queue.

!short:  method ItemEntry=MenuItemEntry       //o:ItemEntry(MD,CurSize,aAccelerators) --> true
^BMenu:ItemEntry(MD,CurSize,aAccelerators)^N:  private: return true
  Internal method by which is the submenu processed when the user selects
  the item. This method is often processed recursive (by submenus).

  Parameter description:
  ~~~~~~~~~~~~~~~~~~~~~~
  ^UMD^N: object_of_MD: no default
   Submenu for this method (to be processed), its data structure is MD.
   The processing is to display the submenu and to select the item by
   the user.

  ^UCurSize^N:
   The item width of current submenu.

  ^UaAccelerators^N: array: default is {}
   The same as in BarEntry() method.

!short:  method Done=MenuDone                 //o:Done(lConfirm) --> true
^BMenu:Done(lConfirm)^N:  public: return true
  It ends the main program cycle (the whole program).
  It is activated mainly as an menu item.

!short:  endclass

