自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

手把手教你開發(fā)自己的VSCode插件

開發(fā) 前端
默認情況下,VSCode不直接支持查看某些特定類型的文件。但是,你可以通過使用自定義編輯器(customerEditors)來擴展其功能。

一、前言

在VSCode市場上搜索一個PDF閱讀插件,找到了下載量最高的插件。在檢查了插件的源代碼之后,發(fā)現它直接嵌入了pdf.js的Web界面。

圖片圖片

開發(fā)這樣的插件并不復雜,只需要一些插件開發(fā)的知識。

接下來,將在這里與大家分享這個插件是如何開發(fā)的。雖然與源代碼可能有些許不同,但基本原理是相同的。

二、定義自定義編輯器

默認情況下,VSCode不直接支持查看某些特定類型的文件。但是,你可以通過使用自定義編輯器(customerEditors)來擴展其功能。

通過customerEditors,你可以創(chuàng)建完全可自定義的讀/寫編輯器,以替換VSCode的標準文本編輯器,用于處理特定類型的資源。

例如,在編輯Markdown文件時,可以創(chuàng)建一個自定義編輯器,從而實時預覽Markdown的渲染效果。

對于PDF文件的預覽,同樣也可以使用customerEditors功能。

首先,在插件的pacakge.json文件中定義它:

"contributes": {
  "customEditors": [
    {
      "viewType": "dodo-reader.pdfEditor",
      "displayName": "PDF Viewer",
      "selector": [
        {
          "filenamePattern": "*.pdf"
        }
      ]
    }
  ]
}

三、注冊自定義編輯器

創(chuàng)建一個實現vscode.CustomEditorProvider接口的類。該接口包含了用于管理自定義編輯器(例如打開和保存)的方法。例如:

class PdfEditorProvider implements Partial {
 constructor() {
 // 可在此處進行初始化操作
 }

resolveCustomEditor(document: CustomDocument, webviewPanel: WebviewPanel, _token: CancellationToken) {
 // 基于URI創(chuàng)建一個自定義文檔,并返回一個自定義文檔對象
 }
openCustomDocument(uri: vscode.Uri, openContext: vscode.CustomDocumentOpenContext, token: vscode.CancellationToken) {
 // 將自定義文檔與Webview面板關聯,并處理編輯器內容與Webview之間的交互
 }
}
 // 注冊你的提供程序
const myProvider = new PdfEditorProvider();
const disposable = vscode.window.registerCustomEditorProvider('dodo-reader.pdfEditor', myProvider);
context.subscriptions.push(disposable);

四、改進視圖提供程序

如上所述注冊自定義編輯器之后,下一步就是加強PdfEditorProvider接口,以定義視圖的顯示方式。

顯示涉及使用網絡視圖,而你將使用pdf.js的Web視圖程序。首先,下載預構建的程序(現代瀏覽器),并將其提取到你的項目目錄中。

圖片圖片

這個程序可以直接在瀏覽器中訪問。在目錄中啟動一個服務,并打開地址:

你可以通過添加查詢參數?file=fileUrl來打開PDF文件。

4.1 openCustomDocument

當打開PDF文件時,首先會調用openCustomDocument方法。你可以基于傳入的URI創(chuàng)建一個自定義文檔對象。該文檔對象將包含你想要編輯的內容。在這個程序中,不進行任何處理,而是直接返回一個包含URI的對象,該對象將傳遞給resolveCustomEditor方法的document參數。

openCustomDocument(uri: vscode.Uri, openContext: vscode.CustomDocumentOpenContext, token: vscode.CancellationToken) {
 return {
   uri,
   dispose: () => { }
 };
}

4.2 resolveCustomEditor

在resolveCustomEditor方法中,可以定義要顯示的視圖,程序如下。

resolveCustomEditor(document: CustomDocument, webviewPanel: WebviewPanel, _token: CancellationToken) {
   webviewPanel.webview.html = 'Hello World!';
}

要顯示PDF文件,只需將下載的PDF程序的HTML內容替換為當前的webviewPanel.webview.html值。最初認為可以更改為:

// 嵌入一個iframe以查看PDF
webviewPanel.webview.html = `
  
  
   
     
   
   
     
   
  
`

這個方法是最簡單的,但令人意外的是,iframe沒有顯示內容。這可能是由于VSCode的安全策略限制造成的。

因此,在這里考慮了另一種方法:讀取PDF視圖主頁的HTML內容,并將其賦值給webviewPanel.webview.html。

然而,這種方法可能會遇到一個問題:如何向PDF視圖程序提供文件鏈接。

