Implement Seltzer and Joker Expiration effect (#252)
* Add Seltzer art * Implement Joker expiration * Add exception to copying Jokers + Seltzer message fix * Move all scoring logic to joker_object_score away from check_and_score_joker_for_event --------- Co-authored-by: MathisMartin31 <mathis.martin31@gmail.com>
This commit is contained in:
Binary file not shown.
|
Before Width: | Height: | Size: 657 B After Width: | Height: | Size: 12 KiB |
@@ -1,6 +1,8 @@
|
|||||||
#ifndef GAME_H
|
#ifndef GAME_H
|
||||||
#define GAME_H
|
#define GAME_H
|
||||||
|
|
||||||
|
#include <tonc.h>
|
||||||
|
|
||||||
#define MAX_HAND_SIZE 16
|
#define MAX_HAND_SIZE 16
|
||||||
#define MAX_DECK_SIZE 52
|
#define MAX_DECK_SIZE 52
|
||||||
#define MAX_JOKERS_HELD_SIZE 5 // This doesn't account for negatives right now.
|
#define MAX_JOKERS_HELD_SIZE 5 // This doesn't account for negatives right now.
|
||||||
@@ -56,6 +58,7 @@ enum PlayState
|
|||||||
PLAY_SCORING_CARD_JOKERS,
|
PLAY_SCORING_CARD_JOKERS,
|
||||||
PLAY_SCORING_HELD_CARDS,
|
PLAY_SCORING_HELD_CARDS,
|
||||||
PLAY_SCORING_INDEPENDENT_JOKERS,
|
PLAY_SCORING_INDEPENDENT_JOKERS,
|
||||||
|
PLAY_SCORING_HAND_SCORED_END,
|
||||||
PLAY_ENDING,
|
PLAY_ENDING,
|
||||||
PLAY_ENDED
|
PLAY_ENDED
|
||||||
};
|
};
|
||||||
@@ -109,11 +112,23 @@ int get_scored_card_index(void);
|
|||||||
bool is_joker_owned(int joker_id);
|
bool is_joker_owned(int joker_id);
|
||||||
bool card_is_face(Card *card);
|
bool card_is_face(Card *card);
|
||||||
List* get_jokers_list(void);
|
List* get_jokers_list(void);
|
||||||
|
List* get_expired_jokers_list(void);
|
||||||
|
|
||||||
int get_deck_top(void);
|
int get_deck_top(void);
|
||||||
int get_num_discards_remaining(void);
|
int get_num_discards_remaining(void);
|
||||||
int get_num_hands_remaining(void);
|
int get_num_hands_remaining(void);
|
||||||
|
|
||||||
|
u32 get_chips(void);
|
||||||
|
void set_chips(u32 new_chips);
|
||||||
|
void display_chips();
|
||||||
|
u32 get_mult(void);
|
||||||
|
void set_mult(u32 new_mult);
|
||||||
|
void display_mult();
|
||||||
int get_money(void);
|
int get_money(void);
|
||||||
|
void set_money(int new_money);
|
||||||
|
void display_money();
|
||||||
|
void set_retrigger(bool new_retrigger);
|
||||||
|
|
||||||
|
|
||||||
int get_game_speed(void);
|
int get_game_speed(void);
|
||||||
void set_game_speed(int new_game_speed);
|
void set_game_speed(int new_game_speed);
|
||||||
|
|||||||
+6
-2
@@ -139,8 +139,12 @@ int joker_get_sell_value(const Joker* joker);
|
|||||||
JokerObject *joker_object_new(Joker *joker);
|
JokerObject *joker_object_new(Joker *joker);
|
||||||
void joker_object_destroy(JokerObject **joker_object);
|
void joker_object_destroy(JokerObject **joker_object);
|
||||||
void joker_object_update(JokerObject *joker_object);
|
void joker_object_update(JokerObject *joker_object);
|
||||||
void joker_object_shake(JokerObject *joker_object, mm_word sound_id); // This doesn't actually score anything, it just performs an animation and plays a sound effect
|
// This doesn't actually score anything, it just performs an animation and plays a sound effect
|
||||||
bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum JokerEvent joker_event, u32 *chips, u32 *mult, int *money, bool *retrigger); // This scores the joker and returns true if it was scored successfully (Card = NULL means the joker is independent and not scored by a card)
|
void joker_object_shake(JokerObject *joker_object, mm_word sound_id);
|
||||||
|
// This scores the joker and returns true if it was scored successfully
|
||||||
|
// card_object = NULL means the joker_event does not concern a particular Card, i.e. Independend or On_Blind_Selected
|
||||||
|
// as opposed to events that concern a particular card, i.e. On_Card_Scored or On_Card_Held
|
||||||
|
bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum JokerEvent joker_event);
|
||||||
|
|
||||||
void joker_object_set_selected(JokerObject* joker_object, bool selected);
|
void joker_object_set_selected(JokerObject* joker_object, bool selected);
|
||||||
bool joker_object_is_selected(JokerObject* joker_object);
|
bool joker_object_is_selected(JokerObject* joker_object);
|
||||||
|
|||||||
+114
-20
@@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
#include <maxmod.h>
|
#include <maxmod.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <tonc.h>
|
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
|
||||||
#include "bitset.h"
|
#include "bitset.h"
|
||||||
@@ -238,6 +237,7 @@ static bool sort_by_suit = false;
|
|||||||
|
|
||||||
static List _owned_jokers_list;
|
static List _owned_jokers_list;
|
||||||
static List _discarded_jokers_list;
|
static List _discarded_jokers_list;
|
||||||
|
static List _expired_jokers_list;
|
||||||
|
|
||||||
BITSET_DEFINE(_avail_jokers_bitset, MAX_DEFINABLE_JOKERS)
|
BITSET_DEFINE(_avail_jokers_bitset, MAX_DEFINABLE_JOKERS)
|
||||||
static List _shop_jokers_list;
|
static List _shop_jokers_list;
|
||||||
@@ -392,6 +392,11 @@ List* get_jokers_list(void)
|
|||||||
return &_owned_jokers_list;
|
return &_owned_jokers_list;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
List* get_expired_jokers_list(void)
|
||||||
|
{
|
||||||
|
return &_expired_jokers_list;
|
||||||
|
}
|
||||||
|
|
||||||
bool is_joker_owned(int joker_id)
|
bool is_joker_owned(int joker_id)
|
||||||
{
|
{
|
||||||
ListItr itr = list_itr_create(&_owned_jokers_list);
|
ListItr itr = list_itr_create(&_owned_jokers_list);
|
||||||
@@ -478,11 +483,42 @@ void set_game_speed(int new_game_speed)
|
|||||||
game_speed = new_game_speed;
|
game_speed = new_game_speed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
u32 get_chips(void)
|
||||||
|
{
|
||||||
|
return chips;
|
||||||
|
}
|
||||||
|
|
||||||
|
void set_chips(u32 new_chips)
|
||||||
|
{
|
||||||
|
chips = new_chips;
|
||||||
|
}
|
||||||
|
|
||||||
|
u32 get_mult(void)
|
||||||
|
{
|
||||||
|
return mult;
|
||||||
|
}
|
||||||
|
|
||||||
|
void set_mult(u32 new_mult)
|
||||||
|
{
|
||||||
|
mult = new_mult;
|
||||||
|
}
|
||||||
|
|
||||||
int get_money(void)
|
int get_money(void)
|
||||||
{
|
{
|
||||||
return money;
|
return money;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void set_money(int new_money)
|
||||||
|
{
|
||||||
|
money = new_money;
|
||||||
|
}
|
||||||
|
|
||||||
|
void set_retrigger(bool new_retrigger)
|
||||||
|
{
|
||||||
|
retrigger = new_retrigger;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// Consts
|
// Consts
|
||||||
|
|
||||||
@@ -1127,11 +1163,11 @@ void display_score(u32 value)
|
|||||||
tte_printf("#{P:%d,48; cx:0x%X000}%lu%c", x_offset, TTE_WHITE_PB, display_value, score_suffix);
|
tte_printf("#{P:%d,48; cx:0x%X000}%lu%c", x_offset, TTE_WHITE_PB, display_value, score_suffix);
|
||||||
}
|
}
|
||||||
|
|
||||||
void display_money(int value)
|
void display_money()
|
||||||
{
|
{
|
||||||
int x_offset = 32 - get_digits_odd(value) * TILE_SIZE;
|
int x_offset = 32 - get_digits_odd(money) * TILE_SIZE;
|
||||||
tte_erase_rect_wrapper(MONEY_TEXT_RECT);
|
tte_erase_rect_wrapper(MONEY_TEXT_RECT);
|
||||||
tte_printf("#{P:%d,%d; cx:0x%X000}$%d", x_offset, MONEY_TEXT_RECT.top, TTE_YELLOW_PB, value);
|
tte_printf("#{P:%d,%d; cx:0x%X000}$%d", x_offset, MONEY_TEXT_RECT.top, TTE_YELLOW_PB, money);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Show/Hide flaming score effect if we will score
|
// Show/Hide flaming score effect if we will score
|
||||||
@@ -1474,6 +1510,7 @@ void game_init()
|
|||||||
// Initialize all jokers list once
|
// Initialize all jokers list once
|
||||||
_owned_jokers_list = list_create();
|
_owned_jokers_list = list_create();
|
||||||
_discarded_jokers_list = list_create();
|
_discarded_jokers_list = list_create();
|
||||||
|
_expired_jokers_list = list_create();
|
||||||
_shop_jokers_list = list_create();
|
_shop_jokers_list = list_create();
|
||||||
// TODO: Move this to an initialization of the play scoring states
|
// TODO: Move this to an initialization of the play scoring states
|
||||||
_joker_scored_itr = list_itr_create(&_owned_jokers_list);
|
_joker_scored_itr = list_itr_create(&_owned_jokers_list);
|
||||||
@@ -1538,7 +1575,7 @@ void game_start()
|
|||||||
display_hands(hands); // Hand
|
display_hands(hands); // Hand
|
||||||
display_discards(discards); // Discard
|
display_discards(discards); // Discard
|
||||||
|
|
||||||
display_money(money); // Set the money display
|
display_money(); // Set the money display
|
||||||
|
|
||||||
tte_printf("#{P:%d,%d; cx:0x%X000}%d#{cx:0x%X000}/%d", ANTE_TEXT_RECT.left, ANTE_TEXT_RECT.top, TTE_YELLOW_PB, ante, TTE_WHITE_PB, MAX_ANTE); // Ante
|
tte_printf("#{P:%d,%d; cx:0x%X000}%d#{cx:0x%X000}/%d", ANTE_TEXT_RECT.left, ANTE_TEXT_RECT.top, TTE_YELLOW_PB, ante, TTE_WHITE_PB, MAX_ANTE); // Ante
|
||||||
|
|
||||||
@@ -2191,12 +2228,8 @@ static bool check_and_score_joker_for_event(ListItr* starting_joker_itr, CardObj
|
|||||||
|
|
||||||
while((joker = list_itr_next(starting_joker_itr)))
|
while((joker = list_itr_next(starting_joker_itr)))
|
||||||
{
|
{
|
||||||
if (joker_object_score(joker, card_object, joker_event, &chips, &mult, &money, &retrigger))
|
if (joker_object_score(joker, card_object, joker_event))
|
||||||
{
|
{
|
||||||
display_chips();
|
|
||||||
display_mult();
|
|
||||||
display_money(money);
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2241,7 +2274,7 @@ static bool play_before_scoring_cards_update()
|
|||||||
}
|
}
|
||||||
|
|
||||||
// returns true if the scoring loop has returned early
|
// returns true if the scoring loop has returned early
|
||||||
static bool play_scoring_cards_update()
|
static bool play_scoring_cards_update(void)
|
||||||
{
|
{
|
||||||
if (timer % FRAMES(30) == 0 && timer > FRAMES(40))
|
if (timer % FRAMES(30) == 0 && timer > FRAMES(40))
|
||||||
{
|
{
|
||||||
@@ -2261,6 +2294,7 @@ static bool play_scoring_cards_update()
|
|||||||
scored_card_index = hand_top;
|
scored_card_index = hand_top;
|
||||||
|
|
||||||
play_state = PLAY_SCORING_HELD_CARDS;
|
play_state = PLAY_SCORING_HELD_CARDS;
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2331,7 +2365,6 @@ static bool play_scoring_card_jokers_update()
|
|||||||
// increment index to start seeking the next scoring card from the next card
|
// increment index to start seeking the next scoring card from the next card
|
||||||
scored_card_index++;
|
scored_card_index++;
|
||||||
play_state = PLAY_SCORING_CARDS;
|
play_state = PLAY_SCORING_CARDS;
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
@@ -2356,7 +2389,7 @@ static bool play_scoring_held_cards_update(int played_idx)
|
|||||||
}
|
}
|
||||||
|
|
||||||
scored_card_index = 0;
|
scored_card_index = 0;
|
||||||
|
_joker_round_end_itr = list_itr_create(&_owned_jokers_list);
|
||||||
play_state = PLAY_SCORING_INDEPENDENT_JOKERS;
|
play_state = PLAY_SCORING_INDEPENDENT_JOKERS;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2377,15 +2410,29 @@ static bool play_scoring_independent_jokers_update(int played_idx)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
scored_card_index = played_top + 1; // Reset the scored card index to the top of the played stack
|
||||||
|
|
||||||
|
play_state = PLAY_SCORING_HAND_SCORED_END;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
// Trigger hand end effect for all jokers once they are done scoring
|
// Trigger hand end effect for all jokers once they are done scoring
|
||||||
|
static bool play_scoring_hand_scored_end_update(int played_idx)
|
||||||
|
{
|
||||||
|
if (played_idx == 0 && (timer % FRAMES(30) == 0) && timer > FRAMES(40))
|
||||||
|
{
|
||||||
|
|
||||||
|
tte_erase_rect_wrapper(PLAYED_CARDS_SCORES_RECT);
|
||||||
|
|
||||||
if (check_and_score_joker_for_event(&_joker_round_end_itr, NULL, JOKER_EVENT_ON_HAND_SCORED_END))
|
if (check_and_score_joker_for_event(&_joker_round_end_itr, NULL, JOKER_EVENT_ON_HAND_SCORED_END))
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
play_state = PLAY_ENDING;
|
|
||||||
timer = TM_ZERO;
|
timer = TM_ZERO;
|
||||||
scored_card_index = played_top + 1; // Reset the scored card index to the top of the played stack
|
play_state = PLAY_ENDING;
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
@@ -2529,6 +2576,14 @@ static void played_cards_update_loop()
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case PLAY_SCORING_HAND_SCORED_END:
|
||||||
|
|
||||||
|
if (play_scoring_hand_scored_end_update(played_idx))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
case PLAY_ENDING:
|
case PLAY_ENDING:
|
||||||
|
|
||||||
play_ending_played_cards_update(played_idx);
|
play_ending_played_cards_update(played_idx);
|
||||||
@@ -2641,7 +2696,7 @@ static int calculate_interest_reward()
|
|||||||
static void game_round_end_cashout()
|
static void game_round_end_cashout()
|
||||||
{
|
{
|
||||||
money += hands + blind_get_reward(current_blind) + calculate_interest_reward(); // Reward the player
|
money += hands + blind_get_reward(current_blind) + calculate_interest_reward(); // Reward the player
|
||||||
display_money(money);
|
display_money();
|
||||||
|
|
||||||
hands = max_hands; // Reset the hands to the maximum
|
hands = max_hands; // Reset the hands to the maximum
|
||||||
discards = max_discards; // Reset the discards to the maximum
|
discards = max_discards; // Reset the discards to the maximum
|
||||||
@@ -3094,7 +3149,7 @@ static void game_shop_intro()
|
|||||||
static void game_shop_reroll(int *reroll_cost)
|
static void game_shop_reroll(int *reroll_cost)
|
||||||
{
|
{
|
||||||
money -= *reroll_cost;
|
money -= *reroll_cost;
|
||||||
display_money(money); // Update the money display
|
display_money(); // Update the money display
|
||||||
|
|
||||||
ListItr itr = list_itr_create(&_shop_jokers_list);
|
ListItr itr = list_itr_create(&_shop_jokers_list);
|
||||||
JokerObject* joker_object;
|
JokerObject* joker_object;
|
||||||
@@ -3173,7 +3228,7 @@ void game_sell_joker(int joker_idx)
|
|||||||
|
|
||||||
JokerObject* joker_object = (JokerObject*)list_get_at_idx(&_owned_jokers_list, joker_idx);
|
JokerObject* joker_object = (JokerObject*)list_get_at_idx(&_owned_jokers_list, joker_idx);
|
||||||
money += joker_get_sell_value(joker_object->joker);
|
money += joker_get_sell_value(joker_object->joker);
|
||||||
display_money(money);
|
display_money();
|
||||||
erase_price_under_sprite_object(joker_object->sprite_object);
|
erase_price_under_sprite_object(joker_object->sprite_object);
|
||||||
|
|
||||||
remove_owned_joker(joker_idx);
|
remove_owned_joker(joker_idx);
|
||||||
@@ -3208,7 +3263,7 @@ static void game_shop_buy_joker(int shop_joker_idx)
|
|||||||
JokerObject *joker_object = (JokerObject*)list_get_at_idx(&_shop_jokers_list, shop_joker_idx);
|
JokerObject *joker_object = (JokerObject*)list_get_at_idx(&_shop_jokers_list, shop_joker_idx);
|
||||||
|
|
||||||
money -= joker_object->joker->value; // Deduct the money spent on the joker
|
money -= joker_object->joker->value; // Deduct the money spent on the joker
|
||||||
display_money(money); // Update the money display
|
display_money(); // Update the money display
|
||||||
erase_price_under_sprite_object(joker_object->sprite_object);
|
erase_price_under_sprite_object(joker_object->sprite_object);
|
||||||
sprite_object_set_focus(joker_object->sprite_object, false);
|
sprite_object_set_focus(joker_object->sprite_object, false);
|
||||||
add_to_held_jokers(joker_object);
|
add_to_held_jokers(joker_object);
|
||||||
@@ -3669,6 +3724,43 @@ static void game_main_menu_on_update()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define EXPIRE_ANIMATION_FRAME_COUNT 3
|
||||||
|
static void expired_jokers_update_loop()
|
||||||
|
{
|
||||||
|
if(list_is_empty(&_expired_jokers_list)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
ListItr itr = list_itr_create(&_expired_jokers_list);
|
||||||
|
JokerObject* joker_object;
|
||||||
|
|
||||||
|
while((joker_object = list_itr_next(&itr)))
|
||||||
|
{
|
||||||
|
joker_object_update(joker_object);
|
||||||
|
|
||||||
|
// let just enough frames pass that we see it rotating and shrinking
|
||||||
|
if (timer % FRAMES(EXPIRE_ANIMATION_FRAME_COUNT) == 0)
|
||||||
|
{
|
||||||
|
// get joker idx
|
||||||
|
int expired_joker_idx = 0;
|
||||||
|
ListItr joker_itr = list_itr_create(&_owned_jokers_list);
|
||||||
|
JokerObject* expired_joker;
|
||||||
|
while ((expired_joker = list_itr_next(&joker_itr)) && expired_joker != joker_object)
|
||||||
|
{
|
||||||
|
expired_joker_idx++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Removing expired Jokers here, instead of immediately like ones we
|
||||||
|
// sell or discard allow us to have a small shrink animation without
|
||||||
|
// the other owned Jokers rearranging themselves to fill the newly
|
||||||
|
// freed space, therefore obscuring the animation
|
||||||
|
remove_owned_joker(expired_joker_idx);
|
||||||
|
list_itr_remove_current_node(&itr);
|
||||||
|
joker_object_destroy(&joker_object);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void discarded_jokers_update_loop()
|
static void discarded_jokers_update_loop()
|
||||||
{
|
{
|
||||||
if(list_is_empty(&_discarded_jokers_list)) {
|
if(list_is_empty(&_discarded_jokers_list)) {
|
||||||
@@ -3720,6 +3812,7 @@ static void jokers_update_loop()
|
|||||||
{
|
{
|
||||||
held_jokers_update_loop();
|
held_jokers_update_loop();
|
||||||
discarded_jokers_update_loop();
|
discarded_jokers_update_loop();
|
||||||
|
expired_jokers_update_loop();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void game_over_anim_frame()
|
static void game_over_anim_frame()
|
||||||
@@ -3767,6 +3860,7 @@ static void game_over_on_exit()
|
|||||||
|
|
||||||
list_clear(&_owned_jokers_list);
|
list_clear(&_owned_jokers_list);
|
||||||
list_clear(&_discarded_jokers_list);
|
list_clear(&_discarded_jokers_list);
|
||||||
|
list_clear(&_expired_jokers_list);
|
||||||
list_clear(&_shop_jokers_list);
|
list_clear(&_shop_jokers_list);
|
||||||
|
|
||||||
game_init();
|
game_init();
|
||||||
@@ -3777,7 +3871,7 @@ static void game_over_on_exit()
|
|||||||
display_mult();
|
display_mult();
|
||||||
display_hands(hands);
|
display_hands(hands);
|
||||||
display_discards(discards);
|
display_discards(discards);
|
||||||
display_money(money);
|
display_money();
|
||||||
tte_printf(
|
tte_printf(
|
||||||
"#{P:%d,%d; cx:0x%X000}%d#{cx:0x%X000}/%d",
|
"#{P:%d,%d; cx:0x%X000}%d#{cx:0x%X000}/%d",
|
||||||
ANTE_TEXT_RECT.left,
|
ANTE_TEXT_RECT.left,
|
||||||
|
|||||||
+25
-7
@@ -265,7 +265,7 @@ void set_and_shift_text(char* str, int* cursor_pos_x, int* cursor_pos_y, int col
|
|||||||
*cursor_pos_x += joker_score_display_offset_px;
|
*cursor_pos_x += joker_score_display_offset_px;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum JokerEvent joker_event, u32 *chips, u32 *mult, int *money, bool *retrigger)
|
bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum JokerEvent joker_event)
|
||||||
{
|
{
|
||||||
if (joker_object == NULL)
|
if (joker_object == NULL)
|
||||||
{
|
{
|
||||||
@@ -280,11 +280,17 @@ bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
u32 chips = get_chips();
|
||||||
|
u32 mult = get_mult();
|
||||||
|
int money = get_money();
|
||||||
|
|
||||||
if (effect_flags_ret & JOKER_EFFECT_FLAG_RETRIGGER)
|
if (effect_flags_ret & JOKER_EFFECT_FLAG_RETRIGGER)
|
||||||
{
|
{
|
||||||
*retrigger = joker_effect->retrigger;
|
set_retrigger(joker_effect->retrigger);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// joker_effect.message will have been set if the Joker had anything custom to say
|
||||||
|
|
||||||
int cursorPosX = TILE_SIZE; // Offset of one tile to better center the text on the card
|
int cursorPosX = TILE_SIZE; // Offset of one tile to better center the text on the card
|
||||||
int cursorPosY = 0;
|
int cursorPosY = 0;
|
||||||
if (joker_event == JOKER_EVENT_ON_CARD_HELD)
|
if (joker_event == JOKER_EVENT_ON_CARD_HELD)
|
||||||
@@ -303,7 +309,7 @@ bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum
|
|||||||
mm_word sfx_id;
|
mm_word sfx_id;
|
||||||
if (effect_flags_ret & JOKER_EFFECT_FLAG_CHIPS)
|
if (effect_flags_ret & JOKER_EFFECT_FLAG_CHIPS)
|
||||||
{
|
{
|
||||||
*chips = u32_protected_add(*chips, joker_effect->chips);
|
chips = u32_protected_add(chips, joker_effect->chips);
|
||||||
char score_buffer[INT_MAX_DIGITS + 2]; // For '+' and null terminator
|
char score_buffer[INT_MAX_DIGITS + 2]; // For '+' and null terminator
|
||||||
snprintf(score_buffer, sizeof(score_buffer), "+%lu", joker_effect->chips);
|
snprintf(score_buffer, sizeof(score_buffer), "+%lu", joker_effect->chips);
|
||||||
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_BLUE_PB);
|
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_BLUE_PB);
|
||||||
@@ -311,7 +317,7 @@ bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum
|
|||||||
}
|
}
|
||||||
if (effect_flags_ret & JOKER_EFFECT_FLAG_MULT)
|
if (effect_flags_ret & JOKER_EFFECT_FLAG_MULT)
|
||||||
{
|
{
|
||||||
*mult = u32_protected_add(*mult, joker_effect->mult);
|
mult = u32_protected_add(mult, joker_effect->mult);
|
||||||
char score_buffer[INT_MAX_DIGITS + 2];
|
char score_buffer[INT_MAX_DIGITS + 2];
|
||||||
snprintf(score_buffer, sizeof(score_buffer), "+%lu", joker_effect->mult);
|
snprintf(score_buffer, sizeof(score_buffer), "+%lu", joker_effect->mult);
|
||||||
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_RED_PB);
|
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_RED_PB);
|
||||||
@@ -320,7 +326,7 @@ bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum
|
|||||||
// if xmult is zero, DO NOT multiply by it
|
// if xmult is zero, DO NOT multiply by it
|
||||||
if (effect_flags_ret & JOKER_EFFECT_FLAG_XMULT && joker_effect->xmult > 0)
|
if (effect_flags_ret & JOKER_EFFECT_FLAG_XMULT && joker_effect->xmult > 0)
|
||||||
{
|
{
|
||||||
*mult = u32_protected_mult(*mult, joker_effect->xmult);
|
mult = u32_protected_mult(mult, joker_effect->xmult);
|
||||||
char score_buffer[INT_MAX_DIGITS + 2];
|
char score_buffer[INT_MAX_DIGITS + 2];
|
||||||
snprintf(score_buffer, sizeof(score_buffer), "X%lu", joker_effect->xmult);
|
snprintf(score_buffer, sizeof(score_buffer), "X%lu", joker_effect->xmult);
|
||||||
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_RED_PB);
|
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_RED_PB);
|
||||||
@@ -328,7 +334,7 @@ bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum
|
|||||||
}
|
}
|
||||||
if (effect_flags_ret & JOKER_EFFECT_FLAG_MONEY)
|
if (effect_flags_ret & JOKER_EFFECT_FLAG_MONEY)
|
||||||
{
|
{
|
||||||
*money += joker_effect->money;
|
money += joker_effect->money;
|
||||||
char score_buffer[INT_MAX_DIGITS + 2];
|
char score_buffer[INT_MAX_DIGITS + 2];
|
||||||
snprintf(score_buffer, sizeof(score_buffer), "%d$", joker_effect->money);
|
snprintf(score_buffer, sizeof(score_buffer), "%d$", joker_effect->money);
|
||||||
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_YELLOW_PB);
|
set_and_shift_text(score_buffer, &cursorPosX, &cursorPosY, TTE_YELLOW_PB);
|
||||||
@@ -340,11 +346,23 @@ bool joker_object_score(JokerObject *joker_object, CardObject* card_object, enum
|
|||||||
{
|
{
|
||||||
set_and_shift_text(joker_effect->message, &cursorPosX, &cursorPosY, TTE_WHITE_PB);
|
set_and_shift_text(joker_effect->message, &cursorPosX, &cursorPosY, TTE_WHITE_PB);
|
||||||
}
|
}
|
||||||
|
// this will start the Joker expire animation
|
||||||
if (effect_flags_ret & JOKER_EFFECT_FLAG_EXPIRE && joker_effect->expire)
|
if (effect_flags_ret & JOKER_EFFECT_FLAG_EXPIRE && joker_effect->expire)
|
||||||
{
|
{
|
||||||
// TODO make Jokers expire
|
joker_object_shake(joker_object, UNDEFINED);
|
||||||
|
list_push_back(get_expired_jokers_list(), joker_object);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Update values
|
||||||
|
set_chips(chips);
|
||||||
|
set_mult(mult);
|
||||||
|
set_money(money);
|
||||||
|
|
||||||
|
// Update displays
|
||||||
|
display_chips();
|
||||||
|
display_mult();
|
||||||
|
display_money();
|
||||||
|
|
||||||
joker_object_shake(joker_object, sfx_id);
|
joker_object_shake(joker_object, sfx_id);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
+16
-11
@@ -976,7 +976,9 @@ static u32 blueprint_brainstorm_joker_effect(Joker *joker, Card *scored_card, en
|
|||||||
|
|
||||||
// No need for this kind of init since these Jokers
|
// No need for this kind of init since these Jokers
|
||||||
// will have their data copied when needed
|
// will have their data copied when needed
|
||||||
if (joker_event == JOKER_EVENT_ON_JOKER_CREATED || joker_event == JOKER_EVENT_ON_ROUND_END)
|
if (joker_event == JOKER_EVENT_ON_JOKER_CREATED ||
|
||||||
|
joker_event == JOKER_EVENT_ON_HAND_SCORED_END ||
|
||||||
|
joker_event == JOKER_EVENT_ON_ROUND_END)
|
||||||
{
|
{
|
||||||
return effect_flags_ret;
|
return effect_flags_ret;
|
||||||
}
|
}
|
||||||
@@ -1090,8 +1092,6 @@ static u32 hack_joker_effect(Joker *joker, Card *scored_card, enum JokerEvent jo
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Note: Joker expiration is not yet implemented so Seltzer cannot be made active before it does.
|
|
||||||
GBLA_UNUSED
|
|
||||||
static u32 seltzer_joker_effect(Joker *joker, Card *scored_card, enum JokerEvent joker_event, JokerEffect **joker_effect)
|
static u32 seltzer_joker_effect(Joker *joker, Card *scored_card, enum JokerEvent joker_event, JokerEffect **joker_effect)
|
||||||
{
|
{
|
||||||
u32 effect_flags_ret = JOKER_EFFECT_FLAG_NONE;
|
u32 effect_flags_ret = JOKER_EFFECT_FLAG_NONE;
|
||||||
@@ -1110,28 +1110,33 @@ static u32 seltzer_joker_effect(Joker *joker, Card *scored_card, enum JokerEvent
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case JOKER_EVENT_ON_CARD_SCORED_END:
|
case JOKER_EVENT_ON_CARD_SCORED_END:
|
||||||
// Works the same way as Dusk, but checks if it can still trigger
|
// Works the same way as Dusk
|
||||||
if (*p_hands_left_until_exp > 0)
|
// No need to check for p_hands_left_until_exp because the Joker
|
||||||
{
|
// will be destroyed the moment we hit 0
|
||||||
*joker_effect = &shared_joker_effect;
|
*joker_effect = &shared_joker_effect;
|
||||||
|
|
||||||
(*joker_effect)->retrigger = (*p_last_retriggered_idx < get_scored_card_index());
|
(*joker_effect)->retrigger = ((*p_last_retriggered_idx) < get_scored_card_index());
|
||||||
if ((*joker_effect)->retrigger)
|
if ((*joker_effect)->retrigger)
|
||||||
{
|
{
|
||||||
*p_last_retriggered_idx = get_scored_card_index();
|
*p_last_retriggered_idx = get_scored_card_index();
|
||||||
(*joker_effect)->message = "Again!";
|
(*joker_effect)->message = "Again!";
|
||||||
effect_flags_ret = JOKER_EFFECT_FLAG_RETRIGGER | JOKER_EFFECT_FLAG_MESSAGE;
|
effect_flags_ret = JOKER_EFFECT_FLAG_RETRIGGER | JOKER_EFFECT_FLAG_MESSAGE;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case JOKER_EVENT_ON_HAND_SCORED_END:
|
case JOKER_EVENT_ON_HAND_SCORED_END:
|
||||||
*joker_effect = &shared_joker_effect;
|
*joker_effect = &shared_joker_effect;
|
||||||
effect_flags_ret = JOKER_EFFECT_FLAG_MESSAGE;
|
effect_flags_ret = JOKER_EFFECT_FLAG_MESSAGE;
|
||||||
|
|
||||||
|
(*p_hands_left_until_exp)--;
|
||||||
if (*p_hands_left_until_exp > 0)
|
if (*p_hands_left_until_exp > 0)
|
||||||
{
|
{
|
||||||
*p_hands_left_until_exp -= 1;
|
// Need to do this for now because the message's memory can't really be allocated
|
||||||
(*joker_effect)->message = "-1";
|
// So we can't use snprintf to craft a message depending on the number of hands left
|
||||||
|
static const char* seltzer_messages[] = {
|
||||||
|
"1", "2", "3", "4", "5", "6", "7", "8", "9"
|
||||||
|
};
|
||||||
|
(*joker_effect)->message = (char*)seltzer_messages[(*p_hands_left_until_exp) - 1];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -1244,12 +1249,12 @@ const JokerInfo joker_registry[] =
|
|||||||
{ UNCOMMON_JOKER, 7, joker_effect_noop, }, // 48 Four Fingers
|
{ UNCOMMON_JOKER, 7, joker_effect_noop, }, // 48 Four Fingers
|
||||||
{ COMMON_JOKER, 4, scholar_joker_effect }, // 49
|
{ COMMON_JOKER, 4, scholar_joker_effect }, // 49
|
||||||
{ UNCOMMON_JOKER, 8, fibonnaci_joker_effect }, // 50
|
{ UNCOMMON_JOKER, 8, fibonnaci_joker_effect }, // 50
|
||||||
|
{ UNCOMMON_JOKER, 6, seltzer_joker_effect, }, // 51
|
||||||
|
|
||||||
// The following jokers don't have sprites yet,
|
// The following jokers don't have sprites yet,
|
||||||
// uncomment them when their sprites are added.
|
// uncomment them when their sprites are added.
|
||||||
#if 0
|
#if 0
|
||||||
|
|
||||||
{ UNCOMMON_JOKER, 6, seltzer_joker_effect, },
|
|
||||||
{ COMMON_JOKER, 5, shoot_the_moon_joker_effect, },
|
{ COMMON_JOKER, 5, shoot_the_moon_joker_effect, },
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user