diff --git a/applications/test/IjkField/Make/files b/applications/test/IjkField/Make/files
new file mode 100644
index 0000000000..8e1017d41d
--- /dev/null
+++ b/applications/test/IjkField/Make/files
@@ -0,0 +1,3 @@
+Test-IjkField.C
+
+EXE = $(FOAM_USER_APPBIN)/Test-IjkField
diff --git a/applications/test/IjkField/Make/options b/applications/test/IjkField/Make/options
new file mode 100644
index 0000000000..2c375bcb61
--- /dev/null
+++ b/applications/test/IjkField/Make/options
@@ -0,0 +1,4 @@
+EXE_INC = -DFULLDEBUG
+
+/* EXE_INC = -I$(LIB_SRC)/finiteVolume/lnInclude */
+/* EXE_LIBS = -lfiniteVolume */
diff --git a/applications/test/IjkField/Test-IjkField.C b/applications/test/IjkField/Test-IjkField.C
new file mode 100644
index 0000000000..8f093218f0
--- /dev/null
+++ b/applications/test/IjkField/Test-IjkField.C
@@ -0,0 +1,138 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2019 OpenCFD Ltd.
+ \\/ 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 .
+
+Description
+ Functionality of IjkField
+
+\*---------------------------------------------------------------------------*/
+
+#include "point.H"
+#include "IjkField.H"
+#include "IOstreams.H"
+
+using namespace Foam;
+
+template
+Ostream& print(const IjkField& fld)
+{
+ Info<< static_cast&>(fld).size()
+ << " " << fld.sizes() << ' ' << flatOutput(fld);
+
+ return Info;
+}
+
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+// Main program:
+
+int main(int argc, char *argv[])
+{
+ // Create with inconsistent sizes
+ IjkField field0({1, 2, 3}, identity(10));
+
+ IjkField field1({3, 4, 5});
+ IjkField field2({2, 3, 3});
+
+ forAll(field1, i)
+ {
+ field1[i] = -i;
+ }
+ forAll(field2, i)
+ {
+ field2[i] = i;
+ }
+
+ Info<< "ijk field "; print(field1) << nl;
+ Info<< "ijk field "; print(field2) << nl;
+
+ field1.resize(field2.sizes());
+
+ Info<< "resized "; print(field1) << nl;
+
+ field1 *= 2;
+
+ Info<< "Multiply: "; print(field1) << nl;
+
+ field1.resize({1, 2, 3});
+
+ Info<< "Resize - shrink: "; print(field1) << nl;
+
+ field1.resize({2, 3, 2});
+
+ Info<< "Resize - grow: "; print(field1) << nl;
+
+ field1.resize({3, 2, 2});
+
+ Info<< "Resize - repartition: "; print(field1) << nl;
+
+ field1 = field2;
+
+ Info<< "Copied: "; print(field1) << nl;
+
+ field1 = 3.14159;
+
+ Info<< "Assigned: "; print(field1) << nl;
+
+ field1 += 3.14159;
+
+ Info<< "+= operator: "; print(field1) << nl;
+
+ field1 /= 1.2;
+
+ Info<< "/= operator: "; print(field1) << nl;
+
+ // Field operations are still limited, but we can bypass things too
+
+ {
+ Field& tmpField = field1;
+ tmpField = sqr(tmpField);
+
+ Info<< "squared (workaround): "; print(field1) << nl;
+ }
+
+
+ Info<< nl
+ << "Before transfer: addr:" << long(field1.data())
+ << " size:" << field1.size() << nl;
+
+ Field sfield1(std::move(field1));
+ field1.clear();
+
+ Info<< "After transfer to regular field" << nl
+ << " source:" << long(field1.data()) << nl
+ << " target:" << long(sfield1.data()) << nl
+ << "Values"
+ << " source:";
+ print(field1) << nl;
+
+ Info<< " target:" << flatOutput(sfield1) << nl;
+
+
+ Info << "\nEnd\n" << endl;
+
+ return 0;
+}
+
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/meshes/ijkMesh/IjkField.C b/src/OpenFOAM/meshes/ijkMesh/IjkField.C
new file mode 100644
index 0000000000..28002e9146
--- /dev/null
+++ b/src/OpenFOAM/meshes/ijkMesh/IjkField.C
@@ -0,0 +1,145 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2019 OpenCFD Ltd.
+ \\/ 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 .
+
+\*---------------------------------------------------------------------------*/
+
+// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
+
+template
+void Foam::IjkField::resize
+(
+ const labelVector& newSizes,
+ const Type& val
+)
+{
+ labelVector& ourSizes = sizes();
+
+ if (ijk_.empty() || !cmptProduct(newSizes))
+ {
+ // Either/both are empty, can redimension directly
+ ourSizes = newSizes;
+ Field::resize(ijk_.size(), val);
+ return;
+ }
+
+ const unsigned diffs
+ (
+ (ourSizes.x() != newSizes.x() ? 0x100 : 0)
+ | (ourSizes.y() != newSizes.y() ? 0x010 : 0)
+ | (ourSizes.z() != newSizes.z() ? 0x001 : 0)
+ );
+
+ switch (diffs)
+ {
+ case 0x000:
+ // No change
+ return;
+ break;
+
+ case 0x001:
+ // Change in k only, can redimension directly
+ ourSizes = newSizes;
+ Field::resize(ijk_.size(), val);
+ return;
+ break;
+
+ case 0x010:
+ // 2D change in j only, can redimension directly
+ if (ourSizes.z() == 1)
+ {
+ ourSizes = newSizes;
+ Field::resize(ijk_.size(), val);
+ return;
+ }
+ break;
+ }
+
+
+ if ((ourSizes.x()*ourSizes.y()) == newSizes.x()*newSizes.y())
+ {
+ // Re-partition i,j with the same size
+ ourSizes = newSizes;
+ Field::resize(ijk_.size(), val);
+ return;
+ }
+
+
+ IjkField& ourContent = *this;
+
+ IjkField newContent(newSizes, val);
+
+ // Need new addressing space
+ const label ni = min(ourSizes.x(), newSizes.x());
+ const label nj = min(ourSizes.y(), newSizes.y());
+ const label nk = min(ourSizes.z(), newSizes.z());
+
+ for (label k=0; k::transfer(newContent);
+}
+
+
+template
+void Foam::IjkField::resize(const labelVector& newSizes)
+{
+ resize(newSizes, Zero);
+}
+
+
+// * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
+
+template
+void Foam::IjkField::operator=(const IjkField& rhs)
+{
+ if (this != &rhs)
+ {
+ sizes() = rhs.sizes();
+
+ Field::operator=(rhs);
+ }
+}
+
+
+template
+void Foam::IjkField::operator=(const tmp>& rhs)
+{
+ if (this != &(rhs()))
+ {
+ sizes() = rhs().sizes();
+
+ Field::operator=(rhs());
+ }
+}
+
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/meshes/ijkMesh/IjkField.H b/src/OpenFOAM/meshes/ijkMesh/IjkField.H
new file mode 100644
index 0000000000..6ef025dfe4
--- /dev/null
+++ b/src/OpenFOAM/meshes/ijkMesh/IjkField.H
@@ -0,0 +1,180 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2019 OpenCFD Ltd.
+ \\/ 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 .
+
+Class
+ Foam::IjkField
+
+Description
+ Generic templated field type.
+
+SourceFiles
+ IjkFieldFunctions.H
+ IjkFieldFunctionsM.H
+ IjkFieldMapper.H
+ IjkFieldI.H
+ IjkFieldM.H
+ IjkField.C
+ IjkFieldFunctions.C
+ IjkFieldFunctionsM.C
+
+\*---------------------------------------------------------------------------*/
+
+#ifndef IjkField_H
+#define IjkField_H
+
+#include "ijkAddressing.H"
+#include "Field.H"
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+namespace Foam
+{
+
+/*---------------------------------------------------------------------------*\
+ Class IjkField Declaration
+\*---------------------------------------------------------------------------*/
+
+template
+class IjkField
+:
+ public Field
+{
+ // Private Data
+
+ //- The i-j-k addressing
+ ijkAddressing ijk_;
+
+ //- Copy construct
+ inline IjkField(const IjkField& fld);
+
+
+public:
+
+ // Constructors
+
+ //- Construct zero-sized
+ inline IjkField();
+
+ //- Construct with sizing information, leaving values uninitialized
+ inline explicit IjkField(const labelVector& ijk);
+
+ //- Construct with sizing information and initial value
+ inline IjkField(const labelVector& ijk, const Type& val);
+
+ //- Construct with sizing information and initial values of zero
+ inline IjkField(const labelVector& ijk, const zero);
+
+ //- Copy construct from components
+ inline IjkField(const labelVector& ijk, const UList& list);
+
+ //- Move construct from components
+ inline IjkField(const labelVector& ijk, Field&& field);
+
+
+ // Member Functions
+
+ // Access
+
+ //- Return i,j,k addressing
+ inline const ijkAddressing& ijk() const;
+
+ //- Return i,j,k addressing for modification
+ inline ijkAddressing& ijk();
+
+ //- Return i,j,k addressing sizes
+ inline const labelVector& sizes() const;
+
+ //- Return i,j,k addressing sizes for modification
+ inline labelVector& sizes();
+
+
+ // Edit
+
+ //- Clear dimensions and field
+ inline void clear();
+
+ //- Change dimensions. Fill new values with Zero
+ void resize(const labelVector& newSizes);
+
+ //- Change dimensions
+ void resize(const labelVector& newSizes, const Type& val);
+
+
+ // Access Operators
+
+ //- Field access at given i-j-k position
+ inline const Type& operator()
+ (
+ const label i,
+ const label j,
+ const label k
+ ) const;
+
+ //- Field access at given i-j-k position
+ inline Type& operator()
+ (
+ const label i,
+ const label j,
+ const label k
+ );
+
+ //- Field access at given i-j-k position
+ inline const Type& operator()(const labelVector& ijk) const;
+
+ //- Field access at given i-j-k position
+ inline Type& operator()(const labelVector& ijk);
+
+
+ // Member Operators
+
+ //- Copy assignment
+ void operator=(const IjkField& rhs);
+ void operator=(const tmp>& rhs);
+
+ //- Move assignment
+ inline void operator=(IjkField&& rhs);
+
+ //- Value assignment
+ inline void operator=(const Type& val);
+ inline void operator=(const zero);
+
+};
+
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+} // End namespace Foam
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#include "IjkFieldI.H"
+
+#ifdef NoRepository
+ #include "IjkField.C"
+#endif
+
+// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
+
+#endif
+
+// ************************************************************************* //
diff --git a/src/OpenFOAM/meshes/ijkMesh/IjkFieldI.H b/src/OpenFOAM/meshes/ijkMesh/IjkFieldI.H
new file mode 100644
index 0000000000..5efc135acd
--- /dev/null
+++ b/src/OpenFOAM/meshes/ijkMesh/IjkFieldI.H
@@ -0,0 +1,226 @@
+/*---------------------------------------------------------------------------*\
+ ========= |
+ \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
+ \\ / O peration |
+ \\ / A nd | Copyright (C) 2019 OpenCFD Ltd.
+ \\/ 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 .
+
+\*---------------------------------------------------------------------------*/
+
+// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
+
+template
+inline Foam::IjkField::IjkField()
+:
+ Field(),
+ ijk_()
+{}
+
+
+template
+inline Foam::IjkField::IjkField(const labelVector& ijk)
+:
+ Field(cmptProduct(ijk)),
+ ijk_(ijk)
+{}
+
+
+template
+inline Foam::IjkField::IjkField
+(
+ const labelVector& ijk,
+ const Type& val
+)
+:
+ Field(cmptProduct(ijk), val),
+ ijk_(ijk)
+{}
+
+
+template
+inline Foam::IjkField::IjkField
+(
+ const labelVector& ijk,
+ const zero
+)
+:
+ Field(cmptProduct(ijk), Zero),
+ ijk_(ijk)
+{}
+
+
+template
+inline Foam::IjkField::IjkField
+(
+ const labelVector& ijk,
+ const UList& list
+)
+:
+ Field(list),
+ ijk_(ijk)
+{
+ if (ijk_.size() != Field::size())
+ {
+ #ifdef FULLDEBUG
+ WarningInFunction
+ << "Resizing field to match i-j-k sizing " << sizes()
+ << nl << nl;
+ #endif
+
+ Field::resize(ijk_.size(), Zero);
+ }
+}
+
+
+template
+inline Foam::IjkField::IjkField
+(
+ const labelVector& ijk,
+ Field&& field
+)
+:
+ Field(std::move(field)),
+ ijk_(ijk)
+{
+ if (ijk_.size() != Field::size())
+ {
+ #ifdef FULLDEBUG
+ WarningInFunction
+ << "Resizing field to match i-j-k sizing " << sizes()
+ << nl << nl;
+ #endif
+
+ Field::resize(ijk_.size(), Zero);
+ }
+}
+
+
+// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
+
+template
+inline const Foam::ijkAddressing& Foam::IjkField::ijk() const
+{
+ return ijk_;
+}
+
+
+template
+inline Foam::ijkAddressing& Foam::IjkField::ijk()
+{
+ return ijk_;
+}
+
+
+template
+inline const Foam::labelVector& Foam::IjkField::sizes() const
+{
+ return ijk_.sizes();
+}
+
+
+template
+inline Foam::labelVector& Foam::IjkField::sizes()
+{
+ return ijk_.sizes();
+}
+
+
+template
+inline void Foam::IjkField::clear()
+{
+ ijk_.clear();
+ Field::clear();
+}
+
+
+// * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
+
+template
+inline const Type& Foam::IjkField::operator()
+(
+ const label i,
+ const label j,
+ const label k
+) const
+{
+ return Field::operator[](ijk_.index(i, j, k));
+}
+
+
+template
+inline Type& Foam::IjkField::operator()
+(
+ const label i,
+ const label j,
+ const label k
+)
+{
+ return Field::operator[](ijk_.index(i, j, k));
+}
+
+
+template
+inline const Type& Foam::IjkField::operator()
+(
+ const labelVector& ijk
+) const
+{
+ return Field::operator[](ijk_.index(ijk));
+}
+
+
+template
+inline Type& Foam::IjkField::operator()
+(
+ const labelVector& ijk
+)
+{
+ return Field::operator[](ijk_.index(ijk));
+}
+
+
+template
+inline void Foam::IjkField::operator=(IjkField&& rhs)
+{
+ if (this != &rhs)
+ {
+ sizes() = rhs.sizes();
+
+ List::transfer(rhs);
+
+ rhs.clear();
+ }
+}
+
+
+template
+inline void Foam::IjkField::operator=(const Type& val)
+{
+ Field::operator=(val);
+}
+
+
+template
+inline void Foam::IjkField::operator=(const zero)
+{
+ Field::operator=(Zero);
+}
+
+
+// ************************************************************************* //