[go: up one dir, main page]

Menu

Git Merge Request #53: Add an option (in preferences dialog) to convert embedded profiles to sRGB (open)

Merging...

Merged

Something went wrong. Please, merge manually

Checking if merge is possible...

Something went wrong. Please, merge manually

Jellby wants to merge 5 commits from /u/jellby/mcomix/ to master, 7 hours ago

This implements the suggestion in #137. Unfortunately, I don't know how to do it with GdkPixbuf, so when the preference is enabled I switch the priority to PIL. Ugly but effective: it works nicely for me.

Commit Date  
[a68cfb] (srgb) by Jellby Jellby

Revert "Try to fix random failure to restore window geometry"

This reverts commit e89aa4478f9f39794aa13530a44876f4a15ece2f.

2025-10-21 16:50:32 Tree
[e89aa4] by Jellby Jellby

Try to fix random failure to restore window geometry

2025-10-19 07:37:29 Tree
[aa0272] by Jellby Jellby

Move preference to a new tab

2025-10-19 07:36:12 Tree
[02bb5a] by Jellby Jellby

Refresh images when toggling convert to sRGB and workaround for animations

2025-10-18 14:11:03 Tree
[52a5b0] by Jellby Jellby

Add an option for converting embedded color profiles to sRGB

Implements #137 (Support CMYK and color profile conversion)

2025-10-14 17:33:16 Tree

Discussion

  • Ark

    Ark - 2025-10-16

    Thank you for your MR, I will have a look into it.

     
  • Ark

    Ark - 6 days ago

    I am sorry for the delay. Your MR looks like a good starting point for proper color management in MComix. You seem knowledgeable when it comes to Pillow and color management in general, so it would be great if you could help us here.

    I tested your MR a bit and, apparently, toggling the checkbox does not seem to work. Normally, when changing a setting in the prefs, the change is applied immediately. (To work around this issue with the current MR, re-caching images appears to be the minimum necessary for the change to be applied.) I think this is because the conversion happens in load_pixbuf. Could you please try and move the conversion step to somewhere later so the conversion can be applied even after the images have been loaded and cached? If this seems impossible or unreasonable, you might find another (or even better!) way to fix it.

    For some reason, when conversion is enabled, any AVIF file becomes undisplayable. Not sure whether it's only on my system (Arch Linux), though.

    The conversion also has the side effect of un-animating any animated image like GIF. Similar issues are already known which is why MComix does not transform animated images if animation is enabled in the prefs. Please have a look at main.py:393 and lens.py:148 (current master) as examples of how is_animation in image_tools.py is used to determine whether an image is considered animated.

     
  • Jellby

    Jellby - 6 days ago

    Thanks for the feedback. Unfortunately, no, I'm not knowledgeable in either Pillow or color management... I mean, I know enough to figure out that some CMYK images are displayed wrong, track it down to images with embedded profiles and find a way to apply/use the profile "on the fly" without re-encoding the image. But I still don't understand color profiles and their quirks. I'm not even sure "convert to sRGB" is right, since sRGB is a colorspace and not a profile. I'm quite lost here. Still, for my problem images applying this hack is better than nothing.

    Right, the checkbox does not work "live", you have to refresh to have it take effect. On the other hand, if you assign a keyboard shortcut it will refresh automatically. I can try to make it refresh when (un)checking the preference too. But I don't think I can do the correction later, I think it must be done before converting PIL.Image to GdkPixbuf.Pixbuf, since the profile is available in the former and not the latter.

    The other problem regarding AVIF, is it maybe due to changing the provider priority? As I mentioned, I had to change it to try PIL first, otherwise the images are loaded directly with GdkPixbuf and color profile is not available (as far as I can see). I'll try to find a solution/workaround, and for the animations too.

     

    Last edit: Jellby 6 days ago
  • Jellby

    Jellby - 6 days ago

    Is it better now? Animations should now work as before (i.e. profile conversion is not available for animations), and toggling the preference should refresh all images. AVIF images do not work for me (Kubuntu 24.04) no matter what, so I cannot test that. Although they work with Gwenview and ImageMagick, so maybe it's just some Python module.

     
  • Ark

    Ark - 6 days ago

    I'm having a look at it. By the way, the current MR still points to the previous commit. Not sure whether you can update the MR, but you probably should (if you can, that is).

     
  • Ark

    Ark - 6 days ago

    Unfortunately, no, I'm not knowledgeable in either Pillow or color management...

    Under those circumstances, your code looks quite impressive!

    I mean, I know enough to figure out that some CMYK images are displayed wrong, track it down to images with embedded profiles and find a way to apply/use the profile "on the fly" without re-encoding the image.

    I see.

    But I still don't understand color profiles and their quirks.

    I am not an expert on that, either, more like an intermediate, but if we combine our understandings, we might be able to get that thing right enough.

    I'm not even sure "convert to sRGB" is right, since sRGB is a colorspace and not a profile. I'm quite lost here.

    Crash course (to the best of my knowledge and with simplifications here and there): Profiles, for the most part, describe a color space by means of some profile connection space (PCS), usually XYZ. As in, "the most luminous reddest red in the color space described here has the XYZ coordinates so-and-so". The most luminous reddest red of one monitor might look totally different (read: has totally different XYZ coordinates) from the reddest red of another. And by "look" I mean according to what a colorimeter (a device that is, essentially, an "objective human eye") has measured. When you profile a monitor, you measure not just the "corners" but many, many points in the color space of the monitor in question because the monitor might have some nonlinearities/surprises here and there. (Think of it as if someone took a hammer to make dents in what would otherwise be a nicely defined, three-dimensional grid.) Profiles can also contain metadata and VCGT data and whatnot, so there are many ways to create essentially broken profiles. On the other hand, there are standardized color spaces like sRGB where the most luminous reddest red has a certain XYZ coordinate by definition. So, for this to work in practice, a CMS can create a synthetic profile on the fly (or has them predefined and cached somewhere), and that synthetic profile describes how the sRGB color space looks like, for example. Thanks to relatively simple definitions, such a standardized color space doesn't have unexpected dents like real devices so a profile that describes it is comparatively small. Most users are even lazier: They do not include a profile at all in their images. For these cases (which is, like, most of the media out there), software like mpv uses heuristics. For example, if the spatial dimensions of a video are 1920x1080, it matches the definition made in BT.709, so the correct color space is probably also defined in BT.709. Using this educated guess, mpv creates a synthetic profile that describes the same color space as defined in BT.709, and uses it as if it had been embedded in the video. Now, with a profile of the input (device, video or image) and a profile of the output device (e. g., a monitor) and a common PCS like XYZ, color (as essentially defined in standards like CIE 1931) can be translated from the input to XYZ and then from XYZ to the output. But wait, what if the user doesn't have a profile for his monitor (good profiles need good colorimeters, which are expensive, after all!), you might ask. Good question! In this case, we can only use heuristics, again. Easiest way out: Since many images still use mere sRGB, just assume that the output device is also perfectly calibrated to match sRGB. (This is not true in many real cases, by the way, as many devices sold today with "better" color reproduction are closer to DCI-P3 or Display P3, for example, and many cheaper devices are only somewhat similar to sRGB but have terribly yellowish red.) This way, color translation is trivial. As in, the user doesn't have a monitor profile, so he probably doesn't care, so we don't care, either! But if we encounter images with radically different definitions like CMYK-based ones, we can now at least do something to get the colors a bit closer to what was intended by the artist. Speaking of intent, the "rendering intent" loosely describes how to bias the color mapping so you can keep what you want from a color that is outside of what your output device can handle ("out of gamut"), like trading saturation for correct hue etc. (You currently use magic constants for that but it would be better to have a drop-down menu for it as well.)

    tl;dr We need a drop-down menu instead of a check box, and we most certainly need a new pref tab labeled "Color Management" where said drop-down menus should appear. More on that later, but if you want, you can already help here by temporarily moving the new option to such a new tab.

    Still, for my problem images applying this hack is better than nothing.

    Definitely. I have a few CMYK-based images myself so I know exactly what you mean.

    I can try to make it refresh when (un)checking the preference too. But I don't think I can do the correction later, I think it must be done before converting PIL.Image to GdkPixbuf.Pixbuf, since the profile is available in the former and not the latter.

    Is it better now? Animations should now work as before (i.e. profile conversion is not available for animations), and toggling the preference should refresh all images.

    The other problem regarding AVIF, is it maybe due to changing the provider priority? As I mentioned, I had to change it to try PIL first, otherwise the images are loaded directly with GdkPixbuf and color profile is not available (as far as I can see). I'll try to find a solution/workaround, and for the animations too.

    Yes, thanks. I think the way you handle this particular issue in the currently most-recent draft is probably good enough, even AVIF works again.

    AVIF images do not work for me (Kubuntu 24.04) no matter what, so I cannot test that. Although they work with Gwenview and ImageMagick, so maybe it's just some Python module.

    Thanks for the info. I would like to help you here but for me, it just works and I can't name a package that you might need for AVIF to work.

    By the way, for experimentation, testing and learning about color management in practice, you might want to have a look at the colord package which comes with files like SwappedRedAndGreen.icc so when you use it in mpv, you can enjoy acid trips for free!

     

    Last edit: Ark 6 days ago
  • Jellby

    Jellby - 6 days ago

    Thanks for the crash course. The intent, and to some extent the math, is relatively clear, but when it comes to when and how each profile should (or actually is) taken into account, I have the impression it's the wild west, and each program/library does whatever.

    I have put the preference in a new tab. For what it's worth, Gwenview has, as far as I can see, only two related settings: enable/disable color management, and select rendering intent (perceptual/relative colorimetric).

    I've also added a trial fix for an annoyance I've been having, where the window geometry fails to be restored apparently at random. If this is not OK I can remove it or create a separate MR.

     

    Last edit: Jellby 6 days ago
  • Jellby

    Jellby - 5 days ago

    I've figured out how to read an embedded profile from a pixbuf, so I'll try to rewrite this.

     
  • Ark

    Ark - 4 days ago

    Thanks for the crash course. The intent, and to some extent the math, is relatively clear,

    So we are on the same page, which is good.

    but when it comes to when and how each profile should (or actually is) taken into account, I have the impression it's the wild west, and each program/library does whatever.

    Also on the same page, unfortunately. :-(

    I have put the preference in a new tab.

    Thanks. My experience tells me that there are several different aspects of real-world scenarios to consider:

    1. Some monitors are used with an appropriate profile, others aren't. Automatic monitor profile detection should be the default but the user must be able to disable it. There should always be a fallback profile selected like sRGB or Display P3.
    2. Most images just assume sRGB without having a suitable profile embedded. This is an issue if the display has a wide gamut and the image in question shows a natural scene taken with a cam, as the result will look over-saturated. However, an image created by a naïve artist (← in a scientific sense, not a pejorative one) right for his own screen can look fine and might even look better on the wide-gamut display. For this reason, for images without a profile, the user should be able to choose whether a chosen profile like sRGB should be assigned or whether color management should be disabled altogether.
    3. I have seen cases where few images were released with a CMYK profile among other related images by the same artist that have been converted to sRGB. In a collection of such images, every single CMYK image stands out like a sore thumb. To make them match the other images, they should be converted to sRGB on the fly such that they will then be processed further as if they always had been sRGB images (similar to soft proofing).
    4. On the other hand, if the entire work of several pages is released as CMYK images (for example, a comic book), there are two meaningful ways to enjoy it: Either converted directly to the color space of the display (so you get most of the colors) or converted to the color space of some print medium (paper) first and then converted to the color space of the monitor (so it looks as if printed on paper, which might have been the originally targeted medium all along). And if you like really fancy stuff, you could select the soft-proofing profile automatically depending on properties like whether an image is monochrome or not. Manga, for example, feature few colored pages which are printed on coated paper while the bulk is printed in black only on uncoated paper. (If I understand this correctly, that is.) But this is probably too extreme, and few users would mind having their favorite manga printed on virtual coated paper.
    5. Then, there are artists using wide-gamut RGB displays to create works supposed to be viewed on similar devices. In those cases, relative-colorimetric conversion might work better than perceptual (which would probably work better for natural photography), and the appropriate profiles are usually embedded.
    6. And then, there is HDR. I have close to no experience with HDR stuff but the man page of mpv indicates that it's complicated. If HDR will ever be supported by MComix, related settings should probably go to the "Color Management" tab as well.

    So, in order to cover many use cases without user interaction reasonably well, there should be several settings with reasonable defaults. I try to conceptualize how the content of the "Color Management" tab could look like to achieve that.

    For what it's worth, Gwenview has, as far as I can see, only two related settings: enable/disable color management, and select rendering intent (perceptual/relative colorimetric).

    Without having checked the code, I guess that they either determine the monitor's profile (with sRGB as a fallback) and map everything to its color space (assuming sRGB where there is no input profile) or leave everything to the Wayland compositor (color management is a thing there since relatively recently, after all). Perceptual and relative colorimetric are the most reasonable choices as well. Looks like a good compromise if you want to keep things simple.

    So, I opened a CMYK file in Gwenview and, as it turns out, the advertised conversion to sRGB only seems to work for RGB files. That being said, mpv only supports RGB profiles, and there is at least one CMYK file where GIMP segfaults when I try to open it. In other words, MComix is (thanks to your contribution!) currently the only application I know of where I can view certain image files in a meaningful way close to the artistic intent.

    I've also a trial fix for an annoyance I've been having, where the window geometry fails to be restored apparently at random. If this is not OK I can remove it or create a separate MR.

    Is that bug related to this MR? Did that behavior occur before any of the changes in this MR?

    I've figured out how to read an embedded profile from a pixbuf, so I'll try to rewrite this.

    Great, looking forward to it!

     
  • Jellby

    Jellby - 4 days ago

    I've figured out how to read an embedded profile from a pixbuf, so I'll try to rewrite this.

    Great, looking forward to it!

    I'm afraid it won't work. Yes, I can read a profile from a pixbuf created directly from file, and yes, I can also make sure that the profile is preserved when converting a PIL image to a pixbuf. But GdkPixbuf does not support CMYK, it only supports RGB (https://docs.gtk.org/gdk-pixbuf/property.Pixbuf.colorspace.html), and a JPG (or anything else, I assume) is probably converted to RGB (ignoring any profile) when read, so that the embedded CMYK profile is now quite useless. It may work for RGB images, but I'd rather not have separate code paths for CMYK and RGB images. It might also be possible to create some pseudo-profile transformation that simulates the effect of a proper profile conversion when applied to a pre-converted-to-RGB image, but that would never be the same, and I don't think it's worth it.

    So, I think we'll have to live with the hack of changing the priority of the two providers. Or maybe PIL should always be the default provider. And given that image enhancements are applied by converting pixbuf to PIL and back to pixbuf, maybe the conversion to pixbuf could be done later?

     

    Last edit: Jellby 4 days ago
  • Jellby

    Jellby - 4 days ago

    I've also a trial fix for an annoyance I've been having, where the window geometry fails to be restored apparently at random. If this is not OK I can remove it or create a separate MR.

    Is that bug related to this MR? Did that behavior occur before any of the changes in this MR?

    As far as I can see it's unrelated to this MR and it did occur before the changes (but I didn't experience it as much as now that I've been opening/closing MComix multiple times...) The change is so small (basically just resizing before show()) that I thought it would be OK to just include it in this MR.

     
  • Ark

    Ark - 4 days ago

    I'm afraid it won't work.

    No problem, and thank you for trying.

    So, I think we'll have to live with hack of changing the priority of the two providers. Or maybe PIL should always be the default provider. And given that image enhancements are applied by converting pixbuf to PIL and back to pixbuf, maybe the conversion to pixbuf could be done later?

    I would not mind using PIL first, given that it seems more powerful in so many ways. The only real downside I see is how (currently) the conversion to Pixbuf takes place, but that's due to a completely unrelated issue. (The issue is, instead of only converting what is actually needed for the current viewport, the entire image is first converted to a Pixbuf, if necessary, and then, the entire Pixbuf is rendered and kept in memory using the final dimensions after scaling. This becomes more and more an issue, not only memory-wise. Avoiding the PIL detour wherever possible hopefully helps a bit regarding memory. A long time ago, I rewrote the core of lens.py in a way that only the relevant portions of an image are processed but I didn't find the time to generalize it for the entire viewport.)

    By the way, another related question is how to overcome the limitations regarding animated images. Currently, all animated images are loaded using Pixbuf's capabilities only. Just the other day, I stumbled on something that might help solving that issue: https://pillow.readthedocs.io/en/stable/reference/ImageSequence.html#extracting-frames-from-an-animation Thus, if you find a way to load animated images in PIL directly, not only would color management and more become available for animations, but we could finally get rid of one of the two main reasons why the Pixbuf stuff is more or less preferred for loading images. (The other reason is the memory issue explained above.)

    With that out of the way, PIL would be, at least feature-wise, clearly the preferred way to load and process images. Also, probably, fewer hoops to jump through in the image loading code (think your newly-introduced IMAGEIO_PIL_NOANIM). Or higher compatibility with more or broken images. That is, if an image can only be loaded via Pixbuf, stuff like color profiles might not be available, but at least there would be an image at all.

    Anyway, what I want to say is that, if animation could be loaded using PIL only, images could be stored in-memory using PIL stuff only, while Pixbuf stuff would only be necessary to interface with GTK. Like, everything could be so much simpler, color management included!

    As far as I can see it's unrelated to this MR

    Okay, then please move that part to a separate MR. Also, you might want to update the ChangeLog.md in the new MR if you think your change is worth mentioning.

     
  • Jellby

    Jellby - 3 days ago

    I've figured out how to read an embedded profile from a pixbuf

    For the record (in case this becomes useful in the future), this is how I could read the profile:

    pixbuf = GdkPixbuf.Pixbuf.new_from_file(path)
    icc = pixbuf.get_options().get('icc-profile', None)
    if icc is not None:
        icc = ImageCms.ImageCmsProfile(BytesIO(base64.b64decode(icc)))
    

    and to preserve the profile when coverting a PIL image to a pixbuf:

    icc = image.info.get('icc_profile', None)
    if icc:
        pixbuf.set_option('icc-profile', base64.b64encode(icc))
    

    Anyway, what I want to say is that, if animation could be loaded using PIL only

    At least animations can be detected (image.is_animated), and the separate frames can be read (image.seek()). I don't know if that's enough, one would at least also need to know the delay, and maybe something else.

    Okay, then please move that part to a separate MR.

    Done. Should I add more changes here? Should I squash commits?

     
  • Ark

    Ark - 3 days ago

    Thanks for your animation experiments. According to https://github.com/python-pillow/Pillow/commit/f84684931d3e3ec0c9f6e1ff263fe7e51ee24013 , if I understand it correctly, a frame has a dict-like memberinfo with maybe a key duration. Maybe that helps understanding how the animation stuff in PIL works.

    If you feel like improving the image loading algorithm of MComix such that PIL can be used as an additional provider for animated images. that would be great! Also, it should probably go to its own MR. I think that for now, it is okay to convert the PIL-provided animation to Pixbuf right after loading if doing so is easier to implement.

    Should I squash commits?

    Please try to remove the commits regarding window geometry as they are essentially covered in the other MR I have merged just recently.

    Should I add more changes here?

    More on the current MR here will follow in another post.

     
  • Ark

    Ark - 1 day ago

    Motivated by the scenarios described earlier, I would like to specify how I think color management should be controlled by the user. Let me first define some hypothetical GUI elements just so we can express this concisely. (How they will be implemented exactly is not important at this point.)

    • A profile selector (PS) lets the user select between predefined profiles like "sRGB", indirectly defined profiles like "use default" or "use embedded" profile, and explicitly selected (ICC) profiles stored in a file (by providing a path to that file). Depending on context, a profile might be selected for assignment, (final) conversion or immediate conversion (think soft-proofing). Note: The naming in PIL regarding soft-proofing is a bit confusing for our use case, see https://pypi.org/project/pillow/2.4.0/ and search for "softproofing" (without quotes).
    • A rendering intent selector (RIS) lets the user select any of the default rendering intents (RI) ("relative colorimetric", "absolute colorimetric", "perceptual", "saturation"), each of them optionally combined with "blackpoint compensation" (BPC). Not every combination is theoretically meaningful (for example, perceptual RI always implies BPC), but from what I have read, it might make a difference if broken profiles are involved.

    Now for the settings and their defaults with (hopefully) obvious semantics:

    "Default output profile"

    • "Try to use the system monitor profile" (← I copied this phrase straight from GIMP, by the way.) check box: (default: enabled)
    • "Fallback profile" PS: "sRGB" (default), path

    "If embedded profile is RGB"

    • input PS: "turn off color management", "use embedded" (default), "assign sRGB", path

    "If embedded profile is CMYK"

    • input PS: "turn off color management", "use embedded" (default), path

    "If embedded profile is of other type"

    • input PS: "turn off color management", "use embedded" (default), path

    "If embedded profile is unavailable"

    • input PS: "turn off color management", "assign sRGB" (default), path

    Each of the four cases above should also have the following four options as well:

    • intermediate conversion PS: "do not convert" (default), "sRGB", path
    • intermediate conversion RIS: (default: perceptual)
    • output PS: "use default" (default), "assign default" (i.e. do not convert any further), "sRGB", path
    • output RIS: (default: perceptual)

    The defaults presented here are chosen based in the idea that there are two kinds of users. Users who don't care too much about colors probably also do not have a valid profile for their monitor installed, so everything will get converted to sRGB, including CMYK. Whether the colors are actually sRGB or not (e.g. oversaturated, probably) is not important because the users don't care too much anyway. On the other hand, users who do care about colors know what color management is, probably have a display profile installed and look up the prefs either spontaneously or when they notice that the colors are unexpectedly off (for example because some CMYK images look different from other images that should look the same but don't because they are not CMYK but actually sRGB). The defaults chosen are supposed to cover most cases for most users, color enthusiasts or not.

    Given the many scenarios I described earlier, I think that being merely able to enable or disable sRGB conversion is not sufficient. Imagine some user with a profiled Adobe RGB display, maybe an artist. CMYK images could be displayed nearly perfectly on such a device but no matter what the user does, it's going to be bad. If the box is unchecked, the colors are virtually useless. If the box is checked, the resulting image on the screen is, strictly speaking, not in sRGB but in some over-saturated sRGB-to-Adobe-RGB-stretched color space because the display profile is not taken into account, which is bad as well. And even if the profile is taken into account, having everything converted to actual sRGB on the screen is going to suck as well because then, CMYK images and even the images created by the artist herself in Adobe RGB will be converted to sRGB which will completely take the fun out of the picture. Literally.

    Some manual switching might always be necessary, but I think it can be kept close to a minimum. The idea is to introduce something that could be called a color management "preset" that represents a combination of all the color management settings. For example, the defaults presented above could be called the "Default" preset. A preset "sRGB" could be used when everything needs to be converted to sRGB, and so on. A current preset that is not saved might be called "(current)". The user can add and remove her own presets and name them appropriately (like "Photography", "Artistic", "Print", "Monitor 1", "Monitor 2", "Projector", etc.). Then, when viewing images, the user can switch between presets using something like a drop-down list in the toolbar or keyboard shortcuts.

    And there is where I think a shortcut like the one you proposed (or at least made provision for) comes into play. However, instead of toggling only one setting between two states, two shortcuts would allow iterating over all possible presets.

    I am aware of the fact that this is more difficult than a checkbox hack, but at the end, it might be worth it. It would make viewing different images of very different kinds a pleasant experience. Also, not everything needs to be implemented at once. For example, the whole preset stuff can be added later.

    What do you think? Any ideas, comments, suggestions?

    By the way, I just checked and, apparently, Firefox also does not (yet) convert CMYK to RGB.

    Another issue that just came to my mind: How to apply color management to PDF files? Maybe MuPDF has some options for that. Needs checking, but that's for later.

     
  • Jellby

    Jellby - 1 day ago

    What do you think? Any ideas, comments, suggestions?

    It sounds reasonable, The main drawback from my perspective is that I have no way of testing if whatever I implement (if you're asking me to implement it) is correct or not. I mean, I just used this ImageCms module to do something that seems sensible and that looks on my screen similar to what e.g. Gimp shows, but I don't know if it's taking into account my monitor profile (if any), or if it's clipping stuff that needn't be clipped, or something like that. The "easy" part, that is adding preferences for default target profile or rendering intent, that I can do.

    By the way, I just checked and, apparently, Firefox also does not (yet) convert CMYK to RGB.

    Hmmm... It converts to RGB, at least it displays my test images with oversaturated but "right" colors, unlike ImageMagick's display, which apparently just maps C->R, M->G, Y->B. It does not use the embedded profile though (I don't know if it uses any other profile, I guess it just does CMYK-to-RBG with some hard-coded formula, and anything else would be applied after). See https://stackoverflow.com/questions/79322180/converting-a-cmyk-jpeg-to-rgb/79322257 and https://bugzilla.mozilla.org/show_bug.cgi?id=1989218 (there is hope).

     
  • Ark

    Ark - 1 day ago

    (Note: Assuming Arch and Xorg here. Not sure about Wayland but displaycal does not work properly when doing stuff with a colorimeter via xwayland. At least it used to be that way, not sure how things are today.)

    • If monitor profile detection needs to be tested, use dispwin -I profile.icc (package argyllcms) to set the monitor profile. If successful, xprop -len 14 -root _ICC_PROFILE (package xorg-xprop) has something meaningful to say. There is an experimental function in PIL that detects a monitor profile (but I can't remember where it is right now). Use dispwin -U -c to undo the monitor profile installation.
    • You can try using other profiles included in package colord. If you want to create your own profiles, launch displaycal (package displaycal which also depends on argyllcms since it is mostly a GUI frontend for it) and go to Tools → Advanced → Create synthetic ICC profile. It can't create CMYK profiles, though.
    • By the way, displaycal/argyllcms is like the ultimate display calibration and profiling tool out there! It took me a while to get used to it, as it is clearly for advanced users, but the correctness, reliability and precision of the results beat virtually every commercial tool out there, according to reviews I read. Also, a good colorimeter was one of the best things I ever bought for my computer. Every display sucks unless properly (optionally) calibrated and profiled!

    The main drawback from my perspective is that I have no way of testing if whatever I implement (if you're asking me to implement it) is correct or not. I mean, I just used this ImageCms module to do something that seems sensible and that looks on my screen similar to what e.g. Gimp shows, but I don't know if it's taking into account my monitor profile (if any), or if it's clipping stuff that needn't be clipped, or something like that.

    I recommend using the aforementioned SwappedRedAndGreen.icc (package colord) for testing so you can see whether it is doing anything at all. As for details like BPC, I think that currently, we do not need to worry about it. Just write code that makes sense according to the documentation, and when in doubt, leave the testing to me.

    By the way, in case you need details about embedded profiles, iccdump -s image.jpg (package colord) might help.

    The "easy" part, that is adding preferences for default target profile or rendering intent, that I can do.

    Any help is welcome. :-) But I need to come up with a more concrete idea for the GUI first. Right now, I'm thinking of doing away with the "Color management" tab and replace it with a new window similar to the "Edit external commands" dialog, as it already features a lot of the functionality we need as well …

    Hmmm... It converts to RGB, at least it displays my test images with oversaturated but "right" colors

    Oh, I see. My bad. I wanted to say that the conversion does not even try understanding that CMYK is very different from RGB.

    It does not use the embedded profile though (I don't know if it uses any other profile, I guess it just does CMYK-to-RBG with some hard-coded formula, and anything else would be applied after).

    You might be right, who knows.

    See https://stackoverflow.com/questions/79322180/converting-a-cmyk-jpeg-to-rgb/79322257 and https://bugzilla.mozilla.org/show_bug.cgi?id=1989218 (there is hope).

    The first link is very helpful, thanks! As for the second link … well, we must get it done before they do!!

     
  • Ark

    Ark - 7 hours ago

    Okay, I think I have a quite concrete idea now. Also, I figured that the whole thing will be too big to fit into the normal prefs window so I think a separate window will probably be better. And since the "Edit external commands" window already features quite a lot of what we need for the design I propose here, I think it is be better to copy it, even though it means that the parts relevant for presets management will be there first. Also, this way, there is no need for a "(current)" preset.

    So, if it counts as "easy", please try the following below. The explanations given there are mostly for later, so no need to implement everything perfectly right away. A mock-up should be good enough to get an impresson first.

    1. Create a copy of the "Edit external commands" dialog and name the copy "Edit color management presets" (or maybe "Color management presets"?). The settings will be stored in the preferences.conf with key "color management presets". The details need to be discussed later. Make the new dialog accessible in some way.
    2. Make the table at the top feature the following columns from left to right:
      • "Built-in": check box, read-only, indicates whether the preset is built-in and, therefore, cannot be removed, renamed or have its CM settings changed. Preliminary.
      • "Listed": check box, controls whether the preset will be listed in a drop-down menu (or similar) to the user in the main window.
      • "Cycle": check box, controls whether the preset can be cycled through using keyboard shortcuts. For consistency reasons, if this box is checked, the "Listed" box must be checked as well.
      • "Label": text field
    3. Add a "Copy" button to the button row. Place it somewhere before the "Remove" button.
    4. Implement a PS by means of an drop-down list with features similar to the "Monitor profile" drop-down list in Preferences → Color Management in GIMP, i. e. some fixed items with special values at the top, then some items previously chosen by the user, and finally a "Select profile from file" entry that opens a file chooser and, if a file has been successfully chosen, adds an entry to the list of previously chosen items.
    5. Add a "Default output profile" section as outlined earlier, using the PS you just implemented.
    6. Add a grid of components structured like the following, along with a label that works as a section header:
    If embedded profile is RGB -----------------
    Input                     PS         Preview
    Intermediate conversion   PS   RIS   Preview
    Output conversion         PS   RIS   Preview
    

    The "Preview" is some kind of test image that demonstrates how colors (RGB, CMY, white, black and near-black) look like when put under the influence of the settings next to it (so the user can tell how a setting influences the result at various stages). If a conversion fails (for example, because of incompatibilities), a warning sign might appear instead. Not sure whether this can easily be implemented, but since it will be more of a gimmick than a necessity, we might just as well drop it.

    Then, create copies of this grid for all the other cases ("CMYK", "other", "unavailable"). Actually, that should be done later because we first need to test and discuss whether something like that grid is usable at all. I just mention it here just to remind us of the fact that the grid will appear three more times.

    If you have issues or you think you have a better idea, or comments, whatever, just let me know.

     

Log in to post a comment.