Skip to content

Latest commit

 

History

History
379 lines (294 loc) · 19.1 KB

09_ModuleLinkages.md

File metadata and controls

379 lines (294 loc) · 19.1 KB

9 Modules and Linkages

| Prev: 08 Configuration | Next: 10 Design and Implementation | Table of Contents |


The fire-behavior-simulator is a Javascript implementation of all the mathematical models contained within the BehavePlus Fire Modeling System, a C++ program that runs on the Windows operating system.

As such, the fire-behavior-simulator is comprised of many inter-connected models; fuel model outputs are inputs for the fuel bed model; whose outputs are inputs to the fire spread rate and intensity model, whose outputs are inputs to surface fire spotting, crown fire, scorch height, and fire ellipse models, whose outputs are inputs to fire containement model, and so forth. Some models are single equations, while others can require many equations and intermediate variables.

The following is a summary of some of the models, generally arranged in their order of input-output dependencies:

  • The herbaceous fuel curing model estimates dead and live herb fuel loads from live herbaceous fuel moisture used by the fuel bed model.

  • The chaparral dynamic fuel model estimates chaparral fuel particles and bed depth used by the fuel bed model.

  • The palmetto-gallberry dynamic fuel model estimates palmetto-gallberry fuel particles and bed depth used by the fuel bed model.

  • The western aspen dynamic fuel model estimates western aspen fuel particles and bed depth used by the fuel bed model.

  • The standard fuel catalog provides pre-defined fuel conditions used by the fuel bed model.

  • The fuel bed model determines fuel array combustion characteristics from fuel particle life category, load, size, moisture, density, heat content, and mineral content, which are required by the **fire intensity and spread rate model.

  • The wind speed adjustment model estimates wind speed at midflame height from thet open-canopy 20-ft wind speed, canopy characteristics, and fuel bed depth.

  • The fire intensity and spread rate model uses fuel bed combustion characteristics along with slope steepness and midflame wind speed to determine maximum fireline intensity, spread rate, reaction intensity, residence time, and heat per unit area.

  • The fire heading model uses wind direction and slope steepness to determine the direction of maximum spread from upslope.

  • The flame length model estimates flame length from fireline intensity (or vice-versa).

  • The fire behavior weighting model estimates overall spread rate, fireline intensity, flame length, direction of maximum spread, heat per unit area for a surface fire with 2 fuel models.

  • The surface fire spotting model estimates firebrand height, drift, and distance over flat and mountaineous terrain from surface fire intensity, wind, and terrain inputs.

  • The fire ellipse model estimates fire ellipse perimeter, size, and fire behavior (spread rate, spread distance, intensity, flame length, scorch height, tree mortality) at the head, back, flanks, or other arbitrary vector given the surface fire spread rate, fireline intensity, and length-to-width ratio.

  • The fire containment model

  • The Rothermel active crown fire model

  • The Scott & Reinhardt crown fire model

  • The crown fire spotting model

fire-behavior-simulator Module Use Cases

When a fire-behavior-simulator DAG is initially created, it is constructed as one large continuous directed acyclical graph. To demonstrate, assume you want a table of tree mortality rates. At its most basic, the tree mortality model requires just 5 inputs; a tree species, dbh, crown height, crown base height, and scorch height.

But because the entire DAG is linked together, tree mortality rate will get its scorch height input from the scorch height model. The scorch height model, in turn, requires fireline intensity as an input. Because the DAG is fully linked, fireline intensity will be provided by the surface fire model, which in turn can require a lot of inputs. The resulting list of 16 required inputs includes fuel parameters, fuel moistures, slope, wind speed, wind direction, canopy parameters, and air temperature:

import { Sim } from '../src/index.js'

