stride3d/stride · error · ArgumentNullException

Value cannot be null. (Parameter 'getParentFunc')

Error message

Value cannot be null. (Parameter 'getParentFunc')

What it means

Thrown by the private FindParentOfType<T> helper when the getParentFunc delegate is null. The delegate supplies each parent step during traversal (VisualTreeHelper.GetParent or LogicalTreeHelper.GetParent), so the helper rejects null at entry with ArgumentNullException.

Solutions

  1. Pass a valid parent-getter such as VisualTreeHelper.GetParent or LogicalTreeHelper.GetParent
  2. Call the public FindVisualParentOfType/FindLogicalParentOfType extensions instead of the raw helper
  3. Assert the delegate is non-null at the wrapper level

Example fix

// before
return FindParentOfType<T>(source, null);
// after
return FindParentOfType<T>(source, VisualTreeHelper.GetParent);
Defensive patterns

Strategy: validation

Validate before calling

if (getParentFunc == null) getParentFunc = VisualTreeHelper.GetParent; // or throw early at the wrapper

Type guard

bool HasValidArgs(DependencyObject d, Func<DependencyObject, DependencyObject> f) => d != null && f != null;

Try / catch

try { return FindParentOfType<T>(source, getParentFunc); }
catch (ArgumentNullException ex) when (ex.ParamName == "getParentFunc") { return FindParentOfType<T>(source, VisualTreeHelper.GetParent); }

Prevention

When it happens

Trigger: Calling FindParentOfType<T>(source, null) directly or via reflection; a misconfigured wrapper passing a null Func<DependencyObject, DependencyObject>.

Common situations: Refactoring a public wrapper where the tree-helper method reference was accidentally null (e.g. conditional binding or a generic indirection returning null).

Related errors


AI-assisted analysis of stride3d/stride@96fad776d2 (2026-09-14). Data as JSON: /api/errors/6022934f8aeb5b94. Report an issue: GitHub.

Appendix: source

Thrown at sources/presentation/Stride.Core.Presentation.Wpf/Extensions/DependencyObjectExtensions.cs:214

            }

            return (T)templatePart;
        }

        #region Helper methods

        /// <summary>
        /// Find the first parent that match the given type.
        /// </summary>
        /// <typeparam name="T">Type of parent to find.</typeparam>
        /// <param name="source">Base node from where to start looking for parent.</param>
        /// <param name="getParentFunc">Function that provide the parent element.</param>
        /// <returns>Returns the retrieved parent, or null otherwise.</returns>
        [CanBeNull]
        private static T FindParentOfType<T>(DependencyObject source, [NotNull] Func<DependencyObject, DependencyObject> getParentFunc) where T : DependencyObject
        {
            if (source == null) throw new ArgumentNullException(nameof(source));
            if (getParentFunc == null) throw new ArgumentNullException(nameof(getParentFunc));

            while (true)
            {
                // try to get visual parent
                var parent = getParentFunc(source);

                if (parent != null)
                {
                    if (parent is T)
                    {
                        // parent is of requested type, returned casted
                        return parent as T;
                    }

                    // there is a parent but not of request type, let's keep traversing the tree up
                    source = parent;
                    continue;
                }

View on GitHub (pinned to 96fad776d2)