剪贴板API调用抛出NotAllowedError而不调用onPermissionRequest()


10

我有一个带有按钮的简单页面,当按下按钮时,该页面使用Async Clipboard API写入剪贴板。

<body>
  <button type="button" onclick="testClipboard();">
    Test Clipboard
  </button>
</body>
function testClipboard() {
  navigator.clipboard.writeText("Clipboard API Test").then(
    v => alert("Success"),
    e => alert("Fail\n" + e));
}

这适用于Chrome和Firefox,台式机和移动设备。但是,在Android Webview上,它引发以下错误:

NotAllowError: Write permission denied.


我认为我需要重写WebChromeClient.onPermissionRequest()以授予许可,但是奇怪的onPermissionRequest()是似乎没有被调用,并且仍然抛出相同的错误。

public class WebChromeController extends WebChromeClient {
  @Override
  public void onPermissionRequest(PermissionRequest request) {
    Log.d("myTag", "Permission request");
    Log.d("myTag", request.getResources().toString());
    request.grant(request.getResources());
  }
}
protected void initWebView() {
  // ...
  myWebView.setWebChromeClient(new WebChromeController());
}

我仍然收到相同的错误:

NotAllowError: Write permission denied.

Logcat也不记录任何内容。


我怀疑我的Android应用可能需要其他权限才能访问剪贴板,但是根据https://developer.android.com/about/versions/10/privacy/changes#clipboard-data,我的应用在具有焦点时应获得许可。实际上,以下代码有效:

ClipboardManager clipboard = (ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("MyLbl", "I have permission");
clipboard.setPrimaryClip(clip);

我还声明了以下内容,AndroidManifest.xml以防请求许可的操作需要许可:

<uses-permission android:name="android.webkit.PermissionRequest" />

这什么也没做。

因此,使用应用程序级别权限可能不是问题。


怎么了?

如何获得异步剪贴板API调用以在Webview中工作?


操作系统:Android 10 Q

网页检视:v。81.0.4044.111


类似的问题,也没有回答:stackoverflow.com/questions/61429649/...
BDL


可能是一个错误。
特拉维斯J

@hereticMonkey thx的链接,但我不认为它会改变任何东西。它指出“尝试读写剪贴板数据会自动提示用户是否已授予许可”,这意味着除了尝试使用剪贴板外,没有其他明确的方法在JS中请求此许可,相信是真的。正如问题中提到的那样,当我在Webview环境中进行操作时,onPermissionRequest()实际上从未被调用过。
cyqsimon

Answers:


2

剪贴板API的writeText方法文档说,我们需要clipboard-write使用Permissions api 获得权限。但navigator.permission在webview中未定义,可能是因为他们不想将网络权限与android os权限混合使用。

我们可以通过另一种方式将文本从android webview复制到剪贴板(通过从webview javascript代码调用本机java方法)。

首先在webview上启用javascript:

myWebView.getSettings().setJavaScriptEnabled(true);

然后添加javascript界面​​:

myWebView.addJavascriptInterface(new WebAppInterface(), "NativeAndroid");

创建方法将使用以下方法将文本复制到剪贴板 android.content.ClipboardManager

public class WebAppInterface {
    @JavascriptInterface
    public void copyToClipboard(String text) {
        ClipboardManager clipboard = (ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
        ClipData clip = ClipData.newPlainText("demo", text);
        clipboard.setPrimaryClip(clip);
    }
}

现在,您可以从testClipboard方法中调用上述方法:

function testClipboard() {
  navigator.clipboard.writeText("Clipboard API Test").then(
    v => alert("Success"),
    e => alert("Fail\n" + e));

  NativeAndroid.copyToClipboard("Clipboard API Test");
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.