test('1: Tree Mortality Rate required inputs for a fully linked DAG', () => {
  const sim = new Sim()
  const dag = sim.createDag('LinkedMortality')

  // Select mortality rate
  dag.select(['mortality.rate'])

  // What inputs are required?
  const inputNodes = dag.requiredInputNodes()
  expect(inputNodes.length).toEqual(16)

  // Requires 4 tree inputs:
  expect(inputNodes).toContain(dag.node('site.canopy.tree.dbh'))
  expect(inputNodes).toContain(dag.node('site.canopy.tree.species.fofem6.code'))
  expect(inputNodes).toContain(dag.node('site.canopy.crown.baseHeight'))
  expect(inputNodes).toContain(dag.node('site.canopy.crown.totalHeight'))

  // and a whole bunch of surface fire inputs to calculate scorch height
  expect(inputNodes).toContain(dag.node('site.temperature.air'))
  expect(inputNodes).toContain(dag.node('surface.primary.fuel.model.catalogKey'))
  expect(inputNodes).toContain(dag.node('surface.primary.fuel.model.behave.parms.cured.herb.fraction'))
  expect(inputNodes).toContain(dag.node('site.moisture.dead.tl1h'))
  expect(inputNodes).toContain(dag.node('site.moisture.dead.tl10h'))
  expect(inputNodes).toContain(dag.node('site.moisture.dead.tl100h'))
  expect(inputNodes).toContain(dag.node('site.moisture.live.herb'))
  expect(inputNodes).toContain(dag.node('site.moisture.live.stem'))
  expect(inputNodes).toContain(dag.node('site.windSpeedAdjustmentFactor'))
  expect(inputNodes).toContain(dag.node('site.slope.steepness.ratio'))
  expect(inputNodes).toContain(dag.node('site.wind.speed.at20ft'))
  expect(inputNodes).toContain(dag.node('site.wind.direction.heading.fromUpslope'))
})

But consider the use case where we simply want to examine tree mortality rate over a range of scorch heights. We want to just enter the desired scorch height values directly rather than try to generate them from a myrad of surface fire module inputs. That is, we just want to enter the bare minimum 5 inputs. To do so, we unlink the Tree Mortality module from the rest of the DAG:

test('2: Tree Mortality Rate required inputs when unlinked', () => {
  const sim = new Sim()
  const dag = sim.createDag('UnlinkedMortality')

  // Unlink the tree mortality model and select mortality rate
  dag.configure([['link.treeMortality', 'standAlone']])
  dag.select(['mortality.rate'])

  // What inputs are required?
  const inputNodes = dag.requiredInputNodes()
  expect(inputNodes.length).toEqual(5)

  // Requires 4 tree inputs:
  expect(inputNodes).toContain(dag.node('site.canopy.crown.baseHeight'))
  expect(inputNodes).toContain(dag.node('site.canopy.crown.totalHeight'))
  expect(inputNodes).toContain(dag.node('site.canopy.tree.dbh'))
  expect(inputNodes).toContain(dag.node('site.canopy.tree.species.fofem6.code'))

  // And the scorch height input
  expect(inputNodes).toContain(dag.node('site.fire.observed.scorchHeight'))
})

To solve this issue, BehavePlus employs the concept of modules to identify subsets of the DAG that can be run as 'stand-alone' models. As shown above, the 'Tree Mortality Module' in stand-alone mode requires just the 4 tree parameters plus scorch height.

When Tree Mortality is 'linked' to the stand-alone 'Scorch Height Module', the required scorch height input is calculated from 3 other inputs: air temperature, midflame wind speed, and fireline intensity:

test('3: Tree Mortality Rate required inputs when stand-alone Scorch Hieight - Tree Mortality models', () => {
  const sim = new Sim()
  const dag = sim.createDag('StandaloneScorchMortality')

  // Unlink the scorch height model tree mortality model and select mortality rate
  dag.configure([
    ['link.scorchHeight', 'standAlone'],
    ['link.treeMortality', 'linkedToScorchHeight'],
    ['configure.wind.speed', 'atMidflame']])
  dag.select(['mortality.rate'])

  // What inputs are required?
  const inputNodes = dag.requiredInputNodes()
  expect(inputNodes.length).toEqual(7)

  // Requires 4 tree inputs:
  expect(inputNodes).toContain(dag.node('site.canopy.crown.baseHeight'))
  expect(inputNodes).toContain(dag.node('site.canopy.crown.totalHeight'))
  expect(inputNodes).toContain(dag.node('site.canopy.tree.dbh'))
  expect(inputNodes).toContain(dag.node('site.canopy.tree.species.fofem6.code'))

  // plus 3 inputs to determine scorch height
  expect(inputNodes).toContain(dag.node('site.fire.observed.firelineIntensity'))
  expect(inputNodes).toContain(dag.node('site.temperature.air'))
  expect(inputNodes).toContain(dag.node('site.wind.speed.atMidflame'))
})

But when 'Scorch Height Module' is linked to the 'Surface Fire Module', we see that a lot more inputs are required to determine the required fireline intensity variable.


BehavePlus Modules

