kennt sich wirklich keiner mit Physik aus?

Übersicht BlitzBasic Allgemein

Neue Antwort erstellen

EPS

Betreff: kennt sich wirklich keiner mit Physik aus?

BeitragFr, März 26, 2004 2:45
Antworten mit Zitat
Benutzer-Profile anzeigen
Hallo, ja ich schon wieder. Ich hab das Proggi jetzt mal etwas vereinfacht. Es handelt sich im Prinzip um eine Billardsimulation die ich im Netz gefunden habe. Diesmal fehlt hier die normale Reibung, d.h. die Kugeln geben nur Energie untereinander bei Kollision ab.

Allerdings möchte ich keine Billardsimulation, sondern ich möchte das die Bälle der Schwerkraft ausgesetzt sind. Man blickt also nicht wie beim Billard von oben auf die Szenerie, sondern von der Seite (wie bei 4 Gewinnt).

Nun zu meinem Problem. Wer kann mir sagen wie ich in diese Simulation Schwerkraft und Reibung einbauen kann. D.h. die Kugeln sollen zwar trotzdem voneinander abprallen, aber auch nach unten fallen und dort ruhig aufeinander liegen bleiben. Das ganze soll so realistisch wie möglich aussehen, ausser das die Bälle etwas unrealistisch stark voneinander abprallen (eher wie Flumminolium Very Happy ).

Ausserdem dürfen die Kugeln nicht ineinander rutschen. Ich hab es leider bisher immer noch nicht rausbekommen und hoffe jemand hat genügend Ahnung von Physik und programmieren.

Vielen Dank schon mal.

Code: [AUSKLAPPEN]
Graphics 800,600,0,2

Global Li = 100
Global Re = 700
Global Ob = 100
Global Un = 500

Global Radius# = 20

Type ball
   Field x#, y#      ;--> Position
   Field dx#,dy#      ;--> Geschwindigkeit
   Field col         ;--> Farbe
End Type

For i=0 To 40
   c.ball = New ball
   c\x = Rnd(200,600)
   c\y = Rnd(200,400)
   c\dx = Rnd(-4,4)
   c\dy = Rnd(-4,4)
   c\col = Rnd(100,255)*$10000+Rnd(100,255)*$100+Rnd(100,255)
Next


SetBuffer BackBuffer()
FPSTimer = CreateTimer(100) ;--> Frametimer
While Not KeyDown(1)

   WaitTimer (FPSTimer)

   PhysicEngine()
   RenderScreen()
   
Wend

WaitKey()
End



Function PhysicEngine()
   ;--> Wandkollision prüfen
   For c.ball = Each ball
      ;--> Wandkollision      
      If c\x<Li+Radius Then c\x=Li+Radius: c\dx=c\dx * -1
      If c\x>Re-Radius Then c\x=Re-Radius: c\dx=c\dx * -1
      If c\y<Ob+Radius Then c\y=Ob+Radius: c\dy=c\dy * -1
      If c\y>Un-Radius Then c\y=Un-Radius: c\dy=c\dy * -1
   Next
   
   ;--> Ballkollision prüfen
   For c.ball = Each ball
      For c2.ball = Each ball
            abstand# = Sqr((c2\x - c\x) ^ 2 + (c2\y - c\y) ^ 2)
            If abstand < Radius * 2 Then
               collNormalAngle# = ATan2(c2\y - c\y, c2\x - c\x)
      
               moveDist# = (Radius * 2 - abstand)
               c\x = c\x + moveDist * Cos(collNormalAngle + 180)
               c\y = c\y + moveDist * Sin(collNormalAngle + 180)
               
               c2\x = c2\x + moveDist * Cos(collNormalAngle)
               c2\y = c2\y + moveDist * Sin(collNormalAngle)
      
               nX# = Cos(collNormalAngle)
               nY# = Sin(collNormalAngle)
               a1# = c\dx * nX  +  c\dy * nY
               a2# = c2\dx * nX +  c2\dy * nY
      
               Abprall# = (a1 - a2)
               
               c\dx = c\dx - (Abprall * nX)
               c\dy = c\dy - (Abprall * nY)
               c2\dx = c2\dx + (Abprall * nX)
               c2\dy = c2\dy + (Abprall * nY)
            End If
      Next
   Next
   
   For c.ball = Each ball
      c\x = c\x + c\dx
      c\y = c\y + c\dy
   Next
   
End Function



Function RenderScreen()
   Cls
   For c.ball = Each ball
      Color 0,0,c\col
      Oval c\x-Radius,c\y-Radius,Radius*2,Radius*2,1
   Next
   Rect Li,Ob,Re-Li,Un-Ob,0
   Flip
End Function
 

Omenaton_2

BeitragFr, März 26, 2004 11:59
Antworten mit Zitat
Benutzer-Profile anzeigen
Nur eine kurze Teilantwort (da ich mich mit 3D eigentlich nicht gut auskenne):

Schaue dir genauer das Beispielprogramm zu BlitzBasic an, wo man mit einem kleinen Wagen über eine Landschaft herumfahren kann. Das hat sehr gut Gravitation drin, da paßt sich das Auto mit allen 4 Rädern an den Boden an. (Ich habe das vor 1,5 Jahren genau (4 Tage lang!) angeschaut und dann so ähnlich zu 95% neu programmiert. Jetzt kann ich mich aber an keine Details erinnern, da ich mich seit dem nicht mehr mit 3D befaßt habe. Ich weiß, aber, daß es mir Anfangs sehr schwer fiel den Code dazu richtig zu verstehen, später wurde dann alles klar. Du mußt nur Zeit investieren.)

Die Reibung kann doch kein Problem sein, einfach immer wenn die Kugel ein kleines Stück Strecke (paar Millimeter) hinterlegt die Geschwindigkeit der Kugel um einen festgelegten Reibungswert verringern.


Nachtrag:(edit)
Ich habe gerade gemerkt, daß du ein 2D Billardsimulation machen willst. Das erscheint mir nicht sehr sinnvol, aber das ist egal. Du kannst dir trotzdem das 3D Beispielprogramm anschauen und die Grundidee von dort in 2D überttragen. Das kann in 2D auch so gemacht werden.
(Die Kugel müssen immer versuchen unter den Boden zu fallen, aber solange Boden unter ihnen ist (der Tisch) können sie das nicht, wenn der Tisch nicht mehr da ist (also Loch), dann hindert sie nichts mehr daran zu fallen, was eine Veränderung der Y Koordinate bedeutet die mit einer festgelegten Fallgeschwindigkeit geschehen soll. Du brauchst also eine Art "karte" oder "Level" des Tisches, wo sich die Kugel bewegen können. Das ist wie bei einem Jump and Run Spiel mit Platformen.)
  • Zuletzt bearbeitet von Omenaton_2 am Fr, März 26, 2004 12:06, insgesamt einmal bearbeitet

Jan_

Ehemaliger Admin

BeitragFr, März 26, 2004 12:06
Antworten mit Zitat
Benutzer-Profile anzeigen
Ähm, kriege ich das Beispiel mal, in meinen Beispiel ordner ist das nicht mit drin!
between angels and insects
 

HOT-BIT

Gast

BeitragFr, März 26, 2004 12:34
Antworten mit Zitat
Hallo !

Wenn ich dich richtig verstanden habe, dann soll es so was ähnliches sein, wie das hier :

Code: [AUSKLAPPEN]

Abprall# = (a1 - a2)

c\dx = c\dx - (Abprall * nX) *0.89
c\dy = c\dy - (Abprall * nY) *0.89+.006
c2\dx = c2\dx + (Abprall * nX)*0.89
c2\dy = c2\dy + (Abprall * nY) *0.89


Einfach das mal statt dem anderen Code eingeben.

So, das ist aber nur ein Vorschlag, wie es aussehen soll.
Was du brauchst, ist eine Variable, welche die Schwerkraft darstellt. Also wie hier der Wert >0.006<.
Dieser muß natürlich im Programm dann noch auf die jeweilige Situation angepasst werden !

Hoffe, das hilft dir auf die Sprünge, Toni

BladeRunner

Moderator

BeitragFr, März 26, 2004 15:39
Antworten mit Zitat
Benutzer-Profile anzeigen
Hi EPS,
also ich hab ne Weile mit deinem alten Code herumgespielt. Der Fehler liegt (wenn ich ihn auch nicht vollständig eliminieren konnte) an zwei Stellen:
1. hüpfende Kugeln am Boden: Du prüfst ob c\y>0, hier würde ich >= prüfen, zudem kannst Du hier c\dy beeinflussen, d.h. unter einem gewissen Schwellenwert c\dy=0 setzen, dann bleibt die Kugel liegen.

