Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Using PDF in iOS

codelynx
November 20, 2016

Using PDF in iOS

Presentation material for `iOS All stars 2` that held in Nov. 2016. You may find tips & tricks how to handle PDF in iOS.

codelynx

November 20, 2016
Tweet

More Decks by codelynx

Other Decks in Programming

Transcript

  1. Using PDF in iOS Using PDF in iOS iOS All

    Stars 2 – Nov. 2016 Kaz Yoshikawa
  2. Using PDF in iOS Kaz Yoshikawa • Electricwoods LLC ୅ද

    / Digital Lynx Systems Inc. ෭୅ද • e-mail: [email protected] () • twitter: @codelynx • Working History • Adobe Systems (Tokyo) • Lionbridge (Tokyo) • Quark (Tokyo / Denver) • Hummingbird Communications (Mt. View, USA) • Fact International (Vancouver, Canada) • Perle Systems (Toronto, Canada), etc.
  3. Using PDF in iOS PDF Reference sixth edition Adobe® Portable

    Document Format Version 1.7 November 2006 Adobe Systems Incorporated
  4. Using PDF in iOS Characteristics • Resolution Independent • Multiple

    Pages • Printing Quality • Color Models: RGB, CMYK • Protection
  5. Using PDF in iOS Outline entry Page Thumbnail image Annotations

    Bead Bead Thread Outline entry Content stream Thread Named destinations Article threads Interactive form Outline hierarchy Document catalog Page • • • • • • • • • • • • Page tree • • • • • • • • • • • •
  6. Using PDF in iOS Hello World %PDF-1.4 1 0 obj

    <</Type /Catalog /Pages 2 0 R>> endobj 2 0 obj <</Type /Pages /Kids [3 0 R] /Count 1>> endobj 3 0 obj<</Type /Page /Parent 2 0 R /Resources 4 0 R / MediaBox [0 0 500 800] /Contents 6 0 R>> endobj 4 0 obj<</Font <</F1 5 0 R>>>> endobj 5 0 obj<</Type /Font /Subtype /Type1 /BaseFont / Helvetica>> endobj 6 0 obj <</Length 44>> stream BT /F1 24 Tf 175 720 Td (Hello World!)Tj ET endstream endobj trailer <</Size 7/Root 1 0 R>> %%EOF Hello World!
  7. Using PDF in iOS CGPDFDocument • init?(_ url: CFURL) •

    var numberOfPages: Int { get } • func page(at pageNumber: Int) -> CGPDFPage? • func unlockWithPassword(_ pw: UnsafePointer<Int8>) -> Bool
  8. Using PDF in iOS CGPDFPage • func getBoxRect(CGPDFBox) • var

    dictionary: CGPDFDictionaryRef? • var rotationAngle: Int32
  9. Using PDF in iOS YOUCANDOIT Sophie Houlden hasn’t spent a

    penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010
  10. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Core Graphics Coordinate Origin
  11. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Origin Origin UIView coordinate
  12. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Origin Origin ctx.translateBy(
 x: 0, 
 y: rect.height)
  13. Using PDF in iOS 18 | JULY 2010 Origin Origin

    ctx.scaleBy(
 x: 1,
 y: -1)
  14. Using PDF in iOS BET A | GOING INDIE Y

    O U C A N D O I T S o p h i e H o u l d e n h a s n ’ t s p e n t a p e n n y o n t o o l s t o m a k e h e r i n d i e g a m e s – s h e j u s t r o l l e d u p h e r s l e e v e s a n d g o t o n w i t h i t . H e r e s h e e x p l a i n s h o w i t ’ s d o n e … 18 | JUL Y 2010 Origin Origin ctx.scaleBy(
 x: 1,
 y: -1)
  15. Using PDF in iOS BET A | GOING INDIE Y

    O U C A N D O I T S o p h i e H o u l d e n h a s n ’ t s p e n t a p e n n y o n t o o l s t o m a k e h e r i n d i e g a m e s – s h e j u s t r o l l e d u p h e r s l e e v e s a n d g o t o n w i t h i t . H e r e s h e e x p l a i n s h o w i t ’ s d o n e … 18 | JUL Y 2010 Origin Origin ctx.scaleBy(
 x: 1,
 y: -1)
  16. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Origin Origin
  17. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Origin Origin let scale = min(
 rect.width/box.width, 
 rect.height/box.height)
 
 ctx.scaleBy(
 x: scale, y: scale)
  18. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Origin Origin ctx.drawPDFPage(
 page)
  19. Using PDF in iOS Code in Swift let box =

    page.getBoxRect(.cropBox) let rect = self.view.bounds ctx.translateBy(x: 0, y: rect.height) ctx.scaleBy(x: 1, y: -1) ctx.scaleBy(x: rect.width / box.width, y: rect.height / box.height) ctx.drawPDFPage(page)
  20. Using PDF in iOS Dealing with CGPDFDocument • CGPDFDocument is

    originally designed for Desktop • It cashes internally, hard to control releasing caches… • Releasing CGPDFDocument on memory warning may be too late… • Releasing CGPDFDocument once in a while
  21. Using PDF in iOS contentScaleFactor • OK – Device size

    like small contents • NG – Magazine / Newspaper like large contents • eg. 2048x1536 12MB — (4x zoom) — 8192 x 6144 48MB ⚠
  22. Using PDF in iOS PDF view draws based on dummy

    view coordinate Zoom → dummy view pdf view
  23. Using PDF in iOS Convert rect from 
 content dummy

    view override func draw(_ layer: CALayer, in ctx: CGContext) { UIGraphicsPushContext(ctx) ctx.saveGState() let box = page.getBoxRect(.cropBox) let rect = self.contentView.convert(self.contentView.bounds, to: self) ctx.translateBy(x: rect.minX, y: rect.minY) ctx.translateBy(x: 0, y: rect.height) ctx.scaleBy(x: 1, y: -1) ctx.scaleBy(x: rect.width / box.width, y: rect.height / box.height) ctx.drawPDFPage(page) ctx.restoreGState() UIGraphicsPopContext() } →
  24. Using PDF in iOS UIScrollView delegate func viewForZooming(in scrollView: UIScrollView)

    -> UIView? { return contentView } func scrollViewDidZoom(_ scrollView: UIScrollView) { self.pdfPageView.setNeedsDisplay() } func scrollViewDidScroll(_ scrollView: UIScrollView) { self.pdfPageView.setNeedsDisplay() }
  25. Using PDF in iOS Use draw(layer, in context)
 not draw(_

    rect) class PDFPageView: UIView { override func draw(_ layer: CALayer, in ctx: CGContext) { UIGraphicsPushContext(ctx) // drawing UIGraphicsPopContext() } override func setNeedsDisplay() { super.setNeedsDisplay() self.layer.setNeedsDisplay() } }
  26. Using PDF in iOS 2.pdf Split a large PDF into

    
 smaller multiple pages paper.pdf 1.pdf 3.pdf
  27. Using PDF in iOS Dummy Content View UIView PDFPageView UIScrollView

    Dummy
 ContentView Low resolution bitmap image (fast) Native PDF
 drawing (slow) show/hide
  28. Using PDF in iOS Use fileURL
 avoid CGDataProvider • PDF

    file includes cross references • Cross references includes file offsets to objects • Using file offset to access objects faster than we think • Do not read whole file and feed to CGPDFDocument
  29. Using PDF in iOS Drawn Image slides BETA | GOING

    INDIE YOUCANDOIT Sophie Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 BETA | GOING INDIE YOUCANDOIT Sophie Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Bitmap drawing Native PDF drawing
  30. Using PDF in iOS Drawn Image slides BETA | GOING

    INDIE YOUCANDOIT Sophie Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 BETA | GOING INDIE YOUCANDOIT Sophie Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Bitmap drawing Native PDF drawing
  31. Using PDF in iOS BETA | GOING INDIE YOUCANDOIT Sophie

    Houlden hasn’t spent a penny on tools to make her indie games – she just rolled up her sleeves and got on with it. Here she explains how it’s done… 18 | JULY 2010 Check origin!! page.getBoxRect(.crop) Origin * Box's minX, minY may not be zero
  32. Using PDF in iOS CGPDFObjectRef .dictionary CGPDFDictionaryRef OpaquePointer .array CGPDFArrayRef

    OpaquePointer .stream CGPDFContentStreamRef OpaquePointer .string CGPDFStringRef OpaquePointer .name UnsafePointer<Int8> UnsafePointer<Int8> .integer CGPDFInteger Int .real CGPDFReal CGFloat .boolean CGPDFBoolean UInt8 .null
  33. Using PDF in iOS Iterating CGPDFDictionary func PDFDictionary(_ dictionary: CGPDFDictionaryRef)

    -> [String: CGPDFObjectRef] { 
 var context = [String: CGPDFObjectRef]() 
 let contextRawPtr = UnsafeMutableRawPointer(&context) CGPDFDictionaryApplyFunction(dictionary, { (key, value, rawPtr) -> Void in if let key = String(validatingUTF8: key), let contextPtr = UnsafeMutablePointer<[String: CGPDFObjectRef]>( OpaquePointer(rawPtr)) { contextPtr.pointee[key] = value } }, contextRawPtr) 
 return context } for (key, object) in PDFDictionary(catalog).enumerated() { print("\(key), \(object)") }
  34. Using PDF in iOS CGPDFObjectGetType WBSWBMVF$(1%'0CKFDU3FGǘ
 TXJUDI$(1%'0CKFDU(FU5ZQF WBMVF \ DBTFBSSBZ

     WBSPCKFDU$(1%'"SSBZ3FG OJM  $(1%'0CKFDU(FU7BMVF WBMVF BSSBZ PCKFDU  DBTFEJDUJPOBSZ  WBSPCKFDU$(1%'%JDUJPOBSZ3FG OJM  $(1%'0CKFDU(FU7BMVF WBMVF EJDUJPOBSZ PCKFDU  DBTFTUSFBN  DBTFTUSJOH  DBTFOBNF   DBTFJOUFHFS  DBTFSFBM   DBTFCPPMFBO  DBTFOVMMCSFBL ^
  35. Using PDF in iOS PDFScanner • Low level API •

    Scanner knows how to parse page content • PDF's operator
  36. Using PDF in iOS Page –> Font MediaBox Resources Page

    Contents … Font … Tc1 Tc2 … subtype … …
  37. Using PDF in iOS Font Types Font Type Entries Type

    1 Name, BaseFont, FirstChar, LastChar, Widths, FontDescriptor, Encoding, ToUnicode, ... True Type Name, BaseFont, FirstChar, LastChar, Widths, FontDescriptor, Encoding, ToUnicode, … Type 3 Name, FontBBox, FontMatrix, CharProcs, FisrChar, LastChar, Widths, FontDescriptor, ToUnicode … Type 0 Name, BaseFont, CIDSystemInfo, FontDescriptor, DW, DW2, CIDToGIDMap, ❌ ToUnicode
  38. Using PDF in iOS A Page knows how to draw

    MediaBox Resources Page Contents Font Tc2 dictionary array stream Drawing operators
  39. Using PDF in iOS Operators BT /F1 24 Tf 175

    720 Td (Hello World!)Tj ET Begin Text End Text Font Location Draw Text
  40. Using PDF in iOS Japanese Text BT /C2_0 1 Tf

    0 Tc 175 720 Td <30533093306B3061306F> Tj ET Font Location Draw Text
  41. Using PDF in iOS Decoding Method Case Decoding Method Has

    `ToUnicode` entry Parse `ToUnicode` entry No `ToUnicode` entry
 but WinAnsiEncoding Predefined Identity-H, Identity-V encoding
 No `ToUnicode` entry Using external CMap
  42. Using PDF in iOS Adobe CMap and CIDFont Files Specification

    Version 1.0 11 June 1993 Adobe Developer Support Adobe Systems Incorporated ® ® ®
  43. Using PDF in iOS ToUnicode = CMap %!PS-Adobe-3.0 Resource-CMap /CIDInit

    /ProcSet findresource begin 12 dict begin begincmap /CIDSystemInfo 3 dict dup begin /Registry (Adobe) def /Ordering (Japan1) def /Supplement 6 def end def /CMapName /Adobe-Japan1-6 def /CMapVersion 1.005 def /CMapType 1 def /XUID [1 10 25614] def /WMode 0 def /CIDCount 23058 def 1 begincodespacerange <0000> <5AFF> endcodespacerange 91 begincidrange <0000> <00ff> 0 <0100> <01ff> 256 <0200> <02ff> 512 <0300> <03ff> 768 <0400> <04ff> 1024 … <5600> <56ff> 22016 <5700> <57ff> 22272 <5800> <58ff> 22528 <5900> <59ff> 22784 <5a00> <5a11> 23040 endcidrange endcmap CMapName currentdict 
 /CMap defineresource pop end end ←Horizontal/Vertical ←code mapping
  44. Using PDF in iOS Outline entry Page Thumbnail image Annotations

    Bead Bead Thread Outline entry Content stream Thread Named destinations Article threads Interactive form Outline hierarchy Document catalog Page • • • • • • • • • • • • Page tree • • • • • • • • • • • •
  45. Using PDF in iOS ZPDF • Tentative name • Swift

    base PDF library • Parsing PDF • Extracting text and glyph positions • Will be open source when ready • sorry — this could take years
  46. Using PDF in iOS Wrap Up • Basic PDF format

    structure • Core Graphics PDF API • Fixing drawing upside down • Fixing runout of memory • Zooming PDF within UIScrollView
  47. Using PDF in iOS Wrap Up • Dealing with too

    slow drawing PDF page • Fixing drawing origin • Voyeur • Extracting text from PDF • ZKIT • Animation with PDF
  48. Using PDF in iOS Last Words • Likely it's hard

    to remember that many tricks and knowledges • What you have to remember is … ask "Kaz" [email protected]