The BehavePlus Windows program has a 'Configure' dialog that allows linking some of its 10 Modules as follows:


  • ☑ Surface Fire
    • ☑ Crown Fire
      • ☑ Crown Fire Spotting
    • ☑ Fire Ellipse
      • ☐ Fire Containment
    • ☑ Surface Fire Spotting
    • ☑ Scorch Height
      • ☑ Tree Mortality
  • ☑ Spotting from Burning Pile or Torching Trees
  • ☑ Ignition Probability

The dialog shows 7 possible linkages where a client Module binds one or more of its required inputs to a provider Module's outputs:

  • Crown Fire (CROWN) may link to Surface Fire (SURFACE),
  • Crown Fire Spotting (CROWN SPOT)may link to Crown Fire (CROWN),
  • Fire Ellipse (SIZE) may link to Surface Fire (SURFACE),
  • Fire Containment (CONTAIN) may link to to Fire Ellipse (SIZE),
  • Surface Spotting (SURF SPOT) may link to Surface Fire (SURFACE),
  • Scorch Height (SCORCH) may link to Surface Fire (SURFACE), and
  • Tree Mortality (MORTALITY) may link to Scorch Height (SCORCH)

The fire-behavior-simulator genome is defined such that the models in the DAG are connected or unconnected by setting 7 corresponding link configuration DagNodes:

Link Node Key Allowable Values
link.crownFire 'linkedToSurfaceFire' or 'standAlone'
link.crownSpot 'linkedToCrownFire' or 'standAlone'
link.fireEllipse 'linkedToSurfaceFire or 'standAlone'
link.fireContain 'linkedToFireEllipse' or 'standAlone'
link.surfaceSpot 'linkedToSurfaceFire' or 'standAlone'
link.scorchHeight 'linkedToSurfaceFire' or 'standAlone'
link.treeMortality 'linkedToScorchHeight'

These flow through the DAG as follows:

                             /------------------/
                             /Surface Fire Model/
                             /------------------/
                                       |
                                       V
        +-------------------+----------+----------+------------------+
        |                   |                     |                  |
        V                   V                     V                  V
 <link.crownFire>   <link.fireEllipse>   <link.surfaceSpot>  <link.scorchHeight>
        |                   |                     |                  |
        V                   V                     V                  V
/----------------/ /------------------/ /------------------/ /---------------/
/Crown Fire Model/ /Fire Ellipse Model/ /Surface Spot Model/ /Scorch Ht Model/
/----------------/ /------------------/ /------------------/ /---------------/
        |                   |                                        |
        V                   V                                        V
 <link.crownSpot>   <link.fireContain>                      <link.treeMortality>
        |                   |                                        |
        V                   V                                        V
/----------------/ /------------------/                    /-------------------/
/Crown Spot Model/ /Fire Contain Model/                   /Tree Mortality Model/
/----------------/ /------------------/                    /-------------------/

link.crownFire - Crown Fire Module Bindings

The Crown Fire Module may link to the Surface Fire Module by setting link.crownFire to 'linkedToSurfaceFire' to obtain its required inputs:

  • surface fireline intensity or flame length
  • surface fire heat per unit area
When link.crownFireis 'standAlone'is 'linkedToSurfaceFire'
crown.fire.surface.firelineIntensity site.fire.observed.firelineIntensity surface.weighted.fire.firelineIntensity
crown.fire.surface.flameLength site.fire.observed.flameLength surface.weighted.fire.flameLength
crown.fire.surface.heatPerUnitArea site.fire.observed.heatPerUnitArea surface.weighted.fire.heatPerUnitArea

The site.fire.observed. DagNodes are always client input.


link.crownSpot - Crown Fire Spotting Module Bindings

The Crown Fire Spotting Module may link to the Crown Fire Module by setting link.crownSpot to 'linkedToCrownFire' to obtain its required input:

  • active crown fire fireline intensity
When link.crownSpotis 'standAlone'is 'linkedToCrownFire'
spotting.crownFire.firelineIntensity firelineIntensityThomas(
site.fire.crown.flameLength )
crown.fire.active.firelineIntensity

link.fireEllipse - Fire Ellipse Module Bindings

The Fire Ellipse Module may link to the Surface Fire Module by setting link.fireEllipse to 'linkedToSurfaceFire' to obtain its required inputs:

  • spread rate at fire head
  • heading direction from upslope
  • fireline intensity (or flame length) at head
  • length-to-width ratio (or effective wind speed)
  • wind speed at midflame height (for scorch height outputs)
