2016-09-21 50 views
0

所以,看起來我對js承諾的理解還相當缺乏。我正在使用PDFJS將PDF的所有頁面顯示爲可滾動的畫布列表(目前正在工作)。當我調整窗口的大小,我這樣調用的函數(我有一個pages陣列中存儲所有的PDF頁面從pdf.getPage(index)PDFJS和承諾減少

// PART A 
// This part works, though "pages" is a representation obviously 
function reRender() { 
    const pages = [ 
    pdfjsPage0, // the result of pdf.getPage(0) 
    pdfjsPage1, 
    pdfjsPage2, 
    ]; 

    return pages.reduce((accum, page, index) => accum.then(() => { 
    const viewport = page.getViewport(scale); 
    const canvas = canvases[index]; 
    canvas.width = viewport.width; 
    canvas.height = viewport.height; 
    const ctx = canvas.getContext('2d'); 
    const renderContext = { 
     canvasContext: ctx, 
     viewport, 
    }; 
    return page.render(renderContext); 
    }), Promise.resolve()); 
} 

但是,按預期該代碼將無法正常工作,因爲承諾是看似如我期望不退換:

// PART B 
// This part only somewhat works, though "pages" is a representation obviously 
// The promise will return and be resolved before all the pages have actually been rendered 
// ie: reRender.then(//somecode), //somecode will execute before the pages have been rendered 
function reRender() { 
    const pages = [ 
    pdfjsPage0, // the result of pdf.getPage(0) 
    pdfjsPage1, 
    pdfjsPage2, 
    ]; 

    let promise = Promise.resolve(); //edited to add "()" 

    pages.forEach((page, index) => { 
    promise = promise.then(() => { 
     const viewport = page.getViewport(scale); 
     const canvas = canvases[index]; 
     canvas.width = viewport.width; 
     canvas.height = viewport.height; 
     const ctx = canvas.getContext('2d'); 
     const renderContext = { 
     canvasContext: ctx, 
     viewport, 
     }; 
     return page.render(renderContext); 
    }); 
    }); 

    return promise; 
} 

然而,抓住了網頁時,貌似,無極需要建立一種完全不同的方式,因爲這樣的工作(同一類型的積聚不會等待或貌似走在我期望重新渲染的順序中:

// PART C 
// This works, nothing in the caller.then will execute until everything 
// has resolved here 
function getPagesAndAddCanvas(pdf, pages = [], canvas = []) { 
    let promise = Promise.resolve(); 

    for (let i = 1; i <= pdf.numPages; i++) { 
     promise = promise.then(() => pdf.getPage(i) 
     .then(page => { 
      pages.push(page); 
      const canvas = angular.element('<canvas></canvas>'); 
      containerElement.append(canvas); 
      canvases.push(canvas[0]); 
     }) 
    ) 
    } 
    return promise; 
    } 

然而,應該怎樣貌似在我的腦海工作,因爲PDFJS.getPage返回一個承諾,這在某種程度上不工作,使我豐富困惑我承諾的認識:

// PART D 
// This does not work at all, pdf.getPage in this scenario 
// does not seem to ever return 
function getPagesAndAddCanvas(pdf, pages = [], canvas = []) { 
    const pageLength = Array(pdf.numPages).fill(1); 

    return pageLength.reduce((accum, irrelevant, index) => accum.then(() => { 
     console.log(pdf); 
     console.log(`index: ${index}`); // this is called for index 0 
     return pdf.getPage(index) 
     .then(page => { 
      console.log(page); // this is NEVER called 
      pages.push(page); 
      const canvas = angular.element('<canvas></canvas>'); 
      containerElement.append(canvas); 
      canvases.push(canvas[0]); 
      return Promise.resolve(); //edited to fix spelling 
     }); 
    }), Promise.resolve()); 
    } 

沒有人有自A部分和C部分工作以來,如何/爲什麼這些看起來相互矛盾的洞察力,但是B部分和D部分沒有?我在這裏碰壁,失去了智慧。

回答

0

B部分不起作用,因爲

let promise = Promise.resolve; 

應該

let promise = Promise.resolve(); 

(但只是用其中一部分工作是清潔)。


部分d不起作用,因爲

  return Promise.resovle(); 

是一個錯字因爲,相比於C部分,在index循環從0numPages-1不像i運行從1numPages

您確實應該添加一些記錄錯誤的處理程序,並查看控制檯上的未捕獲異常。

+0

關於打字錯誤的道歉,完全是我的錯。但是非常感謝,我完全由於一個錯誤而關閉了。 – jdub