1 //-------------------------------------------------------------------------
2 /*
3 Copyright (C) 1996, 2005 - 3D Realms Entertainment
4 
5 This file is NOT part of Shadow Warrior version 1.2
6 However, it is either an older version of a file that is, or is
7 some test code written during the development of Shadow Warrior.
8 This file is provided purely for educational interest.
9 
10 Shadow Warrior is free software; you can redistribute it and/or
11 modify it under the terms of the GNU General Public License
12 as published by the Free Software Foundation; either version 2
13 of the License, or (at your option) any later version.
14 
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
18 
19 See the GNU General Public License for more details.
20 
21 You should have received a copy of the GNU General Public License
22 along with this program; if not, write to the Free Software
23 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
24 
25 Prepared for public release: 03/28/2005 - Charlie Wiederhold, 3D Realms
26 */
27 //-------------------------------------------------------------------------
28 
29 #include "build.h"
30 #include "editor.h"
31 
32 #include "keys.h"
33 #include "names2.h"
34 #include "game.h"
35 
36 
37 extern int posx, posy, posz;
38 extern short cursectnum;
39 extern short ang;
40 extern int horiz;
41 extern int qsetmode;
42 
43 BOOL FindCeilingView(short match, LONGp x, LONGp y, LONG z, SHORTp sectnum);
44 BOOL FindFloorView(short match, LONGp x, LONGp y, LONG z, SHORTp sectnum);
45 short ViewSectorInScene(short cursectnum, short type, short level);
46 void Message(char *string, char color);
47 
48 
49 void
_Assert(char * expr,char * strFile,unsigned uLine)50 _Assert(char *expr, char *strFile, unsigned uLine)
51     {
52     printf(ds, "Assertion failed: %s %s, line %u\n", expr, strFile, uLine);
53     //DSPRINTF(ds, "Assertion failed: %s %s, line %u", expr, strFile, uLine);
54     MONO_PRINT(ds);
55     exit(0);
56     }
57 
58 ////////////////////////////////////////////////////////////////////
59 //
60 // FLOOR ABOVE FLOOR
61 //
62 ////////////////////////////////////////////////////////////////////
63 
64 
65 #define ZMAX 400
66 typedef struct
67     {
68     LONG zval[ZMAX];
69     SHORT sectnum[ZMAX];
70     SHORT pic[ZMAX];
71     SHORT slope[ZMAX];
72     SHORT zcount;
73     } SAVE, *SAVEp;
74 
75 SAVE save;
76 
77 BOOL FAF_DebugView = 0;
78 BOOL FAFon = 0;
79 BOOL FAF_DontMoveSectors = FALSE;
80 
81 short bak_searchsector, bak_searchwall, bak_searchstat;
82 extern short searchsector, searchwall, searchstat, searchit;
83 
84 VOID SetupBuildFAF(VOID);
85 VOID ResetBuildFAF(VOID);
86 
ToggleFAF(void)87 void ToggleFAF(void)
88     {
89     if (keystatus[KEYSC_3])
90         {
91         keystatus[KEYSC_3] = FALSE;
92 
93         FLIP(FAFon, 1);
94         if (FAFon)
95             {
96             SetupBuildFAF();
97             }
98         else
99             {
100             ResetBuildFAF();
101             }
102         }
103 
104     if (FAFon && qsetmode == 200)
105         {
106         DrawOverlapRoom(posx, posy, posz, ang, horiz, cursectnum);
107 
108         // make it so that you can edit both areas in 3D
109         // back up vars after the first drawrooms
110         bak_searchsector = searchsector;
111         bak_searchwall = searchwall;
112         bak_searchstat = searchstat;
113         searchit = 2;
114         }
115 
116     if (FAFon && qsetmode == 200 && keystatus[KEYSC_4])
117         {
118         short match;
119         int tx,ty,tz;
120         short tsectnum;
121         short i;
122         keystatus[KEYSC_4] = FALSE;
123 
124         tx = posx;
125         ty = posy;
126         tz = posz;
127         tsectnum = cursectnum;
128 
129         save.zcount = 0;
130 
131         if (sector[cursectnum].ceilingpicnum == FAF_MIRROR_PIC)
132             {
133             match = ViewSectorInScene(tsectnum, VIEW_THRU_CEILING, VIEW_LEVEL1);
134 
135             FAF_DontMoveSectors = TRUE;
136             FindCeilingView(match, &tx, &ty, tz, &tsectnum);
137             FAF_DontMoveSectors = FALSE;
138 
139             posx = tx;
140             posy = ty;
141             cursectnum = tsectnum;
142             posz = sector[cursectnum].floorz - Z(20);
143             }
144         else
145         if (sector[cursectnum].floorpicnum == FAF_MIRROR_PIC)
146             {
147             match = ViewSectorInScene(tsectnum, VIEW_THRU_FLOOR, VIEW_LEVEL2);
148 
149             FAF_DontMoveSectors = TRUE;
150             FindFloorView(match, &tx, &ty, tz, &tsectnum);
151             FAF_DontMoveSectors = FALSE;
152 
153             posx = tx;
154             posy = ty;
155             cursectnum = tsectnum;
156             posz = sector[cursectnum].ceilingz + Z(20);
157             }
158         }
159 
160 
161     }
162 
163 
FAF_AfterDrawRooms(void)164 void FAF_AfterDrawRooms(void)
165     {
166     // make it so that you can edit both areas in 3D
167     // if your cursor is in the FAF_MIRROR_PIC area use the vars from the first
168     // drawrooms instead
169     if ((searchstat == 1 && sector[searchsector].ceilingpicnum == FAF_MIRROR_PIC) ||
170         (searchstat == 2 && sector[searchsector].floorpicnum == FAF_MIRROR_PIC))
171         {
172         searchsector = bak_searchsector;
173         searchwall = bak_searchwall;
174         searchstat = bak_searchstat;
175         }
176     }
177 
178 VOID
SetupBuildFAF(VOID)179 SetupBuildFAF(VOID)
180     {
181     short i, nexti;
182     SPRITEp sp,vc_sp,vf_sp,vl_sp;
183     short SpriteNum, NextSprite;
184     short vc,nextvc,vf,nextvf,l,nextl;
185     int zdiff;
186 
187     // move every sprite to the correct list
188     TRAVERSE_SPRITE_STAT(headspritestat[STAT_DEFAULT], SpriteNum, NextSprite)
189         {
190         sp = &sprite[SpriteNum];
191 
192         if (sp->picnum != ST1)
193             continue;
194 
195         switch (sp->hitag)
196             {
197             case VIEW_THRU_CEILING:
198             case VIEW_THRU_FLOOR:
199                 {
200                 int i,nexti;
201                 // make sure there is only one set per level of these
202                 TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
203                     {
204                     if (sprite[i].hitag == sp->hitag && sprite[i].lotag == sp->lotag)
205                         {
206                         sprintf(ds,"Two VIEW_THRU_ tags with same match found on level\n1: x %d, y %d \n2: x %d, y %d", sp->x, sp->y, sprite[i].x, sprite[i].y);
207                         Message(ds,0);
208                         }
209                     }
210 
211                 changespritestat(SpriteNum, STAT_FAF);
212                 break;
213                 }
214 
215             case VIEW_LEVEL1:
216             case VIEW_LEVEL2:
217             case VIEW_LEVEL3:
218             case VIEW_LEVEL4:
219             case VIEW_LEVEL5:
220             case VIEW_LEVEL6:
221                 {
222                 changespritestat(SpriteNum, STAT_FAF);
223                 break;
224                 }
225             }
226         }
227 
228     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
229         {
230         sp = &sprite[i];
231 
232         if (sector[sp->sectnum].ceilingpicnum == FAF_PLACE_MIRROR_PIC)
233             {
234             sector[sp->sectnum].ceilingpicnum = FAF_MIRROR_PIC;
235             if (sector[sp->sectnum].floorz == sector[sp->sectnum].ceilingz)
236                 {
237                 sprintf(ds, "Mirror used for non-connect area. Use tile 342. Sect %d, x %d, y %d\n", sp->sectnum, wall[sector[sp->sectnum].wallptr].x, wall[sector[sp->sectnum].wallptr].y);
238                 Message(ds,0);
239                 }
240             }
241 
242         if (sector[sp->sectnum].floorpicnum == FAF_PLACE_MIRROR_PIC)
243             {
244             sector[sp->sectnum].floorpicnum = FAF_MIRROR_PIC;
245             if (sector[sp->sectnum].floorz == sector[sp->sectnum].ceilingz)
246                 {
247                 sprintf(ds, "Mirror used for non-connect area. Use tile 342. Sect %d, x %d, y %d\n", sp->sectnum, wall[sector[sp->sectnum].wallptr].x, wall[sector[sp->sectnum].wallptr].y);
248                 Message(ds,0);
249                 }
250             }
251 
252         if (sector[sp->sectnum].ceilingpicnum == FAF_PLACE_MIRROR_PIC+1)
253             sector[sp->sectnum].ceilingpicnum = FAF_MIRROR_PIC+1;
254 
255         if (sector[sp->sectnum].floorpicnum == FAF_PLACE_MIRROR_PIC+1)
256             sector[sp->sectnum].floorpicnum = FAF_MIRROR_PIC+1;
257         }
258 
259 
260     for (i = 0; i < numwalls; i++)
261         {
262         if (wall[i].picnum == FAF_PLACE_MIRROR_PIC)
263             wall[i].picnum = FAF_MIRROR_PIC;
264 
265         if (wall[i].picnum == FAF_PLACE_MIRROR_PIC+1)
266             wall[i].picnum = FAF_MIRROR_PIC+1;
267         }
268 
269     #if 0
270     // check ceiling and floor heights
271     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], vc, nextvc)
272         {
273         vc_sp = &sprite[vc];
274 
275         if (vc_sp->hitag == VIEW_THRU_CEILING)
276             {
277             TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], vf, nextvf)
278                 {
279                 vf_sp = &sprite[vf];
280 
281                 if (vf_sp->hitag == VIEW_THRU_FLOOR && vf_sp->lotag == vc_sp->lotag)
282                     {
283                     zdiff = labs(sector[vc_sp->sectnum].ceilingz - sector[vf_sp->sectnum].floorz);
284 
285                     //DSPRINTF(ds,"zdiff %d",zdiff);
286                     MONO_PRINT(ds);
287 
288                     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], l, nextl)
289                         {
290                         vl_sp = &sprite[l];
291 
292                         if (vl_sp->hitag == VIEW_LEVEL1)
293                             {
294                             if (sector[vl_sp->sectnum].ceilingz < sector[vc_sp->sectnum].ceilingz + zdiff)
295                                 {
296                                 sprintf(ds,"Sector %d (x %d, y %d) ceiling z to close to VIEW_THRU_CEILING z",
297                                     vl_sp->sectnum, wall[sector[vl_sp->sectnum].wallptr].x, wall[sector[vl_sp->sectnum].wallptr].y);
298                                 Message(ds,0);
299                                 }
300                             }
301                         else
302                         if (vl_sp->hitag == VIEW_LEVEL2)
303                             {
304                             if (sector[vl_sp->sectnum].floorz > sector[vf_sp->sectnum].floorz + zdiff)
305                                 {
306                                 sprintf(ds,"Sector %d (x %d, y %d)floor z to close to VIEW_THRU_FLOOR z",
307                                     vl_sp->sectnum, wall[sector[vl_sp->sectnum].wallptr].x, wall[sector[vl_sp->sectnum].wallptr].y);
308                                 Message(ds,0);
309                                 }
310                             }
311                         }
312                     }
313                 }
314             }
315         }
316     #endif
317 
318     }
319 
320 VOID
ResetBuildFAF(VOID)321 ResetBuildFAF(VOID)
322     {
323     short i, nexti;
324     SPRITEp sp;
325 
326     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
327         {
328         sp = &sprite[i];
329 
330         if (sector[sp->sectnum].ceilingpicnum == FAF_MIRROR_PIC)
331             sector[sp->sectnum].ceilingpicnum = FAF_PLACE_MIRROR_PIC;
332 
333         if (sector[sp->sectnum].floorpicnum == FAF_MIRROR_PIC)
334             sector[sp->sectnum].floorpicnum = FAF_PLACE_MIRROR_PIC;
335 
336         if (sector[sp->sectnum].ceilingpicnum == FAF_MIRROR_PIC+1)
337             sector[sp->sectnum].ceilingpicnum = FAF_PLACE_MIRROR_PIC+1;
338 
339         if (sector[sp->sectnum].floorpicnum == FAF_MIRROR_PIC+1)
340             sector[sp->sectnum].floorpicnum = FAF_PLACE_MIRROR_PIC+1;
341         }
342 
343     for (i = 0; i < numwalls; i++)
344         {
345         if (wall[i].picnum == FAF_MIRROR_PIC)
346             wall[i].picnum = FAF_PLACE_MIRROR_PIC;
347 
348         if (wall[i].picnum == FAF_MIRROR_PIC+1)
349             wall[i].picnum = FAF_PLACE_MIRROR_PIC+1;
350         }
351 
352     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
353         {
354         changespritestat(i, STAT_DEFAULT);
355         }
356     }
357 
358 
359 BOOL
PicInView(short tile_num,BOOL reset)360 PicInView(short tile_num, BOOL reset)
361     {
362     if (TEST(gotpic[tile_num >> 3], 1 << (tile_num & 7)))
363         {
364         if (reset)
365             RESET(gotpic[tile_num >> 3], 1 << (tile_num & 7));
366 
367         return (TRUE);
368         }
369 
370     return (FALSE);
371     }
372 
373 void
GetUpperLowerSector(short match,int x,int y,short * upper,short * lower)374 GetUpperLowerSector(short match, int x, int y, short *upper, short *lower)
375     {
376     int i, j;
377     short sectorlist[16];
378     short sln = 0;
379     short SpriteNum, Next;
380     SPRITEp sp;
381 
382     // didn't find it yet so test ALL sectors
383     if (sln < 2)
384         {
385         sln = 0;
386         for (i = numsectors - 1; i >= 0; i--)
387             {
388             if (inside(x, y, (short) i) == 1)
389                 {
390                 BOOL found = FALSE;
391 
392                 TRAVERSE_SPRITE_SECT(headspritesect[i], SpriteNum, Next)
393                     {
394                     sp = &sprite[SpriteNum];
395 
396                     if (sp->statnum == STAT_FAF &&
397                         (sp->hitag >= VIEW_LEVEL1 && sp->hitag <= VIEW_LEVEL6)
398                         && sp->lotag == match)
399                         {
400                         found = TRUE;
401                         }
402                     }
403 
404                 if (!found)
405                     continue;
406 
407                 sectorlist[sln] = i;
408                 sln++;
409                 }
410             }
411         }
412 
413     if (sln == 0)
414         {
415         *upper = -1;
416         *lower = -1;
417         return;
418         }
419 
420     // Map rooms have NOT been dragged on top of each other
421     if (sln == 1)
422         {
423         *lower = sectorlist[0];
424         *upper = sectorlist[0];
425         return;
426         }
427     else
428     // Map rooms HAVE been dragged on top of each other
429     if (sln > 2)
430         {
431         // try again moving the x,y pos around until you only get two sectors
432         GetUpperLowerSector(match, x - 1, y, upper, lower);
433         }
434 
435     if (sln == 2)
436         {
437         if (sector[sectorlist[0]].floorz < sector[sectorlist[1]].floorz)
438             {
439             // swap
440             // make sectorlist[0] the LOW sector
441             short hold;
442 
443             hold = sectorlist[0];
444             sectorlist[0] = sectorlist[1];
445             sectorlist[1] = hold;
446             }
447 
448         *lower = sectorlist[0];
449         *upper = sectorlist[1];
450         }
451     }
452 
453 BOOL
FindCeilingView(short match,LONGp x,LONGp y,LONG z,SHORTp sectnum)454 FindCeilingView(short match, LONGp x, LONGp y, LONG z, SHORTp sectnum)
455     {
456     int xoff = 0;
457     int yoff = 0;
458     short i, nexti;
459     SPRITEp sp = NULL;
460     short top_sprite = -1;
461     int pix_diff;
462     int newz;
463 
464     save.zcount = 0;
465 
466     // Search Stat List For closest ceiling view sprite
467     // Get the match, xoff, yoff from this point
468     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
469         {
470         sp = &sprite[i];
471 
472         if (sp->hitag == VIEW_THRU_CEILING && sp->lotag == match)
473             {
474             xoff = *x - sp->x;
475             yoff = *y - sp->y;
476 
477             break;
478             }
479         }
480 
481     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
482         {
483         sp = &sprite[i];
484 
485         if (sp->lotag == match)
486             {
487             // determine x,y position
488             if (sp->hitag == VIEW_THRU_FLOOR)
489                 {
490                 short upper, lower;
491 
492                 *x = sp->x + xoff;
493                 *y = sp->y + yoff;
494 
495                 // get new sector
496                 GetUpperLowerSector(match, *x, *y, &upper, &lower);
497                 *sectnum = upper;
498                 break;
499                 }
500             }
501         }
502 
503     if (*sectnum < 0)
504         return(FALSE);
505 
506     ASSERT(sp);
507     ASSERT(sp->hitag == VIEW_THRU_FLOOR);
508 
509     if (FAF_DontMoveSectors)
510         return(TRUE);
511 
512     pix_diff = labs(z - sector[sp->sectnum].floorz) >> 8;
513     newz = sector[sp->sectnum].floorz + ((pix_diff / 128) + 1) * Z(128);
514 
515     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
516         {
517         sp = &sprite[i];
518 
519         if (sp->lotag == match)
520             {
521             // move lower levels ceilings up for the correct view
522             if (sp->hitag == VIEW_LEVEL2)
523                 {
524                 // save it off
525                 save.sectnum[save.zcount] = sp->sectnum;
526                 save.zval[save.zcount] = sector[sp->sectnum].floorz;
527                 save.pic[save.zcount] = sector[sp->sectnum].floorpicnum;
528                 save.slope[save.zcount] = sector[sp->sectnum].floorheinum;
529 
530                 sector[sp->sectnum].floorz = newz;
531                 sector[sp->sectnum].floorpicnum = FAF_MIRROR_PIC+1;
532                 sector[sp->sectnum].floorheinum = 0;
533 
534                 save.zcount++;
535                 ASSERT(save.zcount < ZMAX);
536                 }
537             }
538         }
539 
540     return (TRUE);
541     }
542 
543 BOOL
FindFloorView(short match,LONGp x,LONGp y,LONG z,SHORTp sectnum)544 FindFloorView(short match, LONGp x, LONGp y, LONG z, SHORTp sectnum)
545     {
546     int xoff = 0;
547     int yoff = 0;
548     short i, nexti;
549     SPRITEp sp = NULL;
550     int newz;
551     int pix_diff;
552 
553     save.zcount = 0;
554 
555     // Search Stat List For closest ceiling view sprite
556     // Get the match, xoff, yoff from this point
557     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
558         {
559         sp = &sprite[i];
560 
561         if (sp->hitag == VIEW_THRU_FLOOR && sp->lotag == match)
562             {
563             xoff = *x - sp->x;
564             yoff = *y - sp->y;
565 
566             break;
567             }
568         }
569 
570 
571 
572     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
573         {
574         sp = &sprite[i];
575 
576         if (sp->lotag == match)
577             {
578             // determine x,y position
579             if (sp->hitag == VIEW_THRU_CEILING)
580                 {
581                 short upper, lower;
582 
583                 *x = sp->x + xoff;
584                 *y = sp->y + yoff;
585 
586                 // get new sector
587                 GetUpperLowerSector(match, *x, *y, &upper, &lower);
588                 *sectnum = lower;
589                 break;
590                 }
591             }
592         }
593 
594     if (*sectnum < 0)
595         return(FALSE);
596 
597     ASSERT(sp);
598     ASSERT(sp->hitag == VIEW_THRU_CEILING);
599 
600     if (FAF_DontMoveSectors)
601         return(TRUE);
602 
603     // move ceiling multiple of 128 so that the wall tile will line up
604     pix_diff = labs(z - sector[sp->sectnum].ceilingz) >> 8;
605     newz = sector[sp->sectnum].ceilingz - ((pix_diff / 128) + 1) * Z(128);
606 
607     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
608         {
609         sp = &sprite[i];
610 
611         if (sp->lotag == match)
612             {
613             // move upper levels floors down for the correct view
614             if (sp->hitag == VIEW_LEVEL1)
615                 {
616                 // save it off
617                 save.sectnum[save.zcount] = sp->sectnum;
618                 save.zval[save.zcount] = sector[sp->sectnum].ceilingz;
619                 save.pic[save.zcount] = sector[sp->sectnum].ceilingpicnum;
620                 save.slope[save.zcount] = sector[sp->sectnum].ceilingheinum;
621 
622                 sector[sp->sectnum].ceilingz = newz;
623 
624                 sector[sp->sectnum].ceilingpicnum = FAF_MIRROR_PIC+1;
625                 sector[sp->sectnum].ceilingheinum = 0;
626 
627                 save.zcount++;
628                 ASSERT(save.zcount < ZMAX);
629                 }
630             }
631         }
632 
633     return (TRUE);
634     }
635 
636 BOOL
SectorInScene(short tile_num)637 SectorInScene(short tile_num)
638     {
639     if (TEST(gotsector[tile_num >> 3], 1 << (tile_num & 7)))
640         {
641         RESET(gotsector[tile_num >> 3], 1 << (tile_num & 7));
642         return (TRUE);
643         }
644 
645     return (FALSE);
646     }
647 
648 short
ViewSectorInScene(short cursectnum,short type,short level)649 ViewSectorInScene(short cursectnum, short type, short level)
650     {
651     int i, nexti;
652     int j, nextj;
653     SPRITEp sp;
654     SPRITEp sp2;
655     int cz, fz;
656     short match;
657 
658     TRAVERSE_SPRITE_STAT(headspritestat[STAT_FAF], i, nexti)
659         {
660         sp = &sprite[i];
661 
662         if (sp->hitag == level)
663             {
664             if (cursectnum == sp->sectnum)
665                 {
666                 // ignore case if sprite is pointing up
667                 if (sp->ang == 1536)
668                     continue;
669 
670                 // only gets to here is sprite is pointing down
671                 // found a potential match
672                 match = sp->lotag;
673 
674                 return(match);
675                 }
676             }
677         }
678 
679     return (-1);
680     }
681 
682 VOID
DrawOverlapRoom(int tx,int ty,int tz,short tang,int thoriz,short tsectnum)683 DrawOverlapRoom(int tx, int ty, int tz, short tang, int thoriz, short tsectnum)
684     {
685     short i;
686     short match;
687 
688     save.zcount = 0;
689 
690     match = ViewSectorInScene(tsectnum, VIEW_THRU_CEILING, VIEW_LEVEL1);
691     if (match != -1)
692         {
693         FindCeilingView(match, &tx, &ty, tz, &tsectnum);
694 
695         if (tsectnum < 0)
696             {
697             sprintf(ds,"COULD NOT FIND TAGGED LEVEL2 SECTOR FROM X %d, Y %d, SECTNUM %d.",posx,posy,cursectnum);
698             Message(ds, 0);
699             return;
700             }
701 
702         drawrooms(tx, ty, tz, tang, thoriz, tsectnum);
703         drawmasks();
704 
705         // reset Z's
706         for (i = 0; i < save.zcount; i++)
707             {
708             sector[save.sectnum[i]].floorz = save.zval[i];
709             sector[save.sectnum[i]].floorpicnum = save.pic[i];
710             sector[save.sectnum[i]].floorheinum = save.slope[i];
711             }
712         }
713     else
714         {
715         match = ViewSectorInScene(tsectnum, VIEW_THRU_FLOOR, VIEW_LEVEL2);
716         if (match != -1)
717             {
718             FindFloorView(match, &tx, &ty, tz, &tsectnum);
719 
720         if (tsectnum < 0)
721             {
722             sprintf(ds,"COULD NOT FIND TAGGED LEVEL1 SECTOR FROM X %d, Y %d, SECTNUM %d.",posx,posy,cursectnum);
723             Message(ds, 0);
724             return;
725             }
726 
727             drawrooms(tx, ty, tz, tang, thoriz, tsectnum);
728             drawmasks();
729 
730             // reset Z's
731             for (i = 0; i < save.zcount; i++)
732                 {
733                 sector[save.sectnum[i]].ceilingz = save.zval[i];
734                 sector[save.sectnum[i]].ceilingpicnum = save.pic[i];
735                 sector[save.sectnum[i]].ceilingheinum = save.slope[i];
736                 }
737             }
738         }
739     }
740