Android WebView 上传各种文件(包括拍照 录像 录音 文件 音乐 等,用到图片或拍照的,可以参考下)

  我也是从网上扒下来的,经过多次实验,找到了个好用的。网上能搜到最多的也就是这个解决方案,我英文不好,也没仔细研究,但大多数都是出自这:

http://stackoverflow.com/questions/4944102/android-webview-file-input-field-filechooser-doesnt-show-up

  我终于google到了个好用的方案:http://www.cnblogs.com/sipher/archive/2012/09/05/2672361.html

  android 为了安全考虑把webview 中的上传文件给默认去除了。不过可以自己通过实现接口,自己完成这个功能。

  首先用webview的setWebChromeClient(WebChromeClient wcc)方法,通过这个方法也能让浏览器支持js的alert方法。

  WebChromeClient 类要自己实现,可以用匿名类,也可以用普通类,咱们就用内部类吧,简单,而且小软件也无所谓了,根本不用考虑后期。

复制代码
private class MyWebChromeClient extends WebChromeClient {
//这个重新的方法是为了让js支持alert。不需要的可以去掉
        @Override
        public boolean onJsAlert(WebView view, String url, String message,
                JsResult result) {
            return super.onJsAlert(view, url, message, result);
        }


            // For Android  > 4.1.1
          public void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType, String capture) {
                  openFileChooser(uploadMsg, acceptType);
          }
            // For Android 3.0+
        public void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) {  
               if (mUploadMessage != null) return;
               mUploadMessage = uploadMsg;
               startActivityForResult(createDefaultOpenableIntent(),
                       MainActivity.FILECHOOSER_RESULTCODE);
           }
            // For Android < 3.0
        public void openFileChooser(ValueCallback<Uri> uploadMsg) {
               openFileChooser( uploadMsg, "" );
        }
    }
复制代码

 

  声明并实现了这个类后就可以用webView 的setWebChromeClient(new WebChromeClient())方法加入自己实现的接口了。

webView.setWebChromeClient(new MyWebChromeClient());

  不过上面实现的内部类中有几个方法还要使用,是自己实现的方法。放在内部类里也行,放外面也行,都随意,不过要是写在内部类里的话,String mCameraFilePath;这个属性要声明成activity的属性。

复制代码
private Intent createDefaultOpenableIntent() {
    // Create and return a chooser with the default OPENABLE
    // actions including the camera, camcorder and sound
    // recorder where available.
      Intent i = new Intent(Intent.ACTION_GET_CONTENT);
      i.addCategory(Intent.CATEGORY_OPENABLE);
      i.setType("*/*");

      Intent chooser = createChooserIntent(createCameraIntent(), createCamcorderIntent(),
             createSoundRecorderIntent());
     chooser.putExtra(Intent.EXTRA_INTENT, i);
     return chooser;
 }
 
 private Intent createChooserIntent(Intent... intents) {
     Intent chooser = new Intent(Intent.ACTION_CHOOSER);
     chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS, intents);
     chooser.putExtra(Intent.EXTRA_TITLE, "File Chooser");
    return chooser;
   }
//在原作者代码里我发现这个变量会被下面的方法使用,但他用的是局部变量,我设成属性后就好了
 String mCameraFilePath;
private Intent createCameraIntent() {
   Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
   File externalDataDir = Environment.getExternalStoragePublicDirectory(
             Environment.DIRECTORY_DCIM);
   File cameraDataDir = new File(externalDataDir.getAbsolutePath() +
             File.separator + "browser-photos");
   cameraDataDir.mkdirs();
  mCameraFilePath = cameraDataDir.getAbsolutePath() + File.separator +
             System.currentTimeMillis() + ".jpg";
   cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(mCameraFilePath)));
   return cameraIntent;
 }

private Intent createCamcorderIntent() {
  return new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
 }

private Intent createSoundRecorderIntent() {
  return new Intent(MediaStore.Audio.Media.RECORD_SOUND_ACTION);
 }
复制代码

在activity里加入以上所有代码后就好了,现在就能在网页中用 <input type="file"/>了。

  刚刚成功了,也不想再仔细研究了,小弟不才,博客不会写,有什么问题,请指教

 

posted @   牛孝祖  阅读(4234)  评论(1编辑  收藏  举报
编辑推荐:
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
点击右上角即可分享
微信分享提示