0

私はスヌーカー ゲームのコーディングをしていて、ボールを互いに衝突させる方法を理解する最善の方法は、別のプログラムでそれを行い、それをコピーすることだと判断しました。私は非常に有能な数学者なので、座って、イベントを描き、実際に何が起こっているかを計算しました.

私のアプローチは、各ボールの初速度を xr 成分と yr 成分に分解することです。xr 成分は各ボールの中心を通るベクトルと一致し、yr 成分はそれに垂直な座標系です。これ。次に、ボールの xr コンポーネントの単純な切り替えを行い、yr コンポーネントはそのままにして、速度の x および y コンポーネントが標準参照フレームに戻るかを計算します。

なんらかの理由で、数学またはプログラミングのエラーによるものであるかどうかにかかわらず、私はそれを機能させることができないようです. 以下は私がこれまでに持っていたもので、インターネット上で見つけることができるほぼすべての関連ページと、このサイトで尋ねられたすべての同様の質問に目を通しました. 私も正確に精通したプログラマーではありません。

from visual import *

dt = 0.01
r = 5

red = sphere(pos=(-25,25,0),radius = r,color=color.red)
green = sphere(pos=(25,-25,0),radius = r,color=color.green)


red.velocity = vector(10,-10,0)
green.velocity = vector(-10,10,0)


def posupdate(ball):

        ball.pos = ball.pos + ball.velocity*dt


def ballhit(ball1,ball2):

        v1 = ball1.velocity
        v1x = ball1.velocity.x
        v1y = ball1.velocity.y
        v2 = ball2.velocity
        v2x = ball2.velocity.x
        v2y = ball2.velocity.y
        xaxis = vector(1,0,0)

        btb = ball2.pos - ball1.pos
        nbtb = btb/abs(btb)

        if abs(btb) < 2*r:
                phi = acos(dot(nbtb,xaxis)/abs(nbtb)*abs(xaxis))
                ang1 = acos(dot(v1,xaxis)/abs(v1)*abs(xaxis))
                ang2 = acos(dot(v2,xaxis)/abs(v2)*abs(xaxis))

                v1xr = abs(v1)*cos((ang1-phi))
                v1yr = abs(v1)*sin((ang1-phi))
                v2xr = abs(v2)*cos((ang2-phi))
                v2yr = abs(v2)*sin((ang2-phi))

                v1fxr = v2xr
                v2fxr = v1xr
                v1fyr = v1yr
                v2fyr = v2yr

                v1fx = cos(phi)*v1fxr+cos(phi+pi/2)*v1fyr
                v1fy = sin(phi)*v1fxr+sin(phi+pi/2)*v1fyr
                v2fx = cos(phi)*v2fxr+cos(phi+pi/2)*v2fyr
                v2fy = sin(phi)*v2fxr+sin(phi+pi/2)*v2fyr

                ball1.velocity.x = v1fx
                ball1.velocity.y = v1fy
                ball2.velocity.x = v2fx
                ball2.velocity.y = v2fy

        return ball1.velocity, ball2.velocity


while 1==1:

        rate(100)

        posupdate(red)
        posupdate(green)
        ballhit(red,green)

ご協力いただきありがとうございます。

編集: 衝突検出は問題ではなく、衝突後のボールの速度ベクトルの計算だけです。申し訳ありませんが、私はそれを明確にするべきでした。

4

1 に答える 1

0

ビリヤードの物理学をチェックしてください:

運動量保存が適用され、非弾性衝突を仮定すると、運動エネルギーが保存されます。したがって、次のベクトル方程式が得られます (添字 _0 と _1 は衝突の前後を示します)。

m1*v1_0 + m2*v2_0 = M1*v1_1 + m2*v2_1

0.5*m1*v1_0**2 + 0.5*m2*v2_0**2 = 0.5*m1*v1_1**2 + 0.5*m2*v2_1**2

通常、m1 == m2 であるため、これらは次のように単純化されます。

v1_0 + v2_0 = v1_1 + v2_1

v1_0**2 + v2_0**2 = v1_1**2 + v2_1**2
于 2016-04-08T07:08:39.703 に答える