visible.py
 1  # SPDX-FileCopyrightText: Copyright (c) 2022 JG for Cedar Grove Maker Studios
 2  #
 3  # SPDX-License-Identifier: MIT
 4  """
 5  `cedargrove_rgb_spectrumtools.visible`
 6  ================================================================================
 7  
 8  A Spectral Index to Visible (Rainbow) Spectrum RGB Converter Helper
 9  
10  Based on original 1996 Fortran code by Dan Bruton:
11  physics.sfasu.edu/astro/color/spectra.html
12  
13  * Author(s): JG
14  
15  Implementation Notes
16  --------------------
17  
18  **Hardware:**
19  
20  **Software and Dependencies:**
21  
22  * Adafruit CircuitPython firmware for the supported boards:
23    https://circuitpython.org/downloads
24  """
25  
26  __version__ = "0.0.0+auto.0"
27  __repo__ = "https://github.com/CedarGroveStudios/CircuitPython_RGB_SpectrumTools.git"
28  
29  
30  def index_to_rgb(index=0, gamma=0.5):
31      """
32      Converts a spectral index to rainbow (visible light wavelength)
33      spectrum to an RGB value. Spectral index in range of 0.0 to 1.0
34      (violet --> white). Gamma in range of 0.0 to 1.0 (1.0=linear),
35      default 0.5 for color TFT displays.
36  
37      :param float index: The normalized index value, range 0 to 1.0. Defaults to 0.
38      :param float gamma: The gamma color perception value. Defaults to 0.5.
39  
40      :return: Returns a 24-bit RGB value
41      :rtype: integer
42      """
43  
44      wavelength = (index * 320) + 380
45  
46      if wavelength < 440:
47          intensity = 0.1 + (0.9 * (wavelength - 380) / (440 - 380))
48          red = ((-1.0 * (wavelength - 440) / (440 - 380)) * intensity) ** gamma
49          grn = 0.0
50          blu = (1.0 * intensity) ** gamma
51      if 440 <= wavelength < 490:
52          red = 0.0
53          grn = (1.0 * (wavelength - 440) / (490 - 440)) ** gamma
54          blu = 1.0**gamma
55      if 490 <= wavelength < 510:
56          red = 0.0
57          grn = 1.0**gamma
58          blu = (-1.0 * (wavelength - 510) / (510 - 490)) ** gamma
59      if 510 <= wavelength < 580:
60          red = (1.0 * (wavelength - 510) / (580 - 510)) ** gamma
61          grn = 1.0**gamma
62          blu = 0.0
63      if 580 <= wavelength < 645:
64          red = 1.0**gamma
65          grn = (-1.0 * (wavelength - 645) / (645 - 580)) ** gamma
66          blu = 0.0
67      if wavelength >= 645:
68          intensity = 0.3 + (0.7 * (700 - wavelength) / (700 - 645))
69          red = (1.0) ** gamma
70          grn = (1.0 - intensity) ** gamma
71          blu = (1.0 - intensity) ** gamma
72  
73      return (int(red * 255) << 16) + (int(grn * 255) << 8) + int(blu * 255)