2012-12-20 19 views
6

Rozejrzałem się, znalazłem kilka rzeczy i utknąłem na combobox z dwoma kolumnami wyświetlanymi w rozwijanym obszarze. Mam dostępne motywy xaml, a styl "combobox" jest zdefiniowany i działa dobrze zgodnie z oczekiwaniami, więc część jest w porządku.Combobox w stylu WPF z dwoma kolumnami w rozwijanym menu

Teraz mam combobox, że muszę mieć wyświetlanie dwóch wartości, myślę, że jest to Skrót stanu i Nazwa państwa dla rozwijanej, pochodzących ze źródła danych DataTable.DefaultView dla elementów.

Jeśli mam

<my:cboStates TextSearch.TextPath="StateAbbrev"> 
    <ComboBox.ItemTemplate> 
    <DataTemplate> 
     <StackPanel Orientation="Horizontal" TextSearch.Text="{Binding Path=StateAbbrev}"> 
     <TextBlock Text="{Binding Path=StateAbbrev}"/> 
     <TextBlock Text="{Binding Path=FullStateName}" Margin="10 0"/> 
     </StackPanel> 
    </DataTemplate> 
    </ComboBox.ItemTemplate> 
</my:cboStates> 

to działa. Teraz, jak/gdzie utknąłem ... Teraz chcę tej samej funkcjonalności na przykład 5 różnych formularzy i wszystkich, aby wyświetlać tę samą treść i jeśli kiedykolwiek się zmieniono (nie to, ale w przypadku innych comboboxów z wieloma kolumnami), Nie chcę ciągle umieszczać tego bezpośrednio w pliku XAML formularza.

Miałem nadzieję na umieszczenie w pliku słownika zasobów kompozycji i po prostu ciągle go używałam. Ma sens. Jednak, gdy to zrobię, a wiązanie jest do tabeli danych, tylko wyniki dostaję, gdy próbuje zrobić jako styl jest rozwijana przedstawia wartości

System.Data.DataRowView 
System.Data.DataRowView 
System.Data.DataRowView 
System.Data.DataRowView 

zamiast rzeczywistych 2 kolumnach. Oto, co mam w słowniku zasobów "tematu".

<DataTemplate x:Key="myStateComboTemplate" > 
    <StackPanel Orientation="Horizontal" > 
    <TextBlock Text="{Binding Path=StateAbbrev}"/> 
    <TextBlock Text="{Binding Path=FullStateName}"/> 
    </StackPanel> 
</DataTemplate> 

<Style x:Key="StyleMyStatesCombobox" TargetType="{x:Type ComboBox}" 
    BasedOn="{StaticResource MyOtherWorkingComboBoxStyle}" > 
    <Setter Property="TextSearch.TextPath" Value="{Binding Path=StateAbbrev}" /> 
    <Setter Property="ItemTemplate" Value="{StaticResource myStateComboTemplate}" /> 
</Style> 

Tak więc, jeśli mam dwie instancje moja klasa „cboStates” utworzone w formie i ustawić jeden do wyraźnej stylizacji wymienionego pierwszego, jak i drugiego opartego na „styl” otoczeniu, drugi nie przez wyświetla tylko powtórzone wpisy System.Data.DataRowView, a nie rzeczywista zawartość danych.

Czego mi brakuje.

Tak więc, aby wyjaśnić, co szukam ... Zjednoczonych ... dane ex

AL Alabama 
AK Alaska 
AZ Arizona 
AR Arkansas 
CA California 
CO Colorado 
CT Connecticut 
DE Delaware 

chcę combobox do wyświetlania skrótu AL, AK, AZ, etc i węższy combobox. Będzie to również TAKŻE "Po wybraniu" po powrocie.

Rzeczywiste menu rozwijane przedstawiałoby powyższe dane pokazując ZARÓWNO skrót ORAZ długi opis stanu.

próbki pożądanego combobox

enter image description here

+0

Jakiś powód, dla którego nie możesz połączyć tych dwóch elementów razem? Myślałem, że zawsze możesz spróbować użyć krotki, ale nie wiesz, jak to zadziała. –

+0

@Bob, uważany za Tuple'a, ale był to tylko uproszczony przykład tego, co zostanie zapełnione w comboboxie, który każdy może zrozumieć. W rzeczywistości będę miał wiele podobnych comboboxów, które będą miały dane pochodzące z tabel i mogą się różnić, a więc nie będą to wartości stałe. Nie chciałem przesyłać zapytań do bazy danych, a następnie przepuszczać i umieszczać w kolejnej pamięci Tuple, aby ponownie przeanalizować klucz/wartość/wartość alt/dodatkowy klucz, itp. W zależności od potrzeb z prezentacji combobox. – DRapp

+0

Co z 'Słownikiem '? Przypisz 'Key' do jednego' TextBlock' i 'Value' do drugiego' TextBlock'? A może jest więcej niż dwa wiersze? –

Odpowiedz

0

wreszcie to działa ... i dla tych, którzy próbują podobne. Ponieważ starałem się mieć standardową instancję "klasy", która mogłaby być używana w całym tekście, ale nie chciałbym jawnie odnosić się do XAML na każdej stronie, część stylizacji musiała być obsługiwana podczas rzeczywistej instancji klasy in-code.

Ponieważ nie wiem dokładnie jak/kiedy gdzie struktura .net buduje wszystkie elementy sterujące, przypisania stylów itp., Denerwowałem się, że zadziała, jeśli jest to bezpośrednio z xaml, ale kończy się niepowodzeniem w kodzie. Tak, skończyłem FORCING wartości szablonu i wartości TextSearch.TextPath w kodzie. Oto krótki fragment klasy

public class myStatesCombo : ComboBox 
{ 
    public myStatesCombo() 
    { 
     Loaded += myAfterLoaded; 
    } 

    protected static DataTable myTableOfStates; 

    public void myAfterLoaded() 
    { 
     if(myTableOfStates == null) 
     myTableOfStates = new DataTable(); 

     CallProcedureToPopulateStates(myTableOfStates); 

     ItemsSource = myTableOfStates.DefaultView; 

     // AFTER the object is created, and all default styles attempted to be set, 
     // FORCE looking for the resource of the "DataTemplate" in the themes.xaml file 
     object tryFindObj = TryFindResource("myStateComboTemplate"); 
     if(tryFindObj is DataTemplate) 
     ItemTemplate = (DataTemplate)tryFindObj; 

     // NOW, the CRITICAL component missed in the source code 
     TextSearch.SetTextPath(this, "StateAbbrev"); 
    } 
} 

Teraz specjalna uwaga.W procedurze, w której wypełniałem DataTable, wstępnie sprawdzam, czy tabela istnieje, czy nie. Po raz pierwszy tworzę stół. Jeśli muszę go ponownie wypełnić, jeśli po prostu wykonuję "nową" tabelę danych za każdym razem, powoduje to dezaktywację powiązań szablonów danych/elementów. Aby temu zapobiec, bym wtedy zrobić

if(myTableOfStates.Rows.Count > 0) 
    myTableOfStates.Rows.Clear(); 

Potem zadzwonić do mojego

SQLExecute wezwanie do zapytania z bazy danych (DataAdapter) i Fill() DataTable.

Teraz wszystko wydaje się być wypełnione poprawnie, powiązania wyświetlacza i wyszukiwanie tekstu są kompletne i gotowe do działania.