Browse Source

Make VertexElement::index_ signed

1vanK 3 years ago
parent
commit
f94e4d9adb

+ 4 - 4
Source/Urho3D/AngelScript/Generated_Classes.cpp

@@ -3185,8 +3185,8 @@ static void Register_VertexBufferMorph(asIScriptEngine* engine)
     RegisterImplicitlyDeclaredAssignOperatorIfPossible<VertexBufferMorph>(engine, "VertexBufferMorph");
 }
 
-// VertexElement::VertexElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0, bool perInstance = false) noexcept
-static void VertexElement__VertexElement_VertexElementType_VertexElementSemantic_unsignedspchar_bool(VertexElement* _ptr, VertexElementType type, VertexElementSemantic semantic, unsigned char index, bool perInstance)
+// VertexElement::VertexElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0, bool perInstance = false) noexcept
+static void VertexElement__VertexElement_VertexElementType_VertexElementSemantic_i8_bool(VertexElement* _ptr, VertexElementType type, VertexElementSemantic semantic, i8 index, bool perInstance)
 {
     new(_ptr) VertexElement(type, semantic, index, perInstance);
 }
@@ -3194,8 +3194,8 @@ static void VertexElement__VertexElement_VertexElementType_VertexElementSemantic
 // struct VertexElement | File: ../GraphicsAPI/GraphicsDefs.h
 static void Register_VertexElement(asIScriptEngine* engine)
 {
-    // VertexElement::VertexElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0, bool perInstance = false) noexcept
-    engine->RegisterObjectBehaviour("VertexElement", asBEHAVE_CONSTRUCT, "void f(VertexElementType, VertexElementSemantic, uint8 = 0, bool = false)", AS_FUNCTION_OBJFIRST(VertexElement__VertexElement_VertexElementType_VertexElementSemantic_unsignedspchar_bool), AS_CALL_CDECL_OBJFIRST);
+    // VertexElement::VertexElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0, bool perInstance = false) noexcept
+    engine->RegisterObjectBehaviour("VertexElement", asBEHAVE_CONSTRUCT, "void f(VertexElementType, VertexElementSemantic, int8 = 0, bool = false)", AS_FUNCTION_OBJFIRST(VertexElement__VertexElement_VertexElementType_VertexElementSemantic_i8_bool), AS_CALL_CDECL_OBJFIRST);
 
     // VertexElement::~VertexElement() | Implicitly-declared
     engine->RegisterObjectBehaviour("VertexElement", asBEHAVE_DESTRUCT, "void f()", AS_DESTRUCTOR(VertexElement), AS_CALL_CDECL_OBJFIRST);

+ 26 - 26
Source/Urho3D/AngelScript/Generated_Members.h

@@ -6543,8 +6543,8 @@ template <class T> void RegisterMembers_VertexElement(asIScriptEngine* engine, c
     // VertexElementSemantic VertexElement::semantic_
     engine->RegisterObjectProperty(className, "VertexElementSemantic semantic", offsetof(T, semantic_));
 
-    // unsigned char VertexElement::index_
-    engine->RegisterObjectProperty(className, "uint8 index", offsetof(T, index_));
+    // i8 VertexElement::index_
+    engine->RegisterObjectProperty(className, "int8 index", offsetof(T, index_));
 
     // bool VertexElement::perInstance_
     engine->RegisterObjectProperty(className, "bool perInstance", offsetof(T, perInstance_));
@@ -12401,19 +12401,19 @@ template <class T> bool VertexBuffer_bool_SetSize_unsigned_constspVectorlesVerte
     return result;
 }
 
-// static bool VertexBuffer::HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0)
-template <class T> bool VertexBuffer_bool_HasElement_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_unsignedspchar(CScriptArray* elements_conv, VertexElementType type, VertexElementSemantic semantic, unsigned char index)
+// static bool VertexBuffer::HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0)
+template <class T> bool VertexBuffer_bool_HasElement_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_i8(CScriptArray* elements_conv, VertexElementType type, VertexElementSemantic semantic, i8 index)
 {
     Vector<VertexElement> elements = ArrayToVector<VertexElement>(elements_conv);
     bool result = T::HasElement(elements, type, semantic, index);
     return result;
 }
 
-// static unsigned VertexBuffer::GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0)
-template <class T> unsigned VertexBuffer_unsigned_GetElementOffset_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_unsignedspchar(CScriptArray* elements_conv, VertexElementType type, VertexElementSemantic semantic, unsigned char index)
+// static i32 VertexBuffer::GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0)
+template <class T> i32 VertexBuffer_i32_GetElementOffset_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_i8(CScriptArray* elements_conv, VertexElementType type, VertexElementSemantic semantic, i8 index)
 {
     Vector<VertexElement> elements = ArrayToVector<VertexElement>(elements_conv);
-    unsigned result = T::GetElementOffset(elements, type, semantic, index);
+    i32 result = T::GetElementOffset(elements, type, semantic, index);
     return result;
 }
 
@@ -12438,14 +12438,14 @@ template <class T> void RegisterMembers_VertexBuffer(asIScriptEngine* engine, co
     RegisterMembers_Object<T>(engine, className);
     RegisterMembers_GPUObject<T>(engine, className);
 
-    // const VertexElement* VertexBuffer::GetElement(VertexElementSemantic semantic, unsigned char index = 0) const
+    // const VertexElement* VertexBuffer::GetElement(VertexElementSemantic semantic, i8 index = 0) const
     // Error: type "const VertexElement*" can not automatically bind
-    // const VertexElement* VertexBuffer::GetElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0) const
+    // const VertexElement* VertexBuffer::GetElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0) const
     // Error: type "const VertexElement*" can not automatically bind
-    // unsigned char* VertexBuffer::GetShadowData() const
-    // Error: type "unsigned char*" can not automatically bind
-    // SharedArrayPtr<unsigned char> VertexBuffer::GetShadowDataShared() const
-    // Error: type "SharedArrayPtr<unsigned char>" can not automatically bind
+    // u8* VertexBuffer::GetShadowData() const
+    // Error: type "u8*" can not automatically bind
+    // SharedArrayPtr<u8> VertexBuffer::GetShadowDataShared() const
+    // Error: type "SharedArrayPtr<u8>" can not automatically bind
     // void* VertexBuffer::Lock(unsigned start, unsigned count, bool discard = false)
     // Error: type "void*" can not automatically bind
     // bool VertexBuffer::SetData(const void* data)
@@ -12460,11 +12460,11 @@ template <class T> void RegisterMembers_VertexBuffer(asIScriptEngine* engine, co
     engine->RegisterObjectMethod(className, "VertexMaskFlags GetElementMask() const", AS_METHODPR(T, GetElementMask, () const, VertexMaskFlags), AS_CALL_THISCALL);
     engine->RegisterObjectMethod(className, "VertexMaskFlags get_elementMask() const", AS_METHODPR(T, GetElementMask, () const, VertexMaskFlags), AS_CALL_THISCALL);
 
-    // unsigned VertexBuffer::GetElementOffset(VertexElementSemantic semantic, unsigned char index = 0) const
-    engine->RegisterObjectMethod(className, "uint GetElementOffset(VertexElementSemantic, uint8 = 0) const", AS_METHODPR(T, GetElementOffset, (VertexElementSemantic, unsigned char) const, unsigned), AS_CALL_THISCALL);
+    // i32 VertexBuffer::GetElementOffset(VertexElementSemantic semantic, i8 index = 0) const
+    engine->RegisterObjectMethod(className, "int GetElementOffset(VertexElementSemantic, int8 = 0) const", AS_METHODPR(T, GetElementOffset, (VertexElementSemantic, i8) const, i32), AS_CALL_THISCALL);
 
-    // unsigned VertexBuffer::GetElementOffset(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0) const
-    engine->RegisterObjectMethod(className, "uint GetElementOffset(VertexElementType, VertexElementSemantic, uint8 = 0) const", AS_METHODPR(T, GetElementOffset, (VertexElementType, VertexElementSemantic, unsigned char) const, unsigned), AS_CALL_THISCALL);
+    // i32 VertexBuffer::GetElementOffset(VertexElementType type, VertexElementSemantic semantic, i8 index = 0) const
+    engine->RegisterObjectMethod(className, "int GetElementOffset(VertexElementType, VertexElementSemantic, int8 = 0) const", AS_METHODPR(T, GetElementOffset, (VertexElementType, VertexElementSemantic, i8) const, i32), AS_CALL_THISCALL);
 
     // const Vector<VertexElement>& VertexBuffer::GetElements() const
     engine->RegisterObjectMethod(className, "Array<VertexElement>@ GetElements() const", AS_FUNCTION_OBJFIRST(VertexBuffer_constspVectorlesVertexElementgreamp_GetElements_void_template<VertexBuffer>), AS_CALL_CDECL_OBJFIRST);
@@ -12478,11 +12478,11 @@ template <class T> void RegisterMembers_VertexBuffer(asIScriptEngine* engine, co
     engine->RegisterObjectMethod(className, "uint GetVertexSize() const", AS_METHODPR(T, GetVertexSize, () const, unsigned), AS_CALL_THISCALL);
     engine->RegisterObjectMethod(className, "uint get_vertexSize() const", AS_METHODPR(T, GetVertexSize, () const, unsigned), AS_CALL_THISCALL);
 
-    // bool VertexBuffer::HasElement(VertexElementSemantic semantic, unsigned char index = 0) const
-    engine->RegisterObjectMethod(className, "bool HasElement(VertexElementSemantic, uint8 = 0) const", AS_METHODPR(T, HasElement, (VertexElementSemantic, unsigned char) const, bool), AS_CALL_THISCALL);
+    // bool VertexBuffer::HasElement(VertexElementSemantic semantic, i8 index = 0) const
+    engine->RegisterObjectMethod(className, "bool HasElement(VertexElementSemantic, int8 = 0) const", AS_METHODPR(T, HasElement, (VertexElementSemantic, i8) const, bool), AS_CALL_THISCALL);
 
-    // bool VertexBuffer::HasElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0) const
-    engine->RegisterObjectMethod(className, "bool HasElement(VertexElementType, VertexElementSemantic, uint8 = 0) const", AS_METHODPR(T, HasElement, (VertexElementType, VertexElementSemantic, unsigned char) const, bool), AS_CALL_THISCALL);
+    // bool VertexBuffer::HasElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0) const
+    engine->RegisterObjectMethod(className, "bool HasElement(VertexElementType, VertexElementSemantic, int8 = 0) const", AS_METHODPR(T, HasElement, (VertexElementType, VertexElementSemantic, i8) const, bool), AS_CALL_THISCALL);
 
     // bool VertexBuffer::IsDynamic() const
     engine->RegisterObjectMethod(className, "bool IsDynamic() const", AS_METHODPR(T, IsDynamic, () const, bool), AS_CALL_THISCALL);
@@ -12508,16 +12508,16 @@ template <class T> void RegisterMembers_VertexBuffer(asIScriptEngine* engine, co
     // void VertexBuffer::Unlock()
     engine->RegisterObjectMethod(className, "void Unlock()", AS_METHODPR(T, Unlock, (), void), AS_CALL_THISCALL);
 
-    // static const VertexElement* VertexBuffer::GetElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0)
+    // static const VertexElement* VertexBuffer::GetElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0)
     // Error: type "const VertexElement*" can not automatically bind
     // static void VertexBuffer::UpdateOffsets(Vector<VertexElement>& elements)
     // Error: type "Vector<VertexElement>&" can not automatically bind
 
-    // static bool VertexBuffer::HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0)
-    engine->SetDefaultNamespace(className);engine->RegisterGlobalFunction("bool HasElement(Array<VertexElement>@+, VertexElementType, VertexElementSemantic, uint8 = 0)", AS_FUNCTION(VertexBuffer_bool_HasElement_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_unsignedspchar<VertexBuffer>), AS_CALL_CDECL);engine->SetDefaultNamespace("");
+    // static bool VertexBuffer::HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0)
+    engine->SetDefaultNamespace(className);engine->RegisterGlobalFunction("bool HasElement(Array<VertexElement>@+, VertexElementType, VertexElementSemantic, int8 = 0)", AS_FUNCTION(VertexBuffer_bool_HasElement_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_i8<VertexBuffer>), AS_CALL_CDECL);engine->SetDefaultNamespace("");
 
-    // static unsigned VertexBuffer::GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0)
-    engine->SetDefaultNamespace(className);engine->RegisterGlobalFunction("uint GetElementOffset(Array<VertexElement>@+, VertexElementType, VertexElementSemantic, uint8 = 0)", AS_FUNCTION(VertexBuffer_unsigned_GetElementOffset_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_unsignedspchar<VertexBuffer>), AS_CALL_CDECL);engine->SetDefaultNamespace("");
+    // static i32 VertexBuffer::GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0)
+    engine->SetDefaultNamespace(className);engine->RegisterGlobalFunction("int GetElementOffset(Array<VertexElement>@+, VertexElementType, VertexElementSemantic, int8 = 0)", AS_FUNCTION(VertexBuffer_i32_GetElementOffset_constspVectorlesVertexElementgreamp_VertexElementType_VertexElementSemantic_i8<VertexBuffer>), AS_CALL_CDECL);engine->SetDefaultNamespace("");
 
     // static Vector<VertexElement> VertexBuffer::GetElements(unsigned elementMask)
     engine->SetDefaultNamespace(className);engine->RegisterGlobalFunction("Array<VertexElement>@ GetElements(uint)", AS_FUNCTION(VertexBuffer_VectorlesVertexElementgre_GetElements_unsigned<VertexBuffer>), AS_CALL_CDECL);engine->SetDefaultNamespace("");

+ 7 - 1
Source/Urho3D/Container/Hash.h

@@ -93,7 +93,13 @@ template <> inline unsigned MakeHash(const c32& value)
 }
 
 /// Unsigned char hash function.
-template <> inline unsigned MakeHash(const unsigned char& value)
+template <> inline unsigned MakeHash(const u8& value)
+{
+    return value;
+}
+
+/// Signed char hash function.
+template <> inline unsigned MakeHash(const i8& value)
 {
     return value;
 }

+ 6 - 3
Source/Urho3D/GraphicsAPI/GraphicsDefs.h

@@ -183,7 +183,7 @@ struct URHO3D_API VertexElement
     }
 
     /// Construct with type, semantic, index and whether is per-instance data.
-    VertexElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0, bool perInstance = false) noexcept :
+    VertexElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0, bool perInstance = false) noexcept :
         type_(type),
         semantic_(semantic),
         index_(index),
@@ -193,7 +193,10 @@ struct URHO3D_API VertexElement
     }
 
     /// Test for equality with another vertex element. Offset is intentionally not compared, as it's relevant only when an element exists within a vertex buffer.
