Existe-t-il un autre moyen de suivre la progression de l'effacement des pixels dans Phaser ?
P粉928591383
2023-08-14 20:29:20
<p>J'essaie donc de créer un jeu de cartes à gratter dans lequel l'utilisateur doit gratter la carte pour révéler ce qu'il y a en dessous. Je veux vérifier si l'utilisateur a gratté 70% du canevas pour tout révéler. J'essaie d'utiliser Phaser pour implémenter cette fonctionnalité, mais cela ne fonctionne pas. </p>
<p>J'ai essayé de calculer les données d'image pour obtenir un tableau de pixels, mais cela renvoie un tableau composé uniquement de zéros. J'utilise la fonction calculateScratchRatio dans le code ci-dessous.</p>
<pre class="brush:php;toolbar:false;">importer BaseScene depuis "./BaseScene" ;
const SKY_IMAGE = "ciel";
const SKY_IMAGE_BLACK = "cielnoir";
const CONSEIL = "planche";
const HEADER_ACT = "header_act";
const KEY_BRUSH = "pinceau";
const BGGAME = "bg-jeu";
exporter la classe par défaut Scratch étend BaseScene {
constructeur (config) {
super("Scratch", { ...config });
this.config = config;
this.isDown = faux ;
this.renderTexture = null;
this.brush = null;
this.erasedPixels = 0;
this.screenCenter = [config.width/2, config.height/2] ;
}
créer() {
super.create();
this.cover = this.make.image({
clé : SKY_IMAGE_BLACK,
ajouter : faux,
});
this.board = this.make.image({
clavier,
ajouter : faux,
});
this.ScratchOff();
this.add.image(...this.screenCenter, BOARD).setScale(0.7);
console.log(this.board.getBounds());
const headerinfo = this.add
.image(this.screenCenter[0] - 160, 130, "header_act")
.setScale(0.7);
laissez helloWorld = this.add
.text(0, 0, "Bonjour tout le monde")
.setFont("Arial 20px")
.setColor("#ffffff");
const conteneur = this.add.container(headerinfo.x, headerinfo.y);
conteneur.add(helloWorld);
}
ScratchOff() {
ceci.ajouter
.image(this.screenCenter[0] - 160, this.screenCenter[1], SKY_IMAGE)
.setScale(0.7);
this.cover.setOrigin(0, 0);
const width = this.cover.width;
const hauteur = this.cover.height;
console.log(largeur, hauteur);
const rt = this.add.renderTexture(
this.screenCenter[0] - 160,
ce.screenCenter[1],
largeur * 0,7,
hauteur * 0,71
);
this.isRenderTextureErased = false;
this.erasureThreshold = 0,99 ;
rt.setOrigin(0,5, 0,5);
rt.draw(this.cover); //, largeur * 0,5, hauteur * 0,5)
rt.setInteractive();
rt.on(Phaser.Input.Events.POINTER_DOWN, this.handlePointerDown, this);
rt.on(Phaser.Input.Events.POINTER_MOVE, this.handlePointerMove, this);
rt.on(Phaser.Input.Events.POINTER_UP, () => (this.isDown = false));
this.brush = this.make.image({
clé : KEY_BRUSH,
ajouter : faux,
});
this.renderTexture = rt;
}
handlePointerDown(pointeur) {
this.isDown = vrai ;
this.handlePointerMove(pointeur);
}
handlePointerMove(pointeur) {
si (!this.isDown) {
retour;
}
const x = pointer.x - this.renderTexture.x + this.renderTexture.width * 0,5 ;
const y =
pointeur.y - this.renderTexture.y + this.renderTexture.height * 0,5 ;
this.renderTexture.erase(this.brush, x, y);
résultat const = this.calculateScratchRatio(x, y);
console.log("résultat", résultat);
}calculerScratchRatio(x, y) {
const texture = this.textures.get(SKY_IMAGE_BLACK);
console.log(texture);
si (!texture) {
console.error(`Texture avec la clé '${SKY_IMAGE_BLACK}' introuvable.`);
renvoie 0 ;
}
console.log(texture);
const canvas = document.createElement("canvas");
toile.width = texture.source[0].width;
console.log("canvas.width", toile.width);
toile.hauteur = texture.source[0].hauteur;
const contexte = toile.getContext("2d");
contexte.drawImage(texture.source[0].image, 0, 0);
const imageData = context.getImageData(0, 0, canvas.width, canvas.height);
const pixels = imageData.data;
console.log(imageData, pixels);
laissez effacéCount = 0;
pour (soit i = 3; i < pixels.length; i += 4) {
const alpha = pixels[i + 3];
si (alpha < 128) {
effacéCount++;
}
}
const totalPixels = toile.width * toile.hauteur;
const scratchRatio = (erasedCount / totalPixels) * 100 ;
return Math.round(scratchRatio);
}
}</pré>
<p><br /></p>
Il y a beaucoup de choses dans votre code et il est difficile de le faire fonctionner.
La meilleure chose à faire est de publier un mini code exécutable comme mentionné ici ici.
Cependant, une solution simple et rapide consiste à utiliser
canvasTexture
pour créer une Cover Texture afin de pouvoir accéder au contexte directement depuis cet objet.Voici une courte démonstration de la façon dont je procéderais :
(Basé sur le concept de cette réponse)