Beispiel #1
0
        //should be ok.
        public static void WriteDir(sizebuf_t sb, float[] dir)
        {
            int   i, best;
            float d, bestd;

            if (dir == null)
            {
                MSG.WriteByte(sb, 0);

                return;
            }

            bestd = 0;
            best  = 0;

            for (i = 0; i < Defines.NUMVERTEXNORMALS; i++)
            {
                d = Math3D.DotProduct(dir, Globals.bytedirs[i]);

                if (d > bestd)
                {
                    bestd = d;
                    best  = i;
                }
            }

            MSG.WriteByte(sb, best);
        }
Beispiel #2
0
        /*
         * ===============
         * Mod_PointInLeaf
         * ===============
         */
        protected mleaf_t Mod_PointInLeaf(float[] p, model_t model)
        {
            mnode_t  node;
            float    d;
            cplane_t plane;

            if (model == null || model.nodes == null)
            {
                Com.Error(Defines.ERR_DROP, "Mod_PointInLeaf: bad model");
            }

            node = model.nodes[0];             // root node

            while (true)
            {
                if (node.contents != -1)
                {
                    return((mleaf_t)node);
                }

                plane = node.plane;
                d     = Math3D.DotProduct(p, plane.normal) - plane.dist;

                if (d > 0)
                {
                    node = node.children[0];
                }
                else
                {
                    node = node.children[1];
                }
            }

            // never reached
        }
Beispiel #3
0
            public override void Touch(edict_t self, edict_t other, cplane_t plane, csurface_t surf)
            {
                if (other.client != null)
                {
                    if ((self.spawnflags & 2) != 0)
                    {
                        return;
                    }
                }
                else if ((other.svflags & Defines.SVF_MONSTER) != 0)
                {
                    if (0 == (self.spawnflags & 1))
                    {
                        return;
                    }
                }
                else
                {
                    return;
                }
                if (!Math3D.VectorEquals(self.movedir, Globals.vec3_origin))
                {
                    float[] forward = new float[] { 0, 0, 0 };
                    Math3D.AngleVectors(other.s.angles, forward, null, null);
                    if (Math3D.DotProduct(forward, self.movedir) < 0)
                    {
                        return;
                    }
                }

                self.activator = other;
                Multi_trigger(self);
            }
Beispiel #4
0
        public static void WriteDir(sizebuf_t sb, Single[] dir)
        {
            Int32  i, best;
            Single d, bestd;

            if (dir == null)
            {
                WriteByte(sb, 0);
                return;
            }

            bestd = 0;
            best  = 0;
            for (i = 0; i < NUMVERTEXNORMALS; i++)
            {
                d = Math3D.DotProduct(dir, bytedirs[i]);
                if (d > bestd)
                {
                    bestd = d;
                    best  = i;
                }
            }

            WriteByte(sb, best);
        }
Beispiel #5
0
        public override mleaf_t Mod_PointInLeaf(Single[] p, model_t model)
        {
            mnode_t  node;
            Single   d;
            cplane_t plane;

            if (model == null || model.nodes == null)
            {
                Com.Error(Defines.ERR_DROP, "Mod_PointInLeaf: bad model");
            }
            node = model.nodes[0];
            while (true)
            {
                if (node.contents != -1)
                {
                    return(( mleaf_t )node);
                }
                plane = node.plane;
                d     = Math3D.DotProduct(p, plane.normal) - plane.dist;
                if (d > 0)
                {
                    node = node.children[0];
                }
                else
                {
                    node = node.children[1];
                }
            }
        }
Beispiel #6
0
        public static void PM_AirAccelerate(Single[] wishdir, Single wishspeed, Single accel)
        {
            Int32  i;
            Single addspeed, accelspeed, currentspeed, wishspd = wishspeed;

            if (wishspd > 30)
            {
                wishspd = 30;
            }
            currentspeed = Math3D.DotProduct(pml.velocity, wishdir);
            addspeed     = wishspd - currentspeed;
            if (addspeed <= 0)
            {
                return;
            }
            accelspeed = accel * wishspeed * pml.frametime;
            if (accelspeed > addspeed)
            {
                accelspeed = addspeed;
            }
            for (i = 0; i < 3; i++)
            {
                pml.velocity[i] += accelspeed * wishdir[i];
            }
        }
Beispiel #7
0
        public static int ClipVelocity(float[] in_renamed, float[] normal, float[] out_renamed, float overbounce)
        {
            float backoff;
            float change;
            int   i, blocked;

            blocked = 0;
            if (normal[2] > 0)
            {
                blocked |= 1;
            }
            if (normal[2] == 0F)
            {
                blocked |= 2;
            }
            backoff = Math3D.DotProduct(in_renamed, normal) * overbounce;
            for (i = 0; i < 3; i++)
            {
                change         = normal[i] * backoff;
                out_renamed[i] = in_renamed[i] - change;
                if (out_renamed[i] > -STOP_EPSILON && out_renamed[i] < STOP_EPSILON)
                {
                    out_renamed[i] = 0;
                }
            }

            return(blocked);
        }
Beispiel #8
0
        public virtual void R_DrawInlineBModel( )
        {
            if (gl_flashblend.value == 0)
            {
                dlight_t lt;
                for (var k = 0; k < r_newrefdef.num_dlights; k++)
                {
                    lt = r_newrefdef.dlights[k];
                    R_MarkLights(lt, 1 << k, currentmodel.nodes[currentmodel.firstnode]);
                }
            }

            var psurfp = currentmodel.firstmodelsurface;

            msurface_t[] surfaces = currentmodel.surfaces;
            if ((currententity.flags & Defines.RF_TRANSLUCENT) != 0)
            {
                GL.Enable(EnableCap.Blend);
                GL.Color4(1, 1, 1, 0.25F);
                GL_TexEnv(( Int32 )All.Modulate);
            }

            msurface_t psurf;
            cplane_t   pplane;
            Single     dot;

            for (var i = 0; i < currentmodel.nummodelsurfaces; i++)
            {
                psurf  = surfaces[psurfp++];
                pplane = psurf.plane;
                dot    = Math3D.DotProduct(modelorg, pplane.normal) - pplane.dist;
                if (((psurf.flags & Defines.SURF_PLANEBACK) != 0 && (dot < -BACKFACE_EPSILON)) || ((psurf.flags & Defines.SURF_PLANEBACK) == 0 && (dot > BACKFACE_EPSILON)))
                {
                    if ((psurf.texinfo.flags & (Defines.SURF_TRANS33 | Defines.SURF_TRANS66)) != 0)
                    {
                        psurf.texturechain = r_alpha_surfaces;
                        r_alpha_surfaces   = psurf;
                    }
                    else if ((psurf.flags & Defines.SURF_DRAWTURB) == 0)
                    {
                        GL_RenderLightmappedPoly(psurf);
                    }
                    else
                    {
                        GL_EnableMultitexture(false);
                        R_RenderBrushPoly(psurf);
                        GL_EnableMultitexture(true);
                    }
                }
            }

            if ((currententity.flags & Defines.RF_TRANSLUCENT) != 0)
            {
                GL.Disable(EnableCap.Blend);
                GL.Color4(1, 1, 1, 1);
                GL_TexEnv(( Int32 )All.Replace);
            }
        }
Beispiel #9
0
        public virtual void GL_BuildPolygonFromSurface(msurface_t fa)
        {
            Int32 lindex, lnumverts;

            medge_t[] pedges;
            medge_t   r_pedge;

            Single[] vec;
            Single   s, t;
            glpoly_t poly;

            Single[] total = new Single[] { 0, 0, 0 };
            pedges    = currentmodel.edges;
            lnumverts = fa.numedges;
            Math3D.VectorClear(total);
            poly       = Polygon.Create(lnumverts);
            poly.next  = fa.polys;
            poly.flags = fa.flags;
            fa.polys   = poly;
            for (var i = 0; i < lnumverts; i++)
            {
                lindex = currentmodel.surfedges[fa.firstedge + i];
                if (lindex > 0)
                {
                    r_pedge = pedges[lindex];
                    vec     = currentmodel.vertexes[r_pedge.v[0]].position;
                }
                else
                {
                    r_pedge = pedges[-lindex];
                    vec     = currentmodel.vertexes[r_pedge.v[1]].position;
                }

                s  = Math3D.DotProduct(vec, fa.texinfo.vecs[0]) + fa.texinfo.vecs[0][3];
                s /= fa.texinfo.image.width;
                t  = Math3D.DotProduct(vec, fa.texinfo.vecs[1]) + fa.texinfo.vecs[1][3];
                t /= fa.texinfo.image.height;
                Math3D.VectorAdd(total, vec, total);
                poly.X(i, vec[0]);
                poly.Y(i, vec[1]);
                poly.Z(i, vec[2]);
                poly.S1(i, s);
                poly.T1(i, t);
                s  = Math3D.DotProduct(vec, fa.texinfo.vecs[0]) + fa.texinfo.vecs[0][3];
                s -= fa.texturemins[0];
                s += fa.light_s * 16;
                s += 8;
                s /= BLOCK_WIDTH * 16;
                t  = Math3D.DotProduct(vec, fa.texinfo.vecs[1]) + fa.texinfo.vecs[1][3];
                t -= fa.texturemins[1];
                t += fa.light_t * 16;
                t += 8;
                t /= BLOCK_HEIGHT * 16;
                poly.S2(i, s);
                poly.T2(i, t);
            }
        }
Beispiel #10
0
        /*
         * =============================================================================
         *
         * DYNAMIC LIGHTS
         *
         * =============================================================================
         */

        /*
         * ============= R_MarkLights =============
         */
        protected void R_MarkLights(dlight_t light, int bit, mnode_t node)
        {
            cplane_t   splitplane;
            float      dist;
            msurface_t surf;
            int        i;
            int        sidebit;

            if (node.contents != -1)
            {
                return;
            }

            splitplane = node.plane;
            dist       = Math3D.DotProduct(light.origin, splitplane.normal) - splitplane.dist;

            if (dist > light.intensity - OpenGLRenderApi.DLIGHT_CUTOFF)
            {
                this.R_MarkLights(light, bit, node.children[0]);

                return;
            }

            if (dist < -light.intensity + OpenGLRenderApi.DLIGHT_CUTOFF)
            {
                this.R_MarkLights(light, bit, node.children[1]);

                return;
            }

            // mark the polygons
            for (i = 0; i < node.numsurfaces; i++)
            {
                surf = this.r_worldmodel.surfaces[node.firstsurface + i];

                dist    = Math3D.DotProduct(light.origin, surf.plane.normal) - surf.plane.dist;
                sidebit = dist >= 0 ? 0 : Defines.SURF_PLANEBACK;

                if ((surf.flags & Defines.SURF_PLANEBACK) != sidebit)
                {
                    continue;
                }

                if (surf.dlightframe != this.r_dlightframecount)
                {
                    surf.dlightbits  = 0;
                    surf.dlightframe = this.r_dlightframecount;
                }

                surf.dlightbits |= bit;
            }

            this.R_MarkLights(light, bit, node.children[0]);
            this.R_MarkLights(light, bit, node.children[1]);
        }
Beispiel #11
0
 public virtual void R_SetFrustum( )
 {
     Math3D.RotatePointAroundVector(frustum[0].normal, vup, vpn, -(90F - r_newrefdef.fov_x / 2F));
     Math3D.RotatePointAroundVector(frustum[1].normal, vup, vpn, 90F - r_newrefdef.fov_x / 2F);
     Math3D.RotatePointAroundVector(frustum[2].normal, vright, vpn, 90F - r_newrefdef.fov_y / 2F);
     Math3D.RotatePointAroundVector(frustum[3].normal, vright, vpn, -(90F - r_newrefdef.fov_y / 2F));
     for (var i = 0; i < 4; i++)
     {
         frustum[i].type     = Defines.PLANE_ANYZ;
         frustum[i].dist     = Math3D.DotProduct(r_origin, frustum[i].normal);
         frustum[i].signbits = ( Byte )SignbitsForPlane(frustum[i]);
     }
 }
Beispiel #12
0
        /*
         * =============== CL_TrackerTrail ===============
         */
        public static void TrackerTrail(float[] start, float[] end, int particleColor)
        {
            float       len;
            cparticle_t p;
            int         dec;
            float       dist;

            Math3D.VectorCopy(start, CL_newfx.move);
            Math3D.VectorSubtract(end, start, CL_newfx.vec);
            len = Math3D.VectorNormalize(CL_newfx.vec);
            Math3D.VectorCopy(CL_newfx.vec, CL_newfx.forward);
            Math3D.vectoangles(CL_newfx.forward, CL_newfx.angle_dir);
            Math3D.AngleVectors(CL_newfx.angle_dir, CL_newfx.forward, CL_newfx.right, CL_newfx.up);
            dec = 3;
            Math3D.VectorScale(CL_newfx.vec, 3, CL_newfx.vec);

            // FIXME: this is a really silly way to have a loop
            while (len > 0)
            {
                len -= dec;

                if (CL_fx.free_particles == null)
                {
                    return;
                }

                p = CL_fx.free_particles;
                CL_fx.free_particles = p.next;
                p.next = CL_fx.active_particles;
                CL_fx.active_particles = p;
                Math3D.VectorClear(p.accel);
                p.time     = Globals.cl.time;
                p.alpha    = 1.0f;
                p.alphavel = -2.0f;
                p.color    = particleColor;
                dist       = Math3D.DotProduct(CL_newfx.move, CL_newfx.forward);
                Math3D.VectorMA(CL_newfx.move, (float)(8 * Math.Cos(dist)), CL_newfx.up, p.org);

                for (var j = 0; j < 3; j++)
                {
                    p.vel[j]   = 0;
                    p.accel[j] = 0;
                }

                p.vel[2] = 5;
                Math3D.VectorAdd(CL_newfx.move, CL_newfx.vec, CL_newfx.move);
            }
        }
Beispiel #13
0
        public static bool Infront(edict_t self, edict_t other)
        {
            float[] vec = new float[] { 0, 0, 0 };
            float   dot;

            float[] forward = new float[] { 0, 0, 0 };
            Math3D.AngleVectors(self.s.angles, forward, null, null);
            Math3D.VectorSubtract(other.s.origin, self.s.origin, vec);
            Math3D.VectorNormalize(vec);
            dot = Math3D.DotProduct(vec, forward);
            if (dot > 0.3)
            {
                return(true);
            }
            return(false);
        }
Beispiel #14
0
        public override void R_MarkLights(dlight_t light, Int32 bit, mnode_t node)
        {
            cplane_t   splitplane;
            Single     dist;
            msurface_t surf;
            Int32      i;
            Int32      sidebit;

            if (node.contents != -1)
            {
                return;
            }
            splitplane = node.plane;
            dist       = Math3D.DotProduct(light.origin, splitplane.normal) - splitplane.dist;
            if (dist > light.intensity - DLIGHT_CUTOFF)
            {
                R_MarkLights(light, bit, node.children[0]);
                return;
            }

            if (dist < -light.intensity + DLIGHT_CUTOFF)
            {
                R_MarkLights(light, bit, node.children[1]);
                return;
            }

            for (i = 0; i < node.numsurfaces; i++)
            {
                surf    = r_worldmodel.surfaces[node.firstsurface + i];
                dist    = Math3D.DotProduct(light.origin, surf.plane.normal) - surf.plane.dist;
                sidebit = (dist >= 0) ? 0 : Defines.SURF_PLANEBACK;
                if ((surf.flags & Defines.SURF_PLANEBACK) != sidebit)
                {
                    continue;
                }
                if (surf.dlightframe != r_dlightframecount)
                {
                    surf.dlightbits  = 0;
                    surf.dlightframe = r_dlightframecount;
                }

                surf.dlightbits |= bit;
            }

            R_MarkLights(light, bit, node.children[0]);
            R_MarkLights(light, bit, node.children[1]);
        }
Beispiel #15
0
        static void SpatializeOrigin(Single[] origin, Single master_vol, Single dist_mult, channel_t ch)
        {
            Single dot;
            Single dist;
            Single lscale, rscale, scale;

            Single[] source_vec = new Single[] { 0, 0, 0 };
            if (cls.state != ca_active)
            {
                ch.leftvol = ch.rightvol = 255;
                return;
            }

            Math3D.VectorSubtract(origin, listener_origin, source_vec);
            dist  = Math3D.VectorNormalize(source_vec);
            dist -= SOUND_FULLVOLUME;
            if (dist < 0)
            {
                dist = 0;
            }
            dist *= dist_mult;
            dot   = Math3D.DotProduct(listener_right, source_vec);
            if (dma.channels == 1 || dist_mult == 0F)
            {
                rscale = 1F;
                lscale = 1F;
            }
            else
            {
                rscale = 0.5F * (1F + dot);
                lscale = 0.5F * (1F - dot);
            }

            scale       = (1F - dist) * rscale;
            ch.rightvol = ( Int32 )(master_vol * scale);
            if (ch.rightvol < 0)
            {
                ch.rightvol = 0;
            }
            scale      = (1F - dist) * lscale;
            ch.leftvol = ( Int32 )(master_vol * scale);
            if (ch.leftvol < 0)
            {
                ch.leftvol = 0;
            }
        }
Beispiel #16
0
        public static void PM_ClipVelocity(Single[] in_renamed, Single[] normal, Single[] out_renamed, Single overbounce)
        {
            Single backoff;
            Single change;
            Int32  i;

            backoff = Math3D.DotProduct(in_renamed, normal) * overbounce;
            for (i = 0; i < 3; i++)
            {
                change         = normal[i] * backoff;
                out_renamed[i] = in_renamed[i] - change;
                if (out_renamed[i] > -Defines.MOVE_STOP_EPSILON && out_renamed[i] < Defines.MOVE_STOP_EPSILON)
                {
                    out_renamed[i] = 0;
                }
            }
        }
Beispiel #17
0
        public static void TrackerTrail(float[] start, float[] end, int particleColor)
        {
            float       len;
            cparticle_t p;
            int         dec;
            float       dist;

            Math3D.VectorCopy(start, move);
            Math3D.VectorSubtract(end, start, vec);
            len = Math3D.VectorNormalize(vec);
            Math3D.VectorCopy(vec, forward);
            Math3D.Vectoangles(forward, angle_dir);
            Math3D.AngleVectors(angle_dir, forward, right, up);
            dec = 3;
            Math3D.VectorScale(vec, 3, vec);
            while (len > 0)
            {
                len -= dec;
                if (CL_fx.free_particles == null)
                {
                    return;
                }
                p = CL_fx.free_particles;
                CL_fx.free_particles = p.next;
                p.next = CL_fx.active_particles;
                CL_fx.active_particles = p;
                Math3D.VectorClear(p.accel);
                p.time     = Globals.cl.time;
                p.alpha    = 1F;
                p.alphavel = -2F;
                p.color    = particleColor;
                dist       = Math3D.DotProduct(move, forward);
                Math3D.VectorMA(move, (float)(8 * Math.Cos(dist)), up, p.org);
                for (int j = 0; j < 3; j++)
                {
                    p.vel[j]   = 0;
                    p.accel[j] = 0;
                }

                p.vel[2] = 5;
                Math3D.VectorAdd(move, vec, move);
            }
        }
Beispiel #18
0
        public static float SV_CalcRoll(float[] angles, float[] velocity)
        {
            float sign;
            float side;
            float value;

            side  = Math3D.DotProduct(velocity, right);
            sign  = side < 0 ? -1 : 1;
            side  = Math.Abs(side);
            value = GameBase.sv_rollangle.value;
            if (side < GameBase.sv_rollspeed.value)
            {
                side = side * value / GameBase.sv_rollspeed.value;
            }
            else
            {
                side = value;
            }
            return(side * sign);
        }
        public void WriteDir(float[] dir)
        {
            if (dir == null)
            {
                WriteByte(0);
                return;
            }
            float bestd = 0;
            byte  best  = 0;

            for (byte index = 0; index < Math3D.VertexNormals.Length; index++)
            {
                float d = Math3D.DotProduct(dir, Math3D.VertexNormals[index]);
                if (d > bestd)
                {
                    bestd = d;
                    best  = index;
                }
            }
            WriteByte(best);
        }
Beispiel #20
0
        public override void R_DrawBrushModel(entity_t e)
        {
            if (currentmodel.nummodelsurfaces == 0)
            {
                return;
            }
            currententity = e;
            gl_state.currenttextures[0] = gl_state.currenttextures[1] = -1;
            System.Boolean rotated;
            if (e.angles[0] != 0 || e.angles[1] != 0 || e.angles[2] != 0)
            {
                rotated = true;
                for (var i = 0; i < 3; i++)
                {
                    mins[i] = e.origin[i] - currentmodel.radius;
                    maxs[i] = e.origin[i] + currentmodel.radius;
                }
            }
            else
            {
                rotated = false;
                Math3D.VectorAdd(e.origin, currentmodel.mins, mins);
                Math3D.VectorAdd(e.origin, currentmodel.maxs, maxs);
            }

            if (R_CullBox(mins, maxs))
            {
                return;
            }
            GL.Color3(1, 1, 1);
            Math3D.VectorSubtract(r_newrefdef.vieworg, e.origin, modelorg);
            if (rotated)
            {
                Math3D.VectorCopy(modelorg, org);
                Math3D.AngleVectors(e.angles, forward, right, up);
                modelorg[0] = Math3D.DotProduct(org, forward);
                modelorg[1] = -Math3D.DotProduct(org, right);
                modelorg[2] = Math3D.DotProduct(org, up);
            }

            GL.PushMatrix();
            e.angles[0] = -e.angles[0];
            e.angles[2] = -e.angles[2];
            R_RotateForEntity(e);
            e.angles[0] = -e.angles[0];
            e.angles[2] = -e.angles[2];
            GL_EnableMultitexture(true);
            GL_SelectTexture(TextureUnit.Texture0);
            GL_TexEnv(( Int32 )All.Replace);
            GL.InterleavedArrays(InterleavedArrayFormat.T2fV3f, glpoly_t.BYTE_STRIDE, globalPolygonInterleavedBuf.Array);
            GL_SelectTexture(TextureUnit.Texture1);
            GL_TexEnv(( Int32 )All.Modulate);

            new Pinnable(globalPolygonTexCoord1Buf, (ptr) =>
            {
                GL.TexCoordPointer(2, TexCoordPointerType.Float, glpoly_t.BYTE_STRIDE, ptr);
            });
            GL.EnableClientState(ArrayCap.TextureCoordArray);
            R_DrawInlineBModel();
            GL.ClientActiveTexture(TextureUnit.Texture1);
            GL.DisableClientState(ArrayCap.TextureCoordArray);
            GL_EnableMultitexture(false);
            GL.PopMatrix();
        }
Beispiel #21
0
        public static void PM_FlyMove(Boolean doclip)
        {
            Single speed, drop, friction, control, newspeed;
            Single currentspeed, addspeed, accelspeed;
            Int32  i;

            Single[] wishvel = new Single[] { 0, 0, 0 };
            Single   fmove, smove;

            Single[] wishdir = new Single[] { 0, 0, 0 };
            Single   wishspeed;

            Single[] end = new Single[] { 0, 0, 0 };
            trace_t  trace;

            pm.viewheight = 22;
            speed         = Math3D.VectorLength(pml.velocity);
            if (speed < 1)
            {
                Math3D.VectorCopy(Globals.vec3_origin, pml.velocity);
            }
            else
            {
                drop     = 0;
                friction = pm_friction * 1.5F;
                control  = speed < pm_stopspeed ? pm_stopspeed : speed;
                drop    += control * friction * pml.frametime;
                newspeed = speed - drop;
                if (newspeed < 0)
                {
                    newspeed = 0;
                }
                newspeed /= speed;
                Math3D.VectorScale(pml.velocity, newspeed, pml.velocity);
            }

            fmove = pm.cmd.forwardmove;
            smove = pm.cmd.sidemove;
            Math3D.VectorNormalize(pml.forward);
            Math3D.VectorNormalize(pml.right);
            for (i = 0; i < 3; i++)
            {
                wishvel[i] = pml.forward[i] * fmove + pml.right[i] * smove;
            }
            wishvel[2] += pm.cmd.upmove;
            Math3D.VectorCopy(wishvel, wishdir);
            wishspeed = Math3D.VectorNormalize(wishdir);
            if (wishspeed > pm_maxspeed)
            {
                Math3D.VectorScale(wishvel, pm_maxspeed / wishspeed, wishvel);
                wishspeed = pm_maxspeed;
            }

            currentspeed = Math3D.DotProduct(pml.velocity, wishdir);
            addspeed     = wishspeed - currentspeed;
            if (addspeed <= 0)
            {
                return;
            }
            accelspeed = pm_accelerate * pml.frametime * wishspeed;
            if (accelspeed > addspeed)
            {
                accelspeed = addspeed;
            }
            for (i = 0; i < 3; i++)
            {
                pml.velocity[i] += accelspeed * wishdir[i];
            }
            if (doclip)
            {
                for (i = 0; i < 3; i++)
                {
                    end[i] = pml.origin[i] + pml.frametime * pml.velocity[i];
                }
                trace = pm.trace.Trace(pml.origin, pm.mins, pm.maxs, end);
                Math3D.VectorCopy(trace.endpos, pml.origin);
            }
            else
            {
                Math3D.VectorMA(pml.origin, pml.frametime, pml.velocity, pml.origin);
            }
        }
Beispiel #22
0
        public static void PM_StepSlideMove_( )
        {
            Int32 bumpcount, numbumps;

            Single[] dir = new Single[] { 0, 0, 0 };
            Single   d;
            Int32    numplanes;

            Single[] primal_velocity = new Single[] { 0, 0, 0 };
            Int32    i, j;
            trace_t  trace;

            Single[] end = new Single[] { 0, 0, 0 };
            Single   time_left;

            numbumps = 4;
            Math3D.VectorCopy(pml.velocity, primal_velocity);
            numplanes = 0;
            time_left = pml.frametime;
            for (bumpcount = 0; bumpcount < numbumps; bumpcount++)
            {
                for (i = 0; i < 3; i++)
                {
                    end[i] = pml.origin[i] + time_left * pml.velocity[i];
                }
                trace = pm.trace.Trace(pml.origin, pm.mins, pm.maxs, end);
                if (trace.allsolid)
                {
                    pml.velocity[2] = 0;
                    return;
                }

                if (trace.fraction > 0)
                {
                    Math3D.VectorCopy(trace.endpos, pml.origin);
                    numplanes = 0;
                }

                if (trace.fraction == 1)
                {
                    break;
                }
                if (pm.numtouch < Defines.MAXTOUCH && trace.ent != null)
                {
                    pm.touchents[pm.numtouch] = trace.ent;
                    pm.numtouch++;
                }

                time_left -= time_left * trace.fraction;
                if (numplanes >= SV.MAX_CLIP_PLANES)
                {
                    Math3D.VectorCopy(Globals.vec3_origin, pml.velocity);
                    break;
                }

                Math3D.VectorCopy(trace.plane.normal, planes[numplanes]);
                numplanes++;
                for (i = 0; i < numplanes; i++)
                {
                    PM_ClipVelocity(pml.velocity, planes[i], pml.velocity, 1.01F);
                    for (j = 0; j < numplanes; j++)
                    {
                        if (j != i)
                        {
                            if (Math3D.DotProduct(pml.velocity, planes[j]) < 0)
                            {
                                break;
                            }
                        }
                    }

                    if (j == numplanes)
                    {
                        break;
                    }
                }

                if (i != numplanes)
                {
                }
                else
                {
                    if (numplanes != 2)
                    {
                        Math3D.VectorCopy(Globals.vec3_origin, pml.velocity);
                        break;
                    }

                    Math3D.CrossProduct(planes[0], planes[1], dir);
                    d = Math3D.DotProduct(dir, pml.velocity);
                    Math3D.VectorScale(dir, d, pml.velocity);
                }

                if (Math3D.DotProduct(pml.velocity, primal_velocity) <= 0)
                {
                    Math3D.VectorCopy(Globals.vec3_origin, pml.velocity);
                    break;
                }
            }

            if (pm.s.pm_time != 0)
            {
                Math3D.VectorCopy(primal_velocity, pml.velocity);
            }
        }
Beispiel #23
0
        public virtual System.Boolean R_CullAliasModel(Single[][] bbox, entity_t e)
        {
            Int32 i;

            Single[]             mins = new Single[] { 0, 0, 0 };
            Single[]             maxs = new Single[] { 0, 0, 0 };
            qfiles.dmdl_t        paliashdr;
            Single[][]           vectors = new Single[][] { new Single[] { 0, 0, 0 }, new Single[] { 0, 0, 0 }, new Single[] { 0, 0, 0 } };
            Single[]             thismins = new Single[] { 0, 0, 0 };
            Single[]             oldmins = new Single[] { 0, 0, 0 };
            Single[]             thismaxs = new Single[] { 0, 0, 0 };
            Single[]             oldmaxs = new Single[] { 0, 0, 0 };
            qfiles.daliasframe_t pframe, poldframe;
            Single[]             angles = new Single[] { 0, 0, 0 };
            paliashdr = (qfiles.dmdl_t)currentmodel.extradata;
            if ((e.frame >= paliashdr.num_frames) || (e.frame < 0))
            {
                VID.Printf(Defines.PRINT_ALL, "R_CullAliasModel " + currentmodel.name + ": no such frame " + e.frame + '\\');
                e.frame = 0;
            }

            if ((e.oldframe >= paliashdr.num_frames) || (e.oldframe < 0))
            {
                VID.Printf(Defines.PRINT_ALL, "R_CullAliasModel " + currentmodel.name + ": no such oldframe " + e.oldframe + '\\');
                e.oldframe = 0;
            }

            pframe    = paliashdr.aliasFrames[e.frame];
            poldframe = paliashdr.aliasFrames[e.oldframe];
            if (pframe == poldframe)
            {
                for (i = 0; i < 3; i++)
                {
                    mins[i] = pframe.translate[i];
                    maxs[i] = mins[i] + pframe.scale[i] * 255;
                }
            }
            else
            {
                for (i = 0; i < 3; i++)
                {
                    thismins[i] = pframe.translate[i];
                    thismaxs[i] = thismins[i] + pframe.scale[i] * 255;
                    oldmins[i]  = poldframe.translate[i];
                    oldmaxs[i]  = oldmins[i] + poldframe.scale[i] * 255;
                    if (thismins[i] < oldmins[i])
                    {
                        mins[i] = thismins[i];
                    }
                    else
                    {
                        mins[i] = oldmins[i];
                    }
                    if (thismaxs[i] > oldmaxs[i])
                    {
                        maxs[i] = thismaxs[i];
                    }
                    else
                    {
                        maxs[i] = oldmaxs[i];
                    }
                }
            }

            for (i = 0; i < 8; i++)
            {
                Single[] tmp = new Single[] { 0, 0, 0 };
                if ((i & 1) != 0)
                {
                    tmp[0] = mins[0];
                }
                else
                {
                    tmp[0] = maxs[0];
                }
                if ((i & 2) != 0)
                {
                    tmp[1] = mins[1];
                }
                else
                {
                    tmp[1] = maxs[1];
                }
                if ((i & 4) != 0)
                {
                    tmp[2] = mins[2];
                }
                else
                {
                    tmp[2] = maxs[2];
                }
                Math3D.VectorCopy(tmp, bbox[i]);
            }

            Math3D.VectorCopy(e.angles, angles);
            angles[YAW] = -angles[YAW];
            Math3D.AngleVectors(angles, vectors[0], vectors[1], vectors[2]);
            for (i = 0; i < 8; i++)
            {
                Single[] tmp = new Single[] { 0, 0, 0 };
                Math3D.VectorCopy(bbox[i], tmp);
                bbox[i][0] = Math3D.DotProduct(vectors[0], tmp);
                bbox[i][1] = -Math3D.DotProduct(vectors[1], tmp);
                bbox[i][2] = Math3D.DotProduct(vectors[2], tmp);
                Math3D.VectorAdd(e.origin, bbox[i], bbox[i]);
            }

            {
                Int32 p, f;
                var   aggregatemask = ~0;
                for (p = 0; p < 8; p++)
                {
                    var mask = 0;
                    for (f = 0; f < 4; f++)
                    {
                        var dp = Math3D.DotProduct(frustum[f].normal, bbox[p]);
                        if ((dp - frustum[f].dist) < 0)
                        {
                            mask |= (1 << f);
                        }
                    }

                    aggregatemask &= mask;
                }

                if (aggregatemask != 0)
                {
                    return(true);
                }

                return(false);
            }
        }
