如何在Lua中正确实现HSL到RGB的颜色转换?现有转换代码输出结果不符合预期
Let's break down why your current code is producing incorrect results and fix it step by step:
Key Issues in the Original Code
Incorrect Hue Normalization
Your code divides the hue value by 255, but standard HSL color models use a hue range of 0-360 degrees. Dividing by 255 shifts the hue into an incorrect range, which is why your output colors are swapped and mismatched.HTML Escape Characters
The code uses<and>instead of Lua's native<and>operators. This would actually cause syntax errors when running the script—those are HTML entities, not valid Lua syntax.
Corrected Implementation
Here's the fixed version of your hslToRgb function, with comments explaining the changes:
#!/usr/bin/env lua5.3 local function hslToRgb(h, s, l, a) local r, g, b -- Normalize hue from 0-360 to 0-1 (fixed from dividing by 255) h = h / 360 -- Normalize saturation and lightness from 0-100 to 0-1 s = s / 100 l = l / 100 if s == 0 then r, g, b = l, l, l -- achromatic (grayscale) else local function hue2rgb(p, q, t) -- Fixed HTML entities to Lua's comparison operators if t < 0 then t = t + 1 end if t > 1 then t = t - 1 end if t < 1/6 then return p + (q - p) * 6 * t end if t < 1/2 then return q end if t < 2/3 then return p + (q - p) * (2/3 - t) * 6 end return p end local q if l < 0.5 then q = l * (1 + s) else q = l + s - l * s end local p = 2 * l - q -- These hue offsets are correct for standard HSL to RGB mapping r = hue2rgb(p, q, h + 1/3) g = hue2rgb(p, q, h) b = hue2rgb(p, q, h - 1/3) end -- Default alpha to 1 if not provided if not a then a = 1 end -- Convert normalized values back to 0-255 range, rounded to integers return math.floor(r * 255 + 0.5), math.floor(g * 255 + 0.5), math.floor(b * 255 + 0.5), math.floor(a * 255 + 0.5) end -- Test your sample input local h,s,l,a = hslToRgb(220, 16.4, 21.6) print(h,s,l,a) -- Expected output: 46 52 64 255 -- Actual output now matches the expected values!
What Changed?
- Hue Normalization: We now divide
hby 360 instead of 255 to correctly map the 0-360 degree hue range to the 0-1 scale needed for the conversion math. - Fixed Operators: Replaced
</>with</>to resolve syntax errors and ensure proper comparisons. - Rounded Output: Added
math.floor(...) + 0.5to get clean integer values (matches your expected integer output, but you can remove the rounding if you need decimal precision).
Verification
When you run this corrected code with your sample input (220, 16.4, 21.6), it will output 46 52 64 255, which exactly matches your expected result.
内容的提问来源于stack exchange,提问作者SkyyySi

