static void cdisplay_lcms_changed (GimpColorDisplay *display) { CdisplayLcms *lcms = CDISPLAY_LCMS (display); GtkWidget *widget = NULL; GimpColorConfig *config; GimpColorManaged *managed; GimpColorProfile *src_profile; if (lcms->transform) { g_object_unref (lcms->transform); lcms->transform = NULL; } config = gimp_color_display_get_config (display); managed = gimp_color_display_get_managed (display); if (! config || ! managed) return; if (GTK_IS_WIDGET (managed)) widget = gtk_widget_get_toplevel (GTK_WIDGET (managed)); src_profile = gimp_color_managed_get_color_profile (managed); lcms->transform = gimp_widget_get_color_transform (widget, config, src_profile, babl_format ("R'G'B'A float"), babl_format ("R'G'B'A float")); }
static void cdisplay_lcms_convert_buffer (GimpColorDisplay *display, GeglBuffer *buffer, GeglRectangle *area) { CdisplayLcms *lcms = CDISPLAY_LCMS (display); if (lcms->transform) gimp_color_transform_process_buffer (lcms->transform, buffer, area, buffer, area); }
static void cdisplay_lcms_finalize (GObject *object) { CdisplayLcms *lcms = CDISPLAY_LCMS (object); if (lcms->transform) { cmsDeleteTransform (lcms->transform); lcms->transform = NULL; } G_OBJECT_CLASS (cdisplay_lcms_parent_class)->finalize (object); }
static void cdisplay_lcms_convert_surface (GimpColorDisplay *display, cairo_surface_t *surface) { CdisplayLcms *lcms = CDISPLAY_LCMS (display); gint width = cairo_image_surface_get_width (surface); gint height = cairo_image_surface_get_height (surface); gint stride = cairo_image_surface_get_stride (surface); guchar *buf = cairo_image_surface_get_data (surface); cairo_format_t fmt = cairo_image_surface_get_format (surface); guchar *rowbuf; gint x, y; guchar r, g, b, a; if (fmt != CAIRO_FORMAT_ARGB32) return; if (! lcms->transform) return; rowbuf = g_malloc (stride); for (y = 0; y < height; y++, buf += stride) { /* Switch buf from ARGB premul to ARGB non-premul, since lcms ignores the * alpha channel. The macro takes care of byte order. */ for (x = 0; x < width; x++) { GIMP_CAIRO_ARGB32_GET_PIXEL (buf + 4*x, r, g, b, a); rowbuf[4*x+0] = a; rowbuf[4*x+1] = r; rowbuf[4*x+2] = g; rowbuf[4*x+3] = b; } cmsDoTransform (lcms->transform, rowbuf, rowbuf, width); /* And back to ARGB premul */ for (x = 0; x < width; x++) { a = rowbuf[4*x+0]; r = rowbuf[4*x+1]; g = rowbuf[4*x+2]; b = rowbuf[4*x+3]; GIMP_CAIRO_ARGB32_SET_PIXEL (buf + 4*x, r, g, b, a); } } g_free (rowbuf); }
static void cdisplay_lcms_convert_buffer (GimpColorDisplay *display, GeglBuffer *buffer, GeglRectangle *area) { CdisplayLcms *lcms = CDISPLAY_LCMS (display); GeglBufferIterator *iter; if (! lcms->transform) return; iter = gegl_buffer_iterator_new (buffer, area, 0, babl_format ("R'G'B'A float"), GEGL_BUFFER_READWRITE, GEGL_ABYSS_NONE); while (gegl_buffer_iterator_next (iter)) { gfloat *data = iter->data[0]; cmsDoTransform (lcms->transform, data, data, iter->length); } }
static void cdisplay_lcms_changed (GimpColorDisplay *display) { CdisplayLcms *lcms = CDISPLAY_LCMS (display); GimpColorConfig *config = gimp_color_display_get_config (display); cmsHPROFILE src_profile = NULL; cmsHPROFILE dest_profile = NULL; cmsHPROFILE proof_profile = NULL; cmsUInt16Number alarmCodes[cmsMAXCHANNELS] = { 0, }; if (lcms->transform) { cmsDeleteTransform (lcms->transform); lcms->transform = NULL; } if (! config) return; switch (config->mode) { case GIMP_COLOR_MANAGEMENT_OFF: return; case GIMP_COLOR_MANAGEMENT_SOFTPROOF: proof_profile = cdisplay_lcms_get_printer_profile (lcms); /* fallthru */ case GIMP_COLOR_MANAGEMENT_DISPLAY: src_profile = cdisplay_lcms_get_rgb_profile (lcms); dest_profile = cdisplay_lcms_get_display_profile (lcms); break; } if (proof_profile) { cmsUInt32Number softproof_flags = 0; if (! src_profile) src_profile = gimp_lcms_create_srgb_profile (); if (! dest_profile) dest_profile = gimp_lcms_create_srgb_profile (); softproof_flags |= cmsFLAGS_SOFTPROOFING; if (config->simulation_use_black_point_compensation) { softproof_flags |= cmsFLAGS_BLACKPOINTCOMPENSATION; } if (config->simulation_gamut_check) { guchar r, g, b; softproof_flags |= cmsFLAGS_GAMUTCHECK; gimp_rgb_get_uchar (&config->out_of_gamut_color, &r, &g, &b); alarmCodes[0] = (cmsUInt16Number) r * 256; alarmCodes[1] = (cmsUInt16Number) g * 256; alarmCodes[2] = (cmsUInt16Number) b * 256; cmsSetAlarmCodes (alarmCodes); } lcms->transform = cmsCreateProofingTransform (src_profile, TYPE_RGBA_FLT, dest_profile, TYPE_RGBA_FLT, proof_profile, config->simulation_intent, config->display_intent, softproof_flags); cmsCloseProfile (proof_profile); } else if (src_profile || dest_profile) { cmsUInt32Number display_flags = 0; if (! src_profile) src_profile = gimp_lcms_create_srgb_profile (); if (! dest_profile) dest_profile = gimp_lcms_create_srgb_profile (); if (config->display_use_black_point_compensation) { display_flags |= cmsFLAGS_BLACKPOINTCOMPENSATION; } lcms->transform = cmsCreateTransform (src_profile, TYPE_RGBA_FLT, dest_profile, TYPE_RGBA_FLT, config->display_intent, display_flags); } if (dest_profile) cmsCloseProfile (dest_profile); if (src_profile) cmsCloseProfile (src_profile); }
static GtkWidget * cdisplay_lcms_configure (GimpColorDisplay *display) { CdisplayLcms *lcms = CDISPLAY_LCMS (display); GObject *config = G_OBJECT (gimp_color_display_get_config (display)); GtkWidget *vbox; GtkWidget *hint; GtkWidget *table; GtkWidget *label; gint row = 0; if (! config) return NULL; vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 12); hint = gimp_hint_box_new (_("This filter takes its configuration " "from the Color Management section " "in the Preferences dialog.")); gtk_box_pack_start (GTK_BOX (vbox), hint, FALSE, FALSE, 0); gtk_widget_show (hint); table = gtk_table_new (5, 2, FALSE); gtk_table_set_row_spacings (GTK_TABLE (table), 6); gtk_table_set_row_spacing (GTK_TABLE (table), 0, 12); gtk_table_set_col_spacings (GTK_TABLE (table), 6); gtk_box_pack_start (GTK_BOX (vbox), table, FALSE, FALSE, 0); gtk_widget_show (table); cdisplay_lcms_attach_labelled (GTK_TABLE (table), row++, _("Mode of operation:"), gimp_prop_enum_label_new (config, "mode")); label = gtk_label_new (NULL); gtk_label_set_ellipsize (GTK_LABEL (label), PANGO_ELLIPSIZE_END); g_object_set_data (G_OBJECT (lcms), "rgb-profile", label); cdisplay_lcms_attach_labelled (GTK_TABLE (table), row++, _("Image profile:"), label); cdisplay_lcms_update_profile_label (lcms, "rgb-profile"); label = gtk_label_new (NULL); gtk_label_set_ellipsize (GTK_LABEL (label), PANGO_ELLIPSIZE_END); g_object_set_data (G_OBJECT (lcms), "display-profile", label); cdisplay_lcms_attach_labelled (GTK_TABLE (table), row++, _("Monitor profile:"), label); cdisplay_lcms_update_profile_label (lcms, "display-profile"); label = gtk_label_new (NULL); gtk_label_set_ellipsize (GTK_LABEL (label), PANGO_ELLIPSIZE_END); g_object_set_data (G_OBJECT (lcms), "printer-profile", label); cdisplay_lcms_attach_labelled (GTK_TABLE (table), row++, _("Print simulation profile:"), label); cdisplay_lcms_update_profile_label (lcms, "printer-profile"); g_signal_connect_object (config, "notify", G_CALLBACK (cdisplay_lcms_notify_profile), lcms, 0); return vbox; }