【问题标题】:VSCode: How to enable links in a webpage in the WebviewVSCode:如何在 Webview 中启用网页中的链接
【发布时间】:2019-06-29 19:13:00
【问题描述】:

vscode.previewHtml 被弃用,取而代之的是 Webview。 我使用这个新 API 更新了我的 ahk extension for vscode。 通过hh.exe -decompile Docs AutoHotkey.chm,我获得了 AutoHotkey 主站点的本地网站版本。 我想在第二列中显示一个上下文文档,以便您在编码时阅读它。所以我做了。 我成功地用样式表加载了页面, 但链接不起作用:我总是在同一页面上。

即使我可以更改它们的href,我也无法转到另一个页面。 尽管您可以在工具提示中读取 href 值,但每次单击链接时都不会发生任何事情。 Docs 文件夹存储在扩展路径中,所以localResourceRoots 应该没问题。

我注意到一个奇怪的事情是,即使enableScripts 设置为 true,似乎并不是所有的 js 代码都被执行,因为在 AutoHotkey 网站上,在 .chm 和每个打开的 .html 文件中FF 我可以看到侧边栏,但在 WebView 页面中看不到。

这是创建 WebView 的代码:


 this.docsPanel = vscode.window.createWebviewPanel('ahk-offline-docs', 'Documentation', { viewColumn: vscode.ViewColumn.Two, preserveFocus: true }, {
                enableScripts: true,
                enableFindWidget: true,
                enableCommandUris: true,
                localResourceRoots: [vscode.Uri.file(path.join(this.docsDirectoryPath, 'docs//')).with({ scheme: 'vscode-resource' })]
            });
            this.docsPanel.onDidDispose((e) => {
                this.isDocsPanelDisposed = true;
            });

这是将页面加载到 WebView 中的代码:


let url = vscode.Uri.file(path.join(this.docsDirectoryPath, 'docs/')).with({ scheme: 'vscode-resource' });
                    const dom = new JSDOM(data, { runScripts: "dangerously" });
                    const aTags = dom.window.document.getElementsByTagName('a');
                    const len = aTags.length;
                    const basePath = url.toString();
                    for (let i = 0; i < len; i++) {
                        const a = aTags[i];
                        if (!a.href.includes('about:blank')) {
                            const commentCommandUri = vscode.Uri.parse(`command:ahk.spy`);
                            a.href = basePath + a.href;
                            // a.removeAttribute('href');
                            // a.setAttribute('onclick', '{command:ahk.spy}');
                        }
                    }
                    let ser = dom.serialize();
                    this.docsPanel.webview.html = /*data/*ser*/ser.toString().replace('<head>', `<head>\n<base href="${url.toString()}/">`);

另一种想法是从页面启动 vscode.commands(因为enableCommandUris),但我不知道如何进行这种操作。

如果您需要/想要重现此问题,您只需克隆 repo,进入improving-offline-docs 分支并打开文件offline-docs-manager.ts,方法为openTheDocsPanel()

有没有办法使用链接切换当前页面? 我应该开发一个 postMessage 系统吗? 或者我错过了某个地方的设置? 还是有更好的方法?

提前致谢!

【问题讨论】:

    标签: typescript webview visual-studio-code autohotkey vscode-extensions


    【解决方案1】:

    Webviews 不能导航到当前 webview 中的另一个页面。如果您的 webview 尝试这样做,您应该会在 webview 开发人员工具中看到一条消息,例如 prevented webview navigation

    有两种方法可以处理 webviews 中的链接:

    • &lt;a&gt; 链接到外部资源的元素(例如 https:mailto: 链接)在大多数情况下应该可以工作。可能会有一些奇怪的边缘情况,如果您遇到其中一种情况,您可能希望使用 command uri 或 postMessage 来触发主扩展源中的某些操作

    • 1234563 webview的html

    【讨论】:

    • 嗨,马特·比尔纳,谢谢您的回复!如何使用 arg 发出命令? let dom = new JSDOM(data, { runScripts: "dangerously" }); for (let i = 0; i &lt; len; i++) { if (!a.href.includes('about:blank')) { const commentCommandUri = vscode.Uri.parse(command:ahk.docs?${basePath + a.href}); a.href = commentCommandUri.toString();}} let html = dom.serialize(); 我尝试编码 ahk.spy 命令,但不起作用。我在哪里可以找到 command 的示例?
    • Documentation on command URIs。关键是使用 json 字符串化数组并使用 encodeURIComponent
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-10-29
    • 2015-10-29
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多