mirror of
https://github.com/SpudGunMan/meshing-around.git
synced 2026-08-05 16:32:54 +02:00
ScrubUno
gone but not forgotten
This commit is contained in:
@@ -314,7 +314,6 @@ sudo apt-get install fonts-noto-color-emoji
|
||||
| `videopoker` | Plays basic 5-card hold Video Poker | ✅ |
|
||||
| `mastermind` | Plays the classic code-breaking game | ✅ |
|
||||
| `golfsim` | Plays a 9-hole Golf Simulator | ✅ |
|
||||
| `uno` | Plays Uno card game against the bot or with others on the mesh near you! | ✅ |
|
||||
|
||||
# Recognition
|
||||
|
||||
|
||||
@@ -72,7 +72,6 @@ blackjack = True
|
||||
videopoker = True
|
||||
mastermind = True
|
||||
golfsim = True
|
||||
uno = True
|
||||
|
||||
[sentry]
|
||||
# detect anyone close to the bot
|
||||
|
||||
+1
-27
@@ -10,7 +10,7 @@ from modules.log import *
|
||||
from modules.system import *
|
||||
|
||||
# list of commands to remove from the default list for DM only
|
||||
restrictedCommands = ["blackjack", "videopoker", "dopewars", "lemonstand", "golfsim", "mastermind", "uno"]
|
||||
restrictedCommands = ["blackjack", "videopoker", "dopewars", "lemonstand", "golfsim", "mastermind"]
|
||||
restrictedResponse = "🤖only available in a Direct Message📵" # "" for none
|
||||
|
||||
# Global Variables
|
||||
@@ -56,7 +56,6 @@ def auto_response(message, snr, rssi, hop, pkiStatus, message_from_id, channel_n
|
||||
"motd": lambda: handle_motd(message, message_from_id, isDM),
|
||||
"ping": lambda: handle_ping(message_from_id, deviceID, message, hop, snr, rssi, isDM),
|
||||
"pinging": lambda: handle_ping(message_from_id, deviceID, message, hop, snr, rssi, isDM),
|
||||
"playuno": lambda: handleUno(message, message_from_id, deviceID),
|
||||
"pong": lambda: "🏓PING!!🛜",
|
||||
"rlist": lambda: handle_repeaterQuery(message_from_id, deviceID, channel_number),
|
||||
"sitrep": lambda: handle_lheard(message, message_from_id, deviceID, isDM),
|
||||
@@ -550,30 +549,6 @@ def handleGolf(message, nodeID, deviceID):
|
||||
time.sleep(responseDelay + 1)
|
||||
return msg
|
||||
|
||||
def handleUno(message, nodeID, deviceID):
|
||||
global unoTracker
|
||||
msg = ''
|
||||
|
||||
# get player's last command from tracker if not new player
|
||||
last_cmd = ""
|
||||
for i in range(len(unoTracker)):
|
||||
if unoTracker[i]['nodeID'] == nodeID:
|
||||
last_cmd = unoTracker[i]['cmd']
|
||||
|
||||
if last_cmd == "" and nodeID != 0:
|
||||
# create new player
|
||||
playerName = get_name_from_number(nodeID, 'short', deviceID)
|
||||
logger.debug("System: Uno: New Player: " + str(nodeID) + " " + playerName)
|
||||
unoTracker.append({'nodeID': nodeID, 'last_played': time.time(), 'cmd': '', 'playerName': playerName})
|
||||
msg = "Welcome to 🃏 Uno!, waiting for others to join, (S)tart when ready "
|
||||
|
||||
# play the game
|
||||
msg += playUno(nodeID, message=message)
|
||||
|
||||
# wait a second to keep from message collision
|
||||
time.sleep(responseDelay + 1)
|
||||
return msg
|
||||
|
||||
def handle_wxc(message_from_id, deviceID, cmd):
|
||||
location = get_node_location(message_from_id, deviceID)
|
||||
if use_meteo_wxApi and not "wxc" in cmd and not use_metric:
|
||||
@@ -804,7 +779,6 @@ def checkPlayingGame(message_from_id, message_string, rxNode, channel_number):
|
||||
(jackTracker, "BlackJack", handleBlackJack),
|
||||
(mindTracker, "MasterMind", handleMmind),
|
||||
(golfTracker, "GolfSim", handleGolf),
|
||||
(unoTracker, "Uno", handleUno)
|
||||
]
|
||||
|
||||
for tracker, game_name, handle_game_func in trackers:
|
||||
|
||||
@@ -1,200 +0,0 @@
|
||||
# https://github.com/melvin-02/UNO-game
|
||||
# Adapted for Meshtastic mesh-bot by K7MHI Kelly Keeton 2024
|
||||
|
||||
import random
|
||||
import time
|
||||
from modules.log import *
|
||||
|
||||
color = ('RED', 'GREEN', 'BLUE', 'YELLOW')
|
||||
rank = ('0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'Skip', 'Reverse', 'Draw2', 'Draw4', 'Wild')
|
||||
ctype = {'0': 'number', '1': 'number', '2': 'number', '3': 'number', '4': 'number', '5': 'number', '6': 'number',
|
||||
'7': 'number', '8': 'number', '9': 'number', 'Skip': 'action', 'Reverse': 'action', 'Draw2': 'action',
|
||||
'Draw4': 'action_nocolor', 'Wild': 'action_nocolor'}
|
||||
|
||||
# Player List
|
||||
unoLobby = []
|
||||
unoTracker = [{'nodeID': 0, 'last_played': time.time(), 'cmd': '', 'playerName': ''}]
|
||||
unoGameTable = {'turn': -1, 'direction': 1, 'deck': None, 'hands': None, 'top_card': None}
|
||||
|
||||
class Card:
|
||||
def __init__(self, color, rank):
|
||||
self.rank = rank
|
||||
if ctype[rank] == 'number':
|
||||
self.color = color
|
||||
self.cardtype = 'number'
|
||||
elif ctype[rank] == 'action':
|
||||
self.color = color
|
||||
self.cardtype = 'action'
|
||||
else:
|
||||
self.color = None
|
||||
self.cardtype = 'action_nocolor'
|
||||
|
||||
def __str__(self):
|
||||
if self.color is None:
|
||||
return self.rank
|
||||
else:
|
||||
return self.color + " " + self.rank
|
||||
|
||||
class Deck:
|
||||
def __init__(self):
|
||||
self.deck = []
|
||||
self.discard_pile = []
|
||||
for clr in color:
|
||||
for ran in rank:
|
||||
if ctype[ran] != 'action_nocolor':
|
||||
self.deck.append(Card(clr, ran))
|
||||
self.deck.append(Card(clr, ran))
|
||||
else:
|
||||
self.deck.append(Card(clr, ran))
|
||||
|
||||
def __str__(self):
|
||||
deck_comp = ''
|
||||
for card in self.deck:
|
||||
deck_comp += '\n' + card.__str__()
|
||||
return 'The deck has ' + deck_comp
|
||||
|
||||
def shuffle(self):
|
||||
random.shuffle(self.deck)
|
||||
|
||||
def deal(self):
|
||||
if not self.deck:
|
||||
self.reshuffle_discard_pile()
|
||||
return self.deck.pop()
|
||||
|
||||
def reshuffle_discard_pile(self):
|
||||
if len(self.discard_pile) > 1:
|
||||
top_card = self.discard_pile.pop()
|
||||
self.deck = self.discard_pile[:]
|
||||
self.discard_pile = [top_card]
|
||||
self.shuffle()
|
||||
else:
|
||||
raise IndexError("No cards left to reshuffle")
|
||||
|
||||
class Hand:
|
||||
def __init__(self):
|
||||
self.cards = []
|
||||
self.cardsstr = []
|
||||
self.number_cards = 0
|
||||
self.action_cards = 0
|
||||
|
||||
def add_card(self, card):
|
||||
self.cards.append(card)
|
||||
self.cardsstr.append(str(card))
|
||||
if card.cardtype == 'number':
|
||||
self.number_cards += 1
|
||||
else:
|
||||
self.action_cards += 1
|
||||
self.sort_cards()
|
||||
|
||||
def remove_card(self, place):
|
||||
self.cardsstr.pop(place - 1)
|
||||
return self.cards.pop(place - 1)
|
||||
|
||||
def cards_in_hand(self):
|
||||
msg = ''
|
||||
for i in range(len(self.cardsstr)):
|
||||
msg += f' {i + 1}.{self.cardsstr[i]}'
|
||||
return msg
|
||||
|
||||
def single_card(self, place):
|
||||
return self.cards[place - 1]
|
||||
|
||||
def no_of_cards(self):
|
||||
return len(self.cards)
|
||||
|
||||
def sort_cards(self):
|
||||
self.cards.sort(key=lambda card: (
|
||||
card.color if card.color is not None else '',
|
||||
int(card.rank) if card.cardtype == 'number' and card.rank is not None else 0))
|
||||
self.cardsstr = [str(card) for card in self.cards]
|
||||
|
||||
def choose_first():
|
||||
global unoLobby
|
||||
if unoLobby != []:
|
||||
random_player = random.choice(unoLobby)
|
||||
return random_player
|
||||
else:
|
||||
return None
|
||||
|
||||
def single_card_check(top_card, card):
|
||||
if card.color == top_card.color or top_card.rank == card.rank or card.cardtype == 'action_nocolor':
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
def full_hand_check(hand, top_card):
|
||||
for c in hand.cards:
|
||||
if c.color == top_card.color or c.rank == top_card.rank or c.cardtype == 'action_nocolor':
|
||||
#return hand.remove_card(hand.cardsstr.index(str(c)) + 1)
|
||||
return hand.remove_card(hand.cards.index(c) + 1)
|
||||
else:
|
||||
return 'no card'
|
||||
|
||||
def win_check(hand):
|
||||
if len(hand.cards) == 0:
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
def last_card_check(hand):
|
||||
for c in hand.cards:
|
||||
if c.cardtype != 'number':
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
def getNextPlayer(playerIndex, direction=1, skip=False):
|
||||
current_index = unoLobby.index(playerIndex)
|
||||
next_index = (current_index + direction) % len(unoLobby)
|
||||
if skip:
|
||||
next_index = (next_index + direction) % len(unoLobby)
|
||||
return unoLobby[next_index]
|
||||
|
||||
def getNextPlayerID(playerIndex, direction=1, skip=False):
|
||||
current_index = unoLobby.index(playerIndex)
|
||||
next_index = (current_index + direction) % len(unoLobby)
|
||||
if skip:
|
||||
next_index = (next_index + direction) % len(unoLobby)
|
||||
return unoTracker[next_index]['nodeID']
|
||||
|
||||
def unoPlayerDetail(nodeID):
|
||||
for i in range(len(unoTracker)):
|
||||
if unoTracker[i] == nodeID:
|
||||
return f'{unoTracker[i]}'
|
||||
|
||||
def getUnoPname(nodeID):
|
||||
global unoTracker
|
||||
for i in range(len(unoTracker)):
|
||||
if unoTracker[i]['nodeID'] == nodeID:
|
||||
return unoTracker[i]['playerName']
|
||||
|
||||
def setLastCmd(nodeID, cmd):
|
||||
global unoTracker
|
||||
for i in range(len(unoTracker)):
|
||||
if unoTracker[i]['nodeID'] == nodeID:
|
||||
unoTracker[i]['cmd'] = cmd
|
||||
|
||||
def getLastCmd(nodeID):
|
||||
global unoTracker
|
||||
for i in range(len(unoTracker)):
|
||||
if unoTracker[i]['nodeID'] == nodeID:
|
||||
return unoTracker[i]['cmd']
|
||||
|
||||
def getUnoIDs():
|
||||
global unoTracker, unoLobby
|
||||
userIDlist = []
|
||||
for i in range(len(unoLobby)):
|
||||
for j in range(len(unoTracker)):
|
||||
if unoTracker[j]['playerName'] == unoLobby[i]:
|
||||
unoTracker[j]['last_played'] = time.time()
|
||||
userIDlist.append(unoTracker[j]['nodeID'])
|
||||
return (userIDlist)
|
||||
|
||||
def playUno(nodeID, message):
|
||||
global unoTracker, unoGameTable, unoLobby
|
||||
playing = False
|
||||
nextPlayerNodeID = 0
|
||||
msg = 'Not implemented yet'
|
||||
|
||||
|
||||
return msg
|
||||
@@ -160,7 +160,6 @@ try:
|
||||
videoPoker_enabled = config['games'].getboolean('videoPoker', True)
|
||||
mastermind_enabled = config['games'].getboolean('mastermind', True)
|
||||
golfSim_enabled = config['games'].getboolean('golfSim', True)
|
||||
uno_enabled = config['games'].getboolean('uno', True)
|
||||
|
||||
# messaging settings
|
||||
responseDelay = config['messagingSettings'].getfloat('responseDelay', 0.7) # default 0.7
|
||||
|
||||
@@ -129,11 +129,6 @@ if golfSim_enabled:
|
||||
from modules.games.golfsim import * # from the spudgunman/meshing-around repo
|
||||
trap_list = trap_list + ("golfsim",)
|
||||
games_enabled = True
|
||||
|
||||
if uno_enabled:
|
||||
from modules.games.uno import * # from the spudgunman/meshing-around repo
|
||||
trap_list = trap_list + ("playuno",)
|
||||
games_enabled = True
|
||||
|
||||
# Games Configuration
|
||||
if games_enabled is True:
|
||||
@@ -155,8 +150,6 @@ if games_enabled is True:
|
||||
gamesCmdList += "masterMind, "
|
||||
if golfSim_enabled:
|
||||
gamesCmdList += "golfSim, "
|
||||
if uno_enabled:
|
||||
gamesCmdList += "playuno, "
|
||||
gamesCmdList = gamesCmdList[:-2] # remove the last comma
|
||||
else:
|
||||
gamesCmdList = ""
|
||||
|
||||
Reference in New Issue
Block a user