forked from LeenkxTeam/LNXSDK
Update Files
This commit is contained in:
@ -0,0 +1,841 @@
|
||||
#include <kinc/display.h>
|
||||
#include <kinc/graphics4/graphics.h>
|
||||
#include <kinc/graphics4/indexbuffer.h>
|
||||
#include <kinc/graphics4/pipeline.h>
|
||||
#include <kinc/graphics4/shader.h>
|
||||
#include <kinc/graphics4/texture.h>
|
||||
#include <kinc/graphics4/vertexbuffer.h>
|
||||
#include <kinc/math/core.h>
|
||||
|
||||
#undef CreateWindow
|
||||
#include <kinc/system.h>
|
||||
#include <kinc/window.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
#include <kinc/backend/Windows.h>
|
||||
|
||||
#include <kinc/log.h>
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
LPDIRECT3D9 d3d;
|
||||
LPDIRECT3DDEVICE9 device;
|
||||
|
||||
namespace {
|
||||
HWND hWnd;
|
||||
|
||||
int _width;
|
||||
int _height;
|
||||
|
||||
unsigned hz;
|
||||
bool vsync;
|
||||
|
||||
bool resizable;
|
||||
|
||||
D3DVIEWPORT9 vp;
|
||||
|
||||
bool swapBuffers() {
|
||||
HRESULT result;
|
||||
if (resizable) {
|
||||
RECT vRect;
|
||||
GetClientRect(hWnd, &vRect);
|
||||
result = device->Present(&vRect, &vRect, 0, 0);
|
||||
}
|
||||
else {
|
||||
result = device->Present(0, 0, 0, 0);
|
||||
}
|
||||
return result != D3DERR_DEVICELOST;
|
||||
}
|
||||
|
||||
kinc_g4_shader_t *pixelShader = nullptr;
|
||||
kinc_g4_shader_t *vertexShader = nullptr;
|
||||
IDirect3DSurface9 *backBuffer = nullptr;
|
||||
IDirect3DSurface9 *depthBuffer = nullptr;
|
||||
|
||||
void initDeviceStates() {
|
||||
D3DCAPS9 caps;
|
||||
device->GetDeviceCaps(&caps);
|
||||
|
||||
device->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE);
|
||||
// device->SetRenderState(D3DRS_CULLMODE, D3DCULL_CCW);
|
||||
#ifndef USE_SHADER
|
||||
device->SetRenderState(D3DRS_LIGHTING, FALSE);
|
||||
#endif
|
||||
device->SetRenderState(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
device->SetRenderState(D3DRS_BLENDOP, D3DBLENDOP_ADD);
|
||||
device->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
device->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
|
||||
|
||||
#ifndef USE_SHADER
|
||||
device->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
device->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
device->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_CURRENT);
|
||||
kinc_microsoft_affirm(device->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE));
|
||||
kinc_microsoft_affirm(device->SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE));
|
||||
#endif
|
||||
// if (d3dpp.Windowed != TRUE) Cursor->Hide();
|
||||
|
||||
device->SetSamplerState(0, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
|
||||
device->SetSamplerState(0, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
|
||||
for (int i = 0; i < 16; ++i) {
|
||||
device->SetSamplerState(i, D3DSAMP_MAGFILTER, D3DTEXF_ANISOTROPIC);
|
||||
device->SetSamplerState(i, D3DSAMP_MINFILTER, D3DTEXF_ANISOTROPIC);
|
||||
device->SetSamplerState(i, D3DSAMP_MIPFILTER, D3DTEXF_LINEAR);
|
||||
device->SetSamplerState(i, D3DSAMP_MAXANISOTROPY, caps.MaxAnisotropy);
|
||||
}
|
||||
|
||||
device->SetSamplerState(D3DVERTEXTEXTURESAMPLER0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR);
|
||||
device->SetSamplerState(D3DVERTEXTEXTURESAMPLER0, D3DSAMP_MINFILTER, D3DTEXF_ANISOTROPIC);
|
||||
|
||||
device->SetRenderState(D3DRS_ZENABLE, FALSE);
|
||||
|
||||
device->Clear(0, 0, D3DCLEAR_TARGET, 0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_internal_destroy_window(int window) {}
|
||||
void kinc_g4_internal_destroy() {}
|
||||
|
||||
extern "C" void kinc_internal_resize(int width, int height) {
|
||||
if (!resizable) {
|
||||
return;
|
||||
}
|
||||
|
||||
_width = width;
|
||||
_height = height;
|
||||
kinc_g4_viewport(0, 0, width, height);
|
||||
/*D3DPRESENT_PARAMETERS d3dpp;
|
||||
ZeroMemory(&d3dpp, sizeof(d3dpp));
|
||||
d3dpp.Windowed = (!fullscreen) ? TRUE : FALSE;
|
||||
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
|
||||
d3dpp.BackBufferCount = 2;
|
||||
d3dpp.BackBufferWidth = width;
|
||||
d3dpp.BackBufferHeight = height;
|
||||
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
|
||||
d3dpp.EnableAutoDepthStencil = TRUE;
|
||||
d3dpp.AutoDepthStencilFormat = D3DFMT_D24X8;
|
||||
d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_ONE; //D3DPRESENT_INTERVAL_IMMEDIATE;
|
||||
if (antialiasing()) {
|
||||
if (SUCCEEDED(d3d->CheckDeviceMultiSampleType(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, D3DFMT_A8R8G8B8, FALSE, D3DMULTISAMPLE_4_SAMPLES, nullptr)))
|
||||
d3dpp.MultiSampleType = D3DMULTISAMPLE_4_SAMPLES;
|
||||
if (SUCCEEDED(d3d->CheckDeviceMultiSampleType(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, D3DFMT_A8R8G8B8, FALSE, D3DMULTISAMPLE_8_SAMPLES, nullptr)))
|
||||
d3dpp.MultiSampleType = D3DMULTISAMPLE_8_SAMPLES;
|
||||
}
|
||||
else {
|
||||
d3dpp.MultiSampleType = D3DMULTISAMPLE_NONE;
|
||||
}
|
||||
|
||||
device->Reset(&d3dpp);
|
||||
|
||||
initDeviceStates();*/
|
||||
}
|
||||
|
||||
extern "C" void kinc_internal_change_framebuffer(int window, struct kinc_framebuffer_options *frame) {}
|
||||
|
||||
void kinc_g4_internal_init() {}
|
||||
|
||||
void kinc_g4_internal_init_window(int windowId, int depthBufferBits, int stencilBufferBits, bool vsync) {
|
||||
bool fullscreen = kinc_window_get_mode(windowId) == KINC_WINDOW_MODE_FULLSCREEN || kinc_window_get_mode(windowId) == KINC_WINDOW_MODE_EXCLUSIVE_FULLSCREEN;
|
||||
|
||||
d3d = Direct3DCreate9(D3D_SDK_VERSION);
|
||||
|
||||
hWnd = kinc_windows_window_handle(windowId);
|
||||
long style = GetWindowLong(hWnd, GWL_STYLE);
|
||||
|
||||
resizable = false;
|
||||
|
||||
if ((style & WS_SIZEBOX) != 0) {
|
||||
resizable = true;
|
||||
}
|
||||
|
||||
if ((style & WS_MAXIMIZEBOX) != 0) {
|
||||
resizable = true;
|
||||
}
|
||||
|
||||
// TODO (DK) just setup the primary window for now and ignore secondaries
|
||||
// -this should probably be implemented via swap chain for real at a later time
|
||||
// -http://www.mvps.org/directx/articles/rendering_to_multiple_windows.htm
|
||||
if (windowId > 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef KINC_WINDOWS
|
||||
// TODO (DK) convert depthBufferBits + stencilBufferBits to: d3dpp.AutoDepthStencilFormat = D3DFMT_D24X8;
|
||||
D3DPRESENT_PARAMETERS d3dpp;
|
||||
ZeroMemory(&d3dpp, sizeof(d3dpp));
|
||||
d3dpp.Windowed = (!fullscreen) ? TRUE : FALSE;
|
||||
|
||||
if (resizable) {
|
||||
d3dpp.SwapEffect = D3DSWAPEFFECT_COPY;
|
||||
d3dpp.BackBufferCount = 1;
|
||||
kinc_display_mode_t mode = kinc_display_current_mode(kinc_primary_display());
|
||||
d3dpp.BackBufferWidth = mode.width;
|
||||
d3dpp.BackBufferHeight = mode.height;
|
||||
}
|
||||
else {
|
||||
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
|
||||
d3dpp.BackBufferCount = 2;
|
||||
d3dpp.BackBufferWidth = kinc_window_width(windowId);
|
||||
d3dpp.BackBufferHeight = kinc_window_height(windowId);
|
||||
}
|
||||
|
||||
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
|
||||
d3dpp.EnableAutoDepthStencil = TRUE;
|
||||
d3dpp.AutoDepthStencilFormat = D3DFMT_D24X8;
|
||||
d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_ONE;
|
||||
// d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE;
|
||||
d3dpp.MultiSampleType = D3DMULTISAMPLE_NONE;
|
||||
if (kinc_g4_antialiasing_samples() > 1) {
|
||||
for (int samples = min(kinc_g4_antialiasing_samples(), 16); samples > 1; --samples) {
|
||||
if (SUCCEEDED(d3d->CheckDeviceMultiSampleType(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, D3DFMT_A8R8G8B8, FALSE, (D3DMULTISAMPLE_TYPE)samples, nullptr))) {
|
||||
d3dpp.MultiSampleType = (D3DMULTISAMPLE_TYPE)samples;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!SUCCEEDED(d3d->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd, D3DCREATE_HARDWARE_VERTEXPROCESSING, &d3dpp, &device)))
|
||||
d3d->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp, &device);
|
||||
// d3d->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_REF, hWnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING, &d3dpp, &device);
|
||||
|
||||
#ifdef KINC_WINDOWS
|
||||
// if (System::hasShowWindowFlag(/*windowId*/)) {
|
||||
ShowWindow(hWnd, SW_SHOWDEFAULT);
|
||||
UpdateWindow(hWnd);
|
||||
//}
|
||||
#endif
|
||||
|
||||
initDeviceStates();
|
||||
|
||||
#ifdef KINC_WINDOWS
|
||||
if (fullscreen) {
|
||||
// hz = d3dpp.FullScreen_RefreshRateInHz;
|
||||
D3DDISPLAYMODE mode;
|
||||
device->GetDisplayMode(0, &mode);
|
||||
hz = mode.RefreshRate;
|
||||
}
|
||||
if (!fullscreen || hz == 0) {
|
||||
DEVMODE devMode;
|
||||
EnumDisplaySettings(NULL, ENUM_CURRENT_SETTINGS, &devMode);
|
||||
hz = devMode.dmDisplayFrequency;
|
||||
}
|
||||
#endif
|
||||
|
||||
// vsync = d3dpp.PresentationInterval != D3DPRESENT_INTERVAL_IMMEDIATE;
|
||||
|
||||
kinc_ticks_t test1 = kinc_timestamp();
|
||||
for (int i = 0; i < 3; ++i) {
|
||||
kinc_g4_swap_buffers();
|
||||
}
|
||||
kinc_ticks_t test2 = kinc_timestamp();
|
||||
if (test2 - test1 < (1.0 / hz) * kinc_frequency()) {
|
||||
vsync = false;
|
||||
}
|
||||
else {
|
||||
vsync = true;
|
||||
}
|
||||
|
||||
_width = kinc_window_width(windowId);
|
||||
_height = kinc_window_height(windowId);
|
||||
}
|
||||
|
||||
void kinc_g4_flush() {}
|
||||
|
||||
namespace {
|
||||
DWORD convertFilter(kinc_g4_texture_filter_t filter) {
|
||||
switch (filter) {
|
||||
case KINC_G4_TEXTURE_FILTER_POINT:
|
||||
return D3DTEXF_POINT;
|
||||
case KINC_G4_TEXTURE_FILTER_LINEAR:
|
||||
return D3DTEXF_LINEAR;
|
||||
case KINC_G4_TEXTURE_FILTER_ANISOTROPIC:
|
||||
return D3DTEXF_ANISOTROPIC;
|
||||
default:
|
||||
return D3DTEXF_POINT;
|
||||
}
|
||||
}
|
||||
|
||||
DWORD convertMipFilter(kinc_g4_mipmap_filter_t filter) {
|
||||
switch (filter) {
|
||||
case KINC_G4_MIPMAP_FILTER_NONE:
|
||||
return D3DTEXF_NONE;
|
||||
case KINC_G4_MIPMAP_FILTER_POINT:
|
||||
return D3DTEXF_POINT;
|
||||
case KINC_G4_MIPMAP_FILTER_LINEAR:
|
||||
return D3DTEXF_LINEAR;
|
||||
default:
|
||||
return D3DTEXF_NONE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture_magnification_filter(kinc_g4_texture_unit_t texunit, kinc_g4_texture_filter_t filter) {
|
||||
device->SetSamplerState(texunit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], D3DSAMP_MAGFILTER, convertFilter(filter));
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture3d_magnification_filter(kinc_g4_texture_unit_t texunit, kinc_g4_texture_filter_t filter) {
|
||||
kinc_g4_set_texture_magnification_filter(texunit, filter);
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture_minification_filter(kinc_g4_texture_unit_t texunit, kinc_g4_texture_filter_t filter) {
|
||||
device->SetSamplerState(texunit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], D3DSAMP_MINFILTER, convertFilter(filter));
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture3d_minification_filter(kinc_g4_texture_unit_t texunit, kinc_g4_texture_filter_t filter) {
|
||||
kinc_g4_set_texture_minification_filter(texunit, filter);
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture_mipmap_filter(kinc_g4_texture_unit_t texunit, kinc_g4_mipmap_filter_t filter) {
|
||||
device->SetSamplerState(texunit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], D3DSAMP_MIPFILTER, convertMipFilter(filter));
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture3d_mipmap_filter(kinc_g4_texture_unit_t texunit, kinc_g4_mipmap_filter_t filter) {
|
||||
kinc_g4_set_texture_mipmap_filter(texunit, filter);
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture_compare_mode(kinc_g4_texture_unit_t unit, bool enabled) {}
|
||||
|
||||
void kinc_g4_set_texture_compare_func(kinc_g4_texture_unit_t unit, kinc_g4_compare_mode_t mode) {}
|
||||
|
||||
void kinc_g4_set_cubemap_compare_mode(kinc_g4_texture_unit_t unit, bool enabled) {}
|
||||
|
||||
void kinc_g4_set_cubemap_compare_func(kinc_g4_texture_unit_t unit, kinc_g4_compare_mode_t mode) {}
|
||||
|
||||
void kinc_g4_set_texture_max_anisotropy(kinc_g4_texture_unit_t unit, uint16_t max_anisotropy) {
|
||||
device->SetSamplerState(unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], D3DSAMP_MAXANISOTROPY, max_anisotropy);
|
||||
}
|
||||
|
||||
void kinc_g4_set_cubemap_max_anisotropy(kinc_g4_texture_unit_t unit, uint16_t max_anisotropy) {}
|
||||
|
||||
void kinc_g4_set_texture_lod(kinc_g4_texture_unit_t unit, float lod_min_clamp, float lod_max_clamp) {
|
||||
// device->SetSamplerState(unit.impl.unit, D3DSAMP_, );
|
||||
}
|
||||
|
||||
void kinc_g4_set_cubemap_lod(kinc_g4_texture_unit_t unit, float lod_min_clamp, float lod_max_clamp) {}
|
||||
|
||||
void kinc_g4_set_render_targets(struct kinc_g4_render_target **targets, int count) {
|
||||
// if (backBuffer != nullptr) backBuffer->Release();
|
||||
|
||||
if (backBuffer == nullptr) {
|
||||
device->GetRenderTarget(0, &backBuffer);
|
||||
device->GetDepthStencilSurface(&depthBuffer);
|
||||
}
|
||||
kinc_microsoft_affirm(device->SetDepthStencilSurface(targets[0]->impl.depthSurface));
|
||||
for (int i = 0; i < count; ++i) {
|
||||
kinc_microsoft_affirm(device->SetRenderTarget(i, targets[i]->impl.colorSurface));
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_render_target_face(struct kinc_g4_render_target *texture, int face) {}
|
||||
|
||||
int kinc_g4_max_bound_textures(void) {
|
||||
return 8;
|
||||
}
|
||||
|
||||
// void Graphics::setDepthStencilTarget(Texture* texture) {
|
||||
// //if (depthBuffer != nullptr) depthBuffer->Release();
|
||||
// device->GetDepthStencilSurface(&depthBuffer);
|
||||
// Microsoft::affirm(device->SetDepthStencilSurface(dcast<D3D9Texture*>(texture)->getSurface()));
|
||||
//}
|
||||
|
||||
void kinc_g4_restore_render_target() {
|
||||
if (backBuffer != nullptr) {
|
||||
device->SetRenderTarget(0, backBuffer);
|
||||
device->SetRenderTarget(1, nullptr);
|
||||
backBuffer->Release();
|
||||
backBuffer = nullptr;
|
||||
device->SetDepthStencilSurface(depthBuffer);
|
||||
depthBuffer->Release();
|
||||
depthBuffer = nullptr;
|
||||
kinc_g4_viewport(0, 0, _width, _height);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_draw_indexed_vertices() {
|
||||
device->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, 0, 0, kinc_g4_vertex_buffer_count(kinc_internal_current_vertex_buffer), 0,
|
||||
kinc_g4_index_buffer_count(kinc_internal_current_index_buffer) / 3);
|
||||
}
|
||||
|
||||
void kinc_g4_draw_indexed_vertices_from_to(int start, int count) {
|
||||
device->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, 0, 0, kinc_g4_vertex_buffer_count(kinc_internal_current_vertex_buffer), start, count / 3);
|
||||
}
|
||||
|
||||
void kinc_g4_draw_indexed_vertices_from_to_from(int start, int count, int vertex_offset) {
|
||||
device->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, vertex_offset, 0, kinc_g4_vertex_buffer_count(kinc_internal_current_vertex_buffer), start, count / 3);
|
||||
}
|
||||
|
||||
void kinc_g4_draw_indexed_vertices_instanced(int instanceCount) {
|
||||
kinc_microsoft_affirm(device->SetStreamSourceFreq(kinc_internal_current_vertex_buffer->impl._offset, (D3DSTREAMSOURCE_INDEXEDDATA | instanceCount)));
|
||||
device->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, 0, 0, kinc_g4_vertex_buffer_count(kinc_internal_current_vertex_buffer), 0,
|
||||
kinc_g4_index_buffer_count(kinc_internal_current_index_buffer) / 3);
|
||||
}
|
||||
|
||||
void kinc_g4_draw_indexed_vertices_instanced_from_to(int instanceCount, int start, int count) {
|
||||
kinc_microsoft_affirm(device->SetStreamSourceFreq(kinc_internal_current_vertex_buffer->impl._offset, (D3DSTREAMSOURCE_INDEXEDDATA | instanceCount)));
|
||||
device->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, 0, 0, kinc_g4_vertex_buffer_count(kinc_internal_current_vertex_buffer), start, count / 3);
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture_addressing(kinc_g4_texture_unit_t unit, kinc_g4_texture_direction_t dir, kinc_g4_texture_addressing_t addressing) {
|
||||
DWORD value = 0;
|
||||
switch (addressing) {
|
||||
case KINC_G4_TEXTURE_ADDRESSING_REPEAT:
|
||||
value = D3DTADDRESS_WRAP;
|
||||
break;
|
||||
case KINC_G4_TEXTURE_ADDRESSING_MIRROR:
|
||||
value = D3DTADDRESS_MIRROR;
|
||||
break;
|
||||
case KINC_G4_TEXTURE_ADDRESSING_CLAMP:
|
||||
value = D3DTADDRESS_CLAMP;
|
||||
break;
|
||||
case KINC_G4_TEXTURE_ADDRESSING_BORDER:
|
||||
value = D3DTADDRESS_BORDER;
|
||||
break;
|
||||
}
|
||||
device->SetSamplerState(unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], dir == KINC_G4_TEXTURE_DIRECTION_U ? D3DSAMP_ADDRESSU : D3DSAMP_ADDRESSV, value);
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture3d_addressing(kinc_g4_texture_unit_t unit, kinc_g4_texture_direction_t dir, kinc_g4_texture_addressing_t addressing) {
|
||||
kinc_g4_set_texture_addressing(unit, dir, addressing);
|
||||
}
|
||||
|
||||
namespace {
|
||||
void tod3dmatrix(kinc_matrix4x4_t *matrix, D3DMATRIX &d3dm) {
|
||||
d3dm._11 = kinc_matrix4x4_get(matrix, 0, 0);
|
||||
d3dm._12 = kinc_matrix4x4_get(matrix, 0, 1);
|
||||
d3dm._13 = kinc_matrix4x4_get(matrix, 0, 2);
|
||||
d3dm._14 = kinc_matrix4x4_get(matrix, 0, 3);
|
||||
|
||||
d3dm._21 = kinc_matrix4x4_get(matrix, 1, 0);
|
||||
d3dm._22 = kinc_matrix4x4_get(matrix, 1, 1);
|
||||
d3dm._23 = kinc_matrix4x4_get(matrix, 1, 2);
|
||||
d3dm._24 = kinc_matrix4x4_get(matrix, 1, 3);
|
||||
|
||||
d3dm._31 = kinc_matrix4x4_get(matrix, 2, 0);
|
||||
d3dm._32 = kinc_matrix4x4_get(matrix, 2, 1);
|
||||
d3dm._33 = kinc_matrix4x4_get(matrix, 2, 2);
|
||||
d3dm._34 = kinc_matrix4x4_get(matrix, 2, 3);
|
||||
|
||||
d3dm._41 = kinc_matrix4x4_get(matrix, 3, 0);
|
||||
d3dm._42 = kinc_matrix4x4_get(matrix, 3, 1);
|
||||
d3dm._43 = kinc_matrix4x4_get(matrix, 3, 2);
|
||||
d3dm._44 = kinc_matrix4x4_get(matrix, 3, 3);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_clear(unsigned flags, unsigned color, float depth, int stencil) {
|
||||
device->Clear(0, nullptr, flags, color, depth, stencil);
|
||||
}
|
||||
|
||||
void kinc_g4_begin(int window) {
|
||||
// TODO (DK) ignore secondary windows for now
|
||||
if (window > 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
kinc_g4_viewport(0, 0, _width, _height);
|
||||
device->BeginScene();
|
||||
}
|
||||
|
||||
void kinc_g4_viewport(int x, int y, int width, int height) {
|
||||
vp.X = x;
|
||||
vp.Y = y;
|
||||
vp.Width = width;
|
||||
vp.Height = height;
|
||||
device->SetViewport(&vp);
|
||||
}
|
||||
|
||||
void kinc_g4_scissor(int x, int y, int width, int height) {
|
||||
device->SetRenderState(D3DRS_SCISSORTESTENABLE, TRUE);
|
||||
|
||||
RECT rc;
|
||||
rc.left = x;
|
||||
rc.top = y;
|
||||
rc.right = x + width;
|
||||
rc.bottom = y + height;
|
||||
device->SetScissorRect(&rc);
|
||||
}
|
||||
|
||||
void kinc_g4_disable_scissor() {
|
||||
device->SetRenderState(D3DRS_SCISSORTESTENABLE, FALSE);
|
||||
}
|
||||
|
||||
void kinc_g4_end(int window) {
|
||||
// TODO (DK) ignore secondary windows for now
|
||||
if (window > 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
/*if (backBuffer != nullptr) {
|
||||
backBuffer->Release();
|
||||
backBuffer = nullptr;
|
||||
}*/
|
||||
device->EndScene();
|
||||
}
|
||||
|
||||
bool kinc_window_vsynced(int window) {
|
||||
return vsync;
|
||||
}
|
||||
|
||||
// unsigned Graphics4::refreshRate() {
|
||||
// return hz;
|
||||
//}
|
||||
|
||||
bool kinc_g4_swap_buffers() {
|
||||
return ::swapBuffers();
|
||||
}
|
||||
|
||||
void kinc_g4_set_stencil_reference_value(int value) {}
|
||||
|
||||
void kinc_g4_set_blend_constant(float r, float g, float b, float a) {
|
||||
device->SetRenderState(D3DRS_BLENDFACTOR, D3DCOLOR_RGBA((int)(r * 255), (int)(g * 255), (int)(b * 255), (int)(a * 255)));
|
||||
}
|
||||
|
||||
void kinc_g4_set_bool(kinc_g4_constant_location_t position, bool value) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
BOOL bools[4];
|
||||
bools[0] = value ? 1 : 0;
|
||||
bools[1] = bools[0];
|
||||
bools[2] = bools[0];
|
||||
bools[3] = bools[0];
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantB(position.impl.reg.regindex, &bools[0], 1);
|
||||
else
|
||||
device->SetPixelShaderConstantB(position.impl.reg.regindex, &bools[0], 1);
|
||||
}
|
||||
|
||||
void kinc_g4_set_int(kinc_g4_constant_location_t position, int value) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
if (position.impl.reg.regtype == 'f') {
|
||||
kinc_g4_set_float(position, (float)value);
|
||||
}
|
||||
else {
|
||||
int ints[4];
|
||||
ints[0] = value;
|
||||
ints[1] = value;
|
||||
ints[2] = value;
|
||||
ints[3] = value;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
else
|
||||
device->SetPixelShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_int2(kinc_g4_constant_location_t position, int value1, int value2) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
if (position.impl.reg.regtype == 'f') {
|
||||
kinc_g4_set_float2(position, (float)value1, (float)value2);
|
||||
}
|
||||
else {
|
||||
int ints[4];
|
||||
ints[0] = value1;
|
||||
ints[1] = value2;
|
||||
ints[2] = value1;
|
||||
ints[3] = value2;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
else
|
||||
device->SetPixelShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_int3(kinc_g4_constant_location_t position, int value1, int value2, int value3) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
if (position.impl.reg.regtype == 'f') {
|
||||
kinc_g4_set_float3(position, (float)value1, (float)value2, (float)value3);
|
||||
}
|
||||
else {
|
||||
int ints[4];
|
||||
ints[0] = value1;
|
||||
ints[1] = value2;
|
||||
ints[2] = value3;
|
||||
ints[3] = value1;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
else
|
||||
device->SetPixelShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_int4(kinc_g4_constant_location_t position, int value1, int value2, int value3, int value4) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
if (position.impl.reg.regtype == 'f') {
|
||||
kinc_g4_set_float4(position, (float)value1, (float)value2, (float)value3, (float)value4);
|
||||
}
|
||||
else {
|
||||
int ints[4];
|
||||
ints[0] = value1;
|
||||
ints[1] = value2;
|
||||
ints[2] = value3;
|
||||
ints[3] = value4;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
else
|
||||
device->SetPixelShaderConstantI(position.impl.reg.regindex, &ints[0], 1);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_ints(kinc_g4_constant_location_t location, int *values, int count) {
|
||||
if (location.impl.shaderType == -1)
|
||||
return;
|
||||
int registerCount = (count + 3) / 4; // round up
|
||||
if (registerCount == count / 4) { // round down
|
||||
if (location.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantI(location.impl.reg.regindex, values, registerCount);
|
||||
else
|
||||
device->SetPixelShaderConstantI(location.impl.reg.regindex, values, registerCount);
|
||||
}
|
||||
else {
|
||||
int *data = (int *)alloca(registerCount * 4 * sizeof(int));
|
||||
memcpy(data, values, count * sizeof(int));
|
||||
if (location.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantI(location.impl.reg.regindex, data, registerCount);
|
||||
else
|
||||
device->SetPixelShaderConstantI(location.impl.reg.regindex, data, registerCount);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_float(kinc_g4_constant_location_t position, float value) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
float floats[4];
|
||||
floats[0] = value;
|
||||
floats[1] = value;
|
||||
floats[2] = value;
|
||||
floats[3] = value;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
else
|
||||
device->SetPixelShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
}
|
||||
|
||||
void kinc_g4_set_float2(kinc_g4_constant_location_t position, float value1, float value2) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
float floats[4];
|
||||
floats[0] = value1;
|
||||
floats[1] = value2;
|
||||
floats[2] = value1;
|
||||
floats[3] = value2;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
else
|
||||
device->SetPixelShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
}
|
||||
|
||||
void kinc_g4_set_float3(kinc_g4_constant_location_t position, float value1, float value2, float value3) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
float floats[4];
|
||||
floats[0] = value1;
|
||||
floats[1] = value2;
|
||||
floats[2] = value3;
|
||||
floats[3] = value1;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
else
|
||||
device->SetPixelShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
}
|
||||
|
||||
void kinc_g4_set_float4(kinc_g4_constant_location_t position, float value1, float value2, float value3, float value4) {
|
||||
if (position.impl.shaderType == -1)
|
||||
return;
|
||||
float floats[4];
|
||||
floats[0] = value1;
|
||||
floats[1] = value2;
|
||||
floats[2] = value3;
|
||||
floats[3] = value4;
|
||||
if (position.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
else
|
||||
device->SetPixelShaderConstantF(position.impl.reg.regindex, floats, 1);
|
||||
}
|
||||
|
||||
void kinc_g4_set_floats(kinc_g4_constant_location_t location, float *values, int count) {
|
||||
if (location.impl.shaderType == -1)
|
||||
return;
|
||||
int registerCount = (count + 3) / 4; // round up
|
||||
if (registerCount == count / 4) { // round down
|
||||
if (location.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(location.impl.reg.regindex, values, registerCount);
|
||||
else
|
||||
device->SetPixelShaderConstantF(location.impl.reg.regindex, values, registerCount);
|
||||
}
|
||||
else {
|
||||
float *data = (float *)alloca(registerCount * 4 * sizeof(float));
|
||||
memcpy(data, values, count * sizeof(float));
|
||||
if (location.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(location.impl.reg.regindex, data, registerCount);
|
||||
else
|
||||
device->SetPixelShaderConstantF(location.impl.reg.regindex, data, registerCount);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_matrix4(kinc_g4_constant_location_t location, kinc_matrix4x4_t *value) {
|
||||
if (location.impl.shaderType == -1)
|
||||
return;
|
||||
float floats[16];
|
||||
for (int y = 0; y < 4; ++y) {
|
||||
for (int x = 0; x < 4; ++x) {
|
||||
floats[y * 4 + x] = kinc_matrix4x4_get(value, y, x);
|
||||
}
|
||||
}
|
||||
if (location.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(location.impl.reg.regindex, floats, 4);
|
||||
else
|
||||
device->SetPixelShaderConstantF(location.impl.reg.regindex, floats, 4);
|
||||
}
|
||||
|
||||
void kinc_g4_set_matrix3(kinc_g4_constant_location_t location, kinc_matrix3x3_t *value) {
|
||||
if (location.impl.shaderType == -1)
|
||||
return;
|
||||
float floats[12];
|
||||
for (int y = 0; y < 3; ++y) {
|
||||
for (int x = 0; x < 3; ++x) {
|
||||
floats[y * 4 + x] = kinc_matrix3x3_get(value, y, x);
|
||||
}
|
||||
}
|
||||
if (location.impl.shaderType == 0)
|
||||
device->SetVertexShaderConstantF(location.impl.reg.regindex, floats, 3);
|
||||
else
|
||||
device->SetPixelShaderConstantF(location.impl.reg.regindex, floats, 3);
|
||||
}
|
||||
|
||||
void kinc_g4_set_vertex_buffers(kinc_g4_vertex_buffer_t **buffers, int count) {
|
||||
for (int i = 0; i < count; ++i) {
|
||||
kinc_internal_g4_vertex_buffer_set(buffers[i], i);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_index_buffer(kinc_g4_index_buffer_t *buffer) {
|
||||
kinc_internal_g4_index_buffer_set(buffer);
|
||||
}
|
||||
|
||||
#ifdef KINC_KONG
|
||||
void kinc_internal_texture_set(kinc_g4_texture_t *texture, uint32_t unit);
|
||||
|
||||
void kinc_g4_set_texture(uint32_t unit, struct kinc_g4_texture *texture) {
|
||||
kinc_internal_texture_set(texture, unit);
|
||||
}
|
||||
#else
|
||||
void kinc_internal_texture_set(kinc_g4_texture_t *texture, kinc_g4_texture_unit_t unit);
|
||||
|
||||
void kinc_g4_set_texture(kinc_g4_texture_unit_t unit, struct kinc_g4_texture *texture) {
|
||||
kinc_internal_texture_set(texture, unit);
|
||||
}
|
||||
#endif
|
||||
|
||||
void kinc_g4_set_image_texture(kinc_g4_texture_unit_t unit, struct kinc_g4_texture *texture) {}
|
||||
|
||||
unsigned queryCount = 0;
|
||||
std::vector<IDirect3DQuery9 *> queryPool;
|
||||
|
||||
bool kinc_g4_init_occlusion_query(unsigned *occlusionQuery) {
|
||||
// check if the runtime supports queries
|
||||
HRESULT result = device->CreateQuery(D3DQUERYTYPE_OCCLUSION, NULL);
|
||||
if (FAILED(result)) {
|
||||
kinc_log(KINC_LOG_LEVEL_WARNING, "Internal query creation failed, result: 0x%X.", result);
|
||||
return false;
|
||||
}
|
||||
|
||||
IDirect3DQuery9 *pQuery = nullptr;
|
||||
device->CreateQuery(D3DQUERYTYPE_OCCLUSION, &pQuery);
|
||||
|
||||
queryPool.push_back(pQuery);
|
||||
*occlusionQuery = queryCount;
|
||||
++queryCount;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void kinc_g4_delete_occlusion_query(unsigned occlusionQuery) {
|
||||
if (occlusionQuery < queryPool.size())
|
||||
queryPool[occlusionQuery] = nullptr;
|
||||
}
|
||||
|
||||
void kinc_g4_start_occlusion_query(unsigned occlusionQuery) {
|
||||
IDirect3DQuery9 *pQuery = queryPool[occlusionQuery];
|
||||
if (pQuery != nullptr) {
|
||||
pQuery->Issue(D3DISSUE_BEGIN);
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_end_occlusion_query(unsigned occlusionQuery) {
|
||||
IDirect3DQuery9 *pQuery = queryPool[occlusionQuery];
|
||||
if (pQuery != nullptr) {
|
||||
pQuery->Issue(D3DISSUE_END);
|
||||
}
|
||||
}
|
||||
|
||||
bool kinc_g4_are_query_results_available(unsigned occlusionQuery) {
|
||||
IDirect3DQuery9 *pQuery = queryPool[occlusionQuery];
|
||||
if (pQuery != nullptr) {
|
||||
if (S_OK == pQuery->GetData(0, 0, 0)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void kinc_g4_get_query_results(unsigned occlusionQuery, unsigned *pixelCount) {
|
||||
IDirect3DQuery9 *pQuery = queryPool[occlusionQuery];
|
||||
if (pQuery != nullptr) {
|
||||
DWORD numberOfPixelsDrawn;
|
||||
HRESULT result = pQuery->GetData(&numberOfPixelsDrawn, sizeof(DWORD), 0);
|
||||
if (S_OK == result) {
|
||||
*pixelCount = numberOfPixelsDrawn;
|
||||
}
|
||||
else {
|
||||
kinc_log(KINC_LOG_LEVEL_WARNING, "Check first if results are available");
|
||||
*pixelCount = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_set_texture_array(kinc_g4_texture_unit_t unit, struct kinc_g4_texture_array *array) {}
|
||||
|
||||
void kinc_g4_set_pipeline(struct kinc_g4_pipeline *pipeline) {
|
||||
kinc_g4_internal_set_pipeline(pipeline);
|
||||
}
|
||||
|
||||
bool kinc_g4_supports_instanced_rendering() {
|
||||
return true;
|
||||
}
|
||||
|
||||
bool kinc_g4_supports_compute_shaders() {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool kinc_g4_supports_blend_constants() {
|
||||
D3DCAPS9 pCaps = {};
|
||||
if (FAILED(device->GetDeviceCaps(&pCaps))) {
|
||||
kinc_log(KINC_LOG_LEVEL_ERROR, "Failed to get device caps");
|
||||
return false;
|
||||
}
|
||||
|
||||
return ((pCaps.SrcBlendCaps & D3DPBLENDCAPS_BLENDFACTOR) != 0) && ((pCaps.DestBlendCaps & D3DPBLENDCAPS_BLENDFACTOR) != 0);
|
||||
}
|
||||
|
||||
bool kinc_g4_supports_non_pow2_textures() {
|
||||
D3DCAPS9 pCaps = {};
|
||||
if (FAILED(device->GetDeviceCaps(&pCaps))) {
|
||||
kinc_log(KINC_LOG_LEVEL_ERROR, "Failed to get device caps");
|
||||
return false;
|
||||
}
|
||||
// only advertise full npot support
|
||||
return ((pCaps.TextureCaps & D3DPTEXTURECAPS_POW2) == 0) && ((pCaps.TextureCaps & D3DPTEXTURECAPS_NONPOW2CONDITIONAL) == 0);
|
||||
}
|
||||
|
||||
bool kinc_g4_render_targets_inverted_y(void) {
|
||||
return false;
|
||||
}
|
||||
|
||||
void kinc_g4_set_constant_buffer(uint32_t id, struct kinc_g4_constant_buffer *buffer) {}
|
@ -0,0 +1,12 @@
|
||||
#pragma once
|
||||
|
||||
#include <kinc/graphics4/graphics.h>
|
||||
#include <kinc/math/matrix.h>
|
||||
|
||||
#ifndef NDEBUG
|
||||
#define D3D_DEBUG_INFO
|
||||
#endif
|
||||
#include <d3d9.h>
|
||||
|
||||
extern IDirect3D9 *d3d;
|
||||
extern IDirect3DDevice9 *device;
|
@ -0,0 +1,22 @@
|
||||
#include <kinc/graphics4/compute.h>
|
||||
#include <kinc/graphics4/rendertarget.h>
|
||||
#include <kinc/graphics4/texture.h>
|
||||
#include <kinc/math/core.h>
|
||||
|
||||
void kinc_g4_compute_shader_init(kinc_g4_compute_shader *shader, void *source, int length) {}
|
||||
|
||||
void kinc_g4_compute_shader_destroy(kinc_g4_compute_shader *shader) {}
|
||||
|
||||
kinc_g4_constant_location_t kinc_g4_compute_shader_get_constant_location(kinc_g4_compute_shader *shader, const char *name) {
|
||||
kinc_g4_constant_location_t location = {0};
|
||||
return location;
|
||||
}
|
||||
|
||||
kinc_g4_texture_unit_t kinc_g4_compute_shader_get_texture_unit(kinc_g4_compute_shader *shader, const char *name) {
|
||||
kinc_g4_texture_unit_t unit = {0};
|
||||
return unit;
|
||||
}
|
||||
|
||||
void kinc_g4_set_compute_shader(kinc_g4_compute_shader *shader) {}
|
||||
|
||||
void kinc_g4_compute(int x, int y, int z) {}
|
@ -0,0 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct kinc_g4_compute_shader_impl {
|
||||
int nothing;
|
||||
} kinc_g4_compute_shader_impl;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,34 @@
|
||||
#ifdef KINC_KONG
|
||||
|
||||
#include <kinc/graphics4/constantbuffer.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
void kinc_g4_constant_buffer_init(kinc_g4_constant_buffer *buffer, size_t size) {
|
||||
buffer->impl.size = size;
|
||||
buffer->impl.last_start = 0;
|
||||
buffer->impl.last_size = size;
|
||||
}
|
||||
|
||||
void kinc_g4_constant_buffer_destroy(kinc_g4_constant_buffer *buffer) {}
|
||||
|
||||
uint8_t *kinc_g4_constant_buffer_lock_all(kinc_g4_constant_buffer *buffer) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
uint8_t *kinc_g4_constant_buffer_lock(kinc_g4_constant_buffer *buffer, size_t start, size_t size) {
|
||||
buffer->impl.last_start = start;
|
||||
buffer->impl.last_size = size;
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void kinc_g4_constant_buffer_unlock_all(kinc_g4_constant_buffer *buffer) {}
|
||||
|
||||
void kinc_g4_constant_buffer_unlock(kinc_g4_constant_buffer *buffer, size_t count) {}
|
||||
|
||||
size_t kinc_g4_constant_buffer_size(kinc_g4_constant_buffer *buffer) {
|
||||
return buffer->impl.size;
|
||||
}
|
||||
|
||||
#endif
|
@ -0,0 +1,11 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef KINC_KONG
|
||||
|
||||
typedef struct kinc_g4_constant_buffer_impl {
|
||||
size_t size;
|
||||
size_t last_start;
|
||||
size_t last_size;
|
||||
} kinc_g4_constant_buffer_impl;
|
||||
|
||||
#endif
|
@ -0,0 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include "IndexBufferImpl.h"
|
||||
#include "RenderTargetImpl.h"
|
||||
#include "ShaderImpl.h"
|
||||
#include "VertexBufferImpl.h"
|
@ -0,0 +1,56 @@
|
||||
#include <kinc/graphics4/graphics.h>
|
||||
#include <kinc/graphics4/indexbuffer.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
struct kinc_g4_index_buffer *kinc_internal_current_index_buffer = NULL;
|
||||
|
||||
void kinc_g4_index_buffer_init(kinc_g4_index_buffer_t *buffer, int count, kinc_g4_index_buffer_format_t format, kinc_g4_usage_t usage) {
|
||||
buffer->impl.count = count;
|
||||
buffer->impl.format = format;
|
||||
|
||||
DWORD usageFlags = D3DUSAGE_WRITEONLY;
|
||||
if (usage == KINC_G4_USAGE_DYNAMIC) {
|
||||
usageFlags = D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY;
|
||||
}
|
||||
|
||||
kinc_microsoft_affirm(device->CreateIndexBuffer(
|
||||
sizeof(int) * count, usageFlags, format == KINC_G4_INDEX_BUFFER_FORMAT_32BIT ? D3DFMT_INDEX32 : D3DFMT_INDEX16, D3DPOOL_DEFAULT, &buffer->impl.ib, 0));
|
||||
}
|
||||
|
||||
void kinc_g4_index_buffer_destroy(kinc_g4_index_buffer_t *buffer) {
|
||||
buffer->impl.ib->Release();
|
||||
}
|
||||
|
||||
static int kinc_g4_internal_index_buffer_stride(kinc_g4_index_buffer_t *buffer) {
|
||||
return buffer->impl.format == KINC_G4_INDEX_BUFFER_FORMAT_32BIT ? 4 : 2;
|
||||
}
|
||||
|
||||
void *kinc_g4_index_buffer_lock_all(kinc_g4_index_buffer_t *buffer) {
|
||||
return kinc_g4_index_buffer_lock(buffer, 0, kinc_g4_index_buffer_count(buffer));
|
||||
}
|
||||
|
||||
void *kinc_g4_index_buffer_lock(kinc_g4_index_buffer_t *buffer, int start, int count) {
|
||||
uint8_t *data;
|
||||
kinc_microsoft_affirm(buffer->impl.ib->Lock(0, sizeof(int) * kinc_g4_index_buffer_count(buffer), (void **)&data, D3DLOCK_DISCARD));
|
||||
return &data[start * kinc_g4_internal_index_buffer_stride(buffer)];
|
||||
}
|
||||
|
||||
void kinc_g4_index_buffer_unlock_all(kinc_g4_index_buffer_t *buffer) {
|
||||
kinc_microsoft_affirm(buffer->impl.ib->Unlock());
|
||||
}
|
||||
|
||||
void kinc_g4_index_buffer_unlock(kinc_g4_index_buffer_t *buffer, int count) {
|
||||
kinc_g4_index_buffer_unlock_all(buffer);
|
||||
}
|
||||
|
||||
void kinc_internal_g4_index_buffer_set(kinc_g4_index_buffer_t *buffer) {
|
||||
kinc_internal_current_index_buffer = buffer;
|
||||
kinc_microsoft_affirm(device->SetIndices(buffer->impl.ib));
|
||||
}
|
||||
|
||||
int kinc_g4_index_buffer_count(kinc_g4_index_buffer_t *buffer) {
|
||||
return buffer->impl.count;
|
||||
}
|
@ -0,0 +1,21 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct IDirect3DIndexBuffer9;
|
||||
|
||||
typedef struct {
|
||||
struct IDirect3DIndexBuffer9 *ib;
|
||||
int count;
|
||||
int format;
|
||||
} kinc_g4_index_buffer_impl_t;
|
||||
|
||||
struct kinc_g4_index_buffer;
|
||||
|
||||
extern struct kinc_g4_index_buffer *kinc_internal_current_index_buffer;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,365 @@
|
||||
#include <kinc/graphics4/graphics.h>
|
||||
#include <kinc/graphics4/pipeline.h>
|
||||
#include <kinc/graphics4/shader.h>
|
||||
#include <kinc/graphics4/vertexstructure.h>
|
||||
#include <kinc/log.h>
|
||||
#include <kinc/system.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <malloc.h>
|
||||
|
||||
namespace {
|
||||
_D3DBLEND convert_blend_factor(kinc_g4_blending_factor_t factor) {
|
||||
switch (factor) {
|
||||
case KINC_G4_BLEND_ONE:
|
||||
return D3DBLEND_ONE;
|
||||
case KINC_G4_BLEND_ZERO:
|
||||
return D3DBLEND_ZERO;
|
||||
case KINC_G4_BLEND_SOURCE_ALPHA:
|
||||
return D3DBLEND_SRCALPHA;
|
||||
case KINC_G4_BLEND_DEST_ALPHA:
|
||||
return D3DBLEND_DESTALPHA;
|
||||
case KINC_G4_BLEND_INV_SOURCE_ALPHA:
|
||||
return D3DBLEND_INVSRCALPHA;
|
||||
case KINC_G4_BLEND_INV_DEST_ALPHA:
|
||||
return D3DBLEND_INVDESTALPHA;
|
||||
case KINC_G4_BLEND_CONSTANT:
|
||||
return D3DBLEND_BLENDFACTOR;
|
||||
case KINC_G4_BLEND_INV_CONSTANT:
|
||||
return D3DBLEND_INVBLENDFACTOR;
|
||||
default:
|
||||
assert(false);
|
||||
return D3DBLEND_SRCALPHA;
|
||||
}
|
||||
}
|
||||
|
||||
_D3DBLENDOP convert_blend_operation(kinc_g4_blending_operation_t op) {
|
||||
switch (op) {
|
||||
case KINC_G4_BLENDOP_ADD:
|
||||
return D3DBLENDOP_ADD;
|
||||
case KINC_G4_BLENDOP_SUBTRACT:
|
||||
return D3DBLENDOP_SUBTRACT;
|
||||
case KINC_G4_BLENDOP_REVERSE_SUBTRACT:
|
||||
return D3DBLENDOP_REVSUBTRACT;
|
||||
case KINC_G4_BLENDOP_MIN:
|
||||
return D3DBLENDOP_MIN;
|
||||
case KINC_G4_BLENDOP_MAX:
|
||||
return D3DBLENDOP_MAX;
|
||||
default:
|
||||
assert(false);
|
||||
return D3DBLENDOP_ADD;
|
||||
}
|
||||
}
|
||||
|
||||
_D3DCMPFUNC convert(kinc_g4_compare_mode_t mode) {
|
||||
switch (mode) {
|
||||
default:
|
||||
case KINC_G4_COMPARE_ALWAYS:
|
||||
return D3DCMP_ALWAYS;
|
||||
case KINC_G4_COMPARE_NEVER:
|
||||
return D3DCMP_NEVER;
|
||||
case KINC_G4_COMPARE_EQUAL:
|
||||
return D3DCMP_EQUAL;
|
||||
case KINC_G4_COMPARE_NOT_EQUAL:
|
||||
return D3DCMP_NOTEQUAL;
|
||||
case KINC_G4_COMPARE_LESS:
|
||||
return D3DCMP_LESS;
|
||||
case KINC_G4_COMPARE_LESS_EQUAL:
|
||||
return D3DCMP_LESSEQUAL;
|
||||
case KINC_G4_COMPARE_GREATER:
|
||||
return D3DCMP_GREATER;
|
||||
case KINC_G4_COMPARE_GREATER_EQUAL:
|
||||
return D3DCMP_GREATEREQUAL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_pipeline_init(kinc_g4_pipeline_t *state) {
|
||||
memset(state, 0, sizeof(kinc_g4_pipeline));
|
||||
kinc_g4_internal_pipeline_set_defaults(state);
|
||||
}
|
||||
|
||||
void kinc_g4_pipeline_destroy(kinc_g4_pipeline_t *state) {}
|
||||
|
||||
static int find_attribute(struct ShaderAttribute *attributes, const char *name) {
|
||||
for (int i = 0; i < KINC_INTERNAL_MAX_ATTRIBUTES; ++i) {
|
||||
if (attributes[i].name == 0) {
|
||||
return -1;
|
||||
}
|
||||
if (strcmp(attributes[i].name, name) == 0) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int find_constant(struct ShaderRegister *constants, const char *name) {
|
||||
for (int i = 0; i < KINC_INTERNAL_MAX_CONSTANTS; ++i) {
|
||||
if (constants[i].name == 0) {
|
||||
return -1;
|
||||
}
|
||||
if (strcmp(constants[i].name, name) == 0) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
void kinc_g4_pipeline_compile(kinc_g4_pipeline_t *state) {
|
||||
int highestIndex = 0;
|
||||
for (int i = 0;; ++i) {
|
||||
if (state->vertex_shader->impl.attributes[i].name[0] == 0) {
|
||||
break;
|
||||
}
|
||||
int index = state->vertex_shader->impl.attributes[i].index;
|
||||
if (index > highestIndex) {
|
||||
highestIndex = index;
|
||||
}
|
||||
}
|
||||
|
||||
int all = 0;
|
||||
for (int stream = 0; state->input_layout[stream] != nullptr; ++stream) {
|
||||
for (int index = 0; index < state->input_layout[stream]->size; ++index) {
|
||||
if (state->input_layout[stream]->elements[index].data == KINC_G4_VERTEX_DATA_F32_4X4) {
|
||||
all += 4;
|
||||
}
|
||||
else {
|
||||
all += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
D3DVERTEXELEMENT9 *elements = (D3DVERTEXELEMENT9 *)_alloca(sizeof(D3DVERTEXELEMENT9) * (all + 1));
|
||||
int i = 0;
|
||||
for (int stream = 0; state->input_layout[stream] != nullptr; ++stream) {
|
||||
int stride = 0;
|
||||
for (int index = 0; index < state->input_layout[stream]->size; ++index) {
|
||||
if (state->input_layout[stream]->elements[index].data != KINC_G4_VERTEX_DATA_F32_4X4) {
|
||||
elements[i].Stream = stream;
|
||||
elements[i].Offset = stride;
|
||||
}
|
||||
stride += kinc_g4_vertex_data_size(state->input_layout[stream]->elements[index].data);
|
||||
switch (state->input_layout[stream]->elements[index].data) {
|
||||
case KINC_G4_VERTEX_DATA_F32_1X:
|
||||
elements[i].Type = D3DDECLTYPE_FLOAT1;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_F32_2X:
|
||||
elements[i].Type = D3DDECLTYPE_FLOAT2;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_F32_3X:
|
||||
elements[i].Type = D3DDECLTYPE_FLOAT3;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_F32_4X:
|
||||
elements[i].Type = D3DDECLTYPE_FLOAT4;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_U8_4X:
|
||||
elements[i].Type = D3DDECLTYPE_UBYTE4;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_U8_4X_NORMALIZED:
|
||||
elements[i].Type = D3DDECLTYPE_UBYTE4N;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_I16_2X:
|
||||
elements[i].Type = D3DDECLTYPE_SHORT2;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_I16_2X_NORMALIZED:
|
||||
elements[i].Type = D3DDECLTYPE_SHORT2N;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_U16_2X_NORMALIZED:
|
||||
elements[i].Type = D3DDECLTYPE_USHORT2N;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_I16_4X:
|
||||
elements[i].Type = D3DDECLTYPE_SHORT4;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_I16_4X_NORMALIZED:
|
||||
elements[i].Type = D3DDECLTYPE_SHORT4N;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_U16_4X_NORMALIZED:
|
||||
elements[i].Type = D3DDECLTYPE_USHORT4N;
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_I8_1X:
|
||||
case KINC_G4_VERTEX_DATA_U8_1X:
|
||||
case KINC_G4_VERTEX_DATA_I8_1X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_U8_1X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_I8_2X:
|
||||
case KINC_G4_VERTEX_DATA_U8_2X:
|
||||
case KINC_G4_VERTEX_DATA_I8_2X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_U8_2X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_I8_4X:
|
||||
case KINC_G4_VERTEX_DATA_I8_4X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_I16_1X:
|
||||
case KINC_G4_VERTEX_DATA_U16_1X:
|
||||
case KINC_G4_VERTEX_DATA_I16_1X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_U16_1X_NORMALIZED:
|
||||
case KINC_G4_VERTEX_DATA_U16_2X:
|
||||
case KINC_G4_VERTEX_DATA_U16_4X:
|
||||
case KINC_G4_VERTEX_DATA_I32_1X:
|
||||
case KINC_G4_VERTEX_DATA_U32_1X:
|
||||
case KINC_G4_VERTEX_DATA_I32_2X:
|
||||
case KINC_G4_VERTEX_DATA_U32_2X:
|
||||
case KINC_G4_VERTEX_DATA_I32_3X:
|
||||
case KINC_G4_VERTEX_DATA_U32_3X:
|
||||
case KINC_G4_VERTEX_DATA_I32_4X:
|
||||
case KINC_G4_VERTEX_DATA_U32_4X:
|
||||
elements[i].Type = D3DDECLTYPE_UNUSED;
|
||||
assert(false);
|
||||
break;
|
||||
case KINC_G4_VERTEX_DATA_F32_4X4:
|
||||
for (int i2 = 0; i2 < 4; ++i2) {
|
||||
elements[i].Stream = stream;
|
||||
elements[i].Offset = stride;
|
||||
elements[i].Type = D3DDECLTYPE_FLOAT4;
|
||||
elements[i].Method = D3DDECLMETHOD_DEFAULT;
|
||||
elements[i].Usage = D3DDECLUSAGE_TEXCOORD;
|
||||
char name[101];
|
||||
strcpy(name, state->input_layout[stream]->elements[index].name);
|
||||
strcat(name, "_");
|
||||
size_t length = strlen(name);
|
||||
_itoa(i2, &name[length], 10);
|
||||
name[length + 1] = 0;
|
||||
int attribute_index = find_attribute(state->vertex_shader->impl.attributes, name);
|
||||
if (attribute_index < 0) {
|
||||
kinc_log(KINC_LOG_LEVEL_ERROR, "Could not find attribute %s.", name);
|
||||
elements[i].UsageIndex = ++highestIndex;
|
||||
}
|
||||
else {
|
||||
elements[i].UsageIndex = state->vertex_shader->impl.attributes[attribute_index].index;
|
||||
}
|
||||
++i;
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (state->input_layout[stream]->elements[index].data != KINC_G4_VERTEX_DATA_F32_4X4) {
|
||||
elements[i].Method = D3DDECLMETHOD_DEFAULT;
|
||||
elements[i].Usage = D3DDECLUSAGE_TEXCOORD;
|
||||
int attribute_index = find_attribute(state->vertex_shader->impl.attributes, state->input_layout[stream]->elements[index].name);
|
||||
if (attribute_index < 0) {
|
||||
kinc_log(KINC_LOG_LEVEL_ERROR, "Could not find attribute %s.", state->input_layout[stream]->elements[index].name);
|
||||
elements[i].UsageIndex = ++highestIndex;
|
||||
}
|
||||
else {
|
||||
elements[i].UsageIndex = state->vertex_shader->impl.attributes[attribute_index].index;
|
||||
}
|
||||
++i;
|
||||
}
|
||||
}
|
||||
}
|
||||
elements[all].Stream = 0xff;
|
||||
elements[all].Offset = 0;
|
||||
elements[all].Type = D3DDECLTYPE_UNUSED;
|
||||
elements[all].Method = 0;
|
||||
elements[all].Usage = 0;
|
||||
elements[all].UsageIndex = 0;
|
||||
|
||||
state->impl.vertexDecleration = nullptr;
|
||||
kinc_microsoft_affirm(device->CreateVertexDeclaration(elements, &state->impl.vertexDecleration));
|
||||
|
||||
int constant_index = find_constant(state->vertex_shader->impl.constants, "gl_HalfPixel");
|
||||
state->impl.halfPixelLocation = state->vertex_shader->impl.constants[constant_index].regindex;
|
||||
}
|
||||
|
||||
void kinc_g4_internal_set_pipeline(kinc_g4_pipeline_t *pipeline) {
|
||||
kinc_microsoft_affirm(device->SetVertexShader((IDirect3DVertexShader9 *)pipeline->vertex_shader->impl.shader));
|
||||
kinc_microsoft_affirm(device->SetPixelShader((IDirect3DPixelShader9 *)pipeline->fragment_shader->impl.shader));
|
||||
kinc_microsoft_affirm(device->SetVertexDeclaration(pipeline->impl.vertexDecleration));
|
||||
|
||||
// TODO (DK) System::screenWidth/Height are only main-window dimensions, what about other windows?
|
||||
float floats[4];
|
||||
floats[0] = 1.0f / kinc_width();
|
||||
floats[1] = 1.0f / kinc_height();
|
||||
floats[2] = floats[0];
|
||||
floats[3] = floats[1];
|
||||
kinc_microsoft_affirm(device->SetVertexShaderConstantF(pipeline->impl.halfPixelLocation, floats, 1));
|
||||
|
||||
DWORD flags = 0;
|
||||
if (pipeline->color_write_mask_red[0]) {
|
||||
flags |= D3DCOLORWRITEENABLE_RED;
|
||||
}
|
||||
if (pipeline->color_write_mask_green[0]) {
|
||||
flags |= D3DCOLORWRITEENABLE_GREEN;
|
||||
}
|
||||
if (pipeline->color_write_mask_blue[0]) {
|
||||
flags |= D3DCOLORWRITEENABLE_BLUE;
|
||||
}
|
||||
if (pipeline->color_write_mask_alpha[0]) {
|
||||
flags |= D3DCOLORWRITEENABLE_ALPHA;
|
||||
}
|
||||
|
||||
device->SetRenderState(D3DRS_COLORWRITEENABLE, flags);
|
||||
|
||||
device->SetRenderState(D3DRS_ALPHABLENDENABLE,
|
||||
(pipeline->blend_source != KINC_G4_BLEND_ONE || pipeline->blend_destination != KINC_G4_BLEND_ZERO) ? TRUE : FALSE);
|
||||
device->SetRenderState(D3DRS_SRCBLEND, convert_blend_factor(pipeline->blend_source));
|
||||
device->SetRenderState(D3DRS_DESTBLEND, convert_blend_factor(pipeline->blend_destination));
|
||||
device->SetRenderState(D3DRS_BLENDOP, convert_blend_operation(pipeline->blend_operation));
|
||||
|
||||
switch (pipeline->cull_mode) {
|
||||
case KINC_G4_CULL_CLOCKWISE:
|
||||
device->SetRenderState(D3DRS_CULLMODE, D3DCULL_CW);
|
||||
break;
|
||||
case KINC_G4_CULL_COUNTER_CLOCKWISE:
|
||||
device->SetRenderState(D3DRS_CULLMODE, D3DCULL_CCW);
|
||||
break;
|
||||
case KINC_G4_CULL_NOTHING:
|
||||
device->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE);
|
||||
break;
|
||||
}
|
||||
|
||||
device->SetRenderState(D3DRS_ZENABLE, pipeline->depth_mode != KINC_G4_COMPARE_ALWAYS ? TRUE : FALSE);
|
||||
device->SetRenderState(D3DRS_ZFUNC, convert(pipeline->depth_mode));
|
||||
device->SetRenderState(D3DRS_ZWRITEENABLE, pipeline->depth_write ? TRUE : FALSE);
|
||||
|
||||
/*
|
||||
case AlphaTestState:
|
||||
device->SetRenderState(D3DRS_ALPHATESTENABLE, on ? TRUE : FALSE);
|
||||
device->SetRenderState(D3DRS_ALPHAFUNC, D3DCMP_GREATEREQUAL);
|
||||
break;
|
||||
case AlphaReferenceState:
|
||||
device->SetRenderState(D3DRS_ALPHAREF, (DWORD)v);
|
||||
break;
|
||||
*/
|
||||
}
|
||||
|
||||
kinc_g4_constant_location_t kinc_g4_pipeline_get_constant_location(kinc_g4_pipeline_t *state, const char *name) {
|
||||
kinc_g4_constant_location_t location;
|
||||
|
||||
int fragment_index = find_constant(state->fragment_shader->impl.constants, name);
|
||||
int vertex_index = find_constant(state->vertex_shader->impl.constants, name);
|
||||
|
||||
if (fragment_index >= 0) {
|
||||
location.impl.reg = state->fragment_shader->impl.constants[fragment_index];
|
||||
location.impl.shaderType = 1;
|
||||
}
|
||||
else if (vertex_index >= 0) {
|
||||
location.impl.reg = state->vertex_shader->impl.constants[vertex_index];
|
||||
location.impl.shaderType = 0;
|
||||
}
|
||||
else {
|
||||
location.impl.shaderType = -1;
|
||||
kinc_log(KINC_LOG_LEVEL_WARNING, "Could not find uniform %s.", name);
|
||||
}
|
||||
return location;
|
||||
}
|
||||
|
||||
kinc_g4_texture_unit_t kinc_g4_pipeline_get_texture_unit(kinc_g4_pipeline_t *state, const char *name) {
|
||||
int fragment_index = find_constant(state->fragment_shader->impl.constants, name);
|
||||
int vertex_index = find_constant(state->vertex_shader->impl.constants, name);
|
||||
|
||||
kinc_g4_texture_unit_t unit;
|
||||
for (int i = 0; i < KINC_G4_SHADER_TYPE_COUNT; ++i) {
|
||||
unit.stages[i] = -1;
|
||||
}
|
||||
|
||||
if (fragment_index >= 0) {
|
||||
unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT] = state->fragment_shader->impl.constants[fragment_index].regindex;
|
||||
}
|
||||
|
||||
if (vertex_index >= 0) {
|
||||
unit.stages[KINC_G4_SHADER_TYPE_VERTEX] = state->vertex_shader->impl.constants[vertex_index].regindex;
|
||||
}
|
||||
|
||||
return unit;
|
||||
}
|
@ -0,0 +1,18 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct IDirect3DVertexDeclaration9;
|
||||
|
||||
typedef struct {
|
||||
struct IDirect3DVertexDeclaration9 *vertexDecleration;
|
||||
int halfPixelLocation;
|
||||
} kinc_g4_pipeline_impl_t;
|
||||
|
||||
void kinc_internal_set_constants(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,133 @@
|
||||
#include <kinc/graphics4/rendertarget.h>
|
||||
#include <kinc/log.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
void kinc_g4_render_target_init_with_multisampling(kinc_g4_render_target_t *renderTarget, int width, int height, kinc_g4_render_target_format_t format,
|
||||
int depthBufferBits, int stencilBufferBits, int samples_per_pixel) {
|
||||
renderTarget->width = width;
|
||||
renderTarget->height = height;
|
||||
renderTarget->texWidth = width;
|
||||
renderTarget->texHeight = height;
|
||||
renderTarget->isCubeMap = false;
|
||||
renderTarget->isDepthAttachment = false;
|
||||
|
||||
const bool antialiasing = samples_per_pixel > 1;
|
||||
renderTarget->impl.antialiasing = antialiasing;
|
||||
|
||||
D3DFORMAT d3dformat;
|
||||
switch (format) {
|
||||
case KINC_G4_RENDER_TARGET_FORMAT_64BIT_FLOAT:
|
||||
d3dformat = D3DFMT_A16B16G16R16F;
|
||||
break;
|
||||
case KINC_G4_RENDER_TARGET_FORMAT_32BIT_RED_FLOAT:
|
||||
d3dformat = D3DFMT_R32F;
|
||||
break;
|
||||
case KINC_G4_RENDER_TARGET_FORMAT_32BIT:
|
||||
default:
|
||||
d3dformat = D3DFMT_A8R8G8B8;
|
||||
}
|
||||
|
||||
#if defined(_DEBUG)
|
||||
kinc_log(KINC_LOG_LEVEL_INFO, "depthBufferBits not implemented yet, using defaults (D3DFMT_D24S8)");
|
||||
kinc_log(KINC_LOG_LEVEL_INFO, "stencilBufferBits not implemented yet, using defaults (D3DFMT_D24S8)");
|
||||
#endif
|
||||
|
||||
renderTarget->impl.colorSurface = nullptr;
|
||||
renderTarget->impl.depthSurface = nullptr;
|
||||
renderTarget->impl.colorTexture = nullptr;
|
||||
renderTarget->impl.depthTexture = nullptr;
|
||||
|
||||
if (antialiasing) {
|
||||
kinc_microsoft_affirm(
|
||||
device->CreateRenderTarget(width, height, d3dformat, D3DMULTISAMPLE_8_SAMPLES, 0, FALSE, &renderTarget->impl.colorSurface, nullptr));
|
||||
kinc_microsoft_affirm(
|
||||
device->CreateDepthStencilSurface(width, height, D3DFMT_D24S8, D3DMULTISAMPLE_8_SAMPLES, 0, TRUE, &renderTarget->impl.depthSurface, nullptr));
|
||||
kinc_microsoft_affirm(
|
||||
device->CreateTexture(width, height, 1, D3DUSAGE_RENDERTARGET, d3dformat, D3DPOOL_DEFAULT, &renderTarget->impl.colorTexture, nullptr));
|
||||
// Microsoft::affirm(device->CreateTexture(width, height, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &depthTexture, nullptr));
|
||||
renderTarget->impl.depthTexture = nullptr;
|
||||
}
|
||||
else {
|
||||
if (format == KINC_G4_RENDER_TARGET_FORMAT_16BIT_DEPTH) {
|
||||
kinc_microsoft_affirm(device->CreateTexture(width, height, 1, D3DUSAGE_RENDERTARGET, (D3DFORMAT)MAKEFOURCC('N', 'U', 'L', 'L'), D3DPOOL_DEFAULT,
|
||||
&renderTarget->impl.colorTexture, nullptr));
|
||||
kinc_microsoft_affirm(device->CreateTexture(width, height, 1, D3DUSAGE_DEPTHSTENCIL, (D3DFORMAT)MAKEFOURCC('I', 'N', 'T', 'Z'), D3DPOOL_DEFAULT,
|
||||
&renderTarget->impl.depthTexture, nullptr));
|
||||
renderTarget->isDepthAttachment = true;
|
||||
}
|
||||
else {
|
||||
kinc_microsoft_affirm(
|
||||
device->CreateTexture(width, height, 1, D3DUSAGE_RENDERTARGET, d3dformat, D3DPOOL_DEFAULT, &renderTarget->impl.colorTexture, nullptr));
|
||||
kinc_microsoft_affirm(
|
||||
device->CreateTexture(width, height, 1, D3DUSAGE_DEPTHSTENCIL, D3DFMT_D24S8, D3DPOOL_DEFAULT, &renderTarget->impl.depthTexture, nullptr));
|
||||
}
|
||||
kinc_microsoft_affirm(renderTarget->impl.colorTexture->GetSurfaceLevel(0, &renderTarget->impl.colorSurface));
|
||||
kinc_microsoft_affirm(renderTarget->impl.depthTexture->GetSurfaceLevel(0, &renderTarget->impl.depthSurface));
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_render_target_init_cube_with_multisampling(kinc_g4_render_target_t *renderTarget, int cubeMapSize, kinc_g4_render_target_format_t format,
|
||||
int depthBufferBits, int stencilBufferBits, int samples_per_pixel) {
|
||||
renderTarget->isCubeMap = true;
|
||||
renderTarget->isDepthAttachment = false;
|
||||
}
|
||||
|
||||
void kinc_g4_render_target_destroy(kinc_g4_render_target_t *renderTarget) {
|
||||
if (renderTarget->impl.colorSurface != nullptr) {
|
||||
renderTarget->impl.colorSurface->Release();
|
||||
}
|
||||
if (renderTarget->impl.depthSurface != nullptr) {
|
||||
renderTarget->impl.depthSurface->Release();
|
||||
}
|
||||
if (renderTarget->impl.colorTexture != nullptr) {
|
||||
renderTarget->impl.colorTexture->Release();
|
||||
}
|
||||
if (renderTarget->impl.depthTexture != nullptr) {
|
||||
renderTarget->impl.depthTexture->Release();
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef KINC_KONG
|
||||
void kinc_g4_render_target_use_color_as_texture(kinc_g4_render_target_t *renderTarget, uint32_t unit) {
|
||||
if (renderTarget->impl.antialiasing) {
|
||||
IDirect3DSurface9 *surface;
|
||||
renderTarget->impl.colorTexture->GetSurfaceLevel(0, &surface);
|
||||
kinc_microsoft_affirm(device->StretchRect(renderTarget->impl.colorSurface, nullptr, surface, nullptr, D3DTEXF_NONE));
|
||||
surface->Release();
|
||||
}
|
||||
device->SetTexture(unit, renderTarget->isDepthAttachment ? renderTarget->impl.depthTexture : renderTarget->impl.colorTexture);
|
||||
}
|
||||
#else
|
||||
void kinc_g4_render_target_use_color_as_texture(kinc_g4_render_target_t *renderTarget, kinc_g4_texture_unit_t unit) {
|
||||
if (renderTarget->impl.antialiasing) {
|
||||
IDirect3DSurface9 *surface;
|
||||
renderTarget->impl.colorTexture->GetSurfaceLevel(0, &surface);
|
||||
kinc_microsoft_affirm(device->StretchRect(renderTarget->impl.colorSurface, nullptr, surface, nullptr, D3DTEXF_NONE));
|
||||
surface->Release();
|
||||
}
|
||||
device->SetTexture(unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT],
|
||||
renderTarget->isDepthAttachment ? renderTarget->impl.depthTexture : renderTarget->impl.colorTexture);
|
||||
}
|
||||
#endif
|
||||
|
||||
void kinc_g4_render_target_set_depth_stencil_from(kinc_g4_render_target_t *renderTarget, kinc_g4_render_target_t *source) {
|
||||
renderTarget->impl.depthTexture = source->impl.depthTexture;
|
||||
renderTarget->impl.depthSurface = source->impl.depthSurface;
|
||||
}
|
||||
|
||||
void kinc_g4_render_target_use_depth_as_texture(kinc_g4_render_target_t *renderTarget, kinc_g4_texture_unit_t unit) {
|
||||
if (renderTarget->impl.antialiasing) {
|
||||
IDirect3DSurface9 *surface;
|
||||
renderTarget->impl.depthTexture->GetSurfaceLevel(0, &surface);
|
||||
kinc_microsoft_affirm(device->StretchRect(renderTarget->impl.depthSurface, nullptr, surface, nullptr, D3DTEXF_NONE));
|
||||
surface->Release();
|
||||
}
|
||||
device->SetTexture(unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], renderTarget->impl.depthTexture);
|
||||
}
|
||||
|
||||
void kinc_g4_render_target_get_pixels(kinc_g4_render_target_t *renderTarget, uint8_t *data) {}
|
||||
|
||||
void kinc_g4_render_target_generate_mipmaps(kinc_g4_render_target_t *renderTarget, int levels) {}
|
@ -0,0 +1,20 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct IDirect3DSurface9;
|
||||
struct IDirect3DTexture9;
|
||||
|
||||
typedef struct {
|
||||
struct IDirect3DSurface9 *colorSurface;
|
||||
struct IDirect3DSurface9 *depthSurface;
|
||||
struct IDirect3DTexture9 *colorTexture;
|
||||
struct IDirect3DTexture9 *depthTexture;
|
||||
bool antialiasing;
|
||||
} kinc_g4_render_target_impl_t;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,54 @@
|
||||
#include <kinc/graphics4/shader.h>
|
||||
#include <kinc/math/core.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
#include <cstdio>
|
||||
|
||||
void kinc_g4_shader_init(kinc_g4_shader_t *shader, const void *void_data, size_t length, kinc_g4_shader_type_t type) {
|
||||
unsigned index = 0;
|
||||
|
||||
uint8_t *data = (uint8_t *)void_data;
|
||||
int attributesCount = data[index++];
|
||||
for (int i = 0; i < attributesCount; ++i) {
|
||||
char name[256];
|
||||
for (unsigned i2 = 0; i2 < 255; ++i2) {
|
||||
name[i2] = data[index++];
|
||||
if (name[i2] == 0)
|
||||
break;
|
||||
}
|
||||
strcpy(shader->impl.attributes[i].name, name);
|
||||
shader->impl.attributes[i].index = data[index++];
|
||||
}
|
||||
shader->impl.attributes[attributesCount].name[0] = 0;
|
||||
|
||||
uint8_t constantCount = data[index++];
|
||||
for (unsigned i = 0; i < constantCount; ++i) {
|
||||
char name[256];
|
||||
for (unsigned i2 = 0; i2 < 255; ++i2) {
|
||||
name[i2] = data[index++];
|
||||
if (name[i2] == 0)
|
||||
break;
|
||||
}
|
||||
strcpy(shader->impl.constants[i].name, name);
|
||||
shader->impl.constants[i].regtype = data[index++];
|
||||
shader->impl.constants[i].regindex = data[index++];
|
||||
shader->impl.constants[i].regcount = data[index++];
|
||||
}
|
||||
shader->impl.constants[constantCount].name[0] = 0;
|
||||
|
||||
if (type == KINC_G4_SHADER_TYPE_VERTEX) {
|
||||
kinc_microsoft_affirm(device->CreateVertexShader((DWORD *)&data[index], (IDirect3DVertexShader9 **)&shader));
|
||||
}
|
||||
else {
|
||||
kinc_microsoft_affirm(device->CreatePixelShader((DWORD *)&data[index], (IDirect3DPixelShader9 **)&shader));
|
||||
}
|
||||
}
|
||||
|
||||
int kinc_g4_shader_init_from_source(kinc_g4_shader_t *shader, const char *source, kinc_g4_shader_type_t type) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
void kinc_g4_shader_destroy(kinc_g4_shader_t *shader) {}
|
@ -0,0 +1,41 @@
|
||||
#pragma once
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct ShaderRegister {
|
||||
char name[128];
|
||||
uint8_t regtype;
|
||||
uint8_t regindex;
|
||||
uint8_t regcount;
|
||||
};
|
||||
|
||||
struct ShaderAttribute {
|
||||
char name[128];
|
||||
int index;
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
struct ShaderRegister reg;
|
||||
int shaderType; // 0: Vertex, 1: Fragment
|
||||
} kinc_g4_constant_location_impl_t;
|
||||
|
||||
typedef struct {
|
||||
int unit;
|
||||
} kinc_g4_texture_unit_impl_t;
|
||||
|
||||
#define KINC_INTERNAL_MAX_CONSTANTS 64
|
||||
#define KINC_INTERNAL_MAX_ATTRIBUTES 64
|
||||
|
||||
typedef struct {
|
||||
struct ShaderRegister constants[KINC_INTERNAL_MAX_CONSTANTS];
|
||||
struct ShaderAttribute attributes[KINC_INTERNAL_MAX_ATTRIBUTES];
|
||||
void *shader;
|
||||
} kinc_g4_shader_impl_t;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,110 @@
|
||||
#include <kinc/graphics4/texture.h>
|
||||
#include <kinc/io/filereader.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
namespace {
|
||||
kinc_g4_texture_t *setTextures[16] = {nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr,
|
||||
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr};
|
||||
|
||||
D3DFORMAT convert(kinc_image_format_t format) {
|
||||
switch (format) {
|
||||
case KINC_IMAGE_FORMAT_RGBA32:
|
||||
default:
|
||||
return D3DFMT_A8R8G8B8;
|
||||
case KINC_IMAGE_FORMAT_GREY8:
|
||||
return D3DFMT_L8;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void kinc_g4_texture_init_from_image(kinc_g4_texture_t *texture, kinc_image_t *image) {
|
||||
texture->impl.stage = 0;
|
||||
texture->impl.mipmap = true;
|
||||
DWORD usage = 0;
|
||||
texture->tex_width = image->width;
|
||||
texture->tex_height = image->height;
|
||||
texture->tex_depth = 1;
|
||||
usage = D3DUSAGE_DYNAMIC;
|
||||
kinc_microsoft_affirm_message(
|
||||
device->CreateTexture(image->width, image->height, 1, usage, convert(image->format), D3DPOOL_DEFAULT, &texture->impl.texture, 0),
|
||||
"Texture creation failed.");
|
||||
D3DLOCKED_RECT rect;
|
||||
kinc_microsoft_affirm(texture->impl.texture->LockRect(0, &rect, 0, 0));
|
||||
texture->impl.pitch = rect.Pitch;
|
||||
uint8_t *from = (uint8_t *)image->data;
|
||||
uint8_t *to = (uint8_t *)rect.pBits;
|
||||
// memcpy(to, from, width * height * sizeOf(format));
|
||||
for (int y = 0; y < image->height; ++y) {
|
||||
for (int x = 0; x < image->width; ++x) {
|
||||
to[rect.Pitch * y + x * 4 + 0 /* blue*/] = (from[y * image->width * 4 + x * 4 + 2]); /// 255.0f;
|
||||
to[rect.Pitch * y + x * 4 + 1 /*green*/] = (from[y * image->width * 4 + x * 4 + 1]); /// 255.0f;
|
||||
to[rect.Pitch * y + x * 4 + 2 /* red*/] = (from[y * image->width * 4 + x * 4 + 0]); /// 255.0f;
|
||||
to[rect.Pitch * y + x * 4 + 3 /*alpha*/] = (from[y * image->width * 4 + x * 4 + 3]); /// 255.0f;
|
||||
}
|
||||
}
|
||||
kinc_microsoft_affirm(texture->impl.texture->UnlockRect(0));
|
||||
}
|
||||
|
||||
void kinc_g4_texture_init3d(kinc_g4_texture_t *texture, int width, int height, int depth, kinc_image_format_t format) {}
|
||||
|
||||
void kinc_g4_texture_init(kinc_g4_texture_t *texture, int width, int height, kinc_image_format_t format) {
|
||||
texture->impl.stage = 0;
|
||||
texture->impl.mipmap = true;
|
||||
DWORD usage = 0;
|
||||
texture->tex_width = width;
|
||||
texture->tex_height = height;
|
||||
texture->tex_depth = 1;
|
||||
usage = D3DUSAGE_DYNAMIC;
|
||||
kinc_microsoft_affirm_message(device->CreateTexture(width, height, 1, usage, convert(format), D3DPOOL_DEFAULT, &texture->impl.texture, 0),
|
||||
"Texture creation failed.");
|
||||
}
|
||||
|
||||
void kinc_g4_texture_destroy(kinc_g4_texture_t *texture) {
|
||||
kinc_internal_texture_unset(texture);
|
||||
texture->impl.texture->Release();
|
||||
}
|
||||
|
||||
#ifdef KINC_KONG
|
||||
void kinc_internal_texture_set(kinc_g4_texture_t *texture, uint32_t unit) {
|
||||
kinc_microsoft_affirm(device->SetTexture(unit, texture->impl.texture));
|
||||
texture->impl.stage = unit;
|
||||
setTextures[texture->impl.stage] = texture;
|
||||
}
|
||||
#else
|
||||
void kinc_internal_texture_set(kinc_g4_texture_t *texture, kinc_g4_texture_unit_t unit) {
|
||||
kinc_microsoft_affirm(device->SetTexture(unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT], texture->impl.texture));
|
||||
texture->impl.stage = unit.stages[KINC_G4_SHADER_TYPE_FRAGMENT];
|
||||
setTextures[texture->impl.stage] = texture;
|
||||
}
|
||||
#endif
|
||||
|
||||
void kinc_internal_texture_unset(struct kinc_g4_texture *texture) {
|
||||
if (setTextures[texture->impl.stage] == texture) {
|
||||
device->SetTexture(texture->impl.stage, nullptr);
|
||||
setTextures[texture->impl.stage] = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
unsigned char *kinc_g4_texture_lock(kinc_g4_texture_t *texture) {
|
||||
D3DLOCKED_RECT rect;
|
||||
kinc_microsoft_affirm(texture->impl.texture->LockRect(0, &rect, 0, 0));
|
||||
texture->impl.pitch = rect.Pitch;
|
||||
return (uint8_t *)rect.pBits;
|
||||
}
|
||||
|
||||
void kinc_g4_texture_unlock(kinc_g4_texture_t *texture) {
|
||||
kinc_microsoft_affirm(texture->impl.texture->UnlockRect(0));
|
||||
}
|
||||
|
||||
void kinc_g4_texture_clear(kinc_g4_texture_t *texture, int x, int y, int z, int width, int height, int depth, unsigned color) {}
|
||||
|
||||
int kinc_g4_texture_stride(kinc_g4_texture_t *texture) {
|
||||
return texture->impl.pitch;
|
||||
}
|
||||
|
||||
void kinc_g4_texture_generate_mipmaps(kinc_g4_texture_t *texture, int levels) {}
|
||||
|
||||
void kinc_g4_texture_set_mipmap(kinc_g4_texture_t *texture, kinc_image_t *mipmap, int level) {}
|
@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct IDirect3DTexture9;
|
||||
|
||||
typedef struct {
|
||||
struct IDirect3DTexture9 *texture;
|
||||
int stage;
|
||||
bool mipmap;
|
||||
uint8_t pixfmt;
|
||||
int pitch;
|
||||
} kinc_g4_texture_impl_t;
|
||||
|
||||
struct kinc_g4_texture;
|
||||
|
||||
void kinc_internal_texture_unmipmap(struct kinc_g4_texture *texture);
|
||||
void kinc_internal_texture_unset(struct kinc_g4_texture *texture);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,5 @@
|
||||
#include <kinc/graphics4/texturearray.h>
|
||||
|
||||
void kinc_g4_texture_array_init(kinc_g4_texture_array_t *array, kinc_image_t *textures, int count) {}
|
||||
|
||||
void kinc_g4_texture_array_destroy(kinc_g4_texture_array_t *array) {}
|
@ -0,0 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct {
|
||||
int nothing;
|
||||
} kinc_g4_texture_array_impl_t;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -0,0 +1,75 @@
|
||||
#include <kinc/graphics4/graphics.h>
|
||||
#include <kinc/graphics4/vertexbuffer.h>
|
||||
|
||||
#include <kinc/backend/SystemMicrosoft.h>
|
||||
|
||||
#include "Direct3D9.h"
|
||||
|
||||
struct kinc_g4_vertex_buffer *kinc_internal_current_vertex_buffer = NULL;
|
||||
|
||||
void kinc_g4_vertex_buffer_init(kinc_g4_vertex_buffer_t *buffer, int count, kinc_g4_vertex_structure_t *structure, kinc_g4_usage_t usage,
|
||||
int instance_data_step_rate) {
|
||||
buffer->impl.myCount = count;
|
||||
buffer->impl.instanceDataStepRate = instance_data_step_rate;
|
||||
DWORD usageFlags = D3DUSAGE_WRITEONLY;
|
||||
if (usage == KINC_G4_USAGE_DYNAMIC) {
|
||||
usageFlags = D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY;
|
||||
}
|
||||
|
||||
buffer->impl.myStride = 0;
|
||||
for (int i = 0; i < structure->size; ++i) {
|
||||
buffer->impl.myStride += kinc_g4_vertex_data_size(structure->elements[i].data);
|
||||
}
|
||||
|
||||
kinc_microsoft_affirm(device->CreateVertexBuffer(kinc_g4_vertex_buffer_stride(buffer) * count, usageFlags, 0, D3DPOOL_DEFAULT, &buffer->impl.vb, 0));
|
||||
}
|
||||
|
||||
void kinc_g4_vertex_buffer_destroy(kinc_g4_vertex_buffer_t *buffer) {
|
||||
buffer->impl.vb->Release();
|
||||
}
|
||||
|
||||
float *kinc_g4_vertex_buffer_lock_all(kinc_g4_vertex_buffer_t *buffer) {
|
||||
return kinc_g4_vertex_buffer_lock(buffer, 0, kinc_g4_vertex_buffer_count(buffer));
|
||||
}
|
||||
|
||||
float *kinc_g4_vertex_buffer_lock(kinc_g4_vertex_buffer_t *buffer, int start, int count) {
|
||||
float *vertices;
|
||||
kinc_internal_vertex_buffer_unset(buffer);
|
||||
kinc_microsoft_affirm(buffer->impl.vb->Lock(start, count * kinc_g4_vertex_buffer_stride(buffer), (void **)&vertices, D3DLOCK_DISCARD));
|
||||
return vertices;
|
||||
}
|
||||
|
||||
void kinc_g4_vertex_buffer_unlock_all(kinc_g4_vertex_buffer_t *buffer) {
|
||||
kinc_microsoft_affirm(buffer->impl.vb->Unlock());
|
||||
}
|
||||
|
||||
void kinc_g4_vertex_buffer_unlock(kinc_g4_vertex_buffer_t *buffer, int count) {
|
||||
kinc_microsoft_affirm(buffer->impl.vb->Unlock());
|
||||
}
|
||||
|
||||
int kinc_internal_g4_vertex_buffer_set(kinc_g4_vertex_buffer_t *buffer, int offset) {
|
||||
buffer->impl._offset = offset;
|
||||
if (buffer->impl.instanceDataStepRate == 0) {
|
||||
kinc_internal_current_vertex_buffer = buffer;
|
||||
}
|
||||
else {
|
||||
kinc_microsoft_affirm(device->SetStreamSourceFreq(offset, (D3DSTREAMSOURCE_INSTANCEDATA | buffer->impl.instanceDataStepRate)));
|
||||
}
|
||||
kinc_microsoft_affirm(device->SetStreamSource(offset, buffer->impl.vb, 0, kinc_g4_vertex_buffer_stride(buffer)));
|
||||
return 0;
|
||||
}
|
||||
|
||||
void kinc_internal_vertex_buffer_unset(struct kinc_g4_vertex_buffer *buffer) {
|
||||
if (kinc_internal_current_vertex_buffer == buffer) {
|
||||
kinc_microsoft_affirm(device->SetStreamSource(0, NULL, 0, 0));
|
||||
kinc_internal_current_vertex_buffer = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
int kinc_g4_vertex_buffer_count(kinc_g4_vertex_buffer_t *buffer) {
|
||||
return buffer->impl.myCount;
|
||||
}
|
||||
|
||||
int kinc_g4_vertex_buffer_stride(kinc_g4_vertex_buffer_t *buffer) {
|
||||
return buffer->impl.myStride;
|
||||
}
|
@ -0,0 +1,25 @@
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct IDirect3DVertexBuffer9;
|
||||
|
||||
typedef struct {
|
||||
struct IDirect3DVertexBuffer9 *vb;
|
||||
int myCount;
|
||||
int myStride;
|
||||
int instanceDataStepRate;
|
||||
int _offset;
|
||||
} kinc_g4_vertex_buffer_impl_t;
|
||||
|
||||
struct kinc_g4_vertex_buffer;
|
||||
|
||||
void kinc_internal_vertex_buffer_unset(struct kinc_g4_vertex_buffer *buffer);
|
||||
|
||||
extern struct kinc_g4_vertex_buffer *kinc_internal_current_vertex_buffer;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
Reference in New Issue
Block a user