bool ColorContext::getDeviceProfile(oyConfig_s *device) { kDebug() << device; oyProfile_Release(&m_dstProfile); oyOptions_s *options = 0; oyOptions_SetFromText(&options, "//"OY_TYPE_STD"/config/command", "list", OY_CREATE_NEW); oyOptions_SetFromText(&options, "//"OY_TYPE_STD"/config/icc_profile.x_color_region_target", "yes", OY_CREATE_NEW ); int error = oyDeviceGetProfile(device, options, &m_dstProfile); oyOptions_Release(&options); if (m_dstProfile) { /* check that no sRGB is delivered */ if (error) { oyProfile_s *dummyProfile = oyProfile_FromStd(oyASSUMED_WEB, icc_profile_flags, 0); if (oyProfile_Equal(dummyProfile, m_dstProfile)) { kWarning() << "Output" << m_outputName << "ignoring fallback, error" << error; oyProfile_Release(&m_dstProfile); error = 1; } else error = 0; oyProfile_Release(&dummyProfile); } } else { kWarning() << "Output" << m_outputName << ": no ICC profile found, error" << error; error = 1; } return error == 0; }
int getDeviceProfile ( Display * display, oyConfig_s * device, int screen ) { oyProfile_s * dst_profile = 0; int error = 0; uint32_t icc_profile_flags = oyICCProfileSelectionFlagsFromOptions( OY_CMM_STD, "//" OY_TYPE_STD "/icc_color", NULL, 0 ); oyOptions_s * options = 0; oyDeviceUnset( device ); /*oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/command", "list", OY_CREATE_NEW ); oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/icc_profile.x_color_region_target", "yes", OY_CREATE_NEW );*/ error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/icc_profile_flags", icc_profile_flags, 0, OY_CREATE_NEW ); error = oyDeviceGetProfile( device, options, &dst_profile ); oyOptions_Release( &options ); return error; }
void SySendNativeUpdate(const char * func) { // e.g. send native (e.g. X11) reload event oyOptions_s * opts = oyOptions_New(NULL), * results = 0; int error = oyOptions_Handle( "//" OY_TYPE_STD "/send_native_update_event", opts,"send_native_update_event", &results ); oyOptions_Release( &opts ); if(oy_debug) fprintf(stderr, "send_native_update_event %s()\n", func); if(error) fprintf(stderr, "send_native_update_event failed\n"); }
oyProfile_s * getEditingProfile ( ) { static oyProfile_s * editing = NULL; if(!editing) { oyOption_s *matrix = oyOption_FromRegistration("///color_matrix." "from_primaries." "redx_redy_greenx_greeny_bluex_bluey_whitex_whitey_gamma", NULL ); /* http://www.color.org/chardata/rgb/rommrgb.xalter * original gamma is 1.8, we adapt to typical LCD gamma of 2.2 */ oyOption_SetFromDouble( matrix, 0.7347, 0, 0); oyOption_SetFromDouble( matrix, 0.2653, 1, 0); oyOption_SetFromDouble( matrix, 0.1596, 2, 0); oyOption_SetFromDouble( matrix, 0.8404, 3, 0); oyOption_SetFromDouble( matrix, 0.0366, 4, 0); oyOption_SetFromDouble( matrix, 0.0001, 5, 0); oyOption_SetFromDouble( matrix, 0.3457, 6, 0); oyOption_SetFromDouble( matrix, 0.3585, 7, 0); oyOption_SetFromDouble( matrix, 2.2, 8, 0); oyOptions_s * opts = oyOptions_New(0), * result = 0; oyOptions_MoveIn( opts, &matrix, -1 ); oyOptions_Handle( "//" OY_TYPE_STD "/create_profile.icc", opts,"create_profile.icc_profile.color_matrix", &result ); editing = (oyProfile_s*)oyOptions_GetType( result, -1, "icc_profile", oyOBJECT_PROFILE_S ); oyOptions_Release( &result ); oyProfile_AddTagText( editing, icSigProfileDescriptionTag, "ICC Examin ROMM gamma 2.2" ); if(oy_debug) { size_t size = 0; char * data = (char*) oyProfile_GetMem( editing, &size, 0, malloc ); oyWriteMemToFile_( "ICC Examin ROMM gamma 2.2.icc", data, size ); } } return editing; }
int oyDisplayColorServerIsActive( ) { int color_server_active = 0; /* A XCM color server expects local white point adjustment and effect. */ oyOptions_s * result_opts = oyOptions_New(NULL); oyOptions_Handle( "//" OY_TYPE_STD "/color_server_active", result_opts,"color_server_active.source_data", &result_opts ); color_server_active = oyOptions_FindString( result_opts, "color_server_active", "1" ) != NULL; oyOptions_Release( &result_opts ); if(oy_debug && color_server_active) oyMessageFunc_p( oyMSG_DBG, NULL, OY_DBG_FORMAT_ "color_server_active=%d", OY_DBG_ARGS_, color_server_active ); return color_server_active; }
/** Function oyFilterGraph_Release__Members * @memberof oyFilterGraph_s * @brief Custom FilterGraph destructor * @internal * * This function will free up all memmory allocated by the * input object. First all object members witch have their * own release method are deallocated. Then the deallocateFunc_ * of the oy_ object is used to release the rest of the members * that were allocated with oy_->allocateFunc_. * * @param[in] filtergraph the FilterGraph object * * @version Oyranos: x.x.x * @since YYYY/MM/DD (Oyranos: x.x.x) * @date YYYY/MM/DD */ void oyFilterGraph_Release__Members( oyFilterGraph_s_ * filtergraph ) { /* Deallocate members here * E.g: oyXXX_Release( &filtergraph->member ); */ oyFilterNodes_Release( &filtergraph->nodes ); oyFilterPlugs_Release( &filtergraph->edges ); oyOptions_Release( &filtergraph->options ); if(filtergraph->oy_->deallocateFunc_) { #if 0 oyDeAlloc_f deallocateFunc = filtergraph->oy_->deallocateFunc_; #endif /* Deallocate members of basic type here * E.g.: deallocateFunc( filtergraph->member ); */ } }
int updateOutputConfiguration( Display * display ) { int error = 0, i, n, update = 0; oyOptions_s * options = 0; oyConfigs_s * devices = 0; oyConfig_s * device = 0, * old_device = 0; /* allow Oyranos to see modifications made to the compiz Xlib context */ XFlush( display ); /* obtain device informations, including geometry and ICC profiles from the according Oyranos module */ error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "list", OY_CREATE_NEW ); if(error) WARNc2_S("%s %d", _("found issues"),error); error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/device_rectangle", "true", OY_CREATE_NEW ); if(error) WARNc2_S("%s %d", _("found issues"),error); error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/edid", "refresh", OY_CREATE_NEW ); error = oyDevicesGet( OY_TYPE_STD, "monitor", options, &devices ); if(error) WARNc2_S("%s %d", _("found issues"),error); n = oyOptions_Count( options ); oyOptions_Release( &options ); n = oyConfigs_Count( devices ); /* find out if monitors have changed at all * care only about EDID's and enumeration, no dimension */ if(n != oyConfigs_Count( old_devices )) update = 1; else for(i = 0; i < n; ++i) { const char * edid, * old_edid; device = oyConfigs_Get( devices, i ); old_device = oyConfigs_Get( old_devices, i ); edid = oyOptions_FindString( *oyConfig_GetOptions(device,"backend_core"),"EDID",0 ); old_edid = oyOptions_FindString( *oyConfig_GetOptions(old_device,"backend_core"),"EDID",0 ); if(edid && old_edid && strcmp(edid,old_edid)==0) update = 0; else update = 1; oyConfig_Release( &device ); oyConfig_Release( &old_device ); if(update) break; } if(!update) goto clean_update; cleanDisplay( display, n ); for(i = 0; i < n; ++i) { device = oyConfigs_Get( devices, i ); error = getDeviceProfile( display, device, i ); if(error) WARNc2_S("%s %d", _("found issues"),error); oyConfig_Release( &device ); } clean_update: oyConfigs_Release( &old_devices ); old_devices = devices; return 0; }
int main( int argc , char** argv ) { char *display_name = 0; char *monitor_profile = 0; int error = 0; /* the functional switches */ int erase = 0; int unset = 0; int list = 0; int setup = 0; int daemon = 0; char * format = 0; char * output = 0; int server = 0; int x_color_region_target = 0; int device_meta_tag = 0; char * add_meta = 0, * prof_name = 0, * module_name = 0, * new_profile_name = 0; char * device_class = 0; int list_modules = 0; int list_taxi = 0; int verbose = 0; int simple = 0; char *ptr = NULL; int x = 0, y = 0; int device_pos = -1; char *oy_display_name = NULL; oyProfile_s * prof = 0; oyConfig_s * device = 0; oyConfigs_s * devices = 0; oyOptions_s * options = 0; oyConfig_s * c = 0; oyOption_s * o = 0; size_t size = 0; const char * filename = 0; char * data = 0; uint32_t n = 0; int i; uint32_t icc_profile_flags = 0; oySCOPE_e scope = oySCOPE_USER; if(getenv(OY_DEBUG)) { int value = atoi(getenv(OY_DEBUG)); if(value > 0) oy_debug += value; } #ifdef USE_GETTEXT setlocale(LC_ALL,""); #endif oyI18NInit_(); STRING_ADD( device_class, "monitor._native" ); if(getenv("DISPLAY")) display_name = strdup(getenv("DISPLAY")); if(argc != 1) { int pos = 1; const char *wrong_arg = 0; while(pos < argc) { switch(argv[pos][0]) { case '-': for(i = 1; i < strlen(argv[pos]); ++i) switch (argv[pos][i]) { case '2': icc_profile_flags |= OY_ICC_VERSION_2; break; case '4': icc_profile_flags |= OY_ICC_VERSION_4; break; case 'e': erase = 1; monitor_profile = 0; break; case 'c': x_color_region_target = 1; monitor_profile = 0; break; case 'd': server = 1; OY_PARSE_INT_ARG( device_pos ); break; case 'f': OY_PARSE_STRING_ARG(format); monitor_profile = 0; break; case 'l': list = 1; monitor_profile = 0; break; case 'm': device_meta_tag = 1; break; case 'o': OY_PARSE_STRING_ARG(output); monitor_profile = 0; break; case 'u': unset = 1; monitor_profile = 0; break; case 'x': server = 1; OY_PARSE_INT_ARG( x ); break; case 'y': server = 1; OY_PARSE_INT_ARG( y ); break; case 'v': if(verbose) oy_debug += 1; verbose = 1; break; case 's': setup = 1; break; /* implicite -> setup */ case 'h': case '-': if(i == 1) { if(OY_IS_ARG("erase")) { erase = 1; monitor_profile = 0; i=100; break; } else if(OY_IS_ARG("unset")) { unset = 1; monitor_profile = 0; i=100; break; } else if(strcmp(&argv[pos][2],"x_color_region_target") == 0) { x_color_region_target = 1; i=100; break; } else if(OY_IS_ARG("setup")) { setup = 1; i=100; break; } else if(OY_IS_ARG("daemon")) { daemon = 1; i=100; break; } else if(OY_IS_ARG("format")) { OY_PARSE_STRING_ARG2(format, "format"); break; } else if(OY_IS_ARG("output")) { OY_PARSE_STRING_ARG2(output, "output"); break; } else if(OY_IS_ARG("add-edid")) { OY_PARSE_STRING_ARG2(add_meta,"add-edid"); break; } else if(OY_IS_ARG("name")) { OY_PARSE_STRING_ARG2(new_profile_name, "name"); break; } else if(OY_IS_ARG("profile")) { OY_PARSE_STRING_ARG2(prof_name, "profile"); break; } else if(OY_IS_ARG("display")) { const char * t=0; OY_PARSE_STRING_ARG2(t, "display"); if(t) {display_name = strdup(t);} break; } else if(OY_IS_ARG("modules")) { list_modules = 1; i=100; break; } else if(OY_IS_ARG("module")) { OY_PARSE_STRING_ARG2(module_name, "module"); break; } else if(OY_IS_ARG("list")) { list = 1; monitor_profile = 0; i=100; break; } else if(OY_IS_ARG("list-taxi")) { list_taxi = 1; i=100; break; } else if(OY_IS_ARG("path")) { simple = 2; i=100; break;} else if(OY_IS_ARG("short")) { simple = 1; i=100; break;} else if(OY_IS_ARG("verbose")) { if(verbose) {oy_debug += 1;} verbose = 1; i=100; break;} else if(OY_IS_ARG("system-wide")) { scope = oySCOPE_SYSTEM; i=100; break; } } default: printf("\n"); printf("oyranos-monitor v%d.%d.%d %s\n", OYRANOS_VERSION_A,OYRANOS_VERSION_B,OYRANOS_VERSION_C, _("is a color profile administration tool for monitors")); printf("%s:\n", _("Usage")); printf(" %s\n", _("Set new profile:")); printf(" %s [-x pos -y pos | -d number] [--system-wide] %s\n", argv[0], _("profile name")); printf("\n"); printf(" %s\n", _("Erase profile:")); printf(" %s -e [-x pos -y pos | -d number] [--system-wide]\n", argv[0]); printf("\n"); printf(" %s\n", _("Activate profiles:")); printf(" %s [-x pos -y pos | -d number]\n", argv[0]); printf("\n"); printf(" %s\n", _("List devices:")); printf(" %s -l [-x pos -y pos | -d number] [--short|--path]\n", argv[0]); /* --short argument */ printf(" --short %s\n", _("print only the file name")); /* --path argument */ printf(" --path %s\n", _("print the full file name")); printf("\n"); printf(" %s\n", _("List Taxi DB profiles for selected device:")); printf(" %s --list-taxi [-x pos -y pos | -d number]\n", argv[0]); printf("\n"); printf(" %s\n", _("List modules:")); printf(" %s --modules\n", argv[0]); printf("\n"); printf(" %s\n", _("Dump data:")); printf(" %s -f=[edid|icc|edid_icc] [-o=edid.bin] [-x pos -y pos | -d number] [-m]\n", argv[0]); printf("\n"); printf(" %s\n", _("General options:")); printf(" %s\n", _("-v verbose")); printf(" %s\n", _("--module name")); printf(" %s\n", _("-d device_position_start_from_zero")); printf("\n"); printf(_("For more informations read the man page:")); printf("\n"); printf(" man oyranos-monitor\n"); exit (0); break; } break; default: monitor_profile = argv[pos]; erase = 0; unset = 0; } if( wrong_arg ) { printf("%s %s\n", _("wrong argument to option:"), wrong_arg); exit(1); } ++pos; } if(oy_debug) fprintf( stderr, "%s\n", argv[1] ); } if(verbose) fprintf(stderr, "oyranos-monitor v%d.%d.%d %s\n", OYRANOS_VERSION_A,OYRANOS_VERSION_B,OYRANOS_VERSION_C, _("is a color profile administration tool for monitors")); #ifdef HAVE_X11 if(module_name && strstr(module_name, "oyX1")) { #endif #ifndef __APPLE__ if(!display_name) { WARNc_S( _("DISPLAY variable not set: giving up.") ); error = 1; return error; } #endif /* cut off the screen information */ if(display_name && (ptr = strchr(display_name,':')) != 0) if( (ptr = strchr(ptr, '.')) != 0 ) ptr[0] = '\000'; #ifdef HAVE_X11 } #endif /* implicite selection for the most common default case */ if(!icc_profile_flags) icc_profile_flags = oyICCProfileSelectionFlagsFromOptions( OY_CMM_STD, "//" OY_TYPE_STD "/icc_color", NULL, 0 ); #ifdef XCM_HAVE_X11 if(daemon) { Display * display = XOpenDisplay( display_name ); if(XcmColorServerCapabilities( display ) & XCM_COLOR_SERVER_MANAGEMENT) daemon = 2; XCloseDisplay( display ); } /* we rely on any color server doing X11 setup by its own and do not want to interfere */ if(daemon != 2) #endif { if(!erase && !unset && !list && !setup && !format && !add_meta && !list_modules && !list_taxi) setup = 1; if(module_name) { STRING_ADD( device_class, "."); STRING_ADD( device_class, module_name); } /* by default a given monitor profile is used to setup the major monitor */ if(monitor_profile && !server && device_pos == -1) device_pos = 0; if(device_pos != -1) { error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "properties", OY_CREATE_NEW ); error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/edid", "1", OY_CREATE_NEW ); #ifdef HAVE_X11 if(module_name && strstr(module_name, "oyX1")) { #endif if(server) error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/device_name", oy_display_name, OY_CREATE_NEW ); else error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/display_name", display_name, OY_CREATE_NEW ); #ifdef HAVE_X11 } #endif error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/icc_profile_flags", icc_profile_flags, 0, OY_CREATE_NEW ); error = oyDevicesGet( 0, device_class, options, &devices ); n = oyConfigs_Count( devices ); if(error <= 0 && 0 <= device_pos && device_pos < n ) { c = oyConfigs_Get( devices, device_pos ); oy_display_name = strdup( oyConfig_FindString( c, "device_name", 0 )); oyConfig_Release( &c ); } else fprintf( stderr, "%s %d. %s: %d\n", _("Could not resolve device"), device_pos, _("Available devices"), n); oyConfigs_Release( &devices ); oyOptions_Release( &options ); } else if(server) oy_display_name = oyGetDisplayNameFromPosition2 ( OY_TYPE_STD, device_class, display_name, x,y, oyAllocFunc); if(list_modules) { uint32_t count = 0, * rank_list = 0; char ** texts = 0; error = oyConfigDomainList( device_class, &texts, &count, &rank_list, 0 ); for(i = 0; i < count; ++i) printf("%s\n", strstr(texts[i],"monitor.") + 8 ); return error; } if(list_taxi) { oyConfig_s * taxi_dev; int32_t * ranks; int head = 0; devices = 0; if(!oy_display_name) { fprintf(stderr, "%s\n", _("Please specify a monitor with the -d option.") ); return error; } error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "properties", OY_CREATE_NEW ); error = oyDeviceGet( OY_TYPE_STD, device_class, oy_display_name, 0, &device ); oyDevicesFromTaxiDB( device, options, &devices, NULL ); n = oyConfigs_Count( devices ); if(n == 0) fprintf(stderr, "%s\n", _("Zero profiles found in Taxi ICC DB") ); ranks = calloc(sizeof(int32_t), n*2+1); for(i = 0; i < n; ++i) { taxi_dev = oyConfigs_Get( devices, i ); ranks[2*i+0] = i; error = oyConfig_Compare( device, taxi_dev, &ranks[2*i+1] ); oyConfig_Release( &taxi_dev ); } qsort( ranks, n, sizeof(int32_t)*2, compareRanks ); for(i = 0; i < n; ++i) { taxi_dev = oyConfigs_Get( devices, ranks[2*i+0] ); if(ranks[2*i+1] <= 0 && !verbose) { oyConfig_Release( &taxi_dev ); continue; } if(!head) { oyOptions_s * cs_options = 0; char * text = NULL, * report = NULL; head = 1; if(verbose) { if(x_color_region_target) { /* get XCM_ICC_COLOR_SERVER_TARGET_PROFILE_IN_X_BASE */ error = oyOptions_SetFromText( &cs_options, "//"OY_TYPE_STD"/config/icc_profile.x_color_region_target", "yes", OY_CREATE_NEW ); } error = oyDeviceGetInfo( device, oyNAME_NICK, cs_options, &text, oyAllocFunc ); oyStringAddPrintf_( &report, oyAllocFunc, oyDeAllocFunc, "\"%s\" ", text ? text : "???" ); error = oyDeviceGetInfo( device, oyNAME_NAME, cs_options, &text, oyAllocFunc ); oyStringAddPrintf_( &report, oyAllocFunc, oyDeAllocFunc, "%s", text ? text : "???" ); fprintf( stderr, "%s: %s\n", _("Taxi DB entries for device"), report ); } fprintf( stderr, "%s [%s] \"%s\"\n", _("Taxi ID"), _("match value"), _("description") ); oyOptions_Release( &cs_options ); } printf("%s/0 [%d] ", oyNoEmptyString_m_( oyConfig_FindString(taxi_dev, "TAXI_id", 0)), ranks[2*i+1]); printf("\"%s\"\n", oyNoEmptyString_m_( oyConfig_FindString(taxi_dev, "TAXI_profile_description", 0))); if(oy_debug) { char * json_text = 0; oyDeviceToJSON( taxi_dev, 0, &json_text, oyAllocateFunc_ ); fprintf(stderr, "%s\n", json_text ); oyFree_m_(json_text); } oyConfig_Release( &taxi_dev ); } oyConfig_Release( &device ); oyConfigs_Release( &devices ); oyOptions_Release( &options ); return error; } if(format && (strcmp(format,"edid") == 0 || strcmp(format,"icc") == 0 || strcmp(format,"edid_icc") == 0)) { icHeader * header = 0; char * out_name = 0; error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "properties", OY_CREATE_NEW ); error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/edid", "1", OY_CREATE_NEW ); if(oy_display_name) error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/device_name", oy_display_name, OY_CREATE_NEW ); #ifdef HAVE_X11 else if(module_name && strstr(module_name, "oyX1")) #endif error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/display_name", display_name, OY_CREATE_NEW ); error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/icc_profile_flags", icc_profile_flags, 0, OY_CREATE_NEW ); error = oyDevicesGet( 0, device_class, options, &devices ); n = oyConfigs_Count( devices ); if(!error) { for(i = 0; i < n; ++i) { c = oyConfigs_Get( devices, i ); if(strcmp(format,"edid_icc") == 0) { o = oyConfig_Find( c, "color_matrix.from_edid." "redx_redy_greenx_greeny_bluex_bluey_whitex_whitey_gamma"); if(o) { oyOptions_s * opts = oyOptions_New(0), * result = 0; error = oyOptions_MoveIn( opts, &o, -1 ); error = oyOptions_SetFromInt( &opts, "//" OY_TYPE_STD "/icc_profile_flags", icc_profile_flags, 0, OY_CREATE_NEW ); oyOptions_Handle( "///create_profile.icc", opts,"create_profile.icc_profile.color_matrix", &result ); prof = (oyProfile_s*)oyOptions_GetType( result, -1, "icc_profile", oyOBJECT_PROFILE_S ); oyOptions_Release( &result ); } if(prof) { uint32_t model_id = 0; const char * t = 0; error = oyProfile_AddTagText( prof, icSigProfileDescriptionTag, (char*) output ? output : format ); t = oyConfig_FindString( c, "EDID_manufacturer", 0 ); if(t) error = oyProfile_AddTagText( prof, icSigDeviceMfgDescTag, t ); t = oyConfig_FindString( c, "EDID_model", 0 ); if(t) error = oyProfile_AddTagText( prof, icSigDeviceModelDescTag, t); if(device_meta_tag) { oyOptions_s * opts = 0; error = oyOptions_SetFromText( &opts, "///key_prefix_required", "EDID_.OPENICC_" , OY_CREATE_NEW ); error = oyOptions_SetFromText( oyConfig_GetOptions( c,"backend_core" ), OY_TOP_SHARED OY_SLASH OY_DOMAIN_STD OY_SLASH OY_TYPE_STD OY_SLASH "device" OY_SLASH "config.icc_profile.monitor" OY_SLASH "OPENICC_automatic_generated", "1", OY_CREATE_NEW ); error = oyOptions_SetFromText( oyConfig_GetOptions( c,"backend_core" ), OY_TOP_SHARED OY_SLASH OY_DOMAIN_STD OY_SLASH OY_TYPE_STD OY_SLASH "device" OY_SLASH "config.icc_profile.monitor" OY_SLASH "prefix", "EDID_.OPENICC_", OY_CREATE_NEW ); oyProfile_AddDevice( prof, c, opts ); oyOptions_Release( &opts ); } data = oyProfile_GetMem( prof, &size, 0, oyAllocFunc ); header = (icHeader*) data; t = oyConfig_FindString( c, "EDID_mnft", 0 ); if(t) sprintf( (char*)&header->manufacturer, "%s", t ); t = oyConfig_FindString( c, "EDID_model_id", 0 ); if(t) model_id = atoi( t ); model_id = oyValueUInt32( model_id ); memcpy( &header->model, &model_id, 4 ); oyOption_Release( &o ); } } else if(strcmp(format,"edid") == 0) { o = oyConfig_Find( c, "edid" ); data = oyOption_GetData( o, &size, oyAllocFunc ); } else if(strcmp(format,"icc") == 0) { oyOptions_s * cs_options = 0; if(x_color_region_target) { /* get XCM_ICC_COLOR_SERVER_TARGET_PROFILE_IN_X_BASE */ error = oyOptions_SetFromText( &cs_options, "//"OY_TYPE_STD"/config/icc_profile.x_color_region_target", "yes", OY_CREATE_NEW ); } oyDeviceAskProfile2( c, cs_options, &prof ); oyOptions_Release( &cs_options ); if(device_meta_tag) { oyOptions_s * opts = 0; error = oyOptions_SetFromText( &opts, "///set_device_attributes", "true", OY_CREATE_NEW ); error = oyOptions_SetFromText( &opts, "///key_prefix_required", "EDID_" , OY_CREATE_NEW ); oyProfile_AddDevice( prof, c, opts ); oyOptions_Release( &opts ); } data = oyProfile_GetMem( prof, &size, 0, oyAllocFunc ); } if(data && size) { if(output) error = oyWriteMemToFile2_( output, data, size, 0x01, &out_name, oyAllocFunc ); else fwrite( data, sizeof(char), size, stdout ); oyDeAllocFunc( data ); size = 0; } else error = 1; if(!error) { if(verbose) fprintf( stderr, " written to %s\n", out_name ); } else printf( "Could not write %d bytes to %s\n", (int)size, out_name?out_name:format); if(out_name){ oyDeAllocFunc(out_name); out_name = 0; } oyProfile_Release( &prof ); oyOption_Release( &o ); oyConfig_Release( &c ); } } else WARNc2_S("oyDevicesGet %s %d", _("found issues"),error); oyConfigs_Release( &devices ); oyOptions_Release( &options ); } else if(prof_name && add_meta) { uint32_t id[4]; oyBlob_s * edid = oyBlob_New(0); char * edid_fn = oyResolveDirFileName_(add_meta); data = oyReadFileToMem_( edid_fn, &size, oyAllocateFunc_ ); oyBlob_SetFromData( edid, data, size, "edid" ); oyFree_m_(data); prof = oyProfile_FromName( prof_name, OY_NO_CACHE_READ | icc_profile_flags, 0 ); device = 0; oyOptions_Release( &options ); error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "add_meta", OY_CREATE_NEW ); error = oyOptions_MoveInStruct( &options, "//" OY_TYPE_STD "/config/icc_profile", (oyStruct_s**)&prof, OY_CREATE_NEW ); error = oyOptions_MoveInStruct( &options, "//" OY_TYPE_STD "/config/edid", (oyStruct_s**)&edid, OY_CREATE_NEW ); error = oyDeviceGet( OY_TYPE_STD, device_class, ":0.0", options, &device); if(verbose && device) { /* We need a newly opened profile, otherwise we obtaine cached modifications. */ oyProfile_s * p = oyProfile_FromName( prof_name, OY_NO_CACHE_READ | icc_profile_flags, 0 ); oyConfig_s * p_device = oyConfig_FromRegistration( oyConfig_GetRegistration( device ), 0 ); int32_t rank = 0; int old_oy_debug = oy_debug; char * json = 0; oyProfile_GetDevice( p, p_device ); if(oy_debug > 1) { error = oyDeviceToJSON( p_device, 0, &json, oyAllocateFunc_ ); fprintf(stderr, "device from profile %s:\n%s\n", prof_name, json ); oyFree_m_( json ); } if(oy_debug > 1) { error = oyDeviceToJSON( device, 0, &json, oyAllocateFunc_ ); fprintf(stderr, "device from edid %s:\n%s\n", edid_fn, json ); oyFree_m_( json ); } /*p_device->db = oyOptions_Copy( p_device->backend_core, 0 ); device->db = oyOptions_Copy( device->backend_core, 0 );*/ if(oy_debug < 2) oy_debug = 2; error = oyConfig_Compare( p_device, device, &rank ); oy_debug = old_oy_debug; fprintf(stderr, "rank of edid to previous profile %d\n", rank); } oyConfig_Release( &device ); oyFree_m_(edid_fn); prof = (oyProfile_s*)oyOptions_GetType( options, -1, "icc_profile", oyOBJECT_PROFILE_S ); oyOptions_Release( &options ); if(new_profile_name) error = oyProfile_AddTagText( prof, icSigProfileDescriptionTag, new_profile_name ); /* serialise before requesting a ICC md5 */ data = oyProfile_GetMem( prof, &size, 0, oyAllocFunc ); oyFree_m_(data); oyProfile_GetMD5( prof, OY_COMPUTE, id ); oyProfile_ToFile_( (oyProfile_s_*)prof, prof_name ); oyProfile_Release( &prof ); } if(list) { char * text = 0, * report = 0; uint32_t n = 0, i; oyOptions_s * cs_options = 0; if(x_color_region_target) { /* get XCM_ICC_COLOR_SERVER_TARGET_PROFILE_IN_X_BASE */ error = oyOptions_SetFromText( &cs_options, "//"OY_TYPE_STD"/config/icc_profile.x_color_region_target", "yes", OY_CREATE_NEW ); } error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "properties", OY_CREATE_NEW ); error = oyDevicesGet( 0, device_class, options, &devices ); n = oyConfigs_Count( devices ); if(error <= 0) { const char * device_name = 0; for(i = 0; i < n; ++i) { c = oyConfigs_Get( devices, i ); device_name = oyConfig_FindString( c, "device_name", 0 ); if( oy_display_name && device_name && strcmp( oy_display_name, device_name ) != 0 ) { oyConfig_Release( &c ); device_name = 0; continue; } if(verbose) fprintf(stderr,"------------------------ %d ---------------------------\n",i); error = oyDeviceGetInfo( c, oyNAME_NICK, cs_options, &text, oyAllocFunc ); if(!simple) { oyStringAddPrintf_( &report, oyAllocFunc, oyDeAllocFunc, "%d: ", i ); oyStringAddPrintf_( &report, oyAllocFunc, oyDeAllocFunc, "\"%s\" ", text ? text : "???" ); error = oyDeviceGetInfo( c, oyNAME_NAME, cs_options, &text, oyAllocFunc ); oyStringAddPrintf_( &report, oyAllocFunc, oyDeAllocFunc, "%s%s", text ? text : "???", (i+1 == n) || device_pos != -1 ? "" : "\n" ); } else { oyDeviceAskProfile2( c, cs_options, &prof ); data = oyProfile_GetMem( prof, &size, 0, oyAllocFunc); if(size && data) oyDeAllocFunc( data ); filename = oyProfile_GetFileName( prof, -1 ); oyStringAddPrintf_( &report, oyAllocFunc, oyDeAllocFunc, "%s%s", filename ? (simple == 1)?(strrchr(filename,OY_SLASH_C) ? strrchr(filename,OY_SLASH_C)+1:filename):filename : OY_PROFILE_NONE, (i+1 == n) || device_pos != -1 ? "" : "\n" ); } if(verbose) { error = oyDeviceGetInfo( c, oyNAME_DESCRIPTION, cs_options, &text, oyAllocFunc ); fprintf( stderr,"%s\n", text ? text : "???" ); } if(text) free( text ); /* verbose adds */ if(verbose) { oyDeviceAskProfile2( c, cs_options, &prof ); data = oyProfile_GetMem( prof, &size, 0, oyAllocFunc); if(size && data) oyDeAllocFunc( data ); filename = oyProfile_GetFileName( prof, -1 ); fprintf( stderr, " server profile \"%s\" size: %d\n", filename?filename:OY_PROFILE_NONE, (int)size ); text = 0; oyDeviceProfileFromDB( c, &text, oyAllocFunc ); fprintf( stderr, " DB profile \"%s\"\n keys: %s\n", text?text:OY_PROFILE_NONE, oyConfig_FindString( c, "key_set_name", 0 ) ? oyConfig_FindString( c, "key_set_name", 0 ) : OY_PROFILE_NONE ); oyProfile_Release( &prof ); oyDeAllocFunc( text ); } oyConfig_Release( &c ); } if(report) fprintf( stdout, "%s\n", report ); oyDeAllocFunc( report ); report = 0; } else WARNc2_S("oyDevicesGet %s %d", _("found issues"),error); oyConfigs_Release( &devices ); oyOptions_Release( &cs_options ); } if(oy_display_name) /* make shure the display name is correctly including the screen number */ { error = oyDeviceGet( OY_TYPE_STD, device_class, oy_display_name, 0, &device ); error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/icc_profile_flags", icc_profile_flags, 0, OY_CREATE_NEW ); if(monitor_profile) { if(verbose) fprintf( stdout, "oyDeviceSetProfile()\n" ); oyDeviceSetProfile( device, scope, monitor_profile ); if(verbose) fprintf( stdout, "oyDeviceUnset()\n" ); oyDeviceUnset( device ); } else if(erase || unset) { if(verbose) fprintf( stdout, "oyDeviceUnset()\n" ); oyDeviceUnset( device ); } if(erase) { if(verbose) fprintf( stdout, "oyConfig_EraseFromDB()\n" ); oyConfig_EraseFromDB( device, scope ); } if(setup) { if(monitor_profile) error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/skip_ask_for_profile", "yes", OY_CREATE_NEW ); if(verbose) fprintf( stdout, "oyDeviceSetup()\n" ); oyDeviceSetup( device, options ); } oyConfig_Release( &device ); } else if(erase || unset || setup) { error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/config/command", "list", OY_CREATE_NEW ); #ifdef HAVE_X11 if(module_name && strstr(module_name, "oyX1")) #endif error = oyOptions_SetFromText( &options, "//"OY_TYPE_STD"/config/display_name", display_name, OY_CREATE_NEW ); error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/icc_profile_flags", icc_profile_flags, 0, OY_CREATE_NEW ); error = oyDevicesGet( 0, device_class, options, &devices ); n = oyConfigs_Count( devices ); if(!error) { for(i = 0; i < n; ++i) { device = oyConfigs_Get( devices, i ); if(erase || unset) oyDeviceUnset( device ); if(erase) oyConfig_EraseFromDB( device, scope ); if(setup) oyDeviceSetup( device, options ); oyConfig_Release( &device ); } } oyConfigs_Release( &devices ); oyOptions_Release( &options ); } } if(oy_display_name) oyDeAllocFunc(oy_display_name); #if defined(XCM_HAVE_X11) if(daemon) error = runDaemon( display_name ); #else if(daemon) fprintf( stderr, "daemon mode not supported on your OS\n" ); #endif oyFinish_( FINISH_IGNORE_I18N | FINISH_IGNORE_CACHES ); return error; }
/** Function oyConfigs_FromDeviceClass * @memberof oyConfigs_s * @brief Ask a module for device informations or other direct calls * * @param[in] device_type the device type ::oyFILTER_REG_TYPE, * defaults to OY_TYPE_STD (optional) * @param[in] device_class the device class, e.g. "monitor", * ::oyFILTER_REG_APPLICATION * @param[in] options options to pass to the module, for zero * the usage instructions are requested, * a option "device_name" can be used * as filter * @param[out] devices the devices * @param[in] object the optional object * @return 0 - good, >= 1 - error * * @verbatim // pass empty options to the module to get a usage message oyOptions_s * options = 0; int error = oyConfigs_FromDeviceClass( OY_TYPE_STD, "monitor", options, 0, 0 ); @endverbatim * * @version Oyranos: 0.1.10 * @since 2009/01/28 (Oyranos: 0.1.10) * @date 2009/01/30 */ OYAPI int OYEXPORT oyConfigs_FromDeviceClass ( const char * device_type, const char * device_class, oyOptions_s * options, oyConfigs_s ** devices, oyObject_s object ) { int error = !device_class || !device_class[0]; oyConfig_s * device = 0; oyConfigs_s * configs = 0; int i, j, j_n; uint32_t count = 0, * rank_list = 0; char ** texts = 0, * device_class_registration = 0; const char * tmp = 0, * device_name = 0; if(error > 0) { WARNc_S( "\n No device_class argument provided. Give up" ); return 0; } /** 1. obtain detailed and expensive device informations */ if(options) { options = oyOptions_Copy( options, 0 ); device_name = oyOptions_FindString( options, "device_name", 0 ); } /** 1.2.1 build a device class registration string */ if(error <= 0) { device_class_registration = oyDeviceRegistrationCreate_( device_type, device_class, device_name, device_class_registration ); error = !device_class_registration; } /** 1.2.2 get all device class module names */ if(error <= 0) error = oyConfigDomainList ( device_class_registration, &texts, &count, &rank_list, 0 ); if(devices && !*devices) *devices = oyConfigs_New( object ); /** 1.3 ask each module */ for( i = 0; i < count; ++i ) { const char * registration_domain = texts[i]; /** 1.3.1 call into module */ error = oyConfigs_FromDomain( registration_domain, options, &configs, object); if(devices && *devices) j_n = oyConfigs_Count( configs ); else j_n = 0; for( j = 0; j < j_n; ++j ) { device = oyConfigs_Get( configs, j ); if(device_name) { /** 1.3.1.1 Compare the device_name with the device_name option * and collect the matching devices. */ tmp = oyConfig_FindString( device, "device_name", 0 ); if(tmp && oyStrcmp_( tmp, device_name ) == 0) oyConfigs_MoveIn( *devices, &device, -1 ); } else /** 1.3.1.2 ... or collect all device configurations */ oyConfigs_MoveIn( *devices, &device, -1 ); oyConfig_Release( &device ); } oyConfigs_Release( &configs ); } if(devices) j_n = oyConfigs_Count( *devices ); else j_n = 0; for( j = 0; j < j_n; ++j ) { device = oyConfigs_Get( *devices, j ); /** The basic call on how to obtain the configuration is added here as * the objects name. "properties" and "list" are known. */ if(oyOptions_FindString( options, "command", "properties" ) || oyOptions_FindString( options, "oyNAME_DESCRIPTION", 0 )) oyObject_SetName( device->oy_, "properties", oyNAME_NAME ); else if(oyOptions_FindString( options, "list", 0 )) oyObject_SetName( device->oy_, "list", oyNAME_NAME ); oyConfig_Release( &device ); } oyOptions_Release( &options ); return error; }
/** @brief create_profile.white_point_adjust.bradford * * The profile will be generated in many different shades, which will explode * conversion cache. */ int oyProfileAddWhitePointEffect( oyProfile_s * monitor_profile, oyOptions_s ** module_options ) { oyProfile_s * wtpt = NULL; double src_XYZ[3] = {0.0, 0.0, 0.0}, dst_XYZ[3] = {0.0, 0.0, 0.0}, scale = 1.0; int error = oyProfile_GetWhitePoint( monitor_profile, src_XYZ ); int32_t display_white_point = oyGetBehaviour( oyBEHAVIOUR_DISPLAY_WHITE_POINT ); oyOptions_s * result_opts = NULL, * opts = NULL; const char * desc = NULL; if(*module_options) { const char * value = oyOptions_FindString( *module_options, "display_white_point", 0 ); if(value) { int c = atoi( value ); if(c >= 0) display_white_point = c; } } if(!display_white_point) return 0; if(!error) error = oyGetDisplayWhitePoint( display_white_point, dst_XYZ ); if(isnan(dst_XYZ[0])) error = 1; if(error) { oyMessageFunc_p( oyMSG_WARN,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "automatic display_white_point: not readable", OY_DBG_ARGS_); return error; } desc = oyProfile_GetText( monitor_profile, oyNAME_DESCRIPTION ); error = oyOptions_SetFromString( &opts, "//" OY_TYPE_STD "/src_name", desc, OY_CREATE_NEW ); if(error) return error; DBG_S_( oyPrintTime() ); { int current = -1, choices = 0; const char ** choices_string_list = NULL; uint32_t flags = 0; #ifdef HAVE_LOCALE_H char * old_loc = strdup(setlocale(LC_ALL,NULL)); setlocale(LC_ALL,"C"); #endif error = oyOptionChoicesGet2( oyWIDGET_DISPLAY_WHITE_POINT, flags, oyNAME_NAME, &choices, &choices_string_list, ¤t ); if(error > 0) oyMessageFunc_p( oyMSG_WARN,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "oyOptionChoicesGet2 failed %d", OY_DBG_ARGS_, error); #ifdef HAVE_LOCALE_H setlocale(LC_ALL,old_loc); if(old_loc) { free(old_loc); } old_loc = NULL; #endif if(current > 0 && current < choices && choices_string_list) { if(current == 1) /* automatic */ { double temperature = oyGetTemperature(-1); char k[12]; sprintf(k, "%dK", (int)temperature); oyOptions_SetFromString( &opts, "//" OY_TYPE_STD "/illu_name", k, OY_CREATE_NEW ); if(temperature <= 0.1) oyMessageFunc_p( oyMSG_WARN,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "automatic display_white_point: [%g %g %g] %s", OY_DBG_ARGS_, dst_XYZ[0], dst_XYZ[1], dst_XYZ[2], k); } else oyOptions_SetFromString( &opts, "//" OY_TYPE_STD "/illu_name", choices_string_list[current], OY_CREATE_NEW ); if(oy_debug) oyMessageFunc_p( oyMSG_DBG,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "illu_name: %s", OY_DBG_ARGS_, oyOptions_FindString( opts, "illu_name", 0) ); } oyOptionChoicesFree( oyWIDGET_DISPLAY_WHITE_POINT, &choices_string_list, choices ); } if(oy_debug) oyMessageFunc_p( oyMSG_WARN, NULL, OY_DBG_FORMAT_ "src_name: %s -> illu_name: %s", OY_DBG_ARGS_, oyOptions_FindString(opts, "src_name", 0), oyOptions_FindString(opts, "illu_name", 0) ); oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/src_iccXYZ", src_XYZ[0], 0, OY_CREATE_NEW ); oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/src_iccXYZ", src_XYZ[1], 1, OY_CREATE_NEW ); oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/src_iccXYZ", src_XYZ[2], 2, OY_CREATE_NEW ); oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/illu_iccXYZ", dst_XYZ[0], 0, OY_CREATE_NEW ); oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/illu_iccXYZ", dst_XYZ[1], 1, OY_CREATE_NEW ); oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/illu_iccXYZ", dst_XYZ[2], 2, OY_CREATE_NEW ); /* cache the display white point abstract profile */ error = oyOptions_Handle( "//" OY_TYPE_STD "/create_profile.white_point_adjust.bradford", opts, "create_profile.white_point_adjust.bradford.file_name", &result_opts ); DBG_S_( oyPrintTime() ); if(error > 0) oyMessageFunc_p( oyMSG_WARN,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "oyOptions_Handle(white_point_adjust.bradford.file_name) failed %d", OY_DBG_ARGS_, error); /* write cache profile for slightly better speed and useful for debugging */ if(error == 0) { const char * file_name = oyOptions_FindString( result_opts, "file_name", 0 ); char * cache_path = oyGetInstallPath( oyPATH_CACHE, oySCOPE_USER, oyAllocateFunc_ ), *t; if(strstr( cache_path, "device_link") != NULL) { t = strstr( cache_path, "device_link"); t[0] = '\000'; oyStringAddPrintf( &cache_path, 0,0, "white_point_adjust/%s.icc", file_name ); } if(oyIsFile_(cache_path)) { if(oy_debug) oyMessageFunc_p( oyMSG_DBG,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "found file_name: %s -> %s\n", OY_DBG_ARGS_, file_name, cache_path ); wtpt = oyProfile_FromFile( cache_path, 0,0 ); DBG_S_( oyPrintTime() ); } } if(!error && wtpt) { oyOptions_MoveInStruct( module_options, OY_STD "/icc_color/display.icc_profile.abstract.white_point.automatic.oy-monitor", (oyStruct_s**) &wtpt, OY_CREATE_NEW ); oyOptions_Release( &result_opts ); oyOptions_Release( &opts ); return error; } if(!error && !wtpt) { /* detect scaling factor * - convert monitor device RGB to XYZ, * - apply white point adaption matrix, * - convert back to monitor device RGB and * - again to XYZ to detect clipping and * - use that information for scaling inside the white point effect profile */ oyProfile_s * xyz_profile = oyProfile_FromStd( oyASSUMED_XYZ, 0, 0 ); float rgb[9] = {1,0,0, 0,1,0, 0,0,1}, xyz[9] = {0,0,0, 0,0,0, 0,0,0}; oyDATATYPE_e buf_type = oyFLOAT; oyConversion_s * cc_moni2xyz = oyConversion_CreateBasicPixelsFromBuffers( monitor_profile, rgb, oyDataType_m(buf_type), xyz_profile, xyz, oyDataType_m(buf_type), 0, 3 ); oyConversion_s * cc_xyz2moni = oyConversion_CreateBasicPixelsFromBuffers( xyz_profile, xyz, oyDataType_m(buf_type), monitor_profile, rgb, oyDataType_m(buf_type), 0, 3 ); oyMAT3 wtpt_adapt; oyCIEXYZ srcWtpt = {src_XYZ[0], src_XYZ[1], src_XYZ[2]}, dstIllu = {dst_XYZ[0], dst_XYZ[1], dst_XYZ[2]}; error = !oyAdaptationMatrix( &wtpt_adapt, NULL, &srcWtpt, &dstIllu ); int i,j; for(j = 0; j < 100; ++j) { oyConversion_RunPixels( cc_moni2xyz, 0 ); if(oy_debug) oyMessageFunc_p( oyMSG_DBG,(oyStruct_s*)cc_moni2xyz, OY_DBG_FORMAT_ "rgb->xyz:\nR[%g %g %g] G[%g %g %g] B[%g %g %g]", OY_DBG_ARGS_, xyz[0], xyz[1], xyz[2], xyz[3], xyz[4], xyz[5], xyz[6], xyz[7], xyz[8]); oyVEC3 rXYZ, srcXYZ[3] = { {{xyz[0], xyz[1], xyz[2]}}, {{xyz[3], xyz[4], xyz[5]}}, {{xyz[6], xyz[7], xyz[8]}} }; oyMAT3 wtpt_adapt_scaled, scale_mat = {{ {{scale,0,0}}, {{0,scale,0}}, {{0,0,scale}} }}; oyMAT3per( &wtpt_adapt_scaled, &wtpt_adapt, &scale_mat ); oyMAT3eval( &rXYZ, &wtpt_adapt_scaled, &srcXYZ[0] ); for(i = 0; i < 3; ++i) xyz[0+i] = rXYZ.n[i]; oyMAT3eval( &rXYZ, &wtpt_adapt_scaled, &srcXYZ[1] ); for(i = 0; i < 3; ++i) xyz[3+i] = rXYZ.n[i]; oyMAT3eval( &rXYZ, &wtpt_adapt_scaled, &srcXYZ[2] ); for(i = 0; i < 3; ++i) xyz[6+i] = rXYZ.n[i]; if(oy_debug) oyMessageFunc_p( oyMSG_DBG,(oyStruct_s*)cc_moni2xyz, OY_DBG_FORMAT_ "srcWtpt->Illu:\nR[%g %g %g] G[%g %g %g] B[%g %g %g]", OY_DBG_ARGS_, xyz[0], xyz[1], xyz[2], xyz[3], xyz[4], xyz[5], xyz[6], xyz[7], xyz[8]); oyConversion_RunPixels( cc_xyz2moni, 0 ); if(oy_debug) oyMessageFunc_p( oyMSG_WARN,(oyStruct_s*)cc_moni2xyz, OY_DBG_FORMAT_ "xyz->rgb:\nR[%g %g %g] G[%g %g %g] B[%g %g %g] %g", OY_DBG_ARGS_, rgb[0], rgb[1], rgb[2], rgb[3], rgb[4], rgb[5], rgb[6], rgb[7], rgb[8], scale); if(rgb[0+0] < 0.99 && rgb[3+1] < 0.99 && rgb[6+2] < 0.99) { if(scale < 1.00) scale += 0.01; break; } scale -= 0.01; } } oyMessageFunc_p( /*error ?*/ oyMSG_WARN/*:oyMSG_DBG*/,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "%s display_white_point: %d [%g %g %g] -> [%g %g %g] * %g %d", OY_DBG_ARGS_, desc, display_white_point, src_XYZ[0], src_XYZ[1], src_XYZ[2], dst_XYZ[0], dst_XYZ[1], dst_XYZ[2], scale, error); if(error > 0) return error; /* write cache profile for slightly better speed and useful for debugging */ if(error == 0) { const char * file_name = oyOptions_FindString( result_opts, "file_name", 0 ); char * cache_path = oyGetInstallPath( oyPATH_CACHE, oySCOPE_USER, oyAllocateFunc_ ), *t; if(strstr( cache_path, "device_link") != NULL) { t = strstr( cache_path, "device_link"); t[0] = '\000'; oyStringAddPrintf( &cache_path, 0,0, "white_point_adjust/%s.icc", file_name ); } { error = oyOptions_SetFromDouble( &opts, "//" OY_TYPE_STD "/scale", scale, 0, OY_CREATE_NEW ); if(oy_debug) oyMessageFunc_p( oyMSG_DBG,(oyStruct_s*)monitor_profile, OY_DBG_FORMAT_ "creating file_name: %s -> %s\n", OY_DBG_ARGS_, file_name, cache_path ); error = oyOptions_Handle( "//" OY_TYPE_STD "/create_profile.white_point_adjust.bradford", opts, "create_profile.white_point_adjust.bradford", &result_opts ); wtpt = (oyProfile_s*) oyOptions_GetType( result_opts, -1, "icc_profile", oyOBJECT_PROFILE_S ); error = !wtpt; if(!error) oyProfile_ToFile_( (oyProfile_s_*) wtpt, cache_path ); DBG_S_( oyPrintTime() ); } } error = !wtpt; if(error == 0) oyOptions_MoveInStruct( module_options, OY_STD "/icc_color/display.icc_profile.abstract.white_point.automatic.oy-monitor", (oyStruct_s**) &wtpt, OY_CREATE_NEW ); oyOptions_Release( &result_opts ); oyOptions_Release( &opts ); return error; }
oyConversion_s * oyConversion_FromImageForDisplay_ ( oyImage_s * image_in, oyImage_s * image_out, oyFilterNode_s ** cc_node, uint32_t flags, oyDATATYPE_e data_type, oyOptions_s * cc_options, oyObject_s obj ) { oyFilterNode_s * in = 0, * out = 0, * icc = 0; int error = 0; oyConversion_s * conversion = 0; oyOptions_s * options = 0; oyOption_s * option = 0; const char * sv = 0; double scale = 0; if(!image_in || !image_out) return NULL; /* start with an empty conversion object */ conversion = oyConversion_New( obj ); /* create a filter node */ in = oyFilterNode_NewWith( "//" OY_TYPE_STD "/root", 0, obj ); /* set the above filter node as the input */ oyConversion_Set( conversion, in, 0 ); /* set the image buffer */ oyFilterNode_SetData( in, (oyStruct_s*)image_in, 0, 0 ); /* add a scale node */ out = oyFilterNode_NewWith( "//" OY_TYPE_STD "/scale", 0, obj ); options = oyFilterNode_GetOptions( out, OY_SELECT_FILTER ); /* scale factor from DB */ option = oyOption_FromRegistration( OY_INTERNAL "/scale/scale", 0 ); error = oyOption_SetFromText( option, 0, 0 ); error = oyOption_SetValueFromDB( option ); scale = 1.0; if(!error) { sv = oyOption_GetValueString( option, 0 ); if(sv) scale = strtod( sv, 0 ); } oyOption_Release( &option ); error = oyOptions_SetFromDouble( &options, OY_INTERNAL "/scale/scale", scale, 0, OY_CREATE_NEW ); oyOptions_Release( &options ); /* append the node */ error = oyFilterNode_Connect( in, "//" OY_TYPE_STD "/data", out, "//" OY_TYPE_STD "/data", 0 ); if(error > 0) fprintf( stderr, "could not add filter: %s\n", "//" OY_TYPE_STD "/scale" ); in = out; /* add a expose node */ out = oyFilterNode_NewWith( "//" OY_TYPE_STD "/expose", 0, obj ); options = oyFilterNode_GetOptions( out, OY_SELECT_FILTER ); /* expose factor */ error = oyOptions_SetFromDouble( &options, "//" OY_TYPE_STD "/expose/expose", 1.0, 0, OY_CREATE_NEW ); oyOptions_Release( &options ); /* append the node */ error = oyFilterNode_Connect( in, "//" OY_TYPE_STD "/data", out, "//" OY_TYPE_STD "/data", 0 ); if(error > 0) fprintf( stderr, "could not add filter: %s\n", "//" OY_TYPE_STD "/expose" ); in = out; /* add a channel node */ out = oyFilterNode_NewWith( "//" OY_TYPE_STD "/channel", 0, obj ); options = oyFilterNode_GetOptions( out, OY_SELECT_FILTER ); /* channel option*/ error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "/channel/channel", "", OY_CREATE_NEW ); oyOptions_Release( &options ); /* append the node */ error = oyFilterNode_Connect( in, "//" OY_TYPE_STD "/data", out, "//" OY_TYPE_STD "/data", 0 ); if(error > 0) fprintf( stderr, "could not add filter: %s\n", "//" OY_TYPE_STD "/channel" ); in = out; /* create a new filter node */ { icc = out = oyFilterNode_FromOptions( OY_CMM_STD, "//" OY_TYPE_STD "/icc_color", cc_options, NULL ); /* append the new to the previous one */ error = oyFilterNode_Connect( in, "//" OY_TYPE_STD "/data", out, "//" OY_TYPE_STD "/data", 0 ); if(error > 0) fprintf( stderr, "could not add filter: %s\n", OY_CMM_STD ); /* Set the image to the first/only socket of the filter node. * oyFilterNode_Connect() has now no chance to copy it it the other nodes. * We rely on resolving the image later. */ error = oyFilterNode_SetData( out, (oyStruct_s*)image_out, 0, 0 ); if(error != 0) fprintf( stderr, "could not add data\n" ); } /* swap in and out */ if(out) in = out; /* create a node for preparing the image for displaying */ { out = oyFilterNode_NewWith( "//" OY_TYPE_STD "/display", 0, obj ); options = oyFilterNode_GetOptions( out, OY_SELECT_FILTER ); /* data type for display */ error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/display/datatype", data_type, 0, OY_CREATE_NEW ); /* alpha might be support once by FLTK? */ error = oyOptions_SetFromInt( &options, "//" OY_TYPE_STD "/display/preserve_alpha", 1, 0, OY_CREATE_NEW ); oyOptions_Release( &options ); /* append the node */ error = oyFilterNode_Connect( in, "//" OY_TYPE_STD "/data", out, "//" OY_TYPE_STD "/data", 0 ); if(error > 0) fprintf( stderr, "could not add filter: %s\n", "//" OY_TYPE_STD "/display" ); oyFilterNode_SetData( out, (oyStruct_s*)image_out, 0, 0 ); in = out; } /* add a closing node */ out = oyFilterNode_NewWith( "//" OY_TYPE_STD "/output", 0, obj ); error = oyFilterNode_Connect( in, "//" OY_TYPE_STD "/data", out, "//" OY_TYPE_STD "/data", 0 ); if(error > 0) fprintf( stderr, "could not add filter: %s\n", "//" OY_TYPE_STD "/output" ); /* set the output node of the conversion */ oyConversion_Set( conversion, 0, out ); /* apply policies */ /*error = oyOptions_SetFromText( &options, "//" OY_TYPE_STD "//verbose", "true", OY_CREATE_NEW );*/ oyConversion_Correct( conversion, "//" OY_TYPE_STD "/icc_color", flags, options ); oyOptions_Release( &options ); if(cc_node) *cc_node = icc; return conversion; }
/** Function oyDrawScreenImage * @brief generate a Oyranos image from a given context for display * * The function asks the 'oydi' node to provide parameters to render a * oyImage_s from a prepared oyConversion_s context. * * @param[in] context the Oyranos graph * @param[in,out] ticket rendering context for tracking * rectangles * @param[in] display_rectangle absolute coordinates of visible image * in relation to display * @param[in,out] old_display_rectangle * rembering of display_rectangle + @param[in,out] old_roi_rectangle remembering of ticket's ROI (optional) * @param[in] system_type the system dependent type specification * - "X11" is well supported * - "oy-test" for internal tests * @param[in] data_type_request oyUINT8 or oyUINT16 * @param[in] display the system display with system_type: * - "X11": a Display object * @param[in] window the system window with system_type: * - "X11": a Window ID * @param[in] dirty explicite redraw * @param[out] image the image from graph to display * @return 0 - success, -1 - issue, >= 1 - error * * @version Oyranos: 0.9.6 * @date 2016/09/22 * @since 2010/09/05 (Oyranos: 0.1.11) */ int oyDrawScreenImage ( oyConversion_s * context, oyPixelAccess_s * ticket, oyRectangle_s * display_rectangle, oyRectangle_s * old_display_rectangle, oyRectangle_s * old_roi_rectangle, const char * system_type, oyDATATYPE_e data_type_request, void * display, void * window, int dirty, oyImage_s * image ) { int result = 0; if(context) { double X,Y,W,H; int channels = 0; oyFilterNode_s * node_out = 0; oyRectangle_s * disp_rectangle = 0, * ticket_roi = 0; oyOptions_s * image_tags = 0; oyDATATYPE_e data_type = oyUINT8; oyPixel_t pt = 0; oyRectangle_GetGeo( display_rectangle, &X, &Y, &W, &H ); if(!image) return 1; if( W <= 0 || H <= 0) return -1; image_tags = oyImage_GetTags( image ); if(window && strcmp("X11", system_type) == 0) { #if defined(XCM_HAVE_X11) /* add X11 window and display identifiers to output image */ oyOption_s * o = 0; Display *disp = (Display*) display; Window w = (Window) window; int count = oyOptions_CountType( image_tags, "//" OY_TYPE_STD "/display/window_id", oyOBJECT_BLOB_S ); if(!count && w) { oyBlob_s * win_id = oyBlob_New(0), * display_id = oyBlob_New(0); if(win_id) { oyBlob_SetFromStatic( win_id, (oyPointer)w, 0, 0 ); o = oyOption_FromRegistration( "//" OY_TYPE_STD "/display/window_id", 0 ); oyOption_MoveInStruct( o, (oyStruct_s**)&win_id ); oyOptions_MoveIn( image_tags, &o, -1 ); oyBlob_SetFromStatic( display_id, (oyPointer)disp, 0, 0 ); o = oyOption_FromRegistration( "//" OY_TYPE_STD "/display/display_id", 0 ); oyOption_MoveInStruct( o, (oyStruct_s**)&display_id ); oyOptions_MoveIn( image_tags, &o, -1 ); oyOptions_SetFromText( &image_tags, "//" OY_TYPE_STD "/display/display_name", DisplayString(disp), OY_CREATE_NEW ); } else printf("%s:%d WARNING: no X11 Window obtained or\n" " no oyBlob_s allocateable\n", __FILE__,__LINE__); } #endif } else if(strcmp("oy-test", system_type) == 0) oyOptions_SetFromText( &image_tags, "//" OY_TYPE_STD "/display/display_name", system_type, OY_CREATE_NEW ); /* check if the actual data can be displayed */ pt = oyImage_GetPixelLayout( image, oyLAYOUT ); data_type = oyToDataType_m( pt ); channels = oyToChannels_m( pt ); if(pt != 0 && ((channels != 4 && channels != 3) || data_type != data_type_request)) { printf( "%s:%d WARNING: wrong image data format: %s\n%s\n" "need 4 or 3 channels with %s\n", __FILE__,__LINE__, oyOptions_FindString( image_tags, "filename", 0 ), image ? oyObject_GetName( image->oy_, oyNAME_NICK ) : "", oyDataTypeToText( data_type_request ) ); return 1; } /* Inform about the images display coverage. */ disp_rectangle = (oyRectangle_s*) oyOptions_GetType( image_tags, -1, "display_rectangle", oyOBJECT_RECTANGLE_S ); oyRectangle_SetGeo( disp_rectangle, X,Y,W,H ); node_out = oyConversion_GetNode( context, OY_OUTPUT ); ticket_roi = oyPixelAccess_GetArrayROI( ticket ); /* decide wether to refresh the cached rectangle of our static image */ if( node_out && /* Did the window area move? */ ((!oyRectangle_IsEqual( disp_rectangle, old_display_rectangle ) || /* Something explicite to update? */ (old_roi_rectangle && !oyRectangle_IsEqual( ticket_roi, old_roi_rectangle ))|| /* Did the image move? */ oyPixelAccess_GetStart( ticket,0 ) != oyPixelAccess_GetOldStart( ticket,0 ) || oyPixelAccess_GetStart( ticket,1 ) != oyPixelAccess_GetOldStart( ticket,1 )) || dirty > 0)) { #ifdef DEBUG_ printf( "%s:%d new display rectangle: %s +%d+%d\n", __FILE__,__LINE__, oyRectangle_Show(disp_rectangle), X, Y ), #endif /* convert the image data */ oyConversion_RunPixels( context, ticket ); if(oy_debug && getenv("OY_DEBUG_WRITE")) { oyImage_s * out = oyConversion_GetImage( context, OY_OUTPUT ); oyImage_WritePPM( out, "debug_image_out.ppm", "image_display output image"); oyImage_Release( &out ); } /* remember the old rectangle */ oyRectangle_SetByRectangle( old_display_rectangle, disp_rectangle ); oyRectangle_SetByRectangle( old_roi_rectangle, ticket_roi ); oyPixelAccess_SetOldStart(ticket,0, oyPixelAccess_GetStart(ticket,0)); oyPixelAccess_SetOldStart(ticket,1, oyPixelAccess_GetStart(ticket,1)); } else result = -1; oyFilterNode_Release( &node_out ); oyOptions_Release( &image_tags ); oyRectangle_Release( &disp_rectangle ); oyRectangle_Release( &ticket_roi ); } if(oy_debug >= 4) fprintf( stderr, "%s:%d %s() result: %d\n", strrchr(__FILE__,'/'),__LINE__,__func__, result ); return result; }
/** @brief implement oyCMMFilter_GetNext_f() * * @version Oyranos: 0.9.6 * @date 2016/04/04 * @since 2013/06/10 (Oyranos: 0.9.5) */ int oyraFilter_ImageExposeRun ( oyFilterPlug_s * requestor_plug, oyPixelAccess_s * ticket ) { int result = 0, error = 0; oyFilterSocket_s * socket = 0; oyFilterNode_s * input_node = 0, * node = 0; oyFilterPlug_s * plug = 0; oyImage_s * image = 0; int dirty = 0; socket = oyFilterPlug_GetSocket( requestor_plug ); node = oyFilterSocket_GetNode( socket ); image = (oyImage_s*)oyFilterSocket_GetData( socket ); if(!image) { result = 1; goto clean_expose1; } if(oy_debug) oyra_msg( oyMSG_WARN, (oyStruct_s*)ticket, OY_DBG_FORMAT_ "image [%d](%d)\n",OY_DBG_ARGS_,oyStruct_GetId((oyStruct_s*)image),oyImage_GetWidth(image) ); { oyRectangle_s * ticket_roi = oyPixelAccess_GetArrayROI( ticket ); double expose = 1.0; oyOptions_s * node_opts = oyFilterNode_GetOptions( node, 0 ); if(!node_opts) dirty = 1; if(dirty) { result = dirty; goto clean_expose2; } plug = oyFilterNode_GetPlug( node, 0 ); /* select node */ input_node = oyFilterNode_GetPlugNode( node, 0 ); /* find filters own expose factor */ error = oyOptions_FindDouble( node_opts, "//" OY_TYPE_STD "/expose/expose", 0, &expose ); if(error) WARNc2_S("%s %d", _("found issues"),error); if(oy_debug > 2) oyra_msg( oyMSG_WARN, (oyStruct_s*)ticket, OY_DBG_FORMAT_ "%s expose: %f",OY_DBG_ARGS_, oyPixelAccess_Show(ticket), expose); if(expose != 1.0) { oyImage_s * output_image = oyPixelAccess_GetOutputImage( ticket ); oyArray2d_s * array_out = oyPixelAccess_GetArray( ticket ); oyProfile_s * p = oyImage_GetProfile( output_image ); icColorSpaceSignature sig = oyProfile_GetSignature( p, oySIGNATURE_COLOR_SPACE ); int layout_dst = oyImage_GetPixelLayout( output_image, oyLAYOUT ); int channels_dst = oyToChannels_m( layout_dst ); int byte_swap = oyToByteswap_m( layout_dst ); int ticket_array_pix_width; /* avoid division by zero */ if(!channels_dst) channels_dst = 1; ticket_array_pix_width = oyArray2d_GetWidth( array_out ) / channels_dst; { int w,h,x,y, i, start_x,start_y; unsigned int max = 1; oyRectangle_s * ticket_roi = oyPixelAccess_GetArrayROI( ticket ); oyRectangle_s_ roi_= {oyOBJECT_RECTANGLE_S,0,0,0, 0,0,0,0}; oyRectangle_s * roi = (oyRectangle_s*)&roi_; uint8_t ** array_out_data; /* get pixel layout infos for copying */ oyDATATYPE_e data_type_out = oyToDataType_m( layout_dst ); int bps_out = oyDataTypeGetSize( data_type_out ); /* get the source pixels */ result = oyFilterNode_Run( input_node, plug, ticket ); /* get the channel buffers */ array_out_data = oyArray2d_GetData( array_out ); w = oyArray2d_GetWidth( array_out ) / channels_dst; h = oyArray2d_GetHeight( array_out ); oyRectangle_SetByRectangle( roi, ticket_roi ); oyRectangle_Scale( roi, ticket_array_pix_width ); start_x = OY_ROUND(roi_.x); start_y = OY_ROUND(roi_.y); switch(data_type_out) { case oyUINT8: max = 255; break; case oyUINT16: max = 65535; break; case oyUINT32: max = UINT32_MAX; break; default: break; } /* expose the samples */ #if defined(USE_OPENMP) #pragma omp parallel for private(x,y,i) #endif for(y = start_y; y < h; ++y) { for(x = start_x; x < w; ++x) { if( (sig == icSigRgbData || sig == icSigXYZData || sig == icSigLabData || sig == icSigYCbCrData) && channels_dst >= 3) { double rgb[3], v; for(i = 0; i < 3; ++i) { switch(data_type_out) { case oyUINT8: rgb[i] = array_out_data[y][x*channels_dst*bps_out + i*bps_out]; break; case oyUINT16: { uint16_t v = *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]); if(byte_swap) v = oyByteSwapUInt16(v); rgb[i] = v; } break; case oyUINT32: { uint32_t v = *((uint32_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]); if(byte_swap) v = oyByteSwapUInt32(v); rgb[i] = v; } break; case oyHALF: v = *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]); rgb[i] = v; break; case oyFLOAT: v = *((float*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]); rgb[i] = v; break; case oyDOUBLE: v = *((double*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]); rgb[i] = v; break; } } oySensibleClip ( rgb, sig, max, expose ); for(i = 0; i < 3; ++i) { v = rgb[i]; switch(data_type_out) { case oyUINT8: array_out_data[y][x*channels_dst*bps_out + i*bps_out] = v; break; case oyUINT16: { uint16_t u16 = v; *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) = byte_swap ? oyByteSwapUInt16(u16) : u16; } break; case oyUINT32: { uint32_t u32 = v; *((uint32_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) = byte_swap ? oyByteSwapUInt16(u32) : u32; } break; case oyHALF: *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) = v; break; case oyFLOAT: *((float*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) = v; break; case oyDOUBLE: *((double*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) = v; break; } } } else for(i = 0; i < channels_dst; ++i) { int v; switch(data_type_out) { case oyUINT8: v = array_out_data[y][x*channels_dst*bps_out + i*bps_out] * expose; if(v > 255) v = 255; array_out_data[y][x*channels_dst*bps_out + i*bps_out] = v; break; case oyUINT16: v = *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]); if(byte_swap) v = oyByteSwapUInt16(v); v *= expose; if(v > 65535) v = 65535; *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) = byte_swap ? oyByteSwapUInt16(v) : v; break; case oyUINT32: *((uint32_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) *= expose; break; case oyHALF: *((uint16_t*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) *= expose; break; case oyFLOAT: *((float*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) *= expose; break; case oyDOUBLE: *((double*)&array_out_data[y][x*channels_dst*bps_out + i*bps_out]) *= expose; break; } } } } } oyArray2d_Release( &array_out ); oyImage_Release( &output_image ); oyProfile_Release( &p ); } else /* expose == 1.0 */ { result = oyFilterNode_Run( input_node, plug, ticket ); } clean_expose2: oyOptions_Release( &node_opts ); oyFilterPlug_Release( &plug ); oyRectangle_Release( &ticket_roi ); oyFilterNode_Release( &input_node ); } clean_expose1: oyImage_Release( &image ); oyFilterSocket_Release( &socket ); oyFilterNode_Release( &node ); return result; }
void ColorContext::setupColorLookupTable(bool advanced) { kDebug() << m_outputName; oyProfile_s *dummyProfile = 0; oyOptions_s *options = 0; if (!m_dstProfile) m_dstProfile = dummyProfile = oyProfile_FromStd(oyASSUMED_WEB, icc_profile_flags, 0); /* skip dummyProfile to dummyProfile conversion */ if (!m_srcProfile && dummyProfile) { if (dummyProfile) oyProfile_Release(&dummyProfile); return; } if (!m_srcProfile) { m_srcProfile = oyProfile_FromStd(oyASSUMED_WEB, icc_profile_flags, 0); if (!m_srcProfile) { kError() << "Output" << m_outputName << ":" << "no assumed dummyProfile source profile"; kWarning() << "Output" << m_outputName << "using dummy clut"; buildDummyClut(m_clut); return; } } int error = 0; int flags = 0; // Optionally set advanced options from Oyranos if (advanced) flags = oyOPTIONATTRIBUTE_ADVANCED; // Allocate memory for clut data m_clut.resize(CLUT_ELEMENT_COUNT); kDebug() << "Color conversion for" << m_outputName << "flags" << flags << (advanced ? "advanced" : ""); oyImage_s *imageIn = oyImage_Create( LUT_GRID_POINTS, LUT_GRID_POINTS * LUT_GRID_POINTS, m_clut.data(), OY_TYPE_123_16, m_srcProfile, 0); oyImage_s *imageOut = oyImage_Create( LUT_GRID_POINTS, LUT_GRID_POINTS * LUT_GRID_POINTS, m_clut.data(), OY_TYPE_123_16, m_dstProfile, 0); oyConversion_s *conversion = oyConversion_CreateBasicPixels(imageIn, imageOut, options, 0); if (!conversion) { kWarning() << "No conversion created for" << m_outputName; if (dummyProfile) oyProfile_Release(&dummyProfile); return; } oyOptions_Release(&options); error = oyOptions_SetFromText(&options, "//"OY_TYPE_STD"/config/display_mode", "1", OY_CREATE_NEW); if (error) { kWarning() << "Oy options error:" << error; if (dummyProfile) oyProfile_Release(&dummyProfile); return; } error = oyConversion_Correct(conversion, "//"OY_TYPE_STD"/icc", flags, options); if (error) { kWarning() << "Failed to correct conversion for" << m_outputName << "flags" << flags; if (dummyProfile) oyProfile_Release(&dummyProfile); return; } oyFilterGraph_s *conversionGraph = oyConversion_GetGraph(conversion); oyFilterNode_s *iccNode = oyFilterGraph_GetNode(conversionGraph, -1, "///icc", 0); // See what to search for in the cache QByteArray entryText; const char *t = oyFilterNode_GetText(iccNode, oyNAME_NAME); if (t) entryText = t; oyStructList_s *cache = Display::getInstance()->cache(); oyHash_s *entry = oyStructList_GetHash(cache, 0, entryText.constData()); oyArray2d_s *oyClut = (oyArray2d_s*) oyHash_GetPointer(entry, oyOBJECT_ARRAY2D_S); char ** array2d = (char**)oyArray2d_GetData( oyClut ); oyFilterNode_Release(&iccNode); oyFilterGraph_Release(&conversionGraph); if (oyClut) { // Found in cache kDebug() << "clut" << oyClut << "obtained from cache using entry" << entryText; memcpy(m_clut.data(), array2d[0], CLUT_DATA_SIZE); } else { kDebug() << "clut not found in cache using entry" << entryText << ", doing conversion"; // Create dummy / identity clut data for conversion input buildDummyClut(m_clut); // Do conversion error = oyConversion_RunPixels(conversion, 0); if (error) { kWarning() << "Output" << m_outputName << "Error" << error << "in conversion run pixels"; if (dummyProfile) oyProfile_Release(&dummyProfile); return; } // Save to cache oyClut = oyArray2d_Create( NULL, LUT_GRID_POINTS * 3, LUT_GRID_POINTS * LUT_GRID_POINTS, oyUINT16, NULL); array2d = (char**)oyArray2d_GetData( oyClut ); memcpy(array2d[0], m_clut.data(), CLUT_DATA_SIZE); oyHash_SetPointer(entry, (oyStruct_s*) oyClut); } oyOptions_Release(&options); oyImage_Release(&imageIn); oyImage_Release(&imageOut); oyConversion_Release(&conversion); if (!m_dstProfile) kDebug() << "Output" << m_outputName << "no profile"; }