Currently, I am using a color wheel and it is working fine (image below).
But I am trying to make it like the second image, using 2 separate image how do I do this calculation?
Current wheel system:
What I want:
Currently, I am using a color wheel and it is working fine (image below).
But I am trying to make it like the second image, using 2 separate image how do I do this calculation?
Current wheel system:
What I want:
So you want to make a fancy color wheel. Good luck.
This very long wall of text occasionally uses <abbr>
tags. Hover to read more.
You’ll probably want to use these 2 images. 1024x1024, do whatever you want with them. I don’t care, despite having spent at least an hour of my life writing Lua code to generate them, and even more to type this very long reply.
ImageLabel
of any (square) size. No background.
ImageButton
parented to the static ImageLabel
. No background, 100% size. To achieve the effect I assume you want, you could change its ImageColor3
based on the selected hue, possibly using the Color3
HSV functions.
To make this color wheel interactive, you’ll want to listen to mouse inputs. Suppose you have a function click(x: number, y: number)
. How that function is called is left as an exercise for the reader. It could be something with that ImageButton
. Maybe some signals. UserInputService
to handle edge cases of Roblox not firing signals.
The arguments x
and y
could be the relative position of the mouse, with -1, -1
being the top left corner of the image and 1, 1
being the bottom right corner. Given this relative position:
-0.5, -0.5
and 0.5, 0.5
respectively.
x
and y
to -0.5
…0.5
.x
and can be calculated using x + 0.5
. Left is no saturation, right is full saturation.y
and can be calculated using -y + 0.5
. Bottom is black.0.8
and ends at 1
, leaving the corners of the image transparent.Enter math.atan2(y: number, x: number): number
. It’s almost like magic (and even I don’t fully understand it).
-- see "The fun part" for definition of x and y
-- conversion to degrees could be skipped, but it doesn't really matter
-- as long as you get a number from 0 to 1
local hue = math.deg(math.atan2(y, x) + math.pi / 2) % 360 / 360
-- assuming btn is the ImageButton previously defined in "The boring part"
btn.ImageColor3 = Color3.fromHSV(hue, 1, 1)
One. 2 if you count the assignment of ImageColor3
. More if you also count comments.
All of this information may or may not be useful for solving your problem. If it was, that’s great! If not, please ask as many questions as you can. I’ll do my best to attempt to answer them as soon as I return from being dead
Thank you so much for the in-depth explanation! I will put this into action.
Do I stack the images? That means I would have two of theses on top of each other right?
Assuming the second image is parented to the first with the size defined in my first reply, it should look like this (second image ImageColor3 = Color3.new(1, 0, 0)
):
Hey, I need some help with the color wheel, I can’t seem to get anything working with accurate values, it might be with the way I calculate the mouse position? Any suggestions?
How do you calculate the mouse position?
I am checking to see if they are hovering over the label or whatever it is, then in input service mouse movement to then move the picker icon to the mouse, if the is in label == true, then do input.Position.Y, input.Position.Y
That information doesn’t really explain anything. Could you post your code instead?
My get color function:
local colourPickerCentre = Vector2.new(ColorWheel.Picker.AbsolutePosition.X + (ColorWheel.Picker.AbsoluteSize.X/2),ColorWheel.Picker.AbsolutePosition.Y + (ColorWheel.Picker.AbsoluteSize.Y/2))
local h = (math.pi - math.atan2(colourPickerCentre.Y - centreOfWheel.Y, colourPickerCentre.X - centreOfWheel.X)) / (math.pi * 2)
local s = (centreOfWheel - colourPickerCentre).Magnitude / (ColorWheel.AbsoluteSize.X/2)
local v = math.abs((mouseY - HueWheel.AbsolutePosition.Y) / HueWheel.AbsoluteSize.Y - 1)
local hsv = Color3.fromHSV(math.clamp(h, 0, 1), math.clamp(s, 0, 1), math.clamp(v, 0, 1))
How I get centre of wheel:
centreOfWheel = Vector2.new(ColorWheel.AbsolutePosition.X + (ColorWheel.AbsoluteSize.X/2), ColorWheel.AbsolutePosition.Y + (ColorWheel.AbsoluteSize.Y/2))
selectedColor = getColor(centreOfWheel)
This is in a input changed, first makes sure that the inFrame is equal to true, which is set by a mouse.enter and mouse.leave, it checks for mouse down and mouse movement to where to move the color picker icon to
local h = (math.pi - math.atan2(colourPickerCentre.Y - centreOfWheel.Y, colourPickerCentre.X - centreOfWheel.X)) / (math.pi * 2)
Assuming one of an unknown number of issues with your code is the hue calculation, one way to (hopefully) fix that would be the following:
local h = (math.atan2(colourPickerCentre.Y - centreOfWheel.Y, colourPickerCentre.X - centreOfWheel.X) + math.pi / 2) / (math.pi * 2) % 1
Could you upload a video of your color wheel misbehaving?
It took a concerning amount of effort to fix the hue issue. Most of that effort went into a complete recreation of the color wheel. This recreation made debugging (without the full code) a lot easier at the cost of potentially making all of your effort absolutely pointless.
colorwheel.rbxl (32.5 KB)
My sleep-deprived brain decided to turn the color wheel into a standalone UI component because apparently writing code for 2 hours is better than sleep.
ColorWheel
is an ImageLabel
with the first image. It can be anywhere, with any size (for obvious reasons, it should be a square),[clarification needed] and any AnchorPoint
. The attached place file is just an example.WheelMain
handles mouse input and ColorWheel
's Color
attribute (ColorWheel:GetAttribute("Color")
and ColorWheel:SetAttribute("Color", Color3.new(1, 1, 1))
).H
and SV
are Frame
s indicating the current selection.Button
is an ImageButton
with the second image and a dynamic ImageColor3
.Whenever the user clicks the color wheel, WheelMain
starts handling mouse movement. The initial click determines which part of the color wheel should change whenever the mouse moves. This allows the user to click either the square or the hue wheel and drag anywhere, even outside the color wheel, potentially improving the user experience.[citation needed] The update
function calculates the relative mouse position inside the frame based on the InputObject
's Position
and Button
's AbsolutePosition
and AbsoluteSize
.
External code can use ColorWheel
's Color
attribute to get (and set!) the color wheel’s selected color. ColorWheel:GetAttributeChangedSignal("Color")
is a signal fired whenever the selected color changes. See attached place file for a simple demo; code in StarterGui.ScreenGui.demo
.
Because this is just a prototype, some of the code might be a bit messy. For example,
if if lock then m < 0.8 else not huewheel then
I am not sorry. That if
statement would be even worse without that if
expression.
You shouldn’t feel bad about this. You tried your best, and you hopefully gained more scripting experience!
don’t expect a reply for at least 10 hours because that’s how much sleep I need thanks to this surprise time sink
Holy moly. You absolute legend, I can’t thank you enough, you really didn’t have to do all that, thank you so much have a great day and night