⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 r_alias_c.pas

📁 delphi编的不错的贪吃蛇
💻 PAS
📖 第 1 页 / 共 3 页
字号:
{----------------------------------------------------------------------------}
{                                                                            }
{ File(s): r_alias_c.c                                                       }
{                                                                            }
{ Initial conversion by : Diogo Teixeira - fozi_b@yahoo.com                  }
{ Initial conversion on : 20-Jan-2002                                        }
{                                                                            }
{ This File contains part of convertion of Quake2 source to ObjectPascal.    }
{ More information about this project can be found at:                       }
{ http://www.sulaco.co.za/quake2/                                            }
{                                                                            }
{ Copyright (C) 1997-2001 Id Software, Inc.                                  }
{                                                                            }
{ This program is free software; you can redistribute it and/or              }
{ modify it under the terms of the GNU General Public License                }
{ as published by the Free Software Foundation; either version 2             }
{ of the License, or (at your option) any later version.                     }
{                                                                            }
{ This program is distributed in the hope that it will be useful,            }
{ but WITHOUT ANY WARRANTY; without even the implied warranty of             }
{ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.                       }
{                                                                            }
{ See the GNU General Public License for more details.                       }
{                                                                            }
{----------------------------------------------------------------------------}
{ Updated on :                                                               }
{ Updated by :                                                               }
{                                                                            }
{----------------------------------------------------------------------------}
{ * Still dependent (to compile correctly) on:                               }
{                                                                            }
{----------------------------------------------------------------------------}
{ * TODO:                                                                    }
{ proofread: missing.                                                        }
{                                                                            }
{----------------------------------------------------------------------------}
(*
  - Initial translation by Diogo Teixeira (20/01/2002)
  NOTES:
    .some pointer types are named ptype_t, others type_p and some
     ^type_t, this is because they were different in the files i
     used from the delphi source and some weren't present at all.
     (this should have been discussed earlier)
    .i added a "// TRANSLATOR'S NOTE:" in every critical point in
     the translation, any "missing ->" points to a variable that
     is declared in some other file and should be linked here.
    .ALL_SET switch makes this compile using all the code
     that is hidden because of "missing ->".
    .ASM_CODE switch enables assembly code, i did not translate
     this part since it is not needed and we didn't discussed
     this previously, so the "pure c" version was translated instead.
  - Finished Initial translation in 24/01/2002
  - For any discussion about this delphi translation mail: fozi_b@yahoo.com
*)

unit r_alias_c;

interface

uses
  windows,
  qfiles,
  q_shared,
  r_local,
  r_bsp_c,
  r_model;

type // TRANSLATOR'S NOTE: added to simplify translation
  tmatrix3x4 = array[0..2, 0..3] of single;

procedure R_AliasSetUpLerpData(pmdl : dmdl_p; backlerp : single);
procedure R_AliasSetUpTransform;
procedure R_AliasTransformVector(in_ : vec3_t; var out_ : vec3_t; xf : matrix34);
//procedure R_AliasTransformVector(in_, out_ : vec3_t; xf : tmatrix3x4);
procedure R_AliasProjectAndClipTestFinalVert(fv: finalvert_p);
procedure R_AliasTransformFinalVerts(numpoints: integer; fv: finalvert_p; oldv: dtrivertx_p; newv: dtrivertx_p);

function R_AliasCheckFrameBBox(frame : daliasframe_p; worldxf : matrix34) : cardinal;
function R_AliasCheckBBox : qboolean;
procedure R_AliasPreparePoints;
procedure R_AliasSetupLighting;
procedure R_AliasSetupFrames(pmdl: dmdl_p);
procedure R_AliasDrawModel;

// TRANSLATOR'S NOTE: defined but not used???
//procedure R_AliasLerpFrames(paliashdr : dmdl_p; backlerp : single);

const
  BBOX_TRIVIAL_ACCEPT = 0;
  BBOX_MUST_CLIP_XY = 1;
  BBOX_MUST_CLIP_Z = 2;
  BBOX_TRIVIAL_REJECT = 8;

var
  r_affinetridesc: affinetridesc_t;
  r_aliasblendcolor: integer;
  r_amodels_drawn: integer;

implementation

uses
  ref,
  r_light,
  r_main,
  r_rast,
  r_aclip,
  r_polyse,
  SysUtils;



const
  LIGHT_MIN	= 5;		// lowest light value we'll allow, to avoid the
							          //  need for inner-loop light clamping
  NUMVERTEXNORMALS =	162;

type
  paedge_t = ^aedge_t;
  aedge_t = array[0..1] of integer;

(*
** use a real variable to control lerping
*)
var
  r_plightvec             : vec3_t;
// CodeFusion...The line below MUST be commented out as it is not used.
//  r_lerped                : array [0..1023] of vec3_t;
  r_lerp_frontv           : vec3_t;
  r_lerp_backv            : vec3_t;
  r_lerp_move             : vec3_t;
  r_ambientlight          : integer;
  r_shadelight            : single;
  r_thisframe             : daliasframe_p;
  r_lastframe             : daliasframe_p;
  s_pmdl                  : dmdl_p;
  aliastransform          : matrix34;
  aliasworldtransform     : matrix34;
  aliasoldworldtransform  : matrix34;
  r_avertexnormals        : array [0..NUMVERTEXNORMALS- 1] of vec3_t = ({$I anorms.inc});
  s_ziscale               : Single;
  s_alias_forward         : vec3_t;
  s_alias_right           : vec3_t;
  s_alias_up              : vec3_t;
  aedges                  : array [0..11] of aedge_t = (
                                                        (0, 1), (1, 2), (2, 3), (3, 0),
                                                        (4, 5), (5, 6), (6, 7), (7, 4),
                                                        (0, 5), (1, 4), (2, 7), (3, 6)
                                                       );


(*
================
R_ConcatTransforms
================
*)
// TRANSLATOR'S NOTE: also defined in q_shared.h
(*
procedure R_ConcatTransforms(in1: tmatrix3x4; in2: tmatrix3x4; var out_: tmatrix3x4);
begin
  out_[0][0] := in1[0][0] * in2[0][0] + in1[0][1] * in2[1][0] +
    in1[0][2] * in2[2][0];
  out_[0][1] := in1[0][0] * in2[0][1] + in1[0][1] * in2[1][1] +
    in1[0][2] * in2[2][1];
  out_[0][2] := in1[0][0] * in2[0][2] + in1[0][1] * in2[1][2] +
    in1[0][2] * in2[2][2];
  out_[0][3] := in1[0][0] * in2[0][3] + in1[0][1] * in2[1][3] +
    in1[0][2] * in2[2][3] + in1[0][3];
  out_[1][0] := in1[1][0] * in2[0][0] + in1[1][1] * in2[1][0] +
    in1[1][2] * in2[2][0];
  out_[1][1] := in1[1][0] * in2[0][1] + in1[1][1] * in2[1][1] +
    in1[1][2] * in2[2][1];
  out_[1][2] := in1[1][0] * in2[0][2] + in1[1][1] * in2[1][2] +
    in1[1][2] * in2[2][2];
  out_[1][3] := in1[1][0] * in2[0][3] + in1[1][1] * in2[1][3] +
    in1[1][2] * in2[2][3] + in1[1][3];
  out_[2][0] := in1[2][0] * in2[0][0] + in1[2][1] * in2[1][0] +
    in1[2][2] * in2[2][0];
  out_[2][1] := in1[2][0] * in2[0][1] + in1[2][1] * in2[1][1] +
    in1[2][2] * in2[2][1];
  out_[2][2] := in1[2][0] * in2[0][2] + in1[2][1] * in2[1][2] +
    in1[2][2] * in2[2][2];
  out_[2][3] := in1[2][0] * in2[0][3] + in1[2][1] * in2[1][3] +
    in1[2][2] * in2[2][3] + in1[2][3];
end;
*)
(*
================
R_AliasCheckBBox
================
*)

(*
** R_AliasCheckFrameBBox
**
** Checks a specific alias frame bounding box
*)
function R_AliasCheckFrameBBox(frame : daliasframe_p; worldxf : matrix34) : cardinal;
var
  aggregate_and_clipcode: cardinal;
  aggregate_or_clipcode: cardinal;
  zclipped: qboolean;
  zfullyclipped: qboolean;
//  minz                    : single;
  i: integer;
  mins, maxs: vec3_t;
  transformed_min: vec3_t;
  transformed_max: vec3_t;
  j: integer;
  tmp, transformed: vec3_t;
  clipcode: cardinal;
  dp: single;
begin
  aggregate_and_clipcode := Cardinal(not Cardinal(0));
  aggregate_or_clipcode := 0;
  zclipped := false;
  zfullyclipped := true;
//  minz:= 9999.0;
  clipcode := 0;

 (*
 ** get the exact frame bounding box
 *)
  for i := 0 to 2 do
  begin
    mins[i] := frame^.translate[i];
    maxs[i] := mins[i] + frame^.scale[i] * 255;
  end;

 (*
 ** transform the min and max values into view space
 *)
  R_AliasTransformVector(mins, transformed_min, aliastransform);
  R_AliasTransformVector(maxs, transformed_max, aliastransform);

  if (transformed_min[2] >= ALIAS_Z_CLIP_PLANE) then
    zfullyclipped := false;
  if (transformed_max[2] >= ALIAS_Z_CLIP_PLANE) then
    zfullyclipped := false;

  if (zfullyclipped) then
  begin
    Result := BBOX_TRIVIAL_REJECT;
    Exit;
  end;
  if (zclipped) then
  begin
    Result := (BBOX_MUST_CLIP_XY or BBOX_MUST_CLIP_Z);
    Exit;
  end;

	(*
	** build a transformed bounding box from the given min and max
	*)
	for i:= 0 to 7 do
  begin
    clipcode := 0;
		if ((i and 1) <> 0) then
			tmp[0] := mins[0]
		else
			tmp[0] := maxs[0];

		if ((i and 2) <> 0) then
			tmp[1] := mins[1]
		else
			tmp[1] := maxs[1];

		if ((i and 4) <> 0) then
			tmp[2] := mins[2]
		else
			tmp[2] := maxs[2];

    R_AliasTransformVector(tmp, transformed, worldxf);

    for j := 0 to 3 do
    begin
			dp := DotProduct(transformed, view_clipplanes[j].normal);
      if ((dp - view_clipplanes[j].dist) < 0.0) then
        clipcode := clipcode or (1 shl j);
		end;
		aggregate_and_clipcode := aggregate_and_clipcode and clipcode;
		aggregate_or_clipcode := aggregate_or_clipcode or clipcode;
	end;

  if (aggregate_and_clipcode <> 0) then
  begin
    Result := BBOX_TRIVIAL_REJECT;
    Exit;
  end;
  if (aggregate_or_clipcode = 0) then
  begin
    Result := BBOX_TRIVIAL_ACCEPT;
    Exit;
  end;
  Result := BBOX_MUST_CLIP_XY;
end;

function R_AliasCheckBBox : qboolean;
var
  ccodes: array[0..1] of cardinal;
begin
	(*
	** non-lerping model
	*)
	ccodes[0] := R_AliasCheckFrameBBox(r_thisframe, aliasworldtransform);
  ccodes[1] := 0;
	if (currententity^.backlerp = 0.0) then
  begin
    if (ccodes[0] = BBOX_TRIVIAL_ACCEPT) then
    begin
			Result := qboolean(BBOX_TRIVIAL_ACCEPT);
      Exit;
    end
    else
      if ((ccodes[0] and BBOX_TRIVIAL_REJECT) <> 0) then
      begin
			  Result := qboolean(BBOX_TRIVIAL_REJECT);
        Exit;
      end
      else
      begin
			  Result := qboolean(ccodes[0] and (not cardinal(BBOX_TRIVIAL_REJECT)));
        Exit;
      end;
  end;

  ccodes[1] := R_AliasCheckFrameBBox(r_lastframe, aliasoldworldtransform);
  if ((ccodes[0] or ccodes[1]) = BBOX_TRIVIAL_ACCEPT) then
  begin
		Result := qboolean(BBOX_TRIVIAL_ACCEPT);
    Exit;
  end
  else
    if (((ccodes[0] and ccodes[1]) and BBOX_TRIVIAL_REJECT) <> 0) then
    begin
		  Result := qboolean(BBOX_TRIVIAL_REJECT);
      Exit;
    end
    else
    begin
		  Result:= qboolean((ccodes[0] or ccodes[1]) and (not Cardinal(BBOX_TRIVIAL_REJECT)));
      Exit;
    end;
end;

(*
================
R_AliasTransformVector
================
*)
procedure R_AliasTransformVector(in_ : vec3_t; var out_ : vec3_t; xf : matrix34);
begin
  out_[0] := DotProduct(in_, vec3_p(@xf[0][0])^) + xf[0][3];
  out_[1] := DotProduct(in_, vec3_p(@xf[1][0])^) + xf[1][3];
  out_[2] := DotProduct(in_, vec3_p(@xf[2][0])^) + xf[2][3];
end;

(*
================
R_AliasPreparePoints

General clipped case
================
*)
type
  aliasbatchedtransformdata_t = record
    num_points: integer;
    last_verts: dtrivertx_p; // verts from the last frame
    this_verts: dtrivertx_p; // verts from this frame
    dest_verts: finalvert_p; // destination for transformed verts
  end;

var
  aliasbatchedtransformdata: aliasbatchedtransformdata_t;

procedure R_AliasPreparePoints;
(*type
  tfinalvert_t_array = array [word] of finalvert_t; // TRANSLATOR'S NOTE: added to solve pointer->array problems
  pfinalvert_t_array = ^tfinalvert_t_array;

  tdstvert_t_array = array [word] of dstvert_t; // TRANSLATOR'S NOTE: added to solve pointer->array problems
  pdstvert_t_array = ^tdstvert_t_array; *)
var
  i           : integer;
	pstverts    : dstvert_a;//pdstvert_t_array;
	ptri        : dtriangle_p;
	pfv         : array [0..2] of finalvert_p;
	finalverts  : array [0..integer(MAXALIASVERTS+((CACHE_SIZE- 1) div sizeof(finalvert_t)))+ 3- 1] of finalvert_t;
	pfinalverts : finalvert_arrp;
begin
//PGM
  iractive := 0;
  if ((r_newrefdef.rdflags and RDF_IRGOGGLES) <> 0) and ((currententity^.flags and RF_IR_VISIBLE) <> 0) then
    iractive := 1;
//	iractive:= 0;
//	if(r_newrefdef.rdflags & RDF_IRGOGGLES && currententity.flags & RF_IR_VISIBLE)
//		iractive:= 1;
//PGM

	// put work vertexes on stack, cache aligned
	pfinalverts := finalvert_arrp(((Integer(@finalverts[0]) + CACHE_SIZE - 1) and (not Cardinal(CACHE_SIZE - 1))));

	aliasbatchedtransformdata.num_points := s_pmdl^.num_xyz;
	aliasbatchedtransformdata.last_verts := @r_lastframe^.verts;
	aliasbatchedtransformdata.this_verts := @r_thisframe^.verts;
	aliasbatchedtransformdata.dest_verts := Pointer(pfinalverts);

	R_AliasTransformFinalVerts( aliasbatchedtransformdata.num_points,
		                          aliasbatchedtransformdata.dest_verts,
								              aliasbatchedtransformdata.last_verts,
								              aliasbatchedtransformdata.this_verts );

// clip and draw all triangles
//
	pstverts := Pointer(Cardinal(s_pmdl) + s_pmdl^.ofs_st);
	ptri := Pointer(Cardinal(s_pmdl) + s_pmdl^.ofs_tris);

	if ((currententity^.flags and RF_WEAPONMODEL) <> 0) and (r_lefthand^.value = 1.0) then
  begin
		for i := 0 to s_pmdl^.num_tris-1 do
    begin
			pfv[0] := @pfinalverts^[ptri^.index_xyz[0]];
			pfv[1] := @pfinalverts^[ptri^.index_xyz[1]];
			pfv[2] := @pfinalverts^[ptri^.index_xyz[2]];

      if ((pfv[0]^.flags and pfv[1]^.flags and pfv[2].flags) <> 0) then
      begin
        Inc(Integer(ptri), SizeOf(dtriangle_t));
        continue; // completely clipped
      end;
   // insert s/t coordinates
      pfv[0]^.s := _SAL(pstverts^[ptri^.index_st[0]].s, 16);
      pfv[0]^.t := _SAL(pstverts^[ptri^.index_st[0]].t, 16);

      pfv[1]^.s := _SAL(pstverts^[ptri^.index_st[1]].s, 16);
      pfv[1]^.t := _SAL(pstverts^[ptri^.index_st[1]].t, 16);

      pfv[2]^.s := _SAL(pstverts^[ptri^.index_st[2]].s, 16);
      pfv[2]^.t := _SAL(pstverts^[ptri^.index_st[2]].t, 16);

      if ((pfv[0]^.flags or pfv[1]^.flags or pfv[2]^.flags) = 0) then
      begin
     // totally unclipped
        aliastriangleparms.a := pfv[2];
        aliastriangleparms.b := pfv[1];
        aliastriangleparms.c := pfv[0];
        R_DrawTriangle;
      end
      else
      begin
        R_AliasClipTriangle(pfv[2], pfv[1], pfv[0]);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -