# - Bem-vindo amigo :-)

Bem-vindo ao Sonic Pi. Espero que estejas tão ansioso para começar a criar seus próprios sons como eu estou para te mostrar. Vai ser uma viagem muito divertida onde vais aprender tudo sobre música, síntese, programação, composição, desempenho e mais.

Mas antes de tudo, melhor me apresentar – chamo-me Sam Aaron – o criador do Sonic Pi. Você pode me encontrar em @samaaron no Twitter e terei todo o gosto em te dizer olá. Você também pode estar interessado em saber mais sobre as minhas Performances de Live Coding onde programo com o Sonic Pi, ao vivo, para audiências.

Se você tiver algum pensamento, ou ideia de formas de melhorar o Sonic Pi - por favor não hesite em nos mostrar - o feedback nos ajuda e muito. Nunca se sabe, a sua ideia pode se tornar o recurso de amanhã.

Este tutorial está dividido em secções agrupadas por categoria. Embora o tenha escrito para ter uma evolução de aprendizagem fácil desde o início até ao fim, fica à vontade para saltar entre secções. Se achas que está alguma coisa em falta, diz-me e vou considerar pôr-la numa versão futura.

Por fim, assistir à uma sessão de live coding, é uma excelente forma de aprender. Com frequência faço streams em livecoding.tv/samaaron portanto passem pelo meu canal de youtube, digam-me olá, e façam-me muitas perguntas :-)

Ok, vamos começar…

# 1.1 - Live Coding

Um dos aspectos mais emocionantes do Sonic Pi é que podes escrever e modificar o código em tempo real para fazer música, tal como é possível em uma guitarra ao vivo. Isto significa que após alguma prática é possível levar o Sonic Pi para o palco e tocar.

## Abra a sua mente

Antes de entrarmos nos detalhes de como o Sonic Pi funciona no resto deste tutorial, queria dar-te uma ideia de como é programar em tempo real. Não te preocupes se não perceberes muito (ou nada) disto. Tenta só segurar-te à cadeira e aproveita…

## Um Live Loop

Vamos começar, faça uma cópia do seguinte código para um buffer vazio:

    live_loop :flibble do
      sample :bd_haus, rate: 1
      sleep 0.5
    end

Agora, aperte o botão `Run` e você ouvirá uma batida de bombo. Se a qualquer momento desejar parar o som basta pressionar o botão `Stop`. Mas não pressione ainda… Em vez disso, segue estes passos:

1. Tenha certeza de que o som do bombo ainda está tocando
2. Muda o valor do `sleep` de `0,5` para algo maior, como `1`.
3. Pressione o botão `Run` outra vez
4. Nota como a velocidade do bombo mudou.
5. Por fim, lembra-se deste momento, esta foi a primeira vez que você programou ao vivo com o Sonic Pi e é provável que não seja a última…

Ok, isso foi simples. Vamos adicionar algo mais à mistura. Acima de `sample :bd_haus` adiciona a linha `sample :ambi_choir, rate: 0.3`. O teu código deve estar algo parecido com o seguinte:

    live_loop :flibble do
      sample :ambi_choir, rate: 0.3
      sample :bd_haus, rate: 1
      sleep 1
    end

Sinta-se agora à vontade para testar aquilo que aprendeu. Mude parâmetros, como o rate - preste atenção no que acontece quando usa valores mais altos, valores mais baixos, ou até valores negativos. Repare no que acontece quando você muda o parâmetro ‘rate’ pelo sample ‘:ambi_choir’ (para, por exemplo ‘0.29’). O que acontece quando você escolhe um valor pequeno para o `step`? Veja se você consegue fazer ele ir tão rápido que seu computador vai parar com um erro porque não consegue alcançá-lo (se isso acontecer, escolha um valor mais alto para o tempo de `sleep`, e aperte em `Run` de novo).

Experimenta comentar uma das linhas `sample` adicionando um `#` no início:

    live_loop :flibble do
      sample :ambi_choir, rate: 0.3
    #  sample :bd_haus, rate: 1
      sleep 1
    end

Nota como o computador ignora aquela linha, e por isso não a ouvimos. Isto se chama um comentário. No Sonic Pi podemos usar comentários para adicionar ou remover coisas da música.

Finalmente, vou te mostrar algo divertido. Copia o código abaixo para um buffer vazio. Não faça muito esforço compreendê-lo, além de ver que existem dois loops (ciclos) – duas coisas a tocar ao mesmo tempo. Agora, faz o que você faz melhor – experimente e mude. Aqui estão algumas sugestões:

- Experimenta mudar os valores do `rate:` azul para ouvir o som a mudar.
- Experimenta mudar o valor de `sleep` e nota que os loops tocam a velocidades diferentes.
- Experimenta remover o comentário da linha `sample` (remover o `#`) e desfruta do som da guitarra tocado ao contrário.
- Experimenta mudar um dos valores de `mix:` para números entre `0` (não entra na música) e `1` (entra na música com efeito completo).

Lembra de clicar em `Run` e ouvir as mudanças da próxima vez que o loop tocar. Se o seu código não ficar como deseja, não se preocupe – pressione `Stop`, apaga o código e cola uma cópia nova e você está pronto para voltar à tocar. É errando o jeito mais fácil de se aprender…

    live_loop :guit do
      with_fx :echo, mix: 0.3, phase: 0.25 do
        sample :guit_em9, rate: 0.5
      end
    #  sample :guit_em9, rate: -0.5
      sleep 8
    end
    live_loop :boom do
      with_fx :reverb, room: 1 do
        sample :bd_boom, amp: 10, rate: 1
      end
      sleep 8
    end

Agora, continua a tocar e a experimentar até a sua curiosidade sobre como tudo isto funciona entrar em cena e você começar a se perguntar o que mais é possível no Sonic Pi. Agora você está apto à ler o resto do tutorial.

Então o que você está esperando?

# 1.2 - A Interface do Sonic Pi

O Sonic Pi tem um interface muito simples para programar música. Vamos passar algum tempo explorando-a.

- A - Controles de Reprodução
- B - Controles do Editor
- C - Informação e Ajuda
- D - Editor (de código)
- E - Painel de Opções
- F - Vizualizador de Logs
- G - Sistema de Ajuda
- ‘H’ - Osciloscópio
- F - Vizualizador de cues

## A. Controles de Reprodução

Estes botões rosa são os controlos principais para reproduzir e parar sons. O botão Run serve para reproduzir o código no editor, Stop para parar todas as reproduções, Save para guardar o código num ficheiro externo e Record para gravar (num ficheiro WAV) o som que estiver a tocar.

## B. Controles do Editor

Estes butões laranja permitem manipular o editor de código. Os butões de Tamanho + e “Tamanho -“permitem fazer com que o texto seja maior e mais pequeno.

## C. Informação e Ajuda

Estes botões azuis dão-te acesso a informação, ajuda e opções. O botão Info abre a janela de informação que contém informação sobre o Sonic Pi em si – a equipa, histórico de actualizações, contribuidores e a comunidade. O botão Ajuda abre e fecha o sistema de ajuda (F) e o botão Opções abre e fecha a janela das opções que te permitem controlar alguns parâmetros básicos do sistema.

## D. Editor (de código)

Esta é a área onde irá escrever o seu código e compor/tocar a sua música. Trata-se de um editor de texto simples onde pode escrever código, apagá-lo, ou modificá-lo. Pense no que é uma versão básica do Word ou do Google Docs. O editor irá mudar de cores automaticamente tendo em conta as propriedades do código. Pode parecer estranho em primeiro lugar, mas brevemente irá chegar à conclusão que isto é bastante útil. Por exemplo, irá ficar a saber que algo é um número, no instante, em que o caracter assumir a cor base azul

## E. Painel de Opções

O Sonic Pi suporta um número de preferências que podem ser acedidas ao carregar no botão Prefs. Isto abre o painel das opções que inclui várias opções alteráveis. Alguns exemplos são forçar o mono mode, inverter o stereo, activar/desactivar logs e também um slider para o volume e selector de audio no Raspberry Pi.

## F. Visualizador de logs

Quando corres o teu código, vai ser mostrada informação sobre o que o programa está a fazer no Vizualizador do log. Por defeito, verás uma mensagem por cada som que crias com a hora exacta a que começou a tocar. Isto é útil para debugging e perceber o que o teu código está a fazer.

## G. Sistema de Ajuda

Uma das partes mais importantes da interface do Sonic Pi, é o sistema de ajuda que aparece por baixo da janela. Isto pode ser exibido através do botão azul intitulado “Help”. O sistema contém informação de ajuda acerca de todos os aspectos do SOnic Pi, incluindo este tutorial, e uma lista dos sintetizadores e samples disponíveis, assim como efeitos e uma lista completa de todas as função que o Sonic Pi disponibiliza para fins de criação musical

## H. Osciloscópio

O osciloscópio permite visualizar a forma de onde do sinal de áudio reproduzido. É possível observar fcilmente a forma de uma onda triangular e constatar que o sinal se aproxima de parece uma forma de onda triangular e que um beep básico tem uma curva de sinosoidal. É também possível constatar a diferença entre um som alto e um som calmo através do tamanho das linhas. Existem três osciloscópios com os quais é possível trabalhar-se - o pré-definido é uma combinação do osciloscópio para o canal esquerdo e direito. Existe um osciloscópio estéreo que desenha um osciloscópio com linhas separadas para cada canal. Finalmente, existe um osciloscópio com curva Lissajous que permite ver a relação de fase entre o canal esquerdo e direito e permite desenhar imagens bonitas a partir da forma do som (https://en.wikipedia.org/wiki/Lissajous_curve).

## F. Visualizador de logs

Todos os eventos internos e externos (chamados ‘cues’ no Sonic Pi) são automaticamente registrados no Visualizador de Cues. Por exemplo, se tiver um controlador MIDI conectado e pressionar um dos seus botões, ira aparecer um novo evento no Visualizador de Cues a dizer o nome do controlador e que botão foi pressionado. Quando tiver aperfeiçoado as bases para fazer e produzir sons, poderás “cue” sons ou secções inteiras de som baseado em eventos como estes. Um evento “cue” ‘e apenas uma indicação que algo aconteceu. Por exemplo, todas às vezes que um loop “activo” se repete, envia um “cue” evento que ‘e registado no Visualizador de Cues. Todos os eventos como mensagens MIDI e/ou mensagens de OSCiladores de outros programas ou computadores também são apresentados no Visualizador de Cues. Também ‘e possível de gerar diretamente eventos “cue” usando a função `cue`. Qualquer evento registado no Visualizador de Cues pode ser usado para accionar qualquer funcionalidade. Isso é abordado com mais detalhes nas secções 10 a 12 deste tutorial.

# 1.3 - Aprender ao experimentar

O Sonic Pi incentiva-te a aprender tanto sobre computação como música ao tocar e experimentar. A coisa mais importante é que te estejas a divertir, e antes que te apercebas terás aprendido, consequentemente, como escrever código, compor e tocar.

## Não existem erros

Enquanto nos focamos sobre este assunto, deixa-me dar-te um concelho que aprendi ao longo dos meus anos de live coding com música – não existem erros, apenas oportunidades. Isto é algo que ouvi muitas vezes em relação a jazz mas funciona também com live coding. Independentemente do quão experiente és – de principiante a Algoraver a experiente, quando primes o botão para avaliar o código o resultado é sempre inesperado. Pode soar extremamente bem – e nesse caso usa-o. No entanto, pode ser um tanto ou quanto desajustado. Não interessa que tenha acontecido – o que importa é o que fazes com ele a seguir. Pega no som, muda-o e transforma-o em algo espetacular. As pessoas na plateia vão gostar.

## Começa pelo simples

Quando estás a aprender, é tentador querer fazer coisas espetaculares imediatamente. No entanto, aguenta essa vontade e vê-a como um objectivo distante para atingir mais tarde. Por agora, pensa no que seria mais simples, divertido e recompensador de escrever que te ajudará a chegar à coisa espetacular que tens em mente. Uma vez que tenhas uma ideia sobre esse simples passo, tenta e constrói-o, brinca com ele e vê que ideias novas te dá. Brevemente estarás ocupado a divertir e progredir.

Lembra-te de partilhar o teu trabalho com outros!

# 2 - Sintetizadores

OK, chega de introduções – vamos começar a escrever código e a ouvir resultados.

Nesta secção vamos cobrir a base de criar e manipular sintetizadores. Synth é uma abreviatura para sintetizador, que é uma palavra que soa bem para algo que cria sons. Os sintetizadores são normalmente bastante complicados de usar – especialmente sintetizadores analógicos com muitos fios e módulos. No entanto, o Sonic Pi dá-te grande parte dessa capacidade de forma muito simples.

Não te deixes enganar pela simplicidade da interface do Sonic Pi. É possível ir bem longe com manipulação de som sofisticada se é disso que gostas. Segura-te bem…

# 2.1 - Os teus primeiros Beeps

Dá uma olhadela no código que se segue:

    play 70

É aqui que tudo começa. Copia e cola-o no editor (o espaço em branco por baixo do botão Run). Agora carrega em Run…

## Beep!

Intenso. Carrega outra vez. E outra vez. E outra vez…

Wow, espactualar, tenho a certeza que fazias isso o dia todo. Mas espera, antes que te percas com os beeps, experimenta mudar o número:

    play 75

Consegues ouvir a diferença? Experimenta um número mais pequeno:

    play 60

Portanto, os números mais pequenos produzirão beeps de sons com uma frequência mais baixa, e números mais altos farão beeps com um pitch mais alto. Tal como no piano, as teclas a parte baixa do piano (as da mão esquerda) tocarão notes e teclas na parte mais alta do piano (as do lado da mão direita), tocar notas mais altas

Parece que o Dó na quarta oitava (C na notação anglo-saxónica) é identificada pelo numero 60. Por isso `play 60` toca o C (Dó) na quarta oitava. Para tocar a próxima tecla do piano á direita, tens que adicionar 1 a 60 e digitar `play 61`, que neste caso é a tecla preta do C sustenido. Para tocar o D, a próxima tecla é direita, `play 62`.

Não te preocupes se nada disto fizer sentido para ti – também não fazia para mim quando comecei. O que interessa é que números pequenos fazem sons graves e números grandes fazem sons agudos.

## Acordes

Tocar uma nota e divertido, mas tocar várias ao mesmo tempo pode ser ainda melhor. Experimenta:

    play 72
    play 75
    play 79

Jazzy! Quando escreves vários `play`s, eles tocam todos ao mesmo tempo. Experimenta tu mesmo – que números soam bem juntos? Quais soam mal? Experimenta, explora e descobre por próprio.

## Melodia

Tocar notas e acordes é divertido – mas e a melodia? E se quisesses tocar uma nota depois da outra e não ao mesmo tempo? Bem, isso é fácil, só tens de usar `sleep` entre notas:

    play 72
    sleep 1
    play 75
    sleep 1
    play 79

Que bom, um pequeno arpeggio. Então o que significa o `1` em `sleep 1`? Bem, é a duração da pausa. Na realidade significa pausar durante uma batida (ou um tempo), mas para já podemos pensar como uma pausa de 1 segundo. Então e se quisessemos que o nosso arpeggio tocasse mais rápido? Bem, temos de diminuir o valor da pausa. E que tal metade, `0.5`:

    play 72
    sleep 0.5
    play 75
    sleep 0.5
    play 79

Nota como toca mais rápido. Agora, tenta tu, muda as pausas – usa pausas e notas diferentes.

Uma coisa para se experimentar são valores intermédios como `play 52.3` e `play 52.63`. Não há razão para ficarmos usando apenas valores inteiros. Experimente e se diverta.

## Nomes das notas tradicionais

Para aqueles que já sabem de notação musical (não te preocupes se não souberes – não precias para te divertires) podem querer escrever uma melodia usando os nomes das notas tal como Mi e La em vez de números. podem fazer o seguinte:

    # Do (A) | Re (B) | Mi (C) | Fa (D) | Sol (E) | La (F) | Si (G)
    play :C
    sleep 0.5
    play :D
    sleep 0.5
    play :E

Lembra-te de pôr um `:` antes do nome da nota para que esta fique côr-de-orsa. Também podes especificar a oitava adicionando um número à frente da nota:

    play :C3
    sleep 0.5
    play :D3
    sleep 0.5
    play :E4

Se quiseres adicionar um sustenido, de modo a incrementar o pitch meio tom, adiciona um `s` depois da nota, como `play :Fs3`, e se quiseres adicionar um bemol, adiciona um `b`, como `play :Eb3`.

Há também um atalho útil para uma pausa (uma maneira musical de dizer para não tocar nada em vez de uma nota) usando `:r`, `:rest` ou `nil`.

Agora perde-te no código e diverte-te a fazer as tuas próprias músicas.

# 2.2 - Opções do Sintetizador: Amplitude and Panorâmica

Além de te permitir controlar que nota tocar ou qual o sample a tocar, o Sonic Pi dispõe de um conjunto de opções para criar e controlar os sons. Vamos cobrir algumas destas neste tutorial verifica que existe documentação detalhada para cada uma no sistema de ajuda. No entanto, para já vamos introduzir dois dos parâmetros mais úteis: amplitude e panorâmica. Primeiro, vamos ver quais são as nossas opções.

## Opções

O Sonic Pi suporta a notação de opções (ou opts, abreviando) para os sintetizadores. Opts são controlos que podes passar ao `play` que modificam e controlam aspectos do som que ouves. Cada sintetizador tem as suas próprias opts para afinar o seu som. No entanto, existem conjuntos de opts comuns partilhados por muitos synths tal como `amp:` e opts envelope (para serem faladas noutra secção).

Opts têm duas partes principais, o seu nome (o nome do controlo) e o seu valor (o valor que queres dar a essa opt). Por exemplo, podes ter uma opt chamada `queijo` e dar-lhe um valor de `1`.

Opts são passadas a comandos `play` ao usar uma virgula (`,`) e depois o nome da opt, como `amp:` (não te esqueças dos dois pontos `:`) e depois um espaço e o valor da opt. Por exemplo:

    play 50, queijo: 1

(Nota que `queijo:` não existe mesmo, só estamos a usar como exemplo)

Podes dar várias opts separando-as por vírgulas:

    play 50, queijo: 1, feijões: 0.5

A ordem das opts não interessa, por isso o seguinte é idêntico:

    play 50, beans: 0.5, cheese: 1

Opts que não são reconhecidas pelo sintetizado são simplesmente ignoradas (como `queijo` e `feijões`, que são claramente nomes ridículos para opts!)

Se usares a mesma opt mais de uma vez com valores diferentes, a última ganha. Por exemplo, `feijões:` vai ter o valor `2` em vez de `0.5`:

    play 50, feijões: 0.5, queijo: 3, ovos: 0.1, feijões: 2

Muitas coisas no Sonic Pi aceitam opts, portanto gasta algum tempo a aprender como usá-las e estarás preparado! Vamos brincar com a nossa primeira opt: `amp:`.

## Amplitude

A amplitude é a representação numcomputador do volume de um som. Um nível mais elevador de amplitude conduz a um som com um nível de pressão sonora mais elevado, e consequentemente mais alto e uma amplitude baixa produz um som com um nível de pressão sonora mais baixo, e consequentemente mais suave. Da mesma forma que o Sonic Pi usa números para representar tempo e notas, também usa números para representar amplitude. Uma amplitude de 0 é silenciosa (não vais ouvir nada) enquanto uma amplitude 1 é de volume normal. Até podes aumentar a amplitude para 2, 10, 100 ou mais. No entanto, deve-se notar que quando a amplitude de todos os sons aumenta demasiado, o Sonic Pi usa uma coisa chamada compressor que os baixa para ter a certeza que o som não está demasiado alto para os teus ouvidos. Isto pode fazer o som ficar turvo e estrano. Por isso tenta usar amplitudes baixas, entre 0 e 0.5 para evitar compressão.

## Aumenta o volume

Para mudar a amplitude de um som, podes usar a opt `amp:`. Por exemplo, para tocar com metade do nível de pressão sonora dá-lhe o valor `0.5`:

    play 60, amp: 0.5

Para tocar com o dobro da pressão sonora, e consequentemente amplitude e intensidade, dá-lhe `2`:

    play 60, amp: 2

A opt `amp:` só modifica a amplitude do `play` com que está associada. Então, neste exemplo, o primeiro `play` está a metade do volume e o segundo está no normal (`1`):

    play 60, amp: 0.5
    sleep 0.5
    play 65

Claro, podes usar diferentes valores de `amp:` para cada `play`:

    play 50, amp: 0.1
    sleep 0.25
    play 55, amp: 0.2
    sleep 0.25
    play 57, amp: 0.4
    sleep 0.25
    play 62, amp: 1

## Panorâmica

Outra opt divertida é a `pan:`, que controla o a panorâmica de um som stereo. Usar panning para a esquerda num som significa que só o vais ouvir pela coluna esquerda, e usar panning para a direita significa que que só o vais ouvir pela coluna da direita. Como valores, usamos `-1` para representar a esquerda, `0` para o centro e `1` para a direita, em stereo. Claro, estamos livres para usar qualquer valor entre `-1` e `1` para controlar a posição exacta do som.

Vamos tocar um beep na coluna esquerda:

    play 60, pan: -1

Agora, vamos tocar um beep na coluna direita:

    play 60, pan: 1

Finalmente vamos tocar um beep no centro (posição predefinida):

    play 60, pan: 0

Agora, diverte-te a mudar a amplitude e panning dos teus sons!

# 2.3 - Mudar Synths

Divertimo-nos muito até agora a fazer beeps. Mas, já deves estar a ficar aborrecido do beep básico. Será isto tudo o que o Sonic Pi tem para oferecer? De certeza que existe algo mais em live coding além de tocar beeps, não? Há pois, e nesta secção vanis explorar os sons que o Sonic Pi tem para oferecer.

## Sintetizadores

O Sonic Pi tem um conjunto de instrumentos chamados synths (abreviatura para sintetizadores). Enquanto que os samples de áudio representam sons pré-gravados, sintetizadores são capazes de criar novos sons dependendo de como os controlas (que vamos explorar mais tarde neste tutorial). Os sintetizadores do Sonic Pi são muito poderosos e expressivos e vais-te divertir muito a explorá-los e brincar com eles. Primeiro, vamos aprender como escolher que synth usar.

## Ondas de dente de serra ruidosas e sons do sintetizador prophet da Roland

Um som divertido é a (onda dentes de serra) – vamos experimentar-lo:

    use_synth :saw
    play 38
    sleep 0.25
    play 50
    sleep 0.25
    play 62
    sleep 0.25

Vamos experimentar outro som – o som do sintetizador prophet da Roland:

    use_synth :prophet
    play 38
    sleep 0.25
    play 50
    sleep 0.25
    play 62
    sleep 0.25

E que tal combinar dois sons. Um depois do outro:

    use_synth :saw
    play 38
    sleep 0.25
    play 50
    sleep 0.25
    use_synth :prophet
    play 57
    sleep 0.25

De seguida, iremos escutar sons com a mesma duração (por agora a dormir entre sucessivas chamadas para `tocar`):

    use_synth :tb303
    play 38
    sleep 0.25
    use_synth :dsaw
    play 50
    sleep 0.25
    use_synth :prophet
    play 57
    sleep 0.25

Nota que o comando usar_sintetizador só afecta as chamadas que se seguem do `play`. Pensa nele como um interruptor – novos `play`s vão tocar o synth mais recente. Podes mudar o synth a usar com um novo `use_synth`.

## Decobrindo o Som dos Sintetizadores

Para saberes que synths o Sonic Pi tem para brincares dá uma olhadela na opção Synth no sistema de ajuda (à esquerda de Fx). Existem mais de 20 por onde escolher. Aqui estão alguns dos meus favoritos:

- ‘:prophet’
- ‘:dsaw’
- ‘:fm’
- ‘:tb303’
- ‘:pulse’

Agora vamos brincar experimentado trocar os sintetizadores durante a musica. Diverte-te a combinar sintetizadores para criar sons novos e usar synths diferentes em diferentes secções da tua música.

# 2.4 - Duração com Envolventes

Numa secção anterior vimos como podemos usar o comando `sleep` para controlar quando tocar os nossos sons. Mas ainda não sabemos como controlar a duração dos nossos sons.

Para termos um meio simples, mas eficaz, de controlar a duração dos nossos sons, o Sonic Pi possibilita o control de uma curva de envolvente do tipo ADSR (vamos falar sobre o que ADSR significa mais à frente nesta secção). Uma curva de envolvente de amplitude oferece dois aspectos úteis de controlo:

- controlo sobre a duração de um som
- controlo sobre a amplitude de um som

## Duração

Duração é o tempo que durante o qual conseguimos ouvir o som. Uma duração mais longa faz com que ouçamos o som durante mais tempo. Todos os sons no Sonic Pi têm uma envolvente de amplitude controlável, e a duração total dessa envolvente é a duração do som. Portanto, controlando a envolvente, controlas não só a sua duração, como a curva de forma de onde do som

## Amplitude

Além de controlar a duração, a envolvente ADSR também oferece um controlo excelente sobre a amplitude do som. Todos os sons audíveis começam e acabam com silêncio e contêm uma parte não silenciosa no meio. Os envolventes permitem deslizar e manter a amplitude das partes não silenciosas do som. É como dar instruções de como aumentar e diminuir o volume de um amplificador de guitarra. Por exemplo, podes pedir a alguém para “começar com silêncio, aumentar o volume lentamente até ao máximo, manter durante um bocado e depois diminuir rapidamente até silêncio”. O Sonic Pi permite programar este comportamento com curvas de envolvente.

Para recapitular, como vimos antes, uma amplitude de 0 é silêncio e uma amplitude de 1 é volume normal.

Agora, vamos ver cada uma das partes das curvas de envolvente.

## fase de extinção

A única parte a envolvente que é usada por defeito é o tempo de extinsão do som (ou relaxamento). Isto é o tempo que o som de um sintetizador leva até desaparecer completamente. Todos os synths têm, por defeito, um tempo de extinsão de 1, o que significa que duram uma batida (que é 1 segundo, para BPM de 60):

    play 70

Esta nota vai-se ouvir durante 1 segundo. Segue em frente e contabiliza a duração :-) Isto é a versão curta para a versão mais longa e explicita:

    play 70, release: 1

Nota como soam exactamente iguais (o som dura 1 segundo). No entanto, agora é muito fácil alterar a duração mudando o valor da opt `release:`:

    play 60, release: 2

Podemos fazer com que o som dure muito pouco tempo usando um valor mais baixo para `release:`:

    play 60, release: 0.2

A duração do repouso do som chama-se fase de extinsão (ou repouso) e por defeito é uma transição linear (isto é, uma linha recta). O diagrama seguinte ilustra esta transição:

Copiar →↵…«»“”-–—

A linha vertical à esquerda do diagrama mostra que o som começa com amplitude 0, mas vai até a um nível de amplitude máximo imediatamente (isto é a fase de ataque, tal como vamos analisar de seguir). Tendo em conta a amplitude máxima, esta volta a baixar numa linha recta até 0, levando o tempo especificado pela opt `release:`. Tempos de repouso mais longos produzem fade outs mais longos.

Podes então mudar a duração do teu som ao mudar o tempo de repouso. Experimenta mudar os tempos de repouso da tua música.

## Fase de Ataque

Por defeito, a fase de ataque é 0 para todos os synths, o que significa que a amplitude sobe de 0 para 1 imediatamente. Isto resulta num som inicialmente mais percursivo. No entanto, podes querer que o teu som tenha um fade in. Isto pode ser feito com a opt `attack:`. Experimenta usar fade in em alguns sons:

    play 60, attack: 2
    sleep 3
    play 65, attack: 0.5

Pode querer usar váras opts ao mesmo tempo. Por exemplo, para um ataque curto e repouso longo, experimenta:

    play 60, attack: 0.7, release: 4

Esta ataque curto e repouso longo está ilustrado no diagrama seguinte:

Copiar →↵…«»“”-–—

Claro que podes é possível trocar. Tenta um ataque longo e repouso curto:

    play 60, attack: 4, release: 0.7

Copiar →↵…«»“”-–—

Finalmente, também é possível tirar proveito tanto um tempo de ataque como de extinção curtos para sons curtos.

    play 60, attack: 0.5, release: 0.5

Copiar →↵…«»“”-–—

## Fase de Sustentação

Além de especificar os tempos de ataque e repouso, também podes mudar o tempo de sustentação para controlar a fase de sustentação. Isto é o tempo a que a amplitude se vai manter no máximo, entre as fases de ataque e repouso.

    play 60, attack: 0.3, sustain: 1, release: 1

O tempo de sustentação é útil quando se pretende criar sons com mais presença na mistura, antes de entrar na fase de decaimento e extinção. Claro, é válido dar o valor de `0` às opts `attack:` e `release:` e usar só a sustentação para o som não ter nenhum fade in ou fade out. No entanto, deixamos o aviso, um tempo de repouso de 0 pode produzir clicks no som a ser melhor usar um valor muito baixo como `0.2`.

## Fase de Decaimento

Para um nível extra de controlo, também é possível especificar um tempo de decaimento. Esta é a fase do envelope que fica entre as fases de ataque e sustentação e especifica o tempo em que a amplitude vai baixar do `attack_level:` para o `decay_level:` (que, a não ser que o mudes explicitamente, vai ser o mesmo que o `sustain_level:`). Por defeito, a opt `decay:` é 0 e tanto o ataque (`attack_leve:`) como a sustentação (`sustain_level:`) são 1, portanto precisas de especificá-los para o tempo de decaimento fazer efeito:

    play 60, attack: 0.1, attack_level: 1, decay: 0.2, sustain_level: 0.4, sustain: 1, release: 0.5

Copiar →↵…«»“”-–—

## Nível de Decaimento

Um último truque é que apesar da opt `decay_level:`, por defeito, ser igual ao `sustain_level:` podes dar-lhes valores diferentes para controlo total sobre o envelope. Isto permite-lhe criar envolventes como a seguinte:

    play 60, attack: 0.1, attack_level: 1, decay: 0.2, decay_level: 0.3, sustain: 1, sustain_level: 0.4, release: 0.5

Copiar →↵…«»“”-–—

Também é possível colocar um`decay_level:`, com um valor superior ao `sustain_level:`:

    play 60, attack: 0.1, attack_level: 0.1, decay: 0.2, decay_level: 1, sustain: 0.5, sustain_level: 0.8, release: 1.5

Copiar →↵…«»“”-–—

## Curvas de Envolvente ADSR

Em suma, curvas de envolvente do tipo ADSR no Sonic Pi têm as seguintes fases:

1. ataque - tempo de amplitude 0 até ao `attack_level:`
2. decaimento - tempo para mudar a amplitude de `attack_level:` até `sustain_level:`
3. sustentação - tempo para mudar a amplitude de `decay_level:` até `sustain_level:`
4. extinção - tempo para mudar a amplitude de `sustain_leve:` até 0

É importante notar que a duração de um som é a soma dos tempos de cada uma das fases. Portanto, o seguinte som vai durar 0.5 + 1 + 2 + 0.5 = 4 tempos:

    play 60, attack: 0.5, attack_level: 1, decay: 1, sustain_level: 0.4, sustain: 2, release: 0.5

Agora vamos experimentar usar curvos de envolventes com os teus sons…

# 3 - Samples

Outra boa maneira de criar a tua música é usar sons pré-gravados. Em hip-hop chamamos, tradicionalmente, estes sons de samples. Se levares um microfone para a rua, e gravares o som da chuva a bater nas lonas, acabaste de criar um sample, passível de ser usado neste contexto.

O Sonic Pi permite-te fazer coisas espectaculares com samples. Não só traz um banco de mais de 90 samples de domínio público prontos para serem usados, como te deixa tocar e manipular os teus. Vamos lá…

# 3.1 - Trigar Samples

Tocar beeps é só o início. Uma coisa muito mais divertida é tocar samples pré-gravados. Experimenta:

    sample :ambi_lunar_land

O Sonic Pi traz muitos samples passíveis de serem usados. Podes usá-las usando o comando `play`. Para tocar vários samples e notas basta escreve-los de forma sequencial:

    play 36
    play 48
    sample :ambi_lunar_land
    sample :ambi_drone

Se quiseres separá-los temporalmente, usa o comando `sleep`:

    sample :ambi_lunar_land
    sleep 1
    play 48
    sleep 0.5
    play 36
    sample :ambi_drone
    sleep 1
    play 36

Nota como o Sonic Pi não espera que os sons acabem de tocar antes de começar a tocar o seguinte. O comando `sleep` só conta o espaço de tempo entre o início de dois sons(sejam eles samples ou beeps). Isto permite criar sons facilmente, assim como sobreposição de efeitos. Mais tarde neste tutorial vamos ver como controlar a duração de sons com envolventes.

## Descobrir Samples

Existem duas maneiras de descobrir que samples o Sonic Pi já traz. Primeiro, podes usar o sistema de ajuda. Clica em Samples no menu vertical da esquerda, escolhe uma categoria e vais ver uma lista com os samples disponíveis.

Alternativamente, podes usar o sistema de auto-completação. Basta escreveres o início de um grupo de samples, como: `sample :ambi_` e vais ver um menu suspenso com nomes de samples. Experimenta os prefixos de categorias seguintes:

- ‘:ambi_’
- `:bass_`
- `:elec_`
- `:perc_`
- `:guit_`
- `:drum_`
- `:misc_`
- `:bd_`

Experimenta agora misturar samples nas tuas peças!

# 3.2 - Parâmetros dos Samples: Amplitude e Panorâmica

Como vimos com sintetizadores, podemos, facilmente, controlar sons através do seu sistema de parametrização. Os samples suportam exatamente o mesmo mecanismo de parametrização. Vamos reexaminar os parâmetros `amp:` e `pan:`.

## Usar Amplitude com samples

Podes alterar a amplitude de samples com a mesma abordagem que usaste para os sintetizadores:

    sample :ambi_lunar_land, amp: 0.5

## Usar Panorâmica com Samples

Também podemos usar o parâmetro `pan:` com samples. Por exemplo, podemos repoduzir o Amen Break no ouvido esquerdo e depois, a meio, tocá-lo outra vez pelo ouvido direito:

    sample :loop_amen, pan: -1
    sleep 0.877
    sample :loop_amen, pan: 1

Nota que 0.877 é metade da duração da sample `:loop_amen` em segundos.

Finalmente, nota que se alterares algums valores pré-definidos dos sintetizadores com `use_synth_defaults` (vamos falar mais tarde), estes vão ser ignorados pelo `sample`

# 3.3 - Aplicar time stretching em Samples

Agora que sabemos como tocar uma variedade de sintetizadores e samples para criar música, está na hora de aprender a modificar tanto sintetizadores como samples para criar música com um som mais pessoal e consequentemente interessante. Primeiro, vamos explorar a possibilidade de aplicar time-stretching em samples.

## Representação de Samples

Samples são sons pré-gravados, guardados como números que representam como o diafragma da coluna em movimento com vista a gerar som. O diafragma da coluna pode mover-se para dentro ou fora, e então, os números representam o quão dentro ou fora tem de estar o cone para cada momento no tempo. Um sample normalmente tem de guardar vários milhares de números por segundo para para poder ser reproduzido com qualidade e precisão. O Sonic Pi pega nesses números e dá-os à velocidade certa para mover a coluna para dentro e fora e reproduzir o som. Mas também é divertido mudar a velocidade a que os números são alimentam o processo de conversão de sinal digital analógico para que as colunas gerem som.

## Mudar a Velocidade (Rate)

