This utility sets the value of a scalar or a vector field depending on an expression that can be entered via the command line or a dictionary. It can also be used to set the value of fields on selected patches. It's like the setFields-utility on steroids.
It can be used to set non-uniform initial-conditions without programming.
Note: Active development of funkySetFields now takes place in swak4Foam so please have a look there for more up-to-date versions. Support for this version of funkySetFields is discontinued with OpenFOAM 2.0.
Contents
1 Before we begin
This utility is provided as-is and is a permanent Beta-Version (but it works fine for me, if it doesn't for you: tell me about it and I'll see what the problem is)
1.1 Words of warning
This utility can save you the work to program your own utility to set initial-conditions, but
- you should be familiar with the C++ expression syntax
- it makes it easier to 'shoot yourself in the foot' (do stupid things)
- especially for large cases a custom-made utility might be more efficient
(it's like a Swiss Army Knife: useful for a lot of things, but not necessarily the best tool for these tasks)
2 Pre-requisites
To compile this utility at least version 2.1 of Bison has to be installed. Check with
bison -V
on the command line before trying to compile it.
2.1 For those who don't have bison 2.1
It has been brought to my attention that there are a lot of people that still have to live with 1.x bisons. For those there is a script provided that inserts the generated sources. Just go to the source directory and call
./insertGenerated.sh
It copies the generated files to the directory and modifies Make/files
3 Usage
The utility can be used from the command line or with a dictionary. In both forms an option -time is needed to select the time step.
3.1 Basic command line usage
This mode is selected if the -field option is used to select a target field. If the target doesn't yet exist the option -create has to be added.
In addition an option -expression is needed with the expression that is to be written to the target field (Syntax see below).
An optional option is -condition: only cells for which this expression evaluates to true are overwritten with the expression. For all other cells the old value is kept.
expression and condition should be enclosed in quotes to keep the shell from interpreting special characters.
An example of the usage would be:
funkySetFields -case cavity -field U -expression '(grad(dist())^vector(0,0,-1))*mag(pos()-vector(0.05,0.05,0))/0.05' -time 0
This sets the velocity field to a 'circle' around the center. In the most simple case the velocity field can be set to zero
funkySetFields -case cavity -field U -expression 'vector(0,0,0)' -time 0
Same for the pressure field:
funkySetFields -case cavity -field p -expression '0' -time 0
The damBreak-tutorial could be initialized with
funkySetFields -case damBreak -time 0 -field gamma -expression " pos().x <= 0.1461 && pos().y <= 0.292 ? 1 : 0"
or (if you don't want to overwrite the whole gamma field):
funkySetFields -case damBreak -time 0 -field gamma -expression 1 -condition "pos().x <= 0.1461 && pos().y <= 0.292"
3.2 Advanced command line usage
For a newly created field the dimension can be specified with the -dimension-option.
Usually all the patches of the field (not the symmetry/wedge/...-stuff) are set to the type zeroGradient. With the option -keepPatches the patches are preserved from what was previously on the disk.
The option -valuePatches specifies a list of patches which shall be set to fixed value. The values are taken from the interior of the field.
3.2.1 Hot-Room Example
For instance to get a similar behaviour as the setHotRoom that sets the boundary conditions for the hotRoom-tutorial these commands are issued:
funkySetFields -case hotRoom -time 0 -field T -keepPatches -valuePatches "floor ceiling" -condition "pos().x>4.5 && pos().x<5.5 && pos().z>4.5 && pos().z<5.5 && pos().y<2" -expression "600." funkySetFields -case hotRoom -time 0 -field T -keepPatches -expression "300."
The first one sets the values on the patches, the second one clears the interior field.
3.2.2 Initialization of Free Surface on Sloping Bed
When initializing the water surface for simulations of waves over sub-merged bars, the computational cells will not be aligned with the Cartesian coordinate system. As a consequence the initial flat surface will become distorted. This distortion leads to fast moving surface waves in the simulation which it takes a long time to get rid of. Further they are the effective limiter on the time step in the first part of the simulation.
Different approaches of initializing the free surface surface using funkySetField (FSF), will be given in the following. It is assumed that the free surface is placed at y = 0. As the commands are rather long, the common part is given first, namely:
funkySetFields -case initWaveSurface -time 0 -field gamma -keepPatches -expression
a) An approach similar to the one given by the standard setFields:
In this, the expression only investigates whether the cell center is above or below the water surface. It looks like
"pos().y <= 0. ? 1.0 : 0."
b) An approach taking the face position into consideration
In this, the expression considers all faces on the individual cells. If the cell face position is above the water level, then the gamma field on that face is 0, if the face position is below the surface, then the gamma field on the face is set to 1. It looks like
"average(fpos().y < surf(0.) ? surf(1.0) : surf(0.))"
Note that as fpos().y is a surface scalar, then the scalars in the expression needs to be cast to surface scalar, this is done using the "surf" function.
c) An approach taking the face position together with the extension of the face in the vertical direction into consideration
In this, the length of the projection of the face onto the y-axis, fproj().y, is taken into consideration. Assuming that the horizontal edges pointing into the paper are parallel with the z-axis and that the position of the face center is in the mid-point of the projection onto the y-axis, a more refined model can be defined. If fpos().y + 0.5 fproj().y is below the water surface, then the entire face is wet. The same argument can be used for dry faces. If the condition is not fulfilled, the face is only partial wet, thus the gamma field get a value of '0.5 - fpos().y / fproj().y', which basicly is due to an assumption of constant width of the face. Averaging over all the faces gives a cell value for gamma. The expression look as follows
"average((fpos().y + surf(0.5) * fproj().y) < (surf(0.)) ? surf(1.0) : ((fpos().y - surf(0.5) * fproj().y) > surf(0.0) ? surf(0.0) : (surf(0.5) - fpos().y / (fproj().y + surf(0.00000001)))))"
Again note the usage of "surf" and further the addition of 0.00000001 in the denominator. This is because the " <> ? <> : <>"-expression evaluates everything before choosing, and horizontal faces has fproj().y = 0.
The conclusion is that the more information which is used in the initialization process, the more smooth the free surface becomes. See this thread in the discussion board for figures.
3.3 Dictionary usage
In the dictionary funkySetFieldsDict a list of dictionaries named expressions is read and one dictionary is evaluated after another. The title of the dictionaries is only used for documentation. In each dictionary there can be 3 entries:
- field
- the target field
- expression
- the expression to write to the field
- condition
- select a subset of the cells (this is optional)
- keepPatches
- see command line options (optional)
- create
- see command line options (optional)
- valuePatches
- see command line options (optional)
- dimension
- see command line options (optional)
An example dictionary would be:
expressions ( circleVel { field U; expression "(grad(dist())^vector(0,0,-1))*mag(pos()-vector(0.05,0.05,0))/0.05"; } pressure1 { field p; expression "10.*(0.1-pos().y)"; } pressure2 { field p; expression "p+U&U"; condition "pos().x > (max(pos().x)-min(pos().x))/2"; } );
This sets the velocity field as in the command-line example and then sets the pressure field to a rather strange value.
4 Expression syntax
The most complete documentation of the expression syntax is the source file for the Bison-grammar (*.yy and *.ll). Sorry.
These C++ operators are implemented:
- +,-,*,/
- Arithmetic operators. Can be used for vectors and scalars (only if useful. For instance: vectors can't be added to scalars)
- %
- A modulo-operator. Somehow differently defined from the standard C++ %-operator: the value of % is (not - if you don't understand what I mean, please test for yourself - for most applications of this operator this is in my opinion the more practical implementation)
- &,^
- The vector operators as defined by OpenFOAM
- <,>,<=,>=,!=,==
- Comparison operators (only defined for scalars)
- &&,||
- Logical Operators
- Conditional operator
- The conditional operator ( test ? val1 : val2) is defined for scalars and vectors
Operator precedence should be the same as for C++.
All the fields in the current time-step can be used. If the field is also the target field the old value is used. Then the field is written using the new value.
These pseudo-variables are defined:
- pi
- Guess ;)
These functions are defined:
- pow,log,exp,sqr,sqrt,sin,cos,tan
- Only defined for scalars
- mag
- defined for scalars and vectors
- grad
- gradient of a scalar-field
- curl
- curl of a vector-field
- snGrad
- surface normal gradient
- div
- divergence of a vector-field
- laplaction
- laplacian of a field (with an optional "coefficient"-field)
- min,max
- minimum and maximum of a scalar field
- average,integrate,sum,reconstruct
- reconstruct a face field (yielding a volume field)
These pseudo-functions are defined:
- surf
- Takes a scalar (or vector) constant and generates a constant-value surfaceField
- pos
- Vector field with the cell-centers
- fpos
- face-vectorField with the positions of the faces
- face
- surface field with the face-vectors
- area
- surface field with the face-areas
- fproj
- surface field with the projection of the face onto the Cartesian coordinates
- dist
- Scalar field that gives the distance to the nearest wall (using wallDist)
- rdist
- a field with the distances from a given vector (save mag(pos()-v))
- rand
- Scalars-field with random numbers from [0,1]
- randNormal
- Random-number scalar field that is Gauss-distributed
- vol
- Volume of the cells
- deltaT
- a field that returns the time-step
- time
- a field that returns the current time
These pseudo-functions are defined for logical expressions:
- set
- is true for all cells in a cellSet of that name and false otherwise
- zone
- is true for all cells in a cellZone of that name and false otherwise
5 Usage Examples
TODO: Users. Please feel free to include examples here
- To initialise a circular gamma-field (maybe a drop or bubble for the use with interFoam) containing the value 0 at position (1.5,1.5) with a radius of 3 type
funkySetFields -field gamma -expression 0 -time 0 -keepPatches -condition "pow(pos().x-1.5,2) + pow(pos().y-1.5,2) < pow(3,2)"
Note that the expression in the -condition entry is corrosponding to the analytical representation of a circle. With the unequal-sign (<) you are setting all cells inside the circle with the entry gamma=0.
5.1 Initialise a pressure field gradient due to gravity
This example shows how to initialise a gradient pressure field along the z axis of a water tank. The in the geometry, the water starts at 2.1 meters and extends to -3.4 meter of the tank. Therefore, in total 5.5 meters. The funkySetFieldsDict without the header is:
expressions ( pressureWater { field p; //field to initialise expression "9810.*(2.1-pos().z)+100000"; condition "(pos().z<2.1) && (pos().z>=-3.4)"; //ranging from 2.1 meter to -3.4 meter keepPatches 1; //keep the boundary conditions that were set before } );
After this, one just calls the
funkySetFields -time 0
command.
6 Technical
- the utility only writes volScalar- and volVectorFields. It can read and operate on surfaceFields
- no dimension checking is done (but the dimension of the target field is preserved, if not overwritten by the option)
6.1 Known Bugs
This utility is still under development. Currently there are no known known bugs (but propably some unknown ones)
6.2 Bug Reporting
Bugs can be reported with the at openfoam-extend.sourceforge.net.
6.3 Usage Notes
Turbulent wall boundary conditions (such as epsilonWallFunction) are not linked by funkySetFields. These are located in either libcompressibleRASModels.so or libincompressibleRASModels.so. To execute funkySetFields on a field which uses one of these conditions, force FSF to read these in by adding libs ( "libcompressibleRASModels.so" ); or libs ( "libincompressibleRASModels.so" ); to the system/controlDict file.
7 Download
The most recent version of the sources can always be downloaded via Subversion:
For 1.6:
svn checkout svn://svn.code.sf.net/p/openfoam-extend/svn/trunk/Breeder_1.6/utilities/postProcessing/FunkySetFields/
For 1.5:
svn checkout svn://svn.code.sf.net/p/openfoam-extend/svn/trunk/Breeder_1.5/utilities/postProcessing/FunkySetFields/
The version that works with 1.4.x (missing some features that are in the 1.5-version):
svn checkout svn://svn.code.sf.net/p/openfoam-extend/svn/trunk/Breeder/utilities/postProcessing/FunkySetFields/
7.1 Ancient history
- funkySetFields.tar.gz: The original Version that worked with
- funkySetFields-generatedSources.diff.gz: The diff file with bison-generated (by bison-2.1) sources and patches to compile funkySetFields under OpenFOAM-1.3 and without bison 2.1 (the current bison version 2.3 generates .C files which can't be compiled by gcc-4.1.0 included in OpenFOAM-1.3).
(To Bgschaid: Feel free to remove this link upon completion of the new release. 7islands 00:47, 18 Feb 2007 (CET))
- funkySetFields.r7106.tar.gz: A new version of funkySetFields. Not described yet on this page. Some of the new features include
- new fields are created
- ability to write fixedValue-patches
- work with cell sets
- work with surfaceFields (on writing)
These are the tarballs of the sources:
- funkySetFields.r7568.tar.gz: The tar file with the sources and included generated sources. Works with
- funkySetFields.r7241.tar.gz: The last version that works with
8 Plans
- factor out the parsing in a library to make it usable from other utilities
- make expression evaluation more efficient
9 History
- 2006-03-26: First upload of the utility
- 2007-02-02: New Version uploaded. Has more features than described on this page
- 2007-03-02: New Version with included generated Files uploaded and new features descibed
- 2007-06-20: New Version that works with 1.4 and addtions by Takuya Oshima (rdist and deltaT)
- 2008-07-29: Confirmed that it also works for 1.5
--Bgschaid 22:53, 26 Mar 2006 (CEST)