Java - Comment créer un jeu Multithread en utilisant SwingWorker
Je veux créer un jeu [1 Joueur vs PC] avec des Threads.
Nous avons 10 * 10 deux couleurs Formes dans notre conseil comme ceci:
Lorsque le Joueur clique sur des Cercles BLEUS , Leur couleur devient grise.
De l'autre côté, le PC devrait transformer tous les rectangles ROUGES en gris.
Le GAGNANT est celui qui Efface toutes ses propres Formes Plus Tôt.
Le code pour le Lecteur fonctionne bien mais, Mon problème est dans la mise en œuvre du PC côté du jeu, comme je l'ai lu dans cet article je devrais utiliser SwingWorker pour implémenter le Threading dans l'interface graphique. c'est la première fois que j'utilise SwingWorkers et je ne sais pas comment cela devrait fonctionner correctement.
Voici mes codes:
La Classe Principale
public class BubblePopGame {
public static final Color DEFAULT_COLOR1 = Color.BLUE;
public static final Color DEFAULT_COLOR2 = Color.RED;
public BubblePopGame() {
List<ShapeItem> shapes = new ArrayList<ShapeItem>();
int Total = 10;
for (int i = 1; i <= Total; i++) {
for (int j = 1; j <= Total; j++) {
if ((i + j) % 2 == 0) {
shapes.add(new ShapeItem(new Ellipse2D.Double(i * 25, j * 25, 20, 20),
DEFAULT_COLOR1));
} else {
shapes.add(new ShapeItem(new Rectangle2D.Double(i * 25, j * 25, 20, 20),
DEFAULT_COLOR2));
}
}
}
JFrame frame = new JFrame("Bubble Pop Quest!!");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
ShapesPanel panel = new ShapesPanel(shapes);
frame.add(panel);
frame.setLocationByPlatform(true);
frame.pack();
frame.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
new BubblePopGame();
}
});
}
}
Classe d'élément de forme
public class ShapeItem {
private Shape shape;
private Color color;
public ShapeItem(Shape shape, Color color) {
super();
this.shape = shape;
this.color = color;
}
public Shape getShape() {
return shape;
}
public void setShape(Shape shape) {
this.shape = shape;
}
public Color getColor() {
return color;
}
public void setColor(Color color) {
this.color = color;
}
}
Classe ShapesPanel
public class ShapesPanel extends JPanel {
private List<ShapeItem> shapes;
private Random rand = new Random();
private SwingWorker<Boolean, Integer> worker;
public ShapesPanel(List<ShapeItem> shapesList) {
this.shapes = shapesList;
worker = new SwingWorker<Boolean, Integer>() {
@Override
protected Boolean doInBackground() throws Exception {
while (true) {
Thread.sleep(200);
int dim = rand.nextInt(300);
publish(dim);
return true;
}
}
@Override
protected void done() {
Boolean Status;
try {
Status = get();
System.out.println(Status);
super.done(); //To change body of generated methods, choose Tools | Templates.
} catch (InterruptedException ex) {
Logger.getLogger(ShapesPanel.class.getName()).log(Level.SEVERE, null, ex);
} catch (ExecutionException ex) {
Logger.getLogger(ShapesPanel.class.getName()).log(Level.SEVERE, null, ex);
}
}
@Override
protected void process(List<Integer> chunks) {
int mostRecentValue = chunks.get(chunks.size()-1);
System.out.println(mostRecentValue);
Color color2 = Color.LIGHT_GRAY;
ShapeItem tmpShape = shapes.get(mostRecentValue);
if(tmpShape.getColor()==Color.RED){
tmpShape.setColor(color2);
}
repaint();
}
};
worker.execute ();
addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
Color color1 = Color.LIGHT_GRAY;
for (ShapeItem item : shapes) {
if (item.getColor() == Color.BLUE) {
if (item.getShape().contains(e.getPoint())) {
item.setColor(color1);
}
}
}
repaint();
}
});
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D) g.create();
for (ShapeItem item : shapes) {
g2.setColor(item.getColor());
g2.fill(item.getShape());
}
g2.dispose();
}
@Override
public Dimension getPreferredSize() {
return new Dimension(300, 300);
}
private Color getRandomColor() {
return new Color(rand.nextFloat(), rand.nextFloat(),
rand.nextFloat());
}
}
1 answers
Si j'ai bien compris votre code, vous créez un jeu où le joueur humain doit cliquer aussi vite que possible sur toutes ses formes tandis que le PC clique également au hasard sur les formes. Le premier à effacer toutes ses formes gagne.
Si cela est correct, vous voudrez probablement ajuster votre SwingWorker
à
- boucle jusqu'à la fin du jeu. Actuellement, votre boucle se termine la première fois que la fin de la boucle est atteinte en raison de l'instruction
return
- Puisque vous n'êtes pas faire quoi que ce soit avec la valeur de retour booléenne du
SwingWorker
, vous pourriez aussi bien le laisser retourner void - Pas besoin d'appeler
get
dans ledone
méthode. Au moment où cette méthode est appelée, leSwingWorker
est terminé. Vous ne semblez intéressé que par les résultats intermédiaires - Dans la méthode
process
, vous voudrez peut-être faire une boucle sur toutes les valeurs. Notez que leprocess
méthode est pas, appelé chaque temps vouspublish
quelque chose. Les valeurs que vous publiez sont regroupées et transmises en bloc auprocess
méthode lorsque le thread EDT (Event Dispatch) est disponible