Vamos brincar com um dos sons de ambiente: `:ambi_choir`. Para tocá-la à velocidade (rate) normal, podes passar a opt `rate:` com o valor `1`:

    sample :ambi_choir, rate: 1

Isto toca o sample à velocidade normal (1), nada de especial para já. Mas, podemos mudar esse valor para outro qualquer. Que tal `0.5`:

    sample :ambi_choir, rate: 0.5

Wow! Que é que se passou aqui? Bem, duas coisas. Primeiro, o sample demora o dobro do tempo a ser reproduzido. segundo, o som está uma oitava abaixo. Vamos explorar estas coisas com um bocado mais de detalhe.

## Vamos aplicar time-stretching ao som

Um sample que resulta muito bem com time-stretching é o “Amen Break”. À velocidade normal, poderiamos pô-la numa música de drum ‘n’ bass:

    sample :loop_amen

Contudo, ao mudar a velocidade podemos eventualmente entrar em domínios estéticos, e consequentemente géneros musicais diferentes. Tenta, transpor o sample para metade da velocidade, para obter uma espécie de “hip-hop old school”:

    sample :loop_amen, rate: 0.5

Se aumentarmos a velocidade entramos no território jungle:

    sample :loop_amen, rate: 1.5

Agora para o nosso truque final – vamos ver o que acontece se usarmos um valor de rate (velocidade) negativo:

    sample :loop_amen, rate: -1

Wow! Toca em sentido contrário! Agora experimenta samples diferentes com rates diferentes. Experimenta rates muito altas e muito lentas. Vê até que ponto consegues obter sons interessantes.

## Uma Explicação simples do Termo Sample Rate

Uma maneira de pensar em samples é como molas. Mudar a rate é como esticar ou encolher um mola. Se tocarmos a sample com `rate: 2`, estamos a encolher a mola para metade do seu comprimento normal, e então o sample demora metade do tempo a tocar por ser mais curta. Se tocarmos a sample com `rate: 0.5`, estamos a esticar a mola para o dobro do seu comprimento e, portanto, a sample demora o dobro do tempo a tocar por ser mais longa. Quanto a encolhermos (rate mais alta), esta fica mais curta, quanto mais a esticares (rate mais baixa), mais longa fica.

Ao comprimir uma mola a sua densidade aumenta (número de voltas por cm) – isto faz com que o sample soe mais agudo. Ao esticar a mola a sua densidade diminui e isso faz com que o sample acabe por soar mais grave.

## Vamos perceber o conceito de Sample Rate de um Ponto de Vista Matemático

(Esta parte é para aqueles interessados nos detalhes. Podes passar à frente se não for o teu caso…)

Como vimos anteriormente, um sample é representada por uma lista grelha de representação de valores ao nível das suas coordenadas polares e cartesianas e consequentemente na sua representação através de pfft (fast Fourier transform) e que acabam por ter uma correlação com a fase do som e indicar-nos o ponto onde a coluna se deve encontrar ao longo do tempo. Podemos pegar nessa lista de números e usá-la para desenhar um gráfico que seria parecido com este:

Copiar →↵…«»“”-–—

Já deve ter visto imagens parecidas com esta anteriormente. Esta imagem consiste basicamente na forma de onda de um sample. É só uma gráfico de números. Normalmente, uma onda como esta terá 44100 pontos de informação por segundo (isto deve-se ao Teorema de Nyquist-Shannon), apesar de poder ter mais ou menos (48000, 96000, 192000, etc., resultando daí a necessidade de mais capacidade processamento, e consequentemente um nível superior de qualidade de audio, especialmente em processos de manipulação do áudio como time-stretching). Se o sample tiver a duração de 2 segundos, a onde vai ser representada por 88200 números, e iremos dar à coluna a uma velocidade de 44100 pontos por segundo. Claro, podíamos dá-los ao dobro da velocidade, que seria 88200 pontos por segundo. Levaria, portanto, apenas 1 segundo a tocar. Também podemos tocá-la a metade da velocidade, correspondente a 22050 pontos por segundo, demorando 4 segundos a tocar.

A duração de um sample sample é afectada pela velocidade (rate):

- O Dobro do rate diminui a duração para metade,
- Metade do rate aumenta a duração para o dobro,
- Um rate de 1/4 multiplica a duração por quatro,
- Com um rate de 1/10 o sample acaba por durar 10 vezes mais.

Podemos representar isto com a seguinte fórmula:

    new_sample_duration = (1 / rate) * sample_duration

Mudar o rate também afecta a altura (não confundir com volume!) da sample. A frequência, ou altura, de uma onda é determinada pela velocidade com que esta se move para cima ou para baixo. O nosso cérebro, de alguma forma, transforma o movimento rápido das colunas em notas agudas e movimento lento em notas graves. É por isso que às vezes conseguimos ver as colunas a mexer.

Se pegarmos numa onda e a encolhermos, ela vai mover-se para cima e para baixo mais vezes durante o nosso período de tempo, que corresponde a um segundo (uma vibração por segundo corresponde. a um hz). Isto faz com que o som soe mais agudo. Acontece que ao duplicar o número de oscilações (movimentos para cima e para baixo) duplica a frequência. Então, tocar uma sample ao dobro do rate e isto duplica também a frequência a que esta é ouvida. Do mesmo modo, diminuir o rate para metade vai diminuir a frequência para metade. Outros rates vão afectar a frequência da mesma maneira.

# 3.4 - Samples controlados por curvas de envolvente

Também é possível modificar a duração e amplitude de um sample usando uma curva de envolvente do tipo ADSR. Contudo, isto funciona de forma ligeiramente diferente para curvas de envolvente ADSR disponíveis em sintetizadores. As curvas de envolvente dos samples apenas permitem reduzir a amplitude e duração de um sample - e acabam por não permitir aumenta-la. O sempre irá parar quando tanto o sample tiver terminado de tocar e a envolvente estiver concluída - que acaba por ser primeiro. Portanto, usa um valor de ‘release’ longo, e acabarás por não estender a duração do sample.

## Curvas de Envolvente do Amen Sample

Vamos voltar ao nosso sample de eleição Amen Break:

    sample :loop_amen

Sem opts, ouvimos o sample completo, com toda a sua amplitude. Se quisermos fazer um fade durante 1 segundo usamos o parâmetro ‘ataque’:

    sample :loop_amen, attack: 1

Para um fade in mais curto, escolha um valor de ataque mais curto:

    sample :loop_amen, attack: 0.3

## Sustain Automático

As curvas de envolvente do comportamento do ADSR difere da envolvente do sintetizar standard, ou pre-definido, no valor de sustain. Na envolvente do sintetizador pré-definida, o sustain é 0 por pré-definição a não ser que seja manualmente definido. Com samples, o valor de sustain é definido como default, para um valor automático - o tempo que demora a tocar o resto do sample. É por isto que nós ouvimos o sample completo quando passamos sem pré-definições. Se os valores de ataque, decay, sustain, e release forem todos 0 nós acabamos por nunca ouvir um peep. O Sonic Pi, acaba então por calcular a duração do sample que super-impõe qualquer ataque decay, e tempos de release e usa o resultado como valor de sustain. Se o valor de ataque, decay e release for superior à duração do sample, o sustain é simplesmente definido como 0.

## Fade Outs

Para explorar isto, vamos considerar o Amen Break para mais detalhe. Se perguntarmos ao Sonic Pi durante quanto tempo sample se mantém activo

    print sample_duration :loop_amen

Isto irá imprimir o valor de `1.753310657596372` que possui a duração de um sample em segundos. Vamos agora arrendondá-lo para 1.75 para conveniência neste preciso momento. Agora, se definirmos a o valor do release para ‘0.75’, also surpreendente acabará por acontecer:

    sample :loop_amen, release: 0.75

Irá tocar durante o primeiro segundo do sample num nível de amplitude/pressão sonora/intensidade dinâmica/SPL total, antes de fazer um fade de um período de cerca de 0.75 segundos. Isto é o sustain automático, em acção. Por pré-definição, o tempo de release, outra extinção do som, funciona sempre a partir do fim do sample. Se o nosso sempre tiver 10.75 segundos de duração, este irá tocar durante os primeiro s dez segundos da sua execução em amplitude total antes de fazer um fade out durante cerca de. 0.75s.

Lembre-se: por pré-definição, o valor de ‘release:’ diminui até ao fim do sample.

## Fade In e Fade Out

Podemos usar tanto o valor de ‘ataque:’ e ‘release:’ juntos com o comportment de auto sustain para fazer tanto fade in como fade out durante a duração do sample:

    sample :loop_amen, attack: 0.75, release: 0.75

Como a duração completamente do sample é 1.75s o nosso ataque e release (tempo de extinsão do som), demora cerca de 1.5s, a ser o sustain automaticamente definido para 0.25s. isto permite facilmente fazer fade in e out do sample

## Sustain explicito

Podemos facilmente voltar ao valor normal de ADSR do comportamento do sintetizador definindo manualmente o ‘sustain’ para um valor como 0:

    sample :loop_amen, sustain: 0, release: 0.75

Agora, o nosso sample apenas reproduz durante 0.75 segundos no total. Por pré-definição o ‘ataque:’ e ‘decay:’ é 0, o sample salta automaticamente para a amplitude completa, adiciona ai os 0s e extinguindo-se então para 0 durante o perigo de release - 0.75s.

## Címbalos percussivos

É possível usar este comportamento para afectar positivamente e tornar sons mais longos em sons mais pequenos, e versões mais permissivas. Considere por exemplo o sample ‘:drum_cymbal_open’

    sample :drum_cymbal_open

É possível ouvir o som dos pratos (cymbal), a tocar durante um determinado período de tempo. Contudo, podemos usar a nossa curva de envolvente para o tornar, enfim, mais percussivo:

    sample :drum_cymbal_open, attack: 0.01, sustain: 0, release: 0.1

É então possível emular o ataque de um prato (cymbal) e mantê-lo activo, aumentado o período de sustain

    sample :drum_cymbal_open, attack: 0.01, sustain: 0.3, release: 0.1

Dedica-te agora a colocar curvas de envolvente nos samples. Tenta mudar a velocidade de sobremaneira para resultados realmente interessantes

# 3.5 - Samples Parciais

Esta secção tem como propósito concluir a exploração do reprodutor de simples do Sonic Pi. Vamos fazer uma pequena recapitulação. Até agora foca-mo-nos em possíveis abordagens com vista a disparar samples:

    sample :loop_amen

Observamos então formas de mudar a velocidade de samples tais como tocá-los a a metade da sua velocidade:

    sample :loop_amen, rate: 0.5

De seguida, ire-mo-nos focar em formas de introduzir um sample através de um fade in (vamos fazê-lo a metade da velocidade):

    sample :loop_amen, rate: 0.5, attack: 1

Também olhámos a formas que nos permitem usar o começo de um sample percursivamente dando-lhe ‘sustain’: um valor explícito e definir tanto o ataque como a release (extinção do som), para valores relativamente curtos:

    sample :loop_amen, rate: 2, attack: 0.01, sustain: 0, release: 0.35

Contudo, não seria interessante se nos não tivéssemos que começar no início do sample? Não também interessante se nós não tivesse que acabar sempre no fim do sample?

## Escolhe um ponto de começo

É possível escolher um ponto de começo arbitrário no samples como um valor entre 0 e 1 onde 0 é o início do sample, 1 é o final, e 0.5 é metade da duração do sample. Vamos tentar tocar apenas a última parte do amen break:

    sample :loop_amen, start: 0.5

E que tal um quarto do sample:

    sample :loop_amen, start: 0.75

## A escolher um ponto de conclusão

Do mesmo modo, é possível escolher um ponto arbitrário no sample como um valor entre 0 e 1. Vamos concluir a reprodução do amen break a metade da sua duração:

    sample :loop_amen, finish: 0.5

## A especificar o início e o final

Claro está, podemos combinar estas duas formas de reproduzir segmentos arbitrários dos ficheiros de audio. E que tal uma pequena secção no meio:

    sample :loop_amen, start: 0.4, finish: 0.6

O que acontece se escolhermos um ponto inicial depois da posição final?

    sample :loop_amen, start: 0.6, finish: 0.4

Porreiro! Toca em sentido contrário!

## A combinar com a velocidade

É possível combinar esta possibilidade de tocar arbitrariamente segmentos do audio com o nosso amigo ‘velocidade:’. Por exemplo, podemos reproduzir um pequeno segmento do meio do amen break muito lentamente:

    sample :loop_amen, start: 0.5, finish: 0.7, rate: 0.2

## A combinar com curvas de envolvente

Finalmente, podemos combinar tudo isto com as nossas curvas de envolvente de ADSR para produzir resultados interessantes:

    sample :loop_amen, start: 0.5, finish: 0.8, rate: -0.2, attack: 0.3, release: 1

Agora vamos e temos um mash up de samples em reprodução com todas estas coisas interessantes…

# 3.6 - Samples Externos

Enquanto que os samples incorporados permitem a alguém iniciar o processo de interacção com a plataforma rapidamente, podes desejar experimentar com outros gravados na tua música. O Sonic Pi suporta isto de forma integral. Primeiro, deixa-me ter uma pequena discussão acerca da portabilidade da tua peça.

## Portabilidade

Quando compões uma peça apenas com samples e sintetizadores incorporados, o código é tudo o que precisas para reproduzir fielmente a tua música. Pensa nisto por um breve momento - é espetacular! Um pequeno excerto de texto permite-te enviar a música numa pen ou colocar o código no Gist representado tudo o que precisas para reproduzir os teus sons. Isto faz com que seja realmente simples partilhar com os teus amigos de forma a que eles precisem apenas do código para reproduzir a música

Contudo, se começares a usar os teus sons pré-gravados, perdes esta portabilidade. É por isso que ao reproduzir a tua música aos outras pessoas não precisem apenas do teu código, mas também precisem dos teus samples. Isto limita a possibilidade para outras pessoas manipularem, misturarem e experimentarem com o teu trabalho. É claro que não deves deixar de usar os teus samples, a ser apenas o que deves considerar, a decidir então por ti a melhor forma para trabalhares.

## Samples Locais

Portanto como é que fazes para tocar arbitrariamente um ficheiro WAV, AIFF ou FLAC no teu computador? Tudo o que precisas é de passar o cominho para esse ‘sample’.

    # Raspberry Pi, Mac, Linux
    sample "/Users/sam/Desktop/my-sound.wav"
    # Windows
    sample "C:/Users/sam/Desktop/my-sound.wav"

O Sonic Pir permite carregar automaticamente e tocar o sample. Também podes passar os parâmetros pré-definidos que costumas para passar como ‘sample’:

    # Raspberry Pi, Mac, Linux
    sample "/Users/sam/Desktop/my-sound.wav", rate: 0.5, amp: 0.3
    # Windows
    sample "C:/Users/sam/Desktop/my-sound.wav", rate: 0.5, amp: 0.3

# 3.7 - Pacotes de Samples

Nota: esta secção do tutorial cobre tópicos avançados de trabalho com grandes diretórios dos teus próprios samples. Isto será o caso se tiveres descarregado ou comprado o teu próprio pacote de samples e desejares usa-lo com o Sonic Pi.

Sente-te à vontade para saltar esta secção se estiveres contente com trabalhar com samples pré-incorporados

Quando te encontrares a trabalhar com ficheiros grandes ou ficheiros externos também pode ser espectaculérrimo escrever o caminho completo para disparar um sample individual

Por exemplo, vamos partir do princípio que tens a pasta abaixo na tua máquina:

    /path/to/my/samples/

Quando olhamos para os conteúdos da pasta encontramos os seguintes samples:

- ‘100_A#_melody1.wav’
- `100_A#_melody2.wav`
- `100_A#_melody3.wav`
- `120_A#_melody4.wav`
- `120_Bb_guit1.wav`
- `120_Bb_piano1.wav`

Normalmente de modo a reproduzirmos o sample de piano apenas temo de usar o caminho completo:

    sample "/path/to/my/samples/120_Bb_piano1.wav"

Se quisermos tocar o sample de guitarra podemos usar este caminho, também

    sample "/path/to/my/samples/120_Bb_guit.wav"

Contudo, ambas as evocação do sample exigem que saibamos os nomes dos samples dentro da nossa directoria. E que tal se quisermos apenas ouvir cada um dos samples individualmente de forma rápida?

## A indexar as Bibliotecas de Samples

Se quisermos reproduzir o primeiro sample na directoria apenas precisamos de passar o nome do directório para ‘sample’ e o index a ‘0’ tal como acontece abaixo

    sample "/path/to/my/samples/", 0

Também podemos criar um atalho para a nossa directoria utilizando uma variável:

    samps = "/path/to/my/samples/"
    sample samps, 0

Se agora quisermos reproduzir a segunda amostragem na nossa directoria, apenas é necessário adicionar 1 ao nosso índice:

    samps = "/path/to/my/samples/"
    sample samps, 1

Note-se que não mais é preciso conhecer os nomes das amostragens na directoria - apenas necessitamos de conhecer a própria directoria (ou ter um atalho para ela). Se pedirmos um índice que é maior do que o número de amostragens, simplesmente dará a volta da mesma foram que Rings. Portanto, qualquer que seja o número que for utilizado, é garantido que vamos obter uma das amostragens nessa directoria.

## Como filtrar Pacotes de Amostragens

Geralmente indexar é o suficiente, mas algumas vezes precisamos de mais capacidade para organizar os samples. No entanto, muitos pacotes de samples contém informações úteis nos nomes dos ficheiros. Vamos dar uma olhada nos nomes dos ficheiros de sample no nosso diretório.

- ‘100_A#_melody1.wav’
- `100_A#_melody2.wav`
- `100_A#_melody3.wav`
- `120_A#_melody4.wav`
- `120_Bb_guit1.wav`
- `120_Bb_piano1.wav`

Note que há boas informações nos nomes dos arquivos. Primeiro, BPM (batidas por minuto)

Podemos usar essa convenção de nomenclatura apresentada nos exemplos para ajudar a filtrar o que queremos. Por exemplo, se estamos a trabalhar em 120 BPM, podemos filtrar todos os exemplos que contenham ‘“120’” da seguinte maneira:

    samps = "/path/to/my/samples/"
    sample samps, "120"

Isso tocará o primeiro resultado encontrado. Se quisermos o segundo, basta usar o índice:

    samps = "/path/to/my/samples/"
    sample samps, "120", 1

Podemos usar vários filtros ao mesmo tempo. Se quisermos um exemplo em que o nome do ficheiro contenha tanto “120” como “A#”, podemos usar o seguinte código:

    samps = "/path/to/my/samples/"
    sample samps, "120", "A#"

Finalmente, podemos usar nossas próprias definições para chamar o ‘sample’:

    samps = "/path/to/my/samples/"
    sample samps, "120", "Bb", 1, lpf: 70, amp: 2

## Código

O filtro pre-arg aceita dois tipos de informação: código e filtros. Códigos são informações usadas para criar uma lista de resultados em potencial. Um código pode ter duas formas:

1. “/path/to/samples” - um comando representando um caminho válido para um diretório
2. “/path/to/samples/foo.wav” - um comando representando um caminho válido para um sample

`sample` fn primeiro reunirá todos os códigos e os usará para criar uma grande lista de resultados possíveis. A lista é construída primeiro adicionando todos os caminhos de diretório válidos e depois todos os ficheiros `.flac`, `.aif`, `.aiff`, `.wav`, `.wave` encontrados nos diretórios.

Por exemplo, dê uma olhada no seguinte código:

    samps = "/path/to/my/samples/"
    samps2 = "/path/to/my/samples2/"
    path = "/path/to/my/samples3/foo.wav"
    sample samps, samps2, path, 0

Aqui estamos combinando os samples encontrados em dois diretórios e adicionando um sample específico. Se `"/path/to/my/samples/"` contém 3 samples e `"/path/to/my/samples2/"` contém 12, temos 16 samples possíveis para indexar e filtrar ( 3+ 12 + 1).

Por predefinição, apenas os ficheiros de sample dentro de um diretório são colhidos para a lista de resultados possíveis. Algumas vezes quer pesquisar e filtrar em subdiretórios. Para isso, use a busca recursiva adicionando ‘**’ ao final do diretório raiz.

    samps = "/path/to/nested/samples/**"
    sample samps, 0

Cuidado ao buscar em uma pasta com muitos subdiretórios porque poderá levar muito tempo. Porém, os conteúdos serão guardados para utilização posterior e a demora acontecerá apenas na primeira vez.

Finalmente, note que as fontes precisam de ser definidas inicialmente. Se nenhuma fonte é indicada, os samples de origem serão usados como candidatos na lista padrão de trabalho.

## Filtros

Depois de teres uma lista de candidatos poderás usar os seguintes filtros para reduzir ainda mais a seleção:

- `"foo"` As cadeias filtram ocorrências da sub-cadeia dentro do nome do ficheiro (menos o caminho da directoria e a sua extensão).
- `/fo[oO]/` Usando o padrão de “Expressões Regulares” para filtrar o nome do ficheiro (menos o caminho da directoria e a extensão do ficheiro).
- `:foo` - Keywords filtra os candidatos com base na correspondência directa da palavra chave no nome do ficheiro (menos o caminho da directoria e a extensão do ficheiro).
- `lambda{|a| ... }` - Função PROC com um argumento será tratada como um filtro de candidatos ou uma função geradora. Recebe uma lista de candidatos actuais e devolve uma nova lista de candidatos (uma lista de caminhos para os ficheiros de samples).
- `1` - Números irão selecionar o candidato com esse índice (desdobrando o índice circularmente se necessário).

,Por exemplo. podemos filtrar sobre todos os samples de uma directoria que contêm a cadeia `"foo"`e tocar o sample com a primeira correspondência a meia velocidade:

    sample "/path/to/samples", "foo", rate: 0.5

Consultar a ajuda para `sample` para exemplos mais detalhados de uso. Notar que a ordem dos filtros é honrada.

## Compósitos

Finalmente, poderá ser usadas listas sempre que se colocar uma fonte ou filtro. A lista será “achatada” e o seu conteúdo será tratado como uma fonte regular ou filtro. Assim as seguintes chamadas a `sample` são semanticamente equivalentes:

    sample "/path/to/dir", "100", "C#"
    sample ["/path/to/dir", "100", "C#"]
    sample "/path/to/dir", ["100", "C#"]
    sample ["/path/to/dir", ["100", ["C#"]]]

## Envolvendo

Esta é uma secção avançada para pessoas que necessitam verdadeiro poder para manipular e usar pacotes de samples. Se muito desta secção não fizer sentido não se preocupe. É provável que não necessite de nenhuma da sua funcionalidade por agora. No entanto, saberá quando necessitar e poderá regressar e reler a secção quando começar a trabalhar com grandes directorias de samples.

# 4 - Randomização

Uma boa maneira de adicionar algum interesse à musica é usando números aleatórios. Sonic Pi apresenta uma excelente funcionalidade em adicionar aleatoriedade à sua musica, mas antes de começar temos que aprender a verdade chocante: no Sonic Pi random não é verdadeiramente random. O que raio quer isto dizer? Bem, vamos ver.

## Repetibilidade

Uma função verdadeiramente útil para gerar números aleatórios é `rrand` que devolve um número aleatório entre dois números - um min e um max (`rrand` é abreviatura de ranged random). Vamos tentar tocar uma nota aleatória:

    play rrand(50, 95)

Ooh, tocou uma nota aleatória. Tocou a nota `83.7527`. Um simpática nota entre 50 e 95. Espera, previ a mesma nota que tu? Algo estranho está a acontecer. Tenta correr o código novamente. O quê? Escolheu `83.7527` novamente? Isto não pode ser aleatório!

A resposta é que não é verdadeiramente aleatório, é pseudo-aleatório. Sonic Pi gera números pseudo-aleatórios de uma maneira repetível. Isto é bastante útil para assegurar que a musica que crias na tua maquina soa idêntica na maquina de qualquer pessoa - mesmo que use aleatoriedade na tua composição.

Claro que, numa dada peça de musica, se ‘aleatoriamente’ escolhe `83.7527`todas as vezes, não seria muito interessante. No entanto, não o faz. Experimente o seguinte:

    loop do
      play rrand(50, 95)
      sleep 0.5
    end

Sim! Finalmente soa a aleatório. Numa dada run subsequentes chamadas à função random devolve valores aleatórios. No entanto, a próxima corrida ira produzir exactamente a mesma sequência de valores aleatórios e soa exactamente igual. É como se todo o código do Sonic Pi regressa-se no tempo exactamente ao mesmo ponto cada vez que se pressiona o botão Run. É o dia do Groundhog da síntese musical!

## Sinos amaldiçoados

Uma bonita ilustração da aleatoriedade em acção é o exemplo dos sinos amaldiçoados em que o loop do sample `:perc_bell` é tocado a uma velocidade e tempo de descanço aleatorio entre os sons de sinos.

    loop do
      sample :perc_bell, rate: (rrand 0.125, 1.5)
      sleep rrand(0.2, 2)
    end

## Cutoff aleatório

Outro exemplo giro de aleatoriedade é a modificação do cutoff de um sintetizador de forma aleatória. Um bom sintetizador para experimentar isto é o emulador `:tb303`:

    use_synth :tb303
    loop do
      play 50, release: 0.1, cutoff: rrand(60, 120)
      sleep 0.125
    end

## Sementes para gerar números aleatórios

Então e se não gostares desta sequência em particular de números aleatórios que o Sonic Pi fornece? É totalmente possível escolher um diferente ponto de partida usando `use_random_seed` . A semente padrão usada para gerar números aleatórios é 0, escolhe uma semente diferente para uma diferente experiência aleatória!

Considera o seguinte:

    5.times do
      play rrand(50, 100)
      sleep 0.5
    end

Cada vez que corres este código, ouvirás a mesma sequência de 5 notas. Para ter uma diferente sequência simplesmente altera a semente:

    use_random_seed 40
    5.times do
      play rrand(50, 100)
      sleep 0.5
    end

Isto irá produzir uma sequência diferente de 5 notas. Ao alterar a semente e ouvindo o resultado poderás encontrar algo que gostes - e depois partilhar com outros, eles ouviram exactamente o que ouviste.

Vamos ver algumas outras funções aleatórias úteis.

## escolhe

Algo bastante comum de se fazer é escolher um item aleatoriamente de uma determinada lista de itens conhecidos. Por exemplo, posso querer tocar uma nota da seguinte lista: 60, 65 ou 72. Posso conseguir isso com `choose`que me deixa escolher um item da lista. Primeiro coloco os meus números numa lista o que é feito envolvendo-os em parênteses rectos separados por virgulas: `[60, 65, 72]`. A seguir só temos que os passar ao `choose`:

    choose([60, 65, 72])

Vamos ouvir como soa:

    loop do
      play choose([60, 65, 72])
      sleep 1
    end

## rrand

Já vimos `rrand`, mas voltando a ela. Ela devolve um número aleatório entre dois números exclusivamente. Isso significa que numa irá fornecer o máximo ou o mínimo - mas sim sempre algo entre os dois. O número será sempre um número flutuante - que não é um numero inteiro mas sim a fracção de um numero. Exemplo de números flutuantes devolvidos por `rrand(20,110)`:

- 87.5054931640625
- 86.05255126953125
- 61.77825927734375

## rrand_i

Ocasionalmente queremos um número inteiro e não um flutuante. É ai que a `rrand_i` nos vem ajudar. Trabalha da forma similar a ´rrand`excepto que pode devolver o min e o max como potencial número aleatório (o que significa que é inclusivo e não exclusivo nos limites). Exemplos de números devolvidos por` rrand_i(20,100)` são:

- 88
- 86
- 62

## rand

Isto devolve um número aleatório flutuante entre 0 (inclusive) e um valor máximo especificado (exclusivo). Por padrão irá devolver um valor entre 0 e 1. É assim útil para escolher valores aleatórios `amp:`:

    loop do
      play 60, amp: rand
      sleep 0.25
    end

## rand_i

Similarmente à relação entre `rrand_i` e `rrand`, `rand_i` irá devolver um número aleatório inteiro entre 0 e o valor máximo que especificaste.

## Dado

Às vezes queres emular o lançamento de um dado - isto é um caso especial de `rrand_i` em que o valor mais baixo é 1. Chamar `dice` requer que especifiques o número de lados do dado. Um dado normal tem 6 lados, assim `dice(6)` irá se comportar de forma semelhante - devolvendo os valores 1, 2, 3, 4, 5 ou 6. No entanto, tal como nos jogos de role play, poderás encontrar dados de 4 lados, ou 12 ou 20, ou até mesmo uma dado de 120 lados.

## one_in

Finalmente poderás querer emular o lançamento de uma pontuação máxima num dado tal como um 6 num dado normal. `one_in` devolve true com a probabilidade de um sobre o número de lados do dado. Assim `one_in(6)` irá devolver true com a probabilidade de 1 em 6 ou false em caso contrario. True e false são valores muito úteis nas declarações condicionais `if`, que serão descritas nas seguintes secções deste tutorial.

Agora vai e enche o teu código de aleatoriedade!

# 5 - Estruturas de programação

Agora que aprendemos o básico de como criar sons com `play` e `sample` e a criação de melodias simples e ritmos usando `sleep` entre os sons, perguntas-te o que mais o mundo do código te pode oferecer…

Vais ter uma agradável surpresa! Estruturas básicas de programação como looping, condicionais, funções e threads dão-te ferramentas extremamente poderosas para expressares as tuas ideias musicais.

Vamos começar com o básico…

# 5.1 - Blocos

Uma estrutura que se vê bastante no Sonic Pi é um bloco. Um bloco permite-nos fazer coisas úteis com grandes pedaços de código. Podemos mudar algo que ocorre numa única linha de código com parâmetros de synth e sample. No entanto podemos querer fazer algo mais significativo a várias linhas de código. Por exemplo, podemos querer fazer um loop, adicionar reverb, apenas correr 1 vez a cada 5 vezes, etc. Considera o seguinte código:

    play 50
    sleep 0.5
    sample :elec_plip
    sleep 0.5
    play 62

Para fazer algo com um pedaço de código devemos dizer ao Sonic Pi onde o bloco começa e onde acaba. Usamos `do` para o começo e `end` para o fim. Por exemplo:

    do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end

No entanto isto não está completo e não funcionará (tenta e terás um erro) uma vez que não dissemos ao Sonic Pi o que fazer com este bloco do/end. Dizemos isso aos Sonic Pi escrevendo um código especial antes do `do`. Iremos ver alguns destes pedaços especiais de código mais tarde neste tutorial. Por agora, é importante saber que envolvendo o teu código entre `do`e `end` diz ao Sonic Pi que queres fazer algo especial com esse pedaço de código.

# 5.2 - Iteração e Loops

Até agora passamos imenso tempo a olhar para diferentes sons que podemos fazer com blocos `play` e `sample`. Também aprendemos como lançar esses sons no tempo usando `sleep`.

Como provavelmente descobriste, existe muito divertimento que se tem com estes blocos básicos de construção. No entanto, uma dimensão totalmente nova de divertimento abre-se quando começares a usar o poder do código para estruturar a tua musica e composições. Nas próximas secções iremos explorar essas novas poderosas ferramentas. Primeiro iteração e loops.

## Repetição

Escreveste algum código e gostarias de o repetir algumas vezes? Por exemplo, podes ter algo como isto:

    play 50
    sleep 0.5
    sample :elec_blup
    sleep 0.5
    play 62
    sleep 0.25

Se quiseres repetir isto 3 vezes? O que podemos fazer é copiar e colar três vezes:

    play 50
    sleep 0.5
    sample :elec_blup
    sleep 0.5
    play 62
    sleep 0.25
    play 50
    sleep 0.5
    sample :elec_blup
    sleep 0.5
    play 62
    sleep 0.25
    play 50
    sleep 0.5
    sample :elec_blup
    sleep 0.5
    play 62
    sleep 0.25

Isso é muito código! O que acontece se quiseres mudar o sample para `:elec_plip`? Terás de encontrar todos os locais onde aparece o `:elec_blup`original e os mudar. Mais importante, como repetir o código original 50 ou 1000 vezes? Isso é muito código, e muitas linhas de código para alterar se quiseres fazer uma mudança.

## Iteração

De facto, alterar o código deverá ser fácil como dizer faz isto 3 vezes. Na verdade é isso. Lembraste do nosso velho amigo bloco de código? Podemos o usar para marcar o inicio e o fim do código que queremos repetir 3 vezes. Usamos então o código especial `3.times`. Assim, em vez de escrever faz isto 3 vezes, escrevemos `3.time do` - não é difícil. Não te podes esquecer de escrever `end` no final do código que queres repetir:

    3.times do
      play 50
      sleep 0.5
      sample :elec_blup
      sleep 0.5
      play 62
      sleep 0.25
    end

Isto assim é bem mais limpo que cortar e colar. Podemos usar isto para criar elegantes estruturas repetitivas:

    4.times do
      play 50
      sleep 0.5
    end
    8.times do
      play 55, release: 0.2
      sleep 0.25
    end
    4.times do
      play 50
      sleep 0.5
    end

## Iterações aninhadas

Podemos colocar iterações dentro de iterações e produzir padrões interessantes. Por exemplo:

    4.times do
      sample :drum_heavy_kick
      2.times do
        sample :elec_blip2, rate: 2
        sleep 0.25
      end
      sample :elec_snare
      4.times do
        sample :drum_tom_mid_soft
        sleep 0.125
      end
    end

## Looping

Se quiseres que algo repita muitas vezes, poderás dar por ti a usar números grandes como `1000.times do`. Neste caso é provavelmente melhor pedir ao Sonic Pi para repetir para sempre (pelo menos até premires o botão stop). Vamos repetir o amen break para sempre:

    loop do
      sample :loop_amen
      sleep sample_duration :loop_amen
    end

a coisa importante a saber sobre loops é que eles actuam como buracos negros para o código. Uma vez que o código entra em loop nunca sairá até premires stop - irá repetir para sempre. Isso significa que se tiveres código após o loop nunca o irás ouvir. Por exemplo, o címbalo depois deste loop nunca será tocado:

    loop do
      play 50
      sleep 1
    end
    sample :drum_cymbal_open

Agora podes estruturar o teu código com iterações e loops!

# 5.3 - Condicionais

Uma coisa comum que certamente quererás fazer é não tocar só notas aleatórias (ver a secção anterior em aleatoriedade) mas também tomar decisões aleatórias baseadas no resultado do código que corre ou nalgum outro código. Por exemplo, poderás querer aleatoriamente tocar uma bateria ou címbalo. Podemos conseguir isso com uma declaração `if`.

## Lançar uma moeda

Então, vamos lançar uma moeda: se for cara, toca a bateria, se for coroa, toca o címbalo. Podemos emular o lançamento da moeda com a nossa função `one_in` (introduzida na secção de aleatoriedade), especificando a probabilidade de 1 em 2: `one_in(2)`. Podemos usar esse resultado para decidir entre dois pedaços de código, o código que toca a bateria e o código que toca o címbalo.

    loop do
      if one_in(2)
        sample :drum_heavy_kick
      else
        sample :drum_cymbal_closed
      end

      sleep 0.5

    end

Repara que a declaração `if` tem 3 partes:

- A questão a perguntar
- A primeira escolha de código a executar (se a questão à pergunta for sim)
- A segunda escolha de código a executar (se a resposta à questão for não)

Tipicamente em linguagens de programação, a noção de sim é representada pelo termo `true` e a noção de não é representada pelo termo `false`. Assim temos que arranjar uma questão que nos dirá uma resposta `true` ou `false` o que é exactamente isso que o `one_in` faz.

Repara como a primeira escolha está envolvida entre o `if` e o `else` e a segunda escolha está envolvida entre o `else` e o `end`. Tal como os blocos do/end poderás colocar múltiplas linhas de código nesses espaços. Por exemplo:

    loop do
      if one_in(2)
        sample :drum_heavy_kick
        sleep 0.5
      else
        sample :drum_cymbal_closed
        sleep 0.25
      end

    end

Desta vez estamos a dormir por um determinado tempo diferente dependendo da escolha que fazemos.

## if simples

Por vezes queremos opcionalmente executar apenas uma linha de código. Isto é possível colocando o `if` e depois a questão no final. Por exemplo:

    use_synth :dsaw
    loop do
      play 50, amp: 0.3, release: 2
      play 53, amp: 0.3, release: 2 if one_in(2)
      play 57, amp: 0.3, release: 2 if one_in(3)
      play 60, amp: 0.3, release: 2 if one_in(4)
      sleep 1.5
    end

Isto irá tocar o acorde de diferentes números com a possibilidade de cada nota ter uma diferente probabilidade.

# 5.4 - Threads

Fizeste uma killer bassline e um fat beat. Como os tocar ao mesmo tempo? Uma solução é interligar os dois manualmente - tocar algum baixo, depois um pouco de bateria, e mais algum baixo… No entanto, o tempo torna-se difícil de pensar, especialmente se começares a entrelaçar mais elementos.

E se o Sonic Pi pode-se entrelaçar as coisas por ti automaticamente? Bem, ele pode, e fazes isso com algo chamado thread.

## Loops infinitos

Para manter este exemplo simples, terás que imaginar que isto é um fat beat e uma killer bassline:

    loop do
      sample :drum_heavy_kick
      sleep 1
    end
    loop do
      use_synth :fm
      play 40, release: 0.2
      sleep 0.5
    end

Como discutimos previamente, loops são buracos negros para o programa. Uma vez neles nunca poderás sair até premires stop. Então como tocar ambos os loops ao mesmo tempo? Teremos que dizer ao Sonic Pi que queremos começar algo ao mesmo tempo que o resto do código. É ai que os threads vêm ao nosso auxilio.

## Threads ao auxilio

    in_thread do
      loop do
        sample :drum_heavy_kick
        sleep 1
      end
    end
    loop do
      use_synth :fm
      play 40, release: 0.2
      sleep 0.5
    end

Envolvendo o primeiro loop num `in_thread` do bloco do/end dizemos aos Sonic Pi para correr o conteúdo do bloco exactamente ao mesmo tempo que a declaração seguinte ao bloco (que até é o segundo loop). Experimenta e ouvirás a bateria e o baixo entrelaçados.

Agora e se queremos adicionar um synth por cima. Algo como:

    in_thread do
      loop do
        sample :drum_heavy_kick
        sleep 1
      end
    end
    loop do
      use_synth :fm
      play 40, release: 0.2
      sleep 0.5
    end
    loop do
      use_synth :zawa
      play 52, release: 2.5, phase: 2, amp: 0.5
      sleep 2
    end

Teremos o mesmo problema que anteriormente. O primeiro loop é tocado ao mesmo tempo que o segundo devido ao `in_thread`. No entanto, o terceiro loop nunca é alcançado. Assim necessitamos de outro thread:

    in_thread do
      loop do
        sample :drum_heavy_kick
        sleep 1
      end
    end
    in_thread do
      loop do
        use_synth :fm
        play 40, release: 0.2
        sleep 0.5
      end
    end
    loop do
      use_synth :zawa
      play 52, release: 2.5, phase: 2, amp: 0.5
      sleep 2
    end

## Correr como threads

O que te pode supreender é que quando carregas no botão Run, está a criar um novo thread para o código correr. É por isso que carregando múltiplas vezes irá adicionar camadas de som umas sobre as outras. As próprias corridas são threads, elas irão entrelaçar automaticamente os sons por ti.

## Scope

Quando aprenderes a conquistar o Sonic Pi, aprenderas que os threads são o bloco de construção mais importante da tua musica. Um dos importantes trabalhos que fazem é isolar a noção de settings actuais de outros threads. O que significa isso? Bem, quando trocas de synth usando o `use_synth` apenas estás a mudar de sintetizador na thread actual - nenhum outro thread terá a mudança de sintetizador. Vamos ver isto em pratica:

    play 50
    sleep 1
    in_thread do
      use_synth :tb303
      play 50
    end
    sleep 1
    play 50

Repara como o som do meio foi diferente dos restantes? A declaração `use_synth` apenas afectou o thread onde estava e não o thread principal exterior que corre.

## Herança

Quando crias um novo thread com `in_thread`, o novo thread irá automaticamente herdar todas as settings actuais do thread corrente. Vamos ver isso:

    use_synth :tb303
    play 50
    sleep 1
    in_thread do
      play 55
    end

Repara como a segunda nota foi tocada com o sintetizador `:tb303` apesar de ter sido tocada de uma thread separada? Todas as settings modificadas com as várias funções `use_*` irão se comportar da mesma maneira.

Quando os threads são criados eles herdam todas as settings dos seus pais mas não passam para eles qualquer mudança que tenham.

## Nomeando threads

Finalmente, podemos dar nomes aos nossos threads:

    in_thread(name: :bass) do
      loop do
        use_synth :prophet
        play chord(:e2, :m7).choose, release: 0.6
        sleep 0.5
      end
    end
    in_thread(name: :drums) do
      loop do
        sample :elec_snare
        sleep 1
      end
    end

Vê o painel de registro quando corres este código. Vê como o regsitro reporta o nome do thread na mensagem?

    [Run 36, Time 4.0, Thread :bass]
     |- synth :prophet, {release: 0.6, note: 47}

## Apenas é permitido um Thread por nome

Uma ultima coisa sobre nomear threads é que apenas um thread de um determinado nome pode estar a correr ao mesmo tempo. Vamos explorar isto. Considera o seguinte código:

    in_thread do
      loop do
        sample :loop_amen
        sleep sample_duration :loop_amen
      end
    end

Vamos lá e cola isso num buffer e carrega o butão Run. Carrega-o uma série de vezes. Ouve a cacofonia de vários amen break looping fora de tempo entre eles. Ok, podes carregar o Stop agora.

Este é o comportamento que vemos sempre - se carregares o botão Run, as camadas de som sobrepõem-se às do som existente. Assim se tiveres um loop e carregares o botão Run 3 vezes, terás 3 camadas de loops a correr simultaneamente.

No entanto, com threads com nome é diferente:

    in_thread(name: :amen) do
      loop do
        sample :loop_amen
        sleep sample_duration :loop_amen
      end
    end

Experimenta carregar o botão Run 3 vezes com este código. Apenas irás ouvir um amen break loop. Verás também isto no registro:

    ==> Skipping thread creation: thread with name :amen already exists.

Sonic Pi diz que um thread com o nome `:amen`já está a tocar, e assim não irá criar outro.

Este comportamento pode não ser imediatamente útil para ti por enquanto - mas será muito quando começarmos com o live code…

# 5.5 - Funções

Quando começares a escrever muito código, podes querer encontrar uma maneira de organizar e estruturar as coisas que forma elegante e de fácil compreensão. Funções são maneiras muito poderosas de conseguir isso. Elas dão-nos a habilidade de dar nome a uma serie de código. Vamos dar uma olhada.

## Definindo funções

    define :foo do
      play 50
      sleep 1
      play 55
      sleep 2
    end

Aqui definimos uma nova função chamada `foo`. Fazemos isso com o nosso amigo bloco do/end e a palavra magica `define` seguida pelo nome que queremos dar à nossa função. Não temos que a chamar `foo`, podemos chamar-lhe o que quisermos como `bar`, `baz` ou idealmente algo com sentido para ti como `secção_principal`ou `lead_riff`.

Lembra-te de acrescentar dois pontos `:` ao nome da tua função quando a definires.

## Chamando funções

Depois de definirmos a nossa função podemos a chamar escrevendo o seu nome:

    define :foo do
      play 50
      sleep 1
      play 55
      sleep 0.5
    end
    foo
    sleep 1
    2.times do
      foo
    end

Até podemos usar `foo` dentro de um bloco de iteração ou em qualquer lado que tenhamos escrito `play` ou `sample`. Isto dá-nos uma excelente maneira de nos expressar e cria palavras significativas para usar nas nossas composições.

## As funções são recordadas ao longo das execuções

Até agora, cada vez que carregas no botão Run, o Sonic Pi começa completamente do zero. Ele não sabe nada excepto o que está no buffer. Não podes referir código noutro buffer ou noutra thread. No entanto as funções mudam isso. Quando defines a função, o Sonic Pi lembra-se dela. Vamos experimentar. Apaga todo o código na teu buffer e substitui por:

    foo

Carrega no botão Run - ouve a tua função a tocar. Onde foi o código? Como é que o Sonic Pi sabe o que tocar? O Sonic Pi lembra-se da tua função - assim mesmo que apagues do buffer, ele lembra-se do que escreveste. Este comportamento apenas funciona com funções criadas usando o `define` (e `defonce`).

## Funções parametrizadas

Podes estar interessado em saber que tal como tu podes passar valores mínimos e máximos a `rrand`, tu também podes ensinar as tuas funções a aceitar argumentos. Vamos dar uma olhada:

    define :my_player do |n|
      play n
    end
    my_player 80
    sleep 0.5
    my_player 90

Isto não é muito excitante, mas ilustra o ponto. Criamos a nossa versão de `play`chamada `my_player`que é parametrizada.

Os parâmetros devem vir a seguir ao `do` do bloco `define`, rodeados pela barra vertical `|` e separados por virgulas `,`. Podes usar qualquer palavra para o nome dos parâmetros.

A magia acontece dentro do bloco `define`. Podes querer usar nomes de parâmetros como se fossem valores reais. Neste exemplo estou a tocar a nota `n`. Podes considerar que os parâmetros são uma espécie de promessa que quando o código corre serão substituídos por valores actuais. Fazes isso passando um parâmetro às função quando a chamas. Eu faço isso com `my_player 80` para tocar a nota 80. Dentro da definição da função, `n`é então substituído por 80, assim `play n`fica `play 80`. Quando a chamas novamente com `my_play 90`, o `n`é substituído por 90 e `play n`fica `play 90`.

Vamos ver um exemplo mais interessante:

    define :chord_player do |root, repeats|
      repeats.times do
        play chord(root, :minor), release: 0.3
        sleep 0.5
      end
    end
    chord_player :e3, 2
    sleep 0.5
    chord_player :a3, 3
    chord_player :g3, 4
    sleep 0.5
    chord_player :e3, 3

Onde usei `repeat` como se fosse um número na linha `repeat.times do`. Também usei `root` como se fosse o nome de uma nota na minha chamada a `play`.

Vê como podemos escrever algo muito expressivo e facil à leitura movendo muito da nossa lógica para uma função!

# 5.6 - Variáveis

Uma coisa útil a fazer no nosso código é dar nomes às coisas. Sonic Pi torna isto muito fácil: escreves o nome que queres usar, um sinal de igual (`=`), e a coisa que te queres lembrar:

    sample_name = :loop_amen

Aqui “lembramo-nos” do símbolo `:loop_amen`na variável `sample_name`. Podemos agora usar `sample_name`em todo o lado que usaríamos `:loop_amen`. Por exemplo:

    sample_name = :loop_amen
    sample sample_name

Existem 3 razões principais para usar variáveis no Sonic Pi: comunicar significado, gerir repetições e capturar o resultado de coisas.

## Comunicar sentido

Quando escreves código é fácil de pensar que estas a dizer ao computador como fazer coisas - desde que o computador perceba está Ok. No entanto é importante lembrar que não é só o computador que lê código. Outras pessoas podem o ler e tentar perceber o que se está a passar. Além disso, é provável que tenhas que ler o teu código no futuro e tentar perceber o que se passa. Apesar de poder parecer óbvio para ti agora - pode não o ser para outros ou o teu eu futuro!

Uma maneira de ajudar os outros a perceber o que o teu código está a fazer é adicionar comentários (como vimos na secção anterior). Outra coisa é usar nomes de variáveis com sentido. Vê este código:

    sleep 1.7533

Porque usa o numero `1.7533`? De onde veio este número? O que significa? Vê agora este código:

    loop_amen_duration = 1.7533
    sleep loop_amen_duration

Agora é muito mais claro o que `1.7533`significa: é a duração do sample `:loop_amen`! Claro, podes dizer porque não escrever simplesmente:

    sleep sample_duration(:loop_amen)

Que, claro, é uma boa maneira de comunicar a intenção do código.

## Gerindo a repetição

Frequentemente vês muita repetição no teu código e quando queres mudar as coisas, tens que as mudar em muitos sítios. Vê este código:

    sample :loop_amen
    sleep sample_duration(:loop_amen)
    sample :loop_amen, rate: 0.5
    sleep sample_duration(:loop_amen, rate: 0.5)
    sample :loop_amen
    sleep sample_duration(:loop_amen)

Estamos a fazer muitas coisas com o `:loop_amen`! E se queremos ouvir como soa com outro loop sample como o `:loop_garzul`? Teremos de encontrar e substituir todos os `:loop_amen`s por `:loop_garzul`. Isso pode ser Ok se tiveres muito tempo - mas se tiveres a actuar em palco? As vezes não temos o luxo de tempo - especialmente se queres manter as pessoas a dançar.

E se escreveres código como este:

    sample_name = :loop_amen
    sample sample_name
    sleep sample_duration(sample_name)
    sample sample_name, rate: 0.5
    sleep sample_duration(sample_name, rate: 0.5)
    sample sample_name
    sleep sample_duration(sample_name)

Isto faz exactamente o mesmo que o anterior (experimenta). Também nos dá a habilidade de apenas mudar uma linha `sample_name = :loop_amen` para `sample_name = :loop_garzul`e mudamos em muitos sítios pela magia das variáveis.

## Capturando resultados

Finalmente, uma boa motivação para usar variáveis é para capturar o resultados de coisas, podes querer fazer coisas com a duração do sample:

    sd = sample_duration(:loop_amen)

Agora podemos usar `sd` em qualquer lugar que necessitemos da duração do sample `:loop_amen`.

Talvez mais importante, a variável permite nos capturar o resultado da chamada a `play`ou a `sample`:

    s = play 50, release: 8

Agora capturamos e lembramos-nos de `s` como variável, que nos permite controlar o synth enquanto corre:

    s = play 50, release: 8
    sleep 2
    control s, note: 62

Veremos como controlar os synths em mais detalhe numa secção posterior.

## Aviso: Variáveis and Threads

Embora as variáveis sejam ótimas para dar nomes às coisas e capturar os resultados das coisas, é importante saber que elas normalmente só devem ser usadas localmente num segmento. Por exemplo, não faça isso:

    a = (ring 6, 5, 4, 3, 2, 1)
    live_loop :sorted do
      a = a.sort
      sleep 0.5
      puts "sorted: ", a
    end
    live_loop :shuffled do
      a = a.shuffle
      sleep 0.5
    end

No exemplo acima, atribuímos um anel de números a uma variável ‘a’ e usamo-lo dentro de dois ciclos “live_loop” separados. No primeiro ciclo “live_loop” a cada 0.5 segundos nós ordenamos o anel (para `(anel 1, 2, 3, 4, 5, 6)`) e imprimimos no log. Se executares o código, verás que a lista impressa * nem sempre é ordenada! *. Isto pode surpreender-te - especialmente porque às vezes a lista é impressa ordenada e outras vezes não. Isto é chamado de comportamento não determinístico e é o resultado de um problema bastante desagradável chamado de condição de corrida. O problema deve-se ao fato de que o segundo ciclo “live_loop” também manipular a lista (neste caso, embaralhando-a) e no momento em que a lista é impressa, às vezes ela acaba de ser ordenada e outras vezes acaba de ser embaralhada. Ambos os ciclos “live_loop” estão concorrendo para fazer algo diferente na mesma variável e em cada vez um ciclo diferente ‘ganha’.

Existem duas soluções para isto. Primeiro, não usar as mesmas variáveis em múltiplos ciclos “live_loop” ou threads. Por exemplo, o seguinte código deverá sempre imprimir uma lista ordenada à medida que cada ciclo “live_loop” tenha as suas variáveis separadas

    live_loop :shuffled do
     a = (ring 6, 5, 4, 3, 2, 1)
     a = a.shuffle
    sleep 0.5
    end
    live_loop :sorted do
    a = (ring 6, 5, 4, 3, 2, 1)
    a = a.sort
    sleep 0.5
    puts "sorted: ", a
    end

No entanto, ás vezes queremos partilhar coisas entre threads. Por exemplo, a tecla atual, as BPM, sintetizador, etc. Nestes casos, a solução é o utilizar as funções `get` e`set` que fazem parte do sistema seguro do Sonic PI para partilha entre threads.

# 5.7 - Sincronização de Threads

Quando te tornares suficientemente avançado em live coding com uma serie de funções e threads simultaneamente, irás notar que é bastante fácil fazer em erro num dos threads e o matar. Isso não é muito importante porque o podes reiniciar carregando no Run. No entanto, quando reinicias o thread ele está fora de tempo com os threads originais.

## Herança de tempo

Como discutimos anteriormente, novos threads criados com `in_thread` herdam todas as definições do thread pai. Isto inclui o tempo corrente. Isto significa que os threads estarão sempre sincronizados uns com os outros quando começarem simultaneamente.

No entanto, quando começas um thread por si só, o seu tempo é improvável estar sincronizado com qualquer dos outros threads em execução.

## Fila e sincronização

O Sonic Pi oferece uma solução para este problema com as funções `cue`e `sync`.

`cue`permite-nos enviar uma mensagem de “batimento cardiaco” para todos os outros threads. Por padrão os outro threads não estão interessados na mensagem. No entanto, podes registar interesse com a função `sync`.

A coisa importante a saber é que `sync` é similar a `sleep`na medida que pára o thread corrente de fazer alguma coisa por um período de tempo. No entanto, com `sleep`especificas o tempo de espera enquanto com `sync`não sabes quanto tempo tens de esperar - uma vez que `sync`espera pelo próximo `cue`de outro thread que pode ser logo ou após um longo tempo.

Vamos explorar isto em mais detalhe:

    in_thread do
      loop do
        cue :tick
        sleep 1
      end
    end
    in_thread do
      loop do
        sync :tick
        sample :drum_heavy_kick
      end
    end

Aqui temos 2 threads - um actuando como um metronomo, não tocando nenhum som mas enviando a mensagem de batimento`:tick` a cada beat. O segundo thread está sincronizado na mensagem `tick` e quando recebe um herda o tempo do thread do `cue` e continua a correr.

Como resultado, ouviremos o sample `:drum_heavy_kick` exactamente quando o outro thread envia a mensagem `:tick`, mesmo que o dois threads não começaram o seu tempo de execução ao mesmo tempo:

    in_thread do
      loop do
        cue :tick
        sleep 1
      end
    end
    sleep(0.3)
    in_thread do
      loop do
        sync :tick
        sample :drum_heavy_kick
      end
    end

A chamada maldosa `sleep`tipicamente faria o segundo thread fora de fase com o primeiro. No entanto, como estamos a usar `cue` e `sync`, automaticamente sincronizamos os threads evitando qualquer offset de tempo acidental.

## Nomes de Cues

És livre de usar qualquer nome que queiras para as tuas mensagens de `cue`- não apenas `:tick` . Só tens que assegurar que tal como os outros threads estão `sync`ronizados no nome correcto - ou então ficarão à espera para sempre (ou até carregares no botão Stop).

Vamos jogar com alguns nomes de `cues`:

    in_thread do
      loop do
        cue [:foo, :bar, :baz].choose
        sleep 0.5
      end
    end
    in_thread do
      loop do
        sync :foo
        sample :elec_beep
      end
    end
    in_thread do
      loop do
        sync :bar
        sample :elec_flip
      end
    end
    in_thread do
      loop do
        sync :baz
        sample :elec_blup
      end
    end

Aqui temos um `cue` loop principal que está aleatoriamente a enviar um batimento chamado `:foo`,`:bar` ou `:baz`. Temos também 3 loop threads sincronizando a cada um desses nomes independentemente e tocando um sample diferente. O efeito total é que ouvimos um som cada 0.5 batida porque cada `sync`thread é aleatoriamente sincronizado com a thread `cue` e toca o seu sample.

Isto claro que também funciona se inverteres a ordem dos threads pois eles os threads `sync` simplesmente esperam pela próxima `cue`.

# 6 - Estudio de efeitos

Um dos mais gratificantes e divertidos aspectos do Sonic Pi é a habilidade de facilmente adicionar efeitos de estúdio aos nossos sons. Por exemplo, podes querer adicionar algum reverb a partes das tua peça, ou algum eco ou até distorção ou vibração à tua linha de baixo.

Sonic Pi fornece uma maneira simples mas poderosa de adicionar efeitos. Até permite o encadeamento deles (para que possas passar os teus sons pela distorção, depois echo e depois reverb) e além disso controlar individualmente cada unidade de efeito com opts (numa maneira similar a dar parâmetros a synths e samples). Podes até modificar as opts dos efeitos com ele a correr. Assim por exemplo, podes aumentar o reverb do teu baixo ao longo da faixa…

## Pedais de guitarra

Se tudo isto soa complicado, não te preocupes. Uma vez que brinques um pouco com isto, tudo se tornará claro. Até lá uma simples analogia é a de pedais de efeitos de guitarra. Existem muitos tipos diferentes de pedais de efeitos que podes comprar. Alguns adicionam reverb, outros distorcem, etc. Um guitarrista liga a guitarra um um pedal, p. ex. distorção -, depois com outro cabo conecta (encadeia) a um pedal de reverb. A saída do pedal de reverb pode então ser ligada ao amplificador:

    Guitar -> Distortion -> Reverb -> Amplifier

Isto é chamado encadeamento de efeitos. O Sonic Pi suporta exactamente isto. Adicionalmente, cada pedal tem dials e sliders que te permitem controlar a quantidade de distorção e reverb, eco, etc. a aplicar. Sonic Pi também suporta este tipo de controlo. Finalmente imagina um guitarrista a tocar enquanto alguém controla os efeitos enquanto toca. O sonic Pi também suporta isto - mas em vez de necessitares alguém para controlar as coisas por ti, usamos o computador.

Vamos explorar os efeitos!

# 6.1 - Adicionando efeitos

Nesta secção iremos ver um par de efeitos: rever e eco. Veremos como os usar, como controlar as suas opts e como os podemos encadear.

O sistema de efeitos do Sonic Pi usa blocos. Se ainda não leste a secção 5.1 podes dar uma pequena mirada e depois regressar.

## Reverb

Se queremos usar reverb escrevemos `with_fx :reverb` como o código especial do nosso bloco desta forma:

    with_fx :reverb do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end

Agora toca este código e ouviras a tocar com reverb. Soa bem, não soa! Tudo soa bem com reverb.

Agora vamos ver o que acontece se tivermos código fora do bloco do/end:

    with_fx :reverb do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end
    sleep 1
    play 55

Repara que a nota final `play 55`não é tocada com reverb. Isto é porque está fora do bloco do/end, não a ser capturada pelo efeito reverb.

Similarmente, se fizeres sons antes do bloco do/end, também não serão capturados:

    play 55
    sleep 1
    with_fx :reverb do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end
    sleep 1
    play 55

## Eco

Existem muitos efeitos para escolher. Que tal algum eco?

    with_fx :echo do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end

Um dos aspectos poderosos dos blocos de efeitos do Sonic Pi é que podem ser passadas opts similares às opts que já vimos com `play` e `sample`. Por exemplo uma opt divertida de se brincar é a `phase:` que representa a duração de um determinado eco em beats. Vamos tornar o eco mais lento:

    with_fx :echo, phase: 0.5 do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end

Vamos também ver o eco mais rápido:

    with_fx :echo, phase: 0.125 do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end

Vamos tornar o eco mais longo até desaparecer colocando o tempo de `decay:`para 8 beats:

    with_fx :echo, phase: 0.5, decay: 8 do
      play 50
      sleep 0.5
      sample :elec_plip
      sleep 0.5
      play 62
    end

## Aninhando efeitos

Um dos mais poderosos aspectos dos blocos de efeitos é que podem ser aninhados. Isto permite facilmente encadear efeitos. Por exemplo, se quisermos tocar algum código com eco e a seguido de reverb? Fácil, basta colocar um dentro de outro:

    with_fx :reverb do
      with_fx :echo, phase: 0.5, decay: 8 do
        play 50
        sleep 0.5
        sample :elec_blup
        sleep 0.5
        play 62
      end
    end

Pensa no audio fluindo de dentro para fora. O som do código dentro no bloco do/end interior como o `play 50` é primeiro enviado para o efeito de eco e o som do efeito de eco é então enviado para o efeito de reverb.

Podemos usar aninhamentos muito profundos para resultados estranhos. No entanto, um aviso, os efeitos podem usar muitos recursos, e quando os aninhas efectivamente estas a usar múltiplos efeitos simultaneamente. Limita o uso de efeitos especialmente em plataformas com pouco poder como o Raspberry Pi.

## Descobrindo efeitos

O Sonic Pi vem com um grande número de feitos para brincares com eles. Para descobrires quais estão disponíveis, clica no botão FX no lado esquerdo deste sistema de ajuda e verás uma listagem das opções disponíveis. Aqui vai uma lista dos meus favoritos:

- Ondular,
- reverb,
- eco,
- distorção,
- fatiador

Agora fica maluco e adiciona efeitos em todo lado para incríveis novos sons!

# 6.2 - Efeitos na pratica

Apesar de parecerem relativamente simples exteriormente, os efeitos são uma besta realmente complexa internamente. A sua simplicidade faz com que as pessoas os usem demasiado nas suas peças. Isto pode não ter importância se tiverem uma maquina poderosa mas se - tal como eu - usares uma Rasperry Pi para tocar, terás de ter atenção à quantidade de trabalho que pedes para fazer de forma a garantir que a batida continue a correr.

Considera este código:

    loop do
      with_fx :reverb do
        play 60, release: 0.1
        sleep 0.125
      end
    end

Neste código estamos a tocar a nota 60 com um muito pequeno tempo de release, é uma nota curta. Também queremos reverb assim embrulhamos num bloco de reverb. Até aqui tudo bem. Excepto…

Vamos ver o que este código faz. Primeiro temos um `loop` que significa que tudo dentro dele é repetido para sempre. A seguir temos um bloco `with_fx`. Isto significa que criamos um efeito de reverb cada vez que repetimos. Isto é como ter um pedal de reverb para cada vez que tocamos na corda da guitarra. É muito cool que se possa fazer isso, mas não é sempre o que quer fazer. Por exemplo, este código terá dificuldade em correr bem no Raspberry Pi. Todo o trabalho de criar o reverb e depois esperar até que tenha que ser parado e removido é tratado por `with_fx` por ti, mas isso requer poder de CPU que pode ser precioso.

Como o tornamos mais similar ao setup tradicional em que o guitarrista tem apenas um pedal de reverb e todo o som passa por ele? Simples:

    with_fx :reverb do
      loop do
        play 60, release: 0.1
        sleep 0.125
      end
    end

Colocamos o nosso loop dentro do bloco `with_fx`. Desta forma apenas criamos um simples reverb para todas as notas do nosso loop. Este código é muito mais eficiente e executa bem num Raspberry Pi.

Um compromisso é usar `with_fx`numa iteração dentro do loop:

    loop do
      with_fx :reverb do
        16.times do
          play 60, release: 0.1
          sleep 0.125
        end
      end
    end

Desta forma tiramos o `with_fx`fora da parte interior do `loop`e criamos um novo reverb a cada 16 notas.

Este é um padrão muitos comum que o `with_fx` suporta uma opção que faz exactamente isto mas sem ter de escrever o bloco `16.times`.

    loop do
      with_fx :reverb, reps: 16 do
        play 60, release: 0.1
        sleep 0.125
      end
    end

Tanto o exemplo `reps: 16` como o `16.times do` irão se comportar de forma idêntica. O `resp: 16` essencialmente repete o código no bloco `do/end` 16 vezes assim podes usar um ou outro conforme preferires.

Lembra-te não existem erros, apenas possibilidades. No entanto, algumas destas abordagens terão diferentes sons e características de performance diferentes. Brinca com isso e usa a abordagem que soa melhor para ti trabalhando na performance dentro dos constrangimentos da tua plataforma.

# 7 - Controlando sons que correm

Até agora vimos como podemos despoletar synths e samples, a como podemos mudar as suas opções padrão como a amplitude, panorâmica, envelope e entre outras. Cada som despoletado é essencialmente o seu próprio som com a sua lista de opções durante a sua duração.

Não seria porreiro se pudessemos mudar as opções de som quando ele esta a ser tocado, tal como dobramos a corda de uma guitarra enquanto ela ainda esta a vibrar?

Estás com sorte - esta secção mostra-te como podes fazer exactamente isso.

# 7.1 - Controlando Synths em execução

Até agora apenas nos preocupamos em despoletar novos sons e efeitos. No entanto, o Sonic Pi dá-nos a habilidade de manipular e controlar sons em execução. Fazemos isso usando uma variável para capturar a referencia a um synth:

    s = play 60, release: 5

Aqui temos uma variável de execução local `s` que representa o synth a tocar a nota 60. Nota que é run-local - não poderás aceder a ela a partir de outras corridas como as funções.

Depois de termos `s`, podemos começar a controlar-la via a função `control`:

    s = play 60, release: 5
    sleep 0.5
    control s, note: 65
    sleep 0.5
    control s, note: 67
    sleep 3
    control s, note: 72

A coisa a reparar é que não estamos a despoletar 4 synths diferentes - estamos apenas a despoletar um synth e posteriormente mudamos o pitch 3 vezes, enquanto é tocado.

Podemos passar qualquer das opções padrão ao `control`, assim podes controlar coisas como `amp:`, `cutoff:` ou `pan:`.

## Opções não controláveis

Algumas das opções não podem ser controladas depois do synth ter começado. Este é o caso para todos os parâmetros dos envelopes ADSR. Podes descobrir que opções podem ser controlados vendo a documentação no sistema de ajuda. Se na documentação diz Can not be changed once set, saberás que não é possível controlar as opções depois do synth ter sido iniciado.

# 7.2 - Controlando os efeitos

É também possível controlar os efeitos, apesar de isto ser feito de uma maneira ligeiramente diferente:

    with_fx :reverb do |r|
      play 50
      sleep 0.5
      control r, mix: 0.7
      play 55
      sleep 1
      control r, mix: 0.9
      sleep 1
      play 62
    end

Em vez de usar uma variável, usamos um parâmetro de meta do bloco do/end. Dentro das barras `|`, necessitamos especificar um nome único para o nosso efeito em execução no qual então fazemos referencia no respectivo bloco do/end. Este comportamento é idêntico ao uso de funções parametrizadas.

Vai agora e controla alguns synths e efeitos!

# 7.3 - Opções deslizantes

Enquanto exploravas as opções dos synth e efeitos, poderás ter reparado que existe um número de opções terminando com `_slide`. Podes até ter tentado as chamar e não veres nenhum efeito. Isto é porque eles não são parâmetros normais, eles são opções especiais que apenas funcionam quando controlares synths como introduzido na secção anterior.

Considera o exemplo seguinte:

    s = play 60, release: 5
    sleep 0.5
    control s, note: 65
    sleep 0.5
    control s, note: 67
    sleep 3
    control s, note: 72

Aqui, podes ouvir o pitch do synth mudar imediatamente a cada chamada a `control`. No entanto, podemos querer que o pitch deslize entre as mudanças. Ao controlarmos o parâmetro `note:`, para adicionar o deslizamento, necessitamos de definir o parâmetros `note_slide` no synth:

    s = play 60, release: 5, note_slide: 1
    sleep 0.5
    control s, note: 65
    sleep 0.5
    control s, note: 67
    sleep 3
    control s, note: 72

Agora podemos ouvir as notas a serem dobradas entre as chamadas a `control`. Soa bem ,não soa? Podes acelerar o deslizamento usando um tempo mais curto como `note_slide: 0.2` ou abrandar usando um tempo mais longo.

Cada parâmetro pode ser controlado como um parâmetro `_slide` correspondente para tu brincares com ele.

## Deslizamento é permanente

Uma vez definido um parâmetro `_slide` num synth em execução, ele será lembrado e usado cada vez que deslizes o parâmetro correspondente. Para parar o deslizamento, terás que definir o valor de `_slide` a 0 antes da próxima chamada a `control`.

## Deslizando opções de efeitos

É também possível deslizar opções de efeitos:

    with_fx :wobble, phase: 1, phase_slide: 5 do |e|
      use_synth :dsaw
      play 50, release: 5
      control e, phase: 0.025
    end

Agora diverte-te deslizando coisas para suavizar transições e controlo do fluxo…

# 8 - Estruturas de dados

Uma ferramenta muito útil na caixa de ferramentas de um programador é uma estrutura de dados.

As vezes podes querer representar e usar mais do que uma coisa. Por exemplo, pode ser útil teres uma serie de notas a tocar umas a seguir as outras. Linguagens de programação têm estruturas de dados que te permitem fazer exactamente isso.

Existem muitas estruturas de dados excitantes e exóticas disponíveis para os programadores - as pessoas estão sempre a inventar novas. No entanto, por enquanto precisamos apenas de considerar uma muito simples - a lista.

Vamos ver em mais detalhe. Descrevemos a forma básica e depois como as listas podem ser usadas para representar escalas e acordes.

# 8.1 - Listas

Nesta secção vamos dar uma vista de olhos à estrutura de dados que é bastante útil - a lista. Já encontramos anteriormente na secção de aleatoriedade quando escolhíamos de uma lista de notas a tocar:

    play choose([50, 55, 62])

Nesta secção iremos explorar o uso de listas para representar acordes e escalas. Primeiro vamos recapitular em como poderemos querer tocar um acorde. Lembra-te que se não usarmos o `sleep`, o som acontece todo ao mesmo tempo:

    play 52
    play 55
    play 59

Vamos ver outras maneiras de representar este código.

## Tocando uma lista

Uma das opções é colocar todas as notas numa lista: `[52, 55, 59]`. O nosso amigável `play` é suficientemente esperto para saber como tocar uma lista de notas. Tenta:

    play [52, 55, 59]

Ooh, já é bastante melhor de se ler. Tocar uma lista de notas não te impede de usar qualquer outro parâmetro normalmente:

    play [52, 55, 59], amp: 0.3

Claro, que poderás usar o nome tradicional das notas em vez do seu número MIDI:

    play [:E3, :G3, :B3]

Aqueles sortudos que estudaram teoria musical poderão reconhecer o acorde como Mi Menor tocado na terceira oitava.

## Acedendo à lista

Uma outra característica bastante útil numa lista é a habilidade de receber informação dela. Isto pode soar estranho, mas não é mais complicado do que alguém pedir para abrir o livro na pagina 23. Com uma lista, dizes, qual é o elemento do índice 23? A única coisa estranha é que os índices na programação geralmente começam do 0 e não do 1.

Com os índices das listas não contamos 1, 2, 3… Em vez disso contamos 0, 1, 2…

Vamos ver isto em mais detalhe. Vê esta lista:

    [52, 55, 59]

Não existe nada assustador sobre isto. Agora, qual é o segundo elemento da lista? Sim , claro que é o `55`. É fácil. Vamos ver se o computador dá a mesma resposta que nós:

    puts [52, 55, 59][1]

Ok, isto é um pouco esquisito se não tinhas visto algo assim anteriormente. Acredita em mim, não é difícil. Existe 3 partes na linha acima: a palavra `puts`, a nossa lista `52, 55, 59` e o nosso índice`[1]`. Primeiro estamos a dizer `puts` porque queremos que o Sonic Pi imprima a resposta no registo. Segundo, estamos a dar a nossa lista e finalmente o índice está a perguntar pelo segundo elemento. Necessitamos de rodear o nosso índice com parênteses rectos e como a contagem começa do `0`, o índice do segundo elemento é `1`. Olha:

    # indexes:  0   1   2
               [52, 55, 59]

Tenta correr o código `puts [52, 55, 59][1]`e verás `55` aparecer no registo. Muda o indice `1`para outros índices, tenta listas maiores e pensa em como podes usar uma lista na próxima sessão de jam. Por exemplo, que estruturas musicais podem ser representadas por uma serie de números…

# 8.2 - Acordes

O Sonic Pi tem suporte incluído para nomes de acordes que devolverão listas. Tenta por ti próprio:

    play chord(:E3, :minor)

Agora estamos a chegar a algum lado. Isso parece mais bonito que as listas em bruto (e são mais fáceis de ler para outras pessoas). Assim que outros acordes o Sonic Pi suporta? Bem, muitos. Tenta alguns destes:

- `chord(:E3, :m7)`
- `chord(:E3, :minor)`
- `chord(:E3, :dim7)`
- `chord(:E3, :dom7)`

## Arpejos

Podemos facilmente transformar acordes em arpejos com a função `play_pattern`:

    play_pattern chord(:E3, :m7)

Ok, isto não é tão divertido - tocou muito devagar. `play_pattern` irá tocar cada nota na lista separada com uma chamada a `sleep 1` entre cada chamada a `play`. Podemos usar outra função `play_pattern_timed` para especificar o nosso próprio tempo e acelerar as coisas:

    play_pattern_timed chord(:E3, :m7), 0.25

Podemos até passar uma lista de tempos que ira ser tratada como um circulo de tempos:

    play_pattern_timed chord(:E3, :m13), [0.25, 0.5]

Isto é equivalente a:

    play 52, sustain: 0.25
    sleep 0.25
    play 55, sustain: 0.5
    sleep 0.5
    play 59, sustain: 0.25
    sleep 0.25
    play 62, sustain: 0.5
    sleep 0.5
    play 66, sustain: 0.25
    sleep 0.25
    play 69, sustain: 0.5
    sleep 0.5
    play 73, sustain: 0.25
    sleep 0.25

Qual preveres escrever?

Note that `play_pattern` and `play_pattern_timed` alter the sustain of the notes to fill the times. You can remove this behavior by setting the `sustain:` opt to `0`:

    play_pattern_timed chord(:E3, :m13), [0.25, 0.5]

# 8.3 - Escalas

O Sonic Pi suporta uma grande quantidade de escalas. Que tal tocar uma escala de Dó maior na 3 oitava?

    play_pattern_timed scale(:c3, :major), 0.125, release: 0.1

Podemos até pedir mais oitavas:

    play_pattern_timed scale(:c3, :major, num_octaves: 3), 0.125, release: 0.1

Que tal todas as notas de uma escala pentatónica?

    play_pattern_timed scale(:c3, :major_pentatonic, num_octaves: 3), 0.125, release: 0.1

## Notas aleatórias

Acordes e escalas são óptimas maneiras de constranger as escolhas aleatórias em algo significativo. Brinca com este exemplo que escolhe notas aleatórias do acorde Mi3 menor:

    use_synth :tb303
    loop do
      play choose(chord(:E3, :minor)), release: 0.3, cutoff: rrand(60, 120)
      sleep 0.25
    end

Tenta diferentes acordes e distancias de corte.

## Descobrindo acordes e escalas

Para saber que escalas e acordes são suportados pelo Sonic Pi simplesmente clica no botão Lang na esquerda estrema a este tutorial e escolhe acorde ou escala na lista de API. Na informação do painel principal, no final verás uma longa lista de acordes e escalas (dependendo de qual estiveres a ver).

Diverte-te e lembra-te, não existem erros, apenas oportunidades.

# 8.4 - Anéis

Um variação interessante às listas padrão são os anéis. Se sabes alguma programação, poderás conhecer buffers em anel ou arrays em anel. Aqui chamam-se apenas anéis - é curto e simples.

Na secção anterior sobre listas vimos que podíamos obter elementos dela usando o mecanismo de indexação:

    puts [52, 55, 59][1]

O que acontece se queremos o índice `100`? Bem, claramente que não existe elemento no índice 100 porque a lista só tem 3 elementos. Assim o Sonic Pi devolve `nil` que significa nada.

No entanto, considera que temos um contador tal como a batida corrente que aumenta continuamente. Vamos criar o nosso contador e a nossa lista:

    counter = 0
    notes = [52, 55, 59]

Podemos usar o nosso contador para aceder a nota na nossa lista:

    puts notes[counter]

Boa, obtemos `52`. Agora, vamos aumentar o nosso contador e obter outra nota:

    counter = (inc counter)
    puts notes[counter]

Fantástico, agora obtemos `55`e se o fizéssemos outra vez obteria-mos `59`. No entanto, se o fizéssemos outra vez, ficaríamos sem números na nossa lista e obteríamos `nil`. E se quiséssemos regressar ao inicio da lista novamente? É para isto que os anéis servem.

## Criando anéis

Podemos criar anéis de duas maneiras. Ou usamos a função `ring` com os elementos do anel como parâmetros:

    (ring 52, 55, 59)

Ou podemos usar uma lista normal e converter num anel enviando a mensagem `.ring`:

    [52, 55, 59].ring

## Indexando anéis

Depois de termos um anel, podemos usar exactamente da mesma maneira que usaríamos uma lista normal com a excepção que podemos usar índices que são negativos ou maiores que o tamanho do anel e eles enrolam de forma a apontar sempre para um elemento do anel:

    (ring 52, 55, 59)[0] #=> 52
    (ring 52, 55, 59)[1] #=> 55
    (ring 52, 55, 59)[2] #=> 59
    (ring 52, 55, 59)[3] #=> 52
    (ring 52, 55, 59)[-1] #=> 59

## Usando anéis

Imagina que estamos a usar uma variável que representa o número corrente do beat. Podemos usar isto como índice no nosso anel para buscar notas a tocar, ou tempos de release ou qualquer coisa útil que podemos armazenar no nosso anel independentemente do número de beat que estamos correntemente.

## Escalas e acordes são anéis

Uma coisa útil é que as listas devolvidas por `scale` e `chord` são também anéis e permitem que os acedas com índices arbitrários.

## Construtores de anéis

Além de `ring` existem algumas outras funções que constroem um anel por nós.

- `range` convida-te a especificar um ponto de inicio, um ponto final e um tamanho de passo.
- `bools` permite usar `1`s e `0`s para sucintamente representar booleans.
- `knit`permite-te tricotar uma sequência de valores repetidos.
- `spread` cria um anel de bools com uma distribuição Euclidiana.

Dá uma vista de olhos na documentação respectiva para mais informação.

# 8.5 - Cadeia de anéis

Para além de construtores como `range` e `spread` outra maneira de criar novos anéis é manipular anéis existentes.

## Cadeia de comandos

Para explorar isto, vê este anel simples:

    (ring 10, 20, 30, 40, 50)

E se o quisermos ao contrario? Usamos a cadeia de comando `.reverse` para pegar no anel e o rodar:

    (ring 10, 20, 30, 40, 50).reverse  #=> (ring 50, 40, 30, 20, 10)

Agora, e se quisermos os 3 primeiros valores do anel?

    (ring 10, 20, 30, 40, 50).take(3)  #=> (ring 10, 20, 30)

Finalmente, e se quisermos baralhar o anel?

    (ring 10, 20, 30, 40, 50).shuffle  #=> (ring 40, 30, 10, 50, 20)

## Múltiplas cadeias

Isto já é uma maneira poderosa de criar novos anéis. No entanto, o poder real vem quando encadeias alguns destes comando em conjunto.

Que tal baralhar o anel, largar o 1 elemento e obter os 3 posteriores?

Vamos fazer isso por etapas:

1. `(ring 10, 20, 30, 40, 50)` - o nosso anel inicial
2. `(ring 10, 20, 30, 40, 50).shuffle` - baralhar - `(ring 40, 30, 10, 50, 20)`
3. `(ring 10, 20, 30, 40, 50).shuffle.drop(1)` - retira 1 - `(ring 30, 10, 50, 20)`
4. `(ring 10, 20, 30, 40, 50).shuffle.drop(1).take(3)` - obtem 3 - `(ring 30, 10, 50)`

Como podes ver acabamos de criar uma cadeia longa destes métodos adicionando-os em conjunto. Podemos combinar estes em qualquer ordem criando uma maneira extremamente rica e poderosa de gerar novos anéis a partir de existentes.

## Imutabilidade

Estes anéis têm uma poderosa e importante propriedade. Eles são imutáveis o que significa que não podem mudar. o que quer dizer que encadeando estes métodos descritos nesta secção não mudam os anéis apenas criam novos anéis. Isto significa que estas livre de partilhar anéis entre threads e começar a encadear-los dentro de um thread sabendo que não irá afectar outros threads que estejam a usar o mesmo anel.

## Cadeias de métodos disponíveis

Aqui está uma lista de cadeia de métodos disponíveis para brincares:

- `.reverse` - devolve uma versão invertida do anel
- `.sort`- cria uma versão ordenada do anel
- `.shuffle` - cria uma versão baralhada do anel
- `.pick(3)` - devolve um anel com o resultado de chamar `.choose` 3 vezes
- `.pick(3)` - devolve um anel com o resultado de chamar `.choose` 3 vezes
- `.take(5)`- devolve um novo anel contendo apenas os primeiros 5 elementos
- `drop(3)`- devolve um novo anel com tudo excepto os 3 primeiros elementos
- `butlast` - devolve um novo anel sem o ultimo elemento do anel original
- `.drop_last(3)` - devolve um novo anel com os 3 últimos elementos originais em falta
- `take_last(6)` - devolve um novo anel com apenas os últimos 6 elementos originais
- `.stretch(2)` - repete 2 vezes cada elemento do anel original
- `.repeat(3)` - repete todo o anel original 3 vezes
- `.mirror` - adiciona ao anel original uma versão revertida dele próprio
- `.reflect`- o mesmo que mirror mas não duplica o valor do meio do anel
- `.scale(2)` - devolve um novo anel com todos os elementos multiplicados por 2 (assumindo que o anel apenas contem números)

Claro que estes métodos em cadeia podem receber também outros números. És livre de chamar `.drop(5)` em vez de `.drop(3)`se quiseres largar os primeiros 5 elementos.

# 9 - Live Coding

Um dos aspectos mais excitantes do Sonic Pi é que te permite escrever e modificar código ao vivo para criar musica, como uma performance ao vivo com uma guitarra. Uma vantagem desta abordagem é dar-te mais feedback enquanto compões (pôr um loop a correr enquanto ajustas o som até a perfeição). No entanto, a principal vantagem é que podes levar o Sonic Pi em palco e tocar com ele.

Nesta secção cobrimos os fundamentos de tornar as tuas composições de código estático em performances dinâmicas.

Agarrarem-se às cadeiras…

# 9.1 - Live Coding

Agora aprendemos o suficiente para começar a ter alguma diversão. Nesta secção iremos buscar de todas as outras secções e mostrar em como podes começar a fazer composições musicais ao vivo tornando-as numa performance. Necessitamos 3 ingredientes principais para isso:

- A habilidade de escrever código que gera som - CHECK!
- Uma habilidade de escrever funções - CHECK!
- A habilidade de usar threads (nomeados) - CHECK!

Muito bem, vamos começar. Vamos codificar os nossos primeiros sons. Primeiro necessitamos de uma função contendo o código que queremos tocar. Vamos começar simples. Também queremos num loop chamar essa função num thread:

    define :my_loop do
      play 50
      sleep 1
    end
    in_thread(name: :looper) do
      loop do
        my_loop
      end
    end

Se isto te parece muito complicado para ti, volta a trás e relê a secção sobre funções e threads. Não é muito complicado se já dominares estas coisas.

O que temos aqui é uma definição de função que apenas toca a nota 50 e descansa por um beat. Depois definimos um thread chamado `:looper` que em loop chama `my_loop`repetidamente.

Se correres este código, ouvirás a nota 50 repetidamente uma e outra vez…

## Fazendo alterações

Agora é quando o divertimento começa. Enquanto o código está a correr muda o 50 para outro número, talvez 55, depois prime o botão Run outra vez. WOW! Mudou! Em directo!

Não adicionou uma nova camada porque estamos a usar um thread com nome que apenas permite um thread para cada nome. Também o som mudou porque redefinimos a função. Demos a `:my_loop`uma nova definição. Quando o thread `:looper` repetiu simplesmente chamou a nova definição.

Experimenta mudar novamente, muda a nota, muda o tempo de descanso. Que tal adicionar uma definição `use_synth`? Por exemplo muda para:

    define :my_loop do
      use_synth :tb303
      play 50, release: 0.3
      sleep 0.25
    end

Agora soa bastante interessante, mas podemos apimentar as coisas. Em vez de tocar a mesma nota uma e outra vez, tenta tocar um acorde:

    define :my_loop do
      use_synth :tb303
      play chord(:e3, :minor), release: 0.3
      sleep 0.5
    end

Que tal tocar notas ao acaso do acorde:

    define :my_loop do
      use_synth :tb303
      play choose(chord(:e3, :minor)), release: 0.3
      sleep 0.25
    end

Ou usar um valor de cutoff aleatório:

    define :my_loop do
      use_synth :tb303
      play choose(chord(:e3, :minor)), release: 0.2, cutoff: rrand(60, 130)
      sleep 0.25
    end

Finalmente, adiciona alguma bateria:

    define :my_loop do
      use_synth :tb303
      sample :drum_bass_hard, rate: rrand(0.5, 2)
      play choose(chord(:e3, :minor)), release: 0.2, cutoff: rrand(60, 130)
      sleep 0.25
    end

Agora as coisas estão a ficar excitantes!

No entanto, antes de saltares e começares a codificar ao vivo com funções e threads, pára o que estas a fazer e lê a próxima secção sobre `live_loop` que irá mudar a forma como escreves código no Sonic Pi para sempre…

# 9.2 - Live Loops

Ok, esta secção do tutorial é uma verdadeira gema. Se apenas leres uma secção, deveria ser esta. Se leste as secções anteriores sobre os fundamentos de codificar ao vivo, `live_loop` é uma simples maneira de fazer isso mas sem ter que escrever muito código.

Se não leste a secção anterior, `live_loop`é a melhor maneira de improvisar com o Sonic Pi.

Vamos tocar. Escreve o seguinte num buffer novo:

    live_loop :foo do
      play 60
      sleep 1
    end

Agora prime o botão Run. Ouviras o beep básico. Nada de especial por aqui. No entanto, não primas Stop ainda. Muda o `60` para `65` e clica no Run outra vez.

WOW! Mudou automaticamente sem perder a batida. Isto é Live coding.

Porque não mudar para algo mais parecido com baixo? Actualiza o teu código enquanto corre:

    live_loop :foo do
      use_synth :prophet
      play :e1, release: 8
      sleep 8
    end

Depois prime Run.

Vamos fazer mudanças ao cutoff:

    live_loop :foo do
      use_synth :prophet
      play :e1, release: 8, cutoff: rrand(70, 130)
      sleep 8
    end

Prime o botão Run outra vez.

Adiciona bateria:

    live_loop :foo do
      sample :loop_garzul
      use_synth :prophet
      play :e1, release: 8, cutoff: rrand(70, 130)
      sleep 8
    end

Muda a nota de `e1` para `c1`:

    live_loop :foo do
      sample :loop_garzul
      use_synth :prophet
      play :c1, release: 8, cutoff: rrand(70, 130)
      sleep 8
    end

Agora pára de me ouvir tocar e brinca tu próprio! Diverte-te!

# 9.3 - Múltiplos Live Loops

Considera o seguinte live loop:

    live_loop :foo do
      play 50
      sleep 1
    end

Podes ter-te perguntado porque necessita o nome `:foo`. O seu nome é importante porque significa que este live loop é diferente de todos os outros live loops.

Nunca pode haver 2 live loops a correr com o mesmo nome.

Isso quer dizer que se quisermos múltiplos live loops concorrentes, teremos que dar diferentes nomes:

    live_loop :foo do
      use_synth :prophet
      play :c1, release: 8, cutoff: rrand(70, 130)
      sleep 8
    end
    live_loop :bar do
      sample :bd_haus
      sleep 0.5
    end

Podemos agora actualizar e mudar cada live loop independentemente e tudo funciona.

## Sincronizando live loops

Uma coisa que poderás já ter notado é que os live loops funcionam automaticamente com o mecanismo de cue do threaad que exploramos anteriormente. Cada vez que o live loop repete, ele gera um novo envento `cue` com o nome do live loop. Podemos então `sync` nestes cues para assegurar que os nossos loops estão sincronizados sem ter que parar alguma coisa.

Considera este código muito mal sincronizado:

    live_loop :foo do
      play :e4, release: 0.5
      sleep 0.4
    end
    live_loop :bar do
      sample :bd_haus
      sleep 1
    end

Vamos ver se conseguimos reparar o timing e a sincronização sem parar. Primeiro, vamos arranjar o loop `:foo` para fazer parar pelo factor de 1 - algo como `0.5` serve:

    live_loop :foo do
      play :e4, release: 0.5
      sleep 0.5
    end
    live_loop :bar do
      sample :bd_haus
      sleep 1
    end

Ainda não terminamos - notarás que os beats não se alinham correctamente. ISto é porque os loops estão fora de fase. Vamos resolver isso sincronizando um com o outro:

    live_loop :foo do
      play :e4, release: 0.5
      sleep 0.5
    end
    live_loop :bar do
      sync :foo
      sample :bd_haus
      sleep 1
    end

Wow, agora tudo está perfeitamente a tempo - tudo sem ter que parar.

Agora avança e codifica ao vivo com live loops!

# 9.4 - Ticking

Algo que darás por ti a fazer muitas vezes quando codificas ao vivo é looping por anéis. Irás colocar notas em anéis para melodias, pausas para ritmos, progressões de acordes, variações tímbricas, etc, etc.

## Anéis tiquetantes

O Sonic Pi fornece uma ferramenta muito útil para trabalhar com anéis dentro de `live_loop`s. É chamado o sistema de tick. Na secção sobre anéis falamos algo sobre o contador que está constantemente a aumentar, como o número da batida corrente. Ticks apenas implementam a ideia. Fornece-te a habilidade de tiquetaquear pelo anel. Vamos ver este exemplo:

    counter = 0
    live_loop :arp do
      play (scale :e3, :minor_pentatonic)[counter], release: 0.1
      counter += 1
      sleep 0.125
    end

Isso é equivalente a:

    live_loop :arp do
      play (scale :e3, :minor_pentatonic).tick, release: 0.1
      sleep 0.125
    end

Aqui, estamos a buscar a escala pentatónica de Mi3 menor e tiquetaquear por cada elemento. Isto é feito adicionando `.tick` ao fim da declaração da escala. Este tick é local ao live loop, assim cada live loop pode ter o seu próprio tick independente:

    live_loop :arp do
      play (scale :e3, :minor_pentatonic).tick, release: 0.1
      sleep 0.125
    end
    live_loop :arp2 do
      use_synth :dsaw
      play (scale :e2, :minor_pentatonic, num_octaves: 3).tick, release: 0.25
      sleep 0.25
    end

## Tick

Podes também chamar `tick`como função padrão e usar o valor como índice:

    live_loop :arp do
      idx = tick
      play (scale :e3, :minor_pentatonic)[idx], release: 0.1
      sleep 0.125
    end

No entanto, é muito melhor chamar `.tick` no final. A função `tick` é para quando queres fazer algo coisas mais bonitas com o valor de tick e para quando queres usar ticks com outras coisas que indexar em anéis.

## Olha

A coisa mágica sobre tick é que não só devolve um novo índice (ou o valor do anel nesse índice) mas também garante que a próxima vez que chamares o tick, é um novo valor. Vê os exemplos na documentação para `tick` para as muitas maneiras que podes trabalhar com ele. No entanto, por agora, é importante apontar que algumas vezes apenas queres ver o valor corrente de tick e não aumentar. Isso é conseguido através da função `look`. Podes chamar `look` como função padrão ou adicionando `.look` ao final do anel.

## Nomeando ticks

Finalmente, algumas vezes necessitas de mais do que um tick por live loop. Isto é conseguindo dando nome a um tick:

    live_loop :arp do
      play (scale :e3, :minor_pentatonic).tick(:foo), release: 0.1
      sleep (ring 0.125, 0.25).tick(:bar)
    end

Aqui estamos a usar dois ticks, um para tocar as notas e outro para o tempo de pausa. Como ambos estão no mesmo live loop, para os manter separados necessitamos de lhes dar nomes únicos. Isto é exactamente a mesma coisa que nomear `live_loop`s - apenas passamos o símbolo com o prefixo `:`. No exemplo acima chamamos um dos ticks `:foo` e o outro `:bar`. Se quisermos os `look` temos que passar o nome do tick a `look`.

## Não o faças muito complicado

A maioria do poder do sistema de tick não é útil quando começas. Não tentes aprender tudo nesta secção. Foca-te no tiquetaque de um único anel. Isso dará a maioria da alegria da simplicidade do tiquetaque de anéis nos teus `live_loop`s.

Dá uma vista de olhos na documentação sobre `tick` onde existe muitos exemplos úteis e tem um feliz tiquetaquear!

# 10 - Time State

Frequentemente é útil ter informação partilhada entre varias threads ou live loops. Por exemplo, podes querer partilhar a noção da tecla actual, BPM ou até conceitos abstractos como a ‘complexidade’ actual ( que pode ser interpretada de forma diferente em threads diferentes). Também não queremos a garantia de determinismo existente ao fazermos isto. Ou seja, queremos partilhar código com outros e saber exatamente o que eles vão ouvir ao executa-lo. No final da secção 5.6 deste tutorial nós discutimos brevemente porque é que não devemos utilizar variáveis para partilhar informação entre threads devido à possível perca de determinismo (por sua vez devido à condição de corrida).

A solução do Sonic Pi ao problema de lidar com variáveis globais de forma determinística é através de um sistema novo chamado de Time State. Isto pode parecer complexo e difícil (de facto, no Reino Unido, programar com várias threads e memoria partilhada é normalmente um assunto abordado na universidade) No entanto, como poderás ver, tal como tocar a primeira nota, o Sonic Pi torna incrivelmente fácil a partilha de estado entre múltiplas threads enquanto mantém os teus programas thread safe e deterministicos.

Conhece o `get` e o `set`…

# 10.1 - Set e Get

O Sonic Pi tem um armazenamento global chamado de Time State. As duas coisas principais que fazes com ele é armazenar (`set`) informação e ler ( `get` ) informação. Vamos aprofundar…

## Set

Para armazenar informação no Time State são necessárias duas coisas:

1. a informação que queremos armazenar,
2. uma chave (nome único) para a informação.

Por exemplo, nós podemos querer armazenar o numero `3000` com a chave `:intensity`. Isto é possível utilizando a função `set` :

    set :intensity, 3000

Podemos usar qualquer nome para a nossa chave. Se alguma informação já foi armazenada anteriormente com a mesma chave, o nosso novo `set` vai substitui-la:

    set :intensity, 1000
    set :intensity, 3000

No exemplo em cima, nós guardamos ambos os números utilizando a mesma chave, a ultima chamada `set` ganha , por isso o numero associado a `:intensity` vai ser `3000` já que a primeira chamada ao `set` é efetivamente substituída.

## Get

Para tirar informação do Time State só precisamos de utilizar a chave que utilizamos para armazena-la (`set`) , que no nosso caso e `:intensity`. Só precisamos então de chamar `get[:intensity]`que podemos ver ao imprimirmos o resultado para o log:

    print get[:intensity] #=> prints 3000

Notice that calls to `get` can return information that was `set` in a previous run. Once a piece of information has been `set` it is available until either the information is overridden (just like we clobbered the `:intensity` value of `1000` to `3000` above) or Sonic Pi is closed.

## Várias Threads

The main benefit of the Time State system is that it can be safely used across threads or live loops. For example, you could have one live loop setting information and another one getting it:

    live_loop :setter do
      set :foo, rrand(70, 130)
      sleep 1
    end
    live_loop :getter do
      puts get[:foo]
      sleep 0.5
    end

The nice thing about using `get` and `set` across threads like this is that it will always produce the same result every time you hit run. Go on, try it. See if you get the following in your log:

    {run: 0, time: 0.0}
     └─ 125.72265625
    {run: 0, time: 0.5}
     └─ 125.72265625
    {run: 0, time: 1.0}
     └─ 76.26220703125
    {run: 0, time: 1.5}
     └─ 76.26220703125
    {run: 0, time: 2.0}
     └─ 114.93408203125
    {run: 0, time: 2.5}
     └─ 114.93408203125
    {run: 0, time: 3.0}
     └─ 75.6048583984375
    {run: 0, time: 3.5}
     └─ 75.6048583984375

Try running it a few times - see, it’s the same every time. This is what we call deterministic behaviour and it’s really very important when we want to share our music as code and know that the person playing the code is hearing exactly what we wanted them to hear (just like playing an MP3 or internet stream sounds the same for all listeners).

## A Simple Deterministic State System

Atrás na secção 5.6 discutimos a razão pela qual utilizar variáveis através de diferentes threads pode levar a comportamento aleatório. Isto faz-nos desconfiar de código como este:

    ## Um exemplo de comportamento não-determinístico
    ## (devido a race conditions causadas por múltiplos
    ## loops manipulando a mesma variárvel ao mesmo tempo).
    ##
    ## Se você executar este código você notará
    ## que a lista que é impressa
    ## nem sempre sai ordenada!
    a = (ring 6, 5, 4, 3, 2, 1)
    live_loop :shuffled do
      a = a.shuffle
      sleep 0.5
    end
    live_loop :sorted do
      a = a.sort
      sleep 0.5
      puts "sorted: ", a
    end

Let’s take a look at how this might look using `get` and `set`:

    ## Um exemplo de comportamento determinístico
    ## (apesar do acesso simultâneo ao estado compartilhado)
    ## usando o novo sistema Time State do Sonic Pi.
    ##
    ## Quando este código é executado, a lista
    ## sempre é impressa de forma ordenada!
    set :a, (ring 6, 5, 4, 3, 2, 1)
    live_loop :shuffled do
      set :a, get[:a].shuffle
      sleep 0.5
    end
    live_loop :sorted do
      set :a, get[:a].sort
      sleep 0.5
      puts "sorted: ", get[:a]
    end

Notice how this code is pretty much identical to the version using a variable before it. However when you run the code, it behaves as you would expect with any typical Sonic Pi code - it does the same thing every time in this case thanks to the Time State system.

Therefore, when sharing information across live loops and threads, use `get` and `set` instead of variables for deterministic, reproducible behaviour.

# 10.2 - Sincronização (Sync)

A secção 5.7 introduziu as funções `cue` e `sync` para lidar com problemas de sincronização de threads. O que não foi explicado é que é o sistema de Time State que fornece esta funcionalidade. É de tal forma que `set` é uma variação de `cue`e foi construído de forma que possa trabalhar perfeitamente com o Time State - qualquer informação que nós planeamos armazenar no Time State nós podemos sincronizar. Em outras palavras - nós sincronizamos `sync`eventos que ainda serão inseridos no Time State.

## Aguardando por eventos

Vamos dar uma olhada em como usar `sync` para esperar por novos eventos que serão inseridos ao Time State:

    in_thread do
      sync :foo
      sample :ambi_lunar_land
    end
    sleep 2
    set :foo, 1

Neste exemplo nós primeiro criamos uma thread que espera um evento `:foo` ser adicionado ao Time State. Após a declaração desta thread, nós esperamos por 2 batidas e então setamos (`set`) `:foo` para ser `1`. Isso libera a sincronização (`sync`) que então segue para a próxima linha que dispara a amostra `:ambi_lunar_land`.

Note que `sync` sempre espera por eventos futuros e isso irá bloquear a a thread atual esperando por um novo evento. Também, irá herdar o tempo lógico da thread que chamou a sincronização através de `set` ou `cue` então pode também ser usado para sincronizar tempo.

## Passando valores para o Futuro

No exemplo acima nós configuramos `:foo` igual a `1` e não fizemos nada com isso. Nós podemos, na verdade, recuperar este valor na thread chamando `sync`:

    in_thread do
      amp = sync :foo
      sample :ambi_lunar_land, amp: amp
    end
    sleep 2
    set :foo, 0.5

Note que valores que são passados através de `set` e `cue` devem ser seguros - i.e. Rings imutáveis, números, símbolos ou cadeias congeladas. O Sonic Pi irá gerar um erro se o valor que tenta armazenar no Time State não for válido.

# 10.3 - Correspondência de Padrões

Para passar e recuperar informações para o Time State, é possível usar chaves mais complexas que símbolos básicos como `:foo` e `:bar`. Também pode usar cadeias no formato URL, chamadas de Paths (caminhos) como `"/foo/bar/baz"`. Depois que começãmos a usar paths, nós podemos começar a aproveitar o sofisticado sistema de correspondência de Padrões do Sonic Pi para usar `get` e `sync` com paths ‘similares’ em vez de ‘idênticos’. Vamos dar uma olhada.

## Correspondência com qualquer parte do caminho (path)

Vamos assumir que nós queiramos esperar pelo próximo evento que tem três segmentos no path:

    sync "/*/*/*"

Isto irá corresponder a qualquer evento Time State com exatamente três segmento, independente de seus nomes. Por exemplo:

- `cue "/foo/bar/baz"`
- `cue "/foo/baz/quux"`
- `cue "/eggs/beans/toast"`
- `cue "/moog/synths/rule"`

Entretanto, não irá corresponder a paths com menos ou mais segmentos. Os seguintes paths não serão localizados:

- `cue "/foo/bar"`
- `cue "/foo/baz/quux/quaax"`
- `cue "/eggs"`

Cada `*` (asterisco) significa qualquer conteúdo. Então nós podemos encontrar paths com somente um segmento com `/*` ou paths com cinco segmentos com `/*/*/*/*/*`

## Encontrando segmentos parciais

Se soubermos como o segmento irá começar ou terminar, nós podemos usar um asterisco `*` junto com o nome parcial do segmento. Por exemplo: `"/foo/b*/baz"` irá corresponder a qualquer path com três segmentos, onde o primeiro é `foo`, o último é `baz` e o segmento do meio pode ser qualquer coisa que comece com `b`. Então irá corresponder a:

- `cue "/foo/bar/baz"`
- `cue "/foo/baz/baz"`
- `cue "/foo/beans/baz"`

Mas não irá corresponder a:

- `cue "/foo/flibble/baz"`
- `cue "/foo/abaz/baz"`
- `cue "/foo/beans/baz/eggs"`

Você pode colocar o `*` no início do segmento para especificar os últimos caracteres de um segmento: `"/foo/*zz/baz"` que iráo corresponder a quaisquer 3 segmentos `cue` ou `set` onde o primeiro segmento for `foo`, o último for `baz` e o segmento do meio termine com `zz`, como `"cue "/foo/whizz/baz"`.

