!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!! !!
!! GNU General Public License !!
!! !!
!! This file is part of the Flexible Modeling System (FMS). !!
!! !!
!! FMS is free software; you can redistribute it and/or modify !!
!! it and are expected to follow the terms of the GNU General Public !!
!! License as published by the Free Software Foundation. !!
!! !!
!! FMS is distributed in the hope that it will be useful, !!
!! but WITHOUT ANY WARRANTY; without even the implied warranty of !!
!! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the !!
!! GNU General Public License for more details. !!
!! !!
!! You should have received a copy of the GNU General Public License !!
!! along with FMS; if not, write to: !!
!! Free Software Foundation, Inc. !!
!! 59 Temple Place, Suite 330 !!
!! Boston, MA 02111-1307 USA !!
!! or see: !!
!! http://www.gnu.org/licenses/gpl.txt !!
!! !!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
MODULE diag_axis_mod
!
! Seth Underwood
!
! diag_axis_mod is an integral part
! of diag_manager_mod. It helps to create axis IDs
! that are used in register_diag_field.
!
! Users first create axis ID by calling
! diag_axis_init, then use this axis ID in
! register_diag_field.
!
USE mpp_domains_mod, ONLY: domain1d, domain2d, mpp_get_compute_domain&
&, mpp_get_domain_components, null_domain1d, null_domain2d,&
& OPERATOR(.NE.), mpp_get_global_domain, mpp_get_domain_name
USE fms_mod, ONLY: error_mesg, write_version_number, lowercase, uppercase, FATAL
USE diag_data_mod, ONLY: diag_axis_type, max_subaxes, max_axes,&
& max_num_axis_sets
IMPLICIT NONE
PRIVATE
PUBLIC diag_axis_init, get_diag_axis, get_domain1d, get_domain2d,&
& get_axis_length, get_axis_global_length, diag_subaxes_init,&
& get_diag_axis_cart, get_diag_axis_data, max_axes, get_axis_aux,&
& get_tile_count, get_axes_shift, get_diag_axis_name,&
& get_axis_num, get_diag_axis_domain_name
! Module variables
! counter of number of axes defined
INTEGER, DIMENSION(:), ALLOCATABLE :: num_subaxes
INTEGER :: num_def_axes = 0
! storage for axis set names
CHARACTER(len=128), DIMENSION(:), ALLOCATABLE, SAVE :: Axis_sets
INTEGER :: num_axis_sets = 0
! ---- global storage for all defined axes ----
TYPE(diag_axis_type), ALLOCATABLE, SAVE :: Axes(:)
LOGICAL :: module_is_initialized = .FALSE.
CHARACTER(len=128) :: version =&
& '$Id: diag_axis.F90,v 17.0.4.3 2009/10/05 19:11:50 sdu Exp $'
CHARACTER(len=128) :: tagname =&
& '$Name: mom4p1_pubrel_dec2009_nnz $'
CONTAINS
!
!
! Initialize the axis, and return the axis ID.
!
!
! INTEGER FUNCTION diag_axis_init(name, data, units, cart_name, long_name,
! direction, set_name, edges, Domain, Domain2, aux, tile_count)
!
!
! diag_axis_init initializes an axis and returns the axis ID that
! is to be used with register_diag_field. This function also
! increments the axis counter and fills in the axes
!
! Short name for axis
! Array of coordinate values
! Units for the axis
!
! Cartesian axis ("X", "Y", "Z", "T")
!
!
! Indicates the direction of the axis:
!
! - Up if +1
! - Down if -1
! - Neither up or down if 0
!
!
!
! Long name for the axis.
!
!
! Axis ID for the previously defined "edges axis"
!
!
!
!
! Auxiliary name, can only be geolon_t or geolat_t
!
!
FUNCTION diag_axis_init(name, DATA, units, cart_name, long_name, direction,&
& set_name, edges, Domain, Domain2, aux, tile_count) RESULT (indexx)
CHARACTER(len=*), INTENT(in) :: name
REAL, DIMENSION(:), INTENT(in) :: DATA
CHARACTER(len=*), INTENT(in) :: units
CHARACTER(len=*), INTENT(in) :: cart_name
CHARACTER(len=*), INTENT(in), OPTIONAL :: long_name, set_name
INTEGER, INTENT(in), OPTIONAL :: direction, edges
TYPE(domain1d), INTENT(in), OPTIONAL :: Domain
TYPE(domain2d), INTENT(in), OPTIONAL :: Domain2
CHARACTER(len=*), INTENT(in), OPTIONAL :: aux
INTEGER, INTENT(in), OPTIONAL :: tile_count
TYPE(domain1d) :: domain_x, domain_y
INTEGER :: indexx, ierr, axlen
INTEGER :: i, set, tile
INTEGER :: isc, iec, isg, ieg
CHARACTER(len=128) :: errmsg
IF ( .NOT.module_is_initialized ) THEN
CALL write_version_number( version, tagname )
ENDIF
IF ( PRESENT(tile_count)) THEN
tile = tile_count
ELSE
tile = 1
END IF
! Allocate the axes
IF (.NOT. ALLOCATED(Axis_sets)) ALLOCATE(Axis_sets(max_num_axis_sets))
IF (.NOT. ALLOCATED(Axes)) ALLOCATE(Axes(max_axes))
IF (.NOT. ALLOCATED(num_subaxes)) THEN
ALLOCATE(num_subaxes(max_axes))
num_subaxes = 0
END IF
!---- is there an axis set? ----
IF ( PRESENT(set_name) ) THEN
set = get_axis_set_num (set_name)
!---- add new set name ----
IF (set == 0) THEN
num_axis_sets = num_axis_sets + 1
IF ( num_axis_sets > max_num_axis_sets ) THEN
WRITE (errmsg, FMT='("num_axis_sets (",I2,") exceeds max_num_axis_sets (",I2,"). ")') num_axis_sets, max_num_axis_sets
!
! num_axis_sets () exceeds max_num_axis_sets().
! Increase max_num_axis_sets via diag_manager_nml.
!
CALL error_mesg('diag_axis_mod :: diag_axis_init', &
TRIM(errmsg)//' Increase max_num_axis_sets via diag_manager_nml.', FATAL)
END IF
set = num_axis_sets
Axis_sets(set) = set_name
END IF
ELSE
set = 0
END IF
!---- see if axis already exists --
! if this is time axis, return the ID of a previously defined
! if this is spatial axis, FATAL error
DO i = 1, num_def_axes
IF ( TRIM(name) == Axes(i)%name ) THEN
IF ( TRIM(name) == 'Stations' .OR. TRIM(name) == 'Levels') THEN
indexx = i
RETURN
ELSE IF ( set == Axes(i)%set ) THEN
IF ( TRIM(lowercase(name)) == 'time' .OR.&
& TRIM(lowercase(cart_name)) == 't' .OR.&
& TRIM(lowercase(name)) == 'nv' .OR.&
& TRIM(lowercase(cart_name)) == 'n' ) THEN
indexx = i
RETURN
ELSE IF ( (lowercase(cart_name) /= 'x' .AND. lowercase(cart_name) /= 'y')&
& .OR. tile /= Axes(i)%tile_count) THEN
! axis_name and axis_set already exist.
CALL error_mesg('diag_axis_mod :: diag_axis_init',&
& 'axis_name '//TRIM(name)//' and axis_set already exist.', FATAL)
END IF
END IF
END IF
END DO
!---- register axis ----
num_def_axes = num_def_axes + 1
! max_axes exceeded, increase it via diag_manager_nml
IF (num_def_axes > max_axes) CALL error_mesg ('diag_axis_init in&
& diag_axis_mod', 'max_axes exceeded, increase it via&
& diag_manager_nml', FATAL)
indexx = num_def_axes
!---- check and then save cart_name name ----
IF ( TRIM(uppercase(cart_name)) == 'X' .OR.&
& TRIM(uppercase(cart_name)) == 'Y' .OR.&
& TRIM(uppercase(cart_name)) == 'Z' .OR.&
& TRIM(uppercase(cart_name)) == 'T' .OR.&
& TRIM(uppercase(cart_name)) == 'N' ) THEN
Axes(indexx)%cart_name = TRIM(uppercase(cart_name))
ELSE
! Invalid cart_name name.
CALL error_mesg('diag_axis_mod :: diag_axis_init', 'Invalid cart_name name.', FATAL)
END IF
!---- allocate storage for coordinate values of axis ----
IF ( Axes(indexx)%cart_name == 'T' ) THEN
axlen = 0
ELSE
axlen = SIZE(data(:))
END IF
ALLOCATE ( Axes(indexx)%data(1:axlen) )
! Initialize Axes(indexx)
Axes(indexx)%name = TRIM(name)
Axes(indexx)%data = data(1:axlen)
Axes(indexx)%units = units
Axes(indexx)%length = axlen
Axes(indexx)%set = set
! start and end are used in subaxes information only
Axes(indexx)%start = -1
Axes(indexx)%end = -1
Axes(indexx)%subaxis_name = ""
Axes(indexx)%shift = 0
IF ( PRESENT(long_name) ) THEN
Axes(indexx)%long_name = long_name
ELSE
Axes(indexx)%long_name = name
END IF
IF ( PRESENT(aux) ) THEN
Axes(indexx)%aux = TRIM(aux)
ELSE
Axes(indexx)%aux = 'none'
END IF
!---- axis direction (-1, 0, or +1) ----
IF ( PRESENT(direction) )THEN
IF ( ABS(direction) /= 1 .AND. direction /= 0 )&
! direction must be 0, +1, or -1
& CALL error_mesg('diag_axis_mod :: diag_axis_init',&
& 'direction must be 0, +1 or -1',FATAL)
Axes(indexx)%direction = direction
ELSE
Axes(indexx)%direction = 0
END IF
!---- domain2d type ----
IF ( PRESENT(Domain2) .AND. PRESENT(Domain)) THEN
! Presence of both Domain and Domain2 at the same time is prohibited
CALL error_mesg('diag_axis_mod :: diag_axis_init', &
'Presence of both Domain and Domain2 at the same time is prohibited', &
FATAL)
ELSE IF ( PRESENT(Domain2) .OR. PRESENT(Domain)) THEN
IF ( Axes(indexx)%cart_name /= 'X' .AND. Axes(indexx)%cart_name /= 'Y') THEN
! Domain must not be present for an axis which is not in the X or Y direction.
CALL error_mesg('diag_axis_mod :: diag_axis_init', &
'Domain must not be present for an axis which is not in the X or Y direction', &
FATAL)
END IF
END IF
Axes(indexx)%tile_count = tile
IF ( PRESENT(Domain2) ) THEN
Axes(indexx)%Domain2 = Domain2
CALL mpp_get_domain_components(Domain2, domain_x, domain_y, tile_count=tile_count)
IF ( Axes(indexx)%cart_name == 'X' ) Axes(indexx)%Domain = domain_x
IF ( Axes(indexx)%cart_name == 'Y' ) Axes(indexx)%Domain = domain_y
ELSE IF ( PRESENT(Domain)) THEN
!---- domain1d type ----
Axes(indexx)%Domain2 = null_domain2d ! needed since not 2-D domain
Axes(indexx)%Domain = Domain
ELSE
Axes(indexx)%Domain2 = null_domain2d
Axes(indexx)%Domain = null_domain1d
END IF
!--- set up the shift value for x-y axis
IF ( Axes(indexx)%Domain .NE. null_domain1d ) THEN
CALL mpp_get_compute_domain(Axes(indexx)%Domain, isc, iec)
CALL mpp_get_global_domain(Axes(indexx)%Domain, isg, ieg)
IF ( Axes(indexx)%length == ieg - isg + 2 ) THEN
Axes(indexx)%shift = 1
END IF
END IF
!---- have axis edges been defined ? ----
Axes(indexx)%edges = 0
IF (PRESENT(edges) ) THEN
IF ( edges > 0 .AND. edges < num_def_axes ) THEN
ierr=0
IF ( Axes(edges)%cart_name /= Axes(indexx)%cart_name) ierr=1
IF ( Axes(edges)%length /= Axes(indexx)%length+1 ) ierr=ierr+2
IF ( Axes(edges)%set /= Axes(indexx)%set ) ierr=ierr+4
IF ( ierr > 0 ) THEN
! Edges axis does not match axis (code _CODE_).
WRITE (errmsg,'("Edges axis does not match axis (code ",I1,").")') ierr
CALL error_mesg ('diag_axis_mod :: diag_axis_init', errmsg, FATAL)
END IF
Axes(indexx)%edges = edges
ELSE
! Edges axis is not defined.
CALL error_mesg ('diag_axis_mod :: diag_axis_init', &
'Edges axis is not defined', FATAL)
END IF
END IF
! Module is now initialized
module_is_initialized = .TRUE.
END FUNCTION diag_axis_init
!
!
!
! Create a subaxis on a parent axis.
!
!
! INTEGER FUNCTION diag_subaxes_init(axis, subdata, start_indx, end_indx,
! domain_1d, domain_2d)
!
!
! Given the ID of a parent axis, create a subaxis and fill it with data,
! and return the ID of the corresponding subaxis.
!
! The subaxis is defined on the parent axis from start_indx
! to end_indx.
!
! ID of the parent axis
! Data of the subaxis
! Start index of the subaxis
! End index of the subaxis
!
!
FUNCTION diag_subaxes_init(axis, subdata, start_indx, end_indx, domain_2d) RESULT(index)
INTEGER, INTENT(in) :: axis
REAL, DIMENSION(:), INTENT(in) :: subdata
INTEGER, INTENT(in) :: start_indx
INTEGER, INTENT(in) :: end_indx
TYPE(domain2d), INTENT(in), OPTIONAL :: domain_2d
INTEGER :: index
INTEGER :: i, nsub_axis, direction
CHARACTER(len=128) :: name, nsub_name
CHARACTER(len=128) :: units
CHARACTER(len=128) :: cart_name
CHARACTER(len=128) :: long_name
CHARACTER(len=128) :: errmsg
LOGICAL :: subaxis_set
! there may be more than 1 subaxis on a parent axis, check for redundancy
nsub_axis = 0
subaxis_set = .FALSE.
sa_search: DO i = 1, num_subaxes(axis)
IF ( start_indx == Axes(axis)%start(i) .AND. end_indx == Axes(axis)%end(i) ) THEN
nsub_axis = i
subaxis_set = .TRUE. !subaxis already exists
name = TRIM(Axes(axis)%subaxis_name(nsub_axis))
EXIT sa_search
END IF
END DO sa_search
IF ( nsub_axis == 0 ) THEN ! create new subaxis
num_subaxes(axis) = num_subaxes(axis) + 1
IF (num_subaxes(axis) > max_subaxes) THEN
! max_subaxes (value ) is too small. Consider increasing max_subaxes.
WRITE (errmsg,'("max_subaxes (value ",I4,") is too small. Consider increasing max_subaxes.")') max_subaxes
CALL error_mesg ('diag_subaxes_init in diag_axis_mod',errmsg, FATAL)
END IF
nsub_axis = num_subaxes(axis)
Axes(axis)%start(nsub_axis) = start_indx
Axes(axis)%end(nsub_axis) = end_indx
END IF
! Create new name for the subaxis from name of parent axis
! If subaxis already exists, get the index and return
IF(subaxis_set) THEN
IF ( Axes(axis)%set > 0 ) THEN
index = get_axis_num(name, set_name=TRIM(Axis_sets(Axes(axis)%set)))
ELSE
index = get_axis_num(name)
END IF
ELSE
! get a new index for subaxis
WRITE (nsub_name,'(I1)') nsub_axis
name = TRIM(Axes(axis)%name)//'_sub'//TRIM(nsub_name)
Axes(axis)%subaxis_name(nsub_axis) = name
long_name = TRIM(Axes(axis)%long_name)
units = TRIM(Axes(axis)%units)
cart_name = TRIM(Axes(axis)%cart_name)
direction = Axes(axis)%direction
IF (Axes(axis)%set > 0) THEN
index = diag_axis_init (TRIM(name), subdata, TRIM(units), TRIM(cart_name), TRIM(long_name), &
set_name=TRIM(Axis_sets(Axes(axis)%set)), direction=direction, Domain2=domain_2d)
ELSE
index = diag_axis_init (TRIM(name), subdata, TRIM(units), TRIM(cart_name), TRIM(long_name), &
direction=direction, Domain2=domain_2d)
END IF
END IF
END FUNCTION diag_subaxes_init
!
!
!
! Return information about the axis with index ID
!
!
! SUBROUTINE get_diag_axis(id, name, units, long_name, cart_name,
! direction, edges, Domain, data)
!
!
! Return information about the axis with index ID
!
! Axis ID
! Short name for axis
! Units for axis
! Long name for axis
!
! Cartesian axis ("x", "y", "z", "t").
!
!
! Direction of data. (See diag_axis_init for a description of
! allowed values)
!
!
! Axis ID for the previously defined "edges axis".
!
!
!
! Array of coordinate values for this axis.
!
SUBROUTINE get_diag_axis(id, name, units, long_name, cart_name,&
& direction, edges, Domain, data)
CHARACTER(len=*), INTENT(out) :: name, units, long_name, cart_name
INTEGER, INTENT(in) :: id
TYPE(domain1d), INTENT(out) :: Domain
INTEGER, INTENT(out) :: direction, edges
REAL, DIMENSION(:), INTENT(out) :: DATA
CHARACTER(len=128) :: error_msg
IF ( id < 1 .OR. id > num_def_axes ) THEN
! Illegal value for axis_id used (value ).
WRITE(error_msg,'(i2)')id
CALL error_mesg('get_diag_axis in diag_axis_mod', &
'Illegal value for axis_id used (value '//TRIM(error_msg)//').', FATAL)
END IF
name = Axes(id)%name
units = Axes(id)%units
long_name = Axes(id)%long_name
cart_name = Axes(id)%cart_name
direction = Axes(id)%direction
edges = Axes(id)%edges
Domain = Axes(id)%Domain
IF ( Axes(id)%length > SIZE(data(:)) ) THEN
! array data is too small.
CALL error_mesg ('get_diag_axis in diag_axis_mod', 'array data is too small', FATAL)
ELSE
data(1:Axes(id)%length) = Axes(id)%data
END IF
END SUBROUTINE get_diag_axis
!
!
!
! Return the axis cartesian.
!
!
! SUBROUTINE get_diag_axis_cart(id, cart_name)
!
!
! Return the axis cartesian ('X', 'Y', 'Z' or 'T') for the axis ID given.
!
! Axis ID
! Cartesian axis
SUBROUTINE get_diag_axis_cart(id, cart_name)
CHARACTER(len=*), INTENT(out) :: cart_name
INTEGER, INTENT(in) :: id
cart_name = Axes(id)%cart_name
END SUBROUTINE get_diag_axis_cart
!
!
!
! Return the axis data.
!
!
! SUBROUTINE get_diag_axis_data(id, data)
!
!
! Return the axis data for the axis ID given.
!
! Axis ID
! Axis data
SUBROUTINE get_diag_axis_data(id, DATA)
INTEGER, INTENT(in) :: id
REAL, DIMENSION(:), INTENT(out) :: DATA
IF (Axes(id)%length > SIZE(data(:))) THEN
! array data is too small
CALL error_mesg ('get_diag_axis_data in diag_axis_mod', 'array data is too small', FATAL)
ELSE
data(1:Axes(id)%length) = Axes(id)%data
END IF
END SUBROUTINE get_diag_axis_data
!
!
!
! Return the short name of the axis.
!
!
! SUBROUTINE get_diag_axis_name (id, name)
!
!
! Return the short name for the axis ID given.
!
! Axis ID
! Axis short name
SUBROUTINE get_diag_axis_name (id, name)
INTEGER , INTENT(in) :: id
CHARACTER(len=*), INTENT(out) :: name
CHARACTER(len=128) :: error_msg
IF (id < 1 .OR. id > num_def_axes) THEN
! Illegal value for axis used (value ).
WRITE(error_msg,'(i2)')id
CALL error_mesg('get_diag_axis_name in diag_axis_mod', &
'Illegal value for axis_id used (value '//TRIM(error_msg)//').', FATAL)
ELSE
name = Axes(id)%name
END IF
END SUBROUTINE get_diag_axis_name
!
!
!
! Return the name of the axis' domain
!
!
! SUBROUTINE get_diag_axis_domain_name(id, name)
!
!
! Retruns the name of the axis' domain.
!
! Axis ID
! Axis' domain name
SUBROUTINE get_diag_axis_domain_name(id, name)
INTEGER, INTENT(in) :: id
CHARACTER(len=*), INTENT(out) :: name
CHARACTER(len=128) :: error_msg
IF (id <1 .OR. id > num_def_axes) THEN
!
! Illegal value for axis used (value ).
!
WRITE (error_msg, '(I2)') id
CALL error_mesg('get_diag_axis_domain_name::diag_axis_mod',&
& 'Illegal value for axis_id used (value '&
&//TRIM(error_msg)//').', FATAL)
END IF
name = mpp_get_domain_name(Axes(id)%domain2)
END SUBROUTINE get_diag_axis_domain_name
!
!
!
! Return the length of the axis.
!
!
! INTEGER FUNCTION get_axis_length(id)
!
!
! Return the length of the axis ID given.
!
! Axis ID
INTEGER FUNCTION get_axis_length(id)
INTEGER, INTENT(in) :: id
INTEGER :: length
IF ( Axes(id)%Domain .NE. null_domain1d ) THEN
CALL mpp_get_compute_domain(Axes(id)%Domain,size=length)
!---one extra point is needed for some case. ( like symmetry domain )
get_axis_length = length + Axes(id)%shift
ELSE
get_axis_length = Axes(id)%length
END IF
END FUNCTION get_axis_length
!
!
!
! Return the auxiliary name for the axis.
!
!
! CHARACTER(LEN=128) FUNCTION get_axis_aux(id)
!
!
! Returns the auxiliary name for the axis. The only possible values for
! the auxiliary names is geolon_t or geolat_t.
!
! Axis ID
FUNCTION get_axis_aux (id) RESULT (aux)
INTEGER, INTENT(in) :: id
CHARACTER(len=128) :: aux
aux = Axes(id)%aux
END FUNCTION get_axis_aux
!
!
!
! Return the global length of the axis.
!
!
! INTEGER FUNCTION get_axis_global_length (id)
!
!
! Returns the global length of the axis ID given.
!
! Axis ID
FUNCTION get_axis_global_length(id) RESULT (length)
INTEGER, INTENT(in) :: id
INTEGER :: length
length = Axes(id)%length
END FUNCTION get_axis_global_length
!
!
!
! Return the tile count for the axis.
!
!
! INTEGER FUNCTION get_tile_count (ids)
!
!
! Return the tile count for the axis IDs given.
!
!
! Axis IDs. Possible dimensions: 1 <= size(ids(:)) <= 4.
!
FUNCTION get_tile_count(ids) RESULT (tile_count)
INTEGER, DIMENSION(:), INTENT(in) :: ids
INTEGER :: tile_count
INTEGER :: i, id, flag
IF ( SIZE(ids(:)) < 1 ) THEN
! input argument has incorrect size.
CALL error_mesg ('get_tile_count in diag_axis_mod', 'input argument has incorrect size', FATAL)
END IF
tile_count = 1
flag = 0
DO i = 1, SIZE(ids(:))
id = ids(i)
IF ( Axes(id)%cart_name == 'X' .OR. &
Axes(id)%cart_name == 'Y' ) flag = flag + 1
! --- both x/y axes found ---
IF ( flag == 2 ) THEN
tile_count = Axes(id)%tile_count
EXIT
END IF
END DO
END FUNCTION get_tile_count
!
!
!
! Return the 1D domain.
!
!
! TYPE(domain1d) FUNCTION get_domain1d (id)
!
!
! Retrun the 1D domain for the axis ID given.
!
! Axis ID
FUNCTION get_domain1d(id) RESULT (Domain1)
INTEGER, INTENT(in) :: id
TYPE(domain1d) :: Domain1
IF (Axes(id)%Domain .NE. NULL_DOMAIN1D) THEN
Domain1 = Axes(id)%Domain
ELSE
Domain1 = NULL_DOMAIN1D
ENDIF
END FUNCTION get_domain1d
!
!
!
! Return the 2D domain.
!
!
! TYPE(domain2d) FUNCTION get_domain2d (ids)
!
!
! Return the 2D domain for the axis IDs given.
!
!
! Axis IDs. Possible dimensions: 1 <= size(ids(:)) <= 4.
!
FUNCTION get_domain2d(ids) RESULT (Domain2)
INTEGER, DIMENSION(:), INTENT(in) :: ids
TYPE(domain2d) :: Domain2
INTEGER :: i, id, flag
IF ( SIZE(ids(:)) < 1 ) THEN
! input argument has incorrect size.
CALL error_mesg ('get_domain2d in diag_axis_mod', 'input argument has incorrect size', FATAL)
END IF
Domain2 = null_domain2d
flag = 0
DO i = 1, SIZE(ids(:))
id = ids(i)
IF ( Axes(id)%cart_name == 'X' .OR. Axes(id)%cart_name == 'Y' ) flag = flag + 1
! --- both x/y axes found ---
IF ( flag == 2 ) THEN
IF (Axes(id)%Domain2 .NE. NULL_DOMAIN2D) Domain2 = Axes(id)%Domain2
EXIT
END IF
END DO
END FUNCTION get_domain2d
!
!
!
! Return the value of the shift.
!
!
! SUBROUTINE get_axes_shift(ids, ishift, jshift)
!
!
! Return the value of the shift for the axis IDs given.
!
!
! Axis IDs. Possible dimensions: 1 <= size(ids(:)) <= 4
!
! X shift value.
! Y shift value.
SUBROUTINE get_axes_shift(ids, ishift, jshift)
INTEGER, DIMENSION(:), INTENT(in) :: ids
INTEGER, INTENT(out) :: ishift, jshift
INTEGER :: i, id
!-- get the value of the shift.
ishift = 0
jshift = 0
DO i = 1, SIZE(ids(:))
id = ids(i)
SELECT CASE (Axes(id)%cart_name)
CASE ( 'X' )
ishift = Axes(id)%shift
CASE ( 'Y' )
jshift = Axes(id)%shift
END SELECT
END DO
END SUBROUTINE get_axes_shift
!
!
!
!
! Returns index into axis table corresponding to a given axis name.
!
!
! INTEGER FUNCTION get_axis_num(axis_name, set_name)
!
!
! Returns index into axis table corresponding to a given axis name.
!
! Axis name.
! Set name.
FUNCTION get_axis_num(axis_name, set_name) RESULT (num)
CHARACTER(len=*), INTENT(in) :: axis_name
CHARACTER(len=*), INTENT(in), OPTIONAL :: set_name
INTEGER :: num, set, n
IF ( PRESENT(set_name) ) THEN
set = get_axis_set_num (TRIM(set_name))
ELSE
set = 0
END IF
num = 0
DO n = 1, num_def_axes
IF ( TRIM(axis_name) == TRIM(Axes(n)%name) .AND. Axes(n)%set == set ) THEN
num = n
RETURN
END IF
END DO
END FUNCTION get_axis_num
!
!
!
!
!
! Returns index in axis set table corresponding to a given axis set name.
!
!
! INTEGER FUNCTION get_axis_set_num(set_name)
!
!
! Returns index in axis set table corresponding to a given axis set name.
!
! Set name.
FUNCTION get_axis_set_num (set_name) RESULT (num)
CHARACTER(len=*), INTENT(in) :: set_name
INTEGER :: num, iset
num = 0
DO iset = 1, num_axis_sets
IF (set_name == Axis_sets(iset))THEN
num = iset
RETURN
END IF
END DO
END FUNCTION get_axis_set_num
!
!
END MODULE diag_axis_mod