electricPotential.C
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration |
5  \\ / A nd | www.openfoam.com
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8  Copyright (C) 2021 OpenCFD Ltd.
9 -------------------------------------------------------------------------------
10 License
11  This file is part of OpenFOAM.
12 
13  OpenFOAM is free software: you can redistribute it and/or modify it
14  under the terms of the GNU General Public License as published by
15  the Free Software Foundation, either version 3 of the License, or
16  (at your option) any later version.
17 
18  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21  for more details.
22 
23  You should have received a copy of the GNU General Public License
24  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25 
26 \*---------------------------------------------------------------------------*/
27 
28 #include "electricPotential.H"
29 #include "fvc.H"
30 #include "fvm.H"
31 #include "calculatedFvPatchField.H"
33 
34 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
35 
36 namespace Foam
37 {
38 namespace functionObjects
39 {
40  defineTypeNameAndDebug(electricPotential, 0);
41  addToRunTimeSelectionTable(functionObject, electricPotential, dictionary);
42 }
43 }
44 
45 
46 // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
47 
49 Foam::functionObjects::electricPotential::operandField()
50 {
51  if (!foundObject<volScalarField>(fieldName_))
52  {
53  auto tfldPtr = tmp<volScalarField>::New
54  (
55  IOobject
56  (
57  fieldName_,
58  mesh_.time().timeName(),
59  mesh_,
62  ),
63  mesh_
64  );
65  store(fieldName_, tfldPtr);
66  }
67 
68  return lookupObjectRef<volScalarField>(fieldName_);
69 }
70 
71 
73 Foam::functionObjects::electricPotential::sigma() const
74 {
75  const IOobject sigmaIO
76  (
77  IOobject::scopedName(typeName, "sigma"),
78  mesh_.time().timeName(),
79  mesh_.time(),
82  false
83  );
84 
85  if (phases_.size())
86  {
87  tmp<volScalarField> tsigma = phases_[0]*sigmas_[0];
88 
89  for (label i = 1; i < phases_.size(); ++i)
90  {
91  tsigma.ref() += phases_[i]*sigmas_[i];
92  }
93 
95  (
96  sigmaIO,
97  tsigma,
98  calculatedFvPatchField<scalar>::typeName
99  );
100  }
101 
103  (
104  sigmaIO,
105  mesh_,
106  sigma_,
107  calculatedFvPatchField<scalar>::typeName
108  );
109 }
110 
111 
113 Foam::functionObjects::electricPotential::epsilonm() const
114 {
115  // Vacuum permittivity (aka the electric constant) [A^2 s^4/(kg m^3)]
117  (
119  8.8541878128e-12 // CODATA value
120  );
121 
122  const IOobject epsilonrIO
123  (
124  IOobject::scopedName(typeName, "epsilonr"),
125  mesh_.time().timeName(),
126  mesh_.time(),
129  false
130  );
131 
132  if (phases_.size())
133  {
134  tmp<volScalarField> tepsilonr = phases_[0]*epsilonrs_[0];
135 
136  for (label i = 1; i < phases_.size(); ++i)
137  {
138  tepsilonr.ref() += phases_[i]*epsilonrs_[i];
139  }
140 
142  (
143  epsilonrIO,
144  epsilon0*tepsilonr,
145  calculatedFvPatchField<scalar>::typeName
146  );
147  }
148 
150  (
151  epsilonrIO,
152  mesh_,
153  epsilon0*epsilonr_,
154  calculatedFvPatchField<scalar>::typeName
155  );
156 }
157 
158 
159 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
160 
161 Foam::functionObjects::electricPotential::electricPotential
162 (
163  const word& name,
164  const Time& runTime,
165  const dictionary& dict
166 )
167 :
169  phasesDict_(dict.subOrEmptyDict("phases")),
170  phaseNames_(),
171  phases_(),
172  sigmas_(),
173  sigma_
174  (
176  (
178  dict.getCheckOrDefault<scalar>
179  (
180  "sigma",
181  scalar(1),
182  scalarMinMax::ge(SMALL)
183  )
184  )
185  ),
186  epsilonrs_(),
187  epsilonr_
188  (
190  (
191  dimless,
192  dict.getCheckOrDefault<scalar>
193  (
194  "epsilonr",
195  scalar(1),
196  scalarMinMax::ge(SMALL)
197  )
198  )
199  ),
200  fieldName_
201  (
202  dict.getOrDefault<word>
203  (
204  "field",
205  IOobject::scopedName(typeName, "V")
206  )
207  ),
208  nCorr_(1),
209  writeDerivedFields_(false)
210 {
211  read(dict);
212 
213  // Force creation of transported field so any BCs using it can
214  // look it up
215  volScalarField& eV = operandField();
217 }
218 
219 
220 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
221 
223 {
225  {
226  Log << type() << " read: " << name() << endl;
227 
228  dict.readIfPresent("sigma", sigma_);
229  dict.readIfPresent("epsilonr", epsilonr_);
230  dict.readIfPresent("nCorr", nCorr_);
231  dict.readIfPresent("writeDerivedFields", writeDerivedFields_);
232 
233  // If flow is multiphase
234  if (!phasesDict_.empty())
235  {
236  phaseNames_.setSize(phasesDict_.size());
237  phases_.setSize(phasesDict_.size());
238  sigmas_.setSize(phasesDict_.size());
239 
240  if (writeDerivedFields_)
241  {
242  epsilonrs_.setSize(phasesDict_.size());
243  }
244 
245  label phasei = 0;
246  for (const entry& dEntry : phasesDict_)
247  {
248  const word& key = dEntry.keyword();
249 
250  if (!dEntry.isDict())
251  {
252  FatalIOErrorInFunction(phasesDict_)
253  << "Entry " << key << " is not a dictionary" << nl
254  << exit(FatalIOError);
255  }
256 
257  const dictionary& subDict = dEntry.dict();
258 
259  phaseNames_[phasei] = key;
260 
261  sigmas_.set
262  (
263  phasei,
265  (
267  subDict.getCheck<scalar>
268  (
269  "sigma",
270  scalarMinMax::ge(SMALL)
271  )
272  )
273  );
274 
275  if (writeDerivedFields_)
276  {
277  epsilonrs_.set
278  (
279  phasei,
281  (
282  dimless,
283  subDict.getCheck<scalar>
284  (
285  "epsilonr",
286  scalarMinMax::ge(SMALL)
287  )
288  )
289  );
290  }
291 
292  ++phasei;
293  }
294 
295  forAll(phaseNames_, i)
296  {
297  phases_.set
298  (
299  i,
300  mesh_.getObjectPtr<volScalarField>(phaseNames_[i])
301  );
302  }
303  }
304 
305  return true;
306  }
307 
308  return false;
309 }
310 
311 
313 {
314  Log << type() << " execute: " << name() << endl;
315 
316  tmp<volScalarField> tsigma = this->sigma();
317  const volScalarField& sigma = tsigma();
318 
319  volScalarField& eV = operandField();
320 
321  for (label i = 1; i <= nCorr_; ++i)
322  {
323  fvScalarMatrix eVEqn
324  (
325  - fvm::laplacian(sigma, eV)
326  );
327 
328  eVEqn.relax();
329 
330  eVEqn.solve();
331  }
332 
333  Log << endl;
334 
335  return true;
336 }
337 
338 
340 {
341  Log << type() << " write: " << name() << nl
342  << tab << fieldName_
343  << endl;
344 
345  volScalarField& eV = operandField();
346 
347  if (writeDerivedFields_)
348  {
349  // Write the electric field
350  const volVectorField E
351  (
352  IOobject
353  (
354  IOobject::scopedName(typeName, "E"),
355  mesh_.time().timeName(),
356  mesh_.time(),
359  false
360  ),
361  -fvc::grad(eV),
363  );
364 
365  Log << tab << E.name() << endl;
366 
367  E.write();
368 
369 
370  // Write the current density field
371  tmp<volScalarField> tsigma = this->sigma();
372 
373  auto eJ = tmp<volVectorField>::New
374  (
375  IOobject
376  (
377  IOobject::scopedName(typeName, "J"),
378  mesh_.time().timeName(),
379  mesh_.time(),
382  false
383  ),
384  -tsigma*fvc::grad(eV),
386  );
387 
388  Log << tab << eJ().name() << endl;
389 
390  eJ->write();
391 
392 
393  // Write the free-charge density field
394  tmp<volScalarField> tepsilonm = this->epsilonm();
395 
396  auto erho = tmp<volScalarField>::New
397  (
398  IOobject
399  (
400  IOobject::scopedName(typeName, "rho"),
401  mesh_.time().timeName(),
402  mesh_.time(),
405  false
406  ),
407  fvc::div(tepsilonm*E),
409  );
410 
411  Log << tab << erho().name() << endl;
412 
413  erho->write();
414  }
415 
416  eV.write();
417 
418  return true;
419 }
420 
421 
422 // ************************************************************************* //
Foam::entry
A keyword and a list of tokens is an 'entry'.
Definition: entry.H:67
Foam::IOobject::NO_WRITE
Definition: IOobject.H:195
runTime
engineTime & runTime
Definition: createEngineTime.H:13
Foam::IOobject
Defines the attributes of an object for which implicit objectRegistry management is supported,...
Definition: IOobject.H:169
Log
#define Log
Definition: PDRblock.C:35
Foam::fvc::grad
tmp< GeometricField< typename outerProduct< vector, Type >::type, fvPatchField, volMesh >> grad(const GeometricField< Type, fvsPatchField, surfaceMesh > &ssf)
Definition: fvcGrad.C:54
Foam::Time
Class to control time during OpenFOAM simulations that is also the top-level objectRegistry.
Definition: Time.H:73
Foam::word
A class for handling words, derived from Foam::string.
Definition: word.H:65
Foam::dimLength
const dimensionSet dimLength(0, 1, 0, 0, 0, 0, 0)
Definition: dimensionSets.H:52
Foam::tmp
A class for managing temporary objects.
Definition: PtrList.H:61
Foam::functionObjects::electricPotential::read
virtual bool read(const dictionary &dict)
Read the function object data.
Definition: electricPotential.C:222
Foam::read
bool read(const char *buf, int32_t &val)
Same as readInt32.
Definition: int32.H:108
Foam::Time::timeName
static word timeName(const scalar t, const int precision=precision_)
Definition: Time.C:780
Foam::glTF::key
auto key(const Type &t) -> typename std::enable_if< std::is_enum< Type >::value, typename std::underlying_type< Type >::type >::type
Definition: foamGltfBase.H:108
calculatedFvPatchField.H
Foam::fvc::div
tmp< GeometricField< Type, fvPatchField, volMesh > > div(const GeometricField< Type, fvsPatchField, surfaceMesh > &ssf)
Definition: fvcDiv.C:49
phasei
label phasei
Definition: pEqn.H:27
electricPotential.H
Foam::FatalIOError
IOerror FatalIOError
Foam::endl
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:369
Foam::functionObjects::regionFunctionObject::store
bool store(word &fieldName, const tmp< ObjectType > &tfield, bool cacheable=false)
Store the field in the (sub) objectRegistry under the given name.
Definition: regionFunctionObjectTemplates.C:107
Foam::functionObjects::fvMeshFunctionObject
Specialization of Foam::functionObject for an Foam::fvMesh, providing a reference to the Foam::fvMesh...
Definition: fvMeshFunctionObject.H:64
Foam::constant::electromagnetic::epsilon0
const dimensionedScalar epsilon0
Electric constant: default SI units: [F/m].
forAll
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:296
Foam::dimCurrent
const dimensionSet dimCurrent(0, 0, 0, 0, 0, 1, 0)
Definition: dimensionSets.H:56
Foam::dimTime
const dimensionSet dimTime(0, 0, 1, 0, 0, 0, 0)
Definition: dimensionSets.H:53
Foam::pow4
dimensionedScalar pow4(const dimensionedScalar &ds)
Definition: dimensionedScalar.C:100
Foam::pow3
dimensionedScalar pow3(const dimensionedScalar &ds)
Definition: dimensionedScalar.C:89
Foam::fvm::laplacian
tmp< fvMatrix< Type > > laplacian(const GeometricField< Type, fvPatchField, volMesh > &vf, const word &name)
Definition: fvmLaplacian.C:48
Foam::fvMatrix::relax
void relax(const scalar alpha)
Relax matrix (for steady-state solution).
Definition: fvMatrix.C:1183
Foam::dimensionedScalar
dimensioned< scalar > dimensionedScalar
Dimensioned scalar obtained from generic dimensioned type.
Definition: dimensionedScalarFwd.H:42
dict
dictionary dict
Definition: searchingEngine.H:14
fvm.H
Foam::dictionary
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:123
Foam::functionObjects::regionFunctionObject::read
virtual bool read(const dictionary &dict)
Read optional controls.
Definition: regionFunctionObject.C:173
addToRunTimeSelectionTable.H
Macros for easy insertion into run-time selection tables.
Foam::dimensioned< scalar >
Foam::Ostream::write
virtual bool write(const token &tok)=0
Write token to stream or otherwise handle it.
Foam::calculatedFvPatchField
This boundary condition is not designed to be evaluated; it is assmued that the value is assigned via...
Definition: calculatedFvPatchField.H:66
Foam
Namespace for OpenFOAM.
Definition: atmBoundaryLayer.C:33
Foam::dimMass
const dimensionSet dimMass(1, 0, 0, 0, 0, 0, 0)
Definition: dimensionSets.H:51
Foam::exit
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:130
Foam::GeometricField::correctBoundaryConditions
void correctBoundaryConditions()
Correct boundary field.
Definition: GeometricField.C:940
Foam::sqr
dimensionedSymmTensor sqr(const dimensionedVector &dv)
Definition: dimensionedSymmTensor.C:51
Foam::tab
constexpr char tab
Definition: Ostream.H:403
Foam::nl
constexpr char nl
Definition: Ostream.H:404
Foam::functionObjects::addToRunTimeSelectionTable
addToRunTimeSelectionTable(functionObject, ObukhovLength, dictionary)
Foam::MinMax::ge
static MinMax< T > ge(const T &minVal)
A semi-infinite range from minVal to the type max.
Definition: MinMaxI.H:31
Foam::type
fileName::Type type(const fileName &name, const bool followLink=true)
Return the file type: DIRECTORY or FILE, normally following symbolic links.
Definition: MSwindows.C:590
Foam::functionObjects::fvMeshFunctionObject::mesh_
const fvMesh & mesh_
Reference to the fvMesh.
Definition: fvMeshFunctionObject.H:73
Foam::constant::electromagnetic::e
const dimensionedScalar e
Elementary charge.
Definition: createFields.H:11
Foam::tmp::New
static tmp< T > New(Args &&... args)
Construct tmp of T with forwarding arguments.
Foam::functionObjects::defineTypeNameAndDebug
defineTypeNameAndDebug(ObukhovLength, 0)
Foam::dictionary::getCheck
T getCheck(const word &keyword, const Predicate &pred, enum keyType::option matchOpt=keyType::REGEX) const
Definition: dictionaryTemplates.C:120
Foam::fvMatrix
A special matrix type and solver, designed for finite volume solutions of scalar equations....
Definition: fvPatchField.H:68
Foam::fvMatrix::solve
SolverPerformance< Type > solve(const dictionary &)
Solve returning the solution statistics.
Definition: fvMatrixSolve.C:319
fvc.H
Foam::name
word name(const expressions::valueTypeCode typeCode)
A word representation of a valueTypeCode. Empty for INVALID.
Definition: exprTraits.C:59
Foam::fvMesh::time
const Time & time() const
Return the top-level database.
Definition: fvMesh.H:280
Foam::functionObjects::electricPotential::execute
virtual bool execute()
Calculate the function object.
Definition: electricPotential.C:312
FatalIOErrorInFunction
#define FatalIOErrorInFunction(ios)
Report an error message using Foam::FatalIOError.
Definition: error.H:473
sigma
dimensionedScalar sigma("sigma", dimMass/sqr(dimTime), transportProperties)
Foam::IOobject::scopedName
static word scopedName(const std::string &scope, const word &name)
Create scope:name or scope_name string.
Definition: IOobjectI.H:47
Foam::functionObjects::electricPotential::write
virtual bool write()
Write the function object output.
Definition: electricPotential.C:339
Foam::GeometricField< scalar, fvPatchField, volMesh >
Foam::IOobject::NO_READ
Definition: IOobject.H:188
Foam::dimless
const dimensionSet dimless
Dimensionless.
Definition: dimensionSets.C:189
Foam::IOobject::MUST_READ
Definition: IOobject.H:185