## Encontrando correspondências em segmentos de paths aninhados

As vezes você não sabe quantos segmentos do path você quer achar a correspondência. Nestes casos, você pode usar os poderosos duplos asteriscos: `**` como em `"/foo/**/baz"` que irão corresponder a:

- `cue "/foo/bar/baz"`
- `cue "/foo/bar/beans/baz"`
- `cue "/foo/baz"`
- `cue "/foo/a/b/c/d/e/f/baz"`

## Correspondendo a Letras Sozinhas

Você pode usar o caracter `?` para comparar com um caracter apenas, como em `"/?oo/bar/baz"` que irá corresponder a:

- `cue "/foo/bar/baz"`
- `cue "/goo/bar/baz"`
- `cue "/too/bar/baz"`
- `cue "/woo/bar/baz"`

## Correspondendo a Múltiplas Palavras

Se você sabe que um segmento pode ser uma palavra de um certo conjunto de palavras, você pode usar `{` e `}` para especificar uma lista de opções como em `"/foo/{bar,beans,eggs}/quux"` que irão corresponder aos seguintes padrões:

- `cue "/foo/bar/quux"`
- `cue "/foo/beans/quux"`
- `cue "/foo/eggs/quux"`

## Correspondendo a Múltiplas Letras

Por fim, você pode comparar com uma seleção de letras se você usar `[` e `]` para especificar uma lista de possibilidades como em `"/foo/[abc]ux/baz"` que irá corresponder somente a:

- `cue "/foo/aux/baz"`
- `cue "/foo/bux/baz"`
- `cue "/foo/cux/baz"`

Você também pode utilizar o caracter `-` para especificar sequências de letras. Por exemplo`"/foo/[a-e]ux/baz"` que irá corresponder somente a:

- `cue "/foo/aux/baz"`
- `cue "/foo/bux/baz"`
- `cue "/foo/cux/baz"`
- `cue "/foo/dux/baz"`
- `cue "/foo/eux/baz"`

## Combinando Correspondências

Ao chamar `sync` ou `get` você está livre para combinar localizadores de correspondência em qualquer ordem que você achar necessário para encontrar qualquer evento Time State criado por `cue` ou `set`. Vamos ver um exemplo doido:

    in_thread do
      sync "/?oo/[a-z]*/**/ba*/{quux,quaax}/"
      sample :loop_amen
    end
    sleep 1
    cue "/foo/beans/a/b/c/d/e/bark/quux/"

## Correspondência de Padrões OSC

Para os curiosos, estas regras de correspondência são baseados na especificação de correspondência de padrões do Open Sound Control (controle de som aberto), que é explicado com detalhes em: http://opensoundcontrol.org/spec-1_0

# 11 - MIDI

Uma vez que você tiver dominado a conversão de código em música, você pode pensar - o que vem depois? As vezes, as limitações de trabalhar puramente dentro da sintaxe e do sistema de som do Sonic Pi podem ser excitantes e te colocar em uma nova posição criativa. Entretanto, as vezes é essencial libertar o código para o mundo real. Não queremos duas coisas extras:

1. Sermos capazes de converter ações do mundo real em eventos codificáveis do Sonic Pi
2. Sermos capazes de usar o forte modelo de temporização e semântica do Sonic Pi para controlar e manipular objetos no mundo real

Por sorte, existe um protocolo que está por aí desde os anos 80, que permite este tipo de interação - MIDI. Existe um número incrível de aparelhos externos, incluindo teclados, controladores, sequenciadores e software profissional que suportam MIDI. Nós podemos usar o MIDI para receber dados e também para enviar dados.

O Sonic Pi fornece suporte completo para o protocolo MIDI possibilitando que você conecte seu Código Ao Vivo com o mundo real. Vamos explorá-lo um pouco mais…

# 11.1 - Entrada MIDI

Nesta secção vamos aprender como conectar um controlador MIDI para enviar eventos para o Sonic Pi, para controlar nossos sintetizadores e sons. Vá e pegue um controlador MIDI, como um teclado ou tablet de controle e vamos começar!

## Conectando um controlador MIDI

Para receber no Sonic Pi informações de um aparelho MIDI externo, primeiro nós precisamos conectá-lo ao computador. Tipicamente isso é feito através de uma conexão USB, apesar de que aparelhos antigos usam um conector DIN de 5 pinos, para o qual será necessário suporte de hardware em seu computador (por exemplo: algumas placas de áudio possuem conectores DIN). Uma vez que você tenha conectado seu aparelho, abra o Sonic Pi e dê uma olhada na seção IO (Entrada/Saída) do painel de Preferências. Você poderá ver seu aparelho listado lá. Caso não veja, tente o botão ‘Reiniciar MIDI’ e veja se aparece. Se ainda assim você não encontrar nada, a próxima coisa a tentar é consultar as configurações MIDI do seu sistema operacional para ver se ele enxerga seu aparelho. Se tudo isso falhar, sinta-se a vontade para perguntar na sala de chat: http://gitter.im/samaaron/sonic-pi

## Recebendo eventos MIDI

Assim que o seu aparelho esteja conectado, o Sonic Pi irá receber eventos automaticamente. Você mesmo pode confirmar a manipular o seu aparelho MIDI e olhando no registro de Deixas (cue logger), na janela da app em baixo à direita, abaixo do registo (se isso não estiver visível, vá em Preferências > Editor > Mostrar & Ocultar e ative a caixa ‘Mostrar o registo de deixas’). Verá um fluxo de eventos como:

    /midi/nanokey2_keyboard/0/1/note_off  [55, 64]
    /midi/nanokey2_keyboard/0/1/note_on   [53, 102]
    /midi/nanokey2_keyboard/0/1/note_off  [57, 64]
    /midi/nanokey2_keyboard/0/1/note_off  [53, 64]
    /midi/nanokey2_keyboard/0/1/note_on   [57, 87]
    /midi/nanokey2_keyboard/0/1/note_on   [55, 81]
    /midi/nanokey2_keyboard/0/1/note_on   [53, 96]
    /midi/nanokey2_keyboard/0/1/note_off  [55, 64]

Quando você ver um fluxo de mensagens desta forma, você terá conectado com sucesso seu aparelho MIDI. Parabéns, vamos ver o que você consegue fazer com ele!

## MIDI Time State

MIDI

## Controlando o Código

Agora que você conectou seu aparelho MIDI, viu seus eventos no registro e descobriu que nosso conhecimento do Estado de Tempo (Time State) é tudo o que precisamos para trabalhar com eventos, podemos começar a nos divertir. Vamos construir um piano MIDI simples:

    live_loop :midi_piano do
      note, velocity = sync "/midi/nanokey2_keyboard/0/1/note_on"
      synth :piano, note: note
    end

Temos algumas coisas acontecendo no código acima, incluindo alguns problemas. Primeiro, temos um `live_loop` simples, que irá se repetir para sempre, executando o código entre os blocos `do`/`end`. Isto foi apresentado na secção 9.2. Segundo, estamos a chamar o comando `sync` para esperar pelo próximo evento Time State correspondente. Usamos uma cadeia que representa a mensagem MIDI que estamos a procurar (que é a mesma que foi exibida no registo). Note que esta cadeia longa é fornecida pela função autocompletar do Sonic Pi, desta forma não precisa digitar tudo a mão. No registo nós vemos que haviam dois valores para cada nota MIDI no evento, então nós atribuímos o resultado a duas variáveis `note` e `velocity`. Por fim, disparamos o sintetizador `:piano` passando a nossa nota.

Agora tente você. Digite o código acima, substitua a chave de sincronização com uma cadeia correspondente ao seu aparelho MIDI e clique em Executar. Pronto, tem um piano funcionando! Entretanto, provavelmente notará alguns problemas: primeiro, todas as notas possuem o mesmo volume, independente da força que usa no teclado. Isso pode ser consertado facilmente usando o valor velocity do MIDI e convertendo-o para amplitude. Dado que MIDI possui uma variação entre 0 e 127, para converter este número para um valor entre 0 e 1 nós só precisamos dividi-lo por 127:

    live_loop :midi_piano do
      note, velocity = sync "/midi/nanokey2_keyboard/0/1/note_on"
      synth :piano, note: note, amp: velocity / 127.0
    end

Atualize o código e clique em Executar novamente. Agora a força aplicada ao teclado é respeitada. Em seguida, vamos nos livrar desta pausa irritante.

## Removendo a Latência

Antes de remover a pausa, nós precisamos entender porque ela acontece. Para manter todos os sintetizadores e Efeitos sincronizados através de uma variedade de CPUs com capacidades diferentes, o Sonic Pi agenda o áudio antecipadamente em 0.5s por padrão. (Note que esta latência adicional pode ser configurada pelas funções `set_sched_ahead_time!` e `use_sched_ahead_time`). Estes 0.5s de latência estão a ser adicionados ao disparador do nosso sintetizador `:piano` assim como está a ser adicionado a todos os sintetizadores disparados pelo Sonic Pi. Tipicamente nós realmente queremos manter esta latência, já que isso significa que todos os sintetizadores estarão sincronizados. Entretanto, isso só faz sentindo para sintetizadores disparados por código, usando `play` e `sleep`. No nosso caso, na realidade estamos a disparar o sintetizador `:piano` pelo nosso aparelho MIDI e portanto não queremos que o Sonic Pi controle o tempo por nós. Podemos desligar esta latência com o comando `use_real_time`, que desabilita a latência para a thread atual. Isto significa que pode usar o modo Real Time para loops ao vivo controlado por `sync` com aparelhos externos, e manter a latência padrâo para todos os outros loops. Vejamos:

    live_loop :midi_piano do
      use_real_time
      note, velocity = sync "/midi/nanokey2_keyboard/0/1/note_on"
      synth :piano, note: note, amp: velocity / 127.0
    end

Atualize seu código para que ele corresponda ao código acima e clique em ‘Executar’ novamente. Agora nós temos um piano com baixa latência e sensibilidade variável, programado em apenas 5 linhas.

## Recuperando valores

Finalmente, como nossos eventos MIDI estão indo diretamente para o Time State, nós também podemos usar a função `get` para recuperar o último valor recebido. Isso não bloqueia a thread atual e retorna `nil` se não houver valor para ser recuperado (o que você pode sobrescrever passando um valor padrão - veja a ajuda para `get`). Lembre-se que você pode chamar `get` em qualquer thread a qualquer momento para ver o valor mais recente correspondente ao Time State. Você pode até usar `time_warp` para voltar no tempo e chamar `get` para ver eventos passados…

## Agora Você Está no Controle

O mais importante é que agora você pode usar as mesmas estruturas de código para sincronizar e recuperar (`sync` e `get`) informações MIDI de qualquer aparelho MIDI e fazer o que você quiser com os valores. Você pode agora escolher o que seu aparelho MIDI irá fazer!

# 11.2 - Saída MIDI

Além de receber eventos MIDI nõs podemos também enviar eventos MIDI para disparar e controlar hardware de sintetizadores externos, teclados e outros aparelho. O Sonic Pi fornece um conjunto completo de funções para enviar várias mensagens MIDI como:

1. Ligar nota - `midi_note_on`
2. Desligar nota - `midi_note_off`
3. Mudança de controle - `midi_cc`
4. Pitch bend - `midi_pitch_bend`
5. Tiques do relógio - `midi_clock_tick`

Também existem muitas outras mensagens MIDI suportadas - verifique a documentação da API para todas as outras funções que começam com `midi_`.

## Conectando um aparelho MIDI

In order to send a MIDI message to an external device, we must first have connected it. Check out the subsection ‘Connecting a MIDI Controller’ in section 11.1 for further details. Note that if you’re using USB, connecting to a device which you’re sending to (rather than receiving from) is the same procedure. However, if you’re using the classic DIN connectors, make sure you connect to the MIDI out port of your computer. You should see your MIDI device listed in the preferences pane.

## Enviando eventos MIDI

The many `midi_*` fns work just like `play`, `sample` and `synth` in that they send a message at the current (logical) time. For example, to spread out calls to the `midi_*` fns you need to use `sleep` just like you did with `play`. Let’s take a look:

    midi_note_on :e3, 50

This will send a MIDI note on event to the connected MIDI device with velocity 50. (Note that Sonic Pi will automatically convert notes in the form `:e3` to their corresponding MIDI number such as 52 in this case.)

If your connected MIDI device is a synthesiser, you should be able to hear it playing a note. To disable it use `midi_note_off`:

    midi_note_off :e3

## Selecionando um aparelho MIDI

By default, Sonic Pi will send each MIDI message to all connected devices on all MIDI channels. This is to make it easy to work with a single connected device without having to configure anything. However, sometimes a MIDI device will treat MIDI channels in a special way (perhaps each note has a separate channel) and also you may wish to connect more than one MIDI device at the same time. In more complicated setups, you may wish to be more selective about which MIDI device receives which message(s) and on which channel.

We can specify which device to send to using the `port:` opt, using the device name as displayed in the preferences:

    midi_note_on :e3, port: "moog_minitaur"

We can also specify which channel to send to using the `channel:` opt (using a value in the range 1-16):

    midi_note_on :e3, channel: 3

Of course we can also specify both at the same time to send to a specific device on a specific channel:

    midi_note_on :e3, port: "moog_minitaur", channel: 5

## MIDI Studio

Finally, a really fun thing to do is to connect the audio output of your MIDI synthesiser to one of the audio inputs of your soundcard. You can then control your synth with code using the `midi_*` fns and also manipulate the audio using `live_audio` and FX:

    reverb,

(The fn `midi` is available as a handy shortcut to sending both note on and note off events with a single command. Check out its documentation for further information).

# 12 - OSC

In addition to MIDI, another way to get information in and out of Sonic Pi is via the network using a simple protocol called OSC - Open Sound Control. This will let you send messages to and from external programs (both running on your computer and on external computers) which opens up the potential for control way beyond MIDI which has limitations due to its 1980s design.

For example, you could write a program in another programming language which sends and receives OSC (there are OSC libraries for pretty much every common language) and work directly with Sonic Pi. What you can use this for is only limited by your imagination.

# 12.1 - Receber OSC

MIDI

## A Basic OSC Listener

Let’s build a basic OSC listener:

    foo

In this example we described an OSC path `"/osc*/trigger/prophet"` which we’re syncing on. This can be any valid OSC path (all letters and numbers are supported and the `/` is used like in a URL to break up the path to multiple words). The `/osc` prefix is added by Sonic Pi to all incoming OSC messages, so we need to send an OSC message with the path `/trigger/prophet` for our `sync` to stop blocking and the prophet synth to be triggered.

## Sending OSC to Sonic Pi

We can send OSC to Sonic Pi from any programming language that has an OSC library. For example, if we’re sending OSC from Python we might do something like this:

    from pythonosc import osc_message_builder
    from pythonosc import udp_client
    sender = udp_client.SimpleUDPClient('127.0.0.1', 4560)
    sender.send_message('/trigger/prophet', [70, 100, 8])

