Skip to content

Commit 0443035

Browse files
authored
fix(prt): convert to local coords in ternary cell method (#2122)
This reverts the switch to calculating the centroid via arithmetic mean for triangular cells in #2119 — the rest of the vertex velocity calculation assumes the polygonal definition of the centroid so that change was an error. A more robust way to avoid intermediate loss of precision is converting to local cell-local coordinates before applying the ternary cell method.
1 parent e59d9ac commit 0443035

File tree

1 file changed

+36
-17
lines changed

1 file changed

+36
-17
lines changed

src/Solution/ParticleTracker/MethodCellTernary.f90

+36-17
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ module MethodCellTernaryModule
88
use CellDefnModule
99
use SubcellTriModule, only: SubcellTriType, create_subcell_tri
1010
use ParticleModule
11-
use GeomUtilModule, only: area
11+
use GeomUtilModule, only: area, transform
1212
use ConstantsModule, only: DZERO, DONE, DTWO, DSIX
1313
use GeomUtilModule, only: point_in_polygon
1414
implicit none
@@ -158,6 +158,8 @@ subroutine apply_mct(this, particle, tmax)
158158
real(DP), intent(in) :: tmax
159159
! local
160160
integer(I4B) :: i
161+
real(DP) :: x, y, z, xO, yO
162+
real(DP), allocatable :: xs(:), ys(:)
161163

162164
! (Re)allocate type-bound arrays
163165
select type (cell => this%cell)
@@ -194,10 +196,24 @@ subroutine apply_mct(this, particle, tmax)
194196
allocate (this%xvertnext(this%nverts))
195197
allocate (this%yvertnext(this%nverts))
196198

199+
! New origin is the corner of the cell's
200+
! bounding box closest to the old origin
201+
allocate (xs(this%nverts))
202+
allocate (ys(this%nverts))
203+
xs = cell%defn%polyvert(1, :)
204+
ys = cell%defn%polyvert(2, :)
205+
xO = xs(minloc(abs(xs), dim=1))
206+
yO = ys(minloc(abs(ys), dim=1))
207+
deallocate (xs)
208+
deallocate (ys)
209+
197210
! Cell vertices
198211
do i = 1, this%nverts
199-
this%xvert(i) = cell%defn%polyvert(1, i)
200-
this%yvert(i) = cell%defn%polyvert(2, i)
212+
x = cell%defn%polyvert(1, i)
213+
y = cell%defn%polyvert(2, i)
214+
call transform(x, y, DZERO, x, y, z, xO, yO)
215+
this%xvert(i) = x
216+
this%yvert(i) = y
201217
end do
202218

203219
! Top, bottom, and thickness
@@ -212,13 +228,21 @@ subroutine apply_mct(this, particle, tmax)
212228
this%iprev = cshift(this%iprev, -1)
213229
this%xvertnext = cshift(this%xvert, 1)
214230
this%yvertnext = cshift(this%yvert, 1)
215-
end select
216231

217-
! Calculate vertex velocities.
218-
call this%vertvelo()
232+
! Calculate vertex velocities.
233+
call this%vertvelo()
234+
235+
! Transform particle coordinates
236+
call particle%transform(xO, yO)
237+
238+
! Track the particle across the cell.
239+
call this%track(particle, 2, tmax)
219240

220-
! Track the particle across the cell.
221-
call this%track(particle, 2, tmax)
241+
! Transform particle coordinates back
242+
call particle%transform(xO, yO, invert=.true.)
243+
call particle%reset_transform()
244+
245+
end select
222246

223247
end subroutine apply_mct
224248

@@ -403,16 +427,11 @@ subroutine vertvelo(this)
403427
sixa = areacell * DSIX
404428
wk1 = -(this%xvert * this%yvertnext - this%xvertnext * this%yvert)
405429
nvert = size(this%xvert)
406-
if (nvert == 3) then
407-
this%xctr = sum(this%xvert) / 3.0_DP
408-
this%yctr = sum(this%yvert) / 3.0_DP
409-
else
410-
this%xctr = sum((this%xvert + this%xvertnext) * wk1) / sixa
411-
this%yctr = sum((this%yvert + this%yvertnext) * wk1) / sixa
412-
end if
430+
this%xctr = sum((this%xvert + this%xvertnext) * wk1) / sixa
431+
this%yctr = sum((this%yvert + this%yvertnext) * wk1) / sixa
413432

414-
! TODO: do we need to check if center is in polygon?
415-
! only if using the centroid method which misbehaves
433+
! TODO: can we use some of the terms of the centroid calculation
434+
! to do a cheap point in polygon check?
416435
!
417436
! allocate(poly(2, nvert))
418437
! poly(1,:) = this%xvert

0 commit comments

Comments
 (0)