home *** CD-ROM | disk | FTP | other *** search
/ Amiga ACS 1998 #6 / amigaacscoverdisc1998-061998.iso / games / descent / source / main / editor / med.c < prev    next >
Text File  |  1998-06-08  |  43KB  |  1,598 lines

  1. /*
  2. THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
  3. SOFTWARE CORPORATION ("PARALLAX").  PARALLAX, IN DISTRIBUTING THE CODE TO
  4. END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
  5. ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
  6. IN USING, DISPLAYING,  AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
  7. SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
  8. FREE PURPOSES.  IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
  9. CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES.  THE END-USER UNDERSTANDS
  10. AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.  
  11. COPYRIGHT 1993-1998 PARALLAX SOFTWARE CORPORATION.  ALL RIGHTS RESERVED.
  12. */
  13. /*
  14.  * $Source: f:/miner/source/main/editor/rcs/med.c $
  15.  * $Revision: 2.3 $
  16.  * $Author: john $
  17.  * $Date: 1995/03/06 18:23:52 $
  18.  *
  19.  * Editor loop for Inferno
  20.  *
  21.  * $Log: med.c $
  22.  * Revision 2.3  1995/03/06  18:23:52  john
  23.  * Fixed bug with font screwing up.
  24.  * 
  25.  * Revision 2.2  1995/03/06  16:34:55  john
  26.  * Fixed bug with previous.
  27.  * 
  28.  * Revision 2.1  1995/03/06  15:20:57  john
  29.  * New screen mode method.
  30.  * 
  31.  * Revision 2.0  1995/02/27  11:35:54  john
  32.  * Version 2.0! No anonymous unions, Watcom 10.0, with no need
  33.  * for bitmaps.tbl.
  34.  * 
  35.  * Revision 1.192  1994/11/30  12:33:55  mike
  36.  * set window clearing mode for editor.
  37.  * 
  38.  * Revision 1.191  1994/11/27  23:17:02  matt
  39.  * Made changes for new mprintf calling convention
  40.  * 
  41.  * Revision 1.190  1994/11/19  00:04:33  john
  42.  * Changed some shorts to ints.
  43.  * 
  44.  * Revision 1.189  1994/11/17  14:47:57  mike
  45.  * validation functions moved from editor to game.
  46.  * 
  47.  * Revision 1.188  1994/11/14  11:41:38  john
  48.  * Fixed bug with editor/game sequencing.
  49.  * 
  50.  * Revision 1.187  1994/11/13  15:36:44  john
  51.  * Changed game sequencing with editor.
  52.  * 
  53.  * Revision 1.186  1994/11/10  16:49:12  matt
  54.  * Don't sort seg list if no segs in list
  55.  * 
  56.  * Revision 1.185  1994/11/08  09:28:39  mike
  57.  * reset ai paths on going to game.
  58.  * 
  59.  * Revision 1.184  1994/10/30  14:13:05  mike
  60.  * rip out repair center stuff.
  61.  * 
  62.  * Revision 1.183  1994/10/27  10:07:06  mike
  63.  * adapt to no inverse table.
  64.  * 
  65.  * Revision 1.182  1994/10/20  12:48:03  matt
  66.  * Replaced old save files (MIN/SAV/HOT) with new LVL files
  67.  * 
  68.  * Revision 1.181  1994/10/13  11:39:22  john
  69.  * Took out network stuff/.
  70.  * 
  71.  * Revision 1.180  1994/10/07  22:21:38  mike
  72.  * Stop Delete-{whatever} from hanging you!
  73.  * 
  74.  * Revision 1.179  1994/10/03  23:39:37  mike
  75.  * Adapt to newer, better, fuelcen_activate function.
  76.  * 
  77.  * Revision 1.178  1994/09/30  00:38:05  mike
  78.  * Shorten diagnostic message erase -- was erasing outside canvas.
  79.  * 
  80.  * Revision 1.177  1994/09/28  17:31:37  mike
  81.  * Add call to check_wall_validity();
  82.  * 
  83.  * Revision 1.176  1994/08/19  10:57:42  mike
  84.  * Fix status message erase bug.
  85.  * 
  86.  * Revision 1.175  1994/08/18  10:48:12  john
  87.  * Cleaned up game sequencing.
  88.  * 
  89.  * Revision 1.174  1994/08/16  18:11:04  yuan
  90.  * Maded C place you in the center of a segment.
  91.  * 
  92.  * Revision 1.173  1994/08/10  19:55:05  john
  93.  * Changed font stuff.
  94.  * 
  95.  * Revision 1.172  1994/08/09  16:06:06  john
  96.  * Added the ability to place players.  Made old
  97.  * Player variable be ConsoleObject.
  98.  * 
  99.  * Revision 1.171  1994/08/04  09:14:11  matt
  100.  * Fixed problem I said I fixed last time
  101.  * 
  102.  * Revision 1.170  1994/08/04  00:27:57  matt
  103.  * When viewing a wall, update the objects segnum if moved out of the segment
  104.  * 
  105.  * Revision 1.169  1994/08/02  14:18:12  mike
  106.  * Clean up dialog boxes.
  107.  * 
  108.  * Revision 1.168  1994/07/29  15:34:35  mike
  109.  * Kill some mprintfs.
  110.  * 
  111.  * Revision 1.167  1994/07/29  14:56:46  yuan
  112.  * Close centers window, when you go into game.
  113.  * 
  114.  * Revision 1.166  1994/07/28  17:16:20  john
  115.  * MAde editor use Network stuff.
  116.  * 
  117.  * Revision 1.165  1994/07/28  16:59:10  mike
  118.  * objects containing objects.
  119.  * 
  120.  * Revision 1.164  1994/07/22  12:37:07  matt
  121.  * Cleaned up editor/game interactions some more.
  122.  * 
  123.  * Revision 1.163  1994/07/21  19:35:11  yuan
  124.  * Fixed #include problem
  125.  * 
  126.  * Revision 1.162  1994/07/21  18:02:09  matt
  127.  * Don't re-init player stats when going from editor -> game
  128.  * 
  129.  * Revision 1.161  1994/07/21  12:47:53  mike
  130.  * Add tilde key functionality for object movement.
  131.  * 
  132.  * Revision 1.160  1994/07/18  10:44:55  mike
  133.  * One-click access to keypads.
  134.  * 
  135.  * Revision 1.159  1994/07/01  18:05:54  john
  136.  * *** empty log message ***
  137.  * 
  138.  * Revision 1.158  1994/07/01  17:57:06  john
  139.  * First version of not-working hostage system
  140.  * 
  141.  * 
  142.  * Revision 1.157  1994/07/01  11:32:29  john
  143.  * *** empty log message ***
  144.  * 
  145.  * Revision 1.156  1994/06/24  17:04:36  john
  146.  * *** empty log message ***
  147.  * 
  148.  * Revision 1.155  1994/06/23  15:53:47  matt
  149.  * Finished hacking in 3d rendering in big window
  150.  * 
  151.  * Revision 1.154  1994/06/21  16:17:54  yuan
  152.  * Init stats when you go to game from editor
  153.  * 
  154.  * Revision 1.153  1994/06/21  12:57:14  yuan
  155.  * Remove center from segment function added to menu.
  156.  * 
  157.  */
  158.  
  159. //#define DEMO 1
  160.  
  161. #define    DIAGNOSTIC_MESSAGE_MAX                90
  162. #define    EDITOR_STATUS_MESSAGE_DURATION    4        //    Shows for 3+..4 seconds
  163.  
  164. #pragma off (unreferenced)
  165. static char rcsid[] = "$Id: med.c 2.3 1995/03/06 18:23:52 john Exp $";
  166. #pragma on (unreferenced)
  167.  
  168. #include <stdio.h>
  169. #include <stdlib.h>
  170. #include <stdarg.h>
  171. #include <string.h>
  172. #include <process.h>
  173. #include <time.h>
  174.  
  175. //#define INCLUDE_XLISP
  176.  
  177. #include "inferno.h"
  178. #include "segment.h"
  179. #include "gr.h"
  180. #include "ui.h"
  181. #include "editor.h"
  182. //#include "gamemine.h"
  183. #include "gamesave.h"
  184. #include "gameseg.h"
  185.  
  186. #include "key.h"
  187. #include "mono.h"
  188. #include "error.h"
  189. #include "kfuncs.h"
  190. #include "macro.h"
  191.  
  192. #ifdef INCLUDE_XLISP
  193. #include "medlisp.h"
  194. #endif
  195. #include "mem.h"
  196. #include "render.h"
  197. #include "game.h"
  198. #include "slew.h"
  199. #include "kdefs.h"
  200. #include "func.h"
  201. #include "textures.h"
  202. #include "screens.h"
  203. #include "texmap.h"
  204. #include "object.h"
  205. #include "cflib.h"
  206. #include "effects.h"
  207. #include "wall.h"
  208. #include "info.h"
  209. #include "ai.h"
  210.  
  211. #include "texpage.h"        // Textue selection paging stuff
  212. #include "objpage.h"        // Object selection paging stuff
  213.  
  214. #include "medmisc.h"
  215. #include "meddraw.h"
  216. #include "medsel.h"
  217. #include "medrobot.h"
  218. #include "medwall.h"
  219. #include "eswitch.h"
  220. #include "ehostage.h"
  221. #include "centers.h"
  222.  
  223. #include "fuelcen.h"
  224. #include "gameseq.h"
  225. #include "newmenu.h"
  226.  
  227. //#define _MARK_ON 1
  228. //#include <wsample.h>        //should come after inferno.h to get mark setting //Not included here.
  229.  
  230. #define COMPRESS_INTERVAL    5            // seconds
  231.  
  232. //char *undo_status[128];
  233.  
  234. int initializing;
  235.  
  236. //these are instances of canvases, pointed to by variables below
  237. grs_canvas _canv_editor_game;        //the game on the editor screen
  238.  
  239. //these are pointers to our canvases
  240. grs_canvas *Canv_editor;            //the editor screen
  241. grs_canvas *Canv_editor_game=&_canv_editor_game; //the game on the editor screen
  242.  
  243. grs_canvas *canv_offscreen;        //for off-screen rendering
  244. grs_canvas *Pad_text_canvas;        // Keypad text
  245.  
  246. grs_font *editor_font=NULL;
  247.  
  248. //where the editor is looking
  249. vms_vector Ed_view_target={0,0,0};
  250.  
  251. int gamestate_not_restored = 0;
  252.  
  253. UI_WINDOW * EditorWindow;
  254.  
  255. int    Large_view_index = -1;
  256.  
  257. UI_GADGET_USERBOX * GameViewBox;
  258. UI_GADGET_USERBOX * LargeViewBox;
  259. UI_GADGET_USERBOX * GroupViewBox;
  260.  
  261. #if ORTHO_VIEWS
  262. UI_GADGET_USERBOX * TopViewBox;
  263. UI_GADGET_USERBOX * FrontViewBox;
  264. UI_GADGET_USERBOX * RightViewBox;
  265. #endif
  266.  
  267. UI_GADGET_ICON * ViewIcon;
  268. UI_GADGET_ICON * AllIcon;
  269. UI_GADGET_ICON * AxesIcon;
  270. UI_GADGET_ICON * ChaseIcon;
  271. UI_GADGET_ICON * OutlineIcon;
  272. UI_GADGET_ICON * LockIcon;
  273. //-NOLIGHTICON- UI_GADGET_ICON * LightIcon;
  274.  
  275. UI_EVENT * DemoBuffer = NULL;
  276.  
  277. //grs_canvas * BigCanvas[2];
  278. //int CurrentBigCanvas = 0;
  279. //int BigCanvasFirstTime = 1;
  280.  
  281. int    Found_seg_index=0;                // Index in Found_segs corresponding to Cursegp
  282.  
  283.  
  284. void print_status_bar( char message[DIAGNOSTIC_MESSAGE_MAX] ) {
  285.     int w,h,aw;
  286.  
  287.     gr_set_current_canvas( NULL );
  288.     gr_set_curfont(editor_font);
  289.     gr_set_fontcolor( CBLACK, CGREY );
  290.     gr_get_string_size( message, &w, &h, &aw );
  291.     gr_string( 4, 583, message );
  292.     gr_set_fontcolor( CBLACK, CWHITE );
  293.     gr_setcolor( CGREY );
  294.     gr_rect( 4+w, 583, 799, 599 );
  295. }
  296.  
  297. void print_diagnostic( char message[DIAGNOSTIC_MESSAGE_MAX] ) {
  298.     int w,h,aw;
  299.  
  300.     gr_set_current_canvas( NULL );
  301.     gr_set_curfont(editor_font);
  302.     gr_set_fontcolor( CBLACK, CGREY );
  303.     gr_get_string_size( message, &w, &h, &aw );
  304.     gr_string( 4, 583, message );
  305.     gr_set_fontcolor( CBLACK, CWHITE );
  306.     gr_setcolor( CGREY );
  307.     gr_rect( 4+w, 583, 799, 599 );
  308. }
  309.  
  310. static char status_line[DIAGNOSTIC_MESSAGE_MAX];
  311.  
  312. struct tm    Editor_status_last_time;
  313.  
  314. void editor_status( const char *format, ... )
  315. {
  316.     va_list ap;
  317.  
  318.     va_start(ap, format);
  319.     vsprintf(status_line, format, ap);
  320.     va_end(ap);
  321.  
  322.     print_status_bar(status_line);
  323.  
  324.     Editor_status_last_time = Editor_time_of_day;
  325.  
  326. }
  327.  
  328. //     int  tm_sec;    /* seconds after the minute -- [0,61] */
  329. //     int  tm_min;    /* minutes after the hour    -- [0,59] */
  330. //     int  tm_hour;    /* hours after midnight    -- [0,23] */
  331. //     int  tm_mday;    /* day of the month        -- [1,31] */
  332. //     int  tm_mon;    /* months since January    -- [0,11] */
  333. //     int  tm_year;    /* years since 1900                */
  334. //     int  tm_wday;    /* days since Sunday        -- [0,6]  */
  335. //     int  tm_yday;    /* days since January 1    -- [0,365]*/
  336. //     int  tm_isdst;    /* Daylight Savings Time flag */
  337.  
  338. void clear_editor_status(void)
  339. {
  340.     int cur_time = Editor_time_of_day.tm_hour * 3600 + Editor_time_of_day.tm_min*60 + Editor_time_of_day.tm_sec;
  341.     int erase_time = Editor_status_last_time.tm_hour * 3600 + Editor_status_last_time.tm_min*60 + Editor_status_last_time.tm_sec + EDITOR_STATUS_MESSAGE_DURATION;
  342.  
  343.     if (cur_time > erase_time) {
  344.         int    i;
  345.         char    message[DIAGNOSTIC_MESSAGE_MAX];
  346.  
  347.         for (i=0; i<DIAGNOSTIC_MESSAGE_MAX-1; i++)
  348.             message[i] = ' ';
  349.  
  350.         message[i] = 0;
  351.         print_status_bar(message);
  352.         Editor_status_last_time.tm_hour = 99;
  353.     }
  354. }
  355.  
  356.  
  357. void diagnostic_message( char *format, ... )
  358. {
  359.     char diag_line[DIAGNOSTIC_MESSAGE_MAX];
  360.  
  361.     va_list ap;
  362.  
  363.     va_start(ap, format);
  364.     vsprintf(diag_line, format, ap);
  365.     va_end(ap);
  366.  
  367.     editor_status(diag_line);
  368. }
  369.  
  370.  
  371. static char sub_status_line[DIAGNOSTIC_MESSAGE_MAX];
  372.  
  373. void editor_sub_status( const char *format, ... )
  374. {
  375.     int w,h,aw;
  376.     va_list ap;
  377.  
  378.     va_start(ap, format);
  379.     vsprintf(sub_status_line, format, ap);
  380.     va_end(ap);
  381.  
  382.     gr_set_current_canvas( NULL );
  383.     gr_set_curfont(editor_font);
  384.     gr_set_fontcolor( BM_XRGB(0,0,31), CGREY );
  385.     gr_get_string_size( sub_status_line, &w, &h, &aw );
  386.     gr_string( 500, 583, sub_status_line );
  387.     gr_set_fontcolor( CBLACK, CWHITE );
  388.     gr_setcolor( CGREY );
  389.     gr_rect( 500+w, 583, 799, 599 );
  390. }
  391.  
  392. int DropIntoDebugger()
  393. {
  394.     Int3();
  395.     return 1;
  396. }
  397.  
  398.  
  399. #ifdef INCLUDE_XLISP
  400. int CallLisp()
  401. {
  402.     medlisp_go();
  403.     return 1;
  404. }
  405. #endif
  406.  
  407.  
  408. int ExitEditor()
  409. {
  410.     if (SafetyCheck())  {
  411.         ModeFlag = 1;
  412.     }
  413.     return 1;
  414. }
  415.  
  416. int    GotoGameCommon(int mode) {
  417.     stop_time();
  418.  
  419. //@@    init_player_stats();
  420. //@@
  421. //@@    Player_init.pos = Player->pos;
  422. //@@    Player_init.orient = Player->orient;
  423. //@@    Player_init.segnum = Player->segnum;    
  424.     
  425. // -- must always save gamesave.sav because the restore-objects code relies on it
  426. // -- that code could be made smarter and use the original file, if appropriate.
  427. //    if (mine_changed) 
  428.     if (gamestate_not_restored == 0) {
  429.         gamestate_not_restored = 1;
  430.         save_level("GAMESAVE.LVL");
  431.         editor_status("Gamestate saved.\n");
  432.         mprintf((0, "Gamestate saved.\n"));
  433.     }
  434.  
  435.     ai_reset_all_paths();
  436.  
  437.     start_time();
  438.  
  439.     ModeFlag = mode;
  440.     return 1;
  441. }
  442.  
  443. int GotoGameScreen()
  444. {
  445.     return GotoGameCommon(3);
  446. }
  447.  
  448. int GotoGame()
  449. {
  450.     return GotoGameCommon(2);
  451. }
  452.  
  453.  
  454. void ReadLispMacro( FILE * file, char * buffer )
  455. {
  456. //    char c;
  457. //    int size=0;
  458. //    int pcount = 0;
  459. //    char text[100];
  460. //    int i=0;
  461.     
  462.     fscanf( file, " { %s } ", buffer );
  463.  
  464. /*
  465.     while (1)
  466.     {
  467.         c = text[i++];
  468.         if (pcount > 0 )
  469.             buffer[size++] = c;
  470.         if ( c == '(' ) pcount++;
  471.         if ( c == ')' ) break;
  472.     }
  473.     buffer[size++] = 0;
  474. */
  475.  
  476.     return;
  477. }
  478.  
  479. static int (*KeyFunction[2048])();
  480.  
  481. void medkey_init()
  482. {
  483.     FILE * keyfile;
  484.     char keypress[100];
  485.     int key;
  486.     int i;    //, size;
  487.     int np;
  488.     char * LispCommand;
  489.  
  490.     //MALLOC( LispCommand, char, DIAGNOSTIC_MESSAGE_MAX );//hacked by KRB
  491.     LispCommand = (char *)malloc(DIAGNOSTIC_MESSAGE_MAX*sizeof(char));
  492.  
  493.     for (i=0; i<2048; i++ )
  494.         KeyFunction[i] = NULL;
  495.  
  496.     keyfile = fopen( "GLOBAL.KEY", "rt" );
  497.     if (keyfile)
  498.     {
  499.         while (fscanf( keyfile, " %s %s ", keypress, LispCommand ) != EOF )
  500.         {
  501.             //ReadLispMacro( keyfile, LispCommand );
  502.  
  503.             if ( (key=DecodeKeyText( keypress ))!= -1 )
  504.             {
  505.                 Assert( key < 2048);
  506.                 KeyFunction[key] = func_get( LispCommand, &np );
  507.             } else {
  508.                 Error( "Bad key %s in GLOBAL.KEY!", keypress );
  509.             }
  510.         }
  511.         fclose(keyfile);
  512.     }
  513.     free( LispCommand );
  514. }
  515.  
  516. void init_editor()
  517. {
  518.     minit();
  519.  
  520.     ui_init();
  521.  
  522.     init_med_functions();    // Must be called before medlisp_init
  523.  
  524.     ui_pad_read( 0, "segmove.pad" );
  525.     ui_pad_read( 1, "segsize.pad" );
  526.     ui_pad_read( 2, "curve.pad" );
  527.     ui_pad_read( 3, "texture.pad" );
  528.     ui_pad_read( 4, "object.pad" );
  529.     ui_pad_read( 5, "objmov.pad" );
  530.     ui_pad_read( 6, "group.pad" );
  531.     ui_pad_read( 7, "lighting.pad" );
  532.     ui_pad_read( 8, "test.pad" );
  533.  
  534.     medkey_init();
  535.  
  536.     editor_font = gr_init_font( "pc8x16.fnt" );
  537.     
  538.     menubar_init( "MED.MNU" );
  539.  
  540.     canv_offscreen = gr_create_canvas(LVIEW_W,LVIEW_H);
  541.     
  542.     Draw_all_segments = 1;                        // Say draw all segments, not just connected ones
  543.  
  544.     init_autosave();
  545.   
  546. //    atexit(close_editor);
  547.  
  548.     Clear_window = 1;    //    do full window clear.
  549. }
  550.  
  551. int ShowAbout()
  552. {
  553.     MessageBox( -2, -2, 1,     "INFERNO Mine Editor\n\n"        \
  554.                                     "Copyright (c) 1993  Parallax Software Corp.",
  555.                                     "OK");
  556.     return 0;
  557. }
  558.  
  559. void move_player_2_segment(segment *seg,int side);
  560.  
  561. int SetPlayerFromCurseg()
  562. {
  563.     move_player_2_segment(Cursegp,Curside);
  564.     Update_flags |= UF_ED_STATE_CHANGED | UF_GAME_VIEW_CHANGED;
  565.     return 1;
  566. }
  567.  
  568. int fuelcen_create_from_curseg()
  569. {
  570.     Cursegp->special = SEGMENT_IS_FUELCEN;
  571.     fuelcen_activate( Cursegp, Cursegp->special);
  572.     return 1;
  573. }
  574.  
  575. int repaircen_create_from_curseg()
  576. {
  577.     Int3();    //    -- no longer supported!
  578. //    Cursegp->special = SEGMENT_IS_REPAIRCEN;
  579. //    fuelcen_activate( Cursegp, Cursegp->special);
  580.     return 1;
  581. }
  582.  
  583. int controlcen_create_from_curseg()
  584. {
  585.     Cursegp->special = SEGMENT_IS_CONTROLCEN;
  586.     fuelcen_activate( Cursegp, Cursegp->special);
  587.     return 1;
  588. }
  589.  
  590. int robotmaker_create_from_curseg()
  591. {
  592.     Cursegp->special = SEGMENT_IS_ROBOTMAKER;
  593.     fuelcen_activate( Cursegp, Cursegp->special);
  594.     return 1;
  595. }
  596.  
  597. int fuelcen_reset_all()    {
  598.     fuelcen_reset();
  599.     return 1;
  600. }
  601.  
  602. int fuelcen_delete_from_curseg() {
  603.     fuelcen_delete( Cursegp );
  604.     return 1;
  605. }
  606.  
  607.  
  608. //@@//this routine places the viewer in the center of the side opposite to curside,
  609. //@@//with the view toward the center of curside
  610. //@@int SetPlayerFromCursegMinusOne()
  611. //@@{
  612. //@@    vms_vector vp;
  613. //@@
  614. //@@//    int newseg,newside;
  615. //@@//    get_previous_segment(SEG_PTR_2_NUM(Cursegp),Curside,&newseg,&newside);
  616. //@@//    move_player_2_segment(&Segments[newseg],newside);
  617. //@@
  618. //@@    med_compute_center_point_on_side(&Player->obj_position,Cursegp,Side_opposite[Curside]);
  619. //@@    med_compute_center_point_on_side(&vp,Cursegp,Curside);
  620. //@@    vm_vec_sub2(&vp,&Player->position);
  621. //@@    vm_vector_2_matrix(&Player->orient,&vp,NULL,NULL);
  622. //@@
  623. //@@    Player->seg = SEG_PTR_2_NUM(Cursegp);
  624. //@@
  625. //@@    Update_flags |= UF_GAME_VIEW_CHANGED;
  626. //@@    return 1;
  627. //@@}
  628.  
  629. //this constant determines how much of the window will be occupied by the
  630. //viewed side when SetPlayerFromCursegMinusOne() is called.  It actually
  631. //determine how from from the center of the window the farthest point will be
  632. #define SIDE_VIEW_FRAC (f1_0*8/10)    //80%
  633.  
  634.  
  635. void move_player_2_segment_and_rotate(segment *seg,int side)
  636. {
  637.     vms_vector vp;
  638.     vms_vector    upvec;
  639.     static edgenum=0;
  640.  
  641.     compute_segment_center(&ConsoleObject->pos,seg);
  642.     compute_center_point_on_side(&vp,seg,side);
  643.     vm_vec_sub2(&vp,&ConsoleObject->pos);
  644.  
  645.     vm_vec_sub(&upvec, &Vertices[Cursegp->verts[Side_to_verts[Curside][edgenum%4]]], &Vertices[Cursegp->verts[Side_to_verts[Curside][(edgenum+3)%4]]]);
  646.     edgenum++;
  647.  
  648.     vm_vector_2_matrix(&ConsoleObject->orient,&vp,&upvec,NULL);
  649. //    vm_vector_2_matrix(&ConsoleObject->orient,&vp,NULL,NULL);
  650.  
  651.     obj_relink( ConsoleObject-Objects, SEG_PTR_2_NUM(seg) );
  652.     
  653. }
  654.  
  655. int SetPlayerFromCursegAndRotate()
  656. {
  657.     move_player_2_segment_and_rotate(Cursegp,Curside);
  658.     Update_flags |= UF_ED_STATE_CHANGED | UF_GAME_VIEW_CHANGED;
  659.     return 1;
  660. }
  661.  
  662.  
  663. //sets the player facing curseg/curside, normal to face0 of curside, and
  664. //far enough away to see all of curside
  665. int SetPlayerFromCursegMinusOne()
  666. {
  667.     vms_vector view_vec,view_vec2,side_center;
  668.     vms_vector corner_v[4];
  669.     vms_vector    upvec;
  670.     g3s_point corner_p[4];
  671.     int i;
  672.     fix max,view_dist=f1_0*10;
  673.     static edgenum=0;
  674.     int newseg;
  675.  
  676.     view_vec = Cursegp->sides[Curside].normals[0];
  677.     vm_vec_negate(&view_vec);
  678.  
  679.     compute_center_point_on_side(&side_center,Cursegp,Curside);
  680.     vm_vec_copy_scale(&view_vec2,&view_vec,view_dist);
  681.     vm_vec_sub(&ConsoleObject->pos,&side_center,&view_vec2);
  682.  
  683.     vm_vec_sub(&upvec, &Vertices[Cursegp->verts[Side_to_verts[Curside][edgenum%4]]], &Vertices[Cursegp->verts[Side_to_verts[Curside][(edgenum+3)%4]]]);
  684.     edgenum++;
  685.  
  686.     vm_vector_2_matrix(&ConsoleObject->orient,&view_vec,&upvec,NULL);
  687.  
  688.     gr_set_current_canvas(Canv_editor_game);
  689.     g3_start_frame();
  690.     g3_set_view_matrix(&ConsoleObject->pos,&ConsoleObject->orient,Render_zoom);
  691.  
  692.     for (i=max=0;i<4;i++) {
  693.         corner_v[i] = Vertices[Cursegp->verts[Side_to_verts[Curside][i]]];
  694.         g3_rotate_point(&corner_p[i],&corner_v[i]);
  695.         if (labs(corner_p[i].x) > max) max = labs(corner_p[i].x);
  696.         if (labs(corner_p[i].y) > max) max = labs(corner_p[i].y);
  697.     }
  698.  
  699.     view_dist = fixmul(view_dist,fixdiv(fixdiv(max,SIDE_VIEW_FRAC),corner_p[0].z));
  700.     vm_vec_copy_scale(&view_vec2,&view_vec,view_dist);
  701.     vm_vec_sub(&ConsoleObject->pos,&side_center,&view_vec2);
  702.  
  703.     //obj_relink(ConsoleObject-Objects, SEG_PTR_2_NUM(Cursegp) );
  704.     //update_object_seg(ConsoleObject);        //might have backed right out of curseg
  705.  
  706.     newseg = find_point_seg(&ConsoleObject->pos,SEG_PTR_2_NUM(Cursegp) );
  707.     if (newseg != -1)
  708.         obj_relink(ConsoleObject-Objects,newseg);
  709.  
  710.     Update_flags |= UF_ED_STATE_CHANGED | UF_GAME_VIEW_CHANGED;
  711.     return 1;
  712. }
  713.  
  714. int ToggleLighting(void)
  715. {
  716.     char    outstr[80] = "[shift-L] ";
  717.     int    chindex;
  718.  
  719.     Lighting_on++;
  720.     if (Lighting_on >= 2)
  721.         Lighting_on = 0;
  722.  
  723.     Update_flags |= UF_GAME_VIEW_CHANGED;
  724.  
  725.     if (last_keypress == KEY_L + KEY_SHIFTED)
  726.         chindex = 0;
  727.     else
  728.         chindex = 10;
  729.  
  730.     switch (Lighting_on) {
  731.         case 0:
  732.             strcpy(&outstr[chindex],"Lighting off.");
  733.             break;
  734.         case 1:
  735.             strcpy(&outstr[chindex],"Static lighting.");
  736.             break;
  737.         case 2:
  738.             strcpy(&outstr[chindex],"Ship lighting.");
  739.             break;
  740.         case 3:
  741.             strcpy(&outstr[chindex],"Ship and static lighting.");
  742.             break;
  743.     }
  744.  
  745.     diagnostic_message(outstr);
  746.  
  747.     return Lighting_on;
  748. }
  749.  
  750. void find_concave_segs();
  751.  
  752. int FindConcaveSegs()
  753. {
  754.     find_concave_segs();
  755.  
  756.     Update_flags |= UF_ED_STATE_CHANGED;        //list may have changed
  757.  
  758.     return 1;
  759. }
  760.  
  761. int DosShell()
  762. {
  763.     int ok, w, h;
  764.     grs_bitmap * save_bitmap;
  765.  
  766.     // Save the current graphics state.
  767.  
  768.     w = grd_curscreen->sc_canvas.cv_bitmap.bm_w;
  769.     h = grd_curscreen->sc_canvas.cv_bitmap.bm_h;
  770.  
  771.     save_bitmap = gr_create_bitmap( w, h );
  772.     gr_bm_ubitblt(w, h, 0, 0, 0, 0, &(grd_curscreen->sc_canvas.cv_bitmap), save_bitmap );
  773.  
  774.     gr_restore_mode();
  775.  
  776.     printf( "\n\nType EXIT to return to Inferno" );
  777.     fflush(stdout);
  778.  
  779.     key_close();
  780.     ok = spawnl(P_WAIT,getenv("COMSPEC"), NULL );
  781.     key_init();
  782.  
  783.     gr_set_mode(grd_curscreen->sc_mode);
  784.     gr_bm_ubitblt(w, h, 0, 0, 0, 0, save_bitmap, &(grd_curscreen->sc_canvas.cv_bitmap));
  785.     gr_free_bitmap( save_bitmap );
  786.     //gr_pal_setblock( 0, 256, grd_curscreen->pal );
  787.     //gr_use_palette_table();
  788.  
  789.     return 1;
  790.  
  791. }
  792.  
  793. int ToggleOutlineMode()
  794. {    int mode;
  795.  
  796.     mode=toggle_outline_mode();
  797.  
  798.     if (mode)
  799.         if (last_keypress != KEY_O)
  800.             diagnostic_message("[O] Outline Mode ON.");
  801.         else
  802.             diagnostic_message("Outline Mode ON.");
  803.     else
  804.         if (last_keypress != KEY_O)
  805.             diagnostic_message("[O] Outline Mode OFF.");
  806.         else
  807.             diagnostic_message("Outline Mode OFF.");
  808.  
  809.     Update_flags |= UF_GAME_VIEW_CHANGED;
  810.     return mode;
  811. }
  812.  
  813. //@@int do_reset_orient()
  814. //@@{
  815. //@@    slew_reset_orient(SlewObj);
  816. //@@
  817. //@@    Update_flags |= UF_GAME_VIEW_CHANGED;
  818. //@@
  819. //@@    * (ubyte *) 0x417 &= ~0x20;
  820. //@@
  821. //@@    return 1;
  822. //@@}
  823.  
  824. int GameZoomOut()
  825. {
  826.     Render_zoom = fixmul(Render_zoom,68985);
  827.     Update_flags |= UF_GAME_VIEW_CHANGED;
  828.     return 1;
  829. }
  830.  
  831. int GameZoomIn()
  832. {
  833.     Render_zoom = fixmul(Render_zoom,62259);
  834.     Update_flags |= UF_GAME_VIEW_CHANGED;
  835.     return 1;
  836. }
  837.  
  838.  
  839. int med_keypad_goto_0()    {    ui_pad_goto(0);    return 0;    }
  840. int med_keypad_goto_1()    {    ui_pad_goto(1);    return 0;    }
  841. int med_keypad_goto_2()    {    ui_pad_goto(2);    return 0;    }
  842. int med_keypad_goto_3()    {    ui_pad_goto(3);    return 0;    }
  843. int med_keypad_goto_4()    {    ui_pad_goto(4);    return 0;    }
  844. int med_keypad_goto_5()    {    ui_pad_goto(5);    return 0;    }
  845. int med_keypad_goto_6()    {    ui_pad_goto(6);    return 0;    }
  846. int med_keypad_goto_7()    {    ui_pad_goto(7);    return 0;    }
  847. int med_keypad_goto_8()    {    ui_pad_goto(8);    return 0;    }
  848.  
  849. #define    PAD_WIDTH    30
  850. #define    PAD_WIDTH1    (PAD_WIDTH + 7)
  851.  
  852. int editor_screen_open = 0;
  853.  
  854. //setup the editors windows, canvases, gadgets, etc.
  855. //called whenever the editor screen is selected
  856. void init_editor_screen()
  857. {    
  858. //    grs_bitmap * bmp;
  859.  
  860.     if (editor_screen_open) return;
  861.  
  862.     grd_curscreen->sc_canvas.cv_font = editor_font;
  863.     
  864.     //create canvas for game on the editor screen
  865.     initializing = 1;
  866.     gr_set_current_canvas(Canv_editor);
  867.     Canv_editor->cv_font = editor_font;
  868.     gr_init_sub_canvas(Canv_editor_game,Canv_editor,GAMEVIEW_X,GAMEVIEW_Y,GAMEVIEW_W,GAMEVIEW_H);
  869.     
  870.     //Editor renders into full (320x200) game screen 
  871.  
  872.     init_info = 1;
  873.  
  874.     //do other editor screen setup
  875.  
  876.     // Since the palette might have changed, find some good colors...
  877.     CBLACK = gr_find_closest_color( 1, 1, 1 );
  878.     CGREY = gr_find_closest_color( 28, 28, 28 );
  879.     CWHITE = gr_find_closest_color( 38, 38, 38 );
  880.     CBRIGHT = gr_find_closest_color( 60, 60, 60 );
  881.     CRED = gr_find_closest_color( 63, 0, 0 );
  882.  
  883.     gr_set_curfont(editor_font);
  884.     gr_set_fontcolor( CBLACK, CWHITE );
  885.  
  886.     EditorWindow = ui_open_window( 0 , 0, ED_SCREEN_W, ED_SCREEN_H, WIN_FILLED );
  887.  
  888.     LargeViewBox    = ui_add_gadget_userbox( EditorWindow,LVIEW_X,LVIEW_Y,LVIEW_W,LVIEW_H);
  889. #if ORTHO_VIEWS
  890.     TopViewBox        = ui_add_gadget_userbox( EditorWindow,TVIEW_X,TVIEW_Y,TVIEW_W,TVIEW_H);
  891.      FrontViewBox    = ui_add_gadget_userbox( EditorWindow,FVIEW_X,FVIEW_Y,FVIEW_W,FVIEW_H);
  892.     RightViewBox    = ui_add_gadget_userbox( EditorWindow,RVIEW_X,RVIEW_Y,RVIEW_W,RVIEW_H);
  893. #endif
  894.     ui_gadget_calc_keys(EditorWindow);    //make tab work for all windows
  895.  
  896.     GameViewBox    = ui_add_gadget_userbox( EditorWindow, GAMEVIEW_X, GAMEVIEW_Y, GAMEVIEW_W, GAMEVIEW_H );
  897. //    GroupViewBox    = ui_add_gadget_userbox( EditorWindow,GVIEW_X,GVIEW_Y,GVIEW_W,GVIEW_H);
  898.  
  899. //    GameViewBox->when_tab = GameViewBox->when_btab = (UI_GADGET *) LargeViewBox;
  900. //    LargeViewBox->when_tab = LargeViewBox->when_btab = (UI_GADGET *) GameViewBox;
  901.  
  902. //    ui_gadget_calc_keys(EditorWindow);    //make tab work for all windows
  903.  
  904.     ViewIcon    = ui_add_gadget_icon( EditorWindow, "Lock\nview",    455,25+530,     40, 22,    KEY_V+KEY_CTRLED, ToggleLockViewToCursegp );
  905.     AllIcon    = ui_add_gadget_icon( EditorWindow, "Draw\nall",    500,25+530,      40, 22,    KEY_A+KEY_CTRLED, ToggleDrawAllSegments );
  906.     AxesIcon    = ui_add_gadget_icon( EditorWindow, "Coord\naxes",545,25+530,        40, 22,    KEY_D+KEY_CTRLED, ToggleCoordAxes );
  907. //-NOLIGHTICON-    LightIcon    = ui_add_gadget_icon( EditorWindow, "Light\ning",    590,25+530,     40, 22,    KEY_L+KEY_SHIFTED,ToggleLighting );
  908.     ChaseIcon    = ui_add_gadget_icon( EditorWindow, "Chase\nmode",635,25+530,        40, 22,    -1,                ToggleChaseMode );
  909.     OutlineIcon = ui_add_gadget_icon( EditorWindow, "Out\nline",     680,25+530,      40, 22,    KEY_O,            ToggleOutlineMode );
  910.     LockIcon    = ui_add_gadget_icon( EditorWindow, "Lock\nstep", 725,25+530,     40, 22,    KEY_L,            ToggleLockstep );
  911.  
  912.     meddraw_init_views(LargeViewBox->canvas);
  913.  
  914.     //ui_add_gadget_button( EditorWindow, 460, 510, 50, 25, "Quit", ExitEditor );
  915.     //ui_add_gadget_button( EditorWindow, 520, 510, 50, 25, "Lisp", CallLisp );
  916.     //ui_add_gadget_button( EditorWindow, 580, 510, 50, 25, "Mine", MineMenu );
  917.     //ui_add_gadget_button( EditorWindow, 640, 510, 50, 25, "Help", DoHelp );
  918.     //ui_add_gadget_button( EditorWindow, 460, 540, 50, 25, "Macro", MacroMenu );
  919.     //ui_add_gadget_button( EditorWindow, 520, 540, 50, 25, "About", ShowAbout );
  920.     //ui_add_gadget_button( EditorWindow, 640, 540, 50, 25, "Shell", DosShell );
  921.  
  922.     ui_pad_activate( EditorWindow, PAD_X, PAD_Y );
  923.     Pad_text_canvas = gr_create_sub_canvas(Canv_editor, PAD_X + 250, PAD_Y + 8, 180, 160);
  924.     ui_add_gadget_button( EditorWindow, PAD_X+6, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "<<",  med_keypad_goto_prev );
  925.     ui_add_gadget_button( EditorWindow, PAD_X+PAD_WIDTH1+6, PAD_Y+(30*5)+22, PAD_WIDTH, 20, ">>",  med_keypad_goto_next );
  926.  
  927.     {    int    i;
  928.         i = 0;    ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "SR",  med_keypad_goto_0 );
  929.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "SS",  med_keypad_goto_1 );
  930.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "CF",  med_keypad_goto_2 );
  931.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "TM",  med_keypad_goto_3 );
  932.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "OP",  med_keypad_goto_4 );
  933.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "OR",  med_keypad_goto_5 );
  934.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "GE",  med_keypad_goto_6 );
  935.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "LI",  med_keypad_goto_7 );
  936.         i++;        ui_add_gadget_button( EditorWindow, PAD_X+16+(i+2)*PAD_WIDTH1, PAD_Y+(30*5)+22, PAD_WIDTH, 20, "TT",  med_keypad_goto_8 );
  937.     }
  938.  
  939.     gr_set_curfont(editor_font);
  940.     menubar_show();
  941.  
  942.     // INIT TEXTURE STUFF
  943.     texpage_init( EditorWindow );
  944.     objpage_init( EditorWindow );
  945.  
  946.     EditorWindow->keyboard_focus_gadget = (UI_GADGET *)LargeViewBox;
  947.  
  948.     canv_offscreen->cv_font = grd_curscreen->sc_canvas.cv_font;
  949. //    BigCanvas[0]->cv_font = grd_curscreen->sc_canvas.cv_font; 
  950. //    BigCanvas[1]->cv_font = grd_curscreen->sc_canvas.cv_font; 
  951. //    BigCanvasFirstTime = 1;
  952.  
  953.     // Draw status box
  954.     gr_set_current_canvas( NULL );
  955.     gr_setcolor( CGREY );
  956.     gr_rect(STATUS_X,STATUS_Y,STATUS_X+STATUS_W-1,STATUS_Y+STATUS_H-1);            //0, 582, 799, 599 );
  957.  
  958.     // Draw icon box
  959.     // gr_set_current_canvas( NULL );
  960.     //  gr_setcolor( CBRIGHT );
  961.     //  gr_rect( 528, 2, 798, 22);
  962.     //  gr_setcolor( CGREY);
  963.     //  gr_rect( 530, 2, 799, 20);
  964.  
  965.     Update_flags = UF_ALL;
  966.     initializing = 0;
  967.     editor_screen_open = 1;
  968. }
  969.  
  970. //shutdown ui on the editor screen
  971. close_editor_screen()
  972. {
  973.     if (!editor_screen_open) return;
  974.  
  975.     editor_screen_open = 0;
  976.     ui_pad_deactivate();
  977.     gr_free_sub_canvas(Pad_text_canvas);
  978.  
  979.     ui_close_window(EditorWindow);
  980.  
  981.     close_all_windows();
  982.  
  983.     // CLOSE TEXTURE STUFF
  984.     texpage_close();
  985.     objpage_close();
  986.  
  987.     menubar_hide();
  988.  
  989. }
  990.  
  991. med_show_warning(char *s)
  992. {
  993.     grs_canvas *save_canv=grd_curcanv;
  994.  
  995.     //gr_pal_fade_in(grd_curscreen->pal);    //in case palette is blacked
  996.  
  997.     MessageBox(-2,-2,1,s,"OK");
  998.  
  999.     gr_set_current_canvas(save_canv);
  1000.  
  1001. }
  1002.  
  1003. // Returns 1 if OK to trash current mine.
  1004. int SafetyCheck()
  1005. {
  1006.     int x;
  1007.             
  1008.     if (mine_changed) {
  1009.         stop_time();                
  1010.         x = nm_messagebox( "Warning!", 2, "Cancel", "OK", "You are about to lose work." );
  1011.         if (x<1) {
  1012.             start_time();
  1013.             return 0;
  1014.         }
  1015.         start_time();
  1016.     }
  1017.     return 1;
  1018. }
  1019.  
  1020. //called at the end of the program
  1021. void close_editor() {
  1022.  
  1023.     close_autosave();
  1024.  
  1025.     menubar_close();
  1026.     
  1027.     gr_close_font(editor_font);
  1028.  
  1029.     gr_free_canvas(canv_offscreen); canv_offscreen = NULL;
  1030.  
  1031.     return;
  1032.  
  1033. }
  1034.  
  1035. //variables for find segments process
  1036.  
  1037. // ---------------------------------------------------------------------------------------------------
  1038. //    Subtract all elements in Found_segs from selected list.
  1039. void subtract_found_segments_from_selected_list(void)
  1040. {
  1041.     int    s,f;
  1042.  
  1043.     for (f=0; f<N_found_segs; f++) {
  1044.         int    foundnum = Found_segs[f];
  1045.  
  1046.         for (s=0; s<N_selected_segs; s++) {
  1047.             if (Selected_segs[s] == foundnum) {
  1048.                 Selected_segs[s] = Selected_segs[N_selected_segs-1];
  1049.                 N_selected_segs--;
  1050.                 break;
  1051.             }
  1052.         }
  1053.     }
  1054. }
  1055.  
  1056. // ---------------------------------------------------------------------------------------------------
  1057. //    Add all elements in Found_segs to selected list.
  1058. void add_found_segments_to_selected_list(void) {
  1059.     int    s,f;
  1060.  
  1061.     for (f=0; f<N_found_segs; f++) {
  1062.         int    foundnum = Found_segs[f];
  1063.  
  1064.         for (s=0; s<N_selected_segs; s++)
  1065.             if (Selected_segs[s] == foundnum)
  1066.                 break;
  1067.  
  1068.         if (s == N_selected_segs)
  1069.             Selected_segs[N_selected_segs++] = foundnum;
  1070.     }
  1071. }
  1072.  
  1073. void gamestate_restore_check() {
  1074.     char Message[DIAGNOSTIC_MESSAGE_MAX];
  1075.     obj_position Save_position;
  1076.  
  1077.     if (gamestate_not_restored) {
  1078.         sprintf( Message, "Do you wish to restore game state?\n");
  1079.     
  1080.         if (MessageBox( -2, -2, 2, Message, "Yes", "No" )==1) {
  1081.  
  1082.             // Save current position
  1083.             Save_position.pos = ConsoleObject->pos;
  1084.             Save_position.orient = ConsoleObject->orient;
  1085.             Save_position.segnum = ConsoleObject->segnum;
  1086.  
  1087.             load_level("GAMESAVE.LVL");
  1088.  
  1089.             // Restore current position
  1090.             if (Save_position.segnum <= Highest_segment_index) {
  1091.                 ConsoleObject->pos = Save_position.pos;
  1092.                 ConsoleObject->orient = Save_position.orient;
  1093.                 obj_relink(ConsoleObject-Objects,Save_position.segnum);
  1094.             }
  1095.  
  1096.             gamestate_not_restored = 0;
  1097.             Update_flags |= UF_WORLD_CHANGED;    
  1098.             }
  1099.         else
  1100.             gamestate_not_restored = 1;
  1101.         }
  1102. }
  1103.  
  1104. void RestoreGameState() {
  1105.     load_level("GAMESAVE.LVL");
  1106.     gamestate_not_restored = 0;
  1107.  
  1108.     mprintf((0, "Gamestate restored.\n"));
  1109.     editor_status("Gamestate restored.\n");
  1110.  
  1111.     Update_flags |= UF_WORLD_CHANGED;
  1112. }
  1113.  
  1114. extern void check_wall_validity(void);
  1115.  
  1116. // ---------------------------------------------------------------------------------------------------
  1117. //this function is the editor. called when editor mode selected.  runs until
  1118. //game mode or exit selected
  1119. void editor(void)
  1120. {
  1121.     int w,h;
  1122.     grs_bitmap * savedbitmap;
  1123.     editor_view *new_cv;
  1124.     static padnum=0;
  1125.     vms_matrix    MouseRotMat,tempm;
  1126.     //@@short camera_objnum;            //a camera for viewing
  1127.  
  1128.     init_editor();
  1129.  
  1130.     InitCurve();
  1131.  
  1132.     restore_effect_bitmap_icons();
  1133.  
  1134.     if (!set_screen_mode(SCREEN_EDITOR))    {
  1135.         set_screen_mode(SCREEN_GAME);
  1136.         Function_mode=FMODE_GAME;            //force back into game
  1137.         return;
  1138.     }
  1139.  
  1140.     gr_set_current_canvas( NULL );
  1141.     gr_set_curfont(editor_font);
  1142.  
  1143.     //Editor renders into full (320x200) game screen 
  1144.  
  1145.     set_warn_func(med_show_warning);
  1146.  
  1147.     keyd_repeat = 1;        // Allow repeat in editor
  1148.  
  1149. //    _MARK_("start of editor");//Nuked to compile -KRB
  1150.  
  1151.     ui_mouse_hide();
  1152.  
  1153.     ui_reset_idle_seconds();
  1154.  
  1155. //@@    //create a camera for viewing in the editor. copy position from ConsoleObject
  1156. //@@    camera_objnum = obj_create(OBJ_CAMERA,0,ConsoleObject->segnum,&ConsoleObject->pos,&ConsoleObject->orient,0);
  1157. //@@    Viewer = &Objects[camera_objnum];
  1158. //@@    slew_init(Viewer);        //camera is slewing
  1159.  
  1160.     Viewer = ConsoleObject;
  1161.     slew_init(ConsoleObject);
  1162.  
  1163.     Update_flags = UF_ALL;
  1164.  
  1165.     medlisp_update_screen();
  1166.  
  1167.     //set the wire-frame window to be the current view
  1168.     current_view = &LargeView;
  1169.  
  1170.     if (faded_in==0)
  1171.     {
  1172.         faded_in = 1;
  1173.         //gr_pal_fade_in( grd_curscreen->pal );
  1174.     }
  1175.  
  1176.     w = GameViewBox->canvas->cv_bitmap.bm_w;
  1177.     h = GameViewBox->canvas->cv_bitmap.bm_h;
  1178.     
  1179.     savedbitmap = gr_create_bitmap(w, h );
  1180.  
  1181.     gr_bm_ubitblt( w, h, 0, 0, 0, 0, &GameViewBox->canvas->cv_bitmap, savedbitmap );
  1182.  
  1183.     gr_set_current_canvas( GameViewBox->canvas );
  1184.     gr_set_curfont(editor_font);
  1185.     //gr_setcolor( CBLACK );
  1186.     //gr_deaccent_canvas();
  1187.     //gr_grey_canvas();
  1188.     
  1189.     ui_mouse_show();
  1190.  
  1191.     gr_set_curfont(editor_font);
  1192.     ui_pad_goto(padnum);
  1193.  
  1194.     gamestate_restore_check();
  1195.  
  1196.     while (Function_mode == FMODE_EDITOR) {
  1197.  
  1198.         gr_set_curfont(editor_font);
  1199.         info_display_all(EditorWindow);
  1200.  
  1201.         ModeFlag = 0;
  1202.  
  1203.         // Update the windows
  1204.  
  1205.         // Only update if there is no key waiting and we're not in
  1206.         // fast play mode.
  1207.         if (!key_peekkey()) //-- && (MacroStatus != UI_STATUS_FASTPLAY))
  1208.             medlisp_update_screen();
  1209.  
  1210.         //do editor stuff
  1211.         gr_set_curfont(editor_font);
  1212.         ui_mega_process();
  1213.         last_keypress &= ~KEY_DEBUGGED;        //    mask off delete key bit which has no function in editor.
  1214.         ui_window_do_gadgets(EditorWindow);
  1215.         do_robot_window();
  1216.         do_object_window();
  1217.         do_wall_window();
  1218.         do_trigger_window();
  1219.         do_hostage_window();
  1220.         do_centers_window();
  1221.         check_wall_validity();
  1222.         Assert(Num_walls>=0);
  1223.  
  1224.         if (Gameview_lockstep) {
  1225.             static segment *old_cursegp=NULL;
  1226.             static int old_curside=-1;
  1227.  
  1228.             if (old_cursegp!=Cursegp || old_curside!=Curside) {
  1229.                 SetPlayerFromCursegMinusOne();
  1230.                 old_cursegp = Cursegp;
  1231.                 old_curside = Curside;
  1232.             }
  1233.         }
  1234.  
  1235. //        mprintf((0, "%d    ", ui_get_idle_seconds() ));
  1236.  
  1237.         if ( ui_get_idle_seconds() > COMPRESS_INTERVAL ) 
  1238.             {
  1239.             med_compress_mine();
  1240.             ui_reset_idle_seconds();
  1241.             }
  1242.   
  1243. //    Commented out because it occupies about 25% of time in twirling the mine.
  1244. // Removes some Asserts....
  1245. //        med_check_all_vertices();
  1246.         clear_editor_status();        // if enough time elapsed, clear editor status message
  1247.         TimedAutosave(mine_filename);
  1248.         set_editor_time_of_day();
  1249.         gr_set_current_canvas( GameViewBox->canvas );
  1250.         
  1251.         // Remove keys used for slew
  1252.         switch(last_keypress)
  1253.         {
  1254.         case KEY_PAD9:
  1255.         case KEY_PAD7:
  1256.         case KEY_PADPLUS:
  1257.         case KEY_PADMINUS:
  1258.         case KEY_PAD8:
  1259.         case KEY_PAD2:
  1260.         case KEY_LBRACKET:
  1261.         case KEY_RBRACKET:
  1262.         case KEY_PAD1:
  1263.         case KEY_PAD3:
  1264.         case KEY_PAD6:
  1265.         case KEY_PAD4:
  1266.             last_keypress = 0;
  1267.         }
  1268.         if ((last_keypress&0xff)==KEY_LSHIFT) last_keypress=0;
  1269.         if ((last_keypress&0xff)==KEY_RSHIFT) last_keypress=0;
  1270.         if ((last_keypress&0xff)==KEY_LCTRL) last_keypress=0;
  1271.         if ((last_keypress&0xff)==KEY_RCTRL) last_keypress=0;
  1272. //        if ((last_keypress&0xff)==KEY_LALT) last_keypress=0;
  1273. //        if ((last_keypress&0xff)==KEY_RALT) last_keypress=0;
  1274.  
  1275.         gr_set_curfont(editor_font);
  1276.         menubar_do( last_keypress );
  1277.  
  1278.         //=================== DO FUNCTIONS ====================
  1279.  
  1280.         if ( KeyFunction[ last_keypress ] != NULL )    {
  1281.             KeyFunction[last_keypress]();
  1282.             last_keypress = 0;
  1283.         }
  1284.         switch (last_keypress)
  1285.         {
  1286.         case 0:
  1287.         case KEY_Z:
  1288.         case KEY_G:
  1289.         case KEY_LALT:
  1290.         case KEY_RALT:
  1291.         case KEY_LCTRL:
  1292.         case KEY_RCTRL:
  1293.         case KEY_LSHIFT:
  1294.         case KEY_RSHIFT:
  1295.         case KEY_LAPOSTRO:
  1296.             break;
  1297.         case KEY_SHIFTED + KEY_L:
  1298.             ToggleLighting();
  1299.             break;
  1300.         case KEY_F1:
  1301.             render_3d_in_big_window = !render_3d_in_big_window;
  1302.             Update_flags |= UF_ALL;
  1303.             break;            
  1304.         default:
  1305.             {
  1306.             char kdesc[100];
  1307.             GetKeyDescription( kdesc, last_keypress );
  1308.             editor_status("Error: %s isn't bound to anything.", kdesc  );
  1309.             }
  1310.         }
  1311.  
  1312.         //================================================================
  1313.  
  1314.         if (ModeFlag==1)
  1315.         {
  1316.             close_editor_screen();
  1317.             Function_mode=FMODE_EXIT;
  1318.                 gr_free_bitmap( savedbitmap );
  1319.             break;
  1320.         }
  1321.  
  1322.         if (ModeFlag==2) //-- && MacroStatus==UI_STATUS_NORMAL )
  1323.         {
  1324.             ui_mouse_hide();
  1325.             Function_mode = FMODE_GAME;
  1326.             gr_bm_ubitblt( w, h, 0, 0, 0, 0, savedbitmap, &GameViewBox->canvas->cv_bitmap);
  1327.             gr_free_bitmap( savedbitmap );
  1328.             break;
  1329.         }
  1330.  
  1331.         if (ModeFlag==3) //-- && MacroStatus==UI_STATUS_NORMAL )
  1332.         {
  1333. //            med_compress_mine();                        //will be called anyways before game.
  1334.             close_editor_screen();
  1335.             Function_mode=FMODE_GAME;            //force back into game
  1336.             set_screen_mode(SCREEN_GAME);        //put up game screen
  1337.             gr_free_bitmap( savedbitmap );
  1338.             break;
  1339.         }
  1340.  
  1341. //        if (CurWindow->keyboard_focus_gadget == (UI_GADGET *)GameViewBox) current_view=NULL;
  1342. //        if (CurWindow->keyboard_focus_gadget == (UI_GADGET *)GroupViewBox) current_view=NULL;
  1343.  
  1344.         new_cv = current_view ;
  1345.  
  1346. #if ORTHO_VIEWS
  1347.         if (CurWindow->keyboard_focus_gadget == (UI_GADGET *)LargeViewBox) new_cv=&LargeView;
  1348.         if (CurWindow->keyboard_focus_gadget == (UI_GADGET *)TopViewBox)    new_cv=&TopView;
  1349.         if (CurWindow->keyboard_focus_gadget == (UI_GADGET *)FrontViewBox) new_cv=&FrontView;
  1350.         if (CurWindow->keyboard_focus_gadget == (UI_GADGET *)RightViewBox) new_cv=&RightView;
  1351. #endif
  1352.         if (new_cv != current_view ) {
  1353.             current_view->ev_changed = 1;
  1354.             new_cv->ev_changed = 1;
  1355.             current_view = new_cv;
  1356.         }
  1357.  
  1358.         calc_frame_time();
  1359.         if (slew_frame(0)) {        //do movement and check keys
  1360.             Update_flags |= UF_GAME_VIEW_CHANGED;
  1361.             if (Gameview_lockstep) {
  1362.                 Cursegp = &Segments[ConsoleObject->segnum];
  1363.                 med_create_new_segment_from_cursegp();
  1364.                 Update_flags |= UF_ED_STATE_CHANGED;
  1365.             }
  1366.         }
  1367.  
  1368.         // DO TEXTURE STUFF
  1369.         texpage_do();
  1370.         objpage_do();
  1371.  
  1372.  
  1373.         // Process selection of Cursegp using mouse.
  1374.         if (LargeViewBox->mouse_onme && LargeViewBox->b1_clicked && !render_3d_in_big_window) 
  1375.         {
  1376.             int    xcrd,ycrd;
  1377.             xcrd = LargeViewBox->b1_drag_x1;
  1378.             ycrd = LargeViewBox->b1_drag_y1;
  1379.  
  1380.             find_segments(xcrd,ycrd,LargeViewBox->canvas,&LargeView,Cursegp,Big_depth);    // Sets globals N_found_segs, Found_segs
  1381.  
  1382.             // If shift is down, then add segment to found list
  1383.             if (keyd_pressed[ KEY_LSHIFT ] || keyd_pressed[ KEY_RSHIFT ])
  1384.                 subtract_found_segments_from_selected_list();
  1385.             else
  1386.                 add_found_segments_to_selected_list();
  1387.  
  1388.               Found_seg_index = 0;    
  1389.         
  1390.             if (N_found_segs > 0) {
  1391.                 sort_seg_list(N_found_segs,Found_segs,&ConsoleObject->pos);
  1392.                 Cursegp = &Segments[Found_segs[0]];
  1393.                 med_create_new_segment_from_cursegp();
  1394.                 if (Lock_view_to_cursegp)
  1395.                     set_view_target_from_segment(Cursegp);
  1396.             }
  1397.  
  1398.             Update_flags |= UF_ED_STATE_CHANGED | UF_VIEWPOINT_MOVED;
  1399.         }
  1400.  
  1401.         if (GameViewBox->mouse_onme && GameViewBox->b1_dragging) {
  1402.             int    x, y;
  1403.             x = GameViewBox->b1_drag_x2;
  1404.             y = GameViewBox->b1_drag_y2;
  1405.  
  1406.             ui_mouse_hide();
  1407.             gr_set_current_canvas( GameViewBox->canvas );
  1408.             gr_setcolor( 15 );
  1409.             gr_rect( x-1, y-1, x+1, y+1 );
  1410.             ui_mouse_show();
  1411.  
  1412.         }
  1413.         
  1414.         // Set current segment and side by clicking on a polygon in game window.
  1415.         //    If ctrl pressed, also assign current texture map to that side.
  1416.         //if (GameViewBox->mouse_onme && (GameViewBox->b1_done_dragging || GameViewBox->b1_clicked)) {
  1417.         if ((GameViewBox->mouse_onme && GameViewBox->b1_clicked && !render_3d_in_big_window) ||
  1418.             (LargeViewBox->mouse_onme && LargeViewBox->b1_clicked && render_3d_in_big_window)) {
  1419.  
  1420.             int    xcrd,ycrd;
  1421.             int seg,side,face,poly,tmap;
  1422.  
  1423.             if (render_3d_in_big_window) {
  1424.                 xcrd = LargeViewBox->b1_drag_x1;
  1425.                 ycrd = LargeViewBox->b1_drag_y1;
  1426.             }
  1427.             else {
  1428.                 xcrd = GameViewBox->b1_drag_x1;
  1429.                 ycrd = GameViewBox->b1_drag_y1;
  1430.             }
  1431.     
  1432.             //Int3();
  1433.  
  1434.             if (find_seg_side_face(xcrd,ycrd,&seg,&side,&face,&poly)) {
  1435.  
  1436.  
  1437.                 if (seg<0) {                            //found an object
  1438.  
  1439.                     Cur_object_index = -seg-1;
  1440.                     editor_status("Object %d selected.",Cur_object_index);
  1441.  
  1442.                     Update_flags |= UF_ED_STATE_CHANGED;
  1443.                 }
  1444.                 else {
  1445.  
  1446.                     //    See if either shift key is down and, if so, assign texture map
  1447.                     if (keyd_pressed[KEY_LSHIFT] || keyd_pressed[KEY_RSHIFT]) {
  1448.                         Cursegp = &Segments[seg];
  1449.                         Curside = side;
  1450.                         AssignTexture();
  1451.                         med_create_new_segment_from_cursegp();
  1452.                         editor_status("Texture assigned");
  1453.                     } else if (keyd_pressed[KEY_G])    {
  1454.                         tmap = Segments[seg].sides[side].tmap_num;
  1455.                         texpage_grab_current(tmap);
  1456.                         editor_status( "Texture grabbed." );
  1457.                     } else if (keyd_pressed[ KEY_LAPOSTRO] ) {
  1458.                         ui_mouse_hide();
  1459.                         move_object_to_mouse_click();
  1460.                     } else {
  1461.                         Cursegp = &Segments[seg];
  1462.                         Curside = side;
  1463.                         med_create_new_segment_from_cursegp();
  1464.                         editor_status("Curseg and curside selected");
  1465.                     }
  1466.                 }
  1467.  
  1468.                 Update_flags |= UF_ED_STATE_CHANGED;
  1469.             }
  1470.             else 
  1471.                 editor_status("Click on non-texture ingored");
  1472.  
  1473.         }
  1474.  
  1475.         // Allow specification of LargeView using mouse
  1476.         if (keyd_pressed[ KEY_LCTRL ] || keyd_pressed[ KEY_RCTRL ]) {
  1477.             ui_mouse_hide();
  1478.             if ( (Mouse.dx!=0) && (Mouse.dy!=0) ) {
  1479.                 GetMouseRotation( Mouse.dx, Mouse.dy, &MouseRotMat );
  1480.                 vm_matrix_x_matrix(&tempm,&LargeView.ev_matrix,&MouseRotMat);
  1481.                 LargeView.ev_matrix = tempm;
  1482.                 LargeView.ev_changed = 1;
  1483.                 Large_view_index = -1;            // say not one of the orthogonal views
  1484.             }
  1485.         } else  {
  1486.             ui_mouse_show();
  1487.         }
  1488.  
  1489.         if ( keyd_pressed[ KEY_Z ] ) {
  1490.             ui_mouse_hide();
  1491.             if ( Mouse.dy!=0 ) {
  1492.                 current_view->ev_dist += Mouse.dy*10000;
  1493.                 current_view->ev_changed = 1;
  1494.             }
  1495.         } else {
  1496.             ui_mouse_show();
  1497.         }
  1498.  
  1499.     }
  1500.  
  1501. //    _MARK_("end of editor");//Nuked to compile -KRB
  1502.  
  1503.     clear_warn_func(med_show_warning);
  1504.  
  1505.     //kill our camera object
  1506.  
  1507.     Viewer = ConsoleObject;                    //reset viewer
  1508.     //@@obj_delete(camera_objnum);
  1509.  
  1510.     padnum = ui_pad_get_current();
  1511.  
  1512.     close_editor();
  1513.     ui_close();
  1514.  
  1515.  
  1516. }
  1517.  
  1518. void test_fade(void)
  1519. {
  1520.     int    i,c;
  1521.  
  1522.     for (c=0; c<256; c++) {
  1523.         printf("%4i: {%3i %3i %3i} ",c,gr_palette[3*c],gr_palette[3*c+1],gr_palette[3*c+2]);
  1524.         for (i=0; i<16; i++) {
  1525.             int col = gr_fade_table[256*i+c];
  1526.  
  1527.             printf("[%3i %3i %3i] ",gr_palette[3*col],gr_palette[3*col+1],gr_palette[3*col+2]);
  1528.         }
  1529.         if ( (c%16) == 15)
  1530.             printf("\n");
  1531.         printf("\n");
  1532.     }
  1533. }
  1534.  
  1535. void dump_stuff(void)
  1536. {
  1537.     int    i,j,prev_color;
  1538.  
  1539.     printf("Palette:\n");
  1540.  
  1541.     for (i=0; i<256; i++)
  1542.         printf("%3i: %2i %2i %2i\n",i,gr_palette[3*i],gr_palette[3*i+1],gr_palette[3*i+2]);
  1543.  
  1544.     for (i=0; i<16; i++) {
  1545.         printf("\nFade table #%i\n",i);
  1546.         for (j=0; j<256; j++) {
  1547.             int    c = gr_fade_table[i*256 + j];
  1548.             printf("[%3i %2i %2i %2i] ",c, gr_palette[3*c], gr_palette[3*c+1], gr_palette[3*c+2]);
  1549.             if ((j % 8) == 7)
  1550.                 printf("\n");
  1551.         }
  1552.     }
  1553.  
  1554.     printf("Colors indexed by intensity:\n");
  1555.     printf(". = change from previous, * = no change\n");
  1556.     for (j=0; j<256; j++) {
  1557.         printf("%3i: ",j);
  1558.         prev_color = -1;
  1559.         for (i=0; i<16; i++) {
  1560.             int    c = gr_fade_table[i*256 + j];
  1561.             if (c == prev_color)
  1562.                 printf("*");
  1563.             else
  1564.                 printf(".");
  1565.             prev_color = c;
  1566.         }
  1567.         printf("  ");
  1568.         for (i=0; i<16; i++) {
  1569.             int    c = gr_fade_table[i*256 + j];
  1570.             printf("[%3i %2i %2i %2i] ", c, gr_palette[3*c], gr_palette[3*c+1], gr_palette[3*c+2]);
  1571.         }
  1572.         printf("\n");
  1573.     }
  1574.  
  1575. }
  1576.  
  1577.  
  1578. int MarkStart(void)
  1579. {
  1580.     char mystr[30];
  1581.     sprintf(mystr,"mark %i start",Mark_count);
  1582. //    _MARK_(mystr);//Nuked to compile -KRB
  1583.  
  1584.     return 1;
  1585. }
  1586.  
  1587. int MarkEnd(void)
  1588. {
  1589.     char mystr[30];
  1590.     sprintf(mystr,"mark %i end",Mark_count);
  1591.     Mark_count++;
  1592. //    _MARK_(mystr);//Nuked to compile -KRB
  1593.  
  1594.     return 1;
  1595. }
  1596.  
  1597. 
  1598.