Or, if we’re sending OSC from Clojure we might do something like this from the REPL:

    (use 'overtone.core)
    (def c (osc-client "127.0.0.1" 4560))
    (osc-send c "/trigger/prophet" 70 100 8)

## Receiving from External Machines

For security reasons, by default Sonic Pi does not let remote machines send it OSC messages. However, you can enable support for remote machines in Preferences->IO->Networked OSC->Allow OSC from other computers. Once you’ve enabled this, you can receive OSC messages from any computer on your network. Typically the sending machine will need to know your IP address (a unique identifier for your computer on your network - kind of like a phone number or an email address). You can discover the IP address of your computer by looking at the IO section of the preferences pane. (If your machine happens to have more than one IP address, hovering the mouse over the listed address will pop up with a list of all known addresses).

Note, some programs such as TouchOSC for iPhone and Android support sending OSC as a standard feature. So, once you’re listening to remote machines and know your IP address you can instantly start sending messages from apps like TouchOSC which enable you to build your own custom touch controls with sliders, buttons, dials etc. This can provide you with an enormous range of input options.

# 12.2 - Sending OSC

In addition to receiving OSC and working with it using Time State, we can also send out OSC messages in time with our music (just like we can send out MIDI messages in time with our music). We just need to know which IP address and port we’re sending to. Let’s give it a try:

    use_osc "localhost", 4560
    osc "/hello/world"

If you run the code above, you’ll notice that Sonic Pi is sending itself an OSC message! This is because we set the IP address to the current machine and the port to the default OSC in port. This is essentially the same as posting a letter to yourself - the OSC packet is created, leaves Sonic Pi, gets to the network stack of the operating system which then routes the packet back to Sonic Pi and then it’s received as a standard OSC message and is visible in the cue logger as the incoming message `/osc:127.0.0.1:4560/hello/world`. (Notice how Sonic Pi automatically prefixes all incoming OSC messages with `/osc` and then the hostname and port of the sender.)

## Sending OSC to other programs

Of course, sending OSC messages to ourselves may be fun but it’s not that useful. The real benefit starts when we send messages to other programs:

    use_osc "localhost", 123456
    osc "/hello/world"

In this case we’re assuming there’s another program on the same machine listening to port 123456. If there is, then it will receive a `"/hello/world` OSC message with which it can do what it wants.

If our program is running on another machine, we need to know its IP address which we use instead of `"localhost"`:

    use_osc "192.168.10.23", 123456
    osc "/hello/world"

Now we can send OSC messages to any device reachable to us via our local networks and even the internet!

# 13 - Multichannel Audio

So far, in terms of sound production, we’ve explored triggering synths and recorded sounds via the fns `play`, `synth` and `sample`. These have then generated audio which has played through our stereo speaker system. However, many computers also have the ability to input sound, perhaps through a microphone, in addition to the ability to send sound out to more than two speakers. Often, this capability is made possible through the use of an external sound card - these are available for all platforms. In this section of the tutorial we’ll take a look at how we can take advantage of these external sound cards and effortlessly work with multiple channels of audio in and out of Sonic Pi.

# 13.1 - Sound In

One simple (and perhaps familiar) way of accessing sound inputs is using our friend `synth` by specifying the `:sound_in` synth:

    synth :sound_in

This will operate just like any synth such as `synth :dsaw` with the exception that the audio generated will be read directly from the first input of your system’s sound card. On laptops, this is typically the built-in microphone, but if you have an external sound card, you can plug any audio input to the first input.

## Duração

One thing you might notice is that just like `synth :dsaw` the `:sound_in` synth only lasts for 1 beat as it has a standard envelope. If you’d like to keep it open for a little longer, change the ADSR envelope settings. For example the following will keep the synth open for 8 beats before closing the connection:

    synth :sound_in, sustain: 8

## Adicionando efeitos

Of course, just like any normal synth, you can easily layer on effects with the FX block:

    with_fx :reverb do
      with_fx :distortion do
        synth :sound_in, sustain: 8
      end
    end

If you have plugged in a guitar to your first input, you should be able to hear it with distortion and reverb until the synth terminates as expected.

You are free to use the `:sound_in` synth as many times as you like concurrently (just like you would do with any normal synth). For example, the following will play two `:sound_in` synths at the same time - one through distortion and one through reverb:

    with_fx :distortion do
      synth :sound_in, sustain: 8
    end
    with_fx :reverb do
      synth :sound_in, sustain: 8
    end

## Múltiplas cadeias

You can select which audio input you want to play with the `input:` opt. You can also specify a stereo input (two consecutive inputs) using the `:sound_in_stereo` synth. For example, if you have a sound card with at least three inputs, you can treat the first two as a stereo stream and add distortion and the third as a mono stream and add reverb with the following code:

    with_fx :distortion do
      synth :sound_in_stereo, sustain: 8, input: 1
    end
    with_fx :reverb do
      synth :sound_in, sustain: 8, input: 3
    end

## Potential Issues

However, although this is a useful technique, there are a couple of limitations to this approach. Firstly, it only works for a specific duration (due to it having an ADSR envelope) and secondly, there’s no way to switch the FX around once the synth has been triggered. Both of these things are typical requests when working with external audio feeds such as microphones, guitars and external synthesisers. We’ll therefore take a look at Sonic Pi’s solution to the problem of manipulating a (potentially) infinite stream of live audio input: `live_audio`.

# 13.2 - Live Coding

The `:sound_in` synth as described in the previous section provides a very flexible and familiar method for working with input audio. However, as also discussed it has a few issues when working with a single input of audio as a single instrument (such as a voice or guitar). By far the best approach to working with a single continuous stream of audio is to use `live_audio`.

## A Named Audio Input

`live_audio` shares a couple of core design constraints with `live_loop` (hence the similar name). Firstly it must have a unique name and secondly only one `live_audio` stream with that name may exist at any one time. Let’s take a look:

    live_audio :foo

This code will act in a similar fashion to `synth :sound_in` with some key differences: it runs forever (until you explicitly stop it) and you can move it to new FX contexts dynamically.

## Working with FX

On initial triggering `live_audio` works exactly as you might expect it to work with FX. For example, to start a live audio stream with added reverb simply use a `:reverb` FX block:

    with_fx :reverb do
      live_audio :foo
    end

However, given that `live_audio` runs forever (at least until you stop it) it would be pretty limiting if, like typical synths, the live audio was bound within the `:reverb` FX for its entire existence. Luckily this is not the case and it was designed to be easy to move between different FX. Let’s try it. Run the code above to hear live audio coming directly from the first input of your sound card. Note, if you’re using a laptop, this will typically be out of your built-in microphone, so it’s recommended to use headphones to stop feedback.

reverb,

    with_fx :echo do
      live_audio :foo
    end

Now, hit Run, and you’ll immediately hear the audio played through the echo FX and no longer through reverb. If you wanted them both, just edit the code again and hit Run:

    with_fx :reverb do
      with_fx :echo do
        live_audio :foo
      end
    end

foo

## Stopping live audio

Unlike standard synths, as `live_audio` has no envelope, it will continue running forever (even if you delete the code, just like a function is still defined in memory if you delete the code in the editor). To stop it, you need to use the `:stop` arg:

    foo

It can easily be restarted by calling it without the `:stop` arg again:

    live_audio :foo

Additionally all running live audio synths are stopped when you hit the global Stop button (as with all other running synths and FX).

## Stereo input

With respect to audio channels, by default `live_audio` acts similarly to the `:sound_in` synth in that it takes a single mono input stream of audio and converts it to a stereo stream using the specified panning. However, just like `:sound_in_stereo` it’s also possible to tell `live_audio` to read two consecutive audio inputs and treat them as the left and right channels directly. This is achieved via the `:stereo` opt. For example, to treat input 2 as the left signal and input 3 as the right signal, you need to configure the `input:` opt to 2 and enable stereo mode as follows:

    foo

Note that once you have started a live audio stream in stereo mode, you cannot change it to mono without stopping and starting. Similarly, if you start it in the default mono mode, you can’t switch to stereo without starting and stopping the stream.

# 13.3 - Sound Out

So far in this section we’ve looked at how to get multiple streams of audio into Sonic Pi - either through the use of the `:sound_in` synth or via the powerful `live_audio` system. In addition to working with multiple streams of input audio, Sonic Pi can also output multiple streams of audio. This is achieved via the `:sound_out` FX.

## Output contexts

Let’s quickly recap on how Sonic Pi’s synths and FX output their audio to their current FX context. For example, consider the following:

    with_fx :reverb do    # C
      with_fx :echo do    # B
        sample :bd_haus   # A
      end
    end

The simplest way to understand what’s happening with the audio stream is to start at the innermost audio context and work our way out. In this case, the innermost context is labelled `A` and is the `:bd_haus` sample being triggered. The audio for this goes directly into its context which is `B` - the `:echo` FX. This then adds echo to the incoming audio and outputs it to its context which is `C` - the `:reverb` FX. This then adds reverb to the incoming audio and outputs to its context which is the top level - the left and right speakers (outputs 1 and 2 in your audio card). The audio flows outwards with a stereo signal all the way through.

## Sound Out FX

The above behaviour is true for all synths (including `live_audio`) and the majority of FX with the exception of `:sound_out`. The `:sound_out` FX does two things. Firstly it outputs its audio to its external context as described above. Secondly it also outputs its audio directly to an output on your sound card. Let’s take a look:

    with_fx :reverb do      # C
      with_fx :sound_out, output: 3 do # B
        sample :bd_haus     # A
      end
    end

In this example, our `:bd_haus` sample outputs its audio to its external context which is the `:sound_out` FX. This in turn outputs its audio to its external context the `:reverb` FX (as expected). However, it also outputs a mono mix to the 3rd output of the system’s soundcard. The audio generated within `:sound_out` therefore has two destinations - the `:reverb` FX and audio card output 3.

## Mono and Stereo out

escolhe

## Direct Out

As we have also seen, the default behaviour for `:sound_out` and `:sound_out_stereo` is to send the audio both to their external context (as is typical of all FX) and to the specified output on your soundcard. However, occasionally you may wish to only send to the output on your soundcard and not to the external context (and therefore not have any chance of the sound being mixed and sent to the standard output channels 1 and 2). This is possible by using the standard FX opt `amp:` which operates on the audio after the FX has been able to manipulate the audio:

    sample :loop_amen

In the above example, the `:loop_amen` sample is sent to its outer context, the `:sound_out` FX. This then sends a mono mix to audio card output 3 and then multiplies the audio by 0 which essentially silences it. It is this silenced signal which is then sent out to the `:sound_out`’s outer context which is the standard output. Therefore with this code, the default output channels will not receive any audio, and channel 3 will receive a mono mix of the amen drum break.

# - Conclusões

Isto conclui o tutorial introdutório do Sonic Pi. Espero que tenhas aprendido algo ao longo do caminho. Não te preocupes se sentires que não percebes tudo - apenas brinca e diverte-te e aprenderás ao teu tempo. Está a vontade de regressares se tiveres duvidas que poderão ser explicadas numa das secções.

Se tiveres alguma duvida que não foi coberta no tutorial, tenta os Sonic Pi foruns e coloca a tua questão lá. Encontrarás alguém amigável pronto a ajudar.

Finalmente, Também te convido a dares uma vista aprofundada ao resto da documentação no sistema de ajuda. Existem uma serie de coisas que não foram apresentadas neste tutorial e estão a espera que as descubras.

Brinca, diverte-te, partilha o teu código, actua para os teus amigos, mostra o ecrã e lembra-te:

Não existem erros, apenas oportunidades.

Sam Aaron

# - Artigos na MagPi

Apêndice A colecção de todos os artigo do Sonic Pi para a revista MagPi.

## Verifica os tópicos

Estes artigos não foram feitos para serem lidos numa ordem em particular e contêm muito material repetido do tutorial. Em vez de tentar e ensinar todo o Sonic Pi, eles estão focados num aspecto especifico do Sonic Pi e tentam explica-los de uma forma divertida e acessível.

## Lê a MagPi

Poderás ver o typeset glorioso e profissional na forma de PDF para descarregar a MagPi aqui: https://www.raspberrypi.org/magpi/

## Sugerir um tópico

Se não veres um tópico que tenhas curiosidade nestes artigos - porque não sugerir um? A maneira mais fácil é tweetares a tua sugestão para @Sonic_Pi. A tua sugestão poderá ser o tema do próximo artigo!

# - As cinco melhores dicas

## 1. Não existem erros

A coisa mais importante lição a aprender com o Sonic Pi é que realmente não existem erros. A melhor maneira é tentar e tentar. Tenta coisas diferentes, pára de te preocupar se o teu código soa bem ou não e começa a experimentar com diferentes synths, notas, efeitos e opções o máximo possível. Descobrirás muitas coisas que te farão rir porque soam mal e algumas pérolas que soam realmente bem. Simplesmente retira o que não gostas e fica com as que gostas. Quantos mais ‘erros’ te permitires mais rápido aprenderás e descobrirás o teu som pessoal no código.

## 2. Usa os efeitos

Digamos que já dominas o básico do Sonic Pi de fazer sons com `sample`, `play`? O que se segue? Sabias que o Sonic Pi suporta mais de 27 efeitos de estúdio para mudar o som do teu código? Efeitos são como filtros de imagens bonitos nos programas de desenho excepto que em vez de desfocar ou tornar algo a preto e branco, podes acrescentar reverb, distorção e eco ao teu som. Pensa que é como ligar o cabo de uma guitarra a um pedal de efeitos à tua escolha e depois ao amplificador. Felizmente, o Sonic Pi torna o uso de efeitos muito fácil e não requer cabos! Tudo o que tens que fazer é escolher que secção do código queres adicionar o efeito e embrulhares com o código do efeito. Vamos ver um exemplo. Imagina que tens o seguinte código:

    sample :loop_garzul
    16.times do
      sample :bd_haus
      sleep 0.5
    end

Se quiseres acrescentar um efeito ao sample `:loop_garzul`, apenas tens que o colocar dentro de um bloco `with_fx` assim:

    with_fx :flanger do
      sample :loop_garzul
    end
    16.times do
      sample :bd_haus
      sleep 0.5
    end

Agora, se quiseres adicionar um efeito à bass drum, vai e embrulha isso com o `with_fx` também:

    with_fx :flanger do
      sample :loop_garzul
    end
    with_fx :echo do
      16.times do
        sample :bd_haus
        sleep 0.5
      end
    end

Lembra-te, podes embrulhar qualquer código com o `with_fx` e qualquer som criado passará pelo efeito.

## 3. Paramatriza os teus synths

De forma a realmente descobrires o teu som no código em breve quererás saber como modificar e controlar os synth e efeitos. Por exemplo, poderás querer mudar a duração de uma nota, adicionar mais reverb, ou mudar o tempo entre os ecos. Felizmente, o Sonic Pi dá-te um incrível nível de controlo para fazer isso com uma coisa especial chamada parâmetros opcionais ou opts como abreviatura. Vamos dar uma vista de olhos. Copia este código para o espaço de trabalho e carrega run:

    sample :guit_em9

Ooh, um bonito som de guitarra! Agora, vamos começar a brincar com ele. Que tal mudar a sua rate?

    sample :guit_em9, rate: 0.5

Hey, o que é essa `rate: 0.5` que acrescentei no final? É chamada um opt. Todos os Synths do Sonic Py e efeitos suportam-no e existem muitos para brincar com eles. Eles também estão disponíveis para efeitos. Tenta isto:

    with_fx :flanger, feedback: 0.6 do
      sample :guit_em9
    end

Agora, tenta aumentar o feedback para 1 para ouvires alguns sons malucos! Lê a documentação para todos os detalhes de todas as opts disponíveis para ti.

## 5. Código ao vivo

A melhor maneira de experimentar e explorar o Sonic Pi é codificares ao vivo. Isto permite que comeces um código e o mudes e afines enquanto esta a ser tocado. Por exemplo, se não sabes o que o parâmetro cutoff faz a um sample, brinca com isso. Vamos experimentar! Copia este código para um espaço de trabalho do Sonic Pi:

    live_loop :experiment do
      sample :loop_amen, cutoff: 70
      sleep 1.75
    end

Agora, carrega run e ouvirás um drum break ligeiramente abafado. Agora, muda o valor de `cutoff:` para `80` e carrega outra vez em run. Consegues ouvir a diferença? Experimenta `90`, `100`, `110`…

Once you get the hang of using `live_loop`s you’ll not turn back. Whenever I do a live coding gig I rely on `live_loop` as much as a drummer relies on their sticks. For more information about live coding check out Section 9 of the built-in tutorial.

## 5. Surf the random streams

Finally, one thing I love doing is cheating by getting Sonic Pi to compose things for me. A really great way to do this is using randomisation. It might sound complicated but it really isn’t. Let’s take a look. Copy this into a spare workspace:

    live_loop :rand_surfer do
      use_synth :dsaw
      notes = (scale :e2, :minor_pentatonic, num_octaves: 2)
      16.times do
        play notes.choose, release: 0.1, cutoff: rrand(70, 120)
        sleep 0.125
      end
    end

Now, when you play this, you’ll hear a constant stream of random notes from the scale `:e2 :minor_pentatonic` played with the `:dsaw` synth. “Wait, wait! That’s not a melody”, I hear you shout! Well, here’s the first part of the magic trick. Every time we go round the `live_loop` we can tell Sonic Pi to reset the random stream to a known point. This is a bit like going back in time in the TARDIS with the Doctor to a particular point in time and space. Let’s try it - add the line `use_random_seed 1` to the `live_loop`:

    live_loop :rand_surfer do
      use_random_seed 1
      use_synth :dsaw
      notes = (scale :e2, :minor_pentatonic, num_octaves: 2)
      16.times do
        play notes.choose, release: 0.1, cutoff: rrand(70, 120)
        sleep 0.125
      end
    end

Now, every time the `live_loop` loops around, the random stream is reset. This means it chooses the same 16 notes every time. Hey presto! An instant melody. Now, here’s the really exciting bit. Change the seed value from `1` to another number. Say `4923`. Wow! Another melody! So, just by changing one number (the random seed), you can explore as many melodic combinations as you can imagine! Now, that’s the magic of code.

# - Live Coding

Live Coding

Live Coding

This may sound like a far fetched story from a futuristic night club but coding music like this is a growing trend and is often described as Live Coding (http://toplap.org). One of the recent directions this approach to music making has taken is the Algorave (http://algorave.com) - events where artists like myself code music for people to dance to. However, you don’t need to be in a nightclub to Live Code - with Sonic Pi v2.6+ you can do it anywhere you can take your Raspberry Pi and a pair of headphones or some speakers. Once you reach the end of this article, you’ll be programming your own beats and modifying them live. Where you go afterwards will only be constrained by your imagination.

## Live Loop

The key to live coding with Sonic Pi is mastering the `live_loop`. Let’s look at one:

    live_loop :beats do
      sample :bd_haus
      sleep 0.5
    end

There are 4 core ingredients to a `live_loop`. The first is its name. Our `live_loop` above is called `:beats`. You’re free to call your `live_loop` anything you want. Go wild. Be creative. I often use names that communicate something about the music they’re making to the audience. The second ingredient is the `do` word which marks where the `live_loop` starts. The third is the `end` word which marks where the `live_loop` finishes, and finally there is the body of the `live_loop` which describes what the loop is going to repeat - that’s the bit between the `do` and `end`. In this case we’re repeatedly playing a bass drum sample and waiting for half a beat. This produces a nice regular bass beat. Go ahead, copy it into an empty Sonic Pi buffer and hit run. Boom, Boom, Boom!.

## Redefining On-the-fly

Ok, so what’s so special about the `live_loop`? So far it just seems like a glorified `loop`! Well, the beauty of `live_loop`s is that you can redefine them on-the-fly. This means that whilst they’re still running, you can change what they do. This is the secret to live coding with Sonic Pi. Let’s have a play:

    live_loop :choral_drone do
      sample :ambi_choir, rate: 0.4
      sleep 1
    end

escolhe

## Sleeping is important

One of the most important lessons about `live_loop`s is that they need rest. Consider the following `live_loop`:

    live_loop :infinite_impossibilities do
      sample :ambi_choir
    end

If you try running this code, you’ll immediately see Sonic Pi complaining that the `live_loop` did not sleep. This is a safety system kicking in! Take a moment to think about what this code is asking the computer to do. That’s right, it’s asking the computer to play an infinite amount of choir samples in zero time. Without the safety system the poor computer will try and do this and crash and burn in the process. So remember, your `live_loop`s must contain a `sleep`.

## Combining Sounds

Music is full of things happening at the same time. Drums at the same time as bass at the same time as vocals at the same time as guitars… In computing we call this concurrency and Sonic Pi provides us with an amazingly simple way of playing things at the same time. Simply use more than one `live_loop`!

    live_loop :beats do
      sample :bd_tek
      with_fx :echo, phase: 0.125, mix: 0.4 do
        sample  :drum_cymbal_soft, sustain: 0, release: 0.1
        sleep 0.5
      end
    end
    live_loop :bass do
      use_synth :tb303
      synth :tb303, note: :e1, release: 4, cutoff: 120, cutoff_attack: 1
      sleep 4
    end

Here, we have two `live_loop`s, one looping quickly making beats and another looping slowly making a wild bass sound.

One of the interesting things about using multiple `live_loop`s is that they each manage their own time. This means it’s really easy to create interesting polyrhythmical structures and even play with phasing Steve Reich style. Check this out:

    # Steve Reich's Piano Phase
    notes = (ring :E4, :Fs4, :B4, :Cs5, :D5, :Fs4, :E4, :Cs5, :B4, :Fs4, :D5, :Cs5)
    live_loop :slow do
      play notes.tick, release: 0.1
      sleep 0.3
    end
    live_loop :faster do
      play notes.tick, release: 0.1
      sleep 0.295
    end

## Bringing it all together

In each of these tutorials, we’ll end with a final example in the form of a new piece of music which draws from all of the ideas introduced. Read this code and see if you can imagine what it’s doing. Then, copy it into a fresh Sonic Pi buffer and hit Run and actually hear what it sounds like. Finally, change one of the numbers or comment and uncomment things out. See if you can use this as a starting point for a new performance, and most of all have fun! See you next time…

    with_fx :reverb, room: 1 do
      live_loop :time do
        synth :prophet, release: 8, note: :e1, cutoff: 90, amp: 3
        sleep 8
      end
    end
    live_loop :machine do
      sample :loop_garzul, rate: 0.5, finish: 0.25
      sample :loop_industrial, beat_stretch: 4, amp: 1
      sleep 4
    end
    live_loop :kik do
      sample :bd_haus, amp: 2
      sleep 0.5
    end
    with_fx :echo do
      live_loop :vortex do
        # use_random_seed 800
        notes = (scale :e3, :minor_pentatonic, num_octaves: 3)
        16.times do
          play notes.choose, release: 0.1, amp: 1.5
          sleep 0.125
        end
      end
    end

# - Coded Beats

One of the most exciting and disrupting technical developments in modern music was the invention of samplers. These were boxes that allowed you to record any sound into them and then manipulate and play back those sounds in many interesting ways. For example, you could take an old record, find a drum solo (or break), record it into your sampler and then play it back on repeat at half-speed to provide the foundation for your latest beats. This is how early hip-hop music was born and today it’s almost impossible to find electronic music that doesn’t incorporate samples of some kind. Using samples is a really great way of easily introducing new and interesting elements into your live coded performances.

So where can you get a sampler? Well you already have one - it’s your Raspberry Pi! The built-in live coding app Sonic Pi has an extremely powerful sampler built into its core. Let’s play with it!

## The Amen Break

One of the most classic and recognisable drum break samples is called the Amen Break. It was first performed in 1969 in the song “Amen Brother” by the Winstons as part of a drum break. However, it was when it was discovered by early hip-hop musicians in the 80s and used in samplers that it started being heavily used in a wide variety of other styles such as drum and bass, breakbeat, hardcore techno and breakcore.

I’m sure you’re excited to hear that it’s also built right into Sonic Pi. Clear up a buffer and throw in the following code:

    sample :loop_amen

Hit Run and boom! You’re listening to one of the most influential drum breaks in the history of dance music. However, this sample wasn’t famous for being played as a one-shot, it was built for being looped.

## Beat Stretching

Let’s loop the Amen Break by using our old friend the `live_loop` introduced in this tutorial last month:

    live_loop :amen_break do
      sample :loop_amen
      sleep 2
    end

OK, so it is looping, but there’s an annoying pause every time round. That is because we asked it to sleep for `2` beats and with the default BPM of 60 the `:loop_amen` sample only lasts for `1.753` beats. We therefore have a silence of `2 - 1.753 = 0.247` beats. Even though it’s short, it’s still noticeable.

To fix this issue we can use the `beat_stretch:` opt to ask Sonic Pi to stretch (or shrink) the sample to match the specified number of beats.

Sonic Pi’s `sample` and `synth` fns give you a lot of control via optional parameters such as `amp:`, `cutoff:` and `release:`. However, the term optional parameter is a real mouthful so we just call them opts to keep things nice and simple.

    live_loop :amen_break do
      sample :loop_amen, beat_stretch: 2
      sleep 2
    end

Now we’re dancing! Although, perhaps we want to speed it up or slow it down to suit the mood.

## Playing with Time

OK, so what if we want to change styles to old school hip hop or breakcore? One simple way of doing this is to play with time - or in other words mess with the tempo. This is super easy in Sonic Pi - just throw in a `use_bpm` into your live loop:

    live_loop :amen_break do
      use_bpm 30
      sample :loop_amen, beat_stretch: 2
      sleep 2
    end

Whilst you’re rapping over those slow beats, notice that we’re still sleeping for 2 and our BPM is 30, yet everything is in time. The `beat_stretch` opt works with the current BPM to make sure everything just works.

Now, here’s the fun part. Whilst the loop is still live, change the `30` in the `use_bpm 30` line to `50`. Woah, everything just got faster yet kept in time! Try going faster - up to 80, to 120, now go wild and punch in 200!

## Filtering

Now we can live loop samples, let’s look at some of the most fun opts provided by the `sample` synth. First up is `cutoff:` which controls the cutoff filter of the sampler. By default this is disabled but you can easily turn it on:

    live_loop :amen_break do
      use_bpm 50
      sample :loop_amen, beat_stretch: 2, cutoff: 70
      sleep 2
    end

Go ahead and change the `cutoff:` opt. For example, increase it to 100, hit Run and wait for the loop to cycle round to hear the change in the sound. Notice that low values like 50 sound mellow and bassy and high values like 100 and 120 are more full-sounding and raspy. This is because the `cutoff:` opt will chop out the high frequency parts of the sound just like a lawn-mower chops off the top of the grass. The `cutoff:` opt is like the length setting - determining how much grass is left over.

## Slicing

Another great tool to play with is the slicer FX. This will chop (slice) the sound up. Wrap the `sample` line with the FX code like this:

    live_loop :amen_break do
      use_bpm 50
      with_fx :slicer, phase: 0.25, wave: 0, mix: 1 do
        sample :loop_amen, beat_stretch: 2, cutoff: 100
      end
      sleep 2
    end

Notice how the sound bounces up and down a little more. (You can hear the original sound without the FX by changing the `mix:` opt to `0`.) Now, try playing around with the `phase:` opt. This is the rate (in beats) of the slicing effect. A smaller value like `0.125` will slice faster and larger values like `0.5` will slice more slowly. Notice that successively halving or doubling the `phase:` opts val tends to always sound good. Finally, change the `wave:` opt to one of 0, 1, or 2 and hear how it changes the sound. These are the various wave shapes. 0 is a saw wave, (hard in, fade out) 1 is a square wave (hard in, hard out) and 2 is a triangle wave (fade in, fade out).

## Bringing it all together

Finally, let’s go back in time and revisit the early Bristol drum and bass scene with this month’s example. Don’t worry too much about what all this means, just type it in, hit Run, then start live coding it by changing opt numbers and see where you can take it. Please do share what you create! See you next time…

    use_bpm 100
    live_loop :amen_break do
      p = [0.125, 0.25, 0.5].choose
      with_fx :slicer, phase: p, wave: 0, mix: rrand(0.7, 1) do
        r = [1, 1, 1, -1].choose
        sample :loop_amen, beat_stretch: 2, rate: r, amp: 2
      end
      sleep 2
    end
    live_loop :bass_drum do
      sample :bd_haus, cutoff: 70, amp: 1.5
      sleep 0.5
    end
    live_loop :landing do
      bass_line = (knit :e1, 3, [:c1, :c2].choose, 1)
      with_fx :slicer, phase: [0.25, 0.5].choose, invert_wave: 1, wave: 0 do
        s = synth :square, note: bass_line.tick, sustain: 4, cutoff: 60
        control s, cutoff_slide: 4, cutoff: 120
      end
      sleep 4
    end

# - Synth Riffs

Whether it’s the haunting drift of rumbling oscillators or the detuned punch of saw waves piercing through the mix, the lead synth plays an essential role on any electronic track. In last month’s edition of this tutorial series we covered how to code our beats. In this tutorial we’ll cover how to code up the three core components of a synth riff - the timbre, melody and rhythm.

OK, so power up your Raspberry Pi, crack open Sonic Pi v2.6+ and let’s make some noise!

## Timbral Possibilities

An essential part of any synth riff is changing and playing with the timbre of the sounds. We can control the timbre in Sonic Pi in two ways - choosing different synths for a dramatic change and setting the various synth opts for more subtle modifications. We can also use FX, but that’s for another tutorial…

Let’s create a simple live loop where we continually change the current synth:

    live_loop :timbre do
      use_synth (ring :tb303, :blade, :prophet, :saw, :beep, :tri).tick
      play :e2, attack: 0, release: 0.5, cutoff: 100
      sleep 0.5
    end

Take a look at the code. We’re simply ticking through a ring of synth names (this will cycle through each of these in turn repeating the list over and over). We pass this synth name to the `use_synth` fn (function) which will change the `live_loop`’s current synth. We also play note `:e2` (E at the second octave), with a release time of 0.5 beats (half a second at the default BPM of 60) and with the `cutoff:` opt set to 100.

Hear how the different synths have very different sounds even though they’re all playing the same note. Now experiment and have a play. Change the release time to bigger and smaller values. For example, change the `attack:` and `release:` opts to see how different fade in/out times have a huge impact on the sound. Finally change the `cutoff:` opt to see how different cutoff values also massively influence the timbre (values between 60 and 130 are good). See how many different sounds you can create by just changing a few values. Once you’ve mastered that, just head to the Synths tab in the Help system for a full list of all the synths and all the available opts each individual synth supports to see just how much power you have under your coding fingertips.

## Timbre

Timbre is just a fancy word describing the sound of a sound. If you play the same note with different instruments such as a violin, guitar, or piano, the pitch (how high or low it sounds) would be the same, but the sound quality would be different. That sound quality - the thing which allows you to tell the difference between a piano and a guitar is the timbre.

## Melodic Composition

Another important aspect to our lead synth is the choice of notes we want to play. If you already have a good idea, then you can simply create a ring with your notes in and tick through them:

    live_loop :riff do
      use_synth :prophet
      riff = (ring :e3, :e3, :r, :g3, :r, :r, :r, :a3)
      play riff.tick, release: 0.5, cutoff: 80
      sleep 0.25
    end

Here, we’ve defined our melody with a ring which includes both notes such as `:e3` and rests represented by `:r`. We’re then using `.tick` to cycle through each note to give us a repeating riff.

## Auto Melody

It’s not always easy to come up with a nice riff from scratch. Instead it’s often easier to ask Sonic Pi for a selection of random riffs and to choose the one you like the best. To do that we need to combine three things: rings, randomisation and random seeds. Let’s look at an example:

    live_loop :random_riff do
      use_synth :dsaw
      use_random_seed 3
      notes = (scale :e3, :minor_pentatonic).shuffle
      play notes.tick, release: 0.25, cutoff: 80
      sleep 0.25
    end

There’s a few things going on - let’s look at them in turn. First, we specify that we’re using random seed 3. What does this mean? Well, the useful thing is that when we set the seed, we can predict what the next random value is going to be - it’s the same as it was last time we set the seed to 3! Another useful thing to know is that shuffling a ring of notes works in the same way. In the example above we’re essentially asking for the ‘third shuffle’ in the standard list of shuffles - which is also the same every time as we’re always setting the random seed to the same value right before the shuffle. Finally we’re just ticking through our shuffled notes to play the riff.

Now, here’s where the fun starts. If we change the random seed value to another number, say 3000, we get an entirely different shuffling of the notes. So now it’s extremely easy to explore new melodies. Simply choose the list of notes we want to shuffle (scales are a great starting point) and then choose the seed we want to shuffle with. If we don’t like the melody, just change one of those two things and try again. Repeat until you like what you hear!

## Pseudo Randomisation

Sonic Pi’s randomisation is not actually random it’s what’s called pseudo random. Imagine if you were to roll a dice 100 times and write down the result of each roll onto a piece of paper. Sonic Pi has the equivalent of this list of results which it uses when you ask for a random value. Instead of rolling an actual dice, it just picks the next value from the list. Setting the random seed is just jumping to a specific point in that list.

## Finding your Rhythm

Another important aspect to our riff is the rhythm - when to play a note and when not to. As we saw above we can use `:r` in our rings to insert rests. Another very powerful way is to use spreads which we’ll cover in a future tutorial. Today we’ll use randomisation to help us find our rhythm. Instead of playing every note we can use a conditional to play a note with a given probability. Let’s take a look:

    live_loop :random_riff do
      use_synth :dsaw
      use_random_seed 30
      notes = (scale :e3, :minor_pentatonic).shuffle
      16.times do
        play notes.tick, release: 0.2, cutoff: 90 if one_in(2)
        sleep 0.125
      end
    end

A really useful fn to know is `one_in` which will give us a `true` or `false` value with the specified probability. Here, we’re using a value of 2 so on average one time every two calls to `one_in` it will return `true`. In other words, 50% of the time it will return `true`. Using higher values will make it return `false` more often introducing more space into the riff.

Notice that we’ve added some iteration in here with `16.times`. This is because we only want to reset our random seed value every 16 notes so our rhythm repeats every 16 times. This doesn’t affect the shuffling as that is still done immediately after the seed is set. We can use the iteration size to alter the length of the riff. Try changing the 16 to 8 or even 4 or 3 and see how it affects the rhythm of the riff.

## Bringing it all together

OK, so let’s combine everything we’ve learned together into one final example. See you next time!

    live_loop :random_riff do
      #  uncomment to bring in:
      #  synth :blade, note: :e4, release: 4, cutoff: 100, amp: 1.5
      use_synth :dsaw
      use_random_seed 43
      notes = (scale :e3, :minor_pentatonic, num_octaves: 2).shuffle.take(8)
      8.times do
        play notes.tick, release: rand(0.5), cutoff: rrand(60, 130) if one_in(2)
        sleep 0.125
      end
    end

    live_loop :drums do
      use_random_seed 500
      16.times do
        sample :bd_haus, rate: 2, cutoff: 110 if rand < 0.35
        sleep 0.125
      end
    end

    live_loop :bd do
      sample :bd_haus, cutoff: 100, amp: 3
      sleep 0.5
    end

# - Acid Bass

It’s impossible to look through the history of electronic dance music without seeing the enormous impact of the tiny Roland TB-303 synthesiser. It’s the secret sauce behind the original acid bass sound. Those classic squealing and squelching TB-303 bass riffs can be heard from the early Chicago House scene through to more recent electronic artists such as Plastikman, Squarepusher and Aphex Twin.

Interestingly, Roland never intended for the TB-303 to be used in dance music. It was originally created as a practice aid for guitarists. They imagined that people would program them to play bass lines to jam along to. Unfortunately there were a number of problems: they were a little fiddly to program, didn’t sound particularly good as a bass-guitar replacement and were pretty expensive to buy. Deciding to cut their losses, Roland stopped making them after 10,000 units were sold and after a number of years sitting on guitarist’s shelves, they soon could be found in the windows of second hand shops. These lonely discarded TB-303s were waiting to be discovered by a new generation of experimenters who started using them in ways that Roland didn’t imagine to create wild new sounds. Acid House was born.

Although getting your hands on an original TB-303 is not so easy you will be pleased to know that you can turn your Raspberry Pi into one using the power of Sonic Pi. Behold, fire up Sonic Pi and throw this code into an empty buffer and hit Run:

    use_synth :tb303
    play :e1

Instant acid bass! Let’s play around…

## Squelch that Bass

First, let’s build a live arpeggiator to make things fun. In the last tutorial we looked at how riffs can just be a ring of notes that we tick through one after another, repeating when we get to the end. Let’s create a live loop that does exactly that:

    use_synth :tb303
    live_loop :squelch do
      n = (ring :e1, :e2, :e3).tick
      play n, release: 0.125, cutoff: 100, res: 0.8, wave: 0
      sleep 0.125
    end

Take a look at each line.

1. On the first line we set the default synth to be `tb303` with the `use_synth` fn.
2. On line two we create a live loop called `:squelch` which will just loop round and round.
3. Line three is where we create our riff - a ring of notes (E in octaves 1, 2, and 3) which we simply tick through with `.tick`. We define `n` to represent the current note in the riff. The equals sign just means to assign the value on the right to the name on the left. This will be different every time round the loop. The first time round, `n` will be set to `:e1`. The second time round it will be `:e2`, followed by `:e3`, and then back to `:e1`, cycling round forever.
4. Line four is where we actually trigger our `:tb303` synth. We’re passing a few interesting opts here: `release:`, `cutoff:`, `res:` and `wave:` which we’ll discuss below.
5. Line five is our `sleep` - we’re asking the live loop to loop round every `0.125`s or 8 times a second at the default BPM of 60.
6. Line six is the `end` to the live loop. This just tells Sonic Pi where the end of the live loop is.

Whilst you’re still figuring out what’s going on, type in the code above and hit the Run button. You should hear the `:tb303` kick into action. Now, this is where the action is: let’s start live coding.

Whilst the loop is still live, change the `cutoff:` opt to `110`. Now hit the Run button again. You should hear the sound become a little harsher and more squelchy. Dial in `120` and hit run. Now `130`. Listen how higher cutoff values make it sound more piercing and intense. Finally, drop it down to `80` when you feel like a rest. Then repeat as many times as you want. Don’t worry, I’ll still be here…

Another opt worth playing with is `res:`. This controls the level of resonance of the filter. A high resonance is characteristic of acid bass sounds. We currently have our `res:` set to `0.8`. Try cranking it up to `0.85`, then `0.9`, and finally `0.95`. You might find that a cutoff such as `110` or higher will make the differences easier to hear. Finally go wild and dial in `0.999` for some insane sounds. At a `res` this high, you’re hearing the cutoff filter resonate so much it starts to make sounds of its own!

Finally, for a big impact on the timbre try changing the `wave:` opt to `1`. This is the choice of source oscillator. The default is `0` which is a sawtooth wave. `1` is a pulse wave and `2` is a triangle wave.

Of course, try different riffs by changing the notes in the ring or even picking notes from scales or chords. Have fun with your first acid bass synth.

## Deconstructing the TB-303

The design of the original TB-303 is actually pretty simple. As you can see from the following diagram there’s only 4 core parts.

First is the oscillator wave - the raw ingredients of the sound. In this case we have a square wave. Next there’s the oscillator’s amplitude envelope which controls the amp of the square wave through time. These are accessed in Sonic Pi by the `attack:`, `decay:`, `sustain:` and `release:` opts along with their level counterparts. For more information read Section 2.4 ‘Duration with Envelopes’ in the built-in tutorial. We then pass our enveloped square wave through a resonant low pass filter. This chops off the higher frequencies as well as having that nice resonance effect. Now this is where the fun starts. The cutoff value of this filter is also controlled by its own envelope! This means we have amazing control over the timbre of the sound by playing with both of these envelopes. Let’s take a look:

    use_synth :tb303
    with_fx :reverb, room: 1 do
      live_loop :space_scanner do
        play :e1, cutoff: 100, release: 7, attack: 1, cutoff_attack: 4, cutoff_release: 4
        sleep 8
      end
    end

‘:tb303’

Notice that I’ve passed everything through a `:reverb` FX for extra atmosphere - try other FX to see what works!

## Bringing it all together

Finally, here’s a piece I composed using the ideas in this tutorial. Copy it into an empty buffer, listen for a while and then start live coding your own changes. See what wild sounds you can make with it! See you next time…

    use_synth :tb303
    use_debug false

    with_fx :reverb, room: 0.8 do
      live_loop :space_scanner do
        with_fx :slicer, phase: 0.25, amp: 1.5 do
          co = (line 70, 130, steps: 8).tick
          play :e1, cutoff: co, release: 7, attack: 1, cutoff_attack: 4, cutoff_release: 4
          sleep 8
        end
      end

      live_loop :squelch do
        use_random_seed 3000
        16.times do
          n = (ring :e1, :e2, :e3).tick
          play n, release: 0.125, cutoff: rrand(70, 130), res: 0.9, wave: 1, amp: 0.8
          sleep 0.125
        end
      end
    end

# - Musical Minecraft

Minecraft Pi

Hello and welcome back! In the previous tutorials we’ve focussed purely on the music possibilities of Sonic Pi - (turning your Raspberry Pi into a performance ready musical instrument). So far we’ve learned how to:

- Live Code - changing the sounds on-the-fly,
- Code some huge beats,
- Generate powerful synth leads,
- Re-create the famous TB-303 acid-bass sound.

There’s so much more to show you (which we will explore in future editions). However, this month, let’s look at something Sonic Pi can do that you probably didn’t realise: control Minecraft.

## Hello Minecraft World

OK, let’s get started. Boot up your Raspberry Pi, fire up Minecraft Pi and create a new world. Now start up Sonic Pi and re-size and move your windows so you can see both Sonic Pi and Minecraft Pi at the same time.

In a fresh buffer type the following:

    mc_message "Hello Minecraft from Sonic Pi!"

Now, hit Run. Boom! Your message appeared in Minecraft! How easy was that? Now, stop reading this for a moment and play about with your own messages. Have fun!

## Sonic Teleporter

Now let’s do some exploring. The standard option is to reach for the mouse and keyboard and start walking around. That works, but it’s pretty slow and boring. It would be far better if we had some sort of teleport machine. Well, thanks to Sonic Pi, we have one. Try this:

    mc_teleport 80, 40, 100

Crikey! That was a long way up. If you weren’t in flying-mode then you would have fallen back down all the way to the ground. If you double-tap space to enter flying-mode and teleport again, you’ll stay hovering at the location you zap to.

Now, what do those numbers mean? We have three numbers which describe the coordinates of where in the world we want to go. We give each number a name - x, y and z:

- x - how far left and right (80 in our example)
- y - how high we want to be (40 in our example)
- z - how far forward and back (100 in our example)

By choosing different values for x, y and z we can teleport anywhere in our world. Try it! Choose different numbers and see where you can end up. If the screen goes black it’s because you’ve teleported yourself under the ground or into a mountain. Just choose a higher y value to get back out above land. Keep on exploring until you find somewhere you like…

Using the ideas so far, let’s build a Sonic Teleporter which makes a fun teleport sound whilst it whizzes us across the Minecraft world:

    mc_message "Preparing to teleport...."
    sample :ambi_lunar_land, rate: -1
    sleep 1
    mc_message "3"
    sleep 1
    mc_message "2"
    sleep 1
    mc_message "1"
    sleep 1
    mc_teleport 90, 20, 10
    mc_message "Whoooosh!"

## Magic Blocks

Now you’ve found a nice spot, let’s start building. You could do what you’re used to and start clicking the mouse furiously to place blocks under the cursor. Or you could use the magic of Sonic Pi. Try this:

    x, y, z = mc_location
    mc_set_block :melon, x, y + 5, z

Now look up! There’s a melon in the sky! Take a moment to look at the code. What did we do? On line one we grabbed the current location of Steve as the variables x, y and z. These correspond to our coordinates described above. We use these coordinates in the fn `mc_set_block` which will place the block of your choosing at the specified coordinates. In order to make something higher up in the sky we just need to increase the y value which is why we add 5 to it. Let’s make a long trail of them:

    live_loop :melon_trail do
      x, y, z = mc_location
      mc_set_block :melon, x, y-1, z
      sleep 0.125
    end

Now, jump over to Minecraft, make sure you’re in flying-mode (double tap space if not) and fly all around the world. Look behind you to see a pretty trail of melon blocks! See what kind of twisty patterns you can make in the sky.

## Live Coding Minecraft

Those of you that have been following this tutorial over the last few months will probably have your minds blown at this point. The trail of melons is pretty cool, but the most exciting part of the previous example is that you can use `live_loop` with Minecraft! For those that don’t know, `live_loop` is Sonic Pi’s special magic ability that no other programming language has. It lets you run multiple loops at the same time and allows you to change them whilst they run. They are incredibly powerful and amazing fun. I use `live_loop`s to perform music in nightclubs with Sonic Pi - DJs use discs and I use `live_loop`s :-) However, today we’re going to live code both music and Minecraft.

Let’s get started. Run the code above and start making your melon trail again. Now, without stopping the code, just simply change `:melon` to `:brick` and hit run. Hey presto, you’re now making a brick trail. How simple was that! Fancy some music to go with it? Easy. Try this:

    live_loop :bass_trail do
      tick
      x, y, z = mc_location
      b = (ring :melon, :brick, :glass).look
      mc_set_block b, x, y -1, z
      note = (ring :e1, :e2, :e3).look
      use_synth :tb303
      play note, release: 0.1, cutoff: 70
      sleep 0.125
    end

Now, whilst that’s playing start changing the code. Change the block types - try `:water`, `:grass` or your favourite block type. Also, try changing the cutoff value from `70` to `80` and then up to `100`. Isn’t this fun?

## Bringing it all together

Let’s combine everything we’ve seen so far with a little extra magic. Let’s combine our teleportation ability with block placing and music to make a Minecraft Music Video. Don’t worry if you don’t understand it all, just type it in and have a play by changing some of the values whilst it’s running live. Have fun and see you next time…

    live_loop :note_blocks do
      mc_message "This is Sonic Minecraft"
      with_fx :reverb do
        with_fx :echo, phase: 0.125, reps: 32 do
          tick
          x = (range 30, 90, step: 0.1).look
          y = 20
          z = -10
          mc_teleport x, y, z
          ns = (scale :e3, :minor_pentatonic)
          n = ns.shuffle.choose
          bs = (knit :glass, 3, :sand, 1)
          b = bs.look
          synth :beep, note: n, release: 0.1
          mc_set_block b, x+20, n-60+y, z+10
          mc_set_block b, x+20, n-60+y, z-10
          sleep 0.25
        end
      end
    end
    live_loop :beats do
      sample :bd_haus, cutoff: 100
      sleep 0.5
    end

# - Bizet Beats

After our brief excursion to the fantastic world of coding Minecraft with Sonic Pi last month, let’s get musical again. Today we’re going to bring a classical operatic dance piece straight into the 21st century using the awesome power of code.

## Outrageous and Disruptive

Let’s jump into a time machine back to the year 1875. A composer called Bizet had just finished his latest opera Carmen. Unfortunately like many exciting and disruptive new pieces of music people initially didn’t like it at all because it was too outrageous and different. Sadly Bizet died ten years before the opera gained huge international success and became one of the most famous and frequently performed operas of all time. In sympathy with this tragedy let’s take one of the main themes from Carmen and convert it to a modern format of music that is also too outrageous and different for most people in our time - live coded music!

## Decoding the Habanera

Trying to live code the whole opera would be a bit of a challenge for this tutorial, so let’s focus on one of the most famous parts - the bass line to the Habanera:

This may look extremely unreadable to you if you haven’t yet studied music notation. However, as programmers we see music notation as just another form of code - only it represents instructions to a musician instead of a computer. We therefore need to figure out a way of decoding it.

## Notes

The notes are arranged from left to right like the words in this magazine but also have different heights. The height on the score represents the pitch of the note. The higher the note on the score, the higher the pitch of the note.

In Sonic Pi we already know how to change the pitch of a note - we either use high or low numbers such as `play 75` and `play 80` or we use the note names: `play :E` and `play :F`. Luckily each of the vertical positions of the musical score represents a specific note name. Take a look at this handy look up table:

## Rests

Music scores are an extremely rich and expressive kind of code capable of communicating many things. It therefore shouldn’t come as much of a surprise that musical scores can not only tell you what notes to play but also when not to play notes. In programming this is pretty much equivalent to the idea of `nil` or `null` - the absence of a value. In other words not playing a note is like the absence of a note.

If you look closely at the score you’ll see that it’s actually a combination of black dots with lines which represent notes to play and squiggly things which represent the rests. Luckily Sonic Pi has a very handy representation for a rest: `:r`, so if we run: `play :r` it actually plays silence! We could also write `play :rest`, `play nil` or `play false` which are all equivalent ways of representing rests.

## Rhythm

Finally, there’s one last thing to learn how to decode in the notation - the timings of the notes. In the original notation you’ll see that the notes are connected with thick lines called beams. The second note has two of these beams which means it lasts for a 16th of a beat. The other notes have a single beam which means they last for an 8th of a beat. The rest has two squiggly beams which means it also represents a 16th of the beat.

When we attempt to decode and explore new things a very handy trick is to make everything as similar as possible to try and see any relationships or patterns. For example, when we re-write our notation purely in 16ths you can see that our notation just turns into a nice sequence of notes and rests.

## Re-coding the Habanera

We’re now in a position to start translating this bass line to Sonic Pi. Let’s encode these notes and rests in a ring:

    (ring :d, :r, :r, :a, :f5, :r, :a, :r)

Let’s see what this sounds like. Throw it in a live loop and tick through it:

    live_loop :habanera do
      play (ring :d, :r, :r, :a, :f5, :r, :a, :r).tick
      sleep 0.25
    end

Fabulous, that instantly recognisable riff springs to life through your speakers. It took a lot of effort to get here, but it was worth it - high five!

## Moody Synths

Now we have the bass line, let’s re-create some of the ambience of the operatic scene. One synth to try out is `:blade` which is a moody 80s style synth lead. Let’s try it with the starting note `:d` passed through a slicer and reverb:

    live_loop :habanera do
      use_synth :fm
      use_transpose -12
      play (ring :d, :r, :r, :a, :f5, :r, :a, :r).tick
      sleep 0.25
    end
    with_fx :reverb do
      live_loop :space_light do
        with_fx :slicer, phase: 0.25 do
          synth :blade, note: :d, release: 8, cutoff: 100, amp: 2
        end
        sleep 8
      end
    end

Now, try the other notes in the bass line: `:a` and `:f5`. Remember, you don’t need to hit stop, just modify the code whilst the music is playing and hit run again. Also, try different values for the slicer’s `phase:` opt such as `0.5`, `0.75` and `1`.

## Bringing it all together

Finally, let’s combine all the ideas so far into a new remix of the Habanera. You might notice that I’ve included another part of the bass line as a comment. Once you’ve typed it all into a fresh buffer hit Run to hear the composition. Now, without hitting stop, uncomment the second line by removing the `#` and hit run again - how marvellous is that! Now, start mashing it around yourself and have fun.

    use_debug false
    bizet_bass = (ring :d, :r, :r, :a, :f5, :r, :a, :r)
    #bizet_bass = (ring :d, :r, :r, :Bb, :g5, :r, :Bb, :r)

    with_fx :reverb, room: 1, mix: 0.3 do
      live_loop :bizet do
        with_fx :slicer, phase: 0.125 do
          synth :blade, note: :d4, release: 8,
            cutoff: 100, amp: 1.5
        end
        16.times do
          tick
          play bizet_bass.look, release: 0.1
          play bizet_bass.look - 12, release: 0.3
          sleep 0.125
        end
      end
    end

    live_loop :ind do
      sample :loop_industrial, beat_stretch: 1,
        cutoff: 100, rate: 1
      sleep 1
    end

    live_loop :drums do
      sample :bd_haus, cutoff: 110
      synth :beep, note: 49, attack: 0,
        release: 0.1
      sleep 0.5
    end

# - Become a Minecraft VJ

Minecraft Pi

Everyone has played Minecraft. You will all have built amazing structures, designed cunning traps and even created elaborate cart lines controlled by redstone switches. How many of you have performed with Minecraft? We bet you didn’t know that you could use Minecraft to create amazing visuals just like a professional VJ.

If your only way of modifying Minecraft was with the mouse, you’d have a tough time changing things fast enough. Luckily for you your Raspberry Pi comes with a version of Minecraft that can be controlled with code. It also comes with an app called Sonic Pi which makes coding Minecraft not only easy but also incredibly fun.

In today’s article we’ll be showing you some of the tips and tricks that we’ve used to create performances in night clubs and music venues around the world.

Let’s get started…

## Getting Started

Let’s start with a simple warm up exercise to refresh ourselves with the basics. First up, crack open your Raspberry Pi and then fire up both Minecraft and Sonic Pi. In Minecraft, create a new world, and in Sonic Pi choose a fresh buffer and write in this code:

    mc_message "Let's get started..."

Hit the Run button and you’ll see the message over in the Minecraft window. OK, we’re ready to start, let’s have some fun……

## Sand Storms

When we’re using Minecraft to create visuals we try and think about what will both look interesting and also be easy to generate from code. One nice trick is to create a sand storm by dropping sand blocks from the sky. For that all we need are a few basic fns:

- `sleep` - for inserting a delay between actions
- `mc_location` - to find our current location
- `mc_set_block`- to place sand blocks at a specific location
- `rrand` - to allow us to generate random values within a range
- `live_loop` - to allow us to continually make it rain sand

If you’re unfamiliar with any of the built-in fns such as `rrand`, just type the word into your buffer, click on it and then hit the keyboard combo `Control-i` to bring up the built-in documentation. Alternatively you can navigate to the lang tab in the Help system and then look up the fns directly along with all the other exciting things you can do.

Let’s make it rain a little first before unleashing the full power of the storm. Grab your current location and use it to create a few sand blocks up in the sky nearby:

    x, y, z = mc_location
    mc_set_block :sand, x, y + 20, z + 5
    sleep 2
    mc_set_block :sand, x, y + 20, z + 6
    sleep 2
    mc_set_block :sand, x, y + 20, z + 7
    sleep 2
    mc_set_block :sand, x, y + 20, z + 8

When you hit Run, you might have to look around a little as the blocks may start falling down behind you depending on which direction you’re currently facing. Don’t worry, if you missed them just hit Run again for another batch of sand rain - just make sure you’re looking the right way!

Let’s quickly review what’s going on here. On the first line we grabbed Steve’s location as coordinates with the fn `mc_location` and placed them into the vars `x`, `y`, and `z`. Then on the next lines we used the `mc_set_block` fn to place some sand at the same coordinates as Steve but with some modifications. We chose the same x coordinate, a y coordinate 20 blocks higher and then successively larger z coordinates so the sand dropped in a line away from Steve.

Why don’t you take that code and start playing around with it yourself? Try adding more lines, changing the sleep times, try mixing `:sand` with `:gravel` and choose different coordinates. Just experiment and have fun!

## Live Loops Unleashed

OK, it’s time to get the storm raging by unleashing the full power of the `live_loop` - Sonic Pi’s magical ability which unleashes the full power of live coding - changing code on-the-fly whilst it’s running!

    live_loop :sand_storm do
      x, y, z = mc_location
      xd = rrand(-10, 10)
      zd = rrand(-10, 10)
      co = rrand(70, 130)
      synth :cnoise, attack: 0, release: 0.125, cutoff: co
      mc_set_block :sand, x + xd, y+20, z+zd
      sleep 0.125
    end

What fun! We’re looping round pretty quickly (8 times a second) and during each loop we’re finding Steve’s location like before but then generating 3 random values:

- `xd` - the difference for x which will be between -10 and 10
- `zd` - the difference for z also between -10 and 10
- `co` - a cutoff value for the low pass filter between 70 and 130

We then use those random values in the fns `synth` and `mc_set_block` giving us sand falling in random locations around Steve along with a percussive rain-like sound from the `:cnoise` synth.

For those of you new to live loops - this is where the fun really starts with Sonic Pi. Whilst the code is running and the sand is pouring down, try changing one of the values, perhaps the sleep time to `0.25` or the `:sand` block type to `:gravel`. Now hit run again. Hey Presto! Things changed without the code stopping. This is your gateway to performing like a real VJ. Keep practising and changing things around. How different can you make the visuals without stopping the code?

## Epic Block Patterns

Finally, another great way of generating interesting visuals is to generate huge patterned walls to fly towards and close by. For this effect we’ll need to move from placing the blocks randomly to placing them in an ordered manner. We can do this by nesting two sets of iteration (hit the Help button and navigate to section 5.2 of the tutorial “Iteration and Loops” for more background on iteration). The funny `|xd|` after the do means that `xd` will be set for each value of the iteration. So the first time it will be 0, then 1, then 2… etc. By nesting two lots of iteration together like this we can generate all the coordinates for a square. We can then randomly choose block types from a ring of blocks for an interesting effect:

    x, y, z = mc_location
    bs = (ring :gold, :diamond, :glass)
    10.times do |xd|
      10.times do |yd|
        mc_set_block bs.choose, x + xd, y + yd, z
      end
    end

Pretty neat. Whilst we’re having fun here, try changing `bs.choose` to `bs.tick` to move from a random pattern to a more regular one. Try changing the block types and the more adventurous of you might want to try sticking this within a `live_loop` so that the patterns keep changing automatically.

Now, for the VJ finale - change the two `10.times` to `100.times` and hit Run. Kaboom! A Huge gigantic wall of randomly placed bricks. Imagine how long it would take you to build that manually with your mouse! Double-tap space to enter fly-mode and start swooping by for some great visual effects. Don’t stop here though - use your imagination to conjure up some cool ideas and then use the coding power of Sonic Pi to make it real. When you’ve practised enough dim the lights and put on a VJ show for your friends!

# - Surfing Random Streams

Back in episode 4 of this tutorial series we took a brief look at randomisation whilst coding up some sizzling synth riffs. Given that randomisation is such an important part of my live coding DJ sets I thought it would be useful to cover the fundamentals in much greater detail. So, get your lucky hat on and let’s surf some random streams!

## There is no random

The first thing to learn which might really surprise you when playing with Sonic Pi’s randomisation functions is that they’re not actually really random. What does this actually mean? Well, let’s try a couple of tests. First, imagine a number in your head between 0 and 1. Keep it there and don’t tell me. Now let me guess… was it `0.321567`? No? Bah, I’m clearly no good at this. Let me have another go, but let’s ask Sonic Pi to choose a number this time. Fire up Sonic Pi v2.7+ and ask it for a random number but again don’t tell me:

    print rand

Now for the reveal… was it `0.75006103515625`? Yes! Ha, I can see you’re a little sceptical. Perhaps it was just a lucky guess. Let’s try again. Press the Run button again and see what we get… What? `0.75006103515625` again? This clearly can’t be random! You’re right, it’s not.

What’s going on here? The fancy computer science word here is determinism. This just means that nothing is by chance and everything is destined to be. Your version of Sonic Pi is destined to always return `0.75006103515625` in the program above. This might sound pretty useless, but let me assure you that it’s one of the most powerful parts of Sonic Pi. If you stick at it you’ll learn how to rely on the deterministic nature of Sonic Pi’s randomisation as a fundamental building block for your compositions and live coded DJ sets.

## A Random Melody

When Sonic Pi boots it actually loads into memory a sequence of 441,000 pre-generated random values. When you call a random function such as `rand` or `rrand`, this random stream is used to generate your result. Each call to a random function consumes a value from this stream. Therefore the 10th call to a random function will use the 10th value from the stream. Also, every time you press the Run button, the stream is reset for that run. This is why I could predict the result to `rand` and why the ‘random’ melody was the same every time. Everybody’s version of Sonic Pi uses the exact same random stream which is very important when we start sharing our pieces with each other.

Let’s use this knowledge to generate a repeatable random melody:

    8.times do
     play rrand_i(50, 95)
     sleep 0.125
    end

Type this into a spare buffer and hit Run. You’ll hear a melody consisting of ‘random’ notes between 50 and 95. When it’s finished, hit Run again to hear exactly the same melody again.

## Handy Randomisation Functions

Sonic Pi comes with a number of useful functions for working with the random stream. Here’s a list of some of the most useful:

- `rand` - Simply returns the next value in the random stream
- `rrand` - Returns a random value within a range
- `rrand_i` - Returns a random whole number within a range
- `one_in` - Returns true or false with the given probability
- `dice` - Imitates rolling a dice and returns a value between 1 and 6
- `choose` - Chooses a random value from a list

Check out their documentation in the Help system for detailed information and examples.

## Resetting the Stream

Whilst the ability to repeat a sequence of chosen notes is essential to allow you to replay a riff on the dance floor, it might not be exactly the riff you want. Wouldn’t it be great if we could try a number of different riffs and choose the one we liked best? This is where the real magic starts.

We can manually set the stream with the fn `use_random_seed`. In Computer Science, a random seed is the starting point from which a new stream of random values can sprout out and blossom. Let’s try it:

    use_random_seed 0
    3.times do
      play rrand_i(50, 95)
      sleep 0.125
    end

Great, we get the first three notes of our random melody above: `84`, `83` and `71`. However, we can now change the seed to something else. How about this:

    use_random_seed 1
    3.times do
      play rrand_i(50, 95)
      sleep 0.125
    end

Interesting, we get `83`, `71` and `61` . You might notice that the first two numbers here are the same as the last two numbers before - this isn’t a coincidence.

Remember that the random stream is just a giant list of ‘pre-rolled’ values. Using a random seed simply jumps us to a point in that list. Another way of thinking about it is to imagine a huge deck of pre-shuffled cards. Using a random seed is cutting the deck at a particular point. The fabulous part of this is that it’s precisely this ability to jump around the random stream which gives us huge power when making music.

Let’s revisit our random melody of 8 notes with this new stream resetting power, but let’s also throw in a live loop so we can experiment live whilst it’s playing:

    live_loop :random_riff do
      use_random_seed 0
      8.times do
        play rrand_i(50, 95), release: 0.1
        sleep 0.125
      end
    end

Now, whilst it’s still playing, change the seed value from `0` to something else. Try `100`, what about `999`. Try your own values, experiment and play around - see which seed generates the riff you like best.

## Bringing it all together

This month’s tutorial has been quite a technical dive into the workings of Sonic Pi’s randomisation functionality. Hopefully it has given you some insight into how it works and how you can start using randomisation in a reliable way to create repeatable patterns within your music. It’s important to stress that you can use repeatable randomisation anywhere you want. For example, you can randomise the amplitude of notes, the timing of the rhythm, the amount of reverb, the current synth, the mix of an FX, etc. etc. In the future we’ll take a close look at some of these applications, but for now let me leave you with a short example.

Type the following into a spare buffer, hit Run, and then start changing the seeds around, hit Run again (whilst it’s still playing) and explore the different sounds, rhythms and melodies you can make. When you find a nice one, remember the seed number so you can get back to it. Finally, when you’ve found a few seeds you like, put on a live coded performance for your friends by simply switching between your favourite seeds to create a full piece.

    live_loop :random_riff do
      use_random_seed 10300
      use_synth :prophet
      s = [0.125, 0.25, 0.5].choose
      8.times do
        r = [0.125, 0.25, 1, 2].choose
        n = (scale :e3, :minor).choose
        co = rrand(30, 100)
        play n, release: r, cutoff: co
        sleep s
      end
    end
    live_loop :drums do
      use_random_seed 2001
      16.times do
        r = rrand(0.5, 10)
        sample :drum_bass_hard, rate: r, amp: rand
        sleep 0.125
      end
    end

# - Controlling Your Sound

So far during this series we’ve focussed on triggering sounds. We’ve discovered that we can trigger the many synths built into Sonic Pi with `play` or `synth` and how to trigger pre-recorded samples with `sample`. We’ve also looked at how we can wrap these triggered sounds within studio FX such as reverb and distortion using the `with_fx` command. Combine this with Sonic Pi’s incredibly accurate timing system and you can produce a vast array of sounds, beats and riffs. However, once you’ve carefully selected a particular sound’s options and triggered it, there’s no ability to mess with it whilst it’s playing right? Wrong! Today you’re going to learn something very powerful - how to control running synths.

## A Basic Sound

Let’s create a nice simple sound. Fire up Sonic Pi and in a fresh buffer type the following:

    synth :prophet, note: :e1, release: 8, cutoff: 100

Now press the Run button at the top left to hear a lovely rumbling synth sound. Go ahead, press it again a few times to get a feel for it. OK, done? Let’s start controlling it!

## Synth Nodes

A little known feature in Sonic Pi is that the fns `play`, `synth` and `sample`, return something called a `SynthNode` which represents a running sound. You can capture one of these `SynthNode`s using a standard variable and then control it at a later point in time. For example, let’s change the value of the `cutoff:` opt after 1 beat:

    sn = synth :prophet, note: :e1, release: 8, cutoff: 100
    sleep 1
    control sn, cutoff: 130

Let’s look at each line in turn:

Firstly we trigger the `:prophet` synth using the `synth` fn as normal. However we also capture the result in a variable called `sn`. We could have called this variable something completely different such as `synth_node` or `jane` - the name doesn’t matter. However, it’s important to choose a name that’s meaningful to you for your performances and for people reading your code. I chose `sn` as it’s a nice short mnemonic for synth node.

On line 2 we have a standard `sleep` command. This does nothing special - it just asks the computer to wait for 1 beat before moving onto the next line.

Line 3 is where the control fun starts. Here, we use the `control` fn to tell our running `SynthNode` to change the cutoff value to `130`. If you hit the Run button, you’ll hear the `:prophet` synth start playing as before, but after 1 beat it will shift to sound a lot brighter.

Modulatable Options

Most of Sonic Pi’s synths and FX opts may be changed after being triggered. However, this isn’t the case for all of them. For example, the envelope opts `attack:`, `decay:`, `sustain:` and `release:` can only be set when triggering the synth. Figuring out which opts can and can’t be changed is simple - just head to the documentation for a given synth or FX and then scroll down to the individual option documentation and look for the phrases “May be changed whilst playing” or “Can not be changed once set”. For example, the documentation for the `:beep` synth’s `attack:` opt makes it clear that it’s not possible to change it:

- Default: 0
- Must be zero or greater
- Can not be changed once set
- Scaled with current BPM value

## Multiple Changes

Whilst a synth is running you’re not limited to changing it only once - you’re free to change it as many times as you like. For example, we can turn our `:prophet` into a mini arpeggiator with the following:

    notes = (scale :e3, :minor_pentatonic)
    sn = synth :prophet, note: :e1, release: 8, cutoff: 100
    sleep 1
    16.times do
      control sn, note: notes.tick
      sleep 0.125
    end

In this snippet of code we just added a couple of extra things. First we defined a new variable called `notes` which contains the notes we’d like to cycle through (an arpeggiator is just a fancy name for something that cycles through a list of notes in order). Secondly we replaced our single call to `control` with an iteration calling it 16 times. In each call to `control` we `.tick` through our ring of `notes` which will automatically repeat once we get to the end (thanks to the fabulous power of Sonic Pi’s rings). For a bit of variety try replacing `.tick` with `.choose` and see if you can hear the difference.

Note that we can change multiple opts simultaneously. Try changing the control line to the following and listen for the difference:

    control sn, note: notes.tick, cutoff: rrand(70, 130)

## Sliding

When we control a `SynthNode`, it responds exactly on time and instantly changes the value of the opt to the new one as if you’d pressed a button or flicked a switch requesting the change. This can sound rhythmical and percussive - especially if the opt controls an aspect of the timbre such as `cutoff:`. However, sometimes you don’t want the change to happen instantaneously. Instead, you might want to smoothly move from the current value to the new one as if you’d moved a slider or dial. Of course, Sonic Pi can also do this too using the `_slide:` opts.

Each opt that can be modified also has a special corresponding `_slide:` opt that allows you to specify a slide time. For example, `amp:` has `amp_slide:` and `cutoff:` has `cutoff_slide:`. These slide opts work slightly differently than all the other opts in that they tell the synth note how to behave next time they are controlled. Let’s take a look:

    sn = synth :prophet, note: :e1, release: 8, cutoff: 70, cutoff_slide: 2
    sleep 1
    control sn, cutoff: 130

Notice how this example is exactly the same as before except with the addition of `cutoff_slide:`. This is saying that next time this synth has its `cutoff:` opt controlled, it will take 2 beats to slide from the current value to the new one. Therefore, when we use `control` you can hear the cutoff slide from 70 to 130. It creates an interesting dynamic feel to the sound. Now, try changing the `cutoff_slide:` time to a shorter value such as 0.5 or a longer value such as 4 to see how it changes the sound. Remember, you can slide any of the modifiable opts in exactly this way and each `_slide:` value can be totally different so you can have the cutoff sliding slowly, the amp sliding fast and the pan sliding somewhere in between if that’s what you’re looking to create…

## Bringing it all together

Let’s look at a short example which demonstrates the power of controlling synths after they’ve been triggered. Notice that you can also slide FX just like synths although with a slightly different syntax. Check out section 7.2 of the built-in tutorial for more information on controlling FX.

Copy the code into a spare buffer and take a listen. Don’t stop there though - play around with the code. Change the slide times, change the notes, the synth, the FX and the sleep times and see if you can turn it into something completely different!

    live_loop :moon_rise do
      with_fx :echo, mix: 0, mix_slide: 8 do |fx|
        control fx, mix: 1
        notes = (scale :e3, :minor_pentatonic, num_octaves: 2).shuffle
        sn = synth :prophet , sustain: 8, note: :e1, cutoff: 70, cutoff_slide: 8
        control sn, cutoff: 130
        sleep 2
        32.times do
          control sn, note: notes.tick, pan: rrand(-1, 1)
          sleep 0.125
        end
      end
    end

# - Tracking the Beat

Last month in this series we took a deep technical dive into the randomisation system underpinning Sonic Pi. We explored how we can use it to deterministically add new levels of dynamic control over our code. This month we’re going to continue our technical dive and turn our attention to Sonic Pi’s unique tick system. By the end of this article you’ll be ticking your way through rhythms and riffs on your way to being a live coding DJ.

## Beat Counting

When making music we often want to do a different thing depending on which beat it is. Sonic Pi has a special beat counting system called `tick` to give you precise control over when a beat actually occurs and even supports multiple beats with their own tempos.

Let’s have a play - to advance the beat we just need to call `tick`. Open up a fresh buffer, type in the following and hit Run:

    puts tick #=> 0

This will return the current beat: `0`. Notice that even if you press the Run button a few times it will always return `0`. This is because each run starts a fresh beat counting from 0. However, whilst the run is still active, we can advance the beat as many times as we want:

    puts tick #=> 0
    puts tick #=> 1
    puts tick #=> 2

Whenever you see the symbol `#=>` at the end of a line of code it means that that line will log the text on the right-hand-side. For example, `puts foo #=> 0` means the code `puts foo` prints `0` to the log at that point in the program.

## Checking the Beat

We’ve seen that `tick` does two things. It increments (adds one) and returns the current beat. Sometimes we just want to look at the current beat without having to increment it which we can do via `look`:

    puts tick #=> 0
    puts tick #=> 1
    puts look #=> 1
    puts look #=> 1

In this code we tick the beat up twice and then call `look` twice. We’ll see the following values in the log: `0`, `1`, `1`, `1`. The first two `tick`s returned `0`, then `1` as expected, then the two `look`s just returned the last beat value twice which was `1`.

## Anéis

So now we can advance the beat with `tick` and check the beat with `look`. What next? We need something to tick over. Sonic Pi uses rings for representing riffs, melodies and rhythms and the tick system has been specifically designed to work very closely with them. In fact, rings have their own dot version of `tick` which does two things. Firstly, it acts like a regular tick and increments the beat. Secondly it looks up the ring value using the beat as the index. Let’s take a look:

    puts (ring :a, :b, :c).tick #=> :a

`.tick` is a special dot version of `tick` which will return the first value of the ring `:a`. We can grab each of the values in the ring by calling `.tick` multiple times:

    puts (ring :a, :b, :c).tick #=> :a
    puts (ring :a, :b, :c).tick #=> :b
    puts (ring :a, :b, :c).tick #=> :c
    puts (ring :a, :b, :c).tick #=> :a
    puts look                   #=> 3

Take a look at the log and you’ll see `:a`, `:b`, `:c` and then `:a` again. Notice that `look` returns `3`. Calls to `.tick` act just like they are regular calls to `tick` - they increment the local beat.

## Um Live Loop Arpegiador

O poder real surge quando você mistura `tick` com anéis (rings) e `live_loop`s. Quando combinados nós temos todas as ferramentas que nós precisamos para tanto construir quanto entender um arpejador simples. Precisamos somente de 4 coisas:

1. Um anel (ring) contendo as notas que queremos arpejar.
2. Uma forma de incrementar e obter a batida.
3. A habilidade de tocar uma nota baseada na batida atual.
4. Uma estrutura de loop para manter o arpejador repetindo.

Todos estes conceitos podem ser encontrados no seguinte código:

    notes = (ring 57, 62, 55, 59, 64)
    live_loop :arp do
      use_synth :dpulse
      play notes.tick, release: 0.2
      sleep 0.125
    end

Let’s look at each of these lines. First we define our ring of notes which we’ll continually play. We then create a `live_loop` called `:arp` which loops round for us. Each time round the `live_loop` we set our synth to `:dpulse` and then play the next note in our ring using `.tick`. Remember that this will increment our beat counter and use the latest beat value as an index into our notes ring. Finally, we wait for an eighth of a beat before looping round again.

## Multiple Simultaneous Beats

A really important thing to know is that `tick`s are local to the `live_loop`. This means that each `live_loop` has its own independent beat counter. This is much more powerful than having a global metronome and beat. Let’s take a look at this in action:

    notes = (ring 57, 62, 55, 59, 64)
    with_fx :reverb do
      live_loop :arp do
        use_synth :dpulse
        play notes.tick + 12, release: 0.1
        sleep 0.125
      end
    end
    live_loop :arp2 do
      use_synth :dsaw
      play notes.tick - 12, release: 0.2
      sleep 0.75
    end

## Clashing Beats

A big cause of confusion with Sonic Pi’s tick system is when people want to tick over multiple rings in the same `live_loop`:

    use_bpm 300
    use_synth :blade
    live_loop :foo do
      play (ring :e1, :e2, :e3).tick
      play (scale :e3, :minor_pentatonic).tick
      sleep 1
    end

Even though each `live_loop` has its own independent beat counter, we’re calling `.tick` twice within the same `live_loop`. This means that the beat will be incremented twice every time round. This can produce some interesting polyrhythms but is often not what you want. There are two solutions to this problem. One option is to manually call `tick` at the start of the `live_loop` and then use `.look` to look up the current beat in each `live_loop`. The second solution is to pass a unique name to each call to `.tick` such as `.tick(:foo)`. Sonic Pi will then create and track a separate beat counter for each named tick you use. That way you can work with as many beats as you need! See the section on named ticks in 9.4 of the built-in tutorial for more information.

## Bringing it all together

Let’s bring all this knowledge of `tick`s, `ring`s and `live_loop`s together for a final fun example. As usual, don’t treat this as a finished piece. Start changing things and play around with it and see what you can turn it into. See you next time…

    use_bpm 240
    notes = (scale :e3, :minor_pentatonic).shuffle
    live_loop :foo do
      use_synth :blade
      with_fx :reverb, reps: 8, room: 1 do
        tick
        co = (line 70, 130, steps: 32).tick(:cutoff)
        play (octs :e3, 3).look, cutoff: co, amp: 2
        play notes.look, amp: 4
        sleep 1
      end
    end
    live_loop :bar do
      tick
      sample :bd_ada if (spread 1, 4).look
      use_synth :tb303
      co = (line 70, 130, steps: 16).look
      r = (line 0.1, 0.5, steps: 64).mirror.look
      play notes.look, release: r, cutoff: co
      sleep 0.5
    end

# - Cortando Amostras

Way back in episode 3 of this Sonic Pi series we looked at how to loop, stretch and filter one of the most famous drum breaks of all time - the Amen Break. In this tutorial we’re going to take this one step further and learn how to slice it up, shuffle the slices and glue it back together in a completely new order. If that sounds a bit wild to you, don’t worry, it will all become clear and you’ll soon master a powerful new tool for your live coded sets.

## Sound as Data

Before we get started let’s just take a brief moment to understand how to work with samples. By now, you’ve all hopefully played with Sonic Pi’s powerful sampler. If not, there’s no time like the present! Boot up your Raspberry Pi, launch Sonic Pi from the Programming menu, type the following into a fresh buffer and then hit the Run button to hear a pre-recorded drum beat:

    sample :loop_amen

A recording of a sound is simply represented as data - lots of numbers between -1 and 1 which represent the peaks and troughs of the sound wave. If we play those numbers back in order, we get the original sound. However, what’s to stop us from playing them back in a different order and creating a new sound?

How are samples actually recorded? It’s actually pretty simple once you understand the basic physics of sound. When you make a sound - for example by hitting a drum, the noise travels through the air in a similar fashion to how the surface of a lake ripples when you throw a pebble into it. When those ripples reach your ears, your eardrum moves sympathetically and converts those movements into the sound you hear. If we wish to record and play back the sound, we therefore need a way of capturing, storing and reproducing those ripples. One way is to use a microphone which acts like an eardrum and moves back and forth as the sound ripples hit it. The microphone then converts its position into a tiny electric signal which is then measured many times a second. These measurements are then represented as a series of numbers between -1 and 1.

If we were to plot a visualisation of the sound it would be a simple graph of data with time on the x axis and microphone/speaker position as a value between -1 and 1 on the y axis. You can see an example of such a graph at the top of the diagram.

## Playing Part of a Sample

So, how do we code Sonic Pi to play a sample back in a different order? To answer this question we need to take a look at the `start:` and `finish:` opts for `sample`. These let us control the start and finish positions of our playback of the numbers which represent the sound. The values for both of these opts are represented as a number between `0` and `1` where `0` represents the start of the sample and `1` is the end. So, to play the first half of the Amen Break, we just need to specify a `finish:` of `0.5`:

    sample :loop_amen, finish: 0.5

We can add in a `start:` value to play an even smaller section of the sample:

    sample :loop_amen, start: 0.25, finish: 0.5

For fun, you can even have the `finish:` opt’s value be before `start:` and it will play the section backwards:

    sample :loop_amen, start: 0.5, finish: 0.25

## Re-ordering Sample Playback

Now that we know that a sample is simply a list of numbers that can be played back in any order and also how to play a specific part of a sample we can now start having fun playing a sample back in the ‘wrong’ order.

Let’s take our Amen Break and chop it up into 8 equally-sized slices and then shuffle the pieces around. Take a look at the diagram: at the top A) represents the graph of our original sample data. Chopping it into 8 slices gives us B) - notice that we’ve given each slice a different colour to help distinguish them. You can see each slice’s start and finish values at the top. Finally C) is one possible re-ordering of the slices. We can then play this back to create a new beat. Take a look at the code to do this:

    live_loop :beat_slicer do
      slice_idx = rand_i(8)
      slice_size = 0.125
      s = slice_idx * slice_size
      f = s + slice_size
      sample :loop_amen, start: s, finish: f
      sleep sample_duration :loop_amen, start: s, finish: f
    end

