dotnet/wpf · error · InvalidEnumArgumentException

InvalidEnumArgumentException("action", (int)action…

Error message

InvalidEnumArgumentException("action", (int)action, typeof(AnnotationAction))

What it means

The AnnotationResourceChangedEventArgs constructor throws InvalidEnumArgumentException when the action parameter is not one of the defined AnnotationAction values within the valid range (Added through Modified). Callers firing annotation change events must pass a valid AnnotationAction; out-of-range values indicate a coding error in event-raising code.

Solutions

  1. Pass only valid AnnotationAction values (Added, Removed, Modified) when constructing the args.
  2. Validate the enum value before constructing: if (!Enum.IsDefined(typeof(AnnotationAction), action)) ...
  3. Fix int-to-enum casts that produce out-of-range values from persisted data.
  4. Update custom store/event-raising code to map legacy action codes to current enum members.

Example fix

// before
var args = new AnnotationResourceChangedEventArgs(annotation, (AnnotationAction)rawValue, resource);

// after
var action = Enum.IsDefined(typeof(AnnotationAction), rawValue) ? (AnnotationAction)rawValue : AnnotationAction.Modified;
var args = new AnnotationResourceChangedEventArgs(annotation, action, resource);
Defensive patterns

Strategy: validation

Validate before calling

if (!Enum.IsDefined(typeof(AnnotationAction), action) || action < AnnotationAction.Added || action > AnnotationAction.Modified)
    action = AnnotationAction.Modified; // or reject
var args = new AnnotationResourceChangedEventArgs(annotation, action, resource);

Type guard

bool IsValidAnnotationAction(AnnotationAction a) =>
    a is AnnotationAction.Added or AnnotationAction.Removed or AnnotationAction.Modified;

Try / catch

try { RaiseResourceChanged(new AnnotationResourceChangedEventArgs(a, act, r)); }
catch (InvalidEnumArgumentException ex) { log(ex); }

Prevention

When it happens

Trigger: Constructing AnnotationResourceChangedEventArgs with an int or AnnotationAction value outside the Added..Modified range (e.g. (AnnotationAction)99, uninitialized/default enum from unchecked casts, or arithmetic on enum values).

Common situations: Custom AnnotationStore implementations raising StoreContentChanged events with improperly cast enum values; enum values persisted as int and deserialized without validation; new enum members added upstream but not handled by old code paths.

Understand the failure class

Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.

Related errors


AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14). Data as JSON: /api/errors/23122cd14ff9fb06. Report an issue: GitHub.

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Annotations/AnnotationResourceChangedEventArgs.cs:56

        #region Constructors

        /// <summary>
        ///     Creates an instance of AnnotationResourceChangedEventArgs.
        /// </summary>
        /// <param name="annotation">the Annotation firing the event</param>
        /// <param name="action">the action taken on the Resource</param>
        /// <param name="resource">the Resource that was changed</param>
        /// <exception cref="ArgumentNullException">annotation or action is null</exception>
        /// <exception cref="InvalidEnumArgumentException">action is not a valid value from AnnotationAction</exception>
        public AnnotationResourceChangedEventArgs(Annotation annotation, AnnotationAction action, AnnotationResource resource)
        {
            // The resource parameter can be null here - it is possible to add a null to
            // the list of resources and we must fire an event signalling a change in the collection.

            ArgumentNullException.ThrowIfNull(annotation);
            if (action < AnnotationAction.Added || action > AnnotationAction.Modified)
            {
                throw new InvalidEnumArgumentException("action", (int)action, typeof(AnnotationAction));
            }

            _annotation = annotation;
            _resource = resource;
            _action = action;
        }

        #endregion Constructors

        //------------------------------------------------------
        //
        //  Public Properties
        //
        //------------------------------------------------------

        #region Public Properties

        /// <summary>

View on GitHub (pinned to 81131a70a4)