WPF学习篇 之 自定义控件 动态换肤

网上很多的动态换肤的文章,我这记录下自己开发一个控件时候,写的换肤程序.

 首先,写一个资源文件(xaml)

<?xml version="1.0" encoding="utf-8"?>
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:tsc="clr-namespace:BOCO.IMP.Gui.TopoSubject.Controls"
    >
 
    <!--NodeUI MSC Template-->
    <DataTemplate x:Key="NodeDataTemplate_MSC">
      <StackPanel Cursor="Hand" Orientation="Vertical" Background="Transparent">
        <Image Grid.Row="0" Height="30" Grid.Column="0" Source="../Images/MSC.ico"
           HorizontalAlignment="Center" VerticalAlignment="Top"/>
        <TextBlock Grid.Row="0" Grid.Column="1" Text="{Binding Path=Tag}"
                   VerticalAlignment="Center" HorizontalAlignment="Center"
                   FontFamily="宋体" FontSize="10" ClipToBounds="False">
          <TextBlock.Foreground>
            <SolidColorBrush Color="{Binding Path=Tag.Severity,Mode=OneWay,Converter={x:Static tsc:SeverityColorConverter.Default}}"/>
          </TextBlock.Foreground>
        </TextBlock>
      </StackPanel>
    </DataTemplate>

    <!--NodeUI BSC Template-->
    <DataTemplate x:Key="NodeDataTemplate_BSC">
      <StackPanel Cursor="Hand" Orientation="Vertical" Background="Transparent">
        <Image Grid.Row="0"  Height="30" Source="../Images/TMSC.ico"
           HorizontalAlignment="Center" VerticalAlignment="Top"/>
        <TextBlock Grid.Row="1" Text="{Binding Path=Tag}"
                   VerticalAlignment="Center" HorizontalAlignment="Center"
                   FontFamily="宋体" FontSize="10" ClipToBounds="False">
          <TextBlock.Foreground>
            <SolidColorBrush Color="{Binding Path=Tag.Severity,Mode=OneWay,Converter={x:Static tsc:SeverityColorConverter.Default}}"/>
          </TextBlock.Foreground>
        </TextBlock>
      </StackPanel>
    </DataTemplate>

    <!--NodeUI Default Template-->
    <DataTemplate x:Key="NodeUITemplate">
      <StackPanel Cursor="Hand" Orientation="Vertical" Background="Transparent">
        <Image Grid.Row="0"  Height="30" Source="../Images/GMSC.ico"
            HorizontalAlignment="Center" VerticalAlignment="Top"/>
        <TextBlock Grid.Row="1" Text="{Binding Path=Tag}"
                   VerticalAlignment="Center" HorizontalAlignment="Center"
                   FontFamily="宋体" FontSize="10" ClipToBounds="False">
          <TextBlock.Foreground>
            <SolidColorBrush Color="{Binding Path=Tag.Severity,Mode=OneWay,Converter={x:Static tsc:SeverityColorConverter.Default}}"/>
        
          </TextBlock.Foreground>
        </TextBlock>
      </StackPanel>
    </DataTemplate>
   
</ResourceDictionary>

然后写个DataTemplateSelector.

  public class NodeTemplateSelector : DataTemplateSelector
    {
        private static NodeTemplateSelector instance;
        public static NodeTemplateSelector Instance
        {
            get
            {
                if (instance == null)
                {
                    instance = new NodeTemplateSelector();
                    Uri tempUri = new Uri("/BOCO.IMP.Gui.TopoSubject.Controls;component/Resources/ControlTemplate/ElementTemplates.xaml", UriKind.RelativeOrAbsolute);
                    elementTemplatesResource = Application.LoadComponent(tempUri) as ResourceDictionary;
                }
                return instance;
            }
        }
        public override DataTemplate SelectTemplate(object item, DependencyObject container)
        {
            if (item != null && item is Node)
            {
                Node node = (Node)item;

                string nodeType = ((NeWrapper)node.Tag).NeType.ToString();

                DataTemplate datatemplate;
                if (!dictionaryTemplate.TryGetValue(nodeType, out datatemplate))
                {
                  datatemplate = elementTemplatesResource["NodeDataTemplate_" + nodeType.ToString().Trim()]  as DataTemplate;
                  if (datatemplate == null)
                      datatemplate = elementTemplatesResource["NodeUITemplate"] as DataTemplate;
                  dictionaryTemplate[nodeType] = datatemplate;
                }
                return datatemplate;
            }
            return null;
        }
        static ResourceDictionary elementTemplatesResource;
        static Dictionary<string, DataTemplate> dictionaryTemplate = new Dictionary<string, DataTemplate>();


    }

 

使用的时候: <ControlTemplate TargetType="{x:Type ovt:NodeUI}">
              <ContentPresenter Content="{Binding}"
                                ContentTemplateSelector="{x:Static tsc:NodeTemplateSelector.Instance}" />
            </ControlTemplate>

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
WPF MVVM模式中,可以通过在ViewModel中使用ObservableCollection来动态添加自定义件。ObservableCollection是.NET Framework提供的一个集合类,它能够在集合元素发生变化时自动通知界面进行更新。 首先,在ViewModel中声明一个ObservableCollection属性,用于存储自定义件的集合。然后,在需要添加自定义件的地方,通过操作ObservableCollection来添加新的件。ViewModel会自动通知界面进行更新。 接下来,界面需要绑定这个ObservableCollection属性,并使用数据模板来定义如何渲染每个自定义件。在XAML中,可以使用ItemsControl或者ListBox等件来展示这个集合,并通过绑定将集合和数据模板关联起来。 在这个过程中,可以根据需要使用拖放、缩放、旋转等功能。可以参考中的示例代码,了解如何实现这些功能。 最后,通过实例化ViewModel,并将其赋值给界面的DataContext属性,从而建立ViewModel和View之间的关联。可以参考中的代码。 总结起来,实现在WPF MVVM模式中动态添加自定义件的步骤为: 1. 在ViewModel中声明一个ObservableCollection属性,用于存储自定义件的集合; 2. 在需要添加自定义件的地方,通过操作ObservableCollection来添加新的件; 3. 在界面中,绑定这个ObservableCollection属性,并使用数据模板来定义如何渲染每个自定义件; 4. 根据需要使用拖放、缩放、旋转等功能; 5. 实例化ViewModel,并将其赋值给界面的DataContext属性,建立ViewModel和View之间的关联。 希望这个实现思路对你有帮助,如果需要更详细的代码示例,可以参考中的文章。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *3* [用WPF mvvm如何动态添加自定义件问题](https://blog.csdn.net/netyou/article/details/104371498)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v92^chatsearchT3_1"}}] [.reference_item style="max-width: 50%"] - *2* [WPF Prism MVVM【动态添加件并可用鼠标、拖动、缩放、旋转】](https://blog.csdn.net/redfox6843/article/details/126117819)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v92^chatsearchT3_1"}}] [.reference_item style="max-width: 50%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值