segunda-feira, 11 de dezembro de 2017

Atividade 21 - The Beauty of Data Visualization (MAMI - 2017.2)

O vídeo "The Beauty of Data Visualization", que pode ser acessado ao clicar aqui, fala de um dos maiores problemas da atual "Era Digital", o excesso de dados e informação nas esferas midiáticas. Usando gráficos variados, o palestrante, David McCandless, exibe de forma sistemática gráficos e diagramas que extraem dados e informações, por exemplo, de notícias obtidas no meio jornalístico, exibindo-as de forma a ser facilmente interpretadas, demonstrando, dessa maneira, a importância do Designer de Informação no contexto atual.

Na minha perspectiva, apesar do conteúdo ser excelente, achei um pouco tendencioso, provavelmente por causa das inclinações e/ou nacionalidade do autor. Pois, após exibir os dados brutos do investimento dos Estados Unidos na indústria bélica (que é o primeiro do mundo na categoria), ele mostra um gráfico de porcentagem dessa espécie de investimento pelo PIB e conclui que os EUA estão em 8º, e não aprofunda mais no assunto. Acontece o mesmo quando ele mostra o diagrama de doações dos EUA para instituições de caridades (que tem peso maior vários países juntos), e não explora os "porquês" por trás dessa realidade.

Além disso, muitas das informações diagramadas não foram devidamente creditadas às suas fontes originais. Poderiam também ter sido apresentados mais organogramas interativos e divulgado sobre o mercado de trabalho voltado para o Design de Informação

No entanto, achei o vídeo muito bom, porque nos traz à tona a necessidade cada vez maior do profissional Designer da Informação para a nossa realidade.

domingo, 10 de dezembro de 2017

Atividade 20 - Einstein (MAMI - 2017.2)

Nessa atividade, criei 2 versões adicionais, para as imagens abaixo:

Aplicando essa no Processing, vemos:


Aplicando essa no Processing, vemos:


Aqui estão elas, a primeira de cada com maior brilho, e a segunda com maior contraste:

Aplicando essa no Processing, vemos: 
A média de tons aumentou, por causa do aumento da quantidade da cor branca na foto. A variância também aumentou, porque agora temos novos tons (mais próximos do branco puro). E o desvio também aumentou, porque os valores se distanciam mais da média.


 Aplicando essa no Processing, vemos: 
A média de tons aumentou ligeiramente, porque algumas partes que já eram brancas ficaram mais ainda. A variância aumentou, porque o contraste criou uma maior gama de tons. O desvio aumentou, porque locais que já eram escuros ficaram mais ainda, assim como os claros ficaram mais claros.


Aplicando essa no Processing, vemos: 
A média de tons aumentou, afinal estamos trabalhando com uma tela monocromática. A variância aumentou alguns décimos, acho que deve ser o ruído do formato da imagem .jpg. Idem para o desvio.


 Aplicando essa no Processing, vemos: 
Todos os valores permaneceram, afinal não há como contrastar uma imagem monocromática.

quarta-feira, 6 de dezembro de 2017

Atividade 19 - Olhão (MAMI - 2017.2)

Para fazer o olhão, utilizei a função atan2 para fazê-lo acompanhar o cursor, aplicando mouseY-height/2 e mouseX-width/2 na função. Além disso, criei uma variável que recebe o ângulo do atan2, e depois apliquei ao círculo interior para receber suas respectivas coordenadas cartesianas.


Link do código: https://drive.google.com/open?id=1sxCq6reBkIYBT-6h5T-txV5R7Yp93kR_

quinta-feira, 30 de novembro de 2017

Atividade 18 - Cronômetro (MAMI - 2017.2)



Para fazer o cronômetro mostrado acima, utilizei a função millis dividido pelo módulo de 1000 e 60 como a variável t, e um conversor das coordenadas polares para adquirir as coordenadas cartesianas, tendo o resultado multiplicado por 2*PI, que representa os 360º. Para cada posição, foi criada uma variável correspondente a um array de coordenadas cartesianas, que são aplicadas às posições de cada instante do relógio em uma linha. Para parecer um relógio, carreguei uma imagem de relógio no fundo.

