Arduino Led e Velocità Motore GUI

togli a= arduino.readStringUntil('\n');

e

fill(125);

la text va messa nella funzione draw()

Così dunque:

import processing.serial.*;
int width = 800;
int height = 600;
String inByte;
String a;
int button1X;
int button1Y;
int button1Width = width/10;
int button1Height = height/20;
int button2X;
int button2Y;
int button3X;
int button3Y;
int button2Width = button1Width;
int button2Height = button1Height;
int button3Width = button1Width;
int button3Height = button1Height;
float buttonFont = button1Height/1.5;
float wordFont = button1Height;




Serial arduino;
color buttonColor, buttonHighlight, buttonPressed;

PFont font;

boolean button1Over = false;
boolean button2Over = false;
boolean button3Over = false;
void setup() {
  
  size(width,height);
  smooth();
  font = loadFont("CourierNew36.vlw"); 
  buttonColor = color(255);
  buttonHighlight = color(200);
  buttonPressed = color(50);
  button1X = width/10 - button1Width/2;
  button1Y = height/5 - button1Height/2;
  button2X = 2*width/10 - button1Width/2;
  button2Y = height/5 - button1Height/2;
    button3X = 3*width/10 - button1Width/2;
  button3Y = height/5 - button1Height/2;
  arduino = new Serial(this,"COM3", 9600);
    arduino.bufferUntil('\n'); // SerialEvent for new line 
  arduino.clear();
}

void draw() {
  
  update(mouseX,mouseY);
  background(0);
  
  if(button1Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button1X,button1Y, button1Width, button1Height);
  
  if(button2Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button2X,button2Y, button2Width, button2Height);
  
  
    if(button3Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button3X,button3Y, button3Width, button3Height);
  
  textFont(font, buttonFont);
  fill(0);
  text("On t",button1X + button1Width/3.9,button1Y + button1Height/1.3);
  text("On nt",button2X + button1Width/10.9,button1Y + button1Height/1.3);
    text("Off nt",button3X + button1Width/10.9,button1Y + button1Height/1.3);

      while (arduino.available () > 0) {
inByte = arduino.readStringUntil('\n'); 
if ( inByte != null ) {
   synchronized(a){
      a = inByte;
      }
  synchronized(a){
        text(a,width/2, height/2);
        }
          }
}

  textFont(font, wordFont);
  fill(255);
  text("Accendi/Spegni Led ",button3X + button1Width + width/20,button1Y + button1Height/1.2);
}

///////////////////////////////////

void update(int x, int y) {
  
  if(overButton(button1X,button1Y,button1Width,button1Height)){
    button1Over = true;
  } else {
    button1Over = false;
  }
  if(overButton(button2X,button2Y,button2Width,button2Height)){
    button2Over = true;
  } else {
    button2Over = false;
  }
  if(overButton(button3X,button3Y,button3Width,button3Height)){
    button3Over = true;
  } else {
    button3Over = false;
  }
}

void mousePressed() {
  
  if(button1Over) {
    println("Button1 pressed");
    arduino.write('S');
    fill(buttonPressed);
    rect(button1X,button1Y, button1Width, button1Height);
  }
  if(button2Over) {
    println("Button2 pressed");
     arduino.write('N');
    fill(buttonPressed);
    rect(button2X,button2Y, button2Width, button2Height);
  }
  if(button2Over) {
    println("Button3 pressed");
     arduino.write('Z');
    fill(buttonPressed);
    rect(button3X,button3Y, button3Width, button3Height);
  }
}

boolean overButton(int x, int y, int width, int height) {
  
  if(mouseX >= x && mouseX <= x+width && mouseY >= y && mouseY <= y+height) {
    return true;
  } else {
    return false;
  }
  
}
void serialEvent (Serial arduino) {
  // get the byte:

  // print it:
 // println(inByte);
  // at the edge of the screen, go back to the beginning:
}

