在带有 Pygame 模块的 Python 3.8 中:
我正在尝试为我正在制作的彩色游戏制作颜色渐变。我知道如何制作一维渐变,像这样:
但我希望能够在渐变中创建具有两种以上颜色的图像。来自互联网的一个例子是这样的:(忽略花哨的文字)
如何创建一个函数来在表面上生成多种颜色的渐变?重要的是我可以选择角落的颜色,或者至少能够以我能理解的方式影响它们。
网上找的一个思路是这样的:
for i in range(900):
for j in range(900):
surface.set_at((i,j),(i/4,j/4,i/4))
我的问题是很难选择它生成的颜色。我无法拼凑如何使颜色相互融合,尤其是多种颜色。
没有魔法。 Pygame 没有渐变的 API,虽然你没有发布 你的代码,你可能做了很好的插值。
所以,对于“二维方形渐变”,你必须继续打破你的 小部分的问题,直到你得到你想要的 - 为此,它可能是:在您感兴趣的区域顶部运行一个渐变 y == 0,另一个渐变在您的区域底部运行,在 y = 高度,并且对于每一列,您插入一个新的渐变, 从 顶部渐变的颜色并运行到底部渐变的颜色。
唯一的坏消息是,这在 pygame 中会非常慢 - 但你可以绘制一次并保存生成的图像,然后在游戏时间加载它。
还有其他适合绘制linear渐变的库和框架, 并快速完成,就像 Cairo、GEGL 和 OpenGL 本身一样——但它们都没有现成的方法将一个完整的渐变过渡到另一个。
[继续...]
所以,对于“二维方形渐变”,你必须继续将你的问题分解成更小的部分,直到你得到你想要的 - 为此,它可能是:在你感兴趣的区域的顶部运行一个渐变在 y = 0 处,另一个渐变在您所在区域的底部运行,在 y = 高度处,对于每一列,您插入一个新的渐变,从顶部渐变的颜色开始,一直运行到底部渐变的颜色。
这太棒了!我能够想出三个函数,它们一起创建了很棒的 4 色矩形渐变,每种颜色位于不同的角。如果您想使用它,这是我的代码:
windowSurface = pygame.display.set_mode((1500,900))
s = pygame.Surface(size, pygame.SRCALPHA)
gradientStorage = pygame.Surface((1500,1500))
colorGridStorage = pygame. Surface((1500,1500))
def colorMix(color1, color2, paletteSize): # creates a list of colors that gradually fade from color1 to color2, inclusive. paletteSize is the amount of values that will be generated.
# The smallest useful paletteSize is 3, as it will return [color1, color1MixedWithColor2, color2]
palette = [color1]
colorDifference = [ color1[0] - color2[0], color1[1] - color2[1], color1[2] - color2[2] ]
Rstep = (color1[0] - color2[0]) / (paletteSize -1)
Gstep = (color1[1] - color2[1]) / (paletteSize -1)
Bstep = (color1[2] - color2[2]) / (paletteSize -1)
for i in range(1,paletteSize):
palette.append((color1[0] - Rstep*i, color1[1] - Gstep*i, color1[2] - Bstep*i))
palette.append(color2)
return palette
def createColorGrid(resolution, color1, color2, color3, color4): # build a new colorGrid using a different process than above. colors are RGB format. For a 1D color fade set pairs of colors
# like (255,0,0) (255,0,0) (0,255,255) (0,255,255). Colors are ordered from top left corner and follow corners clockwise.
colorArray = [resolution] # the first value in colorGrid is always a tuple stating the resolution.
leftColumn = colorMix(color1,color4,resolution[1])
rightColumn = colorMix(color2,color3,resolution[1])
for i in range(0,resolution[1]): # color processing goes from top left to top right, then down a row and repeat
colorArray.append(colorMix(leftColumn[i],rightColumn[i],resolution[0]))
return colorArray
def drawColorGrid(colorGrid, rect): # input a colorGrid array. This will draw the set of color tiles decided by the colorGrid you pass into it
colorGridStorage.fill((255,255,255))
iCounter = 0
for i in colorGrid:
jCounter = 0
if isinstance(i[0], int): # the first value in colorGrid is the [x,y] resolution. we need to ignore it and move on to the rest
continue
for j in i:
rectX = (rect[0] + round( jCounter * (rect[2]/colorGrid[0][0])))
rectY = rect[1] + round(iCounter * rect[3]/colorGrid[0][1])
rectWidth = round(rect[2]/colorGrid[0][0])
rectHeight = round(rect[3]/colorGrid[0][1])
pygame.draw.rect(colorGridStorage, j, (rectX, rectY, rectWidth, rectHeight))
jCounter += 1
iCounter +=1
windowSurface.blit(colorGridStorage, (rect[0], rect[1]))
要绘制新的渐变,首先使用 createColorGrid(resolution, color1, color2, color3, color4) 以特定分辨率构建一个颜色块数组。低分辨率看起来就像游戏 I Love Hue 中的东西。获得 colorGrid 变量后,将其插入 drawColorGrid(colorGrid, rect)。这将采用 colorGrid 数组并将其 blit 到屏幕上给定的矩形内。在这种情况下,屏幕表面被命名为 windowSurface。
我是一个相当新的程序员,所以上面的代码肯定会有一些优化。如果您愿意,请将它们指出给我,但这段代码非常适合我正在做的应用程序。它似乎足够流畅,每秒至少生成 20 个随机渐变并将其 blit 到全屏,这比我需要的要多得多。