diff Indoor.cpp @ 1295:86a83e12d795

moving files
author Ritor1
date Mon, 17 Jun 2013 17:34:01 +0600
parents 6bbd50bda571
children 5450af4f57ef
line wrap: on
line diff
--- a/Indoor.cpp	Mon Jun 17 09:09:30 2013 +0600
+++ b/Indoor.cpp	Mon Jun 17 17:34:01 2013 +0600
@@ -37,8 +37,11 @@
 
 #include "mm7_data.h"
 #include "MM7.h"
-
-
+#include "Sprites.h"
+#include "Game.h"
+#include "stru6.h"
+#include "ParticleEngine.h"
+#include "Outdoor_stuff.h"
 
 
 
@@ -1335,7 +1338,7 @@
         nodes[num_nodes].uViewportZ = pBLVRenderParams->uViewportZ;
         nodes[num_nodes].uViewportY = pBLVRenderParams->uViewportY;
         nodes[num_nodes].uViewportW = pBLVRenderParams->uViewportW;
-        nodes[num_nodes].field_C._43F9E1(pBLVRenderParams->uViewportX, pBLVRenderParams->uViewportY,
+        nodes[num_nodes].field_C.GetViewportData(pBLVRenderParams->uViewportX, pBLVRenderParams->uViewportY,
                                          pBLVRenderParams->uViewportZ, pBLVRenderParams->uViewportW);
         AddBspNodeToRenderList(++num_nodes - 1);
         return;
@@ -1491,7 +1494,7 @@
         v3->nodes[v3->num_nodes].uViewportZ = LOWORD(pBLVRenderParams->uViewportZ);
         v3->nodes[v3->num_nodes].uViewportY = LOWORD(pBLVRenderParams->uViewportY);
         v3->nodes[v3->num_nodes].uViewportW = LOWORD(pBLVRenderParams->uViewportW);
-        v3->nodes[v3->num_nodes++].field_C._43F9E1(
+        v3->nodes[v3->num_nodes++].field_C.GetViewportData(
           SLOWORD(pBLVRenderParams->uViewportX),
           pBLVRenderParams->uViewportY,
           SLOWORD(pBLVRenderParams->uViewportZ),
@@ -4638,4 +4641,1249 @@
       }
     }
   }
