【源码剖析】Launcher 8.0 源码 28---用户操作(5)拖拽模式之拖拽的开始和结束

本文深入剖析Android Launcher 8.0中关于用户操作的拖拽模式,特别是DragListener和DropTarget的实现。从workspace、folder、allapp、widget等模块的拖拽逻辑到DragListener的onDragStart和onDragEnd方法,详细阐述了拖拽开始和结束时的处理过程,包括屏幕创建、拖拽预览、拖动效果以及不同组件如DropTargetBar、WidgetHostViewLoader的响应。文章揭示了Android Launcher中拖拽操作的复杂性和解耦设计。
摘要由CSDN通过智能技术生成

开始拖拽应用后,除了workspace进入springload之外,其他模块也会进入springload,主要是folder、allapp、widget这三个模块。而后面三个模块最终也进入workspace的拖拽。当进入springload模式之后,就要关注到拖拽的任务,在前文中有两个拖拽的核心类没有展开讲,现在则开始补上之前很重要而没有细说的DragListener 和DropTarget。这两个方法从开始drag到移动应用到松手始终处于活跃状态。

 

首先是DragListener是一个接口,对于观察者模式,里面包含两个方法,onDragStart和onDragEnd。负责处理拖拽开荒工作和善后工作。

public interface DragListener {
    void onDragStart(DropTarget.DragObject dragObject, DragOptions options);
    void onDragEnd();
}

源码中的绑定:

PopupContainerWithArrow、WidgetHostViewLoader、DropTargetBar、Workspace

 

 

首先看workspace怎么实现DragListener 中两种方法:

@Override
public void onDragStart(DropTarget.DragObject dragObject, DragOptions options) {
    if (ENFORCE_DRAG_EVENT_ORDER) {
        enforceDragParity("onDragStart", 0, 0);
    }

    if (mDragInfo != null && mDragInfo.cell != null) {
        CellLayout layout = (CellLayout) mDragInfo.cell.getParent().getParent();
        layout.markCellsAsUnoccupiedForView(mDragInfo.cell);
    }
//确定是否需要创建在桌面上白色框的预览。
    if (mOutlineProvider != null) {
        // The outline is used to visualize where the item will land if dropped
        mOutlineProvider.generateDragOutline(mCanvas);
    }

//会调用mLauncher的很多方法,比如,drag期间,横竖屏就不切换了,比如,如果集成了callback则onInteractionBegin也可以进行一些操作。


    updateChildrenLayersEnabled(false);
    mLauncher.onDragStarted();
    mLauncher.lockScreenOrientation();
 

仿Launcher的GridView拖动是一个长按GridView的item,然后将其拖拽其他item上面,使得GridView的item发生交换,比较典型的就是我们的Launcher,网上有很多关于GridView的拖动的Demo,但是大部分都是相同的,而且存在一些Bug,而且大部分都是点击GridView的item然后进行拖动,或者item之间不进行实时交换,今天给大家更加详细的介绍GridView拖拽,并且将Demo做的更完美。   实现思路: 1、根据手指按下的X,Y坐标来获取我们在GridView上面点击的item 2、手指按下的时候使用Handler和Runnable来实现一个定时器,假如定时时间为1000毫秒,在1000毫秒内,如果手指抬起了移除定时器,没有抬起并且手指点击在GridView的item所在的区域,则表示我们长按了GridView的item 3、如果我们长按了item则隐藏item,然后使用WindowManager来添加一个item的镜像在屏幕用来代替刚刚隐藏的item 4、当我们手指在屏幕移动的时候,更新item镜像的位置,然后在根据我们移动的X,Y的坐标来获取移动到GridView的哪一个位置 5、到GridView的item过多的时候,可能一屏幕显示不完,我们手指拖动item镜像到屏幕下方,要触发GridView想上滚动,同理,当我们手指拖动item镜像到屏幕上面,触发GridView向下滚动 6、GridView交换数据,刷新界面,移除item的镜像 本例子来自于CSND xiaanming的博客,详细的源码分析已经帮大家离线成pdf文档了。   
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值