FileOCT.pas 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. //
  2. // This unit is part of the GLScene Engine, http://glscene.org
  3. //
  4. {
  5. Loader for FSRad OCT files.
  6. }
  7. unit FileOCT;
  8. interface
  9. {$I GLScene.inc}
  10. uses
  11. System.Classes,
  12. System.SysUtils,
  13. GLVectorGeometry,
  14. GLVectorTypes,
  15. GLVectorLists;
  16. type
  17. TOCTHeader = record
  18. numVerts : Integer;
  19. numFaces : Integer;
  20. numTextures : Integer;
  21. numLightmaps : Integer;
  22. numLights : Integer;
  23. end;
  24. TOCTVertex = record
  25. tv : TTexPoint; // texture coordinates
  26. lv : TTexpoint; // lightmap coordinates
  27. pos : TAffineVector; // vertex position
  28. end;
  29. TOCTFace = record
  30. start : Integer; // first face vert in vertex array
  31. num : Integer; // number of verts in the face
  32. id : Integer; // texture index into the texture array
  33. lid : Integer; // lightmap index into the lightmap array
  34. p : THmgPlane;
  35. end;
  36. POCTFace = ^TOCTFace;
  37. TOCTTexture = record
  38. id : Integer; // texture id
  39. Name : array [0..63] of AnsiChar; // texture name
  40. end;
  41. TOCTLightmap = record
  42. id : Integer; // lightmaps id
  43. map : array [0..49151] of Byte; // 128 x 128 raw RGB data
  44. end;
  45. POCTLightmap = ^TOCTLightmap;
  46. TOCTLight = record
  47. pos : TAffineVector; // Position
  48. color : TAffineVector; // Color (RGB)
  49. intensity : Integer; // Intensity
  50. end;
  51. TOCTFile = class (TObject)
  52. public
  53. Header : TOCTHeader;
  54. Vertices : array of TOCTVertex;
  55. Faces : array of TOCTFace;
  56. Textures : array of TOCTTexture;
  57. Lightmaps : array of TOCTLightmap;
  58. Lights : array of TOCTLight;
  59. PlayerPos : TAffineVector;
  60. constructor Create; overload;
  61. constructor Create(octStream : TStream); overload;
  62. {Saves content to stream in OCT format.
  63. The Header is automatically prepared before streaming. }
  64. procedure SaveToStream(aStream : TStream);
  65. procedure AddTriangles(vertexCoords : TAffineVectorList;
  66. texMapCoords : TAffineVectorList;
  67. const textureName : String);
  68. procedure AddLight(const lightPos : TAffineVector;
  69. const lightColor : TVector;
  70. lightIntensity : Integer);
  71. end;
  72. // ------------------------------------------------------------------
  73. implementation
  74. // ------------------------------------------------------------------
  75. uses
  76. GLMeshUtils;
  77. // ------------------
  78. // ------------------ TOCTFile ------------------
  79. // ------------------
  80. constructor TOCTFile.Create;
  81. begin
  82. inherited Create;
  83. end;
  84. constructor TOCTFile.Create(octStream : TStream);
  85. begin
  86. inherited Create;
  87. // Read in the header
  88. octStream.Read(Header, SizeOf(Header));
  89. // then the rest of the stuff
  90. SetLength(Vertices, Header.numVerts);
  91. octStream.Read(Vertices[0], Header.numVerts*SizeOf(TOCTVertex));
  92. SetLength(Faces, Header.numFaces);
  93. octStream.Read(Faces[0], Header.numFaces*SizeOf(TOCTFace));
  94. SetLength(Textures, Header.numTextures);
  95. octStream.Read(Textures[0], Header.numTextures*SizeOf(TOCTTexture));
  96. SetLength(Lightmaps, Header.numLightmaps);
  97. octStream.Read(Lightmaps[0], Header.numLightmaps*SizeOf(TOCTLightmap));
  98. SetLength(Lights, Header.numLights);
  99. octStream.Read(Lights[0], Header.numLights*SizeOf(TOCTLight));
  100. octStream.Read(PlayerPos, SizeOf(PlayerPos))
  101. end;
  102. procedure TOCTFile.SaveToStream(aStream : TStream);
  103. begin
  104. with Header, aStream do begin
  105. numVerts:=Length(Vertices);
  106. numFaces:=Length(Faces);
  107. numTextures:=Length(Textures);
  108. numLightmaps:=Length(Lightmaps);
  109. numLights:=Length(Lights);
  110. Write(Header, SizeOf(Header));
  111. Write(Vertices[0], numVerts*SizeOf(TOCTVertex));
  112. Write(Faces[0], numFaces*SizeOf(TOCTFace));
  113. Write(Textures[0], numTextures*SizeOf(TOCTTexture));
  114. Write(Lightmaps[0], numLightmaps*SizeOf(TOCTLightmap));
  115. Write(Lights[0], numLights*SizeOf(TOCTLight));
  116. Write(PlayerPos, SizeOf(PlayerPos))
  117. end;
  118. end;
  119. procedure TOCTFile.AddTriangles(vertexCoords : TAffineVectorList;
  120. texMapCoords : TAffineVectorList;
  121. const textureName : String);
  122. var
  123. i : Integer;
  124. baseIdx, texIdx : Integer;
  125. begin
  126. Assert((texMapCoords=nil) or (texMapCoords.Count=vertexCoords.Count));
  127. texIdx:=Length(Textures);
  128. SetLength(Textures, texIdx+1);
  129. Move(textureName[1], Textures[texIdx].Name[0], Length(textureName));
  130. SetLength(Lightmaps, 1);
  131. FillChar(Lightmaps[0].map[0], 128*3, 255);
  132. baseIdx:=Length(Vertices);
  133. SetLength(Vertices, baseIdx+vertexCoords.Count);
  134. for i:=0 to vertexCoords.Count-1 do with Vertices[baseIdx+i] do begin
  135. pos:=vertexCoords.List[i];
  136. if Assigned(texMapCoords) then
  137. tv:=PTexPoint(@texMapCoords.List[i])^;
  138. end;
  139. SetLength(Faces, vertexCoords.Count div 3);
  140. i:=0; while i<vertexCoords.Count do begin
  141. with Faces[i div 3] do begin
  142. start:=baseIdx+i;
  143. num:=3;
  144. id:=texIdx;
  145. p:=PlaneMake(vertexCoords[i],
  146. CalcPlaneNormal(vertexCoords[i+0], vertexCoords[i+1], vertexCoords[i+0]));
  147. end;
  148. Inc(i, 3);
  149. end;
  150. end;
  151. procedure TOCTFile.AddLight(const lightPos : TAffineVector;
  152. const lightColor : TVector;
  153. lightIntensity : Integer);
  154. var
  155. n : Integer;
  156. begin
  157. n:=Length(Lights);
  158. SetLength(Lights, n+1);
  159. with Lights[n] do begin
  160. pos:=lightPos;
  161. color:=PAffineVector(@lightColor)^;
  162. intensity:=lightIntensity;
  163. end;
  164. end;
  165. end.