Fix arm being backface culled when in hand, fix arm rotation in hand.

This commit is contained in:
UnknownShadow200 2017-08-19 11:06:23 +10:00
parent 345426107a
commit 44ec23c931
8 changed files with 100 additions and 66 deletions

View File

@ -37,8 +37,8 @@ namespace ClassicalSharp.Model {
ModelPart MakeLeg(int x1, int x2, int legX1, int legX2) {
const float y1 = 1/64f, y2 = 5/16f, z2 = 1/16f, z1 = -2/16f;
ModelBuilder.YQuad(this, 32, 0, 3, 3, x2/16f, x1/16f, z1, z2, y1); // bottom feet
ModelBuilder.ZQuad(this, 36, 3, 1, 5, legX1/16f, legX2/16f, y1, y2, z2); // vertical part of leg
ModelBuilder.YQuad(this, 32, 0, 3, 3, x2/16f, x1/16f, z1, z2, y1, false); // bottom feet
ModelBuilder.ZQuad(this, 36, 3, 1, 5, legX1/16f, legX2/16f, y1, y2, z2, false); // vertical part of leg
return new ModelPart(index - 2 * 4, 2 * 4, 0/16f, 5/16f, 1/16f);
}

View File

@ -143,7 +143,9 @@ namespace ClassicalSharp.Model {
ModelPart part = model.RightArm;
part.RotX += 1 / 16.0f;
part.RotY -= 4 / 16.0f;
DrawRotate(0, 0, 120 * Utils.Deg2Rad, part, false);
Rotate = RotateOrder.YZX;
DrawRotate(0, -90 * Utils.Deg2Rad, 120 * Utils.Deg2Rad, part, false);
Rotate = RotateOrder.ZYX;
UpdateVB();
game.Graphics.PopMatrix();

View File

@ -225,6 +225,10 @@ namespace ClassicalSharp.Model {
t = cosX * v.Y + sinX * v.Z; v.Z = -sinX * v.Y + cosX * v.Z; v.Y = t; // Inlined RotX
t = cosZ * v.X + sinZ * v.Y; v.Y = -sinZ * v.X + cosZ * v.Y; v.X = t; // Inlined RotZ
t = cosY * v.X - sinY * v.Z; v.Z = sinY * v.X + cosY * v.Z; v.X = t; // Inlined RotY
} else if (Rotate == RotateOrder.YZX) {
t = cosY * v.X - sinY * v.Z; v.Z = sinY * v.X + cosY * v.Z; v.X = t; // Inlined RotY
t = cosZ * v.X + sinZ * v.Y; v.Y = -sinZ * v.X + cosZ * v.Y; v.X = t; // Inlined RotZ
t = cosX * v.Y + sinX * v.Z; v.Z = -sinX * v.Y + cosX * v.Z; v.Y = t; // Inlined RotX
}
// Rotate globally
@ -240,6 +244,6 @@ namespace ClassicalSharp.Model {
}
}
protected enum RotateOrder { ZYX, XZY }
protected enum RotateOrder { ZYX, XZY, YZX }
}
}

View File

