sorry_i_noob
@sorry_i_noob

Как в php удалить из строки определенные теги? Функция strip_tags удалет все кроме определенных. А мне нужно только определенные. Как это сделать?

Здравствуйте. Собственно, сабж.

Знаю, что регулярки - не лучший способ( https://stackoverflow.com/questions/11229831/regul... ). Думаю, что можно попробовать внести все существующие теги в массив. Потом найти расхождение у этого массива с массивом, в котором те теги, которые я хочу удалить. И потом применить strip_tags. Как вы думаете, хороший вариант? Вот бы только упростить как-нибудь создание массива со всеми тегами...
  • Вопрос задан
  • 2146 просмотров
Решения вопроса 1
sorry_i_noob
@sorry_i_noob Автор вопроса
Решил вопрос вот так:
static public function create_dom($string = null) {
		$dom = new DOMDocument();
		// ----------------------------------------------------------------
		// Делается обертка в виде <div> для $string. Это нужно, так как из-за LIBXML_HTML_NOIMPLIED теги могут выводиться несколько некорректно. Подробности по ссылке:
		// https://stackoverflow.com/questions/29493678/loadhtml-libxml-html-noimplied-on-an-html-fragment-generates-incorrect-tags
		// Также добавляется кодировка - так как без вместо текста, полученного от ckeditor, будут кракозябры.
		// ----------------------------------------------------------------
		$dom->loadHTML('<meta http-equiv="Content-Type" content="text/html; charset=utf-8">' . '<div>' . $string . '</div>', LIBXML_HTML_NOIMPLIED | LIBXML_HTML_NODEFDTD);
		$container = $dom->getElementsByTagName('div')->item(0);
		$container = $container->parentNode->removeChild($container);
		while ($dom->firstChild) {
			$dom->removeChild($dom->firstChild);
		}
		while ($container->firstChild) {
			$dom->appendChild($container->firstChild);
		}

		return $dom;
}

static public function unwrap_tags($string, $tags) {
		$dom = static::create_dom($string);

		foreach ($dom->childNodes as $c) {
			if (in_array($c->tagName, $tags)) {
				// если просто добавить в $result $c->nodeValue, то не добавятся внутренние теги (<br>, например), ведь их нет в nodeValue.
				foreach ($c->childNodes as $cc) {
					$result .= $cc->ownerDocument->saveHTML($cc);
				}
			} else {
				$result .= $c->ownerDocument->saveHTML($c);
			}
		}

		return $result;
}

static public function prepare_text($text) {
		$text = static::unwrap_tags($text, array('p', 'div', 'span'));
		return $text;
}

Вроде все работает.
Ответ написан
Комментировать
Пригласить эксперта
Ответы на вопрос 2
sergiks
@sergiks Куратор тега PHP
♬♬
Валидных HTML тегов – конечное множество. Их все можно перечислить. Исключить «определенные».

Потом strip_tags().
Ответ написан
bubandos
@bubandos
bash'у, javascript'ую, php'лю, css'аю, html'каю
А чем регулярки плохи? Имхо - лучший способ.
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы