diff --git a/services/web/public/coffee/base.coffee b/services/web/public/coffee/base.coffee
index 9e1e59b49a..b050b45802 100644
--- a/services/web/public/coffee/base.coffee
+++ b/services/web/public/coffee/base.coffee
@@ -2,13 +2,6 @@ define [
"libs"
"modules/recursionHelper"
"utils/underscore"
- # TODo move these into a separate definition
- "ide/pdfng/directives/pdfViewer"
- "ide/pdfng/directives/pdfPage"
- "ide/pdfng/directives/pdfRenderer"
- "ide/pdfng/directives/pdfTextLayer"
- "ide/pdfng/directives/pdfAnnotations"
- "ide/pdfng/directives/pdfHighlights"
], () ->
App = angular.module("SharelatexApp", [
"ui.bootstrap"
@@ -18,7 +11,6 @@ define [
"underscore"
"ngSanitize"
"ipCookie"
- "pdfViewerApp"
])
return App
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfAnnotations.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfAnnotations.coffee
index a2d9d1751a..99c37aca09 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfAnnotations.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfAnnotations.coffee
@@ -1,42 +1,44 @@
-app = angular.module 'pdfAnnotations', []
+define [
+ "base"
+], (App) ->
+ # App = angular.module 'pdfAnnotations', []
+ App.factory 'pdfAnnotations', [ () ->
+ class pdfAnnotations
-app.factory 'pdfAnnotations', [ () ->
- class pdfAnnotations
+ @EXTERNAL_LINK_TARGET = "_blank";
- @EXTERNAL_LINK_TARGET = "_blank";
+ constructor: (options) ->
+ @annotationsLayerDiv = options.annotations;
+ @viewport = options.viewport
+ @navigateFn = options.navigateFn
- constructor: (options) ->
- @annotationsLayerDiv = options.annotations;
- @viewport = options.viewport
- @navigateFn = options.navigateFn
+ setAnnotations: (annotations) ->
+ for annotation in annotations
+ switch annotation.subtype
+ when 'Link' then @addLink(annotation);
+ when 'Text' then continue
- setAnnotations: (annotations) ->
- for annotation in annotations
- switch annotation.subtype
- when 'Link' then @addLink(annotation);
- when 'Text' then continue
+ addLink: (link) ->
+ element = @buildLinkElementFromRect(link.rect);
+ @setLinkTarget(element, link);
+ @annotationsLayerDiv.appendChild(element);
- addLink: (link) ->
- element = @buildLinkElementFromRect(link.rect);
- @setLinkTarget(element, link);
- @annotationsLayerDiv.appendChild(element);
+ buildLinkElementFromRect: (rect) ->
+ rect = @viewport.convertToViewportRectangle(rect);
+ rect = PDFJS.Util.normalizeRect(rect);
+ element = document.createElement("a");
+ element.style.left = Math.floor(rect[0]) + 'px';
+ element.style.top = Math.floor(rect[1]) + 'px';
+ element.style.width = Math.ceil(rect[2] - rect[0]) + 'px';
+ element.style.height = Math.ceil(rect[3] - rect[1]) + 'px';
+ element
- buildLinkElementFromRect: (rect) ->
- rect = @viewport.convertToViewportRectangle(rect);
- rect = PDFJS.Util.normalizeRect(rect);
- element = document.createElement("a");
- element.style.left = Math.floor(rect[0]) + 'px';
- element.style.top = Math.floor(rect[1]) + 'px';
- element.style.width = Math.ceil(rect[2] - rect[0]) + 'px';
- element.style.height = Math.ceil(rect[3] - rect[1]) + 'px';
- element
-
- setLinkTarget: (element, link) ->
- if link.url
- element.href = link.url;
- element.target = @EXTERNAL_LINK_TARGET;
- else if (link.dest)
- element.href = "#" + link.dest;
- element.onclick = (e) =>
- @navigateFn link
-]
+ setLinkTarget: (element, link) ->
+ if link.url
+ element.href = link.url;
+ element.target = @EXTERNAL_LINK_TARGET;
+ else if (link.dest)
+ element.href = "#" + link.dest;
+ element.onclick = (e) =>
+ @navigateFn link
+ ]
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfHighlights.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfHighlights.coffee
index 2c93e8bef5..fc2b72bd79 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfHighlights.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfHighlights.coffee
@@ -1,26 +1,29 @@
-app = angular.module 'pdfHighlights', []
+define [
+ "base"
+], (App) ->
+ #app = angular.module 'pdfHighlights', []
-app.factory 'pdfHighlights', [ () ->
- class pdfHighlights
+ App.factory 'pdfHighlights', [ () ->
+ class pdfHighlights
- constructor: (options) ->
- @highlightsLayerDiv = options.highlights[0]
- @highlightElements = []
+ constructor: (options) ->
+ @highlightsLayerDiv = options.highlights[0]
+ @highlightElements = []
- addHighlight: (viewport, left, top, width, height) ->
- rect = viewport.convertToViewportRectangle([left, top, left + width, top + height])
- rect = PDFJS.Util.normalizeRect(rect)
- element = document.createElement("div")
- element.style.left = Math.floor(rect[0]) + 'px'
- element.style.top = Math.floor(rect[1]) + 'px'
- element.style.width = Math.ceil(rect[2] - rect[0]) + 'px'
- element.style.height = Math.ceil(rect[3] - rect[1]) + 'px'
- @highlightElements.push(element)
- @highlightsLayerDiv.appendChild(element)
- element
+ addHighlight: (viewport, left, top, width, height) ->
+ rect = viewport.convertToViewportRectangle([left, top, left + width, top + height])
+ rect = PDFJS.Util.normalizeRect(rect)
+ element = document.createElement("div")
+ element.style.left = Math.floor(rect[0]) + 'px'
+ element.style.top = Math.floor(rect[1]) + 'px'
+ element.style.width = Math.ceil(rect[2] - rect[0]) + 'px'
+ element.style.height = Math.ceil(rect[3] - rect[1]) + 'px'
+ @highlightElements.push(element)
+ @highlightsLayerDiv.appendChild(element)
+ element
- clearHighlights: () ->
- for h in @highlightElements
- h.remove()
- @highlightElements = []
-]
+ clearHighlights: () ->
+ for h in @highlightElements
+ h.remove()
+ @highlightElements = []
+ ]
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfJs.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfJs.coffee
index 41e91fbd66..8deba7548a 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfJs.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfJs.coffee
@@ -1,24 +1,12 @@
define [
"base"
- "ide/pdfng/directives/pdfTextLayer"
- "ide/pdfng/directives/pdfAnnotations"
- "ide/pdfng/directives/pdfHighlights"
- "ide/pdfng/directives/pdfRenderer"
- "ide/pdfng/directives/pdfPage"
"ide/pdfng/directives/pdfViewer"
- "libs/pdfjs-1.0.712/pdf"
"text!libs/pdfListView/TextLayer.css"
"text!libs/pdfListView/AnnotationsLayer.css"
"text!libs/pdfListView/HighlightsLayer.css"
], (
App
pdfViewer
- pdfPage
- pdfRenderer
- pdfTextLayer
- pdfAnnotations
- pdfHighlights
- pdf
textLayerCss
annotationsLayerCss
highlightsLayerCss
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfPage.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfPage.coffee
index fcfad6b9c0..f28f09d2dc 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfPage.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfPage.coffee
@@ -1,104 +1,107 @@
-app = angular.module 'pdfPage', ['pdfHighlights']
+define [
+ "base"
+], (App) ->
+ # App = angular.module 'pdfPage', ['pdfHighlights']
-app.directive 'pdfPage', ['$timeout', 'pdfHighlights', ($timeout, pdfHighlights) ->
- {
- require: '^pdfViewer',
- template: '''
-
- '''
- link: (scope, element, attrs, ctrl) ->
- canvasElement = $(element).find('.pdf-canvas')
- textElement = $(element).find('.text-layer')
- annotationsElement = $(element).find('.annotations-layer')
- highlightsElement = $(element).find('.highlights-layer')
+ App.directive 'pdfPage', ['$timeout', 'pdfHighlights', ($timeout, pdfHighlights) ->
+ {
+ require: '^pdfViewer',
+ template: '''
+
+ '''
+ link: (scope, element, attrs, ctrl) ->
+ canvasElement = $(element).find('.pdf-canvas')
+ textElement = $(element).find('.text-layer')
+ annotationsElement = $(element).find('.annotations-layer')
+ highlightsElement = $(element).find('.highlights-layer')
- updatePageSize = (size) ->
- element.height(Math.floor(size[0]))
- element.width(Math.floor(size[1]))
- scope.page.sized = true
+ updatePageSize = (size) ->
+ element.height(Math.floor(size[0]))
+ element.width(Math.floor(size[1]))
+ scope.page.sized = true
- isVisible = (containerSize) ->
- elemTop = element.offset().top - containerSize[2]
- elemBottom = elemTop + element.innerHeight()
- visible = (elemTop < containerSize[1] and elemBottom > 0)
- scope.page.visible = visible
- scope.page.elemTop = elemTop
- scope.page.elemBottom = elemBottom
- return visible
+ isVisible = (containerSize) ->
+ elemTop = element.offset().top - containerSize[2]
+ elemBottom = elemTop + element.innerHeight()
+ visible = (elemTop < containerSize[1] and elemBottom > 0)
+ scope.page.visible = visible
+ scope.page.elemTop = elemTop
+ scope.page.elemBottom = elemBottom
+ return visible
- renderPage = () ->
- scope.document.renderPage {
- canvas: canvasElement,
- text: textElement
- annotations: annotationsElement
+ renderPage = () ->
+ scope.document.renderPage {
+ canvas: canvasElement,
+ text: textElement
+ annotations: annotationsElement
+ highlights: highlightsElement
+ }, scope.page.pageNum
+
+ pausePage = () ->
+ scope.document.pause {
+ canvas: canvasElement,
+ text: textElement
+ }, scope.page.pageNum
+
+ # keep track of our page element, so we can access it in the
+ # parent with scope.pages[i].element
+ scope.page.element = element
+
+ if (!scope.page.sized && scope.defaultPageSize)
+ updatePageSize scope.defaultPageSize
+
+ if scope.page.current
+ console.log 'we must scroll to this page', scope.page.pageNum,
+ 'at position', scope.page.position
+ renderPage()
+ # this is the current page, we want to scroll it into view
+ scope.document.getPdfViewport(scope.page.pageNum).then (viewport) ->
+ scope.page.viewport = viewport
+ ctrl.setPdfPosition(scope.page, scope.page.position)
+
+ scope.$watch 'defaultPageSize', (defaultPageSize) ->
+ return unless defaultPageSize?
+ updatePageSize defaultPageSize
+
+ watchHandle = scope.$watch 'containerSize', (containerSize, oldVal) ->
+ return unless containerSize?
+ return unless scope.page.sized
+ oldVisible = scope.page.visible
+ newVisible = isVisible containerSize
+ scope.page.visible = newVisible
+ if newVisible && !oldVisible
+ renderPage()
+ # TODO deregister this listener after the page is rendered
+ #watchHandle()
+ else if !newVisible && oldVisible
+ pausePage()
+
+ highlightsLayer = new pdfHighlights({
highlights: highlightsElement
- }, scope.page.pageNum
+ })
- pausePage = () ->
- scope.document.pause {
- canvas: canvasElement,
- text: textElement
- }, scope.page.pageNum
-
- # keep track of our page element, so we can access it in the
- # parent with scope.pages[i].element
- scope.page.element = element
-
- if (!scope.page.sized && scope.defaultPageSize)
- updatePageSize scope.defaultPageSize
-
- if scope.page.current
- console.log 'we must scroll to this page', scope.page.pageNum,
- 'at position', scope.page.position
- renderPage()
- # this is the current page, we want to scroll it into view
+ scope.$watch 'highlights', (highlights, oldVal) ->
+ return unless highlights?
+ return unless highlights.length > 0
+ console.log 'got highlight watch in pdfPage', scope.page
+ pageHighlights = (h for h in highlights when h.page == scope.page.pageNum)
+ return unless pageHighlights.length
scope.document.getPdfViewport(scope.page.pageNum).then (viewport) ->
- scope.page.viewport = viewport
- ctrl.setPdfPosition(scope.page, scope.page.position)
+ for hl in pageHighlights
+ console.log 'adding highlight', h, viewport
+ top = viewport.viewBox[3] - hl.v
+ highlightsLayer.addHighlight viewport, hl.h, top, hl.width, hl.height
+ $timeout () ->
+ highlightsLayer.clearHighlights()
+ , 1000
- scope.$watch 'defaultPageSize', (defaultPageSize) ->
- return unless defaultPageSize?
- updatePageSize defaultPageSize
+ scope.$on "$destroy", () ->
+ console.log 'in destroy handler, TODO need to clean up timeout/highlights'
- watchHandle = scope.$watch 'containerSize', (containerSize, oldVal) ->
- return unless containerSize?
- return unless scope.page.sized
- oldVisible = scope.page.visible
- newVisible = isVisible containerSize
- scope.page.visible = newVisible
- if newVisible && !oldVisible
- renderPage()
- # TODO deregister this listener after the page is rendered
- #watchHandle()
- else if !newVisible && oldVisible
- pausePage()
-
- highlightsLayer = new pdfHighlights({
- highlights: highlightsElement
- })
-
- scope.$watch 'highlights', (highlights, oldVal) ->
- return unless highlights?
- return unless highlights.length > 0
- console.log 'got highlight watch in pdfPage', scope.page
- pageHighlights = (h for h in highlights when h.page == scope.page.pageNum)
- return unless pageHighlights.length
- scope.document.getPdfViewport(scope.page.pageNum).then (viewport) ->
- for hl in pageHighlights
- console.log 'adding highlight', h, viewport
- top = viewport.viewBox[3] - hl.v
- highlightsLayer.addHighlight viewport, hl.h, top, hl.width, hl.height
- $timeout () ->
- highlightsLayer.clearHighlights()
- , 1000
-
- scope.$on "$destroy", () ->
- console.log 'in destroy handler, TODO need to clean up timeout/highlights'
-
- }
-]
+ }
+ ]
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfRenderer.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfRenderer.coffee
index 8957fd83c9..eaad381577 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfRenderer.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfRenderer.coffee
@@ -1,185 +1,188 @@
-app = angular.module 'PDFRenderer', ['pdfAnnotations', 'pdfTextLayer']
+define [
+ "base"
+], (App) ->
+ # App = angular.module 'PDFRenderer', ['pdfAnnotations', 'pdfTextLayer']
-console.log 'hello from Renderer'
+ console.log 'hello from Renderer'
-app.factory 'PDFRenderer', ['$q', '$timeout', 'pdfAnnotations', 'pdfTextLayer', ($q, $timeout, pdfAnnotations, pdfTextLayer) ->
+ App.factory 'PDFRenderer', ['$q', '$timeout', 'pdfAnnotations', 'pdfTextLayer', ($q, $timeout, pdfAnnotations, pdfTextLayer) ->
- class PDFRenderer
- @JOB_QUEUE_INTERVAL: 100
+ class PDFRenderer
+ @JOB_QUEUE_INTERVAL: 100
- constructor: (@url, @options) ->
- @scale = @options.scale || 1
- @document = $q.when(PDFJS.getDocument @url)
- @navigateFn = @options.navigateFn
- @resetState()
+ constructor: (@url, @options) ->
+ @scale = @options.scale || 1
+ @document = $q.when(PDFJS.getDocument @url)
+ @navigateFn = @options.navigateFn
+ @resetState()
- resetState: () ->
- console.log 'reseting renderer state'
- @page = []
- @complete = []
- @timeout = []
- @renderTask = []
- @renderQueue = []
- @jobs = 0
+ resetState: () ->
+ console.log 'reseting renderer state'
+ @page = []
+ @complete = []
+ @timeout = []
+ @renderTask = []
+ @renderQueue = []
+ @jobs = 0
- getNumPages: () ->
- @document.then (pdfDocument) ->
- pdfDocument.numPages
+ getNumPages: () ->
+ @document.then (pdfDocument) ->
+ pdfDocument.numPages
- getPage: (pageNum) ->
- # with promise caching
- return @page[pageNum] if @page[pageNum]?
- @page[pageNum] = @document.then (pdfDocument) ->
- pdfDocument.getPage(pageNum)
+ getPage: (pageNum) ->
+ # with promise caching
+ return @page[pageNum] if @page[pageNum]?
+ @page[pageNum] = @document.then (pdfDocument) ->
+ pdfDocument.getPage(pageNum)
- getPdfViewport: (pageNum, scale) ->
- scale ?= @scale
- @document.then (pdfDocument) ->
- pdfDocument.getPage(pageNum).then (page) ->
- viewport = page.getViewport scale
+ getPdfViewport: (pageNum, scale) ->
+ scale ?= @scale
+ @document.then (pdfDocument) ->
+ pdfDocument.getPage(pageNum).then (page) ->
+ viewport = page.getViewport scale
- getDestinations: () ->
- @document.then (pdfDocument) ->
- pdfDocument.getDestinations()
+ getDestinations: () ->
+ @document.then (pdfDocument) ->
+ pdfDocument.getDestinations()
- getPageIndex: (ref) ->
- @document.then (pdfDocument) ->
- pdfDocument.getPageIndex(ref).then (idx) ->
- idx
+ getPageIndex: (ref) ->
+ @document.then (pdfDocument) ->
+ pdfDocument.getPageIndex(ref).then (idx) ->
+ idx
- getScale: () ->
- @scale
+ getScale: () ->
+ @scale
- setScale: (@scale) ->
- @resetState()
+ setScale: (@scale) ->
+ @resetState()
- pause: (element, pagenum) ->
- return if @complete[pagenum]
- @renderQueue = @renderQueue.filter (q) ->
- q.pagenum != pagenum
- @stopSpinner (element.canvas)
+ pause: (element, pagenum) ->
+ return if @complete[pagenum]
+ @renderQueue = @renderQueue.filter (q) ->
+ q.pagenum != pagenum
+ @stopSpinner (element.canvas)
- triggerRenderQueue: () ->
- $timeout () =>
- @processRenderQueue()
- , @JOB_QUEUE_INTERVAL
+ triggerRenderQueue: () ->
+ $timeout () =>
+ @processRenderQueue()
+ , @JOB_QUEUE_INTERVAL
- removeCompletedJob: (pagenum) ->
- # may need to clean up deferred object here
- delete @renderTask[pagenum]
- @jobs = @jobs - 1
- @triggerRenderQueue()
+ removeCompletedJob: (pagenum) ->
+ # may need to clean up deferred object here
+ delete @renderTask[pagenum]
+ @jobs = @jobs - 1
+ @triggerRenderQueue()
- renderPage: (element, pagenum) ->
- viewport = $q.defer()
- current = {
- 'element': element
- 'pagenum': pagenum
- }
- @renderQueue.push(current)
- @triggerRenderQueue()
+ renderPage: (element, pagenum) ->
+ viewport = $q.defer()
+ current = {
+ 'element': element
+ 'pagenum': pagenum
+ }
+ @renderQueue.push(current)
+ @triggerRenderQueue()
- processRenderQueue: () ->
- return if @jobs > 0
- current = @renderQueue.pop()
- return unless current?
- [element, pagenum] = [current.element, current.pagenum]
- return if @complete[pagenum]
- return if @renderTask[pagenum]
- @jobs = @jobs + 1
+ processRenderQueue: () ->
+ return if @jobs > 0
+ current = @renderQueue.pop()
+ return unless current?
+ [element, pagenum] = [current.element, current.pagenum]
+ return if @complete[pagenum]
+ return if @renderTask[pagenum]
+ @jobs = @jobs + 1
- @addSpinner(element.canvas)
+ @addSpinner(element.canvas)
- pageLoad = @getPage(pagenum)
+ pageLoad = @getPage(pagenum)
- @renderTask[pagenum] = pageLoad.then (pageObject) =>
- @doRender element, pagenum, pageObject
+ @renderTask[pagenum] = pageLoad.then (pageObject) =>
+ @doRender element, pagenum, pageObject
- @renderTask[pagenum].then () =>
- # complete
- @complete[pagenum] = true
- @removeCompletedJob pagenum
- , () =>
- # rejected
- @removeCompletedJob pagenum
+ @renderTask[pagenum].then () =>
+ # complete
+ @complete[pagenum] = true
+ @removeCompletedJob pagenum
+ , () =>
+ # rejected
+ @removeCompletedJob pagenum
- doRender: (element, pagenum, page) ->
- self = this
- scale = @scale
+ doRender: (element, pagenum, page) ->
+ self = this
+ scale = @scale
- if (not scale?)
- console.log 'scale is undefined, returning'
- return
+ if (not scale?)
+ console.log 'scale is undefined, returning'
+ return
- canvas = $('')
+ canvas = $('')
- viewport = page.getViewport (scale)
+ viewport = page.getViewport (scale)
- devicePixelRatio = window.devicePixelRatio || 1
+ devicePixelRatio = window.devicePixelRatio || 1
- ctx = canvas[0].getContext '2d'
- backingStoreRatio = ctx.webkitBackingStorePixelRatio ||
- ctx.mozBackingStorePixelRatio ||
- ctx.msBackingStorePixelRatio ||
- ctx.oBackingStorePixelRatio ||
- ctx.backingStorePixelRatio || 1
- pixelRatio = devicePixelRatio / backingStoreRatio
+ ctx = canvas[0].getContext '2d'
+ backingStoreRatio = ctx.webkitBackingStorePixelRatio ||
+ ctx.mozBackingStorePixelRatio ||
+ ctx.msBackingStorePixelRatio ||
+ ctx.oBackingStorePixelRatio ||
+ ctx.backingStorePixelRatio || 1
+ pixelRatio = devicePixelRatio / backingStoreRatio
- scaledWidth = (Math.floor(viewport.width) * pixelRatio) | 0
- scaledHeight = (Math.floor(viewport.height) * pixelRatio) | 0
+ scaledWidth = (Math.floor(viewport.width) * pixelRatio) | 0
+ scaledHeight = (Math.floor(viewport.height) * pixelRatio) | 0
- newWidth = Math.floor(viewport.width)
- newHeight = Math.floor(viewport.height)
+ newWidth = Math.floor(viewport.width)
+ newHeight = Math.floor(viewport.height)
- canvas[0].height = scaledHeight
- canvas[0].width = scaledWidth
+ canvas[0].height = scaledHeight
+ canvas[0].width = scaledWidth
- canvas.height(newHeight + 'px')
- canvas.width(newWidth + 'px')
+ canvas.height(newHeight + 'px')
+ canvas.width(newWidth + 'px')
- element.canvas[0].height = newHeight
- element.canvas[0].width = newWidth
+ element.canvas[0].height = newHeight
+ element.canvas[0].width = newWidth
- if pixelRatio != 1
- ctx.scale(pixelRatio, pixelRatio)
+ if pixelRatio != 1
+ ctx.scale(pixelRatio, pixelRatio)
- textLayer = new pdfTextLayer({
- textLayerDiv: element.text[0]
- viewport: viewport
- })
- page.getTextContent().then (textContent) ->
- console.log 'text content is', textContent
- window.RENDER_DELAY = 0
- textLayer.setTextContent textContent
+ textLayer = new pdfTextLayer({
+ textLayerDiv: element.text[0]
+ viewport: viewport
+ })
+ page.getTextContent().then (textContent) ->
+ console.log 'text content is', textContent
+ window.RENDER_DELAY = 0
+ textLayer.setTextContent textContent
- annotationsLayer = new pdfAnnotations({
- annotations: element.annotations[0]
- viewport: viewport
- navigateFn: @navigateFn
- })
- page.getAnnotations().then (annotations) ->
- console.log 'annotations are', annotations
- window.RENDER_DELAY = 0
- annotationsLayer.setAnnotations annotations
+ annotationsLayer = new pdfAnnotations({
+ annotations: element.annotations[0]
+ viewport: viewport
+ navigateFn: @navigateFn
+ })
+ page.getAnnotations().then (annotations) ->
+ console.log 'annotations are', annotations
+ window.RENDER_DELAY = 0
+ annotationsLayer.setAnnotations annotations
- return @renderTask = page.render {
- canvasContext: ctx
- viewport: viewport
- }
- .then () ->
- element.canvas.replaceWith(canvas)
- canvas.removeClass('pdf-canvas-new')
+ return @renderTask = page.render {
+ canvasContext: ctx
+ viewport: viewport
+ }
+ .then () ->
+ element.canvas.replaceWith(canvas)
+ canvas.removeClass('pdf-canvas-new')
- addSpinner: (element) ->
- element.css({position: 'relative'})
- h = element.parent().height()
- w = element.parent().width()
- size = Math.floor(0.5 * Math.min(h, w))
- spinner = $('
')
- spinner.css({'font-size' : size + 'px'})
- element.append(spinner)
+ addSpinner: (element) ->
+ element.css({position: 'relative'})
+ h = element.parent().height()
+ w = element.parent().width()
+ size = Math.floor(0.5 * Math.min(h, w))
+ spinner = $('
')
+ spinner.css({'font-size' : size + 'px'})
+ element.append(spinner)
- stopSpinner: (element) ->
- element.find('.fa-spin').removeClass('fa-spin')
+ stopSpinner: (element) ->
+ element.find('.fa-spin').removeClass('fa-spin')
- ]
+ ]
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfTextLayer.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfTextLayer.coffee
index 8bbeffa5fd..f863d6a2b2 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfTextLayer.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfTextLayer.coffee
@@ -1,207 +1,210 @@
-app = angular.module 'pdfTextLayer', []
+define [
+ "base"
+], (App) ->
+ # App = angular.module 'pdfTextLayer', []
-app.factory 'pdfTextLayer', [ () ->
+ App.factory 'pdfTextLayer', [ () ->
-# TRANSLATED FROM pdf.js-1.0.712
-# pdf.js-1.0.712/web/ui_utils.js
-# pdf.js-1.0.712/web/text_layer_builder.js
+ # TRANSLATED FROM pdf.js-1.0.712
+ # pdf.js-1.0.712/web/ui_utils.js
+ # pdf.js-1.0.712/web/text_layer_builder.js
-# -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+ # -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
-# Copyright 2012 Mozilla Foundation
-# *
-# * Licensed under the Apache License, Version 2.0 (the "License");
-# * you may not use this file except in compliance with the License.
-# * You may obtain a copy of the License at
-# *
-# * http://www.apache.org/licenses/LICENSE-2.0
-# *
-# * Unless required by applicable law or agreed to in writing, software
-# * distributed under the License is distributed on an "AS IS" BASIS,
-# * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# * See the License for the specific language governing permissions and
-# * limitations under the License.
-#
+ # Copyright 2012 Mozilla Foundation
+ # *
+ # * Licensed under the Apache License, Version 2.0 (the "License");
+ # * you may not use this file except in compliance with the License.
+ # * You may obtain a copy of the License at
+ # *
+ # * http://www.apache.org/licenses/LICENSE-2.0
+ # *
+ # * Unless required by applicable law or agreed to in writing, software
+ # * distributed under the License is distributed on an "AS IS" BASIS,
+ # * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ # * See the License for the specific language governing permissions and
+ # * limitations under the License.
+ #
-# globals CustomStyle, scrollIntoView, PDFJS
-# ms
+ # globals CustomStyle, scrollIntoView, PDFJS
+ # ms
-# optimised CSS custom property getter/setter
+ # optimised CSS custom property getter/setter
- CustomStyle = (CustomStyleClosure = ->
+ CustomStyle = (CustomStyleClosure = ->
- # As noted on: http://www.zachstronaut.com/posts/2009/02/17/
- # animate-css-transforms-firefox-webkit.html
- # in some versions of IE9 it is critical that ms appear in this list
- # before Moz
- CustomStyle = ->
- prefixes = [
- 'ms'
- 'Moz'
- 'Webkit'
- 'O'
- ]
- _cache = {}
- CustomStyle.getProp = get = (propName, element) ->
+ # As noted on: http://www.zachstronaut.com/posts/2009/02/17/
+ # animate-css-transforms-firefox-webkit.html
+ # in some versions of IE9 it is critical that ms appear in this list
+ # before Moz
+ CustomStyle = ->
+ prefixes = [
+ 'ms'
+ 'Moz'
+ 'Webkit'
+ 'O'
+ ]
+ _cache = {}
+ CustomStyle.getProp = get = (propName, element) ->
- # check cache only when no element is given
- return _cache[propName] if arguments.length is 1 and typeof _cache[propName] is 'string'
- element = element or document.documentElement
- style = element.style
- prefixed = undefined
- uPropName = undefined
+ # check cache only when no element is given
+ return _cache[propName] if arguments.length is 1 and typeof _cache[propName] is 'string'
+ element = element or document.documentElement
+ style = element.style
+ prefixed = undefined
+ uPropName = undefined
- # test standard property first
- return (_cache[propName] = propName) if typeof style[propName] is 'string'
+ # test standard property first
+ return (_cache[propName] = propName) if typeof style[propName] is 'string'
- # capitalize
- uPropName = propName.charAt(0).toUpperCase() + propName.slice(1)
+ # capitalize
+ uPropName = propName.charAt(0).toUpperCase() + propName.slice(1)
- # test vendor specific properties
- i = 0
- l = prefixes.length
+ # test vendor specific properties
+ i = 0
+ l = prefixes.length
- while i < l
- prefixed = prefixes[i] + uPropName
- return (_cache[propName] = prefixed) if typeof style[prefixed] is 'string'
- i++
+ while i < l
+ prefixed = prefixes[i] + uPropName
+ return (_cache[propName] = prefixed) if typeof style[prefixed] is 'string'
+ i++
- #if all fails then set to undefined
- _cache[propName] = 'undefined'
+ #if all fails then set to undefined
+ _cache[propName] = 'undefined'
- CustomStyle.setProp = set = (propName, element, str) ->
- prop = @getProp(propName)
- element.style[prop] = str if prop isnt 'undefined'
- return
-
- CustomStyle
- )()
-
- #################################
-
- isAllWhitespace = (str) ->
- not NonWhitespaceRegexp.test(str)
- 'use strict'
- FIND_SCROLL_OFFSET_TOP = -50
- FIND_SCROLL_OFFSET_LEFT = -400
- MAX_TEXT_DIVS_TO_RENDER = 100000
- RENDER_DELAY = 200
- NonWhitespaceRegexp = /\S/
-
- ###*
- TextLayerBuilder provides text-selection functionality for the PDF.
- It does this by creating overlay divs over the PDF text. These divs
- contain text that matches the PDF text they are overlaying. This object
- also provides a way to highlight text that is being searched for.
- ###
-
- class pdfTextLayer
-
- constructor: (options) ->
- @textLayerDiv = options.textLayerDiv
- @layoutDone = false
- @divContentDone = false
- @pageIdx = options.pageIndex
- @matches = []
- @lastScrollSource = options.lastScrollSource or null
- @viewport = options.viewport
- @isViewerInPresentationMode = options.isViewerInPresentationMode
- @textDivs = []
- @findController = options.findController or null
-
- renderLayer: () ->
- textLayerFrag = document.createDocumentFragment()
- textDivs = @textDivs
- textDivsLength = textDivs.length
- canvas = document.createElement('canvas')
- ctx = canvas.getContext('2d')
-
- # No point in rendering many divs as it would make the browser
- # unusable even after the divs are rendered.
- return if textDivsLength > MAX_TEXT_DIVS_TO_RENDER
- lastFontSize = undefined
- lastFontFamily = undefined
- i = 0
-
- while i < textDivsLength
- textDiv = textDivs[i]
- continue if textDiv.dataset.isWhitespace
- fontSize = textDiv.style.fontSize
- fontFamily = textDiv.style.fontFamily
-
- # Only build font string and set to context if different from last.
- if fontSize isnt lastFontSize or fontFamily isnt lastFontFamily
- ctx.font = fontSize + ' ' + fontFamily
- lastFontSize = fontSize
- lastFontFamily = fontFamily
- width = ctx.measureText(textDiv.textContent).width
- if width > 0
- textLayerFrag.appendChild textDiv
-
- # Dataset values come of type string.
- textScale = textDiv.dataset.canvasWidth / width
- rotation = textDiv.dataset.angle
- transform = 'scale(' + textScale + ', 1)'
- transform = 'rotate(' + rotation + 'deg) ' + transform if rotation
- CustomStyle.setProp 'transform', textDiv, transform
- CustomStyle.setProp 'transformOrigin', textDiv, '0% 0%'
- i++
- @textLayerDiv.appendChild textLayerFrag
- return
-
- appendText: (geom, styles) ->
- style = styles[geom.fontName]
- textDiv = document.createElement('div')
- @textDivs.push textDiv
- if isAllWhitespace(geom.str)
- textDiv.dataset.isWhitespace = true
+ CustomStyle.setProp = set = (propName, element, str) ->
+ prop = @getProp(propName)
+ element.style[prop] = str if prop isnt 'undefined'
return
- tx = PDFJS.Util.transform(@viewport.transform, geom.transform)
- angle = Math.atan2(tx[1], tx[0])
- angle += Math.PI / 2 if style.vertical
- fontHeight = Math.sqrt((tx[2] * tx[2]) + (tx[3] * tx[3]))
- fontAscent = fontHeight
- if style.ascent
- fontAscent = style.ascent * fontAscent
- else fontAscent = (1 + style.descent) * fontAscent if style.descent
- left = undefined
- top = undefined
- if angle is 0
- left = tx[4]
- top = tx[5] - fontAscent
- else
- left = tx[4] + (fontAscent * Math.sin(angle))
- top = tx[5] - (fontAscent * Math.cos(angle))
- textDiv.style.left = left + 'px'
- textDiv.style.top = top + 'px'
- textDiv.style.fontSize = fontHeight + 'px'
- textDiv.style.fontFamily = style.fontFamily
- textDiv.textContent = geom.str
- # |fontName| is only used by the Font Inspector. This test will succeed
- # when e.g. the Font Inspector is off but the Stepper is on, but it's
- # not worth the effort to do a more accurate test.
- textDiv.dataset.fontName = geom.fontName if PDFJS.pdfBug
+ CustomStyle
+ )()
- # Storing into dataset will convert number into string.
- textDiv.dataset.angle = angle * (180 / Math.PI) if angle isnt 0
- if style.vertical
- textDiv.dataset.canvasWidth = geom.height * @viewport.scale
- else
- textDiv.dataset.canvasWidth = geom.width * @viewport.scale
- return
+ #################################
- setTextContent: (textContent) ->
- @textContent = textContent
- textItems = textContent.items
- i = 0
- len = textItems.length
+ isAllWhitespace = (str) ->
+ not NonWhitespaceRegexp.test(str)
+ 'use strict'
+ FIND_SCROLL_OFFSET_TOP = -50
+ FIND_SCROLL_OFFSET_LEFT = -400
+ MAX_TEXT_DIVS_TO_RENDER = 100000
+ RENDER_DELAY = 200
+ NonWhitespaceRegexp = /\S/
- while i < len
- @appendText textItems[i], textContent.styles
- i++
- @divContentDone = true
- @renderLayer()
- return
+ ###*
+ TextLayerBuilder provides text-selection functionality for the PDF.
+ It does this by creating overlay divs over the PDF text. These divs
+ contain text that matches the PDF text they are overlaying. This object
+ also provides a way to highlight text that is being searched for.
+ ###
-]
+ class pdfTextLayer
+
+ constructor: (options) ->
+ @textLayerDiv = options.textLayerDiv
+ @layoutDone = false
+ @divContentDone = false
+ @pageIdx = options.pageIndex
+ @matches = []
+ @lastScrollSource = options.lastScrollSource or null
+ @viewport = options.viewport
+ @isViewerInPresentationMode = options.isViewerInPresentationMode
+ @textDivs = []
+ @findController = options.findController or null
+
+ renderLayer: () ->
+ textLayerFrag = document.createDocumentFragment()
+ textDivs = @textDivs
+ textDivsLength = textDivs.length
+ canvas = document.createElement('canvas')
+ ctx = canvas.getContext('2d')
+
+ # No point in rendering many divs as it would make the browser
+ # unusable even after the divs are rendered.
+ return if textDivsLength > MAX_TEXT_DIVS_TO_RENDER
+ lastFontSize = undefined
+ lastFontFamily = undefined
+ i = 0
+
+ while i < textDivsLength
+ textDiv = textDivs[i]
+ continue if textDiv.dataset.isWhitespace
+ fontSize = textDiv.style.fontSize
+ fontFamily = textDiv.style.fontFamily
+
+ # Only build font string and set to context if different from last.
+ if fontSize isnt lastFontSize or fontFamily isnt lastFontFamily
+ ctx.font = fontSize + ' ' + fontFamily
+ lastFontSize = fontSize
+ lastFontFamily = fontFamily
+ width = ctx.measureText(textDiv.textContent).width
+ if width > 0
+ textLayerFrag.appendChild textDiv
+
+ # Dataset values come of type string.
+ textScale = textDiv.dataset.canvasWidth / width
+ rotation = textDiv.dataset.angle
+ transform = 'scale(' + textScale + ', 1)'
+ transform = 'rotate(' + rotation + 'deg) ' + transform if rotation
+ CustomStyle.setProp 'transform', textDiv, transform
+ CustomStyle.setProp 'transformOrigin', textDiv, '0% 0%'
+ i++
+ @textLayerDiv.appendChild textLayerFrag
+ return
+
+ appendText: (geom, styles) ->
+ style = styles[geom.fontName]
+ textDiv = document.createElement('div')
+ @textDivs.push textDiv
+ if isAllWhitespace(geom.str)
+ textDiv.dataset.isWhitespace = true
+ return
+ tx = PDFJS.Util.transform(@viewport.transform, geom.transform)
+ angle = Math.atan2(tx[1], tx[0])
+ angle += Math.PI / 2 if style.vertical
+ fontHeight = Math.sqrt((tx[2] * tx[2]) + (tx[3] * tx[3]))
+ fontAscent = fontHeight
+ if style.ascent
+ fontAscent = style.ascent * fontAscent
+ else fontAscent = (1 + style.descent) * fontAscent if style.descent
+ left = undefined
+ top = undefined
+ if angle is 0
+ left = tx[4]
+ top = tx[5] - fontAscent
+ else
+ left = tx[4] + (fontAscent * Math.sin(angle))
+ top = tx[5] - (fontAscent * Math.cos(angle))
+ textDiv.style.left = left + 'px'
+ textDiv.style.top = top + 'px'
+ textDiv.style.fontSize = fontHeight + 'px'
+ textDiv.style.fontFamily = style.fontFamily
+ textDiv.textContent = geom.str
+
+ # |fontName| is only used by the Font Inspector. This test will succeed
+ # when e.g. the Font Inspector is off but the Stepper is on, but it's
+ # not worth the effort to do a more accurate test.
+ textDiv.dataset.fontName = geom.fontName if PDFJS.pdfBug
+
+ # Storing into dataset will convert number into string.
+ textDiv.dataset.angle = angle * (180 / Math.PI) if angle isnt 0
+ if style.vertical
+ textDiv.dataset.canvasWidth = geom.height * @viewport.scale
+ else
+ textDiv.dataset.canvasWidth = geom.width * @viewport.scale
+ return
+
+ setTextContent: (textContent) ->
+ @textContent = textContent
+ textItems = textContent.items
+ i = 0
+ len = textItems.length
+
+ while i < len
+ @appendText textItems[i], textContent.styles
+ i++
+ @divContentDone = true
+ @renderLayer()
+ return
+
+ ]
diff --git a/services/web/public/coffee/ide/pdfng/directives/pdfViewer.coffee b/services/web/public/coffee/ide/pdfng/directives/pdfViewer.coffee
index 556e1c7d47..3b8a625da8 100644
--- a/services/web/public/coffee/ide/pdfng/directives/pdfViewer.coffee
+++ b/services/web/public/coffee/ide/pdfng/directives/pdfViewer.coffee
@@ -1,359 +1,377 @@
-app = angular.module 'pdfViewerApp', ['pdfPage', 'PDFRenderer', 'pdfHighlights']
+define [
+ "base"
+ "ide/pdfng/directives/pdfTextLayer"
+ "ide/pdfng/directives/pdfAnnotations"
+ "ide/pdfng/directives/pdfHighlights"
+ "ide/pdfng/directives/pdfRenderer"
+ "ide/pdfng/directives/pdfPage"
+ "libs/pdfjs-1.0.712/pdf"
+], (
+ App
+ pdfTextLayer
+ pdfAnnotations
+ pdfHighlights
+ pdfRenderer
+ pdfPage
+ pdf
+) ->
-app.controller 'pdfViewerController', ['$scope', '$q', 'PDFRenderer', '$element', 'pdfHighlights', ($scope, $q, PDFRenderer, $element, pdfHighlights) ->
- @load = () ->
- $scope.document = new PDFRenderer($scope.pdfSrc, {
- scale: 1,
- navigateFn: (ref) ->
- # this function captures clicks on the annotation links
- $scope.navigateTo = ref
- $scope.$apply()
- })
+ # App = angular.module 'pdfViewerApp', ['pdfPage', 'PDFRenderer', 'pdfHighlights']
- # we will have all the main information needed to start display
- # after the following promise is resolved
- $scope.loaded = $q.all({
- numPages: $scope.document.getNumPages()
- destinations: $scope.document.getDestinations()
- # get size of first page as default @ scale 1
- pdfViewport: $scope.document.getPdfViewport 1, 1
- }).then (result) ->
- $scope.pdfViewport = result.pdfViewport
- $scope.pdfPageSize = [
- result.pdfViewport.height,
- result.pdfViewport.width
+ App.controller 'pdfViewerController', ['$scope', '$q', 'PDFRenderer', '$element', 'pdfHighlights', ($scope, $q, PDFRenderer, $element, pdfHighlights) ->
+ @load = () ->
+ $scope.document = new PDFRenderer($scope.pdfSrc, {
+ scale: 1,
+ navigateFn: (ref) ->
+ # this function captures clicks on the annotation links
+ $scope.navigateTo = ref
+ $scope.$apply()
+ })
+
+ # we will have all the main information needed to start display
+ # after the following promise is resolved
+ $scope.loaded = $q.all({
+ numPages: $scope.document.getNumPages()
+ destinations: $scope.document.getDestinations()
+ # get size of first page as default @ scale 1
+ pdfViewport: $scope.document.getPdfViewport 1, 1
+ }).then (result) ->
+ $scope.pdfViewport = result.pdfViewport
+ $scope.pdfPageSize = [
+ result.pdfViewport.height,
+ result.pdfViewport.width
+ ]
+ $scope.destinations = result.destinations
+ console.log 'resolved q.all, page size is', result
+ $scope.numPages = result.numPages
+
+ @setScale = (scale, containerHeight, containerWidth) ->
+ $scope.loaded.then () ->
+ scale = {} if not scale?
+ if scale.scaleMode == 'scale_mode_fit_width'
+ # TODO make this dynamic
+ numScale = (containerWidth - 40) / ($scope.pdfPageSize[1])
+ else if scale.scaleMode == 'scale_mode_fit_height'
+ # TODO magic numbers for jquery ui layout
+ numScale = (containerHeight - 20) / ($scope.pdfPageSize[0])
+ else if scale.scaleMode == 'scale_mode_value'
+ numScale = scale.scale
+ else if scale.scaleMode == 'scale_mode_auto'
+ # TODO
+ else
+ scale.scaleMode = 'scale_mode_fit_width'
+ numScale = (containerWidth - 40) / ($scope.pdfPageSize[1])
+ # TODO
+ $scope.scale.scale = numScale
+ $scope.document.setScale(numScale)
+ $scope.defaultPageSize = [
+ numScale * $scope.pdfPageSize[0],
+ numScale * $scope.pdfPageSize[1]
]
- $scope.destinations = result.destinations
- console.log 'resolved q.all, page size is', result
- $scope.numPages = result.numPages
+ console.log 'in setScale result', $scope.scale.scale, $scope.defaultPageSize
- @setScale = (scale, containerHeight, containerWidth) ->
- $scope.loaded.then () ->
- scale = {} if not scale?
- if scale.scaleMode == 'scale_mode_fit_width'
- # TODO make this dynamic
- numScale = (containerWidth - 40) / ($scope.pdfPageSize[1])
- else if scale.scaleMode == 'scale_mode_fit_height'
- # TODO magic numbers for jquery ui layout
- numScale = (containerHeight - 20) / ($scope.pdfPageSize[0])
- else if scale.scaleMode == 'scale_mode_value'
- numScale = scale.scale
- else if scale.scaleMode == 'scale_mode_auto'
- # TODO
- else
- scale.scaleMode = 'scale_mode_fit_width'
- numScale = (containerWidth - 40) / ($scope.pdfPageSize[1])
- # TODO
- $scope.scale.scale = numScale
- $scope.document.setScale(numScale)
- $scope.defaultPageSize = [
- numScale * $scope.pdfPageSize[0],
- numScale * $scope.pdfPageSize[1]
+ @redraw = (position) ->
+ console.log 'in redraw'
+ console.log 'reseting pages array for', $scope.numPages
+ console.log 'position is', position.page, position.offset
+ $scope.pages = ({
+ pageNum: i + 1
+ } for i in [0 .. $scope.numPages-1])
+ if position? && position.page?
+ console.log 'setting current page', position.page
+ pagenum = position.page
+ $scope.pages[pagenum].current = true
+ $scope.pages[pagenum].position = position
+
+ @zoomIn = () ->
+ console.log 'zoom in'
+ newScale = $scope.scale.scale * 1.2
+ $scope.forceScale = { scaleMode: 'scale_mode_value', scale: newScale }
+
+ @zoomOut = () ->
+ console.log 'zoom out'
+ newScale = $scope.scale.scale / 1.2
+ $scope.forceScale = { scaleMode: 'scale_mode_value', scale: newScale }
+
+ @fitWidth = () ->
+ console.log 'fit width'
+ $scope.forceScale = { scaleMode: 'scale_mode_fit_width' }
+
+ @fitHeight = () ->
+ console.log 'fit height'
+ $scope.forceScale = { scaleMode: 'scale_mode_fit_height' }
+
+ @checkPosition = () ->
+ console.log 'check position'
+ $scope.forceCheck = ($scope.forceCheck || 0) + 1
+
+ @showRandomHighlights = () ->
+ console.log 'show highlights'
+ $scope.highlights = [
+ {
+ page: 3
+ h: 100
+ v: 100
+ height: 30
+ width: 200
+ }
]
- console.log 'in setScale result', $scope.scale.scale, $scope.defaultPageSize
- @redraw = (position) ->
- console.log 'in redraw'
- console.log 'reseting pages array for', $scope.numPages
- console.log 'position is', position.page, position.offset
- $scope.pages = ({
- pageNum: i + 1
- } for i in [0 .. $scope.numPages-1])
- if position? && position.page?
- console.log 'setting current page', position.page
- pagenum = position.page
- $scope.pages[pagenum].current = true
- $scope.pages[pagenum].position = position
+ # we work with (pagenumber, % of height down page from top)
+ # pdfListView works with (pagenumber, vertical position up page from
+ # bottom measured in pts)
- @zoomIn = () ->
- console.log 'zoom in'
- newScale = $scope.scale.scale * 1.2
- $scope.forceScale = { scaleMode: 'scale_mode_value', scale: newScale }
+ @getPdfPosition = () ->
+ console.log 'in getPdfPosition'
+ topPageIdx = 0
+ topPage = $scope.pages[0]
+ # find first visible page
+ visible = $scope.pages.some (page, i) ->
+ [topPageIdx, topPage] = [i, page] if page.visible
+ if visible
+ console.log 'found it', topPageIdx
+ else
+ console.log 'CANNOT FIND TOP PAGE'
- @zoomOut = () ->
- console.log 'zoom out'
- newScale = $scope.scale.scale / 1.2
- $scope.forceScale = { scaleMode: 'scale_mode_value', scale: newScale }
-
- @fitWidth = () ->
- console.log 'fit width'
- $scope.forceScale = { scaleMode: 'scale_mode_fit_width' }
-
- @fitHeight = () ->
- console.log 'fit height'
- $scope.forceScale = { scaleMode: 'scale_mode_fit_height' }
-
- @checkPosition = () ->
- console.log 'check position'
- $scope.forceCheck = ($scope.forceCheck || 0) + 1
-
- @showRandomHighlights = () ->
- console.log 'show highlights'
- $scope.highlights = [
- {
- page: 3
- h: 100
- v: 100
- height: 30
- width: 200
+ console.log 'top page is', topPage.pageNum, topPage.elemTop, topPage.elemBottom, topPage
+ top = topPage.elemTop
+ bottom = topPage.elemBottom
+ viewportTop = 0
+ viewportHeight = $element.height()
+ topVisible = (top >= viewportTop && top < viewportTop + viewportHeight)
+ someContentVisible = (top < viewportTop && bottom > viewportTop)
+ console.log 'in PdfListView', top, topVisible, someContentVisible, viewportTop
+ if topVisible
+ canvasOffset = 0
+ else if someContentVisible
+ canvasOffset = viewportTop - top
+ else
+ canvasOffset = null
+ console.log 'pdfListview position = ', canvasOffset
+ # instead of using promise, check if size is known and revert to
+ # default otherwise
+ console.log 'looking up viewport', topPage.viewport, $scope.pdfViewport
+ if topPage.viewport
+ viewport = topPage.viewport
+ pdfOffset = viewport.convertToPdfPoint(0, canvasOffset);
+ else
+ console.log 'WARNING: had to default to global page size'
+ viewport = $scope.pdfViewport
+ scaledOffset = canvasOffset / $scope.scale.scale
+ pdfOffset = viewport.convertToPdfPoint(0, scaledOffset);
+ console.log 'converted to offset = ', pdfOffset
+ newPosition = {
+ "page": topPageIdx,
+ "offset" : { "top" : pdfOffset[1], "left": 0 }
}
- ]
+ return newPosition
- # we work with (pagenumber, % of height down page from top)
- # pdfListView works with (pagenumber, vertical position up page from
- # bottom measured in pts)
+ @computeOffset = (page, position) ->
+ console.log 'computing offset for', page, position
+ element = page.element
+ pageTop = $(element).offset().top - $(element).parent().offset().top
+ console.log('top of page scroll is', pageTop, 'vs', page.elemTop)
+ console.log('inner height is', $(element).innerHeight())
+ currentScroll = $(element).parent().scrollTop()
+ offset = position.offset
+ # convert offset to pixels
+ return $scope.document.getPdfViewport(page.pageNum).then (viewport) ->
+ page.viewport = viewport
+ pageOffset = viewport.convertToViewportPoint(offset.left, offset.top)
+ console.log 'addition offset =', pageOffset
+ console.log 'total', pageTop + pageOffset[1]
+ Math.round(pageTop + pageOffset[1] + currentScroll) ## 10 is margin
- @getPdfPosition = () ->
- console.log 'in getPdfPosition'
- topPageIdx = 0
- topPage = $scope.pages[0]
- # find first visible page
- visible = $scope.pages.some (page, i) ->
- [topPageIdx, topPage] = [i, page] if page.visible
- if visible
- console.log 'found it', topPageIdx
- else
- console.log 'CANNOT FIND TOP PAGE'
+ @setPdfPosition = (page, position) ->
+ console.log 'required pdf Position is', position
+ @computeOffset(page, position).then (offset) ->
+ $scope.pleaseScrollTo = offset
+ $scope.position = position
- console.log 'top page is', topPage.pageNum, topPage.elemTop, topPage.elemBottom, topPage
- top = topPage.elemTop
- bottom = topPage.elemBottom
- viewportTop = 0
- viewportHeight = $element.height()
- topVisible = (top >= viewportTop && top < viewportTop + viewportHeight)
- someContentVisible = (top < viewportTop && bottom > viewportTop)
- console.log 'in PdfListView', top, topVisible, someContentVisible, viewportTop
- if topVisible
- canvasOffset = 0
- else if someContentVisible
- canvasOffset = viewportTop - top
- else
- canvasOffset = null
- console.log 'pdfListview position = ', canvasOffset
- # instead of using promise, check if size is known and revert to
- # default otherwise
- console.log 'looking up viewport', topPage.viewport, $scope.pdfViewport
- if topPage.viewport
- viewport = topPage.viewport
- pdfOffset = viewport.convertToPdfPoint(0, canvasOffset);
- else
- console.log 'WARNING: had to default to global page size'
- viewport = $scope.pdfViewport
- scaledOffset = canvasOffset / $scope.scale.scale
- pdfOffset = viewport.convertToPdfPoint(0, scaledOffset);
- console.log 'converted to offset = ', pdfOffset
- newPosition = {
- "page": topPageIdx,
- "offset" : { "top" : pdfOffset[1], "left": 0 }
- }
- return newPosition
+ return this
- @computeOffset = (page, position) ->
- console.log 'computing offset for', page, position
- element = page.element
- pageTop = $(element).offset().top - $(element).parent().offset().top
- console.log('top of page scroll is', pageTop, 'vs', page.elemTop)
- console.log('inner height is', $(element).innerHeight())
- currentScroll = $(element).parent().scrollTop()
- offset = position.offset
- # convert offset to pixels
- return $scope.document.getPdfViewport(page.pageNum).then (viewport) ->
- page.viewport = viewport
- pageOffset = viewport.convertToViewportPoint(offset.left, offset.top)
- console.log 'addition offset =', pageOffset
- console.log 'total', pageTop + pageOffset[1]
- Math.round(pageTop + pageOffset[1] + currentScroll) ## 10 is margin
+ ]
- @setPdfPosition = (page, position) ->
- console.log 'required pdf Position is', position
- @computeOffset(page, position).then (offset) ->
- $scope.pleaseScrollTo = offset
- $scope.position = position
-
- return this
-
-]
-
-app.directive 'pdfViewer', ['$q', '$timeout', ($q, $timeout) ->
- {
- controller: 'pdfViewerController'
- controllerAs: 'ctrl'
- scope: {
- "pdfSrc": "="
- "highlights": "="
- "position": "="
- "scale": "="
- "dblClickCallback": "="
- "pleaseJumpTo": "="
- }
- template: """
-
- """
- link: (scope, element, attrs, ctrl) ->
- console.log 'in pdfViewer element is', element
- console.log 'attrs', attrs
- layoutReady = $q.defer()
- layoutReady.notify 'waiting for layout'
- layoutReady.promise.then () ->
- console.log 'layoutReady was resolved'
-
- # TODO can we combine this with scope.parentSize, need to finalize boxes
- updateContainer = () ->
- scope.containerSize = [
- element.innerWidth()
- element.innerHeight()
- element.offset().top
- ]
-
- doRescale = (scale) ->
- console.log 'doRescale', scale
- origposition = angular.copy scope.position
- console.log 'origposition', origposition
+ App.directive 'pdfViewer', ['$q', '$timeout', ($q, $timeout) ->
+ {
+ controller: 'pdfViewerController'
+ controllerAs: 'ctrl'
+ scope: {
+ "pdfSrc": "="
+ "highlights": "="
+ "position": "="
+ "scale": "="
+ "dblClickCallback": "="
+ "pleaseJumpTo": "="
+ }
+ template: """
+
+ """
+ link: (scope, element, attrs, ctrl) ->
+ console.log 'in pdfViewer element is', element
+ console.log 'attrs', attrs
+ layoutReady = $q.defer()
+ layoutReady.notify 'waiting for layout'
layoutReady.promise.then () ->
- [h, w] = [element.innerHeight(), element.width()]
- console.log 'in promise', h, w
- ctrl.setScale(scale, h, w).then () ->
- ctrl.redraw(origposition)
+ console.log 'layoutReady was resolved'
- scope.$on 'layout-ready', () ->
- console.log 'GOT LAYOUT READY EVENT'
- console.log 'calling refresh'
- updateContainer()
- layoutReady.resolve 'layout is ready'
- scope.parentSize = [
- element.innerHeight(),
- element.innerWidth()
- ]
- #scope.$apply()
+ # TODO can we combine this with scope.parentSize, need to finalize boxes
+ updateContainer = () ->
+ scope.containerSize = [
+ element.innerWidth()
+ element.innerHeight()
+ element.offset().top
+ ]
- scope.$on 'layout:pdf:resize', () ->
- console.log 'GOT LAYOUT-RESIZE EVENT'
- scope.parentSize = [
- element.innerHeight(),
- element.innerWidth()
- ]
- #scope.$apply()
+ doRescale = (scale) ->
+ console.log 'doRescale', scale
+ origposition = angular.copy scope.position
+ console.log 'origposition', origposition
+ layoutReady.promise.then () ->
+ [h, w] = [element.innerHeight(), element.width()]
+ console.log 'in promise', h, w
+ ctrl.setScale(scale, h, w).then () ->
+ ctrl.redraw(origposition)
- element.on 'scroll', () ->
- console.log 'scroll detected', scope.adjustingScroll
- updateContainer()
- scope.$apply()
- #console.log 'pdfposition', element.parent().scrollTop()
- if scope.adjustingScroll
- scope.adjustingScroll = false
- return
- #console.log 'not from auto scroll'
- scope.position = ctrl.getPdfPosition()
- console.log 'position is', scope.position.page, scope.position.offset
- scope.$apply()
+ scope.$on 'layout-ready', () ->
+ console.log 'GOT LAYOUT READY EVENT'
+ console.log 'calling refresh'
+ updateContainer()
+ layoutReady.resolve 'layout is ready'
+ scope.parentSize = [
+ element.innerHeight(),
+ element.innerWidth()
+ ]
+ #scope.$apply()
- scope.$watch 'pdfSrc', (newVal, oldVal) ->
- console.log 'loading pdf', newVal, oldVal
- return unless newVal?
- ctrl.load()
- # trigger a redraw
- scope.scale = angular.copy (scope.scale)
+ scope.$on 'layout:pdf:resize', () ->
+ console.log 'GOT LAYOUT-RESIZE EVENT'
+ scope.parentSize = [
+ element.innerHeight(),
+ element.innerWidth()
+ ]
+ #scope.$apply()
- scope.$watch 'scale', (newVal, oldVal) ->
- # no need to set scale when initialising, done in pdfSrc
- return if newVal == oldVal
- console.log 'XXX calling Setscale in scale watch'
- doRescale newVal
+ element.on 'scroll', () ->
+ console.log 'scroll detected', scope.adjustingScroll
+ updateContainer()
+ scope.$apply()
+ #console.log 'pdfposition', element.parent().scrollTop()
+ if scope.adjustingScroll
+ scope.adjustingScroll = false
+ return
+ #console.log 'not from auto scroll'
+ scope.position = ctrl.getPdfPosition()
+ console.log 'position is', scope.position.page, scope.position.offset
+ scope.$apply()
- scope.$watch 'forceScale', (newVal, oldVal) ->
- console.log 'got change in numscale watcher', newVal, oldVal
- return unless newVal?
- doRescale newVal
+ scope.$watch 'pdfSrc', (newVal, oldVal) ->
+ console.log 'loading pdf', newVal, oldVal
+ return unless newVal?
+ ctrl.load()
+ # trigger a redraw
+ scope.scale = angular.copy (scope.scale)
- scope.$watch 'position', (newVal, oldVal) ->
- console.log 'got change in position watcher', newVal, oldVal
+ scope.$watch 'scale', (newVal, oldVal) ->
+ # no need to set scale when initialising, done in pdfSrc
+ return if newVal == oldVal
+ console.log 'XXX calling Setscale in scale watch'
+ doRescale newVal
- scope.$watch 'forceCheck', (newVal, oldVal) ->
- console.log 'forceCheck', newVal, oldVal
- return unless newVal?
- scope.adjustingScroll = true # temporarily disable scroll
- doRescale scope.scale
+ scope.$watch 'forceScale', (newVal, oldVal) ->
+ console.log 'got change in numscale watcher', newVal, oldVal
+ return unless newVal?
+ doRescale newVal
- scope.$watch('parentSize', (newVal, oldVal) ->
- console.log 'XXX in parentSize watch', newVal, oldVal
- if newVal == oldVal
- console.log 'returning because old and new are the same'
- return
- return unless oldVal?
- console.log 'XXX calling setScale in parentSize watcher'
- doRescale scope.scale
- , true)
+ scope.$watch 'position', (newVal, oldVal) ->
+ console.log 'got change in position watcher', newVal, oldVal
- scope.$watch 'elementWidth', (newVal, oldVal) ->
- console.log '*** watch INTERVAL element width is', newVal, oldVal
+ scope.$watch 'forceCheck', (newVal, oldVal) ->
+ console.log 'forceCheck', newVal, oldVal
+ return unless newVal?
+ scope.adjustingScroll = true # temporarily disable scroll
+ doRescale scope.scale
- scope.$watch 'pleaseScrollTo', (newVal, oldVal) ->
- console.log 'got request to ScrollTo', newVal, 'oldVal', oldVal
- return unless newVal?
- scope.adjustingScroll = true # temporarily disable scroll
- # handler while we reposition
- $(element).scrollTop(newVal)
- scope.pleaseScrollTo = undefined
+ scope.$watch('parentSize', (newVal, oldVal) ->
+ console.log 'XXX in parentSize watch', newVal, oldVal
+ if newVal == oldVal
+ console.log 'returning because old and new are the same'
+ return
+ return unless oldVal?
+ console.log 'XXX calling setScale in parentSize watcher'
+ doRescale scope.scale
+ , true)
- scope.$watch 'pleaseJumpTo', (newPosition, oldPosition) ->
- console.log 'in pleaseJumpTo', newPosition, oldPosition
- return unless newPosition?
- ctrl.setPdfPosition scope.pages[newPosition.page-1], newPosition
+ scope.$watch 'elementWidth', (newVal, oldVal) ->
+ console.log '*** watch INTERVAL element width is', newVal, oldVal
- scope.$watch 'navigateTo', (newVal, oldVal) ->
- return unless newVal?
- console.log 'got request to navigate to', newVal, 'oldVal', oldVal
- scope.navigateTo = undefined
- console.log 'navigate to', newVal
- console.log 'look up page num'
- scope.loaded.then () ->
- console.log 'destinations are', scope.destinations
- r = scope.destinations[newVal.dest]
- console.log 'need to go to', r
- console.log 'page ref is', r[0]
- scope.document.getPageIndex(r[0]).then (pidx) ->
- console.log 'page num is', pidx
- page = scope.pages[pidx]
- scope.document.getPdfViewport(page.pageNum).then (viewport) ->
- console.log 'got viewport', viewport
- coords = viewport.convertToViewportPoint r[2], r[3]
- console.log 'viewport position', coords
- console.log 'r is', r, 'r[1]', r[1], 'r[1].name', r[1].name
- if r[1].name == 'XYZ'
- console.log 'XYZ:', r[2], r[3]
- newPosition = {page: pidx, offset: {top: r[3], left: r[2]}}
- ctrl.setPdfPosition scope.pages[pidx], newPosition # XXX?
+ scope.$watch 'pleaseScrollTo', (newVal, oldVal) ->
+ console.log 'got request to ScrollTo', newVal, 'oldVal', oldVal
+ return unless newVal?
+ scope.adjustingScroll = true # temporarily disable scroll
+ # handler while we reposition
+ $(element).scrollTop(newVal)
+ scope.pleaseScrollTo = undefined
- scope.$watch "highlights", (areas) ->
- console.log 'got HIGHLIGHTS in pdfViewer', areas
- return if !areas?
- console.log 'areas are', areas
- highlights = for area in areas or []
- {
- page: area.page - 1
- highlight:
- left: area.h
- top: area.v
- height: area.height
- width: area.width
- }
- console.log 'highlights', highlights
+ scope.$watch 'pleaseJumpTo', (newPosition, oldPosition) ->
+ console.log 'in pleaseJumpTo', newPosition, oldPosition
+ return unless newPosition?
+ ctrl.setPdfPosition scope.pages[newPosition.page-1], newPosition
- return if !highlights.length
+ scope.$watch 'navigateTo', (newVal, oldVal) ->
+ return unless newVal?
+ console.log 'got request to navigate to', newVal, 'oldVal', oldVal
+ scope.navigateTo = undefined
+ console.log 'navigate to', newVal
+ console.log 'look up page num'
+ scope.loaded.then () ->
+ console.log 'destinations are', scope.destinations
+ r = scope.destinations[newVal.dest]
+ console.log 'need to go to', r
+ console.log 'page ref is', r[0]
+ scope.document.getPageIndex(r[0]).then (pidx) ->
+ console.log 'page num is', pidx
+ page = scope.pages[pidx]
+ scope.document.getPdfViewport(page.pageNum).then (viewport) ->
+ console.log 'got viewport', viewport
+ coords = viewport.convertToViewportPoint r[2], r[3]
+ console.log 'viewport position', coords
+ console.log 'r is', r, 'r[1]', r[1], 'r[1].name', r[1].name
+ if r[1].name == 'XYZ'
+ console.log 'XYZ:', r[2], r[3]
+ newPosition = {page: pidx, offset: {top: r[3], left: r[2]}}
+ ctrl.setPdfPosition scope.pages[pidx], newPosition # XXX?
- first = highlights[0]
+ scope.$watch "highlights", (areas) ->
+ console.log 'got HIGHLIGHTS in pdfViewer', areas
+ return if !areas?
+ console.log 'areas are', areas
+ highlights = for area in areas or []
+ {
+ page: area.page - 1
+ highlight:
+ left: area.h
+ top: area.v
+ height: area.height
+ width: area.width
+ }
+ console.log 'highlights', highlights
- pageNum = scope.pages[first.page].pageNum
+ return if !highlights.length
- scope.document.getPdfViewport(pageNum).then (viewport) ->
- position = {
- page: first.page
- offset:
- left: first.highlight.left
- top: viewport.viewBox[3] - first.highlight.top + first.highlight.height + 72
- }
- ctrl.setPdfPosition(scope.pages[first.page], position)
+ first = highlights[0]
+
+ pageNum = scope.pages[first.page].pageNum
+
+ scope.document.getPdfViewport(pageNum).then (viewport) ->
+ position = {
+ page: first.page
+ offset:
+ left: first.highlight.left
+ top: viewport.viewBox[3] - first.highlight.top + first.highlight.height + 72
+ }
+ ctrl.setPdfPosition(scope.pages[first.page], position)
- }
-]
+ }
+ ]