2. der nicht ganz greifbare Teil lag jedoch in der Kollisionsroutine für zwei Kugeln. Wenn ich hier ab einem bestimmten c\dy auf Null gesetzt hab (zB c\dy>-1 and c\dy<1) bleiben die Kugeln zwar recht ruhig liegen, verlieren aber jegliche Elastizität.

Bin also auch noch nit viel schlauer geworden.
Mein Ansatz wär nun, bei der Gravitation nit pauschal zu erhöhen, sondern bei einer geringen c\dy zu prüfen ob unter der Kugel ein Hindernis (Boden oder andere Kugel) ist und nur dann Erdanziehung auszuüben.

Hoffe ich konnte das Ganze vermitteln,
Gruß BladeRunner
Zu Diensten, Bürger.
Intel T2300, 2.5GB DDR 533, Mobility Radeon X1600 Win XP Home SP3
Intel T8400, 4GB DDR3, Nvidia GF9700M GTS Win 7/64
B3D BMax MaxGUI

Stolzer Gewinner des BAC#48, #52 & #92
 

Dreamora

BeitragFr, März 26, 2004 15:45
Antworten mit Zitat
Benutzer-Profile anzeigen
Eine Idee wäre, dass du mal in die Tokamak Kolli DLL reinschmöckerst bzw. den wrapper dafür. Denke die sollte in der Lage sein den gewünschten Effekt zu erreichen Smile

Weil selbst programmieren setzt schon ein sehr tiefgreifendes Verständnis von effizienter Programmierung und Physik voraus. Das ist leider nicht einfach mal "solange das mach das" Programmierung.

EPS

BeitragFr, März 26, 2004 20:28
Antworten mit Zitat
Benutzer-Profile anzeigen
erst mal vielen Dank für eure Ideen und Antworten.

@Omenaton_2 Erstens, ja es ist 2D und zweitens es soll KEIN Billard werden !!!

@HOT-BIT So habe ich es schon getestet und es funktioniert nicht. Grund: Wenn nur so wenige Kugeln da sind, das alle den Boden berühren können, dann funzt es. Wenn aber Kugeln auf anderen Kugeln zum Liegen kommen sollen, versagt das ganze wegen der Kollision zwischen den Kugeln und deren Kraftverteilung.

@BladeRunner Gute Ansätze, aber auch das hatte ich schon mal getestet. Das Problem ist dann nicht nur der Verlust der Elastizität, sondern auch ein nicht mehr realistisches Verhalten der Bälle wenn ihre Bewegung sehr langsam ist. Als Beispiel: Wenn eine Kugel auf ner anderen liegt und nur noch sehr langsam ist, also unter den Schwellenwert kommt, dann bleibt sie an unmöglichen Positionen liegen und rollt nicht mehr runter - was sie eigentlich tun sollte.

@Dreamora ist die Tokamak DLL nicht nur für Blitz3D? Ich hab leider nur Blitz2D und kenn mich mit 3D auch nicht wirklich aus.

tja, ist schon ne knifflige Sache. Bin weiterhin für jede Idee dankbar.

Vielleicht ist ja auch mein Ansatz völlig verkehrt. Ich könnte mir vorstellen das es unmöglich ist aus ner Billard Engine eine zu machen in der Schwerkraft vorkommt.

Möglicherweise hat jemand nen anderen Vorschlag wie an die Sache ranzugehen ist.

TheShadow

Moderator

BeitragFr, März 26, 2004 21:46
Antworten mit Zitat
Benutzer-Profile anzeigen
hm - dein code ist noch zu einfach und berücksichtigt fast gar nix...

das ganze ist auch recht umfangreich

http://www.stud.fh-hannover.de..._1_PPT_97/

du kannst nicht alles berücksichtigen...

http://www.stud.fh-hannover.de...sld294.htm
http://www.stud.fh-hannover.de...sld335.htm
http://www.stud.fh-hannover.de...sld336.htm
http://www.stud.fh-hannover.de...sld337.htm
http://www.stud.fh-hannover.de...sld338.htm
http://www.stud.fh-hannover.de...sld339.htm
http://www.stud.fh-hannover.de...sld340.htm
http://www.stud.fh-hannover.de...sld341.htm
http://www.stud.fh-hannover.de...sld342.htm
AMD64 3500+ | GeForce6600GT 128MB | 1GB DDR | WinXPsp2

