package linea; import java.awt.BorderLayout; import java.awt.Color; import java.awt.FlowLayout; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.KeyEvent; import java.awt.event.KeyListener; import java.util.ArrayList; import java.util.List; import javax.swing.JFrame; import javax.swing.JLabel; import javax.swing.JOptionPane; import javax.swing.JPanel; import javax.swing.Timer; public class Jeu implements KeyListener, ActionListener { //------------------------------------------------------------------------- // PROPRIETES //------------------------------------------------------------------------- protected ZoneDessin ecran = new ZoneDessin(); protected Cercle demiCercleAvant; protected Cercle demiCercleArriere; protected Ligne ligne; private int _niv = 1; protected Timer horloge; protected double score = 0; protected JLabel labScore; protected JLabel labMeilleurScore; private DatabaseConnection db; private int idCompte; private int meilleurSansCompte = 0; private int mortsSansCompte = 0; private int tempsSansCompteSec = 0; private long debutPartieMs = 0; private int meilleurActuel() { return idCompte > 0 ? db.getMeilleurScoreParCompte(idCompte) : meilleurSansCompte; } private String statsActuelles() { if (idCompte > 0) { return db.getStatsParCompte(idCompte); } return "Nombre de morts : " + mortsSansCompte + "\nTemps de jeu total : " + tempsSansCompteSec + " s" + "\nMeilleur score : " + meilleurSansCompte; } private void enregistrerPartie(int scoreActuel, int tempsPartieSec) { if (idCompte > 0) { db.sauvegarderScore(scoreActuel, idCompte, 1, tempsPartieSec); return; } meilleurSansCompte = Math.max(meilleurSansCompte, scoreActuel); mortsSansCompte += 1; tempsSansCompteSec += tempsPartieSec; } //------------------------------------------------------------------------- // CONSTRUCTEUR //------------------------------------------------------------------------- public Jeu(DatabaseConnection db, int idCompte) { this.db = db; this.idCompte = idCompte; labScore = new JLabel(); labScore.setText("

score : 0

"); labMeilleurScore = new JLabel(); JPanel panneauScores = new JPanel(new FlowLayout(FlowLayout.LEFT, 20, 0)); panneauScores.setOpaque(false); panneauScores.add(labScore); panneauScores.add(labMeilleurScore); ecran.add(panneauScores, BorderLayout.NORTH); rafraichirMeilleurScore(); } private void rafraichirMeilleurScore() { labMeilleurScore.setText("

meilleur : " + meilleurActuel() + "

"); } private boolean choisirNouveauCompte() { List pseudos = new ArrayList<>(db.getPseudos()); pseudos.add(0, "Sans compte"); String choix = (String) JOptionPane.showInputDialog( null, "Choisissez le compte pour la prochaine partie :", "Changer de compte", JOptionPane.QUESTION_MESSAGE, null, pseudos.toArray(String[]::new), pseudos.get(0) ); if (choix == null) { return false; } if ("Sans compte".equals(choix)) { idCompte = -1; meilleurSansCompte = 0; mortsSansCompte = 0; tempsSansCompteSec = 0; } else { idCompte = db.getIdParPseudo(choix); } rafraichirMeilleurScore(); return true; } //------------------------------------------------------------------------- // METHODES DE GESTION DU JEU //------------------------------------------------------------------------- /** * Centralise la création et la configuration des objets du jeu. * Évite de répéter ce code dans demarrer() et resetLevel(). */ private void initialiserPartie() { // 1. Nettoyage de l'écran ecran.reinitialiser(); // 2. Création des instances demiCercleAvant = new Cercle(90, -180); demiCercleArriere = new Cercle(90, 180); ligne = new Ligne(_niv); // 3. Configuration visuelle demiCercleArriere.setCouleur(new Color(0.8f, 0.0f, 0.0f)); demiCercleAvant.setCouleur(new Color(0.0f, 0.8f, 0.0f)); // 4. Ajout à l'écran (l'ordre définit la superposition) ecran.ajouterObjet(demiCercleArriere); ecran.ajouterObjet(ligne); ecran.ajouterObjet(demiCercleAvant); } public void demarrer() { JFrame fenetre = new JFrame("Linea Game"); // Initialise les objets une première fois initialiserPartie(); ecran.addKeyListener(this); ecran.setFocusable(true); fenetre.setContentPane(ecran); fenetre.pack(); fenetre.setLocation(100, 100); fenetre.setVisible(true); fenetre.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // Création et lancement du timer horloge = new Timer(40, this); horloge.start(); debutPartieMs = System.currentTimeMillis(); } private void resetLevel() { // Réinitialisation des variables de jeu score = 0; labScore.setText("

score : 0

"); // Ré-initialisation des objets graphiques initialiserPartie(); debutPartieMs = System.currentTimeMillis(); // Relance le timer existant et redonne le focus if (horloge != null) horloge.restart(); ecran.requestFocusInWindow(); } //------------------------------------------------------------------------- // EVENEMENTS (Timer & Clavier) //------------------------------------------------------------------------- @Override public void actionPerformed(ActionEvent e) { ecran.traiterBoucleAnimation(); if (ecran.aCollision()) { horloge.stop(); int scoreActuel = (int) score; int tempsPartieSec = (int) ((System.currentTimeMillis() - debutPartieMs) / 1000L); enregistrerPartie(scoreActuel, tempsPartieSec); rafraichirMeilleurScore(); while (true) { Object[] options = {"Relancer", "Changer de compte", "Voir stats", "Quitter"}; int choix = JOptionPane.showOptionDialog(null, "Perdu\nScore : " + scoreActuel + "\nMeilleur : " + meilleurActuel(), "Game Over", JOptionPane.DEFAULT_OPTION, JOptionPane.INFORMATION_MESSAGE, null, options, options[0]); if (choix == 0) { resetLevel(); break; } if (choix == 1) { if (choisirNouveauCompte()) { resetLevel(); break; } continue; } if (choix == 2) { JOptionPane.showMessageDialog(null, statsActuelles(), "Statistiques", JOptionPane.INFORMATION_MESSAGE); continue; } System.exit(0); } return; } // Calcul du score basé sur le temps écoulé score += (0.05 + (0.05 * horloge.getDelay() / 100.0)); labScore.setText("

score : " + (int)score + "

"); } @Override public void keyPressed(KeyEvent e) { if (e.getKeyCode() == KeyEvent.VK_UP) { demiCercleAvant.Monter(); demiCercleArriere.Monter(); } } @Override public void keyReleased(KeyEvent e) { if (e.getKeyCode() == KeyEvent.VK_UP) { demiCercleAvant.ArreterMonter(); demiCercleArriere.ArreterMonter(); } } @Override public void keyTyped(KeyEvent e) {} }