/* * pdf.c - Generate PDF * * Copyright 2012 by Werner Almesberger * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. */ #define _GNU_SOURCE #include #include #include "comp.h" #include "pdf.h" static int children(const struct node *node) { int n = 0; while (node) { n++; node = node->next; } return n; } static void ps_string(FILE *file, const char *s) { fputc('(', file); while (*s) { if (*s == '(' || *s == ')' || *s == '\\') fputc('\\', file); fputc(*s, file); s++; } fputc(')', file); } static void print_path(FILE *file, const struct node *node) { if (node->parent) { print_path(file, node->parent); fprintf(file, "( > ) show\n"); } ps_string(file, node->name); fprintf(file, " 0.5 setgray show 0 setgray\n"); } static void make_title(FILE *file, const struct node *node, int unit) { fprintf(file, "gsave 90 rotate 0 setgray\n" "/Helvetica-Bold findfont 24 scalefont setfont\n" "20 -30 moveto\n"); ps_string(file, node->canon); fprintf(file, " show\n"); if (node->units > 1) fprintf(file, " ( \\(%c\\)) show\n", 'A'+unit); fprintf(file, "/Hevetica-Bold findfont 18 scalefont setfont\n"); fprintf(file, "20 -60 moveto\n"); print_path(file, node); fprintf(file, "/Courier findfont 12 scalefont setfont\n"); fprintf(file, "20 -75 moveto\n"); ps_string(file, node->lib); fprintf(file, " show\n"); fprintf(file, "grestore\n"); fflush(file); } static void convert_comp(const struct node *node, FILE *out) { char *tmp; int i, res; for (i = 0; i != node->units; i++) { make_title(stdout, node, i); if (asprintf(&tmp, "./sym2xps '%s' '%s' %d '%s' '%s'", node->lib, node->canon, i+1, "tmp", "tmp.ps") < 0) { perror("asprintf"); exit(1); } res = system(tmp); if (res < 0) { perror("system"); exit(1); } if (res) { fprintf(stderr, "sym2xps returned %d\n", res); exit(1); } fflush(out); system("cat tmp.ps"); } } static void convert_tree(const struct node *node, FILE *out) { while (node) { fprintf(out, "[ /Title (%s) /Count %d /OUT pdfmark\n", node->name, -children(node->child)); if (node->child) convert_tree(node->child, out); else convert_comp(node, out); node = node->next; } } void make_pdf(void) { FILE *out; int res; #if 0 out = popen( "gs -q -dNOPAUSE -dBATCH -sDEVICE=pdfwrite -sOutputFile=- -f -", "w"); #else out = popen("cat", "w"); #endif if (!out) { perror("gs"); exit(1); } convert_tree(tree, out); res = pclose(out); if (res < 0) { perror("pclose"); exit(1); } if (res) { fprintf(stderr, "exit status %d\n", res); exit(1); } }