forked from old/legacy-imlib2
Much faster polygon clipping, made span() more sensible.
Added the function: unsigned char imlib_polygon_contains_point(ImlibPolygon poly, int x, int y); Tells you if a point lies in a polygon. Handy for apps that might want to test for "selection" of a polygon shape or something... SVN revision: 3355
This commit is contained in:
parent
d35f3a64d8
commit
cd464e9838
|
@ -334,6 +334,8 @@ extern "C"
|
|||
void imlib_image_fill_polygon(ImlibPolygon poly);
|
||||
void imlib_polygon_get_bounds(ImlibPolygon poly, int *px1, int *py1,
|
||||
int *px2, int *py2);
|
||||
unsigned char imlib_polygon_contains_point(ImlibPolygon poly, int x,
|
||||
int y);
|
||||
|
||||
/* ellipses */
|
||||
void imlib_image_draw_ellipse(int xc, int yc, int a, int b);
|
||||
|
|
189
src/api.c
189
src/api.c
|
@ -140,8 +140,7 @@ imlib_context_set_colormap(Colormap colormap)
|
|||
ctxt_colormap = colormap;
|
||||
}
|
||||
|
||||
Colormap
|
||||
imlib_context_get_colormap(void)
|
||||
Colormap imlib_context_get_colormap(void)
|
||||
{
|
||||
return ctxt_colormap;
|
||||
}
|
||||
|
@ -152,8 +151,7 @@ imlib_context_set_drawable(Drawable drawable)
|
|||
ctxt_drawable = drawable;
|
||||
}
|
||||
|
||||
Drawable
|
||||
imlib_context_get_drawable(void)
|
||||
Drawable imlib_context_get_drawable(void)
|
||||
{
|
||||
return ctxt_drawable;
|
||||
}
|
||||
|
@ -164,8 +162,7 @@ imlib_context_set_mask(Pixmap mask)
|
|||
ctxt_mask = mask;
|
||||
}
|
||||
|
||||
Pixmap
|
||||
imlib_context_get_mask(void)
|
||||
Pixmap imlib_context_get_mask(void)
|
||||
{
|
||||
return ctxt_mask;
|
||||
}
|
||||
|
@ -224,8 +221,7 @@ imlib_context_set_color_modifier(Imlib_Color_Modifier color_modifier)
|
|||
ctxt_color_modifier = color_modifier;
|
||||
}
|
||||
|
||||
Imlib_Color_Modifier
|
||||
imlib_context_get_color_modifier(void)
|
||||
Imlib_Color_Modifier imlib_context_get_color_modifier(void)
|
||||
{
|
||||
return ctxt_color_modifier;
|
||||
}
|
||||
|
@ -236,8 +232,7 @@ imlib_context_set_operation(Imlib_Operation operation)
|
|||
ctxt_operation = operation;
|
||||
}
|
||||
|
||||
Imlib_Operation
|
||||
imlib_context_get_operation(void)
|
||||
Imlib_Operation imlib_context_get_operation(void)
|
||||
{
|
||||
return ctxt_operation;
|
||||
}
|
||||
|
@ -248,8 +243,7 @@ imlib_context_set_font(Imlib_Font font)
|
|||
ctxt_font = font;
|
||||
}
|
||||
|
||||
Imlib_Font
|
||||
imlib_context_get_font(void)
|
||||
Imlib_Font imlib_context_get_font(void)
|
||||
{
|
||||
return ctxt_font;
|
||||
}
|
||||
|
@ -272,8 +266,7 @@ imlib_context_get_angle(void)
|
|||
return ctxt_angle;
|
||||
}
|
||||
|
||||
Imlib_Text_Direction
|
||||
imlib_context_get_direction(void)
|
||||
Imlib_Text_Direction imlib_context_get_direction(void)
|
||||
{
|
||||
return ctxt_direction;
|
||||
}
|
||||
|
@ -308,8 +301,7 @@ imlib_context_set_color_range(Imlib_Color_Range color_range)
|
|||
ctxt_color_range = color_range;
|
||||
}
|
||||
|
||||
Imlib_Color_Range
|
||||
imlib_context_get_color_range(void)
|
||||
Imlib_Color_Range imlib_context_get_color_range(void)
|
||||
{
|
||||
return ctxt_color_range;
|
||||
}
|
||||
|
@ -320,8 +312,7 @@ imlib_context_set_progress_function(Imlib_Progress_Function progress_function)
|
|||
ctxt_progress_func = progress_function;
|
||||
}
|
||||
|
||||
Imlib_Progress_Function
|
||||
imlib_context_get_progress_function(void)
|
||||
Imlib_Progress_Function imlib_context_get_progress_function(void)
|
||||
{
|
||||
return ctxt_progress_func;
|
||||
}
|
||||
|
@ -344,8 +335,7 @@ imlib_context_set_image(Imlib_Image image)
|
|||
ctxt_image = image;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_context_get_image(void)
|
||||
Imlib_Image imlib_context_get_image(void)
|
||||
{
|
||||
return ctxt_image;
|
||||
}
|
||||
|
@ -405,8 +395,7 @@ imlib_get_best_visual(Display * display, int screen, int *depth_return)
|
|||
return __imlib_BestVisual(display, screen, depth_return);
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_load_image(const char *file)
|
||||
Imlib_Image imlib_load_image(const char *file)
|
||||
{
|
||||
Imlib_Image im = NULL;
|
||||
Imlib_Image prev_ctxt_image;
|
||||
|
@ -420,8 +409,7 @@ imlib_load_image(const char *file)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_load_image_immediately(const char *file)
|
||||
Imlib_Image imlib_load_image_immediately(const char *file)
|
||||
{
|
||||
Imlib_Image im = NULL;
|
||||
Imlib_Image prev_ctxt_image;
|
||||
|
@ -436,8 +424,7 @@ imlib_load_image_immediately(const char *file)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_load_image_without_cache(const char *file)
|
||||
Imlib_Image imlib_load_image_without_cache(const char *file)
|
||||
{
|
||||
Imlib_Image im = NULL;
|
||||
Imlib_Image prev_ctxt_image;
|
||||
|
@ -452,8 +439,7 @@ imlib_load_image_without_cache(const char *file)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_load_image_immediately_without_cache(const char *file)
|
||||
Imlib_Image imlib_load_image_immediately_without_cache(const char *file)
|
||||
{
|
||||
Imlib_Image im = NULL;
|
||||
Imlib_Image prev_ctxt_image;
|
||||
|
@ -468,9 +454,9 @@ imlib_load_image_immediately_without_cache(const char *file)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_load_image_with_error_return(const char *file,
|
||||
Imlib_Load_Error * error_return)
|
||||
Imlib_Image imlib_load_image_with_error_return(const char *file,
|
||||
Imlib_Load_Error *
|
||||
error_return)
|
||||
{
|
||||
Imlib_Image im = NULL;
|
||||
ImlibLoadError er;
|
||||
|
@ -910,8 +896,7 @@ imlib_blend_image_onto_image(Imlib_Image source_image, char merge_alpha,
|
|||
ctxt_color_modifier, ctxt_operation);
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_image(int width, int height)
|
||||
Imlib_Image imlib_create_image(int width, int height)
|
||||
{
|
||||
DATA32 *data;
|
||||
|
||||
|
@ -923,8 +908,8 @@ imlib_create_image(int width, int height)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_image_using_data(int width, int height, DATA32 * data)
|
||||
Imlib_Image imlib_create_image_using_data(int width, int height,
|
||||
DATA32 * data)
|
||||
{
|
||||
ImlibImage *im;
|
||||
|
||||
|
@ -938,8 +923,8 @@ imlib_create_image_using_data(int width, int height, DATA32 * data)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_image_using_copied_data(int width, int height, DATA32 * data)
|
||||
Imlib_Image imlib_create_image_using_copied_data(int width, int height,
|
||||
DATA32 * data)
|
||||
{
|
||||
ImlibImage *im;
|
||||
|
||||
|
@ -961,9 +946,9 @@ imlib_create_image_using_copied_data(int width, int height, DATA32 * data)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_image_from_drawable(Pixmap mask, int x, int y, int width,
|
||||
int height, char need_to_grab_x)
|
||||
Imlib_Image imlib_create_image_from_drawable(Pixmap mask, int x, int y,
|
||||
int width, int height,
|
||||
char need_to_grab_x)
|
||||
{
|
||||
ImlibImage *im;
|
||||
char domask = 0;
|
||||
|
@ -979,14 +964,14 @@ imlib_create_image_from_drawable(Pixmap mask, int x, int y, int width,
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_scaled_image_from_drawable(Pixmap mask, int source_x,
|
||||
int source_y, int source_width,
|
||||
int source_height,
|
||||
int destination_width,
|
||||
int destination_height,
|
||||
char need_to_grab_x,
|
||||
char get_mask_from_shape)
|
||||
Imlib_Image imlib_create_scaled_image_from_drawable(Pixmap mask, int source_x,
|
||||
int source_y,
|
||||
int source_width,
|
||||
int source_height,
|
||||
int destination_width,
|
||||
int destination_height,
|
||||
char need_to_grab_x,
|
||||
char get_mask_from_shape)
|
||||
{
|
||||
ImlibImage *im;
|
||||
char domask = 0, tmpmask = 0;
|
||||
|
@ -1135,8 +1120,7 @@ imlib_copy_drawable_to_image(Pixmap mask, int x, int y, int width, int height,
|
|||
height, domask, need_to_grab_x);
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_clone_image(void)
|
||||
Imlib_Image imlib_clone_image(void)
|
||||
{
|
||||
ImlibImage *im, *im_old;
|
||||
|
||||
|
@ -1175,8 +1159,7 @@ imlib_clone_image(void)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_cropped_image(int x, int y, int width, int height)
|
||||
Imlib_Image imlib_create_cropped_image(int x, int y, int width, int height)
|
||||
{
|
||||
ImlibImage *im, *im_old;
|
||||
|
||||
|
@ -1200,11 +1183,11 @@ imlib_create_cropped_image(int x, int y, int width, int height)
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_cropped_scaled_image(int source_x, int source_y,
|
||||
int source_width, int source_height,
|
||||
int destination_width,
|
||||
int destination_height)
|
||||
Imlib_Image imlib_create_cropped_scaled_image(int source_x, int source_y,
|
||||
int source_width,
|
||||
int source_height,
|
||||
int destination_width,
|
||||
int destination_height)
|
||||
{
|
||||
ImlibImage *im, *im_old;
|
||||
|
||||
|
@ -1243,8 +1226,7 @@ imlib_create_cropped_scaled_image(int source_x, int source_y,
|
|||
return (Imlib_Image) im;
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_updates_clone(Imlib_Updates updates)
|
||||
Imlib_Updates imlib_updates_clone(Imlib_Updates updates)
|
||||
{
|
||||
ImlibUpdate *u;
|
||||
|
||||
|
@ -1252,8 +1234,8 @@ imlib_updates_clone(Imlib_Updates updates)
|
|||
return (Imlib_Updates) __imlib_DupUpdates(u);
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_update_append_rect(Imlib_Updates updates, int x, int y, int w, int h)
|
||||
Imlib_Updates imlib_update_append_rect(Imlib_Updates updates, int x, int y,
|
||||
int w, int h)
|
||||
{
|
||||
ImlibUpdate *u;
|
||||
|
||||
|
@ -1261,8 +1243,7 @@ imlib_update_append_rect(Imlib_Updates updates, int x, int y, int w, int h)
|
|||
return (Imlib_Updates) __imlib_AddUpdate(u, x, y, w, h);
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_updates_merge(Imlib_Updates updates, int w, int h)
|
||||
Imlib_Updates imlib_updates_merge(Imlib_Updates updates, int w, int h)
|
||||
{
|
||||
ImlibUpdate *u;
|
||||
|
||||
|
@ -1270,8 +1251,8 @@ imlib_updates_merge(Imlib_Updates updates, int w, int h)
|
|||
return (Imlib_Updates) __imlib_MergeUpdate(u, w, h, 0);
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_updates_merge_for_rendering(Imlib_Updates updates, int w, int h)
|
||||
Imlib_Updates imlib_updates_merge_for_rendering(Imlib_Updates updates, int w,
|
||||
int h)
|
||||
{
|
||||
ImlibUpdate *u;
|
||||
|
||||
|
@ -1288,8 +1269,7 @@ imlib_updates_free(Imlib_Updates updates)
|
|||
__imlib_FreeUpdates(u);
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_updates_get_next(Imlib_Updates updates)
|
||||
Imlib_Updates imlib_updates_get_next(Imlib_Updates updates)
|
||||
{
|
||||
ImlibUpdate *u;
|
||||
|
||||
|
@ -1357,15 +1337,13 @@ imlib_render_image_updates_on_drawable(Imlib_Updates updates, int x, int y)
|
|||
__imlib_SetMaxXImageCount(ctxt_display, 0);
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_updates_init(void)
|
||||
Imlib_Updates imlib_updates_init(void)
|
||||
{
|
||||
return (Imlib_Updates) NULL;
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_updates_append_updates(Imlib_Updates updates,
|
||||
Imlib_Updates appended_updates)
|
||||
Imlib_Updates imlib_updates_append_updates(Imlib_Updates updates,
|
||||
Imlib_Updates appended_updates)
|
||||
{
|
||||
ImlibUpdate *u, *uu;
|
||||
|
||||
|
@ -1558,8 +1536,7 @@ imlib_image_tile(void)
|
|||
__imlib_TileImageVert(im);
|
||||
}
|
||||
|
||||
Imlib_Font
|
||||
imlib_load_font(const char *font_name)
|
||||
Imlib_Font imlib_load_font(const char *font_name)
|
||||
{
|
||||
return (Imlib_Font) __imlib_load_font(font_name);
|
||||
}
|
||||
|
@ -1945,8 +1922,7 @@ imlib_get_maximum_font_descent(void)
|
|||
return ((ImlibFont *) ctxt_font)->max_ascent;
|
||||
}
|
||||
|
||||
Imlib_Color_Modifier
|
||||
imlib_create_color_modifier(void)
|
||||
Imlib_Color_Modifier imlib_create_color_modifier(void)
|
||||
{
|
||||
return (Imlib_Color_Modifier) __imlib_CreateCmod();
|
||||
}
|
||||
|
@ -2077,8 +2053,8 @@ imlib_apply_color_modifier_to_rectangle(int x, int y, int width, int height)
|
|||
(ImlibColorModifier *) ctxt_color_modifier);
|
||||
}
|
||||
|
||||
Imlib_Updates
|
||||
imlib_image_draw_line(int x1, int y1, int x2, int y2, char make_updates)
|
||||
Imlib_Updates imlib_image_draw_line(int x1, int y1, int x2, int y2,
|
||||
char make_updates)
|
||||
{
|
||||
ImlibImage *im;
|
||||
|
||||
|
@ -2101,12 +2077,13 @@ imlib_image_draw_line(int x1, int y1, int x2, int y2, char make_updates)
|
|||
ctxt_cliprect.y +
|
||||
ctxt_cliprect.h,
|
||||
(DATA8) ctxt_color.red,
|
||||
(DATA8) ctxt_color.
|
||||
green,
|
||||
(DATA8) ctxt_color.
|
||||
blue,
|
||||
(DATA8) ctxt_color.
|
||||
alpha, ctxt_operation,
|
||||
(DATA8)
|
||||
ctxt_color.green,
|
||||
(DATA8)
|
||||
ctxt_color.blue,
|
||||
(DATA8)
|
||||
ctxt_color.alpha,
|
||||
ctxt_operation,
|
||||
(char) make_updates);
|
||||
}
|
||||
else
|
||||
|
@ -2281,8 +2258,7 @@ imlib_image_copy_rect(int x, int y, int width, int height, int new_x,
|
|||
__imlib_copy_image_data(im, x, y, width, height, new_x, new_y);
|
||||
}
|
||||
|
||||
Imlib_Color_Range
|
||||
imlib_create_color_range(void)
|
||||
Imlib_Color_Range imlib_create_color_range(void)
|
||||
{
|
||||
return (Imlib_Color_Range) __imlib_CreateRange();
|
||||
}
|
||||
|
@ -2475,8 +2451,7 @@ imlib_save_image_with_error_return(const char *filename,
|
|||
ctxt_image = prev_ctxt_image;
|
||||
}
|
||||
|
||||
Imlib_Image
|
||||
imlib_create_rotated_image(double angle)
|
||||
Imlib_Image imlib_create_rotated_image(double angle)
|
||||
{
|
||||
ImlibImage *im, *im_old;
|
||||
DATA32 *data;
|
||||
|
@ -2653,8 +2628,7 @@ imlib_image_filter(void)
|
|||
__imlib_FilterImage(im, (ImlibFilter *) ctxt_filter);
|
||||
}
|
||||
|
||||
Imlib_Filter
|
||||
imlib_create_filter(int initsize)
|
||||
Imlib_Filter imlib_create_filter(int initsize)
|
||||
{
|
||||
return (Imlib_Filter) __imlib_CreateFilter(initsize);
|
||||
}
|
||||
|
@ -2673,8 +2647,7 @@ imlib_context_set_filter(Imlib_Filter filter)
|
|||
ctxt_filter = filter;
|
||||
}
|
||||
|
||||
Imlib_Filter
|
||||
imlib_context_get_filter(void)
|
||||
Imlib_Filter imlib_context_get_filter(void)
|
||||
{
|
||||
return ctxt_filter;
|
||||
}
|
||||
|
@ -2761,8 +2734,7 @@ imlib_apply_filter(char *script, ...)
|
|||
va_end(param_list);
|
||||
}
|
||||
|
||||
ImlibPolygon
|
||||
imlib_polygon_new(void)
|
||||
ImlibPolygon imlib_polygon_new(void)
|
||||
{
|
||||
return (ImlibPolygon) __imlib_polygon_new();
|
||||
}
|
||||
|
@ -2824,21 +2796,13 @@ imlib_image_fill_polygon(ImlibPolygon poly)
|
|||
return;
|
||||
__imlib_DirtyImage(im);
|
||||
__imlib_DirtyPixmapsForImage(im);
|
||||
if (ctxt_cliprect.w)
|
||||
{
|
||||
__imlib_draw_polygon_filled_clipped(im, poly, ctxt_cliprect.x,
|
||||
ctxt_cliprect.x + ctxt_cliprect.w,
|
||||
ctxt_cliprect.y,
|
||||
ctxt_cliprect.y + ctxt_cliprect.h,
|
||||
ctxt_color.red, ctxt_color.green,
|
||||
ctxt_color.blue, ctxt_color.alpha,
|
||||
ctxt_operation);
|
||||
}
|
||||
else
|
||||
{
|
||||
__imlib_draw_polygon_filled(im, poly, ctxt_color.red, ctxt_color.green,
|
||||
ctxt_color.blue, ctxt_color.alpha, ctxt_operation);
|
||||
}
|
||||
__imlib_draw_polygon_filled(im, poly, ctxt_cliprect.x,
|
||||
ctxt_cliprect.x + ctxt_cliprect.w,
|
||||
ctxt_cliprect.y,
|
||||
ctxt_cliprect.y + ctxt_cliprect.h,
|
||||
ctxt_color.red, ctxt_color.green,
|
||||
ctxt_color.blue, ctxt_color.alpha,
|
||||
ctxt_operation);
|
||||
}
|
||||
|
||||
|
||||
|
@ -2912,3 +2876,10 @@ imlib_image_fill_ellipse(int xc, int yc, int a, int b)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
unsigned char
|
||||
imlib_polygon_contains_point(ImlibPolygon poly, int x, int y)
|
||||
{
|
||||
CHECK_PARAM_POINTER("imlib_polygon_contains_point", "polygon", poly);
|
||||
return __imlib_polygon_contains_point(poly, x, y);
|
||||
}
|
||||
|
|
260
src/rgbadraw.c
260
src/rgbadraw.c
|
@ -14,6 +14,7 @@
|
|||
(((x) >= (rx)) && ((y) >= (ry)) && ((x) <= ((rx) + (rw))) && ((y) <= ((ry) + (rh))))
|
||||
|
||||
#define MAX(a,b) (((a) > (b)) ? (a) : (b))
|
||||
#define MIN(a,b) (((a) < (b)) ? (a) : (b))
|
||||
|
||||
#define round(a) floor(a+0.5)
|
||||
|
||||
|
@ -110,7 +111,7 @@ __imlib_FlipImageDiagonal(ImlibImage * im, int direction)
|
|||
switch (direction)
|
||||
{
|
||||
default:
|
||||
case 0: /*\ DOWN_RIGHT \ */
|
||||
case 0: /*\ DOWN_RIGHT \ */
|
||||
tmp = im->border.top;
|
||||
im->border.top = im->border.left;
|
||||
im->border.left = tmp;
|
||||
|
@ -120,7 +121,7 @@ __imlib_FlipImageDiagonal(ImlibImage * im, int direction)
|
|||
to = data;
|
||||
hw = -hw + 1;
|
||||
break;
|
||||
case 1: /*\ DOWN_LEFT \ */
|
||||
case 1: /*\ DOWN_LEFT \ */
|
||||
tmp = im->border.top;
|
||||
im->border.top = im->border.left;
|
||||
im->border.left = im->border.bottom;
|
||||
|
@ -129,7 +130,7 @@ __imlib_FlipImageDiagonal(ImlibImage * im, int direction)
|
|||
to = data + w - 1;
|
||||
hw = -hw - 1;
|
||||
break;
|
||||
case 2: /*\ UP_RIGHT \ */
|
||||
case 2: /*\ UP_RIGHT \ */
|
||||
tmp = im->border.top;
|
||||
im->border.top = im->border.right;
|
||||
im->border.right = im->border.bottom;
|
||||
|
@ -139,7 +140,7 @@ __imlib_FlipImageDiagonal(ImlibImage * im, int direction)
|
|||
w = -w;
|
||||
hw = hw + 1;
|
||||
break;
|
||||
case 3: /*\ UP_LEFT \ */
|
||||
case 3: /*\ UP_LEFT \ */
|
||||
tmp = im->border.top;
|
||||
im->border.top = im->border.right;
|
||||
im->border.right = tmp;
|
||||
|
@ -1873,7 +1874,7 @@ __imlib_fill_ellipse_clipped(ImlibImage * im, int xc, int yc, int aa, int bb,
|
|||
g, b, a, op);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (dec >= 0)
|
||||
dec += 4 * b2 * (1 - (x--));
|
||||
dec += a2 * (4 * y + 6);
|
||||
|
@ -2076,13 +2077,17 @@ span_clipped(ImlibImage * im, int y, edgeRec * pt1, edgeRec * pt2,
|
|||
ix2 = pt2->x;
|
||||
idx = ix2 - ix1;
|
||||
if (idx == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/* clip x, y is clipped for us by the caller */
|
||||
if (ix1 < clip_xmin)
|
||||
ix1 = clip_xmin;
|
||||
if (ix2 > clip_xmax)
|
||||
ix2 = clip_xmax;
|
||||
|
||||
do
|
||||
{
|
||||
__imlib_draw_set_point_clipped(im, ix1, y, clip_xmin, clip_xmax,
|
||||
clip_ymin, clip_ymax, r, g, b, a, op);
|
||||
__imlib_draw_set_point(im, ix1, y, r, g, b, a, op);
|
||||
ix1++;
|
||||
}
|
||||
while (ix1 < ix2);
|
||||
|
@ -2090,8 +2095,9 @@ span_clipped(ImlibImage * im, int y, edgeRec * pt1, edgeRec * pt2,
|
|||
|
||||
|
||||
void
|
||||
__imlib_draw_polygon_filled(ImlibImage * im, ImlibPoly poly, DATA8 r, DATA8 g,
|
||||
DATA8 b, DATA8 a, ImlibOp op)
|
||||
__imlib_draw_polygon_filled(ImlibImage * im, ImlibPoly poly, int clip_xmin,
|
||||
int clip_xmax, int clip_ymin, int clip_ymax,
|
||||
DATA8 r, DATA8 g, DATA8 b, DATA8 a, ImlibOp op)
|
||||
{
|
||||
long maxy, miny;
|
||||
int iy1, iy2;
|
||||
|
@ -2163,99 +2169,171 @@ __imlib_draw_polygon_filled(ImlibImage * im, ImlibPoly poly, DATA8 r, DATA8 g,
|
|||
}
|
||||
}
|
||||
while (pnt1 != iminy);
|
||||
do
|
||||
|
||||
if (clip_xmin != clip_xmax)
|
||||
{
|
||||
span(im, iy1, &table1[iy1], &table2[iy1], r, g, b, a, op);
|
||||
iy1++;
|
||||
/* there is a cliprect, don't bother with y outside of it */
|
||||
if (iy1 < clip_ymin)
|
||||
iy1 = clip_ymin;
|
||||
if (iy2 > clip_ymax)
|
||||
iy2 = clip_ymax;
|
||||
do
|
||||
{
|
||||
span_clipped(im, iy1, &table1[iy1], &table2[iy1], clip_xmin,
|
||||
clip_xmax, clip_ymin, clip_ymax, r, g, b, a, op);
|
||||
iy1++;
|
||||
}
|
||||
while (iy1 < iy2);
|
||||
}
|
||||
while (iy1 < iy2);
|
||||
else
|
||||
{
|
||||
do
|
||||
{
|
||||
span(im, iy1, &table1[iy1], &table2[iy1], r, g, b, a, op);
|
||||
iy1++;
|
||||
}
|
||||
while (iy1 < iy2);
|
||||
}
|
||||
|
||||
free(table1);
|
||||
free(table2);
|
||||
}
|
||||
|
||||
void
|
||||
__imlib_draw_polygon_filled_clipped(ImlibImage * im, ImlibPoly poly,
|
||||
int clip_xmin, int clip_xmax,
|
||||
int clip_ymin, int clip_ymax, DATA8 r,
|
||||
DATA8 g, DATA8 b, DATA8 a, ImlibOp op)
|
||||
|
||||
unsigned char
|
||||
__imlib_polygon_contains_point(ImlibPoly poly, int x, int y)
|
||||
{
|
||||
long maxy, miny;
|
||||
int iy1, iy2;
|
||||
int imaxy, iminy;
|
||||
int pnt1, pnt2;
|
||||
int i;
|
||||
edgeRec *table1, *table2;
|
||||
int count = 0;
|
||||
int start = 0;
|
||||
int ysave = 0; /* initial value arbitrary */
|
||||
int cx, nx, out_x, out_y, i, n;
|
||||
int curr_x, curr_y, next_x, next_y;
|
||||
|
||||
if (poly->pointcount < 3)
|
||||
{
|
||||
return;
|
||||
}
|
||||
/* find a vertex of poly that does not lie on the test line */
|
||||
while (start < poly->pointcount && poly->points[start].y == y)
|
||||
start++;
|
||||
/* if one doesn't exist we will use point on segment test
|
||||
and can start with vertex 0 anyway */
|
||||
cx = start % poly->pointcount;
|
||||
|
||||
table1 = malloc(sizeof(edgeRec) * im->h);
|
||||
table2 = malloc(sizeof(edgeRec) * im->h);
|
||||
out_x = poly->points[0].x;
|
||||
out_y = y;
|
||||
|
||||
maxy = miny = poly->points[0].y;
|
||||
imaxy = iminy = 0;
|
||||
for (i = 1; i < poly->pointcount; i++)
|
||||
{
|
||||
if (poly->points[i].y > maxy)
|
||||
out_x = MAX(out_x, poly->points[i].x);
|
||||
}
|
||||
out_x++; /* out now guaranteed to be outside poly */
|
||||
|
||||
for (n = 0; n < poly->pointcount; n++)
|
||||
{
|
||||
nx = (cx + 1) % poly->pointcount;
|
||||
|
||||
curr_x = poly->points[cx].x;
|
||||
curr_y = poly->points[cx].y;
|
||||
next_x = poly->points[nx].x;
|
||||
next_y = poly->points[nx].y;
|
||||
|
||||
if (__imlib_point_on_segment(x, y, curr_x, curr_y, next_x, next_y))
|
||||
return TRUE;
|
||||
|
||||
/* ignore horizontal segments from this point on */
|
||||
if (poly->points[cx].y != poly->points[nx].y)
|
||||
{
|
||||
maxy = poly->points[i].y;
|
||||
imaxy = i;
|
||||
}
|
||||
if (poly->points[i].y < miny)
|
||||
{
|
||||
miny = poly->points[i].y;
|
||||
iminy = i;
|
||||
if (__imlib_segments_intersect
|
||||
(curr_x, curr_y, next_x, next_y, x, y, out_x, out_y))
|
||||
{
|
||||
count++;
|
||||
|
||||
if (__imlib_point_on_segment(next_x, next_y, x, y, out_x, out_y))
|
||||
{
|
||||
/* current seg intersects test seg @ 2nd vtx
|
||||
reset ysave */
|
||||
ysave = curr_y;
|
||||
}
|
||||
if (__imlib_point_on_segment(curr_x, curr_y, x, y, out_x, out_y)
|
||||
&& (ysave < y != next_y < y))
|
||||
{
|
||||
/* current seg xsects test seg @ 1st vtx and
|
||||
ysave on opposite side of test line from
|
||||
curr seg 2nd vtx;
|
||||
decrement hits (2-1) for odd parity */
|
||||
count--;
|
||||
}
|
||||
}
|
||||
}
|
||||
cx = nx;
|
||||
}
|
||||
return (count % 2 == 1);
|
||||
}
|
||||
|
||||
unsigned char
|
||||
__imlib_point_on_segment(int p_x, int p_y, int s1_x, int s1_y, int s2_x,
|
||||
int s2_y)
|
||||
{
|
||||
return __imlib_segments_intersect(p_x, p_y, p_x, p_y, s1_x, s1_y, s2_x,
|
||||
s2_y);
|
||||
}
|
||||
|
||||
unsigned char
|
||||
__imlib_segments_intersect(int r1_x, int r1_y, int r2_x, int r2_y, int s1_x,
|
||||
int s1_y, int s2_x, int s2_y)
|
||||
{
|
||||
double testS1R =
|
||||
__imlib_point_delta_from_line(s1_x, s1_y, r1_x, r1_y, r2_x, r2_y);
|
||||
double testS2R =
|
||||
__imlib_point_delta_from_line(s2_x, s2_y, r1_x, r1_y, r2_x, r2_y);
|
||||
double testR1S =
|
||||
__imlib_point_delta_from_line(r1_x, r1_y, s1_x, s1_y, s2_x, s2_y);
|
||||
double testR2S =
|
||||
__imlib_point_delta_from_line(r2_x, r2_y, s1_x, s1_y, s2_x, s2_y);
|
||||
|
||||
/* check if segments are collinear */
|
||||
if (testS1R == 0.0 && testS2R == 0.0)
|
||||
{
|
||||
if (__imlib_point_inside_segment(s1_x, s1_y, r1_x, r1_y, r2_x, r2_y)
|
||||
|| __imlib_point_inside_segment(s2_x, s2_y, r1_x, r1_y, r2_x, r2_y)
|
||||
|| __imlib_point_inside_segment(r1_x, r1_y, s1_x, s1_y, s2_x, s2_y)
|
||||
|| __imlib_point_inside_segment(r2_x, r2_y, s1_x, s1_y, s2_x, s2_y))
|
||||
return TRUE;
|
||||
else
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (testS1R * testS2R <= 0.0 && testR1S * testR2S <= 0.0)
|
||||
return TRUE;
|
||||
else
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* TODO this could prolly be a macro */
|
||||
unsigned char
|
||||
__imlib_point_inside_segment(int p_x, int p_y, int s1_x, int s1_y, int s2_x,
|
||||
int s2_y)
|
||||
{
|
||||
/* Check if p lies on segment [ s1, s2 ] given that
|
||||
it lies on the line defined by s1 and s2. */
|
||||
if (s1_y != s2_y)
|
||||
{
|
||||
if (p_y <= MAX(s1_y, s2_y) && p_y >= MIN(s1_y, s2_y))
|
||||
return TRUE;
|
||||
}
|
||||
else if (p_x <= MAX(s1_x, s2_x) && p_x >= MIN(s1_x, s2_x))
|
||||
return TRUE;
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
double
|
||||
__imlib_point_delta_from_line(int p_x, int p_y, int s1_x, int s1_y, int s2_x,
|
||||
int s2_y)
|
||||
{
|
||||
if (s2_x - s1_x == 0.0)
|
||||
return p_x - s1_x;
|
||||
else
|
||||
{
|
||||
double m = (double) (s2_y - s1_y) / (double) (s2_x - s1_x);
|
||||
|
||||
return (p_y - s1_y - (double) (p_x - s1_x) * m);
|
||||
}
|
||||
iy1 = miny;
|
||||
iy2 = maxy;
|
||||
if (iy1 == iy2)
|
||||
{
|
||||
return;
|
||||
}
|
||||
pnt1 = iminy;
|
||||
pnt2 = iminy + 1;
|
||||
if (pnt2 >= poly->pointcount)
|
||||
{
|
||||
pnt2 = 0;
|
||||
}
|
||||
do
|
||||
{
|
||||
edge(table1, &poly->points[pnt1], &poly->points[pnt2]);
|
||||
pnt1 = pnt2;
|
||||
pnt2 = pnt2 + 1;
|
||||
if (pnt2 >= poly->pointcount)
|
||||
{
|
||||
pnt2 = 0;
|
||||
}
|
||||
}
|
||||
while (pnt1 != imaxy);
|
||||
pnt1 = imaxy;
|
||||
pnt2 = imaxy + 1;
|
||||
if (pnt2 >= poly->pointcount)
|
||||
{
|
||||
pnt2 = 0;
|
||||
}
|
||||
do
|
||||
{
|
||||
edge(table2, &poly->points[pnt1], &poly->points[pnt2]);
|
||||
pnt1 = pnt2;
|
||||
pnt2 = pnt2 + 1;
|
||||
if (pnt2 >= poly->pointcount)
|
||||
{
|
||||
pnt2 = 0;
|
||||
}
|
||||
}
|
||||
while (pnt1 != iminy);
|
||||
do
|
||||
{
|
||||
span_clipped(im, iy1, &table1[iy1], &table2[iy1], clip_xmin, clip_xmax,
|
||||
clip_ymin, clip_ymax, r, g, b, a, op);
|
||||
iy1++;
|
||||
}
|
||||
while (iy1 < iy2);
|
||||
free(table1);
|
||||
free(table2);
|
||||
}
|
||||
|
|
|
@ -101,10 +101,7 @@ __imlib_draw_ellipse_clipped(ImlibImage * im, int xc, int yc, int aa, int bb,
|
|||
int clip_ymax, DATA8 r, DATA8 g, DATA8 b,
|
||||
DATA8 a, ImlibOp op);
|
||||
void
|
||||
__imlib_draw_polygon_filled(ImlibImage * im, ImlibPoly poly, DATA8 r, DATA8 g,
|
||||
DATA8 b, DATA8 a, ImlibOp op);
|
||||
void
|
||||
__imlib_draw_polygon_filled_clipped(ImlibImage * im, ImlibPoly poly,
|
||||
__imlib_draw_polygon_filled(ImlibImage * im, ImlibPoly poly,
|
||||
int clip_xmin, int clip_xmax,
|
||||
int clip_ymin, int clip_ymax, DATA8 r,
|
||||
DATA8 g, DATA8 b, DATA8 a, ImlibOp op);
|
||||
|
@ -116,4 +113,18 @@ __imlib_fill_ellipse_clipped(ImlibImage * im, int xc, int yc, int aa, int bb,
|
|||
int clip_xmin, int clip_xmax, int clip_ymin,
|
||||
int clip_ymax, DATA8 r, DATA8 g, DATA8 b,
|
||||
DATA8 a, ImlibOp op);
|
||||
unsigned char
|
||||
__imlib_polygon_contains_point(ImlibPoly poly, int x, int y);
|
||||
unsigned char
|
||||
__imlib_point_on_segment(int p_x, int p_y, int s1_x, int s1_y, int s2_x,
|
||||
int s2_y);
|
||||
unsigned char
|
||||
__imlib_segments_intersect(int r1_x, int r1_y, int r2_x, int r2_y, int s1_x,
|
||||
int s1_y, int s2_x, int s2_y);
|
||||
unsigned char
|
||||
__imlib_point_inside_segment(int p_x, int p_y, int s1_x, int s1_y, int s2_x,
|
||||
int s2_y);
|
||||
double
|
||||
__imlib_point_delta_from_line(int p_x, int p_y, int s1_x, int s1_y, int s2_x,
|
||||
int s2_y);
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue