Подтвердить что ты не робот

Селектор CSS для пустых или белых пробелов

У нас есть селектор :empty, который может соответствовать элементу, когда он полностью пуст:

<p></p>

Но у меня есть условие, когда оно может быть пустым или оно может содержать разрывы строк или пробелы:

<p>    </p>

Я нашел решение для Firefox, :-moz-only-whitespace:

:empty { width: 300px; height: 15px; background: blue; }
:-moz-only-whitespace { width: 300px; height: 15px; background: orange; }
<p></p>
<p>    </p>
<p>This is paragraph three.</p>
4b9b3361

Ответ 1

Пока в вопросе изображен элемент <p>, содержащий несколько регулярных символов пробела, который выглядит как надзор, гораздо чаще встречается разметка, где элементы содержат только пробелы в виде отступов и пустых строк, например

<ul class="items">
  <li class="item">
    <div>
      <!-- Some complex structure of elements -->
    </div>
  </li>
  <li class="item">
  </li> <!-- Empty, except for a single line break and
             indentation preceding the end tag -->
</ul>

Некоторые элементы, такие как <li> в приведенном выше примере, а также <p>, имеют необязательные концевые теги, которые также могут вызвать непреднамеренные побочные эффекты в обработке DOM при наличии межэлементных пробелов. Например, следующие два элемента <ul> не генерируют эквивалентные деревья node, в частности первый не приводит к li:empty:

li:empty::before { content: '(empty)'; font-style: italic; color: #999; }
<ul>
  <li>
</ul>
<ul>
  <li></li>
</ul>

Ответ 2

@BoltClock предоставил фантастический ответ на этот вопрос, показывая, что это (в настоящее время, т.е. работа с CSS-спецификацией 3) не может быть достигнуто только с помощью CSS.

@BoltClock упомянул, что элементы, которые являются действительно пустыми (что является странным определением, как описано), могут быть нацелены с помощью псевдоселектора :empty. Этот псевдоселектор доступен только в CSS 3 и НЕ выбирает элементы, которые содержат только пробелы в качестве содержимого.

@BoltClock заявила, что единственный способ очистить элементы, которые имеют только пробелы, как содержимое, - это исправить HTML, но это не совсем правильно. Это также может быть достигнуто благодаря внедрению Javascript.

ХРАНИТЬ В УМТЕ! Javascript, который я предлагаю решить эту проблему, может занять очень много времени, поэтому лучший способ - очистить необработанный HTML, если это возможно. Если это невозможно, тогда это может работать как решение, если у вас недостаточно обширного дерева DOM.

Я пройду шаги, чтобы написать script самостоятельно...

Прежде всего, запустите все после загрузки страницы.

Это должно быть довольно очевидно. Перед запуском script убедитесь, что DOM полностью загружен. Добавьте event listener для загрузки страницы:

window.addEventListener("load", cleanUpMyDOM);

... и, конечно же, до этого создайте function, называемый cleanUpMyDOM. Мы напишем остальную часть нашей логики в этой функции.

Второй, соберите элементы, которые мы проверяем.

В нашем примере мы будем проверять всю DOM, но здесь наш script может стать ОЧЕНЬ обширным и может сделать вашу страницу неактуальной. Вы можете ограничить количество узлов, которые вы итерируете.

Мы можем захватить рассматриваемые узлы, используя document.querySelectorAll. Что приятно в этой функции, так это то, что она выровнят дерево DOM, и нам не придется перезаписывать детей из каждого node.

var nodes = document.querySelectorAll("*");

Как я уже говорил ранее, этот код будет захватывать КАЖДОЙ DOM node, и это, вероятно, НЕ хорошая идея.

Например, я работаю с WordPress, и некоторые из внутренних страниц имеют в них некоторый барахло. К счастью, это все элементы p, которые являются дочерними элементами элемента div.body, поэтому я могу изменить селектор на document.querySelectorAll("div.body p"), который будет рекурсивно выбирать только элементы p, которые являются дочерними элементами моего элемента div.body. Это значительно оптимизирует мой script.

Третий, итерации узлов и найти пустые.

Мы создадим цикл для массива nodes и проверим в нем node. Затем нам нужно будет проверить, пуст ли node. Если он пуст, мы применим к нему класс под названием blank.

Я просто снимаю с бедра здесь, поэтому, если вы заметили ошибку в этом коде, сообщите мне.

for(var i = 0; i < nodes.length; i++){
    nodes[i].innerHTML = nodes[i].innerHTML.trim();
    if(!nodes[i].innerHTML)
        nodes[i].className += " blank";
}

Я уверен, что есть более чистый способ написать цикл выше, но это должно выполнить задание.

Наконец,, все, что вам нужно сделать, это нацелить пустые элементы на ваш CSS.

Добавьте это правило в таблицу стилей:

.blank {
    display:none;
}

И вот оно! Все ваши "пустые" узлы были скрыты.

Для тех, кто просто хочет перейти вперед, вот готовый script:

function cleanUpMyDOM(){
    var nodes = document.querySelectorAll("*");
    for(var i = 0; i < nodes.length; i++){
        nodes[i].innerHTML = nodes[i].innerHTML.trim();
        if(!nodes[i].innerHTML)
            nodes[i].className += " blank";
    }
}
window.addEventListener("load", cleanUpMyDOM);

Еще раз, если вы заметили какие-либо проблемы с моим кодом, пожалуйста, дайте мне знать в комментариях ниже.

Надеюсь, это поможет!

P.S.. Многие люди могут задаваться вопросом, почему вы хотели бы это сделать, потому что это похоже на плохую практику. Я бы этого не сделал, но я в ситуации, когда я начинаю это рассматривать. Содержимое страниц на моем сайте создается через редактор WYSIWYG. Этот контент постоянно создается и постоянно изменяется командой по маркетингу, и я становлюсь довольно перегруженным, обрабатывая поддержку их промахов. Не моя работа по исправлению редактора WordPress WYSIWYG (и я никогда не захочу), но я мог бы написать очень простой script, который может обрабатывать некоторые из моих работ. Это определенно кажется лучшим ответом на меня, помимо обучения команды поддержки управлению их пробелами при внесении изменений.