Tele-Spiel
Transcrição
Tele-Spiel
Projecto de Arquitectura de Computadores 2002 / 2003 Tele-Spiel 1. Introdução Pretende-se desenvolver um jogo interactivo como forma de desenvolver as capacidades de programação em assembly e de microprogramação. 1.1 Descrição geral e objectivo do jogo O jogo decorre num campo construído na janela de I/O do simulador e consiste em três variantes: squash, ténis e hóquei. As entidades relevantes para o jogo são: a representação dos jogadores (barras verticais), a bola e as paredes que delimitam os campos de jogo. Para evitar naturais ambiguidades, no restante deste enunciado, a palavra jogador indicará sempre a representação dos jogadores enquanto que a palavra utilizador indicará quem está a jogar, ou seja, a controlar o movimento dos jogadores. A representação das entidades envolvidas no jogo é a seguinte: Entidade Parede vertical Parede horizontal Casa preenchida com bola Linha de separação central Casa livre Jogador Representação ‘|’ ‘-’ ‘O’ ‘:’ ‘ ‘ (espaço) ‘|’ As entidades activas no jogo são os jogadores (representados por barras verticais) e a bola. A movimentação do(s) jogador(es) é controlada pelo utilizador através do teclado. Os jogadores movimentam-se apenas verticalmente. Consoante o jogo seleccionado (squash, ténis ou hóquei) o(s) utilizador(es) podem controlar um ou dois jogadores, cada um representado por um conjunto de barras verticais. No caso da variante squash, o jogo termina quando o tempo expirar completamente. No caso das variantes ténis e hóquei, o jogo termina quando a pontuação máxima de 15 (quinze) for atingida por uma das equipas ou quando o tempo expirar. Para o utilizador vencedor deve surgir uma frase de parabéns ao seu desempenho. Para o derrotado, deve surgir uma frase motivando-o a treinar mais. Como nestes dois últimos desportos não são contemplados empates, no caso do tempo expirar com as equipas empatadas, o jogo deve continuar até que uma das equipas consiga o primeiro ponto. Em qualquer caso deve ser possível ao(s) utilizador(es) recomeçar outro jogo. É parte essencial deste trabalho a microprogramação de uma nova instrução assembly - LOOP - que realiza um ciclo contado. Sugere-se aos alunos que, uma vez realizada, esta instrução deva ser utilizada nos ciclos do programa. 1.2 Inicialização e cenário de jogo O jogo inicia-se pelo desenho no ecrã (janela de I/O) do cenário do jogo constituído pela cercadura, que delimita a zona de jogo, pelos jogadores e pela bola. O cenário de jogo é constituído pela cercadura (fronteira de um rectângulo preenchida com caracteres ‘-‘ e ‘|’). A cercadura é encostada ao canto superior esquerdo da janela de I/O. Os algarismos nos eixos horizontal e vertical são meramente indicativos e não devem ser apresentados. A dimensão do cenário é de 16 linhas por 31 colunas. 1.2.1 Squash 0123456789012345678901234567890 0------------------------------1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | 1 | 2 | 3 | 4 | 5------------------------------- 1.2.2 Ténis 0123456789012345678901234567890 0------------------------------1 : 2 : 3 : 4 : 5 : 6 : 7 : 8 : 9 : 0 : 1 : 2 : 3 : 4 : 5------------------------------- 1.2.3 Hóquei 0123456789012345678901234567890 0------------------------------1| : | 2| : | 3| : | 4 : 5 : 6 : 7 : 8 : 9 : 0 : 1 : 2| : | 3| : | 4| : | 5------------------------------- 2 Jogo O utilizador deve, através dos interruptores, poder escolher a variante que pretende jogar. A partir deste momento o(s) jogador(es) começam deslocar-se verticalmente segundo as indicações do utilizador. Quando encontra uma parede, o jogador não pode progredir, ficando imobilizado, até que o utilizador escolha uma outra direcção para o seu movimento. Quanto à bola, quando colide com a parede, o ângulo de direcção de saída desta em relação à parede deve ser igual ao ângulo de entrada. A bola deve estar sempre em movimento. 2.1 Pontuação A pontuação actual deve ser apresentada nos displays de sete segmentos em base decimal. Os dois displays mais à esquerda apresentarão a pontuação do jogador UM e os da direita, a dos jogador DOIS. 2.1.1 Squash A pontuação corresponde ao número de vezes que a bola colidiu com a parede vertical durante o tempo de jogo. 2.1.2 Ténis e Hóquei A pontuação de cada uma das duas equipas corresponde ao número de vezes que a bola transpôs a fronteira vertical aberta do cenário de jogo defendida pela outra equipa (um ponto ou um golo). 2.2 Posicionamento inicial dos jogadores Todos os jogadores devem ser posicionados inicialmente de forma aproximadamente centrada no eixo vertical, i.e., colocados na linha 7 (sete). Quanto às colunas, estas dependem da variante escolhida: No caso do squash, deve tomar o valor 5; no ténis, 2 e 28;no caso do hóquei: 4, 10, 20,26. 2.3 Lançamento de bola em jogo Cada bola deve ser lançada em jogo a partir de um lado do campo, numa linha e com direcção definidos, todos, de forma aleatória. Deve surgir na coluna imediatamente interior à posição do último defensor desse lado do campo. Tanto o lado escolhido como a linha, bem como o ângulo e direcção (naturalmente, de entre as que apontam para o outro lado do campo) devem ser sorteados recorrendo à rotina RANDOM fornecida no enunciado que deve ser invocada pelo programa de forma a produzir apenas números dentro de gamas válidas. Como exemplo, no caso do ténis, quando a bola é lançada do campo esquerdo deve surgir na coluna 3 (três). No caso de um jogo com várias bolas em simultâneo, sempre que uma bola sai do cenário de jogo deve ser contabilizado o ponto correspondente e verificada a terminação do jogo. Caso contrário, deve ser substituída por outra lançada de um dos campos, escolhido por sorteio, e com uma linha e direcção sorteadas respeitando o disposto no parágrafo anterior. Ex.: 0123456789012345678901234567890 0------------------------------1 : 2 : 3 | : O 4 | : 5 | : 6 : 7 : 8 : 9 : 0 O : 1 : 2 : | 3 : | 4 O : | 5------------------------------- 2.4 a bola recém-lançada está a negrito. Movimento O movimento dos jogadores é controlado pelas teclas "Q", "A", "P" e "L" que indicam o sentido do movimento. O simulador interpreta estas teclas como botões de interrupção (respectivamente I0 a I3). Tecla Q A P L 2.5 Sentido ⇑ Jogador 1 ⇓ Jogador 1 ⇑ Jogador 2 ⇓ Jogador 2 Dimensão do jogador Os jogadores podem ser constituídos por duas ou três peças/elementos conforme escolha dos utilizadores. 2.6 Tempo A medida aparente de movimento utilizado no jogo consiste na contagem do número de execuções do ciclo principal de jogo, i.e., movimentação da(s) bola(s), dos jogadores e verificação da ocorrência de colisões ou marcação de pontos. A isto chamar-se-á a contagem dos movimentos ainda disponíveis. Assim, o número de movimentos ainda disponíveis para jogar deve ser apresentado recorrendo aos leds . Para isso devem ser iluminados todos os leds no início do jogo. Os quatro mais à direita deverão tomar a cor verde, os três imediatamente à esquerda destes, a amarela; e o led mais à esquerda deverá tomar a cor vermelha. Os leds devem ser apagados à medida que o número de movimentos ainda disponíveis vai diminuindo, a intervalos regulares. O tempo disponível para cada jogo corresponde a 8192 posições (este valor é escolhido para facilitar as operações de máscara para apresentação dos leds). Na variante rápida, o jogo durará metade deste tempo. Como os computadores tem velocidade variável, a passagem do tempo deve ser configurada por uma variável existente no programa que controla, aproximadamente, a duração de cada ciclo de jogo, acrescentando por exemplo, um ciclo interior de NOPs . 2.7 Programação do ângulo de incidência da bola O jogo pode ser jogado seleccionando dois tipo de ângulos que a(s) bola(s) em jogo devem fazer com a cercadura e jogadores. Na versão mais simples, a direcção da bola faz sempre ângulos de 45 graus com a cercadura e jogadores. Assim, a velocidade da bola pode ser descrita por um vector de componentes iguais à unidade mas com sinal indicativo do sentido horizontal e vertical. Utilizando a nomenclatura da navegação, e tendo como origem das coordenadas o canto superior esquerdo da janela de texto, tem-se: (-1, -1) (-1, 1) ( 1, -1) ( 1, 1) NorOeste NordEste SudOeste SudEste Portanto, a cada ciclo de jogo, cada bola, em percurso normal, desloca-se uma posição numa direcção vertical e outra na direcção horizontal. A velocidade aparente da bola será a norma do vector, i.e., raiz de 2. Contudo, para minorar a previsibilidade destes movimentos, o jogador pode seleccionar um outro tipo de movimento que incluirá bolas com trajectos com ângulos de ~30 graus (em rigor, 26,6º) e de ~60 graus (na verdade, 63,5º). Assim, a velocidade da bola será representada por um vector em que uma das componentes é um e a outra é dois. No caso da componente horizontal ser dois, a bola fará sempre ângulos de ~30 graus com a horizontal (cercadura) e de ~60 graus com a vertical (jogador). Em qualquer caso, a velocidade aparente da bola e maior, tomando o valor raiz de 5 e tornando, possivelmente, o jogo mais exigente. No caso de ser a componente vertical a ter valor duplo, a situação será complementar. Esta característica da bola é constante, para cada uma, e deve ser sorteada quando esta é lançada. 2.8 Configuração e nível de dificuldade do jogo A configuração do jogo e escolha do seu nível de dificuldade deve ser realizada pelo utilizador através dos interruptores com a seguinte disposição (apenas são utilizados os 7 interruptores mais à esquerda): Variante Squash=00 Ténis=01 Hóquei=1X 2 interruptores 2.9 Duração Normal=0 Rápida=1 1 interruptor Número de bolas 1=01,2=10, 3=11,4=00 2 interruptores Ângulo 45 graus=0 30º - 60º =1 1 interruptor Tamanho Jogador 2 barras = 0 3 barras = 1 1 interruptor Apresentação dos resultados Quando o jogo termina o cenário no plano de jogo permanece estático e no seu centro é apresentada o resultado final e a perguntado ao utilizador se deseja jogar novamente. Quando o jogador responder afirmativamente carregando em qualquer tecla avançase para um novo jogo sendo possível seleccionar uma nova variante. 2.10 Situação de Jogo ( exemplos ) Squash 0123456789012345678901234567890 0------------------------------1 | 2 | 3 | O | 4 | | 5 | | 6 | 7 | 8 O | 9 | 0 | 1 | 2 | 3 | 4 | 5------------------------------- Ténis 0123456789012345678901234567890 0------------------------------1 : 2 : 3 | : 4 | : 5 | : 6 : 7 : 8 : 9 : 0 O : 1 : 2 : | 3 : | 4 : | 5------------------------------- Hóquei 0123456789012345678901234567890 0------------------------------1| : | 2| | : | | 3| | : | O | 4 | | : | | 5 | : | 6 | : | 7 : 8 : 9 : 0 : 1 : 2| : | 3| : | 4| : | 5------------------------------- 3 Plano de desenvolvimento 3.1 Microprogramação de LOOP Parte deste trabalho consiste na microprogramação de uma nova instrução assembly LOOP (ciclo) que decrementa um registo de contagem implícito (R7) e caso o valor deste se mantenha diferente de zero, salta para o endereço especificado no operando da instrução: LOOP op O opcode da instrução LOOP é 017H. A instrução NÃO deverá alterar nenhum dos bits de estado do processador. O funcionamento de LOOP deverá ser demonstrado na 2ª aula para realização do trabalho. 3.2 Desenvolvimento do jogo No que respeita ao desenvolvimento do jogo deverão seguir-se os seguintes passos: 1. Desenhe o fluxograma que descreve a aplicação que pretende desenvolver. Descreva também claramente os algoritmos relevantes para as várias funções do jogo que vai programar (movimento dos jogadores, da bola, determinação da marcação de pontos e da terminação do jogo, etc.). O fluxograma deverá ser apresentado na 1ª aula para a realização do projecto e será a base para a discussão das opções genéricas de projecto, ainda nesta aula. Para que os alunos sejam, tão cedo quanto possível, confrontados com as vantagens e desvantagens das suas decisões, devem também apresentar uma simplificação da variante squash concluída. Os alunos podem tirar duvidas acerca de fluxogramas já' iniciados durante a semana anterior à entrega do enunciado. 2. Identifique as rotinas nas quais acha útil estruturar a aplicação. Por cada rotina identifique claramente as entradas e as saídas. 3. Apresente o código da sua aplicação devidamente comentado. Inclua nos comentários referências ao fluxograma para auxiliar a leitura do programa. 4. Tenha em conta que o seu programa é uma aplicação interactiva que se irá executar num ambiente de simulação. Um critério importante na avaliação da qualidade do resultado final será a sua rapidez de resposta. 5. Teste o seu programa de forma faseada. Inicialmente teste a geração do plano de jogo e só depois o jogo propriamente dito. 6. Indique o seu plano de testes, isto é, identifique as diferentes condições e situações de jogo (nível de dificuldade, colisões com cercadura, marcação de pontos, calculo de ângulos, etc.) e, para cada uma delas, defina um plano de teste. 3.3 Faseamento da Codificação Não deve tentar codificar todo o jogo de uma vez. Implemente a funcionalidade do programa de forma faseada e efectue os testes necessários para verificar o seu correcto funcionamento. Não prossiga para a implementação de funcionalidade mais avançada sem ter garantido que as que lhe servem de base também estão correctamente implementadas. A avaliação do projecto também seguirá este princípio. Assim, os alunos são encorajados a desenvolver a funcionalidade do programa pela seguinte ordem: 1. Apresentação do cenário de jogo do squash e o jogador colocado numa posição válida. 2. Movimento dos jogadores controlados pelos utilizadores e da bola com teste de colisões (apenas com ângulos de 45º) e configuração do tamanho da jogador. 3. Conquista dos pontos, actualização da pontuação nos display de 7 segmentos. 4. Actualização do número de movimentos disponíveis e sua apresentação nos leds tricolores. 5. Desenvolvimento da variante ténis. 6. Programação da configuração e escolha da variante e da duração do jogo. 7. Programação da configuração e escolha do número de bolas e do ângulo que estas fazem com a cercadura e jogadores. 8. Desenvolvimento da variante hóquei. Não avance para um ponto sem ter conseguido implementar completamente o anterior. O núcleo principal do jogo corresponde apenas aos cinco primeiros. Os pontos seis e sete, por serem mais trabalhosos, devem ser abordados apenas depois do núcleo principal estar completamente desenvolvido para não comprometer o resultado final, o funcionamento correcto do jogo. O ponto oito é apenas para trabalhos de nível elevado. 4 A recordar 1ª aula: Entrega do fluxograma da aplicação. Demonstração do funcionamento dos primeiros dois pontos do projecto. Discussão do fluxograma e das opções genéricas de projecto. 2ª aula: Apresentação obrigatória da instrução LOOP microprogramada. É também sugerido que já tenham completado os pontos 3, 4 e 5 embora não sejam avaliados nesta aula. 3ª aula: Apresentação e entrega de todo o projecto realizado. Apêndice: Geração de números aleatórios (rotina RANDOM) A rotina RANDOM deve fazer uso do seguinte algoritmo (registo de deslocamento modificado com realimentação) que gera uma sequência aparentemente aleatória de números de 16 bits, com distribuição uniforme (isto é, os números são equiprováveis), com um passo de repetição elevado: Mascara = 1000 0000 0001 0110 if (n0 = 0) /* Testa o bit de menor peso */ N i+1 = rotate_right (Ni); else N i+1 = rotate_right (XOR (Ni, Mascara)); Em cada invocação de RANDOM, Ni é passado como parâmetro o próprio resultado – Ni+1 – deve ser utilizado na próxima evocação da rotina. A raiz desta sequência (N0) é o valor do operando da primeira vez que a rotina é invocada com esse operando. São deixadas ao critério dos alunos a forma de preservar o estado do gerador de números aleatórios ( por ex: uma variável ) e a validação dos números gerados para uma determinada gama pretendida. Comment [L1]: Alternativa: Ni+1 = shr (Ni, 1) e n15 i+1 = XOR (n15i, n4i, n2i, n1i) , N0 ≠ 0 . Cada número na sequência obtém-se do anterior por deslocamento à direita de uma posição sendo o bit de maior peso (n15) igual ao ou exclusivo dos bits 15, 4, 2 e 1 do número anterior.