Here's another approach based on this comment by Drupella on php.net, that worked well for my project. It defines the innerHTML() by creating a new DOMDocument, importing and appending to it the target node, instead of explicitly iterating over child nodes.
InnerHTML
Let's define this helper function:
function innerHTML( \DOMNode $n, $include_target_tag = true ) {
$doc = new \DOMDocument();
$doc->appendChild( $doc->importNode( $n, true ) );
$html = trim( $doc->saveHTML() );
if ( $include_target_tag ) {
return $html;
}
return preg_replace( '@^nodeName .'[^>]*>|'. $n->nodeName .'>$@', '', $html );
}
where we can include/exclude the outer target tag through the second input argument.
Usage Example
Here we extract the inner HTML for a target tag given by the "first" id attribute:
$html = '
Hello
World!
$doc = new \DOMDocument();
$doc->loadHTML( $html );
$node = $doc->getElementById( 'first' );
if ( $node instanceof \DOMNode ) {
echo innerHTML( $node, true );
// Output:
Hello
echo innerHTML( $node, false );
// Output:
Hello
}
Live example: