SlideShare une entreprise Scribd logo
1  sur  135
Télécharger pour lire hors ligne
PDF.JS
      Julian Viereck
        @jviereck
jviereck.dev@gmail.com
Bespin
Skywriter
  Ace
Bespin
             Firefox
Skywriter
            DevTools
  Ace
Bespin
             Firefox    ETH
Skywriter
            DevTools   Zurich
  Ace
Bespin
             Firefox    ETH
                                 ?
Skywriter                       PDF.JS
            DevTools   Zurich
  Ace
Overview
• What is PDF.JS
• How PDF is structured
• Processing in PDF.JS
• Images & Fonts
• Infrastructure
• Problems & Todos
• Demo
What is PDF.JS
What is PDF.JS

• building faithful & efficient PDF renderer
What is PDF.JS

• building faithful & efficient PDF renderer
• HTML5 technology experiment
What is PDF.JS

• building faithful & efficient PDF renderer
• HTML5 technology experiment
• no native code
What is PDF.JS

•   building faithful & efficient PDF renderer
•   HTML5 technology experiment
•   no native code
•   secure (web sandbox)
What is PDF.JS

•   building faithful & efficient PDF renderer
•   HTML5 technology experiment
•   no native code
•   secure (web sandbox)
•   Mozilla Labs Project - Open Source
Most vulnerable programs




 Source: http://www.csis.dk/en/csis/news/3321
How PDF is structured




 PDF file
How PDF is structured
 Header    PDF version




 PDF file
How PDF is structured
 Header      PDF version

             sequence of objets
   Body

 [Objects]   fonts, drawing cmds, images,
             words, bookmarks, form fields




 PDF file
How PDF is structured
 Header      PDF version

             sequence of objets
   Body

 [Objects]   fonts, drawing cmds, images,
             words, bookmarks, form fields
xRef Table   mapping objID    byte offset


 PDF file
How PDF is structured
 Header      PDF version

             sequence of objets
   Body

 [Objects]   fonts, drawing cmds, images,
             words, bookmarks, form fields
xRef Table   mapping objID     byte offset
  Trailer    root objID, xRef byte offset
 PDF file     root obj = ref to pages catalog
Processing in PDF.JS
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)
• page.startRendering(graphics)
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)
• page.startRendering(graphics)
 • read & convert all PDF cmds ➟ IR
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)               Intermediate


• page.startRendering(graphics)         Representation




 • read & convert all PDF cmds ➟ IR
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)                Intermediate


• page.startRendering(graphics)          Representation




 • read & convert all PDF cmds ➟ IR PartialEvaluator
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)                Intermediate


• page.startRendering(graphics)          Representation




 • read & convert all PDF cmds ➟ IR PartialEvaluator
 • load required objects (fonts, images)
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)                Intermediate


• page.startRendering(graphics)          Representation




 • read & convert all PDF cmds ➟ IR PartialEvaluator
 • load required objects (fonts, images)
 • graphics.executeIR(IR)
Processing in PDF.JS
• get plain Uint8Array via XHR2, build Stream
• new PDFDoc(stream): read xRef, root object
• page = PDFDoc.getPage(N)                  Intermediate


• page.startRendering(graphics)            Representation




 • read & convert all PDF cmds ➟ IR PartialEvaluator
 • load required objects (fonts, images)
 • graphics.executeIR(IR)                CanvasGraphics
Why IR?
Data
Why IR?
                  Partial
Data
                 Evaluator
Why IR?
                  Partial
Data
                 Evaluator
Why IR?
        “get page 2”    Partial
Data
                       Evaluator
Why IR?
        “get page 2”    Partial
Data
                       Evaluator

                             builds
Why IR?
        “get page 2”    Partial
Data
                       Evaluator

                             builds

                       draw(
                         obj#3,
                         dict.x,
                         dict.y
                       )
Why IR?
            “get page 2”    Partial
 Data
                           Evaluator

                                 builds

                           draw(
                             obj#3,
Graphics                     dict.x,
                             dict.y
                           )
Why IR?
            “get page 2”    Partial
 Data
                           Evaluator

                                 builds

                           draw(
                             obj#3,
Graphics                     dict.x,
                             dict.y
                           )
Why IR?
            “get page 2”    Partial
 Data
                           Evaluator

                                 builds

                           draw(
                             obj#3,
Graphics                     dict.x,
            drawing cmds     dict.y
                           )
Why IR?
                      “get page 2”    Partial
              Data
                                     Evaluator


 obj#3?                                    builds
dict.x, .y?
                                     draw(
                                       obj#3,
          Graphics                     dict.x,
                      drawing cmds     dict.y
                                     )
Why IR?
                      “get page 2”    Partial
              Data
                                     Evaluator


 obj#3?                                    builds
dict.x, .y?
                                     draw(
                                       obj#3,
          Graphics                     dict.x,
                      drawing cmds     dict.y
                                     )
Why IR?
                            “get page 2”    Partial
              Data
                                           Evaluator


 obj#3?              obj#3 = ”foo”               builds
dict.x, .y?             x = 20
                        y = 30             draw(
                                             obj#3,
          Graphics                           dict.x,
                           drawing cmds      dict.y
                                           )
Why IR?
                            “get page 2”    Partial
              Data
                                           Evaluator


 obj#3?              obj#3 = ”foo”               builds
dict.x, .y?             x = 20
                        y = 30             draw(
                                             obj#3,
          Graphics                           dict.x,
                           drawing cmds      dict.y
                                           )
Why IR?
                            “get page 2”    Partial
              Data
                                           Evaluator


 obj#3?              obj#3 = ”foo”               builds
dict.x, .y?             x = 20
                        y = 30             draw(
                                             obj#3,
          Graphics                           dict.x,
                           drawing cmds      dict.y
                                           )
                     draw on
                      canvas