Link do código: https://drive.google.com/open?id=1KvsQCEIlw72wwIuthdh0YR1n0VndGOMc

quarta-feira, 22 de novembro de 2017

Atividade 17 - Maré Senoidal (MAMI - 2017.2)


Para fazer o barquinho navegando no mar, utilizei duas linhas para representar as correntes marítimas, as quais variam suas coordenadas X e Y de acordo com o seno de uma variável angular, dnado a sensação de ondulamento. Quando é completado um ciclo dessa variação, o movimento começa novamente por meio do reestabelecimento do valor inicial da variável.

Para acompanhar o movimento das ondinhas, a imagem do barquinho é orientada de acordo com as funções translate e rotate, que recebem o mesmo seno do ângulo da maré.

Link do código: https://drive.google.com/open?id=17-_Uwk8S8ZJriggBuN_njU-KJW_4wTyb

sábado, 18 de novembro de 2017

Atividade 16 - Polígonos (MAMI - 2017.2)

Nessa atividade, foi proposta a criação de uma aplicação que desenhasse um polígono regular (centralizado na tela), empregando a função rotate() e a quantidade de lados da figura que será gerada.

Para isso, usei uma variável que utiliza o valor de 2*PI e divide pelo número de lados. Para cada fatia resultante dessa divisão, é criado um triângulo com um dos vértices centralizado na tela, que por meio do seno e cosseno de cada ângulo gerado, multiplicado pelo tamanho do desejado, é posicionado pelo função rotate(), de modo a compor a figura resultante. O rotate deverá mover cada peça em intervalos iguais ao ângulo dividido.

O rotate() é uma ferramenta poderosa para criação de polígonos, uma vez que é relativamente fácil e econômico de utilizar.

Resultados:

 3 lados
6 lados
 9 lados
50 lados

Link do código: https://drive.google.com/open?id=1FbGyuqOJtEgAV12q2iUc2KB-l8tj5rEI

segunda-feira, 13 de novembro de 2017

Atividade 15 - Transição (MAMI - 2017.2)

A atividade é, basicamente, escolher uma das transições apresentadas nesse vídeo e implementá-la usando Processing. Escolhi a transição que ocorre no minuto 11:31, um fading simples. Para isso, utilizei as duas imagens abaixo (320x240 pixels):



Criei, então, uma variável para cada cor do RGB e , e depois utilizei o scanline para fazer um efeito de escurecimento com uma variável que multiplica os valores por uma variável a que é subtraída por 0.01 a cada frame. Quando o RGB atinge 1 em todos os seus valores (ou seja, fica totalmente sombreado), é feito outro scanline, que desta vez insere a segunda imagem, fazendo, desse modo, a transição.



 Link do código: https://drive.google.com/open?id=152vYiXI1_MMiqg_aYrwJEgrpb4QD4w0j

sexta-feira, 10 de novembro de 2017

Atividade 14 - Cores (MAMI - 2017.2)

O objetivo desta atividade é aplicar ruído em uma imagem qualquer e, após isso, mudar os seus canais de cores para cinza, vermelho e amarelo, respectivamente. Para isso, usei a imagem abaixo (320x240 pixels) como demonstração:


Primeiramente, criei variáveis para cada uma das 4 variações que foram pedidas (ruído, cinza, vermelho e amarelo). Depois, os armazenadores color corOrig e corDestino. Além disso, foram criadas as variáveis c e media, que vão funcionar como "fixadores", das novas cores criadas.

Para o ruído, são criadas cores aleatórias e colocadas na imagem em posições aleatórias. Pode-se controlar a quantidade de ruído pelo número de pixels alterados que deseja-se obter.

Para o cinza, fazemos o processo de scanline na imagem, e obtemos os valores de vermelho, verde e azul de cada pixel da tela. Depois é feita uma média entre esses valores e exibida novamente.

