source: libpipi/trunk/pipi/filter/dilate.c @ 2902

Last change on this file since 2902 was 2902, checked in by Sam Hocevar, 12 years ago

Support C99 types on Win32 through the same hacks as in libcaca.

File size: 4.9 KB
Line 
1/*
2 *  libpipi       Pathetic image processing interface library
3 *  Copyright (c) 2004-2008 Sam Hocevar <sam@zoy.org>
4 *                All Rights Reserved
5 *
6 *  $Id$
7 *
8 *  This library is free software. It comes without any warranty, to
9 *  the extent permitted by applicable law. You can redistribute it
10 *  and/or modify it under the terms of the Do What The Fuck You Want
11 *  To Public License, Version 2, as published by Sam Hocevar. See
12 *  http://sam.zoy.org/wtfpl/COPYING for more details.
13 */
14
15/*
16 * dilate.c: dilate and erode functions
17 */
18
19#include "config.h"
20
21#include <stdlib.h>
22#include <stdio.h>
23#include <string.h>
24#include <math.h>
25
26#include "pipi.h"
27#include "pipi_internals.h"
28
29/* FIXME: these functions are almost the same, try to merge them
30 * somewhat efficiently. */
31/* TODO: - dilate by k (Manhattan distance)
32 *       - dilate by r (euclidian distance, with non-integer r) */
33pipi_image_t *pipi_dilate(pipi_image_t *src)
34{
35    pipi_image_t *dst;
36    pipi_pixels_t *srcp, *dstp;
37    float *srcdata, *dstdata;
38    int x, y, w, h, i, gray;
39
40    w = src->w;
41    h = src->h;
42
43    gray = (src->last_modified == PIPI_PIXELS_Y_F);
44
45    srcp = gray ? pipi_getpixels(src, PIPI_PIXELS_Y_F)
46                : pipi_getpixels(src, PIPI_PIXELS_RGBA_F);
47    srcdata = (float *)srcp->pixels;
48
49    dst = pipi_new(w, h);
50    dstp = gray ? pipi_getpixels(dst, PIPI_PIXELS_Y_F)
51                : pipi_getpixels(dst, PIPI_PIXELS_RGBA_F);
52    dstdata = (float *)dstp->pixels;
53
54    for(y = 0; y < h; y++)
55    {
56        for(x = 0; x < w; x++)
57        {
58            double t;
59            int x2, y2, x3, y3;
60
61            y2 = y - 1;
62            if(y2 < 0) y2 = h - 1;
63            y3 = y + 1;
64            if(y3 >= h) y3 = 0;
65
66            x2 = x - 1;
67            if(x2 < 0) x2 = w - 1;
68            x3 = x + 1;
69            if(x3 >= w) x3 = 0;
70
71            if(gray)
72            {
73                t = srcdata[y * w + x];
74                if(srcdata[y2 * w + x] > t) t = srcdata[y2 * w + x];
75                if(srcdata[y3 * w + x] > t) t = srcdata[y3 * w + x];
76                if(srcdata[y * w + x2] > t) t = srcdata[y * w + x2];
77                if(srcdata[y * w + x3] > t) t = srcdata[y * w + x3];
78                dstdata[y * w + x] = t;
79            }
80            else
81            {
82                for(i = 0; i < 4; i++)
83                {
84                    t = srcdata[4 * (y * w + x) + i];
85                    if(srcdata[4 * (y2 * w + x) + i] > t)
86                        t = srcdata[4 * (y2 * w + x) + i];
87                    if(srcdata[4 * (y3 * w + x) + i] > t)
88                        t = srcdata[4 * (y3 * w + x) + i];
89                    if(srcdata[4 * (y * w + x2) + i] > t)
90                        t = srcdata[4 * (y * w + x2) + i];
91                    if(srcdata[4 * (y * w + x3) + i] > t)
92                        t = srcdata[4 * (y * w + x3) + i];
93                    dstdata[4 * (y * w + x) + i] = t;
94                }
95            }
96        }
97    }
98
99    return dst;
100}
101
102pipi_image_t *pipi_erode(pipi_image_t *src)
103{
104    pipi_image_t *dst;
105    pipi_pixels_t *srcp, *dstp;
106    float *srcdata, *dstdata;
107    int x, y, w, h, i, gray;
108
109    w = src->w;
110    h = src->h;
111
112    gray = (src->last_modified == PIPI_PIXELS_Y_F);
113
114    srcp = gray ? pipi_getpixels(src, PIPI_PIXELS_Y_F)
115                : pipi_getpixels(src, PIPI_PIXELS_RGBA_F);
116    srcdata = (float *)srcp->pixels;
117
118    dst = pipi_new(w, h);
119    dstp = gray ? pipi_getpixels(dst, PIPI_PIXELS_Y_F)
120                : pipi_getpixels(dst, PIPI_PIXELS_RGBA_F);
121    dstdata = (float *)dstp->pixels;
122
123    for(y = 0; y < h; y++)
124    {
125        for(x = 0; x < w; x++)
126        {
127            double t;
128            int x2, y2, x3, y3;
129
130            y2 = y - 1;
131            if(y2 < 0) y2 = h - 1;
132            y3 = y + 1;
133            if(y3 >= h) y3 = 0;
134
135            x2 = x - 1;
136            if(x2 < 0) x2 = w - 1;
137            x3 = x + 1;
138            if(x3 >= w) x3 = 0;
139
140            if(gray)
141            {
142                t = srcdata[y * w + x];
143                if(srcdata[y2 * w + x] < t) t = srcdata[y2 * w + x];
144                if(srcdata[y3 * w + x] < t) t = srcdata[y3 * w + x];
145                if(srcdata[y * w + x2] < t) t = srcdata[y * w + x2];
146                if(srcdata[y * w + x3] < t) t = srcdata[y * w + x3];
147                dstdata[y * w + x] = t;
148            }
149            else
150            {
151                for(i = 0; i < 4; i++)
152                {
153                    t = srcdata[4 * (y * w + x) + i];
154                    if(srcdata[4 * (y2 * w + x) + i] < t)
155                        t = srcdata[4 * (y2 * w + x) + i];
156                    if(srcdata[4 * (y3 * w + x) + i] < t)
157                        t = srcdata[4 * (y3 * w + x) + i];
158                    if(srcdata[4 * (y * w + x2) + i] < t)
159                        t = srcdata[4 * (y * w + x2) + i];
160                    if(srcdata[4 * (y * w + x3) + i] < t)
161                        t = srcdata[4 * (y * w + x3) + i];
162                    dstdata[4 * (y * w + x) + i] = t;
163                }
164            }
165        }
166    }
167
168    return dst;
169}
170
Note: See TracBrowser for help on using the repository browser.