diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/Make/files b/applications/solvers/multiphase/compressibleInterIsoFoam/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..3e4ec6e8991149ab5852470eba69923f64fff96d
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/Make/files
@@ -0,0 +1,3 @@
+compressibleInterIsoFoam.C
+
+EXE = $(FOAM_APPBIN)/compressibleInterIsoFoam
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/Make/options b/applications/solvers/multiphase/compressibleInterIsoFoam/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..9a2c766179fb8e7af91a785db146d9556fecd15c
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/Make/options
@@ -0,0 +1,39 @@
+EXE_INC = \
+    -I. \
+    -I../VoF \
+    -I../compressibleInterFoam \
+    -I$(FOAM_SOLVERS)/multiphase/compressibleInterFoam/twoPhaseMixtureThermo \
+    -I$(FOAM_SOLVERS)/multiphase/compressibleInterFoam/VoFphaseCompressibleTurbulenceModels \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/surfMesh/lnInclude \
+    -I$(LIB_SRC)/meshTools/lnInclude \
+    -I$(LIB_SRC)/dynamicMesh/lnInclude \
+    -I$(LIB_SRC)/dynamicFvMesh/lnInclude \
+    -I$(LIB_SRC)/transportModels/compressible/lnInclude \
+    -I$(LIB_SRC)/thermophysicalModels/basic/lnInclude \
+    -I$(LIB_SRC)/transportModels/twoPhaseMixture/lnInclude \
+    -I$(LIB_SRC)/transportModels/interfaceProperties/lnInclude \
+    -I$(LIB_SRC)/TurbulenceModels/turbulenceModels/lnInclude \
+    -I$(LIB_SRC)/TurbulenceModels/compressible/lnInclude \
+    -I$(LIB_SRC)/TurbulenceModels/phaseCompressible/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude
+
+EXE_LIBS = \
+    -lfiniteVolume \
+    -lfvOptions \
+    -lsurfMesh \
+    -lmeshTools \
+    -ldynamicMesh \
+    -ldynamicFvMesh \
+    -ltwoPhaseMixtureThermo \
+    -ltwoPhaseSurfaceTension \
+    -lcompressibleTransportModels \
+    -lfluidThermophysicalModels \
+    -lspecie \
+    -ltwoPhaseMixture \
+    -ltwoPhaseProperties \
+    -linterfaceProperties \
+    -lturbulenceModels \
+    -lcompressibleTurbulenceModels \
+    -lVoFphaseCompressibleTurbulenceModels \
+    -lgeometricVoF
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/alphaControls.H b/applications/solvers/multiphase/compressibleInterIsoFoam/alphaControls.H
new file mode 100644
index 0000000000000000000000000000000000000000..2e94f34d752b7465f8eade4425fb76d9d84ab880
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/alphaControls.H
@@ -0,0 +1,3 @@
+const dictionary& alphaControls = mesh.solverDict(alpha1.name());
+
+label nAlphaSubCycles(alphaControls.get<label>("nAlphaSubCycles"));
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/alphaEqn.H b/applications/solvers/multiphase/compressibleInterIsoFoam/alphaEqn.H
new file mode 100644
index 0000000000000000000000000000000000000000..5ded2e30c0f130884b2b63a3b2f4be693ca46fc5
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/alphaEqn.H
@@ -0,0 +1,15 @@
+// Update alpha1
+#include "alphaSuSp.H"
+advector.advect(Sp,(Su + divU*min(alpha1(), scalar(1)))());
+
+// Update rhoPhi
+rhoPhi = advector.getRhoPhi(rho1, rho2);
+alphaPhi10 = advector.alphaPhi();
+
+alpha2 = 1.0 - alpha1;
+
+Info<< "Phase-1 volume fraction = "
+    << alpha1.weightedAverage(mesh.Vsc()).value()
+    << "  Min(" << alpha1.name() << ") = " << min(alpha1).value()
+    << "  Max(" << alpha1.name() << ") - 1 = " << max(alpha1).value() - 1
+    << endl;
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/alphaSuSp.H b/applications/solvers/multiphase/compressibleInterIsoFoam/alphaSuSp.H
new file mode 100644
index 0000000000000000000000000000000000000000..65c5750ff94f1acf7549bd16e29b171ff6f308d4
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/alphaSuSp.H
@@ -0,0 +1,43 @@
+volScalarField::Internal Sp
+(
+    IOobject
+    (
+        "Sp",
+        runTime.timeName(),
+        mesh
+    ),
+    mesh,
+    dimensionedScalar(dgdt.dimensions(), Zero)
+);
+
+volScalarField::Internal Su
+(
+    IOobject
+    (
+        "Su",
+        runTime.timeName(),
+        mesh
+    ),
+    mesh,
+    dimensionedScalar(dgdt.dimensions(), Zero)
+);
+
+forAll(dgdt, celli)
+{
+    if (dgdt[celli] > 0.0)
+    {
+        Sp[celli] -= dgdt[celli]/max(1.0 - alpha1[celli], 1e-4);
+        Su[celli] += dgdt[celli]/max(1.0 - alpha1[celli], 1e-4);
+    }
+    else if (dgdt[celli] < 0.0)
+    {
+        Sp[celli] += dgdt[celli]/max(alpha1[celli], 1e-4);
+    }
+}
+
+volScalarField::Internal divU
+(
+    mesh.moving()
+  ? fvc::div(phi + mesh.phi())
+  : fvc::div(phi)
+);
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/compressibleAlphaEqnSubCycle.H b/applications/solvers/multiphase/compressibleInterIsoFoam/compressibleAlphaEqnSubCycle.H
new file mode 100644
index 0000000000000000000000000000000000000000..5fda0912c58c090016a887d6f67090a517c7b44e
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/compressibleAlphaEqnSubCycle.H
@@ -0,0 +1,70 @@
+if (pimple.nCorrPIMPLE() > 1)
+{
+    if (!pimple.firstIter())
+    {
+        // Resetting alpha1 to value before advection in first PIMPLE
+        // iteration.
+        alpha1 = alpha1.oldTime();
+    }
+}
+tmp<surfaceScalarField> talphaPhi1(alphaPhi10);
+
+if (nAlphaSubCycles > 1)
+{
+    dimensionedScalar totalDeltaT = runTime.deltaT();
+
+    talphaPhi1 = new surfaceScalarField
+    (
+        IOobject
+        (
+            "alphaPhi1",
+            runTime.timeName(),
+            mesh
+        ),
+        mesh,
+        dimensionedScalar(alphaPhi10.dimensions(), Zero)
+    );
+
+    surfaceScalarField rhoPhiSum
+    (
+        IOobject
+        (
+            "rhoPhiSum",
+            runTime.timeName(),
+            mesh
+        ),
+        mesh,
+        dimensionedScalar(rhoPhi.dimensions(), Zero)
+    );
+
+    for
+    (
+        subCycle<volScalarField> alphaSubCycle(alpha1, nAlphaSubCycles);
+        !(++alphaSubCycle).end();
+    )
+    {
+        #include "alphaEqn.H"
+        talphaPhi1.ref() += (runTime.deltaT()/totalDeltaT)*alphaPhi10;
+        rhoPhiSum += (runTime.deltaT()/totalDeltaT)*rhoPhi;
+    }
+
+    rhoPhi = rhoPhiSum;
+}
+else
+{
+    #include "alphaEqn.H"
+}
+
+rho == alpha1*rho1 + alpha2*rho2;
+
+const surfaceScalarField& alphaPhi1 = talphaPhi1();
+surfaceScalarField alphaPhi2("alphaPhi2", phi - alphaPhi1);
+
+volScalarField::Internal contErr
+(
+    (
+        fvc::ddt(rho) + fvc::div(rhoPhi)
+      - (fvOptions(alpha1, mixture.thermo1().rho())&rho1)
+      - (fvOptions(alpha2, mixture.thermo2().rho())&rho2)
+    )()
+);
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/compressibleInterIsoFoam.C b/applications/solvers/multiphase/compressibleInterIsoFoam/compressibleInterIsoFoam.C
new file mode 100644
index 0000000000000000000000000000000000000000..59edb5702a757fa1ca805d685db408038b8f3fdd
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/compressibleInterIsoFoam.C
@@ -0,0 +1,203 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 OpenCFD Ltd.
+    Copyright (C) 2020 Johan Roenby
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Application
+    compressibleInterFlow
+
+Description
+    Solver derived from interFoam for two compressible, immiscible
+    fluids using the isoAdvector phase-fraction based interface capturing
+    approach, with optional mesh motion and mesh topology changes including
+    adaptive re-meshing.
+
+    Reference:
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+    \endverbatim
+
+\*---------------------------------------------------------------------------*/
+
+#include "fvCFD.H"
+#include "dynamicFvMesh.H"
+#include "CMULES.H"
+#include "EulerDdtScheme.H"
+#include "localEulerDdtScheme.H"
+#include "CrankNicolsonDdtScheme.H"
+#include "subCycle.H"
+#include "compressibleInterPhaseTransportModel.H"
+#include "pimpleControl.H"
+#include "fvOptions.H"
+#include "CorrectPhi.H"
+#include "fvcSmooth.H"
+#include "dynamicRefineFvMesh.H"
+#include "isoAdvection.H"
+#include "twoPhaseMixtureThermo.H"
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+int main(int argc, char *argv[])
+{
+    argList::addNote
+    (
+        "Solver for two compressible, non-isothermal immiscible fluids"
+        " using VOF phase-fraction based interface capturing.\n"
+        "With optional mesh motion and mesh topology changes including"
+        " adaptive re-meshing."
+    );
+
+    #include "postProcess.H"
+
+    #include "setRootCaseLists.H"
+    #include "createTime.H"
+    #include "createDynamicFvMesh.H"
+    #include "initContinuityErrs.H"
+    #include "createDyMControls.H"
+    #include "createFields.H"
+    #include "createUf.H"
+    #include "CourantNo.H"
+    #include "setInitialDeltaT.H"
+
+    volScalarField& p = mixture.p();
+    volScalarField& T = mixture.T();
+    const volScalarField& psi1 = mixture.thermo1().psi();
+    const volScalarField& psi2 = mixture.thermo2().psi();
+
+    // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+    Info<< "\nStarting time loop\n" << endl;
+
+    while (runTime.run())
+    {
+        #include "readDyMControls.H"
+
+        // Store divU and divUp from the previous mesh so that it can be mapped
+        // and used in correctPhi to ensure the corrected phi has the
+        // same divergence
+        volScalarField divU("divU0", fvc::div(fvc::absolute(phi, U)));
+
+        #include "CourantNo.H"
+        #include "alphaCourantNo.H"
+        #include "setDeltaT.H"
+
+
+        ++runTime;
+
+        Info<< "Time = " << runTime.timeName() << nl << endl;
+
+        // --- Pressure-velocity PIMPLE corrector loop
+        while (pimple.loop())
+        {
+            if (pimple.firstIter() || moveMeshOuterCorrectors)
+            {
+                scalar timeBeforeMeshUpdate = runTime.elapsedCpuTime();
+
+                if (isA<dynamicRefineFvMesh>(mesh))
+                {
+                    advector.surf().reconstruct();
+                }
+
+                mesh.update();
+
+                if (mesh.changing())
+                {
+                    gh = (g & mesh.C()) - ghRef;
+                    ghf = (g & mesh.Cf()) - ghRef;
+
+                    if (isA<dynamicRefineFvMesh>(mesh))
+                    {
+                        advector.surf().mapAlphaField();
+                        alpha2 = 1.0 - alpha1;
+                        alpha2.correctBoundaryConditions();
+                        rho == alpha1*rho1 + alpha2*rho2;
+                        rho.correctBoundaryConditions();
+                        rho.oldTime() = rho;
+                        alpha2.oldTime() = alpha2;
+                    }
+
+                    MRF.update();
+
+                    Info<< "Execution time for mesh.update() = "
+                        << runTime.elapsedCpuTime() - timeBeforeMeshUpdate
+                        << " s" << endl;
+
+                }
+
+                if ((mesh.changing() && correctPhi))
+                {
+                    // Calculate absolute flux from the mapped surface velocity
+                    phi = mesh.Sf() & Uf;
+
+                    #include "correctPhi.H"
+
+                    // Make the fluxes relative to the mesh motion
+                    fvc::makeRelative(phi, U);
+
+                    mixture.correct();
+                }
+
+                if (mesh.changing() && checkMeshCourantNo)
+                {
+                    #include "meshCourantNo.H"
+                }
+            }
+
+            #include "alphaControls.H"
+            #include "compressibleAlphaEqnSubCycle.H"
+
+            turbulence.correctPhasePhi();
+
+            #include "UEqn.H"
+            volScalarField divUp("divUp", fvc::div(fvc::absolute(phi, U), p));
+            #include "TEqn.H"
+
+            // --- Pressure corrector loop
+            while (pimple.correct())
+            {
+                #include "pEqn.H"
+            }
+
+            if (pimple.turbCorr())
+            {
+                turbulence.correct();
+            }
+        }
+
+        runTime.write();
+
+        runTime.printExecutionTime(Info);
+    }
+
+    Info<< "End\n" << endl;
+
+    return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/correctPhi.H b/applications/solvers/multiphase/compressibleInterIsoFoam/correctPhi.H
new file mode 100644
index 0000000000000000000000000000000000000000..ad73a951ff220bfc14c8e9de9afc393515f2fcbd
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/correctPhi.H
@@ -0,0 +1,13 @@
+CorrectPhi
+(
+    U,
+    phi,
+    p,
+    dimensionedScalar("rAUf", dimTime/rho.dimensions(), 1),
+    divU,
+    pimple
+);
+
+//***HGW phi.oldTime() = phi;
+
+#include "continuityErrs.H"
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/createFields.H b/applications/solvers/multiphase/compressibleInterIsoFoam/createFields.H
new file mode 100644
index 0000000000000000000000000000000000000000..4725a8356da967e410e7c38bff04ab96a062c124
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/createFields.H
@@ -0,0 +1,110 @@
+#include "createRDeltaT.H"
+
+Info<< "Reading field p_rgh\n" << endl;
+volScalarField p_rgh
+(
+    IOobject
+    (
+        "p_rgh",
+        runTime.timeName(),
+        mesh,
+        IOobject::MUST_READ,
+        IOobject::AUTO_WRITE
+    ),
+    mesh
+);
+
+Info<< "Reading field U\n" << endl;
+volVectorField U
+(
+    IOobject
+    (
+        "U",
+        runTime.timeName(),
+        mesh,
+        IOobject::MUST_READ,
+        IOobject::AUTO_WRITE
+    ),
+    mesh
+);
+
+#include "createPhi.H"
+
+Info<< "Constructing twoPhaseMixtureThermo\n" << endl;
+twoPhaseMixtureThermo mixture(U, phi);
+
+
+volScalarField& alpha1(mixture.alpha1());
+volScalarField& alpha2(mixture.alpha2());
+
+Info<< "Reading thermophysical properties\n" << endl;
+
+const volScalarField& rho1 = mixture.thermo1().rho();
+const volScalarField& rho2 = mixture.thermo2().rho();
+
+volScalarField rho
+(
+    IOobject
+    (
+        "rho",
+        runTime.timeName(),
+        mesh,
+        IOobject::READ_IF_PRESENT,
+        IOobject::AUTO_WRITE
+    ),
+    alpha1*rho1 + alpha2*rho2
+);
+
+
+dimensionedScalar pMin
+(
+    "pMin",
+    dimPressure,
+    mixture
+);
+
+mesh.setFluxRequired(p_rgh.name());
+mesh.setFluxRequired(alpha1.name());
+
+
+#include "readGravitationalAcceleration.H"
+#include "readhRef.H"
+#include "gh.H"
+
+
+// Mass flux
+// Initialisation does not matter because rhoPhi is reset after the
+// alpha1 solution before it is used in the U equation.
+surfaceScalarField rhoPhi
+(
+    IOobject
+    (
+        "rhoPhi",
+        runTime.timeName(),
+        mesh,
+        IOobject::NO_READ,
+        IOobject::NO_WRITE
+    ),
+    fvc::interpolate(rho)*phi
+);
+
+volScalarField dgdt(alpha1*fvc::div(phi));
+
+#include "createAlphaFluxes.H"
+
+Foam::isoAdvection advector(alpha1,phi,U);
+// Construct compressible turbulence model
+compressibleInterPhaseTransportModel turbulence
+(
+    rho,
+    U,
+    phi,
+    rhoPhi,
+    alphaPhi10,
+    mixture
+);
+
+#include "createK.H"
+
+#include "createMRF.H"
+#include "createFvOptions.H"
diff --git a/applications/solvers/multiphase/compressibleInterIsoFoam/pEqn.H b/applications/solvers/multiphase/compressibleInterIsoFoam/pEqn.H
new file mode 100644
index 0000000000000000000000000000000000000000..f3fc5b546c46cb659cac43eddbc7601613202cb4
--- /dev/null
+++ b/applications/solvers/multiphase/compressibleInterIsoFoam/pEqn.H
@@ -0,0 +1,169 @@
+{
+    volScalarField rAU("rAU", 1.0/UEqn.A());
+    surfaceScalarField rAUf("rAUf", fvc::interpolate(rAU));
+    volVectorField HbyA(constrainHbyA(rAU*UEqn.H(), U, p_rgh));
+    surfaceScalarField phiHbyA
+    (
+        "phiHbyA",
+        fvc::flux(HbyA)
+      + MRF.zeroFilter(fvc::interpolate(rho*rAU)*fvc::ddtCorr(U, Uf))
+    );
+    MRF.makeRelative(phiHbyA);
+
+    surfaceScalarField phig
+    (
+        (
+            mixture.surfaceTensionForce()
+          - ghf*fvc::snGrad(rho)
+        )*rAUf*mesh.magSf()
+    );
+
+    phiHbyA += phig;
+
+    // Update the pressure BCs to ensure flux consistency
+    constrainPressure(p_rgh, U, phiHbyA, rAUf, MRF);
+
+    // Make the fluxes relative to the mesh motion
+    fvc::makeRelative(phiHbyA, U);
+
+    tmp<fvScalarMatrix> p_rghEqnComp1;
+    tmp<fvScalarMatrix> p_rghEqnComp2;
+
+    if (pimple.transonic())
+    {
+        #include "rhofs.H"
+
+        surfaceScalarField phid1("phid1", fvc::interpolate(psi1)*phi);
+        surfaceScalarField phid2("phid2", fvc::interpolate(psi2)*phi);
+
+        p_rghEqnComp1 =
+            (
+                (
+                    fvc::ddt(alpha1, rho1) + fvc::div(alphaPhi1*rho1f)
+                  - (fvOptions(alpha1, mixture.thermo1().rho())&rho1)
+                )/rho1
+              - fvc::ddt(alpha1) - fvc::div(alphaPhi1)
+              + (alpha1/rho1)
+               *correction
+                (
+                    psi1*fvm::ddt(p_rgh)
+                  + fvm::div(phid1, p_rgh) - fvm::Sp(fvc::div(phid1), p_rgh)
+                )
+            );
+        p_rghEqnComp1.ref().relax();
+
+        p_rghEqnComp2 =
+            (
+               (
+                   fvc::ddt(alpha2, rho2) + fvc::div(alphaPhi2*rho2f)
+                 - (fvOptions(alpha2, mixture.thermo2().rho())&rho2)
+               )/rho2
+             - fvc::ddt(alpha2) - fvc::div(alphaPhi2)
+             + (alpha2/rho2)
+              *correction
+               (
+                   psi2*fvm::ddt(p_rgh)
+                 + fvm::div(phid2, p_rgh) - fvm::Sp(fvc::div(phid2), p_rgh)
+               )
+           );
+        p_rghEqnComp2.ref().relax();
+    }
+    else
+    {
+        #include "rhofs.H"
+
+        p_rghEqnComp1 =
+            pos(alpha1)
+           *(
+                (
+                    fvc::ddt(alpha1, rho1) + fvc::div(alphaPhi1*rho1f)
+                  - (fvOptions(alpha1, mixture.thermo1().rho())&rho1)
+                )/rho1
+              - fvc::ddt(alpha1) - fvc::div(alphaPhi1)
+              + (alpha1*psi1/rho1)*correction(fvm::ddt(p_rgh))
+            );
+
+        p_rghEqnComp2 =
+            pos(alpha2)
+           *(
+               (
+                   fvc::ddt(alpha2, rho2) + fvc::div(alphaPhi2*rho2f)
+                 - (fvOptions(alpha2, mixture.thermo2().rho())&rho2)
+               )/rho2
+             - fvc::ddt(alpha2) - fvc::div(alphaPhi2)
+             + (alpha2*psi2/rho2)*correction(fvm::ddt(p_rgh))
+            );
+    }
+
+    if (mesh.moving())
+    {
+        p_rghEqnComp1.ref() += fvc::div(mesh.phi())*alpha1;
+        p_rghEqnComp2.ref() += fvc::div(mesh.phi())*alpha2;
+    }
+
+    p_rghEqnComp1.ref() *= pos(alpha1);
+    p_rghEqnComp2.ref() *= pos(alpha2);
+
+    if (pimple.transonic())
+    {
+        p_rghEqnComp1.ref().relax();
+        p_rghEqnComp2.ref().relax();
+    }
+
+    // Cache p_rgh prior to solve for density update
+    volScalarField p_rgh_0(p_rgh);
+
+    while (pimple.correctNonOrthogonal())
+    {
+        fvScalarMatrix p_rghEqnIncomp
+        (
+            fvc::div(phiHbyA)
+          - fvm::laplacian(rAUf, p_rgh)
+        );
+
+         solve
+         (
+             p_rghEqnComp1() + p_rghEqnComp2() + p_rghEqnIncomp,
+             mesh.solver(p_rgh.select(pimple.finalInnerIter()))
+         );
+
+        if (pimple.finalNonOrthogonalIter())
+        {
+            p = max(p_rgh + (alpha1*rho1 + alpha2*rho2)*gh, pMin);
+            p_rgh = p - (alpha1*rho1 + alpha2*rho2)*gh;
+
+            dgdt =
+            (
+                alpha1*(p_rghEqnComp2 & p_rgh)
+              - alpha2*(p_rghEqnComp1 & p_rgh)
+            );
+
+            phi = phiHbyA + p_rghEqnIncomp.flux();
+
+            U = HbyA
+              + rAU*fvc::reconstruct((phig + p_rghEqnIncomp.flux())/rAUf);
+            U.correctBoundaryConditions();
+            fvOptions.correct(U);
+        }
+    }
+
+    // Correct Uf if the mesh is moving
+    {
+        Uf = fvc::interpolate(U);
+        surfaceVectorField n(mesh.Sf()/mesh.magSf());
+        Uf += n*(fvc::absolute(phi, U)/mesh.magSf() - (n & Uf));
+    }
+
+
+    // Update densities from change in p_rgh
+    mixture.thermo1().correctRho(psi1*(p_rgh - p_rgh_0));
+    mixture.thermo2().correctRho(psi2*(p_rgh - p_rgh_0));
+
+    rho = alpha1*rho1 + alpha2*rho2;
+
+    // Correct p_rgh for consistency with p and the updated densities
+    p_rgh = p - rho*gh;
+    p_rgh.correctBoundaryConditions();
+
+    K = 0.5*magSqr(U);
+}
diff --git a/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/Make/options b/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/Make/options
index 0a7adfbd0409a5342a0f174b97b65cfd1c8386f0..740a55f4a0d7f2473908203fe6e9858c28094895 100644
--- a/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/Make/options
+++ b/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/Make/options
@@ -7,7 +7,8 @@ EXE_INC = \
     -I$(LIB_SRC)/thermophysicalModels/reactionThermo/lnInclude \
     -I$(LIB_SRC)/thermophysicalModels/solidThermo/lnInclude \
     -I$(LIB_SRC)/thermophysicalModels/solidSpecie/lnInclude \
-    -I$(LIB_SRC)/transportModels/compressible/lnInclude
+    -I$(LIB_SRC)/transportModels/compressible/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude
 
 LIB_LIBS = \
     -lfiniteVolume \
@@ -15,4 +16,5 @@ LIB_LIBS = \
     -lfluidThermophysicalModels \
     -lreactionThermophysicalModels \
     -lsolidThermo \
-    -lsolidSpecie
+    -lsolidSpecie \
+    -lgeometricVoF
diff --git a/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/interfaceHeatResistance/interfaceHeatResistance.C b/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/interfaceHeatResistance/interfaceHeatResistance.C
index 32f1145a2d4a33182c110dc09c0ebb601d417e5a..4374ac40a873ba93c6ba142a944bfc410278d9dd 100644
--- a/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/interfaceHeatResistance/interfaceHeatResistance.C
+++ b/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/interfaceHeatResistance/interfaceHeatResistance.C
@@ -28,7 +28,7 @@ License
 
 #include "interfaceHeatResistance.H"
 #include "constants.H"
-#include "isoCutCell.H"
+#include "cutCellIso.H"
 #include "volPointInterpolation.H"
 #include "wallPolyPatch.H"
 #include "fvcSmooth.H"
@@ -52,7 +52,7 @@ interfaceHeatResistance<Thermo, OtherThermo>
         volPointInterpolation::New(mesh).interpolate(alpha)
     );
 
-    isoCutCell cutCell(mesh, ap);
+    cutCellIso cutCell(mesh, ap);
 
     forAll(interfaceArea_, celli)
     {
@@ -61,7 +61,7 @@ interfaceHeatResistance<Thermo, OtherThermo>
         if (status == 0) // cell is cut
         {
             interfaceArea_[celli] =
-                mag(cutCell.isoFaceArea())/mesh.V()[celli];
+                mag(cutCell.faceArea())/mesh.V()[celli];
         }
     }
 
diff --git a/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/kineticGasEvaporation/kineticGasEvaporation.C b/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/kineticGasEvaporation/kineticGasEvaporation.C
index 252e9bbc6028c264363cacabba4f05096347a172..3325fa786d7ca042f93626b132d86939e9224ed6 100644
--- a/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/kineticGasEvaporation/kineticGasEvaporation.C
+++ b/applications/solvers/multiphase/icoReactingMultiphaseInterFoam/massTransferModels/kineticGasEvaporation/kineticGasEvaporation.C
@@ -27,7 +27,7 @@ License
 
 #include "kineticGasEvaporation.H"
 #include "constants.H"
-#include "isoCutCell.H"
+#include "cutCellIso.H"
 #include "volPointInterpolation.H"
 #include "wallPolyPatch.H"
 #include "fvcSmooth.H"
@@ -50,7 +50,7 @@ void Foam::meltingEvaporationModels::kineticGasEvaporation<Thermo, OtherThermo>
         volPointInterpolation::New(mesh).interpolate(alpha)
     );
 
-    isoCutCell cutCell(mesh, ap);
+    cutCellIso cutCell(mesh, ap);
 
     forAll(interfaceArea_, celli)
     {
@@ -59,7 +59,7 @@ void Foam::meltingEvaporationModels::kineticGasEvaporation<Thermo, OtherThermo>
         if (status == 0) // cell is cut
         {
             interfaceArea_[celli] =
-                mag(cutCell.isoFaceArea())/mesh.V()[celli];
+                mag(cutCell.faceArea())/mesh.V()[celli];
         }
     }
 
diff --git a/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/Make/options b/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/Make/options
index 4a85a0ae9f3df278ee724f0e46e2e8025c8f6c82..98ce2f94772fc20cbc8f241bb106cb6bfaec799d 100644
--- a/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/Make/options
+++ b/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/Make/options
@@ -1,16 +1,17 @@
-
 EXE_INC = \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
     -I$(LIB_SRC)/thermophysicalModels/basic/lnInclude \
-    -I$(LIB_SRC)/transportModels/twoPhaseMixture/lnInclude \
     -I$(LIB_SRC)/transportModels \
+    -I$(LIB_SRC)/transportModels/twoPhaseMixture/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude \
     -I$(LIB_SRC)/transportModels/interfaceProperties/lnInclude \
-    -I$(LIB_SRC)/transportModels/incompressible/lnInclude \
-    -I$(LIB_SRC)/finiteVolume/lnInclude
+    -I$(LIB_SRC)/transportModels/incompressible/lnInclude
 
 LIB_LIBS = \
+    -lfiniteVolume \
+    -lgeometricVoF \
     -ltwoPhaseMixture \
     -linterfaceProperties \
     -ltwoPhaseProperties \
     -lincompressibleTransportModels \
-    -lfiniteVolume \
     -lfluidThermophysicalModels
diff --git a/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/interfaceHeatResistance/interfaceHeatResistance.C b/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/interfaceHeatResistance/interfaceHeatResistance.C
index 598d66a243e980ef67bc0d950e873f377577ce07..368ee3dfdb9ae94d5ee8921b62df7c35737779f8 100644
--- a/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/interfaceHeatResistance/interfaceHeatResistance.C
+++ b/applications/solvers/multiphase/interCondensatingEvaporatingFoam/temperaturePhaseChangeTwoPhaseMixtures/interfaceHeatResistance/interfaceHeatResistance.C
@@ -29,7 +29,7 @@ License
 #include "interfaceHeatResistance.H"
 #include "addToRunTimeSelectionTable.H"
 #include "twoPhaseMixtureEThermo.H"
-#include "isoCutCell.H"
+#include "cutCellIso.H"
 #include "volPointInterpolation.H"
 #include "calculatedFvPatchFields.H"
 #include "wallPolyPatch.H"
@@ -342,7 +342,7 @@ updateInterface()
         volPointInterpolation::New(mesh_).interpolate(mixture_.alpha1())
     );
 
-    isoCutCell cutCell(mesh_, ap);
+    cutCellIso cutCell(mesh_, ap);
 
     forAll(interfaceArea_, celli)
     {
@@ -351,7 +351,7 @@ updateInterface()
         if (status == 0) // cell is cut
         {
             interfaceArea_[celli] =
-                mag(cutCell.isoFaceArea())/mesh_.V()[celli];
+                mag(cutCell.faceArea())/mesh_.V()[celli];
         }
     }
 
diff --git a/applications/solvers/multiphase/interIsoFoam/Make/options b/applications/solvers/multiphase/interIsoFoam/Make/options
index 30a64e1962a9dd68f4a09377f58fafc9ffb6781c..71e17b49628eb622c95a9a8b5931f7d70f47b7d9 100644
--- a/applications/solvers/multiphase/interIsoFoam/Make/options
+++ b/applications/solvers/multiphase/interIsoFoam/Make/options
@@ -1,19 +1,26 @@
 EXE_INC = \
+    -I../VoF \
+    -I../interFoam \
     -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/surfMesh/lnInclude \
     -I$(LIB_SRC)/meshTools/lnInclude \
     -I$(LIB_SRC)/sampling/lnInclude \
     -I$(LIB_SRC)/dynamicFvMesh/lnInclude \
+    -I$(LIB_SRC)/dynamicMesh/lnInclude \
     -I$(LIB_SRC)/transportModels \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude \
     -I$(LIB_SRC)/transportModels/twoPhaseMixture/lnInclude \
     -I$(LIB_SRC)/transportModels/incompressible/lnInclude \
     -I$(LIB_SRC)/transportModels/interfaceProperties/lnInclude \
     -I$(LIB_SRC)/TurbulenceModels/turbulenceModels/lnInclude \
     -I$(LIB_SRC)/TurbulenceModels/incompressible/lnInclude \
-    -I$(LIB_SRC)/transportModels/immiscibleIncompressibleTwoPhaseMixture/lnInclude
+    -I$(LIB_SRC)/transportModels/immiscibleIncompressibleTwoPhaseMixture/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude
 
 EXE_LIBS = \
     -lfiniteVolume \
     -lfvOptions \
+    -lsurfMesh \
     -lmeshTools \
     -lsampling \
     -ldynamicFvMesh \
@@ -22,4 +29,5 @@ EXE_LIBS = \
     -limmiscibleIncompressibleTwoPhaseMixture \
     -lturbulenceModels \
     -lincompressibleTurbulenceModels \
-    -lwaveModels
+    -lwaveModels \
+    -lgeometricVoF
diff --git a/applications/solvers/multiphase/interIsoFoam/UEqn.H b/applications/solvers/multiphase/interIsoFoam/UEqn.H
deleted file mode 100644
index 77d1dcd83e8c665fa8127bfadb8d59a94222bc61..0000000000000000000000000000000000000000
--- a/applications/solvers/multiphase/interIsoFoam/UEqn.H
+++ /dev/null
@@ -1,33 +0,0 @@
-    MRF.correctBoundaryVelocity(U);
-
-    fvVectorMatrix UEqn
-    (
-        fvm::ddt(rho, U) + fvm::div(rhoPhi, U)
-      + MRF.DDt(rho, U)
-      + turbulence->divDevRhoReff(rho, U)
-     ==
-        fvOptions(rho, U)
-    );
-
-    UEqn.relax();
-
-    fvOptions.constrain(UEqn);
-
-    if (pimple.momentumPredictor())
-    {
-        solve
-        (
-            UEqn
-         ==
-            fvc::reconstruct
-            (
-                (
-                    mixture.surfaceTensionForce()
-                  - ghf*fvc::snGrad(rho)
-                  - fvc::snGrad(p_rgh)
-                ) * mesh.magSf()
-            )
-        );
-
-        fvOptions.correct(U);
-    }
diff --git a/applications/solvers/multiphase/interIsoFoam/alphaEqn.H b/applications/solvers/multiphase/interIsoFoam/alphaEqn.H
index 8de0ac016121dd1c1e1cc8a93d54e2d4f2d96399..b6f8aecb2f8a209141374939784b0d6fbd99b7f7 100644
--- a/applications/solvers/multiphase/interIsoFoam/alphaEqn.H
+++ b/applications/solvers/multiphase/interIsoFoam/alphaEqn.H
@@ -6,7 +6,8 @@
     }
 
     // Updating alpha1
-    advector.advect();
+    #include "alphaSuSp.H"
+    advector.advect(Sp, Su);
 
     // Making U absolute again after advection step
     if (mesh.moving())
diff --git a/applications/solvers/multiphase/interIsoFoam/correctPhi.H b/applications/solvers/multiphase/interIsoFoam/correctPhi.H
deleted file mode 100644
index fcb5020587cb43e4bdf191ee8d64e8981d53b21b..0000000000000000000000000000000000000000
--- a/applications/solvers/multiphase/interIsoFoam/correctPhi.H
+++ /dev/null
@@ -1,11 +0,0 @@
-CorrectPhi
-(
-    U,
-    phi,
-    p_rgh,
-    surfaceScalarField("rAUf", fvc::interpolate(rAU())),
-    geometricZeroField(),
-    pimple
-);
-
-#include "continuityErrs.H"
diff --git a/applications/solvers/multiphase/interIsoFoam/initCorrectPhi.H b/applications/solvers/multiphase/interIsoFoam/initCorrectPhi.H
deleted file mode 100644
index 03eb7fd7fdf55b40f0fddf841c027491901a372b..0000000000000000000000000000000000000000
--- a/applications/solvers/multiphase/interIsoFoam/initCorrectPhi.H
+++ /dev/null
@@ -1,34 +0,0 @@
-tmp<volScalarField> rAU;
-
-if (correctPhi)
-{
-    rAU = new volScalarField
-    (
-        IOobject
-        (
-            "rAU",
-            runTime.timeName(),
-            mesh,
-            IOobject::READ_IF_PRESENT,
-            IOobject::AUTO_WRITE
-        ),
-        mesh,
-        dimensionedScalar("rAU", dimTime/dimDensity, 1)
-    );
-
-    #include "correctPhi.H"
-}
-else
-{
-    CorrectPhi
-    (
-        U,
-        phi,
-        p_rgh,
-        dimensionedScalar("rAUf", dimTime/rho.dimensions(), 1),
-        geometricZeroField(),
-        pimple
-    );
-
-    #include "continuityErrs.H"
-}
diff --git a/applications/solvers/multiphase/interIsoFoam/interIsoFoam.C b/applications/solvers/multiphase/interIsoFoam/interIsoFoam.C
index 8b0523fc040e6ceeb091d9cb587e018dfbe2a261..6a694e4a814a34aefc070066688256af156db9e0 100644
--- a/applications/solvers/multiphase/interIsoFoam/interIsoFoam.C
+++ b/applications/solvers/multiphase/interIsoFoam/interIsoFoam.C
@@ -9,6 +9,7 @@
     Copyright (C) 2016 DHI
     Copyright (C) 2017 OpenCFD Ltd.
     Copyright (C) 2018 Johan Roenby
+    Copyright (C) 2019-2020 DLR
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -63,6 +64,7 @@ Description
 #include "fvOptions.H"
 #include "CorrectPhi.H"
 #include "fvcSmooth.H"
+#include "dynamicRefineFvMesh.H"
 
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
 
@@ -113,14 +115,29 @@ int main(int argc, char *argv[])
         {
             if (pimple.firstIter() || moveMeshOuterCorrectors)
             {
+                if (isA<dynamicRefineFvMesh>(mesh))
+                {
+                    advector.surf().reconstruct();
+                }
+
                 mesh.update();
 
                 if (mesh.changing())
                 {
-
                     gh = (g & mesh.C()) - ghRef;
                     ghf = (g & mesh.Cf()) - ghRef;
 
+                    if (isA<dynamicRefineFvMesh>(mesh))
+                    {
+                        advector.surf().mapAlphaField();
+                        alpha2 = 1.0 - alpha1;
+                        alpha2.correctBoundaryConditions();
+                        rho == alpha1*rho1 + alpha2*rho2;
+                        rho.correctBoundaryConditions();
+                        rho.oldTime() = rho;
+                        alpha2.oldTime() = alpha2;
+                    }
+
                     MRF.update();
 
                     if (correctPhi)
diff --git a/applications/solvers/multiphase/interIsoFoam/pEqn.H b/applications/solvers/multiphase/interIsoFoam/pEqn.H
deleted file mode 100644
index e443f269848af443a24bff674a839ac86e245ad3..0000000000000000000000000000000000000000
--- a/applications/solvers/multiphase/interIsoFoam/pEqn.H
+++ /dev/null
@@ -1,89 +0,0 @@
-{
-    if (correctPhi)
-    {
-        rAU.ref() = 1.0/UEqn.A();
-    }
-    else
-    {
-        rAU = 1.0/UEqn.A();
-    }
-
-    surfaceScalarField rAUf("rAUf", fvc::interpolate(rAU()));
-    volVectorField HbyA(constrainHbyA(rAU()*UEqn.H(), U, p_rgh));
-    surfaceScalarField phiHbyA
-    (
-        "phiHbyA",
-        fvc::flux(HbyA)
-      + MRF.zeroFilter(fvc::interpolate(rho*rAU())*fvc::ddtCorr(U, phi, Uf))
-    );
-    MRF.makeRelative(phiHbyA);
-
-    if (p_rgh.needReference())
-    {
-        fvc::makeRelative(phiHbyA, U);
-        adjustPhi(phiHbyA, U, p_rgh);
-        fvc::makeAbsolute(phiHbyA, U);
-    }
-
-    surfaceScalarField phig
-    (
-        (
-            mixture.surfaceTensionForce()
-          - ghf*fvc::snGrad(rho)
-        )*rAUf*mesh.magSf()
-    );
-
-    phiHbyA += phig;
-
-    // Update the pressure BCs to ensure flux consistency
-    constrainPressure(p_rgh, U, phiHbyA, rAUf, MRF);
-
-    while (pimple.correctNonOrthogonal())
-    {
-        fvScalarMatrix p_rghEqn
-        (
-            fvm::laplacian(rAUf, p_rgh) == fvc::div(phiHbyA)
-        );
-
-        p_rghEqn.setReference(pRefCell, getRefCellValue(p_rgh, pRefCell));
-
-        p_rghEqn.solve(mesh.solver(p_rgh.select(pimple.finalInnerIter())));
-
-        if (pimple.finalNonOrthogonalIter())
-        {
-            phi = phiHbyA - p_rghEqn.flux();
-
-            p_rgh.relax();
-
-            U = HbyA + rAU()*fvc::reconstruct((phig - p_rghEqn.flux())/rAUf);
-            U.correctBoundaryConditions();
-            fvOptions.correct(U);
-        }
-    }
-
-    #include "continuityErrs.H"
-
-    // Correct Uf if the mesh is moving
-    fvc::correctUf(Uf, U, phi);
-
-    // Make the fluxes relative to the mesh motion
-    fvc::makeRelative(phi, U);
-
-    p == p_rgh + rho*gh;
-
-    if (p_rgh.needReference())
-    {
-        p += dimensionedScalar
-        (
-            "p",
-            p.dimensions(),
-            pRefValue - getRefCellValue(p, pRefCell)
-        );
-        p_rgh = p - rho*gh;
-    }
-
-    if (!correctPhi)
-    {
-        rAU.clear();
-    }
-}
diff --git a/applications/solvers/multiphase/interIsoFoam/rhofs.H b/applications/solvers/multiphase/interIsoFoam/rhofs.H
deleted file mode 100644
index 5949bf1e0a60d21934f09e1fbe8780c5cf7e43d5..0000000000000000000000000000000000000000
--- a/applications/solvers/multiphase/interIsoFoam/rhofs.H
+++ /dev/null
@@ -1,2 +0,0 @@
-const dimensionedScalar& rho1f(rho1);
-const dimensionedScalar& rho2f(rho2);
diff --git a/applications/test/leastSquareGrad/Make/files b/applications/test/leastSquareGrad/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..f72004ebd5e4bac4db15dd26125b8719420281e3
--- /dev/null
+++ b/applications/test/leastSquareGrad/Make/files
@@ -0,0 +1,3 @@
+Test-leastSquareGrad.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-leastSquareGrad
diff --git a/applications/test/leastSquareGrad/Make/options b/applications/test/leastSquareGrad/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..b4ad3d8bdff2f2475467775f28a6c62effa80575
--- /dev/null
+++ b/applications/test/leastSquareGrad/Make/options
@@ -0,0 +1,9 @@
+EXE_INC = \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/meshTools/lnInclude \
+    -I$(LIB_SRC)/sampling/lnInclude
+
+EXE_LIBS = \
+    -lfiniteVolume \
+    -lmeshTools \
+    -lsampling
diff --git a/applications/test/leastSquareGrad/Test-leastSquareGrad.C b/applications/test/leastSquareGrad/Test-leastSquareGrad.C
new file mode 100644
index 0000000000000000000000000000000000000000..ae68fc24cc16fd6f24b2fe00eaa9286cd7b982a4
--- /dev/null
+++ b/applications/test/leastSquareGrad/Test-leastSquareGrad.C
@@ -0,0 +1,101 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Application
+    Test-leastSquareGrad
+
+Description
+
+\*---------------------------------------------------------------------------*/
+
+#include "fvCFD.H"
+#include "leastSquareGrad.H"
+#include "labelVector.H"
+#include "Field.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+int main(int argc, char *argv[])
+{
+    labelVector geomDim(1,1,-1);
+
+    leastSquareGrad<scalar> lsGrad("polyDegree1", geomDim);
+
+    List<vector> pos
+    ({
+        {0,0,0},
+        {1,0,0},
+        {-1,0,0},
+        {0,1,0},
+        {0,-1,0},
+        // {1,1,0}
+    });
+
+    List<scalar> values
+    ({
+        0, 1, -1, 1, -1
+        //, 2
+    });
+
+
+    Map<List<vector>> posMap;
+
+    posMap.insert(0, pos);
+    posMap.insert(1, pos);
+    posMap.insert(2, pos);
+
+    Map<List<scalar>> valMap;
+
+    valMap.insert(0, values);
+    valMap.insert(1, values);
+    valMap.insert(2, values);
+
+    Info<< lsGrad.grad(posMap, valMap) << nl;
+
+
+    leastSquareGrad<vector> lsGradVec("polyDegree1", geomDim);
+
+    List<vector> valuesVec
+    ({
+        {0,0,0},
+        {1,0,0},
+        {-1,0,0},
+        {1,0,0},
+        {-1,0,0}
+    });
+
+    Map<List<vector>> valMapVec;
+
+    valMapVec.insert(0, valuesVec);
+    valMapVec.insert(1, valuesVec);
+    valMapVec.insert(2, valuesVec);
+
+    Info<< lsGradVec.grad(posMap,valMapVec) << nl;
+
+    return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/multiDimPolyFitter/Make/files b/applications/test/multiDimPolyFitter/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..d5b957d1bdc74e9947ba45b84e62929d9923ec6f
--- /dev/null
+++ b/applications/test/multiDimPolyFitter/Make/files
@@ -0,0 +1,3 @@
+Test-multiDimPolyFitter.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-multiDimPolyFitter
diff --git a/applications/test/multiDimPolyFitter/Make/options b/applications/test/multiDimPolyFitter/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..b4ad3d8bdff2f2475467775f28a6c62effa80575
--- /dev/null
+++ b/applications/test/multiDimPolyFitter/Make/options
@@ -0,0 +1,9 @@
+EXE_INC = \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/meshTools/lnInclude \
+    -I$(LIB_SRC)/sampling/lnInclude
+
+EXE_LIBS = \
+    -lfiniteVolume \
+    -lmeshTools \
+    -lsampling
diff --git a/applications/test/multiDimPolyFitter/Test-multiDimPolyFitter.C b/applications/test/multiDimPolyFitter/Test-multiDimPolyFitter.C
new file mode 100644
index 0000000000000000000000000000000000000000..77de98ab181e7ff1f4b12c1755caf262950a40ba
--- /dev/null
+++ b/applications/test/multiDimPolyFitter/Test-multiDimPolyFitter.C
@@ -0,0 +1,113 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Application
+    Test-multiDimPolyFitter
+
+Description
+
+\*---------------------------------------------------------------------------*/
+
+#include "fvCFD.H"
+#include "multiDimPolyFitter.H"
+#include "labelVector.H"
+#include "Field.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+int main(int argc, char *argv[])
+{
+    labelVector test(1,-1,-1);
+
+    autoPtr<multiDimPolyFunctions> polyFunc
+        = multiDimPolyFunctions::New("polyDegree1", test);
+
+    vector vec(1,2,3);
+
+    Info<< "polyFunc" << nl
+        << "    nTerms " << polyFunc->nTerms() << nl
+        << "    coeffs " << polyFunc->coeffs() << nl
+        << "    termValues " << polyFunc->termValues(vec) << nl;
+
+    multiDimPolyFitter<scalar> polyFitter("polyDegree1",test);
+
+    List<vector> pos
+    ({
+        {0,0,0},
+        {1,0,0},
+        {-1,0,0}
+    });
+
+    List<scalar> values
+    ({
+        1, 2, 0
+    });
+
+    Info<< "pos " << pos << nl
+        << "values " << values  << nl;
+
+    scalarField fitData = polyFitter.fitData(pos, values);
+
+    Info<< "fitData " << fitData  << nl;
+
+    autoPtr<multiDimPolyFunctions> polyFuncDeg2
+        = multiDimPolyFunctions::New("polyDegree2", labelVector(1,1,-1));
+
+    //vector vec(1,2,3);
+
+    Info<< "polyFunc" << nl
+        << "    nTerms" << polyFuncDeg2->nTerms()  << nl
+        // << "    coeffs " << polyFunc->coeffs()  << nl
+        << "    termValues " << polyFuncDeg2->termValues(vector(1,1,0)) << nl;
+
+    List<vector> pos2
+    ({
+        {0,0,0},
+        {1,0,0},
+        {-1,0,0},
+        {0,1,0},
+        {0,-1,0},
+        {1,1,0}
+    });
+
+    List<scalar> values2
+    ({
+        0, 1, 1, 1, 1, 2
+    });
+
+    multiDimPolyFitter<scalar> polyFitter2
+    {
+        "polyDegree2", labelVector(1,1,-1)
+    };
+
+    scalarField fitData2 = polyFitter2.fitData(pos2, values2);
+
+    Info<< "fitData " << fitData2  << nl;
+
+    return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/Make/files b/applications/test/reconstructedDistanceFunction/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..5ebed6989897e2d321e32ebaf6164571d41d56c3
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/Make/files
@@ -0,0 +1,3 @@
+Test-reconstructedDistanceFunction.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-reconstructedDistanceFunction
diff --git a/applications/test/reconstructedDistanceFunction/Make/options b/applications/test/reconstructedDistanceFunction/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..c2d01bb839c31916921da3f0af09d140daf1aa42
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/Make/options
@@ -0,0 +1,11 @@
+EXE_INC = \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/meshTools/lnInclude \
+    -I$(LIB_SRC)/sampling/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude
+
+EXE_LIBS = \
+    -lfiniteVolume \
+    -lmeshTools \
+    -lsampling \
+    -lgeometricVoF
diff --git a/applications/test/reconstructedDistanceFunction/Test-reconstructedDistanceFunction.C b/applications/test/reconstructedDistanceFunction/Test-reconstructedDistanceFunction.C
new file mode 100755
index 0000000000000000000000000000000000000000..612419f6fd56842f1ca2291b63f5456730a40526
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/Test-reconstructedDistanceFunction.C
@@ -0,0 +1,139 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           |  www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Application
+
+Description
+
+\*---------------------------------------------------------------------------*/
+
+#include "fvCFD.H"
+#include "reconstructionSchemes.H"
+#include "reconstructedDistanceFunction.H"
+#include "Field.H"
+#include "DynamicField.H"
+#include "zoneDistribute.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+int main(int argc, char *argv[])
+{
+    #include "setRootCase.H"
+    #include "createTime.H"
+    #include "createMesh.H"
+
+    Info<< "Reading field alpha1\n" << endl;
+
+    volScalarField alpha1
+    (
+        IOobject
+        (
+            "alpha1",
+            runTime.timeName(),
+            mesh,
+            IOobject::MUST_READ,
+            IOobject::AUTO_WRITE
+        ),
+        mesh
+    );
+
+    Info<< "Reading field U\n" << endl;
+    volVectorField U
+    (
+        IOobject
+        (
+            "U",
+            runTime.timeName(),
+            mesh,
+            IOobject::MUST_READ,
+            IOobject::AUTO_WRITE
+        ),
+        mesh
+    );
+
+    Info<< "create field phi\n" << endl;
+    surfaceScalarField phi = fvc::interpolate(U) & mesh.Sf();
+
+    dictionary dict = mesh.solverDict(alpha1.name());
+
+    autoPtr<reconstructionSchemes> surf =
+        reconstructionSchemes::New(alpha1,phi,U,dict);
+
+    ++runTime;
+
+    const volVectorField& centre = surf->centre();
+    const volVectorField& normal = surf->normal();
+
+
+    //pointField centres(0);
+    //vectorField normals(0);
+    DynamicField<point> centres(1000);
+    DynamicField<vector> normals(1000);
+
+    surf->reconstruct();
+
+    zoneDistribute exchangeFields_(mesh);
+
+    exchangeFields_.setUpCommforZone(surf->interfaceCell());
+
+    Map<Field<vector>> mapCentres =
+        exchangeFields_.getFields(surf->interfaceCell(),centre);
+
+    Map<Field<vector>> mapNormal =
+        exchangeFields_.getFields(surf->interfaceCell(),normal);
+
+    forAll(surf->centre(),celli)
+    {
+        if (surf->interfaceCell()[celli])
+        {
+            centres.append(surf->centre()[celli]);
+            normals.append(surf->normal()[celli]);
+        }
+    }
+
+    reconstructedDistanceFunction distFunc(mesh);
+
+    {
+        runTime.cpuTimeIncrement();
+
+        Info<< "Time " << runTime.cpuTimeIncrement()  << endl;
+
+        distFunc.constructRDF
+        (
+            surf->interfaceCell(),
+            surf->centre(),
+            surf->normal(),
+            2,
+            exchangeFields_
+        );
+    }
+
+    runTime.write();
+
+    return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/0.orig/U b/applications/test/reconstructedDistanceFunction/case1/0.orig/U
new file mode 100644
index 0000000000000000000000000000000000000000..e4f09a7872265013c05bfc12b6098bca919d0691
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/0.orig/U
@@ -0,0 +1,39 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volVectorField;
+    location    "0";
+    object      U;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -1 0 0 0 0];
+
+internalField   uniform (0 0 0);
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+    front
+    {
+        type            empty;
+    }
+    back
+    {
+        type            empty;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/0.orig/alpha1 b/applications/test/reconstructedDistanceFunction/case1/0.orig/alpha1
new file mode 100644
index 0000000000000000000000000000000000000000..f0e458d11403adb3b6496f7c6d4deb87247afd3e
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/0.orig/alpha1
@@ -0,0 +1,39 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    location    "0";
+    object      alpha1;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 0 0 0 0];
+
+internalField   uniform 0;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+    front
+    {
+        type            empty;
+    }
+    back
+    {
+        type            empty;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/0.orig/markedCells b/applications/test/reconstructedDistanceFunction/case1/0.orig/markedCells
new file mode 100644
index 0000000000000000000000000000000000000000..853cae3a1610f9d3a3d211c1ca92669dd0c439e8
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/0.orig/markedCells
@@ -0,0 +1,40 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    location    "0";
+    object      markedCells;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 0 0 0 0];
+
+internalField   uniform 0;
+
+boundaryField
+{
+    walls
+    {
+        type            calculated;
+        value           uniform 0;
+    }
+    front
+    {
+        type            empty;
+    }
+    back
+    {
+        type            empty;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/Allclean b/applications/test/reconstructedDistanceFunction/case1/Allclean
new file mode 100755
index 0000000000000000000000000000000000000000..a3bdf96f3e768b7c7bacfecd4f367573ff368e62
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/Allclean
@@ -0,0 +1,9 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/CleanFunctions      # Tutorial clean functions
+#------------------------------------------------------------------------------
+
+cleanCase0
+rm -rf AlphaInit/
+
+#------------------------------------------------------------------------------
diff --git a/applications/test/reconstructedDistanceFunction/case1/Allrun b/applications/test/reconstructedDistanceFunction/case1/Allrun
new file mode 100755
index 0000000000000000000000000000000000000000..404ed9ae3170bdd3ad794cba2d0aec4b1e7c1c37
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/Allrun
@@ -0,0 +1,13 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/RunFunctions        # Tutorial run functions
+#------------------------------------------------------------------------------
+
+restore0Dir
+touch Test-reconDistFunc.foam
+
+runApplication blockMesh
+runApplication setAlphaField
+runApplication Test-reconstructedDistanceFunction
+
+#------------------------------------------------------------------------------
diff --git a/applications/test/reconstructedDistanceFunction/case1/constant/g b/applications/test/reconstructedDistanceFunction/case1/constant/g
new file mode 100644
index 0000000000000000000000000000000000000000..9dc396fe907e3e59d01707c76ff74e0c938664f1
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/constant/g
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       uniformDimensionedVectorField;
+    location    "constant";
+    object      g;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -2 0 0 0 0];
+value           ( 0 -9.81 0 );
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/constant/transportProperties b/applications/test/reconstructedDistanceFunction/case1/constant/transportProperties
new file mode 100644
index 0000000000000000000000000000000000000000..3793e29ae781039ab302ca1bbb212b2f0bd13680
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/constant/transportProperties
@@ -0,0 +1,64 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      transportProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+DT              [ 0 2 -1 0 0 0 0 ] 0;
+
+sigma           [ 1 0 -2 0 0 0 0 ] 0;
+
+phase1
+{
+    transportModel  Newtonian;
+    nu              [ 0 2 -1 0 0 0 0 ] 0;
+    rho             [ 1 -3 0 0 0 0 0 ] 1000;
+    BirdCarreauCoeffs
+    {
+        nu0             [ 0 2 -1 0 0 0 0 ] 0.0142515;
+        nuInf           [ 0 2 -1 0 0 0 0 ] 1e-06;
+        k               [ 0 0 1 0 0 0 0 ] 99.6;
+        n               [ 0 0 0 0 0 0 0 ] 0.1003;
+    }
+    CrossPowerLawCoeffs
+    {
+        nu0             [ 0 2 -1 0 0 0 0 ] 1e-06;
+        nuInf           [ 0 2 -1 0 0 0 0 ] 1e-06;
+        m               [ 0 0 1 0 0 0 0 ] 1;
+        n               [ 0 0 0 0 0 0 0 ] 0;
+    }
+}
+
+phase2
+{
+    transportModel  Newtonian;
+    nu              [ 0 2 -1 0 0 0 0 ] 0;
+    rho             [ 1 -3 0 0 0 0 0 ] 1;
+    BirdCarreauCoeffs
+    {
+        nu0             [ 0 2 -1 0 0 0 0 ] 0.0142515;
+        nuInf           [ 0 2 -1 0 0 0 0 ] 1e-06;
+        k               [ 0 0 1 0 0 0 0 ] 99.6;
+        n               [ 0 0 0 0 0 0 0 ] 0.1003;
+    }
+    CrossPowerLawCoeffs
+    {
+        nu0             [ 0 2 -1 0 0 0 0 ] 1e-06;
+        nuInf           [ 0 2 -1 0 0 0 0 ] 1e-06;
+        m               [ 0 0 1 0 0 0 0 ] 1;
+        n               [ 0 0 0 0 0 0 0 ] 0;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/constant/turbulenceProperties b/applications/test/reconstructedDistanceFunction/case1/constant/turbulenceProperties
new file mode 100644
index 0000000000000000000000000000000000000000..7fcefa3b6020ad30b27b2ce2ffdbc88bcf8a80cd
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/constant/turbulenceProperties
@@ -0,0 +1,20 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  laminar;
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/blockMeshDict b/applications/test/reconstructedDistanceFunction/case1/system/blockMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..01380af7b406e57716d9f2dbd3d43aeed7f902b0
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/blockMeshDict
@@ -0,0 +1,89 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      blockMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+scale   1;
+
+L       1;
+n       3;
+
+y1      0;
+y2      1;
+
+H       0.1;
+
+
+vertices
+(
+    (0 $y1 0)
+    ($L $y1 0)
+    ($L $y2 0)
+    (0 $y2 0)
+    (0 $y1 $H)
+    ($L $y1 $H)
+    ($L $y2 $H)
+    (0 $y2 $H)
+);
+
+blocks
+(
+    hex (0 1 2 3 4 5 6 7) (100 100 1) simpleGrading (1 1 1)
+);
+
+edges
+(
+);
+
+boundary
+(
+    walls
+    {
+        type patch;
+        faces
+        (
+            (4 5 6 7)
+            (0 4 7 3)
+            (1 2 6 5)
+            (0 3 2 1)
+            // (2 3 7 6)
+            // (0 1 5 4)
+        );
+    }
+
+    front
+    {
+        type empty;
+        faces
+        (
+            (2 3 7 6)
+        );
+    }
+
+    back
+    {
+        type empty;
+        faces
+        (
+            (0 1 5 4)
+        );
+    }
+
+);
+
+mergePatchPairs
+(
+);
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/changeDictionaryDict b/applications/test/reconstructedDistanceFunction/case1/system/changeDictionaryDict
new file mode 100644
index 0000000000000000000000000000000000000000..4d3e9219fbe5e49f8a4457681dc5f8d6c652f842
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/changeDictionaryDict
@@ -0,0 +1,30 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      changeDictionaryDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+boundary
+{
+    front
+    {
+        type            empty;
+    }
+
+    back
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/controlDict b/applications/test/reconstructedDistanceFunction/case1/system/controlDict
new file mode 100644
index 0000000000000000000000000000000000000000..be6485fa83170d9662fd97f5727a696ab0eb5250
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/controlDict
@@ -0,0 +1,59 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version         2.0;
+    format          ascii;
+    class           dictionary;
+    location        "system";
+    object          controlDict;
+}
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+application     Test-reconstructedDistanceFunction;
+
+startFrom       startTime;
+
+startTime       0.0;
+
+stopAt          writeNow;
+
+endTime         4;
+
+writeControl    adjustableRunTime;
+
+writeInterval   0.1;
+
+deltaT          1e-3;
+
+purgeWrite      0;
+
+writeFormat     ascii;
+
+writePrecision  14;
+
+writeCompression no;
+
+timeFormat      general;
+
+timePrecision   14;
+
+graphFormat     raw;
+
+runTimeModifiable no;
+
+adjustTimeStep  yes;
+
+maxCo           1e6;
+
+maxAlphaCo      0.5;
+
+maxDeltaT       1e6;
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/decomposeParDict b/applications/test/reconstructedDistanceFunction/case1/system/decomposeParDict
new file mode 100644
index 0000000000000000000000000000000000000000..143cc870cb8505bff903e33c686bbd6fd8e4f1c2
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/decomposeParDict
@@ -0,0 +1,27 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      decomposeParDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+numberOfSubdomains 4;
+
+method      simple;
+
+coeffs
+{
+    n       (2 2 1);
+}
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/fvSchemes b/applications/test/reconstructedDistanceFunction/case1/system/fvSchemes
new file mode 100644
index 0000000000000000000000000000000000000000..a84a63acf7e81bc8d903a6b09c60eee2cc185e60
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/fvSchemes
@@ -0,0 +1,62 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSchemes;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+ddtSchemes
+{
+    default         Euler;
+}
+
+gradSchemes
+{
+    //default         Gauss linear;
+    default        pointCellsLeastSquares;
+}
+
+divSchemes
+{
+    div(rho*phi,U)  Gauss limitedLinearV 1;
+    div(phi,alpha)  Gauss vanLeer;
+    div(phi,alpha1)  Gauss HRIC;
+    div(phirb,alpha) Gauss interfaceCompression;
+    div((muEff*dev(T(grad(U))))) Gauss linear;
+}
+
+laplacianSchemes
+{
+    default         Gauss linear corrected;
+}
+
+interpolationSchemes
+{
+    default         linear;
+}
+
+snGradSchemes
+{
+    default         corrected;
+}
+
+fluxRequired
+{
+    default         no;
+    p_rgh;
+    pcorr;
+    alpha1;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/fvSolution b/applications/test/reconstructedDistanceFunction/case1/system/fvSolution
new file mode 100644
index 0000000000000000000000000000000000000000..869c25da627a2791f961755be0d2f09a8b8b7423
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/fvSolution
@@ -0,0 +1,48 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+solvers
+{
+    alpha1
+    {
+
+        reconstructionScheme isoAlpha;
+        vof2IsoTol 1e-8;
+        surfCellTol 1e-8;
+        writeVTK    false;
+    }
+}
+
+
+PIMPLE
+{
+    momentumPredictor no;
+    nCorrectors     -1;
+    nNonOrthogonalCorrectors -1;
+    nAlphaCorr      1;
+    nAlphaSubCycles 1;
+    cAlpha          1;
+    pRefCell        0;
+    pRefValue       0;
+}
+
+SIMPLE
+{
+    nNonOrthogonalCorrectors 0;
+}
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/isoSurfDict b/applications/test/reconstructedDistanceFunction/case1/system/isoSurfDict
new file mode 100644
index 0000000000000000000000000000000000000000..a7a3c3634ba97d2c99fc81010f3c7971c9e102f9
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/isoSurfDict
@@ -0,0 +1,23 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+field   "alpha1";
+type    sphere;
+centre  (0.51 0.51 0.51);
+radius  0.25;
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/setAlphaFieldDict b/applications/test/reconstructedDistanceFunction/case1/system/setAlphaFieldDict
new file mode 100644
index 0000000000000000000000000000000000000000..df664627655d3ef3472515413388b953af78cc1e
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/setAlphaFieldDict
@@ -0,0 +1,23 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+field   "alpha1";
+type    plane;
+origin  (0.485 0.0 0.0);
+normal  (-1 0 0);
+
+// ************************************************************************* //
diff --git a/applications/test/reconstructedDistanceFunction/case1/system/topoSetDict b/applications/test/reconstructedDistanceFunction/case1/system/topoSetDict
new file mode 100644
index 0000000000000000000000000000000000000000..2c27834951037f58bd56cd17dc2208999f51de59
--- /dev/null
+++ b/applications/test/reconstructedDistanceFunction/case1/system/topoSetDict
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      topoSetDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+actions
+(
+    {
+        name    c0;
+        type    cellSet;
+        action  new;
+        source  boxToCell;
+        box     (-1e10 -1e10 -1e10) (1e10 0 1e10);
+    }
+
+    {
+        name    c0;
+        type    cellSet;
+        action  invert;
+    }
+);
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/0.orig/T b/applications/test/setAlphaField/case1/0.orig/T
new file mode 100644
index 0000000000000000000000000000000000000000..21b16adb6a273c08f5358893fcf39591dd9a2f21
--- /dev/null
+++ b/applications/test/setAlphaField/case1/0.orig/T
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      T;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 1 0 0 0];
+
+internalField   uniform 300;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/0.orig/U b/applications/test/setAlphaField/case1/0.orig/U
new file mode 100644
index 0000000000000000000000000000000000000000..00c303e2562e3c3237bfbd1ec92d462d00037d9f
--- /dev/null
+++ b/applications/test/setAlphaField/case1/0.orig/U
@@ -0,0 +1,33 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volVectorField;
+    object      U;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -1 0 0 0 0];
+
+internalField   uniform (0 0 0);
+
+boundaryField
+{
+    walls
+    {
+        type            noSlip;
+    }
+    frontAndBack
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/0.orig/alpha.water b/applications/test/setAlphaField/case1/0.orig/alpha.water
new file mode 100644
index 0000000000000000000000000000000000000000..fa7e6861d029e4d41f0ecac1ce9c17965d9084ca
--- /dev/null
+++ b/applications/test/setAlphaField/case1/0.orig/alpha.water
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      alpha.water;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 0 0 0 0];
+
+internalField   uniform 0;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/0.orig/p b/applications/test/setAlphaField/case1/0.orig/p
new file mode 100644
index 0000000000000000000000000000000000000000..a7ee2ed31c529e5aed5aac42a37ce89dbf219f08
--- /dev/null
+++ b/applications/test/setAlphaField/case1/0.orig/p
@@ -0,0 +1,35 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    walls
+    {
+        type            calculated;
+        value           uniform 1e5;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/0.orig/p_rgh b/applications/test/setAlphaField/case1/0.orig/p_rgh
new file mode 100644
index 0000000000000000000000000000000000000000..c7db9671d503f9abd5bf8efddca9d8d1926f9a1d
--- /dev/null
+++ b/applications/test/setAlphaField/case1/0.orig/p_rgh
@@ -0,0 +1,35 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p_rgh;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    walls
+    {
+        type            fixedFluxPressure;
+        value           uniform 1e5;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/Allclean b/applications/test/setAlphaField/case1/Allclean
new file mode 100755
index 0000000000000000000000000000000000000000..9ba118456fe15932258ba950129513d3c53332ff
--- /dev/null
+++ b/applications/test/setAlphaField/case1/Allclean
@@ -0,0 +1,10 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/CleanFunctions      # Tutorial clean functions
+#------------------------------------------------------------------------------
+
+cleanCase0
+rm -rf processor*
+rm -r AlphaInit/
+
+#------------------------------------------------------------------------------
diff --git a/applications/test/setAlphaField/case1/Allrun b/applications/test/setAlphaField/case1/Allrun
new file mode 100755
index 0000000000000000000000000000000000000000..4e37f5339841278319ab27af2296b7b052105786
--- /dev/null
+++ b/applications/test/setAlphaField/case1/Allrun
@@ -0,0 +1,15 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/RunFunctions        # Tutorial run functions
+#------------------------------------------------------------------------------
+
+runApplication blockMesh
+#runApplication refineMesh -overwrite
+touch test-initAlphaField.foam
+restore0Dir
+runApplication setAlphaField
+#runApplication decomposePar
+#runParallel $(getApplication)
+#runApplication reconstructPar
+
+#------------------------------------------------------------------------------
diff --git a/applications/test/setAlphaField/case1/constant/g b/applications/test/setAlphaField/case1/constant/g
new file mode 100644
index 0000000000000000000000000000000000000000..e986fa078f05d07a6b5d1e847320c9124df73806
--- /dev/null
+++ b/applications/test/setAlphaField/case1/constant/g
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       uniformDimensionedVectorField;
+    location    "constant";
+    object      g;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -2 0 0 0 0];
+value           (0 -9.81 0);
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/constant/thermophysicalProperties b/applications/test/setAlphaField/case1/constant/thermophysicalProperties
new file mode 100644
index 0000000000000000000000000000000000000000..97199ca415d59d3326cd274950f23aead4eb3f8b
--- /dev/null
+++ b/applications/test/setAlphaField/case1/constant/thermophysicalProperties
@@ -0,0 +1,24 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+phases (water air);
+
+pMin        10000;
+
+sigma       0.07;
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/constant/thermophysicalProperties.air b/applications/test/setAlphaField/case1/constant/thermophysicalProperties.air
new file mode 100644
index 0000000000000000000000000000000000000000..5c77a504431c915a7a4e441b5a9a1dcbcde4da2c
--- /dev/null
+++ b/applications/test/setAlphaField/case1/constant/thermophysicalProperties.air
@@ -0,0 +1,48 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState perfectGas;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   28.9;
+    }
+    thermodynamics
+    {
+        Cp          1007;
+        Hf          0;
+    }
+    transport
+    {
+        mu          1.84e-05;
+        Pr          0.7;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/constant/thermophysicalProperties.water b/applications/test/setAlphaField/case1/constant/thermophysicalProperties.water
new file mode 100644
index 0000000000000000000000000000000000000000..175e31bdf955911abef2b2ed520c1fe66b634412
--- /dev/null
+++ b/applications/test/setAlphaField/case1/constant/thermophysicalProperties.water
@@ -0,0 +1,53 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState perfectFluid;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   18.0;
+    }
+    equationOfState
+    {
+        R           3000;
+        rho0        1027;
+    }
+    thermodynamics
+    {
+        Cp          4195;
+        Hf          0;
+    }
+    transport
+    {
+        mu          3.645e-4;
+        Pr          2.289;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/constant/turbulenceProperties b/applications/test/setAlphaField/case1/constant/turbulenceProperties
new file mode 100644
index 0000000000000000000000000000000000000000..fbd1e3c277c13766d96341f6214f8c833ed4b691
--- /dev/null
+++ b/applications/test/setAlphaField/case1/constant/turbulenceProperties
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  laminar;
+
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/system/blockMeshDict b/applications/test/setAlphaField/case1/system/blockMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..7b2d728f7092d3cc65525bccdc92b66314908a58
--- /dev/null
+++ b/applications/test/setAlphaField/case1/system/blockMeshDict
@@ -0,0 +1,53 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      blockMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+scale   1;
+
+vertices
+(
+    (0 0 0)
+    (1 0 0)
+    (1 2 0)
+    (0 2 0)
+    (0 0 1)
+    (1 0 1)
+    (1 2 1)
+    (0 2 1)
+);
+
+blocks
+(
+    hex (0 1 2 3 4 5 6 7) (20 40 20) simpleGrading (1 1 1)
+);
+
+boundary
+(
+    walls
+    {
+        type wall;
+        faces
+        (
+            (3 7 6 2)
+            (0 4 7 3)
+            (2 6 5 1)
+            (1 5 4 0)
+            (0 3 2 1)
+            (4 5 6 7)
+        );
+    }
+);
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/system/controlDict b/applications/test/setAlphaField/case1/system/controlDict
new file mode 100644
index 0000000000000000000000000000000000000000..0e4d411571e1313fede92404ee783a494bde1cc0
--- /dev/null
+++ b/applications/test/setAlphaField/case1/system/controlDict
@@ -0,0 +1,55 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      controlDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+application     setAlphaField;
+
+startFrom       latestTime;
+
+startTime       0;
+
+stopAt          endTime;
+
+endTime         0.1;
+
+deltaT          0.0001;
+
+writeControl    adjustableRunTime;
+
+writeInterval   0.01;
+
+purgeWrite      0;
+
+writeFormat     ascii;
+
+writePrecision  8;
+
+writeCompression off;
+
+timeFormat      general;
+
+timePrecision   10;
+
+runTimeModifiable yes;
+
+adjustTimeStep  yes;
+
+maxCo           0.5;
+maxAlphaCo      0.5;
+maxDeltaT       1;
+
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/system/decomposeParDict b/applications/test/setAlphaField/case1/system/decomposeParDict
new file mode 100644
index 0000000000000000000000000000000000000000..c2de1601afe27da4bf126daedf9a5fbca93d893d
--- /dev/null
+++ b/applications/test/setAlphaField/case1/system/decomposeParDict
@@ -0,0 +1,33 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      decomposeParDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+numberOfSubdomains 64;
+
+method          scotch;
+
+coeffs
+{
+    n           (1 4 1);
+    //delta       0.001; // default=0.001
+    //order       xyz;   // default=xzy
+}
+
+distributed     no;
+
+roots           ( );
+
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/system/fvSchemes b/applications/test/setAlphaField/case1/system/fvSchemes
new file mode 100644
index 0000000000000000000000000000000000000000..c65082c8d9fe57e8bf1f8afad1d51efa0d3dad74
--- /dev/null
+++ b/applications/test/setAlphaField/case1/system/fvSchemes
@@ -0,0 +1,57 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSchemes;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+ddtSchemes
+{
+    default         Euler;
+}
+
+gradSchemes
+{
+    default         Gauss linear;
+}
+
+divSchemes
+{
+    div(phi,alpha)  Gauss vanLeer;
+    div(phirb,alpha) Gauss linear;
+
+    div(rhoPhi,U)  Gauss upwind;
+    div(rhoPhi,T)  Gauss upwind;
+    div(rhoPhi,K)  Gauss upwind;
+    div(phi,p)      Gauss upwind;
+    div(phi,k)      Gauss upwind;
+
+    div(((rho*nuEff)*dev2(T(grad(U))))) Gauss linear;
+}
+
+laplacianSchemes
+{
+    default         Gauss linear uncorrected;
+}
+
+interpolationSchemes
+{
+    default         linear;
+}
+
+snGradSchemes
+{
+    default         uncorrected;
+}
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/system/fvSolution b/applications/test/setAlphaField/case1/system/fvSolution
new file mode 100644
index 0000000000000000000000000000000000000000..d366acd51493efe784b5b604b047afa1c6d05190
--- /dev/null
+++ b/applications/test/setAlphaField/case1/system/fvSolution
@@ -0,0 +1,108 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+solvers
+{
+    "alpha.water.*"
+    {
+        nAlphaCorr      1;
+        nAlphaSubCycles 2;
+        cAlpha          1;
+
+        MULESCorr       no;
+        nLimiterIter    5;
+
+        solver          smoothSolver;
+        smoother        symGaussSeidel;
+        tolerance       1e-8;
+        relTol          0;
+    }
+
+    "pcorr.*"
+    {
+        solver          PCG;
+        preconditioner
+        {
+            preconditioner  GAMG;
+            tolerance       1e-05;
+            relTol          0;
+            smoother        DICGaussSeidel;
+        }
+        tolerance       1e-05;
+        relTol          0;
+        maxIter         100;
+    }
+
+    ".*(rho|rhoFinal)"
+    {
+        solver          diagonal;
+    }
+
+    p_rgh
+    {
+        solver          GAMG;
+        tolerance       1e-07;
+        relTol          0.01;
+        smoother        DIC;
+    }
+
+    p_rghFinal
+    {
+        solver          PCG;
+        preconditioner
+        {
+            preconditioner  GAMG;
+            tolerance       1e-07;
+            relTol          0;
+            nVcycles        2;
+            smoother        DICGaussSeidel;
+            nPreSweeps      2;
+        }
+        tolerance       1e-07;
+        relTol          0;
+        maxIter         20;
+    }
+
+    U
+    {
+        solver          smoothSolver;
+        smoother        GaussSeidel;
+        tolerance       1e-06;
+        relTol          0;
+        nSweeps         1;
+    }
+
+    "(T|k|B|nuTilda).*"
+    {
+        solver          smoothSolver;
+        smoother        symGaussSeidel;
+        tolerance       1e-08;
+        relTol          0;
+    }
+}
+
+PIMPLE
+{
+    momentumPredictor no;
+    transonic       no;
+    nOuterCorrectors 1;
+    nCorrectors     2;
+    nNonOrthogonalCorrectors 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/setAlphaField/case1/system/setAlphaFieldDict b/applications/test/setAlphaField/case1/system/setAlphaFieldDict
new file mode 100644
index 0000000000000000000000000000000000000000..28481221e2068a44ff407fb7270dcf6a3d97e700
--- /dev/null
+++ b/applications/test/setAlphaField/case1/system/setAlphaFieldDict
@@ -0,0 +1,48 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+field "alpha.water";
+
+type composedFunction;
+mode minDist;
+composedFunctions
+{
+    plane
+    {
+        type plane;
+        origin (0 1. 0);
+        normal (0 -1 0);
+    }
+
+    sphere
+    {
+        type sphere;
+        radius 0.4;
+        origin (0.5 1.5 0.5);
+        scale 1;
+    }
+
+    sphere2
+    {
+        type sphere;
+        radius 0.4;
+        origin (0.5 0.5 0.5);
+        scale -1;
+    }
+}
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/Make/files b/applications/test/zoneDistribute/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..6eb2483e218587e9a72ab8fbd3b5ec08e71a9586
--- /dev/null
+++ b/applications/test/zoneDistribute/Make/files
@@ -0,0 +1,3 @@
+Test-zoneDistribute.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-zoneDistribute
diff --git a/applications/test/zoneDistribute/Make/options b/applications/test/zoneDistribute/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..5413c0b3bac8c3ab3b299ab1bf06518bb7e2fa41
--- /dev/null
+++ b/applications/test/zoneDistribute/Make/options
@@ -0,0 +1,13 @@
+EXE_INC = \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/fileFormats/lnInclude \
+    -I$(LIB_SRC)/surfMesh/lnInclude \
+    -I$(LIB_SRC)/meshTools/lnInclude \
+    -I$(LIB_SRC)/sampling/lnInclude
+
+EXE_LIBS = \
+    -lfiniteVolume \
+    -lfileFormats \
+    -lsurfMesh \
+    -lmeshTools \
+    -lsampling
diff --git a/applications/test/zoneDistribute/Test-zoneDistribute.C b/applications/test/zoneDistribute/Test-zoneDistribute.C
new file mode 100644
index 0000000000000000000000000000000000000000..00505735b6356f606804d241a05d7dc8fc5b2abb
--- /dev/null
+++ b/applications/test/zoneDistribute/Test-zoneDistribute.C
@@ -0,0 +1,121 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Application
+    Test-zoneDistribute
+
+Description
+    Test of zoneDistribute validated with mapDistribute
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+\*---------------------------------------------------------------------------*/
+
+#include "fvCFD.H"
+#include "centredCPCCellToCellStencilObject.H"
+#include "zoneDistribute.H"
+
+#include "SortableList.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+int main(int argc, char *argv[])
+{
+    #include "setRootCase.H"
+    #include "createTime.H"
+    #include "createMesh.H"
+
+    const extendedCentredCellToCellStencil& stencil =
+        centredCPCCellToCellStencilObject::New(mesh);
+
+    const List<List<label>>& stencilAddr = stencil.stencil();
+
+    List<List<vector>> stencilCentre(mesh.nCells());
+
+    stencil.collectData
+    (
+       mesh.C(),
+       stencilCentre
+    );
+
+    zoneDistribute exchangeFields(mesh);
+
+
+    boolList interfaceCell(mesh.nCells(),true);
+    exchangeFields.setUpCommforZone(interfaceCell);
+
+
+    const labelListList& stencil_zoneDist = exchangeFields.getStencil();
+    const globalIndex& gblNumbering = exchangeFields.globalNumbering();
+
+    Map<vectorField> mapCC(exchangeFields.getFields(interfaceCell,mesh.C()));
+
+    // compare stencils
+    Pout<< "size of the stencil match "
+        << (stencilAddr.size() == stencil_zoneDist.size()) << endl;
+
+    label stencilMatch = 0;
+
+    forAll(stencilAddr,celli)
+    {
+        const vectorField& neiCC = mapCC[celli];
+        if (neiCC.size() != stencilCentre[celli].size())
+        {
+            continue;
+        }
+
+        bool foundAllLabel = true;
+        for (const vector& cc : neiCC)
+        {
+            if (!stencilCentre[celli].found(cc))
+            {
+                foundAllLabel = false;
+                break;
+            }
+        }
+
+        if (foundAllLabel)
+        {
+            ++stencilMatch;
+        }
+
+    }
+
+    if (stencilMatch == mesh.nCells())
+    {
+        Pout << "all Values are identical "  << endl;
+    }
+    else
+    {
+        Pout << "values did not match in : " << stencilMatch << " of "
+             << mesh.nCells() << " cases" << endl;
+    }
+
+    return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/Allclean b/applications/test/zoneDistribute/case1/Allclean
new file mode 100755
index 0000000000000000000000000000000000000000..36d26d8799bdd6993df3b51e33e675d5c4f90a66
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/Allclean
@@ -0,0 +1,15 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/CleanFunctions      # Tutorial clean functions
+#------------------------------------------------------------------------------
+
+cleanCase0
+
+rm -f ./flange ./*.obj
+
+# Remove surface and features
+rm -f constant/triSurface/flange.stl.gz
+rm -f constant/triSurface/flange.eMesh
+rm -rf constant/extendedFeatureEdgeMesh
+
+#------------------------------------------------------------------------------
diff --git a/applications/test/zoneDistribute/case1/Allrun b/applications/test/zoneDistribute/case1/Allrun
new file mode 100755
index 0000000000000000000000000000000000000000..444a182a12a99c0d571e7a94d401c3158a647a31
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/Allrun
@@ -0,0 +1,13 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/RunFunctions        # Tutorial run functions
+#------------------------------------------------------------------------------
+
+touch test-zoneDistribute.foam
+runApplication blockMesh
+#runApplication surfaceFeatureExtract
+runApplication snappyHexMesh -overwrite
+runApplication decomposePar
+runParallel test-zoneDistribute
+
+#------------------------------------------------------------------------------
diff --git a/applications/test/zoneDistribute/case1/constant/triSurface/README b/applications/test/zoneDistribute/case1/constant/triSurface/README
new file mode 100644
index 0000000000000000000000000000000000000000..de3f29cc01268a637d915dc6d9b8fb98400e9906
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/constant/triSurface/README
@@ -0,0 +1,4 @@
+Directory to house tri-surfaces
+
+The Allrun script copies the surface from the $FOAM_TUTORIALS/resources/geometry
+directory
diff --git a/applications/test/zoneDistribute/case1/system/blockMeshDict b/applications/test/zoneDistribute/case1/system/blockMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..749b1e36299665adc384df9f0b278a267ff10ef3
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/blockMeshDict
@@ -0,0 +1,57 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      blockMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+scale   1;
+
+vertices
+(
+    ( -1 -1 -1)
+    (  1 -1 -1)
+    (  1  1 -1)
+    ( -1  1 -1)
+    ( -1 -1 1)
+    (  1 -1 1)
+    (  1  1 1)
+    ( -1  1 1)
+);
+
+blocks
+(
+    hex (0 1 2 3 4 5 6 7) (10 10 10) simpleGrading (1 1 1)
+);
+
+edges
+(
+);
+
+boundary
+(
+    allBoundary
+    {
+        type patch;
+        faces
+        (
+            (3 7 6 2)
+            (0 4 7 3)
+            (2 6 5 1)
+            (1 5 4 0)
+            (0 3 2 1)
+            (4 5 6 7)
+        );
+    }
+);
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/controlDict b/applications/test/zoneDistribute/case1/system/controlDict
new file mode 100644
index 0000000000000000000000000000000000000000..ff0a7ebf7ae14f7e172177b2fbf4effd59eda844
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/controlDict
@@ -0,0 +1,49 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      controlDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+application     snappyHexMesh;
+
+startFrom       startTime;
+
+startTime       0;
+
+stopAt          endTime;
+
+endTime         50;
+
+deltaT          1;
+
+writeControl    timeStep;
+
+writeInterval   20;
+
+purgeWrite      0;
+
+writeFormat     ascii;
+
+writePrecision  6;
+
+writeCompression off;
+
+timeFormat      general;
+
+timePrecision   6;
+
+runTimeModifiable yes;
+
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/decomposeParDict b/applications/test/zoneDistribute/case1/system/decomposeParDict
new file mode 100644
index 0000000000000000000000000000000000000000..bc2087dad0c4527f6f6a4790938e49a6cd788632
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/decomposeParDict
@@ -0,0 +1,27 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      decomposeParDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+numberOfSubdomains 8;
+
+method          simple;
+
+coeffs
+{
+    n           (4 2 1);
+}
+
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/fvSchemes b/applications/test/zoneDistribute/case1/system/fvSchemes
new file mode 100644
index 0000000000000000000000000000000000000000..34da6be2ea1b3c4c2e26a44290eb1b35a6ad2b83
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/fvSchemes
@@ -0,0 +1,30 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSchemes;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+gradSchemes
+{
+}
+
+divSchemes
+{
+}
+
+laplacianSchemes
+{
+}
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/fvSolution b/applications/test/zoneDistribute/case1/system/fvSolution
new file mode 100644
index 0000000000000000000000000000000000000000..97b46fe07e433f49b5665f44377aac1a9d7ebf51
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/fvSolution
@@ -0,0 +1,18 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/meshQualityDict b/applications/test/zoneDistribute/case1/system/meshQualityDict
new file mode 100644
index 0000000000000000000000000000000000000000..c91a7d24784bad61468ca922133db475fa207c9d
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/meshQualityDict
@@ -0,0 +1,22 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      meshQualityDict;
+}
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+// Include defaults parameters from master dictionary
+#includeEtc "caseDicts/meshQualityDict"
+
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/snappyHexMeshDict b/applications/test/zoneDistribute/case1/system/snappyHexMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..033d15ed48faf632ad547a4eb40e4b8e4e8556a9
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/snappyHexMeshDict
@@ -0,0 +1,310 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      snappyHexMeshDict;
+}
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+// Which of the steps to run
+castellatedMesh true;
+snap            true;
+addLayers       false;
+
+
+// Geometry. Definition of all surfaces. All surfaces are of class
+// searchableSurface.
+// Surfaces are used
+// - to specify refinement for any mesh cell intersecting it
+// - to specify refinement for any mesh cell inside/outside/near
+// - to 'snap' the mesh boundary to the surface
+geometry
+{
+
+    //- Refine a bit extra around the small centre hole
+    sphere
+    {
+        type    sphere;
+        origin  (0 0 -0.00);
+        radius  0.99;
+    }
+}
+
+
+// Settings for the castellatedMesh generation.
+castellatedMeshControls
+{
+
+    // Refinement parameters
+    // ~~~~~~~~~~~~~~~~~~~~~
+
+    // If local number of cells is >= maxLocalCells on any processor
+    // switches from from refinement followed by balancing
+    // (current method) to (weighted) balancing before refinement.
+    maxLocalCells 100000;
+
+    // Overall cell limit (approximately). Refinement will stop immediately
+    // upon reaching this number so a refinement level might not complete.
+    // Note that this is the number of cells before removing the part which
+    // is not 'visible' from the keepPoint. The final number of cells might
+    // actually be a lot less.
+    maxGlobalCells 2000000;
+
+    // The surface refinement loop might spend lots of iterations refining just a
+    // few cells. This setting will cause refinement to stop if <= minimumRefine
+    // are selected for refinement. Note: it will at least do one iteration
+    // (unless the number of cells to refine is 0)
+    minRefinementCells 0;
+
+    // Number of buffer layers between different levels.
+    // 1 means normal 2:1 refinement restriction, larger means slower
+    // refinement.
+    nCellsBetweenLevels 1;
+
+
+
+    // Explicit feature edge refinement
+    // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+    // Specifies a level for any cell intersected by its edges.
+    // This is a featureEdgeMesh, read from constant/triSurface for now.
+    features
+    (
+
+    );
+
+
+
+    // Surface based refinement
+    // ~~~~~~~~~~~~~~~~~~~~~~~~
+
+    // Specifies two levels for every surface. The first is the minimum level,
+    // every cell intersecting a surface gets refined up to the minimum level.
+    // The second level is the maximum level. Cells that 'see' multiple
+    // intersections where the intersections make an
+    // angle > resolveFeatureAngle get refined up to the maximum level.
+
+    refinementSurfaces
+    {
+        sphere
+        {
+            // Surface-wise min and max refinement level
+            level (2 2);
+        }
+    }
+
+    resolveFeatureAngle 30;
+
+
+    // Region-wise refinement
+    // ~~~~~~~~~~~~~~~~~~~~~~
+
+    // Specifies refinement level for cells in relation to a surface. One of
+    // three modes
+    // - distance. 'levels' specifies per distance to the surface the
+    //   wanted refinement level. The distances need to be specified in
+    //   descending order.
+    // - inside. 'levels' is only one entry and only the level is used. All
+    //   cells inside the surface get refined up to the level. The surface
+    //   needs to be closed for this to be possible.
+    // - outside. Same but cells outside.
+
+    refinementRegions
+    {
+        // refineHole
+        // {
+        //     mode inside;
+        //     levels ((1E15 3));
+        // }
+    }
+
+
+    // Mesh selection
+    // ~~~~~~~~~~~~~~
+
+    // After refinement patches get added for all refinementSurfaces and
+    // all cells intersecting the surfaces get put into these patches. The
+    // section reachable from the locationInMesh is kept.
+    // NOTE: This point should never be on a face, always inside a cell, even
+    // after refinement.
+    // This is an outside point locationInMesh (-0.033 -0.033 0.0033);
+    locationInMesh (0 0 0); // Inside point
+
+    // Whether any faceZones (as specified in the refinementSurfaces)
+    // are only on the boundary of corresponding cellZones or also allow
+    // free-standing zone faces. Not used if there are no faceZones.
+    allowFreeStandingZoneFaces true;
+}
+
+
+
+// Settings for the snapping.
+snapControls
+{
+    //- Number of patch smoothing iterations before finding correspondence
+    //  to surface
+    nSmoothPatch 3;
+
+    //- Relative distance for points to be attracted by surface feature point
+    //  or edge. True distance is this factor times local
+    //  maximum edge length.
+    tolerance 1.0;
+
+    //- Number of mesh displacement relaxation iterations.
+    nSolveIter 300;
+
+    //- Maximum number of snapping relaxation iterations. Should stop
+    //  before upon reaching a correct mesh.
+    nRelaxIter 5;
+
+    // Feature snapping
+
+        //- Number of feature edge snapping iterations.
+        //  Leave out altogether to disable.
+        nFeatureSnapIter 10;
+
+        //- Detect (geometric) features by sampling the surface
+        implicitFeatureSnap false;
+
+        //- Use castellatedMeshControls::features
+        explicitFeatureSnap true;
+
+        //- Detect features between multiple surfaces
+        //  (only for explicitFeatureSnap, default = false)
+        multiRegionFeatureSnap true;
+}
+
+
+
+// Settings for the layer addition.
+addLayersControls
+{
+    // Are the thickness parameters below relative to the undistorted
+    // size of the refined cell outside layer (true) or absolute sizes (false).
+    relativeSizes true;
+
+    // Per final patch (so not geometry!) the layer information
+    layers
+    {
+        "flange_.*"
+        {
+            nSurfaceLayers 1;
+        }
+    }
+
+    // Expansion factor for layer mesh
+    expansionRatio 1.0;
+
+
+    // Wanted thickness of final added cell layer. If multiple layers
+    // is the thickness of the layer furthest away from the wall.
+    // Relative to undistorted size of cell outside layer.
+    // See relativeSizes parameter.
+    finalLayerThickness 0.3;
+
+    // Minimum thickness of cell layer. If for any reason layer
+    // cannot be above minThickness do not add layer.
+    // See relativeSizes parameter.
+    minThickness 0.25;
+
+    // If points get not extruded do nGrow layers of connected faces that are
+    // also not grown. This helps convergence of the layer addition process
+    // close to features.
+    nGrow 0;
+
+
+    // Advanced settings
+
+    // When not to extrude surface. 0 is flat surface, 90 is when two faces
+    // are perpendicular
+    featureAngle 30;
+
+    // Maximum number of snapping relaxation iterations. Should stop
+    // before upon reaching a correct mesh.
+    nRelaxIter 5;
+
+    // Number of smoothing iterations of surface normals
+    nSmoothSurfaceNormals 1;
+
+    // Number of smoothing iterations of interior mesh movement direction
+    nSmoothNormals 3;
+
+    // Smooth layer thickness over surface patches
+    nSmoothThickness 10;
+
+    // Stop layer growth on highly warped cells
+    maxFaceThicknessRatio 0.5;
+
+    // Reduce layer growth where ratio thickness to medial
+    // distance is large
+    maxThicknessToMedialRatio 0.3;
+
+    // Angle used to pick up medial axis points
+    minMedialAxisAngle 90;
+
+    // Create buffer region for new layer terminations
+    nBufferCellsNoExtrude 0;
+
+
+    // Overall max number of layer addition iterations. The mesher will exit
+    // if it reaches this number of iterations; possibly with an illegal
+    // mesh.
+    nLayerIter 50;
+
+    // Max number of iterations after which relaxed meshQuality controls
+    // get used. Up to nRelaxIter it uses the settings in meshQualityControls,
+    // after nRelaxIter it uses the values in meshQualityControls::relaxed.
+    nRelaxedIter 20;
+}
+
+
+
+// Generic mesh quality settings. At any undoable phase these determine
+// where to undo.
+meshQualityControls
+{
+    #include "meshQualityDict"
+
+    // Optional : some meshing phases allow usage of relaxed rules.
+    // See e.g. addLayersControls::nRelaxedIter.
+    relaxed
+    {
+        //- Maximum non-orthogonality allowed. Set to 180 to disable.
+        maxNonOrtho 75;
+    }
+
+    // Advanced
+
+    //- Number of error distribution iterations
+    nSmoothScale 4;
+    //- Amount to scale back displacement at error points
+    errorReduction 0.75;
+}
+
+
+// Advanced
+
+// Write flags
+writeFlags
+(
+    scalarLevels    // write volScalarField with cellLevel for postprocessing
+    layerSets       // write cellSets, faceSets of faces in layer
+    layerFields     // write volScalarField for layer coverage
+);
+
+
+// Merge tolerance. Is fraction of overall bounding box of initial mesh.
+// Note: the write tolerance needs to be higher than this.
+mergeTolerance 1E-6;
+
+
+// ************************************************************************* //
diff --git a/applications/test/zoneDistribute/case1/system/surfaceFeatureExtractDict b/applications/test/zoneDistribute/case1/system/surfaceFeatureExtractDict
new file mode 100644
index 0000000000000000000000000000000000000000..e074b996d4e9e25fa49b13261f0a2e44660bb4c7
--- /dev/null
+++ b/applications/test/zoneDistribute/case1/system/surfaceFeatureExtractDict
@@ -0,0 +1,35 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      surfaceFeatureExtractDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+flange.stl
+{
+    // How to obtain raw features (extractFromFile || extractFromSurface)
+    extractionMethod    extractFromSurface;
+
+    // Mark edges whose adjacent surface normals are at an angle less
+    // than includedAngle as features
+    // - 0  : selects no edges
+    // - 180: selects all edges
+    includedAngle       150;
+
+    // Write options
+
+    // Write features to obj format for postprocessing
+    writeObj            yes;
+}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/Allwclean b/applications/utilities/preProcessing/setAlphaField/Allwclean
new file mode 100755
index 0000000000000000000000000000000000000000..bb9e648f9d96a5770ee45b02833053cccff110d5
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/Allwclean
@@ -0,0 +1,7 @@
+#!/bin/sh
+cd "${0%/*}" || exit    # Run from this directory
+
+wclean libso alphaFieldFunctions
+wclean
+
+#------------------------------------------------------------------------------
diff --git a/applications/utilities/preProcessing/setAlphaField/Allwmake b/applications/utilities/preProcessing/setAlphaField/Allwmake
new file mode 100755
index 0000000000000000000000000000000000000000..7c7aa843d103d4d8cde33e401c82c2f6032924dd
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/Allwmake
@@ -0,0 +1,10 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/wmake/scripts/AllwmakeParseArguments
+
+#------------------------------------------------------------------------------
+
+wmake $targetType alphaFieldFunctions
+wmake $targetType
+
+#------------------------------------------------------------------------------
diff --git a/applications/utilities/preProcessing/setAlphaField/Make/options b/applications/utilities/preProcessing/setAlphaField/Make/options
index b4ad3d8bdff2f2475467775f28a6c62effa80575..8f9558bba0fda95af9b546f74b2eb42c8cf06293 100644
--- a/applications/utilities/preProcessing/setAlphaField/Make/options
+++ b/applications/utilities/preProcessing/setAlphaField/Make/options
@@ -1,9 +1,17 @@
 EXE_INC = \
+    -IalphaFieldFunctions/lnInclude \
     -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/surfMesh/lnInclude \
     -I$(LIB_SRC)/meshTools/lnInclude \
-    -I$(LIB_SRC)/sampling/lnInclude
+    -I$(LIB_SRC)/fileFormats/lnInclude \
+    -I$(LIB_SRC)/sampling/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude
 
 EXE_LIBS = \
     -lfiniteVolume \
+    -lfileFormats \
+    -lsurfMesh \
     -lmeshTools \
-    -lsampling
+    -lsampling \
+    -lgeometricVoF \
+    -lalphaFieldFunctions
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/Make/files b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..b7585a9d1a83bd804c8e71f22e69a6674cd45ffd
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/Make/files
@@ -0,0 +1,11 @@
+/* Run-time selectable implicitFunctions */
+implicitFunctions/implicitFunction.C
+implicitFunctions/sphere/sphereImplicitFunction.C
+implicitFunctions/sin/sinImplicitFunction.C
+implicitFunctions/ellipsoid/ellipsoidImplicitFunction.C
+implicitFunctions/paraboloid/paraboloidImplicitFunction.C
+implicitFunctions/plane/planeImplicitFunction.C
+implicitFunctions/cylinder/cylinderImplicitFunction.C
+implicitFunctions/composedFunction/composedFunctionImplicitFunction.C
+
+LIB = $(FOAM_LIBBIN)/libalphaFieldFunctions
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/Make/options b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..6b8588463d9782589e3443f8bb381f736ff3ddfa
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/Make/options
@@ -0,0 +1,2 @@
+/* EXE_INC = */
+/* LIB_LIBS = */
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/composedFunction/composedFunctionImplicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/composedFunction/composedFunctionImplicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..900188e5e2c56bcefd4d67e6c7828680a90f7ff8
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/composedFunction/composedFunctionImplicitFunction.C
@@ -0,0 +1,207 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "composedFunctionImplicitFunction.H"
+#include "scalarField.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(composedFunctionImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            composedFunctionImplicitFunction,
+            dict
+        );
+    }
+}
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+const Foam::Enum
+<
+    Foam::implicitFunctions::composedFunctionImplicitFunction::modeType
+>
+Foam::implicitFunctions::composedFunctionImplicitFunction::modeTypeNames
+({
+    { modeType::ADD, "add" },
+    { modeType::SUBTRACT, "subtract" },
+    { modeType::MINDIST, "minDist" },
+    { modeType::INTERSECT, "intersect" },
+});
+
+
+Foam::label
+Foam::implicitFunctions::composedFunctionImplicitFunction::selectFunction
+(
+    const scalarField& values
+) const
+{
+    switch (mode_)
+    {
+        case modeType::MINDIST:
+        {
+            scalarField absVal(mag(values));
+            return findMin(absVal);
+        }
+        case modeType::ADD:
+        {
+            return findMax(values);
+        }
+        case modeType::SUBTRACT:
+        {
+            // Note: start at the second entry
+            const label idx = findMin(values, 1);
+
+            if (values[idx] < values[0] && pos(values[0]))
+            {
+                return idx;
+            }
+            else
+            {
+                return 0;
+            }
+        }
+        case modeType::INTERSECT:
+        {
+            return findMin(values);
+        }
+        default:
+        {
+            FatalErrorInFunction
+                << "This mode is not supported  only " << nl
+                << "Supported modes are: " << nl
+                << modeTypeNames
+                << abort(FatalError);
+        }
+    }
+
+    return -1;
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::composedFunctionImplicitFunction::
+composedFunctionImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    functions_(),
+    mode_(modeTypeNames.get("mode", dict)),
+    values_()
+{
+    const dictionary& funcDict = dict.subDict("composedFunction");
+
+    functions_.resize(funcDict.size());
+    values_.resize(funcDict.size(), Zero);
+
+    label funci = 0;
+
+    for (const entry& dEntry : funcDict)
+    {
+        const word& key = dEntry.keyword();
+
+        if (!dEntry.isDict())
+        {
+            FatalIOErrorInFunction(funcDict)
+                << "Entry " << key << " is not a dictionary" << endl
+                << exit(FatalError);
+        }
+
+        const dictionary& subdict = dEntry.dict();
+
+        functions_.set
+        (
+            funci,
+            implicitFunction::New(subdict.get<word>("type"), subdict)
+        );
+
+        ++funci;
+    }
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::scalar Foam::implicitFunctions::composedFunctionImplicitFunction::value
+(
+    const vector& p
+) const
+{
+    forAll(values_,i)
+    {
+        values_[i] = functions_[i].value(p);
+    }
+
+    const label idx = selectFunction(values_);
+
+    return values_[idx];
+}
+
+
+Foam::vector Foam::implicitFunctions::composedFunctionImplicitFunction::grad
+(
+    const vector& p
+) const
+{
+    forAll(values_,i)
+    {
+        values_[i] = mag(functions_[i].value(p));
+    }
+
+    const label minIdx = findMin(values_);
+
+    return functions_[minIdx].grad(p);
+}
+
+
+Foam::scalar
+Foam::implicitFunctions::composedFunctionImplicitFunction::distanceToSurfaces
+(
+    const vector& p
+) const
+{
+    forAll(values_,i)
+    {
+        values_[i] = mag(functions_[i].value(p));
+    }
+
+    const label minIdx = findMin(values_);
+
+    return functions_[minIdx].distanceToSurfaces(p);
+}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/composedFunction/composedFunctionImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/composedFunction/composedFunctionImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..f75da2a97be1038b3c1f8137f1a76cf7e5f0f77b
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/composedFunction/composedFunctionImplicitFunction.H
@@ -0,0 +1,169 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::composedFunctionImplicitFunction
+
+Description
+    Handles multiple implicit functions and offers multiple ways to combine
+    them
+
+Usage
+    Example of function object partial specification:
+    \verbatim
+    function composedFunctionImplicitFunction;
+    mode minDist;
+    // following mode are available:
+    // "add" "subtract" "minDist" "intersect"
+    composedFunctionImplicitFunctions
+    {
+        plane
+        {
+            function plane;
+            origin (0 1. 0);
+            normal (0 1 0);
+        }
+
+        sphere
+        {
+            function sphere;
+            radius 0.4;
+            origin (0.5 1.5 0.5);
+            scale 1;
+        }
+
+        sphere2
+        {
+            function sphere;
+            radius 0.4;
+            origin (0.5 0.5 0.5);
+            scale -1;
+        }
+    }
+    \endverbatim
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    composedFunctionImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunctions_composedFunctionImplicitFunction_H
+#define implicitFunctions_composedFunctionImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "scalarField.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+              Class composedFunctionImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class composedFunctionImplicitFunction
+:
+    public implicitFunction
+{
+    // Private Member Data
+
+        //- Enumeration defining the valid actions
+        enum class modeType
+        {
+            ADD,
+            SUBTRACT,
+            MINDIST,
+            INTERSECT
+        };
+
+        //- The setActions text representations
+        static const Enum<modeType> modeTypeNames;
+
+        //- Stores the functions
+        PtrList<implicitFunction> functions_;
+
+        //- Mode
+        modeType mode_;
+
+        //- Needed for finding the closest function.
+        //  Note: avoid creation every call
+        mutable scalarField values_;
+
+
+    // Private Member Functions
+
+        label selectFunction(const scalarField& values) const;
+
+        //- No copy construct
+        composedFunctionImplicitFunction
+        (
+            const composedFunctionImplicitFunction&
+        ) = delete;
+
+        //- No copy assignment
+        void operator=(const composedFunctionImplicitFunction&) = delete;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("composedFunction");
+
+
+    // Constructors
+
+        //- Construct from dictionary
+        explicit composedFunctionImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~composedFunctionImplicitFunction() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& p) const;
+
+        virtual vector grad(const vector& p) const;
+
+        virtual scalar distanceToSurfaces(const vector& p) const;
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/cylinder/cylinderImplicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/cylinder/cylinderImplicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..909087e47329de5e75d1039b03ddd524262cc463
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/cylinder/cylinderImplicitFunction.C
@@ -0,0 +1,82 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cylinderImplicitFunction.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(cylinderImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            cylinderImplicitFunction,
+            dict
+        );
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::cylinderImplicitFunction::cylinderImplicitFunction
+(
+    const point& origin,
+    const scalar radius,
+    const scalar scale,
+    const vector& direction
+)
+:
+    origin_(origin),
+    radius_(radius),
+    scale_(scale),
+    direction_(normalised(direction)),
+    project_(tensor::I - direction_*direction_) // outer product
+{}
+
+
+Foam::implicitFunctions::cylinderImplicitFunction::cylinderImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    cylinderImplicitFunction
+    (
+        dict.get<point>("origin"),
+        dict.get<scalar>("radius"),
+        dict.getOrDefault<scalar>("scale", 1),
+        dict.get<vector>("direction")
+    )
+{}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/cylinder/cylinderImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/cylinder/cylinderImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..65de539668fee65783b3f413d94726b9c653bbc0
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/cylinder/cylinderImplicitFunction.H
@@ -0,0 +1,132 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::cylinderImplicitFunction
+
+Description
+    creates a infintite long cylinderImplicitFunction
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    cylinderImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_cylinderImplicitFunction_H
+#define implicitFunction_cylinderImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "point.H"
+#include "tensor.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+                   Class cylinderImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class cylinderImplicitFunction
+:
+    public implicitFunction
+{
+private:
+
+    // Private Data
+
+        //- Origin point
+        const point origin_;
+
+        //- Radius
+        const scalar radius_;
+
+        const scalar scale_;
+
+        const vector direction_;
+
+        const tensor project_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("cylinder");
+
+
+    // Constructors
+
+        //- Construct from components
+        cylinderImplicitFunction
+        (
+            const point& origin,
+            const scalar radius,
+            const scalar scale,
+            const vector& direction
+        );
+
+        //- Construct from dictionary
+        explicit cylinderImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~cylinderImplicitFunction() = default;
+
+
+    // Member Functions
+
+    virtual scalar value(const vector& p) const
+    {
+        return (-mag(project_ & (p - origin_)) + radius_)*scale_;
+    }
+
+    virtual vector grad(const vector& p) const
+    {
+        return -(project_ & (p - origin_))*scale_;
+    }
+
+    virtual scalar distanceToSurfaces(const vector& p) const
+    {
+        return mag(mag(project_ & (p - origin_)) - radius_)*scale_;
+    }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/ellipsoid/ellipsoidImplicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/ellipsoid/ellipsoidImplicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..2732db3136aa745d64e374b9067dbe4e90fd2064
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/ellipsoid/ellipsoidImplicitFunction.C
@@ -0,0 +1,73 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "ellipsoidImplicitFunction.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(ellipsoidImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            ellipsoidImplicitFunction,
+            dict
+        );
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::ellipsoidImplicitFunction::ellipsoidImplicitFunction
+(
+    const vector& semiAxis
+)
+:
+    semiAxis_(semiAxis),
+    origin_(Zero)
+{}
+
+
+Foam::implicitFunctions::ellipsoidImplicitFunction::ellipsoidImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    ellipsoidImplicitFunction
+    (
+        dict.get<vector>("semiAxis")
+    )
+{}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/ellipsoid/ellipsoidImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/ellipsoid/ellipsoidImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..a383c8b8a850fa393292c0c9dae10b3c433cd055
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/ellipsoid/ellipsoidImplicitFunction.H
@@ -0,0 +1,131 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::ellipsoidImplicitFunction
+
+Description
+    creates an ellipsoidImplicitFunction
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    ellipsoidImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_ellipsoidImplicitFunction_H
+#define implicitFunction_ellipsoidImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "mathematicalConstants.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+                  Class ellipsoidImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class ellipsoidImplicitFunction
+:
+    public implicitFunction
+{
+    // Private Member Data
+
+        //- Axis
+        const vector semiAxis_;
+
+        //- Origin point
+        const vector origin_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("ellipsoidImplicitFunction");
+
+
+    // Constructors
+
+        //- Construct from components
+        explicit ellipsoidImplicitFunction(const vector& semiAxis);
+
+        //- Construct from dictionary
+        explicit ellipsoidImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~ellipsoidImplicitFunction() = default;
+
+
+    // Member Functions
+
+    virtual scalar value(const vector& p) const
+    {
+        return
+           -sqrt
+            (
+                sqr((p.x() - origin_.x())/semiAxis_.x())
+              + sqr((p.y() - origin_.y())/semiAxis_.y())
+              + sqr((p.z() - origin_.z())/semiAxis_.z())
+            ) + 1;
+    }
+
+
+    virtual vector grad(const vector& p) const
+    {
+        // normal_ has the length of one
+        return vector
+        (
+            2*(p.x() - origin_.x())/sqr(semiAxis_.x()),
+            2*(p.y() - origin_.y())/sqr(semiAxis_.y()),
+            2*(p.z() - origin_.z())/sqr(semiAxis_.z())
+        );
+    }
+
+    virtual scalar distanceToSurfaces(const vector& p) const
+    {
+        NotImplemented;
+        return GREAT;
+    }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/implicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/implicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..fb5e1220f67ff2073d2c000d0484611344b8a401
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/implicitFunction.C
@@ -0,0 +1,66 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "implicitFunction.H"
+#include "error.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(implicitFunction, 0);
+    defineRunTimeSelectionTable(implicitFunction, dict);
+}
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+Foam::autoPtr<Foam::implicitFunction> Foam::implicitFunction::New
+(
+    const word& implicitFunctionType,
+    const dictionary& dict
+)
+{
+    auto cstrIter = dictConstructorTablePtr_->cfind(implicitFunctionType);
+
+    if (!cstrIter.found())
+    {
+        FatalIOErrorInLookup
+        (
+            dict,
+            "implicitFunction",
+            implicitFunctionType,
+            *dictConstructorTablePtr_
+        ) << exit(FatalIOError);
+    }
+
+    return autoPtr<implicitFunction>(cstrIter()(dict));
+}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/implicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/implicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..14111622d9b28061d967317387caefce79455577
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/implicitFunction.H
@@ -0,0 +1,122 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunction
+
+Description
+    Base class for implicit functions
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    implicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_H
+#define implicitFunction_H
+
+#include "autoPtr.H"
+#include "dictionary.H"
+#include "vector.H"
+#include "runTimeSelectionTables.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                      Class implicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class implicitFunction
+{
+public:
+
+    //- Runtime type information
+    TypeName("implicitFunction");
+
+    //- Declare run-time constructor selection table
+    declareRunTimeSelectionTable
+    (
+        autoPtr,
+        implicitFunction,
+        dict,
+        (
+            const dictionary& dict
+        ),
+        (dict)
+    );
+
+
+    // Constructors
+
+        //- Default construct
+        implicitFunction() = default;
+
+
+        //- Return a reference to the selected implicitFunction
+        static autoPtr<implicitFunction> New
+        (
+            const word& implicitFunctionType,
+            const dictionary& dict
+        );
+
+
+    //- Destructor
+    virtual ~implicitFunction() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& p) const
+        {
+            return GREAT;
+        }
+
+        virtual vector grad(const vector& p) const
+        {
+            return vector::max;
+        }
+
+        virtual scalar distanceToSurfaces(const vector& p) const
+        {
+            return GREAT;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/solvers/multiphase/interIsoFoam/setDeltaT.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/paraboloid/paraboloidImplicitFunction.C
similarity index 59%
rename from applications/solvers/multiphase/interIsoFoam/setDeltaT.H
rename to applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/paraboloid/paraboloidImplicitFunction.C
index ac59647e7e84d66600d81e06cefa8e5a9bd237e9..f2aae0fadd3ff35e18dd148b35e7a1976784ca34 100644
--- a/applications/solvers/multiphase/interIsoFoam/setDeltaT.H
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/paraboloid/paraboloidImplicitFunction.C
@@ -5,7 +5,8 @@
     \\  /    A nd           | www.openfoam.com
      \\/     M anipulation  |
 -------------------------------------------------------------------------------
-    Copyright (C) 2011-2017 OpenFOAM Foundation
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019 DLR
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -23,33 +24,50 @@ License
     You should have received a copy of the GNU General Public License
     along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
 
-Global
-    setDeltaT
+\*---------------------------------------------------------------------------*/
 
-Description
-    Reset the timestep to maintain a constant maximum courant Number.
-    Reduction of time-step is immediate, but increase is damped to avoid
-    unstable oscillations.
+#include "paraboloidImplicitFunction.H"
+#include "addToRunTimeSelectionTable.H"
 
-\*---------------------------------------------------------------------------*/
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
 
-if (adjustTimeStep)
+namespace Foam
 {
-    scalar maxDeltaTFact =
-        min(maxCo/(CoNum + SMALL), maxAlphaCo/(alphaCoNum + SMALL));
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(paraboloidImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            paraboloidImplicitFunction,
+            dict
+        );
+    }
+
+}
 
-    scalar deltaTFact = min(min(maxDeltaTFact, 1.0 + 0.1*maxDeltaTFact), 1.2);
 
-    runTime.setDeltaT
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::paraboloidImplicitFunction::paraboloidImplicitFunction
+(
+    const vector& coeffs
+)
+:
+    coeffs_(coeffs)
+{}
+
+
+Foam::implicitFunctions::paraboloidImplicitFunction::paraboloidImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    paraboloidImplicitFunction
     (
-        min
-        (
-            deltaTFact*runTime.deltaTValue(),
-            maxDeltaT
-        )
-    );
+        dict.get<vector>("coeffs")
+    )
+{}
 
-    Info<< "deltaT = " <<  runTime.deltaTValue() << endl;
-}
 
 // ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/paraboloid/paraboloidImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/paraboloid/paraboloidImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..a25d908f3d38df07cd713e7a82a17ff64b994896
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/paraboloid/paraboloidImplicitFunction.H
@@ -0,0 +1,120 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::paraboloidImplicitFunction
+
+Description
+    creates a paraboloid
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    paraboloidImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_paraboloidImplicitFunction_H
+#define implicitFunction_paraboloidImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "mathematicalConstants.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+                 Class paraboloidImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class paraboloidImplicitFunction
+:
+    public implicitFunction
+{
+    // Private Data
+
+        //- Coefficients of ax^2 + bx*y + cy^2
+        const vector coeffs_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("paraboloid");
+
+
+    // Constructors
+
+        //- Construct from components
+        explicit paraboloidImplicitFunction(const vector& coeffs);
+
+        //- Construct from dictionary
+        explicit paraboloidImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~paraboloidImplicitFunction() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& p) const
+        {
+            return
+                coeffs_.x()*sqr(p.x())
+              + coeffs_.y()*p.x()*p.y()
+              + coeffs_.z()*sqr(p.y())
+              - p.z();
+        }
+
+        virtual vector grad(const vector& p) const
+        {
+            NotImplemented;
+            return Zero;
+        }
+
+        virtual scalar distanceToSurfaces(const vector& p) const
+        {
+            NotImplemented;
+            return 0;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/plane/planeImplicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/plane/planeImplicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..d1bb0afac4accb66a878a662a72eb18e33683330
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/plane/planeImplicitFunction.C
@@ -0,0 +1,75 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "planeImplicitFunction.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(planeImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            planeImplicitFunction,
+            dict
+        );
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::planeImplicitFunction::planeImplicitFunction
+(
+    const vector& origin,
+    const vector& normal
+)
+:
+    origin_(origin),
+    normal_(normalised(normal))
+{}
+
+
+Foam::implicitFunctions::planeImplicitFunction::planeImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    planeImplicitFunction
+    (
+        dict.get<vector>("origin"),
+        dict.get<vector>("normal")
+    )
+{}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/plane/planeImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/plane/planeImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..a89f603cb5cd3534e949e3f3b3b7484e8c1fa568
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/plane/planeImplicitFunction.H
@@ -0,0 +1,120 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::planeImplicitFunction
+
+Description
+    creates a plane
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    planeImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_planeImplicitFunction_H
+#define implicitFunction_planeImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "mathematicalConstants.H"
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+                    Class planeImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class planeImplicitFunction
+:
+    public implicitFunction
+{
+    // Private Data
+
+        //- Reference point
+        const vector origin_;
+
+        //- Unit-normal vector
+        const vector normal_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("plane");
+
+
+    // Constructors
+
+        //- Construct from components
+        planeImplicitFunction(const vector& origin, const vector& normal);
+
+        //- Construct from dictionary (used by implicitFunctions)
+        explicit planeImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~planeImplicitFunction() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& p) const
+        {
+            return -normal_ & (origin_ - p);
+        }
+
+        virtual vector grad(const vector& p) const
+        {
+            // normal_ has the length of one
+            return normal_;
+        }
+
+        virtual scalar distanceToSurfaces(const vector& p) const
+        {
+            // normal_ has the length of one
+            return mag((p - origin_) & -normal_);
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sin/sinImplicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sin/sinImplicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..a193d2b663b36f9d49a4cd3b4a2f66840ccf615e
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sin/sinImplicitFunction.C
@@ -0,0 +1,87 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "sinImplicitFunction.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(sinImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            sinImplicitFunction,
+            dict
+        );
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::sinImplicitFunction::sinImplicitFunction
+(
+    const scalar period,
+    const scalar phase,
+    const scalar amplitude,
+    const vector& direction,
+    const vector& up,
+    const vector& origin
+)
+:
+    period_(period),
+    phase_(phase),
+    amplitude_(amplitude),
+    up_(normalised(up)),
+    direction_(normalised(direction)),
+    origin_(origin)
+{}
+
+
+Foam::implicitFunctions::sinImplicitFunction::sinImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    sinImplicitFunction
+    (
+        dict.get<scalar>("period"),
+        dict.getOrDefault<scalar>("phase", 0),
+        dict.get<scalar>("amplitude"),
+        dict.get<vector>("direction"),
+        dict.get<vector>("up"),
+        dict.get<vector>("origin")
+    )
+{}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sin/sinImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sin/sinImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..588c20d5e98993266c771164bdd77464dcf131d2
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sin/sinImplicitFunction.H
@@ -0,0 +1,142 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::sinImplicitFunction
+
+Description
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    sinImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_sinImplicitFunction_H
+#define implicitFunction_sinImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "mathematicalConstants.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+                     Class sinImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class sinImplicitFunction
+:
+    public implicitFunction
+{
+private:
+
+    // Private Data
+
+        //- Origin point
+        const scalar period_;
+
+        //- Radius
+        const scalar phase_;
+
+        const scalar amplitude_;
+
+        const vector up_;
+
+        const vector direction_;
+
+        const vector origin_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("sin");
+
+
+    // Constructors
+
+        //- Construct from components
+        sinImplicitFunction
+        (
+            const scalar period,
+            const scalar phase,
+            const scalar amplitude,
+            const vector& direction,
+            const vector& up,
+            const vector& origin
+        );
+
+        //- Construct from dictionary (used by implicitFunctions)
+        explicit sinImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~sinImplicitFunction() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& p) const
+        {
+            const scalar x = (p - origin_) & direction_;
+            const scalar z = (p - origin_) & -up_;
+
+            return
+                z
+              - amplitude_
+               *Foam::sin(2*constant::mathematical::pi*x/period_ + phase_);
+        }
+
+        virtual vector grad(const vector& p) const
+        {
+            NotImplemented;
+            return Zero;
+        }
+
+        virtual scalar distanceToSurfaces(const vector& p) const
+        {
+            NotImplemented;
+            return 0;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sphere/sphereImplicitFunction.C b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sphere/sphereImplicitFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..48a26c3b383753005ab654428e97de9f8d453496
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sphere/sphereImplicitFunction.C
@@ -0,0 +1,78 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "sphereImplicitFunction.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    namespace implicitFunctions
+    {
+        defineTypeNameAndDebug(sphereImplicitFunction, 0);
+        addToRunTimeSelectionTable
+        (
+            implicitFunction,
+            sphereImplicitFunction,
+            dict
+        );
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::implicitFunctions::sphereImplicitFunction::sphereImplicitFunction
+(
+    const point& origin,
+    const scalar radius,
+    const scalar scale
+)
+:
+    origin_(origin),
+    radius_(radius),
+    scale_(scale)
+{}
+
+
+Foam::implicitFunctions::sphereImplicitFunction::sphereImplicitFunction
+(
+    const dictionary& dict
+)
+:
+    sphereImplicitFunction
+    (
+        dict.get<point>("origin"),
+        dict.get<scalar>("radius"),
+        dict.getOrDefault<scalar>("scale", 1)
+    )
+{}
+
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sphere/sphereImplicitFunction.H b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sphere/sphereImplicitFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..93ee773d3d4c393aa552f96447d233322698a69e
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/alphaFieldFunctions/implicitFunctions/sphere/sphereImplicitFunction.H
@@ -0,0 +1,124 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::implicitFunctions::sphereImplicitFunction
+
+Description
+    Creates a sphere
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    sphereImplicitFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef implicitFunction_sphereImplicitFunction_H
+#define implicitFunction_sphereImplicitFunction_H
+
+#include "implicitFunction.H"
+#include "point.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace implicitFunctions
+{
+
+/*---------------------------------------------------------------------------*\
+                   Class sphereImplicitFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class sphereImplicitFunction
+:
+    public implicitFunction
+{
+    // Private Data
+
+        //- Origin point
+        const point origin_;
+
+        //- Radius
+        const scalar radius_;
+
+        const scalar scale_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("sphere");
+
+
+    // Constructors
+
+        //- Construct from components
+        sphereImplicitFunction
+        (
+            const point&,
+            const scalar radius,
+            const scalar scale
+        );
+
+        //- Construct from dictionary
+        explicit sphereImplicitFunction(const dictionary& dict);
+
+
+    //- Destructor
+    virtual ~sphereImplicitFunction() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& p) const
+        {
+            return (-mag(p - origin_) + radius_)*scale_;
+        }
+
+        virtual vector grad(const vector& p) const
+        {
+            return (origin_ - p)*scale_;
+        }
+
+        virtual scalar distanceToSurfaces(const vector& p) const
+        {
+            return mag(mag(p - origin_) - radius_)*scale_;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace implicitFunctions
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/utilities/preProcessing/setAlphaField/setAlphaField.C b/applications/utilities/preProcessing/setAlphaField/setAlphaField.C
index dc343ab657e18a302078f83b18fb2c00c79f8158..82e37fac64827a79d924a934484c9059582539aa 100644
--- a/applications/utilities/preProcessing/setAlphaField/setAlphaField.C
+++ b/applications/utilities/preProcessing/setAlphaField/setAlphaField.C
@@ -7,6 +7,7 @@
 -------------------------------------------------------------------------------
     Copyright (C) 2016-2017 DHI
     Copyright (C) 2017-2020 OpenCFD Ltd.
+    Copyright (c) 2017-2020, German Aerospace Center (DLR)
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -28,86 +29,94 @@ Application
     setAlphaField
 
 Description
-    Uses isoCutCell to create a volume fraction field from either a cylinder,
+    Uses cutCellIso to create a volume fraction field from either a cylinder,
     a sphere or a plane.
 
     Original code supplied by Johan Roenby, DHI (2016)
+    Modification Henning Scheufler, DLR (2019)
 
 \*---------------------------------------------------------------------------*/
 
 #include "fvCFD.H"
-#include "isoCutFace.H"
-#include "isoCutCell.H"
-#include "Enum.H"
-#include "mathematicalConstants.H"
 
-using namespace Foam::constant;
+#include "triSurface.H"
+#include "triSurfaceTools.H"
+
+#include "implicitFunction.H"
+
+#include "cutCellIso.H"
+#include "OBJstream.H"
+
 
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
 
-class shapeSelector
+void isoFacesToFile
+(
+    const DynamicList<List<point>>& faces,
+    const word& fileName
+)
 {
-    public:
+    // Writing isofaces to OBJ file for inspection in paraview
+    OBJstream os(fileName + ".obj");
 
-        enum class shapeType
-        {
-            PLANE,
-            SPHERE,
-            CYLINDER,
-            SIN
-        };
-
-    static const Foam::Enum<shapeType> shapeTypeNames;
-};
+    if (Pstream::parRun())
+    {
+        // Collect points from all the processors
+        List<DynamicList<List<point>>> allProcFaces(Pstream::nProcs());
+        allProcFaces[Pstream::myProcNo()] = faces;
+        Pstream::gatherList(allProcFaces);
 
+        if (Pstream::master())
+        {
+            Info<< "Writing file: " << fileName << endl;
+
+            for (const DynamicList<List<point>>& procFaces : allProcFaces)
+            {
+                for (const List<point>& facePts : procFaces)
+                {
+                    os.write(face(identity(facePts.size())), facePts);
+                }
+            }
+        }
+    }
+    else
+    {
+        Info<< "Writing file: " << fileName << endl;
 
-const Foam::Enum
-<
-    shapeSelector::shapeType
->
-shapeSelector::shapeTypeNames
-({
-    { shapeSelector::shapeType::PLANE, "plane" },
-    { shapeSelector::shapeType::SPHERE, "sphere" },
-    { shapeSelector::shapeType::CYLINDER, "cylinder" },
-    { shapeSelector::shapeType::SIN, "sin" },
-});
+        for (const List<point>& facePts : faces)
+        {
+            os.write(face(identity(facePts.size())), facePts);
+        }
+    }
+}
 
 
 int main(int argc, char *argv[])
 {
     argList::addNote
     (
-        "Uses isoCutCell to create a volume fraction field from a"
-        " cylinder, sphere or a plane."
+        "Uses cutCellIso to create a volume fraction field from an "
+        "implicit function."
     );
 
+    #include "addDictOption.H"
+    #include "addRegionOption.H"
     #include "setRootCase.H"
     #include "createTime.H"
     #include "createNamedMesh.H"
 
-    Info<< "Reading setAlphaFieldDict\n" << endl;
+    const word dictName("setAlphaFieldDict");
+    #include "setSystemMeshDictionaryIO.H"
 
-    IOdictionary dict
-    (
-        IOobject
-        (
-            "setAlphaFieldDict",
-            runTime.system(),
-            mesh,
-            IOobject::MUST_READ,
-            IOobject::NO_WRITE
-        )
-    );
+    IOdictionary setAlphaFieldDict(dictIO);
 
-    const shapeSelector::shapeType surfType
-    (
-        shapeSelector::shapeTypeNames.get("type", dict)
-    );
-    const vector origin(dict.getCompat<vector>("origin", {{"centre", 1806}}));
-    const word fieldName(dict.get<word>("field"));
+    Info<< "Reading " << setAlphaFieldDict.name() << endl;
+
+    const word fieldName = setAlphaFieldDict.get<word>("field");
+    const bool invert = setAlphaFieldDict.getOrDefault("invert", false);
+    const bool writeOBJ = setAlphaFieldDict.getOrDefault("writeOBJ", false);
 
-    Info<< "Reading field " << fieldName << "\n" << endl;
+    Info<< "Reading field " << fieldName << nl << endl;
     volScalarField alpha1
     (
         IOobject
@@ -121,85 +130,76 @@ int main(int argc, char *argv[])
         mesh
     );
 
-    scalar f0 = 0;
-    scalarField f(mesh.points().size());
+    autoPtr<implicitFunction> func = implicitFunction::New
+    (
+        setAlphaFieldDict.get<word>("type"),
+        setAlphaFieldDict
+    );
 
-    Info<< "Processing type '" << shapeSelector::shapeTypeNames[surfType]
-        << "'" << endl;
+    scalarField f(mesh.nPoints(), Zero);
 
-    switch (surfType)
+    forAll(f, pi)
     {
-        case shapeSelector::shapeType::PLANE:
-        {
-            const vector direction(dict.get<vector>("direction"));
+        f[pi] = func->value(mesh.points()[pi]);
+    };
 
-            f = -(mesh.points() - origin) & (direction/mag(direction));
-            f0 = 0;
-            break;
-        }
-        case shapeSelector::shapeType::SPHERE:
-        {
-            const scalar radius(dict.get<scalar>("radius"));
+    cutCellIso cutCell(mesh, f);
+
+    DynamicList<List<point>> facePts;
+
+    DynamicList<triSurface> surface;
+
+    surfaceScalarField cellToCellDist(mag(mesh.delta()));
 
-            f = -mag(mesh.points() - origin);
-            f0 = -radius;
-            break;
+    forAll(alpha1, cellI)
+    {
+        label cellStatus = cutCell.calcSubCell(cellI, 0.0);
+
+        if (cellStatus == -1)
+        {
+            alpha1[cellI] = 1;
         }
-        case shapeSelector::shapeType::CYLINDER:
+        else if (cellStatus == 1)
         {
-            const scalar radius(dict.get<scalar>("radius"));
-            const vector direction(dict.get<vector>("direction"));
-
-            f = -sqrt
-            (
-                sqr(mag(mesh.points() - origin))
-              - sqr(mag((mesh.points() - origin) & direction))
-            );
-            f0 = -radius;
-            break;
+            alpha1[cellI] = 0;
         }
-        case shapeSelector::shapeType::SIN:
+        else if (cellStatus == 0)
         {
-            const scalar period(dict.get<scalar>("period"));
-            const scalar amplitude(dict.get<scalar>("amplitude"));
-            const vector up(dict.get<vector>("up"));
-            const vector direction(dict.get<vector>("direction"));
-
-            const scalarField xx
-            (
-                (mesh.points() - origin) & direction/mag(direction)
-            );
-            const scalarField zz((mesh.points() - origin) & up/mag(up));
-
-            f = amplitude*Foam::sin(2*mathematical::pi*xx/period) - zz;
-            f0 = 0;
-            break;
+            if (mag(cutCell.faceArea()) != 0)
+            {
+                alpha1[cellI] = max(min(cutCell.VolumeOfFluid(), 1), 0);
+                if (writeOBJ && (mag(cutCell.faceArea()) >= 1e-14))
+                {
+                    facePts.append(cutCell.facePoints());
+                }
+            }
         }
     }
 
+    if (writeOBJ)
+    {
+        isoFacesToFile(facePts, fieldName + "0");
+    }
 
-    // Define function on mesh points and isovalue
-
-    // Calculating alpha1 volScalarField from f = f0 isosurface
-    isoCutCell icc(mesh, f);
-    icc.volumeOfFluid(alpha1, f0);
+    ISstream::defaultPrecision(18);
 
-    if (dict.getOrDefault("invertAlpha", false))
+    if (invert)
     {
-        alpha1 = 1 - alpha1;
+        alpha1 = scalar(1) - alpha1;
     }
 
-    // Writing volScalarField alpha1
-    ISstream::defaultPrecision(18);
+    alpha1.correctBoundaryConditions();
+
+    Info<< "Writing new alpha field " << alpha1.name() << endl;
     alpha1.write();
 
-    Info<< nl << "Phase-1 volume fraction = "
-        << alpha1.weightedAverage(mesh.Vsc()).value()
-        << "  Min(" << alpha1.name() << ") = " << min(alpha1).value()
-        << "  Max(" << alpha1.name() << ") - 1 = " << max(alpha1).value() - 1
-        << nl << endl;
+    const scalarField& alpha = alpha1.internalField();
+
+    Info<< "sum(alpha*V):" << gSum(mesh.V()*alpha)
+        << ", 1-max(alpha1): " << 1 - gMax(alpha)
+        << " min(alpha1): " << gMin(alpha) << endl;
 
-    Info<< "End\n" << endl;
+    Info<< "\nEnd\n" << endl;
 
     return 0;
 }
diff --git a/applications/utilities/preProcessing/setAlphaField/setAlphaFieldDict b/applications/utilities/preProcessing/setAlphaField/setAlphaFieldDict
new file mode 100644
index 0000000000000000000000000000000000000000..dcd253a205a0e6a0d7c4d4039ceac4b84ac08169
--- /dev/null
+++ b/applications/utilities/preProcessing/setAlphaField/setAlphaFieldDict
@@ -0,0 +1,48 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v1912                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+field "alpha.water";
+
+type composedFunction;
+mode add;
+composedFunctions
+{
+    plane
+    {
+        type plane;
+        centre (0 1. 0);
+        normal (0 1 0);
+    }
+
+    sphere
+    {
+        type sphere;
+        radius 0.4;
+        centre (0.5 0.8 0.5);
+        scale 1;
+    }
+
+    sphere2
+    {
+        type sphere;
+        radius 0.4;
+        centre (0.5 0.5 0.5);
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/Allwmake b/src/Allwmake
index c2baebc1cae14eefe1630fb340a44e8948f29bd1..57fae7ae8fefa92d570a93153bb3886f99c49899 100755
--- a/src/Allwmake
+++ b/src/Allwmake
@@ -71,12 +71,13 @@ parallel/Allwmake $targetType $*
 wmake $targetType dynamicFvMesh
 wmake $targetType topoChangerFvMesh
 
+transportModels/Allwmake $targetType $*
 wmake $targetType sampling
 randomProcesses/Allwmake $targetType $*
 
 wmake $targetType ODE
 
-transportModels/Allwmake $targetType $*
+
 thermophysicalModels/Allwmake $targetType $*
 TurbulenceModels/Allwmake $targetType $*
 wmake $targetType combustionModels
diff --git a/src/finiteVolume/Make/files b/src/finiteVolume/Make/files
index eef2fd9473fac9a45f8e4b7dcd0a782e9ab4af73..6a0bf5c8fa791c11e0ff223eab504b82fb343f96 100644
--- a/src/finiteVolume/Make/files
+++ b/src/finiteVolume/Make/files
@@ -93,6 +93,10 @@ $(faceToCell)/extendedFaceToCellStencil.C
 $(faceToCell)/extendedCentredFaceToCellStencil.C
 $(faceToCell)/MeshObjects/centredCFCFaceToCellStencilObject.C
 
+fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.C
+fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.C
+fvMesh/zoneDistribute/zoneDistribute.C
+
 functionObjects/fvMeshFunctionObject/fvMeshFunctionObject.C
 functionObjects/volRegion/volRegion.C
 functionObjects/fieldSelections/fieldSelection/fieldSelection.C
@@ -286,11 +290,13 @@ $(fieldExpr)/pointPatchFields/exprValuePointPatchFields.C
 fvMatrices/fvMatrices.C
 fvMatrices/fvScalarMatrix/fvScalarMatrix.C
 fvMatrices/solvers/MULES/MULES.C
-fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.C
-fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.C
-fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.C
 fvMatrices/solvers/GAMGSymSolver/GAMGAgglomerations/faceAreaPairGAMGAgglomeration/faceAreaPairGAMGAgglomeration.C
 
+fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.C
+fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.C
+fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.C
+fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.C
+
 interpolation = interpolation/interpolation
 $(interpolation)/interpolation/interpolations.C
 
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.C b/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.C
deleted file mode 100644
index 5a57e54a17feb7c56a94ba7b436dce997e9db101..0000000000000000000000000000000000000000
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.C
+++ /dev/null
@@ -1,1041 +0,0 @@
-/*---------------------------------------------------------------------------*\
-  =========                 |
-  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
-   \\    /   O peration     |
-    \\  /    A nd           | www.openfoam.com
-     \\/     M anipulation  |
--------------------------------------------------------------------------------
-    Copyright (C) 2016-2017 DHI
-    Copyright (C) 2016-2020 OpenCFD Ltd.
-    Copyright (C) 2019 Johan Roenby
--------------------------------------------------------------------------------
-License
-    This file is part of OpenFOAM.
-
-    OpenFOAM is free software: you can redistribute it and/or modify it
-    under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
-    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-    for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
-
-\*---------------------------------------------------------------------------*/
-
-#include "isoAdvection.H"
-#include "volFields.H"
-#include "interpolationCellPoint.H"
-#include "volPointInterpolation.H"
-#include "fvcSurfaceIntegrate.H"
-#include "fvcGrad.H"
-#include "upwind.H"
-#include "cellSet.H"
-#include "meshTools.H"
-#include "OBJstream.H"
-
-// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
-
-namespace Foam
-{
-    defineTypeNameAndDebug(isoAdvection, 0);
-}
-
-// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
-
-Foam::isoAdvection::isoAdvection
-(
-    volScalarField& alpha1,
-    const surfaceScalarField& phi,
-    const volVectorField& U
-)
-:
-    // General data
-    mesh_(alpha1.mesh()),
-    dict_(mesh_.solverDict(alpha1.name())),
-    alpha1_(alpha1),
-    alpha1In_(alpha1.ref()),
-    phi_(phi),
-    U_(U),
-    dVf_
-    (
-        IOobject
-        (
-            "dVf_",
-            mesh_.time().timeName(),
-            mesh_,
-            IOobject::NO_READ,
-            IOobject::NO_WRITE
-        ),
-        mesh_,
-        dimensionedScalar(dimVol, Zero)
-    ),
-    advectionTime_(0),
-
-    // Interpolation data
-    ap_(mesh_.nPoints()),
-
-    // Tolerances and solution controls
-    nAlphaBounds_(dict_.getOrDefault<label>("nAlphaBounds", 3)),
-    isoFaceTol_(dict_.getOrDefault<scalar>("isoFaceTol", 1e-8)),
-    surfCellTol_(dict_.getOrDefault<scalar>("surfCellTol", 1e-8)),
-    gradAlphaBasedNormal_(dict_.getOrDefault("gradAlphaNormal", false)),
-    writeIsoFacesToFile_(dict_.getOrDefault("writeIsoFaces", false)),
-
-    // Cell cutting data
-    surfCells_(label(0.2*mesh_.nCells())),
-    isoCutCell_(mesh_, ap_),
-    isoCutFace_(mesh_, ap_),
-    cellIsBounded_(mesh_.nCells(), false),
-    checkBounding_(mesh_.nCells(), false),
-    bsFaces_(label(0.2*mesh_.nBoundaryFaces())),
-    bsx0_(bsFaces_.size()),
-    bsn0_(bsFaces_.size()),
-    bsUn0_(bsFaces_.size()),
-    bsf0_(bsFaces_.size()),
-
-    // Parallel run data
-    procPatchLabels_(mesh_.boundary().size()),
-    surfaceCellFacesOnProcPatches_(0)
-{
-    isoCutCell::debug = debug;
-    isoCutFace::debug = debug;
-
-    // Prepare lists used in parallel runs
-    if (Pstream::parRun())
-    {
-        // Force calculation of required demand driven data (else parallel
-        // communication may crash)
-        mesh_.cellCentres();
-        mesh_.cellVolumes();
-        mesh_.faceCentres();
-        mesh_.faceAreas();
-        mesh_.magSf();
-        mesh_.boundaryMesh().patchID();
-        mesh_.cellPoints();
-        mesh_.cellCells();
-        mesh_.cells();
-
-        // Get boundary mesh and resize the list for parallel comms
-        const polyBoundaryMesh& patches = mesh_.boundaryMesh();
-
-        surfaceCellFacesOnProcPatches_.resize(patches.size());
-
-        // Append all processor patch labels to the list
-        forAll(patches, patchi)
-        {
-            if
-            (
-                isA<processorPolyPatch>(patches[patchi])
-             && patches[patchi].size() > 0
-            )
-            {
-                procPatchLabels_.append(patchi);
-            }
-        }
-    }
-}
-
-
-// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
-
-void Foam::isoAdvection::timeIntegratedFlux()
-{
-    // Get time step
-    const scalar dt = mesh_.time().deltaTValue();
-
-    // Create object for interpolating velocity to isoface centres
-    interpolationCellPoint<vector> UInterp(U_);
-
-    // For each downwind face of each surface cell we "isoadvect" to find dVf
-    label nSurfaceCells = 0;
-
-    // Clear out the data for re-use and reset list containing information
-    // whether cells could possibly need bounding
-    clearIsoFaceData();
-
-    // Get necessary references
-    const scalarField& phiIn = phi_.primitiveField();
-    const scalarField& magSfIn = mesh_.magSf().primitiveField();
-    scalarField& dVfIn = dVf_.primitiveFieldRef();
-
-    // Get necessary mesh data
-    const cellList& cellFaces = mesh_.cells();
-    const labelList& own = mesh_.faceOwner();
-    const labelList& nei = mesh_.faceNeighbour();
-    const labelListList& cellCells = mesh_.cellCells();
-
-    // Calculate alpha vertex values, ap_, or cell normals (used to get
-    // interface-vertex distance function if gradAlphaBasedNormal_)
-    volVectorField cellNormals("cellN", fvc::grad(alpha1_));
-    if (gradAlphaBasedNormal_)
-    {
-        // Calculate gradient of alpha1 and normalise and smoothen it.
-        normaliseAndSmooth(cellNormals);
-    }
-    else
-    {
-        // Interpolating alpha1 cell centre values to mesh points (vertices)
-        ap_ = volPointInterpolation::New(mesh_).interpolate(alpha1_);
-    }
-
-    // Storage for isoFace points. Only used if writeIsoFacesToFile_
-    DynamicList<List<point>> isoFacePts;
-
-    // Loop through all cells
-    forAll(alpha1In_, celli)
-    {
-        // If not a surface cell continue to next cell
-        if (!isASurfaceCell(celli)) continue;
-
-        // This is a surface cell, increment counter, append and mark cell
-        // Note: We also have the cellStatus below where the cell might not have
-        // an isoface. So maybe the counter and append should be put there.
-        nSurfaceCells++;
-        surfCells_.append(celli);
-        checkBounding_[celli] = true;
-
-        DebugInfo
-            << "\n------------ Cell " << celli << " with alpha1 = "
-            << alpha1In_[celli] << " and 1-alpha1 = "
-            << 1.0 - alpha1In_[celli] << " ------------"
-            << endl;
-
-        if (gradAlphaBasedNormal_)
-        {
-            vectorField& cellNormalsIn = cellNormals.primitiveFieldRef();
-            setCellVertexValues(celli, cellNormalsIn);
-        }
-
-        // Calculate isoFace centre x0, normal n0 at time t
-
-        // Calculate cell status (-1: cell is fully below the isosurface, 0:
-        // cell is cut, 1: cell is fully above the isosurface)
-        label maxIter = 100; // NOTE: make it a debug switch
-        label cellStatus = isoCutCell_.vofCutCell
-        (
-            celli,
-            alpha1In_[celli],
-            isoFaceTol_,
-            maxIter
-        );
-
-        // If cell is not cut move on to next cell
-        if (cellStatus != 0) continue;
-
-        // If cell is cut calculate isoface unit normal
-        const scalar f0(isoCutCell_.isoValue());
-        const point& x0(isoCutCell_.isoFaceCentre());
-        vector n0(isoCutCell_.isoFaceArea());
-        n0 /= (mag(n0));
-
-        if (writeIsoFacesToFile_ && mesh_.time().writeTime())
-        {
-            isoFacePts.append(isoCutCell_.isoFacePoints());
-        }
-
-        // Get the speed of the isoface by interpolating velocity and
-        // dotting it with isoface unit normal
-        const scalar Un0 = UInterp.interpolate(x0, celli) & n0;
-
-        DebugInfo
-            << "calcIsoFace gives initial surface: \nx0 = " << x0
-            << ", \nn0 = " << n0 << ", \nf0 = " << f0 << ", \nUn0 = "
-            << Un0 << endl;
-
-        // Estimate time integrated flux through each downwind face
-        // Note: looping over all cell faces - in reduced-D, some of
-        //       these faces will be on empty patches
-        const cell& celliFaces = cellFaces[celli];
-        forAll(celliFaces, fi)
-        {
-            const label facei = celliFaces[fi];
-
-            if (mesh_.isInternalFace(facei))
-            {
-                bool isDownwindFace = false;
-                label otherCell = -1;
-
-                if (celli == own[facei])
-                {
-                    if (phiIn[facei] > 10*SMALL)
-                    {
-                        isDownwindFace = true;
-                    }
-
-                    otherCell = nei[facei];
-                }
-                else
-                {
-                    if (phiIn[facei] < -10*SMALL)
-                    {
-                        isDownwindFace = true;
-                    }
-
-                    otherCell = own[facei];
-                }
-
-                if (isDownwindFace)
-                {
-                    dVfIn[facei] = isoCutFace_.timeIntegratedFaceFlux
-                    (
-                        facei,
-                        x0,
-                        n0,
-                        Un0,
-                        f0,
-                        dt,
-                        phiIn[facei],
-                        magSfIn[facei]
-                    );
-                }
-
-                // We want to check bounding of neighbour cells to
-                // surface cells as well:
-                checkBounding_[otherCell] = true;
-
-                // Also check neighbours of neighbours.
-                // Note: consider making it a run time selectable
-                // extension level (easily done with recursion):
-                // 0 - only neighbours
-                // 1 - neighbours of neighbours
-                // 2 - ...
-                // Note: We will like all point neighbours to interface cells to
-                // be checked. Especially if the interface leaves a cell during
-                // a time step, it may enter a point neighbour which should also
-                // be treated like a surface cell. Its interface normal should
-                // somehow be inherrited from its upwind cells from which it
-                // receives the interface.
-                const labelList& nNeighbourCells = cellCells[otherCell];
-                forAll(nNeighbourCells, ni)
-                {
-                    checkBounding_[nNeighbourCells[ni]] = true;
-                }
-            }
-            else
-            {
-                bsFaces_.append(facei);
-                bsx0_.append(x0);
-                bsn0_.append(n0);
-                bsUn0_.append(Un0);
-                bsf0_.append(f0);
-
-                // Note: we must not check if the face is on the
-                // processor patch here.
-            }
-        }
-    }
-
-    // Get references to boundary fields
-    const polyBoundaryMesh& boundaryMesh = mesh_.boundaryMesh();
-    const surfaceScalarField::Boundary& phib = phi_.boundaryField();
-    const surfaceScalarField::Boundary& magSfb = mesh_.magSf().boundaryField();
-    surfaceScalarField::Boundary& dVfb = dVf_.boundaryFieldRef();
-    const label nInternalFaces = mesh_.nInternalFaces();
-
-    // Loop through boundary surface faces
-    forAll(bsFaces_, i)
-    {
-        // Get boundary face index (in the global list)
-        const label facei = bsFaces_[i];
-        const label patchi = boundaryMesh.patchID()[facei - nInternalFaces];
-        const label start = boundaryMesh[patchi].start();
-
-        if (phib[patchi].size())
-        {
-            const label patchFacei = facei - start;
-            const scalar phiP = phib[patchi][patchFacei];
-
-            if (phiP > 10*SMALL)
-            {
-                const scalar magSf = magSfb[patchi][patchFacei];
-
-                dVfb[patchi][patchFacei] = isoCutFace_.timeIntegratedFaceFlux
-                (
-                    facei,
-                    bsx0_[i],
-                    bsn0_[i],
-                    bsUn0_[i],
-                    bsf0_[i],
-                    dt,
-                    phiP,
-                    magSf
-                );
-
-                // Check if the face is on processor patch and append it to
-                // the list if necessary
-                checkIfOnProcPatch(facei);
-            }
-        }
-    }
-
-    // Synchronize processor patches
-    syncProcPatches(dVf_, phi_);
-
-    writeIsoFaces(isoFacePts);
-
-    Info<< "Number of isoAdvector surface cells = "
-        << returnReduce(nSurfaceCells, sumOp<label>()) << endl;
-}
-
-
-void Foam::isoAdvection::setCellVertexValues
-(
-    const label celli,
-    const vectorField& cellNormalsIn
-)
-{
-    const labelListList& cellPoints = mesh_.cellPoints();
-    const vectorField& cellCentres = mesh_.cellCentres();
-    const pointField& points = mesh_.points();
-    const labelList& cp = cellPoints[celli];
-    const point& cellCentre = cellCentres[celli];
-    forAll(cp, vi)
-    {
-        const point& vertex = points[cp[vi]];
-        ap_[cp[vi]] = (vertex - cellCentre) & cellNormalsIn[celli];
-    }
-}
-
-
-void Foam::isoAdvection::normaliseAndSmooth
-(
-    volVectorField& cellN
-)
-{
-    const labelListList& cellPoints = mesh_.cellPoints();
-    const vectorField& cellCentres = mesh_.cellCentres();
-    const pointField& points = mesh_.points();
-
-    vectorField& cellNIn = cellN.primitiveFieldRef();
-    cellNIn /= (mag(cellNIn) + SMALL);
-    vectorField vertexN(mesh_.nPoints(), Zero);
-    vertexN = volPointInterpolation::New(mesh_).interpolate(cellN);
-    vertexN /= (mag(vertexN) + SMALL);
-    // Interpolate vertex normals back to cells
-    forAll(cellNIn, celli)
-    {
-        const labelList& cp = cellPoints[celli];
-        vector cellNi(Zero);
-        const point& cellCentre = cellCentres[celli];
-        forAll(cp, pointI)
-        {
-            point vertex = points[cp[pointI]];
-            scalar w = 1.0/mag(vertex - cellCentre);
-            cellNi += w*vertexN[cp[pointI]];
-        }
-        cellNIn[celli] = cellNi/(mag(cellNi) + SMALL);
-    }
-}
-
-
-void Foam::isoAdvection::setDownwindFaces
-(
-    const label celli,
-    DynamicLabelList& downwindFaces
-) const
-{
-    DebugInFunction << endl;
-
-    // Get necessary mesh data and cell information
-    const labelList& own = mesh_.faceOwner();
-    const cellList& cells = mesh_.cells();
-    const cell& c = cells[celli];
-
-    downwindFaces.clear();
-
-    // Check all faces of the cell
-    forAll(c, fi)
-    {
-        // Get face and corresponding flux
-        const label facei = c[fi];
-        const scalar phi = faceValue(phi_, facei);
-
-        if (own[facei] == celli)
-        {
-            if (phi > 10*SMALL)
-            {
-                downwindFaces.append(facei);
-            }
-        }
-        else if (phi < -10*SMALL)
-        {
-            downwindFaces.append(facei);
-        }
-    }
-
-    downwindFaces.shrink();
-}
-
-
-void Foam::isoAdvection::limitFluxes()
-{
-    DebugInFunction << endl;
-
-    // Get time step size
-    const scalar dt = mesh_.time().deltaT().value();
-
-    volScalarField alphaNew(alpha1_ - fvc::surfaceIntegrate(dVf_));
-    const scalar aTol = 1.0e-12;          // Note: tolerances
-    scalar maxAlphaMinus1 = gMax(alphaNew) - 1;      // max(alphaNew - 1);
-    scalar minAlpha = gMin(alphaNew);           // min(alphaNew);
-    const label nUndershoots = 20;        // sum(neg0(alphaNew + aTol));
-    const label nOvershoots = 20;         // sum(pos0(alphaNew - 1 - aTol));
-    cellIsBounded_ = false;
-
-    Info << "isoAdvection: Before conservative bounding: min(alpha) = "
-        << minAlpha << ", max(alpha) = 1 + " << maxAlphaMinus1 << endl;
-
-    // Loop number of bounding steps
-    for (label n = 0; n < nAlphaBounds_; n++)
-    {
-        if (maxAlphaMinus1 > aTol) // Note: tolerances
-        {
-            DebugInfo << "Bound from above... " << endl;
-
-//          scalarField& dVfcorrected = dVf_.primitiveFieldRef();
-
-            surfaceScalarField dVfcorrected("dVfcorrected", dVf_);
-            DynamicList<label> correctedFaces(3*nOvershoots);
-            boundFromAbove(alpha1In_, dVfcorrected, correctedFaces);
-
-            forAll(correctedFaces, fi)
-            {
-                label facei = correctedFaces[fi];
-
-                // Change to treat boundaries consistently
-                setFaceValue(dVf_, facei, faceValue(dVfcorrected, facei));
-            }
-
-            syncProcPatches(dVf_, phi_);
-        }
-
-        if (minAlpha < -aTol) // Note: tolerances
-        {
-            DebugInfo << "Bound from below... " << endl;
-
-            scalarField alpha2(1.0 - alpha1In_);
-            surfaceScalarField dVfcorrected
-            (
-                "dVfcorrected",
-                phi_*dimensionedScalar("dt", dimTime, dt) - dVf_
-            );
-//          dVfcorrected -= dVf_;   // phi_ and dVf_ have same sign and dVf_ is
-                                    // the portion of phi_*dt that is water.
-            // If phi_ > 0 then dVf_ > 0 and mag(phi_*dt-dVf_) < mag(phi_*dt) as
-            // it should.
-            // If phi_ < 0 then dVf_ < 0 and mag(phi_*dt-dVf_) < mag(phi_*dt) as
-            // it should.
-            DynamicList<label> correctedFaces(3*nUndershoots);
-            boundFromAbove(alpha2, dVfcorrected, correctedFaces);
-            forAll(correctedFaces, fi)
-            {
-                label facei = correctedFaces[fi];
-
-                // Change to treat boundaries consistently
-                scalar phi = faceValue(phi_, facei);
-                scalar dVcorr = faceValue(dVfcorrected, facei);
-                setFaceValue(dVf_, facei, phi*dt - dVcorr);
-            }
-
-            syncProcPatches(dVf_, phi_);
-        }
-
-        if (debug)
-        {
-            // Check if still unbounded
-            scalarField alphaNew(alpha1In_ - fvc::surfaceIntegrate(dVf_)());
-            label maxAlphaMinus1 = max(alphaNew - 1);
-            scalar minAlpha = min(alphaNew);
-            label nUndershoots = sum(neg0(alphaNew + aTol));
-            label nOvershoots = sum(pos0(alphaNew - 1 - aTol));
-            Info<< "After bounding number " << n + 1 << " of time "
-                << mesh_.time().value() << ":" << endl;
-            Info<< "nOvershoots = " << nOvershoots << " with max(alphaNew-1) = "
-                << maxAlphaMinus1 << " and nUndershoots = " << nUndershoots
-                << " with min(alphaNew) = " << minAlpha << endl;
-        }
-    }
-}
-
-
-void Foam::isoAdvection::boundFromAbove
-(
-    const scalarField& alpha1,
-    surfaceScalarField& dVf,
-    DynamicList<label>& correctedFaces
-)
-{
-    DebugInFunction << endl;
-
-    correctedFaces.clear();
-    scalar aTol = 10*SMALL; // Note: tolerances
-
-    const scalarField& meshV = mesh_.cellVolumes();
-    const scalar dt = mesh_.time().deltaTValue();
-
-    DynamicList<label> downwindFaces(10);
-    DynamicList<label> facesToPassFluidThrough(downwindFaces.size());
-    DynamicList<scalar> dVfmax(downwindFaces.size());
-    DynamicList<scalar> phi(downwindFaces.size());
-
-    // Loop through alpha cell centred field
-    forAll(alpha1, celli)
-    {
-        if (checkBounding_.test(celli))
-        {
-            const scalar Vi = meshV[celli];
-            scalar alpha1New = alpha1[celli] - netFlux(dVf, celli)/Vi;
-            scalar alphaOvershoot = alpha1New - 1.0;
-            scalar fluidToPassOn = alphaOvershoot*Vi;
-            label nFacesToPassFluidThrough = 1;
-
-            bool firstLoop = true;
-
-            // First try to pass surplus fluid on to neighbour cells that are
-            // not filled and to which dVf < phi*dt
-            while (alphaOvershoot > aTol && nFacesToPassFluidThrough > 0)
-            {
-                DebugInfo
-                    << "\n\nBounding cell " << celli
-                    << " with alpha overshooting " << alphaOvershoot
-                    << endl;
-
-                facesToPassFluidThrough.clear();
-                dVfmax.clear();
-                phi.clear();
-
-                cellIsBounded_.set(celli);
-
-                // Find potential neighbour cells to pass surplus phase to
-                setDownwindFaces(celli, downwindFaces);
-
-                scalar dVftot = 0;
-                nFacesToPassFluidThrough = 0;
-
-                forAll(downwindFaces, fi)
-                {
-                    const label facei = downwindFaces[fi];
-                    const scalar phif = faceValue(phi_, facei);
-                    const scalar dVff = faceValue(dVf, facei);
-                    const scalar maxExtraFaceFluidTrans = mag(phif*dt - dVff);
-
-                    // dVf has same sign as phi and so if phi>0 we have
-                    // mag(phi_[facei]*dt) - mag(dVf[facei]) = phi_[facei]*dt
-                    // - dVf[facei]
-                    // If phi < 0 we have mag(phi_[facei]*dt) -
-                    // mag(dVf[facei]) = -phi_[facei]*dt - (-dVf[facei]) > 0
-                    // since mag(dVf) < phi*dt
-                    DebugInfo
-                        << "downwindFace " << facei
-                        << " has maxExtraFaceFluidTrans = "
-                        << maxExtraFaceFluidTrans << endl;
-
-                    if (maxExtraFaceFluidTrans/Vi > aTol)
-                    {
-//                    if (maxExtraFaceFluidTrans/Vi > aTol &&
-//                    mag(dVfIn[facei])/Vi > aTol) //Last condition may be
-//                    important because without this we will flux through uncut
-//                    downwind faces
-                        facesToPassFluidThrough.append(facei);
-                        phi.append(phif);
-                        dVfmax.append(maxExtraFaceFluidTrans);
-                        dVftot += mag(phif*dt);
-                    }
-                }
-
-                DebugInfo
-                    << "\nfacesToPassFluidThrough: "
-                    << facesToPassFluidThrough << ", dVftot = "
-                    << dVftot << " m3 corresponding to dalpha = "
-                    << dVftot/Vi << endl;
-
-                forAll(facesToPassFluidThrough, fi)
-                {
-                    const label facei = facesToPassFluidThrough[fi];
-                    scalar fluidToPassThroughFace =
-                        fluidToPassOn*mag(phi[fi]*dt)/dVftot;
-
-                    nFacesToPassFluidThrough +=
-                        pos0(dVfmax[fi] - fluidToPassThroughFace);
-
-                    fluidToPassThroughFace =
-                        min(fluidToPassThroughFace, dVfmax[fi]);
-
-                    scalar dVff = faceValue(dVf, facei);
-                    dVff += sign(phi[fi])*fluidToPassThroughFace;
-                    setFaceValue(dVf, facei, dVff);
-
-                    if (firstLoop)
-                    {
-                        checkIfOnProcPatch(facei);
-                        correctedFaces.append(facei);
-                    }
-                }
-
-                firstLoop = false;
-                alpha1New = alpha1[celli] - netFlux(dVf, celli)/Vi;
-                alphaOvershoot = alpha1New - 1.0;
-                fluidToPassOn = alphaOvershoot*Vi;
-
-                DebugInfo
-                    << "\nNew alpha for cell " << celli << ": "
-                    << alpha1New << endl;
-            }
-        }
-    }
-
-    DebugInfo << "correctedFaces = " << correctedFaces << endl;
-}
-
-
-Foam::scalar Foam::isoAdvection::netFlux
-(
-    const surfaceScalarField& dVf,
-    const label celli
-) const
-{
-    scalar dV = 0;
-
-    // Get face indices
-    const cell& c = mesh_.cells()[celli];
-
-    // Get mesh data
-    const labelList& own = mesh_.faceOwner();
-
-    forAll(c, fi)
-    {
-        const label facei = c[fi];
-        const scalar dVff = faceValue(dVf, facei);
-
-        if (own[facei] == celli)
-        {
-            dV += dVff;
-        }
-        else
-        {
-            dV -= dVff;
-        }
-    }
-
-    return dV;
-}
-
-
-void Foam::isoAdvection::syncProcPatches
-(
-    surfaceScalarField& dVf,
-    const surfaceScalarField& phi
-)
-{
-    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
-
-    if (Pstream::parRun())
-    {
-        PstreamBuffers pBufs(Pstream::commsTypes::nonBlocking);
-
-        // Send
-        forAll(procPatchLabels_, i)
-        {
-            const label patchi = procPatchLabels_[i];
-
-            const processorPolyPatch& procPatch =
-                refCast<const processorPolyPatch>(patches[patchi]);
-
-            UOPstream toNbr(procPatch.neighbProcNo(), pBufs);
-            const scalarField& pFlux = dVf.boundaryField()[patchi];
-
-            const List<label>& surfCellFacesOnProcPatch =
-                surfaceCellFacesOnProcPatches_[patchi];
-
-            const UIndirectList<scalar> dVfPatch
-            (
-                pFlux,
-                surfCellFacesOnProcPatch
-            );
-
-            toNbr << surfCellFacesOnProcPatch << dVfPatch;
-        }
-
-        pBufs.finishedSends();
-
-
-        // Receive and combine
-        forAll(procPatchLabels_, patchLabeli)
-        {
-            const label patchi = procPatchLabels_[patchLabeli];
-
-            const processorPolyPatch& procPatch =
-                refCast<const processorPolyPatch>(patches[patchi]);
-
-            UIPstream fromNeighb(procPatch.neighbProcNo(), pBufs);
-            List<label> faceIDs;
-            List<scalar> nbrdVfs;
-
-            fromNeighb >> faceIDs >> nbrdVfs;
-
-            if (debug)
-            {
-                Pout<< "Received at time = " << mesh_.time().value()
-                    << ": surfCellFacesOnProcPatch = " << faceIDs << nl
-                    << "Received at time = " << mesh_.time().value()
-                    << ": dVfPatch = " << nbrdVfs << endl;
-            }
-
-            // Combine fluxes
-            scalarField& localFlux = dVf.boundaryFieldRef()[patchi];
-
-            forAll(faceIDs, i)
-            {
-                const label facei = faceIDs[i];
-                localFlux[facei] = - nbrdVfs[i];
-                if (debug && mag(localFlux[facei] + nbrdVfs[i]) > 10*SMALL)
-                {
-                    Pout<< "localFlux[facei] = " << localFlux[facei]
-                        << " and nbrdVfs[i] = " << nbrdVfs[i]
-                        << " for facei = " << facei << endl;
-                }
-            }
-        }
-
-        if (debug)
-        {
-            // Write out results for checking
-            forAll(procPatchLabels_, patchLabeli)
-            {
-                const label patchi = procPatchLabels_[patchLabeli];
-                const scalarField& localFlux = dVf.boundaryField()[patchi];
-                Pout<< "time = " << mesh_.time().value() << ": localFlux = "
-                    << localFlux << endl;
-            }
-        }
-
-        // Reinitialising list used for minimal parallel communication
-        forAll(surfaceCellFacesOnProcPatches_, patchi)
-        {
-            surfaceCellFacesOnProcPatches_[patchi].clear();
-        }
-    }
-}
-
-
-void Foam::isoAdvection::checkIfOnProcPatch(const label facei)
-{
-    if (!mesh_.isInternalFace(facei))
-    {
-        const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
-        const label patchi = pbm.patchID()[facei - mesh_.nInternalFaces()];
-
-        if (isA<processorPolyPatch>(pbm[patchi]) && pbm[patchi].size())
-        {
-            const label patchFacei = pbm[patchi].whichFace(facei);
-            surfaceCellFacesOnProcPatches_[patchi].append(patchFacei);
-        }
-    }
-}
-
-
-void Foam::isoAdvection::advect()
-{
-    DebugInFunction << endl;
-
-    scalar advectionStartTime = mesh_.time().elapsedCpuTime();
-
-    // Initialising dVf with upwind values
-    // i.e. phi[facei]*alpha1[upwindCell[facei]]*dt
-    dVf_ = upwind<scalar>(mesh_, phi_).flux(alpha1_)*mesh_.time().deltaT();
-
-    // Do the isoAdvection on surface cells
-    timeIntegratedFlux();
-
-    // Adjust alpha for mesh motion
-    if (mesh_.moving())
-    {
-        alpha1In_ *= (mesh_.Vsc0()/mesh_.Vsc());
-    }
-
-    // Adjust dVf for unbounded cells
-    limitFluxes();
-
-    // Advect the free surface
-    alpha1_ -= fvc::surfaceIntegrate(dVf_);
-    alpha1_.correctBoundaryConditions();
-
-    scalar maxAlphaMinus1 = gMax(alpha1In_) - 1;
-    scalar minAlpha = gMin(alpha1In_);
-    Info << "isoAdvection: After conservative bounding: min(alpha) = "
-        << minAlpha << ", max(alpha) = 1 + " << maxAlphaMinus1 << endl;
-
-    // Apply non-conservative bounding mechanisms (clipping and snapping)
-    // Note: We should be able to write out alpha before this is done!
-    applyBruteForceBounding();
-
-    // Write surface cell set and bound cell set if required by user
-    writeSurfaceCells();
-    writeBoundedCells();
-
-    advectionTime_ += (mesh_.time().elapsedCpuTime() - advectionStartTime);
-    Info << "isoAdvection: time consumption = "
-        << label(100*advectionTime_/(mesh_.time().elapsedCpuTime() + SMALL))
-        << "%" << endl;
-}
-
-
-void Foam::isoAdvection::applyBruteForceBounding()
-{
-    bool alpha1Changed = false;
-
-    scalar snapAlphaTol = dict_.getOrDefault<scalar>("snapTol", 0);
-    if (snapAlphaTol > 0)
-    {
-        alpha1_ =
-            alpha1_
-           *pos0(alpha1_ - snapAlphaTol)
-           *neg0(alpha1_ - (1.0 - snapAlphaTol))
-          + pos0(alpha1_ - (1.0 - snapAlphaTol));
-
-        alpha1Changed = true;
-    }
-
-    if (dict_.getOrDefault("clip", true))
-    {
-        alpha1_ = min(scalar(1), max(scalar(0), alpha1_));
-        alpha1Changed = true;
-    }
-
-    if (alpha1Changed)
-    {
-        alpha1_.correctBoundaryConditions();
-    }
-}
-
-
-void Foam::isoAdvection::writeSurfaceCells() const
-{
-    if (!mesh_.time().writeTime()) return;
-
-    if (dict_.getOrDefault("writeSurfCells", false))
-    {
-        cellSet cSet
-        (
-            IOobject
-            (
-                "surfCells",
-                mesh_.time().timeName(),
-                mesh_,
-                IOobject::NO_READ
-            )
-        );
-
-        cSet.insert(surfCells_);
-
-        cSet.write();
-    }
-}
-
-
-void Foam::isoAdvection::writeBoundedCells() const
-{
-    if (!mesh_.time().writeTime()) return;
-
-    if (dict_.getOrDefault("writeBoundedCells", false))
-    {
-        cellSet cSet
-        (
-            IOobject
-            (
-                "boundedCells",
-                mesh_.time().timeName(),
-                mesh_,
-                IOobject::NO_READ
-            )
-        );
-
-        for (const label celli : cellIsBounded_)
-        {
-            cSet.insert(celli);
-        }
-
-        cSet.write();
-    }
-}
-
-
-void Foam::isoAdvection::writeIsoFaces
-(
-    const DynamicList<List<point>>& faces
-) const
-{
-
-    if (!writeIsoFacesToFile_ || !mesh_.time().writeTime()) return;
-
-    // Writing isofaces to obj file for inspection, e.g. in paraview
-    const fileName outputFile
-    (
-        mesh_.time().globalPath()
-      / "isoFaces"
-      / word::printf("isoFaces_%012d.obj", mesh_.time().timeIndex())
-    );
-
-    if (Pstream::parRun())
-    {
-        // Collect points from all the processors
-        List<DynamicList<List<point>>> allProcFaces(Pstream::nProcs());
-        allProcFaces[Pstream::myProcNo()] = faces;
-        Pstream::gatherList(allProcFaces);
-
-        if (Pstream::master())
-        {
-            mkDir(outputFile.path());
-            OBJstream os(outputFile);
-            Info<< nl << "isoAdvection: writing iso faces to file: "
-                << os.name() << nl << endl;
-
-            face f;
-            forAll(allProcFaces, proci)
-            {
-                const DynamicList<List<point>>& procFacePts =
-                    allProcFaces[proci];
-
-                forAll(procFacePts, i)
-                {
-                    const List<point>& facePts = procFacePts[i];
-
-                    if (facePts.size() != f.size())
-                    {
-                        f = face(identity(facePts.size()));
-                    }
-
-                    os.write(f, facePts, false);
-                }
-            }
-        }
-    }
-    else
-    {
-        mkDir(outputFile.path());
-        OBJstream os(outputFile);
-        Info<< nl << "isoAdvection: writing iso faces to file: "
-            << os.name() << nl << endl;
-
-        face f;
-        forAll(faces, i)
-        {
-            const List<point>& facePts = faces[i];
-
-            if (facePts.size() != f.size())
-            {
-                f = face(identity(facePts.size()));
-            }
-
-            os.write(f, facePts, false);
-        }
-    }
-}
-
-
-// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvectionTemplates.C b/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvectionTemplates.C
deleted file mode 100644
index e8c506deff8686afcc71b0b5c013fdd23967d9bb..0000000000000000000000000000000000000000
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvectionTemplates.C
+++ /dev/null
@@ -1,111 +0,0 @@
-/*---------------------------------------------------------------------------*\
-  =========                 |
-  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
-   \\    /   O peration     |
-    \\  /    A nd           | www.openfoam.com
-     \\/     M anipulation  |
--------------------------------------------------------------------------------
-    Copyright (C) 2016-2017 DHI
-    Copyright (C) 2016-2017 OpenCFD Ltd.
--------------------------------------------------------------------------------
-License
-    This file is part of OpenFOAM.
-
-    OpenFOAM is free software: you can redistribute it and/or modify it
-    under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
-    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-    for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
-
-\*---------------------------------------------------------------------------*/
-
-#include "isoAdvection.H"
-
-// ************************************************************************* //
-
-template<typename Type>
-Type Foam::isoAdvection::faceValue
-(
-    const GeometricField<Type, fvsPatchField, surfaceMesh>& f,
-    const label facei
-) const
-{
-    if (mesh_.isInternalFace(facei))
-    {
-        return f.primitiveField()[facei];
-    }
-    else
-    {
-        const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
-
-        // Boundary face. Find out which face of which patch
-        const label patchi = pbm.patchID()[facei - mesh_.nInternalFaces()];
-
-        if (patchi < 0 || patchi >= pbm.size())
-        {
-            FatalErrorInFunction
-                << "Cannot find patch for face " << facei
-                << abort(FatalError);
-        }
-
-        // Handle empty patches
-        const polyPatch& pp = pbm[patchi];
-        if (isA<emptyPolyPatch>(pp) || pp.empty())
-        {
-            return pTraits<Type>::zero;
-        }
-
-        const label patchFacei = pp.whichFace(facei);
-        return f.boundaryField()[patchi][patchFacei];
-    }
-}
-
-
-template<typename Type>
-void Foam::isoAdvection::setFaceValue
-(
-    GeometricField<Type, fvsPatchField, surfaceMesh>& f,
-    const label facei,
-    const Type& value
-) const
-{
-    if (mesh_.isInternalFace(facei))
-    {
-        f.primitiveFieldRef()[facei] = value;
-    }
-    else
-    {
-        const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
-
-        // Boundary face. Find out which face of which patch
-        const label patchi = pbm.patchID()[facei - mesh_.nInternalFaces()];
-
-        if (patchi < 0 || patchi >= pbm.size())
-        {
-            FatalErrorInFunction
-                << "Cannot find patch for face " << facei
-                << abort(FatalError);
-        }
-
-        // Handle empty patches
-        const polyPatch& pp = pbm[patchi];
-        if (isA<emptyPolyPatch>(pp) || pp.empty())
-        {
-            return;
-        }
-
-        const label patchFacei = pp.whichFace(facei);
-
-        f.boundaryFieldRef()[patchi][patchFacei] = value;
-    }
-}
-
-
-// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.C b/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.C
deleted file mode 100644
index 80e10d80f65c892c5e4455d8e7107912adc64ddd..0000000000000000000000000000000000000000
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.C
+++ /dev/null
@@ -1,725 +0,0 @@
-/*---------------------------------------------------------------------------*\
-  =========                 |
-  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
-   \\    /   O peration     |
-    \\  /    A nd           | www.openfoam.com
-     \\/     M anipulation  |
--------------------------------------------------------------------------------
-    Copyright (C) 2016-2017 DHI
-    Copyright (C) 2018 Johan Roenby
-    Copyright (C) 2016-2019 OpenCFD Ltd.
--------------------------------------------------------------------------------
-License
-    This file is part of OpenFOAM.
-
-    OpenFOAM is free software: you can redistribute it and/or modify it
-    under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
-    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-    for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
-
-\*---------------------------------------------------------------------------*/
-
-#include "isoCutCell.H"
-#include "scalarMatrices.H"
-#include "volFields.H"
-#include "surfaceFields.H"
-
-// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
-
-int Foam::isoCutCell::debug = 0;
-
-// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
-
-Foam::isoCutCell::isoCutCell(const fvMesh& mesh, scalarField& f)
-:
-    mesh_(mesh),
-    cellI_(-1),
-    f_(f),
-    isoValue_(0),
-    isoCutFace_(isoCutFace(mesh_, f_)),
-    isoCutFaces_(10),
-    isoCutFacePoints_(10),
-    isoCutFaceCentres_(10),
-    isoCutFaceAreas_(10),
-    isoFaceEdges_(10),
-    isoFacePoints_(10),
-    isoFaceCentre_(Zero),
-    isoFaceArea_(Zero),
-    subCellCentre_(Zero),
-    subCellVolume_(-10),
-    VOF_(-10),
-    fullySubFaces_(10),
-    cellStatus_(-1),
-    subCellCentreAndVolumeCalculated_(false),
-    isoFaceCentreAndAreaCalculated_(false)
-{
-    clearStorage();
-}
-
-
-// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
-
-void Foam::isoCutCell::calcSubCellCentreAndVolume()
-{
-    if (cellStatus_ == 0)
-    {
-        subCellCentre_ = vector::zero;
-        subCellVolume_ = 0.0;
-
-        // Estimate the approximate cell centre as the average of face centres
-        label nCellFaces(1 + isoCutFaceCentres_.size() + fullySubFaces_.size());
-        vector cEst = isoFaceCentre_ + sum(isoCutFaceCentres_);
-        forAll(fullySubFaces_, facei)
-        {
-            cEst += mesh_.faceCentres()[fullySubFaces_[facei]];
-        }
-        cEst /= scalar(nCellFaces);
-
-
-        // Contribution to subcell centre and volume from isoface
-        const scalar pyr3Vol0 =
-            max(mag(isoFaceArea_ & (isoFaceCentre_ - cEst)), VSMALL);
-
-        // Calculate face-pyramid centre
-        const vector pc0 = 0.75*isoFaceCentre_ + 0.25*cEst;
-
-        // Accumulate volume-weighted face-pyramid centre
-        subCellCentre_ += pyr3Vol0*pc0;
-
-        // Accumulate face-pyramid volume
-        subCellVolume_ += pyr3Vol0;
-
-        // Contribution to subcell centre and volume from cut faces
-        forAll(isoCutFaceCentres_, facei)
-        {
-            // Calculate 3*face-pyramid volume
-            scalar pyr3Vol =
-                max
-                (
-                    mag
-                    (
-                        isoCutFaceAreas_[facei]
-                      & (isoCutFaceCentres_[facei] - cEst)
-                    ),
-                    VSMALL
-                );
-
-            // Calculate face-pyramid centre
-            vector pc = 0.75*isoCutFaceCentres_[facei] + 0.25*cEst;
-
-            // Accumulate volume-weighted face-pyramid centre
-            subCellCentre_ += pyr3Vol*pc;
-
-            // Accumulate face-pyramid volume
-            subCellVolume_ += pyr3Vol;
-        }
-
-        // Contribution to subcell centre and volume from fully submerged faces
-        forAll(fullySubFaces_, i)
-        {
-            const label facei = fullySubFaces_[i];
-            const point& fCentre = mesh_.faceCentres()[facei];
-            const vector& fArea = mesh_.faceAreas()[facei];
-
-            // Calculate 3*face-pyramid volume
-            scalar pyr3Vol = max(mag(fArea & (fCentre - cEst)), VSMALL);
-
-            // Calculate face-pyramid centre
-            vector pc = 0.75*fCentre + 0.25*cEst;
-
-            // Accumulate volume-weighted face-pyramid centre
-            subCellCentre_ += pyr3Vol*pc;
-
-            // Accumulate face-pyramid volume
-            subCellVolume_ += pyr3Vol;
-        }
-
-        subCellCentre_ /= subCellVolume_;
-        subCellVolume_ /= scalar(3);
-        VOF_ = subCellVolume_/mesh_.cellVolumes()[cellI_];
-
-        subCellCentreAndVolumeCalculated_ = true;
-
-        if (debug)
-        {
-            vector sumSf = isoFaceArea_;
-            scalar sumMagSf = mag(isoFaceArea_);
-            forAll(isoCutFaceCentres_, facei)
-            {
-                sumSf += isoCutFaceAreas_[facei];
-                sumMagSf += mag(isoCutFaceAreas_[facei]);
-            }
-            forAll(fullySubFaces_, facei)
-            {
-                sumSf += mesh_.faceAreas()[fullySubFaces_[facei]];
-                sumMagSf += mag(isoCutFaceAreas_[facei]);
-            }
-            if (mag(sumSf) > 1e-10)
-            {
-                Pout<< "Warninig: mag(sumSf)/magSumSf = "
-                    << mag(sumSf)/sumMagSf << " for surface cell"
-                    << cellI_ << endl;
-            }
-        }
-    }
-    else if (cellStatus_ == 1)
-    {
-        // Cell fully above isosurface
-        subCellCentre_ = vector::zero;
-        subCellVolume_ = 0;
-        VOF_ = 0;
-    }
-    else if (cellStatus_ == -1)
-    {
-        // Cell fully below isosurface
-        subCellCentre_ = mesh_.cellCentres()[cellI_];
-        subCellVolume_ = mesh_.cellVolumes()[cellI_];
-        VOF_ = 1;
-    }
-}
-
-
-void Foam::isoCutCell::calcIsoFaceCentreAndArea()
-{
-    // Initial guess of face centre from edge points
-    point fCentre(Zero);
-    label nEdgePoints(0);
-    forAll(isoFaceEdges_, ei)
-    {
-        DynamicList<point>& edgePoints = isoFaceEdges_[ei];
-        forAll(edgePoints, pi)
-        {
-            fCentre += edgePoints[pi];
-            nEdgePoints++;
-        }
-    }
-
-    if (nEdgePoints > 0)
-    {
-        fCentre /= nEdgePoints;
-    }
-    else
-    {
-        DebugPout << "Warning: nEdgePoints = 0 for cell " << cellI_ << endl;
-    }
-
-    vector sumN(Zero);
-    scalar sumA(0);
-    vector sumAc(Zero);
-
-    forAll(isoFaceEdges_, ei)
-    {
-        const DynamicList<point>& edgePoints = isoFaceEdges_[ei];
-        const label nPoints = edgePoints.size();
-        for (label pi = 0; pi < nPoints-1; pi++)
-        {
-            const point& nextPoint = edgePoints[pi + 1];
-
-            vector c = edgePoints[pi] + nextPoint + fCentre;
-            vector n = (nextPoint - edgePoints[pi])^(fCentre - edgePoints[pi]);
-            scalar a = mag(n);
-
-            // Edges may have different orientation
-            sumN += Foam::sign(n & sumN)*n;
-            sumA += a;
-            sumAc += a*c;
-        }
-    }
-
-    // This is to deal with zero-area faces. Mark very small faces
-    // to be detected in e.g., processorPolyPatch.
-    if (sumA < ROOTVSMALL)
-    {
-        isoFaceCentre_ = fCentre;
-        isoFaceArea_ = vector::zero;
-    }
-    else
-    {
-        isoFaceCentre_ = sumAc/sumA/scalar(3);
-        isoFaceArea_ = 0.5*sumN;
-    }
-
-
-    // Check isoFaceArea_ direction and change if not pointing out of subcell
-    if ((isoFaceArea_ & (isoFaceCentre_ - subCellCentre())) < 0)
-    {
-        isoFaceArea_ *= (-1);
-    }
-
-    isoFaceCentreAndAreaCalculated_ = true;
-}
-
-
-void Foam::isoCutCell::calcIsoFacePointsFromEdges()
-{
-    DebugPout
-        << "Enter calcIsoFacePointsFromEdges() with isoFaceArea_ = "
-        << isoFaceArea_ << " and isoFaceCentre_ = " << isoFaceCentre_
-        << " and isoFaceEdges_ = " << isoFaceEdges_ << endl;
-
-    // Defining local coordinates with zhat along isoface normal and xhat from
-    // isoface centre to first point in isoFaceEdges_
-    const vector zhat = normalised(isoFaceArea_);
-    vector xhat = isoFaceEdges_[0][0] - isoFaceCentre_;
-    xhat = (xhat - (xhat & zhat)*zhat);
-    xhat.normalise();
-    vector yhat = normalised(zhat ^ xhat);
-
-    DebugPout << "Calculated local coordinates" << endl;
-
-    // Calculating isoface point angles in local coordinates
-    DynamicList<point> unsortedIsoFacePoints(3*isoFaceEdges_.size());
-    DynamicList<scalar> unsortedIsoFacePointAngles(3*isoFaceEdges_.size());
-    forAll(isoFaceEdges_, ei)
-    {
-        const DynamicList<point>& edgePoints = isoFaceEdges_[ei];
-        forAll(edgePoints, pi)
-        {
-            const point& p = edgePoints[pi];
-            unsortedIsoFacePoints.append(p);
-            unsortedIsoFacePointAngles.append
-            (
-                Foam::atan2
-                (
-                    ((p - isoFaceCentre_) & yhat),
-                    ((p - isoFaceCentre_) & xhat)
-                )
-            );
-        }
-    }
-
-    DebugPout<< "Calculated isoFace point angles" << endl;
-
-    // Sorting isoface points by angle and inserting into isoFacePoints_
-    labelList order(sortedOrder(unsortedIsoFacePointAngles));
-    isoFacePoints_.append(unsortedIsoFacePoints[order[0]]);
-    for (label pi = 1; pi < order.size(); pi++)
-    {
-        if
-        (
-            mag
-            (
-                unsortedIsoFacePointAngles[order[pi]]
-               -unsortedIsoFacePointAngles[order[pi-1]]
-            ) > 1e-8
-        )
-        {
-            isoFacePoints_.append(unsortedIsoFacePoints[order[pi]]);
-        }
-    }
-
-    DebugPout<< "Sorted isoface points by angle" << endl;
-}
-
-
-Foam::label Foam::isoCutCell::calcSubCell
-(
-    const label celli,
-    const scalar isoValue
-)
-{
-    // Populate isoCutFaces_, isoCutFacePoints_, fullySubFaces_, isoFaceCentre_
-    // and isoFaceArea_.
-
-    clearStorage();
-    cellI_ = celli;
-    isoValue_ = isoValue;
-    const cell& c = mesh_.cells()[celli];
-
-    forAll(c, fi)
-    {
-        const label facei = c[fi];
-
-        const label faceStatus = isoCutFace_.calcSubFace(facei, isoValue_);
-
-        if (faceStatus == 0)
-        {
-            // Face is cut
-            isoCutFacePoints_.append(isoCutFace_.subFacePoints());
-            isoCutFaceCentres_.append(isoCutFace_.subFaceCentre());
-            isoCutFaceAreas_.append(isoCutFace_.subFaceArea());
-            isoFaceEdges_.append(isoCutFace_.surfacePoints());
-        }
-        else if (faceStatus == -1)
-        {
-            // Face fully below
-            fullySubFaces_.append(facei);
-        }
-    }
-
-    if (isoCutFacePoints_.size())
-    {
-        // Cell cut at least at one face
-        cellStatus_ = 0;
-        calcIsoFaceCentreAndArea();
-
-        // In the rare but occurring cases where a cell is only touched at a
-        // point or a line the isoFaceArea_ will have zero length and here the
-        // cell should be treated as either completely empty or full.
-        if (mag(isoFaceArea_) < 10*SMALL)
-        {
-            if (fullySubFaces_.empty())
-            {
-                // Cell fully above isosurface
-                cellStatus_ = 1;
-            }
-            else
-            {
-                // Cell fully below isosurface
-                cellStatus_ = -1;
-            }
-        }
-    }
-    else if (fullySubFaces_.empty())
-    {
-        // Cell fully above isosurface
-        cellStatus_ = 1;
-    }
-    else
-    {
-        // Cell fully below isosurface
-        cellStatus_ = -1;
-    }
-
-    return cellStatus_;
-}
-
-
-const Foam::point& Foam::isoCutCell::subCellCentre()
-{
-    if (!subCellCentreAndVolumeCalculated_)
-    {
-        calcSubCellCentreAndVolume();
-    }
-
-    return subCellCentre_;
-}
-
-
-Foam::scalar Foam::isoCutCell::subCellVolume()
-{
-    if (!subCellCentreAndVolumeCalculated_)
-    {
-        calcSubCellCentreAndVolume();
-    }
-
-    return subCellVolume_;
-}
-
-
-const Foam::DynamicList<Foam::point>& Foam::isoCutCell::isoFacePoints()
-{
-    if (cellStatus_ == 0 && isoFacePoints_.size() == 0)
-    {
-        calcIsoFacePointsFromEdges();
-    }
-
-    return isoFacePoints_;
-}
-
-
-const Foam::point& Foam::isoCutCell::isoFaceCentre()
-{
-    if (!isoFaceCentreAndAreaCalculated_)
-    {
-        calcIsoFaceCentreAndArea();
-    }
-
-    return isoFaceCentre_;
-}
-
-
-const Foam::vector& Foam::isoCutCell::isoFaceArea()
-{
-    if (!isoFaceCentreAndAreaCalculated_)
-    {
-        calcIsoFaceCentreAndArea();
-    }
-
-    return isoFaceArea_;
-}
-
-
-Foam::scalar Foam::isoCutCell::volumeOfFluid()
-{
-    if (!subCellCentreAndVolumeCalculated_)
-    {
-        calcSubCellCentreAndVolume();
-    }
-
-    return VOF_;
-}
-
-
-Foam::scalar Foam::isoCutCell::isoValue() const
-{
-    return isoValue_;
-}
-
-
-void Foam::isoCutCell::clearStorage()
-{
-    cellI_ = -1;
-    isoValue_ = 0;
-    isoCutFace_.clearStorage();
-    isoCutFaces_.clear();
-    isoCutFacePoints_.clear();
-    isoCutFaceCentres_.clear();
-    isoCutFaceAreas_.clear();
-    isoFaceEdges_.clear();
-    isoFacePoints_.clear();
-    isoFaceCentre_ = vector::zero;
-    isoFaceArea_ = vector::zero;
-    subCellCentre_ = vector::zero;
-    subCellVolume_ = -10;
-    VOF_ = -10;
-    fullySubFaces_.clear();
-    cellStatus_ = -1;
-    subCellCentreAndVolumeCalculated_ = false;
-    isoFaceCentreAndAreaCalculated_ = false;
-}
-
-
-Foam::label Foam::isoCutCell::vofCutCell
-(
-    const label celli,
-    const scalar alpha1,
-    const scalar tol,
-    const label maxIter
-)
-{
-    DebugInFunction
-        << "vofCutCell for cell " << celli << " with alpha1 = "
-        << alpha1 << " ------" << endl;
-
-    // Finding cell vertex extremum values
-    const labelList& pLabels = mesh_.cellPoints(celli);
-    scalarField fvert(pLabels.size());
-    forAll(pLabels, pi)
-    {
-        fvert[pi] = f_[pLabels[pi]];
-    }
-    labelList order(sortedOrder(fvert));
-    scalar f1 = fvert[order.first()];
-    scalar f2 = fvert[order.last()];
-
-    DebugPout << "fvert = " << fvert << ", and order = " << order << endl;
-
-    // Handling special case where method is handed an almost full/empty cell
-    if (alpha1 < tol)
-    {
-        return calcSubCell(celli, f2);
-    }
-    else if (1 - alpha1 < tol)
-    {
-        return calcSubCell(celli, f1);
-    }
-
-    // Finding the two vertices inbetween which the isovalue giving alpha1 lies
-    label L1 = 0;
-    label L2 = fvert.size() - 1;
-    scalar a1 = 1;
-    scalar a2 = 0;
-    scalar L3, f3, a3;
-
-    while (L2 - L1 > 1)
-    {
-        L3 = round(0.5*(L1 + L2));
-        f3 = fvert[order[L3]];
-        calcSubCell(celli, f3);
-        a3 = volumeOfFluid();
-        if (a3 > alpha1)
-        {
-            L1 = L3; f1 = f3; a1 = a3;
-        }
-        else if (a3 < alpha1)
-        {
-            L2 = L3; f2 = f3; a2 = a3;
-        }
-    }
-
-    if (mag(f1 - f2) < 10*SMALL)
-    {
-        DebugPout<< "Warning: mag(f1 - f2) < 10*SMALL" << endl;
-        return calcSubCell(celli, f1);
-    }
-
-    if (mag(a1 - a2) < tol)
-    {
-        DebugPout<< "Warning: mag(a1 - a2) < tol for cell " << celli << endl;
-        return calcSubCell(celli, 0.5*(f1 + f2));
-    }
-
-    // Now we know that a(f) = alpha1 is to be found on the f interval
-    // [f1, f2], i.e. alpha1 will be in the interval [a2,a1]
-    DebugPout
-        << "L1 = " << L1 << ", f1 = " << f1 << ", a1 = " << a1 << nl
-        << "L2 = " << L2 << ", f2 = " << f2  << ", a2 = " << a2 << endl;
-
-
-    // Finding coefficients in 3 deg polynomial alpha(f) from 4 solutions
-
-    // Finding 2 additional points on 3 deg polynomial
-    f3 = f1 + (f2 - f1)/scalar(3);
-    calcSubCell(celli, f3);
-    a3 = volumeOfFluid();
-
-    scalar f4 = f1 + (f2 - f1)*scalar(2)/scalar(3);
-    calcSubCell(celli, f4);
-    scalar a4 = volumeOfFluid();
-
-    // Building and solving Vandermonde matrix equation
-    scalarField a(4), f(4), C(4);
-    {
-        a[0] = a1, f[0] = 0;
-        a[1] = a3, f[1] = (f3 - f1)/(f2 - f1);
-        a[2] = a4, f[2] = (f4 - f1)/(f2 - f1);
-        a[3] = a2, f[3] = 1;
-        scalarSquareMatrix M(4);
-        forAll(f, i)
-        {
-            forAll(f, j)
-            {
-                M[i][j] = pow(f[i], 3 - j);
-            }
-        }
-
-        // C holds the 4 polynomial coefficients
-        C = a;
-        LUsolve(M, C);
-    }
-
-    // Finding root with Newton method
-    f3 = f[1]; a3 = a[1];
-    label nIter = 0;
-    scalar res = mag(a3 - alpha1);
-    while (res > tol && nIter < 10*maxIter)
-    {
-        f3 -=
-            (C[0]*pow3(f3) + C[1]*sqr(f3) + C[2]*f3 + C[3] - alpha1)
-           /(3*C[0]*sqr(f3) + 2*C[1]*f3 + C[2]);
-        a3 = C[0]*pow3(f3) + C[1]*sqr(f3) + C[2]*f3 + C[3];
-        res = mag(a3 - alpha1);
-        nIter++;
-    }
-    // Scaling back to original range
-    f3 = f3*(f2 - f1) + f1;
-
-    // Check result
-    calcSubCell(celli, f3);
-    const scalar VOF = volumeOfFluid();
-    res = mag(VOF - alpha1);
-
-    if (res > tol)
-    {
-        DebugPout
-            << "Newton obtained f3 = " << f3 << " and a3 = " << a3
-            << " with mag(a3-alpha1) = " << mag(a3-alpha1)
-            << " but calcSubCell(celli,f3) gives VOF  = " << VOF << nl
-            << "M(f)*C = a with " << nl
-            << "f_scaled = " << f << nl
-            << "f = " << f*(f2 - f1) + f1 << nl
-            << "a = " << a << nl
-            << "C = " << C << endl;
-    }
-    else
-    {
-        DebugPout<< "Newton did the job" << endl;
-        return cellStatus_;
-    }
-
-    // If tolerance not met use the secant method  with f3 as a hopefully very
-    // good initial guess to crank res the last piece down below tol
-    // Note: This is expensive because subcell is recalculated every iteration
-    scalar x2 = f3;
-    scalar g2 = VOF - alpha1;
-    scalar x1 = max(1e-3*(f2 - f1), 100*SMALL);
-    x1 = min(max(x1, f1), f2);
-    calcSubCell(celli, x1);
-    scalar g1 = volumeOfFluid() - alpha1;
-
-    nIter = 0;
-    scalar g0(0), x0(0);
-    while (res > tol && nIter < maxIter && g1 != g2)
-    {
-        x0 = (x2*g1 - x1*g2)/(g1 - g2);
-        calcSubCell(celli, x0);
-        g0 = volumeOfFluid() - alpha1;
-        res = mag(g0);
-        x2 = x1; g2 = g1;
-        x1 = x0; g1 = g0;
-        nIter++;
-    }
-
-    if (debug)
-    {
-        if (res < tol)
-        {
-            Pout<< "Bisection finished the job in " << nIter << " iterations."
-                << endl;
-        }
-        else
-        {
-            Pout<< "Warning: Bisection not converged " << endl;
-            Pout<< "Leaving vofCutCell with f3 = " << f3 << " giving a3 = "
-                << a3 << " so alpha1 - a3 = " << alpha1 - a3 << endl;
-        }
-    }
-
-    return cellStatus_;
-}
-
-
-void Foam::isoCutCell::volumeOfFluid
-(
-    volScalarField& alpha1,
-    const scalar f0
-)
-{
-    // Setting internal field
-    scalarField& alphaIn = alpha1;
-    forAll(alphaIn, celli)
-    {
-        const label cellStatus = calcSubCell(celli, f0);
-        if (cellStatus != 1)
-        {
-            // If cell not entirely above isosurface
-            alphaIn[celli] = volumeOfFluid();
-        }
-    }
-
-    // Setting boundary alpha1 values
-    forAll(mesh_.boundary(), patchi)
-    {
-        if (mesh_.boundary()[patchi].size() > 0)
-        {
-            const label start = mesh_.boundary()[patchi].patch().start();
-            scalarField& alphap = alpha1.boundaryFieldRef()[patchi];
-            const scalarField& magSfp = mesh_.magSf().boundaryField()[patchi];
-
-            forAll(alphap, patchFacei)
-            {
-                const label facei = patchFacei + start;
-                const label faceStatus = isoCutFace_.calcSubFace(facei, f0);
-
-                if (faceStatus != 1)
-                {
-                    // Face not entirely above isosurface
-                    alphap[patchFacei] =
-                        mag(isoCutFace_.subFaceArea())/magSfp[patchFacei];
-                }
-            }
-        }
-    }
-}
-
-
-// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.C b/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.C
deleted file mode 100644
index 6e5586946512fa2eef9ef94c3081492aa3ab593c..0000000000000000000000000000000000000000
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.C
+++ /dev/null
@@ -1,773 +0,0 @@
-/*---------------------------------------------------------------------------*\
-  =========                 |
-  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
-   \\    /   O peration     |
-    \\  /    A nd           | www.openfoam.com
-     \\/     M anipulation  |
--------------------------------------------------------------------------------
-    Copyright (C) 2016-2017 DHI
-    Copyright (C) 2018 Johan Roenby
-    Copyright (C) 2016-2019 OpenCFD Ltd.
--------------------------------------------------------------------------------
-License
-    This file is part of OpenFOAM.
-
-    OpenFOAM is free software: you can redistribute it and/or modify it
-    under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
-    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-    for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
-
-\*---------------------------------------------------------------------------*/
-
-#include "isoCutFace.H"
-
-// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
-
-int Foam::isoCutFace::debug = 0;
-
-// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
-
-Foam::isoCutFace::isoCutFace
-(
-    const fvMesh& mesh,
-    scalarField& f
-)
-:
-    mesh_(mesh),
-    f_(f),
-    firstEdgeCut_(-1),
-    lastEdgeCut_(-1),
-    firstFullySubmergedPoint_(-1),
-    nFullySubmergedPoints_(0),
-    subFaceCentre_(Zero),
-    subFaceArea_(Zero),
-    subFacePoints_(10),
-    surfacePoints_(4),
-    subFaceCentreAndAreaIsCalculated_(false)
-{
-    clearStorage();
-}
-
-
-// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
-
-void Foam::isoCutFace::calcSubFaceCentreAndArea()
-{
-    const label nPoints = subFacePoints_.size();
-
-    // If the face is a triangle, do a direct calculation for efficiency
-    // and to avoid round-off error-related problems
-    if (nPoints == 3)
-    {
-        subFaceCentre_ = sum(subFacePoints_)/scalar(3);
-        subFaceArea_ =
-            0.5
-           *(
-                (subFacePoints_[1] - subFacePoints_[0])
-               ^(subFacePoints_[2] - subFacePoints_[0])
-            );
-    }
-    else if (nPoints > 0)
-    {
-        vector sumN(Zero);
-        scalar sumA(0.0);
-        vector sumAc(Zero);
-        const point fCentre = sum(subFacePoints_)/scalar(nPoints);
-
-        for (label pi = 0; pi < nPoints; pi++)
-        {
-            const point& nextPoint = subFacePoints_[subFacePoints_.fcIndex(pi)];
-
-            vector c = subFacePoints_[pi] + nextPoint + fCentre;
-            vector n =
-                (nextPoint - subFacePoints_[pi])^(fCentre - subFacePoints_[pi]);
-            scalar a = magSqr(n);
-
-            sumN += n;
-            sumA += a;
-            sumAc += a*c;
-        }
-
-        // This is to deal with zero-area faces. Mark very small faces
-        // to be detected in e.g., processorPolyPatch.
-        if (sumA < ROOTVSMALL)
-        {
-            subFaceCentre_ = fCentre;
-            subFaceArea_ = vector::zero;
-        }
-        else
-        {
-            subFaceCentre_ = (1.0/3.0)*sumAc/sumA;
-            subFaceArea_ = 0.5*sumN;
-        }
-    }
-
-    subFaceCentreAndAreaIsCalculated_ = true;
-}
-
-
-Foam::label Foam::isoCutFace::calcSubFace
-(
-    const scalar isoValue,
-    const pointField& points,
-    const scalarField& f,
-    const labelList& pLabels
-)
-{
-    // Face status set to one of the values:
-    //  -1: face is fully below the isosurface
-    //   0: face is cut, i.e. has values larger and smaller than isoValue
-    //  +1: face is fully above the isosurface
-    label faceStatus;
-
-    scalar f1 = f[pLabels[0]];
-
-    // If vertex values are very close to isoValue lift them slightly to avoid
-    // dealing with the many special cases of a face being touched either at a
-    // single point, along an edge, or the entire face being on the surface.
-    if (mag(f1 - isoValue) < 10*SMALL)
-    {
-        f1 += sign(f1 - isoValue)*10*SMALL;
-    }
-
-    // Finding cut edges, the point along them where they are cut, and all fully
-    // submerged face points.
-    forAll(pLabels, pi)
-    {
-        label pl2 = pLabels[pLabels.fcIndex(pi)];
-        scalar f2 = f[pl2];
-        if (mag(f2 - isoValue) < 10*SMALL)
-        {
-            f2 += sign(f2 - isoValue)*10*SMALL;
-        }
-
-        if (f1 > isoValue)
-        {
-            nFullySubmergedPoints_ += 1;
-
-            if (f2 < isoValue)
-            {
-                lastEdgeCut_ = (isoValue - f1)/(f2 - f1);
-            }
-        }
-        else if (f1 < isoValue && f2 > isoValue)
-        {
-            if (firstFullySubmergedPoint_ == -1)
-            {
-                firstFullySubmergedPoint_ = pLabels.fcIndex(pi);
-
-                firstEdgeCut_ = (isoValue - f1)/(f2 - f1);
-            }
-            else
-            {
-                if (debug)
-                {
-                    const face fl(pLabels);
-
-                    WarningInFunction
-                        << "More than two face cuts for face " << fl
-                        << endl;
-
-                    Pout<< "Face values: f-isoValue = " << endl;
-                    forAll(fl, fpi)
-                    {
-                        Pout<< f[fl[fpi]] - isoValue << " ";
-                    }
-                    Pout<< " " << endl;
-                }
-            }
-        }
-        f1 = f2;
-    }
-
-    if (firstFullySubmergedPoint_ != -1)
-    {
-        // Face is cut
-        faceStatus = 0;
-        subFacePoints(points, pLabels);
-    }
-    else if (f1 < isoValue)
-    {
-        // Face entirely above isosurface
-        faceStatus = 1;
-    }
-    else
-    {
-        // Face entirely below isosurface
-        faceStatus = -1;
-    }
-
-    return faceStatus;
-}
-
-
-void Foam::isoCutFace::subFacePoints
-(
-    const pointField& points,
-    const labelList& pLabels
-)
-{
-    const label nPoints = pLabels.size();
-
-    surfacePoints(points, pLabels);
-
-    forAll(surfacePoints_, pi)
-    {
-        subFacePoints_.append(surfacePoints_[pi]);
-    }
-
-    for (label pi = 0; pi < nFullySubmergedPoints_; pi++)
-    {
-        subFacePoints_.append
-        (
-            points[pLabels[(firstFullySubmergedPoint_ + pi) % nPoints]]
-        );
-    }
-}
-
-
-void Foam::isoCutFace::surfacePoints
-(
-    const pointField& points,
-    const labelList& pLabels
-)
-{
-    const label nPoints = pLabels.size();
-
-    const label n = firstFullySubmergedPoint_ + nFullySubmergedPoints_;
-
-    label pl1 = pLabels[(n - 1) % nPoints];
-
-    label pl2 = pLabels[n % nPoints];
-
-    surfacePoints_.append
-    (
-        points[pl1] + lastEdgeCut_*(points[pl2] - points[pl1])
-    );
-
-    pl1 = pLabels[(firstFullySubmergedPoint_ - 1 + nPoints) % nPoints];
-    pl2 = pLabels[firstFullySubmergedPoint_];
-
-    surfacePoints_.append
-    (
-        points[pl1] + firstEdgeCut_*(points[pl2] - points[pl1])
-    );
-}
-
-
-// * * * * * * * * * * * Public Member Functions  * * * * * * * * * * * * * //
-
-Foam::label Foam::isoCutFace::calcSubFace
-(
-    const label faceI,
-    const scalar isoValue
-)
-{
-    clearStorage();
-    const labelList& pLabels = mesh_.faces()[faceI];
-    const pointField& points = mesh_.points();
-    return calcSubFace(isoValue, points, f_, pLabels);
-}
-
-
-Foam::label Foam::isoCutFace::calcSubFace
-(
-    const pointField& points,
-    const scalarField& f,
-    const scalar isoValue
-)
-{
-    clearStorage();
-    const labelList pLabels(identity(f.size()));
-    return calcSubFace(isoValue, points, f, pLabels);
-}
-
-
-const Foam::point& Foam::isoCutFace::subFaceCentre()
-{
-    if (!subFaceCentreAndAreaIsCalculated_)
-    {
-        calcSubFaceCentreAndArea();
-    }
-    return subFaceCentre_;
-}
-
-
-const Foam::vector& Foam::isoCutFace::subFaceArea()
-{
-    if (!subFaceCentreAndAreaIsCalculated_)
-    {
-        calcSubFaceCentreAndArea();
-    }
-    return subFaceArea_;
-}
-
-
-const Foam::DynamicList<Foam::point>& Foam::isoCutFace::subFacePoints() const
-{
-    return subFacePoints_;
-}
-
-
-const Foam::DynamicList<Foam::point>& Foam::isoCutFace::surfacePoints() const
-{
-    return surfacePoints_;
-}
-
-
-void Foam::isoCutFace::clearStorage()
-{
-    firstEdgeCut_ = -1;
-    lastEdgeCut_ = -1;
-    firstFullySubmergedPoint_ = -1;
-    nFullySubmergedPoints_ = 0;
-    subFaceCentre_ = vector::zero;
-    subFaceArea_ = vector::zero;
-    subFacePoints_.clear();
-    surfacePoints_.clear();
-    subFaceCentreAndAreaIsCalculated_ = false;
-}
-
-
-Foam::scalar Foam::isoCutFace::timeIntegratedFaceFlux
-(
-    const label facei,
-    const vector& x0,
-    const vector& n0,
-    const scalar Un0,
-    const scalar f0,
-    const scalar dt,
-    const scalar phi,
-    const scalar magSf
-)
-{
-/* Temporarily taken out
-    // Treating rare cases where isoface normal is not calculated properly
-    if (mag(n0) < 0.5)
-    {
-        scalar alphaf = 0;
-        scalar waterInUpwindCell = 0;
-
-        if (phi > 10*SMALL || !mesh_.isInternalFace(facei))
-        {
-            const label upwindCell = mesh_.faceOwner()[facei];
-            alphaf = alpha1In_[upwindCell];
-            waterInUpwindCell = alphaf*mesh_.cellVolumes()[upwindCell];
-        }
-        else
-        {
-            const label upwindCell = mesh_.faceNeighbour()[facei];
-            alphaf = alpha1In_[upwindCell];
-            waterInUpwindCell = alphaf*mesh_.cellVolumes()[upwindCell];
-        }
-
-        if (debug)
-        {
-            WarningInFunction
-                << "mag(n0) = " << mag(n0)
-                << " so timeIntegratedFlux calculates dVf from upwind"
-                << " cell alpha value: " << alphaf << endl;
-        }
-
-        return min(alphaf*phi*dt, waterInUpwindCell);
-    }
-*/
-
-    // Find sorted list of times where the isoFace will arrive at face points
-    // given initial position x0 and velocity Un0*n0
-
-    // Get points for this face
-    const face& f = mesh_.faces()[facei];
-    const pointField fPts(f.points(mesh_.points()));
-    const label nPoints = fPts.size();
-
-    scalarField pTimes(fPts.size());
-    if (mag(Un0) > 10*SMALL) // Note: tolerances
-    {
-        // Here we estimate time of arrival to the face points from their normal
-        // distance to the initial surface and the surface normal velocity
-
-        pTimes = ((fPts - x0) & n0)/Un0;
-
-        scalar dVf = 0;
-
-        // Check if pTimes changes direction more than twice when looping face
-        label nShifts = 0;
-        forAll(pTimes, pi)
-        {
-            const label oldEdgeSign =
-                sign(pTimes[(pi + 1) % nPoints] - pTimes[pi]);
-            const label newEdgeSign =
-                sign(pTimes[(pi + 2) % nPoints] - pTimes[(pi + 1) % nPoints]);
-
-            if (newEdgeSign != oldEdgeSign)
-            {
-                nShifts++;
-            }
-        }
-
-        if (nShifts == 2)
-        {
-            dVf = phi/magSf*timeIntegratedArea(fPts, pTimes, dt, magSf, Un0);
-        }
-        else if (nShifts > 2)
-        {
-            // Triangle decompose the face
-            pointField fPts_tri(3);
-            scalarField pTimes_tri(3);
-            fPts_tri[0] = mesh_.faceCentres()[facei];
-            pTimes_tri[0] = ((fPts_tri[0] - x0) & n0)/Un0;
-            for (label pi = 0; pi < nPoints; pi++)
-            {
-                fPts_tri[1] = fPts[pi];
-                pTimes_tri[1] = pTimes[pi];
-                fPts_tri[2] = fPts[(pi + 1) % nPoints];
-                pTimes_tri[2] = pTimes[(pi + 1) % nPoints];
-                const scalar magSf_tri =
-                    mag
-                    (
-                        0.5
-                       *(fPts_tri[2] - fPts_tri[0])
-                       ^(fPts_tri[1] - fPts_tri[0])
-                    );
-                const scalar phi_tri = phi*magSf_tri/magSf;
-                dVf += phi_tri/magSf_tri
-                   *timeIntegratedArea
-                    (
-                        fPts_tri,
-                        pTimes_tri,
-                        dt,
-                        magSf_tri,
-                        Un0
-                    );
-            }
-        }
-        else
-        {
-            if (debug)
-            {
-                WarningInFunction
-                    << "Warning: nShifts = " << nShifts << " on face " << facei
-                    << " with pTimes = " << pTimes << " owned by cell "
-                    << mesh_.faceOwner()[facei] << endl;
-            }
-        }
-
-        return dVf;
-    }
-    else
-    {
-        // Un0 is almost zero and isoFace is treated as stationary
-        calcSubFace(facei, f0);
-        const scalar alphaf = mag(subFaceArea()/magSf);
-
-        if (debug)
-        {
-            WarningInFunction
-                << "Un0 is almost zero (" << Un0
-                << ") - calculating dVf on face " << facei
-                << " using subFaceFraction giving alphaf = " << alphaf
-                << endl;
-        }
-
-        return phi*dt*alphaf;
-    }
-}
-
-
-Foam::scalar Foam::isoCutFace::timeIntegratedArea
-(
-    const pointField& fPts,
-    const scalarField& pTimes,
-    const scalar dt,
-    const scalar magSf,
-    const scalar Un0
-)
-{
-    // Initialise time integrated area returned by this function
-    scalar tIntArea = 0.0;
-
-    // Finding ordering of vertex points
-    labelList order(sortedOrder(pTimes));
-    const scalar firstTime = pTimes[order.first()];
-    const scalar lastTime = pTimes[order.last()];
-
-    // Dealing with case where face is not cut by surface during time interval
-    // [0,dt] because face was already passed by surface
-    if (lastTime <= 0)
-    {
-        // If all face cuttings were in the past and cell is filling up (Un0>0)
-        // then face must be full during whole time interval
-        tIntArea = magSf*dt*pos0(Un0);
-        return tIntArea;
-    }
-
-    // Dealing with case where face is not cut by surface during time interval
-    // [0, dt] because dt is too small for surface to reach closest face point
-    if (firstTime >= dt)
-    {
-        // If all cuttings are in the future but non of them within [0,dt] then
-        // if cell is filling up (Un0 > 0) face must be empty during whole time
-        // interval
-        tIntArea = magSf*dt*(1 - pos0(Un0));
-        return tIntArea;
-    }
-
-    // If we reach this point in the code some part of the face will be swept
-    // during [tSmall, dt-tSmall]. However, it may be the case that there are no
-    // vertex times within the interval. This will happen sometimes for small
-    // time steps where both the initial and the final face-interface
-    // intersection line (FIIL) will be along the same two edges.
-
-    // Face-interface intersection line (FIIL) to be swept across face
-    DynamicList<point> FIIL(3);
-    // Submerged area at beginning of each sub time interval time
-    scalar initialArea = 0.0;
-    //Running time keeper variable for the integration process
-    scalar time = 0.0;
-
-    // Special treatment of first sub time interval
-    if (firstTime > 0)
-    {
-        // If firstTime > 0 the face is uncut in the time interval
-        // [0, firstTime] and hence fully submerged in fluid A or B.
-        // If Un0 > 0 cell is filling up and it must initially be empty.
-        // If Un0 < 0 cell must initially be full(y immersed in fluid A).
-        time = firstTime;
-        initialArea = magSf*(1.0 - pos0(Un0));
-        tIntArea = initialArea*time;
-        cutPoints(fPts, pTimes, time, FIIL);
-    }
-    else
-    {
-        // If firstTime <= 0 then face is initially cut and we must
-        // calculate the initial submerged area and FIIL:
-        time = 0.0;
-        // Note: calcSubFace assumes well-defined 2-point FIIL!!!!
-        calcSubFace(fPts, -sign(Un0)*pTimes, time);
-        initialArea = mag(subFaceArea());
-        cutPoints(fPts, pTimes, time, FIIL);
-    }
-
-    // Making sorted array of all vertex times that are between max(0,firstTime)
-    // and dt and further than tSmall from the previous time.
-    DynamicList<scalar> sortedTimes(pTimes.size());
-    {
-        scalar prevTime = time;
-        const scalar tSmall = max(1e-6*dt, 10*SMALL);
-        forAll(order, ti)
-        {
-            const scalar timeI = pTimes[order[ti]];
-            if ( timeI > prevTime + tSmall && timeI <= dt)
-            {
-                sortedTimes.append(timeI);
-                prevTime = timeI;
-            }
-        }
-    }
-
-    // Sweeping all quadrilaterals corresponding to the intervals defined above
-    forAll(sortedTimes, ti)
-    {
-        const scalar newTime = sortedTimes[ti];
-        // New face-interface intersection line
-        DynamicList<point> newFIIL(3);
-        cutPoints(fPts, pTimes, newTime, newFIIL);
-
-        // quadrilateral area coefficients
-        scalar alpha = 0, beta = 0;
-        quadAreaCoeffs(FIIL, newFIIL, alpha, beta);
-        // Integration of area(t) = A*t^2+B*t from t = 0 to 1
-        tIntArea += (newTime - time)*
-            (initialArea + sign(Un0)*(alpha/3.0 + 0.5*beta));
-        // Adding quad area to submerged area
-        initialArea += sign(Un0)*(alpha + beta);
-
-        FIIL = newFIIL;
-        time = newTime;
-    }
-
-    // Special treatment of last time interval
-    if (lastTime > dt)
-    {
-        // FIIL will end up cutting the face at dt
-        // New face-interface intersection line
-        DynamicList<point> newFIIL(3);
-        cutPoints(fPts, pTimes, dt, newFIIL);
-
-        // quadrilateral area coefficients
-        scalar alpha = 0, beta = 0;
-        quadAreaCoeffs(FIIL, newFIIL, alpha, beta);
-        // Integration of area(t) = A*t^2+B*t from t = 0 to 1
-        tIntArea += (dt - time)*
-            (initialArea + sign(Un0)*(alpha/3.0 + 0.5*beta));
-    }
-    else
-    {
-        // FIIL will leave the face at lastTime and face will be fully in fluid
-        // A or fluid B in the time interval from lastTime to dt.
-        tIntArea += magSf*(dt - lastTime)*pos0(Un0);
-    }
-
-    return tIntArea;
-}
-
-
-void Foam::isoCutFace::cutPoints
-(
-    const pointField& pts,
-    const scalarField& f,
-    const scalar f0,
-    DynamicList<point>& cutPoints
-)
-{
-    const label nPoints = pts.size();
-    scalar f1(f[0]);
-
-    // Snapping vertex value to f0 if very close (needed for 2D cases)
-    if (mag(f1 - f0) < 10*SMALL)
-    {
-        f1 = f0;
-    }
-
-    forAll(pts, pi)
-    {
-        label pi2 = (pi + 1) % nPoints;
-        scalar f2 = f[pi2];
-
-        // Snapping vertex value
-        if (mag(f2 - f0) < 10*SMALL)
-        {
-            f2 = f0;
-        }
-
-        if ((f1 < f0 && f2 > f0) || (f1 > f0 && f2 < f0))
-        {
-            const scalar s = (f0 - f1)/(f2 - f1);
-            cutPoints.append(pts[pi] + s*(pts[pi2] - pts[pi]));
-        }
-        else if (f1 == f0)
-        {
-            cutPoints.append(pts[pi]);
-        }
-        f1 = f2;
-    }
-
-    if (cutPoints.size() > 2)
-    {
-        WarningInFunction << "cutPoints = " << cutPoints << " for pts = " << pts
-            << ", f - f0 = " << f - f0 << " and f0 = " << f0 << endl;
-    }
-}
-
-
-void Foam::isoCutFace::quadAreaCoeffs
-(
-    const DynamicList<point>& pf0,
-    const DynamicList<point>& pf1,
-    scalar& alpha,
-    scalar& beta
-) const
-{
-    // Number of points in provided face-interface intersection lines
-    const label np0 = pf0.size();
-    const label np1 = pf1.size();
-
-    // quad area coeffs such that area(t) = alpha*t^2 + beta*t.
-    // With time interval normalised, we have full quadArea = alpha + beta
-    // and time integrated quad area = alpha/3 + beta/2;
-    alpha = 0.0;
-    beta = 0.0;
-
-    if (np0 && np1)
-    {
-        // Initialising quadrilateral vertices A, B, C and D
-        vector A(pf0[0]);
-        vector C(pf1[0]);
-        vector B(pf0[0]);
-        vector D(pf1[0]);
-
-        if (np0 == 2)
-        {
-            B = pf0[1];
-        }
-        else if (np0 > 2)
-        {
-            WarningInFunction << "Vertex face was cut at pf0 = " << pf0 << endl;
-        }
-
-        if (np1 == 2)
-        {
-            D = pf1[1];
-        }
-        else if (np1 > 2)
-        {
-            WarningInFunction << "Vertex face was cut at pf1 = " << pf1 << endl;
-        }
-
-        // Swapping pf1 points if pf0 and pf1 point in same general direction
-        // (because we want a quadrilateral ABCD where pf0 = AB and pf1 = CD)
-        if (((B - A) & (D - C)) > 0)
-        {
-            vector tmp = D;
-            D = C;
-            C = tmp;
-        }
-
-        // Defining local coordinates (xhat, yhat) for area integration of swept
-        // quadrilateral ABCD such that A = (0,0), B = (Bx,0), C = (Cx,Cy) and
-        // D = (Dx,Dy) with Cy = 0 and Dy > 0.
-
-        const scalar Bx = mag(B - A);
-
-        vector xhat(Zero);
-        if (Bx > 10*SMALL)
-        {
-            // If |AB| > 0 ABCD we use AB to define xhat
-            xhat = normalised(B - A);
-        }
-        else if (mag(C - D) > 10*SMALL)
-        {
-            // If |AB| ~ 0 ABCD is a triangle ACD and we use CD for xhat
-            xhat = normalised(C - D);
-        }
-        else
-        {
-            return;
-        }
-
-        // Defining vertical axis in local coordinates
-        vector yhat = D - A;
-        yhat -= ((yhat & xhat)*xhat);
-
-        if (mag(yhat) > 10*SMALL)
-        {
-            yhat /= mag(yhat);
-
-            const scalar Cx = (C - A) & xhat;
-            const scalar Cy = mag((C - A) & yhat);
-            const scalar Dx = (D - A) & xhat;
-            const scalar Dy = mag((D - A) & yhat);
-
-            // area = ((Cx - Bx)*Dy - Dx*Cy)/6.0 + 0.25*Bx*(Dy + Cy);
-            alpha = 0.5*((Cx - Bx)*Dy - Dx*Cy);
-            beta = 0.5*Bx*(Dy + Cy);
-        }
-    }
-    else
-    {
-        WarningInFunction
-            << "Vertex face was cut at " << pf0 << " and at " << pf1 << endl;
-    }
-}
-
-
-// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.H b/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.H
deleted file mode 100644
index 56c2b6f22f68498f7e51f24fba4126b559761c33..0000000000000000000000000000000000000000
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutFace/isoCutFace.H
+++ /dev/null
@@ -1,215 +0,0 @@
-/*---------------------------------------------------------------------------*\
-  =========                 |
-  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
-   \\    /   O peration     |
-    \\  /    A nd           | www.openfoam.com
-     \\/     M anipulation  |
--------------------------------------------------------------------------------
-    Copyright (C) 2016-2017 DHI
-    Copyright (C) 2016-2017 OpenCFD Ltd.
-    Copyright (C) 2018 Johan Roenby
--------------------------------------------------------------------------------
-License
-    This file is part of OpenFOAM.
-
-    OpenFOAM is free software: you can redistribute it and/or modify it
-    under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
-    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
-    for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
-
-Class
-    Foam::isoCutFace
-
-Description
-    Class for cutting a face, faceI, of an fvMesh, mesh_, at its intersection
-    with an isosurface defined by the mesh point values f_ and the isovalue,
-    isoValue_.
-
-    Reference:
-        \verbatim
-            Roenby, J., Bredmose, H. and Jasak, H. (2016).
-            A computational method for sharp interface advection
-            Royal Society Open Science, 3
-            doi 10.1098/rsos.160405
-        \endverbatim
-
-    Original code supplied by Johan Roenby, DHI (2016)
-
-SourceFiles
-    isoCutFace.C
-
-\*---------------------------------------------------------------------------*/
-
-#ifndef isoCutFace_H
-#define isoCutFace_H
-
-#include "fvMesh.H"
-
-// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
-
-namespace Foam
-{
-
-/*---------------------------------------------------------------------------*\
-                        Class isoCutFaces Declaration
-\*---------------------------------------------------------------------------*/
-
-class isoCutFace
-{
-    // Private data
-
-        //- Mesh whose cells and faces to cut at their intersection with an
-        //  isoface
-        const fvMesh& mesh_;
-
-        //- Isofunction values at mesh points. f_size() = mesh_.nPoints()
-        scalarField& f_;
-
-        //- Point along first cut edge where isosurface cuts edge
-        scalar firstEdgeCut_;
-
-        //- Point along last cut edge where isosurface cuts edge
-        scalar lastEdgeCut_;
-
-        //- Index in mesh_.faces()[faceI_] of first fully submerged (f > f0)
-        //  face point
-        label firstFullySubmergedPoint_;
-
-        //- Index in mesh_.faces()[faceI_] of last fully submerged (f > f0)
-        //  face point
-        label nFullySubmergedPoints_;
-
-        //- Storage for centre of subface
-        point subFaceCentre_;
-
-        //- Storage for area vector of subface
-        vector subFaceArea_;
-
-        //- Storage for subFacePoints
-        DynamicList<point> subFacePoints_;
-
-        //- Storage for subFacePoints
-        DynamicList<point> surfacePoints_;
-
-        //- Boolean telling if subface centre and area have been calculated
-        bool subFaceCentreAndAreaIsCalculated_;
-
-
-    // Private Member Functions
-
-        void calcSubFaceCentreAndArea();
-
-        //- Calculate cut points along edges of face with values f[pLabels]
-        //  Returns the face status, where:
-        //  -1: face is fully below the isosurface
-        //   0: face is cut, i.e. has values larger and smaller than isoValue
-        //  +1: face is fully above the isosurface
-        label calcSubFace
-        (
-            const scalar isoValue,
-            const pointField& points,
-            const scalarField& f,
-            const labelList& pLabels
-        );
-
-        void subFacePoints(const pointField& points, const labelList& pLabels);
-
-        void surfacePoints(const pointField& points, const labelList& pLabels);
-
-
-public:
-
-    // Constructors
-
-        //- Construct from fvMesh and a scalarField
-        //  Length of scalarField should equal number of mesh points
-        isoCutFace(const fvMesh& mesh, scalarField& f);
-
-    // Static data
-
-        static int debug;
-
-
-    // Member functions
-
-        //- Calculate cut points along edges of faceI
-        label calcSubFace(const label faceI, const scalar isoValue);
-
-        //- Calculate cut points along edges of face with values f
-        label calcSubFace
-        (
-            const pointField& points,
-            const scalarField& f,
-            const scalar isoValue
-        );
-
-        const point& subFaceCentre();
-
-        const vector& subFaceArea();
-
-        const DynamicList<point>& subFacePoints() const;
-
-        const DynamicList<point>& surfacePoints() const;
-
-        void clearStorage();
-
-        //- Calculate volumetric face transport during dt given the isoFace
-        //  data provided as input for face facei
-        scalar timeIntegratedFaceFlux
-        (
-            const label facei,
-            const vector& x0,
-            const vector& n0,
-            const scalar Un0,
-            const scalar f0,
-            const scalar dt,
-            const scalar phi,
-            const scalar magSf
-        );
-
-        //- Calculate time integrated area for a face
-        scalar timeIntegratedArea
-        (
-            const pointField& fPts,
-            const scalarField& pTimes,
-            const scalar dt,
-            const scalar magSf,
-            const scalar Un0
-        );
-
-        void cutPoints
-        (
-            const pointField& pts,
-            const scalarField& f,
-            const scalar f0,
-            DynamicList<point>& cutPoints
-        );
-
-
-        void quadAreaCoeffs
-        (
-            const DynamicList<point>& pf0,
-            const DynamicList<point>& pf1,
-            scalar& alpha,
-            scalar& beta
-        ) const;
-};
-
-
-// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
-
-} // End namespace Foam
-
-// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
-
-#endif
-
-// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.C b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.C
new file mode 100644
index 0000000000000000000000000000000000000000..2f0e00787e3876fc3314dce9649eefaad82e7df2
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.C
@@ -0,0 +1,168 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "leastSquareGrad.H"
+#include "emptyPolyPatch.H"
+#include "processorPolyPatch.H"
+#include "wedgePolyPatch.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+template<class T>
+Foam::leastSquareGrad<T>::leastSquareGrad
+(
+    const word& functionName,
+    const labelVector& geomDir
+)
+:
+    polyFitter_(functionName,geomDir),
+    geomDir_(geomDir),
+    nDims_(0)
+{
+    // Compute number of dimensions
+    for (const label dirn : geomDir_)
+    {
+        if (dirn == 1)
+        {
+            ++nDims_;
+        }
+    }
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+template<class T>
+typename Foam::outerProduct<Foam::vector, T>::type
+Foam::leastSquareGrad<T>::grad
+(
+    const List<vector>& positions,
+    const List<T>& listValue
+)
+{
+    typedef typename outerProduct<vector, T>::type GradType;
+
+    List<T> fitData = polyFitter_.fitData
+    (
+        positions,
+        listValue
+    );
+
+    if (nDims_ == 3)
+    {
+        return GradType(fitData[1],fitData[2],fitData[3]);
+    }
+
+
+    label dimCounter = 0;
+
+    GradType ret(Zero);
+
+    forAll(geomDir_,i)
+    {
+        if (geomDir_[i] == 1)
+        {
+            ++dimCounter;
+            ret[i] = fitData[dimCounter];
+        }
+    }
+
+    return ret;
+}
+
+
+namespace Foam // needed g++ bug
+{
+    template<>
+    tensor leastSquareGrad<vector>::grad
+    (
+        const List<vector>& positions,
+        const List<vector>& listValue
+    )
+    {
+        typedef tensor GradType;
+
+        List<vector> fitData = polyFitter_.fitData
+        (
+            positions,
+            listValue
+        );
+
+        if (nDims_ == 3)
+        {
+            return GradType(fitData[1],fitData[2],fitData[3]);
+        }
+
+        label dimCounter = 0;
+
+        GradType ret(Zero);
+
+        forAll(geomDir_,i)
+        {
+            if (geomDir_[i] == 1)
+            {
+                ++dimCounter;
+                ret.row(i, fitData[dimCounter]);
+            }
+        }
+
+        return ret;
+    }
+}
+
+
+template<class T>
+Foam::Map<typename Foam::outerProduct<Foam::vector, T>::type>
+Foam::leastSquareGrad<T>::grad
+(
+    const Map<List<vector>>& positions,
+    const Map<List<T>>& listValue
+)
+{
+    typedef typename outerProduct<vector, T>::type GradType;
+
+    Map<GradType> gradMap(positions.capacity());
+
+    forAllConstIters(positions, iter)
+    {
+        const label key = iter.key();
+        const List<vector>& positions = iter.val();
+
+        GradType grad(this->grad(positions, listValue[key]));
+
+        gradMap.insert(key, grad);
+    }
+
+    return gradMap;
+}
+
+
+template class Foam::leastSquareGrad<Foam::scalar>;
+template class Foam::leastSquareGrad<Foam::vector>;
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.H b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.H
new file mode 100644
index 0000000000000000000000000000000000000000..9587879ecfa3397dd6c94abc59c4cb1ef910628e
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/leastSquareGrad.H
@@ -0,0 +1,101 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::leastSquareGrad
+
+Description
+    Estimates the gradient with a least square scheme in a cell
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    leastSquareGrad.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef leastSquareGrad_H
+#define leastSquareGrad_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+#include "OFstream.H"
+#include "multiDimPolyFitter.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class leastSquareGrad Declaration
+\*---------------------------------------------------------------------------*/
+template<class T>
+class leastSquareGrad
+{
+    // Private Data
+
+        multiDimPolyFitter<T> polyFitter_;
+
+        labelVector geomDir_;
+
+        label nDims_;
+
+
+public:
+
+    // Constructors
+
+        //- Construct from components
+        leastSquareGrad(const word& functionName, const labelVector& geomDir);
+
+
+    // Member Functions
+
+        //- Return the gradient of the cell
+        typename outerProduct<vector, T>::type grad
+        (
+            const List<vector>& positions,
+            const List<T>& listValue
+        );
+
+        Map<typename outerProduct<vector, T>::type> grad
+        (
+            const Map<List<vector>>& positions,
+            const Map<List<T>>& listValue
+        );
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.C b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.C
new file mode 100644
index 0000000000000000000000000000000000000000..8a03b5ff5cd53932d7426f0eef615cb6581f7a16
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.C
@@ -0,0 +1,375 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "multiDimPolyFitter.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+template<class T>
+Foam::multiDimPolyFitter<T>::multiDimPolyFitter
+(
+    const word& polyFunctionName,
+    const labelVector& geomDirs
+)
+:
+    polyFunc_(multiDimPolyFunctions::New(polyFunctionName,geomDirs)),
+    A_(polyFunc_->nTerms(), scalar(0), Zero)
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+template<class T>
+void Foam::multiDimPolyFitter<T>::resetMatrix()
+{
+    for (label i=0;i<A_.size();i++)
+    {
+        A_.data()[i] = Zero;
+    }
+    A_.source() = Zero;
+}
+
+
+template<class T>
+void Foam::multiDimPolyFitter<T>::fillMatrix
+(
+    const scalarField& polyTerms,
+    const T& value
+)
+{
+    const label size = A_.n();
+
+    // simple matrix is a square
+
+    for (label i=0; i<size; ++i) // col
+    {
+        A_.source()[i] += polyTerms[i]*value;
+        scalar* luMatrixi = A_[i];
+        const scalar tmpValue = polyTerms[i];
+
+        for (label j=0; j<size; ++j) // row
+        {
+            luMatrixi[j] += tmpValue*polyTerms[j];
+        }
+    }
+}
+
+
+template<class T>
+void Foam::multiDimPolyFitter<T>::fillMatrix
+(
+    const scalarField& polyTerms,
+    const T& value,
+    const scalar weight
+)
+{
+    const label size = A_.n();
+
+    //simple matrix is a square
+
+    for (label i=0; i<size; ++i) // col
+    {
+        A_.source()[i] += polyTerms[i]*value*weight;
+        scalar* __restrict luMatrixi = A_[i];
+        const scalar tmpValue = polyTerms[i];
+
+        for (label j=0; j<size; j++) // row
+        {
+            luMatrixi[j] += tmpValue*polyTerms[j]*weight;
+        }
+    }
+}
+
+
+template<class T>
+void Foam::multiDimPolyFitter<T>::fillMatrix
+(
+    const scalarField& polyTerms,
+    scalarSymmetricSquareMatrix& A
+)
+{
+    const label size = A.n();
+
+    // simple matrix is a square
+    for (label i=0; i<size; ++i)
+    {
+        for (label j=0; j<size; ++j)
+        {
+            A[i][j] += polyTerms[i]*polyTerms[j];
+        }
+    }
+}
+
+
+template<class T>
+Foam::Field<T> Foam::multiDimPolyFitter<T>::fitData
+(
+    const List<scalarField>& listPolyTerms,
+    const List<T>& listValue
+)
+{
+    // operator= does not work
+    resetMatrix();
+    if (listPolyTerms.size() == listValue.size())
+    {
+        forAll(listPolyTerms,i)
+        {
+            fillMatrix
+            (
+                listPolyTerms[i],
+                listValue[i]
+            );
+        }
+        // Solve the matrix using Gaussian elimination with pivoting
+        return A_.LUsolve();
+    }
+    else
+    {
+        FatalErrorInFunction
+            << "size of listPolyTerms: " << listPolyTerms.size()
+            << "size of listValues is: " <<  listValue.size()
+            << " they must match!" << nl
+            << exit(FatalError);
+        return Field<T>();
+    }
+}
+
+
+template<class T>
+Foam::Field<T> Foam::multiDimPolyFitter<T>::fitData
+(
+    const List<scalarField>& listPolyTerms,
+    const List<T>& listValue,
+    const List<scalar>& listWeight
+)
+{
+    // operator= does not work
+    resetMatrix();
+    if (listPolyTerms.size() == listValue.size())
+    {
+        forAll(listPolyTerms, i)
+        {
+            fillMatrix
+            (
+                listPolyTerms[i],
+                listValue[i],
+                listWeight[i]
+            );
+        }
+
+        // Solve the matrix using Gaussian elimination with pivoting
+        return A_.LUsolve();
+    }
+    else
+    {
+        FatalErrorInFunction
+            << "size of listPolyTerms: " << listPolyTerms.size()
+            << "size of listValues is:" <<  listValue.size()
+            << "they have to match"
+            << exit(FatalError);
+
+        return Field<T>();
+    }
+}
+
+
+template<class T>
+Foam::scalarSymmetricSquareMatrix Foam::multiDimPolyFitter<T>::computeInverse
+(
+    const List<scalarField>& listPolyTerms
+)
+{
+    // operator= does not work
+    scalarSymmetricSquareMatrix symMatrix(A_.n(), Zero);
+    forAll(listPolyTerms,i)
+    {
+        fillMatrix
+        (
+            listPolyTerms[i],
+            symMatrix
+        );
+    }
+
+    return inv(symMatrix);
+}
+
+
+template<class T>
+Foam::Field<T> Foam::multiDimPolyFitter<T>::computeMatrixSource
+(
+    const List<scalarField>& listPolyTerms,
+    const List<T>& listValue
+)
+{
+    if (listPolyTerms.size() != listValue.size())
+    {
+        FatalErrorInFunction
+            << "size of listPolyTerms: " << listPolyTerms.size()
+            << "size of listValues is:" <<  listValue.size()
+            << "they have to match"
+            << exit(FatalError);
+    }
+
+    Field<T> source(listPolyTerms.size(), Zero);
+
+    forAll(source, i)
+    {
+        forAll(listPolyTerms[i], j)
+        {
+            source[i] += listPolyTerms[i][j]*listValue[i];
+        }
+    }
+
+    return source;
+}
+
+
+template<class T>
+Foam::Field<T> Foam::multiDimPolyFitter<T>::fitData
+(
+    const List<vector>& positions,
+    const List<T>& listValue
+)
+{
+    // operator= does not work
+    if (positions.size() != listValue.size())
+    {
+        FatalErrorInFunction
+            << "size of positions and listValues don't match" << nl
+            << "size of positions is: " << positions.size()  << nl
+            << "size of listValues is: " <<  listValue.size() << nl
+            << exit(FatalError);
+    }
+
+    resetMatrix();
+
+    forAll(positions, i)
+    {
+        fillMatrix
+        (
+            polyFunc_->termValues(positions[i]),
+            listValue[i]
+        );
+    }
+
+    // Solve the matrix using Gaussian elimination with pivoting
+    return A_.LUsolve();
+}
+
+
+template<class T>
+Foam::Field<T> Foam::multiDimPolyFitter<T>::fitData
+(
+    const List<vector>& positions,
+    const List<T>& listValue,
+    const List<scalar>& listWeight
+)
+{
+    // operator= does not work
+    if (positions.size() != listValue.size())
+    {
+        FatalErrorInFunction
+            << "size of positions and listValues don't match" << nl
+            << "size of positions is: " << positions.size()  << nl
+            << "size of listValues is: " <<  listValue.size() << nl
+            << exit(FatalError);
+    }
+
+    resetMatrix();
+
+    forAll(positions, i)
+    {
+        fillMatrix
+        (
+            polyFunc_->termValues(positions[i]),
+            listValue[i],
+            listWeight[i]
+        );
+    }
+
+    // Solve the matrix using Gaussian elimination with pivoting
+    return A_.LUsolve();
+}
+
+
+template<class T>
+Foam::scalarSymmetricSquareMatrix Foam::multiDimPolyFitter<T>::computeInverse
+(
+    const List<vector>& positions
+)
+{
+    // operator= does not work
+    scalarSymmetricSquareMatrix symMatrix(A_.n(), Zero);
+    forAll(positions, i)
+    {
+        fillMatrix
+        (
+            polyFunc_->termValues(positions[i]),
+            symMatrix
+        );
+    }
+
+    return inv(symMatrix);
+}
+
+
+template<class T>
+Foam::Field<T> Foam::multiDimPolyFitter<T>::computeMatrixSource
+(
+    const List<vector>& positions,
+    const List<T>& listValue
+)
+{
+    if (positions.size() != listValue.size())
+    {
+        FatalErrorInFunction
+            << "size of positions: " << positions.size()
+            << "size of listValues is:" <<  listValue.size()
+            << "they have to match"
+            << exit(FatalError);
+    }
+
+    Field<T> source(polyFunc_->nTerms(), Zero);
+
+    forAll(source, i)
+    {
+        scalarField polyTerms = polyFunc_->termValues(positions[i]);
+        forAll(polyTerms, j)
+        {
+            source[i] += polyTerms[j]*listValue[i];
+        }
+    }
+
+    return source;
+}
+
+
+template class Foam::multiDimPolyFitter<Foam::scalar>;
+template class Foam::multiDimPolyFitter<Foam::vector>;
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.H b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.H
new file mode 100644
index 0000000000000000000000000000000000000000..60874e6d415bda317209a765ac7b23934ab5c8ef
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFitter.H
@@ -0,0 +1,170 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::multiDimPolyFitter
+
+Description
+    Fit a polynominal function with the help of multiDimPolyFunction
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    multiDimPolyFitter.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef multiDimPolyFitter_H
+#define multiDimPolyFitter_H
+
+#include "simpleMatrix.H"
+#include "multiDimPolyFunctions.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class multiDimPolyFitter Declaration
+\*---------------------------------------------------------------------------*/
+
+template<class T>
+class multiDimPolyFitter
+{
+    // Private Data
+
+        autoPtr<multiDimPolyFunctions> polyFunc_;
+
+        simpleMatrix<T> A_;
+
+
+public:
+
+    // Constructors
+
+       //- Construct from components
+       multiDimPolyFitter
+       (
+           const word& polyFunctionName,
+           const labelVector& geomDirs
+       );
+
+
+    // Member Functions
+
+        void resetMatrix();
+
+        label nCoeffs() const
+        {
+            return A_.n();
+        }
+
+        void fillMatrix
+        (
+            const scalarField& polyTerms,
+            const T& value
+        );
+
+        void fillMatrix
+        (
+            const scalarField& polyTerms,
+            const T& value,
+            const scalar weight
+        );
+
+        void fillMatrix
+        (
+            const scalarField& polyTerms,
+            scalarSymmetricSquareMatrix& A
+        );
+
+        //- Fit data
+        Field<T> fitData
+        (
+            const List<scalarField>& listPolyTerms,
+            const List<T>& listValue
+        );
+
+        //- Fit data
+        Field<T> fitData
+        (
+            const List<scalarField>& listPolyTerms,
+            const List<T>& listValue,
+            const List<scalar>& listWeight
+        );
+
+        //- Compute inverse
+        scalarSymmetricSquareMatrix computeInverse
+        (
+            const List<scalarField>& listPolyTerms
+        );
+
+        //- Compute source
+        Field<T> computeMatrixSource
+        (
+            const List<scalarField>& listPolyTerms,
+            const List<T>& listValue
+        );
+
+        //- Fit data
+        Field<T> fitData
+        (
+            const List<vector>& positions,
+            const List<T>& listValue
+        );
+
+        //- Fit data
+        Field<T> fitData
+        (
+            const List<vector>& positions,
+            const List<T>& listValue,
+            const List<scalar>& listWeight
+        );
+
+        //- Compute inverse
+        scalarSymmetricSquareMatrix computeInverse
+        (
+            const List<vector>& positions
+        );
+
+        //- Compute source
+        Field<T> computeMatrixSource
+        (
+            const List<vector>& positions,
+            const List<T>& listValue
+        );
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.C b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.C
new file mode 100644
index 0000000000000000000000000000000000000000..07df3230b5a2e5edf13939b33669a9185473333d
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.C
@@ -0,0 +1,76 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "multiDimPolyFunctions.H"
+#include "error.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(multiDimPolyFunctions, 0);
+    defineRunTimeSelectionTable(multiDimPolyFunctions, word);
+}
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+Foam::autoPtr<Foam::multiDimPolyFunctions> Foam::multiDimPolyFunctions::New
+(
+    const word& multiDimPolyFunctionsType,
+    const labelVector& dirs
+)
+{
+    auto cstrIter = wordConstructorTablePtr_->cfind(multiDimPolyFunctionsType);
+
+    if (!cstrIter.found())
+    {
+        FatalErrorInLookup
+        (
+            "multiDimPolyFunction",
+            multiDimPolyFunctionsType,
+            *wordConstructorTablePtr_
+        ) << exit(FatalError);
+    }
+
+    return autoPtr<multiDimPolyFunctions>(cstrIter()(dirs));
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::multiDimPolyFunctions::multiDimPolyFunctions(const labelVector& dirs)
+:
+    nTerms_(-1),
+    geomDir_(dirs),
+    geomCorrection_(pos0(dirs.x()), pos0(dirs.y()), pos0(dirs.z())),
+    coeffs_(),
+    termValues_()
+{}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.H b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.H
new file mode 100644
index 0000000000000000000000000000000000000000..6e33daf6a516bd21b34f24ec14e5f4f9b25a4675
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/multiDimPolyFunctions.H
@@ -0,0 +1,141 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::multiDimPolyFunctions
+
+Description
+    base class for polynomial functions
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    multiDimPolyFunctions.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef multiDimPolyFunctions_H
+#define multiDimPolyFunctions_H
+
+#include "vector.H"
+#include "vector2D.H"
+#include "labelVector.H"
+#include "scalarField.H"
+#include "runTimeSelectionTables.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class multiDimPolyFunctions Declaration
+\*---------------------------------------------------------------------------*/
+
+class multiDimPolyFunctions
+{
+protected:
+
+    // Protected Data
+
+        //- Number of polynomial term
+        label nTerms_;
+
+        const labelVector geomDir_;
+
+        vector geomCorrection_;
+
+        scalarField coeffs_;
+
+        scalarField termValues_;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("multiDimPolyFunctions");
+
+    // Declare run-time constructor selection table
+
+    // For the dictionary constructor
+    declareRunTimeSelectionTable
+    (
+        autoPtr,
+        multiDimPolyFunctions,
+        word,
+        (
+            const Vector<label> dirs
+        ),
+        (dirs)
+    );
+
+
+    // Constructors
+
+        //- Construct with directions
+        explicit multiDimPolyFunctions(const labelVector& dirs);
+
+
+    // Selectors
+
+        //- Select a multiDimPolyFunctions
+        static autoPtr<multiDimPolyFunctions> New
+        (
+            const word& multiDimPolyFunctionsType,
+            const labelVector& dirs
+        );
+
+
+    //- Destructor
+    virtual ~multiDimPolyFunctions() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& vec) = 0;
+
+        virtual const scalarField& termValues(const vector& vec) = 0;
+
+        label& nTerms()
+        {
+            return nTerms_;
+        }
+
+        scalarField& coeffs()
+        {
+            return coeffs_;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.C b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.C
new file mode 100644
index 0000000000000000000000000000000000000000..865ec216c133c5b6e1d889ea5910850a8b6f1bf5
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.C
@@ -0,0 +1,98 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "polyDegree1.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(polyDegree1, 0);
+    addToRunTimeSelectionTable(multiDimPolyFunctions, polyDegree1, word);
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::polyDegree1::polyDegree1
+(
+    const labelVector& dirs
+)
+:
+    multiDimPolyFunctions(dirs)
+{
+    nTerms_ = 1;
+    forAll(geomDir_,i)
+    {
+        if (geomDir_[i] == 1)
+        {
+            ++nTerms_;
+        }
+    }
+    coeffs_.resize(nTerms_, Zero);
+    termValues_.resize(nTerms_, Zero);
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::scalar Foam::polyDegree1::value(const vector& vec)
+{
+    // size has to be 4
+    scalar value = coeffs_[0];
+    forAll(geomDir_,i)
+    {
+        if (geomDir_[i] == 1)
+        {
+            value += coeffs_[i+1]*vec[i];
+        }
+    }
+
+    return value;
+}
+
+
+const Foam::scalarField& Foam::polyDegree1::termValues(const vector& vec)
+{
+    termValues_[0] = 1;
+
+    label dimCounter = 0;
+    forAll(geomDir_,i)
+    {
+        if (geomDir_[i] == 1)
+        {
+            ++dimCounter;
+            termValues_[dimCounter] = vec[i];
+        }
+    }
+
+    return termValues_;
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.H b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.H
new file mode 100644
index 0000000000000000000000000000000000000000..dfbe1ad4c50b20c2c6f6df1634d14fe5d43a57f1
--- /dev/null
+++ b/src/finiteVolume/fvMatrices/solvers/multiDimPolyFitter/multiDimPolyFunctions/polyDegree1.H
@@ -0,0 +1,96 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::polyDegree1
+
+Description
+    First degree polynominal function
+
+    \verbatim
+    c0 + c1*x + c2*y + c3*z
+    \endverbatim
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    polyDegree1.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef polyDegree1_H
+#define polyDegree1_H
+
+#include "vector.H"
+#include "vector2D.H"
+#include "scalarField.H"
+#include "multiDimPolyFunctions.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class polyDegree1 Declaration
+\*---------------------------------------------------------------------------*/
+
+class polyDegree1
+:
+    public multiDimPolyFunctions
+{
+public:
+
+    //- Runtime type information
+    TypeName("polyDegree1");
+
+
+    // Constructors
+
+        //- Construct from nTerms
+        explicit polyDegree1(const labelVector& dirs);
+
+
+    //- Destructor
+    virtual ~polyDegree1() = default;
+
+
+    // Member Functions
+
+        virtual scalar value(const vector& vec);
+
+        virtual const scalarField& termValues(const vector& vec);
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneDistribute.C b/src/finiteVolume/fvMesh/zoneDistribute/zoneDistribute.C
new file mode 100644
index 0000000000000000000000000000000000000000..3194c5ae6d121ab29e5b25cf59b24fa8039f38fd
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneDistribute.C
@@ -0,0 +1,204 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "zoneDistribute.H"
+#include "dummyTransform.H"
+#include "emptyPolyPatch.H"
+#include "processorPolyPatch.H"
+#include "syncTools.H"
+#include "wedgePolyPatch.H"
+
+#include "globalPoints.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(zoneDistribute, 0);
+}
+
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+Foam::autoPtr<Foam::indirectPrimitivePatch>
+Foam::zoneDistribute::coupledFacesPatch() const
+{
+    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+    label nCoupled = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (isA<processorPolyPatch>(pp))
+        {
+            nCoupled += pp.size();
+        }
+    }
+    labelList coupledFaces(nCoupled);
+    nCoupled = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (isA<processorPolyPatch>(pp))
+        {
+            label facei = pp.start();
+
+            forAll(pp, i)
+            {
+                coupledFaces[nCoupled++] = facei++;
+            }
+        }
+    }
+
+    return autoPtr<indirectPrimitivePatch>::New
+    (
+        IndirectList<face>
+        (
+            mesh_.faces(),
+            coupledFaces
+        ),
+        mesh_.points()
+    );
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::zoneDistribute::zoneDistribute(const fvMesh& mesh)
+:
+    MeshObject<fvMesh, Foam::UpdateableMeshObject, zoneDistribute>(mesh),
+    stencil_(mesh),
+    coupledBoundaryPoints_(coupledFacesPatch()().meshPoints()),
+    send_(Pstream::nProcs())
+{
+}
+
+
+// * * * * * * * * * * * * * * * * Selectors  * * * * * * * * * * * * * * //
+
+Foam::zoneDistribute& Foam::zoneDistribute::New(const fvMesh& mesh)
+{
+    zoneDistribute* ptr = mesh.thisDb().getObjectPtr<zoneDistribute>
+    (
+        zoneDistribute::typeName
+    );
+
+    if (!ptr)
+    {
+        ptr = new zoneDistribute(mesh);
+
+        regIOobject::store(ptr);
+    }
+
+    return *ptr;
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+void Foam::zoneDistribute::updateStencil(const boolList& zone)
+{
+    stencil_.updateStencil(zone);
+}
+
+
+void Foam::zoneDistribute::setUpCommforZone
+(
+    const boolList& zone,
+    bool updateStencil
+)
+{
+    if (updateStencil)
+    {
+        stencil_.updateStencil(zone);
+    }
+
+    const labelHashSet comms = stencil_.needsComm();
+
+    List<labelHashSet> needed_(Pstream::nProcs());
+
+    if (Pstream::parRun())
+    {
+        for (const label celli : comms)
+        {
+            if (zone[celli])
+            {
+                for (const label gblIdx : stencil_[celli])
+                {
+                    if (!globalNumbering().isLocal(gblIdx))
+                    {
+                        const label procID =
+                            globalNumbering().whichProcID(gblIdx);
+                        needed_[procID].insert(gblIdx);
+                    }
+                }
+            }
+        }
+
+        PstreamBuffers pBufs(Pstream::commsTypes::nonBlocking);
+
+        // Stream data into buffer
+        for (label domain = 0; domain < Pstream::nProcs(); domain++)
+        {
+            if (domain != Pstream::myProcNo())
+            {
+                // Put data into send buffer
+                UOPstream toDomain(domain, pBufs);
+
+                toDomain << needed_[domain];
+            }
+        }
+
+        // wait until everything is written.
+        pBufs.finishedSends();
+
+        for (label domain = 0; domain < Pstream::nProcs(); domain++)
+        {
+            send_[domain].clear();
+
+            if (domain != Pstream::myProcNo())
+            {
+                // get data from send buffer
+                UIPstream fromDomain(domain, pBufs);
+
+                fromDomain >> send_[domain];
+            }
+        }
+    }
+}
+
+
+void Foam::zoneDistribute::updateMesh(const mapPolyMesh& mpm)
+{
+    if (mesh_.topoChanging())
+    {
+        coupledBoundaryPoints_ = coupledFacesPatch()().meshPoints();
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneDistribute.H b/src/finiteVolume/fvMesh/zoneDistribute/zoneDistribute.H
new file mode 100644
index 0000000000000000000000000000000000000000..dc432c774593c97a8a98915d159d738ed74b2941
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneDistribute.H
@@ -0,0 +1,193 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::zoneDistribute
+
+Description
+    Class for parallel communication in a narrow band. It either provides a Map
+    with the neighbouring values of the selected region or returns a Map of the
+    required values in global addressing. Also holds a reference to the stencil
+    Before the data transfer the communation has to be set up:
+    exchangeFields_.setUpCommforZone(interfaceCell_);
+    Is used in the plicRDF
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    zoneDistribute.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef zoneDistribute_H
+#define zoneDistribute_H
+
+#include "fvMesh.H"
+#include "globalIndex.H"
+#include "volFields.H"
+
+#include "zoneCPCStencil.H"
+#include "IOobject.H"
+#include "MeshObject.H"
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class zoneDistribute Declaration
+\*---------------------------------------------------------------------------*/
+
+class zoneDistribute
+:
+    public MeshObject<fvMesh, UpdateableMeshObject, zoneDistribute>
+{
+    // Private Data
+
+        //- cell-point-cell stencil elements are in global addressing
+        zoneCPCStencil stencil_;
+
+        //- labels of the points on coupled patches
+        labelList coupledBoundaryPoints_;
+
+        //- storage of the addressing for processor-to-processor comms
+        List<labelHashSet> send_;
+
+        //- Return patch of all coupled faces.
+        autoPtr<indirectPrimitivePatch> coupledFacesPatch() const;
+
+
+        //- Gives patchNumber and patchFaceNumber for a given
+        //- Geometric volume field
+        template<typename Type>
+        Type getLocalValue
+        (
+            const GeometricField<Type, fvPatchField, volMesh>& phi,
+            const label localIdx
+        ) const;
+
+
+        //- Gives patchNumber and patchFaceNumber for a given
+        //- Geometric volume field
+        template<typename Type>
+        Type faceValue
+        (
+            const GeometricField<Type, fvPatchField, volMesh>& phi,
+            const label localIdx
+        ) const;
+
+
+public:
+
+    //- Runtime information
+    TypeName("zoneDistribute");
+
+
+    // Constructors
+
+        //- Construct from fvMesh
+        explicit zoneDistribute(const fvMesh&);
+
+
+    // Selectors
+
+        static zoneDistribute& New(const fvMesh&);
+
+
+    // Member Functions
+
+        //- Update stencil with boolList the size has to match mesh nCells
+        void setUpCommforZone(const boolList& zone, bool updateStencil=true);
+
+        //- Updates stencil with boolList the size has to match mesh nCells
+        void updateStencil(const boolList& zone);
+
+        //- Stencil reference
+        const labelListList& getStencil()
+        {
+            return stencil_;
+        }
+
+        //- Addressing reference
+        const globalIndex& globalNumbering() const
+        {
+            return stencil_.globalNumbering();
+        }
+
+        //- Gives patchNumber and patchFaceNumber for a given
+        //- Geometric volume field
+        template<typename Type>
+        Type getValue
+        (
+            const GeometricField<Type, fvPatchField, volMesh>& phi,
+            const Map<Type>& valuesFromOtherProc,
+            const label gblIdx
+        ) const;
+
+        //- Returns stencil and provides a Map with globalNumbering
+        template<typename Type>
+        Map<Field<Type>> getFields
+        (
+            const boolList& zone,
+            const GeometricField<Type, fvPatchField, volMesh>& phi
+        );
+
+        //- Returns stencil and provides a Map with globalNumbering
+        template<typename Type>
+        Map<Type> getDatafromOtherProc
+        (
+            const boolList& zone,
+            const GeometricField<Type, fvPatchField, volMesh>& phi
+        );
+
+        virtual void updateMesh(const mapPolyMesh& mpm);
+
+        virtual bool movePoints()
+        {
+            // do nothing
+            return false;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#ifdef NoRepository
+#include "zoneDistributeI.H"
+#endif
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneDistributeI.H b/src/finiteVolume/fvMesh/zoneDistribute/zoneDistributeI.H
new file mode 100644
index 0000000000000000000000000000000000000000..2289be2509fbe8f9ae429f34743715f94c4dc267
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneDistributeI.H
@@ -0,0 +1,221 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "zoneDistribute.H"
+#include "DynamicField.H"
+#include "syncTools.H"
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+template<typename Type>
+Type Foam::zoneDistribute::getLocalValue
+(
+    const GeometricField<Type, fvPatchField, volMesh>& phi,
+    const label localIdx
+) const
+{
+    if (localIdx < mesh_.nCells()) // internal: cellI
+    {
+        return phi[localIdx];
+    }
+    else
+    {
+        return faceValue(phi,localIdx);
+    }
+
+}
+
+
+template<typename Type>
+Type Foam::zoneDistribute::faceValue
+(
+    const GeometricField<Type, fvPatchField, volMesh>& phi,
+    const label localIdx
+) const
+{
+    const label faceI = localIdx + mesh_.nInternalFaces() - mesh_.nCells();
+
+    const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
+
+    // Boundary face. Find out which face of which patch
+    const label patchI = pbm.whichPatch(faceI);
+
+    if (patchI < 0 || patchI >= pbm.size())
+    {
+       FatalErrorInFunction
+            << "Cannot find patch for face " << faceI
+            << abort(FatalError);
+    }
+
+    const polyPatch& pp = pbm[patchI];
+
+    const label patchFaceI = pp.whichFace(faceI);
+
+    return phi.boundaryField()[patchI][patchFaceI];
+}
+
+
+template<typename Type>
+Type Foam::zoneDistribute::getValue
+(
+    const GeometricField<Type, fvPatchField, volMesh>& phi,
+    const Map<Type>& valuesFromOtherProc,
+    const label gblIdx
+) const
+{
+    if (globalNumbering().isLocal(gblIdx))
+    {
+        const label idx = globalNumbering().toLocal(gblIdx);
+        return getLocalValue(phi,idx);
+    }
+    else // from other proc
+    {
+        return valuesFromOtherProc[gblIdx];
+    }
+}
+
+
+template<typename Type>
+Foam::Map<Foam::Field<Type>> Foam::zoneDistribute::getFields
+(
+    const boolList& zone,
+    const GeometricField<Type, fvPatchField, volMesh>& phi
+)
+{
+    if (zone.size() != phi.size())
+    {
+        FatalErrorInFunction
+            << "size of zone: " << zone.size()
+            << "size of phi:" <<  phi.size()
+            << "do not match. Did the mesh change?"
+            << exit(FatalError);
+
+        return Map<Field<Type>>();
+    }
+
+
+    // Get values from other proc
+    Map<Type> neiValues = getDatafromOtherProc(zone, phi);
+
+    Map<Field<Type>> stencilWithValues;
+
+    DynamicField<Type> tmpField(100);
+
+    forAll(zone,celli)
+    {
+        if (zone[celli])
+        {
+            tmpField.clearStorage();
+
+            for (const label gblIdx : stencil_[celli])
+            {
+                tmpField.append(getValue(phi,neiValues,gblIdx));
+            }
+
+            stencilWithValues.insert(celli,tmpField);
+        }
+    }
+
+    return stencilWithValues;
+}
+
+
+template<typename Type>
+Foam::Map<Type> Foam::zoneDistribute::getDatafromOtherProc
+(
+    const boolList& zone,
+    const GeometricField<Type, fvPatchField, volMesh>& phi
+)
+{
+    if (zone.size() != phi.size())
+    {
+        FatalErrorInFunction
+            << "size of zone: " << zone.size()
+            << "size of phi:" <<  phi.size()
+            << "do not match. Did the mesh change?"
+            << exit(FatalError);
+
+        return Map<Type>();
+    }
+
+
+    // Get values from other proc
+    Map<Type> neiValues;
+    List<Map<Type>> sendValues(Pstream::nProcs());
+
+    if (Pstream::parRun())
+    {
+        forAll(send_, domaini)
+        {
+            for (const label sendIdx : send_[domaini])
+            {
+                sendValues[domaini].insert
+                (
+                    sendIdx,
+                    getLocalValue(phi,globalNumbering().toLocal(sendIdx))
+                );
+            }
+        }
+
+        PstreamBuffers pBufs(Pstream::commsTypes::nonBlocking);
+
+        // Stream data into buffer
+        for (label domain = 0; domain < Pstream::nProcs(); domain++)
+        {
+            if (domain != Pstream::myProcNo())
+            {
+                // Put data into send buffer
+                UOPstream toDomain(domain, pBufs);
+
+                toDomain << sendValues[domain];
+            }
+        }
+
+        // Wait until everything is written.
+        pBufs.finishedSends();
+
+        Map<Type> tmpValue;
+
+        for (label domain = 0; domain < Pstream::nProcs(); domain++)
+        {
+            if (domain != Pstream::myProcNo())
+            {
+                // Get data from send buffer
+                UIPstream fromDomain(domain, pBufs);
+
+                fromDomain >> tmpValue;
+
+                neiValues += tmpValue;
+            }
+        }
+    }
+
+    return neiValues;
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.C b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.C
new file mode 100644
index 0000000000000000000000000000000000000000..1c91f5478aed90121336c673f6eec25a08cee168
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.C
@@ -0,0 +1,242 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "zoneCPCStencil.H"
+#include "syncTools.H"
+#include "ListOps.H"
+#include "dummyTransform.H"
+#include "emptyPolyPatch.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(zoneCPCStencil, 0);
+}
+
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+Foam::Map<bool> Foam::zoneCPCStencil::syncCoupledBoundaryPoints
+(
+    const boolList& zone,
+    const labelList& boundaryPoints
+) const
+{
+    const labelListList& pCells = mesh_.pointCells();
+
+    Map<bool> syncPoints;
+
+    for (const label pointi : boundaryPoints)
+    {
+        bool updatePoint = false;
+
+        // Check if point needs to be updated
+        for (const label celli : pCells[pointi])
+        {
+            if (zone[celli])
+            {
+                updatePoint = true;
+                break;
+            }
+        }
+
+        if (updatePoint)
+        {
+            syncPoints.insert(pointi, true);
+        }
+    }
+
+    syncTools::syncPointMap
+    (
+        mesh_,
+        syncPoints,
+        orEqOp<bool>(),
+        Foam::dummyTransform()
+    );
+
+    return syncPoints;
+}
+
+
+void Foam::zoneCPCStencil::calcPointBoundaryData
+(
+    const boolList& zone,
+    const boolList& isValidBFace,
+    const labelList& boundaryPoints,
+    Map<labelList>& neiGlobal
+) const
+{
+    neiGlobal.resize(2*boundaryPoints.size());
+
+    labelHashSet pointGlobals;
+
+    for (const label pointi : boundaryPoints)
+    {
+        neiGlobal.insert
+        (
+            pointi,
+            calcFaceCells
+            (
+                isValidBFace,
+                mesh_.pointFaces()[pointi],
+                pointGlobals
+            )
+        );
+    }
+
+    syncTools::syncPointMap
+    (
+        mesh_,
+        neiGlobal,
+        ListOps::unionEqOp(),
+        Foam::dummyTransform()
+    );
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::zoneCPCStencil::zoneCPCStencil(const fvMesh& mesh)
+:
+    zoneCellStencils(mesh),
+    nonEmptyBoundaryPoints_(nonEmptyFacesPatch()().meshPoints()),
+    uptodate_(mesh.nCells(), false)
+{
+    // Mark boundary faces to be included in stencil (i.e. not coupled or empty)
+    validBoundaryFaces(isValidBFace_);
+}
+
+
+void Foam::zoneCPCStencil::calculateStencil
+(
+    const boolList& zone,
+    labelListList& globalCellCells
+)
+{
+    // Swap pointCells for coupled points
+    Map<bool> syncPoints = syncCoupledBoundaryPoints
+    (
+        zone,
+        nonEmptyBoundaryPoints_
+    );
+
+    labelList boundaryPoints(syncPoints.toc());
+
+    Map<labelList> neiGlobal;
+    calcPointBoundaryData
+    (
+        zone,
+        isValidBFace_,
+        boundaryPoints,
+        neiGlobal
+    );
+
+    // add boundary Points first
+
+    for (const label pointi : boundaryPoints)
+    {
+        const labelList& pGlobals = neiGlobal[pointi];
+
+        // Distribute to all pointCells
+        const labelList& pCells = mesh_.pointCells(pointi);
+
+        for (const label celli : pCells)
+        {
+            // Insert pGlobals into globalCellCells
+            if (zone[celli] && !uptodate_[celli])
+            {
+                merge
+                (
+                    globalNumbering().toGlobal(celli),
+                    pGlobals,
+                    globalCellCells[celli]
+                );
+
+                for (const label gblIdx : globalCellCells[celli])
+                {
+                    if (!globalNumbering().isLocal(gblIdx))
+                    {
+                        needComm_.insert(celli);
+                    }
+                }
+            }
+        }
+    }
+
+
+    neiGlobal.clear();
+
+    // Do remaining points cells
+    const labelListList& cPoints = mesh_.cellPoints();
+
+    forAll(zone,celli)
+    {
+        if (zone[celli] && !uptodate_[celli])
+        {
+            for (const label pointi : cPoints[celli])
+            {
+                labelList pCells = mesh_.pointCells(pointi);
+
+                for (label& neiCelli : pCells)
+                {
+                    neiCelli = globalNumbering().toGlobal(neiCelli);
+                }
+
+                if (!uptodate_[celli])
+                {
+                    merge
+                    (
+                        globalNumbering().toGlobal(celli),
+                        pCells,
+                        globalCellCells[celli]
+                    );
+                }
+            }
+
+            uptodate_[celli] = true;
+        }
+    }
+}
+
+
+void Foam::zoneCPCStencil::updateMesh(const mapPolyMesh& mpm)
+{
+    if (mesh_.topoChanging())
+    {
+        // resize map and globalIndex
+        zoneCellStencils::updateMesh(mpm);
+
+        nonEmptyBoundaryPoints_ = nonEmptyFacesPatch()().meshPoints();
+        uptodate_.resize(mesh_.nCells());
+        uptodate_ = false;
+        validBoundaryFaces(isValidBFace_);
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.H b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.H
new file mode 100644
index 0000000000000000000000000000000000000000..318fa38d9757ef3465873854424a09e3305b81bc
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCPCStencil.H
@@ -0,0 +1,130 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::zoneCPCStencil
+
+Description
+    computes a cell point cell stencil in a narrow band. resizes in case
+    of topological change
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    zoneCPCStencil.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef zoneCPCStencil_H
+#define zoneCPCStencil_H
+
+#include "zoneCellStencils.H"
+#include "boolList.H"
+#include "HashSet.H"
+#include "Map.H"
+#include "indirectPrimitivePatch.H"
+#include "fvMesh.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                    Class zoneCPCStencil Declaration
+\*---------------------------------------------------------------------------*/
+
+class zoneCPCStencil
+:
+    public zoneCellStencils
+{
+    // Private Data
+
+        labelList nonEmptyBoundaryPoints_;
+
+        //- is valid boundaryface ?
+        //- non valid face are on empty, wedge and processor patches
+        boolList isValidBFace_;
+
+        //- cell is already uptodate
+        boolList uptodate_;
+
+
+    // Private Member Functions
+
+        //- Sync boundary points
+        Map<bool> syncCoupledBoundaryPoints
+        (
+            const boolList& zone,
+            const labelList& boundaryPoints
+        ) const;
+
+        //- Calculates per point the neighbour data (= pointCells)
+        void calcPointBoundaryData
+        (
+            const boolList& zone,
+            const boolList& isValidBFace,
+            const labelList& boundaryPoints,
+            Map<labelList>& neiGlobal
+        ) const;
+
+        //- Calculate stencil
+        void calculateStencil
+        (
+            const boolList& zone,
+            labelListList& globalCellCells
+        );
+
+
+public:
+
+    //- Runtime information
+    TypeName("zoneCPCStencil");
+
+
+    // Constructors
+
+        //- Construct from all cells and boundary faces
+        explicit zoneCPCStencil(const fvMesh&);
+
+
+    // Member Functions
+
+        //- Calculates per cell the neighbour data
+        //-  (= cell or boundary in global numbering).
+        //-  First element is always cell itself!
+        virtual void updateMesh(const mapPolyMesh& mpm);
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.C b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.C
new file mode 100644
index 0000000000000000000000000000000000000000..a397e036ab08d710a6abafee4e7a47078abda0a1
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.C
@@ -0,0 +1,283 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "zoneCellStencils.H"
+#include "syncTools.H"
+#include "dummyTransform.H"
+#include "emptyPolyPatch.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(zoneCellStencils, 0);
+}
+
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+Foam::autoPtr<Foam::indirectPrimitivePatch>
+Foam::zoneCellStencils::nonEmptyFacesPatch() const
+{
+    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+    label nNonEmpty = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (!isA<emptyPolyPatch>(pp))
+        {
+            nNonEmpty += pp.size();
+        }
+    }
+    labelList nonEmptyFaces(nNonEmpty);
+    nNonEmpty = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (!isA<emptyPolyPatch>(pp))
+        {
+            label facei = pp.start();
+
+            forAll(pp, i)
+            {
+                nonEmptyFaces[nNonEmpty++] = facei++;
+            }
+        }
+    }
+
+    return autoPtr<indirectPrimitivePatch>::New
+    (
+        IndirectList<face>
+        (
+            mesh_.faces(),
+            nonEmptyFaces
+        ),
+        mesh_.points()
+    );
+}
+
+
+Foam::autoPtr<Foam::indirectPrimitivePatch>
+Foam::zoneCellStencils::allCoupledFacesPatch() const
+{
+    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+    label nCoupled = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (pp.coupled())
+        {
+            nCoupled += pp.size();
+        }
+    }
+    labelList coupledFaces(nCoupled);
+    nCoupled = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (pp.coupled())
+        {
+            label facei = pp.start();
+
+            forAll(pp, i)
+            {
+                coupledFaces[nCoupled++] = facei++;
+            }
+        }
+    }
+
+    return autoPtr<indirectPrimitivePatch>::New
+    (
+        IndirectList<face>
+        (
+            mesh_.faces(),
+            coupledFaces
+        ),
+        mesh_.points()
+    );
+}
+
+
+void Foam::zoneCellStencils::validBoundaryFaces(boolList& isValidBFace) const
+{
+    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+    isValidBFace.setSize(mesh_.nBoundaryFaces());
+
+    isValidBFace = true;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (pp.coupled() || isA<emptyPolyPatch>(pp))
+        {
+            label bFacei = pp.start()-mesh_.nInternalFaces();
+            forAll(pp, i)
+            {
+                isValidBFace[bFacei++] = false;
+            }
+        }
+    }
+}
+
+
+void Foam::zoneCellStencils::merge
+(
+    const label globalI,
+    const labelList& pGlobals,
+    labelList& cCells
+)
+{
+    labelHashSet set;
+    for (const label celli : cCells)
+    {
+        if (celli != globalI)
+        {
+            set.insert(celli);
+        }
+    }
+
+    for (const label celli : pGlobals)
+    {
+        if (celli != globalI)
+        {
+            set.insert(celli);
+        }
+    }
+
+    cCells.setSize(set.size()+1);
+    label n = 0;
+    cCells[n++] = globalI;
+
+    for (const label seti : set)
+    {
+        cCells[n++] = seti;
+    }
+}
+
+
+void Foam::zoneCellStencils::insertFaceCells
+(
+    const label exclude0,
+    const label exclude1,
+    const boolList& isValidBFace,
+    const labelList& faceLabels,
+    labelHashSet& globals
+) const
+{
+    const labelList& own = mesh_.faceOwner();
+    const labelList& nei = mesh_.faceNeighbour();
+
+    forAll(faceLabels, i)
+    {
+        label facei = faceLabels[i];
+
+        label globalOwn = globalNumbering().toGlobal(own[facei]);
+        if (globalOwn != exclude0 && globalOwn != exclude1)
+        {
+            globals.insert(globalOwn);
+        }
+
+        if (mesh_.isInternalFace(facei))
+        {
+            label globalNei = globalNumbering().toGlobal(nei[facei]);
+            if (globalNei != exclude0 && globalNei != exclude1)
+            {
+                globals.insert(globalNei);
+            }
+        }
+        else
+        {
+            const label bFacei = facei-mesh_.nInternalFaces();
+
+            if (isValidBFace[bFacei])
+            {
+                label globalI = globalNumbering().toGlobal
+                (
+                    mesh_.nCells() + bFacei
+                );
+
+                if (globalI != exclude0 && globalI != exclude1)
+                {
+                    globals.insert(globalI);
+                }
+            }
+        }
+    }
+}
+
+
+Foam::labelList Foam::zoneCellStencils::calcFaceCells
+(
+    const boolList& isValidBFace,
+    const labelList& faceLabels,
+    labelHashSet& globals
+) const
+{
+    globals.clear();
+
+    insertFaceCells
+    (
+        -1,
+        -1,
+        isValidBFace,
+        faceLabels,
+        globals
+    );
+
+    return globals.toc();
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::zoneCellStencils::zoneCellStencils(const fvMesh& mesh)
+:
+    MeshObject<fvMesh, Foam::UpdateableMeshObject, zoneCellStencils>(mesh),
+    labelListList(mesh.nCells()),
+    needComm_(),
+    globalNumbering_(mesh_.nCells() + mesh_.nBoundaryFaces())
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+void Foam::zoneCellStencils::updateMesh(const mapPolyMesh& mpm)
+{
+    if (mesh_.topoChanging())
+    {
+        globalNumbering_ =
+            globalIndex(mesh_.nCells() + mesh_.nBoundaryFaces());
+
+        static_cast<labelListList&>(*this) = labelListList(mesh_.nCells());
+        needComm_.clear();
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.H b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.H
new file mode 100644
index 0000000000000000000000000000000000000000..16a1cde11b81c5700e8001099bf5fc7a72643127
--- /dev/null
+++ b/src/finiteVolume/fvMesh/zoneDistribute/zoneStencils/zoneCellStencils.H
@@ -0,0 +1,171 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::zoneCellStencils
+
+Description
+    base class for cell stencil in a narrow band
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    zoneCellStencils.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef zoneCellStencils_H
+#define zoneCellStencils_H
+
+#include "boolList.H"
+#include "HashSet.H"
+#include "Map.H"
+#include "indirectPrimitivePatch.H"
+#include "MeshObject.H"
+#include "fvMesh.H"
+#include "globalIndex.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                    Class zoneCellStencils Declaration
+\*---------------------------------------------------------------------------*/
+
+class zoneCellStencils
+:
+    public MeshObject<fvMesh, UpdateableMeshObject, zoneCellStencils>,
+    public labelListList
+{
+protected:
+
+    // Protected Members
+
+        labelHashSet needComm_;
+
+        globalIndex globalNumbering_;
+
+
+    // Protected Member Functions
+
+        //- Return patch of all coupled faces.
+        autoPtr<indirectPrimitivePatch> nonEmptyFacesPatch() const;
+
+        //- Return patch of all coupled faces.
+        autoPtr<indirectPrimitivePatch> allCoupledFacesPatch() const;
+
+        //- Valid boundary faces (not empty and not coupled)
+        void validBoundaryFaces(boolList& isValidBFace) const;
+
+        //- Merge two lists and guarantee globalI is first.
+        static void merge
+        (
+            const label globalI,
+            const labelList& pGlobals,
+            labelList& cCells
+        );
+
+        //- Collect cell neighbours of faces in global numbering
+        void insertFaceCells
+        (
+            const label exclude0,
+            const label exclude1,
+            const boolList& nonEmptyFace,
+            const labelList& faceLabels,
+            labelHashSet& globals
+        ) const;
+
+        //- Collect cell neighbours of faces in global numbering
+        labelList calcFaceCells
+        (
+            const boolList& nonEmptyFace,
+            const labelList& faceLabels,
+            labelHashSet& globals
+        ) const;
+
+        virtual void calculateStencil
+        (
+            const boolList& zone,
+            labelListList& globalCellCells
+        ) = 0;
+
+
+public:
+
+        // Declare name of the class and its debug switch
+        TypeName("zoneCellStencils");
+
+
+    // Constructors
+
+        //- Construct from all cells and boundary faces
+        explicit zoneCellStencils(const fvMesh&);
+
+
+    // Member Functions
+
+        //- Calculates per cell the neighbour data
+        //  (= cell or boundary in global numbering).
+        //  First element is always cell itself!
+        void updateStencil
+        (
+            const boolList& zone
+        )
+        {
+            calculateStencil(zone,*this);
+        }
+
+        const labelHashSet& needsComm()
+        {
+            return needComm_;
+        }
+
+        //- Global numbering for cells and boundary faces
+        const globalIndex& globalNumbering() const
+        {
+             return globalNumbering_;
+        }
+
+        virtual void updateMesh(const mapPolyMesh& mpm);
+
+        virtual bool movePoints()
+        {
+            // Do nothing
+            return false;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/sampling/Make/files b/src/sampling/Make/files
index 2d2796dcca52bc16d6a55b397d4a345b5350d1a2..b3bd62acc9a9770decd1f542f3a7218ca8b27c8a 100644
--- a/src/sampling/Make/files
+++ b/src/sampling/Make/files
@@ -50,6 +50,7 @@ sampledSurface/sampledSurface/sampledSurface.C
 sampledSurface/sampledSurface/sampledSurfaceRegister.C
 sampledSurface/sampledSurfaces/sampledSurfaces.C
 sampledSurface/thresholdCellFaces/sampledThresholdCellFaces.C
+sampledSurface/sampledInterface/sampledInterface.C
 
 readers = sampledSurface/readers
 
diff --git a/src/sampling/Make/options b/src/sampling/Make/options
index 6a8180f0ff1f90ef461bb00f52dcf69a1440a4b7..e0aa051f1526822c1c0308c14539cbead0f881c5 100644
--- a/src/sampling/Make/options
+++ b/src/sampling/Make/options
@@ -4,7 +4,8 @@ EXE_INC = \
     -I$(LIB_SRC)/surfMesh/lnInclude \
     -I$(LIB_SRC)/meshTools/lnInclude \
     -I$(LIB_SRC)/dynamicMesh/lnInclude \
-    -I$(LIB_SRC)/lagrangian/basic/lnInclude
+    -I$(LIB_SRC)/lagrangian/basic/lnInclude \
+    -I$(LIB_SRC)/transportModels/geometricVoF/lnInclude
 
 LIB_LIBS = \
     -lfiniteVolume \
@@ -12,4 +13,5 @@ LIB_LIBS = \
     -lsurfMesh \
     -lmeshTools \
     -ldynamicMesh \
-    -llagrangian
+    -llagrangian \
+    -lgeometricVoF
diff --git a/src/sampling/sampledSurface/sampledInterface/sampledInterface.C b/src/sampling/sampledSurface/sampledInterface/sampledInterface.C
new file mode 100644
index 0000000000000000000000000000000000000000..5763a701975c2dc8fce6c16bd8d65aa25eeb205d
--- /dev/null
+++ b/src/sampling/sampledSurface/sampledInterface/sampledInterface.C
@@ -0,0 +1,271 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "sampledInterface.H"
+#include "dictionary.H"
+#include "volFields.H"
+#include "volPointInterpolation.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(sampledInterface, 0);
+    addNamedToRunTimeSelectionTable
+    (
+        sampledSurface,
+        sampledInterface,
+        word,
+        interface
+    );
+}
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+
+bool Foam::sampledInterface::updateGeometry() const
+{
+    const fvMesh& fvm = static_cast<const fvMesh&>(mesh());
+
+    // No update needed
+    if (fvm.time().timeIndex() == prevTimeIndex_)
+    {
+        return false;
+    }
+
+    // Get any subMesh
+    if (!subMeshPtr_ && zoneID_.index() != -1)
+    {
+        const cellZone& cz = mesh().cellZones()[zoneID_.index()];
+
+        const polyBoundaryMesh& patches = mesh().boundaryMesh();
+
+        // Patch to put exposed internal faces into
+        const label exposedPatchi = patches.findPatchID(exposedPatchName_);
+
+        DebugInfo
+            << "Allocating subset of size " << cz.size()
+            << " with exposed faces into patch "
+            << patches[exposedPatchi].name() << endl;
+
+        subMeshPtr_.reset(new fvMeshSubset(fvm, cz, exposedPatchi));
+    }
+
+
+    prevTimeIndex_ = fvm.time().timeIndex();
+
+    // Clear any stored topo
+    surfPtr_.clear();
+
+    // Clear derived data
+    clearGeom();
+
+    surfPtr_.reset
+    (
+        new reconstructionSchemes::interface
+        (
+            fvm.lookupObjectRef<reconstructionSchemes>
+            (
+                "reconstructionScheme"
+            ).surface()
+        )
+    );
+
+    return true;
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::sampledInterface::sampledInterface
+(
+    const word& name,
+    const polyMesh& mesh,
+    const dictionary& dict
+)
+:
+    sampledSurface(name, mesh, dict),
+    zoneID_(dict.getOrDefault<word>("zone", word::null), mesh.cellZones()),
+    exposedPatchName_(word::null),
+    surfPtr_(nullptr),
+    prevTimeIndex_(-1),
+    subMeshPtr_(nullptr)
+{
+    if (zoneID_.index() != -1)
+    {
+        dict.readEntry("exposedPatchName", exposedPatchName_);
+
+        if (mesh.boundaryMesh().findPatchID(exposedPatchName_) == -1)
+        {
+            FatalIOErrorInFunction(dict)
+                << "Cannot find patch " << exposedPatchName_
+                << " in which to put exposed faces." << endl
+                << "Valid patches are " << mesh.boundaryMesh().names()
+                << exit(FatalIOError);
+        }
+
+        DebugInfo
+            << "Restricting to cellZone " << zoneID_.name()
+            << " with exposed internal faces into patch "
+            << exposedPatchName_ << endl;
+    }
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+bool Foam::sampledInterface::needsUpdate() const
+{
+    const fvMesh& fvm = static_cast<const fvMesh&>(mesh());
+
+    return fvm.time().timeIndex() != prevTimeIndex_;
+}
+
+
+bool Foam::sampledInterface::expire()
+{
+    surfPtr_.clear();
+    subMeshPtr_.clear();
+
+    // Clear derived data
+    clearGeom();
+
+    // Already marked as expired
+    if (prevTimeIndex_ == -1)
+    {
+        return false;
+    }
+
+    // Force update
+    prevTimeIndex_ = -1;
+    return true;
+}
+
+
+bool Foam::sampledInterface::update()
+{
+    return updateGeometry();
+}
+
+
+Foam::tmp<Foam::scalarField> Foam::sampledInterface::sample
+(
+    const interpolation<scalar>& sampler
+) const
+{
+    return sampleOnFaces(sampler);
+}
+
+
+Foam::tmp<Foam::vectorField> Foam::sampledInterface::sample
+(
+    const interpolation<vector>& sampler
+) const
+{
+    return sampleOnFaces(sampler);
+}
+
+
+Foam::tmp<Foam::sphericalTensorField> Foam::sampledInterface::sample
+(
+    const interpolation<sphericalTensor>& sampler
+) const
+{
+    return sampleOnFaces(sampler);
+}
+
+
+Foam::tmp<Foam::symmTensorField> Foam::sampledInterface::sample
+(
+    const interpolation<symmTensor>& sampler
+) const
+{
+    return sampleOnFaces(sampler);
+}
+
+
+Foam::tmp<Foam::tensorField> Foam::sampledInterface::sample
+(
+    const interpolation<tensor>& sampler
+) const
+{
+    return sampleOnFaces(sampler);
+}
+
+
+Foam::tmp<Foam::scalarField> Foam::sampledInterface::interpolate
+(
+    const interpolation<scalar>& interpolator
+) const
+{
+    return sampleOnPoints(interpolator);
+}
+
+
+Foam::tmp<Foam::vectorField> Foam::sampledInterface::interpolate
+(
+    const interpolation<vector>& interpolator
+) const
+{
+    return sampleOnPoints(interpolator);
+}
+
+Foam::tmp<Foam::sphericalTensorField> Foam::sampledInterface::interpolate
+(
+    const interpolation<sphericalTensor>& interpolator
+) const
+{
+    return sampleOnPoints(interpolator);
+}
+
+
+Foam::tmp<Foam::symmTensorField> Foam::sampledInterface::interpolate
+(
+    const interpolation<symmTensor>& interpolator
+) const
+{
+    return sampleOnPoints(interpolator);
+}
+
+
+Foam::tmp<Foam::tensorField> Foam::sampledInterface::interpolate
+(
+    const interpolation<tensor>& interpolator
+) const
+{
+    return sampleOnPoints(interpolator);
+}
+
+
+void Foam::sampledInterface::print(Ostream& os) const
+{
+    os  << "sampledInterface: " << name();
+}
+
+
+// ************************************************************************* //
diff --git a/src/sampling/sampledSurface/sampledInterface/sampledInterface.H b/src/sampling/sampledSurface/sampledInterface/sampledInterface.H
new file mode 100644
index 0000000000000000000000000000000000000000..c77ecafb551039c6a7615cdeb34cef4f210ef259
--- /dev/null
+++ b/src/sampling/sampledSurface/sampledInterface/sampledInterface.H
@@ -0,0 +1,287 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::sampledInterface
+
+Description
+    A sampledSurface that calculates the PLIC interface in VoF simulations
+    Only works in combination with isoAdvector and a reconstruction scheme
+
+    This is often embedded as part of a sampled surfaces function object.
+
+Usage
+    Example of function object partial specification:
+    \verbatim
+    surfaces
+    {
+        freeSurf
+        {
+            type            interface;
+            interpolate     false;
+        }
+    }
+    \endverbatim
+
+    Where the sub-entries comprise:
+    \table
+        Property | Description                             | Required | Default
+        type     | interface                               | yes      |
+    \endtable
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    sampledInterface.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef sampledInterface_H
+#define sampledInterface_H
+
+#include "sampledSurface.H"
+#include "ZoneIDs.H"
+#include "fvMeshSubset.H"
+#include "reconstructionSchemes.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                       Class sampledInterface Declaration
+\*---------------------------------------------------------------------------*/
+
+class sampledInterface
+:
+    public sampledSurface
+{
+    // Private Data
+
+        //- Zone name/index (if restricted to zones)
+        mutable cellZoneID zoneID_;
+
+        //- For zones: patch to put exposed faces into
+        mutable word exposedPatchName_;
+
+        mutable autoPtr<reconstructionSchemes::interface> surfPtr_;
+
+    // Recreated for every interface
+
+        //- Time at last call, also track if surface needs an update
+        mutable label prevTimeIndex_;
+
+        //- Cached submesh
+        mutable autoPtr<fvMeshSubset> subMeshPtr_;
+
+
+    // Private Member Functions
+
+        //- Create iso surface (if time has changed)
+        //  Do nothing (and return false) if no update was needed
+        bool updateGeometry() const;
+
+        //- Sample volume field onto surface faces
+        template<class Type>
+        tmp<Field<Type>> sampleOnFaces
+        (
+            const interpolation<Type>& sampler
+        ) const;
+
+        //- Interpolate volume field onto surface points
+        template<class Type>
+        tmp<Field<Type>> sampleOnPoints
+        (
+            const interpolation<Type>& interpolator
+        ) const;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("sampledInterface");
+
+
+    // Constructors
+
+        //- Construct from dictionary
+        sampledInterface
+        (
+            const word& name,
+            const polyMesh& mesh,
+            const dictionary& dict
+        );
+
+
+    //- Destructor
+    virtual ~sampledInterface() = default;
+
+
+    // Member Functions
+
+        const reconstructionSchemes::interface& surface() const
+        {
+            return surfPtr_();
+        }
+
+        //- Does the surface need an update?
+        virtual bool needsUpdate() const;
+
+        //- Mark the surface as needing an update.
+        //  May also free up unneeded data.
+        //  Return false if surface was already marked as expired.
+        virtual bool expire();
+
+        //- Update the surface as required.
+        //  Do nothing (and return false) if no update was needed
+        virtual bool update();
+
+
+        //- Points of surface
+        virtual const pointField& points() const
+        {
+            return surface().points();
+        }
+
+        //- Faces of surface
+        virtual const faceList& faces() const
+        {
+            return surface().surfFaces();
+        }
+
+        //- Const access to per-face zone/region information
+        virtual const labelList& zoneIds() const
+        {
+            return labelList::null();
+        }
+
+        //- Face area magnitudes
+        virtual const vectorField& Sf() const
+        {
+            return surface().Sf();
+        }
+
+        //- Face area magnitudes
+        virtual const scalarField& magSf() const
+        {
+            return surface().magSf();
+        }
+
+        //- Face centres
+        virtual const vectorField& Cf() const
+        {
+            return surface().Cf();
+        }
+
+
+    // Sample
+
+        //- Sample volume field onto surface faces
+        virtual tmp<scalarField> sample
+        (
+            const interpolation<scalar>& sampler
+        ) const;
+
+        //- Sample volume field onto surface faces
+        virtual tmp<vectorField> sample
+        (
+            const interpolation<vector>& sampler
+        ) const;
+
+        //- Sample volume field onto surface faces
+        virtual tmp<sphericalTensorField> sample
+        (
+            const interpolation<sphericalTensor>& sampler
+        ) const;
+
+        //- Sample volume field onto surface faces
+        virtual tmp<symmTensorField> sample
+        (
+            const interpolation<symmTensor>& sampler
+        ) const;
+
+        //- Sample volume field onto surface faces
+        virtual tmp<tensorField> sample
+        (
+            const interpolation<tensor>& sampler
+        ) const;
+
+
+    // Interpolate
+
+        //- Interpolate volume field onto surface points
+        virtual tmp<scalarField> interpolate
+        (
+            const interpolation<scalar>& interpolator
+        ) const;
+
+        //- Interpolate volume field onto surface points
+        virtual tmp<vectorField> interpolate
+        (
+            const interpolation<vector>& interpolator
+        ) const;
+
+        //- Interpolate volume field onto surface points
+        virtual tmp<sphericalTensorField> interpolate
+        (
+            const interpolation<sphericalTensor>& interpolator
+        ) const;
+
+        //- Interpolate volume field onto surface points
+        virtual tmp<symmTensorField> interpolate
+        (
+            const interpolation<symmTensor>& interpolator
+        ) const;
+
+        //- Interpolate volume field onto surface points
+        virtual tmp<tensorField> interpolate
+        (
+            const interpolation<tensor>& interpolator
+        ) const;
+
+
+    // Output
+
+        //- Write
+        virtual void print(Ostream&) const;
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#ifdef NoRepository
+    #include "sampledInterfaceTemplates.C"
+#endif
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/applications/solvers/multiphase/interIsoFoam/alphaCourantNo.H b/src/sampling/sampledSurface/sampledInterface/sampledInterfaceTemplates.C
similarity index 60%
rename from applications/solvers/multiphase/interIsoFoam/alphaCourantNo.H
rename to src/sampling/sampledSurface/sampledInterface/sampledInterfaceTemplates.C
index cc05c618fe2f765a82b7f1ce822580770180b63c..a39ef1697f57f27dce441839eb86772177d9086b 100644
--- a/applications/solvers/multiphase/interIsoFoam/alphaCourantNo.H
+++ b/src/sampling/sampledSurface/sampledInterface/sampledInterfaceTemplates.C
@@ -5,7 +5,8 @@
     \\  /    A nd           | www.openfoam.com
      \\/     M anipulation  |
 -------------------------------------------------------------------------------
-    Copyright (C) 2011-2017 OpenFOAM Foundation
+    Copyright (C) 2019-2019 OpenCFD Ltd.
+    Copyright (C) 2019-2020 DLR
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -23,37 +24,48 @@ License
     You should have received a copy of the GNU General Public License
     along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
 
-Global
-    alphaCourantNo
+\*---------------------------------------------------------------------------*/
 
-Description
-    Calculates and outputs the mean and maximum Courant Numbers.
+#include "sampledInterface.H"
+#include "volFieldsFwd.H"
+#include "pointFields.H"
+#include "volPointInterpolation.H"
 
-\*---------------------------------------------------------------------------*/
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
 
-scalar maxAlphaCo
+template<class Type>
+Foam::tmp<Foam::Field<Type>>
+Foam::sampledInterface::sampleOnFaces
 (
-    runTime.controlDict().get<scalar>("maxAlphaCo")
-);
+    const interpolation<Type>& sampler
+) const
+{
+    updateGeometry();  // Recreate geometry if time has changed
+
+    return sampledSurface::sampleOnFaces
+    (
+        sampler,
+        surface().meshCells(),
+        surface(),
+        points()
+    );
+}
 
-scalar alphaCoNum = 0.0;
-scalar meanAlphaCoNum = 0.0;
 
-if (mesh.nInternalFaces())
+template<class Type>
+Foam::tmp<Foam::Field<Type>>
+Foam::sampledInterface::sampleOnPoints
+(
+    const interpolation<Type>& interpolator
+) const
 {
-    scalarField sumPhi
+    notImplemented
     (
-        mixture.nearInterface()().primitiveField()
-       *fvc::surfaceSum(mag(phi))().primitiveField()
+        "interpolation on points values currently not implemented"
     );
 
-    alphaCoNum = 0.5*gMax(sumPhi/mesh.V().field())*runTime.deltaTValue();
-
-    meanAlphaCoNum =
-        0.5*(gSum(sumPhi)/gSum(mesh.V().field()))*runTime.deltaTValue();
+    return nullptr;
 }
 
-Info<< "Interface Courant Number mean: " << meanAlphaCoNum
-    << " max: " << alphaCoNum << endl;
 
 // ************************************************************************* //
diff --git a/src/transportModels/Allwmake b/src/transportModels/Allwmake
index c0e9865b7b87a58a2051683f455ac7676723dba6..0249ae4823f5810b7eb2a1a5d643417574433785 100755
--- a/src/transportModels/Allwmake
+++ b/src/transportModels/Allwmake
@@ -10,5 +10,6 @@ wmake $targetType twoPhaseProperties
 wmake $targetType incompressible
 wmake $targetType compressible
 wmake $targetType immiscibleIncompressibleTwoPhaseMixture
+wmake $targetType geometricVoF
 
 #------------------------------------------------------------------------------
diff --git a/src/transportModels/geometricVoF/Make/files b/src/transportModels/geometricVoF/Make/files
new file mode 100644
index 0000000000000000000000000000000000000000..a2c382a1ed7105d3c1fcc5c6ce8d9e964665c540
--- /dev/null
+++ b/src/transportModels/geometricVoF/Make/files
@@ -0,0 +1,22 @@
+cellCuts/cutCell/cutCell.C
+cellCuts/cutCell/cutCellPLIC.C
+cellCuts/cutCell/cutCellIso.C
+cellCuts/cutFace/cutFace.C
+cellCuts/cutFace/cutFacePLIC.C
+cellCuts/cutFace/cutFaceAdvect.C
+cellCuts/cutFace/cutFaceIso.C
+surfaceIterators/surfaceIteratorPLIC.C
+surfaceIterators/surfaceIteratorIso.C
+
+reconstructedDistanceFunction/reconstructedDistanceFunction.C
+
+reconstructionSchemes/reconstructionSchemesNew.C
+reconstructionSchemes/reconstructionSchemes.C
+reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.C
+
+reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.C
+reconstructionSchemes/plicSchemes/plicRDF/plicRDF.C
+
+advectionSchemes/isoAdvection/isoAdvection.C
+
+LIB = $(FOAM_LIBBIN)/libgeometricVoF
diff --git a/src/transportModels/geometricVoF/Make/options b/src/transportModels/geometricVoF/Make/options
new file mode 100644
index 0000000000000000000000000000000000000000..31ded987a140d92d9bfcf61c4f142c11e2c6d380
--- /dev/null
+++ b/src/transportModels/geometricVoF/Make/options
@@ -0,0 +1,15 @@
+EXE_INC = \
+    -I$(LIB_SRC)/finiteVolume/lnInclude \
+    -I$(LIB_SRC)/fileFormats/lnInclude \
+    -I$(LIB_SRC)/surfMesh/lnInclude \
+    -I$(LIB_SRC)/meshTools/lnInclude \
+    -I$(LIB_SRC)/transportModels/interfaceProperties/lnInclude \
+    -I$(LIB_SRC)/transportModels/twoPhaseProperties/lnInclude
+
+LIB_LIBS = \
+    -lfiniteVolume \
+    -lfileFormats \
+    -lsurfMesh \
+    -lmeshTools \
+    -ltwoPhaseMixture \
+    -ltwoPhaseProperties
diff --git a/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvection.C b/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvection.C
new file mode 100644
index 0000000000000000000000000000000000000000..e64d80dbee32875973654adabf0403b51c093c2c
--- /dev/null
+++ b/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvection.C
@@ -0,0 +1,643 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Modified code Copyright (C) 2016-2017 OpenCFD Ltd.
+    Modified code Copyright (C) 2019 Johan Roenby
+    Modified code Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "isoAdvection.H"
+#include "volFields.H"
+#include "interpolationCellPoint.H"
+#include "volPointInterpolation.H"
+#include "fvcSurfaceIntegrate.H"
+#include "fvcGrad.H"
+#include "upwind.H"
+#include "cellSet.H"
+#include "meshTools.H"
+#include "OBJstream.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(isoAdvection, 0);
+}
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::isoAdvection::isoAdvection
+(
+    volScalarField& alpha1,
+    const surfaceScalarField& phi,
+    const volVectorField& U
+)
+:
+    mesh_(alpha1.mesh()),
+    dict_(mesh_.solverDict(alpha1.name())),
+    alpha1_(alpha1),
+    alpha1In_(alpha1.ref()),
+    phi_(phi),
+    U_(U),
+    dVf_
+    (
+        IOobject
+        (
+            "dVf_",
+            mesh_.time().timeName(),
+            mesh_,
+            IOobject::NO_READ,
+            IOobject::NO_WRITE
+        ),
+        mesh_,
+        dimensionedScalar(dimVol, Zero)
+    ),
+    alphaPhi_
+    (
+        IOobject
+        (
+            "alphaPhi_",
+            mesh_.time().timeName(),
+            mesh_,
+            IOobject::NO_READ,
+            IOobject::NO_WRITE
+        ),
+        mesh_,
+        dimensionedScalar(dimVol/dimTime, Zero)
+    ),
+    advectionTime_(0),
+
+    // Tolerances and solution controls
+    nAlphaBounds_(dict_.getOrDefault<label>("nAlphaBounds", 3)),
+    isoFaceTol_(dict_.getOrDefault<scalar>("isoFaceTol", 1e-8)),
+    surfCellTol_(dict_.getOrDefault<scalar>("surfCellTol", 1e-8)),
+    writeIsoFacesToFile_(dict_.getOrDefault("writeIsoFaces", false)),
+
+    // Cell cutting data
+    surfCells_(label(0.2*mesh_.nCells())),
+    surf_(reconstructionSchemes::New(alpha1_, phi_, U_, dict_)),
+    advectFace_(alpha1.mesh(), alpha1),
+    bsFaces_(label(0.2*mesh_.nBoundaryFaces())),
+    bsx0_(bsFaces_.size()),
+    bsn0_(bsFaces_.size()),
+    bsUn0_(bsFaces_.size()),
+
+    // Parallel run data
+    procPatchLabels_(mesh_.boundary().size()),
+    surfaceCellFacesOnProcPatches_(0)
+{
+   cutFaceAdvect::debug = debug;
+
+    // Prepare lists used in parallel runs
+    if (Pstream::parRun())
+    {
+        // Force calculation of required demand driven data (else parallel
+        // communication may crash)
+        mesh_.cellCentres();
+        mesh_.cellVolumes();
+        mesh_.faceCentres();
+        mesh_.faceAreas();
+        mesh_.magSf();
+        mesh_.boundaryMesh().patchID();
+        mesh_.cellPoints();
+        mesh_.cellCells();
+        mesh_.cells();
+
+        // Get boundary mesh and resize the list for parallel comms
+        const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+        surfaceCellFacesOnProcPatches_.resize(patches.size());
+
+        // Append all processor patch labels to the list
+        forAll(patches, patchi)
+        {
+            if
+            (
+                isA<processorPolyPatch>(patches[patchi])
+             && patches[patchi].size() > 0
+            )
+            {
+                procPatchLabels_.append(patchi);
+            }
+        }
+    }
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+void Foam::isoAdvection::timeIntegratedFlux()
+{
+    // Get time step
+    const scalar dt = mesh_.time().deltaTValue();
+
+    // Create object for interpolating velocity to isoface centres
+    interpolationCellPoint<vector> UInterp(U_);
+
+    // For each downwind face of each surface cell we "isoadvect" to find dVf
+    label nSurfaceCells = 0;
+
+    // Clear out the data for re-use and reset list containing information
+    // whether cells could possibly need bounding
+    clearIsoFaceData();
+
+    // Get necessary references
+    const scalarField& phiIn = phi_.primitiveField();
+    const scalarField& magSfIn = mesh_.magSf().primitiveField();
+    scalarField& dVfIn = dVf_.primitiveFieldRef();
+
+    // Get necessary mesh data
+    const cellList& cellFaces = mesh_.cells();
+    const labelList& own = mesh_.faceOwner();
+
+
+    // Storage for isoFace points. Only used if writeIsoFacesToFile_
+    DynamicList<List<point>> isoFacePts;
+    const DynamicField<label>& interfaceLabels = surf_->interfaceLabels();
+
+    // Loop through cells
+    forAll(interfaceLabels, i)
+    {
+        const label celli = interfaceLabels[i];
+        if (mag(surf_->normal()[celli]) != 0)
+        {
+
+            // This is a surface cell, increment counter, append and mark cell
+            nSurfaceCells++;
+            surfCells_.append(celli);
+
+            DebugInfo
+                << "\n------------ Cell " << celli << " with alpha1 = "
+                << alpha1In_[celli] << " and 1-alpha1 = "
+                << 1.0 - alpha1In_[celli] << " ------------"
+                << endl;
+
+            // Cell is cut
+            const point x0 = surf_->centre()[celli];
+            vector n0 = -surf_->normal()[celli];
+            n0 /= (mag(n0));
+
+            // Get the speed of the isoface by interpolating velocity and
+            // dotting it with isoface unit normal
+            const scalar Un0 = UInterp.interpolate(x0, celli) & n0;
+
+            DebugInfo
+                << "calcIsoFace gives initial surface: \nx0 = " << x0
+                << ", \nn0 = " << n0 << ", \nUn0 = "
+                << Un0 << endl;
+
+            // Estimate time integrated flux through each downwind face
+            // Note: looping over all cell faces - in reduced-D, some of
+            //       these faces will be on empty patches
+            const cell& celliFaces = cellFaces[celli];
+            forAll(celliFaces, fi)
+            {
+                const label facei = celliFaces[fi];
+
+                if (mesh_.isInternalFace(facei))
+                {
+                    bool isDownwindFace = false;
+
+                    if (celli == own[facei])
+                    {
+                        if (phiIn[facei] >= 0)
+                        {
+                            isDownwindFace = true;
+                        }
+                    }
+                    else
+                    {
+                        if (phiIn[facei] < 0)
+                        {
+                            isDownwindFace = true;
+                        }
+                    }
+
+                    if (isDownwindFace)
+                    {
+                        dVfIn[facei] = advectFace_.timeIntegratedFaceFlux
+                        (
+                            facei,
+                            x0,
+                            n0,
+                            Un0,
+                            dt,
+                            phiIn[facei],
+                            magSfIn[facei]
+                        );
+                    }
+
+                }
+                else
+                {
+                    bsFaces_.append(facei);
+                    bsx0_.append(x0);
+                    bsn0_.append(n0);
+                    bsUn0_.append(Un0);
+
+                    // Note: we must not check if the face is on the
+                    // processor patch here.
+                }
+            }
+        }
+    }
+
+    // Get references to boundary fields
+    const polyBoundaryMesh& boundaryMesh = mesh_.boundaryMesh();
+    const surfaceScalarField::Boundary& phib = phi_.boundaryField();
+    const surfaceScalarField::Boundary& magSfb = mesh_.magSf().boundaryField();
+    surfaceScalarField::Boundary& dVfb = dVf_.boundaryFieldRef();
+    const label nInternalFaces = mesh_.nInternalFaces();
+
+    // Loop through boundary surface faces
+    forAll(bsFaces_, i)
+    {
+        // Get boundary face index (in the global list)
+        const label facei = bsFaces_[i];
+        const label patchi = boundaryMesh.patchID()[facei - nInternalFaces];
+        const label start = boundaryMesh[patchi].start();
+
+        if (phib[patchi].size())
+        {
+            const label patchFacei = facei - start;
+            const scalar phiP = phib[patchi][patchFacei];
+
+            if (phiP >= 0)
+            {
+                const scalar magSf = magSfb[patchi][patchFacei];
+
+                dVfb[patchi][patchFacei] = advectFace_.timeIntegratedFaceFlux
+                (
+                    facei,
+                    bsx0_[i],
+                    bsn0_[i],
+                    bsUn0_[i],
+                    dt,
+                    phiP,
+                    magSf
+                );
+
+                // Check if the face is on processor patch and append it to
+                // the list if necessary
+                checkIfOnProcPatch(facei);
+            }
+        }
+    }
+
+    // Synchronize processor patches
+    syncProcPatches(dVf_, phi_);
+
+    writeIsoFaces(isoFacePts);
+
+    DebugInfo << "Number of isoAdvector surface cells = "
+        << returnReduce(nSurfaceCells, sumOp<label>()) << endl;
+}
+
+
+void Foam::isoAdvection::setDownwindFaces
+(
+    const label celli,
+    DynamicLabelList& downwindFaces
+) const
+{
+    DebugInFunction << endl;
+
+    // Get necessary mesh data and cell information
+    const labelList& own = mesh_.faceOwner();
+    const cellList& cells = mesh_.cells();
+    const cell& c = cells[celli];
+
+    downwindFaces.clear();
+
+    // Check all faces of the cell
+    forAll(c, fi)
+    {
+        // Get face and corresponding flux
+        const label facei = c[fi];
+        const scalar phi = faceValue(phi_, facei);
+
+        if (own[facei] == celli)
+        {
+            if (phi >= 0)
+            {
+                downwindFaces.append(facei);
+            }
+        }
+        else if (phi < 0)
+        {
+            downwindFaces.append(facei);
+        }
+    }
+
+    downwindFaces.shrink();
+}
+
+
+Foam::scalar Foam::isoAdvection::netFlux
+(
+    const surfaceScalarField& dVf,
+    const label celli
+) const
+{
+    scalar dV = 0;
+
+    // Get face indices
+    const cell& c = mesh_.cells()[celli];
+
+    // Get mesh data
+    const labelList& own = mesh_.faceOwner();
+
+    forAll(c, fi)
+    {
+        const label facei = c[fi];
+        const scalar dVff = faceValue(dVf, facei);
+
+        if (own[facei] == celli)
+        {
+            dV += dVff;
+        }
+        else
+        {
+            dV -= dVff;
+        }
+    }
+
+    return dV;
+}
+
+
+Foam::DynamicList<Foam::label>  Foam::isoAdvection::syncProcPatches
+(
+    surfaceScalarField& dVf,
+    const surfaceScalarField& phi,
+    bool returnSyncedFaces
+)
+{
+    DynamicLabelList syncedFaces(0);
+    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+    if (Pstream::parRun())
+    {
+        PstreamBuffers pBufs(Pstream::commsTypes::nonBlocking);
+
+        // Send
+        forAll(procPatchLabels_, i)
+        {
+            const label patchi = procPatchLabels_[i];
+
+            const processorPolyPatch& procPatch =
+                refCast<const processorPolyPatch>(patches[patchi]);
+
+            UOPstream toNbr(procPatch.neighbProcNo(), pBufs);
+            const scalarField& pFlux = dVf.boundaryField()[patchi];
+
+            const List<label>& surfCellFacesOnProcPatch =
+                surfaceCellFacesOnProcPatches_[patchi];
+
+            const UIndirectList<scalar> dVfPatch
+            (
+                pFlux,
+                surfCellFacesOnProcPatch
+            );
+
+            toNbr << surfCellFacesOnProcPatch << dVfPatch;
+        }
+
+        pBufs.finishedSends();
+
+
+        // Receive and combine
+        forAll(procPatchLabels_, patchLabeli)
+        {
+            const label patchi = procPatchLabels_[patchLabeli];
+
+            const processorPolyPatch& procPatch =
+                refCast<const processorPolyPatch>(patches[patchi]);
+
+            UIPstream fromNeighb(procPatch.neighbProcNo(), pBufs);
+            List<label> faceIDs;
+            List<scalar> nbrdVfs;
+
+            fromNeighb >> faceIDs >> nbrdVfs;
+            if (returnSyncedFaces)
+            {
+                List<label> syncedFaceI(faceIDs);
+                for (label& faceI : syncedFaceI)
+                {
+                    faceI += procPatch.start();
+                }
+                syncedFaces.append(syncedFaceI);
+            }
+
+            if (debug)
+            {
+                Pout<< "Received at time = " << mesh_.time().value()
+                    << ": surfCellFacesOnProcPatch = " << faceIDs << nl
+                    << "Received at time = " << mesh_.time().value()
+                    << ": dVfPatch = " << nbrdVfs << endl;
+            }
+
+            // Combine fluxes
+            scalarField& localFlux = dVf.boundaryFieldRef()[patchi];
+
+            forAll(faceIDs, i)
+            {
+                const label facei = faceIDs[i];
+                localFlux[facei] = - nbrdVfs[i];
+                if (debug && mag(localFlux[facei] + nbrdVfs[i]) > 10*SMALL)
+                {
+                    Pout<< "localFlux[facei] = " << localFlux[facei]
+                        << " and nbrdVfs[i] = " << nbrdVfs[i]
+                        << " for facei = " << facei << endl;
+                }
+            }
+        }
+
+        if (debug)
+        {
+            // Write out results for checking
+            forAll(procPatchLabels_, patchLabeli)
+            {
+                const label patchi = procPatchLabels_[patchLabeli];
+                const scalarField& localFlux = dVf.boundaryField()[patchi];
+                Pout<< "time = " << mesh_.time().value() << ": localFlux = "
+                    << localFlux << endl;
+            }
+        }
+
+        // Reinitialising list used for minimal parallel communication
+        forAll(surfaceCellFacesOnProcPatches_, patchi)
+        {
+            surfaceCellFacesOnProcPatches_[patchi].clear();
+        }
+    }
+
+    return syncedFaces;
+}
+
+
+void Foam::isoAdvection::checkIfOnProcPatch(const label facei)
+{
+    if (!mesh_.isInternalFace(facei))
+    {
+        const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
+        const label patchi = pbm.patchID()[facei - mesh_.nInternalFaces()];
+
+        if (isA<processorPolyPatch>(pbm[patchi]) && pbm[patchi].size())
+        {
+            const label patchFacei = pbm[patchi].whichFace(facei);
+            surfaceCellFacesOnProcPatches_[patchi].append(patchFacei);
+        }
+    }
+}
+
+
+
+
+void Foam::isoAdvection::applyBruteForceBounding()
+{
+    bool alpha1Changed = false;
+
+    const scalar snapAlphaTol = dict_.getOrDefault<scalar>("snapTol", 0);
+    if (snapAlphaTol > 0)
+    {
+        alpha1_ =
+            alpha1_
+           *pos0(alpha1_ - snapAlphaTol)
+           *neg0(alpha1_ - (1.0 - snapAlphaTol))
+          + pos0(alpha1_ - (1.0 - snapAlphaTol));
+
+        alpha1Changed = true;
+    }
+
+    if (dict_.getOrDefault("clip", true))
+    {
+        alpha1_ = min(scalar(1), max(scalar(0), alpha1_));
+        alpha1Changed = true;
+    }
+
+    if (alpha1Changed)
+    {
+        alpha1_.correctBoundaryConditions();
+    }
+}
+
+
+void Foam::isoAdvection::writeSurfaceCells() const
+{
+    if (!mesh_.time().writeTime()) return;
+
+    if (dict_.getOrDefault("writeSurfCells", false))
+    {
+        cellSet cSet
+        (
+            IOobject
+            (
+                "surfCells",
+                mesh_.time().timeName(),
+                mesh_,
+                IOobject::NO_READ
+            )
+        );
+
+        cSet.insert(surfCells_);
+
+        cSet.write();
+    }
+}
+
+void Foam::isoAdvection::writeIsoFaces
+(
+    const DynamicList<List<point>>& faces
+) const
+{
+    if (!writeIsoFacesToFile_ || !mesh_.time().writeTime()) return;
+
+    // Writing isofaces to obj file for inspection, e.g. in paraview
+    const fileName outputFile
+    (
+        mesh_.time().globalPath()
+      / "isoFaces"
+      / word::printf("isoFaces_%012d.obj", mesh_.time().timeIndex())
+    );
+
+    if (Pstream::parRun())
+    {
+        // Collect points from all the processors
+        List<DynamicList<List<point>>> allProcFaces(Pstream::nProcs());
+        allProcFaces[Pstream::myProcNo()] = faces;
+        Pstream::gatherList(allProcFaces);
+
+        if (Pstream::master())
+        {
+            mkDir(outputFile.path());
+            OBJstream os(outputFile);
+            Info<< nl << "isoAdvection: writing iso faces to file: "
+                << os.name() << nl << endl;
+
+            face f;
+            forAll(allProcFaces, proci)
+            {
+                const DynamicList<List<point>>& procFacePts =
+                    allProcFaces[proci];
+
+                forAll(procFacePts, i)
+                {
+                    const List<point>& facePts = procFacePts[i];
+
+                    if (facePts.size() != f.size())
+                    {
+                        f = face(identity(facePts.size()));
+                    }
+
+                    os.write(f, facePts, false);
+                }
+            }
+        }
+    }
+    else
+    {
+        mkDir(outputFile.path());
+        OBJstream os(outputFile);
+        Info<< nl << "isoAdvection: writing iso faces to file: "
+            << os.name() << nl << endl;
+
+        face f;
+        forAll(faces, i)
+        {
+            const List<point>& facePts = faces[i];
+
+            if (facePts.size() != f.size())
+            {
+                f = face(identity(facePts.size()));
+            }
+
+            os.write(f, facePts, false);
+        }
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.H b/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvection.H
similarity index 79%
rename from src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.H
rename to src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvection.H
index 7f71959b1f7dd6dc5c8952757a69a8d97ebf3a95..41743a30a208fa651c6260f5685d0841fc5cc74a 100644
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoAdvection/isoAdvection.H
+++ b/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvection.H
@@ -6,8 +6,9 @@
      \\/     M anipulation  |
 -------------------------------------------------------------------------------
     Copyright (C) 2016-2017 DHI
-    Copyright (C) 2018 Johan Roenby
-    Copyright (C) 2016-2017, 2019 OpenCFD Ltd.
+    Modified code Copyright (C) 2016-2019 OpenCFD Ltd.
+    Modified code Copyright (C) 2018 Johan Roenby
+    Modified code Copyright (C) 2019 DLR
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -37,14 +38,15 @@ Description
     isosurfaces.
 
     Reference:
-        \verbatim
-            Roenby, J., Bredmose, H. and Jasak, H. (2016).
-            A computational method for sharp interface advection
-            Royal Society Open Science, 3
-            doi 10.1098/rsos.160405
-        \endverbatim
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+    \endverbatim
 
     Original code supplied by Johan Roenby, DHI (2016)
+    Modified Henning Scheufler, DLR
 
 SourceFiles
     isoAdvection.C
@@ -58,10 +60,12 @@ SourceFiles
 #include "fvMesh.H"
 #include "volFieldsFwd.H"
 #include "surfaceFields.H"
+#include "fvc.H"
 #include "className.H"
-#include "isoCutCell.H"
-#include "isoCutFace.H"
+#include "reconstructionSchemes.H"
+#include "cutFaceAdvect.H"
 #include "bitSet.H"
+#include "zeroField.H"
 
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
 
@@ -105,16 +109,13 @@ class isoAdvection
         //- Face volumetric water transport
         surfaceScalarField dVf_;
 
+        //- Face volumetric transport
+        surfaceScalarField alphaPhi_;
+
         //- Time spent performing interface advection
         scalar advectionTime_;
 
 
-        // Point interpolation data
-
-            //- VOF field interpolated to mesh points
-            scalarField ap_;
-
-
         // Switches and tolerances. Tolerances need to go into toleranceSwitches
 
             //- Number of alpha bounding steps
@@ -127,12 +128,6 @@ class isoAdvection
             //  Those with surfCellTol_ < alpha1 < 1 - surfCellTol_
             scalar surfCellTol_;
 
-            //- Switch controlling whether to use isoface normals for interface
-            //  orientation (default corresponding to false) to base it on
-            //  a smoothed gradient of alpha calculation (giving better results
-            //  on tri on tet meshes).
-            bool gradAlphaBasedNormal_;
-
             //- Print isofaces in a <case>/isoFaces/isoFaces_#N.vtk files.
             //  Intended for debugging
             bool writeIsoFacesToFile_;
@@ -142,17 +137,11 @@ class isoAdvection
             //- List of surface cells
             DynamicLabelList surfCells_;
 
-            //- Cell cutting object
-            isoCutCell isoCutCell_;
+            //- Pointer to reconstruction scheme
+            autoPtr<reconstructionSchemes> surf_;
 
-            //- Face cutting object
-            isoCutFace isoCutFace_;
-
-            //- Cells that have been touched by the bounding step
-            bitSet cellIsBounded_;
-
-            //- True for all surface cells and their neighbours
-            bitSet checkBounding_;
+            //- An isoCutFace object to get access to its face cutting functionality
+            cutFaceAdvect advectFace_;
 
             //- Storage for boundary faces downwind to a surface cell
             DynamicLabelList bsFaces_;
@@ -166,8 +155,6 @@ class isoAdvection
             //- Storage for boundary surface iso face speed
             DynamicScalarList bsUn0_;
 
-            //- Storage for boundary surface iso value
-            DynamicScalarList bsf0_;
 
 
         // Additional data for parallel runs
@@ -195,21 +182,6 @@ class isoAdvection
             //- For each face calculate volumetric face transport during dt
             void timeIntegratedFlux();
 
-            //- Set ap_ values of celli's vertices in accordance with the
-            //  unit normal of celli as obtained from cellNoramlsIn.
-            void setCellVertexValues
-            (
-                const label celli,
-                const vectorField& cellNormalsIn
-            );
-
-            //- Function used to normalise and smoothen grad(alpha) in case
-            //  gradAlphaBasedNormal_ is true.
-            void normaliseAndSmooth
-            (
-                volVectorField& cellN
-            );
-
             //- For a given cell return labels of faces fluxing out of this cell
             //  (based on sign of phi)
             void setDownwindFaces
@@ -218,15 +190,23 @@ class isoAdvection
                 DynamicLabelList& downwindFaces
             ) const;
 
-            // Limit fluxes
-            void limitFluxes();
+            // LimitFluxes
+            template < class SpType, class SuType >
+            void limitFluxes
+            (
+                const SpType& Sp,
+                const SuType& Su
+            );
 
             // Bound fluxes
-            void boundFromAbove
+            template < class SpType, class SuType >
+            void boundFlux
             (
                 const scalarField& alpha1,
-                surfaceScalarField& dVfcorrected,
-                DynamicLabelList& correctedFaces
+                surfaceScalarField& dVfcorrectionValues,
+                DynamicLabelList& correctedFaces,
+                const SpType& Sp,
+                const SuType& Su
             );
 
             //- Given the face volume transport dVf calculates the total volume
@@ -256,17 +236,6 @@ class isoAdvection
                 bsx0_.clear();
                 bsn0_.clear();
                 bsUn0_.clear();
-                bsf0_.clear();
-
-                if (mesh_.topoChanging())
-                {
-                    // Introduced resizing to cope with changing meshes
-                    checkBounding_.resize(mesh_.nCells());
-                    cellIsBounded_.resize(mesh_.nCells());
-                    ap_.resize(mesh_.nPoints());
-                }
-                checkBounding_ = false;
-                cellIsBounded_ = false;
 
             }
 
@@ -294,10 +263,11 @@ class isoAdvection
         // Parallel run handling functions
 
             //- Synchronize dVf across processor boundaries using upwind value
-            void syncProcPatches
+            DynamicList<label> syncProcPatches
             (
                 surfaceScalarField& dVf,
-                const surfaceScalarField& phi
+                const surfaceScalarField& phi,
+                bool returnSyncedFaces=false
             );
 
             //- Check if the face is on processor patch and append it to the
@@ -330,13 +300,20 @@ public:
 
         //- Advect the free surface. Updates alpha field, taking into account
         //  multiple calls within a single time step.
-        void advect();
+        template < class SpType, class SuType >
+        void advect(const SpType& Sp, const SuType& Su);
 
         //- Apply the bounding based on user inputs
         void applyBruteForceBounding();
 
         // Access functions
 
+            //- Return reconstructionSchemes
+            reconstructionSchemes& surf()
+            {
+                return surf_();
+            }
+
             //- Return alpha field
             const volScalarField& alpha() const
             {
@@ -352,9 +329,6 @@ public:
             //- Return cellSet of surface cells
             void writeSurfaceCells() const;
 
-            //- Return cellSet of bounded cells
-            void writeBoundedCells() const;
-
             //- Return mass flux
             tmp<surfaceScalarField> getRhoPhi
             (
@@ -372,6 +346,31 @@ public:
                 );
             }
 
+            //- Return mass flux
+            tmp<surfaceScalarField> getRhoPhi
+            (
+                const volScalarField& rho1,
+                const volScalarField& rho2
+            )
+            {
+                return tmp<surfaceScalarField>
+                (
+                new surfaceScalarField
+                (
+                    "rhoPhi",
+                    fvc::interpolate(rho1 - rho2)*alphaPhi_
+                    + fvc::interpolate(rho2)*phi_
+                )
+                );
+            }
+
+            //- reference to alphaPhi
+            const surfaceScalarField& alphaPhi() const
+            {
+                return alphaPhi_;
+            }
+
+            //- time spend in the advection step
             scalar advectionTime() const
             {
                 return advectionTime_;
diff --git a/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvectionTemplates.C b/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvectionTemplates.C
new file mode 100644
index 0000000000000000000000000000000000000000..82bb1e2fae043982bdb0a659ba0906382ec11f7e
--- /dev/null
+++ b/src/transportModels/geometricVoF/advectionSchemes/isoAdvection/isoAdvectionTemplates.C
@@ -0,0 +1,430 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Modified code Copyright (C) 2016-2017 OpenCFD Ltd.
+    Modified code Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "isoAdvection.H"
+#include "fvcSurfaceIntegrate.H"
+#include "upwind.H"
+
+// ************************************************************************* //
+
+template<typename Type>
+Type Foam::isoAdvection::faceValue
+(
+    const GeometricField<Type, fvsPatchField, surfaceMesh>& f,
+    const label facei
+) const
+{
+    if (mesh_.isInternalFace(facei))
+    {
+        return f.primitiveField()[facei];
+    }
+    else
+    {
+        const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
+
+        // Boundary face. Find out which face of which patch
+        const label patchi = pbm.patchID()[facei - mesh_.nInternalFaces()];
+
+        if (patchi < 0 || patchi >= pbm.size())
+        {
+            FatalErrorInFunction
+                << "Cannot find patch for face " << facei
+                << abort(FatalError);
+        }
+
+        // Handle empty patches
+        const polyPatch& pp = pbm[patchi];
+        if (isA<emptyPolyPatch>(pp) || pp.empty())
+        {
+            return pTraits<Type>::zero;
+        }
+
+        const label patchFacei = pp.whichFace(facei);
+        return f.boundaryField()[patchi][patchFacei];
+    }
+}
+
+
+template<typename Type>
+void Foam::isoAdvection::setFaceValue
+(
+    GeometricField<Type, fvsPatchField, surfaceMesh>& f,
+    const label facei,
+    const Type& value
+) const
+{
+    if (mesh_.isInternalFace(facei))
+    {
+        f.primitiveFieldRef()[facei] = value;
+    }
+    else
+    {
+        const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
+
+        // Boundary face. Find out which face of which patch
+        const label patchi = pbm.patchID()[facei - mesh_.nInternalFaces()];
+
+        if (patchi < 0 || patchi >= pbm.size())
+        {
+            FatalErrorInFunction
+                << "Cannot find patch for face " << facei
+                << abort(FatalError);
+        }
+
+        // Handle empty patches
+        const polyPatch& pp = pbm[patchi];
+        if (isA<emptyPolyPatch>(pp) || pp.empty())
+        {
+            return;
+        }
+
+        const label patchFacei = pp.whichFace(facei);
+
+        f.boundaryFieldRef()[patchi][patchFacei] = value;
+    }
+}
+
+
+template<class SpType, class SuType>
+void Foam::isoAdvection::limitFluxes
+(
+    const SpType& Sp,
+    const SuType& Su
+)
+{
+    DebugInFunction << endl;
+
+    const scalar aTol = 1.0e-12;          // Note: tolerances
+    scalar maxAlphaMinus1 = gMax(alpha1_) - 1;      // max(alphaNew - 1);
+    scalar minAlpha = gMin(alpha1_);           // min(alphaNew);
+    const label nOvershoots = 20;         // sum(pos0(alphaNew - 1 - aTol));
+
+    const labelList& owner = mesh_.faceOwner();
+    const labelList& neighbour = mesh_.faceNeighbour();
+
+    DebugInfo
+        << "isoAdvection: Before conservative bounding: min(alpha) = "
+        << minAlpha << ", max(alpha) = 1 + " << maxAlphaMinus1 << endl;
+
+    surfaceScalarField dVfcorrectionValues("dVfcorrectionValues", dVf_*0.0);
+
+
+    // Loop number of bounding steps
+    for (label n = 0; n < nAlphaBounds_; n++)
+    {
+        if (maxAlphaMinus1 > aTol || minAlpha < -aTol) // Note: tolerances
+        {
+            DebugInfo << "boundAlpha... " << endl;
+
+            DynamicList<label> correctedFaces(3*nOvershoots);
+            dVfcorrectionValues = dimensionedScalar(dimVolume, Zero);
+            boundFlux(alpha1In_, dVfcorrectionValues, correctedFaces,Sp,Su);
+
+            correctedFaces.append
+            (
+                syncProcPatches(dVfcorrectionValues, phi_,true)
+            );
+
+            labelHashSet alreadyUpdated;
+            forAll(correctedFaces, fi)
+            {
+                label facei = correctedFaces[fi];
+                if (alreadyUpdated.insert(facei))
+                {
+                    checkIfOnProcPatch(facei);
+                    const label own = owner[facei];
+
+                    alpha1_[own] +=
+                        -faceValue(dVfcorrectionValues, facei)/mesh_.V()[own];
+                    if (mesh_.isInternalFace(facei))
+                    {
+                        const label nei = neighbour[facei];
+                        alpha1_[nei] -=
+                            -faceValue(dVfcorrectionValues, facei)/mesh_.V()[nei];
+                    }
+
+                    // Change to treat boundaries consistently
+                    scalar corrVf =
+                        faceValue(dVf_, facei)
+                      + faceValue(dVfcorrectionValues, facei);
+
+                    setFaceValue(dVf_, facei, corrVf);
+                }
+            }
+            syncProcPatches(dVf_, phi_);
+        }
+        else
+        {
+            break;
+        }
+
+        maxAlphaMinus1 = gMax(alpha1_) - 1;     // max(alphaNew - 1);
+        minAlpha = gMin(alpha1_);               // min(alphaNew);
+
+        if (debug)
+        {
+            // Check if still unbounded
+            //scalarField alphaNew(alpha1In_ - fvc::surfaceIntegrate(dVf_)());
+            label maxAlphaMinus1 = max(alpha1_.primitiveField() - 1);
+            scalar minAlpha = min(alpha1_.primitiveField());
+            label nUndershoots = sum(neg0(alpha1_.primitiveField() + aTol));
+            label nOvershoots = sum(pos0(alpha1_.primitiveField() - 1 - aTol));
+
+            Info<< "After bounding number " << n + 1 << " of time "
+                << mesh_.time().value() << ":" << nl
+                << "nOvershoots = " << nOvershoots << " with max(alpha1_-1) = "
+                << maxAlphaMinus1 << " and nUndershoots = " << nUndershoots
+                << " with min(alpha1_) = " << minAlpha << endl;
+        }
+    }
+
+    alpha1_.correctBoundaryConditions();
+
+}
+
+
+template<class SpType, class SuType>
+void Foam::isoAdvection::boundFlux
+(
+    const scalarField& alpha1,
+    surfaceScalarField& dVfcorrectionValues,
+    DynamicList<label>& correctedFaces,
+    const SpType& Sp,
+    const SuType& Su
+)
+{
+    DebugInFunction << endl;
+    scalar rDeltaT = 1/mesh_.time().deltaTValue();
+
+    correctedFaces.clear();
+    scalar aTol = 10*SMALL; // Note: tolerances
+
+    const scalarField& meshV = mesh_.cellVolumes();
+    const scalar dt = mesh_.time().deltaTValue();
+
+    DynamicList<label> downwindFaces(10);
+    DynamicList<label> facesToPassFluidThrough(downwindFaces.size());
+    DynamicList<scalar> dVfmax(downwindFaces.size());
+    DynamicList<scalar> phi(downwindFaces.size());
+    const volScalarField& alphaOld = alpha1_.oldTime();
+
+    // Loop through alpha cell centred field
+    forAll(alpha1, celli)
+    {
+        if (alpha1[celli] < -aTol || alpha1[celli] > 1 + aTol)
+        {
+            const scalar Vi = meshV[celli];
+            scalar alphaOvershoot = pos0(alpha1[celli]-1)*(alpha1[celli]-1)
+                + neg0(alpha1[celli])*alpha1[celli];
+            scalar fluidToPassOn = alphaOvershoot*Vi;
+            label nFacesToPassFluidThrough = 1;
+
+            bool firstLoop = true;
+
+            // First try to pass surplus fluid on to neighbour cells that are
+            // not filled and to which dVf < phi*dt
+            while (mag(alphaOvershoot) > aTol && nFacesToPassFluidThrough > 0)
+            {
+                DebugInfo
+                    << "\n\nBounding cell " << celli
+                    << " with alpha overshooting " << alphaOvershoot
+                    << endl;
+
+                facesToPassFluidThrough.clear();
+                dVfmax.clear();
+                phi.clear();
+
+                // Find potential neighbour cells to pass surplus phase to
+                setDownwindFaces(celli, downwindFaces);
+
+                scalar dVftot = 0;
+                nFacesToPassFluidThrough = 0;
+
+                forAll(downwindFaces, fi)
+                {
+                    const label facei = downwindFaces[fi];
+                    const scalar phif = faceValue(phi_, facei);
+
+                    const scalar dVff =
+                        faceValue(dVf_, facei)
+                      + faceValue(dVfcorrectionValues, facei);
+
+                    const scalar maxExtraFaceFluidTrans =
+                        mag(pos0(fluidToPassOn)*phif*dt - dVff);
+
+                    // dVf has same sign as phi and so if phi>0 we have
+                    // mag(phi_[facei]*dt) - mag(dVf[facei]) = phi_[facei]*dt
+                    // - dVf[facei]
+                    // If phi < 0 we have mag(phi_[facei]*dt) -
+                    // mag(dVf[facei]) = -phi_[facei]*dt - (-dVf[facei]) > 0
+                    // since mag(dVf) < phi*dt
+                    DebugInfo
+                        << "downwindFace " << facei
+                        << " has maxExtraFaceFluidTrans = "
+                        << maxExtraFaceFluidTrans << endl;
+
+                    if (maxExtraFaceFluidTrans/Vi > aTol)
+                    {
+//                    if (maxExtraFaceFluidTrans/Vi > aTol &&
+//                    mag(dVfIn[facei])/Vi > aTol) //Last condition may be
+//                    important because without this we will flux through uncut
+//                    downwind faces
+                        facesToPassFluidThrough.append(facei);
+                        phi.append(phif);
+                        dVfmax.append(maxExtraFaceFluidTrans);
+                        dVftot += mag(phif*dt);
+                    }
+                }
+
+                DebugInfo
+                    << "\nfacesToPassFluidThrough: "
+                    << facesToPassFluidThrough << ", dVftot = "
+                    << dVftot << " m3 corresponding to dalpha = "
+                    << dVftot/Vi << endl;
+
+                forAll(facesToPassFluidThrough, fi)
+                {
+                    const label facei = facesToPassFluidThrough[fi];
+                    scalar fluidToPassThroughFace =
+                        mag(fluidToPassOn)*mag(phi[fi]*dt)/dVftot;
+
+                    nFacesToPassFluidThrough +=
+                        pos0(dVfmax[fi] - fluidToPassThroughFace);
+
+                    fluidToPassThroughFace =
+                        min(fluidToPassThroughFace, dVfmax[fi]);
+
+                    scalar dVff = faceValue(dVfcorrectionValues, facei);
+
+                    dVff +=
+                        sign(phi[fi])*fluidToPassThroughFace*sign(fluidToPassOn);
+
+                    setFaceValue(dVfcorrectionValues, facei, dVff);
+
+                    if (firstLoop)
+                    {
+                        checkIfOnProcPatch(facei);
+                        correctedFaces.append(facei);
+                    }
+                }
+
+                firstLoop = false;
+
+                scalar alpha1New =
+                (
+                    alphaOld[celli]*rDeltaT  + Su[celli]
+                  - netFlux(dVf_, celli)/Vi*rDeltaT
+                  - netFlux(dVfcorrectionValues, celli)/Vi*rDeltaT
+                )
+                /
+                (rDeltaT - Sp[celli]);
+
+                alphaOvershoot =
+                    pos0(alpha1New-1)*(alpha1New-1)
+                  + neg0(alpha1New)*alpha1New;
+
+                fluidToPassOn = alphaOvershoot*Vi;
+
+                DebugInfo
+                    << "\nNew alpha for cell " << celli << ": "
+                    << alpha1New << endl;
+            }
+        }
+    }
+
+    DebugInfo << "correctedFaces = " << correctedFaces << endl;
+}
+
+
+template<class SpType, class SuType>
+void Foam::isoAdvection::advect(const SpType& Sp, const SuType& Su)
+{
+    DebugInFunction << endl;
+
+    scalar advectionStartTime = mesh_.time().elapsedCpuTime();
+
+    scalar rDeltaT = 1/mesh_.time().deltaTValue();
+
+    // reconstruct the interface
+    surf_->reconstruct();
+
+    // Initialising dVf with upwind values
+    // i.e. phi[facei]*alpha1[upwindCell[facei]]*dt
+    dVf_ = upwind<scalar>(mesh_, phi_).flux(alpha1_)*mesh_.time().deltaT();
+
+    // Do the isoAdvection on surface cells
+    timeIntegratedFlux();
+
+    // Adjust alpha for mesh motion
+    if (mesh_.moving())
+    {
+        alpha1In_ *= (mesh_.Vsc0()/mesh_.Vsc());
+    }
+
+    // Advect the free surface
+    alpha1_.primitiveFieldRef() =
+    (
+        alpha1_.oldTime().primitiveField()*rDeltaT
+      + Su.field()
+      - fvc::surfaceIntegrate(dVf_)().primitiveField()*rDeltaT
+    )/(rDeltaT - Sp.field());
+
+    alpha1_.correctBoundaryConditions();
+
+    // Adjust dVf for unbounded cells
+    limitFluxes
+    (
+        Sp,
+        Su
+    );
+
+    scalar maxAlphaMinus1 = gMax(alpha1In_) - 1;
+    scalar minAlpha = gMin(alpha1In_);
+
+    Info<< "isoAdvection: After conservative bounding: min(alpha) = "
+        << minAlpha << ", max(alpha) = 1 + " << maxAlphaMinus1 << endl;
+
+    // Apply non-conservative bounding mechanisms (clipping and snapping)
+    // Note: We should be able to write out alpha before this is done!
+    applyBruteForceBounding();
+
+    // Write surface cell set and bound cell set if required by user
+    writeSurfaceCells();
+
+    advectionTime_ += (mesh_.time().elapsedCpuTime() - advectionStartTime);
+    DebugInfo
+        << "isoAdvection: time consumption = "
+        << label(100*advectionTime_/(mesh_.time().elapsedCpuTime() + SMALL))
+        << "%" << endl;
+
+    alphaPhi_ = dVf_/mesh_.time().deltaT();
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutCell/cutCell.C b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCell.C
new file mode 100644
index 0000000000000000000000000000000000000000..05dbc8677fa51086d6dddd283924c0142958a1b5
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCell.C
@@ -0,0 +1,206 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 OpenCFD Ltd.
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutCell.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+int Foam::cutCell::debug = 0;
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutCell::cutCell(const fvMesh&)
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+void Foam::cutCell::calcCellData
+(
+    const DynamicList<point>& cutFaceCentres,
+    const DynamicList<vector>& cutFaceAreas,
+    vector& subCellCentre, scalar& subCellVolume
+)
+{
+    // Clear the fields for accumulation
+    subCellCentre = Zero;
+    subCellVolume = Zero;
+
+    // first estimate the approximate cell centre as the average of
+    // face centres
+
+    vector cEst = average(cutFaceCentres);
+
+    // Contribution to subcell centre and volume from cut faces
+    forAll(cutFaceCentres, facei)
+    {
+        // Calculate 3*face-pyramid volume
+        scalar pyr3Vol = max(
+            mag(cutFaceAreas[facei] & (cutFaceCentres[facei] - cEst)), VSMALL);
+
+        // Calculate face-pyramid centre
+        vector pc = 0.75 * cutFaceCentres[facei] + 0.25 * cEst;
+
+        // Accumulate volume-weighted face-pyramid centre
+        subCellCentre += pyr3Vol * pc;
+
+        // Accumulate face-pyramid volume
+        subCellVolume += pyr3Vol;
+    }
+
+    subCellCentre /= subCellVolume;
+    subCellVolume /= 3; // formula of pyramid
+}
+
+
+void Foam::cutCell::calcGeomDataCutFace
+(
+    const DynamicList<DynamicList<point>>& faceEdges,
+    const vector& subCellCentre,
+    vector& faceArea,
+    vector& faceCentre
+)
+{
+    // Initial guess of face centre from edge points
+    point fCentre{Zero};
+    label nEdgePoints{0};
+    for (const DynamicList<point>& edgePoints : faceEdges)
+    {
+        for (const point& p : edgePoints)
+        {
+            fCentre += p;
+            nEdgePoints++;
+        }
+    }
+    if (nEdgePoints > 0)
+    {
+        fCentre /= nEdgePoints;
+    }
+
+    vector sumN{Zero};
+    scalar sumA{0};
+    vector sumAc{Zero};
+
+    // calculate area and centre
+    forAll(faceEdges, ei)
+    {
+        const DynamicList<point>& edgePoints = faceEdges[ei];
+        const label nPoints = edgePoints.size();
+        for (label pi = 0; pi < nPoints - 1; pi++)
+        {
+            const point& nextPoint = edgePoints[pi + 1];
+
+            vector c = edgePoints[pi] + nextPoint + fCentre;
+            vector n =
+                (nextPoint - edgePoints[pi]) ^ (fCentre - edgePoints[pi]);
+            scalar a = mag(n);
+
+            // Edges may have different orientation
+            sumN += Foam::sign(n & sumN) *  n;
+            sumA += a;
+            sumAc += a * c;
+        }
+    }
+
+    // This is to deal with zero-area faces. Mark very small faces
+    // to be detected in e.g., processorPolyPatch.
+    if (sumA < ROOTVSMALL)
+    {
+        faceCentre = fCentre;
+        faceArea = Zero;
+    }
+    else
+    {
+        faceCentre = (1.0/3.0)*sumAc/sumA;
+        faceArea = 0.5*sumN;
+    }
+
+    // Check faceArea direction and change if not pointing in the subcell
+    if ((faceArea & (faceCentre - subCellCentre)) >= 0)
+    {
+        faceArea *= (-1);
+    }
+}
+
+
+void Foam::cutCell::calcIsoFacePointsFromEdges
+(
+    const vector& faceArea,
+    const vector& faceCentre,
+    const DynamicList<DynamicList<point>>& faceEdges,
+    DynamicList<point>& facePoints
+)
+{
+    const vector zhat = normalised(faceArea);
+    vector xhat = faceEdges[0][0] - faceCentre;
+    xhat = (xhat - (xhat & zhat)*zhat);
+    xhat.normalise();
+    vector yhat = normalised(zhat ^ xhat);
+
+    // Calculating all intersection points
+    DynamicList<point> unsortedFacePoints(3 * faceEdges.size());
+    DynamicList<scalar> unsortedFacePointAngles(3 * faceEdges.size());
+    for (const DynamicList<point>& edgePoints : faceEdges)
+    {
+        for (const point& p : edgePoints)
+        {
+            unsortedFacePoints.append(p);
+            unsortedFacePointAngles.append
+            (
+                Foam::atan2
+                (
+                    ((p - faceCentre) & yhat),
+                    ((p - faceCentre) & xhat)
+                )
+            );
+        }
+    }
+
+    // Sorting face points by angle and inserting into facePoints
+    labelList order(Foam::sortedOrder(unsortedFacePointAngles));
+    facePoints.append(unsortedFacePoints[order[0]]);
+    for (label pi = 1; pi < order.size(); ++pi)
+    {
+        if
+        (
+            mag
+            (
+                unsortedFacePointAngles[order[pi]]
+              - unsortedFacePointAngles[order[pi - 1]]
+            ) > 1e-8)
+        {
+            facePoints.append(unsortedFacePoints[order[pi]]);
+        }
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutCell/cutCell.H b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCell.H
new file mode 100644
index 0000000000000000000000000000000000000000..5376ffda25670ba71c1b8e560aa172479af76ba3
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCell.H
@@ -0,0 +1,114 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::cutCell
+
+Description
+    Service routines for cutting a cell, celli, of an fvMesh, mesh_,
+    at its intersection with a surface
+
+    Original code supplied by
+        Johan Roenby, DHI (2016)
+        Henning Scheufler, DLR (2019)
+
+SourceFiles
+    cutCell.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cutCell_H
+#define cutCell_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                           Class cutCell Declaration
+\*---------------------------------------------------------------------------*/
+
+class cutCell
+{
+protected:
+
+    // Protected Member Functions
+
+        //- Calculates volume and centre of the cutted cell
+        static void calcCellData
+        (
+            const DynamicList<point>& cutFaceCentres,
+            const DynamicList<vector>& cutFaceAreas,
+            vector& subCellCentre,
+            scalar& subCellVolume
+        );
+
+        //- Calculates area and centre of the cutting face
+        static void calcGeomDataCutFace
+        (
+            const DynamicList<DynamicList<point> >& faceEdges,
+            const vector& subCellCentre,
+            vector& faceArea,
+            vector& faceCentre
+        );
+
+        //- Calculates the point of the cutting face
+        static void calcIsoFacePointsFromEdges
+        (
+            const vector& faceArea,
+            const vector& faceCentre,
+            const DynamicList<DynamicList<point>> & faceEdges,
+            DynamicList<point>& facePoints
+        );
+
+public:
+
+    // Static Data
+    static int debug;
+
+
+    // Constructors
+
+        //- Construct from fvMesh
+        explicit cutCell(const fvMesh& unused);
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellIso.C b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellIso.C
new file mode 100644
index 0000000000000000000000000000000000000000..feb54df002ae870649b77918b6734d294a04f36e
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellIso.C
@@ -0,0 +1,250 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutCellIso.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutCellIso::cutCellIso(const fvMesh& mesh, scalarField& f)
+:
+    cutCell(mesh),
+    mesh_(mesh),
+    cellI_(-1),
+    f_(f),
+    cutValue_(0),
+    cutFace_(cutFaceIso(mesh_, f_)),
+    cutFaceCentres_(10),
+    cutFaceAreas_(10),
+    isoFaceEdges_(10),
+    facePoints_(10),
+    faceCentre_(Zero),
+    faceArea_(Zero),
+    subCellCentre_(Zero),
+    subCellVolume_(-10),
+    VOF_(-10),
+    cellStatus_(-1)
+{
+    clearStorage();
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::cutCellIso::calcSubCell
+(
+    const label cellI,
+    const scalar cutValue
+)
+{
+    // resets data members
+    clearStorage();
+    cellI_ = cellI;
+    cutValue_ = cutValue;
+    const cell& c = mesh_.cells()[cellI_];
+
+    bool fullyBelow = true;
+    bool fullyAbove = true;
+
+    label nFaceBelowInterface = 0;
+
+    // loop over cell faces
+    for (const label facei : c)
+    {
+        const label faceStatus = cutFace_.calcSubFace(facei, cutValue_);
+
+        if (faceStatus == 0) // face is cut
+        {
+            cutFaceCentres_.append(cutFace_.subFaceCentre());
+            cutFaceAreas_.append(cutFace_.subFaceArea());
+            isoFaceEdges_.append(cutFace_.surfacePoints());
+            fullyBelow = false;
+            fullyAbove = false;
+        }
+        else if (faceStatus == -1) // face fully below
+        {
+            cutFaceCentres_.append(cutFace_.subFaceCentre());
+            cutFaceAreas_.append(cutFace_.subFaceArea());
+            fullyAbove = false;
+            nFaceBelowInterface++;
+        }
+        else
+        {
+            fullyBelow = false;
+        }
+    }
+
+    if (!fullyBelow && !fullyAbove) // cell cut at least at one face
+    {
+        cellStatus_ = 0;
+
+        // calc faceArea and faceCentre
+        calcGeomDataCutFace
+        (
+            isoFaceEdges_,
+            average(cutFaceCentres_),
+            faceArea_,
+            faceCentre_
+        );
+
+        // In the rare but occuring cases where a cell is only touched at a
+        // point or a line the isoFaceArea_ will have zero length and here the
+        // cell should be treated as either completely empty or full.
+        if (mag(faceArea_) < 10*SMALL)
+        {
+            if (nFaceBelowInterface == 0)
+            {
+                // Cell fully above isosurface
+                cellStatus_ = 1;
+                subCellCentre_ = Zero;
+                subCellVolume_ = 0;
+                VOF_ = 0;
+                return cellStatus_;
+            }
+            else
+            {
+                // Cell fully below isosurface
+                cellStatus_ = -1;
+                subCellCentre_ = mesh_.C()[cellI_];
+                subCellVolume_ = mesh_.V()[cellI_];
+                VOF_ = 1;
+                return cellStatus_;
+            }
+        }
+
+        cutFaceCentres_.append(faceCentre_);
+        cutFaceAreas_.append(faceArea_);
+
+        // calc volume and sub cell centre
+        calcCellData
+        (
+            cutFaceCentres_,
+            cutFaceAreas_,
+            subCellCentre_,
+            subCellVolume_
+        );
+
+        VOF_ = subCellVolume_ / mesh_.V()[cellI_];
+    }
+    else if (fullyAbove) // cell fully above isosurface
+    {
+        cellStatus_ = 1;
+        subCellCentre_ = Zero;
+        subCellVolume_ = 0;
+        VOF_ = 0;
+    }
+    else if (fullyBelow) // cell fully below isosurface
+    {
+        cellStatus_ = -1;
+        subCellCentre_ = mesh_.C()[cellI_];
+        subCellVolume_ = mesh_.V()[cellI_];
+        VOF_ = 1;
+    }
+
+    return cellStatus_;
+}
+
+
+const Foam::point& Foam::cutCellIso::subCellCentre() const
+{
+    return subCellCentre_;
+}
+
+
+Foam::scalar Foam::cutCellIso::subCellVolume() const
+{
+    return subCellVolume_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutCellIso::facePoints()
+{
+    if (facePoints_.size() == 0)
+    {
+        // get face points in sorted order
+        calcIsoFacePointsFromEdges
+        (
+            faceArea_,
+            faceCentre_,
+            isoFaceEdges_,
+            facePoints_
+        );
+    }
+
+    return facePoints_;
+}
+
+
+const Foam::point& Foam::cutCellIso::faceCentre() const
+{
+    return faceCentre_;
+}
+
+
+const Foam::vector& Foam::cutCellIso::faceArea() const
+{
+    return faceArea_;
+}
+
+
+Foam::label Foam::cutCellIso::cellStatus() const
+{
+    return cellStatus_;
+}
+
+
+Foam::scalar Foam::cutCellIso::VolumeOfFluid() const
+{
+    return VOF_;
+}
+
+
+Foam::scalar Foam::cutCellIso::cutValue() const
+{
+    return cutValue_;
+}
+
+
+void Foam::cutCellIso::clearStorage()
+{
+    cellI_ = -1;
+    cutValue_ = 0;
+    cutFaceCentres_.clear();
+    cutFaceAreas_.clear();
+    isoFaceEdges_.clear();
+    facePoints_.clear();
+    faceCentre_ = Zero;
+    faceArea_ = Zero;
+    subCellCentre_ = Zero;
+    subCellVolume_ = -10;
+    VOF_ = -10;
+    cellStatus_ = -1;
+}
+
+
+// ************************************************************************* //
diff --git a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.H b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellIso.H
similarity index 57%
rename from src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.H
rename to src/transportModels/geometricVoF/cellCuts/cutCell/cutCellIso.H
index a3c707aab73176ba4b1887d32236477e835d302a..3e905ff70cd9a8a99a052446552814a95bdcc19e 100644
--- a/src/finiteVolume/fvMatrices/solvers/isoAdvection/isoCutCell/isoCutCell.H
+++ b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellIso.H
@@ -8,6 +8,7 @@
     Copyright (C) 2016-2017 DHI
     Copyright (C) 2016-2017 OpenCFD Ltd.
     Copyright (C) 2018 Johan Roenby
+    Copyright (c) 2017-2019, German Aerospace Center (DLR)
 -------------------------------------------------------------------------------
 License
     This file is part of OpenFOAM.
@@ -26,34 +27,43 @@ License
     along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
 
 Class
-    Foam::isoCutCell
+    Foam::cutCellIso
 
 Description
     Class for cutting a cell, celli, of an fvMesh, mesh_, at its intersection
-    with an isosurface defined by the mesh point values f_ and the isovalue,
+    with an isosurface defined by the mesh point values f_ and the cutValue,
     isoValue_.
 
     Reference:
-        \verbatim
-            Roenby, J., Bredmose, H. and Jasak, H. (2016).
-            A computational method for sharp interface advection
-            Royal Society Open Science, 3
-            doi 10.1098/rsos.160405
-        \endverbatim
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+
+        Henning Scheufler, Johan Roenby,
+        Accurate and efficient surface reconstruction from volume
+        fraction data on general meshes,
+        Journal of Computational Physics, 2019,
+        doi 10.1016/j.jcp.2019.01.009
+
+    \endverbatim
 
     Original code supplied by Johan Roenby, DHI (2016)
 
 SourceFiles
-    isoCutCell.C
+    cutCellIso.C
 
 \*---------------------------------------------------------------------------*/
 
-#ifndef isoCutCell_H
-#define isoCutCell_H
+#ifndef cutCellIso_H
+#define cutCellIso_H
 
+#include "cutCell.H"
+#include "cutFaceIso.H"
 #include "fvMesh.H"
-#include "volFieldsFwd.H"
-#include "isoCutFace.H"
+#include "surfaceFields.H"
+#include "volFields.H"
 
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
 
@@ -61,12 +71,14 @@ namespace Foam
 {
 
 /*---------------------------------------------------------------------------*\
-                         Class isoCutCell Declaration
+                         Class cutCellIso Declaration
 \*---------------------------------------------------------------------------*/
 
-class isoCutCell
+class cutCellIso
+:
+    public cutCell
 {
-    // Private data
+    // Private Data
 
         //- Mesh whose cells and faces to cut at their intersection with an
         //  isosurface.
@@ -78,36 +90,30 @@ class isoCutCell
         //- Isofunction values at mesh points. f_size() = mesh_.nPoints().
         scalarField& f_;
 
-        //- Isovalue used to cut cell
-        scalar isoValue_;
-
-        //- An isoCutFace object to get access to its face cutting functionality
-        isoCutFace isoCutFace_;
-
-        //- List of face labels of isoCutFaces
-        DynamicList<label> isoCutFaces_;
+        //- Cutvalue used to cut cell
+        scalar cutValue_;
 
-        //- List of point lists each defining an isoCutFace
-        DynamicList<DynamicList<point>> isoCutFacePoints_;
+        //- An cutFaceIso object to get access to its face cutting functionality
+        cutFaceIso cutFace_;
 
-        //- List of face centres for isoCutFaces
-        DynamicList<point> isoCutFaceCentres_;
+        //- List of face centres for CutFaces
+        DynamicList<point> cutFaceCentres_;
 
         //- List of face area vectors for isoCutFaces
-        DynamicList<vector> isoCutFaceAreas_;
+        DynamicList<vector> cutFaceAreas_;
 
         //- Storage for subFace edges belonging to isoFace
         DynamicList<DynamicList<point>> isoFaceEdges_;
 
         //- Points constituting the cell-isosurface intersection (isoface)
-        DynamicList<point> isoFacePoints_;
+        DynamicList<point> facePoints_;
 
-        //- Face centre of the isoface
-        point isoFaceCentre_;
+        //- Face centre of the cutFace
+        point faceCentre_;
 
         //- Face normal of the isoface by convention pointing from high to low
         //  values (i.e. opposite of the gradient vector).
-        vector isoFaceArea_;
+        vector faceArea_;
 
         //- Cell centre of the subcell of celli which is "fully submerged", i.e.
         //  where the function value is higher than the isoValue_
@@ -116,80 +122,59 @@ class isoCutCell
         //- Volume of fully submerged subcell
         scalar subCellVolume_;
 
-        //- Volume of Fluid for celli (subCellVolume_/mesh_.V()[celli])
+        //- Volume of Fluid for cellI (subCellVolume_/mesh_.V()[cellI])
         scalar VOF_;
 
-        //- List of fully submerged faces
-        DynamicList<label> fullySubFaces_;
-
         //- A cell status label taking one of the values:
         //
-        //  - -1: cell is fully below the isosurface
-        //  -  0: cell is cut
-        //  - +1: cell is fully above the isosurface
+        //   -1: cell is fully below the isosurface
+        //    0: cell is cut
+        //   +1: cell is fully above the isosurface
         label cellStatus_;
 
-        //- Boolean telling if subcell centre and volume have been calculated
-        bool subCellCentreAndVolumeCalculated_;
-
-        //- Boolean telling if isoface centre and area have been calculated
-        bool isoFaceCentreAndAreaCalculated_;
-
-
-    // Private Member Functions
 
-            void calcSubCellCentreAndVolume();
-
-            void calcIsoFaceCentreAndArea();
-
-            void calcIsoFacePointsFromEdges();
-
-
-public:
+  public:
 
     // Constructors
 
         //- Construct from fvMesh and a scalarField
         //  Length of scalarField should equal number of mesh points
-        isoCutCell(const fvMesh&, scalarField&);
+        cutCellIso(const fvMesh& mesh, scalarField& f);
 
-    // Static data
 
-        static int debug;
+    // Member Functions
 
+        //- Sets internal values and returns face status
+        label calcSubCell(const label cellI, const scalar cutValue);
 
-    // Member functions
+        //- Returns subCellCentre
+        const point& subCellCentre() const;
 
-        label calcSubCell(const label celli, const scalar isoValue);
+        //- Returns subCellVolume
+        scalar subCellVolume() const;
 
-        const point& subCellCentre();
+        //- Returns the points of the cutting isoface
+        const DynamicList<point>& facePoints();
 
-        scalar subCellVolume();
+        //- Returns the centre of the cutting isoface
+        const point& faceCentre() const;
 
-        const DynamicList<point>& isoFacePoints();
+        //- Returns the area normal vector of the cutting isoface
+        const vector& faceArea() const;
 
-        const point& isoFaceCentre();
+        //- Returns cellStatus
+        label cellStatus() const;
 
-        const vector& isoFaceArea();
+        //- Returns volume of fluid value
+        scalar VolumeOfFluid() const;
 
-        scalar volumeOfFluid();
-
-        scalar isoValue() const;
+        //- Returns cutValue
+        scalar cutValue() const;
 
+        //- Resets internal values
         void clearStorage();
-
-        label vofCutCell
-        (
-            const label celli,
-            const scalar alpha1,
-            const scalar tol,
-            const label maxIter
-        );
-
-        void volumeOfFluid(volScalarField& alpha1, const scalar f0);
 };
 
-
 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
 
 } // End namespace Foam
diff --git a/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellPLIC.C b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellPLIC.C
new file mode 100644
index 0000000000000000000000000000000000000000..ca5fcd9f8fe9b19c51d6d533f4533343e6404552
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellPLIC.C
@@ -0,0 +1,252 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutCellPLIC.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutCellPLIC::cutCellPLIC(const fvMesh& mesh)
+:
+    cutCell(mesh),
+    mesh_(mesh),
+    cellI_(-1),
+    normal_(Zero),
+    cutValue_(0),
+    cutFace_(mesh_),
+    cutFaceCentres_(10),
+    cutFaceAreas_(10),
+    plicFaceEdges_(10),
+    facePoints_(10),
+    faceCentre_(Zero),
+    faceArea_(Zero),
+    subCellCentre_(Zero),
+    subCellVolume_(-10),
+    VOF_(-10),
+    cellStatus_(-1)
+{
+    clearStorage();
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::cutCellPLIC::calcSubCell
+(
+    const label celli,
+    const scalar cutValue,
+    const vector& normal
+)
+{
+    clearStorage();
+    normal_ = normal;
+    cellI_ = celli;
+    cutValue_ = cutValue;
+    const cell& c = mesh_.cells()[celli];
+
+    vector base = mesh_.C()[cellI_] + normal_ * cutValue_;
+    bool fullyBelow = true;
+    bool fullyAbove = true;
+
+    label nFaceBelowInterface = 0;
+
+    // loop over all cell faces
+    for (const label faceI : c)
+    {
+        const label faceStatus = cutFace_.calcSubFace(faceI, normal_, base);
+
+        if (faceStatus == 0) // face is cut
+        {
+            cutFaceCentres_.append(cutFace_.subFaceCentre());
+            cutFaceAreas_.append(cutFace_.subFaceArea());
+            plicFaceEdges_.append(cutFace_.surfacePoints());
+            fullyBelow = false;
+            fullyAbove = false;
+        }
+        else if (faceStatus == -1) // face fully below
+        {
+            cutFaceCentres_.append(cutFace_.subFaceCentre());
+            cutFaceAreas_.append(cutFace_.subFaceArea());
+            fullyAbove = false;
+            nFaceBelowInterface++;
+        }
+        else
+        {
+            fullyBelow = false;
+        }
+    }
+
+    if (!fullyBelow && !fullyAbove) // cell cut at least at one face
+    {
+        cellStatus_ = 0;
+
+        // calc faceArea and faceCentre
+        calcGeomDataCutFace
+        (
+            plicFaceEdges_,
+            average(cutFaceCentres_),
+            faceArea_,
+            faceCentre_
+        );
+
+        // In the rare but occuring cases where a cell is only touched at a
+        // point or a line the isoFaceArea_ will have zero length and here the
+        // cell should be treated as either completely empty or full.
+        if (mag(faceArea_) < 10*SMALL)
+        {
+            if (nFaceBelowInterface == 0)
+            {
+                // Cell fully above isosurface
+                cellStatus_ = 1;
+                subCellCentre_ = Zero;
+                subCellVolume_ = 0;
+                VOF_ = 0;
+                return cellStatus_;
+            }
+            else
+            {
+                // Cell fully below isosurface
+                cellStatus_ = -1;
+                subCellCentre_ = mesh_.C()[cellI_];
+                subCellVolume_ = mesh_.V()[cellI_];
+                VOF_ = 1;
+                return cellStatus_;
+            }
+        }
+
+        cutFaceCentres_.append(faceCentre_);
+        cutFaceAreas_.append(faceArea_);
+
+        // calc volume and sub cell centre
+        calcCellData
+        (
+            cutFaceCentres_,
+            cutFaceAreas_,
+            subCellCentre_,
+            subCellVolume_
+        );
+
+        VOF_ = subCellVolume_ / mesh_.V()[cellI_];
+    }
+    else if (fullyAbove) // cell fully above isosurface
+    {
+        cellStatus_ = 1;
+        subCellCentre_ = Zero;
+        subCellVolume_ = 0;
+        VOF_ = 0;
+    }
+    else if (fullyBelow) // cell fully below isosurface
+    {
+        cellStatus_ = -1;
+        subCellCentre_ = mesh_.C()[cellI_];
+        subCellVolume_ = mesh_.V()[cellI_];
+        VOF_ = 1;
+    }
+
+    return cellStatus_;
+}
+
+
+const Foam::point& Foam::cutCellPLIC::subCellCentre() const
+{
+    return subCellCentre_;
+}
+
+
+Foam::scalar Foam::cutCellPLIC::subCellVolume() const
+{
+    return subCellVolume_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutCellPLIC::facePoints()
+{
+    if (facePoints_.size() == 0)
+    {
+        // get face points in sorted order
+        calcIsoFacePointsFromEdges
+        (
+            faceArea_,
+            faceCentre_,
+            plicFaceEdges_,
+            facePoints_
+        );
+    }
+
+    return facePoints_;
+}
+
+
+const Foam::point& Foam::cutCellPLIC::faceCentre() const
+{
+    return faceCentre_;
+}
+
+
+const Foam::vector& Foam::cutCellPLIC::faceArea() const
+{
+    return faceArea_;
+}
+
+
+Foam::scalar Foam::cutCellPLIC::VolumeOfFluid() const
+{
+    return VOF_;
+}
+
+
+Foam::label Foam::cutCellPLIC::cellStatus() const
+{
+    return cellStatus_;
+}
+
+
+Foam::scalar Foam::cutCellPLIC::cutValue() const
+{
+    return cutValue_;
+}
+
+
+void Foam::cutCellPLIC::clearStorage()
+{
+    cellI_ = -1;
+    cutValue_ = 0;
+    cutFaceCentres_.clear();
+    cutFaceAreas_.clear();
+    plicFaceEdges_.clear();
+    facePoints_.clear();
+    faceCentre_ = Zero;
+    faceArea_ = Zero;
+    subCellCentre_ = Zero;
+    subCellVolume_ = -10;
+    VOF_ = -10;
+    cellStatus_ = -1;
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellPLIC.H b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellPLIC.H
new file mode 100644
index 0000000000000000000000000000000000000000..c5aadab2f92c64ae86ce3a206b7cad3dbfb2f61e
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutCell/cutCellPLIC.H
@@ -0,0 +1,186 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::cutCellPLIC
+
+Description
+    Class for cutting a cell, cellI, of an fvMesh, mesh_, at its intersection
+    with an surface defined by a normal and cutValue_ (defined as distance to
+    the cell centre).
+
+    Reference:
+    \verbatim
+        Henning Scheufler, Johan Roenby,
+        Accurate and efficient surface reconstruction from volume
+        fraction data on general meshes,
+        Journal of Computational Physics, 2019,
+        doi 10.1016/j.jcp.2019.01.009
+
+    \endverbatim
+
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    cutCellPLIC.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cutCellPLIC_H
+#define cutCellPLIC_H
+
+#include "cutCell.H"
+#include "cutFacePLIC.H"
+#include "fvMesh.H"
+#include "surfaceFields.H"
+#include "volFields.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class cutCellPLIC Declaration
+\*---------------------------------------------------------------------------*/
+
+class cutCellPLIC
+:
+    public cutCell
+{
+    // Private Data
+
+        //- Mesh whose cells and faces to cut at their intersection with an
+        //  isosurface.
+        const fvMesh& mesh_;
+
+        //- Cell to cut
+        label cellI_;
+
+        //- Normal of the cutting plane
+        vector normal_;
+
+        //- Cutvalue used to cut cell
+        scalar cutValue_;
+
+        //- An cutFacePLIC object to get access to its face cutting functionality
+        cutFacePLIC cutFace_;
+
+        //- List of face centres for CutFaces
+        DynamicList<point> cutFaceCentres_;
+
+        //- List of face area vectors for PLICCutFaces
+        DynamicList<vector> cutFaceAreas_;
+
+        //- Storage for subFace edges belonging to PLICFace
+        DynamicList<DynamicList<point>> plicFaceEdges_;
+
+        //- Points constituting the cell-PLICsurface intersection (isoface)
+        DynamicList<point> facePoints_;
+
+        //- Face centre of the cutFace
+        point faceCentre_;
+
+        //- Face normal of the PLICface by convention pointing from high to low
+        //  values (i.e. opposite of the gradient vector).
+        vector faceArea_;
+
+        //- Cell centre of the subcell of celli which is "fully submerged", i.e.
+        //  where the function value is higher than the isoValue_
+        point subCellCentre_;
+
+        //- Volume of fully submerged subcell
+        scalar subCellVolume_;
+
+        //- Volume of Fluid for cellI (subCellVolume_/mesh_.V()[cellI])
+        scalar VOF_;
+
+        //- A cell status label taking one of the values:
+        //
+        //   -1: cell is fully below the PLICsurface
+        //    0: cell is cut
+        //   +1: cell is fully above the PLICsurface
+        label cellStatus_;
+
+
+  public:
+
+    // Constructors
+
+        //- Construct from fvMesh
+        explicit cutCellPLIC(const fvMesh& mesh);
+
+
+    // Member Functions
+
+        //- Sets internal values and returns face status
+        label calcSubCell
+        (
+            const label celli,
+            const scalar cutValue,
+            const vector& normal
+        );
+
+        //- Returns subCellCentre
+        const point& subCellCentre() const;
+
+        //- Returns subCellVolume
+        scalar subCellVolume() const;
+
+        //- Returns the points of the cutting PLICface
+        const DynamicList<point>& facePoints();
+
+        //- Returns the centre of the cutting PLICface
+        const point& faceCentre() const;
+
+        //- Returns the area normal vector of the cutting PLICface
+        const vector& faceArea() const;
+
+        //- Returns cellStatus
+        label cellStatus() const;
+
+        //- Returns volume of fluid value
+        scalar VolumeOfFluid() const;
+
+        //- Returns cutValue
+        scalar cutValue() const;
+
+        //- Resets internal values
+        void clearStorage();
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFace.C b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFace.C
new file mode 100644
index 0000000000000000000000000000000000000000..7b86efff173c81059325238e27e3e8c6a761e38b
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFace.C
@@ -0,0 +1,337 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutFace.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+int Foam::cutFace::debug = 0;
+
+// * * * * * * * * * * * * * Protected Member Functions  * * * * * * * * * * *
+
+void Foam::cutFace::calcSubFace
+(
+    const label faceI,
+    const scalarList& pointStatus,
+    label firstFullySubmergedPoint,
+    DynamicList<point>& subFacePoints,
+    DynamicList<point>& surfacePoints,
+    label& faceStatus,
+    vector& subFaceCentre,
+    vector& subFaceArea
+)
+{
+    const pointField& points = mesh_.points();
+    const face& f = mesh_.faces()[faceI];
+
+    if (firstFullySubmergedPoint == -1) // is in gasPhase
+    {
+        faceStatus = 1;
+        subFaceCentre = Zero;
+        subFaceArea = Zero;
+        return;
+    }
+
+    // loop face and append the cuts
+    // loop starts at firstFullySubmergedPoint
+    for
+    (
+        label i = firstFullySubmergedPoint;
+        i < firstFullySubmergedPoint + f.size();
+        ++i
+    )
+    {
+        // max two points are appended during one cycle
+        label idx = i % f.size();
+        label nextIdx = (i + 1) % f.size();
+
+        if (pointStatus[idx] > 0) // append fluid point
+        {
+            subFacePoints.append(points[f[idx]]);
+        }
+        else if (pointStatus[idx] == 0) // append cut point
+        {
+            subFacePoints.append(points[f[idx]]);
+            surfacePoints.append(points[f[idx]]);
+        }
+
+        if
+        (
+            (pointStatus[idx] < 0 && pointStatus[nextIdx] > 0) ||
+            (pointStatus[idx] > 0 && pointStatus[nextIdx] < 0)
+        ) // cut on edge cut Value is zero
+        {
+            label nextP = f.nextLabel(idx);
+            vector dir = points[nextP] - points[f[idx]];
+            scalar weight =
+                (0.0 - pointStatus[idx]) /
+                (pointStatus[nextIdx] - pointStatus[idx]); // cutValue is zero
+
+            point p = points[f[idx]] + weight * dir;
+
+            subFacePoints.append(p);
+            surfacePoints.append(p);
+        }
+    }
+
+    if (subFacePoints.size() >= 3)
+    {
+        faceStatus = 0;
+        calcSubFaceCentreAndArea(subFacePoints, subFaceCentre, subFaceArea);
+    }
+    else
+    {
+        faceStatus = -1;
+    }
+}
+
+
+void Foam::cutFace::calcSubFace
+(
+    const label faceI,
+    const scalarList& pointStatus,
+    const scalarList& weights,
+    label firstFullySubmergedPoint,
+    DynamicList<point>& subFacePoints,
+    DynamicList<point>& surfacePoints,
+    label& faceStatus,
+    vector& subFaceCentre,
+    vector& subFaceArea
+)
+{
+    const pointField& points = mesh_.points();
+    const face& f = mesh_.faces()[faceI];
+
+    if (firstFullySubmergedPoint == -1) // is in gasPhase
+    {
+        faceStatus = 1;
+        subFaceCentre = Zero;
+        subFaceArea = Zero;
+        return;
+    }
+
+    // loop face and append the cuts
+    // loop starts at firstFullySubmergedPoint
+    for
+    (
+        label i = firstFullySubmergedPoint;
+        i < firstFullySubmergedPoint + f.size();
+        ++i
+    )
+    {
+        // max two points are appended during one cycle
+        label idx = i % f.size();
+        label nextIdx = (i + 1) % f.size();
+
+        if (pointStatus[idx] > 0) // append fluid point
+        {
+            subFacePoints.append(points[f[idx]]);
+        }
+        else if (pointStatus[idx] == 0) // append cut point
+        {
+            subFacePoints.append(points[f[idx]]);
+            surfacePoints.append(points[f[idx]]);
+        }
+
+        if
+        (
+            (pointStatus[idx] < 0 && pointStatus[nextIdx] > 0) ||
+            (pointStatus[idx] > 0 && pointStatus[nextIdx] < 0)
+        ) // cut on edge cut Value is zero
+        {
+            label nextP = f.nextLabel(idx);
+            vector dir = points[nextP] - points[f[idx]];
+
+            point p = points[f[idx]] + weights[idx] * dir;
+
+            subFacePoints.append(p);
+            surfacePoints.append(p);
+        }
+    }
+
+    if (subFacePoints.size() >= 3)
+    {
+        faceStatus = 0;
+        calcSubFaceCentreAndArea(subFacePoints, subFaceCentre, subFaceArea);
+    }
+    else
+    {
+        faceStatus = -1;
+    }
+}
+
+
+void Foam::cutFace::calcSubFace
+(
+    const face& f,
+    const pointField& points,
+    const scalarList& pointStatus,
+    label firstFullySubmergedPoint,
+    DynamicList<point>& subFacePoints,
+    DynamicList<point>& surfacePoints,
+    label& faceStatus,
+    vector& subFaceCentre,
+    vector& subFaceArea
+)
+{
+    if (firstFullySubmergedPoint == -1) // in Gas
+    {
+        faceStatus = 1;
+        subFaceCentre = Zero;
+        subFaceArea = Zero;
+        return;
+    }
+
+    // loop face and append the cuts
+    for
+    (
+        label i = firstFullySubmergedPoint;
+        i < firstFullySubmergedPoint + f.size();
+        ++i
+    )
+    {
+        // max two points are appended during one cycle
+        label idx = i % f.size();
+        label nextIdx = (i + 1) % f.size();
+
+        if (pointStatus[idx] > 0) // append fluid point
+        {
+            subFacePoints.append(points[f[idx]]);
+        }
+        else if (pointStatus[idx] == 0) // append cut point
+        {
+            subFacePoints.append(points[f[idx]]);
+            surfacePoints.append(points[f[idx]]);
+        }
+
+        if
+        (
+            (pointStatus[idx] < 0 && pointStatus[nextIdx] > 0) ||
+            (pointStatus[idx] > 0 &&  pointStatus[nextIdx] < 0)
+        )
+        {
+            label nextP = f.nextLabel(idx);
+            vector dir = points[nextP] - points[f[idx]];
+            scalar weight =
+                (0.0 - pointStatus[idx]) /
+                (pointStatus[nextIdx] - pointStatus[idx]);
+
+            point p = points[f[idx]] + weight * dir;
+
+            subFacePoints.append(p);
+            surfacePoints.append(p);
+        }
+    }
+
+    if (subFacePoints.size() >= 3)
+    {
+        faceStatus = 0;
+        calcSubFaceCentreAndArea(subFacePoints, subFaceCentre, subFaceArea);
+    }
+    else
+    {
+        faceStatus = -1;
+    }
+}
+
+
+void Foam::cutFace::calcSubFaceCentreAndArea
+(
+    DynamicList<point>& subFacePoints,
+    vector& subFaceCentre,
+    vector& subFaceArea
+)
+{
+    const label nPoints = subFacePoints.size();
+
+    // If the face is a triangle, do a direct calculation for efficiency
+    // and to avoid round-off error-related problems
+    if (nPoints == 3)
+    {
+        subFaceCentre =
+                (1.0 / 3.0) * (subFacePoints[0] + subFacePoints[1] + subFacePoints[2]);
+
+        subFaceArea = 0.5 * ((subFacePoints[1] - subFacePoints[0]) ^
+                             (subFacePoints[2] - subFacePoints[0]));
+    }
+    else if (nPoints > 0)
+    {
+        vector sumN{Zero};
+        scalar sumA{0};
+        vector sumAc{Zero};
+
+        point fCentre = subFacePoints[0];
+        // initial guess of centre as average of subFacePoints
+        for (label pi = 1; pi < nPoints; pi++)
+        {
+            fCentre += subFacePoints[pi];
+        }
+
+        fCentre /= nPoints;
+
+        // loop sub triangles
+        for (label pi = 0; pi < nPoints; pi++)
+        {
+            const point& nextPoint = subFacePoints[(pi + 1) % nPoints];
+
+            vector c = subFacePoints[pi] + nextPoint + fCentre;
+            vector n =
+                (nextPoint - subFacePoints[pi]) ^ (fCentre - subFacePoints[pi]);
+            scalar a = mag(n);
+
+            sumN += n;
+            sumA += a;
+            sumAc += a * c;
+        }
+
+        // This is to deal with zero-area faces. Mark very small faces
+        // to be detected in e.g., processorPolyPatch.
+        if (sumA < ROOTVSMALL)
+        {
+            subFaceCentre = fCentre;
+            subFaceArea = Zero;
+        }
+        else
+        {
+            subFaceCentre = (1.0 / 3.0) * sumAc / sumA;
+            subFaceArea = 0.5 * sumN;
+        }
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutFace::cutFace(const fvMesh& mesh)
+:
+    mesh_(mesh)
+{}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFace.H b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFace.H
new file mode 100644
index 0000000000000000000000000000000000000000..de8f6b72727e79e609ac15fcfa790c303c9acae4
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFace.H
@@ -0,0 +1,152 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::cutFace
+
+Description
+    Base class for cutting a face, faceI, of an fvMesh, mesh_, at its
+    intersections
+
+    Original code supplied by
+        Johan Roenby, DHI (2016)
+        Henning Scheufler, DLR (2019)
+
+SourceFiles
+    cutFace.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cutFace_H
+#define cutFace_H
+
+#include "fvMesh.H"
+#include "surfaceFields.H"
+#include "volFields.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                          Class cutFaces Declaration
+\*---------------------------------------------------------------------------*/
+
+class cutFace
+{
+    // Private Data
+
+        //- Reference to mesh
+        const fvMesh& mesh_;
+
+
+protected:
+
+    //- Calculate cut points along edges of face with pointStatus, pointfield
+    //- and computes geometric information and the face status where:
+    // -  -1: faceStatus is fully below the isosurface
+    // -   0: faceStatus is cut (has values larger and smaller than isoValue)
+    // -  +1: faceStatus is fully above the isosurface
+    void calcSubFace
+    (
+        const label faceI,
+        const scalarList& pointStatus,
+        label firstFullySubmergedPoint,
+        DynamicList<point>& subFacePoints,
+        DynamicList<point>& surfacePoints,
+        label& faceStatus,
+        vector& subFaceCentre,
+        vector& subFaceArea
+     );
+
+    //- Calculate cut points along edges of face with pointStatus, pointfield,
+    //- weights and computes geometric information and the face status where:
+    // -  -1: faceStatus is fully below the isosurface
+    // -   0: faceStatus is cut (has values larger and smaller than isoValue)
+    // -  +1: faceStatus is fully above the isosurface
+    void calcSubFace
+    (
+        const label faceI,
+        const scalarList& pointStatus,
+        const scalarList& weights,
+        label firstFullySubmergedPoint,
+        DynamicList<point>& subFacePoints,
+        DynamicList<point>& surfacePoints,
+        label& faceStatus,
+        vector& subFaceCentre,
+        vector& subFaceArea
+    );
+
+    //- Calculates centre and normal of the face
+    void calcSubFaceCentreAndArea
+    (
+        DynamicList<point>& subFacePoints,
+        vector& subFaceCentre,
+        vector& subFaceArea
+    );
+
+    //- Calculate cut points along edges of face with pointStatus, pointfield
+    //- and computes geometric information and the face status where:
+    // -  -1: faceStatus is fully below the isosurface
+    // -   0: faceStatus is cut (has values larger and smaller than isoValue)
+    // -  +1: faceStatus is fully above the isosurface
+    void calcSubFace
+    (
+        const face& f,
+        const pointField& points,
+        const scalarList& pointStatus,
+        label firstFullySubmergedPoint,
+        DynamicList<point>& subFacePoints,
+        DynamicList<point>& surfacePoints,
+        label& faceStatus,
+        vector& subFaceCentre,
+        vector& subFaceArea
+    );
+
+
+public:
+
+    // Static Data
+    static int debug;
+
+
+    // Constructors
+
+        //- Construct from fvMesh
+        explicit cutFace(const fvMesh& mesh);
+};
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceAdvect.C b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceAdvect.C
new file mode 100644
index 0000000000000000000000000000000000000000..c5bd8b589a01c56e439d1eea753d93e4ea9a7017
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceAdvect.C
@@ -0,0 +1,1024 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutFaceAdvect.H"
+#include "OFstream.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutFaceAdvect::cutFaceAdvect
+(
+    const fvMesh& mesh,
+    const volScalarField& alpha1
+)
+:
+    cutFace(mesh),
+    mesh_(mesh),
+    alpha1_(alpha1),
+    subFaceCentre_(Zero),
+    subFaceArea_(Zero),
+    subFacePoints_(10),
+    surfacePoints_(4),
+    pointStatus_(10),
+    weight_(10),
+    pTimes_(10),
+    faceStatus_(-1)
+{
+    clearStorage();
+}
+
+
+// * * * * * * * * * * * Public Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::cutFaceAdvect::calcSubFace
+(
+    const label faceI,
+    const vector& normal,
+    const vector& base
+)
+{
+    clearStorage();
+
+    const face& f = mesh_.faces()[faceI];
+
+    label inLiquid = 0;
+    label firstFullySubmergedPoint = -1;
+
+    // Loop face and calculate pointStatus
+    forAll(f, i)
+    {
+        scalar value = (mesh_.points()[f[i]] - base) & normal;
+        if (mag(value) < 10 * SMALL)
+        {
+            value = 0;
+        }
+        pointStatus_.append(value);
+        if (pointStatus_[i] > 10 * SMALL)
+        {
+            inLiquid++;
+            if (firstFullySubmergedPoint == -1)
+            {
+                firstFullySubmergedPoint = i;
+            }
+        }
+    }
+
+    if (inLiquid == f.size()) // fluid face
+    {
+        faceStatus_ = -1;
+        subFaceCentre_ = mesh_.faceCentres()[faceI];
+        subFaceArea_ = mesh_.faceAreas()[faceI];
+        return faceStatus_;
+    }
+    else if (inLiquid == 0) // gas face
+    {
+        faceStatus_ = 1;
+        subFaceCentre_ = Zero;
+        subFaceArea_ = Zero;
+        return faceStatus_;
+    }
+
+    cutFace::calcSubFace
+    (
+        faceI,
+        pointStatus_,
+        firstFullySubmergedPoint,
+        subFacePoints_,
+        surfacePoints_,
+        faceStatus_,
+        subFaceCentre_,
+        subFaceArea_
+    );
+
+    return faceStatus_;
+}
+
+
+Foam::label Foam::cutFaceAdvect::calcSubFace
+(
+    const face& f,
+    const pointField& points,
+    const scalarField& val,
+    const scalar cutValue
+)
+{
+    clearStorage();
+
+    label inLiquid = 0;
+    label firstFullySubmergedPoint = -1;
+    scalarList pointStatus(f.size());
+
+    // Loop face and calculate pointStatus
+    forAll(f, i)
+    {
+        pointStatus[i] = val[f[i]] - cutValue;
+        if (mag(pointStatus[i]) < 10 * SMALL)
+        {
+            pointStatus[i] = 0;
+        }
+        if (pointStatus[i] > 10 * SMALL)
+        {
+            ++inLiquid;
+            if (firstFullySubmergedPoint == -1)
+            {
+                firstFullySubmergedPoint = i;
+            }
+        }
+    }
+
+    if (inLiquid == f.size()) // fluid face
+    {
+        faceStatus_ = -1;
+        subFaceCentre_ = f.centre(points);
+        subFaceArea_ = f.areaNormal(points);
+        return faceStatus_;
+    }
+    else if (inLiquid == 0) // gas face
+    {
+        faceStatus_ = 1;
+        subFaceCentre_ = Zero;
+        subFaceArea_ = Zero;
+        return faceStatus_;
+    }
+
+    cutFace::calcSubFace
+    (
+        f,
+        points,
+        pointStatus,
+        firstFullySubmergedPoint,
+        subFacePoints_,
+        surfacePoints_,
+        faceStatus_,
+        subFaceCentre_,
+        subFaceArea_
+    );
+
+    return faceStatus_;
+}
+
+
+Foam::scalar Foam::cutFaceAdvect::timeIntegratedFaceFlux
+(
+    const label faceI,
+    const vector& x0,
+    const vector& n0, // has to has the length of 1
+    const scalar Un0,
+    const scalar dt,
+    const scalar phi,
+    const scalar magSf
+)
+{
+    clearStorage();
+
+/* Temporarily taken out
+    // Treating rare cases where isoface normal is not calculated properly
+    if (mag(n0) < 0.5)
+    {
+        scalar alphaf = 0.0;
+        scalar waterInUpwindCell = 0.0;
+
+        if (phi > 0 || !mesh_.isInternalFace(faceI))
+        {
+            const label upwindCell = mesh_.faceOwner()[faceI];
+            alphaf = alpha1_[upwindCell];
+            waterInUpwindCell = alphaf * mesh_.V()[upwindCell];
+        }
+        else
+        {
+            const label upwindCell = mesh_.faceNeighbour()[faceI];
+            alphaf = alpha1_[upwindCell];
+            waterInUpwindCell = alphaf * mesh_.V()[upwindCell];
+        }
+
+        return min(alphaf * phi * dt, waterInUpwindCell);
+    }*/
+
+    // Find sorted list of times where the isoFace will arrive at face points
+    // given initial position x0 and velocity Un0*n0
+
+    // Get points for this face
+    const face& f = mesh_.faces()[faceI];
+    const label nPoints = f.size();
+
+    if (mag(Un0) > 1e-12) // Note: tolerances
+    {
+        // Here we estimate time of arrival to the face points from their normal
+        // distance to the initial surface and the surface normal velocity
+
+        for (const scalar fi : f)
+        {
+            scalar value = ((mesh_.points()[fi] - x0) & n0) / Un0;
+            if (mag(value) < 10 * SMALL)
+            {
+                value = 0;
+            }
+            pTimes_.append(value);
+        }
+
+        scalar dVf = 0;
+
+        // Check if pTimes changes direction more than twice when looping face
+        label nShifts = 0;
+        forAll(pTimes_, pi) // i have no clue what this is
+        {
+            const label oldEdgeSign =
+                sign(pTimes_[(pi + 1) % nPoints] - pTimes_[pi]);
+            const label newEdgeSign =
+                sign(pTimes_[(pi + 2) % nPoints] - pTimes_[(pi + 1) % nPoints]);
+
+            if (newEdgeSign != oldEdgeSign)
+            {
+                nShifts++;
+            }
+        }
+
+        if (nShifts == 2 || nShifts == 0)
+        {
+            dVf = phi / magSf * timeIntegratedArea(faceI, dt, magSf, Un0);
+        }
+        else if (nShifts >  2) // triangle decompose the non planar face
+        {
+            const pointField fPts(f.points(mesh_.points()));
+            pointField fPts_tri(3);
+            scalarField pTimes_tri(3);
+            fPts_tri[0] = mesh_.faceCentres()[faceI];
+            pTimes_tri[0] = ((fPts_tri[0] - x0) & n0)/Un0;
+            scalar area = 0;
+            for (label pi = 0; pi < nPoints; ++pi)
+            {
+                fPts_tri[1] = fPts[pi];
+                pTimes_tri[1] = pTimes_[pi];
+                fPts_tri[2] = fPts[(pi + 1) % nPoints];
+                pTimes_tri[2] = pTimes_[(pi + 1) % nPoints];
+                const scalar magSf_tri =
+                    mag
+                    (
+                        0.5
+                       *(fPts_tri[2] - fPts_tri[0])
+                       ^(fPts_tri[1] - fPts_tri[0])
+                    );
+                area += magSf_tri;
+                const scalar phi_tri = phi*magSf_tri/magSf;
+                dVf +=
+                    phi_tri/magSf_tri
+                   *timeIntegratedArea
+                    (
+                        fPts_tri,
+                        pTimes_tri,
+                        dt,
+                        magSf_tri,
+                        Un0
+                    );
+            }
+        }
+        else
+        {
+            if (debug)
+            {
+                WarningInFunction
+                    << "Warning: nShifts = " << nShifts << " on face "
+                    << faceI << " with pTimes = " << pTimes_
+                    << " owned by cell " << mesh_.faceOwner()[faceI]
+                    << endl;
+            }
+        }
+
+        return dVf;
+    }
+    else
+    {
+        // Un0 is almost zero and isoFace is treated as stationary
+        calcSubFace(faceI, -n0, x0);
+        const scalar alphaf = mag(subFaceArea() / magSf);
+
+        if (debug)
+        {
+            WarningInFunction
+                << "Un0 is almost zero (" << Un0
+                << ") - calculating dVf on face " << faceI
+                << " using subFaceFraction giving alphaf = " << alphaf
+                << endl;
+        }
+
+        return phi * dt * alphaf;
+    }
+}
+
+
+Foam::scalar Foam::cutFaceAdvect::timeIntegratedFaceFlux
+(
+    const label faceI,
+    const scalarField& times,
+    const scalar Un0,
+    const scalar dt,
+    const scalar phi,
+    const scalar magSf
+)
+{
+    clearStorage();
+
+    label nPoints = times.size();
+
+    {
+        // Here we estimate time of arrival to the face points from their normal
+        // distance to the initial surface and the surface normal velocity
+
+        pTimes_.append(times);
+
+        scalar dVf = 0;
+
+        // Check if pTimes changes direction more than twice when looping face
+        label nShifts = 0;
+        forAll(pTimes_, pi) // i have no clue what this is
+        {
+            const label oldEdgeSign =
+                sign(pTimes_[(pi + 1) % nPoints] - pTimes_[pi]);
+            const label newEdgeSign =
+                sign(pTimes_[(pi + 2) % nPoints] - pTimes_[(pi + 1) % nPoints]);
+
+            if (newEdgeSign != oldEdgeSign)
+            {
+                ++nShifts;
+            }
+        }
+
+        if (nShifts == 2)
+        {
+            dVf = phi/magSf*timeIntegratedArea(faceI, dt, magSf, Un0);
+        }
+        // not possible to decompose face
+        return dVf;
+    }
+}
+
+
+Foam::scalar Foam::cutFaceAdvect::timeIntegratedArea
+(
+    const pointField& fPts,
+    const scalarField& pTimes,
+    const scalar dt,
+    const scalar magSf,
+    const scalar Un0
+)
+{
+    // Initialise time integrated area returned by this function
+    scalar tIntArea = 0.0;
+
+    // Finding ordering of vertex points
+    const labelList order(Foam::sortedOrder(pTimes));
+    const scalar firstTime = pTimes[order.first()];
+    const scalar lastTime = pTimes[order.last()];
+
+    // Dealing with case where face is not cut by surface during time interval
+    // [0,dt] because face was already passed by surface
+    if (lastTime <= 0)
+    {
+        // If all face cuttings were in the past and cell is filling up (Un0>0)
+        // then face must be full during whole time interval
+        tIntArea = magSf * dt * pos0(Un0);
+        return tIntArea;
+    }
+
+    // Dealing with case where face is not cut by surface during time interval
+    // [0, dt] because dt is too small for surface to reach closest face point
+    if (firstTime >= dt)
+    {
+        // If all cuttings are in the future but non of them within [0,dt] then
+        // if cell is filling up (Un0 > 0) face must be empty during whole time
+        // interval
+        tIntArea = magSf * dt * (1 - pos0(Un0));
+        return tIntArea;
+    }
+
+    // If we reach this point in the code some part of the face will be swept
+    // during [tSmall, dt-tSmall]. However, it may be the case that there are no
+    // vertex times within the interval. This will happen sometimes for small
+    // time steps where both the initial and the final face-interface
+    // intersection line (FIIL) will be along the same two edges.
+
+    // Face-interface intersection line (FIIL) to be swept across face
+    DynamicList<point> FIIL(3);
+    // Submerged area at beginning of each sub time interval time
+    scalar initialArea = 0.0;
+    // Running time keeper variable for the integration process
+    scalar time = 0.0;
+
+    // Special treatment of first sub time interval
+    if (firstTime > 0)
+    {
+        // If firstTime > 0 the face is uncut in the time interval
+        // [0, firstTime] and hence fully submerged in fluid A or B.
+        // If Un0 > 0 cell is filling up and it must initially be empty.
+        // If Un0 < 0 cell must initially be full(y immersed in fluid A).
+        time = firstTime;
+        initialArea = magSf * (1.0 - pos0(Un0));
+        tIntArea = initialArea * time;
+        cutPoints(fPts, pTimes, time, FIIL);
+    }
+    else
+    {
+        // If firstTime <= 0 then face is initially cut and we must
+        // calculate the initial submerged area and FIIL:
+        time = 0.0;
+        // Note: calcSubFace assumes well-defined 2-point FIIL!!!!
+        // calcSubFace(fPts, -sign(Un0)*pTimes, time);
+        // calcSubFace(fPts, -sign(Un0)*pTimes, time)
+        calcSubFace(face(identity(pTimes.size())), fPts, pTimes, time);
+        initialArea = mag(subFaceArea());
+        cutPoints(fPts, pTimes, time, FIIL);
+    }
+
+    // Making sorted array of all vertex times that are between max(0,firstTime)
+    // and dt and further than tSmall from the previous time.
+    DynamicList<scalar> sortedTimes(pTimes.size());
+    {
+        scalar prevTime = time;
+        const scalar tSmall = max(1e-6*dt, 10*SMALL);
+
+        for (const scalar timeI : order)
+        {
+            if (timeI > prevTime + tSmall && timeI <= dt)
+            {
+                sortedTimes.append(timeI);
+                prevTime = timeI;
+            }
+        }
+    }
+
+    // Sweeping all quadrilaterals corresponding to the intervals defined above
+    for (const scalar newTime : sortedTimes)
+    {
+        // New face-interface intersection line
+        DynamicList<point> newFIIL(3);
+        cutPoints(fPts, pTimes, newTime, newFIIL);
+
+        // quadrilateral area coefficients
+        scalar alpha = 0, beta = 0;
+        quadAreaCoeffs(FIIL, newFIIL, alpha, beta);
+        // Integration of area(t) = A*t^2+B*t from t = 0 to 1
+        tIntArea += (newTime - time) *
+                    (initialArea + sign(Un0) * (alpha/3.0 + 0.5*beta));
+        // Adding quad area to submerged area
+        initialArea += sign(Un0)*(alpha + beta);
+
+        FIIL = newFIIL;
+        time = newTime;
+    }
+
+    // Special treatment of last time interval
+    if (lastTime > dt)
+    {
+        // FIIL will end up cutting the face at dt
+        // New face-interface intersection line
+        DynamicList<point> newFIIL(3);
+        cutPoints(fPts, pTimes, dt, newFIIL);
+
+        // quadrilateral area coefficients
+        scalar alpha = 0, beta = 0;
+        quadAreaCoeffs(FIIL, newFIIL, alpha, beta);
+        // Integration of area(t) = A*t^2+B*t from t = 0 to 1
+        tIntArea += (dt - time) *
+                    (initialArea + sign(Un0)*(alpha / 3.0 + 0.5 * beta));
+    }
+    else
+    {
+        // FIIL will leave the face at lastTime and face will be fully in fluid
+        // A or fluid B in the time interval from lastTime to dt.
+        tIntArea += magSf*(dt - lastTime)*pos0(Un0);
+    }
+
+    return tIntArea;
+}
+
+
+void Foam::cutFaceAdvect::isoFacesToFile
+(
+    const DynamicList<List<point>>& faces,
+    const word& filNam,
+    const word& filDir
+) const
+{
+    // Writing isofaces to vtk file for inspection in paraview
+
+    fileName outputFile(filDir/(filNam + ".vtk"));
+
+    mkDir(filDir);
+    Info<< "Writing file: " << outputFile << endl;
+
+    OFstream os(outputFile);
+    os  << "# vtk DataFile Version 2.0" << nl
+        << filNam << nl
+        << "ASCII" << nl
+        << "DATASET POLYDATA" << nl;
+
+    label nPoints{0};
+    for (const List<point>& f : faces)
+    {
+        nPoints += f.size();
+    }
+
+    os << "POINTS " << nPoints << " float" << nl;
+    for (const List<point>& f : faces)
+    {
+        for (const point& p : f)
+        {
+            os << p.x() << ' ' << p.y() << ' ' << p.z() << nl;
+        }
+    }
+
+    os  << "POLYGONS "
+        << faces.size() << ' ' << (nPoints + faces.size()) << nl;
+
+    label pointi = 0;
+    for (const List<point>& f : faces)
+    {
+        label endp = f.size();
+        os << endp;
+
+        endp += pointi;
+
+        while (pointi < endp)
+        {
+            os << ' ' << pointi;
+            ++pointi;
+        }
+        os << nl;
+    }
+}
+
+
+Foam::label Foam::cutFaceAdvect::calcSubFace
+(
+    const label faceI,
+    const label sign,
+    const scalar cutValue
+)
+{
+    // clearStorage();
+    const face& f = mesh_.faces()[faceI];
+    label inLiquid = 0;
+    label firstFullySubmergedPoint = -1;
+
+    // Loop face and calculate pointStatus
+    forAll(f, i)
+    {
+        scalar value = (sign * pTimes_[i] - cutValue);
+
+        if (mag(value) < 10 * SMALL)
+        {
+            value = 0;
+        }
+        pointStatus_.append(value);
+        if (pointStatus_[i] > 10 * SMALL)
+        {
+            inLiquid++;
+            if (firstFullySubmergedPoint == -1)
+            {
+                firstFullySubmergedPoint = i;
+            }
+        }
+    }
+
+    if (inLiquid == f.size()) // fluid face
+    {
+        faceStatus_ = -1;
+        subFaceCentre_ = mesh_.faceCentres()[faceI];
+        subFaceArea_ = mesh_.faceAreas()[faceI];
+        return faceStatus_;
+    }
+    else if (inLiquid == 0) // gas face
+    {
+        faceStatus_ = 1;
+        subFaceCentre_ = Zero;
+        subFaceArea_ = Zero;
+        return faceStatus_;
+    }
+
+    cutFace::calcSubFace
+    (
+        faceI,
+        pointStatus_,
+        firstFullySubmergedPoint,
+        subFacePoints_,
+        surfacePoints_,
+        faceStatus_,
+        subFaceCentre_,
+        subFaceArea_
+    );
+
+    return faceStatus_;
+}
+
+
+Foam::scalar Foam::cutFaceAdvect::timeIntegratedArea
+(
+    const label faceI,
+    const scalar dt,
+    const scalar magSf,
+    const scalar Un0
+)
+{
+    // Initialise time integrated area returned by this function
+    scalar tIntArea = 0.0;
+
+    // Finding ordering of vertex points
+    const labelList order(Foam::sortedOrder(pTimes_));
+    const scalar firstTime = pTimes_[order.first()];
+    const scalar lastTime = pTimes_[order.last()];
+
+    // Dealing with case where face is not cut by surface during time interval
+    // [0,dt] because face was already passed by surface
+    if (lastTime <= 0)
+    {
+        // If all face cuttings were in the past and cell is filling up (Un0>0)
+        // then face must be full during whole time interval
+        tIntArea = magSf* dt * pos0(Un0);
+        return tIntArea;
+    }
+
+    // Dealing with case where face is not cut by surface during time interval
+    // [0, dt] because dt is too small for surface to reach closest face point
+    if (firstTime >= dt)
+    {
+        // If all cuttings are in the future but non of them within [0,dt] then
+        // if cell is filling up (Un0 > 0) face must be empty during whole time
+        // interval
+        tIntArea = magSf * dt * (1 - pos0(Un0));
+        return tIntArea;
+    }
+
+    // If we reach this point in the code some part of the face will be swept
+    // during [tSmall, dt-tSmall]. However, it may be the case that there are no
+    // vertex times within the interval. This will happen sometimes for small
+    // time steps where both the initial and the final face-interface
+    // intersection line (FIIL) will be along the same two edges.
+
+    // Face-interface intersection line (FIIL) to be swept across face
+    DynamicList<point> FIIL(3);
+    // Submerged area at beginning of each sub time interval time
+    scalar initialArea = 0.0;
+    // Running time keeper variable for the integration process
+    scalar time = 0.0;
+
+    // Special treatment of first sub time interval
+    if (firstTime > 0)
+    {
+        // If firstTime > 0 the face is uncut in the time interval
+        // [0, firstTime] and hence fully submerged in fluid A or B.
+        // If Un0 > 0 cell is filling up and it must initially be empty.
+        // If Un0 < 0 cell must initially be full(y immersed in fluid A).
+        time = firstTime;
+        initialArea = magSf * (1.0 - pos0(Un0));
+        tIntArea = initialArea * time;
+        cutPoints(faceI, time, FIIL);
+    }
+    else
+    {
+        // If firstTime <= 0 then face is initially cut and we must
+        // calculate the initial submerged area and FIIL:
+        time = 0.0;
+        // Note: calcSubFace assumes well-defined 2-point FIIL!!!!
+        calcSubFace(faceI, -sign(Un0), time);
+        initialArea = mag(subFaceArea());
+        cutPoints(faceI, time, FIIL);
+    }
+
+    // Making sorted array of all vertex times that are between max(0,firstTime)
+    // and dt and further than tSmall from the previous time.
+    DynamicList<scalar> sortedTimes(pTimes_.size());
+    {
+        scalar prevTime = time;
+        const scalar tSmall = max(1e-6*dt, 10*SMALL);
+        for (const label oI : order)
+        {
+            const scalar timeI = pTimes_[oI];
+            if (timeI > prevTime + tSmall && timeI <= dt)
+            {
+                sortedTimes.append(timeI);
+                prevTime = timeI;
+            }
+        }
+    }
+
+    // Sweeping all quadrilaterals corresponding to the intervals defined above
+    for (const scalar newTime : sortedTimes)
+    {
+        // New face-interface intersection line
+        DynamicList<point> newFIIL(3);
+        cutPoints(faceI, newTime, newFIIL);
+
+        // quadrilateral area coefficients
+        scalar alpha = 0, beta = 0;
+
+        quadAreaCoeffs(FIIL, newFIIL, alpha, beta);
+        // Integration of area(t) = A*t^2+B*t from t = 0 to 1
+        tIntArea +=
+            (newTime - time)
+          * (initialArea + sign(Un0)
+          * (alpha / 3.0 + 0.5 * beta));
+        // Adding quad area to submerged area
+        initialArea += sign(Un0) * (alpha + beta);
+
+        FIIL = newFIIL;
+        time = newTime;
+    }
+
+    // Special treatment of last time interval
+    if (lastTime > dt)
+    {
+        // FIIL will end up cutting the face at dt
+        // New face-interface intersection line
+        DynamicList<point> newFIIL(3);
+        cutPoints(faceI, dt, newFIIL);
+
+        // quadrilateral area coefficients
+        scalar alpha = 0, beta = 0;
+        quadAreaCoeffs(FIIL, newFIIL, alpha, beta);
+        // Integration of area(t) = A*t^2+B*t from t = 0 to 1
+        tIntArea +=
+            (dt - time)
+          * (initialArea + sign(Un0) * (alpha / 3.0 + 0.5 * beta));
+    }
+    else
+    {
+        // FIIL will leave the face at lastTime and face will be fully in fluid
+        // A or fluid B in the time interval from lastTime to dt.
+        tIntArea += magSf * (dt - lastTime) * pos0(Un0);
+    }
+
+    return tIntArea;
+}
+
+
+void Foam::cutFaceAdvect::quadAreaCoeffs
+(
+    const DynamicList<point>& pf0,
+    const DynamicList<point>& pf1,
+    scalar& alpha,
+    scalar& beta
+) const
+{
+    // Number of points in provided face-interface intersection lines
+    const label np0 = pf0.size();
+    const label np1 = pf1.size();
+
+    // quad area coeffs such that area(t) = alpha*t^2 + beta*t.
+    // With time interval normalised, we have full quadArea = alpha + beta
+    // and time integrated quad area = alpha/3 + beta/2;
+    alpha = 0.0;
+    beta = 0.0;
+
+    if (np0 && np1)
+    {
+        // Initialising quadrilateral vertices A, B, C and D
+        vector A(pf0[0]);
+        vector C(pf1[0]);
+        vector B(pf0[0]);
+        vector D(pf1[0]);
+
+        if (np0 == 2)
+        {
+            B = pf0[1];
+        }
+        else if (np0 > 2)
+        {
+            WarningInFunction << "Vertex face was cut at pf0 = " << pf0 << endl;
+        }
+
+        if (np1 == 2)
+        {
+            D = pf1[1];
+        }
+        else if (np1 > 2)
+        {
+            WarningInFunction << "Vertex face was cut at pf1 = " << pf1 << endl;
+        }
+
+        // Swapping pf1 points if pf0 and pf1 point in same general direction
+        // (because we want a quadrilateral ABCD where pf0 = AB and pf1 = CD)
+        if (((B - A) & (D - C)) > 0)
+        {
+            vector tmp = D;
+            D = C;
+            C = tmp;
+        }
+
+        // Defining local coordinates (xhat, yhat) for area integration of swept
+        // quadrilateral ABCD such that A = (0,0), B = (Bx,0), C = (Cx,Cy) and
+        // D = (Dx,Dy) with Cy = 0 and Dy > 0.
+
+        const scalar Bx = mag(B - A);
+
+        vector xhat(Zero);
+        if (Bx > 10 * SMALL)
+        {
+            // If |AB| > 0 ABCD we use AB to define xhat
+            xhat = (B - A) / mag(B - A);
+        }
+        else if (mag(C - D) > 10 * SMALL)
+        {
+            // If |AB| ~ 0 ABCD is a triangle ACD and we use CD for xhat
+            xhat = (C - D) / mag(C - D);
+        }
+        else
+        {
+            return;
+        }
+
+        // Defining vertical axis in local coordinates
+        vector yhat = D - A;
+        yhat -= ((yhat & xhat) * xhat);
+
+        if (mag(yhat) > 10 * SMALL)
+        {
+            yhat /= mag(yhat);
+
+            const scalar Cx = (C - A) & xhat;
+            const scalar Cy = mag((C - A) & yhat);
+            const scalar Dx = (D - A) & xhat;
+            const scalar Dy = mag((D - A) & yhat);
+
+            // area = ((Cx - Bx)*Dy - Dx*Cy)/6.0 + 0.25*Bx*(Dy + Cy);
+            alpha = 0.5 * ((Cx - Bx) * Dy - Dx * Cy);
+            beta = 0.5 * Bx * (Dy + Cy);
+        }
+    }
+    else
+    {
+        WarningInFunction
+            << "Vertex face was cut at " << pf0 << " and at "
+            << pf1 << endl;
+    }
+}
+
+
+void Foam::cutFaceAdvect::cutPoints
+(
+    const label faceI,
+    const scalar f0,
+    DynamicList<point>& cutPoints
+)
+{
+    const face& f = mesh_.faces()[faceI];
+    const label nPoints = f.size();
+    scalar f1(pTimes_[0]);
+
+    // Snapping vertex value to f0 if very close (needed for 2D cases)
+    if (mag(f1 - f0) < 10 * SMALL)
+    {
+        f1 = f0;
+    }
+
+    forAll(f, pi)
+    {
+        label pi2 = (pi + 1) % nPoints;
+        scalar f2 = pTimes_[pi2];
+
+        // Snapping vertex value
+        if (mag(f2 - f0) < 10 * SMALL)
+        {
+            f2 = f0;
+        }
+
+        if ((f1 < f0 && f2 > f0) || (f1 > f0 && f2 < f0))
+        {
+            const scalar s = (f0 - f1) / (f2 - f1);
+            cutPoints.append
+            (
+                mesh_.points()[f[pi]]
+              + s*(mesh_.points()[f[pi2]] - mesh_.points()[f[pi]])
+            );
+        }
+        else if (f1 == f0)
+        {
+            cutPoints.append(mesh_.points()[f[pi]]);
+        }
+        f1 = f2;
+    }
+
+    if (cutPoints.size() > 2)
+    {
+        WarningInFunction
+            << "cutPoints = " << cutPoints
+            << " for pts = " << f.points(mesh_.points())
+            << ", f - f0 = " << f - f0 << " and f0 = " << f0
+            << endl;
+    }
+}
+
+
+void Foam::cutFaceAdvect::cutPoints
+(
+    const pointField& pts,
+    const scalarField& f,
+    const scalar f0,
+    DynamicList<point>& cutPoints
+)
+{
+    const label nPoints = pts.size();
+    scalar f1(f[0]);
+
+    // Snapping vertex value to f0 if very close (needed for 2D cases)
+    if (mag(f1 - f0) < 10 * SMALL)
+    {
+        f1 = f0;
+    }
+
+    forAll(pts, pi)
+    {
+        label pi2 = (pi + 1) % nPoints;
+        scalar f2 = f[pi2];
+
+        // Snapping vertex value
+        if (mag(f2 - f0) < 10 * SMALL)
+        {
+            f2 = f0;
+        }
+
+        if ((f1 < f0 && f2 > f0) || (f1 > f0 && f2 < f0))
+        {
+            const scalar s = (f0 - f1) / (f2 - f1);
+            cutPoints.append(pts[pi] + s * (pts[pi2] - pts[pi]));
+        }
+        else if (f1 == f0)
+        {
+            cutPoints.append(pts[pi]);
+        }
+        f1 = f2;
+    }
+
+    if (cutPoints.size() > 2)
+    {
+        WarningInFunction
+            << "cutPoints = " << cutPoints << " for pts = " << pts
+            << ", f - f0 = " << f - f0 << " and f0 = " << f0
+            << endl;
+    }
+}
+
+
+const Foam::point& Foam::cutFaceAdvect::subFaceCentre() const
+{
+    return subFaceCentre_;
+}
+
+
+const Foam::vector& Foam::cutFaceAdvect::subFaceArea() const
+{
+    return subFaceArea_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutFaceAdvect::subFacePoints() const
+{
+    return subFacePoints_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutFaceAdvect::surfacePoints() const
+{
+    return surfacePoints_;
+}
+
+
+void Foam::cutFaceAdvect::clearStorage()
+{
+    subFaceCentre_ = Zero;
+    subFaceArea_ = Zero;
+    subFacePoints_.clear();
+    surfacePoints_.clear();
+    pointStatus_.clear();
+    pTimes_.clear();
+    weight_.clear();
+    faceStatus_ = -1;
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceAdvect.H b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceAdvect.H
new file mode 100644
index 0000000000000000000000000000000000000000..51f3538193c69c2bda3194229029ddd4c7a66788
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceAdvect.H
@@ -0,0 +1,258 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::cutFaceAdvect
+
+Description
+    Calculates the face fluxes
+
+    Reference:
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+
+    \endverbatim
+
+    Original code supplied by Johan Roenby, DHI (2016)
+
+SourceFiles
+    cutFaceAdvect.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cutFaceAdvect_H
+#define cutFaceAdvect_H
+
+#include "cutFace.H"
+#include "fvMesh.H"
+#include "surfaceFields.H"
+#include "volFields.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class cutFaceAdvect Declaration
+\*---------------------------------------------------------------------------*/
+
+class cutFaceAdvect
+:
+    public cutFace
+{
+    // Private Data
+
+        typedef DynamicList<label> DynamicLabelList;
+        typedef DynamicList<scalar> DynamicScalarList;
+        typedef DynamicList<vector> DynamicVectorList;
+        typedef DynamicList<point> DynamicPointList;
+
+        //- Mesh whose cells and faces to cut at their intersection
+        //- with an isoface
+        const fvMesh& mesh_;
+
+        //- Reference to VoF field
+        const volScalarField& alpha1_;
+
+        //- Storage for centre of subface
+        point subFaceCentre_;
+
+        //- Storage for area vector of subface
+        vector subFaceArea_;
+
+        //- Storage for subFacePoints
+        DynamicList<point> subFacePoints_;
+
+        //- Storage for subFacePoints
+        DynamicList<point> surfacePoints_;
+
+        //- Storage for pointStatus_ cuts the cell at 0
+        DynamicList<scalar> pointStatus_;
+
+        //- Storage of the edge weight
+        DynamicList<scalar> weight_;
+
+        //- Storage for arrival Times
+        DynamicList<scalar> pTimes_;
+
+        //- A face status label taking one of the values:
+        //
+        //   -1: face is fully below the isosurface
+        //    0: face is cut, i.e. has values larger and smaller than isoValue_
+        //   +1: face is fully above the isosurface
+        label faceStatus_;
+
+
+    // Private Member Functions
+
+        //- Write faces to vtk files
+        void isoFacesToFile
+        (
+            const DynamicList<List<point>>& isoFacePts,
+            const word& fileName,
+            const word& fileDir
+        ) const;
+
+
+  public:
+
+    // Constructors
+
+        //- Construct from fvMesh and a scalarField
+        //  Length of scalarField should equal number of mesh points
+        cutFaceAdvect(const fvMesh& mesh, const volScalarField& alpha1);
+
+
+    // Member Functions
+
+        //- Calculates cut centre and cut area (plicReconstruction)
+        //  \return face status
+        label calcSubFace
+        (
+            const label faceI,
+            const vector& normal,
+            const vector& base
+        );
+
+        //- Calculates cut centre and cut area (iso reconstruction)
+        //  \return face status
+        label calcSubFace
+        (
+            const face& f,
+            const pointField& points,
+            const scalarField& val,
+            const scalar cutValue
+        );
+
+        //- Calculates cut centre and cut area (iso reconstruction)
+        //  \return face status
+        label calcSubFace
+        (
+            const label faceI,
+            const label sign,
+            const scalar cutValue
+        );
+
+        //- Calculate time integrated flux for a face
+        scalar timeIntegratedFaceFlux
+        (
+            const label faceI,
+            const vector& x0,
+            const vector& n0,
+            const scalar Un0,
+            const scalar dt,
+            const scalar phi,
+            const scalar magSf
+        );
+
+        //- Calculate time integrated flux for a face
+        scalar timeIntegratedFaceFlux
+        (
+            const label faceI,
+            const scalarField& times,
+            const scalar Un0,
+            const scalar dt,
+            const scalar phi,
+            const scalar magSf
+        );
+
+        //- Calculate time integrated area for a face
+        scalar timeIntegratedArea
+        (
+            const label faceI,
+            const scalar dt,
+            const scalar magSf,
+            const scalar Un0
+        );
+
+        //- Calculate time integrated area for a face
+        scalar timeIntegratedArea
+        (
+            const pointField& fPts,
+            const scalarField& pTimes,
+            const scalar dt,
+            const scalar magSf,
+            const scalar Un0
+        );
+
+        //- For face with vertices p calculate its area and integrated area
+        //  between isocutting lines with isovalues f0 and f1 given vertex
+        //  values f
+        void quadAreaCoeffs
+        (
+            const DynamicPointList& pf0,
+            const DynamicPointList& pf1,
+            scalar& quadArea,
+            scalar& intQuadArea
+        ) const;
+
+        //- Get cutPoints of face
+        void cutPoints
+        (
+            const label faceI,
+            const scalar f0,
+            DynamicList<point>& cutPoints
+        );
+
+        //- Get cutPoints of face
+        void cutPoints
+        (
+            const pointField& pts,
+            const scalarField& f,
+            const scalar f0,
+            DynamicList<point>& cutPoints
+        );
+
+        //- Returns centre of cutted face
+        const point& subFaceCentre() const;
+
+        //- Returns area vector of cutted face
+        const vector& subFaceArea() const;
+
+        //- Returns the cut edge of the cutted face
+        const DynamicList<point>& subFacePoints() const;
+
+        //- Returns point of the cutted face in sorted order
+        const DynamicList<point>& surfacePoints() const;
+
+        //- Resets internal variables
+        void clearStorage();
+};
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceIso.C b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceIso.C
new file mode 100644
index 0000000000000000000000000000000000000000..778109da11e05b71e9e634cdde5c5b3e0d4a6634
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceIso.C
@@ -0,0 +1,150 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutFaceIso.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutFaceIso::cutFaceIso(const fvMesh& mesh, scalarField& f)
+:
+    cutFace(mesh),
+    mesh_(mesh),
+    f_(f),
+    subFaceCentre_(Zero),
+    subFaceArea_(Zero),
+    subFacePoints_(10),
+    surfacePoints_(4),
+    pointStatus_(10),
+    weight_(10),
+    faceStatus_(-1)
+{
+    clearStorage();
+}
+
+
+// * * * * * * * * * * * Public Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::cutFaceIso::calcSubFace
+(
+    const label faceI,
+    const scalar cutValue
+)
+{
+    clearStorage();
+    const face& f = mesh_.faces()[faceI];
+    label inLiquid = 0;
+    label firstFullySubmergedPoint = -1;
+
+    // loop over face
+    forAll(f, i)
+    {
+        // pointStatus is f - cutValue
+        pointStatus_.append(f_[f[i]] - cutValue);
+        if (mag(pointStatus_[i]) < 10 * SMALL)
+        {
+            pointStatus_[i] = 0;
+        }
+        if (pointStatus_[i] > 10 * SMALL)
+        {
+            inLiquid++;
+            if (firstFullySubmergedPoint == -1)
+            {
+                firstFullySubmergedPoint = i;
+            }
+        }
+    }
+
+    if (inLiquid == f.size()) // fluid face
+    {
+        faceStatus_ = -1;
+        subFaceCentre_ = mesh_.faceCentres()[faceI];
+        subFaceArea_ = mesh_.faceAreas()[faceI];
+        return faceStatus_;
+    }
+    else if (inLiquid == 0) // gas face
+    {
+        faceStatus_ = 1;
+        subFaceCentre_ = Zero;
+        subFaceArea_ = Zero;
+        return faceStatus_;
+    }
+
+    cutFace::calcSubFace
+    (
+        faceI,
+        pointStatus_,
+        firstFullySubmergedPoint,
+        subFacePoints_,
+        surfacePoints_,
+        faceStatus_,
+        subFaceCentre_,
+        subFaceArea_
+    );
+
+    return faceStatus_;
+}
+
+
+const Foam::point& Foam::cutFaceIso::subFaceCentre() const
+{
+    return subFaceCentre_;
+}
+
+
+const Foam::vector& Foam::cutFaceIso::subFaceArea() const
+{
+    return subFaceArea_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutFaceIso::subFacePoints() const
+{
+    return subFacePoints_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutFaceIso::surfacePoints() const
+{
+    return surfacePoints_;
+}
+
+
+void Foam::cutFaceIso::clearStorage()
+{
+    subFaceCentre_ = Zero;
+    subFaceArea_ = Zero;
+    subFacePoints_.clear();
+    surfacePoints_.clear();
+    pointStatus_.clear();
+    weight_.clear();
+    faceStatus_ = -1;
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceIso.H b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceIso.H
new file mode 100644
index 0000000000000000000000000000000000000000..8051dc80d8daaeef9789c4ad309af22599d2235b
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFaceIso.H
@@ -0,0 +1,151 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::cutFaceIso
+
+Description
+    Class for cutting a face, faceI, of an fvMesh, mesh_, at its intersection
+    with an isosurface defined by the mesh point values f_ and the isovalue,
+    cutValue.
+
+    Reference:
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+
+    \endverbatim
+
+    Original code supplied by Johan Roenby, DHI (2016)
+
+SourceFiles
+    cutFaceIso.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cutFaceIso_H
+#define cutFaceIso_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+#include "cutFace.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                         Class cutFaceIso Declaration
+\*---------------------------------------------------------------------------*/
+
+class cutFaceIso
+:
+    public cutFace
+{
+    // Private Data
+
+        //- Mesh whose cells and faces to cut at their intersection with an
+        //- isoface
+        const fvMesh& mesh_;
+
+        //- Isofunction values at mesh points. f_size() = mesh_.nPoints().
+        scalarField& f_;
+
+        //- Storage for centre of subface
+        point subFaceCentre_;
+
+        //- Storage for area vector of subface
+        vector subFaceArea_;
+
+        //- Storage for subFacePoints
+        DynamicList<point> subFacePoints_;
+
+        //- Storage for subFacePoints
+        DynamicList<point> surfacePoints_;
+
+        //- Storage for pointStatus_ cuts the cell at 0
+        DynamicList<scalar> pointStatus_;
+
+        //- Storage of the edge weight
+        DynamicList<scalar> weight_;
+
+        //- A face status label taking one of the values:
+        //
+        //   -1: face is fully below the isosurface
+        //    0: face is cut, i.e. has values larger and smaller than isoValue_
+        //   +1: face is fully above the isosurface
+        label faceStatus_;
+
+
+public:
+
+    // Constructors
+
+        //- Construct from fvMesh and a scalarField
+        //  length of scalarField should equal number of mesh points
+        cutFaceIso(const fvMesh& mesh, scalarField& f);
+
+
+    // Member Functions
+
+        //- Calculate cut points along edges of faceI
+        label calcSubFace
+        (
+            const label faceI,
+            const scalar cutValue
+        );
+
+        //- Returns centre of cutted face
+        const point& subFaceCentre() const;
+
+        //- Returns area vector of cutted face
+        const vector& subFaceArea() const;
+
+        //- Returns the cut edge of the cutted face
+        const DynamicList<point>& subFacePoints() const;
+
+        //- Returns point of the face in sorted of cutted face
+        const DynamicList<point>& surfacePoints() const;
+
+        //- Resets internal variables
+        void clearStorage();
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFacePLIC.C b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFacePLIC.C
new file mode 100644
index 0000000000000000000000000000000000000000..446b026e61280a40d1bed96ce31dde3797eb2e04
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFacePLIC.C
@@ -0,0 +1,154 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "cutFacePLIC.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::cutFacePLIC::cutFacePLIC(const fvMesh& mesh)
+:
+    cutFace(mesh),
+    mesh_(mesh),
+    subFaceCentre_(Zero),
+    subFaceArea_(Zero),
+    subFacePoints_(10),
+    surfacePoints_(4),
+    pointStatus_(10),
+    weight_(10),
+    faceStatus_(-1)
+{
+    clearStorage();
+}
+
+
+// * * * * * * * * * * * Public Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::cutFacePLIC::calcSubFace
+(
+    const label faceI,
+    const vector& normal,
+    const vector& base
+ )
+{
+    clearStorage();
+
+    const face& f = mesh_.faces()[faceI];
+    label inLiquid = 0;
+    label firstFullySubmergedPoint = -1;
+
+    // loop face
+    forAll(f, i)
+    {
+        // pointStatus is the distance to the plane
+        scalar value = (mesh_.points()[f[i]] - base) & normal;
+        if (mag(value) < SMALL)
+        {
+            value = 0;
+        }
+
+        pointStatus_.append(value);
+        if (pointStatus_[i] > 0)
+        {
+            inLiquid++;
+            if (firstFullySubmergedPoint == -1)
+            {
+                firstFullySubmergedPoint = i;
+            }
+        }
+    }
+
+    if (inLiquid == f.size()) // fluid face
+    {
+        faceStatus_ = -1;
+        subFaceCentre_ = mesh_.faceCentres()[faceI];
+        subFaceArea_ = mesh_.faceAreas()[faceI];
+        return faceStatus_;
+    }
+    else if (inLiquid == 0) // gas face
+    {
+        faceStatus_ = 1;
+        subFaceCentre_ = Zero;
+        subFaceArea_ = Zero;
+        return faceStatus_;
+    }
+
+
+    cutFace::calcSubFace
+    (
+        faceI,
+        pointStatus_,
+        firstFullySubmergedPoint,
+        subFacePoints_,
+        surfacePoints_,
+        faceStatus_,
+        subFaceCentre_,
+        subFaceArea_
+    );
+
+    return faceStatus_;
+}
+
+
+const Foam::point& Foam::cutFacePLIC::subFaceCentre() const
+{
+    return subFaceCentre_;
+}
+
+
+const Foam::vector& Foam::cutFacePLIC::subFaceArea() const
+{
+    return subFaceArea_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutFacePLIC::subFacePoints() const
+{
+    return subFacePoints_;
+}
+
+
+const Foam::DynamicList<Foam::point>& Foam::cutFacePLIC::surfacePoints() const
+{
+    return surfacePoints_;
+}
+
+
+void Foam::cutFacePLIC::clearStorage()
+{
+    subFaceCentre_ = Zero;
+    subFaceArea_ = Zero;
+    subFacePoints_.clear();
+    surfacePoints_.clear();
+    pointStatus_.clear();
+    weight_.clear();
+    faceStatus_ = -1;
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/cellCuts/cutFace/cutFacePLIC.H b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFacePLIC.H
new file mode 100644
index 0000000000000000000000000000000000000000..75b76a44d8ee0a8b761c1cc19d352fac5d4a45d7
--- /dev/null
+++ b/src/transportModels/geometricVoF/cellCuts/cutFace/cutFacePLIC.H
@@ -0,0 +1,150 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2016-2017 DHI
+    Copyright (C) 2018-2019 Johan Roenby
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::cutFacePLIC
+
+Description
+    Class for cutting a face, faceI, of an fvMesh, mesh_, at its intersection
+    with an plane defined by normal and a base point
+
+    Reference:
+    \verbatim
+
+        Henning Scheufler, Johan Roenby,
+        Accurate and efficient surface reconstruction from volume
+        fraction data on general meshes,
+        Journal of Computational Physics, 2019,
+        doi 10.1016/j.jcp.2019.01.009
+
+    \endverbatim
+
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    cutFacePLIC.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef cutFacePLIC_H
+#define cutFacePLIC_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+#include "cutFace.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class cutFacePLIC Declaration
+\*---------------------------------------------------------------------------*/
+
+class cutFacePLIC
+:
+    public cutFace
+{
+    // Private Data
+
+        //- Mesh whose cells and faces to cut at their intersection
+        //- with an isoface
+        const fvMesh& mesh_;
+
+        //- Storage for centre of subface
+        point subFaceCentre_;
+
+        //- Storage for area vector of subface
+        vector subFaceArea_;
+
+        //- Storage for subFacePoints
+        DynamicList<point> subFacePoints_;
+
+        //- Storage for subFacePoints
+        DynamicList<point> surfacePoints_;
+
+        //- Storage for pointStatus_ cuts the cell at 0
+        DynamicList<scalar> pointStatus_;
+
+        //- Storage of the edge weight
+        DynamicList<scalar> weight_;
+
+        //- A face status label taking one of the values:
+        //
+        //   -1: face is fully below the PLICsurface
+        //    0: face is cut (has values larger and smaller than cutValue_)
+        //   +1: face is fully above the PLICsurface
+        label faceStatus_;
+
+
+public:
+
+    // Constructors
+
+        //- Construct from fvMesh and a scalarField
+        explicit cutFacePLIC(const fvMesh& mesh);
+
+
+    // Member Functions
+
+        //- Calculate cut points along edges of faceI
+        label calcSubFace
+        (
+            const label faceI,
+            const vector& normal,
+            const vector& base
+        );
+
+        //- Returns centre of cutted face
+        const point& subFaceCentre() const;
+
+        //- Returns area vector of cutted face
+        const vector& subFaceArea() const;
+
+        //- Returns the cut edge of the cutted face
+        const DynamicList<point>& subFacePoints() const;
+
+        //- Returns point of the face in sorted of cutted face
+        const DynamicList<point>& surfacePoints() const;
+
+        //- Resets internal variables
+        void clearStorage();
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructedDistanceFunction/reconstructedDistanceFunction.C b/src/transportModels/geometricVoF/reconstructedDistanceFunction/reconstructedDistanceFunction.C
new file mode 100644
index 0000000000000000000000000000000000000000..7aba9c546de0ae1faf672ba56ea6a23f3270344c
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructedDistanceFunction/reconstructedDistanceFunction.C
@@ -0,0 +1,427 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "emptyPolyPatch.H"
+#include "reconstructedDistanceFunction.H"
+#include "processorPolyPatch.H"
+#include "syncTools.H"
+#include "unitConversion.H"
+#include "wedgePolyPatch.H"
+#include "alphaContactAngleTwoPhaseFvPatchScalarField.H"
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::autoPtr<Foam::indirectPrimitivePatch>
+Foam::reconstructedDistanceFunction::coupledFacesPatch() const
+{
+    const polyBoundaryMesh& patches = mesh_.boundaryMesh();
+
+    label nCoupled = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (isA<coupledPolyPatch>(pp))
+        {
+            nCoupled += pp.size();
+        }
+    }
+    labelList nCoupledFaces(nCoupled);
+    nCoupled = 0;
+
+    for (const polyPatch& pp : patches)
+    {
+        if (isA<coupledPolyPatch>(pp))
+        {
+            label facei = pp.start();
+
+            forAll(pp, i)
+            {
+                nCoupledFaces[nCoupled++] = facei++;
+            }
+        }
+    }
+
+    return autoPtr<indirectPrimitivePatch>::New
+    (
+        IndirectList<face>
+        (
+            mesh_.faces(),
+            nCoupledFaces
+        ),
+        mesh_.points()
+    );
+}
+
+
+void Foam::reconstructedDistanceFunction::markCellsNearSurf
+(
+    const boolList& interfaceCells,
+    const label neiRingLevel
+)
+{
+    // performance might be improved by increasing the saving last iterations
+    // cells in a Map and loop over the map
+    if (mesh_.topoChanging())
+    {
+        // Introduced resizing to cope with changing meshes
+        if (nextToInterface_.size() != mesh_.nCells())
+        {
+            nextToInterface_.resize(mesh_.nCells());
+        }
+        coupledBoundaryPoints_ = coupledFacesPatch()().meshPoints();
+    }
+
+    const labelListList& pCells = mesh_.cellPoints();
+    const labelListList& cPoints = mesh_.pointCells();
+
+    boolList alreadyMarkedPoint(mesh_.nPoints(), false);
+    nextToInterface_ = false;
+
+    // do coupled face first
+    Map<bool> syncMap;
+
+    for (int level=0;level<=neiRingLevel;level++)
+    {
+        // parallel
+        if (level > 0)
+        {
+            forAll(coupledBoundaryPoints_, i)
+            {
+                const label pi = coupledBoundaryPoints_[i];
+                forAll(mesh_.pointCells()[pi], j)
+                {
+                    const label celli = cPoints[pi][j];
+                    if (cellDistLevel_[celli] == level-1)
+                    {
+                        syncMap.insert(pi, true);
+                        break;
+                    }
+                }
+            }
+
+            syncTools::syncPointMap(mesh_, syncMap, orEqOp<bool>());
+
+            // mark parallel points first
+            forAllConstIters(syncMap, iter)
+            {
+                const label pi = iter.key();
+
+                if (!alreadyMarkedPoint[pi])
+                {
+                    // loop over all cells attached to the point
+                    forAll(cPoints[pi], j)
+                    {
+                        const label pCelli = cPoints[pi][j];
+                        if (cellDistLevel_[pCelli] == -1)
+                        {
+                            cellDistLevel_[pCelli] = level;
+                            nextToInterface_[pCelli] = true;
+                        }
+                    }
+                }
+                alreadyMarkedPoint[pi] = true;
+            }
+        }
+
+
+        forAll(cellDistLevel_, celli)
+        {
+            if (level == 0)
+            {
+                if (interfaceCells[celli])
+                {
+                    cellDistLevel_[celli] = 0;
+                    nextToInterface_[celli] = true;
+                }
+                else
+                {
+                    cellDistLevel_[celli] = -1;
+                }
+            }
+            else
+            {
+                if (cellDistLevel_[celli] == level-1)
+                {
+                    forAll(pCells[celli], i)
+                    {
+                        const label pI = pCells[celli][i];
+
+                        if (!alreadyMarkedPoint[pI])
+                        {
+                            forAll(cPoints[pI], j)
+                            {
+                                const label pCelli = cPoints[pI][j];
+                                if (cellDistLevel_[pCelli] == -1)
+                                {
+                                    cellDistLevel_[pCelli] = level;
+                                    nextToInterface_[pCelli] = true;
+                                }
+                            }
+                        }
+                        alreadyMarkedPoint[pI] = true;
+                    }
+                }
+            }
+        }
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::reconstructedDistanceFunction::reconstructedDistanceFunction
+(
+    const fvMesh& mesh
+)
+:
+    volScalarField
+    (
+        IOobject
+        (
+            "RDF",
+            mesh.time().timeName(),
+            mesh,
+            IOobject::NO_READ,
+            IOobject::AUTO_WRITE
+        ),
+        mesh,
+        dimensionedScalar(dimLength, Zero)
+    ),
+    mesh_(mesh),
+    coupledBoundaryPoints_(coupledFacesPatch()().meshPoints()),
+    cellDistLevel_
+    (
+        IOobject
+        (
+            "cellDistLevel",
+            mesh.time().timeName(),
+            mesh,
+            IOobject::NO_READ,
+            IOobject::NO_WRITE
+        ),
+        mesh,
+        dimensionedScalar("cellDistLevel", dimless, -1)
+    ),
+    nextToInterface_(mesh.nCells(), false)
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+const Foam::volScalarField&  Foam::reconstructedDistanceFunction::constructRDF
+(
+    const boolList& nextToInterface,
+    const volVectorField& centre,
+    const volVectorField& normal,
+    zoneDistribute& distribute,
+    bool updateStencil
+)
+{
+    volScalarField& reconDistFunc = *this;
+
+    if (nextToInterface.size() != centre.size())
+    {
+        FatalErrorInFunction
+            << "size of nextToInterface: " << nextToInterface.size()
+            << "size of centre:" <<  centre.size()
+            << "do not match. Did the mesh change?"
+            << exit(FatalError);
+        return reconDistFunc;
+    }
+
+
+    distribute.setUpCommforZone(nextToInterface, updateStencil);
+
+    Map<vector> mapCentres =
+        distribute.getDatafromOtherProc(nextToInterface, centre);
+    Map<vector> mapNormal =
+        distribute.getDatafromOtherProc(nextToInterface, normal);
+
+    const labelListList& stencil = distribute.getStencil();
+
+
+    forAll(nextToInterface,celli)
+    {
+        if (nextToInterface[celli])
+        {
+            if (mag(normal[celli]) != 0) // interface cell
+            {
+                vector n = -normal[celli]/mag(normal[celli]);
+                scalar dist = (centre[celli] - mesh_.C()[celli]) & n;
+                reconDistFunc[celli] = dist;
+            }
+            else // nextToInterfaceCell or level == 1 cell
+            {
+                scalar averageDist = 0;
+                scalar avgWeight = 0;
+                const point p = mesh_.C()[celli];
+
+                forAll (stencil[celli],i)
+                {
+                    const label gblIdx = stencil[celli][i];
+                    vector n = -distribute.getValue(normal, mapNormal, gblIdx);
+                    if (mag(n) != 0)
+                    {
+                        n /= mag(n);
+                        vector c = distribute.getValue(centre,mapCentres,gblIdx);
+                        vector distanceToIntSeg = (c - p);
+                        scalar distToSurf = distanceToIntSeg & (n);
+                        scalar weight = 0;
+
+                        if (mag(distanceToIntSeg) != 0)
+                        {
+                            distanceToIntSeg /= mag(distanceToIntSeg);
+                            weight = sqr(mag(distanceToIntSeg & n));
+                        }
+                        else // exactly on the center
+                        {
+                            weight = 1;
+                        }
+                        averageDist += distToSurf * weight;
+                        avgWeight += weight;
+                    }
+                }
+
+                if (avgWeight != 0)
+                {
+                    reconDistFunc[celli] = averageDist / avgWeight;
+                }
+            }
+        }
+        else
+        {
+            reconDistFunc[celli] = 0;
+        }
+    }
+
+    forAll(reconDistFunc.boundaryField(), patchI)
+    {
+        fvPatchScalarField& pRDF = reconDistFunc.boundaryFieldRef()[patchI];
+        if (isA<calculatedFvPatchScalarField>(pRDF))
+        {
+            const polyPatch& pp = pRDF.patch().patch();
+            forAll(pRDF, i)
+            {
+                const label pCellI = pp.faceCells()[i];
+
+                if (nextToInterface_[pCellI])
+                {
+                    scalar averageDist = 0;
+                    scalar avgWeight = 0;
+                    const point p = mesh_.C().boundaryField()[patchI][i];
+
+                    forAll (stencil[pCellI], j)
+                    {
+                        const label gblIdx = stencil[pCellI][j];
+                        vector n = -distribute.getValue(normal, mapNormal, gblIdx);
+                        if (mag(n) != 0)
+                        {
+                            n /= mag(n);
+                            vector c =
+                                distribute.getValue(centre, mapCentres, gblIdx);
+                            vector distanceToIntSeg = (c - p);
+                            scalar distToSurf = distanceToIntSeg & (n);
+                            scalar weight = 0;
+
+                            if (mag(distanceToIntSeg) != 0)
+                            {
+                                distanceToIntSeg /= mag(distanceToIntSeg);
+                                weight = sqr(mag(distanceToIntSeg & n));
+                            }
+                            else // exactly on the center
+                            {
+                                weight = 1;
+                            }
+                            averageDist += distToSurf * weight;
+                            avgWeight += weight;
+                        }
+                    }
+
+                    if (avgWeight != 0)
+                    {
+                        pRDF[i] = averageDist / avgWeight;
+                    }
+                    else
+                    {
+                        pRDF[i] = 0;
+                    }
+                }
+                else
+                {
+                    pRDF[i] = 0;
+                }
+            }
+        }
+    }
+
+    reconDistFunc.correctBoundaryConditions();
+
+    return reconDistFunc;
+}
+
+
+void Foam::reconstructedDistanceFunction::updateContactAngle
+(
+    const volScalarField& alpha,
+    const volVectorField& U,
+    surfaceVectorField::Boundary& nHatb
+)
+{
+    const fvMesh& mesh = alpha.mesh();
+    const volScalarField::Boundary& abf = alpha.boundaryField();
+    volScalarField::Boundary& RDFbf = this->boundaryFieldRef();
+
+    const fvBoundaryMesh& boundary = mesh.boundary();
+
+    forAll(boundary, patchi)
+    {
+        if (isA<alphaContactAngleTwoPhaseFvPatchScalarField>(abf[patchi]))
+        {
+            alphaContactAngleTwoPhaseFvPatchScalarField& acap =
+                const_cast<alphaContactAngleTwoPhaseFvPatchScalarField&>
+                (
+                    refCast<const alphaContactAngleTwoPhaseFvPatchScalarField>
+                    (
+                        abf[patchi]
+                    )
+                );
+
+            fvsPatchVectorField& nHatp = nHatb[patchi];
+            const scalarField theta
+            (
+                degToRad()*acap.theta(U.boundaryField()[patchi], nHatp)
+            );
+
+            RDFbf[patchi] =
+                1/acap.patch().deltaCoeffs()*cos(theta)
+              + RDFbf[patchi].patchInternalField();
+        }
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructedDistanceFunction/reconstructedDistanceFunction.H b/src/transportModels/geometricVoF/reconstructedDistanceFunction/reconstructedDistanceFunction.H
new file mode 100644
index 0000000000000000000000000000000000000000..278087e6d15f8444b177644ed56e7afa49c41117
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructedDistanceFunction/reconstructedDistanceFunction.H
@@ -0,0 +1,131 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::reconstructedDistanceFunction
+
+Description
+    Calculates a reconstructed distance function
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    reconstructedDistanceFunction.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef reconstructedDistanceFunction_H
+#define reconstructedDistanceFunction_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+#include "globalIndex.H"
+#include "Map.H"
+#include "zoneDistribute.H"
+#include "dimensionedScalar.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                Class reconstructedDistanceFunction Declaration
+\*---------------------------------------------------------------------------*/
+
+class reconstructedDistanceFunction
+:
+    public volScalarField
+{
+    // Private Data
+
+        //- Reference to mesh
+        const fvMesh& mesh_;
+
+        //- Stores the coupled boundary points which have to be synced
+        labelList coupledBoundaryPoints_;
+
+        //- Distance of the interface band to the interface
+        volScalarField cellDistLevel_;
+
+        //- Is the cell in the interface band?
+        boolList nextToInterface_;
+
+        //- Return patch of all coupled faces.
+        autoPtr<indirectPrimitivePatch> coupledFacesPatch() const;
+
+
+public:
+
+    //- Construct from fvMesh
+    explicit reconstructedDistanceFunction(const fvMesh& mesh);
+
+
+    // Member Functions
+
+        void markCellsNearSurf
+        (
+            const boolList& interfaceCells,
+            const label neiRingLevel
+        );
+
+        const volScalarField& constructRDF
+        (
+            const boolList& nextToInterface,
+            const volVectorField& centre,
+            const volVectorField& normal,
+            zoneDistribute& distribute,
+            bool updateStencil=true
+        );
+
+        void updateContactAngle
+        (
+            const volScalarField& alpha,
+            const volVectorField& U,
+            surfaceVectorField::Boundary& nHatb
+        );
+
+        const volScalarField& cellDistLevel() const
+        {
+            return cellDistLevel_;
+        }
+
+        const boolList& nextToInterface() const
+        {
+            return nextToInterface_;
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.C b/src/transportModels/geometricVoF/reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.C
new file mode 100644
index 0000000000000000000000000000000000000000..8dcd46b87dbd52010d20ed03949df83b7367c0b6
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.C
@@ -0,0 +1,150 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "isoAlpha.H"
+#include "addToRunTimeSelectionTable.H"
+#include "cutCellPLIC.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace reconstruction
+{
+    defineTypeNameAndDebug(isoAlpha, 0);
+    addToRunTimeSelectionTable(reconstructionSchemes,isoAlpha, components);
+}
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::reconstruction::isoAlpha::isoAlpha
+(
+    volScalarField& alpha1,
+    const surfaceScalarField& phi,
+    const volVectorField& U,
+    const dictionary& dict
+)
+:
+    reconstructionSchemes
+    (
+        typeName,
+        alpha1,
+        phi,
+        U,
+        dict
+    ),
+    mesh_(alpha1.mesh()),
+    // Interpolation data
+    ap_(mesh_.nPoints()),
+
+    // Tolerances and solution controls
+    isoFaceTol_(modelDict().getOrDefault<scalar>("isoFaceTol", 1e-8)),
+    surfCellTol_(modelDict().getOrDefault<scalar>("surfCellTol", 1e-8)),
+    sIterIso_(mesh_, ap_, surfCellTol_)
+{
+    reconstruct();
+}
+
+
+// * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * * //
+
+void Foam::reconstruction::isoAlpha::reconstruct(bool forceUpdate)
+{
+    const bool uptodate = alreadyReconstructed(forceUpdate);
+
+    if (uptodate && !forceUpdate)
+    {
+        return;
+    }
+
+    // Interpolating alpha1 cell centre values to mesh points (vertices)
+    if (mesh_.topoChanging())
+    {
+        // Introduced resizing to cope with changing meshes
+        if (ap_.size() != mesh_.nPoints())
+        {
+            ap_.resize(mesh_.nPoints());
+
+        }
+        if (interfaceCell_.size() != mesh_.nCells())
+        {
+            interfaceCell_.resize(mesh_.nCells());
+        }
+    }
+    ap_ = volPointInterpolation::New(mesh_).interpolate(alpha1_);
+
+    DynamicList<List<point>> facePts;
+
+    interfaceLabels_.clear();
+
+    forAll(alpha1_,cellI)
+    {
+        if (sIterIso_.isASurfaceCell(alpha1_[cellI]))
+        {
+            interfaceLabels_.append(cellI);
+
+            sIterIso_.vofCutCell
+            (
+                cellI,
+                alpha1_[cellI],
+                isoFaceTol_,
+                100
+            );
+
+            if (sIterIso_.cellStatus() == 0)
+            {
+                normal_[cellI] = sIterIso_.surfaceArea();
+                centre_[cellI] = sIterIso_.surfaceCentre();
+                if (mag(normal_[cellI]) != 0)
+                {
+                    interfaceCell_[cellI] = true;
+                }
+                else
+                {
+                    interfaceCell_[cellI] = false;
+                }
+            }
+            else
+            {
+                normal_[cellI] = Zero;
+                centre_[cellI] = Zero;
+                interfaceCell_[cellI] = false;
+            }
+         }
+         else
+         {
+            normal_[cellI] = Zero;
+            centre_[cellI] = Zero;
+            interfaceCell_[cellI] = false;
+         }
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.H b/src/transportModels/geometricVoF/reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.H
new file mode 100644
index 0000000000000000000000000000000000000000..b5f436e200e48778d768fa90e612d2336be59d16
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/isoSchemes/isoAlpha/isoAlpha.H
@@ -0,0 +1,150 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::reconstruction::isoAlpha
+
+Description
+    Reconstructs an interface (centre and normal vectors) consisting of isosurfaces
+    to match the internal fluid distribution in cells. The point values (ap_)
+    are estimated by inverse distance interpolation of the VoF (alpha) field.
+
+    Reference:
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+    \endverbatim
+
+    Original code supplied by Johan Roenby, DHI (2016)
+
+Author
+    Johan Roenby, DHI, all rights reserved.
+    Modified Henning Scheufler, DLR
+
+SourceFiles
+    isoAlpha.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef isoAlpha_H
+#define isoAlpha_H
+
+#include "autoPtr.H"
+#include "dimensionedScalar.H"
+#include "reconstructionSchemes.H"
+#include "typeInfo.H"
+#include "volFields.H"
+
+#include "surfaceIteratorIso.H"
+#include "volPointInterpolation.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace reconstruction
+{
+
+/*---------------------------------------------------------------------------*\
+                          Class isoAlpha Declaration
+\*---------------------------------------------------------------------------*/
+
+class isoAlpha
+:
+    public reconstructionSchemes
+{
+    // Private Data
+
+        //- Reference to mesh
+        const fvMesh& mesh_;
+
+        //- VOF field interpolated to mesh points
+        scalarField ap_;
+
+        // Switches and tolerances. Tolerances need to go into toleranceSwitches
+
+        //- Tolerance for search of isoFace giving specified VOF value
+        scalar isoFaceTol_;
+
+        //- Tolerance for marking of surface cells:
+        //  Those with surfCellTol_ < alpha1 < 1 - surfCellTol_
+        scalar surfCellTol_;
+
+        //- surfaceIterator finds the isovalue for specified VOF value
+        surfaceIteratorIso sIterIso_;
+
+
+    // Private Member Functions
+
+        //- No copy construct
+        isoAlpha(const isoAlpha&) = delete;
+
+        //- No copy assignment
+        void operator=(const isoAlpha&) = delete;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("isoAlpha");
+
+    //- Construct from components
+    isoAlpha
+    (
+        volScalarField& alpha1,
+        const surfaceScalarField& phi,
+        const volVectorField& U,
+        const dictionary& dict
+    );
+
+
+    //- Destructor
+    virtual ~isoAlpha() = default;
+
+
+    // Member Functions
+
+        //- Reconstructs the interface
+        virtual void reconstruct(bool forceUpdate = true);
+
+        //- map VoF Field in case of refinement
+        virtual void mapAlphaField() const
+        {
+            // do nothing;
+        }
+};
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace reconstruction
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.C b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.C
new file mode 100644
index 0000000000000000000000000000000000000000..b65b323946b60e29c808934db412218e61960d53
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.C
@@ -0,0 +1,223 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "gradAlpha.H"
+#include "fvc.H"
+#include "leastSquareGrad.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace reconstruction
+{
+    defineTypeNameAndDebug(gradAlpha, 0);
+    addToRunTimeSelectionTable(reconstructionSchemes, gradAlpha, components);
+}
+}
+
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+void Foam::reconstruction::gradAlpha::gradSurf(const volScalarField& phi)
+{
+    leastSquareGrad<scalar> lsGrad("polyDegree1",mesh_.geometricD());
+
+    exchangeFields_.setUpCommforZone(interfaceCell_,true);
+
+    Map<vector> mapCC
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, mesh_.C())
+    );
+    Map<scalar> mapPhi
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, phi)
+    );
+
+    DynamicField<vector> cellCentre(100);
+    DynamicField<scalar> phiValues(100);
+
+    const labelListList& stencil = exchangeFields_.getStencil();
+
+    forAll(interfaceLabels_, i)
+    {
+        const label celli = interfaceLabels_[i];
+
+        cellCentre.clear();
+        phiValues.clear();
+
+        for (const label gblIdx : stencil[celli])
+        {
+            cellCentre.append
+            (
+                exchangeFields_.getValue(mesh_.C(), mapCC, gblIdx)
+            );
+            phiValues.append
+            (
+                exchangeFields_.getValue(phi, mapPhi, gblIdx)
+            );
+        }
+
+        cellCentre -= mesh_.C()[celli];
+        interfaceNormal_[i] = lsGrad.grad(cellCentre, phiValues);
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::reconstruction::gradAlpha::gradAlpha
+(
+    volScalarField& alpha1,
+    const surfaceScalarField& phi,
+    const volVectorField& U,
+    const dictionary& dict
+)
+:
+    reconstructionSchemes
+    (
+        typeName,
+        alpha1,
+        phi,
+        U,
+        dict
+    ),
+    mesh_(alpha1.mesh()),
+    interfaceNormal_(fvc::grad(alpha1)),
+    isoFaceTol_(modelDict().getOrDefault<scalar>("isoFaceTol", 1e-8)),
+    surfCellTol_(modelDict().getOrDefault<scalar>("surfCellTol", 1e-8)),
+    exchangeFields_(zoneDistribute::New(mesh_)),
+    sIterPLIC_(mesh_,surfCellTol_)
+{
+    reconstruct();
+}
+
+
+// * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * * //
+
+void Foam::reconstruction::gradAlpha::reconstruct(bool forceUpdate)
+{
+    const bool uptodate = alreadyReconstructed(forceUpdate);
+
+    if (uptodate && !forceUpdate)
+    {
+        return;
+    }
+
+    if (mesh_.topoChanging())
+    {
+        // Introduced resizing to cope with changing meshes
+        if (interfaceCell_.size() != mesh_.nCells())
+        {
+            interfaceCell_.resize(mesh_.nCells());
+        }
+    }
+    interfaceCell_ = false;
+
+    interfaceLabels_.clear();
+
+    forAll(alpha1_, celli)
+    {
+        if (sIterPLIC_.isASurfaceCell(alpha1_[celli]))
+        {
+            interfaceCell_[celli] = true; // is set to false earlier
+            interfaceLabels_.append(celli);
+        }
+    }
+    interfaceNormal_.resize(interfaceLabels_.size());
+    centre_ = dimensionedVector("centre", dimLength, Zero);
+    normal_ = dimensionedVector("normal", dimArea, Zero);
+
+    gradSurf(alpha1_);
+
+    forAll(interfaceLabels_, i)
+    {
+        const label celli = interfaceLabels_[i];
+        if (mag(interfaceNormal_[i]) == 0)
+        {
+            continue;
+        }
+
+        sIterPLIC_.vofCutCell
+        (
+            celli,
+            alpha1_[celli],
+            isoFaceTol_,
+            100,
+            interfaceNormal_[i]
+        );
+
+        if (sIterPLIC_.cellStatus() == 0)
+        {
+            normal_[celli] = sIterPLIC_.surfaceArea();
+            centre_[celli] = sIterPLIC_.surfaceCentre();
+            if (mag(normal_[celli]) == 0)
+            {
+                normal_[celli] = Zero;
+                centre_[celli] = Zero;
+            }
+        }
+        else
+        {
+            normal_[celli] = Zero;
+            centre_[celli] = Zero;
+        }
+    }
+}
+
+
+void Foam::reconstruction::gradAlpha::mapAlphaField() const
+{
+    // Without this line, we seem to get a race condition
+    mesh_.C();
+
+    cutCellPLIC cutCell(mesh_);
+
+    forAll(normal_, celli)
+    {
+        if (mag(normal_[celli]) != 0)
+        {
+            vector n = normal_[celli]/mag(normal_[celli]);
+            scalar cutValue = (centre_[celli] - mesh_.C()[celli]) & (n);
+            cutCell.calcSubCell
+            (
+                celli,
+                cutValue,
+                n
+            );
+            alpha1_[celli] = cutCell.VolumeOfFluid();
+        }
+    }
+
+    alpha1_.correctBoundaryConditions();
+    alpha1_.oldTime () = alpha1_;
+    alpha1_.oldTime().correctBoundaryConditions();
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.H b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.H
new file mode 100644
index 0000000000000000000000000000000000000000..4933ddd005c929f801a7353e997baa601ecbbb43
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/gradAlpha/gradAlpha.H
@@ -0,0 +1,142 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::reconstruction::gradAlpha
+
+Description
+    Reconstructs an interface (centre and normal vector) consisting of planes
+    to match the internal fluid distribution in cells. The interface normals
+    are estimated by least square gradient scheme on the VoF Field (alpha).
+    Also known as Young method
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    gradAlpha.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef gradAlpha_H
+#define gradAlpha_H
+
+#include "typeInfo.H"
+#include "reconstructionSchemes.H"
+#include "volFields.H"
+#include "dimensionedScalar.H"
+#include "autoPtr.H"
+#include "surfaceIteratorPLIC.H"
+#include "zoneDistribute.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace reconstruction
+{
+
+/*---------------------------------------------------------------------------*\
+                          Class gradAlpha Declaration
+\*---------------------------------------------------------------------------*/
+
+class gradAlpha
+:
+    public reconstructionSchemes
+{
+    // Private Data
+
+        //- Reference to mesh
+        const fvMesh& mesh_;
+
+        //- Interpolation object from cell centres to points
+        DynamicField<vector> interfaceNormal_;
+
+
+    // Switches and tolerances. Tolerances need to go into toleranceSwitches
+
+        //- Tolerance for search of isoFace giving specified VOF value
+        scalar isoFaceTol_;
+
+        //- Tolerance for marking of surface cells:
+        //  Those with surfCellTol_ < alpha1 < 1 - surfCellTol_
+        scalar surfCellTol_;
+
+        //- Provides stencil and map
+        zoneDistribute& exchangeFields_;
+
+        //- SurfaceIterator finds the plane centre for specified VOF value
+        surfaceIteratorPLIC sIterPLIC_;
+
+
+    // Private Member Functions
+
+        //- Compute gradient at the surfaces
+        void gradSurf(const volScalarField& phi);
+
+        //- No copy construct
+        gradAlpha(const gradAlpha&) = delete;
+
+        //- No copy assignment
+        void operator=(const gradAlpha&) = delete;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("gradAlpha");
+
+    //- Construct from components
+    gradAlpha
+    (
+        volScalarField& alpha1,
+        const surfaceScalarField& phi,
+        const volVectorField& U,
+        const dictionary& dict
+    );
+
+    //- Destructor
+    virtual ~gradAlpha() = default;
+
+
+    // Member Functions
+
+        //- Reconstruct interface
+        virtual void reconstruct(bool forceUpdate = true);
+
+        //- map VoF Field in case of refinement
+        virtual void mapAlphaField() const;
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace reconstruction
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/plicRDF/plicRDF.C b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/plicRDF/plicRDF.C
new file mode 100644
index 0000000000000000000000000000000000000000..7f30e66405e3add6ab2b802e4b1a251f49a3ca63
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/plicRDF/plicRDF.C
@@ -0,0 +1,570 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "plicRDF.H"
+#include "interpolationCellPoint.H"
+#include "fvc.H"
+#include "leastSquareGrad.H"
+#include "addToRunTimeSelectionTable.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace reconstruction
+{
+    defineTypeNameAndDebug(plicRDF, 0);
+    addToRunTimeSelectionTable(reconstructionSchemes,plicRDF, components);
+}
+}
+
+
+// * * * * * * * * * * * * * Private Member Functions  * * * * * * * * * * * //
+
+void Foam::reconstruction::plicRDF::interpolateNormal()
+{
+    scalar dt = mesh_.time().deltaTValue();
+
+    leastSquareGrad<scalar> lsGrad("polyDegree1",mesh_.geometricD());
+
+    exchangeFields_.setUpCommforZone(interfaceCell_,false);
+
+    Map<vector> mapCentre
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, centre_)
+    );
+    Map<vector> mapNormal
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, normal_)
+    );
+
+    Map<vector> mapCC
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, mesh_.C())
+    );
+    Map<scalar> mapAlpha
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, alpha1_)
+    );
+
+    DynamicField<vector > cellCentre(100);
+    DynamicField<scalar > alphaValues(100);
+
+    DynamicList<vector> foundNormals(30);
+
+    const labelListList& stencil = exchangeFields_.getStencil();
+
+    forAll(interfaceLabels_, i)
+    {
+        const label celli = interfaceLabels_[i];
+        vector estimatedNormal{Zero};
+        scalar weight{0};
+        foundNormals.clear();
+        forAll(stencil[celli], i)
+        {
+            const label gblIdx = stencil[celli][i];
+            vector n =
+                exchangeFields_.getValue(normal_, mapNormal, gblIdx);
+            point p = mesh_.C()[celli]-U_[celli]*dt;
+            if (mag(n) != 0)
+            {
+                n /= mag(n);
+                vector centre =
+                    exchangeFields_.getValue(centre_, mapCentre, gblIdx);
+                vector distanceToIntSeg = (tensor::I- n*n) & (p - centre);
+                estimatedNormal += n /max(mag(distanceToIntSeg), SMALL);
+                weight += 1/max(mag(distanceToIntSeg), SMALL);
+                foundNormals.append(n);
+            }
+        }
+
+        if (weight != 0 && mag(estimatedNormal) != 0)
+        {
+            estimatedNormal /= weight;
+            estimatedNormal /= mag(estimatedNormal);
+        }
+
+        bool tooCoarse = false;
+
+        if (foundNormals.size() > 1 && mag(estimatedNormal) != 0)
+        {
+            forAll(foundNormals, i)
+            {
+                // all have the length of 1
+                // to coarse if normal angle is bigger than 10 deg
+                if ((estimatedNormal & foundNormals[i]) <= 0.98)
+                {
+                    tooCoarse = true;
+                }
+            }
+        }
+        else
+        {
+            tooCoarse = true;
+        }
+
+        // if a normal was found and the interface is fine enough
+        // smallDist is always smallDist
+        if (mag(estimatedNormal) != 0 && !tooCoarse)
+        {
+            interfaceNormal_[i] = estimatedNormal;
+        }
+        else
+        {
+            cellCentre.clear();
+            alphaValues.clear();
+
+            forAll(stencil[celli],i)
+            {
+                const label gblIdx = stencil[celli][i];
+                cellCentre.append
+                (
+                    exchangeFields_.getValue(mesh_.C(), mapCC, gblIdx)
+                );
+                alphaValues.append
+                (
+                    exchangeFields_.getValue(alpha1_, mapAlpha, gblIdx)
+                );
+            }
+            cellCentre -= mesh_.C()[celli];
+            interfaceNormal_[i] = lsGrad.grad(cellCentre, alphaValues);
+        }
+
+    }
+}
+
+void Foam::reconstruction::plicRDF::gradSurf(const volScalarField& phi)
+{
+    leastSquareGrad<scalar> lsGrad("polyDegree1", mesh_.geometricD());
+
+    exchangeFields_.setUpCommforZone(interfaceCell_, false);
+
+    Map<vector> mapCC
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, mesh_.C())
+    );
+    Map<scalar> mapPhi
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, phi)
+    );
+
+    DynamicField<vector> cellCentre(100);
+    DynamicField<scalar> phiValues(100);
+
+    const labelListList& stencil = exchangeFields_.getStencil();
+
+    forAll(interfaceLabels_, i)
+    {
+        const label celli = interfaceLabels_[i];
+
+        cellCentre.clear();
+        phiValues.clear();
+
+        for (const label gblIdx : stencil[celli])
+        {
+            cellCentre.append
+            (
+                exchangeFields_.getValue(mesh_.C(), mapCC, gblIdx)
+            );
+            phiValues.append
+            (
+                exchangeFields_.getValue(phi, mapPhi, gblIdx)
+            );
+        }
+
+        cellCentre -= mesh_.C()[celli];
+        interfaceNormal_[i] = lsGrad.grad(cellCentre, phiValues);
+    }
+}
+
+
+void Foam::reconstruction::plicRDF::setInitNormals(bool interpolate)
+{
+    interfaceLabels_.clear();
+
+    forAll(alpha1_, celli)
+    {
+        if (sIterPLIC_.isASurfaceCell(alpha1_[celli]))
+        {
+            interfaceCell_[celli] = true; // is set to false earlier
+            interfaceLabels_.append(celli);
+        }
+    }
+    interfaceNormal_.setSize(interfaceLabels_.size());
+
+    RDF_.markCellsNearSurf(interfaceCell_, 1);
+    const boolList& nextToInterface_ = RDF_.nextToInterface();
+    exchangeFields_.updateStencil(nextToInterface_);
+
+    if (interpolate)
+    {
+        interpolateNormal();
+    }
+    else
+    {
+        gradSurf(alpha1_);
+    }
+}
+
+
+void Foam::reconstruction::plicRDF::calcResidual
+(
+    Map<scalar>& normalResidual,
+    Map<scalar>& avgAngle
+)
+{
+    exchangeFields_.setUpCommforZone(interfaceCell_,false);
+
+    Map<vector> mapNormal
+    (
+        exchangeFields_.getDatafromOtherProc(interfaceCell_, normal_)
+    );
+
+    const labelListList& stencil = exchangeFields_.getStencil();
+
+    normalResidual.clear();
+
+    forAll(interfaceLabels_, i)
+    {
+        const label celli = interfaceLabels_[i];
+        if (mag(normal_[celli]) == 0 || mag(interfaceNormal_[i]) == 0)
+        {
+            continue;
+        }
+
+        scalar avgDiffNormal = 0;
+        scalar maxDiffNormal = GREAT;
+        scalar weight= 0;
+        const vector cellNormal = normal_[celli]/mag(normal_[celli]);
+
+        for (const label gblIdx : stencil[celli])
+        {
+            vector normal =
+                exchangeFields_.getValue(normal_, mapNormal, gblIdx);
+
+            if (mag(normal) != 0 && i != 0)
+            {
+                vector n = normal/mag(normal);
+                scalar cosAngle = max(min((cellNormal & n), 1), -1);
+                avgDiffNormal += acos(cosAngle) * mag(normal);
+                weight += mag(normal);
+                if (cosAngle < maxDiffNormal)
+                {
+                    maxDiffNormal = cosAngle;
+                }
+            }
+        }
+
+        if (weight != 0)
+        {
+            avgDiffNormal /= weight;
+        }
+        else
+        {
+            avgDiffNormal = 0;
+        }
+
+        vector newCellNormal = normalised(interfaceNormal_[i]);
+
+        scalar normalRes = (1 - (cellNormal & newCellNormal));
+        avgAngle.insert(celli, avgDiffNormal);
+        normalResidual.insert(celli, normalRes);
+    }
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::reconstruction::plicRDF::plicRDF
+(
+    volScalarField& alpha1,
+    const surfaceScalarField& phi,
+    const volVectorField& U,
+    const dictionary& dict
+)
+:
+    reconstructionSchemes
+    (
+        typeName,
+        alpha1,
+        phi,
+        U,
+        dict
+    ),
+    mesh_(alpha1.mesh()),
+
+    interfaceNormal_(0.2*mesh_.nCells()),
+
+    isoFaceTol_(modelDict().getOrDefault<scalar>("isoFaceTol", 1e-8)),
+    surfCellTol_(modelDict().getOrDefault<scalar>("surfCellTol", 1e-8)),
+    tol_(modelDict().getOrDefault<scalar>("tol", 1e-6)),
+    relTol_(modelDict().getOrDefault<scalar>("relTol", 0.1)),
+    iteration_(modelDict().getOrDefault<label>("iterations", 5)),
+    interpolateNormal_(modelDict().getOrDefault("interpolateNormal", true)),
+    RDF_(mesh_),
+    exchangeFields_(zoneDistribute::New(mesh_)),
+    sIterPLIC_(mesh_,surfCellTol_)
+{
+    setInitNormals(false);
+
+    centre_ = dimensionedVector("centre", dimLength, Zero);
+    normal_ = dimensionedVector("normal", dimArea, Zero);
+
+    forAll(interfaceLabels_, i)
+    {
+        const label celli = interfaceLabels_[i];
+        if (mag(interfaceNormal_[i]) == 0)
+        {
+            continue;
+        }
+        sIterPLIC_.vofCutCell
+        (
+            celli,
+            alpha1_[celli],
+            isoFaceTol_,
+            100,
+            interfaceNormal_[i]
+        );
+
+        if (sIterPLIC_.cellStatus() == 0)
+        {
+            normal_[celli] = sIterPLIC_.surfaceArea();
+            centre_[celli] = sIterPLIC_.surfaceCentre();
+            if (mag(normal_[celli]) == 0)
+            {
+                normal_[celli] = Zero;
+                centre_[celli] = Zero;
+            }
+        }
+        else
+        {
+            normal_[celli] = Zero;
+            centre_[celli] = Zero;
+        }
+    }
+}
+
+
+// * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * * //
+
+void Foam::reconstruction::plicRDF::reconstruct(bool forceUpdate)
+{
+    const bool uptodate = alreadyReconstructed(forceUpdate);
+
+    if (uptodate && !forceUpdate)
+    {
+        return;
+    }
+
+    if (mesh_.topoChanging())
+    {
+        // Introduced resizing to cope with changing meshes
+        if (interfaceCell_.size() != mesh_.nCells())
+        {
+            interfaceCell_.resize(mesh_.nCells());
+        }
+    }
+    interfaceCell_ = false;
+
+    // Sets interfaceCell_ and interfaceNormal
+    setInitNormals(interpolateNormal_);
+
+    centre_ = dimensionedVector("centre", dimLength, Zero);
+    normal_ = dimensionedVector("normal", dimArea, Zero);
+
+    // nextToInterface is update on setInitNormals
+    const boolList& nextToInterface_ = RDF_.nextToInterface();
+
+    labelHashSet tooCoarse;
+
+    for (int iter=0; iter<iteration_; ++iter)
+    {
+        forAll(interfaceLabels_, i)
+        {
+            const label celli = interfaceLabels_[i];
+            if (mag(interfaceNormal_[i]) == 0 || tooCoarse.found(celli))
+            {
+                continue;
+            }
+            sIterPLIC_.vofCutCell
+            (
+                celli,
+                alpha1_[celli],
+                isoFaceTol_,
+                100,
+                interfaceNormal_[i]
+            );
+
+            if (sIterPLIC_.cellStatus() == 0)
+            {
+
+                normal_[celli] = sIterPLIC_.surfaceArea();
+                centre_[celli] = sIterPLIC_.surfaceCentre();
+                if (mag(normal_[celli]) == 0)
+                {
+                    normal_[celli] = Zero;
+                    centre_[celli] = Zero;
+                }
+            }
+            else
+            {
+                normal_[celli] = Zero;
+                centre_[celli] = Zero;
+            }
+        }
+
+        normal_.correctBoundaryConditions();
+        centre_.correctBoundaryConditions();
+        Map<scalar> residual;
+        Map<scalar> avgAngle;
+
+        surfaceVectorField::Boundary nHatb(mesh_.Sf().boundaryField());
+        nHatb *= 1/(mesh_.magSf().boundaryField());
+
+        {
+            RDF_.constructRDF
+            (
+                nextToInterface_,
+                centre_,
+                normal_,
+                exchangeFields_,
+                false
+            );
+            RDF_.updateContactAngle(alpha1_, U_, nHatb);
+            gradSurf(RDF_);
+            calcResidual(residual, avgAngle);
+        }
+
+
+        label resCounter = 0;
+        scalar avgRes = 0;
+        scalar avgNormRes = 0;
+
+        Map<scalar>::iterator resIter = residual.begin();
+        Map<scalar>::iterator avgAngleIter = avgAngle.begin();
+
+        while (resIter.found())
+        {
+            if (avgAngleIter() > 0.26 && iter > 0) // 15 deg
+            {
+                tooCoarse.set(resIter.key());
+            }
+            else
+            {
+                avgRes += resIter();
+                scalar normRes = 0;
+                scalar discreteError = 0.01*sqr(avgAngleIter());
+                if (discreteError != 0)
+                {
+                    normRes= resIter()/max(discreteError, tol_);
+                }
+                else
+                {
+                    normRes= resIter()/tol_;
+                }
+                avgNormRes += normRes;
+                resCounter++;
+
+            }
+
+            ++resIter;
+            ++avgAngleIter;
+        }
+
+        reduce(avgRes,sumOp<scalar>());
+        reduce(avgNormRes,sumOp<scalar>());
+        reduce(resCounter,sumOp<label>());
+
+        if (resCounter == 0) // avoid division  by zero and leave loop
+        {
+            resCounter = 1;
+            avgRes = 0;
+            avgNormRes = 0;
+        }
+
+
+        if (iter == 0)
+        {
+            DebugInfo
+                << "initial residual absolute = "
+                << avgRes/resCounter << nl
+                << "initial residual normalized = "
+                << avgNormRes/resCounter << nl;
+        }
+
+        if
+        (
+            (
+                (avgNormRes/resCounter < relTol_ || avgRes/resCounter < tol_)
+             && (iter >= 1 )
+            )
+         || iter + 1  == iteration_
+        )
+        {
+            DebugInfo
+                << "iterations = " << iter << nl
+                << "final residual absolute = "
+                << avgRes/resCounter << nl
+                << "final residual normalized = " << avgNormRes/resCounter
+                << endl;
+
+            break;
+        }
+    }
+}
+
+
+void Foam::reconstruction::plicRDF::mapAlphaField() const
+{
+    // without it we seem to get a race condition
+    mesh_.C();
+
+    cutCellPLIC cutCell(mesh_);
+
+    forAll(normal_, celli)
+    {
+        if (mag(normal_[celli]) != 0)
+        {
+            vector n = normal_[celli]/mag(normal_[celli]);
+            scalar cutValue = (centre_[celli] - mesh_.C()[celli]) & (n);
+            cutCell.calcSubCell
+            (
+                celli,
+                cutValue,
+                n
+            );
+            alpha1_[celli] = cutCell.VolumeOfFluid();
+
+        }
+    }
+    alpha1_.correctBoundaryConditions();
+    alpha1_.oldTime () = alpha1_;
+    alpha1_.oldTime().correctBoundaryConditions();
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/plicRDF/plicRDF.H b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/plicRDF/plicRDF.H
new file mode 100644
index 0000000000000000000000000000000000000000..6c394b2fc997d3970054c385637ffb094b021a52
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/plicSchemes/plicRDF/plicRDF.H
@@ -0,0 +1,185 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::reconstruction::plicRDF
+
+Description
+    Reconstructs an interface (centre and normal vector) consisting of planes
+    to match the internal fluid distribution in cells. The interface normals
+    are estimated by least square gradient scheme on the RDF function (height).
+    Uses the normal from the previous times step as intial guess.
+
+    Reference:
+    \verbatim
+        Henning Scheufler, Johan Roenby,
+        Accurate and efficient surface reconstruction from volume
+        fraction data on general meshes,
+        Journal of Computational Physics, 2019,
+        doi 10.1016/j.jcp.2019.01.009
+
+    \endverbatim
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    plicRDF.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef plicRDF_H
+#define plicRDF_H
+
+#include "typeInfo.H"
+#include "reconstructionSchemes.H"
+#include "volFields.H"
+#include "dimensionedScalar.H"
+#include "autoPtr.H"
+#include "surfaceIteratorPLIC.H"
+#include "reconstructedDistanceFunction.H"
+#include "zoneDistribute.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+namespace reconstruction
+{
+
+/*---------------------------------------------------------------------------*\
+                           Class plicRDF Declaration
+\*---------------------------------------------------------------------------*/
+
+class plicRDF
+:
+    public reconstructionSchemes
+{
+    // Private Data
+
+        //- Reference to mesh
+        const fvMesh& mesh_;
+
+        //- Interpolation object from cell centres to points
+        DynamicField<vector> interfaceNormal_;
+
+
+    // Switches and tolerances. Tolerances need to go into toleranceSwitches
+
+        //- Tolerance for search of isoFace giving specified VOF value
+        scalar isoFaceTol_;
+
+        //- Tolerance for marking of surface cells:
+        //  Those with surfCellTol_ < alpha1 < 1 - surfCellTol_
+        scalar surfCellTol_;
+
+        //- Tolerance
+        scalar tol_;
+
+        //- Relative tolerance
+        scalar relTol_;
+
+        //- Number of times that the interface is reconstructed
+        //- has to be bigger than 2
+        label iteration_;
+
+        //- Interpolated normal from previous time step
+        bool interpolateNormal_;
+
+        //- Calculates the RDF function
+        reconstructedDistanceFunction RDF_;
+
+        //- Provides stencil and map
+        zoneDistribute& exchangeFields_;
+
+        //- surfaceIterator finds the plane centre for specified VOF value
+        surfaceIteratorPLIC sIterPLIC_;
+
+
+    // Private Member Functions
+
+        //- Set initial normals by interpolation from the previous
+        //- timestep or with the Young method
+        void setInitNormals(bool interpolate);
+
+        //- compute gradient at the surfaces
+        void gradSurf(const volScalarField& phi);
+
+        //- compute the normal residuals
+        void calcResidual
+        (
+            Map<scalar>& normalResidual,
+            Map<scalar>& avgAngle
+        );
+
+        //- interpolation of the normals from the previous time step
+        void interpolateNormal();
+
+        //- No copy construct
+        plicRDF(const plicRDF&) = delete;
+
+        //- No copy assignment
+        void operator=(const plicRDF&) = delete;
+
+
+public:
+
+    //- Runtime type information
+    TypeName("plicRDF");
+
+
+    //- Construct from components
+    plicRDF
+    (
+        volScalarField& alpha1,
+        const surfaceScalarField& phi,
+        const volVectorField& U,
+        const dictionary& dict
+    );
+
+
+    //- Destructor
+    virtual ~plicRDF() = default;
+
+
+    // Member Functions
+
+        //- Reconstruct interface
+        virtual void reconstruct(bool forceUpdate = true);
+
+        //- Map VoF Field in case of refinement
+        virtual void mapAlphaField() const;
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace reconstruction
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemes.C b/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemes.C
new file mode 100644
index 0000000000000000000000000000000000000000..78f81981a0fe98bcca422caed8287fbe5c58a6a7
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemes.C
@@ -0,0 +1,185 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "reconstructionSchemes.H"
+#include "cutCellPLIC.H"
+
+// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
+
+namespace Foam
+{
+    defineTypeNameAndDebug(reconstructionSchemes, 0);
+    defineRunTimeSelectionTable(reconstructionSchemes, components);
+}
+
+
+// * * * * * * * * * * * * Protected Member Functions  * * * * * * * * * * * //
+
+bool Foam::reconstructionSchemes::alreadyReconstructed(bool forceUpdate) const
+{
+    const Time& runTime = alpha1_.mesh().time();
+
+    label& curTimeIndex = timeIndexAndIter_.first();
+    label& curIter = timeIndexAndIter_.second();
+
+    // Reset timeIndex and curIter
+    if (curTimeIndex < runTime.timeIndex())
+    {
+        curTimeIndex = runTime.timeIndex();
+        curIter = 0;
+        return false;
+    }
+
+    if (forceUpdate)
+    {
+        curIter = 0;
+        return false;
+    }
+
+    // Always reconstruct when subcycling
+    if (runTime.subCycling() != 0)
+    {
+        return false;
+    }
+
+    ++curIter;
+    if (curIter > 1)
+    {
+        return true;
+    }
+
+    return false;
+}
+
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::reconstructionSchemes::reconstructionSchemes
+(
+    const word& type,
+    volScalarField& alpha1,
+    const surfaceScalarField& phi,
+    const volVectorField& U,
+    const dictionary& dict
+)
+:
+    IOdictionary
+    (
+        IOobject
+        (
+            "reconstructionScheme",
+            alpha1.time().constant(),
+            alpha1.db(),
+            IOobject::NO_READ,
+            IOobject::NO_WRITE
+        )
+    ),
+    reconstructionSchemesCoeffs_(dict),
+    alpha1_(alpha1),
+    phi_(phi),
+    U_(U),
+    normal_
+    (
+        IOobject
+        (
+            "recon::normal",
+            alpha1_.mesh().time().timeName(),
+            alpha1_.mesh(),
+            IOobject::NO_READ,
+            IOobject::AUTO_WRITE
+        ),
+        alpha1_.mesh(),
+        dimensionedVector(dimArea, Zero)
+    ),
+    centre_
+    (
+        IOobject
+        (
+            "recon::centre",
+            alpha1_.mesh().time().timeName(),
+            alpha1_.mesh(),
+            IOobject::NO_READ,
+            IOobject::AUTO_WRITE
+        ),
+        alpha1_.mesh(),
+        dimensionedVector(dimLength, Zero)
+    ),
+    interfaceCell_(alpha1_.mesh().nCells(), false),
+    interfaceLabels_(0.2*alpha1_.mesh().nCells()),
+    timeIndexAndIter_(0, 0)
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::reconstructionSchemes::interface Foam::reconstructionSchemes::surface()
+{
+    reconstruct(false);
+    const fvMesh& mesh = centre_.mesh();
+
+    cutCellPLIC cellCut(mesh);
+
+    DynamicList<point> dynPts;
+    DynamicList<face> dynFaces(mesh.nCells()*0.1);
+    bitSet interfaceCellAddressing(mesh.nCells());
+
+    forAll(interfaceCell_, celli)
+    {
+        if (interfaceCell_[celli])
+        {
+            if (mag(normal_[celli]) != 0)
+            {
+                interfaceCellAddressing.set(celli);
+                vector n = -normal_[celli]/mag(normal_[celli]);
+
+                scalar cutVal = (centre_[celli] - mesh.C()[celli]) & n;
+                cellCut.calcSubCell(celli, cutVal, n);
+
+                // cellCut.facePoints() are ordered and not connected
+                // to the other face
+                // append face with the starting label: dynPts.size()
+                dynFaces.append
+                (
+                    face(identity(cellCut.facePoints().size(), dynPts.size()))
+                );
+                dynPts.append(cellCut.facePoints());
+            }
+        }
+    }
+
+
+    labelList meshCells(interfaceCellAddressing.sortedToc());
+
+    // Transfer to mesh storage
+    pointField pts(std::move(dynPts));
+    faceList faces(std::move(dynFaces));
+
+    return interface(std::move(pts), std::move(faces), std::move(meshCells));
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemes.H b/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemes.H
new file mode 100644
index 0000000000000000000000000000000000000000..4a3ce6caac4cf281c2d21816ba0ff4d2c1042345
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemes.H
@@ -0,0 +1,269 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::reconstructionSchemes
+
+Description
+
+    Original code supplied by Henning Scheufler, DLR (2019)
+
+SourceFiles
+    reconstructionSchemes.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef reconstructionSchemes_H
+#define reconstructionSchemes_H
+
+#include "typeInfo.H"
+#include "runTimeSelectionTables.H"
+#include "dimensionedScalar.H"
+#include "volFields.H"
+#include "IOdictionary.H"
+#include "DynamicField.H"
+#include "MeshedSurface.H"
+#include "MeshedSurfacesFwd.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                    Class reconstructionSchemes Declaration
+\*---------------------------------------------------------------------------*/
+
+class reconstructionSchemes
+:
+    public IOdictionary
+{
+    // Private Data
+
+        //- Coefficients dictionary
+        dictionary reconstructionSchemesCoeffs_;
+
+
+protected:
+
+    // Protected Data
+
+        //- Reference to the VoF Field
+        volScalarField& alpha1_;
+
+        //- Reference to the face fluxes
+        const surfaceScalarField& phi_;
+
+        //- Reference to the velocity field
+        const volVectorField& U_;
+
+        //- Interface area normals
+        volVectorField normal_;
+
+        //- Interface centres
+        volVectorField centre_;
+
+        //- Is interface cell?
+        boolList interfaceCell_;
+
+        //- List of cell labels that have an interface
+        DynamicField<label> interfaceLabels_;
+
+        //- Store timeindex/iteration to avoid multiple reconstruction
+        mutable Pair<label> timeIndexAndIter_;
+
+
+    // Protected Member Functions
+
+        //- Is the interface already up-to-date?
+        bool alreadyReconstructed(bool forceUpdate = true) const;
+
+        //- No copy construct
+        reconstructionSchemes(const reconstructionSchemes&) = delete;
+
+        //- No copy assignment
+        void operator=(const reconstructionSchemes&) = delete;
+
+
+public:
+
+    // Public Classes
+
+        class interface
+        :
+            public meshedSurface
+        {
+            //- For every face the original cell in mesh
+            labelList meshCells_;
+
+            public:
+
+                interface
+                (
+                    const pointField& pointLst,
+                    const faceList& faceLst,
+                    const labelList& meshCells
+                )
+                :
+                    meshedSurface(pointLst, faceLst, surfZoneList{}),
+                    meshCells_(meshCells)
+                {}
+
+                interface
+                (
+                    pointField&& pointLst,
+                    faceList&& faceLst,
+                    labelList&& meshCells
+                )
+                :
+                    meshedSurface
+                    (
+                        std::move(pointLst),
+                        std::move(faceLst),
+                        surfZoneList{}
+                    ),
+                    meshCells_(std::move(meshCells))
+                {}
+
+                //- For every face, the original cell in mesh
+                const labelList& meshCells() const
+                {
+                    return meshCells_;
+                }
+        };
+
+
+public:
+
+    //- Runtime type information
+    TypeName("reconstructionSchemes");
+
+
+    // Declare run-time constructor selection table
+
+        declareRunTimeSelectionTable
+        (
+            autoPtr,
+            reconstructionSchemes,
+            components,
+            (
+                volScalarField& alpha1,
+                const surfaceScalarField& phi,
+                const volVectorField& U,
+                const dictionary& dict
+            ),
+            (alpha1, phi, U, dict)
+        );
+
+
+    // Selectors
+
+        //- Return a reference to the selected phaseChange model
+        static autoPtr<reconstructionSchemes> New
+        (
+            volScalarField& alpha1,
+            const surfaceScalarField& phi,
+            const volVectorField& U,
+            const dictionary& dict
+        );
+
+
+    // Constructors
+
+        //- Construct from components
+        reconstructionSchemes
+        (
+            const word& type,
+            volScalarField& alpha1,
+            const surfaceScalarField& phi,
+            const volVectorField& U,
+            const dictionary& dict
+        );
+
+
+    //- Destructor
+    virtual ~reconstructionSchemes() = default;
+
+
+    // Member Functions
+
+        //- Access to the model dictionary
+        dictionary& modelDict()
+        {
+            return reconstructionSchemesCoeffs_;
+        }
+
+        //- Const access to the model dictionary
+        const dictionary& modelDict() const
+        {
+            return reconstructionSchemesCoeffs_;
+        }
+
+        //- Reconstruct the interface
+        virtual void reconstruct(bool forceUpdate = true) = 0;
+
+        //- Reference to interface normals
+        const volVectorField& normal() const
+        {
+            return normal_;
+        }
+
+        //- Reference to interface centres
+        const volVectorField& centre() const
+        {
+            return centre_;
+        }
+
+        //- Does the cell contain interface
+        const boolList& interfaceCell() const
+        {
+            return interfaceCell_;
+        }
+
+        //- List of cells with an interface
+        const DynamicField<label>& interfaceLabels() const
+        {
+            return interfaceLabels_;
+        }
+
+        //- Map VoF Field in case of refinement
+        virtual void mapAlphaField() const
+        {}
+
+        //- Generated interface surface points/faces.
+        //  \note the points are disconnected!
+        interface surface();
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemesNew.C b/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemesNew.C
new file mode 100644
index 0000000000000000000000000000000000000000..7891acdc15dd50792d3d3f3fd334429000b0223e
--- /dev/null
+++ b/src/transportModels/geometricVoF/reconstructionSchemes/reconstructionSchemesNew.C
@@ -0,0 +1,72 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "reconstructionSchemes.H"
+#include "messageStream.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+Foam::autoPtr<Foam::reconstructionSchemes>
+Foam::reconstructionSchemes::New
+(
+    volScalarField& alpha1,
+    const surfaceScalarField& phi,
+    const volVectorField& U,
+    const dictionary& dict
+)
+{
+    word schemeType("isoAlpha");
+
+    if (!dict.readIfPresent("reconstructionScheme", schemeType))
+    {
+        Warning
+            << "Entry '"
+            << "reconstructionScheme" << "' not found in dictionary "
+            << dict.name() << nl
+            << "using default" << nl;
+    }
+
+    Info<< "Selecting reconstructionScheme: " << schemeType << endl;
+
+    auto cstrIter = componentsConstructorTablePtr_->cfind(schemeType);
+
+    if (!cstrIter.found())
+    {
+        FatalIOErrorInLookup
+        (
+            dict,
+            "reconstructionSchemes",
+            schemeType,
+            *componentsConstructorTablePtr_
+        ) << exit(FatalIOError);
+    }
+
+    return autoPtr<reconstructionSchemes>(cstrIter()(alpha1, phi, U, dict));
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorIso.C b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorIso.C
new file mode 100644
index 0000000000000000000000000000000000000000..305af0894b66139df17e4b09a482268b98331cfa
--- /dev/null
+++ b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorIso.C
@@ -0,0 +1,203 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "surfaceIteratorIso.H"
+#include "scalarMatrices.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::surfaceIteratorIso::surfaceIteratorIso
+(
+    const fvMesh& mesh,
+    scalarField& pointVal,
+    const scalar tol
+)
+:
+    mesh_(mesh),
+    ap_(pointVal),
+    cutCell_(mesh_,ap_),
+    surfCellTol_(tol)
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::surfaceIteratorIso::vofCutCell
+(   const label celli,
+    const scalar alpha1,
+    const scalar tol,
+    const label maxIter
+)
+{
+    // Finding cell vertex extrema values
+    const labelList& pLabels = mesh_.cellPoints()[celli];
+    scalarField fvert(pLabels.size());
+    forAll(pLabels, pi)
+    {
+        fvert[pi] = ap_[pLabels[pi]];
+    }
+
+    const labelList order(Foam::sortedOrder(fvert));
+    scalar f1 = fvert[order.first()];
+    scalar f2 = fvert[order.last()];
+
+    // Special case where method is given an almost full or empty cell
+    if (alpha1 < tol)
+    {
+        return -1; // is area and centre is zero;
+    }
+    else if (1 - alpha1 < tol)
+    {
+        return 1;
+    }
+
+    // Finding the two vertices inbetween which the isovalue giving alpha1 lies
+    label L1 = 0;
+    label L2 = fvert.size() - 1;
+    scalar a1 = 1;
+    scalar a2 = 0;
+    scalar L3, f3, a3;
+
+    while (L2 - L1 > 1)
+    {
+        L3 = round(0.5*(L1 + L2));
+        f3 = fvert[order[L3]];
+        cutCell_.calcSubCell(celli, f3);
+        a3 = cutCell_.VolumeOfFluid();
+        if (a3 > alpha1)
+        {
+            L1 = L3; f1 = f3; a1 = a3;
+        }
+        else if (a3 < alpha1)
+        {
+            L2 = L3; f2 = f3; a2 = a3;
+        }
+        else
+        {
+            return cutCell_.calcSubCell(celli, f3);
+        }
+    }
+
+    if (mag(f1 - f2) < 10*SMALL)
+    {
+        return cutCell_.calcSubCell(celli, f1);
+    }
+
+    if (mag(a1 - a2) < tol)
+    {
+        return cutCell_.calcSubCell(celli, 0.5*(f1 + f2));
+    }
+    // Now we know that a(f) = alpha1 is to be found on the f interval
+
+
+    // Finding coefficients in 3 deg polynomial alpha(f) from 4 solutions
+    // Finding 2 additional points on 3 deg polynomial
+    f3 = f1 + (f2 - f1)/3;
+    cutCell_.calcSubCell(celli, f3);
+    a3 = cutCell_.VolumeOfFluid();
+
+    scalar f4 = f1 + 2*(f2 - f1)/3;
+    cutCell_.calcSubCell(celli, f4);
+    scalar a4 = cutCell_.VolumeOfFluid();
+
+    // Building and solving Vandermonde matrix equation
+    scalarField a(4), f(4), C(4), fOld(4);
+    {
+        a[0] = a1, a[1] = a3, a[2] = a4, a[3] = a2;
+        fOld[0] = f1, fOld[1] = f3, fOld[2] = f4, fOld[3] = f2;
+        f[0] = 0, f[1] = (f3-f1)/(f2-f1), f[2] = (f4-f1)/(f2-f1), f[3] = 1;
+        scalarSquareMatrix M(4);
+        forAll(f, i)
+        {
+            forAll(f, j)
+            {
+                M[i][j] = pow(f[i], 3 - j);
+            }
+        }
+        // C holds the 4 polynomial coefficients
+        C = a;
+        LUsolve(M, C);
+    }
+
+    // Finding root with Newton method
+
+    f3 = f[1]; a3 = a[1];
+    label nIter = 0;
+    scalar res = mag(a3 - alpha1);
+    while (res > tol && nIter < 10*maxIter)
+    {
+        f3 -= (C[0]*pow3(f3) + C[1]*sqr(f3) + C[2]*f3 + C[3] - alpha1)
+            /(3*C[0]*sqr(f3) + 2*C[1]*f3 + C[2]);
+        a3 = C[0]*pow3(f3) + C[1]*sqr(f3) + C[2]*f3 + C[3];
+        res = mag(a3 - alpha1);
+        nIter++;
+    }
+    // Scaling back to original range
+    f3 = f3*(f2 - f1) + f1;
+
+    //Check result
+    label status = cutCell_.calcSubCell(celli, f3);
+    const scalar VOF = cutCell_.VolumeOfFluid();
+    res = mag(VOF - alpha1);
+
+    if (res > tol)
+    {
+    }
+    else
+    {
+        return status;
+    }
+
+    // If tolerance not met use the secant method  with f3 as a hopefully very
+    // good initial guess to crank res the last piece down below tol
+
+    scalar x2 = f3;
+    scalar g2 = VOF - alpha1;
+    scalar x1 = max(1e-3*(f2 - f1), 100*SMALL);
+    x1 = max(x1, f1);
+    x1 = min(x1, f2);
+    cutCell_.calcSubCell(celli, x1);
+    scalar g1 = cutCell_.VolumeOfFluid() - alpha1;
+
+    nIter = 0;
+    scalar g0(0), x0(0);
+    while (res > tol && nIter < maxIter && g1 != g2)
+    {
+        x0 = (x2*g1 - x1*g2)/(g1 - g2);
+        status = cutCell_.calcSubCell(celli, x0);
+        g0 = cutCell_.VolumeOfFluid() - alpha1;
+        res = mag(g0);
+        x2 = x1; g2 = g1;
+        x1 = x0; g1 = g0;
+        nIter++;
+    }
+
+    return status;
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorIso.H b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorIso.H
new file mode 100644
index 0000000000000000000000000000000000000000..50d9696db9e2ef2cbc1ec43ba47a1a05c58f1ea9
--- /dev/null
+++ b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorIso.H
@@ -0,0 +1,178 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::surfaceIteratorIso
+
+Description
+    Finds the isovalue that matches the volume fraction
+
+    Reference:
+    \verbatim
+        Roenby, J., Bredmose, H. and Jasak, H. (2016).
+        A computational method for sharp interface advection
+        Royal Society Open Science, 3
+        doi 10.1098/rsos.160405
+    \endverbatim
+
+Author
+    Johan Roenby, DHI, all rights reserved.
+
+SourceFiles
+    surfaceIteratorIso.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef surfaceIteratorIso_H
+#define surfaceIteratorIso_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+#include "cutCellIso.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                        Class surfaceIteratorIso Declaration
+\*---------------------------------------------------------------------------*/
+
+class surfaceIteratorIso
+{
+    // Private Data
+
+        //- Mesh whose cells and faces to cut at their intersection with an
+        //- isosurface.
+        const fvMesh& mesh_;
+
+        //- Reference to the point values
+        scalarField& ap_;
+
+        //- Cuts the cell and returns volume centre and normal
+        cutCellIso cutCell_;
+
+        //- Tolerance for marking of surface cells:
+        //  Those with surfCellTol_ < alpha1 < 1 - surfCellTol_
+        scalar surfCellTol_;
+
+
+public:
+
+    // Constructors
+
+        //- Construct from fvMesh and a scalarField
+        //  The scalarField size should equal the number of mesh points
+        surfaceIteratorIso
+        (
+            const fvMesh& mesh,
+            scalarField& pointVal,
+            const scalar tol
+        );
+
+
+    // Member Functions
+
+        //- Determine if a cell is a surface cell
+        bool isASurfaceCell(const scalar alpha1) const
+        {
+            return
+            (
+                surfCellTol_ < alpha1
+             && alpha1 < 1 - surfCellTol_
+            );
+        }
+
+        //- finds matching isoValue for the given value fraction
+        //- returns the cellStatus
+        label vofCutCell
+        (
+            const label celli,
+            const scalar alpha1,
+            const scalar tol,
+            const label maxIter
+        );
+
+        //- The centre point of cutted volume
+        const point& subCellCentre() const
+        {
+            return cutCell_.subCellCentre();
+        }
+
+        //- The volume of cutted volume
+        scalar subCellVolume() const
+        {
+            return cutCell_.subCellVolume();
+        }
+
+        //- The centre of cutting isosurface
+        const point& surfaceCentre() const
+        {
+            return cutCell_.faceCentre();
+        }
+
+        //- The area vector of cutting isosurface
+        const vector& surfaceArea() const
+        {
+            return cutCell_.faceArea();
+        }
+
+        //- Volume of Fluid for cellI (subCellVolume_/mesh_.V()[cellI])
+        scalar VolumeOfFluid() const
+        {
+            return cutCell_.VolumeOfFluid();
+        }
+
+        //- The cutValue
+        scalar cutValue() const
+        {
+            return cutCell_.cutValue();
+        }
+
+        //- The cellStatus
+        label cellStatus()
+        {
+            return cutCell_.cellStatus();
+        }
+
+        //- The points of the cutting isosurface in sorted order
+        const DynamicList<point>& facePoints()
+        {
+            return cutCell_.facePoints();
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorPLIC.C b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorPLIC.C
new file mode 100644
index 0000000000000000000000000000000000000000..7882a449a5d8d425cb5373e306b2e0740a10d914
--- /dev/null
+++ b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorPLIC.C
@@ -0,0 +1,217 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+\*---------------------------------------------------------------------------*/
+
+#include "surfaceIteratorPLIC.H"
+#include "scalarMatrices.H"
+
+// * * * * * * * * * * * * * * * * Constructors  * * * * * * * * * * * * * * //
+
+Foam::surfaceIteratorPLIC::surfaceIteratorPLIC
+(
+    const fvMesh& mesh,
+    const scalar tol
+)
+:
+    mesh_(mesh),
+    cutCell_(mesh_),
+    surfCellTol_(tol)
+{}
+
+
+// * * * * * * * * * * * * * * * Member Functions  * * * * * * * * * * * * * //
+
+Foam::label Foam::surfaceIteratorPLIC::vofCutCell
+(
+    const label celli,
+    const scalar alpha1,
+    const scalar tol,
+    const label maxIter,
+    vector normal
+)
+{
+    if (mag(normal) == 0)
+    {
+        WarningInFunction
+            << "normal length is zero in cell: " << celli << nl
+            << "try increasing nCorrectors" << endl;
+
+        return sign(alpha1-0.5);
+    }
+
+    normal.normalise();
+
+    // Finding cell vertex extrema values
+    const labelList& pLabels = mesh_.cellPoints(celli);
+    scalarField fvert(pLabels.size());
+    forAll(pLabels, pi)
+    {
+        fvert[pi] = (mesh_.points()[pLabels[pi]] - mesh_.C()[celli]) & (normal);
+    }
+
+    const labelList order(Foam::sortedOrder(fvert));
+    scalar f1 = fvert[order.first()];
+    scalar f2 = fvert[order.last()];
+
+
+    //Handling special case where method is handed an almost full or empty cell
+    if (alpha1 < tol)
+    {
+        return -1;
+    }
+    else if (1 - alpha1 < tol)
+    {
+        return 1;
+    }
+
+    // Finding the two vertices inbetween which the isovalue giving alpha1 lies
+    label L1 = 0;
+    label L2 = fvert.size() - 1;
+    scalar a1 = 1;
+    scalar a2 = 0;
+    scalar L3, f3, a3;
+
+    while (L2 - L1 > 1)
+    {
+        L3 = round(0.5*(L1 + L2));
+        f3 = fvert[order[L3]];
+        cutCell_.calcSubCell(celli, f3, normal);
+        a3 = cutCell_.VolumeOfFluid();
+        if (a3 > alpha1)
+        {
+            L1 = L3; f1 = f3; a1 = a3;
+        }
+        else if (a3 < alpha1)
+        {
+            L2 = L3; f2 = f3; a2 = a3;
+        }
+        else
+        {
+            return cutCell_.calcSubCell(celli, f3, normal);
+        }
+    }
+
+    if (mag(f1 - f2) < 10*SMALL)
+    {
+        return cutCell_.calcSubCell(celli, f1, normal);
+    }
+
+    if (mag(a1 - a2) < tol)
+    {
+        return cutCell_.calcSubCell(celli, 0.5*(f1 + f2), normal);
+    }
+    // Now we know that a(f) = alpha1 is to be found on the f interval
+    // [f1, f2], i.e. alpha1 will be in the interval [a2,a1]
+
+
+    // Finding coefficients in 3 deg polynomial alpha(f) from 4 solutions
+
+    // Finding 2 additional points on 3 deg polynomial
+    f3 = f1 + (f2 - f1)/3;
+    cutCell_.calcSubCell(celli, f3, normal);
+    a3 = cutCell_.VolumeOfFluid();
+
+    scalar f4 = f1 + 2*(f2 - f1)/3;
+    cutCell_.calcSubCell(celli, f4, normal);
+    scalar a4 = cutCell_.VolumeOfFluid();
+
+    // Building and solving Vandermonde matrix equation
+    scalarField a(4), f(4), C(4), fOld(4);
+    {
+        a[0] = a1, a[1] = a3, a[2] = a4, a[3] = a2;
+        fOld[0] = f1, fOld[1] = f3, fOld[2] = f4, fOld[3] = f2;
+        f[0] = 0, f[1] = (f3-f1)/(f2-f1), f[2] = (f4-f1)/(f2-f1), f[3] = 1;
+        scalarSquareMatrix M(4);
+        forAll(f, i)
+        {
+            forAll(f, j)
+            {
+                M[i][j] = pow(f[i], 3 - j);
+            }
+        }
+        // C holds the 4 polynomial coefficients
+        C = a;
+        LUsolve(M, C);
+    }
+
+    // Finding root with Newton method
+
+    f3 = f[1]; a3 = a[1];
+    label nIter = 0;
+    scalar res = mag(a3 - alpha1);
+    while (res > tol && nIter < 10*maxIter)
+    {
+        f3 -= (C[0]*pow3(f3) + C[1]*sqr(f3) + C[2]*f3 + C[3] - alpha1)
+            /(3*C[0]*sqr(f3) + 2*C[1]*f3 + C[2]);
+        a3 = C[0]*pow3(f3) + C[1]*sqr(f3) + C[2]*f3 + C[3];
+        res = mag(a3 - alpha1);
+        nIter++;
+    }
+    // Scaling back to original range
+    f3 = f3*(f2 - f1) + f1;
+
+    //Check result
+    label status = cutCell_.calcSubCell(celli, f3, normal);
+    const scalar VOF = cutCell_.VolumeOfFluid();
+    res = mag(VOF - alpha1);
+
+    if (res > tol)
+    {
+    }
+    else
+    {
+        return status;
+    }
+
+    // If tolerance not met use the secant method  with f3 as a hopefully very
+    // good initial guess to crank res the last piece down below tol
+
+    scalar x2 = f3;
+    scalar g2 = VOF - alpha1;
+    scalar x1 = max(1e-3*(f2 - f1), 100*SMALL);
+    x1 = max(x1, f1);
+    x1 = min(x1, f2);
+    cutCell_.calcSubCell(celli, x1,normal);
+    scalar g1 = cutCell_.VolumeOfFluid() - alpha1;
+
+    nIter = 0;
+    scalar g0(0), x0(0);
+    while (res > tol && nIter < maxIter && g1 != g2)
+    {
+        x0 = (x2*g1 - x1*g2)/(g1 - g2);
+        status = cutCell_.calcSubCell(celli, x0, normal);
+        g0 = cutCell_.VolumeOfFluid() - alpha1;
+        res = mag(g0);
+        x2 = x1; g2 = g1;
+        x1 = x0; g1 = g0;
+        nIter++;
+    }
+
+    return status;
+}
+
+
+// ************************************************************************* //
diff --git a/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorPLIC.H b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorPLIC.H
new file mode 100644
index 0000000000000000000000000000000000000000..c18ec3691e0c256e28f7845a5fe91069f9f8b759
--- /dev/null
+++ b/src/transportModels/geometricVoF/surfaceIterators/surfaceIteratorPLIC.H
@@ -0,0 +1,173 @@
+/*---------------------------------------------------------------------------*\
+  =========                 |
+  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
+   \\    /   O peration     |
+    \\  /    A nd           | www.openfoam.com
+     \\/     M anipulation  |
+-------------------------------------------------------------------------------
+    Copyright (C) 2019-2020 DLR
+-------------------------------------------------------------------------------
+License
+    This file is part of OpenFOAM.
+
+    OpenFOAM is free software: you can redistribute it and/or modify it
+    under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
+    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+    for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
+
+Class
+    Foam::surfaceIteratorPLIC
+
+Description
+    Finds the cutValue that matches the volume fraction
+
+    Reference:
+    \verbatim
+        Henning Scheufler, Johan Roenby,
+        Accurate and efficient surface reconstruction from volume
+        fraction data on general meshes,
+        Journal of Computational Physics, 2019,
+        doi 10.1016/j.jcp.2019.01.009
+    \endverbatim
+
+Author
+    Johan Roenby, DHI, all rights reserved.
+    Modified Henning Scheufler, DLR
+
+SourceFiles
+    surfaceIteratorPLIC.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef surfaceIteratorPLIC_H
+#define surfaceIteratorPLIC_H
+
+#include "fvMesh.H"
+#include "volFields.H"
+#include "surfaceFields.H"
+#include "cutCellPLIC.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+                      Class surfaceIteratorPLIC Declaration
+\*---------------------------------------------------------------------------*/
+
+class surfaceIteratorPLIC
+{
+    // Private Data
+
+        //- Mesh whose cells and faces to cut at their intersection with an
+        //- isosurface.
+        const fvMesh& mesh_;
+
+        //- Cuts the cell and returns volume centre and normal
+        cutCellPLIC cutCell_;
+
+        //- Tolerance for marking of surface cells:
+        //  Those with surfCellTol_ < alpha1 < 1 - surfCellTol_
+        scalar surfCellTol_;
+
+
+public:
+
+    // Constructors
+
+        //- Construct from fvMesh and a scalarField
+        //  Length of scalarField should equal number of mesh points
+        surfaceIteratorPLIC(const fvMesh& mesh, const scalar tol);
+
+
+    // Member Functions
+
+        //- Determine if a cell is a surface cell
+        bool isASurfaceCell(const scalar alpha1) const
+        {
+            return
+            (
+                surfCellTol_ < alpha1
+             && alpha1 < 1 - surfCellTol_
+            );
+        }
+
+        //- Finds matching cutValue for the given value fraction
+        //  \return the cellStatus
+        label vofCutCell
+        (
+            const label celli,
+            const scalar alpha1,
+            const scalar tol,
+            const label maxIter,
+            vector normal
+        );
+
+        //- The centre point of cutted volume
+        const point& subCellCentre() const
+        {
+            return cutCell_.subCellCentre();
+        }
+
+        //- The volume of cutted volume
+        scalar subCellVolume() const
+        {
+            return cutCell_.subCellVolume();
+        }
+
+        //- The centre of cutting isosurface
+        const point& surfaceCentre() const
+        {
+            return cutCell_.faceCentre();
+        }
+
+        //- The area vector of cutting isosurface
+        const vector& surfaceArea() const
+        {
+            return cutCell_.faceArea();
+        }
+
+        //- Volume of Fluid for cellI (subCellVolume_/mesh_.V()[cellI])
+        scalar VolumeOfFluid() const
+        {
+            return cutCell_.VolumeOfFluid();
+        }
+
+        //- The cutValue
+        scalar cutValue() const
+        {
+            return cutCell_.cutValue();
+        }
+
+        //- The cellStatus
+        label cellStatus()
+        {
+            return cutCell_.cellStatus();
+        }
+
+        //- The points of the cutting isosurface in sorted order
+        const DynamicList<point>& facePoints()
+        {
+            return cutCell_.facePoints();
+        }
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/T b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/T
new file mode 100644
index 0000000000000000000000000000000000000000..75a7ea9f69f56b51c745bf2a44094f78ded5f17e
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/T
@@ -0,0 +1,37 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      T;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 1 0 0 0];
+
+internalField   uniform 300;
+
+boundaryField
+{
+    wall
+    {
+        type            zeroGradient;
+    }
+
+    atmosphere
+    {
+        type            inletOutlet;
+        inletValue      $internalField;
+    }
+
+    #includeEtc "caseDicts/setConstraintTypes"
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/U b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/U
new file mode 100644
index 0000000000000000000000000000000000000000..93ad57faf604bddb3b802d375d2f76fbddf7ad84
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/U
@@ -0,0 +1,47 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volVectorField;
+    location    "0";
+    object      U;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -1 0 0 0 0];
+
+internalField   uniform (0 0 0);
+
+boundaryField
+{
+    rod
+    {
+        type            rotatingWallVelocity;
+        axis            (0 1 0);
+        origin          (0 0 0);
+        omega           constant #eval{ 2.1 * (2*pi()) };  // rev/s -> rads/s
+        value           uniform (0 0 0);
+    }
+    vessel
+    {
+        type            noSlip;
+    }
+
+    atmosphere
+    {
+        type            pressureInletOutletVelocity;
+        value           $internalField;
+    }
+
+    #includeEtc "caseDicts/setConstraintTypes"
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/alpha.liquid b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/alpha.liquid
new file mode 100644
index 0000000000000000000000000000000000000000..54eaef30cdaa0cd17ef0a57e34610c12dce27d03
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/alpha.liquid
@@ -0,0 +1,37 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      alpha.liquid;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 0 0 0 0];
+
+internalField   uniform 0;
+
+boundaryField
+{
+    wall
+    {
+        type            zeroGradient;
+    }
+
+    atmosphere
+    {
+        type            inletOutlet;
+        inletValue      $internalField;
+    }
+
+    #includeEtc "caseDicts/setConstraintTypes"
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/p b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/p
new file mode 100644
index 0000000000000000000000000000000000000000..eeaa36ccf5f22c4040e1fd93fc5046972c7fb02e
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/p
@@ -0,0 +1,38 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    wall
+    {
+        type            calculated;
+        value           $internalField;
+    }
+
+    atmosphere
+    {
+        type            calculated;
+        value           $internalField;
+    }
+
+    #includeEtc "caseDicts/setConstraintTypes"
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/p_rgh b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/p_rgh
new file mode 100644
index 0000000000000000000000000000000000000000..f69d181a92b4712fedc910a17200593b5aa09d2d
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/p_rgh
@@ -0,0 +1,38 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p_rgh;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    wall
+    {
+        type            fixedFluxPressure;
+        value           $internalField;
+    }
+
+    atmosphere
+    {
+        type            totalPressure;
+        p0              $internalField;
+    }
+
+    #includeEtc "caseDicts/setConstraintTypes"
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/sigma.liquid b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/sigma.liquid
new file mode 100644
index 0000000000000000000000000000000000000000..0b666ff4fae7bdf5289aa3c7aff1b299273069d4
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/0.orig/sigma.liquid
@@ -0,0 +1,38 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volSymmTensorField;
+    object      sigma.liquid;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 2 -2 0 0 0 0];
+
+internalField   uniform (0 0 0 0 0 0);
+
+boundaryField
+{
+    wall
+    {
+        type            zeroGradient;
+    }
+
+    atmosphere
+    {
+        type            inletOutlet;
+        inletValue      $internalField;
+    }
+
+    #includeEtc "caseDicts/setConstraintTypes"
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/Allclean b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/Allclean
new file mode 100755
index 0000000000000000000000000000000000000000..fb1f3847301c377e02e12439ba58cbf303af3ef9
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/Allclean
@@ -0,0 +1,8 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/CleanFunctions      # Tutorial clean functions
+#------------------------------------------------------------------------------
+
+cleanCase0
+
+#------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/Allrun b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/Allrun
new file mode 100755
index 0000000000000000000000000000000000000000..316fb4d9fb2c421202cf3cc9aa27bb73099139c1
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/Allrun
@@ -0,0 +1,14 @@
+#!/bin/sh
+cd "${0%/*}" || exit                                # Run from this directory
+. ${WM_PROJECT_DIR:?}/bin/tools/RunFunctions        # Tutorial run functions
+#------------------------------------------------------------------------------
+
+runApplication blockMesh
+runApplication extrudeMesh
+
+restore0Dir
+
+runApplication setFields
+runApplication $(getApplication)
+
+#------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/README b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/README
new file mode 100644
index 0000000000000000000000000000000000000000..7d86d1f62fe4c5ac131e80e6fd62fb0442b632f1
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/README
@@ -0,0 +1,41 @@
+Reference:
+
+    Figueiredo, R. A., Oishi, C. M., Afonso, A. M., Tasso, I. V. M., &
+    Cuminato, J. A. (2016).
+    A two-phase solver for complex fluids: Studies of the Weissenberg effect.
+    International Journal of Multiphase Flow, 84, 98-115.
+
+In compressibleInterFoam with turbulenceProperties simulationType set to
+twoPhaseTransport separate stress models (laminar, non-Newtonian, LES or RAS)
+are instantiated for each of the two phases allowing for different modeling for
+the phases.
+
+This example case uses:
+- phases "air" and "liquid"
+- air phase
+  - constant/turbulenceProperties.air:
+    - stress model set to laminar, Newtonian
+  - constant/thermophysicalProperties.air:
+    - transport set to const (Newtonian)
+    - mu (dynamic viscoity) = 1.84e-5
+- liquid phase
+  - constant/turbulenceProperties.liquid:
+    - stress model set to laminar, Maxwell non-Newtonian
+    - nuM (kinematic viscosity) = 0.01476
+    - lambda = 0.018225
+  - constant/thermophysicalProperties.liquid
+    - transport set to const (Newtonian)
+    - mu (dynamic viscoity) = 1.46
+
+Liquid phase properties were calculated from the relations given in the paper:
+- rho = 890 kg/m^3
+- mu = mu_{s} + mu_{p} = 146 poise = 14.6 Pa.s
+  s = solvent (Newtonian), p = polymer (Maxwell)
+- mu_{s}/mu_{p} = 1/9
+
+=> mu_{s} = 14.6/10 = 1.46 Pa.s
+=> nu_{p} = nuM = (9/10)*14.6/890 = 0.01476 m^2/s
+
+compressibleInterFoam solves the energy equation, despite not being needed in
+this example.  The case is simply initialised at a uniform temperature of 300K
+throughout the domain and at the atmosphere boundary.
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/fvOptions b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/fvOptions
new file mode 100644
index 0000000000000000000000000000000000000000..9079bfed7a2b64fb8b4181155769ef191ac96add
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/fvOptions
@@ -0,0 +1,28 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      fvOptions;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+stabilization
+{
+    type            symmTensorPhaseLimitStabilization;
+
+    field           sigma.liquid;
+    rate            rLambda.liquid;
+    residualAlpha   1e-3;
+}
+
+
+//************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/g b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/g
new file mode 100644
index 0000000000000000000000000000000000000000..79b4fc3b5f23799fb44f6f3e83a2f8a5ca49da39
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/g
@@ -0,0 +1,22 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       uniformDimensionedVectorField;
+    location    "constant";
+    object      g;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -2 0 0 0 0];
+value           (0 -9.81 0);
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties
new file mode 100644
index 0000000000000000000000000000000000000000..43d9ef28ace6559e73a5c74d1413c731558ab52f
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties
@@ -0,0 +1,24 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+phases (liquid air);
+
+pMin        10000;
+
+sigma       0.0309;
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties.air b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties.air
new file mode 100644
index 0000000000000000000000000000000000000000..2afc5fe91f5b6e4747857970ce861f7f7850b275
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties.air
@@ -0,0 +1,52 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState rhoConst;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   28.9;
+    }
+    equationOfState
+    {
+        rho         1.2;
+    }
+    thermodynamics
+    {
+        Cp          1007;
+        Hf          0;
+    }
+    transport
+    {
+        mu          1.84e-05;
+        Pr          0.7;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties.liquid b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties.liquid
new file mode 100644
index 0000000000000000000000000000000000000000..3b5a74c3a7ddbe36a539316f9ede2ced40936e0d
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/thermophysicalProperties.liquid
@@ -0,0 +1,52 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState rhoConst;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   18.0;
+    }
+    equationOfState
+    {
+        rho         890;
+    }
+    thermodynamics
+    {
+        Cp          4195;
+        Hf          0;
+    }
+    transport
+    {
+        mu          1.46;
+        Pr          2.289;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties
new file mode 100644
index 0000000000000000000000000000000000000000..d9855126fa222f100a24e0f539a0f64b5ba9270c
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  twoPhaseTransport;
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties.air b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties.air
new file mode 100644
index 0000000000000000000000000000000000000000..fbd1e3c277c13766d96341f6214f8c833ed4b691
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties.air
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  laminar;
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties.liquid b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties.liquid
new file mode 100644
index 0000000000000000000000000000000000000000..623d9231297ef6955b6bb506a07e866338416e76
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/constant/turbulenceProperties.liquid
@@ -0,0 +1,29 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  laminar;
+
+laminar
+{
+    laminarModel Maxwell;
+
+    nuM             0.01476;
+    lambda          0.018225;
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/blockMeshDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/blockMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..9170c10a1a09e7a75768275760880ea7e8d9daad
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/blockMeshDict
@@ -0,0 +1,114 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      blockMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+scale   0.001;
+
+// H         77;
+R         6.35;
+Rc        152.25;
+hTotal    110;
+
+rCells     80;
+hCells     80;
+
+rGrading
+(
+    (0.1 1    1)
+    (0.9 2.25 10)
+);
+
+hGrading
+(
+    (0.65 2   0.1)
+    (0.2  2.4 1)
+    (0.15 1.2 2)
+);
+
+vertices
+(
+    ($R   0  -1)
+    ($Rc  0  -1)
+    ($R  $hTotal  -1)
+    ($Rc $hTotal  -1)
+
+    ($R   0   0)
+    ($Rc  0   0)
+    ($R  $hTotal   0)
+    ($Rc $hTotal   0)
+
+);
+
+blocks
+(
+    hex (0 1 3 2 4 5 7 6)
+    ($rCells $hCells 1)
+    simpleGrading ($rGrading $hGrading 1)
+);
+
+edges
+(
+);
+
+boundary
+(
+    rod
+    {
+        type wall;
+        faces
+        (
+            (0 2 6 4)
+        );
+    }
+    vessel
+    {
+        type wall;
+        faces
+        (
+            (1 3 7 5)
+            (0 1 5 4)
+        );
+    }
+    atmosphere
+    {
+        type patch;
+        faces
+        (
+            (2 3 7 6)
+        );
+    }
+    back
+    {
+        type symmetry;
+        faces
+        (
+            (0 2 3 1)
+        );
+    }
+    front
+    {
+        type symmetry;
+        faces
+        (
+            (4 5 7 6)
+        );
+    }
+);
+
+mergePatchPairs
+(
+);
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/controlDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/controlDict
new file mode 100644
index 0000000000000000000000000000000000000000..13e28dcda7361be6a86ae556ca3084ebf214a83a
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/controlDict
@@ -0,0 +1,56 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      controlDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+application     compressibleInterIsoFoam;
+
+startFrom       latestTime;
+
+startTime       0;
+
+stopAt          endTime;
+
+endTime         25;
+
+deltaT          1e-3;
+
+writeControl    adjustableRunTime;
+
+writeInterval   0.5;
+
+purgeWrite      0;
+
+writeFormat     ascii;
+
+writePrecision  10;
+
+writeCompression off;
+
+timeFormat      general;
+
+timePrecision   6;
+
+runTimeModifiable yes;
+
+adjustTimeStep  yes;
+
+maxCo           1;
+maxAlphaCo      1;
+
+maxDeltaT       1;
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/extrudeMeshDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/extrudeMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..ac346f35922b15803f4238e7f18eebeb58cdd477
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/extrudeMeshDict
@@ -0,0 +1,36 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      extrudeMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+constructFrom patch;
+sourceCase "$FOAM_CASE";
+
+sourcePatches (front);
+exposedPatchName back;
+
+extrudeModel    wedge;
+
+sectorCoeffs    //<- Also used for wedge
+{
+    point       (0 0 0);
+    axis        (0 -1 0);
+    angle       1;
+}
+
+flipNormals false;
+
+mergeFaces  false;
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/fvSchemes b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/fvSchemes
new file mode 100644
index 0000000000000000000000000000000000000000..c19fc1c86bd1bcd926b55e95719b31ebb4c3f794
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/fvSchemes
@@ -0,0 +1,67 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSchemes;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+ddtSchemes
+{
+    default         Euler;
+}
+
+gradSchemes
+{
+    default         Gauss linear;
+}
+
+divSchemes
+{
+    div(rhoPhi,U)   Gauss linearUpwindV grad(U);
+    div(rhoPhi,T)   Gauss linearUpwind grad(T);
+    div(phi,thermo:rho.liquid) Gauss linear;
+    div(phi,thermo:rho.air) Gauss linear;
+
+    div(phi,alpha)  Gauss vanLeer;
+    div(phirb,alpha) Gauss linear;
+
+    div(phi,p)      Gauss upwind;
+    div(rhoPhi,K)   Gauss upwind;
+
+    div(alphaRhoPhi.liquid,sigma.liquid) Gauss upwind;
+
+    div(((alpha.liquid*thermo:rho.liquid)*sigma.liquid))   Gauss linear;
+    div((((alpha.liquid*thermo:rho.liquid)*nuM)*grad(U)))   Gauss linear;
+    div((((alpha.liquid*thermo:rho.liquid)*(thermo:mu.liquid|thermo:rho.liquid))*dev2(T(grad(U))))) Gauss linear;
+
+    div((((alpha.air*thermo:rho.air)*nuEff.air)*dev2(T(grad(U))))) Gauss linear;
+    div((((alpha.liquid*thermo:rho.liquid)*nuEff.liquid)*dev2(T(grad(U))))) Gauss linear;
+}
+
+laplacianSchemes
+{
+    default         Gauss linear corrected;
+}
+
+interpolationSchemes
+{
+    default         linear;
+}
+
+snGradSchemes
+{
+    default         corrected;
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/fvSolution b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/fvSolution
new file mode 100644
index 0000000000000000000000000000000000000000..196ab714ebea769a31ad59988c2a86bd23ee3c87
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/fvSolution
@@ -0,0 +1,90 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+solvers
+{
+    "alpha.liquid.*"
+    {
+        nAlphaCorr      2;
+        nAlphaSubCycles 1;
+        cAlpha          1;
+
+        reconstructionScheme isoAlpha;
+        isoFaceTol 1e-8;
+        surfCellTol 1e-8;
+        nAlphaBounds    3;
+        snapTol         1e-12;
+        clip            true;
+    }
+
+    "pcorr.*"
+    {
+        solver          PCG;
+        preconditioner  DIC;
+        tolerance       1e-5;
+        relTol          0;
+    }
+
+    p_rgh
+    {
+        solver          PCG;
+        preconditioner  DIC;
+        tolerance       1e-9;
+        relTol          0.05;
+    }
+
+    p_rghFinal
+    {
+        $p_rgh;
+        relTol          0;
+    }
+
+    "U.*"
+    {
+        solver          PBiCGStab;
+        preconditioner  DILU;
+        tolerance       1e-6;
+        relTol          0;
+    }
+
+    "(T|k|B|nuTilda|sigma).*"
+    {
+        solver          PBiCGStab;
+        preconditioner  DILU;
+        tolerance       1e-8;
+        relTol          0;
+    }
+}
+
+PIMPLE
+{
+    momentumPredictor   no;
+    nOuterCorrectors    1;
+    nCorrectors         2;
+    nNonOrthogonalCorrectors 0;
+}
+
+relaxationFactors
+{
+    equations
+    {
+        ".*" 1;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/setFieldsDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/setFieldsDict
new file mode 100644
index 0000000000000000000000000000000000000000..1f992101fdd9e9ebe1a05bb3972e58f095ec41be
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/climbingRod/system/setFieldsDict
@@ -0,0 +1,36 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      setFieldsDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+defaultFieldValues
+(
+    volScalarFieldValue alpha.liquid 0
+);
+
+regions
+(
+    boxToCell
+    {
+        box (0 0 -1) (1 0.0771 1);
+        fieldValues
+        (
+            volScalarFieldValue alpha.liquid 1
+        );
+    }
+);
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/T b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/T
new file mode 100644
index 0000000000000000000000000000000000000000..21b16adb6a273c08f5358893fcf39591dd9a2f21
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/T
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      T;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 1 0 0 0];
+
+internalField   uniform 300;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/U b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/U
new file mode 100644
index 0000000000000000000000000000000000000000..00c303e2562e3c3237bfbd1ec92d462d00037d9f
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/U
@@ -0,0 +1,33 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volVectorField;
+    object      U;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -1 0 0 0 0];
+
+internalField   uniform (0 0 0);
+
+boundaryField
+{
+    walls
+    {
+        type            noSlip;
+    }
+    frontAndBack
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/alpha.water b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/alpha.water
new file mode 100644
index 0000000000000000000000000000000000000000..fa7e6861d029e4d41f0ecac1ce9c17965d9084ca
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/alpha.water
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      alpha.water;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 0 0 0 0];
+
+internalField   uniform 0;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/p b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/p
new file mode 100644
index 0000000000000000000000000000000000000000..a7ee2ed31c529e5aed5aac42a37ce89dbf219f08
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/p
@@ -0,0 +1,35 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    walls
+    {
+        type            calculated;
+        value           uniform 1e5;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/p_rgh b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/p_rgh
new file mode 100644
index 0000000000000000000000000000000000000000..d332d26e556b288be6a159aaaa5323accb9e1fd8
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/0.orig/p_rgh
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p_rgh;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    walls
+    {
+        type            fixedFluxPressure;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/Allclean b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/Allclean
new file mode 100755
index 0000000000000000000000000000000000000000..188f107b0e907b47bebd868d842a1853f587802a
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/Allclean
@@ -0,0 +1,8 @@
+#!/bin/sh
+cd ${0%/*} || exit 1                        # Run from this directory
+. $WM_PROJECT_DIR/bin/tools/CleanFunctions  # Tutorial clean functions
+
+cleanCase0
+rm -r sequencedVTK
+
+#------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/Allrun b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/Allrun
new file mode 100755
index 0000000000000000000000000000000000000000..98b1a954b1962b7c9b8b87946d83b23f1ccaf5cb
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/Allrun
@@ -0,0 +1,12 @@
+#!/bin/sh
+cd ${0%/*} || exit 1                        # Run from this directory
+. $WM_PROJECT_DIR/bin/tools/RunFunctions    # Tutorial run functions
+
+runApplication blockMesh
+restore0Dir
+runApplication setFields
+runApplication setAlphaField
+runApplication $(getApplication)
+foamSequenceVTKFiles -vtp
+
+#------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/g b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/g
new file mode 100644
index 0000000000000000000000000000000000000000..79b4fc3b5f23799fb44f6f3e83a2f8a5ca49da39
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/g
@@ -0,0 +1,22 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       uniformDimensionedVectorField;
+    location    "constant";
+    object      g;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -2 0 0 0 0];
+value           (0 -9.81 0);
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties
new file mode 100644
index 0000000000000000000000000000000000000000..48fa89f53b49a4438dc67c8bc6018ebd92d741ab
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties
@@ -0,0 +1,28 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+phases (water air);
+
+pMin        10000;
+
+sigma
+{
+    type    constant;
+    sigma   0.07;
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties.air b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties.air
new file mode 100644
index 0000000000000000000000000000000000000000..5c77a504431c915a7a4e441b5a9a1dcbcde4da2c
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties.air
@@ -0,0 +1,48 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState perfectGas;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   28.9;
+    }
+    thermodynamics
+    {
+        Cp          1007;
+        Hf          0;
+    }
+    transport
+    {
+        mu          1.84e-05;
+        Pr          0.7;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties.water b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties.water
new file mode 100644
index 0000000000000000000000000000000000000000..50a924c51306411f5da14767e0db17c397f8cba8
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/thermophysicalProperties.water
@@ -0,0 +1,69 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+/*
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    properties      liquid;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    H2O;
+}
+*/
+
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState perfectFluid;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   18.0;
+    }
+    equationOfState
+    {
+        R           3000;
+        rho0        1027;
+    }
+    thermodynamics
+    {
+        Cp          4195;
+        Hf          0;
+    }
+    transport
+    {
+        mu          3.645e-4;
+        Pr          2.289;
+    }
+}
+
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/turbulenceProperties b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/turbulenceProperties
new file mode 100644
index 0000000000000000000000000000000000000000..fbd1e3c277c13766d96341f6214f8c833ed4b691
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/constant/turbulenceProperties
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  laminar;
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/blockMeshDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/blockMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..4c996b626091aa5adc8fc3c6aff6221e583aa77b
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/blockMeshDict
@@ -0,0 +1,52 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      blockMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+scale   1;
+
+vertices
+(
+    (0 0 -0.1)
+    (1 0 -0.1)
+    (1 2 -0.1)
+    (0 2 -0.1)
+    (0 0 0.1)
+    (1 0 0.1)
+    (1 2 0.1)
+    (0 2 0.1)
+);
+
+blocks
+(
+    hex (0 1 2 3 4 5 6 7) (80 160 1) simpleGrading (1 1 1)
+);
+
+patches
+(
+    wall walls
+    (
+        (3 7 6 2)
+        (0 4 7 3)
+        (2 6 5 1)
+        (1 5 4 0)
+    )
+    empty frontAndBack
+    (
+        (0 3 2 1)
+        (4 5 6 7)
+    )
+);
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/controlDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/controlDict
new file mode 100644
index 0000000000000000000000000000000000000000..a346c2ef7637ef36aac9b89d7575e57ad905b41e
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/controlDict
@@ -0,0 +1,78 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      controlDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+application     compressibleInterIsoFoam;
+
+startFrom       startTime;
+
+startTime       0;
+
+stopAt          endTime;
+
+endTime         0.5;
+
+deltaT          0.0001;
+
+writeControl    adjustableRunTime;
+
+writeInterval   0.01;
+
+purgeWrite      0;
+
+writeFormat     binary;
+
+writePrecision  8;
+
+writeCompression off;
+
+timeFormat      general;
+
+timePrecision   10;
+
+runTimeModifiable yes;
+
+adjustTimeStep  yes;
+
+maxCo           0.5;
+maxAlphaCo      0.5;
+maxDeltaT       1;
+
+functions
+{
+    surfaces
+    {
+        type            surfaces;
+        libs            ("libsampling.so");
+        writeControl    writeTime;
+
+        surfaceFormat   vtp;
+        fields          (p U);
+
+        interpolationScheme cell;
+
+        surfaces
+        {
+            freeSurf
+            {
+                type            interface;
+                interpolate     false;
+            }
+        }
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/fvSchemes b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/fvSchemes
new file mode 100644
index 0000000000000000000000000000000000000000..60587bab5bdbec6ff3d098ba45c93b7f1eabcfa0
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/fvSchemes
@@ -0,0 +1,59 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSchemes;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+ddtSchemes
+{
+    default         Euler;
+}
+
+gradSchemes
+{
+    default         Gauss linear;
+}
+
+divSchemes
+{
+    div(phi,alpha)  Gauss vanLeer;
+    div(phirb,alpha) Gauss linear;
+    div(phi,thermo:rho.water) Gauss upwind;
+    div(phi,thermo:rho.air) Gauss upwind;
+
+    div(rhoPhi,U)  Gauss upwind;
+    div(rhoPhi,T)  Gauss upwind;
+    div(rhoPhi,K)  Gauss upwind;
+    div(phi,p)      Gauss upwind;
+    div(phi,k)      Gauss upwind;
+
+    div(((rho*nuEff)*dev2(T(grad(U))))) Gauss linear;
+}
+
+laplacianSchemes
+{
+    default         Gauss linear uncorrected;
+}
+
+interpolationSchemes
+{
+    default         linear;
+}
+
+snGradSchemes
+{
+    default         uncorrected;
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/fvSolution b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/fvSolution
new file mode 100644
index 0000000000000000000000000000000000000000..377a54e4dbb29d75a943c56c162818f98d6ce872
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/fvSolution
@@ -0,0 +1,107 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+solvers
+{
+    "alpha.water.*"
+    {
+        nAlphaCorr      1;
+        nAlphaSubCycles 2;
+        cAlpha          1;
+
+        reconstructionScheme gradAlpha;
+        isoFaceTol      1e-8;
+        surfCellTol     1e-6;
+        nAlphaBounds    3;
+        snapTol         1e-12;
+        clip            true;
+    }
+
+    ".*(rho|rhoFinal)"
+    {
+        solver          diagonal;
+    }
+
+    "pcorr.*"
+    {
+        solver          PCG;
+        preconditioner
+        {
+            preconditioner  GAMG;
+            tolerance       1e-05;
+            relTol          0;
+            smoother        DICGaussSeidel;
+        }
+        tolerance       1e-05;
+        relTol          0;
+        maxIter         100;
+    }
+
+      p_rgh
+    {
+        solver          GAMG;
+        tolerance       1e-07;
+        relTol          0.01;
+        smoother        DIC;
+    }
+
+    p_rghFinal
+    {
+        solver          PCG;
+        preconditioner
+        {
+            preconditioner  GAMG;
+            tolerance       1e-07;
+            relTol          0;
+            nVcycles        2;
+            smoother        DICGaussSeidel;
+            nPreSweeps      2;
+        }
+        tolerance       1e-07;
+        relTol          0;
+        maxIter         20;
+    }
+
+    U
+    {
+        solver          smoothSolver;
+        smoother        GaussSeidel;
+        tolerance       1e-06;
+        relTol          0;
+        nSweeps         1;
+    }
+
+    "(T|k|B|nuTilda).*"
+    {
+        solver          smoothSolver;
+        smoother        symGaussSeidel;
+        tolerance       1e-08;
+        relTol          0;
+    }
+}
+
+PIMPLE
+{
+    momentumPredictor no;
+    transonic       no;
+    nOuterCorrectors 1;
+    nCorrectors     2;
+    nNonOrthogonalCorrectors 0;
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/setAlphaFieldDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/setAlphaFieldDict
new file mode 100644
index 0000000000000000000000000000000000000000..f1fc08c099ac7c04c1f6547b5b1b30a5e67370c0
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/setAlphaFieldDict
@@ -0,0 +1,40 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      setFieldsDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+field alpha.water;
+type composedFunction;
+mode subtract;
+composedFunction
+{
+    plane
+    {
+        type plane;
+        origin (0 1. 0);
+        normal (0 -1 0);
+    }
+
+    sphere
+    {
+        type cylinder;
+        radius 0.1;
+        origin (0.5 0.5 0);
+        direction (0 0 1);
+        scale -1;
+    }
+
+}
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/setFieldsDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/setFieldsDict
new file mode 100644
index 0000000000000000000000000000000000000000..1e1e4de2615e5477e70a5641fbeaa51be1a9acfa
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge2D/system/setFieldsDict
@@ -0,0 +1,52 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      setFieldsDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+defaultFieldValues
+(
+//    volScalarFieldValue alpha.water 1
+    volScalarFieldValue p_rgh 1e5
+    volScalarFieldValue p 1e5
+    volScalarFieldValue T 300
+);
+
+regions
+(
+    sphereToCell
+    {
+        origin  (0.5 0.5 0);
+        radius  0.1;
+
+        fieldValues
+        (
+            //volScalarFieldValue alpha.water 0
+            volScalarFieldValue p_rgh 1e6
+            volScalarFieldValue p 1e6
+            volScalarFieldValue T 578
+        );
+    }
+   /* boxToCell
+    {
+        box (-10 1 -1) (10 10 1);
+        fieldValues
+        (
+            volScalarFieldValue alpha.water 0
+        );
+    }*/
+);
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/T b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/T
new file mode 100644
index 0000000000000000000000000000000000000000..21b16adb6a273c08f5358893fcf39591dd9a2f21
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/T
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      T;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 1 0 0 0];
+
+internalField   uniform 300;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/U b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/U
new file mode 100644
index 0000000000000000000000000000000000000000..00c303e2562e3c3237bfbd1ec92d462d00037d9f
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/U
@@ -0,0 +1,33 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volVectorField;
+    object      U;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -1 0 0 0 0];
+
+internalField   uniform (0 0 0);
+
+boundaryField
+{
+    walls
+    {
+        type            noSlip;
+    }
+    frontAndBack
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/alpha.water b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/alpha.water
new file mode 100644
index 0000000000000000000000000000000000000000..fa7e6861d029e4d41f0ecac1ce9c17965d9084ca
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/alpha.water
@@ -0,0 +1,34 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      alpha.water;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 0 0 0 0 0 0];
+
+internalField   uniform 0;
+
+boundaryField
+{
+    walls
+    {
+        type            zeroGradient;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/p b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/p
new file mode 100644
index 0000000000000000000000000000000000000000..a7ee2ed31c529e5aed5aac42a37ce89dbf219f08
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/p
@@ -0,0 +1,35 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    walls
+    {
+        type            calculated;
+        value           uniform 1e5;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/p_rgh b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/p_rgh
new file mode 100644
index 0000000000000000000000000000000000000000..c7db9671d503f9abd5bf8efddca9d8d1926f9a1d
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/0.orig/p_rgh
@@ -0,0 +1,35 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       volScalarField;
+    object      p_rgh;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [1 -1 -2 0 0 0 0];
+
+internalField   uniform 1e5;
+
+boundaryField
+{
+    walls
+    {
+        type            fixedFluxPressure;
+        value           uniform 1e5;
+    }
+
+    defaultFaces
+    {
+        type            empty;
+    }
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/Allclean b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/Allclean
new file mode 100755
index 0000000000000000000000000000000000000000..3b8c6e8e2fb2b80437330845ebe5002ef787f4b3
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/Allclean
@@ -0,0 +1,8 @@
+#!/bin/sh
+cd ${0%/*} || exit 1                        # Run from this directory
+. $WM_PROJECT_DIR/bin/tools/CleanFunctions  # Tutorial clean functions
+
+cleanCase0
+rm -rf processor*
+
+#------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/Allrun b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/Allrun
new file mode 100755
index 0000000000000000000000000000000000000000..bdb96428fab4a09fe5434006ac2651a46362525a
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/Allrun
@@ -0,0 +1,12 @@
+#!/bin/sh
+cd ${0%/*} || exit 1                        # Run from this directory
+. $WM_PROJECT_DIR/bin/tools/RunFunctions    # Tutorial run functions
+
+runApplication blockMesh
+restore0Dir
+runApplication setFields
+runApplication decomposePar
+runParallel $(getApplication)
+runApplication reconstructPar
+
+#------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/g b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/g
new file mode 100644
index 0000000000000000000000000000000000000000..79b4fc3b5f23799fb44f6f3e83a2f8a5ca49da39
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/g
@@ -0,0 +1,22 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       uniformDimensionedVectorField;
+    location    "constant";
+    object      g;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+dimensions      [0 1 -2 0 0 0 0];
+value           (0 -9.81 0);
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties
new file mode 100644
index 0000000000000000000000000000000000000000..97199ca415d59d3326cd274950f23aead4eb3f8b
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties
@@ -0,0 +1,24 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+phases (water air);
+
+pMin        10000;
+
+sigma       0.07;
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties.air b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties.air
new file mode 100644
index 0000000000000000000000000000000000000000..5c77a504431c915a7a4e441b5a9a1dcbcde4da2c
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties.air
@@ -0,0 +1,48 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState perfectGas;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   28.9;
+    }
+    thermodynamics
+    {
+        Cp          1007;
+        Hf          0;
+    }
+    transport
+    {
+        mu          1.84e-05;
+        Pr          0.7;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties.water b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties.water
new file mode 100644
index 0000000000000000000000000000000000000000..175e31bdf955911abef2b2ed520c1fe66b634412
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/thermophysicalProperties.water
@@ -0,0 +1,53 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      thermophysicalProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+thermoType
+{
+    type            heRhoThermo;
+    mixture         pureMixture;
+    transport       const;
+    thermo          hConst;
+    equationOfState perfectFluid;
+    specie          specie;
+    energy          sensibleInternalEnergy;
+}
+
+mixture
+{
+    specie
+    {
+        molWeight   18.0;
+    }
+    equationOfState
+    {
+        R           3000;
+        rho0        1027;
+    }
+    thermodynamics
+    {
+        Cp          4195;
+        Hf          0;
+    }
+    transport
+    {
+        mu          3.645e-4;
+        Pr          2.289;
+    }
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/turbulenceProperties b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/turbulenceProperties
new file mode 100644
index 0000000000000000000000000000000000000000..fbd1e3c277c13766d96341f6214f8c833ed4b691
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/constant/turbulenceProperties
@@ -0,0 +1,21 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "constant";
+    object      turbulenceProperties;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+simulationType  laminar;
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/blockMeshDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/blockMeshDict
new file mode 100644
index 0000000000000000000000000000000000000000..0a6ced00636e003bd82c8b8f215196ac3306aae1
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/blockMeshDict
@@ -0,0 +1,53 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      blockMeshDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+scale   1;
+
+vertices
+(
+    (0 0 0)
+    (1 0 0)
+    (1 2 0)
+    (0 2 0)
+    (0 0 1)
+    (1 0 1)
+    (1 2 1)
+    (0 2 1)
+);
+
+blocks
+(
+    hex (0 1 2 3 4 5 6 7) (80 160 80) simpleGrading (1 1 1)
+);
+
+boundary
+(
+    walls
+    {
+        type wall;
+        faces
+        (
+            (3 7 6 2)
+            (0 4 7 3)
+            (2 6 5 1)
+            (1 5 4 0)
+            (0 3 2 1)
+            (4 5 6 7)
+        );
+    }
+);
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/controlDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/controlDict
new file mode 100644
index 0000000000000000000000000000000000000000..7d517d7bf779edf2c39edfb68a28b9ae651b4f83
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/controlDict
@@ -0,0 +1,57 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      controlDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+application     compressibleInterIsoFoam;
+
+startFrom       latestTime;
+
+startTime       0;
+
+stopAt          endTime;
+
+endTime         0.5;
+
+deltaT          0.0001;
+
+writeControl    adjustableRunTime;
+
+writeInterval   0.01;
+
+purgeWrite      0;
+
+writeFormat     binary;
+
+writePrecision  8;
+
+writeCompression off;
+
+timeFormat      general;
+
+timePrecision   10;
+
+runTimeModifiable yes;
+
+adjustTimeStep  yes;
+
+maxCo           0.5;
+
+maxAlphaCo      0.5;
+
+maxDeltaT       1;
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/decomposeParDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/decomposeParDict
new file mode 100644
index 0000000000000000000000000000000000000000..1a1deea863a53cf4d35811abec7dc81676da6774
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/decomposeParDict
@@ -0,0 +1,26 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    object      decomposeParDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+numberOfSubdomains 4;
+
+method          hierarchical;
+
+coeffs
+{
+    n           (1 4 1);
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/fvSchemes b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/fvSchemes
new file mode 100644
index 0000000000000000000000000000000000000000..281915333f391617b199d9398a8670ee4dab9bd9
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/fvSchemes
@@ -0,0 +1,59 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSchemes;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+ddtSchemes
+{
+    default         Euler;
+}
+
+gradSchemes
+{
+    default         Gauss linear;
+}
+
+divSchemes
+{
+    div(phi,alpha)  Gauss vanLeer;
+    div(phirb,alpha) Gauss linear;
+    div(phi,thermo:rho.water) Gauss upwind;
+    div(phi,thermo:rho.air) Gauss upwind;
+    
+    div(rhoPhi,U)  Gauss upwind;
+    div(rhoPhi,T)  Gauss upwind;
+    div(rhoPhi,K)  Gauss upwind;
+    div(phi,p)      Gauss upwind;
+    div(phi,k)      Gauss upwind;
+
+    div(((rho*nuEff)*dev2(T(grad(U))))) Gauss linear;
+}
+
+laplacianSchemes
+{
+    default         Gauss linear uncorrected;
+}
+
+interpolationSchemes
+{
+    default         linear;
+}
+
+snGradSchemes
+{
+    default         uncorrected;
+}
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/fvSolution b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/fvSolution
new file mode 100644
index 0000000000000000000000000000000000000000..1890baebf39069786d3aac5c3fda980a9b96effe
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/fvSolution
@@ -0,0 +1,107 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      fvSolution;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+solvers
+{
+    "alpha.water.*"
+    {
+        nAlphaCorr      1;
+        nAlphaSubCycles 1;
+        cAlpha          1;
+
+        reconstructionScheme isoAlpha;
+        vof2IsoTol 1e-8;
+        surfCellTol 1e-6;
+        nAlphaBounds    3;
+        snapTol         1e-12;
+        clip            true;
+    }
+
+    "pcorr.*"
+    {
+        solver          PCG;
+        preconditioner
+        {
+            preconditioner  GAMG;
+            tolerance       1e-05;
+            relTol          0;
+            smoother        DICGaussSeidel;
+        }
+        tolerance       1e-05;
+        relTol          0;
+        maxIter         100;
+    }
+
+    ".*(rho|rhoFinal)"
+    {
+        solver          diagonal;
+    }
+
+    p_rgh
+    {
+        solver          GAMG;
+        tolerance       1e-10;
+        relTol          0.001;
+        smoother        DIC;
+    }
+
+    p_rghFinal
+    {
+        solver          PCG;
+        preconditioner
+        {
+            preconditioner  GAMG;
+            tolerance       1e-07;
+            relTol          0;
+            nVcycles        2;
+            smoother        DICGaussSeidel;
+            nPreSweeps      2;
+        }
+        tolerance       1e-10;
+        relTol          0;
+        maxIter         50;
+    }
+
+    UFinal
+    {
+        solver          smoothSolver;
+        smoother        GaussSeidel;
+        tolerance       1e-06;
+        relTol          0;
+        nSweeps         1;
+    }
+
+    "(T|k|B|nuTilda).*"
+    {
+        solver          smoothSolver;
+        smoother        symGaussSeidel;
+        tolerance       1e-08;
+        relTol          0;
+    }
+}
+
+PIMPLE
+{
+    momentumPredictor yes;
+    transonic       no;
+    nOuterCorrectors 1;
+    nCorrectors     3;
+    nNonOrthogonalCorrectors 0;
+}
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/setFieldsDict b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/setFieldsDict
new file mode 100644
index 0000000000000000000000000000000000000000..3fa72d5343191bb524ecfb9be08e6dea28a989ed
--- /dev/null
+++ b/tutorials/multiphase/compressibleInterIsoFoam/laminar/depthCharge3D/system/setFieldsDict
@@ -0,0 +1,52 @@
+/*--------------------------------*- C++ -*----------------------------------*\
+| =========                 |                                                 |
+| \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
+|  \\    /   O peration     | Version:  v2006                                 |
+|   \\  /    A nd           | Website:  www.openfoam.com                      |
+|    \\/     M anipulation  |                                                 |
+\*---------------------------------------------------------------------------*/
+FoamFile
+{
+    version     2.0;
+    format      ascii;
+    class       dictionary;
+    location    "system";
+    object      setFieldsDict;
+}
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+defaultFieldValues
+(
+    volScalarFieldValue alpha.water 1
+    volScalarFieldValue p_rgh 1e5
+    volScalarFieldValue p 1e5
+    volScalarFieldValue T 300
+);
+
+regions
+(
+    sphereToCell
+    {
+        origin  (0.5 0.5 0.5);
+        radius  0.1;
+
+        fieldValues
+        (
+            volScalarFieldValue alpha.water 0
+            volScalarFieldValue p_rgh 1e6
+            volScalarFieldValue p 1e6
+            volScalarFieldValue T 578
+        );
+    }
+    boxToCell
+    {
+        box (-10 1 -1) (10 10 1);
+        fieldValues
+        (
+            volScalarFieldValue alpha.water 0
+        );
+    }
+);
+
+
+// ************************************************************************* //
diff --git a/tutorials/multiphase/interIsoFoam/damBreak/Allclean b/tutorials/multiphase/interIsoFoam/damBreak/Allclean
index fb1f3847301c377e02e12439ba58cbf303af3ef9..02237030276d6ec77684aa5e1c1d323f7fd88991 100755
--- a/tutorials/multiphase/interIsoFoam/damBreak/Allclean
+++ b/tutorials/multiphase/interIsoFoam/damBreak/Allclean
@@ -5,4 +5,6 @@ cd "${0%/*}" || exit                                # Run from this directory
 
 cleanCase0
 
+rm -rf isoFaces sequencedVTK
+
 #------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/interIsoFoam/damBreak/Allrun b/tutorials/multiphase/interIsoFoam/damBreak/Allrun
index cc36822e88765b83d3e0074bffb6d56f150595d3..21b3ad0ed3e0c70c2c73a554dca7c94456baeace 100755
--- a/tutorials/multiphase/interIsoFoam/damBreak/Allrun
+++ b/tutorials/multiphase/interIsoFoam/damBreak/Allrun
@@ -10,5 +10,5 @@ runApplication blockMesh
 runApplication setFields
 
 runApplication $(getApplication)
-
+foamSequenceVTKFiles -vtp
 #------------------------------------------------------------------------------
diff --git a/tutorials/multiphase/interIsoFoam/damBreak/system/controlDict b/tutorials/multiphase/interIsoFoam/damBreak/system/controlDict
index f777a69ecf022c0ff98de8f29332b479deda681a..58b788c0b82c685b1fbe6b20723134c1690c037f 100644
--- a/tutorials/multiphase/interIsoFoam/damBreak/system/controlDict
+++ b/tutorials/multiphase/interIsoFoam/damBreak/system/controlDict
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -23,7 +23,7 @@ startTime       0;
 
 stopAt          endTime;
 
-endTime         2;
+endTime         1;
 
 deltaT          0.001;
 
@@ -54,4 +54,29 @@ maxAlphaCo      0.5;
 maxDeltaT       1;
 
 
+functions
+{
+    surfaces
+    {
+        type            surfaces;
+        libs            ("libsampling.so");
+        writeControl    writeTime;
+
+        surfaceFormat   vtp;
+        fields          (p U);
+
+        interpolationScheme cell;
+
+        surfaces
+        (
+            freeSurf
+            {
+                type            interface;
+                interpolate     false;
+            }
+
+        );
+    }
+}
+
 // ************************************************************************* //
diff --git a/tutorials/multiphase/interIsoFoam/damBreak/system/fvSolution b/tutorials/multiphase/interIsoFoam/damBreak/system/fvSolution
index 6b2ebe597ef5e0a23677951ca118966cd9eb240d..9cab438115f041c4266b5ae5ec28a3cd394bbab2 100644
--- a/tutorials/multiphase/interIsoFoam/damBreak/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/damBreak/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -24,6 +24,7 @@ solvers
         nAlphaBounds    3;
         snapTol         1e-12;
         clip            true;
+        reconstructionScheme isoAlpha;
 
         nAlphaSubCycles 1;
         cAlpha          1; // Note: cAlpha is not used by isoAdvector but must
@@ -43,14 +44,14 @@ solvers
     {
         solver          GAMG;
         smoother        DICGaussSeidel;
-        tolerance       1e-07;
+        tolerance       1e-09;
         relTol          0.05;
     }
 
     p_rghFinal
     {
         $p_rgh;
-        tolerance       1e-07;
+        tolerance       1e-09;
         relTol          0;
     }
 
diff --git a/tutorials/multiphase/interIsoFoam/damBreakWithObstacle/system/fvSolution b/tutorials/multiphase/interIsoFoam/damBreakWithObstacle/system/fvSolution
index 2e43fdd84e966d36b6104472978ccc684025b931..1055760c6c2bab5d636d4645923b1dd185dd4ec9 100644
--- a/tutorials/multiphase/interIsoFoam/damBreakWithObstacle/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/damBreakWithObstacle/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -27,6 +27,7 @@ solvers
         writeSurfCells  false;
         writeBoundedCells false;
         writeIsoFaces   false;
+        reconstructionScheme plicRDF; // isoAlpha
 
         nAlphaCorr      1;
         nAlphaSubCycles 1;
diff --git a/tutorials/multiphase/interIsoFoam/discInConstantFlow/system/fvSolution b/tutorials/multiphase/interIsoFoam/discInConstantFlow/system/fvSolution
index 9eca06945a32d2469064ac5e17354232375fbe22..0064e91fec483b4cef90182f528aebe4032325fe 100644
--- a/tutorials/multiphase/interIsoFoam/discInConstantFlow/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/discInConstantFlow/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -26,6 +26,7 @@ solvers
         clip            false;
         cAlpha          1;
         nAlphaSubCycles 1;
+        reconstructionScheme plicRDF; // isoAlpha
     }
 }
 
diff --git a/tutorials/multiphase/interIsoFoam/discInConstantFlowCyclicBCs/system/fvSolution b/tutorials/multiphase/interIsoFoam/discInConstantFlowCyclicBCs/system/fvSolution
index ca8558730b5b21bcd34f03993d490bd7dc4b300d..57e8c9f2abd06f59d79d8cfe5a86ee20bc19b429 100644
--- a/tutorials/multiphase/interIsoFoam/discInConstantFlowCyclicBCs/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/discInConstantFlowCyclicBCs/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -25,6 +25,7 @@ solvers
         snapTol         1e-10;
         nAlphaBounds    3;
         clip            true;
+        reconstructionScheme isoAlpha; // isoAlpha
 
         nAlphaCorr      2;
         nAlphaSubCycles 1;
diff --git a/tutorials/multiphase/interIsoFoam/discInReversedVortexFlow/system/fvSolution b/tutorials/multiphase/interIsoFoam/discInReversedVortexFlow/system/fvSolution
index 8888d89ec34663b031b0da15f2c78cb2a4a27d57..cd741f6105c69a90137938489a35b96058979a07 100644
--- a/tutorials/multiphase/interIsoFoam/discInReversedVortexFlow/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/discInReversedVortexFlow/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -27,6 +27,7 @@ solvers
 
         nAlphaSubCycles 1;
         cAlpha          1;
+        reconstructionScheme plicRDF; // isoAlpha
     }
 }
 
diff --git a/tutorials/multiphase/interIsoFoam/iobasin/system/fvSolution b/tutorials/multiphase/interIsoFoam/iobasin/system/fvSolution
index c65a3141132432934896faf4d1ac5a7d9441f936..e6094374ecf28e9fb39fdca62a61ff075c1602fd 100644
--- a/tutorials/multiphase/interIsoFoam/iobasin/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/iobasin/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -21,6 +21,12 @@ solvers
     {
         nAlphaSubCycles 1;
         cAlpha          1;
+        reconstructionScheme isoAlpha; // plicRDF
+        isoFaceTol      1e-8;
+        surfCellTol     1e-6;
+        nAlphaBounds    3;
+        snapTol         0;
+        clip            false;
     }
 
     "pcorr.*"
diff --git a/tutorials/multiphase/interIsoFoam/notchedDiscInSolidBodyRotation/system/fvSolution b/tutorials/multiphase/interIsoFoam/notchedDiscInSolidBodyRotation/system/fvSolution
index f8e6297298e5136f186f5d789afad8c9d9e793da..212bd37a6ea52c5b8c70deaeed2947ee1caf3230 100644
--- a/tutorials/multiphase/interIsoFoam/notchedDiscInSolidBodyRotation/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/notchedDiscInSolidBodyRotation/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -26,6 +26,7 @@ solvers
         clip            false;
         nAlphaSubCycles 1;
         cAlpha          1;
+        reconstructionScheme isoAlpha; // plicRDF
     }
 }
 
diff --git a/tutorials/multiphase/interIsoFoam/sloshingTank2D/system/fvSolution b/tutorials/multiphase/interIsoFoam/sloshingTank2D/system/fvSolution
index 78da1382a17e8259363a46624b5994d6cb392026..8e67341327c2b51825c6d95306a99267b9b24f6b 100644
--- a/tutorials/multiphase/interIsoFoam/sloshingTank2D/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/sloshingTank2D/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -28,6 +28,7 @@ solvers
         nAlphaBounds    3;
         snapTol         1e-12;
         clip            true;
+        reconstructionScheme isoAlpha; // plicRDF
     }
 
     "pcorr.*"
diff --git a/tutorials/multiphase/interIsoFoam/sphereInReversedVortexFlow/system/fvSolution b/tutorials/multiphase/interIsoFoam/sphereInReversedVortexFlow/system/fvSolution
index 296bb37513e4b30e3017eb3cd9daf77ef247be03..7cf62d33b93426f2043ff33d0bcd0e92cf6980d1 100644
--- a/tutorials/multiphase/interIsoFoam/sphereInReversedVortexFlow/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/sphereInReversedVortexFlow/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -22,10 +22,11 @@ solvers
         isoFaceTol      1e-8;
         surfCellTol     1e-8;
         snapTol         0;
-        nAlphaBounds    4;
+        nAlphaBounds    8;
         clip            false;
         nAlphaSubCycles 1;
         cAlpha          1;
+        reconstructionScheme isoAlpha;
     }
 }
 
diff --git a/tutorials/multiphase/interIsoFoam/standingWave/system/fvSolution b/tutorials/multiphase/interIsoFoam/standingWave/system/fvSolution
index a008fb37fe247c338cf5273f2b4cc977a77eaa59..1f81d8863c4146ebb2dbbb2f311869393176499b 100644
--- a/tutorials/multiphase/interIsoFoam/standingWave/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/standingWave/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -27,6 +27,7 @@ solvers
 
         nAlphaSubCycles 1;
         cAlpha          1;
+        reconstructionScheme isoAlpha; // plicRDF
     }
 
     "pcorr.*"
diff --git a/tutorials/multiphase/interIsoFoam/waveExampleStreamFunction/system/fvSolution b/tutorials/multiphase/interIsoFoam/waveExampleStreamFunction/system/fvSolution
index 7e05141e54b58348533a677be66437cba61130d5..d4b766f007be66ea6f1de4e2dc927c5618301fad 100644
--- a/tutorials/multiphase/interIsoFoam/waveExampleStreamFunction/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/waveExampleStreamFunction/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -29,13 +29,7 @@ solvers
         nAlphaSubCycles 1;
         cAlpha          1;
 
-        MULESCorr       yes;
-        nLimiterIter    5;
-
-        solver          smoothSolver;
-        smoother        symGaussSeidel;
-        tolerance       1e-8;
-        relTol          0;
+        reconstructionScheme plicRDF; // plicRDF
     }
 
     "pcorr.*"
diff --git a/tutorials/multiphase/interIsoFoam/weirOverflow/system/fvSolution b/tutorials/multiphase/interIsoFoam/weirOverflow/system/fvSolution
index 644ee773d2c58f88e3585867d68faf96dc93bef3..03fac114d04d530f41f82eda5d2e5c9c343f6730 100644
--- a/tutorials/multiphase/interIsoFoam/weirOverflow/system/fvSolution
+++ b/tutorials/multiphase/interIsoFoam/weirOverflow/system/fvSolution
@@ -1,7 +1,7 @@
 /*--------------------------------*- C++ -*----------------------------------*\
 | =========                 |                                                 |
 | \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox           |
-|  \\    /   O peration     | Version:  v1912                                 |
+|  \\    /   O peration     | Version:  v2006                                 |
 |   \\  /    A nd           | Website:  www.openfoam.com                      |
 |    \\/     M anipulation  |                                                 |
 \*---------------------------------------------------------------------------*/
@@ -28,6 +28,7 @@ solvers
         cAlpha          1; // Note: cAlpha is not used by isoAdvector but must
                            // be specified because interfacePropertes object
                            // reads it during construction.
+        reconstructionScheme isoAlpha; // plicRDF
     }
 
     "pcorr.*"