List eintrag bzw. Objekt wird nicht gelöscht?

Übersicht BlitzMax, BlitzMax NG Beginners-Corner

Neue Antwort erstellen

Sephka

Betreff: List eintrag bzw. Objekt wird nicht gelöscht?

BeitragMo, Nov 29, 2010 17:24
Antworten mit Zitat
Benutzer-Profile anzeigen
Mein Problem ist wenn Panzer kollidieren solle der schwächere gelöscht werden aber anscheinend Passiert das öfter als einmal obwohl ich gemacht hab.Wo ist der Fehler???
EDIT: Zudem löscht das Pogramm mehrere Panzer!!!!! Mad
Code: [AUSKLAPPEN]

.... ....
Tanklist.remove(T2)
              GCCollect()
.........


Code: [AUSKLAPPEN]
Global Width :Int = 1024,Height:Int = 600
Graphics Width,Height
SeedRnd MilliSecs()
'VARIABLEN
Global Number_of_Tanks:Int = 15
Global Show:Int = True
Global logY:Int = Height - 200
Global channeltext:String
Global time:Float,oltime:Float,FPS:Int
'TYPE DEKLARIEREN
Type Tank
   Field X#,Y#
   Field Dir:Int, Armor:Int=100
   Field Speed:Float=2,Size:Float=0.8
   Field ID:Int
   Field Name:String
   Field Kills:Int
   Global TankNumber=0 'Die aktuelle Zahl der Panzer 

 Method compare(other:Object)
      Local ttank:Tank
      ttank = Tank(other)
      Return kills-ttank.kills
   End Method     
End Type

Type Channellog
  Field Text:String
  Field Typ:String
  Field Endet:Float
  Field x:Float,y:Float
End Type
'_____________________________________
'BILDER
SetMaskColor 255,255,255
Global Panzer:Timage = LoadImage("Panzer.bmp",Maskedimage)
If Not Panzer Then RuntimeError("Bild kann nicht geladen werden")
SetBlend Maskblend
 
'_____________________________________



Global TankList:TList = CreateList() 'Liste machen
Global Loglist:TList = CreateList()

For Local Nr:Int = 1 To Number_of_Tanks
 Global NewTank:Tank   
   NewTank = New Tank
   
  NewTank.Armor = Rand(1,4)*10 'Erzeugt eine Zufallsbewaffnung 10,20,30,40
   NewTank.X = Rand(5,800) ;NewTank.Y = Rand(5,600)'Zufalls Startposition
   NewTank.Dir = Rand(0,360) 'Zufalls Richtung
   NewTank.Name = GenerateName(2,5)
   ListAddLast TankList,NewTank 'Gibt den neuen Panzer in die Panzerliste ein.
   Tank.TankNumber:+1 'Die Panzeranzahl wird um 1 erhöht
   NewTank.ID = Tank.TankNumber
Next   

While Not KeyDown(Key_Escape)



'EINGABE
If KeyHit(Key_S) Then Show = Not Show

'PANZER DURCHGEHEN UND LÖSCHEN,ODER NEUE RICHTUNG ZUWEISEN
   For T:Tank = EachIn TankList  'Lokale T hält jeweils den aktuellen Panzer in der Schleife
If T.ID >0 Then
  'SetColor 128,64,0 
  'DrawRect(T.X,T.Y,T.Size,T.Size)
 SetRotation T.Dir
  SetScale T.Size,T.Size
  SetColor 255,255-T.Kills*38,255-T.Kills*38
  DrawImage panzer,T.X,T.Y
  SetRotation 0
  SetScale 1,1
SetColor 255,0,0;DrawText T.Name+" ATK :"+T.Armor,T.X,T.Y-T.Size*25;SetColor 255,255,255

   
      T.X:+T.Speed*Cos(T.Dir)
      T.Y:+T.Speed*Sin(T.Dir)
     'KOLLISIONEN
      If T.X > Width-T.Size*25 Then T.Dir = Rand(0,359);T.X = Width-T.Size*25
      If T.X < T.Size*25 Then T.Dir = Rand(0,359);T.X = T.Size*25
      If T.Y > Height-T.Size*25 Then T.Dir = Rand(0,360);T.Y = Height-T.Size*25
      If T.Y < T.Size*25 Then T.Dir = Rand(0,359);T.Y = T.Size*25

     For T2:Tank = EachIn TankList'Kollision Prüfen
     
     If T.ID=T2.ID Then'Selber Kollidieren verhindern ;)
      Else
         If ImagesCollide2(panzer,T.X,T.Y,0,T.Dir,T.Size,T.Size,Panzer,T2.X,T2.Y,0,T2.Dir,T2.Size,T2.Size) = True Then
           If T.Armor < T2.Armor Then
             Tank.Tanknumber:-1
             channeltext = T2.Name + " killed " + T.Name + "!!!"
             CreateChannellog(channeltext,"kill",2000)
             T2.Kills:+1
             Tanklist.remove(T)
              GCCollect()
           ElseIf T2.Armor > T.Armor Then
             Tank.Tanknumber:-1
             channeltext = T.Name + " killed " + T2.Name + "!!!"
             CreateChannellog(channeltext,"kill",2000)
             T.Kills:+1
             Tanklist.remove(T2)
              GCCollect()
           ElseIf T2.Armor = T.Armor
             T.Dir = Rand(0,359)
             T2.Dir = Rand(0,359)
           EndIf

         End If
       End If
      Next
    End If       
   Next 'Dieser Loop wird für jeden Panzer in der Liste ausgeführt, bis zum letzten.
