简体   繁体   中英

Hide div that contains specific text

I want to hide a div based on the text inside. In the example below I want to hide the ones with "Handtekening" and the one with "Thuis". I prefer to do that with CSS. Is that possible?

The class names of the divs have to be the same...

<div class="test">
     Pakket
</div>
<div class="test">
     Handtekening
</div>
<div class="test">
     Thuis
</div>

If not possible with CSS, how can it be done with JavaScript?

Here's an easy vanilla Javascript solution:

let divs = document.getElementsByClassName('test');

for (let x = 0; x < divs.length; x++) {
    let div = divs[x];
    let content = div.innerHTML.trim();

    if (content == 'Handtekening' || content == 'Thuis') {
        div.style.display = 'none';
    }
}

Working JSFiddle here

Remember to include the script at the end of your HTML page (right before the </body> tag).

If you have control over the HTML output and have no problems with the text document getting twice as big, you can duplicate the content of each of those divs. Otherwise JavaScript is the way to go. Here is the CSS solution:

<div class="test" content="Pakket">
Pakket
</div>
<div class="test" content="Handtekening">
Handtekening
</div>
<div class="test" content="Thuis">
Thuis
</div>

Then use the selector for an attribute containing a string:

div[content~=Thuis] { display:none; }

The one above will match when "Thuis" is contained in the text as a separate word. If you want to match any occurrence of the string, you should use:

div[content*=and] { display:none; }

No, it won't be possible with pure CSS. You need to use JavaScript to do it.

This is code you can use for that:

var divs = document.querySelectorAll(".test");
Array.from(divs).forEach(function(div) {
  if (div.textContent.indexOf("Handtekening") >= 0 || div.textContent.indexOf("Thuis") >= 0) {
    div.style.display = "none";
  }
});

 var divs = document.querySelectorAll(".test"); Array.from(divs).forEach(function(div) { if (div.textContent.indexOf("Handtekening") >= 0 || div.textContent.indexOf("Thuis") >= 0) { div.style.display = "none"; } });
 <div class="test"> Pakket </div> <div class="test"> Handtekening </div> <div class="test"> Thuis </div>

You could do the easy thing of hiding the elements with a second class .

So let's say we'll add the class="hidden" .

See the example below:

 .test { color: blue; } .hidden { display: none; /* or visibility: hidden; */ }
 <div class="test"> Pakket </div> <div class="test hidden"> Handtekening </div> <div class="test hidden"> Thuis </div>

By adding the second class we're able to make a selection of which <div> element you'd like to show and which not.

Here's one more solution:

 Array.from( document.querySelectorAll('div.test') ) .filter( node => /\\b(Handtekening|Thuis)\\b/i.test(node.textContent) ) .forEach( node => node.style.display = 'none' );
 <div class="test"> Pakket </div> <div class="test"> HANDTEKENING </div> <div class="test"> Test thuis blah blah </div>

The main difference from chsdk's solution is that I'm using a single regexp test instead of multiple .indexOf() calls. IMO this is cleaner, more flexible and possibly more efficient as well.


The \\b anchors in the regexp match word boundaries, so that eg "Thuis test" is matched but "Thuistest" is not. I suspect this is what the OP wants, but if not, the \\b anchors can easily be removed and/or replaced with something else. For example, the regexp:

/^\s*(Handtekening|Thuis)\b/i

would match only if the words "Handtekening" or "Thuis" occur at the beginning of the content (possibly after some whitespace). Replacing the second \\b with \\s*$ would also require there to be nothing (except possibly whitespace) after the matched word.

The i flag at the end of the regexp literal makes the matching case-insensitive. If not desired, the i can simply be removed. I wanted to include it for illustrative purposes, though.


Ps. Some older browsers (such as, notably, Internet Explorer) may not support the ES6 arrow functions and the Array.from() method used in the code above. If compatibility with such old browsers is desired, here's an alternative implementation free from any such newfangled stuff:

 var nodes = document.querySelectorAll('div.test'); for (var i = 0; i < nodes.length; i++) { if ( /\\b(Handtekening|Thuis)\\b/i.test(nodes[i].textContent) ) { nodes[i].style.display = 'none'; } }
 <div class="test"> Pakket </div> <div class="test"> HANDTEKENING </div> <div class="test"> Test thuis blah blah </div>

AFAICT, this should be compatible with IE down to version 9, and of course with all modern browsers as well.

To select elements based on text you can use js and check if text is equal to ones you want to hide. If it is you can set display property to none to hide that element.

 [...document.querySelectorAll('.test')].forEach(function(e) { if (['Handtekening', 'Thuis'].includes(e.textContent.trim())) { e.style.display = 'none' } })
 <div class="test"> Pakket </div> <div class="test"> Handtekening </div> <div class="test"> Thuis </div>

You can do it just like this,

let filteredOut = ['Handtekening', 'Thuis'];

Array.from(document.querySelectorAll(".test")).forEach((elm) => {
 if(filteredOut.includes(elm.textContent.trim())) elm.style.display = "none";
});

DEMO

  • Collect the values that are needs to be filtered out in a separate array.
  • Iterate over all the elements and check its value presents in the filter array.
  • If it exists, just hide it.

Side Note: You can use a class to add to the caught elements instead of inserting inline styles.

You can do it with JavaScript:

 var elements = document.getElementsByClassName('test'); for(var i = 0; i<elements.length; i++){ if(elements[i].innerText==='Handtekening' || elements[i].innerText==='Thuis'){ elements[i].style.display = 'none'; } }
 <div class="test"> Pakket </div> <div class="test"> Handtekening </div> <div class="test"> Thuis </div>

Here's pure JavaScript solution:

// Define your variables
var objectsToCheck = document.getElementsByClassName("test");
var hideText = "Pakket";

// Loop through your div objects
[].forEach.call(objectsToCheck, function (o) {

  // Check if text appears in div under class "test"
  if(o.innerText.toLowerCase() == hideText.toLowerCase()){
      o.style.display = "none";
  }
});
  • With CSS 3: no
  • With JavaScript: yes
  • With XPath: yes (something like //div[contains(text(),'Handtekening')]/.)

You can test your XPath here .

You also have jQuery that makes this easy if you already use this library: contains(text) .

text: A string of text to look for. It's case sensitive .

The matching text can appear directly within the selected element, in any of that element's descendants, or a combination thereof. As with attribute value selectors, text inside the parentheses of :contains() can be written as a bare word or surrounded by quotation marks. The text must have matching case to be selected.

$( ".test:contains('Thuis'),.test:contains('Handtekening')" ).css( "display", "none" );

https://codepen.io/gc-nomade/pen/zEMbLz

You can use querySelector to fetch elements and use element.classList.toggle to add/remove a class that will hide the value.

 document.querySelector('#btn').addEventListener('click', function(){ var text = document.querySelector('#txt').value.trim(); var list = document.querySelectorAll('.test'); for(var i = 0; i< list.length; i++) { list[i].classList.toggle('hide', list[i].textContent.trim() === text); } })
 .hide { display: none; }
 <div class="test"> Pakket </div> <div class="test"> Handtekening </div> <div class="test"> Thuis </div> <input type='text' id='txt' /> <button id='btn'>Hide Div</button>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM