Qua*_*ntm 5 ios uicollectionview swift
(有关更多信息,请参阅更新 3。我修复了原始问题,现在出现了一个我以前从未见过的异常)
所以我一直在尝试实现我自己版本的 IOS11 的拖放功能。我已经实现了一个自定义的gesture recognizer和我自己的拖放会话管理器,称为DragAndDropSession.
我的应用程序的情况如下:我有一个“全屏”垂直滚动collectionView,它collectionView在每个单元格(行)中保持水平滚动。例如,有点像 netflix 所拥有的。
在拖动项目时,我希望这些水平collectionViews 为拖动的项目动态腾出空间(就像 IOS11 的拖放一样)。我通过向行添加一个不可见的单元格collectionView然后collectionView.beginInteractiveMovement(..)在该单元格上使用来做到这一点。这样,当我不断将其更新到当前触摸位置时,它看起来像是在移动间隙。(我还没有找到更好的方法)。
每次触摸移动到不同的行时,我停止第一个interactive movement,删除空单元格,并将其添加到新的collectionView,在那里我再次开始interactive movement. 这里的困难在于管理方面,以便一切都得到“清理”,然后重新正确设置。
由于这很难解释,我创建了一个演示项目来展示所有内容(包括我稍后将要告诉您的崩溃):
https://github.com/d3mueller/DragAndDropTest (我希望它能正常工作。如果没有,请告诉我)
一些东西:
IGListKit(https://github.com/Instagram/IGListKit)来管理我的collectionViews. 不过,这可能与我的问题无关。(我试图评论重要的部分)...SectionController. 这是 collectionView (IGListKit) 中单元格的“管理器”。例如,垂直滚动中的collectionView每一行都有一个部分控制器,其中包含该行的数据,以及该行的 collectionView 等。好的,现在我的问题是:它崩溃了。有时。它给了我这个错误信息:
'NSInternalInconsistencyException',原因:'尝试在重新排序过程中开始重新排序集合视图'
我设置了一个断点来捕获这个异常,所以我知道它在 中崩溃了DragAndDropSession.swift: Line 194,这是这样的:
rowCollectionView.beginInteractiveMovementForItem(at: rowIndexPath)
Run Code Online (Sandbox Code Playgroud)
在这一行中,我为手指当前悬停的 collectionView 行开始了一个新的交互式移动。我只是不知道为什么它会走到这条线,因为它已经开始了互动运动。上面几行(第 171 行)我取消了交互动作。
有一个特定的案例/情况我没有在我的代码中涵盖/捕捉。我就是找不到。我在这上面花了几个小时。
如何重现此错误(查看更新 2。我找到了一种方法):
(我只能在我的 iPad 上重现它,而不是在模拟器中)
长按任何项目,稍微移动它,然后用另一个手指(同时仍然按住拖动的项目)快速上下左右滚动。你必须非常快速和混乱。然后它有时会崩溃。
原因:
首先,它很可能是updateDrag()在方法DragAndDropSession.swift。
该错误表示我正在尝试开始重新排序,而另一个重新排序已在进行中。因此,在某些情况下,我会开始两次,或者在开始另一个动作之前我不会取消动作。我只是不知道为什么。
有时,会出现不同的错误(在同一行,在做完全相同的事情之后):
由于未捕获的异常“NSInternalInconsistencyException”而终止应用程序,原因:“<_UIDragSnappingFeedbackGenerator:0x1c0134dc0:prepared=1> 已经在与之交互”
我以前从未见过这个。我唯一发现的就是这个错误报告:https : //openradar.appspot.com/42139082
有任何想法吗?
我找到了一种 100% 重现它的方法(我更新了演示项目以添加更多行并删除空行):
重现步骤(另见gif):
我已经解决了attempt to begin reordering on collection view while reordering is already in progress. 我花了很长时间,当一行离开屏幕时出现问题(这就是为什么你需要在崩溃之前向下滚动很多)。当该行返回时,一个可能不同的单元格将出列,因此我无法取消原始单元格的交互移动。我通过保存 collectionView 本身(由行包含)解决了这个问题。这个和几个小修复成功了。但是,现在我每次崩溃时都会收到以下错误(如更新 1 中所述)。
2018-07-27 18:33:06.866322+0200 DragAndDropTest[62655:8122083] * -[_UIDragSnappingFeedbackGenerator userInteractionStarted] 中的断言失败,/BuildRoot/Library/Caches/com.appleKit.x3Kit.x3Kit.x369/8Source /_UIDragFeedbackGenerator.m:175 2018-07-27 18:33:06.867191+0200 DragAndDropTest[62655:8122083] *因未捕获的异常“NSInternalInconsistencyException”而终止应用程序,原因:“Snapping>10c9UID 已经准备好 isSnapping=0c0e10c9UID互动过'
我还没有找到一种可靠的方法来重现这一点,但它很容易触发。只需稍微移动拖动项目并滚动等。
现在最大的问题是我完全不知道这是什么。我以前从未见过这个,我不知道如何调试它。有没有人见过这个?
再次,我更新了演示项目。
如果有人可以看看这个,我将非常感激。这可能是我没有看到的微不足道的东西。如果您需要更多信息,请告诉我
谢谢!
我使用 iOS 11 Collection View Drag and Drop API 结合交互式移动(beginInteractiveMove等)也遇到了同样的断言失败。
由于这种情况非常具体且极端,因此您的情况可能会有所不同。
\n\n我冒险进入兔子洞并弄清楚了以下内容:
\n\n_UIDragSnappingFeedbackGenerator是一个私有子类,UIFeedbackGenerator负责触觉反馈UIFeedbackGenerator苹果文档:\n\n\n释放生成器
\n\n如果您不再需要准备好的生成器,请删除对生成器对象的所有引用并让系统释放它。这让 Taptic Engine 返回到其空闲状态。
\n
cancelInteractiveMovement()。反馈生成器保持在准备状态(reason: \'<_UIDragSnappingFeedbackGenerator: 0x1c012c9e0: prepared=1>来自断言失败日志的\xe2\x86\x92),并且在被系统释放之前不会释放该状态。对我来说解决这个问题的是cancelInteractiveMovement在我的 UICollectionView 子类中重写并调用super.cancelInteractiveMovementand super.endInteractiveMovement:
override func cancelInteractiveMovement() {\n super.cancelInteractiveMovement()\n super.endInteractiveMovement() // \xe2\x86\x90 will not perform the standard "end" animation\n // the moving cell was already reset by cancelInteractiveMovement\n}\nRun Code Online (Sandbox Code Playgroud)\n\n这似乎清理了未完成的部分UIFeedbackGenerator并且不再崩溃(到目前为止)。
| 归档时间: |
|
| 查看次数: |
1357 次 |
| 最近记录: |