2015-02-01 1 views
3

В следующем коде я пытаюсь заменить каждое изображение, найденное в $content, на некоторый html. С $dom->saveHTML($image) Я получаю изображение html, но str_replace не заменяет его. Я не знаю почему.Заменить тег изображения на div с помощью DOMDocument и вернуть измененный html

$content = '<div class="content"><img src="some-image.png"></div>'; 
$dom = new DOMDocument; 
$dom->loadHTML($content); 
$images = $dom->getElementsByTagName('img'); 
foreach ($images as $image) { 
    $i = $dom->saveHTML($image); 
    $replacement = '<div class="test"><a href="#">some link</a><span>test</span></div>'; 
    $content = str_replace($i, $replacement, $content); 
} 
// $content should be altered with the previous edits. 
return $content; 

В конце, $content должен вернуться:

<div class="content"><div class="test"><a href="#">some link</a><span>test</span></div></div> 

Любая идея?

+2

Не используйте str_replace. Это DOM, мы можем использовать replaceChild. – Mouser

ответ

3
$dom = new DOMDocument; 
$dom->loadHTML($content); 
$images = $dom->getElementsByTagName('img'); 
foreach ($images as $image) { 
    $node = $dom->createElement("div"); 
    $frag = $dom->createDocumentFragment(); // create fragment 
    $frag->appendXML('<div class="test"><a href="#">some link</a><span>test</span></div>'); 
    $node.appendChild($frag); 
    $image->parentNode->replaceChild($node, $image); 
} 

Это HTML. Динамическая природа HTML очень затрудняет правильное выполнение регулярного выражения или замены строк. Однако PHP позволяет манипулировать домом с помощью DomDocument. Поэтому выберите изображения parentNode и замените изображение на div.

Обновлено с использованием createDocumentFragment(). Это создаст фрагмент DOM в памяти. Вы можете appendXML (читать HTML) к нему как строку. Затем вы можете добавить фрагмент к узлу.

+0

Я обновил свой вопрос, не могли бы вы взглянуть на него? – inwpitrust

+0

@ inwpitrust. Как просили. Однако с самого начала вы должны четко прояснить свой вопрос. Наши ответы здесь позволили решить вопрос, который вы задали. Или отправьте новый вопрос или сделайте окончательный результат очевидным в своем исходном вопросе. – Mouser

+0

«сделать окончательный результат очевидным в вашем исходном вопросе». Вы имеете в виду, что я должен добавить элементы, указанные в вашем ответе, в моем вопросе? Разве это не редондант? Спасибо за вашу помощь! – inwpitrust

3

Путь заменить DOMNode является использование метода replaceChild (str_replace должен иметь дело только с строками):

$dom = new DOMDocument; 
$dom->loadHTML($content); 
$imgNodeList = $dom->getElementsByTagName('img'); 

foreach ($imgNodeList as $imgNode) { 
    $divNode = $dom->createElement('div'); 
    $textNode = $dom->createTextNode('test'); 
    $divNode->appendChild($textNode); 

    $imgNode->parentNode->replaceChild($divNode, $imgNode); 
} 

Если замена более сложной, чем сНу тег с текстом внутри, вы нужно только создать узел замены таким же образом (добавив к нему другие узлы). Чтобы ознакомиться с атрибутами, см. http://php.net/manual/en/domdocument.createattribute.php

+0

Я обновил свой вопрос, не могли бы вы взглянуть на него? – inwpitrust

+0

@ inwpitrust: Я взглянул, теперь у вас есть все элементы, чтобы сделать это самостоятельно (см., Как я добавил текстовый узел в узел div). –

+0

Спасибо! Я отредактировал свой вопрос, чтобы отразить то, что мне нужно в первую очередь, можете ли вы дать мне несколько советов о том, как вернуть $ content в качестве измененного var? – inwpitrust