From df602c7423b7add6d1ca0517b41bcd8c16e40322 Mon Sep 17 00:00:00 2001 From: sancho11 Date: Sat, 12 Jan 2019 02:05:43 -0600 Subject: [PATCH] Added the modifications to work on arduino UNO almost the same features for arduino MEGA, now for arduino UNO! --- .../processing_for_UNO_newmod.pde | 854 ++++++++++++++++++ Microcontroller_Code/UNO/UNO_newmod.ino | 139 +++ 2 files changed, 993 insertions(+) create mode 100644 Computer_Interface/processing_for_UNO_newmod.pde create mode 100644 Microcontroller_Code/UNO/UNO_newmod.ino diff --git a/Computer_Interface/processing_for_UNO_newmod.pde b/Computer_Interface/processing_for_UNO_newmod.pde new file mode 100644 index 0000000..198299c --- /dev/null +++ b/Computer_Interface/processing_for_UNO_newmod.pde @@ -0,0 +1,854 @@ + +import processing.serial.*; +import java.util.Arrays; +Serial p; + +//////////////////////////////////////////////// +/*--------------------SETUP-------------------*/ + +//uncomment the line where your arduino/STM32 is connected +//String LA_port = "/dev/ttyACM0"; //linux DFU +//String LA_port = "/dev/ttyUSB0"; //linux Serial +String LA_port = "COM3"; //windows + +final int baudrate = 115200; //check if it is the same in arduino + + +/*------------------END SETUP-----------------*/ +//////////////////////////////////////////////// + + +//colors: +int white = 255; +int black = 0; +int green = #00FF00; +int red = #FF0000; +int grey = 150; + + +// shift, reducer and millisecond view +float reducer = 1.0; +boolean milliseconds = true; +float xShift; + + +// start point in the processing window +float xEdge = 60; +float yEdge = 10; +float xEnd; +float oldxEnd; +float[] xPos = new float[16]; +float yBottom; +float yDiff; +float yPos = yEdge; +float ySave = yEdge; +boolean textCovered; +boolean drawTimes = true; + + +//Serial from mcu +//initial data +int samples; +int event; +int initialState[]= new int[3]; +boolean first = false; +boolean dataComplete = false; +//following data +boolean [][][] state; +boolean [][] isLow = new boolean[8][3]; +boolean [][] isLowinit = new boolean[8][3]; +float[] usTime; +float[] xTime; +int[][] pinChanged; +int[] PinAssignment = new int[16]; +int[] PinArduinoNames = new int[16]; +int index1; +int index2; +int index3; +boolean refresh= true; +int []cursora= new int[2]; +float cursoraf= 0; +boolean cursorplay=false; + + + +/* +ENGLISH +How the assign of the pins works?. +The entries will be depleted in the order they appear in the whole PinAssignment that goes from 0 to 15 for a total of 16, the value of the integer in each position will +reference the pin to be used. Then the value that must be entered in the integer will be shown to observe the desired pin. + +In case you do not want to show anything on that channel, just assign 00 so that the channel will not be written. +The pins that do not appear in the table can not be used because they were not considered in the arduino programming, to avoid overloading the +arduino and obtain more satisfactory response times. + +SPANISH +Funcionamiento de la asignacion de pines. +Las entradas se deplegaran en el orden que aparezcan en el entero PinAssignment que va del 0 al 15 para un total de 16, el valor del entero en cada posicion referenciara +el pin a utilizar. A continuacion se mostrara el valor que se debe introducir en el entero para observar el pin deseado. + +En caso de no querer mostrar nada en ese canal basta con asignar 00 para que el canal no sea escrito. +Los pines que no aparecen en la tabla no podrán ser utilizados por que no fueron considerados en la programacion de arduino, esto para evitar sobrecargar al +arduino y obtener tiempos de respuesta más satisfactorios. + +EN Number of Pin in the Arduino UNO Number to enter in the PinAssignment +ES Numero de Pin en el Arduino UNO Numero a introducir en el PinAssignment +Digital PIN 8 -------------------------------------------------------> 10 +Digital PIN 9 -------------------------------------------------------> 11 +Digital PIN 10 -------------------------------------------------------> 12 +Digital PIN 11 -------------------------------------------------------> 13 +Digital PIN 12 -------------------------------------------------------> 14 +Digital PIN 13 -------------------------------------------------------> 15 + + + +*/ + +//buttons and others +int button1X = 8; +int button2X = 8; +int button3X = 80; +int button4X = 200; +int button5X = 270; +int buttonY; +int buttonH = 20; +int smallButtonW = 50; +int bigButtonW = 100; +int graphBoxH; +int textBoxH; +int immage = 1; +int corner = 10; +String s; +boolean initial=true; + +// bar scroll +int handleFill = grey; +float handleX; +float handleY; +float handleW = 20; +float handleH = 15; +boolean isDraggable = false; + + + +void setup () { + //p = new Serial(this, Serial.list()[0], 115200); + p = new Serial(this, LA_port, baudrate); + p.bufferUntil('\n'); + + size(1300, 700); + background(black); + smooth(4); + xShift=(width-handleW)/2; + //Here you chose the pins that yuo want to show in the Logic Analizer. Put 00 to OFF the channel. + //Aquí escoges los pines que quieres desplegar. + PinAssignment[0] = 10; + PinAssignment[1] = 11; + PinAssignment[2] = 12; + PinAssignment[3] = 13; + PinAssignment[4] = 14; + PinAssignment[5] = 15; + PinAssignment[6] = 00; + PinAssignment[7] = 00; + PinAssignment[8] = 00; + PinAssignment[9] = 00; + PinAssignment[10]= 00; + PinAssignment[11]= 00; + PinAssignment[12]= 00; + PinAssignment[13]= 00; + PinAssignment[14]= 00; + PinAssignment[15]= 00; + + for (int i=0; i<16; i++) { + switch (PinAssignment[i]) { + case (10): + PinArduinoNames[i]=08; + break; + case (11): + PinArduinoNames[i]=09; + break; + case (12): + PinArduinoNames[i]=10; + break; + case (13): + PinArduinoNames[i]=11; + break; + case (14): + PinArduinoNames[i]=12; + break; + case (15): + PinArduinoNames[i]=13; + break; + default: + PinArduinoNames[i]=00; + break; + + } + } + graphBoxH = height -50; + textBoxH = height - 35; + yBottom = graphBoxH-20; + buttonY = textBoxH +8; + handleX = xEdge; + handleY = graphBoxH; +} + + +void cleanGraph() { + noStroke(); //no borders + fill(black); + rect(xEdge, 0, width, graphBoxH); //cancel the graph + stroke(green); //green lines + Arrays.fill(xPos, 0); //reset start point of the graph + textCovered = false; +} + + +void draw() { + + if (dataComplete==true) { + cleanGraph(); + pushMatrix(); //move the coordinate reference + translate(xEdge, 0); + float firstchange; + boolean cares; + if (cursorplay){ + fill(50); + stroke(75); + if(cursora[1]==16){ //Esta variable la utilizamos para definir el canal sobre el cual estamos trabajando, en esta parte marcamos el rectangulo en el que trabajamos. + rect(0, yBottom-12, width-xEdge, 34); + } + else{ + rect(0, yEdge+36*cursora[1]-2, width-xEdge, 34); + } + stroke(green); + } + updatepos(); //Se encarga de decir que segmento de tiempos se va a escribir + for (int i=0; i// + yDiff=yPos; + yPos+=30; + + } else { + yDiff=yPos+30; + } + isLow[index1][index2]=isLowinit[index1][index2]; + //println(isLowinit[index1][index2]); + } + else { + if (isLow[index1][index2]) { //pin high else low + yDiff=yPos; + yPos+=30; + isLow[index1][index2]=false; + } else { + yDiff=yPos+30; + isLow[index1][index2]=true; + } + } + + + + // Graph lines + line(xPos[n]+xShift, yPos, xTime[i]+xShift, yPos); // straight line + line(xTime[i]+xShift, yPos, xTime[i]+xShift, yDiff); // vertical line + + xPos[n]=xTime[i]; //save last position of the line for the pin + yPos = ySave; //load the initial value of the y + } + } + yPos+=36; //go to the next pin + } + // Text times + if ((drawTimes && cares)||i==0) { + if (cursora[0]==i){ + stroke(red); + fill(red); + }else{ + stroke(grey); + fill(grey); + } + textSize(10); + textCovered=!textCovered; + dashline(xTime[i]+xShift, firstchange, xTime[i]+xShift, yBottom, spacing); + text(round(usTime[i]), xTime[i]+xShift+2, (textCovered==true) ? yBottom : yBottom+10); //write on different height + stroke(green); + } + } + + yPos = yEdge; + for (int n = 0; n < 16; n++) { + if (PinAssignment[n]!=0){ + s= str(PinAssignment[n]); + index1 = s.charAt(1)-'0'; + index2 = s.charAt(0)-'1'; + if (xPos[n]==0) { + if (isLowinit[index1][index2]==true) line(xPos[n]+xShift, yPos+30, xEnd+xShift, yPos+30); + else line(xPos[n]+xShift, yPos, xEnd+xShift, yPos); + } + + } + yPos+=36; + } + dataComplete = false; + popMatrix(); + } + drawText(); +} + + +void drawText() { + stroke(white); //white borders + fill(black); + rect(0, 0, xEdge, graphBoxH); //clean left side + rect(xEdge, graphBoxH, width, handleH); //clean bar scroll + rect(0, textBoxH, width, height); //clean bottom side + + + // write name of the pins + fill(white); + textSize(14); + + int x=5; + int y=30; + + /* if (STM32) { + + for (byte i = 12; i<=15; i++) { + line(x, y-20, xEdge, y-20); + line(x, y+10, xEdge, y+10); + text ("PB"+i, x, y); + y+=60; + } + } else { +*/ + for (byte i = 0; i<16; i++) { + line(x, y-20, xEdge, y-20); + line(x, y+10, xEdge, y+10); + stroke(#EF7F1A); + dashline(xEdge, y-23 , width, y-23, spacingnew); + dashline(xEdge, y+13 , width, y+13, spacingnew); + stroke(white); + if (PinArduinoNames[i]==0){ + text ("Pin "+ "OFF", x, y);} + else{ + text ("Pin "+ str(PinArduinoNames[i]), x, y); + } + y+=36; + + } + + // draw buttons + fill(grey); + + rect(button1X, yBottom-15, smallButtonW, buttonH, corner); + rect(button2X, buttonY, smallButtonW, buttonH, corner); + rect(button3X, buttonY, bigButtonW, buttonH, corner); + rect(button4X, buttonY, smallButtonW, buttonH, corner); + rect(button5X, buttonY, smallButtonW, buttonH, corner); + fill(white); + + text("Start", button2X+3, buttonY+14); + + text(reducer, button4X, buttonY+14); + text("Save", button5X+3, buttonY+14); + text(milliseconds == true ? "milliseconds" : "microseconds", button3X+3, buttonY+14); + text("T:"+ str (drawTimes), button1X+3, yBottom); + //bar scroll + fill(handleFill); + rect(handleX, handleY, handleW, handleH); + + if (isDraggable) { + handleX = mouseX-handleW/2; + if (handleXwidth-handleW) handleX = width-handleW; + updatepos(); + dataComplete = true; + + + } + +} + + +void mousePressed() { + if (mouseX>xEdge && mouseXhandleY && mouseYxTime[samples-1]){ + if (cursoraf<=0){ + cursora[0]=0; + } + if (cursoraf>=xTime[samples-1]){ + cursora[0]=samples-1; + } + }else{ + for (int i=1; iabs(xTime[i+1]-cursoraf)&&state[i][index1][index2]){ + if (abs(xTime[i]-cursoraf)>abs(xTime[i+1]-cursoraf)){ + if(state[i][index1][index2]){ + cursora[0]=i; + } + }else { + break; + } + //println (abs(xTime[i]+xShift)); + //println ("wut"); + } + } + } + println( cursora[0]); + dataComplete=true; +} +void updatepos(){ + if (samples!=0) { + xEnd = (xTime[samples-1]); + // xEnd = xEnd + } else { + xEnd = 0; + } + xShift = -map(handleX, xEdge, width-handleW, 0, xEnd); + xShift = xShift + (width-handleW)/2; + +} + +void movepos(){ + xShift = xTime[cursora[0]]; + handleX = map(xShift, 0, xEnd, xEdge, width-handleW); + xShift = -xShift - (width-handleW)/2; +dataComplete=true; + +} + +void keyPressed() { + int number; + if (key == CODED) { + if (keyCode == UP && cursorplay) { + number=cursora[1]; + cursora[1]= cursora[1]-1; + for (int i=cursora[1]; i>=0; i--){ + if (PinAssignment[cursora[1]]==0){ + cursora[1]= cursora[1]-1; + }else { + break; + } + } + if (cursora[1]==-1){ + cursora[1]= number; + } + cursora[1]=constrain(cursora[1], 0, 16); + //println("cur1 "+cursora[1]+"cur0 "+cursora[0]); + dataComplete=true; + } else if (keyCode == DOWN && cursorplay) { + if(cursora[1]<16){ + cursora[1]= cursora[1]+1; + for (int i=cursora[1]; i<16; i++){ + if (PinAssignment[cursora[1]]==0){ + cursora[1]= cursora[1]+1; + }else { + break; + } + + cursora[1]=constrain(cursora[1], 0, 16); + } } + //println("cur1 "+cursora[1]+"cur0 "+cursora[0]); + dataComplete=true; + } else if (keyCode == RIGHT && cursorplay) { + if (cursora[1]==16){ + if (cursora[0]!=samples-1){ + cursora[0]+=1; + } + } + else{ + s = str(PinAssignment[cursora[1]]); + index1 = s.charAt(1)-'0'; + index2 = s.charAt(0)-'1'; + //println(cursora[0]); + for (int i=cursora[0]+1; i-1; i--){ + cursora[0]=i; + if (state[i][index1][index2]){ + break; + }else { + + } } + } + //println("cur1 "+cursora[1]+"cur0 "+cursora[0]); + //updatepos(); + movepos(); + }else if (keyCode == LEFT && !cursorplay) { + handleX-=1; + if (handleXwidth-handleW) handleX = width-handleW; + dataComplete=true; + }else if (keyCode == RIGHT && !cursorplay) { + handleX+=1; + if (handleXwidth-handleW) handleX = width-handleW; + dataComplete=true; + } + } +} + +void mouseClicked() { + + // bootons over signals + if(mouseX>xEdge && mouseX yBottom-15 && mouseY xEdge && mouseX yEdge && mouseY xEdge && mouseX yEdge+36 && mouseY xEdge && mouseX yEdge+36*2 && mouseY xEdge && mouseX yEdge+36*3 && mouseY xEdge && mouseX yEdge+36*4 && mouseY xEdge && mouseX yEdge+36*5 && mouseY xEdge && mouseX yEdge+36*6 && mouseY xEdge && mouseX yEdge+36*7 && mouseY xEdge && mouseX yEdge+36*8 && mouseY xEdge && mouseX yEdge+36*9 && mouseY xEdge && mouseX yEdge+36*10 && mouseY xEdge && mouseX yEdge+36*11 && mouseY xEdge && mouseX yEdge+36*12 && mouseY xEdge && mouseX yEdge+36*13 && mouseY xEdge && mouseX yEdge+36*14 && mouseY xEdge && mouseX yEdge+36*15 && mouseY yBottom-15 && mouseY button1X && mouseX buttonY && mouseY button2X && mouseX buttonY && mouseY button5X && mouseX buttonY && mouseY button4X && mouseX 90 && !milliseconds){ + reducer=0.1; + milliseconds = !milliseconds; + } + reducer = constrain(reducer, 0.1, 100); + } else { //move the graph + if (reducer<=1){ + reducer-= 0.1; + }else if (reducer<=10){ + reducer-=1; + }else { + reducer-=10; + } + if (reducer<0.1 && milliseconds){ + reducer=100; + milliseconds = !milliseconds; + } + reducer = constrain(reducer, 0.1, 90); + } + scaletime(); + updatepos(); + dataComplete=true; + } else + // micro or millis + if (mouseY>buttonY && mouseY button3X && mouseX width-handleW) handleX = width-handleW; + dataComplete=true; + +} + + +void mouseMoved() { + if (mouseY>buttonY && mouseY button2X && mouseX buttonY && mouseY button3X && mouseX buttonY && mouseY button5X && mouseX buttonY && mouseY button4X && mouseX yBottom-15 && mouseY button1X && mouseX handleX && mouseXhandleY && mouseYxEdge && mouseX yBottom-15 && mouseY xEdge && mouseX yEdge && mouseY xEdge && mouseX yEdge+36 && mouseY xEdge && mouseX yEdge+36*2 && mouseY xEdge && mouseX yEdge+36*3 && mouseY xEdge && mouseX yEdge+36*4 && mouseY xEdge && mouseX yEdge+36*5 && mouseY xEdge && mouseX yEdge+36*6 && mouseY xEdge && mouseX yEdge+36*7 && mouseY xEdge && mouseX yEdge+36*8 && mouseY xEdge && mouseX yEdge+36*9 && mouseY xEdge && mouseX yEdge+36*10 && mouseY xEdge && mouseX yEdge+36*11 && mouseY xEdge && mouseX yEdge+36*12 && mouseY xEdge && mouseX yEdge+36*13 && mouseY xEdge && mouseX yEdge+36*14 && mouseY xEdge && mouseX yEdge+36*15 && mouseY 0) + { + int i; + boolean drawLine = true; // alternate between dashes and gaps + + /* + Figure out x and y distances for each of the spacing values + I decided to trade memory for time; I'd rather allocate + a few dozen bytes than have to do a calculation every time + I draw. + */ + + for (i = 0; i < spacing.length; i++) + { + xSpacing[i] = lerp(0, (x1 - x0), spacing[i] / distance); + ySpacing[i] = lerp(0, (y1 - y0), spacing[i] / distance); + } + + i = 0; + while (drawn < distance) + { + if (drawLine) + { + line(x0, y0, x0 + xSpacing[i], y0 + ySpacing[i]); + } + x0 += xSpacing[i]; + y0 += ySpacing[i]; + /* Add distance "drawn" by this line or gap */ + drawn = drawn + mag(xSpacing[i], ySpacing[i]); + i = (i + 1) % spacing.length; // cycle through array + drawLine = !drawLine; // switch between dash and gap + } + } +} diff --git a/Microcontroller_Code/UNO/UNO_newmod.ino b/Microcontroller_Code/UNO/UNO_newmod.ino new file mode 100644 index 0000000..426ef4d --- /dev/null +++ b/Microcontroller_Code/UNO/UNO_newmod.ino @@ -0,0 +1,139 @@ +/* + * UNO.ino + * + * Created: 11/12/2016 19.35.51 + * Author : Vincenzo + * Led on A0 + */ + +#define baudrate 115200 // check if it is the same in processing +#define samples 200 // the number of samples you want to take +#define timezerooffset 125 //microsegundos +#define F_CPU 16000000UL +#include +#include +#include +#define prescaler 0x02 +volatile uint16_t timer1_overflow_count; + +uint8_t initial, state, old_state; +uint8_t pinChanged[samples]; +uint32_t timer[samples]; +uint32_t timefix; +uint16_t event = 0; + +void init_board() { + + PORTC = (0 << 0); DDRC |= (1 << 0); // led A0 + DDRB |= 0x00; // pin 8-13 input + PORTB |= 0x3F; // pull-up + +} + +void init_timer() { + + //clear + TCCR1A = 0b00000000; + TCCR1B = 0b00000000; + TIMSK1 = 0b00000000; + + //settings + TCCR1A |= (0 << COM1A1) | (0 << COM1A0) | (0 << COM1B1) | (0 << COM1B0); //normal port operation + TCCR1A |= (0 << WGM11) | (0 << WGM10); //normal operation + TCCR1B |= (0 << WGM13) | (0 << WGM12); //normal operation + TCCR1B |= prescaler; //(0 << CS12) | (0 << CS11) | (1 << CS10); //clock prescaler + + sei(); //enable interrupts + TIMSK1 |= (1 << TOIE1); // enable overflow interrupt + +} + +ISR(TIMER1_OVF_vect) { + timer1_overflow_count++; +} + +void reset_timer1 () { + TCNT1 = 0; + timer1_overflow_count = 0; +} + +uint32_t myMicros () { + cli(); + + if (TIFR1 & (1 << TOV1)) { + TIFR1 = (0 << TOV1); + timer1_overflow_count++; + } + + uint32_t total_time = (65536 * timer1_overflow_count + TCNT1) / 2; + sei(); + return total_time; +} + +void start() { + _delay_ms(1000); + + reset_timer1(); + event = 0; + + PORTC = (1 << 0); + initial = PINB; + state = initial; + for (int i=0; i < samples; i++) { + pinChanged[i]=0; + + } +} + + +void sendData() { + PORTC = (0 << 0); //turn off led + + //initial data + Serial.println("S"); + Serial.print(initial); Serial.print(','); Serial.print(B11111111); Serial.print(','); Serial.print(B11111111); Serial.print(":"); + Serial.println(samples+3); + timefix = -timer[0]+timezerooffset; + for (int i = 0; i < samples; i++) { + timer[i]=timer[i]+timefix; + } + Serial.print(B11111111);Serial.print(','); Serial.print(B11111111); Serial.print(','); Serial.print(B11111111); Serial.print(":");//Este segmento de codigo introduce un cambio en todos los + Serial.println(0); //canales, lo que soluciona un error en el codigo en processing + Serial.print(B11111111);Serial.print(','); Serial.print(B11111111); Serial.print(','); Serial.print(B11111111); Serial.print(":");//al final se hace un cambio en todos los canales, lo que soluciona + Serial.println(1); //otro pequeño fallo visual. + //data + for (int i = 0; i < samples; i++) { + Serial.print(pinChanged[i]);Serial.print(','); Serial.print(B00000000); Serial.print(','); Serial.print(B00000000); Serial.print(":"); + Serial.println(timer[i]); + } + Serial.print(B11111111);Serial.print(','); Serial.print(B11111111); Serial.print(','); Serial.print(B11111111); Serial.print(":"); + Serial.println((timer[samples-1]+400)); +} + + +int main(void) { + Serial.begin(baudrate); + + init_board(); + init_timer(); + + start(); + + while (1) { + + old_state = state; + state = PINB; + + if (old_state != state) { + timer[event] = myMicros(); + pinChanged[event] = state ^ old_state; + event++; + + if (event == samples) { + sendData(); + while (Serial.read() != 'G') ; //wait for the "go" + start(); + } + } + } +}