Los eventos de clic de jQuery se activan varias veces
Estoy intentando escribir un juego de video póquer en Javascript como una forma de comprender los conceptos básicos y me encontré con un problema en el que los controladores de eventos de clic de jQuery se activan varias veces.
Están adjuntos a botones para realizar una apuesta y funcionan bien para realizar una apuesta en la primera mano durante un juego (disparándose solo una vez); pero al apostar para la segunda mano, activa el evento de clic dos veces cada vez que se presiona un botón de apuesta o de realizar apuesta (por lo que se apuesta el doble de la cantidad correcta por cada presión). En general, sigue este patrón para la cantidad de veces que se activa el evento de clic al presionar un botón de apuesta una vez, donde el i-ésimo término de la secuencia es para la apuesta de la i-ésima mano desde el comienzo del juego: 1, 2, 4 , 7, 11, 16, 22, 29, 37, 46, que parece ser n(n+1)/2 + 1 para lo que valga la pena, y no fui lo suficientemente inteligente como para darme cuenta de eso, usé OEIS . :)
Aquí está la función con los controladores de eventos de clic que están funcionando mal; Espero que sea fácil de entender (avíseme si no, quiero mejorar en eso también):
/** The following function keeps track of bet buttons that are pressed, until place button is pressed to place bet. **/
function pushingBetButtons() {
$("#money").text("Money left: $" + player.money); // displays money player has left
$(".bet").click(function() {
var amount = 0; // holds the amount of money the player bet on this click
if($(this).attr("id") == "bet1") { // the player just bet $1
amount = 1;
} else if($(this).attr("id") == "bet5") { // etc.
amount = 5;
} else if($(this).attr("id") == "bet25") {
amount = 25;
} else if($(this).attr("id") == "bet100") {
amount = 100;
} else if($(this).attr("id") == "bet500") {
amount = 500;
} else if($(this).attr("id") == "bet1000") {
amount = 1000;
}
if(player.money >= amount) { // check whether the player has this much to bet
player.bet += amount; // add what was just bet by clicking that button to the total bet on this hand
player.money -= amount; // and, of course, subtract it from player's current pot
$("#money").text("Money left: $" + player.money); // then redisplay what the player has left
} else {
alert("You don't have $" + amount + " to bet.");
}
});
$("#place").click(function() {
if(player.bet == 0) { // player didn't bet anything on this hand
alert("Please place a bet first.");
} else {
$("#card_para").css("display", "block"); // now show the cards
$(".card").bind("click", cardClicked); // and set up the event handler for the cards
$("#bet_buttons_para").css("display", "none"); // hide the bet buttons and place bet button
$("#redraw").css("display", "block"); // and reshow the button for redrawing the hand
player.bet = 0; // reset the bet for betting on the next hand
drawNewHand(); // draw the cards
}
});
}
Avíseme si tiene alguna idea o sugerencia, o si la solución a mi problema es similar a una solución a otro problema aquí (he mirado muchos hilos con títulos similares y no tuve suerte en encontrar una solución que pudiera funcionar). para mí).
Para asegurarse de que un clic solo actúe una vez, use esto:
$(".bet").unbind().click(function() {
//Stuff
});
.unbind()
está en desuso y deberías utilizar el .off()
método en su lugar. Simplemente llame .off()
justo antes de llamar .on()
.
Esto eliminará todos los controladores de eventos:
$(element).off().on('click', function() {
// function body
});
Para eliminar únicamente los controladores de eventos de "clic" registrados:
$(element).off('click').on('click', function() {
// function body
});
.uno()
Una mejor opción sería .one()
:
El controlador se ejecuta como máximo una vez por elemento y por tipo de evento.
$(".bet").one('click',function() {
//Your function
});
En caso de que haya varias clases y sea necesario hacer clic en cada clase una vez,
$(".bet").on('click',function() {
//Your function
$(this).off('click'); //or $(this).unbind()
});
Si encuentra que .off() .unbind() o .stopPropagation() aún no soluciona su problema específico, intente usar .stopImmediatePropagation() Funciona muy bien en situaciones en las que solo desea que su evento se maneje sin burbujas y sin efectuar cualquier otro evento que ya se esté manejando. Algo como:
$(".bet").click(function(event) {
event.stopImmediatePropagation();
//Do Stuff
});
¡Hace el truco!