Zwei Keyboardtasten gleichzeitig

Anfängerfragen zum Programmieren mit PureBasic.
Benutzeravatar
Mok
BotHunter
Beiträge: 1484
Registriert: 26.12.2005 14:14
Computerausstattung: MSI GX780R
Intel Core i5-2410M
Nvidia GT 555M
Windows 7 Home Premium 64 bit
Wohnort:   

Zwei Keyboardtasten gleichzeitig

Beitrag von Mok »

N'Tag!

Ich mach grad ein Programm, wo ich meine (ziemlich schlechte) GraKa bis an ihre Grenzen treiben kann.
Die Funktionsweise: Mit verschiedenen Tastenn kann man verschiedene Sachen auf den Screen zeichnen oder Effekte auslösen, während oben rechts permanent die FPS angezeigt werden.
Bisher habe ich nur Space (Screen bei jedem Schleifendurchlauf mit ClearScreen(RGB(Random(255),Random(255),Random(255)) neu machen) und TAB (Zufällig ein paar 2D-Figuren zeichnen) implementiret und habe eben festgestellt, dass nicht beides gleichzeitig gemacht werden kann.
Mein Snippet:

Code: Alles auswählen

Procedure SetNew()
    
  rnd = Random(4)
  If StartDrawing(ScreenOutput())
    For Objects = 20 To (Random(100)+20)
      new = #False
      If (Random(200) % 2 = 0)
        DrawingMode(#PB_2DDrawing_Outlined)
      EndIf
      Select rnd
        Case 0:
          Box(Random(1000),Random(800),Random(30),Random(40),RGB(Random(255),Random(255),Random(255)))
        Case 1:
          Line(Random(1000),Random(800),Random(50),Random(60),RGB(Random(255),Random(255),Random(255)))
        Case 2:
          Circle(Random(1000),Random(800),Random(42),RGB(Random(255),Random(255),Random(255)))
        Case 3:
          Plot((Objects + 3),(Objects + 5),RGB(Random(255),Random(255),Random(255)))
        Case 4:
          Ellipse(Random(1000),Random(800),Random(50),Random(60),RGB(Random(255),Random(255),Random(255)))
      EndSelect
    Next
    StopDrawing()
  EndIf

EndProcedure

Procedure MyClearScreen()

  RndColorR = Random(255)
  RndColorG = Random(255)
  RndColorB = Random(255)
  ClearScreen(RGB(RndColorR,RndColorG,RndColorB))

EndProcedure

[...]

  If KeyboardPushed(#PB_Key_Tab)
    SetNew()
  ElseIf KeyboardPushed(#PB_Key_Space)
    MyClearScreen()
  Else
    ClearScreen(RGB(255,255,255))
  EndIf
MfG, Mok
Zuletzt geändert von Mok am 19.08.2009 16:50, insgesamt 1-mal geändert.
Win 7 Home Premium 64 bit | PureBasic 5.20 - x86 und x86-64 | Firefox [aktuelle stable-Version hier einfügen]
"Jeder macht irgendwann mal Fehler, darum gibt's auch Bleistifte mit Radiergummi." --Carl
Benutzeravatar
RSBasic
Admin
Beiträge: 8047
Registriert: 05.10.2006 18:55
Wohnort: Gernsbach
Kontaktdaten:

Beitrag von RSBasic »

@Mok
Wo ist die Frage?
Oder soll das ein Beispielcode für alle sein?

Falls das ein Beispielcode sein soll, dann bitte immer ein vollständiges Beispiel posten.
Aus privaten Gründen habe ich leider nicht mehr so viel Zeit wie früher. Bitte habt Verständnis dafür.
Bild
Bild
Benutzeravatar
Mok
BotHunter
Beiträge: 1484
Registriert: 26.12.2005 14:14
Computerausstattung: MSI GX780R
Intel Core i5-2410M
Nvidia GT 555M
Windows 7 Home Premium 64 bit
Wohnort:   

Beitrag von Mok »

Ui, 2 neue Probleme. Und keines davon krieg ich alleine weg :(

Problem 1: Wenn ich beide Tasten gleichzeitig drücke, wird nur die Funktion der 1. Taste ausgeführt, ich will aber, dass alle beiden Tasten-Funktionen ausgeführt werden.

Problem 2 (neu): Wenn ich TAB drücke, verschwimmt die FPS-Zahl (weil ich eben kein ClearScreen habe, weil ich soviele Objekte wie möglich zeichnen will). Ist es möglich eine klare FPS-zahl anzuzeigen, den restlichen Screen aber NICHT zu löschen?

Problem 3 (neu): Warum habe ich permanent 0 FPS? So schlecht ist meine GraKa auch wieder net...

Code: Alles auswählen

;{**********************************************
;**    xFPS                                    *
;**    (C)2009 by Wolfram 'aVoX' Weingartner   *
;}**********************************************


;-Procedures:
;
Procedure MyClearScreen()

  RndColorR = Random(255)
  RndColorG = Random(255)
  RndColorB = Random(255)
  ClearScreen(RGB(RndColorR,RndColorG,RndColorB))

EndProcedure

Procedure SetNew()
    
  rnd = Random(4)
  If StartDrawing(ScreenOutput())
    For Objects = 20 To (Random(100)+20)
      new = #False
      If (Random(200) % 2 = 0)
        DrawingMode(#PB_2DDrawing_Outlined)
      EndIf
      Select rnd
        Case 0:
          Box(Random(1000),Random(800),Random(30),Random(40),RGB(Random(255),Random(255),Random(255)))
        Case 1:
          Line(Random(1000),Random(800),Random(50),Random(60),RGB(Random(255),Random(255),Random(255)))
        Case 2:
          Circle(Random(1000),Random(800),Random(42),RGB(Random(255),Random(255),Random(255)))
        Case 3:
          Plot((Objects + 3),(Objects + 5),RGB(Random(255),Random(255),Random(255)))
        Case 4:
          Ellipse(Random(1000),Random(800),Random(50),Random(60),RGB(Random(255),Random(255),Random(255)))
      EndSelect
    Next
    StopDrawing()
  Else
    CloseScreen()
    MessageBox_(#Null,"Could Not draw To Screen","xFPS Error!",#MB_OK|#MB_ICONERROR)
    End
  EndIf

EndProcedure


;-Initializings:
;
If Not InitSprite() Or Not InitKeyboard()
  MessageBox_(#Null,"Fehler beim Initialisieren","Fehler!",#MB_OK|#MB_ICONERROR)
  End
EndIf

If Not OpenScreen(1440,900,32,"xFPS v1.00")
  MessageBox_(#Null,"Fehler beim Öffnen eines Screens","Fehler!",#MB_OK|#MB_ICONERROR)
  End
EndIf


;-Loads:
;
LoadFont(0,"Arial Black",14)


;-MAIN CODE
;
Define.w
  FPS_Timer   = ElapsedMilliseconds()
  FPS         = 0
  FPS_Counter = 0
  new = #True
  
  #R = 255
  #G = 255
  #B = 255
ClearScreen(RGB(#R,#G,#B))


;-* * * M A I N   L O O P   S T A R T * * *
;

Repeat 
  
  If StartDrawing(ScreenOutput())
    DrawingMode(#PB_2DDrawing_Transparent)
    DrawingFont(FontID(0))
    DrawText(0,0,"Current FPS: "+Str(FPS))
    DrawingFont(#PB_Default)
    DrawText(0,30,"Press ESC to exit, press TAB to set new. Press SPACE to ClearScreen permanently.")
  Else
    CloseScreen()
    MessageBox_(#Null,"Could Not draw To Screen","xFPS Error!",#MB_OK|#MB_ICONERROR)
    End
  EndIf
  StopDrawing()
  
  If ElapsedMilliseconds() > FPS_Timer + 1000
    FPS = FPS_Counter
    FPS_Counter = 0
    FPS_Timer = ElapsedMilliseconds()
  Else
    FPS_Counter = FPS_Counter + 1
  EndIf
  
  ExamineKeyboard()

  FlipBuffers(0)
    
  If KeyboardPushed(#PB_Key_Tab)
    SetNew()
  ElseIf KeyboardPushed(#PB_Key_Space)
    MyClearScreen()
  Else
    ClearScreen(RGB(#R,#G,#B))
  EndIf

Until KeyboardPushed(#PB_Key_Escape)

;-* * * M A I N   L O O P   E N D * * *
;
End
Win 7 Home Premium 64 bit | PureBasic 5.20 - x86 und x86-64 | Firefox [aktuelle stable-Version hier einfügen]
"Jeder macht irgendwann mal Fehler, darum gibt's auch Bleistifte mit Radiergummi." --Carl
Benutzeravatar
RSBasic
Admin
Beiträge: 8047
Registriert: 05.10.2006 18:55
Wohnort: Gernsbach
Kontaktdaten:

Beitrag von RSBasic »

Mit dieser Procedure kannst du die FPS ermitteln:

Code: Alles auswählen

Procedure FPS()
  Static Frame, OldTime, FPS, NewTime
  NewTime = GetTickCount_()
  If Not Frame
    OldTime = NewTime
  EndIf
  FRAME + 1
  If NewTime-OldTime > 1000
    FPS = Frame*1000/(NewTime-OldTime)
    Frame = 0
  EndIf
  ProcedureReturn FPS
EndProcedure
Aus privaten Gründen habe ich leider nicht mehr so viel Zeit wie früher. Bitte habt Verständnis dafür.
Bild
Bild
Benutzeravatar
Mok
BotHunter
Beiträge: 1484
Registriert: 26.12.2005 14:14
Computerausstattung: MSI GX780R
Intel Core i5-2410M
Nvidia GT 555M
Windows 7 Home Premium 64 bit
Wohnort:   

Beitrag von Mok »

Ich hab das mit den FPS aus einem PureBasic-Buch ("Programming 2D Scrolling Games", von Krylar aus'm englischen Forum) und es hat bisher immer gefunzt... aber ich schau mir deine Procedure mal an :)

EDIT:
Supi!
Bleibende Probleme:
Problem 1: Wenn ich beide Tasten gleichzeitig drücke, wird nur die Funktion der 1. Taste ausgeführt, ich will aber, dass alle beiden Tasten-Funktionen ausgeführt werden.

Problem 2 (neu): Wenn ich TAB drücke, verschwimmt die FPS-Zahl (weil ich eben kein ClearScreen habe, weil ich soviele Objekte wie möglich zeichnen will). Ist es möglich eine klare FPS-zahl anzuzeigen, den restlichen Screen aber NICHT zu löschen?
Win 7 Home Premium 64 bit | PureBasic 5.20 - x86 und x86-64 | Firefox [aktuelle stable-Version hier einfügen]
"Jeder macht irgendwann mal Fehler, darum gibt's auch Bleistifte mit Radiergummi." --Carl
Benutzeravatar
jojo1541
Beiträge: 431
Registriert: 15.09.2007 17:12
Wohnort: Irgendwo im Nirgendwo

Beitrag von jojo1541 »

Du könntest alle Elemente, die angezeigt werden sollen in eine Linkedlist packen und dann via

Code: Alles auswählen

;dein code (mit Clearscreen)
ForEach Sprite()
  Displaysprite(#deinsprite,x,y)
next
;dein weiterer code
;Fps noch anzeigen lassen
anzeigen lassen.
Ich verkaufe Rechtschreibfehler und jede menge GROßBUCHSTABEN. Alles unbegrenzt zu haben.
Benutzeravatar
kswb73
Beiträge: 319
Registriert: 04.02.2008 16:51
Kontaktdaten:

Beitrag von kswb73 »

Zu Problem 1. (ohne mir dem Code lange anzusehen)

Code: Alles auswählen

  If KeyboardPushed(#PB_Key_Tab)
    SetNew()
  ElseIf KeyboardPushed(#PB_Key_Space)
    MyClearScreen()
  Else
    ClearScreen(RGB(#R,#G,#B))
  EndIf
Dieser Codeausschnitt von dir ist der Hauptgrund elseif wird nur dann geprüft wenn if fehlschlug. Drückst du Tab und die Leertaste gleichzeitig so liefert KeyboardPushed(#PB_Key_Tab) immer true zurück, mit dem Resultat das elseif KeyboardPushed(#PB_Key_Space) übersprungen wird.
Bei mehreren gleichzeitigen Tastendrücken kann es auch vorkommen, das die Tastatur damit überlastet ist. Windows gibt im normalfall Beep-Töne von sich ab wenn dies der Fall ist

Zu Problem 2. Streich #PB_2ddrawing_Transparent streichst wird der Hintergrund der FPS-Zahl automatisch gefüllt. Besser wäre vielleicht sogar eine Box im Hintergrund zu zeichnen, weil du dann nicht das Problem hast Reste der alten FPS Zahl zu sehen. (Die Box muss nur den Bereich der FPS-Zahl abdecken).
Windows XP: PB 4.31, PB 4.4, PB 4.51
Open Suse 11.2: PB 4.4
Benutzeravatar
Mok
BotHunter
Beiträge: 1484
Registriert: 26.12.2005 14:14
Computerausstattung: MSI GX780R
Intel Core i5-2410M
Nvidia GT 555M
Windows 7 Home Premium 64 bit
Wohnort:   

Beitrag von Mok »

kswb73 hat geschrieben:Zu Problem 1. (ohne mir dem Code lange anzusehen)

Code: Alles auswählen

  If KeyboardPushed(#PB_Key_Tab)
    SetNew()
  ElseIf KeyboardPushed(#PB_Key_Space)
    MyClearScreen()
  Else
    ClearScreen(RGB(#R,#G,#B))
  EndIf
Dieser Codeausschnitt von dir ist der Hauptgrund elseif wird nur dann geprüft wenn if fehlschlug. Drückst du Tab und die Leertaste gleichzeitig so liefert KeyboardPushed(#PB_Key_Tab) immer true zurück, mit dem Resultat das elseif KeyboardPushed(#PB_Key_Space) übersprungen wird.
Das versteh ich. Bei folgendem (aktualisiertem) Code würde es mit vielen IFs gehen, aber es wird dadurch immer schwerer den Screen löschen zu lassen, wenn NICHTS gedrückt wird.

Code: Alles auswählen

  If KeyboardPushed(#PB_Key_Tab)
    SetNew()
  ElseIf KeyboardPushed(#PB_Key_Space)
    MyClearScreen()
  ElseIf KeyboardPushed(#PB_Key_LeftShift)
    ExploitCPUPower()
    ClearScreen(RGB(#R,#G,#B))
  Else
    ClearScreen(RGB(#R,#G,#B))
  EndIf
Win 7 Home Premium 64 bit | PureBasic 5.20 - x86 und x86-64 | Firefox [aktuelle stable-Version hier einfügen]
"Jeder macht irgendwann mal Fehler, darum gibt's auch Bleistifte mit Radiergummi." --Carl
Rebon
Beiträge: 263
Registriert: 20.05.2009 19:13

Beitrag von Rebon »

Mok hat geschrieben:

Code: Alles auswählen

  If KeyboardPushed(#PB_Key_Tab)
    SetNew()
  ElseIf KeyboardPushed(#PB_Key_Space)
    MyClearScreen()
  ElseIf KeyboardPushed(#PB_Key_LeftShift)
    ExploitCPUPower()
    ClearScreen(RGB(#R,#G,#B))
  Else
    ClearScreen(RGB(#R,#G,#B))
  EndIf
Bei mir wird es mit diesem Code auch nicht gleichzeitig dargestellt, wobei ich ExploitCPUPower() heraus nahm.
So funktioniert's bei mir:

Code: Alles auswählen

  If KeyboardPushed(#PB_Key_Space) Or KeyboardPushed(#PB_Key_Tab)
    If KeyboardPushed(#PB_Key_Space)
       MyClearScreen()
    EndIf
    If KeyboardPushed(#PB_Key_Tab)
       SetNew()
    EndIf
  Else
    ClearScreen(RGB(#R,#G,#B))
  EndIf
PB 4.00 | Windows XP Home SP3
Benutzeravatar
Mok
BotHunter
Beiträge: 1484
Registriert: 26.12.2005 14:14
Computerausstattung: MSI GX780R
Intel Core i5-2410M
Nvidia GT 555M
Windows 7 Home Premium 64 bit
Wohnort:   

Beitrag von Mok »

@Rebon:
Dran hab ich auch schon gedacht, nur wird das ziemlich aufwändig, wenn ich dann noch ein paar Funktionen hinzufüge... aber ich bin damit zufrieden :D
Win 7 Home Premium 64 bit | PureBasic 5.20 - x86 und x86-64 | Firefox [aktuelle stable-Version hier einfügen]
"Jeder macht irgendwann mal Fehler, darum gibt's auch Bleistifte mit Radiergummi." --Carl
Antworten