1. we choose a random slice to play which should be a random number between 0 and 7 (remember that we start counting at 0). Sonic Pi has a handy function for exactly this: `rand_i(8)`. We then store this random slice index in the variable `slice_idx`.
2. We define our `slice_size` which is 1/8 or 0.125. The `slice_size` is necessary for us to convert our `slice_idx` into a value between 0 and 1 so we can use it as our `start:` opt.
3. We calculate the start position `s` by multiplying the `slice_idx` by the `slice_size`.
4. We calculate the finish position `f` by adding the `slice_size` to the start position `s`.
5. We can now play the sample slice by plugging in the `s` and `f` values into the `start:` and `finish:` opts for `sample`.
6. Before we play the next slice we need to know how long to `sleep` which should be the duration of the sample slice. Luckily, Sonic Pi has us covered with `sample_duration` which accepts all the same opts as `sample` and simply returns the duration. Therefore, by passing `sample_duration` our `start:` and `finish:` opts, we can find out the duration of a single slice.
7. We wrap all of this code in a `live_loop` so that we continue to pick new random slices to play.

## Bringing it all together

Let’s combine everything we’ve seen so far into a final example which demonstrates how we can take a similar approach to combine randomly sliced beats with some bass to create the start of an interesting track. Now it’s your turn - take the code below as a starting point and see if you can take it in your own direction and create something new…

    live_loop :sliced_amen do
      n = 8
      s =  line(0, 1, steps: n).choose
      f = s + (1.0 / n)
      sample :loop_amen, beat_stretch: 2, start: s, finish: f
      sleep 2.0  / n
    end
    live_loop :acid_bass do
      with_fx :reverb, room: 1, reps: 32, amp: 0.6 do
        tick
        n = (octs :e0, 3).look - (knit 0, 3 * 8, -4, 3 * 8).look
        co = rrand(70, 110)
        synth :beep, note: n + 36, release: 0.1, wave: 0, cutoff: co
        synth :tb303, note: n, release: 0.2, wave: 0, cutoff: co
        sleep (ring 0.125, 0.25).look
      end
    end

# - Code a Probabilistic Sequencer

In a previous episode of this Sonic Pi series we explored the power of randomisation to introduce variety, surprise and change into our live coded tracks and performances. For example, we randomly picked notes from a scale to create never-ending melodies. Today we’re going to learn a new technique which uses randomisation for rhythm - probabilistic beats!

## Probability

Before we can start making new beats and synth rhythms we need to take a quick dive into the basics of probability. This might sound daunting and complicated, but really it’s just as simple as rolling a dice - honestly! When you take a regular 6 sided board game dice and roll it what’s actually happening? Well, firstly you’ll roll either a 1, 2, 3, 4, 5 or 6 with exactly the same chance of getting any of the numbers. In fact, given that it’s a 6 sided dice, on average (if you roll lots and lots of times) you’ll throw a 1 every 6 throws. This means you have a 1 in 6 chance of throwing a 1. We can emulate dice rolls in Sonic Pi with the fn `dice`. Let’s roll one 8 times:

    8.times do
      puts dice
      sleep 1
    end

Notice how the log prints values between 1 and 6 just as if we’d rolled a real dice ourselves.

## Random Beats

Now imagine you had a drum and every time you were about to hit it you rolled a dice. If you rolled a 1, you hit the drum and if you rolled any other number you didn’t. You now have a probabilistic drum machine working with a probability of 1/6! Let’s hear what that sounds like:

    live_loop :random_beat do
      sample :drum_snare_hard if dice == 1
      sleep 0.125
    end

Let’s quickly go over each line to make sure everything is very clear. First we create a new `live_loop` called `:random_beat` which will continually repeat the two lines between `do` and `end`. The first of these lines is a call to `sample` which will play a pre-recorded sound (the `:drum_snare_hard` sound in this case). However, this line has a special conditional `if` ending. This means that the line will only be executed if the statement on the right hand side of the `if` is `true`. The statement in this case is `dice == 1`. This calls our `dice` function which, as we have seen, returns a value between 1 and 6. We then use the equality operator `==` to check to see if this value is `1`. If it is `1`, then the statement resolves to `true` and our snare drum sounds, if it isn’t `1` then the statement resolves to `false` and the snare is skipped. The second line simply waits for `0.125` seconds before rolling the dice again.

## Changing Probabilities

Those of you that have played role play games will be familiar with lots of strangely shaped dice with different ranges. For example there is the tetrahedron shaped dice which has 4 sides and even a 20 sided dice in the shape of a icosahedron. The number of sides on the dice changes the chance, or probability of rolling a 1. The fewer sides, the more likely you are to roll a 1 and the more sides the less likely. For example, with a 4 sided dice, there’s a one in 4 chance of rolling a 1 and with a 20 sided dice there’s a one in 20 chance. Luckily, Sonic Pi has the handy `one_in` fn for describing exactly this. Let’s play:

    live_loop :different_probabilities do
      sample :drum_snare_hard if one_in(6)
      sleep 0.125
    end

Start the live loop above and you’ll hear the familiar random rhythm. However, don’t stop the code running. Instead, change the `6` to a different value such as `2` or `20` and hit the `Run` button again. Notice that lower numbers mean the snare drum sounds more frequently and higher numbers mean the snare triggers fewer times. You’re making music with probabilities!

## Combining Probabilities

Things get really exciting when you combine multiple samples being triggered with different probabilities. For example:

    live_loop :multi_beat do
      sample :elec_hi_snare if one_in(6)
      sample :drum_cymbal_closed if one_in(2)
      sample :drum_cymbal_pedal if one_in(3)
      sample :bd_haus if one_in(4)
      sleep 0.125
    end

Again, run the code above and then start changing the probabilities to modify the rhythm. Also, try changing the samples to create an entirely new feel. For example try changing `:drum_cymbal_closed` to `:bass_hit_c` for extra bass!

## Repeatable Rhythms

Next, we can use our old friend `use_random_seed` to reset the random stream after 8 iterations to create a regular beat. Type the following code to hear a much more regular and repeating rhythm. Once you hear the beat, try changing the seed value from `1000` to another number. Notice how different numbers generate different beats.

    live_loop :multi_beat do
      use_random_seed 1000
      8.times do
        sample :elec_hi_snare if one_in(6)
        sample :drum_cymbal_closed if one_in(2)
        sample :drum_cymbal_pedal if one_in(3)
        sample :bd_haus if one_in(4)
        sleep 0.125
      end
    end

One thing I tend to do with this kind of structure is to remember which seeds sound good and make a note of them. That way I can easily re-create my rhythms in future practice sessions or performances.

## Bringing it all together

Finally, we can throw in some random bass to give it some nice melodic content. Notice that we can also use our newly discovered probabilistic sequencing method on synths just as well as samples. Don’t leave it at that though - tweak the numbers and make your own track with the power of probabilities!

    live_loop :multi_beat do
      use_random_seed 2000
      8.times do
        c = rrand(70, 130)
        n = (scale :e1, :minor_pentatonic).take(3).choose
        synth :tb303, note: n, release: 0.1, cutoff: c if rand < 0.9
        sample :elec_hi_snare if one_in(6)
        sample :drum_cymbal_closed if one_in(2)
        sample :drum_cymbal_pedal if one_in(3)
        sample :bd_haus, amp: 1.5 if one_in(4)
        sleep 0.125
      end
    end

# - Amplitude Modulation

This month we’re going to take a deep dive into one of Sonic Pi’s most powerful and flexible audio FX - the `:slicer`. By the end of this article you will have learned how to manipulate the overall volume of parts of our live coded sound in powerful new ways. This will allow you to create new rhythmic and timbral structures and broaden your sonic possibilities.

## Slice that Amp

So, what does the `:slicer` FX actually do? One way to think about it is that it’s just like having someone play around with the volume control on your TV or home hi-fi. Let’s take a look but first, listen to the deep growl of the following code which triggers the `:prophet` synth:

    synth :prophet, note: :e1, release: 8, cutoff: 70
    synth :prophet, note: :e1 + 4, release: 8, cutoff: 80

Now, let’s pipe it through the `:slicer` FX:

    with_fx :slicer do
      synth :prophet, note: :e1, release: 8, cutoff: 70
      synth :prophet, note: :e1 + 4, release: 8, cutoff: 80
    end

Hear how the slicer acts like it’s muting and unmuting the audio with a regular beat. Also, notice how the `:slicer` affects all the audio generated between the `do`/`end` blocks. You can control the speed at which it turns the audio on and off with the `phase:` opt which is short for phase duration. Its default value is `0.25` which means 4 times a second at the default BPM of 60. Let’s make it faster:

    with_fx :slicer, phase: 0.125 do
      synth :prophet, note: :e1, release: 8, cutoff: 70
      synth :prophet, note: :e1 + 4, release: 8, cutoff: 80
    end

Now, play with different `phase:` durations yourself. Try longer and shorter values. See what happens when you choose a really short value. Also, try different synths such as `:beep` or `:dsaw` and different notes. Take a look at the following diagram to see how different `phase:` values change the number of amplitude changes per beat.

Duração

Phase duration is the length of time for one on/off cycle. Therefore smaller values will make the FX switch on and off much faster than larger values. Good values to start playing with are `0.125`, `0.25`, `0.5` and `1`.

## Control Waves

By default, the `:slicer` FX uses a square wave to manipulate the amplitude through time. This is why we hear the amplitude on for a period, then immediately off for a period, then back on again. It turns out that the square wave is just one of 4 different control waves that are supported by `:slicer`. The others are saw, triangle and (co)sine. Take a look at the diagram below to see what these look like. We can also hear what they sound like. For example, the following code uses (co)sine as the control wave. Hear how the sound doesn’t turn on and off abruptly but instead smoothly fades in and out:

    with_fx :slicer, phase: 0.5, wave: 3 do
      synth :dsaw, note: :e3, release: 8, cutoff: 120
      synth :dsaw, note: :e2, release: 8, cutoff: 100
    end

Have a play with the different wave forms by changing the `wave:` opt to `0` for saw, `1` for square, `2` for triangle and `3` for sine. See how different waves sound with different `phase:` opts too.

Each of these waves can be inverted with the `invert_wave:` opt which flips it on the y axis. For example, in a single phase the saw wave typically starts high, and slowly goes down before jumping back to the top. With `invert_wave: 1` it will start low and slowly go up before jumping back down again. Additionally, the control wave can be started at different points with the `phase_offset:` opt which should be a value between `0` and `1`. By playing around with `phase:`, `wave:`, `invert_wave:` and `phase_offset` opts you can dramatically change how the amplitude is modified through time.

Duração

## Setting your levels

By default, `:slicer` switches between amplitude values `1` (fully loud) and `0` (silent). This can be changed with the `amp_min:` and `amp_max:` opts. You can use this alongside the sine wave setting to create a simple tremolo effect:

    with_fx :slicer, amp_min: 0.25, amp_max: 0.75, wave: 3, phase: 0.25 do
      synth :saw, release: 8
    end

This is just like grabbing the volume knob on your hi-fi and moving it up and down just a little so the sound ‘wobbles’ in and out.

## Probabilities

One of `:slicer`’s powerful features is its ability to use probability to choose whether or not to turn the slicer on or off. Before the `:slicer` FX starts a new phase it rolls a dice and based on the result either uses the selected control wave or keeps the amplitude off. Let’s take a listen:

    with_fx :slicer, phase: 0.125, probability: 0.6  do
      synth :tb303, note: :e1, cutoff_attack: 8, release: 8
      synth :tb303, note: :e2, cutoff_attack: 4, release: 8
      synth :tb303, note: :e3, cutoff_attack: 2, release: 8
    end

Hear how we now have an interesting rhythm of pulses. Try changing the `probability:` opt to a different value between `0` and `1`. Values closer to `0` will have more space between each sound due to the likelihood of the sound being triggered being much lower.

Another thing to notice is that the probability system in the FX is just like the randomisation system accessible via fns such as `rand` and `shuffle`. They are both completely deterministic. This means that each time you hit Run you’ll hear exactly the same rhythm of pulses for a given probability. If you would like to change things around you can use the `seed:` opt to select a different starting seed. This works exactly the same as `use_random_seed` but only affects that particular FX.

Finally, you can change the ‘resting’ position of the control wave when the probability test fails from `0` to any other position with the `prob_pos:` opt:

    with_fx :slicer, phase: 0.125, probability: 0.6, prob_pos: 1  do
      synth :tb303, note: :e1, cutoff_attack: 8, release: 8
      synth :tb303, note: :e2, cutoff_attack: 4, release: 8
      synth :tb303, note: :e3, cutoff_attack: 2, release: 8
    end

## Slicing Beats

One really fun thing to do is to use `:slicer` to chop a drum beat in and out:

    with_fx :slicer, phase: 0.125 do
      sample :loop_mika
    end

This allows us to take any sample and create new rhythmical possibilities which is a lot of fun. However, one thing to be careful about is to make sure that the tempo of the sample matches the current BPM in Sonic Pi otherwise the slicing will sound totally off. For example, try swapping `:loop_mika` with the `loop_amen` sample to hear how bad this can sound when the tempos don’t align.

## Mudar a Velocidade (Rate)

As we have already seen, changing the default BPM with `use_bpm` will make all the sleep times and synth envelope durations grow or shrink to match the beat. The `:slicer` FX honours this too, as the `phase:` opt is actually measured in beats not seconds. We can therefore fix the issue with `loop_amen` above by changing the BPM to match the sample:

    sample :loop_amen

## Bringing it all together

Let’s apply all these ideas into a final example that only uses the `:slicer` FX to create an interesting combination. Go ahead, start changing it and make it into your own piece!

    sample :guit_em9, rate: 0.5

# - Programar em tempo Real

Last month we took a look at five important techniques for mastering live coding - in other words, we explored how we could use Sonic Pi to approach code in the same way we would approach a musical instrument. One of the important concepts that we discussed was practice. This month we’re going to take a deeper dive into understanding why live coding practice is important and how you might start.

## Practice regularly

The most important piece of advice is to make sure you practice regularly. As a rule I typically practice for 1-2 hours a day, but 20 mins is just fine when you’re starting out. Little but often is what you’re aiming for - so if you can only manage 10 minutes, that’s a great start.

Practice tip #1 - start to develop a practice routine. Find a nice time in the day that works for you and try and practice at that time as many days of the week as you can. Before long you’ll be looking forward to your regular session.

## Learn to Touch Type

If you watch a professional musician performing on stage you’ll likely notice a few things. Firstly, when they play they don’t stare at their instrument. Their fingers, arms and bodies know which keys to press, strings to pluck or drums to hit without them having to think about it too much. This is known as “muscle memory” and although it might sound like something only professionals can do - it’s just the same as when you first learned to walk or ride a bike - practicing through repetition. Live coders use muscle memory to free their minds from having to think about where to move their fingers so they can focus on the music. This is called touch-typing - typing without having to look at the keyboard.

Practice tip #2 - learn how to touch type. There are many apps, websites and even games which can help you achieve this. Find one you like the look of and stick at it until you can code without looking down.

## Code whilst standing

The body of a musician is conditioned for playing their instrument. For example, a trumpet player needs to be able to blow hard, a guitar player needs to be able to grip the fretboard with strength and a drummer needs to be able to continually hit the drums for long periods of time. So, what’s physical about live coding? Just like DJs, live coders typically perform whilst standing up and some even dance whilst they code! If you practice live coding whilst sitting at a desk and then have to get up and stand at a gig, you’ll likely find the difference very difficult and frustrating.

Practice tip #3 - stand whilst you practice. The easiest way to do this is to use a standing height desk. However, if like me you don’t have one at home, there’s a couple of low-fi options. The approach I take is to use an ironing board which happens to work rather well. Another is to stack some boxes or large books on a normal desk and place your keyboard on top of that. Also, make sure you stretch before you start practicing and try and dance a little during the session. Remember, nobody is watching you, so have fun and you’ll feel much more natural on stage.

## Practice setting up

Most instruments require some assembly and tuning before they can be played. Unless you’re a rockstar with a bus full of roadies, you’ll have to set up your own instrument before your gig. This is often a stressful time and it is easy for problems to occur. One way to help with this is to incorporate the setup process into your practice sessions.

