I boiled this down to as few code as I could without loosing function. You have to run this in Firefox, Chrome has an already reported and confirmed bug involved.
If you click on the second Item (“click here first”) you open a submenu and if you click one of the not-checkboxed-items, that will autoclose.
however, if you click on the checkbox’d item, it should stay open. For the checkbox, this works, but a click on the label doesnt check the box and closes the sublist. can anyone spot, why this is the case?
Both are coupled with id and for, so they should behave he same.
:root {
--menu-padding:0.5em;
--menu-checkmargin:0.5em;
--menu-checksize:1em;
}
nav ul {
position:absolute; white-space:nowrap;
display:flex; width:fit-content;
list-style-type:none; margin:0; padding:0;
}
nav ul > li:has(> a) {
padding: 0;
}
nav ul > li:has(> a) > a {
display: inline-block;
padding: var(--menu-padding);
}
nav ul li:focus-within > ul {
display: flex;
}
nav ul li:focus-within > ul:focus {
height: 0 !important;
width: 0 !important;
margin: 0 !important;
padding: 0 !important;
overflow: hidden !important;
content-visibility: hidden;
}
nav li {
position: relative;
align-items: left;
display: flex;
box-sizing: border-box;
justify-content: space-between;
line-height: 1;
padding: var(--menu-padding);
}
ul.qm-tiled {
position: relative;
text-align: left;
flex-direction: column;
white-space-collapse: collapse;
left: 0;
}
ul.qm-tiled > li:focus-within:has(ul) {
flex-direction: column;
justify-content: space-between;
}
ul.qm-tiled > li:has(> ul:focus) {
flex-direction: row;
}
ul.qm-tiled > li {
display: flex;
}
ul.qm-tiled > li > ul {
bottom: calc(-1 * var(--menu-padding));
}
ul.qm-tiled ul {
position: relative;
margin: 0 calc(-1 * var(--menu-padding));
width: auto;
}
ul.qm-tiled li:not(:has(ul)):hover:focus {
visibility: hidden;
}
ul.qm-tiled:has(> li > label) > li:not(ul.qm-tiled:has(> li > label) > li:has(> label)) {
padding-left: calc(var(--menu-checkmargin) + var(--menu-checksize) + var(--menu-padding));
}
ul.qm-tiled:has(> li > label) > li label {
padding-left: var(--menu-checkmargin);
}
ul.qm-tiled > li {
width: 100%;
}
ul.qm-tiled ul {
display: none;
position: relative;
text-align: left;
flex-direction: column;
white-space-collapse: collapse;
}
ul.qm-tiled ul > li:focus-within:has(ul) {
flex-direction: column;
justify-content: space-between;
}
ul.qm-tiled ul > li:has(> ul:focus) {
flex-direction: row;
}
ul.qm-tiled ul > li {
display: flex;
}
ul.qm-tiled ul > li > ul {
bottom: calc(-1 * var(--menu-padding));
}
ul.qm-tiled ul ul {
position: relative;
margin: 0 calc(-1 * var(--menu-padding));
width: auto;
}
ul.qm-tiled ul li:not(:has(ul)):hover:focus {
visibility: hidden;
}
ul.qm-tiled ul:has(> li > label) > li:not(ul.qm-tiled ul:has(> li > label) > li:has(> label)) {
padding-left: calc(var(--menu-checkmargin) + var(--menu-checksize) + var(--menu-padding));
}
ul.qm-tiled ul:has(> li > label) > li label {
padding-left: var(--menu-checkmargin);
}
nav input[type=checkbox], nav input[type=radio] {
display: inline-flex;
line-height: 1;
font-size: 100%;
min-width: var(--menu-checksize);
height: 0.75em;
margin: 0;
padding: 0;
}
<nav>
<ul class="qm-tiled">
<li tabindex="0">[Item 1]</li>
<li tabindex="0">[click here first]
<ul tabindex="-1">
<li tabindex="0">[Subitem]</li>
<li><input type="checkbox" id="chk22a" name="chk22a" /><label for="chk22a">[LABEL]</label></li>
</ul>
<li tabindex="0">[Item 3]</li>
</ul>
</nav>
When the LABEL is clicked, the first thing that happens is the label is sent a focus event. Since the label isn’t focusable, the event is passed to the LI, and then to the UL, which since it has a tabindex becomes the focused element. This causes the label to be hidden so it does not receive the click event and the checkbox cannot receive the activation action.
When the checkbox is clicked, it receives the focus, the UL doesn’t. and the label is not hidden, so it receives the click event and the checkbox receives the activation action.
You can verify this by giving the label a tabindex so that it can receive the focus.
:root {
--menu-padding:0.5em;
--menu-checkmargin:0.5em;
--menu-checksize:1em;
}
nav ul {
position:absolute; white-space:nowrap;
display:flex; width:fit-content;
list-style-type:none; margin:0; padding:0;
}
nav ul > li:has(> a) {
padding: 0;
}
nav ul > li:has(> a) > a {
display: inline-block;
padding: var(--menu-padding);
}
nav ul li:focus-within > ul {
display: flex;
}
nav ul li:focus-within > ul:focus {
height: 0 !important;
width: 0 !important;
margin: 0 !important;
padding: 0 !important;
overflow: hidden !important;
content-visibility: hidden;
}
nav li {
position: relative;
align-items: left;
display: flex;
box-sizing: border-box;
justify-content: space-between;
line-height: 1;
padding: var(--menu-padding);
}
ul.qm-tiled {
position: relative;
text-align: left;
flex-direction: column;
white-space-collapse: collapse;
left: 0;
}
ul.qm-tiled > li:focus-within:has(ul) {
flex-direction: column;
justify-content: space-between;
}
ul.qm-tiled > li:has(> ul:focus) {
flex-direction: row;
}
ul.qm-tiled > li {
display: flex;
}
ul.qm-tiled > li > ul {
bottom: calc(-1 * var(--menu-padding));
}
ul.qm-tiled ul {
position: relative;
margin: 0 calc(-1 * var(--menu-padding));
width: auto;
}
ul.qm-tiled li:not(:has(ul)):hover:focus {
visibility: hidden;
}
ul.qm-tiled:has(> li > label) > li:not(ul.qm-tiled:has(> li > label) > li:has(> label)) {
padding-left: calc(var(--menu-checkmargin) + var(--menu-checksize) + var(--menu-padding));
}
ul.qm-tiled:has(> li > label) > li label {
padding-left: var(--menu-checkmargin);
}
ul.qm-tiled > li {
width: 100%;
}
ul.qm-tiled ul {
display: none;
position: relative;
text-align: left;
flex-direction: column;
white-space-collapse: collapse;
}
ul.qm-tiled ul > li:focus-within:has(ul) {
flex-direction: column;
justify-content: space-between;
}
ul.qm-tiled ul > li:has(> ul:focus) {
flex-direction: row;
}
ul.qm-tiled ul > li {
display: flex;
}
ul.qm-tiled ul > li > ul {
bottom: calc(-1 * var(--menu-padding));
}
ul.qm-tiled ul ul {
position: relative;
margin: 0 calc(-1 * var(--menu-padding));
width: auto;
}
ul.qm-tiled ul li:not(:has(ul)):hover:focus {
visibility: hidden;
}
ul.qm-tiled ul:has(> li > label) > li:not(ul.qm-tiled ul:has(> li > label) > li:has(> label)) {
padding-left: calc(var(--menu-checkmargin) + var(--menu-checksize) + var(--menu-padding));
}
ul.qm-tiled ul:has(> li > label) > li label {
padding-left: var(--menu-checkmargin);
}
nav input[type=checkbox], nav input[type=radio] {
display: inline-flex;
line-height: 1;
font-size: 100%;
min-width: var(--menu-checksize);
height: 0.75em;
margin: 0;
padding: 0;
}
<nav>
<ul class="qm-tiled">
<li tabindex="0">[Item 1]</li>
<li tabindex="0">[click here first]
<ul tabindex="-1">
<li tabindex="0">[Subitem]</li>
<li><input type="checkbox" id="chk22a" name="chk22a" /><label for="chk22a" tabindex=0>[LABEL]</label></li>
</ul>
<li tabindex="0">[Item 3]</li>
</ul>
</nav>
3