Skip to content

Commit 01dd888

Browse files
authored
Merge pull request #14722 from ericvmueller/master
Correct the vector implementation of Rothermel slope factor for level set spread
2 parents cc2a765 + 4ba1683 commit 01dd888

File tree

3 files changed

+36
-28
lines changed

3 files changed

+36
-28
lines changed

Source/mesh.f90

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -333,7 +333,7 @@ MODULE MESH_VARIABLES
333333
REAL(EB), ALLOCATABLE, DIMENSION(:,:) :: FLUX0_LS,FLUX1_LS,PHI_LS,PHI1_LS,ROS_BACKU, &
334334
ROS_HEAD,ROS_FLANK,WIND_EXP, &
335335
SR_X_LS,SR_Y_LS,U_LS,V_LS,Z_LS,DZTDX,DZTDY,MAG_ZT, &
336-
PHI_WS,UMF,THETA_ELPS,PHI_S,PHI_S_X,PHI_S_Y,PHI_W,LS_WORK1,LS_WORK2
336+
PHI_WS,UMF,THETA_ELPS,PHI_S_X,PHI_S_Y,PHI_W,LS_WORK1,LS_WORK2
337337

338338
END TYPE MESH_TYPE
339339

@@ -475,7 +475,7 @@ MODULE MESH_POINTERS
475475
REAL(EB), POINTER, DIMENSION(:,:) :: FLUX0_LS,FLUX1_LS,PHI_LS,PHI1_LS,ROS_BACKU, &
476476
ROS_HEAD,ROS_FLANK,WIND_EXP, &
477477
SR_X_LS,SR_Y_LS,U_LS,V_LS,Z_LS,DZTDX,DZTDY,MAG_ZT, &
478-
PHI_WS,UMF,THETA_ELPS,PHI_S,PHI_S_X,PHI_S_Y,PHI_W,LS_WORK1,LS_WORK2
478+
PHI_WS,UMF,THETA_ELPS,PHI_S_X,PHI_S_Y,PHI_W,LS_WORK1,LS_WORK2
479479

480480

481481
CONTAINS
@@ -875,7 +875,6 @@ SUBROUTINE POINT_TO_MESH(NM)
875875
PHI_WS => M%PHI_WS
876876
UMF => M%UMF
877877
THETA_ELPS => M%THETA_ELPS
878-
PHI_S => M%PHI_S
879878
PHI_S_X => M%PHI_S_X
880879
PHI_S_Y => M%PHI_S_Y
881880
PHI_W => M%PHI_W

Source/vege.f90

Lines changed: 22 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,7 @@ SUBROUTINE INITIALIZE_LEVEL_SET_FIRESPREAD_2(NM,MODE)
156156

157157
INTEGER, INTENT(IN) :: NM,MODE
158158
INTEGER :: I,IM1,IM2,IIG,IP1,IP2,J,JJG,JM1,JP1
159-
REAL(EB) :: DZT_DUM,G_EAST,G_WEST,G_SOUTH,G_NORTH
159+
REAL(EB) :: DZT_DUM,DZTDX_DUM,DZTDY_DUM,G_EAST,G_WEST,G_SOUTH,G_NORTH
160160

161161
T_NOW = CURRENT_TIME()
162162

@@ -218,7 +218,6 @@ SUBROUTINE INITIALIZE_LEVEL_SET_FIRESPREAD_2(NM,MODE)
218218
! Rothermel 'Phi' factors for effects of Wind and Slope on ROS
219219

220220
ALLOCATE(M%PHI_WS(IBAR,JBAR)) ; CALL ChkMemErr('VEGE:LEVEL SET','PHI_W',IZERO) ; PHI_WS => M%PHI_WS ; PHI_WS = 0.0_EB
221-
ALLOCATE(M%PHI_S(IBAR,JBAR)) ; CALL ChkMemErr('VEGE:LEVEL SET','PHI_S',IZERO) ; PHI_S => M%PHI_S
222221
ALLOCATE(M%PHI_S_X(IBAR,JBAR)) ; CALL ChkMemErr('VEGE:LEVEL SET','PHI_S_X',IZERO) ; PHI_S_X => M%PHI_S_X
223222
ALLOCATE(M%PHI_S_Y(IBAR,JBAR)) ; CALL ChkMemErr('VEGE:LEVEL SET','PHI_S_Y',IZERO) ; PHI_S_Y => M%PHI_S_Y
224223

