MAUI Android端WebView点击下载链接无响应的实现方案咨询
MAUI Android WebView 处理Content-Disposition文件下载
实现思路
Android平台的WebView默认不会自动处理带有Content-Disposition响应头的下载请求,需要通过自定义WebViewClient拦截下载事件,借助系统下载管理器完成文件下载流程。
具体实现步骤
1. 创建Android平台自定义WebView处理类
在Android项目的Platforms/Android目录下新建CustomWebViewHandler.cs文件:
using Android.Content; using Android.Webkit; using Microsoft.Maui.Platform; namespace YourAppNamespace.Platforms.Android; public class CustomWebViewClient : MauiWebViewClient { private readonly Context _context; public CustomWebViewClient(Context context) : base(context) { _context = context; } // 拦截下载请求 public override void OnDownloadStart(Android.Webkit.WebView view, string url, string userAgent, string contentDisposition, string mimetype, long contentLength) { base.OnDownloadStart(view, url, userAgent, contentDisposition, mimetype, contentLength); // 调用系统下载管理器处理下载 var downloadManager = (DownloadManager)_context.GetSystemService(Context.DownloadService); var uri = Android.Net.Uri.Parse(url); var request = new DownloadManager.Request(uri); // 配置下载通知与保存路径 request.SetNotificationVisibility(DownloadManager.Request.VisibilityVisibleNotifyCompleted); request.SetTitle(ExtractFileName(contentDisposition)); request.SetDescription("文件下载中"); request.SetDestinationInExternalPublicDir(Android.OS.Environment.DirectoryDownloads, ExtractFileName(contentDisposition)); // 启动下载任务 downloadManager.Enqueue(request); } // 从Content-Disposition头中提取文件名 private string ExtractFileName(string contentDisposition) { if (string.IsNullOrWhiteSpace(contentDisposition)) return "未知文件"; var fileName = "未知文件"; foreach (var part in contentDisposition.Split(';')) { var trimmedPart = part.Trim(); if (trimmedPart.StartsWith("filename=", StringComparison.OrdinalIgnoreCase)) { fileName = trimmedPart.Substring(9).Trim('"', '\''); break; } } return fileName; } }
2. 注册自定义WebView客户端
在Android项目的MainApplication.cs中添加注册逻辑:
using Microsoft.Maui.Controls.Hosting; using YourAppNamespace.Platforms.Android; namespace YourAppNamespace; [Application] public class MainApplication : MauiApplication { public MainApplication(IntPtr handle, JniHandleOwnership ownership) : base(handle, ownership) { } protected override MauiApp CreateMauiApp() => MauiProgram.CreateMauiApp(); protected override void OnCreate() { base.OnCreate(); // 绑定自定义WebView客户端 Microsoft.Maui.Controls.Handlers.WebViewHandler.Mapper.AppendToMapping("CustomDownloadHandler", (handler, view) => { if (handler.PlatformView is Android.Webkit.WebView webView) { webView.SetWebViewClient(new CustomWebViewClient(handler.Context)); } }); } }
3. 添加必要权限
在Android项目的Platforms/Android/AndroidManifest.xml中补充权限声明:
<uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" android:maxSdkVersion="32" /> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" android:maxSdkVersion="32" />
注:Android 13及以上版本无需读写外部存储权限,系统下载管理器会自动处理文件存储。
4. 共享项目WebView代码保持不变
原有WebView的使用无需修改:
<WebView x:Name="WebView" Source="你的目标网页地址" />
关键说明
OnDownloadStart方法会在WebView检测到下载请求时触发,直接调用系统下载管理器可避免手动处理下载进度、文件存储等复杂逻辑。ExtractFileName方法专门解析Content-Disposition头中的文件名,保证下载后文件名称符合预期。
内容的提问来源于stack exchange,提问作者Edgar
相关产品推荐
相关产品推荐

