2016-01-24 59 views
0

我在Windows 10中的通用Windows應用程序中有一個xaml頁面。此頁面包含兩個列表框。兩個列表框具有像如何知道在Windows 10中的通用Windows應用程序中關注哪個元素10

public class CategoryModel 
{ 
public int CategoryId {get; set;} 
public string CategoryName {get; set;} 
public List<string> ImageURL {get; set;} 
} 

頂部列表框相同的ItemsSource在水平方式上創建菜單標題和底部列表框在垂直方式在菜單頭的底部創建菜單數據。

問題是如何知道底部的哪個菜單數據元素是焦點,這樣我可以突出顯示菜單頭中的相同元素?

    <ListView x:Name="lvMenuBar" Grid.Column="1" FlowDirection="LeftToRight" ItemsSource="{Binding MenuCategories}" Width="Auto"> 
         <ListView.ItemTemplate> 
          <DataTemplate> 
           <Button Click="MenuBarClick" HorizontalAlignment="Center" VerticalAlignment="Top" Tag="{Binding CategoryId}" Content="{Binding CategoryName}" Style="{StaticResource CustomButtonStyle}" FontFamily="Segoe UI" FontWeight="SemiBold" FontSize="18" Margin="0" Padding="20" BorderBrush="Red" BorderThickness="0" Opacity="0.5" Foreground="Black"/> 
          </DataTemplate> 
         </ListView.ItemTemplate> 
         <ListView.ItemsPanel> 
          <ItemsPanelTemplate> 
           <VirtualizingStackPanel Orientation="Horizontal" /> 
          </ItemsPanelTemplate> 
         </ListView.ItemsPanel> 
        </ListView> 

        <ListView x:Name="lvMenuBar" Grid.Column="1" FlowDirection="LeftToRight" ItemsSource="{Binding MenuCategories}" Width="Auto"> 
         <ListView.ItemTemplate> 
          <DataTemplate>          

以上是我的XAML

+0

你能分享你的XAML的? – 2016-01-24 22:30:01

+0

我真的不明白,你需要知道,對不起。你想知道,底部列表框中的哪個元素被選中,那麼你可以突出顯示頂部列表框中的相同元素? –

+0

是@einRobby。我想突出顯示頂部,取決於底部的菜單元素 – Vantage

回答

0

如果我理解正確的問題,要選擇(或以其他方式突出顯示)的其只要在底部列表中選擇了該項目,就會將它們放在頂部列表中。您可以使用數據綁定做到這一點,例如:

<ListView 
    Grid.Row="0" 
    ItemsSource="{Binding MenuCategories}" 
    Margin="8" 
    SelectedIndex="{Binding SelectedIndex, ElementName=verticalList, Mode=OneWay}" 
    > 

這裏的頂級目錄的SelectedIndex屬性反映了底部列表中。

在上下文中,這樣的事情:

<Page.Resources> 
    <Style x:Key="CustomButtonStyle" TargetType="Button" /> 
</Page.Resources> 
<Grid> 
    <Grid.RowDefinitions> 
     <RowDefinition Height="Auto" /> 
     <RowDefinition Height="*" /> 
    </Grid.RowDefinitions> 
    <ListView 
     Grid.Row="0" 
     ItemsSource="{Binding MenuCategories}" 
     Margin="8" 
     SelectedIndex="{Binding SelectedIndex, ElementName=verticalList, Mode=OneWay}" 
     > 
     <ListView.ItemTemplate> 
      <DataTemplate x:DataType="local:CategoryModel"> 
       <Button 
        HorizontalAlignment="Center" 
        VerticalAlignment="Top" 
        Tag="{Binding CategoryId}" 
        Content="{Binding CategoryName}" 
        Style="{StaticResource CustomButtonStyle}" 
        FontFamily="Segoe UI" 
        FontWeight="SemiBold" 
        FontSize="18" 
        Margin="0" 
        Padding="20" 
        BorderBrush="Red" 
        BorderThickness="0" 
        Opacity="0.5" 
        Foreground="Black"/> 
      </DataTemplate> 
     </ListView.ItemTemplate> 
     <ListView.ItemsPanel> 
      <ItemsPanelTemplate> 
       <VirtualizingStackPanel Orientation="Horizontal" /> 
      </ItemsPanelTemplate> 
     </ListView.ItemsPanel> 
    </ListView> 
    <ListView 
     x:Name="verticalList" 
     Grid.Row="1" 
     ItemsSource="{Binding MenuCategories}" 
     Margin="8" 
     IsItemClickEnabled="True" 
     SelectionMode="Single"> 
     <ListView.ItemTemplate> 
      <DataTemplate x:DataType="local:CategoryModel"> 
       <Button 
        HorizontalAlignment="Center" 
        VerticalAlignment="Top" 
        Tag="{Binding CategoryId}" 
        Content="{Binding CategoryName}" 
        Style="{StaticResource CustomButtonStyle}" 
        FontFamily="Segoe UI" 
        FontWeight="SemiBold" 
        FontSize="18" 
        Margin="0" 
        Padding="20" 
        BorderBrush="Red" 
        BorderThickness="0" 
        Opacity="0.5" 
        Foreground="Black"/> 
      </DataTemplate> 
     </ListView.ItemTemplate> 
     <ListView.ItemsPanel> 
      <ItemsPanelTemplate> 
       <VirtualizingStackPanel Orientation="Vertical" /> 
      </ItemsPanelTemplate> 
     </ListView.ItemsPanel> 
    </ListView> 
</Grid> 

警告:當您點擊一個按鈕,該ListView沒有看到,點擊;如果你想要點擊選擇一個項目,請在代碼隱藏中執行。

