109#include "lensserious.h"
110#include "lensserious_db.h"
111#include "lensserious_vendor.h"
192#define DT_LENS_MODIFY_DISTORTION_PACK \
193 (DT_LENS_MODIFY_DISTORTION | DT_LENS_MODIFY_GEOMETRY | DT_LENS_MODIFY_SCALE)
196#define DT_LENS_MODIFY_ANSEL_MASK 0xFF000000u
206#define DT_LENS_MODIFY_ALL_AXES ((int)~DT_LENS_MODIFY_ANSEL_MASK)
213 "the axis space and Ansel's own bits must not overlap");
217 "every correction axis must live in the axis half");
219 "no source field may reach the sign bit of modify_flags");
222 "the source fields must not overlap each other");
280 "projection numbering must match ls_lens_type_t: stored params depend on it");
393 const gboolean tca_override,
546 default:
return FALSE;
671 const char *reason = (!
IS_NULL_PTR(detail) && detail[0]) ? detail :
"no further detail";
685 "[lens] `%s' exists but could not be read: %s. Check its permissions, and "
686 "that it is not truncated\n", path, reason);
695 "[lens] `%s' is a lens database of schema v%d, and this Ansel reads v%d. It "
696 "is almost certainly left over from an older install: rebuild and reinstall "
697 "so the file is replaced, or delete it if it is a stale copy in your "
698 "configuration directory.\n",
713 if(
tls->tried)
return tls->db;
748 "[lens] no calibration database, so no lens correction is available.\n");
790 tls->cam_found = found;
793 if(found) *
out = cam;
846 (
int)(
sizeof(
m) /
sizeof(*
m)));
848 for(
int i = 0;
i <
n;
i++)
916 return _(
"_lens correction");
921 return _(
"vignette|chromatic aberrations|distortion");
928 _(
"linear, RGB, scene-referred"),
929 _(
"geometric and reconstruction, RGB"),
930 _(
"linear, RGB, scene-referred"));
982 n->modify_flags = o->modify_flags;
983 n->inverse = o->inverse;
987 n->aperture = o->aperture;
988 n->distance = o->distance;
989 n->target_geom = o->target_geom;
990 n->tca_override = o->tca_override;
991 g_strlcpy(
n->camera, o->camera,
sizeof(
n->camera));
1034 n->tca_r = o->tca_b;
1035 n->tca_b = o->tca_r;
1068 n->tca_r = o->tca_b;
1069 n->tca_b = o->tca_r;
1182 const float knots_scale =
d->knots_scale * ((
d->scale > 0.f) ?
d->scale : 1.f);
1250 d->distance,
d->scale, (
int)
d->target_geom,
want, reverse);
1320 for(
int k = 0;
k <
ch *
width;
k++) buf[
k] = 0.5f;
1343 const int ch =
piece->dsc_in.channels;
1364 " calibrations, crop %.4f, focal %.1f)\n",
modflags,
d->modify_flags,
1365 d->ls_lens.n_dist,
d->ls_lens.n_tca,
d->ls_lens.n_vig, (
double)
d->crop,
1400#pragma omp parallel for default(none) \
1401 firstprivate(roi_out, roi_in, padded_bufsize, modifier, ch, d, buf, ovoid, ivoid, ch_width, interpolation, raw_monochrome, mask_display, have_vig, vp)
1403 for(
int y = 0; y < roi_out->
height; y++)
1412 dt_aligned_pixel_simd_t
pixel = { 0.f };
1413 for(
int c = 0; c < 3; c++)
1421 const float *
const inptr = (
const float *
const)
ivoid + (
size_t)c;
1432 (
float)(roi_out->
y + y));
1433 for(
int c = 0; c < 3; c++)
pixel[c] *=
v;
1446 const float *
const inptr = (
const float *
const)
ivoid + (
size_t)3;
1457 else for(
int c = 0; c <
ch; c++)
out[c] =
pixel[c];
1470 for(
int y = 0; y < roi_out->
height; y++)
1474 out, (
int)((
ch * roi_out->
width) *
sizeof(
float)));
1496#pragma omp parallel for default(none) \
1497 firstprivate(roi_out, roi_in, ovoid, ivoid, ch, padded_buf2size, modifier, mask_display, raw_monochrome, interpolation, ch_width, d, buf2, have_vig, vp)
1499 for(
int y = 0; y < roi_out->
height; y++)
1507 dt_aligned_pixel_simd_t
pixel = { 0.f };
1508 for(
int c = 0; c < 3; c++)
1548 else for(
int c = 0; c <
ch; c++)
out[c] =
pixel[c];
1561 for(
int y = 0; y < roi_in->
height; y++)
1565 (
int)((
ch * roi_in->
width) *
sizeof(
float)));
1598 const int iwidth = roi_in->
width;
1599 const int iheight = roi_in->
height;
1609 size_t origin[] = { 0, 0, 0 };
1627 switch(interpolation->
id)
1702 const int vw =
d->inverse ?
owidth : iwidth;
1703 const int vh =
d->inverse ?
oheight : iheight;
1755 tiling->factor_cl = 2.0f;
1756 tiling->maxbuf_cl = 1.0f;
1765 float *
const __restrict points,
size_t points_count)
1781 for(
size_t i = 0;
i < points_count * 2;
i += 2)
1788 points[
i + 1] = buf[3];
1797 float *
const __restrict points,
size_t points_count)
1814 for(
size_t i = 0;
i < points_count * 2;
i += 2)
1821 points[
i + 1] = buf[3];
1831 const float *
const in,
float *
const out,
const dt_iop_roi_t *
const roi_in,
1865 for(
int y = 0; y < roi_out->
height; y++)
1917 const int xoff = roi_in->
x;
1918 const int yoff = roi_in->
y;
1936#pragma omp parallel default(none) reduction(min : xm, ym) reduction(max : xM, yM) \
1937 firstprivate(modifier, xoff, yoff, awidth, aheight, width, height, nbpoints, ystep, xstep, buf)
1960 for(
size_t c = 0; c < 6; c+=2)
1962 const float x = buf[6 *
k + c];
1963 const float y = buf[6 *
k + c + 1];
2041 memset(&
d->ls_lens, 0,
sizeof(
d->ls_lens));
2066 d->crop = camera.crop_factor;
2101 "[lens] `%s' is not a camera this database knows, so `%s' cannot be resolved to"
2102 " one lens; correcting from the database is declined\n",
p->camera,
p->lens);
2129 d->ls_lens.crop_factor =
d->crop;
2130 d->ls_lens.min_focal =
p->focal;
2131 d->ls_lens.max_focal =
p->focal;
2139 d->ls_lens.n_tca = 1;
2141 d->ls_lens.tca[0].focal =
p->focal;
2142 d->ls_lens.tca[0].terms[0] =
p->tca_r;
2143 d->ls_lens.tca[0].terms[1] =
p->tca_b;
2144 for(
int i = 2;
i < 6;
i++)
d->ls_lens.tca[0].terms[
i] = 0.f;
2147 d->modify_flags =
p->modify_flags;
2149 d->inverse =
p->inverse;
2150 d->scale =
p->scale;
2151 d->focal =
p->focal;
2152 d->aperture =
p->aperture;
2153 d->distance =
p->distance;
2154 d->target_geom =
p->target_geom;
2155 d->do_nan_checks =
TRUE;
2156 d->tca_override =
p->tca_override;
2169 d->knots_scale = 1.f;
2189 "[lens] an axis asks for the vendor profile but this file carries none;"
2190 " correcting from the community profile instead\n");
2193 "[lens] this file's vendor profile could not be decoded;"
2194 " correcting from the community profile instead\n");
2197 d->knots_scale = (scale > 0.f) ? scale : 1.f;
2198 d->knots_have =
TRUE;
2209 d->do_nan_checks =
FALSE;
2211 else if((
int)
d->target_geom == (
int)
d->ls_lens.type)
2213 d->do_nan_checks =
FALSE;
2265 float *points,
size_t points_count, gboolean inverse)
2271 if(
record->in.width <= 0 ||
record->in.height <= 0)
return 0;
2281 for(
size_t i = 0;
i < points_count * 2;
i += 2)
2288 points[
i + 1] = buf[3];
2348 const int program = 2;
2367 const dt_image_t *img = &
module->dev->image_storage;
2415 for(
char cnt = 0, *c =
model; c <
model + 100 && *c !=
'\0'; c++)
2417 if(++
cnt == 2) *c =
'\0';
2426 char mount[128] = { 0 };
2432 long long lens_id =
_ls_find_lens(cam.mount_id, cam.crop_factor,
d->focal,
d->lens);
2444 long long *ids = (
long long *)
dt_alloc_align(
sizeof(
long long) * (size_t)
n);
2451 for(
int i = 0;
i <
n;
i++)
2476 d->crop = cam.crop_factor;
2478 module->workflow_enabled = dt_image_needs_rawprepare(img);
2509 if(
x == 0)
return 1;
2531 int length = array->len;
2533 const void **root = (
const void **)array->pdata;
2535 int m = 0, l = 0,
r = length - 1;
2538 if(l <=
r && !root[
r])
r--;
2543 int cmp = compare(root[
m], item);
2558 memmove(root +
m + 1, root +
m,
sizeof(
void *) * (length -
m));
2565 int length = array->len;
2566 void **root = array->pdata;
2568 int l = 0,
r = length - 1;
2571 if(!length)
return -1;
2579 cmp = compare(root[
m], item);
2595 int length = array->len;
2597 root = (
const void **)array->pdata;
2598 memmove(root + index + 1, root + index,
sizeof(
void *) * (length - index));
2630 p->crop = cam.crop_factor;
2659 g->camera_id = camera_id;
2674 char mount[128] =
"";
2680 "crop factor:\t%.1f"),
2694 const long long camera_id =
2729 g->camera_menu =
NULL;
2738 for(
int i = 0;
i <
n;
i++)
2774 for(
unsigned i = 0;
i <
makers->len;
i++)
2793 if(
n <= 0)
return NULL;
2794 long long *ids = (
long long *)
dt_alloc_align(
sizeof(
long long) * (size_t)
n);
2802 while(txt[0] &&
isspace(txt[0])) txt++;
2803 size_t len =
strlen(txt);
2874 default:
return _(
"unknown");
2912 = { -
INFINITY, 4.5, 8, 10, 12, 14, 15, 16, 17, 18, 20, 24, 28, 30, 31, 35,
2913 38, 40, 43, 45, 50, 55, 60, 70, 75, 77, 80, 85, 90, 100, 105, 110,
2914 120, 135, 150, 200, 210, 240, 250, 300, 400, 500, 600, 800, 1000,
INFINITY };
2916 = { -
INFINITY, 0.7, 0.8, 0.9, 1, 1.1, 1.2, 1.4, 1.8, 2, 2.2, 2.5, 2.8, 3.2, 3.4, 4, 4.5, 5.0,
2917 5.6, 6.3, 7.1, 8, 9, 10, 11, 13, 14, 16, 18, 20, 22, 25, 29, 32, 38,
INFINITY };
2959 char focal[100], aperture[100],
mounts[200];
2975 "focal range:\t%s\n"
2977 "crop factor:\t%.1f\n"
3058 for(
int k = 0;
k < 25;
k++)
3060 if(
val > 1000.0f)
val = 1000.0f;
3063 if(
val >= 1000.0f)
break;
3087 const long long lens_id =
3116 g->lens_menu =
NULL;
3125 for(
int i = 0;
i <
n;
i++)
3152 for(
unsigned i = 0;
i <
makers->len;
i++)
3191 if(
n <= 0)
return NULL;
3192 long long *ids = (
long long *)
dt_alloc_align(
sizeof(
long long) * (size_t)
n);
3194 for(
int i = 0;
i <
n;
i++) ids[
i] =
m[
i].lens_id;
3202 if(total <= 0)
return NULL;
3203 long long *
all = (
long long *)
dt_alloc_align(
sizeof(
long long) * (size_t)total);
3214 for(
int i = 0;
i <
got;
i++)
3373 for(
int i = 0;
i <
g->axis_rows[
axis];
i++)
3374 if(
g->axis_row[
axis][
i] == source)
return i;
3451 g->axis_row[
axis][
n++] = src;
3477 if(
g->axis_source[
axis] == w)
return axis;
3521 g->axis_source[
axis] = w;
3527 g->axis_rows[
axis] = 0;
3643 g->camera_menu =
NULL;
3644 g->lens_menu =
NULL;
3691 N_(
"correct the lens's light falloff, and where to take it from"));
3695 N_(
"correct the lens's geometric distortion, and where to take it from"));
3724 N_(
"correct lateral chromatic aberration, and where to take it from"));
3793 if(
g->camera_id >= 0 &&
p->lens[0])
static double dist(double x1, double y1, double x2, double y2)
static void error(char *msg)
void dt_bauhaus_slider_set_digits(GtkWidget *widget, int val)
void dt_bauhaus_combobox_clear(GtkWidget *widget)
void dt_bauhaus_combobox_set_editable(GtkWidget *widget, int editable)
int dt_bauhaus_combobox_get(GtkWidget *widget)
const char * dt_bauhaus_combobox_get_text(GtkWidget *widget)
void dt_bauhaus_slider_set(GtkWidget *widget, float pos)
void dt_bauhaus_combobox_set(GtkWidget *widget, const int pos)
void dt_bauhaus_widget_set_label(GtkWidget *widget, const char *label)
GtkWidget * dt_bauhaus_combobox_new(dt_bauhaus_t *bh, dt_gui_module_t *self)
void dt_bauhaus_combobox_add(GtkWidget *widget, const char *text)
void dt_bauhaus_widget_set_quad_paint(GtkWidget *widget, dt_bauhaus_quad_paint_f f, int paint_flags, void *paint_data)
typedef void((*dt_cache_allocate_t)(void *userdata, dt_cache_entry_t *entry))
return vector dt_simd_set1(valid ?(scaling+NORM_MIN) :NORM_MIN)
struct _GtkWidget GtkWidget
GtkWidget, opaque, spelled exactly as GTK spells it.
const dt_colormatrix_t dt_aligned_pixel_t out
dt_store_simd_aligned(out, dt_mat3x4_mul_vec4(vin, dt_colormatrix_row_to_simd(matrix, 0), dt_colormatrix_row_to_simd(matrix, 1), dt_colormatrix_row_to_simd(matrix, 2)))
gboolean dt_image_is_monochrome(const dt_image_t *img)
void * dt_alloc_align(size_t size)
Allocate cacheline-aligned memory.
struct dt_bauhaus_t * dt_bauhaus_get_global(void)
#define dt_dev_add_history_item(dev, module, enable, redraw)
gboolean dt_dev_module_geometry_gui(dt_develop_t *dev, dt_iop_module_t *module, dt_iop_roi_t *in, dt_iop_roi_t *out)
One module's own input and output rectangles at full resolution, from the geometry service.
@ DT_DEV_PIXELPIPE_DISPLAY_MASK
GtkWidget * status
result of the last capture
void dt_loc_get_datadir(char *datadir, size_t bufsize)
void dt_loc_get_user_config_dir(char *configdir, size_t bufsize)
Where things are on the image, answered without a pipeline.
static void dt_iop_image_copy_by_size(float *const __restrict__ out, const float *const __restrict__ in, const size_t width, const size_t height, const size_t ch)
void dt_iop_compute_module_hash(dt_iop_module_t *module, GList *masks)
const char ** dt_iop_set_description(dt_iop_module_t *module, const char *main_text, const char *purpose, const char *input, const char *process, const char *output)
@ IOP_FLAGS_TILING_FULL_ROI
GtkWidget * dt_iop_button_new(dt_iop_module_t *self, const gchar *label, GCallback callback, gboolean local, guint accel_key, GdkModifierType mods, DTGTKCairoPaintIconFunc paint, gint paintflags, GtkWidget *box)
GtkWidget * dt_bauhaus_slider_from_params(dt_iop_module_t *self, const char *param)
GtkWidget * dt_bauhaus_combobox_from_params(dt_iop_module_t *self, const char *param)
static dt_iop_gui_data_t * dt_iop_gui_data(const struct dt_iop_module_t *m)
The module's GUI data blob, NULL-safe for headless callers: IOP process() implementations read it for...
#define IOP_GUI_ALLOC(module)
const struct dt_interpolation * dt_interpolation_new(enum dt_interpolation_type type)
__DT_CLONE_TARGETS__ float dt_interpolation_compute_sample(const struct dt_interpolation *itor, const float *in, const float x, const float y, const int width, const int height, const int samplestride, const int linestride)
@ DT_INTERPOLATION_BICUBIC
@ DT_INTERPOLATION_BILINEAR
@ DT_INTERPOLATION_MITCHELL
@ DT_INTERPOLATION_USERPREF_WARP
static const dt_dev_pixelpipe_t * pipe
static const dt_dev_pixelpipe_t const dt_dev_pixelpipe_iop_t * piece
static const dt_iop_drawlayer_params_t * params
int distort_backtransform(dt_iop_module_t *self, const dt_dev_pixelpipe_t *pipe, const dt_dev_pixelpipe_iop_t *piece, float *const __restrict points, size_t points_count)
#define DT_LENS_MODIFY_ANSEL_MASK
void commit_params(struct dt_iop_module_t *self, dt_iop_params_t *p1, dt_dev_pixelpipe_t *pipe, dt_dev_pixelpipe_iop_t *piece)
static const char *const _lens_source_names[DT_LENS_SOURCE_LAST]
void distort_mask(struct dt_iop_module_t *self, const struct dt_dev_pixelpipe_t *pipe, struct dt_dev_pixelpipe_iop_t *piece, const float *const in, float *const out, const dt_iop_roi_t *const roi_in, const dt_iop_roi_t *const roi_out)
static long long * _camera_all_ids(int *out_n)
Every camera in the database, as ids the caller must free with dt_free_align().
const char ** description(struct dt_iop_module_t *self)
static void _lens_rebuild_axis_rows(dt_iop_module_t *self)
Every axis, for a fresh image.
static const char * _lens_type_name(int type)
A projection's name, replacing lfLens::GetLensTypeDesc().
static void _lens_fill_vignette_row(float *const buf, const int width, const int ch)
static int _lens_used_mask(dt_iop_module_t *self)
The lensfun modify mask this image allows: monochrome sensors get no TCA correction.
static void _lens_build_data(dt_iop_module_t *self, const dt_iop_lensfun_params_t *const p, dt_iop_lensfun_data_t *d)
Build the lensfun state from resolved parameters. THE constructor.
static int ptr_array_find_sorted(const GPtrArray *array, const void *item, GCompareFunc compare)
static gboolean _lens_source_is_library_served(const dt_lens_source_t source)
Is this source served by the LensSerious path, once the data has been prepared?
static int _lens_mask_for_mono(const gboolean monochrome)
Which axes may be attempted on this image.
static int _lens_source_row(const dt_iop_lensfun_gui_data_t *g, const dt_lens_axis_t axis, const dt_lens_source_t source)
Show only the controls the current sources actually use.
static void _lens_free_data(void *ptr)
static void _lens_report_db_failure(const char *path, const ls_db_open_status_t status, const int found_version, const char *detail)
This thread's database handle, opened on first use.
static GtkWidget * _lens_add_axis_combobox(dt_iop_module_t *self, dt_iop_lensfun_gui_data_t *g, const dt_lens_axis_t axis, const char *label, const char *tooltip)
Build one axis's source combobox and pack it at the end of the module.
void reload_defaults(dt_iop_module_t *module)
static int _lens_axis_presence_bit(const dt_lens_axis_t axis)
The single bit that says whether an axis is on.
static int _lens_axis_shift(const dt_lens_axis_t axis)
How far up modify_flags this axis's two source bits sit.
dt_lens_modify_t
What modify_flags holds, bit by bit.
@ DT_LENS_MODIFY_GEOMETRY
@ DT_LENS_MODIFY_VIGNETTING
@ DT_LENS_SOURCE_SHIFT_VIGNETTING
@ DT_LENS_MODIFY_DISTORTION
@ DT_LENS_SOURCE_SHIFT_TCA
@ DT_LENS_SOURCE_SHIFT_DISTORTION
dt_lens_source_t
Where one axis takes its correction from. The same vocabulary for all three.
@ DT_LENS_SOURCE_EMBEDDED
static void lens_comboentry_distance_update(GtkWidget *widget, dt_iop_module_t *self)
static char * _lens_sanitize(const char *orig_lens)
static int _lens_geometry_backtransform(const void *data, const dt_geometry_record_t *const record, dt_geometry_chain_t *chain, float *points, size_t points_count)
static const dt_lens_source_t _lens_axis_sources[DT_LENS_AXIS_LAST][DT_LENS_SOURCE_LAST]
static void lens_set(dt_iop_module_t *self, long long lens_id)
Show a lens in the panel, and offer the sources it makes available. VIEW ONLY – writes no parameter.
static gboolean _lens_flags_move_pixels(const int modify_flags)
Does this flag word describe anything that MOVES pixels?
static void autoscale_pressed(GtkWidget *button, gpointer user_data)
__DT_CLONE_TARGETS__ int process(dt_iop_module_t *self, const dt_dev_pixelpipe_t *pipe, const dt_dev_pixelpipe_iop_t *piece, const void *const ivoid, void *const ovoid)
static ls_db_t * _ls_db(void)
static int _lens_corrections_available(dt_iop_module_t *self, const dt_iop_lensfun_params_t *const p)
Which corrections this configuration will actually apply.
static void camera_menu_select(GtkMenuItem *menuitem, gpointer user_data)
static const dt_geometry_vtable_t _lens_geometry_vtable
static gboolean _ls_find_camera(const char *maker, const char *model, ls_camera_t *out)
The camera an EXIF maker/model names.
static int _lens_axis_flags(const dt_lens_axis_t axis)
The enable bits for one axis. Three of them for distortion; see the pack.
static void lens_comboentry_focal_update(GtkWidget *widget, dt_iop_module_t *self)
static void camera_menusearch_clicked(GtkWidget *button, gpointer user_data)
static gboolean _lens_image_embeds(dt_iop_module_t *self, const dt_lens_axis_t axis)
Does THIS image carry a maker's profile for this axis?
static void lens_comboentry_aperture_update(GtkWidget *widget, dt_iop_module_t *self)
static long long _ls_find_lens(long long mount_id, float crop, float focal, const char *lens_name)
The lens a free-text name names, as an id.
static void _lens_params_set_lens(dt_iop_module_t *self, const long long lens_id)
Write the lens the user picked into the params. USER INTERACTION ONLY.
static void _lens_axis_source_changed(GtkWidget *widget, gpointer user_data)
static gboolean _lens_axis_enabled(const dt_iop_lensfun_params_t *p, const dt_lens_axis_t axis)
Is this axis correcting at all, from wherever?
void init_pipe(struct dt_iop_module_t *self, dt_dev_pixelpipe_t *pipe, dt_dev_pixelpipe_iop_t *piece)
static __DT_CLONE_TARGETS__ int get_modifier(int *mods_done, int w, int h, const dt_iop_lensfun_data_t *d, int mods_filter, gboolean force_inverse, ls_modifier_t *mod, ls_modifier_t *vig_mod)
Resolve the lens at one shooting configuration. THE modifier factory.
dt_lens_axis_t
The correction axes, as an index rather than a bit – so a caller can loop.
@ DT_LENS_AXIS_DISTORTION
@ DT_LENS_AXIS_VIGNETTING
int distort_transform(dt_iop_module_t *self, const dt_dev_pixelpipe_t *pipe, const dt_dev_pixelpipe_iop_t *piece, float *const __restrict points, size_t points_count)
static gboolean _lens_source_applicable(const dt_lens_axis_t axis, const dt_lens_source_t source)
Whether source means anything on axis.
static void ptr_array_insert_index(GPtrArray *array, const void *item, int index)
gboolean geometry_record(dt_iop_module_t *self, const void *params, dt_geometry_record_t *record)
void gui_update(struct dt_iop_module_t *self)
Refresh GUI controls from current params and configuration.
static int _lens_geometry_apply(const void *data, const dt_geometry_record_t *const record, float *points, size_t points_count, gboolean inverse)
Apply the correction to points. inverse selects the direction, as get_modifier() means it: distort_tr...
static gboolean _lens_flags_have_axis(const int modify_flags, const dt_lens_axis_t axis)
Is this axis present in a flag word – typically get_modifier()'s done?
static int precision(double x, double adj)
void gui_init(struct dt_iop_module_t *self)
static void _lens_params_set_camera(dt_iop_module_t *self, const long long camera_id)
Write the camera the user picked into the params. USER INTERACTION ONLY.
void gui_changed(dt_iop_module_t *self, GtkWidget *w, void *previous)
static dt_lens_axis_t _lens_axis_of_widget(const dt_iop_lensfun_gui_data_t *g, const GtkWidget *w)
Which axis a combobox belongs to, by widget identity.
static long long * _lens_ids_for_camera(dt_iop_module_t *self, const char *model, int *out_n)
The lenses to offer for the camera currently shown, as ids.
void tiling_callback(struct dt_iop_module_t *self, const struct dt_dev_pixelpipe_t *pipe, const struct dt_dev_pixelpipe_iop_t *piece, struct dt_develop_tiling_t *tiling)
static int _lens_database_offers(dt_iop_module_t *self, const dt_iop_lensfun_params_t *p)
Which axes the lens DATABASE could correct for this image, whatever is selected.
static void _lens_gui_update_sensitivity(dt_iop_module_t *self)
void cleanup_global(dt_iop_module_so_t *module)
static int _lens_geometry_transform(const void *data, const dt_geometry_record_t *const record, dt_geometry_chain_t *chain, float *points, size_t points_count)
int default_colorspace(dt_iop_module_t *self, dt_dev_pixelpipe_t *pipe, const dt_dev_pixelpipe_iop_t *piece)
static void lens_menu_fill(dt_iop_module_t *self, const long long *ids, int n)
static dt_lens_source_t _lens_source_decode(const int modify_flags, const gboolean tca_override, const dt_lens_axis_t axis)
Decode one axis's source out of a raw flag word.
static void lens_menusearch_clicked(GtkWidget *button, gpointer user_data)
static float get_autoscale(dt_iop_module_t *self, dt_iop_lensfun_params_t *p)
static GPrivate _ls_tls_key
void modify_roi_in(struct dt_iop_module_t *self, const struct dt_dev_pixelpipe_t *pipe, struct dt_dev_pixelpipe_iop_t *piece, const dt_iop_roi_t *const roi_out, dt_iop_roi_t *roi_in)
void gui_cleanup(struct dt_iop_module_t *self)
@ DT_LENS_FISHEYE_EQUISOLID
@ DT_LENS_FISHEYE_ORTHOGRAPHIC
@ DT_LENS_FISHEYE_STEREOGRAPHIC
@ DT_LENS_EQUIRECTANGULAR
static int ptr_array_insert_sorted(GPtrArray *array, const void *item, GCompareFunc compare)
static void lens_menu_select(GtkMenuItem *menuitem, gpointer user_data)
static void _lens_rebuild_axis_row(dt_iop_module_t *self, const dt_lens_axis_t axis)
Rebuild each axis's combobox to hold exactly the sources THIS image can supply.
static gboolean _lens_data_available(const dt_iop_lensfun_data_t *d)
Does this pipe data hold ANY resolvable correction source?
static void target_geometry_changed(GtkWidget *widget, gpointer user_data)
static void parse_model(const char *txt, char *model, size_t sz_model)
void cleanup_pipe(struct dt_iop_module_t *self, dt_dev_pixelpipe_t *pipe, dt_dev_pixelpipe_iop_t *piece)
static dt_lens_source_t _lens_source_get(const dt_iop_lensfun_params_t *p, const dt_lens_axis_t axis)
Where this axis takes its correction from.
static dt_lens_source_t _lens_source_displayed(const dt_iop_lensfun_gui_data_t *g, const dt_iop_lensfun_params_t *p, const dt_lens_axis_t axis)
The source the panel is SHOWING for this axis.
static void camera_set(dt_iop_module_t *self, long long camera_id)
Show a camera in the panel. VIEW ONLY – writes no parameter.
static void delete_children(GtkWidget *widget, gpointer data)
static void _ls_tls_free(gpointer data)
void init_global(dt_iop_module_so_t *module)
#define DT_LENS_MODIFY_ALL_AXES
static gboolean _lens_source_is(const dt_iop_lensfun_params_t *p, const dt_lens_axis_t axis, const dt_lens_source_t source)
Is this axis taking its correction from source?
static const dt_iop_lensfun_params_t * _lens_effective_params(dt_iop_module_t *self, const dt_iop_lensfun_params_t *const p)
Which parameters are actually in force.
int process_cl(struct dt_iop_module_t *self, const dt_dev_pixelpipe_t *pipe, const dt_dev_pixelpipe_iop_t *piece, cl_mem dev_in, cl_mem dev_out)
#define DT_LENS_MODIFY_DISTORTION_PACK
The three lensfun axes that always move together, as one flag.
static _ls_tls_t * _ls_tls_get(void)
This thread's cache block, allocated on first use. NULL only if that allocation failed,...
void modify_roi_out(struct dt_iop_module_t *self, const struct dt_dev_pixelpipe_t *pipe, struct dt_dev_pixelpipe_iop_t *piece, dt_iop_roi_t *roi_out, const dt_iop_roi_t *roi_in)
static void _lens_source_set(dt_iop_lensfun_params_t *p, const dt_lens_axis_t axis, dt_lens_source_t source)
Point one axis at a source, leaving every other axis alone.
int legacy_params(dt_iop_module_t *self, const void *const old_params, const int old_version, void *new_params, const int new_version)
static void camera_menu_fill(dt_iop_module_t *self, const long long *ids, int n)
Build the camera picker from a list of database ids.
_lib_location_type_t type
void dt_print(dt_debug_thread_t thread, const char *msg,...) __attribute__((format(printf
Print to stdout when thread is enabled, prefixed with seconds since startup.
float *const restrict const size_t k
float *const restrict const size_t const size_t ch
#define IS_NULL_PTR(p)
C is way too permissive with !=, == and if(var) checks, which can mean too many things depending on w...
#define dt_free_align(ptr)
Release memory from dt_alloc_align() and set ptr to NULL.
static void * dt_calloc_align(size_t size)
dt_alloc_align() followed by a zero fill.
#define DT_ALIGNED_ARRAY
Align an object on a cacheline boundary, so AVX2 can load it whole.
static void dt_free_gpointer(gpointer ptr)
g_free() one pointer, with the signature GDestroyNotify wants.
#define dt_free(ptr)
g_free() ptr and set it to NULL, skipping both if it is already NULL.
#define DT_MODULE_INTROSPECTION(MODVER, PARAMSTYPE)
DT_MODULE() for a module whose params struct is introspected.
int dt_opencl_enqueue_kernel_2d(const int dev, const int kernel, const size_t *sizes)
int dt_opencl_create_kernel(const int prog, const char *name)
int dt_opencl_enqueue_copy_image(const int devid, cl_mem src, cl_mem dst, size_t *orig_src, size_t *orig_dst, size_t *region)
void dt_opencl_free_kernel(const int kernel)
int dt_opencl_set_kernel_arg(const int dev, const int kernel, const int num, const size_t size, const void *arg)
#define __OMP_PARALLEL_FOR__(...)
#define DT_PATH_MAX
Buffer size for a filesystem path anywhere in Ansel.
void dt_concat_path_file(char destination[4096], const char path[4096], const char *const file)
Append a constant filename to a variable, stack-based, fixed-sized, directory, and add a / in-between...
#define dt_pixelpipe_cache_alloc_align_cache(size, id)
#define dt_pixelpipe_cache_free_align(mem)
#define dt_get_perthread(buf, padsize)
#define dt_pixelpipe_cache_alloc_perthread_float(n, padded_size)
#define DT_PIXEL_SIMD_CHANNELS
One module instance's contribution, as data.
A module's geometry, evaluated. Pure functions of the record's own data.
float exif_focus_distance
ls_vendor_data_t exif_correction
enum dt_interpolation_type id
dt_iop_lensfun_data_t data
dt_lens_type_t target_geom
int kernel_lens_distort_bicubic
int kernel_lens_distort_bilinear
int kernel_lens_distort_mitchell
dt_lens_source_t axis_row[DT_LENS_AXIS_LAST][DT_LENS_SOURCE_LAST]
int axis_rows[DT_LENS_AXIS_LAST]
GtkWidget * axis_source[DT_LENS_AXIS_LAST]
GtkWidget * lens_param_box
dt_lens_type_t target_geom
dt_iop_params_t * default_params
struct dt_iop_module_gui_t * gui
struct dt_develop_t * dev
dt_iop_global_data_t * global_data
Region of interest passed through the pixelpipe.
#define __DT_CLONE_TARGETS__