+}
+//----- (0046CEC3) --------------------------------------------------------
+int BLV_GetFloorLevel(int x, int y, int z, unsigned int uSectorID, unsigned int *pFaceID)
+{
+  int v13; // ecx@13
+  signed int v14; // ebx@14
+  int v15; // eax@16
+  //int v16; // edx@19
+  //int v17; // ST18_4@19
+  //signed int v18; // edx@19
+  //signed __int64 v19; // qtt@19
+  int v21; // eax@27
+  //int v22; // ecx@29
+  signed int v28; // eax@45
+  int v29; // ebx@47
+  int v30; // edx@49
+  //int v31; // ST10_4@49
+  //signed int v32; // edx@49
+  signed __int64 v33; // qtt@49
+  //signed int v34; // eax@54
+  //signed int v35; // esi@56
+  //int result; // eax@57
+  int v38; // edx@62
+  //int v44; // [sp+20h] [bp-20h]@10
+  bool v47; // [sp+24h] [bp-1Ch]@43
+  bool v48; // [sp+28h] [bp-18h]@10
+  bool v49; // [sp+28h] [bp-18h]@41
+  bool v50; // [sp+2Ch] [bp-14h]@12
+  signed int v53; // [sp+30h] [bp-10h]@10
+  signed int v54; // [sp+30h] [bp-10h]@41
+  signed int v55; // [sp+34h] [bp-Ch]@1
+
+  //LOG_DECOMPILATION_WARNING();
+
+  static int blv_floor_id[50]; // 00721200
+  static int blv_floor_level[50]; // 007212C8
+
+  static __int16 word_721390_ys[104]; // idb
+  static __int16 word_721460_xs[104]; // idb
+
+  auto pSector = &pIndoor->pSectors[uSectorID];
+  v55 = 0;
+  for (uint i = 0; i < pSector->uNumFloors; ++i)
+  {
+    auto pFloor = &pIndoor->pFaces[pSector->pFloors[i]];
+    if (pFloor->Clickable())
+      continue;
+
+    assert(pFloor->uNumVertices);
+    if (x <= pFloor->pBounding.x2 && x >= pFloor->pBounding.x1 &&
+        y <= pFloor->pBounding.y2 && y >= pFloor->pBounding.y1)
+    {
+      for (uint j = 0; j < pFloor->uNumVertices; ++j)
+      {
+        word_721460_xs[2 * j] =     pFloor->pXInterceptDisplacements[j] + pIndoor->pVertices[pFloor->pVertexIDs[j]].x;
+        word_721460_xs[2 * j + 1] = pFloor->pXInterceptDisplacements[j] + pIndoor->pVertices[pFloor->pVertexIDs[j + 1]].x;
+        word_721390_ys[2 * j] =     pFloor->pYInterceptDisplacements[j] + pIndoor->pVertices[pFloor->pVertexIDs[j]].y;
+        word_721390_ys[2 * j + 1] = pFloor->pYInterceptDisplacements[j] + pIndoor->pVertices[pFloor->pVertexIDs[j + 1]].y;
+      }
+      word_721460_xs[2 * pFloor->uNumVertices] = word_721460_xs[0];
+      word_721390_ys[2 * pFloor->uNumVertices] = word_721390_ys[0];
+
+      v50 = word_721390_ys[0] >= y;
+      v53 = 0;
+
+      for (uint j = 0; j < 2 * pFloor->uNumVertices; ++j)
+      {
+        if (v53 >= 2)
+          break;
+
+        v48 = v50;
+        v50 = word_721390_ys[j + 1] >= y;
+
+          v13 = i;
+          if (v48 == v50)
+            continue;
+
+            v14 = word_721460_xs[j + 1] >= x ? 0 : 2;
+            v15 = v14 | (word_721460_xs[j] < x);
+
+          if (v15 == 3)
+            continue;
+          else if (!v15)
+            ++v53;
+          else
+          {
+            auto a_div_b = fixpoint_div(y - word_721390_ys[j], word_721390_ys[j + 1] - word_721390_ys[j]);
+            auto res = fixpoint_sub0((signed int)word_721460_xs[j + 1] - (signed int)word_721460_xs[j], a_div_b);
+
+            if (res + word_721460_xs[j] >= x)
+                ++v53;
+          }
+      }
+
+
+        if ( v53 == 1 )
+        {
+          if ( v55 >= 50 )
+            break;
+          if ( pFloor->uPolygonType == POLYGON_Floor || pFloor->uPolygonType == POLYGON_Ceiling )
+          {
+            v21 = pIndoor->pVertices[pFloor->pVertexIDs[0]].z;
+          }
+          else
+          {
+            v21 = fixpoint_sub0(pFloor->zCalc1, x) + fixpoint_sub0(pFloor->zCalc2, y) + (short)(pFloor->zCalc3 >> 16);
+          }
+          blv_floor_level[v55] = v21;
+          blv_floor_id[v55] = pSector->pFloors[i];
+          v55++;
+        }
+    }
+  }
+
+
+  if ( pSector->field_0 & 8 )
+  {
+    for (uint i = 0; i < pSector->uNumPortals; ++i)
+    {
+      auto portal = &pIndoor->pFaces[pSector->pPortals[i]];
+      if (portal->uPolygonType != POLYGON_Floor)
+        continue;
+
+      if (!portal->uNumVertices)
+        continue;
+
+      if (x <= portal->pBounding.x2 && x >= portal->pBounding.x1 &&
+          y <= portal->pBounding.y2 && y >= portal->pBounding.y1 )
+      {
+        for (uint j = 0; j < portal->uNumVertices; ++j)
+        {
+          word_721460_xs[2 * j] =     portal->pXInterceptDisplacements[j] + pIndoor->pVertices[portal->pVertexIDs[j]].x;
+          word_721460_xs[2 * j + 1] = portal->pXInterceptDisplacements[j + 1] + pIndoor->pVertices[portal->pVertexIDs[j + 1]].x;
+          word_721390_ys[2 * j] =     portal->pYInterceptDisplacements[j] + pIndoor->pVertices[portal->pVertexIDs[j]].y;
+          word_721390_ys[2 * j + 1] = portal->pYInterceptDisplacements[j + 1] + pIndoor->pVertices[portal->pVertexIDs[j + 1]].y;
+        }
+        word_721460_xs[2 * portal->uNumVertices] = word_721460_xs[0];
+        word_721390_ys[2 * portal->uNumVertices] = word_721390_ys[0];
+        v54 = 0;
+        v47 = word_721390_ys[0] >= y;
+
+          for (uint j = 0; j < 2 * portal->uNumVertices; ++j)
+          {
+            v49 = v47;
+            if ( v54 >= 2 )
+              break;
+            v47 = word_721390_ys[j + 1] >= y;
+            if ( v49 != v47 )
+            {
+              v28 = word_721460_xs[j + 1] >= x ? 0 : 2;
+              v29 = v28 | (word_721460_xs[j] < x);
+              if ( v29 != 3 )
+              {
+                if ( !v29 )
+                  ++v54;
+                else
+                {
+                  auto a_div_b = fixpoint_div(y - word_721390_ys[j], word_721390_ys[j + 1] - word_721390_ys[j]);
+                  auto res = fixpoint_sub0(word_721460_xs[j + 1] - word_721460_xs[j], a_div_b);
+                  if (res + word_721460_xs[j] >= x)
+                    ++v54;
+                }
+              }
+            }
+          }
+          if ( v54 == 1 )
+          {
+            if ( v55 >= 50 )
+              break;
+            blv_floor_level[v55] = -29000;
+            blv_floor_id[v55] = pSector->pPortals[i];
+            v55++;
+          }
+      }
+    }
+  }
+  if ( v55 == 1 )
+  {
+    *pFaceID = blv_floor_id[0];
+    return blv_floor_level[0];
+  }
+  if ( !v55 )
+    return -30000;
+  *pFaceID = blv_floor_id[0];
+  //result = blv_floor_level[0];
+
+    /*for ( v35 = 1; v35 < v55; ++v35 )
+    {
+      if ( blv_floor_level[0] <= z + 5 )
+      {
+        if ( blv_floor_level[v35] >= blv_floor_level[0] || blv_floor_level[v35] > z + 5 )
+          continue;
+        blv_floor_level[0] = blv_floor_level[v35];
+        *pFaceID = blv_floor_id[v35];
+        continue;
+      }
+      if ( blv_floor_level[v35] < blv_floor_level[0] )
+      {
+        blv_floor_level[0] = blv_floor_level[v35];
+        *pFaceID = blv_floor_id[v35];
+      }
+    }*/
+
+    
+  int result = blv_floor_level[0];
+  for (uint i = 1; i < v55; ++i)
+  {
+      v38 = blv_floor_level[i];
+      if ( result <= z + 5 )
+      {
+        if ( v38 > result && v38 <= z + 5 )
+        {
+          result = blv_floor_level[i];
+          *pFaceID = blv_floor_id[i];
+        }
+      }
+      else if ( v38 < result )
+      {
+        result = blv_floor_level[i];
+        *pFaceID = blv_floor_id[i];
+      }
+  }
+
+  return result;
+}
+//----- (004016FA) --------------------------------------------------------
+int __cdecl MakeActorAIList_BLV()
+{
+  Actor *v0; // esi@2
+  int v1; // eax@4
+  int v2; // ebx@4
+  unsigned int v3; // ecx@4
+  int v4; // edx@5
+  int v5; // edx@7
+  unsigned int v6; // edx@9
+  unsigned int v7; // ST24_4@10
+  int v8; // eax@10
+  int v9; // edi@10
+  int v10; // ebx@14
+  char v11; // zf@16
+  int v12; // eax@22
+  int v13; // edx@24
+  int v14; // ecx@25
+  int v15; // ebx@26
+  unsigned int *v16; // ecx@27
+  unsigned int v17; // esi@27
+  int v18; // ecx@31
+  signed int v19; // edi@31
+  Actor *v20; // esi@32
+  bool v21; // eax@33
+  int v22; // eax@34
+  signed int v23; // ebx@36
+  Actor *v24; // esi@37
+  signed int v25; // eax@40
+  int v26; // eax@43
+  int v27; // ebx@45
+  int j; // edi@45
+  unsigned int v29; // eax@46
+  int v30; // eax@48
+  int v31; // ecx@51
+  int v32; // eax@51
+  signed int v33; // eax@53
+  __int64 v34; // qax@55
+  char *v35; // ecx@56
+  int v37; // [sp+Ch] [bp-18h]@1
+  int v38; // [sp+10h] [bp-14h]@4
+  int v39; // [sp+14h] [bp-10h]@4
+  int v40; // [sp+18h] [bp-Ch]@10
+  int v41; // [sp+18h] [bp-Ch]@29
+  int i; // [sp+18h] [bp-Ch]@31
+  signed int v43; // [sp+1Ch] [bp-8h]@1
+  signed int v44; // [sp+1Ch] [bp-8h]@25
+  int v45; // [sp+20h] [bp-4h]@1
+
+//  __debugbreak(); // refactor for blv ai
+  pParty->uFlags &= 0xFFFFFFCFu;
+  v37 = pIndoor->GetSector(pParty->vPosition.x, pParty->vPosition.y, pParty->vPosition.z);
+  v45 = 0;
+  v43 = 0;
+  if ( (signed int)uNumActors > 0 )
+  {
+    v0 = pActors.data();//[0].uAttributes;
+    do
+    {
+      BYTE1(v0->uAttributes) &= 0xFBu;
+      if ( ! v0->CanAct() )
+        goto LABEL_60;
+	  v39 = abs(pParty->vPosition.z - v0->vPosition.z);
+	  v38 = abs(pParty->vPosition.y - v0->vPosition.y);
+	  v1 = abs(pParty->vPosition.x - v0->vPosition.x);
+      v2 = v38;
+      v3 = v39;
+      if ( v1 < v38 )
+      {
+        v4 = v1;
+        v1 = v38;
+        v2 = v4;
+      }
+      if ( v1 < v39 )
+      {
+        v5 = v1;
+        v1 = v39;
+        v3 = v5;
+      }
+      if ( v2 < (signed int)v3 )
+      {
+        v6 = v3;
+        v3 = v2;
+        v2 = v6;
+      }
+      v7 = ((unsigned int)(11 * v2) >> 5) + (v3 >> 2) + v1;
+      v8 = v0->uActorRadius;
+      v9 = v7 - v8;
+      v40 = v7 - v8;
+      if ( v40 < 0 )
+      {
+        v9 = 0;
+        v40 = 0;
+      }
+      if ( v9 < 10240 )
+      {
+        v10 = v0->uAttributes & 0xFEFFFFFF;
+        v0->uAttributes = v10;
+        if ( v10 & 0x80000 || v0->GetActorsRelation(0) )
+        {
+          v11 = (pParty->uFlags & 0x10) == 0;
+          v0->uAttributes = v10 | 0x1000000;
+          if ( v11 && (double)v40 < 307.2 )
+            pParty->uFlags |= 0x10u;
+          if ( !(pParty->uFlags & 0x20) && v9 < 5120 )
+            pParty->uFlags |= 0x20u;
+        }
+        v12 = v45++;
+        ai_near_actors_distances[v12] = v9;
+        ai_near_actors_ids[v12] = v43;
+      }
+      else
+      {
+LABEL_60:
+        BYTE1(v0->uAttributes) &= 0xBFu;
+      }
+      ++v43;
+      ++v0;
+    }
+    while ( v43 < (signed int)uNumActors );
+  }
+  v13 = 0;
+  if ( v45 > 0 )
+  {
+    v14 = 1;
+    v44 = 1;
+    do
+    {
+      while ( 1 )
+      {
+        v41 = v14;
+        if ( v14 >= v45 )
+          break;
+        v15 = ai_near_actors_distances[v13];
+        if ( v15 > ai_near_actors_distances[v14] )
+        {
+          v16 = &ai_near_actors_ids[v14];
+          v17 = ai_near_actors_ids[v13];
+          ai_near_actors_ids[v13] = *v16;
+          *v16 = v17;
+          v14 = v41;
+          ai_near_actors_distances[v13] = ai_near_actors_distances[v41];
+          ai_near_actors_distances[v41] = v15;
+        }
+        ++v14;
+      }
+      ++v13;
+      v14 = v44 + 1;
+      v44 = v14;
+    }
+    while ( v14 - 1 < v45 );
+  }
+  v18 = 0;
+  v19 = 0;
+  for ( i = 0; v18 < v45; i = v18 )
+  {
+    v20 = &pActors[ai_near_actors_ids[v18]];
+    if ( v20->uAttributes & 0x8000
+      || (v21 = sub_4070EF_prolly_collide_objects(PID(OBJECT_Actor,ai_near_actors_ids[v18]), 4u), v18 = i, v21) )
+    {
+      v22 = ai_near_actors_ids[v18];
+      v20->uAttributes |= 0x8000u;
+      ai_array_4F6638_actor_ids[v19] = v22;
+      ai_array_4F5E68[v19++] = ai_near_actors_distances[v18];
+      if ( v19 >= 30 )
+        break;
+    }
+    ++v18;
+  }
+  v23 = 0;
+  ai_arrays_size = v19;
+  if ( (signed int)uNumActors > 0 )
+  {
+    v24 = pActors.data();//[0].uAttributes;
+    do
+    {
+      if ( v24->CanAct() && v24->uSectorID == v37 )
+      {
+        v25 = 0;
+        if ( v19 <= 0 )
+        {
+LABEL_43:
+          v26 = ai_arrays_size;
+          BYTE1(v24->uAttributes) |= 0x40u;
+          ++ai_arrays_size;
+          ai_array_4F6638_actor_ids[v26] = v23;
+        }
+        else
+        {
+          while ( ai_array_4F6638_actor_ids[v25] != v23 )
+          {
+            ++v25;
+            if ( v25 >= v19 )
+              goto LABEL_43;
+          }
+        }
+      }
+      ++v23;
+      ++v24;
+    }
+    while ( v23 < (signed int)uNumActors );
+  }
+  v27 = ai_arrays_size;
+  for ( j = 0; j < v45; ++j )
+  {
+    v29 = ai_near_actors_ids[j];
+    if ( pActors[v29].uAttributes & 0xC000 && pActors[v29].CanAct() )
+    {
+      v30 = 0;
+      if ( v27 <= 0 )
+      {
+LABEL_51:
+        v31 = ai_arrays_size;
+        v32 = ai_near_actors_ids[j];
+        ++ai_arrays_size;
+        ai_array_4F6638_actor_ids[v31] = v32;
+      }
+      else
+      {
+        while ( ai_array_4F6638_actor_ids[v30] != ai_near_actors_ids[j] )
+        {
+          ++v30;
+          if ( v30 >= v27 )
+            goto LABEL_51;
+        }
+      }
+    }
+  }
+  v33 = ai_arrays_size;
+  if ( ai_arrays_size > 30 )
+  {
+    v33 = 30;
+    ai_arrays_size = 30;
+  }
+  memcpy(ai_near_actors_ids.data(), ai_array_4F6638_actor_ids.data(), 4 * v33);
+  memcpy(ai_near_actors_distances.data(), ai_array_4F5E68.data(), 4 * ai_arrays_size);
+  v34 = (unsigned int)ai_arrays_size;
+  if ( ai_arrays_size > 0 )
+  {
+    do
+    {
+      v35 = (char *)&pActors[ai_near_actors_ids[HIDWORD(v34)]].uAttributes;
+      v35[1] |= 4u;
+      ++HIDWORD(v34);
+    }
+    while ( SHIDWORD(v34) < (signed int)v34 );
+  }
+  return v34;
+}
+//----- (0043FDED) --------------------------------------------------------
+void PrepareActorRenderList_BLV()
+{
+  RenderBillboard *v0; // esi@0
+  unsigned __int16 v3; // ax@3
+  unsigned int v4; // eax@5
+  unsigned __int16 v5; // cx@5
+  int v6; // esi@5
+  unsigned int v7; // eax@7
+  int v8; // eax@10
+  SpriteFrame *v9; // eax@16
+  SpriteFrame *v10; // ebx@18
+  //int *v11; // eax@18
+  int v12; // ecx@28
+  //IndoorCameraD3D **v14; // eax@36
+  double v15; // st7@36
+  float v16; // eax@36
+  //double v17; // ST30_8@36
+  signed __int64 v18; // qtt@36
+  int v19; // ST5C_4@36
+  signed __int64 v20; // qtt@37
+  int v21; // ST5C_4@37
+  signed __int16 v22; // cx@39
+  int v23; // ST50_4@40
+  signed int v24; // ecx@40
+  int v25; // edx@44
+  __int16 v26; // ax@44
+  //MonsterDesc *v27; // edx@44
+  //int v28; // ecx@44
+  unsigned __int8 v29; // zf@44
+  unsigned __int8 v30; // sf@44
+  unsigned int v31; // [sp-8h] [bp-5Ch]@15
+  int v32; // [sp+1Ch] [bp-38h]@5
+  int a3; // [sp+20h] [bp-34h]@5
+  int a2; // [sp+24h] [bp-30h]@5
+  int a1a; // [sp+28h] [bp-2Ch]@5
+  __int16 a5; // [sp+2Ch] [bp-28h]@5
+  int a5a; // [sp+2Ch] [bp-28h]@36
+  int a5b; // [sp+2Ch] [bp-28h]@40
+  __int16 v41; // [sp+3Ch] [bp-18h]@18
+  int a6; // [sp+40h] [bp-14h]@34
+  int v43; // [sp+44h] [bp-10h]@34
+  int z; // [sp+48h] [bp-Ch]@32
+  signed int y; // [sp+4Ch] [bp-8h]@32
+  int x; // [sp+50h] [bp-4h]@32
+
+  for (uint i = 0; i < uNumActors; ++i)
+  {
+    auto p = &pActors[i];
+
+    if (p->uAIState == Removed ||
+        p->uAIState == Disabled)
+      continue;
+
+    a5 = p->uSectorID;
+    a2 = p->vPosition.y;
+    a1a = p->vPosition.x;
+    a3 = p->vPosition.z;
+    v4 = stru_5C6E00->Atan2(a1a - pBLVRenderParams->vPartyPos.x, a2 - pBLVRenderParams->vPartyPos.y);
+    LOWORD(v0) = p->uYawAngle;
+    v5 = p->uCurrentActionAnimation;
+    v6 = ((signed int)((char *)v0 + ((signed int)stru_5C6E00->uIntegerPi >> 3) - v4 + stru_5C6E00->uIntegerPi) >> 8) & 7;
+    v32 = v6;
+    if ( pParty->bTurnBasedModeOn )
+    {
+      if ( v5 == 1 )
+      {
+        v7 = pMiscTimer->uTotalGameTimeElapsed;
+        goto LABEL_10;
+      }
+    }
+    else
+    {
+      if ( v5 == 1 )
+      {
+        v7 = pBLVRenderParams->field_0_timer_;
+LABEL_10:
+        v8 = i * 32 + v7;
+        goto LABEL_12;
+      }
+    }
+    v8 = p->uCurrentActionTime;
+LABEL_12:
+    if (p->pActorBuffs[5].uExpireTime > 0i64 || p->pActorBuffs[6].uExpireTime > 0i64 )
+      v8 = 0;
+    v31 = p->pSpriteIDs[v5];
+    if (p->uAIState == Resurrected)
+      v9 = pSpriteFrameTable->GetFrameBy_x(v31, v8);
+    else
+      v9 = pSpriteFrameTable->GetFrame(v31, v8);
+    v41 = 0;
+    v10 = v9;
+    //v11 = (int *)v9->uFlags;
+    if (v9->uFlags & 2)
+      v41 = 2;
+    if (v9->uFlags & 0x40000)
+      v41 |= 0x40u;
+    if (v9->uFlags & 0x20000)
+      LOBYTE(v41) = v41 | 0x80;
+    v0 = (RenderBillboard *)(256 << v6);
+    if ( (unsigned int)v0 & v9->uFlags)
+      v41 |= 4u;
+    if ( v10->uGlowRadius )
+    {
+      //LOBYTE(v11) = byte_4E94D3;
+      pMobileLightsStack->AddLight(
+        a1a,
+        a2,
+        a3,
+        a5,
+        v10->uGlowRadius,
+        0xFFu,
+        0xFFu,
+        0xFFu,
+        byte_4E94D3);
+    }
+    v12 = 0;
+    if ( pBspRenderer->uNumVisibleNotEmptySectors <= 0 )
+      continue;
+    while (pBspRenderer->pVisibleSectorIDs_toDrawDecorsActorsEtcFrom[v12] != p->uSectorID)
+    {
+      ++v12;
+      if ( v12 >= pBspRenderer->uNumVisibleNotEmptySectors )
+        goto _continue;
+    }
+    if ( !pGame->pIndoorCameraD3D->ApplyViewTransform_TrueIfStillVisible(a1a, a2, a3, &x, &y, &z, 1)
+      || (v0 = (RenderBillboard *)abs(x), (signed int)v0 < abs(y)) )
+      continue;
+    pGame->pIndoorCameraD3D->Project(x, y, z, &v43, &a6);
+    v0 = &pBillboardRenderList[uNumBillboardsToDraw];
+    if (uNumBillboardsToDraw >= 500)
+      break;
+    ++uNumBillboardsToDraw;
+    ++uNumSpritesDrawnThisFrame;
+    p->uAttributes |= 8u;
+    v29 = pRenderer->pRenderD3D == 0;
+    v0->uHwSpriteID = v10->pHwSpriteIDs[v32];
+    v0->uPalette = v10->uPaletteIndex;
+    v0->uIndoorSectorID = a5;
+    if ( v29 )
+    {
+      LODWORD(v20) = pBLVRenderParams->field_40 << 16;
+      HIDWORD(v20) = pBLVRenderParams->field_40 >> 16;
+      v21 = v20 / x;
+      v0->_screenspace_x_scaler_packedfloat = (unsigned __int64)(v10->scale * v20 / x) >> 16;
+      a5a = (unsigned __int64)(v10->scale * (signed __int64)v21) >> 16;
+    }
+    else
+    {
+      //v14 = &pGame->pIndoorCameraD3D;
+      v0->fov_x = pGame->pIndoorCameraD3D->fov_x;
+      v15 = pGame->pIndoorCameraD3D->fov_y;
+      v16 = v0->fov_x;
+      v0->fov_y = v15;
+      //v17 = v16 + 6.7553994e15;
+      LODWORD(v18) = 0;
+      HIDWORD(v18) = floorf(v16 + 0.5f);
+      v19 = v18 / x;
+      v0->_screenspace_x_scaler_packedfloat = (unsigned __int64)(v10->scale * v18 / x) >> 16;
+      a5a = (unsigned __int64)(v10->scale * (signed __int64)v19) >> 16;
+    }
+    v0->_screenspace_y_scaler_packedfloat = a5a;
+    if ( (signed __int64)p->pActorBuffs[3].uExpireTime <= 0 )
+    {
+      if ( (signed __int64)p->pActorBuffs[10].uExpireTime > 0 )
+      {
+        a5b = (unsigned __int64)(pGame->pStru6Instance->_4A806F(p) * (signed __int64)v0->_screenspace_y_scaler_packedfloat) >> 16;
+        goto LABEL_43;
+      }
+    }
+    else
+    {
+      v22 = p->pActorBuffs[3].uPower;
+      if ( v22 )
+      {
+        v23 = (unsigned __int64)(65536 / (unsigned __int16)v22 * (signed __int64)v0->_screenspace_x_scaler_packedfloat) >> 16;
+        v24 = p->pActorBuffs[3].uPower;
+        v0->_screenspace_x_scaler_packedfloat = v23;
+        a5b = (unsigned __int64)(65536 / v24 * (signed __int64)v0->_screenspace_y_scaler_packedfloat) >> 16;
+LABEL_43:
+        v0->_screenspace_y_scaler_packedfloat = a5b;
+        goto LABEL_44;
+      }
+    }
+LABEL_44:
+    HIWORD(v25) = HIWORD(x);
+    v0->world_x = a1a;
+    v0->world_y = a2;
+    v0->world_z = a3;
+    v0->uScreenSpaceX = v43;
+    v0->uScreenSpaceY = a6;
+    LOWORD(v25) = 0;
+    LOBYTE(v26) = v41;
+
+    //v0->sZValue = v25 + (PID(OBJECT_Actor,i));
+    v0->actual_z = HIWORD(x);
+    v0->object_pid = PID(OBJECT_Actor,i);
+
+    v29 = HIDWORD(p->pActorBuffs[5].uExpireTime) == 0;
+    v30 = HIDWORD(p->pActorBuffs[5].uExpireTime) < 0;
+    v0->field_1E = v41;
+    v0->pSpriteFrame = v10;
+    v0->uTintColor = pMonsterList->pMonsters[p->pMonsterInfo.uID - 1].uTintColor;
+    if ( !v30 && (!(v30 | v29) || LODWORD(p->pActorBuffs[5].uExpireTime)) )
+    {
+      HIBYTE(v26) = HIBYTE(v41) | 1;
+      v0->field_1E = v26;
+    }
+    
+_continue:
+    ;
+  }
+}
+//----- (0044028F) --------------------------------------------------------
+void PrepareItemsRenderList_BLV()
+{
+  ObjectDesc *v1; // ebx@4
+  __int16 v2; // ax@5
+  RenderBillboard *v3; // esi@12
+  SpriteFrame *v4; // eax@12
+  SpriteFrame *v5; // ebx@12
+  unsigned int v6; // eax@12
+  int v7; // ecx@12
+  int v8; // edx@12
+  int v9; // ecx@12
+  unsigned __int16 v10; // ax@12
+  int *v11; // eax@20
+  //char v12; // zf@26
+  __int64 v18; // ST5C_4@27
+  signed __int64 v19; // qtt@28
+  int v20; // ST5C_4@28
+  //int v21; // edx@29
+  __int16 v22; // ax@29
+  //int v23; // eax@29
+  SpriteFrame *v24; // [sp+1Ch] [bp-40h]@12
+  //__int16 a5; // [sp+28h] [bp-34h]@12
+  int a6; // [sp+2Ch] [bp-30h]@12
+  int a2; // [sp+30h] [bp-2Ch]@12
+  int a1; // [sp+34h] [bp-28h]@12
+  int v30; // [sp+38h] [bp-24h]@12
+  int v31; // [sp+38h] [bp-24h]@27
+  int a3; // [sp+40h] [bp-1Ch]@12
+  signed __int16 v34; // [sp+44h] [bp-18h]@14
+  int v35; // [sp+48h] [bp-14h]@25
+  int v36; // [sp+4Ch] [bp-10h]@25
+  signed int z; // [sp+50h] [bp-Ch]@24
+  signed int y; // [sp+54h] [bp-8h]@24
+  signed int x; // [sp+58h] [bp-4h]@24
+
+  for (uint i = 0; i < uNumSpriteObjects; ++i)
+  {
+    auto p = &pSpriteObjects[i];
+    if (p->uObjectDescID)
+    {
+      v1 = &pObjectList->pObjects[p->uObjectDescID];
+        if ( !(v1->uFlags & 1) )
+         {
+          if ( ((v2 = p->uType, v2 < 1000) || v2 >= 10000)
+            && (v2 < 500 || v2 >= 600)
+            && (v2 < 811 || v2 >= 815)
+            || pGame->pStru6Instance->_4A81CA(p))
+          {
+            //a5 = p->uSectorID;
+            a1 = p->vPosition.x;
+            a2 = p->vPosition.y;
+            a3 = p->vPosition.z;
+            v3 = &pBillboardRenderList[uNumBillboardsToDraw];
+            v4 = pSpriteFrameTable->GetFrame(v1->uSpriteID, p->uSpriteFrameID);
+            v5 = v4;
+            v24 = v4;
+            v30 = v4->uFlags;
+            a6 = v4->uGlowRadius * p->field_22_glow_radius_multiplier;
+            v6 = stru_5C6E00->Atan2(p->vPosition.x - pBLVRenderParams->vPartyPos.x,
+                                    p->vPosition.y - pBLVRenderParams->vPartyPos.y);
+            LOWORD(v7) = p->uFacing;
+            v8 = v30;
+            v9 = ((signed int)(stru_5C6E00->uIntegerPi + ((signed int)stru_5C6E00->uIntegerPi >> 3) + v7 - v6) >> 8) & 7;
+            v10 = v5->pHwSpriteIDs[v9];
+            v3->uHwSpriteID = v10;
+            if ( v30 & 0x20 )
+            {
+              v8 = v30;
+              a3 -= (signed int)((unsigned __int64)(v5->scale * (signed __int64)pSprites_LOD->pSpriteHeaders[(signed __int16)v10].uHeight) >> 16) >> 1;
+            }
+            v34 = 0;
+            if ( v8 & 2 )
+              v34 = 2;
+            if ( v8 & 0x40000 )
+              v34 |= 0x40u;
+            if ( v8 & 0x20000 )
+              LOBYTE(v34) = v34 | 0x80;
+            v11 = (int *)(256 << v9);
+            if ( (256 << v9) & v8 )
+              v34 |= 4u;
+            if ( a6 )
+            {
+              LOBYTE(v11) = byte_4E94D3;
+              pMobileLightsStack->AddLight(
+                a1,
+                a2,
+                a3,
+                p->uSectorID,
+                a6,
+                v1->uParticleTrailColorR,
+                v1->uParticleTrailColorG,
+                v1->uParticleTrailColorB,
+                byte_4E94D3);
+            }
+            if ( pGame->pIndoorCameraD3D->ApplyViewTransform_TrueIfStillVisible(
+                   a1,
+                   a2,
+                   a3,
+                   &x,
+                   &y,
+                   &z,
+                   1) )
+            {
+              pGame->pIndoorCameraD3D->Project(x, y, z, &v36, &v35);
+
+              assert(uNumBillboardsToDraw < 500);
+              //if ( (signed int)uNumBillboardsToDraw >= 500 )
+              //  return;
+              ++uNumBillboardsToDraw;
+              ++uNumSpritesDrawnThisFrame;
+              p->uAttributes |= 1u;
+              //v12 = pRenderer->pRenderD3D == 0;
+              v3->uPalette = v24->uPaletteIndex;
+              v3->uIndoorSectorID = p->uSectorID;
+              if ( pRenderer->pRenderD3D )
+              {
+                v3->fov_x = pGame->pIndoorCameraD3D->fov_x;
+                v3->fov_y = pGame->pIndoorCameraD3D->fov_y;
+                LODWORD(v18) = 0;
+                HIDWORD(v18) = (int)floorf(v3->fov_x + 0.5f);
+                v18 = v18 / x;
+                v3->_screenspace_x_scaler_packedfloat = (unsigned __int64)(v24->scale * v18) >> 16;
+                v31 = (unsigned __int64)(v24->scale * v18) >> 16;
+              }
+              else
+              {
+                LODWORD(v19) = pBLVRenderParams->field_40 << 16;
+                HIDWORD(v19) = pBLVRenderParams->field_40 >> 16;
+                v20 = v19 / x;
+                v3->_screenspace_x_scaler_packedfloat = (unsigned __int64)(v24->scale * v19 / x) >> 16;
+                v31 = (unsigned __int64)(v24->scale * (signed __int64)v20) >> 16;
+              }
+              //HIWORD(v21) = HIWORD(x);
+              //LOWORD(v21) = 0;
+              v3->_screenspace_y_scaler_packedfloat = v31;
+              v3->field_1E = v34;
+              v3->world_x = a1;
+              v3->world_y = a2;
+              v3->world_z = a3;
+              v3->uScreenSpaceX = v36;
+              v22 = v35;
+              v3->uTintColor = 0;
+              v3->uScreenSpaceY = v22;
+              //v23 = 8 * i;
+              //LOBYTE(v23) = PID(OBJECT_Item,i);
+              v3->pSpriteFrame = v24;
+              //v12 = (p->uAttributes & 0x20) == 0;
+              //v3->sZValue = v21 + v23;
+              v3->actual_z = HIWORD(x);
+              v3->object_pid = PID(OBJECT_Item,i);
+              if (p->uAttributes & 0x20)
+              {
+                if ( !pRenderer->pRenderD3D )
+                  v3->sZValue = 0;
+              }
+            }
+          }
+        }
+      }
+  }
+}
+
+//----- (00440639) --------------------------------------------------------
+void AddBspNodeToRenderList(unsigned int node_id)
+{
+  BLVSector *pSector; // esi@1
+
+  pSector = &pIndoor->pSectors[pBspRenderer->nodes[node_id].uSectorID];
+  if ( pRenderer->pRenderD3D )
+  {
+    for (uint i = 0; i < pSector->uNumNonBSPFaces; ++i)
+      //Log::Warning(L"Non-BSP face: %X", v3->pFaceIDs[v2]);
+      pBspRenderer->AddFaceToRenderList_d3d(node_id, pSector->pFaceIDs[i]);
+  }
+  else
+  {
+    for (uint i = 0; i < pSector->uNumNonBSPFaces; ++i)
+      pBspRenderer->AddFaceToRenderList_sw(node_id, pSector->pFaceIDs[i]);
+  }
+  if ( pSector->field_0 & 0x10 )
+    sub_4406BC(node_id, pSector->uFirstBSPNode);
+}
+
+//----- (004406BC) --------------------------------------------------------
+void __fastcall sub_4406BC(unsigned int node_id, unsigned int uFirstNode)
+{
+  BLVSector *pSector; // esi@2
+  BSPNode *pNode; // edi@2
+  BLVFace *pFace; // eax@2
+  int v5; // ecx@2
+  __int16 v6; // ax@6
+  int v7; // ebp@10
+  int v8; // ebx@10
+  __int16 v9; // di@18
+  //int v10; // [sp+10h] [bp-Ch]@1
+  //bool v11; // [sp+14h] [bp-8h]@5
+  BspRenderer_stru0 *node; // [sp+18h] [bp-4h]@1
+
+  //Log::Warning(L"sub_4406BC(%u, %u)", a1, uFirstNode);
+
+  //v10 = a1;
+  node = &pBspRenderer->nodes[node_id];
+  while ( 1 )
+  {
+    pSector = &pIndoor->pSectors[node->uSectorID];
+    pNode = &pIndoor->pNodes[uFirstNode];
+    pFace = &pIndoor->pFaces[pSector->pFaceIDs[pNode->uCoplanarOffset]];
+    v5 = pFace->pFacePlane_old.dist + pBLVRenderParams->vPartyPos.x * pFace->pFacePlane_old.vNormal.x
+       + pBLVRenderParams->vPartyPos.y * pFace->pFacePlane_old.vNormal.y + pBLVRenderParams->vPartyPos.z * pFace->pFacePlane_old.vNormal.z;//plane equation
+    if (pFace->Portal() && pFace->uSectorID != node->uSectorID )
+      v5 = -v5;
+    //v11 = v5 > 0;
+    if ( v5 <= 0 )
+      v6 = pNode->uFront;
+    else
+      v6 = pNode->uBack;
+    if ( v6 != -1 )
+      sub_4406BC(node_id, v6);
+    v7 = pNode->uCoplanarOffset;
+    v8 = v7 + pNode->uCoplanarSize;
+
+    //Log::Warning(L"Node %u: %X to %X (%hX)", uFirstNode, v7, v8, v2->pFaceIDs[v7]);
+    
+    if ( pRenderer->pRenderD3D )
+    {
+      while ( v7 < v8 )
+        pBspRenderer->AddFaceToRenderList_d3d(node_id, pSector->pFaceIDs[v7++]);
+    }
+    else
+    {
+      while ( v7 < v8 )
+        pBspRenderer->AddFaceToRenderList_sw(node_id, pSector->pFaceIDs[v7++]);
+    }
+    v9 = v5 > 0 ? pNode->uFront : pNode->uBack;
+    if ( v9 == -1 )
+      break;
+    uFirstNode = v9;
+  }
+}
+//----- (0043FA33) --------------------------------------------------------
+void __fastcall PrepareDecorationsRenderList_BLV(unsigned int uDecorationID, unsigned int uSectorID)
+{
+  LevelDecoration *v2; // esi@1
+  DecorationDesc *v3; // ebx@2
+  __int16 v4; // ax@2
+  double v5; // st7@3
+  int v6; // eax@5
+  int v7; // edx@5
+  unsigned int v8; // edi@5
+  int v9; // edi@5
+  int v10; // eax@7
+  SpriteFrame *v11; // eax@7
+  SpriteFrame *v12; // esi@7
+  int v13; // eax@7
+  int v14; // ebx@16
+  RenderBillboard *v15; // ecx@17
+  char v16; // zf@18
+  IndoorCameraD3D **v17; // eax@19
+  double v18; // st7@19
+  //float v19; // eax@19
+  signed __int64 v20; // qtt@19
+  signed __int64 v21; // qtt@20
+  //int v22; // edx@21
+  //int v23; // eax@21
+  Particle_sw local_0; // [sp+Ch] [bp-A0h]@3
+  //double v25; // [sp+74h] [bp-38h]@19
+  //unsigned int v26; // [sp+7Ch] [bp-30h]@1
+  int a2; // [sp+80h] [bp-2Ch]@5
+  int a3; // [sp+84h] [bp-28h]@5
+  int a1; // [sp+88h] [bp-24h]@5
+  int v30; // [sp+8Ch] [bp-20h]@7
+  //float v31; // [sp+90h] [bp-1Ch]@1
+  int a5; // [sp+94h] [bp-18h]@17
+  int z; // [sp+98h] [bp-14h]@15
+  int a6; // [sp+9Ch] [bp-10h]@17
+  int y; // [sp+A0h] [bp-Ch]@15
+  int x; // [sp+A4h] [bp-8h]@15
+  int v37; // [sp+A8h] [bp-4h]@5
+
+  //v26 = uDecorationID;
+  //LODWORD(v31) = uSectorID;
+  v2 = &pLevelDecorations[uDecorationID];
+  if (v2->field_2 & 0x20)
+    return;
+
+    v3 = &pDecorationList->pDecorations[v2->uDecorationDescID];
+    v4 = v3->uFlags;
+    if (v3->uFlags & DECORATION_EMITS_FIRE)
+    {
+      memset(&local_0, 0, 0x68u);               // fire,  like at the Pit's tavern
+      v5 = (double)v2->vPosition.x;
+      local_0.type = ParticleType_Bitmap | ParticleType_Rotating | ParticleType_8;
+      local_0.uDiffuse = 0xFF3C1E;
+      local_0.x = v5;
+      local_0.y = (double)v2->vPosition.y;
+      local_0.z = (double)v2->vPosition.z;
+      local_0.flt_10 = 0.0;
+      local_0.flt_14 = 0.0;
+      local_0.flt_18 = 0.0;
+      local_0.flt_28 = 1.0;
+      local_0.timeToLive = (rand() & 0x80) + 128;
+      local_0.uTextureID = pBitmaps_LOD->LoadTexture("effpar01");
+      pGame->pParticleEngine->AddParticle(&local_0);
+      return;
+    }
+
+
+      if (v4 & DECORATION_DONT_DRAW)
+        return;
+
+        v6 = v2->vPosition.x;
+        v7 = v2->vPosition.z;
+        a2 = v2->vPosition.y;
+        a1 = v6;
+        a3 = v7;
+        v8 = v2->field_10_y_rot
+           + ((signed int)stru_5C6E00->uIntegerPi >> 3)
+           - stru_5C6E00->Atan2(v6 - pBLVRenderParams->vPartyPos.x, a2 - pBLVRenderParams->vPartyPos.y);
+        v37 = pBLVRenderParams->field_0_timer_;
+        v9 = ((signed int)(stru_5C6E00->uIntegerPi + v8) >> 8) & 7;
+        if (pParty->bTurnBasedModeOn)
+          v37 = pMiscTimer->uTotalGameTimeElapsed;
+        v10 = abs(v2->vPosition.x + v2->vPosition.y);
+        v11 = pSpriteFrameTable->GetFrame(v3->uSpriteID, v37 + v10);
+        v30 = 0;
+        v12 = v11;
+        v13 = v11->uFlags;
+        if ( v13 & 2 )
+          v30 = 2;
+        if ( v13 & 0x40000 )
+          v30 |= 0x40u;
+        if ( v13 & 0x20000 )
+          LOBYTE(v30) = v30 | 0x80;
+        if ( (256 << v9) & v13 )
+          v30 |= 4u;
+        if ( pGame->pIndoorCameraD3D->ApplyViewTransform_TrueIfStillVisible(a1, a2, a3, &x, &y, &z, 1) )
+        {
+          v14 = abs(x);
+          if ( v14 >= abs(y) )
+          {
+            pGame->pIndoorCameraD3D->Project(x, y, z, &a5, &a6);
+
+            v15 = &pBillboardRenderList[uNumBillboardsToDraw];
+            assert(uNumBillboardsToDraw < 500);
+
+              ++uNumBillboardsToDraw;
+              ++uNumDecorationsDrawnThisFrame;
+              v16 = pRenderer->pRenderD3D == 0;
+              v15->uHwSpriteID = v12->pHwSpriteIDs[v9];
+              v15->uPalette = v12->uPaletteIndex;
+              v15->uIndoorSectorID = uSectorID;
+              if ( v16 )
+              {
+                LODWORD(v21) = pBLVRenderParams->field_40 << 16;
+                HIDWORD(v21) = pBLVRenderParams->field_40 >> 16;
+                v37 = v21 / x;
+                //LODWORD(v31) = v12->scale;
+                v37 = v21 / x;
+                v15->_screenspace_x_scaler_packedfloat = (unsigned __int64)(v12->scale * v21 / x) >> 16;
+                v37 = (unsigned __int64)(v12->scale * (signed __int64)v37) >> 16;
+              }
+              else
+              {
+                v17 = &pGame->pIndoorCameraD3D;
+                v15->fov_x = pGame->pIndoorCameraD3D->fov_x;
+                v18 = (*v17)->fov_y;
+                //v19 = v15->fov_x;
+                v15->fov_y = v18;
+                //v31 = v19;
+                //v25 = v19 + 6.7553994e15;
+                //v25 = floorf(v15->fov_x + 0.5f);
+                LODWORD(v20) = 0;
+                HIDWORD(v20) = floorf(v15->fov_x + 0.5f);
+                v37 = v20 / x;
+                //LODWORD(v31) = v12->scale;
+                v37 = (unsigned __int64)(v12->scale * v20 / x) >> 16;
+                v15->_screenspace_x_scaler_packedfloat = (unsigned __int64)(v12->scale * v20 / x) >> 16;
+                //v31 = v15->fov_y;
+                //v25 = v31 + 6.7553994e15;
+                //v25 = floorf(v15->fov_y + 0.5f);
+                LODWORD(v20) = 0;
+                HIDWORD(v20) = floorf(v15->fov_y + 0.5f);
+                v37 = v20 / x;
+                v37 = (unsigned __int64)(v12->scale * v20 / x) >> 16;
+              }
+              //HIWORD(v22) = HIWORD(x);
+              //LOWORD(v22) = 0;
+              v15->_screenspace_y_scaler_packedfloat = v37;
+              v15->field_1E = v30;
+              v15->world_x = a1;
+              v15->world_y = a2;
+              v15->world_z = a3;
+              v15->uScreenSpaceX = a5;
+              v15->uScreenSpaceY = a6;
+              //v23 = 8 * uDecorationID;
+              //LOBYTE(v23) = PID(OBJECT_Decoration,uDecorationID);
+
+              //v15->sZValue = v22 + v23;
+              v15->actual_z = HIWORD(x);
+              v15->object_pid = PID(OBJECT_Decoration,uDecorationID);
+
+              v15->uTintColor = 0;
+              v15->pSpriteFrame = v12;
+          }
+        }
+}
+//----- (0043F953) --------------------------------------------------------
+void PrepareBspRenderList_BLV()
+{
+  pBspRenderer->num_faces = 0;
+
+  if (pBLVRenderParams->uPartySectorID)
+  {
+    pBspRenderer->nodes[0].uSectorID = pBLVRenderParams->uPartySectorID;
+    pBspRenderer->nodes[0].uViewportW = pBLVRenderParams->uViewportW;
+    pBspRenderer->nodes[0].uViewportZ = pBLVRenderParams->uViewportZ;
+    pBspRenderer->nodes[0].uViewportY = pBLVRenderParams->uViewportY;
+    pBspRenderer->nodes[0].uViewportX = pBLVRenderParams->uViewportX;
+    pBspRenderer->nodes[0].field_C.GetViewportData(pBLVRenderParams->uViewportX, pBLVRenderParams->uViewportY,
+                                           pBLVRenderParams->uViewportZ, pBLVRenderParams->uViewportW);
+    pBspRenderer->nodes[0].uFaceID = -1;
+    pBspRenderer->nodes[0].viewing_portal_id = -1;
+    pBspRenderer->num_nodes = 1;
+    AddBspNodeToRenderList(0);
+  }
+
+  pBspRenderer->MakeVisibleSectorList();
+}
+
+//----- (0043F9E1) --------------------------------------------------------
+void BspRenderer_stru2::GetViewportData(__int16 x, int y, __int16 z, int w)
+{
+  _viewport_space_y = y;
+  _viewport_space_w = w;
+
+  for (uint i = 0; i < 480; ++i)
+  {
+    if ( i < y || i > w )
+    {
+      viewport_left_side[i] = 640;
+      viewport_right_side[i] = -1;
+    }
+    else
+    {
+      viewport_left_side[i] = x;
+      viewport_right_side[i] = z;
+    } 
+  }
+}
+//----- (0048653D) --------------------------------------------------------
+int stru149::_48653D(int a2, int a3, int a4, int a5, int a6, int a7)//portal frustum culling
+{
+  stru149 *v7; // esi@1
+  int v8; // edi@1
+  int v9; // eax@1
+  //int v10; // edx@1
+  //int v11; // ecx@1
+  int v12; // eax@1
+  int v13; // ebx@2
+  int v14; // ecx@2
+  int v15; // eax@2
+  int v16; // ST14_4@3
+  int v17; // ST10_4@3
+  int v18; // eax@5
+  int v19; // ST10_4@6
+  int v20; // eax@8
+  int v21; // ST10_4@9
+  int v22; // eax@10
+  int v23; // ecx@10
+  int v24; // eax@10
+  int result; // eax@10
+  //int v26; // [sp+14h] [bp-14h]@1
+  int v27; // [sp+18h] [bp-10h]@1
+  int v28; // [sp+1Ch] [bp-Ch]@1
+  int v29; // [sp+24h] [bp-4h]@1
+  int v30; // [sp+30h] [bp+8h]@10
+  int v31; // [sp+3Ch] [bp+14h]@10
+
+  v7 = this;
+  v8 = stru_5C6E00->Cos(pBLVRenderParams->sPartyRotY);
+  v29 = stru_5C6E00->Sin(pBLVRenderParams->sPartyRotY);
+  v28 = stru_5C6E00->Cos(pBLVRenderParams->sPartyRotX);
+  v9 = stru_5C6E00->Sin(pBLVRenderParams->sPartyRotX);
+  //v11 = -pBLVRenderParams->vPartyPos.y;
+  //v26 = -pBLVRenderParams->vPartyPos.x;
+  v27 = v9;
+  v12 = -pBLVRenderParams->vPartyPos.z;
+  if ( pBLVRenderParams->sPartyRotX )
+  {
+    v16 = v8 * -pBLVRenderParams->vPartyPos.x + v29 * -pBLVRenderParams->vPartyPos.y;
+    v13 = v28;
+    v17 = -65536 * pBLVRenderParams->vPartyPos.z;
+    v7->field_0_party_dir_x = ((unsigned __int64)(v16 * (signed __int64)v28) >> 16)
+                + ((unsigned __int64)(-65536 * pBLVRenderParams->vPartyPos.z * (signed __int64)v27) >> 16);
+    v7->field_4_party_dir_y = v8 * -pBLVRenderParams->vPartyPos.y - v29 * -pBLVRenderParams->vPartyPos.x;
+    v14 = v27;
+    v15 = ((unsigned __int64)(v17 * (signed __int64)v28) >> 16) - ((unsigned __int64)(v16 * (signed __int64)v27) >> 16);
+  }
+  else
+  {
+    v7->field_0_party_dir_x = v8 * -pBLVRenderParams->vPartyPos.x + v29 * -pBLVRenderParams->vPartyPos.y;
+    v13 = v28;
+    v7->field_4_party_dir_y = v8 * -pBLVRenderParams->vPartyPos.y - v29 * -pBLVRenderParams->vPartyPos.x;
+    v14 = v27;
+    v15 = v12 << 16;
+  }
+  v7->field_8 = v15;
+  if ( pBLVRenderParams->sPartyRotX )
+  {
+    v19 = ((unsigned __int64)(a2 * (signed __int64)v8) >> 16) + ((unsigned __int64)(a3 * (signed __int64)v29) >> 16);
+    v7->field_C = ((unsigned __int64)(v19 * (signed __int64)v13) >> 16)
+                + ((unsigned __int64)(a4 * (signed __int64)v14) >> 16);
+    v7->field_10 = ((unsigned __int64)(a3 * (signed __int64)v8) >> 16)
+                 - ((unsigned __int64)(a2 * (signed __int64)v29) >> 16);
+    v18 = ((unsigned __int64)(a4 * (signed __int64)v13) >> 16) - ((unsigned __int64)(v19 * (signed __int64)v14) >> 16);
+  }
+  else
+  {
+    v7->field_C = ((unsigned __int64)(a2 * (signed __int64)v8) >> 16)
+                + ((unsigned __int64)(a3 * (signed __int64)v29) >> 16);
+    v7->field_10 = ((unsigned __int64)(a3 * (signed __int64)v8) >> 16)
+                 - ((unsigned __int64)(a2 * (signed __int64)v29) >> 16);
+    v18 = a4;
+  }
+  v7->field_14 = v18;
+  if ( pBLVRenderParams->sPartyRotX )
+  {
+    v21 = ((unsigned __int64)(a5 * (signed __int64)v8) >> 16) + ((unsigned __int64)(a6 * (signed __int64)v29) >> 16);
+    v7->field_18 = ((unsigned __int64)(v21 * (signed __int64)v13) >> 16)
+                 + ((unsigned __int64)(a7 * (signed __int64)v14) >> 16);
+    v7->field_1C = ((unsigned __int64)(a6 * (signed __int64)v8) >> 16)
+                 - ((unsigned __int64)(a5 * (signed __int64)v29) >> 16);
+    v20 = ((unsigned __int64)(a7 * (signed __int64)v13) >> 16) - ((unsigned __int64)(v21 * (signed __int64)v14) >> 16);
+  }
+  else
+  {
+    v7->field_18 = ((unsigned __int64)(a5 * (signed __int64)v8) >> 16)
+                 + ((unsigned __int64)(a6 * (signed __int64)v29) >> 16);
+    v7->field_1C = ((unsigned __int64)(a6 * (signed __int64)v8) >> 16)
+                 - ((unsigned __int64)(a5 * (signed __int64)v29) >> 16);
+    v20 = a7;
+  }
+  v7->field_18 = -v7->field_18;
+  v7->field_1C = -v7->field_1C;
+  v7->field_20 = v20;
+  v22 = v7->field_C;
+  v7->field_20 = -v7->field_20;
+  v23 = ((unsigned __int64)(v22 * (signed __int64)v7->field_0_party_dir_x) >> 16)
+      + ((unsigned __int64)(v7->field_10 * (signed __int64)v7->field_4_party_dir_y) >> 16)
+      + ((unsigned __int64)(v7->field_14 * (signed __int64)v7->field_8) >> 16);
+  v30 = v7->field_18;
+  v24 = v7->field_0_party_dir_x;
+  v7->field_24 = v23;
+  v31 = (unsigned __int64)(v30 * (signed __int64)v24) >> 16;
+  result = (unsigned __int64)(v7->field_1C * (signed __int64)v7->field_4_party_dir_y) >> 16;
+  v7->field_28 = v31 + result + ((unsigned __int64)(v7->field_20 * (signed __int64)v7->field_8) >> 16);
+  return result;
 }
\ No newline at end of file