Element appearing with :focus-visible

Viewed 53

In my project I have a list of 'result items' which can be favourited and then they appear on in a favourites column to the side of the page.

To allow keyboard users easy access, I have created a hidden cta which allows them to skip directly to their favourited item, without having to tab through all the result items first.

I only want this cta to be visible when it is tabbed to. My understanding is that :focus-visible would enable this. However, for some reason, it's not working for me. My HTML and CSS look like:

.sr-only-focusable {
  position: absolute;
  visibility: hidden;
  left: 56%;
  top: rem(65);
  border-radius: 5px;
  border: 1px solid #d7d7d7;
  background-color: $white;
  padding: 1rem 2rem;
  z-index: 10;
}

.sr-only-focusable:focus-visible {
  visibility: visible;
}
<div class="sr-only-focusable">
  <button tabindex="0" @click="skipToShortlist">Skip To Shortlist</button>
</div>

Could anyone help me figure out where i'm going wrong?

Thanks in advance

2 Answers

The button element is what you're trying to tab to, not the div it's contained in. Rather than trying to get to the div, target the button instead. Also, use opacity because visibility doesn't seem to play nicely with tabindex. You can also apply your styling to the button as well.

.sr-only-focusable {
  position: absolute;
  left: 56%;
  top: rem(65);
  z-index: 10;
}

.myBtn {
  display: inline-block;
  font-family: Helvetica, Arial, sans-serif;
  color: black;
  margin: 0 auto;
  font-size: 1.2vw;
  font-weight: 700;
  line-height: 1.25;
  letter-spacing: 0.5px;
  cursor: pointer;
  text-decoration: none;
  opacity: 0;
  border-radius: 5px;
  border: 1px solid #d7d7d7;
  background-color: $white;
  padding: 1rem 2rem;
}

.myBtn:focus-visible {
  opacity: 1;
}
<div class="sr-only-focusable">
  <button class="myBtn" tabindex="0" @click="skipToShortlist">Skip To Shortlist</button>
</div>

From my experience (mostly on chrome) elements with display:none or visibility:hidden cannot be focused by mouse or by keyboard.

Most implementations use something along the lines of this:

.wrapper {
  background: black;
  text-align: center;
  width: 360px;
  height: 100px;
  padding: 40px;
  box-sizing: border-box;
  color: blanchedalmond;
}
.image-nav-button {
  color: blanchedalmond;
  text-decoration: none;
  font-size: 20px;
  line-height: 1em;
  width:1px;
  height:1px;
  position:absolute;
  clip: rect(1px,1px,1px,1px);
  clip-path: inset(50%);
}
.next {
  float: right;
}
.prev {
  float: left;
}

.image-nav-button:focus {
  outline: none;
  /* Try uncommenting below, then clicking the buttons */
  /* outline: 3px solid red; */
}
.image-nav-button:focus-visible {
  outline: 3px solid blanchedalmond;
    width:auto;
  height:auto;
  position:relative;
  clip: none;
  clip-path: none;
}
<div class="wrapper">
<a href="#" tabindex="1" class="image-nav-button prev">&larr; Prev Image</a>
<a href="#"  tabindex="2" class="image-nav-button next">Next Image &rarr;</a>
</div>

Related