Позиции объекта Pymunk Pygame не обновляются

Попытка следующего кода с python 2.7. В основном это круг, который висит на перекладине, и яблоко, в которое можно ударить импульсом, нажав пробел. Есть и квадрат.

import time
import pygame
import pymunk
import pymunk.pygame_util
import sys

pygame.init()
screen = pygame.display.set_mode((800, 600))
clock = pygame.time.Clock()

space = pymunk.Space()
space.gravity = 0, -1000

ball_body = pymunk.Body(100, 100)
ball_body.position = 400.0, 300.0
ball_body.angular_velocity = 10.0
ball_shape = pymunk.Circle(ball_body, 15)
ball_shape.friction = 0.5
ball_shape.elasticity = 0.9
ball_shape.color = (0,0,0,0)
space.add(ball_body, ball_shape)


static_lines = [pymunk.Segment(space.static_body, (20,20), (780,20), 2),
                pymunk.Segment(space.static_body, (20,580), (780,580), 2),
                pymunk.Segment(space.static_body, (20,20), (20,580), 2),
                pymunk.Segment(space.static_body, (780,20), (780,580), 2)]

for static_line in static_lines:
    static_line.color = (255,255,255)
    static_line.elasticity = 0.9
    static_line.friction = 1

space.add(static_lines)


i = 0
prev_body = pymunk.Body(10, 10000)
prev_body.position = (300, 580)
chain_fix_point = pymunk.Body()
chain_fix_point.position = (300, prev_body.position[1])

# Another

i = 0
prev_body = pymunk.Body(10, 10000)
prev_body.position = (600, 580)
chain_fix_point = pymunk.Body()
chain_fix_point.position = (600, prev_body.position[1])

while i < 20:
    # rotation_center_body = pymunk.Body()
    # rotation_center_body.position = (400, prev_body.position[1] - 20)

    body = pymunk.Body(1, 1)
    body.position = (600, prev_body.position[1] - 10)

    line = pymunk.Circle(body, 5)
    line.elasticity = 0
    line.friction = 1
    if i == 0:
        rotation_center_joint = pymunk.PinJoint(body, chain_fix_point)
    else:
        rotation_center_joint = pymunk.PinJoint(body, prev_body)

    space.add(line, body, rotation_center_joint)

    prev_body = body

    i += 1

blob_body = pymunk.Body(5, 1)
blob_body.position = prev_body.position[0], prev_body.position[1] - 40
blob_shape = pymunk.Circle(blob_body, 20)
rotation_center_joint = pymunk.SlideJoint(blob_body, prev_body,(0,0),(0,0),0,40)
space.add(blob_body, blob_shape, rotation_center_joint)

appleimg = pygame.image.load('apple.png')


box_body = pymunk.Body(10,10000)
box_body.position = 600, 300
box_vertices = [(570, 270),(570, 330),(630,330),(630,270)]
box_shape = pymunk.Poly(box_body, box_vertices, offset=(0, 0), radius=1).create_box(box_body, size = (60,60))
box_shape.friction = 0.5
box_shape.elasticity = 0.9
box_shape.color = (255,0,0)
space.add(box_body, box_shape)


def main():
    running = True
    angle = 0;
    while running == True:
        print "game loop"
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                running = False
            if event.type == pygame.KEYDOWN:
                if event.key == pygame.K_SPACE:
                    ball_body.apply_impulse(j = (100000, 100000))

        screen.fill((0,0,0))
        pymunk.pygame_util.draw(screen, space)
        if ball_body.angle != 0:
            angle += ball_body.angular_velocity
        img = pygame.transform.rotate(appleimg, angle)
        screen.blit(img, (ball_body.position[0] - 20, 580 - ball_body.position[1]))
        pygame.display.flip()
        clock.tick(60)
        space.step(1/60)


    pygame.quit()
    quit()

main()

Игровой цикл запускается, но позиция не обновляется.

Этот код работал очень хорошо для Python 3.5. Но когда я перешел на 2.7, это не удалось.


person Saptarshi    schedule 12.12.2015    source источник


Ответы (1)


Проблема в том, что в python 2.x вы получаете 0 при делении 1 на 60 при вызове пошаговой функции, поскольку / выполняет целочисленное деление в 2.x.

Вы можете решить эту проблему, либо импортировав подразделение python 3 с помощью from __future__ import division

Или вы можете вместо этого разделить на число с плавающей запятой 1/60.0

Проверьте этот вопрос для получения дополнительной информации: В Python 2, в чем разница между '/' и '//' при использовании для деления?

person viblo    schedule 13.12.2015
comment
Просто чтобы ответить на вопросы новичка в python 1) Является ли pymunk глючным? Иногда в сильных импульсах два тела сливаются и тело, созданное первым, исчезает за вторым. 2) Кажется, что в 3.x pymunks pyglet util выдает много ошибок с целыми и плавающими операторами? Вы сталкивались с этим? Можете ли вы предложить средство? - person Saptarshi; 13.12.2015
comment
1) Это следствие того, как pymunk (и бурундук, на котором он основан) работает внутри. Это натурально. Один из способов уменьшить эффект — использовать меньший шаг. - person viblo; 13.12.2015
comment
2) Хм, это вы мне пример дайте, я могу посмотреть повнимательнее. Код рисования pyglet немного более незрелый, чем код pygame, поэтому я не удивлен. - person viblo; 13.12.2015
comment
Еще раз спасибо! По поводу 1 - буду иметь в виду. 2 - Это код -› codepad.org/H2IH85tP. На 2.7 работает отлично, а на 3.5 выдает ошибку. Предполагается, что он делает то же самое, что и код в pygame в вопросе. - person Saptarshi; 14.12.2015
comment
Я подумал о Pyglet, потому что вам нужно писать меньше кода + к этому добавляется gl. Но потом я заметил, что он использует больше памяти по сравнению с pygame. Просто изучаю все это, чтобы придумать правильную комбинацию :). - person Saptarshi; 14.12.2015
comment
У меня нет времени на расследование прямо сейчас (не могу запустить pyglet здесь), но я создал задачу в системе отслеживания проблем pymunk, чтобы отслеживать проблему: github.com/viblo/pymunk/issues/97 - person viblo; 16.12.2015
comment
Похоже, он отлично работает с только что выпущенным новым pymunk 5.0. По крайней мере, этот пример кода: gist.github.com/viblo/0b947b50323b5568af1541c5b59b87ba (пришлось сделать некоторые корректировки для обновленного API) - person viblo; 17.07.2016