Added more logging to quant.c. Removed global variables from gif.c.
[imager.git] / convert.c
CommitLineData
f5991c03
TC
1/*
2=head1 NAME
3
4 convert.c - image conversions
5
6=head1 SYNOPSIS
7
8 i_convert(outimage, srcimage, coeff, outchans, inchans)
9
10=head1 DESCRIPTION
11
12Converts images from one format to another, typically in this case for
13converting from RGBA to greyscale and back.
14
15=over
16
17=cut
18*/
19
20#include "image.h"
21
22
23/*
24=item i_convert(im, src, coeff, outchan, inchan)
25
26Converts the image src into another image.
27
28coeff contains the co-efficients of an outchan x inchan matrix, for
29each output pixel:
30
31 coeff[0], coeff[1] ...
32 im[x,y] = [ coeff[inchan], coeff[inchan+1]... ] * [ src[x,y], 1]
33 ... coeff[inchan*outchan-1]
34
35If im has the wrong number of channels or is the wrong size then
36i_convert() will re-create it.
37
38=cut
39*/
40
41int
42i_convert(i_img *im, i_img *src, float *coeff, int outchan, int inchan)
43{
44 i_color *vals;
45 int x, y;
46 int i, j;
47 int ilimit, jlimit;
48 double work[MAXCHANNELS];
49
50 mm_log((1,"i_convert(im* 0x%x, src, 0x%x, coeff 0x%x,outchan %d, inchan %d)\n",im,src, coeff,outchan, inchan));
51
52 i_clear_error();
53
54 ilimit = inchan;
55 if (ilimit > src->channels)
56 ilimit = src->channels;
57 if (outchan > MAXCHANNELS) {
58 i_push_error(0, "cannot have outchan > MAXCHANNELS");
59 return 0;
60 }
61
62 /* first check the output image */
63 if (im->channels != outchan || im->xsize != src->xsize
64 || im->ysize != src->ysize) {
65 i_img_empty_ch(im, src->xsize, src->ysize, outchan);
66 }
67 vals = mymalloc(sizeof(i_color) * src->xsize);
68 for (y = 0; y < src->ysize; ++y) {
69 i_glin(src, 0, src->xsize, y, vals);
70 for (x = 0; x < src->xsize; ++x) {
71 for (j = 0; j < outchan; ++j) {
72 work[j] = 0;
73 for (i = 0; i < ilimit; ++i) {
74 work[j] += coeff[i+inchan*j] * vals[x].channel[i];
75 }
76 if (i < inchan) {
77 work[j] += coeff[i+inchan*j] * 255.9;
78 }
79 }
80 for (j = 0; j < outchan; ++j) {
81 if (work[j] < 0)
82 vals[x].channel[j] = 0;
83 else if (work[j] >= 256)
84 vals[x].channel[j] = 255;
85 else
86 vals[x].channel[j] = work[j];
87 }
88 }
89 i_plin(im, 0, src->xsize, y, vals);
90 }
91 myfree(vals);
92 return 1;
93}
94
95/*
96=back
97
98=head1 SEE ALSO
99
100Imager(3)
101
102=head1 AUTHOR
103
104Tony Cook <tony@develop-help.com>
105
106=cut
107*/