Winform使用Webview2创建界面,配置Router管理界面窗体界面
- 往期目录
- Router的使用
-
- 使用方法
- 配置Router方法
- RouterInfo 配置
- Routers.cs代码文件和使用场景模拟
-
- Routers.cs代码
- RouterUtils.cs代码
- 使用场景
-
- 1.创建窗体程序
- 2.在MainForm窗体上添加`FlowLayoutPanel`用来显示按钮
- 往期目录
往期目录
专栏目录
Router的使用
便于窗口管理,使用统一的路由配置
使用方法
//普通使用 Form form= Routers.Utils.Push('Demo1'); //对 form 做一些其他操作
//定制使用 //根据配置路由获取form Form form = Routers.Utils.CreateForm(routerInfo); //设置参数或添加事件 form.MdiParent = _mainForm; form.WindowState = FormWindowState.Maximized; form.MinimizeBox = false; form.MaximizeBox = false; form.Load+=(object sender,EventArgs:e)=>{ } .... //根据路由配置显示窗口 Routers.Utils.ShowForm(form,routerInfo);
配置Router方法
在
public static List<RouterInfo> List = new List<RouterInfo>() { //创建RouterInfo 对象 new RouterInfo() { //窗口Name 必须唯一 Name="Demo1", //窗口显示文字 Text="Webview2 初始基本HTML展示,回车导航", //是否时多文档窗口 //需要提前为父级多文档窗口设置 MDI //TIP 多文档窗口 和 模态窗口不能同时设置 IsMdiContainer=true , //模态窗口 IsShowDialog=true, //一个描述字段,通常不会使用 Remake="描述字段", //要显示的Form对象 // FormAction方法和Form变量同时设置 会优先使用FormAction Form=new Demo1(), //Form 每次关闭只会隐藏窗口,并不会销毁 FormAction=()=>new Demo1(), //FormAction每次打开都是一个新的窗口 //Form 参数,会存储到Form 的 Tag变量中 Params=( new Dictionary<string, object>(){ { "test1","test2"} }), //Load事件 ,在窗体加载时触发。不会影响原事件 Load=(object sender,EventArgs e) => { MessageBox.Show("Demo1窗体加载了!"); }, }, new RouterInfo(){ ..... }, .... };
RouterInfo 配置
参数 | 类型 | 含义 | 允许空 | 参数 | 返回值 |
---|---|---|---|---|---|
Name | String | 窗口Name 必须唯一 | N | - | - |
Text | String | 窗口显示文字 | Y | - | - |
Remake | String | 描述字段 | Y | - | - |
Params | Dictionary<string, object> | 窗体参数 | Y | - | - |
Form | Form | 要显示的Form对象 | - | - | |
FormAction | FormAction()=>{} | 要显示的Form对象,优先级高于 |
- | Form | |
Load | EventHandler | 窗体加载事件,在窗体加载时触发。不会影响原事件 | Y | - | void |
Routers.cs代码文件和使用场景模拟
创建 Router文件夹,下面创建Routers.cs和RouterUtils.cs文件
Routers.cs代码
?using System; using System.Collections.Generic; using System.Linq; using System.Security.Cryptography; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; using System.Xml.Linq; namespace WinformWebview2.Router { public class Routers { //配置相关窗口信息,假如有一下窗口 Demo1 Demo2 Demo3_1 Demo3_2 public static List<RouterInfo> List = new List<RouterInfo>() { new RouterInfo() { Name="Demo1", Text="Webview2 初始基本HTML展示,回车导航", Form=new Demo1(), Params=( new Dictionary<string, object>(){ { "test1","test2"} }), Load=(object sender,EventArgs e) => { MessageBox.Show("Demo1窗体加载了!"); }, IsShowDialog=true, //模态窗口 }, new RouterInfo() { Name="Demo2", Text="和WebView2 中HTML 和C#之间通信", //Form=new Demo2(), FormAction=()=>new Demo2(), //是否时多文档窗口 //需要提前为父级多文档窗口设置 MDI IsMdiContainer=true , //IsShowDialog=true, //模态窗口 //窗口加载 Load=(object sender,EventArgs e) => { MessageBox.Show("Demo2窗体加载了!"); }, }, new RouterInfo() { Name="Demo3_1", Text="Demo3_1", Form=new Demo3_1(), }, new RouterInfo() { Name="Demo3_2", Text="Demo3_2", Form=new Demo3_1(), }, }; public static RouterUtils Utils = new RouterUtils(List); } }
通过配置进行集中管理
窗体界面 ,后通过调用可以实现页面跳转。
RouterUtils.cs代码
using System.Collections.Generic; using System.Windows.Forms; namespace WinformWebview2.Router { public class RouterUtils { /// <summary> /// 保存路由 /// </summary> public List<RouterInfo> RouteList; public Dictionary<string, RouterInfo> RouteMap = new Dictionary<string, RouterInfo>(); public RouterUtils(List<RouterInfo> _RouteList) { this.RouteList = _RouteList; ///创建 key-value 便于快速查找 _RouteList.ForEach((RouterInfo _route) => { this.RouteMap.Add(_route.Name, _route); }); } /// <summary> /// 获取路由 /// </summary> /// <param name="RouteName">路由唯一标识</param> /// <returns></returns> public RouterInfo GetRouterInfo(string RouteName) { if (this.RouteMap == null || this.RouteMap.Count <= 0) { return null; } return this.RouteMap[RouteName]; } #region 获取窗口 public Form GetForm(RouterInfo routerInfo) { if (routerInfo.FormAction != null) { return routerInfo.FormAction(); } return routerInfo.Form; } #endregion #region 路由跳转 /// <summary> /// 路由跳转 /// </summary> public Form Push(String RouteName) { return this.Push(RouteName, null); } public Form Push(String RouteName, Dictionary<string, object> Params) { RouterInfo routerInfo = this.GetRouterInfo(RouteName); return this.Push(routerInfo, Params); } public Form Push(RouterInfo routerInfo) { return this.Push(routerInfo, null); } public Form Push(RouterInfo routerInfo, Dictionary<string, object> Params) { Form form = this.CreateForm(routerInfo, Params); this.ShowForm(form, routerInfo); return form; } #endregion #region 创建窗口,设置相关参数 public Form CreateForm(RouterInfo routerInfo) { return this.CreateForm(routerInfo, null); } public Form CreateForm(RouterInfo routerInfo, Dictionary<string, object> Params) { Form form = this.GetForm(routerInfo); form.Text = routerInfo.Text; form.Name = routerInfo.Name; ///将form的params存在Tag中 form.Tag = Utils.Utils.MergeDic(Params, routerInfo.Params); if (routerInfo.Load != null) { form.Load += (object sender, EventArgs e) => { routerInfo.Load(sender, e); if (routerInfo.LoadingAfter != null) { form = routerInfo.LoadingAfter(sender, e, form); } }; } form.FormClosing += (object sender, FormClosingEventArgs e) => { if (routerInfo.FormAction == null) { form.Hide(); e.Cancel = true; } }; return form; } #endregion #region 显示窗口 /// <summary> /// 显示窗口 /// </summary> /// <param name="form"></param> /// <param name="isDialog"></param> public void ShowForm(Form form, RouterInfo routerInfo) { this.ShowForm(form, routerInfo.IsShowDialog); } /// <summary> /// 显示窗口 /// </summary> /// <param name="form"></param> /// <param name="isDialog"></param> public void ShowForm(Form form, bool isDialog) { try { if (isDialog) { form.ShowDialog(); return; } form.Show(); } catch(Exception exception) { MessageBox.Show(exception.Message.ToString()); //非顶级窗体不能显示为模式对话框。在调用 showDialog 之前应从所有父窗体中移除该窗体。 //出现以上错误说明:不能同时设置IsMdiContainer和IsShowDialog } } #endregion } public class RouterInfo { /// <summary> /// 路由Name 唯一标识 /// </summary> public string Name; /// <summary> /// 路由地址相关窗口名称 /// </summary> public string Text; /// <summary> /// 路由参数 /// </summary> public Dictionary<string, object> Params; /// <summary> /// 路由对于的窗口 /// </summary> public Form Form; /// <summary> /// 路由对于的窗口 通过函数返回form ,这样在每次调用都可以创建一个新窗口 /// </summary> /// <returns>Form</returns> public delegate Form FormActionHandler(); public FormActionHandler FormAction; /// <summary> /// 是否多文档界面 TIP 需要自行进行关联 /// 需要先设置多文档界面的父级窗口 /// </summary> public bool IsMdiContainer; / <summary> / 多文档界面的父级窗口 / </summary> //public Form MdiParent; /// <summary> /// 是否模态显示 /// </summary> public bool IsShowDialog; /// <summary> /// 描述 /// </summary> public String Remake; /// <summary> /// 窗体的加载事件 /// </summary> /// <returns></returns> public EventHandler Load; /// <summary> /// 在初始化完成后触发事件 /// </summary> /// <param name="form"></param> /// <returns></returns> public delegate Form LoadingAfterAfterHandler(object sender, EventArgs e, Form form); public LoadingAfterAfterHandler LoadingAfter; } }
使用场景
1.创建窗体程序
创建窗体
2.在MainForm窗体上添加FlowLayoutPanel 用来显示按钮
- 将之前的按钮删除掉,使用FlowLayoutPanel布局,设置
Dock 为Top 。 - 在MainForm的构造函数中,通过代码创建button,并和Routers配置关联。
public MainForm() { InitializeComponent(); //创建按钮和按钮事件并添加到FlowLayoutPanel控件上 CreateButton(); } /// <summary> /// 根据路由配置加载按钮 /// </summary> public void CreateButton() { //设置MainForm多文档窗口,如果需要的话,不需要则注释 Form _mainForm = this; //获取路由配置并遍历 Routers.List.ForEach(routerInfo => { //创建按钮 Button button = new Button(); button.Text = routerInfo.Text; button.Name = routerInfo.Name; button.Tag = routerInfo.Params; button.AutoSize = true; //设置按钮点击事件 点击打开窗口 button.Click += (object sender, EventArgs e) => { //根据情况判断要不要设置 多文档窗口 if (routerInfo.IsMdiContainer) { //多文档窗口我们需要获取到对于的form对象 Form form = Routers.Utils.CreateForm(routerInfo); //设置Form窗口为多文档 _mainForm.IsMdiContainer = true; form.MdiParent = _mainForm; //显示窗口 Routers.Utils.ShowForm(form,routerInfo); } else { Routers.Utils.Push(((Control)sender).Name); } }; //添加到FlowLayoutPanel控件上 flyFormPanel.Controls.Add(button); }); }
往期目录
专栏目录