void dx11ShaderProgram::drawElements(ShapeType shape, unsigned int count,
		DataType type, const void *indices, bool modified, ShaderBufferCache **cache,unsigned int first,unsigned int dcount) {
	ShaderEngine::Engine->prepareDraw(this);
	activate();
	updateConstants();

	int indiceSize = 4;
	DXGI_FORMAT iFmt = DXGI_FORMAT_R32_UINT;

	if (type == DUSHORT) {
		indiceSize = 2;
		iFmt = DXGI_FORMAT_R16_UINT;
	}

	D3D11_MAPPED_SUBRESOURCE ms;
	ID3D11Buffer *vbo = cache ? getCachedVBO(cache, true, indiceSize, 1, count) : getGenericVBO(0,indiceSize,1,count);
	if (modified || (!cache))
	{
		g_devcon->Map(vbo, NULL, D3D11_MAP_WRITE_DISCARD, NULL, &ms); // map the buffer
		memcpy(ms.pData, indices, indiceSize * count);              // copy the data
		g_devcon->Unmap(vbo, NULL);                              // unmap the buffer
	}

	UINT stride = indiceSize;
	UINT offset = 0;

	if ((curIndicesVBO != vbo) || (!cache))
	{
		g_devcon->IASetIndexBuffer(vbo, iFmt, 0);
		curIndicesVBO = vbo;
	}

	if (shape == Point)
		g_devcon->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_POINTLIST);
	else if (shape == TriangleStrip)
		g_devcon->IASetPrimitiveTopology(
				D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
	else if (shape == Triangles)
		g_devcon->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
	else if (shape == LineLoop)
		g_devcon->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP);
	else if (shape == Lines)
		g_devcon->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_LINELIST);
	else {
		glog_e("glDrawElements: bad mode\n");
		exit(1);
	}

	g_devcon->DrawIndexed(dcount?dcount:count, first, 0);
}
void dx11ShaderProgram::setupBuffer(int index, DataType type, int mult,
		const void *ptr, unsigned int count, bool modified,
		ShaderBufferCache **cache,int stride,int offset) {
	bool normalize = false; //TODO
	int elmSize = 1;
	switch (type) {
	case DFLOAT:
		elmSize = 4;
		break;
	case DUSHORT:
	case DSHORT:
		elmSize = 2;
		break;
	case DINT:
		elmSize = 4;
		break;
	}
	DataDesc dd = attributes[index];
	ID3D11Buffer *vbo = cache?getCachedVBO(cache,false,elmSize,dd.mult,count):getGenericVBO(index + 1, elmSize, dd.mult, count);
	if (!vbo) return;
	if (modified || (!cache))
	{
		D3D11_MAPPED_SUBRESOURCE ms;
		HRESULT hr = g_devcon->Map(vbo, NULL, D3D11_MAP_WRITE_DISCARD, NULL, &ms); // map the buffer
		if ((mult == 2) && (dd.mult == 3) && (type == DFLOAT)) //TODO should be more generic
		{
			float *vdi = (float *)ptr;
			float *vdo = (float *)ms.pData;
			for (int k = 0; k < count; k++) {
				*(vdo++) = *(vdi++);
				*(vdo++) = *(vdi++);
				*(vdo++) = 0;
			}
			mult = dd.mult;
		}
		else
			memcpy(ms.pData, ptr, mult * elmSize * count);          // copy the data
		//floatdump(vName, ms.pData, 8);
		g_devcon->Unmap(vbo, NULL);                              // unmap the buffer
	}
	UINT tstride = dd.mult * elmSize;
	if (stride)
		tstride=stride;

	UINT voff = offset;
	g_devcon->IASetVertexBuffers(index, 1, &vbo, &tstride, &voff);
}
void dx11ShaderProgram::setupBuffer(int index, DataType type, int mult,
		const void *ptr, unsigned int count, bool modified,
		ShaderBufferCache **cache,int stride,int offset) {
	if (index >= attributes.size())
		return;
	bool normalize = false; //TODO
	int elmSize = 1;
	switch (type) {
	case DFLOAT:
		elmSize = 4;
		break;
	case DUSHORT:
	case DSHORT:
		elmSize = 2;
		break;
	case DINT:
		elmSize = 4;
		break;
	}
	DataDesc dd = attributes[index];
	unsigned int bcount = (flags&ShaderProgram::Flag_PointShader) ? count * 4 : count;
	ID3D11Buffer *vbo = cache?getCachedVBO(cache,false,elmSize,dd.mult,bcount):getGenericVBO(index + 1, elmSize, dd.mult, bcount);
	if (!vbo) return;
	if (modified || (!cache))
	{
		D3D11_MAPPED_SUBRESOURCE ms;
		HRESULT hr = g_devcon->Map(vbo, NULL, D3D11_MAP_WRITE_DISCARD, NULL, &ms); // map the buffer
		if (flags&ShaderProgram::Flag_PointShader)
		{
			copyEnlarge(ptr, ms.pData, mult, dd.mult, elmSize, count, 4);		
			if (index == ShaderProgram::DataVertex)
			{
				int gindex = ShaderProgram::DataTexture + 1;
				//Ensure TexCoord array is present and big enough
				if ((genVBO[gindex] == NULL) || (genVBOcapacity[gindex] < (count * 4))) {
					D3D11_MAPPED_SUBRESOURCE tms;
					ID3D11Buffer *tvbo = getGenericVBO(gindex, 4, 2, count*4);
					g_devcon->Map(tvbo, NULL, D3D11_MAP_WRITE_DISCARD, NULL, &tms); // map the buffer
					float *t = (float *)tms.pData;
					for (int k = 0; k < count; k++) {
						*(t++) = 0.0;
						*(t++) = 0.0;
						*(t++) = 1.0;
						*(t++) = 0.0;
						*(t++) = 1.0;
						*(t++) = 1.0;
						*(t++) = 0.0;
						*(t++) = 1.0;
					}
					g_devcon->Unmap(tvbo, NULL);                          // unmap the buffer
				}
			}
		}
		else
		{
			if ((mult == 2) && (dd.mult == 3) && (type == DFLOAT)) //TODO should be more generic
			{
				float *vdi = (float *)ptr;
				float *vdo = (float *)ms.pData;
				for (int k = 0; k < count; k++) {
					*(vdo++) = *(vdi++);
					*(vdo++) = *(vdi++);
					*(vdo++) = 0;
				}
				mult = dd.mult;
			}
			else
				memcpy(ms.pData, ptr, mult * elmSize * count);          // copy the data
		}
		//floatdump(vName, ms.pData, 8);
		g_devcon->Unmap(vbo, NULL);                              // unmap the buffer
	}
	UINT tstride = dd.mult * elmSize;
	if (stride)
		tstride=stride;

	UINT voff = offset;
	g_devcon->IASetVertexBuffers(index, 1, &vbo, &tstride, &voff);

	if (flags&ShaderProgram::Flag_PointShader)
	{
		if (index == ShaderProgram::DataVertex)
		{
			UINT tstride = 8;
			UINT voff = 0;
			int gindex = ShaderProgram::DataTexture;
			ID3D11Buffer *tvbo = getGenericVBO(gindex+1, 4, 2, count * 4);
			g_devcon->IASetVertexBuffers(gindex, 1, &tvbo, &tstride, &voff);
		}
	}
}