542 auto elementI = intersection.inside();
543 auto elementJ = intersection.outside();
545 const CellData& cellDataJ = problem_.variables().cellData(problem_.variables().index(elementJ));
548 const GlobalPosition& globalPosI = elementI.geometry().center();
549 const GlobalPosition& globalPosJ = elementJ.geometry().center();
552 Scalar volume = elementI.geometry().volume();
554 Scalar porosity = max(problem_.spatialParams().porosity(elementI), porosityThreshold_);
556 if (compressibility_)
558 viscosity_[wPhaseIdx] = cellDataI.viscosity(wPhaseIdx);
559 viscosity_[nPhaseIdx] = cellDataI.viscosity(nPhaseIdx);
563 int isIndex = intersection.indexInInside();
565 GlobalPosition unitOuterNormal = intersection.centerUnitOuterNormal();
567 unitOuterNormal *= -1.0;
569 Scalar faceArea = intersection.geometry().volume();
571 if (
velocity().calculateVelocityInTransport() && !cellDataI.fluxData().haveVelocity(isIndex))
572 velocity().calculateVelocity(intersection, cellDataI);
575 Scalar factorW = (cellDataI.fluxData().
velocity(wPhaseIdx, isIndex) * unitOuterNormal) * faceArea;
576 Scalar factorNw = (cellDataI.fluxData().
velocity(nPhaseIdx, isIndex) * unitOuterNormal) * faceArea;
577 Scalar factorTotal = factorW + factorNw;
580 GlobalPosition distVec = globalPosJ - globalPosI;
582 Scalar dist = distVec.two_norm();
584 bool takeNeighbor = (elementI.level() < elementJ.level());
587 (takeNeighbor) ? !cellDataJ.fluxData().isUpwindCell(wPhaseIdx, intersection.indexInOutside()) :
588 cellDataI.fluxData().isUpwindCell(wPhaseIdx, isIndex);
590 (takeNeighbor) ? !cellDataJ.fluxData().isUpwindCell(nPhaseIdx, intersection.indexInOutside()) :
591 cellDataI.fluxData().isUpwindCell(nPhaseIdx, isIndex);
599 lambdaW = cellDataI.mobility(wPhaseIdx);
600 if (compressibility_)
602 lambdaW /= cellDataI.density(wPhaseIdx);
607 lambdaW = cellDataJ.mobility(wPhaseIdx);
608 if (compressibility_)
610 lambdaW /= cellDataJ.density(wPhaseIdx);
616 lambdaNw = cellDataI.mobility(nPhaseIdx);
617 if (compressibility_)
619 lambdaNw /= cellDataI.density(nPhaseIdx);
624 lambdaNw = cellDataJ.mobility(nPhaseIdx);
625 if (compressibility_)
627 lambdaNw /= cellDataJ.density(nPhaseIdx);
631 switch (velocityType_)
636 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
637 viscosity_[nPhaseIdx], factorTotal, intersection);
640 Scalar satWI = cellDataI.saturation(wPhaseIdx);
641 Scalar satWJ = cellDataJ.saturation(wPhaseIdx);
643 Scalar pcI = cellDataI.capillaryPressure();
644 Scalar pcJ = cellDataJ.capillaryPressure();
647 GlobalPosition pcGradient = unitOuterNormal;
648 pcGradient *= (pcI - pcJ) / dist;
652 capillaryFlux().getFlux(flux, intersection, satWI, satWJ, pcGradient);
656 gravityFlux().getFlux(flux, intersection, satWI, satWJ);
657 Scalar
gravityFlux = (flux * unitOuterNormal * faceArea);
659 switch (saturationType_)
664 factorTotal *= lambdaW / (lambdaW + lambdaNw);
670 factorTotal *= lambdaNw / (lambdaW + lambdaNw);
680 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
682 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
683 viscosity_[nPhaseIdx], 10 *
gravityFlux, intersection);
689 if (compressibility_)
691 factorW /= cellDataI.density(wPhaseIdx);
692 factorNw /= cellDataI.density(nPhaseIdx);
696 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
697 viscosity_[nPhaseIdx], factorW, intersection, wPhaseIdx);
698 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
699 viscosity_[nPhaseIdx], factorNw, intersection, nPhaseIdx);
705 switch (velocityType_)
708 update -= factorTotal / (volume * porosity);
711 switch (saturationType_)
714 update -= factorW / (volume * porosity);
717 update -= factorNw / (volume * porosity);
735 auto elementI = intersection.inside();
738 const GlobalPosition& globalPosI = elementI.geometry().center();
741 const GlobalPosition& globalPosJ = intersection.geometry().center();
744 Scalar volume = elementI.geometry().volume();
746 Scalar porosity = max(problem_.spatialParams().porosity(elementI), porosityThreshold_);
748 if (compressibility_)
750 viscosity_[wPhaseIdx] = cellDataI.viscosity(wPhaseIdx);
751 viscosity_[nPhaseIdx] = cellDataI.viscosity(nPhaseIdx);
755 int isIndex = intersection.indexInInside();
757 GlobalPosition unitOuterNormal = intersection.centerUnitOuterNormal();
759 unitOuterNormal *= -1.0;
761 Scalar faceArea = intersection.geometry().volume();
763 if (
velocity().calculateVelocityInTransport())
764 velocity().calculateVelocityOnBoundary(intersection, cellDataI);
767 Scalar factorW = (cellDataI.fluxData().
velocity(wPhaseIdx, isIndex) * unitOuterNormal) * faceArea;
768 Scalar factorNw = (cellDataI.fluxData().
velocity(nPhaseIdx, isIndex) * unitOuterNormal) * faceArea;
769 Scalar factorTotal = factorW + factorNw;
772 GlobalPosition distVec = globalPosJ - globalPosI;
775 Scalar dist = distVec.two_norm();
778 BoundaryTypes bcType;
779 problem_.boundaryTypes(bcType, intersection);
780 PrimaryVariables boundValues(0.0);
782 if (bcType.isDirichlet(satEqIdx))
784 problem_.dirichlet(boundValues, intersection);
786 Scalar satBound = boundValues[saturationIdx];
789 Scalar satWI = cellDataI.saturation(wPhaseIdx);
790 Scalar satWBound = 0;
791 switch (saturationType_)
795 satWBound = satBound;
800 satWBound = 1 - satBound;
805 const auto fluidMatrixInteraction = problem_.spatialParams().fluidMatrixInteractionAtPos(elementI.geometry().center());
806 const Scalar pcBound = fluidMatrixInteraction.pc(satWBound);
812 if (cellDataI.fluxData().isUpwindCell(wPhaseIdx, isIndex))
814 lambdaW = cellDataI.mobility(wPhaseIdx);
815 if (compressibility_)
817 lambdaW /= cellDataI.density(wPhaseIdx);
822 if (compressibility_)
824 lambdaW = fluidMatrixInteraction.krw(satWBound)
825 / FluidSystem::viscosity(cellDataI.fluidState(), wPhaseIdx);
829 lambdaW = fluidMatrixInteraction.krw(satWBound)
830 / viscosity_[wPhaseIdx];
834 if (cellDataI.fluxData().isUpwindCell(nPhaseIdx, isIndex))
836 lambdaNw = cellDataI.mobility(nPhaseIdx);
837 if (compressibility_)
839 lambdaNw /= cellDataI.density(nPhaseIdx);
844 if (compressibility_)
846 lambdaNw = fluidMatrixInteraction.krn(satWBound)
847 / FluidSystem::viscosity(cellDataI.fluidState(), nPhaseIdx);
851 lambdaNw = fluidMatrixInteraction.krn(satWBound)
852 / viscosity_[nPhaseIdx];
856 switch (velocityType_)
860 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
861 viscosity_[nPhaseIdx], factorTotal, intersection);
863 Scalar pcI = cellDataI.capillaryPressure();
866 GlobalPosition pcGradient = unitOuterNormal;
867 pcGradient *= (pcI - pcBound) / dist;
871 capillaryFlux().getFlux(flux, intersection, satWI, satWBound, pcGradient);
875 gravityFlux().getFlux(flux, intersection, satWI, satWBound);
876 Scalar
gravityFlux = flux * unitOuterNormal * faceArea;
878 switch (saturationType_)
883 factorTotal *= lambdaW / (lambdaW + lambdaNw);
889 factorTotal *= lambdaNw / (lambdaW + lambdaNw);
891 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
892 viscosity_[nPhaseIdx], factorW, intersection, wPhaseIdx);
893 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
894 viscosity_[nPhaseIdx], factorNw, intersection, nPhaseIdx);
904 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
906 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
907 viscosity_[nPhaseIdx], 10 *
gravityFlux, intersection);
913 if (compressibility_)
915 factorW /= cellDataI.density(wPhaseIdx);
916 factorNw /= cellDataI.density(nPhaseIdx);
920 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
921 viscosity_[nPhaseIdx], factorW, intersection, wPhaseIdx);
922 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
923 viscosity_[nPhaseIdx], factorNw, intersection, nPhaseIdx);
930 if (bcType.isNeumann(satEqIdx))
932 problem_.neumann(boundValues, intersection);
933 factorW = boundValues[wPhaseIdx];
934 factorNw = boundValues[nPhaseIdx];
936 factorNw *= faceArea;
939 Scalar lambdaW, lambdaNw;
941 lambdaW = cellDataI.mobility(wPhaseIdx);
942 lambdaNw = cellDataI.mobility(nPhaseIdx);
943 if (compressibility_)
945 lambdaW /= cellDataI.density(wPhaseIdx);
946 lambdaNw /= cellDataI.density(nPhaseIdx);
947 factorW /= cellDataI.density(wPhaseIdx);
948 factorNw /= cellDataI.density(nPhaseIdx);
952 factorW /= density_[wPhaseIdx];
953 factorNw /= density_[nPhaseIdx];
956 switch (velocityType_)
961 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
962 viscosity_[nPhaseIdx], factorW + factorNw, intersection);
967 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
968 viscosity_[nPhaseIdx], factorW, intersection, wPhaseIdx);
969 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
970 viscosity_[nPhaseIdx], factorNw, intersection, nPhaseIdx);
977 if (bcType.isOutflow(satEqIdx))
980 Scalar lambdaW = cellDataI.mobility(wPhaseIdx);
981 Scalar lambdaNw = cellDataI.mobility(nPhaseIdx);
982 if (compressibility_)
984 lambdaW /= cellDataI.density(wPhaseIdx);
985 lambdaNw /= cellDataI.density(nPhaseIdx);
988 if (velocityType_ == vt)
990 switch (saturationType_)
995 factorTotal *= lambdaW / (lambdaW + lambdaNw);
996 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
997 viscosity_[nPhaseIdx], factorTotal, intersection);
1003 factorTotal *= lambdaNw / (lambdaW + lambdaNw);
1004 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
1005 viscosity_[nPhaseIdx], factorTotal, intersection);
1012 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
1013 viscosity_[nPhaseIdx], factorW, intersection, wPhaseIdx);
1014 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
1015 viscosity_[nPhaseIdx], factorNw, intersection, nPhaseIdx);
1018 switch (velocityType_)
1021 update -= factorTotal / (volume * porosity);
1024 switch (saturationType_)
1027 update -= factorW / (volume * porosity);
1030 update -= factorNw / (volume * porosity);
1048 Scalar volume = element.geometry().volume();
1051 Scalar porosity = max(problem_.spatialParams().porosity(element), porosityThreshold_);
1053 if (compressibility_)
1055 viscosity_[wPhaseIdx] = cellDataI.viscosity(wPhaseIdx);
1056 viscosity_[nPhaseIdx] = cellDataI.viscosity(nPhaseIdx);
1059 PrimaryVariables sourceVec(0.0);
1060 problem_.source(sourceVec, element);
1062 if (compressibility_)
1064 sourceVec[wPhaseIdx] /= cellDataI.density(wPhaseIdx);
1065 sourceVec[nPhaseIdx] /= cellDataI.density(nPhaseIdx);
1069 sourceVec[wPhaseIdx] /= density_[wPhaseIdx];
1070 sourceVec[nPhaseIdx] /= density_[nPhaseIdx];
1074 Scalar lambdaW = cellDataI.mobility(wPhaseIdx);
1075 Scalar lambdaNw = cellDataI.mobility(nPhaseIdx);
1076 if (compressibility_)
1078 lambdaW /= cellDataI.density(wPhaseIdx);
1079 lambdaNw /= cellDataI.density(nPhaseIdx);
1082 switch (saturationType_)
1086 if (sourceVec[wPhaseIdx] < 0 && cellDataI.saturation(wPhaseIdx) < threshold_)
1087 sourceVec[wPhaseIdx] = 0.0;
1089 update += sourceVec[wPhaseIdx] / porosity;
1094 if (sourceVec[nPhaseIdx] < 0 && cellDataI.saturation(nPhaseIdx) < threshold_)
1095 sourceVec[nPhaseIdx] = 0.0;
1097 update += sourceVec[nPhaseIdx] / porosity;
1102 switch (velocityType_)
1107 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx], viscosity_[nPhaseIdx],
1108 (sourceVec[wPhaseIdx] + sourceVec[nPhaseIdx]) * -1 * volume, element);
1114 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
1115 viscosity_[nPhaseIdx], sourceVec[wPhaseIdx] * -1 * volume, element,
1117 this->evalCflFluxFunction().addFlux(lambdaW, lambdaNw, viscosity_[wPhaseIdx],
1118 viscosity_[nPhaseIdx], sourceVec[nPhaseIdx] * -1 * volume, element,
1131 if (!compressibility_)
1133 const auto element = *problem_.gridView().template begin<0>();
1134 FluidState fluidState;
1135 fluidState.setPressure(wPhaseIdx, problem_.referencePressure(element));
1136 fluidState.setPressure(nPhaseIdx, problem_.referencePressure(element));
1137 fluidState.setTemperature(problem_.temperature(element));
1138 fluidState.setSaturation(wPhaseIdx, 1.);
1139 fluidState.setSaturation(nPhaseIdx, 0.);
1140 density_[wPhaseIdx] = FluidSystem::density(fluidState, wPhaseIdx);
1141 density_[nPhaseIdx] = FluidSystem::density(fluidState, nPhaseIdx);
1142 viscosity_[wPhaseIdx] = FluidSystem::viscosity(fluidState, wPhaseIdx);
1143 viscosity_[nPhaseIdx] = FluidSystem::viscosity(fluidState, nPhaseIdx);
1147 for (
const auto& element : elements(problem_.gridView()))
1149 PrimaryVariables initSol(0.0);
1150 problem_.initial(initSol, element);
1152 int eIdxGlobal = problem_.variables().index(element);
1154 CellData& cellData = problem_.variables().cellData(eIdxGlobal);
1156 switch (saturationType_)
1160 cellData.setSaturation(wPhaseIdx, initSol[saturationIdx]);
1161 cellData.setSaturation(nPhaseIdx, 1 - initSol[saturationIdx]);
1166 cellData.setSaturation(wPhaseIdx,1 -initSol[saturationIdx]);
1167 cellData.setSaturation(nPhaseIdx, initSol[saturationIdx]);
1174 velocity_->initialize();
1175 capillaryFlux_->initialize();
1176 gravityFlux_->initialize();