You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在动画中调整两个Flexbox的尺寸?

如何在动画中调整两个Flexbox的尺寸?

嗨,我来帮你拆解这个问题,先搞懂为什么你用calc(100% - 200px)会不对齐,再给你两个简单靠谱的解决方案。

先说说你遇到的核心问题

你用position: relative + left来移动div1的时候,div1其实还占据着原来的200px空间(relative定位不会脱离文档流,只是视觉上移走了)。这就导致:

  • 当你给div2设calc(100% - 200px)时,这个100%是父容器的总宽度(比如50vw),所以div2的宽度是50vw - 200px,加上div1的200px,刚好填满父容器,这时候是对的。
  • 但你把div1移到左边-200px后,div1依然占着那200px的位置,这时候你给div2设width: 100%,div2的宽度会变成50vw,但div1还占着200px,flex布局会默认压缩div2(因为flex-shrink: 1),所以实际显示的宽度根本不是你想要的100%,自然就不对齐了。

解决方案1:利用Flex自动填充特性(最推荐)

既然用了flex布局,就该用好它的自动适配能力,完全不用手动算宽度。核心思路是:让div2自动填充剩余空间,通过控制div1的宽度实现滑入滑出动画。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <style>
        *{
            padding: 0;
            margin: 0;
            box-sizing: border-box;
        }
        .chat-container {
            display: flex;
            height: 50vh;
            width: 50vw;
            background-color: #f0f0f0;
        }
        #div1 {
            background-color: #0004ff;
            height: 100%;
            width: 0; /* 默认隐藏,宽度为0 */
            text-align: center;
            transition: width 0.3s ease; /* 宽度过渡动画 */
            overflow: hidden; /* 防止内容在宽度为0时溢出 */
        }
        #div1.active {
            width: 200px; /* 激活时展开到200px */
        }
        #div2 {
            background-color: #ff0000;
            height: 100%;
            text-align: center;
            flex: 1; /* 关键:让div2自动填充父容器剩余空间 */
        }
    </style>
</head>
<body>
    <div class="chat-container">
        <div id="div1">
            <p>div1</p>
        </div>
        <div id="div2">
            <p>div2</p>
        </div>
    </div>
    <button id="button">animation</button>
    <script>
        let isActive = false;
        const div1 = document.getElementById("div1");
        document.getElementById("button").addEventListener("click", function() {
            isActive = !isActive;
            div1.classList.toggle("active", isActive);
        });
    </script>
</body>
</html>

这个方案的好处:

  • 完全不用手动计算宽度,flex:1会让div2自动适配剩余空间,div1展开/收起时,div2会同步自动调整尺寸,绝对不会有对齐问题。
  • 用class控制状态,比直接修改style属性更清晰,后续加样式也更方便维护。
  • 动画平滑同步,因为div1的宽度变化和div2的空间适配都是flex布局自动处理的。

解决方案2:用transform滑入滑出(保留div1原宽度)

如果你想保留div1的200px宽度,只是视觉上滑入滑出,可以用transform: translateX(不影响文档流,但需要配合控制div2的flex属性),不过这个方案稍微复杂一点,不如方案1省心。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <style>
        *{
            padding: 0;
            margin: 0;
            box-sizing: border-box;
        }
        .chat-container {
            display: flex;
            height: 50vh;
            width: 50vw;
            background-color: #f0f0f0;
            overflow: hidden; /* 隐藏超出父容器的部分 */
        }
        #div1 {
            background-color: #0004ff;
            height: 100%;
            width: 200px;
            text-align: center;
            transition: transform 0.3s ease;
            transform: translateX(-100%); /* 默认隐藏在左边 */
            flex-shrink: 0; /* 防止div1被压缩 */
        }
        #div1.active {
            transform: translateX(0); /* 滑入显示 */
        }
        #div2 {
            background-color: #ff0000;
            height: 100%;
            text-align: center;
            flex: 1; /* 自动填充剩余空间 */
            transition: flex 0.3s ease;
        }
        #div1.active + #div2 {
            flex: 0 0 calc(100% - 200px); /* div1显示时,div2固定宽度 */
        }
    </style>
</head>
<body>
    <div class="chat-container">
        <div id="div1">
            <p>div1</p>
        </div>
        <div id="div2">
            <p>div2</p>
        </div>
    </div>
    <button id="button">animation</button>
    <script>
        let isActive = false;
        const div1 = document.getElementById("div1");
        document.getElementById("button").addEventListener("click", function() {
            isActive = !isActive;
            div1.classList.toggle("active", isActive);
        });
    </script>
</body>
</html>

这个方案的核心是用相邻兄弟选择器#div1.active + #div2来控制div2的尺寸,当div1显示时,div2的宽度固定为父容器减200px;当div1隐藏时,div2用flex:1填满整个父容器。

总结

最推荐用方案1,因为它完全利用了flex布局的优势,代码简洁,逻辑清晰,绝对不会出现尺寸不对齐的问题。你之前的calc问题本质上是没搞懂relative定位不脱离文档流,导致div1始终占据空间,而flex布局的自动适配特性可以帮你省去所有手动计算的麻烦。

备注:内容来源于stack exchange,提问作者XCZ_Mike

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.14 10:23:08