Python - Will's Amazing Menu Program

Will

Senior Administrator
Staff member
Joined
Mar 4, 2012
Posts
8,197
Location
%tmp%
Sooooo... I've created a very basic menu program. At present, it is merely 3 rectangles, with choice detection.

So far, it's as basic as can be - but it took me long enough to work out that I thought I would share it. :lol: Hopefully tomorrow I'll make some further progress with it, and actually have it operating as a full functioning menu with text and images and everything.

menuv1.jpg


The code is very basic and untidy at present. Tomorrow I plan to re-write the code as OOP and expand the functionality of it. The code below isn't finished, I haven't added in any way of detecting an ENTER key event yet, but that's easy enough. Once it's added, pressing enter will use the choice variable to call the appropriate function (New, Load, Settings etc).

The overall idea is to write a decent looking menu program, which can then be implemented in larger game projects I intend on making.


Code:
# Menu Program Rectangles.


import pygame
import sys
from pygame.locals import *
pygame.init()
screen = pygame.display.set_mode((600,500))
pygame.display.set_caption("Drawing Rectangles")

pos_x = 200
pos_y = 175

black = Color('black')
white = Color('white')
blue = Color('blue')

choice = 0
        
        
def print_text(font, x, y, text, color=(255,255,255)):
    imgText = font.render(text, True, color)
    screen = pygame.display.get_surface() #req'd when function moved into MyLibrary
    screen.blit(imgText, (x,y))

font = pygame.font.Font(None, 30)



while True:

    for event in pygame.event.get():
        if event.type == QUIT: sys.exit()
        elif event.type == KEYDOWN:
            if event.key == pygame.K_DOWN:
                choice += 1
                if choice > 2: choice = 2
            elif event.key == pygame.K_UP:
                choice -= 1
                if choice < 0: choice = 0

    load = "LOAD"
    new = "NEW"

    screen.fill((black))
    
    color0 = white
    color1 = white
    color2 = white
    
    selected = ""

    keys = pygame.key.get_pressed()

    pos1 = pos_x, 150, 200, 50
    pos2 = pos_x, 210, 200, 50
    pos3 = pos_x, 270, 200, 50
    width = 4

    if choice == 0:
        color0 = blue
    elif choice == 1:
        color1 = blue
    elif choice == 2:
        color2 = blue

    
    pygame.draw.rect(screen,color0, pos1, width)
    pygame.draw.rect(screen,color1, pos2, width)
    pygame.draw.rect(screen,color2, pos3, width)


    pygame.display.update()

Tomorrow:

  • Re-write program as a class.
  • Add "Enter" functionality for selection.
  • Add text and images.
  • Try implementing it in a game.
 
I finally improved the program, it looks much better with actual words and thing. :lol:

willsmenu.jpg


New Class based code, much neater:

Code:
import sys, random, pygame
from pygame.locals import *
from MyLibrary import print_text, Point

class Main_Menu(object):
    """ A Main Menu object. """

    def __init__(self, background, screen, font):
        """Initialises Main Menu """
        self.choice = 0
        self.background = background
        self.screen = screen
        self.font = font
        self.items = ['New', 'Load', 'Settings', 'Quit']

        self.black = Color('black')
        self.white = Color('white')
        self.colors = [self.black, self.black, self.black, self.black]

    def items(self, items):
        self.items = items
        
    def check_events(self):
        """Checks for new keyboard events. """
        for event in pygame.event.get():
            if event.type == QUIT: sys.exit()
            elif event.type == KEYDOWN:
                if event.key == pygame.K_DOWN:
                    self.choice += 1
                    if self.choice >= 3: self.choice = 3
                elif event.key == pygame.K_ESCAPE:
                    sys.exit()
                elif event.key == pygame.K_UP:
                    self.choice -= 1
                    if self.choice <= 0: self.choice = 0
        self.update_colors()

    def update_colors(self):
        self.colors = [self.black, self.black, self.black, self.black]
        self.colors[self.choice] = self.white
                

    def display(self):
        self.color = self.colors[0]
        self.screen.blit(self.background, (0,0))
        self.pos = Point(50, 150)
        text = self.items[0]
        print_text(self.font, self.pos.x, self.pos.y, text, self.color)
        print_text(self.font, 300, self.pos.y, str(self.choice + 1), self.black)

        for n in range(1,4):
            color = self.colors[n]
            text = self.items[n]
            self.pos.y += 50
            print_text(self.font, self.pos.x, self.pos.y, text, color)
            