Para as duas cores pedidas, são adquiridos os valores de vermelho e amarelo da imagem, respectivamente e exibidos na imagem conforme os tons de vermelho são mais presentes nos pixels da imagem, no caso do filtro vermelho, o mesmo vale para o amarelo. Quanto menos houver tais cores nos pixels originais, mais escuro será o pixel modificado.

Resultado:


Link do código: https://drive.google.com/open?id=1zGlORWn3CDJsXRTf8qiueuf8Ro1H-r5S

terça-feira, 24 de outubro de 2017

Atividade 13 - Jogo com Colisão (MAMI - 2017.2)

Para fazer o jogo, utilizei as seguintes imagens:


Sprite da personagem


Cenário


Imagem do inimigo (obstáculo)

Primeiro inicializei as variáveis float da posição do personagem e do inimigo, depois o tempo atual e a pontuação. Após isso, inseri o tempo de queda e vidas (variáveis int). Em seguida, adicionei as variáveis PImage dos três elementos acima. Por fim, adicionei três testes booleanos "pulando", "findajogo" e "ganhou".

No setup, as imagens são carregadas. No void draw, está a função findajogo(), que coordena praticamente todo os processos de acabamento do nível.

No void pular, o teste booleano "pulando" é utilizado para realizar o salto da personagem, por meio do "tQueda" (tempo de queda) e a variável y.

No void inimigo a elipse é criada e a imagem é carregada na mesma posição. O inimigo se move a 20 pixels por segundo por meio de um decremento da variável x. Toda vez que ele sai da tela, ele é reposicionado no ponto inicial.

Adentrando o void colisao, notamos a utilização do bounding box, que detecta a colisão de acordo com as coordenadas dos objetos colididos. Caso haja colisão, a variável vidas (inicialmente de valor 3), é decrementada.

Depois, foi colocada uma nova função: void keyPressed. Se a tecla pressionada for o botão direito do teclado, a função "andando" armazena a string "DIREITA", o mesmo se dá com "ESQUERDA". Se o botão Space for pressionado, "pulando" é verdadeiro. Na função keyReleased, se a tecla direita ou esquerda é solta, a variável "andando" armazena a string "PARADO".

Na função seguinte, void andar, os strings são comparados e x é incrementado em 5 pixels, se para direita, ou decrementado em 5 pixels, se para esquerda.

A maior parte das funções criadas estão conectadas ao void findajogo, que tem o objetivo de inicializar e acabar com o jogo. Caso a variável booleana "findajogo" seja false, os elementos são criados e o jogo começa a rodar. Se o x do personagem for maior que a largura da tela, a variável "ganhou" é verdadeira e a variável "findajogo" também. Além disso, se o número de vidas chegue a 0, "findajogo" = true.

No HUD do jogo são exibidos o número de Vidas do personagem (começa com 3), e o tempo atual. Se "ganhou" = true, aparece a pontuação do personagem que é calculada pela equação: pontuação = vidas*1000/ tempo final. Então, são exibidos os valores de tempo, número de vidas restantes e a pontuação, em letras verdes, por meio do text(). Se a vitória não for atingida, é anunciada sua derrota em letras vermelhas e o tempo também aparece.

Obs.: o printline do x e y do personagem foi incluído.

Três exemplos de partidas:



Trabalho de MAMI - Gerador de Arte (Parte 1)

Série: Chevron Palette
Artista: Alexandre Reis


Modelo Natural: O conjunto de obras são compostas pequenos triângulos nas bordas superior e inferior do quadro, além de "zigue-zagues" que preenchem a maior parte da tela. As cores possuem padrões diferentes, que variam de acordo com o quadro. Os que resolvi "copiar" em especial foram os que possuem variação de saturação e brilho conforme as camadas passam.


Modelo Matemático:

Uma primeira análise da obra permite a observação de uma espécie de grid imaginário alinhando os vértices na vertical e tangenciando-os na horizontal, tornando a obra rigorosamente proporcional.


É possível observar quatro triângulos isósceles em cima e três embaixo, sendo que, dos quatro de cima, apenas os dois do meio estão completos.


