{"record":{"id":"f2419216869f116f","repo":"stride3d/stride","slug":"index-cannot-be-0","errorCode":null,"errorMessage":"index cannot be < 0","messagePattern":"index cannot be < 0","errorType":"exception","errorClass":"ArgumentOutOfRangeException","httpStatus":null,"severity":"error","filePath":"sources/engine/Stride.Engine/Engine/ModelComponent.cs","lineNumber":176,"sourceCode":"        /// <value>The bounding box.</value>\n        [DataMemberIgnore]\n        public BoundingBox BoundingBox;\n\n        /// <summary>\n        /// Gets the bounding sphere in world space.\n        /// </summary>\n        /// <value>The bounding sphere.</value>\n        [DataMemberIgnore]\n        public BoundingSphere BoundingSphere;\n\n        /// <summary>\n        /// Gets the material at the specified index. If the material is not overriden by this component, it will try to get it from <see cref=\"Stride.Rendering.Model.Materials\"/>\n        /// </summary>\n        /// <param name=\"index\">The index of the material</param>\n        /// <returns>The material at the specified index or null if not found</returns>\n        public Material GetMaterial(int index)\n        {\n            if (index < 0) throw new ArgumentOutOfRangeException(nameof(index), @\"index cannot be < 0\");\n\n            Material material;\n            if (Materials.TryGetValue(index, out material))\n            {\n                return material;\n            }\n            // TODO: if Model is null, shouldn't we always return null?\n            if (Model != null && index < Model.Materials.Count)\n            {\n                material = Model.Materials[index].Material;\n            }\n            return material;\n        }\n\n        /// <summary>\n        /// Gets the number of materials (computed from <see cref=\"Stride.Rendering.Model.Materials\"/>)\n        /// </summary>\n        /// <returns></returns>","sourceCodeStart":158,"sourceCodeEnd":194,"githubUrl":"https://github.com/stride3d/stride/blob/96fad776d210c221682aac1ccdf4c79dc046fc38/sources/engine/Stride.Engine/Engine/ModelComponent.cs#L158-L194","documentation":"ModelComponent.GetMaterial throws ArgumentOutOfRangeException when the index passed is negative, because material overrides are keyed by non-negative indices. Indices >= 0 are allowed even if no material exists at them (returns null).","triggerScenarios":"Calling GetMaterial(-1) or with a negative computed index (e.g. loop arithmetic going below zero).","commonSituations":"Loop code computing index from an offset that can be negative; searching a collection backwards and passing -1 sentinel to GetMaterial.","solutions":["Clamp or validate the index to >= 0 before calling GetMaterial.","Fix the caller's loop arithmetic that produces negative indices.","Return early or break loops when the index would go negative instead of querying."],"exampleFix":"// before\nvar mat = modelComponent.GetMaterial(i - 1); // may pass -1\n// after\nif (i - 1 >= 0)\n    var mat = modelComponent.GetMaterial(i - 1);","handlingStrategy":"validation","validationCode":"if (index < 0) return null; // or clamp: index = Math.Max(0, index);","typeGuard":"Material SafeGetMaterial(ModelComponent mc, int i) => i < 0 ? null : mc.GetMaterial(i);","tryCatchPattern":"try { m = mc.GetMaterial(i); }\ncatch (ArgumentOutOfRangeException) { m = null; }","preventionTips":["Validate indices derived from arithmetic before calling GetMaterial.","Prefer iterating known material keys instead of guessing negative sentinel indices."],"tags":["materials","argument-out-of-range","model-component","indexing"],"backgroundTag":"argument-out-of-range","analyzedSha":"96fad776d210c221682aac1ccdf4c79dc046fc38","analyzedAt":"2026-09-14T02:59:31.279Z","contentChangedAt":"2026-09-14T02:59:31.279Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}