The same evening I shipped this, Chrome opened "New in DevTools" and proudly announced DevTools for agents: AI that reads your CSS rules. Thanks Google, I'll take it as a sign I'm on the right track. Their version is for AI agents. Mine is for a 53-year-old guy pressing F6😂😂😂😂😂😂.
We've all done it. A popup stays behind the header, so you write z-index: 999. Then 9999. Then 99999. Nothing changes.
The problem is almost never the element you're fixing. It's one of its ancestors.
The invisible box
When an element has a transform, an opacity below 1, a filter, or a position with a z-index, it creates a stacking context. Think of it as a closed box: its children can only stack inside the box. A child with z-index: 99999 is still only as high as the box itself.
DevTools won't tell you which ancestor is the box. You have to climb the tree by hand.
The idea came from a comment
After my last post about BeeLadybug's CSS hunt, a reader suggested in the comments: scan the ancestors with getComputedStyle, flag whatever creates a stacking context, then group it by cause, like the click-blocker lines. He also warned that will-change is often set on purpose for animations, so it should be a hint, not a verdict.
So that's exactly what 0.5.4 does.
What it looks like
On the demo page:
div.hero creates stacking context (transform) - z-index of 3 children is trapped
Click the line and it lists span.b1, span.b2, span.b3.
will-change stays a grey info line, with the z-index note on the same line:
div.layer-hint will-change: opacity — z-index of 1 child stays in this layer
Then I ran it on my own site
I tested it on my live HTML5 games portal. Logged in, it flagged the WordPress admin bar blocking clicks (only I see that). In incognito, only this was left:
div.entry-content creates stacking context (z-index) - z-index of 1 child is trapped
And the INSPECT section went one step further. It showed the rule responsible, inside my LiteSpeed-minified CSS:
.site-header, .main-navigation, .entry-content, .griglia-giochi-spc {
position: relative !important;
}
One !important rule from my own custom CSS, creating four boxes at once. It's not a bug today, since each box has a single child. But the day I add a dropdown that must cover the header, I already know where to look.
That's the point: not "something is wrong", but "this line caused it".
Try it (F12, paste in the console)
import('https://cdn.jsdelivr.net/npm/bee-ladybug@0.5.4/src/index.js')
.then(({ BeeLadybugCore, WebDOMAdapter, CSSAdapter }) => {
const bee = new BeeLadybugCore();
new WebDOMAdapter(bee).attach(document.body);
new CSSAdapter(bee).attach();
});
Press F6 for the CSS hunt, S to scan the page. Zero dependencies, no extension.
Next time your z-index "doesn't work", let the ladybug find the box. 🐞