@ -89,12 +89,12 @@ namespace ClassicalSharp.Model {
float x2 = desc.X2, y2 = desc.Y2, z2 = desc.Z2;
int x = desc.TexX, y = desc.TexY;
YQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, z2, z1, y2); // top
YQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x2, x1, z2, z1, y1); // bottom
ZQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, y1, y2, z1); // front
ZQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, y1, y2, z2); // back
XQuad(m, x, y + sidesW, sidesW, bodyH, z2, z1, y1, y2, x2); // left
XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, z1, z2, y1, y2, x1); // right
YQuad(m, x + sidesW, y, bodyW, sidesW, x1, x2, z2, z1, y2, true); // top
YQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x2, x1, z2, z1, y1, false); // bottom
ZQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x1, x2, y1, y2, z1, true); // front
ZQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x2, x1, y1, y2, z2, true); // back
XQuad(m, x, y + sidesW, sidesW, bodyH, z1, z2, y1, y2, x2, true); // left
XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, z2, z1, y1, y2, x1, true); // right
return new ModelPart(m.index - 6 * 4, 6 * 4, desc.RotX, desc.RotY, desc.RotZ);
}
@ -117,12 +117,12 @@ namespace ClassicalSharp.Model {
float x2 = desc.X2, y2 = desc.Y2, z2 = desc.Z2;
int x = desc.TexX, y = desc.TexY;
YQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, z1, z2, y2); // top
YQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, z1, z2, y1); // bottom
ZQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, y1, y2, z1); // front
ZQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x1, x2, y2, y1, z2); // back
XQuad(m, x, y + sidesW, sidesW, bodyH, y2, y1, z2, z1, x2); // left
XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, y1, y2, z2, z1, x1); // right
YQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, z1, z2, y2, false); // top
YQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, z1, z2, y1, false); // bottom
ZQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, y1, y2, z1, false); // front
ZQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x1, x2, y2, y1, z2, false); // back
XQuad(m, x, y + sidesW, sidesW, bodyH, y2, y1, z2, z1, x2, false); // left
XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, y1, y2, z2, z1, x1, false); // right
// rotate left and right 90 degrees
for (int i = m.index - 8; i < m.index; i++) {
@ -134,27 +134,36 @@ namespace ClassicalSharp.Model {
}
public static void XQuad(IModel m, int texX, int texY, int texWidth, int texHeight,
float z1, float z2, float y1, float y2, float x) {
m.vertices[m.index++] = new ModelVertex(x, y1, z1, texX, texY + texHeight | UVMaxBit);
m.vertices[m.index++] = new ModelVertex(x, y2, z1, texX, texY);
m.vertices[m.index++] = new ModelVertex(x, y2, z2, texX + texWidth | UVMaxBit, texY);
m.vertices[m.index++] = new ModelVertex(x, y1, z2, texX + texWidth | UVMaxBit, texY + texHeight | UVMaxBit);
float z1, float z2, float y1, float y2, float x, bool swapU) {
int u1 = texX, u2 = texX + texWidth | UVMaxBit;
if (swapU) { int tmp = u1; u1 = u2; u2 = tmp; }
m.vertices[m.index++] = new ModelVertex(x, y1, z1, u1, texY + texHeight | UVMaxBit);
m.vertices[m.index++] = new ModelVertex(x, y2, z1, u1, texY);
m.vertices[m.index++] = new ModelVertex(x, y2, z2, u2, texY);
m.vertices[m.index++] = new ModelVertex(x, y1, z2, u2, texY + texHeight | UVMaxBit);
}
public static void YQuad(IModel m, int texX, int texY, int texWidth, int texHeight,
float x1, float x2, float z1, float z2, float y) {
m.vertices[m.index++] = new ModelVertex(x1, y, z2, texX, texY + texHeight | UVMaxBit);
m.vertices[m.index++] = new ModelVertex(x1, y, z1, texX, texY);
m.vertices[m.index++] = new ModelVertex(x2, y, z1, texX + texWidth | UVMaxBit, texY);
m.vertices[m.index++] = new ModelVertex(x2, y, z2, texX + texWidth | UVMaxBit, texY + texHeight | UVMaxBit);
float x1, float x2, float z1, float z2, float y, bool swapU) {
int u1 = texX, u2 = texX + texWidth | UVMaxBit;
if (swapU) { int tmp = u1; u1 = u2; u2 = tmp; }
m.vertices[m.index++] = new ModelVertex(x1, y, z2, u1, texY + texHeight | UVMaxBit);
m.vertices[m.index++] = new ModelVertex(x1, y, z1, u1, texY);
m.vertices[m.index++] = new ModelVertex(x2, y, z1, u2, texY);
m.vertices[m.index++] = new ModelVertex(x2, y, z2, u2, texY + texHeight | UVMaxBit);
}
public static void ZQuad(IModel m, int texX, int texY, int texWidth, int texHeight,
float x1, float x2, float y1, float y2, float z) {
m.vertices[m.index++] = new ModelVertex(x1, y1, z, texX, texY + texHeight | UVMaxBit);
m.vertices[m.index++] = new ModelVertex(x1, y2, z, texX, texY);
m.vertices[m.index++] = new ModelVertex(x2, y2, z, texX + texWidth | UVMaxBit, texY);
m.vertices[m.index++] = new ModelVertex(x2, y1, z, texX + texWidth | UVMaxBit, texY + texHeight | UVMaxBit);
float x1, float x2, float y1, float y2, float z, bool swapU) {
int u1 = texX, u2 = texX + texWidth | UVMaxBit;
if (swapU) { int tmp = u1; u1 = u2; u2 = tmp; }
m.vertices[m.index++] = new ModelVertex(x1, y1, z, u1, texY + texHeight | UVMaxBit);
m.vertices[m.index++] = new ModelVertex(x1, y2, z, u1, texY);
m.vertices[m.index++] = new ModelVertex(x2, y2, z, u2, texY);
m.vertices[m.index++] = new ModelVertex(x2, y1, z, u2, texY + texHeight | UVMaxBit);
}
}
}

