BabyGnusbuino code examples
setup()
best to set the pins used for programming via USB again as outputs and low, before starting your program
void setup()
{ // Set pins
pinMode(0, OUTPUT);
pinMode(1, OUTPUT);
pinMode(2, OUTPUT);
digitalWrite(0, LOW);
digitalWrite(1, LOW);
digitalWrite(2, LOW);
}
PWM Heartbeat
/*
babygnusbuino: Fading
*/
int PWM_Pin = 0; // LED connected to digital pin 0
int PWM_value = 0;
int wait = 30;
volatile unsigned char e = 0;
void setup()
{
// Timer Init
TCCR0A = (0 << WGM02) | (0 << WGM01) | (0<< WGM00); // Normal Mode 000
TCCR0B = (0 << CS02) | (0 << CS01) | (1<< CS00); // Clock Select no prescaling 001
TIMSK = (1 << TOIE1); // Overflow interrupt is enabled
sei(); // set Global Interrupt Enable
// Set pins
pinMode(PWM_Pin, OUTPUT);
digitalWrite(0, LOW);
}
void loop()
{
for (int c = 0; c < 255; c++) {
PWM_value = c;
delay (wait);
}
for (int c = 255; c > 0; c--) {
PWM_value = c;
delay (wait);
}
}
//Overflow routine for Timer 1
ISR(TIM1_OVF_vect) {
if(e==255) {
e=0;
digitalWrite(PWM_Pin, HIGH);
}
if (PWM_value == e) {
digitalWrite(PWM_Pin, LOW);
}
e++;
}
3 Channels PWM
/*
babygnusbuino: PWM 3 Channels
*/
int PWM_Pin0 = 0; // LED connected to digital pin 0
int PWM_Pin1 = 1; // LED connected to digital pin 0
int PWM_Pin2 = 2; // LED connected to digital pin 0
int PWM_Pin0_value = 0;
int PWM_Pin1_value = 0;
int PWM_Pin2_value = 0;
int wait = 300;
volatile unsigned char e = 0;
void setup()
{
// Timer Init
TCCR0A = (0 << WGM02) | (0 << WGM01) | (0<< WGM00); // Normal Mode 000
TCCR0B = (0 << CS02) | (0 << CS01) | (1<< CS00); // Clock Select no prescaling 001
TIMSK = (1 << TOIE1); // Overflow interrupt is enabled
sei(); // set Global Interrupt Enable
// Set pins
pinMode(PWM_Pin0, OUTPUT);
pinMode(PWM_Pin1, OUTPUT);
pinMode(PWM_Pin2, OUTPUT);
}
void loop()
{
for (int c = 0; c < 255; c++) {
PWM_Pin2_value = c;
delay (wait);
}
for (int c = 255; c > 0; c--) {
PWM_Pin2_value = c;
delay (wait);
}
}
//Overflow routine for Timer 1
ISR(TIM1_OVF_vect) {
if(e==255) {
e=0;
digitalWrite(PWM_Pin0, HIGH);
digitalWrite(PWM_Pin1, HIGH);
digitalWrite(PWM_Pin2, HIGH);
}
if (PWM_Pin0_value == e) {
digitalWrite(PWM_Pin0, LOW);
}
if (PWM_Pin1_value == e) {
digitalWrite(PWM_Pin1, LOW);
}
if (PWM_Pin2_value == e) {
digitalWrite(PWM_Pin2, LOW);
}
e++;
}
RGB Led
// based largely on Atmel's AVR138: Low-Jitter Multi-Channel Software PWM Application Note:
// http://www.atmel.com/dyn/resources/prod_documents/doc8020.pdf
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#define CHMAX 3 // maximum number of PWM channels
#define PWMDEFAULT 0x00 // default PWM value at start up for all channels
#define RED_CLEAR (pinlevelB &= ~(1 << RED)) // map RED to PB4
#define GREEN_CLEAR (pinlevelB &= ~(1 << GREEN)) // map GREEN to PB3
#define BLUE_CLEAR (pinlevelB &= ~(1 << BLUE)) // map BLUE to PB0
//! Set bits corresponding to pin usage above
#define PORTB_MASK (1 << PB4 | 1 << PB3| 1 << PB0)
#define set(x) |= (1<<x)
#define clr(x) &=~(1<<x)
#define inv(x) ^=(1<<x)
#define RED PB4
#define GREEN PB3
#define BLUE PB0
#define LED_PORT PORTB
#define LED_DDR DDRB
// function prototypes
void delay_ms(uint16_t ms);
void init();
void blend(int r, int g, int b, int da);
// global variables
unsigned char compare[CHMAX];
volatile unsigned char compbuff[CHMAX];
unsigned long lfsr = 1;
unsigned char temp;
int main() {
init();
for (;;) { // forever
lfsr = (lfsr >> 1) ^ (-(lfsr & 1u) & 0xd0000001u); // taps 32 31 29 1
temp = (unsigned char) lfsr; // take lowest eight bits
temp = (unsigned char) (lfsr >> 24);
int r = temp & 0xff;
lfsr = (lfsr >> 1) ^ (-(lfsr & 1u) & 0xd0000001u); // taps 32 31 29 1
temp = (unsigned char) lfsr; // take lowest eight bits
temp = (unsigned char) (lfsr >> 24);
int g = temp & 0xff;
lfsr = (lfsr >> 1) ^ (-(lfsr & 1u) & 0xd0000001u); // taps 32 31 29 1
temp = (unsigned char) lfsr; // take lowest eight bits
temp = (unsigned char) (lfsr >> 24);
int b = temp & 0xff;
for (int a = 0; a < 64; a++) {
_delay_ms(20);
blend(r,g,b,a); // r g b alpha
}
}
}
void delay_ms(uint16_t ms) {
while (ms) {
_delay_ms(1);
ms--;
}
}
void init(void) {
// set the direction of the ports
LED_DDR set(RED);
LED_DDR set(GREEN);
LED_DDR set(BLUE);
unsigned char i, pwm;
CLKPR = (1 << CLKPCE); // enable clock prescaler update
CLKPR = 0; // set clock to maximum (= crystal)
pwm = PWMDEFAULT;
// initialise all channels
for(i=0 ; i<CHMAX ; i++) {
compare[i] = pwm; // set default PWM values
compbuff[i] = pwm; // set default PWM values
}
TIFR = (1 << TOV0); // clear interrupt flag
TIMSK = (1 << TOIE0); // enable overflow interrupt
TCCR0B = (1 << CS00); // start timer, no prescale
sei();
}
ISR (TIM0_OVF_vect) {
static unsigned char pinlevelB=PORTB_MASK;
static unsigned char softcount=0xFF;
PORTB = pinlevelB; // update outputs
if(++softcount == 0){ // increment modulo 256 counter and update
// the compare values only when counter = 0.
compare[0] = compbuff[0]; // verbose code for speed
compare[1] = compbuff[1];
compare[2] = compbuff[2];
pinlevelB = PORTB_MASK; // set all port pins high
}
// clear port pin on compare match (executed on next interrupt)
if(compare[0] == softcount) RED_CLEAR;
if(compare[1] == softcount) GREEN_CLEAR;
if(compare[2] == softcount) BLUE_CLEAR;
}
/*
blend color
@param r Red
@param g Green
@param b Blue
@param da Alpha: the factor how much the new color will be blended with the existing color. da = 0: no change, da = 255: new color will be set (no blending).
*/
void blend(int r, int g, int b, int da) {
// source alpha
int sa = 255 - da;
int tr = (sa * compbuff[0] + da * r) + 128;
int tg = (sa * compbuff[1] + da * g) + 128;
int tb = (sa * compbuff[2] + da * b) + 128;
compbuff[0] = ((tr>>8)+tr)>>8;
compbuff[1] = ((tg>>8)+tg)>>8;
compbuff[2] = ((tb>>8)+tb)>>8;
}
Flickering RGB Led
/*
flickering RGB LED!
*/
#include <avr/io.h>
#include <util/delay.h>
unsigned long lfsr = 1;
unsigned char temp;
/**
* delay
* @param ms duration in milliseconds
*/
void delay_ms(uint16_t ms)
{
for (uint16_t i = 0 ; i < ms ; i++) {
_delay_ms (1); // Loop delay
}
}
void setup()
{
DDRB = 0xff;
}
void loop() {
lfsr = (lfsr >> 1) ^ (-(lfsr & 1u) & 0xd0000001u); /* taps 32 31 29 1 */
temp = (unsigned char) lfsr; // take lowest eight bits
DDRB = ~temp; // declare those pins as output where temp is zero
PORTB = temp << 2; // give the value of 0 to the output pins
temp = (unsigned char) (lfsr >> 24);
_delay_loop_2(temp<<7);
delay_ms(100);
}
8-bit Noise
/* Pseudo-Random Bit Sequence Generator 2009-11-25 */
/* Copyright (c) 2009 John Honniball, Dorkbot Bristol */
/*
* For a discussion of PRBS generators, see The Art Of Electronics, by
* Horowitz and Hill, Second Edition, pages 655 to 660. For more info
* on Linear Feedback Shift Registers, see Wikipedia:
* http://en.wikipedia.org/wiki/Linear_feedback_shift_register
* For the actual shift register taps, refer to this article on noise
* generation for synthesisers:
* http://www.electricdruid.net/index.php?page=techniques.practicalLFSRs
*/
// Choose the same pin as the "Melody" example sketch
int speakerPin = 0;
int potiPin = A3;
unsigned int analogValue;
int samplingDelay;
unsigned long int reg;
void setup ()
{
// Serial setup for debugging only; slows down the program far too much
// for audible white noise
//Serial.begin (9600);
// Connect a piezo sounder between Ground and this pin
pinMode (speakerPin, OUTPUT);
// Arbitrary inital value; must not be zero
reg = 0x551155aaL;
}
void loop ()
{
unsigned long int newr;
unsigned char lobit;
unsigned char b31, b29, b25, b24;
// Extract four chosen bits from the 32-bit register
b31 = (reg & (1L << 31)) >> 31;
b29 = (reg & (1L << 29)) >> 29;
b25 = (reg & (1L << 25)) >> 25;
b24 = (reg & (1L << 24)) >> 24;
// EXOR the four bits together
lobit = b31 ^ b29 ^ b25 ^ b24;
// Shift and incorporate new bit at bit position 0
newr = (reg << 1) | lobit;
// Replace register with new value
reg = newr;
// Drive speaker pin from bit 0 of 'reg'
digitalWrite (speakerPin, reg & 1);
// Display 'reg' in the serial console for debugging only
// Serial.println (reg, HEX);
samplingDelay = 1 + (2*(analogRead(potiPin)>>0));
// Delay corresponds to 20kHz, but the actual frequency of updates
// will be lower, due to computation time and loop overhead
delayMicroseconds (samplingDelay);
// If the above delay is increased to a few tens of milliseconds,
// and the piezo sounder is replaced by an LED and a suitable series
// resistor, a randomly flashing light will result. Several LEDs
// could be driven from various bits of the shift register.
}
Crazy shit 8-bit symphony generator
/* Crazy shit 8-bit symphony generator */
/* */
/*
* inspired by:
* http://countercomplex.blogspot.com/2011/10/algorithmic-symphonies-from-one-line-of.html
*/
int speakerPin = 0;
int potiPin = A3;
long t = 0;
int v = 0;
int c = 0;
unsigned int analogValue;
void setup ()
{
// Connect a piezo sounder between Ground and this pin
pinMode (speakerPin, OUTPUT);
}
void loop ()
{
/*
for(t=0;;t++){
c = (analogRead(potiPin)>>3);
v=t*((t>>14|t>>(8))&c&t>>c);
analogWrite (speakerPin, v);
}
*/
for(t=0;;t++){
c = (analogRead(potiPin)>>4);
v=t*((t>>5|t>>11)&c&t>>c);
analogWrite (speakerPin, v);
}
/*
for(t=0;;t++){
c = (analogRead(potiPin)>>4);
v=t*((t>>7|t>>(c+4))&(c)&t>>(c*3));
analogWrite (speakerPin, v);
}
*/
}