Utah Raster Toolkit  9999-git
URT Development version (post-3.1b)
rlepatch.c
Go to the documentation of this file.
1 /*
2  * This software is copyrighted as noted below. It may be freely copied,
3  * modified, and redistributed, provided that the copyright notice is
4  * preserved on all copies.
5  *
6  * There is no warranty or other guarantee of fitness for this software,
7  * it is provided solely "as is". Bug reports or fixes may be sent
8  * to the author, who may or may not act on them as he desires.
9  *
10  * You may not include this software in a program or other software product
11  * without supplying the source, or without informing the end-user that the
12  * source is available for no extra charge.
13  *
14  * If you modify this software, you should include a notice giving the
15  * name of the person performing the modification, the date of modification,
16  * and the reason for such modification.
17  */
18 /*
19  * rlepatch.c - Patch images over a larger image.
20  *
21  * Author: John W. Peterson
22  * Computer Science Dept.
23  * University of Utah
24  * Date: Sun Nov 29 1987
25  * Copyright (c) 1987, University of Utah
26  *
27  * This was a quick hack. It should be changed to use the "raw"
28  * routines someday - this would run MUCH faster for sparse patches.
29  */
30 
31 #include <stdio.h>
32 #include "rle.h"
33 
34 #define IN_WINDOW(y,wind) ((y >= wind.ymin) && (y <= wind.ymax))
35 
36 void
38 int argc;
39 char **argv;
40 {
41  rle_hdr im_hdr, out_hdr;
42  rle_hdr *patch_hdr;
43  CONST_DECL char *imfilename = NULL, *outfilename = NULL;
44  CONST_DECL char **patchnames;
45  FILE *outfile = stdout;
46  rle_pixel ** im_rows, **patch_rows, ** outrows;
47  int stdin_used = 0;
48  int patches = 0, oflag = 0, i, y, c, xlen, width;
49  int rle_cnt, rle_err;
50 
51  im_hdr = *rle_hdr_init( NULL );
52  out_hdr = *rle_hdr_init( NULL );
53 
54  if (! scanargs( argc, argv, "% o%-outfile!s infile!s patchfiles%*s",
55  &oflag, &outfilename, &imfilename, &patches, &patchnames ))
56  exit( -1 );
57 
58  patch_hdr = (rle_hdr *) malloc( sizeof( rle_hdr )
59  * patches );
60  RLE_CHECK_ALLOC( cmd_name( argv ), patch_hdr, "patch headers" );
61 
62  /* Setup the main image data structures. */
63 
64  im_hdr.rle_file = rle_open_f( cmd_name( argv ), imfilename, "r" );
65  if ( im_hdr.rle_file == stdin )
66  stdin_used++;
67  rle_names( &im_hdr, cmd_name( argv ), imfilename, 0 );
68  rle_names( &out_hdr, im_hdr.cmd, outfilename, 0 );
69 
70  for( i = 0; i < patches; i++ )
71  {
72  patch_hdr[i] = *rle_hdr_init( NULL );
73  patch_hdr[i].rle_file = rle_open_f( cmd_name( argv ),
74  patchnames[i], "r" );
75  rle_names( &patch_hdr[i], im_hdr.cmd, patchnames[i], 0 );
76  if ( patch_hdr[i].rle_file == stdin )
77  {
78  if ( stdin_used )
79  {
80  fprintf(stderr, "%s: Only use stdin (-) once.\n",
81  cmd_name( argv ));
82  exit(-1);
83  }
84  stdin_used++;
85  }
86  }
87 
88  for ( rle_cnt = 0;
89  (rle_err = rle_get_setup( &im_hdr )) == RLE_SUCCESS;
90  rle_cnt++ )
91  {
92  /* Get the patch files set up */
93  for( i = 0; i < patches; i++ )
94  {
95  rle_get_setup_ok( &patch_hdr[i], patch_hdr[i].cmd,
96  patch_hdr[i].file_name );
97 
98  /* Sanity checks. */
99 
100  if ((patch_hdr[i].xmin < im_hdr.xmin) ||
101  (patch_hdr[i].xmax > im_hdr.xmax) ||
102  (patch_hdr[i].ymin < im_hdr.ymin) ||
103  (patch_hdr[i].ymax > im_hdr.ymax))
104  {
105  fprintf( stderr, "%s: file %s is outside %s\n", im_hdr.cmd,
106  patch_hdr[i].file_name, im_hdr.file_name );
107  exit( -2 );
108  }
109 
110  if ((patch_hdr[i].ncolors != im_hdr.ncolors) ||
111  (patch_hdr[i].alpha != im_hdr.alpha))
112  {
113  fprintf( stderr,
114  "%s: file %s doesn't have the same channels as %s\n",
115  im_hdr.cmd, patch_hdr[i].file_name,
116  im_hdr.file_name );
117  exit(-2);
118  }
119  }
120 
121  if (rle_row_alloc( &im_hdr, &im_rows ) ||
122  rle_row_alloc( &im_hdr, &patch_rows ))
123  RLE_CHECK_ALLOC( cmd_name( argv ), 0, "image and patch data" );
124 
125  /* Setup output */
126  (void)rle_hdr_cp( &im_hdr, &out_hdr );
127  if ( rle_cnt == 0 )
128  outfile = rle_open_f( cmd_name( argv ), outfilename, "w" );
129  out_hdr.rle_file = outfile;
130 
131  rle_addhist( argv, &im_hdr, &out_hdr );
132 
133  rle_put_setup( &out_hdr );
134 
135  /*
136  * Allocate pointers to the output rows. Note that rle_putrow
137  * expects the pointers to start at xmin, instead of at zero
138  * like rle_getrow (Weird Spencerism).
139  */
140  outrows = (rle_pixel**) malloc( sizeof( rle_pixel** ) *
141  (im_hdr.alpha + im_hdr.ncolors));
142  RLE_CHECK_ALLOC( cmd_name( argv ), outrows, "output image data" );
143  if (im_hdr.alpha)
144  outrows++; /* Put alpha at -1 index */
145 
146  xlen = out_hdr.xmax - out_hdr.xmin + 1;
147  for( i = -im_hdr.alpha; i < im_hdr.ncolors; i++ )
148  outrows[i] = &(im_rows[i][im_hdr.xmin]);
149 
150  /* Process the images. */
151 
152  for (y = im_hdr.ymin; y <= im_hdr.ymax; y++)
153  {
154  rle_getrow( &im_hdr, im_rows );
155 
156  for (i = 0; i < patches; i++)
157  {
158  if (IN_WINDOW( y, patch_hdr[i]))
159  {
160  rle_getrow( &(patch_hdr[i]), patch_rows );
161  width = patch_hdr[i].xmax - patch_hdr[i].xmin + 1;
162  for( c = -im_hdr.alpha; c < im_hdr.ncolors; c++)
163  bcopy( &(patch_rows[c][patch_hdr[i].xmin]),
164  &(im_rows[c][patch_hdr[i].xmin]), width );
165  }
166  }
167  rle_putrow( outrows, xlen, &out_hdr );
168  }
169 
170  rle_puteof( &out_hdr );
171 
172  /* Release memory. */
173  rle_row_free( &im_hdr, im_rows );
174  rle_row_free( &im_hdr, patch_rows );
175  if ( im_hdr.alpha )
176  outrows--;
177  free( outrows );
178  }
179  exit( 0 );
180 }
FILE * rle_open_f(char *prog_name, char *file_name, char *mode)
Definition: rle_open_f.c:216
int xmin
Definition: rle.h:100
rle_hdr * rle_hdr_cp(rle_hdr *from_hdr, rle_hdr *to_hdr)
Definition: rle_hdr.c:119
void rle_names(rle_hdr *the_hdr, const char *pgmname, const char *fname, int img_num)
Definition: rle_hdr.c:48
void rle_row_free(rle_hdr *the_hdr, rle_pixel **scanp)
Definition: rle_row_alc.c:114
char * cmd_name(char **argv)
Definition: cmd_name.c:31
void main(int argc, char **argv)
Definition: aliastorle.c:121
int rle_get_setup(rle_hdr *the_hdr)
Definition: rle_getrow.c:74
int rle_row_alloc(rle_hdr *the_hdr, rle_pixel ***scanp)
Definition: rle_row_alc.c:56
int rle_getrow(rle_hdr *the_hdr, scanline)
Definition: rle_getrow.c:333
#define RLE_SUCCESS
Definition: rle.h:70
int ymin
Definition: rle.h:100
int scanargs(int argc, char **argv, const char *format,...)
Definition: scanargs.c:94
const char * cmd
Definition: rle.h:133
void rle_puteof(rle_hdr *the_hdr)
Definition: rle_putrow.c:474
void rle_putrow(rows, int rowlen, rle_hdr *the_hdr)
Definition: rle_putrow.c:96
int xmax
Definition: rle.h:100
#define IN_WINDOW(y, wind)
Definition: rlecomp.c:54
#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 rle_get_setup_ok(rle_hdr *the_hdr, const char *prog_name, const char *file_name)
Definition: rle_getrow.c:254
int ymax
Definition: rle.h:100
unsigned char rle_pixel
Definition: rle.h:56
void rle_put_setup(rle_hdr *the_hdr)
Definition: rle_putrow.c:453
int alpha
Definition: rle.h:100
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
int ncolors
Definition: rle.h:100
#define RLE_CHECK_ALLOC(pgm, ptr, name)
Definition: rle.h:86