我正在使用 Color.FromArgb
来确定画笔颜色。例如使用这个Pen p= new Pen(new SolidColorBrush(Color.FromArgb(95, 255, 0, 0)), 6);
这个问题是我想使用 4 种颜色画笔(红色、橙色、黄色和绿色)。我有一个条件,根据这个条件下的值,选择具有一定透明度的颜色。这个问题是两种不同颜色之间的过渡,例如从绿色到黄色或从橙色到红色,颜色突然改变,我不想要这个。我想在不同颜色之间平滑过渡,例如从橙色到红色,我希望它采用不同程度的橙色,直到它变得微红,直到它变成红色。
下面是我的代码的快照,试图澄清我做了什么,所以如果有人可以提出建议,请让我知道是否需要更多说明。因此,如下所示,根据 X
的值,颜色以一定的强度确定,但问题在于 X
的最后一个值是否为 10
表示绿色,当前为 11
表示颜色为黄色,这使得 View 不平滑,因为颜色从绿色变为黄色,没有任何平滑度。而且我认为可能使用 HSV 可以解决这个问题。所以如果有人可以请建议。
for(X=0; X<=40; X++)
//this is green phase
if (X == 0)
P = new Pen(new SolidColorBrush(Color.FromArgb(75, 0, 255, 0)), 6);
else if (X == 1)
P = new Pen(new SolidColorBrush(Color.FromArgb(77, 0, 255, 0)), 6);
else if (X == 2)
P = new Pen(new SolidColorBrush(Color.FromArgb(79, 0, 255, 0)), 6);
else if (X == 3)
P = new Pen(new SolidColorBrush(Color.FromArgb(81, 0, 255, 0)), 6);
else if (X == 4)
P = new Pen(new SolidColorBrush(Color.FromArgb(83, 0, 255, 0)), 6);
else if (X == 5)
P = new Pen(new SolidColorBrush(Color.FromArgb(85, 0, 255, 0)), 6);
else if (X == 6)
P = new Pen(new SolidColorBrush(Color.FromArgb(87, 0, 255, 0)), 6);
else if (X == 7)
P = new Pen(new SolidColorBrush(Color.FromArgb(89, 0, 255, 0)), 6);
else if (X == 8)
P = new Pen(new SolidColorBrush(Color.FromArgb(91, 0, 255, 0)), 6);
else if (X == 9)
P = new Pen(new SolidColorBrush(Color.FromArgb(93, 0, 255, 0)), 6);
else if (X == 10)
P = new Pen(new SolidColorBrush(Color.FromArgb(95, 0, 255, 0)), 6);
// this is yellow phase
else if (X == 11)
P = new Pen(new SolidColorBrush(Color.FromArgb(75, 255, 255, 0)), 6);
else if (X == 12)
P = new Pen(new SolidColorBrush(Color.FromArgb(77, 255, 255, 0)), 6);
else if (X == 13)
P = new Pen(new SolidColorBrush(Color.FromArgb(79, 255, 255, 0)), 6);
else if (X == 14)
P = new Pen(new SolidColorBrush(Color.FromArgb(81, 255, 255, 0)), 6);
else if (X == 15)
P = new Pen(new SolidColorBrush(Color.FromArgb(83, 255, 255, 0)), 6);
else if (X == 16)
P = new Pen(new SolidColorBrush(Color.FromArgb(85, 255, 255, 0)), 6);
else if (X == 17)
P = new Pen(new SolidColorBrush(Color.FromArgb(87, 255, 255, 0)), 6);
else if (X == 18)
P = new Pen(new SolidColorBrush(Color.FromArgb(89, 255, 255, 0)), 6);
else if (X == 19)
P = new Pen(new SolidColorBrush(Color.FromArgb(91, 255, 255, 0)), 6);
else if (X == 20)
P = new Pen(new SolidColorBrush(Color.FromArgb(93, 255, 255, 0)), 6);
// this is orange phase
else if (X == 21)
P = new Pen(new SolidColorBrush(Color.FromArgb(75, 255, 127, 0)), 6);
else if (X == 22)
P = new Pen(new SolidColorBrush(Color.FromArgb(77, 255, 127, 0)), 6);
else if (X == 23)
P = new Pen(new SolidColorBrush(Color.FromArgb(79, 255, 127, 0)), 6);
else if (X == 24)
P = new Pen(new SolidColorBrush(Color.FromArgb(81, 255, 127, 0)), 6);
else if (X == 25)
P = new Pen(new SolidColorBrush(Color.FromArgb(83, 255, 127, 0)), 6);
else if (X == 26)
P = new Pen(new SolidColorBrush(Color.FromArgb(85, 255, 127, 0)), 6);
else if (X == 27)
P = new Pen(new SolidColorBrush(Color.FromArgb(87, 255, 127, 0)), 6);
else if (X == 28)
P = new Pen(new SolidColorBrush(Color.FromArgb(89, 255, 127, 0)), 6);
else if (X == 29)
P = new Pen(new SolidColorBrush(Color.FromArgb(91, 255, 127, 0)), 6);
else if (X == 30)
P = new Pen(new SolidColorBrush(Color.FromArgb(93, 255, 127, 0)), 6);
//this is red phase
else if (X == 31)
P = new Pen(new SolidColorBrush(Color.FromArgb(75, 255, 0, 0)), 6);
else if (X == 32)
P = new Pen(new SolidColorBrush(Color.FromArgb(77, 255, 0, 0)), 6);
else if (X == 33)
P = new Pen(new SolidColorBrush(Color.FromArgb(79, 255, 0, 0)), 6);
else if (X == 34)
P = new Pen(new SolidColorBrush(Color.FromArgb(81, 255, 0, 0)), 6);
else if (X == 35)
P = new Pen(new SolidColorBrush(Color.FromArgb(83, 255, 0, 0)), 6);
else if (X == 36)
P = new Pen(new SolidColorBrush(Color.FromArgb(85, 255, 0, 0)), 6);
else if (X == 37)
P = new Pen(new SolidColorBrush(Color.FromArgb(87, 255, 0, 0)), 6);
else if (X == 38)
P = new Pen(new SolidColorBrush(Color.FromArgb(89, 255, 0, 0)), 6);
else if (X == 39)
P = new Pen(new SolidColorBrush(Color.FromArgb(91, 255, 0, 0)), 6);
else if (X == 40)
P = new Pen(new SolidColorBrush(Color.FromArgb(93, 255, 0, 0)), 6);
最佳答案
也许你应该看看 this answer .它可以帮助您使用颜色类中的方法 GetHue()
、GetSaturation()
和 GetBrightness()
并根据这些方法创建新颜色参数。
通过使用它,您可以简单地得到开始和结束颜色的色调,并根据您的步长获得所需的尽可能多的中间颜色。
如果有一个方法不是很好吗:
int numberOfIntermediateColors = 8;
IEnumerable<Colors> colorPalette = Color.Red.Range(Color.Green, numberOfIntermediateColors);
这里是:
public static IEnumerable<Color> Range(this Color firstColor, Color lastColor, int count)
{
float stepHueClockwise = GetStepping(firstColor.GetHue(), lastColor.GetHue(), count, Direction.Clockwise);
float stepHueCounterClockwise = GetStepping(firstColor.GetHue(), lastColor.GetHue(), count, Direction.CounterClockwise);
if (Math.Abs(stepHueClockwise) >= Math.Abs(stepHueCounterClockwise))
return Range(firstColor, lastColor, count, Direction.Clockwise);
else
return Range(firstColor, lastColor, count, Direction.CounterClockwise);
}
public static IEnumerable<Color> Range(this Color firstColor, Color lastColor, int count, Direction hueDirection)
{
var color = firstColor;
if (count <= 0)
yield break;
if (count == 1)
yield return firstColor;
float startingHue = color.GetHue();
float stepHue = GetStepping(firstColor.GetHue(), lastColor.GetHue(), count - 1, hueDirection);
var stepSaturation = (lastColor.GetSaturation() - firstColor.GetSaturation()) / (count - 1);
var stepBrightness = (lastColor.GetBrightness() - firstColor.GetBrightness()) / (count - 1);
var stepAlpha = (lastColor.A - firstColor.A) / (count - 1.0);
for (int i = 1; i < count; i++)
{
yield return color;
var hueValue = startingHue + stepHue * i;
if (hueValue > 360)
hueValue -= 360;
if (hueValue < 0)
hueValue = 360 + hueValue;
color = FromAhsb(
Clamp((int)(color.A + stepAlpha), 0, 255),
hueValue,
Clamp(color.GetSaturation() + stepSaturation, 0, 1),
Clamp(color.GetBrightness() + stepBrightness, 0, 1));
}
yield return lastColor;
}
public enum Direction
{
Clockwise = 0,
CounterClockwise = 1
}
private static float GetStepping(float start, float end, int count, Direction direction)
{
var hueDiff = end - start;
switch (direction)
{
case Direction.CounterClockwise:
if (hueDiff >= 0)
hueDiff = (360 - hueDiff) * -1;
break;
default:
if (hueDiff <= 0)
hueDiff = 360 + hueDiff;
break;
}
return hueDiff / count;
}
private static int Clamp(int value, int min, int max)
{
if (value < min)
return min;
if (value > max)
return max;
return value;
}
private static float Clamp(float value, float min, float max)
{
if (value < min)
return min;
if (value > max)
return max;
return value;
}
要获取笔列表不透明,您可以采用这种简单的方法:
var startColor = Color.Green;
var endColor = Color.Red;
var penWidth = 6;
var rainbow = startColor.Range(endColor, 40, bla.Direction.CounterClockwise);
var pens = rainbow.Select(color => new Pen(color, penWidth))
.ToList();
// Somewhere else...
int x = RetrieveDesiredCondition();
var neededPen = pens[x];
就我在您的示例中看到的而言,您希望让透明度从 75 迭代到 95,每个 block 包含 10 种颜色,总共有 4 个 block 。在那种情况下,也许这个算法可能会有所帮助:
var startColor = Color.Green;
var endColor = Color.Red;
var penWidth = 6;
var lowerTransparency = 75;
var higherTransparency = 95;
var stepsPerSection = 10;
var sections = 4;
var stepsNeeded = stepsPerSection * sections;
var transparencyRange = higherTransparency - lowerTransparency;
var stepSize = transparencyRange / stepsPerSection;
var rainbow = startColor.Range(endColor, stepsNeeded, Direction.CounterClockwise);
var rainbowWithTransparency = rainbow.Select((color, index) =>
{
var step = (index % stepsPerSection) * stepSize;
var neededTransparency = lowerTransparency + step;
return Color.FromArgb(neededTransparency, color);
});
var pens = rainbowWithTransparency.Select(color => new Pen(color, penWidth))
.ToList();
// Somewhere else...
int x = RetrieveDesiredCondition();
var neededPen = pens[x];
关于c# - 在 WPF 中使用 HSV 而不是 RGB,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18821696/