PVReaders: Simplified, rationalized and reorganized source tree and build scripts

This commit is contained in:
Henry Weller
2017-07-24 16:57:13 +01:00
parent 5cf5f8d783
commit aa7f6d12b7
49 changed files with 52 additions and 666 deletions

View File

@ -1,8 +1,13 @@
#!/bin/sh
cd ${0%/*} || exit 1 # Run from this directory
wclean libso vtkPVReaders
PVblockMeshReader/Allwclean
PVFoamReader/Allwclean
wclean libso vtkPVblockMesh
wclean libso vtkPVFoam
rm -f $FOAM_LIBBIN/libPVblockMeshReader* 2>/dev/null
rm -rf PVblockMeshReader/Make
rm -f $FOAM_LIBBIN/libPVFoamReader* 2>/dev/null
rm -rf PVFoamReader/Make
#------------------------------------------------------------------------------

View File

@ -17,9 +17,28 @@ case "$ParaView_VERSION" in
[ -n "$WM_CC" ] && export CC="$WM_CC"
[ -n "$WM_CXX" ] && export CXX="$WM_CXX"
wmake $targetType vtkPVReaders
PVblockMeshReader/Allwmake $targetType $*
PVFoamReader/Allwmake $targetType $*
wmake $targetType vtkPVblockMesh
wmake $targetType vtkPVFoam
if [ "$targetType" != "objects" ]
then
(
cd PVblockMeshReader
mkdir -p Make/$WM_OPTIONS > /dev/null 2>&1
cd Make/$WM_OPTIONS
cmake ../..
make
)
(
cd PVFoamReader
mkdir -p Make/$WM_OPTIONS > /dev/null 2>&1
cd Make/$WM_OPTIONS
cmake ../..
make
)
fi
else
echo " ERROR: ParaView not found in $ParaView_DIR"
fi

View File

@ -1,10 +0,0 @@
#!/bin/sh
cd ${0%/*} || exit 1 # Run from this directory
# deal with client/server vs combined plugins
rm -f $FOAM_LIBBIN/libPVFoamReader* 2>/dev/null
rm -rf PVFoamReader/Make
wclean libso vtkPVFoam
#------------------------------------------------------------------------------

View File

@ -1,23 +0,0 @@
#!/bin/sh
cd ${0%/*} || exit 1 # Run from this directory
# Parse arguments for library compilation
. $WM_PROJECT_DIR/wmake/scripts/AllwmakeParseArguments
if [ -d "$ParaView_DIR" -a -r "$ParaView_DIR" ]
then
wmake $targetType vtkPVFoam
if [ "$targetType" != "objects" ]
then
(
cd PVFoamReader
mkdir -p Make/$WM_OPTIONS > /dev/null 2>&1
cd Make/$WM_OPTIONS
cmake ../..
make
)
fi
fi
#------------------------------------------------------------------------------

View File

@ -1,10 +0,0 @@
#!/bin/sh
cd ${0%/*} || exit 1 # Run from this directory
# deal with client/server vs combined plugins
rm -f $FOAM_LIBBIN/libPVblockMeshReader* 2>/dev/null
rm -rf PVblockMeshReader/Make
wclean libso vtkPVblockMesh
#------------------------------------------------------------------------------

View File

@ -1,23 +0,0 @@
#!/bin/sh
cd ${0%/*} || exit 1 # Run from this directory
# Parse arguments for library compilation
. $WM_PROJECT_DIR/wmake/scripts/AllwmakeParseArguments
if [ -d "$ParaView_DIR" -a -r "$ParaView_DIR" ]
then
wmake $targetType vtkPVblockMesh
if [ "$targetType" != "objects" ]
then
(
cd PVblockMeshReader
mkdir -p Make/$WM_OPTIONS > /dev/null 2>&1
cd Make/$WM_OPTIONS
cmake ../..
make
)
fi
fi
#------------------------------------------------------------------------------

View File

@ -5,7 +5,6 @@ EXE_INC = \
-I$(LIB_SRC)/finiteVolume/lnInclude \
-I$(LIB_SRC)/dynamicMesh/lnInclude \
-I$(LIB_SRC)/lagrangian/basic/lnInclude \
-I../../vtkPVReaders/lnInclude \
-I../PVFoamReader \
-I$(ParaView_INCLUDE_DIR) \
-I$(ParaView_INCLUDE_DIR)/vtkkwiml \
@ -18,5 +17,5 @@ LIB_LIBS = \
-ldynamicMesh \
-lgenericPatchFields \
-llagrangian \
-L$(FOAM_LIBBIN) -lvtkPVReaders \
-L$(FOAM_LIBBIN) \
$(GLIBS)

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -1,3 +0,0 @@
vtkPVReaders.C
LIB = $(FOAM_LIBBIN)/libvtkPVReaders

View File

@ -1,6 +0,0 @@
EXE_INC = \
-I$(ParaView_INCLUDE_DIR) \
-I$(ParaView_INCLUDE_DIR)/vtkkwiml
LIB_LIBS = \
$(GLIBS)

View File

@ -1,333 +0,0 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
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/>.
Description
Misc helper methods and utilities
\*---------------------------------------------------------------------------*/
#include "vtkPVReaders.H"
// OpenFOAM includes
#include "IFstream.H"
// VTK includes
#include "vtkDataArraySelection.h"
#include "vtkDataSet.h"
#include "vtkMultiBlockDataSet.h"
#include "vtkInformation.h"
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
namespace Foam
{
defineTypeNameAndDebug(vtkPVReaders, 0);
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
//! \cond fileScope
// Extract up to the first non-word characters
inline word getFirstWord(const char* str)
{
if (str)
{
label n = 0;
while (str[n] && word::valid(str[n]))
{
++n;
}
return word(str, n, true);
}
else
{
return word::null;
}
}
//! \endcond
} // End namespace Foam
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
void Foam::vtkPVReaders::AddToBlock
(
vtkMultiBlockDataSet* output,
vtkDataSet* dataset,
const partInfo& selector,
const label datasetNo,
const std::string& datasetName
)
{
const int blockNo = selector.block();
vtkDataObject* blockDO = output->GetBlock(blockNo);
vtkMultiBlockDataSet* block = vtkMultiBlockDataSet::SafeDownCast(blockDO);
if (!block)
{
if (blockDO)
{
FatalErrorInFunction
<< "Block already has a vtkDataSet assigned to it"
<< endl;
return;
}
block = vtkMultiBlockDataSet::New();
output->SetBlock(blockNo, block);
block->Delete();
}
if (debug)
{
Info<< "block[" << blockNo << "] has "
<< block->GetNumberOfBlocks()
<< " datasets prior to adding set " << datasetNo
<< " with name: " << datasetName << endl;
}
block->SetBlock(datasetNo, dataset);
// name the block when assigning dataset 0
if (datasetNo == 0)
{
output->GetMetaData(blockNo)->Set
(
vtkCompositeDataSet::NAME(),
selector.name()
);
}
if (datasetName.size())
{
block->GetMetaData(datasetNo)->Set
(
vtkCompositeDataSet::NAME(),
datasetName.c_str()
);
}
}
vtkDataSet* Foam::vtkPVReaders::GetDataSetFromBlock
(
vtkMultiBlockDataSet* output,
const partInfo& selector,
const label datasetNo
)
{
const int blockNo = selector.block();
vtkDataObject* blockDO = output->GetBlock(blockNo);
vtkMultiBlockDataSet* block = vtkMultiBlockDataSet::SafeDownCast(blockDO);
if (block)
{
return vtkDataSet::SafeDownCast(block->GetBlock(datasetNo));
}
return 0;
}
// ununsed at the moment
Foam::label Foam::vtkPVReaders::GetNumberOfDataSets
(
vtkMultiBlockDataSet* output,
const partInfo& selector
)
{
const int blockNo = selector.block();
vtkDataObject* blockDO = output->GetBlock(blockNo);
vtkMultiBlockDataSet* block = vtkMultiBlockDataSet::SafeDownCast(blockDO);
if (block)
{
return block->GetNumberOfBlocks();
}
return 0;
}
// Foam::word Foam::vtkPVReaders::getPartName(int partId)
// {
// return getFirstWord(reader_->GetPartArrayName(partId));
// }
Foam::wordHashSet Foam::vtkPVReaders::getSelected
(
vtkDataArraySelection* select
)
{
int nElem = select->GetNumberOfArrays();
wordHashSet selections(2*nElem);
for (int elemI=0; elemI < nElem; ++elemI)
{
if (select->GetArraySetting(elemI))
{
selections.insert(getFirstWord(select->GetArrayName(elemI)));
}
}
return selections;
}
Foam::wordHashSet Foam::vtkPVReaders::getSelected
(
vtkDataArraySelection* select,
const partInfo& selector
)
{
int nElem = select->GetNumberOfArrays();
wordHashSet selections(2*nElem);
for (int elemI = selector.start(); elemI < selector.end(); ++elemI)
{
if (select->GetArraySetting(elemI))
{
selections.insert(getFirstWord(select->GetArrayName(elemI)));
}
}
return selections;
}
Foam::stringList Foam::vtkPVReaders::getSelectedArrayEntries
(
vtkDataArraySelection* select
)
{
stringList selections(select->GetNumberOfArrays());
label nElem = 0;
forAll(selections, elemI)
{
if (select->GetArraySetting(elemI))
{
selections[nElem++] = select->GetArrayName(elemI);
}
}
selections.setSize(nElem);
if (debug)
{
label nElem = select->GetNumberOfArrays();
Info<< "available(";
for (int elemI = 0; elemI < nElem; ++elemI)
{
Info<< " \"" << select->GetArrayName(elemI) << "\"";
}
Info<< " )\nselected(";
forAll(selections, elemI)
{
Info<< " " << selections[elemI];
}
Info<< " )\n";
}
return selections;
}
Foam::stringList Foam::vtkPVReaders::getSelectedArrayEntries
(
vtkDataArraySelection* select,
const partInfo& selector
)
{
stringList selections(selector.size());
label nElem = 0;
for (int elemI = selector.start(); elemI < selector.end(); ++elemI)
{
if (select->GetArraySetting(elemI))
{
selections[nElem++] = select->GetArrayName(elemI);
}
}
selections.setSize(nElem);
if (debug)
{
Info<< "available(";
for (int elemI = selector.start(); elemI < selector.end(); ++elemI)
{
Info<< " \"" << select->GetArrayName(elemI) << "\"";
}
Info<< " )\nselected(";
forAll(selections, elemI)
{
Info<< " " << selections[elemI];
}
Info<< " )\n";
}
return selections;
}
void Foam::vtkPVReaders::setSelectedArrayEntries
(
vtkDataArraySelection* select,
const stringList& selections
)
{
const int nElem = select->GetNumberOfArrays();
select->DisableAllArrays();
// Loop through entries, setting values from selectedEntries
for (int elemI=0; elemI < nElem; ++elemI)
{
string arrayName(select->GetArrayName(elemI));
forAll(selections, elemI)
{
if (selections[elemI] == arrayName)
{
select->EnableArray(arrayName.c_str());
break;
}
}
}
}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
// ************************************************************************* //

View File

@ -1,228 +0,0 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
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/>.
Namespace
Foam::vtkPVReaders
Description
A collection of helper functions when building a reader interface in
ParaView3.
SourceFiles
vtkPVReaders.C
\*---------------------------------------------------------------------------*/
#ifndef vtkPVReaders_H
#define vtkPVReaders_H
// do not include legacy strstream headers
#ifndef VTK_EXCLUDE_STRSTREAM_HEADERS
# define VTK_EXCLUDE_STRSTREAM_HEADERS
#endif
#include "className.H"
#include "fileName.H"
#include "stringList.H"
#include "wordList.H"
#include "HashSet.H"
// * * * * * * * * * * * * * Forward Declarations * * * * * * * * * * * * * //
class vtkDataArraySelection;
class vtkDataSet;
class vtkPoints;
class vtkPVFoamReader;
class vtkRenderer;
class vtkTextActor;
class vtkMultiBlockDataSet;
class vtkPolyData;
class vtkUnstructuredGrid;
class vtkIndent;
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
namespace vtkPVReaders
{
//- Declare name of the class and its debug switch
NamespaceName("vtkPVReaders");
//- Bookkeeping for GUI checklists and the multi-block organization
class partInfo
{
const char *name_;
int block_;
int start_;
int size_;
public:
partInfo(const char *name, const int blockNo=0)
:
name_(name),
block_(blockNo),
start_(-1),
size_(0)
{}
//- Return the block holding these datasets
int block() const
{
return block_;
}
//- Assign block number, return previous value
int block(int blockNo)
{
int prev = block_;
block_ = blockNo;
return prev;
}
const char* name() const
{
return name_;
}
int start() const
{
return start_;
}
int end() const
{
return start_ + size_;
}
int size() const
{
return size_;
}
bool empty() const
{
return !size_;
}
void reset()
{
start_ = -1;
size_ = 0;
}
//- Assign new start and reset the size
void operator=(const int i)
{
start_ = i;
size_ = 0;
}
//- Increment the size
void operator+=(const int n)
{
size_ += n;
}
};
//- Convenience method use to convert the readers from VTK 5
// multiblock API to the current composite data infrastructure
void AddToBlock
(
vtkMultiBlockDataSet* output,
vtkDataSet* dataset,
const partInfo& selector,
const label datasetNo,
const std::string& datasetName
);
//- Convenience method use to convert the readers from VTK 5
// multiblock API to the current composite data infrastructure
vtkDataSet* GetDataSetFromBlock
(
vtkMultiBlockDataSet* output,
const partInfo& selector,
const label datasetNo
);
//- Convenience method use to convert the readers from VTK 5
// multiblock API to the current composite data infrastructure
// ununsed at the moment
label GetNumberOfDataSets
(
vtkMultiBlockDataSet* output,
const partInfo& selector
);
//- Retrieve the current selections as a wordHashSet
wordHashSet getSelected
(
vtkDataArraySelection* select
);
//- Retrieve a sub-list of the current selections
wordHashSet getSelected
(
vtkDataArraySelection*,
const partInfo&
);
//- Retrieve the current selections
stringList getSelectedArrayEntries(vtkDataArraySelection*);
//- Retrieve a sub-list of the current selections
stringList getSelectedArrayEntries
(
vtkDataArraySelection* select,
const partInfo& selector
);
//- Set selection(s)
void setSelectedArrayEntries
(
vtkDataArraySelection*,
const stringList&
);
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace vtkPV
} // End namespace Foam
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#endif
// ************************************************************************* //

View File

@ -4,12 +4,11 @@ EXE_INC = \
-I$(LIB_SRC)/mesh/blockMesh/lnInclude \
-I$(ParaView_INCLUDE_DIR) \
-I$(ParaView_INCLUDE_DIR)/vtkkwiml \
-I../../vtkPVReaders/lnInclude \
-I../PVblockMeshReader
LIB_LIBS = \
-lmeshTools \
-lfileFormats \
-lblockMesh \
-L$(FOAM_LIBBIN) -lvtkPVReaders \
-L$(FOAM_LIBBIN) \
$(GLIBS)

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License

View File

@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License