'Zeichnen des Restlichem Stuffs
If Show = True
   SetColor 0,255,0;DrawText "FPS: "+FPS,1,1
   SetColor 255,255,255;DrawText "Panzer: "+Tank.TankNumber,20,20
   SetBlend ALPHABLEND 'TRANSPARENZ EINSCHALTEN
   SetAlpha 0.45;SetColor 50,205,50;DrawRect 0,Height-200,300,Height-13;SetColor 255,255,255;SetAlpha 1
   SetBlend MASKBLEND  'MASKE WIEDER EINSCHALTEN
   DrawChannellog()
   ShowScore() 
End If

'FPS AUSRECHNEN
 time = MilliSecs()
  If time - oldtime <> 0 Then FPS = Int(1000 / (time - oldtime))
  If FPS = 0 Then FPS = 1
  oldtime = MilliSecs()   
'-------------------   
 UpdateChannellog()
 
 
Flip   ;Cls
Wend

'########################FUNCTIONS################################
Function GenerateName$(Mini%,Maxi%)
   Local name$, char, vowel, length
   vowel = Rand(0, 1)
   length = Rand(Mini, Maxi)
   For x = 1 To length
      vowel = Not vowel
      If vowel
         Repeat
            char = Rand(95, 122)
         Until (char <> Asc("a")) And (char <> Asc("e")) And (char <> Asc("i")) And (char <> Asc("o")) And (char <> Asc("u"))
      Else
         Select Rand(1, 5)
            Case 1
               char = 97
            Case 2
               char = 101
            Case 3
               char = 105
            Case 4
               char = 111
            Case 5
               char = 117
         End Select
     EndIf
      name = name + Chr(char)
   Next
   name= Replace(name, "q", "qu")
   name= Replace(name, Chr(96), "sch")
   name= Replace(name, Chr(95), "ch")
   name = Upper(Mid(name, 1,1)) + Mid(name,2)
   Return name
End Function

Function DrawChannellog()
For c:channellog = EachIn loglist
Select c.typ
 Case "kill"
  SetColor 178,34,34
End Select
DrawText c.text,c.x,c.y
Next
 SetColor 255,255,255
End Function

Function CreateChannellog(ctext$,ctyp$,cdauer%)'Typen : Kill
 Global Newlog:Channellog   
   Newlog = New Channellog

Newlog.Text = cText$
Newlog.Typ = ctyp$
Newlog.Endet = MilliSecs() + cdauer%
Newlog.X = 10
Newlog.Y = LogY%
LogY:+12
   ListAddLast LogList,Newlog 'Gibt den neuen log in die logliste ein.
End Function

Function UpdateChannellog()
If LogY > Height - 13 Then
loglist.removefirst()
For c:Channellog = EachIn loglist
C.Y:-12
Next
logY:-12
End If
End Function

Function ShowScore()
Tanklist.sort(False)
Local Y:Int= 20
For s:Tank = EachIn Tanklist
DrawText s.Name + ": " + s.kills,400,y
Y:+12
Next
End Function
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit
  • Zuletzt bearbeitet von Sephka am Mo, Nov 29, 2010 19:07, insgesamt einmal bearbeitet

BladeRunner

Moderator

BeitragMo, Nov 29, 2010 17:53
Antworten mit Zitat
Benutzer-Profile anzeigen
Nur einen Tipp: GCcollect() ist nicht notwendig, normalerweise arbeitet der Garbage Collector automatisch.
GCCollect ist nur nötig wenn Du den GC auf manuell schaltest. (Siehe dazu in der Doku)
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

Xeres

Moderator