-    bool operator ==(const VertexElement& rhs) const { return type_ == rhs.type_ && semantic_ == rhs.semantic_ && index_ == rhs.index_ && perInstance_ == rhs.perInstance_; }
+    bool operator ==(const VertexElement& rhs) const
+    {
+        return type_ == rhs.type_ && semantic_ == rhs.semantic_ && index_ == rhs.index_ && perInstance_ == rhs.perInstance_;
+    }
 
     /// Test for inequality with another vertex element.
     bool operator !=(const VertexElement& rhs) const { return !(*this == rhs); }
@@ -203,7 +206,7 @@ struct URHO3D_API VertexElement
     /// Semantic of element.
     VertexElementSemantic semantic_;
     /// Semantic index of element, for example multi-texcoords.
-    unsigned char index_;
+    i8 index_;
     /// Per-instance flag.
     bool perInstance_;
     /// Offset of element from vertex start. Filled by VertexBuffer once the vertex declaration is built.

+ 2 - 2
Source/Urho3D/GraphicsAPI/OpenGL/OGLGraphics.cpp

@@ -3106,8 +3106,8 @@ void Graphics::PrepareDraw_OGL()
             for (Vector<VertexElement>::ConstIterator j = elements.Begin(); j != elements.End(); ++j)
             {
                 const VertexElement& element = *j;
-                HashMap<Pair<unsigned char, unsigned char>, unsigned>::ConstIterator k =
-                    impl->vertexAttributes_->Find(MakePair((unsigned char)element.semantic_, element.index_));
+                HashMap<Pair<i8, i8>, unsigned>::ConstIterator k =
+                    impl->vertexAttributes_->Find(MakePair((i8)element.semantic_, element.index_));
 
                 if (k != impl->vertexAttributes_->End())
                 {

+ 1 - 1
Source/Urho3D/GraphicsAPI/OpenGL/OGLGraphicsImpl.h

@@ -102,7 +102,7 @@ private:
     /// Vertex attribute instancing bitmask for keeping track of divisors.
     unsigned instancingVertexAttributes_{};
     /// Current mapping of vertex attribute locations by semantic. The map is owned by the shader program, so care must be taken to switch a null shader program when it's destroyed.
-    const HashMap<Pair<unsigned char, unsigned char>, unsigned>* vertexAttributes_{};
+    const HashMap<Pair<i8, i8>, unsigned>* vertexAttributes_{};
     /// Currently bound frame buffer object.
     unsigned boundFBO_{};
     /// Currently bound vertex buffer object.

+ 3 - 3
Source/Urho3D/GraphicsAPI/OpenGL/OGLShaderProgram.cpp

@@ -144,7 +144,7 @@ bool ShaderProgram_OGL::Link()
 
         String name = String(nameBuffer, nameLength);
         VertexElementSemantic semantic = MAX_VERTEX_ELEMENT_SEMANTICS;
-        unsigned char semanticIndex = 0;
+        i8 semanticIndex = 0;
 
         // Go in reverse order so that "binormal" is detected before "normal"
         for (i32 j = MAX_VERTEX_ELEMENT_SEMANTICS - 1; j >= 0; --j)
@@ -154,7 +154,7 @@ bool ShaderProgram_OGL::Link()
                 semantic = (VertexElementSemantic)j;
                 unsigned index = NumberPostfix(name);
                 if (index != M_MAX_UNSIGNED)
-                    semanticIndex = (unsigned char)index;
+                    semanticIndex = (i8)index;
                 break;
             }
         }
@@ -167,7 +167,7 @@ bool ShaderProgram_OGL::Link()
         }
 
         int location = glGetAttribLocation(object_.name_, name.CString());
-        vertexAttributes_[MakePair((unsigned char)semantic, semanticIndex)] = location;
+        vertexAttributes_[{(i8)semantic, semanticIndex}] = location;
         usedVertexAttributes_ |= (1u << location);
     }
 

+ 2 - 2
Source/Urho3D/GraphicsAPI/OpenGL/OGLShaderProgram.h

@@ -49,7 +49,7 @@ public:
     const String& GetLinkerOutput() const { return linkerOutput_; }
 
     /// Return semantic to vertex attributes location mappings used by the shader.
-    const HashMap<Pair<unsigned char, unsigned char>, unsigned>& GetVertexAttributes() const { return vertexAttributes_; }
+    const HashMap<Pair<i8, i8>, unsigned>& GetVertexAttributes() const { return vertexAttributes_; }
 
     /// Return attribute location use bitmask.
     unsigned GetUsedVertexAttributes() const { return usedVertexAttributes_; }
@@ -77,7 +77,7 @@ private:
     /// Texture unit use.
     bool useTextureUnits_[MAX_TEXTURE_UNITS]{};
     /// Vertex attributes.
-    HashMap<Pair<unsigned char, unsigned char>, unsigned> vertexAttributes_;
+    HashMap<Pair<i8, i8>, unsigned> vertexAttributes_;
     /// Used vertex attribute location bitmask.
     unsigned usedVertexAttributes_{};
     /// Constant buffers by binding index.

