PHP Color Manipulation - php

I am currently looking into color manipulation / selection etc and have come across the following piece of code. I was wondering of someone could tell me what the following piece of code is doing and break it down for me thanks!
$newVal = round(round(($rgb['red'] / 0x33)) * 0x33);
In particluar what is the 0x33
Thanks in adavnce

It seems to be converting $rgb['red'] the nearest multiple of 0x33.
It's probably doing that so the color will end up on the so-called "web safe" color palette, which (if I recall correctly) consists of colors who's rgb values are multiples of 0x33.
0x33 is the base-16 (hex) representation of 51 (decimal).

0x33 is 51, so it scales the 0-255 value of a single byte to 0-5, and then scales it back out. This results in the value being floored to the highest multiple of 51 lower than the value.

0x33 is just hex value for 33.
I'm not really sure what is happening, but my guess would be it calculates a web safe hex of any color. Or something along these lines.

As #Seth indicated, it's rounding colours to the nearest 'web-safe' colour. It's an old idea, dating from back when most colour displays were 8-bit. One of the people to make it popular was Visibone as their 'websafe colour chart' was their first product.
See Web Colours for more information.

Related

PHP and creating hex or RGB codes for colours as dark as base colour

I'm using PHP and I would like to create an array with colour codes. My base colour's hex code is #16A7B4 (red 180, green 22, and blue 111). I want all colours to be as dark as the base color #16A7B4, but other colours must be different enough that I can see that there are several colours. In other words, it is not allowed that the colours look too similar.
In other words, colours like #164EB4 and #38B416 would be OK, because they are not too similar with #16A7B4. But colour #B41668 is too similar with the base colour.
My problem is that I have no idea how to do this. I can add the base colour to an array, but that is all I can do. I do not know how I could calcute more colour codes which are as dark as the base color but not too similar with it.
I need 100 different colour codes (RGB or hex). Any ideas?

Functions that calculate distance between HEX colors and eliminate colours too similar

I have a simple PHP function that generates the hexadecimal value for HTML colors and insert them in a db.
Considering an array of hexadecimal values extracted from the db, how can I modify this function to avoid generating a color similar to the others?
There are many definitions of the similarity of colours. You might be looking for similar hue, or similar brightness.
For these purposes, perhaps the simplest is to take the euclidian distance between the two points in RGB space, that is:
sqrt(pow($r1 - $r0, 2) + pow($g1 - $g0, 2) + pow($b1 - $b0, 2));
and reject those where that value is too small (e.g. 10?)

Calculating color shades