Beispiel #24
0
        public void ComputeVertex(VertexInput v1)
        {
            #region Завернуть в шейдер

            var worldCoord1 = _modelMatrix * v1.Position;

            var vector1 = _transformMatrix * worldCoord1;
            //var vector2 = _transformMatrix * worldCoord2;
            //var vector3 = _transformMatrix * worldCoord3;

            var decartvector1 = Math3D.ConvertToDecart(vector1);
            //var decartvector2 = Math3D.ConvertToDecart(vector2);
            //var decartvector3 = Math3D.ConvertToDecart(vector3);

            //Vector3f faceNormalInWorldCoord = Math3D.CalculateNormal(Math3D.ConvertToDecart(worldCoord1), Math3D.ConvertToDecart(worldCoord2), Math3D.ConvertToDecart(worldCoord3));

            Vector3f faceNormalInProjectionCoord = SimpleRender.Math.Vector3f.CrossProductLeft((decartvector3 - decartvector1), (decartvector2 - decartvector1));
            faceNormalInProjectionCoord = faceNormalInProjectionCoord.Normalize();
            var    viewDirection = new Vector4(0, 0, -1, 1);
            double intensity     = Math3D.DotProduct(faceNormalInProjectionCoord, viewDirection);

            //TODO Подумать нужноли это в шейдере
            if (intensity <= 0)
            {
                continue;
            }

            //ambient = Ka,
            //diffuse = Kd * cos(N, L),
            //specular = Ks * pow(cos(R, V), Ns),
            //intensity = ambient + amp * (diffuse + specular).

            //-----------------
            //http://www.gamedev.ru/code/articles/HLSL?page=4
            //Lighting:
            //Lambert (ambient lighting)
            //Diffuse (diffuse lighting model)
            //Phong (specular lighting model), Blinn (blinn specular lighting model)
            //Sum of this

            //Реалистичное освещение на основе Кука-Торренса

            //-------------

            var ligthSource         = scene.LightSources.First();
            var globalLightPosition = ligthSource.Position.Normalize();

            double illuminationIntensity = Math3D.DotProduct(faceNormalInWorldCoord, globalLightPosition);
            var    diffuseColor          = new Vector4(
                _material.DiffuseColor.X * ligthSource.Color.X,
                _material.Mategial.DiffuseColor.Y * ligthSource.Color.Y,
                _material.Mategial.DiffuseColor.Z * ligthSource.Color.Z,
                1)
                                           * illuminationIntensity;

            //var reflection = (Vector3f.CrossProductLeft(faceNormalInWorldCoord ,
            //    (Vector3f.CrossProductLeft(faceNormalInWorldCoord ,globalLightPosition) * 2.0f)) -
            //    globalLightPosition).Normalize();   // reflected light

            var sampleColor = _ambientColor + diffuseColor * ligthSource.Intensity;

            #endregion
        }
Beispiel #25
0
        /*
         * ===============
         * P_DamageFeedback
         *
         * Handles color blends and view kicks
         * ===============
         */

        public static void P_DamageFeedback(edict_t player)
        {
            gclient_t client;
            float     side;
            float     realcount, count, kick;

            float[] v = { 0, 0, 0 };
            int     r, l;

            float[] power_color = { 0.0f, 1.0f, 0.0f };
            float[] acolor      = { 1.0f, 1.0f, 1.0f };
            float[] bcolor      = { 1.0f, 0.0f, 0.0f };

            client = player.client;

            // flash the backgrounds behind the status numbers
            client.ps.stats[Defines.STAT_FLASHES] = 0;

            if (client.damage_blood != 0)
            {
                client.ps.stats[Defines.STAT_FLASHES] |= 1;
            }

            if (client.damage_armor != 0 && 0 == (player.flags & Defines.FL_GODMODE) && client.invincible_framenum <= GameBase.level.framenum)
            {
                client.ps.stats[Defines.STAT_FLASHES] |= 2;
            }

            // total points of damage shot at the player this frame
            count = client.damage_blood + client.damage_armor + client.damage_parmor;

            if (count == 0)
            {
                return;                 // didn't take any damage
            }
            // start a pain animation if still in the player model
            if ((client.anim_priority < Defines.ANIM_PAIN) & (player.s.modelindex == 255))
            {
                client.anim_priority = Defines.ANIM_PAIN;

                if ((client.ps.pmove.pm_flags & pmove_t.PMF_DUCKED) != 0)
                {
                    player.s.frame  = M_Player.FRAME_crpain1 - 1;
                    client.anim_end = M_Player.FRAME_crpain4;
                }
                else
                {
                    PlayerView.xxxi = (PlayerView.xxxi + 1) % 3;

                    switch (PlayerView.xxxi)
                    {
                    case 0:
                        player.s.frame  = M_Player.FRAME_pain101 - 1;
                        client.anim_end = M_Player.FRAME_pain104;

                        break;

                    case 1:
                        player.s.frame  = M_Player.FRAME_pain201 - 1;
                        client.anim_end = M_Player.FRAME_pain204;

                        break;

                    case 2:
                        player.s.frame  = M_Player.FRAME_pain301 - 1;
                        client.anim_end = M_Player.FRAME_pain304;

                        break;
                    }
                }
            }

            realcount = count;

            if (count < 10)
            {
                count = 10;                 // always make a visible effect
            }
            // play an apropriate pain sound
            if (GameBase.level.time > player.pain_debounce_time &&
                0 == (player.flags & Defines.FL_GODMODE) &&
                client.invincible_framenum <= GameBase.level.framenum)
            {
                r = 1 + (Lib.rand() & 1);
                player.pain_debounce_time = GameBase.level.time + 0.7f;

                if (player.health < 25)
                {
                    l = 25;
                }
                else if (player.health < 50)
                {
                    l = 50;
                }
                else if (player.health < 75)
                {
                    l = 75;
                }
                else
                {
                    l = 100;
                }

                GameBase.gi.sound(player, Defines.CHAN_VOICE, GameBase.gi.soundindex("*pain" + l + "_" + r + ".wav"), 1, Defines.ATTN_NORM, 0);
            }

            // the total alpha of the blend is always proportional to count
            if (client.damage_alpha < 0)
            {
                client.damage_alpha = 0;
            }

            client.damage_alpha += count * 0.01f;

            if (client.damage_alpha < 0.2f)
            {
                client.damage_alpha = 0.2f;
            }

            if (client.damage_alpha > 0.6f)
            {
                client.damage_alpha = 0.6f;                 // don't go too saturated
            }
            // the color of the blend will vary based on how much was absorbed
            // by different armors
            //

            Math3D.VectorClear(v);

            if (client.damage_parmor != 0)
            {
                Math3D.VectorMA(v, (float)client.damage_parmor / realcount, power_color, v);
            }

            if (client.damage_armor != 0)
            {
                Math3D.VectorMA(v, (float)client.damage_armor / realcount, acolor, v);
            }

            if (client.damage_blood != 0)
            {
                Math3D.VectorMA(v, (float)client.damage_blood / realcount, bcolor, v);
            }

            Math3D.VectorCopy(v, client.damage_blend);

            //
            // calculate view angle kicks
            //
            kick = Math.Abs(client.damage_knockback);

            if (kick != 0 && player.health > 0)             // kick of 0 means no view adjust at
            // all
            {
                kick = kick * 100 / player.health;

                if (kick < count * 0.5)
                {
                    kick = count * 0.5f;
                }

                if (kick > 50)
                {
                    kick = 50;
                }

                Math3D.VectorSubtract(client.damage_from, player.s.origin, v);
                Math3D.VectorNormalize(v);

                side = Math3D.DotProduct(v, PlayerView.right);
                client.v_dmg_roll = kick * side * 0.3f;

                side = -Math3D.DotProduct(v, PlayerView.forward);
                client.v_dmg_pitch = kick * side * 0.3f;

                client.v_dmg_time = GameBase.level.time + Defines.DAMAGE_TIME;
            }

            //
            // clear totals
            //
            client.damage_blood     = 0;
            client.damage_armor     = 0;
            client.damage_parmor    = 0;
            client.damage_knockback = 0;
        }
