4

Code:

#!/usr/bin/python

import pygame, time, sys, random, os
from pygame.locals import *
from time import gmtime, strftime

pygame.init()

w = 640
h = 400

screen = pygame.display.set_mode((w, h),RESIZABLE)
clock = pygame.time.Clock()
x = y = 100

def starting():
    basicfont = pygame.font.SysFont(None, 48)
    text = basicfont.render('Starting...', True, (255, 255, 255), (0, 0, 255))
    textrect = text.get_rect()
    textrect.centerx = screen.get_rect().centerx
    textrect.centery = screen.get_rect().centery
    screen.fill((0, 0, 255))
    screen.blit(text, textrect)

def taskbar():
    basicfont = pygame.font.SysFont(None, 24)
    taskbarrect = pygame.Rect((0, int(h-40)), (int(w), int(h)))
    text = basicfont.render(strftime("%Y-%m-%d", gmtime()), True, (0, 0, 0))
    text2 = basicfont.render(strftime("%H:%M:%S", gmtime()), True, (0, 0, 0))
    taskbarrect.blit(text, (w - 100, h - 37))
    taskbarrect.blit(text2, (w - 100, h - 17))
    pygame.display.update()

starting()
screen.fill((255,255,255))

while 1:
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            sys.exit()  
        elif event.type==VIDEORESIZE:
            w = event.dict['size'][0]
            h = event.dict['size'][1]
            screen=pygame.display.set_mode(event.dict['size'],RESIZABLE)
    taskbar()

Because I want to make my code run faster, I want to create surfaces and blit rects on top of them, so that I can do pygame.display.update(taskbarrect) and speed up my code. However, I don't know how to create multiple surfaces. I have tried taskbarrect=(xcoordinate, ycoordinate, width, length) then blitting an image or text or whatever, but trying it says tuple object has no attribute blit. Trying the method in the code (suggested by @elegent) gives 'pygame.Rect' object has no attribute 'blit'.

What am I doing wrong?

3
  • 1
    FYI, it´s hard to help you when you don´t provide us some code where the error actually happens. ;) Commented Nov 23, 2015 at 20:30
  • You don´t need to crate a new Surface; just blit the text onto the main screen (see my updated answer). Commented Nov 24, 2015 at 22:41
  • @elegent would there be much of a difference? ie how much will the fps diminish? Commented Nov 25, 2015 at 18:10

1 Answer 1

11

Pygame uses surfaces to represent any form of image. This could be either

  • your main screen Surface, which is returned by the pygame.display.set_mode() function

    myDisplay = pygame.display.set_mode((500, 300))
    
  • or created object of the pygame.Surface class:

    #create a new Surface
    myNewSurface = Surface((500, 300))
    
    #change its background color
    myNewSurface.fill((55,155,255))
    
    #blit myNewSurface onto the main screen at the position (0, 0)
    myDisplay.blit(myNewSurface, (0, 0))
    
    #update the screen to display the changes
    display.update() #or  display.flip()
    

Pygame's display.update() has a method that allows one to update only some portions of the screen by passing one object or a list of pygame.Rect objects to it. Therefore, we could also call:

myUpdateRect= pygame.Rect((500, 300), (0, 0))
display.update(myUpdateRect)

Anyway, I recommend to using the pygame.draw module to draw simple shapes like rectangles, circles and polygons onto a surface, because all of these functions return a rectangle representing the bounding area of changed pixels.

This enables you to pass this information to the update() function, so Pygame only updates the pixels of the just drawn shapes:

myDisplay = pygame.display.set_mode((500, 300))

myRect= pygame.Rect((100, 200), (50, 100))
pygame.display.update(pygame.draw.rect(myDisplay, (55, 155, 255), myRect))

Update:

def taskbar():
    basicfont = pygame.font.SysFont(None, 24)

    text = basicfont.render(strftime("%Y-%m-%d", gmtime()), True, (0, 0, 0))
    text2 = basicfont.render(strftime("%H:%M:%S", gmtime()), True, (0, 0, 0))

    screen.fill((55, 155, 255))

    screen.blit(text, (w - 100, h - 37))
    screen.blit(text2, (w - 100, h - 17))

    pygame.display.update()

Hope this helps :)

Sign up to request clarification or add additional context in comments.

3 Comments

Traceback (most recent call last): File "desktop/opsys.py", line 45, in <module> taskbar() File "desktop/opsys.py", line 27, in taskbar taskbarrect = pygame.Surface((0, int(h-40)), (int(w), int(h))) TypeError: an integer is required
@YuBinLee: As I mentioned in my answer, the constructor of a the pygame.Surface class needs a tuple representing the size (i.e. the resolution) of the surface. You want to create a pygame.Rect object: taskbarrect = pygame. Rect ((0, int(h-40)), (int(w), int(h)))
Traceback (most recent call last): File "C:\Users\chef\Desktop\opsys.py", line 45, in <module> taskbar() File "C:\Users\chef\Desktop\opsys.py", line 30, in taskbar taskbarrect.blit(text, (w - 100, h - 37)) AttributeError: 'pygame.Rect' object has no attribute 'blit'

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.