Usando wait() com JTextArea

12 respostas
A

ola amigos!

pois bem, a duvida eh a seguinte, eu tenho um for que a cada iteração joga termo a termo de uma matriz a uma String, e no final da iteração, uso um setText() para passar a string para o JTextArea, estou usando um wait(500) pra ver cada modificacao, seria um jogo de puzzle

o problema q ta dando q nao muda o JTextArea a cada iteração, tentei com wait, deu excecao IllegalMonitorStateException.

o for está ± assim

public void game(int walk){
        for(;;){
            modificaMatriz()
            montaString();
            txt1.setText(output);
            if((k==i && l==j)||(m==i && n==j)) break;
            try{
                wait(300);
            }
            catch(InterruptedException e){
                e.printStackTrace();
            }
        }       
    }

O que devo fazer?

12 Respostas

ViniGodoy

Você está rodando isso de uma thread separada ou na própria thread da AWT?

Se for numa thread separada, você deve empilhar os eventos de texto na AWT usando o InvokeLater.

Se for na mesma thread, você dá os updates no texto, mas os eventos de pintura não serão processados até que você libere a thread (saia do for). É porr isso que algumas interfaces gráficas ficam “congeladas” quando o processamento é muito pesado.

Dá uma olhada nesse tópico, espero que te ajude:
http://www.guj.com.br/posts/list/52022.java#273868

A

kra eu nao fiz usando evento, e tbm nao manjo mto de threads

olha oq eu tentei fazer aí
http://phpfi.com/207633

o problema eh no metodo game(), vc poderia me explicar rapidamente pq q congela a tela e da a exception la?

vlw abraço

ViniGodoy

Ok, você tem 2 problemas.

  1. O wait é usado em sincronização de threads. Substitua-o por Thread.sleep();
  2. Você está dando o setVisible(true) apenas após a engine rodar. Ou seja, todo código do jogo será processado para só depois exibir a tela.

Eu corrigi esses problemas da seguinte forma:
No construtor coloquei o seguinte código:

public Jogo_sexy()
    {
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setLayout(new FlowLayout());
        setLocation(100,100);
        setSize(400,300);
        setTitle("Maze Game");
        
        txt1 = new JTextArea();
        txt1.setEditable(false);
        txt1.setBackground(Color.white);
        txt1.setFont( new Font( "Monospaced", Font.PLAIN, 12 ) );
        Container c = getContentPane();
        c.add(txt1);
        setVisible(true);
    }

Depois, mudei o método engine() para:

public void engine(){
        game(checkMap());   
    }

Achei mais lógico dessa forma, já que o método engine deveria só disparar a engine do jogo, não se preocupar com a pintura da tela. Note que a agora a tela será deixada visível já na construção, antes do engine ser chamado.

Finalmente, troque a linha do wait para
Thread.sleep(300);

ViniGodoy

Legal o seu programa. Eu já fiz uma coisa assim.
Sei que tem uma forma mais fácil usando uma pilha.

Ainda assim, parabéns. Foi só ajeitar aquelas coisinhas e funcionou de primeira.

sergiotaborda

aleeebr:
ola amigos!

pois bem, a duvida eh a seguinte, eu tenho um for que a cada iteração joga termo a termo de uma matriz a uma String, e no final da iteração, uso um setText() para passar a string para o JTextArea, estou usando um wait(500) pra ver cada modificacao, seria um jogo de puzzle

o problema q ta dando q nao muda o JTextArea a cada iteração, tentei com wait, deu excecao IllegalMonitorStateException.

o for está ± assim

public void game(int walk){
        for(;;){
            modificaMatriz()
            montaString();
            txt1.setText(output);
            if((k==i && l==j)||(m==i && n==j)) break;
            try{
                wait(300);
            }
            catch(InterruptedException e){
                e.printStackTrace();
            }
        }       
    }

O que devo fazer?

Esse erro que vc esta tendo é pq não se pode usar wait sem fazer sincronismo, ou seja usar o bloco synchronized.

Mas usar wait não vai fazer o loop demorar mais. para fazer isso use Thread.sleep(300) (este não precisa de sincronização)

Se vc usar sleep vai provavelmente funcionar, mas se quer alguma coisa temporizada use um Timer (temporizador). E como vc está usado swing, use o timer do swing. Ele gera um evento a cada X milisegundos e ai vc
preenche o texto.

Mas o melhor mesmo era não usar nada disto. simplesmente escreve a matriz inteira no text area e pronto.

ViniGodoy

Só uma dica. Seu sistema se perde quando você tem algum circulo no labirinto. Você pode evitar que ele se perca se marcar os locais onde o X já andou com um outro valor (que na hora de pintar você também exibe como .)

A

Ah ta agora entendi, fiquei encucado de nao funcionar o wait() porque pensei q seria algo como um delay() em C.

É eu ja tinha visto que daria problema, mas queria ver se funcionava assim, para esse map, eu pensei em no lugar de ‘.’ deixar espaços em branco, e assim qndo passar por eles deixar um ‘.’ hehe

Vlw vini =)

A

existe alguma lista de dos caracteres possiveis de serem imprimidos em java?

pq eu tentei usar alguns em ascii para mudar as “paredes” do jogo e nao consegui

vlw

ViniGodoy

O Java usa o padrão unicode. Portanto, são os mesmos caracteres que você encontra no Mapa de Caracteres.

Mas cuidado, isso é muito sensível a fonte que você utilizará.

Se quiser fazer desenhos bonitinhos, depois você pode pesquisar como sobrescrever o método paintComponent do seu frame e pintar imagens no local das paredes. Para isso, você utiliza as bibliotecas Graphics2D. Mas isso não é tão trivial quando parece. O melhor mesmo é fazer algo simples e que dê tempo de entregar e garantir sua nota! :wink:

Entretanto, se tiver curiosidade de ver os Graphics e outras técnicas usadas em games, dá uma visitada no site do Killer Game Programming in Java, que contém o livro disponibilizado pelo próprio autor:
http://fivedots.coe.psu.ac.th/~ad/jg/

E você também pode baixar o jogo (com fontes) que eu fiz baseado nesse livro e no Developing Games in Java, do Brackeen:
http://www.guj.com.br/posts/list/48344.java

A

nao eh trabalho de facul

to fazendo por curiosidade msm =p

queria fazer algo parecido com Bomberman sabe, sei q por enquanto eh bastante dificil, mas quero ir progredindo aos poucos ateh entender melhor as classes de java… no caso um jogo assim, a matriz seria de objetos dae neh?

A

E essa sensibilidade das fontes, onde eu acho informacoes sobre isso? ou soh testando mesmo?

A

Ae galera, fiz agora algo mais bonito e interativo, seria um jogador contra o computador.

http://phpfi.com/209899

O problema é que qndo eu coloco pra rodar o jogo… ele faz a execucao do jogo, congelando os eventos de teclado q seria pra jogar contra o comp… a duvida é como fazer os 2 executarem juntos.

vlw

Criado 25 de fevereiro de 2007
Ultima resposta 28 de fev. de 2007
Respostas 12
Participantes 3