Vue组件结构中BEM规范用法疑问:子组件命名及修饰符M
BEM规范使用建议:针对文档列表组件的命名与修饰符说明
一、关于修饰符(M)的核心认知
修饰符不是组件的必填项,它的唯一作用是标记块/元素的状态、样式变体或特殊类型,只有当组件存在不同视觉表现、状态切换场景时才需要添加。比如你的文档项如果有以下情况,才适合用修饰符:
- 文档项处于选中状态
- 区分不同文件类型(文件夹、图片、PDF等)
- 支持紧凑/常规布局变体
- 处于加载中、禁用等特殊状态
举个实际使用的例子:
// DocumentItem.vue <div class="listItem" :class="{'listItem--selected': item.isSelected, 'listItem--folder': item.isFolder}"> <img class="listItem__image" :src="item.iconUrl" /> <div class="listItem__name">{{ item.name }}</div> <div class="listItem__size">{{ item.size }}</div> </div>
对应CSS写法:
.listItem--selected { background-color: #e6f3ff; } .listItem--folder .listItem__image { content: url('./folder-icon.svg'); }
二、父组件与子组件的BEM命名选择
命名方式取决于DocumentItem的复用性:
情况1:DocumentItem是可独立复用的通用组件
如果这个组件还能在其他页面(比如收藏列表、最近文件列表)单独使用,那它应该作为独立的块(B),命名保持listItem或更语义化的documentItem,它的子元素用documentItem__image、documentItem__name,和父组件的documentListing完全解耦,保证组件的通用性。
情况2:DocumentItem是DocumentListing的专属子组件
如果这个组件仅为当前列表服务,无法单独复用,那它应该作为documentListing的元素(E),命名改为documentListing__item,对应的子元素命名为documentListing__itemImage、documentListing__itemName,让整个列表的结构关联性更清晰:
// DocumentListing.vue <div class="documentListing"> <div v-for="item in list" class="documentListing__item" :class="{'documentListing__item--selected': item.isSelected}"> <img class="documentListing__itemImage" /> <div class="documentListing__itemName">{{ item.name }}</div> <div class="documentListing__itemSize">{{ item.size }}</div> </div> </div>
三、当前代码的优化建议
- 先明确
DocumentItem的复用定位:如果是通用组件,保留listItem作为块名即可,不用为了加修饰符而硬凑场景,后续需要状态/变体时再添加。 - 修正父组件的结构:
documentListing应该作为整个列表的容器,而非每个循环项的类名,优化后代码如下:
// 修正后的DocumentListing.vue <div class="documentListing"> <DocumentItem v-for="item in list" :key="item.path" :data="item" /> </div>
此时documentListing负责整个列表的布局(比如间距、网格/列表切换),listItem负责单个项的样式,结构更清晰。
内容的提问来源于stack exchange,提问作者Maik Lowrey
相关产品推荐
相关产品推荐

