2013-06-05 221 views
9

我想滾動到視圖中,以便垂直listivew中最後一項始終顯示,但ListView.ScrollIntoView()從不起作用。爲什麼ListView.ScrollIntoView不能正常工作?

我曾嘗試:

button1_Click(object sender, EventArgs e) 
{ 

      activities.Add(new Activities() 
      { 
       Time = DateTime.Now, 
       Message = message 
      }); 

      ActivityList.ItemsSource = activities; 

      // Go to bottom of ListView. 
      ActivityList.SelectedIndex = ActivityList.Items.Count; 
      ActivityList.ScrollIntoView(ActivityList.SelectedIndex); 
} 

我也曾嘗試:

ActivityList.ScrollIntoView(ActivityList.Items.Count)ActivityList.ScrollIntoView(ActivityList.Items.Count + 1);但沒有什麼工作。

請幫忙。這真的很煩人。在這種情況下文檔isn't very helpful

回答

12

當方法需要項目對象時,您正在傳入索引。試試這個來滾動到選定的項目。

ActivityList.ScrollIntoView(ActivityList.SelectedItem); 

如果你想滾動到最後一個項目,你可以使用這個

ActivityList.ScrollIntoView(ActivityList.Items[ActivityList.Items.Count - 1]); 
+1

對不起上班,我忘了說,這是我想的第一件事情(按照文檔)。那也行不通。 –

+1

'SelectedIndex'也設置在項目listl之外。如果,那麼它應該是'ActivityList.SelectedIndex = ActivityList.Items.Count - 1' – dkozl

+2

+1 @dkozl'SelectedIndex'值。 Jase,如果仍然不起作用,請在'ScrollIntoView'方法之前嘗試調用'ActivityList.UpdateLayout();'。 – keyboardP

1

要指定項目的索引和列表框預計項目本身。 嘗試是這樣的:

var activity = new Activities() 
     { 
      Time = DateTime.Now, 
      Message = message 
     }; 

activities.Add(activity); 

ActivityList.ItemsSource = activities; 
ActivityList.ScrollIntoView(activity); 
+0

這是一個ListView。我最初分配的實際對象(ListView.SelectedItem),但沒有奏效。我忘了在我的問題中提出這個問題,因爲我已經嘗試了十幾件事情來嘗試並使其發揮作用。我實際上在這裏處理一個ListView,而不是一個ListBox,但MSDN鏈接到ListView.ScrollIntoView()鏈接的ListBox頁面。正如你可以從這裏看到的:http://msdn.microsoft.com/en-us/library/system.windows.controls.listview.aspx –

8

它有事情做與內部列表表示,即項目尚未到位,當你調用ScrollIntoView().多次嘗試後,這是我終於想出了這似乎工作:重視處理每一個ListBox/ListView:

​​

void YourList_Loaded(object sender, RoutedEventArgs e) { 
    if (YourList.SelectedItem != null) 
    YourList.ScrollIntoView(YourList.SelectedItem); 
} 

void YourList_SelectionChanged(object sender, SelectionChangedEventArgs e) { 
    if (YourList.SelectedItem != null) 
    YourList.ScrollIntoView(YourList.SelectedItem); 
} 

你不能沒有的第二個處理程序。設置所選項目後,您不能立即致電ScrollIntoView(),但尚未準備就緒。您必須讓列表在其實際更改項目時通知您。第一個處理程序取決於具體情況,如果您在初始加載列表內容後顯示的選擇有問題,則可能也需要它。

+1

這個解決方案適合我! – sharpguru

3

的問題ActivityList.ScrollIntoView(ActivityList.Items[ActivityList.Items.Count - 1]); 和similiar的「解決方案」,至少從什麼我遇到了,就是當列表框包含相同的項目超過一次,它跳轉到它找到的第一個,即最低指數。所以,它不關心你輸入的物品的索引,它只是尋找那個物品並選擇第一個物品。

我還沒有找到一個解決的辦法,但我考慮現在採取的辦法是插入而不是添加物品。在原來的海報的情況下,我認爲這將導致:

activities.Insert(0, new Activities() 
     { 
      Time = DateTime.Now, 
      Message = message 
     }); 

或可能:

ActivityList.Items.Insert(0, new Activities() 
     { 
      Time = DateTime.Now, 
      Message = message 
     }); 

導致每一個新的條目被插在上面,從而ScrollIntoView甚至不需要到叫做。

+0

這是我的問題,但我可以通過在課堂中包裝我的字符串來解決它。 –

0

一個老的文章,但由於沒有一個答案在這裏工作了我的情況我想補充我的實現。 我發現這裏的解決方案:https://social.msdn.microsoft.com/Forums/vstudio/en-US/8a745550-4360-4b53-85f5-032f8f46e2cc/listview-scrollintoview-not-working-with-a-observablecollection?forum=wpf][1]

((INotifyCollectionChanged)lvLogs.Items).CollectionChanged += ListView_CollectionChanged; 

private void ListView_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
{ 
    ScrollToEnd(this.lvLogs); 
} 

private void ListView_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) 
     { 
      if ((e.Action == NotifyCollectionChangedAction.Add) && (e.NewItems != null)) 
      { 
       try 
       { 
        ScrollToEnd(this.lvLogs); 
       } 
       catch (Exception ex) 
       { 
        MessageBox.Show(ex.ToString(), "Error updating list view", MessageBoxButton.OK, MessageBoxImage.Error); 
       } 

      } 
     } 

public void ScrollToEnd(ListView _ListView) 
{ 
    ScrollViewer _ScrollViewer = GetDescendantByType(_ListView, typeof(ScrollViewer)) as ScrollViewer; 
    _ScrollViewer.ScrollToEnd(); 
} 

public Visual GetDescendantByType(Visual element, Type type) 
{ 
    if (element == null) return null; 
    if (element.GetType() == type) return element; 
    Visual foundElement = null; 
    if (element is FrameworkElement) 
    { 
     (element as FrameworkElement).ApplyTemplate(); 
    } 
    for (int i = 0; i < VisualTreeHelper.GetChildrenCount(element); i++) 
    { 
     Visual visual = VisualTreeHelper.GetChild(element, i) as Visual; 
     foundElement = GetDescendantByType(visual, type); 
     if (foundElement != null) 
      break; 
    } 
    return foundElement; 
} 

對我來說完美的作品。

0

我面臨的問題是相似的。我以編程方式添加到列表框,並需要添加最後一個項目才能看到。搭售各種方法後,我發現下面是最簡單和最

lstbox.Items.MoveCurrentToLast(); 
lstbox.ScrollIntoView(lstbox.Items.CurrentItem); 
0

這是一個老的文章,但我已經在Windows商店應用同樣的問題,發現了以下工作:

private void PagesListView_SelectionChanged(object sender, SelectionChangedEventArgs e) 
    { 
     pageListView.UpdateLayout(); 
     pageListView.ScrollIntoView(pageListView.SelectedItem); 
    } 

乾杯, 保羅

0

只需撥打方法UpdateLayout請...

UpdateLayout(); 
ActivityList.ScrollIntoView(ActivityList.Items[ActivityList.Items.Count - 1]); 

這將工作...

或者更簡單的方法...只是編譯應用程序:)而不會導致UpdateLayot()