能否在Workshop App中根据另一节的展开/折叠状态,条件式展开/折叠节?
实现两个工作流节的互斥展开/折叠方案
当然可以实现,核心思路是维护一个互斥的激活状态——同一时间只让一个工作流节处于展开状态,当用户操作其中一个节时,自动同步另一个节的状态。下面是不同技术栈的具体实现方式:
原生JavaScript方案
给两个节设置唯一标识,用变量跟踪当前展开的节,绑定点击事件处理状态切换:
// 获取所有切换按钮 const toggleButtons = document.querySelectorAll('.section-toggle'); // 记录当前展开的节ID let activeSection = null; // 给每个按钮绑定点击事件 toggleButtons.forEach(btn => { btn.addEventListener('click', function() { const targetId = this.dataset.sectionId; const targetSection = document.getElementById(targetId); const isExpanded = targetSection.classList.contains('expanded'); if (isExpanded) { // 折叠当前节,清空激活状态 targetSection.classList.remove('expanded'); activeSection = null; } else { // 先折叠之前展开的节 if (activeSection) { document.getElementById(activeSection).classList.remove('expanded'); } // 展开当前节,更新激活状态 targetSection.classList.add('expanded'); activeSection = targetId; } }); });
配合CSS控制显示/隐藏:
.workshop-section { height: 45px; /* 折叠状态的固定高度 */ overflow: hidden; transition: height 0.3s ease; } .workshop-section.expanded { height: auto; /* 展开后自适应内容高度 */ }
HTML结构示例:
<div class="workshop-section" id="workflow1"> <button class="section-toggle" data-section-id="workflow1">展开工作流1</button> <!-- 工作流1的内容区域 --> </div> <div class="workshop-section" id="workflow2"> <button class="section-toggle" data-section-id="workflow2">展开工作流2</button> <!-- 工作流2的内容区域 --> </div>
React方案
用useState维护激活状态,通过动态类名控制节的展开/折叠:
import { useState } from 'react'; function WorkshopApp() { const [activeSection, setActiveSection] = useState(null); const handleToggle = (sectionId) => { // 点击已展开的节就折叠,否则切换到该节展开 setActiveSection(prev => prev === sectionId ? null : sectionId); }; return ( <div className="workshop-container"> <div className={`workshop-section ${activeSection === 'wf1' ? 'expanded' : ''}`}> <button onClick={() => handleToggle('wf1')}> {activeSection === 'wf1' ? '折叠工作流1' : '展开工作流1'} </button> {/* 工作流1内容 */} </div> <div className={`workshop-section ${activeSection === 'wf2' ? 'expanded' : ''}`}> <button onClick={() => handleToggle('wf2')}> {activeSection === 'wf2' ? '折叠工作流2' : '展开工作流2'} </button> {/* 工作流2内容 */} </div> </div> ); }
CSS和原生方案一致,用.expanded类控制高度。
Vue方案
通过组件数据属性跟踪激活状态,结合动态class实现切换:
<template> <div class="workshop-container"> <div class="workshop-section" :class="{ expanded: activeSection === 'wf1' }"> <button @click="toggleSection('wf1')"> {{ activeSection === 'wf1' ? '折叠工作流1' : '展开工作流1' }} </button> <!-- 工作流1内容 --> </div> <div class="workshop-section" :class="{ expanded: activeSection === 'wf2' }"> <button @click="toggleSection('wf2')"> {{ activeSection === 'wf2' ? '折叠工作流2' : '展开工作流2' }} </button> <!-- 工作流2内容 --> </div> </div> </template> <script> export default { data() { return { activeSection: null }; }, methods: { toggleSection(sectionId) { this.activeSection = this.activeSection === sectionId ? null : sectionId; } } }; </script> <style scoped> .workshop-section { height: 45px; overflow: hidden; transition: height 0.3s ease; } .workshop-section.expanded { height: auto; } </style>
额外说明
如果需要支持“两个节都折叠”的状态,上面的逻辑已经包含了——点击当前展开的节时,就会清空激活状态,让两个节都处于折叠状态。如果要求必须有一个节展开,只需要修改逻辑:当点击折叠按钮时,自动切换到另一个节展开即可。
内容的提问来源于stack exchange,提问作者Max Magid
相关产品推荐
相关产品推荐