@@ -296,16 +295,19 @@ SUBROUTINE INITIALIZE_LEVEL_SET_FIRESPREAD_2(NM,MODE)
296295
E_ROTH = 0.715_EB * EXP(-0.01094_EB * SF%VEG_LSET_SIGMA)
297296
BETA_OP_ROTH = 0.20395_EB * (SF%VEG_LSET_SIGMA**(-0.8189_EB))! Optimum packing ratio
298297

299-
! Limit effect to slope lte 80 degrees. Phi_s_x,y are slope factors (Rothermel model)
300-
301-
DZT_DUM = MIN(5.67_EB,ABS(DZTDX(IIG,JJG))) ! 5.67 ~ tan 80 deg
302-
PHI_S_X(IIG,JJG) = 5.275_EB * ((SF%VEG_LSET_BETA)**(-0.3_EB)) * DZT_DUM**2
303-
PHI_S_X(IIG,JJG) = SIGN(PHI_S_X(IIG,JJG),DZTDX(IIG,JJG))
304-
DZT_DUM = MIN(1.73_EB,ABS(DZTDY(IIG,JJG))) ! 1.73 ~ tan 60 deg
305-
PHI_S_Y(IIG,JJG) = 5.275_EB * ((SF%VEG_LSET_BETA)**(-0.3_EB)) * DZT_DUM**2
306-
PHI_S_Y(IIG,JJG) = SIGN(PHI_S_Y(IIG,JJG),DZTDY(IIG,JJG))
298+
! Slope vector
299+
DZTDX_DUM = DZTDX(IIG,JJG)
300+
DZTDY_DUM = DZTDY(IIG,JJG)
301+
DZT_DUM = SQRT(DZTDX_DUM**2._EB+DZTDY_DUM**2._EB)
302+
! Limit effect to slope lte 80 degrees
303+
IF (DZT_DUM>5.67_EB) THEN
304+
DZTDX_DUM = DZTDX_DUM * 5.67_EB/DZT_DUM
305+
DZTDY_DUM = DZTDY_DUM * 5.67_EB/DZT_DUM
306+
DZT_DUM = 5.67_EB
307+
ENDIF
307308

308-
PHI_S(IIG,JJG) = SQRT(PHI_S_X(IIG,JJG)**2 + PHI_S_Y(IIG,JJG)**2)
309+
PHI_S_X(IIG,JJG) = 5.275_EB * ((SF%VEG_LSET_BETA)**(-0.3_EB)) * DZTDX_DUM * DZT_DUM
310+
PHI_S_Y(IIG,JJG) = 5.275_EB * ((SF%VEG_LSET_BETA)**(-0.3_EB)) * DZTDY_DUM * DZT_DUM
309311

310312
ENDIF IF_ELLIPSE
311313

@@ -332,8 +334,8 @@ SUBROUTINE LEVEL_SET_FIRESPREAD(T,DT,NM)
332334
REAL(EB), INTENT(IN) :: T,DT
333335
INTEGER :: IIG,IW,JJG,IC,OUTPUT_INDEX
334336
INTEGER :: KDUM,KWIND,ICF,IKT
335-
REAL(EB) :: UMF_TMP,PHX,PHY,MAG_PHI,PHI_W_X,PHI_W_Y,UMF_X,UMF_Y,UMAG,ROS_MAG,UMF_MAG,WIND_FACTOR,&
336-
SIN_THETA,COS_THETA,THETA,ZWIND(2),U_Z(2),V_Z(2),REF_WIND_HEIGHT
337+
REAL(EB) :: UMF_TMP,PHX,PHY,MAG_PHI,PHI_S,PHI_W_X,PHI_W_Y,UMF_X,UMF_Y,UMAG,ROS_MAG,UMF_MAG,&
338+
WIND_FACTOR,SIN_THETA,COS_THETA,THETA,ZWIND(2),U_Z(2),V_Z(2),REF_WIND_HEIGHT
337339

338340
T_NOW = CURRENT_TIME()
339341

@@ -464,7 +466,9 @@ SUBROUTINE LEVEL_SET_FIRESPREAD(T,DT,NM)
464466

