Ios 如何在PDFView中禁用选择?
在Ios 如何在PDFView中禁用选择?,ios,swift,pdfkit,pdfview,Ios,Swift,Pdfkit,Pdfview,在PDFView中显示pdf文档允许用户选择文档的某些部分,并使用所选内容执行操作,例如“复制”。 如何在PDFView中禁用选择,同时保留用户在PDF中放大、缩小和滚动的可能性 PDFView本身似乎没有提供这样的属性,PDFViewDelegate您必须对PDFView进行子类化,例如: class MyPDFView: PDFView { override func canPerformAction(_ action: Selector, withSender sender: A
PDFView
中显示pdf文档
允许用户选择文档的某些部分,并使用所选内容执行操作,例如“复制”。
如何在PDFView中禁用选择,同时保留用户在PDF中放大、缩小和滚动的可能性
PDFView
本身似乎没有提供这样的属性,PDFViewDelegate
您必须对PDFView进行子类化,例如:
class MyPDFView: PDFView {
override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool {
return false
}
override func addGestureRecognizer(_ gestureRecognizer: UIGestureRecognizer) {
if gestureRecognizer is UILongPressGestureRecognizer {
gestureRecognizer.isEnabled = false
}
super.addGestureRecognizer(gestureRecognizer)
}
}
使用Swift 5和iOS 12.3,您可以通过覆盖
PDFView
子类中的方法和方法来解决问题
import UIKit
import PDFKit
class NonSelectablePDFView: PDFView {
override func addGestureRecognizer(_ gestureRecognizer: UIGestureRecognizer) {
(gestureRecognizer as? UILongPressGestureRecognizer)?.isEnabled = false
super.addGestureRecognizer(gestureRecognizer)
}
override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool {
return false
}
}
作为上一个实现的替代方案,您只需在初始值设定项中将
ui长按gesturecognizer
isEnabled
属性切换为false
import UIKit
import PDFKit
class NonSelectablePDFView: PDFView {
override init(frame: CGRect) {
super.init(frame: frame)
if let gestureRecognizers = gestureRecognizers {
for gestureRecognizer in gestureRecognizers where gestureRecognizer is UILongPressGestureRecognizer {
gestureRecognizer.isEnabled = false
}
}
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool {
return false
}
}
对于iOS 13,上述解决方案不再有效。看起来他们已经改变了
PDFView
的内部实现,特别是手势识别器的设置方式。我认为一般情况下不鼓励做这种事情,但它仍然可以在不使用任何内部API的情况下完成,方法如下:
1) 递归地收集PDFView
的所有子视图(请参见下面的帮助器函数)
2) 迭代它们并停用任何ui长按gesture识别器
s:
for gestureRec in allSubviews.compactMap({ $0.gestureRecognizers }).flatMap({ $0 }) {
if gestureRec is UILongPressGestureRecognizer {
gestureRec.isEnabled = false
}
}
Helper func递归获取给定类型的所有子视图:
func allSubViewsOf<T: UIView>(type: T.Type) -> [T] {
var all: [T] = []
func getSubview(view: UIView) {
if let aView = view as? T {
all.append(aView)
}
guard view.subviews.count > 0 else { return }
view.subviews.forEach{ getSubview(view: $0) }
}
getSubview(view: self)
return all
}
func allSubViewsOf(类型:T.type)->[T]{
变量全部:[T]=[]
func getSubview(视图:UIView){
如果让aView=视为?T{
all.append(aView)
}
guard view.subviews.count>0其他{return}
view.subviews.forEach{getSubview(视图:$0)}
}
getSubview(视图:self)
全部归还
}
我从包含视图控制器的viewDidLoad
方法调用上述代码
我还没有找到一个很好的方法将其应用到
PDFView
的子类中,这将是可重用性的首选方法,并且可能只是上述NonSelectablePDFView
的一个补充。到目前为止,我尝试的是重写didAddSubview
,并在调用super
后添加上述代码,但这并没有如预期的那样起作用。似乎手势识别器只是在以后的步骤中添加的,因此确定何时添加以及是否有方法让子类在发生这种情况后调用一些自定义代码将是下一步 您应该注意,这不足以禁用文本选择,因为还有一个UITapandHalf识别器——显然是一个私有的Apple类——也可以创建选择
它附加到PDFDocumentView,这是PDFView的另一个私有实现细节,您不能用自己的类实现替换它。只需它将自动清除选择,用户将不再长按PDF文本
class MyPDFView: PDFView {
override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool {
self.currentSelection = nil
self.clearSelection()
return false
}
override func addGestureRecognizer(_ gestureRecognizer: UIGestureRecognizer) {
if gestureRecognizer is UILongPressGestureRecognizer {
gestureRecognizer.isEnabled = false
}
super.addGestureRecognizer(gestureRecognizer)
}
}
以下2行需要添加到canPerformAction()中
看起来这个答案在iOS13中已经不起作用了,苹果确实做了一些改变,即使这个代码仍然是选中的文本,在iOS12及以下版本上,它工作正常!这将禁用长按编辑,但不禁用双击并按住。将:type(of:gestureRec).description()=“UITAPAndalHalfRecognitizer”添加到上面(2)中的if中。
class MyPDFView: PDFView {
override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool {
self.currentSelection = nil
self.clearSelection()
return false
}
override func addGestureRecognizer(_ gestureRecognizer: UIGestureRecognizer) {
if gestureRecognizer is UILongPressGestureRecognizer {
gestureRecognizer.isEnabled = false
}
super.addGestureRecognizer(gestureRecognizer)
}
}
self.currentSelection = nil
self.clearSelection()