BeitragMo, Nov 29, 2010 17:58
Antworten mit Zitat
Benutzer-Profile anzeigen
Bei deiner Bedingung hast du dich vertan:
Code: [AUSKLAPPEN]
 If T.Armor < T2.Armor Then

           ElseIf T2.Armor > T.Armor Then
 

Entweder du tauschst das Objekt oder das Ungleichheitszeichen. Wenn du beides macht, sind beide Bedingungen identisch.
GCCollect() musst du nicht per Hand aufrufen.
Code: [AUSKLAPPEN]
 If T.ID=T2.ID Then'Selber Kollidieren verhindern ;)
Du brauchst keine IDs - du kannst die Objekte Direkt vergleichen, und ungleich entfernt die leere Bedingung:
Code: [AUSKLAPPEN]
If T <> T2  Then
Win10 Prof.(x64)/Ubuntu 16.04|CPU 4x3Ghz (Intel i5-4590S)|RAM 8 GB|GeForce GTX 960
Wie man Fragen richtig stellt || "Es geht nicht" || Video-Tutorial: Sinus & Cosinus
T
HERE IS NO FAIR. THERE IS NO JUSTICE. THERE IS JUST ME. (Death, Discworld)

Sephka

BeitragMo, Nov 29, 2010 17:58
Antworten mit Zitat
Benutzer-Profile anzeigen
Toll funktionier Trotzdem nicht
das mit dem GCcollect war aus verzweiflung :S
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit

Sephka

BeitragMo, Nov 29, 2010 18:34
Antworten mit Zitat
Benutzer-Profile anzeigen
Ok sry.
mir scheint es ja so als wenn das Programm die objekte nicht löscht...
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit
  • Zuletzt bearbeitet von Sephka am Mo, Nov 29, 2010 18:41, insgesamt einmal bearbeitet

BladeRunner

Moderator

BeitragMo, Nov 29, 2010 18:38
Antworten mit Zitat
Benutzer-Profile anzeigen
Nicht drängeln, wenn Dir wer was zu sagen hat wird er es tun. Pushen ist nicht zulässig. Danke.
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

Sephka

BeitragMo, Nov 29, 2010 20:39
Antworten mit Zitat
Benutzer-Profile anzeigen
Ich hab jetzt noch ein bisschen getüftelt und as Problem muss sein das das Objekt erst nach ca. 5 Schleifendurchläufen gelöscht wird und so löscht das Pogramm ( wie auch immer) 5 andere Objekte.
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit

Xeres

Moderator

BeitragMo, Nov 29, 2010 20:43
Antworten mit Zitat
Benutzer-Profile anzeigen
Das Objekt mag ja noch existieren - aber wenn es nicht mehr in der Liste steht, wird nirgendwo mehr wechselwirken.
Win10 Prof.(x64)/Ubuntu 16.04|CPU 4x3Ghz (Intel i5-4590S)|RAM 8 GB|GeForce GTX 960
Wie man Fragen richtig stellt || "Es geht nicht" || Video-Tutorial: Sinus & Cosinus
T
HERE IS NO FAIR. THERE IS NO JUSTICE. THERE IS JUST ME. (Death, Discworld)

Sephka

BeitragMo, Nov 29, 2010 20:47
Antworten mit Zitat
Benutzer-Profile anzeigen
das heißt??
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit

mpmxyz

BeitragMo, Nov 29, 2010 20:48
Antworten mit Zitat
Benutzer-Profile anzeigen
Du hast die Compare-Methode geändert!
BlitzMax: [AUSKLAPPEN]
Method compare(other:Object)
Local ttank:Tank
ttank = Tank(other)
Return kills-ttank.kills
End Method

Die Listen-Objekte nutzen diese, um die Objekte voneinander unterscheiden zu können. (Bei eigenen Wert-Objekten und Strings macht das Sinn!)
Du musst darauf achten, dass der Scorevergleich in der Compare-Methode nur beim Sortieren stattfindet.
Da reicht eine globale Variable und ein If mit einem Aufruf von Super.Compare in der Methode.
("Super": Damit kann man in der Vererbungshierachie einen Schritt nach oben wandern, um z.B. die Originalmethoden von überschriebenen Methoden aufzurufen.)
mfG
mpmxyz
Moin Moin!
Projekte: DBPC CodeCruncher Mandelbrot-Renderer

Sephka

