Los juegos de mesa, aquel conjunto de elementos, piezas, tableros, cartas etc, que con una
idea atractiva, innovadora y sobre todo divertida fueron los dominantes durante mucho
tiempo en muchas familias por una gran cantidad de tiempo hasta que la evolución de la
tecnología y sus avances comenzaron a reinar en la raza humana, a pesar de que aun se
producen muchos juegos de mesa estos no superan las ventas generadas por suscripciones a
videojuegos para computadora, por lo tanto se tuvo que idear algo, ¿Por qué no mezclar estos
juegos que por mucho tiempo fueron los preferidos con los programas de computadoras? Esta
idea revoluciono la forma de jugar a los juegos de mesa, y los desarrolladores se pusieron
manos a la obra a crear miles de versiones de los juegos de mesa ya existentes, desde póker
con apuestas en tiempo real, hasta monopolios que incluyen a varios países, la creación de
juegos de mesa para computadora, a pesar de que no es el mas consumido actualmente fue
una gran idea para ese entonces que puso a pensar a más de un programador.
El problema consiste en crear un juego de mesa, el bingo, el cual debe ser desarrollado
utilizando el lenguaje de programación C por lo tanto es una aplicación para computadoras,
se debe manejar un cartón o tablero, estas especificaciones dejan las puertas abiertas para que
los estudiantes expandan sus conocimientos ya que pueden indagar y tratar de mejorar el
proyecto dado tal y como se hizo en la creación de este programa detallado en capítulos
siguientes.
MARCO TEORICO
Para la realización del proyecto se utilizo el famoso paradigma de diseño “divide y vencerás”
añadiéndole el paradigma “top-down”. Primeramente, el problema se dividió en partes
sencillas (realizar un cartón, un menú, un elector de números aleatorios, y un comparador de
números con el fin de verificar si el número o ficha elegida estaba en el cartón). Luego cuando
se proponía a resolver o “atacar” los problemas enlistados los mismo se volvieron a redefinir
dividiéndolos nuevamente en partes cada vez mas sencillas con el fin de que en otro momento
las funciones se pudieran volver a utilizar o dicho de otro modo, hacer el código reutilizable.
Por ejemplo, al momento de realizar la función para que el programa dibujara el cartón, este
fue dividido en varias funciones que juntas ayudan a la construcción del cartón, por ejemplo
imprimir un línea, imprimir una línea en blanco, imprimir espacios del mismo modo el resto
de los problemas fueron atacados de forma similar.
Las estructuras realizadas para la realización del proyecto fueron las siguientes:
ESTRUCTURAS: Las estructuras fueron utilizadas al momento de crear los hilos ya que
una función propia de la librería de Windows requería que en un solo parámetro se le pasaran
varios en ese caso una estructura con mas datos dentro de ella es la opción correcta.
FUNCIONES
Función utilizada para facilitar la realización del menú con ella se puede definir un “pixel” o
cuadro del tamaño que se requiera de modo que al hacer una letra esta se pueda hacer mas
grande o mas pequeña utilizando como “pixel” el código ascii 219 (█) se puede cambiar el
tamaño de una letra redefiniendo el pixel. Por ejemplo, en el programa se define un pixel con
una cantidad de dos (2) y un pixelMode de uno (1) de modo que el pixel seria
██
Con las funciones make y la función definePixel se puede dibujar una letra, con ellas se
puede dibujar letras del alfabeto por ahora solo están disponibles las letras B, I, N, G, O.
Los parámetros “position_x” y “int position_y” se utilizan para dibujarlos en cualquier
posición.
Imprime un cuadro o caja en la posición indicada por position_x y position_y, con la altura
y anchura que se quiera.
Recibe una ficha o token y un cartón de modo que la función verifica si la ficha existe en el
tablero. La función retorna uno (1) si la ficha está en el tablero y cero (0) si la no está.
getToken():
Esta función simula la elección de una ficha utilizando una pseudo animación que
intercambie varios números hasta seleccionar uno especifico que será la ficha retornada y la
cual se marcara en el tablero.
printSpaces():
printnSpaces(int nSpace):
printLine(char start, char end, char middle, int width, int x, int y):
Imprime una línea para la realización del tablero. Las variables start y end son las esquinas
de la línea por lo que se pueden cambiar por cualquier carácter mientras que la variable
middle es el final de cada casilla. La línea se puede imprimir en cualquier posición utilizando
los argumentos x y y.
Recibe una matriz con números aleatorios y a cada numero lo coloca dentro de un tablero
seguidamente lo imprime en las posiciones que se indiquen a través de las posiciones x y y.
Esta función se utiliza para obtener una serie de números aleatorios que serán los números
que se utilizarán en el tablero, se le debe pasar un numero de inicio o limite inferior y un
número final o límite superior, un arreglo en donde se colocaran cierta cantidad de números
y un limite que indica cuantos números aleatorios tendrá el arreglo.
Esta función recibe un tablero que es una matriz de números enteros y los llena con números
aleatorios dependiendo de un patrón es decir si el patrón es dos (2) la función solo elegirá
números aleatorios entre uno (1) y dos (2). La variable numBox indica el número de casillas
que tendrá que llenar la función por columna, en realidad es una convección usada para
indicar el rango de números que tendrá el arreglo, por lo tanto si le pasamos como argumento
los números seis (6) para numBox y el numero quince (15) para patrón
fillBoardWithRandomNumber llenara una matriz con números aleatorios, la primera
columna tendrá seis (6) números entre uno (1) y quince (15) la segunda entre dieciséis (16)
y treinta (30) hasta completar el tablero siguiendo este patrón.
void text (char text[10], int space, int position_x, int position_y):
Esta función permite escribir un texto con las funciones make en una posición especifica y
con la cantidad de espacios determinada por la variable space, se usa para imprimir la palabra
bingo en el menú de inicio.
void clean():
Limpia la pantalla.
esta función se encarga de inicializar la bolsa de fichas desde 0 hasta lasToken en este caso
se le pasa el número de fichas que queremos en el bingo (75).
void printfTextOnBox(int width, int heigth, char text[100], char lineUp[10], int x, int
y):
Este proceso funciona igual que la función cuadro de texto en Microsoft Word pero en la
consola, recibe una anchura una altura, el texto a ser impreso, y las posiciones donde se
imprimirá, la variable lineUp representa una propiedad de centrado, por ahora solo trabaja
con:
Imprime una línea en blanco para el cartón en las posiciones X, Y. Esta función es un
subproceso utilizado para la impresión del cartón.
Esta función inicializa un cartón. El cartón desde la vista del programador en realidad tiene
16 filas, en la primera se imprime el texto bingo y en las otras 15 se inicializa una matriz
desde el 1 al 75 en cada columna se colocan sucesiones de 15 en 15 por lo que la primera
columna contendrá números del 1 al 15, la segunda del 16 al 30 y así sucesivamente hasta
que la última columna tenga los números desde el 60 al 75. El cartón desde la vista del usuario
tendrá 6 filas y 5 columnas.
Esta función es la que se encarga de mezclar las posiciones de la matriz o cartón inicializado
por setupBoard, básicamente realiza permutaciones a las columnas de la matriz, una
permutación es la variación del orden o de la disposición de los elementos de un conjunto
ordenado o una tupla sin elementos repetidos. Esta forma de obtener una matriz aleatoria es
una implementación sencilla ya que gracias a la propiedad de permutación y a setupBoard
que inicializa la matriz en orden y con el patrón deseado, no se debe preocupar acerca de la
repetición de números en un cartón, aunque puede que al cambiar de cartón existan
posiciones que no cambien pero este problema no suele suceder a menudo y el usuario puede
volver a cambiar el carton si no es de su agrado.
changeBoard(int board[][WIDTH], int token, int whereToPrintX, int whereToPrintY):
Esta función es la que se encargar de verificar si una ficha existe en un cartón, recibe un
cartón y una ficha y verifica si dicha ficha existe en la matriz, si esta condición se cumple
cambia el valor de esa posición de la matriz donde esta la ficha por un cero (0) numero que
no existe en un juego de bingo, y si la matriz tiene una posición con el elemento 0 lo cambiara
por una marca determinada por la constante BINGO_MARCA, esta última operación es
realizada por printfBoard. Los argumentos whereToPrint indican donde se imprimirá el
cartón cambiado.
isWinner(int board[HEIGTH][WIDTH]):
Esta función permite controlar un menú vertical recibe los límites del menú (limitYUP,
limitYDOWN) de modo que se valide los limites donde el menú no debe funcionar, de igual
forma recibe la cantidad de espacios que se quiere que el selector o flecha baje y suba, este
numero siempre es el mismo y por ende las opciones del menú siempre estén separadas por
una “distancia” constante, se le debe pasar una variable por referencia que se modificara
dependiendo de la opción elegida empezando desde 1, por último se le debe pasar la posición
en X a la cual el menú debe empezar.
Esta función borra una sección o parte de la consola dependiendo de las posiciones iniciales
y finales tanto en X como en Y que son pasadas como parámetros.
Esta función imprime una cierta cantidad de textos y los centra en la pantalla, los textos son
pasados como argumentos opcionales de modo que puede imprimir la cantidad de texto que
el usuario desee.
Nargs: Cantidad de textos que se desea imprimir es la variable que define cuantos
argumentos opcionales tendrá la función.
Luego de estos tres parámetros se le deben pasar los textos a imprimir como una cadena, cada
argumento opcional representa una línea.
void desingBingoWindow():
void shuffleBag(int deckStart, int deckEnd,int array[], int downBound, int upBound):
Esta función actúa como una persona que mueve las fichas dentro de una bolsa durante un
juego de bingo, esto lo realiza por medio de un arreglo, el cual fue iniciado por la función
setup bag, y lo que hace es cambiar o permutar el arreglo intercambiando los elementos en
las posiciones inicializadas, cada vez que se obtiene una ficha esta función es llamada para
volver a mezclar o batir el arreglo “bolsa”.
Esta función es la que se encarga de sacar u obtener una ficha en conjunto con función
shuffleBag e imprimirla por pantalla.
void getTokenAnimation():
Esta función realiza una animación antes de obtener una ficha durante una partida.
RUTINAS
mainMenu(int *opt):
Esta función contiene las rutinas del menú principal, recibe una opción por referencia que
permite controlar el menú principal.
void userGuide():
secundaryMenu(int* opt):
Contiene la rutina del menú secundario donde se elige el modo de juego, por lo tanto, recibe
una opción para controlar el menú.
Esta función contiene la rutina utilizada dentro de una partida recibe dos cartones, el número
de jugadores (1 o 2 únicamente) y una bolsa o arreglo de fichas para poder comenzar la
partida.
newGame():
NOMBRE USO
RIGTH_TOP 187 //"╗" Cada una de estas constantes se usan para construir un
RIGTH_BOTTOM 188//"╝" cartón o un cuadro de texto, son constantes numéricas
RIGTH_VERTICAL 185 //"╣" a pesar de que se imprimen como caracteres, los
LEFT_TOP 201//"╔" números de las mismas son el respectivo código ascii
LEFT_BOTTOM 200//"╚" del código comentado, se realizo de esta manera
LEFT_VERTICAL 204 //"╠" debido a que Windows no permitía imprimir este tipo
HORIZONTAL 186 ///"║" de caracteres directamente.
VERTICAL 205 //"═"
TOP 203//"╦"
CENTER 206 //"╬"
BOTTOM 202 // "╩"
CLT 201 //"╔"
CLB 200 //"╚"
CRT 187 //"╗"
CRB 188 //"╝"
H 205 //"═"
V 186 //"║"
1.-Al ser realizado bajo consola la impresión y reimpresión de algunos elementos pueden
verse ralentizada debido al excesivo uso de la función gotoxy.
2.-Este mismo problema trae consigo que la interfaz grafica no sea la mas agradable a la
vista de todas.
4.-Este mismo problema trae consigo que el bingo no se pueda jugar con una n cantidad de
jugadores y los jugadores solo pueden tener hasta un cartón a diferencia del juego en la vida
real.
5.-El programa no tiene limites de entrada de datos el usuario puede presionar cualquier tecla,
pero solo las teclas validadas por el programa permitirán el buen curso del algoritmo, la
aplicación funciona por medio de las flechas del teclado y la tecla enter y algunos sub menús
permiten la salida por medio de caracteres alfabéticos.
6.-El algoritmo no permite la guardar datos a| largo plazo como por eejemplo, cerrar la partida
y reanudarla cuando se vuelva abrir el programa.
7.-debido a otros proyectos y demás actividades algunas funciones pueden no estar 100%
validadas.
8.-El programa solo puede correr en Windows ya que para que corra en linu se requiere la
instalación de librerías y ciertos programas que no fueron permitidos de instalar en el
laboratorio, sin embargo, alguien con experiencia en Linux puede fácilmente implementar
una versión del programa para dicho sistema operativo.
MANUAL DE USUARIO
Al iniciar el programa la primera pantalla que vera el usuario será el menú principal, el
jugador debe moveré mediante el uso de las flechas del teclado a través de alguna de las
opciones la primera iniciara el menú secundario la tercera es una guía dentro del programa
con las instrucciones del mismo y la tercera permite la finalización de la ejecución del
programa. Seguidamente se selecciona una opción.
z
Desde el menú secundario el usuario puede seleccionar cuantas personas jugaran con un
máximo de dos. Se debe seleccionar una opción para continuar la ejecución siempre teniendo
en cuenta que se puede volver al menú principal.
PANTALLA DE LA EJECUCION DEL MODO 2 JUGADORES
El programa permite al usuario cambiar un cartón si este no le gusta luego de que ambos
hayan seleccionado el cartón de su agrado el juego comenzara.
PANTALLA DESPUES DE HABER INICIADO EL JUEGO
Una vez una ficha es obtenida esta se marca automáticamente el uuario puede elegir si
desea continuar la partida o finalizarla.
Cuando existe un ganador el programa mostrara un mensaje con el respectivo ganador si no
hubo ganador el programa imprimirá un mensaje adecuado. Al presionar cualquier tecla el
usuario vuelve al menú de inicio a la espera de las decisiones del usuario, el modo de un solo
jugador funciona igual que el modo de dos jugadores.