When link.fireEllipseis 'standAlone'is 'linkedToSurfaceFire'
surface.fire.ellipse.axis.effectiveWindSpeed site.fire.observed.effectiveWindSpeed surface.weighted.fire.effectiveWindSpeed
surface.fire.ellipse.axis.lengthToWidthRatio site.fire.observed.lengthToWidthRatio surface.weighted.fire.lengthToWidthRatio
surface.fire.ellipse.head.firelineIntensity site.fire.observed.firelineIntensity surface.weighted.fire.firelineIntensity
surface.fire.ellipse.head.flameLength site.fire.observed.flameLength surface.weighted.fire.flameLength
surface.fire.ellipse.head.spreadRate site.fire.observed.spreadRate surface.weighted.fire.spreadRate
surface.fire.ellipse.heading.fromUpslope site.fire.observed.heading.fromUpslope surface.weighted.fire.heading.fromUpslope
surface.fire.ellipse.wind.speed.atMidflame site.wind.speed.atMidflame surface.weighted.fire.wind.speed.atMidflame

The site.fire.observed. DagNodes are always client input.


link.fireContain - Fire Containment Module Bindings

The Fire CONTAIN Module is not implemented!! But if it were...

The Fire Containment Module my link to the Fire Ellipse Module by setting link.fireContain to 'linkedToFireEllipse' to obtain its required inputs:

  • spread rate at head
  • length-to-width ratio

link.surfaceSpot - Surface Spotting Module Bindings

The Surface Spotting Module may link to the Surface Fire Module by setting link.surfaceSpot to 'linkedToSurfaceFire' to obtain its required input:

  • surface fireline intensity (or flame length)
When link.surfaceSpottingis 'standAlone'is 'linkedToSurfaceFire'
spotting.surfaceFire.firelineIntensity site.fire.observed.firelineIntensity surface.weighted.fire.firelineIntensity

The site.fire.observed. DagNodes are always client input.


link.scorchHeight - Scorch Height Module Bindings

The Scorch Height Module may link to the Surface Fire Module by setting link.scorchHeight to 'linkedToSurfaceFire' to obtain its required inputs:

  • surface fireline intensity (or flame length)
  • wind speed at midflame height
configure.link.scorchHeightstandAlonesurfaceFire
scorch.firelineIntensity site.fire.observed.firelineIntensity surface.weighted.fire.firelineIntensity
scorch.wind.speed site.wind.speed.atMidflame surface.weighted.fire.wind.speed.atMidflame

The site.fire.observed. DagNodes are always client input.

Note that 3 scorch height variables are always available from within the Surface Fire Module whether or not the 'Scorch Height Module' is active or linked:

  • surface.primary.fuel.fire.scorchHeight,
  • surface.secondary.fuel.fire.scorchHeight,
  • surface.weighted.fire.scorchHeight,

Similarly, note that 6 scorch height variables are always available from within the Fire Ellipse Module whether or not the 'Scorch Height Module' is active or linked:

  • surface.fire.ellipse.back.scorchHeight
  • surface.fire.ellipse.beta.scorchHeight
  • surface.fire.ellipse.beta5.scorchHeight
  • surface.fire.ellipse.flank.scorchHeight
  • surface.fire.ellipse.head.scorchHeight
  • surface.fire.ellipse.psi.scorchHeight

link.treeMortality - Tree Mortality Module Bindings

The Tree Mortality Module may link to the Scorch Height Module by setting link.treeMortality to 'linkedToScorchHeight' to obtain its required input:

  • scorch height
When link.treeMortalityis 'standAlone'is 'linkedToScorchHeight'
mortality.scorchHeight site.fire.observed.scorchHeight scorch.height

The site.fire.observed. DagNodes are always client input.


Summary

Surface Fire can be linked (provide input) to 4 other modules:

  • Crown Fire can use Surface Fire's
    • surface fireline intensity (or flame length)
    • surface fire heat per unit area
  • Surface Spotting can use Surface Fire's
    • surface fireline intensity (or flame length)
  • Fire Ellipse can use Surface Fire's
    • surface fireline intensity (or flame length)
    • surface fire spread rate
    • fire heading direction from upslope
    • surface fire length-to-width-ratio (or effective wind speed)
    • wind speed at midflame height
  • Scorch Height can use Surface Fire's
    • surface fireline intensity (or flame length)
    • wind speed at midflame height

| Prev: 08 Configuration | Next: 10 Design and Implementation | Table of Contents |