Create gradient map in sass - algorithm

I'm trying to generate a LCH gradient map with 2 gradients in SASS, where red-0 is super white red, red-1000 is super red, and red-2000 is super black red:
$colors: (
red-0: #FCF5F5,
red-100: #FFE2E2,
red-200: #FFCFCD,
red-300: #FFBCB8,
red-400: #FFA9A3,
red-500: #FF958C,
red-600: #FF8175,
red-700: #FF6C5E,
red-800: #FF5545,
red-900: #FF3A2B,
red-1000: #FC0A0A,
red-1100: #E60013,
red-1200: #D00017,
red-1300: #BA0019,
red-1400: #A4001A,
red-1500: #8F0019,
red-1600: #790118,
red-1700: #640316,
red-1800: #500512,
red-1900: #3C060C,
red-2000: #2A0303
);
Is there a way to generate this with an algorithm?

Related

QML: add border to free form image

I have a free form image with transparency (let's say, a small image of a blue car). The image has transparency, so that I can place the car on the map of a game.
Now, some areas of the game map are bluish, and the car kinda blends in. Is it possible to add a white border automatically in QML? I can't use GIMP or other things to work directly on the image (and I have lots of such images to manipulate) so it would be awesome if there was a QML builtin functionality for this...
In situations like this, a drop shadow is a good way of making an item standout. You normally would make it black or white based on the opposite of the average gray level of the image content itself.
It's pretty easy to add a DropShadow to an Image. This example places a nice light black drop shadow onto an image.
import QtGraphicalEffects 1.0
Image {
source: "my_image.png"
layer.enabled: true
layer.effect: DropShadow {
verticalOffset: 3
horizontalOffset: 0
radius: 8
color: "#26000000"
}
}
For more info see: https://doc.qt.io/qt-5/qml-qtgraphicaleffects-dropshadow.html
If you want a centered box shadow instead, just use a Rectangle somewhat like this:
Rectangle {
layer.enabled: true
layer.effect: DropShadow {
radius: 8
color: "#26000000"
}
Image {
source: "my_image.png"
}
}
Or if you just want a white border only:
Rectangle {
color: "transparent"
border.color: "white"
border.width: 2
Image {
source: "my_image.png"
}
}

Why does SASS Saturation color function results in different value from Mac color picker?

I'm using SASS HSL color functions to get individual values from HEX color. At the same time I'm entering the same HEX value into Mac color picker. But the resulting saturation value from SASS color function and Mac color picker are different. Why is that?
Here's the SASS code with the results:
$color: #3e8fcb;
#debug $color;
#debug 'Hue' round( hue($color) );
#debug "Sat" round( saturation($color) );
#debug "Lht" round( lightness($color) );
And here's the Mac color picker:
As you can see the's the difference in saturation:
SASS: 58%
Mac color picker: 69%
Why?
That's because SASS color functions use HSL color model, while Mac color picker uses HSB (same as HSV) color model. In HSB and HSL the Hue is the same, but Saturation takes a different value.
Explained in this answer:
HSB vs HSL vs HSV
And in Wikipedia:
https://en.wikipedia.org/wiki/HSL_and_HSV

how to reference a property inside of a map object

I have a map of colors, and would like to define subsequent colors in the map based on colors defined earlier within the map.
$colors: (
primary: #184770,
secondary: #0969A2,
white: #fff,
black: #000,
green: #24b206,
blue: #428bca,
purple: #813c8e,
grey: (lighten( black, 25%)),
grey-light: (lighten( black, 35%)),
grey-dark: (lighten( black, 15%))
);
I would like to specify grey, grey-light and grey-dark based on map-get($colors, black).
The example above works only because it references inherent color "black" rather than map-get($colors, black)
Can you reference a property inside the same map object?
No, you cannot reference a map's property inside the same map object. The map is not truly defined until the semi-colon is reached, so before that point, its own properties are unavailable to refer to. Here's a similar existing question and answer.
If you want to add subsequent values based on initially defined values, one route is with a combination of the map-get and map-merge functions:
$base-colors: (
black: #000
);
$extended-colors: (
grey: lighten(map-get($base-colors, black), 25%),
grey-light: lighten(map-get($base-colors, black), 35%),
grey-dark: lighten(map-get($base-colors, black), 15%)
);
$colors: map-merge($base-colors, $extended-colors);
Note: map-merge performs a shallow merge that is best for flat one-dimensional maps; if you are dealing with merging deeper multidimensional maps, you may want to define and use a recursive function rather than map-merge.

How do I change an image (icon's) color in css

I have some images representing icons that consists of blue signs and transparent background. I display them using css:
.icon {
background: rgba(0, 0, 0, 0) url("images/icons/my-icon.png") no-repeat scroll 5px center;
}
My icon looks like this one: https://cdn2.iconfinder.com/data/icons/large-svg-icons-part-3/512/zoom_search_find_magnifying_glass-256.png
I want to be able to change the color of the blue using css. I tried to use CSS3's filter function.
The idea is that I have the hex code and I transform it to RGB and later HSL (hue, saturation and luminance). In the end I'll have for each color a value between 0 and 360 (a degree). See for example this image: http://lodev.org/cgtutor/images/hslhuecircle.jpg .
I'm using this filter function:
filter: hue-rotate(220deg) saturate(100);
Where 220deg is the int value of the hue. So the hue (initially a float value) aproximated up is 220.
Take example red: #ff0000
The hue details are:
array(4) {
["hue"]=>
int(0)
["saturation"]=>
int(100)
["luminance"]=>
float(50)
["degrees"]=>
int(0)
}
So the css becomes:
.icon {
background: rgba(0, 0, 0, 0) url("images/icons/my-icon.png") no-repeat scroll 5px center;
filter: hue-rotate(0deg) saturate(100);
}
But in this case, the blue becomes #9AF8FF (which is not red).
In order to obtain red, I should use:
filter: hue-rotate(195deg) saturate(100);
The hue-rotate values can be between 0 and 360, just like degrees. In my case the results are inversed, instead of obtaining red for 0degrees, I obtain the value that can be find on the following image at 195 degrees: http://lodev.org/cgtutor/images/hslhuecircle.jpg .
Is there any css filter or other solution that can help me to change the image color using css? I played with other CSS3 filters but I couldn't change the color to the desired one.
I have an application where users can select the desired color, the only problem is with existing image icons.
Any help will be great, anticipate thanks!
When I wrote the question I found a possible solution. In my case, the results were reversed.
For red, #ff0000 I obtained 0 degrees. I realized that with css3's filter hue-rotate, the red is not at 0, but it starts at 180. So for each hue/degree value that I obtain, I add 180. In this way, I can obtain the desired color.
After this change, the hsl:
array(4) {
["hue"]=>
int(0)
["saturation"]=>
int(100)
["luminance"]=>
float(50)
["degrees"]=>
int(0)
}
become:
array(4) {
["hue"]=>
int(180)
["saturation"]=>
int(100)
["luminance"]=>
float(50)
["degrees"]=>
int(180)
}
I tried it for green and other colors and it works well. If you have a better idea to change the image color with CSS, one that doesn't use the filter function "hue-rotate", I'll be glad to hear about it.
EDIT
I found the solution.
1) I'm using the solution explained above (I add 180 to my degrees).
2) I'm using brightness filter also
So My filter looks like:
filter: hue-rotate(350deg) saturate(100) brightness(1);
This filter changes the icon's color to this color: #00FFFF .
So the solution work 100%. I'm sending color code and brightness and I dynamically calculate the filter values. For darker colors use a lower value for brightness (under 0.5) and for brighter colors use values above 0.5.