Practice tip #4 - treat setting up as an important part of your practice. For example, have a box or bag that you can keep your Raspberry Pi and keyboard in etc. Before each practice session, take out all the parts, connect everything, and work through the boot process until you have Sonic Pi running and can make sounds. Once you’ve finished practicing, take the time to carefully pack everything away afterwards. This may take some time at first, but before long you’ll be able to setup and pack everything away incredibly quickly without having to think about it.

## Experiment Musically

Once you’ve set up and are ready to start making music, you might find yourself struggling to know where to start. One problem many people face is that they might have a good idea of the kinds of sounds they want to make, but are frustrated that they can’t produce them. Some people don’t even know what kind of sounds they want to make! The first thing to do is not to worry - this is very common and happens to every musician - even if they’ve been practicing for a long time. It is much more important to be making sounds you don’t like than not making any sounds at all.

Practice tip #5 - spend time making sounds and music you don’t like. Try to make time to explore new sounds and ideas. Don’t worry that it might sound terrible if it’s not the style you’re looking for. When you’re experimenting like this you increase the chance of stumbling over a sound or combination of sounds which you love! Even if 99% of the sounds you make are bad, that 1% might be the riff or intro to your new track. Forget the things you don’t like and remember the parts you do. This is even easier when you’re making music with code - just hit save!

## Hear the Code

rand

Practice tip #6 - write some code into Sonic Pi but don’t hit the Run button. Instead, try to imagine what sound it is going to produce. Then, hit Run, listen, and think about what you got right and what you didn’t. Keep repeating this until it become a natural part of your coding process. When I practice I normally have a good idea of what the code will sound like. However, I still am occasionally surprised, and then I’ll stop and spend some time thinking about why I was wrong. Each time this happens, I learn new tricks which allow me to express myself in new ways.

## Remove all distractions

A common problem when practicing is to become distracted with other things. Practicing is hard and requires real discipline regardless of the kind of music you’re making - from jazz to classical to EDM. If you’re struggling to get started or make progress, it’s often too easy to hop on social media, or look something up on the internet etc. If you’ve set yourself a target of 20 minutes of practice, it’s important to try and spend all that time being as productive as possible.

Practice tip #7 - before you start practicing remove as many distractions as possible. For example, disconnect from the internet, put your phone in another room and try to practice in a quiet place where you’re unlikely to be disturbed. Try to focus on coding music and you can return to your distractions when you’ve finished.

## Keep a practice diary

When you are practicing, you’ll often find your mind is full of new exciting ideas - new musical directions, new sounds to try out, new functions to write, etc. These ideas are often so interesting that you might stop what you’re doing and start working on the idea. This is another form of distraction!

Practice tip #8 - keep a practice diary by your keyboard. When you get an exciting new idea, temporarily pause your practice session, quickly jot the idea down, then forget about it and carry on practicing. You can then spend some quality time thinking about and working on your ideas after you’ve finished practicing.

## Bringing it all together

Try to establish a practice routine which incorporates as many of these ideas as possible. Try to keep the sessions as fun as possible but be aware that some practice sessions will be hard and feel a little like work. However, it will all be worth it once you’ve created your first piece or given your first performance. Remember, practice is the key to success!

# - Sample Stretching

When people discover Sonic Pi, one of the first things they learn is how simple it is to play pre-recorded sounds using the `sample` function. For example, you can play an industrial drum loop, hear the sound of a choir or even listen to a vinyl scratch all via a single line of code. However, many people don’t realise that you can actually vary the speed that the sample is played back at for some powerful effects and a whole new level of control over your recorded sounds. So, fire up a copy of Sonic Pi and let’s get started stretching some samples!

## Samples

To modify the playback rate of a sample we need to use the `rate:` opt:

    sample :guit_em9, rate: 0.5

If we specify a `rate:` of `1` then the sample is played back at the normal rate. If we want to play it back at half speed we simply use a `rate:` of `0.5`:

    sample :guit_em9, rate: 0.5

escolhe

## Samples

In addition to making the sound longer and lower using a small rate, we can use higher rates to make the sound shorter and higher. Let’s play with a drum loop this time. First, take a listen to how it sounds at the default rate of `1`:

    sample :loop_amen, rate: -1

Now, let’s speed it up a little:

    sample :loop_amen, rate: 1.5

Ha! We just moved musical genres from old-skool techno to jungle. Notice how the pitch of each drum hit is higher as well as how the whole rhythm speeds up. Now, try even higher rates and see how high and short you can make the drum loop. For example, if you use a rate of `100`, the drum loop turns into a click!

## Reverse Gear

Now, I’m sure many of you are thinking the same thing right now… “what if you use a negative number for the rate?”. Great question! Let’s think about this for a moment. If our `rate:` opt signifies the speed with which the sample is played back, `1` being normal speed, `2` being double speed, `0.5` being half speed, `-1` must mean backwards! Let’s try it on a snare. First, play it back at the normal rate:

    sample :elec_filt_snare, rate: 1

Porreiro! Toca em sentido contrário!

    sample :elec_filt_snare, rate: -1

Of course, you can play it backwards twice as fast with a rate of `-2` or backwards at half speed with a rate of `-0.5`. Now, play around with different negative rates and have fun. It’s particularly amusing with the `:misc_burp` sample!

## Sample, Rate and Pitch

One of the effects of rate modification on samples is that faster rates result in the sample sounding higher in pitch and slower rates result in the sample sounding lower in pitch. Another place you may have heard this effect in every day life is when you’re cycling or driving past a beeping pedestrian crossing - as you’re heading towards the sound source the pitch is higher than when you’re moving away from the sound - the so-called Doppler effect. Why is this?

Let’s consider a simple beep which is represented by a sine wave. If we use an oscilloscope to plot a beep, we’ll see something like Figure A. If we plot a beep an octave higher, we’ll see Figure B and an octave lower will look like Figure C. Notice that the waves of higher notes are more compact and the waves of lower notes are more spread out.

A sample of a beep is nothing more than a lot of numbers (x, y, coordinates) which when plotted onto a graph will re-draw the original curves. See figure D where each circle represents a coordinate. To turn the coordinates back into audio, the computer works through each x value and sends the corresponding y value to the speakers. The trick here is that the rate at which the computer works through the x numbers does not have to be the same as the rate with which they were recorded. In other words, the space (representing an amount of time) between each circle can be stretched or compressed. So, if the computer walks through the x values faster than the original rate, it will have the effect of squashing the circles closer together which will result in a higher sounding beep. It will also make the beep shorter as we will work through all the circles faster. This is shown in Figure E.

Finally, one last thing to know is that a mathematician called Fourier proved that any sound is actually lots and lots of sine waves all combined together. Therefore, when we compress and stretch any recorded sound we’re actually stretching and compressing many sine waves all at the same time in exactly this manner.

## Pitch Bending

As we’ve seen, using a faster rate will make the sound higher in pitch and a slower rate will make the sound lower in pitch. A very simple and useful trick is to know that doubling the rate actually results in the pitch being an octave higher and inversely halving the rate results in the pitch being an octave lower. This means that for melodic samples, playing it alongside itself at double/half rates actually sounds rather nice:

    sample :bass_trance_c, rate: 1
    sample :bass_trance_c, rate: 2
    sample :bass_trance_c, rate: 0.5

However, what if we just want to alter the rate such that the pitch goes up one semitone (one note up on a piano)? Sonic Pi makes this very easy via the `rpitch:` opt:

    sample :bass_trance_c
    sample :bass_trance_c, rpitch: 3
    sample :bass_trance_c, rpitch: 7

If you take a look at the log on the right, you’ll notice that an `rpitch:` of `3` actually corresponds to a rate of `1.1892` and a `rpitch:` of `7` corresponds to a rate of `1.4983`. Finally, we can even combine `rate:` and `rpitch:` opts:

    sample :ambi_choir, rate: 0.25, rpitch: 3
    sleep 3
    sample :ambi_choir, rate: 0.25, rpitch: 5
    sleep 2
    sample :ambi_choir, rate: 0.25, rpitch: 6
    sleep 1
    sample :ambi_choir, rate: 0.25, rpitch: 1

## Bringing it all together

Let’s take a look at a simple piece which combines these ideas. Copy it into an empty Sonic Pi buffer, hit play, listen to it for a while and then use it as a starting point for your own piece. See how much fun it is to manipulate the playback rate of samples. As an added exercise try recording your own sounds and play around with the rate to see what wild sounds you can make.

    sample :guit_em9

# - Additive Synthesis

This is the first of a short series of articles on how to use Sonic Pi for sound design. We’ll be taking a quick tour of a number of different techniques available for you to craft your own unique sound. The first technique we’ll look at is called additive synthesis. This may sound complicated - but if we expand each word slightly the meaning pops right out. Firstly, additive means a combination of things and secondly synthesis means to create sound. Additive synthesis therefore means nothing more complicated than combining existing sounds to create new ones. This synthesis technique dates back a very long time - for example, pipe organs in the middle ages had lots of slightly different sounding pipes which you could enable or disable with stops. Pulling out the stop for a given pipe ‘added it to the mix’ making the sound richer and more complex. Now, let’s see how we can pull out all the stops with Sonic Pi.

## Simple Combinations

Let’s start with the most basic sound there is - the humble pure-toned sine wave:

    synth :sine, note: :d3

Now, let’s see how this sounds combined with a square wave:

    synth :sine, note: :d3
    synth :square, note: :d3

Notice how the two sounds combine to form a new, richer sound. Of course, we don’t have to stop there, we can add as many sounds as we need. However, we need to be careful with how many sounds we add together. Just like when we mix paints to create new colours, adding too many colours will result in a messy brown, similarly - adding too many sounds together will result in a muddy sound.

## Blending

Let’s add something to make it sound a little brighter. We could use a triangle wave at an octave higher (for that high bright sound) yet only play it at amp `0.4` so it adds something extra to the sound rather than taking it over:

    synth :sine, note: :d3
    synth :square, note: :d3
    synth :tri, note: :d4, amp: 0.4

Now, try creating your own sounds by combining 2 or more synths at different octaves and amplitudes. Also, note that you can play around with each synth’s opts to modify each source sound before it is mixed in for even more combinations of sounds.

## Detuning

So far, when combining our different synths we’ve used either the same pitch or switched octave. How might it sound if we didn’t stick to octaves but instead chose a slightly higher or lower note? Let’s try it:

    detune = 0.7
    synth :square, note: :e3
    synth :square, note: :e3 + detune

If we detune our square waves by 0.7 notes we hear something that perhaps doesn’t sound in tune or correct - a ‘bad’ note. However, as we move closer to 0 it will sound less and less out of tune as the pitches of the two waves get closer and more similar. Try it for yourself! Change the `detune:` opt value from `0.7` to `0.5` and listen to the new sound. Try `0.2`, `0.1`, `0.05`, `0`. Each time you change the value, take a listen and see if you can hear how the sound is changing. Notice that low detune values such as `0.1` produce a really nice ‘thick’ sound, with both slightly different pitches interacting with each other in interesting, often surprising, ways.

‘:dsaw’

## Amplitude

Another way we can finely craft our sound is to use a different envelope and options for each synth trigger. For example this will allow you to make some aspects of the sound percussive and other aspects ring out for a period of time.

    detune = 0.1
    synth :square, note: :e1, release: 2
    synth :square, note: :e1 + detune, amp: 2, release: 2
    synth :gnoise, release: 2, amp: 1, cutoff: 60
    synth :gnoise, release: 0.5, amp: 1, cutoff: 100
    synth :noise, release: 0.2, amp: 1, cutoff: 90

In the example above I have mixed in a noisy percussive element to the sound along with some more persistent background rumbling. This was achieved firstly by using two noise synths with middling cutoff values (`90` and `100`) using short release times along with a noise with a longer release time but with a low cutoff value (which makes the noise less crisp and more rumbly.)

## Bringing it all together

Let’s combine all these techniques to see if we can use additive synthesis to re-create a basic bell sound. I’ve broken this example into four sections. Firstly we have the ‘hit’ section which is the initial onset part of the bell sound - so uses a short envelope (e.g. a `release:` of around `0.1`). Next we have the long ringing section in which I’m using the pure sound of the sine wave. Notice that I’m often increasing the note by roughly `12` and `24` which are the number of notes in one and two octaves. I have also thrown in a couple of low sine waves to give the sound some bass and depth. Finally, I used `define` to wrap my code in a function which I can then use to play a melody. Try playing your own melody and also messing around with the contents of the `:bell` function until you create your own fun sound to play with!

    define :bell do |n|
      # Triangle waves for the 'hit'
      synth :tri, note: n - 12, release: 0.1
      synth :tri, note: n + 0.1, release: 0.1
      synth :tri, note: n - 0.1, release: 0.1
      synth :tri, note: n, release: 0.2
      # Sine waves for the 'ringing'
      synth :sine, note: n + 24, release: 2
      synth :sine, note: n + 24.1, release: 2
      synth :sine, note: n + 24.2, release: 0.5
      synth :sine, note: n + 11.8, release: 2
      synth :sine, note: n, release: 2
      # Low sine waves for the bass
      synth :sine, note: n - 11.8, release: 2
      synth :sine, note: n - 12, release: 2
    end
    # Play a melody with our new bell!
    bell :e3
    sleep 1
    bell :c2
    sleep 1
    bell :d3
    sleep 1
    bell :g2

# - Subtractive Synthesis

This is the second in a series of articles on how to use Sonic Pi for sound design. Last month we looked at additive synthesis which we discovered was the simple act of playing multiple sounds at the same time to make a new combined sound. For example we could combine different sounding synths or even the same synth at different pitches to build a new complex sound from simple ingredients. This month we’ll look at a new technique commonly called subtractive synthesis which is simply the act of taking an existing complex sound and removing parts of it to create something new. This is a technique which is commonly associated with the sound of analog synthesisers of the 1960s and 1970s but also with the recent renaissance of modular analog synths through popular standards such as Eurorack.

Despite this sounding like a particularly complicated and advanced technique, Sonic Pi makes it surprisingly simple and easy - so let’s dive right in.

## Complex Source Signal

For a sound to work well with subtractive synthesis, it typically needs to be fairly rich and interesting. This doesn’t mean we need something hugely complex - in fact, just a standard `:square` or `:saw` wave will do:

    synth :saw, note: :e2, release: 4

Notice that this sound is already pretty interesting and contains many different frequencies above `:e2` (the second E on a piano) which add to create the timbre. If that didn’t make much sense to you, try comparing it with the `:beep`:

    synth :beep, note: :e2, release: 4

As the `:beep` synth is just a sine wave, you’ll hear a much purer tone and only at `:e2` and none of the high crispy/buzzy sounds which you heard in the `:saw`. It’s this buzziness and variation from a pure sine wave that we can play with when we use subtractive synthesis.

## Filtros

Once we have our raw source signal, the next step is to pass it through a filter of some kind which will modify the sound by removing or reducing parts of it. One of the most common filters used for subtractive synthesis is something called a low pass filter. This will allow all the low parts of the sound through but will reduce or remove the higher parts. Sonic Pi has a powerful yet simple to use FX system that includes a low pass filter, called `:lpf`. Let’s play with it:

    with_fx :lpf, cutoff: 100 do
      synth :saw, note: :e2, release: 4
    end

If you listen carefully you’ll hear how some of that buzziness and crispiness has been removed. In fact, all the frequencies in the sound above note `100` have been reduced or removed and only the ones below are still present in the sound. Try changing that `cutoff:` point to lower notes, say `70` and then `50` and compare the sounds.

Of course, the `:lpf` isn’t the only filter you can use to manipulate the source signal. Another important FX is the high pass filter referred to as `:hpf` in Sonic Pi. This does the opposite to `:lpf` in that it lets the high parts of the sound through and cuts off the low parts.

    with_fx :hpf, cutoff: 90 do
      synth :saw, note: :e2, release: 4
    end

Notice how this sounds much more buzzy and raspy now that all the low frequency sounds have been removed. Play around with the cutoff value - notice how lower values let more of the original bass parts of the source signal through and higher values sound increasingly tinny and quiet.

## Low Pass Filter

‘:prophet’

## Filter Modulation

So far we’ve just produced fairly static sounds. In other words, the sound doesn’t change in any way for the entirety of its duration. Often you might want some movement in the sound to give the timbre some life. One way to achieve this is via filter modulation - changing the filter’s options through time. Luckily Sonic Pi gives you powerful tools to manipulate an FX’s opts through time. For example, you can set a slide time to each modulatable opt to specify how long it should take for the current value to linearly slide to the target value:

    with_fx :lpf, cutoff: 50 do |fx|
      control fx, cutoff_slide: 3, cutoff: 130
      synth :prophet, note: :e2, sustain: 3.5
    end

Let’s take a quick look at what’s going on here. Firstly we start an `:lpf` FX block as normal with an initial `cutoff:` of a low `50`. However, the first line also finishes with the strange `|fx|` at the end. This is an optional part of the `with_fx` syntax which allows you to directly name and control the running FX synth. Line 2 does exactly this and controls the FX to set the `cutoff_slide:` opt to 3 and the new target `cutoff:` to be `130`. The FX will now start sliding the `cutoff:` opt’s value from `50` to `130` over a period of 3 beats. Finally we also trigger a source signal synth so we can hear the effect of the modulated low pass filter.

## Bringing it all together

This is just a very basic taster of what’s possible when you use filters to modify and change a source sound. Try playing with Sonic Pi’s many built-in FX to see what fun sounds you can design. If your sound feels too static, remember you can start modulating the options to create some movement.

Let’s finish by designing a function which will play a new sound created with subtractive synthesis. See if you can figure out what’s going on here - and for the advanced Sonic Pi readers out there - see if you can work out why I wrapped everything inside a call to `at` (please send answers to @samaaron on Twitter).

    rrand

# - Creative coding in the classroom with Sonic Pi

(This article was published in issue 9 of the Hello World Magazine)

Code is one of the most creative media that humans have created. The initially obscure symbols of parentheses and lambdas are not just deeply rooted in science and mathematics, they are the closest we have managed to get to casting the same kind of magical spells as Gandalf and Harry Potter. I believe that this provides a powerful means of engagement in our learning spaces. Through the magic of code we are able to conjure up individually meaningful stories and learning experiences.

We are surrounded by magical experiences. From the sleight of hand of a stage magician making the ball disappear into thin air, to the wonder of seeing your favourite band perform on a big stage. It is these “wow” moments that inspire us to pick up a magic book and learn the French Drop or to start jamming power chords on an old guitar. How might we create similarly deep and lasting senses of wonder that will motivate people to practice and learn the fundamentals of programming?

## Musical Engines and Notation

The histories of music and computers have been intricately woven together since the inception of computing machines, or “engines” as Charles Babbage’s powerful analytical engine was called. Back in 1842 the Mathematician Ada Lovelace, who worked very closely with Babbage, saw the creative potential of these engines. Whilst these first engines had originally been designed to accurately solve hard maths problems, Ada dreamt about making music with them:

”..the engine might compose elaborate and scientific pieces of music of any degree of complexity or extent.” Ada Lovelace, 1842.

Of course, today in 2019 much of our music, regardless of genre, has either been composed, produced or mastered with a digital computer. Ada’s dream came true. It is even possible to trace the history back even further. If you see coding as the art of writing sequences of special symbols that instruct a computer to do specific things, then musical composition is a very similar practice. In Western music, the symbols are black dots positioned on a stave of lines that tell the musician which notes to play and when. Intriguingly, if we trace the roots of Western music notation back to the Italian Benedictine monk, Guido d’Arezzo, we find that the dots and lines system that modern orchestras use is just one of a number of notation systems he worked on. Some of the others were much closer to what we might now see as code.

In education, magical meaningful experiences with computers and programming languages have been explored since the late ’60s. Computer education pioneers Seymour Papert, Marvin Minsky and Cynthia Solomon explored simple Lisp-based languages that moved pens over large pieces of paper. With just a few simple commands it was possible to program the computer to draw any picture. They even experimented by extending their Logo language from drawing to music. Papert wrote about learning through experiencing the reconstruction of knowledge rather than its transmission. Getting people to play with things directly was an important part of his group’s work.

## Sonic Pi Performances

Live Coding

Sonic Pi has been used to perform in a wide range of venues such as school halls, nightclubs, outdoor stages at musical festivals, college chapels and prestigious music venues. For example the amazing Convo project which brought 1000 children together in the Royal Albert Hall to perform an ambitious new composition by composer Charlotte Harding. The piece was written for traditional instruments, choirs, percussion and Sonic Pi code. The pop-artist Jylda also performed with Sonic Pi in the Sage Gateshead for the Thinking Digital Conference, where she created a unique live-coded improvised remix of her song Reeled.

Sonic Pi used as one of the instruments as part of Convo at the Royal Albert Hall. Photo credit: Pete Jones.

## Live coding in the classroom

Sonic Pi is a code-based music creation and performance tool that builds on all of these ideas. Unlike the majority of computing education software, it is both simple enough to use for education and also powerful enough for professionals. It has been used to perform in international music festivals, used to compose in a range of styles from classical, EDM and heavy metal, and was even reviewed in the Rolling Stone magazine. It has a diverse community of over 1.5 million live coders with a variety of backgrounds all learning and sharing their ideas and thoughts through the medium of code. It is free to download for Mac, PC and Raspberry Pi and includes a friendly tutorial that assumes you know nothing about either code or music.

Sonic Pi was initially conceived as a response to the UK’s newly released Computing curriculum in 2014. The goal was to find a motivating and fun way to teach the fundamentals of programming. It turns out that there is a lot in common and it’s huge fun to explain sequencing as melody, iteration as rhythm, conditionals as musical variety. I developed the initial designs and first iterations of the platform with Carrie Anne Philbin, who brought a teacher’s perspective to the project. Since then, Sonic Pi has undergone iterative improvements thanks to the feedback gained from observing learners and collaborating directly with educators in the classroom. A core design philosophy was to never add a feature that couldn’t be easily taught to a 10 year old child. This meant that most ideas had to be heavily refined and reworked until they were simple enough. Making things simple whilst keeping them powerful continues to be the hardest part of the project.

In order to provide the magical motivation, Sonic Pi’s design was never limited to a pure focus on education. Ideally there would be famous musicians and performers using Sonic Pi as a standard instrument alongside guitars, drums, vocals, synths, violins, etc. These performers would then act as motivational role models demonstrating the creative potential of code. For this to be possible sufficient focus and effort therefore had to be placed on making it a powerful instrument whilst still keeping it simple enough for 10 year olds to pick up. In addition to educators, I also worked directly with a variety of different artists in classrooms, art galleries, studios and venues in the early stages of Sonic Pi’s development. This provided essential feedback which enabled Sonic Pi to grow and ultimately flourish as a tool for creative expression.

There were a number of exciting and unexpected side effects of this dual focus on education and professional musicians. Many of the features are beneficial to both groups. For example, a lot of effort has been put into making error messages more friendly and useful (rather than being a huge complicated mess of jargon). This turns out to be very useful when you write a bug while performing in front of thousands of people. Additionally, functionality such as playing studio quality audio samples, adding audio effects, providing access to live audio from the microphone all turn out to make the learning experience more fun, rewarding and ultimately meaningful.

The Sonic Pi community continues to grow and share amazing code compositions, lesson plans, musical algorithms, and much more. Much of this happens on our friendly forum in_thread (in-thread.sonic-pi.net) which is home to a very diverse group of people that includes educators, musicians, programmers, artists and makers. It is a real joy to see people learn to use code to express themselves in new ways and for that in turn to inspire others to do the same.

# - Some fun capabilities

From a Computer Science perspective, Sonic Pi provides you with the building blocks to teach you the basics as found in the UK’s curriculum such as sequencing, iteration, conditionals, functions, data structures, algorithms, etc. However, it also builds on a number of important and relevant concepts which have become adopted in mainstream industry such as concurrency, events, pattern matching, distributed computing and determinism - all whilst keeping things simple enough to explain to a 10 year old child.

Getting started is as simple as:

    play 70

A melody can be constructed with one more command, sleep:

    play 72
    sleep 0.5
    play 75
    sleep 0.5
    play 79

In this example, we play the note 70 (roughly the 70th note on a piano), wait for 1 second, play note 72, wait for half a second and then play note 75. What’s interesting here is that with just two commands we have access to pretty much all of Western notation (which notes to play and when) and learners can code any melody they’ve ever heard. This leads to huge variety in expressive outcomes whilst focussing on the same computing concept: sequencing in this case.

Taking ideas from the professional music world, we can also play back any recorded sound. Sonic Pi can play any audio file on your computer but also has a number of sounds built-in to make things easy to get started:

    sample :loop_amen

This code will play back the drum break which was a pillarstone to early hip-hop, Drum and Bass and Jungle. For example, a number of early hip-hop artists played this drum break back at half speed to give it a more laid-back feeling:

    sample :loop_amen, rate: 0.5

In the 90s a number of music scenes burst out of new technology which enabled artists to take drum breaks like this apart and reassemble in a different order. For example:

    sample :loop_amen

rand

# - Conhecimento essencial

Esta secção descreve algum conhecimento útil - aliás essencial para retirares o máximo da tua experiência com o Sonic Pi.

Falaremos de como podes tiras partido de muitos atalhos de teclado disponíveis para ti, como partilhar o teu trabalho e algumas dicas sobre performance no Sonic Pi.

# 10.1 - Usando atalhos

O Sonic Pi é tanto um instrumento como um ambiente de codificação. Atalhos podem fazer com que tocar o Sonic Pi seja muito mais eficiente e natural - especialmente se estiveres a tocar em frente a uma audiência.

Muito do Sonic Pi pode ser controlado através do teclado. Quanto mais familiaridade tiveres trabalhando e actuando com o Sonic Pi mais tendência terás de usar atalhos. Eu pessoalmente uso o teclado (eu recomendo considerares aprenderes também) sinto-me frustrado quando tenho que alcançar o rato pois isso atrasa-me. Por isso uso todos estes atalhos de uma forma bastante regular!

Assim, se aprenderes os atalhos, aprenderás a usar o teclado de forma efectiva e estarás a fazer live coding como um profissional em tempo record.

No entanto, não tentes aprende-los todos de uma só vez, apenas tenta lembrar-te dos que mais usas e continua a adicionar mais à medida que os praticas.

## Consistência entre plataformas

Imagina que estas a aprender o clarinete. Esperas que todos os clarinetes tenham os mesmos controles e botões. Se não tiverem, terás um tempo difícil a mudar entre vários clarinetes ou ficaras retido em usar só um.

Unfortunately there are a number of standards for shortcuts with macOS and Windows being two of the major styles and other more esoteric editors such as Emacs offering other approaches. You can currently choose between one of these three styles using the menu `IO -> Shortcut Mode`. You can therefore switch between a Windows and a macOS machine and keep your shortcuts consistent.

## Control e Meta

A key part of the notion of consistency is the naming of shortcuts. In Sonic Pi we use the names Control and Meta to refer to the two main combination keys. On all platforms Control is the same. However, on Linux and Windows, Meta is actually the Alt key while on Mac Meta is the Command key. For consistency we’ll use the term Meta - just remember to map that to the appropriate key on your operating system.

## Abreviações

Para ajudar a manter as coisas simples e legíveis, usaremos as abreviaturas C- para Control mais uma outra tecla e M- para Meta mais outra tecla. Por exemplo, se um atalho requer que primas simultaneamente Meta e r escreveremos como M-r. O - significa apenas “ao mesmo tempo”.

Os seguintes são alguns dos atalhos que considero mais úteis.

## Parando e iniciando

Em vez de alcançar o rato cada vez que se quer correr o código, podes simplesmente pressionar `M-r`. Da mesma forma podes parar o código carregando `M-s`.

## Navegação

Fico mesmo perdido sem os atalhos de navegação. Recomendo vivamente que passes algum tempo a aprende-los. Estes atalhos trabalhas extremamente bem quando aprendes a teclar sem mexer as mãos pois eles usam letras standard e não requerem que mexas as mãos para alcançar o rato ou as setas do teu teclado.

For example, if you’re in Emacs Live short cut mode, You can move to the beginning of the line with `C-a`, the end of the line with `C-e`, up a line with `C-p`, down a line with `C-n`, forward a character with `C-f`, and back a character with `C-b`. You can even delete all the characters from the cursor to the end of the line with `C-k`. Other modes will have their own shortcuts which can be easily discovered in the app menu.

## Código limpo

Para auto-alinhar o teu código simplesmente carrega `M-m`.

## Sistema de ajuda

Para comutar o sistema de ajuda podes premir `M-i`- No entanto, um atalho muito mais útil é `C-i` em que irá verificar a palavra por baixo do cursor e mostra os documentos se descobrir algo. Ajuda instantânea!

Para uma listagem completa vê a secção 10.2 com uma folha de ajuda de atalhos.

# 10.2 - Folha de ajuda de atalhos

The following is a summary of the main Emacs Live shortcuts available within Sonic Pi. Please see Section B.1 for motivation and background.

## Convenções

Nesta lista, usamos a seguinte convenção (onde Meta ou é o Alt em Windows/Linux ou o Cmd no Mac):

- `C-a` significa carregar na tecla Control e depois carrega a tecla a estando as duas pressionadas ao mesmo tempo, depois libertando.
- `M-r` significa pressionar a tecla Meta e depois pressionar a tecla r ao mesmo tempo, depois libertando.
- `S-M-z` significa presionar a tecla Shift, depois a tecla Meta, e finalmente a tecla z todas ao mesmo tempo, depois libertando.
- `C-M-f` significa premir a tecla Control, e depois premir a tecla Meta, finalmente a tecla f todas ao mesmo tempo, depois libertando.

## Manipulação da Aplicação principal

- `M-r` - Correr código
- `M-s` - Parar código
- `M-i`- Comutar o sistema de ajuda
- `M-p`- Comutar preferencias
- `M-{` - Mudar para a buffer da esquerda
- `M-}` - Mudar para a buffer da direita
- `S-M-0` - Switch to buffer 0
- `S-M-1` - Switch to buffer 1
- …
- `S-M-9` - Switch to buffer 9
- `M-+` - Aumentar tamanho do texto da buffer corrente
- `M--` - Reduzir o tamanho de texto na corrente buffer

## Selecionar/copiar/colar

- `M-a` - Selecionar tudo
- `M-c`- Copiar selecção para colar na buffer
- `M-]` - Copiar seleção para colar no buffer
- `M-x` - Cortar seleção para colar na buffer
- `C-]` - Cortar seleção para a colar na buffer
- `C-k`- Cortar até ao fim da linha
- `M-v`- Colar para o editor
- `C-y` - Colar para o editor
- `C-SPACE` - Colocar marca. A navegação irá agora manipular a região sublinhada. Usar `C-g`para escapar.

## Manipulação de texto

- `M-m` - Alinhar todo o texto
- `Tab`- Alinha a corrente linha ou seleção (ou escolhe autocompletion)
- `C-l` - Centra o editor
- `M-/` - Comuta os comentários da linha actual ou seleção
- `C-t` - Transpõe/troca caracteres
- `M-u`- Converte a próxima palavra (ou selecção) para maiúsculas.
- `M-l` - Converte a próxima palavra (ou selecção) para minúsculas.

## Navegação

- `C-a` - Mover para o inicio da linha
- `C-e` - Mover para o final da linha
- `C-p` - Mover para a linha anterior
- `C-n` - Mover para a próxima linha
- `C-f` - Mover para a frente um caractere
- `C-b` - Mover para trás um caractere
- `M-f` - Mover para a frente uma palavra
- `M-b`- Mover para trás uma palavra
- `C-M-n` - Mover uma linha ou selecção para baixo
- `C-M-p` - Mover linha ou selecção para cima
- `S-M-u` - Mover para cima 10 linhas
- `S-M-d`- Mover para baixo 10 linhas
- `M-<` - Mover para o inicio da buffer
- `M->` - Mover para o final da buffer

## Remoção

- `C-h` - Remove o caractere anterior
- `C-d` - Remove o proximo caractere

## Características avançadas do editor

- `C-i` - Mostra documentação sobre a palavra por baixo do cursor
- `M-z` - Undo
- `S-M-z` - Refazer
- `C-g` - Escapar
- `S-M-f` - comutar ecrã total
- `S-M-b` - Comutar visibilidade dos botões
- `S-M-l` - Comuta visibilidade do registo
- `S-M-m` - Comuta entre o modo claro/escuro
- `S-M-s`- Salva o conteúdo de uma buffer para um ficheiro
- `S-M-o` - Carrega o conteúdo de uma buffer para um ficheiro

# 10.3 - Partilha

No Sonic Pi é tudo sobre partilha e aprendendo uns com os outros.

Depois de aprenderes a codificar musica, partilhar as tuas composições é tão simples como mandar um email contendo o teu código. Por favor partilha o teu código com outro para que eles possam aprender com o teu trabalho ou mesmo usar num novomash-up.

Se estás inseguro da melhor maneira de partilhar o teu trabalho com outros eu recomendo colocar o código no [GitHub] (https://github.com) e a tua música no SoundCloud. Dessa forma poderás facilmente chegar a uma grande audiência.

## Código -> GitHub

GitHub é um site para trabalhar e partilhar código. É usado por criadores bem como artistas para partilhar e colaborar no código. A maneira mais simples de partilhar uma nova peça de código (ou mesmo uma peça inacabada) é criar um Gist. Um Gist é uma maneira simples de enviar o teu código numa maneira simples para os outros o verem, copiarem e partilharem.

## Audio -> SoundCloud

Uma outra maneira importante de partilhares o teu trabalho é gravares o audio e o enviares para o SoundCloud. Depois de enviares a tua peça, outro utilizadores podem comentar e discutir o teu trabalho. Eu recomendo também colocares uma ligação para o Gist do teu código na descrição da faixa.

Para gravares o teu trabalho, clica no botão `Rec` na barra de ferramentas e a gravação começa imediatamente. Clica `Run` para começar a correr o teu código se não estiver já a correr. Quando estiver pronta a gravação, clica no botão `Rec` a piscar a vermelho outra vez, e será pedido para dar o nome ao ficheiro. A gravação será salva como ficheiro WAV, que pode ser editado e convertido para MP3 por diversos programas grátis (experimenta o Audacity por exemplo).

## Esperança

Eu encorajo-te a partilhares o teu trabalho e tenho esperança que todos aprendamos uns com os outros truques novos para o Sonic Pi. Estou mesmo excitado com o que tens para me mostrar.

# 10.4 - Performance

Um dos aspectos mais excitantes no Sonic Pi é que permite usares código como um instrumento musical. Isto significa que escrever código ao vivo pode agora ser visto como uma performance musical.

Chamamos a isso Live Coding.

## Mostra o teu ecrã

Quando codifica ao vivo recomendo mostrar o seu ecrã. De outro modo é como tocar guitarra, mas esconder os seus dedos e as cordas. Quando pratico em casa uso o Raspberry Pi e um pequeno projetor na minha sala de estar. Poderá usar uma Tv ou um projetor para dares um espetáculo. Experimente, é muito divertido.

## Forma uma banda

Don’t just play on your own - form a live coding band! It’s a lot of fun jamming with others. One person could do beats, another ambient background, etc. Use the `live_audio` functionality to combine code with traditional instruments such as a guitar or a microphone.

See what interesting combinations of sounds you can create with code.

## TOPLAP

Live coding não é uma coisa completamente nova . Um pequeno número de pessoas têm estado a fazer durante alguns anos, tipicamente usando sistemas que eles proprios criaram. Um excelente sitio para descobrir mais sobre live coders e sistemas é TOPLAP.

## Algorave

Outro grande recurso para explorar o mundo do live coding é Algorave. Onde podes descobrir tudo sobre um tipo especifico de live coding para a criação de musica em clubes nocturnos.