• Wpf使用Winform控件后Wpf元素被Winform控件遮盖问题的解决


        有人会说不建议Wpf中使用Winform控件,有人会说建议使用Winform控件在Wpf下的替代方案,然而在实际工作中由于项目的特殊需求,考虑到时间、成本等因素,往往难免会碰到在WPF中使用Winfrom控件的问题,我们知道Wpf可以通过使用WindowsFormsHost容器调用Winform控件,但是在一些场合需要将Wpf元素显示在Winform控件的上层,此时就会出现Wpf元素被Winform控件遮盖的问题。

        一、场景再现

        接到公司命令,在时间紧迫的情况下,需要将原来的Winform程序(别人写的,自己压根没参与任何东西)替换成Wpf实现,给界面做个美容。首先看了看源码,了解到里面的知识盲点,主要一个就是用于地图展示的GMap.NET组件(一个开源的GIS二次开发组件),遂对GMap.NET进行了了解:GMap.net分为for winform及form wpf,且在Wpf下没有图层的概念,一些类结构的设计也月GMap.net.winform有变化,为了稳妥,不出现不必要的麻烦,快速改版应对项目要求,考虑仍使用要来的GMap.net.winform,只对展示层做修改。

        1、添加Wpf调用Winform控件需要的两个DLL引用:WindowsFormsIntegration.dllSystem.Windows.Forms.dll以及GMap.Net.WindowsFroms的两个DLL引用:GMap.Net.Core.dll及GMap.Net.WindowsForms.dll。

        2、程序运行时将MapControl控件处理后加载到WindowsFormsHost容器。

        前台关键代码:

    <Window x:Class="WpfApplication3.MainWindow"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            xmlns:wfi ="clr-namespace:System.Windows.Forms.Integration;assembly=WindowsFormsIntegration"
            Title="MainWindow" Height="350" Width="525" Loaded="Window_Loaded">
        <Grid>
            <wfi:WindowsFormsHost x:Name="mapContainer">
            </wfi:WindowsFormsHost>
            <StackPanel VerticalAlignment="Bottom" HorizontalAlignment="Right" Background="Blue" Width="75" Height="45">
            </StackPanel>
        </Grid>
    </Window>
    

          后台关键代码

          private void Window_Loaded(object sender, RoutedEventArgs e)
            {
                GMap.NET.WindowsForms.GMapControl mapControl = new GMap.NET.WindowsForms.GMapControl();
                mapContainer.Child = mapControl;
            }
    

         设计状态时右下角图例区域设置为最顶层,如下图所示没有问题

        程序运行时,winform类型的GMapControl控件会渲染在最上层,覆盖用于显示地图图例区域的右下角Wpf元素。

        二、寻求解决方案

        自己首先尝试了各种WPF界面布局方式,Canvas,各种Panel等都试了一遍,结果仍然是Wpf元素被Winform控件遮盖,遂去寻求网络帮助,得到的答案基本如下:

        三、最终解决方案

        考虑如果是因为渲染机制问题,始终将winform控件渲染在最上层的话,能不能将Wpf元素也使用WindowsFormsHost容器进行一层包裹呢?理论上应该是可以得,于是进行尝试,最外层使用WindosFormsHost,然后是Wpf元素的容器ElementHost,最后是我们需要的WPF界面元素:

    <Window x:Class="WpfApplication3.MainWindow"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            xmlns:wfi ="clr-namespace:System.Windows.Forms.Integration;assembly=WindowsFormsIntegration"
            Title="MainWindow" Height="350" Width="525" Loaded="Window_Loaded">
        <Grid>
            <wfi:WindowsFormsHost x:Name="mapContainer">
            </wfi:WindowsFormsHost>
            <wfi:WindowsFormsHost >
                <ElementHost>
                    <StackPanel VerticalAlignment="Bottom" HorizontalAlignment="Right" Background="Blue" Width="75" Height="45">
                    </StackPanel>
                </ElementHost>
            </wfi:WindowsFormsHost>
    
        </Grid>
    </Window>
    

        运行程序问题解决:

     

     

     

     

  • 相关阅读:
    [BTS2004]一步一步学习BizTalk2004 CBR(contentbased routing)
    [BTS06]BizTalk2006 SDK阅读笔记(六) 定义流程
    [JS]收藏
    [BTS06]BizTalk2006 SDK阅读笔记(七) 管理与监控
    [C#]关于调用Office应用程序后,程序不退出的问题
    [JS]让表单提交返回后保持在原来提交的位置上
    [BTS][收藏]啥时候用BTS,啥时候用WF,就看这里。
    [BTS06]BizTalk2006 SDK阅读笔记(一) 角色
    [BTS]BizTalk学习之Functoid篇(Database Lookup)
    [LCS]半个月的成果,用RTCClient开发的Robot!
  • 原文地址:https://www.cnblogs.com/yigedaizi/p/4392478.html
Copyright © 2020-2023  润新知