212
# Define some useful macros. Macros of the CImg Library are prefixed by 'cimg_'
213
# Documented macros below may be safely used in your own code
214
# (particularly useful for option parsing, image loops and neighborhoods).
219
// Macros used to describe the program usage, and retrieve command line arguments
220
// (See corresponding module 'Retrieving command line arguments' in the generated documentation).
357
// Check if min/max macros are defined.
359
// CImg does not compile if macros 'min' or 'max' are defined,
360
// because min() and max() functions are also defined in the cimg:: namespace.
361
// so it '#undef' these macros if necessary, and restore them to reasonable
362
// values at the end of the file.
366
#define _cimg_redefine_min
370
#define _cimg_redefine_max
373
// Set the current working directory for native MacOSX bundled applications.
375
// By default, MacOS bundled applications set the cwd at the root directory '/',
376
// the code below allows to set it to the current exec directory instead when
377
// a CImg-based program is executed.
379
#if cimg_OS==1 && cimg_display==3
380
static struct _cimg_macosx_setcwd {
381
_cimg_macosx_setcwd() {
383
ProcessSerialNumber psn;
385
if (GetCurrentProcess(&psn)!=noErr) return;
386
if (GetProcessBundleLocation(&psn,&location)!=noErr) return;
387
FSRefMakePath(&location,(UInt8*)filePath,sizeof(filePath)-1);
388
int p = strlen(filePath);
389
while (filePath[p] != '/') --p;
393
} cimg_macosx_setcwd;
396
/*------------------------------------------------------------------------------
398
# Define user-friendly macros.
400
# User macros are prefixed by 'cimg_' and can be used in your own code.
401
# They are particularly useful for option parsing, and image loops creation.
403
------------------------------------------------------------------------------*/
405
// Define the program usage, and retrieve command line arguments.
221
407
#define cimg_usage(usage) cimg_library::cimg::option((char*)0,argc,argv,(char*)0,usage)
222
408
#define cimg_help(str) cimg_library::cimg::option((char*)0,argc,argv,str,(char*)0)
223
409
#define cimg_option(name,defaut,usage) cimg_library::cimg::option(name,argc,argv,defaut,usage)
225
// Macros used for neighborhood definitions and manipulations.
226
// (see module 'Using Image Loops' in the generated documentation).
227
#define CImg_2(I,T) T I##cc,I##nc=0
228
#define CImg_2x2(I,T) T I##cc,I##nc=0,I##cn,I##nn=0
229
#define CImg_3(I,T) T I##pp,I##cp,I##np=0
230
#define CImg_3x3(I,T) T I##pp,I##cp,I##np=0,I##pc,I##cc,I##nc=0,I##pn,I##cn,I##nn=0
231
#define CImg_4(I,T) T I##pp,I##cp,I##np=0,I##ap=0
232
#define CImg_4x4(I,T) T I##pp,I##cp,I##np=0,I##ap=0, \
233
I##pc,I##cc,I##nc=0,I##ac=0, \
234
I##pn,I##cn,I##nn=0,I##an=0, \
235
I##pa,I##ca,I##na=0,I##aa=0
236
#define CImg_5(I,T) T I##bb,I##pb,I##cb,I##nb=0,I##ab=0
237
#define CImg_5x5(I,T) T I##bb,I##pb,I##cb,I##nb=0,I##ab=0, \
238
I##bp,I##pp,I##cp,I##np=0,I##ap=0, \
239
I##bc,I##pc,I##cc,I##nc=0,I##ac=0, \
240
I##bn,I##pn,I##cn,I##nn=0,I##an=0, \
241
I##ba,I##pa,I##ca,I##na=0,I##aa=0
242
#define CImg_2x2x2(I,T) T I##ccc,I##ncc=0,I##cnc,I##nnc=0, \
243
I##ccn,I##ncn=0,I##cnn,I##nnn=0
244
#define CImg_3x3x3(I,T) T I##ppp,I##cpp,I##npp=0,I##pcp,I##ccp,I##ncp=0,I##pnp,I##cnp,I##nnp=0, \
245
I##ppc,I##cpc,I##npc=0,I##pcc,I##ccc,I##ncc=0,I##pnc,I##cnc,I##nnc=0, \
246
I##ppn,I##cpn,I##npn=0,I##pcn,I##ccn,I##ncn=0,I##pnn,I##cnn,I##nnn=0
248
#define CImg_2x2_ref(I,T,tab) T &I##cc=(tab)[0],&I##nc=(tab)[1],&I##cn=(tab)[2],&I##nn=(tab)[3]
249
#define CImg_3x3_ref(I,T,tab) T &I##pp=(tab)[0],&I##cp=(tab)[1],&I##np=(tab)[2], \
250
&I##pc=(tab)[3],&I##cc=(tab)[4],&I##nc=(tab)[5], \
251
&I##pn=(tab)[6],&I##cn=(tab)[7],&I##nn=(tab)[8]
252
#define CImg_4x4_ref(I,T,tab) T &I##pp=(tab)[0], &I##cp=(tab)[1], &I##np=(tab)[2], &I##ap=(tab)[3], \
253
&I##pc=(tab)[4], &I##cc=(tab)[5], &I##nc=(tab)[6], &I##ac=(tab)[7], \
254
&I##pn=(tab)[8], &I##cn=(tab)[9], &I##nn=(tab)[10],&I##an=(tab)[11], \
255
&I##pa=(tab)[12],&I##ca=(tab)[13],&I##na=(tab)[14],&I##aa=(tab)[15]
256
#define CImg_5x5_ref(I,T,tab) T &I##bb=(tab)[0],&I##pb=(tab)[1],&I##cb=(tab)[2],&I##nb=(tab)[3],&I##ab=(tab)[4], \
257
&I##bp=(tab)[5],&I##pp=(tab)[6],&I##cp=(tab)[7],&I##np=(tab)[8],&I##ap=(tab)[9], \
258
&I##bc=(tab)[10],&I##pc=(tab)[11],&I##cc=(tab)[12],&I##nc=(tab)[13],&I##ac=(tab)[14], \
259
&I##bn=(tab)[15],&I##pn=(tab)[16],&I##cn=(tab)[17],&I##nn=(tab)[18],&I##an=(tab)[19], \
260
&I##ba=(tab)[20],&I##pa=(tab)[21],&I##ca=(tab)[22],&I##na=(tab)[23],&I##aa=(tab)[24]
261
#define CImg_2x2x2_ref(I,T,tab) T &I##ccc=(tab)[0],&I##ncc=(tab)[1],&I##cnc=(tab)[2],&I##nnc=(tab)[3], \
262
&I##ccn=(tab)[4],&I##ncn=(tab)[5],&I##cnn=(tab)[6],&I##nnn=(tab)[7]
263
#define CImg_3x3x3_ref(I,T,tab) T &I##ppp=(tab)[0],&I##cpp=(tab)[1],&I##npp=(tab)[2], \
264
&I##pcp=(tab)[3],&I##ccp=(tab)[4],&I##ncp=(tab)[5], \
265
&I##pnp=(tab)[6],&I##cnp=(tab)[7],&I##nnp=(tab)[8], \
266
&I##ppc=(tab)[9],&I##cpc=(tab)[10],&I##npc=(tab)[11], \
267
&I##pcc=(tab)[12],&I##ccc=(tab)[13],&I##ncc=(tab)[14], \
268
&I##pnc=(tab)[15],&I##cnc=(tab)[16],&I##nnc=(tab)[17], \
269
&I##ppn=(tab)[18],&I##cpn=(tab)[19],&I##npn=(tab)[20], \
270
&I##pcn=(tab)[21],&I##ccn=(tab)[22],&I##ncn=(tab)[23], \
271
&I##pnn=(tab)[24],&I##cnn=(tab)[25],&I##nnn=(tab)[26]
273
#define cimg_copy2x2(J,I) I##cc=J##cc, I##nc=J##nc, I##cn=J##cn, I##nn=J##nn
274
#define cimg_copy3x3(J,I) I##pp=J##pp, I##cp=J##cp, I##np=J##np, \
275
I##pc=J##pc, I##cc=J##cc, I##nc=J##nc, \
276
I##pn=J##pn, I##cn=J##cn, I##nn=J##nn
277
#define cimg_copy5x5(J,I) I##bb=J##bb, I##pb=J##pb, I##cb=J##cb, I##nb=J##nb, I##ab=J##ab, \
278
I##bp=J##bp, I##pp=J##pp, I##cp=J##cp, I##np=J##np, I##ap=J##ap, \
279
I##bc=J##bc, I##pc=J##pc, I##cc=J##cc, I##nc=J##nc, I##ac=J##ac, \
280
I##bn=J##bn, I##pn=J##pn, I##cn=J##cn, I##nn=J##nn, I##an=J##an, \
281
I##ba=J##ba, I##pa=J##pa, I##ca=J##ca, I##na=J##na, I##aa=J##aa
283
#define cimg_squaresum2x2(I) ( I##cc*I##cc + I##nc*I##nc + I##cn*I##cn + I##nn*I##nn )
284
#define cimg_squaresum3x3(I) ( I##pp*I##pp + I##cp*I##cp + I##np*I##np + \
285
I##pc*I##pc + I##cc*I##cc + I##nc*I##nc + \
286
I##pn*I##pn + I##cn*I##cn + I##nn*I##nn )
287
#define cimg_squaresum4x4(I) ( I##pp*I##pp + I##cp*I##cp + I##np*I##np + I##ap*I##ap + \
288
I##pc*I##pc + I##cc*I##cc + I##nc*I##nc + I##ac*I##ac + \
289
I##pn*I##pn + I##cn*I##cn + I##nn*I##nn + I##an*I##an + \
290
I##pa*I##pa + I##ca*I##ca + I##na*I##na + I##aa*I##aa )
291
#define cimg_squaresum5x5(I) ( I##bb*I##bb + I##pb*I##pb + I##cb*I##cb + I##nb*I##nb + I##ab*I##ab + \
292
I##bp*I##bp + I##pp*I##pp + I##cp*I##cp + I##np*I##np + I##ap*I##ap + \
293
I##bc*I##bc + I##pc*I##pc + I##cc*I##cc + I##nc*I##nc + I##ac*I##ac + \
294
I##bn*I##bn + I##pn*I##pn + I##cn*I##cn + I##nn*I##nn + I##an*I##an + \
295
I##ba*I##ba + I##pa*I##pa + I##ca*I##ca + I##na*I##na + I##aa*I##aa )
296
#define cimg_squaresum2x2x2(I) ( I##ccc*I##ccc + I##ncc*I##ncc + I##cnc*I##cnc + I##nnc*I##nnc + \
297
I##ccn*I##ccn + I##ncn*I##ncn + I##cnn*I##cnn + I##nnn*I##nnn )
298
#define cimg_squaresum3x3x3(I) ( I##ppp*I##ppp + I##cpp*I##cpp + I##npp*I##npp + \
299
I##pcp*I##pcp + I##ccp*I##ccp + I##ncp*I##ncp + \
300
I##pnp*I##pnp + I##cnp*I##cnp + I##nnp*I##nnp + \
301
I##ppc*I##ppc + I##cpc*I##cpc + I##npc*I##npc + \
302
I##pcc*I##pcc + I##ccc*I##ccc + I##ncc*I##ncc + \
303
I##pnc*I##pnc + I##cnc*I##cnc + I##nnc*I##nnc + \
304
I##ppn*I##ppn + I##cpn*I##cpn + I##npn*I##npn + \
305
I##pcn*I##pcn + I##ccn*I##ccn + I##ncn*I##ncn + \
306
I##pnn*I##pnn + I##cnn*I##cnn + I##nnn*I##nnn )
308
#define cimg_corr2x2(I,m) ( I##cc*(m)(0,0)+I##nc*(m)(1,0)+I##cn*(m)(0,1)+I##nn*(m)(1,1) )
309
#define cimg_corr3x3(I,m) ( I##pp*(m)(0,0)+I##cp*(m)(1,0)+I##np*(m)(2,0) + \
310
I##pc*(m)(0,1)+I##cc*(m)(1,1)+I##nc*(m)(2,1) + \
311
I##pn*(m)(0,2)+I##cn*(m)(1,2)+I##nn*(m)(2,2) )
312
#define cimg_corr4x4(I,m) ( I##pp*(m)(0,0)+I##cp*(m)(1,0)+I##np*(m)(2,0)+I##ap*(m)(3,0) + \
313
I##pc*(m)(0,1)+I##cc*(m)(1,1)+I##nc*(m)(2,1)+I##ac*(m)(3,1) + \
314
I##pn*(m)(0,2)+I##cn*(m)(1,2)+I##nn*(m)(2,2)+I##an*(m)(3,2) + \
315
I##pa*(m)(0,3)+I##ca*(m)(1,3)+I##na*(m)(2,3)+I##aa*(m)(3,3) )
316
#define cimg_corr5x5(I,m) ( I##bb*(m)(0,0)+I##pb*(m)(1,0)+I##cb*(m)(2,0)+I##nb*(m)(3,0)+I##ab*(m)(4,0) + \
317
I##bp*(m)(0,1)+I##pp*(m)(1,1)+I##cp*(m)(2,1)+I##np*(m)(3,1)+I##ap*(m)(4,1) + \
318
I##bc*(m)(0,2)+I##pc*(m)(1,2)+I##cc*(m)(2,2)+I##nc*(m)(3,2)+I##ac*(m)(4,2) + \
319
I##bn*(m)(0,3)+I##pn*(m)(1,3)+I##cn*(m)(2,3)+I##nn*(m)(3,3)+I##an*(m)(4,3) + \
320
I##ba*(m)(0,4)+I##pa*(m)(1,4)+I##ca*(m)(2,4)+I##na*(m)(3,4)+I##aa*(m)(4,4) )
321
#define cimg_corr2x2x2(I,m) ( I##ccc*(m)(0,0,0)+I##ncc*(m)(1,0,0)+I##cnc*(m)(0,1,0)+I##nnc*(m)(1,1,0) + \
322
I##ccn*(m)(0,0,1)+I##ncn*(m)(1,0,1)+I##cnn*(m)(0,1,1)+I##nnn*(m)(1,1,1) )
323
#define cimg_corr3x3x3(I,m) ( I##ppp*(m)(0,0,0)+I##cpp*(m)(1,0,0)+I##npp*(m)(2,0,0) + \
324
I##pcp*(m)(0,1,0)+I##ccp*(m)(1,1,0)+I##ncp*(m)(2,1,0) + \
325
I##pnp*(m)(0,2,0)+I##cnp*(m)(1,2,0)+I##nnp*(m)(2,2,0) + \
326
I##ppc*(m)(0,0,1)+I##cpc*(m)(1,0,1)+I##npc*(m)(2,0,1) + \
327
I##pcc*(m)(0,1,1)+I##ccc*(m)(1,1,1)+I##ncc*(m)(2,1,1) + \
328
I##pnc*(m)(0,2,1)+I##cnc*(m)(1,2,1)+I##nnc*(m)(2,2,1) + \
329
I##ppn*(m)(0,0,2)+I##cpn*(m)(1,0,2)+I##npn*(m)(2,0,2) + \
330
I##pcn*(m)(0,1,2)+I##ccn*(m)(1,1,2)+I##ncn*(m)(2,1,2) + \
331
I##pnn*(m)(0,2,2)+I##cnn*(m)(1,2,2)+I##nnn*(m)(2,2,2) )
333
#define cimg_conv2x2(I,m) ( I##cc*(m)(1,1)+I##nc*(m)(0,1)+I##cn*(m)(1,0)+I##nn*(m)(0,0) )
334
#define cimg_conv3x3(I,m) ( I##pp*(m)(2,2)+I##cp*(m)(1,2)+I##np*(m)(0,2) + \
335
I##pc*(m)(2,1)+I##cc*(m)(1,1)+I##nc*(m)(0,1) + \
336
I##pn*(m)(2,0)+I##cn*(m)(1,0)+I##nn*(m)(0,0) )
337
#define cimg_conv4x4(I,m) ( I##pp*(m)(3,3)+I##cp*(m)(2,3)+I##np*(m)(1,3)+I##ap*(m)(0,3) + \
338
I##pc*(m)(3,2)+I##cc*(m)(2,2)+I##nc*(m)(1,2)+I##ac*(m)(0,2) + \
339
I##pn*(m)(3,1)+I##cn*(m)(2,1)+I##nn*(m)(1,1)+I##an*(m)(0,1) + \
340
I##pa*(m)(3,0)+I##ca*(m)(2,0)+I##na*(m)(1,0)+I##aa*(m)(0,0) )
341
#define cimg_conv5x5(I,m) ( I##bb*(m)(4,4)+I##pb*(m)(3,4)+I##cb*(m)(2,4)+I##nb*(m)(1,4)+I##ab*(m)(0,4) + \
342
I##bp*(m)(4,3)+I##pp*(m)(3,3)+I##cp*(m)(2,3)+I##np*(m)(1,3)+I##ap*(m)(0,3) + \
343
I##bc*(m)(4,2)+I##pc*(m)(3,2)+I##cc*(m)(2,2)+I##nc*(m)(1,2)+I##ac*(m)(0,2) + \
344
I##bn*(m)(4,1)+I##pn*(m)(3,1)+I##cn*(m)(2,1)+I##nn*(m)(1,1)+I##an*(m)(0,1) + \
345
I##ba*(m)(4,0)+I##pa*(m)(3,0)+I##ca*(m)(2,0)+I##na*(m)(1,0)+I##aa*(m)(0,0) )
346
#define cimg_conv2x2x2(I,m) ( I##ccc*(m)(1,1,1)+I##ncc*(m)(0,1,1)+I##cnc*(m)(1,0,1)+I##nnc*(m)(0,0,1) + \
347
I##ccn*(m)(1,1,0)+I##ncn*(m)(0,1,0)+I##cnn*(m)(1,0,0)+I##nnn*(m)(0,0,0) )
348
#define cimg_conv3x3x3(I,m) ( I##ppp*(m)(2,2,2)+I##cpp*(m)(1,2,2)+I##npp*(m)(0,2,2) + \
349
I##pcp*(m)(2,1,2)+I##ccp*(m)(1,1,2)+I##ncp*(m)(0,1,2) + \
350
I##pnp*(m)(2,0,2)+I##cnp*(m)(1,0,2)+I##nnp*(m)(0,0,2) + \
351
I##ppc*(m)(2,2,1)+I##cpc*(m)(1,2,1)+I##npc*(m)(0,2,1) + \
352
I##pcc*(m)(2,1,1)+I##ccc*(m)(1,1,1)+I##ncc*(m)(0,1,1) + \
353
I##pnc*(m)(2,0,1)+I##cnc*(m)(1,0,1)+I##nnc*(m)(0,0,1) + \
354
I##ppn*(m)(2,2,0)+I##cpn*(m)(1,2,0)+I##npn*(m)(0,2,0) + \
355
I##pcn*(m)(2,1,0)+I##ccn*(m)(1,1,0)+I##ncn*(m)(0,1,0) + \
356
I##pnn*(m)(2,0,0)+I##cnn*(m)(1,0,0)+I##nnn*(m)(0,0,0) )
410
#define cimg_argument(pos) cimg_library::cimg::argument(pos,argc,argv)
411
#define cimg_argument1(pos,s0) cimg_library::cimg::argument(pos,argc,argv,1,s0)
412
#define cimg_argument2(pos,s0,s1) cimg_library::cimg::argument(pos,argc,argv,2,s0,s1)
413
#define cimg_argument3(pos,s0,s1,s2) cimg_library::cimg::argument(pos,argc,argv,3,s0,s1,s2)
414
#define cimg_argument4(pos,s0,s1,s2,s3) cimg_library::cimg::argument(pos,argc,argv,4,s0,s1,s2,s3)
415
#define cimg_argument5(pos,s0,s1,s2,s3,s4) cimg_library::cimg::argument(pos,argc,argv,5,s0,s1,s2,s3,s4)
416
#define cimg_argument6(pos,s0,s1,s2,s3,s4,s5) cimg_library::cimg::argument(pos,argc,argv,6,s0,s1,s2,s3,s4,s5)
417
#define cimg_argument7(pos,s0,s1,s2,s3,s4,s5,s6) cimg_library::cimg::argument(pos,argc,argv,7,s0,s1,s2,s3,s4,s5,s6)
418
#define cimg_argument8(pos,s0,s1,s2,s3,s4,s5,s6,s7) cimg_library::cimg::argument(pos,argc,argv,8,s0,s1,s2,s3,s4,s5,s6,s7)
419
#define cimg_argument9(pos,s0,s1,s2,s3,s4,s5,s6,s7,s8) cimg_library::cimg::argument(pos,argc,argv,9,s0,s1,s2,s3,s4,s5,s6,s7,s8)
421
// Define and manipulate local neighborhoods.
423
#define CImg_2x2(I,T) T I[4]; \
424
T& I##cc = I[0]; T& I##nc = I[1]; \
425
T& I##cn = I[2]; T& I##nn = I[3]; \
429
#define CImg_3x3(I,T) T I[9]; \
430
T& I##pp = I[0]; T& I##cp = I[1]; T& I##np = I[2]; \
431
T& I##pc = I[3]; T& I##cc = I[4]; T& I##nc = I[5]; \
432
T& I##pn = I[6]; T& I##cn = I[7]; T& I##nn = I[8]; \
433
I##pp = I##cp = I##np = \
434
I##pc = I##cc = I##nc = \
435
I##pn = I##cn = I##nn = 0
437
#define CImg_4x4(I,T) T I[16]; \
438
T& I##pp = I[0]; T& I##cp = I[1]; T& I##np = I[2]; T& I##ap = I[3]; \
439
T& I##pc = I[4]; T& I##cc = I[5]; T& I##nc = I[6]; T& I##ac = I[7]; \
440
T& I##pn = I[8]; T& I##cn = I[9]; T& I##nn = I[10]; T& I##an = I[11]; \
441
T& I##pa = I[12]; T& I##ca = I[13]; T& I##na = I[14]; T& I##aa = I[15]; \
442
I##pp = I##cp = I##np = I##ap = \
443
I##pc = I##cc = I##nc = I##ac = \
444
I##pn = I##cn = I##nn = I##an = \
445
I##pa = I##ca = I##na = I##aa = 0
447
#define CImg_5x5(I,T) T I[25]; \
448
T& I##bb = I[0]; T& I##pb = I[1]; T& I##cb = I[2]; T& I##nb = I[3]; T& I##ab = I[4]; \
449
T& I##bp = I[5]; T& I##pp = I[6]; T& I##cp = I[7]; T& I##np = I[8]; T& I##ap = I[9]; \
450
T& I##bc = I[10]; T& I##pc = I[11]; T& I##cc = I[12]; T& I##nc = I[13]; T& I##ac = I[14]; \
451
T& I##bn = I[15]; T& I##pn = I[16]; T& I##cn = I[17]; T& I##nn = I[18]; T& I##an = I[19]; \
452
T& I##ba = I[20]; T& I##pa = I[21]; T& I##ca = I[22]; T& I##na = I[23]; T& I##aa = I[24]; \
453
I##bb = I##pb = I##cb = I##nb = I##ab = \
454
I##bp = I##pp = I##cp = I##np = I##ap = \
455
I##bc = I##pc = I##cc = I##nc = I##ac = \
456
I##bn = I##pn = I##cn = I##nn = I##an = \
457
I##ba = I##pa = I##ca = I##na = I##aa = 0
459
#define CImg_2x2x2(I,T) T I[8]; \
460
T& I##ccc = I[0]; T& I##ncc = I[1]; \
461
T& I##cnc = I[2]; T& I##nnc = I[3]; \
462
T& I##ccn = I[4]; T& I##ncn = I[5]; \
463
T& I##cnn = I[6]; T& I##nnn = I[7]; \
469
#define CImg_3x3x3(I,T) T I[27]; \
470
T& I##ppp = I[0]; T& I##cpp = I[1]; T& I##npp = I[2]; \
471
T& I##pcp = I[3]; T& I##ccp = I[4]; T& I##ncp = I[5]; \
472
T& I##pnp = I[6]; T& I##cnp = I[7]; T& I##nnp = I[8]; \
473
T& I##ppc = I[9]; T& I##cpc = I[10]; T& I##npc = I[11]; \
474
T& I##pcc = I[12]; T& I##ccc = I[13]; T& I##ncc = I[14]; \
475
T& I##pnc = I[15]; T& I##cnc = I[16]; T& I##nnc = I[17]; \
476
T& I##ppn = I[18]; T& I##cpn = I[19]; T& I##npn = I[20]; \
477
T& I##pcn = I[21]; T& I##ccn = I[22]; T& I##ncn = I[23]; \
478
T& I##pnn = I[24]; T& I##cnn = I[25]; T& I##nnn = I[26]; \
479
I##ppp = I##cpp = I##npp = \
480
I##pcp = I##ccp = I##ncp = \
481
I##pnp = I##cnp = I##nnp = \
482
I##ppc = I##cpc = I##npc = \
483
I##pcc = I##ccc = I##ncc = \
484
I##pnc = I##cnc = I##nnc = \
485
I##ppn = I##cpn = I##npn = \
486
I##pcn = I##ccn = I##ncn = \
487
I##pnn = I##cnn = I##nnn = 0
358
489
#define cimg_get2x2(img,x,y,z,v,I) \
359
I##cc=(img)(x, y,z,v), I##nc=(img)(_n##x, y,z,v), \
360
I##cn=(img)(x,_n##y,z,v), I##nn=(img)(_n##x,_n##y,z,v)
490
I[0] = (img)(x,y,z,v), I[1] = (img)(_n1##x,y,z,v), I[2] = (img)(x,_n1##y,z,v), I[3] = (img)(_n1##x,_n1##y,z,v)
361
492
#define cimg_get3x3(img,x,y,z,v,I) \
362
I##pp=(img)(_p##x,_p##y,z,v), I##cp=(img)(x,_p##y,z,v), I##np=(img)(_n##x,_p##y,z,v), \
363
I##pc=(img)(_p##x, y,z,v), I##cc=(img)(x, y,z,v), I##nc=(img)(_n##x, y,z,v), \
364
I##pn=(img)(_p##x,_n##y,z,v), I##cn=(img)(x,_n##y,z,v), I##nn=(img)(_n##x,_n##y,z,v)
493
I[0] = (img)(_p1##x,_p1##y,z,v), I[1] = (img)(x,_p1##y,z,v), I[2] = (img)(_n1##x,_p1##y,z,v), I[3] = (img)(_p1##x,y,z,v), \
494
I[4] = (img)(x,y,z,v), I[5] = (img)(_n1##x,y,z,v), I[6] = (img)(_p1##x,_n1##y,z,v), I[7] = (img)(x,_n1##y,z,v), \
495
I[8] = (img)(_n1##x,_n1##y,z,v)
365
497
#define cimg_get4x4(img,x,y,z,v,I) \
366
I##pp=(img)(_p##x,_p##y,z,v), I##cp=(img)(x,_p##y,z,v), I##np=(img)(_n##x,_p##y,z,v), I##ap=(img)(_a##x,_p##y,z,v), \
367
I##pc=(img)(_p##x, y,z,v), I##cc=(img)(x, y,z,v), I##nc=(img)(_n##x, y,z,v), I##ac=(img)(_a##x, y,z,v), \
368
I##pn=(img)(_p##x,_n##y,z,v), I##cn=(img)(x,_n##y,z,v), I##nn=(img)(_n##x,_n##y,z,v), I##an=(img)(_a##x,_n##y,z,v), \
369
I##pa=(img)(_p##x,_a##y,z,v), I##ca=(img)(x,_a##y,z,v), I##na=(img)(_n##x,_a##y,z,v), I##aa=(img)(_a##x,_a##y,z,v)
498
I[0] = (img)(_p1##x,_p1##y,z,v), I[1] = (img)(x,_p1##y,z,v), I[2] = (img)(_n1##x,_p1##y,z,v), I[3] = (img)(_n2##x,_p1##y,z,v), \
499
I[4] = (img)(_p1##x,y,z,v), I[5] = (img)(x,y,z,v), I[6] = (img)(_n1##x,y,z,v), I[7] = (img)(_n2##x,y,z,v), \
500
I[8] = (img)(_p1##x,_n1##y,z,v), I[9] = (img)(x,_n1##y,z,v), I[10] = (img)(_n1##x,_n1##y,z,v), I[11] = (img)(_n2##x,_n1##y,z,v), \
501
I[12] = (img)(_p1##x,_n2##y,z,v), I[13] = (img)(x,_n2##y,z,v), I[14] = (img)(_n1##x,_n2##y,z,v), I[15] = (img)(_n2##x,_n2##y,z,v)
370
503
#define cimg_get5x5(img,x,y,z,v,I) \
371
I##bb=(img)(_b##x,_b##y,z,v), I##pb=(img)(_p##x,_b##y,z,v), I##cb=(img)(x,_b##y,z,v), I##nb=(img)(_n##x,_b##y,z,v), I##ab=(img)(_a##x,_b##y,z,v), \
372
I##bp=(img)(_b##x,_p##y,z,v), I##pp=(img)(_p##x,_p##y,z,v), I##cp=(img)(x,_p##y,z,v), I##np=(img)(_n##x,_p##y,z,v), I##ap=(img)(_a##x,_p##y,z,v), \
373
I##bc=(img)(_b##x, y,z,v), I##pc=(img)(_p##x, y,z,v), I##cc=(img)(x, y,z,v), I##nc=(img)(_n##x, y,z,v), I##ac=(img)(_a##x, y,z,v), \
374
I##bn=(img)(_b##x,_n##y,z,v), I##pn=(img)(_p##x,_n##y,z,v), I##cn=(img)(x,_n##y,z,v), I##nn=(img)(_n##x,_n##y,z,v), I##an=(img)(_a##x,_n##y,z,v), \
375
I##ba=(img)(_b##x,_a##y,z,v), I##pa=(img)(_p##x,_a##y,z,v), I##ca=(img)(x,_a##y,z,v), I##na=(img)(_n##x,_a##y,z,v), I##aa=(img)(_a##x,_a##y,z,v)
504
I[0] = (img)(_p2##x,_p2##y,z,v), I[1] = (img)(_p1##x,_p2##y,z,v), I[2] = (img)(x,_p2##y,z,v), I[3] = (img)(_n1##x,_p2##y,z,v), \
505
I[4] = (img)(_n2##x,_p2##y,z,v), I[5] = (img)(_p2##x,_p1##y,z,v), I[6] = (img)(_p1##x,_p1##y,z,v), I[7] = (img)(x,_p1##y,z,v), \
506
I[8] = (img)(_n1##x,_p1##y,z,v), I[9] = (img)(_n2##x,_p1##y,z,v), I[10] = (img)(_p2##x,y,z,v), I[11] = (img)(_p1##x,y,z,v), \
507
I[12] = (img)(x,y,z,v), I[13] = (img)(_n1##x,y,z,v), I[14] = (img)(_n2##x,y,z,v), I[15] = (img)(_p2##x,_n1##y,z,v), \
508
I[16] = (img)(_p1##x,_n1##y,z,v), I[17] = (img)(x,_n1##y,z,v), I[18] = (img)(_n1##x,_n1##y,z,v), I[19] = (img)(_n2##x,_n1##y,z,v), \
509
I[20] = (img)(_p2##x,_n2##y,z,v), I[21] = (img)(_p1##x,_n2##y,z,v), I[22] = (img)(x,_n2##y,z,v), I[23] = (img)(_n1##x,_n2##y,z,v), \
510
I[24] = (img)(_n2##x,_n2##y,z,v)
512
#define cimg_get6x6(img,x,y,z,v,I) \
513
I[0] = (img)(_p2##x,_p2##y,z,v), I[1] = (img)(_p1##x,_p2##y,z,v), I[2] = (img)(x,_p2##y,z,v), I[3] = (img)(_n1##x,_p2##y,z,v), \
514
I[4] = (img)(_n2##x,_p2##y,z,v), I[5] = (img)(_n3##x,_p2##y,z,v), I[6] = (img)(_p2##x,_p1##y,z,v), I[7] = (img)(_p1##x,_p1##y,z,v), \
515
I[8] = (img)(x,_p1##y,z,v), I[9] = (img)(_n1##x,_p1##y,z,v), I[10] = (img)(_n2##x,_p1##y,z,v), I[11] = (img)(_n3##x,_p1##y,z,v), \
516
I[12] = (img)(_p2##x,y,z,v), I[13] = (img)(_p1##x,y,z,v), I[14] = (img)(x,y,z,v), I[15] = (img)(_n1##x,y,z,v), \
517
I[16] = (img)(_n2##x,y,z,v), I[17] = (img)(_n3##x,y,z,v), I[18] = (img)(_p2##x,_n1##y,z,v), I[19] = (img)(_p1##x,_n1##y,z,v), \
518
I[20] = (img)(x,_n1##y,z,v), I[21] = (img)(_n1##x,_n1##y,z,v), I[22] = (img)(_n2##x,_n1##y,z,v), I[23] = (img)(_n3##x,_n1##y,z,v), \
519
I[24] = (img)(_p2##x,_n2##y,z,v), I[25] = (img)(_p1##x,_n2##y,z,v), I[26] = (img)(x,_n2##y,z,v), I[27] = (img)(_n1##x,_n2##y,z,v), \
520
I[28] = (img)(_n2##x,_n2##y,z,v), I[29] = (img)(_n3##x,_n2##y,z,v), I[30] = (img)(_p2##x,_n3##y,z,v), I[31] = (img)(_p1##x,_n3##y,z,v), \
521
I[32] = (img)(x,_n3##y,z,v), I[33] = (img)(_n1##x,_n3##y,z,v), I[34] = (img)(_n2##x,_n3##y,z,v), I[35] = (img)(_n3##x,_n3##y,z,v)
523
#define cimg_get7x7(img,x,y,z,v,I) \
524
I[0] = (img)(_p3##x,_p3##y,z,v), I[1] = (img)(_p2##x,_p3##y,z,v), I[2] = (img)(_p1##x,_p3##y,z,v), I[3] = (img)(x,_p3##y,z,v), \
525
I[4] = (img)(_n1##x,_p3##y,z,v), I[5] = (img)(_n2##x,_p3##y,z,v), I[6] = (img)(_n3##x,_p3##y,z,v), I[7] = (img)(_p3##x,_p2##y,z,v), \
526
I[8] = (img)(_p2##x,_p2##y,z,v), I[9] = (img)(_p1##x,_p2##y,z,v), I[10] = (img)(x,_p2##y,z,v), I[11] = (img)(_n1##x,_p2##y,z,v), \
527
I[12] = (img)(_n2##x,_p2##y,z,v), I[13] = (img)(_n3##x,_p2##y,z,v), I[14] = (img)(_p3##x,_p1##y,z,v), I[15] = (img)(_p2##x,_p1##y,z,v), \
528
I[16] = (img)(_p1##x,_p1##y,z,v), I[17] = (img)(x,_p1##y,z,v), I[18] = (img)(_n1##x,_p1##y,z,v), I[19] = (img)(_n2##x,_p1##y,z,v), \
529
I[20] = (img)(_n3##x,_p1##y,z,v), I[21] = (img)(_p3##x,y,z,v), I[22] = (img)(_p2##x,y,z,v), I[23] = (img)(_p1##x,y,z,v), \
530
I[24] = (img)(x,y,z,v), I[25] = (img)(_n1##x,y,z,v), I[26] = (img)(_n2##x,y,z,v), I[27] = (img)(_n3##x,y,z,v), \
531
I[28] = (img)(_p3##x,_n1##y,z,v), I[29] = (img)(_p2##x,_n1##y,z,v), I[30] = (img)(_p1##x,_n1##y,z,v), I[31] = (img)(x,_n1##y,z,v), \
532
I[32] = (img)(_n1##x,_n1##y,z,v), I[33] = (img)(_n2##x,_n1##y,z,v), I[34] = (img)(_n3##x,_n1##y,z,v), I[35] = (img)(_p3##x,_n2##y,z,v), \
533
I[36] = (img)(_p2##x,_n2##y,z,v), I[37] = (img)(_p1##x,_n2##y,z,v), I[38] = (img)(x,_n2##y,z,v), I[39] = (img)(_n1##x,_n2##y,z,v), \
534
I[40] = (img)(_n2##x,_n2##y,z,v), I[41] = (img)(_n3##x,_n2##y,z,v), I[42] = (img)(_p3##x,_n3##y,z,v), I[43] = (img)(_p2##x,_n3##y,z,v), \
535
I[44] = (img)(_p1##x,_n3##y,z,v), I[45] = (img)(x,_n3##y,z,v), I[46] = (img)(_n1##x,_n3##y,z,v), I[47] = (img)(_n2##x,_n3##y,z,v), \
536
I[48] = (img)(_n3##x,_n3##y,z,v)
538
#define cimg_get8x8(img,x,y,z,v,I) \
539
I[0] = (img)(_p3##x,_p3##y,z,v), I[1] = (img)(_p2##x,_p3##y,z,v), I[2] = (img)(_p1##x,_p3##y,z,v), I[3] = (img)(x,_p3##y,z,v), \
540
I[4] = (img)(_n1##x,_p3##y,z,v), I[5] = (img)(_n2##x,_p3##y,z,v), I[6] = (img)(_n3##x,_p3##y,z,v), I[7] = (img)(_n4##x,_p3##y,z,v), \
541
I[8] = (img)(_p3##x,_p2##y,z,v), I[9] = (img)(_p2##x,_p2##y,z,v), I[10] = (img)(_p1##x,_p2##y,z,v), I[11] = (img)(x,_p2##y,z,v), \
542
I[12] = (img)(_n1##x,_p2##y,z,v), I[13] = (img)(_n2##x,_p2##y,z,v), I[14] = (img)(_n3##x,_p2##y,z,v), I[15] = (img)(_n4##x,_p2##y,z,v), \
543
I[16] = (img)(_p3##x,_p1##y,z,v), I[17] = (img)(_p2##x,_p1##y,z,v), I[18] = (img)(_p1##x,_p1##y,z,v), I[19] = (img)(x,_p1##y,z,v), \
544
I[20] = (img)(_n1##x,_p1##y,z,v), I[21] = (img)(_n2##x,_p1##y,z,v), I[22] = (img)(_n3##x,_p1##y,z,v), I[23] = (img)(_n4##x,_p1##y,z,v), \
545
I[24] = (img)(_p3##x,y,z,v), I[25] = (img)(_p2##x,y,z,v), I[26] = (img)(_p1##x,y,z,v), I[27] = (img)(x,y,z,v), \
546
I[28] = (img)(_n1##x,y,z,v), I[29] = (img)(_n2##x,y,z,v), I[30] = (img)(_n3##x,y,z,v), I[31] = (img)(_n4##x,y,z,v), \
547
I[32] = (img)(_p3##x,_n1##y,z,v), I[33] = (img)(_p2##x,_n1##y,z,v), I[34] = (img)(_p1##x,_n1##y,z,v), I[35] = (img)(x,_n1##y,z,v), \
548
I[36] = (img)(_n1##x,_n1##y,z,v), I[37] = (img)(_n2##x,_n1##y,z,v), I[38] = (img)(_n3##x,_n1##y,z,v), I[39] = (img)(_n4##x,_n1##y,z,v), \
549
I[40] = (img)(_p3##x,_n2##y,z,v), I[41] = (img)(_p2##x,_n2##y,z,v), I[42] = (img)(_p1##x,_n2##y,z,v), I[43] = (img)(x,_n2##y,z,v), \
550
I[44] = (img)(_n1##x,_n2##y,z,v), I[45] = (img)(_n2##x,_n2##y,z,v), I[46] = (img)(_n3##x,_n2##y,z,v), I[47] = (img)(_n4##x,_n2##y,z,v), \
551
I[48] = (img)(_p3##x,_n3##y,z,v), I[49] = (img)(_p2##x,_n3##y,z,v), I[50] = (img)(_p1##x,_n3##y,z,v), I[51] = (img)(x,_n3##y,z,v), \
552
I[52] = (img)(_n1##x,_n3##y,z,v), I[53] = (img)(_n2##x,_n3##y,z,v), I[54] = (img)(_n3##x,_n3##y,z,v), I[55] = (img)(_n4##x,_n3##y,z,v), \
553
I[56] = (img)(_p3##x,_n4##y,z,v), I[57] = (img)(_p2##x,_n4##y,z,v), I[58] = (img)(_p1##x,_n4##y,z,v), I[59] = (img)(x,_n4##y,z,v), \
554
I[60] = (img)(_n1##x,_n4##y,z,v), I[61] = (img)(_n2##x,_n4##y,z,v), I[62] = (img)(_n3##x,_n4##y,z,v), I[63] = (img)(_n4##x,_n4##y,z,v);
556
#define cimg_get9x9(img,x,y,z,v,I) \
557
I[0] = (img)(_p4##x,_p4##y,z,v), I[1] = (img)(_p3##x,_p4##y,z,v), I[2] = (img)(_p2##x,_p4##y,z,v), I[3] = (img)(_p1##x,_p4##y,z,v), \
558
I[4] = (img)(x,_p4##y,z,v), I[5] = (img)(_n1##x,_p4##y,z,v), I[6] = (img)(_n2##x,_p4##y,z,v), I[7] = (img)(_n3##x,_p4##y,z,v), \
559
I[8] = (img)(_n4##x,_p4##y,z,v), I[9] = (img)(_p4##x,_p3##y,z,v), I[10] = (img)(_p3##x,_p3##y,z,v), I[11] = (img)(_p2##x,_p3##y,z,v), \
560
I[12] = (img)(_p1##x,_p3##y,z,v), I[13] = (img)(x,_p3##y,z,v), I[14] = (img)(_n1##x,_p3##y,z,v), I[15] = (img)(_n2##x,_p3##y,z,v), \
561
I[16] = (img)(_n3##x,_p3##y,z,v), I[17] = (img)(_n4##x,_p3##y,z,v), I[18] = (img)(_p4##x,_p2##y,z,v), I[19] = (img)(_p3##x,_p2##y,z,v), \
562
I[20] = (img)(_p2##x,_p2##y,z,v), I[21] = (img)(_p1##x,_p2##y,z,v), I[22] = (img)(x,_p2##y,z,v), I[23] = (img)(_n1##x,_p2##y,z,v), \
563
I[24] = (img)(_n2##x,_p2##y,z,v), I[25] = (img)(_n3##x,_p2##y,z,v), I[26] = (img)(_n4##x,_p2##y,z,v), I[27] = (img)(_p4##x,_p1##y,z,v), \
564
I[28] = (img)(_p3##x,_p1##y,z,v), I[29] = (img)(_p2##x,_p1##y,z,v), I[30] = (img)(_p1##x,_p1##y,z,v), I[31] = (img)(x,_p1##y,z,v), \
565
I[32] = (img)(_n1##x,_p1##y,z,v), I[33] = (img)(_n2##x,_p1##y,z,v), I[34] = (img)(_n3##x,_p1##y,z,v), I[35] = (img)(_n4##x,_p1##y,z,v), \
566
I[36] = (img)(_p4##x,y,z,v), I[37] = (img)(_p3##x,y,z,v), I[38] = (img)(_p2##x,y,z,v), I[39] = (img)(_p1##x,y,z,v), \
567
I[40] = (img)(x,y,z,v), I[41] = (img)(_n1##x,y,z,v), I[42] = (img)(_n2##x,y,z,v), I[43] = (img)(_n3##x,y,z,v), \
568
I[44] = (img)(_n4##x,y,z,v), I[45] = (img)(_p4##x,_n1##y,z,v), I[46] = (img)(_p3##x,_n1##y,z,v), I[47] = (img)(_p2##x,_n1##y,z,v), \
569
I[48] = (img)(_p1##x,_n1##y,z,v), I[49] = (img)(x,_n1##y,z,v), I[50] = (img)(_n1##x,_n1##y,z,v), I[51] = (img)(_n2##x,_n1##y,z,v), \
570
I[52] = (img)(_n3##x,_n1##y,z,v), I[53] = (img)(_n4##x,_n1##y,z,v), I[54] = (img)(_p4##x,_n2##y,z,v), I[55] = (img)(_p3##x,_n2##y,z,v), \
571
I[56] = (img)(_p2##x,_n2##y,z,v), I[57] = (img)(_p1##x,_n2##y,z,v), I[58] = (img)(x,_n2##y,z,v), I[59] = (img)(_n1##x,_n2##y,z,v), \
572
I[60] = (img)(_n2##x,_n2##y,z,v), I[61] = (img)(_n3##x,_n2##y,z,v), I[62] = (img)(_n4##x,_n2##y,z,v), I[63] = (img)(_p4##x,_n3##y,z,v), \
573
I[64] = (img)(_p3##x,_n3##y,z,v), I[65] = (img)(_p2##x,_n3##y,z,v), I[66] = (img)(_p1##x,_n3##y,z,v), I[67] = (img)(x,_n3##y,z,v), \
574
I[68] = (img)(_n1##x,_n3##y,z,v), I[69] = (img)(_n2##x,_n3##y,z,v), I[70] = (img)(_n3##x,_n3##y,z,v), I[71] = (img)(_n4##x,_n3##y,z,v), \
575
I[72] = (img)(_p4##x,_n4##y,z,v), I[73] = (img)(_p3##x,_n4##y,z,v), I[74] = (img)(_p2##x,_n4##y,z,v), I[75] = (img)(_p1##x,_n4##y,z,v), \
576
I[76] = (img)(x,_n4##y,z,v), I[77] = (img)(_n1##x,_n4##y,z,v), I[78] = (img)(_n2##x,_n4##y,z,v), I[79] = (img)(_n3##x,_n4##y,z,v), \
577
I[80] = (img)(_n4##x,_n4##y,z,v)
376
579
#define cimg_get2x2x2(img,x,y,z,v,I) \
377
I##ccc=(img)(x,y, z,v), I##ncc=(img)(_n##x,y, z,v), I##cnc=(img)(x,_n##y, z,v), I##nnc=(img)(_n##x,_n##y, z,v), \
378
I##ccc=(img)(x,y,_n##z,v), I##ncc=(img)(_n##x,y,_n##z,v), I##cnc=(img)(x,_n##y,_n##z,v), I##nnc=(img)(_n##x,_n##y,_n##z,v)
580
I[0] = (img)(x,y,z,v), I[1] = (img)(_n1##x,y,z,v), I[2] = (img)(x,_n1##y,z,v), I[3] = (img)(_n1##x,_n1##y,z,v), \
581
I[4] = (img)(x,y,_n1##z,v), I[5] = (img)(_n1##x,y,_n1##z,v), I[6] = (img)(x,_n1##y,_n1##z,v), I[7] = (img)(_n1##x,_n1##y,_n1##z,v)
379
583
#define cimg_get3x3x3(img,x,y,z,v,I) \
380
I##ppp=(img)(_p##x,_p##y,_p##z,v), I##cpp=(img)(x,_p##y,_p##z,v), I##npp=(img)(_n##x,_p##y,_p##z,v), \
381
I##pcp=(img)(_p##x, y,_p##z,v), I##ccp=(img)(x, y,_p##z,v), I##ncp=(img)(_n##x, y,_p##z,v), \
382
I##pnp=(img)(_p##x,_n##y,_p##z,v), I##cnp=(img)(x,_n##y,_p##z,v), I##nnp=(img)(_n##x,_n##y,_p##z,v), \
383
I##ppc=(img)(_p##x,_p##y, z,v), I##cpc=(img)(x,_p##y, z,v), I##npc=(img)(_n##x,_p##y, z,v), \
384
I##pcc=(img)(_p##x, y, z,v), I##ccc=(img)(x, y, z,v), I##ncc=(img)(_n##x, y, z,v), \
385
I##pnc=(img)(_p##x,_n##y, z,v), I##cnc=(img)(x,_n##y, z,v), I##nnc=(img)(_n##x,_n##y, z,v), \
386
I##ppn=(img)(_p##x,_p##y,_n##z,v), I##cpn=(img)(x,_p##y,_n##z,v), I##npn=(img)(_n##x,_p##y,_n##z,v), \
387
I##pcn=(img)(_p##x, y,_n##z,v), I##ccn=(img)(x, y,_n##z,v), I##ncn=(img)(_n##x, y,_n##z,v), \
388
I##pnn=(img)(_p##x,_n##y,_n##z,v), I##cnn=(img)(x,_n##y,_n##z,v), I##nnn=(img)(_n##x,_n##y,_n##z,v)
390
// Macros used to define special image loops.
391
// (see module 'Using Image Loops' in the generated documentation).
392
#define cimg_for(img,ptr,T_ptr) for (T_ptr *ptr=(img).data+(img).size(); (ptr--)>(img).data; )
393
#define cimglist_for(list,l) for (unsigned int l=0; l<(list).size; ++l)
394
#define cimglist_apply(list,fn) cimglist_for(list,__##fn) (list)[__##fn].fn
395
#define cimg_foroff(img,off) for (unsigned int off=0; off<(img).size(); ++off)
396
#define cimg_forX(img,x) for (int x=0; x<(int)((img).width); ++x)
397
#define cimg_forY(img,y) for (int y=0; y<(int)((img).height); ++y)
398
#define cimg_forZ(img,z) for (int z=0; z<(int)((img).depth); ++z)
399
#define cimg_forV(img,v) for (int v=0; v<(int)((img).dim); ++v)
400
#define cimg_forXY(img,x,y) cimg_forY(img,y) cimg_forX(img,x)
401
#define cimg_forXZ(img,x,z) cimg_forZ(img,z) cimg_forX(img,x)
402
#define cimg_forYZ(img,y,z) cimg_forZ(img,z) cimg_forY(img,y)
403
#define cimg_forXV(img,x,v) cimg_forV(img,v) cimg_forX(img,x)
404
#define cimg_forYV(img,y,v) cimg_forV(img,v) cimg_forY(img,y)
405
#define cimg_forZV(img,z,v) cimg_forV(img,v) cimg_forZ(img,z)
406
#define cimg_forXYZ(img,x,y,z) cimg_forZ(img,z) cimg_forXY(img,x,y)
407
#define cimg_forXYV(img,x,y,v) cimg_forV(img,v) cimg_forXY(img,x,y)
408
#define cimg_forXZV(img,x,z,v) cimg_forV(img,v) cimg_forXZ(img,x,z)
409
#define cimg_forYZV(img,y,z,v) cimg_forV(img,v) cimg_forYZ(img,y,z)
584
I[0] = (img)(_p1##x,_p1##y,_p1##z,v), I[1] = (img)(x,_p1##y,_p1##z,v), I[2] = (img)(_n1##x,_p1##y,_p1##z,v), \
585
I[3] = (img)(_p1##x,y,_p1##z,v), I[4] = (img)(x,y,_p1##z,v), I[5] = (img)(_n1##x,y,_p1##z,v), \
586
I[6] = (img)(_p1##x,_n1##y,_p1##z,v), I[7] = (img)(x,_n1##y,_p1##z,v), I[8] = (img)(_n1##x,_n1##y,_p1##z,v), \
587
I[9] = (img)(_p1##x,_p1##y,z,v), I[10] = (img)(x,_p1##y,z,v), I[11] = (img)(_n1##x,_p1##y,z,v), \
588
I[12] = (img)(_p1##x,y,z,v), I[13] = (img)(x,y,z,v), I[14] = (img)(_n1##x,y,z,v), \
589
I[15] = (img)(_p1##x,_n1##y,z,v), I[16] = (img)(x,_n1##y,z,v), I[17] = (img)(_n1##x,_n1##y,z,v), \
590
I[18] = (img)(_p1##x,_p1##y,_n1##z,v), I[19] = (img)(x,_p1##y,_n1##z,v), I[20] = (img)(_n1##x,_p1##y,_n1##z,v), \
591
I[21] = (img)(_p1##x,y,_n1##z,v), I[22] = (img)(x,y,_n1##z,v), I[23] = (img)(_n1##x,y,_n1##z,v), \
592
I[24] = (img)(_p1##x,_n1##y,_n1##z,v), I[25] = (img)(x,_n1##y,_n1##z,v), I[26] = (img)(_n1##x,_n1##y,_n1##z,v)
594
// Define various image loops.
596
// These macros generally avoid the use of iterators, but you are not forced to used them !
598
#define cimg_for(img,ptr,T_ptr) for (T_ptr *ptr = (img).data + (img).size(); (ptr--)>(img).data; )
599
#define cimg_foroff(img,off) for (unsigned int off = 0; off<(img).size(); ++off)
600
#define cimglist_for(list,l) for (unsigned int l=0; l<(list).size; ++l)
601
#define cimglist_apply(list,fn) cimglist_for(list,__##fn) (list)[__##fn].fn
603
#define cimg_for1(bound,i) for (int i = 0; i<(int)(bound); ++i)
604
#define cimg_forX(img,x) cimg_for1((img).width,x)
605
#define cimg_forY(img,y) cimg_for1((img).height,y)
606
#define cimg_forZ(img,z) cimg_for1((img).depth,z)
607
#define cimg_forV(img,v) cimg_for1((img).dim,v)
608
#define cimg_forXY(img,x,y) cimg_forY(img,y) cimg_forX(img,x)
609
#define cimg_forXZ(img,x,z) cimg_forZ(img,z) cimg_forX(img,x)
610
#define cimg_forYZ(img,y,z) cimg_forZ(img,z) cimg_forY(img,y)
611
#define cimg_forXV(img,x,v) cimg_forV(img,v) cimg_forX(img,x)
612
#define cimg_forYV(img,y,v) cimg_forV(img,v) cimg_forY(img,y)
613
#define cimg_forZV(img,z,v) cimg_forV(img,v) cimg_forZ(img,z)
614
#define cimg_forXYZ(img,x,y,z) cimg_forZ(img,z) cimg_forXY(img,x,y)
615
#define cimg_forXYV(img,x,y,v) cimg_forV(img,v) cimg_forXY(img,x,y)
616
#define cimg_forXZV(img,x,z,v) cimg_forV(img,v) cimg_forXZ(img,x,z)
617
#define cimg_forYZV(img,y,z,v) cimg_forV(img,v) cimg_forYZ(img,y,z)
410
618
#define cimg_forXYZV(img,x,y,z,v) cimg_forV(img,v) cimg_forXYZ(img,x,y,z)
411
#define cimg_for_insideX(img,x,n) for (int x=(n); x<(int)((img).width-(n)); ++x)
412
#define cimg_for_insideY(img,y,n) for (int y=(n); y<(int)((img).height-(n)); ++y)
413
#define cimg_for_insideZ(img,z,n) for (int z=(n); z<(int)((img).depth-(n)); ++z)
414
#define cimg_for_insideV(img,v,n) for (int v=(n); v<(int)((img).dim-(n)); ++v)
415
#define cimg_for_insideXY(img,x,y,n) cimg_for_insideY(img,y,n) cimg_for_insideX(img,x,n)
416
#define cimg_for_insideXYZ(img,x,y,z,n) cimg_for_insideZ(img,z,n) cimg_for_insideXY(img,x,y,n)
417
#define cimg_for_borderX(img,x,n) for (int x=0; x<(int)((img).width); x==(n)-1?(x=(img).width-(n)): x++)
418
#define cimg_for_borderY(img,y,n) for (int y=0; y<(int)((img).height); y==(n)-1?(x=(img).height-(n)):y++)
419
#define cimg_for_borderZ(img,z,n) for (int z=0; z<(int)((img).depth); z==(n)-1?(x=(img).depth-(n)): z++)
420
#define cimg_for_borderV(img,v,n) for (int v=0; v<(int)((img).dim); v==(n)-1?(x=(img).dim-(n)): v++)
421
#define cimg_for_borderXY(img,x,y,n) cimg_forY(img,y) for (int x=0; x<(int)((img).width); (y<(n) || y>=(int)((img).height)-(n))?x++: \
422
((x<(n)-1 || x>=(int)((img).width)-(n))?x++:(x=(img).width-(n))))
423
#define cimg_for_borderXYZ(img,x,y,z,n) cimg_forYZ(img,y,z) for (int x=0; x<(int)((img).width); (y<(n) || y>=(int)((img).height)-(n) || z<(n) || z>=(int)((img).depth)-(n))?x++: \
424
((x<(n)-1 || x>=(int)((img).width)-(n))?x++:(x=(img).width-(n))))
425
#define cimg_for_spiralXY(img,x,y) for (int x=0,y=0,_n##x=1,_n##y=(int)((img).width*(img).height); _n##y; \
426
--_n##y, _n##x += (_n##x>>2)-((!(_n##x&3)?--y:((_n##x&3)==1?(img).width-1-++x:((_n##x&3)==2?(img).height-1-++y:--x))))?0:1)
429
#define cimg_for_lineXY(x,y,x0,y0,x1,y1) for (int x=(x0), y=(y0), _sx=1, _sy=1, _steep=0, \
430
_dx=(x1)>(x0)?(x1)-(x0):(_sx=-1,(x0)-(x1)), \
431
_dy=(y1)>(y0)?(y1)-(y0):(_sy=-1,(y0)-(y1)), \
433
_err=_dx>_dy?(_dy>>1):((_steep=1),(_counter=_dy),(_dx>>1)); \
435
--_counter, x+=_steep? \
436
(y+=_sy,(_err-=_dx)<0?_err+=_dy,_sx:0): \
437
(y+=(_err-=_dy)<0?_err+=_dx,_sy:0,_sx))
439
#define cimg_for2X(img,x) for (int x=0,_n##x=1; _n##x<(int)((img).width) || x==--_n##x; x++, _n##x++)
440
#define cimg_for2Y(img,y) for (int y=0,_n##y=1; _n##y<(int)((img).height) || y==--_n##y; y++, _n##y++)
441
#define cimg_for2Z(img,z) for (int z=0,_n##z=1; _n##z<(int)((img).depth) || z==--_n##z; z++, _n##z++)
442
#define cimg_for2XY(img,x,y) cimg_for2Y(img,y) cimg_for2X(img,x)
443
#define cimg_for2XZ(img,x,z) cimg_for2Z(img,z) cimg_for2X(img,x)
444
#define cimg_for2YZ(img,y,z) cimg_for2Z(img,z) cimg_for2Y(img,y)
445
#define cimg_for2XYZ(img,x,y,z) cimg_for2Z(img,z) cimg_for2XY(img,x,y)
446
#define cimg_for3X(img,x) for (int x=0,_p##x=0,_n##x=1; _n##x<(int)((img).width) || x==--_n##x; _p##x=x++,_n##x++)
447
#define cimg_for3Y(img,y) for (int y=0,_p##y=0,_n##y=1; _n##y<(int)((img).height) || y==--_n##y; _p##y=y++,_n##y++)
448
#define cimg_for3Z(img,z) for (int z=0,_p##z=0,_n##z=1; _n##z<(int)((img).depth) || z==--_n##z; _p##z=z++,_n##z++)
449
#define cimg_for3XY(img,x,y) cimg_for3Y(img,y) cimg_for3X(img,x)
450
#define cimg_for3XZ(img,x,z) cimg_for3Z(img,z) cimg_for3X(img,x)
451
#define cimg_for3YZ(img,y,z) cimg_for3Z(img,z) cimg_for3Y(img,y)
452
#define cimg_for3XYZ(img,x,y,z) cimg_for3Z(img,z) cimg_for3XY(img,x,y)
453
#define cimg_for4X(img,x) for (int _p##x=0,x=0,_n##x=1,_a##x=2; \
454
_a##x<(int)((img).width) || _n##x==--_a##x || x==(_a##x=--_n##x); \
455
_p##x=x++,_n##x++,_a##x++)
456
#define cimg_for4Y(img,y) for (int _p##y=0,y=0,_n##y=1,_a##y=2; \
457
_a##y<(int)((img).height) || _n##y==--_a##y || y==(_a##y=--_n##y); \
458
_p##y=y++,_n##y++,_a##y++)
459
#define cimg_for4Z(img,z) for (int _p##z=0,z=0,_n##z=1,_a##z=2; \
460
_a##z<(int)((img).depth) || _n##z==--_a##z || z==(_a##z=--_n##z); \
461
_p##z=z++,_n##z++,_a##z++)
462
#define cimg_for4XY(img,x,y) cimg_for4Y(img,y) cimg_for4X(img,x)
463
#define cimg_for4XZ(img,x,z) cimg_for4Z(img,z) cimg_for4X(img,x)
464
#define cimg_for4YZ(img,y,z) cimg_for4Z(img,z) cimg_for4Y(img,y)
465
#define cimg_for4XYZ(img,x,y,z) cimg_for4Z(img,z) cimg_for4XY(img,x,y)
466
#define cimg_for5X(img,x) for (int _b##x=0,_p##x=0,x=0,_n##x=1,_a##x=2; \
467
_a##x<(int)((img).width) || _n##x==--_a##x || x==(_a##x=--_n##x); \
468
_b##x=_p##x,_p##x=x++,_n##x++,_a##x++)
469
#define cimg_for5Y(img,y) for (int _b##y=0,_p##y=0,y=0,_n##y=1,_a##y=2; \
470
_a##y<(int)((img).height) || _n##y==--_a##y || y==(_a##y=--_n##y); \
471
_b##y=_p##y,_p##y=y++,_n##y++,_a##y++)
472
#define cimg_for5Z(img,z) for (int _b##z=0,_p##z=0,z=0,_n##z=1,_a##z=2; \
473
_a##z<(int)((img).depth) || _n##z==--_a##z || z==(_a##z=--_n##z); \
474
_b##z=_p##z,_p##z=z++,_n##z++,_a##z++)
475
#define cimg_for5XY(img,x,y) cimg_for5Y(img,y) cimg_for5X(img,x)
476
#define cimg_for5XZ(img,x,z) cimg_for5Z(img,z) cimg_for5X(img,x)
477
#define cimg_for5YZ(img,y,z) cimg_for5Z(img,z) cimg_for5Y(img,y)
478
#define cimg_for5XYZ(img,x,y,z) cimg_for5Z(img,z) cimg_for5XY(img,x,y)
480
#define cimg_for2x2(img,x,y,z,v,I) cimg_for2Y(img,y) \
481
for (int _n##x=1, x=(int)((I##cc=(img)(0, y,z,v)), \
482
(I##cn=(img)(0,_n##y,z,v)), \
484
(_n##x<(int)((img).width) && ((I##nc=(img)(_n##x, y,z,v)), \
485
(I##nn=(img)(_n##x,_n##y,z,v)), \
487
I##cc=I##nc, I##cn=I##nn, \
490
#define cimg_for3x3(img,x,y,z,v,I) cimg_for3Y(img,y) \
491
for (int _n##x=1, _p##x=(int)((I##cp=I##pp=(img)(0,_p##y,z,v)), \
492
(I##cc=I##pc=(img)(0, y,z,v)), \
493
(I##cn=I##pn=(img)(0,_n##y,z,v))), \
495
(_n##x<(int)((img).width) && ((I##np=(img)(_n##x,_p##y,z,v)), \
496
(I##nc=(img)(_n##x, y,z,v)), \
497
(I##nn=(img)(_n##x,_n##y,z,v)), \
499
I##pp=I##cp, I##pc=I##cc, I##pn=I##cn, \
500
I##cp=I##np, I##cc=I##nc, I##cn=I##nn, \
504
#define cimg_for4x4(img,x,y,z,v,I) cimg_for4Y(img,y) \
505
for (int _a##x=2, _n##x=1, x=(int)((I##cp=I##pp=(img)(0,_p##y,z,v)), \
506
(I##cc=I##pc=(img)(0, y,z,v)), \
507
(I##cn=I##pn=(img)(0,_n##y,z,v)), \
508
(I##ca=I##pa=(img)(0,_a##y,z,v)), \
509
(I##np=(img)(_n##x,_p##y,z,v)), \
510
(I##nc=(img)(_n##x, y,z,v)), \
511
(I##nn=(img)(_n##x,_n##y,z,v)), \
512
(I##na=(img)(_n##x,_a##y,z,v)), \
514
(_a##x<(int)((img).width) && ((I##ap=(img)(_a##x,_p##y,z,v)), \
515
(I##ac=(img)(_a##x, y,z,v)), \
516
(I##an=(img)(_a##x,_n##y,z,v)), \
517
(I##aa=(img)(_a##x,_a##y,z,v)), \
518
1)) || _n##x==--_a##x || x==(_a##x=--_n##x); \
519
I##pp=I##cp, I##pc=I##cc, I##pn=I##cn, I##pa=I##ca, \
520
I##cp=I##np, I##cc=I##nc, I##cn=I##nn, I##ca=I##na, \
521
I##np=I##ap, I##nc=I##ac, I##nn=I##an, I##na=I##aa, \
522
_p##x=x++, _n##x++, _a##x++ )
524
#define cimg_for5x5(img,x,y,z,v,I) cimg_for5Y(img,y) \
525
for (int _a##x=2, _n##x=1, _b##x=(int)((I##cb=I##pb=I##bb=(img)(0,_b##y,z,v)), \
526
(I##cp=I##pp=I##bp=(img)(0,_p##y,z,v)), \
527
(I##cc=I##pc=I##bc=(img)(0, y,z,v)), \
528
(I##cn=I##pn=I##bn=(img)(0,_n##y,z,v)), \
529
(I##ca=I##pa=I##ba=(img)(0,_a##y,z,v)), \
530
(I##nb=(img)(_n##x,_b##y,z,v)), \
531
(I##np=(img)(_n##x,_p##y,z,v)), \
532
(I##nc=(img)(_n##x, y,z,v)), \
533
(I##nn=(img)(_n##x,_n##y,z,v)), \
534
(I##na=(img)(_n##x,_a##y,z,v))), \
535
x=0, _p##x=_b##x=0; \
536
(_a##x<(int)((img).width) && ((I##ab=(img)(_a##x,_b##y,z,v)), \
537
(I##ap=(img)(_a##x,_p##y,z,v)), \
538
(I##ac=(img)(_a##x, y,z,v)), \
539
(I##an=(img)(_a##x,_n##y,z,v)), \
540
(I##aa=(img)(_a##x,_a##y,z,v)), \
541
1)) || _n##x==--_a##x || x==(_a##x=--_n##x); \
542
I##bb=I##pb, I##bp=I##pp, I##bc=I##pc, I##bn=I##pn, I##ba=I##pa, \
543
I##pb=I##cb, I##pp=I##cp, I##pc=I##cc, I##pn=I##cn, I##pa=I##ca, \
544
I##cb=I##nb, I##cp=I##np, I##cc=I##nc, I##cn=I##nn, I##ca=I##na, \
545
I##nb=I##ab, I##np=I##ap, I##nc=I##ac, I##nn=I##an, I##na=I##aa, \
546
_b##x=_p##x, _p##x=x++, _n##x++, _a##x++ )
548
#define cimg_for2x2x2(img,x,y,z,v,I) cimg_for2YZ(img,y,z) \
549
for (int _n##x=1, x=(int)((I##ccc=(img)(0, y, z,v)), \
550
(I##cnc=(img)(0,_n##y, z,v)), \
551
(I##ccn=(img)(0, y,_n##z,v)), \
552
(I##cnn=(img)(0,_n##y,_n##z,v)), \
554
(_n##x<(int)((img).width) && ((I##ncc=(img)(_n##x, y, z,v)), \
555
(I##nnc=(img)(_n##x,_n##y, z,v)), \
556
(I##ncn=(img)(_n##x, y,_n##z,v)), \
557
(I##nnn=(img)(_n##x,_n##y,_n##z,v)), \
559
I##ccc=I##ncc, I##cnc=I##nnc, \
560
I##ccn=I##ncn, I##cnn=I##nnn, \
563
#define cimg_for3x3x3(img,x,y,z,v,I) cimg_for3YZ(img,y,z) \
564
for (int _n##x=1, _p##x=(int)((I##cpp=I##ppp=(img)(0,_p##y,_p##z,v)), \
565
(I##ccp=I##pcp=(img)(0, y,_p##z,v)), \
566
(I##cnp=I##pnp=(img)(0,_n##y,_p##z,v)), \
567
(I##cpc=I##ppc=(img)(0,_p##y, z,v)), \
568
(I##ccc=I##pcc=(img)(0, y, z,v)), \
569
(I##cnc=I##pnc=(img)(0,_n##y, z,v)), \
570
(I##cpn=I##ppn=(img)(0,_p##y,_n##z,v)), \
571
(I##ccn=I##pcn=(img)(0, y,_n##z,v)), \
572
(I##cnn=I##pnn=(img)(0,_n##y,_n##z,v))),\
574
(_n##x<(int)((img).width) && ((I##npp=(img)(_n##x,_p##y,_p##z,v)), \
575
(I##ncp=(img)(_n##x, y,_p##z,v)), \
576
(I##nnp=(img)(_n##x,_n##y,_p##z,v)), \
577
(I##npc=(img)(_n##x,_p##y, z,v)), \
578
(I##ncc=(img)(_n##x, y, z,v)), \
579
(I##nnc=(img)(_n##x,_n##y, z,v)), \
580
(I##npn=(img)(_n##x,_p##y,_n##z,v)), \
581
(I##ncn=(img)(_n##x, y,_n##z,v)), \
582
(I##nnn=(img)(_n##x,_n##y,_n##z,v)), \
584
I##ppp=I##cpp, I##pcp=I##ccp, I##pnp=I##cnp, \
585
I##cpp=I##npp, I##ccp=I##ncp, I##cnp=I##nnp, \
586
I##ppc=I##cpc, I##pcc=I##ccc, I##pnc=I##cnc, \
587
I##cpc=I##npc, I##ccc=I##ncc, I##cnc=I##nnc, \
588
I##ppn=I##cpn, I##pcn=I##ccn, I##pnn=I##cnn, \
589
I##cpn=I##npn, I##ccn=I##ncn, I##cnn=I##nnn, \
592
#define _CImg_stdarg(img,a0,a1,N,t) \
593
{ unsigned int _siz = (unsigned int)N; \
597
T *ptrd = (img).data; \
599
if (_siz--) { *(ptrd++) = (T)a1; for (; _siz; --_siz) *(ptrd++) = (T)va_arg(ap,t); } \
604
#------------------------------------------------
620
#define cimg_for_in1(bound,i0,i1,i) \
621
for (int i = (int)(i0)<0?0:(int)(i0), _max##i = (int)(i1)<(int)(bound)?(int)(i1):(int)(bound)-1; i<=_max##i; ++i)
622
#define cimg_for_inX(img,x0,x1,x) cimg_for_in1((img).width,x0,x1,x)
623
#define cimg_for_inY(img,y0,y1,y) cimg_for_in1((img).height,y0,y1,y)
624
#define cimg_for_inZ(img,z0,z1,z) cimg_for_in1((img).depth,z0,z1,z)
625
#define cimg_for_inV(img,v0,v1,v) cimg_for_in1((img).dim,v0,v1,v)
626
#define cimg_for_inXY(img,x0,y0,x1,y1,x,y) cimg_for_inY(img,y0,y1,y) cimg_for_inX(img,x0,x1,x)
627
#define cimg_for_inXZ(img,x0,z0,x1,z1,x,z) cimg_for_inZ(img,z0,z1,z) cimg_for_inX(img,x0,x1,x)
628
#define cimg_for_inXV(img,x0,v0,x1,v1,x,v) cimg_for_inV(img,v0,v1,v) cimg_for_inX(img,x0,x1,x)
629
#define cimg_for_inYZ(img,y0,z0,y1,z1,y,z) cimg_for_inZ(img,x0,z1,z) cimg_for_inY(img,y0,y1,y)
630
#define cimg_for_inYV(img,y0,v0,y1,v1,y,v) cimg_for_inV(img,v0,v1,v) cimg_for_inY(img,y0,y1,y)
631
#define cimg_for_inZV(img,z0,v0,z1,v1,z,v) cimg_for_inV(img,v0,v1,v) cimg_for_inZ(img,z0,z1,z)
632
#define cimg_for_inXYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_inZ(img,z0,z1,z) cimg_for_inXY(img,x0,y0,x1,y1,x,y)
633
#define cimg_for_inXYV(img,x0,y0,v0,x1,y1,v1,x,y,v) cimg_for_inV(img,v0,v1,v) cimg_for_inXY(img,x0,y0,x1,y1,x,y)
634
#define cimg_for_inXZV(img,x0,z0,v0,x1,z1,v1,x,z,v) cimg_for_inV(img,v0,v1,v) cimg_for_inXZ(img,x0,z0,x1,z1,x,z)
635
#define cimg_for_inYZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_inV(img,v0,v1,v) cimg_for_inYZ(img,y0,z0,y1,z1,y,z)
636
#define cimg_for_inXYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_inV(img,v0,v1,v) cimg_for_inXYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
637
#define cimg_for_insideX(img,x,n) cimg_for_inX(img,n,(img).width-1-(n),x)
638
#define cimg_for_insideY(img,y,n) cimg_for_inY(img,n,(img).height-1-(n),y)
639
#define cimg_for_insideZ(img,z,n) cimg_for_inZ(img,n,(img).depth-1-(n),z)
640
#define cimg_for_insideV(img,v,n) cimg_for_inV(img,n,(img).dim-1-(n),v)
641
#define cimg_for_insideXY(img,x,y,n) cimg_for_inXY(img,n,n,(img).width-1-(n),(img).height-1-(n),x,y)
642
#define cimg_for_insideXYZ(img,x,y,z,n) cimg_for_inXYZ(img,n,n,n,(img).width-1-(n),(img).height-1-(n),(img).depth-1-(n),x,y,z)
643
#define cimg_for_insideXYZV(img,x,y,z,v,n) cimg_for_inXYZ(img,n,n,n,(img).width-1-(n),(img).height-1-(n),(img).depth-1-(n),x,y,z)
645
#define cimg_for_out1(boundi,i0,i1,i) \
646
for (int i = (int)(i0)>0?0:(int)(i1)+1; i<(int)(boundi); ++i, i = i==(int)(i0)?(int)(i1)+1:i)
647
#define cimg_for_out2(boundi,boundj,i0,j0,i1,j1,i,j) \
648
for (int j = 0; j<(int)(boundj); ++j) \
649
for (int _n1j = (int)(j<(int)(j0) || j>(int)(j1)), i = _n1j?0:(int)(i0)>0?0:(int)(i1)+1; i<(int)(boundi); \
650
++i, i = _n1j?i:(i==(int)(i0)?(int)(i1)+1:i))
651
#define cimg_for_out3(boundi,boundj,boundk,i0,j0,k0,i1,j1,k1,i,j,k) \
652
for (int k = 0; k<(int)(boundk); ++k) \
653
for (int _n1k = (int)(k<(int)(k0) || k>(int)(k1)), j = 0; j<(int)(boundj); ++j) \
654
for (int _n1j = (int)(j<(int)(j0) || j>(int)(j1)), i = _n1j || _n1k?0:(int)(i0)>0?0:(int)(i1)+1; i<(int)(boundi); \
655
++i, i = _n1j || _n1k?i:(i==(int)(i0)?(int)(i1)+1:i))
656
#define cimg_for_out4(boundi,boundj,boundk,boundl,i0,j0,k0,l0,i1,j1,k1,l1,i,j,k,l) \
657
for (int l = 0; l<(int)(boundl); ++l) \
658
for (int _n1l = (int)(l<(int)(l0) || l>(int)(l1)), k = 0; k<(int)(boundk); ++k) \
659
for (int _n1k = (int)(k<(int)(k0) || k>(int)(k1)), j = 0; j<(int)(boundj); ++j) \
660
for (int _n1j = (int)(j<(int)(j0) || j>(int)(j1)), i = _n1j || _n1k || _n1l?0:(int)(i0)>0?0:(int)(i1)+1; i<(int)(boundi); \
661
++i, i = _n1j || _n1k || _n1l?i:(i==(int)(i0)?(int)(i1)+1:i))
662
#define cimg_for_outX(img,x0,x1,x) cimg_for_out1((img).width,x0,x1,x)
663
#define cimg_for_outY(img,y0,y1,y) cimg_for_out1((img).height,y0,y1,y)
664
#define cimg_for_outZ(img,z0,z1,z) cimg_for_out1((img).depth,z0,z1,z)
665
#define cimg_for_outV(img,v0,v1,v) cimg_for_out1((img).dim,v0,v1,v)
666
#define cimg_for_outXY(img,x0,y0,x1,y1,x,y) cimg_for_out2((img).width,(img).height,x0,y0,x1,y1,x,y)
667
#define cimg_for_outXZ(img,x0,z0,x1,z1,x,z) cimg_for_out2((img).width,(img).depth,x0,z0,x1,z1,x,z)
668
#define cimg_for_outXV(img,x0,v0,x1,v1,x,v) cimg_for_out2((img).width,(img).dim,x0,v0,x1,v1,x,v)
669
#define cimg_for_outYZ(img,y0,z0,y1,z1,y,z) cimg_for_out2((img).height,(img).depth,y0,z0,y1,z1,y,z)
670
#define cimg_for_outYV(img,y0,v0,y1,v1,y,v) cimg_for_out2((img).height,(img).dim,y0,v0,y1,v1,y,v)
671
#define cimg_for_outZV(img,z0,v0,z1,v1,z,v) cimg_for_out2((img).depth,(img).dim,z0,v0,z1,v1,z,v)
672
#define cimg_for_outXYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_out3((img).width,(img).height,(img).depth,x0,y0,z0,x1,y1,z1,x,y,z)
673
#define cimg_for_outXYV(img,x0,y0,v0,x1,y1,v1,x,y,v) cimg_for_out3((img).width,(img).height,(img).dim,x0,y0,v0,x1,y1,v1,x,y,v)
674
#define cimg_for_outXZV(img,x0,z0,v0,x1,z1,v1,x,z,v) cimg_for_out3((img).width,(img).depth,(img).dim,x0,z0,v0,x1,z1,v1,x,z,v)
675
#define cimg_for_outYZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_out3((img).height,(img).depth,(img).dim,y0,z0,v0,y1,z1,v1,y,z,v)
676
#define cimg_for_outXYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) \
677
cimg_for_out4((img).width,(img).height,(img).depth,(img).dim,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v)
678
#define cimg_for_borderX(img,x,n) cimg_for_outX(img,n,(img).width-1-(n),x)
679
#define cimg_for_borderY(img,y,n) cimg_for_outY(img,n,(img).height-1-(n),y)
680
#define cimg_for_borderZ(img,z,n) cimg_for_outZ(img,n,(img).depth-1-(n),z)
681
#define cimg_for_borderV(img,v,n) cimg_for_outV(img,n,(img).dim-1-(n),v)
682
#define cimg_for_borderXY(img,x,y,n) cimg_for_outXY(img,n,n,(img).width-1-(n),(img).height-1-(n),x,y)
683
#define cimg_for_borderXYZ(img,x,y,z,n) cimg_for_outXYZ(img,n,n,n,(img).width-1-(n),(img).height-1-(n),(img).depth-1-(n),x,y,z)
684
#define cimg_for_borderXYZV(img,x,y,z,v,n) \
685
cimg_for_outXYZV(img,n,n,n,n,(img).width-1-(n),(img).height-1-(n),(img).depth-1-(n),(img).dim-1-(n),x,y,z,v)
687
#define cimg_for_spiralXY(img,x,y) \
688
for (int x = 0, y = 0, _n1##x = 1, _n1##y = (int)((img).width*(img).height); _n1##y; \
689
--_n1##y, _n1##x += (_n1##x>>2)-((!(_n1##x&3)?--y:((_n1##x&3)==1?(img).width-1-++x:((_n1##x&3)==2?(img).height-1-++y:--x))))?0:1)
691
#define cimg_for_lineXY(x,y,x0,y0,x1,y1) \
692
for (int x = (int)(x0), y = (int)(y0), _sx = 1, _sy = 1, _steep = 0, \
693
_dx=(x1)>(x0)?(int)(x1)-(int)(x0):(_sx=-1,(int)(x0)-(int)(x1)), \
694
_dy=(y1)>(y0)?(int)(y1)-(int)(y0):(_sy=-1,(int)(y0)-(int)(y1)), \
696
_err = _dx>_dy?(_dy>>1):((_steep=1),(_counter=_dy),(_dx>>1)); \
698
--_counter, x+=_steep? \
699
(y+=_sy,(_err-=_dx)<0?_err+=_dy,_sx:0): \
700
(y+=(_err-=_dy)<0?_err+=_dx,_sy:0,_sx))
702
#define cimg_for2(bound,i) \
703
for (int i = 0, _n1##i = 1>=(bound)?(int)(bound)-1:1; \
704
_n1##i<(int)(bound) || i==--_n1##i; \
706
#define cimg_for2X(img,x) cimg_for2((img).width,x)
707
#define cimg_for2Y(img,y) cimg_for2((img).height,y)
708
#define cimg_for2Z(img,z) cimg_for2((img).depth,z)
709
#define cimg_for2V(img,v) cimg_for2((img).dim,v)
710
#define cimg_for2XY(img,x,y) cimg_for2Y(img,y) cimg_for2X(img,x)
711
#define cimg_for2XZ(img,x,z) cimg_for2Z(img,z) cimg_for2X(img,x)
712
#define cimg_for2XV(img,x,v) cimg_for2V(img,v) cimg_for2X(img,x)
713
#define cimg_for2YZ(img,y,z) cimg_for2Z(img,z) cimg_for2Y(img,y)
714
#define cimg_for2YV(img,y,v) cimg_for2V(img,v) cimg_for2Y(img,y)
715
#define cimg_for2ZV(img,z,v) cimg_for2V(img,v) cimg_for2Z(img,z)
716
#define cimg_for2XYZ(img,x,y,z) cimg_for2Z(img,z) cimg_for2XY(img,x,y)
717
#define cimg_for2XZV(img,x,z,v) cimg_for2V(img,v) cimg_for2XZ(img,x,z)
718
#define cimg_for2YZV(img,y,z,v) cimg_for2V(img,v) cimg_for2YZ(img,y,z)
719
#define cimg_for2XYZV(img,x,y,z,v) cimg_for2V(img,v) cimg_for2XYZ(img,x,y,z)
721
#define cimg_for_in2(bound,i0,i1,i) \
722
for (int i = (int)(i0)<0?0:(int)(i0), \
723
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1; \
724
i<=(int)(i1) && (_n1##i<(int)(bound) || i==--_n1##i); \
726
#define cimg_for_in2X(img,x0,x1,x) cimg_for_in2((img).width,x0,x1,x)
727
#define cimg_for_in2Y(img,y0,y1,y) cimg_for_in2((img).height,y0,y1,y)
728
#define cimg_for_in2Z(img,z0,z1,z) cimg_for_in2((img).depth,z0,z1,z)
729
#define cimg_for_in2V(img,v0,v1,v) cimg_for_in2((img).dim,v0,v1,v)
730
#define cimg_for_in2XY(img,x0,y0,x1,y1,x,y) cimg_for_in2Y(img,y0,y1,y) cimg_for_in2X(img,x0,x1,x)
731
#define cimg_for_in2XZ(img,x0,z0,x1,z1,x,z) cimg_for_in2Z(img,z0,z1,z) cimg_for_in2X(img,x0,x1,x)
732
#define cimg_for_in2XV(img,x0,v0,x1,v1,x,v) cimg_for_in2V(img,v0,v1,v) cimg_for_in2X(img,x0,x1,x)
733
#define cimg_for_in2YZ(img,y0,z0,y1,z1,y,z) cimg_for_in2Z(img,z0,z1,z) cimg_for_in2Y(img,y0,y1,y)
734
#define cimg_for_in2YV(img,y0,v0,y1,v1,y,v) cimg_for_in2V(img,v0,v1,v) cimg_for_in2Y(img,y0,y1,y)
735
#define cimg_for_in2ZV(img,z0,v0,z1,v1,z,v) cimg_for_in2V(img,v0,v1,v) cimg_for_in2Z(img,z0,z1,z)
736
#define cimg_for_in2XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in2Z(img,z0,z1,z) cimg_for_in2XY(img,x0,y0,x1,y1,x,y)
737
#define cimg_for_in2XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in2V(img,v0,v1,v) cimg_for_in2XZ(img,x0,y0,x1,y1,x,z)
738
#define cimg_for_in2YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in2V(img,v0,v1,v) cimg_for_in2YZ(img,y0,z0,y1,z1,y,z)
739
#define cimg_for_in2XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in2V(img,v0,v1,v) cimg_for_in2XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
741
#define cimg_for3(bound,i) \
742
for (int i = 0, _p1##i = 0, \
743
_n1##i = 1>=(bound)?(int)(bound)-1:1; \
744
_n1##i<(int)(bound) || i==--_n1##i; \
745
_p1##i = i++, ++_n1##i)
746
#define cimg_for3X(img,x) cimg_for3((img).width,x)
747
#define cimg_for3Y(img,y) cimg_for3((img).height,y)
748
#define cimg_for3Z(img,z) cimg_for3((img).depth,z)
749
#define cimg_for3V(img,v) cimg_for3((img).dim,v)
750
#define cimg_for3XY(img,x,y) cimg_for3Y(img,y) cimg_for3X(img,x)
751
#define cimg_for3XZ(img,x,z) cimg_for3Z(img,z) cimg_for3X(img,x)
752
#define cimg_for3XV(img,x,v) cimg_for3V(img,v) cimg_for3X(img,x)
753
#define cimg_for3YZ(img,y,z) cimg_for3Z(img,z) cimg_for3Y(img,y)
754
#define cimg_for3YV(img,y,v) cimg_for3V(img,v) cimg_for3Y(img,y)
755
#define cimg_for3ZV(img,z,v) cimg_for3V(img,v) cimg_for3Z(img,z)
756
#define cimg_for3XYZ(img,x,y,z) cimg_for3Z(img,z) cimg_for3XY(img,x,y)
757
#define cimg_for3XZV(img,x,z,v) cimg_for3V(img,v) cimg_for3XZ(img,x,z)
758
#define cimg_for3YZV(img,y,z,v) cimg_for3V(img,v) cimg_for3YZ(img,y,z)
759
#define cimg_for3XYZV(img,x,y,z,v) cimg_for3V(img,v) cimg_for3XYZ(img,x,y,z)
761
#define cimg_for_in3(bound,i0,i1,i) \
762
for (int i = (int)(i0)<0?0:(int)(i0), \
763
_p1##i = i-1<0?0:i-1, \
764
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1; \
765
i<=(int)(i1) && (_n1##i<(int)(bound) || i==--_n1##i); \
766
_p1##i = i++, ++_n1##i)
767
#define cimg_for_in3X(img,x0,x1,x) cimg_for_in3((img).width,x0,x1,x)
768
#define cimg_for_in3Y(img,y0,y1,y) cimg_for_in3((img).height,y0,y1,y)
769
#define cimg_for_in3Z(img,z0,z1,z) cimg_for_in3((img).depth,z0,z1,z)
770
#define cimg_for_in3V(img,v0,v1,v) cimg_for_in3((img).dim,v0,v1,v)
771
#define cimg_for_in3XY(img,x0,y0,x1,y1,x,y) cimg_for_in3Y(img,y0,y1,y) cimg_for_in3X(img,x0,x1,x)
772
#define cimg_for_in3XZ(img,x0,z0,x1,z1,x,z) cimg_for_in3Z(img,z0,z1,z) cimg_for_in3X(img,x0,x1,x)
773
#define cimg_for_in3XV(img,x0,v0,x1,v1,x,v) cimg_for_in3V(img,v0,v1,v) cimg_for_in3X(img,x0,x1,x)
774
#define cimg_for_in3YZ(img,y0,z0,y1,z1,y,z) cimg_for_in3Z(img,z0,z1,z) cimg_for_in3Y(img,y0,y1,y)
775
#define cimg_for_in3YV(img,y0,v0,y1,v1,y,v) cimg_for_in3V(img,v0,v1,v) cimg_for_in3Y(img,y0,y1,y)
776
#define cimg_for_in3ZV(img,z0,v0,z1,v1,z,v) cimg_for_in3V(img,v0,v1,v) cimg_for_in3Z(img,z0,z1,z)
777
#define cimg_for_in3XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in3Z(img,z0,z1,z) cimg_for_in3XY(img,x0,y0,x1,y1,x,y)
778
#define cimg_for_in3XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in3V(img,v0,v1,v) cimg_for_in3XZ(img,x0,y0,x1,y1,x,z)
779
#define cimg_for_in3YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in3V(img,v0,v1,v) cimg_for_in3YZ(img,y0,z0,y1,z1,y,z)
780
#define cimg_for_in3XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in3V(img,v0,v1,v) cimg_for_in3XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
782
#define cimg_for4(bound,i) \
783
for (int i = 0, _p1##i = 0, _n1##i = 1>=(bound)?(int)(bound)-1:1, \
784
_n2##i = 2>=(bound)?(int)(bound)-1:2; \
785
_n2##i<(int)(bound) || _n1##i==--_n2##i || i==(_n2##i = --_n1##i); \
786
_p1##i = i++, ++_n1##i, ++_n2##i)
787
#define cimg_for4X(img,x) cimg_for4((img).width,x)
788
#define cimg_for4Y(img,y) cimg_for4((img).height,y)
789
#define cimg_for4Z(img,z) cimg_for4((img).depth,z)
790
#define cimg_for4V(img,v) cimg_for4((img).dim,v)
791
#define cimg_for4XY(img,x,y) cimg_for4Y(img,y) cimg_for4X(img,x)
792
#define cimg_for4XZ(img,x,z) cimg_for4Z(img,z) cimg_for4X(img,x)
793
#define cimg_for4XV(img,x,v) cimg_for4V(img,v) cimg_for4X(img,x)
794
#define cimg_for4YZ(img,y,z) cimg_for4Z(img,z) cimg_for4Y(img,y)
795
#define cimg_for4YV(img,y,v) cimg_for4V(img,v) cimg_for4Y(img,y)
796
#define cimg_for4ZV(img,z,v) cimg_for4V(img,v) cimg_for4Z(img,z)
797
#define cimg_for4XYZ(img,x,y,z) cimg_for4Z(img,z) cimg_for4XY(img,x,y)
798
#define cimg_for4XZV(img,x,z,v) cimg_for4V(img,v) cimg_for4XZ(img,x,z)
799
#define cimg_for4YZV(img,y,z,v) cimg_for4V(img,v) cimg_for4YZ(img,y,z)
800
#define cimg_for4XYZV(img,x,y,z,v) cimg_for4V(img,v) cimg_for4XYZ(img,x,y,z)
802
#define cimg_for_in4(bound,i0,i1,i) \
803
for (int i = (int)(i0)<0?0:(int)(i0), \
804
_p1##i = i-1<0?0:i-1, \
805
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1, \
806
_n2##i = i+2>=(int)(bound)?(int)(bound)-1:i+2; \
807
i<=(int)(i1) && (_n2##i<(int)(bound) || _n1##i==--_n2##i || i==(_n2##i = --_n1##i)); \
808
_p1##i = i++, ++_n1##i, ++_n2##i)
809
#define cimg_for_in4X(img,x0,x1,x) cimg_for_in4((img).width,x0,x1,x)
810
#define cimg_for_in4Y(img,y0,y1,y) cimg_for_in4((img).height,y0,y1,y)
811
#define cimg_for_in4Z(img,z0,z1,z) cimg_for_in4((img).depth,z0,z1,z)
812
#define cimg_for_in4V(img,v0,v1,v) cimg_for_in4((img).dim,v0,v1,v)
813
#define cimg_for_in4XY(img,x0,y0,x1,y1,x,y) cimg_for_in4Y(img,y0,y1,y) cimg_for_in4X(img,x0,x1,x)
814
#define cimg_for_in4XZ(img,x0,z0,x1,z1,x,z) cimg_for_in4Z(img,z0,z1,z) cimg_for_in4X(img,x0,x1,x)
815
#define cimg_for_in4XV(img,x0,v0,x1,v1,x,v) cimg_for_in4V(img,v0,v1,v) cimg_for_in4X(img,x0,x1,x)
816
#define cimg_for_in4YZ(img,y0,z0,y1,z1,y,z) cimg_for_in4Z(img,z0,z1,z) cimg_for_in4Y(img,y0,y1,y)
817
#define cimg_for_in4YV(img,y0,v0,y1,v1,y,v) cimg_for_in4V(img,v0,v1,v) cimg_for_in4Y(img,y0,y1,y)
818
#define cimg_for_in4ZV(img,z0,v0,z1,v1,z,v) cimg_for_in4V(img,v0,v1,v) cimg_for_in4Z(img,z0,z1,z)
819
#define cimg_for_in4XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in4Z(img,z0,z1,z) cimg_for_in4XY(img,x0,y0,x1,y1,x,y)
820
#define cimg_for_in4XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in4V(img,v0,v1,v) cimg_for_in4XZ(img,x0,y0,x1,y1,x,z)
821
#define cimg_for_in4YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in4V(img,v0,v1,v) cimg_for_in4YZ(img,y0,z0,y1,z1,y,z)
822
#define cimg_for_in4XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in4V(img,v0,v1,v) cimg_for_in4XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
824
#define cimg_for5(bound,i) \
825
for (int i = 0, _p2##i = 0, _p1##i = 0, \
826
_n1##i = 1>=(bound)?(int)(bound)-1:1, \
827
_n2##i = 2>=(bound)?(int)(bound)-1:2; \
828
_n2##i<(int)(bound) || _n1##i==--_n2##i || i==(_n2##i = --_n1##i); \
829
_p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i)
830
#define cimg_for5X(img,x) cimg_for5((img).width,x)
831
#define cimg_for5Y(img,y) cimg_for5((img).height,y)
832
#define cimg_for5Z(img,z) cimg_for5((img).depth,z)
833
#define cimg_for5V(img,v) cimg_for5((img).dim,v)
834
#define cimg_for5XY(img,x,y) cimg_for5Y(img,y) cimg_for5X(img,x)
835
#define cimg_for5XZ(img,x,z) cimg_for5Z(img,z) cimg_for5X(img,x)
836
#define cimg_for5XV(img,x,v) cimg_for5V(img,v) cimg_for5X(img,x)
837
#define cimg_for5YZ(img,y,z) cimg_for5Z(img,z) cimg_for5Y(img,y)
838
#define cimg_for5YV(img,y,v) cimg_for5V(img,v) cimg_for5Y(img,y)
839
#define cimg_for5ZV(img,z,v) cimg_for5V(img,v) cimg_for5Z(img,z)
840
#define cimg_for5XYZ(img,x,y,z) cimg_for5Z(img,z) cimg_for5XY(img,x,y)
841
#define cimg_for5XZV(img,x,z,v) cimg_for5V(img,v) cimg_for5XZ(img,x,z)
842
#define cimg_for5YZV(img,y,z,v) cimg_for5V(img,v) cimg_for5YZ(img,y,z)
843
#define cimg_for5XYZV(img,x,y,z,v) cimg_for5V(img,v) cimg_for5XYZ(img,x,y,z)
845
#define cimg_for_in5(bound,i0,i1,i) \
846
for (int i = (int)(i0)<0?0:(int)(i0), \
847
_p2##i = i-2<0?0:i-2, \
848
_p1##i = i-1<0?0:i-1, \
849
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1, \
850
_n2##i = i+2>=(int)(bound)?(int)(bound)-1:i+2; \
851
i<=(int)(i1) && (_n2##i<(int)(bound) || _n1##i==--_n2##i || i==(_n2##i = --_n1##i)); \
852
_p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i)
853
#define cimg_for_in5X(img,x0,x1,x) cimg_for_in5((img).width,x0,x1,x)
854
#define cimg_for_in5Y(img,y0,y1,y) cimg_for_in5((img).height,y0,y1,y)
855
#define cimg_for_in5Z(img,z0,z1,z) cimg_for_in5((img).depth,z0,z1,z)
856
#define cimg_for_in5V(img,v0,v1,v) cimg_for_in5((img).dim,v0,v1,v)
857
#define cimg_for_in5XY(img,x0,y0,x1,y1,x,y) cimg_for_in5Y(img,y0,y1,y) cimg_for_in5X(img,x0,x1,x)
858
#define cimg_for_in5XZ(img,x0,z0,x1,z1,x,z) cimg_for_in5Z(img,z0,z1,z) cimg_for_in5X(img,x0,x1,x)
859
#define cimg_for_in5XV(img,x0,v0,x1,v1,x,v) cimg_for_in5V(img,v0,v1,v) cimg_for_in5X(img,x0,x1,x)
860
#define cimg_for_in5YZ(img,y0,z0,y1,z1,y,z) cimg_for_in5Z(img,z0,z1,z) cimg_for_in5Y(img,y0,y1,y)
861
#define cimg_for_in5YV(img,y0,v0,y1,v1,y,v) cimg_for_in5V(img,v0,v1,v) cimg_for_in5Y(img,y0,y1,y)
862
#define cimg_for_in5ZV(img,z0,v0,z1,v1,z,v) cimg_for_in5V(img,v0,v1,v) cimg_for_in5Z(img,z0,z1,z)
863
#define cimg_for_in5XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in5Z(img,z0,z1,z) cimg_for_in5XY(img,x0,y0,x1,y1,x,y)
864
#define cimg_for_in5XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in5V(img,v0,v1,v) cimg_for_in5XZ(img,x0,y0,x1,y1,x,z)
865
#define cimg_for_in5YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in5V(img,v0,v1,v) cimg_for_in5YZ(img,y0,z0,y1,z1,y,z)
866
#define cimg_for_in5XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in5V(img,v0,v1,v) cimg_for_in5XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
868
#define cimg_for6(bound,i) \
869
for (int i = 0, _p2##i = 0, _p1##i = 0, \
870
_n1##i = 1>=(bound)?(int)(bound)-1:1, \
871
_n2##i = 2>=(bound)?(int)(bound)-1:2, \
872
_n3##i = 3>=(bound)?(int)(bound)-1:3; \
873
_n3##i<(int)(bound) || _n2##i==--_n3##i || _n1##i==--_n2##i || i==(_n3##i = _n2##i = --_n1##i); \
874
_p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i)
875
#define cimg_for6X(img,x) cimg_for6((img).width,x)
876
#define cimg_for6Y(img,y) cimg_for6((img).height,y)
877
#define cimg_for6Z(img,z) cimg_for6((img).depth,z)
878
#define cimg_for6V(img,v) cimg_for6((img).dim,v)
879
#define cimg_for6XY(img,x,y) cimg_for6Y(img,y) cimg_for6X(img,x)
880
#define cimg_for6XZ(img,x,z) cimg_for6Z(img,z) cimg_for6X(img,x)
881
#define cimg_for6XV(img,x,v) cimg_for6V(img,v) cimg_for6X(img,x)
882
#define cimg_for6YZ(img,y,z) cimg_for6Z(img,z) cimg_for6Y(img,y)
883
#define cimg_for6YV(img,y,v) cimg_for6V(img,v) cimg_for6Y(img,y)
884
#define cimg_for6ZV(img,z,v) cimg_for6V(img,v) cimg_for6Z(img,z)
885
#define cimg_for6XYZ(img,x,y,z) cimg_for6Z(img,z) cimg_for6XY(img,x,y)
886
#define cimg_for6XZV(img,x,z,v) cimg_for6V(img,v) cimg_for6XZ(img,x,z)
887
#define cimg_for6YZV(img,y,z,v) cimg_for6V(img,v) cimg_for6YZ(img,y,z)
888
#define cimg_for6XYZV(img,x,y,z,v) cimg_for6V(img,v) cimg_for6XYZ(img,x,y,z)
890
#define cimg_for_in6(bound,i0,i1,i) \
891
for (int i = (int)(i0)<0?0:(int)(i0), \
892
_p2##i = i-2<0?0:i-2, \
893
_p1##i = i-1<0?0:i-1, \
894
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1, \
895
_n2##i = i+2>=(int)(bound)?(int)(bound)-1:i+2, \
896
_n3##i = i+3>=(int)(bound)?(int)(bound)-1:i+3; \
897
i<=(int)(i1) && (_n3##i<(int)(bound) || _n2##i==--_n3##i || _n1##i==--_n2##i || i==(_n3##i = _n2##i = --_n1##i)); \
898
_p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i)
899
#define cimg_for_in6X(img,x0,x1,x) cimg_for_in6((img).width,x0,x1,x)
900
#define cimg_for_in6Y(img,y0,y1,y) cimg_for_in6((img).height,y0,y1,y)
901
#define cimg_for_in6Z(img,z0,z1,z) cimg_for_in6((img).depth,z0,z1,z)
902
#define cimg_for_in6V(img,v0,v1,v) cimg_for_in6((img).dim,v0,v1,v)
903
#define cimg_for_in6XY(img,x0,y0,x1,y1,x,y) cimg_for_in6Y(img,y0,y1,y) cimg_for_in6X(img,x0,x1,x)
904
#define cimg_for_in6XZ(img,x0,z0,x1,z1,x,z) cimg_for_in6Z(img,z0,z1,z) cimg_for_in6X(img,x0,x1,x)
905
#define cimg_for_in6XV(img,x0,v0,x1,v1,x,v) cimg_for_in6V(img,v0,v1,v) cimg_for_in6X(img,x0,x1,x)
906
#define cimg_for_in6YZ(img,y0,z0,y1,z1,y,z) cimg_for_in6Z(img,z0,z1,z) cimg_for_in6Y(img,y0,y1,y)
907
#define cimg_for_in6YV(img,y0,v0,y1,v1,y,v) cimg_for_in6V(img,v0,v1,v) cimg_for_in6Y(img,y0,y1,y)
908
#define cimg_for_in6ZV(img,z0,v0,z1,v1,z,v) cimg_for_in6V(img,v0,v1,v) cimg_for_in6Z(img,z0,z1,z)
909
#define cimg_for_in6XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in6Z(img,z0,z1,z) cimg_for_in6XY(img,x0,y0,x1,y1,x,y)
910
#define cimg_for_in6XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in6V(img,v0,v1,v) cimg_for_in6XZ(img,x0,y0,x1,y1,x,z)
911
#define cimg_for_in6YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in6V(img,v0,v1,v) cimg_for_in6YZ(img,y0,z0,y1,z1,y,z)
912
#define cimg_for_in6XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in6V(img,v0,v1,v) cimg_for_in6XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
914
#define cimg_for7(bound,i) \
915
for (int i = 0, _p3##i = 0, _p2##i = 0, _p1##i = 0, \
916
_n1##i = 1>=(bound)?(int)(bound)-1:1, \
917
_n2##i = 2>=(bound)?(int)(bound)-1:2, \
918
_n3##i = 3>=(bound)?(int)(bound)-1:3; \
919
_n3##i<(int)(bound) || _n2##i==--_n3##i || _n1##i==--_n2##i || i==(_n3##i = _n2##i = --_n1##i); \
920
_p3##i = _p2##i, _p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i)
921
#define cimg_for7X(img,x) cimg_for7((img).width,x)
922
#define cimg_for7Y(img,y) cimg_for7((img).height,y)
923
#define cimg_for7Z(img,z) cimg_for7((img).depth,z)
924
#define cimg_for7V(img,v) cimg_for7((img).dim,v)
925
#define cimg_for7XY(img,x,y) cimg_for7Y(img,y) cimg_for7X(img,x)
926
#define cimg_for7XZ(img,x,z) cimg_for7Z(img,z) cimg_for7X(img,x)
927
#define cimg_for7XV(img,x,v) cimg_for7V(img,v) cimg_for7X(img,x)
928
#define cimg_for7YZ(img,y,z) cimg_for7Z(img,z) cimg_for7Y(img,y)
929
#define cimg_for7YV(img,y,v) cimg_for7V(img,v) cimg_for7Y(img,y)
930
#define cimg_for7ZV(img,z,v) cimg_for7V(img,v) cimg_for7Z(img,z)
931
#define cimg_for7XYZ(img,x,y,z) cimg_for7Z(img,z) cimg_for7XY(img,x,y)
932
#define cimg_for7XZV(img,x,z,v) cimg_for7V(img,v) cimg_for7XZ(img,x,z)
933
#define cimg_for7YZV(img,y,z,v) cimg_for7V(img,v) cimg_for7YZ(img,y,z)
934
#define cimg_for7XYZV(img,x,y,z,v) cimg_for7V(img,v) cimg_for7XYZ(img,x,y,z)
936
#define cimg_for_in7(bound,i0,i1,i) \
937
for (int i = (int)(i0)<0?0:(int)(i0), \
938
_p3##i = i-3<0?0:i-3, \
939
_p2##i = i-2<0?0:i-2, \
940
_p1##i = i-1<0?0:i-1, \
941
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1, \
942
_n2##i = i+2>=(int)(bound)?(int)(bound)-1:i+2, \
943
_n3##i = i+3>=(int)(bound)?(int)(bound)-1:i+3; \
944
i<=(int)(i1) && (_n3##i<(int)(bound) || _n2##i==--_n3##i || _n1##i==--_n2##i || i==(_n3##i = _n2##i = --_n1##i)); \
945
_p3##i = _p2##i, _p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i)
946
#define cimg_for_in7X(img,x0,x1,x) cimg_for_in7((img).width,x0,x1,x)
947
#define cimg_for_in7Y(img,y0,y1,y) cimg_for_in7((img).height,y0,y1,y)
948
#define cimg_for_in7Z(img,z0,z1,z) cimg_for_in7((img).depth,z0,z1,z)
949
#define cimg_for_in7V(img,v0,v1,v) cimg_for_in7((img).dim,v0,v1,v)
950
#define cimg_for_in7XY(img,x0,y0,x1,y1,x,y) cimg_for_in7Y(img,y0,y1,y) cimg_for_in7X(img,x0,x1,x)
951
#define cimg_for_in7XZ(img,x0,z0,x1,z1,x,z) cimg_for_in7Z(img,z0,z1,z) cimg_for_in7X(img,x0,x1,x)
952
#define cimg_for_in7XV(img,x0,v0,x1,v1,x,v) cimg_for_in7V(img,v0,v1,v) cimg_for_in7X(img,x0,x1,x)
953
#define cimg_for_in7YZ(img,y0,z0,y1,z1,y,z) cimg_for_in7Z(img,z0,z1,z) cimg_for_in7Y(img,y0,y1,y)
954
#define cimg_for_in7YV(img,y0,v0,y1,v1,y,v) cimg_for_in7V(img,v0,v1,v) cimg_for_in7Y(img,y0,y1,y)
955
#define cimg_for_in7ZV(img,z0,v0,z1,v1,z,v) cimg_for_in7V(img,v0,v1,v) cimg_for_in7Z(img,z0,z1,z)
956
#define cimg_for_in7XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in7Z(img,z0,z1,z) cimg_for_in7XY(img,x0,y0,x1,y1,x,y)
957
#define cimg_for_in7XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in7V(img,v0,v1,v) cimg_for_in7XZ(img,x0,y0,x1,y1,x,z)
958
#define cimg_for_in7YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in7V(img,v0,v1,v) cimg_for_in7YZ(img,y0,z0,y1,z1,y,z)
959
#define cimg_for_in7XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in7V(img,v0,v1,v) cimg_for_in7XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
961
#define cimg_for8(bound,i) \
962
for (int i = 0, _p3##i = 0, _p2##i = 0, _p1##i = 0, \
963
_n1##i = 1>=(bound)?(int)(bound)-1:1, \
964
_n2##i = 2>=(bound)?(int)(bound)-1:2, \
965
_n3##i = 3>=(bound)?(int)(bound)-1:3, \
966
_n4##i = 4>=(bound)?(int)(bound)-1:4; \
967
_n4##i<(int)(bound) || _n3##i==--_n4##i || _n2##i==--_n3##i || _n1##i==--_n2##i || \
968
i==(_n4##i = _n3##i = _n2##i = --_n1##i); \
969
_p3##i = _p2##i, _p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i, ++_n4##i)
970
#define cimg_for8X(img,x) cimg_for8((img).width,x)
971
#define cimg_for8Y(img,y) cimg_for8((img).height,y)
972
#define cimg_for8Z(img,z) cimg_for8((img).depth,z)
973
#define cimg_for8V(img,v) cimg_for8((img).dim,v)
974
#define cimg_for8XY(img,x,y) cimg_for8Y(img,y) cimg_for8X(img,x)
975
#define cimg_for8XZ(img,x,z) cimg_for8Z(img,z) cimg_for8X(img,x)
976
#define cimg_for8XV(img,x,v) cimg_for8V(img,v) cimg_for8X(img,x)
977
#define cimg_for8YZ(img,y,z) cimg_for8Z(img,z) cimg_for8Y(img,y)
978
#define cimg_for8YV(img,y,v) cimg_for8V(img,v) cimg_for8Y(img,y)
979
#define cimg_for8ZV(img,z,v) cimg_for8V(img,v) cimg_for8Z(img,z)
980
#define cimg_for8XYZ(img,x,y,z) cimg_for8Z(img,z) cimg_for8XY(img,x,y)
981
#define cimg_for8XZV(img,x,z,v) cimg_for8V(img,v) cimg_for8XZ(img,x,z)
982
#define cimg_for8YZV(img,y,z,v) cimg_for8V(img,v) cimg_for8YZ(img,y,z)
983
#define cimg_for8XYZV(img,x,y,z,v) cimg_for8V(img,v) cimg_for8XYZ(img,x,y,z)
985
#define cimg_for_in8(bound,i0,i1,i) \
986
for (int i = (int)(i0)<0?0:(int)(i0), \
987
_p3##i = i-3<0?0:i-3, \
988
_p2##i = i-2<0?0:i-2, \
989
_p1##i = i-1<0?0:i-1, \
990
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1, \
991
_n2##i = i+2>=(int)(bound)?(int)(bound)-1:i+2, \
992
_n3##i = i+3>=(int)(bound)?(int)(bound)-1:i+3, \
993
_n4##i = i+4>=(int)(bound)?(int)(bound)-1:i+4; \
994
i<=(int)(i1) && (_n4##i<(int)(bound) || _n3##i==--_n4##i || _n2##i==--_n3##i || _n1##i==--_n2##i || \
995
i==(_n4##i = _n3##i = _n2##i = --_n1##i)); \
996
_p3##i = _p2##i, _p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i, ++_n4##i)
997
#define cimg_for_in8X(img,x0,x1,x) cimg_for_in8((img).width,x0,x1,x)
998
#define cimg_for_in8Y(img,y0,y1,y) cimg_for_in8((img).height,y0,y1,y)
999
#define cimg_for_in8Z(img,z0,z1,z) cimg_for_in8((img).depth,z0,z1,z)
1000
#define cimg_for_in8V(img,v0,v1,v) cimg_for_in8((img).dim,v0,v1,v)
1001
#define cimg_for_in8XY(img,x0,y0,x1,y1,x,y) cimg_for_in8Y(img,y0,y1,y) cimg_for_in8X(img,x0,x1,x)
1002
#define cimg_for_in8XZ(img,x0,z0,x1,z1,x,z) cimg_for_in8Z(img,z0,z1,z) cimg_for_in8X(img,x0,x1,x)
1003
#define cimg_for_in8XV(img,x0,v0,x1,v1,x,v) cimg_for_in8V(img,v0,v1,v) cimg_for_in8X(img,x0,x1,x)
1004
#define cimg_for_in8YZ(img,y0,z0,y1,z1,y,z) cimg_for_in8Z(img,z0,z1,z) cimg_for_in8Y(img,y0,y1,y)
1005
#define cimg_for_in8YV(img,y0,v0,y1,v1,y,v) cimg_for_in8V(img,v0,v1,v) cimg_for_in8Y(img,y0,y1,y)
1006
#define cimg_for_in8ZV(img,z0,v0,z1,v1,z,v) cimg_for_in8V(img,v0,v1,v) cimg_for_in8Z(img,z0,z1,z)
1007
#define cimg_for_in8XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in8Z(img,z0,z1,z) cimg_for_in8XY(img,x0,y0,x1,y1,x,y)
1008
#define cimg_for_in8XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in8V(img,v0,v1,v) cimg_for_in8XZ(img,x0,y0,x1,y1,x,z)
1009
#define cimg_for_in8YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in8V(img,v0,v1,v) cimg_for_in8YZ(img,y0,z0,y1,z1,y,z)
1010
#define cimg_for_in8XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in8V(img,v0,v1,v) cimg_for_in8XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
1012
#define cimg_for9(bound,i) \
1013
for (int i = 0, _p4##i = 0, _p3##i = 0, _p2##i = 0, _p1##i = 0, \
1014
_n1##i = 1>=(int)(bound)?(int)(bound)-1:1, \
1015
_n2##i = 2>=(int)(bound)?(int)(bound)-1:2, \
1016
_n3##i = 3>=(int)(bound)?(int)(bound)-1:3, \
1017
_n4##i = 4>=(int)(bound)?(int)(bound)-1:4; \
1018
_n4##i<(int)(bound) || _n3##i==--_n4##i || _n2##i==--_n3##i || _n1##i==--_n2##i || \
1019
i==(_n4##i = _n3##i = _n2##i = --_n1##i); \
1020
_p4##i = _p3##i, _p3##i = _p2##i, _p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i, ++_n4##i)
1021
#define cimg_for9X(img,x) cimg_for9((img).width,x)
1022
#define cimg_for9Y(img,y) cimg_for9((img).height,y)
1023
#define cimg_for9Z(img,z) cimg_for9((img).depth,z)
1024
#define cimg_for9V(img,v) cimg_for9((img).dim,v)
1025
#define cimg_for9XY(img,x,y) cimg_for9Y(img,y) cimg_for9X(img,x)
1026
#define cimg_for9XZ(img,x,z) cimg_for9Z(img,z) cimg_for9X(img,x)
1027
#define cimg_for9XV(img,x,v) cimg_for9V(img,v) cimg_for9X(img,x)
1028
#define cimg_for9YZ(img,y,z) cimg_for9Z(img,z) cimg_for9Y(img,y)
1029
#define cimg_for9YV(img,y,v) cimg_for9V(img,v) cimg_for9Y(img,y)
1030
#define cimg_for9ZV(img,z,v) cimg_for9V(img,v) cimg_for9Z(img,z)
1031
#define cimg_for9XYZ(img,x,y,z) cimg_for9Z(img,z) cimg_for9XY(img,x,y)
1032
#define cimg_for9XZV(img,x,z,v) cimg_for9V(img,v) cimg_for9XZ(img,x,z)
1033
#define cimg_for9YZV(img,y,z,v) cimg_for9V(img,v) cimg_for9YZ(img,y,z)
1034
#define cimg_for9XYZV(img,x,y,z,v) cimg_for9V(img,v) cimg_for9XYZ(img,x,y,z)
1036
#define cimg_for_in9(bound,i0,i1,i) \
1037
for (int i = (int)(i0)<0?0:(int)(i0), \
1038
_p4##i = i-4<0?0:i-4, \
1039
_p3##i = i-3<0?0:i-3, \
1040
_p2##i = i-2<0?0:i-2, \
1041
_p1##i = i-1<0?0:i-1, \
1042
_n1##i = i+1>=(int)(bound)?(int)(bound)-1:i+1, \
1043
_n2##i = i+2>=(int)(bound)?(int)(bound)-1:i+2, \
1044
_n3##i = i+3>=(int)(bound)?(int)(bound)-1:i+3, \
1045
_n4##i = i+4>=(int)(bound)?(int)(bound)-1:i+4; \
1046
i<=(int)(i1) && (_n4##i<(int)(bound) || _n3##i==--_n4##i || _n2##i==--_n3##i || _n1##i==--_n2##i || \
1047
i==(_n4##i = _n3##i = _n2##i = --_n1##i)); \
1048
_p4##i = _p3##i, _p3##i = _p2##i, _p2##i = _p1##i, _p1##i = i++, ++_n1##i, ++_n2##i, ++_n3##i, ++_n4##i)
1049
#define cimg_for_in9X(img,x0,x1,x) cimg_for_in9((img).width,x0,x1,x)
1050
#define cimg_for_in9Y(img,y0,y1,y) cimg_for_in9((img).height,y0,y1,y)
1051
#define cimg_for_in9Z(img,z0,z1,z) cimg_for_in9((img).depth,z0,z1,z)
1052
#define cimg_for_in9V(img,v0,v1,v) cimg_for_in9((img).dim,v0,v1,v)
1053
#define cimg_for_in9XY(img,x0,y0,x1,y1,x,y) cimg_for_in9Y(img,y0,y1,y) cimg_for_in9X(img,x0,x1,x)
1054
#define cimg_for_in9XZ(img,x0,z0,x1,z1,x,z) cimg_for_in9Z(img,z0,z1,z) cimg_for_in9X(img,x0,x1,x)
1055
#define cimg_for_in9XV(img,x0,v0,x1,v1,x,v) cimg_for_in9V(img,v0,v1,v) cimg_for_in9X(img,x0,x1,x)
1056
#define cimg_for_in9YZ(img,y0,z0,y1,z1,y,z) cimg_for_in9Z(img,z0,z1,z) cimg_for_in9Y(img,y0,y1,y)
1057
#define cimg_for_in9YV(img,y0,v0,y1,v1,y,v) cimg_for_in9V(img,v0,v1,v) cimg_for_in9Y(img,y0,y1,y)
1058
#define cimg_for_in9ZV(img,z0,v0,z1,v1,z,v) cimg_for_in9V(img,v0,v1,v) cimg_for_in9Z(img,z0,z1,z)
1059
#define cimg_for_in9XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z) cimg_for_in9Z(img,z0,z1,z) cimg_for_in9XY(img,x0,y0,x1,y1,x,y)
1060
#define cimg_for_in9XZV(img,x0,z0,v0,x1,y1,v1,x,z,v) cimg_for_in9V(img,v0,v1,v) cimg_for_in9XZ(img,x0,y0,x1,y1,x,z)
1061
#define cimg_for_in9YZV(img,y0,z0,v0,y1,z1,v1,y,z,v) cimg_for_in9V(img,v0,v1,v) cimg_for_in9YZ(img,y0,z0,y1,z1,y,z)
1062
#define cimg_for_in9XYZV(img,x0,y0,z0,v0,x1,y1,z1,v1,x,y,z,v) cimg_for_in9V(img,v0,v1,v) cimg_for_in9XYZ(img,x0,y0,z0,x1,y1,z1,x,y,z)
1064
#define cimg_for2x2(img,x,y,z,v,I) \
1065
cimg_for2((img).height,y) for (int x = 0, \
1067
(I[0] = (img)(0,y,z,v)), \
1068
(I[2] = (img)(0,_n1##y,z,v)), \
1069
1>=(img).width?(int)((img).width)-1:1); \
1070
(_n1##x<(int)((img).width) && ( \
1071
(I[1] = (img)(_n1##x,y,z,v)), \
1072
(I[3] = (img)(_n1##x,_n1##y,z,v)),1)) || \
1078
#define cimg_for_in2x2(img,x0,y0,x1,y1,x,y,z,v,I) \
1079
cimg_for_in2((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1081
(I[0] = (img)(x,y,z,v)), \
1082
(I[2] = (img)(x,_n1##y,z,v)), \
1083
x+1>=(int)(img).width?(int)((img).width)-1:x+1); \
1084
x<=(int)(x1) && ((_n1##x<(int)((img).width) && ( \
1085
(I[1] = (img)(_n1##x,y,z,v)), \
1086
(I[3] = (img)(_n1##x,_n1##y,z,v)),1)) || \
1092
#define cimg_for3x3(img,x,y,z,v,I) \
1093
cimg_for3((img).height,y) for (int x = 0, \
1096
(I[0] = I[1] = (img)(0,_p1##y,z,v)), \
1097
(I[3] = I[4] = (img)(0,y,z,v)), \
1098
(I[6] = I[7] = (img)(0,_n1##y,z,v)), \
1099
1>=(img).width?(int)((img).width)-1:1); \
1100
(_n1##x<(int)((img).width) && ( \
1101
(I[2] = (img)(_n1##x,_p1##y,z,v)), \
1102
(I[5] = (img)(_n1##x,y,z,v)), \
1103
(I[8] = (img)(_n1##x,_n1##y,z,v)),1)) || \
1105
I[0] = I[1], I[1] = I[2], \
1106
I[3] = I[4], I[4] = I[5], \
1107
I[6] = I[7], I[7] = I[8], \
1108
_p1##x = x++, ++_n1##x)
1110
#define cimg_for_in3x3(img,x0,y0,x1,y1,x,y,z,v,I) \
1111
cimg_for_in3((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1112
_p1##x = x-1<0?0:x-1, \
1114
(I[0] = (img)(_p1##x,_p1##y,z,v)), \
1115
(I[3] = (img)(_p1##x,y,z,v)), \
1116
(I[6] = (img)(_p1##x,_n1##y,z,v)), \
1117
(I[1] = (img)(x,_p1##y,z,v)), \
1118
(I[4] = (img)(x,y,z,v)), \
1119
(I[7] = (img)(x,_n1##y,z,v)), \
1120
x+1>=(int)(img).width?(int)((img).width)-1:x+1); \
1121
x<=(int)(x1) && ((_n1##x<(int)((img).width) && ( \
1122
(I[2] = (img)(_n1##x,_p1##y,z,v)), \
1123
(I[5] = (img)(_n1##x,y,z,v)), \
1124
(I[8] = (img)(_n1##x,_n1##y,z,v)),1)) || \
1126
I[0] = I[1], I[1] = I[2], \
1127
I[3] = I[4], I[4] = I[5], \
1128
I[6] = I[7], I[7] = I[8], \
1129
_p1##x = x++, ++_n1##x)
1131
#define cimg_for4x4(img,x,y,z,v,I) \
1132
cimg_for4((img).height,y) for (int x = 0, \
1134
_n1##x = 1>=(img).width?(int)((img).width)-1:1, \
1136
(I[0] = I[1] = (img)(0,_p1##y,z,v)), \
1137
(I[4] = I[5] = (img)(0,y,z,v)), \
1138
(I[8] = I[9] = (img)(0,_n1##y,z,v)), \
1139
(I[12] = I[13] = (img)(0,_n2##y,z,v)), \
1140
(I[2] = (img)(_n1##x,_p1##y,z,v)), \
1141
(I[6] = (img)(_n1##x,y,z,v)), \
1142
(I[10] = (img)(_n1##x,_n1##y,z,v)), \
1143
(I[14] = (img)(_n1##x,_n2##y,z,v)), \
1144
2>=(img).width?(int)((img).width)-1:2); \
1145
(_n2##x<(int)((img).width) && ( \
1146
(I[3] = (img)(_n2##x,_p1##y,z,v)), \
1147
(I[7] = (img)(_n2##x,y,z,v)), \
1148
(I[11] = (img)(_n2##x,_n1##y,z,v)), \
1149
(I[15] = (img)(_n2##x,_n2##y,z,v)),1)) || \
1150
_n1##x==--_n2##x || x==(_n2##x = --_n1##x); \
1151
I[0] = I[1], I[1] = I[2], I[2] = I[3], \
1152
I[4] = I[5], I[5] = I[6], I[6] = I[7], \
1153
I[8] = I[9], I[9] = I[10], I[10] = I[11], \
1154
I[12] = I[13], I[13] = I[14], I[14] = I[15], \
1155
_p1##x = x++, ++_n1##x, ++_n2##x)
1157
#define cimg_for_in4x4(img,x0,y0,x1,y1,x,y,z,v,I) \
1158
cimg_for_in4((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1159
_p1##x = x-1<0?0:x-1, \
1160
_n1##x = x+1>=(int)(img).width?(int)((img).width)-1:x+1, \
1162
(I[0] = (img)(_p1##x,_p1##y,z,v)), \
1163
(I[4] = (img)(_p1##x,y,z,v)), \
1164
(I[8] = (img)(_p1##x,_n1##y,z,v)), \
1165
(I[12] = (img)(_p1##x,_n2##y,z,v)), \
1166
(I[1] = (img)(x,_p1##y,z,v)), \
1167
(I[5] = (img)(x,y,z,v)), \
1168
(I[9] = (img)(x,_n1##y,z,v)), \
1169
(I[13] = (img)(x,_n2##y,z,v)), \
1170
(I[2] = (img)(_n1##x,_p1##y,z,v)), \
1171
(I[6] = (img)(_n1##x,y,z,v)), \
1172
(I[10] = (img)(_n1##x,_n1##y,z,v)), \
1173
(I[14] = (img)(_n1##x,_n2##y,z,v)), \
1174
x+2>=(int)(img).width?(int)((img).width)-1:x+2); \
1175
x<=(int)(x1) && ((_n2##x<(int)((img).width) && ( \
1176
(I[3] = (img)(_n2##x,_p1##y,z,v)), \
1177
(I[7] = (img)(_n2##x,y,z,v)), \
1178
(I[11] = (img)(_n2##x,_n1##y,z,v)), \
1179
(I[15] = (img)(_n2##x,_n2##y,z,v)),1)) || \
1180
_n1##x==--_n2##x || x==(_n2##x = --_n1##x)); \
1181
I[0] = I[1], I[1] = I[2], I[2] = I[3], \
1182
I[4] = I[5], I[5] = I[6], I[6] = I[7], \
1183
I[8] = I[9], I[9] = I[10], I[10] = I[11], \
1184
I[12] = I[13], I[13] = I[14], I[14] = I[15], \
1185
_p1##x = x++, ++_n1##x, ++_n2##x)
1187
#define cimg_for5x5(img,x,y,z,v,I) \
1188
cimg_for5((img).height,y) for (int x = 0, \
1189
_p2##x = 0, _p1##x = 0, \
1190
_n1##x = 1>=(img).width?(int)((img).width)-1:1, \
1192
(I[0] = I[1] = I[2] = (img)(0,_p2##y,z,v)), \
1193
(I[5] = I[6] = I[7] = (img)(0,_p1##y,z,v)), \
1194
(I[10] = I[11] = I[12] = (img)(0,y,z,v)), \
1195
(I[15] = I[16] = I[17] = (img)(0,_n1##y,z,v)), \
1196
(I[20] = I[21] = I[22] = (img)(0,_n2##y,z,v)), \
1197
(I[3] = (img)(_n1##x,_p2##y,z,v)), \
1198
(I[8] = (img)(_n1##x,_p1##y,z,v)), \
1199
(I[13] = (img)(_n1##x,y,z,v)), \
1200
(I[18] = (img)(_n1##x,_n1##y,z,v)), \
1201
(I[23] = (img)(_n1##x,_n2##y,z,v)), \
1202
2>=(img).width?(int)((img).width)-1:2); \
1203
(_n2##x<(int)((img).width) && ( \
1204
(I[4] = (img)(_n2##x,_p2##y,z,v)), \
1205
(I[9] = (img)(_n2##x,_p1##y,z,v)), \
1206
(I[14] = (img)(_n2##x,y,z,v)), \
1207
(I[19] = (img)(_n2##x,_n1##y,z,v)), \
1208
(I[24] = (img)(_n2##x,_n2##y,z,v)),1)) || \
1209
_n1##x==--_n2##x || x==(_n2##x = --_n1##x); \
1210
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], \
1211
I[5] = I[6], I[6] = I[7], I[7] = I[8], I[8] = I[9], \
1212
I[10] = I[11], I[11] = I[12], I[12] = I[13], I[13] = I[14], \
1213
I[15] = I[16], I[16] = I[17], I[17] = I[18], I[18] = I[19], \
1214
I[20] = I[21], I[21] = I[22], I[22] = I[23], I[23] = I[24], \
1215
_p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x)
1217
#define cimg_for_in5x5(img,x0,y0,x1,y1,x,y,z,v,I) \
1218
cimg_for_in5((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1219
_p2##x = x-2<0?0:x-2, \
1220
_p1##x = x-1<0?0:x-1, \
1221
_n1##x = x+1>=(int)(img).width?(int)((img).width)-1:x+1, \
1223
(I[0] = (img)(_p2##x,_p2##y,z,v)), \
1224
(I[5] = (img)(_p2##x,_p1##y,z,v)), \
1225
(I[10] = (img)(_p2##x,y,z,v)), \
1226
(I[15] = (img)(_p2##x,_n1##y,z,v)), \
1227
(I[20] = (img)(_p2##x,_n2##y,z,v)), \
1228
(I[1] = (img)(_p1##x,_p2##y,z,v)), \
1229
(I[6] = (img)(_p1##x,_p1##y,z,v)), \
1230
(I[11] = (img)(_p1##x,y,z,v)), \
1231
(I[16] = (img)(_p1##x,_n1##y,z,v)), \
1232
(I[21] = (img)(_p1##x,_n2##y,z,v)), \
1233
(I[2] = (img)(x,_p2##y,z,v)), \
1234
(I[7] = (img)(x,_p1##y,z,v)), \
1235
(I[12] = (img)(x,y,z,v)), \
1236
(I[17] = (img)(x,_n1##y,z,v)), \
1237
(I[22] = (img)(x,_n2##y,z,v)), \
1238
(I[3] = (img)(_n1##x,_p2##y,z,v)), \
1239
(I[8] = (img)(_n1##x,_p1##y,z,v)), \
1240
(I[13] = (img)(_n1##x,y,z,v)), \
1241
(I[18] = (img)(_n1##x,_n1##y,z,v)), \
1242
(I[23] = (img)(_n1##x,_n2##y,z,v)), \
1243
x+2>=(int)(img).width?(int)((img).width)-1:x+2); \
1244
x<=(int)(x1) && ((_n2##x<(int)((img).width) && ( \
1245
(I[4] = (img)(_n2##x,_p2##y,z,v)), \
1246
(I[9] = (img)(_n2##x,_p1##y,z,v)), \
1247
(I[14] = (img)(_n2##x,y,z,v)), \
1248
(I[19] = (img)(_n2##x,_n1##y,z,v)), \
1249
(I[24] = (img)(_n2##x,_n2##y,z,v)),1)) || \
1250
_n1##x==--_n2##x || x==(_n2##x = --_n1##x)); \
1251
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], \
1252
I[5] = I[6], I[6] = I[7], I[7] = I[8], I[8] = I[9], \
1253
I[10] = I[11], I[11] = I[12], I[12] = I[13], I[13] = I[14], \
1254
I[15] = I[16], I[16] = I[17], I[17] = I[18], I[18] = I[19], \
1255
I[20] = I[21], I[21] = I[22], I[22] = I[23], I[23] = I[24], \
1256
_p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x)
1258
#define cimg_for6x6(img,x,y,z,v,I) \
1259
cimg_for6((img).height,y) for (int x = 0, \
1260
_p2##x = 0, _p1##x = 0, \
1261
_n1##x = 1>=(img).width?(int)((img).width)-1:1, \
1262
_n2##x = 2>=(img).width?(int)((img).width)-1:2, \
1264
(I[0] = I[1] = I[2] = (img)(0,_p2##y,z,v)), \
1265
(I[6] = I[7] = I[8] = (img)(0,_p1##y,z,v)), \
1266
(I[12] = I[13] = I[14] = (img)(0,y,z,v)), \
1267
(I[18] = I[19] = I[20] = (img)(0,_n1##y,z,v)), \
1268
(I[24] = I[25] = I[26] = (img)(0,_n2##y,z,v)), \
1269
(I[30] = I[31] = I[32] = (img)(0,_n3##y,z,v)), \
1270
(I[3] = (img)(_n1##x,_p2##y,z,v)), \
1271
(I[9] = (img)(_n1##x,_p1##y,z,v)), \
1272
(I[15] = (img)(_n1##x,y,z,v)), \
1273
(I[21] = (img)(_n1##x,_n1##y,z,v)), \
1274
(I[27] = (img)(_n1##x,_n2##y,z,v)), \
1275
(I[33] = (img)(_n1##x,_n3##y,z,v)), \
1276
(I[4] = (img)(_n2##x,_p2##y,z,v)), \
1277
(I[10] = (img)(_n2##x,_p1##y,z,v)), \
1278
(I[16] = (img)(_n2##x,y,z,v)), \
1279
(I[22] = (img)(_n2##x,_n1##y,z,v)), \
1280
(I[28] = (img)(_n2##x,_n2##y,z,v)), \
1281
(I[34] = (img)(_n2##x,_n3##y,z,v)), \
1282
3>=(img).width?(int)((img).width)-1:3); \
1283
(_n3##x<(int)((img).width) && ( \
1284
(I[5] = (img)(_n3##x,_p2##y,z,v)), \
1285
(I[11] = (img)(_n3##x,_p1##y,z,v)), \
1286
(I[17] = (img)(_n3##x,y,z,v)), \
1287
(I[23] = (img)(_n3##x,_n1##y,z,v)), \
1288
(I[29] = (img)(_n3##x,_n2##y,z,v)), \
1289
(I[35] = (img)(_n3##x,_n3##y,z,v)),1)) || \
1290
_n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n3## x = _n2##x = --_n1##x); \
1291
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], \
1292
I[6] = I[7], I[7] = I[8], I[8] = I[9], I[9] = I[10], I[10] = I[11], \
1293
I[12] = I[13], I[13] = I[14], I[14] = I[15], I[15] = I[16], I[16] = I[17], \
1294
I[18] = I[19], I[19] = I[20], I[20] = I[21], I[21] = I[22], I[22] = I[23], \
1295
I[24] = I[25], I[25] = I[26], I[26] = I[27], I[27] = I[28], I[28] = I[29], \
1296
I[30] = I[31], I[31] = I[32], I[32] = I[33], I[33] = I[34], I[34] = I[35], \
1297
_p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x)
1299
#define cimg_for_in6x6(img,x0,y0,x1,y1,x,y,z,v,I) \
1300
cimg_for_in6((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)x0, \
1301
_p2##x = x-2<0?0:x-2, \
1302
_p1##x = x-1<0?0:x-1, \
1303
_n1##x = x+1>=(int)(img).width?(int)((img).width)-1:x+1, \
1304
_n2##x = x+2>=(int)(img).width?(int)((img).width)-1:x+2, \
1306
(I[0] = (img)(_p2##x,_p2##y,z,v)), \
1307
(I[6] = (img)(_p2##x,_p1##y,z,v)), \
1308
(I[12] = (img)(_p2##x,y,z,v)), \
1309
(I[18] = (img)(_p2##x,_n1##y,z,v)), \
1310
(I[24] = (img)(_p2##x,_n2##y,z,v)), \
1311
(I[30] = (img)(_p2##x,_n3##y,z,v)), \
1312
(I[1] = (img)(_p1##x,_p2##y,z,v)), \
1313
(I[7] = (img)(_p1##x,_p1##y,z,v)), \
1314
(I[13] = (img)(_p1##x,y,z,v)), \
1315
(I[19] = (img)(_p1##x,_n1##y,z,v)), \
1316
(I[25] = (img)(_p1##x,_n2##y,z,v)), \
1317
(I[31] = (img)(_p1##x,_n3##y,z,v)), \
1318
(I[2] = (img)(x,_p2##y,z,v)), \
1319
(I[8] = (img)(x,_p1##y,z,v)), \
1320
(I[14] = (img)(x,y,z,v)), \
1321
(I[20] = (img)(x,_n1##y,z,v)), \
1322
(I[26] = (img)(x,_n2##y,z,v)), \
1323
(I[32] = (img)(x,_n3##y,z,v)), \
1324
(I[3] = (img)(_n1##x,_p2##y,z,v)), \
1325
(I[9] = (img)(_n1##x,_p1##y,z,v)), \
1326
(I[15] = (img)(_n1##x,y,z,v)), \
1327
(I[21] = (img)(_n1##x,_n1##y,z,v)), \
1328
(I[27] = (img)(_n1##x,_n2##y,z,v)), \
1329
(I[33] = (img)(_n1##x,_n3##y,z,v)), \
1330
(I[4] = (img)(_n2##x,_p2##y,z,v)), \
1331
(I[10] = (img)(_n2##x,_p1##y,z,v)), \
1332
(I[16] = (img)(_n2##x,y,z,v)), \
1333
(I[22] = (img)(_n2##x,_n1##y,z,v)), \
1334
(I[28] = (img)(_n2##x,_n2##y,z,v)), \
1335
(I[34] = (img)(_n2##x,_n3##y,z,v)), \
1336
x+3>=(int)(img).width?(int)((img).width)-1:x+3); \
1337
x<=(int)(x1) && ((_n3##x<(int)((img).width) && ( \
1338
(I[5] = (img)(_n3##x,_p2##y,z,v)), \
1339
(I[11] = (img)(_n3##x,_p1##y,z,v)), \
1340
(I[17] = (img)(_n3##x,y,z,v)), \
1341
(I[23] = (img)(_n3##x,_n1##y,z,v)), \
1342
(I[29] = (img)(_n3##x,_n2##y,z,v)), \
1343
(I[35] = (img)(_n3##x,_n3##y,z,v)),1)) || \
1344
_n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n3## x = _n2##x = --_n1##x)); \
1345
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], \
1346
I[6] = I[7], I[7] = I[8], I[8] = I[9], I[9] = I[10], I[10] = I[11], \
1347
I[12] = I[13], I[13] = I[14], I[14] = I[15], I[15] = I[16], I[16] = I[17], \
1348
I[18] = I[19], I[19] = I[20], I[20] = I[21], I[21] = I[22], I[22] = I[23], \
1349
I[24] = I[25], I[25] = I[26], I[26] = I[27], I[27] = I[28], I[28] = I[29], \
1350
I[30] = I[31], I[31] = I[32], I[32] = I[33], I[33] = I[34], I[34] = I[35], \
1351
_p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x)
1353
#define cimg_for7x7(img,x,y,z,v,I) \
1354
cimg_for7((img).height,y) for (int x = 0, \
1355
_p3##x = 0, _p2##x = 0, _p1##x = 0, \
1356
_n1##x = 1>=(img).width?(int)((img).width)-1:1, \
1357
_n2##x = 2>=(img).width?(int)((img).width)-1:2, \
1359
(I[0] = I[1] = I[2] = I[3] = (img)(0,_p3##y,z,v)), \
1360
(I[7] = I[8] = I[9] = I[10] = (img)(0,_p2##y,z,v)), \
1361
(I[14] = I[15] = I[16] = I[17] = (img)(0,_p1##y,z,v)), \
1362
(I[21] = I[22] = I[23] = I[24] = (img)(0,y,z,v)), \
1363
(I[28] = I[29] = I[30] = I[31] = (img)(0,_n1##y,z,v)), \
1364
(I[35] = I[36] = I[37] = I[38] = (img)(0,_n2##y,z,v)), \
1365
(I[42] = I[43] = I[44] = I[45] = (img)(0,_n3##y,z,v)), \
1366
(I[4] = (img)(_n1##x,_p3##y,z,v)), \
1367
(I[11] = (img)(_n1##x,_p2##y,z,v)), \
1368
(I[18] = (img)(_n1##x,_p1##y,z,v)), \
1369
(I[25] = (img)(_n1##x,y,z,v)), \
1370
(I[32] = (img)(_n1##x,_n1##y,z,v)), \
1371
(I[39] = (img)(_n1##x,_n2##y,z,v)), \
1372
(I[46] = (img)(_n1##x,_n3##y,z,v)), \
1373
(I[5] = (img)(_n2##x,_p3##y,z,v)), \
1374
(I[12] = (img)(_n2##x,_p2##y,z,v)), \
1375
(I[19] = (img)(_n2##x,_p1##y,z,v)), \
1376
(I[26] = (img)(_n2##x,y,z,v)), \
1377
(I[33] = (img)(_n2##x,_n1##y,z,v)), \
1378
(I[40] = (img)(_n2##x,_n2##y,z,v)), \
1379
(I[47] = (img)(_n2##x,_n3##y,z,v)), \
1380
3>=(img).width?(int)((img).width)-1:3); \
1381
(_n3##x<(int)((img).width) && ( \
1382
(I[6] = (img)(_n3##x,_p3##y,z,v)), \
1383
(I[13] = (img)(_n3##x,_p2##y,z,v)), \
1384
(I[20] = (img)(_n3##x,_p1##y,z,v)), \
1385
(I[27] = (img)(_n3##x,y,z,v)), \
1386
(I[34] = (img)(_n3##x,_n1##y,z,v)), \
1387
(I[41] = (img)(_n3##x,_n2##y,z,v)), \
1388
(I[48] = (img)(_n3##x,_n3##y,z,v)),1)) || \
1389
_n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n3##x = _n2##x = --_n1##x); \
1390
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], I[5] = I[6], \
1391
I[7] = I[8], I[8] = I[9], I[9] = I[10], I[10] = I[11], I[11] = I[12], I[12] = I[13], \
1392
I[14] = I[15], I[15] = I[16], I[16] = I[17], I[17] = I[18], I[18] = I[19], I[19] = I[20], \
1393
I[21] = I[22], I[22] = I[23], I[23] = I[24], I[24] = I[25], I[25] = I[26], I[26] = I[27], \
1394
I[28] = I[29], I[29] = I[30], I[30] = I[31], I[31] = I[32], I[32] = I[33], I[33] = I[34], \
1395
I[35] = I[36], I[36] = I[37], I[37] = I[38], I[38] = I[39], I[39] = I[40], I[40] = I[41], \
1396
I[42] = I[43], I[43] = I[44], I[44] = I[45], I[45] = I[46], I[46] = I[47], I[47] = I[48], \
1397
_p3##x = _p2##x, _p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x)
1399
#define cimg_for_in7x7(img,x0,y0,x1,y1,x,y,z,v,I) \
1400
cimg_for_in7((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1401
_p3##x = x-3<0?0:x-3, \
1402
_p2##x = x-2<0?0:x-2, \
1403
_p1##x = x-1<0?0:x-1, \
1404
_n1##x = x+1>=(int)(img).width?(int)((img).width)-1:x+1, \
1405
_n2##x = x+2>=(int)(img).width?(int)((img).width)-1:x+2, \
1407
(I[0] = (img)(_p3##x,_p3##y,z,v)), \
1408
(I[7] = (img)(_p3##x,_p2##y,z,v)), \
1409
(I[14] = (img)(_p3##x,_p1##y,z,v)), \
1410
(I[21] = (img)(_p3##x,y,z,v)), \
1411
(I[28] = (img)(_p3##x,_n1##y,z,v)), \
1412
(I[35] = (img)(_p3##x,_n2##y,z,v)), \
1413
(I[42] = (img)(_p3##x,_n3##y,z,v)), \
1414
(I[1] = (img)(_p2##x,_p3##y,z,v)), \
1415
(I[8] = (img)(_p2##x,_p2##y,z,v)), \
1416
(I[15] = (img)(_p2##x,_p1##y,z,v)), \
1417
(I[22] = (img)(_p2##x,y,z,v)), \
1418
(I[29] = (img)(_p2##x,_n1##y,z,v)), \
1419
(I[36] = (img)(_p2##x,_n2##y,z,v)), \
1420
(I[43] = (img)(_p2##x,_n3##y,z,v)), \
1421
(I[2] = (img)(_p1##x,_p3##y,z,v)), \
1422
(I[9] = (img)(_p1##x,_p2##y,z,v)), \
1423
(I[16] = (img)(_p1##x,_p1##y,z,v)), \
1424
(I[23] = (img)(_p1##x,y,z,v)), \
1425
(I[30] = (img)(_p1##x,_n1##y,z,v)), \
1426
(I[37] = (img)(_p1##x,_n2##y,z,v)), \
1427
(I[44] = (img)(_p1##x,_n3##y,z,v)), \
1428
(I[3] = (img)(x,_p3##y,z,v)), \
1429
(I[10] = (img)(x,_p2##y,z,v)), \
1430
(I[17] = (img)(x,_p1##y,z,v)), \
1431
(I[24] = (img)(x,y,z,v)), \
1432
(I[31] = (img)(x,_n1##y,z,v)), \
1433
(I[38] = (img)(x,_n2##y,z,v)), \
1434
(I[45] = (img)(x,_n3##y,z,v)), \
1435
(I[4] = (img)(_n1##x,_p3##y,z,v)), \
1436
(I[11] = (img)(_n1##x,_p2##y,z,v)), \
1437
(I[18] = (img)(_n1##x,_p1##y,z,v)), \
1438
(I[25] = (img)(_n1##x,y,z,v)), \
1439
(I[32] = (img)(_n1##x,_n1##y,z,v)), \
1440
(I[39] = (img)(_n1##x,_n2##y,z,v)), \
1441
(I[46] = (img)(_n1##x,_n3##y,z,v)), \
1442
(I[5] = (img)(_n2##x,_p3##y,z,v)), \
1443
(I[12] = (img)(_n2##x,_p2##y,z,v)), \
1444
(I[19] = (img)(_n2##x,_p1##y,z,v)), \
1445
(I[26] = (img)(_n2##x,y,z,v)), \
1446
(I[33] = (img)(_n2##x,_n1##y,z,v)), \
1447
(I[40] = (img)(_n2##x,_n2##y,z,v)), \
1448
(I[47] = (img)(_n2##x,_n3##y,z,v)), \
1449
x+3>=(int)(img).width?(int)((img).width)-1:x+3); \
1450
x<=(int)(x1) && ((_n3##x<(int)((img).width) && ( \
1451
(I[6] = (img)(_n3##x,_p3##y,z,v)), \
1452
(I[13] = (img)(_n3##x,_p2##y,z,v)), \
1453
(I[20] = (img)(_n3##x,_p1##y,z,v)), \
1454
(I[27] = (img)(_n3##x,y,z,v)), \
1455
(I[34] = (img)(_n3##x,_n1##y,z,v)), \
1456
(I[41] = (img)(_n3##x,_n2##y,z,v)), \
1457
(I[48] = (img)(_n3##x,_n3##y,z,v)),1)) || \
1458
_n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n3##x = _n2##x = --_n1##x)); \
1459
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], I[5] = I[6], \
1460
I[7] = I[8], I[8] = I[9], I[9] = I[10], I[10] = I[11], I[11] = I[12], I[12] = I[13], \
1461
I[14] = I[15], I[15] = I[16], I[16] = I[17], I[17] = I[18], I[18] = I[19], I[19] = I[20], \
1462
I[21] = I[22], I[22] = I[23], I[23] = I[24], I[24] = I[25], I[25] = I[26], I[26] = I[27], \
1463
I[28] = I[29], I[29] = I[30], I[30] = I[31], I[31] = I[32], I[32] = I[33], I[33] = I[34], \
1464
I[35] = I[36], I[36] = I[37], I[37] = I[38], I[38] = I[39], I[39] = I[40], I[40] = I[41], \
1465
I[42] = I[43], I[43] = I[44], I[44] = I[45], I[45] = I[46], I[46] = I[47], I[47] = I[48], \
1466
_p3##x = _p2##x, _p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x)
1468
#define cimg_for8x8(img,x,y,z,v,I) \
1469
cimg_for8((img).height,y) for (int x = 0, \
1470
_p3##x = 0, _p2##x = 0, _p1##x = 0, \
1471
_n1##x = 1>=((img).width)?(int)((img).width)-1:1, \
1472
_n2##x = 2>=((img).width)?(int)((img).width)-1:2, \
1473
_n3##x = 3>=((img).width)?(int)((img).width)-1:3, \
1475
(I[0] = I[1] = I[2] = I[3] = (img)(0,_p3##y,z,v)), \
1476
(I[8] = I[9] = I[10] = I[11] = (img)(0,_p2##y,z,v)), \
1477
(I[16] = I[17] = I[18] = I[19] = (img)(0,_p1##y,z,v)), \
1478
(I[24] = I[25] = I[26] = I[27] = (img)(0,y,z,v)), \
1479
(I[32] = I[33] = I[34] = I[35] = (img)(0,_n1##y,z,v)), \
1480
(I[40] = I[41] = I[42] = I[43] = (img)(0,_n2##y,z,v)), \
1481
(I[48] = I[49] = I[50] = I[51] = (img)(0,_n3##y,z,v)), \
1482
(I[56] = I[57] = I[58] = I[59] = (img)(0,_n4##y,z,v)), \
1483
(I[4] = (img)(_n1##x,_p3##y,z,v)), \
1484
(I[12] = (img)(_n1##x,_p2##y,z,v)), \
1485
(I[20] = (img)(_n1##x,_p1##y,z,v)), \
1486
(I[28] = (img)(_n1##x,y,z,v)), \
1487
(I[36] = (img)(_n1##x,_n1##y,z,v)), \
1488
(I[44] = (img)(_n1##x,_n2##y,z,v)), \
1489
(I[52] = (img)(_n1##x,_n3##y,z,v)), \
1490
(I[60] = (img)(_n1##x,_n4##y,z,v)), \
1491
(I[5] = (img)(_n2##x,_p3##y,z,v)), \
1492
(I[13] = (img)(_n2##x,_p2##y,z,v)), \
1493
(I[21] = (img)(_n2##x,_p1##y,z,v)), \
1494
(I[29] = (img)(_n2##x,y,z,v)), \
1495
(I[37] = (img)(_n2##x,_n1##y,z,v)), \
1496
(I[45] = (img)(_n2##x,_n2##y,z,v)), \
1497
(I[53] = (img)(_n2##x,_n3##y,z,v)), \
1498
(I[61] = (img)(_n2##x,_n4##y,z,v)), \
1499
(I[6] = (img)(_n3##x,_p3##y,z,v)), \
1500
(I[14] = (img)(_n3##x,_p2##y,z,v)), \
1501
(I[22] = (img)(_n3##x,_p1##y,z,v)), \
1502
(I[30] = (img)(_n3##x,y,z,v)), \
1503
(I[38] = (img)(_n3##x,_n1##y,z,v)), \
1504
(I[46] = (img)(_n3##x,_n2##y,z,v)), \
1505
(I[54] = (img)(_n3##x,_n3##y,z,v)), \
1506
(I[62] = (img)(_n3##x,_n4##y,z,v)), \
1507
4>=((img).width)?(int)((img).width)-1:4); \
1508
(_n4##x<(int)((img).width) && ( \
1509
(I[7] = (img)(_n4##x,_p3##y,z,v)), \
1510
(I[15] = (img)(_n4##x,_p2##y,z,v)), \
1511
(I[23] = (img)(_n4##x,_p1##y,z,v)), \
1512
(I[31] = (img)(_n4##x,y,z,v)), \
1513
(I[39] = (img)(_n4##x,_n1##y,z,v)), \
1514
(I[47] = (img)(_n4##x,_n2##y,z,v)), \
1515
(I[55] = (img)(_n4##x,_n3##y,z,v)), \
1516
(I[63] = (img)(_n4##x,_n4##y,z,v)),1)) || \
1517
_n3##x==--_n4##x || _n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n4##x = _n3##x = _n2##x = --_n1##x); \
1518
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], I[5] = I[6], I[6] = I[7], \
1519
I[8] = I[9], I[9] = I[10], I[10] = I[11], I[11] = I[12], I[12] = I[13], I[13] = I[14], I[14] = I[15], \
1520
I[16] = I[17], I[17] = I[18], I[18] = I[19], I[19] = I[20], I[20] = I[21], I[21] = I[22], I[22] = I[23], \
1521
I[24] = I[25], I[25] = I[26], I[26] = I[27], I[27] = I[28], I[28] = I[29], I[29] = I[30], I[30] = I[31], \
1522
I[32] = I[33], I[33] = I[34], I[34] = I[35], I[35] = I[36], I[36] = I[37], I[37] = I[38], I[38] = I[39], \
1523
I[40] = I[41], I[41] = I[42], I[42] = I[43], I[43] = I[44], I[44] = I[45], I[45] = I[46], I[46] = I[47], \
1524
I[48] = I[49], I[49] = I[50], I[50] = I[51], I[51] = I[52], I[52] = I[53], I[53] = I[54], I[54] = I[55], \
1525
I[56] = I[57], I[57] = I[58], I[58] = I[59], I[59] = I[60], I[60] = I[61], I[61] = I[62], I[62] = I[63], \
1526
_p3##x = _p2##x, _p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x, ++_n4##x)
1528
#define cimg_for_in8x8(img,x0,y0,x1,y1,x,y,z,v,I) \
1529
cimg_for_in8((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1530
_p3##x = x-3<0?0:x-3, \
1531
_p2##x = x-2<0?0:x-2, \
1532
_p1##x = x-1<0?0:x-1, \
1533
_n1##x = x+1>=(int)((img).width)?(int)((img).width)-1:x+1, \
1534
_n2##x = x+2>=(int)((img).width)?(int)((img).width)-1:x+2, \
1535
_n3##x = x+3>=(int)((img).width)?(int)((img).width)-1:x+3, \
1537
(I[0] = (img)(_p3##x,_p3##y,z,v)), \
1538
(I[8] = (img)(_p3##x,_p2##y,z,v)), \
1539
(I[16] = (img)(_p3##x,_p1##y,z,v)), \
1540
(I[24] = (img)(_p3##x,y,z,v)), \
1541
(I[32] = (img)(_p3##x,_n1##y,z,v)), \
1542
(I[40] = (img)(_p3##x,_n2##y,z,v)), \
1543
(I[48] = (img)(_p3##x,_n3##y,z,v)), \
1544
(I[56] = (img)(_p3##x,_n4##y,z,v)), \
1545
(I[1] = (img)(_p2##x,_p3##y,z,v)), \
1546
(I[9] = (img)(_p2##x,_p2##y,z,v)), \
1547
(I[17] = (img)(_p2##x,_p1##y,z,v)), \
1548
(I[25] = (img)(_p2##x,y,z,v)), \
1549
(I[33] = (img)(_p2##x,_n1##y,z,v)), \
1550
(I[41] = (img)(_p2##x,_n2##y,z,v)), \
1551
(I[49] = (img)(_p2##x,_n3##y,z,v)), \
1552
(I[57] = (img)(_p2##x,_n4##y,z,v)), \
1553
(I[2] = (img)(_p1##x,_p3##y,z,v)), \
1554
(I[10] = (img)(_p1##x,_p2##y,z,v)), \
1555
(I[18] = (img)(_p1##x,_p1##y,z,v)), \
1556
(I[26] = (img)(_p1##x,y,z,v)), \
1557
(I[34] = (img)(_p1##x,_n1##y,z,v)), \
1558
(I[42] = (img)(_p1##x,_n2##y,z,v)), \
1559
(I[50] = (img)(_p1##x,_n3##y,z,v)), \
1560
(I[58] = (img)(_p1##x,_n4##y,z,v)), \
1561
(I[3] = (img)(x,_p3##y,z,v)), \
1562
(I[11] = (img)(x,_p2##y,z,v)), \
1563
(I[19] = (img)(x,_p1##y,z,v)), \
1564
(I[27] = (img)(x,y,z,v)), \
1565
(I[35] = (img)(x,_n1##y,z,v)), \
1566
(I[43] = (img)(x,_n2##y,z,v)), \
1567
(I[51] = (img)(x,_n3##y,z,v)), \
1568
(I[59] = (img)(x,_n4##y,z,v)), \
1569
(I[4] = (img)(_n1##x,_p3##y,z,v)), \
1570
(I[12] = (img)(_n1##x,_p2##y,z,v)), \
1571
(I[20] = (img)(_n1##x,_p1##y,z,v)), \
1572
(I[28] = (img)(_n1##x,y,z,v)), \
1573
(I[36] = (img)(_n1##x,_n1##y,z,v)), \
1574
(I[44] = (img)(_n1##x,_n2##y,z,v)), \
1575
(I[52] = (img)(_n1##x,_n3##y,z,v)), \
1576
(I[60] = (img)(_n1##x,_n4##y,z,v)), \
1577
(I[5] = (img)(_n2##x,_p3##y,z,v)), \
1578
(I[13] = (img)(_n2##x,_p2##y,z,v)), \
1579
(I[21] = (img)(_n2##x,_p1##y,z,v)), \
1580
(I[29] = (img)(_n2##x,y,z,v)), \
1581
(I[37] = (img)(_n2##x,_n1##y,z,v)), \
1582
(I[45] = (img)(_n2##x,_n2##y,z,v)), \
1583
(I[53] = (img)(_n2##x,_n3##y,z,v)), \
1584
(I[61] = (img)(_n2##x,_n4##y,z,v)), \
1585
(I[6] = (img)(_n3##x,_p3##y,z,v)), \
1586
(I[14] = (img)(_n3##x,_p2##y,z,v)), \
1587
(I[22] = (img)(_n3##x,_p1##y,z,v)), \
1588
(I[30] = (img)(_n3##x,y,z,v)), \
1589
(I[38] = (img)(_n3##x,_n1##y,z,v)), \
1590
(I[46] = (img)(_n3##x,_n2##y,z,v)), \
1591
(I[54] = (img)(_n3##x,_n3##y,z,v)), \
1592
(I[62] = (img)(_n3##x,_n4##y,z,v)), \
1593
x+4>=(int)((img).width)?(int)((img).width)-1:x+4); \
1594
x<=(int)(x1) && ((_n4##x<(int)((img).width) && ( \
1595
(I[7] = (img)(_n4##x,_p3##y,z,v)), \
1596
(I[15] = (img)(_n4##x,_p2##y,z,v)), \
1597
(I[23] = (img)(_n4##x,_p1##y,z,v)), \
1598
(I[31] = (img)(_n4##x,y,z,v)), \
1599
(I[39] = (img)(_n4##x,_n1##y,z,v)), \
1600
(I[47] = (img)(_n4##x,_n2##y,z,v)), \
1601
(I[55] = (img)(_n4##x,_n3##y,z,v)), \
1602
(I[63] = (img)(_n4##x,_n4##y,z,v)),1)) || \
1603
_n3##x==--_n4##x || _n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n4##x = _n3##x = _n2##x = --_n1##x)); \
1604
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], I[5] = I[6], I[6] = I[7], \
1605
I[8] = I[9], I[9] = I[10], I[10] = I[11], I[11] = I[12], I[12] = I[13], I[13] = I[14], I[14] = I[15], \
1606
I[16] = I[17], I[17] = I[18], I[18] = I[19], I[19] = I[20], I[20] = I[21], I[21] = I[22], I[22] = I[23], \
1607
I[24] = I[25], I[25] = I[26], I[26] = I[27], I[27] = I[28], I[28] = I[29], I[29] = I[30], I[30] = I[31], \
1608
I[32] = I[33], I[33] = I[34], I[34] = I[35], I[35] = I[36], I[36] = I[37], I[37] = I[38], I[38] = I[39], \
1609
I[40] = I[41], I[41] = I[42], I[42] = I[43], I[43] = I[44], I[44] = I[45], I[45] = I[46], I[46] = I[47], \
1610
I[48] = I[49], I[49] = I[50], I[50] = I[51], I[51] = I[52], I[52] = I[53], I[53] = I[54], I[54] = I[55], \
1611
I[56] = I[57], I[57] = I[58], I[58] = I[59], I[59] = I[60], I[60] = I[61], I[61] = I[62], I[62] = I[63], \
1612
_p3##x = _p2##x, _p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x, ++_n4##x)
1614
#define cimg_for9x9(img,x,y,z,v,I) \
1615
cimg_for9((img).height,y) for (int x = 0, \
1616
_p4##x = 0, _p3##x = 0, _p2##x = 0, _p1##x = 0, \
1617
_n1##x = 1>=((img).width)?(int)((img).width)-1:1, \
1618
_n2##x = 2>=((img).width)?(int)((img).width)-1:2, \
1619
_n3##x = 3>=((img).width)?(int)((img).width)-1:3, \
1621
(I[0] = I[1] = I[2] = I[3] = I[4] = (img)(0,_p4##y,z,v)), \
1622
(I[9] = I[10] = I[11] = I[12] = I[13] = (img)(0,_p3##y,z,v)), \
1623
(I[18] = I[19] = I[20] = I[21] = I[22] = (img)(0,_p2##y,z,v)), \
1624
(I[27] = I[28] = I[29] = I[30] = I[31] = (img)(0,_p1##y,z,v)), \
1625
(I[36] = I[37] = I[38] = I[39] = I[40] = (img)(0,y,z,v)), \
1626
(I[45] = I[46] = I[47] = I[48] = I[49] = (img)(0,_n1##y,z,v)), \
1627
(I[54] = I[55] = I[56] = I[57] = I[58] = (img)(0,_n2##y,z,v)), \
1628
(I[63] = I[64] = I[65] = I[66] = I[67] = (img)(0,_n3##y,z,v)), \
1629
(I[72] = I[73] = I[74] = I[75] = I[76] = (img)(0,_n4##y,z,v)), \
1630
(I[5] = (img)(_n1##x,_p4##y,z,v)), \
1631
(I[14] = (img)(_n1##x,_p3##y,z,v)), \
1632
(I[23] = (img)(_n1##x,_p2##y,z,v)), \
1633
(I[32] = (img)(_n1##x,_p1##y,z,v)), \
1634
(I[41] = (img)(_n1##x,y,z,v)), \
1635
(I[50] = (img)(_n1##x,_n1##y,z,v)), \
1636
(I[59] = (img)(_n1##x,_n2##y,z,v)), \
1637
(I[68] = (img)(_n1##x,_n3##y,z,v)), \
1638
(I[77] = (img)(_n1##x,_n4##y,z,v)), \
1639
(I[6] = (img)(_n2##x,_p4##y,z,v)), \
1640
(I[15] = (img)(_n2##x,_p3##y,z,v)), \
1641
(I[24] = (img)(_n2##x,_p2##y,z,v)), \
1642
(I[33] = (img)(_n2##x,_p1##y,z,v)), \
1643
(I[42] = (img)(_n2##x,y,z,v)), \
1644
(I[51] = (img)(_n2##x,_n1##y,z,v)), \
1645
(I[60] = (img)(_n2##x,_n2##y,z,v)), \
1646
(I[69] = (img)(_n2##x,_n3##y,z,v)), \
1647
(I[78] = (img)(_n2##x,_n4##y,z,v)), \
1648
(I[7] = (img)(_n3##x,_p4##y,z,v)), \
1649
(I[16] = (img)(_n3##x,_p3##y,z,v)), \
1650
(I[25] = (img)(_n3##x,_p2##y,z,v)), \
1651
(I[34] = (img)(_n3##x,_p1##y,z,v)), \
1652
(I[43] = (img)(_n3##x,y,z,v)), \
1653
(I[52] = (img)(_n3##x,_n1##y,z,v)), \
1654
(I[61] = (img)(_n3##x,_n2##y,z,v)), \
1655
(I[70] = (img)(_n3##x,_n3##y,z,v)), \
1656
(I[79] = (img)(_n3##x,_n4##y,z,v)), \
1657
4>=((img).width)?(int)((img).width)-1:4); \
1658
(_n4##x<(int)((img).width) && ( \
1659
(I[8] = (img)(_n4##x,_p4##y,z,v)), \
1660
(I[17] = (img)(_n4##x,_p3##y,z,v)), \
1661
(I[26] = (img)(_n4##x,_p2##y,z,v)), \
1662
(I[35] = (img)(_n4##x,_p1##y,z,v)), \
1663
(I[44] = (img)(_n4##x,y,z,v)), \
1664
(I[53] = (img)(_n4##x,_n1##y,z,v)), \
1665
(I[62] = (img)(_n4##x,_n2##y,z,v)), \
1666
(I[71] = (img)(_n4##x,_n3##y,z,v)), \
1667
(I[80] = (img)(_n4##x,_n4##y,z,v)),1)) || \
1668
_n3##x==--_n4##x || _n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n4##x = _n3##x = _n2##x = --_n1##x); \
1669
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], I[5] = I[6], I[6] = I[7], I[7] = I[8], \
1670
I[9] = I[10], I[10] = I[11], I[11] = I[12], I[12] = I[13], I[13] = I[14], I[14] = I[15], I[15] = I[16], I[16] = I[17], \
1671
I[18] = I[19], I[19] = I[20], I[20] = I[21], I[21] = I[22], I[22] = I[23], I[23] = I[24], I[24] = I[25], I[25] = I[26], \
1672
I[27] = I[28], I[28] = I[29], I[29] = I[30], I[30] = I[31], I[31] = I[32], I[32] = I[33], I[33] = I[34], I[34] = I[35], \
1673
I[36] = I[37], I[37] = I[38], I[38] = I[39], I[39] = I[40], I[40] = I[41], I[41] = I[42], I[42] = I[43], I[43] = I[44], \
1674
I[45] = I[46], I[46] = I[47], I[47] = I[48], I[48] = I[49], I[49] = I[50], I[50] = I[51], I[51] = I[52], I[52] = I[53], \
1675
I[54] = I[55], I[55] = I[56], I[56] = I[57], I[57] = I[58], I[58] = I[59], I[59] = I[60], I[60] = I[61], I[61] = I[62], \
1676
I[63] = I[64], I[64] = I[65], I[65] = I[66], I[66] = I[67], I[67] = I[68], I[68] = I[69], I[69] = I[70], I[70] = I[71], \
1677
I[72] = I[73], I[73] = I[74], I[74] = I[75], I[75] = I[76], I[76] = I[77], I[77] = I[78], I[78] = I[79], I[79] = I[80], \
1678
_p4##x = _p3##x, _p3##x = _p2##x, _p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x, ++_n4##x)
1680
#define cimg_for_in9x9(img,x0,y0,x1,y1,x,y,z,v,I) \
1681
cimg_for_in9((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1682
_p4##x = x-4<0?0:x-4, \
1683
_p3##x = x-3<0?0:x-3, \
1684
_p2##x = x-2<0?0:x-2, \
1685
_p1##x = x-1<0?0:x-1, \
1686
_n1##x = x+1>=(int)((img).width)?(int)((img).width)-1:x+1, \
1687
_n2##x = x+2>=(int)((img).width)?(int)((img).width)-1:x+2, \
1688
_n3##x = x+3>=(int)((img).width)?(int)((img).width)-1:x+3, \
1690
(I[0] = (img)(_p4##x,_p4##y,z,v)), \
1691
(I[9] = (img)(_p4##x,_p3##y,z,v)), \
1692
(I[18] = (img)(_p4##x,_p2##y,z,v)), \
1693
(I[27] = (img)(_p4##x,_p1##y,z,v)), \
1694
(I[36] = (img)(_p4##x,y,z,v)), \
1695
(I[45] = (img)(_p4##x,_n1##y,z,v)), \
1696
(I[54] = (img)(_p4##x,_n2##y,z,v)), \
1697
(I[63] = (img)(_p4##x,_n3##y,z,v)), \
1698
(I[72] = (img)(_p4##x,_n4##y,z,v)), \
1699
(I[1] = (img)(_p3##x,_p4##y,z,v)), \
1700
(I[10] = (img)(_p3##x,_p3##y,z,v)), \
1701
(I[19] = (img)(_p3##x,_p2##y,z,v)), \
1702
(I[28] = (img)(_p3##x,_p1##y,z,v)), \
1703
(I[37] = (img)(_p3##x,y,z,v)), \
1704
(I[46] = (img)(_p3##x,_n1##y,z,v)), \
1705
(I[55] = (img)(_p3##x,_n2##y,z,v)), \
1706
(I[64] = (img)(_p3##x,_n3##y,z,v)), \
1707
(I[73] = (img)(_p3##x,_n4##y,z,v)), \
1708
(I[2] = (img)(_p2##x,_p4##y,z,v)), \
1709
(I[11] = (img)(_p2##x,_p3##y,z,v)), \
1710
(I[20] = (img)(_p2##x,_p2##y,z,v)), \
1711
(I[29] = (img)(_p2##x,_p1##y,z,v)), \
1712
(I[38] = (img)(_p2##x,y,z,v)), \
1713
(I[47] = (img)(_p2##x,_n1##y,z,v)), \
1714
(I[56] = (img)(_p2##x,_n2##y,z,v)), \
1715
(I[65] = (img)(_p2##x,_n3##y,z,v)), \
1716
(I[74] = (img)(_p2##x,_n4##y,z,v)), \
1717
(I[3] = (img)(_p1##x,_p4##y,z,v)), \
1718
(I[12] = (img)(_p1##x,_p3##y,z,v)), \
1719
(I[21] = (img)(_p1##x,_p2##y,z,v)), \
1720
(I[30] = (img)(_p1##x,_p1##y,z,v)), \
1721
(I[39] = (img)(_p1##x,y,z,v)), \
1722
(I[48] = (img)(_p1##x,_n1##y,z,v)), \
1723
(I[57] = (img)(_p1##x,_n2##y,z,v)), \
1724
(I[66] = (img)(_p1##x,_n3##y,z,v)), \
1725
(I[75] = (img)(_p1##x,_n4##y,z,v)), \
1726
(I[4] = (img)(x,_p4##y,z,v)), \
1727
(I[13] = (img)(x,_p3##y,z,v)), \
1728
(I[22] = (img)(x,_p2##y,z,v)), \
1729
(I[31] = (img)(x,_p1##y,z,v)), \
1730
(I[40] = (img)(x,y,z,v)), \
1731
(I[49] = (img)(x,_n1##y,z,v)), \
1732
(I[58] = (img)(x,_n2##y,z,v)), \
1733
(I[67] = (img)(x,_n3##y,z,v)), \
1734
(I[76] = (img)(x,_n4##y,z,v)), \
1735
(I[5] = (img)(_n1##x,_p4##y,z,v)), \
1736
(I[14] = (img)(_n1##x,_p3##y,z,v)), \
1737
(I[23] = (img)(_n1##x,_p2##y,z,v)), \
1738
(I[32] = (img)(_n1##x,_p1##y,z,v)), \
1739
(I[41] = (img)(_n1##x,y,z,v)), \
1740
(I[50] = (img)(_n1##x,_n1##y,z,v)), \
1741
(I[59] = (img)(_n1##x,_n2##y,z,v)), \
1742
(I[68] = (img)(_n1##x,_n3##y,z,v)), \
1743
(I[77] = (img)(_n1##x,_n4##y,z,v)), \
1744
(I[6] = (img)(_n2##x,_p4##y,z,v)), \
1745
(I[15] = (img)(_n2##x,_p3##y,z,v)), \
1746
(I[24] = (img)(_n2##x,_p2##y,z,v)), \
1747
(I[33] = (img)(_n2##x,_p1##y,z,v)), \
1748
(I[42] = (img)(_n2##x,y,z,v)), \
1749
(I[51] = (img)(_n2##x,_n1##y,z,v)), \
1750
(I[60] = (img)(_n2##x,_n2##y,z,v)), \
1751
(I[69] = (img)(_n2##x,_n3##y,z,v)), \
1752
(I[78] = (img)(_n2##x,_n4##y,z,v)), \
1753
(I[7] = (img)(_n3##x,_p4##y,z,v)), \
1754
(I[16] = (img)(_n3##x,_p3##y,z,v)), \
1755
(I[25] = (img)(_n3##x,_p2##y,z,v)), \
1756
(I[34] = (img)(_n3##x,_p1##y,z,v)), \
1757
(I[43] = (img)(_n3##x,y,z,v)), \
1758
(I[52] = (img)(_n3##x,_n1##y,z,v)), \
1759
(I[61] = (img)(_n3##x,_n2##y,z,v)), \
1760
(I[70] = (img)(_n3##x,_n3##y,z,v)), \
1761
(I[79] = (img)(_n3##x,_n4##y,z,v)), \
1762
x+4>=(int)((img).width)?(int)((img).width)-1:x+4); \
1763
x<=(int)(x1) && ((_n4##x<(int)((img).width) && ( \
1764
(I[8] = (img)(_n4##x,_p4##y,z,v)), \
1765
(I[17] = (img)(_n4##x,_p3##y,z,v)), \
1766
(I[26] = (img)(_n4##x,_p2##y,z,v)), \
1767
(I[35] = (img)(_n4##x,_p1##y,z,v)), \
1768
(I[44] = (img)(_n4##x,y,z,v)), \
1769
(I[53] = (img)(_n4##x,_n1##y,z,v)), \
1770
(I[62] = (img)(_n4##x,_n2##y,z,v)), \
1771
(I[71] = (img)(_n4##x,_n3##y,z,v)), \
1772
(I[80] = (img)(_n4##x,_n4##y,z,v)),1)) || \
1773
_n3##x==--_n4##x || _n2##x==--_n3##x || _n1##x==--_n2##x || x==(_n4##x = _n3##x = _n2##x = --_n1##x)); \
1774
I[0] = I[1], I[1] = I[2], I[2] = I[3], I[3] = I[4], I[4] = I[5], I[5] = I[6], I[6] = I[7], I[7] = I[8], \
1775
I[9] = I[10], I[10] = I[11], I[11] = I[12], I[12] = I[13], I[13] = I[14], I[14] = I[15], I[15] = I[16], I[16] = I[17], \
1776
I[18] = I[19], I[19] = I[20], I[20] = I[21], I[21] = I[22], I[22] = I[23], I[23] = I[24], I[24] = I[25], I[25] = I[26], \
1777
I[27] = I[28], I[28] = I[29], I[29] = I[30], I[30] = I[31], I[31] = I[32], I[32] = I[33], I[33] = I[34], I[34] = I[35], \
1778
I[36] = I[37], I[37] = I[38], I[38] = I[39], I[39] = I[40], I[40] = I[41], I[41] = I[42], I[42] = I[43], I[43] = I[44], \
1779
I[45] = I[46], I[46] = I[47], I[47] = I[48], I[48] = I[49], I[49] = I[50], I[50] = I[51], I[51] = I[52], I[52] = I[53], \
1780
I[54] = I[55], I[55] = I[56], I[56] = I[57], I[57] = I[58], I[58] = I[59], I[59] = I[60], I[60] = I[61], I[61] = I[62], \
1781
I[63] = I[64], I[64] = I[65], I[65] = I[66], I[66] = I[67], I[67] = I[68], I[68] = I[69], I[69] = I[70], I[70] = I[71], \
1782
I[72] = I[73], I[73] = I[74], I[74] = I[75], I[75] = I[76], I[76] = I[77], I[77] = I[78], I[78] = I[79], I[79] = I[80], \
1783
_p4##x = _p3##x, _p3##x = _p2##x, _p2##x = _p1##x, _p1##x = x++, ++_n1##x, ++_n2##x, ++_n3##x, ++_n4##x)
1785
#define cimg_for2x2x2(img,x,y,z,v,I) \
1786
cimg_for2((img).depth,z) cimg_for2((img).height,y) for (int x = 0, \
1788
(I[0] = (img)(0,y,z,v)), \
1789
(I[2] = (img)(0,_n1##y,z,v)), \
1790
(I[4] = (img)(0,y,_n1##z,v)), \
1791
(I[6] = (img)(0,_n1##y,_n1##z,v)), \
1792
1>=(img).width?(int)((img).width)-1:1); \
1793
(_n1##x<(int)((img).width) && ( \
1794
(I[1] = (img)(_n1##x,y,z,v)), \
1795
(I[3] = (img)(_n1##x,_n1##y,z,v)), \
1796
(I[5] = (img)(_n1##x,y,_n1##z,v)), \
1797
(I[7] = (img)(_n1##x,_n1##y,_n1##z,v)),1)) || \
1799
I[0] = I[1], I[2] = I[3], I[4] = I[5], I[6] = I[7], \
1802
#define cimg_for_in2x2x2(img,x0,y0,z0,x1,y1,z1,x,y,z,v,I) \
1803
cimg_for_in2((img).depth,z0,z1,z) cimg_for_in2((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1805
(I[0] = (img)(x,y,z,v)), \
1806
(I[2] = (img)(x,_n1##y,z,v)), \
1807
(I[4] = (img)(x,y,_n1##z,v)), \
1808
(I[6] = (img)(x,_n1##y,_n1##z,v)), \
1809
x+1>=(int)(img).width?(int)((img).width)-1:x+1); \
1810
x<=(int)(x1) && ((_n1##x<(int)((img).width) && ( \
1811
(I[1] = (img)(_n1##x,y,z,v)), \
1812
(I[3] = (img)(_n1##x,_n1##y,z,v)), \
1813
(I[5] = (img)(_n1##x,y,_n1##z,v)), \
1814
(I[7] = (img)(_n1##x,_n1##y,_n1##z,v)),1)) || \
1816
I[0] = I[1], I[2] = I[3], I[4] = I[5], I[6] = I[7], \
1819
#define cimg_for3x3x3(img,x,y,z,v,I) \
1820
cimg_for3((img).depth,z) cimg_for3((img).height,y) for (int x = 0, \
1823
(I[0] = I[1] = (img)(0,_p1##y,_p1##z,v)), \
1824
(I[3] = I[4] = (img)(0,y,_p1##z,v)), \
1825
(I[6] = I[7] = (img)(0,_n1##y,_p1##z,v)), \
1826
(I[9] = I[10] = (img)(0,_p1##y,z,v)), \
1827
(I[12] = I[13] = (img)(0,y,z,v)), \
1828
(I[15] = I[16] = (img)(0,_n1##y,z,v)), \
1829
(I[18] = I[19] = (img)(0,_p1##y,_n1##z,v)), \
1830
(I[21] = I[22] = (img)(0,y,_n1##z,v)), \
1831
(I[24] = I[25] = (img)(0,_n1##y,_n1##z,v)), \
1832
1>=(img).width?(int)((img).width)-1:1); \
1833
(_n1##x<(int)((img).width) && ( \
1834
(I[2] = (img)(_n1##x,_p1##y,_p1##z,v)), \
1835
(I[5] = (img)(_n1##x,y,_p1##z,v)), \
1836
(I[8] = (img)(_n1##x,_n1##y,_p1##z,v)), \
1837
(I[11] = (img)(_n1##x,_p1##y,z,v)), \
1838
(I[14] = (img)(_n1##x,y,z,v)), \
1839
(I[17] = (img)(_n1##x,_n1##y,z,v)), \
1840
(I[20] = (img)(_n1##x,_p1##y,_n1##z,v)), \
1841
(I[23] = (img)(_n1##x,y,_n1##z,v)), \
1842
(I[26] = (img)(_n1##x,_n1##y,_n1##z,v)),1)) || \
1844
I[0] = I[1], I[1] = I[2], I[3] = I[4], I[4] = I[5], I[6] = I[7], I[7] = I[8], \
1845
I[9] = I[10], I[10] = I[11], I[12] = I[13], I[13] = I[14], I[15] = I[16], I[16] = I[17], \
1846
I[18] = I[19], I[19] = I[20], I[21] = I[22], I[22] = I[23], I[24] = I[25], I[25] = I[26], \
1847
_p1##x = x++, ++_n1##x)
1849
#define cimg_for_in3x3x3(img,x0,y0,z0,x1,y1,z1,x,y,z,v,I) \
1850
cimg_for_in3((img).depth,z0,z1,z) cimg_for_in3((img).height,y0,y1,y) for (int x = (int)(x0)<0?0:(int)(x0), \
1851
_p1##x = x-1<0?0:x-1, \
1853
(I[0] = (img)(_p1##x,_p1##y,_p1##z,v)), \
1854
(I[3] = (img)(_p1##x,y,_p1##z,v)), \
1855
(I[6] = (img)(_p1##x,_n1##y,_p1##z,v)), \
1856
(I[9] = (img)(_p1##x,_p1##y,z,v)), \
1857
(I[12] = (img)(_p1##x,y,z,v)), \
1858
(I[15] = (img)(_p1##x,_n1##y,z,v)), \
1859
(I[18] = (img)(_p1##x,_p1##y,_n1##z,v)), \
1860
(I[21] = (img)(_p1##x,y,_n1##z,v)), \
1861
(I[24] = (img)(_p1##x,_n1##y,_n1##z,v)), \
1862
(I[1] = (img)(x,_p1##y,_p1##z,v)), \
1863
(I[4] = (img)(x,y,_p1##z,v)), \
1864
(I[7] = (img)(x,_n1##y,_p1##z,v)), \
1865
(I[10] = (img)(x,_p1##y,z,v)), \
1866
(I[13] = (img)(x,y,z,v)), \
1867
(I[16] = (img)(x,_n1##y,z,v)), \
1868
(I[19] = (img)(x,_p1##y,_n1##z,v)), \
1869
(I[22] = (img)(x,y,_n1##z,v)), \
1870
(I[25] = (img)(x,_n1##y,_n1##z,v)), \
1871
x+1>=(int)(img).width?(int)((img).width)-1:x+1); \
1872
x<=(int)(x1) && ((_n1##x<(int)((img).width) && ( \
1873
(I[2] = (img)(_n1##x,_p1##y,_p1##z,v)), \
1874
(I[5] = (img)(_n1##x,y,_p1##z,v)), \
1875
(I[8] = (img)(_n1##x,_n1##y,_p1##z,v)), \
1876
(I[11] = (img)(_n1##x,_p1##y,z,v)), \
1877
(I[14] = (img)(_n1##x,y,z,v)), \
1878
(I[17] = (img)(_n1##x,_n1##y,z,v)), \
1879
(I[20] = (img)(_n1##x,_p1##y,_n1##z,v)), \
1880
(I[23] = (img)(_n1##x,y,_n1##z,v)), \
1881
(I[26] = (img)(_n1##x,_n1##y,_n1##z,v)),1)) || \
1883
I[0] = I[1], I[1] = I[2], I[3] = I[4], I[4] = I[5], I[6] = I[7], I[7] = I[8], \
1884
I[9] = I[10], I[10] = I[11], I[12] = I[13], I[13] = I[14], I[15] = I[16], I[16] = I[17], \
1885
I[18] = I[19], I[19] = I[20], I[21] = I[22], I[22] = I[23], I[24] = I[25], I[25] = I[26], \
1886
_p1##x = x++, ++_n1##x)
1888
/*------------------------------------------------
607
1891
# Definition of the cimg_library:: namespace
610
#------------------------------------------------
613
//! Namespace that encompasses all classes and functions of the %CImg library.
1894
-------------------------------------------------*/
1895
//! This namespace encompasses all classes and functions of the %CImg library.
615
This namespace is defined to avoid class names collisions that could happen
616
with the include of other C++ header files. Anyway, it should not happen
617
very often and you may start most of your programs with
1897
This namespace is defined to avoid functions and class names collisions
1898
that could happen with the include of other C++ header files.
1899
Anyway, it should not happen often and you should reasonnably start most of your
1900
%CImg-based programs with
619
1902
#include "CImg.h"
620
1903
using namespace cimg_library;
622
to simplify the declaration of %CImg Library objects variables afterwards.
1905
to simplify the declaration of %CImg Library variables afterwards.
625
1907
namespace cimg_library {
627
// Define the CImg classes.
1909
// Declare the only four classes of the CImg Library.
628
1911
template<typename T=float> struct CImg;
629
1912
template<typename T=float> struct CImgList;
631
1913
struct CImgDisplay;
632
1914
struct CImgException;
1916
// (Pre)declare the cimg namespace.
1917
// This is not the complete namespace declaration. It only contains some
1918
// necessary stuffs to ensure a correct declaration order of classes and functions
1919
// defined afterwards.
634
1921
namespace cimg {
636
// The bodies of the functions below are defined afterwards
1923
#ifdef cimg_use_vt100
1924
const char t_normal[] = { 0x1b,'[','0',';','0',';','0','m','\0' };
1925
const char t_red[] = { 0x1b,'[','4',';','3','1',';','5','9','m','\0' };
1926
const char t_bold[] = { 0x1b,'[','1','m','\0' };
1927
const char t_purple[] = { 0x1b,'[','0',';','3','5',';','5','9','m','\0' };
1928
const char t_green[] = { 0x1b,'[','0',';','3','2',';','5','9','m','\0' };
1930
const char t_normal[] = { '\0' };
1931
const char *const t_red = cimg::t_normal, *const t_bold = cimg::t_normal,
1932
*const t_purple = cimg::t_normal, *const t_green = cimg::t_normal;
637
1935
inline void info();
639
inline unsigned int& exception_mode();
1937
//! Get/set the current CImg exception mode.
1939
The way error messages are handled by CImg can be changed dynamically, using this function.
1940
Possible values are :
1941
- 0 to hide debug messages (quiet mode, but exceptions are still thrown).
1942
- 1 to display debug messages on standard error (stderr).
1943
- 2 to display debug messages in modal windows (default behavior).
1944
- 3 to do as 1 + add extra warnings (may slow down the code !).
1945
- 4 to do as 2 + add extra warnings (may slow down the code !).
1947
inline unsigned int& exception_mode() { static unsigned int mode = cimg_debug; return mode; }
641
1949
inline int dialog(const char *title, const char *msg, const char *button1_txt="OK",
642
1950
const char *button2_txt=0, const char *button3_txt=0,
4326
template<typename t1, typename t2> inline CImgList<typename cimg::largest<t1,t2>::type> operator/(const t1& val, const CImgList<t2>& list) {
4327
typedef typename cimg::largest<t1,t2>::type restype;
4328
CImgList<restype> res(list.size);
6088
template<typename t1, typename t2> inline CImgList<typename cimg::superset<t1,t2>::type> operator/(const t1 val, const CImgList<t2>& list) {
6089
typedef typename cimg::superset<t1,t2>::type t1t2;
6090
CImgList<t1t2> res(list.size);
4329
6091
cimglist_for(res,l) res[l] = val/list[l];
4334
template<typename t1, typename t2> inline CImg<typename cimg::largest<t1,t2>::type> operator/(const CImg<t1>& img1, const CImg<t2>& img2) {
4335
typedef typename cimg::largest<t1,t2>::type restype;
4336
return CImg<restype>(img1,false)*=img2.get_inverse();
6096
template<typename t1, typename t2> inline CImg<typename cimg::superset<t1,t2>::type> operator/(const CImg<t1>& img1, const CImg<t2>& img2) {
6097
typedef typename cimg::superset<t1,t2>::type t1t2;
6098
return CImg<t1t2>(img1,false)*=img2.get_invert();
4339
template<typename t1, typename t2> inline CImg<typename cimg::largest<t1,t2>::type> operator/(const CImg<t1>& img, const CImgList<t2>& list) {
4340
typedef typename cimg::largest<t1,t2>::type restype;
4341
CImgList<restype> res(list.size);
6101
template<typename t1, typename t2> inline CImg<typename cimg::superset<t1,t2>::type> operator/(const CImg<t1>& img, const CImgList<t2>& list) {
6102
typedef typename cimg::superset<t1,t2>::type t1t2;
6103
CImgList<t1t2> res(list.size);
4342
6104
cimglist_for(res,l) res[l] = img/list[l];
4346
template<typename t1, typename t2> inline CImgList<typename cimg::largest<t1,t2>::type> operator/(const CImgList<t1>& list, const CImg<t2>& img) {
4347
typedef typename cimg::largest<t1,t2>::type restype;
4348
return CImgList<restype>(list)/=img;
4351
template<typename t1, typename t2> inline CImgList<typename cimg::largest<t1,t2>::type> operator/(const CImgList<t1>& list1, const CImgList<t2>& list2) {
4352
typedef typename cimg::largest<t1,t2>::type restype;
4353
return CImgList<restype>(list1)/=list2;
4357
#----------------------------------------
4361
# Definition of the CImgStats structure
4365
#----------------------------------------
4367
//! Class used to compute basic statistics on pixel values of a \ref CImg image.
4369
Constructing a CImgStats instance from an image CImg<T> or a list CImgList<T>
4370
will compute the minimum, maximum and average pixel values of the input object.
4371
Optionally, the variance of the pixel values can be computed.
4372
Coordinates of the pixels whose values are minimum and maximum are also stored.
4373
The example below shows how to use CImgStats objects to retrieve simple statistics of an image :
4375
const CImg<float> img("my_image.jpg"); // Read JPEG image file.
4376
const CImgStats stats(img); // Compute basic statistics on the image.
4377
stats.print("My statistics"); // Display statistics.
4378
std::printf("Max-Min = %lf",stats.max-stats.min); // Compute the difference between extremum values.
4381
Note that statistics are computed by considering the set of \a scalar values of the image pixels.
4382
No vector-valued statistics are computed.
4385
double min; //!< Minimum of the pixel values.
4386
double max; //!< Maximum of the pixel values.
4387
double mean; //!< Mean of the pixel values.
4388
double variance; //!< Variance of the pixel values.
4389
int xmin; //!< X-coordinate of the pixel with minimum value.
4390
int ymin; //!< Y-coordinate of the pixel with minimum value.
4391
int zmin; //!< Z-coordinate of the pixel with minimum value.
4392
int vmin; //!< V-coordinate of the pixel with minimum value.
4393
int lmin; //!< Image number (for a list) containing the minimum pixel.
4394
int xmax; //!< X-coordinate of the pixel with maximum value.
4395
int ymax; //!< Y-coordinate of the pixel with maximum value.
4396
int zmax; //!< Z-coordinate of the pixel with maximum value.
4397
int vmax; //!< V-coordinate of the pixel with maximum value.
4398
int lmax; //!< Image number (for a list) containing the maximum pixel.
4400
#ifdef cimgstats_plugin
4401
#include cimgstats_plugin
4404
//! Default constructor.
4405
CImgStats():min(0),max(0),mean(0),variance(0),xmin(-1),ymin(-1),zmin(-1),vmin(-1),lmin(-1),
4406
xmax(-1),ymax(-1),zmax(-1),vmax(-1),lmax(-1) {}
4408
//! In-place version of the default constructor
4409
CImgStats& assign() {
4410
min = max = mean = variance = 0;
4411
xmin = ymin = zmin = vmin = lmin = xmax = ymax = zmax = vmax = lmax = -1;
4415
//! Copy constructor.
4416
CImgStats(const CImgStats& stats) {
4420
//! In-place version of the copy constructor.
4421
CImgStats& assign(const CImgStats& stats) {
4425
variance = stats.variance;
4426
xmin = stats.xmin; ymin = stats.ymin; zmin = stats.zmin; vmin = stats.vmin; lmin = stats.lmin;
4427
xmax = stats.xmax; ymax = stats.ymax; zmax = stats.zmax; vmax = stats.vmax; lmax = stats.lmax;
4431
//! Constructor that computes statistics of an input image \p img.
4433
\param img The input image.
4434
\param compute_variance If true, the \c variance field is computed, else it is set to 0.
4436
template<typename T> CImgStats(const CImg<T>& img, const bool compute_variance=true) {
4437
assign(img,compute_variance);
4440
//! In-place version of the previous constructor.
4441
template<typename T> CImgStats& assign(const CImg<T>& img, const bool compute_variance=true) {
4443
throw CImgArgumentException("CImgStats::CImgStats() : Specified input image (%u,%u,%u,%u,%p) is empty.",
4444
img.width,img.height,img.depth,img.dim,img.data);
4445
mean = variance = 0;
4447
T pmin=img[0], pmax=pmin, *ptrmin=img.data, *ptrmax=ptrmin;
4448
cimg_for(img,ptr,T) {
4451
if (a<pmin) { pmin=a; ptrmin = ptr; }
4452
if (a>pmax) { pmax=a; ptrmax = ptr; }
4457
unsigned long offmin = (unsigned long)(ptrmin-img.data), offmax = (unsigned long)(ptrmax-img.data);
4458
const unsigned long whz = img.width*img.height*img.depth, wh = img.width*img.height;
4459
vmin = offmin/whz; offmin%=whz; zmin = offmin/wh; offmin%=wh; ymin = offmin/img.width; xmin = offmin%img.width;
4460
vmax = offmax/whz; offmax%=whz; zmax = offmax/wh; offmax%=wh; ymax = offmax/img.width; xmax = offmax%img.width;
4461
if (compute_variance) {
4462
cimg_for(img,ptr,T) { const double tmpf=(*ptr)-mean; variance+=tmpf*tmpf; }
4463
const unsigned int siz = img.size();
4464
if (siz>1) variance/=(siz-1); else variance = 0;
4469
//! Constructor that computes statistics of an input image list \p list.
4471
\param list The input list of images.
4472
\param compute_variance If true, the \c variance field is computed, else it is set to 0.
4474
template<typename T> CImgStats(const CImgList<T>& list, const bool compute_variance=true) {
4475
assign(list,compute_variance);
4478
//! In-place version of the previous constructor.
4479
template<typename T> CImgStats& assign(const CImgList<T>& list, const bool compute_variance=true) {
4481
throw CImgArgumentException("CImgStats::CImgStats() : Specified input list (%u,%p) is empty.",
4482
list.size,list.data);
4483
mean = variance = lmin = lmax = 0;
4484
T pmin = list[0][0], pmax = pmin, *ptrmin = list[0].data, *ptrmax = ptrmin;
4486
cimglist_for(list,l) {
4487
cimg_for(list[l],ptr,T) {
4490
if (a<pmin) { pmin=a; ptrmin = ptr; lmin = l; }
4491
if (a>pmax) { pmax=a; ptrmax = ptr; lmax = l; }
4493
psize+=list[l].size();
4498
const CImg<T> &imin = list[lmin], &imax = list[lmax];
4499
unsigned long offmin = (ptrmin-imin.data), offmax = (ptrmax-imax.data);
4500
const unsigned long whz1 = imin.width*imin.height*imin.depth, wh1 = imin.width*imin.height;
4501
vmin = offmin/whz1; offmin%=whz1; zmin = offmin/wh1; offmin%=wh1; ymin = offmin/imin.width; xmin = offmin%imin.width;
4502
const unsigned long whz2 = imax.width*imax.height*imax.depth, wh2 = imax.width*imax.height;
4503
vmax = offmax/whz2; offmax%=whz2; zmax = offmax/wh2; offmax%=wh2; ymax = offmax/imax.width; xmax = offmax%imax.width;
4504
if (compute_variance) {
4505
cimglist_for(list,l) cimg_for(list[l],ptr,T) { const double tmpf=(*ptr)-mean; variance+=tmpf*tmpf; }
4506
if (psize>1) variance/=(psize-1); else variance = 0;
4511
//! Assignment operator.
4512
CImgStats& operator=(const CImgStats& stats) {
4513
return assign(stats);
4516
//! Return true if the current instance contains valid statistics
4517
bool is_empty() const {
4518
return (xmin>=0 && ymin>=0 && zmin>=0 && vmin>=0 && xmax>=0 && ymax>=0 && zmax>=0 && vmax>=0);
4521
//! Casting operator
4522
operator bool() const {
4526
//! Print the current statistics.
4528
Printing is done on the standard error output.
4530
const CImgStats& print(const char* title=0) const {
4531
if (lmin>=0 && lmax>=0)
4532
std::fprintf(stderr,"%-8s(this=%p) : { min=%g, mean=%g [var=%g], max=%g, "
4533
"pmin=[%d](%d,%d,%d,%d), pmax=[%d](%d,%d,%d,%d) }\n",
4534
title?title:"CImgStats",(void*)this,min,mean,variance,max,
4535
lmin,xmin,ymin,zmin,vmin,lmax,xmax,ymax,zmax,vmax);
4537
std::fprintf(stderr,"%-8s(this=%p) : { min=%g, mean=%g [var=%g], max=%g, "
4538
"pmin=(%d,%d,%d,%d), pmax=(%d,%d,%d,%d) }\n",
4539
title?title:"CImgStats",(void*)this,min,mean,variance,max,
4540
xmin,ymin,zmin,vmin,xmax,ymax,zmax,vmax);
4547
#-------------------------------------------
6108
template<typename t1, typename t2> inline CImgList<typename cimg::superset<t1,t2>::type> operator/(const CImgList<t1>& list, const CImg<t2>& img) {
6109
typedef typename cimg::superset<t1,t2>::type t1t2;
6110
return CImgList<t1t2>(list)/=img;
6113
template<typename t1, typename t2> inline CImgList<typename cimg::superset<t1,t2>::type> operator/(const CImgList<t1>& list1, const CImgList<t2>& list2) {
6114
typedef typename cimg::superset<t1,t2>::type t1t2;
6115
return CImgList<t1t2>(list1)/=list2;
6118
template<typename T, typename t> inline CImg<T> apply(const CImg<T>& instance, t& func) {
6119
return instance.get_apply(func);
6122
template<typename T, typename t> inline CImg<_cimg_Tt> mul(const CImg<T>& instance, const CImg<t>& img) {
6123
return instance.get_mul(img);
6126
template<typename T, typename t> inline CImg<_cimg_Tt> div(const CImg<T>& instance, const CImg<t>& img) {
6127
return instance.get_div(img);
6130
template<typename T, typename t> inline CImg<_cimg_Tt> max(const CImg<T>& instance, const CImg<t>& img) {
6131
return instance.get_max(img);
6134
template<typename T> inline CImg<T> max(const CImg<T>& instance, const T val) {
6135
return instance.get_max(val);
6138
template<typename T, typename t> inline CImg<_cimg_Tt> min(const CImg<T>& instance, const CImg<t>& img) {
6139
return instance.get_min(img);
6142
template<typename T> inline CImg<typename cimg::last<T,double>::type> stats(const CImg<T>& instance) {
6143
return instance.get_stats();
6146
template<typename T> inline CImg<T> min(const CImg<T>& instance, const T val) {
6147
return instance.get_min(val);
6150
template<typename T> inline CImg<_cimg_Tfloat> sqr(const CImg<T>& instance) {
6151
return instance.get_sqr();
6154
template<typename T> inline CImg<_cimg_Tfloat> sqrt(const CImg<T>& instance) {
6155
return instance.get_sqrt();
6158
template<typename T> inline CImg<_cimg_Tfloat> exp(const CImg<T>& instance) {
6159
return instance.get_exp();
6162
template<typename T> inline CImg<_cimg_Tfloat> log(const CImg<T>& instance) {
6163
return instance.get_log();
6166
template<typename T> inline CImg<_cimg_Tfloat> log10(const CImg<T>& instance) {
6167
return instance.get_log10();
6170
template<typename T> inline CImg<_cimg_Tfloat> pow(const CImg<T>& instance, const double p) {
6171
return instance.get_pow(p);
6174
template<typename T, typename t> inline CImg<_cimg_Tfloat> pow(const CImg<T>& instance, const CImg<t>& img) {
6175
return instance.get_pow(img);
6178
template<typename T> inline CImg<_cimg_Tfloat> abs(const CImg<T>& instance) {
6179
return instance.get_abs();
6182
template<typename T> inline CImg<_cimg_Tfloat> cos(const CImg<T>& instance) {
6183
return instance.get_cos();
6186
template<typename T> inline CImg<_cimg_Tfloat> sin(const CImg<T>& instance) {
6187
return instance.get_sin();
6190
template<typename T> inline CImg<_cimg_Tfloat> tan(const CImg<T>& instance) {
6191
return instance.get_tan();
6194
template<typename T> inline CImg<_cimg_Tfloat> acos(const CImg<T>& instance) {
6195
return instance.get_acos();
6198
template<typename T> inline CImg<_cimg_Tfloat> asin(const CImg<T>& instance) {
6199
return instance.get_asin();
6202
template<typename T> inline CImg<_cimg_Tfloat> atan(const CImg<T>& instance) {
6203
return instance.get_atan();
6206
template<typename T> inline CImg<T> round(const CImg<T>& instance, const float x, const unsigned int round_type=0) {
6207
return instance.get_round(x,round_type);
6210
template<typename T> inline CImg<T> rand(const CImg<T>& instance, const T val_min, const T val_max) {
6211
return instance.get_rand(val_min,val_max);
6214
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val) {
6215
return instance.get_fill(val);
6218
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1) {
6219
return instance.get_fill(val0,val1);
6222
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2) {
6223
return instance.get_fill(val0,val1,val2);
6226
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3) {
6227
return instance.get_fill(val0,val1,val2,val3);
6230
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6232
return instance.get_fill(val0,val1,val2,val3,val4);
6235
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6236
const T val4, const T val5) {
6237
return instance.get_fill(val0,val1,val2,val3,val4,val5);
6240
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6241
const T val4, const T val5, const T val6) {
6242
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6);
6245
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6246
const T val4, const T val5, const T val6, const T val7) {
6247
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7);
6250
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6251
const T val4, const T val5, const T val6, const T val7, const T val8) {
6252
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8);
6255
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6256
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9) {
6257
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9);
6260
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6261
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9,
6263
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9,val10);
6266
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6267
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9,
6268
const T val10, const T val11) {
6269
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9,val10,val11);
6272
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6273
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9,
6274
const T val10, const T val11, const T val12) {
6275
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9,val10,val11,val12);
6278
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6279
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9,
6280
const T val10, const T val11, const T val12, const T val13) {
6281
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9,val10,val11,val12,val13);
6284
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6285
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9,
6286
const T val10, const T val11, const T val12, const T val13, const T val14) {
6287
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9,val10,val11,val12,val13,val14);
6290
template<typename T> inline CImg<T> fill(const CImg<T>& instance, const T val0, const T val1, const T val2, const T val3,
6291
const T val4, const T val5, const T val6, const T val7, const T val8, const T val9,
6292
const T val10, const T val11, const T val12, const T val13, const T val14, const T val15) {
6293
return instance.get_fill(val0,val1,val2,val3,val4,val5,val6,val7,val8,val9,val10,val11,val12,val13,val14,val15);
6296
template<typename T, int N> inline CImg<T> fill(const CImg<T>& instance, const int val0, ...) {
6297
CImg<T> res(instance,false);
6300
res.template _fill<N,int>(val0,ap);
6305
template<typename T, int N> inline CImg<T> fill(const CImg<T>& instance, const double val0, ...) {
6306
CImg<T> res(instance,false);
6309
res.template _fill<N,double>(val0,ap);
6314
template<typename T> inline CImg<T> normalize(const CImg<T>& instance, const T a, const T b) {
6315
return instance.get_normalize(a,b);
6318
template<typename T> inline CImg<T> cut(const CImg<T>& instance, const T a, const T b) {
6319
return instance.get_cut(a,b);
6322
template<typename T> inline CImg<T> quantize(const CImg<T>& instance, const unsigned int n=256, const bool keep_range=true) {
6323
return instance.get_quantize(n,keep_range);
6326
template<typename T> inline CImg<T> threshold(const CImg<T>& instance, const T thres) {
6327
return instance.get_threshold(thres);
6330
template<typename T> inline CImg<T> rotate(const CImg<T>& instance, const float angle, const unsigned int cond=3) {
6331
return instance.get_rotate(angle,cond);
6334
template<typename T> inline CImg<T> rotate(const CImg<T>& instance, const float angle, const float cx, const float cy,
6335
const float zoom=1, const unsigned int cond=3) {
6336
return instance.get_rotate(angle,cx,cy,zoom,cond);
6339
template<typename T> inline CImg<T> resize(const CImg<T>& instance,
6340
const int pdx=-100, const int pdy=-100, const int pdz=-100, const int pdv=-100,
6341
const int interpolation_type=1, const int border_condition=-1, const bool center=false) {
6342
return instance.get_resize(pdx,pdy,pdz,pdv,interpolation_type,border_condition,center);
6345
template<typename T, typename t> inline CImg<T> resize(const CImg<T>& instance, const CImg<t>& src,
6346
const int interpolation_type=1, const int border_condition=-1,
6347
const bool center=false) {
6348
return instance.get_resize(src,interpolation_type,border_condition,center);
6351
template<typename T> inline CImg<T> resize(const CImg<T>& instance, const CImgDisplay& disp,
6352
const int interpolation_type=1, const int border_condition=-1, const bool center=false) {
6353
return instance.get_resize(disp,interpolation_type,border_condition,center);
6356
template<typename T, typename t> inline CImg<t> permute_axes(const CImg<T>& instance, const char *permut, const t& pixel_type) {
6357
return instance.get_permute_axes(instance,permut,pixel_type);
6360
template<typename T> inline CImg<T> permute_axes(const CImg<T>& instance, const char *permut="vxyz") {
6361
return instance.get_permute_axes(instance,permut);
6364
template<typename T> inline CImg<T> resize_halfXY(const CImg<T>& instance) {
6365
return instance.get_resize_halfXY();
6368
template<typename T> inline CImg<T> resize_doubleXY(const CImg<T>& instance) {
6369
return instance.get_resize_doubleXY();
6372
template<typename T> inline CImg<T> resize_tripleXY(const CImg<T>& instance) {
6373
return instance.get_resize_tripleXY();
6376
template<typename T> inline CImg<T> crop(const CImg<T>& instance, const int x0, const int y0, const int z0, const int v0,
6377
const int x1, const int y1, const int z1, const int v1,
6378
const bool border_condition=false) {
6379
return instance.get_crop(x0,y0,z0,v0,x1,y1,z1,v1,border_condition);
6382
template<typename T> inline CImg<T> crop(const CImg<T>& instance, const int x0, const int y0, const int z0,
6383
const int x1, const int y1, const int z1,
6384
const bool border_condition=false) {
6385
return instance.get_crop(x0,y0,z0,x1,y1,z1,border_condition);
6388
template<typename T> inline CImg<T> crop(const CImg<T>& instance, const int x0, const int y0,
6389
const int x1, const int y1,
6390
const bool border_condition=false) {
6391
return instance.get_crop(x0,y0,x1,y1,border_condition);
6394
template<typename T> inline CImg<T> crop(const CImg<T>& instance, const int x0, const int x1,
6395
const bool border_condition=false) {
6396
return instance.get_crop(x0,x1,border_condition);
6399
template<typename T> inline CImg<T> columns(const CImg<T>& instance, const unsigned int x0, const unsigned int x1) {
6400
return instance.get_columns(x0,x1);
6403
template<typename T> inline CImg<T> column(const CImg<T>& instance, const unsigned int x0) {
6404
return instance.get_column(x0);
6407
template<typename T> inline CImg<T> lines(const CImg<T>& instance, const unsigned int y0, const unsigned int y1) {
6408
return instance.get_lines(y0,y1);
6411
template<typename T> inline CImg<T> line(const CImg<T>& instance, const unsigned int y0) {
6412
return instance.get_line(y0);
6415
template<typename T> inline CImg<T> slices(const CImg<T>& instance, const unsigned int z0, const unsigned int z1) {
6416
return instance.get_slices(z0,z1);
6419
template<typename T> inline CImg<T> slice(const CImg<T>& instance, const unsigned int z0) {
6420
return instance.get_slice(z0);
6423
template<typename T> inline CImg<T> channels(const CImg<T>& instance, const unsigned int v0, const unsigned int v1) {
6424
return instance.get_channels(v0,v1);
6427
template<typename T> inline CImg<T> channel(const CImg<T>& instance, const unsigned int v0) {
6428
return instance.get_channel(v0);
6431
template<typename T> inline CImg<T> shared_points(CImg<T>& instance, const unsigned int x0, const unsigned int x1,
6432
const unsigned int y0=0, const unsigned int z0=0, const unsigned int v0=0) {
6433
return instance.get_shared_points(x0,x1,y0,z0,v0);
6436
template<typename T> inline CImg<T> shared_points(const CImg<T>& instance, const unsigned int x0, const unsigned int x1,
6437
const unsigned int y0=0, const unsigned int z0=0, const unsigned int v0=0) {
6438
return instance.get_shared_points(x0,x1,y0,z0,v0);
6441
template<typename T> inline CImg<T> shared_lines(CImg<T>& instance, const unsigned int y0, const unsigned int y1,
6442
const unsigned int z0=0, const unsigned int v0=0) {
6443
return instance.get_shared_lines(y0,y1,z0,v0);
6446
template<typename T> inline CImg<T> shared_lines(const CImg<T>& instance, const unsigned int y0, const unsigned int y1,
6447
const unsigned int z0=0, const unsigned int v0=0) {
6448
return instance.get_shared_lines(y0,y1,z0,v0);
6451
template<typename T> inline CImg<T> shared_line(CImg<T>& instance,
6452
const unsigned int y0, const unsigned int z0=0, const unsigned int v0=0) {
6453
return instance.get_shared_line(y0,z0,v0);
6456
template<typename T> inline CImg<T> shared_line(const CImg<T>& instance,
6457
const unsigned int y0, const unsigned int z0=0, const unsigned int v0=0) {
6458
return instance.get_shared_line(y0,z0,v0);
6461
template<typename T> inline CImg<T> shared_planes(CImg<T>& instance,
6462
const unsigned int z0, const unsigned int z1, const unsigned int v0=0) {
6463
return instance.get_shared_planes(z0,z1,v0);
6466
template<typename T> inline CImg<T> shared_planes(const CImg<T>& instance,
6467
const unsigned int z0, const unsigned int z1, const unsigned int v0=0) {
6468
return instance.get_shared_planes(z0,z1,v0);
6471
template<typename T> inline CImg<T> shared_plane(CImg<T>& instance, const unsigned int z0, const unsigned int v0=0) {
6472
return instance.get_shared_plane(z0,v0);
6475
template<typename T> inline CImg<T> shared_plane(const CImg<T>& instance, const unsigned int z0, const unsigned int v0=0) {
6476
return instance.get_shared_plane(z0,v0);
6479
template<typename T> inline CImg<T> shared_channels(CImg<T>& instance, const unsigned int v0, const unsigned int v1) {
6480
return instance.get_shared_channels(v0,v1);
6483
template<typename T> inline CImg<T> shared_channels(const CImg<T>& instance, const unsigned int v0, const unsigned int v1) {
6484
return instance.get_shared_channels(v0,v1);
6487
template<typename T> inline CImg<T> shared_channel(CImg<T>& instance, const unsigned int v0) {
6488
return instance.get_shared_channel(v0);
6491
template<typename T> inline CImg<T> shared_channel(const CImg<T>& instance, const unsigned int v0) {
6492
return instance.get_shared_channel(v0);
6495
template<typename T> inline CImg<T> shared(CImg<T>& instance) {
6496
return instance.get_shared();
6499
template<typename T> inline CImg<T> shared(const CImg<T>& instance) {
6500
return instance.get_shared();
6503
template<typename T> inline CImg<T> mirror(const CImg<T>& instance, const char axe='x') {
6504
return instance.get_mirror(axe);
6507
template<typename T> inline CImg<T> translate(const CImg<T>& instance, const int deltax, const int deltay=0, const int deltaz=0,
6508
const int deltav=0, const int border_condition=0) {
6509
return instance.get_translate(deltax,deltay,deltaz,deltav,border_condition);
6512
template<typename T> inline CImg<T> projections2d(const CImg<T>& instance,
6513
const unsigned int x0, const unsigned int y0, const unsigned int z0,
6514
const int dx=-100, const int dy=-100, const int dz=-100) {
6515
return instance.get_projections2d(x0,y0,z0,dx,dy,dz);
6518
template<typename T> inline CImg<typename cimg::last<T,float>::type>
6519
histogram(const CImg<T>& instance, const unsigned int nblevels=256, const T val_min=(T)0, const T val_max=(T)0) {
6520
return instance.get_histogram(nblevels,val_min,val_max);
6523
template<typename T> inline CImg<T> equalize_histogram(const CImg<T>& instance,
6524
const unsigned int nblevels=256, const T val_min=(T)0, const T val_max=(T)0) {
6525
return instance.get_equalize_histogram(nblevels,val_min,val_max);
6528
template<typename T> inline CImg<typename cimg::last<T,unsigned int>::type> label_regions(const CImg<T>& instance) {
6529
return instance.get_label_regions();
6532
template<typename T> inline CImg<_cimg_Tfloat> norm_pointwise(const CImg<T>& instance, int norm_type=2) {
6533
return instance.get_norm_pointwise(norm_type);
6536
template<typename T> inline CImg<_cimg_Tfloat> orientation_pointwise(const CImg<T>& instance) {
6537
return instance.get_orientation_pointwise();
6540
template<typename T> inline CImgList<T> split(const CImg<T>& instance, const char axe='x', const unsigned int nb=0) {
6541
return instance.get_split(axe,nb);
6544
template<typename T> inline CImg<T> append(const CImg<T>& instance, const CImg<T>& img, const char axis='x', const char align='c') {
6545
return instance.get_append(img,axis,align);
6548
template<typename T> inline CImgList<_cimg_Tfloat> gradientXY(const CImg<T>& instance, const int scheme=0) {
6549
return instance.get_gradientXY(scheme);
6552
template<typename T> inline CImgList<_cimg_Tfloat> gradientXYZ(const CImg<T>& instance, const int scheme=0) {
6553
return instance.get_gradientXYZ(scheme);
6556
template<typename T> inline CImg<_cimg_Tfloat> structure_tensorXY(const CImg<T>& instance, const int scheme=1) {
6557
return instance.get_structure_tensorXY(scheme);
6560
template<typename T> inline CImg<_cimg_Tfloat> structure_tensorXYZ(const CImg<T>& instance, const int scheme=1) {
6561
return instance.get_structure_tensorXYZ(scheme);
6564
template<typename T> inline CImg<_cimg_Tfloat>
6565
distance_function(const CImg<T>& instance, const unsigned int nb_iter=100, const float band_size=0.0f, const float precision=0.5f) {
6566
return instance.get_distance_function(nb_iter,band_size,precision);
6569
template<typename T, typename t> inline CImg<_cimg_Tfloat>
6570
dijkstra(const CImg<T>& instance, const unsigned int starting_node, const unsigned int ending_node, CImg<t>& previous) {
6571
return instance.get_dijkstra(starting_node,ending_node,previous);
6574
template<typename T, typename t> inline CImg<_cimg_Tfloat>
6575
dijkstra(const CImg<T>& instance, const unsigned int starting_node, const unsigned int ending_node=~0U) {
6576
return instance.get_dijkstra(starting_node,ending_node);
6579
template<typename T, typename t> inline CImg<t> RGBtoLUT(const CImg<T>& instance, const CImg<t>& palette,
6580
const bool dithering=true, const bool indexing=false) {
6581
return instance.get_RGBtoLUT(palette,dithering,indexing);
6584
template<typename T> inline CImg<_cimg_Tuchar> RGBtoLUT(const CImg<T>& instance,
6585
const bool dithering=true, const bool indexing=false) {
6586
return instance.get_RGBtoLUT(dithering,indexing);
6589
template<typename T, typename t> inline CImg<t> LUTtoRGB(const CImg<T>& instance, const CImg<t>& palette) {
6590
return instance.get_LUTtoRGB(palette);
6593
template<typename T> inline CImg<_cimg_Tuchar> LUTtoRGB(const CImg<T>& instance) {
6594
return instance.get_LUTtoRGB();
6597
template<typename T> inline CImg<_cimg_Tfloat> RGBtoHSV(const CImg<T>& instance) {
6598
return instance.get_RGBtoHSV();
6601
template<typename T> inline CImg<_cimg_Tfloat> HSVtoRGB(const CImg<T>& instance) {
6602
return instance.get_HSVtoRGB();
6605
template<typename T> inline CImg<_cimg_Tfloat> RGBtoHSL(const CImg<T>& instance) {
6606
return instance.get_RGBtoHSL();
6609
template<typename T> inline CImg<_cimg_Tuchar> HSLtoRGB(const CImg<T>& instance) {
6610
return instance.get_HSLtoRGB();
6613
template<typename T> inline CImg<_cimg_Tfloat> RGBtoHSI(const CImg<T>& instance) {
6614
return instance.get_RGBtoHSI();
6617
template<typename T> inline CImg<_cimg_Tuchar> HSItoRGB(const CImg<T>& instance) {
6618
return instance.get_HSItoRGB();
6621
template<typename T> inline CImg<_cimg_Tuchar> RGBtoYCbCr(const CImg<T>& instance) {
6622
return instance.get_RGBtoYCbCr();
6625
template<typename T> inline CImg<_cimg_Tuchar> YCbCrtoRGB(const CImg<T>& instance) {
6626
return instance.get_YCbCrtoRGB();
6629
template<typename T> inline CImg<_cimg_Tfloat> RGBtoYUV(const CImg<T>& instance) {
6630
return instance.get_RGBtoYUV();
6633
template<typename T> inline CImg<_cimg_Tuchar> YUVtoRGB(const CImg<T>& instance) {
6634
return instance.get_YUVtoRGB();
6637
template<typename T> inline CImg<_cimg_Tfloat> RGBtoXYZ(const CImg<T>& instance) {
6638
return instance.get_RGBtoXYZ();
6641
template<typename T> inline CImg<_cimg_Tuchar> XYZtoRGB(const CImg<T>& instance) {
6642
return instance.get_XYZtoRGB();
6645
template<typename T> inline CImg<_cimg_Tfloat> RGBtoCMY(const CImg<T>& instance) {
6646
return instance.get_RGBtoCMY();
6649
template<typename T> inline CImg<_cimg_Tuchar> CMYtoRGB(const CImg<T>& instance) {
6650
return instance.get_CMYtoRGB();
6653
template<typename T> inline CImg<_cimg_Tfloat> CMYtoCMYK(const CImg<T>& instance) {
6654
return instance.get_CMYtoCMYK();
6657
template<typename T> inline CImg<_cimg_Tfloat> CMYKtoCMY(const CImg<T>& instance) {
6658
return instance.get_CMYKtoCMY();
6661
template<typename T> inline CImg<_cimg_Tfloat> RGBtoCMYK(const CImg<T>& instance) {
6662
return instance.get_RGBtoCMYK();
6665
template<typename T> inline CImg<_cimg_Tuchar> CMYKtoRGB(const CImg<T>& instance) {
6666
return instance.get_CMYKtoRGB();
6669
template<typename T> inline CImg<_cimg_Tfloat> XYZtoLab(const CImg<T>& instance) {
6670
return instance.get_XYZtoLab();
6673
template<typename T> inline CImg<_cimg_Tfloat> LabtoXYZ(const CImg<T>& instance) {
6674
return instance.get_LabtoXYZ();
6677
template<typename T> inline CImg<_cimg_Tfloat> XYZtoxyY(const CImg<T>& instance) {
6678
return instance.get_XYZtoxyY();
6681
template<typename T> inline CImg<_cimg_Tfloat> xyYtoXYZ(const CImg<T>& instance) {
6682
return instance.get_xyYtoXYZ();
6685
template<typename T> inline CImg<_cimg_Tfloat> RGBtoLab(const CImg<T>& instance) {
6686
return instance.get_RGBtoLab();
6689
template<typename T> inline CImg<_cimg_Tuchar> LabtoRGB(const CImg<T>& instance) {
6690
return instance.get_LabtoRGB();
6693
template<typename T> inline CImg<_cimg_Tfloat> RGBtoxyY(const CImg<T>& instance) {
6694
return instance.get_RGBtoxyY();
6697
template<typename T> inline CImg<_cimg_Tuchar> xyYtoRGB(const CImg<T>& instance) {
6698
return instance.get_xyYtoRGB();
6701
template<typename T> inline CImg<T> RGBtoBayer(const CImg<T>& instance, const bool even_mode=true) {
6702
return instance.get_RGBtoBayer(even_mode);
6705
template<typename T> inline CImg<T> BayertoRGB(const CImg<T>& instance, const unsigned int interpolation_type=3, const bool even_mode=true) {
6706
return instance.get_BayertoRGB(interpolation_type,even_mode);
6709
template<typename T, typename t> inline CImg<_cimg_Tt>
6710
correlate(const CImg<T>& instance, const CImg<t>& mask, const unsigned int cond=1, const bool weighted_correl=false) {
6711
return instance.get_correlate(mask,cond,weighted_correl);
6714
template<typename T, typename t> inline CImg<_cimg_Tt>
6715
convolve(const CImg<T>& instance, const CImg<t>& mask, const unsigned int cond=1, const bool weighted_convol=false) {
6716
return instance.get_convolve(mask,cond,weighted_convol);
6719
template<typename T, typename t> inline CImg<_cimg_Tt>
6720
erode(const CImg<T>& instance, const CImg<t>& mask, const unsigned int cond=1, const bool weighted_erosion=false) {
6721
return instance.get_erode(mask,cond,weighted_erosion);
6724
template<typename T> inline CImg<T> erode(const CImg<T>& instance, const unsigned int n, const unsigned int cond=1) {
6725
return instance.get_erode(n,cond);
6728
template<typename T, typename t> inline CImg<_cimg_Tt>
6729
dilate(const CImg<T>& instance, const CImg<t>& mask, const unsigned int cond=1, const bool weighted_dilatation=false) {
6730
return instance.get_dilate(mask,cond,weighted_dilatation);
6733
template<typename T> inline CImg<T> dilate(const CImg<T>& instance, const unsigned int n, const unsigned int cond=1) {
6734
return instance.get_dilate(n,cond);
6737
template<typename T> inline CImg<T> noise(const CImg<T>& instance, const double sigma=-20, const unsigned int ntype=0) {
6738
return instance.get_noise(sigma,ntype);
6741
template<typename T> inline CImg<_cimg_Tfloat>
6742
deriche(const CImg<T>& instance, const float sigma, const int order=0, const char axe='x', const bool cond=true) {
6743
return instance.get_deriche(sigma,order,axe,cond);
6746
template<typename T> inline CImg<_cimg_Tfloat>
6747
blur(const CImg<T>& instance, const float sigmax, const float sigmay, const float sigmaz, const bool cond=true) {
6748
return instance.get_blur(sigmax,sigmay,sigmaz,cond);
6751
template<typename T> inline CImg<_cimg_Tfloat>
6752
blur(const CImg<T>& instance, const float sigma, const bool cond=true) {
6753
return instance.get_blur(sigma,cond);
6756
template<typename T, typename t> inline CImg<T> blur_anisotropic(const CImg<T>& instance, const CImg<t>& G, const float amplitude=60.0f,
6757
const float dl=0.8f, const float da=30.0f,
6758
const float gauss_prec=2.0f, const unsigned int interpolation_type=0,
6759
const bool fast_approx=true) {
6760
return instance.get_blur_anisotropic(G,amplitude,dl,da,gauss_prec,interpolation_type,fast_approx);
6763
template<typename T, typename tm> inline CImg<T> blur_anisotropic(const CImg<T>& instance, const CImg<tm>& mask,
6764
const float amplitude, const float sharpness=0.7f, const float anisotropy=0.3f,
6765
const float alpha=0.6f, const float sigma=1.1f, const float dl=0.8f,
6766
const float da=30.0f, const float gauss_prec=2.0f,
6767
const unsigned int interpolation_type=0, const bool fast_approx=true,
6768
const float geom_factor=1.0f) {
6769
return instance.get_blur_anisotropic(mask,amplitude,sharpness,anisotropy,alpha,sigma,dl,da,gauss_prec,interpolation_type,fast_approx,geom_factor);
6772
template<typename T> inline CImg<T> blur_anisotropic(const CImg<T>& instance, const float amplitude, const float sharpness=0.7f,
6773
const float anisotropy=0.3f,
6774
const float alpha=0.6f, const float sigma=1.1f, const float dl=0.8f,
6775
const float da=30.0f, const float gauss_prec=2.0f, const unsigned int interpolation_type=0,
6776
const bool fast_approx=true, const float geom_factor=1.0f) {
6777
return instance.get_blur_anisotropic(amplitude,sharpness,anisotropy,alpha,sigma,dl,da,gauss_prec,interpolation_type,fast_approx,geom_factor);
6780
template<typename T> inline CImg<T> blur_bilateral(const CImg<T>& instance,
6781
const float sigmax, const float sigmay, const float sigmaz, const float sigmar,
6782
const int bgridx, const int bgridy, const int bgridz, const int bgridr,
6783
const bool interpolation_type=true) {
6784
return instance.get_blur_bilateral(sigmax,sigmay,sigmaz,sigmar,bgridx,bgridy,bgridz,bgridr,interpolation_type);
6787
template<typename T> inline CImg<T> blur_bilateral(const CImg<T>& instance,
6788
const float sigmas, const float sigmar, const int bgrids=-33, const int bgridr=32,
6789
const bool interpolation_type=true) {
6790
return instance.get_blur_bilateral(sigmas,sigmar,bgrids,bgridr,interpolation_type);
6793
template<typename T> inline CImg<T> blur_patch(const CImg<T>& instance, const unsigned int patch_size=3,
6794
const float sigma_p=10.0f, const float sigma_s=10.0f,
6795
const unsigned int lookup_size=4, const bool fast_approx=true) {
6796
return instance.get_blur_patch(patch_size,sigma_p,sigma_s,lookup_size,fast_approx);
6799
template<typename T> inline CImgList<_cimg_Tfloat> FFT(const CImg<T>& instance, const char axe, const bool invert=false) {
6800
return instance.get_FFT(axe,invert);
6803
template<typename T> inline CImgList<_cimg_Tfloat> FFT(const CImg<T>& instance, const bool invert=false) {
6804
return instance.get_FFT(invert);
6807
template<typename T> inline CImg<T> blur_median(const CImg<T>& instance, const unsigned int n=3) {
6808
return instance.get_blur_median(n);
6811
template<typename T> inline CImg<T> sharpen(const CImg<T>& instance, const float amplitude=50.0f, const float edge=1.0f,
6812
const float alpha=0.0f, const float sigma=0.0f) {
6813
return instance.get_sharpen(amplitude,edge,alpha,sigma);
6816
template<typename T> inline CImg<_cimg_Tfloat>
6817
haar(const CImg<T>& instance, const char axis, const bool invert=false, const unsigned int nb_scales=1) {
6818
return instance.get_haar(axis,invert,nb_scales);
6821
template<typename T> inline CImg<_cimg_Tfloat>
6822
haar(const CImg<T>& instance, const bool invert=false, const unsigned int nb_scales=1) {
6823
return instance.get_haar(invert,nb_scales);
6826
template<typename T> inline CImg<_cimg_Tfloat>
6827
displacement_field(const CImg<T>& instance, const CImg<T>& target,
6828
const float smooth=0.1f, const float precision=0.1f,
6829
const unsigned int nb_scales=0, const unsigned int itermax=10000) {
6830
return instance.get_displacement_field(target,smooth,precision,nb_scales,itermax);
6833
template<typename T> inline CImg<T> matrix(const CImg<T>& instance) {
6834
return instance.get_matrix();
6837
template<typename T> inline CImg<T> tensor(const CImg<T>& instance) {
6838
return instance.get_tensor();
6841
template<typename T> inline CImg<T> unroll(const CImg<T>& instance, const char axe='x') {
6842
return instance.get_unroll(axe);
6845
template<typename T> inline CImg<T> diagonal(const CImg<T>& instance) {
6846
return instance.get_diagonal();
6849
template<typename T> inline CImg<T> identity_matrix(const CImg<T>& instance) {
6850
return instance.get_identity_matrix();
6853
template<typename T> inline CImg<T> sequence(const CImg<T>& instance, const T a0, const T a1) {
6854
return instance.get_sequence(a0,a1);
6857
template<typename T> inline CImg<T> vector_at(const CImg<T>& instance, const unsigned int x=0, const unsigned int y=0, const unsigned int z=0) {
6858
return instance.get_vector_at(x,y,z);
6861
template<typename T> inline CImg<T> matrix_at(const CImg<T>& instance, const unsigned int x=0, const unsigned int y=0, const unsigned int z=0) {
6862
return instance.get_matrix_at(x,y,z);
6865
template<typename T> inline CImg<T> tensor_at(const CImg<T>& instance, const unsigned int x=0, const unsigned int y=0, const unsigned int z=0) {
6866
return instance.get_tensor_at(x,y,z);
6869
template<typename T> inline CImg<T> transpose(const CImg<T>& instance) {
6870
return instance.get_transpose();
6873
template<typename T> inline CImg<_cimg_Tfloat> invert(const CImg<T>& instance, const bool use_LU=true) {
6874
return instance.get_invert(use_LU);
6877
template<typename T> inline CImg<_cimg_Tfloat> pseudoinvert(const CImg<T>& instance) {
6878
return instance.get_pseudoinvert();
6881
template<typename T, typename t> inline CImg<_cimg_Tt> cross(const CImg<T>& instance, const CImg<t>& img) {
6882
return instance.get_cross(img);
6885
template<typename T> inline CImgList<_cimg_Tfloat> SVD(const CImg<T>& instance, const bool sorting=true) {
6886
return instance.get_SVD(sorting);
6889
template<typename T, typename t> inline CImg<typename cimg::superset2<T,t,float>::type> solve(const CImg<T>& instance, const CImg<t>& A) {
6890
return instance.get_solve(A);
6893
template<typename T> inline CImgList<_cimg_Tfloat> eigen(const CImg<T>& instance) {
6894
return instance.get_eigen();
6897
template<typename T> inline CImgList<_cimg_Tfloat> symmetric_eigen(const CImg<T>& instance) {
6898
return instance.get_symmetric_eigen();
6901
template<typename T, typename t> inline CImg<T> sort(const CImg<T>& instance, CImg<t>& permutations, const bool increasing=true) {
6902
return instance.get_sort(permutations,increasing);
6905
template<typename T> inline CImg<T> sort(const CImg<T>& instance, const bool increasing=true) {
6906
return instance.get_sort(increasing);
6909
template<typename T, typename t> inline CImg<T> permute(const CImg<T>& instance, const CImg<t>& permutation) {
6910
return instance.get_permute(permutation);
6913
template<typename T> inline CImg<typename cimg::last<T,int>::type>
6914
coordinates(const CImg<T>& instance, const int coords_type, CImgDisplay &disp,
6915
unsigned int *const XYZ=0, const unsigned char *const color=0) {
6916
return instance.get_coordinates(coords_type,disp,XYZ,color);
6919
template<typename T, typename t> inline CImgList<_cimg_Tt>
6920
insert(const CImgList<T>& instance, const CImg<t>& img, const unsigned int pos=~0U, const bool shared=false) {
6921
return instance.get_insert(img,pos,shared);
6924
template<typename T, typename t> inline CImgList<_cimg_Tt>
6925
insert(const CImgList<T>& instance, const unsigned int n, const CImg<t>& img,
6926
const unsigned int pos=~0U, const bool shared=false) {
6927
return instance.get_insert(n,img,pos,shared);
6930
template<typename T, typename t> inline CImgList<_cimg_Tt>
6931
insert(const CImgList<T>& instance, const CImgList<t>& list, const unsigned int pos=~0U, int shared=0) {
6932
return instance.get_insert(list,pos,shared);
6935
template<typename T, typename t> inline CImgList<_cimg_Tt>
6936
insert(const CImgList<T>& instance, const unsigned int n, const CImgList<t>& list, const unsigned int pos=~0U, const int shared=0) {
6937
return instance.insert(n,list,pos,shared);
6940
template<typename T> inline CImgList<T> remove(const CImgList<T>& instance, const unsigned int pos) {
6941
return instance.get_remove(pos);
6944
template<typename T> inline CImgList<T> remove(const CImgList<T>& instance) {
6945
return instance.get_remove();
6948
template<typename T> inline CImgList<T> reverse(const CImgList<T>& instance) {
6949
return instance.get_reverse();
6952
template<typename T> inline CImgList<T> crop(const CImgList<T>& instance, const unsigned int i0, const unsigned int i1,
6953
const bool shared=false) {
6954
return instance.get_crop(i0,i1,shared);
6957
template<typename T> inline CImgList<T> crop(const CImgList<T>& instance, const unsigned int i0, const unsigned int i1,
6958
const int x0, const int y0, const int z0, const int v0,
6959
const int x1, const int y1, const int z1, const int v1) {
6960
return instance.get_crop(i0,i1,x0,y0,z0,v0,x1,y1,z1,v1);
6963
template<typename T> inline CImgList<T> crop(const CImgList<T>& instance, const unsigned int i0, const unsigned int i1,
6964
const int x0, const int y0, const int z0,
6965
const int x1, const int y1, const int z1) {
6966
return instance.get_crop(i0,i1,x0,y0,z0,x1,y1,z1);
6969
template<typename T> inline CImgList<T> crop(const CImgList<T>& instance, const unsigned int i0, const unsigned int i1,
6970
const int x0, const int y0,
6971
const int x1, const int y1) {
6972
return instance.get_crop(i0,i1,x0,y0,x1,y1);
6975
template<typename T> inline CImgList<T> crop(const CImgList<T>& instance, const unsigned int i0, const unsigned int i1,
6976
const int x0, const int x1) {
6977
return instance.get_crop(i0,i1,x0,x1);
6980
template<typename T> inline CImgList<_cimg_Tfloat>
6981
FFT(const CImgList<T>& instance, const char axe, const bool invert=false) {
6982
return instance.get_FFT(axe,invert);
6985
template<typename T> inline CImgList<_cimg_Tfloat>
6986
FFT(const CImgList<T>& instance, const bool invert=false) {
6987
return instance.get_FFT(invert);
6990
template<typename T> inline CImgList<T> split(const CImgList<T>& instance, const char axe='x') {
6991
return instance.get_split(axe);
6994
template<typename T> inline CImg<T> append(const CImgList<T>& instance, const char axe='x', const char align='c') {
6995
return instance.get_append(axe,align);
6998
template<typename T> inline CImgList<T> crop_font(const CImgList<T>& instance) {
6999
return instance.get_crop_font();
7002
/*-------------------------------------------
7703
//! Read a pixel value with Dirichlet or Neumann boundary conditions.
7705
\param x X-coordinate of the pixel.
7706
\param y Y-coordinate of the pixel.
7707
\param z Z-coordinate of the pixel.
7708
\param v V-coordinate of the pixel.
7709
\param out_val Desired value if pixel coordinates are outside the image range (optional parameter).
7711
- This function allows to read pixel values with boundary checking on all coordinates.
7712
- If given coordinates are outside the image range and the parameter out_val is specified, the value \c out_val is returned.
7713
- If given coordinates are outside the image range and the parameter out_val is not specified, the closest pixel value
7718
CImg<float> img(100,100,1,1,128); // Define a 100x100 images with all pixel values equal to 128.
7719
const float val1 = img.pix4d(10,10,0,0,0); // Equivalent to val1=img(10,10) (but slower).
7720
const float val2 = img.pix4d(-4,5,0,0,0); // Return 0, since coordinates are outside the image range.
7721
const float val3 = img.pix4d(10,10,5,0,64); // Return 64, since coordinates are outside the image range.
7724
\sa operator()(), linear_pix4d(), cubic_pix2d().
7726
T pix4d(const int x, const int y, const int z, const int v, const T& out_val) const {
11622
//! Read a pixel value with Dirichlet boundary conditions.
11623
T at(const int x, const int y, const int z, const int v, const T out_val) const {
11624
return at4(x,y,z,v,out_val);
11627
//! Read a pixel value with Neumann boundary conditions.
11628
T& at(const int x, const int y=0, const int z=0, const int v=0) {
11629
return at4(x,y,z,v);
11632
const T& at(const int x, const int y=0, const int z=0, const int v=0) const {
11633
return at4(x,y,z,v);
11636
//! Read a pixel value with Dirichlet boundary conditions.
11637
T at4(const int x, const int y, const int z, const int v, const T out_val) const {
7727
11638
return (x<0 || y<0 || z<0 || v<0 || x>=dimx() || y>=dimy() || z>=dimz() || v>=dimv())?out_val:(*this)(x,y,z,v);
7730
T pix4d(const int x, const int y, const int z, const int v) const {
7731
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),
7732
z<0?0:(z>=dimz()?dimz()-1:z), v<0?0:(v>=dimv()?dimv()-1:v));
7735
//! Read a pixel value with Dirichlet or Neumann boundary conditions for the three first coordinates (\c x,\c y,\c z).
7736
T pix3d(const int x, const int y, const int z, const int v, const T& out_val) const {
11641
//! Read a pixel value with Neumann boundary conditions.
11642
T& at4(const int x, const int y=0, const int z=0, const int v=0) {
11643
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),
11644
z<0?0:(z>=dimz()?dimz()-1:z), v<0?0:(v>=dimv()?dimv()-1:v));
11647
const T& at4(const int x, const int y=0, const int z=0, const int v=0) const {
11648
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),
11649
z<0?0:(z>=dimz()?dimz()-1:z), v<0?0:(v>=dimv()?dimv()-1:v));
11652
//! Read a pixel value with Dirichlet boundary conditions for the three first coordinates (\c x,\c y,\c z).
11653
T at3(const int x, const int y, const int z, const int v, const T out_val) const {
7737
11654
return (x<0 || y<0 || z<0 || x>=dimx() || y>=dimy() || z>=dimz())?out_val:(*this)(x,y,z,v);
7740
const T& pix3d(const int x, const int y, const int z, const int v=0) const {
7741
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),
7742
z<0?0:(z>=dimz()?dimz()-1:z),v);
7745
//! Read a pixel value with Dirichlet or Neumann boundary conditions for the two first coordinates (\c x,\c y).
7746
T pix2d(const int x, const int y, const int z, const int v, const T& out_val) const {
11657
//! Read a pixel value with Neumann boundary conditions for the three first coordinates (\c x,\c y,\c z).
11658
T& at3(const int x, const int y, const int z, const int v=0) {
11659
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),
11660
z<0?0:(z>=dimz()?dimz()-1:z),v);
11663
const T& at3(const int x, const int y, const int z, const int v=0) const {
11664
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),
11665
z<0?0:(z>=dimz()?dimz()-1:z),v);
11668
//! Read a pixel value with Dirichlet boundary conditions for the two first coordinates (\c x,\c y).
11669
T at2(const int x, const int y, const int z, const int v, const T out_val) const {
7747
11670
return (x<0 || y<0 || x>=dimx() || y>=dimy())?out_val:(*this)(x,y,z,v);
7750
const T& pix2d(const int x, const int y, const int z=0, const int v=0) const {
7751
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),z,v);
7754
//! Read a pixel value with Dirichlet or Neumann boundary conditions for the first coordinate \c x.
7755
T pix1d(const int x, const int y, const int z, const int v, const T& out_val) const {
11673
//! Read a pixel value with Neumann boundary conditions for the two first coordinates (\c x,\c y).
11674
T& at2(const int x, const int y, const int z=0, const int v=0) {
11675
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),z,v);
11678
const T& at2(const int x, const int y, const int z=0, const int v=0) const {
11679
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x), y<0?0:(y>=dimy()?dimy()-1:y),z,v);
11682
//! Read a pixel value with Dirichlet boundary conditions for the first coordinates (\c x).
11683
T at1(const int x, const int y, const int z, const int v, const T out_val) const {
7756
11684
return (x<0 || x>=dimx())?out_val:(*this)(x,y,z,v);
7759
const T& pix1d(const int x, const int y=0, const int z=0, const int v=0) const {
7760
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x),y,z,v);
7763
//! Read a pixel value using linear interpolation.
7765
\param ffx X-coordinate of the pixel (float-valued).
7766
\param ffy Y-coordinate of the pixel (float-valued).
7767
\param ffz Z-coordinate of the pixel (float-valued).
7768
\param ffv V-coordinate of the pixel (float-valued).
7769
\param out_val Out-of-border pixel value
7771
- This function allows to read pixel values with boundary checking on all coordinates.
7772
- If given coordinates are outside the image range, the value of the nearest pixel inside the image is returned
7773
(Neumann boundary conditions).
7774
- If given coordinates are float-valued, a linear interpolation is performed in order to compute the returned value.
7778
CImg<float> img(2,2); // Define a greyscale 2x2 image.
7779
img(0,0) = 0; // Fill image with specified pixel values.
7783
const double val = img.linear_pix4d(0.5,0.5); // Return val=1.5, which is the average intensity of the four pixels values.
7786
\sa operator()(), linear_pix3d(), linear_pix2d(), linear_pix1d(), cubic_pix2d().
7788
typename cimg::largest<T,float>::type linear_pix4d(const float fx, const float fy, const float fz, const float fv,
7789
const T& out_val) const {
7790
const int x = (int)fx-(fx>=0?0:1), y = (int)fy-(fy>=0?0:1), z = (int)fz-(fz>=0?0:1), v = (int)fv-(fv>=0?0:1),
7791
nx = x+1, ny = y+1, nz = z+1, nv = v+1;
7792
const float dx = fx-x, dy = fy-y, dz = fz-z, dv = fv-v;
7794
Icccc = pix4d(x,y,z,v,out_val), Inccc = pix4d(nx,y,z,v,out_val),
7795
Icncc = pix4d(x,ny,z,v,out_val), Inncc = pix4d(nx,ny,z,v,out_val),
7796
Iccnc = pix4d(x,y,nz,v,out_val), Incnc = pix4d(nx,y,nz,v,out_val),
7797
Icnnc = pix4d(x,ny,nz,v,out_val), Innnc = pix4d(nx,ny,nz,v,out_val),
7798
Icccn = pix4d(x,y,z,nv,out_val), Inccn = pix4d(nx,y,z,nv,out_val),
7799
Icncn = pix4d(x,ny,z,nv,out_val), Inncn = pix4d(nx,ny,z,nv,out_val),
7800
Iccnn = pix4d(x,y,nz,nv,out_val), Incnn = pix4d(nx,y,nz,nv,out_val),
7801
Icnnn = pix4d(x,ny,nz,nv,out_val), Innnn = pix4d(nx,ny,nz,nv,out_val);
7804
dy*(Icccc+Inncc-Icncc-Inccc +
7805
dz*(Iccnc+Innnc+Icncc+Inccc-Icnnc-Incnc-Icccc-Inncc +
7806
dv*(Iccnn+Innnn+Icncn+Inccn+Icnnc+Incnc+Icccc+Inncc-Icnnn-Incnn-Icccn-Inncn-Iccnc-Innnc-Icncc-Inccc)) +
7807
dv*(Icccn+Inncn+Icncc+Inccc-Icncn-Inccn-Icccc-Inncc)) +
7808
dz*(Icccc+Incnc-Iccnc-Inccc +
7809
dv*(Icccn+Incnn+Iccnc+Inccc-Iccnn-Inccn-Icccc-Incnc)) +
7810
dv*(Icccc+Inccn-Inccc-Icccn)) +
7812
dz*(Icccc+Icnnc-Iccnc-Icncc +
7813
dv*(Icccn+Icnnn+Iccnc+Icncc-Iccnn-Icncn-Icccc-Icnnc)) +
7814
dv*(Icccc+Icncn-Icncc-Icccn)) +
7816
dv*(Icccc+Iccnn-Iccnc-Icccn)) +
7820
typename cimg::largest<T,float>::type linear_pix4d(const float ffx, const float ffy=0, const float ffz=0, const float ffv=0) const {
7822
fx = ffx<0?0:(ffx>width-1?width-1:ffx), fy = ffy<0?0:(ffy>height-1?height-1:ffy),
7823
fz = ffz<0?0:(ffz>depth-1?depth-1:ffz), fv = ffv<0?0:(ffv>dim-1?dim-1:ffv);
7824
const unsigned int x = (unsigned int)fx, y = (unsigned int)fy, z = (unsigned int)fz, v = (unsigned int)fv;
7825
const float dx = fx-x, dy = fy-y, dz = fz-z, dv = fv-v;
7826
const unsigned int nx = dx>0?x+1:x, ny = dy>0?y+1:y, nz = dz>0?z+1:z, nv = dv>0?v+1:v;
7828
&Icccc = (*this)(x,y,z,v), &Inccc = (*this)(nx,y,z,v), &Icncc = (*this)(x,ny,z,v), &Inncc = (*this)(nx,ny,z,v),
7829
&Iccnc = (*this)(x,y,nz,v), &Incnc = (*this)(nx,y,nz,v), &Icnnc = (*this)(x,ny,nz,v), &Innnc = (*this)(nx,ny,nz,v),
7830
&Icccn = (*this)(x,y,z,nv), &Inccn = (*this)(nx,y,z,nv), &Icncn = (*this)(x,ny,z,nv), &Inncn = (*this)(nx,ny,z,nv),
7831
&Iccnn = (*this)(x,y,nz,nv), &Incnn = (*this)(nx,y,nz,nv), &Icnnn = (*this)(x,ny,nz,nv), &Innnn = (*this)(nx,ny,nz,nv);
7834
dy*(Icccc+Inncc-Icncc-Inccc +
7835
dz*(Iccnc+Innnc+Icncc+Inccc-Icnnc-Incnc-Icccc-Inncc +
7836
dv*(Iccnn+Innnn+Icncn+Inccn+Icnnc+Incnc+Icccc+Inncc-Icnnn-Incnn-Icccn-Inncn-Iccnc-Innnc-Icncc-Inccc)) +
7837
dv*(Icccn+Inncn+Icncc+Inccc-Icncn-Inccn-Icccc-Inncc)) +
7838
dz*(Icccc+Incnc-Iccnc-Inccc +
7839
dv*(Icccn+Incnn+Iccnc+Inccc-Iccnn-Inccn-Icccc-Incnc)) +
7840
dv*(Icccc+Inccn-Inccc-Icccn)) +
7842
dz*(Icccc+Icnnc-Iccnc-Icncc +
7843
dv*(Icccn+Icnnn+Iccnc+Icncc-Iccnn-Icncn-Icccc-Icnnc)) +
7844
dv*(Icccc+Icncn-Icncc-Icccn)) +
7846
dv*(Icccc+Iccnn-Iccnc-Icccn)) +
7850
//! Read a pixel value using linear interpolation for the three first coordinates (\c cx,\c cy,\c cz).
7852
- Same as linear_pix4d(), except that linear interpolation and boundary checking is performed only on the three first coordinates.
7854
\sa operator()(), linear_pix4d(), linear_pix2d(), linear_pix1d(), linear_pix3d(), cubic_pix2d().
7856
typename cimg::largest<T,float>::type linear_pix3d(const float fx, const float fy, const float fz, const int v,
7857
const T& out_val) const {
7858
const int x = (int)fx-(fx>=0?0:1), y = (int)fy-(fy>=0?0:1), z = (int)fz-(fz>=0?0:1), nx = x+1, ny = y+1, nz = z+1;
7859
const float dx = fx-x, dy = fy-y, dz = fz-z;
7861
Iccc = pix3d(x,y,z,v,out_val), Incc = pix3d(nx,y,z,v,out_val), Icnc = pix3d(x,ny,z,v,out_val), Innc = pix3d(nx,ny,z,v,out_val),
7862
Iccn = pix3d(x,y,nz,v,out_val), Incn = pix3d(nx,y,nz,v,out_val), Icnn = pix3d(x,ny,nz,v,out_val), Innn = pix3d(nx,ny,nz,v,out_val);
7865
dy*(Iccc+Innc-Icnc-Incc +
7866
dz*(Iccn+Innn+Icnc+Incc-Icnn-Incn-Iccc-Innc)) +
7867
dz*(Iccc+Incn-Iccn-Incc)) +
7869
dz*(Iccc+Icnn-Iccn-Icnc)) +
7873
typename cimg::largest<T,float>::type linear_pix3d(const float ffx, const float ffy=0, const float ffz=0, const int v=0) const {
7874
const float fx = ffx<0?0:(ffx>width-1?width-1:ffx), fy = ffy<0?0:(ffy>height-1?height-1:ffy), fz = ffz<0?0:(ffz>depth-1?depth-1:ffz);
7875
const unsigned int x = (unsigned int)fx, y = (unsigned int)fy, z = (unsigned int)fz;
7876
const float dx = fx-x, dy = fy-y, dz = fz-z;
7877
const unsigned int nx = dx>0?x+1:x, ny = dy>0?y+1:y, nz = dz>0?z+1:z;
7879
&Iccc = (*this)(x,y,z,v), &Incc = (*this)(nx,y,z,v), &Icnc = (*this)(x,ny,z,v), &Innc = (*this)(nx,ny,z,v),
7880
&Iccn = (*this)(x,y,nz,v), &Incn = (*this)(nx,y,nz,v), &Icnn = (*this)(x,ny,nz,v), &Innn = (*this)(nx,ny,nz,v);
7883
dy*(Iccc+Innc-Icnc-Incc +
7884
dz*(Iccn+Innn+Icnc+Incc-Icnn-Incn-Iccc-Innc)) +
7885
dz*(Iccc+Incn-Iccn-Incc)) +
7887
dz*(Iccc+Icnn-Iccn-Icnc)) +
7891
//! Read a pixel value using linear interpolation for the two first coordinates (\c cx,\c cy).
7893
- Same as linear_pix4d(), except that linear interpolation and boundary checking is performed only on the two first coordinates.
7895
\sa operator()(), linear_pix4d(), linear_pix3d(), linear_pix1d(), linear_pix2d(), cubic_pix2d().
7897
typename cimg::largest<T,float>::type linear_pix2d(const float fx, const float fy, const int z, const int v,
7898
const T& out_val) const {
7899
const int x = (int)fx-(fx>0?0:1), y = (int)fy-(fy>0?0:1), nx = x+1, ny = y+1;
7900
const float dx = fx-x, dy = fy-y;
7902
Icc = pix2d(x,y,z,v,out_val), Inc = pix2d(nx,y,z,v,out_val),
7903
Icn = pix2d(x,ny,z,v,out_val), Inn = pix2d(nx,ny,z,v,out_val);
7904
return Icc + dx*(Inc-Icc + dy*(Icc+Inn-Icn-Inc)) + dy*(Icn-Icc);
7907
typename cimg::largest<T,float>::type linear_pix2d(const float ffx, const float ffy=0, const int z=0, const int v=0) const {
7908
const float fx = ffx<0?0:(ffx>width-1?width-1:ffx), fy = ffy<0?0:(ffy>height-1?height-1:ffy);
7909
const unsigned int x = (unsigned int)fx, y = (unsigned int)fy;
7910
const float dx = fx-x, dy = fy-y;
7911
const unsigned int nx = dx>0?x+1:x, ny = dy>0?y+1:y;
7912
const T &Icc = (*this)(x,y,z,v), &Inc = (*this)(nx,y,z,v), &Icn = (*this)(x,ny,z,v), &Inn = (*this)(nx,ny,z,v);
7913
return Icc + dx*(Inc-Icc + dy*(Icc+Inn-Icn-Inc)) + dy*(Icn-Icc);
7916
//! Read a pixel value using linear interpolation for the first coordinate \c cx.
7918
- Same as linear_pix4d(), except that linear interpolation and boundary checking is performed only on the first coordinate.
7920
\sa operator()(), linear_pix4d(), linear_pix3d(), linear_pix2d(), linear_pix1d(), cubic_pix1d().
7922
typename cimg::largest<T,float>::type linear_pix1d(const float fx, const int y, const int z, const int v,
7923
const T& out_val) const {
7924
const int x = (int)fx-(fx>0?0:1), nx = x+1;
7925
const float dx = fx-x;
7926
const T Ic = pix1d(x,y,z,v,out_val), In = pix2d(nx,y,z,v,out_val);
7927
return Ic + dx*(In-Ic);
7930
typename cimg::largest<T,float>::type linear_pix1d(const float ffx, const int y=0, const int z=0, const int v=0) const {
7931
const float fx = ffx<0?0:(ffx>width-1?width-1:ffx);
7932
const unsigned int x = (unsigned int)fx;
7933
const float dx = fx-x;
7934
const unsigned int nx = dx>0?x+1:x;
7935
const T &Ic = (*this)(x,y,z,v), &In = (*this)(nx,y,z,v);
7936
return Ic + dx*(In-Ic);
7939
// This function is used as a subroutine for cubic interpolation
7940
static float _cubic_R(const float x) {
7941
const float xp2 = x+2, xp1 = x+1, xm1 = x-1,
7942
nxp2 = xp2>0?xp2:0, nxp1 = xp1>0?xp1:0, nx = x>0?x:0, nxm1 = xm1>0?xm1:0;
7943
return (nxp2*nxp2*nxp2 - 4*nxp1*nxp1*nxp1 + 6*nx*nx*nx - 4*nxm1*nxm1*nxm1)/6.0f;
7946
//! Read a pixel value using cubic interpolation for the first coordinate \c cx.
7948
- Same as cubic_pix2d(), except that cubic interpolation and boundary checking is performed only on the first coordinate.
7950
\sa operator()(), cubic_pix2d(), linear_pix1d().
7952
typename cimg::largest<T,float>::type cubic_pix1d(const float fx, const int y, const int z, const int v,
7953
const T& out_val) const {
7954
const int x = (int)fx-(fx>=0?0:1), px = x-1, nx = x+1, ax = nx+1;
7955
const float dx = fx-x;
7956
const T a = pix2d(px,y,z,v,out_val), b = pix2d(x,y,z,v,out_val), c = pix2d(nx,y,z,v,out_val), d = pix2d(ax,y,z,v,out_val);
7957
const float Rxp = _cubic_R(-1-dx), Rxc = _cubic_R(dx), Rxn = _cubic_R(1-dx), Rxa = _cubic_R(2-dx);
7958
return Rxp*a + Rxc*b + Rxn*c + Rxa*d;
7961
typename cimg::largest<T,float>::type cubic_pix1d(const float pfx, const int y=0, const int z=0, const int v=0) const {
7962
const float fx = pfx<0?0:(pfx>width-1?width-1:pfx);
7963
const unsigned int x = (unsigned int)fx, px = (int)x-1>=0?x-1:0, nx = x+1<width?x+1:width-1, ax = nx+1<width?nx+1:width-1;
7964
const float dx = fx-x;
7965
const T& a = (*this)(px,y,z,v), b = (*this)(x,y,z,v), c = (*this)(nx,y,z,v), d = (*this)(ax,y,z,v);
7966
const float Rxp = _cubic_R(-1-dx), Rxc = _cubic_R(dx), Rxn = _cubic_R(1-dx), Rxa = _cubic_R(2-dx);
7967
return Rxp*a + Rxc*b + Rxn*c + Rxa*d;
7970
//! Read a pixel value using bicubic interpolation.
7972
\param pfx X-coordinate of the pixel (float-valued).
7973
\param pfy Y-coordinate of the pixel (float-valued).
7974
\param z Z-coordinate of the pixel.
7975
\param v V-coordinate of the pixel.
7977
- This function allows to read pixel values with boundary checking on the two first coordinates.
7978
- If given coordinates are outside the image range, the value of the nearest pixel inside the image is returned
7979
(Neumann boundary conditions).
7980
- If given coordinates are float-valued, a cubic interpolation is performed in order to compute the returned value.
7982
\sa operator()(), cubic_pix1d(), linear_pix2d().
7984
typename cimg::largest<T,float>::type cubic_pix2d(const float fx, const float fy, const int z, const int v,
7985
const T& out_val) const {
7987
x = (int)fx-(fx>=0?0:1), y = (int)fy-(fy>=0?0:1),
7988
px = x-1, nx = x+1, ax = nx+1, py = y-1, ny = y+1, ay = ny+1;
7989
const float dx = fx-x, dy = fy-y;
7991
a = pix2d(px,py,z,v,out_val), b = pix2d(x,py,z,v,out_val), c = pix2d(nx,py,z,v,out_val), d = pix2d(ax,py,z,v,out_val),
7992
e = pix2d(px, y,z,v,out_val), f = pix2d(x, y,z,v,out_val), g = pix2d(nx, y,z,v,out_val), h = pix2d(ax, y,z,v,out_val),
7993
i = pix2d(px,ny,z,v,out_val), j = pix2d(x,ny,z,v,out_val), k = pix2d(nx,ny,z,v,out_val), l = pix2d(ax,ny,z,v,out_val),
7994
m = pix2d(px,ay,z,v,out_val), n = pix2d(x,ay,z,v,out_val), o = pix2d(nx,ay,z,v,out_val), p = pix2d(ax,ay,z,v,out_val);
7996
Rxp = _cubic_R(-1-dx), Rxc = _cubic_R(dx), Rxn = _cubic_R(1-dx), Rxa = _cubic_R(2-dx),
7997
Ryp = _cubic_R(dy+1), Ryc = _cubic_R(dy), Ryn = _cubic_R(dy-1), Rya = _cubic_R(dy-2);
7999
Rxp*Ryp*a + Rxc*Ryp*b + Rxn*Ryp*c + Rxa*Ryp*d +
8000
Rxp*Ryc*e + Rxc*Ryc*f + Rxn*Ryc*g + Rxa*Ryc*h +
8001
Rxp*Ryn*i + Rxc*Ryn*j + Rxn*Ryn*k + Rxa*Ryn*l +
8002
Rxp*Rya*m + Rxc*Rya*n + Rxn*Rya*o + Rxa*Rya*p;
8005
typename cimg::largest<T,float>::type cubic_pix2d(const float pfx, const float pfy=0, const int z=0, const int v=0) const {
8006
const float fx = pfx<0?0:(pfx>width-1?width-1:pfx), fy = pfy<0?0:(pfy>height-1?height-1:pfy);
8008
x = (unsigned int)fx, px = (int)x-1>=0?x-1:0, nx = x+1<width?x+1:width-1, ax = nx+1<width?nx+1:width-1,
8009
y = (unsigned int)fy, py = (int)y-1>=0?y-1:0, ny = y+1<height?y+1:height-1, ay = ny+1<height?ny+1:height-1;
8010
const float dx = fx-x, dy = fy-y;
8012
a = (*this)(px,py,z,v), b = (*this)(x,py,z,v), c = (*this)(nx,py,z,v), d = (*this)(ax,py,z,v),
8013
e = (*this)(px, y,z,v), f = (*this)(x, y,z,v), g = (*this)(nx, y,z,v), h = (*this)(ax, y,z,v),
8014
i = (*this)(px,ny,z,v), j = (*this)(x,ny,z,v), k = (*this)(nx,ny,z,v), l = (*this)(ax,ny,z,v),
8015
m = (*this)(px,ay,z,v), n = (*this)(x,ay,z,v), o = (*this)(nx,ay,z,v), p = (*this)(ax,ay,z,v);
8017
Rxp = _cubic_R(-1-dx), Rxc = _cubic_R(dx), Rxn = _cubic_R(1-dx), Rxa = _cubic_R(2-dx),
8018
Ryp = _cubic_R(dy+1), Ryc = _cubic_R(dy), Ryn = _cubic_R(dy-1), Rya = _cubic_R(dy-2);
8020
Rxp*Ryp*a + Rxc*Ryp*b + Rxn*Ryp*c + Rxa*Ryp*d +
8021
Rxp*Ryc*e + Rxc*Ryc*f + Rxn*Ryc*g + Rxa*Ryc*h +
8022
Rxp*Ryn*i + Rxc*Ryn*j + Rxn*Ryn*k + Rxa*Ryn*l +
8023
Rxp*Rya*m + Rxc*Rya*n + Rxn*Rya*o + Rxa*Rya*p;
11687
//! Read a pixel value with Neumann boundary conditions for the first coordinates (\c x).
11688
T& at1(const int x, const int y=0, const int z=0, const int v=0) {
11689
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x),y,z,v);
11692
const T& at1(const int x, const int y=0, const int z=0, const int v=0) const {
11693
return (*this)(x<0?0:(x>=dimx()?dimx()-1:x),y,z,v);
11696
//! Read a pixel value using linear interpolation and Dirichlet boundary conditions.
11697
Tfloat linear_at(const float fx, const float fy, const float fz, const float fv, const T out_val) const {
11698
return linear_at(fx,fy,fz,fv,out_val);
11701
//! Read a pixel value using linear interpolation and Neumann boundary conditions.
11702
Tfloat linear_at(const float fx, const float fy=0, const float fz=0, const float fv=0) const {
11703
return linear_at(fx,fy,fz,fv);
11706
//! Read a pixel value using linear interpolation and Dirichlet boundary conditions.
11707
Tfloat linear_at4(const float fx, const float fy, const float fz, const float fv, const T out_val) const {
11709
x = (int)fx-(fx>=0?0:1), nx = x+1,
11710
y = (int)fy-(fy>=0?0:1), ny = y+1,
11711
z = (int)fz-(fz>=0?0:1), nz = z+1,
11712
v = (int)fv-(fv>=0?0:1), nv = v+1;
11719
Icccc = (Tfloat)at(x,y,z,v,out_val), Inccc = (Tfloat)at(nx,y,z,v,out_val),
11720
Icncc = (Tfloat)at(x,ny,z,v,out_val), Inncc = (Tfloat)at(nx,ny,z,v,out_val),
11721
Iccnc = (Tfloat)at(x,y,nz,v,out_val), Incnc = (Tfloat)at(nx,y,nz,v,out_val),
11722
Icnnc = (Tfloat)at(x,ny,nz,v,out_val), Innnc = (Tfloat)at(nx,ny,nz,v,out_val),
11723
Icccn = (Tfloat)at(x,y,z,nv,out_val), Inccn = (Tfloat)at(nx,y,z,nv,out_val),
11724
Icncn = (Tfloat)at(x,ny,z,nv,out_val), Inncn = (Tfloat)at(nx,ny,z,nv,out_val),
11725
Iccnn = (Tfloat)at(x,y,nz,nv,out_val), Incnn = (Tfloat)at(nx,y,nz,nv,out_val),
11726
Icnnn = (Tfloat)at(x,ny,nz,nv,out_val), Innnn = (Tfloat)at(nx,ny,nz,nv,out_val);
11729
dy*(Icccc+Inncc-Icncc-Inccc +
11730
dz*(Iccnc+Innnc+Icncc+Inccc-Icnnc-Incnc-Icccc-Inncc +
11731
dv*(Iccnn+Innnn+Icncn+Inccn+Icnnc+Incnc+Icccc+Inncc-Icnnn-Incnn-Icccn-Inncn-Iccnc-Innnc-Icncc-Inccc)) +
11732
dv*(Icccn+Inncn+Icncc+Inccc-Icncn-Inccn-Icccc-Inncc)) +
11733
dz*(Icccc+Incnc-Iccnc-Inccc +
11734
dv*(Icccn+Incnn+Iccnc+Inccc-Iccnn-Inccn-Icccc-Incnc)) +
11735
dv*(Icccc+Inccn-Inccc-Icccn)) +
11737
dz*(Icccc+Icnnc-Iccnc-Icncc +
11738
dv*(Icccn+Icnnn+Iccnc+Icncc-Iccnn-Icncn-Icccc-Icnnc)) +
11739
dv*(Icccc+Icncn-Icncc-Icccn)) +
11741
dv*(Icccc+Iccnn-Iccnc-Icccn)) +
11745
//! Read a pixel value using linear interpolation and Neumann boundary conditions.
11746
Tfloat linear_at4(const float fx, const float fy=0, const float fz=0, const float fv=0) const {
11748
nfx = fx<0?0:(fx>width-1?width-1:fx),
11749
nfy = fy<0?0:(fy>height-1?height-1:fy),
11750
nfz = fz<0?0:(fz>depth-1?depth-1:fz),
11751
nfv = fv<0?0:(fv>dim-1?dim-1:fv);
11753
x = (unsigned int)nfx,
11754
y = (unsigned int)nfy,
11755
z = (unsigned int)nfz,
11756
v = (unsigned int)nfv;
11768
Icccc = (Tfloat)(*this)(x,y,z,v), Inccc = (Tfloat)(*this)(nx,y,z,v),
11769
Icncc = (Tfloat)(*this)(x,ny,z,v), Inncc = (Tfloat)(*this)(nx,ny,z,v),
11770
Iccnc = (Tfloat)(*this)(x,y,nz,v), Incnc = (Tfloat)(*this)(nx,y,nz,v),
11771
Icnnc = (Tfloat)(*this)(x,ny,nz,v), Innnc = (Tfloat)(*this)(nx,ny,nz,v),
11772
Icccn = (Tfloat)(*this)(x,y,z,nv), Inccn = (Tfloat)(*this)(nx,y,z,nv),
11773
Icncn = (Tfloat)(*this)(x,ny,z,nv), Inncn = (Tfloat)(*this)(nx,ny,z,nv),
11774
Iccnn = (Tfloat)(*this)(x,y,nz,nv), Incnn = (Tfloat)(*this)(nx,y,nz,nv),
11775
Icnnn = (Tfloat)(*this)(x,ny,nz,nv), Innnn = (Tfloat)(*this)(nx,ny,nz,nv);
11778
dy*(Icccc+Inncc-Icncc-Inccc +
11779
dz*(Iccnc+Innnc+Icncc+Inccc-Icnnc-Incnc-Icccc-Inncc +
11780
dv*(Iccnn+Innnn+Icncn+Inccn+Icnnc+Incnc+Icccc+Inncc-Icnnn-Incnn-Icccn-Inncn-Iccnc-Innnc-Icncc-Inccc)) +
11781
dv*(Icccn+Inncn+Icncc+Inccc-Icncn-Inccn-Icccc-Inncc)) +
11782
dz*(Icccc+Incnc-Iccnc-Inccc +
11783
dv*(Icccn+Incnn+Iccnc+Inccc-Iccnn-Inccn-Icccc-Incnc)) +
11784
dv*(Icccc+Inccn-Inccc-Icccn)) +
11786
dz*(Icccc+Icnnc-Iccnc-Icncc +
11787
dv*(Icccn+Icnnn+Iccnc+Icncc-Iccnn-Icncn-Icccc-Icnnc)) +
11788
dv*(Icccc+Icncn-Icncc-Icccn)) +
11790
dv*(Icccc+Iccnn-Iccnc-Icccn)) +
11794
//! Read a pixel value using linear interpolation and Dirichlet boundary conditions (first three coordinates).
11795
Tfloat linear_at3(const float fx, const float fy, const float fz, const int v, const T out_val) const {
11797
x = (int)fx-(fx>=0?0:1), nx = x+1,
11798
y = (int)fy-(fy>=0?0:1), ny = y+1,
11799
z = (int)fz-(fz>=0?0:1), nz = z+1;
11805
Iccc = (Tfloat)at3(x,y,z,v,out_val), Incc = (Tfloat)at3(nx,y,z,v,out_val),
11806
Icnc = (Tfloat)at3(x,ny,z,v,out_val), Innc = (Tfloat)at3(nx,ny,z,v,out_val),
11807
Iccn = (Tfloat)at3(x,y,nz,v,out_val), Incn = (Tfloat)at3(nx,y,nz,v,out_val),
11808
Icnn = (Tfloat)at3(x,ny,nz,v,out_val), Innn = (Tfloat)at3(nx,ny,nz,v,out_val);
11811
dy*(Iccc+Innc-Icnc-Incc +
11812
dz*(Iccn+Innn+Icnc+Incc-Icnn-Incn-Iccc-Innc)) +
11813
dz*(Iccc+Incn-Iccn-Incc)) +
11815
dz*(Iccc+Icnn-Iccn-Icnc)) +
11819
//! Read a pixel value using linear interpolation and Neumann boundary conditions (first three coordinates).
11820
Tfloat linear_at3(const float fx, const float fy=0, const float fz=0, const int v=0) const {
11822
nfx = fx<0?0:(fx>width-1?width-1:fx),
11823
nfy = fy<0?0:(fy>height-1?height-1:fy),
11824
nfz = fz<0?0:(fz>depth-1?depth-1:fz);
11826
x = (unsigned int)nfx,
11827
y = (unsigned int)nfy,
11828
z = (unsigned int)nfz;
11838
Iccc = (Tfloat)(*this)(x,y,z,v), Incc = (Tfloat)(*this)(nx,y,z,v),
11839
Icnc = (Tfloat)(*this)(x,ny,z,v), Innc = (Tfloat)(*this)(nx,ny,z,v),
11840
Iccn = (Tfloat)(*this)(x,y,nz,v), Incn = (Tfloat)(*this)(nx,y,nz,v),
11841
Icnn = (Tfloat)(*this)(x,ny,nz,v), Innn = (Tfloat)(*this)(nx,ny,nz,v);
11844
dy*(Iccc+Innc-Icnc-Incc +
11845
dz*(Iccn+Innn+Icnc+Incc-Icnn-Incn-Iccc-Innc)) +
11846
dz*(Iccc+Incn-Iccn-Incc)) +
11848
dz*(Iccc+Icnn-Iccn-Icnc)) +
11852
//! Read a pixel value using linear interpolation and Dirichlet boundary conditions (first two coordinates).
11853
Tfloat linear_at2(const float fx, const float fy, const int z, const int v, const T out_val) const {
11855
x = (int)fx-(fx>=0?0:1), nx = x+1,
11856
y = (int)fy-(fy>=0?0:1), ny = y+1;
11861
Icc = (Tfloat)at2(x,y,z,v,out_val), Inc = (Tfloat)at2(nx,y,z,v,out_val),
11862
Icn = (Tfloat)at2(x,ny,z,v,out_val), Inn = (Tfloat)at2(nx,ny,z,v,out_val);
11863
return Icc + dx*(Inc-Icc + dy*(Icc+Inn-Icn-Inc)) + dy*(Icn-Icc);
11866
//! Read a pixel value using linear interpolation and Neumann boundary conditions (first two coordinates).
11867
Tfloat linear_at2(const float fx, const float fy, const int z=0, const int v=0) const {
11869
nfx = fx<0?0:(fx>width-1?width-1:fx),
11870
nfy = fy<0?0:(fy>height-1?height-1:fy);
11872
x = (unsigned int)nfx,
11873
y = (unsigned int)nfy;
11881
Icc = (Tfloat)(*this)(x,y,z,v), Inc = (Tfloat)(*this)(nx,y,z,v),
11882
Icn = (Tfloat)(*this)(x,ny,z,v), Inn = (Tfloat)(*this)(nx,ny,z,v);
11883
return Icc + dx*(Inc-Icc + dy*(Icc+Inn-Icn-Inc)) + dy*(Icn-Icc);
11886
//! Read a pixel value using linear interpolation and Dirichlet boundary conditions (first coordinate).
11887
Tfloat linear_at1(const float fx, const int y, const int z, const int v, const T out_val) const {
11889
x = (int)fx-(fx>=0?0:1), nx = x+1;
11893
Ic = (Tfloat)at1(x,y,z,v,out_val), In = (Tfloat)at2(nx,y,z,v,out_val);
11894
return Ic + dx*(In-Ic);
11897
//! Read a pixel value using linear interpolation and Neumann boundary conditions (first coordinate).
11898
Tfloat linear_at1(const float fx, const int y=0, const int z=0, const int v=0) const {
11900
nfx = fx<0?0:(fx>width-1?width-1:fx);
11902
x = (unsigned int)nfx;
11908
Ic = (Tfloat)(*this)(x,y,z,v), In = (Tfloat)(*this)(nx,y,z,v);
11909
return Ic + dx*(In-Ic);
11912
//! Read a pixel value using cubic interpolation and Dirichlet boundary conditions.
11913
Tfloat cubic_at(const float fx, const float fy, const int z, const int v, const T out_val) const {
11914
return cubic_at2(fx,fy,z,v,out_val);
11917
//! Read a pixel value using cubic interpolation and Neumann boundary conditions.
11918
Tfloat cubic_at(const float fx, const float fy, const int z=0, const int v=0) const {
11919
return cubic_at2(fx,fy,z,v);
11922
//! Read a pixel value using cubic interpolation and Dirichlet boundary conditions.
11923
Tfloat cubic_at2(const float fx, const float fy, const int z, const int v, const T out_val) const {
11925
x = (int)fx-(fx>=0?0:1), px = x-1, nx = x+1, ax = x+2,
11926
y = (int)fy-(fy>=0?0:1), py = y-1, ny = y+1, ay = y+2;
11928
dx = fx-x, dx2 = dx*dx, dx3 = dx2*dx,
11931
Ipp = (Tfloat)at2(px,py,z,v,out_val), Icp = (Tfloat)at2(x,py,z,v,out_val),
11932
Inp = (Tfloat)at2(nx,py,z,v,out_val), Iap = (Tfloat)at2(ax,py,z,v,out_val),
11933
Ipc = (Tfloat)at2(px,y,z,v,out_val), Icc = (Tfloat)at2(x,y,z,v,out_val),
11934
Inc = (Tfloat)at2(nx,y,z,v,out_val), Iac = (Tfloat)at2(ax,y,z,v,out_val),
11935
Ipn = (Tfloat)at2(px,ny,z,v,out_val), Icn = (Tfloat)at2(x,ny,z,v,out_val),
11936
Inn = (Tfloat)at2(nx,ny,z,v,out_val), Ian = (Tfloat)at2(ax,ny,z,v,out_val),
11937
Ipa = (Tfloat)at2(px,ay,z,v,out_val), Ica = (Tfloat)at2(x,ay,z,v,out_val),
11938
Ina = (Tfloat)at2(nx,ay,z,v,out_val), Iaa = (Tfloat)at2(ax,ay,z,v,out_val),
11939
valm = cimg::min(cimg::min(Ipp,Icp,Inp,Iap),cimg::min(Ipc,Icc,Inc,Iac),cimg::min(Ipn,Icn,Inn,Ian),cimg::min(Ipa,Ica,Ina,Iaa)),
11940
valM = cimg::max(cimg::max(Ipp,Icp,Inp,Iap),cimg::max(Ipc,Icc,Inc,Iac),cimg::max(Ipn,Icn,Inn,Ian),cimg::max(Ipa,Ica,Ina,Iaa)),
11943
ap = 2*(Icp-Inp) + u0p + u1p,
11944
bp = 3*(Inp-Icp) - 2*u0p - u1p,
11947
ac = 2*(Icc-Inc) + u0c + u1c,
11948
bc = 3*(Inc-Icc) - 2*u0c - u1c,
11951
an = 2*(Icn-Inn) + u0n + u1n,
11952
bn = 3*(Inn-Icn) - 2*u0n - u1n,
11955
aa = 2*(Ica-Ina) + u0a + u1a,
11956
ba = 3*(Ina-Ica) - 2*u0a - u1a,
11957
valp = ap*dx3 + bp*dx2 + u0p*dx + Icp,
11958
valc = ac*dx3 + bc*dx2 + u0c*dx + Icc,
11959
valn = an*dx3 + bn*dx2 + u0n*dx + Icn,
11960
vala = aa*dx3 + ba*dx2 + u0a*dx + Ica,
11963
a = 2*(valc-valn) + u0 + u1,
11964
b = 3*(valn-valc) - 2*u0 - u1,
11965
val = a*dy*dy*dy + b*dy*dy + u0*dy + valc;
11966
return val<valm?valm:(val>valM?valM:val);
11969
//! Read a pixel value using cubic interpolation and Neumann boundary conditions.
11970
Tfloat cubic_at2(const float fx, const float fy, const int z=0, const int v=0) const {
11972
nfx = fx<0?0:(fx>width-1?width-1:fx),
11973
nfy = fy<0?0:(fy>height-1?height-1:fy);
11978
dx = nfx-x, dx2 = dx*dx, dx3 = dx2*dx,
11981
px = x-1<0?0:x-1, nx = dx>0?x+1:x, ax = x+2>=dimx()?dimx()-1:x+2,
11982
py = y-1<0?0:y-1, ny = dy>0?y+1:y, ay = y+2>=dimy()?dimy()-1:y+2;
11984
Ipp = (Tfloat)(*this)(px,py,z,v), Icp = (Tfloat)(*this)(x,py,z,v),
11985
Inp = (Tfloat)(*this)(nx,py,z,v), Iap = (Tfloat)(*this)(ax,py,z,v),
11986
Ipc = (Tfloat)(*this)(px,y,z,v), Icc = (Tfloat)(*this)(x,y,z,v),
11987
Inc = (Tfloat)(*this)(nx,y,z,v), Iac = (Tfloat)(*this)(ax,y,z,v),
11988
Ipn = (Tfloat)(*this)(px,ny,z,v), Icn = (Tfloat)(*this)(x,ny,z,v),
11989
Inn = (Tfloat)(*this)(nx,ny,z,v), Ian = (Tfloat)(*this)(ax,ny,z,v),
11990
Ipa = (Tfloat)(*this)(px,ay,z,v), Ica = (Tfloat)(*this)(x,ay,z,v),
11991
Ina = (Tfloat)(*this)(nx,ay,z,v), Iaa = (Tfloat)(*this)(ax,ay,z,v),
11992
valm = cimg::min(cimg::min(Ipp,Icp,Inp,Iap),cimg::min(Ipc,Icc,Inc,Iac),cimg::min(Ipn,Icn,Inn,Ian),cimg::min(Ipa,Ica,Ina,Iaa)),
11993
valM = cimg::max(cimg::max(Ipp,Icp,Inp,Iap),cimg::max(Ipc,Icc,Inc,Iac),cimg::max(Ipn,Icn,Inn,Ian),cimg::max(Ipa,Ica,Ina,Iaa)),
11996
ap = 2*(Icp-Inp) + u0p + u1p,
11997
bp = 3*(Inp-Icp) - 2*u0p - u1p,
12000
ac = 2*(Icc-Inc) + u0c + u1c,
12001
bc = 3*(Inc-Icc) - 2*u0c - u1c,
12004
an = 2*(Icn-Inn) + u0n + u1n,
12005
bn = 3*(Inn-Icn) - 2*u0n - u1n,
12008
aa = 2*(Ica-Ina) + u0a + u1a,
12009
ba = 3*(Ina-Ica) - 2*u0a - u1a,
12010
valp = ap*dx3 + bp*dx2 + u0p*dx + Icp,
12011
valc = ac*dx3 + bc*dx2 + u0c*dx + Icc,
12012
valn = an*dx3 + bn*dx2 + u0n*dx + Icn,
12013
vala = aa*dx3 + ba*dx2 + u0a*dx + Ica,
12016
a = 2*(valc-valn) + u0 + u1,
12017
b = 3*(valn-valc) - 2*u0 - u1,
12018
val = a*dy*dy*dy + b*dy*dy + u0*dy + valc;
12019
return val<valm?valm:(val>valM?valM:val);
12022
//! Read a pixel value using cubic interpolation and Dirichlet boundary conditions (first coordinates).
12023
Tfloat cubic_at1(const float fx, const int y, const int z, const int v, const T out_val) const {
12025
x = (int)fx-(fx>=0?0:1), px = x-1, nx = x+1, ax = x+2;
12029
Ip = (Tfloat)at1(px,y,z,v,out_val), Ic = (Tfloat)at1(x,y,z,v,out_val),
12030
In = (Tfloat)at1(nx,y,z,v,out_val), Ia = (Tfloat)at1(ax,y,z,v,out_val),
12031
valm = cimg::min(Ip,In,Ic,Ia), valM = cimg::max(Ip,In,Ic,Ia),
12034
a = 2*(Ic-In) + u0 + u1,
12035
b = 3*(In-Ic) - 2*u0 - u1,
12036
val = a*dx*dx*dx + b*dx*dx + u0*dx + Ic;
12037
return val<valm?valm:(val>valM?valM:val);
12040
//! Read a pixel value using cubic interpolation and Neumann boundary conditions (first coordinates).
12041
Tfloat cubic_at1(const float fx, const int y=0, const int z=0, const int v=0) const {
12043
nfx = fx<0?0:(fx>width-1?width-1:fx);
12049
px = x-1<0?0:x-1, nx = dx>0?x+1:x, ax = x+2>=dimx()?dimx()-1:x+2;
12051
Ip = (Tfloat)(*this)(px,y,z,v), Ic = (Tfloat)(*this)(x,y,z,v),
12052
In = (Tfloat)(*this)(nx,y,z,v), Ia = (Tfloat)(*this)(ax,y,z,v),
12053
valm = cimg::min(Ip,In,Ic,Ia), valM = cimg::max(Ip,In,Ic,Ia),
12056
a = 2*(Ic-In) + u0 + u1,
12057
b = 3*(In-Ic) - 2*u0 - u1,
12058
val = a*dx*dx*dx + b*dx*dx + u0*dx + Ic;
12059
return val<valm?valm:(val>valM?valM:val);
12062
//! Return a reference to the maximum pixel value of the instance image
12063
const T& max() const {
12064
if (is_empty()) throw CImgInstanceException("CImg<%s>::max() : Instance image is empty.",pixel_type());
12065
const T *ptrmax = data;
12066
T max_value = *ptrmax;
12067
cimg_for(*this,ptr,T) if ((*ptr)>max_value) max_value = *(ptrmax=ptr);
12071
//! Return a reference to the maximum pixel value of the instance image
12073
if (is_empty()) throw CImgInstanceException("CImg<%s>::max() : Instance image is empty.",pixel_type());
12075
T max_value = *ptrmax;
12076
cimg_for(*this,ptr,T) if ((*ptr)>max_value) max_value = *(ptrmax=ptr);
12080
//! Return a reference to the minimum pixel value of the instance image
12081
const T& min() const {
12082
if (is_empty()) throw CImgInstanceException("CImg<%s>::min() : Instance image is empty.",pixel_type());
12083
const T *ptrmin = data;
12084
T min_value = *ptrmin;
12085
cimg_for(*this,ptr,T) if ((*ptr)<min_value) min_value = *(ptrmin=ptr);
12089
//! Return a reference to the minimum pixel value of the instance image
12091
if (is_empty()) throw CImgInstanceException("CImg<%s>::min() : Instance image is empty.",pixel_type());
12093
T min_value = *ptrmin;
12094
cimg_for(*this,ptr,T) if ((*ptr)<min_value) min_value = *(ptrmin=ptr);
12098
//! Return a reference to the minimum pixel value and return also the maximum pixel value.
12099
template<typename t> const T& minmax(t& max_val) const {
12100
if (is_empty()) throw CImgInstanceException("CImg<%s>::minmax() : Instance image is empty.",pixel_type());
12101
const T *ptrmin = data;
12102
T min_value = *ptrmin, max_value = min_value;
12103
cimg_for(*this,ptr,T) {
12104
const T val = *ptr;
12105
if (val<min_value) { min_value = val; ptrmin = ptr; }
12106
if (val>max_value) max_value = val;
12108
max_val = (t)max_value;
12112
//! Return a reference to the minimum pixel value and return also the maximum pixel value.
12113
template<typename t> T& minmax(t& max_val) {
12114
if (is_empty()) throw CImgInstanceException("CImg<%s>::minmax() : Instance image is empty.",pixel_type());
12116
T min_value = *ptrmin, max_value = min_value;
12117
cimg_for(*this,ptr,T) {
12118
const T val = *ptr;
12119
if (val<min_value) { min_value = val; ptrmin = ptr; }
12120
if (val>max_value) max_value = val;
12122
max_val = (t)max_value;
12126
//! Return a reference to the maximum pixel value and return also the minimum pixel value.
12127
template<typename t> const T& maxmin(t& min_val) const {
12128
if (is_empty()) throw CImgInstanceException("CImg<%s>::maxmin() : Instance image is empty.",pixel_type());
12129
const T *ptrmax = data;
12130
T max_value = *ptrmax, min_value = max_value;
12131
cimg_for(*this,ptr,T) {
12132
const T val = *ptr;
12133
if (val>max_value) { max_value = val; ptrmax = ptr; }
12134
if (val<min_value) min_value = val;
12136
min_val = (t)min_value;
12140
//! Return a reference to the maximum pixel value and return also the minimum pixel value.
12141
template<typename t> T& maxmin(t& min_val) {
12142
if (is_empty()) throw CImgInstanceException("CImg<%s>::maxmin() : Instance image is empty.",pixel_type());
12144
T max_value = *ptrmax, min_value = max_value;
12145
cimg_for(*this,ptr,T) {
12146
const T val = *ptr;
12147
if (val>max_value) { max_value = val; ptrmax = ptr; }
12148
if (val<min_value) min_value = val;
12150
min_val = (t)min_value;
12154
//! Return the mean pixel value of the instance image.
12155
double mean() const {
12156
if (is_empty()) throw CImgInstanceException("CImg<%s>::mean() : Instance image is empty.",pixel_type());
12158
cimg_for(*this,ptr,T) val+=(double)*ptr;
12162
//! Return the variance and the mean of the image.
12163
template<typename t> double variancemean(const unsigned int variance_method, t& mean) const {
12165
throw CImgInstanceException("CImg<%s>::variance() : Instance image is empty.",pixel_type());
12166
double variance = 0, average = 0;
12167
const unsigned int siz = size();
12168
switch (variance_method) {
12169
case 3: { // Least trimmed of Squares
12170
CImg<double> buf(*this);
12171
const unsigned int siz2 = siz>>1;
12172
{ cimg_for(buf,ptrs,double) { const double val = *ptrs; (*ptrs)*=val; average+=val; }}
12175
const double *ptrs = buf.ptr();
12176
for (unsigned int j=0; j<siz2; ++j) a+=(*ptrs++);
12177
const double sig = 2.6477*std::sqrt(a/siz2);
12178
variance = sig*sig;
12180
case 2: { // Least Median of Squares (MAD)
12181
CImg<double> buf(*this);
12183
const unsigned int siz2 = siz>>1;
12184
const double med_i = buf[siz2];
12185
cimg_for(buf,ptrs,double) { const double val = *ptrs; *ptrs = cimg::abs(val-med_i); average+=val; }
12187
const double sig = 1.4828*buf[siz2];
12188
variance = sig*sig;
12190
case 1: { // Least mean square (robust definition)
12191
double S = 0, S2 = 0;
12192
cimg_for(*this,ptr,T) { const double val = (double)*ptr; S+=val; S2+=val*val; }
12193
variance = siz>1?(S2 - S*S/siz)/(siz-1):0;
12196
case 0:{ // Least mean square (standard definition)
12197
double S = 0, S2 = 0;
12198
cimg_for(*this,ptr,T) { const double val = (double)*ptr; S+=val; S2+=val*val; }
12199
variance = (S2 - S*S/siz)/siz;
12203
throw CImgArgumentException("CImg<%s>::variancemean() : Incorrect parameter 'variance_method = %d' (correct values are 0,1,2 or 3).",
12204
pixel_type(),variance_method);
12206
mean = (t)(average/siz);
12210
//! Return the variance and the mean of the image.
12211
double variance(const unsigned int variance_method=0) const {
12213
return variancemean(variance_method,foo);
12216
//! Compute the MSE (Mean-Squared Error) between two images.
12217
template<typename t> double MSE(const CImg<t>& img) const {
12218
if (img.size()!=size())
12219
throw CImgArgumentException("CImg<%s>::MSE() : Instance image (%u,%u,%u,%u) and given image (%u,%u,%u,%u) have different dimensions.",
12220
pixel_type(),width,height,depth,dim,img.width,img.height,img.depth,img.dim);
12223
const t* ptr2 = img.end();
12224
cimg_for(*this,ptr1,T) {
12225
const double diff = (double)*ptr1 - (double)*(--ptr2);
12232
//! Compute the PSNR between two images.
12233
template<typename t> double PSNR(const CImg<t>& img, const double valmax=255.0) const {
12234
const double vMSE = std::sqrt(MSE(img));
12235
return (vMSE!=0)?(20*std::log10(valmax/vMSE)):(cimg::type<double>::max());
12238
//! Return the trace of the current matrix.
12239
double trace() const {
12241
throw CImgInstanceException("CImg<%s>::trace() : Instance matrix (%u,%u,%u,%u,%p) is empty.",
12242
pixel_type(),width,height,depth,dim,data);
12244
cimg_forX(*this,k) res+=(*this)(k,k);
12248
//! Return the median of the image.
12250
const unsigned int s = size();
12251
const T res = kth_smallest(s>>1);
12252
return (s%2)?res:((res+kth_smallest((s>>1)-1))/2);
12255
//! Return the dot product of the current vector/matrix with the vector/matrix \p img.
12256
template<typename t> double dot(const CImg<t>& img) const {
12258
throw CImgInstanceException("CImg<%s>::dot() : Instance object (%u,%u,%u,%u,%p) is empty.",
12259
pixel_type(),width,height,depth,dim,data);
12261
throw CImgArgumentException("CImg<%s>::trace() : Specified argument (%u,%u,%u,%u,%p) is empty.",
12262
pixel_type(),img.width,img.height,img.depth,img.dim,img.data);
12263
const unsigned long nb = cimg::min(size(),img.size());
12265
for (unsigned long off=0; off<nb; ++off) res+=(double)data[off]*(double)img[off];
12269
//! Return the determinant of the current matrix.
12270
double det() const {
12271
if (is_empty() || width!=height || depth!=1 || dim!=1)
12272
throw CImgInstanceException("CImg<%s>::det() : Instance matrix (%u,%u,%u,%u,%p) is not square or is empty.",
12273
pixel_type(),width,height,depth,dim,data);
12275
case 1: return (*this)(0,0);
12276
case 2: return (*this)(0,0)*(*this)(1,1)-(*this)(0,1)*(*this)(1,0);
12279
a = data[0], d = data[1], g = data[2],
12280
b = data[3], e = data[4], h = data[5],
12281
c = data[6], f = data[7], i = data[8];
12282
return i*a*e-a*h*f-i*b*d+b*g*f+c*d*h-c*g*e;
12285
CImg<Tfloat> lu(*this);
12286
CImg<unsigned int> indx;
12289
double res = d?1.0:-1.0;
12290
cimg_forX(lu,i) res*=lu(i,i);
12297
//! Return the norm of the current vector/matrix. \p ntype = norm type (0=L2, 1=L1, -1=Linf).
12298
double norm(const int norm_type=2) const {
12300
throw CImgInstanceException("CImg<%s>::norm() : Instance object (%u,%u,%u,%u,%p) is empty.",
12301
pixel_type(),width,height,depth,dim,data);
12303
switch (norm_type) {
12305
cimg_foroff(*this,off) {
12306
const double tmp = cimg::abs((double)data[off]);
12307
if (tmp>res) res = tmp;
12312
cimg_foroff(*this,off) res+=cimg::abs((double)data[off]);
12315
case 2: return std::sqrt(dot(*this)); break;
12317
throw CImgArgumentException("CImg<%s>::norm() : Incorrect parameter 'norm_type=%d' (correct values are -1,1 or 2).",
12318
pixel_type(),norm_type);
12323
//! Return the sum of all the pixel values in an image.
12324
double sum() const {
12326
throw CImgInstanceException("CImg<%s>::sum() : Instance object (%u,%u,%u,%u,%p) is empty.",
12327
pixel_type(),width,height,depth,dim,data);
12329
cimg_for(*this,ptr,T) res+=*ptr;
12333
//! Return the kth smallest element of the image.
12334
// (Adapted from the numerical recipies for CImg)
12335
const T kth_smallest(const unsigned int k) const {
12337
throw CImgInstanceException("CImg<%s>::kth_smallest() : Instance image (%u,%u,%u,%u,%p) is empty.",
12338
pixel_type(),width,height,depth,dim,data);
12339
CImg<T> arr(*this);
12340
unsigned long l = 0, ir = size()-1;
12343
if (ir==l+1 && arr[ir]<arr[l]) cimg::swap(arr[l],arr[ir]);
12346
const unsigned long mid = (l+ir)>>1;
12347
cimg::swap(arr[mid],arr[l+1]);
12348
if (arr[l]>arr[ir]) cimg::swap(arr[l],arr[ir]);
12349
if (arr[l+1]>arr[ir]) cimg::swap(arr[l+1],arr[ir]);
12350
if (arr[l]>arr[l+1]) cimg::swap(arr[l],arr[l+1]);
12351
unsigned long i = l+1, j = ir;
12352
const T pivot = arr[l+1];
12354
do ++i; while (arr[i]<pivot);
12355
do --j; while (arr[j]>pivot);
12357
cimg::swap(arr[i],arr[j]);
8026
12368
//! Display informations about the image on the standard error output.
8028
12370
\param title Name for the considered image (optional).
8029
\param print_flag Level of informations to be printed.
8031
- The possible values for \c print_flag are :
8032
- -1 : print nothing
8033
- 0 : print only informations about image size and pixel buffer.
8034
- 1 : print also statistics on the image pixels.
8035
- 2 : print also the content of the pixel buffer, in a matlab-style.
8039
CImg<float> img("foo.jpg"); // Load image from a JPEG file.
8040
img.print("Image : foo.jpg",1); // Print image informations and statistics.
12371
\param display_stats Compute and display image statistics (optional).
8045
const CImg& print(const char *title=0, const int print_flag=1) const {
8046
if (print_flag>=0) {
8047
std::fprintf(stderr,"%-8s(this=%p): { size=(%u,%u,%u,%u), data=(%s*)%p (%s)",
8048
title?title:"CImg",(void*)this,
8049
width,height,depth,dim,pixel_type(),(void*)data,
8050
is_shared?"shared":"not shared");
8051
if (is_empty()) { std::fprintf(stderr,", [Undefined pixel data] }\n"); return *this; }
8052
if (print_flag>=1) {
8053
const CImgStats st(*this);
8054
std::fprintf(stderr,", min=%g, mean=%g [var=%g], max=%g, pmin=(%d,%d,%d,%d), pmax=(%d,%d,%d,%d)",
8055
st.min,st.mean,st.variance,st.max,st.xmin,st.ymin,st.zmin,st.vmin,st.xmax,st.ymax,st.zmax,st.vmax);
8057
if (print_flag>=2 || size()<=16) {
8058
std::fprintf(stderr," }\n%s = [ ",title?title:"data");
8059
cimg_forXYZV(*this,x,y,z,k)
8060
std::fprintf(stderr,"%g%s",(double)(*this)(x,y,z,k),
8061
((x+1)*(y+1)*(z+1)*(k+1)==(int)size()?" ]\n":(((x+1)%width==0)?" ; ":" ")));
8062
} else std::fprintf(stderr," }\n");
8067
//! Display informations about the image on the standard output.
8068
const CImg& print(const int print_flag) const {
8069
return print(0,print_flag);
12373
const CImg<T>& print(const char *title=0, const bool display_stats=true) const {
12374
int xm = 0, ym = 0, zm = 0, vm = 0, xM = 0, yM = 0, zM = 0, vM = 0;
12375
typedef typename cimg::last<T,double>::type cdouble;
12376
static CImg<cdouble> st;
12377
if (!is_empty() && display_stats) {
12379
contains(data[(unsigned int)st(4)],xm,ym,zm,vm);
12380
contains(data[(unsigned int)st(5)],xM,yM,zM,vM);
12382
const unsigned long siz = size(), msiz = siz*sizeof(T), siz1 = siz-1;
12383
const unsigned int mdisp = msiz<8*1024?0:(msiz<8*1024*1024?1:2), width1 = width-1;
12384
char ntitle[64] = { 0 };
12385
if (!title) std::sprintf(ntitle,"CImg<%s>",pixel_type());
12386
std::fprintf(stderr,"%s: this = %p, size = (%u,%u,%u,%u) [%lu %s], data = (%s*)%p (%s) = [ ",
12387
title?title:ntitle,(void*)this,width,height,depth,dim,
12388
mdisp==0?msiz:(mdisp==1?(msiz>>10):(msiz>>20)),
12389
mdisp==0?"b":(mdisp==1?"Kb":"Mb"),
12390
pixel_type(),(void*)data,is_shared?"shared":"not shared");
12391
if (!is_empty()) cimg_foroff(*this,off) {
12392
std::fprintf(stderr,cimg::type<T>::format(),cimg::type<T>::format(data[off]));
12393
if (off!=siz1) std::fprintf(stderr,"%s",off%width==width1?" ; ":" ");
12394
if (off==7 && siz>16) { off = siz1-8; if (off!=7) std::fprintf(stderr,"... "); }
12396
if (!is_empty() && display_stats)
12397
std::fprintf(stderr," ], min = %g, max = %g, mean = %g, std = %g, coords(min) = (%u,%u,%u,%u), coords(max) = (%u,%u,%u,%u).\n",
12398
st[0],st[1],st[2],std::sqrt(st[3]),xm,ym,zm,vm,xM,yM,zM,vM);
12399
else std::fprintf(stderr,"%s].\n",is_empty()?"":" ");
9835
14208
dz = pdz<0?-pdz*depth/100:pdz,
9836
14209
dv = pdv<0?-pdv*dim/100:pdv;
9837
14210
if (width==dx && height==dy && depth==dz && dim==dv) return *this;
9838
if (interp==-1 && dx*dy*dz*dv==size()) {
14211
if (interpolation_type==-1 && dx*dy*dz*dv==size()) {
9839
14212
width = dx; height = dy; depth = dz; dim = dv;
9842
return get_resize(dx,dy,dz,dv,interp,border_condition).swap(*this);
14215
return get_resize(dx,dy,dz,dv,interpolation_type,border_condition,center).transfer_to(*this);
9845
//! Resize the image.
14218
//! Resize an image.
9847
\param src = Image giving the geometry of the resize.
9848
\param interp = Resizing type :
14220
\param src Image giving the geometry of the resize.
14221
\param interpolation_type Interpolation method :
9849
14223
- 0 = no interpolation : additional space is filled with 0.
9850
14224
- 1 = bloc interpolation (nearest point).
9851
14225
- 2 = mosaic : image is repeated if necessary.
9852
14226
- 3 = linear interpolation.
9853
14227
- 4 = grid interpolation.
9854
14228
- 5 = bi-cubic interpolation.
14229
\param border_condition Border condition type.
9855
14230
\note If pd[x,y,z,v]<0, it corresponds to a percentage of the original size (the default value is -100).
9857
template<typename t> CImg& resize(const CImg<t>& src, const int interp=1, const int border_condition=-1) {
9858
return resize(src.width,src.height,src.depth,src.dim,interp,border_condition);
9861
//! Resize the image
14232
template<typename t> CImg<T> get_resize(const CImg<t>& src, const int interpolation_type=1,
14233
const int border_condition=-1, const bool center=false) const {
14234
return get_resize(src.width,src.height,src.depth,src.dim,interpolation_type,border_condition,center);
14237
//! Resize an image (in-place).
14238
template<typename t> CImg<T>& resize(const CImg<t>& src, const int interpolation_type=1,
14239
const int border_condition=-1, const bool center=false) {
14240
return resize(src.width,src.height,src.depth,src.dim,interpolation_type,border_condition,center);
14243
//! Resize an image.
9863
14245
\param disp = Display giving the geometry of the resize.
9864
\param interp = Resizing type :
14246
\param interpolation_type = Resizing type :
9865
14247
- 0 = no interpolation : additional space is filled with 0.
9866
14248
- 1 = bloc interpolation (nearest point).
9867
14249
- 2 = mosaic : image is repeated if necessary.
9868
14250
- 3 = linear interpolation.
9869
14251
- 4 = grid interpolation.
9870
14252
- 5 = bi-cubic interpolation.
14253
- 6 = moving average (best quality for photographs)
14254
\param border_condition Border condition type.
9871
14255
\note If pd[x,y,z,v]<0, it corresponds to a percentage of the original size (the default value is -100).
9873
CImg& resize(const CImgDisplay& disp, const int interp=1, const int border_condition=-1) {
9874
return resize(disp.width,disp.height,depth,dim,interp,border_condition);
14257
CImg<T> get_resize(const CImgDisplay& disp, const int interpolation_type=1,
14258
const int border_condition=-1, const bool center=false) const {
14259
return get_resize(disp.width,disp.height,depth,dim,interpolation_type,border_condition,center);
14262
//! Resize an image (in-place).
14263
CImg<T>& resize(const CImgDisplay& disp, const int interpolation_type=1,
14264
const int border_condition=-1, const bool center=false) {
14265
return resize(disp.width,disp.height,depth,dim,interpolation_type,border_condition,center);
14268
//! Half-resize an image, using a special optimized filter.
14269
CImg<T> get_resize_halfXY() const {
14270
if (is_empty()) return CImg<T>();
14271
const Tfloat mask[9] = { 0.07842776544f, 0.1231940459f, 0.07842776544f,
14272
0.1231940459f, 0.1935127547f, 0.1231940459f,
14273
0.07842776544f, 0.1231940459f, 0.07842776544f };
14274
Tfloat I[9] = { 0 };
14275
CImg<T> dest(width/2,height/2,depth,dim);
14276
cimg_forZV(*this,z,k) cimg_for3x3(*this,x,y,z,k,I)
14277
if (x%2 && y%2) dest(x/2,y/2,z,k) = (T)
14278
(I[0]*mask[0] + I[1]*mask[1] + I[2]*mask[2] +
14279
I[3]*mask[3] + I[4]*mask[4] + I[5]*mask[5] +
14280
I[6]*mask[6] + I[7]*mask[7] + I[8]*mask[8]);
14284
//! Half-resize an image, using a special optimized filter (in-place).
14285
CImg<T>& resize_halfXY() {
14286
return get_resize_halfXY().transfer_to(*this);
14289
//! Upscale an image by a factor 2x.
14291
Use anisotropic upscaling algorithm described at
14292
http://scale2x.sourceforge.net/algorithm.html
14294
CImg<T> get_resize_doubleXY() const {
14296
#define _cimg_gs2x_for3(bound,i) \
14297
for (int i = 0, _p1##i = 0, \
14298
_n1##i = 1>=(bound)?(int)(bound)-1:1; \
14299
_n1##i<(int)(bound) || i==--_n1##i; \
14300
_p1##i = i++, ++_n1##i, ptrd1+=(res).width, ptrd2+=(res).width)
14302
#define _cimg_gs2x_for3x3(img,x,y,z,v,I) \
14303
_cimg_gs2x_for3((img).height,y) for (int x = 0, \
14306
(I[1] = (img)(0,_p1##y,z,v)), \
14307
(I[3] = I[4] = (img)(0,y,z,v)), \
14308
(I[7] = (img)(0,_n1##y,z,v)), \
14309
1>=(img).width?(int)((img).width)-1:1); \
14310
(_n1##x<(int)((img).width) && ( \
14311
(I[2] = (img)(_n1##x,_p1##y,z,v)), \
14312
(I[5] = (img)(_n1##x,y,z,v)), \
14313
(I[8] = (img)(_n1##x,_n1##y,z,v)),1)) || \
14316
I[3] = I[4], I[4] = I[5], \
14318
_p1##x = x++, ++_n1##x)
14320
if (is_empty()) return *this;
14321
CImg<T> res(2*width,2*height,depth,dim);
14323
cimg_forZV(*this,z,k) {
14325
*ptrd1 = res.ptr(0,0,0,k),
14326
*ptrd2 = ptrd1 + res.width;
14327
_cimg_gs2x_for3x3(*this,x,y,0,k,I) {
14328
if (Icp!=Icn && Ipc!=Inc) {
14329
*(ptrd1++) = Ipc==Icp?Ipc:Icc;
14330
*(ptrd1++) = Icp==Inc?Inc:Icc;
14331
*(ptrd2++) = Ipc==Icn?Ipc:Icc;
14332
*(ptrd2++) = Icn==Inc?Inc:Icc;
14333
} else { *(ptrd1++) = Icc; *(ptrd1++) = Icc; *(ptrd2++) = Icc; *(ptrd2++) = Icc; }
14339
//! Upscale an image by a factor 2x (in-place).
14340
CImg<T>& resize_doubleXY() {
14341
return get_resize_doubleXY().transfer_to(*this);
14344
//! Upscale an image by a factor 3x.
14346
Use anisotropic upscaling algorithm described at
14347
http://scale2x.sourceforge.net/algorithm.html
14349
CImg<T> get_resize_tripleXY() const {
14351
#define _cimg_gs3x_for3(bound,i) \
14352
for (int i = 0, _p1##i = 0, \
14353
_n1##i = 1>=(bound)?(int)(bound)-1:1; \
14354
_n1##i<(int)(bound) || i==--_n1##i; \
14355
_p1##i = i++, ++_n1##i, ptrd1+=2*(res).width, ptrd2+=2*(res).width, ptrd3+=2*(res).width)
14357
#define _cimg_gs3x_for3x3(img,x,y,z,v,I) \
14358
_cimg_gs3x_for3((img).height,y) for (int x = 0, \
14361
(I[0] = I[1] = (img)(0,_p1##y,z,v)), \
14362
(I[3] = I[4] = (img)(0,y,z,v)), \
14363
(I[6] = I[7] = (img)(0,_n1##y,z,v)), \
14364
1>=(img).width?(int)((img).width)-1:1); \
14365
(_n1##x<(int)((img).width) && ( \
14366
(I[2] = (img)(_n1##x,_p1##y,z,v)), \
14367
(I[5] = (img)(_n1##x,y,z,v)), \
14368
(I[8] = (img)(_n1##x,_n1##y,z,v)),1)) || \
14370
I[0] = I[1], I[1] = I[2], \
14371
I[3] = I[4], I[4] = I[5], \
14372
I[6] = I[7], I[7] = I[8], \
14373
_p1##x = x++, ++_n1##x)
14375
if (is_empty()) return *this;
14376
CImg<T> res(3*width,3*height,depth,dim);
14378
cimg_forZV(*this,z,k) {
14380
*ptrd1 = res.ptr(0,0,0,k),
14381
*ptrd2 = ptrd1 + res.width,
14382
*ptrd3 = ptrd2 + res.width;
14383
_cimg_gs3x_for3x3(*this,x,y,0,k,I) {
14384
if (Icp != Icn && Ipc != Inc) {
14385
*(ptrd1++) = Ipc==Icp?Ipc:Icc;
14386
*(ptrd1++) = (Ipc==Icp && Icc!=Inp) || (Icp==Inc && Icc!=Ipp)?Icp:Icc;
14387
*(ptrd1++) = Icp==Inc?Inc:Icc;
14388
*(ptrd2++) = (Ipc==Icp && Icc!=Ipn) || (Ipc==Icn && Icc!=Ipp)?Ipc:Icc;
14390
*(ptrd2++) = (Icp==Inc && Icc!=Inn) || (Icn==Inc && Icc!=Inp)?Inc:Icc;
14391
*(ptrd3++) = Ipc==Icn?Ipc:Icc;
14392
*(ptrd3++) = (Ipc==Icn && Icc!=Inn) || (Icn==Inc && Icc!=Ipn)?Icn:Icc;
14393
*(ptrd3++) = Icn==Inc?Inc:Icc;
14395
*(ptrd1++) = Icc; *(ptrd1++) = Icc; *(ptrd1++) = Icc;
14396
*(ptrd2++) = Icc; *(ptrd2++) = Icc; *(ptrd2++) = Icc;
14397
*(ptrd3++) = Icc; *(ptrd3++) = Icc; *(ptrd3++) = Icc;
14404
//! Upscale an image by a factor 3x (in-place).
14405
CImg<T>& resize_tripleXY() {
14406
return get_resize_tripleXY().transfer_to(*this);
14409
// Permute axes order (internal).
14410
template<typename t> CImg<t> get_permute_axes(const char *permut, const t&) const {
14411
if (is_empty() || !permut) return CImg<t>(*this,false);
14413
const T* ptrs = data;
14414
if (!cimg::strncasecmp(permut,"xyzv",4)) return (+*this);
14415
if (!cimg::strncasecmp(permut,"xyvz",4)) {
14416
res.assign(width,height,dim,depth);
14417
cimg_forXYZV(*this,x,y,z,v) res(x,y,v,z) = (t)*(ptrs++);
14419
if (!cimg::strncasecmp(permut,"xzyv",4)) {
14420
res.assign(width,depth,height,dim);
14421
cimg_forXYZV(*this,x,y,z,v) res(x,z,y,v) = (t)*(ptrs++);
14423
if (!cimg::strncasecmp(permut,"xzvy",4)) {
14424
res.assign(width,depth,dim,height);
14425
cimg_forXYZV(*this,x,y,z,v) res(x,z,v,y) = (t)*(ptrs++);
14427
if (!cimg::strncasecmp(permut,"xvyz",4)) {
14428
res.assign(width,dim,height,depth);
14429
cimg_forXYZV(*this,x,y,z,v) res(x,v,y,z) = (t)*(ptrs++);
14431
if (!cimg::strncasecmp(permut,"xvzy",4)) {
14432
res.assign(width,dim,depth,height);
14433
cimg_forXYZV(*this,x,y,z,v) res(x,v,z,y) = (t)*(ptrs++);
14435
if (!cimg::strncasecmp(permut,"yxzv",4)) {
14436
res.assign(height,width,depth,dim);
14437
cimg_forXYZV(*this,x,y,z,v) res(y,x,z,v) = (t)*(ptrs++);
14439
if (!cimg::strncasecmp(permut,"yxvz",4)) {
14440
res.assign(height,width,dim,depth);
14441
cimg_forXYZV(*this,x,y,z,v) res(y,x,v,z) = (t)*(ptrs++);
14443
if (!cimg::strncasecmp(permut,"yzxv",4)) {
14444
res.assign(height,depth,width,dim);
14445
cimg_forXYZV(*this,x,y,z,v) res(y,z,x,v) = (t)*(ptrs++);
14447
if (!cimg::strncasecmp(permut,"yzvx",4)) {
14448
res.assign(height,depth,dim,width);
14451
t *ptrR = res.ptr(0,0,0,0);
14452
for (unsigned long siz = height*depth*dim+1; siz; --siz) {
14453
*(ptrR++) = (t)*(ptrs++);
14457
t *ptrR = res.ptr(0,0,0,0), *ptrG = res.ptr(0,0,0,1);
14458
for (unsigned long siz = height*depth*dim+1; siz; --siz) {
14459
*(ptrR++) = (t)*(ptrs++); *(ptrG++) = (t)*(ptrs++);
14462
case 3: { // Optimization for the classical conversion from interleaved RGB to planar RGB
14463
t *ptrR = res.ptr(0,0,0,0), *ptrG = res.ptr(0,0,0,1), *ptrB = res.ptr(0,0,0,2);
14464
for (unsigned long siz = height*depth*dim+1; siz; --siz) {
14465
*(ptrR++) = (t)*(ptrs++); *(ptrG++) = (t)*(ptrs++); *(ptrB++) = (t)*(ptrs++);
14468
case 4: { // Optimization for the classical conversion from interleaved RGBA to planar RGBA
14469
t *ptrR = res.ptr(0,0,0,0), *ptrG = res.ptr(0,0,0,1), *ptrB = res.ptr(0,0,0,2), *ptrA = res.ptr(0,0,0,3);
14470
for (unsigned long siz = height*depth*dim+1; siz; --siz) {
14471
*(ptrR++) = (t)*(ptrs++); *(ptrG++) = (t)*(ptrs++); *(ptrB++) = (t)*(ptrs++); *(ptrA++) = (t)*(ptrs++);
14475
cimg_forXYZV(*this,x,y,z,v) res(y,z,v,x) = *(ptrs++); return res;
14479
if (!cimg::strncasecmp(permut,"yvxz",4)) {
14480
res.assign(height,dim,width,depth);
14481
cimg_forXYZV(*this,x,y,z,v) res(y,v,x,z) = (t)*(ptrs++);
14483
if (!cimg::strncasecmp(permut,"yvzx",4)) {
14484
res.assign(height,dim,depth,width);
14485
cimg_forXYZV(*this,x,y,z,v) res(y,v,z,x) = (t)*(ptrs++);
14487
if (!cimg::strncasecmp(permut,"zxyv",4)) {
14488
res.assign(depth,width,height,dim);
14489
cimg_forXYZV(*this,x,y,z,v) res(z,x,y,v) = (t)*(ptrs++);
14491
if (!cimg::strncasecmp(permut,"zxvy",4)) {
14492
res.assign(depth,width,dim,height);
14493
cimg_forXYZV(*this,x,y,z,v) res(z,x,v,y) = (t)*(ptrs++);
14495
if (!cimg::strncasecmp(permut,"zyxv",4)) {
14496
res.assign(depth,height,width,dim);
14497
cimg_forXYZV(*this,x,y,z,v) res(z,y,x,v) = (t)*(ptrs++);
14499
if (!cimg::strncasecmp(permut,"zyvx",4)) {
14500
res.assign(depth,height,dim,width);
14501
cimg_forXYZV(*this,x,y,z,v) res(z,y,v,x) = (t)*(ptrs++);
14503
if (!cimg::strncasecmp(permut,"zvxy",4)) {
14504
res.assign(depth,dim,width,height);
14505
cimg_forXYZV(*this,x,y,z,v) res(z,v,x,y) = (t)*(ptrs++);
14507
if (!cimg::strncasecmp(permut,"zvyx",4)) {
14508
res.assign(depth,dim,height,width);
14509
cimg_forXYZV(*this,x,y,z,v) res(z,v,y,x) = (t)*(ptrs++);
14511
if (!cimg::strncasecmp(permut,"vxyz",4)) {
14512
res.assign(dim,width,height,depth);
14515
const T *ptrR = ptr(0,0,0,0);
14516
t *ptrd = res.ptr();
14517
for (unsigned long siz = width*height*depth+1; siz; --siz) {
14518
*(ptrd++) = (t)*(ptrR++);
14522
const T *ptrR = ptr(0,0,0,0), *ptrG = ptr(0,0,0,1);
14523
t *ptrd = res.ptr();
14524
for (unsigned long siz = width*height*depth+1; siz; --siz) {
14525
*(ptrd++) = (t)*(ptrR++); *(ptrd++) = (t)*(ptrG++);
14528
case 3: { // Optimization for the classical conversion from planar RGB to interleaved RGB
14529
const T *ptrR = ptr(0,0,0,0), *ptrG = ptr(0,0,0,1), *ptrB = ptr(0,0,0,2);
14530
t *ptrd = res.ptr();
14531
for (unsigned long siz = width*height*depth+1; siz; --siz) {
14532
*(ptrd++) = (t)*(ptrR++); *(ptrd++) = (t)*(ptrG++); *(ptrd++) = (t)*(ptrB++);
14535
case 4: { // Optimization for the classical conversion from planar RGBA to interleaved RGBA
14536
const T *ptrR = ptr(0,0,0,0), *ptrG = ptr(0,0,0,1), *ptrB = ptr(0,0,0,2), *ptrA = ptr(0,0,0,3);
14537
t *ptrd = res.ptr();
14538
for (unsigned long siz = width*height*depth+1; siz; --siz) {
14539
*(ptrd++) = (t)*(ptrR++); *(ptrd++) = (t)*(ptrG++); *(ptrd++) = (t)*(ptrB++); *(ptrd++) = (t)*(ptrA++);
14543
cimg_forXYZV(*this,x,y,z,v) res(v,x,y,z) = (t)*(ptrs++);
14547
if (!cimg::strncasecmp(permut,"vxzy",4)) {
14548
res.assign(dim,width,depth,height);
14549
cimg_forXYZV(*this,x,y,z,v) res(v,x,z,y) = (t)*(ptrs++);
14551
if (!cimg::strncasecmp(permut,"vyxz",4)) {
14552
res.assign(dim,height,width,depth);
14553
cimg_forXYZV(*this,x,y,z,v) res(v,y,x,z) = (t)*(ptrs++);
14555
if (!cimg::strncasecmp(permut,"vyzx",4)) {
14556
res.assign(dim,height,depth,width);
14557
cimg_forXYZV(*this,x,y,z,v) res(v,y,z,x) = (t)*(ptrs++);
14559
if (!cimg::strncasecmp(permut,"vzxy",4)) {
14560
res.assign(dim,depth,width,height);
14561
cimg_forXYZV(*this,x,y,z,v) res(v,z,x,y) = (t)*(ptrs++);
14563
if (!cimg::strncasecmp(permut,"vzyx",4)) {
14564
res.assign(dim,depth,height,width);
14565
cimg_forXYZV(*this,x,y,z,v) res(v,z,y,x) = (t)*(ptrs++);
14567
if (!res) throw CImgArgumentException("CImg<%s>::permute_axes() : Invalid input permutation '%s'.",pixel_type(),permut);
9877
14571
//! Permute axes order.
9879
14573
This function permutes image axes.
9880
14574
\param permut = String describing the permutation (4 characters).
9883
CImg get_permute_axes(const char *permut="vxyz") const {
9884
if (is_empty() || !permut) return (+*this);
9886
const T* ptr = data;
9887
if (!cimg::strncasecmp(permut,"xyzv",4)) return (+*this);
9888
if (!cimg::strncasecmp(permut,"xyvz",4)) { res.assign(width,height,dim,depth); cimg_forXYZV(*this,x,y,z,v) res(x,y,v,z) = *(ptr++); return res; }
9889
if (!cimg::strncasecmp(permut,"xzyv",4)) { res.assign(width,depth,height,dim); cimg_forXYZV(*this,x,y,z,v) res(x,z,y,v) = *(ptr++); return res; }
9890
if (!cimg::strncasecmp(permut,"xzvy",4)) { res.assign(width,depth,dim,height); cimg_forXYZV(*this,x,y,z,v) res(x,z,v,y) = *(ptr++); return res; }
9891
if (!cimg::strncasecmp(permut,"xvyz",4)) { res.assign(width,dim,height,depth); cimg_forXYZV(*this,x,y,z,v) res(x,v,y,z) = *(ptr++); return res; }
9892
if (!cimg::strncasecmp(permut,"xvzy",4)) { res.assign(width,dim,depth,height); cimg_forXYZV(*this,x,y,z,v) res(x,v,z,y) = *(ptr++); return res; }
9893
if (!cimg::strncasecmp(permut,"yxzv",4)) { res.assign(height,width,depth,dim); cimg_forXYZV(*this,x,y,z,v) res(y,x,z,v) = *(ptr++); return res; }
9894
if (!cimg::strncasecmp(permut,"yxvz",4)) { res.assign(height,width,dim,depth); cimg_forXYZV(*this,x,y,z,v) res(y,x,v,z) = *(ptr++); return res; }
9895
if (!cimg::strncasecmp(permut,"yzxv",4)) { res.assign(height,depth,width,dim); cimg_forXYZV(*this,x,y,z,v) res(y,z,x,v) = *(ptr++); return res; }
9896
if (!cimg::strncasecmp(permut,"yzvx",4)) { res.assign(height,depth,dim,width); cimg_forXYZV(*this,x,y,z,v) res(y,z,v,x) = *(ptr++); return res; }
9897
if (!cimg::strncasecmp(permut,"yvxz",4)) { res.assign(height,dim,width,depth); cimg_forXYZV(*this,x,y,z,v) res(y,v,x,z) = *(ptr++); return res; }
9898
if (!cimg::strncasecmp(permut,"yvzx",4)) { res.assign(height,dim,depth,width); cimg_forXYZV(*this,x,y,z,v) res(y,v,z,x) = *(ptr++); return res; }
9899
if (!cimg::strncasecmp(permut,"zxyv",4)) { res.assign(depth,width,height,dim); cimg_forXYZV(*this,x,y,z,v) res(z,x,y,v) = *(ptr++); return res; }
9900
if (!cimg::strncasecmp(permut,"zxvy",4)) { res.assign(depth,width,dim,height); cimg_forXYZV(*this,x,y,z,v) res(z,x,v,y) = *(ptr++); return res; }
9901
if (!cimg::strncasecmp(permut,"zyxv",4)) { res.assign(depth,height,width,dim); cimg_forXYZV(*this,x,y,z,v) res(z,y,x,v) = *(ptr++); return res; }
9902
if (!cimg::strncasecmp(permut,"zyvx",4)) { res.assign(depth,height,dim,width); cimg_forXYZV(*this,x,y,z,v) res(z,y,v,x) = *(ptr++); return res; }
9903
if (!cimg::strncasecmp(permut,"zvxy",4)) { res.assign(depth,dim,width,height); cimg_forXYZV(*this,x,y,z,v) res(z,v,x,y) = *(ptr++); return res; }
9904
if (!cimg::strncasecmp(permut,"zvyx",4)) { res.assign(depth,dim,height,width); cimg_forXYZV(*this,x,y,z,v) res(z,v,y,x) = *(ptr++); return res; }
9905
if (!cimg::strncasecmp(permut,"vxyz",4)) { res.assign(dim,width,height,depth); cimg_forXYZV(*this,x,y,z,v) res(v,x,y,z) = *(ptr++); return res; }
9906
if (!cimg::strncasecmp(permut,"vxzy",4)) { res.assign(dim,width,depth,height); cimg_forXYZV(*this,x,y,z,v) res(v,x,z,y) = *(ptr++); return res; }
9907
if (!cimg::strncasecmp(permut,"vyxz",4)) { res.assign(dim,height,width,depth); cimg_forXYZV(*this,x,y,z,v) res(v,y,x,z) = *(ptr++); return res; }
9908
if (!cimg::strncasecmp(permut,"vyzx",4)) { res.assign(dim,height,depth,width); cimg_forXYZV(*this,x,y,z,v) res(v,y,z,x) = *(ptr++); return res; }
9909
if (!cimg::strncasecmp(permut,"vzxy",4)) { res.assign(dim,depth,width,height); cimg_forXYZV(*this,x,y,z,v) res(v,z,x,y) = *(ptr++); return res; }
9910
if (!cimg::strncasecmp(permut,"vzyx",4)) { res.assign(dim,depth,height,width); cimg_forXYZV(*this,x,y,z,v) res(v,z,y,x) = *(ptr++); return res; }
9911
throw CImgArgumentException("CImg<%s>::permute_axes() : Invalid input permutation '%s'.",pixel_type(),permut);
9915
//! Permute axes order (in-place version).
9916
CImg& permute_axes(const char *order="vxyz") {
9917
return get_permute_axes(order).swap(*this);
9920
//! Return an half-resized image, using a special filter.
9922
\see resize_halfXY(), resize(), get_resize().
9924
CImg get_resize_halfXY() const {
9925
typedef typename cimg::largest<T,float>::type ftype;
9926
if (is_empty()) return CImg<T>();
9927
CImg<ftype> mask = CImg<ftype>::matrix(0.07842776544f, 0.1231940459f, 0.07842776544f,
9928
0.1231940459f, 0.1935127547f, 0.1231940459f,
9929
0.07842776544f, 0.1231940459f, 0.07842776544f);
9931
CImg dest(width/2,height/2,depth,dim);
9932
cimg_forZV(*this,z,k) cimg_for3x3(*this,x,y,z,k,I)
9933
if (x%2 && y%2) dest(x/2,y/2,z,k) = (T)cimg_conv3x3(I,mask);
9937
//! Half-resize the image, using a special filter
9939
\see get_resize_halfXY(), resize(), get_resize().
9941
CImg& resize_halfXY() {
9942
return get_resize_halfXY().swap(*this);
9945
//! Return a square region of the image, as a new image
9947
\param x0 = X-coordinate of the upper-left crop rectangle corner.
9948
\param y0 = Y-coordinate of the upper-left crop rectangle corner.
9949
\param z0 = Z-coordinate of the upper-left crop rectangle corner.
9950
\param v0 = V-coordinate of the upper-left crop rectangle corner.
9951
\param x1 = X-coordinate of the lower-right crop rectangle corner.
9952
\param y1 = Y-coordinate of the lower-right crop rectangle corner.
9953
\param z1 = Z-coordinate of the lower-right crop rectangle corner.
9954
\param v1 = V-coordinate of the lower-right crop rectangle corner.
9955
\param border_condition = Dirichlet (false) or Neumann border conditions.
9958
CImg get_crop(const int x0, const int y0, const int z0, const int v0,
9959
const int x1, const int y1, const int z1, const int v1,
9960
const bool border_condition=false) const {
9961
if (is_empty()) return *this;
9963
nx0 = x0<x1?x0:x1, nx1 = x0^x1^nx0,
9964
ny0 = y0<y1?y0:y1, ny1 = y0^y1^ny0,
9965
nz0 = z0<z1?z0:z1, nz1 = z0^z1^nz0,
9966
nv0 = v0<v1?v0:v1, nv1 = v0^v1^nv0;
9967
CImg dest(1U+nx1-nx0,1U+ny1-ny0,1U+nz1-nz0,1U+nv1-nv0);
9968
if (nx0<0 || nx1>=dimx() || ny0<0 || ny1>=dimy() || nz0<0 || nz1>=dimz() || nv0<0 || nv1>=dimv()) {
9969
if (border_condition) cimg_forXYZV(dest,x,y,z,v) dest(x,y,z,v) = pix4d(nx0+x,ny0+y,nz0+z,nv0+v);
9970
else dest.fill(0).draw_image(*this,-nx0,-ny0,-nz0,-nv0);
9971
} else dest.draw_image(*this,-nx0,-ny0,-nz0,-nv0);
9975
//! Return a square region of the image, as a new image
9977
\param x0 = X-coordinate of the upper-left crop rectangle corner.
9978
\param y0 = Y-coordinate of the upper-left crop rectangle corner.
9979
\param z0 = Z-coordinate of the upper-left crop rectangle corner.
9980
\param x1 = X-coordinate of the lower-right crop rectangle corner.
9981
\param y1 = Y-coordinate of the lower-right crop rectangle corner.
9982
\param z1 = Z-coordinate of the lower-right crop rectangle corner.
9983
\param border_condition = determine the type of border condition if
9984
some of the desired region is outside the image.
9987
CImg get_crop(const int x0, const int y0, const int z0,
9988
const int x1, const int y1, const int z1,
9989
const bool border_condition=false) const {
9990
return get_crop(x0,y0,z0,0,x1,y1,z1,dim-1,border_condition);
9993
//! Return a square region of the image, as a new image
9995
\param x0 = X-coordinate of the upper-left crop rectangle corner.
9996
\param y0 = Y-coordinate of the upper-left crop rectangle corner.
9997
\param x1 = X-coordinate of the lower-right crop rectangle corner.
9998
\param y1 = Y-coordinate of the lower-right crop rectangle corner.
9999
\param border_condition = determine the type of border condition if
10000
some of the desired region is outside the image.
10003
CImg get_crop(const int x0, const int y0,
10004
const int x1, const int y1,
10005
const bool border_condition=false) const {
10006
return get_crop(x0,y0,0,0,x1,y1,depth-1,dim-1,border_condition);
10009
//! Return a square region of the image, as a new image
10011
\param x0 = X-coordinate of the upper-left crop rectangle corner.
10012
\param x1 = X-coordinate of the lower-right crop rectangle corner.
10013
\param border_condition = determine the type of border condition if
10014
some of the desired region is outside the image.
10017
CImg get_crop(const int x0, const int x1, const bool border_condition=false) const {
10018
return get_crop(x0,0,0,0,x1,height-1,depth-1,dim-1,border_condition);
10021
//! Replace the image by a square region of the image
10023
\param x0 = X-coordinate of the upper-left crop rectangle corner.
10024
\param y0 = Y-coordinate of the upper-left crop rectangle corner.
10025
\param z0 = Z-coordinate of the upper-left crop rectangle corner.
10026
\param v0 = V-coordinate of the upper-left crop rectangle corner.
10027
\param x1 = X-coordinate of the lower-right crop rectangle corner.
10028
\param y1 = Y-coordinate of the lower-right crop rectangle corner.
10029
\param z1 = Z-coordinate of the lower-right crop rectangle corner.
10030
\param v1 = V-coordinate of the lower-right crop rectangle corner.
10031
\param border_condition = determine the type of border condition if
10032
some of the desired region is outside the image.
10035
CImg& crop(const int x0, const int y0, const int z0, const int v0,
10036
const int x1, const int y1, const int z1, const int v1,
10037
const bool border_condition=false) {
10038
return get_crop(x0,y0,z0,v0,x1,y1,z1,v1,border_condition).swap(*this);
10041
//! Replace the image by a square region of the image
10043
\param x0 = X-coordinate of the upper-left crop rectangle corner.
10044
\param y0 = Y-coordinate of the upper-left crop rectangle corner.
10045
\param z0 = Z-coordinate of the upper-left crop rectangle corner.
10046
\param x1 = X-coordinate of the lower-right crop rectangle corner.
10047
\param y1 = Y-coordinate of the lower-right crop rectangle corner.
10048
\param z1 = Z-coordinate of the lower-right crop rectangle corner.
10049
\param border_condition = determine the type of border condition if
10050
some of the desired region is outside the image.
10053
CImg& crop(const int x0, const int y0, const int z0,
10054
const int x1, const int y1, const int z1,
10055
const bool border_condition=false) {
10056
return crop(x0,y0,z0,0,x1,y1,z1,dim-1,border_condition);
10059
//! Replace the image by a square region of the image
10061
\param x0 = X-coordinate of the upper-left crop rectangle corner.
10062
\param y0 = Y-coordinate of the upper-left crop rectangle corner.
10063
\param x1 = X-coordinate of the lower-right crop rectangle corner.
10064
\param y1 = Y-coordinate of the lower-right crop rectangle corner.
10065
\param border_condition = determine the type of border condition if
10066
some of the desired region is outside the image.
10069
CImg& crop(const int x0, const int y0,
10070
const int x1, const int y1,
10071
const bool border_condition=false) {
10072
return crop(x0,y0,0,0,x1,y1,depth-1,dim-1,border_condition);
10075
//! Replace the image by a square region of the image
10077
\param x0 = X-coordinate of the upper-left crop rectangle corner.
10078
\param x1 = X-coordinate of the lower-right crop rectangle corner.
10079
\param border_condition = determine the type of border condition if
10080
some of the desired region is outside the image.
10083
CImg& crop(const int x0, const int x1, const bool border_condition=false) {
10084
return crop(x0,0,0,0,x1,height-1,depth-1,dim-1,border_condition);
10087
//! Return a set of columns
10088
CImg get_columns(const unsigned int x0, const unsigned int x1) const {
10089
return get_crop((int)x0,0,0,0,(int)x1,(int)height-1,(int)depth-1,(int)dim-1);
10092
//! Replace the instance image by a set of its columns
10093
CImg& columns(const unsigned int x0, const unsigned int x1) {
10094
return get_columns(x0,x1).swap(*this);
10097
//! Return one column
10098
CImg get_column(const unsigned int x0) const {
10099
return get_columns(x0,x0);
10102
//! Replace the instance image by one of its column
10103
CImg& column(const unsigned int x0) {
10104
return columns(x0,x0);
10107
//! Get a copy of a set of lines of the instance image.
10108
CImg get_lines(const unsigned int y0, const unsigned int y1) const {
10109
return get_crop(0,(int)y0,0,0,(int)width-1,(int)y1,(int)depth-1,(int)dim-1);
10112
//! Replace the instance image by a set of lines of the instance image.
10113
CImg& lines(const unsigned int y0, const unsigned int y1) {
10114
return get_lines(y0,y1).swap(*this);
10117
//! Get a copy of a line of the instance image.
10118
CImg get_line(const unsigned int y0) const {
10119
return get_lines(y0,y0);
10122
//! Replace the instance image by one of its line.
10123
CImg& line(const unsigned int y0) {
10124
return lines(y0,y0);
10127
//! Get a set of slices
10128
CImg get_slices(const unsigned int z0, const unsigned int z1) const {
10129
return get_crop(0,0,(int)z0,0,(int)width-1,(int)height-1,(int)z1,(int)dim-1);
10132
// Replace the image by a set of its z-slices
10133
CImg& slices(const unsigned int z0, const unsigned int z1) {
10134
return get_slices(z0,z1).swap(*this);
10137
//! Get the z-slice \a z of *this, as a new image.
10138
CImg get_slice(const unsigned int z0) const {
10139
return get_slices(z0,z0);
10142
//! Replace the image by one of its slice.
10143
CImg& slice(const unsigned int z0) {
10144
return slices(z0,z0);
10147
//! Return a copy of a set of channels of the instance image.
10148
CImg get_channels(const unsigned int v0, const unsigned int v1) const {
10149
return get_crop(0,0,0,(int)v0,(int)width-1,(int)height-1,(int)depth-1,(int)v1);
10152
//! Replace the instance image by a set of channels of the instance image.
10153
CImg& channels(const unsigned int v0, const unsigned int v1) {
10154
return get_channels(v0,v1).swap(*this);
10157
//! Return a copy of a channel of the instance image.
10158
CImg get_channel(const unsigned int v0) const {
10159
return get_channels(v0,v0);
10162
//! Replace the instance image by one of its channel.
10163
CImg& channel(const unsigned int v0) {
10164
return channels(v0,v0);
10167
//! Get a shared-memory image referencing a set of points of the instance image.
10168
CImg get_shared_points(const unsigned int x0, const unsigned int x1,
10169
const unsigned int y0=0, const unsigned int z0=0, const unsigned int v0=0) {
10170
const unsigned long beg = offset(x0,y0,z0,v0), end = offset(x1,y0,z0,v0);
10171
if (beg>end || beg>=size() || end>=size())
10172
throw CImgArgumentException("CImg<%s>::get_shared_points() : Cannot return a shared-memory subset (%u->%u,%u,%u,%u) from "
10173
"a (%u,%u,%u,%u) image.",pixel_type(),x0,x1,y0,z0,v0,width,height,depth,dim);
10174
return CImg<T>(data+beg,x1-x0+1,1,1,1,true);
10177
//! Get a shared-memory image referencing a set of points of the instance image (const version).
10178
const CImg get_shared_points(const unsigned int x0, const unsigned int x1,
10179
const unsigned int y0=0, const unsigned int z0=0, const unsigned int v0=0) const {
10180
const unsigned long beg = offset(x0,y0,z0,v0), end = offset(x1,y0,z0,v0);
10181
if (beg>end || beg>=size() || end>=size())
10182
throw CImgArgumentException("CImg<%s>::get_shared_points() : Cannot return a shared-memory subset (%u->%u,%u,%u,%u) from "
10183
"a (%u,%u,%u,%u) image.",pixel_type(),x0,x1,y0,z0,v0,width,height,depth,dim);
10184
return CImg<T>(data+beg,x1-x0+1,1,1,1,true);
10187
//! Return a shared-memory image referencing a set of lines of the instance image.
10188
CImg get_shared_lines(const unsigned int y0, const unsigned int y1,
10189
const unsigned int z0=0, const unsigned int v0=0) {
10190
const unsigned long beg = offset(0,y0,z0,v0), end = offset(0,y1,z0,v0);
10191
if (beg>end || beg>=size() || end>=size())
10192
throw CImgArgumentException("CImg<%s>::get_shared_lines() : Cannot return a shared-memory subset (0->%u,%u->%u,%u,%u) from "
10193
"a (%u,%u,%u,%u) image.",pixel_type(),width-1,y0,y1,z0,v0,width,height,depth,dim);
10194
return CImg<T>(data+beg,width,y1-y0+1,1,1,true);
10197
//! Return a shared-memory image referencing a set of lines of the instance image (const version).
10198
const CImg get_shared_lines(const unsigned int y0, const unsigned int y1,
10199
const unsigned int z0=0, const unsigned int v0=0) const {
10200
const unsigned long beg = offset(0,y0,z0,v0), end = offset(0,y1,z0,v0);
10201
if (beg>end || beg>=size() || end>=size())
10202
throw CImgArgumentException("CImg<%s>::get_shared_lines() : Cannot return a shared-memory subset (0->%u,%u->%u,%u,%u) from "
10203
"a (%u,%u,%u,%u) image.",pixel_type(),width-1,y0,y1,z0,v0,width,height,depth,dim);
10204
return CImg<T>(data+beg,width,y1-y0+1,1,1,true);
10207
//! Return a shared-memory image referencing one particular line (y0,z0,v0) of the instance image.
10208
CImg get_shared_line(const unsigned int y0, const unsigned int z0=0, const unsigned int v0=0) {
10209
return get_shared_lines(y0,y0,z0,v0);
10212
//! Return a shared-memory image referencing one particular line (y0,z0,v0) of the instance image (const version).
10213
const CImg get_shared_line(const unsigned int y0, const unsigned int z0=0, const unsigned int v0=0) const {
10214
return get_shared_lines(y0,y0,z0,v0);
10217
//! Return a shared memory image referencing a set of planes (z0->z1,v0) of the instance image.
10218
CImg get_shared_planes(const unsigned int z0, const unsigned int z1, const unsigned int v0=0) {
10219
const unsigned long beg = offset(0,0,z0,v0), end = offset(0,0,z1,v0);
10220
if (beg>end || beg>=size() || end>=size())
10221
throw CImgArgumentException("CImg<%s>::get_shared_planes() : Cannot return a shared-memory subset (0->%u,0->%u,%u->%u,%u) from "
10222
"a (%u,%u,%u,%u) image.",pixel_type(),width-1,height-1,z0,z1,v0,width,height,depth,dim);
10223
return CImg<T>(data+beg,width,height,z1-z0+1,1,true);
10226
//! Return a shared-memory image referencing a set of planes (z0->z1,v0) of the instance image (const version).
10227
const CImg get_shared_planes(const unsigned int z0, const unsigned int z1, const unsigned int v0=0) const {
10228
const unsigned long beg = offset(0,0,z0,v0), end = offset(0,0,z1,v0);
10229
if (beg>end || beg>=size() || end>=size())
10230
throw CImgArgumentException("CImg<%s>::get_shared_planes() : Cannot return a shared-memory subset (0->%u,0->%u,%u->%u,%u) from "
10231
"a (%u,%u,%u,%u) image.",pixel_type(),width-1,height-1,z0,z1,v0,width,height,depth,dim);
10232
return CImg<T>(data+beg,width,height,z1-z0+1,1,true);
10235
//! Return a shared-memory image referencing one plane (z0,v0) of the instance image.
10236
CImg get_shared_plane(const unsigned int z0, const unsigned int v0=0) {
10237
return get_shared_planes(z0,z0,v0);
10240
//! Return a shared-memory image referencing one plane (z0,v0) of the instance image (const version).
10241
const CImg get_shared_plane(const unsigned int z0, const unsigned int v0=0) const {
10242
return get_shared_planes(z0,z0,v0);
10245
//! Return a shared-memory image referencing a set of channels (v0->v1) of the instance image.
10246
CImg get_shared_channels(const unsigned int v0, const unsigned int v1) {
10247
const unsigned long beg = offset(0,0,0,v0), end = offset(0,0,0,v1);
10248
if (beg>end || beg>=size() || end>=size())
10249
throw CImgArgumentException("CImg<%s>::get_shared_channels() : Cannot return a shared-memory subset (0->%u,0->%u,0->%u,%u->%u) from "
10250
"a (%u,%u,%u,%u) image.",pixel_type(),width-1,height-1,depth-1,v0,v1,width,height,depth,dim);
10251
return CImg<T>(data+beg,width,height,depth,v1-v0+1,true);
10254
//! Return a shared-memory image referencing a set of channels (v0->v1) of the instance image (const version).
10255
const CImg get_shared_channels(const unsigned int v0, const unsigned int v1) const {
10256
const unsigned long beg = offset(0,0,0,v0), end = offset(0,0,0,v1);
10257
if (beg>end || beg>=size() || end>=size())
10258
throw CImgArgumentException("CImg<%s>::get_shared_channels() : Cannot return a shared-memory subset (0->%u,0->%u,0->%u,%u->%u) from "
10259
"a (%u,%u,%u,%u) image.",pixel_type(),width-1,height-1,depth-1,v0,v1,width,height,depth,dim);
10260
return CImg<T>(data+beg,width,height,depth,v1-v0+1,true);
10263
//! Return a shared-memory image referencing one channel v0 of the instance image.
10264
CImg get_shared_channel(const unsigned int v0) {
10265
return get_shared_channels(v0,v0);
10268
//! Return a shared-memory image referencing one channel v0 of the instance image (const version).
10269
const CImg get_shared_channel(const unsigned int v0) const {
10270
return get_shared_channels(v0,v0);
10273
//! Return a shared version of the instance image.
10274
CImg get_shared() {
10275
return CImg<T>(data,width,height,depth,dim,true);
10278
//! Return a shared version of the instance image (const version).
10279
const CImg get_shared() const {
10280
return CImg<T>(data,width,height,depth,dim,true);
14576
CImg<T> get_permute_axes(const char *permut="vxyz") const {
14577
const T foo = (T)0;
14578
return get_permute_axes(permut,foo);
14581
//! Permute axes order (in-place).
14582
CImg<T>& permute_axes(const char *order="vxyz") {
14583
return get_permute_axes(order).transfer_to(*this);
10283
14586
//! Mirror an image along the specified axis.
10285
This is the in-place version of get_mirror().
10288
CImg& mirror(const char axe='x') {
14587
CImg<T> get_mirror(const char axe='x') const {
14588
return (+*this).mirror(axe);
14591
//! Mirror an image along the specified axis (in-place).
14592
CImg<T>& mirror(const char axe='x') {
10289
14593
if (!is_empty()) {
10290
14594
T *pf, *pb, *buf = 0;
10291
14595
switch (cimg::uncase(axe)) {
10293
pf = ptr(); pb = ptr(width-1);
14597
pf = data; pb = ptr(width-1);
10294
14598
for (unsigned int yzv=0; yzv<height*depth*dim; ++yzv) {
10295
14599
for (unsigned int x=0; x<width/2; ++x) { const T val = *pf; *(pf++) = *pb; *(pb--) = val; }
10296
14600
pf+=width-width/2;
11130
15906
return *this;
15909
//! Return a 3D centered cube.
15910
template<typename tf> static CImg<typename cimg::last<T,float>::type>
15911
cube3d(CImgList<tf>& primitives, const float size=100) {
15912
typedef typename cimg::last<T,float>::type t_float;
15913
const double s = size/2.0;
15914
primitives.assign(6,1,4,1,1, 0,3,2,1, 4,5,6,7, 0,1,5,4, 3,7,6,2, 0,4,7,3, 1,2,6,5);
15915
return CImg<t_float>(8,3,1,1,
15916
-s,s,s,-s,-s,s,s,-s,
15917
-s,-s,s,s,-s,-s,s,s,
15918
-s,-s,-s,-s,s,s,s,s);
15921
//! Return a 3D centered cuboid.
15922
template<typename tf> static CImg<typename cimg::last<T,float>::type>
15923
cuboid3d(CImgList<tf>& primitives,const float sizex=200, const float sizey=100, const float sizez=100) {
15924
typedef typename cimg::last<T,float>::type t_float;
15925
const double sx = sizex/2.0, sy = sizey/2.0, sz = sizez/2.0;
15926
primitives.assign(6,1,4,1,1, 0,3,2,1, 4,5,6,7, 0,1,5,4, 3,7,6,2, 0,4,7,3, 1,2,6,5);
15927
return CImg<t_float>(8,3,1,1,
15928
-sx,sx,sx,-sx,-sx,sx,sx,-sx,
15929
-sy,-sy,sy,sy,-sy,-sy,sy,sy,
15930
-sz,-sz,-sz,-sz,sz,sz,sz,sz);
15933
//! Return a 3D centered cone.
15934
template<typename tf> static CImg<typename cimg::last<T,float>::type>
15935
cone3d(CImgList<tf>& primitives, const float radius=50, const float height=100,
15936
const unsigned int subdivisions=24, const bool symetrize=false) {
15937
typedef typename cimg::last<T,float>::type t_float;
15938
primitives.assign();
15939
if (!subdivisions) return CImg<t_float>();
15940
const double r = (double)radius, h = (double)height/2;
15941
CImgList<t_float> points(2,1,3,1,1,
15944
const float delta = 360.0f/subdivisions, nh = symetrize?0:-(float)h;
15945
for (float angle = 0.0f; angle<360.0f; angle+=delta) {
15946
const float a = (float)(angle*cimg::valuePI/180);
15947
points.insert(CImg<t_float>::vector((float)(r*std::cos(a)),(float)(r*std::sin(a)),nh));
15949
const unsigned int nbr = points.size-2;
15950
for (unsigned int p = 0; p<nbr; ++p) {
15951
const unsigned int curr = 2+p, next = 2+((p+1)%nbr);
15952
primitives.insert(CImg<tf>::vector(1,next,curr)).
15953
insert(CImg<tf>::vector(0,curr,next));
15955
return points.get_append('x');
15958
//! Return a 3D centered cylinder.
15959
template<typename tf> static CImg<typename cimg::last<T,float>::type>
15960
cylinder3d(CImgList<tf>& primitives, const float radius=50, const float height=100,
15961
const unsigned int subdivisions=24) {
15962
typedef typename cimg::last<T,float>::type t_float;
15963
primitives.assign();
15964
if (!subdivisions) return CImg<t_float>();
15965
const double r = (double)radius, h = (double)height/2;
15966
CImgList<t_float> points(2,1,3,1,1,
15970
const float delta = 360.0f/subdivisions;
15971
for (float angle = 0.0f; angle<360.0f; angle+=delta) {
15972
const float a = (float)(angle*cimg::valuePI/180);
15973
points.insert(CImg<t_float>::vector((float)(r*std::cos(a)),(float)(r*std::sin(a)),-(float)h));
15974
points.insert(CImg<t_float>::vector((float)(r*std::cos(a)),(float)(r*std::sin(a)),(float)h));
15976
const unsigned int nbr = (points.size-2)/2;
15977
for (unsigned int p = 0; p<nbr; ++p) {
15978
const unsigned int curr = 2+2*p, next = 2+(2*((p+1)%nbr));
15979
primitives.insert(CImg<tf>::vector(0,next,curr)).
15980
insert(CImg<tf>::vector(1,curr+1,next+1)).
15981
insert(CImg<tf>::vector(curr,next,next+1,curr+1));
15983
return points.get_append('x');
15986
//! Return a 3D centered torus.
15987
template<typename tf> static CImg<typename cimg::last<T,float>::type>
15988
torus3d(CImgList<tf>& primitives, const float radius1=100, const float radius2=30,
15989
const unsigned int subdivisions1=24, const unsigned int subdivisions2=12) {
15990
typedef typename cimg::last<T,float>::type type_float;
15991
primitives.assign();
15992
if (!subdivisions1 || !subdivisions2) return CImg<type_float>();
15993
CImgList<type_float> points;
15994
for (unsigned int v = 0; v<subdivisions1; ++v) {
15996
beta = (float)(v*2*cimg::valuePI/subdivisions1),
15997
xc = radius1*(float)std::cos(beta),
15998
yc = radius1*(float)std::sin(beta);
15999
for (unsigned int u=0; u<subdivisions2; ++u) {
16001
alpha = (float)(u*2*cimg::valuePI/subdivisions2),
16002
x = xc + radius2*(float)(std::cos(alpha)*std::cos(beta)),
16003
y = yc + radius2*(float)(std::cos(alpha)*std::sin(beta)),
16004
z = radius2*(float)std::sin(alpha);
16005
points.insert(CImg<type_float>::vector(x,y,z));
16008
for (unsigned int vv = 0; vv<subdivisions1; ++vv) {
16009
const unsigned int nv = (vv+1)%subdivisions1;
16010
for (unsigned int uu = 0; uu<subdivisions2; ++uu) {
16011
const unsigned int nu = (uu+1)%subdivisions2, svv = subdivisions2*vv, snv = subdivisions2*nv;
16012
primitives.insert(CImg<tf>::vector(svv+nu,svv+uu,snv+uu));
16013
primitives.insert(CImg<tf>::vector(svv+nu,snv+uu,snv+nu));
16016
return points.get_append('x');
16019
//! Return a 3D centered XY plane.
16020
template<typename tf> static CImg<typename cimg::last<T,float>::type>
16021
plane3d(CImgList<tf>& primitives, const float sizex=100, const float sizey=100,
16022
const unsigned int subdivisionsx=3, const unsigned int subdivisionsy=3,
16023
const bool double_sided=false) {
16024
typedef typename cimg::last<T,float>::type type_float;
16025
primitives.assign();
16026
if (!subdivisionsx || !subdivisionsy) return CImg<type_float>();
16027
CImgList<type_float> points;
16028
const unsigned int w = subdivisionsx + 1, h = subdivisionsy + 1;
16029
const float w2 = subdivisionsx/2.0f, h2 = subdivisionsy/2.0f, fx = (float)sizex/w, fy = (float)sizey/h;
16030
for (unsigned int yy = 0; yy<h; ++yy)
16031
for (unsigned int xx = 0; xx<w; ++xx)
16032
points.insert(CImg<type_float>::vector(fx*(xx-w2),fy*(yy-h2),0));
16033
for (unsigned int y = 0; y<subdivisionsy; ++y) for (unsigned int x = 0; x<subdivisionsx; ++x) {
16034
const int off1 = x+y*w, off2 = x+1+y*w, off3 = x+1+(y+1)*w, off4 = x+(y+1)*w;
16035
primitives.insert(CImg<tf>::vector(off1,off4,off3,off2));
16036
if (double_sided) primitives.insert(CImg<tf>::vector(off1,off2,off3,off4));
16038
return points.get_append('x');
16041
//! Return a 3D centered sphere.
16042
template<typename tf> static CImg<typename cimg::last<T,float>::type>
16043
sphere3d(CImgList<tf>& primitives, const float radius=50, const unsigned int subdivisions=3) {
16045
// Create initial icosahedron
16046
typedef typename cimg::last<T,float>::type type_float;
16047
primitives.assign();
16048
if (!subdivisions) return CImg<type_float>();
16049
const double tmp = (1+std::sqrt(5.0f))/2.0f, a = 1.0/std::sqrt(1+tmp*tmp), b = tmp*a;
16050
CImgList<type_float> points(12,1,3,1,1, b,a,0.0, -b,a,0.0, -b,-a,0.0, b,-a,0.0, a,0.0,b, a,0.0,-b,
16051
-a,0.0,-b, -a,0.0,b, 0.0,b,a, 0.0,-b,a, 0.0,-b,-a, 0.0,b,-a);
16052
primitives.assign(20,1,3,1,1, 4,8,7, 4,7,9, 5,6,11, 5,10,6, 0,4,3, 0,3,5, 2,7,1, 2,1,6,
16053
8,0,11, 8,11,1, 9,10,3, 9,2,10, 8,4,0, 11,0,5, 4,9,3,
16054
5,3,10, 7,8,1, 6,1,11, 7,2,9, 6,10,2);
16056
// Recurse subdivisions
16057
for (unsigned int i = 0; i<subdivisions; ++i) {
16058
const unsigned int L = primitives.size;
16059
for (unsigned int l = 0; l<L; ++l) {
16061
p0 = (unsigned int)primitives(0,0), p1 = (unsigned int)primitives(0,1), p2 = (unsigned int)primitives(0,2);
16063
x0 = points(p0,0), y0 = points(p0,1), z0 = points(p0,2),
16064
x1 = points(p1,0), y1 = points(p1,1), z1 = points(p1,2),
16065
x2 = points(p2,0), y2 = points(p2,1), z2 = points(p2,2),
16066
tnx0 = (x0+x1)/2, tny0 = (y0+y1)/2, tnz0 = (z0+z1)/2, nn0 = (float)std::sqrt(tnx0*tnx0+tny0*tny0+tnz0*tnz0),
16067
tnx1 = (x0+x2)/2, tny1 = (y0+y2)/2, tnz1 = (z0+z2)/2, nn1 = (float)std::sqrt(tnx1*tnx1+tny1*tny1+tnz1*tnz1),
16068
tnx2 = (x1+x2)/2, tny2 = (y1+y2)/2, tnz2 = (z1+z2)/2, nn2 = (float)std::sqrt(tnx2*tnx2+tny2*tny2+tnz2*tnz2),
16069
nx0 = tnx0/nn0, ny0 = tny0/nn0, nz0 = tnz0/nn0,
16070
nx1 = tnx1/nn1, ny1 = tny1/nn1, nz1 = tnz1/nn1,
16071
nx2 = tnx2/nn2, ny2 = tny2/nn2, nz2 = tnz2/nn2;
16072
int i0 = -1, i1 = -1, i2 = -1;
16073
cimglist_for(points,p) {
16074
const float x = (float)points(p,0), y = (float)points(p,1), z = (float)points(p,2);
16075
if (x==nx0 && y==ny0 && z==nz0) i0 = p;
16076
if (x==nx1 && y==ny1 && z==nz1) i1 = p;
16077
if (x==nx2 && y==ny2 && z==nz2) i2 = p;
16079
if (i0<0) { points.insert(CImg<>::vector(nx0,ny0,nz0)); i0 = points.size-1; }
16080
if (i1<0) { points.insert(CImg<>::vector(nx1,ny1,nz1)); i1 = points.size-1; }
16081
if (i2<0) { points.insert(CImg<>::vector(nx2,ny2,nz2)); i2 = points.size-1; }
16082
primitives.remove(0);
16083
primitives.insert(CImg<unsigned int>::vector(p0,i0,i1)).
16084
insert(CImg<unsigned int>::vector(i0,p1,i2)).
16085
insert(CImg<unsigned int>::vector(i1,i2,p2)).
16086
insert(CImg<unsigned int>::vector(i1,i0,i2));
16089
return points.get_append('x')*=radius;
16092
//! Return a 3D centered ellipsoid.
16093
template<typename tf, typename t> static CImg<typename cimg::last<T,float>::type>
16094
ellipsoid3d(CImgList<tf>& primitives, const CImg<t>& tensor, const unsigned int subdivisions=3) {
16095
typedef typename cimg::last<T,float>::type type_float;
16096
primitives.assign();
16097
if (!subdivisions) return CImg<type_float>();
16098
typedef typename cimg::superset<t,float>::type tfloat;
16100
tensor.symmetric_eigen(S,V);
16101
const tfloat l0 = S[0], l1 = S[1], l2 = S[2];
16102
CImg<type_float> points = sphere(primitives,subdivisions);
16103
cimg_forX(points,p) {
16104
points(p,0) = (float)(points(p,0)*l0);
16105
points(p,1) = (float)(points(p,1)*l1);
16106
points(p,2) = (float)(points(p,2)*l2);
16113
//! Translate a 3D object.
16114
CImg<Tfloat> get_translate_object3d(const float tx, const float ty=0, const float tz=0) const {
16115
return CImg<Tfloat>(*this,false).translate_object3d(tx,ty,tz);
16118
//! Translate a 3D object (in-place).
16119
CImg<T>& translate_object3d(const float tx, const float ty=0, const float tz=0) {
16120
get_shared_line(0)+=tx; get_shared_line(1)+=ty; get_shared_line(2)+=tz;
16124
//! Translate a 3D object so that it becomes centered.
16125
CImg<Tfloat> get_translate_object3d() const {
16126
return CImg<Tfloat>(*this,false).translate_object3d();
16129
//! Translate a 3D object so that it becomes centered (in-place).
16130
CImg<T>& translate_object3d() {
16131
CImg<T> xcoords = get_shared_line(0), ycoords = get_shared_line(1), zcoords = get_shared_line(2);
16132
float xm, xM = xcoords.maxmin(xm), ym, yM = ycoords.maxmin(ym), zm, zM = zcoords.maxmin(zm);
16133
xcoords-=(xm + xM)/2; ycoords-=(ym + yM)/2; zcoords-=(zm + zM)/2;
16137
//! Resize a 3D object.
16138
CImg<Tfloat> get_resize_object3d(const float sx, const float sy=-100, const float sz=-100) const {
16139
return CImg<Tfloat>(*this,false).resize_object3d(sx,sy,sz);
16142
//! Resize a 3D object (in-place).
16143
CImg<T>& resize_object3d(const float sx, const float sy=-100, const float sz=-100) {
16144
CImg<T> xcoords = get_shared_line(0), ycoords = get_shared_line(1), zcoords = get_shared_line(2);
16145
float xm, xM = xcoords.maxmin(xm), ym, yM = ycoords.maxmin(ym), zm, zM = zcoords.maxmin(zm);
16146
if (xm<xM) { if (sx>0) xcoords*=sx/(xM-xm); else xcoords*=-sx/100; }
16147
if (ym<yM) { if (sy>0) ycoords*=sy/(yM-ym); else ycoords*=-sy/100; }
16148
if (zm<zM) { if (sz>0) zcoords*=sz/(zM-zm); else zcoords*=-sz/100; }
16152
//! Append a 3D object to another one.
16153
template<typename tf, typename tp, typename tff>
16154
CImg<T>& append_object3d(CImgList<tf>& primitives, const CImg<tp>& obj_points, const CImgList<tff>& obj_primitives) {
16155
const unsigned int P = width;
16156
append(obj_points,'x');
16157
const unsigned int N = primitives.size;
16158
primitives.insert(obj_primitives);
16159
for (unsigned int i = N; i<primitives.size; ++i) {
16160
CImg<tf> &p = primitives[i];
16161
if (p.size()!=5) p+=P;
16162
else { p[0]+=P; if (p[2]==0) p[1]+=P; }
11134
16168
//----------------------------
11136
//! \name Color conversions
16170
//! \name Color bases
11138
16172
//----------------------------
11140
//! Return the default 256 colors palette.
16174
//! Return a default indexed color palette with 256 (R,G,B) entries.
11142
16176
The default color palette is used by %CImg when displaying images on 256 colors displays.
11143
16177
It consists in the quantification of the (R,G,B) color space using 3:3:2 bits for color coding
11144
16178
(i.e 8 levels for the Red and Green and 4 levels for the Blue).
11145
\return A 256x1x1x3 color image defining the palette entries.
16179
\return a 1x256x1x3 color image defining the palette entries.
11147
static CImg<T> get_default_LUT8() {
11148
static CImg<T> palette;
16181
static CImg<Tuchar> get_default_LUT8() {
16182
static CImg<Tuchar> palette;
11149
16183
if (!palette) {
11150
16184
palette.assign(1,256,1,3);
11151
for (unsigned int index=0, r=16; r<256; r+=32)
11152
for (unsigned int g=16; g<256; g+=32)
11153
for (unsigned int b=32; b<256; b+=64) {
11154
palette(index,0) = r;
11155
palette(index,1) = g;
11156
palette(index++,2) = b;
16185
for (unsigned int index = 0, r = 16; r<256; r+=32)
16186
for (unsigned int g = 16; g<256; g+=32)
16187
for (unsigned int b = 32; b<256; b+=64) {
16188
palette(0,index,0) = (Tuchar)r;
16189
palette(0,index,1) = (Tuchar)g;
16190
palette(0,index++,2) = (Tuchar)b;
11159
16193
return palette;
11162
//! Return a rainbow-palette
11163
static CImg<T> get_rainbow_LUT8() {
11164
static CImg<T> palette;
16196
//! Return a rainbow color palette with 256 (R,G,B) entries.
16197
static CImg<Tuchar> get_rainbow_LUT8() {
16198
static CImg<Tuchar> palette;
11165
16199
if (!palette) {
11166
palette.assign(1,256,1,3,255);
11167
palette.get_shared_channel(0).sequence(0,359);
11168
palette.HSVtoRGB();
16200
CImg<Tint> tmp(1,256,1,3,1);
16201
tmp.get_shared_channel(0).sequence(0,359);
16202
palette = tmp.HSVtoRGB();
11170
16204
return palette;
11173
//! Return contrasted palette optmized for cluster visualization
11174
static CImg<T> get_cluster_LUT8() {
11175
static const unsigned char pal[] =
11176
{ 217,62,88,75,1,237,240,12,56,160,165,116,1,1,204,2,15,248,148,185,133,141,46,246,222,116,16,5,207,226,
11177
17,114,247,1,214,53,238,0,95,55,233,235,109,0,17,54,33,0,90,30,3,0,94,27,19,0,68,212,166,130,0,15,7,119,
11178
238,2,246,198,0,3,16,10,13,2,25,28,12,6,2,99,18,141,30,4,3,140,12,4,30,233,7,10,0,136,35,160,168,184,20,
11179
233,0,1,242,83,90,56,180,44,41,0,6,19,207,5,31,214,4,35,153,180,75,21,76,16,202,218,22,17,2,136,71,74,
11180
81,251,244,148,222,17,0,234,24,0,200,16,239,15,225,102,230,186,58,230,110,12,0,7,129,249,22,241,37,219,
11181
1,3,254,210,3,212,113,131,197,162,123,252,90,96,209,60,0,17,0,180,249,12,112,165,43,27,229,77,40,195,12,
11182
87,1,210,148,47,80,5,9,1,137,2,40,57,205,244,40,8,252,98,0,40,43,206,31,187,0,180,1,69,70,227,131,108,0,
11183
223,94,228,35,248,243,4,16,0,34,24,2,9,35,73,91,12,199,51,1,249,12,103,131,20,224,2,70,32,
11184
233,1,165,3,8,154,246,233,196,5,0,6,183,227,247,195,208,36,0,0,226,160,210,198,69,153,210,1,23,8,192,2,4,
11185
137,1,0,52,2,249,241,129,0,0,234,7,238,71,7,32,15,157,157,252,158,2,250,6,13,30,11,162,0,199,21,11,27,224,
11186
4,157,20,181,111,187,218,3,0,11,158,230,196,34,223,22,248,135,254,210,157,219,0,117,239,3,255,4,227,5,247,
11187
11,4,3,188,111,11,105,195,2,0,14,1,21,219,192,0,183,191,113,241,1,12,17,248,0,48,7,19,1,254,212,0,239,246,
11188
0,23,0,250,165,194,194,17,3,253,0,24,6,0,141,167,221,24,212,2,235,243,0,0,205,1,251,133,204,28,4,6,1,10,
11189
141,21,74,12,236,254,228,19,1,0,214,1,186,13,13,6,13,16,27,209,6,216,11,207,251,59,32,9,155,23,19,235,143,
11190
116,6,213,6,75,159,23,6,0,228,4,10,245,249,1,7,44,234,4,102,174,0,19,239,103,16,15,18,8,214,22,4,47,244,
11191
255,8,0,251,173,1,212,252,250,251,252,6,0,29,29,222,233,246,5,149,0,182,180,13,151,0,203,183,0,35,149,0,
11192
235,246,254,78,9,17,203,73,11,195,0,3,5,44,0,0,237,5,106,6,130,16,214,20,168,247,168,4,207,11,5,1,232,251,
11193
129,210,116,231,217,223,214,27,45,38,4,177,186,249,7,215,172,16,214,27,249,230,236,2,34,216,217,0,175,30,
11194
243,225,244,182,20,212,2,226,21,255,20,0,2,13,62,13,191,14,76,64,20,121,4,118,0,216,1,147,0,2,210,1,215,
11195
95,210,236,225,184,46,0,248,24,11,1,9,141,250,243,9,221,233,160,11,147,2,55,8,23,12,253,9,0,54,0,231,6,3,
11196
141,8,2,246,9,180,5,11,8,227,8,43,110,242,1,130,5,97,36,10,6,219,86,133,11,108,6,1,5,244,67,19,28,0,174,
11197
154,16,127,149,252,188,196,196,228,244,9,249,0,0,0,37,170,32,250,0,73,255,23,3,224,234,38,195,198,0,255,87,
11198
33,221,174,31,3,0,189,228,6,153,14,144,14,108,197,0,9,206,245,254,3,16,253,178,248,0,95,125,8,0,3,168,21,
11199
23,168,19,50,240,244,185,0,1,144,10,168,31,82,1,13 };
11200
static const CImg<T> palette(pal,256,1,1,3);
16207
//! Return a contrasted color palette with 256 (R,G,B) entries.
16208
static CImg<Tuchar> get_contrast_LUT8() {
16209
static const unsigned char pal[] = {
16210
217,62,88,75,1,237,240,12,56,160,165,116,1,1,204,2,15,248,148,185,133,141,46,246,222,116,16,5,207,226,
16211
17,114,247,1,214,53,238,0,95,55,233,235,109,0,17,54,33,0,90,30,3,0,94,27,19,0,68,212,166,130,0,15,7,119,
16212
238,2,246,198,0,3,16,10,13,2,25,28,12,6,2,99,18,141,30,4,3,140,12,4,30,233,7,10,0,136,35,160,168,184,20,
16213
233,0,1,242,83,90,56,180,44,41,0,6,19,207,5,31,214,4,35,153,180,75,21,76,16,202,218,22,17,2,136,71,74,
16214
81,251,244,148,222,17,0,234,24,0,200,16,239,15,225,102,230,186,58,230,110,12,0,7,129,249,22,241,37,219,
16215
1,3,254,210,3,212,113,131,197,162,123,252,90,96,209,60,0,17,0,180,249,12,112,165,43,27,229,77,40,195,12,
16216
87,1,210,148,47,80,5,9,1,137,2,40,57,205,244,40,8,252,98,0,40,43,206,31,187,0,180,1,69,70,227,131,108,0,
16217
223,94,228,35,248,243,4,16,0,34,24,2,9,35,73,91,12,199,51,1,249,12,103,131,20,224,2,70,32,
16218
233,1,165,3,8,154,246,233,196,5,0,6,183,227,247,195,208,36,0,0,226,160,210,198,69,153,210,1,23,8,192,2,4,
16219
137,1,0,52,2,249,241,129,0,0,234,7,238,71,7,32,15,157,157,252,158,2,250,6,13,30,11,162,0,199,21,11,27,224,
16220
4,157,20,181,111,187,218,3,0,11,158,230,196,34,223,22,248,135,254,210,157,219,0,117,239,3,255,4,227,5,247,
16221
11,4,3,188,111,11,105,195,2,0,14,1,21,219,192,0,183,191,113,241,1,12,17,248,0,48,7,19,1,254,212,0,239,246,
16222
0,23,0,250,165,194,194,17,3,253,0,24,6,0,141,167,221,24,212,2,235,243,0,0,205,1,251,133,204,28,4,6,1,10,
16223
141,21,74,12,236,254,228,19,1,0,214,1,186,13,13,6,13,16,27,209,6,216,11,207,251,59,32,9,155,23,19,235,143,
16224
116,6,213,6,75,159,23,6,0,228,4,10,245,249,1,7,44,234,4,102,174,0,19,239,103,16,15,18,8,214,22,4,47,244,
16225
255,8,0,251,173,1,212,252,250,251,252,6,0,29,29,222,233,246,5,149,0,182,180,13,151,0,203,183,0,35,149,0,
16226
235,246,254,78,9,17,203,73,11,195,0,3,5,44,0,0,237,5,106,6,130,16,214,20,168,247,168,4,207,11,5,1,232,251,
16227
129,210,116,231,217,223,214,27,45,38,4,177,186,249,7,215,172,16,214,27,249,230,236,2,34,216,217,0,175,30,
16228
243,225,244,182,20,212,2,226,21,255,20,0,2,13,62,13,191,14,76,64,20,121,4,118,0,216,1,147,0,2,210,1,215,
16229
95,210,236,225,184,46,0,248,24,11,1,9,141,250,243,9,221,233,160,11,147,2,55,8,23,12,253,9,0,54,0,231,6,3,
16230
141,8,2,246,9,180,5,11,8,227,8,43,110,242,1,130,5,97,36,10,6,219,86,133,11,108,6,1,5,244,67,19,28,0,174,
16231
154,16,127,149,252,188,196,196,228,244,9,249,0,0,0,37,170,32,250,0,73,255,23,3,224,234,38,195,198,0,255,87,
16232
33,221,174,31,3,0,189,228,6,153,14,144,14,108,197,0,9,206,245,254,3,16,253,178,248,0,95,125,8,0,3,168,21,
16233
23,168,19,50,240,244,185,0,1,144,10,168,31,82,1,13 };
16234
static const CImg<Tuchar> palette(pal,1,256,1,3);
11201
16235
return palette;
11204
//! Convert color pixels from (R,G,B) to match a specified palette.
11206
This function return a (R,G,B) image where colored pixels are constrained to match entries
11207
of the specified color \c palette.
11208
\param palette User-defined palette that will constraint the color conversion.
11209
\param dithering Enable/Disable Floyd-Steinberg dithering.
11210
\param indexing If \c true, each resulting image pixel is an index to the given color palette.
11211
Otherwise, (R,G,B) values of the palette are copied instead.
16238
//! Convert (R,G,B) color image to indexed color image.
11213
16239
template<typename t> CImg<t> get_RGBtoLUT(const CImg<t>& palette, const bool dithering=true, const bool indexing=false) const {
11214
16240
if (is_empty()) return CImg<t>();
11215
16241
if (dim!=3) throw CImgInstanceException("CImg<%s>::RGBtoLUT() : Input image dimension is dim=%u, "
19673
27009
//! Load an image from a PNG file.
19674
CImg& load_png(const char *const filename) {
19675
return load_png(0,filename);
19678
//! Load an image from a PNG file.
19679
static CImg get_load_png(std::FILE *const file, const char *const filename=0) {
19680
return CImg<T>().load_png(file,filename);
19683
//! Load an image from a PNG file.
19684
static CImg get_load_png(const char *const filename) {
19685
return CImg<T>().load_png(0,filename);
19688
//! Load an image from a TIFF file.
27010
static CImg<T> get_load_png(const char *const filename) {
27011
return CImg<T>().load_png(filename);
27014
//! Load an image from a PNG file.
27015
static CImg<T> get_load_png(std::FILE *const file) {
27016
return CImg<T>().load_png(file);
27019
//! Load an image from a PNG file (in-place).
27020
CImg<T>& load_png(const char *const filename) {
27021
return _load_png(0,filename);
27024
//! Load an image from a PNG file (in-place).
27025
CImg<T>& load_png(std::FILE *const file) {
27026
return _load_png(file,0);
27029
// Load an image from a PNM file (internal).
27030
CImg<T>& _load_pnm(std::FILE *const file, const char *const filename) {
27031
if (!filename && !file) throw CImgArgumentException("CImg<%s>::load_pnm() : Cannot load (null) filename.",pixel_type());
27032
std::FILE *const nfile=file?file:cimg::fopen(filename,"rb");
27033
unsigned int ppm_type, W, H, colormax=255;
27034
char item[1024] = { 0 };
27035
int err, rval, gval, bval;
27036
const int cimg_iobuffer = 12*1024*1024;
27037
while ((err=std::fscanf(nfile,"%1023[^\n]",item))!=EOF && (item[0]=='#' || !err)) std::fgetc(nfile);
27038
if(std::sscanf(item," P%u",&ppm_type)!=1) {
27039
if (!file) cimg::fclose(nfile);
27040
throw CImgIOException("CImg<%s>::load_pnm() : File '%s', PNM header 'P?' not found.",
27041
pixel_type(),filename?filename:"(FILE*)");
27043
while ((err=std::fscanf(nfile," %1023[^\n]",item))!=EOF && (item[0]=='#' || !err)) std::fgetc(nfile);
27044
if ((err=std::sscanf(item," %u %u %u",&W,&H,&colormax))<2) {
27045
if (!file) cimg::fclose(nfile);
27046
throw CImgIOException("CImg<%s>::load_pnm() : File '%s', WIDTH and HEIGHT fields are not defined in PNM header.",
27047
pixel_type(),filename?filename:"(FILE*)");
27050
while ((err=std::fscanf(nfile," %1023[^\n]",item))!=EOF && (item[0]=='#' || !err)) std::fgetc(nfile);
27051
if (std::sscanf(item,"%u",&colormax)!=1)
27052
cimg::warn("CImg<%s>::load_pnm() : File '%s', COLORMAX field is not defined in PNM header.",
27053
pixel_type(),filename?filename:"(FILE*)");
27058
switch (ppm_type) {
27059
case 2: { // Grey Ascii
27062
cimg_foroff(*this,off) { std::fscanf(nfile,"%d",&rval); *(rdata++) = (T)rval; }
27064
case 3: { // Color Ascii
27066
T *rdata = ptr(0,0,0,0), *gdata = ptr(0,0,0,1), *bdata = ptr(0,0,0,2);
27067
cimg_forXY(*this,x,y) {
27068
std::fscanf(nfile,"%d %d %d",&rval,&gval,&bval);
27069
*(rdata++) = (T)rval;
27070
*(gdata++) = (T)gval;
27071
*(bdata++) = (T)bval; }
27073
case 5: { // Grey Binary
27074
if (colormax<256) { // 8 bits
27075
CImg<unsigned char> raw;
27077
T *ptrd = ptr(0,0,0,0);
27078
for (int toread = (int)size(); toread>0; ) {
27079
raw.assign(cimg::min(toread,cimg_iobuffer));
27080
cimg::fread(raw.data,raw.width,nfile);
27082
const unsigned char *ptrs = raw.data;
27083
for (unsigned int off = raw.width; off; --off) *(ptrd++) = (T)*(ptrs++);
27085
} else { // 16 bits
27086
CImg<unsigned short> raw;
27088
T *ptrd = ptr(0,0,0,0);
27089
for (int toread = (int)size(); toread>0; ) {
27090
raw.assign(cimg::min(toread,cimg_iobuffer/2));
27091
cimg::fread(raw.data,raw.width,nfile);
27093
const unsigned short *ptrs = raw.data;
27094
for (unsigned int off = raw.width; off; --off) *(ptrd++) = (T)*(ptrs++);
27098
case 6: { // Color Binary
27099
if (colormax<256) { // 8 bits
27100
CImg<unsigned char> raw;
27103
*ptr_r = ptr(0,0,0,0),
27104
*ptr_g = ptr(0,0,0,1),
27105
*ptr_b = ptr(0,0,0,2);
27106
for (int toread = (int)size(); toread>0; ) {
27107
raw.assign(cimg::min(toread,cimg_iobuffer));
27108
cimg::fread(raw.data,raw.width,nfile);
27110
const unsigned char *ptrs = raw.data;
27111
for (unsigned int off = raw.width/3; off; --off) {
27112
*(ptr_r++) = (T)*(ptrs++);
27113
*(ptr_g++) = (T)*(ptrs++);
27114
*(ptr_b++) = (T)*(ptrs++);
27117
} else { // 16 bits
27118
CImg<unsigned short> raw;
27121
*ptr_r = ptr(0,0,0,0),
27122
*ptr_g = ptr(0,0,0,1),
27123
*ptr_b = ptr(0,0,0,2);
27124
for (int toread = (int)size(); toread>0; ) {
27125
raw.assign(cimg::min(toread,cimg_iobuffer/2));
27126
cimg::fread(raw.data,raw.width,nfile);
27127
if (!cimg::endianness()) cimg::invert_endianness(raw.data,raw.width);
27129
const unsigned short *ptrs = raw.data;
27130
for (unsigned int off = raw.width/3; off; --off) {
27131
*(ptr_r++) = (T)*(ptrs++);
27132
*(ptr_g++) = (T)*(ptrs++);
27133
*(ptr_b++) = (T)*(ptrs++);
27139
if (!file) cimg::fclose(nfile);
27140
throw CImgIOException("CImg<%s>::load_pnm() : File '%s', PPM type 'P%d' not supported.",
27141
pixel_type(),filename?filename:"(FILE*)",ppm_type);
27143
if (!file) cimg::fclose(nfile);
27147
//! Load an image from a PNM file.
27148
static CImg<T> get_load_pnm(const char *const filename) {
27149
return CImg<T>().load_pnm(filename);
27152
//! Load an image from a PNM file.
27153
static CImg<T> get_load_pnm(std::FILE *const file) {
27154
return CImg<T>().load_pnm(file);
27157
//! Load an image from a PNM file (in-place).
27158
CImg<T>& load_pnm(const char *const filename) {
27159
return _load_pnm(0,filename);
27162
//! Load an image from a PNM file (in-place).
27163
CImg<T>& load_pnm(std::FILE *const file) {
27164
return _load_pnm(file,0);
27167
// Load an image from a RGB file (internal).
27168
CImg<T>& _load_rgb(std::FILE *const file, const char *const filename, const unsigned int dimw, const unsigned int dimh) {
27169
if (!filename && !file) throw CImgArgumentException("CImg<%s>::load_rgb() : Cannot load (null) filename.",pixel_type());
27170
if (!dimw || !dimh) return assign();
27171
const int cimg_iobuffer = 12*1024*1024;
27172
std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
27173
CImg<unsigned char> raw;
27174
assign(dimw,dimh,1,3);
27176
*ptr_r = ptr(0,0,0,0),
27177
*ptr_g = ptr(0,0,0,1),
27178
*ptr_b = ptr(0,0,0,2);
27179
for (int toread = (int)size(); toread>0; ) {
27180
raw.assign(cimg::min(toread,cimg_iobuffer));
27181
cimg::fread(raw.data,raw.width,nfile);
27183
const unsigned char *ptrs = raw.data;
27184
for (unsigned int off = raw.width/3; off; --off) {
27185
*(ptr_r++) = (T)*(ptrs++);
27186
*(ptr_g++) = (T)*(ptrs++);
27187
*(ptr_b++) = (T)*(ptrs++);
27190
if (!file) cimg::fclose(nfile);
27194
//! Load an image from a RGB file.
27195
static CImg<T> get_load_rgb(const char *const filename, const unsigned int dimw, const unsigned int dimh=1) {
27196
return CImg<T>().load_rgb(filename,dimw,dimh);
27199
//! Load an image from a RGB file.
27200
static CImg<T> get_load_rgb(std::FILE *const file, const unsigned int dimw, const unsigned int dimh=1) {
27201
return CImg<T>().load_rgb(file,dimw,dimh);
27204
//! Load an image from a RGB file (in-place).
27205
CImg<T>& load_rgb(const char *const filename, const unsigned int dimw, const unsigned int dimh=1) {
27206
return _load_rgb(0,filename,dimw,dimh);
27209
//! Load an image from a RGB file (in-place).
27210
CImg<T>& load_rgb(std::FILE *const file, const unsigned int dimw, const unsigned int dimh=1) {
27211
return _load_rgb(file,0,dimw,dimh);
27214
// Load an image from a RGBA file (internal).
27215
CImg<T>& _load_rgba(std::FILE *const file, const char *const filename, const unsigned int dimw, const unsigned int dimh) {
27216
if (!filename && !file) throw CImgArgumentException("CImg<%s>::load_rgba() : Cannot load (null) filename.",pixel_type());
27217
if (!dimw || !dimh) return assign();
27218
const int cimg_iobuffer = 12*1024*1024;
27219
std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
27220
CImg<unsigned char> raw;
27221
assign(dimw,dimh,1,4);
27223
*ptr_r = ptr(0,0,0,0),
27224
*ptr_g = ptr(0,0,0,1),
27225
*ptr_b = ptr(0,0,0,2),
27226
*ptr_a = ptr(0,0,0,3);
27227
for (int toread = (int)size(); toread>0; ) {
27228
raw.assign(cimg::min(toread,cimg_iobuffer));
27229
cimg::fread(raw.data,raw.width,nfile);
27231
const unsigned char *ptrs = raw.data;
27232
for (unsigned int off = raw.width/4; off; --off) {
27233
*(ptr_r++) = (T)*(ptrs++);
27234
*(ptr_g++) = (T)*(ptrs++);
27235
*(ptr_b++) = (T)*(ptrs++);
27236
*(ptr_a++) = (T)*(ptrs++);
27239
if (!file) cimg::fclose(nfile);
27243
//! Load an image from a RGBA file.
27244
static CImg<T> get_load_rgba(const char *const filename, const unsigned int dimw, const unsigned int dimh=1) {
27245
return CImg<T>().load_rgba(filename,dimw,dimh);
27248
//! Load an image from a RGBA file.
27249
static CImg<T> get_load_rgba(std::FILE *const file, const unsigned int dimw, const unsigned int dimh=1) {
27250
return CImg<T>().load_rgba(file,dimw,dimh);
27253
//! Load an image from a RGBA file (in-place).
27254
CImg<T>& load_rgba(const char *const filename, const unsigned int dimw, const unsigned int dimh=1) {
27255
return _load_rgba(0,filename,dimw,dimh);
27258
//! Load an image from a RGBA file (in-place).
27259
CImg<T>& load_rgba(std::FILE *const file, const unsigned int dimw, const unsigned int dimh=1) {
27260
return _load_rgba(file,0,dimw,dimh);
27263
// Load an image from a TIFF file (internal).
19689
27264
// (Original contribution by Jerome Boulanger).
19690
CImg& load_tiff(const char *const filename) {
19691
#ifndef cimg_use_tiff
19692
return load_other(filename);
19694
TIFF *tif = TIFFOpen(filename,"r");
19696
TIFFSetWarningHandler(0);
19697
TIFFSetErrorHandler(0);
19700
unsigned int number_of_directories = 0;
19701
do ++number_of_directories; while (TIFFReadDirectory(tif));
19702
uint16 samplesperpixel, bitspersample;
19704
TIFFGetField(tif,TIFFTAG_IMAGEWIDTH,&nx);
19705
TIFFGetField(tif,TIFFTAG_IMAGELENGTH,&ny);
19706
TIFFGetField(tif,TIFFTAG_SAMPLESPERPIXEL,&samplesperpixel);
19707
if (samplesperpixel!=1 && samplesperpixel!=3 && samplesperpixel!=4) {
19708
cimg::warn("CImg<%s>::load_tiff() : File '%s', unknow value for tag : TIFFTAG_SAMPLESPERPIXEL, will force it to 1.",
19709
pixel_type(),filename?filename:"(FILE*)");
19712
TIFFGetFieldDefaulted(tif, TIFFTAG_BITSPERSAMPLE, &bitspersample);
19714
tif = TIFFOpen(filename,"r");
19715
assign(nx,ny,number_of_directories,samplesperpixel);
19716
unsigned int dir = 0;
19718
if (bitspersample!=8 || !(samplesperpixel == 3 || samplesperpixel == 4)) {
19719
uint16 photo, config;
19720
TIFFGetField(tif,TIFFTAG_PLANARCONFIG,&config);
19721
TIFFGetField(tif,TIFFTAG_PHOTOMETRIC,&photo);
19722
if (TIFFIsTiled(tif)) {
19724
TIFFGetField(tif, TIFFTAG_TILEWIDTH, &tw);
19725
TIFFGetField(tif, TIFFTAG_TILELENGTH, &th);
19726
if (config==PLANARCONFIG_CONTIG) switch(bitspersample) {
19728
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFTileSize(tif));
27265
#ifdef cimg_use_tiff
27266
CImg<T>& _load_tiff(TIFF *tif, const unsigned int directory) {
27267
if (!TIFFSetDirectory(tif,directory)) return assign();
27268
uint16 samplesperpixel, bitspersample;
27270
const char *const filename = TIFFFileName(tif);
27271
TIFFGetField(tif,TIFFTAG_IMAGEWIDTH,&nx);
27272
TIFFGetField(tif,TIFFTAG_IMAGELENGTH,&ny);
27273
TIFFGetField(tif,TIFFTAG_SAMPLESPERPIXEL,&samplesperpixel);
27274
if (samplesperpixel!=1 && samplesperpixel!=3 && samplesperpixel!=4) {
27275
cimg::warn("CImg<%s>::load_tiff() : File '%s', unknow value for tag : TIFFTAG_SAMPLESPERPIXEL, will force it to 1.",
27276
pixel_type(),filename);
27277
samplesperpixel = 1;
27279
TIFFGetFieldDefaulted(tif,TIFFTAG_BITSPERSAMPLE,&bitspersample);
27280
assign(nx,ny,1,samplesperpixel);
27281
if (bitspersample!=8 || !(samplesperpixel==3 || samplesperpixel==4)) {
27282
uint16 photo, config;
27283
TIFFGetField(tif,TIFFTAG_PLANARCONFIG,&config);
27284
TIFFGetField(tif,TIFFTAG_PHOTOMETRIC,&photo);
27285
if (TIFFIsTiled(tif)) {
27287
TIFFGetField(tif,TIFFTAG_TILEWIDTH,&tw);
27288
TIFFGetField(tif,TIFFTAG_TILELENGTH,&th);
27289
if (config==PLANARCONFIG_CONTIG) switch (bitspersample) {
27291
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFTileSize(tif));
27293
for (unsigned int row = 0; row<ny; row+=th)
27294
for (unsigned int col = 0; col<nx; col+=tw) {
27295
if (TIFFReadTile(tif,buf,col,row,0,0)<0) {
27296
_TIFFfree(buf); TIFFClose(tif);
27297
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
27298
pixel_type(),filename);
27300
unsigned char *ptr = buf;
27301
for (unsigned int rr = row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
27302
for (unsigned int cc = col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
27303
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
27304
(*this)(cc,rr,vv) = (T)(float)(ptr[(rr-row)*th*samplesperpixel + (cc-col)*samplesperpixel + vv]);
27311
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFTileSize(tif));
27313
for (unsigned int row = 0; row<ny; row+=th)
27314
for (unsigned int col = 0; col<nx; col+=tw) {
27315
if (TIFFReadTile(tif,buf,col,row,0,0)<0) {
27316
_TIFFfree(buf); TIFFClose(tif);
27317
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
27318
pixel_type(),filename);
27320
unsigned short *ptr = buf;
27321
for (unsigned int rr = row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
27322
for (unsigned int cc = col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
27323
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
27324
(*this)(cc,rr,vv) = (T)(float)(ptr[(rr-row)*th*samplesperpixel + (cc-col)*samplesperpixel + vv]);
27331
float *buf = (float*)_TIFFmalloc(TIFFTileSize(tif));
27333
for (unsigned int row = 0; row<ny; row+=th)
27334
for (unsigned int col = 0; col<nx; col+=tw) {
27335
if (TIFFReadTile(tif,buf,col,row,0,0)<0) {
27336
_TIFFfree(buf); TIFFClose(tif);
27337
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
27338
pixel_type(),filename);
27341
for (unsigned int rr = row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
27342
for (unsigned int cc = col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
27343
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
27344
(*this)(cc,rr,vv) = (T)(float)(ptr[(rr-row)*th*samplesperpixel + (cc-col)*samplesperpixel + vv]);
27350
} else switch (bitspersample) {
27352
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFTileSize(tif));
27354
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
19730
27355
for (unsigned int row = 0; row<ny; row+=th)
19731
27356
for (unsigned int col = 0; col<nx; col+=tw) {
19732
if (TIFFReadTile(tif,buf,col,row,0,0)<0) {
27357
if (TIFFReadTile(tif,buf,col,row,0,vv)<0) {
19733
27358
_TIFFfree(buf); TIFFClose(tif);
19734
27359
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
19735
pixel_type(),filename?filename:"(FILE*)");
27360
pixel_type(),filename);
19737
27362
unsigned char *ptr = buf;
19738
for (unsigned int rr=row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
19739
for (unsigned int cc=col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
19740
for (unsigned int vv=0; vv<samplesperpixel; ++vv) (*this)(cc,rr,dir,vv) = (T)(float)*(ptr++);
27363
for (unsigned int rr = row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
27364
for (unsigned int cc = col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
27365
(*this)(cc,rr,vv) = (T)(float)*(ptr++);
19747
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFTileSize(tif));
27372
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFTileSize(tif));
27374
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
19749
27375
for (unsigned int row = 0; row<ny; row+=th)
19750
27376
for (unsigned int col = 0; col<nx; col+=tw) {
19751
if (TIFFReadTile(tif,buf,col,row,0,0)<0) {
27377
if (TIFFReadTile(tif,buf,col,row,0,vv)<0) {
19752
27378
_TIFFfree(buf); TIFFClose(tif);
19753
27379
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
19754
pixel_type(),filename?filename:"(FILE*)");
27380
pixel_type(),filename);
19756
27382
unsigned short *ptr = buf;
19757
for (unsigned int rr=row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
19758
for (unsigned int cc=col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
19759
for (unsigned int vv=0; vv<samplesperpixel; ++vv) (*this)(cc,rr,dir,vv) = (T)(float)*(ptr++);
27383
for (unsigned int rr = row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
27384
for (unsigned int cc = col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
27385
(*this)(cc,rr,vv) = (T)(float)*(ptr++);
19766
float *buf = (float*)_TIFFmalloc(TIFFTileSize(tif));
27392
float *buf = (float*)_TIFFmalloc(TIFFTileSize(tif));
27394
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
19768
27395
for (unsigned int row = 0; row<ny; row+=th)
19769
27396
for (unsigned int col = 0; col<nx; col+=tw) {
19770
if (TIFFReadTile(tif,buf,col,row,0,0)<0) {
27397
if (TIFFReadTile(tif,buf,col,row,0,vv)<0) {
19771
27398
_TIFFfree(buf); TIFFClose(tif);
19772
27399
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
19773
pixel_type(),filename?filename:"(FILE*)");
27400
pixel_type(),filename);
19775
27402
float *ptr = buf;
19776
for (unsigned int rr=row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
19777
for (unsigned int cc=col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
19778
for (unsigned int vv=0; vv<samplesperpixel; ++vv) (*this)(cc,rr,dir,vv) = (T)(float)*(ptr++);
27403
for (unsigned int rr = row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
27404
for (unsigned int cc = col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
27405
(*this)(cc,rr,vv) = (T)(float)*(ptr++);
19784
} else switch (bitspersample) {
19786
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFTileSize(tif));
19788
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19789
for (unsigned int row = 0; row<ny; row+=th)
19790
for (unsigned int col = 0; col<nx; col+=tw) {
19791
if (TIFFReadTile(tif,buf,col,row,0,vv)<0) {
19792
_TIFFfree(buf); TIFFClose(tif);
19793
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
19794
pixel_type(),filename?filename:"(FILE*)");
19796
unsigned char *ptr = buf;
19797
for (unsigned int rr=row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
19798
for (unsigned int cc=col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
19799
(*this)(cc,rr,dir,vv) = (T)(float)*(ptr++);
19806
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFTileSize(tif));
19808
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19809
for (unsigned int row = 0; row<ny; row+=th)
19810
for (unsigned int col = 0; col<nx; col+=tw) {
19811
if (TIFFReadTile(tif,buf,col,row,0,vv)<0) {
19812
_TIFFfree(buf); TIFFClose(tif);
19813
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
19814
pixel_type(),filename?filename:"(FILE*)");
19816
unsigned short *ptr = buf;
19817
for (unsigned int rr=row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
19818
for (unsigned int cc=col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
19819
(*this)(cc,rr,dir,vv) = (T)(float)*(ptr++);
19826
float *buf = (float*)_TIFFmalloc(TIFFTileSize(tif));
19828
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19829
for (unsigned int row = 0; row<ny; row+=th)
19830
for (unsigned int col = 0; col<nx; col+=tw) {
19831
if (TIFFReadTile(tif,buf,col,row,0,vv)<0) {
19832
_TIFFfree(buf); TIFFClose(tif);
19833
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a tile.",
19834
pixel_type(),filename?filename:"(FILE*)");
19837
for (unsigned int rr=row; rr<cimg::min((unsigned int)(row+th),(unsigned int)ny); ++rr)
19838
for (unsigned int cc=col; cc<cimg::min((unsigned int)(col+tw),(unsigned int)nx); ++cc)
19839
(*this)(cc,rr,dir,vv) = (T)(float)*(ptr++);
19847
if (config==PLANARCONFIG_CONTIG) switch (bitspersample) {
19849
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFStripSize(tif));
19851
uint32 row, rowsperstrip = (uint32)-1;
19852
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27413
if (config==PLANARCONFIG_CONTIG) switch (bitspersample) {
27415
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFStripSize(tif));
27417
uint32 row, rowsperstrip = (uint32)-1;
27418
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27419
for (row = 0; row<ny; row+= rowsperstrip) {
27420
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
27421
tstrip_t strip = TIFFComputeStrip(tif, row, 0);
27422
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
27423
_TIFFfree(buf); TIFFClose(tif);
27424
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a strip.",
27425
pixel_type(),filename);
27427
unsigned char *ptr = buf;
27428
for (unsigned int rr = 0; rr<nrow; ++rr)
27429
for (unsigned int cc = 0; cc<nx; ++cc)
27430
for (unsigned int vv = 0; vv<samplesperpixel; ++vv) (*this)(cc,row+rr,vv) = (T)(float)*(ptr++);
27436
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFStripSize(tif));
27438
uint32 row, rowsperstrip = (uint32)-1;
27439
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27440
for (row = 0; row<ny; row+= rowsperstrip) {
27441
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
27442
tstrip_t strip = TIFFComputeStrip(tif, row, 0);
27443
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
27444
_TIFFfree(buf); TIFFClose(tif);
27445
throw CImgException("CImg<%s>::load_tiff() : File '%s', error while reading a strip.",
27446
pixel_type(),filename);
27448
unsigned short *ptr = buf;
27449
for (unsigned int rr = 0; rr<nrow; ++rr)
27450
for (unsigned int cc = 0; cc<nx; ++cc)
27451
for (unsigned int vv = 0; vv<samplesperpixel; ++vv) (*this)(cc,row+rr,vv) = (T)(float)*(ptr++);
27457
float *buf = (float*)_TIFFmalloc(TIFFStripSize(tif));
27459
uint32 row, rowsperstrip = (uint32)-1;
27460
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27461
for (row = 0; row<ny; row+= rowsperstrip) {
27462
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
27463
tstrip_t strip = TIFFComputeStrip(tif, row, 0);
27464
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
27465
_TIFFfree(buf); TIFFClose(tif);
27466
throw CImgException("CImg<%s>::load_tiff() : File '%s', error while reading a strip.",
27467
pixel_type(),filename);
27470
for (unsigned int rr = 0; rr<nrow; ++rr)
27471
for (unsigned int cc = 0; cc<nx; ++cc)
27472
for (unsigned int vv = 0; vv<samplesperpixel; ++vv) (*this)(cc,row+rr,vv) = (T)(float)*(ptr++);
27477
} else switch (bitspersample){
27479
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFStripSize(tif));
27481
uint32 row, rowsperstrip = (uint32)-1;
27482
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27483
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19853
27484
for (row = 0; row<ny; row+= rowsperstrip) {
19854
27485
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
19855
tstrip_t strip = TIFFComputeStrip(tif, row, 0);
27486
tstrip_t strip = TIFFComputeStrip(tif, row, vv);
19856
27487
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
19857
27488
_TIFFfree(buf); TIFFClose(tif);
19858
27489
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a strip.",
19859
pixel_type(),filename?filename:"(FILE*)");
27490
pixel_type(),filename);
19861
27492
unsigned char *ptr = buf;
19862
for (unsigned int rr=0; rr<nrow; ++rr) for (unsigned int cc=0; cc<nx; ++cc)
19863
for (unsigned int vv=0; vv<samplesperpixel; ++vv) (*this)(cc,row+rr,dir,vv) = (T)(float)*(ptr++);
27493
for (unsigned int rr = 0;rr<nrow; ++rr)
27494
for (unsigned int cc = 0; cc<nx; ++cc)
27495
(*this)(cc,row+rr,vv) = (T)(float)*(ptr++);
19869
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFStripSize(tif));
19871
uint32 row, rowsperstrip = (uint32)-1;
19872
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27501
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFStripSize(tif));
27503
uint32 row, rowsperstrip = (uint32)-1;
27504
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27505
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
19873
27506
for (row = 0; row<ny; row+= rowsperstrip) {
19874
27507
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
19875
tstrip_t strip = TIFFComputeStrip(tif, row, 0);
27508
tstrip_t strip = TIFFComputeStrip(tif, row, vv);
19876
27509
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
19877
27510
_TIFFfree(buf); TIFFClose(tif);
19878
27511
throw CImgException("CImg<%s>::load_tiff() : File '%s', error while reading a strip.",
19879
pixel_type(),filename?filename:"(FILE*)");
27512
pixel_type(),filename);
19881
27514
unsigned short *ptr = buf;
19882
for (unsigned int rr=0; rr<nrow; ++rr) for (unsigned int cc=0; cc<nx; ++cc)
19883
for (unsigned int vv=0; vv<samplesperpixel; ++vv) (*this)(cc,row+rr,dir,vv) = (T)(float)*(ptr++);
27515
for (unsigned int rr = 0; rr<nrow; ++rr)
27516
for (unsigned int cc = 0; cc<nx; ++cc)
27517
(*this)(cc,row+rr,vv) = (T)(float)*(ptr++);
19889
float *buf = (float*)_TIFFmalloc(TIFFStripSize(tif));
19891
uint32 row, rowsperstrip = (uint32)-1;
19892
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27523
float *buf = (float*)_TIFFmalloc(TIFFStripSize(tif));
27525
uint32 row, rowsperstrip = (uint32)-1;
27526
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
27527
for (unsigned int vv = 0; vv<samplesperpixel; ++vv)
19893
27528
for (row = 0; row<ny; row+= rowsperstrip) {
19894
27529
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
19895
tstrip_t strip = TIFFComputeStrip(tif, row, 0);
27530
tstrip_t strip = TIFFComputeStrip(tif, row, vv);
19896
27531
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
19897
27532
_TIFFfree(buf); TIFFClose(tif);
19898
27533
throw CImgException("CImg<%s>::load_tiff() : File '%s', error while reading a strip.",
19899
pixel_type(),filename?filename:"(FILE*)");
27534
pixel_type(),filename);
19901
27536
float *ptr = buf;
19902
for (unsigned int rr=0; rr<nrow; ++rr) for (unsigned int cc=0; cc<nx; ++cc)
19903
for (unsigned int vv=0; vv<samplesperpixel; ++vv) (*this)(cc,row+rr,dir,vv) = (T)(float)*(ptr++);
27537
for (unsigned int rr = 0; rr<nrow; ++rr) for (unsigned int cc = 0; cc<nx; ++cc)
27538
(*this)(cc,row+rr,vv) = (T)(float)*(ptr++);
19908
} else switch(bitspersample){
19910
unsigned char *buf = (unsigned char*)_TIFFmalloc(TIFFStripSize(tif));
19912
uint32 row, rowsperstrip = (uint32)-1;
19913
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
19914
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19915
for (row = 0; row<ny; row+= rowsperstrip) {
19916
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
19917
tstrip_t strip = TIFFComputeStrip(tif, row, vv);
19918
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
19919
_TIFFfree(buf); TIFFClose(tif);
19920
throw CImgException("CImg<%s>::load_tiff() : File '%s', an error occure while reading a strip.",
19921
pixel_type(),filename?filename:"(FILE*)");
19923
unsigned char *ptr = buf;
19924
for (unsigned int rr=0;rr<nrow; ++rr) for (unsigned int cc=0; cc<nx; ++cc)
19925
(*this)(cc,row+rr,dir,vv) = (T)(float)*(ptr++);
19931
unsigned short *buf = (unsigned short*)_TIFFmalloc(TIFFStripSize(tif));
19933
uint32 row, rowsperstrip = (uint32)-1;
19934
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
19935
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19936
for (row = 0; row<ny; row+= rowsperstrip) {
19937
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
19938
tstrip_t strip = TIFFComputeStrip(tif, row, vv);
19939
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
19940
_TIFFfree(buf); TIFFClose(tif);
19941
throw CImgException("CImg<%s>::load_tiff() : File '%s', error while reading a strip.",
19942
pixel_type(),filename?filename:"(FILE*)");
19944
unsigned short *ptr = buf;
19945
for (unsigned int rr=0; rr<nrow; ++rr) for (unsigned int cc=0; cc<nx; ++cc)
19946
(*this)(cc,row+rr,dir,vv) = (T)(float)*(ptr++);
19952
float *buf = (float*)_TIFFmalloc(TIFFStripSize(tif));
19954
uint32 row, rowsperstrip = (uint32)-1;
19955
TIFFGetField(tif,TIFFTAG_ROWSPERSTRIP,&rowsperstrip);
19956
for (unsigned int vv=0; vv<samplesperpixel; ++vv)
19957
for (row = 0; row<ny; row+= rowsperstrip) {
19958
uint32 nrow = (row+rowsperstrip>ny?ny-row:rowsperstrip);
19959
tstrip_t strip = TIFFComputeStrip(tif, row, vv);
19960
if ((TIFFReadEncodedStrip(tif,strip,buf,-1))<0) {
19961
_TIFFfree(buf); TIFFClose(tif);
19962
throw CImgException("CImg<%s>::load_tiff() : File '%s', error while reading a strip.",
19963
pixel_type(),filename?filename:"(FILE*)");
19966
for (unsigned int rr=0; rr<nrow; ++rr) for (unsigned int cc=0; cc<nx; ++cc)
19967
(*this)(cc,row+rr,dir,vv) = (T)(float)*(ptr++);
19975
uint32* raster = (uint32*)_TIFFmalloc(nx * ny * sizeof (uint32));
19977
_TIFFfree(raster); TIFFClose(tif);
19978
throw CImgException("CImg<%s>::load_tiff() : File '%s', not enough memory for buffer allocation.",
19979
pixel_type(),filename?filename:"(FILE*)");
19981
TIFFReadRGBAImage(tif,nx,ny,raster,0);
19982
switch (samplesperpixel) {
19984
cimg_forXY(*this,x,y) (*this)(x,y,dir) = (T)(float)((raster[nx*(ny-1-y)+x]+ 128) / 257);
19987
cimg_forXY(*this,x,y) {
19988
(*this)(x,y,dir,0) = (T)(float)TIFFGetR(raster[nx*(ny-1-y)+x]);
19989
(*this)(x,y,dir,1) = (T)(float)TIFFGetG(raster[nx*(ny-1-y)+x]);
19990
(*this)(x,y,dir,2) = (T)(float)TIFFGetB(raster[nx*(ny-1-y)+x]);
19994
cimg_forXY(*this,x,y) {
19995
(*this)(x,y,dir,0) = (T)(float)TIFFGetR(raster[nx*(ny-1-y)+x]);
19996
(*this)(x,y,dir,1) = (T)(float)TIFFGetG(raster[nx*(ny-1-y)+x]);
19997
(*this)(x,y,dir,2) = (T)(float)TIFFGetB(raster[nx*(ny-1-y)+x]);
19998
(*this)(x,y,dir,3) = (T)(float)TIFFGetA(raster[nx*(ny-1-y)+x]);
20005
} while (TIFFReadDirectory(tif));
27546
uint32* raster = (uint32*)_TIFFmalloc(nx * ny * sizeof (uint32));
27548
_TIFFfree(raster); TIFFClose(tif);
27549
throw CImgException("CImg<%s>::load_tiff() : File '%s', not enough memory for buffer allocation.",
27550
pixel_type(),filename);
27552
TIFFReadRGBAImage(tif,nx,ny,raster,0);
27553
switch (samplesperpixel) {
27555
cimg_forXY(*this,x,y) (*this)(x,y) = (T)(float)((raster[nx*(ny-1-y)+x]+ 128) / 257);
27558
cimg_forXY(*this,x,y) {
27559
(*this)(x,y,0) = (T)(float)TIFFGetR(raster[nx*(ny-1-y)+x]);
27560
(*this)(x,y,1) = (T)(float)TIFFGetG(raster[nx*(ny-1-y)+x]);
27561
(*this)(x,y,2) = (T)(float)TIFFGetB(raster[nx*(ny-1-y)+x]);
27565
cimg_forXY(*this,x,y) {
27566
(*this)(x,y,0) = (T)(float)TIFFGetR(raster[nx*(ny-1-y)+x]);
27567
(*this)(x,y,1) = (T)(float)TIFFGetG(raster[nx*(ny-1-y)+x]);
27568
(*this)(x,y,2) = (T)(float)TIFFGetB(raster[nx*(ny-1-y)+x]);
27569
(*this)(x,y,3) = (T)(float)TIFFGetA(raster[nx*(ny-1-y)+x]);
27579
//! Load an image from a TIFF file.
27580
static CImg<T> get_load_tiff(const char *const filename,
27581
const unsigned int first_frame=0, const unsigned int last_frame=~0U,
27582
const unsigned int step_frame=1) {
27583
return CImg<T>().load_tiff(filename,first_frame,last_frame,step_frame);
27586
//! Load an image from a TIFF file (in-place).
27587
CImg<T>& load_tiff(const char *const filename,
27588
const unsigned int first_frame=0, const unsigned int last_frame=~0U,
27589
const unsigned int step_frame=1) {
27590
if (!filename) throw CImgArgumentException("CImg<%s>::load_tiff() : Cannot load (null) filename.",pixel_type());
27592
nfirst_frame = first_frame<last_frame?first_frame:last_frame,
27593
nstep_frame = step_frame?step_frame:1;
27594
unsigned int nlast_frame = first_frame<last_frame?last_frame:first_frame;
27596
#ifndef cimg_use_tiff
27597
if (nfirst_frame || nlast_frame!=~0U || nstep_frame>1)
27598
throw CImgArgumentException("CImg<%s>::load_tiff() : File '%s', reading sub-images from a tiff file requires the use of libtiff.\n"
27599
"('cimg_use_tiff' must be defined).",pixel_type(),filename);
27600
return load_other(filename);
27602
TIFF *tif = TIFFOpen(filename,"r");
27604
unsigned int nb_images = 0;
27605
do ++nb_images; while (TIFFReadDirectory(tif));
27606
if (nfirst_frame>=nb_images || (nlast_frame!=~0U && nlast_frame>=nb_images))
27607
cimg::warn("CImg<%s>::load_tiff() : File '%s' contains %u image(s), specified frame range is [%u,%u] (step %u).",
27608
pixel_type(),filename,nb_images,nfirst_frame,nlast_frame,nstep_frame);
27609
if (nfirst_frame>=nb_images) return assign();
27610
if (nlast_frame>=nb_images) nlast_frame = nb_images-1;
27611
TIFFSetDirectory(tif,0);
27613
for (unsigned int l = nfirst_frame; l<=nlast_frame; l+=nstep_frame) {
27614
frame._load_tiff(tif,l);
27615
if (l==nfirst_frame) assign(frame.width,frame.height,1+(nlast_frame-nfirst_frame)/nstep_frame,frame.dim);
27616
if (frame.width>width || frame.height>height || frame.dim>dim)
27617
resize(cimg::max(frame.width,width),cimg::max(frame.height,height),-100,cimg::max(frame.dim,dim),0);
27618
draw_image(frame,0,0,(l-nfirst_frame)/nstep_frame,0);
20006
27620
TIFFClose(tif);
20007
} else throw CImgException("CImg<%s>::load_tiff() : File '%s', error while loading the image.",
20008
pixel_type(),filename?filename:"(FILE*)");
27621
} else throw CImgException("CImg<%s>::load_tiff() : File '%s', cannot open file.",pixel_type(),filename);
20009
27622
return *this;
20013
//! Load an image from a TIFF file.
20014
static CImg get_load_tiff(const char *const filename) {
20015
return CImg<T>().load_tiff(filename);
27626
//! Load an image from an ANALYZE7.5/NIFTI file.
27627
static CImg<T> get_load_analyze(const char *const filename, float *const voxsize=0) {
27628
return CImg<T>().load_analyze(filename,voxsize);
20018
//! Load an image from a JPEG file.
20019
CImg& load_jpeg(std::FILE *const file, const char *const filename=0) {
20020
#ifndef cimg_use_jpeg
20022
throw CImgIOException("CImg<%s>::load_jpeg() : File '(FILE*)' cannot be read without using libjpeg.",
20024
else return load_other(filename);
20026
struct jpeg_decompress_struct cinfo;
20027
struct jpeg_error_mgr jerr;
20028
std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
20030
cinfo.err = jpeg_std_error(&jerr);
20031
jpeg_create_decompress(&cinfo);
20032
jpeg_stdio_src(&cinfo,nfile);
20033
jpeg_read_header(&cinfo,TRUE);
20034
jpeg_start_decompress(&cinfo);
20036
if (cinfo.output_components!=1 && cinfo.output_components!=3 && cinfo.output_components!=4) {
20037
cimg::warn("CImg<%s>::load_jpeg() : Don't know how to read image '%s' with libpeg, trying ImageMagick's convert",
20038
pixel_type(),filename?filename:"(unknown)");
20039
if (!file) return load_other(filename);
20041
if (!file) cimg::fclose(nfile);
20042
throw CImgIOException("CImg<%s>::load_jpeg() : Cannot read JPEG image '%s' using a *FILE input.",
20043
pixel_type(),filename?filename:"(FILE*)");
20047
const unsigned int row_stride = cinfo.output_width * cinfo.output_components;
20048
unsigned char *buf = new unsigned char[cinfo.output_width*cinfo.output_height*cinfo.output_components], *buf2 = buf;
20049
JSAMPROW row_pointer[1];
20050
while (cinfo.output_scanline < cinfo.output_height) {
20051
row_pointer[0] = &buf[cinfo.output_scanline*row_stride];
20052
jpeg_read_scanlines(&cinfo,row_pointer,1);
20054
jpeg_finish_decompress(&cinfo);
20055
jpeg_destroy_decompress(&cinfo);
20056
if (!file) cimg::fclose(nfile);
20058
assign(cinfo.output_width,cinfo.output_height,1,cinfo.output_components);
20062
cimg_forXY(*this,x,y) *(ptr_g++) = (T)*(buf2++);
20065
T *ptr_r = ptr(0,0,0,0), *ptr_g = ptr(0,0,0,1), *ptr_b = ptr(0,0,0,2);
20066
cimg_forXY(*this,x,y) {
20067
*(ptr_r++) = (T)*(buf2++);
20068
*(ptr_g++) = (T)*(buf2++);
20069
*(ptr_b++) = (T)*(buf2++);
27631
//! Load an image from an ANALYZE7.5/NIFTI file (in-place).
27632
CImg<T>& load_analyze(const char *const filename, float *const voxsize=0) {
27633
if (!filename) throw CImgArgumentException("CImg<%s>::load_analyze() : Cannot load (null) filename.",pixel_type());
27634
std::FILE *file_header = 0, *file = 0;
27635
bool error_file = false;
27637
const char *ext = cimg::split_filename(filename,body);
27638
if (!cimg::strncasecmp(ext,"nii",3)) file_header = cimg::fopen(filename,"rb");
27640
if (!cimg::strncasecmp(ext,"hdr",3) ||
27641
!cimg::strncasecmp(ext,"img",3)) {
27642
std::sprintf(body+cimg::strlen(body),".hdr");
27643
file_header = cimg::fopen(body,"rb");
27644
if (!file_header) error_file = true;
27646
std::sprintf(body+cimg::strlen(body)-3,"img");
27647
file = cimg::fopen(body,"rb");
27648
if (!file) { cimg::fclose(file_header); error_file = true; }
27652
if (error_file) throw CImgIOException("CImg<%s>::load_analyze() : Filename '%s', not recognized as an Analyze 7.5 or NIFTI file.",
27653
pixel_type(),filename);
27656
bool endian = false;
27657
unsigned int header_size;
27658
cimg::fread(&header_size,1,file_header);
27659
if (header_size>=4096) { endian = true; cimg::invert_endianness(header_size); }
27660
unsigned char *header = new unsigned char[header_size];
27661
cimg::fread(header+4,header_size-4,file_header);
27662
if (file) cimg::fclose(file_header);
27664
cimg::invert_endianness((short*)(header+40),5);
27665
cimg::invert_endianness((short*)(header+70),1);
27666
cimg::invert_endianness((short*)(header+72),1);
27667
cimg::invert_endianness((float*)(header+76),4);
27668
cimg::invert_endianness((float*)(header+112),1);
27670
unsigned short *dim = (unsigned short*)(header+40), dimx=1, dimy=1, dimz=1, dimv=1;
27671
if (!dim[0]) cimg::warn("CImg<%s>::load_analyze() : Specified image has zero dimensions.",pixel_type());
27672
if (dim[0]>4) cimg::warn("CImg<%s>::load_analyze() : Number of image dimension is %d, reading only the 4 first dimensions",
27673
pixel_type(),dim[0]);
27674
if (dim[0]>=1) dimx = dim[1];
27675
if (dim[0]>=2) dimy = dim[2];
27676
if (dim[0]>=3) dimz = dim[3];
27677
if (dim[0]>=4) dimv = dim[4];
27679
float scalefactor = *(float*)(header+112); if (scalefactor==0) scalefactor=1;
27680
const unsigned short datatype = *(short*)(header+70);
27681
if (voxsize) { const float *vsize = (float*)(header+76); voxsize[0] = vsize[1]; voxsize[1] = vsize[2]; voxsize[2] = vsize[3]; }
27685
std::FILE *nfile = file?file:file_header;
27686
assign(dimx,dimy,dimz,dimv);
27687
switch (datatype) {
27689
unsigned char *buffer = new unsigned char[dimx*dimy*dimz*dimv];
27690
cimg::fread(buffer,dimx*dimy*dimz*dimv,nfile);
27691
cimg_foroff(*this,off) data[off] = (T)(buffer[off]*scalefactor);
20073
T *ptr_r = ptr(0,0,0,0), *ptr_g = ptr(0,0,0,1),
20074
*ptr_b = ptr(0,0,0,2), *ptr_a = ptr(0,0,0,3);
20075
cimg_forXY(*this,x,y) {
20076
*(ptr_r++) = (T)*(buf2++);
20077
*(ptr_g++) = (T)*(buf2++);
20078
*(ptr_b++) = (T)*(buf2++);
20079
*(ptr_a++) = (T)*(buf2++);
20088
//! Load an image from a JPEG file.
20089
CImg& load_jpeg(const char *const filename) {
20090
return load_jpeg(0,filename);
20093
//! Load an image from a JPEG file.
20094
static CImg get_load_jpeg(std::FILE *const file, const char *const filename=0) {
20095
return CImg<T>().load_jpeg(file,filename);
20098
//! Load an image from a JPEG file.
20099
static CImg get_load_jpeg(const char *const filename) {
20100
return CImg<T>().load_jpeg(0,filename);
20103
//! Load an image using builtin ImageMagick++ Library.
20105
Added April/may 2006 by Christoph Hormann <chris_hormann@gmx.de>
20106
This is experimental code, not much tested, use with care.
20108
CImg& load_magick(const char *const filename) {
20109
#ifdef cimg_use_magick
20110
Magick::Image image(filename);
20111
const unsigned int W = image.size().width(), H = image.size().height();
20112
switch (image.type()) {
20113
case Magick::PaletteMatteType:
20114
case Magick::TrueColorMatteType:
20115
case Magick::ColorSeparationType: {
20117
T *rdata = ptr(0,0,0,0), *gdata = ptr(0,0,0,1), *bdata = ptr(0,0,0,2), *adata = ptr(0,0,0,3);
20118
Magick::PixelPacket *pixels = image.getPixels(0,0,W,H);
20119
for (unsigned int off = W*H; off; --off) {
20120
*(rdata++) = (T)(pixels->red);
20121
*(gdata++) = (T)(pixels->green);
20122
*(bdata++) = (T)(pixels->blue);
20123
*(adata++) = (T)(pixels->opacity);
20127
case Magick::PaletteType:
20128
case Magick::TrueColorType: {
20130
T *rdata = ptr(0,0,0,0), *gdata = ptr(0,0,0,1), *bdata = ptr(0,0,0,2);
20131
Magick::PixelPacket *pixels = image.getPixels(0,0,W,H);
20132
for (unsigned int off = W*H; off; --off) {
20133
*(rdata++) = (T)(pixels->red);
20134
*(gdata++) = (T)(pixels->green);
20135
*(bdata++) = (T)(pixels->blue);
20139
case Magick::GrayscaleMatteType: {
20141
T *data = ptr(0,0,0,0), *adata = ptr(0,0,0,1);
20142
Magick::PixelPacket *pixels = image.getPixels(0,0,W,H);
20143
for (unsigned int off = W*H; off; --off) {
20144
*(data++) = (T)(pixels->red);
20145
*(adata++) = (T)(pixels->opacity);
20151
T *data = ptr(0,0,0,0);
20152
Magick::PixelPacket *pixels = image.getPixels(0,0,W,H);
20153
for (unsigned int off = W*H; off; --off) {
20154
*(data++) = (T)(pixels->red);
20160
throw CImgIOException("CImg<%s>::load_magick() : File '%s', Magick++ has not been linked during compilation.",
20161
pixel_type(),filename?filename:"(null)");
20166
//! Load an image using builtin ImageMagick++ Library.
20167
static CImg get_load_magick(const char *const filename) {
20168
return CImg<T>().load_magick(filename);
20171
//! Load an image from a .RAW file.
20172
CImg& load_raw(std::FILE *const file, const char *const filename,
20173
const unsigned int sizex, const unsigned int sizey=1,
20174
const unsigned int sizez=1, const unsigned int sizev=1,
20175
const bool multiplexed = false, const bool endian_swap = false) {
20176
assign(sizex,sizey,sizez,sizev,0);
20177
const unsigned int siz = size();
20179
std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
20180
if (!multiplexed) {
20181
cimg::fread(ptr(),siz,nfile);
20182
if (endian_swap) cimg::endian_swap(ptr(),siz);
20185
CImg<T> buf(1,1,1,sizev);
20186
cimg_forXYZ(*this,x,y,z) {
20187
cimg::fread(buf.ptr(),sizev,nfile);
20188
if (endian_swap) cimg::endian_swap(buf.ptr(),sizev);
20189
set_vector_at(buf,x,y,z); }
20191
if (!file) cimg::fclose(nfile);
20196
//! Load an image from a .RAW file.
20197
CImg& load_raw(const char *const filename,
20198
const unsigned int sizex, const unsigned int sizey=1,
20199
const unsigned int sizez=1, const unsigned int sizev=1,
20200
const bool multiplexed = false, const bool endian_swap = false) {
20201
return load_raw(0,filename,sizex,sizey,sizez,sizev,multiplexed,endian_swap);
20204
//! Load an image from a RAW file.
20205
static CImg get_load_raw(std::FILE *const file, const char *const filename,
20206
const unsigned int sizex, const unsigned int sizey=1,
20207
const unsigned int sizez=1, const unsigned int sizev=1,
20208
const bool multiplexed=false, const bool endian_swap=false) {
20209
return CImg<T>().load_raw(file,filename,sizex,sizey,sizez,sizev,multiplexed,endian_swap);
20212
//! Load an image from a RAW file.
20213
static CImg get_load_raw(const char *const filename,
20214
const unsigned int sizex, const unsigned int sizey=1,
20215
const unsigned int sizez=1, const unsigned int sizev=1,
20216
const bool multiplexed = false, const bool endian_swap = false) {
20217
return CImg<T>().load_raw(0,filename,sizex,sizey,sizez,sizev,multiplexed,endian_swap);
20220
//! Load an image from a RGBA file.
20221
CImg& load_rgba(std::FILE *const file, const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20222
const int cimg_iobuffer = 12*1024*1024;
20223
std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
20224
CImg<unsigned char> raw;
20225
assign(dimw,dimh,1,4);
20227
*ptr_r = ptr(0,0,0,0),
20228
*ptr_g = ptr(0,0,0,1),
20229
*ptr_b = ptr(0,0,0,2),
20230
*ptr_a = ptr(0,0,0,3);
20231
for (int toread = (int)size(); toread>0; ) {
20232
raw.assign(cimg::min(toread,cimg_iobuffer));
20233
cimg::fread(raw.data,raw.width,nfile);
20235
const unsigned char *ptrs = raw.ptr();
20236
for (unsigned int off = raw.width/4; off; --off) {
20237
*(ptr_r++) = (T)*(ptrs++);
20238
*(ptr_g++) = (T)*(ptrs++);
20239
*(ptr_b++) = (T)*(ptrs++);
20240
*(ptr_a++) = (T)*(ptrs++);
20243
if (!file) cimg::fclose(nfile);
20247
//! Load an image from a RGBA file.
20248
CImg& load_rgba(const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20249
return load_rgba(0,filename,dimw,dimh);
20252
//! Load an image from a RGBA file.
20253
static CImg get_load_rgba(std::FILE *const file, const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20254
return CImg<T>().load_rgba(file,filename,dimw,dimh);
20257
//! Load an image from a RGBA file.
20258
static CImg get_load_rgba(const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20259
return CImg<T>().load_rgba(0,filename,dimw,dimh);
20262
//! Load an image from a RGB file.
20263
CImg& load_rgb(std::FILE *const file, const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20264
const int cimg_iobuffer = 12*1024*1024;
20265
std::FILE *const nfile = file?file:cimg::fopen(filename,"rb");
20266
CImg<unsigned char> raw;
20267
assign(dimw,dimh,1,3);
20269
*ptr_r = ptr(0,0,0,0),
20270
*ptr_g = ptr(0,0,0,1),
20271
*ptr_b = ptr(0,0,0,2);
20272
for (int toread = (int)size(); toread>0; ) {
20273
raw.assign(cimg::min(toread,cimg_iobuffer));
20274
cimg::fread(raw.data,raw.width,nfile);
20276
const unsigned char *ptrs = raw.ptr();
20277
for (unsigned int off = raw.width/3; off; --off) {
20278
*(ptr_r++) = (T)*(ptrs++);
20279
*(ptr_g++) = (T)*(ptrs++);
20280
*(ptr_b++) = (T)*(ptrs++);
20283
if (!file) cimg::fclose(nfile);
20287
//! Load an image from a RGB file.
20288
CImg& load_rgb(const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20289
return load_rgb(0,filename,dimw,dimh);
20292
//! Load an image from a RGB file.
20293
static CImg get_load_rgb(std::FILE *const file, const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20294
return CImg<T>().load_rgb(file,filename,dimw,dimh);
20297
//! Load an image from a RGB file.
20298
static CImg get_load_rgb(const char *const filename, const unsigned int dimw, const unsigned int dimh) {
20299
return CImg<T>().load_rgb(0,filename,dimw,dimh);
20302
static void _load_inr(std::FILE *file, int out[8], float *const voxsize=0) {
20304
#define cimg_load_inr_case(Tf,sign,pixsize,Ts) \
20305
if (!loaded && fopt[6]==pixsize && fopt[4]==Tf && fopt[5]==sign) { \
20306
Ts *xval, *val = new Ts[fopt[0]*fopt[3]]; \
20307
cimg_forYZ(*this,y,z) { \
20308
cimg::fread(val,fopt[0]*fopt[3],nfile); \
20309
if (fopt[7]!=endian) cimg::endian_swap(val,fopt[0]*fopt[3]); \
20310
xval = val; cimg_forX(*this,x) cimg_forV(*this,k) (*this)(x,y,z,k) = (T)*(xval++); \
27695
short *buffer = new short[dimx*dimy*dimz*dimv];
27696
cimg::fread(buffer,dimx*dimy*dimz*dimv,nfile);
27697
if (endian) cimg::invert_endianness(buffer,dimx*dimy*dimz*dimv);
27698
cimg_foroff(*this,off) data[off] = (T)(buffer[off]*scalefactor);
27702
int *buffer = new int[dimx*dimy*dimz*dimv];
27703
cimg::fread(buffer,dimx*dimy*dimz*dimv,nfile);
27704
if (endian) cimg::invert_endianness(buffer,dimx*dimy*dimz*dimv);
27705
cimg_foroff(*this,off) data[off] = (T)(buffer[off]*scalefactor);
27709
float *buffer = new float[dimx*dimy*dimz*dimv];
27710
cimg::fread(buffer,dimx*dimy*dimz*dimv,nfile);
27711
if (endian) cimg::invert_endianness(buffer,dimx*dimy*dimz*dimv);
27712
cimg_foroff(*this,off) data[off] = (T)(buffer[off]*scalefactor);
27716
double *buffer = new double[dimx*dimy*dimz*dimv];
27717
cimg::fread(buffer,dimx*dimy*dimz*dimv,nfile);
27718
if (endian) cimg::invert_endianness(buffer,dimx*dimy*dimz*dimv);
27719
cimg_foroff(*this,off) data[off] = (T)(buffer[off]*scalefactor);
27723
cimg::fclose(nfile);
27724
throw CImgIOException("CImg<%s>::load_analyze() : File '%s, cannot read images with 'datatype = %d'",
27725
pixel_type(),filename,datatype);
27727
cimg::fclose(nfile);
27731
//! Load an image (list) from a .cimg file.
27732
static CImg<T> get_load_cimg(const char *const filename, const char axis='z', const char align='p') {
27733
return CImg<T>().load_cimg(filename,axis,align);
27736
//! Load an image (list) from a .cimg file.
27737
static CImg<T> get_load_cimg(std::FILE *const file, const char axis='z', const char align='p') {
27738
return CImg<T>().load_cimg(file,axis,align);
27741
//! Load an image (list) from a .cimg file (in-place).
27742
CImg<T>& load_cimg(const char *const filename, const char axis='z', const char align='p') {
27744
list.load_cimg(filename);
27745
if (list.size==1) return list[0].transfer_to(*this);
27746
return assign(list.get_append(axis,align));
27749
//! Load an image (list) from a .cimg file (in-place).
27750
CImg<T>& load_cimg(std::FILE *const file, const char axis='z', const char align='p') {
27752
list.load_cimg(file);
27753
if (list.size==1) return list[0].transfer_to(*this);
27754
return assign(list.get_append(axis,align));
27757
//! Load a sub-image (list) from a .cimg file.
27758
static CImg<T> get_load_cimg(const char *const filename,
27759
const unsigned int n0, const unsigned int n1,
27760
const unsigned int x0, const unsigned int y0, const unsigned int z0, const unsigned int v0,
27761
const unsigned int x1, const unsigned int y1, const unsigned int z1, const unsigned int v1,
27762
const char axis='z', const char align='p') {
27763
return CImg<T>().load_cimg(filename,n0,n1,x0,y0,z0,v0,x1,y1,z1,v1,axis,align);
27766
//! Load a sub-image (list) from a non-compressed .cimg file.
27767
static CImg<T> get_load_cimg(std::FILE *const file,
27768
const unsigned int n0, const unsigned int n1,
27769
const unsigned int x0, const unsigned int y0, const unsigned int z0, const unsigned int v0,
27770
const unsigned int x1, const unsigned int y1, const unsigned int z1, const unsigned int v1,
27771
const char axis='z', const char align='p') {
27772
return CImg<T>().load_cimg(file,n0,n1,x0,y0,z0,v0,x1,y1,z1,v1,axis,align);
27775
//! Load a sub-image (list) from a non-compressed .cimg file (in-place).
27776
CImg<T>& load_cimg(const char *const filename,
27777
const unsigned int n0, const unsigned int n1,
27778
const unsigned int x0, const unsigned int y0, const unsigned int z0, const unsigned int v0,
27779
const unsigned int x1, const unsigned int y1, const unsigned int z1, const unsigned int v1,
27780
const char axis='z', const char align='p') {
27782
list.load_cimg(filename,n0,n1,x0,y0,z0,v0,x1,y1,z1,v1);
27783
if (list.size==1) return list[0].transfer_to(*this);
27784
return assign(list.get_append(axis,align));
27787
//! Load a sub-image (list) from a non-compressed .cimg file (in-place).
27788
CImg<T>& load_cimg(std::FILE *const file,
27789
const unsigned int n0, const unsigned int n1,
27790
const unsigned int x0, const unsigned int y0, const unsigned int z0, const unsigned int v0,
27791
const unsigned int x1, const unsigned int y1, const unsigned int z1, const unsigned int v1,
27792
const char axis='z', const char align='p') {
27794
list.load_cimg(file,n0,n1,x0,y0,z0,v0,x1,y1,z1,v1);
27795
if (list.size==1) return list[0].transfer_to(*this);
27796
return assign(list.get_append(axis,align));
27799
// Load an image from an INRIMAGE-4 file (internal).
27800
static void _load_inr_header(std::FILE *file, int out[8], float *const voxsize) {
20316
27801
char item[1024], tmp1[64], tmp2[64];
20317
27802
out[0] = out[1] = out[2] = out[3] = out[5] = 1; out[4] = out[6] = out[7] = -1;
20318
27803
std::fscanf(file,"%63s",item);