Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ios/116.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
iOS 11 PDFKit墨水批注-无法填充UIBezierPath_Ios_Ipad_Uibezierpath_Pdfkit - Fatal编程技术网

iOS 11 PDFKit墨水批注-无法填充UIBezierPath

iOS 11 PDFKit墨水批注-无法填充UIBezierPath,ios,ipad,uibezierpath,pdfkit,Ios,Ipad,Uibezierpath,Pdfkit,我正在使用带有子类型ink的PDFAnnotation()类向PDFDocument添加墨迹注释。其想法是捕捉使用触摸绘制的签名 受UberSignature的启发,我的UberzierPath是一系列应该用颜色填充的矩形。但是,当我将注释添加到PDFDocument时,它不会被填充 当添加到PDFAnnotation时,UIBezierPath的fill()方法似乎什么都不做 如果我使用相同的UIBezierPath并将其绘制在UIImage上,它将正确填充纯色 对可能出现的问题有什么看法吗

我正在使用带有子类型ink的PDFAnnotation()类向PDFDocument添加墨迹注释。其想法是捕捉使用触摸绘制的签名

受UberSignature的启发,我的UberzierPath是一系列应该用颜色填充的矩形。但是,当我将注释添加到PDFDocument时,它不会被填充

当添加到PDFAnnotation时,UIBezierPath的fill()方法似乎什么都不做

如果我使用相同的UIBezierPath并将其绘制在UIImage上,它将正确填充纯色

对可能出现的问题有什么看法吗

问题代码:

UIColor.red.setStroke()
UIColor.red.setFill()

var path = UIBezierPath()
path.append(myRectangles)
path.fill()

var annotation = PDFAnnotation(bounds: path.bounds, forType: .ink, withProperties: nil)
annotation.add(path)
myPDFPage.addAnnotation(annotation)


在截图中,我尝试编写普通文本和两行示例。左边的线画得慢,右边的线画得快。其思想是根据绘制速度改变线条的宽度,使签名看起来更自然/真实。

InkAnnotation被渲染为笔划路径的集合。没有办法根据颜色来填充它

苹果的预览版使用戳记注释将签名添加到PDF中。我尝试使用PDFKit对其进行反向工程,但我看不到任何包含我在PDF中放置的签名的矢量数据。PDFKit在这里可能不够

(lldb) po annotation.annotationKeyValues
▿ 10 elements
  ▿ 0 : 2 elements
    ▿ key : AnyHashable("/AAPL:Hash")
      - value : "/AAPL:Hash"
    - value : /264236ab9aaabfe2d536167a89c26c2d
  ▿ 1 : 2 elements
    ▿ key : AnyHashable("/DA")
      - value : "/DA"
    - value : /Helvetica 12 Tf 0 g
  ▿ 2 : 2 elements
    ▿ key : AnyHashable("/T")
      - value : "/T"
    - value : Wojciech Nagrodzki
  ▿ 3 : 2 elements
    ▿ key : AnyHashable("/F")
      - value : "/F"
    - value : 4
  ▿ 4 : 2 elements
    ▿ key : AnyHashable("/Subtype")
      - value : "/Subtype"
    - value : /Stamp
  ▿ 5 : 2 elements
    ▿ key : AnyHashable("/Name")
      - value : "/Name"
    - value : /Draft
  ▿ 6 : 2 elements
    ▿ key : AnyHashable("/Rect")
      - value : "/Rect"
    - value : NSRect: {{5.8745389999999995, 748.38995}, {307.66119599999996, 87.648936000000049}}
  ▿ 7 : 2 elements
    ▿ key : AnyHashable("/Border")
      - value : "/Border"
    - value : PDFBorder: {solid lineWidth:2.8 hCorner:0.0 vCorner:0.0 dashCount:0 dashPattern:(
)}
  ▿ 8 : 2 elements
    ▿ key : AnyHashable("/Type")
      - value : "/Type"
    - value : /Annot
  ▿ 9 : 2 elements
    ▿ key : AnyHashable("/C")
      - value : "/C"
    - value : kCGColorSpaceModelRGB 0 0 0 1 
用于在当前图形上下文中填充路径的
fill()
方法与注释无关

如果使用stamp annotation失败,您还可以在图形上下文中呈现路径,将其转换为图像并放置在PDF中。但我不确定你是否考虑过这一点


您可以在中找到更多PDF参考。

我设法找到了一个似乎相对最优的问题解决方案

诀窍是创建PDFAnnotation的子类,并重写draw(在上下文中使用box:)函数。在这个函数中,我可以使用drawPath(使用:.fill)方法来填充bezier路径

代码可以如下所示:

class SignatureAnnotation : PDFAnnotation {
  public var myPath : UIBezierPath = UIBezierPath()

  override func draw(with box: PDFDisplayBox, in context: CGContext) {
    context.saveGState()
    self.page?.transform(context, for: box)
    context.beginPath()
    context.setLineWidth(0.1)
    context.setShouldAntialias(true)
    context.addPath(self.myPath.cgPath.mutableCopy()!)
    context.drawPath(using: .fill)
    context.restoreGState()
  }
}
将此批注(type.stamp)添加到PDF而不是墨水批注,所有内容都将呈现为矢量(完全可缩放,无需像素化),并在保存到文件或数据缓冲区时与PDF的其余部分一起保存


唯一的缺点是UIBezierPath不能太复杂,因为如果draw()函数花费的时间太长,将引入闪烁。这可以通过简单地将UIBezierPath拆分为多个单独的路径来解决,每个路径都有自己的注释。

遗憾的是,这些都不能真正解决问题。与墨迹注释的矢量格式相反,图像在放大时会被像素化,因此是次优的。另外,在PDF中添加图像也是有问题的,因为PDFKit实际上没有任何机制来更改仅PDF注释的内容。同时,我在前几天解决了这个问题——现在添加了一个带有细节的答案。这个注释在其他PDF渲染应用程序中可见吗?它可以像注释一样操作(移动、更改大小、复制、粘贴)?是的,在其他PDF渲染应用程序中可见(我已经用Apple Preview和内置的Google Chrome PDF viewer进行了测试)。我对事后处理注释不感兴趣,所以我没有尝试过。嘿,你能上传一个示例代码吗?你是如何做到这一点的?非常感谢@谢谢你分享这个。试图在我的项目中实现您的解决方案,我只能绘制UIBezierPath的第一段,而其他部分则无法绘制。请您再分享一些代码好吗?您是否尝试过在调试器中检查UIBezierPath以检查实际上是否有多个段对我来说没有问题。你有没有找到一种方法根据铅笔的压力、速度和位置来调整线条的宽度和样式?我试图用与苹果在其示例应用程序()中使用的相同的方法实现,但面临严重的性能问题。是的,我使用了问答中显示的技术,将线条“切碎”成许多不同大小的较小四边形。为了提高性能,我确保制作多个注释,而不是将所有内容都集中到一个注释中,并且我还实现了位图缓存。也就是说,我存储为每x次迭代计算的实际位图,这样当添加笔划时,我只需在每个绘图上渲染最新的笔划。其余的被缓存。