Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Undocumented .NET code related to Multi-Touch Manipulations throwing exception

A favorable outcome would be preventing this exception, preferably, or at least handling it gracefully.

I am getting an exception thrown within Microsoft code. On top of that, the method throwing the exception is System.Windows.Input.Manipulations.ManipulationSequence.ProcessManipulators, which I can't find in Microsoft Reference Source.

When the exception is thrown, I can see that one line down in the Call Stack window it references Windows.Input.Manipulations.ManipulationProcessor2D.ProcessManipulators, which does exist in Microsoft Reference Source.

But as you can see, it doesn't have a sibling class named ManipulationSequence.

As for the exception itself, it is a System.Argument.OutOfRangeException with a value of Timestamp values must not decrease. Parameter name: timestamp Actual value was 6590630705479.

The fully qualified signature of the method throwing the exception is System.Windows.Input.Manipulations.ManipulationSequence.ProcessManipulators(long timestamp, System.Collections.Generic.IEnumerable<System.Windows.Input.Manipulations.Manipulator2D> manipulators, System.Windows.Input.Manipulations.ManipulationSequence.ISettings settings)

It appears as if one other person in the universe has had this problem, but it could not be reproduced according to the only comment.

I have 6 MediaElement objects on a canvas that are all running videos when being manipulated, so I feel as though it might have something to do with the CPU being taxed and slowing down, possibly making timestamps be sent into the method out of order (though the same problem occurs when using Image rather than MediaElement). The exception happens sporadically, sometimes it will happen after just a few seconds of messing around with the objects, sometimes it can go for a few minutes or more of manipulating the objects.

My code that does the actual manipulation within ManipulationDelta looks like this:

//Get current values to manipulate
TransformGroup group = (TransformGroup)element.RenderTransform.Clone();
TranslateTransform translate = (TranslateTransform)group.Children[0].Clone();
ScaleTransform scale = (ScaleTransform)group.Children[1].Clone();
RotateTransform rotate = (RotateTransform)group.Children[2].Clone();

//...does manipulations on each by changing values...

//Apply transformation changes
group.Children[0] = translate;
group.Children[1] = scale;
group.Children[2] = rotate;
element.RenderTransform = group;

I have a Storyboard in XAML messing with the RotateTransform, so I can't really use MatrixTransform.

I am creating this using WPF with .NET 4.5.1. The error occurs in both Windows 8.1 and Windows 7. Any ideas on how to prevent this exception from occurring?


Some thoughts as I investigate the problem:

  • I also have ManipulationInertiaStarting in play here as a possible cause of this error.
  • I just added e.Handled = true; to the end of ManipulationCompleted, which wasn't there before. I haven't got the error since (though, again, very sporadic, so it is hard to tell when it is fixed).
  • If a ManipulationDelta method is not yet complete, and it is hit again from user input, could there be some sort of race condition occurring where the first method hit is starved for CPU resources and the second runs through, then when the first method finally completes the timestamp created is in the past?
    • Per a comment, this isn't likely.
  • I conferred with a co-worker to gain better understanding. He helped me realize I can't swallow the exception from within my methods that handle manipulation events because the exception is happening before it gets there, in the actual creation of the manipulation data. So the only place I can handle the exception is on App.Main() (the first place in the Call Stack where my code exists), which makes handling it gracefully all the more difficult.
like image 706
jporcenaluk Avatar asked Aug 22 '14 14:08

jporcenaluk


1 Answers

I had this exact problem myself. After a lot of testing it could be reproduced with slower machines under heavy load.

The Application was for Digital Signage and showed a lot of different items ( Video, Html , Images , etc ) and had also some animations.

I am not sure about it but it seems to be a problem of handling the input events in time.

For myself i could "solve" this issue with outsourcing code from the manipulating to other code asynchronous and also profiling and rewriting code performance-wise.( shortened the path to run inside the event as much as possible and did everything needed to do also later with a Task )

Also i added an Exceptionhandler to my application to "ignore and log" this issue, because it had no other impact.

Feel free to contact me for more info on this.

PS: this is my first answer here, so i hope it is alright the way i wrote it

like image 165
Micha R Avatar answered Nov 03 '22 10:11

Micha R