+ 25 - 17
Source/Urho3D/GraphicsAPI/VertexBuffer.cpp

@@ -39,7 +39,7 @@ void VertexBuffer::SetShadowed(bool enable)
     if (enable != shadowed_)
     {
         if (enable && vertexSize_ && vertexCount_)
-            shadowData_ = new unsigned char[vertexCount_ * vertexSize_];
+            shadowData_ = new u8[vertexCount_ * vertexSize_];
         else
             shadowData_.Reset();
 
@@ -63,7 +63,7 @@ bool VertexBuffer::SetSize(unsigned vertexCount, const Vector<VertexElement>& el
     UpdateOffsets();
 
     if (shadowed_ && vertexCount_ && vertexSize_)
-        shadowData_ = new unsigned char[vertexCount_ * vertexSize_];
+        shadowData_ = new u8[vertexCount_ * vertexSize_];
     else
         shadowData_.Reset();
 
@@ -94,48 +94,56 @@ void VertexBuffer::UpdateOffsets()
     vertexSize_ = elementOffset;
 }
 
-const VertexElement* VertexBuffer::GetElement(VertexElementSemantic semantic, unsigned char index) const
+const VertexElement* VertexBuffer::GetElement(VertexElementSemantic semantic, i8 index/* = 0*/) const
 {
-    for (Vector<VertexElement>::ConstIterator i = elements_.Begin(); i != elements_.End(); ++i)
+    assert(index >= 0);
+
+    for (const VertexElement& element : elements_)
     {
-        if (i->semantic_ == semantic && i->index_ == index)
-            return &(*i);
+        if (element.semantic_ == semantic && element.index_ == index)
+            return &element;
     }
 
     return nullptr;
 }
 
-const VertexElement* VertexBuffer::GetElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index) const
+const VertexElement* VertexBuffer::GetElement(VertexElementType type, VertexElementSemantic semantic, i8 index/* = 0*/) const
 {
-    for (Vector<VertexElement>::ConstIterator i = elements_.Begin(); i != elements_.End(); ++i)
+    assert(index >= 0);
+
+    for (const VertexElement& element : elements_)
     {
-        if (i->type_ == type && i->semantic_ == semantic && i->index_ == index)
-            return &(*i);
+        if (element.type_ == type && element.semantic_ == semantic && element.index_ == index)
+            return &element;
     }
 
     return nullptr;
 }
 
-const VertexElement* VertexBuffer::GetElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index)
+const VertexElement* VertexBuffer::GetElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index/* = 0*/)
 {
-    for (Vector<VertexElement>::ConstIterator i = elements.Begin(); i != elements.End(); ++i)
+    assert(index >= 0);
+
+    for (const VertexElement& element : elements)
     {
-        if (i->type_ == type && i->semantic_ == semantic && i->index_ == index)
-            return &(*i);
+        if (element.type_ == type && element.semantic_ == semantic && element.index_ == index)
+            return &element;
     }
 
     return nullptr;
 }
 
-bool VertexBuffer::HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index)
+bool VertexBuffer::HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index/* = 0*/)
 {
+    assert(index >= 0);
     return GetElement(elements, type, semantic, index) != nullptr;
 }
 
-unsigned VertexBuffer::GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index)
+i32 VertexBuffer::GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index/* = 0*/)
 {
+    assert(index >= 0);
     const VertexElement* element = GetElement(elements, type, semantic, index);
-    return element ? element->offset_ : M_MAX_UNSIGNED;
+    return element ? element->offset_ : NINDEX;
 }
 
 Vector<VertexElement> VertexBuffer::GetElements(unsigned elementMask)

+ 35 - 17
Source/Urho3D/GraphicsAPI/VertexBuffer.h

