ruby-vips 0.1.1

Sign up to get free protection for your applications and to get access to all the features.
data/ext/image.h ADDED
@@ -0,0 +1,71 @@
1
+ #ifndef RUBY_VIPS_IMAGE_H
2
+ #define RUBY_VIPS_IMAGE_H
3
+
4
+ #include "ruby_vips.h"
5
+
6
+ extern VALUE cVIPSImage;
7
+
8
+ struct _vipsImg {
9
+ VipsImage *in;
10
+ VALUE *deps;
11
+ int deps_len;
12
+ };
13
+ typedef struct _vipsImg vipsImg;
14
+
15
+ void img_add_dep(vipsImg*, VALUE);
16
+ VALUE img_spawn(VALUE);
17
+ VALUE img_spawn2(VALUE, VALUE);
18
+ VALUE img_spawn3(VALUE, VALUE, VALUE);
19
+ VALUE img_alloc(VALUE);
20
+ VALUE img_init(VALUE, VipsImage*);
21
+ VALUE img_init_partial();
22
+ VALUE img_init_partial_anyclass(VALUE);
23
+ VipsBandFmt img_id_to_band_fmt(VALUE);
24
+
25
+ #define GetImg(obj, data, im) \
26
+ vipsImg *data; \
27
+ VipsImage *im; \
28
+ Data_Get_Struct(obj, vipsImg, data); \
29
+ im = data->in;
30
+
31
+ #define OutImg(obj, new, data_new, im_new) \
32
+ VALUE new = img_spawn(obj); \
33
+ GetImg(new, data_new, im_new);
34
+
35
+ #define OutImg2(obj, obj2, new, data_new, im_new) \
36
+ VALUE new = img_spawn2(obj, obj2); \
37
+ GetImg(new, data_new, im_new);
38
+
39
+ #define OutImg3(obj, obj2, obj3, new, data_new, im_new) \
40
+ VALUE new = img_spawn3(obj, obj2, obj3); \
41
+ GetImg(new, data_new, im_new);
42
+
43
+ #define OutPartial(new, data_new, im_new) \
44
+ VALUE new = img_init_partial(); \
45
+ GetImg(new, data_new, im_new);
46
+
47
+ #define RUBY_VIPS_UNARY(VIPS_METHOD) \
48
+ do { \
49
+ GetImg(obj, data, im); \
50
+ OutImg(obj, new, data_new, im_new); \
51
+ \
52
+ if (VIPS_METHOD(im, im_new)) \
53
+ vips_lib_error(); \
54
+ \
55
+ return new; \
56
+ } while(0)
57
+
58
+ #define RUBY_VIPS_BINARY(VIPS_METHOD) \
59
+ do { \
60
+ GetImg(obj, data, im); \
61
+ GetImg(obj2, data2, im2); \
62
+ OutImg2(obj, obj2, new, data_new, im_new); \
63
+ \
64
+ if (VIPS_METHOD(im, im2, im_new)) \
65
+ vips_lib_error(); \
66
+ \
67
+ return new; \
68
+ } while(0)
69
+
70
+ #endif
71
+
@@ -0,0 +1,940 @@
1
+ #include "ruby_vips.h"
2
+ #include "image.h"
3
+ #include "mask.h"
4
+ #include "interpolator.h"
5
+
6
+ /*
7
+ * call-seq:
8
+ * im.measure_area(left, top, width, height, h, v, sel) -> array
9
+ *
10
+ * Analyse a grid of colour patches, producing an array of averages.
11
+ * Pass a box defined by <i>left</i>, <i>top</i>, <i>width</i>, and
12
+ * <i>height</i>, the number of horizontal and vertical patches <i>h</i> and
13
+ * <i>v</i>, an array giving the numbers of the patches to measure <i>sel</i>
14
+ * (patches are numbered left-to-right, top-to-bottom, starting with 1). Return
15
+ * an array in which rows are patches and columns are bands. Only the central
16
+ * 50% of each patch is averaged.
17
+ */
18
+
19
+ VALUE
20
+ img_measure_area(VALUE obj, VALUE left, VALUE top, VALUE width, VALUE height,
21
+ VALUE h, VALUE v, VALUE sel)
22
+ {
23
+ DOUBLEMASK *ret;
24
+ VALUE results;
25
+ int *a, i, len = RARRAY_LENINT(sel);
26
+ GetImg(obj, data, im);
27
+
28
+ a = ALLOC_N(int, len);
29
+ for (i = 0; i < len; i++)
30
+ a[i] = NUM2INT(RARRAY_PTR(sel)[i]);
31
+
32
+ ret = im_measure_area(im, NUM2INT(left), NUM2INT(top), NUM2INT(width),
33
+ NUM2INT(height), NUM2INT(h), NUM2INT(v), a, len, "img_measure_area");
34
+
35
+ xfree(a);
36
+
37
+ return dmask2rb(ret);
38
+ }
39
+
40
+ /*
41
+ * call-seq:
42
+ * im.stats -> array
43
+ *
44
+ * Find many image statistics in a single pass through the pixels. Returns an
45
+ * array of 6 columns by n+1 (where n is number of bands in the image) rows.
46
+ * Columns are statistics, and are, in order: minimum, maximum, sum, sum of
47
+ * squares, mean, standard deviation. Row 0 has statistics for all bands
48
+ * together, row 1 has stats for band 1, and so on.
49
+ */
50
+
51
+ VALUE
52
+ img_stats(VALUE obj)
53
+ {
54
+ DOUBLEMASK *ret;
55
+ GetImg(obj, data, im);
56
+
57
+ if (!(ret = im_stats(im)))
58
+ vips_lib_error();
59
+
60
+ return dmask2rb(ret);
61
+ }
62
+
63
+ /*
64
+ * call-seq:
65
+ * im.max -> number
66
+ *
67
+ * Finds the the maximum value of *self*. If input is complex, the max modulus
68
+ * is returned. Finds the maximum of all bands: if you want to find the maximum
69
+ * of each band separately, use Image#stats.
70
+ */
71
+
72
+ VALUE
73
+ img_max(VALUE obj) {
74
+ double out;
75
+ GetImg(obj, data, im);
76
+
77
+ if (im_max(im, &out))
78
+ vips_lib_error();
79
+
80
+ return DBL2NUM(out);
81
+ }
82
+
83
+ /*
84
+ * call-seq:
85
+ * im.min -> number
86
+ *
87
+ * Finds the the minimum value of the image. If input is complex, the min
88
+ * modulus is returned. Finds the minimum of all bands: if you want to find the
89
+ * minimum of each band separately, use Image#stats.
90
+ */
91
+
92
+ VALUE
93
+ img_min(VALUE obj) {
94
+ double out;
95
+ GetImg(obj, data, im);
96
+
97
+ if (im_min(im, &out))
98
+ vips_lib_error();
99
+
100
+ return DBL2NUM(out);
101
+ }
102
+
103
+ /*
104
+ * call-seq:
105
+ * im.avg -> number
106
+ *
107
+ * Finds the average of an image. Works on any non-complex image format.
108
+ */
109
+
110
+ VALUE
111
+ img_avg(VALUE obj) {
112
+ double out;
113
+ GetImg(obj, data, im);
114
+
115
+ if (im_avg(im, &out))
116
+ vips_lib_error();
117
+
118
+ return DBL2NUM(out);
119
+ }
120
+
121
+ /*
122
+ * call-seq:
123
+ * im.deviate -> number
124
+ *
125
+ * This operation finds the standard deviation of all pixels in the image. It
126
+ * operates on all bands of the input image: use Image#stats if you need to
127
+ * calculate an average for each band.
128
+ *
129
+ * Non-complex images only.
130
+ */
131
+
132
+ VALUE
133
+ img_deviate(VALUE obj) {
134
+ double out;
135
+ GetImg(obj, data, im);
136
+
137
+ if (im_deviate(im, &out))
138
+ vips_lib_error();
139
+
140
+ return DBL2NUM(out);
141
+ }
142
+
143
+ /*
144
+ * call-seq:
145
+ * im.maxpos_avg -> [ x, y, value ]
146
+ *
147
+ * Function to find the maximum of an image. In the event of a draw, returns
148
+ * average of all drawing coords.
149
+ */
150
+
151
+ VALUE
152
+ img_maxpos_avg(VALUE obj) {
153
+ double x, y, out;
154
+ GetImg(obj, data, im);
155
+
156
+ if (im_maxpos_avg(im, &x, &y, &out))
157
+ vips_lib_error();
158
+
159
+ return rb_ary_new3(3, DBL2NUM(x), DBL2NUM(y), DBL2NUM(out));
160
+ }
161
+
162
+ static VALUE
163
+ img_maxpos_single(VALUE obj) {
164
+ double out;
165
+ int x, y;
166
+ GetImg(obj, data, im);
167
+
168
+ if (im_maxpos(im, &x, &y, &out))
169
+ vips_lib_error();
170
+
171
+ return rb_ary_new3(3, INT2NUM(x), INT2NUM(y), DBL2NUM(out));
172
+ }
173
+
174
+ static VALUE
175
+ img_maxpos_n(VALUE obj, int len) {
176
+ double *out;
177
+ int im_return, i, *x, *y;
178
+ VALUE t, ary;
179
+ GetImg(obj, data, im);
180
+
181
+ ary = rb_ary_new2(len);
182
+
183
+ x = ALLOC_N(int, len);
184
+ y = ALLOC_N(int, len);
185
+ out = ALLOC_N(double, len);
186
+
187
+ if (!(im_return = im_maxpos_vec(im, x, y, out, len))) {
188
+ for (i = 0; i < len; i++) {
189
+ t = rb_ary_new3(3, INT2NUM(x[i]), INT2NUM(y[i]), DBL2NUM(out[i]));
190
+ rb_ary_push(ary, t);
191
+ }
192
+ }
193
+
194
+ xfree(x);
195
+ xfree(y);
196
+ xfree(out);
197
+
198
+ if(im_return)
199
+ vips_lib_error();
200
+
201
+ return ary;
202
+ }
203
+
204
+ /*
205
+ * call-seq:
206
+ * im.maxpos -> x, y, value
207
+ * im.maxpos(n, ...) -> [ x, y, value ], ...
208
+ *
209
+ * Function to find the maximum of an image. Works for any image type. Returns
210
+ * an array with the x and y coordinates of the maximum value and the
211
+ * corresponding value. If <i>n</i> is given, returns the <i>n</i> largest
212
+ * values. For complex images, finds the pixel with the highest modulus.
213
+ */
214
+
215
+ VALUE
216
+ img_maxpos(int argc, VALUE *argv, VALUE obj) {
217
+ VALUE v_num;
218
+
219
+ rb_scan_args(argc, argv, "01", &v_num);
220
+ if (NIL_P(v_num))
221
+ return img_maxpos_single(obj);
222
+ else
223
+ return img_maxpos_n(obj, NUM2INT(v_num));
224
+ }
225
+
226
+ static VALUE
227
+ img_minpos_single(VALUE obj) {
228
+ double out;
229
+ int x, y;
230
+ GetImg(obj, data, im);
231
+
232
+ if (im_minpos(im, &x, &y, &out))
233
+ vips_lib_error();
234
+
235
+ return rb_ary_new3(3, INT2NUM(x), INT2NUM(y), DBL2NUM(out));
236
+ }
237
+
238
+ static VALUE
239
+ img_minpos_n(VALUE obj, int len) {
240
+ double *out;
241
+ int im_return, i, *x, *y;
242
+ VALUE t, ary;
243
+ GetImg(obj, data, im);
244
+
245
+ ary = rb_ary_new2(len);
246
+
247
+ x = ALLOC_N(int, len);
248
+ y = ALLOC_N(int, len);
249
+ out = ALLOC_N(double, len);
250
+
251
+ if (!(im_return = im_minpos_vec(im, x, y, out, len))) {
252
+ for (i = 0; i < len; i++) {
253
+ t = rb_ary_new3(3, INT2NUM(x[i]), INT2NUM(y[i]), DBL2NUM(out[i]));
254
+ rb_ary_push(ary, t);
255
+ }
256
+ }
257
+
258
+ xfree(x);
259
+ xfree(y);
260
+ xfree(out);
261
+
262
+ if(im_return)
263
+ vips_lib_error();
264
+
265
+ return ary;
266
+ }
267
+
268
+ /*
269
+ * call-seq:
270
+ * im.minpos -> x, y, value
271
+ * im.minpos(n) -> [ x, y, value ], ...
272
+ *
273
+ * Function to find the minimum of an image. Works for any image type. Returns
274
+ * an array with the x and y coordinates of the minimum value and the
275
+ * corresponding value. If <i>n</i> is given, returns the <i>n</i> lowest
276
+ * values. For complex images, finds the pixel with the lowest modulus.
277
+ */
278
+
279
+ VALUE
280
+ img_minpos(int argc, VALUE *argv, VALUE obj) {
281
+ VALUE v_num;
282
+
283
+ rb_scan_args(argc, argv, "01", &v_num);
284
+ if (NIL_P(v_num))
285
+ return img_minpos_single(obj);
286
+ else
287
+ return img_minpos_n(obj, NUM2INT(v_num));
288
+ }
289
+
290
+ /*
291
+ * call-seq:
292
+ * im.bandmean -> image
293
+ *
294
+ * Creates a one-band image where each pixel is the average of the bands for
295
+ * that pixel in the input image. The output band format is the same as the
296
+ * input band format. Integer types use round-to-nearest averaging.
297
+ *
298
+ */
299
+
300
+ VALUE
301
+ img_bandmean(VALUE obj)
302
+ {
303
+ RUBY_VIPS_UNARY(im_bandmean);
304
+ }
305
+
306
+ /*
307
+ * call-seq:
308
+ * im.add(other_image) -> image
309
+ * im + other_image -> image
310
+ *
311
+ * This operation calculates im + <i>other_image</i> and writes the result to
312
+ * a new image. The images must be the same size. They may have any format.
313
+ *
314
+ * If the number of bands differs, one of the images must have one band. In
315
+ * this case, an n-band image is formed from the one-band image by joining n
316
+ * copies of the one-band image together, and then the two n-band images are
317
+ * operated upon.
318
+ *
319
+ * The two input images are cast up to the smallest common type.
320
+ */
321
+
322
+ VALUE
323
+ img_add(VALUE obj, VALUE obj2)
324
+ {
325
+ RUBY_VIPS_BINARY(im_add);
326
+ }
327
+
328
+ /*
329
+ * call-seq:
330
+ * im.subtract(other_image) -> image
331
+ * im - other_image -> image
332
+ *
333
+ * This operation calculates im - <i>image</i> and writes the result to a new
334
+ * image. The images must be the same size. They may have any format.
335
+ *
336
+ * If the number of bands differs, one of the images must have one band. In this
337
+ * case, an n-band image is formed from the one-band image by joining n copies
338
+ * of the one-band image together, and then the two n-band images are operated
339
+ * upon.
340
+ *
341
+ * The two input images are cast up to the smallest common type.
342
+ */
343
+
344
+ VALUE
345
+ img_subtract(VALUE obj, VALUE obj2)
346
+ {
347
+ RUBY_VIPS_BINARY(im_subtract);
348
+ }
349
+
350
+ /*
351
+ * call-seq:
352
+ * im.invert -> image
353
+ *
354
+ * This operation calculates (255 - im). The operation works on uchar images
355
+ * only. The input can have any no of channels.
356
+ *
357
+ * See Image#exptra for a function which can process any input image type.
358
+ */
359
+
360
+ VALUE
361
+ img_invert(VALUE obj)
362
+ {
363
+ RUBY_VIPS_UNARY(im_invert);
364
+ }
365
+
366
+ static VALUE
367
+ img_lin_mult(int argc, VALUE *argv_a, VALUE *argv_b, VALUE obj)
368
+ {
369
+ double *a, *b;
370
+ int i;
371
+
372
+ GetImg(obj, data, im);
373
+ OutImg(obj, new, data_new, im_new);
374
+
375
+ a = IM_ARRAY(im_new, argc, double);
376
+ b = IM_ARRAY(im_new, argc, double);
377
+
378
+ for (i = 0; i < argc; i++) {
379
+ a[i] = NUM2DBL(argv_a[i]);
380
+ b[i] = NUM2DBL(argv_b[i]);
381
+ }
382
+
383
+ if (im_lintra_vec(argc, a, im, b, im_new))
384
+ vips_lib_error();
385
+
386
+ return new;
387
+ }
388
+
389
+ /*
390
+ * call-seq:
391
+ * im.lin(a, b) -> image
392
+ * im.lin([a1, a2, a3], [b1, b2, b3]) -> image
393
+ *
394
+ * Pass an image through a linear transform - ie. im * <i>a</i> + <i>b</i>.
395
+ * Output is always float for integer input, double for double input, complex
396
+ * for complex input and double complex for double complex input.
397
+ *
398
+ * If the arrays are passed in and they have the same number of elements as
399
+ * there are bands in the image, then one array element is used for each band.
400
+ * If the arrays have more than one element and the image only has a single
401
+ * band, the result is a many-band image where each band corresponds to one
402
+ * array element.
403
+ */
404
+
405
+ VALUE
406
+ img_lin(VALUE obj, VALUE a, VALUE b)
407
+ {
408
+ int len = 1;
409
+ VALUE *a_v = &a;
410
+ VALUE *b_v = &b;
411
+
412
+ if (TYPE(a) == T_ARRAY) {
413
+ len = RARRAY_LEN(a);
414
+
415
+ if (len < 1 || len != RARRAY_LEN(b))
416
+ rb_raise(rb_eArgError, "argument arrays must be of equal length with at least one element");
417
+
418
+ a_v = RARRAY_PTR(a);
419
+ b_v = RARRAY_PTR(b);
420
+ }
421
+
422
+ return img_lin_mult(len, a_v, b_v, obj);
423
+ }
424
+
425
+ /*
426
+ * call-seq:
427
+ * im.multiply(other_image) -> image
428
+ * im * other_image -> image
429
+ *
430
+ * This operation calculates im * <i>other_image</i>. The images must be the
431
+ * same size. They may have any format.
432
+ *
433
+ * If the number of bands differs, one of the images must have one band. In
434
+ * this case, an n-band image is formed from the one-band image by joining n
435
+ * copies of the one-band image together, and then the two n-band images are
436
+ * operated upon.
437
+ *
438
+ * The two input images are cast up to the smallest common type.
439
+ */
440
+
441
+ VALUE
442
+ img_multiply(VALUE obj, VALUE obj2)
443
+ {
444
+ RUBY_VIPS_BINARY(im_multiply);
445
+ }
446
+
447
+ static VALUE
448
+ img_remainder_img(VALUE obj, VALUE obj2)
449
+ {
450
+ RUBY_VIPS_BINARY(im_remainder);
451
+ }
452
+
453
+ static VALUE
454
+ img_remainder_const(int argc, VALUE *argv, VALUE obj)
455
+ {
456
+ int i;
457
+ double *c;
458
+
459
+ GetImg(obj, data, im);
460
+ OutImg(obj, new, data_new, im_new);
461
+
462
+ c = IM_ARRAY(im_new, argc, double);
463
+ for (i = 0; i < argc; i++)
464
+ c[i] = NUM2DBL(argv[i]);
465
+
466
+ if (im_remainder_vec(im, im_new, argc, c))
467
+ vips_lib_error();
468
+
469
+ return new;
470
+ }
471
+
472
+ /*
473
+ * call-seq:
474
+ * im % other_image -> image
475
+ * im % c -> image
476
+ * im % [c, ...] -> image
477
+ *
478
+ * im.remainder(other_image) -> image
479
+ * im.remainder(c) -> image
480
+ * im.remainder(c, ...) -> image
481
+ *
482
+ * The first form calculates im % <i>other_image</i> (remainder after
483
+ * division). The images must be the same size. They may have any non-complex
484
+ * format. For float formats, it calculates im - <i>other_image</i> * floor (im
485
+ * / <i>other_image</i>).
486
+ *
487
+ * If the number of bands differs, one of the images must have one band. In
488
+ * this case, an n-band image is formed from the one-band image by joining n
489
+ * copies of the one-band image together, and then the two n-band images are
490
+ * operated upon.
491
+ *
492
+ * The two input images are cast up to the smallest common type.
493
+ *
494
+ * The second and third form calculates im % <i>c</i> (remainder after division
495
+ * by constant). The image may have any non-complex format. For float formats,
496
+ * calculates im - <i>c</i> * floor (im / <i>c</i>).
497
+ *
498
+ * If the number of image bands and constants differs, then the image must have
499
+ * one band or there must only one constant. Either the image is up-banded by
500
+ * joining n copies of the one-band image together, or the same constant is
501
+ * used for all image bands.
502
+ */
503
+
504
+ VALUE
505
+ img_remainder(int argc, VALUE *argv, VALUE obj)
506
+ {
507
+ if (argc < 1)
508
+ rb_raise(rb_eArgError, "Expected at least one constant");
509
+ else if (argc == 1 && CLASS_OF(argv[0]) == cVIPSImage)
510
+ return img_remainder_img(obj, argv[0]);
511
+ else
512
+ return img_remainder_const(argc, argv, obj);
513
+ }
514
+
515
+ VALUE
516
+ img_remainder_binop(VALUE obj, VALUE arg)
517
+ {
518
+ int argc = 1;
519
+ VALUE *argv = &arg;
520
+
521
+ if (TYPE(arg) == T_ARRAY) {
522
+ argc = RARRAY_LEN(arg);
523
+ argv = RARRAY_PTR(arg);
524
+ }
525
+
526
+ return img_remainder(argc, argv, obj);
527
+ }
528
+
529
+ /*
530
+ * call-seq:
531
+ * im.divide(other_image) -> image
532
+ * im / other_image -> image
533
+ *
534
+ * This operation calculates im / <i>other_image</i>. The images must be the
535
+ * same size. They may have any format.
536
+ *
537
+ * If the number of bands differs, one of the images must have one band. In
538
+ * this case, an n-band image is formed from the one-band image by joining n
539
+ * copies of the one-band image together, and then the two n-band images are
540
+ * operated upon.
541
+ *
542
+ * The two input images are cast up to the smallest common type.
543
+ */
544
+
545
+ VALUE
546
+ img_divide(VALUE obj, VALUE obj2)
547
+ {
548
+ RUBY_VIPS_BINARY(im_divide);
549
+ }
550
+
551
+ /*
552
+ * call-seq:
553
+ * im.recomb(array) -> image
554
+ *
555
+ * This operation recombines an image's bands. Each pixel in im is treated as
556
+ * an n-element vector, where n is the number of bands in im, and multipled by
557
+ * the n x m matrix <i>array</i> to produce the m-band output image.
558
+ *
559
+ * The output image is always float, unless im is double, in which case it is
560
+ * double too. No complex images allowed.
561
+ *
562
+ * It's useful for various sorts of colour space conversions.
563
+ */
564
+
565
+ VALUE
566
+ img_recomb(VALUE obj, VALUE recomb)
567
+ {
568
+ DOUBLEMASK *dmask;
569
+
570
+ GetImg(obj, data, im);
571
+ OutImg(obj, new, data_new, im_new);
572
+
573
+ mask_arg2mask(recomb, NULL, &dmask);
574
+
575
+ if (im_recomb(im, im_new, dmask))
576
+ vips_lib_error();
577
+
578
+ return new;
579
+ }
580
+
581
+ /*
582
+ * call-seq:
583
+ * im.sign -> image
584
+ *
585
+ * Finds the unit vector in the direction of the pixel value. For non-complex
586
+ * images, it returns a signed char image with values -1, 0, and 1 for
587
+ * negative, zero and positive pixels. For complex images, it returns a complex
588
+ * normalised to length 1.
589
+ */
590
+
591
+ VALUE
592
+ img_sign(VALUE obj)
593
+ {
594
+ RUBY_VIPS_UNARY(im_sign);
595
+ }
596
+
597
+ /*
598
+ * call-seq:
599
+ * im.abs -> image
600
+ *
601
+ * This operation finds the absolute value of an image. It does a copy for
602
+ * unsigned integer types, negate for negative values in signed integer types,
603
+ * fabs(3) for float types, and calculate modulus for complex types.
604
+ */
605
+
606
+ VALUE
607
+ img_abs(VALUE obj)
608
+ {
609
+ RUBY_VIPS_UNARY(im_abs);
610
+ }
611
+
612
+ /*
613
+ * call-seq:
614
+ * im.floor -> image
615
+ *
616
+ * For each pixel, find the largest integral value not less than. Copy for
617
+ * integer types. Output type == input type.
618
+ */
619
+
620
+ VALUE
621
+ img_floor(VALUE obj)
622
+ {
623
+ RUBY_VIPS_UNARY(im_floor);
624
+ }
625
+
626
+ /*
627
+ * call-seq:
628
+ * im.rint -> image
629
+ *
630
+ * Finds the nearest integral value. Copy for integer types. Output type ==
631
+ * input type.
632
+ */
633
+
634
+ VALUE
635
+ img_rint(VALUE obj)
636
+ {
637
+ RUBY_VIPS_UNARY(im_rint);
638
+ }
639
+
640
+ /*
641
+ * call-seq:
642
+ * im.ceil -> image
643
+ *
644
+ * For each pixel, find the smallest integral value not less than. Copy for
645
+ * integer types. Output type == input type.
646
+ */
647
+
648
+ VALUE
649
+ img_ceil(VALUE obj)
650
+ {
651
+ RUBY_VIPS_UNARY(im_ceil);
652
+ }
653
+
654
+ /*
655
+ * call-seq:
656
+ * linreg(x) -> image
657
+ * linreg(*args) -> image
658
+ *
659
+ * Function to find perform pixelwise linear regression on an array of
660
+ * single band images. The output is a seven-band double image.
661
+ *
662
+ * <i>x</i> is the position of each image (pixel value is Y).
663
+ */
664
+
665
+ VALUE
666
+ img_s_linreg(int argc, VALUE *argv, VALUE obj)
667
+ {
668
+ vipsImg *in;
669
+ IMAGE **ins;
670
+ double *vips_xs;
671
+ VALUE cur_img;
672
+ int i;
673
+ OutPartial(new, data_new, im_new);
674
+
675
+ vips_xs = IM_ARRAY(im_new, argc, double);
676
+ ins = IM_ARRAY(im_new, argc + 1, IMAGE*);
677
+
678
+ ins[argc] = NULL; /* takes a NULL terminated array of IMAGE pointers */
679
+
680
+ for (i = 0; i < argc; i++) {
681
+ cur_img = RARRAY_PTR(argv[i])[0];
682
+ img_add_dep(data_new, cur_img);
683
+
684
+ Data_Get_Struct(cur_img, vipsImg, in);
685
+ ins[i] = in->in;
686
+
687
+ vips_xs[i] = NUM2DBL(RARRAY_PTR(argv[i])[1]);
688
+ }
689
+
690
+ if (im_linreg(ins, im_new, vips_xs))
691
+ vips_lib_error();
692
+
693
+ return new;
694
+ }
695
+
696
+ /*
697
+ * call-seq:
698
+ * im.point(interpolator_sym, x, y, band) -> number
699
+ *
700
+ * Find the value at (@x, @y) in given band of image.
701
+ * Non-integral values are calculated using the supplied interpolator, e.g.
702
+ * :bilinear.
703
+ *
704
+ * To get a list of available interpolators, look at
705
+ * VIPS::Interpolator::INTERPOLATORS.keys
706
+ */
707
+
708
+ VALUE
709
+ img_point(VALUE obj, VALUE itrp_sym, VALUE x, VALUE y, VALUE band)
710
+ {
711
+ double out;
712
+ VipsInterpolate *itrp_vips = interp_lookup(itrp_sym);
713
+ GetImg(obj, data, im);
714
+
715
+ if (im_point(im, itrp_vips, NUM2DBL(x), NUM2DBL(y), NUM2INT(band), &out))
716
+ vips_lib_error();
717
+
718
+ return DBL2NUM(out);
719
+ }
720
+
721
+ /*
722
+ * call-seq:
723
+ * im.pow(c, ...) -> image
724
+ *
725
+ * im ** c -> image
726
+ * im ** [c, ...] -> image
727
+ *
728
+ * Tansforms each pixel value in the input image to value ** <i>c</i> in the
729
+ * output image. It detects division by zero, setting those pixels to zero in
730
+ * the output. Beware: it does this silently!
731
+ *
732
+ * If one constant <i>c</i> is given, that constant is used for each image
733
+ * band. If more than one value is given, it must have the same number of
734
+ * elements as there are bands in the image, and one element is used for each
735
+ * band.
736
+ */
737
+
738
+ VALUE
739
+ img_pow(int argc, VALUE *argv, VALUE obj)
740
+ {
741
+ double *c;
742
+ int i;
743
+
744
+ if (argc < 1)
745
+ rb_raise(rb_eArgError, "Expected at least one constant");
746
+
747
+ GetImg(obj, data, im);
748
+ OutImg(obj, new, data_new, im_new);
749
+
750
+ c = IM_ARRAY(im_new, argc, double);
751
+
752
+ for (i = 0; i < argc; i++)
753
+ c[i] = NUM2DBL(argv[i]);
754
+
755
+ if (im_powtra_vec(im, im_new, argc, c))
756
+ vips_lib_error();
757
+
758
+ return new;
759
+ }
760
+
761
+ VALUE
762
+ img_pow_binop(VALUE obj, VALUE arg)
763
+ {
764
+ int argc = 1;
765
+ VALUE *argv = &arg;
766
+
767
+ if (TYPE(arg) == T_ARRAY) {
768
+ argc = RARRAY_LEN(arg);
769
+ argv = RARRAY_PTR(arg);
770
+ }
771
+
772
+ return img_pow(argc, argv, obj);
773
+ }
774
+
775
+ /*
776
+ * call-seq:
777
+ * im.expn(c, ...) -> image
778
+ *
779
+ * Transforms each pixel value of the input image to <i>c</i> ** value in the
780
+ * output image. It detects division by zero, setting those pixels to zero in
781
+ * the output. Beware: it does this silently!
782
+ *
783
+ * If one constant <i>c</i> is given, that constant is used for each image
784
+ * band. If more than one value is given, it must have the same number of
785
+ * elements as there are bands in the image, and one element is used for each
786
+ * band.
787
+ */
788
+
789
+ VALUE
790
+ img_expn(int argc, VALUE *argv, VALUE obj)
791
+ {
792
+ double *c;
793
+ int i;
794
+ GetImg(obj, data, im);
795
+ OutImg(obj, new, data_new, im_new);
796
+
797
+ c = IM_ARRAY(im_new, argc, double);
798
+
799
+ for (i = 0; i < argc; i++)
800
+ c[i] = NUM2DBL(argv[i]);
801
+
802
+ if (im_expntra_vec(im, im_new, argc, c))
803
+ vips_lib_error();
804
+
805
+ return new;
806
+ }
807
+
808
+ /*
809
+ * call-seq:
810
+ * im.log -> image
811
+ *
812
+ * For each pixel, calculate the natural logarithm. The output type is float,
813
+ * unless the input is double, in which case the output is double. Non-complex
814
+ * images only.
815
+ */
816
+
817
+ VALUE
818
+ img_log(VALUE obj)
819
+ {
820
+ RUBY_VIPS_UNARY(im_logtra);
821
+ }
822
+
823
+ /*
824
+ * call-seq:
825
+ * im.log10 -> image
826
+ *
827
+ * For each pixel, calculate the base 10 logarithm. The output type is float,
828
+ * unless the input is double, in which case the output is double. Non-complex
829
+ * images only.
830
+ */
831
+
832
+ VALUE
833
+ img_log10(VALUE obj)
834
+ {
835
+ RUBY_VIPS_UNARY(im_log10tra);
836
+ }
837
+
838
+ /*
839
+ * call-seq:
840
+ * im.sin -> image
841
+ *
842
+ * For each pixel, calculate the sine. Angles are expressed in degrees. The
843
+ * output type is float, unless the input is double, in which case the output
844
+ * is double. Non-complex images only.
845
+ */
846
+
847
+ VALUE
848
+ img_sin(VALUE obj)
849
+ {
850
+ RUBY_VIPS_UNARY(im_sintra);
851
+ }
852
+
853
+ /*
854
+ * call-seq:
855
+ * im.cos -> image
856
+ *
857
+ * For each pixel, calculate the cosine. Angles are expressed in degrees. The
858
+ * output type is float, unless the input is double, in which case the output
859
+ * is double. Non-complex images only.
860
+ */
861
+
862
+ VALUE
863
+ img_cos(VALUE obj)
864
+ {
865
+ RUBY_VIPS_UNARY(im_costra);
866
+ }
867
+
868
+ /*
869
+ * call-seq:
870
+ * im.tan -> image
871
+ *
872
+ * For each pixel, calculate the tangent. Angles are expressed in degrees. The
873
+ * output type is float, unless the input is double, in which case the output
874
+ * is double. Non-complex images only.
875
+ */
876
+
877
+ VALUE
878
+ img_tan(VALUE obj)
879
+ {
880
+ RUBY_VIPS_UNARY(im_tantra);
881
+ }
882
+
883
+ /*
884
+ * call-seq:
885
+ * im.asin -> image
886
+ *
887
+ * For each pixel, calculate the arc or inverse sine. Angles are expressed in
888
+ * degrees. The output type is float, unless the input is double, in which case
889
+ * the output is double. Non-complex images only.
890
+ */
891
+
892
+ VALUE
893
+ img_asin(VALUE obj)
894
+ {
895
+ RUBY_VIPS_UNARY(im_asintra);
896
+ }
897
+
898
+ /*
899
+ * call-seq:
900
+ * im.acos -> image
901
+ *
902
+ * For each pixel, calculate the arc or inverse cosine. Angles are expressed in
903
+ * degrees. The output type is float, unless the input is double, in which case
904
+ * the output is double. Non-complex images only.
905
+ */
906
+
907
+ VALUE
908
+ img_acos(VALUE obj)
909
+ {
910
+ RUBY_VIPS_UNARY(im_acostra);
911
+ }
912
+
913
+ /*
914
+ * call-seq:
915
+ * im.atan -> image
916
+ *
917
+ * For each pixel, calculate the arc or inverse tangent. Angles are expressed
918
+ * in degrees. The output type is float, unless the input is double, in which
919
+ * case the output is double. Non-complex images only.
920
+ */
921
+
922
+ VALUE
923
+ img_atan(VALUE obj)
924
+ {
925
+ RUBY_VIPS_UNARY(im_atantra);
926
+ }
927
+
928
+ /*
929
+ * call-seq:
930
+ * im.cross_phase(other_image) -> image
931
+ *
932
+ * Find the phase of the cross power spectrum of two complex images, expressed
933
+ * as a complex image where the modulus of each pixel is one.
934
+ */
935
+
936
+ VALUE
937
+ img_cross_phase(VALUE obj, VALUE obj2)
938
+ {
939
+ RUBY_VIPS_BINARY(im_cross_phase);
940
+ }