Berechnung einer Bewegung

  • Hallo
    Hab folgenden Code zurzeit:

    [autoit]

    #include <Array.au3>
    #include <GDIPlus.au3>
    #include <GUIConstantsEx.au3>
    #include <WindowsConstants.au3>
    #include <GUIConstantsEx.au3>
    #include <WindowsConstants.au3>
    #include <GDIPlus.au3>
    Opt("GUIOnEventMode", 1)
    OnAutoItExitRegister("__GDIPlus_Shutdown")

    [/autoit][autoit][/autoit][autoit]

    global const $PI = 3.1415926535
    global const $degToRad = $PI / 180

    [/autoit][autoit][/autoit][autoit][/autoit][autoit]

    _GDIPlus_Startup()

    [/autoit][autoit][/autoit][autoit]

    Global $iWidth = 400, $iHeight = 400
    $GUI_Back_Color = 0xFF000000 + 0xF0F0F0

    [/autoit][autoit][/autoit][autoit]

    $hGUI = GUICreate("", $iWidth, $iHeight)
    $hGraphic = _GDIPlus_GraphicsCreateFromHWND($hGUI)
    ;Erstmal das normale Grafik-Objekt erstellen.
    $hBitmap = _GDIPlus_BitmapCreateFromGraphics($iWidth, $iHeight, $hGraphic)
    ;Statt uns mit dem normalen Frontbuffer zufrieden zu geben, erstellen wir erstmal eine
    ;Bitmap, mit Bezug auf unser Grafikobjekt.
    $hBackbuffer = _GDIPlus_ImageGetGraphicsContext($hBitmap)
    ;Nachdem unser Bitmap erstellt ist, holen wir uns den Graphics Context. Dieser
    ;wird von uns verwendet, um darin zu zeichnen.

    [/autoit][autoit][/autoit][autoit]

    GUISetOnEvent(-3, "_Exit")
    GUIRegisterMsg($WM_PAINT, "WM_PAINT")

    [/autoit][autoit][/autoit][autoit]

    GUISetState()
    $kugel1 = _GDIPlus_BitmapCreateFromFile("kugeln/kugel.bmp")
    $kugel2 = _GDIPlus_BitmapCreateFromFile("kugeln/kugel.bmp")
    $x = 200
    $y = 200
    $reibung = 0.985
    $speed = 2
    $richtung = 90
    msgbox(0, "", xverschiebung($richtung, 10) & "&" & yverschiebung($richtung, 10))

    [/autoit][autoit][/autoit][autoit]

    While 1 * Sleep(10)
    _GDIPlus_GraphicsClear($hBackbuffer, $GUI_Back_Color)
    ; Super Radierer benutzen um alten Backbuffer zu löschen
    $speed = $speed * $reibung
    $y = $y - $speed
    _GDIPlus_GraphicsDrawImage($hBackbuffer, $kugel1, 200, Round($y, 0))
    if $speed < 0.03 Then
    msgbox(0, "ende", "ENDE")
    endif

    [/autoit][autoit][/autoit][autoit][/autoit][autoit]

    _WinAPI_RedrawWindow($hGUI, 0, 0, $RDW_INTERNALPAINT)
    ; WM_PAINT wird nur aufgerufen, wenn alle Berechnungen fertig sind!
    ; In WM_PAINT wird selbst nichts berechnet, oder gezeichnet. diese Funktion wird nur das
    ; Bitmap-Objekt in das Grafik-Objekt übertragen.
    WEnd

    [/autoit][autoit][/autoit][autoit]

    Func _Exit()
    Exit
    EndFunc ;==>_Exit

    [/autoit][autoit][/autoit][autoit]

    Func WM_PAINT()
    _GDIPlus_GraphicsDrawImageRect($hGraphic, $hBitmap, 0, 0, $iWidth, $iHeight)
    ; _GDIPlus_GraphicsDrawImageRect() überträgt den Backbuffer in den Frontbuffer.
    ; Der erste Parameter ist unser Frontbuffer (Grafik Objekt).
    ; Der zweite ist unsere Bitmap, welche ja als BackBuffer fungiert.
    ; Darauf folgt der Abschnitt den man übertragen will.
    ; i.d.R. ist es 0, 0 für X und Y koordinaten, und die GUI Breite und Höhe für
    ; Width und Height. Kommt natürlich immer drauf an, wie groß euer Grafikobjekt ist,
    ; und ob ihr den vollen Teil zeichnen wollt.
    Return $GUI_RUNDEFMSG
    EndFunc ;==>WM_PAINT

    [/autoit][autoit][/autoit][autoit]

    Func __GDIPlus_Shutdown()
    _GDIPlus_GraphicsDispose($hGraphic)
    _GDIPlus_BitmapDispose($hBitmap)
    _GDIPlus_Shutdown()
    EndFunc ;==>__GDIPlus_Shutdown

    [/autoit][autoit][/autoit][autoit]

    Func xverschiebung($grad, $strecke)
    Return Sin($grad*$degToRad)*$strecke
    endfunc
    Func yverschiebung($grad, $strecke)
    Return Cos($grad*$degToRad)*$strecke
    endfunc

    [/autoit][autoit][/autoit][autoit][/autoit]


    das ganze Grafikzeugs is erstmal unwichtig, wichtig ist die msgbox oben.
    Also bei 0 grad bewegt sich das teil 10 nach oben, bei 90 Grad kommt allerdings 10 nach rechts (was ja richtig wäre) und 4.irgendwas nach unten. was is da falsch?[MSIE_newline_end ]

  • Hallo.
    problem hat sich erstmal gelöst, dafür ist ein anderes gekommen.
    Bei kollision sollen die kugeln logischerweise abprallen.
    ich habe jetzt erstmal ein script, wobei die eine kugel bei kolidierung erstmal stehenbleibt, und die andere dann eigentlich abprallen soll.
    1. Problem: Ich weiß nicht genau was die formel ist und wie ich sie anwende.
    2. Problem: Wenn die kugel nun so schnell ist, dass sie schon NEBEN der anderen ist (halb darin) prallt sie anders ab als wenn sie sie grade erst berührt. Deswegen muss das Abprallen irgendwie anders berechnet werden, und zwar aus den beiden Flugbahnen der kugeln. Ich hab echt keine ahnung wie ich das machen sollte... Jemand vll. ne idee oder sogar ne lösung?
    Die Kugeln mal im anhang.
    Hier der derzeitige Code:

    [autoit]

    #include <Array.au3>
    #include <GDIPlus.au3>
    #include <GUIConstantsEx.au3>
    #include <WindowsConstants.au3>
    #include <GUIConstantsEx.au3>
    #include <WindowsConstants.au3>
    #include <GDIPlus.au3>
    Opt("GUIOnEventMode", 1)
    OnAutoItExitRegister("__GDIPlus_Shutdown")

    [/autoit][autoit][/autoit][autoit]

    global const $PI = 3.1415926535897932384626433832795
    global const $degToRad = $PI / 180

    [/autoit][autoit][/autoit][autoit][/autoit][autoit][/autoit][autoit]

    _GDIPlus_Startup()

    [/autoit][autoit][/autoit][autoit]

    Global $iWidth = 400, $iHeight = 400
    $GUI_Back_Color = 0xFF000000 + 0xF0F0F0

    [/autoit][autoit][/autoit][autoit]

    $hGUI = GUICreate("", $iWidth, $iHeight)
    $hGraphic = _GDIPlus_GraphicsCreateFromHWND($hGUI)
    ;Erstmal das normale Grafik-Objekt erstellen.
    $hBitmap = _GDIPlus_BitmapCreateFromGraphics($iWidth, $iHeight, $hGraphic)
    ;Statt uns mit dem normalen Frontbuffer zufrieden zu geben, erstellen wir erstmal eine
    ;Bitmap, mit Bezug auf unser Grafikobjekt.
    $hBackbuffer = _GDIPlus_ImageGetGraphicsContext($hBitmap)
    ;Nachdem unser Bitmap erstellt ist, holen wir uns den Graphics Context. Dieser
    ;wird von uns verwendet, um darin zu zeichnen.

    [/autoit][autoit][/autoit][autoit]

    GUISetOnEvent(-3, "_Exit")
    GUIRegisterMsg($WM_PAINT, "WM_PAINT")

    [/autoit][autoit][/autoit][autoit]

    GUISetState()

    [/autoit][autoit][/autoit][autoit][/autoit][autoit]

    $kugel1 = _GDIPlus_BitmapCreateFromFile("kugeln/kugel.bmp")
    $kugel2 = _GDIPlus_BitmapCreateFromFile("kugeln/kugel.bmp")
    $x1 = 200
    $y1 = 200
    $x2 = 207.5
    $y2 = 300
    $reibung = 0.985
    $speed1 = 2
    $richtung1 = 0
    $speed2 = 2
    $richtung2 = 180

    [/autoit][autoit][/autoit][autoit]

    ;msgbox(0, "", Sin($richtung*$degToRad) & "&" & Cos($richtung*$degToRad))
    ;msgbox(0, "", Cos(ACos(0)))
    ;msgbox(0, "", xverschiebung($richtung, 10) & "&" & yverschiebung($richtung, 10))

    [/autoit][autoit][/autoit][autoit]

    While 1 * Sleep(1)

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_GraphicsClear($hBackbuffer, $GUI_Back_Color)

    [/autoit][autoit][/autoit][autoit]

    $speed1 = $speed1 * $reibung
    $speed2 = $speed2 * $reibung
    $x1 = $x1 + xverschiebung($richtung1, $speed1)
    $y1 = $y1 + yverschiebung($richtung1, $speed1)
    $x2 = $x2 + xverschiebung($richtung2, $speed2)
    $y2 = $y2 + yverschiebung($richtung2, $speed2)
    _GDIPlus_GraphicsDrawImage($hBackbuffer, $kugel1, Round($x1), Round($y1))
    _GDIPlus_GraphicsDrawImage($hBackbuffer, $kugel1, Round($x2), Round($y2))
    if entfernung($x1, $y1, $x2, $y2) < 15 Then
    $speed1 = 0
    $t = richtung($x2, $y2, $x1, $y1)
    $ew = $t-$richtung2
    $richtung2 = $ew*2+180
    msgbox(0, "", $ew)
    EndIf

    [/autoit][autoit][/autoit][autoit][/autoit][autoit]

    #cs
    ; Super Radierer benutzen um alten Backbuffer zu löschen
    $speed = $speed * $reibung
    $y = $y - $speed
    _GDIPlus_GraphicsDrawImage($hBackbuffer, $kugel1, 200, Round($y, 0))
    if $speed < 0.03 Then
    msgbox(0, "ende", "ENDE")
    endif
    #ce

    [/autoit][autoit][/autoit][autoit]

    _WinAPI_RedrawWindow($hGUI, 0, 0, $RDW_INTERNALPAINT)
    ; WM_PAINT wird nur aufgerufen, wenn alle Berechnungen fertig sind!
    ; In WM_PAINT wird selbst nichts berechnet, oder gezeichnet. diese Funktion wird nur das
    ; Bitmap-Objekt in das Grafik-Objekt übertragen.
    WEnd

    [/autoit][autoit][/autoit][autoit]

    Func _Exit()
    Exit
    EndFunc ;==>_Exit

    [/autoit][autoit][/autoit][autoit]

    Func WM_PAINT()
    _GDIPlus_GraphicsDrawImageRect($hGraphic, $hBitmap, 0, 0, $iWidth, $iHeight)
    ; _GDIPlus_GraphicsDrawImageRect() überträgt den Backbuffer in den Frontbuffer.
    ; Der erste Parameter ist unser Frontbuffer (Grafik Objekt).
    ; Der zweite ist unsere Bitmap, welche ja als BackBuffer fungiert.
    ; Darauf folgt der Abschnitt den man übertragen will.
    ; i.d.R. ist es 0, 0 für X und Y koordinaten, und die GUI Breite und Höhe für
    ; Width und Height. Kommt natürlich immer drauf an, wie groß euer Grafikobjekt ist,
    ; und ob ihr den vollen Teil zeichnen wollt.
    Return $GUI_RUNDEFMSG
    EndFunc ;==>WM_PAINT

    [/autoit][autoit][/autoit][autoit]

    Func __GDIPlus_Shutdown()
    _GDIPlus_GraphicsDispose($hGraphic)
    _GDIPlus_BitmapDispose($hBitmap)
    _GDIPlus_Shutdown()
    EndFunc ;==>__GDIPlus_Shutdown

    [/autoit][autoit][/autoit][autoit]

    Func xverschiebung($grad, $strecke)
    if $grad = 180 OR $grad = 360 Then
    return 0
    endif
    Return Sin($grad*$degToRad)*$strecke
    endfunc
    Func yverschiebung($grad, $strecke)
    if $grad = 90 OR $grad = 270 Then
    return 0
    endif
    Return Cos($grad*$degToRad)*$strecke
    endfunc

    [/autoit][autoit][/autoit][autoit]

    func entfernung($x1, $y1, $x2, $y2)
    Return Sqrt((($x1-$x2)^2)+(($y1-$y2)^2))
    EndFunc

    [/autoit][autoit][/autoit][autoit]

    func richtung($x1, $y1, $x2, $y2)
    $atan = ATan(($x1-$x2)/($y1-$y2))/$degToRad
    $vor = ""
    if $x1 < $x2 Then
    if $y1 < $y2 Then
    return $atan
    Else
    return 180 + $atan
    endif
    Else
    if $y1 < $y2 Then
    return 360 + $atan
    Else
    return 180 + $atan
    endif
    endif
    endfunc

    [/autoit][autoit][/autoit][autoit][/autoit]

    [MSIE_newline_end ]

  • Gut, danke für den tipp.
    Hat denn noch jemand ne idee zu meinem problem?[MSIE_newline_end ]

  • Hab mir die Funktion "KollisionReaktionKugeln" mal angeguckt. allerdings sind daso viele Variablen und mit drehung undso, da blick ich nicht wirklich durch...
    kann mir die ganze engine vieleicht ein Profi kurz umschreiben nur auf Kugeln, und ohne den ganzen schnickschnack?
    wäre nett, ich blick da echt nicht durch bei den ganzen variablen...[MSIE_newline_end ]