/* core.h
 * This file is part of Amsam photo cropping program
 * Copyright 2021, 2023, 2024, 2025, 2026 Nandakumar Edamana
 * Distributed under GNU General Public License, version 3
 */ 

#ifndef N96_DRAW_core_h
#define N96_DRAW_core_h

typedef enum Tool Tool;
typedef struct VaraRect VaraRect;
typedef struct DrawingParams DrawingParams;
typedef struct Image Image;
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include "warpcore.h"
#include "pixel.h"
#include "brush-params.h"
#include "brush-params.h"
#ifdef _WIN32
static inline double drand48() { return rand() / (double) RAND_MAX; }
#endif
extern Pixel PIXEL_BLACK;
extern Pixel PIXEL_GRAY;
extern Pixel PIXEL_VPBG;
extern Pixel PIXEL_WHITE;
extern LinearPixel LINEAR_PIXEL_BLACK;
extern LinearPixel LINEAR_PIXEL_RED;
extern LinearPixel LINEAR_PIXEL_TRANSP;
extern LinearPixel LINEAR_PIXEL_WHITE;
#define CIRCLE1_AA_IS_INSIDE (true)
extern double AA_RADIUS_CIRCLE2;
extern double AA_MAXDIFF_LINE;
#define NOISEDIVISOR (10)
enum Tool {
	TOOL_BRUSH,
	TOOL_EYEDROPPER,
	TOOL_FLOODFILL,
	TOOL_PENCIL,
};
_Bool is_double_nan(double x);
struct VaraRect {
	int x;
	int y;
	int w;
	int h;
};
VaraRect rectangle_new_from_boundaries(int x1, int y1, int x2, int y2);
_Bool region_is_zero(VaraRect region);
VaraRect region_new(int x, int y, int w, int h);
VaraRect union_regions(VaraRect rect1, VaraRect rect2);
struct DrawingParams {
	Tool active_tool;
	BrushParams brushparams;
	LinearPixel fgcolor;
	_Bool erase;
	double pressure;
	double oldpressure;
};
struct Image {
	int width;
	int height;
	int depth;
	float *buf;
};
void image_construct(Image *this, int width, int height, int depth);
Image * image_Clone(Image *this);
void image_assert_region(Image *this, VaraRect region);
void image_copy_image(Image *this, Image *src);
Image * image_make_clone(Image *this);
VaraRect image_copy_image_region_with_destoffset(Image *this, Image *src, VaraRect region, int destx, int desty);
VaraRect image_copy_image_region_with_scale(Image *this, Image *src, VaraRect region, int destx, int desty, double scl);
VaraRect image_copy_image_with_destoffset(Image *this, Image *src, int destx, int desty);
VaraRect image_copy_image_with_scale(Image *this, Image *src, int destx, int desty, double scl);
VaraRect image_clip_region(Image *this, VaraRect region);
void image_copy_image_region(Image *this, Image *src, VaraRect region);
VaraRect image_dip(Image *this, double x, double y, DrawingParams dp);
void image_draw_debug_region(Image *this, VaraRect region);
VaraRect image_get_dirty_region_by_stroke(Image *this, double lbx, double lby, double ubx, double uby, DrawingParams dp);
VaraRect image_get_region(Image *this);
void image_fill(Image *this, LinearPixel pixel);
void image_fill_region(Image *this, LinearPixel pixel, VaraRect region);
_Bool image_is_point_outside(Image *this, int x, int y);
VaraRect image_line(Image *this, double x1, double y1, double x2, double y2, DrawingParams dp);
void image_overlay_image(Image *this, Image *img);
void image_overlay_image_region(Image *this, Image *img, VaraRect region);
void image_overlay_image_region_with_alpha(Image *this, Image *img, double alpha, VaraRect region);
void image_overlay_image_with_alpha(Image *this, Image *img, double alpha);
void image_overlay_image_with_offset(Image *this, Image *src, int destx, int desty);
void image_alphen_image_with_offset(Image *this, Image *src, int destx, int desty);
void image_destruct(Image *this);
double effective_brush_radius(double radius, DrawingParams dp);
double get_effective_scatter_radius(DrawingParams dp);
Image * nan_img_new(int width, int height, int depth);
void nan_img_aaline_dot(Image *img, int x, int y, double diff, DrawingParams dp);
double distance(double xdist, double ydist);
double dist2pixmid(double x1, double y1, int x2, int y2);
double dmax2(double a, double b);
double dmax3(double a, double b, double c);
double dmin2(double a, double b);
double dmin3(double a, double b, double c);
float fnonzero_or_one(float a);
int imax2(int a, int b);
int imin2(int a, int b);
unsigned int umin2(unsigned int a, unsigned int b);
void nan_img_aaline_inner_by_x_dbl(Image *img, double x1, double y1, double x2, double y2, double lbx, double lby, double ubx, double uby, double m, DrawingParams dp);
void nan_img_aaline_inner_by_y_dbl(Image *img, double x1, double y1, double x2, double y2, double lbx, double lby, double ubx, double uby, double m, DrawingParams dp);
void nan_img_thickline_inner_by_x(Image *img, double x1, double y1, double x2, double y2, double lbx, double lby, double ubx, double uby, double m, DrawingParams dp);
void nan_img_thickline_inner_by_y(Image *img, double x1, double y1, double x2, double y2, double lbx, double lby, double ubx, double uby, double m, DrawingParams dp);
void nan_img_thick_dot(Image *img, double x, double y, double progress, DrawingParams dp);
void nan_img_thick_dot_with_scatter(Image *img, double x, double y, double progress, DrawingParams dp);
void nan_img_fill_circle1(Image *img, double x, double y, double brush_size, double opacity, _Bool noisy, DrawingParams dp);
void nan_img_fill_circle2(Image *img, double x, double y, double brush_size, double opacity, DrawingParams dp);
void nan_img_fill_random_square(Image *img, double x, double y, double brush_size, double opacity, DrawingParams dp);
_Bool linear_pixels_match(LinearPixel px1, LinearPixel px2);
_Bool pixelsmatch(Pixel px1, Pixel px2);
void nan_copy_pixel_to_argb32(LinearPixel pixel, unsigned char *dest);
void nan_img_copy_pixel_to_argb32(Image *img, int x, int y, unsigned char *dest);
void nan_copy_pixel_to_rgb24(LinearPixel pixel, unsigned char *dest);
void nan_img_copy_pixel_to_rgb24(Image *img, int x, int y, unsigned char *dest);
void print_region(VaraRect region, const char *label);
void nan_img_draw_circle(Image *img, int x, int y, int radius, int aaradius);
int roundedpercsiz(double perc, int canvsiz);
VaraRect vara_rect_default();
DrawingParams drawing_params_default();

#endif /* N96_DRAW_core_h */
