The electric field from a triangular element is incorrect. Issue with
directional derivative depending on the definition of first node. Trying to solve it with searching for the right first node but it is very difficult. A solution is required to allow triangular meshes in charged simulations.
This commit is contained in:
parent
20dc4d4012
commit
075530e967
11 changed files with 1028 additions and 440 deletions
|
|
@ -138,6 +138,9 @@ MODULE moduleInput
|
|||
!Allocate the solver for charged pusher 2D Cylindrical
|
||||
ALLOCATE(solver, source=solverCylCharged())
|
||||
|
||||
CASE DEFAULT
|
||||
CALL criticalError('Solver ' // solverType // ' not found','readCase')
|
||||
|
||||
END SELECT
|
||||
|
||||
!Convert simulation time to number of iterations
|
||||
|
|
|
|||
|
|
@ -10,9 +10,9 @@ MODULE moduleMeshCyl
|
|||
REAL(8), PARAMETER:: corQuad(1:3) = (/ -DSQRT(3.D0/5.D0), 0.D0, DSQRT(3.D0/5.D0) /)
|
||||
REAL(8), PARAMETER:: wQuad(1:3) = (/ 5.D0/9.D0, 8.D0/9.D0, 5.D0/9.D0 /)
|
||||
|
||||
REAL(8), PARAMETER:: xi1Tria(1:3) = (/ 1.D0/6.D0, 2.D0/3.D0, 1.D0/6.D0 /)
|
||||
REAL(8), PARAMETER:: xi2Tria(1:3) = (/ 1.D0/6.D0, 1.D0/6.D0, 2.D0/3.D0 /)
|
||||
REAL(8), PARAMETER:: wTria(1:3) = (/ 1.D0/6.D0, 1.D0/6.D0, 1.D0/6.D0 /)
|
||||
REAL(8), PARAMETER:: xi1Tria(1:4) = (/ 1.D0/3.D0, 1.D0/5.D0, 3.D0/5.D0, 1.D0/5.D0 /)
|
||||
REAL(8), PARAMETER:: xi2Tria(1:4) = (/ 1.D0/3.D0, 1.D0/5.D0, 1.D0/5.D0, 3.D0/5.D0 /)
|
||||
REAL(8), PARAMETER:: wTria(1:4) = (/ -27.D0/96.D0, 25.D0/96.D0, 25.D0/96.D0, 25.D0/96.D0 /)
|
||||
|
||||
TYPE, PUBLIC, EXTENDS(meshNode):: meshNodeCyl
|
||||
!Element coordinates
|
||||
|
|
@ -284,7 +284,7 @@ MODULE moduleMeshCyl
|
|||
END SUBROUTINE areaQuad
|
||||
|
||||
!Computes element functions in point xi
|
||||
PURE FUNCTION fPsiQuad(xi) RESULT(fpsi)
|
||||
PURE FUNCTION fPsiQuad(xi) RESULT(fPsi)
|
||||
IMPLICIT NONE
|
||||
|
||||
REAL(8),INTENT(in):: xi(1:3)
|
||||
|
|
@ -371,6 +371,7 @@ MODULE moduleMeshCyl
|
|||
INTEGER:: l, m
|
||||
|
||||
ke=0.D0
|
||||
xi=0.D0
|
||||
!Start 2D Gauss Quad Integral
|
||||
DO l=1, 3
|
||||
xi(2) = corQuad(l)
|
||||
|
|
@ -489,7 +490,8 @@ MODULE moduleMeshCyl
|
|||
CLASS(meshVolCylQuad), INTENT(in):: self
|
||||
REAL(8), INTENT(in):: xi(1:3)
|
||||
REAL(8):: dPsi(1:2,1:4)
|
||||
REAL(8):: j(1:2,1:2), detJ
|
||||
REAL(8):: dPsiR(1:2,1:4)!Derivative of shpae functions in global coordinates
|
||||
REAL(8):: invJ(1:2,1:2), detJ
|
||||
REAL(8):: phi(1:4)
|
||||
REAL(8):: EF(1:3)
|
||||
|
||||
|
|
@ -498,11 +500,12 @@ MODULE moduleMeshCyl
|
|||
self%n3%emData%phi, &
|
||||
self%n4%emData%phi /)
|
||||
|
||||
dPsi = self%dPsi(xi)
|
||||
detJ = self%detJac(xi,dPsi)
|
||||
j = self%invJac(xi,dPsi)
|
||||
EF(1) = -DOT_PRODUCT(dPsi(1,:), phi)*j(2,2)/detJ
|
||||
EF(2) = -DOT_PRODUCT(dPsi(2,:), phi)*j(1,1)/detJ
|
||||
dPsi = self%dPsi(xi)
|
||||
detJ = self%detJac(xi,dPsi)
|
||||
invJ = self%invJac(xi,dPsi)
|
||||
dPsiR = MATMUL(invJ, dPsi)/detJ
|
||||
EF(1) = -DOT_PRODUCT(dPsiR(1,:), phi)
|
||||
EF(2) = -DOT_PRODUCT(dPsiR(2,:), phi)
|
||||
EF(3) = 0.D0
|
||||
|
||||
END FUNCTION gatherEFQuad
|
||||
|
|
@ -526,7 +529,7 @@ MODULE moduleMeshCyl
|
|||
CLASS(meshVolCylQuad), INTENT(in):: self
|
||||
REAL(8), INTENT(in):: r(1:3)
|
||||
REAL(8):: xN(1:3)
|
||||
REAL(8):: xO(1:3), detJ, j(1:2,1:2), f(1:2)
|
||||
REAL(8):: xO(1:3), detJ, invJ(1:2,1:2), f(1:2)
|
||||
REAL(8):: dPsi(1:2,1:4), fPsi(1:4)
|
||||
REAL(8):: conv
|
||||
|
||||
|
|
@ -536,12 +539,12 @@ MODULE moduleMeshCyl
|
|||
|
||||
DO WHILE(conv>1.D-4)
|
||||
dPsi = self%dPsi(xO)
|
||||
j = self%invJac(xO, dPsi)
|
||||
invJ = self%invJac(xO, dPsi)
|
||||
fPsi = self%fPsi(xO)
|
||||
f(1) = DOT_PRODUCT(fPsi,self%z)-r(1)
|
||||
f(2) = DOT_PRODUCT(fPsi,self%r)-r(2)
|
||||
detJ = self%detJac(xO,dPsi)
|
||||
xN(1:2)=xO(1:2) - MATMUL(j, f)/detJ
|
||||
xN(1:2)=xO(1:2) - MATMUL(invJ, f)/detJ
|
||||
conv=MAXVAL(DABS(xN-xO),1)
|
||||
xO=xN
|
||||
|
||||
|
|
@ -615,12 +618,39 @@ MODULE moduleMeshCyl
|
|||
CLASS(meshVolCylTria), INTENT(out):: self
|
||||
INTEGER, INTENT(in):: n
|
||||
INTEGER, INTENT(in):: p(:)
|
||||
REAL(8):: ldCorner(1:3) !left down (ld) corner of square enclousing the triangle
|
||||
INTEGER:: minP
|
||||
INTEGER:: pOrder(1:3)
|
||||
REAL(8), DIMENSION(1:3):: r1, r2, r3
|
||||
|
||||
!Assign node index
|
||||
self%n = n
|
||||
self%n1 => mesh%nodes(p(1))%obj
|
||||
self%n2 => mesh%nodes(p(2))%obj
|
||||
self%n3 => mesh%nodes(p(3))%obj
|
||||
|
||||
!Find the first node
|
||||
r1 = mesh%nodes(p(1))%obj%getCoordinates()
|
||||
r2 = mesh%nodes(p(2))%obj%getCoordinates()
|
||||
r3 = mesh%nodes(p(3))%obj%getCoordinates()
|
||||
ldCorner = (/ MINVAL((/r1(1), r2(1), r3(1)/), 1), &
|
||||
MINVAL((/r1(2), r2(2), r3(2)/), 1), &
|
||||
0.D0 /)
|
||||
minP = MINLOC((/ NORM2(r1-ldCorner), NORM2(r2-ldCorner), NORM2(r3-ldCorner) /), 1)
|
||||
pOrder(1) = p(minP)
|
||||
SELECT CASE(minP)
|
||||
CASE(1)
|
||||
pOrder(2) = p(2)
|
||||
pOrder(3) = p(3)
|
||||
CASE(2)
|
||||
pOrder(2) = p(3)
|
||||
pOrder(3) = p(1)
|
||||
CASE(3)
|
||||
pOrder(2) = p(1)
|
||||
pOrder(3) = p(2)
|
||||
END SELECT
|
||||
|
||||
!Assign nodes to element
|
||||
self%n1 => mesh%nodes(pOrder(1))%obj
|
||||
self%n2 => mesh%nodes(pOrder(2))%obj
|
||||
self%n3 => mesh%nodes(pOrder(3))%obj
|
||||
!Get element coordinates
|
||||
r1 = self%n1%getCoordinates()
|
||||
r2 = self%n2%getCoordinates()
|
||||
|
|
@ -653,7 +683,7 @@ MODULE moduleMeshCyl
|
|||
self%arNodes = 0.D0
|
||||
!2D 1 point Gauss Quad Integral
|
||||
xi = (/1.D0/3.D0, 1.D0/3.D0, 0.D0 /)
|
||||
detJ = self%detJac(xi)*8.D0*PI
|
||||
detJ = self%detJac(xi)*PI !2PI*1/2
|
||||
fPsi = self%fPsi(xi)
|
||||
r = DOT_PRODUCT(fPsi,self%r)
|
||||
self%volume = r*detJ
|
||||
|
|
@ -697,7 +727,7 @@ MODULE moduleMeshCyl
|
|||
REAL(8), INTENT(in):: xi2
|
||||
REAL(8):: dPsiXi1(1:3)
|
||||
|
||||
dPsiXi1(1) = -xi2
|
||||
dPsiXi1(1) = -1.D0
|
||||
dPsiXi1(2) = 1.D0
|
||||
dPsiXi1(3) = 0.D0
|
||||
|
||||
|
|
@ -710,7 +740,7 @@ MODULE moduleMeshCyl
|
|||
REAL(8), INTENT(in):: xi1
|
||||
REAL(8):: dPsiXi2(1:3)
|
||||
|
||||
dPsiXi2(1) = -xi1
|
||||
dPsiXi2(1) = -1.D0
|
||||
dPsiXi2(2) = 0.D0
|
||||
dPsiXi2(3) = 1.D0
|
||||
|
||||
|
|
@ -739,20 +769,21 @@ MODULE moduleMeshCyl
|
|||
REAL(8):: r, xi(1:3)
|
||||
REAL(8):: fPsi(1:3), dPsi(1:2,1:3)
|
||||
REAL(8):: ke(1:3,1:3)
|
||||
REAL(8):: j(1:2,1:2), detJ
|
||||
REAL(8):: invJ(1:2,1:2), detJ
|
||||
INTEGER:: l
|
||||
|
||||
ke=0.D0
|
||||
xi=0.D0
|
||||
!Start 2D Gauss Quad Integral
|
||||
DO l=1, 3
|
||||
DO l=1, 4
|
||||
xi(1) = xi1Tria(l)
|
||||
xi(2) = xi2Tria(l)
|
||||
dPsi = self%dPsi(xi)
|
||||
detJ = self%detJac(xi,dPsi)
|
||||
j = self%invJac(xi,dPsi)
|
||||
invJ = self%invJac(xi,dPsi)
|
||||
fPsi = self%fPsi(xi)
|
||||
r = DOT_PRODUCT(fPsi,self%r)
|
||||
ke = ke + MATMUL(TRANSPOSE(MATMUL(j,dPsi)),MATMUL(j,dPsi))*r*wTria(l)/detJ
|
||||
ke = ke + MATMUL(TRANSPOSE(MATMUL(invJ,dPsi)),MATMUL(invJ,dPsi))*r*wTria(l)/detJ
|
||||
|
||||
END DO
|
||||
ke = ke*2.D0*PI
|
||||
|
|
@ -776,7 +807,7 @@ MODULE moduleMeshCyl
|
|||
localF = 0.D0
|
||||
xi = 0.D0
|
||||
!Start 2D Gauss Quad Integral
|
||||
DO l=1, 3
|
||||
DO l=1, 4
|
||||
xi(1) = xi1Tria(l)
|
||||
xi(2) = xi2Tria(l)
|
||||
detJ = self%detJac(xi)
|
||||
|
|
@ -852,7 +883,8 @@ MODULE moduleMeshCyl
|
|||
CLASS(meshVolCylTria), INTENT(in):: self
|
||||
REAL(8), INTENT(in):: xi(1:3)
|
||||
REAL(8):: dPsi(1:2,1:3)
|
||||
REAL(8):: j(1:2,1:2), detJ
|
||||
REAL(8):: dPsiR(1:2,1:3)
|
||||
REAL(8):: invJ(1:2,1:2), detJ
|
||||
REAL(8):: phi(1:3)
|
||||
REAL(8):: EF(1:3)
|
||||
|
||||
|
|
@ -860,16 +892,17 @@ MODULE moduleMeshCyl
|
|||
self%n2%emData%phi, &
|
||||
self%n3%emData%phi/)
|
||||
|
||||
dPsi = self%dPsi(xi)
|
||||
detJ = self%detJac(xi,dPsi)
|
||||
j = self%invJac(xi,dPsi)
|
||||
EF(1) = -DOT_PRODUCT(dPsi(1,:), phi)*j(2,2)/detJ
|
||||
EF(2) = -DOT_PRODUCT(dPsi(2,:), phi)*j(1,1)/detJ
|
||||
dPsi = self%dPsi(xi)
|
||||
detJ = self%detJac(xi,dPsi)
|
||||
invJ = self%invJac(xi,dPsi)
|
||||
dPsiR = MATMUL(invJ, dPsi)/detJ
|
||||
EF(1) = -DOT_PRODUCT(dPsiR(1,:), phi)
|
||||
EF(2) = -DOT_PRODUCT(dPsiR(2,:), phi)
|
||||
EF(3) = 0.D0
|
||||
|
||||
END FUNCTION gatherEFTria
|
||||
|
||||
!Gets nodes from triangular element
|
||||
!Gets node indexes from triangular element
|
||||
PURE FUNCTION getNodesTria(self) RESULT(n)
|
||||
IMPLICIT NONE
|
||||
|
||||
|
|
@ -882,33 +915,23 @@ MODULE moduleMeshCyl
|
|||
END FUNCTION getNodesTria
|
||||
|
||||
!Transforms physical coordinates to element coordinates
|
||||
PURE FUNCTION phy2logTria(self,r) RESULT(xN)
|
||||
PURE FUNCTION phy2logTria(self,r) RESULT(xi)
|
||||
IMPLICIT NONE
|
||||
|
||||
CLASS(meshVolCylTria), INTENT(in):: self
|
||||
REAL(8), INTENT(in):: r(1:3)
|
||||
REAL(8):: xN(1:3)
|
||||
REAL(8):: xO(1:3), detJ, j(1:2,1:2), f(1:2)
|
||||
REAL(8):: dPsi(1:2,1:3), fPsi(1:3)
|
||||
REAL(8):: conv
|
||||
REAL(8):: xi(1:3)
|
||||
REAL(8):: invJ(1:2,1:2), detJ
|
||||
REAL(8):: deltaR(1:2)
|
||||
REAL(8):: dPsi(1:2,1:3)
|
||||
|
||||
!Iterative newton method to transform coordinates
|
||||
!TODO: Try to find a direct alternative
|
||||
conv=1.D0
|
||||
xO=(/1.D0/3.D0, 1.D0/3.D0, 0.D0 /)
|
||||
|
||||
DO WHILE(conv>1.D-4)
|
||||
dPsi = self%dPsi(xO)
|
||||
j = self%invJac(xO, dPsi)
|
||||
fPsi = self%fPsi(xO)
|
||||
f(1) = DOT_PRODUCT(fPsi,self%z)-r(1)
|
||||
f(2) = DOT_PRODUCT(fPsi,self%r)-r(2)
|
||||
detJ = self%detJac(xO,dPsi)
|
||||
xN(1:2)=xO(1:2) - MATMUL(j, f)/detJ
|
||||
conv=MAXVAL(DABS(xN-xO),1)
|
||||
xO=xN
|
||||
|
||||
END DO
|
||||
!Direct method to convert coordinates
|
||||
xi = (/ 0.D0, 0.D0, 0.D0 /) !Irrelevant, required for input
|
||||
deltaR = (/ r(1) - self%z(1), r(2) - self%r(1) /)
|
||||
dPsi = self%dPsi(xi)
|
||||
invJ = self%invJac(xi, dPsi)
|
||||
detJ = self%detJac(xi, dPsi)
|
||||
xi(1:2) = MATMUL(invJ,deltaR)/detJ
|
||||
|
||||
END FUNCTION phy2logTria
|
||||
|
||||
|
|
@ -969,7 +992,7 @@ MODULE moduleMeshCyl
|
|||
|
||||
CLASS(meshVolCyl), INTENT(in):: self
|
||||
REAL(8), INTENT(in):: xi(1:3)
|
||||
REAL(8), INTENT(in), OPTIONAL:: dPsi_in(:,:)
|
||||
REAL(8), INTENT(in), OPTIONAL:: dPsi_in(1:,1:)
|
||||
REAL(8), ALLOCATABLE:: dPsi(:,:)
|
||||
REAL(8):: dJ
|
||||
REAL(8):: dz(1:2), dr(1:2)
|
||||
|
|
@ -993,8 +1016,8 @@ MODULE moduleMeshCyl
|
|||
|
||||
CLASS(meshVolCyl), INTENT(in):: self
|
||||
REAL(8), INTENT(in):: xi(1:3)
|
||||
REAL(8), INTENT(in), OPTIONAL:: dPsi_in(:,:)
|
||||
REAL(8):: dPsi(1:2,1:4)
|
||||
REAL(8), INTENT(in), OPTIONAL:: dPsi_in(1:,1:)
|
||||
REAL(8), ALLOCATABLE:: dPsi(:,:)
|
||||
REAL(8):: dz(1:2), dr(1:2)
|
||||
REAL(8):: invJ(1:2,1:2)
|
||||
|
||||
|
|
@ -1033,7 +1056,7 @@ MODULE moduleMeshCyl
|
|||
!
|
||||
! END IF
|
||||
part%e_p = self%n
|
||||
part%xi = xi
|
||||
part%xi = xi
|
||||
part%n_in = .TRUE.
|
||||
!Assign particle to listPart_in
|
||||
CALL OMP_SET_LOCK(self%lock)
|
||||
|
|
|
|||
|
|
@ -78,7 +78,6 @@ MODULE moduleMeshCylRead
|
|||
BACKSPACE(10)
|
||||
END DO
|
||||
|
||||
!TODO: symplify to read all elements independently if they are edges or vols
|
||||
!Reads edges
|
||||
DO e=1, self%numEdges
|
||||
READ(10,*) n, elemType, eTemp, boundaryType, eTemp, p(1:2)
|
||||
|
|
@ -97,16 +96,30 @@ MODULE moduleMeshCylRead
|
|||
|
||||
END SELECT
|
||||
|
||||
CALL self%edges(e)%obj%init(n, p, bt, boundaryType)
|
||||
CALL self%edges(e)%obj%init(n, p(1:2), bt, boundaryType)
|
||||
|
||||
END DO
|
||||
|
||||
!Read and initialize volumes
|
||||
!TODO: Extend to triangular elements
|
||||
DO e=1, self%numVols
|
||||
READ(10,*) n, elemType, eTemp, eTemp, eTemp, p(1:4)
|
||||
ALLOCATE(meshVolCylQuad:: self%vols(e)%obj)
|
||||
CALL self%vols(e)%obj%init(n - self%numEdges, p)
|
||||
READ(10,*) n, elemType
|
||||
BACKSPACE(10)
|
||||
|
||||
SELECT CASE(elemType)
|
||||
CASE (2)
|
||||
!Triangular element
|
||||
READ(10,*) n, elemType, eTemp, eTemp, eTemp, p(1:3)
|
||||
ALLOCATE(meshVolCylTria:: self%vols(e)%obj)
|
||||
CALL self%vols(e)%obj%init(n - self%numEdges, p(1:3))
|
||||
|
||||
CASE (3)
|
||||
!Quadrilateral element
|
||||
READ(10,*) n, elemType, eTemp, eTemp, eTemp, p(1:4)
|
||||
ALLOCATE(meshVolCylQuad:: self%vols(e)%obj)
|
||||
CALL self%vols(e)%obj%init(n - self%numEdges, p(1:4))
|
||||
|
||||
END SELECT
|
||||
|
||||
|
||||
END DO
|
||||
|
||||
|
|
@ -115,10 +128,12 @@ MODULE moduleMeshCylRead
|
|||
!Build connectivity between elements
|
||||
DO e = 1, self%numVols
|
||||
!Connectivity between volumes
|
||||
DO et = 1, self%numVols
|
||||
CALL connected(self%vols(e)%obj, self%vols(et)%obj)
|
||||
IF (e /= et) THEN
|
||||
DO et = 1, self%numVols
|
||||
CALL connected(self%vols(e)%obj, self%vols(et)%obj)
|
||||
|
||||
END DO
|
||||
END DO
|
||||
END IF
|
||||
|
||||
!Connectivity between vols and edges
|
||||
DO et = 1, self%numEdges
|
||||
|
|
@ -133,19 +148,38 @@ MODULE moduleMeshCylRead
|
|||
|
||||
END SUBROUTINE
|
||||
|
||||
!Selects type of elements to build connection
|
||||
SUBROUTINE connectedVolVol(elemA, elemB)
|
||||
IMPLICIT NONE
|
||||
|
||||
CLASS(meshVol), INTENT(inout):: elemA
|
||||
CLASS(meshVol), INTENT(inout):: elemB
|
||||
|
||||
|
||||
SELECT TYPE(elemA)
|
||||
TYPE IS (meshVolCylQuad)
|
||||
TYPE IS(meshVolCylQuad)
|
||||
!Element A is a quadrilateral
|
||||
SELECT TYPE(elemB)
|
||||
TYPE IS(meshVolCylQuad)
|
||||
!Element B is a quadrilateral
|
||||
CALL connectedQuadQuad(elemA, elemB)
|
||||
|
||||
TYPE IS(meshVolCylTria)
|
||||
!Element B is a triangle
|
||||
CALL connectedQuadTria(elemA, elemB)
|
||||
|
||||
END SELECT
|
||||
|
||||
TYPE IS(meshVolCylTria)
|
||||
!Element A is a Triangle
|
||||
SELECT TYPE(elemB)
|
||||
TYPE IS(meshVolCylQuad)
|
||||
!Element B is a quadrilateral
|
||||
CALL connectedQuadTria(elemB, elemA)
|
||||
|
||||
TYPE IS(meshVolCylTria)
|
||||
!Element B is a triangle
|
||||
CALL connectedTriaTria(elemA, elemB)
|
||||
|
||||
END SELECT
|
||||
|
||||
END SELECT
|
||||
|
|
@ -158,12 +192,17 @@ MODULE moduleMeshCylRead
|
|||
CLASS(meshVol), INTENT(inout):: elemA
|
||||
CLASS(meshEdge), INTENT(inout):: elemB
|
||||
|
||||
SELECT TYPE(elemA)
|
||||
TYPE IS (meshVolCylQuad)
|
||||
SELECT TYPE(elemB)
|
||||
CLASS IS(meshEdgeCyl)
|
||||
SELECT TYPE(elemB)
|
||||
CLASS IS(meshEdgeCyl)
|
||||
SELECT TYPE(elemA)
|
||||
TYPE IS(meshVolCylQuad)
|
||||
!Element A is a quadrilateral
|
||||
CALL connectedQuadEdge(elemA, elemB)
|
||||
|
||||
TYPE IS(meshVolCylTria)
|
||||
!Element A is a triangle
|
||||
CALL connectedTriaEdge(elemA, elemB)
|
||||
|
||||
END SELECT
|
||||
|
||||
END SELECT
|
||||
|
|
@ -176,44 +215,208 @@ MODULE moduleMeshCylRead
|
|||
CLASS(meshVolCylQuad), INTENT(inout), TARGET:: elemA
|
||||
CLASS(meshVolCylQuad), INTENT(inout), TARGET:: elemB
|
||||
|
||||
!Check direction 1
|
||||
IF (.NOT. ASSOCIATED(elemA%e1) .AND. &
|
||||
elemA%n1%n == elemB%n4%n .AND. &
|
||||
elemA%n2%n == elemB%n3%n) THEN
|
||||
!Check direction 1
|
||||
IF (.NOT. ASSOCIATED(elemA%e1) .AND. &
|
||||
elemA%n1%n == elemB%n4%n .AND. &
|
||||
elemA%n2%n == elemB%n3%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 2
|
||||
IF (.NOT. ASSOCIATED(elemA%e2) .AND. &
|
||||
elemA%n2%n == elemB%n1%n .AND. &
|
||||
elemA%n3%n == elemB%n4%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e4 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 3
|
||||
IF (.NOT. ASSOCIATED(elemA%e3) .AND. &
|
||||
elemA%n3%n == elemB%n2%n .AND. &
|
||||
elemA%n4%n == elemB%n1%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 4
|
||||
IF (.NOT. ASSOCIATED(elemA%e4) .AND. &
|
||||
elemA%n4%n == elemB%n3%n .AND. &
|
||||
elemA%n1%n == elemB%n2%n) THEN
|
||||
elemA%e4 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
END SUBROUTINE connectedQuadQuad
|
||||
|
||||
SUBROUTINE connectedQuadTria(elemA, elemB)
|
||||
IMPLICIT NONE
|
||||
|
||||
CLASS(meshVolCylQuad), INTENT(inout), TARGET:: elemA
|
||||
CLASS(meshVolCylTria), INTENT(inout), TARGET:: elemB
|
||||
|
||||
!Check direction 1
|
||||
IF (.NOT. ASSOCIATED(elemA%e1)) THEN
|
||||
IF (elemA%n1%n == elemB%n1%n .AND. &
|
||||
elemA%n2%n == elemB%n3%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n1%n == elemB%n3%n .AND. &
|
||||
elemA%n2%n == elemB%n2%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n1%n == elemB%n2%n .AND. &
|
||||
elemA%n2%n == elemB%n1%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 2
|
||||
IF (.NOT. ASSOCIATED(elemA%e2) .AND. &
|
||||
elemA%n2%n == elemB%n1%n .AND. &
|
||||
elemA%n3%n == elemB%n4%n) THEN
|
||||
END IF
|
||||
|
||||
!Check direction 2
|
||||
IF (.NOT. ASSOCIATED(elemA%e2)) THEN
|
||||
IF (elemA%n2%n == elemB%n1%n .AND. &
|
||||
elemA%n3%n == elemB%n3%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e4 => elemA
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n2%n == elemB%n3%n .AND. &
|
||||
elemA%n3%n == elemB%n2%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n2%n == elemB%n2%n .AND. &
|
||||
elemA%n3%n == elemB%n1%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 3
|
||||
IF (.NOT. ASSOCIATED(elemA%e3) .AND. &
|
||||
elemA%n3%n == elemB%n2%n .AND. &
|
||||
elemA%n4%n == elemB%n1%n) THEN
|
||||
END IF
|
||||
|
||||
!Check direction 3
|
||||
IF (.NOT. ASSOCIATED(elemA%e3)) THEN
|
||||
IF (elemA%n3%n == elemB%n1%n .AND. &
|
||||
elemA%n4%n == elemB%n3%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n3%n == elemB%n3%n .AND. &
|
||||
elemA%n4%n == elemB%n2%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n3%n == elemB%n2%n .AND. &
|
||||
elemA%n4%n == elemB%n1%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 4
|
||||
IF (.NOT. ASSOCIATED(elemA%e4)) THEN
|
||||
IF (elemA%n4%n == elemB%n1%n .AND. &
|
||||
elemA%n1%n == elemB%n3%n) THEN
|
||||
elemA%e4 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n4%n == elemB%n3%n .AND. &
|
||||
elemA%n1%n == elemB%n2%n) THEN
|
||||
elemA%e4 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n4%n == elemB%n2%n .AND. &
|
||||
elemA%n1%n == elemB%n1%n) THEN
|
||||
elemA%e4 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 4
|
||||
IF (.NOT. ASSOCIATED(elemA%e4) .AND. &
|
||||
elemA%n4%n == elemB%n3%n .AND. &
|
||||
elemA%n1%n == elemB%n2%n) THEN
|
||||
elemA%e4 => elemB
|
||||
END IF
|
||||
|
||||
END SUBROUTINE connectedQuadTria
|
||||
|
||||
SUBROUTINE connectedTriaTria(elemA, elemB)
|
||||
IMPLICIT NONE
|
||||
|
||||
CLASS(meshVolCylTria), INTENT(inout), TARGET:: elemA
|
||||
CLASS(meshVolCylTria), INTENT(inout), TARGET:: elemB
|
||||
|
||||
!Check direction 1
|
||||
IF (.NOT. ASSOCIATED(elemA%e1)) THEN
|
||||
IF (elemA%n1%n == elemB%n1%n .AND. &
|
||||
elemA%n2%n == elemB%n3%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n1%n == elemB%n2%n .AND. &
|
||||
elemA%n2%n == elemB%n1%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
ELSEIF (elemA%n1%n == elemB%n3%n .AND. &
|
||||
elemA%n2%n == elemB%n2%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
END SUBROUTINE connectedQuadQuad
|
||||
END IF
|
||||
|
||||
!Check direction 2
|
||||
IF (.NOT. ASSOCIATED(elemA%e2)) THEN
|
||||
IF (elemA%n2%n == elemB%n1%n .AND. &
|
||||
elemA%n3%n == elemB%n3%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n2%n == elemB%n2%n .AND. &
|
||||
elemA%n3%n == elemB%n1%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
ELSEIF (elemA%n2%n == elemB%n3%n .AND. &
|
||||
elemA%n3%n == elemB%n2%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 3
|
||||
IF (.NOT. ASSOCIATED(elemA%e3)) THEN
|
||||
IF (elemA%n3%n == elemB%n1%n .AND. &
|
||||
elemA%n1%n == elemB%n3%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e3 => elemA
|
||||
|
||||
ELSEIF (elemA%n3%n == elemB%n2%n .AND. &
|
||||
elemA%n1%n == elemB%n1%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
ELSEIF (elemA%n3%n == elemB%n3%n .AND. &
|
||||
elemA%n1%n == elemB%n2%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
|
||||
END IF
|
||||
|
||||
END SUBROUTINE connectedTriaTria
|
||||
|
||||
SUBROUTINE connectedQuadEdge(elemA, elemB)
|
||||
IMPLICIT NONE
|
||||
|
|
@ -287,6 +490,62 @@ MODULE moduleMeshCylRead
|
|||
|
||||
END SUBROUTINE connectedQuadEdge
|
||||
|
||||
SUBROUTINE connectedTriaEdge(elemA, elemB)
|
||||
IMPLICIT NONE
|
||||
|
||||
CLASS(meshVolCylTria), INTENT(inout), TARGET:: elemA
|
||||
CLASS(meshEdgeCyl), INTENT(inout), TARGET:: elemB
|
||||
|
||||
!Check direction 1
|
||||
IF (.NOT. ASSOCIATED(elemA%e1)) THEN
|
||||
IF (elemA%n1%n == elemB%n1%n .AND. &
|
||||
elemA%n2%n == elemB%n2%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n1%n == elemB%n2%n .AND. &
|
||||
elemA%n2%n == elemB%n1%n) THEN
|
||||
elemA%e1 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 2
|
||||
IF (.NOT. ASSOCIATED(elemA%e2)) THEN
|
||||
IF (elemA%n2%n == elemB%n1%n .AND. &
|
||||
elemA%n3%n == elemB%n2%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n2%n == elemB%n2%n .AND. &
|
||||
elemA%n3%n == elemB%n1%n) THEN
|
||||
elemA%e2 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
END IF
|
||||
|
||||
!Check direction 3
|
||||
IF (.NOT. ASSOCIATED(elemA%e3)) THEN
|
||||
IF (elemA%n3%n == elemB%n1%n .AND. &
|
||||
elemA%n1%n == elemB%n2%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e2 => elemA
|
||||
|
||||
ELSEIF (elemA%n3%n == elemB%n2%n .AND. &
|
||||
elemA%n1%n == elemB%n1%n) THEN
|
||||
elemA%e3 => elemB
|
||||
elemB%e1 => elemA
|
||||
|
||||
END IF
|
||||
|
||||
END IF
|
||||
|
||||
END SUBROUTINE connectedTriaEdge
|
||||
|
||||
SUBROUTINE constructGlobalK(K, elem)
|
||||
IMPLICIT NONE
|
||||
|
||||
|
|
@ -305,6 +564,13 @@ MODULE moduleMeshCylRead
|
|||
n = (/ elem%n1%n, elem%n2%n, &
|
||||
elem%n3%n, elem%n4%n /)
|
||||
|
||||
TYPE IS(meshVolCylTria)
|
||||
nNodes = 3
|
||||
ALLOCATE(localK(1:nNodes,1:nNodes))
|
||||
localK = elem%elemK()
|
||||
ALLOCATE(n(1:nNodes))
|
||||
n = (/ elem%n1%n, elem%n2%n, elem%n3%n /)
|
||||
|
||||
CLASS DEFAULT
|
||||
nNodes = 0
|
||||
ALLOCATE(localK(1:1, 1:1))
|
||||
|
|
@ -461,6 +727,7 @@ MODULE moduleMeshCylRead
|
|||
REAL(8):: time
|
||||
CHARACTER(:), ALLOCATABLE:: fileName
|
||||
CHARACTER (LEN=6):: tstring !TODO: Review to allow any number of iterations
|
||||
REAL(8):: xi(1:3)
|
||||
|
||||
IF (emOutput) THEN
|
||||
time = DBLE(t)*tau*ti_ref
|
||||
|
|
@ -496,7 +763,13 @@ MODULE moduleMeshCylRead
|
|||
WRITE(20, *) 3
|
||||
WRITE(20, *) self%numVols
|
||||
DO e=1, self%numVols
|
||||
WRITE(20, *) e+self%numEdges, self%vols(e)%obj%gatherEF((/0.D0, 0.D0, 0.D0/))*EF_ref
|
||||
SELECT TYPE(elem=>self%vols(e)%obj)
|
||||
TYPE IS(meshVolCylQuad)
|
||||
xi = (/ 0.D0, 0.D0, 0.D0 /)
|
||||
TYPE IS(meshVolCylTria)
|
||||
xi = (/ 1.D0/3.D0, 1.D0/3.D0, 0.D0 /)
|
||||
END SELECT
|
||||
WRITE(20, *) e+self%numEdges, self%vols(e)%obj%gatherEF(xi)*EF_ref
|
||||
END DO
|
||||
WRITE(20, "(A)") '$EndElementData'
|
||||
CLOSE(20)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue