Domanda

Io sto usando un ListView per mostrare elementi in un elenco. L'utente può selezionare le voci di se stesso, o utilizzare un po 'di tasti di preselezione' per selezionare gli elementi con gli attributi specificati.

Per controllare gli elementi che uso qualcosa di simile:

for(int i;i<MyListView.Items.Count;++i)
{
    if( /*... Check if the items should be selected ...*/ )
        (MyListView.ItemContainerGenerator.ContainerFromIndex(i) as ListViewItem).IsSelected = true;
}

Questo funziona perfettamente per gli elementi, che sono visibili al momento della excecution. Ma per gli oggetti, che non sono visibili, ContainerFromIndex () restituisce il valore null. Ho sentito questo ha qualcosa a che fare con la virtualizzazione, e che l'elenco non conosce oggetti rialzo o al ribasso il 'campo visivo'. Ma come arriva che è possibile avere gli elementi selezionati nella lista fuorigioco il 'campo visivo', quando si seleziona manualmente?

E come fare una selezione di un elemento al di fuori 'campo visivo'? Penso che deve essere possibile.

Grazie per qualsiasi aiuto, Marks

È stato utile?

Soluzione

Come lei ha ricordato, la mia ipotesi è che il problema è la virtualizzazione degli elementi ListView. Per impostazione predefinita, ListView (e ListBox) l'uso VirtualizingStackPanel come loro ItemsPanel per migliorare le prestazioni. Una breve spiegazione di come funziona può essere letta qui .

E 'possibile sostituire un altro pannello, però. In questo caso, provare a utilizzare uno StackPanel normale. Se si dispone di una tonnellata di elementi nel controllo ListView, soprattutto se sono oggetti complessi, le prestazioni potrebbero soffrire un po '.

<ListView>
    <ListView.ItemsPanel>
        <ItemsPanelTemplate>
            <StackPanel/>
        </ItemsPanelTemplate>
    </ListView.ItemsPanel>
</ListView>

Modifica

Si può anche provare a soluzione descritta in questa domanda simile , a seconda della modello. Tuttavia, questo probabilmente non funzionerà per voi.

Altri suggerimenti

Quando si tratta di virtualizzazione controlli articoli, un'alternativa alla disattivazione di virtualizzazione (che è in realtà una funzione utile, a volte, anche se interferisce con il corretto funzionamento di altre parti della API), è quello di trovare il VirtualizingPanel e dire esplicitamente a scorrimento.

Ad esempio:

void ScrollToIndex(ListBox listBox, int index)
{
    VirtualizingPanel panel = FindVisualChild<VirtualizingPanel>(listBox);

    panel.BringIndexIntoViewPublic(index);
}

static T FindVisualChild<T>(DependencyObject o) where T : class
{
    T result = o as T;

    if (result != null)
    {
        return result;
    }

    int childCount = VisualTreeHelper.GetChildrenCount(o);

    for (int i = 0; i < childCount; i++)
    {
        result = FindVisualChild<T>(VisualTreeHelper.GetChild(o, i));

        if (result != null)
        {
            return result;
        }
    }

    return null;
}

Non sono molto felice con la necessità di cercare attraverso la struttura ad albero visuale per trovare il pannello, ma io non sono a conoscenza di alcun altro modo per farlo, né di scorrimento a un indice specifico quando si tratta di un pannello di Virtualizzazione .

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top