ios - `dropSessionDidUpdate` 中的 UICollectionViewDropDelegate 错误的目标索引路径
问题描述
它具有水平布局,具有不同大小的单元格和部分。
拖动交互效果很好,但我注意到UICollectionViewDropDelegate中的一个问题:
func collectionView(
_ collectionView: UICollectionView,
dropSessionDidUpdate session: UIDropSession,
withDestinationIndexPath destinationIndexPath: IndexPath?)
-> UICollectionViewDropProposal {
if let destination = destinationIndexPath {
print(destination) // Prints WRONG index path!!!
return UICollectionViewDropProposal(
operation: .move, intent: .insertAtDestinationIndexPath
)
}
return UICollectionViewDropProposal(
operation: .cancel, intent: .unspecified
)
}
错误的目标索引路径传递给collectionView(_:dropSessionDidUpdate:withDestinationIndexPath:)
。
因此,我无法正确确定该部分并确定该部分是否可用。
解决方案
所以,这是 UIKit 的一个 bug。正确的目的索引路径可以计算如下:
func collectionView(
_ collectionView: UICollectionView,
dropSessionDidUpdate session: UIDropSession,
withDestinationIndexPath destinationIndexPath: IndexPath?)
-> UICollectionViewDropProposal {
// Calculating location in view
let location = session.location(in: collectionView)
var correctDestination: IndexPath?
// Calculate index inside performUsingPresentationValues
collectionView.performUsingPresentationValues {
correctDestination = collectionView.indexPathForItem(at: location)
}
guard let destination = correctDestination else {
return UICollectionViewDropProposal(
operation: .cancel, intent: .unspecified
)
}
// check destination
// ...
}
为了修复这个错误,首先,我尝试使用 和 的location(in:)
组合indexPathForItem(at:)
。生成的索引路径等于destinationIndexPath
委托方法提供的索引路径。为什么?UIDataSourceTranslating引起了我的注意。这是一个协议,允许集合和表格视图显示用于拖放的占位符单元格,而无需更改实际数据源。当拖放交互结束时,占位符很容易被删除。所以,我做了一个假设
destinationIndexPath
是在帮助下计算的indexPathForItem(at:)
- 它忽略了由 UIDataSourceTranslating 创建的占位符,这是一个错误
然后我尝试换indexPathForItem(at:)
行performUsingPresentationValues(_:)
,收到的索引路径是正确的!
推荐阅读
- java - getClass() 在 Enum 中使用构造函数时打印二进制格式
- opengl - 在 Windows 上的 LLDB 中运行 Rust OpenGL 程序时,窗口不会打开
- java - 会通知中断睡眠线程吗?
- python-3.x - 强制 sock.accept() 引发测试异常
- unit-testing - 使用接口进行依赖注入等测试
- ios - SceneKit 将对象移动到另一个对象之上
- ionic-framework - 如何解决设备离子4中的安装问题
- azure - 使用 azure 自动化脚本扩大和缩小 azure 应用服务计划(基于非营业时间)
- c++ - 如何使用 std:fill 为 C 数组的特定范围设置值
- java - 如何读取 Firestore 子集合并将其传递给 FirestoreRecyclerOptions