def main_menu():
    pygame.init()
    screen = pygame.display.set_mode((800,600))
    pygame.display.set_caption("Menu Test")
    font = pygame.font.Font(None, 50)
    framerate = pygame.time.Clock()
    

    bg = pygame.image.load("background.png").convert_alpha()


    menu = Main_Menu(bg,screen,font)

    while True:
        framerate.tick(30)
        ticks = pygame.time.get_ticks()

        """for event in pygame.event.get():
            if event.type == QUIT:
                sys.exit()
                
        keys = pygame.key.get_pressed()
        if keys[K_ESCAPE]: sys.exit()"""

        menu.display()
        menu.check_events()
        pygame.display.update()

        

        

main_menu()
 
Yes, I'm currently trying to make a very basic 2d Top Down RPG (hopefully, and slowly). At present trying to finish the tile display for the map/level and work on the sprites and scrolling. I'm using Pygame, so the sprites are easy enough, not sure how to scroll yet - but I'll find out soon enough.
 
You'd have to check the position of the character, there's various ways, scrolling which allows the character to ALWAYS stay in the center of the screen, scrolling which moves the screen after the character hits a certain offset from the edge of the screen which allows him to go no farther than that point within the actual game window, and scrolling which basically changes the backimage instantly when the user goes out of the window's bounds starting the character at the opposite end of the screen again like I did in my 2D TLF Breaker XNA game.

All of which rely on the character sprite/object position. Whenever a character move event is fired, this is where you place the logic on when you want to scroll or sync the background in relation to the characters movements.

Whatever way you take on, makes the method behind it differ slightly though, with the out of bounds method, the character always moves, with the screen scrolling to keep the player in the center or never let the player go past a certain bounds within the actual game window, you keep the player's on spot movement going, but from that point on the only thing that really moves is the background.

With that logic though you'd have to have the background and it's actual objects interacting with where the character is on screen at all times.
 
I think I'll try it so the character is a fixed point on screen, slightly off centre (Pokemon style). Currently, my game programs run with a while loop, and then keyboard/mouse events are the first thing checked. I'm not sure if there are better ways to do it or not, I've only been programming Python for about 2 months now.

I'll be ending up with several hundred tile bitmaps on the screen (each image is only loaded once in memory, I think), which are all then drawn to the surface. I already intend each tile to have a set of variables to interact with the player. Walls/Cliffs/Trees etc "Solid = True", so the background will already be interacting with the player to allow/prevent movement.
 
Yes that's the best way to do it is to have all your images loaded into a collection, don't dispose of them, just keep them in the heap (memory), and reference them when you need them.

Did you see my TLF Rollaway game? That's essentially the way I did the images there:

 
I saw that video, the 2D Sonic themed one looked cool as well.

I'm currently using Python IDE, IDLE to make programs. It's pretty basic compared to how some seem to look - is there any benefit to using something more advanced like Eclipse, or is it a case of "If you don't know why, you don't need it" for anything more complex?
 
Nice work, dude!

Although.... I doubt I'll ever know what a "2d Top Down RPG" is. :dsmile:

No gamer here.....

Very well done, Will.
 
The Pokemon gameboy games are probably the most famous example.
 
I saw that video, the 2D Sonic themed one looked cool as well.

I'm currently using Python IDE, IDLE to make programs. It's pretty basic compared to how some seem to look - is there any benefit to using something more advanced like Eclipse, or is it a case of "If you don't know why, you don't need it" for anything more complex?

Thanks :)

As per your question, I would say no personally, python is a fairly decent language, and it all depends on the person too, you could be a really bad C++ programmer, but a genius with C#, so then the debate, which would be better to use for that person?

Avoiding semantics though, I would still say no. I don't really like Java, some people think it's the only way to go. I have views that would argue otherwise though. For gaming, I'd say C or C++ (preferably now C++ though in today's world).
 

Has Sysnative Forums helped you? Please consider donating to help us support the site!

Back
Top