Displaying background colour through transparent PNG on material?

I'm making a case builder using THREE.js, the basics are i want to be able to change the height/width/length of a box, rotate it around, and also change the background color of the box.
This is it so far:
http://design365hosting.co.uk/casebuilder3D/
The dimension changing works, as does the dragging of the box, now i'm working with the background color change.
The way i want this to work is by using transparent PNGs as the faces of the box, and setting background colors so that this background colour shows through the transparent PNG.
This is how I'm currently doing it:
var texture = THREE.ImageUtils.loadTexture("images/crate.png");
materials.push(new THREE.MeshBasicMaterial({color:0xFF0000, map: texture}));
as you can see I set the material to have a background colour of red and overlay the transparent PNG, problem is, three.js seems to ignore the background colour and just show the transparent PNG, meaning no colour shows through.
The expected result should be a red box with the overlayed PNG.
Hope that made sense, can anyone help?
You are trying to apply your transparent texture as a decal.
The three.js built-in materials do not support what you are trying to do. If the PNG is partially transparent, then the material will be partially transparent.
You would like the material to remain opaque, and the texture to be applied as a decal.
You can do this by modifying the material's shader. For example,
var material = new THREE.MeshPhongMaterial( {
color: 0x0080ff,
map: texture
} );
material.onBeforeCompile = function ( shader ) {
const custom_map_fragment = THREE.ShaderChunk.map_fragment.replace(
`diffuseColor *= sampledDiffuseColor;`,
`diffuseColor = vec4( mix( diffuse, sampledDiffuseColor.rgb, sampledDiffuseColor.a ), opacity );`
);
shader.fragmentShader = shader.fragmentShader.replace( '#include <map_fragment>', custom_map_fragment );
};
three.js r.147

Resources