An Alternative Arduino Sonar Using HCSR-04

Hello everyone! I have a couple of questions for you and I would really appreciate it if you could give some answers.

For my project I'm trying to determine the size,distance and speed of an approaching object and put all the data on screen. For the size and distance part I'm using the code below - using Arduino IDE and Processing - but I couldn't figure out how to derive the speed aspect of the object.

1)Could you help me or share some ideas about how to measure speed and put it on the screen?

2)Is it possible to do it using the same Arduino Mega by altering the Arduino and Processing codes?

3)Also is it possible to integrate an Ov7670 to take a picture of the object under a specific distance value? And again is it possible to do it using the same tools and altering the codes?

Here are the codes and the picture of the system output. (Sorry that the comment sections are in Turkish):

Arduino Code:

// Servo kütüphanesi
#include <Servo.h> 
// Ultrasonik sensörün trigger ve echo pinleri
const int trigPin = 10;
const int echoPin = 11;
// duration ve distance değişkenleri
long duration;
int distance;
Servo myServo; // servo kontrolü için bir servo objesi yaratıldı
void setup() {
  pinMode(trigPin, OUTPUT); // trigPin çıkış olarak tanımlandı
  pinMode(echoPin, INPUT); // echoPin giriş olarak tanımlandı
  Serial.begin(9600);
  myServo.attach(12); // Servonun bağlı olduğu pin
}
void loop() {
  // servo motoru 60 - 120 derecelik açılar arası döndür
  for(int i=60;i<=120;i++){  
  myServo.write(i);
  delay(30);
  distance = calculateDistance();// her derece için ultrasonik sensörün ölçtüğü mesafeyi hesaplayan fonksiyon
  
  Serial.print(i); // mevcut açıyı serial porta yolla
  Serial.print(","); // processing de değerler arasına konulacak karakter
  Serial.print(distance); // mesafe değerini serial porta yolla
  Serial.print("."); // processing de değerler arasına konulacak karakter
  }
  // aynı işlemleri geri dönerken de yap
  for(int i=120;i>60;i--){  
  myServo.write(i);
  delay(30);
  distance = calculateDistance();
  Serial.print(i);
  Serial.print(",");
  Serial.print(distance);
  Serial.print(".");
  }
}
// ultrasonik sensörün ölçtüğü mesafeyi hesaplayan fonksiyon
int calculateDistance(){ 
  
  digitalWrite(trigPin, LOW); 
  delayMicroseconds(2);
  // trigPin i 10 ms için HIGH yap
  digitalWrite(trigPin, HIGH); 
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH); // echoPin den değer oku,ses dalgasının yol alma süresini ms e çevir
  distance= duration*0.034/2;
  return distance;
}

Processing Code:

import processing.serial.*; // seri haberleşme kütüphanesi
import java.awt.event.KeyEvent; // seri porttan veri okuma kütüphanesi
import java.io.IOException;
Serial myPort; // seri obje tanımı
// değişken tanımlamaları
String angle="";
String distance="";
String data="";
String noObject;
float pixsDistance;
int iAngle, iDistance;
int index1=0;
int index2=0;