Podemos perceber que, excetuando os triângulos na parte superior e inferior, podemos dividir as formas em pequenos paralelogramos.

Como a imagem possui aproximadamente de 400x520 pixels, podemos tomar a largura (400px) por módulo. Dessa forma, as medidas ficariam assim:








Modelo Computacional: 

Sabendo disso, comecei a trabalhar no modelo computacional. Primeiro, foi criado um background branco na tela. Para criar as primeiras e últimas formas, os triângulos, usei a função beginShape(TRIANGLES). Depois, para criar a primeira camada de "zigue-zagues", dividi cada camada em quatro partes principais que se repetem, cada uma criada com a função beginShape():


É importante ressaltar que, na função beginShape(), os pontos são estabelecidos nas posições ordenadas, e depois a forma é construída. Portanto, foi muito importante a utilização de rascunhos para prever o que iria ser desenhado na tela. As linhas de contorno foram retiradas com a função noStroke(). Após construir o modelo da camada, usei um laço de repetição for para recriar as 7 subsequentes, sendo que essa estrutura foi encapsulada na função cheVron().

Após isso, verifiquei as cores da imagem original. Apesar de serem semelhantes, e aparentarem estar em degradê de luminância e saturação, isso não é bem verdade.


As camadas variam semi-aleatoriamente a brilho, saturação e um pouco da paleta. Então criei uma variável randômica para cada um desses atributos h (varia de 0~360), s (varia de 25~40) e b (varia de 25~40). Como as camadas de cima tendem a ser mais claras, deixei alto o índice de brilho nesses segmentos, adicionando valores. Conforme foi passando de camada em camada, eu aumentei os índices de saturação e reduzi os índices de brilho, mas com as três variáveis aleatórias influenciando na formação das cores.

Depois, criei uma função que inverte a ordem de cores da tela pela função keyPressed() que é relacionada a uma variável booleana change. Quando é pressionada a tecla Space, change se torna verdadeiro. Desse modo, os quadros passariam a se assemelhar mais com o padrão do quadro abaixo:


Para os quadros passarem de forma mais pausada, deixei o frameRate em 1, ou seja, apenas 1 quadro irá passar a cada segundo.

O resultado final foi este abaixo:

Sem a tecla SPACE pressionada.


Com a tecla SPACE pressionada.

domingo, 22 de outubro de 2017

Atividade 12 - Tilesets (MAMI - 2017.2)

Para criar o mapa desejado, utilizei os dois tiles abaixo.



No programa primeiro iniciei as variáveis PImage, que guardam as informações das imagens escolhidas.

Depois fiz uma matriz que mapeia as imagens dos tiles de acordo com o número dado na função que será implementada posteriormente, no comando switch.


Então, fiz uma função que lê a matriz e carrega a imagem de acordo com a numeração dada pelo comando switch em cada posição. Caso seja 0, carrega a imagem da grama, se for 1, carrega a imagem da água. Para a imagem não ficar muito grande, fiz os espaçamentos horizontais entre as unidades serem de 60 pixels, e os verticais, de 30 píxels. O resultado pode ser verificado abaixo:


Link do código: https://drive.google.com/open?id=0B3-iqp7LYuNJS2k2VFJUTHlNems

Atividade 11 - Máquina de Estados (MAMI - 2017.2)

O objetivo desta atividade é reimplementar a máquina de estados já criada, substituindo a variável keyPressed pela função keyPressed(), explicando as diferenças de uso, vantagens e desvantagens.

Primeiramente, é importante estabelecer as diferenças entre a variável booleana keyPressed e a própria função keyPressed(). No caso da variável, podemos inseri-la em qualquer função do nosso programa como um elemento pontual, tornando-o mais extenso por causa de verificação true ou false, porém mais prático se houverem poucas instâncias.

No entanto, ao optar pela função keyPressed(), podemos criar uma única variável booleana (verificador) no começo do código, e depois apenas coordenar as ações com o verificador, as ferramentas "keyCode" e "key" e a função keyReleased(). Dessa forma, podemos inserir várias ações sem prejudicar a legibilidade do código.