I have the next problem.
I have a base color with couple of different shades of that color.
Example:
Base color: #4085c5
Shade: #005cb1
Now, I have a different color (let's say #d60620), but no shades of it. From the color I would like to calculate shades, that have similar difference as colors mentioned in first paragraph.
First I tried calculating difference of RGB elements and applying them to second color, but the result was not like I expected to be.
Than I tried with converting color to HSV, reading saturation value and applying the difference to second color, but again the resulting color was still weird.
The formula was something like: (HSV(BaseColor)[S] - HSV(Shade)[S]) + HSV(SecondColor)[H]
Does anyone know how this problem could be solved? I know I am doing something wrong, but I don't know what. :)
There are two ways to darken a color:
Subtract an equal amount from R,G,B. This increases the saturation. Obviously you can only subtract an mount equal to the least of the R,G,B values.
Multiply R,G,B by a value less than 1.0. This leaves the saturation more or less intact.
Similarly, there are two ways to lighten a color:
Add an equal amount to R,G,B. This decreases the saturation.
Multiply R,G,B by a value greater than 1.0. This increases the vividness of the color and thus the apparent saturation.
Your example appears to have done both - subtracting 0x40 from each value and multiplying by 1.33.
Using your second color, we can subtract 06 from each resulting in #d0000a but this is not dark enough. Multiplying it by 0.735 results in #990013.
Your first two colours both have a "H" (hue) value of 209, and varying values for "S" and "V".
This common hue is what defines the second colour as being a "shade" of the first colour.
To find alternative shades of your third colour, use an RGB to HSV conversion to find its hue, modify its S and V values as desired, and then convert back to RGB.

How to convert artbitrary number to rgb color?

I have an application that has about one hundred users. We have a calender view in which every user can have multiple entries. Every entry of the same user should have the same color, but different users should have different colors. At the moment we have manually defined about 25 colors in an array, and the color a user gets is determined by
$color = $colors[$userid % count($colors)];
We don't want to manually add colors for every new user, and selecting a color for each user seems a bit tedious too.
Is there a simple function to map a number (the users id) to a color (preferably RGB)? The next question that rises is; Is there a way to limit the function to a certain types of colors (ie. only colors in which white letters are readable)?
I don't have a solution, per se, but a suggestion.
First, since you want each user's colors to be unique but random, you could get started with some kind of numerical hash function. That gets you a random number that's most likely unique. if your hash function is decent and your users are in the hundreds that should suffice.
Now you need to turn that into colors, preferably on the dark end of the spectrum. If you go with RGB, You need three numbers. To keep them dark, lets say you keep the total or R, G and B under 200. That's a guess, of course, but it should be pretty dark. Pick a random number [index] between 1 and 3 - that's the R, G or B you're going to start with. Get a number between 0 and 200, and set record it for color[index1]. Now pick one of the remaining indexes, 1-3. For this, pick a number between 0 and color[index1] that you already have. Set the remaining number to 200-color[index1]-color[index2]. Now you have a randomish RGB value that should contrast with white.
I realize I never got much use from that hash function up front - maybe ditch it and just use the userid as a random(seed).
You want to work in the hue-saturation-lightness or hue-saturation-value (HSL or HSV) space.
http://en.wikipedia.org/wiki/HSL_and_HSV
Start by defining some colors based on hue and saturation, and set the lightness to the highest tolerable level that makes the text readable.
Then you can fix the hue and saturation for these colors and decrease the lightness.
So say you started by choosing 25 tolerable colors with different hues and maximum/minimum tolerable lightness.
To generate a color for an index you pick the base color to start with base = id % 25 You then decrease the luminance depending on the index within that color index = (Math.floor(id/25)). Set the luminance somewhere within the tolerable luminance range based on that value. So let's say we will have 5 luminance values per color, set the luminance to
lightness = maxLightness - index*(maxLightness / 4*minLightness)
This simply varies the lightness for each color. You can choose to vary saturation and hue slightly if you would prefer. Converting between HSV and RGB is a well documented procedure.
PHP HSV to RGB formula comprehension

sorting images by color

I'm looking for a way to sort images as in the following screenshot:
http://www.pixolution.de/sites/LargeImages_en.html
I've looked at all the threads on this topic on stackoverflow but none of the proposed solutions even come close to giving me the image above.
Approaches I've tried:
for each image, build histogram of rgb colors in descending order of occurrence
for each histogram, calculate a distance from black (r:0,g:0,b:0) as follows:
for color in image_histogram:
total_distance += color.percentage_of_image * distance(BLACK_RGB, color.rgb)
then sort images by their distances
I was hoping that images of similar color distribution would end up with a similar distance and result in a visual ordering by color. This was not the case, it seems to somewhat work but not like in the image above.
For the distance function, I've tried euclidean distance, hsv sorting (h->s->v) and even Lab distance sorting. None of which has helped
If anyone has a better approach, I would love to know!
I've never done something like this myself, so forgive me if the following approach is naive:
For each image, boil it down to 1 average RGB value by summing the R, G, B values of all pixels, and divide by the total # pixels. Normalize the components to [0..1]
Plot the image in your 2D color space based on the RGB values. This can be a 2D projection of a 3D (r, g, b) vector transformation.
you could convert to HSV and sort by H
Hue is what most people think of when they think "color"
see: RGB to HSV in PHP
Group similar colors using the distance between them and not between them and black, and use the average color in the image.
You might want to check out ImagePlot. I'm not sure if the algorithms behind the system are available, but you can certainly download and run your image collection through the free software to analyze them.
This software is used in many interesting visualizations of massive image collections, millions+
Info: http://lab.softwarestudies.com/p/imageplot.html#whatsnew
Source: https://github.com/culturevis/imageplot

Categories