Utah Raster Toolkit  9999-git
URT Development version (post-3.1b)
unslice.c
Go to the documentation of this file.
1 /*
2  * unslice.c - Build a finished frame from a series of slices
3  *
4  * Author: John W. Peterson
5  * Computer Science Dept.
6  * University of Utah
7  * Date: Tue May 19 1987
8  * Copyright (c) 1987, University of Utah
9  *
10  * Lots of this code is swiped from comp.c
11  */
12 static char rcsid[] = "$Header: /l/spencer/src/urt/tools/RCS/unslice.c,v 3.0.1.2 1992/04/30 14:14:54 spencer Exp $";
13 /*
14 unslice() Tag the file.
15 */
16 
17 /*
18  * The "control file" is a text file with two numbers per line, each
19  * line giving the starting and ending lines (inclusive) that are to
20  * be taken from each input file to the output file. This allows
21  * potentially ragged portions of slices to be cropped away.
22  *
23  * If no control file is given, then the extents given in the slices' headers
24  * are used. If two files overlap, the first lines from the second file
25  * are thrown away. The maximum y of the image must be specified this way.
26  */
27 
28 #include <stdio.h>
29 #include "rle.h"
30 #include "rle_raw.h"
31 
32 void do_slice(), copy_scanline();
33 
34 rle_hdr in_hdr, out_hdr;
35 
36 /*
37  * Global raw data structures for copy_scanline.
38  */
39 rle_op ** out_raw;
40 int * out_nraw;
41 
42 int max_y = 0; /* Maximum Y value */
43 int num_skip = 0; /* Counter for keeping track of raw lines */
44 
45 int ctlflag = 0; /* If true then we are using a ctl file */
46 int ctl_lines; /* Number of lines in control file */
48  *stop_line; /* Start and ending lines for the slices */
49 
50 char default_ctl_file[] = "unslice.ctl";
51 char *progname;
52 char **gargv;
53 
54 void
56 int argc;
57 char **argv;
58 {
59  int nfiles, i;
60  char **slicefiles;
61  FILE *ctlfile;
62  int y_flag, oflag = 0;
63 
64  char * ctlfilename = NULL, * out_fname = NULL;
65 
66  progname = cmd_name( argv );
67  gargv = argv;
68 
69  if (! scanargs(argc, argv,
70  "% y%-ymax!d f%-ctlfile!s files!*s o%-outfile!s",
71  &y_flag, &max_y,
72  &ctlflag, &ctlfilename, &nfiles, &slicefiles,
73  &oflag, &out_fname ))
74  exit(1);
75 
76  /* Open the output file */
77  (void)rle_hdr_init( &in_hdr );
78  (void)rle_hdr_init( &out_hdr );
80  rle_names( &out_hdr, cmd_name( argv ), out_fname, 0 );
81 
82  start_line = (int *) malloc( nfiles * sizeof(int) );
84  stop_line = (int *) malloc( nfiles * sizeof(int) );
86 
87  if (ctlflag) /* Read in and verify the control file */
88  {
89  if (! ctlfilename)
90  ctlfilename = default_ctl_file;
91 
92  /* Read in the control file */
93 
94  ctlfile = rle_open_f( progname, ctlfilename, "r" );
95 
96  ctl_lines = 0;
97  while (! feof( ctlfile ))
98  {
99  fscanf( ctlfile, "%d %d",
101 
103  fprintf( stderr, "%s: ctl file garbled? (start %d, stop %d)\n",
104  progname,
106  ctl_lines++;
107  }
108  ctl_lines--;
109 
110  if (ctl_lines > nfiles)
111  fprintf(stderr,
112  "%s: Warning: not enough slices for ctl file\n", progname);
113  if (ctl_lines < nfiles)
114  fprintf(stderr,
115  "%s: Warning: too many slices for ctl file\n", progname);
116 
117  }
118  else
119  if (! max_y)
120  {
121  fprintf(stderr,
122  "%s: max y (-y ymax) must be given if no ctl file used\n",
123  progname);
124  exit(-1);
125  }
126 
127  /* Process the slices */
128 
129  for (i = 0; i < nfiles; i++)
130  do_slice( i, slicefiles[i] );
131 
133 
134  exit( 0 );
135 }
136 
137 /*****************************************************************
138  * TAG( do_slice )
139  *
140  * Read one slice from the given file and write it to the output.
141  * Also generate the output header if it's the first file.
142  */
143 void
145 int num;
146 char *filename;
147 {
148  register int y;
149  static int current_y = 0;
150 
152  rle_names( &in_hdr, progname, filename, 0 );
153 
154  /*
155  * Many sanity checks. Code must be 3am-proof!
156  */
157 
159 
160  if (ctlflag &&
161  ((start_line[num] > in_hdr.ymax) ||
162  (stop_line[num] < in_hdr.ymin)))
163  {
164  fprintf(stderr, "%s: %s is out of slice range (%d %d)\n",
165  progname, filename, start_line[num], stop_line[num]);
166  exit(-1);
167  }
168 
169  /*
170  * If this is the first slice, generate the output header.
171  */
172 
173  if (num == 0)
174  {
175  FILE *f = out_hdr.rle_file;
176  CONST_DECL char *name = out_hdr.file_name;
177 
178  out_hdr.file_name = NULL;
179  (void)rle_hdr_cp( &in_hdr, &out_hdr );
180  out_hdr.file_name = name;
181  out_hdr.rle_file = f;
182  rle_addhist( gargv, (rle_hdr *)0, &out_hdr );
183 
184  if (ctlflag)
185  {
188  }
189  else
190  {
193  }
194  current_y = out_hdr.ymin;
196 
198  RLE_CHECK_ALLOC( progname, 0, 0 );
199  }
200 
201  if ((! ctlflag) && (in_hdr.ymax < current_y))
202  {
203  fprintf(stderr,
204  "%s: warning: slice %s completely ignored (wrong order?)\n",
205  progname, filename);
206  fclose( in_hdr.rle_file );
207  return;
208  }
209 
210  /*
211  * Copy the file to the output.
212  */
213  num_skip = 0;
214 
215  if (ctlflag)
216  {
217  for (y = in_hdr.ymin; y <= in_hdr.ymax; y++ )
218  if ((y >= start_line[num]) && (y <= stop_line[num]))
219  copy_scanline( y, 1 );
220  else
221  copy_scanline( y, 0 ); /* Data out of range, just toss it. */
222  }
223  else
224  {
225  for (y = in_hdr.ymin; y <= in_hdr.ymax; y++ )
226  if (y >= current_y)
227  copy_scanline( y, 1 );
228  else
229  copy_scanline( y, 0 );
230 
231  current_y = in_hdr.ymax + 1;
232  }
233 
234  fclose( in_hdr.rle_file );
235 }
236 
237 /*
238  * The "skip counter" is stolen from comp. It works like this:
239  * if num_skip == 0, then we read the next line normally. If it's
240  * positive, then it tells us how many blank lines before the
241  * next available real data. If it's -1, then it means that the
242  * output raw data should be used before calling rle_getraw again.
243  */
244 
245 /*****************************************************************
246  * TAG( copy_scanline )
247  *
248  * Copy the scanlines using the raw format, if the copy_flag is on. If
249  * copy_flag is false, scanlines are just eaten away from the input file.
250  */
251 void
253 int ypos;
254 int copy_flag; /* If true, write the output */
255 {
256 
257  SKIP_ROW:
258 
259  if (num_skip > 0) /* Must skip blank rows */
260  {
261  if (copy_flag)
263  num_skip--;
264  if (num_skip == 0)
265  num_skip = -1; /* Flag raw data available */
266  return;
267  }
268 
269  if (num_skip == 0) /* ...Must read new data */
271  else
272  num_skip = ypos; /* num_skip < 0, data was already there */
273 
274  if (num_skip == 32768) /* Hit the EOF */
275  {
276  if (copy_flag)
278  return;
279  }
280 
281  num_skip -= ypos; /* Find how many blank lines left */
282 
283  if (num_skip > 0)
284  goto SKIP_ROW;
285 
286  if (copy_flag)
289 }
FILE * rle_open_f(char *prog_name, char *file_name, char *mode)
Definition: rle_open_f.c:216
char default_ctl_file[]
Definition: unslice.c:50
rle_hdr * rle_hdr_cp(rle_hdr *from_hdr, rle_hdr *to_hdr)
Definition: rle_hdr.c:119
void rle_freeraw(rle_hdr *the_hdr, scanraw, nraw)
Definition: rle_getraw.c:268
int * start_line
Definition: unslice.c:47
void rle_names(rle_hdr *the_hdr, const char *pgmname, const char *fname, int img_num)
Definition: rle_hdr.c:48
int rle_raw_alloc(rle_hdr *the_hdr, rle_op ***scanp, int **nrawp)
Definition: rle_raw_alc.c:60
char * cmd_name(char **argv)
Definition: cmd_name.c:31
void main(int argc, char **argv)
Definition: aliastorle.c:121
int * out_nraw
Definition: unslice.c:40
void rle_putraw(rle_op **scanraw, int *nraw, rle_hdr *the_hdr)
Definition: rle_putraw.c:60
int * stop_line
Definition: unslice.c:47
int ymin
Definition: rle.h:100
char * progname
Definition: unslice.c:51
int ctlflag
Definition: unslice.c:45
int scanargs(int argc, char **argv, const char *format,...)
Definition: scanargs.c:94
void rle_puteof(rle_hdr *the_hdr)
Definition: rle_putrow.c:474
rle_hdr out_hdr
Definition: unslice.c:34
void do_slice(int num, char *filename)
Definition: unslice.c:144
#define CONST_DECL
Definition: rle_config.h:42
void rle_addhist(argv, rle_hdr *in_hdr, rle_hdr *out_hdr)
Definition: rle_addhist.c:54
void copy_scanline(int ypos, int copy_flag)
Definition: unslice.c:252
void rle_get_setup_ok(rle_hdr *the_hdr, const char *prog_name, const char *file_name)
Definition: rle_getrow.c:254
void rle_skiprow(rle_hdr *the_hdr, int nrow)
Definition: rle_putrow.c:393
int num_skip
Definition: unslice.c:43
char ** gargv
Definition: unslice.c:52
int ctl_lines
Definition: unslice.c:46
int ymax
Definition: rle.h:100
void rle_put_setup(rle_hdr *the_hdr)
Definition: rle_putrow.c:453
static char rcsid[]
Definition: unslice.c:12
rle_op ** out_raw
Definition: unslice.c:39
int max_y
Definition: unslice.c:42
rle_hdr in_hdr
Definition: unslice.c:34
const char * file_name
Definition: rle.h:134
rle_hdr * rle_hdr_init(rle_hdr *the_hdr)
Definition: rle_hdr.c:267
FILE * rle_file
Definition: rle.h:114
unsigned int rle_getraw(rle_hdr *the_hdr, scanraw, nraw)
Definition: rle_getraw.c:78
#define RLE_CHECK_ALLOC(pgm, ptr, name)
Definition: rle.h:86