[7/16] WineD3D: Pass the baseVertexIndex of indexed drawing in the
device structure
Stefan Dösinger
stefandoesinger at gmx.at
Mon Jan 1 18:11:52 CST 2007
The idea behind this is that the basevertexindex for non-indexed
drawing can be passed directly to glDrawArrays, while the indexed
offset has to be taken into account when setting the opengl stream
sources. This value is ignored for the strided data structure, only
LoadVertexData and drawStridedSlow use it. This will allow the vertex
buffer code to reuse the information from the device later.
-------------- next part --------------
From 8eb1fd336f96682b7a64916a856ed43f648d4ce0 Mon Sep 17 00:00:00 2001
From: =?utf-8?q?Stefan_D=C3=B6singer?= <stefan at imac.local>
Date: Wed, 27 Dec 2006 14:02:20 +0100
Subject: [PATCH] WineD3D: Pass the baseVertexIndex in the device impl structure
---
dlls/wined3d/device.c | 15 +++++++++-
dlls/wined3d/drawprim.c | 61 ++++++++++++++++++----------------------
dlls/wined3d/vertexbuffer.c | 1 -
dlls/wined3d/wined3d_private.h | 4 +--
4 files changed, 44 insertions(+), 37 deletions(-)
diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c
index cfb3354..e4a6ab6 100644
--- a/dlls/wined3d/device.c
+++ b/dlls/wined3d/device.c
@@ -4664,6 +4664,11 @@ static HRESULT WINAPI IWineD3DDeviceImpl
TRACE("(%p) : Type=(%d,%s), Start=%d, Count=%d\n", This, PrimitiveType,
debug_d3dprimitivetype(PrimitiveType),
StartVertex, PrimitiveCount);
+ if(This->baseVIndex != 0) {
+ /* TODO: Deal with that better */
+ This->baseVIndex = 0;
+ IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
+ }
drawPrimitive(iface, PrimitiveType, PrimitiveCount, StartVertex, 0/* NumVertices */, -1 /* indxStart */,
0 /* indxSize */, NULL /* indxData */, 0 /* minIndex */, NULL);
@@ -4696,7 +4701,12 @@ static HRESULT WINAPI IWineD3DDeviceIm
idxStride = 4;
}
- drawPrimitive(iface, PrimitiveType, primCount, baseVIndex, NumVertices, startIndex,
+ if(This->baseVIndex != baseVIndex) {
+ This->baseVIndex = baseVIndex;
+ IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
+ }
+
+ drawPrimitive(iface, PrimitiveType, primCount, 0, NumVertices, startIndex,
idxStride, ((IWineD3DIndexBufferImpl *) pIB)->resource.allocatedMemory, minIndex, NULL);
return WINED3D_OK;
@@ -4723,6 +4733,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl
/* Mark the state dirty until we have nicer tracking */
IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
+ This->baseVIndex = 0;
drawPrimitive(iface, PrimitiveType, PrimitiveCount, 0 /* start vertex */, 0 /* NumVertices */,
0 /* indxStart*/, 0 /* indxSize*/, NULL /* indxData */, 0 /* indxMin */, NULL);
@@ -4769,6 +4780,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl
/* Mark the state dirty until we have nicer tracking */
IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
+ This->baseVIndex = 0;
drawPrimitive(iface, PrimitiveType, PrimitiveCount, 0 /* vertexStart */, NumVertices, 0 /* indxStart */, idxStride, pIndexData, MinVertexIndex, NULL);
@@ -4785,6 +4797,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl
/* Mark the state dirty until we have nicer tracking */
IWineD3DDeviceImpl_MarkStateDirty(This, STATE_VDECL);
+ This->baseVIndex = 0;
drawPrimitive(iface, PrimitiveType, PrimitiveCount, 0, 0, 0, 0, NULL, 0, DrawPrimStrideData);
return WINED3D_OK;
}
diff --git a/dlls/wined3d/drawprim.c b/dlls/wined3d/drawprim.c
index da555bc..644f1ff 100644
--- a/dlls/wined3d/drawprim.c
+++ b/dlls/wined3d/drawprim.c
@@ -391,8 +391,7 @@ static BOOL fixed_get_input(
void primitiveDeclarationConvertToStridedData(
IWineD3DDevice *iface,
BOOL useVertexShaderFunction,
- WineDirect3DVertexStridedData *strided,
- LONG BaseVertexIndex,
+ WineDirect3DVertexStridedData *strided,
BOOL *fixup) {
/* We need to deal with frequency data!*/
@@ -442,7 +441,6 @@ void primitiveDeclarationConvertToStride
}
}
stride = This->stateBlock->streamStride[element->Stream];
- data += (BaseVertexIndex * stride);
data += element->Offset;
reg = element->Reg;
@@ -594,7 +592,7 @@ void primitiveConvertFVFtoOffset(DWORD t
}
}
-void primitiveConvertToStridedData(IWineD3DDevice *iface, WineDirect3DVertexStridedData *strided, LONG BaseVertexIndex, BOOL *fixup) {
+void primitiveConvertToStridedData(IWineD3DDevice *iface, WineDirect3DVertexStridedData *strided, BOOL *fixup) {
short LoopThroughTo = 0;
short nStream;
@@ -646,10 +644,6 @@ #endif
if (thisFVF == 0) continue;
/* Now convert the stream into pointers */
-
- /* Shuffle to the beginning of the vertexes to render and index from there */
- data = data + (BaseVertexIndex * stride);
-
primitiveConvertFVFtoOffset(thisFVF, stride, data, strided, streamVBO);
}
}
@@ -832,7 +826,7 @@ static void loadNumberedArrays(
WINED3D_ATR_GLTYPE(strided->u.input[i].dwType),
WINED3D_ATR_NORMALIZED(strided->u.input[i].dwType),
strided->u.input[i].dwStride,
- strided->u.input[i].lpData));
+ strided->u.input[i].lpData + This->baseVIndex * strided->u.input[i].dwStride));
GL_EXTCALL(glEnableVertexAttribArrayARB(i));
}
}
@@ -876,7 +870,7 @@ #if 1
#endif
TRACE("Blend %d %p %d\n", WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType),
- sd->u.s.blendWeights.lpData, sd->u.s.blendWeights.dwStride);
+ sd->u.s.blendWeights.lpData + This->baseVIndex * sd->u.s.blendWeights.dwStride, sd->u.s.blendWeights.dwStride);
/* FIXME("TODO\n");*/
/* Note dwType == float3 or float4 == 2 or 3 */
@@ -891,7 +885,7 @@ #endif
VTRACE(("glWeightPointerARB(%d, GL_FLOAT, %d, %p)\n",
WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType) ,
sd->u.s.blendWeights.dwStride,
- sd->u.s.blendWeights.lpData));
+ sd->u.s.blendWeights.lpData + This->baseVIndex * sd->u.s.blendWeights.dwStride));
if(curVBO != sd->u.s.blendWeights.VBO) {
GL_EXTCALL(glBindBufferARB(GL_ARRAY_BUFFER_ARB, sd->u.s.blendWeights.VBO));
@@ -903,7 +897,7 @@ #endif
WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType),
WINED3D_ATR_GLTYPE(sd->u.s.blendWeights.dwType),
sd->u.s.blendWeights.dwStride,
- sd->u.s.blendWeights.lpData);
+ sd->u.s.blendWeights.lpData + This->baseVIndex * sd->u.s.blendWeights.dwStride);
checkGLcall("glWeightPointerARB");
@@ -923,7 +917,7 @@ #if 0
WINED3D_ATR_SIZE(sd->u.s.blendWeights.dwType),
WINED3D_ATR_GLTYPE(sd->u.s.blendWeights.dwType),
sd->u.s.blendWeights.dwStride,
- sd->u.s.blendWeights.lpData);
+ sd->u.s.blendWeights.lpData + This->baseVIndex * sd->u.s.blendWeights.dwStride);
checkGLcall("glVertexWeightPointerEXT(numBlends, ...)");
glEnableClientState(GL_VERTEX_WEIGHT_ARRAY_EXT);
checkGLcall("glEnableClientState(GL_VERTEX_WEIGHT_ARRAY_EXT)");
@@ -955,7 +949,7 @@ #if 0 /* FOG --------------------------
(GL_EXTCALL)(FogCoordPointerEXT)(
WINED3D_ATR_GLTYPE(sd->u.s.fog.dwType),
sd->u.s.fog.dwStride,
- sd->u.s.fog.lpData);
+ sd->u.s.fog.lpData + This->baseVIndex * sd->u.s.fog.dwStride);
} else {
/* don't bother falling back to 'slow' as we don't support software FOG yet. */
/* FIXME: fixme once */
@@ -979,7 +973,7 @@ #if 0 /* tangents ---------------------
(GL_EXTCALL)(TangentPointerEXT)(
WINED3D_ATR_GLTYPE(sd->u.s.tangent.dwType),
sd->u.s.tangent.dwStride,
- sd->u.s.tangent.lpData);
+ sd->u.s.tangent.lpData + This->baseVIndex * sd->u.s.tangent.dwStride);
} else {
glDisable(GL_TANGENT_ARRAY_EXT);
}
@@ -988,7 +982,7 @@ #if 0 /* tangents ---------------------
(GL_EXTCALL)(BinormalPointerEXT)(
WINED3D_ATR_GLTYPE(sd->u.s.binormal.dwType),
sd->u.s.binormal.dwStride,
- sd->u.s.binormal.lpData);
+ sd->u.s.binormal.lpData + This->baseVIndex * sd->u.s.binormal.dwStride);
} else{
glDisable(GL_BINORMAL_ARRAY_EXT);
}
@@ -1041,12 +1035,12 @@ #endif
if(sd->u.s.position.VBO == 0) {
glVertexPointer(3 /* min(WINED3D_ATR_SIZE(sd->u.s.position.dwType),3) */,
WINED3D_ATR_GLTYPE(sd->u.s.position.dwType),
- sd->u.s.position.dwStride, sd->u.s.position.lpData);
+ sd->u.s.position.dwStride, sd->u.s.position.lpData + This->baseVIndex * sd->u.s.position.dwStride);
} else {
glVertexPointer(
WINED3D_ATR_SIZE(sd->u.s.position.dwType),
WINED3D_ATR_GLTYPE(sd->u.s.position.dwType),
- sd->u.s.position.dwStride, sd->u.s.position.lpData);
+ sd->u.s.position.dwStride, sd->u.s.position.lpData + This->baseVIndex * sd->u.s.position.dwStride);
}
checkGLcall("glVertexPointer(...)");
glEnableClientState(GL_VERTEX_ARRAY);
@@ -1071,7 +1065,7 @@ #endif
glNormalPointer(
WINED3D_ATR_GLTYPE(sd->u.s.normal.dwType),
sd->u.s.normal.dwStride,
- sd->u.s.normal.lpData);
+ sd->u.s.normal.lpData + This->baseVIndex * sd->u.s.normal.dwStride);
checkGLcall("glNormalPointer(...)");
glEnableClientState(GL_NORMAL_ARRAY);
checkGLcall("glEnableClientState(GL_NORMAL_ARRAY)");
@@ -1105,7 +1099,7 @@ #endif
}
glColorPointer(4, GL_UNSIGNED_BYTE,
sd->u.s.diffuse.dwStride,
- sd->u.s.diffuse.lpData);
+ sd->u.s.diffuse.lpData + This->baseVIndex * sd->u.s.diffuse.dwStride);
checkGLcall("glColorPointer(4, GL_UNSIGNED_BYTE, ...)");
glEnableClientState(GL_COLOR_ARRAY);
checkGLcall("glEnableClientState(GL_COLOR_ARRAY)");
@@ -1132,7 +1126,7 @@ #endif
}
GL_EXTCALL(glSecondaryColorPointerEXT)(4, GL_UNSIGNED_BYTE,
sd->u.s.specular.dwStride,
- sd->u.s.specular.lpData);
+ sd->u.s.specular.lpData + This->baseVIndex * sd->u.s.specular.dwStride);
vcheckGLcall("glSecondaryColorPointerEXT(4, GL_UNSIGNED_BYTE, ...)");
glEnableClientState(GL_SECONDARY_COLOR_ARRAY_EXT);
vcheckGLcall("glEnableClientState(GL_SECONDARY_COLOR_ARRAY_EXT)");
@@ -1197,7 +1191,7 @@ #endif
WINED3D_ATR_SIZE(sd->u.s.texCoords[coordIdx].dwType),
WINED3D_ATR_GLTYPE(sd->u.s.texCoords[coordIdx].dwType),
sd->u.s.texCoords[coordIdx].dwStride,
- sd->u.s.texCoords[coordIdx].lpData);
+ sd->u.s.texCoords[coordIdx].lpData + This->baseVIndex * sd->u.s.texCoords[coordIdx].dwStride);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
}
} else if (!GL_SUPPORT(NV_REGISTER_COMBINERS)) {
@@ -1216,7 +1210,7 @@ #endif
}
static void drawStridedFast(IWineD3DDevice *iface,UINT numberOfVertices, GLenum glPrimitiveType,
- const void *idxData, short idxSize, ULONG minIndex, ULONG startIdx) {
+ const void *idxData, short idxSize, ULONG minIndex, ULONG startIdx, ULONG startVertex) {
IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
if (idxData != NULL /* This crashes sometimes!*/) {
@@ -1241,7 +1235,7 @@ #endif
/* Note first is now zero as we shuffled along earlier */
TRACE("(%p) : glDrawArrays(%x, 0, %d)\n", This, glPrimitiveType, numberOfVertices);
- glDrawArrays(glPrimitiveType, 0, numberOfVertices);
+ glDrawArrays(glPrimitiveType, startVertex, numberOfVertices);
checkGLcall("glDrawArrays");
}
@@ -1256,13 +1250,13 @@ #endif
static void drawStridedSlow(IWineD3DDevice *iface, WineDirect3DVertexStridedData *sd,
UINT NumVertexes, GLenum glPrimType,
- const void *idxData, short idxSize, ULONG minIndex, ULONG startIdx) {
+ const void *idxData, short idxSize, ULONG minIndex, ULONG startIdx, ULONG startVertex) {
unsigned int textureNo = 0;
unsigned int texture_idx = 0;
const short *pIdxBufS = NULL;
const long *pIdxBufL = NULL;
- LONG SkipnStrides = 0;
+ LONG SkipnStrides = startVertex;
LONG vx_index;
float x = 0.0f, y = 0.0f, z = 0.0f; /* x,y,z coordinates */
float nx = 0.0f, ny = 0.0, nz = 0.0f; /* normal x,y,z coordinates */
@@ -1300,10 +1294,10 @@ static void drawStridedSlow(IWineD3DDevi
/* Indexed so work out the number of strides to skip */
if (idxSize == 2) {
VTRACE(("Idx for vertex %d = %d\n", vx_index, pIdxBufS[startIdx+vx_index]));
- SkipnStrides = pIdxBufS[startIdx + vx_index];
+ SkipnStrides = pIdxBufS[startIdx + vx_index] + This->baseVIndex;
} else {
VTRACE(("Idx for vertex %d = %d\n", vx_index, pIdxBufL[startIdx+vx_index]));
- SkipnStrides = pIdxBufL[startIdx + vx_index];
+ SkipnStrides = pIdxBufL[startIdx + vx_index] + This->baseVIndex;
}
}
@@ -1717,6 +1711,7 @@ inline static void drawPrimitiveDrawStri
BOOL useVertexShaderFunction,
BOOL usePixelShaderFunction,
WineDirect3DVertexStridedData *dataLocations,
+ ULONG baseVIndex,
UINT numberOfvertices,
UINT numberOfIndicies,
GLenum glPrimType,
@@ -1789,9 +1784,9 @@ #undef BUFFER_OR_DATA
/* Draw vertex-by-vertex */
if (useDrawStridedSlow)
- drawStridedSlow(iface, dataLocations, numberOfIndicies, glPrimType, idxData, idxSize, minIndex, StartIdx);
+ drawStridedSlow(iface, dataLocations, numberOfIndicies, glPrimType, idxData, idxSize, minIndex, StartIdx, baseVIndex);
else
- drawStridedFast(iface, numberOfIndicies, glPrimType, idxData, idxSize, minIndex, StartIdx);
+ drawStridedFast(iface, numberOfIndicies, glPrimType, idxData, idxSize, minIndex, StartIdx, baseVIndex);
/* Cleanup any shaders */
This->shader_backend->shader_cleanup(usePixelShaderFunction, useVertexShaderFunction);
@@ -2020,7 +2015,7 @@ void drawPrimitive(IWineD3DDevice *iface
((IWineD3DVertexShaderImpl *)This->stateBlock->vertexShader)->vertexDeclaration != NULL)
primitiveDeclarationConvertToStridedData(iface, useVertexShaderFunction,
- &This->strided_streams, StartVertexIndex, &fixup);
+ &This->strided_streams, &fixup);
} else {
@@ -2030,7 +2025,7 @@ void drawPrimitive(IWineD3DDevice *iface
TRACE("================ FVF ===================\n");
memset(&This->strided_streams, 0, sizeof(This->strided_streams));
- primitiveConvertToStridedData(iface, &This->strided_streams, StartVertexIndex, &fixup);
+ primitiveConvertToStridedData(iface, &This->strided_streams, &fixup);
drawPrimitiveTraceDataLocations(&This->strided_streams);
}
@@ -2049,7 +2044,7 @@ void drawPrimitive(IWineD3DDevice *iface
numberOfVertices = calculatedNumberOfindices;
drawPrimitiveDrawStrided(iface, useVertexShaderFunction, usePixelShaderFunction,
- &This->strided_streams, numberOfVertices, calculatedNumberOfindices, glPrimType,
+ &This->strided_streams, StartVertexIndex, numberOfVertices, calculatedNumberOfindices, glPrimType,
idxData, idxSize, minIndex, StartIdx, fixup);
}
diff --git a/dlls/wined3d/vertexbuffer.c b/dlls/wined3d/vertexbuffer.c
index 820309f..922d014 100644
--- a/dlls/wined3d/vertexbuffer.c
+++ b/dlls/wined3d/vertexbuffer.c
@@ -204,7 +204,6 @@ inline BOOL WINAPI IWineD3DVertexBufferI
primitiveDeclarationConvertToStridedData((IWineD3DDevice *) device,
FALSE,
&strided,
- 0,
&ret /* buffer contains fixed data, ignored here */);
This->Flags &= ~VBFLAG_LOAD;
diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h
index 0915b73..f5a6dd3 100644
--- a/dlls/wined3d/wined3d_private.h
+++ b/dlls/wined3d/wined3d_private.h
@@ -385,13 +385,12 @@ void drawPrimitive(IWineD3DDevice *iface
int minIndex,
WineDirect3DVertexStridedData *DrawPrimStrideData);
-void primitiveConvertToStridedData(IWineD3DDevice *iface, WineDirect3DVertexStridedData *strided, LONG BaseVertexIndex, BOOL *fixup);
+void primitiveConvertToStridedData(IWineD3DDevice *iface, WineDirect3DVertexStridedData *strided, BOOL *fixup);
void primitiveDeclarationConvertToStridedData(
IWineD3DDevice *iface,
BOOL useVertexShaderFunction,
WineDirect3DVertexStridedData *strided,
- LONG BaseVertexIndex,
BOOL *fixup);
void primitiveConvertFVFtoOffset(DWORD thisFVF,
@@ -670,6 +669,7 @@ #define NEEDS_DI
/* Stream source management */
WineDirect3DVertexStridedData strided_streams;
+ UINT baseVIndex;
} IWineD3DDeviceImpl;
--
1.4.2.4
-------------- next part --------------
More information about the wine-patches
mailing list