I can't figure out the proper way to get the world coordinates from the mouse coords.
In issues like this: mouseWorld Coordinates Box2D there is a method: box2d.coordPixelsToWorld(x,y); but I can't find this method in the Python library for box2d.
position = pygame.mouse.get_pos()
position = ??? * ???
body.position = position
More Code for Context:
PPM = 20.0 # pixels per meter
TARGET_FPS = 60
TIME_STEP = 1.0 / TARGET_FPS
SCREEN_WIDTH, SCREEN_HEIGHT = 1280, 720 # 640, 480
# --- pygame setup ---
screen = pygame.display.set_mode((SCREEN_WIDTH, SCREEN_HEIGHT), 0, 32, display=1)
pygame.display.set_caption('Simple pygame example')
clock = pygame.time.Clock()
body = world.CreateStaticBody(
position=(i, 1),
shapes=box2d.b2PolygonShape(box=(1, 1)),
))
bodies.append(body)
colors = {
box2d.b2_staticBody: (255, 255, 255, 255),
box2d.b2_dynamicBody: (127, 127, 127, 255),
}
# --- main game loop ---
running = True
while running:
# Check the event queue
for event in pygame.event.get():
if event.type == QUIT or (event.type == KEYDOWN and event.key == K_ESCAPE):
# The user closed the window or pressed escape
running = False
screen.fill((0, 0, 0, 0))
position = pygame.mouse.get_pos()
position = ??? * ???
body.position = position
for body in bodies: # or: world.bodies
# The body gives us the position and angle of its shapes
# body
for fixture in body.fixtures:
# The fixture holds information like density and friction,
# and also the shape.
shape = fixture.shape
# Naively assume that this is a polygon shape. (not good normally!)
# We take the body's transform and multiply it with each
# vertex, and then convert from meters to pixels with the scale
# factor.
vertices = [(body.transform * v) * PPM for v in shape.vertices]
# But wait! It's upside-down! Pygame and Box2D orient their
# axes in different ways. Box2D is just like how you learned
# in high school, with positive x and y directions going
# right and up. Pygame, on the other hand, increases in the
# right and downward directions. This means we must flip
# the y components.
vertices = [(v[0], SCREEN_HEIGHT - v[1]) for v in vertices]
pygame.draw.polygon(screen, colors[body.type], vertices)
# Make Box2D simulate the physics of our world for one step.
# Instruct the world to perform a single step of simulation. It is
# generally best to keep the time step and iterations fixed.
# See the manual (Section "Simulating the World") for further discussion
# on these parameters and their implications.
world.Step(TIME_STEP, 10, 10)
# Flip the screen and try to keep at the target FPS
pygame.display.flip()
clock.tick(TARGET_FPS)
pygame.quit()
if __name__ == "__main__":
print('Done!')
EDIT: The PPM value is the amount on pixels per meter. If I divide the pygame.mouse.get_pos().x with PPM it is the correct value. But the y value is off by 3 'meters'
EDIT2: Because it is (SCREEN_HEIGHT - y) / PPM
While not familiar with Box2d for Python, but if what you are looking for is to convert mouse X,Y to world X,Y just converting the mouse x,y with the Box2d conversion factor, PIXEL_PER_METERS or whatever you use, so f.ex float PIXEL_PER_METER = 100.f; thus screenpos 1200, 600 is 12,6 in "box2d units / meters"
But the answer to how to convert mouse to world is: -if you want world in Box2d units: convert with the scaling factor -add the Camera.Offset value to the mouse x,y to get world position
Camera.MinWorld <- update this depending on what camera is focused on
Mouse.x + Camera.MinWorld.x , Mouse.y + Camera.MinWorld.y = world position
world pos to screenpos: pos.x - Camera.MinWorld.x , pos.y - Camera.MinWorld.y