Beispiel #26
0
        public virtual void R_RecursiveWorldNode(mnode_t node)
        {
            if (node.contents == Defines.CONTENTS_SOLID)
            {
                return;
            }
            if (node.visframe != r_visframecount)
            {
                return;
            }
            if (R_CullBox(node.mins, node.maxs))
            {
                return;
            }
            Int32      c;
            msurface_t mark;

            if (node.contents != -1)
            {
                mleaf_t pleaf = ( mleaf_t )node;
                if (r_newrefdef.areabits != null)
                {
                    if (((r_newrefdef.areabits[pleaf.area >> 3] & 0xFF) & (1 << (pleaf.area & 7))) == 0)
                    {
                        return;
                    }
                }

                var markp = 0;
                mark = pleaf.GetMarkSurface(markp);
                c    = pleaf.nummarksurfaces;
                if (c != 0)
                {
                    do
                    {
                        mark.visframe = r_framecount;
                        mark          = pleaf.GetMarkSurface(++markp);
                    }while (--c != 0);
                }

                return;
            }

            cplane_t plane = node.plane;
            Single   dot;

            switch (plane.type)

            {
            case Defines.PLANE_X:
                dot = modelorg[0] - plane.dist;
                break;

            case Defines.PLANE_Y:
                dot = modelorg[1] - plane.dist;
                break;

            case Defines.PLANE_Z:
                dot = modelorg[2] - plane.dist;
                break;

            default:
                dot = Math3D.DotProduct(modelorg, plane.normal) - plane.dist;
                break;
            }

            Int32 side, sidebit;

            if (dot >= 0F)
            {
                side    = 0;
                sidebit = 0;
            }
            else
            {
                side    = 1;
                sidebit = Defines.SURF_PLANEBACK;
            }

            R_RecursiveWorldNode(node.children[side]);
            msurface_t surf;
            image_t    image;

            for (c = 0; c < node.numsurfaces; c++)
            {
                surf = r_worldmodel.surfaces[node.firstsurface + c];
                if (surf.visframe != r_framecount)
                {
                    continue;
                }
                if ((surf.flags & Defines.SURF_PLANEBACK) != sidebit)
                {
                    continue;
                }
                if ((surf.texinfo.flags & Defines.SURF_SKY) != 0)
                {
                    R_AddSkySurface(surf);
                }
                else if ((surf.texinfo.flags & (Defines.SURF_TRANS33 | Defines.SURF_TRANS66)) != 0)
                {
                    surf.texturechain = r_alpha_surfaces;
                    r_alpha_surfaces  = surf;
                }
                else
                {
                    if ((surf.flags & Defines.SURF_DRAWTURB) == 0)
                    {
                        GL_RenderLightmappedPoly(surf);
                    }
                    else
                    {
                        image              = R_TextureAnimation(surf.texinfo);
                        surf.texturechain  = image.texturechain;
                        image.texturechain = surf;
                    }
                }
            }

            R_RecursiveWorldNode(node.children[1 - side]);
        }
Beispiel #27
0
        public virtual void SubdividePolygon(int numverts, float[][] verts)
        {
            int i, j, k;

            float[] mins = new float[] { 0, 0, 0 };
            float[] maxs = new float[] { 0, 0, 0 };
            float   m;

            float[]   v = new float[] { 0, 0, 0 };
            float[][] front = Lib.CreateJaggedArray <float[][]>(64, 3);
            float[][] back = Lib.CreateJaggedArray <float[][]>(64, 3);
            int       f, b;

            float[] dist = new float[64];
            float   frac;
            float   s, t;

            float[] total = new float[] { 0, 0, 0 };
            float   total_s, total_t;

            if (numverts > 60)
            {
                Com.Error(Defines.ERR_DROP, "numverts = " + numverts);
            }
            BoundPoly(numverts, verts, mins, maxs);
            for (i = 0; i < 3; i++)
            {
                m = (mins[i] + maxs[i]) * 0.5F;
                m = SUBDIVIDE_SIZE * (float)Math.Floor(m / SUBDIVIDE_SIZE + 0.5F);
                if (maxs[i] - m < 8)
                {
                    continue;
                }
                if (m - mins[i] < 8)
                {
                    continue;
                }
                for (j = 0; j < numverts; j++)
                {
                    dist[j] = verts[j][i] - m;
                }

                dist[j] = dist[0];
                Math3D.VectorCopy(verts[0], verts[numverts]);
                f = b = 0;
                for (j = 0; j < numverts; j++)
                {
                    v = verts[j];
                    if (dist[j] >= 0)
                    {
                        Math3D.VectorCopy(v, front[f]);
                        f++;
                    }

                    if (dist[j] <= 0)
                    {
                        Math3D.VectorCopy(v, back[b]);
                        b++;
                    }

                    if (dist[j] == 0 || dist[j + 1] == 0)
                    {
                        continue;
                    }
                    if ((dist[j] > 0) != (dist[j + 1] > 0))
                    {
                        frac = dist[j] / (dist[j] - dist[j + 1]);
                        for (k = 0; k < 3; k++)
                        {
                            front[f][k] = back[b][k] = v[k] + frac * (verts[j + 1][k] - v[k]);
                        }
                        f++;
                        b++;
                    }
                }

                SubdividePolygon(f, front);
                SubdividePolygon(b, back);
                return;
            }

            glpoly_t poly = Polygon.Create(numverts + 2);

            poly.next      = warpface.polys;
            warpface.polys = poly;
            Math3D.VectorClear(total);
            total_s = 0;
            total_t = 0;
            for (i = 0; i < numverts; i++)
            {
                poly.X(i + 1, verts[i][0]);
                poly.Y(i + 1, verts[i][1]);
                poly.Z(i + 1, verts[i][2]);
                s        = Math3D.DotProduct(verts[i], warpface.texinfo.vecs[0]);
                t        = Math3D.DotProduct(verts[i], warpface.texinfo.vecs[1]);
                total_s += s;
                total_t += t;
                Math3D.VectorAdd(total, verts[i], total);
                poly.S1(i + 1, s);
                poly.T1(i + 1, t);
            }

            float scale = 1F / numverts;

            poly.X(0, total[0] * scale);
            poly.Y(0, total[1] * scale);
            poly.Z(0, total[2] * scale);
            poly.S1(0, total_s * scale);
            poly.T1(0, total_t * scale);
            poly.X(i + 1, poly.X(1));
            poly.Y(i + 1, poly.Y(1));
            poly.Z(i + 1, poly.Z(1));
            poly.S1(i + 1, poly.S1(1));
            poly.T1(i + 1, poly.T1(1));
            poly.S2(i + 1, poly.S2(1));
            poly.T2(i + 1, poly.T2(1));
        }