@@ -69,44 +69,62 @@ public:
     const Vector<VertexElement>& GetElements() const { return elements_; }
 
     /// Return vertex element, or null if does not exist.
-    const VertexElement* GetElement(VertexElementSemantic semantic, unsigned char index = 0) const;
+    const VertexElement* GetElement(VertexElementSemantic semantic, i8 index = 0) const;
 
     /// Return vertex element with specific type, or null if does not exist.
-    const VertexElement* GetElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0) const;
+    const VertexElement* GetElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0) const;
 
     /// Return whether has a specified element semantic.
-    bool HasElement(VertexElementSemantic semantic, unsigned char index = 0) const { return GetElement(semantic, index) != nullptr; }
+    bool HasElement(VertexElementSemantic semantic, i8 index = 0) const
+    {
+        assert(index >= 0);
+        return GetElement(semantic, index) != nullptr;
+    }
 
     /// Return whether has an element semantic with specific type.
-    bool HasElement(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0) const { return GetElement(type, semantic, index) != nullptr; }
-
-    /// Return offset of a element within vertex, or M_MAX_UNSIGNED if does not exist.
-    unsigned GetElementOffset(VertexElementSemantic semantic, unsigned char index = 0) const { const VertexElement* element = GetElement(semantic, index); return element ? element->offset_ : M_MAX_UNSIGNED; }
-
-    /// Return offset of a element with specific type within vertex, or M_MAX_UNSIGNED if element does not exist.
-    unsigned GetElementOffset(VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0) const { const VertexElement* element = GetElement(type, semantic, index); return element ? element->offset_ : M_MAX_UNSIGNED; }
+    bool HasElement(VertexElementType type, VertexElementSemantic semantic, i8 index = 0) const
+    {
+        assert(index >= 0);
+        return GetElement(type, semantic, index) != nullptr;
+    }
+
+    /// Return offset of a element within vertex, or NINDEX if does not exist.
+    i32 GetElementOffset(VertexElementSemantic semantic, i8 index = 0) const
+    {
+        assert(index >= 0);
+        const VertexElement* element = GetElement(semantic, index);
+        return element ? element->offset_ : NINDEX;
+    }
+
+    /// Return offset of a element with specific type within vertex, or NINDEX if element does not exist.
+    i32 GetElementOffset(VertexElementType type, VertexElementSemantic semantic, i8 index = 0) const
+    {
+        assert(index >= 0);
+        const VertexElement* element = GetElement(type, semantic, index);
+        return element ? element->offset_ : NINDEX;
+    }
 
     /// Return legacy vertex element mask. Note that both semantic and type must match the legacy element for a mask bit to be set.
     /// @property
     VertexMaskFlags GetElementMask() const { return elementMask_; }
 
     /// Return CPU memory shadow data.
