mirror of https://github.com/GNOME/gimp.git
Start of a stable/unstable plug-in split (these are going into
gimp-plugins-unstable) -Yosh
This commit is contained in:
parent
0e9f9891f6
commit
4607c5e5e5
|
@ -289,7 +289,6 @@ plug-ins/maze/Makefile
|
|||
plug-ins/max_rgb/Makefile
|
||||
plug-ins/mail/Makefile
|
||||
plug-ins/magiceye/Makefile
|
||||
plug-ins/lic/Makefile
|
||||
plug-ins/laplace/Makefile
|
||||
plug-ins/ifscompose/Makefile
|
||||
plug-ins/iwarp/Makefile
|
||||
|
@ -307,10 +306,8 @@ plug-ins/gfli/Makefile
|
|||
plug-ins/gbr/Makefile
|
||||
plug-ins/gauss_iir/Makefile
|
||||
plug-ins/gauss_rle/Makefile
|
||||
plug-ins/fp/Makefile
|
||||
plug-ins/fits/Makefile
|
||||
plug-ins/film/Makefile
|
||||
plug-ins/figures/Makefile
|
||||
plug-ins/faxg3/Makefile
|
||||
plug-ins/exchange/Makefile
|
||||
plug-ins/engrave/Makefile
|
||||
|
@ -358,13 +355,10 @@ plug-ins/flame/Makefile
|
|||
plug-ins/gimptcl/Makefile
|
||||
plug-ins/gimptcl/scripts/Makefile
|
||||
plug-ins/fuse/Makefile
|
||||
plug-ins/mathmap/Makefile
|
||||
plug-ins/rcm/Makefile
|
||||
plug-ins/refract/Makefile
|
||||
plug-ins/struc/Makefile
|
||||
plug-ins/twist/Makefile
|
||||
plug-ins/user_filter/Makefile
|
||||
plug-ins/warp/Makefile
|
||||
plug-ins/zealouscrop/Makefile
|
||||
plug-ins/xwd/Makefile
|
||||
plug-ins/whirlpinch/Makefile
|
||||
|
|
|
@ -14,11 +14,9 @@ SUBDIRS = \
|
|||
fuse \
|
||||
gflare \
|
||||
@GIMPTCL@ \
|
||||
refract \
|
||||
script-fu \
|
||||
struc \
|
||||
twist \
|
||||
warp \
|
||||
@TIFF@ \
|
||||
@JPEG@ \
|
||||
@PNG@ \
|
||||
|
@ -57,12 +55,10 @@ SUBDIRS = \
|
|||
engrave \
|
||||
exchange \
|
||||
faxg3 \
|
||||
figures \
|
||||
film \
|
||||
fits \
|
||||
flame \
|
||||
flarefx \
|
||||
fp \
|
||||
fractaltrace \
|
||||
gauss_iir \
|
||||
gauss_rle \
|
||||
|
@ -83,7 +79,6 @@ SUBDIRS = \
|
|||
illusion \
|
||||
iwarp \
|
||||
laplace \
|
||||
lic \
|
||||
magiceye \
|
||||
mail \
|
||||
max_rgb \
|
||||
|
|
|
@ -1,287 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "gtk/gtk.h"
|
||||
#include "libgimp/gimp.h"
|
||||
#include "fp.h"
|
||||
#include "fp_hsv.h"
|
||||
|
||||
FP_Params Current =
|
||||
{
|
||||
1,
|
||||
.25, /* Initial Roughness */
|
||||
NULL,
|
||||
.6, /* Initial Degree of Aliasing */
|
||||
NULL,
|
||||
60,
|
||||
NULL,
|
||||
MIDTONES, /* Initial Range */
|
||||
BY_VAL, /* Initial God knows what */
|
||||
TRUE, /* Selection Only */
|
||||
TRUE, /* Real Time */
|
||||
0, /* Offset */
|
||||
HUE|VALUE,
|
||||
{32,224,255},
|
||||
{0,0,0}
|
||||
};
|
||||
|
||||
GDrawable *drawable, *mask;
|
||||
|
||||
void query (void);
|
||||
void run (char *name,
|
||||
int nparams,
|
||||
GParam *param,
|
||||
int *nreturn_vals,
|
||||
GParam **return_vals);
|
||||
|
||||
GPlugInInfo PLUG_IN_INFO =
|
||||
{
|
||||
NULL, /* init_proc */
|
||||
NULL, /* quit_proc */
|
||||
query, /* query_proc */
|
||||
run, /* run_proc */
|
||||
};
|
||||
|
||||
|
||||
|
||||
MAIN()
|
||||
|
||||
|
||||
void
|
||||
query ()
|
||||
{
|
||||
GParamDef args[] =
|
||||
{
|
||||
{ PARAM_INT32, "run_mode", "Interactive, non-interactive" },
|
||||
{ PARAM_IMAGE, "image", "Input image (used for indexed images)" },
|
||||
{ PARAM_DRAWABLE, "drawable", "Input drawable" },
|
||||
};
|
||||
GParamDef *return_vals = NULL;
|
||||
int nargs = sizeof (args) / sizeof (args[0]);
|
||||
int nreturn_vals = 0;
|
||||
|
||||
gimp_install_procedure ("plug_in_filter_pack",
|
||||
"Allows the user to change H, S, or C with many previews",
|
||||
"Then something else here",
|
||||
"Pavel Grinfeld (pavel@ml.com)",
|
||||
"Pavel Grinfeld (pavel@ml.com)",
|
||||
"27th March 1997",
|
||||
"<Image>/Filters/Colors/Filter Pack",
|
||||
"RGB*,INDEXED*,GRAY*",
|
||||
PROC_PLUG_IN,
|
||||
nargs, nreturn_vals,
|
||||
args, return_vals);
|
||||
}
|
||||
|
||||
/********************************STANDARD RUN*************************/
|
||||
void
|
||||
run (char *name,
|
||||
int nparams,
|
||||
GParam *param,
|
||||
int *nreturn_vals,
|
||||
GParam **return_vals)
|
||||
{
|
||||
GParam values[1];
|
||||
GStatusType status = STATUS_SUCCESS;
|
||||
|
||||
*nreturn_vals = 1;
|
||||
*return_vals = values;
|
||||
|
||||
values[0].type = PARAM_STATUS;
|
||||
values[0].data.d_status = status;
|
||||
|
||||
initializeFilterPacks();
|
||||
|
||||
drawable = gimp_drawable_get (param[2].data.d_drawable);
|
||||
mask=gimp_drawable_get(gimp_image_get_selection(param[1].data.d_image));
|
||||
|
||||
if (gimp_drawable_indexed (drawable->id) ||gimp_drawable_gray (drawable->id) ) {
|
||||
ErrorMessage("Convert the image to RGB first!");
|
||||
status = STATUS_EXECUTION_ERROR;
|
||||
}
|
||||
|
||||
else if (gimp_drawable_color (drawable->id) && fp_dialog())
|
||||
{
|
||||
gimp_progress_init ("Applying the Filter Pack...");
|
||||
gimp_tile_cache_ntiles (2 * (drawable->width / gimp_tile_width () + 1));
|
||||
fp (drawable);
|
||||
gimp_displays_flush ();
|
||||
}
|
||||
else status = STATUS_EXECUTION_ERROR;
|
||||
|
||||
|
||||
values[0].data.d_status = status;
|
||||
if (status==STATUS_SUCCESS)
|
||||
gimp_drawable_detach (drawable);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
fp_row (const guchar *src_row,
|
||||
guchar *dest_row,
|
||||
gint row,
|
||||
gint row_width,
|
||||
gint bytes)
|
||||
{
|
||||
gint col, bytenum, k;
|
||||
int JudgeBy, Intensity, P[3], backupP[3];
|
||||
hsv H,S,V;
|
||||
gint M, m, middle;
|
||||
|
||||
/* initialize */
|
||||
|
||||
Intensity = 0;
|
||||
|
||||
for (col = 0; col < row_width ; col++)
|
||||
{
|
||||
|
||||
backupP[0] = P[0] = src_row[col*bytes+0];
|
||||
backupP[0] = P[1] = src_row[col*bytes+1];
|
||||
backupP[0] = P[2] = src_row[col*bytes+2];
|
||||
|
||||
|
||||
rgb_to_hsv(P[0]/255.0, P[1]/255.0, P[2]/255.0, &H, &S, &V);
|
||||
|
||||
for (JudgeBy=BY_HUE; JudgeBy<JUDGE_BY; JudgeBy++) {
|
||||
if (!Current.Touched[JudgeBy]) continue;
|
||||
|
||||
switch (JudgeBy) {
|
||||
case BY_HUE:
|
||||
Intensity=255*H;
|
||||
break;
|
||||
case BY_SAT:
|
||||
Intensity=255*S;
|
||||
break;
|
||||
case BY_VAL:
|
||||
Intensity=255*V;
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
/* It's important to take care of Saturation first!!! */
|
||||
|
||||
m = MIN(MIN(P[0],P[1]),P[2]);
|
||||
M = MAX(MAX(P[0],P[1]),P[2]);
|
||||
middle=(M+m)/2;
|
||||
|
||||
for (k=0; k<3; k++)
|
||||
if (P[k]!=m && P[k]!=M) middle=P[k];
|
||||
|
||||
for (k=0; k<3; k++)
|
||||
if (M!=m)
|
||||
if (P[k] == M)
|
||||
P[k] = MAX(P[k]+Current.satAdj[JudgeBy][Intensity],middle);
|
||||
else if (P[k] == m)
|
||||
P[k] = MIN(P[k]-Current.satAdj[JudgeBy][Intensity],middle);
|
||||
|
||||
|
||||
|
||||
P[0] += Current.redAdj[JudgeBy][Intensity];
|
||||
P[1] += Current.greenAdj[JudgeBy][Intensity];
|
||||
P[2] += Current.blueAdj[JudgeBy][Intensity];
|
||||
|
||||
P[0] = MAX(0,MIN(255, P[0]));
|
||||
P[1] = MAX(0,MIN(255, P[1]));
|
||||
P[2] = MAX(0,MIN(255, P[2]));
|
||||
}
|
||||
dest_row[col*bytes + 0] = P[0];
|
||||
dest_row[col*bytes + 1] = P[1];
|
||||
dest_row[col*bytes + 2] = P[2];
|
||||
|
||||
if (bytes>3)
|
||||
for (bytenum = 3; bytenum<bytes; bytenum++)
|
||||
dest_row[col*bytes+bytenum] = src_row[col*bytes+bytenum];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void fp (GDrawable *drawable)
|
||||
{
|
||||
GPixelRgn srcPR, destPR;
|
||||
gint width, height;
|
||||
gint bytes;
|
||||
guchar *src_row, *dest_row;
|
||||
gint row;
|
||||
gint x1, y1, x2, y2;
|
||||
|
||||
gimp_drawable_mask_bounds (drawable->id, &x1, &y1, &x2, &y2);
|
||||
|
||||
width = drawable->width;
|
||||
height = drawable->height;
|
||||
bytes = drawable->bpp;
|
||||
|
||||
src_row = (guchar *) malloc ((x2 - x1) * bytes);
|
||||
dest_row = (guchar *) malloc ((x2 - x1) * bytes);
|
||||
|
||||
gimp_pixel_rgn_init (&srcPR, drawable, 0, 0, width, height, FALSE, FALSE);
|
||||
gimp_pixel_rgn_init (&destPR, drawable, 0, 0, width, height, TRUE, TRUE);
|
||||
|
||||
for (row = y1; row < y2; row++)
|
||||
{
|
||||
gimp_pixel_rgn_get_row (&srcPR, src_row, x1, row, (x2 - x1));
|
||||
|
||||
fp_row (src_row,
|
||||
dest_row,
|
||||
row,
|
||||
(x2 - x1),
|
||||
bytes
|
||||
);
|
||||
|
||||
gimp_pixel_rgn_set_row (&destPR, dest_row, x1, row, (x2 - x1));
|
||||
|
||||
if ((row % 10) == 0)
|
||||
gimp_progress_update ((double) row / (double) (y2 - y1));
|
||||
}
|
||||
|
||||
|
||||
/* update the processed region */
|
||||
|
||||
gimp_drawable_flush (drawable);
|
||||
gimp_drawable_merge_shadow (drawable->id, TRUE);
|
||||
gimp_drawable_update (drawable->id, x1, y1, (x2 - x1), (y2 - y1));
|
||||
|
||||
free (src_row);
|
||||
free (dest_row);
|
||||
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ErrorMessage(guchar *message)
|
||||
{
|
||||
GtkWidget *window, *label, *button,*table;
|
||||
gchar **argv=g_new (gchar *, 1);
|
||||
gint argc=1;
|
||||
argv[0] = g_strdup ("fp");
|
||||
gtk_init (&argc, &argv);
|
||||
gtk_rc_parse (gimp_gtkrc ());
|
||||
|
||||
window=gtk_dialog_new();
|
||||
gtk_window_position (GTK_WINDOW (window), GTK_WIN_POS_MOUSE);
|
||||
gtk_window_set_title(GTK_WINDOW(window),"Filter Pack Simulation Message");
|
||||
gtk_signal_connect (GTK_OBJECT (window), "destroy",
|
||||
(GtkSignalFunc) fp_close_callback,
|
||||
NULL);
|
||||
|
||||
button = gtk_button_new_with_label ("Got It!");
|
||||
GTK_WIDGET_SET_FLAGS (button, GTK_CAN_DEFAULT);
|
||||
gtk_signal_connect (GTK_OBJECT (button), "clicked",
|
||||
(GtkSignalFunc) fp_ok_callback,
|
||||
window);
|
||||
gtk_widget_grab_default (button);
|
||||
gtk_widget_show (button);
|
||||
gtk_box_pack_start (GTK_BOX (GTK_DIALOG (window)->action_area), button, TRUE, TRUE, 0);
|
||||
|
||||
table=gtk_table_new(2,2,FALSE);
|
||||
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(window)->vbox),table,TRUE,TRUE,0);
|
||||
gtk_widget_show(table);
|
||||
|
||||
label=gtk_label_new("");
|
||||
gtk_label_set(GTK_LABEL(label),message);
|
||||
gtk_widget_show(label);
|
||||
gtk_table_attach(GTK_TABLE(table),label,0,1,0,1,
|
||||
GTK_FILL|GTK_EXPAND,GTK_FILL|GTK_EXPAND,15,15);
|
||||
|
||||
gtk_widget_show(window);
|
||||
gtk_main ();
|
||||
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -1,6 +0,0 @@
|
|||
Makefile.in
|
||||
Makefile
|
||||
.deps
|
||||
_libs
|
||||
.libs
|
||||
figures
|
|
@ -1,39 +0,0 @@
|
|||
## Process this file with automake to produce Makefile.in
|
||||
|
||||
pluginlibdir = $(gimpplugindir)/plug-ins
|
||||
|
||||
pluginlib_PROGRAMS = figures
|
||||
|
||||
figures_SOURCES = \
|
||||
figures.c
|
||||
|
||||
INCLUDES = \
|
||||
$(X_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
-I$(includedir)
|
||||
|
||||
LDADD = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la \
|
||||
$(X_LIBS) \
|
||||
\
|
||||
-lc
|
||||
|
||||
DEPS = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la
|
||||
|
||||
figures_DEPENDENCIES = $(DEPS)
|
||||
|
||||
.PHONY: files
|
||||
|
||||
files:
|
||||
@files=`ls $(DISTFILES) 2> /dev/null`; for p in $$files; do \
|
||||
echo $$p; \
|
||||
done
|
||||
@for subdir in $(SUBDIRS); do \
|
||||
files=`cd $$subdir; $(MAKE) files | grep -v "make\[[1-9]\]"`; \
|
||||
for file in $$files; do \
|
||||
echo $$subdir/$$file; \
|
||||
done; \
|
||||
done
|
|
@ -1,442 +0,0 @@
|
|||
/* The GIMP -- an image manipulation program * Copyright (C) 1995 Spencer
|
||||
* Kimball and Peter Mattis * * This program is free software; you can
|
||||
* redistribute it and/or modify * it under the terms of the GNU General
|
||||
* Public License as published by * the Free Software Foundation; either
|
||||
* version 2 of the License, or * (at your option) any later version. * *
|
||||
* This program is distributed in the hope that it will be useful, * but
|
||||
* WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU
|
||||
* General Public License for more details. * * You should have received a
|
||||
* copy of the GNU General Public License * along with this program; if not,
|
||||
* write to the Free Software * Foundation, Inc., 675 Mass Ave, Cambridge, MA
|
||||
* 02139, USA. */
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <time.h>
|
||||
#include "libgimp/gimp.h"
|
||||
#include "gtk/gtk.h"
|
||||
|
||||
/* Declare local functions. */
|
||||
static void query(void);
|
||||
static void run(char *name,
|
||||
int nparams,
|
||||
GParam * param,
|
||||
int *nreturn_vals,
|
||||
GParam ** return_vals);
|
||||
static gint dialog();
|
||||
|
||||
static void doit(GDrawable * drawable);
|
||||
|
||||
GPlugInInfo PLUG_IN_INFO =
|
||||
{
|
||||
NULL, /* init_proc */
|
||||
NULL, /* quit_proc */
|
||||
query, /* query_proc */
|
||||
run, /* run_proc */
|
||||
};
|
||||
|
||||
gint bytes;
|
||||
gint sx1, sy1, sx2, sy2;
|
||||
int run_flag = 0;
|
||||
|
||||
typedef struct {
|
||||
gint min_width, max_width;
|
||||
gint min_height, max_height;
|
||||
float density;
|
||||
} config;
|
||||
|
||||
config my_config =
|
||||
{
|
||||
10, 30, /* min_width, max_width */
|
||||
10, 30, /* min_height, max_height */
|
||||
4 /* density */
|
||||
};
|
||||
|
||||
|
||||
MAIN()
|
||||
|
||||
static void query()
|
||||
{
|
||||
static GParamDef args[] =
|
||||
{
|
||||
{PARAM_INT32, "run_mode", "Interactive, non-interactive"},
|
||||
{PARAM_IMAGE, "image", "Input image (unused)"},
|
||||
{PARAM_DRAWABLE, "drawable", "Input drawable"},
|
||||
{PARAM_FLOAT, "density", "Density"},
|
||||
{PARAM_INT32, "min_width", "Min. width"},
|
||||
{PARAM_INT32, "max_width", "Max. width"},
|
||||
{PARAM_INT32, "min_height", "Min. height"},
|
||||
{PARAM_INT32, "max_height", "Max. height"},
|
||||
};
|
||||
static GParamDef *return_vals = NULL;
|
||||
static int nargs = sizeof(args) / sizeof(args[0]);
|
||||
static int nreturn_vals = 0;
|
||||
|
||||
gimp_install_procedure("plug_in_figures",
|
||||
"Draws lots of rectangles.",
|
||||
"Can be nice to use as \"textures\".",
|
||||
"Tim Newsome",
|
||||
"Tim Newsome",
|
||||
"1997",
|
||||
"<Image>/Filters/Render/Figures",
|
||||
"RGB*, GRAY*",
|
||||
PROC_PLUG_IN,
|
||||
nargs, nreturn_vals,
|
||||
args, return_vals);
|
||||
}
|
||||
|
||||
static void run(char *name, int n_params, GParam * param, int *nreturn_vals,
|
||||
GParam ** return_vals)
|
||||
{
|
||||
static GParam values[1];
|
||||
GDrawable *drawable;
|
||||
GRunModeType run_mode;
|
||||
GStatusType status = STATUS_SUCCESS;
|
||||
|
||||
*nreturn_vals = 1;
|
||||
*return_vals = values;
|
||||
|
||||
run_mode = param[0].data.d_int32;
|
||||
|
||||
if (run_mode == RUN_NONINTERACTIVE) {
|
||||
if (n_params != 8) {
|
||||
status = STATUS_CALLING_ERROR;
|
||||
} else {
|
||||
my_config.density = param[3].data.d_float;
|
||||
my_config.min_width = param[4].data.d_int32;
|
||||
my_config.max_width = param[5].data.d_int32;
|
||||
my_config.min_height = param[6].data.d_int32;
|
||||
my_config.max_height = param[7].data.d_int32;
|
||||
}
|
||||
} else {
|
||||
/* Possibly retrieve data */
|
||||
gimp_get_data("plug_in_figures", &my_config);
|
||||
|
||||
if (run_mode == RUN_INTERACTIVE) {
|
||||
/* Oh boy. We get to do a dialog box, because we can't really expect the
|
||||
* user to set us up with the right values using gdb.
|
||||
*/
|
||||
if (!dialog()) {
|
||||
/* The dialog was closed, or something similarly evil happened. */
|
||||
status = STATUS_EXECUTION_ERROR;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (status == STATUS_SUCCESS) {
|
||||
/* Get the specified drawable */
|
||||
drawable = gimp_drawable_get(param[2].data.d_drawable);
|
||||
|
||||
/* Make sure that the drawable is gray or RGB color */
|
||||
if (gimp_drawable_color(drawable->id) || gimp_drawable_gray(drawable->id)) {
|
||||
gimp_progress_init("Drawing Figures...");
|
||||
gimp_tile_cache_ntiles(2 * (drawable->width / gimp_tile_width() + 1));
|
||||
|
||||
srand(time(NULL));
|
||||
doit(drawable);
|
||||
|
||||
if (run_mode != RUN_NONINTERACTIVE)
|
||||
gimp_displays_flush();
|
||||
|
||||
if (run_mode == RUN_INTERACTIVE)
|
||||
gimp_set_data("plug_in_figures", &my_config, sizeof(my_config));
|
||||
} else {
|
||||
status = STATUS_EXECUTION_ERROR;
|
||||
}
|
||||
gimp_drawable_detach(drawable);
|
||||
}
|
||||
|
||||
values[0].type = PARAM_STATUS;
|
||||
values[0].data.d_status = status;
|
||||
}
|
||||
|
||||
/*
|
||||
* Draws a rectangle in region, using tmp as tempspace, with center x, y,
|
||||
* width w, height h, with color color, and opaqueness a.
|
||||
*/
|
||||
static void draw_rectangle(guchar * tmp, GPixelRgn * region, int x, int y,
|
||||
int w, int h, guchar color[], float a)
|
||||
{
|
||||
int i, j, k;
|
||||
int rx1, rx2, ry1, ry2;
|
||||
|
||||
rx1 = x - w / 2;
|
||||
rx2 = rx1 + w;
|
||||
ry1 = y - h / 2;
|
||||
ry2 = ry1 + h;
|
||||
|
||||
rx1 = rx1 < sx1 ? sx1 : rx1;
|
||||
ry1 = ry1 < sy1 ? sy1 : ry1;
|
||||
rx2 = rx2 > sx2 ? sx2 : rx2;
|
||||
ry2 = ry2 > sy2 ? sy2 : ry2;
|
||||
|
||||
gimp_pixel_rgn_get_rect(region, tmp, rx1, ry1, rx2 - rx1, ry2 - ry1);
|
||||
for (j = 0; j < (rx2 - rx1); j++) {
|
||||
for (k = 0; k < (ry2 - ry1); k++) {
|
||||
for (i = 0; i < bytes; i++) {
|
||||
tmp[(j + (rx2 - rx1) * k) * bytes + i] =
|
||||
(float) tmp[(j + (rx2 - rx1) * k) * bytes + i] * (1 - a) +
|
||||
(float) color[i] * a;
|
||||
}
|
||||
}
|
||||
}
|
||||
gimp_pixel_rgn_set_rect(region, tmp, rx1, ry1, rx2 - rx1, ry2 - ry1);
|
||||
}
|
||||
|
||||
static void doit(GDrawable * drawable)
|
||||
{
|
||||
GPixelRgn srcPR, destPR;
|
||||
gint width, height;
|
||||
int x, y, w, h;
|
||||
int i, j;
|
||||
guchar *tmp, *copybuf;
|
||||
guchar color[4];
|
||||
int objects;
|
||||
|
||||
/* Get the input area. This is the bounding box of the selection in
|
||||
* the image (or the entire image if there is no selection). Only
|
||||
* operating on the input area is simply an optimization. It doesn't
|
||||
* need to be done for correct operation. (It simply makes it go
|
||||
* faster, since fewer pixels need to be operated on).
|
||||
*/
|
||||
gimp_drawable_mask_bounds(drawable->id, &sx1, &sy1, &sx2, &sy2);
|
||||
|
||||
/* Get the size of the input image. (This will/must be the same
|
||||
* as the size of the output image.
|
||||
*/
|
||||
width = drawable->width;
|
||||
height = drawable->height;
|
||||
bytes = drawable->bpp;
|
||||
|
||||
tmp = (guchar *) malloc(my_config.max_width * my_config.max_height * bytes);
|
||||
if (tmp == NULL) {
|
||||
return;
|
||||
}
|
||||
/* initialize the pixel regions */
|
||||
gimp_pixel_rgn_init(&srcPR, drawable, 0, 0, width, height, FALSE, FALSE);
|
||||
gimp_pixel_rgn_init(&destPR, drawable, 0, 0, width, height, TRUE, TRUE);
|
||||
|
||||
/* First off, copy the old one to the new one. */
|
||||
copybuf = malloc(width * bytes);
|
||||
for (i = sy1; i < sy2; i++) {
|
||||
gimp_pixel_rgn_get_row(&srcPR, copybuf, sx1, i, width);
|
||||
gimp_pixel_rgn_set_row(&destPR, copybuf, sx1, i, width);
|
||||
}
|
||||
free(copybuf);
|
||||
|
||||
objects = my_config.density * (float) (width * height) /
|
||||
(float) (((my_config.min_width + my_config.max_width) / 2) *
|
||||
((my_config.min_height + my_config.max_height)) / 2);
|
||||
|
||||
for (i = 0; i < objects; i++) {
|
||||
w = my_config.min_width + rand() * (double) (my_config.max_width -
|
||||
my_config.min_width) / (double) RAND_MAX;
|
||||
h = my_config.min_height + rand() * (double) (my_config.max_height -
|
||||
my_config.min_height) / (double) RAND_MAX;
|
||||
x = sx1 + rand() * (double) width / (double) RAND_MAX;
|
||||
y = sy1 + rand() * (double) height / (double) RAND_MAX;
|
||||
for (j = 0; j < bytes; j++) {
|
||||
color[j] = rand() * 255. / (double) RAND_MAX;
|
||||
}
|
||||
draw_rectangle(tmp, &destPR, x, y, w, h, color,
|
||||
rand() / (double) RAND_MAX);
|
||||
if (!(i % 64)) {
|
||||
gimp_progress_update((double) i / (double) objects);
|
||||
}
|
||||
}
|
||||
|
||||
/* update the timred region */
|
||||
gimp_drawable_flush(drawable);
|
||||
gimp_drawable_merge_shadow(drawable->id, TRUE);
|
||||
gimp_drawable_update(drawable->id, sx1, sy1, sx2 - sx1, sy2 - sy1);
|
||||
}
|
||||
|
||||
/***************************************************
|
||||
* GUI stuff
|
||||
*/
|
||||
|
||||
static void close_callback(GtkWidget * widget, gpointer data)
|
||||
{
|
||||
gtk_main_quit();
|
||||
}
|
||||
|
||||
static void ok_callback(GtkWidget * widget, gpointer data)
|
||||
{
|
||||
run_flag = 1;
|
||||
gtk_widget_destroy(GTK_WIDGET(data));
|
||||
}
|
||||
|
||||
static void entry_callback(GtkWidget * widget, gpointer data)
|
||||
{
|
||||
if (data == &my_config.density)
|
||||
my_config.density = atof(gtk_entry_get_text(GTK_ENTRY(widget)));
|
||||
else if (data == &my_config.min_width)
|
||||
my_config.min_width = atoi(gtk_entry_get_text(GTK_ENTRY(widget)));
|
||||
else if (data == &my_config.max_width)
|
||||
my_config.max_width = atoi(gtk_entry_get_text(GTK_ENTRY(widget)));
|
||||
else if (data == &my_config.min_height)
|
||||
my_config.min_height = atoi(gtk_entry_get_text(GTK_ENTRY(widget)));
|
||||
else if (data == &my_config.max_height)
|
||||
my_config.max_height = atoi(gtk_entry_get_text(GTK_ENTRY(widget)));
|
||||
}
|
||||
|
||||
static gint dialog()
|
||||
{
|
||||
GtkWidget *dlg;
|
||||
GtkWidget *button;
|
||||
GtkWidget *label;
|
||||
GtkWidget *entry;
|
||||
GtkWidget *table;
|
||||
gchar buffer[12];
|
||||
gchar **argv;
|
||||
gint argc;
|
||||
|
||||
argc = 1;
|
||||
argv = g_new(gchar *, 1);
|
||||
argv[0] = g_strdup("plasma");
|
||||
|
||||
gtk_init(&argc, &argv);
|
||||
gtk_rc_parse (gimp_gtkrc ());
|
||||
|
||||
dlg = gtk_dialog_new();
|
||||
gtk_window_set_title(GTK_WINDOW(dlg), "Figures");
|
||||
gtk_window_position(GTK_WINDOW(dlg), GTK_WIN_POS_MOUSE);
|
||||
gtk_signal_connect(GTK_OBJECT(dlg), "destroy",
|
||||
(GtkSignalFunc) close_callback, NULL);
|
||||
|
||||
/* Action area */
|
||||
button = gtk_button_new_with_label("OK");
|
||||
GTK_WIDGET_SET_FLAGS(button, GTK_CAN_DEFAULT);
|
||||
gtk_signal_connect(GTK_OBJECT(button), "clicked",
|
||||
(GtkSignalFunc) ok_callback,
|
||||
dlg);
|
||||
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dlg)->action_area), button, TRUE, TRUE, 0);
|
||||
gtk_widget_grab_default(button);
|
||||
gtk_widget_show(button);
|
||||
|
||||
button = gtk_button_new_with_label("Cancel");
|
||||
GTK_WIDGET_SET_FLAGS(button, GTK_CAN_DEFAULT);
|
||||
gtk_signal_connect_object(GTK_OBJECT(button), "clicked",
|
||||
(GtkSignalFunc) gtk_widget_destroy,
|
||||
GTK_OBJECT(dlg));
|
||||
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dlg)->action_area), button, TRUE, TRUE, 0);
|
||||
gtk_widget_show(button);
|
||||
|
||||
/* The main table */
|
||||
/* Set its size (y, x) */
|
||||
table = gtk_table_new(5, 3, FALSE);
|
||||
gtk_container_border_width(GTK_CONTAINER(table), 10);
|
||||
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dlg)->vbox), table, TRUE, TRUE, 0);
|
||||
gtk_widget_show(table);
|
||||
|
||||
gtk_table_set_row_spacings(GTK_TABLE(table), 10);
|
||||
gtk_table_set_col_spacings(GTK_TABLE(table), 10);
|
||||
|
||||
/*********************
|
||||
* The density entry *
|
||||
*********************/
|
||||
label = gtk_label_new("Density:");
|
||||
gtk_misc_set_alignment(GTK_MISC(label), 0.0, 0.5);
|
||||
gtk_table_attach(GTK_TABLE(table), label, 0, 1, 1, 2, GTK_FILL, GTK_FILL, 0,
|
||||
0);
|
||||
gtk_widget_show(label);
|
||||
|
||||
entry = gtk_entry_new();
|
||||
gtk_table_attach(GTK_TABLE(table), entry, 1, 3, 1, 2,
|
||||
GTK_EXPAND | GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
|
||||
gtk_widget_set_usize(entry, 50, 0);
|
||||
sprintf(buffer, "%0.2f", my_config.density);
|
||||
gtk_entry_set_text(GTK_ENTRY(entry), buffer);
|
||||
gtk_signal_connect(GTK_OBJECT(entry), "changed",
|
||||
(GtkSignalFunc) entry_callback,
|
||||
&my_config.density);
|
||||
gtk_widget_show(entry);
|
||||
|
||||
/**********************
|
||||
* The min/max labels *
|
||||
**********************/
|
||||
label = gtk_label_new("Min.");
|
||||
gtk_misc_set_alignment(GTK_MISC(label), 0.0, 0.5);
|
||||
gtk_table_attach(GTK_TABLE(table), label, 1, 2, 2, 3, GTK_FILL, GTK_FILL, 0,
|
||||
0);
|
||||
gtk_widget_show(label);
|
||||
|
||||
label = gtk_label_new("Max.");
|
||||
gtk_misc_set_alignment(GTK_MISC(label), 0.0, 0.5);
|
||||
gtk_table_attach(GTK_TABLE(table), label, 2, 3, 2, 3, GTK_FILL, GTK_FILL, 0,
|
||||
0);
|
||||
gtk_widget_show(label);
|
||||
|
||||
/************************
|
||||
* The min_width entry: *
|
||||
************************/
|
||||
label = gtk_label_new("Width:");
|
||||
gtk_misc_set_alignment(GTK_MISC(label), 0.0, 0.5);
|
||||
gtk_table_attach(GTK_TABLE(table), label, 0, 1, 3, 4, GTK_FILL, GTK_FILL, 0,
|
||||
0);
|
||||
gtk_widget_show(label);
|
||||
|
||||
entry = gtk_entry_new();
|
||||
gtk_table_attach(GTK_TABLE(table), entry, 1, 2, 3, 4, GTK_EXPAND | GTK_FILL,
|
||||
GTK_EXPAND | GTK_FILL, 0, 0);
|
||||
gtk_widget_set_usize(entry, 50, 0);
|
||||
sprintf(buffer, "%i", my_config.min_width);
|
||||
gtk_entry_set_text(GTK_ENTRY(entry), buffer);
|
||||
gtk_signal_connect(GTK_OBJECT(entry), "changed",
|
||||
(GtkSignalFunc) entry_callback, &my_config.min_width);
|
||||
gtk_widget_show(entry);
|
||||
|
||||
/************************
|
||||
* The max_width entry: *
|
||||
************************/
|
||||
entry = gtk_entry_new();
|
||||
gtk_table_attach(GTK_TABLE(table), entry, 2, 3, 3, 4, GTK_EXPAND | GTK_FILL,
|
||||
GTK_EXPAND | GTK_FILL, 0, 0);
|
||||
gtk_widget_set_usize(entry, 50, 0);
|
||||
sprintf(buffer, "%i", my_config.max_width);
|
||||
gtk_entry_set_text(GTK_ENTRY(entry), buffer);
|
||||
gtk_signal_connect(GTK_OBJECT(entry), "changed",
|
||||
(GtkSignalFunc) entry_callback, &my_config.max_width);
|
||||
gtk_widget_show(entry);
|
||||
|
||||
gtk_widget_show(dlg);
|
||||
|
||||
/************************
|
||||
* The min_height entry: *
|
||||
************************/
|
||||
label = gtk_label_new("Height:");
|
||||
gtk_misc_set_alignment(GTK_MISC(label), 0.0, 0.5);
|
||||
gtk_table_attach(GTK_TABLE(table), label, 0, 1, 4, 5, GTK_FILL, GTK_FILL, 0,
|
||||
0);
|
||||
gtk_widget_show(label);
|
||||
|
||||
entry = gtk_entry_new();
|
||||
gtk_table_attach(GTK_TABLE(table), entry, 1, 2, 4, 5, GTK_EXPAND | GTK_FILL,
|
||||
GTK_EXPAND | GTK_FILL, 0, 0);
|
||||
gtk_widget_set_usize(entry, 50, 0);
|
||||
sprintf(buffer, "%i", my_config.min_height);
|
||||
gtk_entry_set_text(GTK_ENTRY(entry), buffer);
|
||||
gtk_signal_connect(GTK_OBJECT(entry), "changed",
|
||||
(GtkSignalFunc) entry_callback, &my_config.min_height);
|
||||
gtk_widget_show(entry);
|
||||
|
||||
/************************
|
||||
* The max_height entry: *
|
||||
************************/
|
||||
entry = gtk_entry_new();
|
||||
gtk_table_attach(GTK_TABLE(table), entry, 2, 3, 4, 5, GTK_EXPAND | GTK_FILL,
|
||||
GTK_EXPAND | GTK_FILL, 0, 0);
|
||||
gtk_widget_set_usize(entry, 50, 0);
|
||||
sprintf(buffer, "%i", my_config.max_height);
|
||||
gtk_entry_set_text(GTK_ENTRY(entry), buffer);
|
||||
gtk_signal_connect(GTK_OBJECT(entry), "changed",
|
||||
(GtkSignalFunc) entry_callback, &my_config.max_height);
|
||||
gtk_widget_show(entry);
|
||||
|
||||
gtk_widget_show(dlg);
|
||||
|
||||
gtk_main();
|
||||
gdk_flush();
|
||||
|
||||
return run_flag;
|
||||
}
|
|
@ -1,6 +0,0 @@
|
|||
Makefile.in
|
||||
Makefile
|
||||
.deps
|
||||
_libs
|
||||
.libs
|
||||
fp
|
|
@ -1,39 +0,0 @@
|
|||
## Process this file with automake to produce Makefile.in
|
||||
|
||||
pluginlibdir = $(gimpplugindir)/plug-ins
|
||||
|
||||
pluginlib_PROGRAMS = fp
|
||||
|
||||
fp_SOURCES = \
|
||||
fp.c fp.h fp_gdk.c fp_gtk.c fp_hsv.c fp_hsv.h fp_misc.c
|
||||
|
||||
INCLUDES = \
|
||||
$(X_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
-I$(includedir)
|
||||
|
||||
LDADD = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la \
|
||||
$(X_LIBS) \
|
||||
\
|
||||
-lc
|
||||
|
||||
DEPS = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la
|
||||
|
||||
fp_DEPENDENCIES = $(DEPS)
|
||||
|
||||
.PHONY: files
|
||||
|
||||
files:
|
||||
@files=`ls $(DISTFILES) 2> /dev/null`; for p in $$files; do \
|
||||
echo $$p; \
|
||||
done
|
||||
@for subdir in $(SUBDIRS); do \
|
||||
files=`cd $$subdir; $(MAKE) files | grep -v "make\[[1-9]\]"`; \
|
||||
for file in $$files; do \
|
||||
echo $$subdir/$$file; \
|
||||
done; \
|
||||
done
|
287
plug-ins/fp/fp.c
287
plug-ins/fp/fp.c
|
@ -1,287 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "gtk/gtk.h"
|
||||
#include "libgimp/gimp.h"
|
||||
#include "fp.h"
|
||||
#include "fp_hsv.h"
|
||||
|
||||
FP_Params Current =
|
||||
{
|
||||
1,
|
||||
.25, /* Initial Roughness */
|
||||
NULL,
|
||||
.6, /* Initial Degree of Aliasing */
|
||||
NULL,
|
||||
60,
|
||||
NULL,
|
||||
MIDTONES, /* Initial Range */
|
||||
BY_VAL, /* Initial God knows what */
|
||||
TRUE, /* Selection Only */
|
||||
TRUE, /* Real Time */
|
||||
0, /* Offset */
|
||||
HUE|VALUE,
|
||||
{32,224,255},
|
||||
{0,0,0}
|
||||
};
|
||||
|
||||
GDrawable *drawable, *mask;
|
||||
|
||||
void query (void);
|
||||
void run (char *name,
|
||||
int nparams,
|
||||
GParam *param,
|
||||
int *nreturn_vals,
|
||||
GParam **return_vals);
|
||||
|
||||
GPlugInInfo PLUG_IN_INFO =
|
||||
{
|
||||
NULL, /* init_proc */
|
||||
NULL, /* quit_proc */
|
||||
query, /* query_proc */
|
||||
run, /* run_proc */
|
||||
};
|
||||
|
||||
|
||||
|
||||
MAIN()
|
||||
|
||||
|
||||
void
|
||||
query ()
|
||||
{
|
||||
GParamDef args[] =
|
||||
{
|
||||
{ PARAM_INT32, "run_mode", "Interactive, non-interactive" },
|
||||
{ PARAM_IMAGE, "image", "Input image (used for indexed images)" },
|
||||
{ PARAM_DRAWABLE, "drawable", "Input drawable" },
|
||||
};
|
||||
GParamDef *return_vals = NULL;
|
||||
int nargs = sizeof (args) / sizeof (args[0]);
|
||||
int nreturn_vals = 0;
|
||||
|
||||
gimp_install_procedure ("plug_in_filter_pack",
|
||||
"Allows the user to change H, S, or C with many previews",
|
||||
"Then something else here",
|
||||
"Pavel Grinfeld (pavel@ml.com)",
|
||||
"Pavel Grinfeld (pavel@ml.com)",
|
||||
"27th March 1997",
|
||||
"<Image>/Filters/Colors/Filter Pack",
|
||||
"RGB*,INDEXED*,GRAY*",
|
||||
PROC_PLUG_IN,
|
||||
nargs, nreturn_vals,
|
||||
args, return_vals);
|
||||
}
|
||||
|
||||
/********************************STANDARD RUN*************************/
|
||||
void
|
||||
run (char *name,
|
||||
int nparams,
|
||||
GParam *param,
|
||||
int *nreturn_vals,
|
||||
GParam **return_vals)
|
||||
{
|
||||
GParam values[1];
|
||||
GStatusType status = STATUS_SUCCESS;
|
||||
|
||||
*nreturn_vals = 1;
|
||||
*return_vals = values;
|
||||
|
||||
values[0].type = PARAM_STATUS;
|
||||
values[0].data.d_status = status;
|
||||
|
||||
initializeFilterPacks();
|
||||
|
||||
drawable = gimp_drawable_get (param[2].data.d_drawable);
|
||||
mask=gimp_drawable_get(gimp_image_get_selection(param[1].data.d_image));
|
||||
|
||||
if (gimp_drawable_indexed (drawable->id) ||gimp_drawable_gray (drawable->id) ) {
|
||||
ErrorMessage("Convert the image to RGB first!");
|
||||
status = STATUS_EXECUTION_ERROR;
|
||||
}
|
||||
|
||||
else if (gimp_drawable_color (drawable->id) && fp_dialog())
|
||||
{
|
||||
gimp_progress_init ("Applying the Filter Pack...");
|
||||
gimp_tile_cache_ntiles (2 * (drawable->width / gimp_tile_width () + 1));
|
||||
fp (drawable);
|
||||
gimp_displays_flush ();
|
||||
}
|
||||
else status = STATUS_EXECUTION_ERROR;
|
||||
|
||||
|
||||
values[0].data.d_status = status;
|
||||
if (status==STATUS_SUCCESS)
|
||||
gimp_drawable_detach (drawable);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
fp_row (const guchar *src_row,
|
||||
guchar *dest_row,
|
||||
gint row,
|
||||
gint row_width,
|
||||
gint bytes)
|
||||
{
|
||||
gint col, bytenum, k;
|
||||
int JudgeBy, Intensity, P[3], backupP[3];
|
||||
hsv H,S,V;
|
||||
gint M, m, middle;
|
||||
|
||||
/* initialize */
|
||||
|
||||
Intensity = 0;
|
||||
|
||||
for (col = 0; col < row_width ; col++)
|
||||
{
|
||||
|
||||
backupP[0] = P[0] = src_row[col*bytes+0];
|
||||
backupP[0] = P[1] = src_row[col*bytes+1];
|
||||
backupP[0] = P[2] = src_row[col*bytes+2];
|
||||
|
||||
|
||||
rgb_to_hsv(P[0]/255.0, P[1]/255.0, P[2]/255.0, &H, &S, &V);
|
||||
|
||||
for (JudgeBy=BY_HUE; JudgeBy<JUDGE_BY; JudgeBy++) {
|
||||
if (!Current.Touched[JudgeBy]) continue;
|
||||
|
||||
switch (JudgeBy) {
|
||||
case BY_HUE:
|
||||
Intensity=255*H;
|
||||
break;
|
||||
case BY_SAT:
|
||||
Intensity=255*S;
|
||||
break;
|
||||
case BY_VAL:
|
||||
Intensity=255*V;
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
/* It's important to take care of Saturation first!!! */
|
||||
|
||||
m = MIN(MIN(P[0],P[1]),P[2]);
|
||||
M = MAX(MAX(P[0],P[1]),P[2]);
|
||||
middle=(M+m)/2;
|
||||
|
||||
for (k=0; k<3; k++)
|
||||
if (P[k]!=m && P[k]!=M) middle=P[k];
|
||||
|
||||
for (k=0; k<3; k++)
|
||||
if (M!=m)
|
||||
if (P[k] == M)
|
||||
P[k] = MAX(P[k]+Current.satAdj[JudgeBy][Intensity],middle);
|
||||
else if (P[k] == m)
|
||||
P[k] = MIN(P[k]-Current.satAdj[JudgeBy][Intensity],middle);
|
||||
|
||||
|
||||
|
||||
P[0] += Current.redAdj[JudgeBy][Intensity];
|
||||
P[1] += Current.greenAdj[JudgeBy][Intensity];
|
||||
P[2] += Current.blueAdj[JudgeBy][Intensity];
|
||||
|
||||
P[0] = MAX(0,MIN(255, P[0]));
|
||||
P[1] = MAX(0,MIN(255, P[1]));
|
||||
P[2] = MAX(0,MIN(255, P[2]));
|
||||
}
|
||||
dest_row[col*bytes + 0] = P[0];
|
||||
dest_row[col*bytes + 1] = P[1];
|
||||
dest_row[col*bytes + 2] = P[2];
|
||||
|
||||
if (bytes>3)
|
||||
for (bytenum = 3; bytenum<bytes; bytenum++)
|
||||
dest_row[col*bytes+bytenum] = src_row[col*bytes+bytenum];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void fp (GDrawable *drawable)
|
||||
{
|
||||
GPixelRgn srcPR, destPR;
|
||||
gint width, height;
|
||||
gint bytes;
|
||||
guchar *src_row, *dest_row;
|
||||
gint row;
|
||||
gint x1, y1, x2, y2;
|
||||
|
||||
gimp_drawable_mask_bounds (drawable->id, &x1, &y1, &x2, &y2);
|
||||
|
||||
width = drawable->width;
|
||||
height = drawable->height;
|
||||
bytes = drawable->bpp;
|
||||
|
||||
src_row = (guchar *) malloc ((x2 - x1) * bytes);
|
||||
dest_row = (guchar *) malloc ((x2 - x1) * bytes);
|
||||
|
||||
gimp_pixel_rgn_init (&srcPR, drawable, 0, 0, width, height, FALSE, FALSE);
|
||||
gimp_pixel_rgn_init (&destPR, drawable, 0, 0, width, height, TRUE, TRUE);
|
||||
|
||||
for (row = y1; row < y2; row++)
|
||||
{
|
||||
gimp_pixel_rgn_get_row (&srcPR, src_row, x1, row, (x2 - x1));
|
||||
|
||||
fp_row (src_row,
|
||||
dest_row,
|
||||
row,
|
||||
(x2 - x1),
|
||||
bytes
|
||||
);
|
||||
|
||||
gimp_pixel_rgn_set_row (&destPR, dest_row, x1, row, (x2 - x1));
|
||||
|
||||
if ((row % 10) == 0)
|
||||
gimp_progress_update ((double) row / (double) (y2 - y1));
|
||||
}
|
||||
|
||||
|
||||
/* update the processed region */
|
||||
|
||||
gimp_drawable_flush (drawable);
|
||||
gimp_drawable_merge_shadow (drawable->id, TRUE);
|
||||
gimp_drawable_update (drawable->id, x1, y1, (x2 - x1), (y2 - y1));
|
||||
|
||||
free (src_row);
|
||||
free (dest_row);
|
||||
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ErrorMessage(guchar *message)
|
||||
{
|
||||
GtkWidget *window, *label, *button,*table;
|
||||
gchar **argv=g_new (gchar *, 1);
|
||||
gint argc=1;
|
||||
argv[0] = g_strdup ("fp");
|
||||
gtk_init (&argc, &argv);
|
||||
gtk_rc_parse (gimp_gtkrc ());
|
||||
|
||||
window=gtk_dialog_new();
|
||||
gtk_window_position (GTK_WINDOW (window), GTK_WIN_POS_MOUSE);
|
||||
gtk_window_set_title(GTK_WINDOW(window),"Filter Pack Simulation Message");
|
||||
gtk_signal_connect (GTK_OBJECT (window), "destroy",
|
||||
(GtkSignalFunc) fp_close_callback,
|
||||
NULL);
|
||||
|
||||
button = gtk_button_new_with_label ("Got It!");
|
||||
GTK_WIDGET_SET_FLAGS (button, GTK_CAN_DEFAULT);
|
||||
gtk_signal_connect (GTK_OBJECT (button), "clicked",
|
||||
(GtkSignalFunc) fp_ok_callback,
|
||||
window);
|
||||
gtk_widget_grab_default (button);
|
||||
gtk_widget_show (button);
|
||||
gtk_box_pack_start (GTK_BOX (GTK_DIALOG (window)->action_area), button, TRUE, TRUE, 0);
|
||||
|
||||
table=gtk_table_new(2,2,FALSE);
|
||||
gtk_box_pack_start(GTK_BOX(GTK_DIALOG(window)->vbox),table,TRUE,TRUE,0);
|
||||
gtk_widget_show(table);
|
||||
|
||||
label=gtk_label_new("");
|
||||
gtk_label_set(GTK_LABEL(label),message);
|
||||
gtk_widget_show(label);
|
||||
gtk_table_attach(GTK_TABLE(table),label,0,1,0,1,
|
||||
GTK_FILL|GTK_EXPAND,GTK_FILL|GTK_EXPAND,15,15);
|
||||
|
||||
gtk_widget_show(window);
|
||||
gtk_main ();
|
||||
|
||||
}
|
212
plug-ins/fp/fp.h
212
plug-ins/fp/fp.h
|
@ -1,212 +0,0 @@
|
|||
#define MAX_PREVIEW_SIZE 125
|
||||
#define MAX_ROUGHNESS 128
|
||||
#define RANGE_HEIGHT 15
|
||||
#define PR_BX_BRDR 10
|
||||
#define ALL 255
|
||||
|
||||
#define RANGE_ADJUST_MASK GDK_EXPOSURE_MASK | \
|
||||
GDK_ENTER_NOTIFY_MASK | \
|
||||
GDK_BUTTON_PRESS_MASK | \
|
||||
GDK_BUTTON_RELEASE_MASK | \
|
||||
GDK_BUTTON1_MOTION_MASK | \
|
||||
GDK_POINTER_MOTION_HINT_MASK
|
||||
|
||||
|
||||
typedef struct {
|
||||
gint run;
|
||||
} fpInterface;
|
||||
|
||||
typedef double hsv;
|
||||
|
||||
typedef struct {
|
||||
gint width;
|
||||
gint height;
|
||||
guchar *rgb;
|
||||
hsv *hsv;
|
||||
guchar *mask;
|
||||
} ReducedImage;
|
||||
|
||||
typedef enum {
|
||||
SHADOWS,
|
||||
MIDTONES,
|
||||
HIGHLIGHTS,
|
||||
INTENSITIES
|
||||
}FP_Intensity;
|
||||
|
||||
enum {
|
||||
NONEATALL =0,
|
||||
CURRENT =1,
|
||||
HUE =2,
|
||||
SATURATION =4,
|
||||
VALUE =8
|
||||
};
|
||||
|
||||
|
||||
enum {
|
||||
RED,
|
||||
GREEN,
|
||||
BLUE,
|
||||
CYAN,
|
||||
YELLOW,
|
||||
MAGENTA,
|
||||
ALL_PRIMARY
|
||||
};
|
||||
|
||||
enum {
|
||||
DOWN = -1,
|
||||
UP = 1
|
||||
};
|
||||
|
||||
enum {
|
||||
BY_HUE,
|
||||
BY_SAT,
|
||||
BY_VAL,
|
||||
JUDGE_BY
|
||||
};
|
||||
|
||||
|
||||
typedef struct {
|
||||
GtkWidget *window;
|
||||
GtkWidget *shadowsEntry;
|
||||
GtkWidget *midtonesEntry;
|
||||
GtkWidget *rangePreview;
|
||||
GtkWidget *aliasingPreview;
|
||||
GtkObject *aliasingData;
|
||||
GtkWidget *aliasingGraph;
|
||||
} AdvancedWindow;
|
||||
|
||||
|
||||
typedef struct {
|
||||
int Color;
|
||||
float Rough;
|
||||
GtkWidget *roughnessScale;
|
||||
float Alias;
|
||||
GtkWidget *aliasingScale;
|
||||
float PreviewSize;
|
||||
GtkWidget *previewSizeScale;
|
||||
FP_Intensity Range;
|
||||
gint ValueBy;
|
||||
gint SlctnOnly;
|
||||
gint RealTime;
|
||||
guchar Offset;
|
||||
guchar VisibleFrames;
|
||||
guchar Cutoffs[INTENSITIES];
|
||||
gint Touched[JUDGE_BY];
|
||||
gint redAdj[JUDGE_BY][256];
|
||||
gint blueAdj[JUDGE_BY][256];
|
||||
gint greenAdj[JUDGE_BY][256];
|
||||
gint satAdj[JUDGE_BY][256];
|
||||
GtkWidget *rangeLabels[12];
|
||||
}FP_Params;
|
||||
|
||||
GtkWidget *fp_create_bna(void);
|
||||
GtkWidget *fp_create_rough(void);
|
||||
GtkWidget *fp_create_range(void);
|
||||
GtkWidget *fp_create_circle_palette(void);
|
||||
GtkWidget *fp_create_lnd(void);
|
||||
GtkWidget *fp_create_show(void);
|
||||
GtkWidget *fp_create_msnls();
|
||||
GtkWidget *fp_create_frame_select();
|
||||
GtkWidget *fp_create_pixels_select_by();
|
||||
|
||||
void fp_show_hide_frame(GtkWidget *button,
|
||||
GtkWidget *frame);
|
||||
|
||||
|
||||
ReducedImage *Reduce_The_Image (GDrawable *,
|
||||
GDrawable *,
|
||||
gint,
|
||||
gint);
|
||||
|
||||
void fp_render_preview (GtkWidget *,
|
||||
gint,
|
||||
gint );
|
||||
|
||||
void Update_Current_FP (gint,
|
||||
gint );
|
||||
|
||||
void fp_Create_Nudge (gint* );
|
||||
|
||||
gint fp_dialog (void);
|
||||
gint fp_advanced_dialog (void);
|
||||
|
||||
void fp_advanced_call (void);
|
||||
|
||||
void fp_entire_image (GtkWidget *,
|
||||
gpointer );
|
||||
void fp_selection_only (GtkWidget *,
|
||||
gpointer );
|
||||
|
||||
void fp_selection_in_context (GtkWidget *,
|
||||
gpointer );
|
||||
|
||||
void selectionMade (GtkWidget *,
|
||||
gpointer );
|
||||
void fp_close_callback (GtkWidget *,
|
||||
gpointer );
|
||||
void fp_ok_callback (GtkWidget *,
|
||||
gpointer );
|
||||
void fp_scale_update (GtkAdjustment *,
|
||||
float* );
|
||||
void fp_change_current_range (GtkAdjustment*,
|
||||
gint* );
|
||||
void fp_change_current_pixels_by (GtkWidget *,
|
||||
gint *);
|
||||
void resetFilterPacks (void);
|
||||
|
||||
void update_range_labels (void);
|
||||
|
||||
void fp_create_smoothness_graph (GtkWidget* );
|
||||
|
||||
void fp_range_preview_spill (GtkWidget*,
|
||||
gint );
|
||||
|
||||
void Create_A_Preview (GtkWidget **,
|
||||
GtkWidget **,
|
||||
int,
|
||||
int );
|
||||
|
||||
void Create_A_Table_Entry (GtkWidget **,
|
||||
GtkWidget *,
|
||||
char *);
|
||||
|
||||
GSList* Button_In_A_Box (GtkWidget *,
|
||||
GSList *,
|
||||
guchar *,
|
||||
GtkSignalFunc,
|
||||
gpointer,
|
||||
int );
|
||||
|
||||
void Check_Button_In_A_Box (GtkWidget *,
|
||||
guchar *label,
|
||||
GtkSignalFunc func,
|
||||
gpointer data,
|
||||
int clicked);
|
||||
|
||||
void Adjust_Preview_Sizes (int width,
|
||||
int height );
|
||||
void refreshPreviews (int);
|
||||
void initializeFilterPacks (void);
|
||||
|
||||
void fp (GDrawable *drawable);
|
||||
void fp_row (const guchar *src_row,
|
||||
guchar *dest_row,
|
||||
gint row,
|
||||
gint row_width,
|
||||
gint bytes);
|
||||
|
||||
void draw_slider (GdkWindow *window,
|
||||
GdkGC *border_gc,
|
||||
GdkGC *fill_gc,
|
||||
int xpos);
|
||||
gint FP_Range_Change_Events (GtkWidget *,
|
||||
GdkEvent *,
|
||||
FP_Params *);
|
||||
|
||||
void As_You_Drag (GtkWidget *button);
|
||||
void preview_size_scale_update (GtkAdjustment *adjustment,
|
||||
float *scale_val);
|
||||
void ErrorMessage (guchar *);
|
||||
|
||||
|
||||
void fp_advanced_ok();
|
|
@ -1,160 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <math.h>
|
||||
#include "gtk/gtk.h"
|
||||
#include "libgimp/gimp.h"
|
||||
#include "fp.h"
|
||||
#include "fp_hsv.h"
|
||||
|
||||
extern AdvancedWindow AW;
|
||||
extern FP_Params Current;
|
||||
|
||||
|
||||
extern gint nudgeArray[256];
|
||||
|
||||
void
|
||||
draw_slider(GdkWindow *window,
|
||||
GdkGC *border_gc,
|
||||
GdkGC *fill_gc,
|
||||
int xpos)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < RANGE_HEIGHT; i++)
|
||||
gdk_draw_line(window, fill_gc,xpos-i/2, i,xpos+i/2,i);
|
||||
|
||||
gdk_draw_line(window, border_gc, xpos, 0,
|
||||
xpos - (RANGE_HEIGHT - 1) / 2, RANGE_HEIGHT - 1);
|
||||
|
||||
gdk_draw_line(window, border_gc, xpos, 0,
|
||||
xpos + (RANGE_HEIGHT - 1) / 2, RANGE_HEIGHT - 1);
|
||||
|
||||
gdk_draw_line(window, border_gc,xpos-(RANGE_HEIGHT-1)/2,RANGE_HEIGHT-1,
|
||||
xpos + (RANGE_HEIGHT-1)/2, RANGE_HEIGHT-1);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
draw_it(GtkWidget *widget)
|
||||
{
|
||||
draw_slider(AW.aliasingGraph->window,
|
||||
AW.aliasingGraph->style->black_gc,
|
||||
AW.aliasingGraph->style->dark_gc[GTK_STATE_NORMAL],
|
||||
Current.Cutoffs[SHADOWS]);
|
||||
|
||||
draw_slider(AW.aliasingGraph->window,
|
||||
AW.aliasingGraph->style->black_gc,
|
||||
AW.aliasingGraph->style->dark_gc[GTK_STATE_NORMAL],
|
||||
Current.Cutoffs[MIDTONES]);
|
||||
|
||||
draw_slider(AW.aliasingGraph->window,
|
||||
AW.aliasingGraph->style->black_gc,
|
||||
AW.aliasingGraph->style->dark_gc[GTK_STATE_NORMAL],
|
||||
Current.Offset);
|
||||
}
|
||||
|
||||
void
|
||||
slider_erase (GdkWindow *window,
|
||||
int xpos)
|
||||
{
|
||||
gdk_window_clear_area (window, xpos - (RANGE_HEIGHT - 1) / 2, 0,
|
||||
RANGE_HEIGHT, RANGE_HEIGHT);
|
||||
}
|
||||
|
||||
gint
|
||||
FP_Range_Change_Events (GtkWidget *widget,
|
||||
GdkEvent *event,
|
||||
FP_Params *current)
|
||||
{
|
||||
GdkEventButton *bevent;
|
||||
GdkEventMotion *mevent;
|
||||
gint shad, mid, offset, min;
|
||||
static guchar *new;
|
||||
gint x;
|
||||
|
||||
switch(event->type) {
|
||||
|
||||
case GDK_EXPOSE:
|
||||
draw_it(NULL);
|
||||
|
||||
case GDK_BUTTON_PRESS:
|
||||
bevent=(GdkEventButton *) event;
|
||||
|
||||
shad = abs(bevent->x - Current.Cutoffs[SHADOWS]);
|
||||
mid = abs(bevent->x - Current.Cutoffs[MIDTONES]);
|
||||
offset = abs(bevent->x - Current.Offset);
|
||||
|
||||
min= MIN(MIN(shad,mid),offset);
|
||||
|
||||
|
||||
if (bevent->x >0 && bevent->x<256) {
|
||||
if (min==shad)
|
||||
new = &Current.Cutoffs[SHADOWS];
|
||||
else if (min==mid)
|
||||
new = &Current.Cutoffs[MIDTONES];
|
||||
else
|
||||
new = &Current.Offset;
|
||||
|
||||
slider_erase(AW.aliasingGraph->window,*new);
|
||||
*new=bevent->x;
|
||||
}
|
||||
|
||||
draw_it(NULL);
|
||||
|
||||
if (Current.RealTime) {
|
||||
fp_range_preview_spill(AW.rangePreview,Current.ValueBy);
|
||||
update_range_labels();
|
||||
fp_create_smoothness_graph(AW.aliasingPreview);
|
||||
refreshPreviews(Current.VisibleFrames);
|
||||
}
|
||||
break;
|
||||
|
||||
case GDK_BUTTON_RELEASE:
|
||||
if (!Current.RealTime) {
|
||||
fp_range_preview_spill(AW.rangePreview,Current.ValueBy);
|
||||
update_range_labels();
|
||||
fp_create_smoothness_graph(AW.aliasingPreview);
|
||||
refreshPreviews(Current.VisibleFrames);
|
||||
}
|
||||
break;
|
||||
|
||||
case GDK_MOTION_NOTIFY:
|
||||
mevent= (GdkEventMotion *) event;
|
||||
gdk_window_get_pointer(widget->window, &x,NULL, NULL);
|
||||
|
||||
if (x>=0 && x<256) {
|
||||
slider_erase(AW.aliasingGraph->window,*new);
|
||||
*new=x;
|
||||
draw_it(NULL);
|
||||
if (Current.RealTime) {
|
||||
fp_range_preview_spill(AW.rangePreview,Current.ValueBy);
|
||||
update_range_labels();
|
||||
fp_create_smoothness_graph(AW.aliasingPreview);
|
||||
refreshPreviews(Current.VisibleFrames);
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
update_range_labels()
|
||||
{
|
||||
guchar buffer[3];
|
||||
|
||||
gtk_label_set(GTK_LABEL(Current.rangeLabels[1]),"0");
|
||||
|
||||
sprintf(buffer,"%d",Current.Cutoffs[SHADOWS]);
|
||||
gtk_label_set(GTK_LABEL(Current.rangeLabels[3]),buffer);
|
||||
gtk_label_set(GTK_LABEL(Current.rangeLabels[5]),buffer);
|
||||
|
||||
sprintf(buffer,"%d",Current.Cutoffs[MIDTONES]);
|
||||
gtk_label_set(GTK_LABEL(Current.rangeLabels[7]),buffer);
|
||||
gtk_label_set(GTK_LABEL(Current.rangeLabels[9]),buffer);
|
||||
|
||||
gtk_label_set(GTK_LABEL(Current.rangeLabels[11]),"255");
|
||||
}
|
1101
plug-ins/fp/fp_gtk.c
1101
plug-ins/fp/fp_gtk.c
File diff suppressed because it is too large
Load Diff
|
@ -1,93 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <math.h>
|
||||
#include "libgimp/gimp.h"
|
||||
|
||||
typedef double hsv;
|
||||
void rgb_to_hsv (hsv r,
|
||||
hsv g,
|
||||
hsv b,
|
||||
hsv *h,
|
||||
hsv *s,
|
||||
hsv *l)
|
||||
{
|
||||
hsv v;
|
||||
hsv m;
|
||||
hsv vm;
|
||||
hsv r2, g2, b2;
|
||||
|
||||
v = MAX(r,g);
|
||||
v = MAX(v,b);
|
||||
m = MIN(r,g);
|
||||
m = MIN(m,b);
|
||||
|
||||
if ((*l = (m + v) / 2.0) <= 0.0)
|
||||
{
|
||||
*s=*h=0;
|
||||
return;
|
||||
}
|
||||
if ((*s = vm = v - m) > 0.0)
|
||||
{
|
||||
*s /= (*l <= 0.5) ? (v + m ) :
|
||||
(2.0 - v - m) ;
|
||||
}
|
||||
else
|
||||
{
|
||||
*h=0;
|
||||
return;
|
||||
}
|
||||
|
||||
r2 = (v - r) / vm;
|
||||
g2 = (v - g) / vm;
|
||||
b2 = (v - b) / vm;
|
||||
|
||||
if (r == v)
|
||||
*h = (g == m ? 5.0 + b2 : 1.0 - g2);
|
||||
else if (g == v)
|
||||
*h = (b == m ? 1.0 + r2 : 3.0 - b2);
|
||||
else
|
||||
*h = (r == m ? 3.0 + g2 : 5.0 - r2);
|
||||
|
||||
*h /= 6;
|
||||
}
|
||||
|
||||
void hsv_to_rgb (hsv h,
|
||||
hsv sl,
|
||||
hsv l,
|
||||
hsv *r,
|
||||
hsv *g,
|
||||
hsv *b)
|
||||
{
|
||||
hsv v;
|
||||
|
||||
v = (l <= 0.5) ? (l * (1.0 + sl)) : (l + sl - l * sl);
|
||||
if (v <= 0)
|
||||
{
|
||||
*r = *g = *b = 0.0;
|
||||
}
|
||||
else
|
||||
{
|
||||
hsv m;
|
||||
hsv sv;
|
||||
gint sextant;
|
||||
hsv fract, vsf, mid1, mid2;
|
||||
|
||||
m = l + l - v;
|
||||
sv = (v - m ) / v;
|
||||
h *= 6.0;
|
||||
sextant = h;
|
||||
fract = h - sextant;
|
||||
vsf = v * sv * fract;
|
||||
mid1 = m + vsf;
|
||||
mid2 = v - vsf;
|
||||
switch (sextant)
|
||||
{
|
||||
case 0: *r = v; *g = mid1; *b = m; break;
|
||||
case 1: *r = mid2; *g = v; *b = m; break;
|
||||
case 2: *r = m; *g = v; *b = mid1; break;
|
||||
case 3: *r = m; *g = mid2; *b = v; break;
|
||||
case 4: *r = mid1; *g = m; *b = v; break;
|
||||
case 5: *r = v; *g = m; *b = mid2; break;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
void rgb_to_hsv (hsv r,
|
||||
hsv g,
|
||||
hsv b,
|
||||
hsv *h,
|
||||
hsv *s,
|
||||
hsv *l);
|
||||
|
||||
void hsv_to_rgb (hsv h,
|
||||
hsv sl,
|
||||
hsv l,
|
||||
hsv *r,
|
||||
hsv *g,
|
||||
hsv *b);
|
|
@ -1,394 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <math.h>
|
||||
#include "gtk/gtk.h"
|
||||
#include "libgimp/gimp.h"
|
||||
#include "fp.h"
|
||||
#include "fp_hsv.h"
|
||||
|
||||
extern FP_Params Current;
|
||||
|
||||
extern GDrawable *drawable, *mask;
|
||||
extern ReducedImage *reduced;
|
||||
|
||||
extern gint nudgeArray[256];
|
||||
|
||||
gint colorSign[3][ALL_PRIMARY]=
|
||||
{{1,-1,-1,-1,1,1},{-1,1,-1,1,1,-1},{-1,-1,1,1,-1,1}};
|
||||
|
||||
|
||||
void initializeFilterPacks()
|
||||
{
|
||||
gint i, j;
|
||||
for (i=0; i<256; i++)
|
||||
for (j=BY_HUE; j<JUDGE_BY; j++) {
|
||||
Current.redAdj [j][i]=0;
|
||||
Current.greenAdj [j][i]=0;
|
||||
Current.blueAdj [j][i]=0;
|
||||
Current.satAdj [j][i]=0;
|
||||
}
|
||||
}
|
||||
|
||||
void resetFilterPacks()
|
||||
{
|
||||
initializeFilterPacks();
|
||||
refreshPreviews(Current.VisibleFrames);
|
||||
}
|
||||
|
||||
ReducedImage *Reduce_The_Image(GDrawable *drawable,
|
||||
GDrawable *mask,
|
||||
gint LongerSize,
|
||||
gint Slctn)
|
||||
{
|
||||
gint width;
|
||||
gint height;
|
||||
gint bytes=drawable->bpp;
|
||||
gint RH, RW;
|
||||
ReducedImage *temp=(ReducedImage *)malloc(sizeof(ReducedImage));
|
||||
guchar *tempRGB, *src_row, *tempmask, *src_mask_row,R,G,B;
|
||||
gint i, j, whichcol, whichrow, x1, x2, y1, y2;
|
||||
GPixelRgn srcPR, srcMask;
|
||||
gint NoSelectionMade=TRUE;
|
||||
hsv *tempHSV, H, S, V;
|
||||
|
||||
gimp_drawable_mask_bounds (drawable->id, &x1, &y1, &x2, &y2);
|
||||
width = x2-x1;
|
||||
height = y2-y1;
|
||||
|
||||
if (width != drawable->width && height != drawable->height)
|
||||
NoSelectionMade=FALSE;
|
||||
|
||||
if (Slctn==0) {
|
||||
x1=0;
|
||||
x2=drawable->width;
|
||||
y1=0;
|
||||
y2=drawable->height;
|
||||
}
|
||||
|
||||
if (Slctn==2) {
|
||||
x1=MAX(0, x1-width/2.0);
|
||||
x2=MIN(drawable->width, x2+width/2.0);
|
||||
y1=MAX(0, y1-height/2.0);
|
||||
y2=MIN(drawable->height, y2+height/2.0);
|
||||
}
|
||||
|
||||
width = x2-x1;
|
||||
height = y2-y1;
|
||||
|
||||
if (width>height) {
|
||||
RW=LongerSize;
|
||||
RH=(float) height * (float) LongerSize/ (float) width;
|
||||
}
|
||||
else {
|
||||
RH=LongerSize;
|
||||
RW=(float)width * (float) LongerSize/ (float) height;
|
||||
}
|
||||
|
||||
tempRGB = (guchar *) malloc(RW*RH*bytes);
|
||||
tempHSV = (hsv *) malloc(RW*RH*bytes*sizeof(hsv));
|
||||
tempmask = (guchar *) malloc(RW*RH);
|
||||
|
||||
gimp_pixel_rgn_init (&srcPR, drawable, x1, y1, width, height, FALSE, FALSE);
|
||||
gimp_pixel_rgn_init (&srcMask, mask, x1, y1, width, height, FALSE, FALSE);
|
||||
|
||||
src_row = (guchar *) malloc (width*bytes);
|
||||
src_mask_row = (guchar *) malloc (width*bytes);
|
||||
|
||||
for (i=0; i<RH; i++) {
|
||||
whichrow=(float)i*(float)height/(float)RH;
|
||||
gimp_pixel_rgn_get_row (&srcPR, src_row, x1, y1+whichrow, width);
|
||||
gimp_pixel_rgn_get_row (&srcMask, src_mask_row, x1, y1+whichrow, width);
|
||||
|
||||
for (j=0; j<RW; j++) {
|
||||
whichcol=(float)j*(float)width/(float)RW;
|
||||
|
||||
if (NoSelectionMade)
|
||||
tempmask[i*RW+j]=255;
|
||||
else
|
||||
tempmask[i*RW+j]=src_mask_row[whichcol];
|
||||
|
||||
R=src_row[whichcol*bytes+0];
|
||||
G=src_row[whichcol*bytes+1];
|
||||
B=src_row[whichcol*bytes+2];
|
||||
|
||||
rgb_to_hsv(R/255.0,G/255.0,B/255.0,&H,&S,&V);
|
||||
|
||||
tempRGB[i*RW*bytes+j*bytes+0]=R;
|
||||
tempRGB[i*RW*bytes+j*bytes+1]=G;
|
||||
tempRGB[i*RW*bytes+j*bytes+2]=B;
|
||||
|
||||
tempHSV[i*RW*bytes+j*bytes+0]=H;
|
||||
tempHSV[i*RW*bytes+j*bytes+1]=S;
|
||||
tempHSV[i*RW*bytes+j*bytes+2]=V;
|
||||
|
||||
if (bytes==4)
|
||||
tempRGB[i*RW*bytes+j*bytes+3]=src_row[whichcol*bytes+3];
|
||||
|
||||
}
|
||||
}
|
||||
temp->width=RW;
|
||||
temp->height=RH;
|
||||
temp->rgb=tempRGB;
|
||||
temp->hsv=tempHSV;
|
||||
temp->mask=tempmask;
|
||||
return temp;
|
||||
}
|
||||
|
||||
/*************************************************************/
|
||||
/************** The Preview Function *************************/
|
||||
void
|
||||
fp_render_preview(GtkWidget *preview,
|
||||
gint changewhat,
|
||||
gint changewhich)
|
||||
{
|
||||
guchar *a;
|
||||
gint Inten, bytes=drawable->bpp;
|
||||
gint i, j, k, nudge, M, m, middle,JudgeBy;
|
||||
float partial;
|
||||
gint RW=reduced->width;
|
||||
gint RH=reduced->height;
|
||||
gint backupP[3], P[3], tempSat[JUDGE_BY][256];
|
||||
|
||||
a =(guchar *) malloc(bytes*RW);
|
||||
|
||||
if (changewhat==SATURATION)
|
||||
for (k=0; k<256; k++) {
|
||||
for (JudgeBy=BY_HUE; JudgeBy<JUDGE_BY; JudgeBy++)
|
||||
tempSat[JudgeBy][k]=0;
|
||||
tempSat[Current.ValueBy][k] += changewhich*nudgeArray[(k+Current.Offset)%256];
|
||||
}
|
||||
|
||||
for (i=0; i<RH; i++) {
|
||||
for (j=0; j<RW; j++) {
|
||||
|
||||
backupP[0] = P[0] = (int) reduced->rgb[i*RW*bytes + j*bytes + 0];
|
||||
backupP[1] = P[1] = (int) reduced->rgb[i*RW*bytes + j*bytes + 1];
|
||||
backupP[2] = P[2] = (int) reduced->rgb[i*RW*bytes + j*bytes + 2];
|
||||
|
||||
m = MIN(MIN(P[0],P[1]),P[2]);
|
||||
M = MAX(MAX(P[0],P[1]),P[2]);
|
||||
middle=(M+m)/2;
|
||||
for (k=0; k<3; k++)
|
||||
if (P[k]!=m && P[k]!=M) middle=P[k];
|
||||
|
||||
partial = reduced->mask[i*RW+j]/255.0;
|
||||
|
||||
for (JudgeBy=BY_HUE; JudgeBy<JUDGE_BY; JudgeBy++) {
|
||||
if (!Current.Touched[JudgeBy]) continue;
|
||||
|
||||
Inten = reduced->hsv[i*RW*bytes + j*bytes + JudgeBy]*255.0;
|
||||
|
||||
/*DO SATURATION FIRST*/
|
||||
if (changewhat != NONEATALL) {
|
||||
if (M!=m)
|
||||
for (k=0; k<3; k++)
|
||||
if (backupP[k] == M)
|
||||
P[k] = MAX(P[k]+partial*Current.satAdj[JudgeBy][Inten],middle);
|
||||
else if (backupP[k] == m)
|
||||
P[k] = MIN(P[k]-partial*Current.satAdj[JudgeBy][Inten],middle);
|
||||
|
||||
P[0] += partial*Current.redAdj[JudgeBy][Inten];
|
||||
P[1] += partial*Current.greenAdj[JudgeBy][Inten];
|
||||
P[2] += partial*Current.blueAdj[JudgeBy][Inten];
|
||||
}
|
||||
}
|
||||
|
||||
Inten = reduced->hsv[i*RW*bytes + j*bytes + Current.ValueBy]*255.0;
|
||||
nudge = partial*nudgeArray[(Inten+Current.Offset)%256];
|
||||
|
||||
switch (changewhat) {
|
||||
case HUE:
|
||||
P[0] += colorSign[RED][changewhich] * nudge;
|
||||
P[1] += colorSign[GREEN][changewhich] * nudge;
|
||||
P[2] += colorSign[BLUE][changewhich] * nudge;
|
||||
break;
|
||||
|
||||
case SATURATION:
|
||||
for (JudgeBy=BY_HUE; JudgeBy<JUDGE_BY; JudgeBy++)
|
||||
for (k=0; k<3; k++)
|
||||
if (M!=m)
|
||||
if (backupP[k] == M)
|
||||
P[k] = MAX(P[k]+
|
||||
partial*tempSat[JudgeBy][Inten],middle);
|
||||
else if (backupP[k] == m)
|
||||
P[k] = MIN(P[k]-
|
||||
partial*tempSat[JudgeBy][Inten],middle);
|
||||
break;
|
||||
|
||||
case VALUE:
|
||||
P[0] += changewhich * nudge;
|
||||
P[1] += changewhich * nudge;
|
||||
P[2] += changewhich * nudge;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
a[j*3+0] = MAX(0,MIN(P[0], 255));
|
||||
a[j*3+1] = MAX(0,MIN(P[1], 255));
|
||||
a[j*3+2] = MAX(0,MIN(P[2], 255));
|
||||
|
||||
}
|
||||
gtk_preview_draw_row( GTK_PREVIEW(preview),a,0,i,RW);
|
||||
}
|
||||
|
||||
free(a);
|
||||
gtk_widget_draw(preview,NULL);
|
||||
gdk_flush();
|
||||
}
|
||||
|
||||
void
|
||||
Update_Current_FP (gint changewhat,
|
||||
gint changewhich)
|
||||
{
|
||||
int i, nudge;
|
||||
|
||||
for (i=0; i<256; i++) {
|
||||
|
||||
fp_Create_Nudge(nudgeArray);
|
||||
nudge=nudgeArray[(i+Current.Offset)%256];
|
||||
|
||||
switch (changewhat) {
|
||||
case HUE:
|
||||
Current.redAdj[Current.ValueBy][i] +=
|
||||
colorSign[RED][changewhich] * nudge;
|
||||
|
||||
Current.greenAdj[Current.ValueBy][i] +=
|
||||
colorSign[GREEN][changewhich] * nudge;
|
||||
|
||||
Current.blueAdj[Current.ValueBy][i] +=
|
||||
colorSign[BLUE][changewhich] * nudge;
|
||||
break;
|
||||
|
||||
case SATURATION:
|
||||
Current.satAdj[Current.ValueBy][i] += changewhich*nudge;
|
||||
break;
|
||||
|
||||
case VALUE:
|
||||
Current.redAdj[Current.ValueBy][i] += changewhich * nudge;
|
||||
Current.greenAdj[Current.ValueBy][i] += changewhich * nudge;
|
||||
Current.blueAdj[Current.ValueBy][i] += changewhich * nudge;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
} /* switch */
|
||||
|
||||
} /* for */
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
fp_create_smoothness_graph (GtkWidget *preview)
|
||||
{
|
||||
guchar data[256*3];
|
||||
gint nArray[256];
|
||||
int i, j, toBeBlack;
|
||||
|
||||
fp_Create_Nudge(nArray);
|
||||
|
||||
for (i=0; i<MAX_ROUGHNESS; i++)
|
||||
{
|
||||
int coor=MAX_ROUGHNESS-i;
|
||||
for (j=0; j<256; j++) {
|
||||
data[3*j+0]=255;
|
||||
data[3*j+1]=255;
|
||||
data[3*j+2]=255;
|
||||
if (!(i%(MAX_ROUGHNESS/4))) {
|
||||
data[3*j+0]=255;
|
||||
data[3*j+1]=128;
|
||||
data[3*j+2]=128;
|
||||
}
|
||||
if (!((j+1)%32)) {
|
||||
data[3*j+0]=255;
|
||||
data[3*j+1]=128;
|
||||
data[3*j+2]=128;
|
||||
}
|
||||
toBeBlack=0;
|
||||
if (nArray[j]==coor) toBeBlack=1;
|
||||
|
||||
if (j<255) {
|
||||
int jump=abs(nArray[j]-nArray[j+1]);
|
||||
if ( abs(coor-nArray[j]) < jump
|
||||
&& abs(coor-nArray[j+1]) < jump)
|
||||
toBeBlack=1;
|
||||
}
|
||||
if (toBeBlack) {
|
||||
data[3*j+0]=0;
|
||||
data[3*j+1]=0;
|
||||
data[3*j+2]=0;
|
||||
}
|
||||
}
|
||||
gtk_preview_draw_row( GTK_PREVIEW(preview),data,0,i,256);
|
||||
}
|
||||
gtk_widget_draw(preview,NULL);
|
||||
gdk_flush();
|
||||
}
|
||||
|
||||
void
|
||||
fp_range_preview_spill(GtkWidget *preview, int type)
|
||||
{
|
||||
guchar data[256*3];
|
||||
int i, j;
|
||||
hsv R,G,B;
|
||||
|
||||
for (i=0; i<RANGE_HEIGHT; i++) {
|
||||
for (j=0; j<256; j++)
|
||||
if (!((j+1)%32)) {
|
||||
data[3*j+0]=255;
|
||||
data[3*j+1]=128;
|
||||
data[3*j+2]=128;
|
||||
}
|
||||
else
|
||||
switch (type) {
|
||||
case BY_VAL:
|
||||
data[3*j+0]=j-Current.Offset;
|
||||
data[3*j+1]=j-Current.Offset;
|
||||
data[3*j+2]=j-Current.Offset;
|
||||
break;
|
||||
case BY_HUE:
|
||||
hsv_to_rgb((hsv)((j-Current.Offset+256)%256)/255.0, 1.0, .5, &R, &G, &B);
|
||||
data[3*j+0]=R*255;
|
||||
data[3*j+1]=G*255;
|
||||
data[3*j+2]=B*255;
|
||||
break;
|
||||
case BY_SAT:
|
||||
hsv_to_rgb(.5,(hsv)((j-(gint)Current.Offset+256)%256)/255.0,.5,&R,&G,&B);
|
||||
data[3*j+0]=R*255;
|
||||
data[3*j+1]=G*255;
|
||||
data[3*j+2]=B*255;
|
||||
break;
|
||||
}
|
||||
gtk_preview_draw_row( GTK_PREVIEW(preview),data,0,i,256);
|
||||
}
|
||||
gtk_widget_draw(preview,NULL);
|
||||
gdk_flush();
|
||||
}
|
||||
|
||||
|
||||
void fp_Create_Nudge(gint *adjArray)
|
||||
{
|
||||
int left, right, middle,i;
|
||||
/* The following function was determined by trial and error */
|
||||
double Steepness=pow(1-Current.Alias,4)*.8;
|
||||
|
||||
left = (Current.Range == SHADOWS) ? 0 : Current.Cutoffs[Current.Range-1];
|
||||
right = Current.Cutoffs[Current.Range];
|
||||
middle = (left + right)/2;
|
||||
|
||||
if (Current.Alias!=0)
|
||||
for (i=0; i<256; i++)
|
||||
if (i<=middle)
|
||||
adjArray[i] = MAX_ROUGHNESS *
|
||||
Current.Rough*(1+tanh(Steepness*(i-left)))/2;
|
||||
else
|
||||
adjArray[i] = MAX_ROUGHNESS *
|
||||
Current.Rough*(1+tanh(Steepness*(right-i)))/2;
|
||||
else
|
||||
for (i=0; i<256; i++)
|
||||
if (left<=i && i<=right)
|
||||
adjArray[i] = MAX_ROUGHNESS * Current.Rough;
|
||||
else
|
||||
adjArray[i] = 0;
|
||||
}
|
|
@ -1,6 +0,0 @@
|
|||
Makefile.in
|
||||
Makefile
|
||||
.deps
|
||||
_libs
|
||||
.libs
|
||||
lic
|
|
@ -1,39 +0,0 @@
|
|||
## Process this file with automake to produce Makefile.in
|
||||
|
||||
pluginlibdir = $(gimpplugindir)/plug-ins
|
||||
|
||||
pluginlib_PROGRAMS = lic
|
||||
|
||||
lic_SOURCES = \
|
||||
lic.c
|
||||
|
||||
INCLUDES = \
|
||||
$(X_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
-I$(includedir)
|
||||
|
||||
LDADD = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la \
|
||||
$(X_LIBS) \
|
||||
\
|
||||
-lc
|
||||
|
||||
DEPS = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la
|
||||
|
||||
lic_DEPENDENCIES = $(DEPS)
|
||||
|
||||
.PHONY: files
|
||||
|
||||
files:
|
||||
@files=`ls $(DISTFILES) 2> /dev/null`; for p in $$files; do \
|
||||
echo $$p; \
|
||||
done
|
||||
@for subdir in $(SUBDIRS); do \
|
||||
files=`cd $$subdir; $(MAKE) files | grep -v "make\[[1-9]\]"`; \
|
||||
for file in $$files; do \
|
||||
echo $$subdir/$$file; \
|
||||
done; \
|
||||
done
|
1441
plug-ins/lic/lic.c
1441
plug-ins/lic/lic.c
File diff suppressed because it is too large
Load Diff
|
@ -1,6 +0,0 @@
|
|||
Makefile.in
|
||||
Makefile
|
||||
.deps
|
||||
_libs
|
||||
.libs
|
||||
mathmap
|
|
@ -1,38 +0,0 @@
|
|||
## Process this file with automake to produce Makefile.in
|
||||
|
||||
pluginlibdir = $(gimpplugindir)/plug-ins
|
||||
|
||||
pluginlib_PROGRAMS = #STD#
|
||||
|
||||
#STD#_SOURCES = \
|
||||
#STD#.c
|
||||
|
||||
INCLUDES = \
|
||||
$(X_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
-I$(includedir)
|
||||
|
||||
LDADD = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la \
|
||||
$(X_LIBS) \
|
||||
-lc
|
||||
|
||||
DEPS = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la
|
||||
|
||||
#STD#_DEPENDENCIES = $(DEPS)
|
||||
|
||||
.PHONY: files
|
||||
|
||||
files:
|
||||
@files=`ls $(DISTFILES) 2> /dev/null`; for p in $$files; do \
|
||||
echo $$p; \
|
||||
done
|
||||
@for subdir in $(SUBDIRS); do \
|
||||
files=`cd $$subdir; $(MAKE) files | grep -v "make\[[1-9]\]"`; \
|
||||
for file in $$files; do \
|
||||
echo $$subdir/$$file; \
|
||||
done; \
|
||||
done
|
|
@ -1,25 +0,0 @@
|
|||
CFLAGS=-D_GIMP -Wall -O3
|
||||
CC = gcc
|
||||
|
||||
OBJECTS=mathmap.o builtins.o exprtree.o parser.o scanner.o postfix.o vars.o
|
||||
|
||||
mathmap : $(OBJECTS)
|
||||
$(CC) -o mathmap -lglib -lgdk -lgtk -lgimp -lm $(OBJECTS)
|
||||
|
||||
%.o : %.c
|
||||
$(CC) $(CFLAGS) -c $<
|
||||
|
||||
parser.c : parser.y
|
||||
bison -d parser.y
|
||||
mv parser.tab.c parser.c
|
||||
mv parser.tab.h parser.h
|
||||
|
||||
scanner.c : scanner.fl
|
||||
flex scanner.fl
|
||||
mv lex.yy.c scanner.c
|
||||
|
||||
install : mathmap
|
||||
cp mathmap $(HOME)/.gimp/plug-ins/
|
||||
|
||||
clean :
|
||||
rm -f *~ *.o mathmap scanner.c parser.[ch]
|
|
@ -1,801 +0,0 @@
|
|||
#include <math.h>
|
||||
#include <string.h>
|
||||
#ifdef _GIMP
|
||||
#include <stdlib.h>
|
||||
#else
|
||||
#include <libc.h>
|
||||
#endif
|
||||
|
||||
#include "builtins.h"
|
||||
|
||||
extern int imageWidth,
|
||||
imageHeight,
|
||||
inputBPP;
|
||||
extern double middleX,
|
||||
middleY;
|
||||
extern unsigned char *imageData;
|
||||
extern double stack[];
|
||||
extern int stackp;
|
||||
extern int intersamplingEnabled,
|
||||
oversamplingEnabled;
|
||||
|
||||
builtin *firstBuiltin = 0;
|
||||
|
||||
double
|
||||
color_to_double (unsigned int red, unsigned int green, unsigned int blue, unsigned int alpha)
|
||||
{
|
||||
double val;
|
||||
|
||||
*(unsigned int*)&val = (alpha << 24) | (red << 16) | (green << 8) | blue;
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
double
|
||||
pixel_to_double (unsigned char *pixel)
|
||||
{
|
||||
if (inputBPP == 1)
|
||||
return color_to_double(pixel[0], pixel[0], pixel[0], 255);
|
||||
else if (inputBPP == 2)
|
||||
return color_to_double(pixel[0], pixel[0], pixel[0], pixel[1]);
|
||||
else if (inputBPP == 3)
|
||||
return color_to_double(pixel[0], pixel[1], pixel[2], 255);
|
||||
else
|
||||
return color_to_double(pixel[0], pixel[1], pixel[2], pixel[3]);
|
||||
}
|
||||
|
||||
void
|
||||
double_to_color (double val, unsigned int *red, unsigned int *green,
|
||||
unsigned int *blue, unsigned int *alpha)
|
||||
{
|
||||
unsigned int color = *(unsigned int*)&val;
|
||||
|
||||
*alpha = color >> 24;
|
||||
*red = (color >> 16) & 0xff;
|
||||
*green = (color >> 8) & 0xff;
|
||||
*blue = color & 0xff;
|
||||
}
|
||||
|
||||
unsigned int
|
||||
alpha_component (double val)
|
||||
{
|
||||
unsigned int color = *(unsigned int*)&val;
|
||||
|
||||
return color >> 24;
|
||||
}
|
||||
|
||||
unsigned int
|
||||
red_component (double val)
|
||||
{
|
||||
unsigned int color = *(unsigned int*)&val;
|
||||
|
||||
return (color >> 16) & 0xff;
|
||||
}
|
||||
|
||||
unsigned int
|
||||
green_component (double val)
|
||||
{
|
||||
unsigned int color = *(unsigned int*)&val;
|
||||
|
||||
return (color >> 8) & 0xff;
|
||||
}
|
||||
|
||||
unsigned int
|
||||
blue_component (double val)
|
||||
{
|
||||
unsigned int color = *(unsigned int*)&val;
|
||||
|
||||
return color & 0xff;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_sin (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = sin(stack[stackp - 1] * M_PI / 180.0);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_cos (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = cos(stack[stackp - 1] * M_PI / 180.0);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_tan (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = tan(stack[stackp - 1] * M_PI / 180.0);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_asin (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = asin(stack[stackp - 1]) * 180.0 / M_PI;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_acos (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = acos(stack[stackp - 1]) * 180.0 / M_PI;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_atan (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = atan(stack[stackp - 1]) * 180.0 / M_PI;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_pow (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = pow(stack[stackp - 2], stack[stackp - 1]);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_abs (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = fabs(stack[stackp - 1]);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_floor (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = floor(stack[stackp - 1]);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_sign (void *arg)
|
||||
{
|
||||
if (stack[stackp - 1] < 0)
|
||||
stack[stackp - 1] = -1.0;
|
||||
else if (stack[stackp - 1] > 0)
|
||||
stack[stackp - 1] = 1.0;
|
||||
else
|
||||
stack[stackp - 1] = 0.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_min (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] >= stack[stackp - 1])
|
||||
stack[stackp - 2] = stack[stackp - 1];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_max (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] <= stack[stackp - 1])
|
||||
stack[stackp - 2] = stack[stackp - 1];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_not (void *arg)
|
||||
{
|
||||
if (stack[stackp - 1] != 0.0)
|
||||
stack[stackp - 1] = 0.0;
|
||||
else
|
||||
stack[stackp - 1] = 1.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_or (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] || stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_and (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] && stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_equal (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] == stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_less (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] < stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_greater (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] > stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_lessequal (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] <= stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_greaterequal (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] >= stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_notequal (void *arg)
|
||||
{
|
||||
if (stack[stackp - 2] != stack[stackp - 1])
|
||||
stack[stackp - 2] = 1.0;
|
||||
else
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_inintv (void *arg)
|
||||
{
|
||||
if (stack[stackp - 3] >= stack[stackp - 2] && stack[stackp - 3] <= stack[stackp - 1])
|
||||
stack[stackp - 3] = 1.0;
|
||||
else
|
||||
stack[stackp - 3] = 0.0;
|
||||
stackp -= 2;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_rand (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = (random() / (double)0x7fffffff)
|
||||
* (stack[stackp - 1] - stack[stackp - 2]) + stack[stackp - 2];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
#ifdef _GIMP
|
||||
|
||||
void mathmap_get_pixel (int x, int y, unsigned char *pixel);
|
||||
|
||||
extern int originX,
|
||||
originY,
|
||||
wholeImageWidth,
|
||||
wholeImageHeight;
|
||||
|
||||
void
|
||||
builtin_origValXY (void *arg)
|
||||
{
|
||||
double x = stack[stackp - 2],
|
||||
y = stack[stackp - 1];
|
||||
unsigned char pixel[4];
|
||||
|
||||
if (!oversamplingEnabled)
|
||||
{
|
||||
x += 0.5;
|
||||
y += 0.5;
|
||||
}
|
||||
|
||||
mathmap_get_pixel(floor(x + originX + middleX), floor(y + originY + middleY), pixel);
|
||||
|
||||
stack[stackp - 2] = pixel_to_double(pixel);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_origValXYIntersample (void *arg)
|
||||
{
|
||||
double x = stack[stackp - 2] + middleX + originX,
|
||||
y = stack[stackp - 1] + middleY + originY;
|
||||
int x1 = floor(x),
|
||||
x2 = x1 + 1,
|
||||
y1 = floor(y),
|
||||
y2 = y1 + 1;
|
||||
double x2fact = (x - x1),
|
||||
y2fact = (y - y1),
|
||||
x1fact = 1.0 - x2fact,
|
||||
y1fact = 1.0 - y2fact,
|
||||
p1fact = x1fact * y1fact,
|
||||
p2fact = x1fact * y2fact,
|
||||
p3fact = x2fact * y1fact,
|
||||
p4fact = x2fact * y2fact;
|
||||
static unsigned char blackPixel[4] = { 0, 0, 0, 0 };
|
||||
unsigned char pixel1a[4],
|
||||
pixel2a[4],
|
||||
pixel3a[4],
|
||||
pixel4a[4],
|
||||
resultPixel[4];
|
||||
unsigned char *pixel1 = pixel1a,
|
||||
*pixel2 = pixel2a,
|
||||
*pixel3 = pixel3a,
|
||||
*pixel4 = pixel4a;
|
||||
int i;
|
||||
|
||||
if (x1 < 0 || x1 >= wholeImageWidth || y1 < 0 || y1 >= wholeImageHeight)
|
||||
pixel1 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x1, y1, pixel1);
|
||||
|
||||
if (x1 < 0 || x1 >= wholeImageWidth || y2 < 0 || y2 >= wholeImageHeight)
|
||||
pixel2 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x1, y2, pixel2);
|
||||
|
||||
if (x2 < 0 || x2 >= wholeImageWidth || y1 < 0 || y1 >= wholeImageHeight)
|
||||
pixel3 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x2, y1, pixel3);
|
||||
|
||||
if (x2 < 0 || x2 >= wholeImageWidth || y2 < 0 || y2 >= wholeImageHeight)
|
||||
pixel4 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x2, y2, pixel4);
|
||||
|
||||
for (i = 0; i < inputBPP; ++i)
|
||||
resultPixel[i] = pixel1[i] * p1fact
|
||||
+ pixel2[i] * p2fact
|
||||
+ pixel3[i] * p3fact
|
||||
+ pixel4[i] * p4fact;
|
||||
|
||||
stack[stackp - 2] = pixel_to_double(resultPixel);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_origValRA (void *arg)
|
||||
{
|
||||
double x = cos(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleX,
|
||||
y = sin(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleY;
|
||||
unsigned char pixel[4];
|
||||
|
||||
if (!oversamplingEnabled)
|
||||
{
|
||||
x += 0.5;
|
||||
y += 0.5;
|
||||
}
|
||||
|
||||
mathmap_get_pixel(floor(x + originX), floor(y + originY), pixel);
|
||||
|
||||
stack[stackp - 2] = pixel_to_double(pixel);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_origValRAIntersample (void *arg)
|
||||
{
|
||||
double x = cos(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleX + originX,
|
||||
y = sin(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleY + originY;
|
||||
int x1 = floor(x),
|
||||
x2 = x1 + 1,
|
||||
y1 = floor(y),
|
||||
y2 = y1 + 1;
|
||||
double x2fact = (x - x1),
|
||||
y2fact = (y - y1),
|
||||
x1fact = 1.0 - x2fact,
|
||||
y1fact = 1.0 - y2fact,
|
||||
p1fact = x1fact * y1fact,
|
||||
p2fact = x1fact * y2fact,
|
||||
p3fact = x2fact * y1fact,
|
||||
p4fact = x2fact * y2fact;
|
||||
static unsigned char blackPixel[4] = { 0, 0, 0, 0 };
|
||||
unsigned char pixel1a[4],
|
||||
pixel2a[4],
|
||||
pixel3a[4],
|
||||
pixel4a[4],
|
||||
resultPixel[4];
|
||||
unsigned char *pixel1 = pixel1a,
|
||||
*pixel2 = pixel2a,
|
||||
*pixel3 = pixel3a,
|
||||
*pixel4 = pixel4a;
|
||||
int i;
|
||||
|
||||
if (x1 < 0 || x1 >= wholeImageWidth || y1 < 0 || y1 >= wholeImageHeight)
|
||||
pixel1 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x1, y1, pixel1);
|
||||
|
||||
if (x1 < 0 || x1 >= wholeImageWidth || y2 < 0 || y2 >= wholeImageHeight)
|
||||
pixel2 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x1, y2, pixel2);
|
||||
|
||||
if (x2 < 0 || x2 >= wholeImageWidth || y1 < 0 || y1 >= wholeImageHeight)
|
||||
pixel3 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x2, y1, pixel3);
|
||||
|
||||
if (x2 < 0 || x2 >= wholeImageWidth || y2 < 0 || y2 >= wholeImageHeight)
|
||||
pixel4 = blackPixel;
|
||||
else
|
||||
mathmap_get_pixel(x2, y2, pixel4);
|
||||
|
||||
for (i = 0; i < inputBPP; ++i)
|
||||
resultPixel[i] = pixel1[i] * p1fact
|
||||
+ pixel2[i] * p2fact
|
||||
+ pixel3[i] * p3fact
|
||||
+ pixel4[i] * p4fact;
|
||||
|
||||
stack[stackp - 2] = pixel_to_double(resultPixel);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
void
|
||||
builtin_origValXY (void *arg)
|
||||
{
|
||||
int x = stack[stackp - 2] + middleX,
|
||||
y = stack[stackp - 1] + middleY;
|
||||
unsigned char *pixel;
|
||||
|
||||
if (x < 0 || y < 0 || x >= imageWidth || y >= imageHeight)
|
||||
{
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
return;
|
||||
}
|
||||
|
||||
pixel = imageData + (y * imageWidth + x) * 3;
|
||||
|
||||
stack[stackp - 2] = color_to_double(pixel[0], pixel[1], pixel[2]);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_origValXYIntersample (void *arg)
|
||||
{
|
||||
double x = stack[stackp - 2] + middleX,
|
||||
y = stack[stackp - 1] + middleY;
|
||||
int x1 = floor(x),
|
||||
x2 = x1 + 1,
|
||||
y1 = floor(y),
|
||||
y2 = y1 + 1;
|
||||
double x2fact = (x - x1),
|
||||
y2fact = (y - y1),
|
||||
x1fact = 1.0 - x2fact,
|
||||
y1fact = 1.0 - y2fact,
|
||||
p1fact = x1fact * y1fact,
|
||||
p2fact = x1fact * y2fact,
|
||||
p3fact = x2fact * y1fact,
|
||||
p4fact = x2fact * y2fact;
|
||||
static unsigned char blackPixel[] = { 0, 0, 0 };
|
||||
unsigned char *pixel1,
|
||||
*pixel2,
|
||||
*pixel3,
|
||||
*pixel4;
|
||||
int red,
|
||||
green,
|
||||
blue;
|
||||
|
||||
if (x1 < 0 || x1 >= imageWidth || y1 < 0 || y1 >= imageHeight)
|
||||
pixel1 = blackPixel;
|
||||
else
|
||||
pixel1 = imageData + (y1 * imageWidth + x1) * 3;
|
||||
|
||||
if (x1 < 0 || x1 >= imageWidth || y2 < 0 || y2 >= imageHeight)
|
||||
pixel2 = blackPixel;
|
||||
else
|
||||
pixel2 = imageData + (y2 * imageWidth + x1) * 3;
|
||||
|
||||
if (x2 < 0 || x2 >= imageWidth || y1 < 0 || y1 >= imageHeight)
|
||||
pixel3 = blackPixel;
|
||||
else
|
||||
pixel3 = imageData + (y1 * imageWidth + x2) * 3;
|
||||
|
||||
if (x2 < 0 || x2 >= imageWidth || y2 < 0 || y2 >= imageHeight)
|
||||
pixel4 = blackPixel;
|
||||
else
|
||||
pixel4 = imageData + (y2 * imageWidth + x2) * 3;
|
||||
|
||||
red = pixel1[0] * p1fact + pixel2[0] * p2fact + pixel3[0] * p3fact + pixel4[0] * p4fact;
|
||||
green = pixel1[1] * p1fact + pixel2[1] * p2fact + pixel3[1] * p3fact + pixel4[1] * p4fact;
|
||||
blue = pixel1[2] * p1fact + pixel2[2] * p2fact + pixel3[2] * p3fact + pixel4[2] * p4fact;
|
||||
|
||||
stack[stackp - 2] = color_to_double(red, green, blue);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_origValRA (void *arg)
|
||||
{
|
||||
int x = cos(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleX,
|
||||
y = sin(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleY;
|
||||
unsigned char *pixel;
|
||||
|
||||
if (x < 0 || y < 0 || x >= imageWidth || y >= imageHeight)
|
||||
{
|
||||
stack[stackp - 2] = 0.0;
|
||||
--stackp;
|
||||
return;
|
||||
}
|
||||
|
||||
pixel = imageData + (y * imageWidth + x) * 3;
|
||||
|
||||
stack[stackp - 2] = color_to_double(pixel[0], pixel[1], pixel[2]);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_origValRAIntersample (void *arg)
|
||||
{
|
||||
double x = cos(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleX,
|
||||
y = sin(stack[stackp - 1] * M_PI / 180) * stack[stackp - 2] + middleY;
|
||||
int x1 = floor(x),
|
||||
x2 = x1 + 1,
|
||||
y1 = floor(y),
|
||||
y2 = y1 + 1;
|
||||
double x2fact = (x - x1),
|
||||
y2fact = (y - y1),
|
||||
x1fact = 1.0 - x2fact,
|
||||
y1fact = 1.0 - y2fact,
|
||||
p1fact = x1fact * y1fact,
|
||||
p2fact = x1fact * y2fact,
|
||||
p3fact = x2fact * y1fact,
|
||||
p4fact = x2fact * y2fact;
|
||||
static unsigned char blackPixel[] = { 0, 0, 0 };
|
||||
unsigned char *pixel1,
|
||||
*pixel2,
|
||||
*pixel3,
|
||||
*pixel4;
|
||||
int red,
|
||||
green,
|
||||
blue;
|
||||
|
||||
if (x1 < 0 || x1 >= imageWidth || y1 < 0 || y1 >= imageHeight)
|
||||
pixel1 = blackPixel;
|
||||
else
|
||||
pixel1 = imageData + (y1 * imageWidth + x1) * 3;
|
||||
|
||||
if (x1 < 0 || x1 >= imageWidth || y2 < 0 || y2 >= imageHeight)
|
||||
pixel2 = blackPixel;
|
||||
else
|
||||
pixel2 = imageData + (y2 * imageWidth + x1) * 3;
|
||||
|
||||
if (x2 < 0 || x2 >= imageWidth || y1 < 0 || y1 >= imageHeight)
|
||||
pixel3 = blackPixel;
|
||||
else
|
||||
pixel3 = imageData + (y1 * imageWidth + x2) * 3;
|
||||
|
||||
if (x2 < 0 || x2 >= imageWidth || y2 < 0 || y2 >= imageHeight)
|
||||
pixel4 = blackPixel;
|
||||
else
|
||||
pixel4 = imageData + (y2 * imageWidth + x2) * 3;
|
||||
|
||||
red = pixel1[0] * p1fact + pixel2[0] * p2fact + pixel3[0] * p3fact + pixel4[0] * p4fact;
|
||||
green = pixel1[1] * p1fact + pixel2[1] * p2fact + pixel3[1] * p3fact + pixel4[1] * p4fact;
|
||||
blue = pixel1[2] * p1fact + pixel2[2] * p2fact + pixel3[2] * p3fact + pixel4[2] * p4fact;
|
||||
|
||||
stack[stackp - 2] = color_to_double(red, green, blue);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
#endif /* _GIMP */
|
||||
|
||||
void
|
||||
builtin_red (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = red_component(stack[stackp - 1]) / 255.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_green (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = green_component(stack[stackp - 1]) / 255.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_blue (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = blue_component(stack[stackp - 1]) / 255.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_gray (void *arg)
|
||||
{
|
||||
int red,
|
||||
green,
|
||||
blue,
|
||||
alpha;
|
||||
|
||||
double_to_color(stack[stackp - 1], &red, &green, &blue, &alpha);
|
||||
stack[stackp - 1] = (0.299 * red + 0.587 * green + 0.114 * blue) / 255.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_alpha (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = alpha_component(stack[stackp - 1]) / 255.0;
|
||||
}
|
||||
|
||||
void
|
||||
builtin_rgbColor (void *arg)
|
||||
{
|
||||
int redComponent = stack[stackp - 3] * 255,
|
||||
greenComponent = stack[stackp - 2] * 255,
|
||||
blueComponent = stack[stackp - 1] * 255;
|
||||
|
||||
stackp -= 2;
|
||||
|
||||
if (redComponent < 0)
|
||||
redComponent = 0;
|
||||
else if (redComponent > 255)
|
||||
redComponent = 255;
|
||||
|
||||
if (greenComponent < 0)
|
||||
greenComponent = 0;
|
||||
else if (greenComponent > 255)
|
||||
greenComponent = 255;
|
||||
|
||||
if (blueComponent < 0)
|
||||
blueComponent = 0;
|
||||
else if (blueComponent > 255)
|
||||
blueComponent = 255;
|
||||
|
||||
stack[stackp - 1] = color_to_double(redComponent, greenComponent, blueComponent, 255);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_rgbaColor (void *arg)
|
||||
{
|
||||
int redComponent = stack[stackp - 4] * 255,
|
||||
greenComponent = stack[stackp - 3] * 255,
|
||||
blueComponent = stack[stackp - 2] * 255,
|
||||
alphaComponent = stack[stackp - 1] * 255;
|
||||
|
||||
stackp -= 3;
|
||||
|
||||
if (redComponent < 0)
|
||||
redComponent = 0;
|
||||
else if (redComponent > 255)
|
||||
redComponent = 255;
|
||||
|
||||
if (greenComponent < 0)
|
||||
greenComponent = 0;
|
||||
else if (greenComponent > 255)
|
||||
greenComponent = 255;
|
||||
|
||||
if (blueComponent < 0)
|
||||
blueComponent = 0;
|
||||
else if (blueComponent > 255)
|
||||
blueComponent = 255;
|
||||
|
||||
if (alphaComponent < 0)
|
||||
alphaComponent = 0;
|
||||
else if (alphaComponent > 255)
|
||||
alphaComponent = 255;
|
||||
|
||||
stack[stackp - 1] = color_to_double(redComponent, greenComponent,
|
||||
blueComponent, alphaComponent);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_grayColor (void *arg)
|
||||
{
|
||||
int grayLevel = stack[stackp - 1] * 255;
|
||||
|
||||
if (grayLevel < 0)
|
||||
grayLevel = 0;
|
||||
else if (grayLevel > 255)
|
||||
grayLevel = 255;
|
||||
|
||||
stack[stackp - 1] = color_to_double(grayLevel, grayLevel, grayLevel, 255);
|
||||
}
|
||||
|
||||
void
|
||||
builtin_grayaColor (void *arg)
|
||||
{
|
||||
int grayLevel = stack[stackp - 2] * 255,
|
||||
alphaComponent = stack[stackp - 1] * 255;
|
||||
|
||||
--stackp;
|
||||
|
||||
if (grayLevel < 0)
|
||||
grayLevel = 0;
|
||||
else if (grayLevel > 255)
|
||||
grayLevel = 255;
|
||||
|
||||
if (alphaComponent < 0)
|
||||
alphaComponent = 0;
|
||||
else if (alphaComponent > 255)
|
||||
alphaComponent = 255;
|
||||
|
||||
stack[stackp - 1] = color_to_double(grayLevel, grayLevel, grayLevel, alphaComponent);
|
||||
}
|
||||
|
||||
builtin*
|
||||
builtin_with_name (const char *name)
|
||||
{
|
||||
builtin *next;
|
||||
|
||||
if (intersamplingEnabled)
|
||||
{
|
||||
if (strcmp(name, "origValXY") == 0)
|
||||
return builtin_with_name("origValXYIntersample");
|
||||
else if (strcmp(name, "origValRA") == 0)
|
||||
return builtin_with_name("origValRAIntersample");
|
||||
}
|
||||
|
||||
for (next = firstBuiltin; next != 0; next = next->next)
|
||||
if (strcmp(name, next->name) == 0)
|
||||
return next;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
register_builtin (const char *name, builtinFunction function, int numParams)
|
||||
{
|
||||
builtin *theBuiltin = (builtin*)malloc(sizeof(builtin));
|
||||
|
||||
strncpy(theBuiltin->name, name, MAX_BUILTIN_LENGTH);
|
||||
theBuiltin->name[MAX_BUILTIN_LENGTH] = '\0';
|
||||
theBuiltin->function = function;
|
||||
theBuiltin->numParams = numParams;
|
||||
theBuiltin->next = firstBuiltin;
|
||||
|
||||
firstBuiltin = theBuiltin;
|
||||
}
|
||||
|
||||
void
|
||||
init_builtins (void)
|
||||
{
|
||||
register_builtin("sin", builtin_sin, 1);
|
||||
register_builtin("cos", builtin_cos, 1);
|
||||
register_builtin("tan", builtin_tan, 1);
|
||||
register_builtin("asin", builtin_asin, 1);
|
||||
register_builtin("acos", builtin_acos, 1);
|
||||
register_builtin("atan", builtin_atan, 1);
|
||||
register_builtin("pow", builtin_pow, 2);
|
||||
register_builtin("abs", builtin_abs, 1);
|
||||
register_builtin("floor", builtin_floor, 1);
|
||||
register_builtin("sign", builtin_sign, 1);
|
||||
register_builtin("min", builtin_min, 2);
|
||||
register_builtin("max", builtin_max, 2);
|
||||
register_builtin("not", builtin_not, 1);
|
||||
register_builtin("or", builtin_or, 2);
|
||||
register_builtin("and", builtin_and, 2);
|
||||
register_builtin("equal", builtin_equal, 2);
|
||||
register_builtin("less", builtin_less, 2);
|
||||
register_builtin("greater", builtin_greater, 2);
|
||||
register_builtin("lessequal", builtin_lessequal, 2);
|
||||
register_builtin("greaterequal", builtin_greaterequal, 2);
|
||||
register_builtin("notequal", builtin_notequal, 2);
|
||||
register_builtin("inintv", builtin_inintv, 3);
|
||||
register_builtin("rand", builtin_rand, 2);
|
||||
register_builtin("origValXY", builtin_origValXY, 2);
|
||||
register_builtin("origValXYIntersample", builtin_origValXYIntersample, 2);
|
||||
register_builtin("origValRA", builtin_origValRA, 2);
|
||||
register_builtin("origValRAIntersample", builtin_origValRAIntersample, 2);
|
||||
register_builtin("red", builtin_red, 1);
|
||||
register_builtin("green", builtin_green, 1);
|
||||
register_builtin("blue", builtin_blue, 1);
|
||||
register_builtin("gray", builtin_gray, 1);
|
||||
register_builtin("alpha", builtin_alpha, 1);
|
||||
register_builtin("rgbColor", builtin_rgbColor, 3);
|
||||
register_builtin("rgbaColor", builtin_rgbaColor, 4);
|
||||
register_builtin("grayColor", builtin_grayColor, 1);
|
||||
register_builtin("grayaColor", builtin_grayaColor, 2);
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
/* -*- c -*- */
|
||||
|
||||
#ifndef __BUILTINS_H__
|
||||
#define __BUILTINS_H__
|
||||
|
||||
#define MAX_BUILTIN_LENGTH 63
|
||||
|
||||
typedef void (*builtinFunction) (void*);
|
||||
|
||||
typedef struct _builtin
|
||||
{
|
||||
char name[MAX_BUILTIN_LENGTH + 1];
|
||||
builtinFunction function;
|
||||
int numParams;
|
||||
struct _builtin *next;
|
||||
} builtin;
|
||||
|
||||
double color_to_double (unsigned int red, unsigned int green,
|
||||
unsigned int blue, unsigned int alpha);
|
||||
void double_to_color (double val, unsigned int *red, unsigned int *green,
|
||||
unsigned int *blue, unsigned int *alpha);
|
||||
|
||||
builtin* builtin_with_name (const char *name);
|
||||
|
||||
void init_builtins (void);
|
||||
|
||||
#endif
|
|
@ -1,197 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "exprtree.h"
|
||||
#include "builtins.h"
|
||||
|
||||
extern double currentX,
|
||||
currentY,
|
||||
currentR,
|
||||
currentA;
|
||||
extern int imageWidth,
|
||||
imageHeight;
|
||||
extern int usesRA;
|
||||
extern int intersamplingEnabled;
|
||||
|
||||
exprtree*
|
||||
make_number (double num)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_NUMBER;
|
||||
tree->val.number = num;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_var (char *name)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
if (strcmp(name, "x") == 0)
|
||||
tree->type = EXPR_VAR_X;
|
||||
else if (strcmp(name, "y") == 0)
|
||||
tree->type = EXPR_VAR_Y;
|
||||
else if (strcmp(name, "t") == 0)
|
||||
tree->type = EXPR_VAR_T;
|
||||
else if (strcmp(name, "r") == 0)
|
||||
{
|
||||
tree->type = EXPR_VAR_R;
|
||||
usesRA = 1;
|
||||
}
|
||||
else if (strcmp(name, "a") == 0)
|
||||
{
|
||||
tree->type = EXPR_VAR_A;
|
||||
usesRA = 1;
|
||||
}
|
||||
else if (strcmp(name, "W") == 0)
|
||||
tree->type = EXPR_VAR_W;
|
||||
else if (strcmp(name, "H") == 0)
|
||||
tree->type = EXPR_VAR_H;
|
||||
else if (strcmp(name, "R") == 0)
|
||||
tree->type = EXPR_VAR_BIG_R;
|
||||
else if (strcmp(name, "X") == 0)
|
||||
tree->type = EXPR_VAR_BIG_X;
|
||||
else if (strcmp(name, "Y") == 0)
|
||||
tree->type = EXPR_VAR_BIG_Y;
|
||||
else
|
||||
{
|
||||
tree->type = EXPR_VARIABLE;
|
||||
tree->val.var = register_variable(name);
|
||||
}
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_operator (int type, exprtree *left, exprtree *right)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = type;
|
||||
tree->val.operator.left = left;
|
||||
tree->val.operator.right = right;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_function (builtin *theBuiltin, exprtree *args)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_FUNC;
|
||||
tree->val.func.routine = theBuiltin->function;
|
||||
tree->val.func.numArgs = theBuiltin->numParams;
|
||||
tree->val.func.args = args;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_sequence (exprtree *left, exprtree *right)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_SEQUENCE;
|
||||
tree->val.operator.left = left;
|
||||
tree->val.operator.right = right;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_assignment (char *name, exprtree *value)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
variable *var = register_variable(name);
|
||||
|
||||
tree->type = EXPR_ASSIGNMENT;
|
||||
tree->val.assignment.var = var;
|
||||
tree->val.assignment.value = value;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_if_then (exprtree *condition, exprtree *consequence)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_IF_THEN;
|
||||
tree->val.ifExpr.condition = condition;
|
||||
tree->val.ifExpr.consequence = consequence;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_if_then_else (exprtree *condition, exprtree *consequence, exprtree *alternative)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_IF_THEN_ELSE;
|
||||
tree->val.ifExpr.condition = condition;
|
||||
tree->val.ifExpr.consequence = consequence;
|
||||
tree->val.ifExpr.alternative = alternative;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_while (exprtree *invariant, exprtree *body)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_WHILE;
|
||||
tree->val.whileExpr.invariant = invariant;
|
||||
tree->val.whileExpr.body = body;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
make_do_while (exprtree *body, exprtree *invariant)
|
||||
{
|
||||
exprtree *tree = (exprtree*)malloc(sizeof(exprtree));
|
||||
|
||||
tree->type = EXPR_DO_WHILE;
|
||||
tree->val.whileExpr.invariant = invariant;
|
||||
tree->val.whileExpr.body = body;
|
||||
|
||||
tree->next = 0;
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
exprtree*
|
||||
arglist_append (exprtree *list1, exprtree *list2)
|
||||
{
|
||||
exprtree *tree = list1;
|
||||
|
||||
while (tree->next != 0)
|
||||
tree = tree->next;
|
||||
|
||||
tree->next = list2;
|
||||
|
||||
return list1;
|
||||
}
|
|
@ -1,102 +0,0 @@
|
|||
#ifndef __EXPRTREE_H__
|
||||
#define __EXPRTREE_H__
|
||||
|
||||
#include "vars.h"
|
||||
#include "builtins.h"
|
||||
|
||||
#ifdef USE_TREE
|
||||
typedef double (*function) (double*);
|
||||
#else
|
||||
typedef void (*function) (void*);
|
||||
#endif
|
||||
|
||||
#define MAX_IDENT_LENGTH 63
|
||||
|
||||
typedef char ident[MAX_IDENT_LENGTH + 1];
|
||||
|
||||
typedef struct _exprtree
|
||||
{
|
||||
int type;
|
||||
|
||||
union
|
||||
{
|
||||
double number;
|
||||
variable *var;
|
||||
struct
|
||||
{
|
||||
int numArgs;
|
||||
function routine;
|
||||
struct _exprtree *args;
|
||||
} func;
|
||||
struct
|
||||
{
|
||||
struct _exprtree *left;
|
||||
struct _exprtree *right;
|
||||
} operator;
|
||||
struct
|
||||
{
|
||||
variable *var;
|
||||
struct _exprtree *value;
|
||||
} assignment;
|
||||
struct
|
||||
{
|
||||
struct _exprtree *condition;
|
||||
struct _exprtree *consequence;
|
||||
struct _exprtree *alternative;
|
||||
int label1;
|
||||
int label2;
|
||||
} ifExpr;
|
||||
struct
|
||||
{
|
||||
struct _exprtree *invariant;
|
||||
struct _exprtree *body;
|
||||
int label1;
|
||||
int label2;
|
||||
} whileExpr;
|
||||
} val;
|
||||
|
||||
struct _exprtree *next;
|
||||
} exprtree;
|
||||
|
||||
#define EXPR_NUMBER 1
|
||||
#define EXPR_ADD 2
|
||||
#define EXPR_SUB 3
|
||||
#define EXPR_MUL 4
|
||||
#define EXPR_DIV 5
|
||||
#define EXPR_MOD 6
|
||||
#define EXPR_NEG 7
|
||||
#define EXPR_FUNC 8
|
||||
#define EXPR_VAR_X 9
|
||||
#define EXPR_VAR_Y 10
|
||||
#define EXPR_VAR_T 11
|
||||
#define EXPR_VAR_R 12
|
||||
#define EXPR_VAR_A 13
|
||||
#define EXPR_VAR_W 14
|
||||
#define EXPR_VAR_H 15
|
||||
#define EXPR_VAR_BIG_R 16
|
||||
#define EXPR_VAR_BIG_X 17
|
||||
#define EXPR_VAR_BIG_Y 18
|
||||
#define EXPR_SEQUENCE 19
|
||||
#define EXPR_ASSIGNMENT 20
|
||||
#define EXPR_VARIABLE 21
|
||||
#define EXPR_IF_THEN 22
|
||||
#define EXPR_IF_THEN_ELSE 23
|
||||
#define EXPR_WHILE 24
|
||||
#define EXPR_DO_WHILE 25
|
||||
|
||||
exprtree* make_number (double num);
|
||||
exprtree* make_var (char *name);
|
||||
exprtree* make_operator (int type, exprtree *left, exprtree *right);
|
||||
exprtree* make_function (builtin *theBuiltin, exprtree *args);
|
||||
exprtree* make_sequence (exprtree *left, exprtree *right);
|
||||
exprtree* make_assignment (char *name, exprtree *value);
|
||||
exprtree* make_if_then (exprtree *condition, exprtree *conclusion);
|
||||
exprtree* make_if_then_else (exprtree *condition, exprtree *conclusion, exprtree *alternative);
|
||||
exprtree* make_while (exprtree *invariant, exprtree *body);
|
||||
exprtree* make_do_while (exprtree *body, exprtree *invariant);
|
||||
|
||||
exprtree* arglist_append (exprtree *list1, exprtree *list2);
|
||||
|
||||
double eval_exprtree (exprtree *tree);
|
||||
|
||||
#endif
|
File diff suppressed because it is too large
Load Diff
|
@ -1,102 +0,0 @@
|
|||
%{
|
||||
#include <stdio.h>
|
||||
|
||||
#include "exprtree.h"
|
||||
#include "builtins.h"
|
||||
|
||||
extern exprtree *theExprtree;
|
||||
%}
|
||||
|
||||
%union {
|
||||
ident ident;
|
||||
exprtree *exprtree;
|
||||
builtin *builtin;
|
||||
}
|
||||
|
||||
%token T_IDENT T_NUMBER
|
||||
%token T_IF T_THEN T_ELSE T_END
|
||||
%token T_WHILE T_DO
|
||||
%token T_BUILTIN
|
||||
|
||||
%right ';'
|
||||
%right '='
|
||||
%left T_OR T_AND
|
||||
%left T_EQUAL '<' '>' T_LESSEQUAL T_GREATEREQUAL T_NOTEQUAL
|
||||
%left '+' '-'
|
||||
%left '*' '/' '%'
|
||||
%left UNARY
|
||||
|
||||
%%
|
||||
|
||||
start : expr { theExprtree = $<exprtree>1; }
|
||||
;
|
||||
|
||||
expr : T_NUMBER { $<exprtree>$ = $<exprtree>1; }
|
||||
| T_IDENT { $<exprtree>$ = make_var($<ident>1); }
|
||||
| expr '+' expr { $<exprtree>$ = make_operator(EXPR_ADD,
|
||||
$<exprtree>1, $<exprtree>3); }
|
||||
| expr '-' expr { $<exprtree>$ = make_operator(EXPR_SUB,
|
||||
$<exprtree>1, $<exprtree>3); }
|
||||
| expr '*' expr { $<exprtree>$ = make_operator(EXPR_MUL,
|
||||
$<exprtree>1, $<exprtree>3); }
|
||||
| expr '/' expr { $<exprtree>$ = make_operator(EXPR_DIV,
|
||||
$<exprtree>1, $<exprtree>3); }
|
||||
| expr '%' expr { $<exprtree>$ = make_operator(EXPR_MOD,
|
||||
$<exprtree>1, $<exprtree>3); }
|
||||
| expr T_EQUAL expr { $<exprtree>$ = make_function(builtin_with_name("equal"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr '<' expr { $<exprtree>$ = make_function(builtin_with_name("less"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr '>' expr { $<exprtree>$ = make_function(builtin_with_name("greater"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr T_LESSEQUAL expr
|
||||
{ $<exprtree>$ = make_function(builtin_with_name("lessequal"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr T_GREATEREQUAL expr
|
||||
{ $<exprtree>$ = make_function(builtin_with_name("greaterequal"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr T_NOTEQUAL expr
|
||||
{ $<exprtree>$ = make_function(builtin_with_name("notequal"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr T_OR expr { $<exprtree>$ = make_function(builtin_with_name("or"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| expr T_AND expr { $<exprtree>$ = make_function(builtin_with_name("and"),
|
||||
arglist_append($<exprtree>1, $<exprtree>3)); }
|
||||
| '-' expr %prec UNARY
|
||||
{ $<exprtree>$ = make_operator(EXPR_NEG, $<exprtree>2, 0); }
|
||||
| '!' expr %prec UNARY
|
||||
{ $<exprtree>$ = make_function(builtin_with_name("not"), $<exprtree>2); }
|
||||
| '(' expr ')' { $<exprtree>$ = $<exprtree>2; };
|
||||
| T_BUILTIN '(' arglist ')'
|
||||
{ $<exprtree>$ = make_function($<builtin>1, $<exprtree>3); }
|
||||
| T_IDENT '=' expr { $<exprtree>$ = make_assignment($<ident>1, $<exprtree>3); }
|
||||
| expr ';' expr { $<exprtree>$ = make_sequence($<exprtree>1, $<exprtree>3); }
|
||||
| T_IF expr T_THEN expr T_END
|
||||
{ $<exprtree>$ = make_if_then($<exprtree>2, $<exprtree>4); }
|
||||
| T_IF expr T_THEN expr T_ELSE expr T_END
|
||||
{ $<exprtree>$ = make_if_then_else($<exprtree>2,
|
||||
$<exprtree>4,
|
||||
$<exprtree>6); }
|
||||
| T_WHILE expr T_DO expr T_END
|
||||
{ $<exprtree>$ = make_while($<exprtree>2, $<exprtree>4); }
|
||||
| T_DO expr T_WHILE expr T_END
|
||||
{ $<exprtree>$ = make_do_while($<exprtree>2, $<exprtree>4); }
|
||||
;
|
||||
|
||||
arglist : { $<exprtree>$ = 0; }
|
||||
| args { $<exprtree>$ = $<exprtree>1; }
|
||||
;
|
||||
|
||||
args : expr { $<exprtree>$ = $<exprtree>1; }
|
||||
| args ',' expr { $<exprtree>$ = arglist_append($<exprtree>1, $<exprtree>3); }
|
||||
;
|
||||
|
||||
%%
|
||||
|
||||
int
|
||||
yyerror (char *s)
|
||||
{
|
||||
fprintf(stderr, "%s\n", s);
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -1,567 +0,0 @@
|
|||
#include <stdio.h>
|
||||
#include <math.h>
|
||||
#include <assert.h>
|
||||
|
||||
#include "builtins.h"
|
||||
#include "vars.h"
|
||||
|
||||
#include "postfix.h"
|
||||
|
||||
extern double currentX,
|
||||
currentY,
|
||||
currentT,
|
||||
currentR,
|
||||
currentA,
|
||||
imageR,
|
||||
imageX,
|
||||
imageY;
|
||||
extern int imageWidth,
|
||||
imageHeight;
|
||||
|
||||
#define STACKSIZE 128
|
||||
#define EXPRSIZE 256
|
||||
|
||||
double stack[STACKSIZE];
|
||||
int stackp;
|
||||
|
||||
postfix expression[EXPRSIZE];
|
||||
int exprp,
|
||||
exprlen;
|
||||
|
||||
void
|
||||
stack_push (double *arg)
|
||||
{
|
||||
stack[stackp++] = *arg;
|
||||
}
|
||||
|
||||
void
|
||||
stack_pop (void *arg)
|
||||
{
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
stack_jmp (int *arg)
|
||||
{
|
||||
exprp = *arg - 1;
|
||||
}
|
||||
|
||||
void
|
||||
stack_jez (int *arg)
|
||||
{
|
||||
if (stack[--stackp] == 0.0)
|
||||
exprp = *arg - 1;
|
||||
}
|
||||
|
||||
void
|
||||
stack_jnez (int *arg)
|
||||
{
|
||||
if (stack[--stackp] != 0.0)
|
||||
exprp = *arg - 1;
|
||||
}
|
||||
|
||||
void
|
||||
stack_add (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = stack[stackp - 2] + stack[stackp - 1];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
stack_add_i (double *arg)
|
||||
{
|
||||
stack[stackp - 1] += *arg;
|
||||
}
|
||||
|
||||
void
|
||||
stack_sub (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = stack[stackp - 2] - stack[stackp - 1];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
stack_sub_i (double *arg)
|
||||
{
|
||||
stack[stackp - 1] -= *arg;
|
||||
}
|
||||
|
||||
void
|
||||
stack_neg (void *arg)
|
||||
{
|
||||
stack[stackp - 1] = -stack[stackp - 1];
|
||||
}
|
||||
|
||||
void
|
||||
stack_mul (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = stack[stackp - 2] * stack[stackp - 1];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
stack_mul_i (double *arg)
|
||||
{
|
||||
stack[stackp - 1] *= *arg;
|
||||
}
|
||||
|
||||
void
|
||||
stack_div (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = stack[stackp - 2] / stack[stackp - 1];
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
stack_div_i (double *arg)
|
||||
{
|
||||
stack[stackp - 1] /= *arg;
|
||||
}
|
||||
|
||||
void
|
||||
stack_mod (void *arg)
|
||||
{
|
||||
stack[stackp - 2] = fmod(stack[stackp - 2], stack[stackp - 1]);
|
||||
--stackp;
|
||||
}
|
||||
|
||||
void
|
||||
stack_mod_i (double *arg)
|
||||
{
|
||||
stack[stackp - 1] = fmod(stack[stackp - 1], *arg);
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_x (void *arg)
|
||||
{
|
||||
stack[stackp++] = currentX;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_y (void *arg)
|
||||
{
|
||||
stack[stackp++] = currentY;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_t (void *arg)
|
||||
{
|
||||
stack[stackp++] = currentT;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_r (void *arg)
|
||||
{
|
||||
stack[stackp++] = currentR;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_a (void *arg)
|
||||
{
|
||||
stack[stackp++] = currentA;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_w (void *arg)
|
||||
{
|
||||
stack[stackp++] = imageWidth;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_h (void *arg)
|
||||
{
|
||||
stack[stackp++] = imageHeight;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_big_r (void *arg)
|
||||
{
|
||||
stack[stackp++] = imageR;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_big_x (void *arg)
|
||||
{
|
||||
stack[stackp++] = imageX;
|
||||
}
|
||||
|
||||
void
|
||||
stack_var_big_y (void *arg)
|
||||
{
|
||||
stack[stackp++] = imageY;
|
||||
}
|
||||
|
||||
void
|
||||
stack_variable (variable *var)
|
||||
{
|
||||
stack[stackp++] = var->value;
|
||||
}
|
||||
|
||||
void
|
||||
stack_assign (variable *var)
|
||||
{
|
||||
var->value = stack[stackp - 1];
|
||||
}
|
||||
|
||||
void
|
||||
make_postfix_recursive (exprtree *tree)
|
||||
{
|
||||
static double theZeroValue = 0.0;
|
||||
|
||||
switch (tree->type)
|
||||
{
|
||||
case EXPR_NUMBER :
|
||||
expression[exprp].func = (stackfunc)stack_push;
|
||||
expression[exprp].arg = &tree->val.number;
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_ADD :
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
if (tree->val.operator.right->type == EXPR_NUMBER)
|
||||
{
|
||||
expression[exprp].func = (stackfunc)stack_add_i;
|
||||
expression[exprp].arg = &tree->val.operator.right->val.number;
|
||||
}
|
||||
else
|
||||
{
|
||||
make_postfix_recursive(tree->val.operator.right);
|
||||
expression[exprp].func = stack_add;
|
||||
}
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_SUB :
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
if (tree->val.operator.right->type == EXPR_NUMBER)
|
||||
{
|
||||
expression[exprp].func = (stackfunc)stack_sub_i;
|
||||
expression[exprp].arg = &tree->val.operator.right->val.number;
|
||||
}
|
||||
else
|
||||
{
|
||||
make_postfix_recursive(tree->val.operator.right);
|
||||
expression[exprp].func = stack_sub;
|
||||
}
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_NEG :
|
||||
/*
|
||||
if (tree->val.operator.left->type == EXPR_NUMBER)
|
||||
{
|
||||
expression[exprp].func = (stackfunc)stack_push;
|
||||
expression[exprp].arg = -tree->val.operator.left->val.number;
|
||||
}
|
||||
else
|
||||
{ */
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
expression[exprp].func = stack_neg;
|
||||
/* } */
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_MUL :
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
if (tree->val.operator.right->type == EXPR_NUMBER)
|
||||
{
|
||||
expression[exprp].func = (stackfunc)stack_mul_i;
|
||||
expression[exprp].arg = &tree->val.operator.right->val.number;
|
||||
}
|
||||
else
|
||||
{
|
||||
make_postfix_recursive(tree->val.operator.right);
|
||||
expression[exprp].func = stack_mul;
|
||||
}
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_DIV :
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
if (tree->val.operator.right->type == EXPR_NUMBER)
|
||||
{
|
||||
expression[exprp].func = (stackfunc)stack_div_i;
|
||||
expression[exprp].arg = &tree->val.operator.right->val.number;
|
||||
}
|
||||
else
|
||||
{
|
||||
make_postfix_recursive(tree->val.operator.right);
|
||||
expression[exprp].func = stack_div;
|
||||
}
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_MOD :
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
if (tree->val.operator.right->type == EXPR_NUMBER)
|
||||
{
|
||||
expression[exprp].func = (stackfunc)stack_mod_i;
|
||||
expression[exprp].arg = &tree->val.operator.right->val.number;
|
||||
}
|
||||
else
|
||||
{
|
||||
make_postfix_recursive(tree->val.operator.right);
|
||||
expression[exprp].func = stack_mod;
|
||||
}
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_X :
|
||||
expression[exprp++].func = stack_var_x;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_Y :
|
||||
expression[exprp++].func = stack_var_y;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_T :
|
||||
expression[exprp++].func = stack_var_t;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_R :
|
||||
expression[exprp++].func = stack_var_r;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_A :
|
||||
expression[exprp++].func = stack_var_a;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_W :
|
||||
expression[exprp++].func = stack_var_w;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_H :
|
||||
expression[exprp++].func = stack_var_h;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_BIG_R :
|
||||
expression[exprp++].func = stack_var_big_r;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_BIG_X :
|
||||
expression[exprp++].func = stack_var_big_x;
|
||||
break;
|
||||
|
||||
case EXPR_VAR_BIG_Y :
|
||||
expression[exprp++].func = stack_var_big_y;
|
||||
break;
|
||||
|
||||
case EXPR_FUNC :
|
||||
{
|
||||
exprtree *arg = tree->val.func.args;
|
||||
|
||||
while (arg != 0)
|
||||
{
|
||||
make_postfix_recursive(arg);
|
||||
arg = arg->next;
|
||||
}
|
||||
|
||||
expression[exprp++].func = tree->val.func.routine;
|
||||
break;
|
||||
}
|
||||
|
||||
case EXPR_VARIABLE :
|
||||
expression[exprp].func = (stackfunc)stack_variable;
|
||||
expression[exprp].arg = tree->val.var;
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_ASSIGNMENT :
|
||||
make_postfix_recursive(tree->val.assignment.value);
|
||||
expression[exprp].func = (stackfunc)stack_assign;
|
||||
expression[exprp].arg = tree->val.assignment.var;
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_SEQUENCE :
|
||||
make_postfix_recursive(tree->val.operator.left);
|
||||
expression[exprp++].func = stack_pop;
|
||||
make_postfix_recursive(tree->val.operator.right);
|
||||
break;
|
||||
|
||||
case EXPR_IF_THEN :
|
||||
make_postfix_recursive(tree->val.ifExpr.condition);
|
||||
expression[exprp].func = (stackfunc)stack_jez;
|
||||
expression[exprp].arg = &tree->val.ifExpr.label1;
|
||||
++exprp;
|
||||
make_postfix_recursive(tree->val.ifExpr.consequence);
|
||||
expression[exprp].func = (stackfunc)stack_jmp;
|
||||
expression[exprp].arg = &tree->val.ifExpr.label2;
|
||||
++exprp;
|
||||
tree->val.ifExpr.label1 = exprp;
|
||||
expression[exprp].func = (stackfunc)stack_push;
|
||||
expression[exprp].arg = &theZeroValue;
|
||||
++exprp;
|
||||
tree->val.ifExpr.label2 = exprp;
|
||||
break;
|
||||
|
||||
case EXPR_IF_THEN_ELSE :
|
||||
make_postfix_recursive(tree->val.ifExpr.condition);
|
||||
expression[exprp].func = (stackfunc)stack_jez;
|
||||
expression[exprp].arg = &tree->val.ifExpr.label1;
|
||||
++exprp;
|
||||
make_postfix_recursive(tree->val.ifExpr.consequence);
|
||||
expression[exprp].func = (stackfunc)stack_jmp;
|
||||
expression[exprp].arg = &tree->val.ifExpr.label2;
|
||||
++exprp;
|
||||
tree->val.ifExpr.label1 = exprp;
|
||||
make_postfix_recursive(tree->val.ifExpr.alternative);
|
||||
tree->val.ifExpr.label2 = exprp;
|
||||
break;
|
||||
|
||||
case EXPR_WHILE :
|
||||
tree->val.whileExpr.label1 = exprp;
|
||||
make_postfix_recursive(tree->val.whileExpr.invariant);
|
||||
expression[exprp].func = (stackfunc)stack_jez;
|
||||
expression[exprp].arg = &tree->val.whileExpr.label2;
|
||||
++exprp;
|
||||
make_postfix_recursive(tree->val.whileExpr.body);
|
||||
expression[exprp++].func = stack_pop;
|
||||
expression[exprp].func = (stackfunc)stack_jmp;
|
||||
expression[exprp].arg = &tree->val.whileExpr.label1;
|
||||
++exprp;
|
||||
tree->val.whileExpr.label2 = exprp;
|
||||
expression[exprp].func = (stackfunc)stack_push;
|
||||
expression[exprp].arg = &theZeroValue;
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
case EXPR_DO_WHILE :
|
||||
tree->val.whileExpr.label1 = exprp;
|
||||
make_postfix_recursive(tree->val.whileExpr.body);
|
||||
expression[exprp++].func = stack_pop;
|
||||
make_postfix_recursive(tree->val.whileExpr.invariant);
|
||||
expression[exprp].func = (stackfunc)stack_jnez;
|
||||
expression[exprp].arg = &tree->val.whileExpr.label1;
|
||||
++exprp;
|
||||
expression[exprp].func = (stackfunc)stack_push;
|
||||
expression[exprp].arg = &theZeroValue;
|
||||
++exprp;
|
||||
break;
|
||||
|
||||
default :
|
||||
fprintf(stderr, "illegal expr\n");
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
make_postfix (exprtree *tree)
|
||||
{
|
||||
exprp = 0;
|
||||
make_postfix_recursive(tree);
|
||||
exprlen = exprp;
|
||||
}
|
||||
|
||||
void
|
||||
output_postfix (void)
|
||||
{
|
||||
int i;
|
||||
|
||||
printf("-------------------------\n");
|
||||
|
||||
for (i = 0; i < exprlen; ++i)
|
||||
{
|
||||
printf("%d ", i);
|
||||
if (expression[i].func == (stackfunc)stack_push)
|
||||
printf("push %f\n", *(double*)expression[i].arg);
|
||||
else if (expression[i].func == stack_pop)
|
||||
printf("pop\n");
|
||||
else if (expression[i].func == (stackfunc)stack_jmp)
|
||||
printf("jmp %d\n", *(int*)expression[i].arg);
|
||||
else if (expression[i].func == (stackfunc)stack_jez)
|
||||
printf("jez %d\n", *(int*)expression[i].arg);
|
||||
else if (expression[i].func == (stackfunc)stack_jnez)
|
||||
printf("jnez %d\n", *(int*)expression[i].arg);
|
||||
else if (expression[i].func == stack_add)
|
||||
printf("add\n");
|
||||
else if (expression[i].func == (stackfunc)stack_add_i)
|
||||
printf("addi %f\n", *(double*)expression[i].arg);
|
||||
else if (expression[i].func == stack_sub)
|
||||
printf("sub\n");
|
||||
else if (expression[i].func == (stackfunc)stack_sub_i)
|
||||
printf("subi %f\n", *(double*)expression[i].arg);
|
||||
else if (expression[i].func == stack_neg)
|
||||
printf("neg\n");
|
||||
else if (expression[i].func == stack_mul)
|
||||
printf("mul\n");
|
||||
else if (expression[i].func == (stackfunc)stack_mul_i)
|
||||
printf("muli %f\n", *(double*)expression[i].arg);
|
||||
else if (expression[i].func == stack_div)
|
||||
printf("div\n");
|
||||
else if (expression[i].func == (stackfunc)stack_div_i)
|
||||
printf("divi %f\n", *(double*)expression[i].arg);
|
||||
else if (expression[i].func == stack_mod)
|
||||
printf("mod\n");
|
||||
else if (expression[i].func == (stackfunc)stack_mod_i)
|
||||
printf("modi %f\n", *(double*)expression[i].arg);
|
||||
else if (expression[i].func == stack_var_x)
|
||||
printf("push x\n");
|
||||
else if (expression[i].func == stack_var_y)
|
||||
printf("push y\n");
|
||||
else if (expression[i].func == stack_var_t)
|
||||
printf("push t\n");
|
||||
else if (expression[i].func == stack_var_r)
|
||||
printf("push r\n");
|
||||
else if (expression[i].func == stack_var_a)
|
||||
printf("push a\n");
|
||||
else if (expression[i].func == stack_var_w)
|
||||
printf("push w\n");
|
||||
else if (expression[i].func == stack_var_h)
|
||||
printf("push h\n");
|
||||
else if (expression[i].func == stack_var_big_r)
|
||||
printf("push R\n");
|
||||
else if (expression[i].func == stack_var_big_x)
|
||||
printf("push X\n");
|
||||
else if (expression[i].func == stack_var_big_y)
|
||||
printf("push Y\n");
|
||||
else if (expression[i].func == (stackfunc)stack_variable)
|
||||
printf("push %s\n", ((variable*)expression[i].arg)->name);
|
||||
else if (expression[i].func == (stackfunc)stack_assign)
|
||||
printf("sto %s\n", ((variable*)expression[i].arg)->name);
|
||||
/*
|
||||
else if (expression[i].func == builtin_sin)
|
||||
printf("sin\n");
|
||||
else if (expression[i].func == builtin_cos)
|
||||
printf("cos\n");
|
||||
else if (expression[i].func == builtin_tan)
|
||||
printf("tan\n");
|
||||
else if (expression[i].func == builtin_asin)
|
||||
printf("asin\n");
|
||||
else if (expression[i].func == builtin_acos)
|
||||
printf("acos\n");
|
||||
else if (expression[i].func == builtin_atan)
|
||||
printf("atan\n");
|
||||
else if (expression[i].func == builtin_sign)
|
||||
printf("sign\n");
|
||||
else if (expression[i].func == builtin_min)
|
||||
printf("min\n");
|
||||
else if (expression[i].func == builtin_max)
|
||||
printf("max\n");
|
||||
else if (expression[i].func == builtin_inintv)
|
||||
printf("inintv\n");
|
||||
else if (expression[i].func == builtin_rand)
|
||||
printf("rand\n");
|
||||
else if (expression[i].func == builtin_origValXY)
|
||||
printf("origValXY\n");
|
||||
else if (expression[i].func == builtin_origValXYIntersample)
|
||||
printf("origValXY\n");
|
||||
else if (expression[i].func == builtin_origValRA)
|
||||
printf("origValRA\n");
|
||||
else if (expression[i].func == builtin_origValRAIntersample)
|
||||
printf("origValRA\n");
|
||||
else if (expression[i].func == builtin_grayColor)
|
||||
printf("grayColor\n");
|
||||
*/
|
||||
else
|
||||
printf("unknown opcode\n");
|
||||
}
|
||||
}
|
||||
|
||||
double
|
||||
eval_postfix (void)
|
||||
{
|
||||
stackp = 0;
|
||||
for (exprp = 0; exprp < exprlen; ++exprp)
|
||||
expression[exprp].func(expression[exprp].arg);
|
||||
return stack[0];
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
#include "exprtree.h"
|
||||
|
||||
typedef void (*stackfunc) (void*);
|
||||
|
||||
typedef struct _postfix
|
||||
{
|
||||
stackfunc func;
|
||||
void *arg;
|
||||
} postfix;
|
||||
|
||||
void make_postfix (exprtree *tree);
|
||||
void output_postfix (void);
|
||||
double eval_postfix (void);
|
|
@ -1,58 +0,0 @@
|
|||
%{
|
||||
#include <string.h>
|
||||
|
||||
#include "exprtree.h"
|
||||
#include "builtins.h"
|
||||
#include "parser.h"
|
||||
%}
|
||||
|
||||
%option noyywrap
|
||||
|
||||
%%
|
||||
|
||||
if return T_IF;
|
||||
then return T_THEN;
|
||||
else return T_ELSE;
|
||||
end return T_END;
|
||||
while return T_WHILE;
|
||||
do return T_DO;
|
||||
[a-zA-Z_][a-zA-Z0-9_]* {
|
||||
builtin *theBuiltin = builtin_with_name(yytext);
|
||||
|
||||
if (theBuiltin != 0)
|
||||
{
|
||||
yylval.builtin = theBuiltin;
|
||||
return T_BUILTIN;
|
||||
}
|
||||
else
|
||||
{
|
||||
strncpy(yylval.ident, yytext, MAX_IDENT_LENGTH);
|
||||
yylval.ident[MAX_IDENT_LENGTH] = 0;
|
||||
return T_IDENT;
|
||||
}
|
||||
}
|
||||
[0-9]+ { yylval.exprtree = make_number(atof(yytext)); return T_NUMBER; }
|
||||
[0-9]*\.[0-9]+ { yylval.exprtree = make_number(atof(yytext)); return T_NUMBER; }
|
||||
"==" return T_EQUAL;
|
||||
"<=" return T_LESSEQUAL;
|
||||
">=" return T_GREATEREQUAL;
|
||||
"!=" return T_NOTEQUAL;
|
||||
"||" return T_OR;
|
||||
"&&" return T_AND;
|
||||
[-<>!,()+*/%=;] return yytext[0];
|
||||
#.* ;
|
||||
[ \t\n] ;
|
||||
|
||||
%%
|
||||
|
||||
void
|
||||
scanFromString (char *string)
|
||||
{
|
||||
yy_scan_string(string);
|
||||
}
|
||||
|
||||
void
|
||||
endScanningFromString (void)
|
||||
{
|
||||
yy_delete_buffer(YY_CURRENT_BUFFER);
|
||||
}
|
|
@ -1,7 +0,0 @@
|
|||
#ifndef __SCANNER_H__
|
||||
#define __SCANNER_H__
|
||||
|
||||
void scanFromString (char *string);
|
||||
void endScanningFromString (void);
|
||||
|
||||
#endif
|
|
@ -1,42 +0,0 @@
|
|||
#include <assert.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "vars.h"
|
||||
|
||||
variable *firstVariable = 0;
|
||||
|
||||
variable*
|
||||
register_variable (char *name)
|
||||
{
|
||||
variable *var;
|
||||
|
||||
assert(strlen(name) < VAR_MAX_LENGTH);
|
||||
|
||||
for (var = firstVariable; var != 0; var = var->next)
|
||||
if (strcmp(name, var->name) == 0)
|
||||
return var;
|
||||
|
||||
var = (variable*)malloc(sizeof(variable));
|
||||
strcpy(var->name, name);
|
||||
var->value = 0.0;
|
||||
var->next = firstVariable;
|
||||
firstVariable = var;
|
||||
|
||||
return var;
|
||||
}
|
||||
|
||||
void
|
||||
clear_all_variables (void)
|
||||
{
|
||||
variable *var = firstVariable;
|
||||
|
||||
while (var != 0)
|
||||
{
|
||||
variable *next = var->next;
|
||||
|
||||
free(var);
|
||||
var = next;
|
||||
}
|
||||
|
||||
firstVariable = 0;
|
||||
}
|
|
@ -1,18 +0,0 @@
|
|||
#ifndef __VARS_H__
|
||||
#define __VARS_H__
|
||||
|
||||
#define VAR_MAX_LENGTH 32
|
||||
|
||||
typedef struct _variable
|
||||
{
|
||||
char name[VAR_MAX_LENGTH];
|
||||
double value;
|
||||
|
||||
struct _variable *next;
|
||||
} variable;
|
||||
|
||||
variable* register_variable (char *name);
|
||||
|
||||
void clear_all_variables (void);
|
||||
|
||||
#endif
|
|
@ -1,6 +0,0 @@
|
|||
Makefile.in
|
||||
Makefile
|
||||
.deps
|
||||
_libs
|
||||
.libs
|
||||
refract
|
|
@ -1,21 +0,0 @@
|
|||
1/10/98:
|
||||
|
||||
Simultaniously changed the name of the menu entry to "Refract" instead
|
||||
of "Refract&Reflect" and made changes preparing to add Reflect
|
||||
functionality. Note that this changed the PDB interface.
|
||||
|
||||
Discovered that the GParam thing didn't need to be "fixed", so I put
|
||||
it back.
|
||||
|
||||
1/2/98: refract-Beta
|
||||
|
||||
Refract is back, and better than ever! That's right... The New Layer
|
||||
checkbox now works properly from layers with and without alpha.
|
||||
|
||||
Fixed so small or goofily placed lenses don't crash. Lo and behold,
|
||||
lens offsets also seem to be working. How that happened is beyond me.
|
||||
|
||||
Fixed some bad GParam values thing in run().
|
||||
|
||||
Changed the name of the parameter that determines the lens thickness
|
||||
to "thick" instead of "depth".
|
|
@ -1,12 +0,0 @@
|
|||
Files that should be in refract distributions:
|
||||
FILES - this file
|
||||
INSTALL - Installation instructions (if not part of GIMP distrib)
|
||||
Makefile
|
||||
README
|
||||
TODO
|
||||
refguts.c - source file containing the actual distort refract code
|
||||
refmain.c - source file containing query, run, and dialog things
|
||||
refract.h - common header file, contains configurable settings
|
||||
|
||||
Additional file included in refract-bin distributions:
|
||||
refract - the compiled plug-in executable for linux-ELF-i386
|
|
@ -1,31 +0,0 @@
|
|||
If this file came as part of a GIMP distribution, no special
|
||||
installation instructions are required. Refract will get built and
|
||||
installed when all the other plug-ins do.
|
||||
|
||||
However, if you wish to install this plug-in seperately, perhaps
|
||||
because it's a newer version than the one in your distribution...
|
||||
|
||||
First, try typing
|
||||
|
||||
make install
|
||||
|
||||
If that worked, stop reading and go play with GIMP. If it didn't,
|
||||
read on...
|
||||
|
||||
At this point in time, refract needs the files megawidget.h and
|
||||
megawidget.o to compile. Since I've found megawidgets don't fully
|
||||
suffice my needs, this will probably change in the near future. But
|
||||
for now, stick those files (or links to them) somewhere where your
|
||||
compiler can find them when compiling refract... They should be
|
||||
included somewhere in the plug-ins directory of your GIMP source
|
||||
distribution.
|
||||
|
||||
You may also wish to dink with the compiler options in the Makefile.
|
||||
At the moment, as refract is still Not Quite There Yet, it comes
|
||||
shipped with all sorts of debugging flags turned on and optimizations
|
||||
turned OFF. If you don't care why refract crashes if and when it
|
||||
does, go ahead and comment out the debug flags and uncomment the
|
||||
optimizations. Hopefully it will pick up some speed that way.
|
||||
|
||||
There are also a few options available for dinking in refract.h, but
|
||||
none too interesting at the moment.
|
|
@ -1,43 +0,0 @@
|
|||
## Process this file with automake to produce Makefile.in
|
||||
|
||||
pluginlibdir = $(gimpplugindir)/plug-ins
|
||||
|
||||
pluginlib_PROGRAMS = refract
|
||||
|
||||
refract_SOURCES = \
|
||||
refmain.c \
|
||||
refguts.c \
|
||||
refract.h \
|
||||
$(top_srcdir)/plug-ins/megawidget/megawidget.h
|
||||
|
||||
INCLUDES = \
|
||||
$(X_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
-I$(includedir)
|
||||
|
||||
LDADD = \
|
||||
$(top_builddir)/plug-ins/megawidget/libmegawidget.a \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la \
|
||||
$(X_LIBS) \
|
||||
-lc
|
||||
|
||||
DEPS = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/plug-ins/megawidget/libmegawidget.a \
|
||||
$(top_builddir)/libgimp/libgimp.la
|
||||
|
||||
refract_DEPENDENCIES = $(DEPS)
|
||||
|
||||
.PHONY: files
|
||||
|
||||
files:
|
||||
@files=`ls $(DISTFILES) 2> /dev/null`; for p in $$files; do \
|
||||
echo $$p; \
|
||||
done
|
||||
@for subdir in $(SUBDIRS); do \
|
||||
files=`cd $$subdir; $(MAKE) files | grep -v "make\[[1-9]\]"`; \
|
||||
for file in $$files; do \
|
||||
echo $$subdir/$$file; \
|
||||
done; \
|
||||
done
|
|
@ -1,48 +0,0 @@
|
|||
refract: A plug-in for the GIMP 0.99
|
||||
by Kevin Turner <kevint@poboxes.com>
|
||||
http://www.poboxes.com/kevint/gimp/refract.html
|
||||
|
||||
Refract distorts an image by passing it through the lens. The side of
|
||||
the lens towards the image is flat, the shape the other side is
|
||||
determined by a height map; a grayscale image where white pixels are
|
||||
high, black pixels are low, and anything between is somewhere
|
||||
inbetween. (Refract will accept an RGB image as a lens map, but will
|
||||
only use the first channel.)
|
||||
|
||||
The thickness of the lens is determined by the "Thickness"
|
||||
paramater. The "Distance" parameter is the distance between the
|
||||
bottom of the lens and the image. (The distance between the observer
|
||||
and the image is fixed at somewhere around infinity minus one.
|
||||
Fortunately, there are no perspective effects.)
|
||||
|
||||
The two indicies of refraction describe what substances you're
|
||||
looking through. Index A is for the substance between you and the
|
||||
lens, index B is that of the material the lens is crafted from. So
|
||||
when looking from air in to water, index A would be about 1 and index
|
||||
B is 1.333. These indicies are physical constants and can be obtained
|
||||
by looking in your copy of the CRC, or using the samples provided.
|
||||
|
||||
The X and Y offsets move the position of the lens. Sorry,
|
||||
a preview image is on the TO DO list, but it ain't here yet. The
|
||||
resulting image can be placed on a new layer by checking the "New
|
||||
layer" checkbox.
|
||||
|
||||
Read the code and the aformentioned web page for more
|
||||
information. Questions, comments, reservations, and bug reports are
|
||||
always welcome.
|
||||
|
||||
* * *
|
||||
|
||||
I'm not a very expirenced C programmer, so questions, comments, and
|
||||
reservations on code and style are more than welcome. This plug-in
|
||||
was developed on Linux and I will be the first to admit that I'm
|
||||
rather inexpirenced (okay, ignorant) with other operating systems.
|
||||
If I do wrong, educate me.
|
||||
|
||||
Credits:
|
||||
Pixel fetcher routines are from Quartic's whirlpinch plug-in. Thanks,
|
||||
Quartic[1]!
|
||||
|
||||
1: Quartic, AKA Federico Mena-Quintero
|
||||
federico@nuclecu.unam.mx
|
||||
http://www.nuclecu.unam.mx/~federico
|
|
@ -1,27 +0,0 @@
|
|||
TO DO:
|
||||
|
||||
code:
|
||||
Do The Right Thing with respect to row buffers, macros, and inline functions.
|
||||
Have the plug-in return the ID of the new layer, if it created one.
|
||||
|
||||
UI:
|
||||
megawidgets are insufficient. (No way to integrate entry_scale
|
||||
with tooltips or option_menu). Replace them.
|
||||
|
||||
necessary luxuries:
|
||||
Add radio buttons for edge wrapping options.
|
||||
|
||||
nicities:
|
||||
Find why two undo steps are required to undo.
|
||||
Find a way to reduce the speckling.
|
||||
|
||||
excess luxuries:
|
||||
Variable IOR information in some [alpha?] channel.
|
||||
|
||||
for version 1.1:
|
||||
THIS PLUGIN NEEDS A PREVIEW THING!
|
||||
Reflections
|
||||
|
||||
for version > 1.1:
|
||||
Diffraction or whatever that thing that makes rainbows is called.
|
||||
Lighting
|
|
@ -1,539 +0,0 @@
|
|||
/* refguts.c, 1/2/98 - this file contains the icky stuff.
|
||||
* refract: a plug-in for the GIMP 0.99
|
||||
* By Kevin Turner <kevint@poboxes.com>
|
||||
* http://www.poboxes.com/kevint/gimp/refract.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*
|
||||
*/
|
||||
|
||||
/* Refresher course in optics:
|
||||
Incident ray is the light ray hitting the surface.
|
||||
Angles are measured from the perpendicular to the surface.
|
||||
Angle of reflection is equal to angle of incidence.
|
||||
Angle of refraction is determined by
|
||||
|
||||
Snell's law: index[a] * sin(a) = index[b] * sin(b)
|
||||
|
||||
If second index is smaller than first, light is bent toward normal.
|
||||
Otherwise, away.
|
||||
*/
|
||||
|
||||
#include "refract.h"
|
||||
#include "libgimp/gimp.h"
|
||||
|
||||
typedef struct { /* Quartic's pixelfetcher thing */
|
||||
gint col, row;
|
||||
gint img_width, img_height, img_bpp, img_has_alpha;
|
||||
gint tile_width, tile_height;
|
||||
guchar bg_color[4];
|
||||
GDrawable *drawable;
|
||||
GTile *tile;
|
||||
} pixel_fetcher_t;
|
||||
|
||||
extern RefractValues refractvals;
|
||||
|
||||
void go_refract(GDrawable *drawable,
|
||||
gint32 image_id);
|
||||
static void do_refract(GPixelRgn *dest_rgn,
|
||||
GPixelRgn *lens_rgn,
|
||||
pixel_fetcher_t *pf);
|
||||
static gint delta (gdouble *offset, gdouble slope, gint height);
|
||||
#ifndef OLD_SLOPE_MACROS
|
||||
static gdouble slope(gint h, /* FIXME: I should probably be inlined. */
|
||||
HEIGHT_TYPE p1,
|
||||
HEIGHT_TYPE p2,
|
||||
HEIGHT_TYPE p3,
|
||||
HEIGHT_TYPE p4);
|
||||
#endif
|
||||
|
||||
/* More pixelfetcher things */
|
||||
static pixel_fetcher_t *pixel_fetcher_new(GDrawable *drawable);
|
||||
static void pixel_fetcher_set_bg_color(pixel_fetcher_t *pf, guchar r, guchar g, guchar b, guchar a);
|
||||
static void pixel_fetcher_get_pixel(pixel_fetcher_t *pf, int x, int y, guchar *pixel);
|
||||
static void pixel_fetcher_destroy(pixel_fetcher_t *pf);
|
||||
|
||||
/* This bilinear interpolation function also borrowed. */
|
||||
static guchar bilinear_new (double x,
|
||||
double y,
|
||||
guchar v[4][4],
|
||||
guint8 i);
|
||||
|
||||
static gint sel_x1=-1,sel_x2=-1,sel_y1=-1,sel_y2=-1;
|
||||
static gint sel_w, sel_h;
|
||||
static guchar fg_color[4];
|
||||
|
||||
void
|
||||
go_refract( GDrawable * drawable, gint32 image_id)
|
||||
{
|
||||
/* For Initialize pixel fetcher. */
|
||||
pixel_fetcher_t *pf;
|
||||
guchar bg_color[4];
|
||||
|
||||
/* For Initialize lens region. */
|
||||
GDrawable *lensmap;
|
||||
GPixelRgn lens_rgn;
|
||||
gint lxoff, lyoff;
|
||||
#if 0
|
||||
gint use_x1,use_x2,use_y1,use_y2, use_w, use_h;
|
||||
#endif
|
||||
|
||||
/* For Initialize dest region. */
|
||||
GPixelRgn dest_rgn;
|
||||
GDrawable *output_drawable;
|
||||
gint32 new_layer_id;
|
||||
char buf[256];
|
||||
|
||||
/*****************************/
|
||||
/* Initialize pixel fetcher. */
|
||||
|
||||
gimp_drawable_mask_bounds (drawable->id, &sel_x1, &sel_y1, &sel_x2, &sel_y2);
|
||||
sel_w=sel_x2-sel_x1; sel_h=sel_y2-sel_y1;
|
||||
pf = pixel_fetcher_new(drawable);
|
||||
gimp_palette_get_background(&bg_color[0], &bg_color[1], &bg_color[2]);
|
||||
pixel_fetcher_set_bg_color(pf,
|
||||
bg_color[0],
|
||||
bg_color[1],
|
||||
bg_color[2],
|
||||
0);
|
||||
|
||||
/***************************/
|
||||
/* Initialize lens region: */
|
||||
|
||||
lensmap = gimp_drawable_get (refractvals.lens_id);
|
||||
|
||||
/* Fortunately, this isn't really run repeatedly, so it's OK if
|
||||
it's not all that compact, right? */
|
||||
|
||||
#ifdef __PSYCHIC_COMPILER__ /* If your compiler can read my mind better than I can. */
|
||||
|
||||
/* Crap. We need a smegging lens-wrap toggle. */
|
||||
|
||||
if (lens wrap) {
|
||||
|
||||
if (no lens offsets) {
|
||||
/* no problems. */
|
||||
lens_rgn = foo(sel_x1, sel_x2, sel_w, sel_h);
|
||||
/* To conserve resources, we might want to change that
|
||||
to take less if the lens stops before the image
|
||||
does. */
|
||||
} else { /* offsets. Uhoh. */
|
||||
if (lens_size >= drawable_size) { /* Do this for each dimension. */
|
||||
/* Oh, it'll be okay. We'll just add offset and take absmod. */
|
||||
if (split) {
|
||||
lens_rgn = wholething; /* Oh well, we'll take the whole thing. */
|
||||
} else { /* not split */
|
||||
lens_rgn = foo(sel_x1-xoff, sel_y1-yoff, sel_w, sel_h);
|
||||
} /* endif not split */
|
||||
} else { /* lens is smaller */
|
||||
if (split) { g_warning("refract: refguts.c: Go to hell.\n"); }
|
||||
else { lens_rgn= foo(sel_x1-xoff, sel_y1-yoff, sel_w, sel_h); }
|
||||
} /* lens is smaller */
|
||||
} /* endif offsets */
|
||||
|
||||
} else { /* no lens wrap */
|
||||
/* If there's no lens wrapping, I have no problem. It's yo
|
||||
own dang fault if your lens doesn't land on your drawable
|
||||
any more. */
|
||||
|
||||
/* Let's rub it in... */
|
||||
if (((xoff > 0) ? (xoff >= sel_w) : (-xoff <= lens_w)) ||
|
||||
((yoff > 0) ? (yoff >= sel_h) : (-yoff <= lens_h))) {
|
||||
g_warning("refract: refguts.c: loose nut detected between chair and keyboard.\n");
|
||||
g_error("refract: refguts.c: Offsets move lens off image.\n");
|
||||
} else {
|
||||
lens_rgn = foo(sel_x1-xoff, sel_y1-yoff, sel_w, sel_h);
|
||||
/* To conserve resources, we might want to change that
|
||||
to take less if the lens stops before the image
|
||||
does. */
|
||||
}
|
||||
|
||||
} /* endif no lens wrap */
|
||||
|
||||
#else /* Compiler requires actual code. */
|
||||
|
||||
gimp_drawable_offsets(lensmap->id,&lxoff, &lyoff);
|
||||
|
||||
#ifdef REFRACT_DEBUG
|
||||
|
||||
g_print("x: %d\ty: %d\tw: %d\th: %d\n",
|
||||
lxoff, lyoff,
|
||||
lensmap->width,lensmap->height);
|
||||
|
||||
#endif /* REFRACT_DEBUG */
|
||||
|
||||
#if 0 /* If we *didn't* wrap the lens... */
|
||||
if( (sel_x1 > (lxoff + lensmap->width)) ||
|
||||
(lxoff > sel_x2) ||
|
||||
(sel_y1 > (lyoff + lensmap->height)) ||
|
||||
(lyoff > sel_y2)) {
|
||||
g_error("refract:refguts.c:Selection and lens don't overlap. You lose.\n");
|
||||
} else {
|
||||
use_x1=MAX(sel_x1,lxoff);
|
||||
use_x2=MIN(sel_x2,lxoff + lensmap->width);
|
||||
use_y1=MAX(sel_y1,lyoff);
|
||||
use_y2=MIN(sel_y2,lyoff + lensmap->height);
|
||||
use_w=use_x2-use_x1;
|
||||
use_h=use_y2-use_y1;
|
||||
}
|
||||
#endif /* if we didn't wrap lenses */
|
||||
|
||||
gimp_pixel_rgn_init (&lens_rgn, lensmap,
|
||||
lxoff, lyoff, lensmap->width, lensmap->height,
|
||||
FALSE, FALSE);
|
||||
|
||||
#endif /* Compiler requires actual code. */
|
||||
|
||||
/**********************************/
|
||||
/* Initialize destination region: */
|
||||
|
||||
sprintf(buf,"Refracted %s",gimp_drawable_name(drawable->id));
|
||||
|
||||
if (refractvals.newl) { /* New layer? Yes... */
|
||||
new_layer_id=gimp_layer_new(image_id, buf, sel_w, sel_h,
|
||||
gimp_drawable_gray(drawable->id)
|
||||
? GRAYA_IMAGE : RGBA_IMAGE,
|
||||
100.0, NORMAL_MODE);
|
||||
/* For layer position (currently 0), how would I say
|
||||
"one above current layer"? */
|
||||
gimp_image_add_layer(image_id,new_layer_id,0);
|
||||
gimp_layer_set_offsets(new_layer_id, sel_x1, sel_y1);
|
||||
output_drawable=gimp_drawable_get(new_layer_id);
|
||||
} else { /* New layer No. */
|
||||
output_drawable=drawable;
|
||||
} /* New layer No. */
|
||||
|
||||
gimp_pixel_rgn_init (&dest_rgn, output_drawable,
|
||||
sel_x1, sel_y1, sel_w, sel_h,
|
||||
TRUE, TRUE);
|
||||
|
||||
#ifdef REFRACT_DEBUG
|
||||
g_print("drawable-id: %d\toutput-id: %d:\tlens_rgn-id: %d\n",
|
||||
drawable->id,output_drawable->id,lens_rgn.drawable->id);
|
||||
#endif
|
||||
|
||||
/********/
|
||||
/* Misc */
|
||||
|
||||
gimp_palette_get_foreground(&fg_color[0], &fg_color[1], &fg_color[2]);
|
||||
fg_color[3] = 255;
|
||||
|
||||
/**********/
|
||||
/* Do it! */
|
||||
|
||||
do_refract(&dest_rgn,&lens_rgn,pf);
|
||||
|
||||
/*************/
|
||||
/* Clean up. */
|
||||
|
||||
/* FIXME: If we are cancelled, make sure there's none of that
|
||||
unsightly new layer residue. */
|
||||
|
||||
pixel_fetcher_destroy(pf);
|
||||
|
||||
/* I hope this works... */
|
||||
|
||||
gimp_drawable_flush(output_drawable);
|
||||
gimp_drawable_merge_shadow(output_drawable->id,!refractvals.newl);
|
||||
gimp_drawable_update(output_drawable->id,sel_x1,sel_y1,sel_w,sel_h);
|
||||
gimp_drawable_detach(drawable);
|
||||
if (drawable != output_drawable) gimp_drawable_detach(output_drawable);
|
||||
gimp_drawable_detach(lensmap);
|
||||
|
||||
/* return (refractvals.newl ? new_layer_id : NULL); */
|
||||
|
||||
} /* go_refract */
|
||||
|
||||
#define ABSMOD(A,B) ( ((A) < 0) ? (((B) + (A)) % (B)) : ((A) % (B)) )
|
||||
|
||||
#define X(F) ( ABSMOD((F)+refractvals.xofs,lens_rgn->w) )
|
||||
#define Y(F) ( ABSMOD((F)+refractvals.yofs,lens_rgn->h) )
|
||||
|
||||
#define ROWM2 (lm_rowm2[ X(x) * lens_rgn->bpp ])
|
||||
#define ROWM1 (lm_rowm1[ X(x) * lens_rgn->bpp ])
|
||||
#define ROW0(F) (lm_row0[ X(x+(F)) * lens_rgn->bpp ])
|
||||
#define ROWP1 (lm_rowp1[ X(x) * lens_rgn->bpp ])
|
||||
#define ROWP2 (lm_rowp2[ X(x) * lens_rgn->bpp ])
|
||||
|
||||
#ifdef OLD_SLOPE_MACROS
|
||||
#define SLOPE_X ((gdouble) 1.0 / (12 * h) * ( ROW0(-2*h) - 8 * ROW0(-1*h) + 8 * ROW0(1*h) - ROW0(2*h) ) * depths )
|
||||
#define SLOPE_Y ((gdouble) 1.0 / (12 * h) * ( ROWM2 - 8 * ROWM1 + 8 * ROWP1 - ROWP2 ) * depths )
|
||||
#else /* Macros calling the slope function. Functionally equivillant. */
|
||||
#define SLOPE_X (slope(h,ROW0(-2*h), ROW0(-1*h), ROW0(1*h), ROW0(2*h)))
|
||||
#define SLOPE_Y (slope(h,ROWM2, ROWM1, ROWP1, ROWP2))
|
||||
#endif /* OLD_SLOPE_MACROS */
|
||||
|
||||
static void
|
||||
do_refract(GPixelRgn *dest_rgn, GPixelRgn *lens_rgn,
|
||||
pixel_fetcher_t *pf)
|
||||
{
|
||||
HEIGHT_TYPE *lm_rowm2, *lm_rowm1, *lm_row0, *lm_rowp1, *lm_rowp2;
|
||||
HEIGHT_TYPE *lm_rowfoo;
|
||||
|
||||
guchar pixel[4][4];
|
||||
guint8 i, j;
|
||||
gint8 diff_bpp;
|
||||
guchar *dest, *dest_row;
|
||||
gdouble dx, dy;
|
||||
gint x, y, xf, yf;
|
||||
|
||||
gdouble depths=(gdouble) refractvals.thick/ (gdouble) 256.0; /* Depth scalar */
|
||||
const gint h=1; /* The delta value for the slope interpolation equation. */
|
||||
/* FIXME: Give option of changing h? */
|
||||
|
||||
/* See if dest_rgn and pf have different bpp */
|
||||
diff_bpp = dest_rgn->bpp - pf->img_bpp;
|
||||
|
||||
/***************/
|
||||
/* Allocations */
|
||||
|
||||
lm_rowm2 = g_malloc(lens_rgn->w * lens_rgn->bpp * sizeof(HEIGHT_TYPE));
|
||||
lm_rowm1 = g_malloc(lens_rgn->w * lens_rgn->bpp * sizeof(HEIGHT_TYPE));
|
||||
lm_row0 = g_malloc(lens_rgn->w * lens_rgn->bpp * sizeof(HEIGHT_TYPE));
|
||||
lm_rowp1 = g_malloc(lens_rgn->w * lens_rgn->bpp * sizeof(HEIGHT_TYPE));
|
||||
lm_rowp2 = g_malloc(lens_rgn->w * lens_rgn->bpp * sizeof(HEIGHT_TYPE));
|
||||
|
||||
dest_row = g_malloc(dest_rgn->w * dest_rgn->bpp * sizeof(guchar));
|
||||
|
||||
/************************/
|
||||
/* Grab some lens rows. */
|
||||
|
||||
gimp_pixel_rgn_get_row(lens_rgn, lm_rowm2, 0, Y(sel_y1 - 2*h), lens_rgn->w);
|
||||
gimp_pixel_rgn_get_row(lens_rgn, lm_rowm1, 0, Y(sel_y1 - 1*h), lens_rgn->w);
|
||||
gimp_pixel_rgn_get_row(lens_rgn, lm_row0, 0, Y(sel_y1), lens_rgn->w);
|
||||
gimp_pixel_rgn_get_row(lens_rgn, lm_rowp1, 0, Y(sel_y1 + 1*h), lens_rgn->w);
|
||||
gimp_pixel_rgn_get_row(lens_rgn, lm_rowp2, 0, Y(sel_y1 + 2*h), lens_rgn->w);
|
||||
|
||||
/***********************/
|
||||
/* Let's begin work... */
|
||||
for (y=sel_y1; y < sel_y2; y++) {
|
||||
|
||||
gimp_pixel_rgn_get_row(dest_rgn, dest_row, sel_x1, y, sel_w);
|
||||
dest = dest_row;
|
||||
|
||||
for (x=sel_x1; x < sel_x2; x++) {
|
||||
|
||||
/* If offsets in both X and Y direction exist... */
|
||||
/* (meaning no internal refraction) */
|
||||
if (delta(&dx, SLOPE_X, ROW0(0) * depths) &&
|
||||
delta(&dy, SLOPE_Y, ROW0(0) * depths)) {
|
||||
|
||||
switch (refractvals.edge) {
|
||||
case WRAP:
|
||||
xf = ABSMOD(x + (gint) dx, dest_rgn->drawable->width);
|
||||
yf = ABSMOD(y + (gint) dy, dest_rgn->drawable->height);
|
||||
break;
|
||||
case BACKGROUND:
|
||||
case OUTSIDE:
|
||||
xf = x + (gint) dx;
|
||||
yf = y + (gint) dy;
|
||||
break;
|
||||
default:
|
||||
g_error("refract: refract.c: Unanticipated value for edge in do_refract\n");
|
||||
} /* switch refractvals.edge */
|
||||
|
||||
pixel_fetcher_get_pixel(pf, xf, yf, pixel[0]);
|
||||
pixel_fetcher_get_pixel(pf, xf + 1, yf, pixel[1]);
|
||||
pixel_fetcher_get_pixel(pf, xf, yf + 1, pixel[2]);
|
||||
pixel_fetcher_get_pixel(pf, xf + 1, yf + 1, pixel[3]);
|
||||
|
||||
for (i = 0; i < pf->img_bpp; i++) {
|
||||
*dest++ = bilinear_new(dx, dy, pixel, i);
|
||||
} /* next i */
|
||||
/* If dest_rgn has more bpp than pf's source,
|
||||
then fill in the rest with 255's... This helps
|
||||
when making a new layer from a non-alpha layer. */
|
||||
for (j = 0; j < diff_bpp; j++) {
|
||||
*dest++ = 255;
|
||||
}
|
||||
|
||||
} else { /* if a delta() call returns false. */
|
||||
for (i = 0; i < dest_rgn->bpp; i++) {
|
||||
*dest++ = fg_color[i];
|
||||
} /* next i */
|
||||
} /* endif delta() */
|
||||
} /* next x */
|
||||
|
||||
gimp_pixel_rgn_set_row(dest_rgn, dest_row, sel_x1, y, sel_w);
|
||||
|
||||
if (!(y % PROGRESS_ROWS))
|
||||
gimp_progress_update((double) (y-sel_y1) / (double) (sel_y2-sel_y1));
|
||||
|
||||
/* move lensmap pointers */
|
||||
|
||||
lm_rowfoo=lm_rowm2;
|
||||
lm_rowm2=lm_rowm1;
|
||||
lm_rowm1=lm_row0;
|
||||
lm_row0= lm_rowp1;
|
||||
lm_rowp1=lm_rowp2;
|
||||
lm_rowp2=lm_rowfoo;
|
||||
|
||||
/* get new lensmap row */
|
||||
|
||||
gimp_pixel_rgn_get_row(lens_rgn, lm_rowp2, 0, Y(y+3*h), lens_rgn->w);
|
||||
|
||||
} /* next y */
|
||||
} /* do_refract */
|
||||
|
||||
#ifndef OLD_SLOPE_MACROS
|
||||
static gdouble /* FIXME: I should probably be inlined. */
|
||||
slope(gint h, HEIGHT_TYPE p1, HEIGHT_TYPE p2, HEIGHT_TYPE p3, HEIGHT_TYPE p4)
|
||||
{
|
||||
/* p1 = f(x-2h), p2 = f(x-1h), p3 = f(x+1h), p4=f(x+2h) */
|
||||
return 1.0 / (12 * h) * ( p1 - 8 * p2 + 8 * p3 - p4 );
|
||||
}
|
||||
#endif /* OLD_SLOPE_MACROS */
|
||||
|
||||
static gint
|
||||
delta(gdouble *offset, gdouble slope, gint height)
|
||||
{
|
||||
gdouble alpha, beta;
|
||||
|
||||
alpha = atan(slope);
|
||||
|
||||
if( alpha > asin( refractvals.nb / refractvals.na )) {
|
||||
return FALSE; /* Total Internal Refraction. Aiee! */
|
||||
}
|
||||
|
||||
beta = asin(refractvals.na * sin(alpha)/refractvals.nb);
|
||||
*offset = -(refractvals.refr_dist + height) * tan(beta - alpha);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* A "borrowed" bilinear interpolation function, modified to select from a
|
||||
two dimensional array instead of a linear one. */
|
||||
static guchar
|
||||
bilinear_new(double x, double y, guchar values[4][4], guint8 i)
|
||||
{
|
||||
double m0, m1;
|
||||
|
||||
x = fmod(x, 1.0);
|
||||
y = fmod(y, 1.0);
|
||||
|
||||
if (x < 0.0)
|
||||
x += 1.0;
|
||||
|
||||
if (y < 0.0)
|
||||
y += 1.0;
|
||||
|
||||
m0 = (double) values[0][i] + x * ((double) values[1][i] - values[0][i]);
|
||||
m1 = (double) values[2][i] + x * ((double) values[3][i] - values[2][i]);
|
||||
|
||||
return (guchar) (m0 + y * (m1 - m0));
|
||||
} /* bilinear_new */
|
||||
|
||||
/************************************************************************
|
||||
*
|
||||
* Fun pixel fetching stuff... Quartic's code from whirlpinch.c
|
||||
* Uses the globals sel_x1,sel_x2,sel_y1,sel_y2.
|
||||
*/
|
||||
|
||||
static pixel_fetcher_t *
|
||||
pixel_fetcher_new(GDrawable *drawable)
|
||||
{
|
||||
pixel_fetcher_t *pf;
|
||||
|
||||
pf = g_malloc(sizeof(pixel_fetcher_t));
|
||||
|
||||
pf->col = -1;
|
||||
pf->row = -1;
|
||||
pf->img_width = drawable->width;
|
||||
pf->img_height = drawable->height;
|
||||
pf->img_bpp = drawable->bpp;
|
||||
pf->img_has_alpha = gimp_drawable_has_alpha(drawable->id);
|
||||
pf->tile_width = gimp_tile_width();
|
||||
pf->tile_height = gimp_tile_height();
|
||||
pf->bg_color[0] = 0;
|
||||
pf->bg_color[1] = 0;
|
||||
pf->bg_color[2] = 0;
|
||||
pf->bg_color[3] = 0;
|
||||
|
||||
pf->drawable = drawable;
|
||||
pf->tile = NULL;
|
||||
|
||||
return pf;
|
||||
} /* pixel_fetcher_new */
|
||||
|
||||
|
||||
/*****/
|
||||
|
||||
static void
|
||||
pixel_fetcher_set_bg_color(pixel_fetcher_t *pf, guchar r, guchar g, guchar b, guchar a)
|
||||
{
|
||||
pf->bg_color[0] = r;
|
||||
pf->bg_color[1] = g;
|
||||
pf->bg_color[2] = b;
|
||||
|
||||
if (pf->img_has_alpha)
|
||||
pf->bg_color[pf->img_bpp - 1] = a;
|
||||
} /* pixel_fetcher_set_bg_color */
|
||||
|
||||
|
||||
/*****/
|
||||
|
||||
static void
|
||||
pixel_fetcher_get_pixel(pixel_fetcher_t *pf, int x, int y, guchar *pixel)
|
||||
{
|
||||
gint col, row;
|
||||
gint coloff, rowoff;
|
||||
guchar *p;
|
||||
int i;
|
||||
|
||||
if ((x < sel_x1) || (x >= sel_x2) ||
|
||||
(y < sel_y1) || (y >= sel_y2)) {
|
||||
for (i = 0; i < pf->img_bpp; i++)
|
||||
pixel[i] = pf->bg_color[i];
|
||||
|
||||
return;
|
||||
} /* if */
|
||||
|
||||
col = x / pf->tile_width;
|
||||
coloff = x % pf->tile_width;
|
||||
row = y / pf->tile_height;
|
||||
rowoff = y % pf->tile_height;
|
||||
|
||||
if ((col != pf->col) ||
|
||||
(row != pf->row) ||
|
||||
(pf->tile == NULL)) {
|
||||
if (pf->tile != NULL)
|
||||
gimp_tile_unref(pf->tile, FALSE);
|
||||
|
||||
pf->tile = gimp_drawable_get_tile(pf->drawable, FALSE, row, col);
|
||||
gimp_tile_ref(pf->tile);
|
||||
|
||||
pf->col = col;
|
||||
pf->row = row;
|
||||
} /* if */
|
||||
|
||||
p = pf->tile->data + pf->img_bpp * (pf->tile->ewidth * rowoff + coloff);
|
||||
|
||||
for (i = pf->img_bpp; i; i--)
|
||||
*pixel++ = *p++;
|
||||
} /* pixel_fetcher_get_pixel */
|
||||
|
||||
|
||||
/*****/
|
||||
|
||||
static void
|
||||
pixel_fetcher_destroy(pixel_fetcher_t *pf)
|
||||
{
|
||||
if (pf->tile != NULL)
|
||||
gimp_tile_unref(pf->tile, FALSE);
|
||||
|
||||
g_free(pf);
|
||||
} /* pixel_fetcher_destroy */
|
|
@ -1,536 +0,0 @@
|
|||
/* refmain.c, 1/2/98 - this file contains startup routine and dialogs.
|
||||
* refract: A plug-in for the GIMP 0.99.
|
||||
* Uses a height field as a lens of specified refraction index.
|
||||
*
|
||||
* by Kevin Turner <kevint@poboxes.com>
|
||||
* http://www.poboxes.com/kevint/gimp/refract.html
|
||||
*/
|
||||
|
||||
/* I require megawidgets to compile! A copy was probably compiled in
|
||||
the plug-ins directory of your GIMP source distribution, it will
|
||||
work nicely. Just move me or it somewhere I can see it... */
|
||||
|
||||
/*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#ifdef REFRACT_DEBUG
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <signal.h>
|
||||
#endif /* DEBUG */
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <math.h> /* It's not clear to me if this needs be here or no... */
|
||||
#include "refract.h"
|
||||
#include "libgimp/gimp.h"
|
||||
#include "libgimp/gimpui.h"
|
||||
|
||||
/* megawidget.h could be in any of several places relative to us... */
|
||||
/* should this be an autoconf thing? */
|
||||
#ifdef HAVE_CONFIG_H /* We're part of the GIMP distribution. */
|
||||
#include <plug-ins/megawidget/megawidget.h>
|
||||
#else
|
||||
#include "megawidget.h"
|
||||
/* #include <megawidget.h> */
|
||||
#endif
|
||||
|
||||
typedef struct {
|
||||
gint run;
|
||||
} RefractInterface;
|
||||
|
||||
/* go_refract is in refguts.c */
|
||||
extern void go_refract(GDrawable *drawable,
|
||||
gint32 image_id);
|
||||
static void query (void);
|
||||
static void run (gchar *name,
|
||||
gint nparams,
|
||||
GParam *param,
|
||||
gint *nreturn_vals,
|
||||
GParam **return_vals);
|
||||
|
||||
static gint refract_dialog();
|
||||
static gint map_constrain(gint32 image_id,
|
||||
gint32 drawable_id,
|
||||
gpointer data);
|
||||
static void newl_toggle_callback (GtkWidget *widget,
|
||||
gpointer data);
|
||||
static void tooltips_toggle_callback (GtkWidget *widget,
|
||||
gpointer data);
|
||||
static void refract_close_callback(GtkWidget *widget,
|
||||
gpointer data);
|
||||
static void refract_ok_callback(GtkWidget *widget,
|
||||
gpointer data);
|
||||
static void map_menu_callback (gint32 id,
|
||||
gpointer data);
|
||||
static GtkWidget* ior_menu_new(GtkWidget *tieto);
|
||||
static void ior_menu_callback (GtkWidget *widget,
|
||||
gfloat *data);
|
||||
|
||||
|
||||
GPlugInInfo PLUG_IN_INFO =
|
||||
{
|
||||
NULL, /* init_proc */
|
||||
NULL, /* quit_proc */
|
||||
query, /* query_proc */
|
||||
run, /* run_proc */
|
||||
};
|
||||
|
||||
/* refractvals defined in refract.h */
|
||||
/* not static, used in refguts.c */
|
||||
RefractValues refractvals =
|
||||
{
|
||||
-1, /* Lens map ID */
|
||||
-1, /* Reflection source ID */
|
||||
32, /* lens thickness */
|
||||
0, /* lens to image distance */
|
||||
64, /* lens to reflection source distance */
|
||||
1.0003, /* index a */
|
||||
1.333, /* index b */
|
||||
WRAP, /* wrap behaviour */
|
||||
FALSE, /* new layer? */
|
||||
0, /* offset x */
|
||||
0, /* offset y */
|
||||
};
|
||||
|
||||
static RefractInterface refractint =
|
||||
{
|
||||
FALSE /* run */
|
||||
};
|
||||
|
||||
MAIN ()
|
||||
|
||||
static void
|
||||
query ()
|
||||
{
|
||||
static GParamDef args[] =
|
||||
{
|
||||
{ PARAM_INT32, "run_mode", "Interactive, non-interactive" },
|
||||
{ PARAM_IMAGE, "image", "Input image" },
|
||||
{ PARAM_DRAWABLE, "drawable", "Input drawable" },
|
||||
/* If we did have parameters, these be them: */
|
||||
{ PARAM_DRAWABLE, "lens_id", "Lens map drawable" },
|
||||
{ PARAM_DRAWABLE, "refl_id", "Reflection source drawable." },
|
||||
{ PARAM_INT32, "thick", "Lens thickness" },
|
||||
{ PARAM_INT32, "refr_dist", "Lens distance from image" },
|
||||
{ PARAM_INT32, "refl_dist", "Lens distance from reflection source" },
|
||||
{ PARAM_FLOAT, "na", "Index of Refraction A" },
|
||||
{ PARAM_FLOAT, "nb", "Index of Refraction B" },
|
||||
{ PARAM_INT32, "edge", "Background (0), Outside (1), Wrap (2)" },
|
||||
{ PARAM_INT32, "newl", "New layer?" },
|
||||
{ PARAM_INT32, "xofs", "X offset" },
|
||||
{ PARAM_INT32, "yofs", "Y offset" }
|
||||
};
|
||||
static GParamDef *return_vals = NULL;
|
||||
static int nargs = sizeof (args) / sizeof (args[0]);
|
||||
static int nreturn_vals = 0;
|
||||
|
||||
gimp_install_procedure ("plug_in_refract",
|
||||
"Uses a height field as a lens.",
|
||||
"Distorts the image by refracting it through a height field 'lens' with a specified index of refraction.",
|
||||
"Kevin Turner <kevint@poboxes.com>",
|
||||
"Kevin Turner",
|
||||
"1997",
|
||||
"<Image>/Filters/Glass Effects/Refract",
|
||||
"RGB*, GRAY*, INDEXED*",
|
||||
PROC_PLUG_IN,
|
||||
nargs, nreturn_vals,
|
||||
args, return_vals);
|
||||
} /* query */
|
||||
|
||||
static void
|
||||
run (gchar *name,
|
||||
gint nparams,
|
||||
GParam *param,
|
||||
gint *nreturn_vals,
|
||||
GParam **return_vals)
|
||||
{
|
||||
static GParam values[1];
|
||||
GDrawable *drawable;
|
||||
GRunModeType run_mode;
|
||||
GStatusType status = STATUS_SUCCESS;
|
||||
|
||||
#ifdef REFRACT_DEBUG
|
||||
printf("refract: pid %d\n", getpid());
|
||||
#endif
|
||||
|
||||
/* values=g_new(GParam,1); */
|
||||
|
||||
run_mode = param[0].data.d_int32;
|
||||
|
||||
*nreturn_vals = 1;
|
||||
*return_vals = values;
|
||||
|
||||
values[0].type = PARAM_STATUS;
|
||||
values[0].data.d_status = status;
|
||||
|
||||
drawable = gimp_drawable_get (param[2].data.d_drawable);
|
||||
|
||||
switch (run_mode) {
|
||||
case RUN_INTERACTIVE:
|
||||
/* Possibly retrieve data */
|
||||
gimp_get_data ("plug_in_refract", &refractvals);
|
||||
|
||||
/* Acquire info with a dialog */
|
||||
if (! refract_dialog ()) {
|
||||
gimp_drawable_detach (drawable);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
|
||||
case RUN_NONINTERACTIVE:
|
||||
if (status == STATUS_SUCCESS) {
|
||||
refractvals.lens_id = param[3].data.d_drawable;
|
||||
refractvals.refl_id = param[4].data.d_int32;
|
||||
refractvals.thick = param[5].data.d_int32;
|
||||
refractvals.refr_dist = param[6].data.d_float;
|
||||
refractvals.refl_dist = param[7].data.d_float;
|
||||
refractvals.na = param[8].data.d_int32;
|
||||
refractvals.nb = param[9].data.d_int32;
|
||||
refractvals.edge = param[10].data.d_int32;
|
||||
refractvals.newl = param[11].data.d_int32;
|
||||
refractvals.xofs = param[12].data.d_int32;
|
||||
refractvals.yofs = param[13].data.d_int32;
|
||||
} /* if */
|
||||
|
||||
break;
|
||||
|
||||
case RUN_WITH_LAST_VALS:
|
||||
/* Possibly retrieve data */
|
||||
gimp_get_data ("plug_in_refract", &refractvals);
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
} /* switch run_mode */
|
||||
|
||||
if (gimp_drawable_color (drawable->id) || gimp_drawable_gray (drawable->id)) {
|
||||
gimp_progress_init ("Doing optics homework...");
|
||||
|
||||
/* What's this do? */
|
||||
gimp_tile_cache_ntiles(2 * (drawable->width + gimp_tile_width() - 1)
|
||||
/ gimp_tile_width());
|
||||
|
||||
go_refract (drawable, param[1].data.d_image);
|
||||
|
||||
if (run_mode != RUN_NONINTERACTIVE)
|
||||
gimp_displays_flush ();
|
||||
|
||||
if (run_mode == RUN_INTERACTIVE /*|| run_mode == RUN_WITH_LAST_VALS*/)
|
||||
gimp_set_data ("plug_in_refract", &refractvals, sizeof (RefractValues));
|
||||
} else {
|
||||
status = STATUS_EXECUTION_ERROR;
|
||||
}
|
||||
|
||||
values[0].data.d_status = status;
|
||||
|
||||
} /* run */
|
||||
|
||||
static gint
|
||||
refract_dialog()
|
||||
{
|
||||
gint argc;
|
||||
gchar **argv;
|
||||
|
||||
GtkTooltips *tooltips;
|
||||
GtkWidget *menu, *option_menu, *ior_a_menu, *ior_b_menu;
|
||||
GtkWidget *ok_button, *cancel_button;
|
||||
GtkWidget *layercheck, *toolcheck;
|
||||
GtkWidget *dlg;
|
||||
GtkWidget *table;
|
||||
GtkWidget *label;
|
||||
|
||||
#ifdef REFRACT_DEBUG
|
||||
#if 0
|
||||
printf("refract: waiting... (pid %d)\n", getpid());
|
||||
kill(getpid(), SIGSTOP);
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* Standard GTK startup sequence */
|
||||
argc = 1;
|
||||
argv = g_new (gchar *, 1);
|
||||
argv[0] = g_strdup ("refract");
|
||||
|
||||
gtk_init (&argc, &argv);
|
||||
|
||||
gdk_set_use_xshm(gimp_use_xshm());
|
||||
|
||||
/* FIXME: Can we use the GIMP colormap when in 8-bit to reduce flashing? */
|
||||
/* end standard GTK startup */
|
||||
|
||||
/* I guess we need a window... */
|
||||
dlg = gtk_dialog_new();
|
||||
gtk_window_set_title(GTK_WINDOW(dlg), REFRACT_TITLE);
|
||||
gtk_signal_connect(GTK_OBJECT(dlg), "destroy",
|
||||
(GtkSignalFunc) refract_close_callback,
|
||||
NULL);
|
||||
|
||||
tooltips = gtk_tooltips_new ();
|
||||
|
||||
/* Action area: */
|
||||
|
||||
/* OK */
|
||||
ok_button = gtk_button_new_with_label ("OK");
|
||||
GTK_WIDGET_SET_FLAGS (ok_button, GTK_CAN_DEFAULT);
|
||||
gtk_signal_connect (GTK_OBJECT (ok_button), "clicked",
|
||||
(GtkSignalFunc) refract_ok_callback, dlg);
|
||||
gtk_widget_grab_default (ok_button);
|
||||
gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dlg)->action_area), ok_button,
|
||||
TRUE, TRUE, 0);
|
||||
gtk_widget_show (ok_button);
|
||||
|
||||
/* Cancel */
|
||||
cancel_button = gtk_button_new_with_label ("Cancel");
|
||||
GTK_WIDGET_SET_FLAGS (cancel_button, GTK_CAN_DEFAULT);
|
||||
gtk_signal_connect_object (GTK_OBJECT (cancel_button), "clicked",
|
||||
(GtkSignalFunc) refract_close_callback,
|
||||
NULL);
|
||||
gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dlg)->action_area), cancel_button,
|
||||
TRUE, TRUE, 0);
|
||||
gtk_widget_show (cancel_button);
|
||||
|
||||
/* Paramater settings: */
|
||||
table = gtk_table_new(7, 3, FALSE);
|
||||
gtk_container_add(GTK_CONTAINER (GTK_DIALOG (dlg)->vbox),table);
|
||||
gtk_widget_show (table);
|
||||
|
||||
/* FIXME: add preview box */
|
||||
|
||||
/* drop box for lens map */
|
||||
label = gtk_label_new("Lens map");
|
||||
|
||||
option_menu = gtk_option_menu_new();
|
||||
|
||||
menu = gimp_drawable_menu_new(map_constrain, map_menu_callback,
|
||||
NULL, refractvals.lens_id);
|
||||
gtk_option_menu_set_menu(GTK_OPTION_MENU(option_menu),menu);
|
||||
gtk_tooltips_set_tips (tooltips, option_menu,
|
||||
"The drawable to use as the lens.");
|
||||
|
||||
gtk_table_attach_defaults(GTK_TABLE(table),label,0,1,0,1);
|
||||
gtk_table_attach_defaults(GTK_TABLE(table),option_menu,1,3,0,1);
|
||||
gtk_widget_show(label);
|
||||
gtk_widget_show(option_menu);
|
||||
|
||||
/* TODO? Add "Invert lens map" Not anytime soon... */
|
||||
/* Would require adding all sorts of conditional subtracting stuff
|
||||
in the main loop... Let them invert it first! :) */
|
||||
|
||||
/* Eek. Megawidgets don't return a value I can tie tooltips to.
|
||||
Maybe I should look in to libgck. */
|
||||
|
||||
/* entry/scale for lens thickness */
|
||||
|
||||
mw_iscale_entry_new(table, "Thickness",
|
||||
0, 256,
|
||||
1, 10, 0,
|
||||
0, 2, 1, 2,
|
||||
&refractvals.thick);
|
||||
|
||||
/* entry/scale pair for distance */
|
||||
mw_iscale_entry_new(table, "Distance",
|
||||
0, 1000,
|
||||
1, 10, 0/*what's this do?*/,
|
||||
0, 2, 2, 3,
|
||||
&refractvals.refr_dist);
|
||||
|
||||
/* a entry/scale/drop-menu for each index */
|
||||
mw_fscale_entry_new(table, "Index A",
|
||||
INDEX_SCALE_MIN, INDEX_SCALE_MAX,
|
||||
1.0, 0.1, 0,
|
||||
0,1, 3, 4,
|
||||
&refractvals.na);
|
||||
|
||||
ior_a_menu = ior_menu_new(NULL/*FIXME*/);
|
||||
gtk_table_attach_defaults(GTK_TABLE(table),ior_a_menu,2,3,3,4);
|
||||
gtk_widget_show (ior_a_menu);
|
||||
|
||||
gtk_tooltips_set_tips (tooltips, ior_a_menu,
|
||||
"FIXME (No, it doesn't work.)");
|
||||
|
||||
mw_fscale_entry_new(table, "Index B",
|
||||
INDEX_SCALE_MIN, INDEX_SCALE_MAX,
|
||||
1.0, 0.1, 0,
|
||||
0, 1, 4, 5,
|
||||
&refractvals.nb);
|
||||
|
||||
ior_b_menu = ior_menu_new(NULL/*FIXME*/);
|
||||
gtk_table_attach_defaults(GTK_TABLE(table),ior_b_menu,2,3,4,5);
|
||||
gtk_widget_show (ior_b_menu);
|
||||
|
||||
gtk_tooltips_set_tips (tooltips, ior_b_menu,
|
||||
"FIXME (No, it doesn't work.)");
|
||||
|
||||
/* entry/scale pairs for x and y offsets */
|
||||
|
||||
mw_iscale_entry_new(table, "X Offset",
|
||||
-1000, 1000,
|
||||
1, 20, 0,
|
||||
0,2, 5, 6,
|
||||
&refractvals.xofs);
|
||||
|
||||
mw_iscale_entry_new(table, "Y Offset",
|
||||
-1000, 1000,
|
||||
1, 20, 0,
|
||||
0,2, 6, 7,
|
||||
&refractvals.yofs);
|
||||
|
||||
/* radio buttons for wrap/transparent (or bg, if image isn't layered) */
|
||||
|
||||
/* button = gtk_check_button_new_with_label ("Wrap?");
|
||||
toggle_button_callback (button, gpointer data);
|
||||
gtk_toggle_button_set_state (GtkToggleButton button, refractvals.edge); */
|
||||
|
||||
/* Make new layer(s) or dirty the old? */
|
||||
layercheck = gtk_check_button_new_with_label ("New layer?");
|
||||
gtk_container_add(GTK_CONTAINER (GTK_DIALOG (dlg)->vbox),layercheck);
|
||||
gtk_signal_connect (GTK_OBJECT (layercheck), "clicked",
|
||||
GTK_SIGNAL_FUNC (newl_toggle_callback), NULL);
|
||||
gtk_toggle_button_set_state (GTK_TOGGLE_BUTTON (layercheck), refractvals.newl);
|
||||
gtk_tooltips_set_tips (tooltips, layercheck,
|
||||
"Put the refracted image on a new layer or dirty this one?");
|
||||
|
||||
gtk_widget_show (layercheck);
|
||||
|
||||
toolcheck = gtk_check_button_new_with_label ("Tooltips?");
|
||||
gtk_container_add(GTK_CONTAINER (GTK_DIALOG (dlg)->vbox),toolcheck);
|
||||
gtk_signal_connect (GTK_OBJECT (toolcheck), "clicked",
|
||||
GTK_SIGNAL_FUNC (tooltips_toggle_callback), (gpointer) tooltips);
|
||||
gtk_tooltips_set_tips (tooltips, toolcheck,
|
||||
"Turn off these dumb tooltips.");
|
||||
gtk_widget_show (toolcheck);
|
||||
|
||||
/* Tooltips OFF by default. */
|
||||
gtk_toggle_button_set_state (GTK_TOGGLE_BUTTON (toolcheck), FALSE);
|
||||
gtk_tooltips_disable (tooltips);
|
||||
|
||||
gtk_widget_show (dlg);
|
||||
|
||||
gtk_main ();
|
||||
gtk_object_unref (GTK_OBJECT (tooltips));
|
||||
gdk_flush ();
|
||||
|
||||
return refractint.run;
|
||||
} /* refract_dialog */
|
||||
|
||||
static GtkWidget*
|
||||
ior_menu_new(GtkWidget *tieto)
|
||||
{
|
||||
GtkWidget *chooser;
|
||||
GtkWidget *menu, *menuitem;
|
||||
guint i;
|
||||
|
||||
struct foo
|
||||
{
|
||||
const gfloat index;
|
||||
const gchar *name;
|
||||
};
|
||||
|
||||
/* If you change stuff, don't forget to change this. */
|
||||
#define NUMSTUFF 9
|
||||
static const struct foo material[NUMSTUFF] =
|
||||
{
|
||||
/* Common indicies of refraction (for yellow sodium light, 589 nm) */
|
||||
/* From my Sears, Zemansky, Young physics book. */
|
||||
/* For more, check your copy of the CRC or your favorite pov-ray
|
||||
include file. */
|
||||
|
||||
{ 1.0003, "Air" },
|
||||
{ 1.309, "Ice" },
|
||||
{ 1.333, "Water"},
|
||||
{ 1.36, "Alcohol"},
|
||||
{ 1.473, "Glycerine"},
|
||||
{ 1.52, "Glass"},
|
||||
{ 1.544, "Quartz"},
|
||||
{ 1.923, "Zircon"},
|
||||
{ 2.417, "Diamond"},
|
||||
};
|
||||
|
||||
chooser = gtk_option_menu_new();
|
||||
|
||||
menu = gtk_menu_new();
|
||||
|
||||
for (i=0; i < NUMSTUFF; i++) {
|
||||
menuitem = gtk_menu_item_new_with_label(material[i].name);
|
||||
gtk_menu_append(GTK_MENU(menu), menuitem);
|
||||
gtk_signal_connect(GTK_OBJECT(menuitem), "activate",
|
||||
(GtkSignalFunc)ior_menu_callback,(gfloat *)&material[i].index);
|
||||
gtk_widget_show(menuitem);
|
||||
}; /* next i */
|
||||
|
||||
gtk_option_menu_set_menu(GTK_OPTION_MENU(chooser), menu);
|
||||
|
||||
return chooser;
|
||||
}
|
||||
|
||||
static void
|
||||
ior_menu_callback (GtkWidget *widget, gfloat *data)
|
||||
{
|
||||
#ifdef REFRACT_DEBUG
|
||||
printf("%f\n",*data);
|
||||
#endif
|
||||
}
|
||||
|
||||
static gint
|
||||
map_constrain(gint32 image_id, gint32 drawable_id, gpointer data)
|
||||
{
|
||||
if (drawable_id == -1)
|
||||
return TRUE;
|
||||
|
||||
return (gimp_drawable_color(drawable_id) || gimp_drawable_gray(drawable_id));
|
||||
} /* map_constrain */
|
||||
|
||||
/* Callbacks */
|
||||
static void
|
||||
newl_toggle_callback (GtkWidget *widget, gpointer data)
|
||||
{
|
||||
refractvals.newl = GTK_TOGGLE_BUTTON (widget)->active;
|
||||
}
|
||||
|
||||
static void
|
||||
tooltips_toggle_callback (GtkWidget *widget, gpointer data)
|
||||
{
|
||||
GtkTooltips *tooltips;
|
||||
tooltips= (GtkTooltips *) data;
|
||||
|
||||
if (GTK_TOGGLE_BUTTON (widget)->active)
|
||||
gtk_tooltips_enable (tooltips);
|
||||
else
|
||||
gtk_tooltips_disable (tooltips);
|
||||
|
||||
}
|
||||
|
||||
static void
|
||||
refract_close_callback (GtkWidget *widget,
|
||||
gpointer data)
|
||||
{
|
||||
gtk_main_quit ();
|
||||
}
|
||||
|
||||
static void
|
||||
refract_ok_callback (GtkWidget *widget, gpointer data)
|
||||
{
|
||||
refractint.run = TRUE;
|
||||
gtk_widget_destroy (GTK_WIDGET (data));
|
||||
}
|
||||
|
||||
static void
|
||||
map_menu_callback (gint32 id, gpointer data)
|
||||
{
|
||||
refractvals.lens_id = id;
|
||||
}
|
|
@ -1,82 +0,0 @@
|
|||
/* refract.h, 1/2/98
|
||||
* refract: a plug-in for the GIMP 0.99
|
||||
* By Kevin Turner <kevint@poboxes.com>
|
||||
* http://www.poboxes.com/kevint/gimp/refract.html
|
||||
*/
|
||||
|
||||
#ifndef REFRACT_DEBUG
|
||||
#define REFRACT_TITLE "Refract 1/2/98-Beta"
|
||||
#else
|
||||
#define REFRACT_TITLE "Refract 1/2/98 (debug)"
|
||||
#endif
|
||||
|
||||
/* Update the progress bar every this-many rows... */
|
||||
#ifndef PROGRESS_ROWS
|
||||
#define PROGRESS_ROWS 8
|
||||
#endif
|
||||
|
||||
/* Realistically, this number should be 1.0. An index of refraction
|
||||
of less than 1 means the speed of light in that substance is
|
||||
*faster* than in a vacuum! But hey, it's GIMP, when was the last
|
||||
time we payed any attention to reality? Go ahead... Add
|
||||
"subspace" to the list of materials... */
|
||||
#ifndef INDEX_SCALE_MIN
|
||||
#define INDEX_SCALE_MIN 0.0
|
||||
#endif
|
||||
|
||||
/* This can be whatever is convient. However, I don't know of any
|
||||
substances (even artifically generated ones) that have an index of
|
||||
refraction higher than 4.7 or so...*/
|
||||
|
||||
#ifndef INDEX_SCALE_MAX
|
||||
#define INDEX_SCALE_MAX 5.0
|
||||
#endif
|
||||
|
||||
/* For now, our height maps only have one byte per pixel, so guchar
|
||||
should be sufficient. May need to change in future versions of
|
||||
GIMP when it supports greater pixel depth. */
|
||||
#ifndef HEIGHT_TYPE
|
||||
#define HEIGHT_TYPE guchar
|
||||
#endif
|
||||
|
||||
/* Should we rely more on macros or functions? */
|
||||
/* #define OLD_SLOPE_MACROS */
|
||||
|
||||
#include "gtk/gtk.h"
|
||||
|
||||
typedef struct {
|
||||
gint32 lens_id; /* lens map id */
|
||||
gint32 refl_id; /* Reflection source ID */
|
||||
gint32 thick; /* lens thickness */
|
||||
gint32 refr_dist; /* distance from lens to image. */
|
||||
gint32 refl_dist; /* Distance from lens/mirror to reflection source. */
|
||||
gdouble na; /* index a */
|
||||
gdouble nb; /* index b */
|
||||
gint32 edge; /* wrap/transparent */
|
||||
gint32 newl; /* new layer? */
|
||||
gint32 xofs; /* offset x */
|
||||
gint32 yofs; /* offset y */
|
||||
} RefractValues;
|
||||
|
||||
/* for refractvals.edge */
|
||||
/* If a point is outside the selection, then */
|
||||
#define BACKGROUND 0 /* use background color (or leave transparent, if alpha) */
|
||||
#define OUTSIDE 1 /* look outside the selection for the point. If the point is
|
||||
beyond the edge of the layer, use background or alpha.
|
||||
Only makes sense if the drawable is a selection of only part
|
||||
of the layer. */
|
||||
#define WRAP 2 /* like OUTSIDE, but if the point is over the edge of the layer,
|
||||
get the point by wrapping around. Probably most useful on
|
||||
images which are tileable. */
|
||||
|
||||
/* TO DO: provide a "smear" option? Would take whatever pixel was on
|
||||
the edge of the selection or layer (depending if IN_ONLY or
|
||||
OUTSIDE) where we went over. Then BACKGROUND/SMEAR would be a
|
||||
choice independant of IN_ONLY/OUTSIDE/WRAP. BACKGROUND/SMEAR would
|
||||
be ignored in the case of WRAP. */
|
||||
|
||||
/* One can also imagine a WRAP_WITHIN_SELECTION option, but I don't
|
||||
think I would use it too often. Would you? Well, if you're
|
||||
enthusiastic enough, either write a patch to implement it or
|
||||
convince me to. For now, take the selection and float it, make it
|
||||
a new layer, merge it back when you're done, or whatever. */
|
|
@ -1,6 +0,0 @@
|
|||
Makefile.in
|
||||
Makefile
|
||||
.deps
|
||||
_libs
|
||||
.libs
|
||||
warp
|
|
@ -1,43 +0,0 @@
|
|||
## Process this file with automake to produce Makefile.in
|
||||
|
||||
pluginlibdir = $(gimpplugindir)/plug-ins
|
||||
|
||||
pluginlib_PROGRAMS = warp
|
||||
|
||||
warp_SOURCES = \
|
||||
warp.c
|
||||
|
||||
INCLUDES = \
|
||||
$(X_CFLAGS) \
|
||||
-I$(top_srcdir) \
|
||||
-I$(includedir)
|
||||
|
||||
LDADD = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la \
|
||||
$(X_LIBS) \
|
||||
-lc
|
||||
|
||||
DEPS = \
|
||||
$(top_builddir)/libgimp/libgimpui.la \
|
||||
$(top_builddir)/libgimp/libgimp.la
|
||||
|
||||
warp_DEPENDENCIES = $(DEPS)
|
||||
|
||||
.PHONY: files
|
||||
|
||||
files:
|
||||
@files=`ls $(DISTFILES) 2> /dev/null`; for p in $$files; do \
|
||||
echo $$p; \
|
||||
done
|
||||
@for subdir in $(SUBDIRS); do \
|
||||
files=`cd $$subdir; $(MAKE) files | grep -v "make\[[1-9]\]"`; \
|
||||
for file in $$files; do \
|
||||
echo $$subdir/$$file; \
|
||||
done; \
|
||||
done
|
||||
|
||||
|
||||
|
||||
|
||||
|
1918
plug-ins/warp/warp.c
1918
plug-ins/warp/warp.c
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue