Use constant grid in output writing

Grid manager returns a const UnstructuredGrid*, and the entire chain
of pointer-passing glory should adhere to this const-ness.
Use correct pointer indirection

When the sim parameter is a pointer to a simulator, we must of course
use indirect access to its field; the shared_ptr template class does not
have this method!
Define destructor in .cpp to avoid defining members

If the compiler is to create the default destructor for us, it will
need the size of the OutputWriter type to be defined at the time of
inclusion in the header. By explicitly defining it in a compilation
unit, we can avoid that.
Define Event type completely

The Event type must be known because we call it from the inline template
method. The alternative is worse, we'd have to instantiate the template
for every possible simulator type in the .cpp!