mirror of
https://github.com/RobTillaart/Arduino.git
synced 2024-10-03 18:09:02 -04:00
0.2.0 map2colour
This commit is contained in:
parent
3cdd0e5a43
commit
c2badab145
@ -6,13 +6,24 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/)
|
||||
and this project adheres to [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
## [0.2.0] - 2023-04-24
|
||||
- add dynamic size in constructor (minimum 7 for backwards)
|
||||
- add destructor.
|
||||
- add **uint8_t size()**
|
||||
- add **m2c_colours.h** for colour constants
|
||||
- add **M2C_GRAY** constants
|
||||
- array of values now may be non-decreasing (iso increasing)
|
||||
- update readme.md
|
||||
- minor edits
|
||||
|
||||
----
|
||||
|
||||
## [0.1.6] - 2023-02-21
|
||||
- update readme.md
|
||||
- update GitHub actions
|
||||
- update license 2023
|
||||
- minor edits
|
||||
|
||||
|
||||
## [0.1.5] - 2022-10-19
|
||||
- redo **begin()** of map2colourFast to always create divFactors.
|
||||
- add compare example to compare map2colour and map2colourFast.
|
||||
|
@ -8,45 +8,57 @@
|
||||
|
||||
# map2colour
|
||||
|
||||
Arduino library for mapping a float to colour spectrum.
|
||||
Arduino library for mapping a float to a colour spectrum.
|
||||
|
||||
|
||||
## Description
|
||||
|
||||
The map2colour library is used to make map a reading from a sensor, e.g. temperature or pressure,
|
||||
to a colour in the RGB spectrum. This can be used to colour an element on a graphical display, drive an RGB LED, or even a LED string etc.
|
||||
The map2colour library is used to map a float value to a colour in the RGB spectrum.
|
||||
The float value can be the result of a calculation or read from a sensor,
|
||||
e.g. temperature, humidity, light, distance, direction or pressure.
|
||||
|
||||
The initial release uses 7 floats values that describe the range being mapped.
|
||||
These are passed to the library with **begin()**.
|
||||
These 7 floats must be in ascending order and are mapped default on the following colour array.
|
||||
This function can be used to colour an element on a graphical display,
|
||||
drive an RGB LED, or a LED string etc to indicate some sort of state visually.
|
||||
|
||||
The first releases used a fixed number of 7 floats values that describe the range being mapped.
|
||||
With version 0.2.0 one can define the size as a parameter of the constructor.
|
||||
There is no limit (except RAM) in theory, but in practice 16 or 32 entries is a lot.
|
||||
|
||||
A lookup array of float values is passed to the library with **begin()**.
|
||||
These floats must be in **non-decreasing** order and are mapped default on the following colour array.
|
||||
|
||||
```cpp
|
||||
uint32_t colours[] =
|
||||
{
|
||||
// BLACK RED YELLOW GREEN AQUA BLUE WHITE
|
||||
// M2C_BLACK M2C_RED M2C_YELLOW M2C_LIME M2C_AQUA M2C_BLUE M2C_WHITE
|
||||
0x00000000, 0x00FF0000, 0x00FFFF00, 0x0000FF00, 0x0000FFFF, 0x000000FF, 0x00FFFFFF
|
||||
}
|
||||
```
|
||||
|
||||
New values will be linear interpolated between two points when needed.
|
||||
|
||||
Assume you initialize a float array
|
||||
Assume you initialize a float value array indicating temperature Celsius levels.
|
||||
|
||||
```cpp
|
||||
float tempArray[] = { -20, -10, 5, 15, 30, 60, 125 };
|
||||
```
|
||||
A temperature of 0°C will be mapped between the 2nd and 3rd element so
|
||||
between RED and YELLOW.
|
||||
A temperature between 60°C and 125°C will be mapped between BLUE and WHITE.
|
||||
|
||||
**begin()** also allows one to overrule the colours array with a colour array of your choice.
|
||||
A temperature of 0°C will be between the 2nd and 3rd value so it will be mapped
|
||||
between the 2nd and 3rd element colour so between M2C_RED and M2C_YELLOW.
|
||||
Similarly any temperature between 60°C and 125°C will be mapped between M2C_BLUE and M2C_WHITE.
|
||||
|
||||
**begin()** allows one to overrule the values and the colours array with arrays of your choice.
|
||||
Adjusting the colour array allows one to use a "full spectrum" like the default or only
|
||||
interpolate between two colours. Note the library has several colours predefined as constant
|
||||
to make the colour table (and the code) more readable. If colours are missing please make a
|
||||
PullRequest (preferred) or file an issue.
|
||||
interpolate between two colours.
|
||||
Note the library has several colours predefined in **m2c_colours.h** as constants to make the
|
||||
colour table and therefore the code more readable.
|
||||
If colours are missing please make a PullRequest (preferred) or file an issue.
|
||||
|
||||
**begin()** returns false if the array of values is not in increasing order, true otherwise.
|
||||
**begin()** returns true if the array of values is in non-decreasing order, false otherwise.
|
||||
If returned false the code might behave in unexpected ways.
|
||||
|
||||
Please note that the colourMap can have duplicate entries even side by side.
|
||||
|
||||
|
||||
## Interface
|
||||
|
||||
@ -56,19 +68,23 @@ If returned false the code might behave in unexpected ways.
|
||||
|
||||
#### Functions
|
||||
|
||||
- **map2colour()** constructor.
|
||||
- **map2colourFast()** constructor, (larger code base, more RAM and faster)
|
||||
- **bool begin(float \* values, uint32_t \* colourMap = NULL)** load the array with **7**
|
||||
boundary values and the associated array of **7** colours packed in uint32_t **0x00RRGGBB**.
|
||||
- **map2colour(uint8_t size = 7)** constructor, default size 7 to be backwards compatible.
|
||||
- **~map2colour()** destructor.
|
||||
- **map2colourFast(uint8_t size = 7)** constructor, (larger code base, more RAM and faster)
|
||||
- **~map2colourFast()** destructor.
|
||||
- **uint8_t size()** returns the size of the arrays needed (== parameter of constructor).
|
||||
- **bool begin(float \* values, uint32_t \* colourMap = NULL)** load the array with **size**
|
||||
boundary values and the associated array of **size** colours packed in uint32_t **0x00RRGGBB**.
|
||||
If the colour array is not given the last given (or the default) colour array is used.
|
||||
**begin()** can be called multiple times to change the mapping.
|
||||
The function returns false if the array of values is not in increasing order.
|
||||
The function returns false if the array of values is not in non-decreasing order.
|
||||
- **uint32_t map2RGB(float value)** returns RGB colour packed in an uint32_t **0x00RRGGBB**.
|
||||
If the value is out of range of the original values array, the value is always mapped upon the first colour.
|
||||
If the value is out of range of the original values array, the value is always mapped upon the
|
||||
first or last colour.
|
||||
- **uint16_t map2_565(float value)** often used 16 bit colour format.
|
||||
Currently a wrapper around **map2RGB**.
|
||||
|
||||
Note: the arrays passed to **begin()** should both have at least 7 elements!
|
||||
Note: the arrays passed to **begin()** should both have **size** elements!
|
||||
|
||||
The colour array can be filled with decimal or HEX values or predefined colours can be used.
|
||||
See below.
|
||||
@ -76,7 +92,9 @@ See below.
|
||||
|
||||
## Predefined colours
|
||||
|
||||
Colours are represented as 24 bit RGB values and have the pattern **0x00RRGGBB**.
|
||||
Colours are represented as 32 bit .RGB values and have the pattern **0x00RRGGBB**.
|
||||
|
||||
In the file **m2c_colours.h** a number of colours are predefined.
|
||||
|
||||
|
||||
| define | value | define | value |
|
||||
@ -91,45 +109,72 @@ Colours are represented as 24 bit RGB values and have the pattern **0x00RRGGBB**
|
||||
| M2C_FUCHSIA | 0x00FF00FF | M2C_AQUA | 0x0000FFFF |
|
||||
|
||||
|
||||
Besides these colours, the file contains also GRAY-scale VALUES M2C_GRAY_0 .. M2C_GRAY_16.
|
||||
|
||||
More colour definitions can be found on the internet
|
||||
e.g. https://www.w3.org/wiki/CSS/Properties/color/keywords
|
||||
|
||||
Note that only 3 bytes of 4 of the 32 bit colour patterns are used.
|
||||
The 4th byte might be used in the future.
|
||||
|
||||
|
||||
|
||||
## Operation
|
||||
|
||||
See examples.
|
||||
|
||||
By changing the colour map one can get different effects.
|
||||
The minimum to implement is an intensity effect going from black towards a colour at max intensity.
|
||||
More complex colour schemes are possible, up to 7 different colours.
|
||||
This number 7 is hardcoded (for now) and that might change in the future.
|
||||
The minimum to implement is an intensity effect going e.g. from black towards a colour at max intensity.
|
||||
For this effect only two values are significant, however one must provide full size arrays.
|
||||
|
||||
```cpp
|
||||
float values[7] = { -200, 200, 200, 200, 200, 200, 200, };
|
||||
uint32_t colours[7] = { M2C_BLACK, M2C_RED, 0, 0, 0, 0, 0};
|
||||
```
|
||||
|
||||
Note that the above colour scheme maps all colokrs above 200 to BLACK (0).
|
||||
|
||||
Another interesting colour scheme could be a symmetric one.
|
||||
This could indicate 25 as an optimal value (GREEN).
|
||||
|
||||
```cpp
|
||||
float values[5] = { -50, -25, 0, 25, 50, 75, 100};
|
||||
uint32_t colours[5] = { M2C_BLACK, M2C_RED, M2C_YELLOW, M2C_GREEN, M2C_YELLOW, M2C_RED, M2C_BLACK};
|
||||
```
|
||||
|
||||
More complex colour schemes are possible, up to **size** different colours.
|
||||
|
||||
|
||||
#### Experimental in 0.1.5
|
||||
#### Non-decreasing array
|
||||
|
||||
(was planned for 0.2.0)
|
||||
(experimental in 0.1.5)
|
||||
If you create a non-decreasing array of values one can create a break in the colour gradient.
|
||||
See example.
|
||||
|
||||
```cpp
|
||||
float values[7] = { -200, -90, 0, 45, 45, 150, 180 };
|
||||
float values[7] = { -200, -90, 0, 45, 45, 150, 180 };
|
||||
uint32_t colours[7] = { M2C_BLUE, M2C_AQUA, M2C_LIME, M2C_YELLOW, M2C_RED, M2C_YELLOW, M2C_BLUE};
|
||||
```
|
||||
|
||||
With the double 45 in the values array there would be no gradient between the **M2C_YELLOW** and **M2C_RED**
|
||||
effectively having 2 continuous gradients.
|
||||
With **45** occurring twice in the values array above there would be no interpolation or colour gradient
|
||||
between the **M2C_YELLOW** and **M2C_RED** effectively resulting in 2 continuous gradients.
|
||||
|
||||
Note: **begin()** will report such array as false.
|
||||
A slightly less hard edge could be made by changing the second 45 to 46 or 47,
|
||||
so there is a small area with a very steep gradient.
|
||||
|
||||
Note: Since 0.2.0 **begin()** will accept a non-decreasing value array and return true.
|
||||
This was false in 0.1.5.
|
||||
|
||||
|
||||
## Performance
|
||||
|
||||
Indicative performance figures measured with performance example.
|
||||
Indicative performance figures measured with the performance example.
|
||||
Performance depends on colours chosen, platform etc.
|
||||
|
||||
Note: time in microseconds
|
||||
Note: UNO at 16 MHz, ESP32 at 240 MHz
|
||||
|
||||
|
||||
#### version 0.1.2
|
||||
|
||||
| function call | time UNO | time ESP32 |
|
||||
@ -152,6 +197,8 @@ Note: UNO at 16 MHz, ESP32 at 240 MHz
|
||||
|
||||
#### version 0.1.4
|
||||
|
||||
map2colourFast.
|
||||
|
||||
| function call | time UNO | time ESP32 | notes |
|
||||
|:-------------------------|------------:|-------------:|:------------------------|
|
||||
| begin(values) | 284 | 15 | unexpected peak ESP32 |
|
||||
@ -164,15 +211,29 @@ Note: UNO at 16 MHz, ESP32 at 240 MHz
|
||||
|
||||
One performance optimization (trade memory for speed) is replacing the float division
|
||||
in map2RGB by a multiplication.
|
||||
This requires 24 bytes RAM to hold the 6 factors and ~100 bytes of PROGMEM for the
|
||||
calculation of the dividers in begin().
|
||||
This optimization is implemented as a derived class **map2colourFast** in version 0.1.4.
|
||||
|
||||
This requires (size x 4) bytes RAM to hold the \[size] factors and some ~100 bytes
|
||||
of PROGMEM for the calculation of the dividers in **begin()**.
|
||||
The **map2RGB()** call is about 40 % faster compared to the original 0.1.2.
|
||||
Although the **begin()** call is ~300 us longer, it only takes a dozen **map2RGB()** calls to break even.
|
||||
|
||||
Note: the gain for the ESP32 is less pronounced, but can still be interesting.
|
||||
|
||||
|
||||
#### version 0.2.0
|
||||
|
||||
map2colourFast, slightly slower compared to 0.1.4.
|
||||
Note that the larger the size the more time it takes to find the correct interval for the value.
|
||||
|
||||
| function call | time UNO | time ESP32 |
|
||||
|:-------------------------|------------:|-------------:|
|
||||
| begin(values) | 316 | 22 |
|
||||
| begin(values, colours) | 332 | 7 |
|
||||
| map2RGB(value) | 48 - 116 | 1 - 2 |
|
||||
| map2_565(value) | 52 - 120 | 1 - 2 |
|
||||
|
||||
|
||||
## Future
|
||||
|
||||
#### Must
|
||||
@ -181,24 +242,18 @@ Note: the gain for the ESP32 is less pronounced, but can still be interesting.
|
||||
|
||||
#### Should
|
||||
|
||||
- redo **begin()** of map2colour to allow all values. (0.2.0)
|
||||
- non-decreasing array (already experimental in 0.1.5, will still return false! )
|
||||
- any array of numbers. (return value will always be true then)
|
||||
- look for optimizations.
|
||||
- cache last value?
|
||||
|
||||
|
||||
#### Could
|
||||
|
||||
- make size configurable ?
|
||||
- at least smaller than 7 (speeds up)
|
||||
- ...
|
||||
- **void adjustColour(uint8_t index, uint32_t RGB)**
|
||||
- single colour adjust
|
||||
- faster than calling begin() again
|
||||
- divfactors need to be calculated again.
|
||||
- map2RGB variant that gives a colour to the delta with previous value
|
||||
- user can do that fairly easy => example
|
||||
- add **reset()** for default array? (RAM)
|
||||
- create a memory efficient version
|
||||
- keep a pointer to the colour array.
|
||||
- split RGB channels for every mapping.
|
||||
- is this useful? only for smallest RAM devices.
|
||||
- remove default array and break backwards compatibility.
|
||||
|
||||
|
||||
#### Wont
|
||||
|
||||
@ -206,10 +261,28 @@ Note: the gain for the ESP32 is less pronounced, but can still be interesting.
|
||||
- PROGMEM for default array? ==> slower, AVR specific.
|
||||
- move up the test for non-increase in **begin()** ==> fail fast.
|
||||
- conflicts with begin of fast version.
|
||||
- should a 4th (alpha) channel be enabled?
|
||||
- user responsibility.
|
||||
- could a 4th (alpha) channel be enabled?
|
||||
- not needed yet, would need new constants
|
||||
- faster 16 bit 565 version?
|
||||
- only on request as a separate class map2colour565.
|
||||
- map2HSL() as extra colour space.
|
||||
- not seen much HSL displays in "arduino" world
|
||||
- not seen much HSL displays in "Arduino" world
|
||||
- separate converter solves this.
|
||||
- add **reset()** for default array?
|
||||
- takes too much RAM.
|
||||
- improve the constructor
|
||||
- add **splitColorMap()**
|
||||
- only done once so too little gain.
|
||||
- map2RGB variant that gives a colour as the delta with the previous value.
|
||||
- user can do that fairly easy => example
|
||||
- add 3rd param size to **begin()** to allow smaller arrays?
|
||||
- suppose you allocate size = 20 and want to use only 5 entries.
|
||||
- create a new object.
|
||||
- **bool adjustColour(uint8_t index, uint32_t RGB)**
|
||||
- single colour adjustment
|
||||
- returns false if index out of range.
|
||||
- faster than calling **begin()**.
|
||||
- divfactors need to be calculated again?
|
||||
- see no real use case.
|
||||
|
||||
|
@ -0,0 +1,57 @@
|
||||
//
|
||||
// FILE: map2colour_dynamic.ino
|
||||
// AUTHOR: Rob Tillaart
|
||||
// PURPOSE: map2colour demo
|
||||
// URL: https://github.com/RobTillaart/map2colour
|
||||
|
||||
|
||||
#include "Arduino.h"
|
||||
#include "map2colour.h"
|
||||
|
||||
|
||||
map2colour mc(12);
|
||||
|
||||
|
||||
// must be in increasing order
|
||||
float values[12] = { 0, 33, 66, 100, 150, 200, 250, 300, 400, 600, 800, 1024 };
|
||||
|
||||
// arbitrary colors
|
||||
uint32_t colmap[12] =
|
||||
{
|
||||
M2C_BLACK, M2C_SILVER, M2C_GRAY,
|
||||
M2C_WHITE, M2C_MAROON, M2C_RED,
|
||||
M2C_PURPLE, M2C_FUCHSIA, M2C_GREEN,
|
||||
M2C_LIME, M2C_OLIVE, M2C_YELLOW
|
||||
};
|
||||
|
||||
|
||||
|
||||
void setup()
|
||||
{
|
||||
Serial.begin(115200);
|
||||
Serial.println(__FILE__);
|
||||
Serial.print("MAP2COLOUR_LIB_VERSION: ");
|
||||
Serial.println(MAP2COLOUR_LIB_VERSION);
|
||||
Serial.println();
|
||||
|
||||
// load the values array
|
||||
mc.begin(values, colmap);
|
||||
|
||||
// show the interpolating
|
||||
for (float i = 0; i < 1024; i += 10)
|
||||
{
|
||||
uint32_t rgb = mc.map2RGB(i);
|
||||
Serial.print(i);
|
||||
Serial.print("\t");
|
||||
Serial.println(rgb, HEX);
|
||||
}
|
||||
Serial.println();
|
||||
}
|
||||
|
||||
|
||||
void loop()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
// -- END OF FILE --
|
@ -0,0 +1,225 @@
|
||||
map2colour_performance.ino - map2colourFast
|
||||
|
||||
MAP2COLOUR_LIB_VERSION: 0.2.0
|
||||
|
||||
begin()
|
||||
316
|
||||
332
|
||||
|
||||
map2RGB()
|
||||
16 0.00 FF0000
|
||||
52 10.00 FF0000
|
||||
48 20.00 FF0000
|
||||
52 30.00 FF0000
|
||||
76 40.00 FF3F00
|
||||
76 50.00 FF8F00
|
||||
80 60.00 FFDF00
|
||||
116 70.00 E8FD00
|
||||
112 80.00 C3FB00
|
||||
108 90.00 9DF800
|
||||
112 100.00 78F600
|
||||
112 110.00 52F400
|
||||
116 120.00 2DF100
|
||||
112 130.00 12F000
|
||||
108 140.00 25F100
|
||||
112 150.00 38F200
|
||||
112 160.00 4BF300
|
||||
108 170.00 5DF400
|
||||
112 180.00 70F600
|
||||
112 190.00 83F700
|
||||
108 200.00 96F800
|
||||
112 210.00 A8F900
|
||||
116 220.00 BBFA00
|
||||
112 230.00 CEFB00
|
||||
116 240.00 E1FD00
|
||||
112 250.00 F3FE00
|
||||
88 260.00 FFFB00
|
||||
96 270.00 FFF100
|
||||
88 280.00 FFE700
|
||||
92 290.00 FFDD00
|
||||
88 300.00 FFD300
|
||||
92 310.00 FFC900
|
||||
88 320.00 FFBF00
|
||||
88 330.00 FFB500
|
||||
92 340.00 FFAB00
|
||||
92 350.00 FFA100
|
||||
88 360.00 FF9700
|
||||
92 370.00 FF8D00
|
||||
92 380.00 FF8300
|
||||
88 390.00 FF7900
|
||||
88 400.00 FF6F00
|
||||
88 410.00 FF6500
|
||||
92 420.00 FF5B00
|
||||
88 430.00 FF5100
|
||||
92 440.00 FF4700
|
||||
92 450.00 FF3D00
|
||||
92 460.00 FF3300
|
||||
88 470.00 FF2900
|
||||
96 480.00 FF1F00
|
||||
92 490.00 FF1500
|
||||
92 500.00 FF0B00
|
||||
96 510.00 FF0100
|
||||
72 520.00 FF0000
|
||||
72 530.00 FF0000
|
||||
72 540.00 FF0000
|
||||
72 550.00 FF0000
|
||||
72 560.00 FF0000
|
||||
76 570.00 FF0000
|
||||
72 580.00 FF0000
|
||||
72 590.00 FF0000
|
||||
72 600.00 FF0000
|
||||
76 610.00 FF0000
|
||||
72 620.00 FF0000
|
||||
72 630.00 FF0000
|
||||
72 640.00 FF0000
|
||||
76 650.00 FF0000
|
||||
72 660.00 FF0000
|
||||
76 670.00 FF0000
|
||||
72 680.00 FF0000
|
||||
72 690.00 FF0000
|
||||
72 700.00 FF0000
|
||||
72 710.00 FF0000
|
||||
72 720.00 FF0000
|
||||
76 730.00 FF0000
|
||||
72 740.00 FF0000
|
||||
72 750.00 FF0000
|
||||
72 760.00 FF0000
|
||||
72 770.00 FF0000
|
||||
72 780.00 FF0000
|
||||
76 790.00 FF0000
|
||||
76 800.00 FF0000
|
||||
76 810.00 FF0000
|
||||
72 820.00 FF0000
|
||||
72 830.00 FF0000
|
||||
72 840.00 FF0000
|
||||
72 850.00 FF0000
|
||||
76 860.00 FF0000
|
||||
76 870.00 FF0000
|
||||
76 880.00 FF0000
|
||||
76 890.00 FF0000
|
||||
72 900.00 FF0000
|
||||
72 910.00 FF0000
|
||||
76 920.00 FF0000
|
||||
72 930.00 FF0000
|
||||
76 940.00 FF0000
|
||||
76 950.00 FF0000
|
||||
72 960.00 FF0000
|
||||
76 970.00 FF0000
|
||||
72 980.00 FF0000
|
||||
76 990.00 FF0000
|
||||
72 1000.00 FF0000
|
||||
76 1010.00 FF0000
|
||||
76 1020.00 FF0000
|
||||
|
||||
TOTAL: 8636
|
||||
AVG: 83.84
|
||||
|
||||
map2_565()
|
||||
20 0.00 F800
|
||||
56 10.00 F800
|
||||
52 20.00 F800
|
||||
56 30.00 F800
|
||||
80 40.00 F9E0
|
||||
80 50.00 FC60
|
||||
80 60.00 FEE0
|
||||
120 70.00 EFE0
|
||||
112 80.00 C7C0
|
||||
112 90.00 9FC0
|
||||
116 100.00 7FA0
|
||||
112 110.00 57A0
|
||||
116 120.00 2F80
|
||||
112 130.00 1780
|
||||
112 140.00 2780
|
||||
116 150.00 3F80
|
||||
112 160.00 4F80
|
||||
112 170.00 5FA0
|
||||
112 180.00 77A0
|
||||
116 190.00 87A0
|
||||
116 200.00 97C0
|
||||
112 210.00 AFC0
|
||||
112 220.00 BFC0
|
||||
116 230.00 CFC0
|
||||
120 240.00 E7E0
|
||||
116 250.00 F7E0
|
||||
92 260.00 FFC0
|
||||
92 270.00 FF80
|
||||
92 280.00 FF20
|
||||
96 290.00 FEE0
|
||||
92 300.00 FE80
|
||||
92 310.00 FE40
|
||||
96 320.00 FDE0
|
||||
100 330.00 FDA0
|
||||
96 340.00 FD40
|
||||
96 350.00 FD00
|
||||
100 360.00 FCA0
|
||||
92 370.00 FC60
|
||||
96 380.00 FC00
|
||||
100 390.00 FBC0
|
||||
96 400.00 FB60
|
||||
92 410.00 FB20
|
||||
100 420.00 FAC0
|
||||
92 430.00 FA80
|
||||
96 440.00 FA20
|
||||
100 450.00 F9E0
|
||||
92 460.00 F980
|
||||
96 470.00 F940
|
||||
96 480.00 F8E0
|
||||
96 490.00 F8A0
|
||||
96 500.00 F840
|
||||
108 510.00 F800
|
||||
76 520.00 F800
|
||||
76 530.00 F800
|
||||
84 540.00 F800
|
||||
76 550.00 F800
|
||||
76 560.00 F800
|
||||
76 570.00 F800
|
||||
80 580.00 F800
|
||||
80 590.00 F800
|
||||
76 600.00 F800
|
||||
76 610.00 F800
|
||||
84 620.00 F800
|
||||
76 630.00 F800
|
||||
76 640.00 F800
|
||||
76 650.00 F800
|
||||
76 660.00 F800
|
||||
76 670.00 F800
|
||||
76 680.00 F800
|
||||
76 690.00 F800
|
||||
76 700.00 F800
|
||||
76 710.00 F800
|
||||
76 720.00 F800
|
||||
84 730.00 F800
|
||||
80 740.00 F800
|
||||
76 750.00 F800
|
||||
80 760.00 F800
|
||||
80 770.00 F800
|
||||
80 780.00 F800
|
||||
76 790.00 F800
|
||||
80 800.00 F800
|
||||
84 810.00 F800
|
||||
76 820.00 F800
|
||||
80 830.00 F800
|
||||
80 840.00 F800
|
||||
80 850.00 F800
|
||||
80 860.00 F800
|
||||
76 870.00 F800
|
||||
76 880.00 F800
|
||||
76 890.00 F800
|
||||
76 900.00 F800
|
||||
80 910.00 F800
|
||||
80 920.00 F800
|
||||
76 930.00 F800
|
||||
76 940.00 F800
|
||||
80 950.00 F800
|
||||
76 960.00 F800
|
||||
76 970.00 F800
|
||||
76 980.00 F800
|
||||
76 990.00 F800
|
||||
80 1000.00 F800
|
||||
80 1010.00 F800
|
||||
80 1020.00 F800
|
||||
|
||||
TOTAL: 9064
|
||||
AVG: 88.00
|
||||
|
||||
done...
|
@ -0,0 +1,48 @@
|
||||
//
|
||||
// FILE: map2colour_windys_demo.ino
|
||||
// AUTHOR: Rob Tillaart
|
||||
// PURPOSE: demo
|
||||
// URL: https://github.com/RobTillaart/map2colour
|
||||
// https://github.com/RobTillaart/map2colour/issues/9
|
||||
|
||||
#include "Arduino.h"
|
||||
#include "map2colour.h"
|
||||
|
||||
map2colour mc(13);
|
||||
|
||||
// float windys_values[] = { -70, -55, -40, -25, -15, -8.33, -3.89, 0, 1, 10, 21, 30, 45}; // Celsius
|
||||
float windys_values[13] = { -94,-67,-40,-13,5,17,25,32,34,50,70,86,116}; // Fahrenheit.
|
||||
uint32_t windys_colour[13] =
|
||||
{
|
||||
0x734669, 0xcaacc3, 0xa24691, 0x8f59a9, 0x9ddbd9, 0x6abfb5, 0x64a6bd,
|
||||
0x5d85c6, 0x447d63, 0x809318, 0xf3b704, 0xe85319, 0x470e00
|
||||
};
|
||||
|
||||
|
||||
void setup()
|
||||
{
|
||||
Serial.begin(115200);
|
||||
Serial.println(__FILE__);
|
||||
Serial.print("MAP2COLOUR_LIB_VERSION: ");
|
||||
Serial.println(MAP2COLOUR_LIB_VERSION);
|
||||
Serial.println();
|
||||
|
||||
// load the windys arrays
|
||||
mc.begin(windys_values, windys_colour);
|
||||
|
||||
// show the interpolating
|
||||
for (float i = -100; i < 125; i += 5)
|
||||
{
|
||||
uint32_t rgb = mc.map2RGB(i);
|
||||
Serial.print(i);
|
||||
Serial.print("\t");
|
||||
Serial.println(rgb, HEX);
|
||||
}
|
||||
Serial.println();
|
||||
}
|
||||
|
||||
void loop()
|
||||
{
|
||||
}
|
||||
|
||||
// -- END OF FILE --
|
@ -7,6 +7,8 @@ map2colourFast KEYWORD1
|
||||
|
||||
# Methods and Functions (KEYWORD2)
|
||||
begin KEYWORD2
|
||||
size KEYWORD2
|
||||
|
||||
map2RGB KEYWORD2
|
||||
map2_565 KEYWORD2
|
||||
|
||||
|
@ -15,7 +15,7 @@
|
||||
"type": "git",
|
||||
"url": "https://github.com/RobTillaart/map2colour.git"
|
||||
},
|
||||
"version": "0.1.6",
|
||||
"version": "0.2.0",
|
||||
"license": "MIT",
|
||||
"frameworks": "arduino",
|
||||
"platforms": "*",
|
||||
|
@ -1,5 +1,5 @@
|
||||
name=map2colour
|
||||
version=0.1.6
|
||||
version=0.2.0
|
||||
author=Rob Tillaart <rob.tillaart@gmail.com>
|
||||
maintainer=Rob Tillaart <rob.tillaart@gmail.com>
|
||||
sentence=Arduino library for mapping a float to colour spectrum
|
||||
|
48
libraries/map2colour/m2c_colours.h
Normal file
48
libraries/map2colour/m2c_colours.h
Normal file
@ -0,0 +1,48 @@
|
||||
#pragma once
|
||||
//
|
||||
// FILE: m2c_colours.h
|
||||
// AUTHOR: Rob Tillaart
|
||||
// PURPOSE: Arduino library for mapping a float to colour spectrum
|
||||
// URL: https://github.com/RobTillaart/map2colour
|
||||
|
||||
|
||||
// https://www.w3.org/wiki/CSS/Properties/color/keywords
|
||||
#define M2C_BLACK 0x00000000
|
||||
#define M2C_SILVER 0x00C0C0C0
|
||||
#define M2C_GRAY 0x00808080
|
||||
#define M2C_WHITE 0x00FFFFFF
|
||||
#define M2C_MAROON 0x00800000
|
||||
#define M2C_RED 0x00FF0000
|
||||
#define M2C_PURPLE 0x00800080
|
||||
#define M2C_FUCHSIA 0x00FF00FF
|
||||
#define M2C_GREEN 0x00008000
|
||||
#define M2C_LIME 0x000FF000
|
||||
#define M2C_OLIVE 0x00808000
|
||||
#define M2C_YELLOW 0x00FFFF00
|
||||
#define M2C_NAVY 0x00000080
|
||||
#define M2C_BLUE 0x000000FF
|
||||
#define M2C_TEAL 0x00008080
|
||||
#define M2C_AQUA 0x0000FFFF
|
||||
|
||||
|
||||
#define M2C_GRAY_0 0x00000000
|
||||
#define M2C_GRAY_1 0x00101010
|
||||
#define M2C_GRAY_2 0x00202020
|
||||
#define M2C_GRAY_3 0x00303030
|
||||
#define M2C_GRAY_4 0x00404040
|
||||
#define M2C_GRAY_5 0x00505050
|
||||
#define M2C_GRAY_6 0x00606060
|
||||
#define M2C_GRAY_7 0x00707070
|
||||
#define M2C_GRAY_8 0x00808080
|
||||
#define M2C_GRAY_9 0x00909090
|
||||
#define M2C_GRAY_10 0x00A0A0A0
|
||||
#define M2C_GRAY_11 0x00B0B0B0
|
||||
#define M2C_GRAY_12 0x00C0C0C0
|
||||
#define M2C_GRAY_13 0x00D0D0D0
|
||||
#define M2C_GRAY_14 0x00E0E0E0
|
||||
#define M2C_GRAY_15 0x00F0F0F0
|
||||
#define M2C_GRAY_16 0x00FFFFFF
|
||||
|
||||
|
||||
// -- END OF FILE --
|
||||
|
@ -1,25 +1,54 @@
|
||||
//
|
||||
// FILE: map2colour.cpp
|
||||
// AUTHOR: Rob Tillaart
|
||||
// VERSION: 0.1.6
|
||||
// VERSION: 0.2.0
|
||||
// PURPOSE: Arduino library for mapping a float to colour spectrum
|
||||
// URL: https://github.com/RobTillaart/map2colour
|
||||
|
||||
|
||||
#include "map2colour.h"
|
||||
|
||||
#define M2C_MIN_SIZE 7
|
||||
|
||||
map2colour::map2colour()
|
||||
map2colour::map2colour(uint8_t size)
|
||||
{
|
||||
_size = size;
|
||||
if (_size < M2C_MIN_SIZE) _size = M2C_MIN_SIZE;
|
||||
|
||||
_Red = (uint8_t *)malloc(_size);
|
||||
_Green = (uint8_t *)malloc(_size);
|
||||
_Blue = (uint8_t *)malloc(_size);
|
||||
|
||||
// for backwards compatibility
|
||||
uint8_t r[7] = { 0x00, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0xFF };
|
||||
uint8_t g[7] = { 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x00, 0xFF };
|
||||
uint8_t b[7] = { 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF };
|
||||
|
||||
memcpy(_Red, r, 7);
|
||||
memcpy(_Green, g, 7);
|
||||
memcpy(_Blue, b, 7);
|
||||
}
|
||||
|
||||
|
||||
map2colour::~map2colour()
|
||||
{
|
||||
if (_Red) free(_Red);
|
||||
if (_Green) free(_Green);
|
||||
if (_Blue) free(_Blue);
|
||||
}
|
||||
|
||||
|
||||
bool map2colour::begin(float * values, uint32_t * colourMap)
|
||||
{
|
||||
if ((_Red == NULL) || (_Green == NULL) || (_Blue == NULL))
|
||||
{
|
||||
// need error codes?
|
||||
return false;
|
||||
}
|
||||
// split colour map in channels to allow interpolation per channel
|
||||
if (colourMap != NULL)
|
||||
{
|
||||
for (int i = 0; i < 7; i++)
|
||||
for (int i = 0; i < _size; i++)
|
||||
{
|
||||
uint32_t val = colourMap[i];
|
||||
_Blue[i] = val & 0xFF;
|
||||
@ -30,16 +59,21 @@ bool map2colour::begin(float * values, uint32_t * colourMap)
|
||||
}
|
||||
}
|
||||
_values = values;
|
||||
for (int index = 1; index < 7; index++)
|
||||
for (int index = 1; index < _size; index++)
|
||||
{
|
||||
// catch non increasing values.
|
||||
float den = _values[index] - _values[index - 1];
|
||||
if (den <= 0.0) return false;
|
||||
if (den < 0.0) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
uint8_t map2colour::size()
|
||||
{
|
||||
return _size;
|
||||
}
|
||||
|
||||
|
||||
uint32_t map2colour::map2RGB(float value)
|
||||
{
|
||||
uint8_t index = 1;
|
||||
@ -50,7 +84,7 @@ uint32_t map2colour::map2RGB(float value)
|
||||
|
||||
if (_values[0] < value)
|
||||
{
|
||||
if (value < _values[6] )
|
||||
if (value < _values[_size-1] )
|
||||
{
|
||||
// search the interval
|
||||
while (_values[index] < value) index++;
|
||||
@ -77,9 +111,9 @@ uint32_t map2colour::map2RGB(float value)
|
||||
else
|
||||
{
|
||||
// out of upper range
|
||||
R = _Red[6];
|
||||
G = _Green[6];
|
||||
B = _Blue[6];
|
||||
R = _Red[_size-1];
|
||||
G = _Green[_size-1];
|
||||
B = _Blue[_size-1];
|
||||
}
|
||||
}
|
||||
uint32_t colour = R;
|
||||
@ -109,17 +143,25 @@ uint16_t map2colour::map2_565(float value)
|
||||
//
|
||||
// DERIVED CLASS
|
||||
//
|
||||
map2colourFast::map2colourFast() : map2colour()
|
||||
map2colourFast::map2colourFast(uint8_t size) : map2colour(size)
|
||||
{
|
||||
divFactor = (float *) malloc(size * sizeof(float));
|
||||
}
|
||||
|
||||
|
||||
map2colourFast::~map2colourFast()
|
||||
{
|
||||
if (divFactor) free(divFactor);
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool map2colourFast::begin(float * values, uint32_t * colourMap)
|
||||
{
|
||||
// load the colour-map and check non-decreasing order.
|
||||
bool OK = map2colour::begin(values, colourMap);
|
||||
// pre-calculate dividers
|
||||
for (int index = 1; index < 7; index++)
|
||||
for (int index = 1; index < _size; index++)
|
||||
{
|
||||
float divider = _values[index] - _values[index - 1];
|
||||
if (divider > 0)
|
||||
@ -145,7 +187,7 @@ uint32_t map2colourFast::map2RGB(float value)
|
||||
|
||||
if (_values[0] < value)
|
||||
{
|
||||
if (value < _values[6] )
|
||||
if (value < _values[_size-1] )
|
||||
{
|
||||
// search the interval
|
||||
while (_values[index] < value) index++;
|
||||
@ -170,9 +212,9 @@ uint32_t map2colourFast::map2RGB(float value)
|
||||
else
|
||||
{
|
||||
// out of upper range
|
||||
R = _Red[6];
|
||||
G = _Green[6];
|
||||
B = _Blue[6];
|
||||
R = _Red[_size-1];
|
||||
G = _Green[_size-1];
|
||||
B = _Blue[_size-1];
|
||||
}
|
||||
}
|
||||
uint32_t colour = R;
|
||||
|
@ -2,71 +2,37 @@
|
||||
//
|
||||
// FILE: map2colour.h
|
||||
// AUTHOR: Rob Tillaart
|
||||
// VERSION: 0.1.6
|
||||
// VERSION: 0.2.0
|
||||
// PURPOSE: Arduino library for mapping a float to colour spectrum
|
||||
// URL: https://github.com/RobTillaart/map2colour
|
||||
|
||||
|
||||
#include "Arduino.h"
|
||||
|
||||
#define MAP2COLOUR_LIB_VERSION (F("0.1.6"))
|
||||
#include "m2c_colours.h"
|
||||
|
||||
|
||||
// https://www.w3.org/wiki/CSS/Properties/color/keywords
|
||||
#define M2C_BLACK 0x00000000
|
||||
#define M2C_SILVER 0x00C0C0C0
|
||||
#define M2C_GRAY 0x00808080
|
||||
#define M2C_WHITE 0x00FFFFFF
|
||||
#define M2C_MAROON 0x00800000
|
||||
#define M2C_RED 0x00FF0000
|
||||
#define M2C_PURPLE 0x00800080
|
||||
#define M2C_FUCHSIA 0x00FF00FF
|
||||
#define M2C_GREEN 0x00008000
|
||||
#define M2C_LIME 0x000FF000
|
||||
#define M2C_OLIVE 0x00808000
|
||||
#define M2C_YELLOW 0x00FFFF00
|
||||
#define M2C_NAVY 0x00000080
|
||||
#define M2C_BLUE 0x000000FF
|
||||
#define M2C_TEAL 0x00008080
|
||||
#define M2C_AQUA 0x0000FFFF
|
||||
|
||||
|
||||
// needed?
|
||||
// #define M2C_GRAY_1 0x00101010
|
||||
// #define M2C_GRAY_2 0x00202020
|
||||
// #define M2C_GRAY_3 0x00303030
|
||||
// #define M2C_GRAY_4 0x00404040
|
||||
// #define M2C_GRAY_5 0x00505050
|
||||
// #define M2C_GRAY_6 0x00606060
|
||||
// #define M2C_GRAY_7 0x00707070
|
||||
// #define M2C_GRAY_8 0x00808080
|
||||
// #define M2C_GRAY_9 0x00909090
|
||||
// #define M2C_GRAY_10 0x00A0A0A0
|
||||
// #define M2C_GRAY_11 0x00B0B0B0
|
||||
// #define M2C_GRAY_12 0x00C0C0C0
|
||||
// #define M2C_GRAY_13 0x00D0D0D0
|
||||
// #define M2C_GRAY_14 0x00E0E0E0
|
||||
#define MAP2COLOUR_LIB_VERSION (F("0.2.0"))
|
||||
|
||||
|
||||
class map2colour
|
||||
{
|
||||
public:
|
||||
map2colour();
|
||||
map2colour(uint8_t size = 7);
|
||||
~map2colour();
|
||||
|
||||
// values is an array of 7 values in ascending order
|
||||
bool begin(float * values, uint32_t * colourMap = NULL);
|
||||
// values is an array of size values in ascending order
|
||||
bool begin(float * values, uint32_t * colourMap = NULL);
|
||||
uint8_t size();
|
||||
uint32_t map2RGB(float value);
|
||||
uint16_t map2_565(float value);
|
||||
|
||||
protected:
|
||||
uint8_t _size = 7;
|
||||
uint8_t _size;
|
||||
float * _values;
|
||||
|
||||
// default colours, split up per channel for performance.
|
||||
uint8_t _Red[7] = { 0x00, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0xFF };
|
||||
uint8_t _Green[7] = { 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0x00, 0xFF };
|
||||
uint8_t _Blue[7] = { 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF };
|
||||
// uint8_t _Alpha[7] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
|
||||
uint8_t * _Red;
|
||||
uint8_t * _Green;
|
||||
uint8_t * _Blue;
|
||||
};
|
||||
|
||||
|
||||
@ -79,14 +45,16 @@ class map2colour
|
||||
class map2colourFast : public map2colour
|
||||
{
|
||||
public:
|
||||
map2colourFast();
|
||||
// values is an array of 7 values in ascending order
|
||||
map2colourFast(uint8_t size = 7);
|
||||
~map2colourFast();
|
||||
|
||||
// values is an array of size values in ascending order
|
||||
bool begin(float * values, uint32_t * colourMap = NULL);
|
||||
uint32_t map2RGB(float value);
|
||||
uint16_t map2_565(float value);
|
||||
|
||||
private:
|
||||
float divFactor[6];
|
||||
float * divFactor;
|
||||
};
|
||||
|
||||
|
||||
|
@ -59,7 +59,7 @@ unittest(test_constructor_II)
|
||||
map2colour mc;
|
||||
|
||||
float values[7] = { 1, 2, 3, 4, 5, 6, 7 };
|
||||
uint32_t colours[7] =
|
||||
uint32_t colours[7] =
|
||||
{
|
||||
M2C_WHITE, M2C_BLACK, M2C_FUCHSIA, M2C_OLIVE, M2C_NAVY, M2C_GREEN, M2C_YELLOW
|
||||
};
|
||||
@ -75,7 +75,7 @@ unittest(test_constructor_II)
|
||||
}
|
||||
|
||||
|
||||
unittest(test_constants)
|
||||
unittest(test_constants_I)
|
||||
{
|
||||
assertEqual(M2C_BLACK ,0x00000000);
|
||||
assertEqual(M2C_SILVER ,0x00C0C0C0);
|
||||
@ -96,6 +96,28 @@ unittest(test_constants)
|
||||
}
|
||||
|
||||
|
||||
unittest(test_constants_II)
|
||||
{
|
||||
assertEqual(M2C_GRAY_0 ,0x00000000);
|
||||
assertEqual(M2C_GRAY_1 ,0x00101010);
|
||||
assertEqual(M2C_GRAY_2 ,0x00202020);
|
||||
assertEqual(M2C_GRAY_3 ,0x00303030);
|
||||
assertEqual(M2C_GRAY_4 ,0x00404040);
|
||||
assertEqual(M2C_GRAY_5 ,0x00505050);
|
||||
assertEqual(M2C_GRAY_6 ,0x00606060);
|
||||
assertEqual(M2C_GRAY_7 ,0x00707070);
|
||||
assertEqual(M2C_GRAY_8 ,0x00808080);
|
||||
assertEqual(M2C_GRAY_9 ,0x00909090);
|
||||
assertEqual(M2C_GRAY_10 ,0x00A0A0A0);
|
||||
assertEqual(M2C_GRAY_11 ,0x00B0B0B0);
|
||||
assertEqual(M2C_GRAY_12 ,0x00C0C0C0);
|
||||
assertEqual(M2C_GRAY_13 ,0x00D0D0D0);
|
||||
assertEqual(M2C_GRAY_14 ,0x00E0E0E0);
|
||||
assertEqual(M2C_GRAY_15 ,0x00F0F0F0);
|
||||
assertEqual(M2C_GRAY_16 ,0x00FFFFFF);
|
||||
}
|
||||
|
||||
|
||||
unittest(test_compare_RGB)
|
||||
{
|
||||
map2colour mc;
|
||||
@ -105,7 +127,7 @@ unittest(test_compare_RGB)
|
||||
|
||||
mc.begin(values);
|
||||
mcf.begin(values);
|
||||
|
||||
|
||||
int fails = 0;
|
||||
for (float i = 0; i <= 1024; i++)
|
||||
{
|
||||
@ -131,7 +153,7 @@ unittest(test_compare_RGB565)
|
||||
|
||||
mc.begin(values);
|
||||
mcf.begin(values);
|
||||
|
||||
|
||||
int fails = 0;
|
||||
for (float i = 0; i <= 1024; i++)
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user