還要注意第二個(垂直)列表上的IsItemClickEnabled屬性。


編輯:如果我理解你正確,你想在上部水平列表中的選擇跟蹤滾動在較低的垂直而不是選擇。在這種情況下,你需要獲得的內置ScrollViewer和做這樣的事情擱置:

public MainPage() 
{ 
    InitializeComponent(); 
    DataContext = this; 
    Loaded += (sender, args) => 
     { 
      ScrollViewer scrollViewer = FindVisualChild<ScrollViewer>(verticalList); 
      if (scrollViewer != null) 
      { 
       scrollViewer.ViewChanged += (o, eventArgs) => 
        { 
         int length = MenuCategories.Length; 
         double offset = scrollViewer.VerticalOffset; 
         double height = scrollViewer.ExtentHeight; 
         int index = (int)(length * offset/height); 
         horizontalList.SelectedIndex = index; 
        }; 
      } 
     }; 
} 

private static T FindVisualChild<T>(DependencyObject parent) 
    where T : DependencyObject 
{ 
    if (parent != null) 
    { 
     for (int i = 0; i < VisualTreeHelper.GetChildrenCount(parent); i++) 
     { 
      DependencyObject child = VisualTreeHelper.GetChild(parent, i); 
      T candidate = child as T; 
      if (candidate != null) 
      { 
       return candidate; 
      } 

      T childOfChild = FindVisualChild<T>(child); 
      if (childOfChild != null) 
      { 
       return childOfChild; 
      } 
     } 
    } 

    return default(T); 
} 

你可能需要在這裏的計算實驗;這在我的方面有點實驗。

+0

...如果你想讓下面的列表也反映上面的列表,只要將綁定模式改爲'TwoWay'。:-) –

+0

我想澄清這個答案。這個想法是你的DataContext(你的綁定的來源)和你的XAML中的兩個ListView有一個項目和一個整數。您將集合綁定到ListViews,並將兩個集合的'Mode = TwoWay'綁定到'SelectedItem'。通過這種方式,當從兩個ListView中的任何一箇中選擇一個項目時,該整數的值會更改,另一個ListView會自動進行通知。 – Corcus

+0

你當然可以將'SelectedIndex'綁定到一個屬性,但這對於綁定工作不是必需的。 'SelectedItem'是一個項目引用; 'SelectedIndex'是一個索引。兩者都可用於同步列表,並且您只需在其中一個「TwoWay」綁定上實現該功能即可。 –

0

這段代碼已經解決了很多我的問題

private double _scrollExtentHeight; 
    private ScrollViewer _scrollViewer; 

_scrollViewer = FindVisualChild<ScrollViewer>(lvMenuItems); 
     if (_scrollViewer != null) 
     { 
      _scrollViewer.ManipulationMode = ManipulationModes.TranslateY; 
      _scrollViewer.DirectManipulationCompleted += scrollViewerDirectManipulationCompleted; 
      _scrollExtentHeight = _scrollViewer.ExtentHeight; 
     } 



    private static T FindVisualChild<T>(DependencyObject parent) 
where T : DependencyObject 
    { 
     if (parent != null) 
     { 
      for (int i = 0; i < VisualTreeHelper.GetChildrenCount(parent); i++) 
      { 
       DependencyObject child = VisualTreeHelper.GetChild(parent, i); 
       T candidate = child as T; 
       if (candidate != null) 
       { 
        return candidate; 
       } 

       T childOfChild = FindVisualChild<T>(child); 
       if (childOfChild != null) 
       { 
        return childOfChild; 
       } 
      } 
     } 

     return default(T); 
    } 

    private void scrollViewerDirectManipulationCompleted(object sender, object e) 
    { 
     _menuVM.StartDispatcher(); 
     if (_scrollViewer != null) 
     { 
      int length = _menuVM.Categories.Count; 
      double offset = _scrollViewer.VerticalOffset; 
    //Horizontal scroll viewer 
      List<Button> menuItems = GetAllMenuItemControl(lvMenuBar); 
      int currIndex = 0, index = 0; 
    //Categories height ratio contains the height ratio of each element for total height 
      for (; index < _menuVM.CategoriesHeightRatio.Count; index++) 
      { 
       if ((_menuVM.CategoriesHeightRatio[index - 1 > 0 ? index - 1 : 0] * _scrollExtentHeight) < offset && (_menuVM.CategoriesHeightRatio[index] * _scrollExtentHeight) >= offset) 
       { 
        currIndex = index; 
       } 
       else 
       { 
        menuItems[index].BorderThickness = new Thickness(0, 0, 0, 0); 
        menuItems[index].Opacity = 0.5; 
       } 
      } 
      menuItems[currIndex].BorderThickness = new Thickness(0, 0, 0, 2); 
      menuItems[currIndex].Opacity = 1; 
      var transform = lvMenuBar.TransformToVisual(menuItems[currIndex]); 
      Point absolutePoint = transform.TransformPoint(new Point(0, 0)); 
      svMenuBar.ChangeView(Math.Abs(absolutePoint.X), null, null, false); 
     } 
    } 

    private List<Button> GetAllMenuItemControl(DependencyObject parent) 
    { 
     var _List = new List<Button>(); 
     for (int index = 0; index < VisualTreeHelper.GetChildrenCount(parent); index++) 
     { 
      var _Child = VisualTreeHelper.GetChild(parent, index); 
      if (_Child is Button) 
       _List.Add(_Child as Button); 
      _List.AddRange(GetAllMenuItemControl(_Child)); 
     } 
     return _List; 
    } 
相關問題