Trabalhos de MAC 441/5714

Além dos trabalhos realizados em sala de aula, teremos um EP de aquecimento e um projeto em várias fazes para realizar em casa.

Datas de Entrega dos Trabalhos:

EP Zero (aquecimento) - brincando com o Morphic

Este exercício-programa deve ajudar vocês a adquirirem alguma familiaridade com o Morphic, o arcabouço para a construção de interfaces gráficas (GUIs) do Squeak. Seria até certo ponto impreciso chamar o Morphic de um "arcabouço para interfaces gráficas" já que se trata, na verdade, de um "arcabouço para a construção de objetos interativos" (chamados de morphs). Esses "objetos interativos" constituem a base de todos os elementos da interface do Squeak - desde janelas, botões e texto até imagens e figuras animadas. O arcabouço isola o programador e o usuário de grande parte dos detalhes que fazem parte do desenvolvimento de interfaces gráficas, gerenciando automaticamente atualização de tela, despacho de eventos, leiaute e operações como arrastar-e-soltar e composição.

Parte do poder do Morphic vem de uma linguagem (gráfica) de scripts introduzida pelo arcabouço, que serve para a especificação de certas interações entre objetos (morphs). Outra parte desse poder vem do fato que o arcabouço prevê, em seu projeto, a construção de interfaces gráficas dotadas de vivacidade. Isso significa que os objetos da interface podem ser dotados de comportamentos ativos, atualizando-se automaticamente e interagindo com outros objetos a cada instante . Os "instantes" são discretos e podem ser encarados como iterações coletivas, compartilhadas por todos os morphs presentes no mundo Smalltalk. Neste exercício-programa, vamos explorar a linguagem de scripts e a possibilidade de construção de interfaces dotadas de vivacidade.

Dirigindo
O exercício-programa consiste num jogo de computador bastante simples, em que o jogador dirige um carrinho em uma pista circular. Para que seja possível dirigir o carro, ele deve, obviamente, ser dotado de dois controles fundamentais: um para o ajuste de velocidade (acelerador/freio) e outro para o ajuste de direção (volante). Recomendo que você utilize o próprio editor gráfico do Morphic (aquele que se parece com o PaintBrush) para criar a pista, o carrinho e o volante. Para o controle de velocidade, você pode utilizar uma instância da classe SimpleSliderMorph.

Você deve ainda manter um contador na tela, que mostra a pontuação do jogador até o presente instante. A pontuação deve ser calculada da seguinte maneira:

O volante deve responder a comandos como num veículo de verdade. Isso significa que, se o jogador estiver acelerando e virar o volante, o veículo deve passar a descrever uma trajetória circular até que a posição do volante seja corrigida (não vale fazer o carrinho simplesmente apontar para a mesma direção do volante). O volante deve ser girado pelo botão "rotate", disponível no halo do morph que o representa.

Por fim, você deve adicionar um controle para iniciar e suspender o jogo.

Dicas

A princípio você não precisa, para fazer este EP, escrever uma linha sequer de código Smalltalk. Isso não quer dizer, no entanto, que seja proibido.

Veja mais ou menos como deve ficar o seu EP aqui.

Veja a página de ponteiros para alguns tutoriais do Morphic.

O que entregar

Você deve entregar um arquivo contendo o projeto Squeak com a sua solução. Para criar um projeto basta clicar, com o botão da esquerda (também conhecido como botão vermelho no Squeak), em um lugar "vazio" do mundo e um menu deve aparecer. Nesse menu, clique em projects -> create new morphic project. Para exportar seu projeto, acesse, de dentro dele, o mesmo menu e clique em save project on file.... Entregue também um pequeno relatório (formato PDF ou PS, por favor) documentando a sua solução - esse relatório é especialmente importante se você decidir escrever código.

O seu projeto deve funcionar no Squeak 3.7.


Projeto Marcador de Reuniões

Este é um sistema Web que será utilizado para auxiliar na marcação de uma reunião com vários participantes. Um dos participantes, responsável pela organização da reunião, indica em qual período ele gostaria de marcar a reunião (por exemplo, entre 10 e 20 de abril); ele determina também a lista de participantes identificados pelos seus endereços eletrônicos. A seguir, cada um dos participantes indica uma lista de horários dentro do período determinado pelo organizador e, para cada um desses horários, indica sua disponibilidade (ótima, razoável, ruim ou impossível). O organizador então visualiza a sobreposição dos horários de todos os participantes e escolhe um horário para a reunião. Finalmente, o organizador escolhe uma sala para a reunião e uma notificação é enviada para todos os participantes (inclusive para os que se disseram indisponíveis no horário escolhido).

