!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!
module cubetools_primitive_arg
  use cubetools_parameters
  use cubelist_types
  use cubetools_terminal_tool
  use cubesyntax_messaging
  !
  public :: primitive_arg_t,narg_k
  public :: cubetools_primitive_arg_ptr
  private
  !
  integer(kind=4), parameter :: narg_k = 4
  integer(kind=4), parameter :: abst_l = 80
  !
  type, extends(list_object_t) :: primitive_arg_t
     integer(kind=narg_k)          :: inum = code_abs       ! Argument number in option
     character(len=argu_l)         :: name = strg_unk
     character(len=abst_l)         :: abstract = strg_emp   ! One-line abstract help
     character(len=:), allocatable :: help_strg             ! Long/multiline help
     integer(kind=code_k)          :: mandatory = code_arg_mandatory
   contains
     ! General
     procedure :: init  => cubetools_primitive_arg_init
     procedure :: final => cubetools_primitive_arg_final
     !
     ! Registering
     procedure :: put   => cubetools_primitive_arg_put
     !
     ! Printing and Help
     procedure :: print_abstract => cubetools_primitive_arg_abstract  ! ZZZ Should be renamed 'list'
     procedure :: summary        => cubetools_primitive_arg_summary
     procedure :: help           => cubetools_primitive_arg_help
  end type primitive_arg_t
  !
contains
  !
  !---General------------------------------------------------------------
  !
  subroutine cubetools_primitive_arg_init(arg,error)
    !----------------------------------------------------------------------
    !
    !----------------------------------------------------------------------
    class(primitive_arg_t), intent(out)   :: arg
    logical,                intent(inout) :: error
    !
    character(len=*), parameter :: rname='ARGUMENT>INIT'
    !
    call cubesyntax_message(syntaxseve%trace,rname,'Welcome')
  end subroutine cubetools_primitive_arg_init
  !
  subroutine cubetools_primitive_arg_final(obj,error)
    !----------------------------------------------------------------------
    !
    !----------------------------------------------------------------------
    class(primitive_arg_t), intent(inout) :: obj
    logical,                intent(inout) :: error
    !
    character(len=*), parameter :: rname='ARGUMENT>FINAL'
    !
    call cubesyntax_message(syntaxseve%trace,rname,'Welcome')
  end subroutine cubetools_primitive_arg_final
  !
  function cubetools_primitive_arg_ptr(tot,error)
    !-------------------------------------------------------------------
    ! Check if the input class is of class(primitive_arg_t), and return
    ! a pointer to it if relevant.
    !-------------------------------------------------------------------
    class(primitive_arg_t), pointer :: cubetools_primitive_arg_ptr  ! Function value on return
    class(list_object_t),  pointer       :: tot
    logical,               intent(inout) :: error
    !
    character(len=*), parameter :: rname='ARGUMENT>PTR'
    !
    select type(tot)
    class is (primitive_arg_t)
      cubetools_primitive_arg_ptr => tot
    class default
      cubetools_primitive_arg_ptr => null()
      call cubesyntax_message(seve%e,rname,  &
        'Internal error: object is not a primitive_arg_t class')
      error = .true.
      return
    end select
  end function cubetools_primitive_arg_ptr
  !
  !---Registering----------------------------------------------------------
  !
  subroutine cubetools_primitive_arg_put(arg,inum,name,abstract,help,mandat,error)
    !----------------------------------------------------------------------
    !
    !----------------------------------------------------------------------
    class(primitive_arg_t), intent(inout) :: arg
    integer(kind=narg_k),   intent(in)    :: inum
    character(len=*),       intent(in)    :: name
    character(len=*),       intent(in)    :: abstract
    character(len=*),       intent(in)    :: help
    integer(kind=code_k),   intent(in)    :: mandat
    logical,                intent(inout) :: error
    !
    character(len=*), parameter :: rname='ARGUMENT>PUT'
    !
    call cubesyntax_message(syntaxseve%trace,rname,'Welcome')
    !
    call cubetools_primitive_arg_final(arg,error)
    if (error) return
    call cubetools_primitive_arg_init(arg,error)
    if (error) return
    arg%inum      = inum
    arg%name      = name
    arg%abstract  = abstract
    arg%help_strg = help
    arg%mandatory = mandat
  end subroutine cubetools_primitive_arg_put
  !
  !---Printing-and-Help--------------------------------------------------
  !
  subroutine cubetools_primitive_arg_abstract(arg,iarg,error)
    use gkernel_interfaces
    use cubetools_format
    !----------------------------------------------------------------------
    !
    !----------------------------------------------------------------------
    class(primitive_arg_t), intent(in)    :: arg
    integer(kind=narg_k),   intent(in)    :: iarg
    logical,                intent(inout) :: error
    !
    character(len=mess_l) :: name,mess
    character(len=*), parameter :: rname='ARGUMENT>ABSTRACT'
    !
    call cubesyntax_message(syntaxseve%trace,rname,'Welcome')
    !
    if ((iarg.lt.1).or.(9.lt.iarg)) then
       call cubesyntax_message(seve%e,rname,'Argument number out of authorized range: [1-9]')
       error = .true.
       return
    endif
    name = arg%name
    call sic_upper(name)
    write(mess,'(a1,i1,1x,3a,1x,a)')   &
      '#',iarg,'(',trim(arg_status(arg%mandatory)),')',trim(name)
    mess = '  '//cubetools_format_stdkey_boldval(mess,arg%abstract,terminal%width())
    call cubesyntax_message(syntaxseve%help,rname,mess)
  end subroutine cubetools_primitive_arg_abstract
  !
  subroutine cubetools_primitive_arg_help(arg,error)
    use cubetools_terminal_tool
    !-------------------------------------------------------------------
    ! Print option help from arg%help_strg
    !-------------------------------------------------------------------
    class(primitive_arg_t), intent(in)    :: arg
    logical,                intent(inout) :: error
    !
    character(len=*), parameter :: rname='ARGUMENT>HELP'
    !
    call cubesyntax_message(syntaxseve%trace,rname,'Welcome')
    if (.not.allocated(arg%help_strg)) return
    if (len_trim(arg%help_strg).le.0) return
    if (arg%help_strg.eq.strg_emp) return
    !
    call cubesyntax_message(syntaxseve%help,rname,blankstr)
    call terminal%print_strg(syntaxseve%help,arg%help_strg)
  end subroutine cubetools_primitive_arg_help
  !
  subroutine cubetools_primitive_arg_summary(arg,error)
    !-------------------------------------------------------------------
    ! Short option summary
    !-------------------------------------------------------------------
    class(primitive_arg_t), intent(in)    :: arg
    logical,                intent(inout) :: error
    !
    character(len=*), parameter :: rname='ARGUMENT>SUMMARY'
    !
    call cubesyntax_message(syntaxseve%trace,rname,'Welcome')
    !
    ! No syntax for arguments?
    ! call arg%print_syntax(error)
    ! if (error) return
    call cubesyntax_message(syntaxseve%help,rname,terminal%dash_strg())
    call arg%print_abstract(arg%inum,error)
    if (error) return
    call arg%help(error)
    if (error) return
    call cubesyntax_message(syntaxseve%help,rname,blankstr)
  end subroutine cubetools_primitive_arg_summary
end module cubetools_primitive_arg
!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
