CFD Online Discussion Forums (https://www.cfd-online.com/Forums/)
-   OpenFOAM (https://www.cfd-online.com/Forums/openfoam/)
-   -   magneticFoam (https://www.cfd-online.com/Forums/openfoam/95146-magneticfoam.html)

 latvietis December 7, 2011 12:07

magneticFoam

Hello, Foamers!

So, there is magneticFoam solver, but there isn't any tutorial. Is there anyone who could share one? I know I'm not the only one looking for it.

Yours,
latvietis

 wyldckat December 12, 2011 18:23

Greetings latvietis and welcome to the forum!

You don't seem to be alone in wanting a tutorial for that solver:
I haven't looked deep into it, but it should work along the same lines as the basic solvers, such as: potentialFoam, scalarTransportFoam and laplacianFoam. I say this because they share one detail in common: each solve one simple equation.

Best regards,
Bruno

 latvietis December 13, 2011 21:22

Well, you know, they were old and there weren't any answers.

Will check those solvers.

 latvietis December 16, 2011 13:27

Ok, the problem is in the transportProperties. Before explaining I have to tell I'm total noob in OpenFOAM, I have managed to get through tutorials only. But this... Ok, so I can't find any similar tutorial (I haven't checked all yet), but how should my transportProperties file look? I don't understand what should I write there. createFields file looks like this

List<magnet> magnets(transportProperties.lookup("magnets"));

surfaceScalarField murf
(
IOobject
(
"murf",
runTime.timeName(),
mesh
),
mesh,
1
);

surfaceScalarField Mrf
(
IOobject
(
"Mrf",
runTime.timeName(),
mesh
),
mesh,
dimensionedScalar("Mr", dimensionSet(0, 1, 0, 0, 0, 1, 0), 0)
);

forAll(magnets, i)
{
label magnetZonei = mesh.faceZones().findZoneID(magnets[i].name());

if (magnetZonei == -1)
{
FatalIOErrorIn(args.executable().c_str(), transportProperties)
<< "Cannot find faceZone for magnet " << magnets[i].name()
<< exit(FatalIOError);
}

const labelList& faces = mesh.faceZones()[magnetZonei];

const scalar muri = magnets[i].mur();
const scalar Mri = magnets[i].Mr().value();
const vector& orientationi = magnets[i].orientation();

const surfaceVectorField& Sf = mesh.Sf();

forAll(faces, i)
{
label facei = faces[i];
murf[facei] = muri;
Mrf[facei] = Mri*(orientationi & Sf[facei]);
}
}

 wyldckat December 17, 2011 20:00

Hi latvietis,

OK, I'll try to give you a boost based on what I know (which might not be much).
So, first thing to take into account is the description available on the top comment header of "magneticFoam.C":
Quote:
 Solver for the magnetic field generated by permanent magnets. A Poisson's equation for the magnetic scalar potential psi is solved from which the magnetic field intensity H and magnetic flux density B are obtained. The paramagnetic particle force field (H dot grad(H)) is optionally available.
As for fields, you've got at least three:
• "psi" - this one should be somewhat similar to "phi", the one on potentialFoam.
• "murf" - relative permeability field, based on what is read on the "magnet.H".
• "Mrf" - remanence field, also based on what is read on the "magnet.H".
All 3 are meant to reside in the time snapshot folders. Other fields are created as outputs on demand via arguments given to the solver at runtime.

To go onward, first follow this tutorial: http://openfoamwiki.net/index.php/Ho...ure_to_icoFoam
Then base yourself on that tutorial and the tips I tried to give you here to continue onward!

Here you'll find more helpful info: http://www.openfoamworkshop.org/6th_...m/training.htm - starting with:
Good luck!
Bruno

 latvietis December 20, 2011 20:49

Ok, sir. I'm more confused than before, sorry. First things first, I did read the header and understood that. And here comes the bad part.. I didn't get your help.

First, about this "magnet" class. You gave me link that takes me to localPoints class reference. What should I find there? I'm really bad at reading short descriptions where most part is in C.

How did you think something like that in code? What those numbers stand for? Why in that order?
magnet1 0.2 5000 (0,0,1);

Last is about temperature? How knowing how to add temperature could help in magnets? I'm really bad at seeing things, sorry.

Thanks for those presentation links, interesting start.

Yours sincerely,
latvietis

 latvietis December 21, 2011 09:34

Oh, I think I got one answer to my own question.

What I need to define is found in magnet.H

magnet1 0.2 5000 (0,0,1);
And then it means you defined
1) name of magnet
2) mur
3) Mr
4) orientation of magnet