BeitragMo, Nov 29, 2010 20:52
Antworten mit Zitat
Benutzer-Profile anzeigen
Das mit Super compare versteh ich nicht habs jetzt so:
Code: [AUSKLAPPEN]
Global Width :Int = 1024,Height:Int = 600
Graphics Width,Height
SeedRnd MilliSecs()
'VARIABLEN
Global Number_of_Tanks:Int = 5
Global Show:Int = True
Global logY:Int = Height - 200
Global channeltext:String
Global time:Float,oltime:Float,FPS:Int
Global sort = False
'TYPE DEKLARIEREN
Type Tank
   Field X#,Y#
   Field Dir:Int, Armor:Int=100
   Field Size:Float=1
   Field ID:Int
   Field Name:String
   Field Kills:Int
   Global TankNumber=0 'Die aktuelle Zahl der Panzer 
   Global Speed = 1
 Method compare(other:Object)
If sort = True
      Local ttank:Tank
      ttank = Tank(other)
      Return kills-ttank.kills
End If
   End Method     
End Type

Type Channellog
  Field Text:String
  Field Typ:String

  Field x:Float,y:Float
End Type
'_____________________________________
'BILDER
SetMaskColor 255,255,255
Global Panzer:Timage = LoadImage("Panzer.bmp",Maskedimage)
If Not Panzer Then RuntimeError("Bild kann nicht geladen werden")
SetBlend Maskblend
 
'_____________________________________



Global TankList:TList = CreateList() 'Liste machen
Global Loglist:TList = CreateList()

For Local Nr:Int = 1 To Number_of_Tanks
 Global NewTank:Tank   
   NewTank = New Tank
   
  NewTank.Armor = Rand(1,4)*10 'Erzeugt eine Zufallsbewaffnung 10,20,30,40
   NewTank.X = Rand(5,800) ;NewTank.Y = Rand(5,600)'Zufalls Startposition
   NewTank.Dir = Rand(0,360) 'Zufalls Richtung
   NewTank.Name = GenerateName(2,5)
   ListAddLast TankList,NewTank 'Gibt den neuen Panzer in die Panzerliste ein.
   Tank.TankNumber:+1 'Die Panzeranzahl wird um 1 erhöht
   NewTank.ID = Tank.TankNumber
Next   

While Not KeyDown(Key_Escape)



'EINGABE
If KeyHit(Key_S) Then Show = Not Show
If KeyDown(Key_D) Then Tank.Speed=3 Else Tank.Speed=1
'PANZER DURCHGEHEN UND LÖSCHEN,ODER NEUE RICHTUNG ZUWEISEN
   For T:Tank = EachIn TankList  'Lokale T hält jeweils den aktuellen Panzer in der Schleife
If T.ID >0 Then
  'SetColor 128,64,0 
  'DrawRect(T.X,T.Y,T.Size,T.Size)
 SetRotation T.Dir
  SetScale T.Size,T.Size
  SetColor 255,255-T.Kills*38,255-T.Kills*38
  DrawImage panzer,T.X,T.Y
  SetRotation 0
  SetScale 1,1
SetColor 255,0,0;DrawText T.Name+" ATK :"+T.Armor,T.X,T.Y-T.Size*25;SetColor 255,255,255

   
      T.X:+T.Speed*Cos(T.Dir)
      T.Y:+T.Speed*Sin(T.Dir)
     'KOLLISIONEN
      If T.X > Width-T.Size*25 Then T.Dir = Rand(0,359);T.X = Width-T.Size*25
      If T.X < T.Size*25 Then T.Dir = Rand(0,359);T.X = T.Size*25
      If T.Y > Height-T.Size*25 Then T.Dir = Rand(0,360);T.Y = Height-T.Size*25
      If T.Y < T.Size*25 Then T.Dir = Rand(0,359);T.Y = T.Size*25

     For T2:Tank = EachIn TankList'Kollision Prüfen
     
     If T<>T2 Then'Selber Kollidieren verhindern ;)
      If ImagesCollide2(panzer,T.X,T.Y,0,T.Dir,T.Size,T.Size,Panzer,T2.X,T2.Y,0,T2.Dir,T2.Size,T2.Size) = True Then
           If T.Armor > T2.Armor Then
             Tank.Tanknumber:-1
             channeltext = T.Name + " killed " + T2.Name + "!!!"
             CreateChannellog(channeltext,"kill")
             T.Kills:+1
             Tanklist.remove(T2)
           
                            Exit
           ElseIf T2.Armor > T.Armor Then
             Tank.Tanknumber:-1
             channeltext = T2.Name + " killed " + T.Name + "!!!"
             CreateChannellog(channeltext,"kill")
             T2.Kills:+1
             
             Tanklist.remove(T)
             
           
              Exit
           ElseIf T2.Armor = T.Armor
             T.Dir = Rand(0,359)
             T2.Dir = Rand(0,359)
             Exit
           EndIf
         
         End If
       End If
      Next
    End If       
   Next 'Dieser Loop wird für jeden Panzer in der Liste ausgeführt, bis zum letzten.
