对于学校作业,我需要做这样的事情:

该500x500矩形应显示不同的色调,饱和度和亮度的任何颜色鼠标所指向的,有点像一个颜色选择器。
但既然我编码太烂了,我不知道该怎么做。我不太理解HSB。这是我的代码和一张我现在拥有的图片。

void setup() {
size(500,550);
}
void draw() {
noStroke();
colorMode(HSB, 100);
for (int i = 0; i < 500; i++) {
for (int j = 0; j < 50; j++) {
int h = i-200;
int s = j+500;
int b = 500 + j;
stroke(h,s,b);
point(i, j);
}
}
noStroke();
fill(mouseX, mouseY);
rect(0,50,500,500);
}任何帮助都将不胜感激。非常感谢!
发布于 2021-04-14 22:24:11
使用colorMode(HSB)渲染彩虹已经做得很好了。我会将嵌套的for循环移动到安装程序中,以使其更高效:它只呈现一次并停留在那里,因为您没有调用background(),而且rect(0,50,500,500);低于彩虹梯度。
HSB实际上比RGB更容易使用。这是维基百科的一张图表:

SharkD,CC BY-SA3.0 https://creativecommons.org/licenses/by-sa/3.0,通过维基共享
值是相同的亮度。色调通常在0-360度的范围内,所以在彩虹圈中旋转,从红色开始,以红色结束。假设你从红色开始,在0度色调,你知道黄色是60度色调。从直觉上看,你会在30度的红色和黄色之间找到橙色。事实上,如果你每60度走一次,你就会经历红色,黄色,绿色,青色,蓝色,洋红,然后回到360/0的红色。
饱和度和亮度通常在0-100%之间.请注意,在上图中,饱和度在远离中心的地方增加:0饱和度=灰色,100%饱和度=全色调。
在图表中,亮度从下到上都在增加。
这有点奇怪,你是映射到0-100范围内的色调,饱和度和亮度。也许是为了简化事情,把色调也当作百分比来处理。
可以使事情变得更简单的一件事是map()函数。它将一个数字从一个范围映射到另一个范围。
例如,这段代码试图将i,j位置重新映射为色调和饱和度。
i, j在0-500,0-50范围内(x,y位置)i从0-499范围映射到0-100以映射到色调例如:
void setup() {
size(500, 550);
colorMode(HSB, 100);
for (int i = 0; i < 500; i++) {
for (int j = 0; j < 50; j++) {
// remap i (x -> width) to 0 - 100 range for hue
// since map returns a float, round helps make that an int
int h = round(map(i, 0, 499, 0, 100));
int s = 100;
int b = 100;
stroke(h, s, b);
point(i, j);
}
}
noStroke();
}
void draw() {
fill(map(mouseX, 0, width, 0, 100), map(mouseY, 0, height, 0, 100), 100);
rect(0, 50, 500, 500);
}在这种情况下,0-500到0-50范围是微不足道的: 500 / 100 = 5,因此:
int h = i / 5;将获得与int h = round(map(i, 0, 499, 0, 100));相同的结果,只是不必过多地考虑算术问题。
在嵌套的for循环中,您正在设置HSB颜色。在下一部分中,您需要获取/读取HSB颜色,幸运的是,处理已经为您提供了色调()、饱和()和亮度()。对于颜色选择器,您只需要hue()。
要获取光标位置下的颜色,只需调用get(x, y),它将返回一个颜色,即这些坐标。
如果您查看渐变图像,您会注意到:
如果在顶部彩虹梯度上单击鼠标时读取hue(),则只需将x,y坐标映射到饱和度和亮度,就可以产生更大的梯度波纹:
float hue;
void setup() {
size(500, 550);
colorMode(HSB, 100);
for (int i = 0; i < 500; i++) {
for (int j = 0; j < 50; j++) {
// remap i (x -> width) to 0 - 100 range for hue
// since map returns a float, round helps make that an int
int h = round(map(i, 0, 499, 0, 100));
int s = 100;
int b = 100;
stroke(h, s, b);
point(i, j);
}
}
noStroke();
}
void draw() {
// pick colour (hue)
if(mousePressed){
// check if the mouse was pressed on the top side only
if((mouseX >= 0 && mouseX <= 500) &&
(mouseY >= 0 && mouseY <= 50)){
hue = hue(get(mouseX, mouseY));
}
}
// render saturation , brightness mapping
for (int i = 0; i < 500; i++) {
for (int j = 50; j < 550; j++) {
int saturation = round(map(i, 0, 500, 100, 0));
// swap output mapping range: brightness goes up when y decreases
int brightness = round(map(j, 50, 550, 100, 0));
stroke(hue, saturation, brightness);
point(i, j);
}
}
}你会注意到这有点慢。使用pixels[]可以更快。然而,有一些曲线球:
loadPixels()index = x + y * widthupdatePixels()以更新后,需要调用pixels[]这将运行得更快:
float hue;
void setup() {
size(500, 550);
colorMode(HSB, 100);
for (int i = 0; i < 500; i++) {
for (int j = 0; j < 50; j++) {
// remap i (x -> width) to 0 - 100 range for hue
// since map returns a float, round helps make that an int
int h = round(map(i, 0, 499, 0, 100));
int s = 100;
int b = 100;
stroke(h, s, b);
point(i, j);
}
}
noStroke();
}
void draw() {
// make latest pixels[] data available
loadPixels();
// pick colour (hue)
if(mousePressed){
// check if the mouse was pressed on the top side only
if((mouseX >= 0 && mouseX <= 500) &&
(mouseY >= 0 && mouseY <= 50)){
//hue = hue(get(mouseX, mouseY));
hue = hue(pixels[mouseX + mouseY * width]);
}
}
// render saturation , brightness mapping
for (int i = 0; i < 500; i++) {
for (int j = 50; j < 550; j++) {
int saturation = round(map(i, 0, 500, 100, 0));
// swap output mapping range: brightness goes up when y decreases
int brightness = round(map(j, 50, 550, 100, 0));
//stroke(hue, saturation, brightness);
//point(i, j);
pixels[i + j * width] = color(hue, saturation, brightness);
}
}
// update
updatePixels();
}https://stackoverflow.com/questions/67093678
复制相似问题