-    unsigned char* GetShadowData() const { return shadowData_.Get(); }
+    u8* GetShadowData() const { return shadowData_.Get(); }
 
     /// Return shared array pointer to the CPU memory shadow data.
-    SharedArrayPtr<unsigned char> GetShadowDataShared() const { return shadowData_; }
+    SharedArrayPtr<u8> GetShadowDataShared() const { return shadowData_; }
 
     /// Return buffer hash for building vertex declarations. Used internally.
     unsigned long long GetBufferHash(unsigned streamIndex) { return elementHash_ << (streamIndex * 16); }
 
     /// Return element with specified type and semantic from a vertex element list, or null if does not exist.
-    static const VertexElement* GetElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0);
+    static const VertexElement* GetElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0);
 
     /// Return whether element list has a specified element type and semantic.
-    static bool HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0);
+    static bool HasElement(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0);
 
-    /// Return element offset for specified type and semantic from a vertex element list, or M_MAX_UNSIGNED if does not exist.
-    static unsigned GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, unsigned char index = 0);
+    /// Return element offset for specified type and semantic from a vertex element list, or NINDEX if does not exist.
+    static i32 GetElementOffset(const Vector<VertexElement>& elements, VertexElementType type, VertexElementSemantic semantic, i8 index = 0);
 
     /// Return a vertex element list from a legacy element bitmask.
     static Vector<VertexElement> GetElements(unsigned elementMask);
@@ -175,7 +193,7 @@ private:
 #endif // def URHO3D_D3D11
 
     /// Shadow data.
-    SharedArrayPtr<unsigned char> shadowData_;
+    SharedArrayPtr<u8> shadowData_;
     /// Number of vertices.
     unsigned vertexCount_{};
     /// Vertex size.