下面给你一份 全面、稳定、可在实际项目中使用 的document.body.clientHeight 返回 0 的 完美解决方案合集(含原因 + 修复方式 + 推荐写法)。
适用于:
- H5 网页
- uni-app H5 端
- Vue/React/原生 JS
尤其是在 页面初始化时读取高度为 0 的情况。
🔥 一、为什么 document.body.clientHeight 会返回 0?
最常见原因只有三个:
① CSS 使用了 html, body { height: 100%; }
如果 html 高度没有内容支撑,body 就会被撑到 0 → clientHeight = 0。
② DOM 未完成布局(未渲染)
在页面初始化(如 mounted / onLoad)过早读取高度,会得到 0。
③ 在 iframe / 某些 WebView(特别是 uni-app H5)中
body 高度被框架接管,真实高度由外层控制,因此返回 0。
⭐ 二、最完美、通用的解决方案(推荐优先级最高)
✔ 方案 1:改用 document.documentElement.clientHeight
这是兼容性最强、最稳定的方案。
let h = document.documentElement.clientHeight;
documentElement(html)能保证永远存在高度,不受 body 的 height:100% 影响。
99% 的项目都应该改用这个。
⭐ 三、通用的补救方案(适合已经写死 body 高度的项目)
✔ 方案 2:确保 body 能撑开高度
通常是因为:
html, body {
height: 100%;
padding: 0;
margin: 0;
}
但 body 里面没内容,所以高度为 0。
解决方法:为 body 加最小高度:
body {
min-height: 100vh;
}
或者:
html, body {
height: auto !important;
}
⭐ 四、适用于 Vue / uni-app 的最佳时机方案
✔ 方案 3:等 DOM 渲染后再获取高度
Vue/uni-app 中:
this.$nextTick(() => {
console.log(document.body.clientHeight);
});
原生 JS:
window.onload = () => {
console.log(document.body.clientHeight);
};
或事件监听:
document.addEventListener('DOMContentLoaded', () => {
console.log(document.body.clientHeight);
});
⭐ 五、在 uni-app H5 中的特别注意事项(关键)
uni-app 运行在 WebView 下,body 默认几乎是 0 高度(HBuilderX 会重写样式)。
👉 必须改用:
document.documentElement.clientHeight
而不要用:
document.body.clientHeight // 经常返回 0
或者获取窗体可视高度:
uni.getSystemInfo({
success: res => {
console.log('windowHeight:', res.windowHeight);
}
});
⭐ 六、终极兜底方案(保底不会失败)
如果你必须获取真实页面高度(整个内容高度):
let height = Math.max(
document.body.scrollHeight,
document.documentElement.scrollHeight,
document.body.offsetHeight,
document.documentElement.offsetHeight,
document.body.clientHeight,
document.documentElement.clientHeight
);
这个是业内通用的“全兼容方案”。
🎯 七、最佳实践总结(必看)
✔ 最推荐用:
document.documentElement.clientHeight
✔ uni-app H5 强烈推荐:
uni.getSystemInfo()
✔ 页面初始化获取高度:
this.$nextTick(() => {...})
✔ 如必须获取内容总高度:
Math.max(...六项)