Beispiel #28
0
        public virtual void ClipSkyPolygon(int nump, float[][] vecs, int stage)
        {
            float[] norm;
            float[] v;
            bool    front, back;
            float   d, e;

            int[] newc = new[] { 0, 0 };
            int   i, j;

            if (nump > MAX_CLIP_VERTS - 2)
            {
                Com.Error(Defines.ERR_DROP, "ClipSkyPolygon: MAX_CLIP_VERTS");
            }
            if (stage == 6)
            {
                DrawSkyPolygon(nump, vecs);
                return;
            }

            front = back = false;
            norm  = skyclip[stage];
            for (i = 0; i < nump; i++)
            {
                d = Math3D.DotProduct(vecs[i], norm);
                if (d > ON_EPSILON)
                {
                    front    = true;
                    sides[i] = SIDE_FRONT;
                }
                else if (d < -ON_EPSILON)
                {
                    back     = true;
                    sides[i] = SIDE_BACK;
                }
                else
                {
                    sides[i] = SIDE_ON;
                }
                dists[i] = d;
            }

            if (!front || !back)
            {
                ClipSkyPolygon(nump, vecs, stage + 1);
                return;
            }

            sides[i] = sides[0];
            dists[i] = dists[0];
            Math3D.VectorCopy(vecs[0], vecs[i]);
            newc[0] = newc[1] = 0;
            for (i = 0; i < nump; i++)
            {
                v = vecs[i];
                switch (sides[i])

                {
                case SIDE_FRONT:
                    Math3D.VectorCopy(v, newv[stage][0][newc[0]]);
                    newc[0]++;
                    break;

                case SIDE_BACK:
                    Math3D.VectorCopy(v, newv[stage][1][newc[1]]);
                    newc[1]++;
                    break;

                case SIDE_ON:
                    Math3D.VectorCopy(v, newv[stage][0][newc[0]]);
                    newc[0]++;
                    Math3D.VectorCopy(v, newv[stage][1][newc[1]]);
                    newc[1]++;
                    break;
                }

                if (sides[i] == SIDE_ON || sides[i + 1] == SIDE_ON || sides[i + 1] == sides[i])
                {
                    continue;
                }
                d = dists[i] / (dists[i] - dists[i + 1]);
                for (j = 0; j < 3; j++)
                {
                    e = v[j] + d * (vecs[i + 1][j] - v[j]);
                    newv[stage][0][newc[0]][j] = e;
                    newv[stage][1][newc[1]][j] = e;
                }

                newc[0]++;
                newc[1]++;
            }

            ClipSkyPolygon(newc[0], newv[stage][0], stage + 1);
            ClipSkyPolygon(newc[1], newv[stage][1], stage + 1);
        }
Beispiel #29
0
        public virtual void GL_DrawAliasFrameLerp(qfiles.dmdl_t paliashdr, Single backlerp)
        {
            Single l;

            qfiles.daliasframe_t frame, oldframe;
            Int32[] v, ov;
            Int32[] order;
            var     orderIndex = 0;
            Int32   count;
            Single  frontlerp;
            Single  alpha;

            Single[]   move    = new Single[] { 0, 0, 0 };
            Single[][] vectors = new Single[][] { new Single[] { 0, 0, 0 }, new Single[] { 0, 0, 0 }, new Single[] { 0, 0, 0 } };
            Single[]   frontv  = new Single[] { 0, 0, 0 };
            Single[]   backv   = new Single[] { 0, 0, 0 };
            Int32      i;
            Int32      index_xyz;

            frame    = paliashdr.aliasFrames[currententity.frame];
            v        = frame.verts;
            oldframe = paliashdr.aliasFrames[currententity.oldframe];
            ov       = oldframe.verts;
            order    = paliashdr.glCmds;
            if ((currententity.flags & Defines.RF_TRANSLUCENT) != 0)
            {
                alpha = currententity.alpha;
            }
            else
            {
                alpha = 1F;
            }
            if ((currententity.flags & (Defines.RF_SHELL_RED | Defines.RF_SHELL_GREEN | Defines.RF_SHELL_BLUE | Defines.RF_SHELL_DOUBLE | Defines.RF_SHELL_HALF_DAM)) != 0)
            {
                GL.Disable(EnableCap.Texture2D);
            }
            frontlerp = 1F - backlerp;
            Math3D.VectorSubtract(currententity.oldorigin, currententity.origin, frontv);
            Math3D.AngleVectors(currententity.angles, vectors[0], vectors[1], vectors[2]);
            move[0] = Math3D.DotProduct(frontv, vectors[0]);
            move[1] = -Math3D.DotProduct(frontv, vectors[1]);
            move[2] = Math3D.DotProduct(frontv, vectors[2]);
            Math3D.VectorAdd(move, oldframe.translate, move);
            for (i = 0; i < 3; i++)
            {
                move[i]   = backlerp * move[i] + frontlerp * frame.translate[i];
                frontv[i] = frontlerp * frame.scale[i];
                backv[i]  = backlerp * oldframe.scale[i];
            }

            if (gl_vertex_arrays.value != 0F)
            {
                GL_LerpVerts(paliashdr.num_xyz, ov, v, move, frontv, backv);
                GL.EnableClientState(ArrayCap.VertexArray);
                new Pinnable(vertexArrayBuf.Array, (ptr) =>
                {
                    GL.VertexPointer(3, VertexPointerType.Float, 0, ptr);
                });
                if ((currententity.flags & (Defines.RF_SHELL_RED | Defines.RF_SHELL_GREEN | Defines.RF_SHELL_BLUE | Defines.RF_SHELL_DOUBLE | Defines.RF_SHELL_HALF_DAM)) != 0)
                {
                    GL.DisableClientState(ArrayCap.ColorArray);
                    GL.Color4(shadelight[0], shadelight[1], shadelight[2], alpha);
                }
                else
                {
                    GL.EnableClientState(ArrayCap.ColorArray);
                    new Pinnable(colorArrayBuf.Array, (ptr) =>
                    {
                        GL.ColorPointer(4, ColorPointerType.Float, 0, ptr);
                    });
                    SingleBuffer color = colorArrayBuf;
                    var          j     = 0;
                    for (i = 0; i < paliashdr.num_xyz; i++)
                    {
                        l = shadedots[(v[i] >> 24) & 0xFF];
                        color.Put(j++, l * shadelight[0]);
                        color.Put(j++, l * shadelight[1]);
                        color.Put(j++, l * shadelight[2]);
                        color.Put(j++, alpha);
                    }
                }

                //if (qglLockArraysEXT)
                //    gl.GlLockArraysEXT(0, paliashdr.num_xyz);
                while (true)
                {
                    count = order[orderIndex++];
                    if (count == 0)
                    {
                        break;
                    }
                    if (count < 0)
                    {
                        count = -count;
                        GL.Begin(PrimitiveType.TriangleFan);
                    }
                    else
                    {
                        GL.Begin(PrimitiveType.TriangleStrip);
                    }

                    if ((currententity.flags & (Defines.RF_SHELL_RED | Defines.RF_SHELL_GREEN | Defines.RF_SHELL_BLUE | Defines.RF_SHELL_DOUBLE | Defines.RF_SHELL_HALF_DAM)) != 0)
                    {
                        do
                        {
                            index_xyz   = order[orderIndex + 2];
                            orderIndex += 3;
                            GL.ArrayElement(index_xyz);
                        }while (--count != 0);
                    }
                    else
                    {
                        do
                        {
                            GL.TexCoord2(BitConverter.ToSingle(BitConverter.GetBytes(order[orderIndex + 0])), BitConverter.ToSingle(BitConverter.GetBytes(order[orderIndex + 1])));
                            index_xyz   = order[orderIndex + 2];
                            orderIndex += 3;
                            GL.ArrayElement(index_xyz);
                        }while (--count != 0);
                    }

                    GL.End();
                }

                // if (qglLockArraysEXT)
                //     gl.GlUnlockArraysEXT();
            }
            else
            {
                GL_LerpVerts(paliashdr.num_xyz, ov, v, s_lerped, move, frontv, backv);
                Single[] tmp;
                while (true)
                {
                    count = order[orderIndex++];
                    if (count == 0)
                    {
                        break;
                    }
                    if (count < 0)
                    {
                        count = -count;
                        GL.Begin(PrimitiveType.TriangleFan);
                    }
                    else
                    {
                        GL.Begin(PrimitiveType.TriangleStrip);
                    }

                    if ((currententity.flags & (Defines.RF_SHELL_RED | Defines.RF_SHELL_GREEN | Defines.RF_SHELL_BLUE)) != 0)
                    {
                        do
                        {
                            index_xyz   = order[orderIndex + 2];
                            orderIndex += 3;
                            GL.Color4(shadelight[0], shadelight[1], shadelight[2], alpha);
                            tmp = s_lerped[index_xyz];
                            GL.Vertex3(tmp[0], tmp[1], tmp[2]);
                        }while (--count != 0);
                    }
                    else
                    {
                        do
                        {
                            GL.TexCoord2(BitConverter.ToSingle(BitConverter.GetBytes(order[orderIndex + 0])), BitConverter.ToSingle(BitConverter.GetBytes(order[orderIndex + 1])));
                            index_xyz   = order[orderIndex + 2];
                            orderIndex += 3;
                            l           = shadedots[(v[index_xyz] >> 24) & 0xFF];
                            GL.Color4(l * shadelight[0], l * shadelight[1], l * shadelight[2], alpha);
                            tmp = s_lerped[index_xyz];
                            GL.Vertex3(tmp[0], tmp[1], tmp[2]);
                        }while (--count != 0);
                    }

                    GL.End();
                }
            }

            if ((currententity.flags & (Defines.RF_SHELL_RED | Defines.RF_SHELL_GREEN | Defines.RF_SHELL_BLUE | Defines.RF_SHELL_DOUBLE | Defines.RF_SHELL_HALF_DAM)) != 0)
            {
                GL.Enable(EnableCap.Texture2D);
            }
        }
