79 NO,RLAT,RLON,IBO,LO,GO,IRET)
80 class(ip_grid),
intent(in) :: grid_in, grid_out
81 INTEGER,
INTENT(IN ) :: IPOPT(20)
82 INTEGER,
INTENT(IN ) :: MI,MO,KM
83 INTEGER,
INTENT(IN ) :: IBI(KM)
84 INTEGER,
INTENT(INOUT) :: NO
85 INTEGER,
INTENT( OUT) :: IRET, IBO(KM)
87 LOGICAL*1,
INTENT(IN ) :: LI(MI,KM)
88 LOGICAL*1,
INTENT( OUT) :: LO(MO,KM)
90 REAL,
INTENT(IN ) :: GI(MI,KM)
91 REAL,
INTENT(INOUT) :: RLAT(MO),RLON(MO)
92 REAL,
INTENT( OUT) :: GO(MO,KM)
94 REAL,
PARAMETER :: FILL=-9999.
96 INTEGER :: IJX(4),IJY(4)
97 INTEGER :: MCON,MP,N,I,J,K
99 LOGICAL :: SAME_GRIDI, SAME_GRIDO
101 REAL :: PMP,XIJ,YIJ,XF,YF
102 REAL :: G,W,GMIN,GMAX
104 REAL :: XPTS(MO),YPTS(MO)
105 logical :: to_station_points
108 REAL,
ALLOCATABLE,
SAVE :: RLATX(:),RLONX(:)
109 REAL,
ALLOCATABLE,
SAVE :: WXY(:,:,:)
110 INTEGER,
SAVE :: NOX=-1,iretx=-1
111 INTEGER,
ALLOCATABLE,
SAVE :: NXY(:,:,:),NC(:)
112 class(ip_grid),
allocatable,
save :: prev_grid_in, prev_grid_out
119 IF(mp.EQ.-1.OR.mp.EQ.0) mp=50
120 IF(mp.LT.0.OR.mp.GT.100) iret=32
123 if (.not.
allocated(prev_grid_in) .or. .not.
allocated(prev_grid_out))
then
124 allocate(prev_grid_in, source = grid_in)
125 allocate(prev_grid_out, source = grid_out)
130 same_gridi = grid_in == prev_grid_in
131 same_grido = grid_out == prev_grid_out
133 if (.not. same_gridi .or. .not. same_grido)
then
134 deallocate(prev_grid_in)
135 deallocate(prev_grid_out)
137 allocate(prev_grid_in, source = grid_in)
138 allocate(prev_grid_out, source = grid_out)
142 select type(grid_out)
143 type is(ip_station_points_grid)
144 to_station_points = .true.
146 to_station_points = .false.
151 IF(iret.EQ.0.AND.(to_station_points.OR..NOT.same_gridi.OR..NOT.same_grido))
THEN
154 CALL gdswzd(grid_out,0,mo,fill,xpts,ypts,rlon,rlat,no)
158 CALL gdswzd(grid_in,-1,no,fill,xpts,ypts,rlon,rlat,nv)
159 IF(iret.EQ.0.AND.nv.EQ.0) iret=2
163 IF(nox.GE.0)
DEALLOCATE(rlatx,rlonx,nc,nxy,wxy)
164 ALLOCATE(rlatx(no),rlonx(no),nc(no),nxy(4,4,no),wxy(4,4,no))
177 IF(xij.NE.fill.AND.yij.NE.fill)
THEN
178 ijx(1:4)=floor(xij-1)+(/0,1,2,3/)
179 ijy(1:4)=floor(yij-1)+(/0,1,2,3/)
184 nxy(i,j,n) = grid_in%field_pos(ijx(i), ijy(j))
187 IF(minval(nxy(1:4,1:4,n)).GT.0)
THEN
190 wx(1)=xf*(1-xf)*(2-xf)/(-6.)
191 wx(2)=(xf+1)*(1-xf)*(2-xf)/2.
192 wx(3)=(xf+1)*xf*(2-xf)/2.
193 wx(4)=(xf+1)*xf*(1-xf)/(-6.)
194 wy(1)=yf*(1-yf)*(2-yf)/(-6.)
195 wy(2)=(yf+1)*(1-yf)*(2-yf)/2.
196 wy(3)=(yf+1)*yf*(2-yf)/2.
197 wy(4)=(yf+1)*yf*(1-yf)/(-6.)
212 wxy(i,j,n)=wx(i)*wy(j)
223 IF(iret.EQ.0.AND.iretx.EQ.0)
THEN
224 IF(.not. to_station_points)
THEN
238 IF(mcon.GT.0) gmin=huge(gmin)
239 IF(mcon.GT.0) gmax=-huge(gmax)
242 IF(nxy(i,j,n).GT.0)
THEN
243 IF(ibi(k).EQ.0.OR.li(nxy(i,j,n),k))
THEN
244 g=g+wxy(i,j,n)*gi(nxy(i,j,n),k)
246 IF(mcon.GT.0) gmin=min(gmin,gi(nxy(i,j,n),k))
247 IF(mcon.GT.0) gmax=max(gmax,gi(nxy(i,j,n),k))
255 IF(mcon.GT.0) go(n,k)=min(max(go(n,k),gmin),gmax)
266 IF(.NOT.all(lo(1:no,k))) ibo(k)=1
268 select type(grid_out)
269 type is(ip_equid_cylind_grid)
270 CALL polfixs(no,mo,km,rlat,ibo,lo,go)
273 IF(iret.EQ.0) iret=iretx
274 IF(.not. to_station_points) no=0
336 mi, mo, km, ibi, li, ui, vi, &
337 no, rlat, rlon, crot, srot, ibo, lo, uo, vo, iret)
338 class(ip_grid),
intent(in) :: grid_in, grid_out
339 INTEGER,
INTENT(IN ) :: IPOPT(20)
340 INTEGER,
INTENT(IN ) :: IBI(KM),MI,MO,KM
341 INTEGER,
INTENT(INOUT) :: NO
342 INTEGER,
INTENT( OUT) :: IRET, IBO(KM)
344 LOGICAL*1,
INTENT(IN ) :: LI(MI,KM)
345 LOGICAL*1,
INTENT( OUT) :: LO(MO,KM)
347 REAL,
INTENT(IN ) :: UI(MI,KM),VI(MI,KM)
348 REAL,
INTENT(INOUT) :: RLAT(MO),RLON(MO),CROT(MO),SROT(MO)
349 REAL,
INTENT( OUT) :: UO(MO,KM),VO(MO,KM)
351 REAL,
PARAMETER :: FILL=-9999.
353 INTEGER :: IJX(4),IJY(4)
354 INTEGER :: MCON,MP,N,I,J,K,NK,NV
356 LOGICAL :: SAME_GRIDI,SAME_GRIDO
358 REAL :: CM,SM,UROT,VROT
359 REAL :: PMP,XIJ,YIJ,XF,YF
360 REAL :: U,V,W,UMIN,UMAX,VMIN,VMAX
361 REAL :: XPTS(MO),YPTS(MO)
363 REAL :: XPTI(MI),YPTI(MI),RLOI(MI),RLAI(MI)
364 REAL :: CROI(MI),SROI(MI)
366 logical :: to_station_points
369 REAL,
ALLOCATABLE,
SAVE :: RLATX(:),RLONX(:),CROTX(:),SROTX(:)
370 REAL,
ALLOCATABLE,
SAVE :: WXY(:,:,:),CXY(:,:,:),SXY(:,:,:)
371 INTEGER,
SAVE :: NOX=-1,iretx=-1
372 INTEGER,
ALLOCATABLE,
SAVE :: NXY(:,:,:),NC(:)
373 class(ip_grid),
allocatable,
save :: prev_grid_in, prev_grid_out
379 IF(mp.EQ.-1.OR.mp.EQ.0) mp=50
380 IF(mp.LT.0.OR.mp.GT.100) iret=32
384 if (.not.
allocated(prev_grid_in) .or. .not.
allocated(prev_grid_out))
then
385 allocate(prev_grid_in, source = grid_in)
386 allocate(prev_grid_out, source = grid_out)
391 same_gridi = grid_in == prev_grid_in
392 same_grido = grid_out == prev_grid_out
394 if (.not. same_gridi .or. .not. same_grido)
then
395 deallocate(prev_grid_in)
396 deallocate(prev_grid_out)
398 allocate(prev_grid_in, source = grid_in)
399 allocate(prev_grid_out, source = grid_out)
403 select type(grid_out)
404 type is(ip_station_points_grid)
405 to_station_points = .true.
407 to_station_points = .false.
412 IF(iret.EQ.0.AND.(to_station_points.OR..NOT.same_gridi.OR..NOT.same_grido))
THEN
415 CALL gdswzd(grid_out, 0,mo,fill,xpts,ypts,rlon,rlat,no,crot,srot)
419 CALL gdswzd(grid_in,-1,no,fill,xpts,ypts,rlon,rlat,nv)
420 IF(iret.EQ.0.AND.nv.EQ.0) iret=2
421 CALL gdswzd(grid_in, 0,mi,fill,xpti,ypti,rloi,rlai,nv,croi,sroi)
425 IF(nox.GE.0)
DEALLOCATE(rlatx,rlonx,crotx,srotx,nc,nxy,wxy,cxy,sxy)
426 ALLOCATE(rlatx(no),rlonx(no),crotx(no),srotx(no),nc(no), &
427 nxy(4,4,no),wxy(4,4,no),cxy(4,4,no),sxy(4,4,no))
442 IF(xij.NE.fill.AND.yij.NE.fill)
THEN
443 ijx(1:4)=floor(xij-1)+(/0,1,2,3/)
444 ijy(1:4)=floor(yij-1)+(/0,1,2,3/)
449 nxy(i,j,n) = grid_in%field_pos(ijx(i), ijy(j))
452 IF(minval(nxy(1:4,1:4,n)).GT.0)
THEN
455 wx(1)=xf*(1-xf)*(2-xf)/(-6.)
456 wx(2)=(xf+1)*(1-xf)*(2-xf)/2.
457 wx(3)=(xf+1)*xf*(2-xf)/2.
458 wx(4)=(xf+1)*xf*(1-xf)/(-6.)
459 wy(1)=yf*(1-yf)*(2-yf)/(-6.)
460 wy(2)=(yf+1)*(1-yf)*(2-yf)/2.
461 wy(3)=(yf+1)*yf*(2-yf)/2.
462 wy(4)=(yf+1)*yf*(1-yf)/(-6.)
477 wxy(i,j,n)=wx(i)*wy(j)
478 IF(nxy(i,j,n).GT.0)
THEN
479 CALL movect(rlai(nxy(i,j,n)),rloi(nxy(i,j,n)), &
480 rlat(n),rlon(n),cm,sm)
481 cxy(i,j,n)=cm*croi(nxy(i,j,n))+sm*sroi(nxy(i,j,n))
482 sxy(i,j,n)=sm*croi(nxy(i,j,n))-cm*sroi(nxy(i,j,n))
494 IF(iret.EQ.0.AND.iretx.EQ.0)
THEN
495 IF(.not. to_station_points)
THEN
512 IF(mcon.GT.0) umin=huge(umin)
513 IF(mcon.GT.0) umax=-huge(umax)
514 IF(mcon.GT.0) vmin=huge(vmin)
515 IF(mcon.GT.0) vmax=-huge(vmax)
518 IF(nxy(i,j,n).GT.0)
THEN
519 IF(ibi(k).EQ.0.OR.li(nxy(i,j,n),k))
THEN
520 urot=cxy(i,j,n)*ui(nxy(i,j,n),k)-sxy(i,j,n)*vi(nxy(i,j,n),k)
521 vrot=sxy(i,j,n)*ui(nxy(i,j,n),k)+cxy(i,j,n)*vi(nxy(i,j,n),k)
525 IF(mcon.GT.0) umin=min(umin,urot)
526 IF(mcon.GT.0) umax=max(umax,urot)
527 IF(mcon.GT.0) vmin=min(vmin,vrot)
528 IF(mcon.GT.0) vmax=max(vmax,vrot)
535 urot=crot(n)*u-srot(n)*v
536 vrot=srot(n)*u+crot(n)*v
539 IF(mcon.GT.0) uo(n,k)=min(max(uo(n,k),umin),umax)
540 IF(mcon.GT.0) vo(n,k)=min(max(vo(n,k),vmin),vmax)
553 IF(.NOT.all(lo(1:no,k))) ibo(k)=1
555 select type(grid_out)
556 type is(ip_equid_cylind_grid)
557 CALL polfixv(no,mo,km,rlat,rlon,ibo,lo,uo,vo)
561 IF(iret.EQ.0) iret=iretx
562 IF(.not. to_station_points) no=0
subroutine movect(FLAT, FLON, TLAT, TLON, CROT, SROT)
This subprogram provides the rotation parameters to move a vector along a great circle from one posit...
Bicubic interpolation routines for scalars and vectors.
subroutine interpolate_bicubic_scalar(IPOPT, grid_in, grid_out, MI, MO, KM, IBI, LI, GI, NO, RLAT, RLON, IBO, LO, GO, IRET)
This subprogram performs bicubic interpolation from any grid to any grid for scalar fields.
subroutine interpolate_bicubic_vector(ipopt, grid_in, grid_out, mi, mo, km, ibi, li, ui, vi, no, rlat, rlon, crot, srot, ibo, lo, uo, vo, iret)
This subprogram performs bicubic interpolation from any grid to any grid for vector fields.
Driver module for gdswzd routines.
Re-export the individual grids.
Make multiple pole scalar values consistent.
subroutine, public polfixs(NM, NX, KM, RLAT, IB, LO, GO)
Make multiple pole scalar values consistent.
subroutine, public polfixv(NM, NX, KM, RLAT, RLON, IB, LO, UO, VO)
Make multiple pole vector values consistent,.