# Game Python Postgres Moving Monsters

Get Started >>

## Introduction

In this tutorial, we will continue creating a game with Python and Postgres with moving monsters as part 4 of a multi-part series of lessons where the final result will be a simple 2D graphical top-down view game like PacMan. We will use Python’s “Arcade” framework for the gaming-related features. We used PostgreSQL to read and write screen data. In part 1 we created two tables for that. In this lesson we will add: placing enemy Sprites on the screen and moving them using the random function. In the next lesson, we’ll learn how to address collisions in the game.

## Prerequisites

See part 1 through 3, where we learned how to draw a screen, create tables in Postgres for storing and reading screen data and screen objects as Sprites, and reading the arrow keys to control player movement: Create game with Python and Postgres Part 1. For this lesson we will be using much of what we learned in part 1 through 3.

## Random game enemy movement

Our goal is to create two enemies that move around the screen mostly randomly. First, we’ll use the random() function to get a random direction out of eight directions, which includes left, right, up, down, and the diagonal directions. then – in a future article – we’ll add a different random check – after the left/right/etc calculation – to possibly nudge the enemy toward the player. Later, if we choose to give the game variable difficulty level, that would influence the probability of the enemy moving toward the player, as well as enemy speed of movement.

### Python random example

 123 import random x = random.random() print (x)

Run the above code and you will get the following output, which is a random floating number between 0.0000000 and 0.9999999:

 1 0.35781

Now, if you don’t want to go through the hassle of converting that to an integer in the range you want, you can use the randint function like so:

 1234 import random for y in range (0,4):     x = random.randint(1, 6)     print (x + ", ")

Output:

 1 3, 1, 4, 6

NOTE: The parameters in the roundint function are inclusive, meaning, as you can see from the output above, 1 and 6 are both included as potential output numbers.

Also of note: Numbers generated via the above random functions will produce “pseudo-random” numbers, as there will be patterns. Do NOT use these functions for security-related applications. For those, we recommend looking at the “secrets” library. We are using the random library because it is faster and we do not need FULL randomness here.

Finally, one way to influence how truly random the random functions above are is to use the random.seed function to “seed” the random functions with a value, so as to disrupt patterns. If random.seed is not used, the system time is used as a seed.

Now we will move into the graphics aspect of our tutorial. We will be repeating some of the lessons from previous articles in this series, for purposes of ease and continuity but with changes.

We’ll begin with creating a simple window and then adding one Sprite to that window.

We encourage you to play with the above example until you feel confident you understand the various arcade functions outlined in it. You can change various parameters, add a for loop to move the player in a line or along a path defined by a sin function, for example. Once you feel comfortable with those functions, continue on with the lesson.

## Get screen from PostgreSQL

To get screen and object positions and function from the database, we’ll use a database. Please refer to part 1 in this series for the CREATE TABLE we used for both PostgreSQL tables. Why two? Tbl_screens will have a row per screen, while tbl_screens_objects will store all objects (player, enemies, and obstacles) using the indexed id_screen column to point up to the id column in tbl_screens.

### Postgres tables to save game screen data

Here is tbl_screens with one row of data to represent screen 1 of the game:

idt_titlet_colori_widthi_height
1Screen 01black1280720

The following diagram shows tbl_screens_objects, for storing the objects on any given screen, which all will be Sprites. This table relates via foreign key to the above table by way of the id and id_screen columns.

id_screent_obj_namet_obj_typet_obj_img_URLb_hit_possiblen_hit_awardsn_hit_damaget_hit_sound
1Playerplayerplayer.pngtrue00
1Wallobstacleblock.pngtrue00hit_block.mp3
1Treeobstaclebush-01.pngtrue00hit_bush.mp3
1Poweruppoweruppower-up.pngtrue100power-up.mp3
1Enemy01enemyenemy-01.pngtrue010explode.mp3
1Enemy02enemyenemy-02.pngtrue010explode.mp3

NOTE: For tbl_screens_objects, we are showing more columns than in previous lessons because we are doing more with the Sprites now. We also left out the “id” field because it is irrelevant to this lesson.

IMPORTANT: Here and in the database, in order to (a) reduce amount of typing; and (b) reduce size of the above diagram, for easier display, we changed “collision” to “hit”, changed “object” to “obj”, and changed “image” to “img”.

### Query PostgreSQL for screen data

We covered this part in detail in part 2 of this series, so here, we will leave out the queries and go straight to adding movement to our player sprite. That said, ALL will be in the final source code, including those queries.

## Random sprite movement

Now we will plan out the function we’ll use to handle movement of the on-screen Player enemy Sprites. As mentioned above, their movement will be “mostly” random. Let’s write some code.

[](https://gyazo.com/1b866b42b69e736c3fdb2c2b765bc8a1 “Eight directions of Sprite movement”)

 123456789101112131415161718192021 def enemyMovement(i_which_Sprite, x, y):     direction = random.randint(1, 8)     if direction == 1:         y += 1     if direction == 2:         x += 1         y += 1     if direction == 3:         x +=1     if direction == 4:         x += 1         y -= 1     if direction == 5:         y -= 1     if direction == 6:         y -= 1         x -= 1     if direction == 7:         x -= 1     if direction == 8:         x -= 1

The above function, enemyMovement, accepts three parameters:

• i_which_Sprite: Which Sprite to move.
• x: What is the current Sprite x coordinate?
• y: What is the current Sprite y coordinate?

In the previous part of this multi-article series, we learned how to reposition a Sprite, so we’ll go ahead and do that in the full source code below.