Subversion Repositories spacemission

Rev

Rev 1 | Blame | Compare with Previous | Last modification | View Log | RSS feed

  1. unit DXRender;
  2.  
  3. interface
  4.  
  5. {$INCLUDE DelphiXcfg.inc}
  6.  
  7. uses
  8.   Windows,
  9. {$IfDef StandardDX}
  10.   DirectDraw,
  11.   {$ifdef DX7}
  12.   Direct3D;
  13.   {$endif}
  14.   {$IfDef DX9}
  15.   Direct3D9, Direct3D, D3DX9, {Direct3D8,} DX7toDX8;
  16.   {$EndIf}
  17. {$Else}
  18.   DirectX;
  19. {$EndIf}
  20.  
  21. const
  22.   DXR_MAXTEXTURE = 4;
  23.  
  24. type
  25.   TDXR_Value = Double;
  26.  
  27.   TDXR_Color = DWORD;
  28.   TDXR_SurfaceColor = DWORD;
  29.  
  30.   {  TDXR_Option  }
  31.  
  32.   PDXR_Option = ^TDXR_Option;
  33.   TDXR_Option = (
  34.     DXR_OPTION_VERSION,
  35.     DXR_OPTION_MMXENABLE,
  36.     DXR_OPTION_RENDERPRIMITIVES
  37.   );                            
  38.  
  39.   {  TDXR_ShadeMode  }
  40.  
  41.   TDXR_ShadeMode = (
  42.     DXR_SHADEMODE_FLAT,
  43.     DXR_SHADEMODE_GOURAUD
  44.   );
  45.  
  46.   {  TDXR_Blend  }
  47.  
  48.   TDXR_Blend = (
  49.     // for blending
  50.     DXR_BLEND_ZERO,                        // r=0
  51.     DXR_BLEND_ONE1,                        // r=c1
  52.     DXR_BLEND_ONE2,                        // r=c2
  53.     DXR_BLEND_ONE1_ADD_ONE2,               // r=c1+c2
  54.     DXR_BLEND_ONE1_SUB_ONE2,               // r=c1-c2
  55.     DXR_BLEND_ONE2_SUB_ONE1,               // r=c2-c1
  56.     DXR_BLEND_ONE1_MUL_ONE2,               // r=c1*c2
  57.     DXR_BLEND_SRCALPHA1,                   // r=c1*a1
  58.     DXR_BLEND_SRCALPHA1_ADD_ONE2,          // r=c1*a1+c2
  59.     DXR_BLEND_ONE2_SUB_SRCALPHA1,          // r=c2-c1*a1
  60.     DXR_BLEND_SRCALPHA1_ADD_INVSRCALPHA2,  // r=c1*a1+c2*(1-a2)
  61.     DXR_BLEND_INVSRCALPHA1_ADD_SRCALPHA2,  // r=c1*(1-a1)+c2*a2
  62.     // for lighting
  63.     DXR_BLEND_DECAL,                       // r=c1
  64.     DXR_BLEND_DECALALPHA,                  // r=c1    ra=a2
  65.     DXR_BLEND_MODULATE,                    // r=c1*c2 ra=a2
  66.     DXR_BLEND_MODULATEALPHA,               // r=c1*c2
  67.     DXR_BLEND_ADD                          // r=c1+c2 ra=a2
  68.   );
  69.  
  70.   {  TDXR_TextureFilter  }
  71.  
  72.   TDXR_TextureFilter = (
  73.     DXR_TEXTUREFILTER_NEAREST,
  74.     DXR_TEXTUREFILTER_LINEAR,
  75.     DXR_TEXTUREFILTER_MIPMAP_NEAREST,
  76.     DXR_TEXTUREFILTER_MIPMAP_LINEAR
  77.   );
  78.  
  79.   {  TDXR_TextureAddress  }
  80.  
  81.   TDXR_TextureAddress = (
  82.     DXR_TEXTUREADDRESS_TILE,           // tx=tx and WidthMask ty=ty and HeightMask
  83.     DXR_TEXTUREADDRESS_DONOTCLIP       // tx=tx               ty=ty
  84.   );
  85.  
  86.   {  TDXR_CmpFunc  }
  87.  
  88.   TDXR_CmpFunc = (
  89.     DXR_CMPFUNC_NEVER,
  90.     DXR_CMPFUNC_LESS,
  91.     DXR_CMPFUNC_EQUAL,
  92.     DXR_CMPFUNC_LESSEQUAL,
  93.     DXR_CMPFUNC_GREATER,
  94.     DXR_CMPFUNC_NOTEQUAL,
  95.     DXR_CMPFUNC_GREATEREQUAL,
  96.     DXR_CMPFUNC_ALWAYS
  97.   );
  98.  
  99.   {  TDXR_ColorType  }
  100.  
  101.   TDXR_ColorType = (
  102.     DXR_COLORTYPE_INDEXED,     // Palette indexed color
  103.     DXR_COLORTYPE_RGB          // RGB color
  104.   );
  105.  
  106.   {  TDXR_ColorChannel  }
  107.  
  108.   TDXR_ColorChannel = record
  109.     Mask: DWORD;                // Bit Mask
  110.     BitCount: DWORD;            // Number of bit
  111.     rshift: DWORD;
  112.     lshift: DWORD;
  113.   end;
  114.  
  115.   {  TDXR_Surface  }
  116.  
  117.   PDXR_Surface = ^TDXR_Surface;
  118.   TDXR_Surface = record
  119.     ColorType: TDXR_ColorType;   // Color type
  120.     Width, Height: DWORD;        // Size of surface
  121.     WidthBit, HeightBit: DWORD;  // Size of surface (Number of bit)
  122.     Width2, Height2: DWORD;      // 1 shl WidthBit, 1 shl HeightBit
  123.     WidthMask, HeightMask: DWORD;// Bit Mask of size of surface
  124.     BitCount: DWORD;             // BitCount per Pixel(1, 2, 4, 8, 16, 24, 32 only)
  125.     Bits: Pointer;               // Pointer to pixeldata(x:0 y:0)
  126.     Pitch: Integer;              // Offset of next scanline
  127.     PitchBit: Integer;           // Offset of next scanline (Number of bit)
  128.     MipmapChain: PDXR_Surface;
  129.     case Integer of
  130.       0: (
  131.         { Indexed color }
  132.         idx_index: TDXR_ColorChannel;  // Index channel
  133.         idx_alpha: TDXR_ColorChannel;  // Alpha channel
  134.         idx_palette: array[0..255] of TPaletteEntry;
  135.                                        // Palette
  136.       );
  137.       1: (
  138.         { RGB color }
  139.         rgb_red: TDXR_ColorChannel;    // Red channel
  140.         rgb_green: TDXR_ColorChannel;  // Green channel
  141.         rgb_blue: TDXR_ColorChannel;   // Blue channel
  142.         rgb_alpha: TDXR_ColorChannel;  // Alpha channel
  143.       );
  144.   end;
  145.  
  146.   {  TDXR_Vertex  }
  147.  
  148.   PDXR_Vertex = ^TDXR_Vertex;
  149.   TDXR_Vertex = record
  150.     sx: TDXR_Value;            // Screen coordinates
  151.     sy: TDXR_Value;
  152.     sz: TDXR_Value;
  153.     rhw: TDXR_Value;           // 1/sz
  154.     color: TDXR_Color;
  155.     specular: TDXR_Color;
  156.     tu, tv: array[0..DXR_MAXTEXTURE-1] of TDXR_Value;
  157.   end;
  158.  
  159.   PPDXR_Vertex = ^PDXR_Vertex;
  160.  
  161.   {  TDXR_PrimitiveType  }
  162.  
  163.   TDXR_PrimitiveType = (
  164.     DXR_PRIMITIVETYPE_TRIANGLELIST,
  165.     DXR_PRIMITIVETYPE_TRIANGLESTRIP
  166.   );
  167.  
  168.   {  TDXR_TextureLayerBlend  }
  169.  
  170.   TDXR_TextureLayerBlend = (
  171.     DXR_TEXTURELAYERBLEND_TEXTURE,
  172.     DXR_TEXTURELAYERBLEND_LAST,
  173.     DXR_TEXTURELAYERBLEND_NOBLEND
  174.   );
  175.  
  176.   {  TDXR_TextureLayer  }
  177.  
  178.   PDXR_TextureLayer = ^TDXR_TextureLayer;
  179.   TDXR_TextureLayer = record
  180.     Surface: PDXR_Surface;
  181.     LayerBlend: TDXR_TextureLayerBlend;
  182.     Blend: TDXR_Blend;
  183.     ColorKeyEnable: Boolean;
  184.     ColorKey: TDXR_SurfaceColor;
  185.     TextureAddress: TDXR_TextureAddress;
  186.     BumpTexture: Integer;
  187.   end;
  188.  
  189.   {  TDXR_Cull  }
  190.  
  191.   TDXR_Cull = (
  192.     DXR_CULL_NONE,
  193.     DXR_CULL_CW,
  194.     DXR_CULL_CCW
  195.   );
  196.  
  197.   {  TDXR_RenderStates  }
  198.  
  199.   TDXR_RenderStates = record
  200.     DitherEnable: Boolean;
  201.     SpecularEnable: Boolean;
  202.     CullMode: TDXR_Cull;
  203.     Shade: TDXR_ShadeMode;
  204.     TexBlend: TDXR_Blend;
  205.     Blend: TDXR_Blend;
  206.     TextureEnable: Boolean;
  207.     TextureList: array[0..DXR_MAXTEXTURE-1] of TDXR_TextureLayer;
  208.     TextureFilter: TDXR_TextureFilter;
  209.     ZBuffer: PDXR_Surface;
  210.     ZFunc: TDXR_CmpFunc;
  211.     ZWriteEnable: Boolean;
  212.     EnableDrawLine: Integer;
  213.   end;
  214.  
  215. function dxrGetOption(Option: TDXR_Option): DWORD;
  216. procedure dxrSetOption(Option: TDXR_Option; Value: DWORD);
  217.  
  218. procedure dxrMakeIndexedSurface(var Surface: TDXR_Surface; Width, Height, BitCount: DWORD;
  219.   Bits: Pointer; pitch: Integer; idx_index, idx_alpha: DWORD);
  220. procedure dxrMakeRGBSurface(var Surface: TDXR_Surface; Width, Height, BitCount: DWORD;
  221.   Bits: Pointer; pitch: Integer; rgb_red, rgb_green, rgb_blue, rgb_alpha: DWORD);
  222. function dxrScanLine(const Surface: TDXR_Surface; y: DWORD): Pointer;
  223. procedure dxrZBufferClear(const Surface: TDXR_Surface);
  224.  
  225. function dxrDDSurfaceLock(DDSurface: {$IFDEF D3D_deprecated}IDirectDrawSurface{$ELSE}IDirectDrawSurface7{$ENDIF}; var Surface: TDXR_Surface): Boolean; {$IFDEF VER9UP}inline;{$ENDIF}
  226. function dxrDDSurfaceLock2(DDSurface: {$IFDEF D3D_deprecated}IDirectDrawSurface{$ELSE}IDirectDrawSurface7{$ENDIF}; var ddsd: {$IFDEF D3D_deprecated}TDDSurfaceDesc{$ELSE}TDDSurfaceDesc2{$ENDIF};
  227.   var Surface: TDXR_Surface): Boolean; {$IFDEF VER9UP}inline;{$ENDIF}
  228. procedure dxrDDSurfaceUnLock(DDSurface: {$IFDEF D3D_deprecated}IDirectDrawSurface{$ELSE}IDirectDrawSurface7{$ENDIF}; const Surface: TDXR_Surface); {$IFDEF VER9UP}inline;{$ENDIF}
  229.  
  230. procedure dxrDefRenderStates(var States: TDXR_RenderStates);
  231.  
  232. procedure dxrDrawPrimitive(const Dest: TDXR_Surface; const States: TDXR_RenderStates; PrimitiveType: TDXR_PrimitiveType;
  233.   VertexList: PDXR_Vertex; VertexCount: DWORD);
  234. procedure dxrDrawPointeredPrimitive(const Dest: TDXR_Surface; const States: TDXR_RenderStates; PrimitiveType: TDXR_PrimitiveType;
  235.   VertexList: PPDXR_Vertex; VertexCount: DWORD);
  236. procedure dxrDrawIndexedPrimitive(const Dest: TDXR_Surface; const States: TDXR_RenderStates; PrimitiveType: TDXR_PrimitiveType;
  237.   VertexList: PDXR_Vertex; VertexCount: DWORD; IndexList: PDWORD; IndexCount: DWORD);
  238.  
  239. procedure dxrCopyRectBlend(const Dest, Src: TDXR_Surface;
  240.   const DestRect, SrcRect: TRect; Blend: TDXR_Blend; Alpha: Integer;
  241.   ColorKeyEnable: Boolean; ColorKey: DWORD);
  242.  
  243. procedure dxrFillRectColorBlend(const Dest: TDXR_Surface;
  244.   const DestRect: TRect; Blend: TDXR_Blend; Col: COLORREF);
  245.  
  246. procedure dxrDrawWaveXBlend(const Dest, Src: TDXR_Surface;
  247.   X, Y, Width, Height: Integer; const SrcRect: TRect; amp, Len, ph: Integer;
  248.   Blend: TDXR_Blend; Alpha: Integer;
  249.   ColorKeyEnable: Boolean; ColorKey: DWORD);
  250.  
  251. procedure dxrDrawRotateBlend(const Dest, Src: TDXR_Surface;
  252.   X, Y, Width, Height: Integer; const SrcRect: TRect; CenterX, CenterY: Double;
  253.   Angle: Integer; Blend: TDXR_Blend; Alpha: Integer;
  254.   ColorKeyEnable: Boolean; ColorKey: DWORD);
  255.  
  256. implementation
  257.  
  258. const
  259.   TextureAxisFloatBit = 16;
  260.   TextureAxisFloat = 1 shl TextureAxisFloatBit;
  261.  
  262.   ColorFloatBit = 8;
  263.   ColorFloat = 1 shl ColorFloatBit;
  264.                
  265. type
  266.  
  267.   PInteger = ^Integer;
  268.  
  269.   {  TDXRMachine  }
  270.  
  271.   TDXRMachine_TreeType = (
  272.     DXR_TREETYPE_LOADBLACK,      // Load black color
  273.     DXR_TREETYPE_LOADCOLOR,      // Load vertex color
  274.     DXR_TREETYPE_LOADCONSTCOLOR, // Load constant color
  275.     DXR_TREETYPE_LOADTEXTURE,    // Load texel
  276.     DXR_TREETYPE_LOADBUMPTEXTURE,// Load texel with Bump mapping
  277.                                  //   dx := nx + (BumpTexture[nx-1, ny]-BumpTexture[nx+1, ny]);
  278.                                  //   dy := ny + (BumpTexture[nx, ny-1]-BumpTexture[nx, ny+1]);
  279.     DXR_TREETYPE_LOADDESTPIXEL,  // Load dest pixel
  280.     DXR_TREETYPE_BLEND           // Blend color
  281.   );
  282.  
  283.   TDXRColorChannel = (chRed, chGreen, chBlue, chAlpha);
  284.   TDXRColorChannels = set of TDXRColorChannel;
  285.  
  286.   PDXRMachine_Color = ^TDXRMachine_Color;
  287.   TDXRMachine_Color = packed record
  288.     R, G, B, A: WORD;
  289.   end;
  290.  
  291.   PDXRMachine_Axis = ^TDXRMachine_Axis;
  292.   TDXRMachine_Axis = packed record
  293.     X, Y: Integer;
  294.   end;
  295.  
  296.   PDXRMachine_Int64 = ^TDXRMachine_Int64;
  297.   TDXRMachine_Int64 = Comp;
  298.  
  299.   PDXRMachine_Reg_Color = ^TDXRMachine_Reg_Color;
  300.   TDXRMachine_Reg_Color = record
  301.     Enable: Boolean;
  302.     nColor: TDXRMachine_Color;
  303.     iColor: TDXRMachine_Color;
  304.     Gouraud: Boolean;
  305.     Channels: TDXRColorChannels;
  306.   end;
  307.  
  308.   PDXRMachine_Reg_Texture = ^TDXRMachine_Reg_Texture;
  309.   TDXRMachine_Reg_Texture = record
  310.     Enable: Boolean;
  311.     Surface: PDXR_Surface;
  312.     nAxis: TDXRMachine_Axis;
  313.     iAxis: TDXRMachine_Axis;
  314.     iAxisConstant: Boolean;
  315.     Filter: TDXR_TextureFilter;
  316.     ColorKeyEnable: Boolean;
  317.     ColorKey: TDXR_SurfaceColor;
  318.     EnableChannels: TDXRColorChannels;
  319.     TextureAddress: TDXR_TextureAddress;
  320.     DefaultColor: TDXRMachine_Color;
  321.   end;
  322.  
  323.   TDXRMachine_Reg_RHW = record
  324.     Enable: Boolean;
  325.     nRHW: TDXRMachine_Int64;
  326.     iRHW: TDXRMachine_Int64;
  327.   end;
  328.  
  329.   TDXRMachine_Reg_Dither = record
  330.     Enable: Boolean;
  331.   end;
  332.  
  333.   TDXRMachine_Reg_ZBuffer = record
  334.     Enable: Boolean;
  335.     Surface: PDXR_Surface;
  336.     CmpFunc: TDXR_CmpFunc;
  337.     WriteEnable: Boolean;
  338.   end;
  339.  
  340.   TDXRMachine_Reg_Axis = record
  341.     Axis: TDXRMachine_Axis;
  342.     IncEnable: Boolean;
  343.   end;
  344.  
  345.   PDXRMachine_Tree = ^TDXRMachine_Tree;
  346.   TDXRMachine_Tree = record
  347.     Typ: TDXRMachine_TreeType;
  348.     Channels: TDXRColorChannels;
  349.     case TDXRMachine_TreeType of
  350.       DXR_TREETYPE_LOADBLACK: (
  351.         );
  352.       DXR_TREETYPE_LOADCOLOR: (
  353.         Color: Integer
  354.         );
  355.       DXR_TREETYPE_LOADCONSTCOLOR: (
  356.         ConstColor: TDXRMachine_Color;
  357.         );
  358.       DXR_TREETYPE_LOADTEXTURE: (
  359.         Texture: Integer
  360.         );
  361.       DXR_TREETYPE_LOADBUMPTEXTURE: (
  362.         _Texture: Integer;
  363.         BumpTexture: Integer;
  364.         );
  365.       DXR_TREETYPE_LOADDESTPIXEL: (
  366.         );
  367.       DXR_TREETYPE_BLEND: (
  368.         Blend: TDXR_Blend;
  369.         BlendTree1: PDXRMachine_Tree;
  370.         BlendTree2: PDXRMachine_Tree;
  371.         );
  372.   end;
  373.  
  374.   TDXRMachine = class
  375.   private
  376.     FBuf: Pointer;
  377.     FCall: Pointer;
  378.     FCompiled: Boolean;
  379.     FTreeCount: Integer;
  380.     FTreeList: array[0..127] of TDXRMachine_Tree;
  381.     FMMXUsed: Boolean;
  382.     F_ZBuf: Pointer;
  383.     F_BiLinearAxis: TDXRMachine_Axis;
  384.     F_BiLinearCol1: TDXRMachine_Color;
  385.     F_BiLinearCol2: TDXRMachine_Color;
  386.     F_BiLinearCol3: TDXRMachine_Color;
  387.     F_BiLinearCol4: TDXRMachine_Color;
  388.     F_BumpAxis: TDXRMachine_Axis;
  389.     F_BumpAxis2: TDXRMachine_Axis;
  390.     F_BumpTempCol: DWORD;
  391.     FStack: array[0..255] of TDXRMachine_Color;
  392.     procedure GenerateCode(var Code: Pointer; Tree: PDXRMachine_Tree);
  393.   public
  394.     Dest: PDXR_Surface;
  395.     ColorList: array[0..7] of TDXRMachine_Reg_Color;
  396.     ColorIndex: array[0..7] of Integer;
  397.     ColorIndexCount: Integer;
  398.     TextureList: array[0..7] of TDXRMachine_Reg_Texture;
  399.     TextureIndex: array[0..7] of Integer;
  400.     TextureIndexCount: Integer;
  401.     Dither: TDXRMachine_Reg_Dither;
  402.     ZBuffer: TDXRMachine_Reg_ZBuffer;
  403.     Axis: TDXRMachine_Reg_Axis;
  404.     RHW: TDXRMachine_Reg_RHW;
  405.     constructor Create;
  406.     destructor Destroy; override;
  407.     function CreateTree: PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  408.     function CreateTree2(Typ: TDXRMachine_TreeType): PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  409.     function CreateTree_LoadColor(Color: DWORD): PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  410.     function CreateTree_LoadConstColor(R, G, B, A: Byte): PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  411.     function CreateTree_LoadTexture(Texture: DWORD): PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  412.     function CreateTree_LoadBumpTexture(Texture, BumpTexture: DWORD): PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  413.     function CreateTree_Blend(Blend: TDXR_Blend; BlendTree1, BlendTree2: PDXRMachine_Tree): PDXRMachine_Tree; {$IFDEF VER9UP}inline;{$ENDIF}
  414.     procedure Initialize; {$IFDEF VER9UP}inline;{$ENDIF}
  415.     procedure Compile(Tree: PDXRMachine_Tree);
  416.     procedure Run(Count: Integer);
  417.     property Compiled: Boolean read FCompiled write FCompiled;
  418.   end;
  419.  
  420. const
  421.   CPUIDF_FPU  = 1 shl 0;  {  Floating-point unit on-chip  }
  422.   CPUIDF_VME  = 1 shl 1;  {  Virtual Mode Extension  }
  423.   CPUIDF_DE   = 1 shl 2;  {  Debugging Extension  }
  424.   CPUIDF_PSE  = 1 shl 3;  {  Page Size Extension  }
  425.   CPUIDF_TSC  = 1 shl 4;  {  Time Stamp Counter  }
  426.   CPUIDF_MSR  = 1 shl 5;  {  Mode Spacific Registers  }
  427.   CPUIDF_PAE  = 1 shl 6;  {  Physical Address Extension  }
  428.   CPUIDF_MCE  = 1 shl 7;  {  Machine Check Exception  }
  429.   CPUIDF_CX8  = 1 shl 8;  {  CMPXCHG8 Instruction Supported  }
  430.   CPUIDF_APIC = 1 shl 9;  {  On-chip APIC Hardware Supported }
  431.   CPUIDF_MTRR = 1 shl 12; {  Memory Type Range Registers  }
  432.   CPUIDF_PGE  = 1 shl 13; {  Page Global Enable  }
  433.   CPUIDF_MCA  = 1 shl 14; {  Machine Check Architecture  }
  434.   CPUIDF_CMOV = 1 shl 15; {  Conditional Move Instruction Supported  }
  435.   CPUIDF_MMX  = 1 shl 23; {  Intel Architecture MMX Technology supported  }
  436.  
  437. var
  438.   CPUIDVendor: array[0..11] of Char;
  439.   CPUIDSignature: Integer;
  440.   CPUIDFeatures: Integer;
  441.   UseMMX: Boolean;
  442.  
  443.   RenderPrimitiveCount: Integer;
  444.  
  445. procedure ReadCPUID;
  446. begin
  447.   asm
  448.     push ebx
  449.  
  450.     pushfd
  451.     pop eax
  452.     mov ecx,eax
  453.     xor eax,$200000
  454.     push eax
  455.     popfd
  456.     pushfd
  457.     pop eax
  458.     xor eax,ecx
  459.     jz @@exit
  460.  
  461.     mov eax,0
  462.     db $0F,$A2                  ///cpuid
  463.     cmp eax,1
  464.     jl @@exit
  465.  
  466.     {  Vendor ID  }
  467.     mov eax,0
  468.     db $0F,$A2                  ///cpuid
  469.     mov dword ptr [CPUIDVendor], ebx
  470.     mov dword ptr [CPUIDVendor+4], edx
  471.     mov dword ptr [CPUIDVendor+8], ecx
  472.  
  473.     {  Features, Signature  }
  474.     mov eax,1
  475.     db $0F,$A2                  ///cpuid
  476.     mov CPUIDSignature,eax
  477.     mov CPUIDFeatures,edx
  478.   @@exit:
  479.     pop ebx
  480.   end;
  481.   UseMMX := CPUIDFeatures and CPUIDF_MMX<>0;
  482. end;
  483.  
  484. function dxrGetOption(Option: TDXR_Option): DWORD;
  485. begin
  486.   Result := 0;
  487.   case Option of
  488.     DXR_OPTION_VERSION:
  489.         begin
  490.           Result := 1*100 + 0;
  491.         end;
  492.     DXR_OPTION_MMXENABLE:
  493.         begin
  494.           Result := DWORD(LongBool(UseMMX));
  495.         end;
  496.     DXR_OPTION_RENDERPRIMITIVES:
  497.         begin
  498.           Result := RenderPrimitiveCount;
  499.         end;
  500.   end;
  501. end;
  502.  
  503. procedure dxrSetOption(Option: TDXR_Option; Value: DWORD);
  504. begin
  505.   case Option of
  506.     DXR_OPTION_MMXENABLE:
  507.         begin
  508.           UseMMX := LongBool(Value) and (CPUIDFeatures and CPUIDF_MMX<>0);
  509.         end;
  510.     DXR_OPTION_RENDERPRIMITIVES:
  511.         begin
  512.           RenderPrimitiveCount := Value;
  513.         end;
  514.   end;
  515. end;
  516.  
  517. function GetBitCount(B: Integer): DWORD;
  518. begin
  519.   Result := 31;
  520.   while (Result>0) and (((1 shl Result) and B)=0) do Dec(Result);
  521. end;
  522.  
  523. function GetFirstZeroBitCount(B: Integer): DWORD;
  524. begin
  525.   Result := 0;
  526.   while (Result<31) and (((1 shl Result) and B)=0) do Inc(Result);
  527. end;
  528.  
  529. function GetOneBitCount(B: Integer): DWORD;
  530. var
  531.   i: Integer;
  532. begin
  533.   Result := 0;
  534.   for i:=0 to 31 do
  535.     Inc(Result, Ord(b and (1 shl i)<>0));
  536. end;
  537.  
  538. function dxrMakeColorChannel(Mask: DWORD; indexed: Boolean): TDXR_ColorChannel;
  539. var
  540.   i: Integer;
  541. begin
  542.   Result.BitCount := GetOneBitCount(Mask shr (GetFirstZeroBitCount(Mask)));
  543.   Result.Mask := Mask;
  544.  
  545.   if indexed then
  546.   begin
  547.     Result.rshift := GetFirstZeroBitCount(Mask);
  548.     Result.lshift := 0;
  549.   end else
  550.   begin
  551.     i :=  GetFirstZeroBitCount(Mask)-(8-Result.BitCount);
  552.  
  553.     if i<0 then
  554.     begin
  555.       Result.lshift := -i;
  556.       Result.rshift := 0;
  557.     end else
  558.     begin
  559.       Result.lshift := 0;
  560.       Result.rshift := DWORD(i);
  561.     end;
  562.   end;
  563. end;
  564.  
  565. procedure dxrMakeIndexedSurface(var Surface: TDXR_Surface; Width, Height, BitCount: DWORD;
  566.   Bits: Pointer; pitch: Integer; idx_index, idx_alpha: DWORD);
  567. begin
  568.   FillChar(Surface, SizeOf(Surface), 0);
  569.  
  570.   Surface.ColorType := DXR_COLORTYPE_INDEXED;
  571.   Surface.Width := Width;
  572.   Surface.Height := Height;
  573.   Surface.WidthBit := GetBitCount(Width);
  574.   Surface.HeightBit := GetBitCount(Height);
  575.   Surface.Width2 := 1 shl Surface.WidthBit;
  576.   Surface.Height2 := 1 shl Surface.HeightBit;
  577.   Surface.WidthMask := Surface.Width-1;
  578.   Surface.HeightMask := Surface.Height2-1;
  579.  
  580.   Surface.BitCount := BitCount;
  581.   Surface.Bits := Bits;
  582.   Surface.Pitch := Pitch;
  583.   Surface.PitchBit := GetBitCount(Abs(Pitch));
  584.  
  585.   Surface.idx_index := dxrMakeColorChannel(idx_index, True);
  586.   Surface.idx_alpha := dxrMakeColorChannel(idx_alpha, False);
  587. end;
  588.  
  589. procedure dxrMakeRGBSurface(var Surface: TDXR_Surface; Width, Height, BitCount: DWORD;
  590.   Bits: Pointer; pitch: Integer; rgb_red, rgb_green, rgb_blue, rgb_alpha: DWORD);
  591. begin
  592.   FillChar(Surface, SizeOf(Surface), 0);
  593.  
  594.   Surface.ColorType := DXR_COLORTYPE_RGB;
  595.   Surface.Width := Width;
  596.   Surface.Height := Height;
  597.   Surface.WidthBit := GetBitCount(Width);
  598.   Surface.HeightBit := GetBitCount(Height);
  599.   Surface.Width2 := 1 shl Surface.WidthBit;
  600.   Surface.Height2 := 1 shl Surface.HeightBit;
  601.   Surface.WidthMask := Surface.Width-1;
  602.   Surface.HeightMask := Surface.Height2-1;
  603.  
  604.   Surface.BitCount := BitCount;
  605.   Surface.Bits := Bits;
  606.   Surface.Pitch := Pitch;
  607.   Surface.PitchBit := GetBitCount(Abs(Pitch));
  608.  
  609.   Surface.rgb_red := dxrMakeColorChannel(rgb_red, False);
  610.   Surface.rgb_green := dxrMakeColorChannel(rgb_green, False);
  611.   Surface.rgb_blue := dxrMakeColorChannel(rgb_blue, False);
  612.   Surface.rgb_alpha := dxrMakeColorChannel(rgb_alpha, False);
  613. end;
  614.  
  615. function dxrCompareSurface(const Surface1, Surface2: TDXR_Surface): Boolean;
  616. begin
  617.   if Surface1.ColorType=DXR_COLORTYPE_INDEXED then
  618.   begin
  619.     Result := (Surface2.ColorType=DXR_COLORTYPE_INDEXED) and
  620.       (Surface1.idx_index.Mask=Surface2.idx_index.Mask) and
  621.       (Surface1.idx_alpha.Mask=Surface2.idx_alpha.Mask);
  622.   end else if Surface1.ColorType=DXR_COLORTYPE_RGB then
  623.   begin
  624.     Result := (Surface2.ColorType=DXR_COLORTYPE_RGB) and
  625.       (Surface1.rgb_red.Mask=Surface2.rgb_red.Mask) and
  626.       (Surface1.rgb_green.Mask=Surface2.rgb_green.Mask) and
  627.       (Surface1.rgb_blue.Mask=Surface2.rgb_blue.Mask) and
  628.       (Surface1.rgb_alpha.Mask=Surface2.rgb_alpha.Mask);
  629.   end else
  630.     Result := False;
  631. end;
  632.  
  633. function dxrDDSurfaceLock(DDSurface: {$IFDEF D3D_deprecated}IDirectDrawSurface{$ELSE}IDirectDrawSurface7{$ENDIF}; var Surface: TDXR_Surface): Boolean;
  634. var
  635.   ddsd: {$IFDEF D3D_deprecated}TDDSurfaceDesc{$ELSE}TDDSurfaceDesc2{$ENDIF};
  636. begin
  637.   Result := dxrDDSurfaceLock2(DDSurface, ddsd, Surface);
  638. end;
  639.                                                                                    
  640. function dxrDDSurfaceLock2(DDSurface: {$IFDEF D3D_deprecated}IDirectDrawSurface{$ELSE}IDirectDrawSurface7{$ENDIF}; var ddsd: {$IFDEF D3D_deprecated}TDDSurfaceDesc{$ELSE}TDDSurfaceDesc2{$ENDIF};
  641.   var Surface: TDXR_Surface): Boolean;
  642. const
  643.   DDPF_PALETTEINDEXED = DDPF_PALETTEINDEXED1 or DDPF_PALETTEINDEXED2 or
  644.     DDPF_PALETTEINDEXED4 or DDPF_PALETTEINDEXED8;
  645. begin
  646.   ddsd.dwSize := SizeOf(ddsd);
  647.   Result := DDSurface.Lock(nil, ddsd, DDLOCK_WAIT, 0)=DD_OK;
  648.   if Result then
  649.   begin
  650.     FillChar(Surface, SizeOf(Surface), 0);
  651.     if ddsd.ddpfPixelFormat.dwFlags and DDPF_PALETTEINDEXED<>0 then
  652.     begin
  653.       dxrMakeIndexedSurface(Surface, ddsd.dwWidth, ddsd.dwHeight, ddsd.ddpfPixelFormat.dwRGBBitCount,
  654.         ddsd.lpSurface, ddsd.lPitch, (1 shl ddsd.ddpfPixelFormat.dwRGBBitCount)-1, 0);
  655.     end else
  656.     begin
  657.       if ddsd.ddpfPixelFormat.dwFlags and DDPF_ALPHAPIXELS<>0 then
  658.       begin
  659.         dxrMakeRGBSurface(Surface, ddsd.dwWidth, ddsd.dwHeight, ddsd.ddpfPixelFormat.dwRGBBitCount,
  660.           ddsd.lpSurface, ddsd.lPitch, ddsd.ddpfPixelFormat.dwRBitMask, ddsd.ddpfPixelFormat.dwGBitMask,
  661.           ddsd.ddpfPixelFormat.dwBBitMask, ddsd.ddpfPixelFormat.dwRGBAlphaBitMask);
  662.       end else
  663.       begin
  664.         dxrMakeRGBSurface(Surface, ddsd.dwWidth, ddsd.dwHeight, ddsd.ddpfPixelFormat.dwRGBBitCount,
  665.           ddsd.lpSurface, ddsd.lPitch, ddsd.ddpfPixelFormat.dwRBitMask, ddsd.ddpfPixelFormat.dwGBitMask,
  666.           ddsd.ddpfPixelFormat.dwBBitMask, 0);
  667.       end;                          
  668.     end;
  669.   end;
  670. end;
  671.  
  672. procedure dxrDDSurfaceUnLock(DDSurface: {$IFDEF D3D_deprecated}IDirectDrawSurface{$ELSE}IDirectDrawSurface7{$ENDIF}; const Surface: TDXR_Surface);
  673. begin
  674.   DDSurface.Unlock(Surface.Bits);
  675. end;
  676.  
  677. function dxrScanLine(const Surface: TDXR_Surface; y: DWORD): Pointer;
  678. begin
  679.   Result := Pointer(Integer(Surface.Bits)+Surface.Pitch*Integer(y));
  680. end;
  681.  
  682. procedure dxrZBufferClear(const Surface: TDXR_Surface);
  683. var
  684.   i: Integer;
  685. begin
  686.   for i:=0 to Surface.Height-1 do
  687.     FillChar(dxrScanLine(Surface, i)^, Abs(Surface.Pitch), $FF);
  688. end;
  689.  
  690. {  TDXRMachine  }
  691.  
  692. constructor TDXRMachine.Create;
  693. begin
  694.   inherited Create;
  695.   FBuf := VirtualAlloc(nil, 2048, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
  696. end;
  697.  
  698. destructor TDXRMachine.Destroy;
  699. begin
  700.   VirtualFree(FBuf, 0, MEM_RELEASE);
  701.   inherited Destroy;
  702. end;
  703.  
  704. procedure TDXRMachine.Initialize;
  705. begin
  706.   FCall := nil;
  707.   ColorIndexCount := 0;
  708.   TextureIndexCount := 0;
  709.  
  710.   FTreeCount := 0;
  711.  
  712.   Dest := nil;
  713.   FCompiled := False;
  714.   FMMXUsed := False;
  715.  
  716.   FillChar(ColorList, SizeOf(ColorList), 0);
  717.   FillChar(TextureList, SizeOf(TextureList), 0);
  718.   FillChar(Dither, SizeOf(Dither), 0);
  719.   FillChar(ZBuffer, SizeOf(ZBuffer), 0);
  720.   FillChar(Axis, SizeOf(Axis), 0);
  721.   FillChar(RHW, SizeOf(RHW), 0);
  722. end;
  723.  
  724. function TDXRMachine.CreateTree: PDXRMachine_Tree;
  725. begin
  726.   Result := @FTreeList[FTreeCount];
  727.   FillChar(Result^, SizeOf(Result^), 0);
  728.   Inc(FTreeCount);
  729. end;
  730.  
  731. function TDXRMachine.CreateTree2(Typ: TDXRMachine_TreeType): PDXRMachine_Tree;
  732. begin
  733.   Result := CreateTree;
  734.   Result.Typ := Typ;
  735. end;
  736.  
  737. function TDXRMachine.CreateTree_LoadColor(Color: DWORD): PDXRMachine_Tree;
  738. begin
  739.   Result := CreateTree;
  740.   Result.Typ := DXR_TREETYPE_LOADCOLOR;
  741.   Result.Color := Color;
  742. end;
  743.  
  744. function TDXRMachine.CreateTree_LoadConstColor(R, G, B, A: Byte): PDXRMachine_Tree;
  745. begin
  746.   Result := CreateTree;
  747.   Result.Typ := DXR_TREETYPE_LOADCONSTCOLOR;
  748.   Result.ConstColor.R := R shl 8;
  749.   Result.ConstColor.G := G shl 8;
  750.   Result.ConstColor.B := B shl 8;
  751.   Result.ConstColor.A := A shl 8;
  752. end;
  753.  
  754. function TDXRMachine.CreateTree_LoadTexture(Texture: DWORD): PDXRMachine_Tree;
  755. begin
  756.   Result := CreateTree;
  757.   Result.Typ := DXR_TREETYPE_LOADTEXTURE;
  758.   Result.Texture := Texture;
  759. end;
  760.  
  761. function TDXRMachine.CreateTree_LoadBumpTexture(Texture, BumpTexture: DWORD): PDXRMachine_Tree;
  762. begin
  763.   Result := CreateTree;
  764.   Result.Typ := DXR_TREETYPE_LOADBUMPTEXTURE;
  765.   Result.Texture := Texture;
  766.   Result.BumpTexture := BumpTexture;
  767. end;
  768.  
  769. function TDXRMachine.CreateTree_Blend(Blend: TDXR_Blend; BlendTree1, BlendTree2: PDXRMachine_Tree): PDXRMachine_Tree;
  770. begin
  771.   Result := CreateTree;
  772.   Result.Typ := DXR_TREETYPE_BLEND;
  773.   Result.Blend := Blend;
  774.   Result.BlendTree1 := BlendTree1;
  775.   Result.BlendTree2 := BlendTree2;
  776. end;
  777.  
  778. procedure TDXRMachine.Compile;
  779.  
  780.   function GetSurfaceChannels(const Surface: TDXR_Surface): TDXRColorChannels;
  781.   begin
  782.     Result := [];
  783.  
  784.     if Surface.ColorType=DXR_COLORTYPE_INDEXED then
  785.     begin
  786.       if Surface.idx_index.Mask<>0 then Result := Result + [chRed, chGreen, chBlue];
  787.       if Surface.idx_alpha.Mask<>0 then Result := Result + [chAlpha];
  788.     end else
  789.     begin
  790.       if Surface.rgb_red.Mask<>0 then Result := Result + [chRed];
  791.       if Surface.rgb_green.Mask<>0 then Result := Result + [chGreen];
  792.       if Surface.rgb_blue.Mask<>0 then Result := Result + [chBlue];
  793.       if Surface.rgb_alpha.Mask<>0 then Result := Result + [chAlpha];
  794.     end;
  795.   end;
  796.  
  797.   procedure OptimizeTree(var Tree: PDXRMachine_Tree);
  798.  
  799.     procedure GetBlendChannels(Blend: TDXR_Blend; var Col1_1, Col1_2, Col2_1, Col2_2: TDXRColorChannels);
  800.     begin
  801.       case Blend of
  802.         DXR_BLEND_ZERO:
  803.           begin
  804.             Col1_1 := [];
  805.             Col1_2 := [];
  806.             Col2_1 := [];
  807.             Col2_2 := [];
  808.           end;
  809.         DXR_BLEND_ONE1:
  810.           begin
  811.             Col1_1 := [chRed, chGreen, chBlue, chAlpha];
  812.             Col1_2 := [];
  813.             Col2_1 := [];
  814.             Col2_2 := [];
  815.           end;
  816.         DXR_BLEND_ONE2:
  817.           begin
  818.             Col1_1 := [];
  819.             Col1_2 := [];
  820.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  821.             Col2_2 := [];
  822.           end;
  823.         DXR_BLEND_ONE1_ADD_ONE2, DXR_BLEND_ONE1_SUB_ONE2:
  824.           begin
  825.             Col1_1 := [chRed, chGreen, chBlue, chAlpha];
  826.             Col1_2 := [];
  827.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  828.             Col2_2 := [];
  829.           end;
  830.         DXR_BLEND_ONE2_SUB_ONE1, DXR_BLEND_ONE1_MUL_ONE2:
  831.           begin
  832.             Col1_1 := [chRed, chGreen, chBlue, chAlpha];
  833.             Col1_2 := [];
  834.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  835.             Col2_2 := [];
  836.           end;
  837.         DXR_BLEND_SRCALPHA1:
  838.           begin
  839.             Col1_1 := [chRed, chGreen, chBlue];
  840.             Col1_2 := [chAlpha];
  841.             Col2_1 := [];
  842.             Col2_2 := [];
  843.           end;
  844.         DXR_BLEND_SRCALPHA1_ADD_ONE2:
  845.           begin
  846.             Col1_1 := [chRed, chGreen, chBlue];
  847.             Col1_2 := [chAlpha];
  848.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  849.             Col2_2 := [];
  850.           end;
  851.         DXR_BLEND_ONE2_SUB_SRCALPHA1:
  852.           begin
  853.             Col1_1 := [chRed, chGreen, chBlue];
  854.             Col1_2 := [chAlpha];
  855.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  856.             Col2_2 := [];
  857.           end;
  858.         DXR_BLEND_SRCALPHA1_ADD_INVSRCALPHA2:
  859.           begin
  860.             Col1_1 := [chRed, chGreen, chBlue];
  861.             Col1_2 := [chAlpha];
  862.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  863.             Col2_2 := [];
  864.           end;
  865.         DXR_BLEND_INVSRCALPHA1_ADD_SRCALPHA2:
  866.           begin
  867.             Col1_1 := [chRed, chGreen, chBlue];
  868.             Col1_2 := [chAlpha];
  869.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  870.             Col2_2 := [];
  871.           end;
  872.  
  873.         DXR_BLEND_DECAL:
  874.           begin
  875.             Col1_1 := [chRed, chGreen, chBlue, chAlpha];
  876.             Col1_2 := [];
  877.             Col2_1 := [];
  878.             Col2_2 := [];
  879.           end;
  880.         DXR_BLEND_DECALALPHA:
  881.           begin
  882.             Col1_1 := [chRed, chGreen, chBlue];
  883.             Col1_2 := [];
  884.             Col2_1 := [];
  885.             Col2_2 := [chAlpha];
  886.           end;
  887.         DXR_BLEND_MODULATE:
  888.           begin
  889.             Col1_1 := [chRed, chGreen, chBlue, chAlpha];
  890.             Col1_2 := [];
  891.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  892.             Col2_2 := [];
  893.           end;
  894.         DXR_BLEND_MODULATEALPHA:
  895.           begin
  896.             Col1_1 := [chRed, chGreen, chBlue];
  897.             Col1_2 := [chAlpha];
  898.             Col2_1 := [chRed, chGreen, chBlue];
  899.             Col2_2 := [chAlpha];
  900.           end;
  901.         DXR_BLEND_ADD:
  902.           begin
  903.             Col1_1 := [chRed, chGreen, chBlue, chAlpha];
  904.             Col1_2 := [];
  905.             Col2_1 := [chRed, chGreen, chBlue, chAlpha];
  906.             Col2_2 := [];
  907.           end;
  908.       end;
  909.     end;
  910.  
  911.   var
  912.     c: TDXRColorChannels;
  913.     Col1_1, Col1_2, Col2_1, Col2_2: TDXRColorChannels;
  914.   begin
  915.     case Tree.Typ of
  916.       DXR_TREETYPE_LOADBLACK:
  917.           begin
  918.             // Load black color
  919.           end;
  920.       DXR_TREETYPE_LOADCOLOR:
  921.           begin
  922.             // Load color
  923.           end;
  924.       DXR_TREETYPE_LOADTEXTURE:
  925.           begin
  926.             // Load texel
  927.           end;
  928.       DXR_TREETYPE_LOADBUMPTEXTURE:
  929.           begin
  930.             // Load texel with Bump mapping
  931.           end;
  932.       DXR_TREETYPE_LOADDESTPIXEL:
  933.           begin
  934.             // Load dest pixel
  935.           end;
  936.       DXR_TREETYPE_BLEND:
  937.           begin
  938.             // Blend color
  939.             GetBlendChannels(Tree.Blend, Col1_1, Col1_2, Col2_1, Col2_2);
  940.  
  941.             Tree.BlendTree1.Channels := Tree.Channels*Col1_1+Col1_2;
  942.             Tree.BlendTree2.Channels := Tree.Channels*Col2_1+Col2_2;
  943.  
  944.             OptimizeTree(Tree.BlendTree1);
  945.             OptimizeTree(Tree.BlendTree2);
  946.  
  947.             if (Tree.Blend=DXR_BLEND_ZERO) then
  948.             begin
  949.               c := Tree.Channels; Tree^.Typ := DXR_TREETYPE_LOADBLACK; Tree.Channels := c;
  950.             end else
  951.             if (Tree.Blend in [DXR_BLEND_ONE1, DXR_BLEND_DECAL]) then
  952.             begin
  953.               c := Tree.Channels; Tree := Tree.BlendTree1; Tree.Channels := c;
  954.             end else
  955.             if (Tree.Blend=DXR_BLEND_ONE2) then
  956.             begin
  957.               c := Tree.Channels; Tree := Tree.BlendTree2; Tree.Channels := c;
  958.             end else
  959.             if (Tree.Blend in [DXR_BLEND_ONE1_ADD_ONE2, DXR_BLEND_ONE2_SUB_ONE1]) and
  960.               (Tree.BlendTree2.Typ=DXR_TREETYPE_LOADBLACK) then
  961.             begin
  962.               c := Tree.Channels; Tree := Tree.BlendTree1; Tree.Channels := c;
  963.             end else
  964.             if (Tree.Blend in [DXR_BLEND_ONE1_ADD_ONE2, DXR_BLEND_ONE2_SUB_ONE1]) and
  965.               (Tree.BlendTree1.Typ=DXR_TREETYPE_LOADBLACK) then
  966.             begin
  967.               c := Tree.Channels; Tree := Tree.BlendTree2; Tree.Channels := c;
  968.             end else
  969.             begin
  970.               if (Col1_1=[]) and (Col1_2=[]) then Tree.BlendTree1 := nil;
  971.               if (Col2_1=[]) and (Col2_2=[]) then Tree.BlendTree2 := nil;
  972.             end;
  973.           end;
  974.     end;
  975.   end;
  976.  
  977.   procedure GetEnableChannels(Tree: PDXRMachine_Tree);
  978.   begin
  979.     case Tree.Typ of
  980.       DXR_TREETYPE_LOADBLACK:
  981.           begin
  982.             // Load black color
  983.           end;
  984.       DXR_TREETYPE_LOADCOLOR:
  985.           begin
  986.             // Load color
  987.             ColorList[Tree.Color].Channels := ColorList[Tree.Color].Channels + Tree.Channels;
  988.             ColorList[Tree.Color].Enable := ColorList[Tree.Color].Channels<>[];
  989.           end;
  990.       DXR_TREETYPE_LOADTEXTURE:
  991.           begin
  992.             // Load texel
  993.             TextureList[Tree.Texture].EnableChannels := TextureList[Tree.Texture].EnableChannels +
  994.               Tree.Channels*GetSurfaceChannels(TextureList[Tree.Texture].Surface^);
  995.             TextureList[Tree.Texture].Enable := TextureList[Tree.Texture].EnableChannels<>[];
  996.           end;
  997.       DXR_TREETYPE_LOADBUMPTEXTURE:
  998.           begin
  999.             // Load texel with Bump mapping
  1000.             TextureList[Tree.Texture].EnableChannels := TextureList[Tree.Texture].EnableChannels +
  1001.               Tree.Channels*GetSurfaceChannels(TextureList[Tree.Texture].Surface^);
  1002.             TextureList[Tree.Texture].Enable := TextureList[Tree.Texture].EnableChannels<>[];
  1003.             TextureList[Tree.BumpTexture].Enable := True;
  1004.           end;
  1005.       DXR_TREETYPE_LOADDESTPIXEL:
  1006.           begin
  1007.             // Load dest pixel
  1008.           end;
  1009.       DXR_TREETYPE_BLEND:
  1010.           begin
  1011.             // Blend color
  1012.             if Tree.BlendTree1<>nil then GetEnableChannels(Tree.BlendTree1);
  1013.             if Tree.BlendTree2<>nil then GetEnableChannels(Tree.BlendTree2);
  1014.           end;
  1015.     end;
  1016.   end;
  1017.  
  1018. var
  1019.   Code: Pointer;
  1020.   i: Integer;
  1021. begin
  1022.   {  Optimize tree  }
  1023.   Tree.Channels := GetSurfaceChannels(Dest^);
  1024.   OptimizeTree(Tree);
  1025.  
  1026.   {  Get enable channels  }
  1027.   GetEnableChannels(Tree);
  1028.  
  1029.   for i:=Low(ColorList) to High(ColorList) do
  1030.     if ColorList[i].Enable then
  1031.     begin
  1032.       ColorIndex[ColorIndexCount] := i;
  1033.       Inc(ColorIndexCount);
  1034.     end;
  1035.  
  1036.   for i:=Low(TextureList) to High(TextureList) do
  1037.     if TextureList[i].Enable then
  1038.     begin
  1039.       TextureIndex[TextureIndexCount] := i;
  1040.       Inc(TextureIndexCount);
  1041.     end;
  1042.  
  1043.   ZBuffer.Enable := ZBuffer.Surface<>nil;
  1044.  
  1045.   RHW.Enable := ZBuffer.Enable;
  1046.   Axis.IncEnable := Dither.Enable;
  1047.  
  1048.   {  Generate X86 code  }
  1049.   Code := FBuf; GenerateCode(Code, Tree);
  1050.  
  1051.   FCompiled := True;
  1052. end;
  1053.  
  1054. const
  1055.   Mask1: array[0..7] of DWORD= ($80, $40, $20, $10, $08, $04, $02, $01);
  1056.   Mask2: array[0..3] of DWORD= ($C0, $30, $0C, $03);
  1057.   Mask4: array[0..1] of DWORD= ($F0, $0F);
  1058.  
  1059.   Shift1: array[0..7] of DWORD= (7, 6, 5, 4, 3, 2, 1, 0);
  1060.   Shift2: array[0..3] of DWORD= (6, 4, 2, 0);
  1061.   Shift4: array[0..1] of DWORD= (4, 0);
  1062.  
  1063. var
  1064.   _null: Byte;
  1065.  
  1066.   // Saturation addition table
  1067.   //   Result := Min(n+j, 255)
  1068.   _AddTable: array[0..256*2-1] of Byte;
  1069.   _SubTable: array[-255..255] of Byte;
  1070.  
  1071.   // Byte to QWORD convert table
  1072.   //   Result := (n shl 56)+(n shl 48)+(n shl 32)+(n shl 24)+(n shl 16)+(n shl 8)+n
  1073.   _ByteToQWORDTable: array[0..255, 0..3] of WORD;
  1074.  
  1075.   _BlackColor: TDXRMachine_Color = (R: 0; G: 0; B: 0; A: 0);
  1076.  
  1077. procedure Init;
  1078. var
  1079.   i: Integer;
  1080. begin
  1081.   for i:=Low(_AddTable) to High(_AddTable) do
  1082.   begin
  1083.     if i>255 then
  1084.       _AddTable[i] := 255
  1085.     else
  1086.       _AddTable[i] := i;
  1087.   end;
  1088.  
  1089.   for i:=Low(_SubTable) to High(_SubTable) do
  1090.   begin
  1091.     if i<0 then
  1092.       _SubTable[i] := 0
  1093.     else
  1094.       _SubTable[i] := i;
  1095.   end;
  1096.  
  1097.   for i:=0 to 255 do
  1098.   begin
  1099.     _ByteToQWORDTable[i, 0] := i;
  1100.     _ByteToQWORDTable[i, 1] := i;
  1101.     _ByteToQWORDTable[i, 2] := i;
  1102.     _ByteToQWORDTable[i, 3] := i;
  1103.   end;
  1104. end;
  1105.  
  1106. procedure TDXRMachine.GenerateCode(var Code: Pointer; Tree: PDXRMachine_Tree);
  1107. var
  1108.   SkipAddress: Pointer;
  1109.  
  1110.   procedure genCmpFunc(var Code: Pointer; Func: TDXR_CmpFunc; JmpAdress: Pointer);
  1111.  
  1112.     procedure genShortJmp(var Code: Pointer; JmpCode: Pointer; sC: Byte);
  1113.     type
  1114.       PShortJmp = ^TShortJmp;
  1115.       TShortJmp = packed record
  1116.         c: Byte;
  1117.         A: ShortInt;
  1118.       end;
  1119.     begin
  1120.       with PShortJmp(Code)^ do
  1121.       begin
  1122.         c := sC;
  1123.         A := Integer(JmpCode)-(Integer(Code)+2);
  1124.       end;
  1125.       Inc(Integer(Code), 2);
  1126.     end;
  1127.  
  1128.     procedure genNearJmp(var Code: Pointer; JmpCode: Pointer; nC: Byte);
  1129.     type
  1130.       PNearJmp = ^TNearJmp;
  1131.       TNearJmp = packed record
  1132.         c: Byte;
  1133.         A: Integer;
  1134.       end;
  1135.     begin
  1136.       with PNearJmp(Code)^ do
  1137.       begin
  1138.         c := nC;
  1139.         A := Integer(JmpCode)-(Integer(Code)+5);
  1140.       end;
  1141.       Inc(Integer(Code), 5);
  1142.     end;
  1143.  
  1144.     procedure genNearJmp2(var Code: Pointer; JmpCode: Pointer; nC1, nC2: Byte);
  1145.     type
  1146.       PNearJmp2 = ^TNearJmp2;
  1147.       TNearJmp2 = packed record
  1148.         c1, c2: Byte;
  1149.         A: Integer;
  1150.       end;
  1151.     begin
  1152.       with PNearJmp2(Code)^ do
  1153.       begin
  1154.         c1 := nC1;
  1155.         c2 := nC2;
  1156.         A := Integer(JmpCode)-(Integer(Code)+6);
  1157.       end;
  1158.       Inc(Integer(Code), 6);
  1159.     end;
  1160.  
  1161.     procedure genFlagJmp(var Code: Pointer; JmpCode: Pointer; sC, nC1, nC2: Byte);
  1162.     var
  1163.       i: Integer;
  1164.     begin
  1165.       i := Integer(JmpCode)-(Integer(Code)+2);
  1166.       if abs(i)<128 then
  1167.         genShortJmp(Code, JmpCode, sC)
  1168.       else
  1169.         genNearJmp2(Code, JmpCode, nC1, nC2);
  1170.     end;
  1171.  
  1172.     procedure genJmp(var Code: Pointer; JmpCode: Pointer);
  1173.     var
  1174.       i: Integer;
  1175.     begin
  1176.       i := Integer(JmpCode)-(Integer(Code)+2);
  1177.       if abs(i)<128 then
  1178.         genShortJmp(Code, JmpCode, $EB)
  1179.       else
  1180.         genNearJmp(Code, JmpCode, $E9);
  1181.     end;
  1182.  
  1183.   begin
  1184.     case Func of
  1185.       DXR_CMPFUNC_NEVER:
  1186.           begin
  1187.             {  if (False) then Jump }
  1188.           end;
  1189.       DXR_CMPFUNC_LESS:
  1190.           begin
  1191.             {  if (New<Old) then Jump  }
  1192.             genFlagJmp(Code, JmpAdress, $7C, $0F, $8C);
  1193.           end;
  1194.       DXR_CMPFUNC_EQUAL:
  1195.           begin
  1196.             {  if (New=Old) then Jump  }
  1197.             genFlagJmp(Code, JmpAdress, $74, $0F, $84);
  1198.           end;
  1199.       DXR_CMPFUNC_LESSEQUAL:
  1200.           begin
  1201.             {  if (New<=Old) then Jump  }
  1202.             genFlagJmp(Code, JmpAdress, $7E, $0F, $8E);
  1203.           end;
  1204.       DXR_CMPFUNC_GREATER:
  1205.           begin
  1206.             {  if (New>Old) then Jump  }
  1207.             genFlagJmp(Code, JmpAdress, $7F, $0F, $8F);
  1208.           end;
  1209.       DXR_CMPFUNC_NOTEQUAL:
  1210.           begin
  1211.             {  if (New<>Old) then Jump  }
  1212.             genFlagJmp(Code, JmpAdress, $75, $0F, $85);
  1213.           end;
  1214.       DXR_CMPFUNC_GREATEREQUAL:
  1215.           begin
  1216.             {  if (New>=Old) then Jump  }
  1217.             genFlagJmp(Code, JmpAdress, $7D, $0F, $8D);
  1218.           end;
  1219.       DXR_CMPFUNC_ALWAYS:
  1220.           begin
  1221.             {  if (True) then Break }
  1222.             genJmp(Code, JmpAdress);
  1223.           end;
  1224.     end;
  1225.   end;
  1226.  
  1227.   procedure genInitDestAddress(var Code: Pointer);
  1228.   var
  1229.     _Axis: Pointer;
  1230.     ByteCount, Pitch: DWORD;
  1231.     Bits: Pointer;
  1232.   begin
  1233.     _Axis := @Axis.Axis;
  1234.  
  1235.     ByteCount := Dest.BitCount shr 3;
  1236.     Pitch := Dest.pitch;
  1237.     Bits := Dest.Bits;
  1238.  
  1239.     asm
  1240.       jmp @@EndCode
  1241.     @@StartCode:
  1242.       mov eax,dword ptr [offset _null]{}@@AxisX:
  1243.       imul eax,$11{}        @@ByteCount: // Dest.BitCount div 8
  1244.       mov edi,dword ptr [offset _null]{}@@AxisY:
  1245.       imul edi,$11111111{}  @@Pitch: // Dest.pitch
  1246.       add edi,$11111111{}   @@Bits:  // Dest.Bits
  1247.       add edi,eax
  1248.     @@EndCode:
  1249.       {$I DXRender.inc}
  1250.       {  @@AxisX  }
  1251.       mov eax,_Axis; add eax,TDXRMachine_Axis.X
  1252.       mov edx,offset @@AxisX-4
  1253.       sub edx,offset @@StartCode
  1254.       mov dword ptr [ecx+edx],eax
  1255.  
  1256.       {  @@AxisY  }
  1257.       mov eax,_Axis; add eax,TDXRMachine_Axis.Y
  1258.       mov edx,offset @@AxisY-4
  1259.       sub edx,offset @@StartCode
  1260.       mov dword ptr [ecx+edx],eax
  1261.  
  1262.       {  @@ByteCount  }
  1263.       mov eax,ByteCount
  1264.       mov edx,offset @@ByteCount-1
  1265.       sub edx,offset @@StartCode
  1266.       mov byte ptr [ecx+edx],al
  1267.  
  1268.       {  @@Pitch  }
  1269.       mov eax,Pitch
  1270.       mov edx,offset @@Pitch-4
  1271.       sub edx,offset @@StartCode
  1272.       mov dword ptr [ecx+edx],eax
  1273.  
  1274.       {  @@Bits  }
  1275.       mov eax,Bits
  1276.       mov edx,offset @@Bits-4
  1277.       sub edx,offset @@StartCode
  1278.       mov dword ptr [ecx+edx],eax
  1279.     end;
  1280.   end;
  1281.  
  1282.   procedure genInitZBuffer(var Code: Pointer);
  1283.   var
  1284.     _Axis: Pointer;
  1285.     ByteCount, Pitch: DWORD;
  1286.     Bits, _ZBuf: Pointer;
  1287.   begin
  1288.     if not ZBuffer.Enable then Exit;
  1289.  
  1290.     _Axis := @Axis.Axis;
  1291.  
  1292.     ByteCount := ZBuffer.Surface.BitCount div 8;
  1293.     Pitch := ZBuffer.Surface.Pitch;
  1294.     Bits := ZBuffer.Surface.Bits;
  1295.  
  1296.     _ZBuf := @F_ZBuf;
  1297.  
  1298.     asm
  1299.       jmp @@EndCode
  1300.     @@StartCode:
  1301.       mov edx,dword ptr [offset _null]{}@@AxisX:
  1302.       imul edx,$11{}        @@ByteCount: // States.ZBuffer.BitCount div 8
  1303.       mov eax,dword ptr [offset _null]{}@@AxisY:
  1304.       imul eax,$11111111{}  @@Pitch: // States.ZBuffer.pitch
  1305.       add eax,$11111111{}   @@Bits:  // States.ZBuffer.Bits
  1306.       add eax,edx
  1307.       mov dword ptr [offset _null],eax{}@@_ZBuf:
  1308.     @@EndCode:
  1309.       {$I DXRender.inc}
  1310.       {  @@AxisX  }
  1311.       mov eax,_Axis; add eax,TDXRMachine_Axis.X
  1312.       mov edx,offset @@AxisX-4
  1313.       sub edx,offset @@StartCode
  1314.       mov dword ptr [ecx+edx],eax
  1315.  
  1316.       {  @@AxisY  }
  1317.       mov eax,_Axis; add eax,TDXRMachine_Axis.Y
  1318.       mov edx,offset @@AxisY-4
  1319.       sub edx,offset @@StartCode
  1320.       mov dword ptr [ecx+edx],eax
  1321.  
  1322.       {  @@ByteCount  }
  1323.       mov eax,ByteCount
  1324.       mov edx,offset @@ByteCount-1
  1325.       sub edx,offset @@StartCode
  1326.       mov byte ptr [ecx+edx],al
  1327.  
  1328.       {  @@Pitch  }
  1329.       mov eax,Pitch
  1330.       mov edx,offset @@Pitch-4
  1331.       sub edx,offset @@StartCode
  1332.       mov dword ptr [ecx+edx],eax
  1333.  
  1334.       {  @@Bits  }
  1335.       mov eax,Bits
  1336.       mov edx,offset @@Bits-4
  1337.       sub edx,offset @@StartCode
  1338.       mov dword ptr [ecx+edx],eax
  1339.  
  1340.       {  @@_ZBuf  }
  1341.       mov eax,_ZBuf
  1342.       mov edx,offset @@_ZBuf-4
  1343.       sub edx,offset @@StartCode
  1344.       mov dword ptr [ecx+edx],eax
  1345.     end;
  1346.   end;
  1347.  
  1348.   procedure genZBufferTest(var Code: Pointer);
  1349.   var
  1350.     _ZBuf, _RHW: Pointer;
  1351.   begin
  1352.     if not ZBuffer.Enable then Exit;
  1353.  
  1354.     _ZBuf := @F_ZBuf;
  1355.     _RHW := @RHW.nRHW;
  1356.  
  1357.     asm
  1358.       jmp @@EndCode
  1359.     @@StartCode:
  1360.       mov edx,dword ptr [offset _null]{}@@_ZBuf:
  1361.       mov ebx,dword ptr [offset _null]{}@@_RHW:
  1362.     @@EndCode:
  1363.       {$I DXRender.inc}
  1364.       {  @@_ZBuf  }
  1365.       mov eax,_ZBuf
  1366.       mov edx,offset @@_ZBuf-4
  1367.       sub edx,offset @@StartCode
  1368.       mov dword ptr [ecx+edx],eax
  1369.  
  1370.       {  @@_RHW  }
  1371.       mov eax,_RHW; add eax,4
  1372.       mov edx,offset @@_RHW-4
  1373.       sub edx,offset @@StartCode
  1374.       mov dword ptr [ecx+edx],eax
  1375.     end;
  1376.  
  1377.     if ZBuffer.CmpFunc<>DXR_CMPFUNC_ALWAYS then
  1378.     begin
  1379.       case ZBuffer.Surface.BitCount of
  1380.         8: begin
  1381.              asm
  1382.                jmp @@EndCode
  1383.              @@StartCode:
  1384.                movzx eax,byte ptr [edx]
  1385.              @@EndCode:
  1386.                {$I DXRender.inc}
  1387.              end;
  1388.            end;
  1389.        16: begin
  1390.              asm
  1391.                jmp @@EndCode
  1392.              @@StartCode:
  1393.                movzx eax,word ptr [edx]
  1394.              @@EndCode:
  1395.                {$I DXRender.inc}
  1396.              end;
  1397.            end;
  1398.        24: begin
  1399.              asm
  1400.                jmp @@EndCode
  1401.              @@StartCode:
  1402.                movzx ax,byte ptr [edx+2]
  1403.                shl eax,16
  1404.                mov ax,word ptr [edx]
  1405.              @@EndCode:
  1406.                {$I DXRender.inc}
  1407.              end;
  1408.            end;
  1409.        32: begin
  1410.              asm
  1411.                jmp @@EndCode
  1412.              @@StartCode:
  1413.                mov eax,dword ptr [edx]
  1414.              @@EndCode:
  1415.                {$I DXRender.inc}
  1416.              end;
  1417.            end;
  1418.       end;
  1419.  
  1420.       asm
  1421.         jmp @@EndCode
  1422.       @@StartCode:
  1423.         cmp eax,ebx
  1424.       @@EndCode:
  1425.         {$I DXRender.inc}
  1426.       end;
  1427.       genCmpFunc(Code, ZBuffer.CmpFunc, SkipAddress);
  1428.     end;
  1429.  
  1430.     if ZBuffer.WriteEnable then
  1431.     begin
  1432.       case ZBuffer.Surface.BitCount of
  1433.         8: begin
  1434.              asm
  1435.                jmp @@EndCode
  1436.              @@StartCode:
  1437.                mov byte ptr [edx],bl
  1438.              @@EndCode:
  1439.                {$I DXRender.inc}
  1440.              end;
  1441.            end;
  1442.        16: begin
  1443.              asm
  1444.                jmp @@EndCode
  1445.              @@StartCode:
  1446.                mov word ptr [edx],bx
  1447.              @@EndCode:
  1448.                {$I DXRender.inc}
  1449.              end;
  1450.            end;
  1451.        24: begin
  1452.              asm
  1453.                jmp @@EndCode
  1454.              @@StartCode:
  1455.                mov word ptr [edx],bx
  1456.                bswap ebx
  1457.                mov byte ptr [edx+2],bh
  1458.              @@EndCode:
  1459.                {$I DXRender.inc}
  1460.              end;
  1461.            end;
  1462.        32: begin
  1463.              asm
  1464.                jmp @@EndCode
  1465.              @@StartCode:
  1466.                mov dword ptr [edx],ebx
  1467.              @@EndCode:
  1468.                {$I DXRender.inc}
  1469.              end;
  1470.            end;
  1471.       end;
  1472.     end;
  1473.   end;
  1474.  
  1475.   procedure genUpdateZBufferAddress(var Code: Pointer);
  1476.   var
  1477.     ByteCount: DWORD;
  1478.     _ZBuf: Pointer;
  1479.   begin
  1480.     if not ZBuffer.Enable then Exit;
  1481.  
  1482.     ByteCount := ZBuffer.Surface.BitCount shr 3;
  1483.  
  1484.     _ZBuf := @F_ZBuf;
  1485.  
  1486.     asm
  1487.       jmp @@EndCode
  1488.     @@StartCode:
  1489.       add dword ptr [offset _null],$11{}@@_ZBuf:
  1490.     @@EndCode:
  1491.       {$I DXRender.inc}
  1492.       {  @@_ZBuf  }
  1493.       mov eax,ByteCount
  1494.       mov edx,offset @@_ZBuf-1
  1495.       sub edx,offset @@StartCode
  1496.       mov byte ptr [ecx+edx],al
  1497.  
  1498.       {  @@_ZBuf  }
  1499.       mov eax,_ZBuf
  1500.       mov edx,offset @@_ZBuf-5
  1501.       sub edx,offset @@StartCode
  1502.       mov dword ptr [ecx+edx],eax
  1503.     end;
  1504.   end;
  1505.  
  1506.   procedure genReadDestPixel(var Code: Pointer);
  1507.   begin
  1508.     case Dest.BitCount of
  1509.       8: begin
  1510.            asm
  1511.              jmp @@EndCode
  1512.            @@StartCode:
  1513.              movzx eax,byte ptr [edi]
  1514.            @@EndCode:
  1515.              {$I DXRender.inc}
  1516.            end;
  1517.          end;
  1518.      16: begin
  1519.            asm
  1520.              jmp @@EndCode
  1521.            @@StartCode:
  1522.              movzx eax,word ptr [edi]
  1523.            @@EndCode:
  1524.              {$I DXRender.inc}
  1525.            end;
  1526.          end;
  1527.      24: begin
  1528.            asm
  1529.              jmp @@EndCode
  1530.            @@StartCode:
  1531.              movzx eax,byte ptr [edi+2]
  1532.              shl eax,16
  1533.              mov ax,word ptr [edi]
  1534.            @@EndCode:
  1535.              {$I DXRender.inc}
  1536.            end;
  1537.          end;
  1538.      32: begin
  1539.            asm
  1540.              jmp @@EndCode
  1541.            @@StartCode:
  1542.              mov eax,dword ptr [edi]
  1543.            @@EndCode:
  1544.              {$I DXRender.inc}
  1545.            end;
  1546.          end;
  1547.     end;
  1548.   end;
  1549.  
  1550.   procedure genWriteDestPixel(var Code: Pointer);
  1551.   begin
  1552.     case Dest.BitCount of
  1553.       8: begin
  1554.            asm
  1555.              jmp @@EndCode
  1556.            @@StartCode:
  1557.              mov byte ptr [edi],al
  1558.            @@EndCode:
  1559.              {$I DXRender.inc}
  1560.            end;
  1561.          end;
  1562.      16: begin
  1563.            asm
  1564.              jmp @@EndCode
  1565.            @@StartCode:
  1566.              mov word ptr [edi],ax
  1567.            @@EndCode:
  1568.              {$I DXRender.inc}
  1569.            end;
  1570.          end;
  1571.      24: begin
  1572.            asm
  1573.              jmp @@EndCode
  1574.            @@StartCode:
  1575.              mov word ptr [edi],ax
  1576.              bswap eax
  1577.              mov byte ptr [edi+2],ah
  1578.            @@EndCode:
  1579.              {$I DXRender.inc}
  1580.            end;
  1581.          end;
  1582.      32: begin
  1583.            asm
  1584.              jmp @@EndCode
  1585.            @@StartCode:
  1586.              mov dword ptr [edi],eax
  1587.            @@EndCode:
  1588.              {$I DXRender.inc}
  1589.            end;
  1590.          end;
  1591.     end;
  1592.   end;
  1593.  
  1594.   procedure genUpdateDestAddress(var Code: Pointer);
  1595.   var
  1596.     ByteCount: DWORD;
  1597.   begin
  1598.     ByteCount := Dest.BitCount shr 3;
  1599.  
  1600.     if ByteCount=1 then
  1601.     begin
  1602.       asm
  1603.         jmp @@EndCode
  1604.       @@StartCode:
  1605.         inc edi
  1606.       @@EndCode:
  1607.         {$I DXRender.inc}
  1608.       end;
  1609.     end else
  1610.     begin
  1611.       asm
  1612.         jmp @@EndCode
  1613.       @@StartCode:
  1614.         add edi,$11{}@@ByteCount:    // Dest.BitCount div 8;
  1615.       @@EndCode:
  1616.         {$I DXRender.inc}
  1617.         {  @@ByteCount  }
  1618.         mov eax,ByteCount
  1619.         mov edx,offset @@ByteCount-1
  1620.         sub edx,offset @@StartCode
  1621.         mov byte ptr [ecx+edx],al
  1622.       end;
  1623.     end;
  1624.   end;
  1625.  
  1626.   procedure genReadSurfacePixel_Tile(var Code: Pointer; const Source: TDXR_Surface; Axis: PDXRMachine_Axis);
  1627.   begin
  1628.     case Source.BitCount of
  1629.       1: begin
  1630.            asm
  1631.              jmp @@EndCode
  1632.            @@StartCode:
  1633.              mov esi,dword ptr [offset _null]{}//TexY
  1634.                                  @@TexY:
  1635.              shr esi,16
  1636.              and esi,$11111111{} @@MaskY:   // Source.HeightMask
  1637.              imul esi,$11111111{}@@Pitch:   // Source.pitch
  1638.              mov edx,dword ptr [offset _null]{}//TexX
  1639.                                  @@TexX:
  1640.              shr edx,16
  1641.              and edx,$11111111{} @@MaskX:   // Source.WidthMask
  1642.              mov ebx,edx
  1643.              shr edx,3
  1644.              and ebx,7
  1645.              movzx eax,byte ptr [esi+edx+$11111111]
  1646.                                  @@Bits:   // Source.Bits
  1647.              and eax,dword ptr [offset Mask1+ebx*4]
  1648.              push ecx
  1649.              mov ecx,dword ptr [offset Shift1+ebx*4]
  1650.              shr eax,cl
  1651.              pop ecx
  1652.            @@EndCode:
  1653.              {$I DXRender.inc}
  1654.              {  @@TexX  }
  1655.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  1656.              mov edx,offset @@TexX-4
  1657.              sub edx,offset @@StartCode
  1658.              mov dword ptr [ecx+edx],eax
  1659.  
  1660.              {  @@TexY  }
  1661.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  1662.              mov edx,offset @@TexY-4
  1663.              sub edx,offset @@StartCode
  1664.              mov dword ptr [ecx+edx],eax
  1665.  
  1666.              {  @@MaskY  }
  1667.              mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  1668.              mov edx,offset @@MaskY-4
  1669.              sub edx,offset @@StartCode
  1670.              mov dword ptr [ecx+edx],eax
  1671.  
  1672.              {  @@Pitch  }
  1673.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  1674.              mov edx,offset @@Pitch-4
  1675.              sub edx,offset @@StartCode
  1676.              mov dword ptr [ecx+edx],eax
  1677.  
  1678.              {  @@MaskX  }
  1679.              mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  1680.              mov edx,offset @@MaskX-4
  1681.              sub edx,offset @@StartCode
  1682.              mov dword ptr [ecx+edx],eax
  1683.  
  1684.              {  @@Bits  }
  1685.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  1686.              mov edx,offset @@Bits-4
  1687.              sub edx,offset @@StartCode
  1688.              mov dword ptr [ecx+edx],eax
  1689.            end;
  1690.          end;
  1691.       2: begin
  1692.            asm
  1693.              jmp @@EndCode
  1694.            @@StartCode:
  1695.              mov esi,dword ptr [offset _null]{}//TexY
  1696.                                  @@TexY:
  1697.              shr esi,16
  1698.              and esi,$11111111{} @@MaskY:  // Source.HeightMask
  1699.              imul esi,$11111111{}@@Pitch:  // Source.pitch
  1700.              mov edx,dword ptr [offset _null]{}//TexX
  1701.                                  @@TexX:
  1702.              shr edx,16
  1703.              and edx,$11111111{} @@MaskX:  // Source.WidthMask
  1704.              mov ebx,edx
  1705.              shr edx,2
  1706.              and ebx,3
  1707.              movzx eax,byte ptr [esi+edx+$11111111]
  1708.                                  @@Bits:   // Source.Bits
  1709.              and eax,dword ptr [offset Mask2+ebx*4]
  1710.              push ecx
  1711.              mov ecx,dword ptr [offset Shift2+ebx*4]
  1712.              shr eax,cl
  1713.              pop ecx
  1714.            @@EndCode:
  1715.              {$I DXRender.inc}
  1716.              {  @@TexX  }
  1717.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  1718.              mov edx,offset @@TexX-4
  1719.              sub edx,offset @@StartCode
  1720.              mov dword ptr [ecx+edx],eax
  1721.  
  1722.              {  @@TexY  }
  1723.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  1724.              mov edx,offset @@TexY-4
  1725.              sub edx,offset @@StartCode
  1726.              mov dword ptr [ecx+edx],eax
  1727.  
  1728.              {  @@MaskY  }
  1729.              mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  1730.              mov edx,offset @@MaskY-4
  1731.              sub edx,offset @@StartCode
  1732.              mov dword ptr [ecx+edx],eax
  1733.  
  1734.              {  @@Pitch  }
  1735.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  1736.              mov edx,offset @@Pitch-4
  1737.              sub edx,offset @@StartCode
  1738.              mov dword ptr [ecx+edx],eax
  1739.  
  1740.              {  @@MaskX  }
  1741.              mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  1742.              mov edx,offset @@MaskX-4
  1743.              sub edx,offset @@StartCode
  1744.              mov dword ptr [ecx+edx],eax
  1745.              {  @@Bits  }
  1746.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  1747.              mov edx,offset @@Bits-4
  1748.              sub edx,offset @@StartCode
  1749.              mov dword ptr [ecx+edx],eax
  1750.            end;
  1751.          end;
  1752.       4: begin
  1753.            asm
  1754.              jmp @@EndCode
  1755.            @@StartCode:
  1756.              mov esi,dword ptr [offset _null]{}//TexY
  1757.                                  @@TexY:
  1758.              shr esi,16
  1759.              and esi,$11111111{} @@MaskY:  // Source.HeightMask
  1760.              imul esi,$11111111{}@@Pitch:  // Source.pitch
  1761.              mov edx,dword ptr [offset _null]{}//TexX
  1762.                                  @@TexX:
  1763.              shr edx,16
  1764.              and edx,$11111111{} @@MaskX:  // Source.WidthMask
  1765.              mov ebx,edx
  1766.              shr edx,1
  1767.              and ebx,1
  1768.              movzx eax,byte ptr [esi+edx+$11111111]
  1769.                                  @@Bits:   // Source.Bits
  1770.              and eax,dword ptr [offset Mask4+ebx*4]
  1771.              push ecx
  1772.              mov ecx,dword ptr [offset Shift4+ebx*4]
  1773.              shr eax,cl
  1774.              pop ecx
  1775.            @@EndCode:
  1776.              {$I DXRender.inc}
  1777.              {  @@TexX  }
  1778.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  1779.              mov edx,offset @@TexX-4
  1780.              sub edx,offset @@StartCode
  1781.              mov dword ptr [ecx+edx],eax
  1782.  
  1783.              {  @@TexY  }
  1784.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  1785.              mov edx,offset @@TexY-4
  1786.              sub edx,offset @@StartCode
  1787.              mov dword ptr [ecx+edx],eax
  1788.  
  1789.              {  @@MaskY  }
  1790.              mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  1791.              mov edx,offset @@MaskY-4
  1792.              sub edx,offset @@StartCode
  1793.              mov dword ptr [ecx+edx],eax
  1794.  
  1795.              {  @@Pitch  }
  1796.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  1797.              mov edx,offset @@Pitch-4
  1798.              sub edx,offset @@StartCode
  1799.              mov dword ptr [ecx+edx],eax
  1800.  
  1801.              {  @@MaskX  }
  1802.              mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  1803.              mov edx,offset @@MaskX-4
  1804.              sub edx,offset @@StartCode
  1805.              mov dword ptr [ecx+edx],eax
  1806.  
  1807.              {  @@Bits  }
  1808.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  1809.              mov edx,offset @@Bits-4
  1810.              sub edx,offset @@StartCode
  1811.              mov dword ptr [ecx+edx],eax
  1812.            end;
  1813.          end;
  1814.       8: begin
  1815.            if Source.pitch=(1 shl Source.PitchBit) then
  1816.            begin
  1817.              asm
  1818.                jmp @@EndCode
  1819.              @@StartCode:
  1820.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  1821.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  1822.                shr esi,$11{}       @@YShift: // 16-Source.PitchBit
  1823.                shr edx,16
  1824.                and esi,$11111111{} @@MaskY:  // Source.HeightMask shl Source.PitchBit
  1825.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  1826.                movzx eax,byte ptr [$11111111+esi+edx]
  1827.                                    @@Bits:   // Source.Bits
  1828.              @@EndCode:
  1829.                {$I DXRender.inc}
  1830.                {  @@TexX  }
  1831.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  1832.                mov edx,offset @@TexX-4
  1833.                sub edx,offset @@StartCode
  1834.                mov dword ptr [ecx+edx],eax
  1835.  
  1836.                {  @@TexY  }
  1837.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  1838.                mov edx,offset @@TexY-4
  1839.                sub edx,offset @@StartCode
  1840.                mov dword ptr [ecx+edx],eax
  1841.  
  1842.                {  @@YShift  }
  1843.                push ebx
  1844.                mov eax,16
  1845.                mov ebx,Source; sub eax,[ebx + TDXR_Surface.PitchBit]
  1846.                pop ebx
  1847.                mov edx,offset @@YShift-1
  1848.                sub edx,offset @@StartCode
  1849.                mov byte ptr [ecx+edx],al
  1850.  
  1851.                {  @@MaskY  }
  1852.                push ecx
  1853.                mov ecx,Source; mov ecx,[ecx + TDXR_Surface.PitchBit]
  1854.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  1855.                shl eax,cl
  1856.                pop ecx
  1857.                mov edx,offset @@MaskY-4
  1858.                sub edx,offset @@StartCode
  1859.                mov dword ptr [ecx+edx],eax
  1860.  
  1861.                {  @@MaskX  }
  1862.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  1863.                mov edx,offset @@MaskX-4
  1864.                sub edx,offset @@StartCode
  1865.                mov dword ptr [ecx+edx],eax
  1866.  
  1867.                {  @@Bits  }
  1868.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  1869.                mov edx,offset @@Bits-4
  1870.                sub edx,offset @@StartCode
  1871.                mov dword ptr [ecx+edx],eax
  1872.              end;
  1873.            end else
  1874.            if -Source.pitch=(1 shl Source.PitchBit) then
  1875.            begin
  1876.              asm
  1877.                jmp @@EndCode
  1878.              @@StartCode:
  1879.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  1880.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  1881.                shr esi,$11{}       @@YShift: // 16-Source.PitchBit
  1882.                shr edx,16
  1883.                and esi,$11111111{} @@MaskY:  // Source.HeightMask shl Source.PitchBit
  1884.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  1885.                neg esi
  1886.                movzx eax,byte ptr [$11111111+esi+edx]
  1887.                                    @@Bits:   // Source.Bits
  1888.              @@EndCode:
  1889.                {$I DXRender.inc}
  1890.                {  @@TexX  }
  1891.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  1892.                mov edx,offset @@TexX-4
  1893.                sub edx,offset @@StartCode
  1894.                mov dword ptr [ecx+edx],eax
  1895.  
  1896.                {  @@TexY  }
  1897.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  1898.                mov edx,offset @@TexY-4
  1899.                sub edx,offset @@StartCode
  1900.                mov dword ptr [ecx+edx],eax
  1901.  
  1902.                {  @@YShift  }
  1903.                push ebx
  1904.                mov eax,16
  1905.                mov ebx,Source; sub eax,[ebx + TDXR_Surface.PitchBit]
  1906.                pop ebx
  1907.                mov edx,offset @@YShift-1
  1908.                sub edx,offset @@StartCode
  1909.                mov byte ptr [ecx+edx],al
  1910.  
  1911.                {  @@MaskY  }
  1912.                push ecx
  1913.                mov ecx,Source; mov ecx,[ecx + TDXR_Surface.PitchBit]
  1914.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  1915.                shl eax,cl
  1916.                pop ecx
  1917.                mov edx,offset @@MaskY-4
  1918.                sub edx,offset @@StartCode
  1919.                mov dword ptr [ecx+edx],eax
  1920.  
  1921.                {  @@MaskX  }
  1922.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  1923.                mov edx,offset @@MaskX-4
  1924.                sub edx,offset @@StartCode
  1925.                mov dword ptr [ecx+edx],eax
  1926.  
  1927.                {  @@Bits  }
  1928.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  1929.                mov edx,offset @@Bits-4
  1930.                sub edx,offset @@StartCode
  1931.                mov dword ptr [ecx+edx],eax
  1932.              end;
  1933.            end else
  1934.            begin
  1935.              asm
  1936.                jmp @@EndCode
  1937.              @@StartCode:
  1938.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  1939.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  1940.                shr esi,16
  1941.                shr edx,16
  1942.                and esi,$11111111{} @@MaskY:  // Source.HeightMask
  1943.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  1944.                imul esi,$11111111{}@@Pitch:  // Source.pitch
  1945.                movzx eax,byte ptr [esi+edx+$11111111]
  1946.                                    @@Bits:   // Source.Bits
  1947.              @@EndCode:
  1948.                {$I DXRender.inc}
  1949.                {  @@TexX  }
  1950.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  1951.                mov edx,offset @@TexX-4
  1952.                sub edx,offset @@StartCode
  1953.                mov dword ptr [ecx+edx],eax
  1954.  
  1955.                {  @@TexY  }
  1956.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  1957.                mov edx,offset @@TexY-4
  1958.                sub edx,offset @@StartCode
  1959.                mov dword ptr [ecx+edx],eax
  1960.  
  1961.                {  @@MaskY  }
  1962.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  1963.                mov edx,offset @@MaskY-4
  1964.                sub edx,offset @@StartCode
  1965.                mov dword ptr [ecx+edx],eax
  1966.  
  1967.                {  @@Pitch  }
  1968.                mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  1969.                mov edx,offset @@Pitch-4
  1970.                sub edx,offset @@StartCode
  1971.                mov dword ptr [ecx+edx],eax
  1972.  
  1973.                {  @@MaskX  }
  1974.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  1975.                mov edx,offset @@MaskX-4
  1976.                sub edx,offset @@StartCode
  1977.                mov dword ptr [ecx+edx],eax
  1978.  
  1979.                {  @@Bits  }
  1980.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  1981.                mov edx,offset @@Bits-4
  1982.                sub edx,offset @@StartCode
  1983.                mov dword ptr [ecx+edx],eax
  1984.              end;
  1985.            end;
  1986.          end;
  1987.      16: begin
  1988.            if Source.pitch=(1 shl Source.PitchBit) then
  1989.            begin
  1990.              asm
  1991.                jmp @@EndCode
  1992.              @@StartCode:
  1993.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  1994.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  1995.                shr esi,$11{}       @@YShift: // 16-Source.PitchBit
  1996.                shr edx,16
  1997.                and esi,$11111111{} @@MaskY:  // Source.HeightMask shl Source.PitchBit
  1998.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  1999.                movzx eax,word ptr [$11111111+esi+edx*2]
  2000.                                    @@Bits:   // Source.Bits
  2001.              @@EndCode:
  2002.                {$I DXRender.inc}
  2003.                {  @@TexX  }
  2004.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2005.                mov edx,offset @@TexX-4
  2006.                sub edx,offset @@StartCode
  2007.                mov dword ptr [ecx+edx],eax
  2008.  
  2009.                {  @@TexY  }
  2010.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2011.                mov edx,offset @@TexY-4
  2012.                sub edx,offset @@StartCode
  2013.                mov dword ptr [ecx+edx],eax
  2014.  
  2015.                {  @@YShift  }
  2016.                push ebx
  2017.                mov eax,16
  2018.                mov ebx,Source; sub eax,[ebx + TDXR_Surface.PitchBit]
  2019.                pop ebx
  2020.                mov edx,offset @@YShift-1
  2021.                sub edx,offset @@StartCode
  2022.                mov byte ptr [ecx+edx],al
  2023.  
  2024.                {  @@MaskY  }
  2025.                push ecx
  2026.                mov ecx,Source; mov ecx,[ecx + TDXR_Surface.PitchBit]
  2027.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2028.                shl eax,cl
  2029.                pop ecx
  2030.                mov edx,offset @@MaskY-4
  2031.                sub edx,offset @@StartCode
  2032.                mov dword ptr [ecx+edx],eax
  2033.  
  2034.                {  @@MaskX  }
  2035.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2036.                mov edx,offset @@MaskX-4
  2037.                sub edx,offset @@StartCode
  2038.                mov dword ptr [ecx+edx],eax
  2039.  
  2040.                {  @@Bits  }
  2041.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2042.                mov edx,offset @@Bits-4
  2043.                sub edx,offset @@StartCode
  2044.                mov dword ptr [ecx+edx],eax
  2045.              end;
  2046.            end else
  2047.            if -Source.pitch=(1 shl Source.PitchBit) then
  2048.            begin
  2049.              asm
  2050.                jmp @@EndCode
  2051.              @@StartCode:
  2052.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2053.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2054.                shr esi,$11{}       @@YShift: // 16-Source.PitchBit
  2055.                shr edx,16
  2056.                and esi,$11111111{} @@MaskY:  // Source.HeightMask shl Source.PitchBit
  2057.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  2058.                neg esi
  2059.                movzx eax,word ptr [$11111111+esi+edx*2]
  2060.                                    @@Bits:   // Source.Bits
  2061.              @@EndCode:
  2062.                {$I DXRender.inc}
  2063.                {  @@TexX  }
  2064.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2065.                mov edx,offset @@TexX-4
  2066.                sub edx,offset @@StartCode
  2067.                mov dword ptr [ecx+edx],eax
  2068.  
  2069.                {  @@TexY  }
  2070.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2071.                mov edx,offset @@TexY-4
  2072.                sub edx,offset @@StartCode
  2073.                mov dword ptr [ecx+edx],eax
  2074.  
  2075.                {  @@YShift  }
  2076.                push ebx
  2077.                mov eax,16
  2078.                mov ebx,Source; sub eax,[ebx + TDXR_Surface.PitchBit]
  2079.                pop ebx
  2080.                mov edx,offset @@YShift-1
  2081.                sub edx,offset @@StartCode
  2082.                mov byte ptr [ecx+edx],al
  2083.  
  2084.                {  @@MaskY  }
  2085.                push ecx
  2086.                mov ecx,Source; mov ecx,[ecx + TDXR_Surface.PitchBit]
  2087.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2088.                shl eax,cl
  2089.                pop ecx
  2090.                mov edx,offset @@MaskY-4
  2091.                sub edx,offset @@StartCode
  2092.                mov dword ptr [ecx+edx],eax
  2093.  
  2094.                {  @@MaskX  }
  2095.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2096.                mov edx,offset @@MaskX-4
  2097.                sub edx,offset @@StartCode
  2098.                mov dword ptr [ecx+edx],eax
  2099.  
  2100.                {  @@Bits  }
  2101.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2102.                mov edx,offset @@Bits-4
  2103.                sub edx,offset @@StartCode
  2104.                mov dword ptr [ecx+edx],eax
  2105.              end;
  2106.            end else
  2107.            begin
  2108.              asm
  2109.                jmp @@EndCode
  2110.              @@StartCode:
  2111.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2112.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2113.                shr esi,16
  2114.                shr edx,16
  2115.                and esi,$11111111{} @@MaskY:  // Source.HeightMask
  2116.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  2117.                imul esi,$11111111{}@@Pitch:  // Source.pitch
  2118.                movzx eax,word ptr [esi+edx*2+$11111111]
  2119.                                    @@Bits:   // Source.Bits
  2120.              @@EndCode:
  2121.                {$I DXRender.inc}
  2122.                {  @@TexX  }
  2123.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2124.                mov edx,offset @@TexX-4
  2125.                sub edx,offset @@StartCode
  2126.                mov dword ptr [ecx+edx],eax
  2127.  
  2128.                {  @@TexY  }
  2129.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2130.                mov edx,offset @@TexY-4
  2131.                sub edx,offset @@StartCode
  2132.                mov dword ptr [ecx+edx],eax
  2133.  
  2134.                {  @@MaskY  }
  2135.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2136.                mov edx,offset @@MaskY-4
  2137.                sub edx,offset @@StartCode
  2138.                mov dword ptr [ecx+edx],eax
  2139.  
  2140.                {  @@Pitch  }
  2141.                mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2142.                mov edx,offset @@Pitch-4
  2143.                sub edx,offset @@StartCode
  2144.                mov dword ptr [ecx+edx],eax
  2145.  
  2146.                {  @@MaskX  }
  2147.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2148.                mov edx,offset @@MaskX-4
  2149.                sub edx,offset @@StartCode
  2150.                mov dword ptr [ecx+edx],eax
  2151.  
  2152.                {  @@Bits  }
  2153.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2154.                mov edx,offset @@Bits-4
  2155.                sub edx,offset @@StartCode
  2156.                mov dword ptr [ecx+edx],eax
  2157.              end;
  2158.            end;
  2159.          end;
  2160.      24: begin
  2161.            asm
  2162.              jmp @@EndCode
  2163.            @@StartCode:
  2164.              mov esi,dword ptr [offset _null]{}//TexY
  2165.                                  @@TexY:
  2166.              mov edx,dword ptr [offset _null]{}//TexX
  2167.                                  @@TexX:
  2168.              shr esi,16
  2169.              shr edx,16
  2170.              and esi,$11111111{} @@MaskY:  // Source.HeightMask
  2171.              and edx,$11111111{} @@MaskX:  // Source.WidthMask
  2172.              imul esi,$11111111{}@@Pitch:  // Source.pitch
  2173.              lea edx,[edx+edx*2+$11111111] // Source.Bits
  2174.                                  @@Bits:
  2175.              movzx eax,byte ptr [esi+edx+2]
  2176.              shl eax,16
  2177.              mov ax,word ptr [esi+edx]
  2178.            @@EndCode:
  2179.              {$I DXRender.inc}
  2180.              {  @@TexX  }
  2181.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  2182.              mov edx,offset @@TexX-4
  2183.              sub edx,offset @@StartCode
  2184.              mov dword ptr [ecx+edx],eax
  2185.  
  2186.              {  @@TexY  }
  2187.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2188.              mov edx,offset @@TexY-4
  2189.              sub edx,offset @@StartCode
  2190.              mov dword ptr [ecx+edx],eax
  2191.  
  2192.              {  @@MaskY  }
  2193.              mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2194.              mov edx,offset @@MaskY-4
  2195.              sub edx,offset @@StartCode
  2196.              mov dword ptr [ecx+edx],eax
  2197.  
  2198.              {  @@Pitch  }
  2199.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2200.              mov edx,offset @@Pitch-4
  2201.              sub edx,offset @@StartCode
  2202.              mov dword ptr [ecx+edx],eax
  2203.  
  2204.              {  @@MaskX  }
  2205.              mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2206.              mov edx,offset @@MaskX-4
  2207.              sub edx,offset @@StartCode
  2208.              mov dword ptr [ecx+edx],eax
  2209.  
  2210.              {  @@Bits  }
  2211.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2212.              mov edx,offset @@Bits-4
  2213.              sub edx,offset @@StartCode
  2214.              mov dword ptr [ecx+edx],eax
  2215.            end;
  2216.          end;
  2217.      32: begin
  2218.            if Source.pitch=(1 shl Source.PitchBit) then
  2219.            begin
  2220.              asm
  2221.                jmp @@EndCode
  2222.              @@StartCode:
  2223.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2224.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2225.                shr esi,$11{}       @@YShift: // 16-Source.PitchBit
  2226.                shr edx,16
  2227.                and esi,$11111111{} @@MaskY:  // Source.HeightMask shl Source.PitchBit
  2228.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  2229.                mov eax,dword ptr [$11111111+esi+edx*4]
  2230.                                    @@Bits:   // Source.Bits
  2231.              @@EndCode:
  2232.                {$I DXRender.inc}
  2233.                {  @@TexX  }
  2234.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2235.                mov edx,offset @@TexX-4
  2236.                sub edx,offset @@StartCode
  2237.                mov dword ptr [ecx+edx],eax
  2238.  
  2239.                {  @@TexY  }
  2240.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2241.                mov edx,offset @@TexY-4
  2242.                sub edx,offset @@StartCode
  2243.                mov dword ptr [ecx+edx],eax
  2244.  
  2245.                {  @@YShift  }
  2246.                push ebx
  2247.                mov eax,16
  2248.                mov ebx,Source; sub eax,[ebx + TDXR_Surface.PitchBit]
  2249.                pop ebx
  2250.                mov edx,offset @@YShift-1
  2251.                sub edx,offset @@StartCode
  2252.                mov byte ptr [ecx+edx],al
  2253.  
  2254.                {  @@MaskY  }
  2255.                push ecx
  2256.                mov ecx,Source; mov ecx,[ecx + TDXR_Surface.PitchBit]
  2257.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2258.                shl eax,cl
  2259.                pop ecx
  2260.                mov edx,offset @@MaskY-4
  2261.                sub edx,offset @@StartCode
  2262.                mov dword ptr [ecx+edx],eax
  2263.  
  2264.                {  @@MaskX  }
  2265.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2266.                mov edx,offset @@MaskX-4
  2267.                sub edx,offset @@StartCode
  2268.                mov dword ptr [ecx+edx],eax
  2269.  
  2270.                {  @@Bits  }
  2271.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2272.                mov edx,offset @@Bits-4
  2273.                sub edx,offset @@StartCode
  2274.                mov dword ptr [ecx+edx],eax
  2275.              end;
  2276.            end else
  2277.            if -Source.pitch=(1 shl Source.PitchBit) then
  2278.            begin
  2279.              asm
  2280.                jmp @@EndCode
  2281.              @@StartCode:
  2282.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2283.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2284.                shr esi,$11{}       @@YShift: // 16-Source.PitchBit
  2285.                shr edx,16
  2286.                and esi,$11111111{} @@MaskY:  // Source.HeightMask shl Source.PitchBit
  2287.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  2288.                neg esi
  2289.                mov eax,dword ptr [$11111111+esi+edx*4]
  2290.                                    @@Bits:   // Source.Bits
  2291.              @@EndCode:
  2292.                {$I DXRender.inc}
  2293.                {  @@TexX  }
  2294.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2295.                mov edx,offset @@TexX-4
  2296.                sub edx,offset @@StartCode
  2297.                mov dword ptr [ecx+edx],eax
  2298.  
  2299.                {  @@TexY  }
  2300.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2301.                mov edx,offset @@TexY-4
  2302.                sub edx,offset @@StartCode
  2303.                mov dword ptr [ecx+edx],eax
  2304.  
  2305.                {  @@YShift  }
  2306.                push ebx
  2307.                mov eax,16
  2308.                mov ebx,Source; sub eax,[ebx + TDXR_Surface.PitchBit]
  2309.                pop ebx
  2310.                mov edx,offset @@YShift-1
  2311.                sub edx,offset @@StartCode
  2312.                mov byte ptr [ecx+edx],al
  2313.  
  2314.                {  @@MaskY  }
  2315.                push ecx
  2316.                mov ecx,Source; mov ecx,[ecx + TDXR_Surface.PitchBit]
  2317.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2318.                shl eax,cl
  2319.                pop ecx
  2320.                mov edx,offset @@MaskY-4
  2321.                sub edx,offset @@StartCode
  2322.                mov dword ptr [ecx+edx],eax
  2323.  
  2324.                {  @@MaskX  }
  2325.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2326.                mov edx,offset @@MaskX-4
  2327.                sub edx,offset @@StartCode
  2328.                mov dword ptr [ecx+edx],eax
  2329.  
  2330.                {  @@Bits  }
  2331.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2332.                mov edx,offset @@Bits-4
  2333.                sub edx,offset @@StartCode
  2334.                mov dword ptr [ecx+edx],eax
  2335.              end;
  2336.            end else
  2337.            begin
  2338.              asm
  2339.                jmp @@EndCode
  2340.              @@StartCode:
  2341.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2342.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2343.                shr esi,16
  2344.                shr edx,16
  2345.                and esi,$11111111{} @@MaskY:  // Source.HeightMask
  2346.                and edx,$11111111{} @@MaskX:  // Source.WidthMask
  2347.                imul esi,$11111111{}@@Pitch:  // Source.pitch
  2348.                mov eax,dword ptr [esi+edx*4+$11111111]
  2349.                                    @@Bits:   // Source.Bits
  2350.              @@EndCode:
  2351.                {$I DXRender.inc}
  2352.                {  @@TexX  }
  2353.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2354.                mov edx,offset @@TexX-4
  2355.                sub edx,offset @@StartCode
  2356.                mov dword ptr [ecx+edx],eax
  2357.  
  2358.                {  @@TexY  }
  2359.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2360.                mov edx,offset @@TexY-4
  2361.                sub edx,offset @@StartCode
  2362.                mov dword ptr [ecx+edx],eax
  2363.  
  2364.                {  @@MaskY  }
  2365.                mov eax,Source; mov eax,[eax + TDXR_Surface.HeightMask]
  2366.                mov edx,offset @@MaskY-4
  2367.                sub edx,offset @@StartCode
  2368.                mov dword ptr [ecx+edx],eax
  2369.  
  2370.                {  @@Pitch  }
  2371.                mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2372.                mov edx,offset @@Pitch-4
  2373.                sub edx,offset @@StartCode
  2374.                mov dword ptr [ecx+edx],eax
  2375.  
  2376.                {  @@MaskX  }
  2377.                mov eax,Source; mov eax,[eax + TDXR_Surface.WidthMask]
  2378.                mov edx,offset @@MaskX-4
  2379.                sub edx,offset @@StartCode
  2380.                mov dword ptr [ecx+edx],eax
  2381.  
  2382.                {  @@Bits  }
  2383.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2384.                mov edx,offset @@Bits-4
  2385.                sub edx,offset @@StartCode
  2386.                mov dword ptr [ecx+edx],eax
  2387.              end;
  2388.            end;
  2389.          end;
  2390.     end;
  2391.   end;
  2392.  
  2393.   procedure genReadSurfacePixel_DoNotClip(var Code: Pointer; const Source: TDXR_Surface; Axis: PDXRMachine_Axis);
  2394.   begin
  2395.     case Source.BitCount of
  2396.       1: begin
  2397.            asm
  2398.              jmp @@EndCode
  2399.            @@StartCode:
  2400.              mov esi,dword ptr [offset _null]{}//TexY
  2401.                                  @@TexY:
  2402.              shr esi,16
  2403.              imul esi,$11111111{}@@Pitch:   // Source.pitch
  2404.              mov edx,dword ptr [offset _null]{}//TexX
  2405.                                  @@TexX:
  2406.              shr edx,16
  2407.              mov ebx,edx
  2408.              shr edx,3
  2409.              and ebx,7
  2410.              movzx eax,byte ptr [esi+edx+$11111111]
  2411.                                  @@Bits:   // Source.Bits
  2412.              and eax,dword ptr [offset Mask1+ebx*4]
  2413.              push ecx
  2414.              mov ecx,dword ptr [offset Shift1+ebx*4]
  2415.              shr eax,cl
  2416.              pop ecx
  2417.            @@EndCode:
  2418.              {$I DXRender.inc}
  2419.              {  @@TexX  }
  2420.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  2421.              mov edx,offset @@TexX-4
  2422.              sub edx,offset @@StartCode
  2423.              mov dword ptr [ecx+edx],eax
  2424.  
  2425.              {  @@TexY  }
  2426.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2427.              mov edx,offset @@TexY-4
  2428.              sub edx,offset @@StartCode
  2429.              mov dword ptr [ecx+edx],eax
  2430.  
  2431.              {  @@Pitch  }
  2432.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2433.              mov edx,offset @@Pitch-4
  2434.              sub edx,offset @@StartCode
  2435.              mov dword ptr [ecx+edx],eax
  2436.  
  2437.              {  @@Bits  }
  2438.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2439.              mov edx,offset @@Bits-4
  2440.              sub edx,offset @@StartCode
  2441.              mov dword ptr [ecx+edx],eax
  2442.            end;
  2443.          end;
  2444.       2: begin
  2445.            asm
  2446.              jmp @@EndCode
  2447.            @@StartCode:
  2448.              mov esi,dword ptr [offset _null]{}//TexY
  2449.                                  @@TexY:
  2450.              shr esi,16
  2451.              imul esi,$11111111{}@@Pitch:  // Source.pitch
  2452.              mov edx,dword ptr [offset _null]{}//TexX
  2453.                                  @@TexX:
  2454.              shr edx,16
  2455.              mov ebx,edx
  2456.              shr edx,2
  2457.              and ebx,3
  2458.              movzx eax,byte ptr [esi+edx+$11111111]
  2459.                                  @@Bits:   // Source.Bits
  2460.              and eax,dword ptr [offset Mask2+ebx*4]
  2461.              push ecx
  2462.              mov ecx,dword ptr [offset Shift2+ebx*4]
  2463.              shr eax,cl
  2464.              pop ecx
  2465.            @@EndCode:
  2466.              {$I DXRender.inc}
  2467.              {  @@TexX  }
  2468.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  2469.              mov edx,offset @@TexX-4
  2470.              sub edx,offset @@StartCode
  2471.              mov dword ptr [ecx+edx],eax
  2472.  
  2473.              {  @@TexY  }
  2474.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2475.              mov edx,offset @@TexY-4
  2476.              sub edx,offset @@StartCode
  2477.              mov dword ptr [ecx+edx],eax
  2478.  
  2479.              {  @@Pitch  }
  2480.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2481.              mov edx,offset @@Pitch-4
  2482.              sub edx,offset @@StartCode
  2483.              mov dword ptr [ecx+edx],eax
  2484.  
  2485.              {  @@Bits  }
  2486.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2487.              mov edx,offset @@Bits-4
  2488.              sub edx,offset @@StartCode
  2489.              mov dword ptr [ecx+edx],eax
  2490.            end;
  2491.          end;
  2492.       4: begin
  2493.            asm
  2494.              jmp @@EndCode
  2495.            @@StartCode:
  2496.              mov esi,dword ptr [offset _null]{}//TexY
  2497.                                  @@TexY:
  2498.              shr esi,16
  2499.              imul esi,$11111111{}@@Pitch:  // Source.pitch
  2500.              mov edx,dword ptr [offset _null]{}//TexX
  2501.                                  @@TexX:
  2502.              shr edx,16
  2503.              mov ebx,edx
  2504.              shr edx,1
  2505.              and ebx,1
  2506.              movzx eax,byte ptr [esi+edx+$11111111]
  2507.                                  @@Bits:   // Source.Bits
  2508.              and eax,dword ptr [offset Mask4+ebx*4]
  2509.              push ecx
  2510.              mov ecx,dword ptr [offset Shift4+ebx*4]
  2511.              shr eax,cl
  2512.              pop ecx
  2513.            @@EndCode:
  2514.              {$I DXRender.inc}
  2515.              {  @@TexX  }
  2516.              mov eax,Axis; add eax,TDXRMachine_Axis.X
  2517.              mov edx,offset @@TexX-4
  2518.              sub edx,offset @@StartCode
  2519.              mov dword ptr [ecx+edx],eax
  2520.  
  2521.              {  @@TexY  }
  2522.              mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2523.              mov edx,offset @@TexY-4
  2524.              sub edx,offset @@StartCode
  2525.              mov dword ptr [ecx+edx],eax
  2526.  
  2527.              {  @@Pitch  }
  2528.              mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2529.              mov edx,offset @@Pitch-4
  2530.              sub edx,offset @@StartCode
  2531.              mov dword ptr [ecx+edx],eax
  2532.  
  2533.              {  @@Bits  }
  2534.              mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2535.              mov edx,offset @@Bits-4
  2536.              sub edx,offset @@StartCode
  2537.              mov dword ptr [ecx+edx],eax
  2538.            end;
  2539.          end;
  2540.       8: begin
  2541.            if Source.pitch=(1 shl Source.PitchBit) then
  2542.            begin
  2543.              asm
  2544.                jmp @@EndCode
  2545.              @@StartCode:
  2546.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2547.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2548.                shr esi,16
  2549.                shr edx,16
  2550.                shl esi,$11{}       @@PitchBit: // Source.PitchBit
  2551.                movzx eax,byte ptr [$11111111+esi+edx]
  2552.                                    @@Bits:     // Source.Bits
  2553.              @@EndCode:
  2554.                {$I DXRender.inc}
  2555.                {  @@TexX  }
  2556.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2557.                mov edx,offset @@TexX-4
  2558.                sub edx,offset @@StartCode
  2559.                mov dword ptr [ecx+edx],eax
  2560.  
  2561.                {  @@TexY  }
  2562.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2563.                mov edx,offset @@TexY-4
  2564.                sub edx,offset @@StartCode
  2565.                mov dword ptr [ecx+edx],eax
  2566.  
  2567.                {  @@PitchBit  }
  2568.                mov eax,Source; mov eax,[eax + TDXR_Surface.PitchBit]
  2569.                mov edx,offset @@PitchBit-1
  2570.                sub edx,offset @@StartCode
  2571.                mov byte ptr [ecx+edx],al
  2572.  
  2573.                {  @@Bits  }
  2574.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2575.                mov edx,offset @@Bits-4
  2576.                sub edx,offset @@StartCode
  2577.                mov dword ptr [ecx+edx],eax
  2578.              end;
  2579.            end else
  2580.            if -Source.pitch=(1 shl Source.PitchBit) then
  2581.            begin
  2582.              asm
  2583.                jmp @@EndCode
  2584.              @@StartCode:
  2585.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2586.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2587.                shr esi,16
  2588.                shr edx,16
  2589.                shl esi,$11{}       @@PitchBit: // Source.PitchBit
  2590.                neg esi
  2591.                movzx eax,byte ptr [$11111111+esi+edx]
  2592.                                    @@Bits:     // Source.Bits
  2593.              @@EndCode:
  2594.                {$I DXRender.inc}
  2595.                {  @@TexX  }
  2596.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2597.                mov edx,offset @@TexX-4
  2598.                sub edx,offset @@StartCode
  2599.                mov dword ptr [ecx+edx],eax
  2600.  
  2601.                {  @@TexY  }
  2602.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2603.                mov edx,offset @@TexY-4
  2604.                sub edx,offset @@StartCode
  2605.                mov dword ptr [ecx+edx],eax
  2606.  
  2607.                {  @@PitchBit  }
  2608.                mov eax,Source; mov eax,[eax + TDXR_Surface.PitchBit]
  2609.                mov edx,offset @@PitchBit-1
  2610.                sub edx,offset @@StartCode
  2611.                mov byte ptr [ecx+edx],al
  2612.  
  2613.                {  @@Bits  }
  2614.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2615.                mov edx,offset @@Bits-4
  2616.                sub edx,offset @@StartCode
  2617.                mov dword ptr [ecx+edx],eax
  2618.              end;
  2619.            end else
  2620.            begin
  2621.              asm
  2622.                jmp @@EndCode
  2623.              @@StartCode:
  2624.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2625.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2626.                shr esi,16
  2627.                shr edx,16
  2628.                imul esi,$11111111{}@@Pitch:  // Source.pitch
  2629.                movzx eax,byte ptr [esi+edx+$11111111]
  2630.                                    @@Bits:   // Source.Bits
  2631.              @@EndCode:
  2632.                {$I DXRender.inc}
  2633.                {  @@TexX  }
  2634.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2635.                mov edx,offset @@TexX-4
  2636.                sub edx,offset @@StartCode
  2637.                mov dword ptr [ecx+edx],eax
  2638.  
  2639.                {  @@TexY  }
  2640.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2641.                mov edx,offset @@TexY-4
  2642.                sub edx,offset @@StartCode
  2643.                mov dword ptr [ecx+edx],eax
  2644.  
  2645.                {  @@Pitch  }
  2646.                mov eax,Source; mov eax,[eax + TDXR_Surface.Pitch]
  2647.                mov edx,offset @@Pitch-4
  2648.                sub edx,offset @@StartCode
  2649.                mov dword ptr [ecx+edx],eax
  2650.  
  2651.                {  @@Bits  }
  2652.                mov eax,Source; mov eax,[eax + TDXR_Surface.Bits]
  2653.                mov edx,offset @@Bits-4
  2654.                sub edx,offset @@StartCode
  2655.                mov dword ptr [ecx+edx],eax
  2656.              end;
  2657.            end;
  2658.          end;
  2659.      16: begin
  2660.            if Source.pitch=(1 shl Source.PitchBit) then
  2661.            begin
  2662.              asm
  2663.                jmp @@EndCode
  2664.              @@StartCode:
  2665.                mov esi,dword ptr [offset _null]{}@@TexY: //TexY
  2666.                mov edx,dword ptr [offset _null]{}@@TexX: //TexX
  2667.                shr esi,16
  2668.                shr edx,16
  2669.                shl esi,$11{}       @@PitchBit: // Source.PitchBit
  2670.                movzx eax,word ptr [$11111111+esi+edx*2]
  2671.                                    @@Bits:     // Source.Bits
  2672.              @@EndCode:
  2673.                {$I DXRender.inc}
  2674.                {  @@TexX  }
  2675.                mov eax,Axis; add eax,TDXRMachine_Axis.X
  2676.                mov edx,offset @@TexX-4
  2677.                sub edx,offset @@StartCode
  2678.                mov dword ptr [ecx+edx],eax
  2679.  
  2680.                {  @@TexY  }
  2681.                mov eax,Axis; add eax,TDXRMachine_Axis.Y
  2682.                mov edx,offset @@TexY-4
  2683.                sub edx,offset @@StartCode
  2684.                mov