react 拖拽功能

react 拖拽功能

用法简介

  • 基于react的拖拽功能,有这么几个比较流行的库:

    1. react-dnd
    2. react-beautiful-dnd
    3. dnd-kit
    4. react-sortable-hoc
  • 点击查看原文

介绍react-sortable-hoc 用法

  • 下载==>(项目中安装 react-sorting-hoc 以及 array-move,后者是用来实现数组移动。)

    • yarn add react-sortable-hoc array-move
    • npm add react-sortable-hoc array-move
  • 项目页面中引入包

    • import {sortableContainer, sortableElement} from 'react-sortable-hoc';
    • import arrayMove from 'array-move';
  • 基本概念

    • SortableContainer 拖拽排序的容器
    • SortableElement 拖拽排序的元素
  • 用法

    • 在 render 里写

      <SortableContainer distance={10} items={sendMsgList || []} onSortEnd={this.onSortEnd} />
      

      // items里存放需要便利拖拽的数组

      // distance属性 作用:(设置触发排序之前要拖动的最小距离) eg:可以设置为10px

      ​ 目的:防止拖拽组件里的onClick时间不能触发

    • 	// 列表拖动
      	onSortEnd = ({oldIndex, newIndex}) => {
      		const {sendMsgList} = enterpriseMicroSOP.addTeskNode;
      		if (oldIndex !== newIndex) {
      			const newData = arrayMove([].concat(sendMsgList), oldIndex, newIndex).filter(el => !!el);
      			enterpriseMicroSOP.addTeskNode.sendMsgList = JSON.parse(JSON.stringify(newData));
      		}
      	};
      
    • 		const SortableContainer = sortableContainer(({items}) => {
      			return (
      				<div className={style.Timeline_info} ref={this.listRef} onScrollCapture={() => this.handleScroll()}>
      					{items.map((item_, index_) => {
      						if (item_.sendType == 0) {
      							return <RenderTextInfo key={`item-${index_}`} index={index_} index_={index_} item_={item_} disabled={false} />;
      						}
      						
      					})}
      				</div>
      			);
      		});
      
    • 需要创建一个ref节点 目的是为了拖拽滚动的时候,滚动位置不变

    this.listRef = React.createRef();
    
    	componentDidUpdate() {
    		// 滚动位置不变
    		this.listRef.current.scrollTop = this.scrollTop;
    	}
    
    • 需要排序的元素(也要写在render里面)
    // 渲染文本样式
    		const RenderTextInfo = sortableElement(({item_, index_}) => {
    			return (
    				<div className={style.list_template} key={index_}>
    					<div className={style.left}>
    						<div className={style.list_template_left}>
    							<span>{index_ + 1}</span>
    						</div>
    						<div className={style.text_info}>{item_.sendTypeMessage}</div>
    					</div>
    				</div>
    			);
    		});
    

介绍react-beautiful-dnd 用法

  • 下载

    • yarn add react-beautiful-dnd
    • npm install react-beautiful-dnd --save
  • 项目页面中引入包

    • import {DragDropContext, Droppable, Draggable} from 'react-beautiful-dnd';
  • 基本用法

    1. DragDropContext : 用于包装拖拽根组件,Draggable和Droppable都需要包裹在DragDropContext内
    2. Draggable 用于包装你需要拖动的组件,使组件能够被拖拽(make it draggable)
    3. Droppable 用于包装接收拖拽元素的组件,使组件能够放置(dropped on it)
	return (
			<DragDropContext onDragEnd={this.handleDragEnd}>
				<Droppable droppableId="droppable">
					{(provided, snapshot) => (
						<div {...provided.droppableProps} ref={provided.innerRef} className={style.drop_col_container} key={'droppable'}>
							{typeList.map((item, index) => {
								if (this.props.isCustomerGroup) {
									if (item.typeKey == 'file' || item.typeKey == 'miniprogram') return;
								}
								return (
									<Draggable key={item.id} draggableId={String(item.id)} index={index}>
										{(provided, snapshot) => (
											<div
												ref={provided.innerRef}
												{...provided.draggableProps}
												{...provided.dragHandleProps}
												key={index}
												className={`${style.drop_item} ${this.state.activeKey == item.typeKey ? style.drop_item_selected : ''}`}>
												<div className={style.drop_col}>
													<div className="drop"></div>
													<TextArea
														id={'SortName'}
														className="SortName"
														onChange={e => {
															this.handleInputChange(e, item.typeKey);
														}}
														value={item.typeName}
														showCount
														placeholder="请输入名称"
														maxLength={10}
														rows={1}
													/>
												</div>
											</div>
										)}
									</Draggable>
								);
							})}
						</div>
					)}
				</Droppable>
			</DragDropContext>
		);
handleDragEnd = result => {
		const {typeList} = this.state;
		if (!result.source || !result.destination) return;
		const sourceIndex = result.source.index; // 被拖动元素位置
		const endIndex = result.destination.index; // 拖动的位置
		const list = this.swapArr(typeList, sourceIndex, endIndex);
		this.setState({typeList: list});
	};
// 排序
	swapArr(arr, index1, index2) {
		if (index1 > index2) {
			arr.splice(index2, 0, arr[index1]);
			arr.splice(index1 + 1, 1);
		} else {
			arr.splice(index2 + 1, 0, arr[index1]);
			arr.splice(index1, 1);
		}
		return arr;
	}
posted @ 2022-05-07 17:18  海绵jay  阅读(1409)  评论(0编辑  收藏  举报