No código da Máquina de Estados criada, foram criadas armazenadores de imagem pelo PImage, e constantes "final int" para os Estados. Por padrão, o Estado irá ser "parado" e o tempo será 0. No "void setup" são carregadas as imagens.

No "void draw" são colocadas as funções criadas processaEstados(), mostraMario(estadoMario) e println(estadoMario, tempo), este último para indicar o tempo em que a ação está sendo realizada e o número do Estado (0 = parado, 1 = andando, 2= martelada).

No processaEstados() são usados testes booleanos para mudanças dos estados, no mostraMario exibem-se as imagens de acordo com o Estado atual e na função keyPressed() verifica-se as teclas pressionadas e muda-se o estadoMario até que se solte a tecla.

sábado, 21 de outubro de 2017

Atividade 10 - Botão Arredondado (MAMI - 2017.2)

O objetivo dessa atividade era fazer um botão quadrado com bordas arredondadas. No começo do programa, foi inicializada a variável raio, que irá ser um parâmetro importante na construção do botão. Depois, utilizei a função apresentada anteriormente chamada rectMode(RADIUS), que cria um retângulo a partir de um vértice no centro deste, para facilitar sua alocação.

Comecei, então, colocando quatro círculos, cada um tangenciando um vértice do retângulo com um ponto de sua borda. Após isso guardei todas essas informações na função criaBotao(). Então, criei a função dist1D, que calcula a diferença entre B e A, e depois fiz a função dist2D, que calcula uma distância entre dois pontos qualquer, baseando-se na primeira função. É retornada a variável "a".

Para checar o pressionamento do botão, foi criada uma função mousePressed, que utiliza a dist1D para calcular a posição do mouse e, por ser uma função de pressionamento, foi colocado um comando "if" para verificar se o clique está nos limites do retângulo pela função dist2D e os parâmetros relativos ao próprio retângulo. Caso esteja, o programa responde com uma mudança de cor (o frame rate foi diminuído na função setup para as diferenças serem notadas) e de texto.



Atividade 9 - Breakout (MAMI - 2017.2)

A técnica de colisão virtual bouding box é uma das mais simples em termos de execução de código, sendo uma boa escolha na criação de jogos amadores. Ela consiste em comparar a forma do objeto a ser colidido com os eixos de um retângulo imaginário criado a partir das coordenadas cartesianas deste.


Dessa forma, as larguras e alturas dos retângulos não precisam estar necessariamente coincidentes com o objeto a ser colidido. Bastam estar aproximados para a colisão funcionar. No entanto, é preciso ter certeza de estar localizando corretamente as "peças" de colisão.


Apesar disso, é um método que está sujeito a inúmeros bugs, por causa de sua simplicidade. Existiram tentativas, no caso do Breakout criado no Processing, em que quando existia um certo nível de desaceleração na bolinha, esta ficava "presa" nos obstáculos. Eventuais erros podem surgir na colisão dos vértices, por causa de "checagens duplas" deste fenômeno.




Além das propriedades da bolinha e da barra movimentadora, vistos em sala de aula, foi implementado um findador de jogo, que ocorre quando a posição da bolinha for superior à da altura da tela. Os obstáculos foram implementados de acordo com a bounding box. Se a posição X da bola for superior à posição X barra + 10 pixels + largura da barra, e posição Y da bola for maior que a posição Y da barra +10 + altura da barra, o movimento é invertido e decrementado em 0.6 na vertical e na horizontal.

Link do código: https://drive.google.com/open?id=0B3-iqp7LYuNJd3FKQlZldVhnem8
Link do tutorial do Youtube usado: https://www.youtube.com/watch?v=8b_reDI7iPM

Trabalho de MAMI - Gerador de Arte (Parte 2)

Link do código: https://drive.google.com/open?id=1AUI4WUZtjbgH_A4s6xBvi9jPa_UV_rkT