Um jogo de damas em mbed os

Dependencies:   Terminal

Revision:
0:e1459cfa4a6a
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Sat Dec 10 17:07:22 2016 +0000
@@ -0,0 +1,1601 @@
+
+#define MINLINHA 1
+#define MAXLINHA 8
+#define MINCOLUNA 1
+#define MAXCOLUNA 8
+#define PEDRA_NORMAL_JOGADOR1 '1'
+#define PEDRA_NORMAL_JOGADOR2 '2'
+#define PEDRA_DAMA_JOGADOR1 '3'
+#define PEDRA_DAMA_JOGADOR2 '4'
+#define VAZIO 'S'
+#define JOGADA 'J'
+#define CAPTURADA 'C'
+#define BORDA "                    "
+
+#define VITORIAS 0
+#define EMPATES  1
+#define DERROTAS 2
+
+#define HUMANO1  '1'
+#define HUMANO2  '2'
+#define MAQUINA1 '3'
+#define MAQUINA2 '4'
+
+#define NOME_HUMANO1  "HUMANO1"
+#define NOME_HUMANO2  "HUMANO2"
+#define NOME_MAQUINA1 "MAQUINA1"
+#define NOME_MAQUINA2 "MAQUINA2"
+#define TAM_NOME 30
+
+#define ASCII_PEDRA_NORMAL 'O'
+#define ASCII_PEDRA_DAMA   'D'
+
+#define ENTER 13
+
+//#define __PC__ 1
+#define __EMBARCADO__ 1
+
+#ifdef __PC__
+#define _CRT_SECURE_NO_WARNINGS
+#include <stdio.h>
+#include <memory.h>
+#include <stdlib.h>
+#include <windows.h>
+#include <conio.h>
+#include <string.h>
+#define PRINTF _cprintf
+#define SLEEP  sleep
+#define FIM_DE_LINHA "\n"
+#define GETCHE _getche
+
+#define ASCII_BLOCK     219
+#define ASCII_BORDER_H  205
+#define ASCII_BORDER_V  186
+#define ASCII_BORDER_TL 201
+#define ASCII_BORDER_TR 187
+#define ASCII_BORDER_BL 200
+#define ASCII_BORDER_BR 188
+
+HANDLE hConsoleHandle;
+CONSOLE_SCREEN_BUFFER_INFO *ConsoleInfo;
+
+#define BACKGROUND_WHITE (BACKGROUND_GREEN|BACKGROUND_RED|BACKGROUND_BLUE)
+#define FOREGROUND_WHITE (FOREGROUND_GREEN|FOREGROUND_RED|FOREGROUND_BLUE)
+#define BACKGROUND_BLACK 0
+#define FOREGROUND_BLACK 0
+
+#define COR_FUNDO_BORDA BACKGROUND_BLUE
+#define COR_TEXTO_BORDA FOREGROUND_WHITE
+
+#define COR_FUNDO_CASA_SEM_PEDRA BACKGROUND_WHITE
+#define COR_TEXTO_CASA_SEM_PEDRA FOREGROUND_WHITE
+
+#define COR_FUNDO_CASA_COM_PEDRA BACKGROUND_GREEN
+#define COR_TEXTO_CASA_COM_PEDRA_VAZIO FOREGROUND_GREEN
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADOR1 FOREGROUND_WHITE
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADOR2 FOREGROUND_RED
+
+#define COR_FUNDO_CASA_COM_PEDRA_CAPTURADA (BACKGROUND_GREEN|BACKGROUND_INTENSITY)
+#define COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_VAZIO (BACKGROUND_GREEN|BACKGROUND_INTENSITY)
+#define COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR1 (COR_TEXTO_CASA_COM_PEDRA_JOGADOR1|BACKGROUND_INTENSITY)
+#define COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR2 (COR_TEXTO_CASA_COM_PEDRA_JOGADOR2|BACKGROUND_INTENSITY)
+
+#define COR_FUNDO_CASA_COM_PEDRA_JOGADA BACKGROUND_BLACK
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADA_VAZIO BACKGROUND_BLACK
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADA_JOGADOR1 COR_TEXTO_CASA_COM_PEDRA_JOGADOR1
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADA_JOGADOR2 COR_TEXTO_CASA_COM_PEDRA_JOGADOR2
+
+#define COR_FUNDO_MENSAGEM BACKGROUND_BLACK
+#define COR_TEXTO_MENSAGEM FOREGROUND_WHITE
+
+
+#else
+#include "mbed.h"
+#include "Terminal.h"
+
+//Serial pc( USBTX, USBRX);
+Terminal term(USBTX, USBRX); // tx, rx
+//#define PRINTF pc.printf
+#define PRINTF term.printf
+#define SLEEP  Thread::wait
+#define FIM_DE_LINHA "\r\n"
+#define GETCHE pega_tecla_echo
+
+#define ASCII_BLOCK     219
+#define ASCII_BORDER_H  205
+#define ASCII_BORDER_V  186
+#define ASCII_BORDER_TL 201
+#define ASCII_BORDER_TR 187
+#define ASCII_BORDER_BL 200
+#define ASCII_BORDER_BR 188
+
+#define WHITE 0xFFFFFF
+#define WHITE_DIFERENCIADO 0x888888
+#define BLACK 0x000000
+#define GREEN 0x00FF00
+#define GREEN_DIFERENCIADO 0x008800
+#define BLUE 0x0000FF
+#define BLUE_DIFERENCIADO 0x000088
+#define RED 0xFF0000
+#define RED_DIFERENCIADO 0x880000
+
+#define COR_FUNDO_BORDA BLUE
+#define COR_TEXTO_BORDA WHITE
+
+#define COR_FUNDO_CASA_SEM_PEDRA WHITE
+#define COR_TEXTO_CASA_SEM_PEDRA WHITE
+
+#define COR_FUNDO_CASA_COM_PEDRA GREEN
+#define COR_TEXTO_CASA_COM_PEDRA_VAZIO GREEN
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADOR1 WHITE
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADOR2 RED
+
+#define COR_FUNDO_CASA_COM_PEDRA_CAPTURADA GREEN_DIFERENCIADO
+#define COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_VAZIO GREEN_DIFERENCIADO
+#define COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR1 WHITE_DIFERENCIADO
+#define COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR2 RED_DIFERENCIADO
+
+#define COR_FUNDO_CASA_COM_PEDRA_JOGADA BLACK
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADA_VAZIO BLACK
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADA_JOGADOR1 COR_TEXTO_CASA_COM_PEDRA_JOGADOR1
+#define COR_TEXTO_CASA_COM_PEDRA_JOGADA_JOGADOR2 COR_TEXTO_CASA_COM_PEDRA_JOGADOR2
+
+#define COR_FUNDO_MENSAGEM BLACK
+#define COR_TEXTO_MENSAGEM WHITE
+
+
+#endif
+
+char tabuleiro_controle[MAXLINHA][MAXCOLUNA], tabuleiro_jogada[MAXLINHA][MAXCOLUNA];
+int jogadas = 0;
+int jogada_em_que_ultima_pedra_capturada = 0;
+int jogada_em_que_ultima_pedra_nomal_movimentada = 0;
+int jogada_empate_lances_especiais = 0;
+int placar[4][3];
+//int numero_pedras_para_capturar = -1;
+
+int numero_pedras_capturadas_jogador1 = 0;
+int numero_pedras_capturadas_jogador2 = 0;
+
+int numero_pedras_capturadas_antes_jogador1 = 0;
+int numero_pedras_capturadas_antes_jogador2 = 0;
+
+#ifdef __EMBARCADO__
+
+char pega_tecla_echo(void) {
+    char retorno;
+    
+    //retorno = pc.getc();
+    retorno = term.getc();
+    //pc.putc(retorno);
+    term.putc(retorno);
+    return retorno;
+}
+
+#endif
+
+void SELECIONA_COR(int cor_fundo, int cor_texto) {
+
+#ifdef __PC__
+    SetConsoleTextAttribute(hConsoleHandle, cor_fundo | cor_texto);
+#else
+    term.foreground(cor_texto);
+    term.background(cor_fundo);
+#endif
+
+}
+
+void LOCATE(int coluna, int linha) {
+
+#ifdef __PC__
+    COORD coordScreen;
+
+    coordScreen.X = coluna;
+    coordScreen.Y = linha;
+    SetConsoleCursorPosition(hConsoleHandle, coordScreen);
+#else
+    term.locate(coluna, linha);
+#endif
+
+}
+
+
+int lerIteiro(void) {
+    
+    char buffer[100+1];
+    int indice;
+    char lido;
+    
+    memset(buffer, 0, sizeof(buffer));
+    
+    for(indice = 0; indice < sizeof(buffer) - 1; ++indice) {
+        lido = GETCHE();
+        
+        if(lido == ENTER) {
+            break;
+        } else {
+            buffer[indice] = lido;
+        }
+    }
+    
+    return(atoi(buffer));
+}
+
+#ifdef __PC__
+
+void cls(HANDLE hConsole)
+{
+    COORD coordScreen = { 0, 0 };    /* here's where we'll home the
+                                     cursor */
+    BOOL bSuccess;
+    DWORD cCharsWritten;
+    CONSOLE_SCREEN_BUFFER_INFO csbi; /* to get buffer info */
+    DWORD dwConSize;                 /* number of character cells in
+                                     the current buffer */
+
+                                     /* get the number of character cells in the current buffer */
+
+    SetConsoleTextAttribute(hConsoleHandle, ConsoleInfo->wAttributes);
+
+    bSuccess = GetConsoleScreenBufferInfo(hConsole, &csbi);
+    dwConSize = csbi.dwSize.X * csbi.dwSize.Y;
+
+    /* fill the entire screen with blanks */
+
+    bSuccess = FillConsoleOutputCharacter(hConsole, (TCHAR) ' ',
+        dwConSize, coordScreen, &cCharsWritten);
+
+    /* get the current text attribute */
+
+    bSuccess = GetConsoleScreenBufferInfo(hConsole, &csbi);
+
+    /* now set the buffer's attributes accordingly */
+
+    bSuccess = FillConsoleOutputAttribute(hConsole, csbi.wAttributes,
+        dwConSize, coordScreen, &cCharsWritten);
+
+    /* put the cursor at (0, 0) */
+
+    bSuccess = SetConsoleCursorPosition(hConsole, coordScreen);
+    return;
+}
+
+void LimparTela(void) {
+    //system("CLS");
+    cls(hConsoleHandle);
+}
+
+#else
+    
+void LimparTela(void) {
+    //PRINTF("\033[2J\033[1;1H");
+    //PRINTF("\e[1;1H\e[2J");
+    term.cls();
+}
+
+#endif
+
+char * retorna_nome_jogador(char opcao1, char *nome) {
+
+    switch (opcao1) {
+        case HUMANO1:
+            strcpy(nome, NOME_HUMANO1);
+            break;
+        case HUMANO2:
+            strcpy(nome, NOME_HUMANO2);
+            break;
+        case MAQUINA1:
+            strcpy(nome, NOME_MAQUINA1);
+            break;
+        case MAQUINA2:
+            strcpy(nome, NOME_MAQUINA2);
+            break;
+    }
+
+    return nome;
+}
+
+char * retorna_nome_jogador_tipo_jogo(int indice, char opcao1, char *nome) {
+
+    switch(opcao1) {
+        case '1':
+            if(indice == 1) {
+                strcpy(nome, NOME_HUMANO1);
+            } else {
+                strcpy(nome, NOME_HUMANO2);
+            }
+            break;
+        case '2':
+            if(indice == 1) {
+                strcpy(nome, NOME_HUMANO1);
+            } else {
+                strcpy(nome, NOME_MAQUINA1);
+            }
+            break;
+        case '3':
+            if(indice == 1) {
+                strcpy(nome, NOME_MAQUINA1);
+            } else {
+                strcpy(nome, NOME_MAQUINA2);
+            }
+            break;
+    }
+    
+    return nome;
+}
+
+char retorna_jogador(int indice, char opcao1) {
+    
+    char jogador;
+
+    switch(opcao1) {
+        case '1':
+            if(indice == 1) {
+                jogador = HUMANO1;
+            } else {
+                jogador = HUMANO2;
+            }
+            break;
+        case '2':
+            if(indice == 1) {
+                jogador = HUMANO1;
+            } else {
+                jogador = MAQUINA1;
+            }
+            break;
+        case '3':
+            if(indice == 1) {
+                jogador = MAQUINA1;
+            } else {
+                jogador = MAQUINA2;
+            }
+            break;
+    }
+    
+    return jogador;
+}
+
+void imprime_placar(void) {
+    
+    char nome[TAM_NOME + 1];
+    int indice, tamanho;
+
+    LimparTela();
+
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    LOCATE(10, 1);
+    PRINTF("PLACAR%s", FIM_DE_LINHA);
+    PRINTF("%- *.*s|VITORIAS|EMPATES|DERROTAS%s", TAM_NOME, TAM_NOME, "JOGADOR", FIM_DE_LINHA);
+    
+    tamanho = TAM_NOME + 1 + strlen("VITORIAS") + 1 + strlen("EMPATES") + 1 + strlen("DERROTAS");
+
+    for (indice = 0; indice < tamanho; ++indice) {
+        PRINTF("%c", ASCII_BORDER_H);
+    }
+    PRINTF("%s", FIM_DE_LINHA);
+
+
+
+    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+    PRINTF("%- *.*s|%0*d|%0*d|%0*d%s", 
+        TAM_NOME, TAM_NOME, retorna_nome_jogador(HUMANO1, nome), 
+        strlen("VITORIAS"), placar[HUMANO1 - '1'][VITORIAS],
+        strlen("EMPATES"), placar[HUMANO1 - '1'][EMPATES],
+        strlen("DERROTAS"), placar[HUMANO1 - '1'][DERROTAS], FIM_DE_LINHA);
+    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+    PRINTF("%- *.*s|%0*d|%0*d|%0*d%s",
+        TAM_NOME, TAM_NOME, retorna_nome_jogador(HUMANO2, nome),
+        strlen("VITORIAS"), placar[HUMANO2 - '1'][VITORIAS],
+        strlen("EMPATES"), placar[HUMANO2 - '1'][EMPATES],
+        strlen("DERROTAS"), placar[HUMANO2 - '1'][DERROTAS], FIM_DE_LINHA);
+#if 0
+    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+    PRINTF("%- *.*s|%0*d|%0*d|%0*d%s",
+        TAM_NOME, TAM_NOME, retorna_nome_jogador(MAQUINA1, nome),
+        strlen("VITORIAS"), placar[MAQUINA1 - '1'][VITORIAS],
+        strlen("EMPATES"), placar[MAQUINA1 - '1'][EMPATES],
+        strlen("DERROTAS"), placar[MAQUINA1 - '1'][DERROTAS], FIM_DE_LINHA);
+    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+    PRINTF("%- *.*s|%0*d|%0*d|%0*d%s",
+        TAM_NOME, TAM_NOME, retorna_nome_jogador(MAQUINA2, nome),
+        strlen("VITORIAS"), placar[MAQUINA2 - '1'][VITORIAS],
+        strlen("EMPATES"), placar[MAQUINA2 - '1'][EMPATES],
+        strlen("DERROTAS"), placar[MAQUINA2 - '1'][DERROTAS], FIM_DE_LINHA);
+#endif
+
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    PRINTF("%s", FIM_DE_LINHA);
+    PRINTF("Pressione <Qualquer Tecla>");
+    GETCHE();
+}
+
+
+void ImprimeMenu(char &jogador1, char &jogador2) {
+    
+    char opcao1, opcao2;
+    int indice;
+    char nome[TAM_NOME + 1];
+    
+    do {
+        LimparTela();
+        SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+        PRINTF("1 - %s  X %s%s", NOME_HUMANO1, NOME_HUMANO2, FIM_DE_LINHA);
+#if 0
+        PRINTF("2 - %s  X %s%s", NOME_HUMANO1, NOME_MAQUINA1, FIM_DE_LINHA);
+        PRINTF("3 - %s X %s%s",  NOME_MAQUINA1, NOME_MAQUINA2, FIM_DE_LINHA);
+#endif
+        //PRINTF("4 - PLACAR%s", FIM_DE_LINHA);
+        PRINTF("2 - PLACAR%s", FIM_DE_LINHA);
+        
+        opcao1 = GETCHE();
+        
+        //if(opcao1 == '4') {
+        if (opcao1 == '2') {
+            imprime_placar();
+        }
+        
+    } while( opcao1 < '1'  || opcao1 > '1' );
+    
+    do {
+        indice = 0;
+        LimparTela();
+        ++indice;
+        SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+        PRINTF("%d - %s INICIA O JOGO%s", indice, retorna_nome_jogador_tipo_jogo(indice, opcao1, nome), FIM_DE_LINHA);
+        ++indice;
+        PRINTF("%d - %s INICIA O JOGO%s", indice, retorna_nome_jogador_tipo_jogo(indice, opcao1, nome), FIM_DE_LINHA);
+        
+        opcao2 = GETCHE();
+    } while( opcao2 < '1'  || opcao2 > '2' );
+    
+    if(opcao2 == '1') {
+        jogador1 = retorna_jogador(1, opcao1);
+        jogador2 = retorna_jogador(2, opcao1);
+    } else {
+        jogador1 = retorna_jogador(2, opcao1);
+        jogador2 = retorna_jogador(1, opcao1);
+    }
+
+    LimparTela();
+    
+}
+
+void InicializarTabuleiro(char jogador_que_inicia, char segundo_jogador) {
+    
+    int indice1, indice2;
+    
+    memset(tabuleiro_jogada, VAZIO, sizeof(tabuleiro_controle));
+    
+    for(indice1 = 0; indice1 < MAXCOLUNA; ++indice1) {
+        //for(indice2 = 0; indice2 < ((MAXLINHA/2)-1); ++indice2) {
+        for (indice2 = 0; indice2 < 1; ++indice2) {
+            if( (indice2 == 0) || (indice2 == 2) ){
+                if((indice1%2) == 1) {
+                    tabuleiro_jogada[indice2][indice1] = segundo_jogador;
+                }
+            } else {
+                if((indice1%2) == 0) {
+                    tabuleiro_jogada[indice2][indice1] = segundo_jogador;
+                }
+            }
+        }
+    }
+    
+    for(indice1 = 0; indice1 < MAXCOLUNA; ++indice1) {
+        for(indice2 = (MAXLINHA - 1); indice2 > (MAXLINHA/2); --indice2) {
+            if(indice2 == 6){
+                if((indice1%2) == 1) {
+                    tabuleiro_jogada[indice2][indice1] = jogador_que_inicia;
+                }
+            } else {
+                if((indice1%2) == 0) {
+                    tabuleiro_jogada[indice2][indice1] = jogador_que_inicia;
+                }
+            }
+        }
+    }
+    
+    memcpy(tabuleiro_controle, tabuleiro_jogada, sizeof(tabuleiro_jogada));
+}
+
+void ImprimirTabuleiro(char jogador1, char jogador2) {
+    
+    char nome1[TAM_NOME + 1];
+    char nome2[TAM_NOME + 1];
+    int linha, coluna;
+
+    LimparTela();
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+
+    LOCATE(10, 1);
+    PRINTF("PARTIDA DE DAMAS ");
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+    PRINTF("%s", retorna_nome_jogador(jogador1, nome1));
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    PRINTF("(%d) VERSUS ", numero_pedras_capturadas_jogador1);
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+    PRINTF("%s", retorna_nome_jogador(jogador2, nome2));
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    PRINTF("(%d) % s", numero_pedras_capturadas_jogador2, FIM_DE_LINHA);
+
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    PRINTF("%s", BORDA);
+
+    SELECIONA_COR(COR_FUNDO_BORDA, COR_TEXTO_BORDA);
+    PRINTF("  12345678 %s", FIM_DE_LINHA);
+
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    PRINTF("%s", BORDA);
+
+    SELECIONA_COR(COR_FUNDO_BORDA, COR_TEXTO_BORDA);
+    PRINTF(" %c", ASCII_BORDER_TL);
+    for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+        PRINTF("%c", ASCII_BORDER_H);
+    }
+    PRINTF("%c%s", ASCII_BORDER_TR, FIM_DE_LINHA);
+
+    for (linha = 0; linha < MAXLINHA; ++linha) {
+
+        SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+        PRINTF("%s", BORDA);
+
+        SELECIONA_COR(COR_FUNDO_BORDA, COR_TEXTO_BORDA);
+        PRINTF("%d%c", linha + 1, ASCII_BORDER_V);
+        if (linha % 2 == 0) {
+            // Este tipo de linha comeca com um tipo de casa na qual 
+            //  as pedras nao podem se movimentar
+            for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+                if (coluna % 2 == 0) {
+                    SELECIONA_COR(COR_FUNDO_CASA_SEM_PEDRA, COR_TEXTO_CASA_SEM_PEDRA);
+                    PRINTF(" ");
+                }
+                else {
+                    switch (tabuleiro_jogada[linha][coluna]) {
+                        case PEDRA_NORMAL_JOGADOR1:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+                            PRINTF("%c", ASCII_PEDRA_NORMAL);
+                            break;
+                        case PEDRA_NORMAL_JOGADOR2:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+                            PRINTF("%c", ASCII_PEDRA_NORMAL);
+                            break;
+                        case PEDRA_DAMA_JOGADOR1:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+                            PRINTF("%c", ASCII_PEDRA_DAMA);
+                            break;
+                        case PEDRA_DAMA_JOGADOR2:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+                            PRINTF("%c", ASCII_PEDRA_DAMA);
+                            break;
+                        case VAZIO:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_VAZIO);
+                            PRINTF(" ");
+                            break;
+                        case JOGADA:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_JOGADA, COR_TEXTO_CASA_COM_PEDRA_JOGADA_VAZIO);
+                            PRINTF(" ");
+                            break;
+                        case CAPTURADA:
+                            switch (tabuleiro_controle[linha][coluna]) {
+                                case PEDRA_NORMAL_JOGADOR1:
+                                    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR1);
+                                    PRINTF("%c", ASCII_PEDRA_NORMAL);
+                                    break;
+                                case PEDRA_DAMA_JOGADOR1:
+                                    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR1);
+                                    PRINTF("%c", ASCII_PEDRA_DAMA);
+                                    break;
+                                case PEDRA_NORMAL_JOGADOR2:
+                                    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR2);
+                                    PRINTF("%c", ASCII_PEDRA_NORMAL);
+                                    break;
+                                case PEDRA_DAMA_JOGADOR2:
+                                    SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR2);
+                                    PRINTF("%c", ASCII_PEDRA_DAMA);
+                                    break;
+                            }
+                            break;
+                    }
+                }
+            }
+            SELECIONA_COR(COR_FUNDO_BORDA, COR_TEXTO_BORDA);
+            PRINTF("%c", ASCII_BORDER_V);
+            PRINTF("%s", FIM_DE_LINHA);
+        }
+        else {
+            // Este tipo de linha comeca com um tipo de casa na qual 
+            //  as pedras podem se movimentar
+            for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+                if (coluna % 2 == 1) {
+                    SELECIONA_COR(COR_FUNDO_CASA_SEM_PEDRA, COR_TEXTO_CASA_SEM_PEDRA);
+                    PRINTF(" ");
+                }
+                else {
+                    switch (tabuleiro_jogada[linha][coluna]) {
+                    case PEDRA_NORMAL_JOGADOR1:
+                        SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+                        PRINTF("%c", ASCII_PEDRA_NORMAL);
+                        break;
+                    case PEDRA_NORMAL_JOGADOR2:
+                        SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+                        PRINTF("%c", ASCII_PEDRA_NORMAL);
+                        break;
+                    case PEDRA_DAMA_JOGADOR1:
+                        SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR1);
+                        PRINTF("%c", ASCII_PEDRA_DAMA);
+                        break;
+                    case PEDRA_DAMA_JOGADOR2:
+                        SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_JOGADOR2);
+                        PRINTF("%c", ASCII_PEDRA_DAMA);
+                        break;
+                    case VAZIO:
+                        SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA, COR_TEXTO_CASA_COM_PEDRA_VAZIO);
+                        PRINTF(" ");
+                        break;
+                    case JOGADA:
+                        SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_JOGADA, COR_TEXTO_CASA_COM_PEDRA_JOGADA_VAZIO);
+                        PRINTF(" ");
+                        break;
+                    case CAPTURADA:
+                        switch (tabuleiro_controle[linha][coluna]) {
+                        case PEDRA_NORMAL_JOGADOR1:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR1);
+                            PRINTF("%c", ASCII_PEDRA_NORMAL);
+                            break;
+                        case PEDRA_DAMA_JOGADOR1:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR1);
+                            PRINTF("%c", ASCII_PEDRA_DAMA);
+                            break;
+                        case PEDRA_NORMAL_JOGADOR2:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR2);
+                            PRINTF("%c", ASCII_PEDRA_NORMAL);
+                            break;
+                        case PEDRA_DAMA_JOGADOR2:
+                            SELECIONA_COR(COR_FUNDO_CASA_COM_PEDRA_CAPTURADA, COR_TEXTO_CASA_COM_PEDRA_CAPTURADA_JOGADOR2);
+                            PRINTF("%c", ASCII_PEDRA_DAMA);
+                            break;
+                        }
+                        break;
+                    }
+                }
+            }
+            SELECIONA_COR(COR_FUNDO_BORDA, COR_TEXTO_BORDA);
+            PRINTF("%c", ASCII_BORDER_V);
+            PRINTF("%s", FIM_DE_LINHA);
+        }
+    }
+
+    SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+    PRINTF("%s", BORDA);
+
+    SELECIONA_COR(COR_FUNDO_BORDA, COR_TEXTO_BORDA);
+    PRINTF(" %c", ASCII_BORDER_BL);
+    for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+        PRINTF("%c", ASCII_BORDER_H);
+    }
+    PRINTF("%c%s", ASCII_BORDER_BR, FIM_DE_LINHA);
+}
+
+// 0 - Movimento simples
+// 1 - Movimento com multiplas capturas
+int Movimento_Multiplo(void) {
+
+    int linha, coluna;
+
+    return 0;
+
+    for (linha = 0; linha < MAXLINHA; ++linha) {
+        for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+            if (tabuleiro_jogada[linha][coluna] == JOGADA) {
+                // nao pode jogar sem capturar em uma jogada com multiplas capturas
+                return 1;
+            }
+        }
+    }
+    return 0;
+}
+
+// 0 - Movimento de pedra simples nao eh para traz
+// 1 - Movimento de pedra simples eh para traz
+int Movimento_Para_Traz(int linha_origem, int linha_destino, char jogador1, char jogador_vez) {
+
+    int retorno = 0;
+
+    // O jogador 1 sempre começa o jogo e ele sempre inicia a partir da parte de baixo do tabuleiro
+    if (jogador_vez == jogador1) {
+        if ((linha_origem - linha_destino) <= 0) {
+            retorno = 1;
+        }
+    }
+    else {
+        if ((linha_destino - linha_origem) <= 0) {
+            retorno = 1;
+        }
+    }
+
+    return retorno;
+}
+
+// retorna numero de pedras que faltam capturar
+int Existe_Pedra_Para_Capturar(void) {
+
+    return 0;
+#if 0
+    if ( (numero_pedras_para_capturar == -1) || (numero_pedras_para_capturar == 0) ) {
+        return 0;
+    }
+    return numero_pedras_para_capturar;
+#endif
+}
+
+char Posiciona_Pedra(int linha_origem, int coluna_origem, int linha_destino, int coluna_destino, char jogador_vez, char jogador1) {
+    char retorno;
+
+    // O jogador 1 sempre começa o jogo e ele sempre inicia a partir da parte de baixo do tabuleiro
+    if (jogador_vez == jogador1) {
+        //if ( (linha_destino == (MINLINHA - 1)) && ( (numero_pedras_para_capturar == -1) || (numero_pedras_para_capturar == 0)) ) {
+        if (linha_destino == (MINLINHA - 1)) {
+            retorno = PEDRA_DAMA_JOGADOR1;
+        }
+        else {
+            retorno = tabuleiro_jogada[linha_origem][coluna_origem];
+        }
+    }
+    else {
+        //if ((linha_destino == (MAXLINHA - 1)) && ((numero_pedras_para_capturar == -1) || (numero_pedras_para_capturar == 0))) {
+        if (linha_destino == (MAXLINHA - 1)) {
+            retorno = PEDRA_DAMA_JOGADOR2;
+        }
+        else {
+            retorno = tabuleiro_jogada[linha_origem][coluna_origem];
+        }
+    }
+
+    return retorno;
+}
+
+// 0 - Esta no caminho maximo de captura
+// 1 - Nao esta no caminho maximo de captura
+int Caminho_Maximo_Captura(int linha_origem, int coluna_origem, int linha_destino, int coluna_destino) {
+    // @todo fazer funcao
+    //int retorno = 1;
+    int retorno = 0;
+
+    return retorno;
+}
+
+void Calcula_Quantidade_Maxima_Capturas(char jogador_vez, char jogador1, char jogador2) {
+
+    // @todo fazer funcao
+
+    return;
+
+    //if (numero_pedras_para_capturar > 0) {
+    //    return;  // funcao ja foi executada
+    //}
+
+}
+
+void contabiliza_pedra(char jogador_vez, char jogador1, char jogador2) {
+
+    if (jogador_vez == jogador1) {
+        ++numero_pedras_capturadas_jogador1;
+    }
+    else {
+        ++numero_pedras_capturadas_jogador2;
+    }
+}
+
+// 0 - Movimento Invalido
+// 1 - Movimento Valido
+int Movimento_Valido(int &linha_origem, int &coluna_origem, int &linha_destino, int &coluna_destino, char jogador_vez, char jogador1, char jogador2) {
+
+    char pedra_normal = 1;
+    char pedra_normal_oponente;
+    char pedra_dama_oponente;
+    char pedra_normal_jogador;
+    char pedra_dama_jogador;
+    int  unidade_linha, unidade_coluna, linha_aux, coluna_aux, pedras_capturadas;
+    int  linha_pedra_capturada, coluna_pedra_capturada;
+
+    // Valida se existe uma pedra deste jogador no tabuleiro de jogada na posicao de origem.
+    // O tabuleiro de jogada server para guardar a memoria de uma jogada com multiplas capturas, 
+    //  por isso que´eh utilizado para validar as jogadas.
+    if (jogador_vez == jogador1) {
+        pedra_normal_jogador = PEDRA_NORMAL_JOGADOR1;
+        pedra_dama_jogador = PEDRA_DAMA_JOGADOR1;
+        pedra_normal_oponente = PEDRA_NORMAL_JOGADOR2;
+        pedra_dama_oponente = PEDRA_DAMA_JOGADOR2;
+        if (tabuleiro_jogada[linha_origem][coluna_origem] == PEDRA_NORMAL_JOGADOR1) {
+        } else if (tabuleiro_jogada[linha_origem][coluna_origem] == PEDRA_DAMA_JOGADOR1) {
+            pedra_normal = 0;
+        } else {
+            return 0; // pedra nao pertence ao jogador
+        }
+    }
+    else {
+        pedra_normal_jogador = PEDRA_NORMAL_JOGADOR2;
+        pedra_dama_jogador = PEDRA_DAMA_JOGADOR2;
+        pedra_normal_oponente = PEDRA_NORMAL_JOGADOR1;
+        pedra_dama_oponente = PEDRA_DAMA_JOGADOR1;
+        if (tabuleiro_jogada[linha_origem][coluna_origem] == PEDRA_NORMAL_JOGADOR2) {
+        } else if (tabuleiro_jogada[linha_origem][coluna_origem] == PEDRA_DAMA_JOGADOR2) {
+            pedra_normal = 0;
+        }
+        else {
+            return 0; // pedra nao pertence ao jogador
+        }
+    }
+
+    Calcula_Quantidade_Maxima_Capturas(jogador_vez, jogador1, jogador2);
+
+    if (pedra_normal) {
+        // pedra jogada eh normal
+        // valida se a coordenada de destino eh valida para uma captura
+        if ((linha_origem - linha_destino) == 2) { 
+            if ((coluna_origem - coluna_destino) == 2) {
+                if (Caminho_Maximo_Captura(linha_origem, coluna_origem, linha_destino, coluna_destino)) {
+                    return 0; // Eh obrigatorio executar a jogada que 
+                              //   captura o maximo de pedras do adversario
+                }
+                // diagonal para cima e para esquerda 
+                if ( (tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) || 
+                     (tabuleiro_jogada[linha_destino][coluna_destino] == JOGADA) ) { // a posicao destino deve estar vazia ou foi uma jogada 
+                    if (tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] == pedra_normal_oponente) {
+                        // pedra normal do oponente capturada
+                        tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] = 
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino, 
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else if (tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] == pedra_dama_oponente) {
+                        // pedra dama do oponente capturada
+                        tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else {
+                        // pedra capturada invalida!!
+                        return 0;
+                    }
+                }
+                else {
+                    return 0;  // casa destino ocupada!!
+                }
+            }
+            else if ((coluna_destino - coluna_origem) == 2) {
+                if (Caminho_Maximo_Captura(linha_origem, coluna_origem, linha_destino, coluna_destino)) {
+                    return 0; // Eh obrigatorio executar a jogada que 
+                              //   captura o maximo de pedras do adversario
+                }
+                // diagonal para cima e para direita
+                if ((tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) ||
+                    (tabuleiro_jogada[linha_destino][coluna_destino] == JOGADA)) { // a posicao destino deve estar vazia ou foi uma jogada 
+                    if (tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] == pedra_normal_oponente) {
+                        // pedra normal do oponente capturada
+                        tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else if (tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] == pedra_dama_oponente) {
+                        // pedra dama do oponente capturada
+                        tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else {
+                        // pedra capturada invalida!!
+                        return 0;
+                    }
+                }
+                else {
+                    // casa destino ocupada!!
+                    return 0;
+                }
+            }
+            else {
+                // uma jogada de uma pedra normal apenas pode capturar uma pedra para esquerda ou para direita em diagonal
+                return 0;
+            }
+        } else if ((linha_destino - linha_origem) == 2) {
+            if ((coluna_origem - coluna_destino) == 2) {
+                if (Caminho_Maximo_Captura(linha_origem, coluna_origem, linha_destino, coluna_destino)) {
+                    return 0; // Eh obrigatorio executar a jogada que 
+                              //   captura o maximo de pedras do adversario
+                }
+                // diagonal para baixo e para esquerda 
+                if ((tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) ||
+                    (tabuleiro_jogada[linha_destino][coluna_destino] == JOGADA)) { // a posicao destino deve estar vazia ou foi uma jogada 
+                    if (tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] == pedra_normal_oponente) {
+                        // pedra normal do oponente capturada
+                        tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else if (tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] == pedra_dama_oponente) {
+                        // pedra dama do oponente capturada
+                        tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else {
+                        // pedra capturada invalida!!
+                        return 0;
+                    }
+                }
+                else {
+                    // casa destino ocupada!!
+                    return 0;
+                }
+            }
+            else if ((coluna_destino - coluna_origem) == 2) {
+                if (Caminho_Maximo_Captura(linha_origem, coluna_origem, linha_destino, coluna_destino)) {
+                    return 0; // Eh obrigatorio executar a jogada que 
+                              //   captura o maximo de pedras do adversario
+                }
+                // diagonal para baixo e para direita
+                if ((tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) ||
+                    (tabuleiro_jogada[linha_destino][coluna_destino] == JOGADA)) { // a posicao destino deve estar vazia ou foi uma jogada 
+                    if (tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] == pedra_normal_oponente) {
+                        // pedra normal do oponente capturada
+                        tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else if (tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] == pedra_dama_oponente) {
+                        // pedra dama do oponente capturada
+                        tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] = CAPTURADA;
+                        //--numero_pedras_para_capturar;
+                        contabiliza_pedra(jogador_vez, jogador1, jogador2);
+                        jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+                        tabuleiro_jogada[linha_destino][coluna_destino] =
+                            Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                                jogador_vez, jogador1);
+                        tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+                    }
+                    else {
+                        // pedra capturada invalida!!
+                        return 0;
+                    }
+                }
+                else {
+                    // casa destino ocupada!!
+                    return 0;
+                }
+            }
+            else {
+                // uma jogada de uma pedra normal apenas pode capturar uma pedra para esquerda ou para direita em diagonal
+                return 0;
+            }
+        }
+        else if ((linha_origem - linha_destino) == 1) {
+            if (Movimento_Para_Traz(linha_origem, linha_destino, jogador1, jogador_vez)) {
+                return 0; // Uma pedra simples nao pode se movimentar para traz
+            }
+            else if (Existe_Pedra_Para_Capturar()) {
+                return 0; // Eh obrigatorio capturar uma pedra
+            }
+            else if (Movimento_Multiplo()) {
+                return 0; // Movimento de multiplas capturas, nao pode fazer um movimento simples apos a captura
+            }
+            // pedra fez um movimento, nao esta capturando uma pedra
+            if ((coluna_origem - coluna_destino) == 1) {
+                // diagonal para cima e para esquerda 
+                if (tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) { // a posicao destino deve estar vazia
+                    tabuleiro_jogada[linha_destino][coluna_destino] =
+                        Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                            jogador_vez, jogador1);;
+                    jogada_em_que_ultima_pedra_nomal_movimentada = jogadas + 1;
+                    tabuleiro_jogada[linha_origem][coluna_origem] = VAZIO;
+                }
+                else {
+                    return 0;
+                }
+            }
+            else if ((coluna_destino - coluna_origem) == 1) {
+                // diagonal para cima e para direita
+                if (tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) { // a posicao destino deve estar vazia 
+                    tabuleiro_jogada[linha_destino][coluna_destino] =
+                        Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                            jogador_vez, jogador1);
+                    jogada_em_que_ultima_pedra_nomal_movimentada = jogadas + 1;
+                    tabuleiro_jogada[linha_origem][coluna_origem] = VAZIO;
+                }
+                else {
+                    // casa destino ocupada!!
+                    return 0;
+                }
+            }
+            else {
+                // uma jogada de uma pedra normal apenas pode andar uma casa para esquerda ou para direita em diagonal
+                return 0;
+            }
+        }
+        else if ((linha_destino - linha_origem) == 1) {
+            if (Movimento_Para_Traz(linha_origem, linha_destino, jogador1, jogador_vez)) {
+                return 0; // Uma pedra simples nao pode se movimentar para traz
+            }
+            else if (Existe_Pedra_Para_Capturar()) {
+                return 0; // Eh obrigatorio capturar uma pedra
+            }
+            else if (Movimento_Multiplo()) {
+                return 0; // Movimento de multiplas capturas, nao pode fazer um movimento simples apos a captura
+            }
+            if ((coluna_origem - coluna_destino) == 1) {
+                // diagonal para baixo e para esquerda 
+                if (tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) { // a posicao destino deve estar vazia 
+                    tabuleiro_jogada[linha_destino][coluna_destino] =
+                        Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                            jogador_vez, jogador1);
+                    jogada_em_que_ultima_pedra_nomal_movimentada = jogadas + 1;
+                    tabuleiro_jogada[linha_origem][coluna_origem] = VAZIO;
+                }
+                else {
+                    // casa destino ocupada!!
+                    return 0;
+                }
+            }
+            else if ((coluna_destino - coluna_origem) == 1) {
+                // diagonal para baixo e para direita
+                if (tabuleiro_jogada[linha_destino][coluna_destino] == VAZIO) { // a posicao destino deve estar vazia 
+                    tabuleiro_jogada[linha_destino][coluna_destino] =
+                        Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                            jogador_vez, jogador1);
+                    jogada_em_que_ultima_pedra_nomal_movimentada = jogadas + 1;
+                    tabuleiro_jogada[linha_origem][coluna_origem] = VAZIO;
+                }
+                else {
+                    // casa destino ocupada!!
+                    return 0;
+                }
+            }
+            else {
+                // uma jogada de uma pedra normal apenas pode andar uma casa para esquerda ou para direita em diagonal
+                return 0;
+            }
+        }
+        else {
+            // pedra normal executou um movimento invalido!!
+            return 0;
+        }
+    } else {
+        
+        if (tabuleiro_jogada[linha_destino][coluna_destino] != VAZIO) {
+            return 0; // A dama nao pode movimentar-se para uma casa ocupada
+        }
+
+        linha_aux = linha_origem;
+        coluna_aux = coluna_origem;
+        if (coluna_origem > coluna_destino) {
+            unidade_coluna = -1;
+        }
+        else {
+            unidade_coluna = 1;
+        }
+
+        if (linha_origem > linha_destino) {
+            unidade_linha = -1;
+        }
+        else {
+            unidade_linha = 1;
+        }
+
+        pedras_capturadas = 0;
+
+        do {
+            linha_aux += unidade_linha;
+            coluna_aux += unidade_coluna;
+
+            if ((tabuleiro_jogada[linha_aux][coluna_aux] == pedra_normal_jogador) || 
+                (tabuleiro_jogada[linha_aux][coluna_aux] == pedra_dama_jogador)) {
+                return 0;  // Dama nao pode pular pedras do mesmo jogador
+            } else if ((tabuleiro_jogada[linha_aux][coluna_aux] == pedra_normal_oponente) ||
+                (tabuleiro_jogada[linha_aux][coluna_aux] == pedra_dama_oponente)) {
+                ++pedras_capturadas;  // A dama capturou uma pedra do oponente
+                linha_pedra_capturada = linha_aux;
+                coluna_pedra_capturada = coluna_aux;
+            }
+
+            if (pedras_capturadas > 1) {
+                return 0; // A dama nao pode capturar mais de uma pedra em um unico movimento
+            }
+
+        } while (linha_aux != linha_destino);
+
+        if ((pedras_capturadas == 0) && (Existe_Pedra_Para_Capturar() || Movimento_Multiplo())) {
+            return 0; // Eh obrigatorio a captura
+        } else if (Caminho_Maximo_Captura(linha_origem, coluna_origem, linha_destino, coluna_destino)) {
+            return 0; // Eh obrigatorio executar a jogada que 
+                      //   captura o maximo de pedras do adversario
+        }
+
+        if (pedras_capturadas == 1) {
+            contabiliza_pedra(jogador_vez, jogador1, jogador2);
+            jogada_em_que_ultima_pedra_capturada = jogadas + 1;
+            tabuleiro_jogada[linha_destino][coluna_destino] =
+                Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                    jogador_vez, jogador1);
+            tabuleiro_jogada[linha_origem][coluna_origem] = JOGADA;
+            tabuleiro_jogada[linha_pedra_capturada][coluna_pedra_capturada] = CAPTURADA;
+        }
+        else {
+            tabuleiro_jogada[linha_destino][coluna_destino] =
+                Posiciona_Pedra(linha_origem, coluna_origem, linha_destino, coluna_destino,
+                    jogador_vez, jogador1);
+            jogada_em_que_ultima_pedra_nomal_movimentada = jogadas + 1;
+            tabuleiro_jogada[linha_origem][coluna_origem] = VAZIO;
+        }
+    }
+
+    return 1;
+}
+
+// 0 - Faixa invalida
+// 1 - Faixa valida
+int Faixa_Valida(int linha_origem, int coluna_origem, int linha_destino, int coluna_destino) {
+    
+    int retorno = 1;
+
+    // Testa a faixa de valores
+    if ( (linha_origem < 0) || (linha_origem > (MAXLINHA - 1)) ) {
+        retorno = 0;
+    }
+    else if ((linha_destino < 0) || (linha_destino > (MAXLINHA - 1))) {
+        retorno = 0;
+    }
+    else if ((coluna_origem < 0) || (coluna_origem > (MAXCOLUNA - 1))) {
+        retorno = 0;
+    }
+    else if ((coluna_destino < 0) || (coluna_destino > (MAXCOLUNA - 1))) {
+        retorno = 0;
+    }
+    // Testa se eh uma casa de movimentacao de pedra
+    else if ( (linha_origem % 2 == 0) && (coluna_origem % 2 == 0) ) {
+        retorno = 0;
+    }
+    else if ((linha_destino % 2 == 0) && (coluna_destino % 2 == 0)) {
+        retorno = 0;
+    }
+    else if ((linha_origem % 2 == 1) && (coluna_origem % 2 == 1)) {
+        retorno = 0;
+    }
+    else if ((linha_destino % 2 == 1) && (coluna_destino % 2 == 1)) {
+        retorno = 0;
+    }
+
+    return retorno;
+}
+
+void Entrada(int &linha_origem, int &coluna_origem, int &linha_destino, int &coluna_destino, char jogador_vez, char jogador1, char jogador2){
+
+    char nome[TAM_NOME + 1];
+    
+    do {
+        //LimparTela();
+        PRINTF("%s", FIM_DE_LINHA);
+        SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+        PRINTF("Jogador %s entre com a coordenada de origem da pedra a ser movida.%s", retorna_nome_jogador(jogador_vez, nome), FIM_DE_LINHA);
+        PRINTF("Entre com o valor da linha(1-8): ");
+        linha_origem = lerIteiro() - 1;
+        PRINTF("%s", FIM_DE_LINHA);
+        PRINTF("Entre com o valor de coluna(1-8): ");
+        coluna_origem = lerIteiro() - 1;
+        PRINTF("%s", FIM_DE_LINHA);
+
+        PRINTF("Jogador %s entre com a coordenada de destino da pedra a ser movida.%s", retorna_nome_jogador(jogador_vez, nome), FIM_DE_LINHA);
+        PRINTF("Entre com o valor de linha(1-8): ");
+        linha_destino = lerIteiro() - 1;
+        PRINTF("%s", FIM_DE_LINHA);
+        PRINTF("Entre com o valor de coluna(1-8): ");
+        coluna_destino = lerIteiro() - 1;
+        PRINTF("%s", FIM_DE_LINHA);
+
+        if (Faixa_Valida(linha_origem, coluna_origem, linha_destino, coluna_destino) && 
+            Movimento_Valido(linha_origem, coluna_origem, linha_destino, coluna_destino, jogador_vez, jogador1, jogador2)) {
+            break;
+        } else {
+            PRINTF("%s", FIM_DE_LINHA);
+            PRINTF("Movimento invalido!! Pressione <Qualquer Tecla>");
+            GETCHE();
+        }
+    }   while (1);
+}
+
+void Numero_Oponentes(int &jogador1_pedra_normal, int &jogador1_pedra_dama, 
+                      int &jogador2_pedra_normal, int &jogador2_pedra_dama) {
+
+    int linha, coluna;
+
+    for (linha = 0; linha < MAXLINHA; ++linha) {
+        for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+            switch (tabuleiro_jogada[linha][coluna]) {
+            case PEDRA_NORMAL_JOGADOR1:
+                ++jogador1_pedra_normal;
+                break;
+            case PEDRA_DAMA_JOGADOR1:
+                ++jogador1_pedra_dama;
+                break;
+            case PEDRA_NORMAL_JOGADOR2:
+                ++jogador2_pedra_normal;
+                break;
+            case PEDRA_DAMA_JOGADOR2:
+                ++jogador2_pedra_dama;
+                break;
+            }
+        }
+    }
+}
+
+// 0 - Existem oponentes
+// 1 - Sem oponentes
+int Sem_Oponentes(void) {
+
+    int jogador1_pedra_normal = 0, jogador1_pedra_dama = 0, 
+        jogador2_pedra_normal = 0, jogador2_pedra_dama = 0;
+
+    Numero_Oponentes(jogador1_pedra_normal, jogador1_pedra_dama, 
+                     jogador2_pedra_normal, jogador2_pedra_dama);
+
+    if ( (jogador1_pedra_normal || jogador1_pedra_dama) && (jogador2_pedra_normal || jogador2_pedra_dama) ) {
+        return 0;
+    }
+    return 1;
+}
+
+// 0 - Sem condicoes especiais
+// 1 - Com comdicoes especiais
+int Codicoes_Especiais(void) {
+    // @todo falta terminar as codicoes especiais
+
+    int retorno = 0;
+
+    int jogador1_pedra_normal = 0, jogador1_pedra_dama = 0,
+        jogador2_pedra_normal = 0, jogador2_pedra_dama = 0;
+
+    Numero_Oponentes(jogador1_pedra_normal, jogador1_pedra_dama,
+        jogador2_pedra_normal, jogador2_pedra_dama);
+
+    if ((jogador1_pedra_normal == 0) &&
+        (jogador2_pedra_normal == 0) &&
+        (jogador1_pedra_dama == 2) &&
+        (jogador2_pedra_dama == 2)) {
+        // 2 damas contras 2 damas
+    }
+
+    return retorno;
+}
+
+// 0 - Sem empate
+// 1 - Emapate
+int Verifica_Empate(void) {
+
+    // @todo Verificar como iniciar as condicoes especiais
+
+    return 0;
+
+    int retorno = 0;
+
+    if( ((jogadas - jogada_em_que_ultima_pedra_capturada) == 20) ||
+        ((jogadas - jogada_em_que_ultima_pedra_nomal_movimentada) == 20) ) {
+        // Apos 20 lances sucessivos de damas, sem captura ou deslocamento de pedra, 
+        //  a partida eh declarada empatada
+        retorno = 1;
+    }
+    else if ( (jogada_empate_lances_especiais) && 
+              ((jogadas - jogada_empate_lances_especiais) == 5) && 
+              Codicoes_Especiais() ) {
+            retorno = 1;
+    }
+
+    return retorno;
+}
+
+// 0 - Existe pedra a ser movimentada
+// 1 - Nao existe pedra a ser movimentada
+int Existe_Pedra_Movimento(int linha_destino, int coluna_destino, char jogador1, char jogador2, char jogador) {
+
+    int retorno = 1;
+
+    if (jogador == jogador1) {
+        if ((linha_destino - 1 >= 0) &&
+            (coluna_destino - 1 >= 0) &&
+            (tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] == VAZIO)) {
+            retorno = 0;
+        }
+        else if ((linha_destino - 1 >= 0) &&
+            (coluna_destino + 1 < MAXCOLUNA) &&
+            (tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] == VAZIO)) {
+            retorno = 0;
+        }
+    }
+    else {
+        if ((linha_destino + 1 < MAXLINHA) &&
+            (coluna_destino + 1 < MAXCOLUNA) &&
+            (tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] == VAZIO)) {
+            retorno = 0;
+        }
+        else if ((linha_destino + 1 < MAXLINHA) &&
+            (coluna_destino - 1 >= 0) &&
+            (tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] == VAZIO)) {
+            retorno = 0;
+        }
+    }
+    return retorno;
+}
+
+// 0 - Existe pedra a ser capturada
+// 1 - Nao existe pedra a ser capturada
+int Existe_Pedra_Capturar(int linha_destino, int coluna_destino, char jogador1, char jogador2, char jogador) {
+    
+    int retorno = 1;
+    char pedra_nomal, pedra_dama;
+
+    if (jogador == jogador1) {
+        pedra_nomal = PEDRA_NORMAL_JOGADOR2;
+        pedra_dama = PEDRA_DAMA_JOGADOR2;
+    }
+    else {
+        pedra_nomal = PEDRA_NORMAL_JOGADOR1;
+        pedra_dama = PEDRA_DAMA_JOGADOR1;
+    }
+
+    if ((linha_destino + 2 < MAXLINHA) &&
+        (coluna_destino + 2 < MAXCOLUNA) &&
+        ((tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] == pedra_nomal) ||
+         (tabuleiro_jogada[linha_destino + 1][coluna_destino + 1] == pedra_dama)) && 
+        (tabuleiro_jogada[linha_destino + 2][coluna_destino + 2] == VAZIO)) {
+        retorno = 0;
+    }
+    else if ((linha_destino + 2 < MAXLINHA) &&
+                (coluna_destino - 2 >= 0) &&
+                ((tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] == pedra_nomal) ||
+                 (tabuleiro_jogada[linha_destino + 1][coluna_destino - 1] == pedra_dama)) &&
+                (tabuleiro_jogada[linha_destino + 2][coluna_destino - 2] == VAZIO)) {
+        retorno = 0;
+    }
+    else if ((linha_destino - 2 >= 0) &&
+                (coluna_destino - 2 >= 0) &&
+                ((tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] == pedra_nomal) ||
+                 (tabuleiro_jogada[linha_destino - 1][coluna_destino - 1] == pedra_dama)) &&
+                (tabuleiro_jogada[linha_destino - 2][coluna_destino - 2] == VAZIO)) {
+        retorno = 0;
+    }
+    else if ((linha_destino - 2 >= 0) &&
+                (coluna_destino + 2 < MAXCOLUNA) &&
+                ((tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] == pedra_nomal) ||
+                 (tabuleiro_jogada[linha_destino - 1][coluna_destino + 1] == pedra_dama)) &&
+                (tabuleiro_jogada[linha_destino - 2][coluna_destino + 2] == VAZIO)) {
+        retorno = 0;
+    }
+
+    return retorno;
+}
+
+// 0 - Nao existe jogada para o jogador selecionado
+// 1 - Existe jogada para o jogador selecionado
+int Existe_Jogada(char jogador1, char jogador2, char jogador) {
+    int retorno = 0;
+    int linha, coluna;
+
+
+    if (jogador == jogador1) {
+        for (linha = 0; linha < MAXLINHA; ++linha) {
+            for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+                if (tabuleiro_jogada[linha][coluna] == PEDRA_NORMAL_JOGADOR1) {
+                    if (!Existe_Pedra_Movimento(linha, coluna, jogador1, jogador2, jogador)) {
+                        return 1;
+                    }
+                    else if (!Existe_Pedra_Capturar(linha, coluna, jogador1, jogador2, jogador)) {
+                        return 1;
+                    }
+                }
+            }
+        }
+    }
+    else {
+        for (linha = 0; linha < MAXLINHA; ++linha) {
+            for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+                if (tabuleiro_jogada[linha][coluna] == PEDRA_NORMAL_JOGADOR2) {
+                    if (!Existe_Pedra_Movimento(linha, coluna, jogador1, jogador2, jogador)) {
+                        return 1;
+                    }
+                    else if (!Existe_Pedra_Capturar(linha, coluna, jogador1, jogador2, jogador)) {
+                        return 1;
+                    }
+                }
+            }
+        }
+    }
+    return retorno;
+}
+
+int Analisar(int linha_origem, int coluna_origem, int linha_destino, int coluna_destino, 
+             char &jogador_vez, char jogador1, char jogador2){
+
+    int linha, coluna;
+    char nome[TAM_NOME + 1];
+    int retorno = 0;
+
+    ++jogadas;
+
+    // Verifica se existem oponentes
+    if (Sem_Oponentes()) {
+        if (jogador_vez == jogador1) {
+            placar[jogador1 - '1'][VITORIAS] += 1;
+            placar[jogador2 - '1'][DERROTAS] += 1;
+        }
+        else {
+            placar[jogador2 - '1'][VITORIAS] += 1;
+            placar[jogador1 - '1'][DERROTAS] += 1;
+        }
+        //LimparTela();
+        PRINTF("%s", FIM_DE_LINHA);
+        SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+        PRINTF("Jogador %s VENCEU!! com %d jogadas.%s", retorna_nome_jogador(jogador_vez, nome), jogadas, FIM_DE_LINHA);
+        PRINTF("Pressione <Qualquer Tecla>");
+        GETCHE();
+        jogadas = 0;
+        retorno = 1;
+    }
+    // Verifica empate
+    else if (Verifica_Empate()) {
+        placar[jogador1 - '1'][EMPATES] += 1;
+        placar[jogador2 - '1'][EMPATES] += 1;
+        //LimparTela();
+        PRINTF("%s", FIM_DE_LINHA);
+        SELECIONA_COR(COR_FUNDO_MENSAGEM, COR_TEXTO_MENSAGEM);
+        PRINTF("Jogadores %s  e %s EMPATARAM!! apos %d jogadas.%s", retorna_nome_jogador(jogador1, nome),
+            retorna_nome_jogador(jogador2, nome), jogadas, FIM_DE_LINHA);
+        PRINTF("Pressione <Qualquer Tecla>");
+        GETCHE();
+        jogadas = 0;
+        retorno = 1;
+    }
+    // Verifica mudanca de vez de jogador
+    else {//if ( (numero_pedras_para_capturar == 0) || (numero_pedras_para_capturar == -1) ) {
+
+        for (linha = 0; linha < MAXLINHA; ++linha) {
+            for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+                switch (tabuleiro_jogada[linha][coluna]) {
+                case PEDRA_NORMAL_JOGADOR1:
+                case PEDRA_DAMA_JOGADOR1:
+                case PEDRA_NORMAL_JOGADOR2:
+                case PEDRA_DAMA_JOGADOR2:
+                    break;
+                default:
+                    tabuleiro_jogada[linha][coluna] = VAZIO;
+                    break;
+                }
+            }
+        }
+        memcpy(tabuleiro_controle, tabuleiro_jogada, sizeof(tabuleiro_jogada));
+
+        // @todo falta verificar o caso em que o jogador nao tem casa para jogar
+        if (jogador_vez == jogador1) {
+            if (numero_pedras_capturadas_jogador1 > numero_pedras_capturadas_antes_jogador1) {
+                if (Existe_Pedra_Capturar(linha_destino, coluna_destino, jogador1, jogador2, jogador1)) {
+                    jogador_vez = jogador2;
+                }
+            }
+            else if (Existe_Jogada(jogador1, jogador2, jogador2)) {
+                jogador_vez = jogador2;
+            }
+        }
+        else {
+            if (numero_pedras_capturadas_jogador2 > numero_pedras_capturadas_antes_jogador2) {
+                if (Existe_Pedra_Capturar(linha_destino, coluna_destino, jogador1, jogador2, jogador2)) {
+                    jogador_vez = jogador1;
+                }
+            }
+            else if (Existe_Jogada(jogador1, jogador2, jogador1)) {
+                jogador_vez = jogador1;
+            }
+        }
+        //numero_pedras_para_capturar = -1;
+
+        numero_pedras_capturadas_antes_jogador1 = numero_pedras_capturadas_jogador1;
+        numero_pedras_capturadas_antes_jogador2 = numero_pedras_capturadas_jogador2;
+#if 0
+        for (linha = 0; linha < MAXLINHA; ++linha) {
+            for (coluna = 0; coluna < MAXCOLUNA; ++coluna) {
+                switch (tabuleiro_jogada[linha][coluna]) {
+                    case PEDRA_NORMAL_JOGADOR1:
+                    case PEDRA_DAMA_JOGADOR1:
+                    case PEDRA_NORMAL_JOGADOR2:
+                    case PEDRA_DAMA_JOGADOR2:
+                        break;
+                    default :
+                        tabuleiro_jogada[linha][coluna] = VAZIO;
+                        break;
+                }
+            }
+        }
+        memcpy(tabuleiro_controle, tabuleiro_jogada, sizeof(tabuleiro_jogada));
+#endif
+    }
+    
+    return(retorno);
+} 
+
+void Jogar(char jogador1, char jogador2) {
+    
+    char fim = '0';
+    char jogador_vez;
+    int linha_origem, coluna_origem, linha_destino, coluna_destino;
+    
+    InicializarTabuleiro(jogador1, jogador2);
+    
+    jogador_vez = jogador1;
+    
+    do {
+        ImprimirTabuleiro(jogador1, jogador2);
+        
+        Entrada(linha_origem, coluna_origem, linha_destino, coluna_destino,jogador_vez, jogador1, jogador2);
+        
+        if(Analisar(linha_origem, coluna_origem, linha_destino, coluna_destino, jogador_vez, jogador1, jogador2)) {
+            fim = '1';
+        }
+    } while(fim != '1');
+}
+
+int main() {
+    
+    char jogador1, jogador2;
+    
+#ifdef __PC__
+
+    hConsoleHandle = GetStdHandle(STD_OUTPUT_HANDLE);
+    ConsoleInfo = new CONSOLE_SCREEN_BUFFER_INFO();
+    GetConsoleScreenBufferInfo(hConsoleHandle, ConsoleInfo);
+
+#else
+
+    //pc.baud(115200);
+    term.baud(115200);
+    
+#endif
+
+    // Zerando o placar
+    memset(placar, 0, sizeof(placar));
+    
+    while(true) {
+        
+        ImprimeMenu(jogador1, jogador2);
+        
+        Jogar(jogador1, jogador2);
+    }
+}