zoukankan      html  css  js  c++  java
  • 使用ListBox中遇到的问题

        这几天一直与ListBox打交道,对ListBox的了解也加深了一层,这篇文章把相关的思路写下来,为了简化起见,省略了一些无关重要的东西

        首先声明数据源对象,这里以一个简单的类为例

        public class Person
    
        {
    
            public string FirstName { get; set; }
    
            public string LastName { get; set; }
    
        }
    
        public class People : ObservableCollection<Person>
    
        {
    
            public List<Person> Detailes { get; set; }
    
            public People()
    
            {
    
                Detailes = new List<Person> 
    
                {
    
                    new Person{FirstName="David",LastName="White"},
    
                    new Person{FirstName="Jim",LastName="Green"},
    
                    new Person{FirstName="Tom",LastName="Polly"}
    
                   
    
                };
    
            }
    
         }

       数据源已经建立好了,现在将其绑定到ListBox中,这里需要横向绑定,SDK中有横向绑定的实现,这里就不再进行细说,按照需求,当鼠标移到FirstName时提示关于LastName的信息,才开始做的时候总是无法显示提示信息,然后在网上找到了原因:附加属性ToolTipService.ToolTip并没有继承上层元素的DataContext

      原因找到了,解决思路就清晰了,先声明一个值转换器

           public class MyConvert : IValueConverter
    
          {
    
            public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    
            {
    
                if (value != null)
    
                {
    
                    var str = value.ToString();
    
                    TextBlock tb = new TextBlock();
    
                    tb.Text = str;
    
                    return tb;
    
                }
    
                return null;
    
            }
    
            ...    
    
         }

      将相关的类声明为资源

            <loacls:People x:Key="people"></loacls:People>
    
            <loacls:MyConvert x:Key="convert"></loacls:MyConvert>

      Xaml代码:

           <Grid  DataContext="{StaticResource people}" >
    
            <ListBox ItemsSource="{Binding Detailes}"                              
    
                     ScrollViewer.VerticalScrollBarVisibility="Hidden">       
    
                <ItemsControl.ItemsPanel>
    
                    <ItemsPanelTemplate>
    
                        <StackPanel Orientation="Horizontal">
    
                        </StackPanel>
    
                    </ItemsPanelTemplate>
    
                </ItemsControl.ItemsPanel>
    
                <ListBox.ItemTemplate>
    
                    <DataTemplate>
    
                        <Grid>
    

    <TextBlock Text="{Binding FirstName}" ToolTipService.Placement="Mouse"

    ToolTipService.ToolTip="{Binding LastName,Converter={StaticResource convert}}" />

                        </Grid>
    
                    </DataTemplate>
    
                </ListBox.ItemTemplate>
    
            </ListBox>
    
         </Grid>

    这样就能够最终显示提示信息了,

      1

    现在我需要将提示信息随鼠标的移动而移动,网上有实现的方法,不过我这里首先要需要解决怎样获取DataTemplate内的控件

           <TextBlock x:Name="myTxt"  MouseMove="TextBlock_MouseMove"  FontFamily="Arial" Foreground="#333333" FontSize="18"  Text="{Binding FirstName}">
    
              <ToolTipService.ToolTip>
    
                <ToolTip x:Name="tip" Placement="Mouse">
    
                  <Binding Path="LastName" Converter="{StaticResource convert}"></Binding>
    
                </ToolTip>
    
             </ToolTipService.ToolTip>
    
           </TextBlock>

    DataTemplate进行了一些改动,那么我需要先获取TextBlock,再获取其中的ToolTip,这个部分参考了园里这篇文章,当鼠标在TextBlock移动时,就进行下面的处理:

           private void TextBlock_MouseMove(object sender, MouseEventArgs e)
    
            {
    
                double x;
    
                Random random = new Random();
    
                x = e.GetPosition(null).X;
    
                ListBoxItem _selectedItem;
    
                if (this.listBox1.SelectedItem != null)
    
                {
    
                   _selectedItem = (ListBoxItem)(this.listBox1.ItemContainerGenerator.ContainerFromItem(this.listBox1.SelectedItem));
    
                }
    
                else
    
                {
    
                   _selectedItem = (ListBoxItem)(this.listBox1.ItemContainerGenerator.ContainerFromItem(this.listBox1.Items[0]));              
    
                }
    
                TextBlock myTxt = FindFirstVisualChild<TextBlock>(_selectedItem, "myTxt");
    
                ToolTip tip = myTxt.FindName("tip") as ToolTip;
    
                if (tip != null)
    
                {
    
                    if (x > 5)
    
                    {
    
                        tip.HorizontalOffset = random.Next(1, 3);
    
                    }
    
                    else
    
                    {
    
                        tip.HorizontalOffset = x;
    
                    }
    
                }
    
            }

            获取可视化的代码也贴出来:

            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;
    
            }
    
    完成以后,就实现选择ListBox的Item时,提示信息就会跟随鼠标的移动而移动了。其实利用上面的方法,也可以动态的改变listboxItem的背景色
            _selectedItem.Background = new SolidColorBrush(Colors.Orange);

            上面所讲用到不少的知识点,希望对你有所帮助,不过上面有个地方我总是无法实现,即如DataGrid那样,将ListBoxItem的背景色进行交替变换,我模仿MSDN上改变 ListView 中各行的背景色进行修改,但是没能实现,只好以后如果解决了再贴出来,如果有朋友实现过这个功能,也请不吝赐教!

          

    代码下载:ListBoxExample.rar

  • 相关阅读:
    hdu 2680(最短路)
    hdu 1548(最短路)
    hdu 1596(最短路变形)
    hdu 1546(dijkstra)
    hdu 3790(SPFA)
    hdu 2544(SPFA)
    CodeForces 597B Restaurant
    CodeForces 597A Divisibility
    CodeForces 598E Chocolate Bar
    CodeForces 598D Igor In the Museum
  • 原文地址:https://www.cnblogs.com/626498301/p/1833151.html
Copyright © 2011-2022 走看看