tomwalters@0
|
1 /*
|
tomwalters@0
|
2 Copyright (c) Applied Psychology Unit, Medical Research Council. 1988, 1989
|
tomwalters@0
|
3 ===========================================================================
|
tomwalters@0
|
4
|
tomwalters@0
|
5 Permission to use, copy, modify, and distribute this software without fee
|
tomwalters@0
|
6 is hereby granted for research purposes, provided that this copyright
|
tomwalters@0
|
7 notice appears in all copies and in all supporting documentation, and that
|
tomwalters@0
|
8 the software is not redistributed for any fee (except for a nominal shipping
|
tomwalters@0
|
9 charge). Anyone wanting to incorporate all or part of this software in a
|
tomwalters@0
|
10 commercial product must obtain a license from the Medical Research Council.
|
tomwalters@0
|
11
|
tomwalters@0
|
12 The MRC makes no representations about the suitability of this
|
tomwalters@0
|
13 software for any purpose. It is provided "as is" without express or implied
|
tomwalters@0
|
14 warranty.
|
tomwalters@0
|
15
|
tomwalters@0
|
16 THE MRC DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
|
tomwalters@0
|
17 ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL THE
|
tomwalters@0
|
18 A.P.U. BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY
|
tomwalters@0
|
19 DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
|
tomwalters@0
|
20 AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
tomwalters@0
|
21 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
tomwalters@0
|
22 */
|
tomwalters@0
|
23
|
tomwalters@0
|
24 /*
|
tomwalters@0
|
25 fill.c
|
tomwalters@0
|
26 ======
|
tomwalters@0
|
27
|
tomwalters@0
|
28
|
tomwalters@0
|
29 window filling source
|
tomwalters@0
|
30
|
tomwalters@0
|
31
|
tomwalters@0
|
32 Copyright (c), 1989 The Medical Research Council, Applied Psychology Unit.
|
tomwalters@0
|
33
|
tomwalters@0
|
34
|
tomwalters@0
|
35 Author : John Holdsworth
|
tomwalters@0
|
36 Written : 11th May, 1989.
|
tomwalters@0
|
37
|
tomwalters@0
|
38 Edited :
|
tomwalters@0
|
39
|
tomwalters@0
|
40
|
tomwalters@0
|
41 */
|
tomwalters@0
|
42
|
tomwalters@0
|
43 #include "windows.h"
|
tomwalters@0
|
44 #include "stitch.h"
|
tomwalters@0
|
45 #include "source.h"
|
tomwalters@0
|
46 #include "fill.h"
|
tomwalters@0
|
47
|
tomwalters@0
|
48 #ifndef lint
|
tomwalters@0
|
49 static char *sccs_id = "@(#)fill.c 1.9 J. Holdsworth (MRC-APU) 11/8/90" ;
|
tomwalters@0
|
50 #endif
|
tomwalters@0
|
51
|
tomwalters@0
|
52
|
tomwalters@0
|
53 static int *Match( n1, n2 )
|
tomwalters@0
|
54 int n1, n2 ;
|
tomwalters@0
|
55 {
|
tomwalters@0
|
56 DeclareNewArray( int, array, n2+16, "for match" ) ;
|
tomwalters@0
|
57 float scale ;
|
tomwalters@0
|
58 int i ;
|
tomwalters@0
|
59
|
tomwalters@0
|
60 if( n2 > 1 )
|
tomwalters@0
|
61 {
|
tomwalters@0
|
62 scale = ( abs( n1 ) - 1. ) / ( n2 - 1. ) ;
|
tomwalters@0
|
63
|
tomwalters@0
|
64 if( n1 > 0 )
|
tomwalters@0
|
65 for( i=0 ; i < n2 ; i++ )
|
tomwalters@0
|
66 array[ i ] = i * scale + .5 ;
|
tomwalters@0
|
67 else
|
tomwalters@0
|
68 for( i=0 ; i < n2 ; i++ )
|
tomwalters@0
|
69 array[ i ] = abs( n1 ) - 1 - (int) ( i * scale + .5 ) ;
|
tomwalters@0
|
70
|
tomwalters@0
|
71 for( i=n2 ; i < n2 + 16 ; i++ )
|
tomwalters@0
|
72 array[ i ] = 0 ;
|
tomwalters@0
|
73 }
|
tomwalters@0
|
74 else
|
tomwalters@0
|
75 array[ 0 ] = 0 ;
|
tomwalters@0
|
76
|
tomwalters@0
|
77 return( array ) ;
|
tomwalters@0
|
78 }
|
tomwalters@0
|
79
|
tomwalters@0
|
80 struct _fill_state { WindowObject window ; int row_flag, frame, framepoints, frames, major_count, *major, *minor ; short black, white ; } ;
|
tomwalters@0
|
81
|
tomwalters@0
|
82 static void fill_callback( state, bytes, buffer )
|
tomwalters@0
|
83 struct _fill_state *state ;
|
tomwalters@0
|
84 ByteCount *bytes ;
|
tomwalters@0
|
85 short *buffer ;
|
tomwalters@0
|
86 {
|
tomwalters@0
|
87 short *bptr = buffer ;
|
tomwalters@0
|
88
|
tomwalters@0
|
89 while( (char *) bptr < (char *) buffer + *bytes ) {
|
tomwalters@0
|
90
|
tomwalters@0
|
91 if( state->frames != 0 && state->frame % state->frames == 0 ) {
|
tomwalters@0
|
92 state->frame = 0 ;
|
tomwalters@0
|
93 state->major_count=0 ;
|
tomwalters@0
|
94 }
|
tomwalters@0
|
95
|
tomwalters@0
|
96 while( state->major[ state->major_count ] == state->frame ) {
|
tomwalters@0
|
97 state->major_count++ ;
|
tomwalters@0
|
98 if( state->row_flag )
|
tomwalters@0
|
99 FillRow( state->window, state->major_count, bptr, state->black, state->white, state->minor, Width( state->window ) ) ;
|
tomwalters@0
|
100 else
|
tomwalters@0
|
101 FillCol( state->window, state->major_count, bptr, state->black, state->white, state->minor, Height( state->window ) ) ;
|
tomwalters@0
|
102 }
|
tomwalters@0
|
103
|
tomwalters@0
|
104 state->frame++ ;
|
tomwalters@0
|
105
|
tomwalters@0
|
106 bptr += state->framepoints ;
|
tomwalters@0
|
107 }
|
tomwalters@0
|
108
|
tomwalters@0
|
109 return ;
|
tomwalters@0
|
110 }
|
tomwalters@0
|
111
|
tomwalters@0
|
112 static void excite_callback( state, bytes, buffer )
|
tomwalters@0
|
113 struct _fill_state *state ;
|
tomwalters@0
|
114 ByteCount *bytes ;
|
tomwalters@0
|
115 short *buffer ;
|
tomwalters@0
|
116 {
|
tomwalters@0
|
117 double origin = 1. + ( Height( state->window ) - 1. ) * ( 0. - state->black ) / ( state->white - state->black ) ;
|
tomwalters@0
|
118
|
tomwalters@0
|
119 Clear( state->window ) ;
|
tomwalters@0
|
120
|
tomwalters@0
|
121 Function( state->window, buffer, ToPoints( short, *bytes ), 1, origin, (double) ( state->white - state->black ) ) ;
|
tomwalters@0
|
122
|
tomwalters@0
|
123 return ;
|
tomwalters@0
|
124 }
|
tomwalters@0
|
125
|
tomwalters@0
|
126 static void smear_callback( state, bytes, buffer )
|
tomwalters@0
|
127 struct _fill_state *state ;
|
tomwalters@0
|
128 ByteCount *bytes ;
|
tomwalters@0
|
129 short *buffer ;
|
tomwalters@0
|
130 {
|
tomwalters@0
|
131 double origin = 1. + ( Height( state->window ) - 1. ) * ( 0. - state->black ) / ( state->white - state->black ) ;
|
tomwalters@0
|
132
|
tomwalters@0
|
133 Function( state->window, buffer, ToPoints( short, *bytes ), 1, origin, (double) ( state->white - state->black ) ) ;
|
tomwalters@0
|
134
|
tomwalters@0
|
135 return ;
|
tomwalters@0
|
136 }
|
tomwalters@0
|
137
|
tomwalters@0
|
138
|
tomwalters@0
|
139 static void fill_close( state )
|
tomwalters@0
|
140 struct _fill_state *state ;
|
tomwalters@0
|
141 {
|
tomwalters@0
|
142 Delete( state->major ) ;
|
tomwalters@0
|
143 Delete( state->minor ) ;
|
tomwalters@0
|
144
|
tomwalters@0
|
145 Delete( state ) ;
|
tomwalters@0
|
146
|
tomwalters@0
|
147 return ;
|
tomwalters@0
|
148 }
|
tomwalters@0
|
149
|
tomwalters@0
|
150 /*
|
tomwalters@0
|
151 Source SourceFill( source, black, white, window, framewidth, frameheight, frames, cfs )
|
tomwalters@0
|
152 Source source ;
|
tomwalters@0
|
153 int black, white ;
|
tomwalters@0
|
154 WindowObject window ;
|
tomwalters@0
|
155 int framewidth, frameheight ;
|
tomwalters@0
|
156 long frames ;
|
tomwalters@0
|
157 double *cfs ;
|
tomwalters@0
|
158 {
|
tomwalters@0
|
159 DeclareNew( struct _fill_state *, state ) ;
|
tomwalters@0
|
160 double mincf, spancf, pixcf ;
|
tomwalters@0
|
161 int row, chan ;
|
tomwalters@0
|
162
|
tomwalters@0
|
163 state->window = window ;
|
tomwalters@0
|
164
|
tomwalters@0
|
165 state->black = black ;
|
tomwalters@0
|
166 state->white = white ;
|
tomwalters@0
|
167
|
tomwalters@0
|
168 state->major = Match( (int) frames, Width( window ) ) ;
|
tomwalters@0
|
169 state->minor = Match( frameheight, Height( window ) ) ;
|
tomwalters@0
|
170
|
tomwalters@0
|
171 if( cfs != (double *) 0 ) {
|
tomwalters@0
|
172 chan = 0 ;
|
tomwalters@0
|
173 mincf = cfs[0] ;
|
tomwalters@0
|
174 spancf = cfs[frameheight-1]-mincf ;
|
tomwalters@0
|
175
|
tomwalters@0
|
176 for( row=0 ; row<Height( window ) ; row++ ) {
|
tomwalters@0
|
177
|
tomwalters@0
|
178 pixcf = mincf + ( row + 0.5 ) / Height( window ) * spancf ;
|
tomwalters@0
|
179
|
tomwalters@0
|
180 while( cfs[chan]<pixcf )
|
tomwalters@0
|
181 chan++ ;
|
tomwalters@0
|
182
|
tomwalters@0
|
183 state->minor[row] = chan ;
|
tomwalters@0
|
184 }
|
tomwalters@0
|
185 }
|
tomwalters@0
|
186
|
tomwalters@0
|
187 state->major_count = 0 ;
|
tomwalters@0
|
188 state->frame = 0 ;
|
tomwalters@0
|
189 state->frames = 0 ;
|
tomwalters@0
|
190 state->framepoints = 0 ;
|
tomwalters@0
|
191
|
tomwalters@0
|
192 state->row_flag = 0 ;
|
tomwalters@0
|
193
|
tomwalters@0
|
194 switch( abs( framewidth ) ) {
|
tomwalters@0
|
195 case 1 :
|
tomwalters@0
|
196 return ( NewTappingSource( (Pointer) state, fill_callback, fill_close, source, "fill.c filling" ) ) ;
|
tomwalters@0
|
197 case 2 :
|
tomwalters@0
|
198 return ( NewTappingSource( (Pointer) state, excite_callback, fill_close, source, "fill.c filling" ) ) ;
|
tomwalters@0
|
199 case 3 :
|
tomwalters@0
|
200 return ( NewTappingSource( (Pointer) state, smear_callback, fill_close, source, "fill.c filling" ) ) ;
|
tomwalters@0
|
201 }
|
tomwalters@0
|
202 }
|
tomwalters@0
|
203 */
|
tomwalters@0
|
204
|
tomwalters@0
|
205 static Source FillEither( window, source, black, white, framepoints, frames, scale, row_flag )
|
tomwalters@0
|
206 WindowObject window ;
|
tomwalters@0
|
207 Source source ;
|
tomwalters@0
|
208 int black, white ;
|
tomwalters@0
|
209 int framepoints, frames ;
|
tomwalters@0
|
210 double *scale ;
|
tomwalters@0
|
211 int row_flag ;
|
tomwalters@0
|
212 {
|
tomwalters@0
|
213 DeclareNew( struct _fill_state *, state ) ;
|
tomwalters@0
|
214 int minor_pixels, major_pixels ;
|
tomwalters@0
|
215 double min, span, value ;
|
tomwalters@0
|
216 int row, chan ;
|
tomwalters@0
|
217
|
tomwalters@0
|
218 if( row_flag ) {
|
tomwalters@0
|
219 minor_pixels = Width( window ) ;
|
tomwalters@0
|
220 major_pixels = Height( window ) ;
|
tomwalters@0
|
221 }
|
tomwalters@0
|
222 else {
|
tomwalters@0
|
223 minor_pixels = Height( window ) ;
|
tomwalters@0
|
224 major_pixels = Width( window ) ;
|
tomwalters@0
|
225 }
|
tomwalters@0
|
226
|
tomwalters@0
|
227 state->window = window ;
|
tomwalters@0
|
228
|
tomwalters@0
|
229 state->black = black ;
|
tomwalters@0
|
230 state->white = white ;
|
tomwalters@0
|
231
|
tomwalters@0
|
232 state->major = Match( frames, major_pixels ) ;
|
tomwalters@0
|
233 state->minor = Match( framepoints, minor_pixels ) ;
|
tomwalters@0
|
234
|
tomwalters@0
|
235 if( !row_flag ) /* reverse match array for columns for now */
|
tomwalters@0
|
236 for( chan=0 ; chan<minor_pixels/2 ; chan++ ) {
|
tomwalters@0
|
237 row = state->minor[minor_pixels-1-chan] ;
|
tomwalters@0
|
238 state->minor[minor_pixels-1-chan] = state->minor[chan] ;
|
tomwalters@0
|
239 state->minor[chan]= row ;
|
tomwalters@0
|
240 }
|
tomwalters@0
|
241
|
tomwalters@0
|
242 if( scale != (double *) 0 ) {
|
tomwalters@0
|
243
|
tomwalters@0
|
244 chan = 0 ;
|
tomwalters@0
|
245 min = scale[0] ;
|
tomwalters@0
|
246 span = scale[framepoints-1]-min ;
|
tomwalters@0
|
247
|
tomwalters@0
|
248 for( row=0 ; row < minor_pixels ; row++ ) {
|
tomwalters@0
|
249
|
tomwalters@0
|
250 value = min + ( row + 0.5 ) / minor_pixels * span ;
|
tomwalters@0
|
251
|
tomwalters@0
|
252 while( scale[chan] < value )
|
tomwalters@0
|
253 chan++ ;
|
tomwalters@0
|
254
|
tomwalters@0
|
255 state->minor[row] = chan ;
|
tomwalters@0
|
256 }
|
tomwalters@0
|
257 }
|
tomwalters@0
|
258
|
tomwalters@0
|
259 state->framepoints = framepoints ;
|
tomwalters@0
|
260 state->frames = frames ;
|
tomwalters@0
|
261 state->frame = 0 ;
|
tomwalters@0
|
262 state->major_count = 0 ;
|
tomwalters@0
|
263
|
tomwalters@0
|
264 state->row_flag = row_flag ;
|
tomwalters@0
|
265
|
tomwalters@0
|
266 return ( NewTappingSource( (Pointer) state, fill_callback, fill_close, source, "fill.c filling" ) ) ;
|
tomwalters@0
|
267 }
|
tomwalters@0
|
268
|
tomwalters@0
|
269 Source fillAcross( window, source, black, white, framepoints, frames, scale )
|
tomwalters@0
|
270 WindowObject window ;
|
tomwalters@0
|
271 Source source ;
|
tomwalters@0
|
272 int black, white ;
|
tomwalters@0
|
273 int framepoints, frames ;
|
tomwalters@0
|
274 double *scale ;
|
tomwalters@0
|
275 {
|
tomwalters@0
|
276 return ( FillEither( window, source, black, white, framepoints, frames, scale, 0 ) ) ;
|
tomwalters@0
|
277 }
|
tomwalters@0
|
278
|
tomwalters@0
|
279 Source fillDown( window, source, black, white, framepoints, frames, scale )
|
tomwalters@0
|
280 WindowObject window ;
|
tomwalters@0
|
281 Source source ;
|
tomwalters@0
|
282 int black, white ;
|
tomwalters@0
|
283 int framepoints, frames ;
|
tomwalters@0
|
284 double *scale ;
|
tomwalters@0
|
285 {
|
tomwalters@0
|
286 return ( FillEither( window, source, black, white, framepoints, frames, scale, 1 ) ) ;
|
tomwalters@0
|
287 }
|
tomwalters@0
|
288
|
tomwalters@0
|
289
|