Science Kid
Science Kid

Reputation: 1

Photoshop API color normalization gives wrong hex code

Photoshop API gives text layer as follows

{
    "blendOptions": {
        "blendMode": "normal",
        "opacity": 100
    },
    "bounds": {
        "height": 179,
        "left": 536,
        "top": 56,
        "width": 176
    },
    "id": 25,
    "index": 17,
    "locked": false,
    "name": "Curved text with hint <TPH>",
    "rotate": 0,
    "text": {
        "characterStyles": [
            {
                "fontAvailable": true,
                "fontColor": {
                    "rgb": {
                        "blue": 23383,
                        "green": 17251,
                        "red": 1306
                    }
                },
                "fontName": "ArialMT",
                "fontSize": 24,
                "orientation": "horizontal"
            }
        ],
        "content": "Type your text here * Type your text here",
        "frameType": "onCurve",
        "paragraphStyles": [
            {
                "alignment": "center"
            }
        ]
    },
    "type": "textLayer",
    "visible": true
}

I am converting the rgb to hex code as follows:

rgb_values = {
  "blue": 23383,
  "green": 17251,
  "red": 1306
}

def normalize_and_convert_to_hex(rgb_values):
    red = round((rgb_values["red"] / 65536) * 255)
    green = round((rgb_values["green"] / 65536) * 255)
    blue = round((rgb_values["blue"] / 65536) * 255)
    return f"#{red:02x}{green:02x}{blue:02x}"

x = normalize_and_convert_to_hex(rgb_values)
print(x)

The above Python code gives the hex as: #05435B

The hex code in Photoshop is different: #0A86B6
Check: Image of Photoshop color picker

Is my normalization wrong or the color from the Photoshop API wrong?

Upvotes: -1

Views: 45

Answers (1)

VC.One
VC.One

Reputation: 15926

Short version: Multiply each channel's conversion result by 2.

Example: red = round( (1306 / 65536) * 255 ) * 2
Should give you a result that matches Photoshop's red of hex 0A (or decimal 10).

Why is it happening?:
It seems you are not accounting for the bit-depth (or number of bytes that the original color occupies per channel). Since you have numbers like 23383 it means your bit-depth is 16 bits (or better said as "is using 2 bytes").

Edit: It seems you simply just have to multiply by 2. The bit-depth does not matter for this situation (of 16-bit values). In any case, the logic below is valid for any 8-bit and 16-bit colours.

Therefore to get a correct answer (matches Photoshop) you must calculate as:

rgb_values = {
  "blue": 23383,
  "green": 17251,
  "red": 1306
}

# num_bytes = 1;    ## if using 0-255 range eg: max of [0xFF] per channel
num_bytes = 2;      ## if using 0-65536 range eg: max of [0xFFFF] per channel

def normalize_and_convert_to_hex(input_rgb):
    red = round((input_rgb["red"] / 65536) * 255) * num_bytes
    green = round((input_rgb["green"] / 65536) * 255) * num_bytes
    blue = round((input_rgb["blue"] / 65536) * 255) * num_bytes
    return f"#{red:02x}{green:02x}{blue:02x}"


x = normalize_and_convert_to_hex(rgb_values)

print(x)

Upvotes: 1

Related Questions