!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!
module xymap_types
  !
  use image_def
  use gkernel_types
  !
  integer(kind=4), parameter :: ctype_pill_box    = 1
  integer(kind=4), parameter :: ctype_exponential = 2
  integer(kind=4), parameter :: ctype_sinc        = 3
  integer(kind=4), parameter :: ctype_exp_x_sinc  = 4
  integer(kind=4), parameter :: ctype_spheroidal  = 5
  integer(kind=4), parameter :: ctype_gaussian    = 6
  !
  ! Support type for user inputs in the Sic structure MAP%
  type :: sic_xymap_t
     !
     integer(kind=4) :: xcol        ! [] Column of X coordinates
     integer(kind=4) :: ycol        ! [] Column of Y coordinates
     integer(kind=4) :: wcol        ! [] Column of weights
     integer(kind=4) :: col(2)      ! [] Range of columns to grid
     !
     integer(kind=4)    :: size(2)  ! [pixel ] Map size
     real(kind=4)       :: cell(2)  ! [arcsec] Pixel size
     real(kind=4)       :: reso(2)  ! [arcsec] Map resolution
     real(kind=4)       :: tole     ! [arcsec] Position tolerance
     logical            :: shift    ! [      ] Shift and/or Rotate grid?
     real(kind=8)       :: pang     ! [degree] Grid position angle
   ! real(kind=8)       :: lii      ! [radian]
   ! real(kind=8)       :: bii      ! [radian]
     character(len=16)  :: ra       ! [  HH:MM:SS]
     character(len=16)  :: dec      ! [+DDD:MM:SS]
     character(len=256) :: like     ! [] Name of reference data cube used as an
                                    !    external data cube as reference for the
                                    !    spatial sampling
     !
     character(len=12) :: tele  ! [] Telescope name
     real(kind=4)      :: diam  ! [m] Antenna diameter
     real(kind=4)      :: beam  ! [arcsec] Beam FWHM
     !
     integer(kind=4)  :: ctype       ! []       Convolution kernel type
     real(kind=4)     :: support(2)  ! [arcsec] Convolution kernel support
     !
     character(len=8) :: wmode  ! Weighting mode (NAtural or UNiform)
     !
  end type sic_xymap_t
  !
  ! Table description
  type :: xymap_tab_t
    !
    ! Disk description
    type(gildas) :: hdisk      ! Table header (on disk)
    logical      :: velofirst  ! Is the table VELO-POSI?
    integer(kind=index_length) :: ndata  ! Size of table (X, Y, W, VELO)
    integer(kind=index_length) :: nposi  ! Size of table
    !
    ! Memory description (in memory, the working table is always
    ! [VELOCITY,POSITION])
    type(gildas) :: hmem                 ! Table header (in memory)
    integer(kind=index_length) :: nchan  ! Number of channels in buffer
    real(kind=4), allocatable  :: data(:,:)  ! Actual data
    real(kind=4), allocatable  :: buff(:,:)  ! Transposing and sorting buffer
    !
    integer(kind=index_length) :: xcol  ! [] Column of X coordinates
    integer(kind=index_length) :: ycol  ! [] Column of Y coordinates
    integer(kind=index_length) :: wcol  ! [] Column of weights
    real(kind=4), allocatable  :: x(:)  ! X coordinates
    real(kind=4), allocatable  :: y(:)  ! Y coordinates
    real(kind=4), allocatable  :: w(:)  ! Weights
    !
    logical :: dosort  ! Is data sorting needed?
    integer(kind=4), allocatable :: sort(:)  ! Sorting array
    !
  end type xymap_tab_t
  !
  ! Data cube and weight image description
  type :: xymap_cub_t
    !
    ! Disk description / final cube
    type(gildas) :: hout  ! Cube header description
    type(gildas) :: hwei  ! Weight image description
    logical      :: velofirst  ! Is the cube VELO-POSI-POSI (vlm)?
    integer(kind=index_length) :: nx           ! Size of final cube
    integer(kind=index_length) :: ny           !        "
    integer(kind=index_length) :: nc           !        "
    real(kind=4), allocatable  :: dout(:,:,:)  ! Final cube, optionally allocated
    real(kind=4), allocatable  :: dwei(:,:)    ! Weight image
    !
    ! Memory description (in memory, the working cube is always
    ! [VELOCITY,POSITION,POSITION]) / per-block buffers
    integer(kind=index_length) :: nchan  ! Number of channels in buffer
    real(kind=4), allocatable  :: data(:,:,:)  ! Actual data
    real(kind=4), allocatable  :: buff(:,:,:)  ! Transposing buffer
    !
  end type xymap_cub_t
  !
  type :: xymap_conv1d_t
    integer(kind=4) :: ctype  ! Function kind
    real(kind=4) :: parm(10)  ! Function parameters
    real(kind=4) :: bias
    real(kind=4), allocatable :: buff(:)
  end type xymap_conv1d_t
  !
  type :: xymap_conv2d_t
    type(xymap_conv1d_t) :: x
    type(xymap_conv1d_t) :: y
  end type xymap_conv2d_t
  !
  ! Type for measuring time spent in some pieces of the code
  type :: xymap_time_t
    type(cputime_t) :: total
    type(cputime_t) :: xyw   ! Reading the X Y W columns
    type(cputime_t) :: read  ! Reading (pieces of) the table
    type(cputime_t) :: sort  ! Sorting (pieces of) the table
    type(cputime_t) :: tran  ! Transposing (pieces of) the table or the cube
    type(cputime_t) :: conv  ! Convolving or placing
    type(cputime_t) :: writ  ! Writing (pieces of) the cube
  end type xymap_time_t
  !
  type :: xymap_t
    type(xymap_tab_t) :: tab
    type(xymap_cub_t) :: cub
    !
    integer(kind=4) :: col(2)    ! [] Range of columns to grid
    !
    real(kind=8)    :: xconv(3)  !
    real(kind=8)    :: yconv(3)  !
    real(kind=8)    :: vconv(3)  !
    real(kind=4)    :: tole      ! [radian] Position tolerance
    !
    real(kind=4)      :: diam         ! [m]
    real(kind=4)      :: beam         ! [radian] Beam FWHM
    character(len=12) :: beam_origin  ! Table header or MAP% variables
    !
    integer(kind=4) :: ptyp  ! [code]   Type of projection
    real(kind=8)    :: a0    ! [radian] Projection center (lambda)
    real(kind=8)    :: d0    ! [radian] Projection center (beta)
    real(kind=8)    :: pang  ! [radian] Grid position angle
    !
    real(kind=4) :: reso(2)     ! [radian] Map resolution
    real(kind=4) :: cell(2)     ! [radian] Pixel size
    real(kind=4) :: support(2)  ! [radian] Support of convolution function
    !
    character(len=8) :: wmode  ! Weighting mode (NAtural or UNiform)
    !
    type(xymap_conv2d_t) :: conv  ! Convolution buffer
    !
    type(xymap_time_t) :: time
    !
  end type xymap_t
  !
end module xymap_types
!
module xymap_def
  use xymap_types
  !
  type(sic_xymap_t), save :: sic_xymap
  !
end module xymap_def
!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
