Angular 4/5中Bootstrap 4双列布局可拖拽中间调整栏实现咨询
当然可以实现!在 Angular 4/5 里有几种很实用的方案能满足你的需求,我来给你详细说说:
方案一:自定义 Angular 拖拽指令(最灵活)
Angular 的指令天生适合封装这种交互逻辑,你可以自己写一个拖拽指令来控制两列的宽度和显示状态:
1. 编写拖拽指令
创建一个监听鼠标事件的指令,用来捕捉拖拽动作并传递宽度变化:
import { Directive, ElementRef, HostListener, Output, EventEmitter } from '@angular/core'; @Directive({ selector: '[resizeHandle]' }) export class ResizeHandleDirective { @Output() resize = new EventEmitter<number>(); private startX: number; private startRightWidth: number; constructor(private el: ElementRef) {} @HostListener('mousedown', ['$event']) onMouseDown(event: MouseEvent) { // 记录初始位置和右侧列宽度 this.startX = event.clientX; const rightCol = document.getElementById('right-column'); this.startRightWidth = rightCol.offsetWidth; // 绑定全局鼠标事件 document.addEventListener('mousemove', this.onMouseMove); document.addEventListener('mouseup', this.onMouseUp); event.preventDefault(); } private onMouseMove = (event: MouseEvent) => { // 计算拖拽偏移量,得出右侧列的新宽度 const deltaX = this.startX - event.clientX; const newRightWidth = this.startRightWidth - deltaX; // 把结果传给组件 this.resize.emit(newRightWidth); }; private onMouseUp = () => { // 移除全局事件监听 document.removeEventListener('mousemove', this.onMouseMove); document.removeEventListener('mouseup', this.onMouseUp); }; }
2. 在组件中使用指令
在模板里给边框元素加上指令,绑定事件来调整列的样式和类:
<div class="row"> <div class="col-8 p-3" [class.col-12]="isRightColHidden" #leftCol > <!-- 左侧内容 --> <h3>左侧8列内容</h3> <p>拖拽中间边框可调整宽度,拖到最右侧我会占满屏幕~</p> </div> <!-- 拖拽边框 --> <div class="resize-border" resizeHandle (resize)="onResize($event)" ></div> <div class="col-4 p-3" [class.d-none]="isRightColHidden" id="right-column" #rightCol > <!-- 右侧内容 --> <h3>右侧4列内容</h3> <p>被拖到消失啦😢</p> </div> </div>
3. 组件逻辑处理
在组件类里接收拖拽事件,判断是否隐藏右侧列:
import { Component, ViewChild, ElementRef } from '@angular/core'; @Component({ selector: 'app-resizable-columns', templateUrl: './resizable-columns.component.html', styleUrls: ['./resizable-columns.component.css'] }) export class ResizableColumnsComponent { isRightColHidden = false; @ViewChild('leftCol') leftCol!: ElementRef; @ViewChild('rightCol') rightCol!: ElementRef; onResize(newRightWidth: number) { if (newRightWidth <= 0) { // 右侧列宽度小于等于0时隐藏 this.isRightColHidden = true; } else { this.isRightColHidden = false; // 动态调整两列宽度(替代Bootstrap栅格类的方式) this.rightCol.nativeElement.style.width = `${newRightWidth}px`; this.leftCol.nativeElement.style.width = `calc(100% - ${newRightWidth + 8}px)`; // 加上边框的宽度 } } }
4. 给边框加样式
让边框看起来像可拖拽的样子:
.resize-border { width: 8px; background-color: #ccc; cursor: ew-resize; margin: 0; align-self: stretch; }
方案二:使用第三方调整大小库(更省心)
如果不想自己写指令,可以用成熟的第三方库,比如 angular-resizable-element,它专门为 Angular 提供元素拖拽调整功能:
1. 安装库
npm install angular-resizable-element --save
2. 导入模块
在你的 Angular 模块里导入 ResizableModule:
import { ResizableModule } from 'angular-resizable-element'; @NgModule({ imports: [ // ...其他导入 ResizableModule ] }) export class YourModule { }
3. 模板中使用
直接给右侧列加上 resizable 指令,监听调整事件:
<div class="row"> <div class="col p-3" [style.width.%]="leftWidth"> <!-- 左侧内容 --> </div> <div class="resize-border"></div> <div class="col p-3" [style.width.%]="rightWidth" resizable [resizeEdges]="{left: true}" (resizeEnd)="onResizeEnd($event)" [class.d-none]="isRightColHidden" > <!-- 右侧内容 --> </div> </div>
4. 组件逻辑
初始化宽度为 Bootstrap 栅格的比例,处理调整结束事件:
leftWidth = 66.66; // 对应col-8 rightWidth = 33.34; // 对应col-4 isRightColHidden = false; onResizeEnd(event: any) { // 更新宽度比例 this.rightWidth = event.rectangle.width / event.hostElement.parentElement.offsetWidth * 100; this.leftWidth = 100 - this.rightWidth; // 当右侧列宽度小于5%时隐藏 if (this.rightWidth < 5) { this.isRightColHidden = true; } else { this.isRightColHidden = false; } }
替代方案:简化版(纯交互+Bootstrap折叠)
如果不需要平滑拖拽调整,只需要“拖拽到右侧隐藏”的效果,可以简化逻辑:给边框绑定mousedown事件,直接切换两列的类(比如给左侧加col-12,右侧加d-none),这种方式适合需求简单的场景。
内容的提问来源于stack exchange,提问作者Rolando
相关产品推荐
相关产品推荐

