2009-06-08 5 views
15

Je veux dire WPF: membre « Si TextBlock ne contient aucune donnée, alors ne pas le montrer. »Comment faire pour qu'un TextBlock XAML s'effondre lorsqu'il ne contient aucune donnée?

# 1 TRY avec un déclencheur simple, produit l'erreur "« texte » est pas valide parce qu'il ne dispose pas d'un nom de type de qualification « .

<StackPanel Margin="10"> 
    <TextBlock Padding="10" Background="Yellow" Text="{Binding MainMessage}"> 
     <TextBlock.Triggers> 
      <Trigger Property="Text" Value="{x:Null}"> 
       <Setter Property="Visibility" Value="Collapsed"/> 
      </Trigger> 
     </TextBlock.Triggers> 
    </TextBlock> 
</StackPanel> 

# 2 TRY avec un déclencheur de style produit t il l'erreur Le type 'style' ne contient pas une classe publique de type convertisseur:

<UserControl x:Class="TestItemsSource234.Views.SmartForm" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> 
    <UserControl.Resources> 
     <Style x:Key="MainMessageStyle" TargetType="TextBlock"> 
      <Style.Triggers> 
       <Trigger> 
        <Trigger Property="Text" Value="{x:Null}"> 
         <Setter Property="Visibility" Value="Collapsed"/> 
        </Trigger> 
       </Trigger> 
      </Style.Triggers> 
     </Style> 
    </UserControl.Resources> 
    <StackPanel Margin="10">   
     <TextBlock Style="MainMessageStyle" Padding="10" Background="Yellow" Text="{Binding MainMessage}"/> 
    </StackPanel> 
</UserControl> 

TRY # 3 avec un DataTrigger de style produit la même erreur Le type 'style' ne contient pas une classe publique de type convertisseur:

<UserControl x:Class="TestItemsSource234.Views.SmartForm" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> 
    <UserControl.Resources> 
     <Style x:Key="MainMessageStyle" TargetType="TextBlock"> 
      <Style.Triggers> 
       <Trigger> 
        <DataTrigger Binding="{Binding MainMessage}" Value="{x:Null}"> 
         <Setter Property="Visibility" Value="Collapsed"/> 
        </DataTrigger> 
       </Trigger> 
      </Style.Triggers> 
     </Style> 
    </UserControl.Resources> 
    <StackPanel Margin="10">   
     <TextBlock Style="MainMessageStyle" Padding="10" Background="Yellow" Text="{Binding MainMessage}"/> 
    </StackPanel> 
</UserControl> 

# 4 TRY: OK, c'était un oubli stupide de moi, oublièrent StaticResource, mais même alors à la fois Essayez # 2 et # 3 Essayez obtenir une nouvelle erreur Le type System.Windows.Trigger dans le style est inconnu:

<UserControl x:Class="TestItemsSource234.Views.SmartForm" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> 
    <UserControl.Resources> 
     <Style x:Key="MainMessageStyle" TargetType="TextBlock"> 
      <Style.Triggers> 
       <Trigger> 
        <Trigger Property="Text" Value=""> 
         <Setter Property="Visibility" Value="Collapsed"/> 
        </Trigger> 
       </Trigger> 
      </Style.Triggers> 
     </Style> 
    </UserControl.Resources> 
    <StackPanel Margin="10">   
     <TextBlock Style="{StaticResource MainMessageStyle}" Padding="10" Background="Yellow" Text="{Binding MainMessage}"/> 
    </StackPanel> 
</UserControl> 

Alors, comment dois-je faire cela?

RÉPONSE:

OK, ce qui était une chasse de syntaxe affolant avec une fin heureuse, voici la version qui fonctionne, espérons que cela aide quelqu'un, les leçons apprises:

  • si le déclencheur, puis le style
  • si le style, puis StaticResource
  • si la liaison, puis DataTrigger
Code

qui fonctionne:

<UserControl x:Class="TestItemsSource234.Views.SmartForm" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"> 
    <UserControl.Resources> 
     <Style x:Key="MainMessageStyle" TargetType="TextBlock"> 
      <Style.Triggers> 
       <DataTrigger Binding="{Binding MainMessage}" Value="{x:Null}"> 
        <Setter Property="Visibility" Value="Collapsed"/> 
       </DataTrigger> 
      </Style.Triggers> 
     </Style> 
    </UserControl.Resources> 
    <StackPanel Margin="10"> 
     <ItemsControl 
      ItemsSource="{Binding DataTypeViews}"/> 
     <TextBlock Style="{StaticResource MainMessageStyle}" Padding="10" Background="Yellow" Text="{Binding MainMessage}"/> 
    </StackPanel> 
</UserControl> 
+7

Pourquoi wpf est-il si horrible? – PeterAllenWebb

+2

Il n'y a aucune excuse pour l'équipe WPF pour pourquoi # 4 ne fonctionne pas seulement! Pourquoi WPF est-il si énigmatique? –

Répondre

2

Soit Essayez # 2 ou Essayez n ° 3 devrait être bon - le problème est dans la ligne où vous référencez le style - vous devez utiliser soit « Style = "{StaticResource [KeyName]}" 'ou' Style = "{DynamicResource [KeyName]}" '.

Essayez cette (Essai n ° 2):

<StackPanel Margin="10">   
    <TextBlock Style="{StaticResource MainMessageStyle}" Padding="10" Background="Yellow" Text="{Binding MainMessage}"/> 
</StackPanel> 

Essai 1 vous révéliez une limitation des versions actuelles WPF: Triggers ne sont pas directement pris en charge sur les éléments.

+1

"Les déclencheurs ne sont pas pris en charge directement sur les éléments." - Alors le compilateur devrait vous dire ceci, pas une autre erreur sans rapport. –

1

Je pense que la façon la plus simple de le faire serait de définir un convertisseur qui convertit la chaîne à la visibilité.

... 

    return string.IsNullOrEmpty(s) ? Visibility.Collapsed : Visibility.Visible; 
} 

Ensuite, il suffit

<TextBlock Visibility="{StaticResource StringToVisibilityConverter}" 
5

Le plus simple, plus simple et plus rapide sont des convertisseurs. Alors, pourquoi pas KISS? (reste simple, stupide)?

Pour implémenter des classes de convertisseur, seules quelques lignes de code sont nécessaires.

Converter:

public class StringToVisibilityConverter : IValueConverter 
{ 
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture) 
    { 
     return string.IsNullOrWhiteSpace((string)value) ? Visibility.Collapsed : Visibility.Visible; 
    } 

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) 
    { 
     var visiblity = (Visibility)value; 
     return visiblity == Visibility.Visible; 
    } 
} 

Utilisation:

Inclure l'espace de noms: xmlns:c="clr-namespace:Hfr.Windows.Controls"

Définir ressource: <c:StringToVisibilityConverter x:Key="StringToVisiblity"/>

Utilisez-le:

<TextBlock 
    Text="{Binding SomeStringPropertyValue}" 
    TextWrapping="Wrap" 
    Visibility="{Binding SomeStringPropertyValue, Converter={StaticResource StringToVisiblity}}" /> 

Puisque vous utiliserez vos convertisseurs dans plusieurs projets, implémentez les classes de conversion dans une «bibliothèque commune».

Questions connexes