腾讯x5 WebView选择文件的正确姿势
将项目中的webview换成x5以后突然今天有个上传图片的功能要实现,但是原本好好的上传逻辑报错了,有点慌,但是也不慌,一想就是x5搞的鬼。然后就开始跟源码,找方案,,,最后顺利解决。看了网上没有相关例子,记录一下,免得后生们踩坑
报错信息如下图
Caused by: java.lang.IllegalStateException: showFileChooser result was already called
分析以下代码可能是由于onReceiveValue调用了多次导致的
public interface ValueCallback<T> extends android.webkit.ValueCallback<T> {
void onReceiveValue(T var1);
}
原生webview的常规写法要适配不同版本,如下
mWebView.setWebChromeClient(new WebChromeClient() {
//以下是在各个Android版本中 WebView调用文件选择器的方法
// For Android < 3.0
public void openFileChooser(ValueCallback<Uri> valueCallback) {
openImageChooserActivity(valueCallback);
}
// For Android >= 3.0
public void openFileChooser(ValueCallback valueCallback, String acceptType) {
openImageChooserActivity(valueCallback);
}
//For Android >= 4.1
@Override
public void openFileChooser(ValueCallback<Uri> valueCallback,
String acceptType, String capture) {
openImageChooserActivity(valueCallback);
}
// For Android >= 5.0
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
@Override
public boolean onShowFileChooser(WebView webView,
ValueCallback<Uri[]> filePathCallback,
FileChooserParams fileChooserParams) {
mValueCallback2 = filePathCallback;
Intent intent = fileChooserParams.createIntent();
startActivityForResult(intent, CHOOSE_ANDROID_5);
return true;
}
});
但是x5内部是做了适配的,只要实现一个方法即可
public void openFileChooser(ValueCallback<Uri> valueCallback,
String acceptType, String capture){}
注意:这里千万不要调用super
完整的x5选择文件如下
private final int CHOOSE_REQUEST_CODE = 1000;
private ValueCallback<Uri> mValueCallback;
private void webViewSettings() {
mWebView.setWebChromeClient(new WebChromeClient() {
@Override
public void openFileChooser(ValueCallback<Uri> valueCallback,
String acceptType, String capture) {
openImageChooserActivity(valueCallback);
}
});
}
private void openImageChooserActivity(ValueCallback<Uri> valueCallback) {
mValueCallback = valueCallback;
Intent intent = new Intent();
if (Build.VERSION.SDK_INT < 19) {
intent.setAction(Intent.ACTION_GET_CONTENT);
} else {
intent.setAction(Intent.ACTION_PICK);
intent.setData(MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
}
intent.setType("image/*");
((MyPinkFamilyActivity) mContext).startActivityForResult(Intent.createChooser(intent,"选择图片",CHOOSE_REQUEST_CODE);
}
public void onActivityResult(int requestCode, int resultCode, Intent intent) {
switch (requestCode) {
case CHOOSE://以下选择图片后的回调
processResult(resultCode, intent);
break;
}
}
private void processResult(int resultCode, Intent intent) {
if (mValueCallback == null) {
return;
}
if (resultCode == Activity.RESULT_OK && intent != null) {
Uri result = intent.getData();
mValueCallback.onReceiveValue(result);
} else {
mValueCallback.onReceiveValue(null);
}
mValueCallback = null;
}
总结
遇事不慌,从源码出手!希望对你有所帮助。。。少走弯路,多点时间陪陪家人