'Zeichnen des Restlichem Stuffs
If Show = True
   SetColor 0,255,0;DrawText "FPS: "+FPS,1,1
   SetColor 255,255,255;DrawText "Panzer: "+Tank.TankNumber,20,20
   SetBlend ALPHABLEND 'TRANSPARENZ EINSCHALTEN
   SetAlpha 0.45;SetColor 50,205,50;DrawRect 0,Height-200,300,Height-13;SetColor 255,255,255;SetAlpha 1
   SetBlend MASKBLEND  'MASKE WIEDER EINSCHALTEN
   DrawChannellog()
   ShowScore() 
End If

'FPS AUSRECHNEN
 time = MilliSecs()
  If time - oldtime <> 0 Then FPS = Int(1000 / (time - oldtime))
  If FPS = 0 Then FPS = 1
  oldtime = MilliSecs()   
'-------------------   
 UpdateChannellog()
 
 
Flip   ;Cls
Wend

'########################FUNCTIONS################################
Function GenerateName$(Mini%,Maxi%)
   Local name$, char, vowel, length
   vowel = Rand(0, 1)
   length = Rand(Mini, Maxi)
   For x = 1 To length
      vowel = Not vowel
      If vowel
         Repeat
            char = Rand(95, 122)
         Until (char <> Asc("a")) And (char <> Asc("e")) And (char <> Asc("i")) And (char <> Asc("o")) And (char <> Asc("u"))
      Else
         Select Rand(1, 5)
            Case 1
               char = 97
            Case 2
               char = 101
            Case 3
               char = 105
            Case 4
               char = 111
            Case 5
               char = 117
         End Select
     EndIf
      name = name + Chr(char)
   Next
   name= Replace(name, "q", "qu")
   name= Replace(name, Chr(96), "sch")
   name= Replace(name, Chr(95), "ch")
   name = Upper(Mid(name, 1,1)) + Mid(name,2)
   Return name
End Function

Function DrawChannellog()
For c:channellog = EachIn loglist
Select c.typ
 Case "kill"
  SetColor 178,34,34
End Select
DrawText c.text,c.x,c.y
Next
 SetColor 255,255,255
End Function

Function CreateChannellog(ctext$,ctyp$)'Typen : Kill
 Global Newlog:Channellog   
   Newlog = New Channellog

Newlog.Text = cText$
Newlog.Typ = ctyp$
Newlog.X = 10
Newlog.Y = LogY%
LogY:+12
   ListAddLast LogList,Newlog 'Gibt den neuen log in die logliste ein.
End Function

Function UpdateChannellog()
If LogY > Height - 13 Then
loglist.removefirst()
For c:Channellog = EachIn loglist
C.Y:-12
Next
logY:-12
End If
End Function

Function ShowScore()
sort = True
Tanklist.sort(False)
sort = False
Local Y:Int= 20
For s:Tank = EachIn Tanklist
DrawText s.Name + ": " + s.kills,400,y
Y:+12
Next
End Function
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit

mpmxyz

BeitragMo, Nov 29, 2010 20:58
Antworten mit Zitat
Benutzer-Profile anzeigen
Hier hast du ein Beispiel zur Anwendung von Super:
BlitzMax: [AUSKLAPPEN]
  Method compare(other:Object)
If sort = True
Local ttank:Tank
ttank = Tank(other)
Return kills-ttank.kills
Else
Return Super.Compare(other) 'ruft die Compare-Methode von der "Object"-Klasse auf
End If
End Method

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

Sephka

BeitragMo, Nov 29, 2010 21:07
Antworten mit Zitat
Benutzer-Profile anzeigen
Danke da wär ich nicht drauf gekommen. Laughing Very Happy Shocked
Mein Freund und Helfer:
Win7 Home Premium SP1
AMD Athlon II X4 645 3.1GHZ
8GB Ram
64bit
 

undefined

BeitragMo, Nov 29, 2010 21:10
Antworten mit Zitat
Benutzer-Profile anzeigen
Bei der Compare-Methode muss man ansich nur darauf achten, dass:

1) der Rückgabewert immer = 0 ist, wenn das Objekt mit sich selbst verglichen wird
2) der Rückgabewert beim Vergleich mit anderen Objekten immer <> 0 ist

Es ist nicht notwendig, über einen Schalter auf Super-Compare umzuspringen!

Neue Antwort erstellen


Übersicht BlitzMax, BlitzMax NG Beginners-Corner

Gehe zu:

Powered by phpBB © 2001 - 2006, phpBB Group