{"record":{"id":"e2cf0922dc602748","repo":"dotnet/wpf","slug":"sr-timing-accelanddecelgreaterthanone","errorCode":null,"errorMessage":"SR.Timing_AccelAndDecelGreaterThanOne","messagePattern":"SR\\.Timing_AccelAndDecelGreaterThanOne","errorType":"exception","errorClass":"InvalidOperationException","httpStatus":null,"severity":"error","filePath":"src/Microsoft.DotNet.Wpf/src/PresentationCore/System/Windows/Media/Animation/Timeline.cs","lineNumber":720,"sourceCode":"        }\n\n        /// <summary>\n        /// This method will throw an exception if a timeline has been incorrectly\n        /// constructed.  Currently we validate all possible values when they are \n        /// set, but it is not possible to do this for Acceleration/DecelerationRatio.\n        /// \n        /// The reason is when a timeline is instantiated in xaml the properties are\n        /// set with direct calls to DependencyObject.SetValue.  This means our only\n        /// chance to validate the value is in the ValidateValue callback, which does\n        /// not allow querying of other DPs.  Acceleration/DecelerationRatio are invalid\n        /// if their sum is > 1.  This can't be verified in the ValidateValue callback,\n        /// so is done here.\n        /// </summary>\n        private void ValidateTimeline()\n        {\n            if (AccelerationRatio + DecelerationRatio > 1)\n            {\n                throw new InvalidOperationException(SR.Timing_AccelAndDecelGreaterThanOne);\n            }\n        }\n\n        #endregion // Methods\n\n        #region Events\n\n        /// <summary>\n        /// Raised whenever the value of the CurrentStateInvalidated property changes.\n        /// </summary>\n        public event EventHandler CurrentStateInvalidated\n        {\n            add\n            {\n                AddEventHandler(CurrentStateInvalidatedKey, value);\n            }\n            remove\n            {","sourceCodeStart":702,"sourceCodeEnd":738,"githubUrl":"https://github.com/dotnet/wpf/blob/81131a70a4c573cd62748a5c36908fc4d662daa9/src/Microsoft.DotNet.Wpf/src/PresentationCore/System/Windows/Media/Animation/Timeline.cs#L702-L738","documentation":"Timeline.ValidateTimeline (invoked when the timeline is frozen via FreezeCore) enforces the invariant AccelerationRatio + DecelerationRatio <= 1; exceeding it throws InvalidOperationException with Timing_AccelAndDecelGreaterThanOne. The timing engine cannot both accelerate and decelerate for more than 100% of the duration, so the freeze fails.","triggerScenarios":"Setting AccelerationRatio = 0.7 and DecelerationRatio = 0.5 (sum 1.2) and then calling timeline.Freeze() — or implicitly when WPF freezes the timeline (e.g., assigning it to a style/resource used from multiple threads). Individually valid values can still sum > 1.","commonSituations":"Tuning both ratios independently in XAML where each stays <= 1 but the sum exceeds 1; copying ratios from two different animations; animation templates whose combined defaults sum above 1.","solutions":["Ensure AccelerationRatio + DecelerationRatio <= 1 before freezing; scale both down proportionally if needed.","Freeze manually at a point you control so you get the error early with a clear stack.","If ratios come from config, validate the pair together, not individually."],"exampleFix":"// before\nanim.AccelerationRatio = 0.7;\nanim.DecelerationRatio = 0.5; // sum 1.2\n// after\ndouble a = 0.7, d = 0.5;\ndouble scale = a + d > 1.0 ? 1.0 / (a + d) : 1.0;\nanim.AccelerationRatio = a * scale;\nanim.DecelerationRatio = d * scale;","handlingStrategy":"validation","validationCode":"if (a + d > 1.0) { double s = 1.0 / (a + d); a *= s; d *= s; }\nanim.AccelerationRatio = a; anim.DecelerationRatio = d;\nanim.Freeze();","typeGuard":"static bool AreValidRatios(double a, double d) => a >= 0 && a <= 1 && d >= 0 && d <= 1 && a + d <= 1;","tryCatchPattern":"try { anim.Freeze(); }\ncatch (InvalidOperationException) { /* rescale ratios and refreeze */ }","preventionTips":["Validate AccelerationRatio and DecelerationRatio as a pair, not individually.","Rescale proportionally whenever the sum exceeds 1.","Freeze timelines early in a controlled place so violations surface with clear context."],"tags":["wpf","animation","timeline","freeze","invalid-operation"],"backgroundTag":"invalid-state-transition","analyzedSha":"81131a70a4c573cd62748a5c36908fc4d662daa9","analyzedAt":"2026-09-14T10:12:48.479Z","contentChangedAt":"2026-09-14T10:12:48.479Z","schemaVersion":2},"datasetVersion":"2026-09-21T21:30:21.729Z"}