Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Accessible, keyboard-friendly way to remove focus style from checkbox label after mouseup

Tags:

I have styled input:focus + label to visually indicate when an input has been focused using keyboard navigation.

But Chrome (and maybe not just Chrome?) persists the :focus state after using a mouse to click the input, which looks ugly.

I want to remove the :focus styling after the click without altering keyboard navigation. i.e., when you move your mouse away after clicking a label, it should no longer be red.

I have seen suggestions to .blur() the input on mouseup; but 1) it hasn't worked for me (see snippet below), and 2) I'm concerned it will take keyboard navigation out of its usual flow.

Yes, someone using the mouse to click a checkbox and then going to keyboard navigation is an edge case. But it's one I would like to account for.

$("label").mouseup(function () {
	$(this).blur();  // This has no apparent affect.
	$("#" + this.htmlFor).blur();  // Or this.
});
input:hover + label, input:focus + label {
  color: red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<form>
  <p>Form Part One</p>
  <input type="checkbox" id="cb1" name="cb" /><label for="cb1">First Checkbox</label><br>
  <input type="checkbox" id="cb2" name="cb" /><label for="cb2">Second Checkbox</label>
  
  <p>Form Part Two</p>
  <input type="radio" id="r1" name="r" /><label for="r1">First Radio</label><br>
  <input type="radio" id="r2" name="r" /><label for="r2">Second Radio</label>
</form>
like image 669
crenshaw-dev Avatar asked Sep 19 '17 18:09

crenshaw-dev


2 Answers

EDITED based on comment:

//set checkbox hover
$("input").hover(function() {
  $(this).next("label").css("color", "red");
}, function() {
  $(this).next("label").css("color", "black");
});
//set label hover
$("label").hover(function() {
  $(this).css("color", "red");
}, function() {
  $(this).css("color", "black");
});
//set checkbox focusin focusout
$("input").focusin(function() {
  $(this).next("label").css("color", "red");
  $(this).next("label").siblings().css("color", "black");
});
//set checkbox label active on click
$('input:checkbox').on('click', function() {
  $(this).next('label').toggleClass('active');
});
//set radio label active on click
$('input:radio').on('click', function() {
  $(this).next('label').toggleClass('active');
  $(this).siblings().next('label').removeClass('active');
});
.active {
  color: red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<form>
  <p>Form Part One</p>
  <input type="checkbox" id="cb1" name="cb" /><label for="cb1">First Checkbox</label><br>
  <input type="checkbox" id="cb2" name="cb" /><label for="cb2">Second Checkbox</label>
  <p>Form Part Two</p>
  <input type="radio" id="r1" name="r" /><label for="r1">First Radio</label><br>
  <input type="radio" id="r2" name="r" /><label for="r2">Second Radio</label>
</form>
like image 190
Syden Avatar answered Oct 11 '22 15:10

Syden


I might be misunderstanding you here, but I think the issue is that you are putting your event trigger on the wrong element. Input is the parent of label in the case of your html structure, and is the active element upon which the mouseup event should trigger.

  

$("input").mouseup(function () {
	$(this).blur();  // This has no apparent affect.
	$("#" + this.htmlFor).blur();  // Or this.
});
input:hover + label, input:focus + label {
  color: red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<form>
  <p>Form Part One</p>
  <input type="checkbox" id="cb1" name="cb" /><label for="cb1">First Checkbox</label><br>
  <input type="checkbox" id="cb2" name="cb" /><label for="cb2">Second Checkbox</label>
  
  <p>Form Part Two</p>
  <input type="radio" id="r1" name="r" /><label for="r1">First Radio</label><br>
  <input type="radio" id="r2" name="r" /><label for="r2">Second Radio</label>
</form>
like image 39
D Lowther Avatar answered Oct 11 '22 16:10

D Lowther