21

I have this in using Bootstrap:

    <ul class="list-group">
        <li  class="list-group-item active">Cras justo odio</li>
        <li class="list-group-item">Dapibus ac facilisis in</li>
        <li class="list-group-item">Morbi leo risus</li>
        <li class="list-group-item">Porta ac consectetur ac</li>
        <li class="list-group-item">Vestibulum at eros</li>
        <li class="list-group-item">Cras justo odio</li>
        <li class="list-group-item">Dapibus ac facilisis in</li>
        <li class="list-group-item">Morbi leo risus</li>
        <li class="list-group-item">Porta ac consectetur ac</li>
        <li class="list-group-item">Vestibulum at eros</li>
    </ul>

The top row is selected.

I only ever want to show to the User 1 selected row.

I can raise an event when the User clicks on a row by adding a function to a Click-Event using Javascript.

I can then set that Row to be Active. but what happens is that the previous selected Row needs to be deselected.

What is the accepted way to do this?

How do I enumerate and access each row to change its Class settings?

Is there a better CSS way to do this?

ADDITIONAL All these methods work (thanks everyone) but if I have more than 1 option group on my page how can I explicitly remove the active highlighted row on the one I am using?

Paolo
  • 20,112
  • 21
  • 72
  • 113
Andrew Simpson
  • 6,883
  • 11
  • 79
  • 179

10 Answers10

26

Here we go buddy. I have made a JSfiddle for ya

demo

$(function(){
    console.log('ready');

    $('.list-group li').click(function(e) {
        e.preventDefault()

        $that = $(this);

        $that.parent().find('li').removeClass('active');
        $that.addClass('active');
    });
})

JSFiddle updated to have more than one Group

http://jsfiddle.net/mgjk3xk2/1/

Sahan
  • 1,422
  • 2
  • 18
  • 33
  • Why would you make a variable for $(this) as $that? It doesn't seem to serve a purpose. – Edward Sep 02 '16 at 15:10
  • Rather than using jquery to get the "this" object multiple times I save the "this" in a variable and then use it everywhere. So the idea is create it once and use it as much as you want. – Sahan Sep 03 '16 at 18:16
  • @Sahan you should also change the event handler to only attach once to the `.list-group` instead of every `li` – NorCalKnockOut Nov 15 '16 at 18:29
13

If you'd be using jQuery, it looks like this:

$(".list-group .list-group-item").click(function(e) {
   $(".list-group .list-group-item").removeClass("active");
   $(e.target).addClass("active");
});
Jevgeni
  • 2,556
  • 1
  • 15
  • 18
3
var $lis = $('.list-group li')
$lis.on('click', function(){
  $lis.removeClass('active')
  $(this).addClass('active')
})
Yohn
  • 2,519
  • 19
  • 23
1

I would use javascript to first find the first element within your list-group element that has the "active class", then remove that class. When you've done that, you can then proceed to add the active class to the element you clicked on.

This can be done with jQuery's .addClass() and .removeClass() functionality.

Rik_S
  • 381
  • 4
  • 13
1

just another way that i think this is a better way:

$(document).off("click" ,".list-group .list-group-item").on("click" ,".list-group .list-group-item" ,function(){

    $(this).sibbling().removeClass("active");
    $(this).addClass("active");
});
Iraj
  • 1,492
  • 5
  • 18
  • 42
  • I use this method with good results, although i think you mean $(this).addClass("active"); not $(this).addClass("class"); – MX313 Mar 09 '20 at 20:29
1

Here is a solution I have had success with. I have a menu with several Li items, the following solution will switch the formatting of selected element and will deselect the previous one.

javascript:

myList.addEventListener("click", function (e) {
  if (e.target && e.target.nodeName == "LI") {
    let current = document.getElementsByClassName("activeMenuItem");
    if (current.length > 0) {
      current[0].classList.remove("activeMenuItem");
    }
    e.target.classList.add("activeMenuItem");
  }
});

css: .activeMenuItem {background-color:white; color:black;}

sb16
  • 65
  • 1
  • 9
0

Probably bootstrap cannot it. You can use our own class name and write our own css similarly as in bootstrap.

For example:

.choised > span { color: #DDDDDD; }

0

I made a solution using CSS only (no JavaScript). However, it doesn't work with standard <ul> and <li> HTML tags. In other words, the result will look like a Boostrap list group in style only, but won't be an HTML list, semantically speaking.

It's a shame that CSS doesn't have a :parent selector, and the :has selector cannot be used within stylesheets, which would help us achieve what you are suggesting.

If you are okay with trading semantically-broken code for your desired style, my solution will certainly help you.

It boils down to hiding an <input type="radio" /> element, but not its <label>, and then using a CSS pseudo-selector in order to make the list element change its style when the radio button is selected.

The basic CSS would be:

.list-group input[type="radio"] {
  display: none;
}

.list-group input[type="radio"]:checked + .list-group-item {
  background-color: #0275D8;
  color: #FFF;
}

And the basic HTML would be:

<div class=""list-group>
  <input type="radio" name="RadioInputName" value="Value1" id="Radio1" />
  <label class="list-group-item" for="Radio1">Caption for Radio1</label>
</div>

Here's a CodePen in case you want to see the code in action: https://codepen.io/lehonti/pen/OzoXVa

Lehonti
  • 133
  • 8
0

This works for me...

$(document).off("click", ".list-group .list-group-item").on("click", ".list-group .list-group-item", function () {
    try {
        $(".list-group .list-group-item").removeClass("active");
    } catch (e) { }

    $(this).addClass("active");
});
MX313
  • 129
  • 1
  • 9
0
$(function(){
    console.log('ready');
    
    $('.list-group li').click(function(e) {
        e.preventDefault()
        
        $that = $(this);
        
        $that.parent().find('li').removeClass('active');
        $that.addClass('active');
    });
})

  //style
      .list-group-item.active 
      {
        z-index: 2;
        color: #fff;
         background-color: white; 
        border-color: #0168fa;
        color: white;
      }
     
  • Code-only answers are not particularly helpful. Please add some descriptions of how this code solves the problem. – Sven Eberth Jun 09 '21 at 23:08