void
InterfaceOrientationMaterial::computeQpProperties()
{
  Real cutoff = 0.99999;

  // cosine of the gradient orientation angle
  Real n;
  if (_grad_op[_qp].norm() == 0)
    n = 0;
  else
    n = _grad_op[_qp](0) / _grad_op[_qp].norm();

  if (n > cutoff)
    n = cutoff;

  if (n < -cutoff)
    n = -cutoff;

  const Real angle = std::acos(n);

  // Compute derivative of angle wrt n
  const Real dangledn = - 1.0 / std::sqrt(1.0 - n * n);

  // Compute derivative of n with respect to grad_op
  RealGradient dndgrad_op;
  if (_grad_op[_qp].norm_sq() == 0)
    dndgrad_op = 0;
  else
  {
    dndgrad_op(0) = _grad_op[_qp](1) * _grad_op[_qp](1);
    dndgrad_op(1) = - _grad_op[_qp](0) * _grad_op[_qp](1);
    dndgrad_op /= (_grad_op[_qp].norm_sq() * _grad_op[_qp].norm());
  }

  // Calculate interfacial parameter epsilon and its derivatives
  _eps[_qp]= _eps_bar * (_delta * std::cos(_j * (angle - _theta0 * libMesh::pi/180.0)) + 1.0);
  _deps[_qp]= - _eps_bar * _delta * _delta * std::sin(_j * (angle - _theta0 * libMesh::pi/180.0));
  Real d2eps = - _eps_bar * _delta * _delta * _delta * std::cos(_j * (angle - _theta0 * libMesh::pi/180.0));

  // Compute derivatives of epsilon and its derivative wrt grad_op
  _depsdgrad_op[_qp] = _deps[_qp] * dangledn * dndgrad_op;
  _ddepsdgrad_op[_qp] = d2eps * dangledn * dndgrad_op;
}
void
WidmanstattenMaterial::computeQpProperties()
{
  const Real tol = 1e-9;
  const Real cutoff = 1.0 - tol;

  // cosine of the gradient orientation angle
  Real n = 0.0;
  const Real nsq = _grad_op[_qp].norm_sq();
  if (nsq > tol)
    n = _grad_op[_qp](0) / std::sqrt(nsq);

  if (n > cutoff)
    n = cutoff;

  if (n < -cutoff)
    n = -cutoff;

  const Real angle = std::acos(n) * MathUtils::sign(_grad_op[_qp](1));

  // Compute derivative of angle wrt n
  const Real dangledn = - MathUtils::sign(_grad_op[_qp](1)) / std::sqrt(1.0 - n * n);

  // Compute derivative of n with respect to grad_op
  RealGradient dndgrad_op;
  if (nsq > tol)
  {
    dndgrad_op(0) = _grad_op[_qp](1) * _grad_op[_qp](1);
    dndgrad_op(1) = - _grad_op[_qp](0) * _grad_op[_qp](1);
    dndgrad_op /= (_grad_op[_qp].norm_sq() * _grad_op[_qp].norm());
  }

  // Calculate interfacial parameter epsilon and its derivatives
  _eps[_qp]= _eps_bar * (_delta * std::cos(_j * (angle - _theta0 * libMesh::pi/180.0)) + 1.0) * (1 / (1 + _delta));
  _deps[_qp]= - _eps_bar * (_delta * _j * std::sin(_j * (angle - _theta0 * libMesh::pi/180.0)) * (1 / (1 + _delta)));
  Real d2eps = - _eps_bar * (_delta * _j * _j * std::cos(_j * (angle - _theta0 * libMesh::pi/180.0)) * (1 / (1 + _delta)));

  // Compute derivatives of epsilon and its derivative wrt grad_op
  _depsdgrad_op[_qp] = _deps[_qp] * dangledn * dndgrad_op;
  _ddepsdgrad_op[_qp] = d2eps * dangledn * dndgrad_op;
}