Gedrehtes Rechteck ziehen

Übersicht BlitzBasic Allgemein

Neue Antwort erstellen

das wurgel

Betreff: Gedrehtes Rechteck ziehen

BeitragSa, Mai 15, 2010 19:04
Antworten mit Zitat
Benutzer-Profile anzeigen
Moin

Ich habe grad ne kleine Denksperre. Ich möchte mit der Maus ein gedrehtes Rechteck ziehen. Vorgegeben sind also ein Winkel und zwei Punkte. Was ich brauche sind die X- und Y-Koordinate des Rechtecks, sowie die Höhe und Breite. Das Rechteck wird mit SetRotation und DrawRect in BMax gezeichnet, es dreht sich also um die linke obere Ecke im Uhrzeigersinn. Das Rechteck soll in jede Richtung ziehbar sein und genau da harkts bei mir. Bitte um Hilfe.
1 ist ungefähr 3

Holzchopf

Meisterpacker

BeitragSa, Mai 15, 2010 19:32
Antworten mit Zitat
Benutzer-Profile anzeigen
Ich würde das so machen: Den Vektor Punkt 1 - Punkt 2 (Maus) auf die Vektoren Seite 1 und Seite 2 projizieren (Stichwort Skalarprodukt), um die Höhe resp. Breite zu erhalten. Alles andere (Drehwinkel und Startpunkt) sind ja vorgegeben.

mfG
Holzchopf
Erledige alles Schritt um Schritt - erledige alles. - Holzchopf
CC BYBinaryBorn - Yogurt ♫ (31.10.2018)
Im Kopf da knackt's und knistert's sturm - 's ist kein Gedanke, nur ein Wurm

das wurgel

BeitragSa, Mai 15, 2010 19:48
Antworten mit Zitat
Benutzer-Profile anzeigen
Das habe ich schon versucht. Das Problem ist, dass der Startpunkt nicht vorgegeben ist, da man ja keine negativen Höhen und Breiten angeben darf (, oder?) Der Startpunkt hängt also davon ab, in welche Richtung man das Rechteck zieht.

Hab hier mal zwei Vorlagen gemacht, für den Fall dass irgendein netter Mensch mir das Coden will:

BlitzBasic: [AUSKLAPPEN]
Graphics 800, 600, 16, 2
SetBuffer BackBuffer()
Local timer=CreateTimer(60)
Local zeichenwinkel#=20
Local punkt1x, punkt1y
Local punkt2x, punkt2y
While Not KeyHit(1)

If MouseHit(1) Then
punkt1x=MouseX()
punkt1y=MouseY()
EndIf
If MouseDown(1) Then
punkt2x=MouseX()
punkt2y=MouseY()
EndIf


Flip
Cls
WaitTimer timer
Wend

End

; Verhält sich wie SetRotation + DrawRect in BMax
Function Rechteck(x1, y1, w, h, winkel#)
Local x2=x1+Sin(winkel+90)*w
Local y2=y1-Cos(winkel+90)*w
Local x3=x1+Sin(winkel+90)*w-Sin(winkel)*h
Local y3=y1-Cos(winkel+90)*w+Cos(winkel)*h
Local x4=x1-Sin(winkel)*h
Local y4=y1+Cos(winkel)*h
Line x1, y1, x2, y2
Line x2, y2, x3, y3
Line x3, y3, x4, y4
Line x4, y4, x1, y1
End Function
BlitzMax: [AUSKLAPPEN]
Strict

Graphics 800, 600, 0, 60, 2

Local timer:TTimer=CreateTimer(60)
Local zeichenwinkel#=20
Local punkt1x, punkt1y
Local punkt2x, punkt2y

SetRotation zeichenwinkel
While Not (KeyHit(KEY_ESCAPE) Or AppTerminate())

If MouseHit(1) Then
punkt1x=MouseX()
punkt1y=MouseY()
EndIf
If MouseDown(1) Then
punkt2x=MouseX()
punkt2y=MouseY()
EndIf



Flip
Cls
WaitTimer timer
Wend
1 ist ungefähr 3

Holzchopf

Meisterpacker

BeitragSa, Mai 15, 2010 20:11
Antworten mit Zitat
Benutzer-Profile anzeigen
So auf die Schnelle:
BlitzMax: [AUSKLAPPEN]
Strict

Graphics 800, 600, 0, 60, 2

Local timer:TTimer=CreateTimer(60)
Local zeichenwinkel#=10
Local punkt1x, punkt1y
Local punkt2x, punkt2y
Local breite:Int, hoehe:Int

SetRotation zeichenwinkel
While Not (KeyHit(KEY_ESCAPE) Or AppTerminate())

If MouseHit(1) Then
punkt1x=MouseX()
punkt1y=MouseY()
EndIf
If MouseDown(1) Then
punkt2x=MouseX()
punkt2y=MouseY()
EndIf

' vektor seite 1 (breite)
' | cos(zeichenwinkel) |
' | sin(zeichenwinkel) |
' vektor seite 2 (hoehe)
' | cos(zeichenwinkel+90) |
' | sin(zeichenwinkel+90) |
' vektor pointer
' | (punkt2x -punkt1x) |
' | (punkt2y -punkt1y) |
breite = (punkt2x -punkt1x) *Cos(zeichenwinkel) +(punkt2y -punkt1y) *Sin(zeichenwinkel)
hoehe = (punkt2x -punkt1x) *Cos(zeichenwinkel+90) +(punkt2y -punkt1y) *Sin(zeichenwinkel+90)
DrawRect punkt1x, punkt1y, breite, hoehe

Flip 0
Cls
WaitTimer timer
Wend


Oder möchtest du, dass der Startpunkt die Mitte des Rechtecks angibt?
Erledige alles Schritt um Schritt - erledige alles. - Holzchopf
CC BYBinaryBorn - Yogurt ♫ (31.10.2018)
Im Kopf da knackt's und knistert's sturm - 's ist kein Gedanke, nur ein Wurm

mpmxyz

BeitragSa, Mai 15, 2010 20:14
Antworten mit Zitat
Benutzer-Profile anzeigen
Er möchte keine negativen Höhen-/Breitenangaben haben:
BlitzMax: [AUSKLAPPEN]
Strict

Graphics 800, 600, 0, 60, 2

Local timer:TTimer=CreateTimer(60)
Local zeichenwinkel#=20
Local punkt1x, punkt1y
Local punkt2x, punkt2y

While Not (KeyHit(KEY_ESCAPE) Or AppTerminate())

If MouseHit(1) Then
punkt1x=MouseX()
punkt1y=MouseY()
EndIf
If MouseDown(1) Then
punkt2x=MouseX()
punkt2y=MouseY()
EndIf

zeichenwinkel:+0.25
SetRotation zeichenwinkel
Local x:Float,y:Float,w:Float,h:Float
CalcRectPosition(x,y,w,h,punkt1x,punkt1y,punkt2x,punkt2y,zeichenwinkel)
DrawRect x,y,w,h

Flip
Cls
WaitTimer timer
Wend


Function CalcRectPosition(rectX:Float Var, rectY:Float Var, rectWidth:Float Var, rectHeight:Float Var, p1X:Float, p1Y:Float, p2X:Float, p2Y:Float, angle:Float)
Local tmpS:Float=Sin(angle)
Local tmpC:Float=Cos(angle)
Rem
Breitenvektor: (Cos(angle) Sin(angle))
Höhenvektor: (-Sin(angle) Cos(angle))
EndRem

Local dpX:Float=p2X-p1X 'Vektor vom Punkt 1 zum Punkt 2
Local dpY:Float=p2Y-p1Y

'Größen mit dem Skalarprodukt berechnen
rectWidth=(tmpC*dpX)+(tmpS*dpY)
rectHeight=(-tmpS*dpX)+(tmpC*dpY)

'Als Startpunkt den ersten Punkt festlegen
rectX=p1X
rectY=p1Y

'Wenn die Höhe oder die Breite negativ ist, muss der Startpunkt an eine andere Ecke wandern.
If rectWidth<0
rectX:+tmpC*rectWidth
rectY:+tmpS*rectWidth
rectWidth=-rectWidth
EndIf
If rectHeight<0
rectX:-tmpS*rectHeight
rectY:+tmpC*rectHeight
rectHeight=-rectHeight
EndIf
EndFunction

mfG
mpmxyz
Moin Moin!
Projekte: DBPC CodeCruncher Mandelbrot-Renderer

das wurgel

BeitragSa, Mai 15, 2010 20:38
Antworten mit Zitat
Benutzer-Profile anzeigen
@ Holzchopf
Ich wusste garnicht das man auch negative Höhen und Breitenwerte angeben kann. Danke!

@mpmxyz
Ja genau so wollte ich das haben. Ich bin aber kurz bevor ich deinen Beitrag gelesen habe selbst auf die Lösung gekommen. Ich saß schon seit Stunden an dem Problem, aber manchmal ist es das beste einfach ncoheinmal ganz von vorne anzufangen und sich nicht von den alten Fehlgedanken irreleiten zu lassen. Trotzdem danke und sorry das ich deine Zeit verschwendet habe.

@all
Falls es jemanden intressiert, das ist meine Lösung:
BlitzBasic: [AUSKLAPPEN]
Graphics 800, 600, 16, 2
SetBuffer BackBuffer()
Local timer=CreateTimer(60)
Local zeichenwinkel#=20
Local punkt1x, punkt1y
Local punkt2x, punkt2y
While Not KeyHit(1)

If MouseHit(1) Then
punkt1x=MouseX()
punkt1y=MouseY()
EndIf
If MouseDown(1) Then
punkt2x=MouseX()
punkt2y=MouseY()
EndIf


Local winkel#=ATan2(punkt2x-punkt1x, punkt2y-punkt1y)+zeichenwinkel
Local abstand#=Sqr((punkt2x-punkt1x)^2+(punkt2y-punkt1y)^2)
Local w=Sin(winkel)*abstand
Local h=Cos(winkel)*abstand
Local x=punkt1x, y=punkt1y
If w<0 Then
w=-w
x=x-Sin(zeichenwinkel+90)*w
y=y+Cos(zeichenwinkel+90)*w
EndIf
If h<0 Then
h=-h
x=x+Sin(zeichenwinkel)*h
y=y-Cos(zeichenwinkel)*h
EndIf

Rechteck(x, y, w, h, zeichenwinkel)

Flip
Cls
WaitTimer timer
Wend

End

; Verhält sich wie SetRotation + DrawRect in BMax
Function Rechteck(x1, y1, w, h, winkel#)

; Trotz diesen beiden Zeilen funktioniert es:
If w<0 Then w=0
If h<0 Then h=0

Local x2=x1+Sin(winkel+90)*w
Local y2=y1-Cos(winkel+90)*w
Local x3=x1+Sin(winkel+90)*w-Sin(winkel)*h
Local y3=y1-Cos(winkel+90)*w+Cos(winkel)*h
Local x4=x1-Sin(winkel)*h
Local y4=y1+Cos(winkel)*h
Line x1, y1, x2, y2
Line x2, y2, x3, y3
Line x3, y3, x4, y4
Line x4, y4, x1, y1
End Function


edit:
@mpmxyz
Ich habe mich geirrt, deine Zeit ist doch nicht verschwendet, denn deine Art es Berechnens ist genauer. Bei meiner Lösung wackeln die Ecken herum.

Neue Antwort erstellen


Übersicht BlitzBasic Allgemein

Gehe zu:

Powered by phpBB © 2001 - 2006, phpBB Group