no allora chiariamo le cose.
Tu hai 2 thread, ovvero 2 "programmi" in parallelo su processing.
Uno ha il loop che si chiama appunto loop() come su arduino, che non stai usando (infatti manca mi pare, ma va bene così. Quà vanno messe tutte le operazioni logiche.
Uno si chiama draw() e viene chiamato quando bisogna aggiornare la finestra. Qua vanno messe SOLO le operazioni di disegno. Niente letture seriali o boiate del fenere.

In oltre ci sono degli eventi, ovvero funzioni che sono chiamate quando succede qualcosa. In questo caso "void serialEvent (Serial arduino) {"

quindi nell'evento seriale leggi la seriale e metti il risultato in una stringa (nel tuo caso "a").

il draw semplicemente stampa "a", nient'altro. se poi in "a" c'è un valore messo da seriale o il numero seriale di windows la fuunzione draw se ne deve fregare.

PERCHE?

perchè se la seriale si impalla (prova a staccare arduino), se fai come dico io la grafica è INDIPENDENTE dalla seriale e puoi chiudere/continuare ad usare il tuo programma... col tuo sistema anche la grafica si impalla e devi uccidere il programma da taskmanager.

altro esempio è se "a" fosse un'elaborazione pesante, l'immagine della finestra rimarrebbe congelata e non responsiva... non ti è mai capitato? bene, sappi che quello è un errore di strutturazione, o di architettura del programma.

kiss

Lesto ti chiederei troppo se ti chiedessi di fare i due pezzi di codice che mi servirebbero a prendere questi dati da arduino? Per piacere ne sto uscendo pazzo :astonished: :astonished:

Ho provato a modificare il codice in questo modo

import processing.serial.*;
int width = 800;
int height = 600;
String inByte = null;
String a;
int lf = 10; 
int button1X;
int button1Y;
int button1Width = width/10;
int button1Height = height/20;
int button2X;
int button2Y;
int button3X;
int button3Y;
int button2Width = button1Width;
int button2Height = button1Height;
int button3Width = button1Width;
int button3Height = button1Height;
float buttonFont = button1Height/1.5;
float wordFont = button1Height;




Serial arduino;
color buttonColor, buttonHighlight, buttonPressed;

PFont font;

boolean button1Over = false;
boolean button2Over = false;
boolean button3Over = false;
void setup() {
  
  size(width,height);
  smooth();
  font = loadFont("CourierNew36.vlw"); 
  buttonColor = color(255);
  buttonHighlight = color(200);
  buttonPressed = color(50);
  button1X = width/10 - button1Width/2;
  button1Y = height/5 - button1Height/2;
  button2X = 2*width/10 - button1Width/2;
  button2Y = height/5 - button1Height/2;
    button3X = 3*width/10 - button1Width/2;
  button3Y = height/5 - button1Height/2;
  arduino = new Serial(this,"COM3", 9600);
    arduino.bufferUntil('\n'); // SerialEvent for new line 
  arduino.clear();
}


void draw() {
  
  update(mouseX,mouseY);
  background(0);
  
  if(button1Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button1X,button1Y, button1Width, button1Height);
  
  if(button2Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button2X,button2Y, button2Width, button2Height);
  
  
    if(button3Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button3X,button3Y, button3Width, button3Height);
  
  textFont(font, buttonFont);
  fill(0);
  text("On t",button1X + button1Width/3.9,button1Y + button1Height/1.3);
  text("On nt",button2X + button1Width/10.9,button1Y + button1Height/1.3);
    text("Off nt",button3X + button1Width/10.9,button1Y + button1Height/1.3);

 
synchronized(a){
        text(a,width/2, height/2);
        }
       


  textFont(font, wordFont);
  fill(255);
  text("Accendi/Spegni Led ",button3X + button1Width + width/20,button1Y + button1Height/1.2);
}

///////////////////////////////////

void update(int x, int y) {
  
  if(overButton(button1X,button1Y,button1Width,button1Height)){
    button1Over = true;
  } else {
    button1Over = false;
  }
  if(overButton(button2X,button2Y,button2Width,button2Height)){
    button2Over = true;
  } else {
    button2Over = false;
  }
  if(overButton(button3X,button3Y,button3Width,button3Height)){
    button3Over = true;
  } else {
    button3Over = false;
  }
}

void mousePressed() {
  
  if(button1Over) {
    println("Button1 pressed");
    arduino.write('S');
    fill(buttonPressed);
    rect(button1X,button1Y, button1Width, button1Height);
  }
  if(button2Over) {
    println("Button2 pressed");
     arduino.write('N');
    fill(buttonPressed);
    rect(button2X,button2Y, button2Width, button2Height);
  }
  if(button2Over) {
    println("Button3 pressed");
     arduino.write('Z');
    fill(buttonPressed);
    rect(button3X,button3Y, button3Width, button3Height);
  }
}

boolean overButton(int x, int y, int width, int height) {
  
  if(mouseX >= x && mouseX <= x+width && mouseY >= y && mouseY <= y+height) {
    return true;
  } else {
    return false;
  }
  
}
void serialEvent (Serial arduino) {
inByte =  arduino.readStringUntil(lf);  // Receive one reading from Arduino
  if (inByte != null) {
       synchronized(a){
     a = inByte;
    }
    println(a);
  }
}

leggendo anche un pò il codice di http://scuola.arduino.cc/en/content/how-create-graphical-interface-tinkerkit-gyro-module

con risultato una schermata grigia senza nulla all'interno.
In processing mi da questi errori:

Exception in thread "Animation Thread" java.lang.NullPointerException
	at sketch_130203abbbbbb.draw(sketch_130203abbbbbb.java:107)
	at processing.core.PApplet.handleDraw(PApplet.java:2142)
	at processing.core.PGraphicsJava2D.requestDraw(PGraphicsJava2D.java:193)
	at processing.core.PApplet.run(PApplet.java:2020)
	at java.lang.Thread.run(Thread.java:662)
error, disabling serialEvent() for //./COM3
java.lang.reflect.InvocationTargetException
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
	at java.lang.reflect.Method.invoke(Method.java:597)
	at processing.serial.Serial.serialEvent(Unknown Source)
	at gnu.io.RXTXPort.sendEvent(RXTXPort.java:732)
	at gnu.io.RXTXPort.eventLoop(Native Method)
	at gnu.io.RXTXPort$MonitorThread.run(RXTXPort.java:1575)
Caused by: java.lang.NullPointerException
	at sketch_130203abbbbbb.serialEvent(sketch_130203abbbbbb.java:173)
	... 8 more

(Guarda allegato)

ad occhio

String a;

in

String a="nessun valore ricevuto per ora";

in processing le variabili GLOBALI non inizializzate sono "null"
non sai se a verrà prima inizializzata dalla seriale o prima usata dalla grafica, e la grafica se prova a stanapare una stringa "null" va in errore (infatti hai un "null pointer exception")

Ho messo il codice come dicevi tu

import processing.serial.*;
int width = 800;
int height = 600;
String inByte = null;
String a="nessun valore ricevuto per ora";
int lf = 10; 
int button1X;
int button1Y;
int button1Width = width/10;
int button1Height = height/20;
int button2X;
int button2Y;
int button3X;
int button3Y;
int button2Width = button1Width;
int button2Height = button1Height;
int button3Width = button1Width;
int button3Height = button1Height;
float buttonFont = button1Height/1.5;
float wordFont = button1Height;




Serial arduino;
color buttonColor, buttonHighlight, buttonPressed;

PFont font;

boolean button1Over = false;
boolean button2Over = false;
boolean button3Over = false;
void setup() {
  
  size(width,height);
  smooth();
  font = loadFont("CourierNew36.vlw"); 
  buttonColor = color(255);
  buttonHighlight = color(200);
  buttonPressed = color(50);
  button1X = width/10 - button1Width/2;
  button1Y = height/5 - button1Height/2;
  button2X = 2*width/10 - button1Width/2;
  button2Y = height/5 - button1Height/2;
    button3X = 3*width/10 - button1Width/2;
  button3Y = height/5 - button1Height/2;
  arduino = new Serial(this,"COM3", 9600);
    arduino.bufferUntil('\n'); // SerialEvent for new line 
  arduino.clear();
}


void draw() {
  
  update(mouseX,mouseY);
  background(0);
  
  if(button1Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button1X,button1Y, button1Width, button1Height);
  
  if(button2Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button2X,button2Y, button2Width, button2Height);
  
  
    if(button3Over) {
    fill(buttonHighlight);
  } else {
    fill(buttonColor);
  }
  stroke(0);
  rect(button3X,button3Y, button3Width, button3Height);
  
  textFont(font, buttonFont);
  fill(0);
  text("On t",button1X + button1Width/3.9,button1Y + button1Height/1.3);
  text("On nt",button2X + button1Width/10.9,button1Y + button1Height/1.3);
    text("Off nt",button3X + button1Width/10.9,button1Y + button1Height/1.3);

 
synchronized(a){
        text(a,width/2, height/2);
        }
       


  textFont(font, wordFont);
  fill(255);
  text("Accendi/Spegni Led ",button3X + button1Width + width/20,button1Y + button1Height/1.2);
}

///////////////////////////////////

void update(int x, int y) {
  
  if(overButton(button1X,button1Y,button1Width,button1Height)){
    button1Over = true;
  } else {
    button1Over = false;
  }
  if(overButton(button2X,button2Y,button2Width,button2Height)){
    button2Over = true;
  } else {
    button2Over = false;
  }
  if(overButton(button3X,button3Y,button3Width,button3Height)){
    button3Over = true;
  } else {
    button3Over = false;
  }
}

void mousePressed() {
  
  if(button1Over) {
    println("Button1 pressed");
    arduino.write('S');
    fill(buttonPressed);
    rect(button1X,button1Y, button1Width, button1Height);
  }
  if(button2Over) {
    println("Button2 pressed");
     arduino.write('N');
    fill(buttonPressed);
    rect(button2X,button2Y, button2Width, button2Height);
  }
  if(button2Over) {
    println("Button3 pressed");
     arduino.write('Z');
    fill(buttonPressed);
    rect(button3X,button3Y, button3Width, button3Height);
  }
}

boolean overButton(int x, int y, int width, int height) {
  
  if(mouseX >= x && mouseX <= x+width && mouseY >= y && mouseY <= y+height) {
    return true;
  } else {
    return false;
  }
  
}
void serialEvent (Serial arduino) {
inByte =  arduino.readStringUntil(lf);  // Receive one reading from Arduino
  if (inByte != null) {
       synchronized(a){
     a = inByte;
    }
    println(a);
  }
}

In terminale seriale il valore viene visualizzato ma nella GUI no.Come devo fare? (Guarda immagine in allegato)

Sono riuscito a risolvere il problema usando questo codice qui

// Example by Tom Igoe

import processing.serial.*;

Serial myPort;    // The serial port
PFont myFont;     // The display font
String inString;  // Input string from serial port
int lf = 10;      // ASCII linefeed

void setup() {
  size(400,200);
  // Make your own font. It's fun!
  myFont = loadFont("CourierNew36.vlw");
  textFont(myFont, 18);
  // List all the available serial ports:
  println(Serial.list());
  // Open the port you are using at the rate you want:
  myPort = new Serial(this, Serial.list()[0], 9600);
  myPort.bufferUntil(lf);
}

void draw() {
  background(0);
  text("received: " + inString, 10,50);
}

void serialEvent(Serial p) {
  inString = (myPort.readString());
}

preso dalle guide di Processing disponibile al link http://www.processing.org/reference/libraries/serial/Serial_bufferUntil_.html

Ora quello che io mi chiedo, Mettiamo caso io debba prelevare + dati da + sensori... come organizzo quel codice?Lesto intanto ti ringrazio per l'aiuto e la tua disponibilità, ho già provveduto ad assegnarti il karma.

Nessuno sa aiutarmi?

ora tu prendi una stringa di una riga a la stampi.

Ora, arduino potrebbe stampare tutti i valori su una riga e poi a fine loop andare a capo, così avetsri tutti i valori in una riga.

Poi volendo puoi dividere i valori con una virgola, o con una lettera, in modo che poi lato processing giocando con la stringa (un pò di cerca e taglia, vedi substring e indexOf della classe String), puoi anche estrarre i valori dei vari sensori per poterli visualizzare in posti differenti od animare qualche grafico etc..

potresti farmi un esempio

nessuno sa farmi un esempio?

fai qualche prova da solo, e se non funziona posta il codice che hai usato, cosa ti apsettavi facesse, e cosa invece ha fatto.

Ho provato a modificare il codice così ma non so se e corretto ora non sono in condizione di poter testare.
Arduino:

void displayvalue(){
 pass = digitalRead(A1);
 if(pass != 0)
 {
   car++;
   }

  Serial.println(mph);
  Serial.print(",");
  Serial.println(car);
 delay(1000);      
}

processing:

void serialEvent(Serial p) {
 inString = (myPort.readString());
int sensors[] = int(split(inString, ','));
println(sensors[0]);
println(sensors[1]);
}

Così dovrebbe funzionare?

se al primo giro mph è 11 e car è 22, e al secndo mph è 55 e car 23 otterresti:

11
,22
55
,23

invece, a quanto vedo dal codice processing, ti apsetti di ricevere:

11,22
55,23

devi solo sistemare gli "a capo" nel codice arduino, ricorda che print() stampa i valori SENZA andare a capo, mentre println() stampa i valori andando a capo

per il resto mi aspetto che funzioni

Quindi

void displayvalue(){
 pass = digitalRead(A1);
 if(pass != 0)
 {
   car++;
   }

  Serial.print(mph);
  Serial.print(",");
  Serial.print(car);
 delay(1000);      
}

ora non c'è nessun a capo, quindi la tua riga non avrà mai fine... sempre in base all'esempio precedente avrai

11,2255,23

Quindi

void displayvalue(){
 pass = digitalRead(A1);
 if(pass != 0)
 {
   car++;
   }

  Serial.print(mph);
  Serial.print(",");
  Serial.println(car);
 delay(1000);      
}

ok :grin: