OOF: Finite Element Analysis of Microstructures
Changes to the API for OOF2 Property Extensions
This page is still under construction.
A number of changes will have to be made to OOF2 Property extensions to get them to work with version 2.1.0. Probably the easiest way to update old Properties is to compare with an example from the OOF2 2.1.0 source code. This brief summary may help, as will referring to the relevant section of the old OOF2 manual.
The Property Class
User defined Properties should now be derived from one of three Property subclasses, FluxProperty, EqnProperty, or AuxiliaryProperty.
 FluxProperty is for Properties that contribute to a Flux. Elasticity is a FluxProperty because it computes the Stress. See SRC/engine/property/elasticity/, for example.
 EqnPropertys make contributions directly to an Equation. Mass density is an EqnProperty because it computes the coefficient of the displacement's second time derivative. Gravity is an EqnProperty because it contributes directly to the right hand side vector. See SRC/engine/property/massdensity/ and SRC/engine/property/forcedensity/ for examples.
 AuxiliaryPropertys don't make any contributions to Fluxes or Equations, but may be used by other Properties. Color and Orientation are AuxiliaryPropertys. See SRC/engine/property/color/.
The Python versions of these base classes are PyFluxProperty and PyEqnProperty. These should be used instead of the old PyPropertyWrapper class. There is no Python version of AuxiliaryProperty (although we could construct one, if necessary).
Property methods discussed in the OOF2 2.0 manual but not mentioned in the following list are unchanged.
 begin_point and end_point are now FluxProperty methods only and should not be defined in EqnPropertys.

Property::fluxmatrix has been replaced by FluxProperty::flux_matrix (with an underscore). Its purpose is the same as before: it computes the linearization of the Flux as a function of the Field gradients. That is, if u are the fields and Du are their gradients, then
flux = K(x,u,Du,t)*Du + s0(x,u,Du,t),
where s0 has no linear dependence on Du. flux_matrix's job is to compute K, which may be a function of the fields, their gradients, position, and/or time. The arguments to flux_matrix are unchanged from the old,fluxmatrix arguments, except that time has been added, and the FluxData* has been replaced with a SmallSystem*:virtual void flux_matrix( const FEMesh*, const Element*, const ElementFuncNodeIterator&, const Flux*, const MasterPosition&, double time, SmallSystem*) const;
flux_matrix should use SmallSystem::stiffness_matrix_element to record its results. (See SRC/engine/property/elasticity/elasticity.C for an example.) If the Flux depends on the time derivatives of the Fields, flux_matrix should use SmallSystem::damping_matrix instead of stiffness_matrix. (See SRC/engine/property/elasticity/visco/visco.C.)flux_matrix does not need to be defined for nonlinear Properties if static_flux_value (below) is defined, although some OOF2 solvers will run faster if they can call flux_matrix. Linear Properties should be able to define flux_matrix easily.

Property::fluxrhs has been replaced by FluxProperty::flux_offset, which must compute the quantity s0 defined above.
virtual void flux_offset( const FEMesh*, const Element*, const Flux*, const MasterPosition&, double time, SmallSystem*) const;
flux_offset should use SmallSystem::offset_vector_element to record its values. (See SRC/engine/property/thermalexpansion/thermalexpansion.C for an example.) 
FluxProperty::static_flux_value is a new function. It does not need to be defined if flux_matrix is defined. It computes the full Flux, except for parts that depend on time derivatives of the Fields. For most Properties, static_flux_value will be computing the actual Flux.
virtual void static_flux_value( const FEMesh *mesh, const Element *element, const Flux *flux, const MasterPosition &pt, double time, SmallSystem *fluxdata) const;
static_flux_value should use SmallSystem::flux_vector_element to record the computed values. (See SRC/engine/property/elasticity/elasticity.C for an example.) 
FluxProperty::flux_value is another new function. It only needs to be defined if the flux depends on time derivatives of the Fields and flux_matrix is not defined. It has the same arguments as static_flux_value:
virtual void flux_value( const FEMesh *mesh, const Element *element, const Flux *flux, const MasterPosition &pt, double time, SmallSystem *fluxdata) const;
EqnPropertys differ from FluxPropertys in that they make contributions directly to equations, instead of to Fluxes. The general form of an OOF2 timedependent divergence equation is
M d^{2}u/dt^{2} + C du/dt u + K u + f = 0where M is the mass matrix, C is the damping matrix, and K is the stiffness matrix. f is the vector of external forces, and u is the vector of unknowns. FluxPropertys contribute to K (and sometimes C) indirectly, via their divergences. EqnPropertys, by definition, contribute directly to M, C, K, or f.

[ ... EqnProperty methods should be described here ...]
The SmallSystem Class
The FluxData object used in 2.0.x to hold the data generated by the Property methods has been replaced by a SmallSystem object, defined in SRC/engine/smallsystem.h. (We need a better name for this class. It's called SmallSystem because it contains a small part of the full linear system of equations.
SmallSystem contains the following methods:

[... to be continued ...]
Property Registrations
Caveats
Properties written in C++ can't cross reference Properties written in Python. For example, a ThermalExpansion Property needs to be able to find its Material's Elasticity Property, so that it can call Elasticity::cijkl(). If ThermalExpansion is in C++ and Elasticity is in Python, this won't work, because as far as C++ is concerned, the Python Elasticity object is a generic PyFluxProperty instance, with no cijkl method. It will work the other way around, because cijkl() is a swigged method of the Elasticity class.
This page is still under construction.