dotnet/wpf · error · ArgumentException

SR.ClassTypeIllegal

Error message

SR.ClassTypeIllegal

What it means

EventManager.RegisterClassHandler only accepts class types deriving from UIElement, ContentElement, or UIElement3D, since class handling is implemented on those element cores. A classType outside that hierarchy throws ArgumentException with SR.ClassTypeIllegal. This is validated before the handler-legality check.

Solutions

  1. Pass a class type deriving from UIElement, UIElement3D, or ContentElement
  2. Register handlers on the nearest element base class that is in the allowed hierarchy
  3. Move the handler registration to the element class itself instead of an unrelated class

Example fix

// before
EventManager.RegisterClassHandler(typeof(MyService), Mouse.MouseDownEvent, handler, false);
// after
EventManager.RegisterClassHandler(typeof(MyElement), Mouse.MouseDownEvent, new MouseButtonEventHandler(handler), false);
Defensive patterns

Strategy: validation

Validate before calling

bool ok = typeof(UIElement).IsAssignableFrom(classType) || typeof(ContentElement).IsAssignableFrom(classType) || typeof(UIElement3D).IsAssignableFrom(classType);

Type guard

bool IsClassHandlerTarget(Type t) => typeof(UIElement).IsAssignableFrom(t) || typeof(ContentElement).IsAssignableFrom(t) || typeof(UIElement3D).IsAssignableFrom(t);

Try / catch

try { EventManager.RegisterClassHandler(classType, evt, handler, false); } catch (ArgumentException) { /* classType not an element type */ }

Prevention

When it happens

Trigger: Calling RegisterClassHandler with a type that does not derive from UIElement/ContentElement/UIElement3D — e.g. a plain Control-derived non-visual class, a service class, or a DependencyObject that is not an element.

Common situations: Attempting class handling on DispatcherObject/DependencyObject subclasses; wiring handlers for custom non-element classes; typo passing typeof(HandlerClass) instead of typeof(ElementClass).

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


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

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/PresentationCore/System/Windows/EventManager.cs:159

        /// </param>
        /// <ExternalAPI/>
        public static void RegisterClassHandler(
            Type classType,
            RoutedEvent routedEvent,
            Delegate handler,
            bool handledEventsToo)
        {
            ArgumentNullException.ThrowIfNull(classType);

            ArgumentNullException.ThrowIfNull(routedEvent);

            ArgumentNullException.ThrowIfNull(handler);

            if (!typeof(UIElement).IsAssignableFrom(classType) &&
                !typeof(ContentElement).IsAssignableFrom(classType) &&
                !typeof(UIElement3D).IsAssignableFrom(classType))
            {
                throw new ArgumentException(SR.ClassTypeIllegal);
            }
            
            if (!routedEvent.IsLegalHandler(handler))
            {
                throw new ArgumentException(SR.HandlerTypeIllegal);
            }
            
            GlobalEventManager.RegisterClassHandler(classType, routedEvent, handler, handledEventsToo);
        }

        /// <summary>
        ///     Returns <see cref="RoutedEvent"/>s 
        ///     that have been registered so far
        /// </summary>
        /// <remarks>
        ///     Also see 
        ///     <see cref="EventManager.RegisterRoutedEvent"/>
        ///     <para/>

View on GitHub (pinned to 81131a70a4)