如前所述,PDF視圖程序將通過查詢參數“file.”獲取文件鏈接。如果沒有提供此參數,程序將讀取默認鏈接。以下是一個相關的源代碼示例:

file = params.get("file") ?? _app_options.AppOptions.get("defaultUrl");

然而,直接賦值HTML文本不能通過URL提供“file”的值。這可能需要修改源代碼。盡管修改源代碼可能會帶來一些不便,但一開始似乎也沒有其他辦法,所以不得不嘗試一下。一種方法是改變獲取“file”值的方式,直接從全局變量中獲取。可以使用如下方法在HTML內容中添加“file”值:

window.file = 'https://...'

然后將上述源代碼修改為:

file = window.file ?? _app_options.AppOptions.get("defaultUrl");

然而,就在我以為成功即將到來的時候,出現了一個紅色錯誤:“加載PDF時出現錯誤。文件來源與閱覽器不匹配”。

經過進一步調查,在相應的源代碼中發(fā)現了一個“fileinputchange”事件監(jiān)聽處理程序,如下所示:

var webViewerFileInputChange = function (evt) {
 if (PDFViewerApplication.pdfViewer?.isInPresentationMode) {
   return;
 }
 const file = evt.fileInput.files[0];
 PDFViewerApplication.open({
   url: URL.createObjectURL(file),
   originalUrl: file.name
 });
};

從代碼中很容易看出,一旦檢測到文件發(fā)生更改,就會立即調用open方法打開文件。重要的是要注意,該open方法并不驗證URL是否與當前源相匹配。目前,它使用了一個blob鏈接。在這種情況下,我們是否可以在初始化后直接調用open方法來打開文件呢?經過一些改造,最終證明是可行的。以下是修改后的代碼示例:

resolveCustomEditor(document: CustomDocument, webviewPanel: WebviewPanel, _token: CancellationToken) {
   webviewPanel.webview.options = {
     enableScripts: true,
     localResourceRoots: [vscode.Uri.file(path.dirname(document.uri.fsPath)), this.context.extensionUri]
  };
   const base = vscode.Uri.joinPath(this.context.extensionUri, 'dist/web/pdf/web/')
   webviewPanel.webview.html = readFileSync(path.join(base.fsPath, 'viewer.html'), 'utf8').replace('', `
   
   
   
 `)
}

對上面的關鍵代碼進行分析:

  • localResourceRoots參數:該參數的目的是定義可以通過Web URL訪問的目錄。在這里,需要明確定義兩個目錄:一個用于打開PDF文件的當前目錄,另一個用于插件所在的目錄。確保兩者都正確定義,否則可能在訪問時遇到401錯誤。
  • tag:通過設置tag,可以為網頁內部加載資源提供基本路徑。確保資源能夠正確加載。
  • setTimeout函數:在調用程序打開文件時使用setTimeout的目的是在打開默認PDF文件后再打開所需的PDF文件。這樣可以防止后面執(zhí)行打開默認PDF的操作覆蓋想要打開的PDF(盡管實際上會出現默認文件錯誤,但不會產生實質性影響)。

與之前提到的PDF插件實現相比,這種實現要簡單得多,但原理基本相同。

責任編輯:武曉燕 來源: Java學研大本營
相關推薦

2021-02-26 11:54:38

MyBatis 插件接口

2024-04-02 08:58:13

2024-03-05 18:27:43

2021-09-26 16:08:23

CC++clang_forma

2022-01-04 08:52:14

博客網站Linux 系統(tǒng)開源

2011-04-28 15:09:15

jQueryjqPlot

2011-05-27 08:41:26

JavascriptFirefox

2017-09-05 13:01:11

CocoaPods開源庫GitHub

2021-07-14 09:00:00

JavaFX開發(fā)應用

2011-01-10 14:41:26

2011-05-03 15:59:00

黑盒打印機

2011-03-28 16:14:38

jQuery

2021-06-04 05:18:29

ARM程序Gdbserver

2022-01-08 20:04:20

攔截系統(tǒng)調用

2023-04-26 12:46:43

DockerSpringKubernetes

2022-12-07 08:42:35

2022-07-27 08:16:22

搜索引擎Lucene

2022-03-14 14:47:21

HarmonyOS操作系統(tǒng)鴻蒙

2011-02-22 13:46:27

微軟SQL.NET

2021-12-28 08:38:26

Linux 中斷喚醒系統(tǒng)Linux 系統(tǒng)
點贊
收藏

51CTO技術棧公眾號