zoukankan      html  css  js  c++  java
  • silverlight:ListBox中如何取得DateTemplate/ItemsPanelTemplate中的命名控件?

    Xaml如下:
    代码
    <UserControl x:Class="ToolsTest.Test"
        xmlns
    ="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
        xmlns:x
    ="http://schemas.microsoft.com/winfx/2006/xaml" 
        Width
    ="400" Height="300">
        
    <UserControl.Resources>
            
    <DataTemplate x:Key="dt">
                
    <TextBlock Padding="5,0,5,0"  Text="{Binding d}" x:Name="myTxt"/>
            
    </DataTemplate>
        
    </UserControl.Resources>
        
    <StackPanel>
            
    <ListBox Name="myListBox" ItemTemplate="{StaticResource dt}" />      
            
    <Button Content="查找myTxt" x:Name="btnFind" Width="90" Click="btnFind_Click"></Button>
        
    </StackPanel>
    </UserControl>

    Xaml.cs如下:

    代码
    using System.Collections.ObjectModel;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Media;

    namespace ToolsTest
    {
        
    public partial class Test : UserControl
        {
            ObservableCollection
    <TestData> oc;

            
    public Test()
            {
                InitializeComponent();
                
    this.Loaded += new RoutedEventHandler(Test_Loaded);
            }

            
    void Test_Loaded(object sender, RoutedEventArgs e)
            {
                oc 
    = new ObservableCollection<TestData>();
                oc.Add(
    new TestData() { d = "A" });
                oc.Add(
    new TestData() { d = "B" });
                
    this.myListBox.ItemsSource = oc;
            }       

            
    private void btnFind_Click(object sender, RoutedEventArgs e)
            {
                
    if (myListBox.SelectedItem != null)
                {
                    ListBoxItem _selectedItem 
    = (ListBoxItem)(myListBox.ItemContainerGenerator.ContainerFromItem(myListBox.SelectedItem));
                    TextBlock myTxt 
    = FindFirstVisualChild<TextBlock>(_selectedItem, "myTxt");
                    MessageBox.Show(
    string.Format("选中行的TextBlock值为:" + myTxt.Text));
                }
               

                ListBoxItem _firstItem 
    = (ListBoxItem)(myListBox.ItemContainerGenerator.ContainerFromItem(myListBox.Items[0]));

                
    //var t =  _firstItem.FindName("myTxt");//这样是找不到的
                TextBlock myTxtFirst = FindFirstVisualChild<TextBlock>(_firstItem, "myTxt");
                MessageBox.Show(
    string.Format("第一行的TextBlock值为:" + myTxtFirst.Text));
            }
           

            
    public T FindFirstVisualChild<T>(DependencyObject obj,string childName) where T : DependencyObject
            {
                
    for (int i = 0; i < VisualTreeHelper.GetChildrenCount(obj); i++)
                {
                    DependencyObject child 
    = VisualTreeHelper.GetChild(obj, i);
                    
    if (child != null && child is T && child.GetValue(NameProperty).ToString()==childName)
                    {
                        
    return (T)child;
                    }
                    
    else
                    {
                        T childOfChild 
    = FindFirstVisualChild<T>(child,childName);
                        
    if (childOfChild != null)
                        {
                            
    return childOfChild;
                        }
                    }
                }
                
    return null;
            }
        }

        
    public class TestData{public string d{set;get;}}
    }

    这里我们借助VisualTreeHelper对指定行(ListBoxItem)做了一个遍历,以查找符合要求的控件

    对于ItemsPanelTemplate中的命名控件,比如下面这样的:

    代码
    <ListBox>
                
    <ItemsPanelTemplate>
                    
    <StackPanel Orientation="Horizontal" x:Name="sp"></StackPanel>
                
    </ItemsPanelTemplate>
                
                
    <ListBox.ItemTemplate>
                    
    <DataTemplate>
                        
    <Rectangle Width="100" Height="100" Fill="{Binding Color}" x:Name="listItem" MouseLeftButtonDown="listItem_MouseLeftButtonDown"></Rectangle>
                    
    </DataTemplate>
                
    </ListBox.ItemTemplate>
            
    </ListBox>

    如果想在listItem_MouseLeftButtonDown中引用sp,按正统处理方法还真是比较麻烦(各位可以google,baidu印证),这里给出一个很取巧的办法:
    <ItemsPanelTemplate>
            <StackPanel Orientation="Horizontal" x:Name="sp" Loaded="sp_Loaded"></StackPanel>
    </ItemsPanelTemplate>
    然后在后端代码中,添加一个私有变量,并处理sp_Loaded事件:

     StackPanel _sp = null;
     private void sp_Loaded(object sender, RoutedEventArgs e)
     {
         _sp = sender as StackPanel;
     }

    这样,在listItem_MouseLeftButtonDown中就能借助"_sp"正确引用到ItemsPanelTemplate中的sp了

    作者:菩提树下的杨过
    出处:http://yjmyzz.cnblogs.com
    本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
  • 相关阅读:
    【Linux】- Systemd 命令篇
    【Linux】- 守护进程的启动方法
    【Linux】- CentOS安装docker及docker-compose
    【Python】- scrapy 爬取图片保存到本地、且返回保存路径
    解决百度ueditor支持iframe框架页面的视频播放问题
    php CURL 请求头和响应头获取
    phpcms pc标签 start不生效的原因
    单点登录的实现
    Linux下删除相互依赖的包
    如何通过js关闭微信浏览器页面
  • 原文地址:https://www.cnblogs.com/yjmyzz/p/1638227.html
Copyright © 2011-2022 走看看