2012-04-04 5 views
3

Was passiert hier und wie wird ein Workaround durchgeführt?WPF ToggleButton falsches Renderverhalten

  1. Drücken Sie MyToggleButton. Jetzt sieht es so aus als wäre es sofort gedrückt (überprüft).
  2. Zur gleichen Zeit MyToggleButton_Checked Handler deaktiviert die MyToggleButton.
  3. Drücken Sie jetzt die Nicht-Umschalttaste 'Aktivieren'. Was wir sehen? Das MyToggleButton scheint wie es aktiviert ist. OK. Aber warte, jetzt sieht es aus wie nicht gedrückt! Warum?!

XAML:

<StackPanel> 

    <ToggleButton x:Name="MyToggleButton" Content="MyToggleButton" Checked="MyToggleButton_Checked"/> 

    <TextBlock Text="{Binding IsChecked, ElementName=MyToggleButton}" Margin="0,4"/> 

    <Button Name="EnableButton" Content="Enable" Click="EnableButton_Click"/> 
    <Button Name="DisableButton" Content="Disable" Click="DisableButton_Click"/> 

</StackPanel> 

-Code-behind:

void MyToggleButton_Checked(object sender, RoutedEventArgs e) 
{ 
    MyToggleButton.IsEnabled = false; 
} 


void EnableButton_Click(object sender, RoutedEventArgs e) 
{ 
    MyToggleButton.IsEnabled = true; 
} 

void DisableButton_Click(object sender, RoutedEventArgs e) 
{ 
    MyToggleButton.IsEnabled = false; 
} 

UPD:

Die einzig mögliche Abhilfe auf den Moment ist:

void EnableButton_Click(object sender, RoutedEventArgs e) 
{ 
    MyToggleButton.IsEnabled = true; 

    var controlTemplate = MyToggleButton.Template; 

    var buttonChrome = (Microsoft.Windows.Themes.ButtonChrome)controlTemplate.FindName("Chrome", MyToggleButton); 

    buttonChrome.RenderPressed = false; 

    buttonChrome.RenderPressed = true; 
} 

Gibt es noch andere?

UPD2:

Eine andere Lösung ist:

void EnableButton_Click(object sender, RoutedEventArgs e) 
{ 
    MyToggleButton.IsEnabled = true; 

    var controlTemplate = MyToggleButton.Template; 
    MyToggleButton.Template = null; 
    MyToggleButton.Template = controlTemplate; 
} 

Aber die Steuerung wird im Moment der Vorlage Substitution flackern.

+0

Es ist wie der Effekt sieht erscheint nicht auf allen Maschinen. Mein Computer ist Windows 7 Professional 64-Bit .NET 4. Der Effekt ist immer noch hier. – frtnum

+0

Der Effekt hängt vom aktiven Thema ab. Zumindest auf meiner Maschine. Klassisches Thema funktioniert wie es sollte. Einfache Themen und Aero-Themen funktionieren nicht. Hier ist das Video, das ich aufgenommen habe, Upload-Größe des Ganzen war 3.1 Mb: http://screencast.com/t/KLCIwo9whs – frtnum

Antwort

6

Das ist meine Lösung für das Problem ist, hier ist die video, die Nutzung:

<StackPanel> 
    <ToggleButton x:Name="MyToggleButton" Content="MyToggleButton" Checked="MyToggleButton_Checked" 
        l:CorrectToggleButtonCheckedEnableBehavior.IsActive="True"/> 
    <Button Name="EnableButton" Content="Enable" Click="EnableButton_Click"/> 
</StackPanel> 

und der angeschlossene Verhalten Quellcode:

public static class CorrectToggleButtonCheckedEnableBehavior 
{ 
    public static bool GetIsActive(ToggleButton toggleButton) 
    { 
     return (bool)toggleButton.GetValue(IsActiveProperty); 
    } 

    public static void SetIsActive(ToggleButton toggleButton, bool value) 
    { 
     toggleButton.SetValue(IsActiveProperty, value); 
    } 

    public static readonly DependencyProperty IsActiveProperty = 
     DependencyProperty.RegisterAttached("IsActive", typeof(bool), typeof(CorrectToggleButtonCheckedEnableBehavior), 
     new UIPropertyMetadata(false, OnIsActiveChanged)); 

    static void OnIsActiveChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
    { 
     var toggleButton = (ToggleButton)d; 

     if (GetIsActive(toggleButton)) 
     { 
      toggleButton.IsEnabledChanged += new DependencyPropertyChangedEventHandler(ToggleButton_IsEnabledChanged); 
     } 
     else 
     { 
      toggleButton.IsEnabledChanged -= new DependencyPropertyChangedEventHandler(ToggleButton_IsEnabledChanged); 
     } 
    } 

    static void ToggleButton_IsEnabledChanged(object sender, DependencyPropertyChangedEventArgs e) 
    { 
     var toggleButton = (ToggleButton)sender; 

     if (toggleButton.IsEnabled && (toggleButton.IsChecked ?? false)) 
     { 
      Invalidate(toggleButton); 
     } 
    } 

    static void Invalidate(ToggleButton toggleButton) 
    { 
     var controlTemplate = toggleButton.Template; 
     toggleButton.Template = null; 
     toggleButton.Template = controlTemplate; 
    } 
} 
+0

Das ist genau das, was ich und meine Mitarbeiter LANG und EAGERLY gesucht haben! Ich danke Ihnen ganz herzlich. – user4134476