Beispiel #30
0
        /**
         *
         * fall from 128: 400 = 160000
         * fall from 256: 580 = 336400
         * fall from 384: 720 = 518400
         * fall from 512: 800 = 640000
         * fall from 640: 960 =
         * damage = deltavelocity*deltavelocity * 0.0001
         */
        public static void SV_CalcViewOffset(edict_t ent)
        {
            float[] angles = { 0, 0, 0 };
            float   bob;
            float   ratio;
            float   delta;

            float[] v = { 0, 0, 0 };

            // base angles
            angles = ent.client.ps.kick_angles;

            // if dead, fix the angle and don't add any kick
            if (ent.deadflag != 0)
            {
                Math3D.VectorClear(angles);

                ent.client.ps.viewangles[Defines.ROLL]  = 40;
                ent.client.ps.viewangles[Defines.PITCH] = -15;
                ent.client.ps.viewangles[Defines.YAW]   = ent.client.killer_yaw;
            }
            else
            {
                // add angles based on weapon kick
                Math3D.VectorCopy(ent.client.kick_angles, angles);

                // add angles based on damage kick
                ratio = (ent.client.v_dmg_time - GameBase.level.time) / Defines.DAMAGE_TIME;

                if (ratio < 0)
                {
                    ratio = 0;
                    ent.client.v_dmg_pitch = 0;
                    ent.client.v_dmg_roll  = 0;
                }

                angles[Defines.PITCH] += ratio * ent.client.v_dmg_pitch;
                angles[Defines.ROLL]  += ratio * ent.client.v_dmg_roll;

                // add pitch based on fall kick
                ratio = (ent.client.fall_time - GameBase.level.time) / Defines.FALL_TIME;

                if (ratio < 0)
                {
                    ratio = 0;
                }

                angles[Defines.PITCH] += ratio * ent.client.fall_value;

                // add angles based on velocity
                delta = Math3D.DotProduct(ent.velocity, PlayerView.forward);
                angles[Defines.PITCH] += delta * GameBase.run_pitch.value;

                delta = Math3D.DotProduct(ent.velocity, PlayerView.right);
                angles[Defines.ROLL] += delta * GameBase.run_roll.value;

                // add angles based on bob
                delta = PlayerView.bobfracsin * GameBase.bob_pitch.value * PlayerView.xyspeed;

                if ((ent.client.ps.pmove.pm_flags & pmove_t.PMF_DUCKED) != 0)
                {
                    delta *= 6;                     // crouching
                }
                angles[Defines.PITCH] += delta;
                delta = PlayerView.bobfracsin * GameBase.bob_roll.value * PlayerView.xyspeed;

                if ((ent.client.ps.pmove.pm_flags & pmove_t.PMF_DUCKED) != 0)
                {
                    delta *= 6;                     // crouching
                }
                if ((PlayerView.bobcycle & 1) != 0)
                {
                    delta = -delta;
                }

                angles[Defines.ROLL] += delta;
            }

            // base origin
            Math3D.VectorClear(v);

            // add view height
            v[2] += ent.viewheight;

            // add fall height
            ratio = (ent.client.fall_time - GameBase.level.time) / Defines.FALL_TIME;

            if (ratio < 0)
            {
                ratio = 0;
            }

            v[2] -= ratio * ent.client.fall_value * 0.4f;

            // add bob height
            bob = PlayerView.bobfracsin * PlayerView.xyspeed * GameBase.bob_up.value;

            if (bob > 6)
            {
                bob = 6;
            }

            //gi.DebugGraph (bob *2, 255);
            v[2] += bob;

            // add kick offset

            Math3D.VectorAdd(v, ent.client.kick_origin, v);

            // absolutely bound offsets
            // so the view can never be outside the player box

            if (v[0] < -14)
            {
                v[0] = -14;
            }
            else if (v[0] > 14)
            {
                v[0] = 14;
            }

            if (v[1] < -14)
            {
                v[1] = -14;
            }
            else if (v[1] > 14)
            {
                v[1] = 14;
            }

            if (v[2] < -22)
            {
                v[2] = -22;
            }
            else if (v[2] > 30)
            {
                v[2] = 30;
            }

            Math3D.VectorCopy(v, ent.client.ps.viewoffset);
        }