diff --git a/docs/progress.svg b/docs/progress.svg
index 5a6d3486..1fa1606f 100644
--- a/docs/progress.svg
+++ b/docs/progress.svg
@@ -69,10 +69,10 @@
Tomb2.exe progress according to the physical function order:
-26.52% (323) · 71.02% (865) · 0.66% (8) · 1.81% (22)
+26.60% (324) · 70.94% (864) · 0.66% (8) · 1.81% (22)
-
-
+
+
@@ -140,7 +140,7 @@
void __cdecl Output_DrawPoly_Gouraud(int32_t vtx_count, int32_t red, int32_t green, int32_t blue);
const int16_t *__cdecl Output_InsertObjectG3_ZBuffered(const int16_t *obj_ptr, int32_t num, enum SORT_TYPE sort_type);
void __cdecl Output_InsertFlatRect_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
-void __cdecl Output_InsertLine_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
+void __cdecl Output_InsertLine_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
void __cdecl Output_InsertGT3_Sorted(const struct PHD_VBUF *vtx0, const struct PHD_VBUF *vtx1, const struct PHD_VBUF *vtx2, const struct PHD_TEXTURE *texture, const struct PHD_UV *uv0, const struct PHD_UV *uv1, const struct PHD_UV *uv2, enum SORT_TYPE sort_type);
void __cdecl Output_InsertClippedPoly_Textured(int32_t vtx_count, float z, int16_t poly_type, int16_t tex_page);
void __cdecl Output_InsertGT4_Sorted(const struct PHD_VBUF *vtx0, const struct PHD_VBUF *vtx1, const struct PHD_VBUF *vtx2, const struct PHD_VBUF *vtx3, const struct PHD_TEXTURE *texture, enum SORT_TYPE sort_type);
@@ -1299,10 +1299,10 @@
Tomb2.exe progress according to the function sizes:
-23.28% · 76.39% · 0.02% · 0.31%
+23.37% · 76.30% · 0.02% · 0.31%
-
-
+
+
@@ -1615,7 +1615,7 @@
void __cdecl Lara_DeflectEdgeJump(struct ITEM_INFO *item, struct COLL_INFO *coll);
BOOL __cdecl LoadSprites(HANDLE handle);
void __cdecl Output_InsertSkybox(const int16_t *obj_ptr);
-void __cdecl Output_InsertLine_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
+void __cdecl Output_InsertLine_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
void __cdecl DrawAmmoInfo(void);
void __cdecl DoInventoryBackground(void);
int32_t __cdecl Creature_Vault(int16_t item_num, int16_t angle, int32_t vault, int32_t shift);
diff --git a/docs/progress.txt b/docs/progress.txt
index fe9712c7..38bb087b 100644
--- a/docs/progress.txt
+++ b/docs/progress.txt
@@ -1321,7 +1321,7 @@ typedef enum LARA_MESH {
004097F0 000000F7 - void __cdecl Output_DrawPoly_Gouraud(int32_t vtx_count, int32_t red, int32_t green, int32_t blue);
004098F0 000002D3 + const int16_t *__cdecl Output_InsertObjectG3_ZBuffered(const int16_t *obj_ptr, int32_t num, enum SORT_TYPE sort_type);
00409BD0 000001C9 + void __cdecl Output_InsertFlatRect_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
-00409DA0 00000133 - void __cdecl Output_InsertLine_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
+00409DA0 00000133 + void __cdecl Output_InsertLine_ZBuffered(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx);
00409EE0 00000706 - void __cdecl Output_InsertGT3_Sorted(const struct PHD_VBUF *vtx0, const struct PHD_VBUF *vtx1, const struct PHD_VBUF *vtx2, const struct PHD_TEXTURE *texture, const struct PHD_UV *uv0, const struct PHD_UV *uv1, const struct PHD_UV *uv2, enum SORT_TYPE sort_type);
0040A5F0 000001AC - void __cdecl Output_InsertClippedPoly_Textured(int32_t vtx_count, float z, int16_t poly_type, int16_t tex_page);
0040A7A0 000004D7 - void __cdecl Output_InsertGT4_Sorted(const struct PHD_VBUF *vtx0, const struct PHD_VBUF *vtx1, const struct PHD_VBUF *vtx2, const struct PHD_VBUF *vtx3, const struct PHD_TEXTURE *texture, enum SORT_TYPE sort_type);
diff --git a/src/game/output.c b/src/game/output.c
index 12b338fa..8c1dbbcb 100644
--- a/src/game/output.c
+++ b/src/game/output.c
@@ -3227,3 +3227,37 @@ void __cdecl Output_InsertFlatRect_ZBuffered(
g_D3DDev, D3DPT_TRIANGLESTRIP, D3DVT_TLVERTEX, g_VBufferD3D, 4,
D3DDP_DONOTCLIP | D3DDP_DONOTUPDATEEXTENTS);
}
+
+void __cdecl Output_InsertLine_ZBuffered(
+ const int32_t x1, const int32_t y1, const int32_t x2, const int32_t y2,
+ int32_t z, const uint8_t color_idx)
+{
+ if (z >= g_PhdFarZ) {
+ return;
+ }
+ CLAMPL(z, g_PhdNearZ);
+
+ const double rhw = g_RhwFactor / (double)z;
+ const double sz = g_FltResZBuf - rhw * g_FltResZORhw;
+
+ const RGB888 *const color = &g_GamePalette8[color_idx];
+ const D3DCOLOR d3d_color =
+ Output_ShadeColor(color->red, color->green, color->blue, 0xFF);
+
+ g_VBufferD3D[0].sx = (float)(g_PhdWinMinX + x1);
+ g_VBufferD3D[0].sy = (float)(g_PhdWinMinY + y1);
+ g_VBufferD3D[1].sx = (float)(g_PhdWinMinX + x2);
+ g_VBufferD3D[1].sy = (float)(g_PhdWinMinY + y2);
+
+ for (int i = 0; i < 2; i++) {
+ g_VBufferD3D[i].sz = sz;
+ g_VBufferD3D[i].rhw = rhw;
+ g_VBufferD3D[i].color = d3d_color;
+ }
+
+ HWR_TexSource(0);
+ HWR_EnableColorKey(0);
+ g_D3DDev->lpVtbl->DrawPrimitive(
+ g_D3DDev, D3DPT_LINESTRIP, D3DVT_TLVERTEX, g_VBufferD3D, 2,
+ D3DDP_DONOTCLIP | D3DDP_DONOTUPDATEEXTENTS);
+}
diff --git a/src/game/output.h b/src/game/output.h
index 247b6455..bbdfd40b 100644
--- a/src/game/output.h
+++ b/src/game/output.h
@@ -95,3 +95,7 @@ void __cdecl Output_InsertGT4_ZBuffered(
void __cdecl Output_InsertFlatRect_ZBuffered(
int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z,
uint8_t color_idx);
+
+void __cdecl Output_InsertLine_ZBuffered(
+ int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z,
+ uint8_t color_idx);
diff --git a/src/global/funcs.h b/src/global/funcs.h
index 59bf416d..1f1aac65 100644
--- a/src/global/funcs.h
+++ b/src/global/funcs.h
@@ -8,7 +8,6 @@
#define Output_InsertInventoryBackground ((void __cdecl (*)(const int16_t *obj_ptr))0x00401D50)
#define Output_DrawClippedPoly_Textured ((void __cdecl (*)(int32_t vtx_count))0x00408D70)
#define Output_DrawPoly_Gouraud ((void __cdecl (*)(int32_t vtx_count, int32_t red, int32_t green, int32_t blue))0x004097F0)
-#define Output_InsertLine_ZBuffered ((void __cdecl (*)(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t z, uint8_t color_idx))0x00409DA0)
#define Output_InsertGT3_Sorted ((void __cdecl (*)(const struct PHD_VBUF *vtx0, const struct PHD_VBUF *vtx1, const struct PHD_VBUF *vtx2, const struct PHD_TEXTURE *texture, const struct PHD_UV *uv0, const struct PHD_UV *uv1, const struct PHD_UV *uv2, enum SORT_TYPE sort_type))0x00409EE0)
#define Output_InsertClippedPoly_Textured ((void __cdecl (*)(int32_t vtx_count, float z, int16_t poly_type, int16_t tex_page))0x0040A5F0)
#define Output_InsertGT4_Sorted ((void __cdecl (*)(const struct PHD_VBUF *vtx0, const struct PHD_VBUF *vtx1, const struct PHD_VBUF *vtx2, const struct PHD_VBUF *vtx3, const struct PHD_TEXTURE *texture, enum SORT_TYPE sort_type))0x0040A7A0)
diff --git a/src/global/vars.h b/src/global/vars.h
index bef94350..95ca1407 100644
--- a/src/global/vars.h
+++ b/src/global/vars.h
@@ -94,7 +94,7 @@
#define g_IsWaterEffect (*(int32_t*)0x004D6C14)
#define g_VBuffer (*(struct VERTEX_INFO(*)[20])0x004D6CD8)
#define g_IsShadeEffect (*(int8_t*)0x004D6F78)
-#define g_VBufferD3D (*(D3DTLVERTEX(*)[132])0x004D6F80)
+#define g_VBufferD3D (*(D3DTLVERTEX(*)[32])0x004D6F80)
#define g_GamePalette16 (*(PALETTEENTRY(*)[256])0x004D7380)
#define g_CineFrameCurrent (*(int32_t*)0x004D7780)
#define g_IsChunkyCamera (*(int32_t*)0x004D778C)
diff --git a/src/inject_exec.c b/src/inject_exec.c
index 9d1466de..d9752745 100644
--- a/src/inject_exec.c
+++ b/src/inject_exec.c
@@ -176,6 +176,7 @@ static void Inject_Output(void)
INJECT(1, 0x00409450, Output_InsertObjectG4_ZBuffered);
INJECT(1, 0x004098F0, Output_InsertObjectG3_ZBuffered);
INJECT(1, 0x00409BD0, Output_InsertFlatRect_ZBuffered);
+ INJECT(1, 0x00409DA0, Output_InsertLine_ZBuffered);
INJECT(1, 0x0041BA50, Output_InsertPolygons_I);
}