1

I have a custom control based on ToggleButton. In its constructor, I create a few elements of type FrameworkElementFactory and to one of them I assign an EventHandler like this:

button.AddHandler(Ellipse.MouseDownEvent, new MouseButtonEventHandler(Toggle));

And here's my event handler:

private void Toggle(object sender, EventArgs e)
{
    var active = GetTemplateChild("Active");
    var button = GetTemplateChild("ToggleButton");
    Storyboard sb = new Storyboard();

    var ta = new ThicknessAnimation();
    Storyboard.SetTargetProperty(ta, new PropertyPath("Margin"));
    Storyboard.SetTarget(ta, button);
    ta.Duration = TimeSpan.FromSeconds(0.2);


    var da = new DoubleAnimation();
    Storyboard.SetTargetProperty(da, new PropertyPath("Width"));
    Storyboard.SetTarget(da, active);
    da.Duration = TimeSpan.FromSeconds(0.2);

    if ((bool)IsChecked)
    {
        ta.To = new Thickness(0);
        da.To = (double)button.GetValue(Ellipse.WidthProperty);
        IsChecked = !IsChecked;
    }
    else
    {
        ta.To = new Thickness(this.Width - (double)button.GetValue(Ellipse.WidthProperty), 0, 0, 0);
        da.To = this.Width;
        IsChecked = !IsChecked;
    }

    sb.Children.Add(ta);
    sb.Children.Add(da);
    sb.Begin();
}

But it doesn't work. Doesn't work in the sense that it works only once. I mean it is supposed to set a slider's width based on the IsChecked property. Initially, it is set to false. When I click it, it expands to the right as expected. But when I click again, it does not move left as expected.

The more surprising thing is that it works perfectly with the MouseEnter event. All other events like MouseDown/Up/LeftMouseButtonUp/PreviewMouseDown..... are not working either.

If you want to reproduce the problem without much editing use the code here. Then just use it in a WPF app and you'll see.

Any help much appreciated.

Edit: Another discovery: It works with Right Clicks and Middle Button Clicks but not with Left Clicks. Wonder why...?? My mouse works fine.

Edit#2: Converters

AustinWBryan
  • 3,249
  • 3
  • 24
  • 42
Fᴀʀʜᴀɴ Aɴᴀᴍ
  • 6,131
  • 5
  • 31
  • 52

2 Answers2

6

MouseDown and MouseUp events are fired by UserControl. You should use the events: PreviewMouseDown and PreviewMouseUp.

Further, you may use MouseEnter and MouseLeave events in order to address the visual feedback when the mouse is located over your object.

AustinWBryan
  • 3,249
  • 3
  • 24
  • 42
benoch
  • 59
  • 1
  • 1
4

Having implemented a couple custom controls I've found some interesting behavior dealing with mouse events in particular. Basically, you may be running into a case where another control, possibly even in your ControlTemplate is stealing the mouse focus and consuming the mouse event before you get it.

There are two solutions to the problem:

  • Use MousePreviewEvents, and be careful not to mark the event consumed
  • Bind to the actual property that you are wanting to see changed

In this particular case I would have an InternalIsCheckedProperty that you bind to the ToggleButton.IsCheckedProperty to invoke your storyboard.

Berin Loritsch
  • 11,400
  • 4
  • 30
  • 57