465467
! Include Rothermel slope factor
466468

467-
IF (PHI_S(IIG,JJG) > 0.0_EB) THEN
469+
PHI_S = SQRT(PHI_S_X(IIG,JJG)+PHI_S_Y(IIG,JJG))
470+
471+
IF (PHI_S > 0.0_EB) THEN
468472

469473
PHX = PHI_W_X + PHI_S_X(IIG,JJG)
470474
PHY = PHI_W_Y + PHI_S_Y(IIG,JJG)
@@ -487,13 +491,11 @@ SUBROUTINE LEVEL_SET_FIRESPREAD(T,DT,NM)
487491
! 0.3048 ~= 1/3.281
488492
! if phi_s < 0 then a complex value (NaN) results. Using abs(phi_s) and sign function to correct.
489493

490-
UMF_TMP = (((ABS(PHI_S_X(IIG,JJG)) * (SF%VEG_LSET_BETA / BETA_OP_ROTH)**E_ROTH)/C_ROTH)**(1/B_ROTH))*0.3048
491-
UMF_TMP = SIGN(UMF_TMP,PHI_S_X(IIG,JJG))
492-
UMF_X = UMF_X + UMF_TMP
494+
UMF_TMP = &
495+
0.3048_EB/PHI_S*(((SF%VEG_LSET_BETA / BETA_OP_ROTH)**E_ROTH)*PHI_S/C_ROTH)**(1._EB/B_ROTH)
493496

494-
UMF_TMP = (((ABS(PHI_S_Y(IIG,JJG)) * (SF%VEG_LSET_BETA / BETA_OP_ROTH)**E_ROTH)/C_ROTH)**(1/B_ROTH))*0.3048
495-
UMF_TMP = SIGN(UMF_TMP,PHI_S_Y(IIG,JJG))
496-
UMF_Y = UMF_Y + UMF_TMP
497+
UMF_X = UMF_X + UMF_TMP*PHI_S_X(IIG,JJG)
498+
UMF_Y = UMF_Y + UMF_TMP*PHI_S_Y(IIG,JJG)
497499

498500
ELSE
499501

Utilities/Matlab/scripts/level_set_ellipse.m

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -163,7 +163,7 @@
163163
end
164164

165165
max_err = max(error_table{:,2:end}(:));
166-
if max_err>.15
166+
if max_err>.2
167167
display(['Matlab Warning: LS_ellipse is out of tolerance. Max error = ',num2str(max_err)])
168168
end
169169

@@ -218,8 +218,9 @@
218218
function [phi_s_x,phi_s_y] = slope_adj(dzdx,dzdy)
219219
beta=0.01; % packing ratio (-), FDS default
220220
% Rothermel optimum packing ratio
221-
phi_s_x = sign(dzdx)*5.275*beta^-0.3*dzdx^2;
222-
phi_s_y = sign(dzdy)*5.275*beta^-0.3*dzdy^2;
221+
dzds = sqrt(dzdx^2+dzdy^2);
222+
phi_s_x = 5.275*beta^-0.3*dzdx*dzds;
223+
phi_s_y = 5.275*beta^-0.3*dzdy*dzds;
223224
end
224225

225226
% calculate virtual wind vector for slope
@@ -233,7 +234,13 @@
233234
C = 7.47*exp(-0.8711*sigma.^0.55);
234235
B = 0.15988*sigma.^0.54;
235236
E = 0.715*exp(-0.01094*sigma);
237+
phi_s=sqrt(phi_s_x^2+phi_s_y^2);
238+
if (phi_s>0)
239+
uv_tmp = 0.3048/phi_s*(phi_s/C*beta_ratio^E)^(1/B);
240+
else
241+
uv_tmp = 0;
242+
end
236243
% divide by 60 to maintain units of m/s elsewhere
237-
u_virtual = 0.3048*(phi_s_x/C*beta_ratio^E)^(1/B)/60;
238-
v_virtual = 0.3048*(phi_s_y/C*beta_ratio^E)^(1/B)/60;
244+
u_virtual = uv_tmp*phi_s_x/60;
245+
v_virtual = uv_tmp*phi_s_y/60;
239246
end

0 commit comments

Comments
 (0)