stride3d/stride · error · ArgumentNullException

ArgumentNullException: heightStickArray

Error message

ArgumentNullException: heightStickArray

What it means

FloatHeightStickArraySource.CopyTo fills a segment of an unmanaged height array with the initial height. It throws ArgumentNullException when the destination heightStickArray is null, since there is no buffer to fill.

Solutions

  1. Allocate the UnmanagedArray before calling CopyTo.
  2. Check the array for null before calling CopyTo.
  3. Ensure the upstream code that creates the heightstick array actually ran (e.g. HeightmapUtils heightstick setup).

Example fix

// before
source.CopyTo(heightStickArray, 0); // throws if null
// after
heightStickArray ??= new UnmanagedArray<float>(size.X * size.Y);
source.CopyTo(heightStickArray, 0);
Defensive patterns

Strategy: validation

Validate before calling

if (heightStickArray == null)
    throw new InvalidOperationException("Allocate heightstick array before CopyTo");

Try / catch

try { source.CopyTo(heightStickArray, 0); }
catch (ArgumentNullException ex) { /* allocate the buffer and retry */ }

Prevention

When it happens

Trigger: Calling CopyTo on a FloatHeightStickArraySource and passing null as the heightStickArray parameter (typically when the heightstick buffer was never allocated before population).

Common situations: Setting up a heightfield collider where the heightstick array allocation was skipped or failed; passing an uninitialized variable from an earlier setup step.

Related errors


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

Appendix: source

Thrown at sources/engine/Stride.Physics/FloatHeightStickArraySource.cs:37

        [DataMember(20)]
        public Vector2 HeightRange { get; set; } = new Vector2(-10, 10);

        [DataMemberIgnore]
        public float HeightScale => 1f;

        /// <summary>
        /// The value to fill the height stick array.
        /// </summary>
        [DataMember(30)]
        public float InitialHeight { get; set; } = 0;

        public bool IsValid() => HeightmapUtils.CheckHeightParameters(HeightStickSize, HeightType, HeightRange, HeightScale, false) &&
            MathUtil.IsInRange(InitialHeight, HeightRange.X, HeightRange.Y);

        public void CopyTo<T>(UnmanagedArray<T> heightStickArray, int index) where T : struct
        {
            if (heightStickArray == null) throw new ArgumentNullException(nameof(heightStickArray));
            if (heightStickArray is UnmanagedArray<float> unmanagedArray)
            {
                unmanagedArray.Fill(InitialHeight, index, HeightStickSize.X * HeightStickSize.Y);
            }
            else
            {
                throw new NotSupportedException($"{ typeof(UnmanagedArray<T>) } type is not supported.");
            }
        }

        public bool Match(object obj)
        {
            var other = obj as FloatHeightStickArraySource;

            if (other == null)
            {
                return false;
            }

View on GitHub (pinned to 96fad776d2)