Siemka, mam takie pytanko jak opóźnić przycisk, szukałem w googlach, bo mnie odbanowali, ale nie znalazlem.
Chodzi mi o to, że pod przyciskiem np. spacja mam funkcje która mi się wywoluje w wątku i ja ją opozniam przez Thread.sleep(); ale jest problem bo jak przytrzymam spacje to nabije mi tych przyciśnięć strasznie dużo a tego nie chce. Wtedy program się zawiesza, to znaczy wykonuje sie caly czas ta funkcja w odstepach czasu az sie nie skonczy liczba razów wcisnietego przycisku spacja. Ktoś wie jak pomóc?
Może odpalenie tej funkcji czy tam wątku daj dopiero po puszczeniu spacji. Dokonaj analizy ze wciśnieta spacja ale metode odpalaj gdy klawisz jest zluzowany
No wlasnie nie, to jest tak jak grasz w gre, strzelasz jak nacisniesz spacje a nie jak puscisz....
no ale to trzymając to operacja ma się powtarzać? Czy ma się nie powtarzać?
Zawsze możesz flagę jakąś ustawić aby tylko jedno wciśnięcie brał
Nie wiem czy o dokładnie o to Ci chodzi, ale kiedyś sobie napisałem paranoicznie dokładną obsługę klawiatury, która w wersji dla jednego klawisza wygląda mniej więcej tak:
//JButton przycisk - Twój przycisk do "opóźniania"
//innaKontrolka - jakaś kontrolka z focusem na klawisze
//...
private boolean pressed = false;
//...
innaKontrolka.addKeyListener(new KeyAdapter()
{
@Override public void keyPressed(KeyEvent e)
{
if(e.getKeyCode() == KeyEvent.VK_SPACE && !pressed)
{
spacePressed = true;
wciśnij(przycisk);
}
}
@Override public void keyReleased(KeyEvent e)
{
if(e.getKeyCode() == KeyEvent.VK_SPACE && pressed)
{
spacePressed = false;
puść(przycisk);
}
}
});
//...
/**
* Wizualnie wciska przycisk i wyzwala zdarzenie jego przyciśnięcia
* @param przycisk przycisk do wciśnięcia
*/
public static void wciśnij(JButton przycisk)
{
ButtonModel m = przycisk.getModel();
m.setArmed(true);
m.setPressed(true);
przycisk.paintImmediately(0, 0,
przycisk.getWidth(), przycisk.getHeight());
}
/**
* Wizualnie puszcza przycisk i wyzwala zdarzenie jego puszczenia
* @param przycisk
*/
public static void puść(JButton przycisk)
{
ButtonModel m = przycisk.getModel();
m.setPressed(false);
m.setArmed(false);
przycisk.paintImmediately(0, 0,
przycisk.getWidth(), przycisk.getHeight());
}
tutaj masz moj fragment kodu:
case KeyEvent.VK_SPACE :
if(spaceDown){
try{
fire();
Thread.sleep(300);
}
catch ( InterruptedException b) {
System.out.println("Strzał zbyt wcześnie");
}
spaceDown = false;
}
break;
chce aby funkcja fire byla opozniana, strzelam w grze z broni, w sensie strzelam z broni i nie moge strzelac ciagiem pociskow jeden za drugim co milimetr, taki spam.... tylko chce zeby bylo opoznienie, ze nie mozna strzelac czesciej niz 300 ms i teraz wstawilem flage jak widac, keyReleased daje flage na true i mamy polowe sukcesu, bo jak sie trzyma to wykonuje sie juz tylko raz ta funkcja, ale teraz znow mozna "nawalać" w spację i będzie podobny efekt do tego, gdy trzymalem spacje, znow program zapamieta jakies 1000 przycisniec i bedzie odpalal je co 300 milisekund. Rozumiecie o czym mówie i w czym problem?
Zrób sobie zmienną która przechowywać będzie odstęp czasowy pomiędzy kolejnymi wystrzeleniami.
W grze na pewno masz zaimplementowany upływający czas od ostatniej pętli.
Kiedy strzelisz zmienną ustawiasz na np. te 300; int shootTime = 300;
W każdym przebiegu pętli gry odejmujesz od tych 300 czas który upłynął shootTime-=elapsedTime;
Kiedy strzelasz ponownie sprawdzasz czy ta zmienna jest mniejsza równa 0.
if(shoot Time <=0){
strzelaj();
shootTime = 300; // z powrotem będziemy odliczać
}
nie rozumiecie albo ja was, chodzi o to, że program java nalicza mnostwo przycisniec spacji, które mialy za zadanie wykonac funkcje w odstepie czasowym i mimo ze ty juz pol godziny temu przestales naciskac spacje, to on jeszcze pamieta i strzela.
To jest gra napisana przeze mnie ;d, nie mam czegos takiego jak czas ktory uplynal od ostatniej petli, nie wiem w ogóle co to jest. Uczę się pisać gry i jestem początkujący :)
Chcę się bawić tak aby nie używac bibliotek zewnetrznych, czyli gotowych rozwiazan i wszystko stworzyc od zera po swojemu.
Wyobraź sobie, ze grasz w gre, jestes zolnierzem strzelasz spacją. Napierdzielasz w spacje ile wlezie, bo chcesz zabić wroga, wróg w koncu został zabity, ale program dalej strzela, bo nabiłeś mu 10000000 spacji i będzie wykonywać te 10000000 funkcji w odstepie 300ms :D czyli do jutra sie nie skonczy :D Rozumiecie :)? Mam nadzieje, że wyjaśnilem problem.
Inną ciekawą rzeczą z tym także związaną jest np. to, że chce stworzyć wyskakujący tekst np. "Zdobyłeś dodatkową amunicję" i tekst się pojawia na ekranie rośnie i znika. Czyli wydaje mi się, że czcionka powinna rosnąć, ale teraz jak to zrobić, zeby to było dla oka zauważalne ;d, jakieś opóźnienia pewnie. Ale trzeba to zrobić tak, aby gry nie zacinać i nie zawieszać.
Proszę pomóżcie albo jak znacie jakies fajne linki czy coś, ale nie chce zewnetrznych gotowych bibliotek ;d, ewentualnie możecie podrzucić ciekawe rozwiązanie stamtąd.
Nie potrzeba żadnych dodatkowych bibliotek, tylko standardowe Javy. Sleep nie może być używany do takich zastosowań bo on na ten czas po prostu Ci zamrozi cały proces i robi się kolejka eventów, które nie zostały obsłużone bo był sleep i dlatego nabija ci tyle naciśnięć które dopiero po sleepie mogą być obsłużone, ale z taką ilością obsluga nie nadąża.
Zrób jak napisałem wyżej.
System.currentTimeMillis() - podaje ci aktualny czas w milisekndach.
Jeśli nie użyjesz sleepa to te 100 wywołań spacji zostanie od razu obsłużone a nie z opóźnieniem, a w obsłudze naciśięcia spacji sprawdzasz czy te 300milisekund już mineło, jeśli nie to czekasz dalej, jak już 300 milisekund mineło to strzelasz.
jednak do końca nie łapie, dam ci kod:
public void keyPressed(KeyEvent e) {
switch (e.getKeyCode()) {
case KeyEvent.VK_B :
startTime=System.currentTimeMillis();
while((System.currentTimeMillis()-startTime)<=delayTimeBomb)
if((System.currentTimeMillis()-startTime)>=delayTimeBomb)
fireCluster();
break;
}
}
taki fragment tego kodu, ja to robie źle, mógłbyś to napisać jak użyc tego poprawnie?
Przyklad do przycisku B, na "bomby"