Fifteen, ou Fifteen, é um ótimo exemplo de um simples jogo de lógica popular em todo o mundo. Para resolver o quebra-cabeça, você precisa organizar os quadrados com os números em ordem, do menor para o maior. Não é fácil, mas interessante.
No tutorial de hoje, mostramos como desenvolver o Fifteen no Java 8 com Eclipse. Para desenvolver a interface do usuário, usaremos a API Swing.
Lembramos que: para todos os leitores de "Habr" - um desconto de 10.000 rublos ao se inscrever em qualquer curso Skillbox usando o código promocional "Habr".
A Skillbox recomenda: O curso educacional on-line "Profissão Java-developer" .
Design de jogos
Nesta fase, você precisa definir as propriedades:
- Tamanho - o tamanho do campo de jogo;
- nbTiles - o número de pontos no campo. nbTiles = tamanho * tamanho - 1;
- Tiles é uma tag, que é uma matriz unidimensional de números inteiros. Cada tag receberá um valor exclusivo no intervalo [0, nbTiles]. Zero indica um quadrado vazio;
- blankPos - posição do quadrado vazio.
Lógica do jogo
Você precisa definir um método de redefinição usado para inicializar uma nova posição do jogo. Então, definimos o valor para cada elemento da matriz de tags. Bem, então colocamos blankPos na última posição da matriz.
Você também precisa do método de reprodução aleatória para embaralhar uma matriz de tags. Não incluímos uma tag vazia no processo de reprodução aleatória para deixá-la em sua posição anterior.
Como apenas metade das posições iniciais possíveis do quebra-cabeça tem uma solução, é necessário verificar o resultado resultante da mistura para garantir que o layout atual seja geralmente resolvido. Para fazer isso, definimos o método isSolvable.
Se uma tag específica é precedida por uma tag com um valor mais alto, isso é considerado uma inversão. Quando a etiqueta vazia está no lugar, o número de inversões deve ser uniforme para que o quebra-cabeça seja solucionável. Então, contamos o número de inversões e retornamos true se o número for par.
É importante definir o método isSolved para verificar se o alinhamento do jogo dos quinze está resolvido. Primeiro, examinamos onde está a tag vazia. Se na posição inicial, o alinhamento atual é um novo, que não foi decidido antes. Depois, iteramos sobre os blocos na ordem inversa e, se o valor da tag diferir do índice +1 correspondente, retorne false. Caso contrário, é hora de retornar true no final do método, porque o quebra-cabeça já foi resolvido.
Outro método para definir é newGame. É necessário criar uma nova instância do jogo. Para fazer isso, redefinimos o campo de jogo, embaralhá-lo e continuar até a posição de jogo ser resolvida.
Aqui está um código de exemplo com lógica de tag key:
private void newGame() { do { reset();
Finalmente, você precisa programar o movimento dos pontos na matriz. Esse código será chamado posteriormente por meio de um retorno de chamada para responder ao movimento do cursor. Nosso jogo suportará vários movimentos de peças simultaneamente. Assim, depois de convertermos a posição pressionada na tela em uma etiqueta, obtemos a posição de uma etiqueta vazia e procuramos a direção do movimento para suportar vários de seus movimentos ao mesmo tempo.
Aqui está um código de exemplo:
Desenvolvemos interface do usuário na API Swing
É hora de fazer a interface. Primeiro, tomamos a classe Jpanel. Então desenhamos pontos no campo - para calcular os tamanhos de cada um, usaremos os dados especificados no parâmetro construtor do jogo:
gridSize = (dim - 2 * margin); tileSize = gridSize / size;
Margem também é um parâmetro especificado no construtor do jogo.
Agora você precisa definir o método drawGrid para desenhar a grade e os pontos na tela. Analisamos a matriz de tags e convertemos as coordenadas nas coordenadas da interface do usuário. Em seguida, desenhe cada etiqueta com o número correspondente no centro:
private void drawGrid(Graphics2D g) { for (int i = 0; i < tiles.length; i++) {
Finalmente, redefinimos o método paintComponent, que é um derivado da classe JPane. Em seguida, usamos o método drawGrid e, depois disso, usamos o método drawStartMessage para exibir uma mensagem solicitando o clique para iniciar o jogo:
private void drawStartMessage(Graphics2D g) { if (gameOver) { g.setFont(getFont().deriveFont(Font.BOLD, 18)); g.setColor(FOREGROUND_COLOR); String s = "Click to start new game"; g.drawString(s, (getWidth() - g.getFontMetrics().stringWidth(s)) / 2, getHeight() - margin); } } private void drawCenteredString(Graphics2D g, String s, int x, int y) {
Respondemos às ações do usuário na interface do usuário
Para que o jogo siga seu curso, é necessário processar as ações do usuário na interface do usuário. Para fazer isso, adicione a implementação MouseListener no Jpanel e o código para mover os pontos já mostrados acima:
addMouseListener(new MouseAdapter() { @Override public void mousePressed(MouseEvent e) {
Colocamos o código no construtor da classe GameOfFifteen. No final, chamamos o método newGame para iniciar um novo jogo.
Código do jogo completo
O último passo, antes de você ver o jogo em ação, é coletar todos os elementos do código juntos. Aqui está o resultado:
import java.awt.BorderLayout; import java.awt.Color; import java.awt.Dimension; import java.awt.Font; import java.awt.FontMetrics; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import java.util.Random; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.SwingUtilities;
Finalmente, jogue!
É hora de iniciar o jogo e verificá-lo em ação. O campo deve ficar assim:

Tentando resolver o quebra-cabeça. Se tudo correu bem, obtemos o seguinte:

Isso é tudo. Você esperava mais? :)
A Skillbox recomenda: