The "Mobile VH" Headache
Ugh, I have been there! It is super frustrating when things look perfect on Chrome DevTools but break the second they hit a real phone. You aren't alone—this is one of the most common CSS headaches when it comes to mobile responsive design. The reason your footer is jumping is likely because mobile browsers (especially Safari) calculate 100vh differently than desktops. They don't account for the browser's address bar or navigation buttons, which effectively "shrinks" the visible space and pushes your footer up into the middle of the screen.
Try Using Dynamic Viewport Units
If you haven't tried it yet, swap out your 100vh for 100dvh (Dynamic Viewport Height). This is a newer CSS unit specifically designed to handle those shifting browser bars on iPhones. While 100vh is "fixed," 100dvh is "dynamic" and adjusts in real-time as the URL bar expands or collapses. It should force the body to actually fill the space that is visible to the user at that exact moment.
Double-Check Your Flexbox "Push"
Since you are already using Flexbox, a common trick to keep that footer pinned is to make sure your middle content section is doing the heavy lifting. I usually set my layout up like this:
- Body/Wrapper: Set to
display: flex; flex-direction: column; min-height: 100dvh;
- Main Content Section: Give this a
flex: 1; or flex-grow: 1;
- Footer: No special height needed, just let it sit at the bottom.
By giving the main content flex: 1, you're telling the browser to stretch that middle section to fill every single bit of available space, which naturally pins the footer to the very bottom regardless of how much content is on the page. If there is a massive white gap, it usually means the "main" container isn't actually expanding to fill the viewport height.
Give that 100dvh swap a shot first—it's honestly a lifesaver for Safari bugs. Let me know if that clears it up!