Eu tenho um enum como este:
public enum MyLovelyEnum
{
FirstSelection,
TheOtherSelection,
YetAnotherOne
};
Eu tenho uma propriedade no meu DataContext:
public MyLovelyEnum VeryLovelyEnum { get; set; }
E eu tenho três RadioButtons no meu cliente WPF.
<RadioButton Margin="3">First Selection</RadioButton>
<RadioButton Margin="3">The Other Selection</RadioButton>
<RadioButton Margin="3">Yet Another one</RadioButton>
Agora, como vinculo os RadioButtons à propriedade para uma ligação bidirecional adequada?
Respostas:
Você poderia usar um conversor mais genérico
E na parte XAML você usa:
fonte
Você pode simplificar ainda mais a resposta aceita. Em vez de digitar as enumerações como seqüências de caracteres no xaml e fazer mais trabalho no conversor do que o necessário, você pode transmitir explicitamente o valor da enumeração, em vez de uma representação de sequência, e, como comentou o CrimsonX, os erros são gerados no momento da compilação, em vez do tempo de execução:
ConverterParameter = {x: local estático: YourEnumType.Enum1}
Em seguida, simplifique o conversor:
Editar (16 de dez '10):
Agradecemos a anon por sugerir o retorno de Binding.DoNothing em vez de DependencyProperty.UnsetValue.Nota - Vários grupos de RadioButtons no mesmo contêiner (17 de fevereiro de 11):
No xaml, se os botões de opção compartilharem o mesmo contêiner pai, a seleção de um desmarcará todos os outros contidos nesse contêiner (mesmo que estejam vinculados a uma propriedade diferente). Portanto, tente manter o seu RadioButton vinculado a uma propriedade comum agrupada em seu próprio contêiner como um painel de pilha. Nos casos em que seus RadioButtons relacionados não possam compartilhar um único contêiner pai, defina a propriedade GroupName de cada RadioButton como um valor comum para agrupá-los logicamente.Editar (5 de abril de 11):
Caso contrário do ConvertBack simplificado para usar um Operador Ternário.Nota - Tipo de enum aninhado em uma classe (28 de abril de 11):
Se o seu tipo de enumeração estiver aninhado em uma classe (em vez de diretamente no espaço de nomes), você poderá usar a sintaxe '+' para acessar a enumeração no XAML, conforme indicado em uma resposta (não marcada) à pergunta Não é possível encontrar tipo de enum para referência estática no WPF :ConverterParameter = {x: local estático: YourClass + YourNestedEnumType.Enum1}
Devido a este problema do Microsoft Connect , no entanto, o designer no VS2010 não carregará mais a declaração
"Type 'local:YourClass+YourNestedEnumType' was not found."
, mas o projeto é compilado e executado com êxito. Obviamente, você pode evitar esse problema se conseguir mover seu tipo de enum diretamente para o espaço para nome.Editar (27 de janeiro de 12):
Se estiver usando sinalizadores Enum, o conversor seria o seguinte:Editar (7 de maio de 15):
No caso de um Enum Nullable (que não é perguntado na pergunta, mas pode ser necessário em alguns casos, por exemplo, ORM retornando nulo do DB ou sempre que possa fazer sentido que na lógica do programa o valor não seja fornecido), lembre-se de adicionar uma verificação nula inicial no método Convert e retorne o valor bool apropriado, que normalmente é falso (se você não deseja selecionar nenhum botão de opção), como abaixo:Nota - NullReferenceException (10 de outubro de 18):
Atualizado o exemplo para remover a possibilidade de lançar uma NullReferenceException.IsChecked
é um tipo anulável, portanto, retornarNullable<Boolean>
parece uma solução razoável.fonte
Para a resposta EnumToBooleanConverter: em vez de retornar DependencyProperty.UnsetValue, considere retornar Binding.DoNothing para o caso em que o valor do botão de opção IsChecked se torna falso. O primeiro indica um problema (e pode mostrar ao usuário um retângulo vermelho ou indicadores de validação semelhantes), enquanto o último apenas indica que nada deve ser feito, que é o que se deseja nesse caso.
http://msdn.microsoft.com/en-us/library/system.windows.data.ivalueconverter.convertback.aspx http://msdn.microsoft.com/en-us/library/system.windows.data.binding .donothing.aspx
fonte
Eu usaria os RadioButtons em um ListBox e vincularia ao SelectedValue.
Este é um tópico mais antigo sobre este tópico, mas a ideia base deve ser a mesma: http://social.msdn.microsoft.com/Forums/en-US/wpf/thread/323d067a-efef-4c9f-8d99-fecf45522395/
fonte
Para o UWP, não é tão simples: você deve pular um aro extra para passar um valor de campo como parâmetro.
Exemplo 1
Válido para WPF e UWP.
Exemplo 2
Válido para WPF e UWP.
Exemplo 3
Válido apenas para o WPF!
UWP não suporta,
x:Static
portanto o Exemplo 3 está fora de questão; supondo que você siga o exemplo 1 , o resultado é um código mais detalhado. O exemplo 2 é um pouco melhor, mas ainda não é o ideal.Solução
Em seguida, para cada tipo que você deseja oferecer suporte, defina um conversor que contenha o tipo de enumeração.
O motivo pelo qual ele deve ser encaixotado é que aparentemente não há como referenciar o tipo no
ConvertBack
método; o boxe cuida disso. Se você seguir um dos dois primeiros exemplos, poderá referenciar o tipo de parâmetro, eliminando a necessidade de herdar de uma classe in a box; se você deseja fazer tudo em uma linha e com o mínimo de detalhamento possível, a última solução é ideal.O uso se assemelha ao Exemplo 2 , mas é, de fato, menos detalhado.
A desvantagem é que você deve definir um conversor para cada tipo que deseja oferecer suporte.
fonte
Eu criei uma nova classe para manipular RadioButtons e CheckBoxes a enumerações. Funciona para enumerações sinalizadas (com várias seleções de caixas de seleção) e enumerações não sinalizadas para caixas de seleção de seleção única ou botões de opção. Também não requer nenhum ValueConverters.
Isso pode parecer mais complicado no começo, no entanto, depois que você copia essa classe em seu projeto, está pronto. É genérico e pode ser reutilizado facilmente para qualquer enumeração.
E para saber como usá-lo, digamos que você tenha uma enumeração para executar uma tarefa manual ou automaticamente, e pode ser agendado para qualquer dia da semana e algumas opções opcionais ...
Agora, veja como é fácil usar esta classe:
E aqui está como é fácil vincular caixas de seleção e botões de opção a esta classe:
fonte
EnumSelection<StartTask>
objeto. Se você olhar para a definição,EnumSelection<T>
poderá ver que ela possui uma propriedade Value. Portanto, o modelo de visualização não precisa ter uma "SelectedStartTask". Você usariaStartUp.Value
. E, para ter um valor padrão de Indefinido, consulte o 3º enum, AdditionalOptions, ele possui None em vez de Indefinido, mas você pode alterar o nome para o que quiser.Este trabalho para a caixa de seleção também.
Vincular uma única enumeração a várias caixas de seleção.
fonte
Baseado no EnumToBooleanConverter de Scott. Notei que o método ConvertBack não funciona no código Enum com sinalizadores.
Eu tentei o seguinte código:
A única coisa que não consigo trabalhar é fazer um elenco de
int
para,targetType
então eu o codifiquei paraNavigationProjectDates
o enum que eu uso. EtargetType == NavigationProjectDates
...Edite para um conversor genérico de Flags Enum:
fonte
Você pode criar os botões de opção dinamicamente,
ListBox
pode ajudá-lo a fazer isso, sem conversores, bastante simples.As etapas do concreate estão abaixo: crie um ListBox e defina o ItemsSource para o listbox como a enumeração
MyLovelyEnum
e vinculando o SelectedItem do ListBox àVeryLovelyEnum
propriedade Em seguida, os botões de opção para cada ListBoxItem serão criados.Control Template
para preencher cada item dentro como botão de opçãoA vantagem está abaixo: se algum dia sua classe enum mudar, você não precisará atualizar a GUI (arquivo XAML).
Referências: https://brianlagunas.com/a-better-way-to-data-bind-enums-in-wpf/
fonte