home *** CD-ROM | disk | FTP | other *** search
/ D!Zone (Collector's Edition) / D_ZONE_CD.ISO / programs / editors / bsp11x / bsp.c next >
C/C++ Source or Header  |  1994-12-06  |  20KB  |  752 lines

  1. /*- BSP.C -------------------------------------------------------------------*
  2.  
  3.  Node builder for DOOM levels, still only version 0.9, so not totally finished
  4.  but, seems to be doing pretty well, for about a weeks work!
  5.  Credit to Raphael Quinet (Some of the code has been modified from DEU).
  6.  Also, the original idea for some of the techniques where also taken from the
  7.  comment at the bottom of OBJECTS.C in DEU, and the doc by Matt Fell about
  8.  the nodes.
  9.  
  10.  Also to Dylan Cuthbert, cos I am really shit at C, and maths.
  11.  And Giles Goddard for helping with the which side checker.
  12.  
  13.  Any inquiries to Colin Reed via DYL@CIX.COMPULINK.CO.UK
  14.  
  15.  Use this code for your own editors, but please credit me.
  16.  
  17. *---------------------------------------------------------------------------*/
  18.  
  19. #include "bsp.h"
  20. #include "structs.h"
  21.  
  22. /*- Global Vars ------------------------------------------------------------*/
  23.  
  24. FILE *infile,*outfile;
  25. char *testwad;
  26. char *outwad;
  27.  
  28. struct wad_header *wad = NULL;
  29. struct directory *direc = NULL;
  30. char rname[]="\0\0\0\0\0\0\0\0";
  31.  
  32. struct Thing *things;
  33. long num_things = 0;
  34. long things_start = 0;
  35.  
  36. struct Vertex *vertices;
  37. long num_verts = 0;
  38. long vertices_start = 0;
  39.  
  40. struct LineDef *linedefs;
  41. long num_lines = 0;
  42. long linedefs_start = 0;
  43.  
  44. struct SideDef *sidedefs;
  45. long num_sides = 0;
  46. long sidedefs_start = 0;
  47.  
  48. struct Sector *sectors;
  49. long num_sects = 0;
  50. long sectors_start = 0;
  51.  
  52. struct SSector *ssectors;
  53. long num_ssectors = 0;
  54. long ssectors_start = 0;
  55.  
  56. struct Pseg *psegs = NULL;
  57. long num_psegs = 0;
  58. long segs_start = 0;
  59.  
  60. struct Pnode *pnodes = NULL;
  61. long num_pnodes = 0;
  62. long pnode_indx = 0;
  63. long pnodes_start = 0;
  64.  
  65. struct Seg *tsegs = NULL;
  66. long num_tsegs = 0;
  67.  
  68. struct Node *nodelist = NULL;
  69. long num_nodes = 0;
  70.  
  71. long reject_start;
  72. long reject_size;
  73.  
  74. struct Block blockhead;
  75. short int *blockptrs;
  76. short int *blocklists=NULL;
  77. long blockptrs_size;
  78. long blockmap_size;
  79. long blockmap_start;
  80.  
  81. struct splitter sp;
  82.  
  83. short node_x;
  84. short node_y;
  85. short node_dx;
  86. short node_dy;
  87.  
  88. short lminx;
  89. short lmaxx;
  90. short lminy;
  91. short lmaxy;
  92.  
  93. short mapminx;
  94. short mapmaxx;
  95. short mapminy;
  96. short mapmaxy;
  97.  
  98. long psx,psy,pex,pey,pdx,pdy;
  99. long lsx,lsy,lex,ley;
  100.  
  101. unsigned char pcnt;
  102.  
  103. long fagcount = 0;
  104.  
  105. /*- Prototypes -------------------------------------------------------------*/
  106.  
  107. void OpenWadFile(char *);
  108. void Printname(struct directory *);
  109. int  FindDir(char *);
  110. void GetThings(void);
  111. void GetVertexes(void);
  112. void GetLinedefs(void);
  113. void GetSidedefs(void);
  114. void GetSectors(void);
  115. void FindLimits(struct Seg *);
  116.  
  117. struct Seg *CreateSegs();
  118.  
  119. struct Node *CreateNode(struct Seg *);
  120. void DivideSegs(struct Seg *,struct Seg **,struct Seg **);
  121. int IsItConvex(struct Seg *);
  122.  
  123. struct Seg *PickNode(struct Seg *);
  124. void ComputeIntersection(short int *,short int *);
  125. int DoLinesIntersect();
  126. int SplitDist(struct Seg *);
  127.  
  128. void ReverseNodes(struct Node *);
  129. long CreateBlockmap(void);
  130.  
  131. void progress(void);
  132.  
  133. /*--------------------------------------------------------------------------*/
  134.  
  135. #include "makenode.c"
  136. #include "picknode.c"
  137. #include "funcs.c"
  138.  
  139. /*- Main Program -----------------------------------------------------------*/
  140.  
  141. int main(int argc,char *argv[])
  142. {
  143.     long dir_start = 12;                                    /* Skip Pwad header*/
  144.     long dir_entries = 0;
  145.     
  146.     int n;
  147.     unsigned char *data;
  148.     
  149.     printf("** Doom BSP node builder ver 1.1x (c) 1994 Colin Reed **\n");
  150.  
  151.     if(argc<2 || argc>3)
  152.         {
  153.         printf("\nThis Node builder was created from the basic theory stated in DEU5 (OBJECTS.C)\n");
  154.         printf("\nCredits should go to :-\n");
  155.         printf("Matt Fell      (matt.burnett@acebbs.com) for the Doom Specs.\n");
  156.         printf("Raphael Quinet (quinet@montefiore.ulg.ac.be) for DEU and the original idea.\n");
  157.         printf("Dylan Cuthbert (dyl@cix.compulink.co.uk) for allowing the public to get hold\n");
  158.         printf("               of this program.\n");
  159.         printf("\nUsage: BSP name.wad {output.wad}\n");
  160.         printf("     : (If no output.wad is specified, TMP.WAD is written)\n");
  161.         exit(0);
  162.         }
  163.  
  164.     testwad = argv[1];                                    /* Get input name*/
  165.     if(argc == 3) outwad = argv[2];                    /* Get output name*/
  166.     else outwad = "tmp.wad";
  167.  
  168.     OpenWadFile(testwad);                                /* Opens and reads directory*/
  169.     GetThings();                                            /* of wad file*/
  170.     GetLinedefs();                                            /* Get linedefs and vertices*/
  171.     GetVertexes();                                            /* and delete redundant.*/
  172.     GetSidedefs();
  173.      GetSectors();
  174.  
  175.     num_tsegs = 0;
  176.     tsegs = CreateSegs();                                  /* Initially create segs*/
  177.  
  178.     FindLimits(tsegs);                                    /* Find limits of vertices*/
  179.     
  180.     mapminx = lminx;                                        /* store as map limits*/
  181.     mapmaxx = lmaxx;
  182.     mapminy = lminy;
  183.     mapmaxy = lmaxy;
  184.     
  185.     printf("Map goes from X (%d,%d) Y (%d,%d)\n",lminx,lmaxx,lminy,lmaxy);
  186.     
  187.     num_nodes = 0;
  188.     nodelist = CreateNode(tsegs);                        /* recursively create nodes*/
  189.     printf("%lu NODES created, with %lu SSECTORS.\n",num_nodes,num_ssectors);
  190.  
  191.     pnodes = GetMemory(sizeof(struct Pnode)*num_nodes);
  192.     num_pnodes = 0;
  193.     pnode_indx = 0;
  194.     ReverseNodes(nodelist);
  195.  
  196.     dir_entries++;                                            /* Skip level number*/
  197.  
  198.     things_start = dir_start;
  199.     dir_start = dir_start + (sizeof(struct Thing)*num_things);
  200.     direc[dir_entries].start = things_start;
  201.     direc[dir_entries].length = (sizeof(struct Thing)*num_things);
  202.     dir_entries++;
  203.     
  204.     linedefs_start = dir_start;
  205.     dir_start = dir_start + (sizeof(struct LineDef)*num_lines);
  206.     direc[dir_entries].start = linedefs_start;
  207.     direc[dir_entries].length = (sizeof(struct LineDef)*num_lines);
  208.     dir_entries++;
  209.     
  210.     sidedefs_start = dir_start;
  211.     dir_start = dir_start + (sizeof(struct SideDef)*num_sides);
  212.     direc[dir_entries].start = sidedefs_start;
  213.     direc[dir_entries].length = (sizeof(struct SideDef)*num_sides);
  214.     dir_entries++;
  215.     
  216.     printf("Found %lu used vertices\n",num_verts);
  217.     
  218.     vertices_start = dir_start;
  219.     dir_start = dir_start + (sizeof(struct Vertex)*num_verts);
  220.     direc[dir_entries].start = vertices_start;
  221.     direc[dir_entries].length = (sizeof(struct Vertex)*num_verts);
  222.     dir_entries++;
  223.     
  224.     segs_start = dir_start;
  225.     dir_start = dir_start + (sizeof(struct Pseg)*num_psegs);
  226.     direc[dir_entries].start = segs_start;
  227.     direc[dir_entries].length = (sizeof(struct Pseg)*num_psegs);
  228.     dir_entries++;
  229.     
  230.     ssectors_start = dir_start;
  231.     dir_start = dir_start + (sizeof(struct SSector)*num_ssectors);
  232.     direc[dir_entries].start = ssectors_start;
  233.     direc[dir_entries].length = (sizeof(struct SSector)*num_ssectors);
  234.     dir_entries++;
  235.     
  236.     pnodes_start = dir_start;
  237.     dir_start = dir_start + (sizeof(struct Pnode)*num_pnodes);
  238.     direc[dir_entries].start = pnodes_start;
  239.     direc[dir_entries].length = (sizeof(struct Pnode)*num_pnodes);
  240.     dir_entries++;
  241.     
  242.     sectors_start = dir_start;
  243.     dir_start = dir_start + (sizeof(struct Sector)*num_sects);
  244.     direc[dir_entries].start = sectors_start;
  245.     direc[dir_entries].length = (sizeof(struct Sector)*num_sects);
  246.     dir_entries++;
  247.  
  248.     reject_size = (num_sects*num_sects+7)/8;
  249.     data = calloc(reject_size,1);
  250.     reject_start = dir_start;
  251.     dir_start+=reject_size;
  252.     direc[dir_entries].start = reject_start;            /* Skip reject map*/
  253.     direc[dir_entries].length = reject_size;
  254.     dir_entries++;
  255.  
  256.     blockmap_size = CreateBlockmap();
  257.  
  258.     blockmap_start = dir_start;
  259.     dir_start = dir_start + (blockmap_size+blockptrs_size+8);
  260.     direc[dir_entries].start = blockmap_start;
  261.     direc[dir_entries].length = (blockmap_size+blockptrs_size+8);
  262.     dir_entries++;
  263.  
  264.     printf("Completed blockmap building and saved PWAD as %s\n",outwad);
  265.     
  266.     if((outfile = fopen(outwad,"wb")) == NULL)
  267.         {
  268.       printf("Error: Could not open output PWAD file %s", outwad);
  269.         exit(0);
  270.         }
  271.     fwrite(wad,4,1,outfile);
  272.     fwrite(&dir_entries,sizeof(long),1,outfile);
  273.     fwrite(&dir_start,sizeof(long),1,outfile);
  274.     fwrite(things,(sizeof(struct Thing)*num_things),1,outfile);
  275.     fwrite(linedefs,(sizeof(struct LineDef)*num_lines),1,outfile);
  276.     fwrite(sidedefs,(sizeof(struct SideDef)*num_sides),1,outfile);
  277.     fwrite(vertices,(sizeof(struct Vertex)*num_verts),1,outfile);
  278.     fwrite(psegs,(sizeof(struct Pseg)*num_psegs),1,outfile);
  279.     fwrite(ssectors,(sizeof(struct SSector)*num_ssectors),1,outfile);
  280.     fw