home *** CD-ROM | disk | FTP | other *** search
- /*****************************************************************************
- * Module to handle PostScript output. *
- * *
- * Written by: Gershon Elber Ver 1.0, Apr. 1990 *
- *****************************************************************************/
-
- #ifdef __MSDOS__
- #include <sys\types.h>
- #else
- #include <sys/types.h>
- #endif
-
- #include <stdio.h>
- #include <string.h>
- #include <time.h>
- #include "program.h"
- #include "genmat.h"
- #include "interact.h"
- #include "graphgen.h"
-
- static FILE *PSFile = NULL; /* Used to save PostScript text file. */
-
- static void (* SavedMoveToPtr)(RealType Coord[3]);
- static void (* SavedDrawToPtr)(RealType Coord[3]);
- static void PSMoveTo(RealType Coord[3]);
- static void PSDrawTo(RealType Coord[3]);
-
- /*****************************************************************************
- * Routine to save the current view as PostScript text file. *
- * Although this routine dumps EPSF-1.2 compatible code, it still dumps *
- * the 'showpage' command. The 'showpage' is allowed by the EPSF document and *
- * it is the responsibility of the including program to disable showpage. *
- *****************************************************************************/
- void SavePostScript(IPObjectStruct *Objects)
- {
- int i;
- time_t time1970 = time(NULL);
- char *p, FileName[PATH_NAME_LEN];
- static char FileCount = '0';
-
- static char *PSHeader[] = {
- "%!PS-Adobe-2.0 EPSF-1.2",
- "%%BoundingBox: 36 108 540 612", /* 7x7 inches, LL at [0.5, 1.5]. */
- "%%Title:",
- "%%Creator: Poly3d",
- "%%CreationDate:",
- "%%EndComments",
- "",
- "gsave",
- "",
- "72 72 scale", /* First scale to inches, se we can speak in inches. */
- "4.0 5.0 translate", /* To Center of image area. */
- "3.5 3.5 scale", /* Make the universe -1..1 on both X and Y. */
- "",
- "/line {",
- " newpath",
- " moveto",
- " lineto",
- " stroke",
- "} def",
- "",
- "/setdashline {",
- " [0.012 0.024] 0 setdash",
- "} def",
- "",
- "/setfullline {",
- " [] 0 setdash",
- "} def",
- "",
- "0.006 setlinewidth", /* Set some default line attributes. */
- "1 setlinecap",
- "1 setlinejoin",
- "setfullline",
- "",
- NULL
- };
- static char *PSTrailer[] = {
- "",
- "showpage",
- "grestore",
- NULL
- };
-
- strcpy(FileName, GENERIC_PS_FILE);
- if ((p = strchr(FileName, '#')) != NULL) {
- *p = FileCount;
- if (FileCount++ == '9') FileCount = '0';
- }
- if ((PSFile = fopen(FileName, "wt")) == NULL) {
- GGTone(700, 200);
- return;
- }
-
- for (i = 0; PSHeader[i] != NULL; i++) {
- if (strcmp(PSHeader[i], "%%Title:") == 0)
- fprintf(PSFile, "%s %s\n", PSHeader[i], GlblFirstDataFileName);
- else if (strcmp(PSHeader[i], "%%CreationDate:") == 0)
- fprintf(PSFile, "%s %s", PSHeader[i], ctime(&time1970));
- else
- fprintf(PSFile, "%s\n", PSHeader[i]);
- }
-
- SavedMoveToPtr = MoveToPtr;
- SavedDrawToPtr = DrawToPtr;
- MoveToPtr = PSMoveTo;
- DrawToPtr = PSDrawTo;
- DrawAllObjects(Objects);
- MoveToPtr = SavedMoveToPtr;
- DrawToPtr = SavedDrawToPtr;
-
- for (i = 0; PSTrailer[i] != NULL; i++)
- fprintf(PSFile, "%s\n", PSTrailer[i]);
-
- fclose(PSFile);
- }
-
- static RealType LastCoord[3]; /* Used to store last point we moved/draw to. */
-
- /*****************************************************************************
- * Routine to mave to 3D point given as Coord[3], using Mat transform. *
- *****************************************************************************/
- static void PSMoveTo(RealType Coord[3])
- {
- MultVecby4by4(LastCoord, Coord, CrntViewMat); /* Set last point coord. */
- }
-
- /*****************************************************************************
- * Routine to draw to 3D point given as Coord[3], using Mat transform, from *
- * the last point we moved to. *
- *****************************************************************************/
- static void PSDrawTo(RealType Coord[3])
- {
- static DashState = FALSE;
- RealType NewCoord[3], MiddleCoord[3], t;
-
- MultVecby4by4(NewCoord, Coord, CrntViewMat); /* Set last point coord. */
- if (GlblClosedObject && NewCoord[2] < LastCoord[2]) {
- GEN_COPY(LastCoord, NewCoord, 3 * sizeof(RealType));
- return;
- }
-
- /* Implementation of simple depth cue - if line is >Z or <Z ... */
- if (LastCoord[2] <= 0.0 && NewCoord[2] <= 0.0) {
- if (GlblDepthCue && !DashState) {
- fprintf(PSFile, "setdashline\n");
- DashState = TRUE;
- }
- fprintf(PSFile, "%10.7lf %10.7lf ", LastCoord[0], LastCoord[1]);
- fprintf(PSFile, "%10.7lf %10.7lf line\n", NewCoord[0], NewCoord[1]);
- }
- else if (LastCoord[2] >= 0.0 && NewCoord[2] >= 0.0 ||
- ABS(LastCoord[2] - NewCoord[2]) < EPSILON) {
- if (GlblDepthCue && DashState) {
- fprintf(PSFile, "setfullline\n");
- DashState = FALSE;
- }
- fprintf(PSFile, "%10.7lf %10.7lf ", LastCoord[0], LastCoord[1]);
- fprintf(PSFile, "%10.7lf %10.7lf line\n", NewCoord[0], NewCoord[1]);
- }
- else { /* Line intersect Z = 0 plane. */
- t = LastCoord[2] / (LastCoord[2] - NewCoord[2]);
- MiddleCoord[0] = LastCoord[0] * (1.0 - t) + NewCoord[0] * t;
- MiddleCoord[1] = LastCoord[1] * (1.0 - t) + NewCoord[1] * t;
-
- if (GlblDepthCue && DashState) {
- fprintf(PSFile, "setfullline\n");
- DashState = FALSE;
- }
- if (LastCoord[2] > 0.0) {
- fprintf(PSFile, "%10.7lf %10.7lf ", LastCoord[0], LastCoord[1]);
- fprintf(PSFile, "%10.7lf %10.7lf line\n", MiddleCoord[0], MiddleCoord[1]);
- }
- else {
- fprintf(PSFile, "%10.7lf %10.7lf ", MiddleCoord[0], MiddleCoord[1]);
- fprintf(PSFile, "%10.7lf %10.7lf line\n", NewCoord[0], NewCoord[1]);
- }
-
- if (GlblDepthCue && !DashState) {
- fprintf(PSFile, "setdashline\n");
- DashState = TRUE;
- }
- if (LastCoord[2] < 0.0) {
- fprintf(PSFile, "%10.7lf %10.7lf ", LastCoord[0], LastCoord[1]);
- fprintf(PSFile, "%10.7lf %10.7lf line\n", MiddleCoord[0], MiddleCoord[1]);
- }
- else {
- fprintf(PSFile, "%10.7lf %10.7lf ", MiddleCoord[0], MiddleCoord[1]);
- fprintf(PSFile, "%10.7lf %10.7lf line\n", NewCoord[0], NewCoord[1]);
- }
- }
-
- GEN_COPY(LastCoord, NewCoord, 3 * sizeof(RealType)); /* Current point. */
- }
-