Right? So this should be saved it transportProperties? But then again, it means that magnet is oriented in z-axis?

The fields you mentioned should be saved in "0" folder?

 latvietis December 21, 2011 09:59

I kinda tried what you said, but got this:

--> FOAM FATAL IO ERROR:
Attempt to return dictionary entry as a primitive

file: /run/magnets/constant/transportProperties::magnets from line 20 to line 21.

From function ITstream& primitiveEntry::stream() const
in file db/dictionary/dictionaryEntry/dictionaryEntry.C at line 82.

FOAM aborting

So what is meant with 'primitive' in magnets?

 wyldckat December 21, 2011 16:26

Hi latvietis,

Quote:
 Originally Posted by latvietis (Post 336542) Last is about temperature? How knowing how to add temperature could help in magnets? I'm really bad at seeing things, sorry.
Simple: the idea is for you to get familiar with the inner workings of OpenFOAM! Then it would start to be easier for you to understand what is where and why.

Quote:
 Originally Posted by latvietis (Post 336615) Oh, I think I got one answer to my own question. What I need to define is found in magnet.H magnet1 0.2 5000 (0,0,1); And then it means you defined 1) name of magnet 2) mur 3) Mr 4) orientation of magnet Right? So this should be saved it transportProperties? But then again, it means that magnet is oriented in z-axis? The fields you mentioned should be saved in "0" folder?
Exactly, this was basically why I had pointed you to the temperature tutorial, so it would be easier to understand where things are placed.

And yes, the fields I listed are meant to be placed in the 0 (zero) folder. Again, the other tutorial shows the example of having to add a new field file.

Quote:
 Originally Posted by latvietis (Post 336616) I kinda tried what you said, but got this: --> FOAM FATAL IO ERROR: Attempt to return dictionary entry as a primitive file: /run/magnets/constant/transportProperties::magnets from line 20 to line 21. From function ITstream& primitiveEntry::stream() const in file db/dictionary/dictionaryEntry/dictionaryEntry.C at line 82. FOAM aborting So what is meant with 'primitive' in magnets?
Mmmm, I'm not sure. The idea is to do a bit of trial-and-error, since I can't fully understand the code to be able to infer the expected structure at the first try :(
A trick that I remembered that usually works is ... the bananas trick: http://openfoamwiki.net/index.php/Op...de/Use_bananas

Good luck!
Bruno

 latvietis December 22, 2011 21:26

I guess the problem is that I have no idea how to define transportProperties.

So I see what is needed:
//- Construct from components
inline magnet
(
const word& name,
const scalar mur,
const scalar Mr,
const vector& orientation
)

but how it must be defined? Also what is that 'orientation'?

 mturcios777 December 23, 2011 14:30

I would guess orientation is supposed to point from the south to the north pole for each magnet. I'm not sure bananas will work for this constructor. How do readBegin and readEnd take input?

I wanted to add that for each magnet you will need to make a faceZone that defines the physical extent of the permanent magnet. You can use setSet or topoSet, and the name of the cellZone must have the same name as the magnet in the transportProperties.

 wyldckat December 24, 2011 09:20

1 Attachment(s)
Greetings to all!

Since I have an old passion for magnetic fields and such, I had a go at creating an example myself.

First of all, Marco, thanks for the hint!

@latvietis: Attached is a working case named "magSandbox", albeit it doesn't necessarily represent anything very physical. Like the name implies, it's a case set-up for playing around with magneticFoam. To use it, run:
Code:

`./Allrun`
To clean it up and start over (remove mesh and solvers iterations):
Code:

`foamCleanTutorials`
Run:
Code:

`magneticFoam -help`
For more information about other options available for running from the command line. I say this because this was how I found out about "-HdotGradH" that you can see in Allrun.

Development details:
• Base structure for the case was taken from two other cases:
• "basic/scalarTransportFoam/pitzDaily" - most of the structure, since it has most of the basic files necessary.
• "stressAnalysis/solidDisplacementFoam/plateHole" - took only "controlDict" from there, but I could have taken it from "basic/potentialFoam/pitzDaily/system".
• Geometry taken from the cavity case.
• Changed the box from 0.1 to 1m.
• Renamed walls. 3 kinds of walls have been defined: topWall, sideWall and numbWall.
Top and side will have magnets, "numbWall" is... numb :D
• Looking at "createFields.H" from "magneticFoam.C", one can see that "psi" is a "volScalarField". Therefore I renamed "0/T" to "0/psi".
Also, removed "0/U" for now, just to see if things worked with the minimum set of changes.
• The new "0/psi" file was a bit of trial and error, after setting the proper boundary names for the walls.
• "constant/transportProperties" - this took several iterations of trial and error. Bananas did not help much, but the concept of throwing stuff at it still worked ;)
The base idea was correct, expect for the following details:
• "orientation" is a vector, so it doesn't use commas: (1 0 0)
• "magnets" is a list, or perhaps better visualized as a special vector. So, instead of using "{}", one has to use "()".
• Code:

`magnets(  (magnet1));`
This complained about missing scalar. Without the inner parenthesis, it complained about something else... which led me to believe it was meant to be a vector as well.
In the end, this was how it should be:
Code:

```magnets (   (magnet1 0.2 5000 (0 1 0))   (magnet2 0.4 2000 (1 0 0)) );```
Similar, ain't it? ;)
• About "faceZones using topoSet" - I ran:
Code:

`find \$FOAM_TUTORIALS -name "topo*"`
And found several tutorials with examples. I'm vaguely familiar with the tutorials that exist, so I took the simplest one: "heatTransfer/buoyantSimpleFoam/circuitBoardCooling/system/topoSetDict".
Upon examining it, I found out that it had the basic blocks that I needed, namely:
Code:

```        type    faceSet;         action  new;         source  boxToFace;```
Copied the file to my case and pruned out what I didn't need. A few more iterations of trial and error and found out how to properly define the bounding box and that it was "faceZoneSet", not "faceSet".
• "system/fvSchemes": the solver complained about a missing entry at "laplacianSchemes". All I had to do was replace the one already there with the one it asked for, leaving the "Gauss linear corrected" untouched.
Also, commented out "div(phi,T)".
• "system/fvSolution": missing "psi" entry. Replaced "T" with "psi".
Complained about the solution "solver", giving possible entries, so I used "PCG" since it's also one of the basic ones.
Also complained about the "preconditioner", so I used "DIC".
Left the rest untouched.
• After these basics were complete, I had magneticFoam running. Keep in mind that at each iteration/trial, I ran magneticFoam for know what was missing.
• The fields "murf" and "Mrf" have pre-set values when created, as shown in "createFields.H". I'll leave it to you to do some more trial and error.
If you have more questions, feel free to ask!

Best regards,
Bruno

 latvietis December 25, 2011 12:09

Ok, I have a question. Is there any other ways how to tell how great this is besides adding to reputation and liking it?

But now for the good part - so, there are some results etc. But I guess I also am useless in ParaView. Any chance you could tell me how to see H and B?

 wyldckat December 25, 2011 12:42

Hi latvietis,
Quote:
 Originally Posted by latvietis (Post 336976) Ok, I have a question. Is there any other ways how to tell how great this is besides adding to reputation and liking it?
Please document it! Here is a page I've just set-up for continuing documentation of magneticFoam: http://openfoamwiki.net/index.php/MagneticFoam

And the link is already accessible from where it should be accessible, namely here: http://openfoamwiki.net/index.php/Main_OFSolvers

Quote:
 Originally Posted by latvietis (Post 336976) But now for the good part - so, there are some results etc. But I guess I also am useless in ParaView. Any chance you could tell me how to see H and B?
See the User Guide ;) Here is a link to the Post-processing section for the "cavity" tutorial: http://www.openfoam.org/docs/user/ca...#x5-130002.1.4
You will only be able to see the fields on the time snapshot "1", which is accessible on the upper right corner on the Figure 2.3: http://www.openfoam.org/docs/user/cavity.php#x5-110123

Good luck! And Merry Christmas :)
Bruno

 latvietis December 25, 2011 13:11

Oh, how silly, I just forgot to check volume fields in properties window. Now I can see some picks! It is time for some playing!

 latvietis December 27, 2011 14:56

What am I defining with
1) orientation
2) topoSet

To be more precise with my questions..
1) What can I define in magnet with one vector? Something with poles? All I can think of is that for example (1 0 0) would say that my magnet is oriented in x axis with poles like this [- +]. But I don't know how scientific that could sound. What else could be called with 'orientation'?

2) In topoSet I define 2 faces for each magnet. It defines the centers of faces with given coordinates. For example (0.5 0.5 0.5) can be seen as my magnets pole center is in the middle if its 'face' is 1x1. Is that right? But why 2 faces? I believe it defines the centers of north (first) and south (second) pole. Is this the right guess?

 wyldckat December 27, 2011 18:24

Hi latvietis,

Let's see:
Quote:
 Originally Posted by latvietis (Post 337129) To be more precise with my questions.. 1) What can I define in magnet with one vector? Something with poles? All I can think of is that for example (1 0 0) would say that my magnet is oriented in x axis with poles like this [- +]. But I don't know how scientific that could sound. What else could be called with 'orientation'?
Honestly, I don't know which way is the positive side, since it might depend on the convention used for North-South. Nonetheless, I assume that the magnetic orientation of the example (1 0 0) means that North is at (1 0 0) and South is at (0 0 0).
Although, the other possibility is the usage of the "right hand rule": http://en.wikipedia.org/wiki/File:Manoderecha.svg - where the vector indicates where the thumb is pointing to. You'll have to figure that one out from the source code and the equations at hand.
I didn't focus on what psi, B and H represent, I only focused on having something that simply works, looked nice and non-random. I tried with other psi values, but things got very strange and nonsensical.

Quote:
 Originally Posted by latvietis (Post 337129) 2) In topoSet I define 2 faces for each magnet. It defines the centers of faces with given coordinates. For example (0.5 0.5 0.5) can be seen as my magnets pole center is in the middle if its 'face' is 1x1. Is that right? But why 2 faces? I believe it defines the centers of north (first) and south (second) pole. Is this the right guess?
Technically, each magnet is a "face zone set" using a "box" selection method. Imagine that for the "magnet1", you wanted to select only the top faces of the cells on the top row of cells on the mesh. Using a box selection, you would click on one corner of the zone where said cell faces were and then finish the selection on the other corner, making a rectangle that would only include those faces.
This means that if the selection box were to be extended in order to pick up more faces, all of those faces would have the same magnet specification.
In other words, this way of selecting faces you could have a magnet placed in the middle of the domain, with a thickness of either:
• One thin magnetic surface, with virtually no thickness.
• Or one whole group of mesh cells, portraying a magnet placed in the middle of the mesh domain.
• Note: this way you cannot have a thickness that is one half of a cell, since there is no face in the middle of said cell.
So yes, a selection box of 1x1 square meter geometry would represent a single magnet with a center on (0.5 0.5 0.5)... which would cover the whole geometry.

I used two magnets simply to make sure that there was a list of magnets and that said list was being properly defined and used. Each one represents an independent magnet.

Their placement was only made as an example, in an attempt to have two magnets that were either deflecting or continuing a magnetic flow that wasn't linear. From another view, if I had placed the two magnets on opposite sides of the geometry, it would be harder to see any understandable results without previously knowing how things really work... which we don't know.

Oh, and don't forget that important detail I mentioned near the end of the other post:
Code:

`The fields "murf" and "Mrf" have pre-set values when created, as shown  in "createFields.H".`
This means that the geometry where no magnet resides, has a pre-set environment for magnetic flow. It probably implies that the magnets are placed in a vacuum domain, including themselves being made out of vacuum... :eek:

Best regards,
Bruno

 latvietis December 27, 2011 20:02

For second question I wanted to know something else. Why you define

box (0 0.999 0) (1 1.001 0.1);

My explanation is the first part defines the center of Npole, second part the center of Spole. Do I understand this correctly?

Good idea about right hand law, will try to figure this out.

Thank you.

 latvietis December 27, 2011 20:17

Oh, no.. It means the coordinates of opposite corners? In this way I define my 'box'? But then what is this face of magnet? Where are its poles then? Defined by orientation?

 wyldckat December 28, 2011 09:06

Hi latvietis,

OK, I probably shouldn't have written so much, but I wasn't feeling artistic enough to do videos or drawings... and I'm still not in the mood to draw ;)

Quote:
 Originally Posted by wyldckat (Post 337138) Technically, each magnet is a "face zone set" using a "box" selection method. Imagine that for the "magnet1", you wanted to select only the top faces of the cells on the top row of cells on the mesh. Using a box selection, you would click on one corner of the zone where said cell faces were and then finish the selection on the other corner, making a rectangle that would only include those faces.
The selection box is for selecting faces on the mesh cells, where those faces have the magnet characteristics. Those faces represent the surface of the magnet.

Let's take the cavity tutorial as an example once more:
• In the cavity tutorial on "icoFoam", you have 4 walls: top wall is a moving wall; the other 3 walls are... static walls. The moving wall forces the fluid inside the square to circulate.
• If you redefine the top wall as a magnet (the "magnet1" I defined on the sandbox case), that magnet surface will generate a field with the orientation and specifications defined in the "transportProperties" file.
• "magnet2" merely acts as a second wall that has some other motion associated to it.
It should be as simple as that :D You'll have to do more tests, trials and errors to figure out more details about how things work ;)

Best regards,
Bruno

All times are GMT -4. The time now is 00:02.