Я пытаюсь определить, как долго клавиша удерживается нажатой, используя vPython

Пишу программу к выпускному экзамену по физике. В течение всего семестра мы использовали vPython для моделирования ситуаций, получения точных ответов и т. д. Наш последний проект — создать игру с использованием vPython, включающую некоторые типы физики.

Я решил переделать Боумена, но только с танками. Итак, у вас есть танк справа от экрана и слева от экрана со стеной посередине. Цель состоит в том, чтобы нацелить свою пушку и выстрелить с нужной скоростью, чтобы поразить танк противника. У меня есть хороший кусок программы, но я застрял на нескольких разных вещах.

Во-первых, как я могу определить время нажатия клавиши? У меня это есть, поэтому я стреляю из каждой пушки, однако я хочу иметь возможность удерживать клавишу и в зависимости от того, как долго она удерживается, тем выше будет начальная скорость.

Во-вторых, где бы я мог включить гравитацию в программу? У меня есть общее представление о том, как это сделать, но я просто не знаю, в какую функцию его поместить.

Наконец, высота стены генерируется случайным образом при каждом запуске программы. Однако иногда стена настолько мала, что ее не видно. Есть ли способ установить для этого диапазон значений?

Вот мой код:

from visual import*
from random import*

scene.autoscale=False
scene.width = 1500
scene.height = 800
scene.title='Tanks'


def moveaup(gun):
    theta=arctan(gun.axis.y/gun.axis.x)
    dtheta=.1

    if (theta<pi/2):
        theta=theta+dtheta
        if not (theta>pi/2):
            gun.axis=(cos(theta),sin(theta),0)
    else:
        gun.axis=vector(0,1,0)

def moveadown(gun):
    theta=arctan(gun.axis.y/gun.axis.x)
    dtheta=.1

    if (theta>0):
        theta=theta-dtheta
        gun.axis=(cos(theta),sin(theta),0)

def movebup(gun):
    theta=arctan(gun.axis.y/gun.axis.x)+pi
    dtheta=.1

    if (theta>pi/2):
        theta=theta-dtheta
        if not (theta<pi/2):
            gun.axis=(cos(theta),sin(theta),0)
    else:
        gun.axis=vector(0,1,0)

def movebdown(gun):
    theta=arctan(gun.axis.y/gun.axis.x)+pi
    dtheta=.1

    if (theta<pi):
        theta=theta+dtheta
        gun.axis=(cos(theta),sin(theta),0)


def shoota(gun):
    vel = vector(1,1,0)
    bullet = sphere(pos=(gun.pos.x+gun.axis.x,gun.pos.y+gun.axis.y,0),radius=(.0785),color=color.yellow)
    bullet.v = vector(0,0,0)
    bullet.v = bullet.v+vel
    bulletlist.append(bullet)


def shootb(gun):
    vel = vector(-1,1,0)
    bullet = sphere(pos=(gun.pos.x+gun.axis.x,gun.pos.y+gun.axis.y,0),radius=(.0785),color=color.green)
    bullet.v = vector(0,0,0)
    bullet.v = bullet.v+vel
    bulletlist.append(bullet)

def bulletlistupdate(bulletlist):
    dt=.01
    for a in bulletlist:
        a.pos=a.pos+a.v*dt


def checks(agun,bgun):
    if scene.kb.keys:
        key=scene.kb.getkey()
        if key=='a':
            moveaup(agun)
        if key=='s':
            moveadown(agun)
        if key=='l':
            movebup(bgun)
        if key=='k':
            movebdown(bgun)
        if key=='d':
            shoota(agun)
        if key=='j':
            shootb(bgun)


#enviroment
ground = box(pos=(0,-8,0),size=(50,5,0),color=color.red)
wall = box(pos=(0,-8,0),size=(.25,20*random(),0),color=color.red)

#playerA
abody = box(pos=(-11,-5.25,0),size=(.5,.5,0),color=color.blue)
agun = cylinder(pos=(-11,-5.1,0),axis=(.8,.8,0),radius=(.08),color=color.blue)

#playerB
bbody= box(pos=(11,-5.25,0),size=(.5,.5,0),color=color.yellow)
bgun = cylinder(pos=(11,-5.1,0),axis=(-.8,.8,0),radius=(.08),color=color.yellow)

bulletlist = []

while True:
    rate(1000)
    checks(agun,bgun)
    bulletlistupdate(bulletlist)

Любая помощь приветствуется!

Спасибо большое!


person user3071544    schedule 05.12.2013    source источник


Ответы (2)


Вы можете рассчитать время в python, используя модуль time

import time

start = time.time()
finish = time.time()
print start # 1386269106.18
print finish # 1386269111.11
print (finish - start) # 4.9276599884

Поэтому, когда игрок впервые начнет нажимать на кнопку, сэкономьте время. Затем снова сохраните время, когда игрок перестанет нажимать на кнопку. Разница между этими двумя значениями времени составляет количество секунд, в течение которых игрок удерживал кнопку.

[Изменить] Если все, что вы можете сделать, это проверить, нажата ли клавиша, вы можете получить время внутри основного цикла и вычислить dt (количество прошедшего времени):

t = time.time()
while True:
    new_t = time.time()
    dt = new_t - t
    t = new_t

    rate(1000)
    checks(agun,bgun, dt)
    bulletlistupdate(bulletlist)

Затем передайте dt в checks, и если клавиша нажата, вы знаете, что клавиша была нажата еще dt секунды, и вы можете добавить это к промежуточному итогу времени, в течение которого она была нажата.

person cstack    schedule 05.12.2013
comment
Я только знаю, как определить, была ли нажата клавиша. Я не знаю конкретных клавиш/команд. - person user3071544; 05.12.2013
comment
Обратите внимание, что VPython 6 дает вам возможность привязываться к событиям нажатия и нажатия клавиши. vpython.org/contents/docs/keyboard.html - person Sam Mussmann; 06.12.2013
comment
Хм. Должно быть что-то упущено. Только отредактировал его для агуна. pastebin.com/B1YmgCJ9 - person user3071544; 06.12.2013

Для рандома вам нужно будет ввести команду, подобную этой:

    random.randrange(5,31) #this would give you a random range between the numbers 4-30

Я не хочу делать твою домашнюю работу за тебя, потому что я не думаю, что ты просишь об этом. Я надеюсь, это поможет вам.

Мне жаль, что это должен быть правильный код для вас:

    random.randint(7,40)  # this would get you a random integer of 7-40

Прошу прощения за дезинформацию.

person Bmart15    schedule 05.12.2013
comment
Файл H:\Tanks.py, строка 88, в ‹module› h=random.randrange(8,24) AttributeError: у объекта 'builtin_function_or_method' нет атрибута 'randrange' Я не знаю, ввожу ли я его или контекст неверен, но я не могу заставить его работать. - person user3071544; 05.12.2013
comment
AttributeError: у объекта «builtin_function_or_method» нет атрибута «randint». Та же ошибка. pastebin.com/34DvTzBu - person user3071544; 06.12.2013
comment
Вы должны сделать import random вместо from random import *, и тогда этот ответ сработает. - person Sam Mussmann; 06.12.2013