I am trying to create an inventory system in Python using the module pygame. The inventory system is similar to Minecraft. It is a slot-based inventory system, meaning that each item is attached to a slot, and can be moved around the inventory.
This is the code:
#Module that allows me to create a screen and add images to the screen
import pygame
pygame.init()
win = pygame.display.set_mode((800,600))
#Variable that will keep track of the index of what slot the player is
#selecting
selectedSlot = None
#Function that checks whether there is collision or not
def collision(x,y,x2,y2,w):
if x + w > x2 > x and y+w > y2 > y:
return True
else:
return False
#Slot Class
class slotClass:
def __init__(self,x,y):
self.x = x
self.y = y
def draw(self,win):
#Draws the slots using the x and y values
pygame.draw.rect(win,(255,0,0),(self.x,self.y,50,50))
#Uses a function to test for collision with the mouse's x and y values
if collision(self.x,self.y,mx,my,66):
global selectedSlot
pygame.draw.rect(win,(128,0,0),(self.x,self.y,50,50))
#This will set an integer value to a varaible, dependent on what the index of the element the player selecting is
selectedSlot = slotArray.index(self)
#Problem with code:
#When the following 2 lines are uncommmented, the variable selectedSlot is set to "None", regardless of whether there is collision or not
#else:
#selectedSlot = None
#Slot array
slotArray = []
#Slot information
slotCount = 9
#Populates the slotArray with the desired slotCount
while len(slotArray) != slotCount:
slotArray.append(slotClass(100+len(slotArray)*70,50))
#main loop
run = True
while run:
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
print(selectedSlot)
#Mouse x and y value to set to the vars mx and my
mx,my = pygame.mouse.get_pos()
win.fill((0,0,0))
#For every element in the slotArray, the function draw is called from the slotClass
for i in slotArray:
i.draw(win)
pygame.display.update()
pygame.quit()
How it works is I have a class, which will hold the information for each slot. Such as the x value, y value and what item is in every slot. Then I have an array, which will contain every slot instance. I also defined how many slots I want entirely.
To populate this array with the slots, I first started by constantly appending to this array of slots until it equals the desired amount of slots in each row. I multiply 55 by the number of elements in the array to spread apart the slots.
The problem I am having comes when trying to create the ability for the player to mouse over/select each slot. What I want is for the player to simply be able to hover over a slot, that slot will turn a different colour, and then the player can select an item out of said slot.
I created a collision function for that and I'm calling that function within the draw function inside the slotClass. I also have a variable called slotSelected, which keeps track of the index of the slot that the player is mousing over with/hovering over.
The problem I am experiencing is, that whenever the player hovers over a slot and then stops hovering over any slots, the slot index that I am setting still remains to be the index of the slot the player was just on. When I add an else statement to check if there is no collision with a slot, and set the var slotSelected to something like None for example (to show that the player isn't colliding with any slot) the var slotSelected is constantly set to None, regardless of whether there is collision or not. I have a print statement that prints the value of slotSelected. You'll notice that it prints the index of the slot the player is colliding with. However, when you uncomment the else statement I have contained in the slotClass, the var slotSelected will always be set to None.
Any suggestions on how to fix this?
8box works. This could be a useful clue - Reedinationerelse:;selectedSlot = Noneyour code will detect collisions, but only on the box at the far right that outputs8. I think this should be useful information for you to figure out what is going wrong - Reedinationer