WPF项目中使用WInform版本的 ChromiumWebBrowser控件嵌套网页 解决中文输入法候选框定位问题

发布时间 2023-05-06 09:59:41作者: 安静点--

创建一个用户控件,后台代码:

 public partial class CefControl : UserControl
    {
        ChromiumWebBrowser webView = null;
        public CefControl()
        {
            InitializeComponent();


            if (!CefSharp.Cef.IsInitialized)
            {
                var settings = new CefSettings() { RemoteDebuggingPort = 8088 };
                {
                    //By default CefSharp will use an in-memory cache, you need to specify a Cache Folder to persist data
                    var CachePath = System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "CefSharp\\Cache");
                };
                settings.Locale = "zh-CN";
                settings.UserAgent = "Mozilla/5.0 (Windows; U; Windows NT 6.2; zh-CN) AppleWebKit/533+ (KHTML, like Gecko)";
                settings.CefCommandLineArgs.Add("enable-media-stream", "1");
                settings.CefCommandLineArgs.Add("disable-gpu", "1"); // 禁用gpu  
                Cef.Initialize(settings, performDependencyCheck: true, browserProcessHandler: null);

            }

            webView = new ChromiumWebBrowser("https://www.baidu.com/");
            this.Controls.Add(webView);
            webView.Dock = DockStyle.Fill;
            CefSharpSettings.LegacyJavascriptBindingEnabled = true;
            //注册js对象
            JSHelperChrome helper = new JSHelperChrome();
            helper.OpeningFile += Helper_OpeningFile;
            BindingOptions bindingOption = new BindingOptions
            {
                CamelCaseJavascriptNames = false,
                Binder = BindingOptions.DefaultBinder.Binder,
            };
            webView.JavascriptObjectRepository.Register("JSBridge", helper, isAsync: false, options: bindingOption);
            //按F12显示调试工具
            webView.KeyboardHandler = new CEFKeyBoardHander();
            webView.FrameLoadEnd += Webview_FrameLoadEnd;
            webView.FrameLoadStart += WebView_FrameLoadStart;
        }

        private void WebView_FrameLoadStart(object sender, FrameLoadStartEventArgs e)
        {
        }

        private void Webview_FrameLoadEnd(object sender, FrameLoadEndEventArgs e)
        {
            if (e.Frame.IsMain)
            {
                this.webView.ExecuteScriptAsync(@"
                //设置test对象 这样前段页面就能拿到window.test这个参数信息
                window.test = JSBridge;
                //alert('test!');
                ");
            }
        }
        private void Helper_OpeningFile()
        {
        }

        public void WriteLog(string msg)
        {
            FileStream fs = null;
            StreamWriter sw = null;
            try
            {
                var basePath = AppDomain.CurrentDomain.BaseDirectory;
                if (!basePath.EndsWith("/"))
                    basePath += "/";

                var logFile = basePath + "Log";
                if (!File.Exists(logFile))
                    File.CreateText(logFile).Dispose();

                fs = new FileStream(logFile, FileMode.Append, FileAccess.Write, FileShare.ReadWrite);
                sw = new StreamWriter(fs, Encoding.UTF8);

                sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd hh:mm:ss.fff"));
                sw.WriteLine(msg);
                sw.WriteLine("-------------------------------------");
                sw.Flush();
                fs.Flush();
            }
            catch { }
            finally
            {
                if (sw != null)
                {
                    try { sw.Close(); sw.Dispose(); } catch { }
                }
                if (fs != null)
                {
                    try { fs.Close(); fs.Dispose(); } catch { }
                }
            }
        }
    }

    public class CEFKeyBoardHander : IKeyboardHandler
    {
        public bool OnKeyEvent(IWebBrowser browserControl, IBrowser browser, KeyType type, int windowsKeyCode, int nativeKeyCode, CefEventFlags modifiers, bool isSystemKey)
        {
            if (type == KeyType.KeyUp && Enum.IsDefined(typeof(Keys), windowsKeyCode))
            {
                var key = (Keys)windowsKeyCode;
                switch (key)
                {
                    case Keys.F12:
                        browser.ShowDevTools();
                        break;

                    case Keys.F5:

                        if (modifiers == CefEventFlags.ControlDown)
                        {
                            browser.Reload(true); //强制忽略缓存
                        }
                        else
                        {
                            browser.Reload();
                        }
                        break;
                }
            }
            return false;
        }

        public bool OnPreKeyEvent(IWebBrowser browserControl, IBrowser browser, KeyType type, int windowsKeyCode, int nativeKeyCode, CefEventFlags modifiers, bool isSystemKey, ref bool isKeyboardShortcut)
        {
            return false;
        }
    }
    public class JSHelperChrome
    {

        public event Action OpeningFile;

        public JSHelperChrome()
        {

        }

        public void OpenFile(string cloudFileUrl)
        {
            OpeningFile?.Invoke();
        }
    }

 

创建一个WPF Window界面

<Window x:Class="WpfApp1.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApp1"
        mc:Ignorable="d"  WindowState="Maximized" 
        Title="MainWindow" Height="450" Width="800" WindowStyle="SingleBorderWindow">
    <Grid x:Name="root">
        <ContentControl Name="contextHolder" Grid.Row="1"    />
    </Grid>
   

 

后台使用:

    /// <summary>
    /// MainWindow.xaml 的交互逻辑
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            WindowsFormsHost browser = new WindowsFormsHost();
            browser.Child = new CefControl();
            contextHolder.Content = browser;
       
        }
    }