Problem Processing
Problem Processing
• Extracting data slow (compressed)
Problem Processing
• Extracting data slow (compressed)
• Transform data (images) slow
Problem Processing
• Extracting data slow (compressed)
• Transform data (images) slow
• Sometimes a lot of objects on page
Problem Processing
• Extracting data slow (compressed)
• Transform data (images) slow
• Sometimes a lot of objects on page
➡ Freezes UI
Problem Processing
• Extracting data slow (compressed)
• Transform data (images) slow
• Sometimes a lot of objects on page
➡ Freezes UI
➡ Use WebWorker
Problem Processing
• Extracting data slow (compressed)
• Transform data (images) slow
• Sometimes a lot of objects on page
➡ Freezes UI
➡ Use WebWorker
➡ :( no direct memory access, postMessage
Main     Web
Thread   Worker


Data
Main          Web
Thread        Worker

          Partial
Data
         Evaluator
Main                         Web
Thread                       Worker

            data         Partial
Data
         “get page 2”   Evaluator
Main                         Web
Thread                       Worker

            data         Partial
Data                                Data
         “get page 2”   Evaluator
Main                             Web
Thread                           Worker

            data            Partial
Data                                   Data
         “get page 2”      Evaluator


                        builds
Main                             Web
Thread                           Worker

            data            Partial
Data                                   Data
         “get page 2”      Evaluator


                        builds

                           draw(
                             obj#3,
                             dict.x,
                             dict.y
                           )
Main                             Web
Thread                           Worker

            data            Partial
Data                                   Data
         “get page 2”      Evaluator


                        builds

                           draw(
                             obj#3,
                             dict.x,
                             dict.y
                           )
Main                             Web
Thread                           Worker

            data            Partial
Data                                    Data
         “get page 2”      Evaluator


                        builds

                           draw(
                             draw(
                             obj#3,
                               “foo”,
                             dict.x,
                               20,
                             dict.y
                               30
                           )
                             )
Main                             Web
Thread                           Worker

            data            Partial
Data                                    Data
         “get page 2”      Evaluator


                        builds

                           draw(
                             draw(        IR
                             obj#3,
                               “foo”,
                             dict.x,
                               20,
                             dict.y
                               30
                           )
                             )
Main                             Web
  Thread                           Worker

              data            Partial
 Data                                     Data
           “get page 2”      Evaluator


                          builds

                             draw(
                               draw(        IR
                               obj#3,
                                 “foo”,
Graphics                       dict.x,
                                 20,
                               dict.y
                                 30
                             )
                               )
Main                             Web
  Thread                           Worker

              data            Partial
 Data                                     Data
           “get page 2”      Evaluator


                          builds

                             draw(
                               draw(        IR
                               obj#3,
                                 “foo”,
Graphics                       dict.x,
             IR cmds             20,
                               dict.y
                                 30
                             )
                               )
Main                             Web
  Thread                           Worker

              data            Partial
 Data                                     Data
           “get page 2”      Evaluator


                          builds

                             draw(
                               draw(        IR
                               obj#3,
                                 “foo”,
Graphics                       dict.x,
             IR cmds             20,
                               dict.y
                                 30
                             )
                               )
Main                                Web
  Thread                              Worker

                   data          Partial
 Data                                        Data
              “get page 2”      Evaluator


                             builds

                                draw(
                                  draw(        IR
                                  obj#3,
                                    “foo”,
Graphics                          dict.x,
                  IR cmds           20,
                                  dict.y
                                    30
                                )
        draw on                   )
         canvas
5 0 obj
<<
 /Length 8 0 R
>>
 stream
   /GS1 gs
   /F0 12 Tf
   BT
     100 700 Td
     (Hello World!) Tj
   ET
   50 600 m
   400 600 l
   S
 endstream
endobj
5 0 obj                  PartialEvaluator
<<
 /Length 8 0 R
>>
 stream
   /GS1 gs
   /F0 12 Tf
   BT
     100 700 Td
     (Hello World!) Tj
   ET
   50 600 m
   400 600 l
   S
 endstream
endobj
5 0 obj             xRef, catalog,
                 + resources         PartialEvaluator
<<
 /Length 8 0 R
>>
 stream
   /GS1 gs
   /F0 12 Tf
   BT
     100 700 Td
     (Hello World!) Tj
   ET
   50 600 m
   400 600 l
   S
 endstream
endobj
5 0 obj             xRef, catalog,
                 + resources         PartialEvaluator
<<
 /Length 8 0 R
>>
 stream
   /GS1 gs
   /F0 12 Tf
   BT
     100 700 Td
     (Hello World!) Tj
   ET
   50 600 m
   400 600 l
   S
 endstream
endobj                                  Graphics
5 0 obj             xRef, catalog,
                 + resources              PartialEvaluator
<<
 /Length 8 0 R
>>                                   setGState: 	

   [ LW: 10 ]
 stream                              dependency:	

   [ font0 ]
   /GS1 gs                           setFont: 	

     font0, 12
   /F0 12 Tf                         beginText
   BT                                moveText: 	

    100, 700
     100 700 Td                      showText: 	

    “Hello World!”
     (Hello World!) Tj               endText
   ET                                moveTo: 	

      50, 600
   50 600 m                          lineTo: 	

      400, 600
   400 600 l                         stroke
   S
 endstream
endobj                                        Graphics
5 0 obj             xRef, catalog,
                 + resources              PartialEvaluator
<<
 /Length 8 0 R
>>                                   setGState: 	

   [ LW: 10 ]
 stream                              dependency:	

   [ font0 ]
   /GS1 gs                           setFont: 	

     font0, 12
   /F0 12 Tf                         beginText
   BT                                moveText: 	

    100, 700
     100 700 Td                      showText: 	

    “Hello World!”
     (Hello World!) Tj               endText
   ET                                moveTo: 	

      50, 600
   50 600 m                          lineTo: 	

      400, 600
   400 600 l                         stroke
   S
 endstream
endobj                                        Graphics
5 0 obj             xRef, catalog,                                 IR
                 + resources              PartialEvaluator
<<
 /Length 8 0 R
>>                                   setGState: 	

   [ LW: 10 ]
 stream                              dependency:	

   [ font0 ]
   /GS1 gs                           setFont: 	

     font0, 12
   /F0 12 Tf                         beginText
   BT                                moveText: 	

    100, 700
     100 700 Td                      showText: 	

    “Hello World!”
     (Hello World!) Tj               endText
   ET                                moveTo: 	

      50, 600
   50 600 m                          lineTo: 	

      400, 600
   400 600 l                         stroke
   S
 endstream
endobj                                        Graphics
Images
Images
• JPEG streams:
Images
• JPEG streams:
 • DOMImg.src = 'data:image/jpeg;base64,'
    + window.btoa(bytesToString(bytes));
Images
• JPEG streams:
 • DOMImg.src = 'data:image/jpeg;base64,'
    + window.btoa(bytesToString(bytes));
• If not JPEG stream:
Images
• JPEG streams:
 • DOMImg.src = 'data:image/jpeg;base64,'
    + window.btoa(bytesToString(bytes));
• If not JPEG stream:
 • read bytes, convert to colorspace
Images
• JPEG streams:
 • DOMImg.src = 'data:image/jpeg;base64,'
    + window.btoa(bytesToString(bytes));
• If not JPEG stream:
 • read bytes, convert to colorspace
 • imgData = canvas.getImageData()
Images
• JPEG streams:
 • DOMImg.src = 'data:image/jpeg;base64,'
    + window.btoa(bytesToString(bytes));
• If not JPEG stream:
 • read bytes, convert to colorspace
 • imgData = canvas.getImageData()
 • fillWithPixelData(bytes, imgData)
Images
• JPEG streams:
 • DOMImg.src = 'data:image/jpeg;base64,'
    + window.btoa(bytesToString(bytes));
• If not JPEG stream:
 • read bytes, convert to colorspace
 • imgData = canvas.getImageData()
 • fillWithPixelData(bytes, imgData)
 • canvas.putImageData(imgData)
Jpeg, but...
Jpeg, but...

• no natives support for CMYK Jpeg
Jpeg, but...

• no natives support for CMYK Jpeg
 ➡ use JS implementation
Jpeg, but...

• no natives support for CMYK Jpeg
 ➡ use JS implementation
• no native support for Jpeg 2000
Jpeg, but...

• no natives support for CMYK Jpeg
 ➡ use JS implementation
• no native support for Jpeg 2000
 ➡ use EMScripten: C-Lib ➟ JS
Jpeg, but...

• no natives support for CMYK Jpeg
 ➡ use JS implementation
• no native support for Jpeg 2000
 ➡ use EMScripten: C-Lib ➟ JS
‣ works, but not that performant
Fonts
Fonts
• There are lots of different font formats!
Fonts
• There are lots of different font formats!
 • fonts are converted to OpenType
Fonts
• There are lots of different font formats!
 • fonts are converted to OpenType
 • use CSS:
      @font-face { font-family:'font0';
    src:url(data:font/opentype;base64, ...)
Fonts
• There are lots of different font formats!
 • fonts are converted to OpenType
 • use CSS:
      @font-face { font-family:'font0';
    src:url(data:font/opentype;base64, ...)
• some fonts can’t be converted :(
Fonts
• There are lots of different font formats!
 • fonts are converted to OpenType
 • use CSS:
      @font-face { font-family:'font0';
    src:url(data:font/opentype;base64, ...)
• some fonts can’t be converted :(
 • paint them
Fonts
Type I     convert to Type II

Type II      “use directly”

Type III     paint ourself

 CDI       convert to Type II
Fonts
Type I     convert to Type II
                                still need
Type II      “use directly”     to repair
                                  fonts!
Type III     paint ourself

 CDI       convert to Type II
Infrastructure
Infrastructure
• Using GitHub
Infrastructure
• Using GitHub
 • Issue Tracker
Infrastructure
• Using GitHub
 • Issue Tracker
 • Pull Requests
Infrastructure
• Using GitHub
 • Issue Tracker
 • Pull Requests
 • Wiki
Infrastructure
• Using GitHub
 • Issue Tracker
 • Pull Requests
 • Wiki
• Update gh-pages on every push
Infrastructure
• Using GitHub
 • Issue Tracker
 • Pull Requests
 • Wiki
• Update gh-pages on every push
• Testing:
Infrastructure
• Using GitHub
 • Issue Tracker
 • Pull Requests
 • Wiki
• Update gh-pages on every push
• Testing:
 • In Pull Request: “@pdfjsbot test”
Infrastructure
• Using GitHub
 • Issue Tracker
 • Pull Requests
 • Wiki
• Update gh-pages on every push
• Testing:
 • In Pull Request: “@pdfjsbot test”
 • Runs tests on AC2 instance
Infrastructure
Infrastructure
• AreWePdfYet?
Infrastructure
• AreWePdfYet?
 • Take top100 PDFs from Google
Infrastructure
• AreWePdfYet?
 • Take top100 PDFs from Google
 • render the first 5 pages each
Infrastructure
• AreWePdfYet?
 • Take top100 PDFs from Google
 • render the first 5 pages each
 • compare to Preview
Infrastructure
• AreWePdfYet?
 • Take top100 PDFs from Google
 • render the first 5 pages each
 • compare to Preview
 • http://people.mozilla.com/~bdahl/
    corpusreport/test/ref/
Todo = Help :)
Worker Canvas
'Read-Only' Memory
    Web Worker
Faster Canvas
  Rendering
CMYK Jpeg
 Jpeg2000
Font Load Event
WebPrint API
XHR Range Support
Font Support
Parallel Web Worker
SVG Backend
(text selection [Gecko])
“HTML5” Backend
Search | Selection | Copy
Input Forms
More Parts Of Spec
Improve Viewer
Pref & Memory
    Analysis
Improve Test
Infrastructure
More Testing!
More Testing

• use PDF.JS extension!
• http://mozilla.github.com/pdf.js/extensions/
  firefox/pdf.js.xpi
• report broken PDFs!
• help us categorize issues
Feedback Feature
Demo
Github:                              Readme
 https://github.com/mozilla/pdf.js    Issues
                                       Wiki
Twitter:
 @pdfjs
Mailing List:
 https://groups.google.com/group/
mozilla.dev.pdf-js/topics
IRC:
 irc.mozilla.org #pdfjs
Engineering Weekly Call:
 Thursday - 10:00am PDT, 17:00 UTC
Q &A

Contenu connexe

Tendances

Tendances (8)

XNA L09–2D Graphics and Particle Engines
XNA L09–2D Graphics and Particle EnginesXNA L09–2D Graphics and Particle Engines
XNA L09–2D Graphics and Particle Engines
 
Iphone course 1
Iphone course 1Iphone course 1
Iphone course 1
 
Gazr
GazrGazr
Gazr
 
Classification Theory
Classification TheoryClassification Theory
Classification Theory
 
Lambda expressions in C++
Lambda expressions in C++Lambda expressions in C++
Lambda expressions in C++
 
Python Objects
Python ObjectsPython Objects
Python Objects
 
Swift, via "swift-2048"
Swift, via "swift-2048"Swift, via "swift-2048"
Swift, via "swift-2048"
 
The Ring programming language version 1.5.1 book - Part 46 of 180
The Ring programming language version 1.5.1 book - Part 46 of 180The Ring programming language version 1.5.1 book - Part 46 of 180
The Ring programming language version 1.5.1 book - Part 46 of 180
 

En vedette (6)

2011 05-jszurich
2011 05-jszurich2011 05-jszurich
2011 05-jszurich
 
PDF.JS at SwissJeese 2012
PDF.JS at SwissJeese 2012PDF.JS at SwissJeese 2012
PDF.JS at SwissJeese 2012
 
2011 09-pdfjs
2011 09-pdfjs2011 09-pdfjs
2011 09-pdfjs
 
Implementing New Web
Implementing New WebImplementing New Web
Implementing New Web
 
Implementing new WebAPIs
Implementing new WebAPIsImplementing new WebAPIs
Implementing new WebAPIs
 
Learn BEM: CSS Naming Convention
Learn BEM: CSS Naming ConventionLearn BEM: CSS Naming Convention
Learn BEM: CSS Naming Convention
 

Similaire à 2011 11-mozcamp

Introducing AlloyUI DiagramBuilder
Introducing AlloyUI DiagramBuilderIntroducing AlloyUI DiagramBuilder
Introducing AlloyUI DiagramBuilder
Eduardo Lundgren
 
February 2017 HUG: Data Sketches: A required toolkit for Big Data Analytics
February 2017 HUG: Data Sketches: A required toolkit for Big Data AnalyticsFebruary 2017 HUG: Data Sketches: A required toolkit for Big Data Analytics
February 2017 HUG: Data Sketches: A required toolkit for Big Data Analytics
Yahoo Developer Network
 
Lens: Data exploration with Dask and Jupyter widgets
Lens: Data exploration with Dask and Jupyter widgetsLens: Data exploration with Dask and Jupyter widgets
Lens: Data exploration with Dask and Jupyter widgets
Víctor Zabalza
 

Similaire à 2011 11-mozcamp (20)

The InfoGrid Graph DataBase
The InfoGrid Graph DataBaseThe InfoGrid Graph DataBase
The InfoGrid Graph DataBase
 
Extjs + Gears
Extjs + GearsExtjs + Gears
Extjs + Gears
 
Python business intelligence (PyData 2012 talk)
Python business intelligence (PyData 2012 talk)Python business intelligence (PyData 2012 talk)
Python business intelligence (PyData 2012 talk)
 
Introducing AlloyUI DiagramBuilder
Introducing AlloyUI DiagramBuilderIntroducing AlloyUI DiagramBuilder
Introducing AlloyUI DiagramBuilder
 
MongoDB Solution for Internet of Things and Big Data
MongoDB Solution for Internet of Things and Big DataMongoDB Solution for Internet of Things and Big Data
MongoDB Solution for Internet of Things and Big Data
 
Lab pratico per la progettazione di soluzioni MongoDB in ambito Internet of T...
Lab pratico per la progettazione di soluzioni MongoDB in ambito Internet of T...Lab pratico per la progettazione di soluzioni MongoDB in ambito Internet of T...
Lab pratico per la progettazione di soluzioni MongoDB in ambito Internet of T...
 
February 2017 HUG: Data Sketches: A required toolkit for Big Data Analytics
February 2017 HUG: Data Sketches: A required toolkit for Big Data AnalyticsFebruary 2017 HUG: Data Sketches: A required toolkit for Big Data Analytics
February 2017 HUG: Data Sketches: A required toolkit for Big Data Analytics
 
Secrets of Awesome JavaScript API Design
Secrets of Awesome JavaScript API DesignSecrets of Awesome JavaScript API Design
Secrets of Awesome JavaScript API Design
 
KVSの性能、RDBMSのインデックス、更にMapReduceを併せ持つAll-in-One NoSQL: MongoDB
KVSの性能、RDBMSのインデックス、更にMapReduceを併せ持つAll-in-One NoSQL: MongoDB KVSの性能、RDBMSのインデックス、更にMapReduceを併せ持つAll-in-One NoSQL: MongoDB
KVSの性能、RDBMSのインデックス、更にMapReduceを併せ持つAll-in-One NoSQL: MongoDB
 
The NASA Vision Workbench: Reflections on Image Processing in C++
The NASA Vision Workbench: Reflections on Image Processing in C++The NASA Vision Workbench: Reflections on Image Processing in C++
The NASA Vision Workbench: Reflections on Image Processing in C++
 
D3.js: Data Visualization for the Web
D3.js: Data Visualization for the Web D3.js: Data Visualization for the Web
D3.js: Data Visualization for the Web
 
Scalable Cloud Solutions with Node.js
Scalable Cloud Solutions with Node.jsScalable Cloud Solutions with Node.js
Scalable Cloud Solutions with Node.js
 
Graph computation
Graph computationGraph computation
Graph computation
 
Building Your First MongoDB Application
Building Your First MongoDB ApplicationBuilding Your First MongoDB Application
Building Your First MongoDB Application
 
Lens: Data exploration with Dask and Jupyter widgets
Lens: Data exploration with Dask and Jupyter widgetsLens: Data exploration with Dask and Jupyter widgets
Lens: Data exploration with Dask and Jupyter widgets
 
Tools and practices for rapid application development
Tools and practices for rapid application developmentTools and practices for rapid application development
Tools and practices for rapid application development
 
The Visualization Toolkit (VTK) and why you might care about it
The Visualization Toolkit (VTK) and why you might care about itThe Visualization Toolkit (VTK) and why you might care about it
The Visualization Toolkit (VTK) and why you might care about it
 
How dojo works
How dojo worksHow dojo works
How dojo works
 
HTML5 - Chances and Pitfalls (Bytro Labs GmbH)
HTML5 - Chances and Pitfalls (Bytro Labs GmbH)HTML5 - Chances and Pitfalls (Bytro Labs GmbH)
HTML5 - Chances and Pitfalls (Bytro Labs GmbH)
 
Backbone.js: Run your Application Inside The Browser
Backbone.js: Run your Application Inside The BrowserBackbone.js: Run your Application Inside The Browser
Backbone.js: Run your Application Inside The Browser
 

Dernier

Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)
Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)
Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)
Business Bay Call Girls || 0529877582 || Call Girls Service in Business Bay Dubai
 
FULL NIGHT — 9999894380 Call Girls In Patel Nagar | Delhi
FULL NIGHT — 9999894380 Call Girls In Patel Nagar | DelhiFULL NIGHT — 9999894380 Call Girls In Patel Nagar | Delhi
FULL NIGHT — 9999894380 Call Girls In Patel Nagar | Delhi
SaketCallGirlsCallUs
 
Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...
Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...
Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...
home
 
FULL NIGHT — 9999894380 Call Girls In Ashok Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In Ashok Vihar | DelhiFULL NIGHT — 9999894380 Call Girls In Ashok Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In Ashok Vihar | Delhi
SaketCallGirlsCallUs
 
FULL NIGHT — 9999894380 Call Girls In Paschim Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In  Paschim Vihar | DelhiFULL NIGHT — 9999894380 Call Girls In  Paschim Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In Paschim Vihar | Delhi
SaketCallGirlsCallUs
 
FULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | Delhi
FULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | DelhiFULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | Delhi
FULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | Delhi
SaketCallGirlsCallUs
 
Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)
Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)
Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)
Business Bay Call Girls || 0529877582 || Call Girls Service in Business Bay Dubai
 
UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)
UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)
UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)
Business Bay Call Girls || 0529877582 || Call Girls Service in Business Bay Dubai
 
Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)
Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)
Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)
Business Bay Call Girls || 0529877582 || Call Girls Service in Business Bay Dubai
 

Dernier (20)

Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)
Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)
Dubai Call Girls # 00971528860074 # 24/7 Call Girls In Dubai || (UAE)
 
FULL NIGHT — 9999894380 Call Girls In Patel Nagar | Delhi
FULL NIGHT — 9999894380 Call Girls In Patel Nagar | DelhiFULL NIGHT — 9999894380 Call Girls In Patel Nagar | Delhi
FULL NIGHT — 9999894380 Call Girls In Patel Nagar | Delhi
 
VIP Ramnagar Call Girls, Ramnagar escorts Girls 📞 8617697112
VIP Ramnagar Call Girls, Ramnagar escorts Girls 📞 8617697112VIP Ramnagar Call Girls, Ramnagar escorts Girls 📞 8617697112
VIP Ramnagar Call Girls, Ramnagar escorts Girls 📞 8617697112
 
GENUINE EscoRtS,Call Girls IN South Delhi Locanto TM''| +91-8377087607
GENUINE EscoRtS,Call Girls IN South Delhi Locanto TM''| +91-8377087607GENUINE EscoRtS,Call Girls IN South Delhi Locanto TM''| +91-8377087607
GENUINE EscoRtS,Call Girls IN South Delhi Locanto TM''| +91-8377087607
 
Akbar Religious Policy and Sufism comparison.pptx
Akbar Religious Policy and Sufism comparison.pptxAkbar Religious Policy and Sufism comparison.pptx
Akbar Religious Policy and Sufism comparison.pptx
 
Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...
Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...
Authentic # 00971556872006 # Hot Call Girls Service in Dubai By International...
 
FULL NIGHT — 9999894380 Call Girls In Ashok Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In Ashok Vihar | DelhiFULL NIGHT — 9999894380 Call Girls In Ashok Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In Ashok Vihar | Delhi
 
Young⚡Call Girls in Tughlakabad Delhi >༒9667401043 Escort Service
Young⚡Call Girls in Tughlakabad Delhi >༒9667401043 Escort ServiceYoung⚡Call Girls in Tughlakabad Delhi >༒9667401043 Escort Service
Young⚡Call Girls in Tughlakabad Delhi >༒9667401043 Escort Service
 
FULL NIGHT — 9999894380 Call Girls In Paschim Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In  Paschim Vihar | DelhiFULL NIGHT — 9999894380 Call Girls In  Paschim Vihar | Delhi
FULL NIGHT — 9999894380 Call Girls In Paschim Vihar | Delhi
 
Young⚡Call Girls in Uttam Nagar Delhi >༒9667401043 Escort Service
Young⚡Call Girls in Uttam Nagar Delhi >༒9667401043 Escort ServiceYoung⚡Call Girls in Uttam Nagar Delhi >༒9667401043 Escort Service
Young⚡Call Girls in Uttam Nagar Delhi >༒9667401043 Escort Service
 
FULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | Delhi
FULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | DelhiFULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | Delhi
FULL NIGHT — 9999894380 Call Girls In Shivaji Enclave | Delhi
 
Jeremy Casson - An Architectural and Historical Journey Around Europe
Jeremy Casson - An Architectural and Historical Journey Around EuropeJeremy Casson - An Architectural and Historical Journey Around Europe
Jeremy Casson - An Architectural and Historical Journey Around Europe
 
Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)
Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)
Dubai Call Girl Number # 0522916705 # Call Girl Number In Dubai # (UAE)
 
Jeremy Casson - How Painstaking Restoration Has Revealed the Beauty of an Imp...
Jeremy Casson - How Painstaking Restoration Has Revealed the Beauty of an Imp...Jeremy Casson - How Painstaking Restoration Has Revealed the Beauty of an Imp...
Jeremy Casson - How Painstaking Restoration Has Revealed the Beauty of an Imp...
 
Moradabad Call Girls - 📞 8617697112 🔝 Top Class Call Girls Service Available
Moradabad Call Girls - 📞 8617697112 🔝 Top Class Call Girls Service AvailableMoradabad Call Girls - 📞 8617697112 🔝 Top Class Call Girls Service Available
Moradabad Call Girls - 📞 8617697112 🔝 Top Class Call Girls Service Available
 