stfighter01

BeitragFr, März 26, 2004 22:33
Antworten mit Zitat
Benutzer-Profile anzeigen
schwerkraft und reibung sind kein problem.

schwerkraft:
zähle zu dy immer einen konstanten wert (beschleunigung) dazu bei jedem durchlauf
z.b.:
c\dy= c\dy+schwerkraft

dadurch wird die geschwindigkeit nach unten immer grösser und die kugel beschleunigt nach unten.

reibung:
ist etwas schwerer aber auch kein problem.
reibung ist eine konstante kraft die immer GEGEN die bewegungsrichtung arbeitet.
und aus beschleunigung= kraft / masse kannnst du die die brems beschleunigung deiner bälle ausrechnen.

dxr = reibung in x
dyr = reibung in y
reibbeschleunigung= kraft/masse = irgend ein wert (relativ klein)

dxr= - (dx / abs(dx) * reibbeschleunigung)
dyr= - (dy / abs(dy) * reibbeschleunigung)

edit--
um ein zittern der stillstehenden bälle zu vermeiden solltest du noch abfragen:

if abs(dx) < abs(dxr)
dxr= -dx
endif

und auch in y richtung

edit ende--


dx= dx+dxr
dy= dy+dyr


zum ruhig liegenbleiben:
bei dy < schwerkraft einfach nicht mehr zu y dazuzählen


was dein problem mit ineinaderrutschen der kugeln betrifft so kann ich dir gleich sagen das das eine verdammt harte nuss ist, und nur mit grossem aufwand zu berkstelligen ist
an deiner stelle würde ich einfach die berechnungsschritte verkürzen, dann kommt ein ineinanderrutschen so gut wie nicht zustande.

noch kurz zu codeoptimierung:
verwende kein sqr(), das ist ne ziemlich langsame funktion
besser ist du vergleichst direkt die quadrate

abstand= (c2\x - c\x) ^ 2 + (c2\y - c\y) ^ 2

und

if abstand < (radius*2) ^ 2
.
.
.
endif


mfg stfighter
Denken hilft!

EPS

BeitragSa, März 27, 2004 3:31
Antworten mit Zitat
Benutzer-Profile anzeigen
vielen Dank nochmals

@stfighter01 hab das ganze jetzt mal reingehämmert. Das mit der Reibung und der Schwerkraft funkioniert auch, aber das Zappeln bleibt trotzdem.

Verdammter Mist, wer hätte gedacht das das so kompliziert ist. Ich glaub ich lass das lieber mit der Spielidee bis ich mal Blitz3D und ne anständige Physik Engine habe.

Aber trotzdem vielen Dank euch allen.

Vielleicht sollte man aus diesem Problem mal einen Programmierwettbewerb machen. Wink

Ctuchik

BeitragSa, März 27, 2004 15:21
Antworten mit Zitat
Benutzer-Profile anzeigen
Das eigentlich Problem, bei der Sache ist ja, dass man nicht nur die Kollision zwischen 2 Kugeln betrachten darf, man muss auch Kollsionen zwischen mehreren Kugeln betrachten!
Damit sie nicht ineinander rutschen muss man sie außerdem im Falle einer Kollison genau auf Kollisionsdistanz zurückbewegen, was auch nicht einfach umzusetzen ist (zumindest komm ich nicht drauf)!
Also das ganze ist schon höchstkompliziert!

mfG Ctuchik
 

Omenaton_2

BeitragSa, März 27, 2004 18:46
Antworten mit Zitat
Benutzer-Profile anzeigen
stfighter01 hat Folgendes geschrieben:
schwerkraft und reibung sind kein problem.

schwerkraft:
zähle zu dy immer einen konstanten wert (beschleunigung) dazu bei jedem durchlauf
z.b.:
c\dy= c\dy+schwerkraft

dadurch wird die geschwindigkeit nach unten immer grösser und die kugel beschleunigt nach unten.



Ja, nur vergiß nicht, daß sobald ein bestimmter Wert für die Fallgeschwindigkeit erreicht ist, diese Geschwindigkeit beibehalten, da bei freiem Fall das objekt sich während des Falls nicht beschleunigt. Der fällt mit konstanter Geschwindigkeit.

Neue Antwort erstellen


Übersicht BlitzBasic Allgemein

Gehe zu:

Powered by phpBB © 2001 - 2006, phpBB Group