How to change the cursor in Pygame to a custom image
Asked Answered
K

6

6

I have a button in my Pygame program.
Whenever my cursor is hovering over the button, I want the cursor to change to this image (but it could be any custom image), which is different from the default pointer image for Pygame:

enter image description here

I already know how to get the position of the mouse and when it is pressed. I just don't know how to change the cursor.

Krafftebing answered 12/8, 2020 at 3:11 Comment(0)
T
8

In case you want to create and use your own colorfully customized cursor from an image (and display different cursors depending on where you are in the game, e.g. in the menu or "ingame").

Here is the procedure:

  • set mouse visibility to false
  • create a customized image you want to use as cursor
  • create a rect from that customized cursor image
  • update the rects position to your (invisible) mouse position
  • draw the image at the location of the rect

Here is a short code example:

pygame.mouse.set_visible(False)
cursor_img_rect = cursor_img.get_rect()

while True:
    # in your main loop update the position every frame and blit the image    
    cursor_img_rect.center = pygame.mouse.get_pos()  # update position 
    gameDisplay.blit(cursor_img, cursor_img_rect) # draw the cursor
Tavis answered 14/8, 2020 at 8:54 Comment(0)
D
7
pygame.mouse.set_cursor()

Pygame Cursor Constant           Description
--------------------------------------------
pygame.SYSTEM_CURSOR_ARROW       arrow
pygame.SYSTEM_CURSOR_IBEAM       i-beam
pygame.SYSTEM_CURSOR_WAIT        wait
pygame.SYSTEM_CURSOR_CROSSHAIR   crosshair
pygame.SYSTEM_CURSOR_WAITARROW   small wait cursor
                                 (or wait if not available)
pygame.SYSTEM_CURSOR_SIZENWSE    double arrow pointing
                                 northwest and southeast
pygame.SYSTEM_CURSOR_SIZENESW    double arrow pointing
                                 northeast and southwest
pygame.SYSTEM_CURSOR_SIZEWE      double arrow pointing
                                 west and east
pygame.SYSTEM_CURSOR_SIZENS      double arrow pointing
                                 north and south
pygame.SYSTEM_CURSOR_SIZEALL     four pointed arrow pointing
                                 north, south, east, and west
pygame.SYSTEM_CURSOR_NO          slashed circle or crossbones
pygame.SYSTEM_CURSOR_HAND        hand

for example:
pygame.mouse.set_cursor(pygame.SYSTEM_CURSOR_HAND)
Disputant answered 29/4, 2022 at 12:51 Comment(5)
This answer doesn't fit the question. But it could be useful to other people looking to change to one of the specified cursors.Krafftebing
@Krafftebing How does it not fit the question? Looks like it does exactly what you ask for.Bombshell
@TylerH, I said it didn't fit the question because the specific cursor that I wanted (image in question) is not provided by the defaults. That being said, I did upvote this question because it did provide useful information relevant to the topic and it might be useful for people with a similar question.Krafftebing
@Krafftebing The image in your question looks like a standard pointer cursor on Windows. If you want to display a custom image instead of the standard pointer cursor, you should edit your question to clarify that; currently (and at the time NinjaAdoberGab answered it), it does not include such a requirement.Bombshell
@Bombshell It is the default on windows. But it is not a default in pygame.Krafftebing
S
2

You know: Pygame only supports black and white cursors for the system. You can load cursors in PyGame with pygame.cursors.load_xbm, Read the full article here, for more
If you wanna detect cursor hovering the item, which (100,100) to (200,200) is the item position, this is the code:

if event.type == pygame.MOUSEMOTION:
    x, y = event.pos
    if ( x in range(100,100)) and (y in range(200,200)):
        print("Hovering over the item!")
        new_cursor()
    else: default_cursor()
Sinker answered 12/8, 2020 at 5:25 Comment(2)
I still have 2 questions: 1. Is there a default pygame cursor that you can use? Since on windows if you hover over a button it is the same cursor as the one mentioned above. 2. If there is no default pygame cursor I can use how do I create my own one? The link to the manual provided doesn't explain how to do so.Krafftebing
range(100,100), do you really mean that? That's an empty iterable.Flores
F
1

def load_cursor():
    # Load your custom cursor image (128x128 pixels)
    cursor_surface = pygame.image.load('Default.png')

    # Resize to 32x32
    cursor_surface_32x32 = pygame.transform.scale(cursor_surface, (32, 32))

    # Define hotspot
    hotspot = (0, 0)  # Top-left corner as the hotspot
    
    # Create a custom cursor
    cursor = pygame.cursors.Cursor(hotspot, cursor_surface_32x32)
    
    # Set custom cursor
    pygame.mouse.set_cursor(cursor)

Flagellum answered 22/6, 2024 at 22:50 Comment(0)
M
0

One thing about blitting a custom cursor to the screen of every frame is that its position will be affected by the frame rate however small that delay is. So the exact x y coordinates of the mouse click might not line up exactly with the drawn image. If all you want is the hand cursor another option might be to add this line

pygame.mouse.set_cursor(pygame.cursors.Cursor(pygame.SYSTEM_CURSOR_HAND))
Monjo answered 8/5, 2022 at 12:28 Comment(0)
T
-1

I recommend colliding the point into the rect that the "button" is in.(collidepoint function). Or alternatively use if x in range(button x range) and x in range (button y range).

Once you do collidepoint you can set cursor visibility to False and then draw an image/ rect/ circle at the coordinates of the cursor. It will create the change the cursor effect.

Use pygame.org. It is a helpful site for pygame.

I'll show you my code for this to help you out:

# --- Libraries --- #

# Import pygame
import pygame

# INITialize pygame


pygame.init() 
# --- Window & Cursor --- #

# Open a WINDOW of size [500, 300]
window=pygame.display.set_mode([500,300]) 

# SET_VISIBLE of cursor to False
pygame.mouse.set_visible(False) 
# Set the variable cursor_size to 10
cursor_size=10


#### ---- MAIN LOOP ---- ####
running=True 
# Create a variable called running with value True
while running: 

# Loop while running



    # --- Event Loop --- #

    # Create an EVENT LOOP
    for event in pygame.event.get(): 

        # Check for the QUIT event
        if event.type==pygame.QUIT: 
            running=False 

            # Set running to False
            # ---> TEST AFTER THIS LINE <--- #



        # --- The cursor increases size while clicking --- #

        # Check if the event TYPE is MOUSEBUTTONDOWN

        if event.type==pygame.MOUSEBUTTONDOWN: 
            cursor_size=20
            # Set cursor_size to 20
            # ---> TEST AFTER THIS LINE <--- #


        # Otherwise if the event TYPE is MOUSEBUTTONUP
        elif event.type==pygame.MOUSEBUTTONUP: 
            cursor_size=10
        
 


    # GET_POSition of mouse and store it in x, y
    x,y=pygame.mouse.get_pos() 
    # ---> TEST AFTER THIS LINE <--- #



    # --- Draw --- #

    # FILL the window with WHITE
    window.fill((215,158,222)) 


    # Draw a CIRCLE of any COLOR at position (x, y)
    # with cursor_size
    pygame.draw.circle(window,(255,255,255),(x,y),cursor_size,10) 


    # FLIP the display
    pygame.display.flip() 
    # ---> TEST AFTER THIS LINE <--- #




# Turn in your Coding Exercise.
Theravada answered 28/2, 2022 at 16:53 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.