View File

@ -78,6 +78,7 @@ namespace ClassicalSharp {
AdjustHeadX(player.HeadX));
Vector3 eyePos = player.EyePosition;
float reach = game.LocalPlayer.ReachDistance;
Picking.CalculatePickedBlock(game, eyePos, dir, reach, pos);
}

View File

@ -96,6 +96,10 @@ void IModel_DrawPart(ModelPart part) {
}
}
#define IMODEL_ROTATEX t = cosX * v.Y + sinX * v.Z; v.Z = -sinX * v.Y + cosX * v.Z; v.Y = t;
#define IMODEL_ROTATEY t = cosY * v.X - sinY * v.Z; v.Z = sinY * v.X + cosY * v.Z; v.X = t;
#define IMODEL_ROTATEZ t = cosZ * v.X + sinZ * v.Y; v.Y = -sinZ * v.X + cosZ * v.Y; v.X = t;
void IModel_DrawRotate(Real32 angleX, Real32 angleY, Real32 angleZ, ModelPart part, bool head) {
IModel* model = IModel_ActiveModel;
Real32 cosX = Math_Cos(-angleX), sinX = Math_Sin(-angleX);
@ -112,13 +116,17 @@ void IModel_DrawRotate(Real32 angleX, Real32 angleY, Real32 angleZ, ModelPart pa
/* Rotate locally */
if (model->Rotation == RotateOrder_ZYX) {
t = cosZ * v.X + sinZ * v.Y; v.Y = -sinZ * v.X + cosZ * v.Y; v.X = t; /* Inlined RotZ */
t = cosY * v.X - sinY * v.Z; v.Z = sinY * v.X + cosY * v.Z; v.X = t; /* Inlined RotY */
t = cosX * v.Y + sinX * v.Z; v.Z = -sinX * v.Y + cosX * v.Z; v.Y = t; /* Inlined RotX */
IMODEL_ROTATEZ
IMODEL_ROTATEY
IMODEL_ROTATEX
} else if (model->Rotation == RotateOrder_XZY) {
t = cosX * v.Y + sinX * v.Z; v.Z = -sinX * v.Y + cosX * v.Z; v.Y = t; /* Inlined RotX */
t = cosZ * v.X + sinZ * v.Y; v.Y = -sinZ * v.X + cosZ * v.Y; v.X = t; /* Inlined RotZ */
t = cosY * v.X - sinY * v.Z; v.Z = sinY * v.X + cosY * v.Z; v.X = t; /* Inlined RotY */
IMODEL_ROTATEX
IMODEL_ROTATEZ
IMODEL_ROTATEY
} else if (model->Rotation == RotateOrder_YZX) {
IMODEL_ROTATEY
IMODEL_ROTATEZ
IMODEL_ROTATEX
}
/* Rotate globally */

View File

@ -19,12 +19,13 @@
#define IModel_UVMaxShift 15
/* Order in which axis rotations are applied to a part. */
typedef Int32 RotateOrder;
typedef UInt8 RotateOrder;
#define RotateOrder_ZYX 0
#define RotateOrder_XZY 1
#define RotateOrder_YZX 2
/* Skin layout a humanoid skin texture can have. */
typedef Int32 SkinType;
typedef UInt8 SkinType;
#define SkinType_64x32 0
#define SkinType_64x64 1
#define SkinType_64x64Slim 2

View File

@ -63,12 +63,12 @@ ModelPart BoxDesc_BuildBox(IModel* m, BoxDesc* desc) {
Real32 x2 = desc->X2, y2 = desc->Y2, z2 = desc->Z2;
Int32 x = desc->TexX, y = desc->TexY;
BoxDesc_YQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, z2, z1, y2); /* top */
BoxDesc_YQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x2, x1, z2, z1, y1); /* bottom */
BoxDesc_ZQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, y1, y2, z1); /* front */
BoxDesc_ZQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, y1, y2, z2); /* back */
BoxDesc_XQuad(m, x, y + sidesW, sidesW, bodyH, z2, z1, y1, y2, x2); /* left */
BoxDesc_XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, z1, z2, y1, y2, x1); /* right */
BoxDesc_YQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, z2, z1, y2, false); /* top */
BoxDesc_YQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x2, x1, z2, z1, y1, false); /* bottom */
BoxDesc_ZQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, y1, y2, z1, false); /* front */
BoxDesc_ZQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, y1, y2, z2, false); /* back */
BoxDesc_XQuad(m, x, y + sidesW, sidesW, bodyH, z2, z1, y1, y2, x2, false); /* left */
BoxDesc_XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, z1, z2, y1, y2, x1, false); /* right */
ModelPart part;
ModelPart_Init(&part, m->index - IModel_BoxVertices, IModel_BoxVertices,
@ -82,12 +82,12 @@ ModelPart BoxDesc_BuildRotatedBox(IModel* m, BoxDesc* desc) {
Real32 x2 = desc->X2, y2 = desc->Y2, z2 = desc->Z2;
Int32 x = desc->TexX, y = desc->TexY;
BoxDesc_YQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, z1, z2, y2); /* top */
BoxDesc_YQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, z1, z2, y1); /* bottom */
BoxDesc_ZQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, y1, y2, z1); /* front */
BoxDesc_ZQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x1, x2, y2, y1, z2); /* back */
BoxDesc_XQuad(m, x, y + sidesW, sidesW, bodyH, y2, y1, z2, z1, x2); /* left */
BoxDesc_XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, y1, y2, z2, z1, x1); /* right */
BoxDesc_YQuad(m, x + sidesW + bodyW + sidesW, y + sidesW, bodyW, bodyH, x1, x2, z1, z2, y2, false); /* top */
BoxDesc_YQuad(m, x + sidesW, y + sidesW, bodyW, bodyH, x2, x1, z1, z2, y1, false); /* bottom */
BoxDesc_ZQuad(m, x + sidesW, y, bodyW, sidesW, x2, x1, y1, y2, z1, false); /* front */
BoxDesc_ZQuad(m, x + sidesW + bodyW, y, bodyW, sidesW, x1, x2, y2, y1, z2, false); /* back */
BoxDesc_XQuad(m, x, y + sidesW, sidesW, bodyH, y2, y1, z2, z1, x2, false); /* left */
BoxDesc_XQuad(m, x + sidesW + bodyW, y + sidesW, sidesW, bodyH, y1, y2, z2, z1, x1, false); /* right */
/* rotate left and right 90 degrees */
Int32 i;
@ -106,26 +106,35 @@ ModelPart BoxDesc_BuildRotatedBox(IModel* m, BoxDesc* desc) {
#define UV_MAX IModel_UVMaxBit
void BoxDesc_XQuad(IModel* m, Int32 texX, Int32 texY, Int32 texWidth, Int32 texHeight,
Real32 z1, Real32 z2, Real32 y1, Real32 y2, Real32 x) {
ModelVertex_Init(&m->vertices[m->index], x, y1, z1, texX, texY + texHeight | UV_MAX); m->index++;
ModelVertex_Init(&m->vertices[m->index], x, y2, z1, texX, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x, y2, z2, texX + texWidth | UV_MAX, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x, y1, z2, texX + texWidth | UV_MAX, texY + texHeight | UV_MAX); m->index++;
Real32 z1, Real32 z2, Real32 y1, Real32 y2, Real32 x, bool swapU) {
Int32 u1 = texX, u2 = texX + texWidth | UV_MAX;
if (swapU) { Int32 tmp = u1; u1 = u2; u2 = tmp; }
ModelVertex_Init(&m->vertices[m->index], x, y1, z1, u1, texY + texHeight | UV_MAX); m->index++;
ModelVertex_Init(&m->vertices[m->index], x, y2, z1, u1, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x, y2, z2, u2, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x, y1, z2, u2, texY + texHeight | UV_MAX); m->index++;
}
void BoxDesc_YQuad(IModel* m, Int32 texX, Int32 texY, Int32 texWidth, Int32 texHeight,
Real32 x1, Real32 x2, Real32 z1, Real32 z2, Real32 y) {
ModelVertex_Init(&m->vertices[m->index], x1, y, z2, texX, texY + texHeight | UV_MAX); m->index++;
ModelVertex_Init(&m->vertices[m->index], x1, y, z1, texX, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y, z1, texX + texWidth | UV_MAX, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y, z2, texX + texWidth | UV_MAX, texY + texHeight | UV_MAX); m->index++;
Real32 x1, Real32 x2, Real32 z1, Real32 z2, Real32 y, bool swapU) {
Int32 u1 = texX, u2 = texX + texWidth | UV_MAX;
if (swapU) { Int32 tmp = u1; u1 = u2; u2 = tmp; }
ModelVertex_Init(&m->vertices[m->index], x1, y, z2, u1, texY + texHeight | UV_MAX); m->index++;
ModelVertex_Init(&m->vertices[m->index], x1, y, z1, u1, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y, z1, u2, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y, z2, u2, texY + texHeight | UV_MAX); m->index++;
}
void BoxDesc_ZQuad(IModel* m, Int32 texX, Int32 texY, Int32 texWidth, Int32 texHeight,
Real32 x1, Real32 x2, Real32 y1, Real32 y2, Real32 z) {
ModelVertex_Init(&m->vertices[m->index], x1, y1, z, texX, texY + texHeight | UV_MAX); m->index++;
ModelVertex_Init(&m->vertices[m->index], x1, y2, z, texX, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y2, z, texX + texWidth | UV_MAX, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y1, z, texX + texWidth | UV_MAX, texY + texHeight | UV_MAX); m->index++;
Real32 x1, Real32 x2, Real32 y1, Real32 y2, Real32 z, bool swapU) {
Int32 u1 = texX, u2 = texX + texWidth | UV_MAX;
if (swapU) { Int32 tmp = u1; u1 = u2; u2 = tmp; }
ModelVertex_Init(&m->vertices[m->index], x1, y1, z, u1, texY + texHeight | UV_MAX); m->index++;
ModelVertex_Init(&m->vertices[m->index], x1, y2, z, u1, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y2, z, u2, texY); m->index++;
ModelVertex_Init(&m->vertices[m->index], x2, y1, z, u2, texY + texHeight | UV_MAX); m->index++;
}
#endif