Sirmaur Call Girls Book Now 8617697112 Top Class Pondicherry Escort Service A...
Sirmaur Call Girls Book Now 8617697112 Top Class Pondicherry Escort Service A...Sirmaur Call Girls Book Now 8617697112 Top Class Pondicherry Escort Service A...
Sirmaur Call Girls Book Now 8617697112 Top Class Pondicherry Escort Service A...
 
UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)
UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)
UAE Call Girls # 0528675665 # Independent Call Girls In Dubai ~ (UAE)
 
Deconstructing Gendered Language; Feminist World-Making 2024
Deconstructing Gendered Language; Feminist World-Making 2024Deconstructing Gendered Language; Feminist World-Making 2024
Deconstructing Gendered Language; Feminist World-Making 2024
 
Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)
Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)
Dubai Call Girls Service # +971588046679 # Call Girls Service In Dubai # (UAE)
 
Storyboard short: Ferrarius Tries to Sing
Storyboard short: Ferrarius Tries to SingStoryboard short: Ferrarius Tries to Sing
Storyboard short: Ferrarius Tries to Sing
 

2011 11-mozcamp

  • 1. PDF.JS Julian Viereck @jviereck jviereck.dev@gmail.com
  • 2.
  • 4. Bespin Firefox Skywriter DevTools Ace
  • 5. Bespin Firefox ETH Skywriter DevTools Zurich Ace
  • 6. Bespin Firefox ETH ? Skywriter PDF.JS DevTools Zurich Ace
  • 7. Overview • What is PDF.JS • How PDF is structured • Processing in PDF.JS • Images & Fonts • Infrastructure • Problems & Todos • Demo
  • 9. What is PDF.JS • building faithful & efficient PDF renderer
  • 10. What is PDF.JS • building faithful & efficient PDF renderer • HTML5 technology experiment
  • 11. What is PDF.JS • building faithful & efficient PDF renderer • HTML5 technology experiment • no native code
  • 12. What is PDF.JS • building faithful & efficient PDF renderer • HTML5 technology experiment • no native code • secure (web sandbox)
  • 13. What is PDF.JS • building faithful & efficient PDF renderer • HTML5 technology experiment • no native code • secure (web sandbox) • Mozilla Labs Project - Open Source
  • 14. Most vulnerable programs Source: http://www.csis.dk/en/csis/news/3321
  • 15. How PDF is structured PDF file
  • 16. How PDF is structured Header PDF version PDF file
  • 17. How PDF is structured Header PDF version sequence of objets Body [Objects] fonts, drawing cmds, images, words, bookmarks, form fields PDF file
  • 18. How PDF is structured Header PDF version sequence of objets Body [Objects] fonts, drawing cmds, images, words, bookmarks, form fields xRef Table mapping objID byte offset PDF file
  • 19. How PDF is structured Header PDF version sequence of objets Body [Objects] fonts, drawing cmds, images, words, bookmarks, form fields xRef Table mapping objID byte offset Trailer root objID, xRef byte offset PDF file root obj = ref to pages catalog
  • 21. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream
  • 22. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object
  • 23. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N)
  • 24. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) • page.startRendering(graphics)
  • 25. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) • page.startRendering(graphics) • read & convert all PDF cmds ➟ IR
  • 26. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) Intermediate • page.startRendering(graphics) Representation • read & convert all PDF cmds ➟ IR
  • 27. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) Intermediate • page.startRendering(graphics) Representation • read & convert all PDF cmds ➟ IR PartialEvaluator
  • 28. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) Intermediate • page.startRendering(graphics) Representation • read & convert all PDF cmds ➟ IR PartialEvaluator • load required objects (fonts, images)
  • 29. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) Intermediate • page.startRendering(graphics) Representation • read & convert all PDF cmds ➟ IR PartialEvaluator • load required objects (fonts, images) • graphics.executeIR(IR)
  • 30. Processing in PDF.JS • get plain Uint8Array via XHR2, build Stream • new PDFDoc(stream): read xRef, root object • page = PDFDoc.getPage(N) Intermediate • page.startRendering(graphics) Representation • read & convert all PDF cmds ➟ IR PartialEvaluator • load required objects (fonts, images) • graphics.executeIR(IR) CanvasGraphics
  • 32. Why IR? Partial Data Evaluator
  • 33. Why IR? Partial Data Evaluator
  • 34. Why IR? “get page 2” Partial Data Evaluator
  • 35. Why IR? “get page 2” Partial Data Evaluator builds
  • 36. Why IR? “get page 2” Partial Data Evaluator builds draw( obj#3, dict.x, dict.y )
  • 37. Why IR? “get page 2” Partial Data Evaluator builds draw( obj#3, Graphics dict.x, dict.y )
  • 38. Why IR? “get page 2” Partial Data Evaluator builds draw( obj#3, Graphics dict.x, dict.y )
  • 39. Why IR? “get page 2” Partial Data Evaluator builds draw( obj#3, Graphics dict.x, drawing cmds dict.y )
  • 40. Why IR? “get page 2” Partial Data Evaluator obj#3? builds dict.x, .y? draw( obj#3, Graphics dict.x, drawing cmds dict.y )
  • 41. Why IR? “get page 2” Partial Data Evaluator obj#3? builds dict.x, .y? draw( obj#3, Graphics dict.x, drawing cmds dict.y )
  • 42. Why IR? “get page 2” Partial Data Evaluator obj#3? obj#3 = ”foo” builds dict.x, .y? x = 20 y = 30 draw( obj#3, Graphics dict.x, drawing cmds dict.y )
  • 43. Why IR? “get page 2” Partial Data Evaluator obj#3? obj#3 = ”foo” builds dict.x, .y? x = 20 y = 30 draw( obj#3, Graphics dict.x, drawing cmds dict.y )
  • 44. Why IR? “get page 2” Partial Data Evaluator obj#3? obj#3 = ”foo” builds dict.x, .y? x = 20 y = 30 draw( obj#3, Graphics dict.x, drawing cmds dict.y ) draw on canvas
  • 46. Problem Processing • Extracting data slow (compressed)
  • 47. Problem Processing • Extracting data slow (compressed) • Transform data (images) slow
  • 48. Problem Processing • Extracting data slow (compressed) • Transform data (images) slow • Sometimes a lot of objects on page
  • 49. Problem Processing • Extracting data slow (compressed) • Transform data (images) slow • Sometimes a lot of objects on page ➡ Freezes UI
  • 50. Problem Processing • Extracting data slow (compressed) • Transform data (images) slow • Sometimes a lot of objects on page ➡ Freezes UI ➡ Use WebWorker
  • 51. Problem Processing • Extracting data slow (compressed) • Transform data (images) slow • Sometimes a lot of objects on page ➡ Freezes UI ➡ Use WebWorker ➡ :( no direct memory access, postMessage
  • 52. Main Web Thread Worker Data
  • 53. Main Web Thread Worker Partial Data Evaluator
  • 54. Main Web Thread Worker data Partial Data “get page 2” Evaluator
  • 55. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator
  • 56. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds
  • 57. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( obj#3, dict.x, dict.y )
  • 58. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( obj#3, dict.x, dict.y )
  • 59. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( draw( obj#3, “foo”, dict.x, 20, dict.y 30 ) )
  • 60. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( draw( IR obj#3, “foo”, dict.x, 20, dict.y 30 ) )
  • 61. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( draw( IR obj#3, “foo”, Graphics dict.x, 20, dict.y 30 ) )
  • 62. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( draw( IR obj#3, “foo”, Graphics dict.x, IR cmds 20, dict.y 30 ) )
  • 63. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( draw( IR obj#3, “foo”, Graphics dict.x, IR cmds 20, dict.y 30 ) )
  • 64. Main Web Thread Worker data Partial Data Data “get page 2” Evaluator builds draw( draw( IR obj#3, “foo”, Graphics dict.x, IR cmds 20, dict.y 30 ) draw on ) canvas
  • 65.
  • 66. 5 0 obj << /Length 8 0 R >> stream /GS1 gs /F0 12 Tf BT 100 700 Td (Hello World!) Tj ET 50 600 m 400 600 l S endstream endobj
  • 67. 5 0 obj PartialEvaluator << /Length 8 0 R >> stream /GS1 gs /F0 12 Tf BT 100 700 Td (Hello World!) Tj ET 50 600 m 400 600 l S endstream endobj
  • 68. 5 0 obj xRef, catalog, + resources PartialEvaluator << /Length 8 0 R >> stream /GS1 gs /F0 12 Tf BT 100 700 Td (Hello World!) Tj ET 50 600 m 400 600 l S endstream endobj
  • 69. 5 0 obj xRef, catalog, + resources PartialEvaluator << /Length 8 0 R >> stream /GS1 gs /F0 12 Tf BT 100 700 Td (Hello World!) Tj ET 50 600 m 400 600 l S endstream endobj Graphics
  • 70. 5 0 obj xRef, catalog, + resources PartialEvaluator << /Length 8 0 R >> setGState: [ LW: 10 ] stream dependency: [ font0 ] /GS1 gs setFont: font0, 12 /F0 12 Tf beginText BT moveText: 100, 700 100 700 Td showText: “Hello World!” (Hello World!) Tj endText ET moveTo: 50, 600 50 600 m lineTo: 400, 600 400 600 l stroke S endstream endobj Graphics
  • 71. 5 0 obj xRef, catalog, + resources PartialEvaluator << /Length 8 0 R >> setGState: [ LW: 10 ] stream dependency: [ font0 ] /GS1 gs setFont: font0, 12 /F0 12 Tf beginText BT moveText: 100, 700 100 700 Td showText: “Hello World!” (Hello World!) Tj endText ET moveTo: 50, 600 50 600 m lineTo: 400, 600 400 600 l stroke S endstream endobj Graphics
  • 72. 5 0 obj xRef, catalog, IR + resources PartialEvaluator << /Length 8 0 R >> setGState: [ LW: 10 ] stream dependency: [ font0 ] /GS1 gs setFont: font0, 12 /F0 12 Tf beginText BT moveText: 100, 700 100 700 Td showText: “Hello World!” (Hello World!) Tj endText ET moveTo: 50, 600 50 600 m lineTo: 400, 600 400 600 l stroke S endstream endobj Graphics
  • 75. Images • JPEG streams: • DOMImg.src = 'data:image/jpeg;base64,' + window.btoa(bytesToString(bytes));
  • 76. Images • JPEG streams: • DOMImg.src = 'data:image/jpeg;base64,' + window.btoa(bytesToString(bytes)); • If not JPEG stream:
  • 77. Images • JPEG streams: • DOMImg.src = 'data:image/jpeg;base64,' + window.btoa(bytesToString(bytes)); • If not JPEG stream: • read bytes, convert to colorspace
  • 78. Images • JPEG streams: • DOMImg.src = 'data:image/jpeg;base64,' + window.btoa(bytesToString(bytes)); • If not JPEG stream: • read bytes, convert to colorspace • imgData = canvas.getImageData()
  • 79. Images • JPEG streams: • DOMImg.src = 'data:image/jpeg;base64,' + window.btoa(bytesToString(bytes)); • If not JPEG stream: • read bytes, convert to colorspace • imgData = canvas.getImageData() • fillWithPixelData(bytes, imgData)
  • 80. Images • JPEG streams: • DOMImg.src = 'data:image/jpeg;base64,' + window.btoa(bytesToString(bytes)); • If not JPEG stream: • read bytes, convert to colorspace • imgData = canvas.getImageData() • fillWithPixelData(bytes, imgData) • canvas.putImageData(imgData)
  • 82. Jpeg, but... • no natives support for CMYK Jpeg
  • 83. Jpeg, but... • no natives support for CMYK Jpeg ➡ use JS implementation
  • 84. Jpeg, but... • no natives support for CMYK Jpeg ➡ use JS implementation • no native support for Jpeg 2000
  • 85. Jpeg, but... • no natives support for CMYK Jpeg ➡ use JS implementation • no native support for Jpeg 2000 ➡ use EMScripten: C-Lib ➟ JS
  • 86. Jpeg, but... • no natives support for CMYK Jpeg ➡ use JS implementation • no native support for Jpeg 2000 ➡ use EMScripten: C-Lib ➟ JS ‣ works, but not that performant
  • 87. Fonts
  • 88. Fonts • There are lots of different font formats!
  • 89. Fonts • There are lots of different font formats! • fonts are converted to OpenType
  • 90. Fonts • There are lots of different font formats! • fonts are converted to OpenType • use CSS: @font-face { font-family:'font0'; src:url(data:font/opentype;base64, ...)
  • 91. Fonts • There are lots of different font formats! • fonts are converted to OpenType • use CSS: @font-face { font-family:'font0'; src:url(data:font/opentype;base64, ...) • some fonts can’t be converted :(
  • 92. Fonts • There are lots of different font formats! • fonts are converted to OpenType • use CSS: @font-face { font-family:'font0'; src:url(data:font/opentype;base64, ...) • some fonts can’t be converted :( • paint them
  • 93. Fonts Type I convert to Type II Type II “use directly” Type III paint ourself CDI convert to Type II
  • 94. Fonts Type I convert to Type II still need Type II “use directly” to repair fonts! Type III paint ourself CDI convert to Type II
  • 97. Infrastructure • Using GitHub • Issue Tracker
  • 98. Infrastructure • Using GitHub • Issue Tracker • Pull Requests
  • 99. Infrastructure • Using GitHub • Issue Tracker • Pull Requests • Wiki
  • 100. Infrastructure • Using GitHub • Issue Tracker • Pull Requests • Wiki • Update gh-pages on every push
  • 101. Infrastructure • Using GitHub • Issue Tracker • Pull Requests • Wiki • Update gh-pages on every push • Testing:
  • 102. Infrastructure • Using GitHub • Issue Tracker • Pull Requests • Wiki • Update gh-pages on every push • Testing: • In Pull Request: “@pdfjsbot test”
  • 103. Infrastructure • Using GitHub • Issue Tracker • Pull Requests • Wiki • Update gh-pages on every push • Testing: • In Pull Request: “@pdfjsbot test” • Runs tests on AC2 instance
  • 104.
  • 105.
  • 108. Infrastructure • AreWePdfYet? • Take top100 PDFs from Google
  • 109. Infrastructure • AreWePdfYet? • Take top100 PDFs from Google • render the first 5 pages each
  • 110. Infrastructure • AreWePdfYet? • Take top100 PDFs from Google • render the first 5 pages each • compare to Preview
  • 111. Infrastructure • AreWePdfYet? • Take top100 PDFs from Google • render the first 5 pages each • compare to Preview • http://people.mozilla.com/~bdahl/ corpusreport/test/ref/
  • 112. Todo = Help :)
  • 114. 'Read-Only' Memory Web Worker
  • 115. Faster Canvas Rendering
  • 126. More Parts Of Spec
  • 128. Pref & Memory Analysis
  • 131. More Testing • use PDF.JS extension! • http://mozilla.github.com/pdf.js/extensions/ firefox/pdf.js.xpi • report broken PDFs! • help us categorize issues
  • 133. Demo
  • 134. Github: Readme https://github.com/mozilla/pdf.js Issues Wiki Twitter: @pdfjs Mailing List: https://groups.google.com/group/ mozilla.dev.pdf-js/topics IRC: irc.mozilla.org #pdfjs Engineering Weekly Call: Thursday - 10:00am PDT, 17:00 UTC
  • 135. Q &A