1 /* This file is an image processing operation for GEGL
2  *
3  * GEGL is free software; you can redistribute it and/or
4  * modify it under the terms of the GNU Lesser General Public
5  * License as published by the Free Software Foundation; either
6  * version 3 of the License, or (at your option) any later version.
7  *
8  * GEGL is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11  * Lesser General Public License for more details.
12  *
13  * You should have received a copy of the GNU Lesser General Public
14  * License along with GEGL; if not, see <https://www.gnu.org/licenses/>.
15  *
16  * Copyright 2006 Øyvind Kolås <pippin@gimp.org>
17  */
18 
19 #include "config.h"
20 #include <glib/gi18n-lib.h>
21 
22 
23 #ifdef GEGL_PROPERTIES
24 
25 property_double (alpha, _("Alpha"), 1.2)
26     ui_range    (0.0, 4.0)
27 property_double (scale, _("Scale"), 1.8)
28     ui_range    (0.0, 20.0)
29 
30 property_double (zoff,  _("Z offset"), -1)
31     ui_range    (-1.0, 8.0)
32 
33 property_int (n, _("Iterations"), 3)
34   value_range     (0, 20)
35 
36 #else
37 
38 #define GEGL_OP_POINT_RENDER
39 #define GEGL_OP_NAME     noise_perlin
40 #define GEGL_OP_C_SOURCE noise-perlin.c
41 
42 #include "gegl-op.h"
43 #include "perlin/perlin.c"
44 #include "perlin/perlin.h"
45 
46 static void
47 prepare (GeglOperation *operation)
48 {
49   gegl_operation_set_format (operation, "output", babl_format ("Y float"));
50 }
51 
52 static gboolean
53 process (GeglOperation       *operation,
54          void                *out_buf,
55          glong                n_pixels,
56          const GeglRectangle *roi,
57          gint                 level)
58 {
59   GeglProperties *o = GEGL_PROPERTIES (operation);
60   gfloat     *out_pixel = out_buf;
61   gint        x = roi->x; /* initial x                   */
62   gint        y = roi->y; /*           and y coordinates */
63 
64 
65   while (n_pixels--)
66     {
67       gfloat val;
68 
69       val = PerlinNoise3D ((double) (x)/50.0,
70                            (double) (y)/50.0,
71                            (double) o->zoff, o->alpha, o->scale,
72                            o->n);
73       *out_pixel = val * 0.5 + 0.5;
74       out_pixel ++;
75 
76       /* update x and y coordinates */
77       x++;
78       if (x>=roi->x + roi->width)
79         {
80           x=roi->x;
81           y++;
82         }
83     }
84   return  TRUE;
85 }
86 
87 static GeglRectangle
88 get_bounding_box (GeglOperation *operation)
89 {
90   return gegl_rectangle_infinite_plane ();
91 }
92 
93 
94 static void
95 gegl_op_class_init (GeglOpClass *klass)
96 {
97   GeglOperationClass            *operation_class;
98   GeglOperationPointRenderClass *point_render_class;
99 
100   perlin_init ();
101 
102   operation_class = GEGL_OPERATION_CLASS (klass);
103   point_render_class = GEGL_OPERATION_POINT_RENDER_CLASS (klass);
104 
105   point_render_class->process = process;
106   operation_class->get_bounding_box = get_bounding_box;
107   operation_class->prepare = prepare;
108 
109   gegl_operation_class_set_keys (operation_class,
110     "name",               "gegl:perlin-noise",
111     "title",              _("Perlin Noise"),
112     "categories",         "render",
113     "reference-hash",     "78a43934ae5b69e48ed523a61bdea6c4",
114     "position-dependent", "true",
115     "description", _("Perlin noise generator"),
116     NULL);
117 
118 }
119 
120 #endif
121