Todas as suas classes deverão ser incluídas dentro de uma categoria e este deve ser gravado através da opção fileOut e o respectivo arquivo deverá ser entregue através do panda. O nome da categoria deve conter o sobrenome (ou parte do sobrenome) dos autores.

O trabalho deve ser feito preferencialmente em grupos de 2. Grupos individuais são aceitos (a contragosto :-). Recomendo fortemente que os pares desenvolvam os programas usando programação pareada (os dois programadores sentados lado a lado compartilhando o mesmo computador).

Fase 1: Disponibilidade de horários

Para a Fase 1, que deve ser entregue ao final da semana do breque, em 24/4, a implementação deve se basear em uma interface de texto somente, ou seja, a visualização dos horários dos participantes será feita em modo texto utilizando-se, por exemplo, o objeto Transcript.

A definição dos participantes da reunião será feita através do seguinte método que deverá ser implementado na classe MarcadorDeReuniao :

marcador marqueReuniaoEntre: dataInicial E: dataFinal comParticipantes: listaDeParticipantes

as datas devem ser do tipo Date e a listaDeParticipantes é uma OrderedCollection de Strings identificando os participantes;

cada participante define os seus horários disponíveis através do seguinte método:

marcador disponibilidade: qualidadeDaDisponibilidade de: participante de: inicio a: fim

onde qualidadeDaDisponibilidade é um símbolo (ótima, razoável, ruim ou impossível),  participante é um String e inicio e fim são do tipo TimeStamp

e, finalmente, o método

marcador mostraSobreposicao

que provavelmente vai dar o maior trabalho e vai exigir mais criatividade de vocês, para informar os dados de uma forma clara e elegante.

Fase 2: Reserva de Salas

Na fase 2, que deverá ser entregue em 23 de maio faremos uma nova classe cujo objetivo é reservar as salas para as nossas reuniões e acrescentaremos um método na classe da fase 1 para divulgar a reunião marcada. A classe GerenciadorDeSalas deve implementar, pelo menos, os seguintes métodos:
 
adicionaSalaChamada: nome noLocal: local comCapacidade: numeroDePessoas obs: observacoes

removeSalaChamada: nome

listaDeSalas "devolve uma OrderedCollection de objetos do tipo Sala"

adicionaSala: umaSala

reservaSalaChamada: nome de: timeStampInicial a: timeStampFinal "devolve uma Reserva"

cancelaReserva: umaReserva
"Onde umaReserva é o objeto devolvido pelo método reservaSalaChamada:"

reservasParaSala: umaSala
"devolve uma Collection de objetos Reserva que são as reservas da respectiva sala."

imprimeReservasDaSala: umaSala


Objetos do tipo Sala possuem métodos de acesso para os seguintes atributos: nome, local, capacidade e observacoes
capacidade é um inteiro, os demais atributos são Strings.

Se a reserva for efetuada com sucesso, o método reservaSalaChamada: devolve uma instância do objeto Reserva (com métodos sala, inicio, e fim, que devolvem respectivamente uma instância de sala e dois TimeStamps, do início e do fim da reserva). Se a reserva falhar por qualquer motivo (p.ex. sala inexistente ou sala já reservada) o gerenciador deve obrigatoriamente lançar uma exceção e opcionalmente imprimir uma mensagem de erro.

Exemplo de uso do programa:

gerenciador := GerenciadorDeSalas new.
gerenciador
    adicionaSalaChamada: 'B-3'
    noLocal: 'IME - Bloco B - Térreo'   
    comCapacidade: 60
    obs: nil.

gerenciador
    adicionaSalaChamada: 'Auditório Antonio Giglioli'
    noLocal: 'IME - Bloco A - Primeiro Andar'
    comCapacidade: 95
    obs: 'Possui projetor LCD, rede com e sem fio e lousa eletrônica'.

quentura := Sala new.
quentura
    nome: 'B-143';
    local: 'IME - Bloco B - Primeiro Andar';
    capacidade: 75;
    obs: 'No verão, é quente prá danar.'.

gerenciador adicionaSala: quentura.

umaReserva := gerenciador
                    reservaSalaChamada: 'B-143'
                    de: TimeStamp now
                    a:  (TimeStamp now addSeconds: 60*60).

gerenciador cancelaReserva: umaReserva.



Além da classe acima, você deverá também adicionar à classe MarcadorDeReuniao o seguinte método:

MarcadorDeReuniao>>divulgueReuniaoMarcada: umaReserva

este método deverá enviar uma mensagem de correio eletrônico (via SMTP) para todos os participantes da reunião informando todos os dados da reunião (quem marcou, horário de início e fim, nome e local da sala onde ela será realizada, etc.).

