9 Inset, /* move border in or out uniformly */
10 Insetxy, /* move border in or out; different parameters for x and y */
11 Set, /* set rectangle to absolute values */
12 Blank, /* cut off blank region according to color value */
13 /* Blank is not actually set as a mode; it can be combined with others */
19 fprint(2, "usage: crop [-c rgb] [-i ±inset | -r R | -x ±inset | -y ±inset] [-t tx ty] [-b rgb ] [imagefile]\n");
20 fprint(2, "\twhere R is a rectangle minx miny maxx maxy\n");
21 fprint(2, "\twhere rgb is a color red green blue\n");
38 crop(Memimage *m, ulong c)
42 int left, right, top, bottom;
50 if(m->chan != RGBA32){
51 /* convert type for simplicity */
52 n = allocmemimage(m->r, RGBA32);
54 sysfatal("can't allocate temporary image: %r");
55 memimagedraw(n, n->r, m, m->r.min, nil, ZP, S);
58 wpl = wordsperline(m->r, m->depth);
59 bpl = wpl*sizeof(ulong);
62 sysfatal("can't allocate buffer: %r");
64 for(y=m->r.min.y; y<m->r.max.y; y++){
65 x = unloadmemimage(m, Rect(m->r.min.x, y, m->r.max.x, y+1), (uchar*)buf, bpl);
67 sysfatal("unloadmemimage");
82 return Rect(left, top, right+1, bottom+1);
86 main(int argc, char *argv[])
88 int fd, mode, red, green, blue;
101 memset(&rparam, 0, sizeof rparam);
107 red = getint(ARGF())&0xFF;
108 green = getint(ARGF())&0xFF;
109 blue = getint(ARGF())&0xFF;
110 bg = (red<<24)|(green<<16)|(blue<<8)|0xFF;
115 red = getint(ARGF())&0xFF;
116 green = getint(ARGF())&0xFF;
117 blue = getint(ARGF())&0xFF;
118 cropval = (red<<24)|(green<<16)|(blue<<8)|0xFF;
124 rparam.min.x = getint(ARGF());
127 if(mode != None && mode != Insetxy)
130 rparam.min.x = getint(ARGF());
133 if(mode != None && mode != Insetxy)
136 rparam.min.y = getint(ARGF());
142 rparam.min.x = getint(ARGF());
143 rparam.min.y = getint(ARGF());
144 rparam.max.x = getint(ARGF());
145 rparam.max.y = getint(ARGF());
148 t.x = getint(ARGF());
149 t.y = getint(ARGF());
155 if(mode == None && cropval == 0 && eqpt(ZP, t))
164 fd = open(file, OREAD);
166 sysfatal("can't open %s: %r", file);
169 m = readmemimage(fd);
171 sysfatal("can't read %s: %r", file);
175 r = crop(m, cropval);
183 r = insetrect(r, rparam.min.x);
186 r.min.x += rparam.min.x;
187 r.max.x -= rparam.min.x;
188 r.min.y += rparam.min.y;
189 r.max.y -= rparam.min.y;
196 new = allocmemimage(r, m->chan);
198 sysfatal("can't allocate new image: %r");
200 memfillcolor(new, bg);
202 memfillcolor(new, 0x000000FF);
204 memimagedraw(new, m->clipr, m, m->clipr.min, nil, ZP, S);
205 dw = byteaddr(new, ZP) - byteaddr(new, t);
206 new->r = rectaddpt(new->r, t);
208 if(writememimage(1, new) < 0)
209 sysfatal("write error on output: %r");