Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
path: root/Imaging/libImaging/Chops.c
blob: fdd13fdf354d24f2e1f94e15696eef3b3ba310cf (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
/* 
 * The Python Imaging Library
 * $Id: Chops.c 2506 2005-09-10 14:52:13Z Fredrik $
 *
 * basic channel operations
 *
 * history:
 * 1996-03-28 fl   Created
 * 1996-08-13 fl   Added and/or/xor for "1" images
 * 1996-12-14 fl   Added add_modulo, sub_modulo
 * 2005-09-10 fl   Fixed output values from and/or/xor
 *
 * Copyright (c) 1996 by Fredrik Lundh.
 * Copyright (c) 1997 by Secret Labs AB.
 *
 * See the README file for details on usage and redistribution.
 */


#include "Imaging.h"

#define	CHOP(operation, mode)\
    int x, y;\
    Imaging imOut;\
    imOut = create(imIn1, imIn2, mode);\
    if (!imOut)\
	return NULL;\
    for (y = 0; y < imOut->ysize; y++) {\
	UINT8* out = (UINT8*) imOut->image[y];\
	UINT8* in1 = (UINT8*) imIn1->image[y];\
	UINT8* in2 = (UINT8*) imIn2->image[y];\
	for (x = 0; x < imOut->linesize; x++) {\
	    int temp = operation;\
	    if (temp <= 0)\
		out[x] = 0;\
	    else if (temp >= 255)\
		out[x] = 255;\
	    else\
		out[x] = temp;\
	}\
    }\
    return imOut;

#define	CHOP2(operation, mode)\
    int x, y;\
    Imaging imOut;\
    imOut = create(imIn1, imIn2, mode);\
    if (!imOut)\
	return NULL;\
    for (y = 0; y < imOut->ysize; y++) {\
	UINT8* out = (UINT8*) imOut->image[y];\
	UINT8* in1 = (UINT8*) imIn1->image[y];\
	UINT8* in2 = (UINT8*) imIn2->image[y];\
	for (x = 0; x < imOut->linesize; x++) {\
	    out[x] = operation;\
	}\
    }\
    return imOut;

static Imaging
create(Imaging im1, Imaging im2, char* mode)
{
    int xsize, ysize;

    if (!im1 || !im2 || im1->type != IMAGING_TYPE_UINT8 ||
        (mode != NULL && (strcmp(im1->mode, "1") || strcmp(im2->mode, "1"))))
	return (Imaging) ImagingError_ModeError();
    if (im1->type  != im2->type  ||
        im1->bands != im2->bands)
	return (Imaging) ImagingError_Mismatch();

    xsize = (im1->xsize < im2->xsize) ? im1->xsize : im2->xsize;
    ysize = (im1->ysize < im2->ysize) ? im1->ysize : im2->ysize;

    return ImagingNew(im1->mode, xsize, ysize);
}

Imaging
ImagingChopLighter(Imaging imIn1, Imaging imIn2)
{
    CHOP((in1[x] > in2[x]) ? in1[x] : in2[x], NULL);
}

Imaging
ImagingChopDarker(Imaging imIn1, Imaging imIn2)
{
    CHOP((in1[x] < in2[x]) ? in1[x] : in2[x], NULL);
}

Imaging
ImagingChopDifference(Imaging imIn1, Imaging imIn2)
{
    CHOP(abs((int) in1[x] - (int) in2[x]), NULL);
}

Imaging
ImagingChopMultiply(Imaging imIn1, Imaging imIn2)
{
    CHOP((int) in1[x] * (int) in2[x] / 255, NULL);
}

Imaging
ImagingChopScreen(Imaging imIn1, Imaging imIn2)
{
    CHOP(255 - ((int) (255 - in1[x]) * (int) (255 - in2[x])) / 255, NULL);
}

Imaging
ImagingChopAdd(Imaging imIn1, Imaging imIn2, float scale, int offset)
{
    CHOP(((int) in1[x] + (int) in2[x]) / scale + offset, NULL);
}

Imaging
ImagingChopSubtract(Imaging imIn1, Imaging imIn2, float scale, int offset)
{
    CHOP(((int) in1[x] - (int) in2[x]) / scale + offset, NULL);
}

Imaging
ImagingChopAnd(Imaging imIn1, Imaging imIn2)
{
    CHOP2((in1[x] && in2[x]) ? 255 : 0, "1");
}

Imaging
ImagingChopOr(Imaging imIn1, Imaging imIn2)
{
    CHOP2((in1[x] || in2[x]) ? 255 : 0, "1");
}

Imaging
ImagingChopXor(Imaging imIn1, Imaging imIn2)
{
    CHOP2(((in1[x] != 0) ^ (in2[x] != 0)) ? 255 : 0, "1");
}

Imaging
ImagingChopAddModulo(Imaging imIn1, Imaging imIn2)
{
    CHOP2(in1[x] + in2[x], NULL);
}

Imaging
ImagingChopSubtractModulo(Imaging imIn1, Imaging imIn2)
{
    CHOP2(in1[x] - in2[x], NULL);
}