Você tem total liberdade para criar classes auxiliares além das classes descritas acima. Por exemplo, seria uma boa idéia não "poluir" a classe MarcadorDeReuniao com código específico para lidar com detalhes do envio de mensagens através do protocolo SMTP. Dica: usem algo já pronto para enviar mensagens via SMTP, não re-implemente o protocolo.


Fase 3: Interface Web

O objetivo da fase final é implementar, usando o arcabouço Seaside, uma interface Web para o nosso sistema gerenciador de reuniões incluindo tanto a marcação da reunião quanto a reserva da sala apropriada.

O formato da interface que vocês desenvolverão é totalmente livre. Mas ela será avaliada de acordo com a sua praticidade, facilidade de uso e elegância. Utilizando uma página de gerenciamento, o administrador do sistema deverá ser capaz de criar [e remover] novas salas (digitando os seus atributos) e criar [e remover] novos usuários para o sistema (fornecendo seus atributos e senha). Utilizando a página de acesso para usuários normais, um usuário entrará no sistema fornecendo seu email (como "login-name") e senha. A partir daí ele poderá fazer 3 coisas: 1) solicitar a marcação de uma nova reunião, 2) indicar o seu horário de disponibilidade caso já haja alguma reunião sendo marcada da qual ele seja um dos participantes e 3) reservar uma sala para uma reunião. Caso o usuário tenha solicitado a marcação de uma reunião no passado, ele também terá a opção de visualizar a sobreposição dos horários dos participantes da reunião que já indicaram a sua disponibilidade.

Concentre-se na praticidade de uso do seu sistema. Por exemplo, na página de marcação de uma nova reunião, seria ruim ter que digitar o nome dos participantes. O melhor seria, por exemplo, ver uma lista de todos os usuários registrados no sistema com checkboxes ao lado para selecionarmos quem participará ou não da reunião. Outra opção é ter um botão de adicionar participante ao lado de uma pop-down-selection-list que mostre todos os participantes de forma que o usuário possa selecionar um de cada vez. Outras opções são possíveis, use sua imaginação...

Normalmente, a sala só será reservada após a confirmação do horário da reunião. Mas isso não é obrigatório. Deve ser possível reservar uma sala mesmo que não tenha havido o processo de marcação da reunião através do sistema.


O sistema deverá também fornecer informações sobre quais reuniões estão marcadas e qual a disponibilidade das salas. Pense em como fornecer estas informações de forma organizada, legível e útil para o usuário. Tanto listagem completa das informações armazenadas quanto uma pequena ferramenta de busca por informações específicas seriam desejáveis. Organize as informações na página de forma elegante, por exemplo, usando tabelas HTML e/ou vários componentes Seaside.

Finalmente, lembre-se que esta especificação é bem aberta, ela indica apenas o mínimo necessário. Seja criativo, desenvolva a solução que lhe pareça ser a melhor possível para o usuário final.


Nesta fase final, o objetivo é tornar o sistema o tão bem acabado quanto possível de forma que ele possa ser colocado em produção em um ambiente real ou chegar perto disso. Para tanto vocês deverão fazer o seguinte:

  1. Guardar as senhas em um arquivo de forma criptografada. (não obrigatório, se fizer ganha 0.5 ponto extra, é fácil).
  2. A página de login onde o usuário digita sua senha deve ser servida através de HTTPS de forma que a senha não transite de forma aberta pela rede. (não obrigatório, se fizer ganha 0.5 ponto extra)
  3. Os dados devem ser armazenados de forma persistente. O sistema deve gerar um (ou mais) arquivos de backup de tempos em tempos. O estado do sistema deverá ser armazenado em arquivos XML ou em arquivos binários usando seriação de objetos. Cuidado para não gravar no arquivo dados inconsistentes resultantes de operações em andamento. É necessário tomar cuidado com a concorrência evitando que duas sessões Web diferentes tentem mexer nos mesmos dados ou arquivos ao mesmo tempo. (persistência não é obrigatório, se fizer corretamente ganha 1 ponto extra).
  4. Quando um usuário solicita a marcação de um horário para uma reunião, o sistema deverá enviar uma mensagem (via SMTP) para todos os participantes da reunião dizendo que tal pessoa o está convidando a participar de uma certa reunião em um certo período e que ele deverá visitar uma certa página para indicar suas disponibilidades. (obrigatório)
  5. Além do código-fonte, entregar 3 documentos:
    (estes documentos são obrigatórios mas não precisam ser muito longos e detalhados, basta colocar o essencial)
    1. Manual de instalação (explicando a um sysadmin como instalar o sistema).
    2. Manual do usuário (para usuários comuns e administradores, explicando como usar o sistema).
    3. Manual para programadores (contendo descrição da arquitetura interna do seu sistema e detalhes sobre a implementação, UML é bem-vinda).


Página de MAC 441/5714
Página do Fabio
Página do DCC