3

我是 stackoverflow 的新手,但希望能从更高级的程序员那里得到一点见解。下学期我将转专业为计算机科学,并正在参加一个入门课程,学习一些初学者的 Python 编程。我已经完成了下面的程序(任务是通过填写一些教授的代码来制作一个在窗口表面绘制椭圆的程序,一点也不差)但我想添加一些额外的东西:你可以看,我将椭圆的颜色设置为随机的,但在程序完全重新启动之前它保持不变,即所有椭圆都是程序长度的特定颜色。使用按原样编写的代码,我想不出一种方法来改变每个椭圆的颜色。请记住,这一切都是为了好玩,但如果有人 感觉特别有帮助或有创意,我很想知道你要说什么。让我知道我是否可以解释任何事情。谢谢!


import pygame, random, sys

WINDOWWIDTH = 700
WINDOWHEIGHT = 700
BACKGROUNDCOLOR = (150,160,100)
#A different color every run
OVAL_COLOR = (random.randint (0,255),random.randint (0,255),
                    random.randint (0,255))

pygame.init()
windowSurface = pygame.display.set_mode((WINDOWWIDTH, WINDOWHEIGHT))
pygame.display.set_caption("Mobile Ovals")

#The draw variable is used later to indicate the mouse is still pressed
ovals = []
completedOvals = []
finished = False
draw = False
startXY = (-1, -1)

while not finished:
    for event in pygame.event.get():
        if event.type == pygame.QUIT or (event.type == pygame.KEYUP and
                    event.key == pygame.K_ESCAPE):
            finished = True

        elif event.type == pygame.KEYDOWN:
            pressed = pygame.key.get_pressed()
            if pressed[pygame.K_F4] and (pressed[pygame.K_LALT] or
                        pressed[pygame.K_RALT]):
                finished  = True

        elif event.type == pygame.MOUSEBUTTONDOWN:
            startXY = event.pos
            draw = True

        elif event.type == pygame.MOUSEBUTTONUP:
            draw = False
            for oval in ovals:
                completedOvals.append (oval)

        if draw == True:
            del ovals [:]

            #The above function ensures only one oval is onscreen at any given time
            endXY = event.pos
            width = (abs(endXY[0]-startXY[0]))
            height = (abs(endXY[1]-startXY[1]))

            #The code below allows the user to drag any direction
            if endXY[0] < startXY[0]:
                left = endXY[0]
            else:
                left = startXY[0]
            if endXY[1] < startXY[1]:
                top = endXY[1]
            else:
                top = startXY[1]

            ovals.append (pygame.Rect (left, top, width, height))

            windowSurface.fill(BACKGROUNDCOLOR)

            for oval in ovals:
                pygame.draw.ellipse(windowSurface, OVAL_COLOR, oval)

            for completedOval in completedOvals:
                pygame.draw.ellipse(windowSurface, OVAL_COLOR, completedOval)

            pygame.display.update()

pygame.quit()
4

2 回答 2

2

你的问题很简单。你设置OVAL_COLOR一次。但是每次引用变量OVAL_COLOR时,都不是在创建新的随机颜色,而是在重新使用创建变量时随机生成的 RGB 颜色。

现在,您的程序的结构方式是,您维护一个所有完整椭圆的列表,每次将draw变量设置为 true 时您都重新绘制这些椭圆。如果将OVAL_COLOR变量放在 for 循环中,每次鼠标移动都会更新颜色,改变正在绘制的椭圆的颜色,以及重新绘制的所有旧椭圆的颜色。

获得新的随机椭圆颜色的解决方案是OVAL_COLOR在鼠标按钮按下时设置变量。这样,当您拖动鼠标调整椭圆时,椭圆颜色不会改变。但是,鉴于程序的当前结构,您需要保存分配给已完成椭圆的椭圆颜色,否则每次椭圆颜色都会发生变化。


当按下鼠标按钮时,我们想要一个新的随机颜色为我们的圆圈。生成一个随机值,每次重新绘制圆时都会使用该值。

    elif event.type == pygame.MOUSEBUTTONDOWN:
        startXY = event.pos
        OVAL_COLOR = (random.randint (0,255),random.randint (0,255),
                            random.randint (0,255))
        draw = True

释放鼠标按钮时,保存椭圆的坐标以及绘制它的颜色

    elif event.type == pygame.MOUSEBUTTONUP:
        draw = False
        # print len(ovals) # (always ==1)
        completedOvals.append ((ovals[-1], OVAL_COLOR)) 

当我们遍历这些完成的椭圆时,每次都用相同的颜色绘制它们。

        for (completedOval, color) in completedOvals:
            pygame.draw.ellipse(windowSurface, color, completedOval)
于 2012-04-14T23:32:42.023 回答
1

创建一个简单的Oval()类,其中包含它的颜色和大小。

import pygame
from pygame.locals import * 

class Oval(object):
    """handle, and draw basic ovals. stores Rect() and Color()"""
    def __init__(self, startXY, endXY):
        self.color = Color(random.randint(0,255), random.randint(0,255), random.randint(0,255))
        self.rect = Rect(0,0,1,1)
        self.coord_to_oval(startXY, endXY)

    def draw(self):
        pygame.draw.ellipse(windowSurface, self.color, self.rect)

    def coord_to_oval(self, startXY, endXY):
        width = (abs(endXY[0]-startXY[0]))
        height = (abs(endXY[1]-startXY[1]))

        #The code below allows the user to drag any direction
        if endXY[0] < startXY[0]:
            left = endXY[0]
        else:
            left = startXY[0]
        if endXY[1] < startXY[1]:
            top = endXY[1]
        else:
            top = startXY[1]

        self.rect = Rect(left, top, width, height)

# main loop
while not finished:
    for event in pygame.event.get():
       # events, and creation:
       # ... your other events here ...

       elif event.type == MOUSEBUTTONDOWN:
            startXY = event.pos
            draw = True

        elif event.type ==MOUSEBUTTONUP:
            # on mouseup, create instance.
            endXY = event.pos
            oval_new = Oval(startXY, endXY)
            completedOvals.append(oval_new)

        # draw them:
        for oval in ovals:
                oval.draw()
        for oval in completedOvals:
                oval.draw()

我大多遗漏了你未完成的椭圆形。是在点击之前显示尺寸吗?

于 2012-04-15T20:54:44.537 回答