void setup() {
  
 size (800, 600); // ekran çözünürlüğü
 smooth();
 myPort = new Serial(this,"COM9", 9600); // seri haberleşmeye başla
 myPort.bufferUntil('.'); // Seri porttan '.' karakterine kadar değer oku. örneğin: angle,distance.
 
}
void draw() {
  
  fill(98,245,31);
  
  // hareket çizgisinin hareketlerini belirle
  noStroke();
  fill(0,4); 
  rect(0, 0, width, height-height*0.065); 
  
  fill(98,245,31); // yeşil renk
  // radarı çizmek için fonksiyonları çağır
  drawRadar(); 
  drawLine();
  drawObject();
  drawText();
}
void serialEvent (Serial myPort) { // seri porttan veri oku
  // Seri porttan '.' karakterine kadar değer oku ve "data" değişkenie ata.
  data = myPort.readStringUntil('.');
  data = data.substring(0,data.length()-1);
  
  index1 = data.indexOf(","); //  ',' karakterini bul ve "index1" değişkenine koy
  angle= data.substring(0, index1); // "0" konumundan index1 in konumuna kadar veri oku ve açı değeri olarak seri porta yolla
  distance= data.substring(index1+1, data.length()); //  "index1" in konumundan "data" nın konumuna kadar veri oku ve mesafe olarak seri porta yolla
  
  // string değerlerini integer a çevir
  iAngle = int(angle);
  iDistance = int(distance);
}
void drawRadar() {
  pushMatrix();
  translate(width/2,height-height*0.074); // başlangıç koordinatlarını yeni konuma taşı
  noFill();
  strokeWeight(2);
  stroke(98,245,31);
  // yay çizgilerinin çizilmesi
  arc(0,0,(width-width*0.0625),(width-width*0.0625),PI,TWO_PI);
  arc(0,0,(width-width*0.27),(width-width*0.27),PI,TWO_PI);
  arc(0,0,(width-width*0.479),(width-width*0.479),PI,TWO_PI);
  arc(0,0,(width-width*0.687),(width-width*0.687),PI,TWO_PI);
  // açı çizgilerini çiz
  line(-width/2,0,width/2,0);
  line(0,0,(-width/2)*cos(radians(30)),(-width/2)*sin(radians(30)));
  line(0,0,(-width/2)*cos(radians(60)),(-width/2)*sin(radians(60)));
  line(0,0,(-width/2)*cos(radians(90)),(-width/2)*sin(radians(90)));
  line(0,0,(-width/2)*cos(radians(120)),(-width/2)*sin(radians(120)));
  line(0,0,(-width/2)*cos(radians(150)),(-width/2)*sin(radians(150)));
  line((-width/2)*cos(radians(30)),0,width/2,0);
  popMatrix();
}
void drawObject() {
  pushMatrix();
  translate(width/2,height-height*0.074); // başlangıç koordinatlarını yeni konuma taşı
  strokeWeight(9);
  stroke(255,10,10); // kırmızı renk
  pixsDistance = iDistance*((height-height*0.1666)*0.025); // sensörden alınan mesafe değerini cm den piksele çevir
  // range i 40 cm belirle
  if(iDistance<40){
    // açı ve mesafeye göre objeyi çiz
  line(pixsDistance*cos(radians(iAngle)),-pixsDistance*sin(radians(iAngle)),(width-width*0.505)*cos(radians(iAngle)),-(width-width*0.505)*sin(radians(iAngle)));
  }
  popMatrix();
}
void drawLine() {
  pushMatrix();
  strokeWeight(9);
  stroke(30,250,60);
  translate(width/2,height-height*0.074); // başlangıç koordinatlarını yeni konuma taşı
  line(0,0,(height-height*0.12)*cos(radians(iAngle)),-(height-height*0.12)*sin(radians(iAngle))); // açıya göre çizgi çek
  popMatrix();
}
void drawText() { // text leri ekrana ver
  
  pushMatrix(); // Referans 40 cm değerine göre menzil durumunu belirle
  if(iDistance>40) {
  noObject = "Menzil Dışı";
  }
  else {
  noObject = "Menzilde";
  }
  fill(0,0,0);
  noStroke();
  rect(0, height-height*0.0648, width, height);
  fill(98,245,31);
  textSize(12);
  
  //Ekranda buluan yazıların ayarlamaları
  text("10cm",width-width*0.3854,height-height*0.0833);
  text("20cm",width-width*0.281,height-height*0.0833);
  text("30cm",width-width*0.177,height-height*0.0833);
  text("40cm",width-width*0.0729,height-height*0.0833);
  textSize(12);
  text("Araç: " + noObject, width-width*0.875, height-height*0.0277);
  text("Açı: " + iAngle +" °", width-width*0.48, height-height*0.0277);
  text("Mesafe: ", width-width*0.26, height-height*0.0277);
  if(iDistance<40) {
  text("        " + iDistance +" cm", width-width*0.225, height-height*0.0277);
  }
  textSize(12);
  fill(98,245,60);
  translate((width-width*0.4994)+width/2*cos(radians(30)),(height-height*0.0907)-width/2*sin(radians(30)));
  rotate(-radians(-60));
  text("30°",0,0);
  resetMatrix();
  translate((width-width*0.503)+width/2*cos(radians(60)),(height-height*0.0888)-width/2*sin(radians(60)));
  rotate(-radians(-30));
  text("60°",0,0);
  resetMatrix();
  translate((width-width*0.507)+width/2*cos(radians(90)),(height-height*0.0833)-width/2*sin(radians(90)));
  rotate(radians(0));
  text("90°",0,0);
  resetMatrix();
  translate(width-width*0.513+width/2*cos(radians(120)),(height-height*0.07129)-width/2*sin(radians(120)));
  rotate(radians(-30));
  text("120°",0,0);
  resetMatrix();
  translate((width-width*0.5104)+width/2*cos(radians(150)),(height-height*0.0574)-width/2*sin(radians(150)));
  rotate(radians(-60));
  text("150°",0,0);
  popMatrix(); 
}

Are you physically rotating the SR04 sensor to build your 'radar' picture ? Maybe attach a picture of your set up.
Speed is simply distance (meters) divided by time (seconds) so if say an object travels 1.5 meters in half a second, its speed is 3 meters per second.

Yes I use a servo motor to rotate the sensor. Here is the picture of the system.

Speed is indeed quite straightforward, change in distance over time.

How do you determine the SIZE of the object? That's what I'm curious about as it's not trivial, and I don't see it in your code.

As you look at the radar picture in my first message in the attachment section, as an object stays within sight of the sensor, red bars lay together. So by amount of the red bars, I know whether it's a thin or wide object.

The sensor's beam is MUCH wider than that, about a 30 degree cone.